diff options
author | Eelco Dolstra <e.dolstra@tudelft.nl> | 2006-11-30T17·43+0000 |
---|---|---|
committer | Eelco Dolstra <e.dolstra@tudelft.nl> | 2006-11-30T17·43+0000 |
commit | e2ef5e07fdc142670f7f3161d3133ff04e99d342 (patch) | |
tree | bf724d6af6f7fbe3b388fdfdd40f190da9a8378e /src/libstore/store-api.cc | |
parent | 5f0b9de6d837daf43c6ab26d41c829621c3ca727 (diff) |
* Refactoring. There is now an abstract interface class StoreAPI
containing functions that operate on the Nix store. One implementation is LocalStore, which operates on the Nix store directly. The next step, to enable secure multi-user Nix, is to create a different implementation RemoteStore that talks to a privileged daemon process that uses LocalStore to perform the actual operations.
Diffstat (limited to 'src/libstore/store-api.cc')
-rw-r--r-- | src/libstore/store-api.cc | 107 |
1 files changed, 107 insertions, 0 deletions
diff --git a/src/libstore/store-api.cc b/src/libstore/store-api.cc new file mode 100644 index 000000000000..3a07d1c73ca2 --- /dev/null +++ b/src/libstore/store-api.cc @@ -0,0 +1,107 @@ +#include "store-api.hh" +#include "globals.hh" + + +namespace nix { + + +bool isInStore(const Path & path) +{ + return path[0] == '/' + && string(path, 0, nixStore.size()) == nixStore + && path.size() >= nixStore.size() + 2 + && path[nixStore.size()] == '/'; +} + + +bool isStorePath(const Path & path) +{ + return isInStore(path) + && path.find('/', nixStore.size() + 1) == Path::npos; +} + + +void assertStorePath(const Path & path) +{ + if (!isStorePath(path)) + throw Error(format("path `%1%' is not in the Nix store") % path); +} + + +Path toStorePath(const Path & path) +{ + if (!isInStore(path)) + throw Error(format("path `%1%' is not in the Nix store") % path); + Path::size_type slash = path.find('/', nixStore.size() + 1); + if (slash == Path::npos) + return path; + else + return Path(path, 0, slash); +} + + +void checkStoreName(const string & name) +{ + string validChars = "+-._?="; + /* Disallow names starting with a dot for possible security + reasons (e.g., "." and ".."). */ + if (string(name, 0, 1) == ".") + throw Error(format("illegal name: `%1%'") % name); + for (string::const_iterator i = name.begin(); i != name.end(); ++i) + if (!((*i >= 'A' && *i <= 'Z') || + (*i >= 'a' && *i <= 'z') || + (*i >= '0' && *i <= '9') || + validChars.find(*i) != string::npos)) + { + throw Error(format("invalid character `%1%' in name `%2%'") + % *i % name); + } +} + + +Path makeStorePath(const string & type, + const Hash & hash, const string & suffix) +{ + /* e.g., "source:sha256:1abc...:/nix/store:foo.tar.gz" */ + string s = type + ":sha256:" + printHash(hash) + ":" + + nixStore + ":" + suffix; + + checkStoreName(suffix); + + return nixStore + "/" + + printHash32(compressHash(hashString(htSHA256, s), 20)) + + "-" + suffix; +} + + +Path makeFixedOutputPath(bool recursive, + string hashAlgo, Hash hash, string name) +{ + /* !!! copy/paste from primops.cc */ + Hash h = hashString(htSHA256, "fixed:out:" + + (recursive ? (string) "r:" : "") + hashAlgo + ":" + + printHash(hash) + ":" + + ""); + return makeStorePath("output:out", h, name); +} + + +} + + +#include "local-store.hh" + + +namespace nix { + + +boost::shared_ptr<StoreAPI> store; + + +boost::shared_ptr<StoreAPI> openStore(bool reserveSpace) +{ + return boost::shared_ptr<StoreAPI>(new LocalStore(reserveSpace)); +} + + +} |