diff options
author | Ludovic Courtès <ludo@gnu.org> | 2016-10-28 20:34:15 +0200 |
---|---|---|
committer | Ludovic Courtès <ludo@gnu.org> | 2016-10-28 22:30:17 +0200 |
commit | 12b6c951cf5ca6055a22a2eec85665353f5510e5 (patch) | |
tree | d5350f52cf28075df53819e8912c97c84a86eb12 /nix/libstore/optimise-store.cc | |
parent | b1fd0ab73425e682a0a1404da6963f47a033bb34 (diff) |
daemon: Do not error out when deduplication fails due to ENOSPC.
This solves a problem whereby if /gnu/store/.links had enough entries,
ext4's directory index would be full, leading to link(2) returning
ENOSPC.
* nix/libstore/optimise-store.cc (LocalStore::optimisePath_): Upon
ENOSPC from link(2), print a message and return instead of throwing a
'SysError'.
Diffstat (limited to 'nix/libstore/optimise-store.cc')
-rw-r--r-- | nix/libstore/optimise-store.cc | 23 |
1 files changed, 18 insertions, 5 deletions
diff --git a/nix/libstore/optimise-store.cc b/nix/libstore/optimise-store.cc index d7508b025e..565c62ca83 100644 --- a/nix/libstore/optimise-store.cc +++ b/nix/libstore/optimise-store.cc @@ -148,10 +148,23 @@ void LocalStore::optimisePath_(OptimiseStats & stats, const Path & path, InodeHa inodeHash.insert(st.st_ino); return; } - if (errno != EEXIST) + + switch (errno) { + case EEXIST: + /* Fall through if another process created ‘linkPath’ before + we did. */ + break; + + case ENOSPC: + /* On ext4, that probably means the directory index is full. When + that happens, it's fine to ignore it: we just effectively + disable deduplication of this file. */ + printMsg(lvlInfo, format("cannot link `%1%' to `%2%': %m") % linkPath % path); + return; + + default: throw SysError(format("cannot link `%1%' to `%2%'") % linkPath % path); - /* Fall through if another process created ‘linkPath’ before - we did. */ + } } /* Yes! We've seen a file with the same contents. Replace the @@ -195,8 +208,8 @@ void LocalStore::optimisePath_(OptimiseStats & stats, const Path & path, InodeHa printMsg(lvlInfo, format("`%1%' has maximum number of links") % linkPath); return; } - throw SysError(format("cannot link `%1%' to `%2%'") % tempLink % linkPath); - } + throw SysError(format("cannot link `%1%' to `%2%'") % tempLink % linkPath); + } /* Atomically replace the old file with the new hard link. */ if (rename(tempLink.c_str(), path.c_str()) == -1) { |