Loading cmds/statsd/src/HashableDimensionKey.cpp +28 −8 Original line number Diff line number Diff line Loading @@ -59,10 +59,11 @@ android::hash_t hashDimension(const HashableDimensionKey& value) { return JenkinsHashWhiten(hash); } bool filterValues(const Matcher& matcherField, const vector<FieldValue>& values, Value* output) { bool filterValues(const Matcher& matcherField, const vector<FieldValue>& values, FieldValue* output) { for (const auto& value : values) { if (value.mField.matches(matcherField)) { (*output) = value.mValue; (*output) = value; return true; } } Loading Loading @@ -106,7 +107,6 @@ void getDimensionForCondition(const std::vector<FieldValue>& eventValues, size_t count = conditionDimension->getValues().size(); if (count != links.conditionFields.size()) { // ALOGE("WTF condition link is bad"); return; } Loading @@ -118,6 +118,26 @@ void getDimensionForCondition(const std::vector<FieldValue>& eventValues, } } void getDimensionForState(const std::vector<FieldValue>& eventValues, const Metric2State& link, HashableDimensionKey* statePrimaryKey) { // First, get the dimension from the event using the "what" fields from the // MetricStateLinks. filterValues(link.metricFields, eventValues, statePrimaryKey); // Then check that the statePrimaryKey size equals the number of state fields size_t count = statePrimaryKey->getValues().size(); if (count != link.stateFields.size()) { return; } // For each dimension Value in the statePrimaryKey, set the field and tag // using the state atom fields from MetricStateLinks. for (size_t i = 0; i < count; i++) { statePrimaryKey->mutableValue(i)->mField.setField(link.stateFields[i].mMatcher.getField()); statePrimaryKey->mutableValue(i)->mField.setTag(link.stateFields[i].mMatcher.getTag()); } } bool LessThan(const vector<FieldValue>& s1, const vector<FieldValue>& s2) { if (s1.size() != s2.size()) { return s1.size() < s2.size(); Loading Loading @@ -185,11 +205,11 @@ string HashableDimensionKey::toString() const { bool MetricDimensionKey::operator==(const MetricDimensionKey& that) const { return mDimensionKeyInWhat == that.getDimensionKeyInWhat() && mDimensionKeyInCondition == that.getDimensionKeyInCondition(); mStateValuesKey == that.getStateValuesKey(); }; string MetricDimensionKey::toString() const { return mDimensionKeyInWhat.toString() + mDimensionKeyInCondition.toString(); return mDimensionKeyInWhat.toString() + mStateValuesKey.toString(); } bool MetricDimensionKey::operator<(const MetricDimensionKey& that) const { Loading @@ -199,7 +219,7 @@ bool MetricDimensionKey::operator<(const MetricDimensionKey& that) const { return false; } return mDimensionKeyInCondition < that.getDimensionKeyInCondition(); return mStateValuesKey < that.getStateValuesKey(); } } // namespace statsd Loading cmds/statsd/src/HashableDimensionKey.h +28 −16 Original line number Diff line number Diff line Loading @@ -34,6 +34,12 @@ struct Metric2Condition { std::vector<Matcher> conditionFields; }; struct Metric2State { int32_t stateAtomId; std::vector<Matcher> metricFields; std::vector<Matcher> stateFields; }; class HashableDimensionKey { public: explicit HashableDimensionKey(const std::vector<FieldValue>& values) { Loading Loading @@ -78,15 +84,14 @@ private: class MetricDimensionKey { public: explicit MetricDimensionKey(const HashableDimensionKey& dimensionKeyInWhat, const HashableDimensionKey& dimensionKeyInCondition) : mDimensionKeyInWhat(dimensionKeyInWhat), mDimensionKeyInCondition(dimensionKeyInCondition) {}; const HashableDimensionKey& stateValuesKey) : mDimensionKeyInWhat(dimensionKeyInWhat), mStateValuesKey(stateValuesKey){}; MetricDimensionKey(){}; MetricDimensionKey(const MetricDimensionKey& that) : mDimensionKeyInWhat(that.getDimensionKeyInWhat()), mDimensionKeyInCondition(that.getDimensionKeyInCondition()) {}; mStateValuesKey(that.getStateValuesKey()){}; MetricDimensionKey& operator=(const MetricDimensionKey& from) = default; Loading @@ -96,16 +101,16 @@ class MetricDimensionKey { return mDimensionKeyInWhat; } inline const HashableDimensionKey& getDimensionKeyInCondition() const { return mDimensionKeyInCondition; inline const HashableDimensionKey& getStateValuesKey() const { return mStateValuesKey; } inline void setDimensionKeyInCondition(const HashableDimensionKey& key) { mDimensionKeyInCondition = key; inline void setStateValuesKey(const HashableDimensionKey& key) { mStateValuesKey = key; } bool hasDimensionKeyInCondition() const { return mDimensionKeyInCondition.getValues().size() > 0; bool hasStateValuesKey() const { return mStateValuesKey.getValues().size() > 0; } bool operator==(const MetricDimensionKey& that) const; Loading @@ -114,7 +119,7 @@ class MetricDimensionKey { private: HashableDimensionKey mDimensionKeyInWhat; HashableDimensionKey mDimensionKeyInCondition; HashableDimensionKey mStateValuesKey; }; android::hash_t hashDimension(const HashableDimensionKey& key); Loading @@ -124,7 +129,7 @@ android::hash_t hashDimension(const HashableDimensionKey& key); * The value of the FieldValue is output. */ bool filterValues(const Matcher& matcherField, const std::vector<FieldValue>& values, Value* output); FieldValue* output); /** * Creating HashableDimensionKeys from FieldValues using matcher. Loading Loading @@ -152,6 +157,13 @@ void getDimensionForCondition(const std::vector<FieldValue>& eventValues, const Metric2Condition& links, HashableDimensionKey* conditionDimension); /** * Get dimension values using metric's "what" fields and fill statePrimaryKey's * mField information using "state" fields. */ void getDimensionForState(const std::vector<FieldValue>& eventValues, const Metric2State& link, HashableDimensionKey* statePrimaryKey); } // namespace statsd } // namespace os } // namespace android Loading @@ -172,7 +184,7 @@ template <> struct hash<MetricDimensionKey> { std::size_t operator()(const MetricDimensionKey& key) const { android::hash_t hash = hashDimension(key.getDimensionKeyInWhat()); hash = android::JenkinsHashMix(hash, hashDimension(key.getDimensionKeyInCondition())); hash = android::JenkinsHashMix(hash, hashDimension(key.getStateValuesKey())); return android::JenkinsHashWhiten(hash); } }; Loading cmds/statsd/src/StatsLogProcessor.h +4 −3 Original line number Diff line number Diff line Loading @@ -263,9 +263,10 @@ private: FRIEND_TEST(MetricActivationE2eTest, TestCountMetricWithSameDeactivation); FRIEND_TEST(MetricActivationE2eTest, TestCountMetricWithTwoMetricsTwoDeactivations); FRIEND_TEST(CountMetricE2eTest, TestWithSimpleState); FRIEND_TEST(CountMetricE2eTest, TestWithMappedState); FRIEND_TEST(CountMetricE2eTest, TestWithMultipleStates); FRIEND_TEST(CountMetricE2eTest, TestSlicedState); FRIEND_TEST(CountMetricE2eTest, TestSlicedStateWithMap); FRIEND_TEST(CountMetricE2eTest, TestMultipleSlicedStates); FRIEND_TEST(CountMetricE2eTest, TestSlicedStateWithPrimaryFields); FRIEND_TEST(DurationMetricE2eTest, TestOneBucket); FRIEND_TEST(DurationMetricE2eTest, TestTwoBuckets); Loading cmds/statsd/src/metrics/CountMetricProducer.cpp +19 −21 Original line number Diff line number Diff line Loading @@ -57,10 +57,9 @@ const int FIELD_ID_IS_ACTIVE = 14; const int FIELD_ID_DATA = 1; // for CountMetricData const int FIELD_ID_DIMENSION_IN_WHAT = 1; const int FIELD_ID_DIMENSION_IN_CONDITION = 2; const int FIELD_ID_SLICE_BY_STATE = 6; const int FIELD_ID_BUCKET_INFO = 3; const int FIELD_ID_DIMENSION_LEAF_IN_WHAT = 4; const int FIELD_ID_DIMENSION_LEAF_IN_CONDITION = 5; // for CountBucketInfo const int FIELD_ID_COUNT = 3; const int FIELD_ID_BUCKET_NUM = 4; Loading Loading @@ -102,7 +101,13 @@ CountMetricProducer::CountMetricProducer( mConditionSliced = true; } // TODO(tsaichristine): b/142124705 handle metric state links for (const auto& stateLink : metric.state_link()) { Metric2State ms; ms.stateAtomId = stateLink.state_atom_id(); translateFieldMatcher(stateLink.fields_in_what(), &ms.metricFields); translateFieldMatcher(stateLink.fields_in_state(), &ms.stateFields); mMetric2StateLinks.push_back(ms); } flushIfNeededLocked(startTimeNs); // Adjust start for partial bucket Loading Loading @@ -132,10 +137,9 @@ void CountMetricProducer::dumpStatesLocked(FILE* out, bool verbose) const { (unsigned long)mCurrentSlicedCounter->size()); if (verbose) { for (const auto& it : *mCurrentSlicedCounter) { fprintf(out, "\t(what)%s\t(condition)%s %lld\n", fprintf(out, "\t(what)%s\t(state)%s %lld\n", it.first.getDimensionKeyInWhat().toString().c_str(), it.first.getDimensionKeyInCondition().toString().c_str(), (unsigned long long)it.second); it.first.getStateValuesKey().toString().c_str(), (unsigned long long)it.second); } } } Loading Loading @@ -196,22 +200,16 @@ void CountMetricProducer::onDumpReportLocked(const int64_t dumpTimeNs, FIELD_TYPE_MESSAGE | FIELD_ID_DIMENSION_IN_WHAT); writeDimensionToProto(dimensionKey.getDimensionKeyInWhat(), str_set, protoOutput); protoOutput->end(dimensionToken); if (dimensionKey.hasDimensionKeyInCondition()) { uint64_t dimensionInConditionToken = protoOutput->start( FIELD_TYPE_MESSAGE | FIELD_ID_DIMENSION_IN_CONDITION); writeDimensionToProto(dimensionKey.getDimensionKeyInCondition(), str_set, protoOutput); protoOutput->end(dimensionInConditionToken); } } else { writeDimensionLeafNodesToProto(dimensionKey.getDimensionKeyInWhat(), FIELD_ID_DIMENSION_LEAF_IN_WHAT, str_set, protoOutput); if (dimensionKey.hasDimensionKeyInCondition()) { writeDimensionLeafNodesToProto(dimensionKey.getDimensionKeyInCondition(), FIELD_ID_DIMENSION_LEAF_IN_CONDITION, str_set, protoOutput); } // Then fill slice_by_state. for (auto state : dimensionKey.getStateValuesKey().getValues()) { uint64_t stateToken = protoOutput->start(FIELD_TYPE_MESSAGE | FIELD_COUNT_REPEATED | FIELD_ID_SLICE_BY_STATE); writeStateToProto(state, protoOutput); protoOutput->end(stateToken); } // Then fill bucket_info (CountBucketInfo). for (const auto& bucket : counter.second) { Loading Loading @@ -282,7 +280,7 @@ void CountMetricProducer::onMatchedLogEventInternalLocked( int64_t eventTimeNs = event.GetElapsedTimestampNs(); flushIfNeededLocked(eventTimeNs); if (condition == false) { if (!condition) { return; } Loading cmds/statsd/src/metrics/CountMetricProducer.h +1 −1 Original line number Diff line number Diff line Loading @@ -52,7 +52,7 @@ public: virtual ~CountMetricProducer(); void onStateChanged(int atomId, const HashableDimensionKey& primaryKey, int oldState, void onStateChanged(int32_t atomId, const HashableDimensionKey& primaryKey, int oldState, int newState) override; protected: Loading Loading
cmds/statsd/src/HashableDimensionKey.cpp +28 −8 Original line number Diff line number Diff line Loading @@ -59,10 +59,11 @@ android::hash_t hashDimension(const HashableDimensionKey& value) { return JenkinsHashWhiten(hash); } bool filterValues(const Matcher& matcherField, const vector<FieldValue>& values, Value* output) { bool filterValues(const Matcher& matcherField, const vector<FieldValue>& values, FieldValue* output) { for (const auto& value : values) { if (value.mField.matches(matcherField)) { (*output) = value.mValue; (*output) = value; return true; } } Loading Loading @@ -106,7 +107,6 @@ void getDimensionForCondition(const std::vector<FieldValue>& eventValues, size_t count = conditionDimension->getValues().size(); if (count != links.conditionFields.size()) { // ALOGE("WTF condition link is bad"); return; } Loading @@ -118,6 +118,26 @@ void getDimensionForCondition(const std::vector<FieldValue>& eventValues, } } void getDimensionForState(const std::vector<FieldValue>& eventValues, const Metric2State& link, HashableDimensionKey* statePrimaryKey) { // First, get the dimension from the event using the "what" fields from the // MetricStateLinks. filterValues(link.metricFields, eventValues, statePrimaryKey); // Then check that the statePrimaryKey size equals the number of state fields size_t count = statePrimaryKey->getValues().size(); if (count != link.stateFields.size()) { return; } // For each dimension Value in the statePrimaryKey, set the field and tag // using the state atom fields from MetricStateLinks. for (size_t i = 0; i < count; i++) { statePrimaryKey->mutableValue(i)->mField.setField(link.stateFields[i].mMatcher.getField()); statePrimaryKey->mutableValue(i)->mField.setTag(link.stateFields[i].mMatcher.getTag()); } } bool LessThan(const vector<FieldValue>& s1, const vector<FieldValue>& s2) { if (s1.size() != s2.size()) { return s1.size() < s2.size(); Loading Loading @@ -185,11 +205,11 @@ string HashableDimensionKey::toString() const { bool MetricDimensionKey::operator==(const MetricDimensionKey& that) const { return mDimensionKeyInWhat == that.getDimensionKeyInWhat() && mDimensionKeyInCondition == that.getDimensionKeyInCondition(); mStateValuesKey == that.getStateValuesKey(); }; string MetricDimensionKey::toString() const { return mDimensionKeyInWhat.toString() + mDimensionKeyInCondition.toString(); return mDimensionKeyInWhat.toString() + mStateValuesKey.toString(); } bool MetricDimensionKey::operator<(const MetricDimensionKey& that) const { Loading @@ -199,7 +219,7 @@ bool MetricDimensionKey::operator<(const MetricDimensionKey& that) const { return false; } return mDimensionKeyInCondition < that.getDimensionKeyInCondition(); return mStateValuesKey < that.getStateValuesKey(); } } // namespace statsd Loading
cmds/statsd/src/HashableDimensionKey.h +28 −16 Original line number Diff line number Diff line Loading @@ -34,6 +34,12 @@ struct Metric2Condition { std::vector<Matcher> conditionFields; }; struct Metric2State { int32_t stateAtomId; std::vector<Matcher> metricFields; std::vector<Matcher> stateFields; }; class HashableDimensionKey { public: explicit HashableDimensionKey(const std::vector<FieldValue>& values) { Loading Loading @@ -78,15 +84,14 @@ private: class MetricDimensionKey { public: explicit MetricDimensionKey(const HashableDimensionKey& dimensionKeyInWhat, const HashableDimensionKey& dimensionKeyInCondition) : mDimensionKeyInWhat(dimensionKeyInWhat), mDimensionKeyInCondition(dimensionKeyInCondition) {}; const HashableDimensionKey& stateValuesKey) : mDimensionKeyInWhat(dimensionKeyInWhat), mStateValuesKey(stateValuesKey){}; MetricDimensionKey(){}; MetricDimensionKey(const MetricDimensionKey& that) : mDimensionKeyInWhat(that.getDimensionKeyInWhat()), mDimensionKeyInCondition(that.getDimensionKeyInCondition()) {}; mStateValuesKey(that.getStateValuesKey()){}; MetricDimensionKey& operator=(const MetricDimensionKey& from) = default; Loading @@ -96,16 +101,16 @@ class MetricDimensionKey { return mDimensionKeyInWhat; } inline const HashableDimensionKey& getDimensionKeyInCondition() const { return mDimensionKeyInCondition; inline const HashableDimensionKey& getStateValuesKey() const { return mStateValuesKey; } inline void setDimensionKeyInCondition(const HashableDimensionKey& key) { mDimensionKeyInCondition = key; inline void setStateValuesKey(const HashableDimensionKey& key) { mStateValuesKey = key; } bool hasDimensionKeyInCondition() const { return mDimensionKeyInCondition.getValues().size() > 0; bool hasStateValuesKey() const { return mStateValuesKey.getValues().size() > 0; } bool operator==(const MetricDimensionKey& that) const; Loading @@ -114,7 +119,7 @@ class MetricDimensionKey { private: HashableDimensionKey mDimensionKeyInWhat; HashableDimensionKey mDimensionKeyInCondition; HashableDimensionKey mStateValuesKey; }; android::hash_t hashDimension(const HashableDimensionKey& key); Loading @@ -124,7 +129,7 @@ android::hash_t hashDimension(const HashableDimensionKey& key); * The value of the FieldValue is output. */ bool filterValues(const Matcher& matcherField, const std::vector<FieldValue>& values, Value* output); FieldValue* output); /** * Creating HashableDimensionKeys from FieldValues using matcher. Loading Loading @@ -152,6 +157,13 @@ void getDimensionForCondition(const std::vector<FieldValue>& eventValues, const Metric2Condition& links, HashableDimensionKey* conditionDimension); /** * Get dimension values using metric's "what" fields and fill statePrimaryKey's * mField information using "state" fields. */ void getDimensionForState(const std::vector<FieldValue>& eventValues, const Metric2State& link, HashableDimensionKey* statePrimaryKey); } // namespace statsd } // namespace os } // namespace android Loading @@ -172,7 +184,7 @@ template <> struct hash<MetricDimensionKey> { std::size_t operator()(const MetricDimensionKey& key) const { android::hash_t hash = hashDimension(key.getDimensionKeyInWhat()); hash = android::JenkinsHashMix(hash, hashDimension(key.getDimensionKeyInCondition())); hash = android::JenkinsHashMix(hash, hashDimension(key.getStateValuesKey())); return android::JenkinsHashWhiten(hash); } }; Loading
cmds/statsd/src/StatsLogProcessor.h +4 −3 Original line number Diff line number Diff line Loading @@ -263,9 +263,10 @@ private: FRIEND_TEST(MetricActivationE2eTest, TestCountMetricWithSameDeactivation); FRIEND_TEST(MetricActivationE2eTest, TestCountMetricWithTwoMetricsTwoDeactivations); FRIEND_TEST(CountMetricE2eTest, TestWithSimpleState); FRIEND_TEST(CountMetricE2eTest, TestWithMappedState); FRIEND_TEST(CountMetricE2eTest, TestWithMultipleStates); FRIEND_TEST(CountMetricE2eTest, TestSlicedState); FRIEND_TEST(CountMetricE2eTest, TestSlicedStateWithMap); FRIEND_TEST(CountMetricE2eTest, TestMultipleSlicedStates); FRIEND_TEST(CountMetricE2eTest, TestSlicedStateWithPrimaryFields); FRIEND_TEST(DurationMetricE2eTest, TestOneBucket); FRIEND_TEST(DurationMetricE2eTest, TestTwoBuckets); Loading
cmds/statsd/src/metrics/CountMetricProducer.cpp +19 −21 Original line number Diff line number Diff line Loading @@ -57,10 +57,9 @@ const int FIELD_ID_IS_ACTIVE = 14; const int FIELD_ID_DATA = 1; // for CountMetricData const int FIELD_ID_DIMENSION_IN_WHAT = 1; const int FIELD_ID_DIMENSION_IN_CONDITION = 2; const int FIELD_ID_SLICE_BY_STATE = 6; const int FIELD_ID_BUCKET_INFO = 3; const int FIELD_ID_DIMENSION_LEAF_IN_WHAT = 4; const int FIELD_ID_DIMENSION_LEAF_IN_CONDITION = 5; // for CountBucketInfo const int FIELD_ID_COUNT = 3; const int FIELD_ID_BUCKET_NUM = 4; Loading Loading @@ -102,7 +101,13 @@ CountMetricProducer::CountMetricProducer( mConditionSliced = true; } // TODO(tsaichristine): b/142124705 handle metric state links for (const auto& stateLink : metric.state_link()) { Metric2State ms; ms.stateAtomId = stateLink.state_atom_id(); translateFieldMatcher(stateLink.fields_in_what(), &ms.metricFields); translateFieldMatcher(stateLink.fields_in_state(), &ms.stateFields); mMetric2StateLinks.push_back(ms); } flushIfNeededLocked(startTimeNs); // Adjust start for partial bucket Loading Loading @@ -132,10 +137,9 @@ void CountMetricProducer::dumpStatesLocked(FILE* out, bool verbose) const { (unsigned long)mCurrentSlicedCounter->size()); if (verbose) { for (const auto& it : *mCurrentSlicedCounter) { fprintf(out, "\t(what)%s\t(condition)%s %lld\n", fprintf(out, "\t(what)%s\t(state)%s %lld\n", it.first.getDimensionKeyInWhat().toString().c_str(), it.first.getDimensionKeyInCondition().toString().c_str(), (unsigned long long)it.second); it.first.getStateValuesKey().toString().c_str(), (unsigned long long)it.second); } } } Loading Loading @@ -196,22 +200,16 @@ void CountMetricProducer::onDumpReportLocked(const int64_t dumpTimeNs, FIELD_TYPE_MESSAGE | FIELD_ID_DIMENSION_IN_WHAT); writeDimensionToProto(dimensionKey.getDimensionKeyInWhat(), str_set, protoOutput); protoOutput->end(dimensionToken); if (dimensionKey.hasDimensionKeyInCondition()) { uint64_t dimensionInConditionToken = protoOutput->start( FIELD_TYPE_MESSAGE | FIELD_ID_DIMENSION_IN_CONDITION); writeDimensionToProto(dimensionKey.getDimensionKeyInCondition(), str_set, protoOutput); protoOutput->end(dimensionInConditionToken); } } else { writeDimensionLeafNodesToProto(dimensionKey.getDimensionKeyInWhat(), FIELD_ID_DIMENSION_LEAF_IN_WHAT, str_set, protoOutput); if (dimensionKey.hasDimensionKeyInCondition()) { writeDimensionLeafNodesToProto(dimensionKey.getDimensionKeyInCondition(), FIELD_ID_DIMENSION_LEAF_IN_CONDITION, str_set, protoOutput); } // Then fill slice_by_state. for (auto state : dimensionKey.getStateValuesKey().getValues()) { uint64_t stateToken = protoOutput->start(FIELD_TYPE_MESSAGE | FIELD_COUNT_REPEATED | FIELD_ID_SLICE_BY_STATE); writeStateToProto(state, protoOutput); protoOutput->end(stateToken); } // Then fill bucket_info (CountBucketInfo). for (const auto& bucket : counter.second) { Loading Loading @@ -282,7 +280,7 @@ void CountMetricProducer::onMatchedLogEventInternalLocked( int64_t eventTimeNs = event.GetElapsedTimestampNs(); flushIfNeededLocked(eventTimeNs); if (condition == false) { if (!condition) { return; } Loading
cmds/statsd/src/metrics/CountMetricProducer.h +1 −1 Original line number Diff line number Diff line Loading @@ -52,7 +52,7 @@ public: virtual ~CountMetricProducer(); void onStateChanged(int atomId, const HashableDimensionKey& primaryKey, int oldState, void onStateChanged(int32_t atomId, const HashableDimensionKey& primaryKey, int oldState, int newState) override; protected: Loading