Open-source project
pellepl/spiffs avatar
pellepl/spiffs

SPIFFS for small SPI NOR flash devices

Wear-leveled SPI flash file system for embedded devices

1,632 stars419 forksCMIT

At a glance

What is it?
SPIFFS is a C file system for SPI NOR flash on embedded targets with limited RAM. It uses static buffers and wear leveling, but its flat namespace, poor scalability, and lack of bad-block handling make it a targeted choice rather than a general-purpose storage layer.
Who is it for?
Adopt SPIFFS when an embedded target has sparse RAM, erasable NOR flash, small files, and a need for multiple independently configured file systems. Do not choose it for large flash capacities, realtime write timing, directory trees, bad-block management, or a generic binary that can mount every device.
Can I use it commercially?
Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 99 days ago.
What is it written in?
Mainly C, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on October 22, 2026, and from our analysis. They are not legal advice.

Editorial analysis

Why SPIFFS targets embedded SPI NOR flash

SPIFFS solves a storage problem that is specific to small embedded devices: providing files on SPI NOR flash without requiring a large RAM-based cache or a conventional block device with uniform overwrite semantics. The README says the project is intended for SPI NOR flash on embedded targets, especially devices with sparse RAM and no heap. Its design assumes that data is written in large eraseable areas called blocks. Erasing resets the bits in a block to ones, while writing changes selected bits from one to zero. Existing zero bits cannot be restored without erasing the block.

That write model matters because files cannot simply be rewritten in place. SPIFFS uses the properties of NOR flash to store files in a form compatible with small memory budgets, and the feature list includes static wear leveling. The intended users are firmware developers who need persistent configuration, calibration, logging, or application data on a microcontroller rather than developers looking for a desktop filesystem. The project is also relevant when one device contains several storage areas that need separate SPIFFS configurations, including configurations placed on the same SPI flash device.

The API is described as POSIX-like, with operations such as open, close, read, write, seek, and stat. That wording should be read carefully. SPIFFS provides familiar file operations, but it does not reproduce the full behavior of a Unix filesystem. In particular, its namespace is flat, and operation timing is not suitable for workloads that require predictable realtime write completion.

SPIFFS data layout, buffers, and wear leveling

SPIFFS is designed around statically sized RAM buffers whose size does not depend on the number of files. The README lists several configuration options, including optional index mapping, a temporal file descriptor cache, and additional file metadata. These are build-time choices rather than a generic runtime binary. One configuration produces one binary, so a deployment must be compiled for the storage geometry and feature set it needs.

The technical specification is the appropriate source for the detailed internal format, while the feature list gives the architectural summary visible here. Files and filesystem metadata are managed through flash operations that respect the one-way bit transition described in the introduction. Static wear leveling is included because embedded flash storage has a finite erase cycle life. Removing or replacing a file can therefore require additional flash activity, and operation duration can vary with the state of the storage.

The API also exposes optional mechanisms intended to improve access to index metadata. Version 0.3.6 introduced `SPIFFS_ix_map`, `SPIFFS_ix_unmap`, and `SPIFFS_ix_remap`, together with conversion helpers for calculating the memory required for mapped entries. Version 0.3.7 added `SPIFFS_update_meta` and `SPIFFS_fupdate_meta` for file metadata updates. These additions indicate that file indexing and metadata are separate concerns that can be tuned, but the README does not provide enough implementation detail to claim a particular performance gain for any target.

Building SPIFFS and running the host check

The README documents a basic host build from the repository. The following command creates the default build directory and invokes `make`:

bash
mkdir build; make

The README says the default output directory is `build`, controlled by the `builddir` variable near the top of `makefile`. If a project needs another directory, that variable is the documented configuration point. The build instructions do not specify a compiler version, generated library name, or platform-specific environment setup, so those details must come from the target integration documentation rather than being inferred from this command.

For a host-side sanity check, the repository documents `make test`. This is described as a sanity check, not as a guarantee that a target's flash driver, interrupt timing, or power-loss behavior is correct.

bash
make test

The `.travis.yml` file is identified as the reference for the official in-depth testing procedure. For an actual embedded product, the next step would be to follow the project wiki's integration guidance. The README also points to `spiffsimg` in the `nodemcu` firmware repository as an example integration.

Using SPIFFS on an embedded target

The repository provides the file system implementation and its API, but it does not include a complete, universal target program in the README. Integration therefore starts with the project wiki's `Integrate spiffs` and `Configure spiffs` guidance. A target must provide access to the underlying flash and select the configuration appropriate for the storage layout. The README specifically says that the project is not a generic SPIFFS binary for all types of configurations.

