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