xref: /aosp_15_r20/external/crosvm/fuse/src/filesystem.rs (revision bb4ee6a4ae7042d18b07a98463b9c8b875e44b39)
1*bb4ee6a4SAndroid Build Coastguard Worker // Copyright 2019 The ChromiumOS Authors
2*bb4ee6a4SAndroid Build Coastguard Worker // Use of this source code is governed by a BSD-style license that can be
3*bb4ee6a4SAndroid Build Coastguard Worker // found in the LICENSE file.
4*bb4ee6a4SAndroid Build Coastguard Worker 
5*bb4ee6a4SAndroid Build Coastguard Worker //! Data structures and traits for the fuse filesystem.
6*bb4ee6a4SAndroid Build Coastguard Worker 
7*bb4ee6a4SAndroid Build Coastguard Worker #![deny(missing_docs)]
8*bb4ee6a4SAndroid Build Coastguard Worker 
9*bb4ee6a4SAndroid Build Coastguard Worker use std::convert::TryInto;
10*bb4ee6a4SAndroid Build Coastguard Worker use std::ffi::CStr;
11*bb4ee6a4SAndroid Build Coastguard Worker use std::fs::File;
12*bb4ee6a4SAndroid Build Coastguard Worker use std::io;
13*bb4ee6a4SAndroid Build Coastguard Worker use std::mem;
14*bb4ee6a4SAndroid Build Coastguard Worker use std::mem::MaybeUninit;
15*bb4ee6a4SAndroid Build Coastguard Worker use std::time::Duration;
16*bb4ee6a4SAndroid Build Coastguard Worker 
17*bb4ee6a4SAndroid Build Coastguard Worker use crate::server::Mapper;
18*bb4ee6a4SAndroid Build Coastguard Worker use crate::sys;
19*bb4ee6a4SAndroid Build Coastguard Worker pub use crate::sys::FsOptions;
20*bb4ee6a4SAndroid Build Coastguard Worker pub use crate::sys::IoctlFlags;
21*bb4ee6a4SAndroid Build Coastguard Worker pub use crate::sys::IoctlIovec;
22*bb4ee6a4SAndroid Build Coastguard Worker pub use crate::sys::OpenOptions;
23*bb4ee6a4SAndroid Build Coastguard Worker pub use crate::sys::RemoveMappingOne;
24*bb4ee6a4SAndroid Build Coastguard Worker pub use crate::sys::SetattrValid;
25*bb4ee6a4SAndroid Build Coastguard Worker pub use crate::sys::ROOT_ID;
26*bb4ee6a4SAndroid Build Coastguard Worker 
27*bb4ee6a4SAndroid Build Coastguard Worker const MAX_BUFFER_SIZE: u32 = 1 << 20;
28*bb4ee6a4SAndroid Build Coastguard Worker 
29*bb4ee6a4SAndroid Build Coastguard Worker /// Information about a path in the filesystem.
30*bb4ee6a4SAndroid Build Coastguard Worker #[derive(Debug)]
31*bb4ee6a4SAndroid Build Coastguard Worker pub struct Entry {
32*bb4ee6a4SAndroid Build Coastguard Worker     /// An `Inode` that uniquely identifies this path. During `lookup`, setting this to `0` means a
33*bb4ee6a4SAndroid Build Coastguard Worker     /// negative entry. Returning `ENOENT` also means a negative entry but setting this to `0`
34*bb4ee6a4SAndroid Build Coastguard Worker     /// allows the kernel to cache the negative result for `entry_timeout`. The value should be
35*bb4ee6a4SAndroid Build Coastguard Worker     /// produced by converting a `FileSystem::Inode` into a `u64`.
36*bb4ee6a4SAndroid Build Coastguard Worker     pub inode: u64,
37*bb4ee6a4SAndroid Build Coastguard Worker 
38*bb4ee6a4SAndroid Build Coastguard Worker     /// The generation number for this `Entry`. Typically used for network file systems. An `inode`
39*bb4ee6a4SAndroid Build Coastguard Worker     /// / `generation` pair must be unique over the lifetime of the file system (rather than just
40*bb4ee6a4SAndroid Build Coastguard Worker     /// the lifetime of the mount). In other words, if a `FileSystem` implementation re-uses an
41*bb4ee6a4SAndroid Build Coastguard Worker     /// `Inode` after it has been deleted then it must assign a new, previously unused generation
42*bb4ee6a4SAndroid Build Coastguard Worker     /// number to the `Inode` at the same time.
43*bb4ee6a4SAndroid Build Coastguard Worker     pub generation: u64,
44*bb4ee6a4SAndroid Build Coastguard Worker 
45*bb4ee6a4SAndroid Build Coastguard Worker     /// Inode attributes. Even if `attr_timeout` is zero, `attr` must be correct. For example, for
46*bb4ee6a4SAndroid Build Coastguard Worker     /// `open()`, FUSE uses `attr.st_size` from `lookup()` to determine how many bytes to request.
47*bb4ee6a4SAndroid Build Coastguard Worker     /// If this value is not correct, incorrect data will be returned.
48*bb4ee6a4SAndroid Build Coastguard Worker     pub attr: libc::stat64,
49*bb4ee6a4SAndroid Build Coastguard Worker 
50*bb4ee6a4SAndroid Build Coastguard Worker     /// How long the values in `attr` should be considered valid. If the attributes of the `Entry`
51*bb4ee6a4SAndroid Build Coastguard Worker     /// are only modified by the FUSE client, then this should be set to a very large value.
52*bb4ee6a4SAndroid Build Coastguard Worker     pub attr_timeout: Duration,
53*bb4ee6a4SAndroid Build Coastguard Worker 
54*bb4ee6a4SAndroid Build Coastguard Worker     /// How long the name associated with this `Entry` should be considered valid. If directory
55*bb4ee6a4SAndroid Build Coastguard Worker     /// entries are only changed or deleted by the FUSE client, then this should be set to a very
56*bb4ee6a4SAndroid Build Coastguard Worker     /// large value.
57*bb4ee6a4SAndroid Build Coastguard Worker     pub entry_timeout: Duration,
58*bb4ee6a4SAndroid Build Coastguard Worker }
59*bb4ee6a4SAndroid Build Coastguard Worker 
60*bb4ee6a4SAndroid Build Coastguard Worker impl From<Entry> for sys::EntryOut {
from(entry: Entry) -> sys::EntryOut61*bb4ee6a4SAndroid Build Coastguard Worker     fn from(entry: Entry) -> sys::EntryOut {
62*bb4ee6a4SAndroid Build Coastguard Worker         sys::EntryOut {
63*bb4ee6a4SAndroid Build Coastguard Worker             nodeid: entry.inode,
64*bb4ee6a4SAndroid Build Coastguard Worker             generation: entry.generation,
65*bb4ee6a4SAndroid Build Coastguard Worker             entry_valid: entry.entry_timeout.as_secs(),
66*bb4ee6a4SAndroid Build Coastguard Worker             attr_valid: entry.attr_timeout.as_secs(),
67*bb4ee6a4SAndroid Build Coastguard Worker             entry_valid_nsec: entry.entry_timeout.subsec_nanos(),
68*bb4ee6a4SAndroid Build Coastguard Worker             attr_valid_nsec: entry.attr_timeout.subsec_nanos(),
69*bb4ee6a4SAndroid Build Coastguard Worker             attr: entry.attr.into(),
70*bb4ee6a4SAndroid Build Coastguard Worker         }
71*bb4ee6a4SAndroid Build Coastguard Worker     }
72*bb4ee6a4SAndroid Build Coastguard Worker }
73*bb4ee6a4SAndroid Build Coastguard Worker 
74*bb4ee6a4SAndroid Build Coastguard Worker impl Entry {
75*bb4ee6a4SAndroid Build Coastguard Worker     /// Creates a new negative cache entry. A negative d_entry has an inode number of 0, and is
76*bb4ee6a4SAndroid Build Coastguard Worker     /// valid for the duration of `negative_timeout`.
77*bb4ee6a4SAndroid Build Coastguard Worker     ///
78*bb4ee6a4SAndroid Build Coastguard Worker     /// # Arguments
79*bb4ee6a4SAndroid Build Coastguard Worker     ///
80*bb4ee6a4SAndroid Build Coastguard Worker     /// * `negative_timeout` - The duration for which this negative d_entry should be considered
81*bb4ee6a4SAndroid Build Coastguard Worker     ///   valid. After the timeout expires, the d_entry will be invalidated.
82*bb4ee6a4SAndroid Build Coastguard Worker     ///
83*bb4ee6a4SAndroid Build Coastguard Worker     /// # Returns
84*bb4ee6a4SAndroid Build Coastguard Worker     ///
85*bb4ee6a4SAndroid Build Coastguard Worker     /// A new negative entry with provided entry timeout and 0 attr timeout.
new_negative(negative_timeout: Duration) -> Entry86*bb4ee6a4SAndroid Build Coastguard Worker     pub fn new_negative(negative_timeout: Duration) -> Entry {
87*bb4ee6a4SAndroid Build Coastguard Worker         let attr = MaybeUninit::<libc::stat64>::zeroed();
88*bb4ee6a4SAndroid Build Coastguard Worker         Entry {
89*bb4ee6a4SAndroid Build Coastguard Worker             inode: 0, // Using 0 for negative entry
90*bb4ee6a4SAndroid Build Coastguard Worker             entry_timeout: negative_timeout,
91*bb4ee6a4SAndroid Build Coastguard Worker             // Zero-fill other fields that won't be used.
92*bb4ee6a4SAndroid Build Coastguard Worker             attr_timeout: Duration::from_secs(0),
93*bb4ee6a4SAndroid Build Coastguard Worker             generation: 0,
94*bb4ee6a4SAndroid Build Coastguard Worker             // SAFETY: zero-initialized `stat64` is a valid value.
95*bb4ee6a4SAndroid Build Coastguard Worker             attr: unsafe { attr.assume_init() },
96*bb4ee6a4SAndroid Build Coastguard Worker         }
97*bb4ee6a4SAndroid Build Coastguard Worker     }
98*bb4ee6a4SAndroid Build Coastguard Worker }
99*bb4ee6a4SAndroid Build Coastguard Worker 
100*bb4ee6a4SAndroid Build Coastguard Worker /// Represents information about an entry in a directory.
101*bb4ee6a4SAndroid Build Coastguard Worker pub struct DirEntry<'a> {
102*bb4ee6a4SAndroid Build Coastguard Worker     /// The inode number for this entry. This does NOT have to be the same as the `Inode` for this
103*bb4ee6a4SAndroid Build Coastguard Worker     /// directory entry. However, it must be the same as the `attr.st_ino` field of the `Entry`
104*bb4ee6a4SAndroid Build Coastguard Worker     /// that would be returned by a `lookup` request in the parent directory for `name`.
105*bb4ee6a4SAndroid Build Coastguard Worker     pub ino: libc::ino64_t,
106*bb4ee6a4SAndroid Build Coastguard Worker 
107*bb4ee6a4SAndroid Build Coastguard Worker     /// Any non-zero value that the kernel can use to identify the current point in the directory
108*bb4ee6a4SAndroid Build Coastguard Worker     /// entry stream. It does not need to be the actual physical position. A value of `0` is
109*bb4ee6a4SAndroid Build Coastguard Worker     /// reserved to mean "from the beginning" and should never be used. The `offset` value of the
110*bb4ee6a4SAndroid Build Coastguard Worker     /// first entry in a stream should point to the beginning of the second entry and so on.
111*bb4ee6a4SAndroid Build Coastguard Worker     pub offset: u64,
112*bb4ee6a4SAndroid Build Coastguard Worker 
113*bb4ee6a4SAndroid Build Coastguard Worker     /// The type of this directory entry. Valid values are any of the `libc::DT_*` constants.
114*bb4ee6a4SAndroid Build Coastguard Worker     pub type_: u32,
115*bb4ee6a4SAndroid Build Coastguard Worker 
116*bb4ee6a4SAndroid Build Coastguard Worker     /// The name of this directory entry. There are no requirements for the contents of this field
117*bb4ee6a4SAndroid Build Coastguard Worker     /// and any sequence of bytes is considered valid.
118*bb4ee6a4SAndroid Build Coastguard Worker     pub name: &'a CStr,
119*bb4ee6a4SAndroid Build Coastguard Worker }
120*bb4ee6a4SAndroid Build Coastguard Worker 
121*bb4ee6a4SAndroid Build Coastguard Worker /// A reply to a `getxattr` method call.
122*bb4ee6a4SAndroid Build Coastguard Worker #[derive(Debug)]
123*bb4ee6a4SAndroid Build Coastguard Worker pub enum GetxattrReply {
124*bb4ee6a4SAndroid Build Coastguard Worker     /// The value of the requested extended attribute. This can be arbitrary textual or binary data
125*bb4ee6a4SAndroid Build Coastguard Worker     /// and does not need to be nul-terminated.
126*bb4ee6a4SAndroid Build Coastguard Worker     Value(Vec<u8>),
127*bb4ee6a4SAndroid Build Coastguard Worker 
128*bb4ee6a4SAndroid Build Coastguard Worker     /// The size of the buffer needed to hold the value of the requested extended attribute. Should
129*bb4ee6a4SAndroid Build Coastguard Worker     /// be returned when the `size` parameter is 0. Callers should note that it is still possible
130*bb4ee6a4SAndroid Build Coastguard Worker     /// for the size of the value to change in between `getxattr` calls and should not assume that
131*bb4ee6a4SAndroid Build Coastguard Worker     /// a subsequent call to `getxattr` with the returned count will always succeed.
132*bb4ee6a4SAndroid Build Coastguard Worker     Count(u32),
133*bb4ee6a4SAndroid Build Coastguard Worker }
134*bb4ee6a4SAndroid Build Coastguard Worker 
135*bb4ee6a4SAndroid Build Coastguard Worker /// A reply to a `listxattr` method call.
136*bb4ee6a4SAndroid Build Coastguard Worker pub enum ListxattrReply {
137*bb4ee6a4SAndroid Build Coastguard Worker     /// A buffer containing a nul-separated list of the names of all the extended attributes
138*bb4ee6a4SAndroid Build Coastguard Worker     /// associated with this `Inode`. This list of names may be unordered and includes a namespace
139*bb4ee6a4SAndroid Build Coastguard Worker     /// prefix. There may be several disjoint namespaces associated with a single `Inode`.
140*bb4ee6a4SAndroid Build Coastguard Worker     Names(Vec<u8>),
141*bb4ee6a4SAndroid Build Coastguard Worker 
142*bb4ee6a4SAndroid Build Coastguard Worker     /// This size of the buffer needed to hold the full list of extended attribute names associated
143*bb4ee6a4SAndroid Build Coastguard Worker     /// with this `Inode`. Should be returned when the `size` parameter is 0. Callers should note
144*bb4ee6a4SAndroid Build Coastguard Worker     /// that it is still possible for the set of extended attributes to change between `listxattr`
145*bb4ee6a4SAndroid Build Coastguard Worker     /// calls and so should not assume that a subsequent call to `listxattr` with the returned
146*bb4ee6a4SAndroid Build Coastguard Worker     /// count will always succeed.
147*bb4ee6a4SAndroid Build Coastguard Worker     Count(u32),
148*bb4ee6a4SAndroid Build Coastguard Worker }
149*bb4ee6a4SAndroid Build Coastguard Worker 
150*bb4ee6a4SAndroid Build Coastguard Worker /// A reply to an `ioctl` method call.
151*bb4ee6a4SAndroid Build Coastguard Worker #[derive(Debug)]
152*bb4ee6a4SAndroid Build Coastguard Worker pub enum IoctlReply {
153*bb4ee6a4SAndroid Build Coastguard Worker     /// Indicates that the ioctl should be retried. This is only a valid reply when the `flags`
154*bb4ee6a4SAndroid Build Coastguard Worker     /// field of the ioctl request contains `IoctlFlags::UNRESTRICTED`. The kernel will read in
155*bb4ee6a4SAndroid Build Coastguard Worker     /// data and prepare output buffers as specified in the `input` and `output` fields before
156*bb4ee6a4SAndroid Build Coastguard Worker     /// re-sending the ioctl message.
157*bb4ee6a4SAndroid Build Coastguard Worker     Retry {
158*bb4ee6a4SAndroid Build Coastguard Worker         /// Data that should be read by the kernel module and sent to the server when the ioctl is
159*bb4ee6a4SAndroid Build Coastguard Worker         /// retried.
160*bb4ee6a4SAndroid Build Coastguard Worker         input: Vec<IoctlIovec>,
161*bb4ee6a4SAndroid Build Coastguard Worker 
162*bb4ee6a4SAndroid Build Coastguard Worker         /// Buffer space that should be prepared so that the server can send back the response to
163*bb4ee6a4SAndroid Build Coastguard Worker         /// the ioctl.
164*bb4ee6a4SAndroid Build Coastguard Worker         output: Vec<IoctlIovec>,
165*bb4ee6a4SAndroid Build Coastguard Worker     },
166*bb4ee6a4SAndroid Build Coastguard Worker 
167*bb4ee6a4SAndroid Build Coastguard Worker     /// Indicates that the ioctl was processed.
168*bb4ee6a4SAndroid Build Coastguard Worker     Done(io::Result<Vec<u8>>),
169*bb4ee6a4SAndroid Build Coastguard Worker }
170*bb4ee6a4SAndroid Build Coastguard Worker 
171*bb4ee6a4SAndroid Build Coastguard Worker /// A trait for directly copying data from the fuse transport into a `File` without first storing it
172*bb4ee6a4SAndroid Build Coastguard Worker /// in an intermediate buffer.
173*bb4ee6a4SAndroid Build Coastguard Worker pub trait ZeroCopyReader {
174*bb4ee6a4SAndroid Build Coastguard Worker     /// Copies at most `count` bytes from `self` directly into `f` at offset `off` without storing
175*bb4ee6a4SAndroid Build Coastguard Worker     /// it in any intermediate buffers. If the return value is `Ok(n)` then it must be guaranteed
176*bb4ee6a4SAndroid Build Coastguard Worker     /// that `0 <= n <= count`. If `n` is `0`, then it can indicate one of 3 possibilities:
177*bb4ee6a4SAndroid Build Coastguard Worker     ///
178*bb4ee6a4SAndroid Build Coastguard Worker     /// 1. There is no more data left in `self`.
179*bb4ee6a4SAndroid Build Coastguard Worker     /// 2. There is no more space in `f`.
180*bb4ee6a4SAndroid Build Coastguard Worker     /// 3. `count` was `0`.
181*bb4ee6a4SAndroid Build Coastguard Worker     ///
182*bb4ee6a4SAndroid Build Coastguard Worker     /// # Errors
183*bb4ee6a4SAndroid Build Coastguard Worker     ///
184*bb4ee6a4SAndroid Build Coastguard Worker     /// If any error is returned then the implementation must guarantee that no bytes were copied
185*bb4ee6a4SAndroid Build Coastguard Worker     /// from `self`. If the underlying write to `f` returns `0` then the implementation must return
186*bb4ee6a4SAndroid Build Coastguard Worker     /// an error of the kind `io::ErrorKind::WriteZero`.
read_to(&mut self, f: &mut File, count: usize, off: u64) -> io::Result<usize>187*bb4ee6a4SAndroid Build Coastguard Worker     fn read_to(&mut self, f: &mut File, count: usize, off: u64) -> io::Result<usize>;
188*bb4ee6a4SAndroid Build Coastguard Worker 
189*bb4ee6a4SAndroid Build Coastguard Worker     /// Copies exactly `count` bytes of data from `self` into `f` at offset `off`. `off + count`
190*bb4ee6a4SAndroid Build Coastguard Worker     /// must be less than `u64::MAX`.
191*bb4ee6a4SAndroid Build Coastguard Worker     ///
192*bb4ee6a4SAndroid Build Coastguard Worker     /// # Errors
193*bb4ee6a4SAndroid Build Coastguard Worker     ///
194*bb4ee6a4SAndroid Build Coastguard Worker     /// If an error is returned then the number of bytes copied from `self` is unspecified but it
195*bb4ee6a4SAndroid Build Coastguard Worker     /// will never be more than `count`.
read_exact_to(&mut self, f: &mut File, mut count: usize, mut off: u64) -> io::Result<()>196*bb4ee6a4SAndroid Build Coastguard Worker     fn read_exact_to(&mut self, f: &mut File, mut count: usize, mut off: u64) -> io::Result<()> {
197*bb4ee6a4SAndroid Build Coastguard Worker         let c = count
198*bb4ee6a4SAndroid Build Coastguard Worker             .try_into()
199*bb4ee6a4SAndroid Build Coastguard Worker             .map_err(|e| io::Error::new(io::ErrorKind::InvalidInput, e))?;
200*bb4ee6a4SAndroid Build Coastguard Worker         if off.checked_add(c).is_none() {
201*bb4ee6a4SAndroid Build Coastguard Worker             return Err(io::Error::new(
202*bb4ee6a4SAndroid Build Coastguard Worker                 io::ErrorKind::InvalidInput,
203*bb4ee6a4SAndroid Build Coastguard Worker                 "`off` + `count` must be less than u64::MAX",
204*bb4ee6a4SAndroid Build Coastguard Worker             ));
205*bb4ee6a4SAndroid Build Coastguard Worker         }
206*bb4ee6a4SAndroid Build Coastguard Worker 
207*bb4ee6a4SAndroid Build Coastguard Worker         while count > 0 {
208*bb4ee6a4SAndroid Build Coastguard Worker             match self.read_to(f, count, off) {
209*bb4ee6a4SAndroid Build Coastguard Worker                 Ok(0) => {
210*bb4ee6a4SAndroid Build Coastguard Worker                     return Err(io::Error::new(
211*bb4ee6a4SAndroid Build Coastguard Worker                         io::ErrorKind::WriteZero,
212*bb4ee6a4SAndroid Build Coastguard Worker                         "failed to fill whole buffer",
213*bb4ee6a4SAndroid Build Coastguard Worker                     ))
214*bb4ee6a4SAndroid Build Coastguard Worker                 }
215*bb4ee6a4SAndroid Build Coastguard Worker                 Ok(n) => {
216*bb4ee6a4SAndroid Build Coastguard Worker                     count -= n;
217*bb4ee6a4SAndroid Build Coastguard Worker                     off += n as u64;
218*bb4ee6a4SAndroid Build Coastguard Worker                 }
219*bb4ee6a4SAndroid Build Coastguard Worker                 Err(ref e) if e.kind() == io::ErrorKind::Interrupted => {}
220*bb4ee6a4SAndroid Build Coastguard Worker                 Err(e) => return Err(e),
221*bb4ee6a4SAndroid Build Coastguard Worker             }
222*bb4ee6a4SAndroid Build Coastguard Worker         }
223*bb4ee6a4SAndroid Build Coastguard Worker 
224*bb4ee6a4SAndroid Build Coastguard Worker         Ok(())
225*bb4ee6a4SAndroid Build Coastguard Worker     }
226*bb4ee6a4SAndroid Build Coastguard Worker 
227*bb4ee6a4SAndroid Build Coastguard Worker     /// Copies all remaining bytes from `self` into `f` at offset `off`. Equivalent to repeatedly
228*bb4ee6a4SAndroid Build Coastguard Worker     /// calling `read_to` until it returns either `Ok(0)` or a non-`ErrorKind::Interrupted` error.
229*bb4ee6a4SAndroid Build Coastguard Worker     ///
230*bb4ee6a4SAndroid Build Coastguard Worker     /// # Errors
231*bb4ee6a4SAndroid Build Coastguard Worker     ///
232*bb4ee6a4SAndroid Build Coastguard Worker     /// If an error is returned then the number of bytes copied from `self` is unspecified.
copy_to_end(&mut self, f: &mut File, mut off: u64) -> io::Result<usize>233*bb4ee6a4SAndroid Build Coastguard Worker     fn copy_to_end(&mut self, f: &mut File, mut off: u64) -> io::Result<usize> {
234*bb4ee6a4SAndroid Build Coastguard Worker         let mut out = 0;
235*bb4ee6a4SAndroid Build Coastguard Worker         loop {
236*bb4ee6a4SAndroid Build Coastguard Worker             match self.read_to(f, usize::MAX, off) {
237*bb4ee6a4SAndroid Build Coastguard Worker                 Ok(0) => return Ok(out),
238*bb4ee6a4SAndroid Build Coastguard Worker                 Ok(n) => {
239*bb4ee6a4SAndroid Build Coastguard Worker                     off = off.saturating_add(n as u64);
240*bb4ee6a4SAndroid Build Coastguard Worker                     out += n;
241*bb4ee6a4SAndroid Build Coastguard Worker                 }
242*bb4ee6a4SAndroid Build Coastguard Worker                 Err(ref e) if e.kind() == io::ErrorKind::Interrupted => {}
243*bb4ee6a4SAndroid Build Coastguard Worker                 Err(e) => return Err(e),
244*bb4ee6a4SAndroid Build Coastguard Worker             }
245*bb4ee6a4SAndroid Build Coastguard Worker         }
246*bb4ee6a4SAndroid Build Coastguard Worker     }
247*bb4ee6a4SAndroid Build Coastguard Worker }
248*bb4ee6a4SAndroid Build Coastguard Worker 
249*bb4ee6a4SAndroid Build Coastguard Worker impl<'a, R: ZeroCopyReader> ZeroCopyReader for &'a mut R {
read_to(&mut self, f: &mut File, count: usize, off: u64) -> io::Result<usize>250*bb4ee6a4SAndroid Build Coastguard Worker     fn read_to(&mut self, f: &mut File, count: usize, off: u64) -> io::Result<usize> {
251*bb4ee6a4SAndroid Build Coastguard Worker         (**self).read_to(f, count, off)
252*bb4ee6a4SAndroid Build Coastguard Worker     }
read_exact_to(&mut self, f: &mut File, count: usize, off: u64) -> io::Result<()>253*bb4ee6a4SAndroid Build Coastguard Worker     fn read_exact_to(&mut self, f: &mut File, count: usize, off: u64) -> io::Result<()> {
254*bb4ee6a4SAndroid Build Coastguard Worker         (**self).read_exact_to(f, count, off)
255*bb4ee6a4SAndroid Build Coastguard Worker     }
copy_to_end(&mut self, f: &mut File, off: u64) -> io::Result<usize>256*bb4ee6a4SAndroid Build Coastguard Worker     fn copy_to_end(&mut self, f: &mut File, off: u64) -> io::Result<usize> {
257*bb4ee6a4SAndroid Build Coastguard Worker         (**self).copy_to_end(f, off)
258*bb4ee6a4SAndroid Build Coastguard Worker     }
259*bb4ee6a4SAndroid Build Coastguard Worker }
260*bb4ee6a4SAndroid Build Coastguard Worker 
261*bb4ee6a4SAndroid Build Coastguard Worker /// A trait for directly copying data from a `File` into the fuse transport without first storing
262*bb4ee6a4SAndroid Build Coastguard Worker /// it in an intermediate buffer.
263*bb4ee6a4SAndroid Build Coastguard Worker pub trait ZeroCopyWriter {
264*bb4ee6a4SAndroid Build Coastguard Worker     /// Copies at most `count` bytes from `f` at offset `off` directly into `self` without storing
265*bb4ee6a4SAndroid Build Coastguard Worker     /// it in any intermediate buffers. If the return value is `Ok(n)` then it must be guaranteed
266*bb4ee6a4SAndroid Build Coastguard Worker     /// that `0 <= n <= count`. If `n` is `0`, then it can indicate one of 3 possibilities:
267*bb4ee6a4SAndroid Build Coastguard Worker     ///
268*bb4ee6a4SAndroid Build Coastguard Worker     /// 1. There is no more data left in `f`.
269*bb4ee6a4SAndroid Build Coastguard Worker     /// 2. There is no more space in `self`.
270*bb4ee6a4SAndroid Build Coastguard Worker     /// 3. `count` was `0`.
271*bb4ee6a4SAndroid Build Coastguard Worker     ///
272*bb4ee6a4SAndroid Build Coastguard Worker     /// # Errors
273*bb4ee6a4SAndroid Build Coastguard Worker     ///
274*bb4ee6a4SAndroid Build Coastguard Worker     /// If any error is returned then the implementation must guarantee that no bytes were copied
275*bb4ee6a4SAndroid Build Coastguard Worker     /// from `f`. If the underlying read from `f` returns `0` then the implementation must return an
276*bb4ee6a4SAndroid Build Coastguard Worker     /// error of the kind `io::ErrorKind::UnexpectedEof`.
write_from(&mut self, f: &mut File, count: usize, off: u64) -> io::Result<usize>277*bb4ee6a4SAndroid Build Coastguard Worker     fn write_from(&mut self, f: &mut File, count: usize, off: u64) -> io::Result<usize>;
278*bb4ee6a4SAndroid Build Coastguard Worker 
279*bb4ee6a4SAndroid Build Coastguard Worker     /// Copies exactly `count` bytes of data from `f` at offset `off` into `self`. `off + count`
280*bb4ee6a4SAndroid Build Coastguard Worker     /// must be less than `u64::MAX`.
281*bb4ee6a4SAndroid Build Coastguard Worker     ///
282*bb4ee6a4SAndroid Build Coastguard Worker     /// # Errors
283*bb4ee6a4SAndroid Build Coastguard Worker     ///
284*bb4ee6a4SAndroid Build Coastguard Worker     /// If an error is returned then the number of bytes copied from `self` is unspecified but it
285*bb4ee6a4SAndroid Build Coastguard Worker     /// well never be more than `count`.
write_all_from(&mut self, f: &mut File, mut count: usize, mut off: u64) -> io::Result<()>286*bb4ee6a4SAndroid Build Coastguard Worker     fn write_all_from(&mut self, f: &mut File, mut count: usize, mut off: u64) -> io::Result<()> {
287*bb4ee6a4SAndroid Build Coastguard Worker         let c = count
288*bb4ee6a4SAndroid Build Coastguard Worker             .try_into()
289*bb4ee6a4SAndroid Build Coastguard Worker             .map_err(|e| io::Error::new(io::ErrorKind::InvalidInput, e))?;
290*bb4ee6a4SAndroid Build Coastguard Worker         if off.checked_add(c).is_none() {
291*bb4ee6a4SAndroid Build Coastguard Worker             return Err(io::Error::new(
292*bb4ee6a4SAndroid Build Coastguard Worker                 io::ErrorKind::InvalidInput,
293*bb4ee6a4SAndroid Build Coastguard Worker                 "`off` + `count` must be less than u64::MAX",
294*bb4ee6a4SAndroid Build Coastguard Worker             ));
295*bb4ee6a4SAndroid Build Coastguard Worker         }
296*bb4ee6a4SAndroid Build Coastguard Worker 
297*bb4ee6a4SAndroid Build Coastguard Worker         while count > 0 {
298*bb4ee6a4SAndroid Build Coastguard Worker             match self.write_from(f, count, off) {
299*bb4ee6a4SAndroid Build Coastguard Worker                 Ok(0) => {
300*bb4ee6a4SAndroid Build Coastguard Worker                     return Err(io::Error::new(
301*bb4ee6a4SAndroid Build Coastguard Worker                         io::ErrorKind::UnexpectedEof,
302*bb4ee6a4SAndroid Build Coastguard Worker                         "failed to write whole buffer",
303*bb4ee6a4SAndroid Build Coastguard Worker                     ))
304*bb4ee6a4SAndroid Build Coastguard Worker                 }
305*bb4ee6a4SAndroid Build Coastguard Worker                 Ok(n) => {
306*bb4ee6a4SAndroid Build Coastguard Worker                     // No need for checked math here because we verified that `off + count` will not
307*bb4ee6a4SAndroid Build Coastguard Worker                     // overflow and `n` must be <= `count`.
308*bb4ee6a4SAndroid Build Coastguard Worker                     count -= n;
309*bb4ee6a4SAndroid Build Coastguard Worker                     off += n as u64;
310*bb4ee6a4SAndroid Build Coastguard Worker                 }
311*bb4ee6a4SAndroid Build Coastguard Worker                 Err(ref e) if e.kind() == io::ErrorKind::Interrupted => {}
312*bb4ee6a4SAndroid Build Coastguard Worker                 Err(e) => return Err(e),
313*bb4ee6a4SAndroid Build Coastguard Worker             }
314*bb4ee6a4SAndroid Build Coastguard Worker         }
315*bb4ee6a4SAndroid Build Coastguard Worker 
316*bb4ee6a4SAndroid Build Coastguard Worker         Ok(())
317*bb4ee6a4SAndroid Build Coastguard Worker     }
318*bb4ee6a4SAndroid Build Coastguard Worker 
319*bb4ee6a4SAndroid Build Coastguard Worker     /// Copies all remaining bytes from `f` at offset `off` into `self`. Equivalent to repeatedly
320*bb4ee6a4SAndroid Build Coastguard Worker     /// calling `write_from` until it returns either `Ok(0)` or a non-`ErrorKind::Interrupted`
321*bb4ee6a4SAndroid Build Coastguard Worker     /// error.
322*bb4ee6a4SAndroid Build Coastguard Worker     ///
323*bb4ee6a4SAndroid Build Coastguard Worker     /// # Errors
324*bb4ee6a4SAndroid Build Coastguard Worker     ///
325*bb4ee6a4SAndroid Build Coastguard Worker     /// If an error is returned then the number of bytes copied from `f` is unspecified.
copy_to_end(&mut self, f: &mut File, mut off: u64) -> io::Result<usize>326*bb4ee6a4SAndroid Build Coastguard Worker     fn copy_to_end(&mut self, f: &mut File, mut off: u64) -> io::Result<usize> {
327*bb4ee6a4SAndroid Build Coastguard Worker         let mut out = 0;
328*bb4ee6a4SAndroid Build Coastguard Worker         loop {
329*bb4ee6a4SAndroid Build Coastguard Worker             match self.write_from(f, usize::MAX, off) {
330*bb4ee6a4SAndroid Build Coastguard Worker                 Ok(0) => return Ok(out),
331*bb4ee6a4SAndroid Build Coastguard Worker                 Ok(n) => {
332*bb4ee6a4SAndroid Build Coastguard Worker                     off = off.saturating_add(n as u64);
333*bb4ee6a4SAndroid Build Coastguard Worker                     out += n;
334*bb4ee6a4SAndroid Build Coastguard Worker                 }
335*bb4ee6a4SAndroid Build Coastguard Worker                 Err(ref e) if e.kind() == io::ErrorKind::Interrupted => {}
336*bb4ee6a4SAndroid Build Coastguard Worker                 Err(e) => return Err(e),
337*bb4ee6a4SAndroid Build Coastguard Worker             }
338*bb4ee6a4SAndroid Build Coastguard Worker         }
339*bb4ee6a4SAndroid Build Coastguard Worker     }
340*bb4ee6a4SAndroid Build Coastguard Worker }
341*bb4ee6a4SAndroid Build Coastguard Worker 
342*bb4ee6a4SAndroid Build Coastguard Worker impl<'a, W: ZeroCopyWriter> ZeroCopyWriter for &'a mut W {
write_from(&mut self, f: &mut File, count: usize, off: u64) -> io::Result<usize>343*bb4ee6a4SAndroid Build Coastguard Worker     fn write_from(&mut self, f: &mut File, count: usize, off: u64) -> io::Result<usize> {
344*bb4ee6a4SAndroid Build Coastguard Worker         (**self).write_from(f, count, off)
345*bb4ee6a4SAndroid Build Coastguard Worker     }
write_all_from(&mut self, f: &mut File, count: usize, off: u64) -> io::Result<()>346*bb4ee6a4SAndroid Build Coastguard Worker     fn write_all_from(&mut self, f: &mut File, count: usize, off: u64) -> io::Result<()> {
347*bb4ee6a4SAndroid Build Coastguard Worker         (**self).write_all_from(f, count, off)
348*bb4ee6a4SAndroid Build Coastguard Worker     }
copy_to_end(&mut self, f: &mut File, off: u64) -> io::Result<usize>349*bb4ee6a4SAndroid Build Coastguard Worker     fn copy_to_end(&mut self, f: &mut File, off: u64) -> io::Result<usize> {
350*bb4ee6a4SAndroid Build Coastguard Worker         (**self).copy_to_end(f, off)
351*bb4ee6a4SAndroid Build Coastguard Worker     }
352*bb4ee6a4SAndroid Build Coastguard Worker }
353*bb4ee6a4SAndroid Build Coastguard Worker 
354*bb4ee6a4SAndroid Build Coastguard Worker /// Additional context associated with requests.
355*bb4ee6a4SAndroid Build Coastguard Worker #[derive(Clone, Copy, Debug)]
356*bb4ee6a4SAndroid Build Coastguard Worker pub struct Context {
357*bb4ee6a4SAndroid Build Coastguard Worker     /// The user ID of the calling process.
358*bb4ee6a4SAndroid Build Coastguard Worker     pub uid: libc::uid_t,
359*bb4ee6a4SAndroid Build Coastguard Worker 
360*bb4ee6a4SAndroid Build Coastguard Worker     /// The group ID of the calling process.
361*bb4ee6a4SAndroid Build Coastguard Worker     pub gid: libc::gid_t,
362*bb4ee6a4SAndroid Build Coastguard Worker 
363*bb4ee6a4SAndroid Build Coastguard Worker     /// The thread group ID of the calling process.
364*bb4ee6a4SAndroid Build Coastguard Worker     pub pid: libc::pid_t,
365*bb4ee6a4SAndroid Build Coastguard Worker }
366*bb4ee6a4SAndroid Build Coastguard Worker 
367*bb4ee6a4SAndroid Build Coastguard Worker impl From<sys::InHeader> for Context {
from(source: sys::InHeader) -> Self368*bb4ee6a4SAndroid Build Coastguard Worker     fn from(source: sys::InHeader) -> Self {
369*bb4ee6a4SAndroid Build Coastguard Worker         Context {
370*bb4ee6a4SAndroid Build Coastguard Worker             uid: source.uid,
371*bb4ee6a4SAndroid Build Coastguard Worker             gid: source.gid,
372*bb4ee6a4SAndroid Build Coastguard Worker             pid: source.pid as i32,
373*bb4ee6a4SAndroid Build Coastguard Worker         }
374*bb4ee6a4SAndroid Build Coastguard Worker     }
375*bb4ee6a4SAndroid Build Coastguard Worker }
376*bb4ee6a4SAndroid Build Coastguard Worker 
377*bb4ee6a4SAndroid Build Coastguard Worker /// A trait for iterating over the contents of a directory. This trait is needed because rust
378*bb4ee6a4SAndroid Build Coastguard Worker /// doesn't support generic associated types, which means that it's not possible to implement a
379*bb4ee6a4SAndroid Build Coastguard Worker /// regular iterator that yields a `DirEntry` due to its generic lifetime parameter.
380*bb4ee6a4SAndroid Build Coastguard Worker pub trait DirectoryIterator {
381*bb4ee6a4SAndroid Build Coastguard Worker     /// Returns the next entry in the directory or `None` if there are no more.
next(&mut self) -> Option<DirEntry>382*bb4ee6a4SAndroid Build Coastguard Worker     fn next(&mut self) -> Option<DirEntry>;
383*bb4ee6a4SAndroid Build Coastguard Worker }
384*bb4ee6a4SAndroid Build Coastguard Worker 
385*bb4ee6a4SAndroid Build Coastguard Worker /// The main trait that connects a file system with a transport.
386*bb4ee6a4SAndroid Build Coastguard Worker #[allow(unused_variables)]
387*bb4ee6a4SAndroid Build Coastguard Worker pub trait FileSystem {
388*bb4ee6a4SAndroid Build Coastguard Worker     /// Represents a location in the filesystem tree and can be used to perform operations that act
389*bb4ee6a4SAndroid Build Coastguard Worker     /// on the metadata of a file/directory (e.g., `getattr` and `setattr`). Can also be used as the
390*bb4ee6a4SAndroid Build Coastguard Worker     /// starting point for looking up paths in the filesystem tree. An `Inode` may support operating
391*bb4ee6a4SAndroid Build Coastguard Worker     /// directly on the content of the path that to which it points. `FileSystem` implementations
392*bb4ee6a4SAndroid Build Coastguard Worker     /// that support this should set the `FsOptions::ZERO_MESSAGE_OPEN` option in the return value
393*bb4ee6a4SAndroid Build Coastguard Worker     /// of the `init` function. On linux based systems, an `Inode` is equivalent to opening a file
394*bb4ee6a4SAndroid Build Coastguard Worker     /// or directory with the `libc::O_PATH` flag.
395*bb4ee6a4SAndroid Build Coastguard Worker     ///
396*bb4ee6a4SAndroid Build Coastguard Worker     /// # Lookup Count
397*bb4ee6a4SAndroid Build Coastguard Worker     ///
398*bb4ee6a4SAndroid Build Coastguard Worker     /// The `FileSystem` implementation is required to keep a "lookup count" for every `Inode`.
399*bb4ee6a4SAndroid Build Coastguard Worker     /// Every time an `Entry` is returned by a `FileSystem` trait method, this lookup count should
400*bb4ee6a4SAndroid Build Coastguard Worker     /// increase by 1. The lookup count for an `Inode` decreases when the kernel sends a `forget`
401*bb4ee6a4SAndroid Build Coastguard Worker     /// request. `Inode`s with a non-zero lookup count may receive requests from the kernel even
402*bb4ee6a4SAndroid Build Coastguard Worker     /// after calls to `unlink`, `rmdir` or (when overwriting an existing file) `rename`.
403*bb4ee6a4SAndroid Build Coastguard Worker     /// `FileSystem` implementations must handle such requests properly and it is recommended to
404*bb4ee6a4SAndroid Build Coastguard Worker     /// defer removal of the `Inode` until the lookup count reaches zero. Calls to `unlink`, `rmdir`
405*bb4ee6a4SAndroid Build Coastguard Worker     /// or `rename` will be followed closely by `forget` unless the file or directory is open, in
406*bb4ee6a4SAndroid Build Coastguard Worker     /// which case the kernel issues `forget` only after the `release` or `releasedir` calls.
407*bb4ee6a4SAndroid Build Coastguard Worker     ///
408*bb4ee6a4SAndroid Build Coastguard Worker     /// Note that if a file system will be exported over NFS the `Inode`'s lifetime must extend even
409*bb4ee6a4SAndroid Build Coastguard Worker     /// beyond `forget`. See the `generation` field in `Entry`.
410*bb4ee6a4SAndroid Build Coastguard Worker     type Inode: From<u64> + Into<u64>;
411*bb4ee6a4SAndroid Build Coastguard Worker 
412*bb4ee6a4SAndroid Build Coastguard Worker     /// Represents a file or directory that is open for reading/writing.
413*bb4ee6a4SAndroid Build Coastguard Worker     type Handle: From<u64> + Into<u64>;
414*bb4ee6a4SAndroid Build Coastguard Worker 
415*bb4ee6a4SAndroid Build Coastguard Worker     /// An iterator over the entries of a directory. See the documentation for `readdir` for more
416*bb4ee6a4SAndroid Build Coastguard Worker     /// details.
417*bb4ee6a4SAndroid Build Coastguard Worker     type DirIter: DirectoryIterator;
418*bb4ee6a4SAndroid Build Coastguard Worker 
419*bb4ee6a4SAndroid Build Coastguard Worker     /// Maximum size of the buffer that the filesystem can generate data to, including the header.
420*bb4ee6a4SAndroid Build Coastguard Worker     /// This corresponds to max_write in the initialization.
max_buffer_size(&self) -> u32421*bb4ee6a4SAndroid Build Coastguard Worker     fn max_buffer_size(&self) -> u32 {
422*bb4ee6a4SAndroid Build Coastguard Worker         MAX_BUFFER_SIZE
423*bb4ee6a4SAndroid Build Coastguard Worker     }
424*bb4ee6a4SAndroid Build Coastguard Worker 
425*bb4ee6a4SAndroid Build Coastguard Worker     /// Initialize the file system.
426*bb4ee6a4SAndroid Build Coastguard Worker     ///
427*bb4ee6a4SAndroid Build Coastguard Worker     /// This method is called when a connection to the FUSE kernel module is first established. The
428*bb4ee6a4SAndroid Build Coastguard Worker     /// `capable` parameter indicates the features that are supported by the kernel module. The
429*bb4ee6a4SAndroid Build Coastguard Worker     /// implementation should return the options that it supports. Any options set in the returned
430*bb4ee6a4SAndroid Build Coastguard Worker     /// `FsOptions` that are not also set in `capable` are silently dropped.
init(&self, capable: FsOptions) -> io::Result<FsOptions>431*bb4ee6a4SAndroid Build Coastguard Worker     fn init(&self, capable: FsOptions) -> io::Result<FsOptions> {
432*bb4ee6a4SAndroid Build Coastguard Worker         Ok(FsOptions::empty())
433*bb4ee6a4SAndroid Build Coastguard Worker     }
434*bb4ee6a4SAndroid Build Coastguard Worker 
435*bb4ee6a4SAndroid Build Coastguard Worker     /// Clean up the file system.
436*bb4ee6a4SAndroid Build Coastguard Worker     ///
437*bb4ee6a4SAndroid Build Coastguard Worker     /// Called when the filesystem exits. All open `Handle`s should be closed and the lookup count
438*bb4ee6a4SAndroid Build Coastguard Worker     /// for all open `Inode`s implicitly goes to zero. At this point the connection to the FUSE
439*bb4ee6a4SAndroid Build Coastguard Worker     /// kernel module may already be gone so implementations should not rely on being able to
440*bb4ee6a4SAndroid Build Coastguard Worker     /// communicate with the kernel.
destroy(&self)441*bb4ee6a4SAndroid Build Coastguard Worker     fn destroy(&self) {}
442*bb4ee6a4SAndroid Build Coastguard Worker 
443*bb4ee6a4SAndroid Build Coastguard Worker     /// Look up a directory entry by name and get its attributes.
444*bb4ee6a4SAndroid Build Coastguard Worker     ///
445*bb4ee6a4SAndroid Build Coastguard Worker     /// If this call is successful then the lookup count of the `Inode` associated with the returned
446*bb4ee6a4SAndroid Build Coastguard Worker     /// `Entry` must be increased by 1.
lookup(&self, ctx: Context, parent: Self::Inode, name: &CStr) -> io::Result<Entry>447*bb4ee6a4SAndroid Build Coastguard Worker     fn lookup(&self, ctx: Context, parent: Self::Inode, name: &CStr) -> io::Result<Entry> {
448*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
449*bb4ee6a4SAndroid Build Coastguard Worker     }
450*bb4ee6a4SAndroid Build Coastguard Worker 
451*bb4ee6a4SAndroid Build Coastguard Worker     /// Forget about an inode.
452*bb4ee6a4SAndroid Build Coastguard Worker     ///
453*bb4ee6a4SAndroid Build Coastguard Worker     /// Called when the kernel removes an inode from its internal caches. `count` indicates the
454*bb4ee6a4SAndroid Build Coastguard Worker     /// amount by which the lookup count for the inode should be decreased. If reducing the lookup
455*bb4ee6a4SAndroid Build Coastguard Worker     /// count by `count` causes it to go to zero, then the implementation may delete the `Inode`.
forget(&self, ctx: Context, inode: Self::Inode, count: u64)456*bb4ee6a4SAndroid Build Coastguard Worker     fn forget(&self, ctx: Context, inode: Self::Inode, count: u64) {}
457*bb4ee6a4SAndroid Build Coastguard Worker 
458*bb4ee6a4SAndroid Build Coastguard Worker     /// Forget about multiple inodes.
459*bb4ee6a4SAndroid Build Coastguard Worker     ///
460*bb4ee6a4SAndroid Build Coastguard Worker     /// `requests` is a vector of `(inode, count)` pairs. See the documentation for `forget` for
461*bb4ee6a4SAndroid Build Coastguard Worker     /// more information.
batch_forget(&self, ctx: Context, requests: Vec<(Self::Inode, u64)>)462*bb4ee6a4SAndroid Build Coastguard Worker     fn batch_forget(&self, ctx: Context, requests: Vec<(Self::Inode, u64)>) {
463*bb4ee6a4SAndroid Build Coastguard Worker         for (inode, count) in requests {
464*bb4ee6a4SAndroid Build Coastguard Worker             self.forget(ctx, inode, count)
465*bb4ee6a4SAndroid Build Coastguard Worker         }
466*bb4ee6a4SAndroid Build Coastguard Worker     }
467*bb4ee6a4SAndroid Build Coastguard Worker 
468*bb4ee6a4SAndroid Build Coastguard Worker     /// Get attributes for a file / directory.
469*bb4ee6a4SAndroid Build Coastguard Worker     ///
470*bb4ee6a4SAndroid Build Coastguard Worker     /// If `handle` is not `None`, then it contains the handle previously returned by the
471*bb4ee6a4SAndroid Build Coastguard Worker     /// implementation after a call to `open` or `opendir`. However, implementations should still
472*bb4ee6a4SAndroid Build Coastguard Worker     /// take care to verify the handle if they do not trust the client (e.g., virtio-fs).
473*bb4ee6a4SAndroid Build Coastguard Worker     ///
474*bb4ee6a4SAndroid Build Coastguard Worker     /// If writeback caching is enabled (`FsOptions::WRITEBACK_CACHE`), then the kernel module
475*bb4ee6a4SAndroid Build Coastguard Worker     /// likely has a better idea of the length of the file than the file system (for
476*bb4ee6a4SAndroid Build Coastguard Worker     /// example, if there was a write that extended the size of the file but has not yet been
477*bb4ee6a4SAndroid Build Coastguard Worker     /// flushed). In this case, the `st_size` field of the returned struct is ignored.
478*bb4ee6a4SAndroid Build Coastguard Worker     ///
479*bb4ee6a4SAndroid Build Coastguard Worker     /// The returned `Duration` indicates how long the returned attributes should be considered
480*bb4ee6a4SAndroid Build Coastguard Worker     /// valid by the client. If the attributes are only changed via the FUSE kernel module (i.e.,
481*bb4ee6a4SAndroid Build Coastguard Worker     /// the kernel module has exclusive access), then this should be a very large value.
getattr( &self, ctx: Context, inode: Self::Inode, handle: Option<Self::Handle>, ) -> io::Result<(libc::stat64, Duration)>482*bb4ee6a4SAndroid Build Coastguard Worker     fn getattr(
483*bb4ee6a4SAndroid Build Coastguard Worker         &self,
484*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
485*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
486*bb4ee6a4SAndroid Build Coastguard Worker         handle: Option<Self::Handle>,
487*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<(libc::stat64, Duration)> {
488*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
489*bb4ee6a4SAndroid Build Coastguard Worker     }
490*bb4ee6a4SAndroid Build Coastguard Worker 
491*bb4ee6a4SAndroid Build Coastguard Worker     /// Set attributes for a file / directory.
492*bb4ee6a4SAndroid Build Coastguard Worker     ///
493*bb4ee6a4SAndroid Build Coastguard Worker     /// If `handle` is not `None`, then it contains the handle previously returned by the
494*bb4ee6a4SAndroid Build Coastguard Worker     /// implementation after a call to `open` or `opendir`. However, implementations should still
495*bb4ee6a4SAndroid Build Coastguard Worker     /// take care to verify the handle if they do not trust the client (e.g., virtio-fs).
496*bb4ee6a4SAndroid Build Coastguard Worker     ///
497*bb4ee6a4SAndroid Build Coastguard Worker     /// The `valid` parameter indicates the fields of `attr` that may be considered valid and should
498*bb4ee6a4SAndroid Build Coastguard Worker     /// be set by the file system. The content of all other fields in `attr` is undefined.
499*bb4ee6a4SAndroid Build Coastguard Worker     ///
500*bb4ee6a4SAndroid Build Coastguard Worker     /// If the `FsOptions::HANDLE_KILLPRIV` was set during `init`, then the implementation is
501*bb4ee6a4SAndroid Build Coastguard Worker     /// expected to reset the setuid and setgid bits if the file size or owner is being changed.
502*bb4ee6a4SAndroid Build Coastguard Worker     ///
503*bb4ee6a4SAndroid Build Coastguard Worker     /// This method returns the new attributes after making the modifications requested by the
504*bb4ee6a4SAndroid Build Coastguard Worker     /// client. The returned `Duration` indicates how long the returned attributes should be
505*bb4ee6a4SAndroid Build Coastguard Worker     /// considered valid by the client. If the attributes are only changed via the FUSE kernel
506*bb4ee6a4SAndroid Build Coastguard Worker     /// module (i.e., the kernel module has exclusive access), then this should be a very large
507*bb4ee6a4SAndroid Build Coastguard Worker     /// value.
setattr( &self, ctx: Context, inode: Self::Inode, attr: libc::stat64, handle: Option<Self::Handle>, valid: SetattrValid, ) -> io::Result<(libc::stat64, Duration)>508*bb4ee6a4SAndroid Build Coastguard Worker     fn setattr(
509*bb4ee6a4SAndroid Build Coastguard Worker         &self,
510*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
511*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
512*bb4ee6a4SAndroid Build Coastguard Worker         attr: libc::stat64,
513*bb4ee6a4SAndroid Build Coastguard Worker         handle: Option<Self::Handle>,
514*bb4ee6a4SAndroid Build Coastguard Worker         valid: SetattrValid,
515*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<(libc::stat64, Duration)> {
516*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
517*bb4ee6a4SAndroid Build Coastguard Worker     }
518*bb4ee6a4SAndroid Build Coastguard Worker 
519*bb4ee6a4SAndroid Build Coastguard Worker     /// Read a symbolic link.
readlink(&self, ctx: Context, inode: Self::Inode) -> io::Result<Vec<u8>>520*bb4ee6a4SAndroid Build Coastguard Worker     fn readlink(&self, ctx: Context, inode: Self::Inode) -> io::Result<Vec<u8>> {
521*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
522*bb4ee6a4SAndroid Build Coastguard Worker     }
523*bb4ee6a4SAndroid Build Coastguard Worker 
524*bb4ee6a4SAndroid Build Coastguard Worker     /// Create a symbolic link.
525*bb4ee6a4SAndroid Build Coastguard Worker     ///
526*bb4ee6a4SAndroid Build Coastguard Worker     /// The file system must create a symbolic link named `name` in the directory represented by
527*bb4ee6a4SAndroid Build Coastguard Worker     /// `parent`, which contains the string `linkname`. Returns an `Entry` for the newly created
528*bb4ee6a4SAndroid Build Coastguard Worker     /// symlink.
529*bb4ee6a4SAndroid Build Coastguard Worker     ///
530*bb4ee6a4SAndroid Build Coastguard Worker     /// If this call is successful then the lookup count of the `Inode` associated with the returned
531*bb4ee6a4SAndroid Build Coastguard Worker     /// `Entry` must be increased by 1.
symlink( &self, ctx: Context, linkname: &CStr, parent: Self::Inode, name: &CStr, security_ctx: Option<&CStr>, ) -> io::Result<Entry>532*bb4ee6a4SAndroid Build Coastguard Worker     fn symlink(
533*bb4ee6a4SAndroid Build Coastguard Worker         &self,
534*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
535*bb4ee6a4SAndroid Build Coastguard Worker         linkname: &CStr,
536*bb4ee6a4SAndroid Build Coastguard Worker         parent: Self::Inode,
537*bb4ee6a4SAndroid Build Coastguard Worker         name: &CStr,
538*bb4ee6a4SAndroid Build Coastguard Worker         security_ctx: Option<&CStr>,
539*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<Entry> {
540*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
541*bb4ee6a4SAndroid Build Coastguard Worker     }
542*bb4ee6a4SAndroid Build Coastguard Worker 
543*bb4ee6a4SAndroid Build Coastguard Worker     /// Create a file node.
544*bb4ee6a4SAndroid Build Coastguard Worker     ///
545*bb4ee6a4SAndroid Build Coastguard Worker     /// Create a regular file, character device, block device, fifo, or socket node named `name` in
546*bb4ee6a4SAndroid Build Coastguard Worker     /// the directory represented by `inode`. Valid values for `mode` and `rdev` are the same as
547*bb4ee6a4SAndroid Build Coastguard Worker     /// those accepted by the `mknod(2)` system call. Returns an `Entry` for the newly created node.
548*bb4ee6a4SAndroid Build Coastguard Worker     ///
549*bb4ee6a4SAndroid Build Coastguard Worker     /// When the `FsOptions::DONT_MASK` feature is set, the file system is responsible for setting
550*bb4ee6a4SAndroid Build Coastguard Worker     /// the permissions of the created node to `mode & !umask`.
551*bb4ee6a4SAndroid Build Coastguard Worker     ///
552*bb4ee6a4SAndroid Build Coastguard Worker     /// If this call is successful then the lookup count of the `Inode` associated with the returned
553*bb4ee6a4SAndroid Build Coastguard Worker     /// `Entry` must be increased by 1.
mknod( &self, ctx: Context, inode: Self::Inode, name: &CStr, mode: u32, rdev: u32, umask: u32, security_ctx: Option<&CStr>, ) -> io::Result<Entry>554*bb4ee6a4SAndroid Build Coastguard Worker     fn mknod(
555*bb4ee6a4SAndroid Build Coastguard Worker         &self,
556*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
557*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
558*bb4ee6a4SAndroid Build Coastguard Worker         name: &CStr,
559*bb4ee6a4SAndroid Build Coastguard Worker         mode: u32,
560*bb4ee6a4SAndroid Build Coastguard Worker         rdev: u32,
561*bb4ee6a4SAndroid Build Coastguard Worker         umask: u32,
562*bb4ee6a4SAndroid Build Coastguard Worker         security_ctx: Option<&CStr>,
563*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<Entry> {
564*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
565*bb4ee6a4SAndroid Build Coastguard Worker     }
566*bb4ee6a4SAndroid Build Coastguard Worker 
567*bb4ee6a4SAndroid Build Coastguard Worker     /// Create a directory.
568*bb4ee6a4SAndroid Build Coastguard Worker     ///
569*bb4ee6a4SAndroid Build Coastguard Worker     /// When the `FsOptions::DONT_MASK` feature is set, the file system is responsible for setting
570*bb4ee6a4SAndroid Build Coastguard Worker     /// the permissions of the created directory to `mode & !umask`. Returns an `Entry` for the
571*bb4ee6a4SAndroid Build Coastguard Worker     /// newly created directory.
572*bb4ee6a4SAndroid Build Coastguard Worker     ///
573*bb4ee6a4SAndroid Build Coastguard Worker     /// If this call is successful then the lookup count of the `Inode` associated with the returned
574*bb4ee6a4SAndroid Build Coastguard Worker     /// `Entry` must be increased by 1.
mkdir( &self, ctx: Context, parent: Self::Inode, name: &CStr, mode: u32, umask: u32, security_ctx: Option<&CStr>, ) -> io::Result<Entry>575*bb4ee6a4SAndroid Build Coastguard Worker     fn mkdir(
576*bb4ee6a4SAndroid Build Coastguard Worker         &self,
577*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
578*bb4ee6a4SAndroid Build Coastguard Worker         parent: Self::Inode,
579*bb4ee6a4SAndroid Build Coastguard Worker         name: &CStr,
580*bb4ee6a4SAndroid Build Coastguard Worker         mode: u32,
581*bb4ee6a4SAndroid Build Coastguard Worker         umask: u32,
582*bb4ee6a4SAndroid Build Coastguard Worker         security_ctx: Option<&CStr>,
583*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<Entry> {
584*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
585*bb4ee6a4SAndroid Build Coastguard Worker     }
586*bb4ee6a4SAndroid Build Coastguard Worker 
587*bb4ee6a4SAndroid Build Coastguard Worker     /// Create an unnamed temporary file.
chromeos_tmpfile( &self, ctx: Context, parent: Self::Inode, mode: u32, umask: u32, security_ctx: Option<&CStr>, ) -> io::Result<Entry>588*bb4ee6a4SAndroid Build Coastguard Worker     fn chromeos_tmpfile(
589*bb4ee6a4SAndroid Build Coastguard Worker         &self,
590*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
591*bb4ee6a4SAndroid Build Coastguard Worker         parent: Self::Inode,
592*bb4ee6a4SAndroid Build Coastguard Worker         mode: u32,
593*bb4ee6a4SAndroid Build Coastguard Worker         umask: u32,
594*bb4ee6a4SAndroid Build Coastguard Worker         security_ctx: Option<&CStr>,
595*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<Entry> {
596*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
597*bb4ee6a4SAndroid Build Coastguard Worker     }
598*bb4ee6a4SAndroid Build Coastguard Worker 
599*bb4ee6a4SAndroid Build Coastguard Worker     /// Remove a file.
600*bb4ee6a4SAndroid Build Coastguard Worker     ///
601*bb4ee6a4SAndroid Build Coastguard Worker     /// If the file's inode lookup count is non-zero, then the file system is expected to delay
602*bb4ee6a4SAndroid Build Coastguard Worker     /// removal of the inode until the lookup count goes to zero. See the documentation of the
603*bb4ee6a4SAndroid Build Coastguard Worker     /// `forget` function for more information.
unlink(&self, ctx: Context, parent: Self::Inode, name: &CStr) -> io::Result<()>604*bb4ee6a4SAndroid Build Coastguard Worker     fn unlink(&self, ctx: Context, parent: Self::Inode, name: &CStr) -> io::Result<()> {
605*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
606*bb4ee6a4SAndroid Build Coastguard Worker     }
607*bb4ee6a4SAndroid Build Coastguard Worker 
608*bb4ee6a4SAndroid Build Coastguard Worker     /// Remove a directory.
609*bb4ee6a4SAndroid Build Coastguard Worker     ///
610*bb4ee6a4SAndroid Build Coastguard Worker     /// If the directory's inode lookup count is non-zero, then the file system is expected to delay
611*bb4ee6a4SAndroid Build Coastguard Worker     /// removal of the inode until the lookup count goes to zero. See the documentation of the
612*bb4ee6a4SAndroid Build Coastguard Worker     /// `forget` function for more information.
rmdir(&self, ctx: Context, parent: Self::Inode, name: &CStr) -> io::Result<()>613*bb4ee6a4SAndroid Build Coastguard Worker     fn rmdir(&self, ctx: Context, parent: Self::Inode, name: &CStr) -> io::Result<()> {
614*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
615*bb4ee6a4SAndroid Build Coastguard Worker     }
616*bb4ee6a4SAndroid Build Coastguard Worker 
617*bb4ee6a4SAndroid Build Coastguard Worker     /// Rename a file / directory.
618*bb4ee6a4SAndroid Build Coastguard Worker     ///
619*bb4ee6a4SAndroid Build Coastguard Worker     /// If the destination exists, it should be atomically replaced. If the destination's inode
620*bb4ee6a4SAndroid Build Coastguard Worker     /// lookup count is non-zero, then the file system is expected to delay removal of the inode
621*bb4ee6a4SAndroid Build Coastguard Worker     /// until the lookup count goes to zero. See the documentation of the `forget` function for more
622*bb4ee6a4SAndroid Build Coastguard Worker     /// information.
623*bb4ee6a4SAndroid Build Coastguard Worker     ///
624*bb4ee6a4SAndroid Build Coastguard Worker     /// `flags` may be `libc::RENAME_EXCHANGE` or `libc::RENAME_NOREPLACE`. If
625*bb4ee6a4SAndroid Build Coastguard Worker     /// `libc::RENAME_NOREPLACE` is specified, the implementation must not overwrite `newname` if it
626*bb4ee6a4SAndroid Build Coastguard Worker     /// exists and must return an error instead. If `libc::RENAME_EXCHANGE` is specified, the
627*bb4ee6a4SAndroid Build Coastguard Worker     /// implementation must atomically exchange the two files, i.e., both must exist and neither may
628*bb4ee6a4SAndroid Build Coastguard Worker     /// be deleted.
rename( &self, ctx: Context, olddir: Self::Inode, oldname: &CStr, newdir: Self::Inode, newname: &CStr, flags: u32, ) -> io::Result<()>629*bb4ee6a4SAndroid Build Coastguard Worker     fn rename(
630*bb4ee6a4SAndroid Build Coastguard Worker         &self,
631*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
632*bb4ee6a4SAndroid Build Coastguard Worker         olddir: Self::Inode,
633*bb4ee6a4SAndroid Build Coastguard Worker         oldname: &CStr,
634*bb4ee6a4SAndroid Build Coastguard Worker         newdir: Self::Inode,
635*bb4ee6a4SAndroid Build Coastguard Worker         newname: &CStr,
636*bb4ee6a4SAndroid Build Coastguard Worker         flags: u32,
637*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<()> {
638*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
639*bb4ee6a4SAndroid Build Coastguard Worker     }
640*bb4ee6a4SAndroid Build Coastguard Worker 
641*bb4ee6a4SAndroid Build Coastguard Worker     /// Create a hard link.
642*bb4ee6a4SAndroid Build Coastguard Worker     ///
643*bb4ee6a4SAndroid Build Coastguard Worker     /// Create a hard link from `inode` to `newname` in the directory represented by `newparent`.
644*bb4ee6a4SAndroid Build Coastguard Worker     ///
645*bb4ee6a4SAndroid Build Coastguard Worker     /// If this call is successful then the lookup count of the `Inode` associated with the returned
646*bb4ee6a4SAndroid Build Coastguard Worker     /// `Entry` must be increased by 1.
link( &self, ctx: Context, inode: Self::Inode, newparent: Self::Inode, newname: &CStr, ) -> io::Result<Entry>647*bb4ee6a4SAndroid Build Coastguard Worker     fn link(
648*bb4ee6a4SAndroid Build Coastguard Worker         &self,
649*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
650*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
651*bb4ee6a4SAndroid Build Coastguard Worker         newparent: Self::Inode,
652*bb4ee6a4SAndroid Build Coastguard Worker         newname: &CStr,
653*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<Entry> {
654*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
655*bb4ee6a4SAndroid Build Coastguard Worker     }
656*bb4ee6a4SAndroid Build Coastguard Worker 
657*bb4ee6a4SAndroid Build Coastguard Worker     /// Open a file.
658*bb4ee6a4SAndroid Build Coastguard Worker     ///
659*bb4ee6a4SAndroid Build Coastguard Worker     /// Open the file associated with `inode` for reading / writing. All values accepted by the
660*bb4ee6a4SAndroid Build Coastguard Worker     /// `open(2)` system call are valid values for `flags` and must be handled by the file system.
661*bb4ee6a4SAndroid Build Coastguard Worker     /// However, there are some additional rules:
662*bb4ee6a4SAndroid Build Coastguard Worker     ///
663*bb4ee6a4SAndroid Build Coastguard Worker     /// * Creation flags (`libc::O_CREAT`, `libc::O_EXCL`, `libc::O_NOCTTY`) will be filtered out
664*bb4ee6a4SAndroid Build Coastguard Worker     ///   and handled by the kernel.
665*bb4ee6a4SAndroid Build Coastguard Worker     ///
666*bb4ee6a4SAndroid Build Coastguard Worker     /// * The file system should check the access modes (`libc::O_RDONLY`, `libc::O_WRONLY`,
667*bb4ee6a4SAndroid Build Coastguard Worker     ///   `libc::O_RDWR`) to determine if the operation is permitted. If the file system was mounted
668*bb4ee6a4SAndroid Build Coastguard Worker     ///   with the `-o default_permissions` mount option, then this check will also be carried out
669*bb4ee6a4SAndroid Build Coastguard Worker     ///   by the kernel before sending the open request.
670*bb4ee6a4SAndroid Build Coastguard Worker     ///
671*bb4ee6a4SAndroid Build Coastguard Worker     /// * When writeback caching is enabled (`FsOptions::WRITEBACK_CACHE`) the kernel may send read
672*bb4ee6a4SAndroid Build Coastguard Worker     ///   requests even for files opened with `libc::O_WRONLY`. The file system should be prepared
673*bb4ee6a4SAndroid Build Coastguard Worker     ///   to handle this.
674*bb4ee6a4SAndroid Build Coastguard Worker     ///
675*bb4ee6a4SAndroid Build Coastguard Worker     /// * When writeback caching is enabled, the kernel will handle the `libc::O_APPEND` flag.
676*bb4ee6a4SAndroid Build Coastguard Worker     ///   However, this will not work reliably unless the kernel has exclusive access to the file.
677*bb4ee6a4SAndroid Build Coastguard Worker     ///   In this case the file system may either ignore the `libc::O_APPEND` flag or return an
678*bb4ee6a4SAndroid Build Coastguard Worker     ///   error to indicate that reliable `libc::O_APPEND` handling is not available.
679*bb4ee6a4SAndroid Build Coastguard Worker     ///
680*bb4ee6a4SAndroid Build Coastguard Worker     /// * When writeback caching is disabled, the file system is expected to properly handle
681*bb4ee6a4SAndroid Build Coastguard Worker     ///   `libc::O_APPEND` and ensure that each write is appended to the end of the file.
682*bb4ee6a4SAndroid Build Coastguard Worker     ///
683*bb4ee6a4SAndroid Build Coastguard Worker     /// The file system may choose to return a `Handle` to refer to the newly opened file. The
684*bb4ee6a4SAndroid Build Coastguard Worker     /// kernel will then use this `Handle` for all operations on the content of the file (`read`,
685*bb4ee6a4SAndroid Build Coastguard Worker     /// `write`, `flush`, `release`, `fsync`). If the file system does not return a
686*bb4ee6a4SAndroid Build Coastguard Worker     /// `Handle` then the kernel will use the `Inode` for the file to operate on its contents. In
687*bb4ee6a4SAndroid Build Coastguard Worker     /// this case the file system may wish to enable the `FsOptions::ZERO_MESSAGE_OPEN` feature if
688*bb4ee6a4SAndroid Build Coastguard Worker     /// it is supported by the kernel (see below).
689*bb4ee6a4SAndroid Build Coastguard Worker     ///
690*bb4ee6a4SAndroid Build Coastguard Worker     /// The returned `OpenOptions` allow the file system to change the way the opened file is
691*bb4ee6a4SAndroid Build Coastguard Worker     /// handled by the kernel. See the documentation of `OpenOptions` for more information.
692*bb4ee6a4SAndroid Build Coastguard Worker     ///
693*bb4ee6a4SAndroid Build Coastguard Worker     /// If the `FsOptions::ZERO_MESSAGE_OPEN` feature is enabled by both the file system
694*bb4ee6a4SAndroid Build Coastguard Worker     /// implementation and the kernel, then the file system may return an error of `ENOSYS`. This
695*bb4ee6a4SAndroid Build Coastguard Worker     /// will be interpreted by the kernel as success and future calls to `open` and `release` will
696*bb4ee6a4SAndroid Build Coastguard Worker     /// be handled by the kernel without being passed on to the file system.
open( &self, ctx: Context, inode: Self::Inode, flags: u32, ) -> io::Result<(Option<Self::Handle>, OpenOptions)>697*bb4ee6a4SAndroid Build Coastguard Worker     fn open(
698*bb4ee6a4SAndroid Build Coastguard Worker         &self,
699*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
700*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
701*bb4ee6a4SAndroid Build Coastguard Worker         flags: u32,
702*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<(Option<Self::Handle>, OpenOptions)> {
703*bb4ee6a4SAndroid Build Coastguard Worker         // Matches the behavior of libfuse.
704*bb4ee6a4SAndroid Build Coastguard Worker         Ok((None, OpenOptions::empty()))
705*bb4ee6a4SAndroid Build Coastguard Worker     }
706*bb4ee6a4SAndroid Build Coastguard Worker 
707*bb4ee6a4SAndroid Build Coastguard Worker     /// Create and open a file.
708*bb4ee6a4SAndroid Build Coastguard Worker     ///
709*bb4ee6a4SAndroid Build Coastguard Worker     /// If the file does not already exist, the file system should create it with the specified
710*bb4ee6a4SAndroid Build Coastguard Worker     /// `mode`. When the `FsOptions::DONT_MASK` feature is set, the file system is responsible for
711*bb4ee6a4SAndroid Build Coastguard Worker     /// setting the permissions of the created file to `mode & !umask`.
712*bb4ee6a4SAndroid Build Coastguard Worker     ///
713*bb4ee6a4SAndroid Build Coastguard Worker     /// If the file system returns an `ENOSYS` error, then the kernel will treat this method as
714*bb4ee6a4SAndroid Build Coastguard Worker     /// unimplemented and all future calls to `create` will be handled by calling the `mknod` and
715*bb4ee6a4SAndroid Build Coastguard Worker     /// `open` methods instead.
716*bb4ee6a4SAndroid Build Coastguard Worker     ///
717*bb4ee6a4SAndroid Build Coastguard Worker     /// See the documentation for the `open` method for more information about opening the file. In
718*bb4ee6a4SAndroid Build Coastguard Worker     /// addition to the optional `Handle` and the `OpenOptions`, the file system must also return an
719*bb4ee6a4SAndroid Build Coastguard Worker     /// `Entry` for the file. This increases the lookup count for the `Inode` associated with the
720*bb4ee6a4SAndroid Build Coastguard Worker     /// file by 1.
create( &self, ctx: Context, parent: Self::Inode, name: &CStr, mode: u32, flags: u32, umask: u32, security_ctx: Option<&CStr>, ) -> io::Result<(Entry, Option<Self::Handle>, OpenOptions)>721*bb4ee6a4SAndroid Build Coastguard Worker     fn create(
722*bb4ee6a4SAndroid Build Coastguard Worker         &self,
723*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
724*bb4ee6a4SAndroid Build Coastguard Worker         parent: Self::Inode,
725*bb4ee6a4SAndroid Build Coastguard Worker         name: &CStr,
726*bb4ee6a4SAndroid Build Coastguard Worker         mode: u32,
727*bb4ee6a4SAndroid Build Coastguard Worker         flags: u32,
728*bb4ee6a4SAndroid Build Coastguard Worker         umask: u32,
729*bb4ee6a4SAndroid Build Coastguard Worker         security_ctx: Option<&CStr>,
730*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<(Entry, Option<Self::Handle>, OpenOptions)> {
731*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
732*bb4ee6a4SAndroid Build Coastguard Worker     }
733*bb4ee6a4SAndroid Build Coastguard Worker 
734*bb4ee6a4SAndroid Build Coastguard Worker     /// Read data from a file.
735*bb4ee6a4SAndroid Build Coastguard Worker     ///
736*bb4ee6a4SAndroid Build Coastguard Worker     /// Returns `size` bytes of data starting from offset `off` from the file associated with
737*bb4ee6a4SAndroid Build Coastguard Worker     /// `inode` or `handle`.
738*bb4ee6a4SAndroid Build Coastguard Worker     ///
739*bb4ee6a4SAndroid Build Coastguard Worker     /// `flags` contains the flags used to open the file. Similarly, `handle` is the `Handle`
740*bb4ee6a4SAndroid Build Coastguard Worker     /// returned by the file system from the `open` method, if any. If the file system
741*bb4ee6a4SAndroid Build Coastguard Worker     /// implementation did not return a `Handle` from `open` then the contents of `handle` are
742*bb4ee6a4SAndroid Build Coastguard Worker     /// undefined.
743*bb4ee6a4SAndroid Build Coastguard Worker     ///
744*bb4ee6a4SAndroid Build Coastguard Worker     /// This method should return exactly the number of bytes requested by the kernel, except in the
745*bb4ee6a4SAndroid Build Coastguard Worker     /// case of error or EOF. Otherwise, the kernel will substitute the rest of the data with
746*bb4ee6a4SAndroid Build Coastguard Worker     /// zeroes. An exception to this rule is if the file was opened with the "direct I/O" option
747*bb4ee6a4SAndroid Build Coastguard Worker     /// (`libc::O_DIRECT`), in which case the kernel will forward the return code from this method
748*bb4ee6a4SAndroid Build Coastguard Worker     /// to the userspace application that made the system call.
read<W: io::Write + ZeroCopyWriter>( &self, ctx: Context, inode: Self::Inode, handle: Self::Handle, w: W, size: u32, offset: u64, lock_owner: Option<u64>, flags: u32, ) -> io::Result<usize>749*bb4ee6a4SAndroid Build Coastguard Worker     fn read<W: io::Write + ZeroCopyWriter>(
750*bb4ee6a4SAndroid Build Coastguard Worker         &self,
751*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
752*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
753*bb4ee6a4SAndroid Build Coastguard Worker         handle: Self::Handle,
754*bb4ee6a4SAndroid Build Coastguard Worker         w: W,
755*bb4ee6a4SAndroid Build Coastguard Worker         size: u32,
756*bb4ee6a4SAndroid Build Coastguard Worker         offset: u64,
757*bb4ee6a4SAndroid Build Coastguard Worker         lock_owner: Option<u64>,
758*bb4ee6a4SAndroid Build Coastguard Worker         flags: u32,
759*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<usize> {
760*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
761*bb4ee6a4SAndroid Build Coastguard Worker     }
762*bb4ee6a4SAndroid Build Coastguard Worker 
763*bb4ee6a4SAndroid Build Coastguard Worker     /// Write data to a file.
764*bb4ee6a4SAndroid Build Coastguard Worker     ///
765*bb4ee6a4SAndroid Build Coastguard Worker     /// Writes `size` bytes of data starting from offset `off` to the file associated with `inode`
766*bb4ee6a4SAndroid Build Coastguard Worker     /// or `handle`.
767*bb4ee6a4SAndroid Build Coastguard Worker     ///
768*bb4ee6a4SAndroid Build Coastguard Worker     /// `flags` contains the flags used to open the file. Similarly, `handle` is the `Handle`
769*bb4ee6a4SAndroid Build Coastguard Worker     /// returned by the file system from the `open` method, if any. If the file system
770*bb4ee6a4SAndroid Build Coastguard Worker     /// implementation did not return a `Handle` from `open` then the contents of `handle` are
771*bb4ee6a4SAndroid Build Coastguard Worker     /// undefined.
772*bb4ee6a4SAndroid Build Coastguard Worker     ///
773*bb4ee6a4SAndroid Build Coastguard Worker     /// If the `FsOptions::HANDLE_KILLPRIV` feature is not enabled then then the file system is
774*bb4ee6a4SAndroid Build Coastguard Worker     /// expected to clear the setuid and setgid bits.
775*bb4ee6a4SAndroid Build Coastguard Worker     ///
776*bb4ee6a4SAndroid Build Coastguard Worker     /// If `delayed_write` is true then it indicates that this is a write for buffered data.
777*bb4ee6a4SAndroid Build Coastguard Worker     ///
778*bb4ee6a4SAndroid Build Coastguard Worker     /// This method should return exactly the number of bytes requested by the kernel, except in the
779*bb4ee6a4SAndroid Build Coastguard Worker     /// case of error. An exception to this rule is if the file was opened with the "direct I/O"
780*bb4ee6a4SAndroid Build Coastguard Worker     /// option (`libc::O_DIRECT`), in which case the kernel will forward the return code from this
781*bb4ee6a4SAndroid Build Coastguard Worker     /// method to the userspace application that made the system call.
write<R: io::Read + ZeroCopyReader>( &self, ctx: Context, inode: Self::Inode, handle: Self::Handle, r: R, size: u32, offset: u64, lock_owner: Option<u64>, delayed_write: bool, flags: u32, ) -> io::Result<usize>782*bb4ee6a4SAndroid Build Coastguard Worker     fn write<R: io::Read + ZeroCopyReader>(
783*bb4ee6a4SAndroid Build Coastguard Worker         &self,
784*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
785*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
786*bb4ee6a4SAndroid Build Coastguard Worker         handle: Self::Handle,
787*bb4ee6a4SAndroid Build Coastguard Worker         r: R,
788*bb4ee6a4SAndroid Build Coastguard Worker         size: u32,
789*bb4ee6a4SAndroid Build Coastguard Worker         offset: u64,
790*bb4ee6a4SAndroid Build Coastguard Worker         lock_owner: Option<u64>,
791*bb4ee6a4SAndroid Build Coastguard Worker         delayed_write: bool,
792*bb4ee6a4SAndroid Build Coastguard Worker         flags: u32,
793*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<usize> {
794*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
795*bb4ee6a4SAndroid Build Coastguard Worker     }
796*bb4ee6a4SAndroid Build Coastguard Worker 
797*bb4ee6a4SAndroid Build Coastguard Worker     /// Flush the contents of a file.
798*bb4ee6a4SAndroid Build Coastguard Worker     ///
799*bb4ee6a4SAndroid Build Coastguard Worker     /// This method is called on every `close()` of a file descriptor. Since it is possible to
800*bb4ee6a4SAndroid Build Coastguard Worker     /// duplicate file descriptors there may be many `flush` calls for one call to `open`.
801*bb4ee6a4SAndroid Build Coastguard Worker     ///
802*bb4ee6a4SAndroid Build Coastguard Worker     /// File systems should not make any assumptions about when `flush` will be
803*bb4ee6a4SAndroid Build Coastguard Worker     /// called or even if it will be called at all.
804*bb4ee6a4SAndroid Build Coastguard Worker     ///
805*bb4ee6a4SAndroid Build Coastguard Worker     /// `handle` is the `Handle` returned by the file system from the `open` method, if any. If the
806*bb4ee6a4SAndroid Build Coastguard Worker     /// file system did not return a `Handle` from `open` then the contents of `handle` are
807*bb4ee6a4SAndroid Build Coastguard Worker     /// undefined.
808*bb4ee6a4SAndroid Build Coastguard Worker     ///
809*bb4ee6a4SAndroid Build Coastguard Worker     /// Unlike `fsync`, the file system is not required to flush pending writes. One reason to flush
810*bb4ee6a4SAndroid Build Coastguard Worker     /// data is if the file system wants to return write errors during close. However, this is not
811*bb4ee6a4SAndroid Build Coastguard Worker     /// portable because POSIX does not require `close` to wait for delayed I/O to complete.
812*bb4ee6a4SAndroid Build Coastguard Worker     ///
813*bb4ee6a4SAndroid Build Coastguard Worker     /// If the `FsOptions::POSIX_LOCKS` feature is enabled, then the file system must remove all
814*bb4ee6a4SAndroid Build Coastguard Worker     /// locks belonging to `lock_owner`.
815*bb4ee6a4SAndroid Build Coastguard Worker     ///
816*bb4ee6a4SAndroid Build Coastguard Worker     /// If this method returns an `ENOSYS` error then the kernel will treat it as success and all
817*bb4ee6a4SAndroid Build Coastguard Worker     /// subsequent calls to `flush` will be handled by the kernel without being forwarded to the
818*bb4ee6a4SAndroid Build Coastguard Worker     /// file system.
flush( &self, ctx: Context, inode: Self::Inode, handle: Self::Handle, lock_owner: u64, ) -> io::Result<()>819*bb4ee6a4SAndroid Build Coastguard Worker     fn flush(
820*bb4ee6a4SAndroid Build Coastguard Worker         &self,
821*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
822*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
823*bb4ee6a4SAndroid Build Coastguard Worker         handle: Self::Handle,
824*bb4ee6a4SAndroid Build Coastguard Worker         lock_owner: u64,
825*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<()> {
826*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
827*bb4ee6a4SAndroid Build Coastguard Worker     }
828*bb4ee6a4SAndroid Build Coastguard Worker 
829*bb4ee6a4SAndroid Build Coastguard Worker     /// Synchronize file contents.
830*bb4ee6a4SAndroid Build Coastguard Worker     ///
831*bb4ee6a4SAndroid Build Coastguard Worker     /// File systems must ensure that the file contents have been flushed to disk before returning
832*bb4ee6a4SAndroid Build Coastguard Worker     /// from this method. If `datasync` is true then only the file data (but not the metadata) needs
833*bb4ee6a4SAndroid Build Coastguard Worker     /// to be flushed.
834*bb4ee6a4SAndroid Build Coastguard Worker     ///
835*bb4ee6a4SAndroid Build Coastguard Worker     /// `handle` is the `Handle` returned by the file system from the `open` method, if any. If the
836*bb4ee6a4SAndroid Build Coastguard Worker     /// file system did not return a `Handle` from `open` then the contents of
837*bb4ee6a4SAndroid Build Coastguard Worker     /// `handle` are undefined.
838*bb4ee6a4SAndroid Build Coastguard Worker     ///
839*bb4ee6a4SAndroid Build Coastguard Worker     /// If this method returns an `ENOSYS` error then the kernel will treat it as success and all
840*bb4ee6a4SAndroid Build Coastguard Worker     /// subsequent calls to `fsync` will be handled by the kernel without being forwarded to the
841*bb4ee6a4SAndroid Build Coastguard Worker     /// file system.
fsync( &self, ctx: Context, inode: Self::Inode, datasync: bool, handle: Self::Handle, ) -> io::Result<()>842*bb4ee6a4SAndroid Build Coastguard Worker     fn fsync(
843*bb4ee6a4SAndroid Build Coastguard Worker         &self,
844*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
845*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
846*bb4ee6a4SAndroid Build Coastguard Worker         datasync: bool,
847*bb4ee6a4SAndroid Build Coastguard Worker         handle: Self::Handle,
848*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<()> {
849*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
850*bb4ee6a4SAndroid Build Coastguard Worker     }
851*bb4ee6a4SAndroid Build Coastguard Worker 
852*bb4ee6a4SAndroid Build Coastguard Worker     /// Allocate requested space for file data.
853*bb4ee6a4SAndroid Build Coastguard Worker     ///
854*bb4ee6a4SAndroid Build Coastguard Worker     /// If this function returns success, then the file sytem must guarantee that it is possible to
855*bb4ee6a4SAndroid Build Coastguard Worker     /// write up to `length` bytes of data starting at `offset` without failing due to a lack of
856*bb4ee6a4SAndroid Build Coastguard Worker     /// free space on the disk.
857*bb4ee6a4SAndroid Build Coastguard Worker     ///
858*bb4ee6a4SAndroid Build Coastguard Worker     /// `handle` is the `Handle` returned by the file system from the `open` method, if any. If the
859*bb4ee6a4SAndroid Build Coastguard Worker     /// file system did not return a `Handle` from `open` then the contents of `handle` are
860*bb4ee6a4SAndroid Build Coastguard Worker     /// undefined.
861*bb4ee6a4SAndroid Build Coastguard Worker     ///
862*bb4ee6a4SAndroid Build Coastguard Worker     /// If this method returns an `ENOSYS` error then the kernel will treat that as a permanent
863*bb4ee6a4SAndroid Build Coastguard Worker     /// failure: all future calls to `fallocate` will fail with `EOPNOTSUPP` without being forwarded
864*bb4ee6a4SAndroid Build Coastguard Worker     /// to the file system.
fallocate( &self, ctx: Context, inode: Self::Inode, handle: Self::Handle, mode: u32, offset: u64, length: u64, ) -> io::Result<()>865*bb4ee6a4SAndroid Build Coastguard Worker     fn fallocate(
866*bb4ee6a4SAndroid Build Coastguard Worker         &self,
867*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
868*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
869*bb4ee6a4SAndroid Build Coastguard Worker         handle: Self::Handle,
870*bb4ee6a4SAndroid Build Coastguard Worker         mode: u32,
871*bb4ee6a4SAndroid Build Coastguard Worker         offset: u64,
872*bb4ee6a4SAndroid Build Coastguard Worker         length: u64,
873*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<()> {
874*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
875*bb4ee6a4SAndroid Build Coastguard Worker     }
876*bb4ee6a4SAndroid Build Coastguard Worker 
877*bb4ee6a4SAndroid Build Coastguard Worker     /// Release an open file.
878*bb4ee6a4SAndroid Build Coastguard Worker     ///
879*bb4ee6a4SAndroid Build Coastguard Worker     /// This method is called when there are no more references to an open file: all file
880*bb4ee6a4SAndroid Build Coastguard Worker     /// descriptors are closed and all memory mappings are unmapped.
881*bb4ee6a4SAndroid Build Coastguard Worker     ///
882*bb4ee6a4SAndroid Build Coastguard Worker     /// For every `open` call there will be exactly one `release` call (unless the file system is
883*bb4ee6a4SAndroid Build Coastguard Worker     /// force-unmounted).
884*bb4ee6a4SAndroid Build Coastguard Worker     ///
885*bb4ee6a4SAndroid Build Coastguard Worker     /// The file system may reply with an error, but error values are not returned to the `close()`
886*bb4ee6a4SAndroid Build Coastguard Worker     /// or `munmap()` which triggered the release.
887*bb4ee6a4SAndroid Build Coastguard Worker     ///
888*bb4ee6a4SAndroid Build Coastguard Worker     /// `handle` is the `Handle` returned by the file system from the `open` method, if any. If the
889*bb4ee6a4SAndroid Build Coastguard Worker     /// file system did not return a `Handle` from `open` then the contents of
890*bb4ee6a4SAndroid Build Coastguard Worker     /// `handle` are undefined.
891*bb4ee6a4SAndroid Build Coastguard Worker     ///
892*bb4ee6a4SAndroid Build Coastguard Worker     /// If `flush` is `true` then the contents of the file should also be flushed to disk.
release( &self, ctx: Context, inode: Self::Inode, flags: u32, handle: Self::Handle, flush: bool, flock_release: bool, lock_owner: Option<u64>, ) -> io::Result<()>893*bb4ee6a4SAndroid Build Coastguard Worker     fn release(
894*bb4ee6a4SAndroid Build Coastguard Worker         &self,
895*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
896*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
897*bb4ee6a4SAndroid Build Coastguard Worker         flags: u32,
898*bb4ee6a4SAndroid Build Coastguard Worker         handle: Self::Handle,
899*bb4ee6a4SAndroid Build Coastguard Worker         flush: bool,
900*bb4ee6a4SAndroid Build Coastguard Worker         flock_release: bool,
901*bb4ee6a4SAndroid Build Coastguard Worker         lock_owner: Option<u64>,
902*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<()> {
903*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
904*bb4ee6a4SAndroid Build Coastguard Worker     }
905*bb4ee6a4SAndroid Build Coastguard Worker 
906*bb4ee6a4SAndroid Build Coastguard Worker     /// Get information about the file system.
statfs(&self, ctx: Context, inode: Self::Inode) -> io::Result<libc::statvfs64>907*bb4ee6a4SAndroid Build Coastguard Worker     fn statfs(&self, ctx: Context, inode: Self::Inode) -> io::Result<libc::statvfs64> {
908*bb4ee6a4SAndroid Build Coastguard Worker         // SAFETY: zero-initializing a struct with only POD fields.
909*bb4ee6a4SAndroid Build Coastguard Worker         let mut st: libc::statvfs64 = unsafe { mem::zeroed() };
910*bb4ee6a4SAndroid Build Coastguard Worker 
911*bb4ee6a4SAndroid Build Coastguard Worker         // This matches the behavior of libfuse as it returns these values if the
912*bb4ee6a4SAndroid Build Coastguard Worker         // filesystem doesn't implement this method.
913*bb4ee6a4SAndroid Build Coastguard Worker         st.f_namemax = 255;
914*bb4ee6a4SAndroid Build Coastguard Worker         st.f_bsize = 512;
915*bb4ee6a4SAndroid Build Coastguard Worker 
916*bb4ee6a4SAndroid Build Coastguard Worker         Ok(st)
917*bb4ee6a4SAndroid Build Coastguard Worker     }
918*bb4ee6a4SAndroid Build Coastguard Worker 
919*bb4ee6a4SAndroid Build Coastguard Worker     /// Set an extended attribute.
920*bb4ee6a4SAndroid Build Coastguard Worker     ///
921*bb4ee6a4SAndroid Build Coastguard Worker     /// If this method fails with an `ENOSYS` error, then the kernel will treat that as a permanent
922*bb4ee6a4SAndroid Build Coastguard Worker     /// failure. The kernel will return `EOPNOTSUPP` for all future calls to `setxattr` without
923*bb4ee6a4SAndroid Build Coastguard Worker     /// forwarding them to the file system.
924*bb4ee6a4SAndroid Build Coastguard Worker     ///
925*bb4ee6a4SAndroid Build Coastguard Worker     /// Valid values for flags are the same as those accepted by the `setxattr(2)` system call and
926*bb4ee6a4SAndroid Build Coastguard Worker     /// have the same behavior.
setxattr( &self, ctx: Context, inode: Self::Inode, name: &CStr, value: &[u8], flags: u32, ) -> io::Result<()>927*bb4ee6a4SAndroid Build Coastguard Worker     fn setxattr(
928*bb4ee6a4SAndroid Build Coastguard Worker         &self,
929*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
930*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
931*bb4ee6a4SAndroid Build Coastguard Worker         name: &CStr,
932*bb4ee6a4SAndroid Build Coastguard Worker         value: &[u8],
933*bb4ee6a4SAndroid Build Coastguard Worker         flags: u32,
934*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<()> {
935*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
936*bb4ee6a4SAndroid Build Coastguard Worker     }
937*bb4ee6a4SAndroid Build Coastguard Worker 
938*bb4ee6a4SAndroid Build Coastguard Worker     /// Get an extended attribute.
939*bb4ee6a4SAndroid Build Coastguard Worker     ///
940*bb4ee6a4SAndroid Build Coastguard Worker     /// If `size` is 0, then the file system should respond with `GetxattrReply::Count` and the
941*bb4ee6a4SAndroid Build Coastguard Worker     /// number of bytes needed to hold the value. If `size` is large enough to hold the value, then
942*bb4ee6a4SAndroid Build Coastguard Worker     /// the file system should reply with `GetxattrReply::Value` and the value of the extended
943*bb4ee6a4SAndroid Build Coastguard Worker     /// attribute. If `size` is not 0 but is also not large enough to hold the value, then the file
944*bb4ee6a4SAndroid Build Coastguard Worker     /// system should reply with an `ERANGE` error.
945*bb4ee6a4SAndroid Build Coastguard Worker     ///
946*bb4ee6a4SAndroid Build Coastguard Worker     /// If this method fails with an `ENOSYS` error, then the kernel will treat that as a permanent
947*bb4ee6a4SAndroid Build Coastguard Worker     /// failure. The kernel will return `EOPNOTSUPP` for all future calls to `getxattr` without
948*bb4ee6a4SAndroid Build Coastguard Worker     /// forwarding them to the file system.
getxattr( &self, ctx: Context, inode: Self::Inode, name: &CStr, size: u32, ) -> io::Result<GetxattrReply>949*bb4ee6a4SAndroid Build Coastguard Worker     fn getxattr(
950*bb4ee6a4SAndroid Build Coastguard Worker         &self,
951*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
952*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
953*bb4ee6a4SAndroid Build Coastguard Worker         name: &CStr,
954*bb4ee6a4SAndroid Build Coastguard Worker         size: u32,
955*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<GetxattrReply> {
956*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
957*bb4ee6a4SAndroid Build Coastguard Worker     }
958*bb4ee6a4SAndroid Build Coastguard Worker 
959*bb4ee6a4SAndroid Build Coastguard Worker     /// List extended attribute names.
960*bb4ee6a4SAndroid Build Coastguard Worker     ///
961*bb4ee6a4SAndroid Build Coastguard Worker     /// If `size` is 0, then the file system should respond with `ListxattrReply::Count` and the
962*bb4ee6a4SAndroid Build Coastguard Worker     /// number of bytes needed to hold a `\0` byte separated list of the names of all the extended
963*bb4ee6a4SAndroid Build Coastguard Worker     /// attributes. If `size` is large enough to hold the `\0` byte separated list of the attribute
964*bb4ee6a4SAndroid Build Coastguard Worker     /// names, then the file system should reply with `ListxattrReply::Names` and the list. If
965*bb4ee6a4SAndroid Build Coastguard Worker     /// `size` is not 0 but is also not large enough to hold the list, then the file system should
966*bb4ee6a4SAndroid Build Coastguard Worker     /// reply with an `ERANGE` error.
967*bb4ee6a4SAndroid Build Coastguard Worker     ///
968*bb4ee6a4SAndroid Build Coastguard Worker     /// If this method fails with an `ENOSYS` error, then the kernel will treat that as a permanent
969*bb4ee6a4SAndroid Build Coastguard Worker     /// failure. The kernel will return `EOPNOTSUPP` for all future calls to `listxattr` without
970*bb4ee6a4SAndroid Build Coastguard Worker     /// forwarding them to the file system.
listxattr(&self, ctx: Context, inode: Self::Inode, size: u32) -> io::Result<ListxattrReply>971*bb4ee6a4SAndroid Build Coastguard Worker     fn listxattr(&self, ctx: Context, inode: Self::Inode, size: u32) -> io::Result<ListxattrReply> {
972*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
973*bb4ee6a4SAndroid Build Coastguard Worker     }
974*bb4ee6a4SAndroid Build Coastguard Worker 
975*bb4ee6a4SAndroid Build Coastguard Worker     /// Remove an extended attribute.
976*bb4ee6a4SAndroid Build Coastguard Worker     ///
977*bb4ee6a4SAndroid Build Coastguard Worker     /// If this method fails with an `ENOSYS` error, then the kernel will treat that as a permanent
978*bb4ee6a4SAndroid Build Coastguard Worker     /// failure. The kernel will return `EOPNOTSUPP` for all future calls to `removexattr` without
979*bb4ee6a4SAndroid Build Coastguard Worker     /// forwarding them to the file system.
removexattr(&self, ctx: Context, inode: Self::Inode, name: &CStr) -> io::Result<()>980*bb4ee6a4SAndroid Build Coastguard Worker     fn removexattr(&self, ctx: Context, inode: Self::Inode, name: &CStr) -> io::Result<()> {
981*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
982*bb4ee6a4SAndroid Build Coastguard Worker     }
983*bb4ee6a4SAndroid Build Coastguard Worker 
984*bb4ee6a4SAndroid Build Coastguard Worker     /// Open a directory for reading.
985*bb4ee6a4SAndroid Build Coastguard Worker     ///
986*bb4ee6a4SAndroid Build Coastguard Worker     /// The file system may choose to return a `Handle` to refer to the newly opened directory. The
987*bb4ee6a4SAndroid Build Coastguard Worker     /// kernel will then use this `Handle` for all operations on the content of the directory
988*bb4ee6a4SAndroid Build Coastguard Worker     /// (`readdir`, `readdirplus`, `fsyncdir`, `releasedir`). If the file system does not return a
989*bb4ee6a4SAndroid Build Coastguard Worker     /// `Handle` then the kernel will use the `Inode` for the directory to operate on its contents.
990*bb4ee6a4SAndroid Build Coastguard Worker     /// In this case the file system may wish to enable the `FsOptions::ZERO_MESSAGE_OPENDIR`
991*bb4ee6a4SAndroid Build Coastguard Worker     /// feature if it is supported by the kernel (see below).
992*bb4ee6a4SAndroid Build Coastguard Worker     ///
993*bb4ee6a4SAndroid Build Coastguard Worker     /// The returned `OpenOptions` allow the file system to change the way the opened directory is
994*bb4ee6a4SAndroid Build Coastguard Worker     /// handled by the kernel. See the documentation of `OpenOptions` for more information.
995*bb4ee6a4SAndroid Build Coastguard Worker     ///
996*bb4ee6a4SAndroid Build Coastguard Worker     /// If the `FsOptions::ZERO_MESSAGE_OPENDIR` feature is enabled by both the file system
997*bb4ee6a4SAndroid Build Coastguard Worker     /// implementation and the kernel, then the file system may return an error of `ENOSYS`. This
998*bb4ee6a4SAndroid Build Coastguard Worker     /// will be interpreted by the kernel as success and future calls to `opendir` and `releasedir`
999*bb4ee6a4SAndroid Build Coastguard Worker     /// will be handled by the kernel without being passed on to the file system.
opendir( &self, ctx: Context, inode: Self::Inode, flags: u32, ) -> io::Result<(Option<Self::Handle>, OpenOptions)>1000*bb4ee6a4SAndroid Build Coastguard Worker     fn opendir(
1001*bb4ee6a4SAndroid Build Coastguard Worker         &self,
1002*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
1003*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
1004*bb4ee6a4SAndroid Build Coastguard Worker         flags: u32,
1005*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<(Option<Self::Handle>, OpenOptions)> {
1006*bb4ee6a4SAndroid Build Coastguard Worker         // Matches the behavior of libfuse.
1007*bb4ee6a4SAndroid Build Coastguard Worker         Ok((None, OpenOptions::empty()))
1008*bb4ee6a4SAndroid Build Coastguard Worker     }
1009*bb4ee6a4SAndroid Build Coastguard Worker 
1010*bb4ee6a4SAndroid Build Coastguard Worker     /// Read a directory.
1011*bb4ee6a4SAndroid Build Coastguard Worker     ///
1012*bb4ee6a4SAndroid Build Coastguard Worker     /// `handle` is the `Handle` returned by the file system from the `opendir` method, if any. If
1013*bb4ee6a4SAndroid Build Coastguard Worker     /// the file system did not return a `Handle` from `opendir` then the contents of `handle` are
1014*bb4ee6a4SAndroid Build Coastguard Worker     /// undefined.
1015*bb4ee6a4SAndroid Build Coastguard Worker     ///
1016*bb4ee6a4SAndroid Build Coastguard Worker     /// `size` indicates the maximum number of bytes that should be returned by this method.
1017*bb4ee6a4SAndroid Build Coastguard Worker     ///
1018*bb4ee6a4SAndroid Build Coastguard Worker     /// If `offset` is non-zero then it corresponds to one of the `offset` values from a `DirEntry`
1019*bb4ee6a4SAndroid Build Coastguard Worker     /// that was previously returned by a call to `readdir` for the same handle. In this case the
1020*bb4ee6a4SAndroid Build Coastguard Worker     /// file system should skip over the entries before the position defined by the `offset` value.
1021*bb4ee6a4SAndroid Build Coastguard Worker     /// If entries were added or removed while the `Handle` is open then the file system may still
1022*bb4ee6a4SAndroid Build Coastguard Worker     /// include removed entries or skip newly created entries. However, adding or removing entries
1023*bb4ee6a4SAndroid Build Coastguard Worker     /// should never cause the file system to skip over unrelated entries or include an entry more
1024*bb4ee6a4SAndroid Build Coastguard Worker     /// than once. This means that `offset` cannot be a simple index and must include sufficient
1025*bb4ee6a4SAndroid Build Coastguard Worker     /// information to uniquely determine the next entry in the list even when the set of entries is
1026*bb4ee6a4SAndroid Build Coastguard Worker     /// being changed.
1027*bb4ee6a4SAndroid Build Coastguard Worker     ///
1028*bb4ee6a4SAndroid Build Coastguard Worker     /// The file system may return entries for the current directory (".") and parent directory
1029*bb4ee6a4SAndroid Build Coastguard Worker     /// ("..") but is not required to do so. If the file system does not return these entries, then
1030*bb4ee6a4SAndroid Build Coastguard Worker     /// they are implicitly added by the kernel.
1031*bb4ee6a4SAndroid Build Coastguard Worker     ///
1032*bb4ee6a4SAndroid Build Coastguard Worker     /// The lookup count for `Inode`s associated with the returned directory entries is **NOT**
1033*bb4ee6a4SAndroid Build Coastguard Worker     /// affected by this method.
readdir( &self, ctx: Context, inode: Self::Inode, handle: Self::Handle, size: u32, offset: u64, ) -> io::Result<Self::DirIter>1034*bb4ee6a4SAndroid Build Coastguard Worker     fn readdir(
1035*bb4ee6a4SAndroid Build Coastguard Worker         &self,
1036*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
1037*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
1038*bb4ee6a4SAndroid Build Coastguard Worker         handle: Self::Handle,
1039*bb4ee6a4SAndroid Build Coastguard Worker         size: u32,
1040*bb4ee6a4SAndroid Build Coastguard Worker         offset: u64,
1041*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<Self::DirIter> {
1042*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1043*bb4ee6a4SAndroid Build Coastguard Worker     }
1044*bb4ee6a4SAndroid Build Coastguard Worker 
1045*bb4ee6a4SAndroid Build Coastguard Worker     /// Synchronize the contents of a directory.
1046*bb4ee6a4SAndroid Build Coastguard Worker     ///
1047*bb4ee6a4SAndroid Build Coastguard Worker     /// File systems must ensure that the directory contents have been flushed to disk before
1048*bb4ee6a4SAndroid Build Coastguard Worker     /// returning from this method. If `datasync` is true then only the directory data (but not the
1049*bb4ee6a4SAndroid Build Coastguard Worker     /// metadata) needs to be flushed.
1050*bb4ee6a4SAndroid Build Coastguard Worker     ///
1051*bb4ee6a4SAndroid Build Coastguard Worker     /// `handle` is the `Handle` returned by the file system from the `opendir` method, if any. If
1052*bb4ee6a4SAndroid Build Coastguard Worker     /// the file system did not return a `Handle` from `opendir` then the contents of
1053*bb4ee6a4SAndroid Build Coastguard Worker     /// `handle` are undefined.
1054*bb4ee6a4SAndroid Build Coastguard Worker     ///
1055*bb4ee6a4SAndroid Build Coastguard Worker     /// If this method returns an `ENOSYS` error then the kernel will treat it as success and all
1056*bb4ee6a4SAndroid Build Coastguard Worker     /// subsequent calls to `fsyncdir` will be handled by the kernel without being forwarded to the
1057*bb4ee6a4SAndroid Build Coastguard Worker     /// file system.
fsyncdir( &self, ctx: Context, inode: Self::Inode, datasync: bool, handle: Self::Handle, ) -> io::Result<()>1058*bb4ee6a4SAndroid Build Coastguard Worker     fn fsyncdir(
1059*bb4ee6a4SAndroid Build Coastguard Worker         &self,
1060*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
1061*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
1062*bb4ee6a4SAndroid Build Coastguard Worker         datasync: bool,
1063*bb4ee6a4SAndroid Build Coastguard Worker         handle: Self::Handle,
1064*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<()> {
1065*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1066*bb4ee6a4SAndroid Build Coastguard Worker     }
1067*bb4ee6a4SAndroid Build Coastguard Worker 
1068*bb4ee6a4SAndroid Build Coastguard Worker     /// Release an open directory.
1069*bb4ee6a4SAndroid Build Coastguard Worker     ///
1070*bb4ee6a4SAndroid Build Coastguard Worker     /// For every `opendir` call there will be exactly one `releasedir` call (unless the file system
1071*bb4ee6a4SAndroid Build Coastguard Worker     /// is force-unmounted).
1072*bb4ee6a4SAndroid Build Coastguard Worker     ///
1073*bb4ee6a4SAndroid Build Coastguard Worker     /// `handle` is the `Handle` returned by the file system from the `opendir` method, if any. If
1074*bb4ee6a4SAndroid Build Coastguard Worker     /// the file system did not return a `Handle` from `opendir` then the contents of `handle` are
1075*bb4ee6a4SAndroid Build Coastguard Worker     /// undefined.
1076*bb4ee6a4SAndroid Build Coastguard Worker     ///
1077*bb4ee6a4SAndroid Build Coastguard Worker     /// `flags` contains used the flags used to open the directory in `opendir`.
releasedir( &self, ctx: Context, inode: Self::Inode, flags: u32, handle: Self::Handle, ) -> io::Result<()>1078*bb4ee6a4SAndroid Build Coastguard Worker     fn releasedir(
1079*bb4ee6a4SAndroid Build Coastguard Worker         &self,
1080*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
1081*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
1082*bb4ee6a4SAndroid Build Coastguard Worker         flags: u32,
1083*bb4ee6a4SAndroid Build Coastguard Worker         handle: Self::Handle,
1084*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<()> {
1085*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1086*bb4ee6a4SAndroid Build Coastguard Worker     }
1087*bb4ee6a4SAndroid Build Coastguard Worker 
1088*bb4ee6a4SAndroid Build Coastguard Worker     /// Check file access permissions.
1089*bb4ee6a4SAndroid Build Coastguard Worker     ///
1090*bb4ee6a4SAndroid Build Coastguard Worker     /// This method is called when a userspace process in the client makes an `access()` or
1091*bb4ee6a4SAndroid Build Coastguard Worker     /// `chdir()` system call. If the file system was mounted with the `-o default_permissions`
1092*bb4ee6a4SAndroid Build Coastguard Worker     /// mount option, then the kernel will perform these checks itself and this method will not be
1093*bb4ee6a4SAndroid Build Coastguard Worker     /// called.
1094*bb4ee6a4SAndroid Build Coastguard Worker     ///
1095*bb4ee6a4SAndroid Build Coastguard Worker     /// If this method returns an `ENOSYS` error, then the kernel will treat it as a permanent
1096*bb4ee6a4SAndroid Build Coastguard Worker     /// success: all future calls to `access` will return success without being forwarded to the
1097*bb4ee6a4SAndroid Build Coastguard Worker     /// file system.
access(&self, ctx: Context, inode: Self::Inode, mask: u32) -> io::Result<()>1098*bb4ee6a4SAndroid Build Coastguard Worker     fn access(&self, ctx: Context, inode: Self::Inode, mask: u32) -> io::Result<()> {
1099*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1100*bb4ee6a4SAndroid Build Coastguard Worker     }
1101*bb4ee6a4SAndroid Build Coastguard Worker 
1102*bb4ee6a4SAndroid Build Coastguard Worker     /// Perform an ioctl on a file or directory.
1103*bb4ee6a4SAndroid Build Coastguard Worker     ///
1104*bb4ee6a4SAndroid Build Coastguard Worker     /// `handle` is the `Handle` returned by the file system from the `open` or `opendir` methods,
1105*bb4ee6a4SAndroid Build Coastguard Worker     /// if any. If the file system did not return a `Handle` from then the contents of `handle` are
1106*bb4ee6a4SAndroid Build Coastguard Worker     /// undefined.
1107*bb4ee6a4SAndroid Build Coastguard Worker     ///
1108*bb4ee6a4SAndroid Build Coastguard Worker     /// If `flags` contains `IoctlFlags::UNRESTRICTED` then the file system may retry the ioctl
1109*bb4ee6a4SAndroid Build Coastguard Worker     /// after informing the kernel about the input and output areas. If `flags` does not contain
1110*bb4ee6a4SAndroid Build Coastguard Worker     /// `IoctlFlags::UNRESTRICTED` then the kernel will prepare the input and output areas according
1111*bb4ee6a4SAndroid Build Coastguard Worker     /// to the encoding in the ioctl command. In that case the ioctl cannot be retried.
1112*bb4ee6a4SAndroid Build Coastguard Worker     ///
1113*bb4ee6a4SAndroid Build Coastguard Worker     /// `cmd` is the ioctl request made by the calling process, truncated to 32 bits.
1114*bb4ee6a4SAndroid Build Coastguard Worker     ///
1115*bb4ee6a4SAndroid Build Coastguard Worker     /// `arg` is the argument provided by the calling process.
1116*bb4ee6a4SAndroid Build Coastguard Worker     ///
1117*bb4ee6a4SAndroid Build Coastguard Worker     /// `in_size` is the length of the additional data that accompanies the request. The file system
1118*bb4ee6a4SAndroid Build Coastguard Worker     /// may fetch this data from `reader`.
1119*bb4ee6a4SAndroid Build Coastguard Worker     ///
1120*bb4ee6a4SAndroid Build Coastguard Worker     /// `out_size` is the length of the output area prepared by the kernel to hold the response to
1121*bb4ee6a4SAndroid Build Coastguard Worker     /// the ioctl.
ioctl<R: io::Read>( &self, ctx: Context, inode: Self::Inode, handle: Self::Handle, flags: IoctlFlags, cmd: u32, arg: u64, in_size: u32, out_size: u32, reader: R, ) -> io::Result<IoctlReply>1122*bb4ee6a4SAndroid Build Coastguard Worker     fn ioctl<R: io::Read>(
1123*bb4ee6a4SAndroid Build Coastguard Worker         &self,
1124*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
1125*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
1126*bb4ee6a4SAndroid Build Coastguard Worker         handle: Self::Handle,
1127*bb4ee6a4SAndroid Build Coastguard Worker         flags: IoctlFlags,
1128*bb4ee6a4SAndroid Build Coastguard Worker         cmd: u32,
1129*bb4ee6a4SAndroid Build Coastguard Worker         arg: u64,
1130*bb4ee6a4SAndroid Build Coastguard Worker         in_size: u32,
1131*bb4ee6a4SAndroid Build Coastguard Worker         out_size: u32,
1132*bb4ee6a4SAndroid Build Coastguard Worker         reader: R,
1133*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<IoctlReply> {
1134*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1135*bb4ee6a4SAndroid Build Coastguard Worker     }
1136*bb4ee6a4SAndroid Build Coastguard Worker 
1137*bb4ee6a4SAndroid Build Coastguard Worker     /// TODO: support this
getlk(&self) -> io::Result<()>1138*bb4ee6a4SAndroid Build Coastguard Worker     fn getlk(&self) -> io::Result<()> {
1139*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1140*bb4ee6a4SAndroid Build Coastguard Worker     }
1141*bb4ee6a4SAndroid Build Coastguard Worker 
1142*bb4ee6a4SAndroid Build Coastguard Worker     /// TODO: support this
setlk(&self) -> io::Result<()>1143*bb4ee6a4SAndroid Build Coastguard Worker     fn setlk(&self) -> io::Result<()> {
1144*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1145*bb4ee6a4SAndroid Build Coastguard Worker     }
1146*bb4ee6a4SAndroid Build Coastguard Worker 
1147*bb4ee6a4SAndroid Build Coastguard Worker     /// TODO: support this
setlkw(&self) -> io::Result<()>1148*bb4ee6a4SAndroid Build Coastguard Worker     fn setlkw(&self) -> io::Result<()> {
1149*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1150*bb4ee6a4SAndroid Build Coastguard Worker     }
1151*bb4ee6a4SAndroid Build Coastguard Worker 
1152*bb4ee6a4SAndroid Build Coastguard Worker     /// TODO: support this
bmap(&self) -> io::Result<()>1153*bb4ee6a4SAndroid Build Coastguard Worker     fn bmap(&self) -> io::Result<()> {
1154*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1155*bb4ee6a4SAndroid Build Coastguard Worker     }
1156*bb4ee6a4SAndroid Build Coastguard Worker 
1157*bb4ee6a4SAndroid Build Coastguard Worker     /// TODO: support this
poll(&self) -> io::Result<()>1158*bb4ee6a4SAndroid Build Coastguard Worker     fn poll(&self) -> io::Result<()> {
1159*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1160*bb4ee6a4SAndroid Build Coastguard Worker     }
1161*bb4ee6a4SAndroid Build Coastguard Worker 
1162*bb4ee6a4SAndroid Build Coastguard Worker     /// TODO: support this
notify_reply(&self) -> io::Result<()>1163*bb4ee6a4SAndroid Build Coastguard Worker     fn notify_reply(&self) -> io::Result<()> {
1164*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1165*bb4ee6a4SAndroid Build Coastguard Worker     }
1166*bb4ee6a4SAndroid Build Coastguard Worker 
1167*bb4ee6a4SAndroid Build Coastguard Worker     /// TODO: support this
lseek(&self) -> io::Result<()>1168*bb4ee6a4SAndroid Build Coastguard Worker     fn lseek(&self) -> io::Result<()> {
1169*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1170*bb4ee6a4SAndroid Build Coastguard Worker     }
1171*bb4ee6a4SAndroid Build Coastguard Worker 
1172*bb4ee6a4SAndroid Build Coastguard Worker     /// Copy a range of data from one file to another
1173*bb4ee6a4SAndroid Build Coastguard Worker     ///
1174*bb4ee6a4SAndroid Build Coastguard Worker     /// Performs an optimized copy between two file descriptors without the additional cost of
1175*bb4ee6a4SAndroid Build Coastguard Worker     /// transferring data through the kernel module to user space (glibc) and then back into
1176*bb4ee6a4SAndroid Build Coastguard Worker     /// the file system again.
1177*bb4ee6a4SAndroid Build Coastguard Worker     ///
1178*bb4ee6a4SAndroid Build Coastguard Worker     /// In case this method is not implemented, glibc falls back to reading data from the source and
1179*bb4ee6a4SAndroid Build Coastguard Worker     /// writing to the destination.
1180*bb4ee6a4SAndroid Build Coastguard Worker     ///
1181*bb4ee6a4SAndroid Build Coastguard Worker     /// If this method fails with an `ENOSYS` error, then the kernel will treat that as a permanent
1182*bb4ee6a4SAndroid Build Coastguard Worker     /// failure. The kernel will return `EOPNOTSUPP` for all future calls to `copy_file_range`
1183*bb4ee6a4SAndroid Build Coastguard Worker     /// without forwarding them to the file system.
1184*bb4ee6a4SAndroid Build Coastguard Worker     ///
1185*bb4ee6a4SAndroid Build Coastguard Worker     /// All values accepted by the `copy_file_range(2)` system call are valid values for `flags` and
1186*bb4ee6a4SAndroid Build Coastguard Worker     /// must be handled by the file system.
copy_file_range( &self, ctx: Context, inode_src: Self::Inode, handle_src: Self::Handle, offset_src: u64, inode_dst: Self::Inode, handle_dst: Self::Handle, offset_dst: u64, length: u64, flags: u64, ) -> io::Result<usize>1187*bb4ee6a4SAndroid Build Coastguard Worker     fn copy_file_range(
1188*bb4ee6a4SAndroid Build Coastguard Worker         &self,
1189*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
1190*bb4ee6a4SAndroid Build Coastguard Worker         inode_src: Self::Inode,
1191*bb4ee6a4SAndroid Build Coastguard Worker         handle_src: Self::Handle,
1192*bb4ee6a4SAndroid Build Coastguard Worker         offset_src: u64,
1193*bb4ee6a4SAndroid Build Coastguard Worker         inode_dst: Self::Inode,
1194*bb4ee6a4SAndroid Build Coastguard Worker         handle_dst: Self::Handle,
1195*bb4ee6a4SAndroid Build Coastguard Worker         offset_dst: u64,
1196*bb4ee6a4SAndroid Build Coastguard Worker         length: u64,
1197*bb4ee6a4SAndroid Build Coastguard Worker         flags: u64,
1198*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<usize> {
1199*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1200*bb4ee6a4SAndroid Build Coastguard Worker     }
1201*bb4ee6a4SAndroid Build Coastguard Worker 
1202*bb4ee6a4SAndroid Build Coastguard Worker     /// Set up memory mappings.
1203*bb4ee6a4SAndroid Build Coastguard Worker     ///
1204*bb4ee6a4SAndroid Build Coastguard Worker     /// Used to set up file mappings in DAX window.
1205*bb4ee6a4SAndroid Build Coastguard Worker     ///
1206*bb4ee6a4SAndroid Build Coastguard Worker     /// # Arguments
1207*bb4ee6a4SAndroid Build Coastguard Worker     ///
1208*bb4ee6a4SAndroid Build Coastguard Worker     /// * `file_offset` - Offset into the file to start the mapping.
1209*bb4ee6a4SAndroid Build Coastguard Worker     /// * `mem_offset` - Offset in Memory Window.
1210*bb4ee6a4SAndroid Build Coastguard Worker     /// * `size` - Length of mapping required.
1211*bb4ee6a4SAndroid Build Coastguard Worker     /// * `flags` - Bit field of `FUSE_SETUPMAPPING_FLAGS_*`.
1212*bb4ee6a4SAndroid Build Coastguard Worker     /// * `mapper` - Mapper object which performs the mapping.
set_up_mapping<M: Mapper>( &self, ctx: Context, inode: Self::Inode, handle: Self::Handle, file_offset: u64, mem_offset: u64, size: usize, flags: u32, mapper: M, ) -> io::Result<()>1213*bb4ee6a4SAndroid Build Coastguard Worker     fn set_up_mapping<M: Mapper>(
1214*bb4ee6a4SAndroid Build Coastguard Worker         &self,
1215*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
1216*bb4ee6a4SAndroid Build Coastguard Worker         inode: Self::Inode,
1217*bb4ee6a4SAndroid Build Coastguard Worker         handle: Self::Handle,
1218*bb4ee6a4SAndroid Build Coastguard Worker         file_offset: u64,
1219*bb4ee6a4SAndroid Build Coastguard Worker         mem_offset: u64,
1220*bb4ee6a4SAndroid Build Coastguard Worker         size: usize,
1221*bb4ee6a4SAndroid Build Coastguard Worker         flags: u32,
1222*bb4ee6a4SAndroid Build Coastguard Worker         mapper: M,
1223*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<()> {
1224*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1225*bb4ee6a4SAndroid Build Coastguard Worker     }
1226*bb4ee6a4SAndroid Build Coastguard Worker 
1227*bb4ee6a4SAndroid Build Coastguard Worker     /// Remove memory mappings.
1228*bb4ee6a4SAndroid Build Coastguard Worker     ///
1229*bb4ee6a4SAndroid Build Coastguard Worker     /// Used to tear down file mappings in DAX window. This method must be supported when
1230*bb4ee6a4SAndroid Build Coastguard Worker     /// `set_up_mapping` is supported.
remove_mapping<M: Mapper>(&self, msgs: &[RemoveMappingOne], mapper: M) -> io::Result<()>1231*bb4ee6a4SAndroid Build Coastguard Worker     fn remove_mapping<M: Mapper>(&self, msgs: &[RemoveMappingOne], mapper: M) -> io::Result<()> {
1232*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1233*bb4ee6a4SAndroid Build Coastguard Worker     }
1234*bb4ee6a4SAndroid Build Coastguard Worker 
1235*bb4ee6a4SAndroid Build Coastguard Worker     /// Lookup and open/create the file
1236*bb4ee6a4SAndroid Build Coastguard Worker     ///
1237*bb4ee6a4SAndroid Build Coastguard Worker     /// In this call, program first do a lookup on the file. Then depending upon
1238*bb4ee6a4SAndroid Build Coastguard Worker     /// flags combination, either do create + open, open only or return error.
1239*bb4ee6a4SAndroid Build Coastguard Worker     /// In all successful cases, it will return the dentry. For return value's
1240*bb4ee6a4SAndroid Build Coastguard Worker     /// handle and open options atomic_open should apply same rules to handle
1241*bb4ee6a4SAndroid Build Coastguard Worker     /// flags and configuration in open/create system call.
1242*bb4ee6a4SAndroid Build Coastguard Worker     ///
1243*bb4ee6a4SAndroid Build Coastguard Worker     /// This function is called when the client supports FUSE_OPEN_ATOMIC.
1244*bb4ee6a4SAndroid Build Coastguard Worker     /// Implementing atomic_open is optional. When the it's not implemented,
1245*bb4ee6a4SAndroid Build Coastguard Worker     /// the client fall back to send lookup and open requests separately.
1246*bb4ee6a4SAndroid Build Coastguard Worker     ///
1247*bb4ee6a4SAndroid Build Coastguard Worker     ///  # Specification
1248*bb4ee6a4SAndroid Build Coastguard Worker     ///
1249*bb4ee6a4SAndroid Build Coastguard Worker     /// If file was indeed newly created (as a result of O_CREAT), then set
1250*bb4ee6a4SAndroid Build Coastguard Worker     /// `FOPEN_FILE_CREATED` bit in `struct OpenOptions open`. This bit is used by
1251*bb4ee6a4SAndroid Build Coastguard Worker     ///  crosvm to inform the fuse client to set `FILE_CREATED` bit in `struct
1252*bb4ee6a4SAndroid Build Coastguard Worker     /// fuse_file_info'.
1253*bb4ee6a4SAndroid Build Coastguard Worker     ///
1254*bb4ee6a4SAndroid Build Coastguard Worker     /// All flags applied to open/create should be handled samely in atomic open,
1255*bb4ee6a4SAndroid Build Coastguard Worker     /// only the following are exceptions:
1256*bb4ee6a4SAndroid Build Coastguard Worker     /// * The O_NOCTTY is filtered out by fuse client.
1257*bb4ee6a4SAndroid Build Coastguard Worker     /// * O_TRUNC is filtered out by VFS for O_CREAT, O_EXCL combination.
1258*bb4ee6a4SAndroid Build Coastguard Worker     ///
1259*bb4ee6a4SAndroid Build Coastguard Worker     /// # Implementation
1260*bb4ee6a4SAndroid Build Coastguard Worker     ///
1261*bb4ee6a4SAndroid Build Coastguard Worker     /// To implement this API, you need to handle the following cases:
1262*bb4ee6a4SAndroid Build Coastguard Worker     ///
1263*bb4ee6a4SAndroid Build Coastguard Worker     /// a) File does not exist
1264*bb4ee6a4SAndroid Build Coastguard Worker     ///  - O_CREAT:
1265*bb4ee6a4SAndroid Build Coastguard Worker     ///    - Create file with specified mode
1266*bb4ee6a4SAndroid Build Coastguard Worker     ///    - Set `FOPEN_FILE_CREATED` bit in `struct OpenOptions open`
1267*bb4ee6a4SAndroid Build Coastguard Worker     ///    - Open the file
1268*bb4ee6a4SAndroid Build Coastguard Worker     ///    - Return d_entry and file handler
1269*bb4ee6a4SAndroid Build Coastguard Worker     ///  - ~O_CREAT:
1270*bb4ee6a4SAndroid Build Coastguard Worker     ///    - ENOENT
1271*bb4ee6a4SAndroid Build Coastguard Worker     ///
1272*bb4ee6a4SAndroid Build Coastguard Worker     /// b) File exist already (exception is O_EXCL)
1273*bb4ee6a4SAndroid Build Coastguard Worker     ///    - O_CREAT:
1274*bb4ee6a4SAndroid Build Coastguard Worker     ///      - Open the file
1275*bb4ee6a4SAndroid Build Coastguard Worker     ///      - Return d_entry and file handler
1276*bb4ee6a4SAndroid Build Coastguard Worker     ///    - O_EXCL:
1277*bb4ee6a4SAndroid Build Coastguard Worker     ///      - EEXIST
1278*bb4ee6a4SAndroid Build Coastguard Worker     ///
1279*bb4ee6a4SAndroid Build Coastguard Worker     /// c) File is symbol link
1280*bb4ee6a4SAndroid Build Coastguard Worker     ///    - Return dentry and file handler
atomic_open( &self, ctx: Context, parent: Self::Inode, name: &CStr, mode: u32, flags: u32, umask: u32, security_ctx: Option<&CStr>, ) -> io::Result<(Entry, Option<Self::Handle>, OpenOptions)>1281*bb4ee6a4SAndroid Build Coastguard Worker     fn atomic_open(
1282*bb4ee6a4SAndroid Build Coastguard Worker         &self,
1283*bb4ee6a4SAndroid Build Coastguard Worker         ctx: Context,
1284*bb4ee6a4SAndroid Build Coastguard Worker         parent: Self::Inode,
1285*bb4ee6a4SAndroid Build Coastguard Worker         name: &CStr,
1286*bb4ee6a4SAndroid Build Coastguard Worker         mode: u32,
1287*bb4ee6a4SAndroid Build Coastguard Worker         flags: u32,
1288*bb4ee6a4SAndroid Build Coastguard Worker         umask: u32,
1289*bb4ee6a4SAndroid Build Coastguard Worker         security_ctx: Option<&CStr>,
1290*bb4ee6a4SAndroid Build Coastguard Worker     ) -> io::Result<(Entry, Option<Self::Handle>, OpenOptions)> {
1291*bb4ee6a4SAndroid Build Coastguard Worker         Err(io::Error::from_raw_os_error(libc::ENOSYS))
1292*bb4ee6a4SAndroid Build Coastguard Worker     }
1293*bb4ee6a4SAndroid Build Coastguard Worker }
1294