pub struct MfsFilesystem<R: Read + Seek + Send> { /* private fields */ }Expand description
Live MFS reader. Holds the parsed MDB, the volume bitmap, and a re-decoded directory cache (small — at most a few hundred entries on a 400 KB floppy).
Implementations§
Source§impl<R: Read + Seek + Send> MfsFilesystem<R>
impl<R: Read + Seek + Send> MfsFilesystem<R>
Sourcepub fn open(reader: R, partition_offset: u64) -> Result<Self, FilesystemError>
pub fn open(reader: R, partition_offset: u64) -> Result<Self, FilesystemError>
Open an MFS volume at the given partition offset.
Sourcepub fn read_resource_fork(
&mut self,
entry: &FileEntry,
) -> Result<Vec<u8>, FilesystemError>
pub fn read_resource_fork( &mut self, entry: &FileEntry, ) -> Result<Vec<u8>, FilesystemError>
Read the resource fork of a directory entry. Returns an empty Vec
if the file has no resource fork. Surfaced as a side channel
because the trait’s read_file only exposes the data fork; classic
Mac apps often live in the resource fork and consumers (e.g. the
mac_archive exporter) need access.
Trait Implementations§
Source§impl<R: Read + Write + Seek + Send> EditableFilesystem for MfsFilesystem<R>
impl<R: Read + Write + Seek + Send> EditableFilesystem for MfsFilesystem<R>
Source§fn write_resource_fork(
&mut self,
entry: &FileEntry,
data: &mut dyn Read,
len: u64,
) -> Result<(), FilesystemError>
fn write_resource_fork( &mut self, entry: &FileEntry, data: &mut dyn Read, len: u64, ) -> Result<(), FilesystemError>
Replace a file’s resource fork (used by setrsrc, the batch archive
importer, and fork-carrying cp). Frees the old resource chain, then
allocates + writes the new one and updates the directory entry. Call
sync_metadata to persist. Freeing before allocating means a replacement
only needs the delta in free space, not room for both copies.
Source§fn as_filesystem(&self) -> &dyn Filesystem
fn as_filesystem(&self) -> &dyn Filesystem
Filesystem trait object. Read moreSource§fn as_filesystem_mut(&mut self) -> &mut dyn Filesystem
fn as_filesystem_mut(&mut self) -> &mut dyn Filesystem
as_filesystem.Source§fn create_file(
&mut self,
parent: &FileEntry,
name: &str,
data: &mut dyn Read,
data_len: u64,
options: &CreateFileOptions,
) -> Result<FileEntry, FilesystemError>
fn create_file( &mut self, parent: &FileEntry, name: &str, data: &mut dyn Read, data_len: u64, options: &CreateFileOptions, ) -> Result<FileEntry, FilesystemError>
Source§fn create_directory(
&mut self,
_parent: &FileEntry,
_name: &str,
_options: &CreateDirectoryOptions,
) -> Result<FileEntry, FilesystemError>
fn create_directory( &mut self, _parent: &FileEntry, _name: &str, _options: &CreateDirectoryOptions, ) -> Result<FileEntry, FilesystemError>
Source§fn delete_entry(
&mut self,
parent: &FileEntry,
entry: &FileEntry,
) -> Result<(), FilesystemError>
fn delete_entry( &mut self, parent: &FileEntry, entry: &FileEntry, ) -> Result<(), FilesystemError>
Source§fn sync_metadata(&mut self) -> Result<(), FilesystemError>
fn sync_metadata(&mut self) -> Result<(), FilesystemError>
Source§fn free_space(&mut self) -> Result<u64, FilesystemError>
fn free_space(&mut self) -> Result<u64, FilesystemError>
Source§fn repair(&mut self) -> Result<RepairReport, FilesystemError>
fn repair(&mut self) -> Result<RepairReport, FilesystemError>
Source§fn set_type_creator(
&mut self,
entry: &FileEntry,
type_code: &str,
creator_code: &str,
) -> Result<(), FilesystemError>
fn set_type_creator( &mut self, entry: &FileEntry, type_code: &str, creator_code: &str, ) -> Result<(), FilesystemError>
Unsupported so callers can branch on capability
rather than relying on silent no-ops.Source§fn rename(
&mut self,
parent: &FileEntry,
entry: &FileEntry,
new_name: &str,
) -> Result<(), FilesystemError>
fn rename( &mut self, parent: &FileEntry, entry: &FileEntry, new_name: &str, ) -> Result<(), FilesystemError>
new_name must validate via Filesystem::validate_name and
must not already name another entry in parent. Read moreSource§fn begin_bulk(&mut self)
fn begin_bulk(&mut self)
create_file), that bookkeeping dominates a large import. Read moreSource§fn end_bulk(&mut self)
fn end_bulk(&mut self)
begin_bulk). Default
is a no-op.Source§fn delete_recursive(
&mut self,
parent: &FileEntry,
entry: &FileEntry,
) -> Result<(), FilesystemError>
fn delete_recursive( &mut self, parent: &FileEntry, entry: &FileEntry, ) -> Result<(), FilesystemError>
Source§fn set_permissions(
&mut self,
_entry: &FileEntry,
_mode: u32,
) -> Result<(), FilesystemError>
fn set_permissions( &mut self, _entry: &FileEntry, _mode: u32, ) -> Result<(), FilesystemError>
mode carries permission bits
only — implementations keep the inode’s file-type bits (see
[crate::fs::unix_common::inode::with_permission_bits]). Read moreSource§fn set_owner(
&mut self,
_entry: &FileEntry,
_uid: u32,
_gid: u32,
) -> Result<(), FilesystemError>
fn set_owner( &mut self, _entry: &FileEntry, _uid: u32, _gid: u32, ) -> Result<(), FilesystemError>
Source§fn set_xattr(
&mut self,
_entry: &FileEntry,
_name: &str,
_value: &[u8],
) -> Result<(), FilesystemError>
fn set_xattr( &mut self, _entry: &FileEntry, _name: &str, _value: &[u8], ) -> Result<(), FilesystemError>
Unsupported. name must carry a valid namespace prefix
([crate::fs::xattr::has_valid_namespace]).Source§fn remove_xattr(
&mut self,
_entry: &FileEntry,
_name: &str,
) -> Result<(), FilesystemError>
fn remove_xattr( &mut self, _entry: &FileEntry, _name: &str, ) -> Result<(), FilesystemError>
Unsupported. Removing an absent attribute is
not an error.Source§fn set_prodos_type(
&mut self,
_entry: &FileEntry,
_type_byte: u8,
_aux_type: u16,
) -> Result<(), FilesystemError>
fn set_prodos_type( &mut self, _entry: &FileEntry, _type_byte: u8, _aux_type: u16, ) -> Result<(), FilesystemError>
Unsupported — override on ProDOS.Source§fn set_prodos_access(
&mut self,
_entry: &FileEntry,
_access: u8,
) -> Result<(), FilesystemError>
fn set_prodos_access( &mut self, _entry: &FileEntry, _access: u8, ) -> Result<(), FilesystemError>
Source§fn set_blessed_folder(
&mut self,
_entry: &FileEntry,
) -> Result<(), FilesystemError>
fn set_blessed_folder( &mut self, _entry: &FileEntry, ) -> Result<(), FilesystemError>
Unsupported so the GUI can
gate the action and surface unexpected calls.Source§fn write_boot_blocks(
&mut self,
_blocks: &[u8; 1024],
) -> Result<(), FilesystemError>
fn write_boot_blocks( &mut self, _blocks: &[u8; 1024], ) -> Result<(), FilesystemError>
sync_metadata time. Used to make a
classic-HFS volume bootable by copying a donor’s boot blocks. Override
on HFS/HFS+ (the only filesystems with a Mac boot region); others
return Unsupported so the GUI can gate the action.Source§fn set_volume_name(&mut self, _new_name: &str) -> Result<(), FilesystemError>
fn set_volume_name(&mut self, _new_name: &str) -> Result<(), FilesystemError>
Unsupported).Source§fn set_finder_info(
&mut self,
_entry: &FileEntry,
_finfo: [u8; 16],
_fxinfo: [u8; 16],
) -> Result<(), FilesystemError>
fn set_finder_info( &mut self, _entry: &FileEntry, _finfo: [u8; 16], _fxinfo: [u8; 16], ) -> Result<(), FilesystemError>
Unsupported. Used
by the MacBinary put path to apply Finder flags / location / folder
in one shot.Source§fn set_amiga_protection(
&mut self,
_entry: &FileEntry,
_protection: u32,
) -> Result<(), FilesystemError>
fn set_amiga_protection( &mut self, _entry: &FileEntry, _protection: u32, ) -> Result<(), FilesystemError>
Unsupported.
Set the DOS attribute bits on an entry: read-only 0x01, hidden 0x02,
system 0x04, archive 0x20. Read morefn set_dos_attributes( &mut self, _parent: &FileEntry, _entry: &FileEntry, _attrs: u16, ) -> Result<(), FilesystemError>
fn set_dates( &mut self, _entry: &FileEntry, _create: u32, _modify: u32, _backup: u32, ) -> Result<(), FilesystemError>
Source§fn supports_symlinks(&self) -> bool
fn supports_symlinks(&self) -> bool
Self::create_symlink is actually implemented). Default false;
override to true alongside create_symlink. Lets callers (e.g. the
tar-import preflight) warn before a lossy import that symlinks will
be dropped, rather than discovering it entry-by-entry.Source§fn stores_raw_names(&self) -> bool
fn stores_raw_names(&self) -> bool
crate::fs::raw_name] placeholders.
Only NeXT UFS volumes say yes; everywhere else a placeholder would land as junk.Source§fn create_symlink(
&mut self,
_parent: &FileEntry,
_name: &str,
_target: &str,
_options: &CreateFileOptions,
) -> Result<FileEntry, FilesystemError>
fn create_symlink( &mut self, _parent: &FileEntry, _name: &str, _target: &str, _options: &CreateFileOptions, ) -> Result<FileEntry, FilesystemError>
parent pointing at target (a path
string interpreted by the filesystem’s own resolver semantics).
Returns the new symlink’s entry. Default returns Unsupported —
override on filesystems that support symlinks (PFS3, AFFS,
ext, etc).Source§fn create_hardlink(
&mut self,
_parent: &FileEntry,
_name: &str,
_target: &FileEntry,
_options: &CreateFileOptions,
) -> Result<FileEntry, FilesystemError>
fn create_hardlink( &mut self, _parent: &FileEntry, _name: &str, _target: &FileEntry, _options: &CreateFileOptions, ) -> Result<FileEntry, FilesystemError>
parent pointing at an existing entry
already on this filesystem. target must be an entry returned
by a previous create_file / create_directory / list_directory
call on this same volume — its location identifies the inode /
anode / CNID that the new link references. Returns the new
hardlink’s entry. Default returns Unsupported — override on
filesystems that support hardlinks (PFS3, HFS+, ext, etc).Source§impl<R: Read + Seek + Send> Filesystem for MfsFilesystem<R>
impl<R: Read + Seek + Send> Filesystem for MfsFilesystem<R>
Source§fn allocation_unit(&self) -> Option<u64>
fn allocation_unit(&self) -> Option<u64>
MFS allocates fork storage in fixed-size allocation blocks
(drAlBlkSiz), so a fork’s real on-disk footprint is its length
rounded up to this unit. Exposing it lets the copy preflight and
du model destination consumption exactly instead of falling back
to a 512-byte floor.
Source§fn write_resource_fork_to(
&mut self,
entry: &FileEntry,
writer: &mut dyn Write,
) -> Result<u64, FilesystemError>
fn write_resource_fork_to( &mut self, entry: &FileEntry, writer: &mut dyn Write, ) -> Result<u64, FilesystemError>
Stream a file’s resource fork. MFS files carry a data + resource fork
like HFS; consumers (get-binhex, MacBinary / AppleDouble export, cp,
the remote daemon) reach it only through this trait method, so it must
bridge to the inherent read_resource_fork
(which follows the resource fork’s own allocation-block chain).
Source§fn list_directory(
&mut self,
entry: &FileEntry,
) -> Result<Vec<FileEntry>, FilesystemError>
fn list_directory( &mut self, entry: &FileEntry, ) -> Result<Vec<FileEntry>, FilesystemError>
Source§fn read_file(
&mut self,
entry: &FileEntry,
max_bytes: usize,
) -> Result<Vec<u8>, FilesystemError>
fn read_file( &mut self, entry: &FileEntry, max_bytes: usize, ) -> Result<Vec<u8>, FilesystemError>
max_bytes).Source§fn validate_name(&self, name: &str) -> Result<(), FilesystemError>
fn validate_name(&self, name: &str) -> Result<(), FilesystemError>
name is legal for a new file or directory on this
filesystem. Returns Err(InvalidData) with a human-readable reason
when the name violates length, character, or encoding rules. Read moreSource§fn volume_label(&self) -> Option<&str>
fn volume_label(&self) -> Option<&str>
Source§fn total_size(&self) -> u64
fn total_size(&self) -> u64
Source§fn resource_fork_size(&mut self, entry: &FileEntry) -> u64
fn resource_fork_size(&mut self, entry: &FileEntry) -> u64
0.Source§fn fsck(&mut self) -> Option<Result<FsckResult, FilesystemError>>
fn fsck(&mut self) -> Option<Result<FsckResult, FilesystemError>>
None if not supported for
this filesystem type. Override in implementations that support fsck.Source§fn last_data_byte(&mut self) -> Result<u64, FilesystemError>
fn last_data_byte(&mut self) -> Result<u64, FilesystemError>
Source§fn defragmented_minimum_size(&mut self) -> Result<u64, FilesystemError>
fn defragmented_minimum_size(&mut self) -> Result<u64, FilesystemError>
Source§fn fragmentation_stats(
&mut self,
) -> Option<Result<FragmentationStats, FilesystemError>>
fn fragmentation_stats( &mut self, ) -> Option<Result<FragmentationStats, FilesystemError>>
None
when the filesystem can’t compute them (e.g. cluster-allocation
filesystems whose CompactReader already repacks during the backup
stream so “fragmentation” doesn’t translate into a backup-time
decision the user can make). Read moreSource§fn write_file_to(
&mut self,
entry: &FileEntry,
writer: &mut dyn Write,
) -> Result<u64, FilesystemError>
fn write_file_to( &mut self, entry: &FileEntry, writer: &mut dyn Write, ) -> Result<u64, FilesystemError>
Source§fn blessed_system_folder(&mut self) -> Option<(u64, String)>
fn blessed_system_folder(&mut self) -> Option<(u64, String)>
Source§fn set_show_deleted(&mut self, _on: bool) -> bool
fn set_show_deleted(&mut self, _on: bool) -> bool
false when unsupported.Source§fn journal_detail(
&mut self,
) -> Result<Option<Box<dyn Any + Send>>, FilesystemError>
fn journal_detail( &mut self, ) -> Result<Option<Box<dyn Any + Send>>, FilesystemError>
Ok(None) if unjournaled.
The value is the filesystem’s own detail type (HFS+: JournalDetail), for the caller to downcast.Source§fn uses_colon_paths(&self) -> bool
fn uses_colon_paths(&self) -> bool
: as its native path separator
(classic Mac HFS / HFS+), so : can never appear in a catalog name. Read moreSource§fn case_insensitive_lookup(&self) -> bool
fn case_insensitive_lookup(&self) -> bool
Source§fn supports_xattrs(&self) -> bool
fn supports_xattrs(&self) -> bool
user.*,
security.*, …). True on ext / XFS / SquashFS; false on filesystems with
no xattr concept (Minix, EFS, FAT, HFS). The UI uses this to show or hide
the xattr section rather than probing every file.Source§fn list_xattrs(
&mut self,
_entry: &FileEntry,
) -> Result<Vec<Xattr>, FilesystemError>
fn list_xattrs( &mut self, _entry: &FileEntry, ) -> Result<Vec<Xattr>, FilesystemError>
entry. Default: none. Override on
xattr-bearing filesystems. Returning an empty list is normal — most files
carry no xattrs even where the filesystem supports them.