From 73c2a45af6afca253159d2cf9c1ecf5747f0217e Mon Sep 17 00:00:00 2001 From: Marius Kintel Date: Mon, 15 Apr 2013 20:58:15 -0400 Subject: Reinstate recursion guard to new context handling, fixes the last known subissue of #116 and #328 diff --git a/src/context.cc b/src/context.cc index bc54b88..6189205 100644 --- a/src/context.cc +++ b/src/context.cc @@ -44,7 +44,6 @@ std::vector Context::ctx_stack; Context::Context(const Context *parent) : parent(parent) { - if (parent) recursioncount = parent->recursioncount; ctx_stack.push_back(this); if (parent) document_path = parent->document_path; } @@ -120,24 +119,8 @@ Value Context::lookup_variable(const std::string &name, bool silent) const return Value(); } -class RecursionGuard -{ -public: - RecursionGuard(const Context &c, const std::string &name) : c(c), name(name) { c.recursioncount[name]++; } - ~RecursionGuard() { if (--c.recursioncount[name] == 0) c.recursioncount.erase(name); } - bool recursion_detected() const { return (c.recursioncount[name] > 100); } -private: - const Context &c; - const std::string &name; -}; - Value Context::evaluate_function(const std::string &name, const EvalContext *evalctx) const { - RecursionGuard g(*this, name); - if (g.recursion_detected()) { - PRINTB("Recursion detected calling function '%s'", name); - return Value(); - } if (this->parent) return this->parent->evaluate_function(name, evalctx); PRINTB("WARNING: Ignoring unknown function '%s'.", name); return Value(); diff --git a/src/context.h b/src/context.h index 5c75e48..282a940 100644 --- a/src/context.h +++ b/src/context.h @@ -33,8 +33,6 @@ public: static std::vector ctx_stack; - mutable boost::unordered_map recursioncount; - protected: typedef boost::unordered_map ValueMap; ValueMap constants; diff --git a/src/modcontext.cc b/src/modcontext.cc index 7902608..3280108 100644 --- a/src/modcontext.cc +++ b/src/modcontext.cc @@ -49,8 +49,27 @@ void ModuleContext::registerBuiltin() this->set_constant("PI",Value(M_PI)); } +class RecursionGuard +{ +public: + RecursionGuard(const ModuleContext &c, const std::string &name) : c(c), name(name) { + c.recursioncount[name]++; + } + ~RecursionGuard() { if (--c.recursioncount[name] == 0) c.recursioncount.erase(name); } + bool recursion_detected() const { return (c.recursioncount[name] > 100); } +private: + const ModuleContext &c; + const std::string &name; +}; + Value ModuleContext::evaluate_function(const std::string &name, const EvalContext *evalctx) const { + RecursionGuard g(*this, name); + if (g.recursion_detected()) { + PRINTB("Recursion detected calling function '%s'", name); + return Value(); + } + if (this->functions_p && this->functions_p->find(name) != this->functions_p->end()) { return this->functions_p->find(name)->second->evaluate(this, evalctx); } diff --git a/src/modcontext.h b/src/modcontext.h index cecf91f..5fce88f 100644 --- a/src/modcontext.h +++ b/src/modcontext.h @@ -2,6 +2,7 @@ #define FILECONTEXT_H_ #include "context.h" +#include /*! This holds the context for a Module definition; keeps track of @@ -32,6 +33,8 @@ public: #ifdef DEBUG virtual void dump(const class AbstractModule *mod, const ModuleInstantiation *inst); #endif + + mutable boost::unordered_map recursioncount; }; #endif -- cgit v0.10.1