diff --git a/roxie/ccd/ccdserver.cpp b/roxie/ccd/ccdserver.cpp index 3e4dfa92b21..712eea453ba 100644 --- a/roxie/ccd/ccdserver.cpp +++ b/roxie/ccd/ccdserver.cpp @@ -390,6 +390,60 @@ class IndirectAgentContext : implements IRoxieAgentContext, public CInterface //================================================================================= +class MergingStatsGatherer : implements CUnsharedInterfaceOf +{ +public: + MergingStatsGatherer(IStatisticGatherer * _gatherer) : gatherer(_gatherer) + { + } + + virtual void beginScope(const StatsScopeId & id) override + { + gatherer->beginScope(id); + } + virtual void beginSubGraphScope(unsigned id) override + { + gatherer->beginSubGraphScope(id); + } + virtual void beginActivityScope(unsigned id) override + { + gatherer->beginActivityScope(id); + } + virtual void beginEdgeScope(unsigned id, unsigned oid) override + { + gatherer->beginEdgeScope(id, oid); + } + virtual void beginChildGraphScope(unsigned id) override + { + gatherer->beginChildGraphScope(id); + } + virtual void beginChannelScope(unsigned id) override + { + gatherer->beginChannelScope(id); + } + virtual void endScope() override + { + gatherer->endScope(); + } + virtual void addStatistic(StatisticKind kind, unsigned __int64 value) override + { + //Always merge rather than updating + gatherer->updateStatistic(kind, value, queryMergeMode(kind)); + } + virtual void updateStatistic(StatisticKind kind, unsigned __int64 value, StatsMergeAction mergeAction) override + { + gatherer->updateStatistic(kind, value, mergeAction); + } + virtual IStatisticCollection * getResult() override + { + return gatherer->getResult(); + } + +private: + IStatisticGatherer * gatherer; +}; + +//================================================================================= #define RESULT_FLUSH_THRESHOLD 10000u #ifdef _DEBUG @@ -16532,8 +16586,9 @@ class CRoxieServerParallelGraphLoopActivity : public CRoxieServerGraphLoopActivi resultStream = NULL; resultJunction.clear(); + MergingStatsGatherer mergeStats(childStats); ForEachItemIn(i, iterationGraphs) - iterationGraphs.item(i).gatherStatistics(childStats); + iterationGraphs.item(i).gatherStatistics(childStats ? &mergeStats : nullptr); outputs.kill(); iterationGraphs.kill(); // must be done after all activities killed @@ -28506,9 +28561,11 @@ class CProxyActivityGraph : implements IActivityGraph, implements IThorChildGrap virtual const char *queryName() const override { throwUnexpected(); } virtual void gatherStatistics(IStatisticGatherer * statsBuilder) const override { + //Merge the stats from multiple graph instances. + MergingStatsGatherer mergeStatsBuilder(statsBuilder); CriticalBlock b(graphCrit); ForEachItemIn(i, stack) - stack.item(i).gatherStatistics(statsBuilder); + stack.item(i).gatherStatistics(statsBuilder ? &mergeStatsBuilder : nullptr); } virtual IEclGraphResults * evaluate(unsigned parentExtractSize, const byte * parentExtract) override { diff --git a/system/jlib/jstats.cpp b/system/jlib/jstats.cpp index 4dafcc75ed2..81f314a538a 100644 --- a/system/jlib/jstats.cpp +++ b/system/jlib/jstats.cpp @@ -1919,6 +1919,10 @@ class CStatisticCollection : public CInterfaceOf //other public interface functions void addStatistic(StatisticKind kind, unsigned __int64 value) { +#if 1 //def _DEBUG + unsigned __int64 debugTest; + assertex(getStatistic(kind,debugTest)==false); +#endif Statistic s(kind, value); stats.append(s); }