diff --git a/prep.go b/prep.go index 90b106a..ac4b963 100644 --- a/prep.go +++ b/prep.go @@ -3,8 +3,11 @@ package gouring import ( "syscall" "unsafe" + + "golang.org/x/sys/unix" ) +//go:nosplit func PrepRW(op IoUringOp, sqe *IoUringSqe, fd int, addr unsafe.Pointer, len int, offset uint64) { sqe.Opcode = op @@ -141,19 +144,37 @@ func PrepFilesUpdate(sqe *IoUringSqe, fds []int32, offset int) { PrepRW(IORING_OP_FILES_UPDATE, sqe, -1, unsafe.Pointer(&fds[0]), len(fds), uint64(offset)) } -// func PrepFallocate(sqe *IoUringSqe, fd int, mode int, offset uint64, length uint64) { -// PrepRW(IORING_OP_FALLOCATE, sqe, fd, ) -// } +func PrepFallocate(sqe *IoUringSqe, fd int, mode int, offset uint64, length int) { + PrepRW(IORING_OP_FALLOCATE, sqe, fd, nil, mode, offset) + sqe.SetAddr_Value(uint64(length)) +} func PrepOpenat(sqe *IoUringSqe, dfd int, path *byte, flags uint32, mode int) { PrepRW(IORING_OP_OPENAT, sqe, dfd, unsafe.Pointer(path), mode, 0) sqe.SetOpenFlags(flags) } + +func PrepOpenat2(sqe *IoUringSqe, dfd int, path *byte, how *unix.OpenHow) { + PrepRW(IORING_OP_OPENAT2, sqe, dfd, unsafe.Pointer(path), int(unsafe.Sizeof(*how)), 0) + sqe.SetOffset_RawPtr(unsafe.Pointer(how)) +} + +func PrepOpenat2Direct(sqe *IoUringSqe, dfd int, path *byte, how *unix.OpenHow, fileIndex uint32) { + PrepOpenat2(sqe, dfd, path, how) + __io_uring_set_target_fixed_file(sqe, fileIndex) +} + func PrepOpenatDirect(sqe *IoUringSqe, dfd int, path *byte, flags uint32, mode int, fileIndex uint32) { PrepOpenat(sqe, dfd, path, flags, mode) __io_uring_set_target_fixed_file(sqe, fileIndex) } +func PrepStatx(sqe *IoUringSqe, dfd int, path *byte, flags uint32, mask uint32, statxbuf *unix.Statx_t) { + PrepRW(IORING_OP_STATX, sqe, dfd, unsafe.Pointer(path), int(mask), 0) + sqe.SetOffset_RawPtr(unsafe.Pointer(statxbuf)) + sqe.SetStatxFlags(flags) +} + func PrepFadvise(sqe *IoUringSqe, fd int, offset uint64, length int, advice uint32) { PrepRW(IORING_OP_FADVISE, sqe, fd, nil, length, offset) sqe.SetFadviseAdvice(advice) @@ -178,31 +199,10 @@ func PrepSendZcFixed(sqe *IoUringSqe, sockfd int, buf *byte, length int, flags u sqe.SetBufIndex(bufIndex) } -// statx -//send -//recv -//openat2 -//openat2Direct -//epollCtl -//provide_buffers -//remove_buffers -//shutdown -//unlinkat -//unlink -//renameat -//rename -//sync_file_range -//mkdirat -//mkdir -//symlinkat -//symlink -//linkat -//link -//msg_ring -//getxattr -//setxattr -//fgetxattr -//fsetxattr +func PrepRecv(sqe *IoUringSqe, sockfd int, buf *byte, length int, flags uint32) { + PrepRW(IORING_OP_RECV, sqe, sockfd, unsafe.Pointer(buf), length, 0) + sqe.SetMsgFlags(flags) +} func PrepSocket(sqe *IoUringSqe, domain int, _type int, protocol int, flags uint32) { PrepRW(IORING_OP_SOCKET, sqe, domain, nil, protocol, uint64(_type)) @@ -223,6 +223,11 @@ func PrepSocketDirectAlloc(sqe *IoUringSqe, domain int, _type int, protocol int, Poll */ +// PrepEpollCtl syscall.EpollCtl look-alike +func PrepEpollCtl(sqe *IoUringSqe, epfd int, op int, fd int, ev *syscall.EpollEvent) { + PrepRW(IORING_OP_EPOLL_CTL, sqe, epfd, unsafe.Pointer(ev), op, uint64(fd)) +} + func PrepPollAdd(sqe *IoUringSqe, fd int, pollMask uint32) { PrepRW(IORING_OP_POLL_ADD, sqe, fd, nil, 0, 0) sqe.SetPoll32Events(pollMask) // TODO: check endiannes @@ -246,6 +251,24 @@ func PrepFsync(sqe *IoUringSqe, fd int, fsyncFlags uint32) { sqe.SetFsyncFlags(fsyncFlags) } +/* + Multishot +*/ + +func PrepMultishotAccept(sqe *IoUringSqe, fd int, rsa *syscall.RawSockaddrAny, rsaSz *uintptr, flags uint32) { + PrepAccept(sqe, fd, rsa, rsaSz, flags) + sqe.IoPrio |= IORING_ACCEPT_MULTISHOT +} + +func PrepMultishotAcceptDirect(sqe *IoUringSqe, fd int, rsa *syscall.RawSockaddrAny, rsaSz *uintptr, flags uint32) { + PrepMultishotAccept(sqe, fd, rsa, rsaSz, flags) + __io_uring_set_target_fixed_file(sqe, IORING_FILE_INDEX_ALLOC-1) +} + +/* + Extra +*/ + func PrepCancel64(sqe *IoUringSqe, ud UserData, flags uint32) { PrepRW(IORING_OP_ASYNC_CANCEL, sqe, -1, nil, 0, 0) sqe.SetAddr(ud.GetUnsafe()) @@ -264,18 +287,91 @@ func PrepLinkTimeout(sqe *IoUringSqe, ts *syscall.Timespec, flags uint32) { sqe.SetTimeoutFlags(flags) } -/* - Multishot -*/ - -func PrepMultishotAccept(sqe *IoUringSqe, fd int, rsa *syscall.RawSockaddrAny, rsaSz *uintptr, flags uint32) { - PrepAccept(sqe, fd, rsa, rsaSz, flags) - sqe.IoPrio |= IORING_ACCEPT_MULTISHOT +func PrepProvideBuffers(sqe *IoUringSqe, addr unsafe.Pointer, length int, nr int, bGid uint16, bId int) { + PrepRW(IORING_OP_PROVIDE_BUFFERS, sqe, nr, addr, length, uint64(bId)) + sqe.SetBufGroup(bGid) } -func PrepMultishotAcceptDirect(sqe *IoUringSqe, fd int, rsa *syscall.RawSockaddrAny, rsaSz *uintptr, flags uint32) { - PrepMultishotAccept(sqe, fd, rsa, rsaSz, flags) - __io_uring_set_target_fixed_file(sqe, IORING_FILE_INDEX_ALLOC-1) +func PrepRemoveBuffers(sqe *IoUringSqe, nr int, bGid uint16) { + PrepRW(IORING_OP_REMOVE_BUFFERS, sqe, nr, nil, 0, 0) + sqe.SetBufGroup(bGid) +} + +func PrepShutdown(sqe *IoUringSqe, fd int, how int) { + PrepRW(IORING_OP_SHUTDOWN, sqe, fd, nil, how, 0) +} + +func PrepUnlinkat(sqe *IoUringSqe, dfd int, path *byte, flags uint32) { + PrepRW(IORING_OP_UNLINKAT, sqe, dfd, unsafe.Pointer(path), 0, 0) + sqe.SetUnlinkFlags(flags) +} + +func PrepUnlink(sqe *IoUringSqe, path *byte, flags uint32) { + PrepUnlinkat(sqe, unix.AT_FDCWD, path, flags) +} + +func PrepRenameat(sqe *IoUringSqe, oldDfd int, oldPath *byte, newDfd int, newPath *byte, flags uint32) { + PrepRW(IORING_OP_RENAMEAT, sqe, oldDfd, unsafe.Pointer(oldPath), newDfd, 0) + sqe.SetOffset_RawPtr(unsafe.Pointer(newPath)) + sqe.SetRenameFlags(flags) +} + +func PrepRename(sqe *IoUringSqe, oldPath *byte, newPath *byte) { + PrepRenameat(sqe, unix.AT_FDCWD, oldPath, unix.AT_FDCWD, newPath, 0) +} + +func PrepSyncFileRange(sqe *IoUringSqe, fd int, length int, offset uint64, flags uint32) { + PrepRW(IORING_OP_SYNC_FILE_RANGE, sqe, fd, nil, length, offset) + sqe.SetSyncRangeFlags(flags) +} + +func PrepMkdirat(sqe *IoUringSqe, dfd int, path *byte, mode int) { + PrepRW(IORING_OP_MKDIRAT, sqe, dfd, unsafe.Pointer(path), mode, 0) +} + +func PrepMkdir(sqe *IoUringSqe, dfd int, path *byte, mode int) { + PrepMkdirat(sqe, unix.AT_FDCWD, path, mode) +} + +func PrepSymlinkat(sqe *IoUringSqe, target *byte, newDirfd int, linkpath *byte) { + PrepRW(IORING_OP_SYMLINKAT, sqe, newDirfd, unsafe.Pointer(target), 0, 0) + sqe.SetOffset_RawPtr(unsafe.Pointer(linkpath)) +} + +func PrepSymlink(sqe *IoUringSqe, target *byte, linkpath *byte) { + PrepSymlinkat(sqe, target, unix.AT_FDCWD, linkpath) +} + +func PrepLinkat(sqe *IoUringSqe, oldDfd int, oldPath *byte, newDfd int, newPath *byte, flags uint32) { + PrepRW(IORING_OP_LINKAT, sqe, oldDfd, unsafe.Pointer(oldPath), newDfd, 0) + sqe.SetOffset_RawPtr(unsafe.Pointer(newPath)) +} + +func PrepLink(sqe *IoUringSqe, oldPath *byte, newPath *byte, flags uint32) { + PrepLinkat(sqe, unix.AT_FDCWD, oldPath, unix.AT_FDCWD, newPath, flags) +} + +func PrepMsgRing(sqe *IoUringSqe, fd int, length int, data uint64, flags uint32) { + PrepRW(IORING_OP_MSG_RING, sqe, fd, nil, length, data) + sqe.SetRwFlags(flags) +} + +func PrepGetxattr(sqe *IoUringSqe, name *byte, value *byte, path *byte, length int) { + PrepRW(IORING_OP_GETXATTR, sqe, 0, unsafe.Pointer(name), length, 0) + sqe.SetOffset_RawPtr(unsafe.Pointer(path)) + sqe.SetXattrFlags(0) +} + +func PrepSetxattr(sqe *IoUringSqe, name *byte, value *byte, path *byte, flags uint32, length int) { + PrepRW(IORING_OP_SETXATTR, sqe, 0, unsafe.Pointer(name), length, 0) + sqe.SetOffset_RawPtr(unsafe.Pointer(value)) + sqe.SetXattrFlags(flags) +} + +func PrepFsetxattr(sqe *IoUringSqe, fd int, name *byte, value *byte, flags uint32, length int) { + PrepRW(IORING_OP_FSETXATTR, sqe, fd, unsafe.Pointer(name), length, 0) + sqe.SetOffset_RawPtr(unsafe.Pointer(value)) + sqe.SetXattrFlags(flags) } //go:nosplit