diff options
| author | Dan Willemsen <dwillemsen@google.com> | 2020-06-26 18:46:21 -0700 |
|---|---|---|
| committer | Dan Willemsen <dwillemsen@google.com> | 2020-06-26 18:52:06 -0700 |
| commit | 979e7ae6e417ae4ee45e835104b66191ae16a14c (patch) | |
| tree | 6b5075e832cbdf2a7996a25a26659363527b6e4c /src/rule.cc | |
| parent | 003cf51e9b6da48063c90cf4c6710fde103c9c4a (diff) | |
| download | platform_build_kati-979e7ae6e417ae4ee45e835104b66191ae16a14c.tar.gz platform_build_kati-979e7ae6e417ae4ee45e835104b66191ae16a14c.tar.bz2 platform_build_kati-979e7ae6e417ae4ee45e835104b66191ae16a14c.zip | |
Refactor source tree into directories
Now instead of almost every file in the top level, move the old go code
into its own directory 'golang', and the C++ code into it's own 'src'
Also removes a few obsolete scripts that were used to work on Android
before Android fully switched to Kati.
Diffstat (limited to 'src/rule.cc')
| -rw-r--r-- | src/rule.cc | 122 |
1 files changed, 122 insertions, 0 deletions
diff --git a/src/rule.cc b/src/rule.cc new file mode 100644 index 0000000..867a7e3 --- /dev/null +++ b/src/rule.cc @@ -0,0 +1,122 @@ +// Copyright 2015 Google Inc. All rights reserved +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +// +build ignore + +#include "rule.h" + +#include "expr.h" +#include "log.h" +#include "parser.h" +#include "stringprintf.h" +#include "strutil.h" +#include "symtab.h" + +Rule::Rule() : is_double_colon(false), is_suffix_rule(false), cmd_lineno(0) {} + +void Rule::ParseInputs(const StringPiece& inputs_str) { + bool is_order_only = false; + for (auto const& input : WordScanner(inputs_str)) { + if (input == "|") { + is_order_only = true; + continue; + } + Symbol input_sym = Intern(TrimLeadingCurdir(input)); + (is_order_only ? order_only_inputs : inputs).push_back(input_sym); + } +} + +void Rule::ParsePrerequisites(const StringPiece& line, + size_t separator_pos, + const RuleStmt* rule_stmt) { + // line is either + // prerequisites [ ; command ] + // or + // target-prerequisites : prereq-patterns [ ; command ] + // First, separate command. At this point separator_pos should point to ';' + // unless null. + StringPiece prereq_string = line; + if (separator_pos != string::npos && + rule_stmt->sep != RuleStmt::SEP_SEMICOLON) { + CHECK(line[separator_pos] == ';'); + // TODO: Maybe better to avoid Intern here? + cmds.push_back(Value::NewLiteral( + Intern(TrimLeftSpace(line.substr(separator_pos + 1))).str())); + prereq_string = line.substr(0, separator_pos); + } + + if ((separator_pos = prereq_string.find(':')) == string::npos) { + // Simple prerequisites + ParseInputs(prereq_string); + return; + } + + // Static pattern rule. + if (!output_patterns.empty()) { + ERROR_LOC(loc, "*** mixed implicit and normal rules: deprecated syntax"); + } + + // Empty static patterns should not produce rules, but need to eat the + // commands So return a rule with no outputs nor output_patterns + if (outputs.empty()) { + return; + } + + StringPiece target_prereq = prereq_string.substr(0, separator_pos); + StringPiece prereq_patterns = prereq_string.substr(separator_pos + 1); + + for (StringPiece target_pattern : WordScanner(target_prereq)) { + target_pattern = TrimLeadingCurdir(target_pattern); + for (Symbol target : outputs) { + if (!Pattern(target_pattern).Match(target.str())) { + WARN_LOC(loc, "target `%s' doesn't match the target pattern", + target.c_str()); + } + } + output_patterns.push_back(Intern(target_pattern)); + } + + if (output_patterns.empty()) { + ERROR_LOC(loc, "*** missing target pattern."); + } + if (output_patterns.size() > 1) { + ERROR_LOC(loc, "*** multiple target patterns."); + } + if (!IsPatternRule(output_patterns[0].str())) { + ERROR_LOC(loc, "*** target pattern contains no '%%'."); + } + ParseInputs(prereq_patterns); +} + +string Rule::DebugString() const { + vector<string> v; + v.push_back(StringPrintf("outputs=[%s]", JoinSymbols(outputs, ",").c_str())); + v.push_back(StringPrintf("inputs=[%s]", JoinSymbols(inputs, ",").c_str())); + if (!order_only_inputs.empty()) { + v.push_back(StringPrintf("order_only_inputs=[%s]", + JoinSymbols(order_only_inputs, ",").c_str())); + } + if (!output_patterns.empty()) { + v.push_back(StringPrintf("output_patterns=[%s]", + JoinSymbols(output_patterns, ",").c_str())); + } + if (is_double_colon) + v.push_back("is_double_colon"); + if (is_suffix_rule) + v.push_back("is_suffix_rule"); + if (!cmds.empty()) { + v.push_back(StringPrintf("cmds=[%s]", JoinValues(cmds, ",").c_str())); + } + return JoinStrings(v, " "); +} |
