1#![allow(missing_docs)]
8
9use std::fmt::{Debug, Formatter};
10use std::mem;
11
12use bitflags::bitflags;
13use vm_memory::ByteValued;
14
15pub use libc::{
16 blksize_t, dev_t, ino64_t, mode_t, nlink_t, off64_t, pread64, preadv64, pwrite64, pwritev64,
17 stat64, statvfs64,
18};
19
20pub const KERNEL_VERSION: u32 = 7;
22
23pub const KERNEL_MINOR_VERSION: u32 = 33;
25
26pub const KERNEL_MINOR_VERSION_INIT_OUT_SIZE: u32 = 5;
28
29pub const KERNEL_MINOR_VERSION_INIT_22_OUT_SIZE: u32 = 23;
31
32pub const KERNEL_MINOR_VERSION_LOOKUP_NEGATIVE_ENTRY_ZERO: u32 = 4;
34
35pub const ROOT_ID: u64 = 1;
37
38const FATTR_MODE: u32 = 0x1;
40const FATTR_UID: u32 = 0x2;
41const FATTR_GID: u32 = 0x4;
42const FATTR_SIZE: u32 = 0x8;
43const FATTR_ATIME: u32 = 0x10;
44const FATTR_MTIME: u32 = 0x20;
45pub const FATTR_FH: u32 = 0x40;
46const FATTR_ATIME_NOW: u32 = 0x80;
47const FATTR_MTIME_NOW: u32 = 0x100;
48pub const FATTR_LOCKOWNER: u32 = 0x200;
49const FATTR_CTIME: u32 = 0x400;
50const FATTR_KILL_SUIDGID: u32 = 0x800;
51
52bitflags! {
53 pub struct SetattrValid: u32 {
54 const MODE = FATTR_MODE;
55 const UID = FATTR_UID;
56 const GID = FATTR_GID;
57 const SIZE = FATTR_SIZE;
58 const ATIME = FATTR_ATIME;
59 const MTIME = FATTR_MTIME;
60 const ATIME_NOW = FATTR_ATIME_NOW;
61 const MTIME_NOW = FATTR_MTIME_NOW;
62 const CTIME = FATTR_CTIME;
63 const KILL_SUIDGID = FATTR_KILL_SUIDGID;
64 }
65}
66
67pub const FOPEN_IN_KILL_SUIDGID: u32 = 1;
71
72const FOPEN_DIRECT_IO: u32 = 1;
74
75const FOPEN_KEEP_CACHE: u32 = 2;
77
78const FOPEN_NONSEEKABLE: u32 = 4;
80
81const FOPEN_CACHE_DIR: u32 = 8;
83
84const FOPEN_STREAM: u32 = 16;
86
87bitflags! {
88 pub struct OpenOptions: u32 {
91 const DIRECT_IO = FOPEN_DIRECT_IO;
93 const KEEP_CACHE = FOPEN_KEEP_CACHE;
95 const NONSEEKABLE = FOPEN_NONSEEKABLE;
97 const CACHE_DIR = FOPEN_CACHE_DIR;
99 const STREAM = FOPEN_STREAM;
101 }
102}
103
104const ASYNC_READ: u64 = 0x1;
108
109const POSIX_LOCKS: u64 = 0x2;
111
112const FILE_OPS: u64 = 0x4;
114
115const ATOMIC_O_TRUNC: u64 = 0x8;
117
118const EXPORT_SUPPORT: u64 = 0x10;
120
121const BIG_WRITES: u64 = 0x20;
123
124const DONT_MASK: u64 = 0x40;
126
127const SPLICE_WRITE: u64 = 0x80;
129
130const SPLICE_MOVE: u64 = 0x100;
132
133const SPLICE_READ: u64 = 0x200;
135
136const FLOCK_LOCKS: u64 = 0x400;
138
139const HAS_IOCTL_DIR: u64 = 0x800;
141
142const AUTO_INVAL_DATA: u64 = 0x1000;
144
145const DO_READDIRPLUS: u64 = 0x2000;
147
148const READDIRPLUS_AUTO: u64 = 0x4000;
150
151const ASYNC_DIO: u64 = 0x8000;
153
154const WRITEBACK_CACHE: u64 = 0x1_0000;
156
157const NO_OPEN_SUPPORT: u64 = 0x2_0000;
159
160const PARALLEL_DIROPS: u64 = 0x4_0000;
162
163const HANDLE_KILLPRIV: u64 = 0x8_0000;
165
166const POSIX_ACL: u64 = 0x10_0000;
168
169const ABORT_ERROR: u64 = 0x20_0000;
171
172const MAX_PAGES: u64 = 0x40_0000;
174
175const CACHE_SYMLINKS: u64 = 0x80_0000;
177
178const NO_OPENDIR_SUPPORT: u64 = 0x100_0000;
180
181const EXPLICIT_INVAL_DATA: u64 = 0x200_0000;
183
184const MAP_ALIGNMENT: u64 = 0x400_0000;
187
188const SUBMOUNTS: u64 = 0x800_0000;
190
191const HANDLE_KILLPRIV_V2: u64 = 0x1000_0000;
193
194const INIT_EXT: u64 = 0x4000_0000;
196
197const PERFILE_DAX: u64 = 0x2_0000_0000;
199
200const FD_PASSTHROUGH: u64 = 0x8000_0000_0000_0000;
204
205pub const FUSE_ATTR_DAX: u32 = 1 << 1;
215
216bitflags! {
217 pub struct FsOptions: u64 {
220 const ASYNC_READ = ASYNC_READ;
228
229 const POSIX_LOCKS = POSIX_LOCKS;
234
235 const FILE_OPS = FILE_OPS;
237
238 const ATOMIC_O_TRUNC = ATOMIC_O_TRUNC;
244
245 const EXPORT_SUPPORT = EXPORT_SUPPORT;
249
250 const BIG_WRITES = BIG_WRITES;
252
253 const DONT_MASK = DONT_MASK;
258
259 const SPLICE_WRITE = SPLICE_WRITE;
264
265 const SPLICE_MOVE = SPLICE_MOVE;
270
271 const SPLICE_READ = SPLICE_READ;
276
277 const FLOCK_LOCKS = FLOCK_LOCKS;
285
286 const HAS_IOCTL_DIR = HAS_IOCTL_DIR;
290
291 const AUTO_INVAL_DATA = AUTO_INVAL_DATA;
307
308 const DO_READDIRPLUS = DO_READDIRPLUS;
313
314 const READDIRPLUS_AUTO = READDIRPLUS_AUTO;
328
329 const ASYNC_DIO = ASYNC_DIO;
337
338 const WRITEBACK_CACHE = WRITEBACK_CACHE;
344
345 const ZERO_MESSAGE_OPEN = NO_OPEN_SUPPORT;
354
355 const PARALLEL_DIROPS = PARALLEL_DIROPS;
361
362 const HANDLE_KILLPRIV = HANDLE_KILLPRIV;
367
368 const POSIX_ACL = POSIX_ACL;
382
383 const ABORT_ERROR = ABORT_ERROR;
390
391 const MAX_PAGES = MAX_PAGES;
398
399 const CACHE_SYMLINKS = CACHE_SYMLINKS;
405
406 const ZERO_MESSAGE_OPENDIR = NO_OPENDIR_SUPPORT;
417
418 const EXPLICIT_INVAL_DATA = EXPLICIT_INVAL_DATA;
427
428 const MAP_ALIGNMENT = MAP_ALIGNMENT;
435
436 const SUBMOUNTS = SUBMOUNTS;
438
439 const HANDLE_KILLPRIV_V2 = HANDLE_KILLPRIV_V2;
449
450 const FD_PASSTHROUGH = FD_PASSTHROUGH;
452
453 const INIT_EXT = INIT_EXT;
455
456 const PERFILE_DAX = PERFILE_DAX;
461 }
462}
463
464pub const RELEASE_FLUSH: u32 = 1;
466pub const RELEASE_FLOCK_UNLOCK: u32 = 2;
467
468pub const GETATTR_FH: u32 = 1;
470
471pub const LK_FLOCK: u32 = 1;
473
474pub const WRITE_CACHE: u32 = 1;
478
479pub const WRITE_LOCKOWNER: u32 = 2;
481
482pub const WRITE_KILL_PRIV: u32 = 4;
484
485pub const READ_LOCKOWNER: u32 = 2;
487
488const IOCTL_COMPAT: u32 = 1;
492
493const IOCTL_UNRESTRICTED: u32 = 2;
495
496const IOCTL_RETRY: u32 = 4;
498
499const IOCTL_32BIT: u32 = 8;
501
502const IOCTL_DIR: u32 = 16;
504
505const IOCTL_COMPAT_X32: u32 = 32;
507
508const IOCTL_MAX_IOV: u32 = 256;
510
511bitflags! {
512 pub struct IoctlFlags: u32 {
513 const IOCTL_COMPAT = IOCTL_COMPAT;
515
516 const IOCTL_UNRESTRICTED = IOCTL_UNRESTRICTED;
518
519 const IOCTL_RETRY = IOCTL_RETRY;
521
522 const IOCTL_32BIT = IOCTL_32BIT;
524
525 const IOCTL_DIR = IOCTL_DIR;
527
528 const IOCTL_COMPAT_X32 = IOCTL_COMPAT_X32;
530
531 const IOCTL_MAX_IOV = IOCTL_MAX_IOV;
533 }
534}
535
536pub const ATTR_SUBMOUNT: u32 = 1;
539
540pub const POLL_SCHEDULE_NOTIFY: u32 = 1;
542
543pub const FSYNC_FDATASYNC: u32 = 1;
547
548pub const FUSE_MIN_READ_BUFFER: u32 = 8192;
550
551pub const FUSE_COMPAT_ENTRY_OUT_SIZE: usize = 120;
552pub const FUSE_COMPAT_ATTR_OUT_SIZE: usize = 96;
553pub const FUSE_COMPAT_MKNOD_IN_SIZE: usize = 8;
554pub const FUSE_COMPAT_WRITE_IN_SIZE: usize = 24;
555pub const FUSE_COMPAT_STATFS_SIZE: usize = 48;
556pub const FUSE_COMPAT_INIT_OUT_SIZE: usize = 8;
557pub const FUSE_COMPAT_22_INIT_OUT_SIZE: usize = 24;
558
559#[repr(C)]
563#[derive(Debug, Default, Copy, Clone)]
564pub struct Attr {
565 pub ino: u64,
566 pub size: u64,
567 pub blocks: u64,
568 pub atime: u64,
569 pub mtime: u64,
570 pub ctime: u64,
571 pub atimensec: u32,
572 pub mtimensec: u32,
573 pub ctimensec: u32,
574 pub mode: u32,
575 pub nlink: u32,
576 pub uid: u32,
577 pub gid: u32,
578 pub rdev: u32,
579 pub blksize: u32,
580 pub flags: u32,
581}
582unsafe impl ByteValued for Attr {}
583
584impl From<stat64> for Attr {
585 fn from(st: stat64) -> Attr {
586 Attr::with_flags(st, 0)
587 }
588}
589
590impl Attr {
591 pub fn with_flags(st: stat64, flags: u32) -> Attr {
592 Attr {
593 ino: st.st_ino,
594 size: st.st_size as u64,
595 blocks: st.st_blocks as u64,
596 atime: st.st_atime as u64,
597 mtime: st.st_mtime as u64,
598 ctime: st.st_ctime as u64,
599 atimensec: st.st_atime_nsec as u32,
600 mtimensec: st.st_mtime_nsec as u32,
601 ctimensec: st.st_ctime_nsec as u32,
602 mode: st.st_mode,
603 #[allow(clippy::unnecessary_cast)]
607 nlink: st.st_nlink as u32,
608 uid: st.st_uid,
609 gid: st.st_gid,
610 rdev: st.st_rdev as u32,
611 blksize: st.st_blksize as u32,
612 flags,
613 }
614 }
615}
616
617impl From<Attr> for stat64 {
618 fn from(attr: Attr) -> stat64 {
619 let mut out: stat64 = unsafe { mem::zeroed() };
621 out.st_ino = attr.ino;
622 out.st_size = attr.size as i64;
623 out.st_blocks = attr.blocks as i64;
624 out.st_atime = attr.atime as i64;
625 out.st_mtime = attr.mtime as i64;
626 out.st_ctime = attr.ctime as i64;
627 out.st_atime_nsec = attr.atimensec as i64;
628 out.st_mtime_nsec = attr.mtimensec as i64;
629 out.st_ctime_nsec = attr.ctimensec as i64;
630 out.st_mode = attr.mode as mode_t;
631 out.st_nlink = attr.nlink as nlink_t;
632 out.st_uid = attr.uid;
633 out.st_gid = attr.gid;
634 out.st_rdev = attr.rdev as dev_t;
635 out.st_blksize = attr.blksize as blksize_t;
636
637 out
638 }
639}
640
641#[repr(C)]
642#[derive(Debug, Default, Copy, Clone)]
643pub struct Kstatfs {
644 pub blocks: u64,
645 pub bfree: u64,
646 pub bavail: u64,
647 pub files: u64,
648 pub ffree: u64,
649 pub bsize: u32,
650 pub namelen: u32,
651 pub frsize: u32,
652 pub padding: u32,
653 pub spare: [u32; 6],
654}
655unsafe impl ByteValued for Kstatfs {}
656
657impl From<statvfs64> for Kstatfs {
658 fn from(st: statvfs64) -> Self {
659 Kstatfs {
660 blocks: st.f_blocks,
661 bfree: st.f_bfree,
662 bavail: st.f_bavail,
663 files: st.f_files,
664 ffree: st.f_ffree,
665 bsize: st.f_bsize as u32,
666 namelen: st.f_namemax as u32,
667 frsize: st.f_frsize as u32,
668 ..Default::default()
669 }
670 }
671}
672
673#[repr(C)]
674#[derive(Debug, Default, Copy, Clone)]
675pub struct FileLock {
676 pub start: u64,
677 pub end: u64,
678 pub type_: u32,
679 pub pid: u32, }
681unsafe impl ByteValued for FileLock {}
682
683#[repr(u32)]
684#[derive(Debug, Copy, Clone)]
685pub enum Opcode {
686 Lookup = 1,
687 Forget = 2, Getattr = 3,
689 Setattr = 4,
690 Readlink = 5,
691 Symlink = 6,
692 Mknod = 8,
693 Mkdir = 9,
694 Unlink = 10,
695 Rmdir = 11,
696 Rename = 12,
697 Link = 13,
698 Open = 14,
699 Read = 15,
700 Write = 16,
701 Statfs = 17,
702 Release = 18,
703 Fsync = 20,
704 Setxattr = 21,
705 Getxattr = 22,
706 Listxattr = 23,
707 Removexattr = 24,
708 Flush = 25,
709 Init = 26,
710 Opendir = 27,
711 Readdir = 28,
712 Releasedir = 29,
713 Fsyncdir = 30,
714 Getlk = 31,
715 Setlk = 32,
716 Setlkw = 33,
717 Access = 34,
718 Create = 35,
719 Interrupt = 36,
720 Bmap = 37,
721 Destroy = 38,
722 Ioctl = 39,
723 Poll = 40,
724 NotifyReply = 41,
725 BatchForget = 42,
726 Fallocate = 43,
727 Readdirplus = 44,
728 Rename2 = 45,
729 Lseek = 46,
730 CopyFileRange = 47,
731 SetupMapping = 48,
732 RemoveMapping = 49,
733 MaxOpcode = 50,
734
735 CuseInitBswapReserved = 1_048_576, InitBswapReserved = 436_207_616, }
739
740impl From<u32> for Opcode {
741 fn from(op: u32) -> Opcode {
742 if op >= Opcode::MaxOpcode as u32 {
743 return Opcode::MaxOpcode;
744 }
745 unsafe { mem::transmute(op) }
746 }
747}
748
749#[repr(u32)]
750#[derive(Debug, Copy, Clone)]
751pub enum NotifyOpcode {
752 Poll = 1,
753 InvalInode = 2,
754 InvalEntry = 3,
755 Store = 4,
756 Retrieve = 5,
757 Delete = 6,
758 CodeMax = 7,
759}
760
761#[repr(C)]
762#[derive(Debug, Default, Copy, Clone)]
763pub struct EntryOut {
764 pub nodeid: u64, pub generation: u64, pub entry_valid: u64, pub attr_valid: u64, pub entry_valid_nsec: u32,
769 pub attr_valid_nsec: u32,
770 pub attr: Attr,
771}
772unsafe impl ByteValued for EntryOut {}
773
774#[repr(C)]
775#[derive(Debug, Default, Copy, Clone)]
776pub struct ForgetIn {
777 pub nlookup: u64,
778}
779unsafe impl ByteValued for ForgetIn {}
780
781#[repr(C)]
782#[derive(Debug, Default, Copy, Clone)]
783pub struct ForgetOne {
784 pub nodeid: u64,
785 pub nlookup: u64,
786}
787unsafe impl ByteValued for ForgetOne {}
788
789#[repr(C)]
790#[derive(Debug, Default, Copy, Clone)]
791pub struct BatchForgetIn {
792 pub count: u32,
793 pub dummy: u32,
794}
795unsafe impl ByteValued for BatchForgetIn {}
796
797#[repr(C)]
798#[derive(Debug, Default, Copy, Clone)]
799pub struct GetattrIn {
800 pub flags: u32,
801 pub dummy: u32,
802 pub fh: u64,
803}
804unsafe impl ByteValued for GetattrIn {}
805
806#[repr(C)]
807#[derive(Debug, Default, Copy, Clone)]
808pub struct AttrOut {
809 pub attr_valid: u64, pub attr_valid_nsec: u32,
811 pub dummy: u32,
812 pub attr: Attr,
813}
814unsafe impl ByteValued for AttrOut {}
815
816#[repr(C)]
817#[derive(Debug, Default, Copy, Clone)]
818pub struct MknodIn {
819 pub mode: u32,
820 pub rdev: u32,
821 pub umask: u32,
822 pub padding: u32,
823}
824unsafe impl ByteValued for MknodIn {}
825
826#[repr(C)]
827#[derive(Debug, Default, Copy, Clone)]
828pub struct MkdirIn {
829 pub mode: u32,
830 pub umask: u32,
831}
832unsafe impl ByteValued for MkdirIn {}
833
834#[repr(C)]
835#[derive(Debug, Default, Copy, Clone)]
836pub struct RenameIn {
837 pub newdir: u64,
838}
839unsafe impl ByteValued for RenameIn {}
840
841#[repr(C)]
842#[derive(Debug, Default, Copy, Clone)]
843pub struct Rename2In {
844 pub newdir: u64,
845 pub flags: u32,
846 pub padding: u32,
847}
848unsafe impl ByteValued for Rename2In {}
849
850#[repr(C)]
851#[derive(Debug, Default, Copy, Clone)]
852pub struct LinkIn {
853 pub oldnodeid: u64,
854}
855unsafe impl ByteValued for LinkIn {}
856
857#[repr(C)]
858#[derive(Debug, Default, Copy, Clone)]
859pub struct SetattrIn {
860 pub valid: u32,
861 pub padding: u32,
862 pub fh: u64,
863 pub size: u64,
864 pub lock_owner: u64,
865 pub atime: u64,
866 pub mtime: u64,
867 pub ctime: u64,
868 pub atimensec: u32,
869 pub mtimensec: u32,
870 pub ctimensec: u32,
871 pub mode: u32,
872 pub unused4: u32,
873 pub uid: u32,
874 pub gid: u32,
875 pub unused5: u32,
876}
877unsafe impl ByteValued for SetattrIn {}
878
879impl From<SetattrIn> for stat64 {
880 fn from(setattr: SetattrIn) -> stat64 {
881 let mut out: stat64 = unsafe { mem::zeroed() };
883 out.st_mode = setattr.mode as mode_t;
884 out.st_uid = setattr.uid;
885 out.st_gid = setattr.gid;
886 out.st_size = setattr.size as i64;
887 out.st_atime = setattr.atime as i64;
888 out.st_mtime = setattr.mtime as i64;
889 out.st_ctime = setattr.ctime as i64;
890 out.st_atime_nsec = i64::from(setattr.atimensec);
891 out.st_mtime_nsec = i64::from(setattr.mtimensec);
892 out.st_ctime_nsec = i64::from(setattr.ctimensec);
893
894 out
895 }
896}
897
898#[repr(C)]
899#[derive(Debug, Default, Copy, Clone)]
900pub struct OpenIn {
901 pub flags: u32,
902 pub fuse_flags: u32,
903}
904unsafe impl ByteValued for OpenIn {}
905
906#[repr(C)]
907#[derive(Debug, Default, Copy, Clone)]
908pub struct CreateIn {
909 pub flags: u32,
910 pub mode: u32,
911 pub umask: u32,
912 pub fuse_flags: u32,
913}
914unsafe impl ByteValued for CreateIn {}
915
916#[repr(C)]
917#[derive(Debug, Default, Copy, Clone)]
918pub struct OpenOut {
919 pub fh: u64,
920 pub open_flags: u32,
921 pub passthrough: u32,
922}
923unsafe impl ByteValued for OpenOut {}
924
925#[repr(C)]
926#[derive(Debug, Default, Copy, Clone)]
927pub struct ReleaseIn {
928 pub fh: u64,
929 pub flags: u32,
930 pub release_flags: u32,
931 pub lock_owner: u64,
932}
933unsafe impl ByteValued for ReleaseIn {}
934
935#[repr(C)]
936#[derive(Debug, Default, Copy, Clone)]
937pub struct FlushIn {
938 pub fh: u64,
939 pub unused: u32,
940 pub padding: u32,
941 pub lock_owner: u64,
942}
943unsafe impl ByteValued for FlushIn {}
944
945#[repr(C)]
946#[derive(Debug, Default, Copy, Clone)]
947pub struct ReadIn {
948 pub fh: u64,
949 pub offset: u64,
950 pub size: u32,
951 pub read_flags: u32,
952 pub lock_owner: u64,
953 pub flags: u32,
954 pub padding: u32,
955}
956unsafe impl ByteValued for ReadIn {}
957
958#[repr(C)]
959#[derive(Debug, Default, Copy, Clone)]
960pub struct WriteIn {
961 pub fh: u64,
962 pub offset: u64,
963 pub size: u32,
964 pub fuse_flags: u32,
965 pub lock_owner: u64,
966 pub flags: u32,
967 pub padding: u32,
968}
969unsafe impl ByteValued for WriteIn {}
970
971#[repr(C)]
972#[derive(Debug, Default, Copy, Clone)]
973pub struct WriteOut {
974 pub size: u32,
975 pub padding: u32,
976}
977unsafe impl ByteValued for WriteOut {}
978
979#[repr(C)]
980#[derive(Debug, Default, Copy, Clone)]
981pub struct StatfsOut {
982 pub st: Kstatfs,
983}
984unsafe impl ByteValued for StatfsOut {}
985
986#[repr(C)]
987#[derive(Debug, Default, Copy, Clone)]
988pub struct FsyncIn {
989 pub fh: u64,
990 pub fsync_flags: u32,
991 pub padding: u32,
992}
993unsafe impl ByteValued for FsyncIn {}
994
995#[repr(C)]
996#[derive(Debug, Default, Copy, Clone)]
997pub struct SetxattrIn {
998 pub size: u32,
999 pub flags: u32,
1000}
1001unsafe impl ByteValued for SetxattrIn {}
1002
1003#[repr(C)]
1004#[derive(Debug, Default, Copy, Clone)]
1005pub struct GetxattrIn {
1006 pub size: u32,
1007 pub padding: u32,
1008}
1009unsafe impl ByteValued for GetxattrIn {}
1010
1011#[repr(C)]
1012#[derive(Debug, Default, Copy, Clone)]
1013pub struct GetxattrOut {
1014 pub size: u32,
1015 pub padding: u32,
1016}
1017unsafe impl ByteValued for GetxattrOut {}
1018
1019#[repr(C)]
1020#[derive(Debug, Default, Copy, Clone)]
1021pub struct LkIn {
1022 pub fh: u64,
1023 pub owner: u64,
1024 pub lk: FileLock,
1025 pub lk_flags: u32,
1026 pub padding: u32,
1027}
1028unsafe impl ByteValued for LkIn {}
1029
1030#[repr(C)]
1031#[derive(Debug, Default, Copy, Clone)]
1032pub struct LkOut {
1033 pub lk: FileLock,
1034}
1035unsafe impl ByteValued for LkOut {}
1036
1037#[repr(C)]
1038#[derive(Debug, Default, Copy, Clone)]
1039pub struct AccessIn {
1040 pub mask: u32,
1041 pub padding: u32,
1042}
1043unsafe impl ByteValued for AccessIn {}
1044
1045#[repr(C)]
1046#[derive(Debug, Default, Copy, Clone)]
1047pub struct InitIn {
1048 pub major: u32,
1049 pub minor: u32,
1050 pub max_readahead: u32,
1051 pub flags: u32,
1052}
1053unsafe impl ByteValued for InitIn {}
1054
1055#[repr(C)]
1057#[derive(Debug, Default, Copy, Clone)]
1058pub struct InitIn2 {
1059 pub flags2: u32,
1060 pub unused: [u32; 11],
1061}
1062unsafe impl ByteValued for InitIn2 {}
1063
1064#[repr(C)]
1065#[derive(Debug, Default, Copy, Clone)]
1066pub struct InitOut {
1067 pub major: u32,
1068 pub minor: u32,
1069 pub max_readahead: u32,
1070 pub flags: u32,
1071 pub max_background: u16,
1072 pub congestion_threshold: u16,
1073 pub max_write: u32,
1074 pub time_gran: u32,
1075 pub max_pages: u16,
1076 pub map_alignment: u16,
1077 pub flags2: u32,
1078 pub unused: [u32; 7],
1079}
1080unsafe impl ByteValued for InitOut {}
1081
1082#[repr(C)]
1083#[derive(Debug, Default, Copy, Clone)]
1084pub struct InterruptIn {
1085 pub unique: u64,
1086}
1087unsafe impl ByteValued for InterruptIn {}
1088
1089#[repr(C)]
1090#[derive(Debug, Default, Copy, Clone)]
1091pub struct BmapIn {
1092 pub block: u64,
1093 pub blocksize: u32,
1094 pub padding: u32,
1095}
1096unsafe impl ByteValued for BmapIn {}
1097
1098#[repr(C)]
1099#[derive(Debug, Default, Copy, Clone)]
1100pub struct BmapOut {
1101 pub block: u64,
1102}
1103unsafe impl ByteValued for BmapOut {}
1104
1105#[repr(C)]
1106#[derive(Debug, Default, Copy, Clone)]
1107pub struct IoctlIn {
1108 pub fh: u64,
1109 pub flags: u32,
1110 pub cmd: u32,
1111 pub arg: u64,
1112 pub in_size: u32,
1113 pub out_size: u32,
1114}
1115unsafe impl ByteValued for IoctlIn {}
1116
1117#[repr(C)]
1118#[derive(Debug, Default, Copy, Clone)]
1119pub struct IoctlIovec {
1120 pub base: u64,
1121 pub len: u64,
1122}
1123unsafe impl ByteValued for IoctlIovec {}
1124
1125#[repr(C)]
1126#[derive(Debug, Default, Copy, Clone)]
1127pub struct IoctlOut {
1128 pub result: i32,
1129 pub flags: u32,
1130 pub in_iovs: u32,
1131 pub out_iovs: u32,
1132}
1133unsafe impl ByteValued for IoctlOut {}
1134
1135#[repr(C)]
1136#[derive(Debug, Default, Copy, Clone)]
1137pub struct PollIn {
1138 pub fh: u64,
1139 pub kh: u64,
1140 pub flags: u32,
1141 pub events: u32,
1142}
1143unsafe impl ByteValued for PollIn {}
1144
1145#[repr(C)]
1146#[derive(Debug, Default, Copy, Clone)]
1147pub struct PollOut {
1148 pub revents: u32,
1149 pub padding: u32,
1150}
1151unsafe impl ByteValued for PollOut {}
1152
1153#[repr(C)]
1154#[derive(Debug, Default, Copy, Clone)]
1155pub struct NotifyPollWakeupOut {
1156 pub kh: u64,
1157}
1158unsafe impl ByteValued for NotifyPollWakeupOut {}
1159
1160#[repr(C)]
1161#[derive(Debug, Default, Copy, Clone)]
1162pub struct FallocateIn {
1163 pub fh: u64,
1164 pub offset: u64,
1165 pub length: u64,
1166 pub mode: u32,
1167 pub padding: u32,
1168}
1169unsafe impl ByteValued for FallocateIn {}
1170
1171#[repr(C)]
1172#[derive(Default, Copy, Clone)]
1173pub struct InHeader {
1174 pub len: u32,
1175 pub opcode: u32,
1176 pub unique: u64,
1177 pub nodeid: u64,
1178 pub uid: u32,
1179 pub gid: u32,
1180 pub pid: u32,
1181 pub padding: u32,
1182}
1183unsafe impl ByteValued for InHeader {}
1184
1185impl Debug for InHeader {
1186 fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
1187 write!(
1188 f,
1189 "InHeader {{ len: {}, opcode: {}, unique: {}, nodeid: 0x{:x}, uid: {}, gid: {}, pid: {}, padding: {} }}",
1190 self.len, self.opcode, self.unique, self.nodeid, self.uid, self.gid, self.pid, self.padding
1191 )
1192 }
1193}
1194
1195#[repr(C)]
1196#[derive(Debug, Default, Copy, Clone)]
1197pub struct OutHeader {
1198 pub len: u32,
1199 pub error: i32,
1200 pub unique: u64,
1201}
1202unsafe impl ByteValued for OutHeader {}
1203
1204#[repr(C)]
1205#[derive(Debug, Default, Copy, Clone)]
1206pub struct Dirent {
1207 pub ino: u64,
1208 pub off: u64,
1209 pub namelen: u32,
1210 pub type_: u32,
1211 }
1213unsafe impl ByteValued for Dirent {}
1214
1215#[repr(C)]
1216#[derive(Debug, Default, Copy, Clone)]
1217pub struct Direntplus {
1218 pub entry_out: EntryOut,
1219 pub dirent: Dirent,
1220}
1221unsafe impl ByteValued for Direntplus {}
1222
1223#[repr(C)]
1224#[derive(Debug, Default, Copy, Clone)]
1225pub struct NotifyInvalInodeOut {
1226 pub ino: u64,
1227 pub off: i64,
1228 pub len: i64,
1229}
1230unsafe impl ByteValued for NotifyInvalInodeOut {}
1231
1232#[repr(C)]
1233#[derive(Debug, Default, Copy, Clone)]
1234pub struct NotifyInvalEntryOut {
1235 pub parent: u64,
1236 pub namelen: u32,
1237 pub padding: u32,
1238}
1239unsafe impl ByteValued for NotifyInvalEntryOut {}
1240
1241#[repr(C)]
1242#[derive(Debug, Default, Copy, Clone)]
1243pub struct NotifyDeleteOut {
1244 pub parent: u64,
1245 pub child: u64,
1246 pub namelen: u32,
1247 pub padding: u32,
1248}
1249unsafe impl ByteValued for NotifyDeleteOut {}
1250
1251#[repr(C)]
1252#[derive(Debug, Default, Copy, Clone)]
1253pub struct NotifyStoreOut {
1254 pub nodeid: u64,
1255 pub offset: u64,
1256 pub size: u32,
1257 pub padding: u32,
1258}
1259unsafe impl ByteValued for NotifyStoreOut {}
1260
1261#[repr(C)]
1262#[derive(Debug, Default, Copy, Clone)]
1263pub struct Notify_Retrieve_Out {
1264 pub notify_unique: u64,
1265 pub nodeid: u64,
1266 pub offset: u64,
1267 pub size: u32,
1268 pub padding: u32,
1269}
1270unsafe impl ByteValued for Notify_Retrieve_Out {}
1271
1272#[repr(C)]
1274#[derive(Debug, Default, Copy, Clone)]
1275pub struct NotifyRetrieveIn {
1276 pub dummy1: u64,
1277 pub offset: u64,
1278 pub size: u32,
1279 pub dummy2: u32,
1280 pub dummy3: u64,
1281 pub dummy4: u64,
1282}
1283unsafe impl ByteValued for NotifyRetrieveIn {}
1284
1285#[repr(C)]
1286#[derive(Debug, Default, Copy, Clone)]
1287pub struct LseekIn {
1288 pub fh: u64,
1289 pub offset: u64,
1290 pub whence: u32,
1291 pub padding: u32,
1292}
1293unsafe impl ByteValued for LseekIn {}
1294
1295#[repr(C)]
1296#[derive(Debug, Default, Copy, Clone)]
1297pub struct LseekOut {
1298 pub offset: u64,
1299}
1300unsafe impl ByteValued for LseekOut {}
1301
1302#[repr(C)]
1303#[derive(Debug, Default, Copy, Clone)]
1304pub struct CopyFileRangeIn {
1306 pub fh_in: u64,
1307 pub offset_in: u64,
1308 pub nodeid_out: u64,
1309 pub fh_out: u64,
1310 pub offset_out: u64,
1311 pub len: u64,
1312 pub flags: u64,
1313}
1314unsafe impl ByteValued for CopyFileRangeIn {}
1315
1316#[cfg(test)]
1317mod tests {
1318 use super::*;
1319
1320 #[test]
1321 fn test_struct_size() {
1322 assert_eq!(std::mem::size_of::<Attr>(), 88);
1323 assert_eq!(std::mem::size_of::<Kstatfs>(), 80);
1324 assert_eq!(std::mem::size_of::<FileLock>(), 24);
1325 assert_eq!(std::mem::size_of::<EntryOut>(), 128);
1326 assert_eq!(std::mem::size_of::<ForgetIn>(), 8);
1327 assert_eq!(std::mem::size_of::<ForgetOne>(), 16);
1328 assert_eq!(std::mem::size_of::<BatchForgetIn>(), 8);
1329 assert_eq!(std::mem::size_of::<GetattrIn>(), 16);
1330 assert_eq!(std::mem::size_of::<AttrOut>(), 104);
1331 assert_eq!(std::mem::size_of::<MknodIn>(), 16);
1332 assert_eq!(std::mem::size_of::<MkdirIn>(), 8);
1333 assert_eq!(std::mem::size_of::<InHeader>(), 40);
1334 assert_eq!(std::mem::size_of::<OutHeader>(), 16);
1335 }
1336
1337 #[test]
1338 fn test_byte_valued() {
1339 let buf = [
1340 0x1u8, 0x2u8, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x5u8, 0x6u8, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0,
1341 ];
1342 let forget: &ForgetOne = ForgetOne::from_slice(&buf).unwrap();
1343
1344 assert_eq!(forget.nodeid, 0x201u64);
1345 assert_eq!(forget.nlookup, 0x605u64);
1346
1347 let forget = ForgetOne {
1348 nodeid: 0x201u64,
1349 nlookup: 0x605u64,
1350 };
1351 let buf = forget.as_slice();
1352 assert_eq!(buf[0], 0x1u8);
1353 assert_eq!(buf[1], 0x2u8);
1354 assert_eq!(buf[8], 0x5u8);
1355 assert_eq!(buf[9], 0x6u8);
1356 }
1357}