async fn open_child_file_helper(
        &mut self,
        child_file_name: OsString,
        oflags: OFlag,
        mode: Mode,
        create_file: bool,
        global_cache: Arc<GlobalCache>,
    ) -> anyhow::Result<Self> {
        let ino = self.get_ino();
        let fd = self.fd;
        let dir_data = self.get_dir_data_mut();
        if create_file {
            debug_assert!(
                !dir_data.contains_key(&child_file_name),
                "open_child_file_helper() cannot create duplicated file name={:?}",
                child_file_name
            );
            debug_assert!(oflags.contains(OFlag::O_CREAT));
        }
        let child_file_name_clone = child_file_name.clone();
        let child_fd = smol::unblock(move || {
            fcntl::openat(fd, child_file_name_clone.as_os_str(), oflags, mode)
        })
        .await
        .context(format!(
            "open_child_file_helper() failed to open a file name={:?} \
                under parent ino={} with oflags={:?} and mode={:?}",
            child_file_name, ino, oflags, mode,
        ))?;

        // get new file attribute
        let child_attr = fs_util::load_attr(child_fd)
            .await
            .context("open_child_file_helper() failed to get the attribute of the new child")?;
        debug_assert_eq!(SFlag::S_IFREG, child_attr.kind);

        if create_file {
            // insert new entry to parent directory
            // TODO: support thread-safe
            let previous_value = dir_data.insert(
                child_file_name.clone(),
                DirEntry::new(child_attr.ino, child_file_name.clone(), SFlag::S_IFREG),
            );
            debug_assert!(previous_value.is_none()); // double check creation race
        }

        let mut full_path = OsString::clone(&self.full_path);
        full_path.push(OsString::clone(&child_file_name));

        Ok(Self::new(
            self.get_ino(),
            child_file_name,
            full_path,
            child_attr,
            NodeData::RegFile(global_cache),
            child_fd,
        ))
    }
/// Helper function to open or create file in a directory
Helper function to open or create file in a directory
Helper function to open or create file in a directory
async fn open_child_file_helper(
        &mut self,
        child_file_name: OsString,
        oflags: OFlag,
        mode: Mode,
        create_file: bool,
        global_cache: Arc<GlobalCache>,
    ) -> anyhow::Result<Self> {
        let ino = self.get_ino();
        let fd = self.fd;
        let dir_data = self.get_dir_data_mut();
        if create_file {
            debug_assert!(
                !dir_data.contains_key(&child_file_name),
                "open_child_file_helper() cannot create duplicated file name={:?}",
                child_file_name
            );
            debug_assert!(oflags.contains(OFlag::O_CREAT));
        }
        let child_file_name_clone = child_file_name.clone();
        let child_fd = smol::unblock(move || {
            fcntl::openat(fd, child_file_name_clone.as_os_str(), oflags, mode)
        })
        .await
        .context(format!(
            "open_child_file_helper() failed to open a file name={:?} \
                under parent ino={} with oflags={:?} and mode={:?}",
            child_file_name, ino, oflags, mode,
        ))?;
        // get new file attribute
        let child_attr = fs_util::load_attr(child_fd)
            .await
            .context("open_child_file_helper() failed to get the attribute of the new child")?;
        debug_assert_eq!(SFlag::S_IFREG, child_attr.kind);
        if create_file {
            // insert new entry to parent directory
            // TODO: support thread-safe
            let previous_value = dir_data.insert(
                child_file_name.clone(),
                DirEntry::new(child_attr.ino, child_file_name.clone(), SFlag::S_IFREG),
            );
            debug_assert!(previous_value.is_none()); // double check creation race
        }
        let mut full_path = OsString::clone(&self.full_path);
        full_path.push(OsString::clone(&child_file_name));
        Ok(Self::new(
            self.get_ino(),
            child_file_name,
            full_path,
            child_attr,
            NodeData::RegFile(global_cache),
            child_fd,
        ))
    }
async fn open_child_file_helper ( & mut self , child_file_name : OsString , oflags : OFlag , mode : Mode , create_file : bool , global_cache : Arc < GlobalCache > , ) -> anyhow :: Result < Self > { let ino = self . get_ino ( ) ; let fd = self . fd ; let dir_data = self . get_dir_data_mut ( ) ; if create_file { debug_assert ! ( dir_data contains_key ( child_file_name ) " " child_file_name ) ; debug_assert ! ( oflags contains ( OFlag O_CREAT ) ) ; } let child_file_name_clone = child_file_name . clone ( ) ; let child_fd = smol :: unblock ( move | | { fcntl :: openat ( fd , child_file_name_clone . as_os_str ( ) , oflags , mode ) } ) . await . context ( format ! ( " \
 " child_file_name ino oflags mode ) ) ? ; // get new file attribute let child_attr = fs_util :: load_attr ( child_fd ) . await . context ( " " ) ? ; debug_assert_eq ! ( SFlag S_IFREG child_attr kind ) ; if create_file { // insert new entry to parent directory // TODO: support thread-safe let previous_value = dir_data . insert ( child_file_name . clone ( ) , DirEntry :: new ( child_attr . ino , child_file_name . clone ( ) , SFlag :: S_IFREG ) , ) ; debug_assert ! ( previous_value is_none ( ) ) ; // double check creation race } let mut full_path = OsString :: clone ( & self . full_path ) ; full_path . push ( OsString :: clone ( & child_file_name ) ) ; Ok ( Self :: new ( self . get_ino ( ) , child_file_name , full_path , child_attr , NodeData :: RegFile ( global_cache ) , child_fd , ) ) }
Helper function to open or create file in a directory
Helper function to open or create file in a directory
&mut self
child_file_name
OsString
oflags
OFlag
mode
Mode
create_file
bool
global_cache
Arc<GlobalCache>
&mut self
child_file_name
OsString
oflags
OFlag
mode
Mode
create_file
bool
global_cache
Arc<GlobalCache>