def test_read_w_priority(self): with open('/etc/passwd') as fp: ctx = aio_context_t() io_setup(c_uint(1), pointer(ctx)) self.assertNotEqual(0, ctx.value) len_buf = 64 buf = bytearray(len_buf) arr_t = c_char * len_buf arr_p = cast(arr_t.from_buffer(buf), c_void_p) iocb = IOCB(aio_lio_opcode=IOCBCMD.PREAD, aio_fildes=fp.fileno(), aio_buf=arr_p.value, aio_offset=0, aio_nbytes=len_buf, aio_reqprio=gen_io_priority(IOCBPriorityClass.IDLE, 10), aio_flags=IOCBFlag.IOPRIO) submit_ret = io_submit(ctx, c_long(1), create_c_array(iocb_p, (pointer(iocb),))) self.assertEqual(1, submit_ret) event = IOEvent() get_event_ret = io_getevents(ctx, c_long(1), c_long(1), create_c_array(IOEvent, (event,)), None) self.assertEqual(1, get_event_ret) self.assertEqual(fp.read(len_buf), buf.strip().decode()) io_destroy(ctx)
def test_writev(self): with open('test.txt', 'w+') as fp: ctx = aio_context_t() io_setup(c_uint(1), pointer(ctx)) self.assertNotEqual(0, ctx.value) contents1 = 'This is a long sample text.' len_contents1 = len(contents1) arr_p1 = cast(c_char_p(contents1.encode()), c_void_p) vec1 = IOVec(arr_p1, len_contents1) contents2 = '\nThis is a long sample text 2.' len_contents2 = len(contents2) arr_p2 = cast(c_char_p(contents2.encode()), c_void_p) vec2 = IOVec(arr_p2, len_contents2) vec_arr = create_c_array(IOVec, (vec1, vec2)) iocb = IOCB(aio_lio_opcode=IOCBCMD.PWRITEV, aio_fildes=fp.fileno(), aio_buf=addressof(vec_arr), aio_offset=0, aio_nbytes=2) submit_ret = io_submit(ctx, c_long(1), create_c_array(iocb_p, (pointer(iocb),))) self.assertEqual(1, submit_ret) event = IOEvent() get_event_ret = io_getevents(ctx, c_long(1), c_long(1), create_c_array(IOEvent, (event,)), None) self.assertEqual(1, get_event_ret) fp.seek(0) self.assertEqual(contents1 + contents2, fp.read(len_contents1 + len_contents2)) io_destroy(ctx)
def test_readv(self): with open('/etc/passwd') as fp: ctx = aio_context_t() io_setup(c_uint(1), pointer(ctx)) self.assertNotEqual(0, ctx.value) len_buf1 = 64 buf1 = bytearray(len_buf1) arr_t1 = c_char * len_buf1 arr_p1 = cast(arr_t1.from_buffer(buf1), c_void_p) vec1 = IOVec(arr_p1, len_buf1) len_buf2 = 32 buf2 = bytearray(len_buf2) arr_t2 = c_char * len_buf2 arr_p2 = cast(arr_t2.from_buffer(buf2), c_void_p) vec2 = IOVec(arr_p2, len_buf2) vec_arr = create_c_array(IOVec, (vec1, vec2)) iocb = IOCB(aio_lio_opcode=IOCBCMD.PREADV, aio_fildes=fp.fileno(), aio_buf=addressof(vec_arr), aio_offset=0, aio_nbytes=2) submit_ret = io_submit(ctx, c_long(1), create_c_array(iocb_p, (pointer(iocb),))) self.assertEqual(1, submit_ret) event = IOEvent() get_event_ret = io_getevents(ctx, c_long(1), c_long(1), create_c_array(IOEvent, (event,)), None) self.assertEqual(1, get_event_ret) self.assertEqual(fp.read(len_buf1 + len_buf2), buf1.strip().decode() + buf2.strip().decode()) io_destroy(ctx)
def submit(self, *cmds: AIOCmd) -> Generator[None, None, Tuple[AIOEvent, ...]]: for cmd in cmds: if cmd._deleted: raise ValueError( f'{cmd} can not be used because it has already been transformed into another AIOCmd.' ) submitted_cmd = io_submit( self._ctx, c_long(len(cmds)), create_c_array(iocb_p, (pointer(block._iocb) for block in cmds))) event_buf = create_c_array(IOEvent, (), submitted_cmd) tot_done_jobs = 0 remaining_jobs = submitted_cmd while remaining_jobs is not 0: yield completed_jobs = io_getevents( self._ctx, c_long(0), c_long(remaining_jobs), _io_event_p(event_buf[tot_done_jobs]), None) tot_done_jobs += completed_jobs remaining_jobs -= completed_jobs return tuple(AIOEvent(event) for event in event_buf[:tot_done_jobs])
def test_empty_submit_n_getevents(self): ctx = aio_context_t() io_setup(c_uint(10), pointer(ctx)) self.assertNotEqual(0, ctx.value) ret = io_submit(ctx, c_long(0), create_c_array(iocb_p, (), 0)) self.assertEqual(0, ret) ret = io_getevents(ctx, c_long(0), c_long(100), create_c_array(IOEvent, (), 0), None) self.assertEqual(0, ret) io_destroy(ctx)
def test_submit_with_invalid_ctx(self): with self.assertRaises(OSError) as assertion: with open('/etc/passwd') as fp: iocb = IOCB(aio_lio_opcode=IOCBCMD.PREAD, aio_fildes=fp.fileno()) submit_ret = io_submit(aio_context_t(10), c_long(1), create_c_array(iocb_p, (pointer(iocb),))) self.assertEqual(1, submit_ret) self.assertEqual(errno.EINVAL, assertion.exception.errno)
def submit(self, *blocks: AIOBlock) -> int: for block in blocks: if block._deleted: raise ValueError( f'{block} can not be used because it has already been transformed into another AIOBlock.' ) return io_submit( self._ctx, c_long(len(blocks)), create_c_array(iocb_p, (pointer(block._iocb) for block in blocks)))
def get_events(self, min_jobs: int, max_jobs: int, timeout_ns: int = 0) -> Tuple[AIOEvent, ...]: event_buf = create_c_array(IOEvent, (), max_jobs) completed_jobs = io_getevents( self._ctx, c_long(min_jobs), c_long(max_jobs), event_buf, pointer(Timespec(*divmod(timeout_ns, 1_000_000_000))) if timeout_ns > 0 else None) return tuple(AIOEvent(event) for event in event_buf[:completed_jobs])
def test_write(self): with open('test.txt', 'w+') as fp: ctx = aio_context_t() io_setup(c_uint(1), pointer(ctx)) self.assertNotEqual(0, ctx.value) contents = 'This is a long sample text.' len_contents = len(contents) arr_p = cast(c_char_p(contents.encode()), c_void_p) iocb = IOCB(aio_lio_opcode=IOCBCMD.PWRITE, aio_fildes=fp.fileno(), aio_buf=arr_p.value, aio_offset=0, aio_nbytes=len_contents) submit_ret = io_submit(ctx, c_long(1), create_c_array(iocb_p, (pointer(iocb),))) self.assertEqual(1, submit_ret) event = IOEvent() get_event_ret = io_getevents(ctx, c_long(1), c_long(1), create_c_array(IOEvent, (event,)), None) self.assertEqual(1, get_event_ret) self.assertEqual(contents, fp.read(len_contents)) io_destroy(ctx)
def test_invalid_priority_req(self): fp = open('/etc/passwd') ctx = aio_context_t() io_setup(c_uint(1), pointer(ctx)) self.assertNotEqual(0, ctx.value) len_buf = 64 buf = bytearray(len_buf) arr_t = c_char * len_buf arr_p = cast(arr_t.from_buffer(buf), c_void_p) iocb = IOCB(aio_lio_opcode=IOCBCMD.PREAD, aio_fildes=fp.fileno(), aio_buf=arr_p.value, aio_offset=0, aio_nbytes=len_buf, aio_resfd=5, aio_flags=IOCBFlag.RESFD) with self.assertRaises(OSError) as assertion: io_submit(ctx, c_long(1), create_c_array(iocb_p, (pointer(iocb),))) self.assertEqual(errno.EBADF, assertion.exception.errno) io_destroy(ctx) fp.close()
def _create_io_vectors(cls, buffers: BUF_TYPE) -> Any: return create_c_array(IOVec, (IOVec(cls._inner_buf_pointer(buf), len(buf)) for buf in buffers))