1#![allow(clippy::new_without_default)]
4
5use std::convert::TryInto;
6use std::mem;
7use std::os::unix::io::RawFd;
8
9use crate::squeue::Entry;
10use crate::squeue::Entry128;
11use crate::sys;
12use crate::types::{self, sealed};
13
14macro_rules! assign_fd {
15 ( $sqe:ident . fd = $opfd:expr ) => {
16 match $opfd {
17 sealed::Target::Fd(fd) => $sqe.fd = fd,
18 sealed::Target::Fixed(idx) => {
19 $sqe.fd = idx as _;
20 $sqe.flags |= crate::squeue::Flags::FIXED_FILE.bits();
21 }
22 }
23 };
24}
25
26macro_rules! opcode {
27 (@type impl sealed::UseFixed ) => {
28 sealed::Target
29 };
30 (@type impl sealed::UseFd ) => {
31 RawFd
32 };
33 (@type $name:ty ) => {
34 $name
35 };
36 (
37 $( #[$outer:meta] )*
38 pub struct $name:ident {
39 $( #[$new_meta:meta] )*
40
41 $( $field:ident : { $( $tnt:tt )+ } ),*
42
43 $(,)?
44
45 ;;
46
47 $(
48 $( #[$opt_meta:meta] )*
49 $opt_field:ident : $opt_tname:ty = $default:expr
50 ),*
51
52 $(,)?
53 }
54
55 pub const CODE = $opcode:expr;
56
57 $( #[$build_meta:meta] )*
58 pub fn build($self:ident) -> $entry:ty $build_block:block
59 ) => {
60 $( #[$outer] )*
61 pub struct $name {
62 $( $field : opcode!(@type $( $tnt )*), )*
63 $( $opt_field : $opt_tname, )*
64 }
65
66 impl $name {
67 $( #[$new_meta] )*
68 #[inline]
69 pub fn new($( $field : $( $tnt )* ),*) -> Self {
70 $name {
71 $( $field: $field.into(), )*
72 $( $opt_field: $default, )*
73 }
74 }
75
76 pub const CODE: u8 = $opcode as _;
80
81 $(
82 $( #[$opt_meta] )*
83 #[inline]
84 pub const fn $opt_field(mut self, $opt_field: $opt_tname) -> Self {
85 self.$opt_field = $opt_field;
86 self
87 }
88 )*
89
90 $( #[$build_meta] )*
91 #[inline]
92 pub fn build($self) -> $entry $build_block
93 }
94 }
95}
96
97#[inline(always)]
99fn sqe_zeroed() -> sys::io_uring_sqe {
100 unsafe { mem::zeroed() }
101}
102
103opcode! {
104 #[derive(Debug)]
108 pub struct Nop { ;; }
109
110 pub const CODE = sys::IORING_OP_NOP;
111
112 pub fn build(self) -> Entry {
113 let Nop {} = self;
114
115 let mut sqe = sqe_zeroed();
116 sqe.opcode = Self::CODE;
117 sqe.fd = -1;
118 Entry(sqe)
119 }
120}
121
122opcode! {
123 #[derive(Debug)]
125 pub struct Readv {
126 fd: { impl sealed::UseFixed },
127 iovec: { *const libc::iovec },
128 len: { u32 },
129 ;;
130 ioprio: u16 = 0,
131 offset: u64 = 0,
132 rw_flags: i32 = 0,
135 buf_group: u16 = 0
136 }
137
138 pub const CODE = sys::IORING_OP_READV;
139
140 pub fn build(self) -> Entry {
141 let Readv {
142 fd,
143 iovec, len, offset,
144 ioprio, rw_flags,
145 buf_group
146 } = self;
147
148 let mut sqe = sqe_zeroed();
149 sqe.opcode = Self::CODE;
150 assign_fd!(sqe.fd = fd);
151 sqe.ioprio = ioprio;
152 sqe.__bindgen_anon_2.addr = iovec as _;
153 sqe.len = len;
154 sqe.__bindgen_anon_1.off = offset;
155 sqe.__bindgen_anon_3.rw_flags = rw_flags as _;
156 sqe.__bindgen_anon_4.buf_group = buf_group;
157 Entry(sqe)
158 }
159}
160
161opcode! {
162 #[derive(Debug)]
164 pub struct Writev {
165 fd: { impl sealed::UseFixed },
166 iovec: { *const libc::iovec },
167 len: { u32 },
168 ;;
169 ioprio: u16 = 0,
170 offset: u64 = 0,
171 rw_flags: i32 = 0,
174 write_stream: u8 = 0
177 }
178
179 pub const CODE = sys::IORING_OP_WRITEV;
180
181 pub fn build(self) -> Entry {
182 let Writev {
183 fd,
184 iovec, len, offset,
185 ioprio, rw_flags,
186 write_stream
187 } = self;
188
189 let mut sqe = sqe_zeroed();
190 sqe.opcode = Self::CODE;
191 assign_fd!(sqe.fd = fd);
192 sqe.ioprio = ioprio;
193 sqe.__bindgen_anon_2.addr = iovec as _;
194 sqe.len = len;
195 sqe.__bindgen_anon_1.off = offset;
196 sqe.__bindgen_anon_3.rw_flags = rw_flags as _;
197 sqe.__bindgen_anon_5.__bindgen_anon_2.write_stream = write_stream;
198 Entry(sqe)
199 }
200}
201
202opcode! {
203 #[derive(Debug)]
218 pub struct Fsync {
219 fd: { impl sealed::UseFixed },
220 ;;
221 offset: u64 = 0,
224 len: u32 = 0,
227 flags: types::FsyncFlags = types::FsyncFlags::empty()
231 }
232
233 pub const CODE = sys::IORING_OP_FSYNC;
234
235 pub fn build(self) -> Entry {
236 let Fsync {
237 fd,
238 offset,
239 len,
240 flags,
241 } = self;
242
243 let mut sqe = sqe_zeroed();
244 sqe.opcode = Self::CODE;
245 assign_fd!(sqe.fd = fd);
246 sqe.len = len;
247 sqe.__bindgen_anon_1.off = offset;
248 sqe.__bindgen_anon_3.fsync_flags = flags.bits();
249 Entry(sqe)
250 }
251}
252
253opcode! {
254 #[derive(Debug)]
259 pub struct ReadFixed {
260 fd: { impl sealed::UseFixed },
261 buf: { *mut u8 },
262 len: { u32 },
263 buf_index: { u16 },
264 ;;
265 ioprio: u16 = 0,
266 offset: u64 = 0,
268 rw_flags: i32 = 0
271 }
272
273 pub const CODE = sys::IORING_OP_READ_FIXED;
274
275 pub fn build(self) -> Entry {
276 let ReadFixed {
277 fd,
278 buf, len, offset,
279 buf_index,
280 ioprio, rw_flags
281 } = self;
282
283 let mut sqe = sqe_zeroed();
284 sqe.opcode = Self::CODE;
285 assign_fd!(sqe.fd = fd);
286 sqe.ioprio = ioprio;
287 sqe.__bindgen_anon_2.addr = buf as _;
288 sqe.len = len;
289 sqe.__bindgen_anon_1.off = offset;
290 sqe.__bindgen_anon_3.rw_flags = rw_flags as _;
291 sqe.__bindgen_anon_4.buf_index = buf_index;
292 Entry(sqe)
293 }
294}
295
296opcode! {
297 #[derive(Debug)]
302 pub struct WriteFixed {
303 fd: { impl sealed::UseFixed },
304 buf: { *const u8 },
305 len: { u32 },
306 buf_index: { u16 },
307 ;;
308 ioprio: u16 = 0,
309 offset: u64 = 0,
311 rw_flags: i32 = 0,
314 write_stream: u8 = 0
317 }
318
319 pub const CODE = sys::IORING_OP_WRITE_FIXED;
320
321 pub fn build(self) -> Entry {
322 let WriteFixed {
323 fd,
324 buf, len, offset,
325 buf_index,
326 ioprio, rw_flags,
327 write_stream
328 } = self;
329
330 let mut sqe = sqe_zeroed();
331 sqe.opcode = Self::CODE;
332 assign_fd!(sqe.fd = fd);
333 sqe.ioprio = ioprio;
334 sqe.__bindgen_anon_2.addr = buf as _;
335 sqe.len = len;
336 sqe.__bindgen_anon_1.off = offset;
337 sqe.__bindgen_anon_3.rw_flags = rw_flags as _;
338 sqe.__bindgen_anon_5.__bindgen_anon_2.write_stream = write_stream;
339 sqe.__bindgen_anon_4.buf_index = buf_index;
340 Entry(sqe)
341 }
342}
343
344opcode! {
345 #[derive(Debug)]
357 pub struct PollAdd {
358 fd: { impl sealed::UseFixed },
361 flags: { u32 },
362 ;;
363 multi: bool = false
364 }
365
366 pub const CODE = sys::IORING_OP_POLL_ADD;
367
368 pub fn build(self) -> Entry {
369 let PollAdd { fd, flags, multi } = self;
370
371 let mut sqe = sqe_zeroed();
372 sqe.opcode = Self::CODE;
373 assign_fd!(sqe.fd = fd);
374 if multi {
375 sqe.len = sys::IORING_POLL_ADD_MULTI;
376 }
377
378 #[cfg(target_endian = "little")] {
379 sqe.__bindgen_anon_3.poll32_events = flags;
380 }
381
382 #[cfg(target_endian = "big")] {
383 let x = flags << 16;
384 let y = flags >> 16;
385 let flags = x | y;
386 sqe.__bindgen_anon_3.poll32_events = flags;
387 }
388
389 Entry(sqe)
390 }
391}
392
393opcode! {
394 #[derive(Debug)]
399 pub struct PollRemove {
400 user_data: { u64 }
401 ;;
402 }
403
404 pub const CODE = sys::IORING_OP_POLL_REMOVE;
405
406 pub fn build(self) -> Entry {
407 let PollRemove { user_data } = self;
408
409 let mut sqe = sqe_zeroed();
410 sqe.opcode = Self::CODE;
411 sqe.fd = -1;
412 sqe.__bindgen_anon_2.addr = user_data;
413 Entry(sqe)
414 }
415}
416
417opcode! {
418 #[derive(Debug)]
420 pub struct SyncFileRange {
421 fd: { impl sealed::UseFixed },
422 len: { u32 },
423 ;;
424 offset: u64 = 0,
426 flags: u32 = 0
428 }
429
430 pub const CODE = sys::IORING_OP_SYNC_FILE_RANGE;
431
432 pub fn build(self) -> Entry {
433 let SyncFileRange {
434 fd,
435 len, offset,
436 flags
437 } = self;
438
439 let mut sqe = sqe_zeroed();
440 sqe.opcode = Self::CODE;
441 assign_fd!(sqe.fd = fd);
442 sqe.len = len;
443 sqe.__bindgen_anon_1.off = offset;
444 sqe.__bindgen_anon_3.sync_range_flags = flags;
445 Entry(sqe)
446 }
447}
448
449opcode! {
450 #[derive(Debug)]
455 pub struct SendMsg {
456 fd: { impl sealed::UseFixed },
457 msg: { *const libc::msghdr },
458 ;;
459 ioprio: u16 = 0,
460 flags: u32 = 0
461 }
462
463 pub const CODE = sys::IORING_OP_SENDMSG;
464
465 pub fn build(self) -> Entry {
466 let SendMsg { fd, msg, ioprio, flags } = self;
467
468 let mut sqe = sqe_zeroed();
469 sqe.opcode = Self::CODE;
470 assign_fd!(sqe.fd = fd);
471 sqe.ioprio = ioprio;
472 sqe.__bindgen_anon_2.addr = msg as _;
473 sqe.len = 1;
474 sqe.__bindgen_anon_3.msg_flags = flags;
475 Entry(sqe)
476 }
477}
478
479opcode! {
480 #[derive(Debug)]
484 pub struct RecvMsg {
485 fd: { impl sealed::UseFixed },
486 msg: { *mut libc::msghdr },
487 ;;
488 ioprio: u16 = 0,
489 flags: u32 = 0,
490 buf_group: u16 = 0
491 }
492
493 pub const CODE = sys::IORING_OP_RECVMSG;
494
495 pub fn build(self) -> Entry {
496 let RecvMsg { fd, msg, ioprio, flags, buf_group } = self;
497
498 let mut sqe = sqe_zeroed();
499 sqe.opcode = Self::CODE;
500 assign_fd!(sqe.fd = fd);
501 sqe.ioprio = ioprio;
502 sqe.__bindgen_anon_2.addr = msg as _;
503 sqe.len = 1;
504 sqe.__bindgen_anon_3.msg_flags = flags;
505 sqe.__bindgen_anon_4.buf_group = buf_group;
506 Entry(sqe)
507 }
508}
509
510opcode! {
511 #[derive(Debug)]
534 pub struct RecvMsgMulti {
535 fd: { impl sealed::UseFixed },
536 msg: { *const libc::msghdr },
537 buf_group: { u16 },
538 ;;
539 ioprio: u16 = 0,
540 flags: u32 = 0
541 }
542
543 pub const CODE = sys::IORING_OP_RECVMSG;
544
545 pub fn build(self) -> Entry {
546 let RecvMsgMulti { fd, msg, buf_group, ioprio, flags } = self;
547
548 let mut sqe = sqe_zeroed();
549 sqe.opcode = Self::CODE;
550 assign_fd!(sqe.fd = fd);
551 sqe.__bindgen_anon_2.addr = msg as _;
552 sqe.len = 1;
553 sqe.__bindgen_anon_3.msg_flags = flags;
554 sqe.__bindgen_anon_4.buf_group = buf_group;
555 sqe.flags |= crate::squeue::Flags::BUFFER_SELECT.bits();
556 sqe.ioprio = ioprio | (sys::IORING_RECV_MULTISHOT as u16);
557 Entry(sqe)
558 }
559}
560
561opcode! {
562 #[derive(Debug)]
571 pub struct Timeout {
572 timespec: { *const types::Timespec },
573 ;;
574 count: u32 = 0,
578
579 flags: types::TimeoutFlags = types::TimeoutFlags::empty()
580 }
581
582 pub const CODE = sys::IORING_OP_TIMEOUT;
583
584 pub fn build(self) -> Entry {
585 let Timeout { timespec, count, flags } = self;
586
587 let mut sqe = sqe_zeroed();
588 sqe.opcode = Self::CODE;
589 sqe.fd = -1;
590 sqe.__bindgen_anon_2.addr = timespec as _;
591 sqe.len = 1;
592 sqe.__bindgen_anon_1.off = count as _;
593 sqe.__bindgen_anon_3.timeout_flags = flags.bits();
594 Entry(sqe)
595 }
596}
597
598opcode! {
601 pub struct TimeoutRemove {
603 user_data: { u64 },
604 ;;
605 }
606
607 pub const CODE = sys::IORING_OP_TIMEOUT_REMOVE;
608
609 pub fn build(self) -> Entry {
610 let TimeoutRemove { user_data } = self;
611
612 let mut sqe = sqe_zeroed();
613 sqe.opcode = Self::CODE;
614 sqe.fd = -1;
615 sqe.__bindgen_anon_2.addr = user_data;
616 Entry(sqe)
617 }
618}
619
620opcode! {
621 pub struct TimeoutUpdate {
624 user_data: { u64 },
625 timespec: { *const types::Timespec },
626 ;;
627 flags: types::TimeoutFlags = types::TimeoutFlags::empty()
628 }
629
630 pub const CODE = sys::IORING_OP_TIMEOUT_REMOVE;
631
632 pub fn build(self) -> Entry {
633 let TimeoutUpdate { user_data, timespec, flags } = self;
634
635 let mut sqe = sqe_zeroed();
636 sqe.opcode = Self::CODE;
637 sqe.fd = -1;
638 sqe.__bindgen_anon_1.off = timespec as _;
639 sqe.__bindgen_anon_2.addr = user_data;
640 sqe.__bindgen_anon_3.timeout_flags = flags.bits() | sys::IORING_TIMEOUT_UPDATE;
641 Entry(sqe)
642 }
643}
644
645opcode! {
646 pub struct Accept {
648 fd: { impl sealed::UseFixed },
649 addr: { *mut libc::sockaddr },
650 addrlen: { *mut libc::socklen_t },
651 ;;
652 file_index: Option<types::DestinationSlot> = None,
653 flags: i32 = 0
654 }
655
656 pub const CODE = sys::IORING_OP_ACCEPT;
657
658 pub fn build(self) -> Entry {
659 let Accept { fd, addr, addrlen, file_index, flags } = self;
660
661 let mut sqe = sqe_zeroed();
662 sqe.opcode = Self::CODE;
663 assign_fd!(sqe.fd = fd);
664 sqe.__bindgen_anon_2.addr = addr as _;
665 sqe.__bindgen_anon_1.addr2 = addrlen as _;
666 sqe.__bindgen_anon_3.accept_flags = flags as _;
667 if let Some(dest) = file_index {
668 sqe.__bindgen_anon_5.file_index = dest.kernel_index_arg();
669 }
670 Entry(sqe)
671 }
672}
673
674opcode! {
675 pub struct SetSockOpt {
677 fd: { impl sealed::UseFixed },
678 level: { u32 },
679 optname: { u32 },
680 optval: { *const libc::c_void },
681 optlen: { u32 },
682 ;;
683 flags: u32 = 0
684 }
685
686 pub const CODE = sys::IORING_OP_URING_CMD;
687
688 pub fn build(self) -> Entry {
689 let SetSockOpt { fd, level, optname, optval, optlen, flags } = self;
690 let mut sqe = sqe_zeroed();
691 sqe.opcode = Self::CODE;
692 assign_fd!(sqe.fd = fd);
693 sqe.__bindgen_anon_1.__bindgen_anon_1.cmd_op = sys::SOCKET_URING_OP_SETSOCKOPT;
694
695 sqe.__bindgen_anon_2.__bindgen_anon_1.level = level;
696 sqe.__bindgen_anon_2.__bindgen_anon_1.optname = optname;
697 sqe.__bindgen_anon_3.uring_cmd_flags = flags;
698 sqe.__bindgen_anon_5.optlen = optlen;
699 unsafe { *sqe.__bindgen_anon_6.optval.as_mut() = optval as u64 };
700 Entry(sqe)
701 }
702}
703
704opcode! {
705 pub struct AsyncCancel {
707 user_data: { u64 }
708 ;;
709
710 }
712
713 pub const CODE = sys::IORING_OP_ASYNC_CANCEL;
714
715 pub fn build(self) -> Entry {
716 let AsyncCancel { user_data } = self;
717
718 let mut sqe = sqe_zeroed();
719 sqe.opcode = Self::CODE;
720 sqe.fd = -1;
721 sqe.__bindgen_anon_2.addr = user_data;
722 Entry(sqe)
723 }
724}
725
726opcode! {
727 pub struct LinkTimeout {
731 timespec: { *const types::Timespec },
732 ;;
733 flags: types::TimeoutFlags = types::TimeoutFlags::empty()
734 }
735
736 pub const CODE = sys::IORING_OP_LINK_TIMEOUT;
737
738 pub fn build(self) -> Entry {
739 let LinkTimeout { timespec, flags } = self;
740
741 let mut sqe = sqe_zeroed();
742 sqe.opcode = Self::CODE;
743 sqe.fd = -1;
744 sqe.__bindgen_anon_2.addr = timespec as _;
745 sqe.len = 1;
746 sqe.__bindgen_anon_3.timeout_flags = flags.bits();
747 Entry(sqe)
748 }
749}
750
751opcode! {
752 pub struct Connect {
754 fd: { impl sealed::UseFixed },
755 addr: { *const libc::sockaddr },
756 addrlen: { libc::socklen_t }
757 ;;
758 }
759
760 pub const CODE = sys::IORING_OP_CONNECT;
761
762 pub fn build(self) -> Entry {
763 let Connect { fd, addr, addrlen } = self;
764
765 let mut sqe = sqe_zeroed();
766 sqe.opcode = Self::CODE;
767 assign_fd!(sqe.fd = fd);
768 sqe.__bindgen_anon_2.addr = addr as _;
769 sqe.__bindgen_anon_1.off = addrlen as _;
770 Entry(sqe)
771 }
772}
773
774opcode! {
777 pub struct Fallocate {
779 fd: { impl sealed::UseFixed },
780 len: { u64 },
781 ;;
782 offset: u64 = 0,
783 mode: i32 = 0
784 }
785
786 pub const CODE = sys::IORING_OP_FALLOCATE;
787
788 pub fn build(self) -> Entry {
789 let Fallocate { fd, len, offset, mode } = self;
790
791 let mut sqe = sqe_zeroed();
792 sqe.opcode = Self::CODE;
793 assign_fd!(sqe.fd = fd);
794 sqe.__bindgen_anon_2.addr = len;
795 sqe.len = mode as _;
796 sqe.__bindgen_anon_1.off = offset;
797 Entry(sqe)
798 }
799}
800
801opcode! {
802 pub struct OpenAt {
804 dirfd: { impl sealed::UseFd },
805 pathname: { *const libc::c_char },
806 ;;
807 file_index: Option<types::DestinationSlot> = None,
808 flags: i32 = 0,
809 mode: libc::mode_t = 0
810 }
811
812 pub const CODE = sys::IORING_OP_OPENAT;
813
814 pub fn build(self) -> Entry {
815 let OpenAt { dirfd, pathname, file_index, flags, mode } = self;
816
817 let mut sqe = sqe_zeroed();
818 sqe.opcode = Self::CODE;
819 sqe.fd = dirfd;
820 sqe.__bindgen_anon_2.addr = pathname as _;
821 sqe.len = mode;
822 sqe.__bindgen_anon_3.open_flags = flags as _;
823 if let Some(dest) = file_index {
824 sqe.__bindgen_anon_5.file_index = dest.kernel_index_arg();
825 }
826 Entry(sqe)
827 }
828}
829
830opcode! {
831 pub struct Close {
835 fd: { impl sealed::UseFixed },
836 ;;
837 }
838
839 pub const CODE = sys::IORING_OP_CLOSE;
840
841 pub fn build(self) -> Entry {
842 let Close { fd } = self;
843
844 let mut sqe = sqe_zeroed();
845 sqe.opcode = Self::CODE;
846 match fd {
847 sealed::Target::Fd(fd) => sqe.fd = fd,
848 sealed::Target::Fixed(idx) => {
849 sqe.fd = 0;
850 sqe.__bindgen_anon_5.file_index = idx + 1;
851 }
852 }
853 Entry(sqe)
854 }
855}
856
857opcode! {
858 pub struct FilesUpdate {
862 fds: { *const RawFd },
863 len: { u32 },
864 ;;
865 offset: i32 = 0
866 }
867
868 pub const CODE = sys::IORING_OP_FILES_UPDATE;
869
870 pub fn build(self) -> Entry {
871 let FilesUpdate { fds, len, offset } = self;
872
873 let mut sqe = sqe_zeroed();
874 sqe.opcode = Self::CODE;
875 sqe.fd = -1;
876 sqe.__bindgen_anon_2.addr = fds as _;
877 sqe.len = len;
878 sqe.__bindgen_anon_1.off = offset as _;
879 Entry(sqe)
880 }
881}
882
883opcode! {
884 pub struct Statx {
886 dirfd: { impl sealed::UseFd },
887 pathname: { *const libc::c_char },
888 statxbuf: { *mut types::statx },
889 ;;
890 flags: i32 = 0,
891 mask: u32 = 0
892 }
893
894 pub const CODE = sys::IORING_OP_STATX;
895
896 pub fn build(self) -> Entry {
897 let Statx {
898 dirfd, pathname, statxbuf,
899 flags, mask
900 } = self;
901
902 let mut sqe = sqe_zeroed();
903 sqe.opcode = Self::CODE;
904 sqe.fd = dirfd;
905 sqe.__bindgen_anon_2.addr = pathname as _;
906 sqe.len = mask;
907 sqe.__bindgen_anon_1.off = statxbuf as _;
908 sqe.__bindgen_anon_3.statx_flags = flags as _;
909 Entry(sqe)
910 }
911}
912
913opcode! {
914 pub struct Read {
925 fd: { impl sealed::UseFixed },
926 buf: { *mut u8 },
927 len: { u32 },
928 ;;
929 offset: u64 = 0,
935 ioprio: u16 = 0,
936 rw_flags: i32 = 0,
937 buf_group: u16 = 0
938 }
939
940 pub const CODE = sys::IORING_OP_READ;
941
942 pub fn build(self) -> Entry {
943 let Read {
944 fd,
945 buf, len, offset,
946 ioprio, rw_flags,
947 buf_group
948 } = self;
949
950 let mut sqe = sqe_zeroed();
951 sqe.opcode = Self::CODE;
952 assign_fd!(sqe.fd = fd);
953 sqe.ioprio = ioprio;
954 sqe.__bindgen_anon_2.addr = buf as _;
955 sqe.len = len;
956 sqe.__bindgen_anon_1.off = offset;
957 sqe.__bindgen_anon_3.rw_flags = rw_flags as _;
958 sqe.__bindgen_anon_4.buf_group = buf_group;
959 Entry(sqe)
960 }
961}
962
963opcode! {
964 pub struct Write {
975 fd: { impl sealed::UseFixed },
976 buf: { *const u8 },
977 len: { u32 },
978 ;;
979 offset: u64 = 0,
985 ioprio: u16 = 0,
986 rw_flags: i32 = 0,
987 write_stream: u8 = 0
991 }
992
993 pub const CODE = sys::IORING_OP_WRITE;
994
995 pub fn build(self) -> Entry {
996 let Write {
997 fd,
998 buf, len, offset,
999 ioprio, rw_flags,
1000 write_stream
1001 } = self;
1002
1003 let mut sqe = sqe_zeroed();
1004 sqe.opcode = Self::CODE;
1005 assign_fd!(sqe.fd = fd);
1006 sqe.ioprio = ioprio;
1007 sqe.__bindgen_anon_2.addr = buf as _;
1008 sqe.len = len;
1009 sqe.__bindgen_anon_1.off = offset;
1010 sqe.__bindgen_anon_3.rw_flags = rw_flags as _;
1011 sqe.__bindgen_anon_5.__bindgen_anon_2.write_stream = write_stream;
1012 Entry(sqe)
1013 }
1014}
1015
1016opcode! {
1017 pub struct Fadvise {
1019 fd: { impl sealed::UseFixed },
1020 len: { libc::off_t },
1021 advice: { i32 },
1022 ;;
1023 offset: u64 = 0,
1024 }
1025
1026 pub const CODE = sys::IORING_OP_FADVISE;
1027
1028 pub fn build(self) -> Entry {
1029 let Fadvise { fd, len, advice, offset } = self;
1030
1031 let mut sqe = sqe_zeroed();
1032 sqe.opcode = Self::CODE;
1033 assign_fd!(sqe.fd = fd);
1034 sqe.len = len as _;
1035 sqe.__bindgen_anon_1.off = offset;
1036 sqe.__bindgen_anon_3.fadvise_advice = advice as _;
1037 Entry(sqe)
1038 }
1039}
1040
1041opcode! {
1042 pub struct Madvise {
1044 addr: { *const libc::c_void },
1045 len: { libc::off_t },
1046 advice: { i32 },
1047 ;;
1048 }
1049
1050 pub const CODE = sys::IORING_OP_MADVISE;
1051
1052 pub fn build(self) -> Entry {
1053 let Madvise { addr, len, advice } = self;
1054
1055 let mut sqe = sqe_zeroed();
1056 sqe.opcode = Self::CODE;
1057 sqe.fd = -1;
1058 sqe.__bindgen_anon_2.addr = addr as _;
1059 sqe.len = len as _;
1060 sqe.__bindgen_anon_3.fadvise_advice = advice as _;
1061 Entry(sqe)
1062 }
1063}
1064
1065opcode! {
1066 pub struct Send {
1068 fd: { impl sealed::UseFixed },
1069 buf: { *const u8 },
1070 len: { u32 },
1071 ;;
1072 ioprio: u16 = 0,
1073 flags: i32 = 0,
1074
1075 dest_addr: *const libc::sockaddr = core::ptr::null(),
1080 dest_addr_len: libc::socklen_t = 0,
1081 }
1082
1083 pub const CODE = sys::IORING_OP_SEND;
1084
1085 pub fn build(self) -> Entry {
1086 let Send { fd, buf, len, ioprio, flags, dest_addr, dest_addr_len } = self;
1087
1088 let mut sqe = sqe_zeroed();
1089 sqe.opcode = Self::CODE;
1090 assign_fd!(sqe.fd = fd);
1091 sqe.__bindgen_anon_2.addr = buf as _;
1092 sqe.__bindgen_anon_1.addr2 = dest_addr as _;
1093 sqe.__bindgen_anon_5.__bindgen_anon_1.addr_len = dest_addr_len as _;
1094 sqe.len = len;
1095 sqe.ioprio = ioprio;
1096 sqe.__bindgen_anon_3.msg_flags = flags as _;
1097 Entry(sqe)
1098 }
1099}
1100
1101opcode! {
1102 pub struct Recv {
1104 fd: { impl sealed::UseFixed },
1105 buf: { *mut u8 },
1106 len: { u32 },
1107 ;;
1108 ioprio: u16 = 0,
1109 flags: i32 = 0,
1110 buf_group: u16 = 0
1111 }
1112
1113 pub const CODE = sys::IORING_OP_RECV;
1114
1115 pub fn build(self) -> Entry {
1116 let Recv { fd, buf, len, ioprio, flags, buf_group } = self;
1117
1118 let mut sqe = sqe_zeroed();
1119 sqe.opcode = Self::CODE;
1120 assign_fd!(sqe.fd = fd);
1121 sqe.__bindgen_anon_2.addr = buf as _;
1122 sqe.len = len;
1123 sqe.ioprio = ioprio;
1124 sqe.__bindgen_anon_3.msg_flags = flags as _;
1125 sqe.__bindgen_anon_4.buf_group = buf_group;
1126 Entry(sqe)
1127 }
1128}
1129
1130opcode! {
1131 pub struct RecvMulti {
1147 fd: { impl sealed::UseFixed },
1148 buf_group: { u16 },
1149 ;;
1150 flags: i32 = 0,
1151 len: u32 = 0,
1152 }
1153
1154 pub const CODE = sys::IORING_OP_RECV;
1155
1156 pub fn build(self) -> Entry {
1157 let RecvMulti { fd, buf_group, flags, len } = self;
1158
1159 let mut sqe = sqe_zeroed();
1160 sqe.opcode = Self::CODE;
1161 assign_fd!(sqe.fd = fd);
1162 sqe.len = len;
1163 sqe.__bindgen_anon_3.msg_flags = flags as _;
1164 sqe.__bindgen_anon_4.buf_group = buf_group;
1165 sqe.flags |= crate::squeue::Flags::BUFFER_SELECT.bits();
1166 sqe.ioprio = sys::IORING_RECV_MULTISHOT as _;
1167 Entry(sqe)
1168 }
1169}
1170
1171opcode! {
1172 pub struct OpenAt2 {
1174 dirfd: { impl sealed::UseFd },
1175 pathname: { *const libc::c_char },
1176 how: { *const types::OpenHow }
1177 ;;
1178 file_index: Option<types::DestinationSlot> = None,
1179 }
1180
1181 pub const CODE = sys::IORING_OP_OPENAT2;
1182
1183 pub fn build(self) -> Entry {
1184 let OpenAt2 { dirfd, pathname, how, file_index } = self;
1185
1186 let mut sqe = sqe_zeroed();
1187 sqe.opcode = Self::CODE;
1188 sqe.fd = dirfd;
1189 sqe.__bindgen_anon_2.addr = pathname as _;
1190 sqe.len = mem::size_of::<sys::open_how>() as _;
1191 sqe.__bindgen_anon_1.off = how as _;
1192 if let Some(dest) = file_index {
1193 sqe.__bindgen_anon_5.file_index = dest.kernel_index_arg();
1194 }
1195 Entry(sqe)
1196 }
1197}
1198
1199opcode! {
1200 pub struct EpollCtl {
1202 epfd: { impl sealed::UseFixed },
1203 fd: { impl sealed::UseFd },
1204 op: { i32 },
1205 ev: { *const types::epoll_event },
1206 ;;
1207 }
1208
1209 pub const CODE = sys::IORING_OP_EPOLL_CTL;
1210
1211 pub fn build(self) -> Entry {
1212 let EpollCtl { epfd, fd, op, ev } = self;
1213
1214 let mut sqe = sqe_zeroed();
1215 sqe.opcode = Self::CODE;
1216 assign_fd!(sqe.fd = epfd);
1217 sqe.__bindgen_anon_2.addr = ev as _;
1218 sqe.len = op as _;
1219 sqe.__bindgen_anon_1.off = fd as _;
1220 Entry(sqe)
1221 }
1222}
1223
1224opcode! {
1227 pub struct Splice {
1232 fd_in: { impl sealed::UseFixed },
1233 off_in: { i64 },
1234 fd_out: { impl sealed::UseFixed },
1235 off_out: { i64 },
1236 len: { u32 },
1237 ;;
1238 flags: u32 = 0
1240 }
1241
1242 pub const CODE = sys::IORING_OP_SPLICE;
1243
1244 pub fn build(self) -> Entry {
1245 let Splice { fd_in, off_in, fd_out, off_out, len, mut flags } = self;
1246
1247 let mut sqe = sqe_zeroed();
1248 sqe.opcode = Self::CODE;
1249 assign_fd!(sqe.fd = fd_out);
1250 sqe.len = len;
1251 sqe.__bindgen_anon_1.off = off_out as _;
1252
1253 sqe.__bindgen_anon_5.splice_fd_in = match fd_in {
1254 sealed::Target::Fd(fd) => fd,
1255 sealed::Target::Fixed(idx) => {
1256 flags |= sys::SPLICE_F_FD_IN_FIXED;
1257 idx as _
1258 }
1259 };
1260
1261 sqe.__bindgen_anon_2.splice_off_in = off_in as _;
1262 sqe.__bindgen_anon_3.splice_flags = flags;
1263 Entry(sqe)
1264 }
1265}
1266
1267opcode! {
1268 pub struct ProvideBuffers {
1272 addr: { *mut u8 },
1273 len: { i32 },
1274 nbufs: { u16 },
1275 bgid: { u16 },
1276 bid: { u16 }
1277 ;;
1278 }
1279
1280 pub const CODE = sys::IORING_OP_PROVIDE_BUFFERS;
1281
1282 pub fn build(self) -> Entry {
1283 let ProvideBuffers { addr, len, nbufs, bgid, bid } = self;
1284
1285 let mut sqe = sqe_zeroed();
1286 sqe.opcode = Self::CODE;
1287 sqe.fd = nbufs as _;
1288 sqe.__bindgen_anon_2.addr = addr as _;
1289 sqe.len = len as _;
1290 sqe.__bindgen_anon_1.off = bid as _;
1291 sqe.__bindgen_anon_4.buf_group = bgid;
1292 Entry(sqe)
1293 }
1294}
1295
1296opcode! {
1297 pub struct RemoveBuffers {
1300 nbufs: { u16 },
1301 bgid: { u16 }
1302 ;;
1303 }
1304
1305 pub const CODE = sys::IORING_OP_REMOVE_BUFFERS;
1306
1307 pub fn build(self) -> Entry {
1308 let RemoveBuffers { nbufs, bgid } = self;
1309
1310 let mut sqe = sqe_zeroed();
1311 sqe.opcode = Self::CODE;
1312 sqe.fd = nbufs as _;
1313 sqe.__bindgen_anon_4.buf_group = bgid;
1314 Entry(sqe)
1315 }
1316}
1317
1318opcode! {
1321 pub struct Tee {
1323 fd_in: { impl sealed::UseFixed },
1324 fd_out: { impl sealed::UseFixed },
1325 len: { u32 }
1326 ;;
1327 flags: u32 = 0
1328 }
1329
1330 pub const CODE = sys::IORING_OP_TEE;
1331
1332 pub fn build(self) -> Entry {
1333 let Tee { fd_in, fd_out, len, mut flags } = self;
1334
1335 let mut sqe = sqe_zeroed();
1336 sqe.opcode = Self::CODE;
1337
1338 assign_fd!(sqe.fd = fd_out);
1339 sqe.len = len;
1340
1341 sqe.__bindgen_anon_5.splice_fd_in = match fd_in {
1342 sealed::Target::Fd(fd) => fd,
1343 sealed::Target::Fixed(idx) => {
1344 flags |= sys::SPLICE_F_FD_IN_FIXED;
1345 idx as _
1346 }
1347 };
1348
1349 sqe.__bindgen_anon_3.splice_flags = flags;
1350
1351 Entry(sqe)
1352 }
1353}
1354
1355opcode! {
1358 pub struct Shutdown {
1361 fd: { impl sealed::UseFixed },
1362 how: { i32 },
1363 ;;
1364 }
1365
1366 pub const CODE = sys::IORING_OP_SHUTDOWN;
1367
1368 pub fn build(self) -> Entry {
1369 let Shutdown { fd, how } = self;
1370
1371 let mut sqe = sqe_zeroed();
1372 sqe.opcode = Self::CODE;
1373 assign_fd!(sqe.fd = fd);
1374 sqe.len = how as _;
1375 Entry(sqe)
1376 }
1377}
1378
1379opcode! {
1380 pub struct RenameAt {
1383 olddirfd: { impl sealed::UseFd },
1384 oldpath: { *const libc::c_char },
1385 newdirfd: { impl sealed::UseFd },
1386 newpath: { *const libc::c_char },
1387 ;;
1388 flags: u32 = 0
1389 }
1390
1391 pub const CODE = sys::IORING_OP_RENAMEAT;
1392
1393 pub fn build(self) -> Entry {
1394 let RenameAt {
1395 olddirfd, oldpath,
1396 newdirfd, newpath,
1397 flags
1398 } = self;
1399
1400 let mut sqe = sqe_zeroed();
1401 sqe.opcode = Self::CODE;
1402 sqe.fd = olddirfd;
1403 sqe.__bindgen_anon_2.addr = oldpath as _;
1404 sqe.len = newdirfd as _;
1405 sqe.__bindgen_anon_1.off = newpath as _;
1406 sqe.__bindgen_anon_3.rename_flags = flags;
1407 Entry(sqe)
1408 }
1409}
1410
1411opcode! {
1412 pub struct UnlinkAt {
1415 dirfd: { impl sealed::UseFd },
1416 pathname: { *const libc::c_char },
1417 ;;
1418 flags: i32 = 0
1419 }
1420
1421 pub const CODE = sys::IORING_OP_UNLINKAT;
1422
1423 pub fn build(self) -> Entry {
1424 let UnlinkAt { dirfd, pathname, flags } = self;
1425
1426 let mut sqe = sqe_zeroed();
1427 sqe.opcode = Self::CODE;
1428 sqe.fd = dirfd;
1429 sqe.__bindgen_anon_2.addr = pathname as _;
1430 sqe.__bindgen_anon_3.unlink_flags = flags as _;
1431 Entry(sqe)
1432 }
1433}
1434
1435opcode! {
1438 pub struct MkDirAt {
1440 dirfd: { impl sealed::UseFd },
1441 pathname: { *const libc::c_char },
1442 ;;
1443 mode: libc::mode_t = 0
1444 }
1445
1446 pub const CODE = sys::IORING_OP_MKDIRAT;
1447
1448 pub fn build(self) -> Entry {
1449 let MkDirAt { dirfd, pathname, mode } = self;
1450
1451 let mut sqe = sqe_zeroed();
1452 sqe.opcode = Self::CODE;
1453 sqe.fd = dirfd;
1454 sqe.__bindgen_anon_2.addr = pathname as _;
1455 sqe.len = mode;
1456 Entry(sqe)
1457 }
1458}
1459
1460opcode! {
1461 pub struct SymlinkAt {
1463 newdirfd: { impl sealed::UseFd },
1464 target: { *const libc::c_char },
1465 linkpath: { *const libc::c_char },
1466 ;;
1467 }
1468
1469 pub const CODE = sys::IORING_OP_SYMLINKAT;
1470
1471 pub fn build(self) -> Entry {
1472 let SymlinkAt { newdirfd, target, linkpath } = self;
1473
1474 let mut sqe = sqe_zeroed();
1475 sqe.opcode = Self::CODE;
1476 sqe.fd = newdirfd;
1477 sqe.__bindgen_anon_2.addr = target as _;
1478 sqe.__bindgen_anon_1.addr2 = linkpath as _;
1479 Entry(sqe)
1480 }
1481}
1482
1483opcode! {
1484 pub struct LinkAt {
1486 olddirfd: { impl sealed::UseFd },
1487 oldpath: { *const libc::c_char },
1488 newdirfd: { impl sealed::UseFd },
1489 newpath: { *const libc::c_char },
1490 ;;
1491 flags: i32 = 0
1492 }
1493
1494 pub const CODE = sys::IORING_OP_LINKAT;
1495
1496 pub fn build(self) -> Entry {
1497 let LinkAt { olddirfd, oldpath, newdirfd, newpath, flags } = self;
1498
1499 let mut sqe = sqe_zeroed();
1500 sqe.opcode = Self::CODE;
1501 sqe.fd = olddirfd as _;
1502 sqe.__bindgen_anon_2.addr = oldpath as _;
1503 sqe.len = newdirfd as _;
1504 sqe.__bindgen_anon_1.addr2 = newpath as _;
1505 sqe.__bindgen_anon_3.hardlink_flags = flags as _;
1506 Entry(sqe)
1507 }
1508}
1509
1510opcode! {
1513 pub struct GetXattr {
1515 name: { *const libc::c_char },
1516 value: { *mut libc::c_void },
1517 path: { *const libc::c_char },
1518 len: { u32 },
1519 ;;
1520 }
1521
1522 pub const CODE = sys::IORING_OP_GETXATTR;
1523
1524 pub fn build(self) -> Entry {
1525 let GetXattr { name, value, path, len } = self;
1526
1527 let mut sqe = sqe_zeroed();
1528 sqe.opcode = Self::CODE;
1529 sqe.__bindgen_anon_2.addr = name as _;
1530 sqe.len = len;
1531 sqe.__bindgen_anon_1.off = value as _;
1532 unsafe { sqe.__bindgen_anon_6.__bindgen_anon_1.as_mut().addr3 = path as _ };
1533 sqe.__bindgen_anon_3.xattr_flags = 0;
1534 Entry(sqe)
1535 }
1536}
1537
1538opcode! {
1539 pub struct SetXattr {
1541 name: { *const libc::c_char },
1542 value: { *const libc::c_void },
1543 path: { *const libc::c_char },
1544 len: { u32 },
1545 ;;
1546 flags: i32 = 0
1547 }
1548
1549 pub const CODE = sys::IORING_OP_SETXATTR;
1550
1551 pub fn build(self) -> Entry {
1552 let SetXattr { name, value, path, flags, len } = self;
1553
1554 let mut sqe = sqe_zeroed();
1555 sqe.opcode = Self::CODE;
1556 sqe.__bindgen_anon_2.addr = name as _;
1557 sqe.len = len;
1558 sqe.__bindgen_anon_1.off = value as _;
1559 unsafe { sqe.__bindgen_anon_6.__bindgen_anon_1.as_mut().addr3 = path as _ };
1560 sqe.__bindgen_anon_3.xattr_flags = flags as _;
1561 Entry(sqe)
1562 }
1563}
1564
1565opcode! {
1566 pub struct FGetXattr {
1568 fd: { impl sealed::UseFixed },
1569 name: { *const libc::c_char },
1570 value: { *mut libc::c_void },
1571 len: { u32 },
1572 ;;
1573 }
1574
1575 pub const CODE = sys::IORING_OP_FGETXATTR;
1576
1577 pub fn build(self) -> Entry {
1578 let FGetXattr { fd, name, value, len } = self;
1579
1580 let mut sqe = sqe_zeroed();
1581 sqe.opcode = Self::CODE;
1582 assign_fd!(sqe.fd = fd);
1583 sqe.__bindgen_anon_2.addr = name as _;
1584 sqe.len = len;
1585 sqe.__bindgen_anon_1.off = value as _;
1586 sqe.__bindgen_anon_3.xattr_flags = 0;
1587 Entry(sqe)
1588 }
1589}
1590
1591opcode! {
1592 pub struct FSetXattr {
1594 fd: { impl sealed::UseFixed },
1595 name: { *const libc::c_char },
1596 value: { *const libc::c_void },
1597 len: { u32 },
1598 ;;
1599 flags: i32 = 0
1600 }
1601
1602 pub const CODE = sys::IORING_OP_FSETXATTR;
1603
1604 pub fn build(self) -> Entry {
1605 let FSetXattr { fd, name, value, flags, len } = self;
1606
1607 let mut sqe = sqe_zeroed();
1608 sqe.opcode = Self::CODE;
1609 assign_fd!(sqe.fd = fd);
1610 sqe.__bindgen_anon_2.addr = name as _;
1611 sqe.len = len;
1612 sqe.__bindgen_anon_1.off = value as _;
1613 sqe.__bindgen_anon_3.xattr_flags = flags as _;
1614 Entry(sqe)
1615 }
1616}
1617
1618opcode! {
1621 pub struct MsgRingData {
1623 ring_fd: { impl sealed::UseFd },
1624 result: { i32 },
1625 user_data: { u64 },
1626 user_flags: { Option<u32> },
1627 ;;
1628 opcode_flags: u32 = 0
1629 }
1630
1631 pub const CODE = sys::IORING_OP_MSG_RING;
1632
1633 pub fn build(self) -> Entry {
1634 let MsgRingData { ring_fd, result, user_data, user_flags, opcode_flags } = self;
1635
1636 let mut sqe = sqe_zeroed();
1637 sqe.opcode = Self::CODE;
1638 sqe.__bindgen_anon_2.addr = sys::IORING_MSG_DATA.into();
1639 sqe.fd = ring_fd;
1640 sqe.len = result as u32;
1641 sqe.__bindgen_anon_1.off = user_data;
1642 sqe.__bindgen_anon_3.msg_ring_flags = opcode_flags;
1643 if let Some(flags) = user_flags {
1644 sqe.__bindgen_anon_5.file_index = flags;
1645 unsafe {sqe.__bindgen_anon_3.msg_ring_flags |= sys::IORING_MSG_RING_FLAGS_PASS};
1646 }
1647 Entry(sqe)
1648 }
1649}
1650
1651opcode! {
1654 pub struct AsyncCancel2 {
1658 builder: { types::CancelBuilder }
1659 ;;
1660 }
1661
1662 pub const CODE = sys::IORING_OP_ASYNC_CANCEL;
1663
1664 pub fn build(self) -> Entry {
1665 let AsyncCancel2 { builder } = self;
1666
1667 let mut sqe = sqe_zeroed();
1668 sqe.opcode = Self::CODE;
1669 sqe.fd = builder.to_fd();
1670 sqe.__bindgen_anon_2.addr = builder.user_data.unwrap_or(0);
1671 sqe.__bindgen_anon_3.cancel_flags = builder.flags.bits();
1672 Entry(sqe)
1673 }
1674}
1675
1676opcode! {
1677 pub struct UringCmd16 {
1679 fd: { impl sealed::UseFixed },
1680 cmd_op: { u32 },
1681 ;;
1682 buf_index: Option<u16> = None,
1685 cmd: [u8; 16] = [0u8; 16],
1687 addr: Option<u64> = None,
1692 }
1693
1694 pub const CODE = sys::IORING_OP_URING_CMD;
1695
1696 pub fn build(self) -> Entry {
1697 let UringCmd16 { fd, cmd_op, cmd, buf_index, addr } = self;
1698
1699 let mut sqe = sqe_zeroed();
1700 sqe.opcode = Self::CODE;
1701 assign_fd!(sqe.fd = fd);
1702 sqe.__bindgen_anon_1.__bindgen_anon_1.cmd_op = cmd_op;
1703 unsafe { *sqe.__bindgen_anon_6.cmd.as_mut().as_mut_ptr().cast::<[u8; 16]>() = cmd };
1704 if let Some(buf_index) = buf_index {
1705 sqe.__bindgen_anon_4.buf_index = buf_index;
1706 unsafe {
1707 sqe.__bindgen_anon_3.uring_cmd_flags |= sys::IORING_URING_CMD_FIXED;
1708 }
1709 }
1710 if let Some(addr) = addr {
1711 sqe.__bindgen_anon_2.addr = addr;
1712 }
1713 Entry(sqe)
1714 }
1715}
1716
1717opcode! {
1718 pub struct UringCmd80 {
1720 fd: { impl sealed::UseFixed },
1721 cmd_op: { u32 },
1722 ;;
1723 buf_index: Option<u16> = None,
1726 cmd: [u8; 80] = [0u8; 80],
1728 addr: Option<u64> = None,
1733 }
1734
1735 pub const CODE = sys::IORING_OP_URING_CMD;
1736
1737 pub fn build(self) -> Entry128 {
1738 let UringCmd80 { fd, cmd_op, cmd, buf_index, addr } = self;
1739
1740 let cmd1 = cmd[..16].try_into().unwrap();
1741 let cmd2 = cmd[16..].try_into().unwrap();
1742
1743 let mut sqe = sqe_zeroed();
1744 sqe.opcode = Self::CODE;
1745 assign_fd!(sqe.fd = fd);
1746 sqe.__bindgen_anon_1.__bindgen_anon_1.cmd_op = cmd_op;
1747 unsafe { *sqe.__bindgen_anon_6.cmd.as_mut().as_mut_ptr().cast::<[u8; 16]>() = cmd1 };
1748 if let Some(buf_index) = buf_index {
1749 sqe.__bindgen_anon_4.buf_index = buf_index;
1750 unsafe {
1751 sqe.__bindgen_anon_3.uring_cmd_flags |= sys::IORING_URING_CMD_FIXED;
1752 }
1753 }
1754 if let Some(addr) = addr {
1755 sqe.__bindgen_anon_2.addr = addr;
1756 }
1757 Entry128(Entry(sqe), cmd2)
1758 }
1759}
1760
1761opcode! {
1762 pub struct Socket {
1772 domain: { i32 },
1773 socket_type: { i32 },
1774 protocol: { i32 },
1775 ;;
1776 file_index: Option<types::DestinationSlot> = None,
1777 flags: i32 = 0,
1778 }
1779
1780 pub const CODE = sys::IORING_OP_SOCKET;
1781
1782 pub fn build(self) -> Entry {
1783 let Socket { domain, socket_type, protocol, file_index, flags } = self;
1784
1785 let mut sqe = sqe_zeroed();
1786 sqe.opcode = Self::CODE;
1787 sqe.fd = domain as _;
1788 sqe.__bindgen_anon_1.off = socket_type as _;
1789 sqe.len = protocol as _;
1790 sqe.__bindgen_anon_3.rw_flags = flags as _;
1791 if let Some(dest) = file_index {
1792 sqe.__bindgen_anon_5.file_index = dest.kernel_index_arg();
1793 }
1794 Entry(sqe)
1795 }
1796}
1797
1798opcode! {
1799 pub struct AcceptMulti {
1805 fd: { impl sealed::UseFixed },
1806 ;;
1807 allocate_file_index: bool = false,
1808 flags: i32 = 0
1809 }
1810
1811 pub const CODE = sys::IORING_OP_ACCEPT;
1812
1813 pub fn build(self) -> Entry {
1814 let AcceptMulti { fd, allocate_file_index, flags } = self;
1815
1816 let mut sqe = sqe_zeroed();
1817 sqe.opcode = Self::CODE;
1818 assign_fd!(sqe.fd = fd);
1819 sqe.ioprio = sys::IORING_ACCEPT_MULTISHOT as u16;
1820 sqe.__bindgen_anon_3.accept_flags = flags as _;
1823 if allocate_file_index {
1824 sqe.__bindgen_anon_5.file_index = sys::IORING_FILE_INDEX_ALLOC as u32;
1825 }
1826 Entry(sqe)
1827 }
1828}
1829
1830opcode! {
1833 pub struct MsgRingSendFd {
1835 ring_fd: { impl sealed::UseFd },
1836 fixed_slot_src: { types::Fixed },
1837 dest_slot_index: { types::DestinationSlot },
1838 user_data: { u64 },
1839 ;;
1840 opcode_flags: u32 = 0
1841 }
1842
1843 pub const CODE = sys::IORING_OP_MSG_RING;
1844
1845 pub fn build(self) -> Entry {
1846 let MsgRingSendFd { ring_fd, fixed_slot_src, dest_slot_index, user_data, opcode_flags } = self;
1847
1848 let mut sqe = sqe_zeroed();
1849 sqe.opcode = Self::CODE;
1850 sqe.__bindgen_anon_2.addr = sys::IORING_MSG_SEND_FD.into();
1851 sqe.fd = ring_fd;
1852 sqe.__bindgen_anon_1.off = user_data;
1853 unsafe { sqe.__bindgen_anon_6.__bindgen_anon_1.as_mut().addr3 = fixed_slot_src.0 as u64 };
1854 sqe.__bindgen_anon_5.file_index = dest_slot_index.kernel_index_arg();
1855 sqe.__bindgen_anon_3.msg_ring_flags = opcode_flags;
1856 Entry(sqe)
1857 }
1858}
1859
1860opcode! {
1863 pub struct SendZc {
1877 fd: { impl sealed::UseFixed },
1878 buf: { *const u8 },
1879 len: { u32 },
1880 ;;
1881 buf_index: Option<u16> = None,
1888 dest_addr: *const libc::sockaddr = core::ptr::null(),
1889 dest_addr_len: libc::socklen_t = 0,
1890 flags: i32 = 0,
1891 zc_flags: u16 = 0,
1892 }
1893
1894 pub const CODE = sys::IORING_OP_SEND_ZC;
1895
1896 pub fn build(self) -> Entry {
1897 let SendZc { fd, buf, len, buf_index, dest_addr, dest_addr_len, flags, zc_flags } = self;
1898
1899 let mut sqe = sqe_zeroed();
1900 sqe.opcode = Self::CODE;
1901 assign_fd!(sqe.fd = fd);
1902 sqe.__bindgen_anon_2.addr = buf as _;
1903 sqe.len = len;
1904 sqe.__bindgen_anon_3.msg_flags = flags as _;
1905 sqe.ioprio = zc_flags;
1906 if let Some(buf_index) = buf_index {
1907 sqe.__bindgen_anon_4.buf_index = buf_index;
1908 sqe.ioprio |= sys::IORING_RECVSEND_FIXED_BUF as u16;
1909 }
1910 sqe.__bindgen_anon_1.addr2 = dest_addr as _;
1911 sqe.__bindgen_anon_5.__bindgen_anon_1.addr_len = dest_addr_len as _;
1912 Entry(sqe)
1913 }
1914}
1915
1916opcode! {
1919 #[derive(Debug)]
1924 pub struct SendMsgZc {
1925 fd: { impl sealed::UseFixed },
1926 msg: { *const libc::msghdr },
1927 ;;
1928 ioprio: u16 = 0,
1929 flags: u32 = 0
1930 }
1931
1932 pub const CODE = sys::IORING_OP_SENDMSG_ZC;
1933
1934 pub fn build(self) -> Entry {
1935 let SendMsgZc { fd, msg, ioprio, flags } = self;
1936
1937 let mut sqe = sqe_zeroed();
1938 sqe.opcode = Self::CODE;
1939 assign_fd!(sqe.fd = fd);
1940 sqe.ioprio = ioprio;
1941 sqe.__bindgen_anon_2.addr = msg as _;
1942 sqe.len = 1;
1943 sqe.__bindgen_anon_3.msg_flags = flags;
1944 Entry(sqe)
1945 }
1946}
1947
1948opcode! {
1951 pub struct ReadMulti {
1953 fd: { impl sealed::UseFixed },
1954 len: { u32 },
1955 buf_group: { u16 },
1956 ;;
1957 offset: u64 = 0,
1958 }
1959
1960 pub const CODE = sys::IORING_OP_READ_MULTISHOT;
1961
1962 pub fn build(self) -> Entry {
1963 let Self { fd, len, buf_group, offset } = self;
1964
1965 let mut sqe = sqe_zeroed();
1966 sqe.opcode = Self::CODE;
1967 assign_fd!(sqe.fd = fd);
1968 sqe.__bindgen_anon_1.off = offset;
1969 sqe.len = len;
1970 sqe.__bindgen_anon_4.buf_group = buf_group;
1971 sqe.flags = crate::squeue::Flags::BUFFER_SELECT.bits();
1972 Entry(sqe)
1973 }
1974}
1975
1976opcode! {
1977 #[derive(Debug)]
1986 pub struct FutexWait {
1987 futex: { *const u32 },
1988 val: { u64 },
1989 mask: { u64 },
1990 futex_flags: { u32 },
1991 ;;
1992 flags: u32 = 0
1993 }
1994
1995 pub const CODE = sys::IORING_OP_FUTEX_WAIT;
1996
1997 pub fn build(self) -> Entry {
1998 let FutexWait { futex, val, mask, futex_flags, flags } = self;
1999
2000 let mut sqe = sqe_zeroed();
2001 sqe.opcode = Self::CODE;
2002 sqe.fd = futex_flags as _;
2003 sqe.__bindgen_anon_2.addr = futex as usize as _;
2004 sqe.__bindgen_anon_1.off = val;
2005 unsafe { sqe.__bindgen_anon_6.__bindgen_anon_1.as_mut().addr3 = mask };
2006 sqe.__bindgen_anon_3.futex_flags = flags;
2007 Entry(sqe)
2008 }
2009}
2010
2011opcode! {
2012 #[derive(Debug)]
2020 pub struct FutexWake {
2021 futex: { *const u32 },
2022 val: { u64 },
2023 mask: { u64 },
2024 futex_flags: { u32 },
2025 ;;
2026 flags: u32 = 0
2027 }
2028
2029 pub const CODE = sys::IORING_OP_FUTEX_WAKE;
2030
2031 pub fn build(self) -> Entry {
2032 let FutexWake { futex, val, mask, futex_flags, flags } = self;
2033
2034 let mut sqe = sqe_zeroed();
2035 sqe.opcode = Self::CODE;
2036 sqe.fd = futex_flags as _;
2037 sqe.__bindgen_anon_2.addr = futex as usize as _;
2038 sqe.__bindgen_anon_1.off = val;
2039 unsafe { sqe.__bindgen_anon_6.__bindgen_anon_1.as_mut().addr3 = mask };
2040 sqe.__bindgen_anon_3.futex_flags = flags;
2041 Entry(sqe)
2042 }
2043}
2044
2045opcode! {
2046 #[derive(Debug)]
2052 pub struct FutexWaitV {
2053 futexv: { *const types::FutexWaitV },
2054 nr_futex: { u32 },
2055 ;;
2056 flags: u32 = 0
2057 }
2058
2059 pub const CODE = sys::IORING_OP_FUTEX_WAITV;
2060
2061 pub fn build(self) -> Entry {
2062 let FutexWaitV { futexv, nr_futex, flags } = self;
2063
2064 let mut sqe = sqe_zeroed();
2065 sqe.opcode = Self::CODE;
2066 sqe.__bindgen_anon_2.addr = futexv as usize as _;
2067 sqe.len = nr_futex;
2068 sqe.__bindgen_anon_3.futex_flags = flags;
2069 Entry(sqe)
2070 }
2071}
2072
2073opcode! {
2074 #[derive(Debug)]
2078 pub struct WaitId {
2079 idtype: { libc::idtype_t },
2080 id: { libc::id_t },
2081 options: { libc::c_int },
2082 ;;
2083 infop: *const libc::siginfo_t = std::ptr::null(),
2084 flags: libc::c_uint = 0,
2085 }
2086
2087 pub const CODE = sys::IORING_OP_WAITID;
2088
2089 pub fn build(self) -> Entry {
2090 let mut sqe = sqe_zeroed();
2091 sqe.opcode = Self::CODE;
2092 sqe.fd = self.id as _;
2093 sqe.len = self.idtype as _;
2094 sqe.__bindgen_anon_3.waitid_flags = self.flags;
2095 sqe.__bindgen_anon_5.file_index = self.options as _;
2096 sqe.__bindgen_anon_1.addr2 = self.infop as _;
2097 Entry(sqe)
2098 }
2099}
2100
2101opcode! {
2104 #[derive(Debug)]
2109 pub struct FixedFdInstall {
2110 fd: { types::Fixed },
2111 file_flags: { u32 },
2112 ;;
2113 }
2114
2115 pub const CODE = sys::IORING_OP_FIXED_FD_INSTALL;
2116
2117 pub fn build(self) -> Entry {
2118 let FixedFdInstall { fd, file_flags } = self;
2119
2120 let mut sqe = sqe_zeroed();
2121 sqe.opcode = Self::CODE;
2122 sqe.fd = fd.0 as _;
2123 sqe.flags = crate::squeue::Flags::FIXED_FILE.bits();
2124 sqe.__bindgen_anon_3.install_fd_flags = file_flags;
2125 Entry(sqe)
2126 }
2127}
2128
2129opcode! {
2132 #[derive(Debug)]
2134 pub struct Ftruncate {
2135 fd: { impl sealed::UseFixed },
2136 len: { u64 },
2137 ;;
2138 }
2139
2140 pub const CODE = sys::IORING_OP_FTRUNCATE;
2141
2142 pub fn build(self) -> Entry {
2143 let Ftruncate { fd, len } = self;
2144
2145 let mut sqe = sqe_zeroed();
2146 sqe.opcode = Self::CODE;
2147 assign_fd!(sqe.fd = fd);
2148 sqe.__bindgen_anon_1.off = len;
2149 Entry(sqe)
2150 }
2151}
2152
2153opcode! {
2156 pub struct SendBundle {
2158 fd: { impl sealed::UseFixed },
2159 buf_group: { u16 },
2160 ;;
2161 flags: i32 = 0,
2162 len: u32 = 0
2163 }
2164
2165 pub const CODE = sys::IORING_OP_SEND;
2166
2167 pub fn build(self) -> Entry {
2168 let SendBundle { fd, len, flags, buf_group } = self;
2169
2170 let mut sqe = sqe_zeroed();
2171 sqe.opcode = Self::CODE;
2172 assign_fd!(sqe.fd = fd);
2173 sqe.len = len;
2174 sqe.__bindgen_anon_3.msg_flags = flags as _;
2175 sqe.ioprio |= sys::IORING_RECVSEND_BUNDLE as u16;
2176 sqe.flags |= crate::squeue::Flags::BUFFER_SELECT.bits();
2177 sqe.__bindgen_anon_4.buf_group = buf_group;
2178 Entry(sqe)
2179 }
2180}
2181
2182opcode! {
2183 pub struct RecvBundle {
2193 fd: { impl sealed::UseFixed },
2194 buf_group: { u16 },
2195 ;;
2196 flags: i32 = 0
2197 }
2198
2199 pub const CODE = sys::IORING_OP_RECV;
2200
2201 pub fn build(self) -> Entry {
2202 let RecvBundle { fd, buf_group, flags } = self;
2203
2204 let mut sqe = sqe_zeroed();
2205 sqe.opcode = Self::CODE;
2206 assign_fd!(sqe.fd = fd);
2207 sqe.__bindgen_anon_3.msg_flags = flags as _;
2208 sqe.__bindgen_anon_4.buf_group = buf_group;
2209 sqe.flags |= crate::squeue::Flags::BUFFER_SELECT.bits();
2210 sqe.ioprio |= sys::IORING_RECVSEND_BUNDLE as u16;
2211 Entry(sqe)
2212 }
2213}
2214
2215opcode! {
2216 pub struct RecvMultiBundle {
2234 fd: { impl sealed::UseFixed },
2235 buf_group: { u16 },
2236 ;;
2237 flags: i32 = 0
2238 }
2239
2240 pub const CODE = sys::IORING_OP_RECV;
2241
2242 pub fn build(self) -> Entry {
2243 let RecvMultiBundle { fd, buf_group, flags } = self;
2244
2245 let mut sqe = sqe_zeroed();
2246 sqe.opcode = Self::CODE;
2247 assign_fd!(sqe.fd = fd);
2248 sqe.__bindgen_anon_3.msg_flags = flags as _;
2249 sqe.__bindgen_anon_4.buf_group = buf_group;
2250 sqe.flags |= crate::squeue::Flags::BUFFER_SELECT.bits();
2251 sqe.ioprio = sys::IORING_RECV_MULTISHOT as _;
2252 sqe.ioprio |= sys::IORING_RECVSEND_BUNDLE as u16;
2253 Entry(sqe)
2254 }
2255}
2256
2257opcode! {
2260 pub struct Bind {
2262 fd: { impl sealed::UseFixed },
2263 addr: { *const libc::sockaddr },
2264 addrlen: { libc::socklen_t }
2265 ;;
2266 }
2267
2268 pub const CODE = sys::IORING_OP_BIND;
2269
2270 pub fn build(self) -> Entry {
2271 let Bind { fd, addr, addrlen } = self;
2272
2273 let mut sqe = sqe_zeroed();
2274 sqe.opcode = Self::CODE;
2275 assign_fd!(sqe.fd = fd);
2276 sqe.__bindgen_anon_2.addr = addr as _;
2277 sqe.__bindgen_anon_1.off = addrlen as _;
2278 Entry(sqe)
2279 }
2280}
2281
2282opcode! {
2283 pub struct Listen {
2285 fd: { impl sealed::UseFixed },
2286 backlog: { i32 },
2287 ;;
2288 }
2289
2290 pub const CODE = sys::IORING_OP_LISTEN;
2291
2292 pub fn build(self) -> Entry {
2293 let Listen { fd, backlog } = self;
2294
2295 let mut sqe = sqe_zeroed();
2296 sqe.opcode = Self::CODE;
2297 assign_fd!(sqe.fd = fd);
2298 sqe.len = backlog as _;
2299 Entry(sqe)
2300 }
2301}
2302
2303opcode! {
2306 pub struct RecvZc {
2308 fd: { impl sealed::UseFixed },
2309 len: { u32 },
2310 ;;
2311 ifq: u32 = 0,
2312 ioprio: u16 = 0,
2313 }
2314
2315 pub const CODE = sys::IORING_OP_RECV_ZC;
2316
2317 pub fn build(self) -> Entry {
2318 let Self { fd, len, ifq, ioprio } = self;
2319
2320 let mut sqe = sqe_zeroed();
2321 sqe.opcode = Self::CODE;
2322 assign_fd!(sqe.fd = fd);
2323 sqe.len = len;
2324 sqe.ioprio = ioprio | sys::IORING_RECV_MULTISHOT as u16;
2325 sqe.__bindgen_anon_5.zcrx_ifq_idx = ifq;
2326 Entry(sqe)
2327 }
2328}
2329
2330opcode! {
2331 pub struct EpollWait {
2333 fd: { impl sealed::UseFixed },
2334 events: { *mut types::epoll_event },
2335 max_events: { u32 },
2336 ;;
2337 flags: u32 = 0,
2338 }
2339
2340 pub const CODE = sys::IORING_OP_EPOLL_WAIT;
2341
2342 pub fn build(self) -> Entry {
2343 let Self { fd, events, max_events, flags } = self;
2344
2345 let mut sqe = sqe_zeroed();
2346 sqe.opcode = Self::CODE;
2347 assign_fd!(sqe.fd = fd);
2348 sqe.__bindgen_anon_2.addr = events as u64;
2349 sqe.len = max_events;
2350 sqe.__bindgen_anon_3.poll32_events = flags;
2351 Entry(sqe)
2352 }
2353}
2354
2355opcode! {
2356 pub struct ReadvFixed {
2358 fd: { impl sealed::UseFixed },
2359 iovec: { *const ::libc::iovec },
2360 len: { u32 },
2361 buf_index: { u16 },
2362 ;;
2363 ioprio: u16 = 0,
2364 offset: u64 = 0,
2365 rw_flags: i32 = 0,
2366 }
2367
2368 pub const CODE = sys::IORING_OP_READV_FIXED;
2369
2370 pub fn build(self) -> Entry {
2371 let Self { fd, iovec, len, buf_index, offset, ioprio, rw_flags } = self;
2372
2373 let mut sqe = sqe_zeroed();
2374 sqe.opcode = Self::CODE;
2375 assign_fd!(sqe.fd = fd);
2376 sqe.__bindgen_anon_1.off = offset as _;
2377 sqe.__bindgen_anon_2.addr = iovec as _;
2378 sqe.len = len;
2379 sqe.__bindgen_anon_4.buf_index = buf_index;
2380 sqe.ioprio = ioprio;
2381 sqe.__bindgen_anon_3.rw_flags = rw_flags as _;
2382 Entry(sqe)
2383 }
2384}
2385
2386opcode! {
2387 pub struct WritevFixed {
2389 fd: { impl sealed::UseFixed },
2390 iovec: { *const ::libc::iovec },
2391 len: { u32 },
2392 buf_index: { u16 },
2393 ;;
2394 ioprio: u16 = 0,
2395 offset: u64 = 0,
2396 rw_flags: i32 = 0,
2397 write_stream: u8 = 0,
2400 }
2401
2402 pub const CODE = sys::IORING_OP_WRITEV_FIXED;
2403
2404 pub fn build(self) -> Entry {
2405 let Self { fd, iovec, len, buf_index, offset, ioprio, rw_flags, write_stream } = self;
2406
2407 let mut sqe = sqe_zeroed();
2408 sqe.opcode = Self::CODE;
2409 assign_fd!(sqe.fd = fd);
2410 sqe.__bindgen_anon_1.off = offset as _;
2411 sqe.__bindgen_anon_2.addr = iovec as _;
2412 sqe.len = len;
2413 sqe.__bindgen_anon_4.buf_index = buf_index;
2414 sqe.ioprio = ioprio;
2415 sqe.__bindgen_anon_3.rw_flags = rw_flags as _;
2416 sqe.__bindgen_anon_5.__bindgen_anon_2.write_stream = write_stream;
2417 Entry(sqe)
2418 }
2419}
2420
2421opcode! {
2424 pub struct Pipe {
2426 fds: { *mut RawFd },
2427 ;;
2428 flags: u32 = 0,
2429 file_index: Option<types::DestinationSlot> = None,
2430 }
2431
2432 pub const CODE = sys::IORING_OP_PIPE;
2433
2434 pub fn build(self) -> Entry {
2435 let Self { fds, flags, file_index } = self;
2436
2437 let mut sqe = sqe_zeroed();
2438 sqe.opcode = Self::CODE;
2439 sqe.fd = 0;
2440 sqe.__bindgen_anon_2.addr = fds as _;
2441 sqe.__bindgen_anon_3.pipe_flags = flags;
2442 if let Some(dest) = file_index {
2443 sqe.__bindgen_anon_5.file_index = dest.kernel_index_arg();
2444 }
2445 Entry(sqe)
2446 }
2447}