diff options
Diffstat (limited to 'src/libexpr')
-rw-r--r-- | src/libexpr/nix.sdf | 3 | ||||
-rw-r--r-- | src/libexpr/parser.cc | 81 | ||||
-rw-r--r-- | src/libexpr/parser.hh | 6 |
3 files changed, 55 insertions, 35 deletions
diff --git a/src/libexpr/nix.sdf b/src/libexpr/nix.sdf index 615bdb974..b6bb23ebd 100644 --- a/src/libexpr/nix.sdf +++ b/src/libexpr/nix.sdf @@ -104,6 +104,7 @@ exports "\"" ~[\n\"]* "\"" -> Str PathComp ("/" PathComp)+ -> Path + ("/" PathComp)+ -> Path [a-zA-Z0-9\.\_\-\+]+ -> PathComp "true" -> Bool @@ -184,7 +185,7 @@ exports [0-9] -> Udigit lexical restrictions - Uri -/- [a-zA-Z0-9\-\_\.\!\~\*\'\(\)] + Uri -/- [a-zA-Z0-9\-\_\.\!\~\*\'\(\)\/] %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% diff --git a/src/libexpr/parser.cc b/src/libexpr/parser.cc index e3c863a55..aecfa4348 100644 --- a/src/libexpr/parser.cc +++ b/src/libexpr/parser.cc @@ -66,23 +66,9 @@ struct Cleanup : TermFun }; -Expr parseExprFromFile(Path path) +static Expr parse(const char * text, const string & location, + const Path & basePath) { - assert(path[0] == '/'); - -#if 0 - /* Perhaps this is already an imploded parse tree? */ - Expr e = ATreadFromNamedFile(path.c_str()); - if (e) return e; -#endif - - /* If `path' refers to a directory, append `/default.nix'. */ - struct stat st; - if (stat(path.c_str(), &st)) - throw SysError(format("getting status of `%1%'") % path); - if (S_ISDIR(st.st_mode)) - path = canonPath(path + "/default.nix"); - /* Initialise the SDF libraries. */ static bool initialised = false; static ATerm parseTable = 0; @@ -113,26 +99,13 @@ Expr parseExprFromFile(Path path) initialised = true; } - /* Read the input file. We can't use SGparseFile() because it's - broken, so we read the input ourselves and call - SGparseString(). */ - AutoCloseFD fd = open(path.c_str(), O_RDONLY); - if (fd == -1) throw SysError(format("opening `%1%'") % path); - - if (fstat(fd, &st) == -1) - throw SysError(format("statting `%1%'") % path); - - char text[st.st_size + 1]; - readFull(fd, (unsigned char *) text, st.st_size); - text[st.st_size] = 0; - /* Parse it. */ - ATerm result = SGparseString(lang, "Expr", text); + ATerm result = SGparseString(lang, "Expr", (char *) text); if (!result) - throw SysError(format("parse failed in `%1%'") % path); + throw SysError(format("parse failed in `%1%'") % location); if (SGisParseError(result)) throw Error(format("parse error in `%1%': %2%") - % path % result); + % location % result); /* Implode it. */ PT_ParseTree tree = PT_makeParseTreeFromTerm(result); @@ -155,10 +128,50 @@ Expr parseExprFromFile(Path path) throw Error(format("cannot implode parse tree")); printMsg(lvlVomit, format("imploded parse tree of `%1%': %2%") - % path % imploded); + % location % imploded); /* Finally, clean it up. */ Cleanup cleanup; - cleanup.basePath = dirOf(path); + cleanup.basePath = basePath; return bottomupRewrite(cleanup, imploded); } + + +Expr parseExprFromFile(Path path) +{ + assert(path[0] == '/'); + +#if 0 + /* Perhaps this is already an imploded parse tree? */ + Expr e = ATreadFromNamedFile(path.c_str()); + if (e) return e; +#endif + + /* If `path' refers to a directory, append `/default.nix'. */ + struct stat st; + if (stat(path.c_str(), &st)) + throw SysError(format("getting status of `%1%'") % path); + if (S_ISDIR(st.st_mode)) + path = canonPath(path + "/default.nix"); + + /* Read the input file. We can't use SGparseFile() because it's + broken, so we read the input ourselves and call + SGparseString(). */ + AutoCloseFD fd = open(path.c_str(), O_RDONLY); + if (fd == -1) throw SysError(format("opening `%1%'") % path); + + if (fstat(fd, &st) == -1) + throw SysError(format("statting `%1%'") % path); + + char text[st.st_size + 1]; + readFull(fd, (unsigned char *) text, st.st_size); + text[st.st_size] = 0; + + return parse(text, path, dirOf(path)); +} + + +Expr parseExprFromString(const string & s, const Path & basePath) +{ + return parse(s.c_str(), "(string)", basePath); +} diff --git a/src/libexpr/parser.hh b/src/libexpr/parser.hh index 5983ec562..461dae08c 100644 --- a/src/libexpr/parser.hh +++ b/src/libexpr/parser.hh @@ -4,7 +4,13 @@ #include "nixexpr.hh" +/* Parse a Nix expression from the specified file. If `path' refers + to a directory, the "/default.nix" is appended. */ Expr parseExprFromFile(Path path); +/* Parse a Nix expression from the specified string. */ +Expr parseExprFromString(const string & s, + const Path & basePath); + #endif /* !__PARSER_H */ |