From 43708dcc214f793ad6fb8f93f9327d5c13b594b9 Mon Sep 17 00:00:00 2001 From: Dieter Baron Date: Sun, 14 Apr 2024 15:55:30 +0200 Subject: [PATCH] =?UTF-8?q?Don=E2=80=99t=20expand=20filename=20variables?= =?UTF-8?q?=20in=20rule=20bindings.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This allows $build_directory to be used in command. --- src/Bindings.cc | 10 ++++------ src/Bindings.h | 2 +- src/File.cc | 2 +- src/FilenameVariable.cc | 4 ++++ src/FilenameVariable.h | 2 +- src/ResolveContext.h | 3 ++- src/Rule.cc | 4 +++- src/Word.cc | 10 ++++++---- tests/explicit-filename.test | 5 +++++ tests/filelist.test | 6 ++++++ tests/implicit-output.test | 5 +++++ tests/rule.test | 5 +++++ tests/special-characters.test | 5 +++++ tests/special_directories.test | 8 ++++++++ tests/subninja.test | 8 ++++++++ 15 files changed, 64 insertions(+), 15 deletions(-) diff --git a/src/Bindings.cc b/src/Bindings.cc index c768249..fe0ec5f 100644 --- a/src/Bindings.cc +++ b/src/Bindings.cc @@ -62,15 +62,13 @@ Bindings::Bindings(Tokenizer& tokenizer) { void Bindings::print(std::ostream& stream, const std::string& indent) const { for (auto& pair : *this) { - if (!pair.second->is_filename()) { - stream << indent; - pair.second->print_definition(stream); - } + stream << indent; + pair.second->print_definition(stream); } } -void Bindings::resolve(const Scope& scope) { - auto context = ResolveContext{scope}; +void Bindings::resolve(const Scope& scope, bool expand_variables) { + auto context = ResolveContext{scope, expand_variables}; for (auto& pair : variables) { pair.second->resolve(context); } diff --git a/src/Bindings.h b/src/Bindings.h index da7440c..4a50b7f 100644 --- a/src/Bindings.h +++ b/src/Bindings.h @@ -45,7 +45,7 @@ class Bindings { explicit Bindings(Tokenizer& tokenizer); void print(std::ostream& stream, const std::string& indent) const; - void resolve(const Scope& scope); + void resolve(const Scope& scope, bool expand_variables = true); void add(std::shared_ptr variable) {variables[variable->name] = std::move(variable);} [[nodiscard]] auto empty() const {return variables.empty();} diff --git a/src/File.cc b/src/File.cc index 3857b5b..ea8691b 100644 --- a/src/File.cc +++ b/src/File.cc @@ -136,7 +136,7 @@ void File::create_output() const { } stream << "# This file is automatically created by fast-ninja from " << source_filename.string() << std::endl; - stream << "# Do not edit." << std::endl; + stream << "# Do not edit." << std::endl << std::endl; if (!bindings.empty()) { bindings.print(stream, ""); diff --git a/src/FilenameVariable.cc b/src/FilenameVariable.cc index c3854be..706592d 100644 --- a/src/FilenameVariable.cc +++ b/src/FilenameVariable.cc @@ -51,3 +51,7 @@ FilenameVariable::FilenameVariable(std::string name, Tokenizer& tokenizer) : Var value = FilenameList(tokenizer, FilenameList::INLINE); } } + +void FilenameVariable::print_definition(std::ostream& stream) const { + stream << name << " = " << value << std::endl; +} \ No newline at end of file diff --git a/src/FilenameVariable.h b/src/FilenameVariable.h index 1945aa1..24af75e 100644 --- a/src/FilenameVariable.h +++ b/src/FilenameVariable.h @@ -44,7 +44,7 @@ class FilenameVariable : public Variable { FilenameVariable(std::string name, FilenameList value): Variable(std::move(name)), value{std::move(value)} {} void resolve_sub(const ResolveContext& context) override {value.resolve(context);} - void print_definition(std::ostream& stream) const override {} // TODO + void print_definition(std::ostream& stream) const override; void print_use(std::ostream& stream) const override {} // TODO [[nodiscard]] std::string string() const override {return value.string();} void collect_filenames(std::vector& collector) const {return value.collect_filenames(collector);} diff --git a/src/ResolveContext.h b/src/ResolveContext.h index fbd5809..f1bf61d 100644 --- a/src/ResolveContext.h +++ b/src/ResolveContext.h @@ -38,12 +38,13 @@ IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. class ResolveContext { public: - explicit ResolveContext(const Scope& scope): scope{scope} {} + explicit ResolveContext(const Scope& scope, bool expand_variables = false): scope{scope}, expand_variables{expand_variables} {} [[nodiscard]] ResolveContext resolving(const std::string& name) const; [[nodiscard]] const Variable* get_variable(const std::string& name) const; const Scope& scope; + bool expand_variables{false}; private: std::unordered_set resolving_variables; diff --git a/src/Rule.cc b/src/Rule.cc index c9a1113..d8d2e9f 100644 --- a/src/Rule.cc +++ b/src/Rule.cc @@ -40,7 +40,9 @@ Rule::Rule(const File* file, std::string name, Tokenizer& tokenizer) : ScopedDir Rule::Rule(const File* file, std::string name, Bindings bindings): ScopedDirective{file, std::move(bindings)}, name{std::move(name)} {} -void Rule::process(const File& file) { bindings.resolve(file); } +void Rule::process(const File& file) { + bindings.resolve(file, false); +} void Rule::print(std::ostream& stream) const { stream << std::endl << "rule " << name << std::endl; diff --git a/src/Word.cc b/src/Word.cc index e009855..19a508a 100644 --- a/src/Word.cc +++ b/src/Word.cc @@ -140,10 +140,12 @@ void Word::print(std::ostream& stream) const { void Word::resolve(const ResolveContext& context) { for (auto& element : elements) { if (std::holds_alternative(element)) { - auto& variable_reference = std::get(element); - variable_reference.resolve(context); - if (variable_reference.is_text_variable()) { - element = StringElement{variable_reference.variable->string(), true}; + if (context.expand_variables) { + auto& variable_reference = std::get(element); + variable_reference.resolve(context); + if (variable_reference.is_text_variable()) { + element = StringElement{ variable_reference.variable->string(), true }; + } } } else if (std::holds_alternative(element)) { diff --git a/tests/explicit-filename.test b/tests/explicit-filename.test index 2d5cd6f..fb1f1b7 100644 --- a/tests/explicit-filename.test +++ b/tests/explicit-filename.test @@ -13,6 +13,11 @@ file build/build.ninja {} <> # This file is automatically created by fast-ninja from ../build.fninja # Do not edit. +build_directory = . +source_directory = .. +top_build_directory = . +top_source_directory = .. + rule a command = ../input $in $out flags = --verbose diff --git a/tests/filelist.test b/tests/filelist.test index c8a8baa..1fba939 100644 --- a/tests/filelist.test +++ b/tests/filelist.test @@ -22,6 +22,12 @@ end-of-inline-data file build/build.ninja {} <> # This file is automatically created by fast-ninja from ../build.fninja # Do not edit. + +build_directory = . +source_directory = .. +sources = ../input ../input-2 output +top_build_directory = . +top_source_directory = .. version = 2 rule a diff --git a/tests/implicit-output.test b/tests/implicit-output.test index 0528707..e368214 100644 --- a/tests/implicit-output.test +++ b/tests/implicit-output.test @@ -13,6 +13,11 @@ file build/build.ninja {} <> # This file is automatically created by fast-ninja from ../build.fninja # Do not edit. +build_directory = . +source_directory = .. +top_build_directory = . +top_source_directory = .. + rule a command = a $in $out flags = --verbose diff --git a/tests/rule.test b/tests/rule.test index 7d386fe..c05a452 100644 --- a/tests/rule.test +++ b/tests/rule.test @@ -8,6 +8,11 @@ file build/build.ninja {} <> # This file is automatically created by fast-ninja from ../build.fninja # Do not edit. +build_directory = . +source_directory = .. +top_build_directory = . +top_source_directory = .. + rule a command = a $in $out flags = --verbose diff --git a/tests/special-characters.test b/tests/special-characters.test index 52158ca..bdc00b9 100644 --- a/tests/special-characters.test +++ b/tests/special-characters.test @@ -7,6 +7,11 @@ file build/build.ninja {} <> # This file is automatically created by fast-ninja from ../build.fninja # Do not edit. +build_directory = . +source_directory = .. +top_build_directory = . +top_source_directory = .. + rule a command = a rule build = "a$ b" |@ || | @ diff --git a/tests/special_directories.test b/tests/special_directories.test index 97b20a4..0537424 100644 --- a/tests/special_directories.test +++ b/tests/special_directories.test @@ -15,6 +15,11 @@ file build/build.ninja {} <> # This file is automatically created by fast-ninja from ../build.fninja # Do not edit. +build_directory = . +source_directory = .. +top_build_directory = . +top_source_directory = .. + rule a command = a $in @@ -33,5 +38,8 @@ file build/src/build.ninja {} <> # This file is automatically created by fast-ninja from ../src/build.fninja # Do not edit. +build_directory = src +source_directory = ../src + build src/test : a src ../src . .. end-of-inline-data diff --git a/tests/subninja.test b/tests/subninja.test index 430e3ac..a952264 100644 --- a/tests/subninja.test +++ b/tests/subninja.test @@ -23,6 +23,11 @@ file build/build.ninja {} <> # This file is automatically created by fast-ninja from ../build.fninja # Do not edit. +build_directory = . +source_directory = .. +top_build_directory = . +top_source_directory = .. + rule a command = a $in $out flags = --verbose @@ -44,5 +49,8 @@ file build/src/build.ninja {} <> # This file is automatically created by fast-ninja from ../src/build.fninja # Do not edit. +build_directory = src +source_directory = ../src + build src/output : a output ../src/input ../input end-of-inline-data