A first embedded use would normally involve compiling SPIFFS into the firmware, providing the platform's flash access layer, mounting the file system, and then using the documented operations such as `open`, `close`, `read`, and `write`. The README does not give a complete application example with exact port names, callback signatures, or initialization arguments, so those values should be copied from the selected integration guide and the repository headers rather than guessed. The README confirms the operation names and integration references, but not a runnable target-specific sequence.

The flat namespace is visible even in a basic filename example. Passing `tmp/myfile.txt` does not create a `tmp` directory. SPIFFS treats the complete string as the file name. This is a deliberate consequence of the current feature set, and applications must flatten their paths before passing them to SPIFFS.

Limits of the current SPIFFS design

SPIFFS has several boundaries that can make it the wrong tool even when a device uses SPI NOR flash. First, it does not support directories. Its flat structure simplifies the implementation and reduces metadata requirements, but an application that needs a hierarchy must maintain its own namespace mapping. Second, write latency is variable. The README explicitly states that one write operation might take much longer than another, so a caller cannot assume a write completes within a fixed time budget.

Third, scalability is poor. The README advises against capacities beyond approximately 128 Mbyte, because the design prioritizes low RAM use. Fourth, SPIFFS does not detect or handle bad blocks. A design that depends on replacement of defective erase regions needs another layer or a different storage strategy. Finally, SPIFFS is not a realtime stack, and it does not provide one universal configuration.

There is also a versioning constraint. The README says version 0.4.0 is under construction as a full rewrite with a changed underlying structure. It will not be compatible with earlier filesystem versions, although the API is expected to remain similar with minor modifications. Some configuration flags may be removed and some features may be absent until 0.4.1. This makes filesystem image compatibility and upgrade planning part of product evaluation, not merely a software version detail.

License, maintenance, and upgrade implications

The repository identifies `MIT` as the license. The README summarizes the permission in informal language, including use, modification, sale, and printing, while directing readers to `LICENSE` for the legal terms. This review does not provide legal advice. The practical implication for engineering review is that the project has a permissive license, but integrators should read the actual license file and account for their own dependencies and hardware obligations.

The repository is not archived, and its last push was on 2026-07-16. The recent release list still ends at 0.3.7, dated 2017-07-17, so the release history does not establish a sequence of new packaged releases after that point. The README's separate notice that 0.4.0 is under construction describes the direction of the next version, not a shipped release.

Upgrading from an existing SPIFFS image requires special attention. The README warns that 0.4.0 changes the underlying structure and is not compatible with earlier versions. An embedded product should therefore determine whether its stored data must be migrated, recreated, or retained through an explicit compatibility process. The README does not document rollback procedures for the 0.4.0 rewrite, so that behavior should not be assumed.

Editorial conclusion

Adopt SPIFFS when an embedded target has sparse RAM, erasable NOR flash, small files, and a need for multiple independently configured file systems. Do not choose it for large flash capacities, realtime write timing, directory trees, bad-block management, or a generic binary that can mount every device. Before integration, verify the target flash erase and write behavior, choose the required configuration constants, and review the project's migration note because version 0.4.0 is described as an incompatible rewrite under construction.

Frequently asked questions

What kind of storage does SPIFFS support?

SPIFFS is intended for SPI NOR flash on embedded targets. The README says it can theoretically run on other embedded flash that follows the same erase and bit-transition characteristics.

Does SPIFFS support directories?

No. SPIFFS uses a flat namespace, so `tmp/myfile.txt` is treated as a file name rather than a file inside a `tmp` directory.

Can SPIFFS handle large SPI flash devices?

The README warns that scalability is poor and says going beyond approximately 128 Mbyte is probably a bad idea. It recommends keeping SPIFFS within the small-memory-device range for which it was designed.

What is the documented way to build SPIFFS?

The README gives `mkdir build; make` as the basic build command and `make test` as a host sanity check. It also directs users to the wiki for integration and configuration details.

Is SPIFFS 0.4.0 compatible with 0.3.x file systems?

No. The README says 0.4.0 is a full rewrite with a changed underlying structure and will not be compatible with earlier versions of the filesystem.

Official sources

  1. Issues
  2. License: MIT
  3. pellepl/spiffs on GitHub
  4. README
  5. Releases
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/pellepl-spiffs.svg)](https://hysenlabs.com/projects/pellepl-spiffs)

Was this useful?