Partial Config Update: Matchers
There are two primary steps: 1. Determine which matchers to update 2. Perform the update Added unit tests Test: atest statsd_test Bug: 162322018 Change-Id: I6dbaeb781eef362e2d024a560904497a3525cad2
This commit is contained in:
@@ -85,8 +85,9 @@ cc_defaults {
|
||||
"src/metrics/EventMetricProducer.cpp",
|
||||
"src/metrics/GaugeMetricProducer.cpp",
|
||||
"src/metrics/MetricProducer.cpp",
|
||||
"src/metrics/metrics_manager_util.cpp",
|
||||
"src/metrics/MetricsManager.cpp",
|
||||
"src/metrics/parsing_utils/config_update_utils.cpp",
|
||||
"src/metrics/parsing_utils/metrics_manager_util.cpp",
|
||||
"src/metrics/ValueMetricProducer.cpp",
|
||||
"src/packages/UidMap.cpp",
|
||||
"src/shell/shell_config.proto",
|
||||
@@ -317,6 +318,8 @@ cc_test {
|
||||
"tests/metrics/metrics_test_helper.cpp",
|
||||
"tests/metrics/OringDurationTracker_test.cpp",
|
||||
"tests/metrics/ValueMetricProducer_test.cpp",
|
||||
"tests/metrics/parsing_utils/config_update_utils_test.cpp",
|
||||
"tests/metrics/parsing_utils/metrics_manager_util_test.cpp",
|
||||
"tests/MetricsManager_test.cpp",
|
||||
"tests/shell/ShellSubscriber_test.cpp",
|
||||
"tests/state/StateTracker_test.cpp",
|
||||
|
||||
@@ -533,7 +533,8 @@ void StatsLogProcessor::OnConfigUpdatedLocked(const int64_t timestampNs, const C
|
||||
}
|
||||
} else {
|
||||
// Preserve the existing MetricsManager, update necessary components and metadata in place.
|
||||
configValid = it->second->updateConfig(timestampNs, config);
|
||||
configValid = it->second->updateConfig(config, mTimeBaseNs, timestampNs,
|
||||
mAnomalyAlarmMonitor, mPeriodicAlarmMonitor);
|
||||
if (configValid) {
|
||||
// TODO(b/162323476): refresh TTL, ensure init() is handled properly.
|
||||
mUidMap->OnConfigUpdated(key);
|
||||
|
||||
@@ -22,6 +22,7 @@ namespace android {
|
||||
namespace os {
|
||||
namespace statsd {
|
||||
|
||||
// Uses murmur2 hashing algorithm.
|
||||
extern uint32_t Hash32(const char *data, size_t n, uint32_t seed);
|
||||
extern uint64_t Hash64(const char* data, size_t n, uint64_t seed);
|
||||
|
||||
|
||||
@@ -27,8 +27,9 @@ using std::set;
|
||||
using std::unordered_map;
|
||||
using std::vector;
|
||||
|
||||
CombinationLogMatchingTracker::CombinationLogMatchingTracker(const int64_t& id, const int index)
|
||||
: LogMatchingTracker(id, index) {
|
||||
CombinationLogMatchingTracker::CombinationLogMatchingTracker(const int64_t& id, const int index,
|
||||
const uint64_t protoHash)
|
||||
: LogMatchingTracker(id, index, protoHash) {
|
||||
}
|
||||
|
||||
CombinationLogMatchingTracker::~CombinationLogMatchingTracker() {
|
||||
|
||||
@@ -28,7 +28,7 @@ namespace statsd {
|
||||
// Represents a AtomMatcher_Combination in the StatsdConfig.
|
||||
class CombinationLogMatchingTracker : public virtual LogMatchingTracker {
|
||||
public:
|
||||
CombinationLogMatchingTracker(const int64_t& id, const int index);
|
||||
CombinationLogMatchingTracker(const int64_t& id, const int index, const uint64_t protoHash);
|
||||
|
||||
bool init(const std::vector<AtomMatcher>& allLogMatchers,
|
||||
const std::vector<sp<LogMatchingTracker>>& allTrackers,
|
||||
|
||||
@@ -33,8 +33,8 @@ namespace statsd {
|
||||
|
||||
class LogMatchingTracker : public virtual RefBase {
|
||||
public:
|
||||
LogMatchingTracker(const int64_t& id, const int index)
|
||||
: mId(id), mIndex(index), mInitialized(false){};
|
||||
LogMatchingTracker(const int64_t& id, const int index, const uint64_t protoHash)
|
||||
: mId(id), mIndex(index), mInitialized(false), mProtoHash(protoHash){};
|
||||
|
||||
virtual ~LogMatchingTracker(){};
|
||||
|
||||
@@ -69,10 +69,14 @@ public:
|
||||
return mAtomIds;
|
||||
}
|
||||
|
||||
const int64_t& getId() const {
|
||||
int64_t getId() const {
|
||||
return mId;
|
||||
}
|
||||
|
||||
uint64_t getProtoHash() const {
|
||||
return mProtoHash;
|
||||
}
|
||||
|
||||
protected:
|
||||
// Name of this matching. We don't really need the name, but it makes log message easy to debug.
|
||||
const int64_t mId;
|
||||
@@ -87,6 +91,14 @@ protected:
|
||||
// return kNotMatched when we receive an event with an id not in the list. This is especially
|
||||
// useful when we have a complex CombinationLogMatcherTracker.
|
||||
std::set<int> mAtomIds;
|
||||
|
||||
// Hash of the AtomMatcher's proto bytes from StatsdConfig.
|
||||
// Used to determine if the definition of this matcher has changed across a config update.
|
||||
const uint64_t mProtoHash;
|
||||
|
||||
FRIEND_TEST(MetricsManagerTest, TestCreateLogTrackerSimple);
|
||||
FRIEND_TEST(MetricsManagerTest, TestCreateLogTrackerCombination);
|
||||
FRIEND_TEST(ConfigUpdateTest, TestUpdateMatchers);
|
||||
};
|
||||
|
||||
} // namespace statsd
|
||||
|
||||
@@ -26,11 +26,11 @@ namespace statsd {
|
||||
using std::unordered_map;
|
||||
using std::vector;
|
||||
|
||||
|
||||
SimpleLogMatchingTracker::SimpleLogMatchingTracker(const int64_t& id, const int index,
|
||||
const uint64_t protoHash,
|
||||
const SimpleAtomMatcher& matcher,
|
||||
const UidMap& uidMap)
|
||||
: LogMatchingTracker(id, index), mMatcher(matcher), mUidMap(uidMap) {
|
||||
const sp<UidMap>& uidMap)
|
||||
: LogMatchingTracker(id, index, protoHash), mMatcher(matcher), mUidMap(uidMap) {
|
||||
if (!matcher.has_atom_id()) {
|
||||
mInitialized = false;
|
||||
} else {
|
||||
|
||||
@@ -29,9 +29,8 @@ namespace statsd {
|
||||
|
||||
class SimpleLogMatchingTracker : public virtual LogMatchingTracker {
|
||||
public:
|
||||
SimpleLogMatchingTracker(const int64_t& id, const int index,
|
||||
const SimpleAtomMatcher& matcher,
|
||||
const UidMap& uidMap);
|
||||
SimpleLogMatchingTracker(const int64_t& id, const int index, const uint64_t protoHash,
|
||||
const SimpleAtomMatcher& matcher, const sp<UidMap>& uidMap);
|
||||
|
||||
~SimpleLogMatchingTracker();
|
||||
|
||||
@@ -46,7 +45,7 @@ public:
|
||||
|
||||
private:
|
||||
const SimpleAtomMatcher mMatcher;
|
||||
const UidMap& mUidMap;
|
||||
const sp<UidMap> mUidMap;
|
||||
};
|
||||
|
||||
} // namespace statsd
|
||||
|
||||
@@ -81,14 +81,15 @@ bool combinationMatch(const vector<int>& children, const LogicalOperation& opera
|
||||
return matched;
|
||||
}
|
||||
|
||||
bool tryMatchString(const UidMap& uidMap, const FieldValue& fieldValue, const string& str_match) {
|
||||
bool tryMatchString(const sp<UidMap>& uidMap, const FieldValue& fieldValue,
|
||||
const string& str_match) {
|
||||
if (isAttributionUidField(fieldValue) || isUidField(fieldValue)) {
|
||||
int uid = fieldValue.mValue.int_value;
|
||||
auto aidIt = UidMap::sAidToUidMapping.find(str_match);
|
||||
if (aidIt != UidMap::sAidToUidMapping.end()) {
|
||||
return ((int)aidIt->second) == uid;
|
||||
}
|
||||
std::set<string> packageNames = uidMap.getAppNamesFromUid(uid, true /* normalize*/);
|
||||
std::set<string> packageNames = uidMap->getAppNamesFromUid(uid, true /* normalize*/);
|
||||
return packageNames.find(str_match) != packageNames.end();
|
||||
} else if (fieldValue.mValue.getType() == STRING) {
|
||||
return fieldValue.mValue.str_value == str_match;
|
||||
@@ -96,7 +97,7 @@ bool tryMatchString(const UidMap& uidMap, const FieldValue& fieldValue, const st
|
||||
return false;
|
||||
}
|
||||
|
||||
bool matchesSimple(const UidMap& uidMap, const FieldValueMatcher& matcher,
|
||||
bool matchesSimple(const sp<UidMap>& uidMap, const FieldValueMatcher& matcher,
|
||||
const vector<FieldValue>& values, int start, int end, int depth) {
|
||||
if (depth > 2) {
|
||||
ALOGE("Depth > 3 not supported");
|
||||
@@ -353,7 +354,7 @@ bool matchesSimple(const UidMap& uidMap, const FieldValueMatcher& matcher,
|
||||
}
|
||||
}
|
||||
|
||||
bool matchesSimple(const UidMap& uidMap, const SimpleAtomMatcher& simpleMatcher,
|
||||
bool matchesSimple(const sp<UidMap>& uidMap, const SimpleAtomMatcher& simpleMatcher,
|
||||
const LogEvent& event) {
|
||||
if (event.GetTagId() != simpleMatcher.atom_id()) {
|
||||
return false;
|
||||
|
||||
@@ -36,8 +36,8 @@ enum MatchingState {
|
||||
bool combinationMatch(const std::vector<int>& children, const LogicalOperation& operation,
|
||||
const std::vector<MatchingState>& matcherResults);
|
||||
|
||||
bool matchesSimple(const UidMap& uidMap,
|
||||
const SimpleAtomMatcher& simpleMatcher, const LogEvent& wrapper);
|
||||
bool matchesSimple(const sp<UidMap>& uidMap, const SimpleAtomMatcher& simpleMatcher,
|
||||
const LogEvent& wrapper);
|
||||
|
||||
} // namespace statsd
|
||||
} // namespace os
|
||||
|
||||
@@ -26,7 +26,8 @@
|
||||
#include "guardrail/StatsdStats.h"
|
||||
#include "matchers/CombinationLogMatchingTracker.h"
|
||||
#include "matchers/SimpleLogMatchingTracker.h"
|
||||
#include "metrics_manager_util.h"
|
||||
#include "parsing_utils/config_update_utils.h"
|
||||
#include "parsing_utils/metrics_manager_util.h"
|
||||
#include "state/StateManager.h"
|
||||
#include "stats_log_util.h"
|
||||
#include "stats_util.h"
|
||||
@@ -76,13 +77,14 @@ MetricsManager::MetricsManager(const ConfigKey& key, const StatsdConfig& config,
|
||||
// Init the ttl end timestamp.
|
||||
refreshTtl(timeBaseNs);
|
||||
|
||||
mConfigValid = initStatsdConfig(
|
||||
key, config, *uidMap, pullerManager, anomalyAlarmMonitor, periodicAlarmMonitor,
|
||||
timeBaseNs, currentTimeNs, mTagIds, mAllAtomMatchers, mAllConditionTrackers,
|
||||
mAllMetricProducers, mAllAnomalyTrackers, mAllPeriodicAlarmTrackers,
|
||||
mConditionToMetricMap, mTrackerToMetricMap, mTrackerToConditionMap,
|
||||
mActivationAtomTrackerToMetricMap, mDeactivationAtomTrackerToMetricMap,
|
||||
mAlertTrackerMap, mMetricIndexesWithActivation, mNoReportMetricIds);
|
||||
mConfigValid =
|
||||
initStatsdConfig(key, config, uidMap, pullerManager, anomalyAlarmMonitor,
|
||||
periodicAlarmMonitor, timeBaseNs, currentTimeNs, mTagIds,
|
||||
mAllAtomMatchers, mLogTrackerMap, mAllConditionTrackers,
|
||||
mAllMetricProducers, mAllAnomalyTrackers, mAllPeriodicAlarmTrackers,
|
||||
mConditionToMetricMap, mTrackerToMetricMap, mTrackerToConditionMap,
|
||||
mActivationAtomTrackerToMetricMap, mDeactivationAtomTrackerToMetricMap,
|
||||
mAlertTrackerMap, mMetricIndexesWithActivation, mNoReportMetricIds);
|
||||
|
||||
mHashStringsInReport = config.hash_strings_in_metric_report();
|
||||
mVersionStringsInReport = config.version_strings_in_metric_report();
|
||||
@@ -195,7 +197,19 @@ MetricsManager::~MetricsManager() {
|
||||
VLOG("~MetricsManager()");
|
||||
}
|
||||
|
||||
bool MetricsManager::updateConfig(const int64_t currentTimeNs, const StatsdConfig& config) {
|
||||
bool MetricsManager::updateConfig(const StatsdConfig& config, const int64_t timeBaseNs,
|
||||
const int64_t currentTimeNs,
|
||||
const sp<AlarmMonitor>& anomalyAlarmMonitor,
|
||||
const sp<AlarmMonitor>& periodicAlarmMonitor) {
|
||||
vector<sp<LogMatchingTracker>> newAtomMatchers;
|
||||
unordered_map<int64_t, int> newLogTrackerMap;
|
||||
mTagIds.clear();
|
||||
mConfigValid =
|
||||
updateStatsdConfig(mConfigKey, config, mUidMap, mPullerManager, anomalyAlarmMonitor,
|
||||
periodicAlarmMonitor, timeBaseNs, currentTimeNs, mAllAtomMatchers,
|
||||
mLogTrackerMap, mTagIds, newAtomMatchers, newLogTrackerMap);
|
||||
mAllAtomMatchers = newAtomMatchers;
|
||||
mLogTrackerMap = newLogTrackerMap;
|
||||
return mConfigValid;
|
||||
}
|
||||
|
||||
|
||||
@@ -46,7 +46,9 @@ public:
|
||||
|
||||
virtual ~MetricsManager();
|
||||
|
||||
bool updateConfig(const int64_t currentTimeNs, const StatsdConfig& config);
|
||||
bool updateConfig(const StatsdConfig& config, const int64_t timeBaseNs,
|
||||
const int64_t currentTimeNs, const sp<AlarmMonitor>& anomalyAlarmMonitor,
|
||||
const sp<AlarmMonitor>& periodicAlarmMonitor);
|
||||
|
||||
// Return whether the configuration is valid.
|
||||
bool isConfigValid() const;
|
||||
@@ -237,6 +239,12 @@ private:
|
||||
// Hold all periodic alarm trackers.
|
||||
std::vector<sp<AlarmTracker>> mAllPeriodicAlarmTrackers;
|
||||
|
||||
// To make updating configs faster, we map the id of a LogMatchingTracker, MetricProducer, and
|
||||
// ConditionTracker to its index in the corresponding vector.
|
||||
|
||||
// Maps the id of an atom matcher to its index in mAllAtomMatchers.
|
||||
std::unordered_map<int64_t, int> mLogTrackerMap;
|
||||
|
||||
// To make the log processing more efficient, we want to do as much filtering as possible
|
||||
// before we go into individual trackers and conditions to match.
|
||||
|
||||
|
||||
203
cmds/statsd/src/metrics/parsing_utils/config_update_utils.cpp
Normal file
203
cmds/statsd/src/metrics/parsing_utils/config_update_utils.cpp
Normal file
@@ -0,0 +1,203 @@
|
||||
/*
|
||||
* Copyright (C) 2020 The Android Open Source Project
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
#define DEBUG false // STOPSHIP if true
|
||||
|
||||
#include "config_update_utils.h"
|
||||
|
||||
#include "external/StatsPullerManager.h"
|
||||
#include "hash.h"
|
||||
#include "metrics_manager_util.h"
|
||||
|
||||
namespace android {
|
||||
namespace os {
|
||||
namespace statsd {
|
||||
|
||||
// Recursive function to determine if a matcher needs to be updated. Populates matcherToUpdate.
|
||||
// Returns whether the function was successful or not.
|
||||
bool determineMatcherUpdateStatus(const StatsdConfig& config, const int matcherIdx,
|
||||
const unordered_map<int64_t, int>& oldLogTrackerMap,
|
||||
const vector<sp<LogMatchingTracker>>& oldAtomMatchers,
|
||||
const unordered_map<int64_t, int>& newLogTrackerMap,
|
||||
vector<UpdateStatus>& matchersToUpdate,
|
||||
vector<bool>& cycleTracker) {
|
||||
// Have already examined this matcher.
|
||||
if (matchersToUpdate[matcherIdx] != UPDATE_UNKNOWN) {
|
||||
return true;
|
||||
}
|
||||
|
||||
const AtomMatcher& matcher = config.atom_matcher(matcherIdx);
|
||||
int64_t id = matcher.id();
|
||||
// Check if new matcher.
|
||||
const auto& oldLogTrackerIt = oldLogTrackerMap.find(id);
|
||||
if (oldLogTrackerIt == oldLogTrackerMap.end()) {
|
||||
matchersToUpdate[matcherIdx] = UPDATE_REPLACE;
|
||||
return true;
|
||||
}
|
||||
|
||||
// This is an existing matcher. Check if it has changed.
|
||||
string serializedMatcher;
|
||||
if (!matcher.SerializeToString(&serializedMatcher)) {
|
||||
ALOGE("Unable to serialize matcher %lld", (long long)id);
|
||||
return false;
|
||||
}
|
||||
uint64_t newProtoHash = Hash64(serializedMatcher);
|
||||
if (newProtoHash != oldAtomMatchers[oldLogTrackerIt->second]->getProtoHash()) {
|
||||
matchersToUpdate[matcherIdx] = UPDATE_REPLACE;
|
||||
return true;
|
||||
}
|
||||
|
||||
switch (matcher.contents_case()) {
|
||||
case AtomMatcher::ContentsCase::kSimpleAtomMatcher: {
|
||||
matchersToUpdate[matcherIdx] = UPDATE_PRESERVE;
|
||||
return true;
|
||||
}
|
||||
case AtomMatcher::ContentsCase::kCombination: {
|
||||
// Recurse to check if children have changed.
|
||||
cycleTracker[matcherIdx] = true;
|
||||
UpdateStatus status = UPDATE_PRESERVE;
|
||||
for (const int64_t childMatcherId : matcher.combination().matcher()) {
|
||||
const auto& childIt = newLogTrackerMap.find(childMatcherId);
|
||||
if (childIt == newLogTrackerMap.end()) {
|
||||
ALOGW("Matcher %lld not found in the config", (long long)childMatcherId);
|
||||
return false;
|
||||
}
|
||||
const int childIdx = childIt->second;
|
||||
if (cycleTracker[childIdx]) {
|
||||
ALOGE("Cycle detected in matcher config");
|
||||
return false;
|
||||
}
|
||||
if (!determineMatcherUpdateStatus(config, childIdx, oldLogTrackerMap,
|
||||
oldAtomMatchers, newLogTrackerMap,
|
||||
matchersToUpdate, cycleTracker)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (matchersToUpdate[childIdx] == UPDATE_REPLACE) {
|
||||
status = UPDATE_REPLACE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
matchersToUpdate[matcherIdx] = status;
|
||||
cycleTracker[matcherIdx] = false;
|
||||
return true;
|
||||
}
|
||||
default: {
|
||||
ALOGE("Matcher \"%lld\" malformed", (long long)id);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool updateLogTrackers(const StatsdConfig& config, const sp<UidMap>& uidMap,
|
||||
const unordered_map<int64_t, int>& oldLogTrackerMap,
|
||||
const vector<sp<LogMatchingTracker>>& oldAtomMatchers, set<int>& allTagIds,
|
||||
unordered_map<int64_t, int>& newLogTrackerMap,
|
||||
vector<sp<LogMatchingTracker>>& newAtomMatchers) {
|
||||
const int atomMatcherCount = config.atom_matcher_size();
|
||||
|
||||
vector<AtomMatcher> matcherProtos;
|
||||
matcherProtos.reserve(atomMatcherCount);
|
||||
newAtomMatchers.reserve(atomMatcherCount);
|
||||
|
||||
// Maps matcher id to their position in the config. For fast lookup of dependencies.
|
||||
for (int i = 0; i < atomMatcherCount; i++) {
|
||||
const AtomMatcher& matcher = config.atom_matcher(i);
|
||||
if (newLogTrackerMap.find(matcher.id()) != newLogTrackerMap.end()) {
|
||||
ALOGE("Duplicate atom matcher found for id %lld", (long long)matcher.id());
|
||||
return false;
|
||||
}
|
||||
newLogTrackerMap[matcher.id()] = i;
|
||||
matcherProtos.push_back(matcher);
|
||||
}
|
||||
|
||||
// For combination matchers, we need to determine if any children need to be updated.
|
||||
vector<UpdateStatus> matchersToUpdate(atomMatcherCount, UPDATE_UNKNOWN);
|
||||
vector<bool> cycleTracker(atomMatcherCount, false);
|
||||
for (int i = 0; i < atomMatcherCount; i++) {
|
||||
if (!determineMatcherUpdateStatus(config, i, oldLogTrackerMap, oldAtomMatchers,
|
||||
newLogTrackerMap, matchersToUpdate, cycleTracker)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
for (int i = 0; i < atomMatcherCount; i++) {
|
||||
const AtomMatcher& matcher = config.atom_matcher(i);
|
||||
const int64_t id = matcher.id();
|
||||
switch (matchersToUpdate[i]) {
|
||||
case UPDATE_PRESERVE: {
|
||||
const auto& oldLogTrackerIt = oldLogTrackerMap.find(id);
|
||||
if (oldLogTrackerIt == oldLogTrackerMap.end()) {
|
||||
ALOGE("Could not find AtomMatcher %lld in the previous config, but expected it "
|
||||
"to be there",
|
||||
(long long)id);
|
||||
return false;
|
||||
}
|
||||
const int oldIndex = oldLogTrackerIt->second;
|
||||
newAtomMatchers.push_back(oldAtomMatchers[oldIndex]);
|
||||
break;
|
||||
}
|
||||
case UPDATE_REPLACE: {
|
||||
sp<LogMatchingTracker> tracker = createLogTracker(matcher, i, uidMap);
|
||||
if (tracker == nullptr) {
|
||||
return false;
|
||||
}
|
||||
newAtomMatchers.push_back(tracker);
|
||||
break;
|
||||
}
|
||||
default: {
|
||||
ALOGE("Matcher \"%lld\" update state is unknown. This should never happen",
|
||||
(long long)id);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
std::fill(cycleTracker.begin(), cycleTracker.end(), false);
|
||||
for (auto& matcher : newAtomMatchers) {
|
||||
if (!matcher->init(matcherProtos, newAtomMatchers, newLogTrackerMap, cycleTracker)) {
|
||||
return false;
|
||||
}
|
||||
// Collect all the tag ids that are interesting. TagIds exist in leaf nodes only.
|
||||
const set<int>& tagIds = matcher->getAtomIds();
|
||||
allTagIds.insert(tagIds.begin(), tagIds.end());
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool updateStatsdConfig(const ConfigKey& key, const StatsdConfig& config, const sp<UidMap>& uidMap,
|
||||
const sp<StatsPullerManager>& pullerManager,
|
||||
const sp<AlarmMonitor>& anomalyAlarmMonitor,
|
||||
const sp<AlarmMonitor>& periodicAlarmMonitor, const int64_t timeBaseNs,
|
||||
const int64_t currentTimeNs,
|
||||
const vector<sp<LogMatchingTracker>>& oldAtomMatchers,
|
||||
const unordered_map<int64_t, int>& oldLogTrackerMap, set<int>& allTagIds,
|
||||
vector<sp<LogMatchingTracker>>& newAtomMatchers,
|
||||
unordered_map<int64_t, int>& newLogTrackerMap) {
|
||||
if (!updateLogTrackers(config, uidMap, oldLogTrackerMap, oldAtomMatchers, allTagIds,
|
||||
newLogTrackerMap, newAtomMatchers)) {
|
||||
ALOGE("updateLogMatchingTrackers failed");
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
} // namespace statsd
|
||||
} // namespace os
|
||||
} // namespace android
|
||||
89
cmds/statsd/src/metrics/parsing_utils/config_update_utils.h
Normal file
89
cmds/statsd/src/metrics/parsing_utils/config_update_utils.h
Normal file
@@ -0,0 +1,89 @@
|
||||
/*
|
||||
* Copyright (C) 2020 The Android Open Source Project
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <vector>
|
||||
|
||||
#include "anomaly/AlarmMonitor.h"
|
||||
#include "external/StatsPullerManager.h"
|
||||
#include "matchers/LogMatchingTracker.h"
|
||||
|
||||
namespace android {
|
||||
namespace os {
|
||||
namespace statsd {
|
||||
|
||||
// Helper functions for MetricsManager to update itself from a new StatsdConfig.
|
||||
// *Note*: only updateStatsdConfig() should be called from outside this file.
|
||||
// All other functions are intermediate steps, created to make unit testing easier.
|
||||
|
||||
// Possible update states for a component. PRESERVE means we should keep the existing one.
|
||||
// REPLACE means we should create a new one, either because it didn't exist or it changed.
|
||||
enum UpdateStatus {
|
||||
UPDATE_UNKNOWN = 0,
|
||||
UPDATE_PRESERVE = 1,
|
||||
UPDATE_REPLACE = 2,
|
||||
};
|
||||
|
||||
// Recursive function to determine if a matcher needs to be updated.
|
||||
// input:
|
||||
// [config]: the input StatsdConfig
|
||||
// [matcherIdx]: the index of the current matcher to be updated
|
||||
// [newLogTrackerMap]: matcher id to index mapping in the input StatsdConfig
|
||||
// [oldLogTrackerMap]: matcher id to index mapping in the existing MetricsManager
|
||||
// [oldAtomMatchers]: stores the existing LogMatchingTrackers
|
||||
// output:
|
||||
// [matchersToUpdate]: vector of the update status of each matcher. The matcherIdx index will
|
||||
// be updated from UPDATE_UNKNOWN after this call.
|
||||
// [cycleTracker]: intermediate param used during recursion.
|
||||
bool determineMatcherUpdateStatus(const StatsdConfig& config, const int matcherIdx,
|
||||
const unordered_map<int64_t, int>& oldLogTrackerMap,
|
||||
const vector<sp<LogMatchingTracker>>& oldAtomMatchers,
|
||||
const unordered_map<int64_t, int>& newLogTrackerMap,
|
||||
vector<UpdateStatus>& matchersToUpdate,
|
||||
vector<bool>& cycleTracker);
|
||||
|
||||
// Updates the LogMatchingTrackers.
|
||||
// input:
|
||||
// [config]: the input StatsdConfig
|
||||
// [oldLogTrackerMap]: existing matcher id to index mapping
|
||||
// [oldAtomMatchers]: stores the existing LogMatchingTrackers
|
||||
// output:
|
||||
// [allTagIds]: contains the set of all interesting tag ids to this config.
|
||||
// [newLogTrackerMap]: new matcher id to index mapping
|
||||
// [newAtomMatchers]: stores the new LogMatchingTrackers
|
||||
bool updateLogTrackers(const StatsdConfig& config, const sp<UidMap>& uidMap,
|
||||
const unordered_map<int64_t, int>& oldLogTrackerMap,
|
||||
const vector<sp<LogMatchingTracker>>& oldAtomMatchers, set<int>& allTagIds,
|
||||
unordered_map<int64_t, int>& newLogTrackerMap,
|
||||
vector<sp<LogMatchingTracker>>& newAtomMatchers);
|
||||
|
||||
// Updates the existing MetricsManager from a new StatsdConfig.
|
||||
// Parameters are the members of MetricsManager. See MetricsManager for declaration.
|
||||
bool updateStatsdConfig(const ConfigKey& key, const StatsdConfig& config, const sp<UidMap>& uidMap,
|
||||
const sp<StatsPullerManager>& pullerManager,
|
||||
const sp<AlarmMonitor>& anomalyAlarmMonitor,
|
||||
const sp<AlarmMonitor>& periodicAlarmMonitor, const int64_t timeBaseNs,
|
||||
const int64_t currentTimeNs,
|
||||
const std::vector<sp<LogMatchingTracker>>& oldAtomMatchers,
|
||||
const unordered_map<int64_t, int>& oldLogTrackerMap,
|
||||
std::set<int>& allTagIds,
|
||||
std::vector<sp<LogMatchingTracker>>& newAtomMatchers,
|
||||
unordered_map<int64_t, int>& newLogTrackerMap);
|
||||
|
||||
} // namespace statsd
|
||||
} // namespace os
|
||||
} // namespace android
|
||||
@@ -22,10 +22,10 @@
|
||||
#include <inttypes.h>
|
||||
|
||||
#include "FieldValue.h"
|
||||
#include "MetricProducer.h"
|
||||
#include "condition/CombinationConditionTracker.h"
|
||||
#include "condition/SimpleConditionTracker.h"
|
||||
#include "external/StatsPullerManager.h"
|
||||
#include "hash.h"
|
||||
#include "matchers/CombinationLogMatchingTracker.h"
|
||||
#include "matchers/EventMatcherWizard.h"
|
||||
#include "matchers/SimpleLogMatchingTracker.h"
|
||||
@@ -33,6 +33,7 @@
|
||||
#include "metrics/DurationMetricProducer.h"
|
||||
#include "metrics/EventMetricProducer.h"
|
||||
#include "metrics/GaugeMetricProducer.h"
|
||||
#include "metrics/MetricProducer.h"
|
||||
#include "metrics/ValueMetricProducer.h"
|
||||
#include "state/StateManager.h"
|
||||
#include "stats_util.h"
|
||||
@@ -61,6 +62,28 @@ bool hasLeafNode(const FieldMatcher& matcher) {
|
||||
|
||||
} // namespace
|
||||
|
||||
sp<LogMatchingTracker> createLogTracker(const AtomMatcher& logMatcher, const int index,
|
||||
const sp<UidMap>& uidMap) {
|
||||
string serializedMatcher;
|
||||
if (!logMatcher.SerializeToString(&serializedMatcher)) {
|
||||
ALOGE("Unable to serialize matcher %lld", (long long)logMatcher.id());
|
||||
return nullptr;
|
||||
}
|
||||
uint64_t protoHash = Hash64(serializedMatcher);
|
||||
switch (logMatcher.contents_case()) {
|
||||
case AtomMatcher::ContentsCase::kSimpleAtomMatcher:
|
||||
return new SimpleLogMatchingTracker(logMatcher.id(), index, protoHash,
|
||||
logMatcher.simple_atom_matcher(), uidMap);
|
||||
break;
|
||||
case AtomMatcher::ContentsCase::kCombination:
|
||||
return new CombinationLogMatchingTracker(logMatcher.id(), index, protoHash);
|
||||
break;
|
||||
default:
|
||||
ALOGE("Matcher \"%lld\" malformed", (long long)logMatcher.id());
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
bool handleMetricWithLogTrackers(const int64_t what, const int metricIndex,
|
||||
const bool usedForDimension,
|
||||
const vector<sp<LogMatchingTracker>>& allAtomMatchers,
|
||||
@@ -184,9 +207,7 @@ bool handleMetricWithStateLink(const FieldMatcher& stateMatcher,
|
||||
// to provide the producer with state about its activators and deactivators.
|
||||
// Returns false if there are errors.
|
||||
bool handleMetricActivation(
|
||||
const StatsdConfig& config,
|
||||
const int64_t metricId,
|
||||
const int metricIndex,
|
||||
const StatsdConfig& config, const int64_t metricId, const int metricIndex,
|
||||
const unordered_map<int64_t, int>& metricToActivationMap,
|
||||
const unordered_map<int64_t, int>& logTrackerMap,
|
||||
unordered_map<int, vector<int>>& activationAtomTrackerToMetricMap,
|
||||
@@ -210,10 +231,11 @@ bool handleMetricActivation(
|
||||
return false;
|
||||
}
|
||||
|
||||
ActivationType activationType = (activation.has_activation_type()) ?
|
||||
activation.activation_type() : metricActivation.activation_type();
|
||||
std::shared_ptr<Activation> activationWrapper = std::make_shared<Activation>(
|
||||
activationType, activation.ttl_seconds() * NS_PER_SEC);
|
||||
ActivationType activationType = (activation.has_activation_type())
|
||||
? activation.activation_type()
|
||||
: metricActivation.activation_type();
|
||||
std::shared_ptr<Activation> activationWrapper =
|
||||
std::make_shared<Activation>(activationType, activation.ttl_seconds() * NS_PER_SEC);
|
||||
|
||||
int atomMatcherIndex = itr->second;
|
||||
activationAtomTrackerToMetricMap[atomMatcherIndex].push_back(metricIndex);
|
||||
@@ -235,7 +257,7 @@ bool handleMetricActivation(
|
||||
return true;
|
||||
}
|
||||
|
||||
bool initLogTrackers(const StatsdConfig& config, const UidMap& uidMap,
|
||||
bool initLogTrackers(const StatsdConfig& config, const sp<UidMap>& uidMap,
|
||||
unordered_map<int64_t, int>& logTrackerMap,
|
||||
vector<sp<LogMatchingTracker>>& allAtomMatchers, set<int>& allTagIds) {
|
||||
vector<AtomMatcher> matcherConfigs;
|
||||
@@ -245,22 +267,12 @@ bool initLogTrackers(const StatsdConfig& config, const UidMap& uidMap,
|
||||
|
||||
for (int i = 0; i < atomMatcherCount; i++) {
|
||||
const AtomMatcher& logMatcher = config.atom_matcher(i);
|
||||
|
||||
int index = allAtomMatchers.size();
|
||||
switch (logMatcher.contents_case()) {
|
||||
case AtomMatcher::ContentsCase::kSimpleAtomMatcher:
|
||||
allAtomMatchers.push_back(new SimpleLogMatchingTracker(
|
||||
logMatcher.id(), index, logMatcher.simple_atom_matcher(), uidMap));
|
||||
break;
|
||||
case AtomMatcher::ContentsCase::kCombination:
|
||||
allAtomMatchers.push_back(
|
||||
new CombinationLogMatchingTracker(logMatcher.id(), index));
|
||||
break;
|
||||
default:
|
||||
ALOGE("Matcher \"%lld\" malformed", (long long)logMatcher.id());
|
||||
return false;
|
||||
// continue;
|
||||
sp<LogMatchingTracker> tracker = createLogTracker(logMatcher, index, uidMap);
|
||||
if (tracker == nullptr) {
|
||||
return false;
|
||||
}
|
||||
allAtomMatchers.push_back(tracker);
|
||||
if (logTrackerMap.find(logMatcher.id()) != logTrackerMap.end()) {
|
||||
ALOGE("Duplicate AtomMatcher found!");
|
||||
return false;
|
||||
@@ -383,7 +395,7 @@ bool initMetrics(const ConfigKey& key, const StatsdConfig& config, const int64_t
|
||||
const MetricActivation& metricActivation = config.metric_activation(i);
|
||||
int64_t metricId = metricActivation.metric_id();
|
||||
if (metricToActivationMap.find(metricId) != metricToActivationMap.end()) {
|
||||
ALOGE("Metric %lld has multiple MetricActivations", (long long) metricId);
|
||||
ALOGE("Metric %lld has multiple MetricActivations", (long long)metricId);
|
||||
return false;
|
||||
}
|
||||
metricToActivationMap.insert({metricId, i});
|
||||
@@ -402,9 +414,8 @@ bool initMetrics(const ConfigKey& key, const StatsdConfig& config, const int64_t
|
||||
metricMap.insert({metric.id(), metricIndex});
|
||||
int trackerIndex;
|
||||
if (!handleMetricWithLogTrackers(metric.what(), metricIndex,
|
||||
metric.has_dimensions_in_what(),
|
||||
allAtomMatchers, logTrackerMap, trackerToMetricMap,
|
||||
trackerIndex)) {
|
||||
metric.has_dimensions_in_what(), allAtomMatchers,
|
||||
logTrackerMap, trackerToMetricMap, trackerIndex)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -438,10 +449,10 @@ bool initMetrics(const ConfigKey& key, const StatsdConfig& config, const int64_t
|
||||
|
||||
unordered_map<int, shared_ptr<Activation>> eventActivationMap;
|
||||
unordered_map<int, vector<shared_ptr<Activation>>> eventDeactivationMap;
|
||||
bool success = handleMetricActivation(config, metric.id(), metricIndex,
|
||||
metricToActivationMap, logTrackerMap, activationAtomTrackerToMetricMap,
|
||||
deactivationAtomTrackerToMetricMap, metricsWithActivation, eventActivationMap,
|
||||
eventDeactivationMap);
|
||||
bool success = handleMetricActivation(
|
||||
config, metric.id(), metricIndex, metricToActivationMap, logTrackerMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap,
|
||||
metricsWithActivation, eventActivationMap, eventDeactivationMap);
|
||||
if (!success) return false;
|
||||
|
||||
sp<MetricProducer> countProducer =
|
||||
@@ -544,10 +555,10 @@ bool initMetrics(const ConfigKey& key, const StatsdConfig& config, const int64_t
|
||||
|
||||
unordered_map<int, shared_ptr<Activation>> eventActivationMap;
|
||||
unordered_map<int, vector<shared_ptr<Activation>>> eventDeactivationMap;
|
||||
bool success = handleMetricActivation(config, metric.id(), metricIndex,
|
||||
metricToActivationMap, logTrackerMap, activationAtomTrackerToMetricMap,
|
||||
deactivationAtomTrackerToMetricMap, metricsWithActivation, eventActivationMap,
|
||||
eventDeactivationMap);
|
||||
bool success = handleMetricActivation(
|
||||
config, metric.id(), metricIndex, metricToActivationMap, logTrackerMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap,
|
||||
metricsWithActivation, eventActivationMap, eventDeactivationMap);
|
||||
if (!success) return false;
|
||||
|
||||
sp<MetricProducer> durationMetric = new DurationMetricProducer(
|
||||
@@ -591,10 +602,10 @@ bool initMetrics(const ConfigKey& key, const StatsdConfig& config, const int64_t
|
||||
|
||||
unordered_map<int, shared_ptr<Activation>> eventActivationMap;
|
||||
unordered_map<int, vector<shared_ptr<Activation>>> eventDeactivationMap;
|
||||
bool success = handleMetricActivation(config, metric.id(), metricIndex,
|
||||
metricToActivationMap, logTrackerMap, activationAtomTrackerToMetricMap,
|
||||
deactivationAtomTrackerToMetricMap, metricsWithActivation, eventActivationMap,
|
||||
eventDeactivationMap);
|
||||
bool success = handleMetricActivation(
|
||||
config, metric.id(), metricIndex, metricToActivationMap, logTrackerMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap,
|
||||
metricsWithActivation, eventActivationMap, eventDeactivationMap);
|
||||
if (!success) return false;
|
||||
|
||||
sp<MetricProducer> eventMetric =
|
||||
@@ -626,9 +637,8 @@ bool initMetrics(const ConfigKey& key, const StatsdConfig& config, const int64_t
|
||||
metricMap.insert({metric.id(), metricIndex});
|
||||
int trackerIndex;
|
||||
if (!handleMetricWithLogTrackers(metric.what(), metricIndex,
|
||||
metric.has_dimensions_in_what(),
|
||||
allAtomMatchers, logTrackerMap, trackerToMetricMap,
|
||||
trackerIndex)) {
|
||||
metric.has_dimensions_in_what(), allAtomMatchers,
|
||||
logTrackerMap, trackerToMetricMap, trackerIndex)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -718,9 +728,8 @@ bool initMetrics(const ConfigKey& key, const StatsdConfig& config, const int64_t
|
||||
metricMap.insert({metric.id(), metricIndex});
|
||||
int trackerIndex;
|
||||
if (!handleMetricWithLogTrackers(metric.what(), metricIndex,
|
||||
metric.has_dimensions_in_what(),
|
||||
allAtomMatchers, logTrackerMap, trackerToMetricMap,
|
||||
trackerIndex)) {
|
||||
metric.has_dimensions_in_what(), allAtomMatchers,
|
||||
logTrackerMap, trackerToMetricMap, trackerIndex)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -775,10 +784,10 @@ bool initMetrics(const ConfigKey& key, const StatsdConfig& config, const int64_t
|
||||
|
||||
unordered_map<int, shared_ptr<Activation>> eventActivationMap;
|
||||
unordered_map<int, vector<shared_ptr<Activation>>> eventDeactivationMap;
|
||||
bool success = handleMetricActivation(config, metric.id(), metricIndex,
|
||||
metricToActivationMap, logTrackerMap, activationAtomTrackerToMetricMap,
|
||||
deactivationAtomTrackerToMetricMap, metricsWithActivation, eventActivationMap,
|
||||
eventDeactivationMap);
|
||||
bool success = handleMetricActivation(
|
||||
config, metric.id(), metricIndex, metricToActivationMap, logTrackerMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap,
|
||||
metricsWithActivation, eventActivationMap, eventDeactivationMap);
|
||||
if (!success) return false;
|
||||
|
||||
sp<MetricProducer> gaugeProducer = new GaugeMetricProducer(
|
||||
@@ -813,8 +822,7 @@ bool initMetrics(const ConfigKey& key, const StatsdConfig& config, const int64_t
|
||||
return true;
|
||||
}
|
||||
|
||||
bool initAlerts(const StatsdConfig& config,
|
||||
const unordered_map<int64_t, int>& metricProducerMap,
|
||||
bool initAlerts(const StatsdConfig& config, const unordered_map<int64_t, int>& metricProducerMap,
|
||||
unordered_map<int64_t, int>& alertTrackerMap,
|
||||
const sp<AlarmMonitor>& anomalyAlarmMonitor,
|
||||
vector<sp<MetricProducer>>& allMetricProducers,
|
||||
@@ -832,8 +840,8 @@ bool initAlerts(const StatsdConfig& config,
|
||||
return false;
|
||||
}
|
||||
if (alert.trigger_if_sum_gt() < 0 || alert.num_buckets() <= 0) {
|
||||
ALOGW("invalid alert: threshold=%f num_buckets= %d",
|
||||
alert.trigger_if_sum_gt(), alert.num_buckets());
|
||||
ALOGW("invalid alert: threshold=%f num_buckets= %d", alert.trigger_if_sum_gt(),
|
||||
alert.num_buckets());
|
||||
return false;
|
||||
}
|
||||
const int metricIndex = itr->second;
|
||||
@@ -853,14 +861,13 @@ bool initAlerts(const StatsdConfig& config,
|
||||
}
|
||||
if (subscription.subscriber_information_case() ==
|
||||
Subscription::SubscriberInformationCase::SUBSCRIBER_INFORMATION_NOT_SET) {
|
||||
ALOGW("subscription \"%lld\" has no subscriber info.\"",
|
||||
(long long)subscription.id());
|
||||
ALOGW("subscription \"%lld\" has no subscriber info.\"", (long long)subscription.id());
|
||||
return false;
|
||||
}
|
||||
const auto& itr = alertTrackerMap.find(subscription.rule_id());
|
||||
if (itr == alertTrackerMap.end()) {
|
||||
ALOGW("subscription \"%lld\" has unknown rule id: \"%lld\"",
|
||||
(long long)subscription.id(), (long long)subscription.rule_id());
|
||||
(long long)subscription.id(), (long long)subscription.rule_id());
|
||||
return false;
|
||||
}
|
||||
const int anomalyTrackerIndex = itr->second;
|
||||
@@ -870,12 +877,11 @@ bool initAlerts(const StatsdConfig& config,
|
||||
}
|
||||
|
||||
bool initAlarms(const StatsdConfig& config, const ConfigKey& key,
|
||||
const sp<AlarmMonitor>& periodicAlarmMonitor,
|
||||
const int64_t timeBaseNs, const int64_t currentTimeNs,
|
||||
vector<sp<AlarmTracker>>& allAlarmTrackers) {
|
||||
const sp<AlarmMonitor>& periodicAlarmMonitor, const int64_t timeBaseNs,
|
||||
const int64_t currentTimeNs, vector<sp<AlarmTracker>>& allAlarmTrackers) {
|
||||
unordered_map<int64_t, int> alarmTrackerMap;
|
||||
int64_t startMillis = timeBaseNs / 1000 / 1000;
|
||||
int64_t currentTimeMillis = currentTimeNs / 1000 /1000;
|
||||
int64_t currentTimeMillis = currentTimeNs / 1000 / 1000;
|
||||
for (int i = 0; i < config.alarm_size(); i++) {
|
||||
const Alarm& alarm = config.alarm(i);
|
||||
if (alarm.offset_millis() <= 0) {
|
||||
@@ -888,8 +894,7 @@ bool initAlarms(const StatsdConfig& config, const ConfigKey& key,
|
||||
}
|
||||
alarmTrackerMap.insert(std::make_pair(alarm.id(), allAlarmTrackers.size()));
|
||||
allAlarmTrackers.push_back(
|
||||
new AlarmTracker(startMillis, currentTimeMillis,
|
||||
alarm, key, periodicAlarmMonitor));
|
||||
new AlarmTracker(startMillis, currentTimeMillis, alarm, key, periodicAlarmMonitor));
|
||||
}
|
||||
for (int i = 0; i < config.subscription_size(); ++i) {
|
||||
const Subscription& subscription = config.subscription(i);
|
||||
@@ -898,14 +903,13 @@ bool initAlarms(const StatsdConfig& config, const ConfigKey& key,
|
||||
}
|
||||
if (subscription.subscriber_information_case() ==
|
||||
Subscription::SubscriberInformationCase::SUBSCRIBER_INFORMATION_NOT_SET) {
|
||||
ALOGW("subscription \"%lld\" has no subscriber info.\"",
|
||||
(long long)subscription.id());
|
||||
ALOGW("subscription \"%lld\" has no subscriber info.\"", (long long)subscription.id());
|
||||
return false;
|
||||
}
|
||||
const auto& itr = alarmTrackerMap.find(subscription.rule_id());
|
||||
if (itr == alarmTrackerMap.end()) {
|
||||
ALOGW("subscription \"%lld\" has unknown rule id: \"%lld\"",
|
||||
(long long)subscription.id(), (long long)subscription.rule_id());
|
||||
(long long)subscription.id(), (long long)subscription.rule_id());
|
||||
return false;
|
||||
}
|
||||
const int trackerIndex = itr->second;
|
||||
@@ -914,12 +918,13 @@ bool initAlarms(const StatsdConfig& config, const ConfigKey& key,
|
||||
return true;
|
||||
}
|
||||
|
||||
bool initStatsdConfig(const ConfigKey& key, const StatsdConfig& config, UidMap& uidMap,
|
||||
bool initStatsdConfig(const ConfigKey& key, const StatsdConfig& config, const sp<UidMap>& uidMap,
|
||||
const sp<StatsPullerManager>& pullerManager,
|
||||
const sp<AlarmMonitor>& anomalyAlarmMonitor,
|
||||
const sp<AlarmMonitor>& periodicAlarmMonitor, const int64_t timeBaseNs,
|
||||
const int64_t currentTimeNs, set<int>& allTagIds,
|
||||
vector<sp<LogMatchingTracker>>& allAtomMatchers,
|
||||
unordered_map<int64_t, int>& logTrackerMap,
|
||||
vector<sp<ConditionTracker>>& allConditionTrackers,
|
||||
vector<sp<MetricProducer>>& allMetricProducers,
|
||||
vector<sp<AnomalyTracker>>& allAnomalyTrackers,
|
||||
@@ -930,9 +935,7 @@ bool initStatsdConfig(const ConfigKey& key, const StatsdConfig& config, UidMap&
|
||||
unordered_map<int, std::vector<int>>& activationAtomTrackerToMetricMap,
|
||||
unordered_map<int, std::vector<int>>& deactivationAtomTrackerToMetricMap,
|
||||
unordered_map<int64_t, int>& alertTrackerMap,
|
||||
vector<int>& metricsWithActivation,
|
||||
std::set<int64_t>& noReportMetricIds) {
|
||||
unordered_map<int64_t, int> logTrackerMap;
|
||||
vector<int>& metricsWithActivation, std::set<int64_t>& noReportMetricIds) {
|
||||
unordered_map<int64_t, int> conditionTrackerMap;
|
||||
vector<ConditionState> initialConditionCache;
|
||||
unordered_map<int64_t, int> metricProducerMap;
|
||||
@@ -969,8 +972,8 @@ bool initStatsdConfig(const ConfigKey& key, const StatsdConfig& config, UidMap&
|
||||
ALOGE("initAlerts failed");
|
||||
return false;
|
||||
}
|
||||
if (!initAlarms(config, key, periodicAlarmMonitor,
|
||||
timeBaseNs, currentTimeNs, allPeriodicAlarmTrackers)) {
|
||||
if (!initAlarms(config, key, periodicAlarmMonitor, timeBaseNs, currentTimeNs,
|
||||
allPeriodicAlarmTrackers)) {
|
||||
ALOGE("initAlarms failed");
|
||||
return false;
|
||||
}
|
||||
@@ -20,16 +20,28 @@
|
||||
#include <unordered_map>
|
||||
#include <vector>
|
||||
|
||||
#include "../anomaly/AlarmTracker.h"
|
||||
#include "../condition/ConditionTracker.h"
|
||||
#include "../external/StatsPullerManager.h"
|
||||
#include "../matchers/LogMatchingTracker.h"
|
||||
#include "../metrics/MetricProducer.h"
|
||||
#include "anomaly/AlarmTracker.h"
|
||||
#include "condition/ConditionTracker.h"
|
||||
#include "external/StatsPullerManager.h"
|
||||
#include "matchers/LogMatchingTracker.h"
|
||||
#include "metrics/MetricProducer.h"
|
||||
|
||||
namespace android {
|
||||
namespace os {
|
||||
namespace statsd {
|
||||
|
||||
// Helper functions for creating individual config components from StatsdConfig.
|
||||
// Should only be called from metrics_manager_util and config_update_utils.
|
||||
|
||||
// Create a LogMatchingTracker.
|
||||
// input:
|
||||
// [logMatcher]: the input AtomMatcher from the StatsdConfig
|
||||
// [index]: the index of the matcher
|
||||
// output:
|
||||
// new LogMatchingTracker, or null if the tracker is unable to be created
|
||||
sp<LogMatchingTracker> createLogTracker(const AtomMatcher& logMatcher, const int index,
|
||||
const sp<UidMap>& uidMap);
|
||||
|
||||
// Helper functions for MetricsManager to initialize from StatsdConfig.
|
||||
// *Note*: only initStatsdConfig() should be called from outside.
|
||||
// All other functions are intermediate
|
||||
@@ -44,8 +56,7 @@ namespace statsd {
|
||||
// [logTrackerMap]: this map should contain matcher name to index mapping
|
||||
// [allAtomMatchers]: should store the sp to all the LogMatchingTracker
|
||||
// [allTagIds]: contains the set of all interesting tag ids to this config.
|
||||
bool initLogTrackers(const StatsdConfig& config,
|
||||
const UidMap& uidMap,
|
||||
bool initLogTrackers(const StatsdConfig& config, const sp<UidMap>& uidMap,
|
||||
std::unordered_map<int64_t, int>& logTrackerMap,
|
||||
std::vector<sp<LogMatchingTracker>>& allAtomMatchers,
|
||||
std::set<int>& allTagIds);
|
||||
@@ -97,7 +108,7 @@ bool initStates(const StatsdConfig& config, unordered_map<int64_t, int>& stateAt
|
||||
// [trackerToMetricMap]: contains the mapping from log tracker to MetricProducer index.
|
||||
bool initMetrics(
|
||||
const ConfigKey& key, const StatsdConfig& config, const int64_t timeBaseTimeNs,
|
||||
const int64_t currentTimeNs, UidMap& uidMap, const sp<StatsPullerManager>& pullerManager,
|
||||
const int64_t currentTimeNs, const sp<StatsPullerManager>& pullerManager,
|
||||
const std::unordered_map<int64_t, int>& logTrackerMap,
|
||||
const std::unordered_map<int64_t, int>& conditionTrackerMap,
|
||||
const std::unordered_map<int, std::vector<MetricConditionLink>>& eventConditionLinks,
|
||||
@@ -116,12 +127,13 @@ bool initMetrics(
|
||||
|
||||
// Initialize MetricsManager from StatsdConfig.
|
||||
// Parameters are the members of MetricsManager. See MetricsManager for declaration.
|
||||
bool initStatsdConfig(const ConfigKey& key, const StatsdConfig& config, UidMap& uidMap,
|
||||
bool initStatsdConfig(const ConfigKey& key, const StatsdConfig& config, const sp<UidMap>& uidMap,
|
||||
const sp<StatsPullerManager>& pullerManager,
|
||||
const sp<AlarmMonitor>& anomalyAlarmMonitor,
|
||||
const sp<AlarmMonitor>& periodicAlarmMonitor, const int64_t timeBaseNs,
|
||||
const int64_t currentTimeNs, std::set<int>& allTagIds,
|
||||
std::vector<sp<LogMatchingTracker>>& allAtomMatchers,
|
||||
std::unordered_map<int64_t, int>& logTrackerMap,
|
||||
std::vector<sp<ConditionTracker>>& allConditionTrackers,
|
||||
std::vector<sp<MetricProducer>>& allMetricProducers,
|
||||
vector<sp<AnomalyTracker>>& allAnomalyTrackers,
|
||||
@@ -132,8 +144,7 @@ bool initStatsdConfig(const ConfigKey& key, const StatsdConfig& config, UidMap&
|
||||
unordered_map<int, std::vector<int>>& activationAtomTrackerToMetricMap,
|
||||
unordered_map<int, std::vector<int>>& deactivationAtomTrackerToMetricMap,
|
||||
std::unordered_map<int64_t, int>& alertTrackerMap,
|
||||
vector<int>& metricsWithActivation,
|
||||
std::set<int64_t>& noReportMetricIds);
|
||||
vector<int>& metricsWithActivation, std::set<int64_t>& noReportMetricIds);
|
||||
|
||||
} // namespace statsd
|
||||
} // namespace os
|
||||
@@ -191,7 +191,7 @@ void ShellSubscriber::writePulledAtomsLocked(const vector<std::shared_ptr<LogEve
|
||||
mProto.clear();
|
||||
int count = 0;
|
||||
for (const auto& event : data) {
|
||||
if (matchesSimple(*mUidMap, matcher, *event)) {
|
||||
if (matchesSimple(mUidMap, matcher, *event)) {
|
||||
count++;
|
||||
uint64_t atomToken = mProto.start(util::FIELD_TYPE_MESSAGE |
|
||||
util::FIELD_COUNT_REPEATED | FIELD_ID_ATOM);
|
||||
@@ -209,7 +209,7 @@ void ShellSubscriber::onLogEvent(const LogEvent& event) {
|
||||
|
||||
mProto.clear();
|
||||
for (const auto& matcher : mSubscriptionInfo->mPushedMatchers) {
|
||||
if (matchesSimple(*mUidMap, matcher, event)) {
|
||||
if (matchesSimple(mUidMap, matcher, event)) {
|
||||
uint64_t atomToken = mProto.start(util::FIELD_TYPE_MESSAGE |
|
||||
util::FIELD_COUNT_REPEATED | FIELD_ID_ATOM);
|
||||
event.ToProto(mProto);
|
||||
|
||||
@@ -113,7 +113,7 @@ void makeBoolLogEvent(LogEvent* logEvent, const int32_t atomId, const int64_t ti
|
||||
} // anonymous namespace
|
||||
|
||||
TEST(AtomMatcherTest, TestSimpleMatcher) {
|
||||
UidMap uidMap;
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
|
||||
// Set up the matcher
|
||||
AtomMatcher matcher;
|
||||
@@ -132,7 +132,7 @@ TEST(AtomMatcherTest, TestSimpleMatcher) {
|
||||
}
|
||||
|
||||
TEST(AtomMatcherTest, TestAttributionMatcher) {
|
||||
UidMap uidMap;
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
std::vector<int> attributionUids = {1111, 2222, 3333};
|
||||
std::vector<string> attributionTags = {"location1", "location2", "location3"};
|
||||
|
||||
@@ -207,7 +207,7 @@ TEST(AtomMatcherTest, TestAttributionMatcher) {
|
||||
"pkg0");
|
||||
EXPECT_FALSE(matchesSimple(uidMap, *simpleMatcher, event));
|
||||
|
||||
uidMap.updateMap(
|
||||
uidMap->updateMap(
|
||||
1, {1111, 1111, 2222, 3333, 3333} /* uid list */, {1, 1, 2, 1, 2} /* version list */,
|
||||
{android::String16("v1"), android::String16("v1"), android::String16("v2"),
|
||||
android::String16("v1"), android::String16("v2")},
|
||||
@@ -359,8 +359,8 @@ TEST(AtomMatcherTest, TestAttributionMatcher) {
|
||||
}
|
||||
|
||||
TEST(AtomMatcherTest, TestUidFieldMatcher) {
|
||||
UidMap uidMap;
|
||||
uidMap.updateMap(
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
uidMap->updateMap(
|
||||
1, {1111, 1111, 2222, 3333, 3333} /* uid list */, {1, 1, 2, 1, 2} /* version list */,
|
||||
{android::String16("v1"), android::String16("v1"), android::String16("v2"),
|
||||
android::String16("v1"), android::String16("v2")},
|
||||
@@ -395,8 +395,8 @@ TEST(AtomMatcherTest, TestUidFieldMatcher) {
|
||||
}
|
||||
|
||||
TEST(AtomMatcherTest, TestNeqAnyStringMatcher) {
|
||||
UidMap uidMap;
|
||||
uidMap.updateMap(
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
uidMap->updateMap(
|
||||
1, {1111, 1111, 2222, 3333, 3333} /* uid list */, {1, 1, 2, 1, 2} /* version list */,
|
||||
{android::String16("v1"), android::String16("v1"), android::String16("v2"),
|
||||
android::String16("v1"), android::String16("v2")},
|
||||
@@ -456,8 +456,8 @@ TEST(AtomMatcherTest, TestNeqAnyStringMatcher) {
|
||||
}
|
||||
|
||||
TEST(AtomMatcherTest, TestEqAnyStringMatcher) {
|
||||
UidMap uidMap;
|
||||
uidMap.updateMap(
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
uidMap->updateMap(
|
||||
1, {1111, 1111, 2222, 3333, 3333} /* uid list */, {1, 1, 2, 1, 2} /* version list */,
|
||||
{android::String16("v1"), android::String16("v1"), android::String16("v2"),
|
||||
android::String16("v1"), android::String16("v2")},
|
||||
@@ -520,7 +520,7 @@ TEST(AtomMatcherTest, TestEqAnyStringMatcher) {
|
||||
}
|
||||
|
||||
TEST(AtomMatcherTest, TestBoolMatcher) {
|
||||
UidMap uidMap;
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
// Set up the matcher
|
||||
AtomMatcher matcher;
|
||||
auto simpleMatcher = matcher.mutable_simple_atom_matcher();
|
||||
@@ -553,7 +553,7 @@ TEST(AtomMatcherTest, TestBoolMatcher) {
|
||||
}
|
||||
|
||||
TEST(AtomMatcherTest, TestStringMatcher) {
|
||||
UidMap uidMap;
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
// Set up the matcher
|
||||
AtomMatcher matcher;
|
||||
auto simpleMatcher = matcher.mutable_simple_atom_matcher();
|
||||
@@ -571,7 +571,7 @@ TEST(AtomMatcherTest, TestStringMatcher) {
|
||||
}
|
||||
|
||||
TEST(AtomMatcherTest, TestMultiFieldsMatcher) {
|
||||
UidMap uidMap;
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
// Set up the matcher
|
||||
AtomMatcher matcher;
|
||||
auto simpleMatcher = matcher.mutable_simple_atom_matcher();
|
||||
@@ -600,7 +600,7 @@ TEST(AtomMatcherTest, TestMultiFieldsMatcher) {
|
||||
}
|
||||
|
||||
TEST(AtomMatcherTest, TestIntComparisonMatcher) {
|
||||
UidMap uidMap;
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
// Set up the matcher
|
||||
AtomMatcher matcher;
|
||||
auto simpleMatcher = matcher.mutable_simple_atom_matcher();
|
||||
@@ -657,7 +657,7 @@ TEST(AtomMatcherTest, TestIntComparisonMatcher) {
|
||||
}
|
||||
|
||||
TEST(AtomMatcherTest, TestFloatComparisonMatcher) {
|
||||
UidMap uidMap;
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
// Set up the matcher
|
||||
AtomMatcher matcher;
|
||||
auto simpleMatcher = matcher.mutable_simple_atom_matcher();
|
||||
|
||||
@@ -28,7 +28,7 @@
|
||||
#include "src/metrics/GaugeMetricProducer.h"
|
||||
#include "src/metrics/MetricProducer.h"
|
||||
#include "src/metrics/ValueMetricProducer.h"
|
||||
#include "src/metrics/metrics_manager_util.h"
|
||||
#include "src/metrics/parsing_utils/metrics_manager_util.h"
|
||||
#include "src/state/StateManager.h"
|
||||
#include "statsd_test_util.h"
|
||||
|
||||
@@ -48,7 +48,6 @@ namespace statsd {
|
||||
|
||||
namespace {
|
||||
const ConfigKey kConfigKey(0, 12345);
|
||||
const long kAlertId = 3;
|
||||
|
||||
const long timeBaseSec = 1000;
|
||||
|
||||
@@ -90,287 +89,6 @@ StatsdConfig buildGoodConfig() {
|
||||
metric->set_bucket(ONE_MINUTE);
|
||||
metric->mutable_dimensions_in_what()->set_field(2 /*SCREEN_STATE_CHANGE*/);
|
||||
metric->mutable_dimensions_in_what()->add_child()->set_field(1);
|
||||
|
||||
config.add_no_report_metric(3);
|
||||
|
||||
auto alert = config.add_alert();
|
||||
alert->set_id(kAlertId);
|
||||
alert->set_metric_id(3);
|
||||
alert->set_num_buckets(10);
|
||||
alert->set_refractory_period_secs(100);
|
||||
alert->set_trigger_if_sum_gt(100);
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildCircleMatchers() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
|
||||
|
||||
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
|
||||
simpleAtomMatcher->add_field_value_matcher()->set_field(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE*/);
|
||||
simpleAtomMatcher->mutable_field_value_matcher(0)->set_eq_int(
|
||||
2 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_ON*/);
|
||||
|
||||
eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_ON_OR_OFF"));
|
||||
|
||||
AtomMatcher_Combination* combination = eventMatcher->mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_matcher(StringToId("SCREEN_IS_ON"));
|
||||
// Circle dependency
|
||||
combination->add_matcher(StringToId("SCREEN_ON_OR_OFF"));
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildAlertWithUnknownMetric() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
|
||||
|
||||
CountMetric* metric = config.add_count_metric();
|
||||
metric->set_id(3);
|
||||
metric->set_what(StringToId("SCREEN_IS_ON"));
|
||||
metric->set_bucket(ONE_MINUTE);
|
||||
metric->mutable_dimensions_in_what()->set_field(2 /*SCREEN_STATE_CHANGE*/);
|
||||
metric->mutable_dimensions_in_what()->add_child()->set_field(1);
|
||||
|
||||
auto alert = config.add_alert();
|
||||
alert->set_id(3);
|
||||
alert->set_metric_id(2);
|
||||
alert->set_num_buckets(10);
|
||||
alert->set_refractory_period_secs(100);
|
||||
alert->set_trigger_if_sum_gt(100);
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildMissingMatchers() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
|
||||
|
||||
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
|
||||
simpleAtomMatcher->add_field_value_matcher()->set_field(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE*/);
|
||||
simpleAtomMatcher->mutable_field_value_matcher(0)->set_eq_int(
|
||||
2 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_ON*/);
|
||||
|
||||
eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_ON_OR_OFF"));
|
||||
|
||||
AtomMatcher_Combination* combination = eventMatcher->mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_matcher(StringToId("SCREEN_IS_ON"));
|
||||
// undefined matcher
|
||||
combination->add_matcher(StringToId("ABC"));
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildMissingPredicate() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
CountMetric* metric = config.add_count_metric();
|
||||
metric->set_id(3);
|
||||
metric->set_what(StringToId("SCREEN_EVENT"));
|
||||
metric->set_bucket(ONE_MINUTE);
|
||||
metric->set_condition(StringToId("SOME_CONDITION"));
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_EVENT"));
|
||||
|
||||
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2);
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildDimensionMetricsWithMultiTags() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("BATTERY_VERY_LOW"));
|
||||
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2);
|
||||
|
||||
eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("BATTERY_VERY_VERY_LOW"));
|
||||
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(3);
|
||||
|
||||
eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("BATTERY_LOW"));
|
||||
|
||||
AtomMatcher_Combination* combination = eventMatcher->mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_matcher(StringToId("BATTERY_VERY_LOW"));
|
||||
combination->add_matcher(StringToId("BATTERY_VERY_VERY_LOW"));
|
||||
|
||||
// Count process state changes, slice by uid, while SCREEN_IS_OFF
|
||||
CountMetric* metric = config.add_count_metric();
|
||||
metric->set_id(3);
|
||||
metric->set_what(StringToId("BATTERY_LOW"));
|
||||
metric->set_bucket(ONE_MINUTE);
|
||||
// This case is interesting. We want to dimension across two atoms.
|
||||
metric->mutable_dimensions_in_what()->add_child()->set_field(1);
|
||||
|
||||
auto alert = config.add_alert();
|
||||
alert->set_id(kAlertId);
|
||||
alert->set_metric_id(3);
|
||||
alert->set_num_buckets(10);
|
||||
alert->set_refractory_period_secs(100);
|
||||
alert->set_trigger_if_sum_gt(100);
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildCirclePredicates() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
|
||||
|
||||
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
|
||||
simpleAtomMatcher->add_field_value_matcher()->set_field(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE*/);
|
||||
simpleAtomMatcher->mutable_field_value_matcher(0)->set_eq_int(
|
||||
2 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_ON*/);
|
||||
|
||||
eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_IS_OFF"));
|
||||
|
||||
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
|
||||
simpleAtomMatcher->add_field_value_matcher()->set_field(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE*/);
|
||||
simpleAtomMatcher->mutable_field_value_matcher(0)->set_eq_int(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_OFF*/);
|
||||
|
||||
auto condition = config.add_predicate();
|
||||
condition->set_id(StringToId("SCREEN_IS_ON"));
|
||||
SimplePredicate* simplePredicate = condition->mutable_simple_predicate();
|
||||
simplePredicate->set_start(StringToId("SCREEN_IS_ON"));
|
||||
simplePredicate->set_stop(StringToId("SCREEN_IS_OFF"));
|
||||
|
||||
condition = config.add_predicate();
|
||||
condition->set_id(StringToId("SCREEN_IS_EITHER_ON_OFF"));
|
||||
|
||||
Predicate_Combination* combination = condition->mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_predicate(StringToId("SCREEN_IS_ON"));
|
||||
combination->add_predicate(StringToId("SCREEN_IS_EITHER_ON_OFF"));
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildConfigWithDifferentPredicates() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
auto pulledAtomMatcher =
|
||||
CreateSimpleAtomMatcher("SUBSYSTEM_SLEEP", util::SUBSYSTEM_SLEEP_STATE);
|
||||
*config.add_atom_matcher() = pulledAtomMatcher;
|
||||
auto screenOnAtomMatcher = CreateScreenTurnedOnAtomMatcher();
|
||||
*config.add_atom_matcher() = screenOnAtomMatcher;
|
||||
auto screenOffAtomMatcher = CreateScreenTurnedOffAtomMatcher();
|
||||
*config.add_atom_matcher() = screenOffAtomMatcher;
|
||||
auto batteryNoneAtomMatcher = CreateBatteryStateNoneMatcher();
|
||||
*config.add_atom_matcher() = batteryNoneAtomMatcher;
|
||||
auto batteryUsbAtomMatcher = CreateBatteryStateUsbMatcher();
|
||||
*config.add_atom_matcher() = batteryUsbAtomMatcher;
|
||||
|
||||
// Simple condition with InitialValue set to default (unknown).
|
||||
auto screenOnUnknownPredicate = CreateScreenIsOnPredicate();
|
||||
*config.add_predicate() = screenOnUnknownPredicate;
|
||||
|
||||
// Simple condition with InitialValue set to false.
|
||||
auto screenOnFalsePredicate = config.add_predicate();
|
||||
screenOnFalsePredicate->set_id(StringToId("ScreenIsOnInitialFalse"));
|
||||
SimplePredicate* simpleScreenOnFalsePredicate =
|
||||
screenOnFalsePredicate->mutable_simple_predicate();
|
||||
simpleScreenOnFalsePredicate->set_start(screenOnAtomMatcher.id());
|
||||
simpleScreenOnFalsePredicate->set_stop(screenOffAtomMatcher.id());
|
||||
simpleScreenOnFalsePredicate->set_initial_value(SimplePredicate_InitialValue_FALSE);
|
||||
|
||||
// Simple condition with InitialValue set to false.
|
||||
auto onBatteryFalsePredicate = config.add_predicate();
|
||||
onBatteryFalsePredicate->set_id(StringToId("OnBatteryInitialFalse"));
|
||||
SimplePredicate* simpleOnBatteryFalsePredicate =
|
||||
onBatteryFalsePredicate->mutable_simple_predicate();
|
||||
simpleOnBatteryFalsePredicate->set_start(batteryNoneAtomMatcher.id());
|
||||
simpleOnBatteryFalsePredicate->set_stop(batteryUsbAtomMatcher.id());
|
||||
simpleOnBatteryFalsePredicate->set_initial_value(SimplePredicate_InitialValue_FALSE);
|
||||
|
||||
// Combination condition with both simple condition InitialValues set to false.
|
||||
auto screenOnFalseOnBatteryFalsePredicate = config.add_predicate();
|
||||
screenOnFalseOnBatteryFalsePredicate->set_id(StringToId("ScreenOnFalseOnBatteryFalse"));
|
||||
screenOnFalseOnBatteryFalsePredicate->mutable_combination()->set_operation(
|
||||
LogicalOperation::AND);
|
||||
addPredicateToPredicateCombination(*screenOnFalsePredicate,
|
||||
screenOnFalseOnBatteryFalsePredicate);
|
||||
addPredicateToPredicateCombination(*onBatteryFalsePredicate,
|
||||
screenOnFalseOnBatteryFalsePredicate);
|
||||
|
||||
// Combination condition with one simple condition InitialValue set to unknown and one set to
|
||||
// false.
|
||||
auto screenOnUnknownOnBatteryFalsePredicate = config.add_predicate();
|
||||
screenOnUnknownOnBatteryFalsePredicate->set_id(StringToId("ScreenOnUnknowneOnBatteryFalse"));
|
||||
screenOnUnknownOnBatteryFalsePredicate->mutable_combination()->set_operation(
|
||||
LogicalOperation::AND);
|
||||
addPredicateToPredicateCombination(screenOnUnknownPredicate,
|
||||
screenOnUnknownOnBatteryFalsePredicate);
|
||||
addPredicateToPredicateCombination(*onBatteryFalsePredicate,
|
||||
screenOnUnknownOnBatteryFalsePredicate);
|
||||
|
||||
// Simple condition metric with initial value false.
|
||||
ValueMetric* metric1 = config.add_value_metric();
|
||||
metric1->set_id(StringToId("ValueSubsystemSleepWhileScreenOnInitialFalse"));
|
||||
metric1->set_what(pulledAtomMatcher.id());
|
||||
*metric1->mutable_value_field() =
|
||||
CreateDimensions(util::SUBSYSTEM_SLEEP_STATE, {4 /* time sleeping field */});
|
||||
metric1->set_bucket(FIVE_MINUTES);
|
||||
metric1->set_condition(screenOnFalsePredicate->id());
|
||||
|
||||
// Simple condition metric with initial value unknown.
|
||||
ValueMetric* metric2 = config.add_value_metric();
|
||||
metric2->set_id(StringToId("ValueSubsystemSleepWhileScreenOnInitialUnknown"));
|
||||
metric2->set_what(pulledAtomMatcher.id());
|
||||
*metric2->mutable_value_field() =
|
||||
CreateDimensions(util::SUBSYSTEM_SLEEP_STATE, {4 /* time sleeping field */});
|
||||
metric2->set_bucket(FIVE_MINUTES);
|
||||
metric2->set_condition(screenOnUnknownPredicate.id());
|
||||
|
||||
// Combination condition metric with initial values false and false.
|
||||
ValueMetric* metric3 = config.add_value_metric();
|
||||
metric3->set_id(StringToId("ValueSubsystemSleepWhileScreenOnFalseDeviceUnpluggedFalse"));
|
||||
metric3->set_what(pulledAtomMatcher.id());
|
||||
*metric3->mutable_value_field() =
|
||||
CreateDimensions(util::SUBSYSTEM_SLEEP_STATE, {4 /* time sleeping field */});
|
||||
metric3->set_bucket(FIVE_MINUTES);
|
||||
metric3->set_condition(screenOnFalseOnBatteryFalsePredicate->id());
|
||||
|
||||
// Combination condition metric with initial values unknown and false.
|
||||
ValueMetric* metric4 = config.add_value_metric();
|
||||
metric4->set_id(StringToId("ValueSubsystemSleepWhileScreenOnUnknownDeviceUnpluggedFalse"));
|
||||
metric4->set_what(pulledAtomMatcher.id());
|
||||
*metric4->mutable_value_field() =
|
||||
CreateDimensions(util::SUBSYSTEM_SLEEP_STATE, {4 /* time sleeping field */});
|
||||
metric4->set_bucket(FIVE_MINUTES);
|
||||
metric4->set_condition(screenOnUnknownOnBatteryFalsePredicate->id());
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
@@ -379,274 +97,6 @@ bool isSubset(const set<int32_t>& set1, const set<int32_t>& set2) {
|
||||
}
|
||||
} // anonymous namespace
|
||||
|
||||
TEST(MetricsManagerTest, TestInitialConditions) {
|
||||
UidMap uidMap;
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildConfigWithDifferentPredicates();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
EXPECT_TRUE(initStatsdConfig(
|
||||
kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor, periodicAlarmMonitor,
|
||||
timeBaseSec, timeBaseSec, allTagIds, allAtomMatchers, allConditionTrackers,
|
||||
allMetricProducers, allAnomalyTrackers, allAlarmTrackers, conditionToMetricMap,
|
||||
trackerToMetricMap, trackerToConditionMap, activationAtomTrackerToMetricMap,
|
||||
deactivationAtomTrackerToMetricMap, alertTrackerMap, metricsWithActivation,
|
||||
noReportMetricIds));
|
||||
ASSERT_EQ(4u, allMetricProducers.size());
|
||||
ASSERT_EQ(5u, allConditionTrackers.size());
|
||||
|
||||
ConditionKey queryKey;
|
||||
vector<ConditionState> conditionCache(5, ConditionState::kNotEvaluated);
|
||||
|
||||
allConditionTrackers[3]->isConditionMet(queryKey, allConditionTrackers, false, conditionCache);
|
||||
allConditionTrackers[4]->isConditionMet(queryKey, allConditionTrackers, false, conditionCache);
|
||||
EXPECT_EQ(ConditionState::kUnknown, conditionCache[0]);
|
||||
EXPECT_EQ(ConditionState::kFalse, conditionCache[1]);
|
||||
EXPECT_EQ(ConditionState::kFalse, conditionCache[2]);
|
||||
EXPECT_EQ(ConditionState::kFalse, conditionCache[3]);
|
||||
EXPECT_EQ(ConditionState::kUnknown, conditionCache[4]);
|
||||
|
||||
EXPECT_EQ(ConditionState::kFalse, allMetricProducers[0]->mCondition);
|
||||
EXPECT_EQ(ConditionState::kUnknown, allMetricProducers[1]->mCondition);
|
||||
EXPECT_EQ(ConditionState::kFalse, allMetricProducers[2]->mCondition);
|
||||
EXPECT_EQ(ConditionState::kUnknown, allMetricProducers[3]->mCondition);
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestGoodConfig) {
|
||||
UidMap uidMap;
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildGoodConfig();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
EXPECT_TRUE(initStatsdConfig(kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor,
|
||||
periodicAlarmMonitor, timeBaseSec, timeBaseSec, allTagIds,
|
||||
allAtomMatchers, allConditionTrackers, allMetricProducers,
|
||||
allAnomalyTrackers, allAlarmTrackers, conditionToMetricMap,
|
||||
trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap,
|
||||
alertTrackerMap, metricsWithActivation,
|
||||
noReportMetricIds));
|
||||
ASSERT_EQ(1u, allMetricProducers.size());
|
||||
ASSERT_EQ(1u, allAnomalyTrackers.size());
|
||||
ASSERT_EQ(1u, noReportMetricIds.size());
|
||||
ASSERT_EQ(1u, alertTrackerMap.size());
|
||||
EXPECT_NE(alertTrackerMap.find(kAlertId), alertTrackerMap.end());
|
||||
EXPECT_EQ(alertTrackerMap.find(kAlertId)->second, 0);
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestDimensionMetricsWithMultiTags) {
|
||||
UidMap uidMap;
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildDimensionMetricsWithMultiTags();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
EXPECT_FALSE(initStatsdConfig(kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor,
|
||||
periodicAlarmMonitor, timeBaseSec, timeBaseSec, allTagIds,
|
||||
allAtomMatchers, allConditionTrackers, allMetricProducers,
|
||||
allAnomalyTrackers, allAlarmTrackers, conditionToMetricMap,
|
||||
trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap,
|
||||
alertTrackerMap, metricsWithActivation,
|
||||
noReportMetricIds));
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestCircleLogMatcherDependency) {
|
||||
UidMap uidMap;
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildCircleMatchers();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
EXPECT_FALSE(initStatsdConfig(kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor,
|
||||
periodicAlarmMonitor, timeBaseSec, timeBaseSec, allTagIds,
|
||||
allAtomMatchers, allConditionTrackers, allMetricProducers,
|
||||
allAnomalyTrackers, allAlarmTrackers, conditionToMetricMap,
|
||||
trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap,
|
||||
alertTrackerMap, metricsWithActivation,
|
||||
noReportMetricIds));
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestMissingMatchers) {
|
||||
UidMap uidMap;
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildMissingMatchers();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
EXPECT_FALSE(initStatsdConfig(kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor,
|
||||
periodicAlarmMonitor, timeBaseSec, timeBaseSec, allTagIds,
|
||||
allAtomMatchers, allConditionTrackers, allMetricProducers,
|
||||
allAnomalyTrackers, allAlarmTrackers, conditionToMetricMap,
|
||||
trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap,
|
||||
alertTrackerMap, metricsWithActivation,
|
||||
noReportMetricIds));
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestMissingPredicate) {
|
||||
UidMap uidMap;
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildMissingPredicate();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
EXPECT_FALSE(initStatsdConfig(kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor,
|
||||
periodicAlarmMonitor, timeBaseSec, timeBaseSec, allTagIds,
|
||||
allAtomMatchers, allConditionTrackers, allMetricProducers,
|
||||
allAnomalyTrackers, allAlarmTrackers, conditionToMetricMap,
|
||||
trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap,
|
||||
alertTrackerMap, metricsWithActivation, noReportMetricIds));
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestCirclePredicateDependency) {
|
||||
UidMap uidMap;
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildCirclePredicates();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
EXPECT_FALSE(initStatsdConfig(kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor,
|
||||
periodicAlarmMonitor, timeBaseSec, timeBaseSec, allTagIds,
|
||||
allAtomMatchers, allConditionTrackers, allMetricProducers,
|
||||
allAnomalyTrackers, allAlarmTrackers, conditionToMetricMap,
|
||||
trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap,
|
||||
alertTrackerMap, metricsWithActivation,
|
||||
noReportMetricIds));
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, testAlertWithUnknownMetric) {
|
||||
UidMap uidMap;
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildAlertWithUnknownMetric();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
EXPECT_FALSE(initStatsdConfig(kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor,
|
||||
periodicAlarmMonitor, timeBaseSec, timeBaseSec, allTagIds,
|
||||
allAtomMatchers, allConditionTrackers, allMetricProducers,
|
||||
allAnomalyTrackers, allAlarmTrackers, conditionToMetricMap,
|
||||
trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap,
|
||||
alertTrackerMap, metricsWithActivation,
|
||||
noReportMetricIds));
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestLogSources) {
|
||||
string app1 = "app1";
|
||||
set<int32_t> app1Uids = {1111, 11111};
|
||||
@@ -680,7 +130,7 @@ TEST(MetricsManagerTest, TestLogSources) {
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
|
||||
StatsdConfig config = buildGoodConfig();
|
||||
StatsdConfig config;
|
||||
config.add_allowed_log_source("AID_SYSTEM");
|
||||
config.add_allowed_log_source(app1);
|
||||
config.add_default_pull_packages("AID_SYSTEM");
|
||||
@@ -744,7 +194,7 @@ TEST(MetricsManagerTest, TestCheckLogCredentialsWhitelistedAtom) {
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
|
||||
StatsdConfig config = buildGoodConfig();
|
||||
StatsdConfig config;
|
||||
config.add_whitelisted_atom_ids(3);
|
||||
config.add_whitelisted_atom_ids(4);
|
||||
|
||||
|
||||
@@ -47,7 +47,6 @@ namespace {
|
||||
const ConfigKey kConfigKey(0, 12345);
|
||||
const int tagId = 1;
|
||||
const int64_t metricId = 123;
|
||||
const int64_t atomMatcherId = 678;
|
||||
const int logEventMatcherIndex = 0;
|
||||
const int64_t bucketStartTimeNs = 10 * NS_PER_SEC;
|
||||
const int64_t bucketSizeNs = TimeUnitToBucketSizeInMillis(ONE_MINUTE) * 1000000LL;
|
||||
@@ -94,11 +93,8 @@ TEST(GaugeMetricProducerTest, TestFirstBucket) {
|
||||
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard = new EventMatcherWizard({
|
||||
new SimpleLogMatchingTracker(atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -127,12 +123,8 @@ TEST(GaugeMetricProducerTest, TestPulledEventsNoCondition) {
|
||||
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _)).WillOnce(Return());
|
||||
@@ -217,12 +209,8 @@ TEST_P(GaugeMetricProducerTest_PartialBucket, TestPushedEvents) {
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
|
||||
GaugeMetricProducer gaugeProducer(kConfigKey, metric, -1 /*-1 meaning no condition*/, {},
|
||||
wizard, logEventMatcherIndex, eventMatcherWizard,
|
||||
@@ -301,12 +289,9 @@ TEST_P(GaugeMetricProducerTest_PartialBucket, TestPulled) {
|
||||
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _)).WillOnce(Return());
|
||||
EXPECT_CALL(*pullerManager, UnRegisterReceiver(tagId, kConfigKey, _)).WillOnce(Return());
|
||||
@@ -378,12 +363,8 @@ TEST(GaugeMetricProducerTest, TestPulledWithAppUpgradeDisabled) {
|
||||
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _)).WillOnce(Return());
|
||||
@@ -428,12 +409,8 @@ TEST(GaugeMetricProducerTest, TestPulledEventsWithCondition) {
|
||||
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
|
||||
int64_t conditionChangeNs = bucketStartTimeNs + 8;
|
||||
|
||||
@@ -502,12 +479,8 @@ TEST(GaugeMetricProducerTest, TestPulledEventsWithSlicedCondition) {
|
||||
dim->set_field(tagId);
|
||||
dim->add_child()->set_field(1);
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
EXPECT_CALL(*wizard, query(_, _, _))
|
||||
@@ -577,12 +550,8 @@ TEST(GaugeMetricProducerTest, TestPulledEventsAnomalyDetection) {
|
||||
gaugeFieldMatcher->set_field(tagId);
|
||||
gaugeFieldMatcher->add_child()->set_field(2);
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
|
||||
GaugeMetricProducer gaugeProducer(kConfigKey, metric, -1 /*-1 meaning no condition*/, {},
|
||||
wizard, logEventMatcherIndex, eventMatcherWizard, tagId, -1,
|
||||
@@ -657,12 +626,8 @@ TEST(GaugeMetricProducerTest, TestPullOnTrigger) {
|
||||
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
EXPECT_CALL(*pullerManager, Pull(tagId, kConfigKey, _, _))
|
||||
@@ -729,12 +694,8 @@ TEST(GaugeMetricProducerTest, TestRemoveDimensionInOutput) {
|
||||
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
EXPECT_CALL(*pullerManager, Pull(tagId, kConfigKey, _, _))
|
||||
@@ -807,12 +768,8 @@ TEST(GaugeMetricProducerTest_BucketDrop, TestBucketDropWhenBucketTooSmall) {
|
||||
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
EXPECT_CALL(*pullerManager, Pull(tagId, kConfigKey, bucketStartTimeNs + 3, _))
|
||||
|
||||
@@ -46,7 +46,6 @@ namespace {
|
||||
const ConfigKey kConfigKey(0, 12345);
|
||||
const int tagId = 1;
|
||||
const int64_t metricId = 123;
|
||||
const int64_t atomMatcherId = 678;
|
||||
const int logEventMatcherIndex = 0;
|
||||
const int64_t bucketStartTimeNs = 10000000000;
|
||||
const int64_t bucketSizeNs = TimeUnitToBucketSizeInMillis(ONE_MINUTE) * 1000000LL;
|
||||
@@ -99,12 +98,8 @@ class ValueMetricProducerTestHelper {
|
||||
public:
|
||||
static sp<ValueMetricProducer> createValueProducerNoConditions(
|
||||
sp<MockStatsPullerManager>& pullerManager, ValueMetric& metric) {
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _))
|
||||
.WillOnce(Return());
|
||||
@@ -122,12 +117,8 @@ public:
|
||||
static sp<ValueMetricProducer> createValueProducerWithCondition(
|
||||
sp<MockStatsPullerManager>& pullerManager, ValueMetric& metric,
|
||||
ConditionState conditionAfterFirstBucketPrepared) {
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _))
|
||||
.WillOnce(Return());
|
||||
@@ -147,12 +138,8 @@ public:
|
||||
sp<MockStatsPullerManager>& pullerManager, ValueMetric& metric,
|
||||
vector<int32_t> slicedStateAtoms,
|
||||
unordered_map<int, unordered_map<int, int64_t>> stateGroupMap) {
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _))
|
||||
.WillOnce(Return());
|
||||
@@ -172,12 +159,8 @@ public:
|
||||
vector<int32_t> slicedStateAtoms,
|
||||
unordered_map<int, unordered_map<int, int64_t>> stateGroupMap,
|
||||
ConditionState conditionAfterFirstBucketPrepared) {
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _))
|
||||
.WillOnce(Return());
|
||||
@@ -237,12 +220,8 @@ TEST(ValueMetricProducerTest, TestCalcPreviousBucketEndTime) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
|
||||
int64_t startTimeBase = 11;
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -267,12 +246,8 @@ TEST(ValueMetricProducerTest, TestCalcPreviousBucketEndTime) {
|
||||
TEST(ValueMetricProducerTest, TestFirstBucket) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -421,15 +396,11 @@ TEST_P(ValueMetricProducerTest_PartialBucket, TestPartialBucketCreated) {
|
||||
TEST(ValueMetricProducerTest, TestPulledEventsWithFiltering) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
auto keyValue = atomMatcher.add_field_value_matcher();
|
||||
keyValue->set_field(1);
|
||||
keyValue->set_eq_int(3);
|
||||
FieldValueMatcher fvm;
|
||||
fvm.set_field(1);
|
||||
fvm.set_eq_int(3);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex, {fvm});
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _)).WillOnce(Return());
|
||||
@@ -698,12 +669,8 @@ TEST(ValueMetricProducerTest, TestEventsWithNonSlicedCondition) {
|
||||
TEST_P(ValueMetricProducerTest_PartialBucket, TestPushedEvents) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -759,12 +726,8 @@ TEST_P(ValueMetricProducerTest_PartialBucket, TestPushedEvents) {
|
||||
TEST_P(ValueMetricProducerTest_PartialBucket, TestPulledValue) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
int64_t partialBucketSplitTimeNs = bucket2StartTimeNs + 150;
|
||||
@@ -820,12 +783,8 @@ TEST(ValueMetricProducerTest, TestPulledWithAppUpgradeDisabled) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
metric.set_split_bucket_for_app_upgrade(false);
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _)).WillOnce(Return());
|
||||
@@ -900,12 +859,8 @@ TEST_P(ValueMetricProducerTest_PartialBucket, TestPulledValueWhileConditionFalse
|
||||
TEST(ValueMetricProducerTest, TestPushedEventsWithoutCondition) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -944,12 +899,8 @@ TEST(ValueMetricProducerTest, TestPushedEventsWithoutCondition) {
|
||||
TEST(ValueMetricProducerTest, TestPushedEventsWithCondition) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -1015,12 +966,8 @@ TEST(ValueMetricProducerTest, TestAnomalyDetection) {
|
||||
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -1317,12 +1264,8 @@ TEST(ValueMetricProducerTest, TestPushedAggregateMin) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
metric.set_aggregation_type(ValueMetric::MIN);
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -1361,12 +1304,8 @@ TEST(ValueMetricProducerTest, TestPushedAggregateMax) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
metric.set_aggregation_type(ValueMetric::MAX);
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -1404,12 +1343,8 @@ TEST(ValueMetricProducerTest, TestPushedAggregateAvg) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
metric.set_aggregation_type(ValueMetric::AVG);
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -1452,12 +1387,8 @@ TEST(ValueMetricProducerTest, TestPushedAggregateSum) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
metric.set_aggregation_type(ValueMetric::SUM);
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -1496,12 +1427,8 @@ TEST(ValueMetricProducerTest, TestSkipZeroDiffOutput) {
|
||||
metric.set_aggregation_type(ValueMetric::MIN);
|
||||
metric.set_use_diff(true);
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -1568,12 +1495,8 @@ TEST(ValueMetricProducerTest, TestSkipZeroDiffOutputMultiValue) {
|
||||
metric.set_aggregation_type(ValueMetric::MIN);
|
||||
metric.set_use_diff(true);
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
|
||||
@@ -2097,12 +2020,8 @@ TEST(ValueMetricProducerTest, TestResetBaseOnPullDelayExceeded) {
|
||||
TEST(ValueMetricProducerTest, TestResetBaseOnPullTooLate) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetricWithCondition();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _)).WillOnce(Return());
|
||||
@@ -2920,12 +2839,8 @@ TEST(ValueMetricProducerTest, TestBucketInvalidIfGlobalBaseIsNotSet) {
|
||||
TEST(ValueMetricProducerTest, TestPullNeededFastDump) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _)).WillOnce(Return());
|
||||
@@ -2958,12 +2873,8 @@ TEST(ValueMetricProducerTest, TestPullNeededFastDump) {
|
||||
TEST(ValueMetricProducerTest, TestFastDumpWithoutCurrentBucket) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _)).WillOnce(Return());
|
||||
@@ -3002,12 +2913,8 @@ TEST(ValueMetricProducerTest, TestFastDumpWithoutCurrentBucket) {
|
||||
TEST(ValueMetricProducerTest, TestPullNeededNoTimeConstraints) {
|
||||
ValueMetric metric = ValueMetricProducerTestHelper::createMetric();
|
||||
|
||||
UidMap uidMap;
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
sp<EventMatcherWizard> eventMatcherWizard =
|
||||
new EventMatcherWizard({new SimpleLogMatchingTracker(
|
||||
atomMatcherId, logEventMatcherIndex, atomMatcher, uidMap)});
|
||||
createEventMatcherWizard(tagId, logEventMatcherIndex);
|
||||
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
|
||||
sp<MockStatsPullerManager> pullerManager = new StrictMock<MockStatsPullerManager>();
|
||||
EXPECT_CALL(*pullerManager, RegisterReceiver(tagId, kConfigKey, _, _, _)).WillOnce(Return());
|
||||
|
||||
@@ -0,0 +1,382 @@
|
||||
// Copyright (C) 2020 The Android Open Source Project
|
||||
//
|
||||
// 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.
|
||||
|
||||
#include "src/metrics/parsing_utils/config_update_utils.h"
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
#include <private/android_filesystem_config.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#include <set>
|
||||
#include <unordered_map>
|
||||
#include <vector>
|
||||
|
||||
#include "frameworks/base/cmds/statsd/src/statsd_config.pb.h"
|
||||
#include "src/metrics/parsing_utils/metrics_manager_util.h"
|
||||
#include "tests/statsd_test_util.h"
|
||||
|
||||
using namespace testing;
|
||||
using android::sp;
|
||||
using android::os::statsd::Predicate;
|
||||
using std::map;
|
||||
using std::set;
|
||||
using std::unordered_map;
|
||||
using std::vector;
|
||||
|
||||
#ifdef __ANDROID__
|
||||
|
||||
namespace android {
|
||||
namespace os {
|
||||
namespace statsd {
|
||||
|
||||
namespace {
|
||||
|
||||
ConfigKey key(123, 456);
|
||||
const int64_t timeBaseNs = 1000;
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> oldAtomMatchers;
|
||||
unordered_map<int64_t, int> oldLogTrackerMap;
|
||||
vector<sp<ConditionTracker>> oldConditionTrackers;
|
||||
vector<sp<MetricProducer>> oldMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> oldAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> oldAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
class ConfigUpdateTest : public ::testing::Test {
|
||||
public:
|
||||
ConfigUpdateTest() {
|
||||
}
|
||||
|
||||
void SetUp() override {
|
||||
allTagIds.clear();
|
||||
oldAtomMatchers.clear();
|
||||
oldLogTrackerMap.clear();
|
||||
oldConditionTrackers.clear();
|
||||
oldMetricProducers.clear();
|
||||
oldAnomalyTrackers.clear();
|
||||
oldAlarmTrackers.clear();
|
||||
conditionToMetricMap.clear();
|
||||
trackerToMetricMap.clear();
|
||||
trackerToConditionMap.clear();
|
||||
activationAtomTrackerToMetricMap.clear();
|
||||
deactivationAtomTrackerToMetricMap.clear();
|
||||
alertTrackerMap.clear();
|
||||
metricsWithActivation.clear();
|
||||
noReportMetricIds.clear();
|
||||
}
|
||||
};
|
||||
|
||||
bool initConfig(const StatsdConfig& config) {
|
||||
return initStatsdConfig(key, config, uidMap, pullerManager, anomalyAlarmMonitor,
|
||||
periodicAlarmMonitor, timeBaseNs, timeBaseNs, allTagIds,
|
||||
oldAtomMatchers, oldLogTrackerMap, oldConditionTrackers,
|
||||
oldMetricProducers, oldAnomalyTrackers, oldAlarmTrackers,
|
||||
conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap,
|
||||
alertTrackerMap, metricsWithActivation, noReportMetricIds);
|
||||
}
|
||||
|
||||
} // anonymous namespace
|
||||
|
||||
TEST_F(ConfigUpdateTest, TestSimpleMatcherPreserve) {
|
||||
StatsdConfig config;
|
||||
AtomMatcher matcher = CreateSimpleAtomMatcher("TEST", /*atom=*/10);
|
||||
int64_t matcherId = matcher.id();
|
||||
*config.add_atom_matcher() = matcher;
|
||||
|
||||
// Create an initial config.
|
||||
EXPECT_TRUE(initConfig(config));
|
||||
|
||||
vector<UpdateStatus> matchersToUpdate(1, UPDATE_UNKNOWN);
|
||||
vector<bool> cycleTracker(1, false);
|
||||
unordered_map<int64_t, int> newLogTrackerMap;
|
||||
newLogTrackerMap[matcherId] = 0;
|
||||
EXPECT_TRUE(determineMatcherUpdateStatus(config, 0, oldLogTrackerMap, oldAtomMatchers,
|
||||
newLogTrackerMap, matchersToUpdate, cycleTracker));
|
||||
EXPECT_EQ(matchersToUpdate[0], UPDATE_PRESERVE);
|
||||
}
|
||||
|
||||
TEST_F(ConfigUpdateTest, TestSimpleMatcherReplace) {
|
||||
StatsdConfig config;
|
||||
AtomMatcher matcher = CreateSimpleAtomMatcher("TEST", /*atom=*/10);
|
||||
*config.add_atom_matcher() = matcher;
|
||||
|
||||
EXPECT_TRUE(initConfig(config));
|
||||
|
||||
StatsdConfig newConfig;
|
||||
// Same id, different atom, so should be replaced.
|
||||
AtomMatcher newMatcher = CreateSimpleAtomMatcher("TEST", /*atom=*/11);
|
||||
int64_t matcherId = newMatcher.id();
|
||||
EXPECT_EQ(matcherId, matcher.id());
|
||||
*newConfig.add_atom_matcher() = newMatcher;
|
||||
|
||||
vector<UpdateStatus> matchersToUpdate(1, UPDATE_UNKNOWN);
|
||||
vector<bool> cycleTracker(1, false);
|
||||
unordered_map<int64_t, int> newLogTrackerMap;
|
||||
newLogTrackerMap[matcherId] = 0;
|
||||
EXPECT_TRUE(determineMatcherUpdateStatus(newConfig, 0, oldLogTrackerMap, oldAtomMatchers,
|
||||
newLogTrackerMap, matchersToUpdate, cycleTracker));
|
||||
EXPECT_EQ(matchersToUpdate[0], UPDATE_REPLACE);
|
||||
}
|
||||
|
||||
TEST_F(ConfigUpdateTest, TestCombinationMatcherPreserve) {
|
||||
StatsdConfig config;
|
||||
AtomMatcher matcher1 = CreateSimpleAtomMatcher("TEST1", /*atom=*/10);
|
||||
int64_t matcher1Id = matcher1.id();
|
||||
*config.add_atom_matcher() = matcher1;
|
||||
|
||||
AtomMatcher matcher2 = CreateSimpleAtomMatcher("TEST2", /*atom=*/11);
|
||||
*config.add_atom_matcher() = matcher2;
|
||||
int64_t matcher2Id = matcher2.id();
|
||||
|
||||
AtomMatcher matcher3;
|
||||
matcher3.set_id(StringToId("TEST3"));
|
||||
AtomMatcher_Combination* combination = matcher3.mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_matcher(matcher1Id);
|
||||
combination->add_matcher(matcher2Id);
|
||||
int64_t matcher3Id = matcher3.id();
|
||||
*config.add_atom_matcher() = matcher3;
|
||||
|
||||
EXPECT_TRUE(initConfig(config));
|
||||
|
||||
StatsdConfig newConfig;
|
||||
unordered_map<int64_t, int> newLogTrackerMap;
|
||||
// Same matchers, different order, all should be preserved.
|
||||
*newConfig.add_atom_matcher() = matcher2;
|
||||
newLogTrackerMap[matcher2Id] = 0;
|
||||
*newConfig.add_atom_matcher() = matcher3;
|
||||
newLogTrackerMap[matcher3Id] = 1;
|
||||
*newConfig.add_atom_matcher() = matcher1;
|
||||
newLogTrackerMap[matcher1Id] = 2;
|
||||
|
||||
vector<UpdateStatus> matchersToUpdate(3, UPDATE_UNKNOWN);
|
||||
vector<bool> cycleTracker(3, false);
|
||||
// Only update the combination. It should recurse the two child matchers and preserve all 3.
|
||||
EXPECT_TRUE(determineMatcherUpdateStatus(newConfig, 1, oldLogTrackerMap, oldAtomMatchers,
|
||||
newLogTrackerMap, matchersToUpdate, cycleTracker));
|
||||
EXPECT_EQ(matchersToUpdate[0], UPDATE_PRESERVE);
|
||||
EXPECT_EQ(matchersToUpdate[1], UPDATE_PRESERVE);
|
||||
EXPECT_EQ(matchersToUpdate[2], UPDATE_PRESERVE);
|
||||
}
|
||||
|
||||
TEST_F(ConfigUpdateTest, TestCombinationMatcherReplace) {
|
||||
StatsdConfig config;
|
||||
AtomMatcher matcher1 = CreateSimpleAtomMatcher("TEST1", /*atom=*/10);
|
||||
int64_t matcher1Id = matcher1.id();
|
||||
*config.add_atom_matcher() = matcher1;
|
||||
|
||||
AtomMatcher matcher2 = CreateSimpleAtomMatcher("TEST2", /*atom=*/11);
|
||||
*config.add_atom_matcher() = matcher2;
|
||||
int64_t matcher2Id = matcher2.id();
|
||||
|
||||
AtomMatcher matcher3;
|
||||
matcher3.set_id(StringToId("TEST3"));
|
||||
AtomMatcher_Combination* combination = matcher3.mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_matcher(matcher1Id);
|
||||
combination->add_matcher(matcher2Id);
|
||||
int64_t matcher3Id = matcher3.id();
|
||||
*config.add_atom_matcher() = matcher3;
|
||||
|
||||
EXPECT_TRUE(initConfig(config));
|
||||
|
||||
// Change the logical operation of the combination matcher, causing a replacement.
|
||||
matcher3.mutable_combination()->set_operation(LogicalOperation::AND);
|
||||
|
||||
StatsdConfig newConfig;
|
||||
unordered_map<int64_t, int> newLogTrackerMap;
|
||||
*newConfig.add_atom_matcher() = matcher2;
|
||||
newLogTrackerMap[matcher2Id] = 0;
|
||||
*newConfig.add_atom_matcher() = matcher3;
|
||||
newLogTrackerMap[matcher3Id] = 1;
|
||||
*newConfig.add_atom_matcher() = matcher1;
|
||||
newLogTrackerMap[matcher1Id] = 2;
|
||||
|
||||
vector<UpdateStatus> matchersToUpdate(3, UPDATE_UNKNOWN);
|
||||
vector<bool> cycleTracker(3, false);
|
||||
// Only update the combination. The simple matchers should not be evaluated.
|
||||
EXPECT_TRUE(determineMatcherUpdateStatus(newConfig, 1, oldLogTrackerMap, oldAtomMatchers,
|
||||
newLogTrackerMap, matchersToUpdate, cycleTracker));
|
||||
EXPECT_EQ(matchersToUpdate[0], UPDATE_UNKNOWN);
|
||||
EXPECT_EQ(matchersToUpdate[1], UPDATE_REPLACE);
|
||||
EXPECT_EQ(matchersToUpdate[2], UPDATE_UNKNOWN);
|
||||
}
|
||||
|
||||
TEST_F(ConfigUpdateTest, TestCombinationMatcherDepsChange) {
|
||||
StatsdConfig config;
|
||||
AtomMatcher matcher1 = CreateSimpleAtomMatcher("TEST1", /*atom=*/10);
|
||||
int64_t matcher1Id = matcher1.id();
|
||||
*config.add_atom_matcher() = matcher1;
|
||||
|
||||
AtomMatcher matcher2 = CreateSimpleAtomMatcher("TEST2", /*atom=*/11);
|
||||
*config.add_atom_matcher() = matcher2;
|
||||
int64_t matcher2Id = matcher2.id();
|
||||
|
||||
AtomMatcher matcher3;
|
||||
matcher3.set_id(StringToId("TEST3"));
|
||||
AtomMatcher_Combination* combination = matcher3.mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_matcher(matcher1Id);
|
||||
combination->add_matcher(matcher2Id);
|
||||
int64_t matcher3Id = matcher3.id();
|
||||
*config.add_atom_matcher() = matcher3;
|
||||
|
||||
EXPECT_TRUE(initConfig(config));
|
||||
|
||||
// Change a dependency of matcher 3.
|
||||
matcher2.mutable_simple_atom_matcher()->set_atom_id(12);
|
||||
|
||||
StatsdConfig newConfig;
|
||||
unordered_map<int64_t, int> newLogTrackerMap;
|
||||
*newConfig.add_atom_matcher() = matcher2;
|
||||
newLogTrackerMap[matcher2Id] = 0;
|
||||
*newConfig.add_atom_matcher() = matcher3;
|
||||
newLogTrackerMap[matcher3Id] = 1;
|
||||
*newConfig.add_atom_matcher() = matcher1;
|
||||
newLogTrackerMap[matcher1Id] = 2;
|
||||
|
||||
vector<UpdateStatus> matchersToUpdate(3, UPDATE_UNKNOWN);
|
||||
vector<bool> cycleTracker(3, false);
|
||||
// Only update the combination.
|
||||
EXPECT_TRUE(determineMatcherUpdateStatus(newConfig, 1, oldLogTrackerMap, oldAtomMatchers,
|
||||
newLogTrackerMap, matchersToUpdate, cycleTracker));
|
||||
// Matcher 2 and matcher3 must be reevaluated. Matcher 1 might, but does not need to be.
|
||||
EXPECT_EQ(matchersToUpdate[0], UPDATE_REPLACE);
|
||||
EXPECT_EQ(matchersToUpdate[1], UPDATE_REPLACE);
|
||||
}
|
||||
|
||||
TEST_F(ConfigUpdateTest, TestUpdateMatchers) {
|
||||
StatsdConfig config;
|
||||
// Will be preserved.
|
||||
AtomMatcher simple1 = CreateSimpleAtomMatcher("SIMPLE1", /*atom=*/10);
|
||||
int64_t simple1Id = simple1.id();
|
||||
*config.add_atom_matcher() = simple1;
|
||||
|
||||
// Will be replaced.
|
||||
AtomMatcher simple2 = CreateSimpleAtomMatcher("SIMPLE2", /*atom=*/11);
|
||||
*config.add_atom_matcher() = simple2;
|
||||
int64_t simple2Id = simple2.id();
|
||||
|
||||
// Will be removed.
|
||||
AtomMatcher simple3 = CreateSimpleAtomMatcher("SIMPLE3", /*atom=*/12);
|
||||
*config.add_atom_matcher() = simple3;
|
||||
int64_t simple3Id = simple3.id();
|
||||
|
||||
// Will be preserved.
|
||||
AtomMatcher combination1;
|
||||
combination1.set_id(StringToId("combination1"));
|
||||
AtomMatcher_Combination* combination = combination1.mutable_combination();
|
||||
combination->set_operation(LogicalOperation::NOT);
|
||||
combination->add_matcher(simple1Id);
|
||||
int64_t combination1Id = combination1.id();
|
||||
*config.add_atom_matcher() = combination1;
|
||||
|
||||
// Will be replaced since it depends on simple2.
|
||||
AtomMatcher combination2;
|
||||
combination2.set_id(StringToId("combination2"));
|
||||
combination = combination2.mutable_combination();
|
||||
combination->set_operation(LogicalOperation::AND);
|
||||
combination->add_matcher(simple1Id);
|
||||
combination->add_matcher(simple2Id);
|
||||
int64_t combination2Id = combination2.id();
|
||||
*config.add_atom_matcher() = combination2;
|
||||
|
||||
EXPECT_TRUE(initConfig(config));
|
||||
|
||||
// Change simple2, causing simple2 and combination2 to be replaced.
|
||||
simple2.mutable_simple_atom_matcher()->set_atom_id(111);
|
||||
|
||||
// 2 new matchers: simple4 and combination3:
|
||||
AtomMatcher simple4 = CreateSimpleAtomMatcher("SIMPLE4", /*atom=*/13);
|
||||
int64_t simple4Id = simple4.id();
|
||||
|
||||
AtomMatcher combination3;
|
||||
combination3.set_id(StringToId("combination3"));
|
||||
combination = combination3.mutable_combination();
|
||||
combination->set_operation(LogicalOperation::AND);
|
||||
combination->add_matcher(simple4Id);
|
||||
combination->add_matcher(simple2Id);
|
||||
int64_t combination3Id = combination3.id();
|
||||
|
||||
StatsdConfig newConfig;
|
||||
*newConfig.add_atom_matcher() = combination3;
|
||||
*newConfig.add_atom_matcher() = simple2;
|
||||
*newConfig.add_atom_matcher() = combination2;
|
||||
*newConfig.add_atom_matcher() = simple1;
|
||||
*newConfig.add_atom_matcher() = simple4;
|
||||
*newConfig.add_atom_matcher() = combination1;
|
||||
|
||||
set<int> newTagIds;
|
||||
unordered_map<int64_t, int> newLogTrackerMap;
|
||||
vector<sp<LogMatchingTracker>> newAtomMatchers;
|
||||
EXPECT_TRUE(updateLogTrackers(newConfig, uidMap, oldLogTrackerMap, oldAtomMatchers, newTagIds,
|
||||
newLogTrackerMap, newAtomMatchers));
|
||||
|
||||
ASSERT_EQ(newTagIds.size(), 3);
|
||||
EXPECT_EQ(newTagIds.count(10), 1);
|
||||
EXPECT_EQ(newTagIds.count(111), 1);
|
||||
EXPECT_EQ(newTagIds.count(13), 1);
|
||||
|
||||
ASSERT_EQ(newLogTrackerMap.size(), 6);
|
||||
EXPECT_EQ(newLogTrackerMap.at(combination3Id), 0);
|
||||
EXPECT_EQ(newLogTrackerMap.at(simple2Id), 1);
|
||||
EXPECT_EQ(newLogTrackerMap.at(combination2Id), 2);
|
||||
EXPECT_EQ(newLogTrackerMap.at(simple1Id), 3);
|
||||
EXPECT_EQ(newLogTrackerMap.at(simple4Id), 4);
|
||||
EXPECT_EQ(newLogTrackerMap.at(combination1Id), 5);
|
||||
|
||||
ASSERT_EQ(newAtomMatchers.size(), 6);
|
||||
// Make sure all atom matchers are initialized:
|
||||
for (const sp<LogMatchingTracker>& tracker : newAtomMatchers) {
|
||||
EXPECT_TRUE(tracker->mInitialized);
|
||||
}
|
||||
// Make sure preserved atom matchers are the same.
|
||||
EXPECT_EQ(oldAtomMatchers[oldLogTrackerMap.at(simple1Id)],
|
||||
newAtomMatchers[newLogTrackerMap.at(simple1Id)]);
|
||||
EXPECT_EQ(oldAtomMatchers[oldLogTrackerMap.at(combination1Id)],
|
||||
newAtomMatchers[newLogTrackerMap.at(combination1Id)]);
|
||||
// Make sure replaced matchers are different.
|
||||
EXPECT_NE(oldAtomMatchers[oldLogTrackerMap.at(simple2Id)],
|
||||
newAtomMatchers[newLogTrackerMap.at(simple2Id)]);
|
||||
EXPECT_NE(oldAtomMatchers[oldLogTrackerMap.at(combination2Id)],
|
||||
newAtomMatchers[newLogTrackerMap.at(combination2Id)]);
|
||||
|
||||
// Validation, make sure the matchers have the proper ids. Could do more checks here.
|
||||
EXPECT_EQ(newAtomMatchers[0]->getId(), combination3Id);
|
||||
EXPECT_EQ(newAtomMatchers[1]->getId(), simple2Id);
|
||||
EXPECT_EQ(newAtomMatchers[2]->getId(), combination2Id);
|
||||
EXPECT_EQ(newAtomMatchers[3]->getId(), simple1Id);
|
||||
EXPECT_EQ(newAtomMatchers[4]->getId(), simple4Id);
|
||||
EXPECT_EQ(newAtomMatchers[5]->getId(), combination1Id);
|
||||
}
|
||||
|
||||
} // namespace statsd
|
||||
} // namespace os
|
||||
} // namespace android
|
||||
|
||||
#else
|
||||
GTEST_LOG_(INFO) << "This test does nothing.\n";
|
||||
#endif
|
||||
@@ -0,0 +1,708 @@
|
||||
// Copyright (C) 2020 The Android Open Source Project
|
||||
//
|
||||
// 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.
|
||||
|
||||
#include "src/metrics/parsing_utils/metrics_manager_util.h"
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
#include <private/android_filesystem_config.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#include <set>
|
||||
#include <unordered_map>
|
||||
#include <vector>
|
||||
|
||||
#include "frameworks/base/cmds/statsd/src/statsd_config.pb.h"
|
||||
#include "src/condition/ConditionTracker.h"
|
||||
#include "src/matchers/LogMatchingTracker.h"
|
||||
#include "src/metrics/CountMetricProducer.h"
|
||||
#include "src/metrics/GaugeMetricProducer.h"
|
||||
#include "src/metrics/MetricProducer.h"
|
||||
#include "src/metrics/ValueMetricProducer.h"
|
||||
#include "src/state/StateManager.h"
|
||||
#include "tests/metrics/metrics_test_helper.h"
|
||||
#include "tests/statsd_test_util.h"
|
||||
|
||||
using namespace testing;
|
||||
using android::sp;
|
||||
using android::os::statsd::Predicate;
|
||||
using std::map;
|
||||
using std::set;
|
||||
using std::unordered_map;
|
||||
using std::vector;
|
||||
|
||||
#ifdef __ANDROID__
|
||||
|
||||
namespace android {
|
||||
namespace os {
|
||||
namespace statsd {
|
||||
|
||||
namespace {
|
||||
const ConfigKey kConfigKey(0, 12345);
|
||||
const long kAlertId = 3;
|
||||
|
||||
const long timeBaseSec = 1000;
|
||||
|
||||
StatsdConfig buildGoodConfig() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
|
||||
|
||||
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
|
||||
simpleAtomMatcher->add_field_value_matcher()->set_field(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE*/);
|
||||
simpleAtomMatcher->mutable_field_value_matcher(0)->set_eq_int(
|
||||
2 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_ON*/);
|
||||
|
||||
eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_IS_OFF"));
|
||||
|
||||
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
|
||||
simpleAtomMatcher->add_field_value_matcher()->set_field(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE*/);
|
||||
simpleAtomMatcher->mutable_field_value_matcher(0)->set_eq_int(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_OFF*/);
|
||||
|
||||
eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_ON_OR_OFF"));
|
||||
|
||||
AtomMatcher_Combination* combination = eventMatcher->mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_matcher(StringToId("SCREEN_IS_ON"));
|
||||
combination->add_matcher(StringToId("SCREEN_IS_OFF"));
|
||||
|
||||
CountMetric* metric = config.add_count_metric();
|
||||
metric->set_id(3);
|
||||
metric->set_what(StringToId("SCREEN_IS_ON"));
|
||||
metric->set_bucket(ONE_MINUTE);
|
||||
metric->mutable_dimensions_in_what()->set_field(2 /*SCREEN_STATE_CHANGE*/);
|
||||
metric->mutable_dimensions_in_what()->add_child()->set_field(1);
|
||||
|
||||
config.add_no_report_metric(3);
|
||||
|
||||
auto alert = config.add_alert();
|
||||
alert->set_id(kAlertId);
|
||||
alert->set_metric_id(3);
|
||||
alert->set_num_buckets(10);
|
||||
alert->set_refractory_period_secs(100);
|
||||
alert->set_trigger_if_sum_gt(100);
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildCircleMatchers() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
|
||||
|
||||
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
|
||||
simpleAtomMatcher->add_field_value_matcher()->set_field(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE*/);
|
||||
simpleAtomMatcher->mutable_field_value_matcher(0)->set_eq_int(
|
||||
2 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_ON*/);
|
||||
|
||||
eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_ON_OR_OFF"));
|
||||
|
||||
AtomMatcher_Combination* combination = eventMatcher->mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_matcher(StringToId("SCREEN_IS_ON"));
|
||||
// Circle dependency
|
||||
combination->add_matcher(StringToId("SCREEN_ON_OR_OFF"));
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildAlertWithUnknownMetric() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
|
||||
|
||||
CountMetric* metric = config.add_count_metric();
|
||||
metric->set_id(3);
|
||||
metric->set_what(StringToId("SCREEN_IS_ON"));
|
||||
metric->set_bucket(ONE_MINUTE);
|
||||
metric->mutable_dimensions_in_what()->set_field(2 /*SCREEN_STATE_CHANGE*/);
|
||||
metric->mutable_dimensions_in_what()->add_child()->set_field(1);
|
||||
|
||||
auto alert = config.add_alert();
|
||||
alert->set_id(3);
|
||||
alert->set_metric_id(2);
|
||||
alert->set_num_buckets(10);
|
||||
alert->set_refractory_period_secs(100);
|
||||
alert->set_trigger_if_sum_gt(100);
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildMissingMatchers() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
|
||||
|
||||
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
|
||||
simpleAtomMatcher->add_field_value_matcher()->set_field(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE*/);
|
||||
simpleAtomMatcher->mutable_field_value_matcher(0)->set_eq_int(
|
||||
2 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_ON*/);
|
||||
|
||||
eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_ON_OR_OFF"));
|
||||
|
||||
AtomMatcher_Combination* combination = eventMatcher->mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_matcher(StringToId("SCREEN_IS_ON"));
|
||||
// undefined matcher
|
||||
combination->add_matcher(StringToId("ABC"));
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildMissingPredicate() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
CountMetric* metric = config.add_count_metric();
|
||||
metric->set_id(3);
|
||||
metric->set_what(StringToId("SCREEN_EVENT"));
|
||||
metric->set_bucket(ONE_MINUTE);
|
||||
metric->set_condition(StringToId("SOME_CONDITION"));
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_EVENT"));
|
||||
|
||||
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2);
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildDimensionMetricsWithMultiTags() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("BATTERY_VERY_LOW"));
|
||||
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2);
|
||||
|
||||
eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("BATTERY_VERY_VERY_LOW"));
|
||||
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(3);
|
||||
|
||||
eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("BATTERY_LOW"));
|
||||
|
||||
AtomMatcher_Combination* combination = eventMatcher->mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_matcher(StringToId("BATTERY_VERY_LOW"));
|
||||
combination->add_matcher(StringToId("BATTERY_VERY_VERY_LOW"));
|
||||
|
||||
// Count process state changes, slice by uid, while SCREEN_IS_OFF
|
||||
CountMetric* metric = config.add_count_metric();
|
||||
metric->set_id(3);
|
||||
metric->set_what(StringToId("BATTERY_LOW"));
|
||||
metric->set_bucket(ONE_MINUTE);
|
||||
// This case is interesting. We want to dimension across two atoms.
|
||||
metric->mutable_dimensions_in_what()->add_child()->set_field(1);
|
||||
|
||||
auto alert = config.add_alert();
|
||||
alert->set_id(kAlertId);
|
||||
alert->set_metric_id(3);
|
||||
alert->set_num_buckets(10);
|
||||
alert->set_refractory_period_secs(100);
|
||||
alert->set_trigger_if_sum_gt(100);
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildCirclePredicates() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
AtomMatcher* eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
|
||||
|
||||
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
|
||||
simpleAtomMatcher->add_field_value_matcher()->set_field(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE*/);
|
||||
simpleAtomMatcher->mutable_field_value_matcher(0)->set_eq_int(
|
||||
2 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_ON*/);
|
||||
|
||||
eventMatcher = config.add_atom_matcher();
|
||||
eventMatcher->set_id(StringToId("SCREEN_IS_OFF"));
|
||||
|
||||
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
|
||||
simpleAtomMatcher->add_field_value_matcher()->set_field(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE*/);
|
||||
simpleAtomMatcher->mutable_field_value_matcher(0)->set_eq_int(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_OFF*/);
|
||||
|
||||
auto condition = config.add_predicate();
|
||||
condition->set_id(StringToId("SCREEN_IS_ON"));
|
||||
SimplePredicate* simplePredicate = condition->mutable_simple_predicate();
|
||||
simplePredicate->set_start(StringToId("SCREEN_IS_ON"));
|
||||
simplePredicate->set_stop(StringToId("SCREEN_IS_OFF"));
|
||||
|
||||
condition = config.add_predicate();
|
||||
condition->set_id(StringToId("SCREEN_IS_EITHER_ON_OFF"));
|
||||
|
||||
Predicate_Combination* combination = condition->mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_predicate(StringToId("SCREEN_IS_ON"));
|
||||
combination->add_predicate(StringToId("SCREEN_IS_EITHER_ON_OFF"));
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
StatsdConfig buildConfigWithDifferentPredicates() {
|
||||
StatsdConfig config;
|
||||
config.set_id(12345);
|
||||
|
||||
auto pulledAtomMatcher =
|
||||
CreateSimpleAtomMatcher("SUBSYSTEM_SLEEP", util::SUBSYSTEM_SLEEP_STATE);
|
||||
*config.add_atom_matcher() = pulledAtomMatcher;
|
||||
auto screenOnAtomMatcher = CreateScreenTurnedOnAtomMatcher();
|
||||
*config.add_atom_matcher() = screenOnAtomMatcher;
|
||||
auto screenOffAtomMatcher = CreateScreenTurnedOffAtomMatcher();
|
||||
*config.add_atom_matcher() = screenOffAtomMatcher;
|
||||
auto batteryNoneAtomMatcher = CreateBatteryStateNoneMatcher();
|
||||
*config.add_atom_matcher() = batteryNoneAtomMatcher;
|
||||
auto batteryUsbAtomMatcher = CreateBatteryStateUsbMatcher();
|
||||
*config.add_atom_matcher() = batteryUsbAtomMatcher;
|
||||
|
||||
// Simple condition with InitialValue set to default (unknown).
|
||||
auto screenOnUnknownPredicate = CreateScreenIsOnPredicate();
|
||||
*config.add_predicate() = screenOnUnknownPredicate;
|
||||
|
||||
// Simple condition with InitialValue set to false.
|
||||
auto screenOnFalsePredicate = config.add_predicate();
|
||||
screenOnFalsePredicate->set_id(StringToId("ScreenIsOnInitialFalse"));
|
||||
SimplePredicate* simpleScreenOnFalsePredicate =
|
||||
screenOnFalsePredicate->mutable_simple_predicate();
|
||||
simpleScreenOnFalsePredicate->set_start(screenOnAtomMatcher.id());
|
||||
simpleScreenOnFalsePredicate->set_stop(screenOffAtomMatcher.id());
|
||||
simpleScreenOnFalsePredicate->set_initial_value(SimplePredicate_InitialValue_FALSE);
|
||||
|
||||
// Simple condition with InitialValue set to false.
|
||||
auto onBatteryFalsePredicate = config.add_predicate();
|
||||
onBatteryFalsePredicate->set_id(StringToId("OnBatteryInitialFalse"));
|
||||
SimplePredicate* simpleOnBatteryFalsePredicate =
|
||||
onBatteryFalsePredicate->mutable_simple_predicate();
|
||||
simpleOnBatteryFalsePredicate->set_start(batteryNoneAtomMatcher.id());
|
||||
simpleOnBatteryFalsePredicate->set_stop(batteryUsbAtomMatcher.id());
|
||||
simpleOnBatteryFalsePredicate->set_initial_value(SimplePredicate_InitialValue_FALSE);
|
||||
|
||||
// Combination condition with both simple condition InitialValues set to false.
|
||||
auto screenOnFalseOnBatteryFalsePredicate = config.add_predicate();
|
||||
screenOnFalseOnBatteryFalsePredicate->set_id(StringToId("ScreenOnFalseOnBatteryFalse"));
|
||||
screenOnFalseOnBatteryFalsePredicate->mutable_combination()->set_operation(
|
||||
LogicalOperation::AND);
|
||||
addPredicateToPredicateCombination(*screenOnFalsePredicate,
|
||||
screenOnFalseOnBatteryFalsePredicate);
|
||||
addPredicateToPredicateCombination(*onBatteryFalsePredicate,
|
||||
screenOnFalseOnBatteryFalsePredicate);
|
||||
|
||||
// Combination condition with one simple condition InitialValue set to unknown and one set to
|
||||
// false.
|
||||
auto screenOnUnknownOnBatteryFalsePredicate = config.add_predicate();
|
||||
screenOnUnknownOnBatteryFalsePredicate->set_id(StringToId("ScreenOnUnknowneOnBatteryFalse"));
|
||||
screenOnUnknownOnBatteryFalsePredicate->mutable_combination()->set_operation(
|
||||
LogicalOperation::AND);
|
||||
addPredicateToPredicateCombination(screenOnUnknownPredicate,
|
||||
screenOnUnknownOnBatteryFalsePredicate);
|
||||
addPredicateToPredicateCombination(*onBatteryFalsePredicate,
|
||||
screenOnUnknownOnBatteryFalsePredicate);
|
||||
|
||||
// Simple condition metric with initial value false.
|
||||
ValueMetric* metric1 = config.add_value_metric();
|
||||
metric1->set_id(StringToId("ValueSubsystemSleepWhileScreenOnInitialFalse"));
|
||||
metric1->set_what(pulledAtomMatcher.id());
|
||||
*metric1->mutable_value_field() =
|
||||
CreateDimensions(util::SUBSYSTEM_SLEEP_STATE, {4 /* time sleeping field */});
|
||||
metric1->set_bucket(FIVE_MINUTES);
|
||||
metric1->set_condition(screenOnFalsePredicate->id());
|
||||
|
||||
// Simple condition metric with initial value unknown.
|
||||
ValueMetric* metric2 = config.add_value_metric();
|
||||
metric2->set_id(StringToId("ValueSubsystemSleepWhileScreenOnInitialUnknown"));
|
||||
metric2->set_what(pulledAtomMatcher.id());
|
||||
*metric2->mutable_value_field() =
|
||||
CreateDimensions(util::SUBSYSTEM_SLEEP_STATE, {4 /* time sleeping field */});
|
||||
metric2->set_bucket(FIVE_MINUTES);
|
||||
metric2->set_condition(screenOnUnknownPredicate.id());
|
||||
|
||||
// Combination condition metric with initial values false and false.
|
||||
ValueMetric* metric3 = config.add_value_metric();
|
||||
metric3->set_id(StringToId("ValueSubsystemSleepWhileScreenOnFalseDeviceUnpluggedFalse"));
|
||||
metric3->set_what(pulledAtomMatcher.id());
|
||||
*metric3->mutable_value_field() =
|
||||
CreateDimensions(util::SUBSYSTEM_SLEEP_STATE, {4 /* time sleeping field */});
|
||||
metric3->set_bucket(FIVE_MINUTES);
|
||||
metric3->set_condition(screenOnFalseOnBatteryFalsePredicate->id());
|
||||
|
||||
// Combination condition metric with initial values unknown and false.
|
||||
ValueMetric* metric4 = config.add_value_metric();
|
||||
metric4->set_id(StringToId("ValueSubsystemSleepWhileScreenOnUnknownDeviceUnpluggedFalse"));
|
||||
metric4->set_what(pulledAtomMatcher.id());
|
||||
*metric4->mutable_value_field() =
|
||||
CreateDimensions(util::SUBSYSTEM_SLEEP_STATE, {4 /* time sleeping field */});
|
||||
metric4->set_bucket(FIVE_MINUTES);
|
||||
metric4->set_condition(screenOnUnknownOnBatteryFalsePredicate->id());
|
||||
|
||||
return config;
|
||||
}
|
||||
} // anonymous namespace
|
||||
|
||||
TEST(MetricsManagerTest, TestInitialConditions) {
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildConfigWithDifferentPredicates();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
unordered_map<int64_t, int> logTrackerMap;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
EXPECT_TRUE(initStatsdConfig(
|
||||
kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor, periodicAlarmMonitor,
|
||||
timeBaseSec, timeBaseSec, allTagIds, allAtomMatchers, logTrackerMap,
|
||||
allConditionTrackers, allMetricProducers, allAnomalyTrackers, allAlarmTrackers,
|
||||
conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap, alertTrackerMap,
|
||||
metricsWithActivation, noReportMetricIds));
|
||||
ASSERT_EQ(4u, allMetricProducers.size());
|
||||
ASSERT_EQ(5u, allConditionTrackers.size());
|
||||
|
||||
ConditionKey queryKey;
|
||||
vector<ConditionState> conditionCache(5, ConditionState::kNotEvaluated);
|
||||
|
||||
allConditionTrackers[3]->isConditionMet(queryKey, allConditionTrackers, false, conditionCache);
|
||||
allConditionTrackers[4]->isConditionMet(queryKey, allConditionTrackers, false, conditionCache);
|
||||
EXPECT_EQ(ConditionState::kUnknown, conditionCache[0]);
|
||||
EXPECT_EQ(ConditionState::kFalse, conditionCache[1]);
|
||||
EXPECT_EQ(ConditionState::kFalse, conditionCache[2]);
|
||||
EXPECT_EQ(ConditionState::kFalse, conditionCache[3]);
|
||||
EXPECT_EQ(ConditionState::kUnknown, conditionCache[4]);
|
||||
|
||||
EXPECT_EQ(ConditionState::kFalse, allMetricProducers[0]->mCondition);
|
||||
EXPECT_EQ(ConditionState::kUnknown, allMetricProducers[1]->mCondition);
|
||||
EXPECT_EQ(ConditionState::kFalse, allMetricProducers[2]->mCondition);
|
||||
EXPECT_EQ(ConditionState::kUnknown, allMetricProducers[3]->mCondition);
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestGoodConfig) {
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildGoodConfig();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
unordered_map<int64_t, int> logTrackerMap;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
EXPECT_TRUE(initStatsdConfig(
|
||||
kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor, periodicAlarmMonitor,
|
||||
timeBaseSec, timeBaseSec, allTagIds, allAtomMatchers, logTrackerMap,
|
||||
allConditionTrackers, allMetricProducers, allAnomalyTrackers, allAlarmTrackers,
|
||||
conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap, alertTrackerMap,
|
||||
metricsWithActivation, noReportMetricIds));
|
||||
ASSERT_EQ(1u, allMetricProducers.size());
|
||||
ASSERT_EQ(1u, allAnomalyTrackers.size());
|
||||
ASSERT_EQ(1u, noReportMetricIds.size());
|
||||
ASSERT_EQ(1u, alertTrackerMap.size());
|
||||
EXPECT_NE(alertTrackerMap.find(kAlertId), alertTrackerMap.end());
|
||||
EXPECT_EQ(alertTrackerMap.find(kAlertId)->second, 0);
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestDimensionMetricsWithMultiTags) {
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildDimensionMetricsWithMultiTags();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
unordered_map<int64_t, int> logTrackerMap;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
EXPECT_FALSE(initStatsdConfig(
|
||||
kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor, periodicAlarmMonitor,
|
||||
timeBaseSec, timeBaseSec, allTagIds, allAtomMatchers, logTrackerMap,
|
||||
allConditionTrackers, allMetricProducers, allAnomalyTrackers, allAlarmTrackers,
|
||||
conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap, alertTrackerMap,
|
||||
metricsWithActivation, noReportMetricIds));
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestCircleLogMatcherDependency) {
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildCircleMatchers();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
unordered_map<int64_t, int> logTrackerMap;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
EXPECT_FALSE(initStatsdConfig(
|
||||
kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor, periodicAlarmMonitor,
|
||||
timeBaseSec, timeBaseSec, allTagIds, allAtomMatchers, logTrackerMap,
|
||||
allConditionTrackers, allMetricProducers, allAnomalyTrackers, allAlarmTrackers,
|
||||
conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap, alertTrackerMap,
|
||||
metricsWithActivation, noReportMetricIds));
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestMissingMatchers) {
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildMissingMatchers();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
unordered_map<int64_t, int> logTrackerMap;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
EXPECT_FALSE(initStatsdConfig(
|
||||
kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor, periodicAlarmMonitor,
|
||||
timeBaseSec, timeBaseSec, allTagIds, allAtomMatchers, logTrackerMap,
|
||||
allConditionTrackers, allMetricProducers, allAnomalyTrackers, allAlarmTrackers,
|
||||
conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap, alertTrackerMap,
|
||||
metricsWithActivation, noReportMetricIds));
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestMissingPredicate) {
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildMissingPredicate();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
unordered_map<int64_t, int> logTrackerMap;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
EXPECT_FALSE(initStatsdConfig(
|
||||
kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor, periodicAlarmMonitor,
|
||||
timeBaseSec, timeBaseSec, allTagIds, allAtomMatchers, logTrackerMap,
|
||||
allConditionTrackers, allMetricProducers, allAnomalyTrackers, allAlarmTrackers,
|
||||
conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap, alertTrackerMap,
|
||||
metricsWithActivation, noReportMetricIds));
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestCirclePredicateDependency) {
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildCirclePredicates();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
unordered_map<int64_t, int> logTrackerMap;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
EXPECT_FALSE(initStatsdConfig(
|
||||
kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor, periodicAlarmMonitor,
|
||||
timeBaseSec, timeBaseSec, allTagIds, allAtomMatchers, logTrackerMap,
|
||||
allConditionTrackers, allMetricProducers, allAnomalyTrackers, allAlarmTrackers,
|
||||
conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap, alertTrackerMap,
|
||||
metricsWithActivation, noReportMetricIds));
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, testAlertWithUnknownMetric) {
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
sp<StatsPullerManager> pullerManager = new StatsPullerManager();
|
||||
sp<AlarmMonitor> anomalyAlarmMonitor;
|
||||
sp<AlarmMonitor> periodicAlarmMonitor;
|
||||
StatsdConfig config = buildAlertWithUnknownMetric();
|
||||
set<int> allTagIds;
|
||||
vector<sp<LogMatchingTracker>> allAtomMatchers;
|
||||
unordered_map<int64_t, int> logTrackerMap;
|
||||
vector<sp<ConditionTracker>> allConditionTrackers;
|
||||
vector<sp<MetricProducer>> allMetricProducers;
|
||||
std::vector<sp<AnomalyTracker>> allAnomalyTrackers;
|
||||
std::vector<sp<AlarmTracker>> allAlarmTrackers;
|
||||
unordered_map<int, std::vector<int>> conditionToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> trackerToConditionMap;
|
||||
unordered_map<int, std::vector<int>> activationAtomTrackerToMetricMap;
|
||||
unordered_map<int, std::vector<int>> deactivationAtomTrackerToMetricMap;
|
||||
unordered_map<int64_t, int> alertTrackerMap;
|
||||
vector<int> metricsWithActivation;
|
||||
std::set<int64_t> noReportMetricIds;
|
||||
|
||||
EXPECT_FALSE(initStatsdConfig(
|
||||
kConfigKey, config, uidMap, pullerManager, anomalyAlarmMonitor, periodicAlarmMonitor,
|
||||
timeBaseSec, timeBaseSec, allTagIds, allAtomMatchers, logTrackerMap,
|
||||
allConditionTrackers, allMetricProducers, allAnomalyTrackers, allAlarmTrackers,
|
||||
conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
|
||||
activationAtomTrackerToMetricMap, deactivationAtomTrackerToMetricMap, alertTrackerMap,
|
||||
metricsWithActivation, noReportMetricIds));
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestCreateLogTrackerInvalidMatcher) {
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
AtomMatcher matcher;
|
||||
matcher.set_id(21);
|
||||
EXPECT_EQ(createLogTracker(matcher, 0, uidMap), nullptr);
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestCreateLogTrackerSimple) {
|
||||
int index = 1;
|
||||
int64_t id = 123;
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
AtomMatcher matcher;
|
||||
matcher.set_id(id);
|
||||
SimpleAtomMatcher* simpleAtomMatcher = matcher.mutable_simple_atom_matcher();
|
||||
simpleAtomMatcher->set_atom_id(util::SCREEN_STATE_CHANGED);
|
||||
simpleAtomMatcher->add_field_value_matcher()->set_field(
|
||||
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE*/);
|
||||
simpleAtomMatcher->mutable_field_value_matcher(0)->set_eq_int(
|
||||
android::view::DisplayStateEnum::DISPLAY_STATE_ON);
|
||||
|
||||
sp<LogMatchingTracker> tracker = createLogTracker(matcher, index, uidMap);
|
||||
EXPECT_NE(tracker, nullptr);
|
||||
|
||||
EXPECT_TRUE(tracker->mInitialized);
|
||||
EXPECT_EQ(tracker->getId(), id);
|
||||
EXPECT_EQ(tracker->mIndex, index);
|
||||
const set<int>& atomIds = tracker->getAtomIds();
|
||||
ASSERT_EQ(atomIds.size(), 1);
|
||||
EXPECT_EQ(atomIds.count(util::SCREEN_STATE_CHANGED), 1);
|
||||
}
|
||||
|
||||
TEST(MetricsManagerTest, TestCreateLogTrackerCombination) {
|
||||
int index = 1;
|
||||
int64_t id = 123;
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
AtomMatcher matcher;
|
||||
matcher.set_id(id);
|
||||
AtomMatcher_Combination* combination = matcher.mutable_combination();
|
||||
combination->set_operation(LogicalOperation::OR);
|
||||
combination->add_matcher(123);
|
||||
combination->add_matcher(223);
|
||||
|
||||
sp<LogMatchingTracker> tracker = createLogTracker(matcher, index, uidMap);
|
||||
EXPECT_NE(tracker, nullptr);
|
||||
|
||||
// Combination matchers need to be initialized first.
|
||||
EXPECT_FALSE(tracker->mInitialized);
|
||||
EXPECT_EQ(tracker->getId(), id);
|
||||
EXPECT_EQ(tracker->mIndex, index);
|
||||
const set<int>& atomIds = tracker->getAtomIds();
|
||||
ASSERT_EQ(atomIds.size(), 0);
|
||||
}
|
||||
|
||||
} // namespace statsd
|
||||
} // namespace os
|
||||
} // namespace android
|
||||
|
||||
#else
|
||||
GTEST_LOG_(INFO) << "This test does nothing.\n";
|
||||
#endif
|
||||
@@ -15,6 +15,8 @@
|
||||
#include "statsd_test_util.h"
|
||||
|
||||
#include <aidl/android/util/StatsEventParcel.h>
|
||||
|
||||
#include "matchers/SimpleLogMatchingTracker.h"
|
||||
#include "stats_event.h"
|
||||
|
||||
using aidl::android::util::StatsEventParcel;
|
||||
@@ -996,6 +998,20 @@ int64_t StringToId(const string& str) {
|
||||
return static_cast<int64_t>(std::hash<std::string>()(str));
|
||||
}
|
||||
|
||||
sp<EventMatcherWizard> createEventMatcherWizard(
|
||||
int tagId, int matcherIndex, const vector<FieldValueMatcher>& fieldValueMatchers) {
|
||||
sp<UidMap> uidMap = new UidMap();
|
||||
SimpleAtomMatcher atomMatcher;
|
||||
atomMatcher.set_atom_id(tagId);
|
||||
for (const FieldValueMatcher& fvm : fieldValueMatchers) {
|
||||
*atomMatcher.add_field_value_matcher() = fvm;
|
||||
}
|
||||
uint64_t matcherHash = 0x12345678;
|
||||
int64_t matcherId = 678;
|
||||
return new EventMatcherWizard({new SimpleLogMatchingTracker(matcherId, matcherIndex,
|
||||
matcherHash, atomMatcher, uidMap)});
|
||||
}
|
||||
|
||||
void ValidateWakelockAttributionUidAndTagDimension(const DimensionsValue& value, const int atomId,
|
||||
const int uid, const string& tag) {
|
||||
EXPECT_EQ(value.field(), atomId);
|
||||
|
||||
@@ -25,6 +25,7 @@
|
||||
#include "src/StatsLogProcessor.h"
|
||||
#include "src/hash.h"
|
||||
#include "src/logd/LogEvent.h"
|
||||
#include "src/matchers/EventMatcherWizard.h"
|
||||
#include "src/packages/UidMap.h"
|
||||
#include "src/stats_log_util.h"
|
||||
#include "stats_event.h"
|
||||
@@ -335,6 +336,9 @@ void sortLogEventsByTimestamp(std::vector<std::unique_ptr<LogEvent>> *events);
|
||||
|
||||
int64_t StringToId(const string& str);
|
||||
|
||||
sp<EventMatcherWizard> createEventMatcherWizard(
|
||||
int tagId, int matcherIndex, const std::vector<FieldValueMatcher>& fieldValueMatchers = {});
|
||||
|
||||
void ValidateWakelockAttributionUidAndTagDimension(const DimensionsValue& value, const int atomId,
|
||||
const int uid, const string& tag);
|
||||
void ValidateUidDimension(const DimensionsValue& value, int node_idx, int atomId, int uid);
|
||||
|
||||
Reference in New Issue
Block a user