1 unstable release
0.1.0 | Jan 27, 2024 |
---|
#27 in #embassy
2.5MB
23K
SLoC
fatfs-embedded
Rust bindings for the popular embedded FatFs library from elm-chan.org. Full documentation is available on docs.rs.
lib.rs
:
FatFs is a generic FAT/exFAT filesystem module designed for small embedded systems.
fatfs-embedded
is a Rust wrapper of the popular FatFs library from
elm-chan.org.
It is based on the R0.15 release.
Goals
- Embedded use - This library is
no_std
by default, but isstd
compatible for testing purposes when targeting an OS. - Thread safe - The choice was made to have a dependency on the Embassy
framework for concurrency support which is suitable for embedded systems. A global
file system mutex is implemented in favor of the
FF_FS_REENTRANT
option, which is more suitable to a Rust implementation. - Portable - Implement the
FatFsDriver
trait to add support for any block device. To support this implementation,alloc
support is unfortunately required due to the structure of FatFs. A simulated block storage driver implementation is included for test purposes that may be used for reference.
Drop
The decision was made not to implement the Drop
trait for files or directories.
This is because doing so would require acquiring a lock on the file system object,
which can easily cause a lockup condition.
Files and directories must be manually closed. (The file system object itself is
implemented as a static singleton and thus is never dropped.)
FatFs Configuration
Most features of FatFs are enabled with a few exceptions:
FF_USE_FORWARD
is disabled to avoid using additionalunsafe
code.FF_CODE_PAGE
is set to 0 and thus must be set via a call tosetcp()
.FF_VOLUMES
is currently set to 1 limiting the number of volumes supported to 1.FF_MULTI_PARTITION
is not currently supported.FF_FS_LOCK
is configured to support 10 simultaneous open files.- An implementation of the
f_printf()
function is not provided.
Features
chrono
(default) - Enables time support in the library. Access to an RTC may be provided via an implementation of theFatFsDriver
trait.
Examples
A brief example that formats and mounts a simulated drive, writes a string to a file, then reads the data back:
#[path = "../tests/simulated_driver.rs"]
mod simulated_driver;
use fatfs_embedded::fatfs::{self, File, FileOptions, FormatOptions};
use embassy_futures::block_on;
const TEST_STRING: &[u8] = b"Hello world!";
//Install a block device driver that implements `FatFsDriver`
let driver = simulated_driver::RamBlockStorage::new();
block_on(fatfs::diskio::install(driver));
//Acquire a lock on the file system.
let mut locked_fs = block_on(fatfs::FS.lock());
//Format the drive.
locked_fs.mkfs("", FormatOptions::FAT32, 0, 0, 0, 0);
//Mount the drive.
locked_fs.mount();
//Create a new file.
let mut test_file: File = locked_fs.open("test.txt",
FileOptions::CreateAlways |
FileOptions::Read |
FileOptions::Write).unwrap();
//Write a string to the file.
locked_fs.write(&mut test_file, TEST_STRING);
//Seek back to the beginning of the file.
locked_fs.seek(&mut test_file, 0);
//Read the string back from the file.
let mut read_back: [u8; TEST_STRING.len()] = [0; TEST_STRING.len()];
locked_fs.read(&mut test_file, &mut read_back);
assert_eq!(TEST_STRING, read_back);
//Close the file when done.
locked_fs.close(&mut test_file);
Dependencies
~2.3–5MB
~92K SLoC