SilverFS is the native persistent filesystem built into SilverOS. It is an inode-based, block-device filesystem designed specifically for simplicity and direct integration with the kernel’s ATA driver. Rather than relying on an existing filesystem standard like FAT or ext2, SilverFS provides a minimal but complete feature set: hierarchical directories, file creation and deletion, random-access reads and writes, and persistence across reboots — all stored on a raw ATA disk image (Documentation Index
Fetch the complete documentation index at: https://mintlify.com/pastaboy12345/SilverOS/llms.txt
Use this file to discover all available pages before exploring further.
.svd) passed to QEMU as a virtual hard drive.
On-disk layout
SilverFS divides the disk into fixed-size 4096-byte blocks. The first 22 blocks are reserved for filesystem metadata; all remaining blocks are available as data blocks.| Block(s) | Content |
|---|---|
| 0 | Superblock (silverfs_superblock_t) |
| 1 | Inode bitmap (1024 bits = 128 bytes used, rest zeroed) |
| 2 | Block bitmap (4096 bits = 512 bytes used, rest zeroed) |
| 3–21 | Inode table (1024 inodes × 76 bytes ≈ 19 blocks) |
| 22+ | Data blocks |
SilverFS is persisted on the ATA disk (
build/disk.svd) and survives QEMU reboots as long as disk.svd is not regenerated. Any files written during a session remain intact on the next boot. Regenerating the disk via make disk or make wipes all data.Data structures
The following constants and types are defined ininclude/silverfs.h and describe the complete on-disk and in-memory representation of the filesystem.
SILVERFS_TYPE_FILE is 1 and SILVERFS_TYPE_DIR is 2. New files are created with permissions 0644; new directories with 0755. The indirect_block field in silverfs_inode_t is reserved and never populated by the current kernel implementation.
Filesystem API
All public functions are declared ininclude/silverfs.h and implemented in fs/silverfs.c. Every function that returns int returns 0 on success and -1 on failure unless documented otherwise.
silverfs_format
-1. All formatting must be done on the host using the mkfs_svd tool before booting SilverOS.
silverfs_mount
SILV magic (0x53494C56). If the magic is not found at offset 0, it retries at LBA offset 131072 (a legacy fallback). On success it loads the inode bitmap (Block 1) and block bitmap (Block 2) into kernel RAM and prints the volume name to the serial port. Returns 0 on success, -1 if no valid superblock is found.
silverfs_create
SILVERFS_TYPE_FILE) or directory (SILVERFS_TYPE_DIR) at the given absolute path. The parent directory must already exist. Returns -1 if the path already exists, if the parent is not found, or if no free inodes or blocks are available.
silverfs_open
path to an inode, then sets file->inode_idx to the inode index, file->offset to 0, and file->open to true. Returns 0 on success or -1 if the path does not exist.
silverfs_read
count bytes from the file’s current offset into buf. The read is clipped to the end of the file automatically. Advances file->offset by the number of bytes read. Returns the number of bytes actually read, or -1 if the file handle is not open.
silverfs_write
count bytes from buf into the file at the current offset, allocating new data blocks from the block bitmap as needed. Uses a read-modify-write strategy per block to avoid clobbering data in partially-written blocks. Advances file->offset and updates inode.size on disk after each block write. Returns the number of bytes written, or -1 if the file handle is not open.
silverfs_close
file->open = false. No data is flushed at close time — all writes go directly to disk as they occur.
silverfs_mkdir
path. This is a thin wrapper around silverfs_create(path, SILVERFS_TYPE_DIR). Returns 0 on success or -1 on failure.
silverfs_readdir
path and fills entries with every silverfs_dirent_t whose inode field is non-zero (i.e., is a valid entry). Stops after max_entries entries are collected. Returns the total count of entries found, or -1 if path does not exist or is not a directory.
silverfs_delete
path, clears the inode bitmap bit, zeroes the inode on disk, and removes the corresponding silverfs_dirent_t from the parent directory’s data block. Returns 0 on success or -1 if the path is not found.
silverfs_stat
path to an inode index and copies the full silverfs_inode_t into *inode. Returns 0 on success or -1 if the path does not exist.
Code examples
Write a text file
Read a file back
List a directory
Stat a file
Create a directory tree
Limitations
SilverFS is intentionally minimal. Be aware of the following constraints:- Maximum 1024 inodes (
SILVERFS_MAX_INODES) and 4096 blocks (SILVERFS_MAX_BLOCKS) per volume. - No indirect block support —
indirect_blockinsilverfs_inode_tis reserved but never used. The maximum file size is12 × 4096 = 48 KB. - No runtime timestamps —
created_timeandmodified_timefields exist in the inode structure but are never set or updated by the kernel. They will always read as0. - No hard links —
link_countis always set to1for files and2for directories; there is no mechanism to create additional links. - Absolute paths only — all path arguments passed to any SilverFS function must begin with
/. Relative paths will causeresolve_pathto return-1. - No symbolic links, permissions enforcement, or access-control — the
permissionsfield is stored but never checked by the kernel.