Skip to content
πŸ”₯ a versioning filesystem inspired by git
Branch: master
Clone or download
artagnon [LICENSE] Modernize; MIT
Signed-off-by: Ramkumar Ramachandra <artagnon@gmail.com>
Latest commit 6ea03d9 May 1, 2019
Permalink
Type Name Latest commit message Commit time
Failed to load latest commit information.
block-sha1 block-sha1: Import SHA1 library from git.git Mar 21, 2011
t test-sha1: fix segfault Jul 9, 2013
xdiff Add xdiff library Mar 21, 2011
.gitignore Change project name to phoenixfs Mar 22, 2011
LICENSE [LICENSE] Modernize; MIT May 1, 2019
Makefile Makefile; add test target pointing to t Jul 9, 2013
README.md [README] Modernize md style Jun 15, 2018
btree.c btree: resurrect print_btree() Jul 9, 2013
btree.h btree: change BTREE_ORDER to 3 Aug 29, 2012
buffer.c buffer: Write small library for buffered IO Mar 21, 2011
buffer.h Makefile: Scrub both Makefiles clean Mar 21, 2011
common.c Implement subcommand `diff` and refactor heavily Mar 21, 2011
common.h Change project name to phoenixfs Mar 22, 2011
compress.c Makefile: Scrub both Makefiles clean Mar 21, 2011
compress.h compress: Write a test-compress and deflate old revisions Mar 21, 2011
crc32.c crc32: Import from Linux source tree Mar 21, 2011
crc32.h crc32: Import from Linux source tree Mar 21, 2011
delta.c delta: Import deltification algorithm from git.git Mar 21, 2011
delta.h delta: Import deltification algorithm from git.git Mar 21, 2011
diff.c Squelch some compiler warnings Aug 24, 2012
diff.h Update remaining references to "gitfs" Mar 31, 2012
fstree.c btree: resurrect print_btree() Jul 9, 2013
fstree.h fstree: re-create frs on startup Aug 28, 2012
fuse.c fuse: thread-lock read, write, and release Sep 21, 2012
fuse.h Update remaining references to "gitfs" Mar 31, 2012
loose.c loose: zero-length pointer arrays are illegal Sep 17, 2012
loose.h loose: zero-length pointer arrays are illegal Sep 17, 2012
main.c Squelch some compiler warnings Aug 24, 2012
main.h Change project name to phoenixfs Mar 22, 2011
pack.c loose: zero-length pointer arrays are illegal Sep 17, 2012
pack.h Squelch some compiler warnings Aug 24, 2012
persist.c persist: destroy B+ tree after dumping Sep 17, 2012
persist.h persist: Introduce a persistence layer above fstree Mar 21, 2011
sha1.c sha1: rewrite print_sha1 Sep 17, 2012
sha1.h Squelch some compiler warnings Aug 24, 2012

README.md

phoenixfs

A filesystem implemented in userspace (using FUSE), inspired by the way Git is designed. Only works on Linux, since macOS implements userspace filesystems differently. Seamlessly versions files on save, without any additional machinery: traps save events in the editor, and writes out to a mount point, in the form of loose objects.

Dependencies

  1. Zlib (>= 1.2)
  2. FUSE (>= 2.6)
  3. pkg-config (>= 0.25)
  4. Linux kernel (>= 2.6.15)

Usage

For the first run, you need two directories:

  1. A git directory where the data will be stored.
  2. An empty directory to use as the mountpoint.
 $ cd /tmp
 $ mkdir gitdir mountp
 $ phoneixfs mount gitdir mountp

Use the mountpoint as you see fit. Data will be written to the gitdir on umount: you can use it for subsequent mounts.

Now, everything in mountpoint is versioned. To access older revisions of FILE, use FILE@REV syntax, where REV is the number of revisions in the past you want to access. For example:

 $ echo "hello" >file1
 $ echo "goodbye" >file1
 $ echo "another hello" >file1
 $ cat file1
 another hello
 $ cat file1@1
 goodbye
 $ cat file1@2
 hello

Finally, to umount:

 $ fusermount -u mountp

Technical documentation

Uses a B+ tree to keep track of the filesystem tree, and a modified version of packfile v3/ packfile index v2 for storing revision information.

  • gitdir/.git/loose/ contains zlib-deflated versions of content blobs, named by the SHA-1 digest of the content.

  • gitdir/fstree is a raw dump of the B+ tree in a custom format.

  • gitdir/master.pack and gitdir/master.idx are the packfile and packfile index respectively. During an unmount, the files in gitdir/.git/loose/ are packed up, and an index is generated.

  • /tmp/phoenixfs.log is the debug log

master.idx, master.pack, and fstree are enough to recreate the entire versioned filesystem. The files in gitdir/ and gitdir/.git/loose/ can be removed after unmount.

Notes on the filesystem tree:

(dr: directory record | fr: file record | vfr: versioned file record)

  • dr just contains a name and node pointer referencing vfrs. drs are inserted directly into the root node.

  • vfr contains the path of the file, a list of frs representing the various versions of the file (fixed at REV_TRUNCATE), and a HEAD pointer to keep track of the latest version of the file.

  • The B+ tree is keyed by the CRC32 hash of the path of the vfr/ dr, a design decision inspired by Btrfs.

  • An fr, vfr, and dr (corresponding to its path) are created when a new file is created on the filesystem. Empty directories are not tracked: no dr is created for empty directories.

Limitations

The following invocations don't work:

 $ cp file1@1 file1 # FILE@REV can't be treated like a file

Contributing

Simply fork the project on GitHub and send pull requests.

You can’t perform that action at this time.