123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217 |
- Written by: Neil Brown
- Please see MAINTAINERS file for where to send questions.
- Overlay Filesystem
- ==================
- This document describes a prototype for a new approach to providing
- overlay-filesystem functionality in Linux (sometimes referred to as
- union-filesystems). An overlay-filesystem tries to present a
- filesystem which is the result over overlaying one filesystem on top
- of the other.
- The result will inevitably fail to look exactly like a normal
- filesystem for various technical reasons. The expectation is that
- many use cases will be able to ignore these differences.
- This approach is 'hybrid' because the objects that appear in the
- filesystem do not all appear to belong to that filesystem. In many
- cases an object accessed in the union will be indistinguishable
- from accessing the corresponding object from the original filesystem.
- This is most obvious from the 'st_dev' field returned by stat(2).
- While directories will report an st_dev from the overlay-filesystem,
- all non-directory objects will report an st_dev from the lower or
- upper filesystem that is providing the object. Similarly st_ino will
- only be unique when combined with st_dev, and both of these can change
- over the lifetime of a non-directory object. Many applications and
- tools ignore these values and will not be affected.
- Upper and Lower
- ---------------
- An overlay filesystem combines two filesystems - an 'upper' filesystem
- and a 'lower' filesystem. When a name exists in both filesystems, the
- object in the 'upper' filesystem is visible while the object in the
- 'lower' filesystem is either hidden or, in the case of directories,
- merged with the 'upper' object.
- It would be more correct to refer to an upper and lower 'directory
- tree' rather than 'filesystem' as it is quite possible for both
- directory trees to be in the same filesystem and there is no
- requirement that the root of a filesystem be given for either upper or
- lower.
- The lower filesystem can be any filesystem supported by Linux and does
- not need to be writable. The lower filesystem can even be another
- overlayfs. The upper filesystem will normally be writable and if it
- is it must support the creation of trusted.* extended attributes, and
- must provide valid d_type in readdir responses, so NFS is not suitable.
- A read-only overlay of two read-only filesystems may use any
- filesystem type.
- Directories
- -----------
- Overlaying mainly involves directories. If a given name appears in both
- upper and lower filesystems and refers to a non-directory in either,
- then the lower object is hidden - the name refers only to the upper
- object.
- Where both upper and lower objects are directories, a merged directory
- is formed.
- At mount time, the two directories given as mount options "lowerdir" and
- "upperdir" are combined into a merged directory:
- mount -t overlay overlay -olowerdir=/lower,upperdir=/upper,\
- workdir=/work /merged
- The "workdir" needs to be an empty directory on the same filesystem
- as upperdir.
- Then whenever a lookup is requested in such a merged directory, the
- lookup is performed in each actual directory and the combined result
- is cached in the dentry belonging to the overlay filesystem. If both
- actual lookups find directories, both are stored and a merged
- directory is created, otherwise only one is stored: the upper if it
- exists, else the lower.
- Only the lists of names from directories are merged. Other content
- such as metadata and extended attributes are reported for the upper
- directory only. These attributes of the lower directory are hidden.
- whiteouts and opaque directories
- --------------------------------
- In order to support rm and rmdir without changing the lower
- filesystem, an overlay filesystem needs to record in the upper filesystem
- that files have been removed. This is done using whiteouts and opaque
- directories (non-directories are always opaque).
- A whiteout is created as a character device with 0/0 device number.
- When a whiteout is found in the upper level of a merged directory, any
- matching name in the lower level is ignored, and the whiteout itself
- is also hidden.
- A directory is made opaque by setting the xattr "trusted.overlay.opaque"
- to "y". Where the upper filesystem contains an opaque directory, any
- directory in the lower filesystem with the same name is ignored.
- readdir
- -------
- When a 'readdir' request is made on a merged directory, the upper and
- lower directories are each read and the name lists merged in the
- obvious way (upper is read first, then lower - entries that already
- exist are not re-added). This merged name list is cached in the
- 'struct file' and so remains as long as the file is kept open. If the
- directory is opened and read by two processes at the same time, they
- will each have separate caches. A seekdir to the start of the
- directory (offset 0) followed by a readdir will cause the cache to be
- discarded and rebuilt.
- This means that changes to the merged directory do not appear while a
- directory is being read. This is unlikely to be noticed by many
- programs.
- seek offsets are assigned sequentially when the directories are read.
- Thus if
- - read part of a directory
- - remember an offset, and close the directory
- - re-open the directory some time later
- - seek to the remembered offset
- there may be little correlation between the old and new locations in
- the list of filenames, particularly if anything has changed in the
- directory.
- Readdir on directories that are not merged is simply handled by the
- underlying directory (upper or lower).
- Non-directories
- ---------------
- Objects that are not directories (files, symlinks, device-special
- files etc.) are presented either from the upper or lower filesystem as
- appropriate. When a file in the lower filesystem is accessed in a way
- the requires write-access, such as opening for write access, changing
- some metadata etc., the file is first copied from the lower filesystem
- to the upper filesystem (copy_up). Note that creating a hard-link
- also requires copy_up, though of course creation of a symlink does
- not.
- The copy_up may turn out to be unnecessary, for example if the file is
- opened for read-write but the data is not modified.
- The copy_up process first makes sure that the containing directory
- exists in the upper filesystem - creating it and any parents as
- necessary. It then creates the object with the same metadata (owner,
- mode, mtime, symlink-target etc.) and then if the object is a file, the
- data is copied from the lower to the upper filesystem. Finally any
- extended attributes are copied up.
- Once the copy_up is complete, the overlay filesystem simply
- provides direct access to the newly created file in the upper
- filesystem - future operations on the file are barely noticed by the
- overlay filesystem (though an operation on the name of the file such as
- rename or unlink will of course be noticed and handled).
- Multiple lower layers
- ---------------------
- Multiple lower layers can now be given using the the colon (":") as a
- separator character between the directory names. For example:
- mount -t overlay overlay -olowerdir=/lower1:/lower2:/lower3 /merged
- As the example shows, "upperdir=" and "workdir=" may be omitted. In
- that case the overlay will be read-only.
- The specified lower directories will be stacked beginning from the
- rightmost one and going left. In the above example lower1 will be the
- top, lower2 the middle and lower3 the bottom layer.
- Non-standard behavior
- ---------------------
- The copy_up operation essentially creates a new, identical file and
- moves it over to the old name. The new file may be on a different
- filesystem, so both st_dev and st_ino of the file may change.
- Any open files referring to this inode will access the old data.
- Any file locks (and leases) obtained before copy_up will not apply
- to the copied up file.
- If a file with multiple hard links is copied up, then this will
- "break" the link. Changes will not be propagated to other names
- referring to the same inode.
- Changes to underlying filesystems
- ---------------------------------
- Offline changes, when the overlay is not mounted, are allowed to either
- the upper or the lower trees.
- Changes to the underlying filesystems while part of a mounted overlay
- filesystem are not allowed. If the underlying filesystem is changed,
- the behavior of the overlay is undefined, though it will not result in
- a crash or deadlock.
- Testsuite
- ---------
- There's testsuite developed by David Howells at:
- git://git.infradead.org/users/dhowells/unionmount-testsuite.git
- Run as root:
- # cd unionmount-testsuite
- # ./run --ov
|