forked from lix-project/lix
Artemis Tosini
3058029fba
bindPath/doBind is a useful function in build that is used in several
parts of LocalDerivationGoal. Moving this function makes it easier to
split LocalDerivationGoal implementation between several files.
Change-Id: Ic5a0768479c153c1aa3ed425f12604b20bbf0f42
44 lines
1.1 KiB
C++
44 lines
1.1 KiB
C++
#include "mount.hh"
|
|
#include "error.hh"
|
|
#include "file-system.hh"
|
|
#include "logging.hh"
|
|
#if __linux__
|
|
#include <sys/mount.h>
|
|
|
|
namespace nix {
|
|
|
|
void bindPath(const Path & source, const Path & target, bool optional) {
|
|
debug("bind mounting '%1%' to '%2%'", source, target);
|
|
|
|
auto bindMount = [&]() {
|
|
if (mount(source.c_str(), target.c_str(), "", MS_BIND | MS_REC, 0) == -1)
|
|
throw SysError("bind mount from '%1%' to '%2%' failed", source, target);
|
|
};
|
|
|
|
auto maybeSt = maybeLstat(source);
|
|
if (!maybeSt) {
|
|
if (optional)
|
|
return;
|
|
else
|
|
throw SysError("getting attributes of path '%1%'", source);
|
|
}
|
|
auto st = *maybeSt;
|
|
|
|
if (S_ISDIR(st.st_mode)) {
|
|
createDirs(target);
|
|
bindMount();
|
|
} else if (S_ISLNK(st.st_mode)) {
|
|
// Symlinks can (apparently) not be bind-mounted, so just copy it
|
|
createDirs(dirOf(target));
|
|
copyFile(source, target, {});
|
|
} else {
|
|
createDirs(dirOf(target));
|
|
writeFile(target, "");
|
|
bindMount();
|
|
}
|
|
}
|
|
|
|
}
|
|
|
|
#endif
|