diff options
author | Sasha Smundak <asmundak@google.com> | 2022-10-31 12:47:09 -0700 |
---|---|---|
committer | Sasha Smundak <asmundak@google.com> | 2022-10-31 12:47:09 -0700 |
commit | 7749f2a01f2e83bb8bc1353b22db9919be28b9ee (patch) | |
tree | 7a62ab24c367dfd5026c7de9f48345d87072a7bb | |
parent | 09dfa26c4e59b15919aaad6986f9b47c883dc4f1 (diff) | |
download | kati-7749f2a01f2e83bb8bc1353b22db9919be28b9ee.tar.gz |
Add --variable_assignment_trace_filter option
In addition, write assignment event to the trace file.
-rw-r--r-- | src/eval.cc | 82 | ||||
-rw-r--r-- | src/eval.h | 6 | ||||
-rw-r--r-- | src/flags.cc | 14 | ||||
-rw-r--r-- | src/flags.h | 2 | ||||
-rw-r--r-- | src/strutil.cc | 3 |
5 files changed, 80 insertions, 27 deletions
diff --git a/src/eval.cc b/src/eval.cc index 7f9dc6f..637f373 100644 --- a/src/eval.cc +++ b/src/eval.cc @@ -177,7 +177,7 @@ Evaluator::Evaluator() trace_ = g_flags.dump_variable_assignment_trace || g_flags.dump_include_graph; assignment_tracefile_ = nullptr; - assignment_count_ = 0; + assignment_sep_ = "\n"; } Evaluator::~Evaluator() { @@ -345,6 +345,7 @@ void Evaluator::EvalAssign(const AssignStmt* stmt) { if (stmt->is_final) { var->SetReadOnly(); } + TraceVariableAssign(lhs, var); } // With rule broken into @@ -709,35 +710,70 @@ Var* Evaluator::LookupVarGlobal(Symbol name) { return v; } -void Evaluator::TraceVariableLookup(const char* operation, - Symbol name, - Var* var) { +bool Evaluator::IsTraced(Symbol& name) const { if (assignment_tracefile_ == nullptr) { - return; + return false; } - if (assignment_count_++ == 0) { - fprintf(assignment_tracefile_, "\n"); - } else { - fprintf(assignment_tracefile_, ",\n"); + bool trace_var = g_flags.traced_variables_pattern.size() == 0; + // trace every variable unless filtered + if (trace_var) { + return true; + } + + for (const auto& pat : g_flags.traced_variables_pattern) { + if (pat.Match(name.c_str())) { + return true; + } + } + return false; +} + +void Evaluator::TraceVariableLookup(const char* operation, + Symbol& name, + Var* var) { + if (!IsTraced(name)) { + return; } - bool has_definition_trace = var->Definition() != nullptr; - fprintf(assignment_tracefile_, " {\n"); - fprintf(assignment_tracefile_, " \"name\": \"%s\",\n", name.c_str()); - fprintf(assignment_tracefile_, " \"operation\": \"%s\",\n", operation); - fprintf(assignment_tracefile_, " \"defined\": %s,\n", - var->IsDefined() ? "true" : "false"); + fputs(assignment_sep_, assignment_tracefile_); + assignment_sep_ = ",\n"; + fprintf(assignment_tracefile_, + " {\n" + " \"name\": \"%s\",\n" + " \"operation\": \"%s\",\n" + " \"defined\": %s,\n", + name.c_str(), operation, var->IsDefined() ? "true" : "false"); fprintf(assignment_tracefile_, " \"reference_stack\": [\n"); CurrentFrame()->PrintJSONTrace(assignment_tracefile_, 8); - fprintf(assignment_tracefile_, " ]%s\n", - has_definition_trace ? "," : ""); - if (has_definition_trace) { - fprintf(assignment_tracefile_, " \"value_stack\": [\n"); - var->Definition()->PrintJSONTrace(assignment_tracefile_, 8); - fprintf(assignment_tracefile_, " ]\n"); - } - fprintf(assignment_tracefile_, " }"); + fprintf(assignment_tracefile_, + " ]\n" + " }"); +} + +void Evaluator::TraceVariableAssign(Symbol& name, Var* var) { + if (!IsTraced(name)) { + return; + } + fputs(assignment_sep_, assignment_tracefile_); + assignment_sep_ = ",\n"; + fprintf(assignment_tracefile_, + " {\n" + " \"name\": \"%s\",\n" + " \"operation\": \"assign\",\n" + " \"value\": \"%s\"", + name.c_str(), var->DebugString().c_str()); + Frame* definition = var->Definition(); + if (definition != nullptr) { + fprintf(assignment_tracefile_, + ",\n" + " \"value_stack\": [\n"); + definition->PrintJSONTrace(assignment_tracefile_, 8); + fprintf(assignment_tracefile_, " ]"); + } + fprintf(assignment_tracefile_, + "\n" + " }"); } Var* Evaluator::LookupVarForEval(Symbol name) { @@ -228,7 +228,9 @@ class Evaluator { bool* needs_assign); void DoInclude(const string& fname); - void TraceVariableLookup(const char* operation, Symbol name, Var* var); + bool IsTraced(Symbol& name) const; + void TraceVariableLookup(const char* operation, Symbol& name, Var* var); + void TraceVariableAssign(Symbol& name, Var* var); Var* LookupVarGlobal(Symbol name); // Equivalent to LookupVarInCurrentScope, but doesn't mark as used. @@ -256,7 +258,7 @@ class Evaluator { bool trace_; std::vector<Frame*> stack_; FILE* assignment_tracefile_; - long int assignment_count_; + const char* assignment_sep_; std::vector<Loc> include_stack_; diff --git a/src/flags.cc b/src/flags.cc index e21a541..1bba336 100644 --- a/src/flags.cc +++ b/src/flags.cc @@ -53,6 +53,7 @@ void Flags::Parse(int argc, char** argv) { num_jobs = num_cpus = sysconf(_SC_NPROCESSORS_ONLN); const char* num_jobs_str; const char* writable_str; + const char* variable_assignment_trace_filter; if (const char* makeflags = getenv("MAKEFLAGS")) { for (StringPiece tok : WordScanner(makeflags)) { @@ -154,6 +155,12 @@ void Flags::Parse(int argc, char** argv) { } else if (ParseCommandLineOptionWithArg("--dump_variable_assignment_trace", argv, &i, &dump_variable_assignment_trace)) { + } else if (ParseCommandLineOptionWithArg( + "--variable_assignment_trace_filter", argv, &i, + &variable_assignment_trace_filter)) { + for (StringPiece pat : WordScanner(variable_assignment_trace_filter)) { + traced_variables_pattern.push_back(Pattern(pat)); + } } else if (ParseCommandLineOptionWithArg("-j", argv, &i, &num_jobs_str)) { num_jobs = strtol(num_jobs_str, NULL, 10); if (num_jobs <= 0) { @@ -202,4 +209,11 @@ void Flags::Parse(int argc, char** argv) { } } } + + if (traced_variables_pattern.size() && + dump_variable_assignment_trace == nullptr) { + ERROR( + "--variable_assignment_trace_filter is valid only together with " + "--dump_variable_assignment_trace"); + } } diff --git a/src/flags.h b/src/flags.h index 73410d5..e173730 100644 --- a/src/flags.h +++ b/src/flags.h @@ -19,6 +19,7 @@ #include <vector> #include "string_piece.h" +#include "strutil.h" #include "symtab.h" using namespace std; @@ -80,6 +81,7 @@ struct Flags { vector<Symbol> targets; vector<StringPiece> cl_vars; vector<string> writable; + vector<Pattern> traced_variables_pattern; void Parse(int argc, char** argv); }; diff --git a/src/strutil.cc b/src/strutil.cc index 8c4bdc0..4546265 100644 --- a/src/strutil.cc +++ b/src/strutil.cc @@ -160,8 +160,7 @@ bool Pattern::MatchImpl(StringPiece str) const { StringPiece Pattern::Stem(StringPiece str) const { if (!Match(str)) return ""; - return str.substr(percent_index_, - str.size() - pat_.size() + 1); + return str.substr(percent_index_, str.size() - pat_.size() + 1); } void Pattern::AppendSubst(StringPiece str, |