Merge "Fix some nits while reading the code"
diff --git a/api/current.txt b/api/current.txt
index 8925846..9741fbc 100644
--- a/api/current.txt
+++ b/api/current.txt
@@ -31570,6 +31570,7 @@
method public final boolean postAtTime(java.lang.Runnable, long);
method public final boolean postAtTime(java.lang.Runnable, java.lang.Object, long);
method public final boolean postDelayed(java.lang.Runnable, long);
+ method public final boolean postDelayed(java.lang.Runnable, java.lang.Object, long);
method public final void removeCallbacks(java.lang.Runnable);
method public final void removeCallbacks(java.lang.Runnable, java.lang.Object);
method public final void removeCallbacksAndMessages(java.lang.Object);
diff --git a/api/system-current.txt b/api/system-current.txt
index 3e78167..02a1953 100644
--- a/api/system-current.txt
+++ b/api/system-current.txt
@@ -4368,10 +4368,10 @@
}
public final class StatsManager {
- method public boolean addConfiguration(java.lang.String, byte[], java.lang.String, java.lang.String);
- method public byte[] getData(java.lang.String);
+ method public boolean addConfiguration(long, byte[], java.lang.String, java.lang.String);
+ method public byte[] getData(long);
method public byte[] getMetadata();
- method public boolean removeConfiguration(java.lang.String);
+ method public boolean removeConfiguration(long);
}
}
diff --git a/cmds/statsd/src/HashableDimensionKey.cpp b/cmds/statsd/src/HashableDimensionKey.cpp
index 6da1243..288ebe9 100644
--- a/cmds/statsd/src/HashableDimensionKey.cpp
+++ b/cmds/statsd/src/HashableDimensionKey.cpp
@@ -21,8 +21,8 @@
namespace os {
namespace statsd {
-android::hash_t hashDimensionsValue(const DimensionsValue& value) {
- android::hash_t hash = 0;
+android::hash_t hashDimensionsValue(int64_t seed, const DimensionsValue& value) {
+ android::hash_t hash = seed;
hash = android::JenkinsHashMix(hash, android::hash_type(value.field()));
hash = android::JenkinsHashMix(hash, android::hash_type((int)value.value_case()));
@@ -63,6 +63,10 @@
return JenkinsHashWhiten(hash);
}
+android::hash_t hashDimensionsValue(const DimensionsValue& value) {
+ return hashDimensionsValue(0, value);
+}
+
using std::string;
diff --git a/cmds/statsd/src/HashableDimensionKey.h b/cmds/statsd/src/HashableDimensionKey.h
index 3a4ffce..85c317f 100644
--- a/cmds/statsd/src/HashableDimensionKey.h
+++ b/cmds/statsd/src/HashableDimensionKey.h
@@ -53,6 +53,7 @@
DimensionsValue mDimensionsValue;
};
+android::hash_t hashDimensionsValue(int64_t seed, const DimensionsValue& value);
android::hash_t hashDimensionsValue(const DimensionsValue& value);
} // namespace statsd
diff --git a/cmds/statsd/src/StatsLogProcessor.cpp b/cmds/statsd/src/StatsLogProcessor.cpp
index 13f332e..9678014 100644
--- a/cmds/statsd/src/StatsLogProcessor.cpp
+++ b/cmds/statsd/src/StatsLogProcessor.cpp
@@ -54,7 +54,7 @@
const int FIELD_ID_REPORTS = 2;
// for ConfigKey
const int FIELD_ID_UID = 1;
-const int FIELD_ID_NAME = 2;
+const int FIELD_ID_ID = 2;
// for ConfigMetricsReport
const int FIELD_ID_METRICS = 1;
const int FIELD_ID_UID_MAP = 2;
@@ -157,7 +157,7 @@
return;
}
report->mutable_config_key()->set_uid(key.GetUid());
- report->mutable_config_key()->set_name(key.GetName());
+ report->mutable_config_key()->set_id(key.GetId());
ConfigMetricsReport* configMetricsReport = report->add_reports();
it->second->onDumpReport(dumpTimeStampNs, configMetricsReport);
// TODO: dump uid mapping.
@@ -181,7 +181,7 @@
// Start of ConfigKey.
long long configKeyToken = proto.start(FIELD_TYPE_MESSAGE | FIELD_ID_CONFIG_KEY);
proto.write(FIELD_TYPE_INT32 | FIELD_ID_UID, key.GetUid());
- proto.write(FIELD_TYPE_STRING | FIELD_ID_NAME, key.GetName());
+ proto.write(FIELD_TYPE_INT64 | FIELD_ID_ID, (long long)key.GetId());
proto.end(configKeyToken);
// End of ConfigKey.
@@ -278,8 +278,8 @@
vector<uint8_t> data;
onDumpReport(key, &data);
// TODO: Add a guardrail to prevent accumulation of file on disk.
- string file_name = StringPrintf("%s/%d-%s-%ld", STATS_DATA_DIR, key.GetUid(),
- key.GetName().c_str(), time(nullptr));
+ string file_name = StringPrintf("%s/%d-%lld-%ld", STATS_DATA_DIR, key.GetUid(),
+ (long long)key.GetId(), time(nullptr));
StorageManager::writeFile(file_name.c_str(), &data[0], data.size());
}
}
diff --git a/cmds/statsd/src/StatsService.cpp b/cmds/statsd/src/StatsService.cpp
index e8b0bd2..45f1ea1 100644
--- a/cmds/statsd/src/StatsService.cpp
+++ b/cmds/statsd/src/StatsService.cpp
@@ -335,7 +335,7 @@
print_cmd_help(out);
return UNKNOWN_ERROR;
}
- auto receiver = mConfigManager->GetConfigReceiver(ConfigKey(uid, name));
+ auto receiver = mConfigManager->GetConfigReceiver(ConfigKey(uid, StrToInt64(name)));
sp<IStatsCompanionService> sc = getStatsCompanionService();
if (sc != nullptr) {
sc->sendBroadcast(String16(receiver.first.c_str()), String16(receiver.second.c_str()));
@@ -404,13 +404,13 @@
}
// Add / update the config.
- mConfigManager->UpdateConfig(ConfigKey(uid, name), config);
+ mConfigManager->UpdateConfig(ConfigKey(uid, StrToInt64(name)), config);
} else {
if (argCount == 2) {
cmd_remove_all_configs(out);
} else {
// Remove the config.
- mConfigManager->RemoveConfig(ConfigKey(uid, name));
+ mConfigManager->RemoveConfig(ConfigKey(uid, StrToInt64(name)));
}
}
@@ -459,7 +459,7 @@
}
if (good) {
vector<uint8_t> data;
- mProcessor->onDumpReport(ConfigKey(uid, name), &data);
+ mProcessor->onDumpReport(ConfigKey(uid, StrToInt64(name)), &data);
// TODO: print the returned StatsLogReport to file instead of printing to logcat.
if (proto) {
for (size_t i = 0; i < data.size(); i ++) {
@@ -699,12 +699,11 @@
mProcessor->OnLogEvent(event);
}
-Status StatsService::getData(const String16& key, vector<uint8_t>* output) {
+Status StatsService::getData(int64_t key, vector<uint8_t>* output) {
IPCThreadState* ipc = IPCThreadState::self();
VLOG("StatsService::getData with Pid %i, Uid %i", ipc->getCallingPid(), ipc->getCallingUid());
if (checkCallingPermission(String16(kPermissionDump))) {
- string keyStr = string(String8(key).string());
- ConfigKey configKey(ipc->getCallingUid(), keyStr);
+ ConfigKey configKey(ipc->getCallingUid(), key);
mProcessor->onDumpReport(configKey, output);
return Status::ok();
} else {
@@ -724,14 +723,13 @@
}
}
-Status StatsService::addConfiguration(const String16& key,
+Status StatsService::addConfiguration(int64_t key,
const vector <uint8_t>& config,
const String16& package, const String16& cls,
bool* success) {
IPCThreadState* ipc = IPCThreadState::self();
if (checkCallingPermission(String16(kPermissionDump))) {
- string keyString = string(String8(key).string());
- ConfigKey configKey(ipc->getCallingUid(), keyString);
+ ConfigKey configKey(ipc->getCallingUid(), key);
StatsdConfig cfg;
if (!cfg.ParseFromArray(&config[0], config.size())) {
*success = false;
@@ -748,11 +746,10 @@
}
}
-Status StatsService::removeConfiguration(const String16& key, bool* success) {
+Status StatsService::removeConfiguration(int64_t key, bool* success) {
IPCThreadState* ipc = IPCThreadState::self();
if (checkCallingPermission(String16(kPermissionDump))) {
- string keyStr = string(String8(key).string());
- mConfigManager->RemoveConfig(ConfigKey(ipc->getCallingUid(), keyStr));
+ mConfigManager->RemoveConfig(ConfigKey(ipc->getCallingUid(), key));
*success = true;
return Status::ok();
} else {
diff --git a/cmds/statsd/src/StatsService.h b/cmds/statsd/src/StatsService.h
index 08fcdac..c0424f3 100644
--- a/cmds/statsd/src/StatsService.h
+++ b/cmds/statsd/src/StatsService.h
@@ -77,25 +77,27 @@
/**
* Binder call for clients to request data for this configuration key.
*/
- virtual Status getData(const String16& key, vector<uint8_t>* output) override;
+ virtual Status getData(int64_t key, vector<uint8_t>* output) override;
+
/**
* Binder call for clients to get metadata across all configs in statsd.
*/
virtual Status getMetadata(vector<uint8_t>* output) override;
+
/**
* Binder call to let clients send a configuration and indicate they're interested when they
* should requestData for this configuration.
*/
- virtual Status addConfiguration(const String16& key, const vector <uint8_t>& config,
- const String16& package, const String16& cls, bool* success)
+ virtual Status addConfiguration(int64_t key, const vector <uint8_t>& config,
+ const String16& package, const String16& cls, bool* success)
override;
/**
* Binder call to allow clients to remove the specified configuration.
*/
- virtual Status removeConfiguration(const String16& key, bool* success) override;
+ virtual Status removeConfiguration(int64_t key, bool* success) override;
// TODO: public for testing since statsd doesn't run when system starts. Change to private
// later.
diff --git a/cmds/statsd/src/anomaly/AnomalyTracker.cpp b/cmds/statsd/src/anomaly/AnomalyTracker.cpp
index f8a9413..9c797dc 100644
--- a/cmds/statsd/src/anomaly/AnomalyTracker.cpp
+++ b/cmds/statsd/src/anomaly/AnomalyTracker.cpp
@@ -205,23 +205,21 @@
// TODO: If we had access to the bucket_size_millis, consider calling resetStorage()
// if (mAlert.refractory_period_secs() > mNumOfPastBuckets * bucketSizeNs) { resetStorage(); }
- if (mAlert.has_incidentd_details()) {
- if (mAlert.has_name()) {
- ALOGI("An anomaly (%s) has occurred! Informing incidentd.",
- mAlert.name().c_str());
+ if (!mSubscriptions.empty()) {
+ if (mAlert.has_id()) {
+ ALOGI("An anomaly (%llu) has occurred! Informing subscribers.",mAlert.id());
+ informSubscribers();
} else {
- // TODO: Can construct a name based on the criteria (and/or relay the criteria).
- ALOGI("An anomaly (nameless) has occurred! Informing incidentd.");
+ ALOGI("An anomaly (with no id) has occurred! Not informing any subscribers.");
}
- informIncidentd();
} else {
- ALOGI("An anomaly has occurred! (But informing incidentd not requested.)");
+ ALOGI("An anomaly has occurred! (But no subscriber for that alert.)");
}
- StatsdStats::getInstance().noteAnomalyDeclared(mConfigKey, mAlert.name());
+ StatsdStats::getInstance().noteAnomalyDeclared(mConfigKey, mAlert.id());
android::util::stats_write(android::util::ANOMALY_DETECTED, mConfigKey.GetUid(),
- mConfigKey.GetName().c_str(), mAlert.name().c_str());
+ mConfigKey.GetId(), mAlert.id());
}
void AnomalyTracker::detectAndDeclareAnomaly(const uint64_t& timestampNs,
@@ -246,27 +244,46 @@
timestampNs - mLastAnomalyTimestampNs <= mAlert.refractory_period_secs() * NS_PER_SEC;
}
-void AnomalyTracker::informIncidentd() {
- VLOG("informIncidentd called.");
- if (!mAlert.has_incidentd_details()) {
- ALOGE("Attempted to call incidentd without any incidentd_details.");
- return;
- }
- sp<IIncidentManager> service = interface_cast<IIncidentManager>(
- defaultServiceManager()->getService(android::String16("incident")));
- if (service == NULL) {
- ALOGW("Couldn't get the incident service.");
+void AnomalyTracker::informSubscribers() {
+ VLOG("informSubscribers called.");
+ if (mSubscriptions.empty()) {
+ ALOGE("Attempt to call with no subscribers.");
return;
}
- IncidentReportArgs incidentReport;
- const Alert::IncidentdDetails& details = mAlert.incidentd_details();
- for (int i = 0; i < details.section_size(); i++) {
- incidentReport.addSection(details.section(i));
+ std::set<int> incidentdSections;
+ for (const Subscription& subscription : mSubscriptions) {
+ switch (subscription.subscriber_information_case()) {
+ case Subscription::SubscriberInformationCase::kIncidentdDetails:
+ for (int i = 0; i < subscription.incidentd_details().section_size(); i++) {
+ incidentdSections.insert(subscription.incidentd_details().section(i));
+ }
+ break;
+ case Subscription::SubscriberInformationCase::kPerfettoDetails:
+ ALOGW("Perfetto reports not implemented.");
+ break;
+ default:
+ break;
+ }
}
- // TODO: Pass in mAlert.name() into the addHeader?
-
- service->reportIncident(incidentReport);
+ if (!incidentdSections.empty()) {
+ sp<IIncidentManager> service = interface_cast<IIncidentManager>(
+ defaultServiceManager()->getService(android::String16("incident")));
+ if (service != NULL) {
+ IncidentReportArgs incidentReport;
+ for (const auto section : incidentdSections) {
+ incidentReport.addSection(section);
+ }
+ int64_t alertId = mAlert.id();
+ std::vector<uint8_t> header;
+ uint8_t* src = static_cast<uint8_t*>(static_cast<void*>(&alertId));
+ header.insert(header.end(), src, src + sizeof(int64_t));
+ incidentReport.addHeader(header);
+ service->reportIncident(incidentReport);
+ } else {
+ ALOGW("Couldn't get the incident service.");
+ }
+ }
}
} // namespace statsd
diff --git a/cmds/statsd/src/anomaly/AnomalyTracker.h b/cmds/statsd/src/anomaly/AnomalyTracker.h
index 48f0203..2d5ab86 100644
--- a/cmds/statsd/src/anomaly/AnomalyTracker.h
+++ b/cmds/statsd/src/anomaly/AnomalyTracker.h
@@ -40,6 +40,11 @@
virtual ~AnomalyTracker();
+ // Add subscriptions that depend on this alert.
+ void addSubscription(const Subscription& subscription) {
+ mSubscriptions.push_back(subscription);
+ }
+
// Adds a bucket.
// Bucket index starts from 0.
void addPastBucket(std::shared_ptr<DimToValMap> bucketValues, const int64_t& bucketNum);
@@ -97,6 +102,9 @@
// statsd_config.proto Alert message that defines this tracker.
const Alert mAlert;
+ // The subscriptions that depend on this alert.
+ std::vector<Subscription> mSubscriptions;
+
// A reference to the Alert's config key.
const ConfigKey& mConfigKey;
@@ -104,7 +112,7 @@
// for the anomaly detection (since the current bucket is not in the past).
int mNumOfPastBuckets;
- // The exisiting bucket list.
+ // The existing bucket list.
std::vector<shared_ptr<DimToValMap>> mPastBuckets;
// Sum over all existing buckets cached in mPastBuckets.
@@ -133,8 +141,8 @@
// Resets all bucket data. For use when all the data gets stale.
virtual void resetStorage();
- // Informs the incident service that an anomaly has occurred.
- void informIncidentd();
+ // Informs the subscribers that an anomaly has occurred.
+ void informSubscribers();
FRIEND_TEST(AnomalyTrackerTest, TestConsecutiveBuckets);
FRIEND_TEST(AnomalyTrackerTest, TestSparseBuckets);
diff --git a/cmds/statsd/src/atoms.proto b/cmds/statsd/src/atoms.proto
index 1ee86f0..221a554 100644
--- a/cmds/statsd/src/atoms.proto
+++ b/cmds/statsd/src/atoms.proto
@@ -845,11 +845,11 @@
// Uid that owns the config whose anomaly detection alert fired.
optional int32 config_uid = 1;
- // Name of the config whose anomaly detection alert fired.
- optional string config_name = 2;
+ // Id of the config whose anomaly detection alert fired.
+ optional int64 config_id = 2;
- // Name of the alert (i.e. name of the anomaly that was detected).
- optional string alert_name = 3;
+ // Id of the alert (i.e. name of the anomaly that was detected).
+ optional int64 alert_id = 3;
}
/**
diff --git a/cmds/statsd/src/condition/CombinationConditionTracker.cpp b/cmds/statsd/src/condition/CombinationConditionTracker.cpp
index 52b83d8..afa26f6 100644
--- a/cmds/statsd/src/condition/CombinationConditionTracker.cpp
+++ b/cmds/statsd/src/condition/CombinationConditionTracker.cpp
@@ -30,20 +30,20 @@
using std::unordered_map;
using std::vector;
-CombinationConditionTracker::CombinationConditionTracker(const string& name, const int index)
- : ConditionTracker(name, index) {
- VLOG("creating CombinationConditionTracker %s", mName.c_str());
+CombinationConditionTracker::CombinationConditionTracker(const int64_t& id, const int index)
+ : ConditionTracker(id, index) {
+ VLOG("creating CombinationConditionTracker %lld", (long long)mConditionId);
}
CombinationConditionTracker::~CombinationConditionTracker() {
- VLOG("~CombinationConditionTracker() %s", mName.c_str());
+ VLOG("~CombinationConditionTracker() %lld", (long long)mConditionId);
}
bool CombinationConditionTracker::init(const vector<Predicate>& allConditionConfig,
const vector<sp<ConditionTracker>>& allConditionTrackers,
- const unordered_map<string, int>& conditionNameIndexMap,
+ const unordered_map<int64_t, int>& conditionIdIndexMap,
vector<bool>& stack) {
- VLOG("Combination predicate init() %s", mName.c_str());
+ VLOG("Combination predicate init() %lld", (long long)mConditionId);
if (mInitialized) {
return true;
}
@@ -62,11 +62,11 @@
return false;
}
- for (string child : combinationCondition.predicate()) {
- auto it = conditionNameIndexMap.find(child);
+ for (auto child : combinationCondition.predicate()) {
+ auto it = conditionIdIndexMap.find(child);
- if (it == conditionNameIndexMap.end()) {
- ALOGW("Predicate %s not found in the config", child.c_str());
+ if (it == conditionIdIndexMap.end()) {
+ ALOGW("Predicate %lld not found in the config", (long long)child);
return false;
}
@@ -79,13 +79,13 @@
}
bool initChildSucceeded = childTracker->init(allConditionConfig, allConditionTrackers,
- conditionNameIndexMap, stack);
+ conditionIdIndexMap, stack);
if (!initChildSucceeded) {
- ALOGW("Child initialization failed %s ", child.c_str());
+ ALOGW("Child initialization failed %lld ", (long long)child);
return false;
} else {
- ALOGW("Child initialization success %s ", child.c_str());
+ ALOGW("Child initialization success %lld ", (long long)child);
}
mChildren.push_back(childIndex);
@@ -154,8 +154,8 @@
}
}
nonSlicedConditionCache[mIndex] = ConditionState::kUnknown;
- ALOGD("CombinationPredicate %s sliced may changed? %d", mName.c_str(),
- conditionChangedCache[mIndex] == true);
+ ALOGD("CombinationPredicate %lld sliced may changed? %d", (long long)mConditionId,
+ conditionChangedCache[mIndex] == true);
}
}
diff --git a/cmds/statsd/src/condition/CombinationConditionTracker.h b/cmds/statsd/src/condition/CombinationConditionTracker.h
index 8942833..dfd3837 100644
--- a/cmds/statsd/src/condition/CombinationConditionTracker.h
+++ b/cmds/statsd/src/condition/CombinationConditionTracker.h
@@ -26,13 +26,13 @@
class CombinationConditionTracker : public virtual ConditionTracker {
public:
- CombinationConditionTracker(const std::string& name, const int index);
+ CombinationConditionTracker(const int64_t& id, const int index);
~CombinationConditionTracker();
bool init(const std::vector<Predicate>& allConditionConfig,
const std::vector<sp<ConditionTracker>>& allConditionTrackers,
- const std::unordered_map<std::string, int>& conditionNameIndexMap,
+ const std::unordered_map<int64_t, int>& conditionIdIndexMap,
std::vector<bool>& stack) override;
void evaluateCondition(const LogEvent& event,
diff --git a/cmds/statsd/src/condition/ConditionTracker.h b/cmds/statsd/src/condition/ConditionTracker.h
index 1154b6f..773860f 100644
--- a/cmds/statsd/src/condition/ConditionTracker.h
+++ b/cmds/statsd/src/condition/ConditionTracker.h
@@ -32,8 +32,8 @@
class ConditionTracker : public virtual RefBase {
public:
- ConditionTracker(const std::string& name, const int index)
- : mName(name),
+ ConditionTracker(const int64_t& id, const int index)
+ : mConditionId(id),
mIndex(index),
mInitialized(false),
mTrackerIndex(),
@@ -42,7 +42,7 @@
virtual ~ConditionTracker(){};
- inline const string& getName() { return mName; }
+ inline const int64_t& getId() { return mConditionId; }
// Initialize this ConditionTracker. This initialization is done recursively (DFS). It can also
// be done in the constructor, but we do it separately because (1) easy to return a bool to
@@ -50,11 +50,11 @@
// allConditionConfig: the list of all Predicate config from statsd_config.
// allConditionTrackers: the list of all ConditionTrackers (this is needed because we may also
// need to call init() on children conditions)
- // conditionNameIndexMap: the mapping from condition name to its index.
+ // conditionIdIndexMap: the mapping from condition id to its index.
// stack: a bit map to keep track which nodes have been visited on the stack in the recursion.
virtual bool init(const std::vector<Predicate>& allConditionConfig,
const std::vector<sp<ConditionTracker>>& allConditionTrackers,
- const std::unordered_map<std::string, int>& conditionNameIndexMap,
+ const std::unordered_map<int64_t, int>& conditionIdIndexMap,
std::vector<bool>& stack) = 0;
// evaluate current condition given the new event.
@@ -99,9 +99,7 @@
}
protected:
- // We don't really need the string name, but having a name here makes log messages
- // easy to debug.
- const std::string mName;
+ const int64_t mConditionId;
// the index of this condition in the manager's condition list.
const int mIndex;
diff --git a/cmds/statsd/src/condition/SimpleConditionTracker.cpp b/cmds/statsd/src/condition/SimpleConditionTracker.cpp
index 1803cbb..2525721 100644
--- a/cmds/statsd/src/condition/SimpleConditionTracker.cpp
+++ b/cmds/statsd/src/condition/SimpleConditionTracker.cpp
@@ -33,17 +33,17 @@
using std::vector;
SimpleConditionTracker::SimpleConditionTracker(
- const ConfigKey& key, const string& name, const int index,
+ const ConfigKey& key, const int64_t& id, const int index,
const SimplePredicate& simplePredicate,
- const unordered_map<string, int>& trackerNameIndexMap)
- : ConditionTracker(name, index), mConfigKey(key) {
- VLOG("creating SimpleConditionTracker %s", mName.c_str());
+ const unordered_map<int64_t, int>& trackerNameIndexMap)
+ : ConditionTracker(id, index), mConfigKey(key) {
+ VLOG("creating SimpleConditionTracker %lld", (long long)mConditionId);
mCountNesting = simplePredicate.count_nesting();
if (simplePredicate.has_start()) {
auto pair = trackerNameIndexMap.find(simplePredicate.start());
if (pair == trackerNameIndexMap.end()) {
- ALOGW("Start matcher %s not found in the config", simplePredicate.start().c_str());
+ ALOGW("Start matcher %lld not found in the config", (long long)simplePredicate.start());
return;
}
mStartLogMatcherIndex = pair->second;
@@ -55,7 +55,7 @@
if (simplePredicate.has_stop()) {
auto pair = trackerNameIndexMap.find(simplePredicate.stop());
if (pair == trackerNameIndexMap.end()) {
- ALOGW("Stop matcher %s not found in the config", simplePredicate.stop().c_str());
+ ALOGW("Stop matcher %lld not found in the config", (long long)simplePredicate.stop());
return;
}
mStopLogMatcherIndex = pair->second;
@@ -67,7 +67,7 @@
if (simplePredicate.has_stop_all()) {
auto pair = trackerNameIndexMap.find(simplePredicate.stop_all());
if (pair == trackerNameIndexMap.end()) {
- ALOGW("Stop all matcher %s not found in the config", simplePredicate.stop().c_str());
+ ALOGW("Stop all matcher %lld found in the config", (long long)simplePredicate.stop_all());
return;
}
mStopAllLogMatcherIndex = pair->second;
@@ -99,15 +99,15 @@
bool SimpleConditionTracker::init(const vector<Predicate>& allConditionConfig,
const vector<sp<ConditionTracker>>& allConditionTrackers,
- const unordered_map<string, int>& conditionNameIndexMap,
+ const unordered_map<int64_t, int>& conditionIdIndexMap,
vector<bool>& stack) {
// SimpleConditionTracker does not have dependency on other conditions, thus we just return
// if the initialization was successful.
return mInitialized;
}
-void print(map<HashableDimensionKey, int>& conditions, const string& name) {
- VLOG("%s DUMP:", name.c_str());
+void print(map<HashableDimensionKey, int>& conditions, const int64_t& id) {
+ VLOG("%lld DUMP:", (long long)id);
for (const auto& pair : conditions) {
VLOG("\t%s : %d", pair.first.c_str(), pair.second);
}
@@ -135,10 +135,11 @@
// 1. Report the tuple count if the tuple count > soft limit
if (mSlicedConditionState.size() > StatsdStats::kDimensionKeySizeSoftLimit - 1) {
size_t newTupleCount = mSlicedConditionState.size() + 1;
- StatsdStats::getInstance().noteConditionDimensionSize(mConfigKey, mName, newTupleCount);
+ StatsdStats::getInstance().noteConditionDimensionSize(mConfigKey, mConditionId, newTupleCount);
// 2. Don't add more tuples, we are above the allowed threshold. Drop the data.
if (newTupleCount > StatsdStats::kDimensionKeySizeHardLimit) {
- ALOGE("Predicate %s dropping data for dimension key %s", mName.c_str(), newKey.c_str());
+ ALOGE("Predicate %lld dropping data for dimension key %s",
+ (long long)mConditionId, newKey.c_str());
return true;
}
}
@@ -222,13 +223,13 @@
// dump all dimensions for debugging
if (DEBUG) {
- print(mSlicedConditionState, mName);
+ print(mSlicedConditionState, mConditionId);
}
conditionChangedCache[mIndex] = changed;
conditionCache[mIndex] = newCondition;
- VLOG("SimplePredicate %s nonSlicedChange? %d", mName.c_str(),
+ VLOG("SimplePredicate %lld nonSlicedChange? %d", (long long)mConditionId,
conditionChangedCache[mIndex] == true);
}
@@ -239,7 +240,8 @@
vector<bool>& conditionChangedCache) {
if (conditionCache[mIndex] != ConditionState::kNotEvaluated) {
// it has been evaluated.
- VLOG("Yes, already evaluated, %s %d", mName.c_str(), conditionCache[mIndex]);
+ VLOG("Yes, already evaluated, %lld %d",
+ (long long)mConditionId, conditionCache[mIndex]);
return;
}
@@ -320,11 +322,11 @@
const ConditionKey& conditionParameters,
const vector<sp<ConditionTracker>>& allConditions,
vector<ConditionState>& conditionCache) const {
- const auto pair = conditionParameters.find(mName);
+ const auto pair = conditionParameters.find(mConditionId);
if (pair == conditionParameters.end() && mOutputDimensions.child_size() > 0) {
- ALOGE("Predicate %s output has dimension, but it's not specified in the query!",
- mName.c_str());
+ ALOGE("Predicate %lld output has dimension, but it's not specified in the query!",
+ (long long)mConditionId);
conditionCache[mIndex] = mInitialValue;
return;
}
@@ -343,7 +345,7 @@
}
}
conditionCache[mIndex] = conditionState;
- VLOG("Predicate %s return %d", mName.c_str(), conditionCache[mIndex]);
+ VLOG("Predicate %lld return %d", (long long)mConditionId, conditionCache[mIndex]);
}
} // namespace statsd
diff --git a/cmds/statsd/src/condition/SimpleConditionTracker.h b/cmds/statsd/src/condition/SimpleConditionTracker.h
index 5048635..815b445 100644
--- a/cmds/statsd/src/condition/SimpleConditionTracker.h
+++ b/cmds/statsd/src/condition/SimpleConditionTracker.h
@@ -29,15 +29,15 @@
class SimpleConditionTracker : public virtual ConditionTracker {
public:
- SimpleConditionTracker(const ConfigKey& key, const std::string& name, const int index,
+ SimpleConditionTracker(const ConfigKey& key, const int64_t& id, const int index,
const SimplePredicate& simplePredicate,
- const std::unordered_map<std::string, int>& trackerNameIndexMap);
+ const std::unordered_map<int64_t, int>& trackerNameIndexMap);
~SimpleConditionTracker();
bool init(const std::vector<Predicate>& allConditionConfig,
const std::vector<sp<ConditionTracker>>& allConditionTrackers,
- const std::unordered_map<std::string, int>& conditionNameIndexMap,
+ const std::unordered_map<int64_t, int>& conditionIdIndexMap,
std::vector<bool>& stack) override;
void evaluateCondition(const LogEvent& event,
diff --git a/cmds/statsd/src/config/ConfigKey.cpp b/cmds/statsd/src/config/ConfigKey.cpp
index a365dc0..d791f86 100644
--- a/cmds/statsd/src/config/ConfigKey.cpp
+++ b/cmds/statsd/src/config/ConfigKey.cpp
@@ -27,10 +27,10 @@
ConfigKey::ConfigKey() {
}
-ConfigKey::ConfigKey(const ConfigKey& that) : mName(that.mName), mUid(that.mUid) {
+ConfigKey::ConfigKey(const ConfigKey& that) : mId(that.mId), mUid(that.mUid) {
}
-ConfigKey::ConfigKey(int uid, const string& name) : mName(name), mUid(uid) {
+ConfigKey::ConfigKey(int uid, const int64_t& id) : mId(id), mUid(uid) {
}
ConfigKey::~ConfigKey() {
@@ -38,10 +38,21 @@
string ConfigKey::ToString() const {
ostringstream out;
- out << '(' << mUid << ',' << mName << ')';
+ out << '(' << mUid << ',' << mId << ')';
return out.str();
}
+
+int64_t StrToInt64(const string& str) {
+ char* endp;
+ int64_t value;
+ value = strtoll(str.c_str(), &endp, 0);
+ if (endp == str.c_str() || *endp != '\0') {
+ value = 0;
+ }
+ return value;
+}
+
} // namespace statsd
} // namespace os
} // namespace android
diff --git a/cmds/statsd/src/config/ConfigKey.h b/cmds/statsd/src/config/ConfigKey.h
index 3489c43..3ad0eed 100644
--- a/cmds/statsd/src/config/ConfigKey.h
+++ b/cmds/statsd/src/config/ConfigKey.h
@@ -37,14 +37,14 @@
public:
ConfigKey();
explicit ConfigKey(const ConfigKey& that);
- ConfigKey(int uid, const string& name);
+ ConfigKey(int uid, const int64_t& id);
~ConfigKey();
inline int GetUid() const {
return mUid;
}
- inline const string& GetName() const {
- return mName;
+ inline const int64_t& GetId() const {
+ return mId;
}
inline bool operator<(const ConfigKey& that) const {
@@ -54,17 +54,17 @@
if (mUid > that.mUid) {
return false;
}
- return mName < that.mName;
+ return mId < that.mId;
};
inline bool operator==(const ConfigKey& that) const {
- return mUid == that.mUid && mName == that.mName;
+ return mUid == that.mUid && mId == that.mId;
};
string ToString() const;
private:
- string mName;
+ int64_t mId;
int mUid;
};
@@ -72,6 +72,8 @@
return os << config.ToString();
}
+int64_t StrToInt64(const string& str);
+
} // namespace statsd
} // namespace os
} // namespace android
@@ -87,7 +89,7 @@
template <>
struct hash<ConfigKey> {
std::size_t operator()(const ConfigKey& key) const {
- return (7 * key.GetUid()) ^ ((hash<string>()(key.GetName())));
+ return (7 * key.GetUid()) ^ ((hash<long long>()(key.GetId())));
}
};
diff --git a/cmds/statsd/src/config/ConfigManager.cpp b/cmds/statsd/src/config/ConfigManager.cpp
index addc111..5cf8b9b 100644
--- a/cmds/statsd/src/config/ConfigManager.cpp
+++ b/cmds/statsd/src/config/ConfigManager.cpp
@@ -103,7 +103,7 @@
}
void ConfigManager::remove_saved_configs(const ConfigKey& key) {
- string prefix = StringPrintf("%d-%s", key.GetUid(), key.GetName().c_str());
+ string prefix = StringPrintf("%d-%lld", key.GetUid(), (long long)key.GetId());
StorageManager::deletePrefixedFiles(STATS_SERVICE_DIR, prefix.c_str());
}
@@ -173,7 +173,7 @@
fprintf(out, "CONFIGURATIONS (%d)\n", (int)mConfigs.size());
fprintf(out, " uid name\n");
for (const auto& key : mConfigs) {
- fprintf(out, " %6d %s\n", key.GetUid(), key.GetName().c_str());
+ fprintf(out, " %6d %lld\n", key.GetUid(), (long long)key.GetId());
auto receiverIt = mConfigReceivers.find(key);
if (receiverIt != mConfigReceivers.end()) {
fprintf(out, " -> received by %s, %s\n", receiverIt->second.first.c_str(),
@@ -189,8 +189,8 @@
remove_saved_configs(key);
// Then we save the latest config.
- string file_name = StringPrintf("%s/%d-%s-%ld", STATS_SERVICE_DIR, key.GetUid(),
- key.GetName().c_str(), time(nullptr));
+ string file_name = StringPrintf("%s/%d-%lld-%ld", STATS_SERVICE_DIR, key.GetUid(),
+ (long long)key.GetId(), time(nullptr));
const int numBytes = config.ByteSize();
vector<uint8_t> buffer(numBytes);
config.SerializeToArray(&buffer[0], numBytes);
@@ -200,7 +200,7 @@
StatsdConfig build_fake_config() {
// HACK: Hard code a test metric for counting screen on events...
StatsdConfig config;
- config.set_name("CONFIG_12345");
+ config.set_id(12345);
int WAKE_LOCK_TAG_ID = 1111; // put a fake id here to make testing easier.
int WAKE_LOCK_UID_KEY_ID = 1;
@@ -232,14 +232,14 @@
// Count Screen ON events.
CountMetric* metric = config.add_count_metric();
- metric->set_name("METRIC_1");
- metric->set_what("SCREEN_TURNED_ON");
+ metric->set_id(1); // METRIC_1
+ metric->set_what(102); // "SCREEN_TURNED_ON"
metric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
// Anomaly threshold for screen-on count.
// TODO(b/70627390): Uncomment once the bug is fixed.
/*Alert* alert = config.add_alert();
- alert->set_name("ALERT_1");
+ alert->set_id("ALERT_1");
alert->set_metric_name("METRIC_1");
alert->set_number_of_buckets(6);
alert->set_trigger_if_sum_gt(10);
@@ -256,8 +256,8 @@
// Count process state changes, slice by uid.
metric = config.add_count_metric();
- metric->set_name("METRIC_2");
- metric->set_what("PROCESS_STATE_CHANGE");
+ metric->set_id(2); // "METRIC_2"
+ metric->set_what(104);
metric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
FieldMatcher* dimensions = metric->mutable_dimensions();
dimensions->set_field(UID_PROCESS_STATE_TAG_ID);
@@ -267,7 +267,7 @@
// TODO(b/70627390): Uncomment once the bug is fixed.
/*
alert = config.add_alert();
- alert->set_name("ALERT_2");
+ alert->set_id("ALERT_2");
alert->set_metric_name("METRIC_2");
alert->set_number_of_buckets(4);
alert->set_trigger_if_sum_gt(30);
@@ -278,28 +278,28 @@
// Count process state changes, slice by uid, while SCREEN_IS_OFF
metric = config.add_count_metric();
- metric->set_name("METRIC_3");
- metric->set_what("PROCESS_STATE_CHANGE");
+ metric->set_id(3);
+ metric->set_what(104);
metric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
dimensions = metric->mutable_dimensions();
dimensions->set_field(UID_PROCESS_STATE_TAG_ID);
dimensions->add_child()->set_field(UID_PROCESS_STATE_UID_KEY);
- metric->set_condition("SCREEN_IS_OFF");
+ metric->set_condition(202);
// Count wake lock, slice by uid, while SCREEN_IS_ON and app in background
metric = config.add_count_metric();
- metric->set_name("METRIC_4");
- metric->set_what("APP_GET_WL");
+ metric->set_id(4);
+ metric->set_what(107);
metric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
dimensions = metric->mutable_dimensions();
dimensions->set_field(WAKE_LOCK_TAG_ID);
dimensions->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
- metric->set_condition("APP_IS_BACKGROUND_AND_SCREEN_ON");
+ metric->set_condition(204);
MetricConditionLink* link = metric->add_links();
- link->set_condition("APP_IS_BACKGROUND");
+ link->set_condition(203);
link->mutable_dimensions_in_what()->set_field(WAKE_LOCK_TAG_ID);
link->mutable_dimensions_in_what()->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
link->mutable_dimensions_in_condition()->set_field(APP_USAGE_TAG_ID);
@@ -307,16 +307,16 @@
// Duration of an app holding any wl, while screen on and app in background, slice by uid
DurationMetric* durationMetric = config.add_duration_metric();
- durationMetric->set_name("METRIC_5");
+ durationMetric->set_id(5);
durationMetric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
durationMetric->set_aggregation_type(DurationMetric_AggregationType_SUM);
dimensions = durationMetric->mutable_dimensions();
dimensions->set_field(WAKE_LOCK_TAG_ID);
dimensions->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
- durationMetric->set_what("WL_HELD_PER_APP_PER_NAME");
- durationMetric->set_condition("APP_IS_BACKGROUND_AND_SCREEN_ON");
+ durationMetric->set_what(205);
+ durationMetric->set_condition(204);
link = durationMetric->add_links();
- link->set_condition("APP_IS_BACKGROUND");
+ link->set_condition(203);
link->mutable_dimensions_in_what()->set_field(WAKE_LOCK_TAG_ID);
link->mutable_dimensions_in_what()->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
link->mutable_dimensions_in_condition()->set_field(APP_USAGE_TAG_ID);
@@ -324,16 +324,16 @@
// max Duration of an app holding any wl, while screen on and app in background, slice by uid
durationMetric = config.add_duration_metric();
- durationMetric->set_name("METRIC_6");
+ durationMetric->set_id(6);
durationMetric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
durationMetric->set_aggregation_type(DurationMetric_AggregationType_MAX_SPARSE);
dimensions = durationMetric->mutable_dimensions();
dimensions->set_field(WAKE_LOCK_TAG_ID);
dimensions->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
- durationMetric->set_what("WL_HELD_PER_APP_PER_NAME");
- durationMetric->set_condition("APP_IS_BACKGROUND_AND_SCREEN_ON");
+ durationMetric->set_what(205);
+ durationMetric->set_condition(204);
link = durationMetric->add_links();
- link->set_condition("APP_IS_BACKGROUND");
+ link->set_condition(203);
link->mutable_dimensions_in_what()->set_field(WAKE_LOCK_TAG_ID);
link->mutable_dimensions_in_what()->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
link->mutable_dimensions_in_condition()->set_field(APP_USAGE_TAG_ID);
@@ -341,13 +341,13 @@
// Duration of an app holding any wl, while screen on and app in background
durationMetric = config.add_duration_metric();
- durationMetric->set_name("METRIC_7");
+ durationMetric->set_id(7);
durationMetric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
durationMetric->set_aggregation_type(DurationMetric_AggregationType_MAX_SPARSE);
- durationMetric->set_what("WL_HELD_PER_APP_PER_NAME");
- durationMetric->set_condition("APP_IS_BACKGROUND_AND_SCREEN_ON");
+ durationMetric->set_what(205);
+ durationMetric->set_condition(204);
link = durationMetric->add_links();
- link->set_condition("APP_IS_BACKGROUND");
+ link->set_condition(203);
link->mutable_dimensions_in_what()->set_field(WAKE_LOCK_TAG_ID);
link->mutable_dimensions_in_what()->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
link->mutable_dimensions_in_condition()->set_field(APP_USAGE_TAG_ID);
@@ -356,17 +356,17 @@
// Duration of screen on time.
durationMetric = config.add_duration_metric();
- durationMetric->set_name("METRIC_8");
+ durationMetric->set_id(8);
durationMetric->mutable_bucket()->set_bucket_size_millis(10 * 1000L);
durationMetric->set_aggregation_type(DurationMetric_AggregationType_SUM);
- durationMetric->set_what("SCREEN_IS_ON");
+ durationMetric->set_what(201);
// Anomaly threshold for background count.
// TODO(b/70627390): Uncomment once the bug is fixed.
/*
alert = config.add_alert();
- alert->set_name("ALERT_8");
- alert->set_metric_name("METRIC_8");
+ alert->set_id(308);
+ alert->set_metric_id(8);
alert->set_number_of_buckets(4);
alert->set_trigger_if_sum_gt(2000000000); // 2 seconds
alert->set_refractory_period_secs(120);
@@ -375,10 +375,10 @@
// Value metric to count KERNEL_WAKELOCK when screen turned on
ValueMetric* valueMetric = config.add_value_metric();
- valueMetric->set_name("METRIC_6");
- valueMetric->set_what("KERNEL_WAKELOCK");
+ valueMetric->set_id(11);
+ valueMetric->set_what(109);
valueMetric->set_value_field(KERNEL_WAKELOCK_COUNT_KEY);
- valueMetric->set_condition("SCREEN_IS_ON");
+ valueMetric->set_condition(201);
dimensions = valueMetric->mutable_dimensions();
dimensions->set_field(KERNEL_WAKELOCK_TAG_ID);
dimensions->add_child()->set_field(KERNEL_WAKELOCK_NAME_KEY);
@@ -387,13 +387,13 @@
// Add an EventMetric to log process state change events.
EventMetric* eventMetric = config.add_event_metric();
- eventMetric->set_name("METRIC_9");
- eventMetric->set_what("SCREEN_TURNED_ON");
+ eventMetric->set_id(9);
+ eventMetric->set_what(102); // "SCREEN_TURNED_ON"
// Add an GaugeMetric.
GaugeMetric* gaugeMetric = config.add_gauge_metric();
- gaugeMetric->set_name("METRIC_10");
- gaugeMetric->set_what("DEVICE_TEMPERATURE");
+ gaugeMetric->set_id(10);
+ gaugeMetric->set_what(101);
auto gaugeFieldMatcher = gaugeMetric->mutable_gauge_fields_filter()->mutable_fields();
gaugeFieldMatcher->set_field(DEVICE_TEMPERATURE_TAG_ID);
gaugeFieldMatcher->add_child()->set_field(DEVICE_TEMPERATURE_KEY);
@@ -401,12 +401,12 @@
// Event matchers.
AtomMatcher* temperatureAtomMatcher = config.add_atom_matcher();
- temperatureAtomMatcher->set_name("DEVICE_TEMPERATURE");
+ temperatureAtomMatcher->set_id(101); // "DEVICE_TEMPERATURE"
temperatureAtomMatcher->mutable_simple_atom_matcher()->set_atom_id(
DEVICE_TEMPERATURE_TAG_ID);
AtomMatcher* eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_TURNED_ON");
+ eventMatcher->set_id(102); // "SCREEN_TURNED_ON"
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(SCREEN_EVENT_TAG_ID);
FieldValueMatcher* fieldValueMatcher = simpleAtomMatcher->add_field_value_matcher();
@@ -414,7 +414,7 @@
fieldValueMatcher->set_eq_int(SCREEN_EVENT_ON_VALUE);
eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_TURNED_OFF");
+ eventMatcher->set_id(103); // "SCREEN_TURNED_OFF"
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(SCREEN_EVENT_TAG_ID);
fieldValueMatcher = simpleAtomMatcher->add_field_value_matcher();
@@ -422,12 +422,12 @@
fieldValueMatcher->set_eq_int(SCREEN_EVENT_OFF_VALUE);
eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("PROCESS_STATE_CHANGE");
+ eventMatcher->set_id(104); // "PROCESS_STATE_CHANGE"
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(UID_PROCESS_STATE_TAG_ID);
eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("APP_GOES_BACKGROUND");
+ eventMatcher->set_id(105); // "APP_GOES_BACKGROUND"
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(APP_USAGE_TAG_ID);
fieldValueMatcher = simpleAtomMatcher->add_field_value_matcher();
@@ -435,7 +435,7 @@
fieldValueMatcher->set_eq_int(APP_USAGE_BACKGROUND);
eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("APP_GOES_FOREGROUND");
+ eventMatcher->set_id(106); // "APP_GOES_FOREGROUND"
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(APP_USAGE_TAG_ID);
fieldValueMatcher = simpleAtomMatcher->add_field_value_matcher();
@@ -443,7 +443,7 @@
fieldValueMatcher->set_eq_int(APP_USAGE_FOREGROUND);
eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("APP_GET_WL");
+ eventMatcher->set_id(107); // "APP_GET_WL"
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(WAKE_LOCK_TAG_ID);
fieldValueMatcher = simpleAtomMatcher->add_field_value_matcher();
@@ -451,7 +451,7 @@
fieldValueMatcher->set_eq_int(WAKE_LOCK_ACQUIRE_VALUE);
eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("APP_RELEASE_WL");
+ eventMatcher->set_id(108); //"APP_RELEASE_WL"
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(WAKE_LOCK_TAG_ID);
fieldValueMatcher = simpleAtomMatcher->add_field_value_matcher();
@@ -460,47 +460,47 @@
// pulled events
eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("KERNEL_WAKELOCK");
+ eventMatcher->set_id(109); // "KERNEL_WAKELOCK"
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(KERNEL_WAKELOCK_TAG_ID);
// Predicates.............
Predicate* predicate = config.add_predicate();
- predicate->set_name("SCREEN_IS_ON");
+ predicate->set_id(201); // "SCREEN_IS_ON"
SimplePredicate* simplePredicate = predicate->mutable_simple_predicate();
- simplePredicate->set_start("SCREEN_TURNED_ON");
- simplePredicate->set_stop("SCREEN_TURNED_OFF");
+ simplePredicate->set_start(102); // "SCREEN_TURNED_ON"
+ simplePredicate->set_stop(103);
simplePredicate->set_count_nesting(false);
predicate = config.add_predicate();
- predicate->set_name("SCREEN_IS_OFF");
+ predicate->set_id(202); // "SCREEN_IS_OFF"
simplePredicate = predicate->mutable_simple_predicate();
- simplePredicate->set_start("SCREEN_TURNED_OFF");
- simplePredicate->set_stop("SCREEN_TURNED_ON");
+ simplePredicate->set_start(103);
+ simplePredicate->set_stop(102); // "SCREEN_TURNED_ON"
simplePredicate->set_count_nesting(false);
predicate = config.add_predicate();
- predicate->set_name("APP_IS_BACKGROUND");
+ predicate->set_id(203); // "APP_IS_BACKGROUND"
simplePredicate = predicate->mutable_simple_predicate();
- simplePredicate->set_start("APP_GOES_BACKGROUND");
- simplePredicate->set_stop("APP_GOES_FOREGROUND");
+ simplePredicate->set_start(105);
+ simplePredicate->set_stop(106);
FieldMatcher* predicate_dimension1 = simplePredicate->mutable_dimensions();
predicate_dimension1->set_field(APP_USAGE_TAG_ID);
predicate_dimension1->add_child()->set_field(APP_USAGE_UID_KEY_ID);
simplePredicate->set_count_nesting(false);
predicate = config.add_predicate();
- predicate->set_name("APP_IS_BACKGROUND_AND_SCREEN_ON");
+ predicate->set_id(204); // "APP_IS_BACKGROUND_AND_SCREEN_ON"
Predicate_Combination* combination_predicate = predicate->mutable_combination();
combination_predicate->set_operation(LogicalOperation::AND);
- combination_predicate->add_predicate("APP_IS_BACKGROUND");
- combination_predicate->add_predicate("SCREEN_IS_ON");
+ combination_predicate->add_predicate(203);
+ combination_predicate->add_predicate(201);
predicate = config.add_predicate();
- predicate->set_name("WL_HELD_PER_APP_PER_NAME");
+ predicate->set_id(205); // "WL_HELD_PER_APP_PER_NAME"
simplePredicate = predicate->mutable_simple_predicate();
- simplePredicate->set_start("APP_GET_WL");
- simplePredicate->set_stop("APP_RELEASE_WL");
+ simplePredicate->set_start(107);
+ simplePredicate->set_stop(108);
FieldMatcher* predicate_dimension = simplePredicate->mutable_dimensions();
predicate_dimension1->set_field(WAKE_LOCK_TAG_ID);
predicate_dimension->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
@@ -508,10 +508,10 @@
simplePredicate->set_count_nesting(true);
predicate = config.add_predicate();
- predicate->set_name("WL_HELD_PER_APP");
+ predicate->set_id(206); // "WL_HELD_PER_APP"
simplePredicate = predicate->mutable_simple_predicate();
- simplePredicate->set_start("APP_GET_WL");
- simplePredicate->set_stop("APP_RELEASE_WL");
+ simplePredicate->set_start(107);
+ simplePredicate->set_stop(108);
simplePredicate->set_initial_value(SimplePredicate_InitialValue_FALSE);
predicate_dimension = simplePredicate->mutable_dimensions();
predicate_dimension->set_field(WAKE_LOCK_TAG_ID);
diff --git a/cmds/statsd/src/guardrail/StatsdStats.cpp b/cmds/statsd/src/guardrail/StatsdStats.cpp
index bf277f0..33927aa 100644
--- a/cmds/statsd/src/guardrail/StatsdStats.cpp
+++ b/cmds/statsd/src/guardrail/StatsdStats.cpp
@@ -80,7 +80,7 @@
StatsdStatsReport_ConfigStats configStats;
configStats.set_uid(key.GetUid());
- configStats.set_name(key.GetName());
+ configStats.set_id(key.GetId());
configStats.set_creation_time_sec(nowTimeSec);
configStats.set_metric_count(metricsCount);
configStats.set_condition_count(conditionsCount);
@@ -196,34 +196,34 @@
mUidMapStats.set_bytes_used(bytes);
}
-void StatsdStats::noteConditionDimensionSize(const ConfigKey& key, const string& name, int size) {
+void StatsdStats::noteConditionDimensionSize(const ConfigKey& key, const int64_t& id, int size) {
lock_guard<std::mutex> lock(mLock);
// if name doesn't exist before, it will create the key with count 0.
auto& conditionSizeMap = mConditionStats[key];
- if (size > conditionSizeMap[name]) {
- conditionSizeMap[name] = size;
+ if (size > conditionSizeMap[id]) {
+ conditionSizeMap[id] = size;
}
}
-void StatsdStats::noteMetricDimensionSize(const ConfigKey& key, const string& name, int size) {
+void StatsdStats::noteMetricDimensionSize(const ConfigKey& key, const int64_t& id, int size) {
lock_guard<std::mutex> lock(mLock);
// if name doesn't exist before, it will create the key with count 0.
auto& metricsDimensionMap = mMetricsStats[key];
- if (size > metricsDimensionMap[name]) {
- metricsDimensionMap[name] = size;
+ if (size > metricsDimensionMap[id]) {
+ metricsDimensionMap[id] = size;
}
}
-void StatsdStats::noteMatcherMatched(const ConfigKey& key, const string& name) {
+void StatsdStats::noteMatcherMatched(const ConfigKey& key, const int64_t& id) {
lock_guard<std::mutex> lock(mLock);
auto& matcherStats = mMatcherStats[key];
- matcherStats[name]++;
+ matcherStats[id]++;
}
-void StatsdStats::noteAnomalyDeclared(const ConfigKey& key, const string& name) {
+void StatsdStats::noteAnomalyDeclared(const ConfigKey& key, const int64_t& id) {
lock_guard<std::mutex> lock(mLock);
auto& alertStats = mAlertStats[key];
- alertStats[name]++;
+ alertStats[id]++;
}
void StatsdStats::noteRegisteredAnomalyAlarmChanged() {
@@ -279,9 +279,10 @@
const auto& matcherStats = mMatcherStats[key];
for (const auto& stats : matcherStats) {
auto output = configStats.add_matcher_stats();
- output->set_name(stats.first);
+ output->set_id(stats.first);
output->set_matched_times(stats.second);
- VLOG("matcher %s matched %d times", stats.first.c_str(), stats.second);
+ VLOG("matcher %lld matched %d times",
+ (long long)stats.first, stats.second);
}
}
// Add condition stats
@@ -289,9 +290,10 @@
const auto& conditionStats = mConditionStats[key];
for (const auto& stats : conditionStats) {
auto output = configStats.add_condition_stats();
- output->set_name(stats.first);
+ output->set_id(stats.first);
output->set_max_tuple_counts(stats.second);
- VLOG("condition %s max output tuple size %d", stats.first.c_str(), stats.second);
+ VLOG("condition %lld max output tuple size %d",
+ (long long)stats.first, stats.second);
}
}
// Add metrics stats
@@ -299,9 +301,10 @@
const auto& conditionStats = mMetricsStats[key];
for (const auto& stats : conditionStats) {
auto output = configStats.add_metric_stats();
- output->set_name(stats.first);
+ output->set_id(stats.first);
output->set_max_tuple_counts(stats.second);
- VLOG("metrics %s max output tuple size %d", stats.first.c_str(), stats.second);
+ VLOG("metrics %lld max output tuple size %d",
+ (long long)stats.first, stats.second);
}
}
// Add anomaly detection alert stats
@@ -309,9 +312,9 @@
const auto& alertStats = mAlertStats[key];
for (const auto& stats : alertStats) {
auto output = configStats.add_alert_stats();
- output->set_name(stats.first);
+ output->set_id(stats.first);
output->set_alerted_times(stats.second);
- VLOG("alert %s declared %d times", stats.first.c_str(), stats.second);
+ VLOG("alert %lld declared %d times", (long long)stats.first, stats.second);
}
}
}
@@ -343,9 +346,9 @@
// in production.
if (DEBUG) {
VLOG("*****ICEBOX*****");
- VLOG("Config {%d-%s}: creation=%d, deletion=%d, #metric=%d, #condition=%d, "
+ VLOG("Config {%d-%lld}: creation=%d, deletion=%d, #metric=%d, #condition=%d, "
"#matcher=%d, #alert=%d, #valid=%d",
- configStats.uid(), configStats.name().c_str(), configStats.creation_time_sec(),
+ configStats.uid(), (long long)configStats.id(), configStats.creation_time_sec(),
configStats.deletion_time_sec(), configStats.metric_count(),
configStats.condition_count(), configStats.matcher_count(),
configStats.alert_count(), configStats.is_valid());
@@ -364,9 +367,9 @@
auto& configStats = pair.second;
if (DEBUG) {
VLOG("********Active Configs***********");
- VLOG("Config {%d-%s}: creation=%d, deletion=%d, #metric=%d, #condition=%d, "
+ VLOG("Config {%d-%lld}: creation=%d, deletion=%d, #metric=%d, #condition=%d, "
"#matcher=%d, #alert=%d, #valid=%d",
- configStats.uid(), configStats.name().c_str(), configStats.creation_time_sec(),
+ configStats.uid(), (long long)configStats.id(), configStats.creation_time_sec(),
configStats.deletion_time_sec(), configStats.metric_count(),
configStats.condition_count(), configStats.matcher_count(),
configStats.alert_count(), configStats.is_valid());
diff --git a/cmds/statsd/src/guardrail/StatsdStats.h b/cmds/statsd/src/guardrail/StatsdStats.h
index cb868e1f..45aa192 100644
--- a/cmds/statsd/src/guardrail/StatsdStats.h
+++ b/cmds/statsd/src/guardrail/StatsdStats.h
@@ -99,10 +99,10 @@
* count > kDimensionKeySizeSoftLimit.
*
* [key]: The config key that this condition belongs to.
- * [name]: The name of the condition.
+ * [id]: The id of the condition.
* [size]: The output tuple size.
*/
- void noteConditionDimensionSize(const ConfigKey& key, const std::string& name, int size);
+ void noteConditionDimensionSize(const ConfigKey& key, const int64_t& id, int size);
/**
* Report the size of output tuple of a metric.
@@ -111,26 +111,26 @@
* count > kDimensionKeySizeSoftLimit.
*
* [key]: The config key that this metric belongs to.
- * [name]: The name of the metric.
+ * [id]: The id of the metric.
* [size]: The output tuple size.
*/
- void noteMetricDimensionSize(const ConfigKey& key, const std::string& name, int size);
+ void noteMetricDimensionSize(const ConfigKey& key, const int64_t& id, int size);
/**
* Report a matcher has been matched.
*
* [key]: The config key that this matcher belongs to.
- * [name]: The name of the matcher.
+ * [id]: The id of the matcher.
*/
- void noteMatcherMatched(const ConfigKey& key, const std::string& name);
+ void noteMatcherMatched(const ConfigKey& key, const int64_t& id);
/**
* Report that an anomaly detection alert has been declared.
*
* [key]: The config key that this alert belongs to.
- * [name]: The name of the alert.
+ * [id]: The id of the alert.
*/
- void noteAnomalyDeclared(const ConfigKey& key, const std::string& name);
+ void noteAnomalyDeclared(const ConfigKey& key, const int64_t& id);
/**
* Report an atom event has been logged.
@@ -187,12 +187,12 @@
// Stores the number of output tuple of condition trackers when it's bigger than
// kDimensionKeySizeSoftLimit. When you see the number is kDimensionKeySizeHardLimit +1,
// it means some data has been dropped.
- std::map<const ConfigKey, std::map<const std::string, int>> mConditionStats;
+ std::map<const ConfigKey, std::map<const int64_t, int>> mConditionStats;
// Stores the number of output tuple of metric producers when it's bigger than
// kDimensionKeySizeSoftLimit. When you see the number is kDimensionKeySizeHardLimit +1,
// it means some data has been dropped.
- std::map<const ConfigKey, std::map<const std::string, int>> mMetricsStats;
+ std::map<const ConfigKey, std::map<const int64_t, int>> mMetricsStats;
// Stores the number of times a pushed atom is logged.
// The size of the vector is the largest pushed atom id in atoms.proto + 1. Atoms
@@ -206,10 +206,10 @@
// Stores the number of times an anomaly detection alert has been declared
// (per config, per alert name).
- std::map<const ConfigKey, std::map<const std::string, int>> mAlertStats;
+ std::map<const ConfigKey, std::map<const int64_t, int>> mAlertStats;
// Stores how many times a matcher have been matched.
- std::map<const ConfigKey, std::map<const std::string, int>> mMatcherStats;
+ std::map<const ConfigKey, std::map<const int64_t, int>> mMatcherStats;
void noteConfigRemovedInternalLocked(const ConfigKey& key);
diff --git a/cmds/statsd/src/matchers/CombinationLogMatchingTracker.cpp b/cmds/statsd/src/matchers/CombinationLogMatchingTracker.cpp
index bd5e3cb..15c067e 100644
--- a/cmds/statsd/src/matchers/CombinationLogMatchingTracker.cpp
+++ b/cmds/statsd/src/matchers/CombinationLogMatchingTracker.cpp
@@ -29,8 +29,8 @@
using std::unordered_map;
using std::vector;
-CombinationLogMatchingTracker::CombinationLogMatchingTracker(const string& name, const int index)
- : LogMatchingTracker(name, index) {
+CombinationLogMatchingTracker::CombinationLogMatchingTracker(const int64_t& id, const int index)
+ : LogMatchingTracker(id, index) {
}
CombinationLogMatchingTracker::~CombinationLogMatchingTracker() {
@@ -38,7 +38,7 @@
bool CombinationLogMatchingTracker::init(const vector<AtomMatcher>& allLogMatchers,
const vector<sp<LogMatchingTracker>>& allTrackers,
- const unordered_map<string, int>& matcherMap,
+ const unordered_map<int64_t, int>& matcherMap,
vector<bool>& stack) {
if (mInitialized) {
return true;
@@ -60,10 +60,10 @@
return false;
}
- for (const string& child : matcher.matcher()) {
+ for (const auto& child : matcher.matcher()) {
auto pair = matcherMap.find(child);
if (pair == matcherMap.end()) {
- ALOGW("Matcher %s not found in the config", child.c_str());
+ ALOGW("Matcher %lld not found in the config", (long long)child);
return false;
}
@@ -76,7 +76,7 @@
}
if (!allTrackers[childIndex]->init(allLogMatchers, allTrackers, matcherMap, stack)) {
- ALOGW("child matcher init failed %s", child.c_str());
+ ALOGW("child matcher init failed %lld", (long long)child);
return false;
}
diff --git a/cmds/statsd/src/matchers/CombinationLogMatchingTracker.h b/cmds/statsd/src/matchers/CombinationLogMatchingTracker.h
index 81f6e80..2a3f08d 100644
--- a/cmds/statsd/src/matchers/CombinationLogMatchingTracker.h
+++ b/cmds/statsd/src/matchers/CombinationLogMatchingTracker.h
@@ -31,11 +31,11 @@
// Represents a AtomMatcher_Combination in the StatsdConfig.
class CombinationLogMatchingTracker : public virtual LogMatchingTracker {
public:
- CombinationLogMatchingTracker(const std::string& name, const int index);
+ CombinationLogMatchingTracker(const int64_t& id, const int index);
bool init(const std::vector<AtomMatcher>& allLogMatchers,
const std::vector<sp<LogMatchingTracker>>& allTrackers,
- const std::unordered_map<std::string, int>& matcherMap,
+ const std::unordered_map<int64_t, int>& matcherMap,
std::vector<bool>& stack);
~CombinationLogMatchingTracker();
diff --git a/cmds/statsd/src/matchers/LogMatchingTracker.h b/cmds/statsd/src/matchers/LogMatchingTracker.h
index 567944f..4f30a04 100644
--- a/cmds/statsd/src/matchers/LogMatchingTracker.h
+++ b/cmds/statsd/src/matchers/LogMatchingTracker.h
@@ -33,8 +33,8 @@
class LogMatchingTracker : public virtual RefBase {
public:
- LogMatchingTracker(const std::string& name, const int index)
- : mName(name), mIndex(index), mInitialized(false){};
+ LogMatchingTracker(const int64_t& id, const int index)
+ : mId(id), mIndex(index), mInitialized(false){};
virtual ~LogMatchingTracker(){};
@@ -48,7 +48,7 @@
// circle dependency.
virtual bool init(const std::vector<AtomMatcher>& allLogMatchers,
const std::vector<sp<LogMatchingTracker>>& allTrackers,
- const std::unordered_map<std::string, int>& matcherMap,
+ const std::unordered_map<int64_t, int>& matcherMap,
std::vector<bool>& stack) = 0;
// Called when a log event comes.
@@ -69,13 +69,13 @@
return mAtomIds;
}
- const std::string& getName() const {
- return mName;
+ const int64_t& getId() const {
+ return mId;
}
protected:
// Name of this matching. We don't really need the name, but it makes log message easy to debug.
- const std::string mName;
+ const int64_t mId;
// Index of this LogMatchingTracker in MetricsManager's container.
const int mIndex;
diff --git a/cmds/statsd/src/matchers/SimpleLogMatchingTracker.cpp b/cmds/statsd/src/matchers/SimpleLogMatchingTracker.cpp
index 91ef034..31b3db5 100644
--- a/cmds/statsd/src/matchers/SimpleLogMatchingTracker.cpp
+++ b/cmds/statsd/src/matchers/SimpleLogMatchingTracker.cpp
@@ -29,10 +29,10 @@
using std::vector;
-SimpleLogMatchingTracker::SimpleLogMatchingTracker(const string& name, const int index,
+SimpleLogMatchingTracker::SimpleLogMatchingTracker(const int64_t& id, const int index,
const SimpleAtomMatcher& matcher,
const UidMap& uidMap)
- : LogMatchingTracker(name, index), mMatcher(matcher), mUidMap(uidMap) {
+ : LogMatchingTracker(id, index), mMatcher(matcher), mUidMap(uidMap) {
if (!matcher.has_atom_id()) {
mInitialized = false;
} else {
@@ -46,7 +46,7 @@
bool SimpleLogMatchingTracker::init(const vector<AtomMatcher>& allLogMatchers,
const vector<sp<LogMatchingTracker>>& allTrackers,
- const unordered_map<string, int>& matcherMap,
+ const unordered_map<int64_t, int>& matcherMap,
vector<bool>& stack) {
// no need to do anything.
return mInitialized;
@@ -56,7 +56,7 @@
const vector<sp<LogMatchingTracker>>& allTrackers,
vector<MatchingState>& matcherResults) {
if (matcherResults[mIndex] != MatchingState::kNotComputed) {
- VLOG("Matcher %s already evaluated ", mName.c_str());
+ VLOG("Matcher %lld already evaluated ", (long long)mId);
return;
}
@@ -67,7 +67,7 @@
bool matched = matchesSimple(mUidMap, mMatcher, event);
matcherResults[mIndex] = matched ? MatchingState::kMatched : MatchingState::kNotMatched;
- VLOG("Stats SimpleLogMatcher %s matched? %d", mName.c_str(), matched);
+ VLOG("Stats SimpleLogMatcher %lld matched? %d", (long long)mId, matched);
}
} // namespace statsd
diff --git a/cmds/statsd/src/matchers/SimpleLogMatchingTracker.h b/cmds/statsd/src/matchers/SimpleLogMatchingTracker.h
index 68518f8..28b339c 100644
--- a/cmds/statsd/src/matchers/SimpleLogMatchingTracker.h
+++ b/cmds/statsd/src/matchers/SimpleLogMatchingTracker.h
@@ -32,7 +32,7 @@
class SimpleLogMatchingTracker : public virtual LogMatchingTracker {
public:
- SimpleLogMatchingTracker(const std::string& name, const int index,
+ SimpleLogMatchingTracker(const int64_t& id, const int index,
const SimpleAtomMatcher& matcher,
const UidMap& uidMap);
@@ -40,7 +40,7 @@
bool init(const std::vector<AtomMatcher>& allLogMatchers,
const std::vector<sp<LogMatchingTracker>>& allTrackers,
- const std::unordered_map<std::string, int>& matcherMap,
+ const std::unordered_map<int64_t, int>& matcherMap,
std::vector<bool>& stack) override;
void onLogEvent(const LogEvent& event,
diff --git a/cmds/statsd/src/metrics/CountMetricProducer.cpp b/cmds/statsd/src/metrics/CountMetricProducer.cpp
index 5bf3cff..a24364d 100644
--- a/cmds/statsd/src/metrics/CountMetricProducer.cpp
+++ b/cmds/statsd/src/metrics/CountMetricProducer.cpp
@@ -43,7 +43,7 @@
namespace statsd {
// for StatsLogReport
-const int FIELD_ID_NAME = 1;
+const int FIELD_ID_ID = 1;
const int FIELD_ID_START_REPORT_NANOS = 2;
const int FIELD_ID_END_REPORT_NANOS = 3;
const int FIELD_ID_COUNT_METRICS = 5;
@@ -61,7 +61,7 @@
const int conditionIndex,
const sp<ConditionWizard>& wizard,
const uint64_t startTimeNs)
- : MetricProducer(metric.name(), key, startTimeNs, conditionIndex, wizard) {
+ : MetricProducer(metric.id(), key, startTimeNs, conditionIndex, wizard) {
// TODO: evaluate initial conditions. and set mConditionMet.
if (metric.has_bucket() && metric.bucket().has_bucket_size_millis()) {
mBucketSizeNs = metric.bucket().bucket_size_millis() * 1000 * 1000;
@@ -78,7 +78,7 @@
mConditionSliced = true;
}
- VLOG("metric %s created. bucket size %lld start_time: %lld", metric.name().c_str(),
+ VLOG("metric %lld created. bucket size %lld start_time: %lld", (long long)metric.id(),
(long long)mBucketSizeNs, (long long)mStartTimeNs);
}
@@ -87,12 +87,12 @@
}
void CountMetricProducer::onSlicedConditionMayChangeLocked(const uint64_t eventTime) {
- VLOG("Metric %s onSlicedConditionMayChange", mName.c_str());
+ VLOG("Metric %lld onSlicedConditionMayChange", (long long)mMetricId);
}
void CountMetricProducer::onDumpReportLocked(const uint64_t dumpTimeNs, StatsLogReport* report) {
flushIfNeededLocked(dumpTimeNs);
- report->set_metric_name(mName);
+ report->set_metric_id(mMetricId);
report->set_start_report_nanos(mStartTimeNs);
auto count_metrics = report->mutable_count_metrics();
@@ -112,11 +112,11 @@
ProtoOutputStream* protoOutput) {
flushIfNeededLocked(dumpTimeNs);
- protoOutput->write(FIELD_TYPE_STRING | FIELD_ID_NAME, mName);
+ protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_ID, (long long)mMetricId);
protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_START_REPORT_NANOS, (long long)mStartTimeNs);
long long protoToken = protoOutput->start(FIELD_TYPE_MESSAGE | FIELD_ID_COUNT_METRICS);
- VLOG("metric %s dump report now...", mName.c_str());
+ VLOG("metric %lld dump report now...",(long long)mMetricId);
for (const auto& counter : mPastBuckets) {
const HashableDimensionKey& hashableKey = counter.first;
@@ -158,7 +158,7 @@
void CountMetricProducer::onConditionChangedLocked(const bool conditionMet,
const uint64_t eventTime) {
- VLOG("Metric %s onConditionChanged", mName.c_str());
+ VLOG("Metric %lld onConditionChanged", (long long)mMetricId);
mCondition = conditionMet;
}
@@ -170,11 +170,11 @@
// 1. Report the tuple count if the tuple count > soft limit
if (mCurrentSlicedCounter->size() > StatsdStats::kDimensionKeySizeSoftLimit - 1) {
size_t newTupleCount = mCurrentSlicedCounter->size() + 1;
- StatsdStats::getInstance().noteMetricDimensionSize(mConfigKey, mName, newTupleCount);
+ StatsdStats::getInstance().noteMetricDimensionSize(mConfigKey, mMetricId, newTupleCount);
// 2. Don't add more tuples, we are above the allowed threshold. Drop the data.
if (newTupleCount > StatsdStats::kDimensionKeySizeHardLimit) {
- ALOGE("CountMetric %s dropping data for dimension key %s", mName.c_str(),
- newKey.c_str());
+ ALOGE("CountMetric %lld dropping data for dimension key %s",
+ (long long)mMetricId, newKey.c_str());
return true;
}
}
@@ -215,7 +215,7 @@
mCurrentSlicedCounter->find(eventKey)->second);
}
- VLOG("metric %s %s->%lld", mName.c_str(), eventKey.c_str(),
+ VLOG("metric %lld %s->%lld", (long long)mMetricId, eventKey.c_str(),
(long long)(*mCurrentSlicedCounter)[eventKey]);
}
@@ -234,8 +234,8 @@
info.mCount = counter.second;
auto& bucketList = mPastBuckets[counter.first];
bucketList.push_back(info);
- VLOG("metric %s, dump key value: %s -> %lld", mName.c_str(), counter.first.c_str(),
- (long long)counter.second);
+ VLOG("metric %lld, dump key value: %s -> %lld",
+ (long long)mMetricId, counter.first.c_str(), (long long)counter.second);
}
for (auto& tracker : mAnomalyTrackers) {
@@ -247,7 +247,7 @@
uint64_t numBucketsForward = (eventTimeNs - mCurrentBucketStartTimeNs) / mBucketSizeNs;
mCurrentBucketStartTimeNs = mCurrentBucketStartTimeNs + numBucketsForward * mBucketSizeNs;
mCurrentBucketNum += numBucketsForward;
- VLOG("metric %s: new bucket start time: %lld", mName.c_str(),
+ VLOG("metric %lld: new bucket start time: %lld", (long long)mMetricId,
(long long)mCurrentBucketStartTimeNs);
}
diff --git a/cmds/statsd/src/metrics/DurationMetricProducer.cpp b/cmds/statsd/src/metrics/DurationMetricProducer.cpp
index 30b105c..99545ae 100644
--- a/cmds/statsd/src/metrics/DurationMetricProducer.cpp
+++ b/cmds/statsd/src/metrics/DurationMetricProducer.cpp
@@ -42,7 +42,7 @@
namespace statsd {
// for StatsLogReport
-const int FIELD_ID_NAME = 1;
+const int FIELD_ID_ID = 1;
const int FIELD_ID_START_REPORT_NANOS = 2;
const int FIELD_ID_END_REPORT_NANOS = 3;
const int FIELD_ID_DURATION_METRICS = 6;
@@ -63,7 +63,7 @@
const sp<ConditionWizard>& wizard,
const FieldMatcher& internalDimensions,
const uint64_t startTimeNs)
- : MetricProducer(metric.name(), key, startTimeNs, conditionIndex, wizard),
+ : MetricProducer(metric.id(), key, startTimeNs, conditionIndex, wizard),
mAggregationType(metric.aggregation_type()),
mStartIndex(startIndex),
mStopIndex(stopIndex),
@@ -88,7 +88,7 @@
mConditionSliced = true;
}
- VLOG("metric %s created. bucket size %lld start_time: %lld", metric.name().c_str(),
+ VLOG("metric %lld created. bucket size %lld start_time: %lld", (long long)metric.id(),
(long long)mBucketSizeNs, (long long)mStartTimeNs);
}
@@ -116,17 +116,17 @@
switch (mAggregationType) {
case DurationMetric_AggregationType_SUM:
return make_unique<OringDurationTracker>(
- mConfigKey, mName, eventKey, mWizard, mConditionTrackerIndex, mNested,
+ mConfigKey, mMetricId, eventKey, mWizard, mConditionTrackerIndex, mNested,
mCurrentBucketStartTimeNs, mBucketSizeNs, mAnomalyTrackers);
case DurationMetric_AggregationType_MAX_SPARSE:
return make_unique<MaxDurationTracker>(
- mConfigKey, mName, eventKey, mWizard, mConditionTrackerIndex, mNested,
+ mConfigKey, mMetricId, eventKey, mWizard, mConditionTrackerIndex, mNested,
mCurrentBucketStartTimeNs, mBucketSizeNs, mAnomalyTrackers);
}
}
void DurationMetricProducer::onSlicedConditionMayChangeLocked(const uint64_t eventTime) {
- VLOG("Metric %s onSlicedConditionMayChange", mName.c_str());
+ VLOG("Metric %lld onSlicedConditionMayChange", (long long)mMetricId);
flushIfNeededLocked(eventTime);
// Now for each of the on-going event, check if the condition has changed for them.
for (auto& pair : mCurrentSlicedDuration) {
@@ -136,7 +136,7 @@
void DurationMetricProducer::onConditionChangedLocked(const bool conditionMet,
const uint64_t eventTime) {
- VLOG("Metric %s onConditionChanged", mName.c_str());
+ VLOG("Metric %lld onConditionChanged", (long long)mMetricId);
mCondition = conditionMet;
flushIfNeededLocked(eventTime);
// TODO: need to populate the condition change time from the event which triggers the condition
@@ -148,7 +148,7 @@
void DurationMetricProducer::onDumpReportLocked(const uint64_t dumpTimeNs, StatsLogReport* report) {
flushIfNeededLocked(dumpTimeNs);
- report->set_metric_name(mName);
+ report->set_metric_id(mMetricId);
report->set_start_report_nanos(mStartTimeNs);
auto duration_metrics = report->mutable_duration_metrics();
@@ -168,11 +168,11 @@
ProtoOutputStream* protoOutput) {
flushIfNeededLocked(dumpTimeNs);
- protoOutput->write(FIELD_TYPE_STRING | FIELD_ID_NAME, mName);
+ protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_ID, (long long)mMetricId);
protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_START_REPORT_NANOS, (long long)mStartTimeNs);
long long protoToken = protoOutput->start(FIELD_TYPE_MESSAGE | FIELD_ID_DURATION_METRICS);
- VLOG("metric %s dump report now...", mName.c_str());
+ VLOG("metric %lld dump report now...", (long long)mMetricId);
for (const auto& pair : mPastBuckets) {
const HashableDimensionKey& hashableKey = pair.first;
@@ -237,11 +237,11 @@
// 1. Report the tuple count if the tuple count > soft limit
if (mCurrentSlicedDuration.size() > StatsdStats::kDimensionKeySizeSoftLimit - 1) {
size_t newTupleCount = mCurrentSlicedDuration.size() + 1;
- StatsdStats::getInstance().noteMetricDimensionSize(mConfigKey, mName, newTupleCount);
+ StatsdStats::getInstance().noteMetricDimensionSize(mConfigKey, mMetricId, newTupleCount);
// 2. Don't add more tuples, we are above the allowed threshold. Drop the data.
if (newTupleCount > StatsdStats::kDimensionKeySizeHardLimit) {
- ALOGE("DurationMetric %s dropping data for dimension key %s", mName.c_str(),
- newKey.c_str());
+ ALOGE("DurationMetric %lld dropping data for dimension key %s",
+ (long long)mMetricId, newKey.c_str());
return true;
}
}
diff --git a/cmds/statsd/src/metrics/EventMetricProducer.cpp b/cmds/statsd/src/metrics/EventMetricProducer.cpp
index c8138d3..821d8ea4 100644
--- a/cmds/statsd/src/metrics/EventMetricProducer.cpp
+++ b/cmds/statsd/src/metrics/EventMetricProducer.cpp
@@ -41,7 +41,7 @@
namespace statsd {
// for StatsLogReport
-const int FIELD_ID_NAME = 1;
+const int FIELD_ID_ID = 1;
const int FIELD_ID_START_REPORT_NANOS = 2;
const int FIELD_ID_END_REPORT_NANOS = 3;
const int FIELD_ID_EVENT_METRICS = 4;
@@ -55,7 +55,7 @@
const int conditionIndex,
const sp<ConditionWizard>& wizard,
const uint64_t startTimeNs)
- : MetricProducer(metric.name(), key, startTimeNs, conditionIndex, wizard) {
+ : MetricProducer(metric.id(), key, startTimeNs, conditionIndex, wizard) {
if (metric.links().size() > 0) {
mConditionLinks.insert(mConditionLinks.begin(), metric.links().begin(),
metric.links().end());
@@ -64,7 +64,7 @@
startNewProtoOutputStreamLocked();
- VLOG("metric %s created. bucket size %lld start_time: %lld", metric.name().c_str(),
+ VLOG("metric %lld created. bucket size %lld start_time: %lld", (long long)metric.id(),
(long long)mBucketSizeNs, (long long)mStartTimeNs);
}
@@ -102,12 +102,13 @@
void EventMetricProducer::onDumpReportLocked(const uint64_t dumpTimeNs,
ProtoOutputStream* protoOutput) {
- protoOutput->write(FIELD_TYPE_STRING | FIELD_ID_NAME, mName);
+ protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_ID, (long long)mMetricId);
protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_START_REPORT_NANOS, (long long)mStartTimeNs);
protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_END_REPORT_NANOS, (long long)dumpTimeNs);
size_t bufferSize = mProto->size();
- VLOG("metric %s dump report now... proto size: %zu ", mName.c_str(), bufferSize);
+ VLOG("metric %lld dump report now... proto size: %zu ",
+ (long long)mMetricId, bufferSize);
std::unique_ptr<std::vector<uint8_t>> buffer = serializeProtoLocked(*mProto);
protoOutput->write(FIELD_TYPE_MESSAGE | FIELD_ID_EVENT_METRICS,
@@ -119,7 +120,7 @@
void EventMetricProducer::onConditionChangedLocked(const bool conditionMet,
const uint64_t eventTime) {
- VLOG("Metric %s onConditionChanged", mName.c_str());
+ VLOG("Metric %lld onConditionChanged", (long long)mMetricId);
mCondition = conditionMet;
}
diff --git a/cmds/statsd/src/metrics/GaugeMetricProducer.cpp b/cmds/statsd/src/metrics/GaugeMetricProducer.cpp
index 51fd9fc..eaf1de2 100644
--- a/cmds/statsd/src/metrics/GaugeMetricProducer.cpp
+++ b/cmds/statsd/src/metrics/GaugeMetricProducer.cpp
@@ -44,7 +44,7 @@
namespace statsd {
// for StatsLogReport
-const int FIELD_ID_NAME = 1;
+const int FIELD_ID_ID = 1;
const int FIELD_ID_START_REPORT_NANOS = 2;
const int FIELD_ID_END_REPORT_NANOS = 3;
const int FIELD_ID_GAUGE_METRICS = 8;
@@ -63,7 +63,7 @@
const sp<ConditionWizard>& wizard, const int atomTagId,
const int pullTagId, const uint64_t startTimeNs,
shared_ptr<StatsPullerManager> statsPullerManager)
- : MetricProducer(metric.name(), key, startTimeNs, conditionIndex, wizard),
+ : MetricProducer(metric.id(), key, startTimeNs, conditionIndex, wizard),
mStatsPullerManager(statsPullerManager),
mPullTagId(pullTagId),
mAtomTagId(atomTagId) {
@@ -92,7 +92,7 @@
metric.bucket().bucket_size_millis());
}
- VLOG("metric %s created. bucket size %lld start_time: %lld", metric.name().c_str(),
+ VLOG("metric %lld created. bucket size %lld start_time: %lld", (long long)metric.id(),
(long long)mBucketSizeNs, (long long)mStartTimeNs);
}
@@ -118,11 +118,11 @@
void GaugeMetricProducer::onDumpReportLocked(const uint64_t dumpTimeNs,
ProtoOutputStream* protoOutput) {
- VLOG("gauge metric %s dump report now...", mName.c_str());
+ VLOG("gauge metric %lld report now...", (long long)mMetricId);
flushIfNeededLocked(dumpTimeNs);
- protoOutput->write(FIELD_TYPE_STRING | FIELD_ID_NAME, mName);
+ protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_ID, (long long)mMetricId);
protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_START_REPORT_NANOS, (long long)mStartTimeNs);
long long protoToken = protoOutput->start(FIELD_TYPE_MESSAGE | FIELD_ID_GAUGE_METRICS);
@@ -166,7 +166,7 @@
void GaugeMetricProducer::onConditionChangedLocked(const bool conditionMet,
const uint64_t eventTime) {
- VLOG("Metric %s onConditionChanged", mName.c_str());
+ VLOG("Metric %lld onConditionChanged", (long long)mMetricId);
flushIfNeededLocked(eventTime);
mCondition = conditionMet;
@@ -194,7 +194,7 @@
}
void GaugeMetricProducer::onSlicedConditionMayChangeLocked(const uint64_t eventTime) {
- VLOG("Metric %s onSlicedConditionMayChange", mName.c_str());
+ VLOG("Metric %lld onSlicedConditionMayChange", (long long)mMetricId);
}
std::shared_ptr<FieldValueMap> GaugeMetricProducer::getGaugeFields(const LogEvent& event) {
@@ -223,11 +223,11 @@
// 1. Report the tuple count if the tuple count > soft limit
if (mCurrentSlicedBucket->size() > StatsdStats::kDimensionKeySizeSoftLimit - 1) {
size_t newTupleCount = mCurrentSlicedBucket->size() + 1;
- StatsdStats::getInstance().noteMetricDimensionSize(mConfigKey, mName, newTupleCount);
+ StatsdStats::getInstance().noteMetricDimensionSize(mConfigKey, mMetricId, newTupleCount);
// 2. Don't add more tuples, we are above the allowed threshold. Drop the data.
if (newTupleCount > StatsdStats::kDimensionKeySizeHardLimit) {
- ALOGE("GaugeMetric %s dropping data for dimension key %s", mName.c_str(),
- newKey.c_str());
+ ALOGE("GaugeMetric %lld dropping data for dimension key %s",
+ (long long)mMetricId, newKey.c_str());
return true;
}
}
@@ -314,7 +314,8 @@
info.mGaugeFields = slice.second;
auto& bucketList = mPastBuckets[slice.first];
bucketList.push_back(info);
- VLOG("gauge metric %s, dump key value: %s", mName.c_str(), slice.first.c_str());
+ VLOG("gauge metric %lld, dump key value: %s",
+ (long long)mMetricId, slice.first.c_str());
}
// Reset counters
@@ -331,7 +332,7 @@
int64_t numBucketsForward = (eventTimeNs - mCurrentBucketStartTimeNs) / mBucketSizeNs;
mCurrentBucketStartTimeNs = mCurrentBucketStartTimeNs + numBucketsForward * mBucketSizeNs;
mCurrentBucketNum += numBucketsForward;
- VLOG("metric %s: new bucket start time: %lld", mName.c_str(),
+ VLOG("metric %lld: new bucket start time: %lld", (long long)mMetricId,
(long long)mCurrentBucketStartTimeNs);
}
diff --git a/cmds/statsd/src/metrics/MetricProducer.cpp b/cmds/statsd/src/metrics/MetricProducer.cpp
index 4ed8289..d620a7e 100644
--- a/cmds/statsd/src/metrics/MetricProducer.cpp
+++ b/cmds/statsd/src/metrics/MetricProducer.cpp
@@ -29,13 +29,13 @@
}
bool condition;
- map<string, std::vector<HashableDimensionKey>> conditionKeys;
+ ConditionKey conditionKey;
if (mConditionSliced) {
for (const auto& link : mConditionLinks) {
- conditionKeys.insert(std::make_pair(link.condition(),
- getDimensionKeysForCondition(event, link)));
+ conditionKey.insert(std::make_pair(link.condition(),
+ getDimensionKeysForCondition(event, link)));
}
- if (mWizard->query(mConditionTrackerIndex, conditionKeys) != ConditionState::kTrue) {
+ if (mWizard->query(mConditionTrackerIndex, conditionKey) != ConditionState::kTrue) {
condition = false;
} else {
condition = true;
@@ -48,11 +48,11 @@
vector<DimensionsValue> dimensionValues = getDimensionKeys(event, mDimensions);
for (const DimensionsValue& dimensionValue : dimensionValues) {
onMatchedLogEventInternalLocked(
- matcherIndex, HashableDimensionKey(dimensionValue), conditionKeys, condition, event);
+ matcherIndex, HashableDimensionKey(dimensionValue), conditionKey, condition, event);
}
} else {
onMatchedLogEventInternalLocked(
- matcherIndex, DEFAULT_DIMENSION_KEY, conditionKeys, condition, event);
+ matcherIndex, DEFAULT_DIMENSION_KEY, conditionKey, condition, event);
}
}
diff --git a/cmds/statsd/src/metrics/MetricProducer.h b/cmds/statsd/src/metrics/MetricProducer.h
index fe1a53b..3779c44 100644
--- a/cmds/statsd/src/metrics/MetricProducer.h
+++ b/cmds/statsd/src/metrics/MetricProducer.h
@@ -39,9 +39,9 @@
// be a no-op.
class MetricProducer : public virtual PackageInfoListener {
public:
- MetricProducer(const std::string& name, const ConfigKey& key, const int64_t startTimeNs,
+ MetricProducer(const int64_t& metricId, const ConfigKey& key, const int64_t startTimeNs,
const int conditionIndex, const sp<ConditionWizard>& wizard)
- : mName(name),
+ : mMetricId(metricId),
mConfigKey(key),
mStartTimeNs(startTimeNs),
mCurrentBucketStartTimeNs(startTimeNs),
@@ -117,8 +117,8 @@
return mBucketSizeNs;
}
- inline const string& getName() {
- return mName;
+ inline const int64_t& getMetricId() {
+ return mMetricId;
}
protected:
@@ -129,7 +129,7 @@
virtual void onDumpReportLocked(const uint64_t dumpTimeNs, StatsLogReport* report) = 0;
virtual size_t byteSizeLocked() const = 0;
- const std::string mName;
+ const int64_t mMetricId;
const ConfigKey mConfigKey;
diff --git a/cmds/statsd/src/metrics/MetricsManager.cpp b/cmds/statsd/src/metrics/MetricsManager.cpp
index 9749e0f..7f0239f 100644
--- a/cmds/statsd/src/metrics/MetricsManager.cpp
+++ b/cmds/statsd/src/metrics/MetricsManager.cpp
@@ -51,7 +51,7 @@
mConfigValid =
initStatsdConfig(key, config, *uidMap, timeBaseSec, mTagIds, mAllAtomMatchers, mAllConditionTrackers,
mAllMetricProducers, mAllAnomalyTrackers, mConditionToMetricMap,
- mTrackerToMetricMap, mTrackerToConditionMap);
+ mTrackerToMetricMap, mTrackerToConditionMap, mNoReportMetricIds);
if (!config.has_log_source()) {
// TODO(b/70794411): uncomment the following line and remove the hard coded log source
@@ -143,8 +143,10 @@
}
void MetricsManager::onDumpReport(const uint64_t& dumpTimeStampNs, ConfigMetricsReport* report) {
- for (auto& producer : mAllMetricProducers) {
- producer->onDumpReport(dumpTimeStampNs, report->add_metrics());
+ for (const auto& producer : mAllMetricProducers) {
+ if (mNoReportMetricIds.find(producer->getMetricId()) == mNoReportMetricIds.end()) {
+ producer->onDumpReport(dumpTimeStampNs, report->add_metrics());
+ }
}
}
@@ -152,11 +154,13 @@
VLOG("=========================Metric Reports Start==========================");
uint64_t dumpTimeStampNs = time(nullptr) * NS_PER_SEC;
// one StatsLogReport per MetricProduer
- for (auto& metric : mAllMetricProducers) {
- long long token =
- protoOutput->start(FIELD_TYPE_MESSAGE | FIELD_COUNT_REPEATED | FIELD_ID_METRICS);
- metric->onDumpReport(dumpTimeStampNs, protoOutput);
- protoOutput->end(token);
+ for (const auto& producer : mAllMetricProducers) {
+ if (mNoReportMetricIds.find(producer->getMetricId()) == mNoReportMetricIds.end()) {
+ long long token =
+ protoOutput->start(FIELD_TYPE_MESSAGE | FIELD_COUNT_REPEATED | FIELD_ID_METRICS);
+ producer->onDumpReport(dumpTimeStampNs, protoOutput);
+ protoOutput->end(token);
+ }
}
VLOG("=========================Metric Reports End==========================");
}
@@ -173,6 +177,22 @@
VLOG("log source %d not on the whitelist", event.GetUid());
return;
}
+ } else { // Check that app hook fields are valid.
+ // TODO: Find a way to make these checks easier to maintain if the app hooks get changed.
+
+ // Label is 2nd from last field and must be from [0, 15].
+ status_t err = NO_ERROR;
+ long label = event.GetLong(event.size()-1, &err);
+ if (err != NO_ERROR || label < 0 || label > 15) {
+ VLOG("App hook does not have valid label %ld", label);
+ return;
+ }
+ // The state must be from 0,3. This part of code must be manually updated.
+ long apphookState = event.GetLong(event.size(), &err);
+ if (err != NO_ERROR || apphookState < 0 || apphookState > 3) {
+ VLOG("App hook does not have valid state %ld", apphookState);
+ return;
+ }
}
int tagId = event.GetTagId();
@@ -240,7 +260,7 @@
for (size_t i = 0; i < mAllAtomMatchers.size(); i++) {
if (matcherCache[i] == MatchingState::kMatched) {
StatsdStats::getInstance().noteMatcherMatched(mConfigKey,
- mAllAtomMatchers[i]->getName());
+ mAllAtomMatchers[i]->getId());
auto pair = mTrackerToMetricMap.find(i);
if (pair != mTrackerToMetricMap.end()) {
auto& metricList = pair->second;
diff --git a/cmds/statsd/src/metrics/MetricsManager.h b/cmds/statsd/src/metrics/MetricsManager.h
index 51c4c90..8175cd2 100644
--- a/cmds/statsd/src/metrics/MetricsManager.h
+++ b/cmds/statsd/src/metrics/MetricsManager.h
@@ -131,6 +131,9 @@
void initLogSourceWhiteList();
+ // The metrics that don't need to be uploaded or even reported.
+ std::set<int64_t> mNoReportMetricIds;
+
FRIEND_TEST(WakelockDurationE2eTest, TestAggregatedPredicateDimensions);
FRIEND_TEST(MetricConditionLinkE2eTest, TestMultiplePredicatesAndLinks);
};
diff --git a/cmds/statsd/src/metrics/ValueMetricProducer.cpp b/cmds/statsd/src/metrics/ValueMetricProducer.cpp
index b58dc68..ea90170 100644
--- a/cmds/statsd/src/metrics/ValueMetricProducer.cpp
+++ b/cmds/statsd/src/metrics/ValueMetricProducer.cpp
@@ -46,7 +46,7 @@
namespace statsd {
// for StatsLogReport
-const int FIELD_ID_NAME = 1;
+const int FIELD_ID_ID = 1;
const int FIELD_ID_START_REPORT_NANOS = 2;
const int FIELD_ID_END_REPORT_NANOS = 3;
const int FIELD_ID_VALUE_METRICS = 7;
@@ -68,7 +68,7 @@
const sp<ConditionWizard>& wizard, const int pullTagId,
const uint64_t startTimeNs,
shared_ptr<StatsPullerManager> statsPullerManager)
- : MetricProducer(metric.name(), key, startTimeNs, conditionIndex, wizard),
+ : MetricProducer(metric.id(), key, startTimeNs, conditionIndex, wizard),
mValueField(metric.value_field()),
mStatsPullerManager(statsPullerManager),
mPullTagId(pullTagId) {
@@ -92,8 +92,8 @@
mStatsPullerManager->RegisterReceiver(mPullTagId, this,
metric.bucket().bucket_size_millis());
}
- VLOG("value metric %s created. bucket size %lld start_time: %lld", metric.name().c_str(),
- (long long)mBucketSizeNs, (long long)mStartTimeNs);
+ VLOG("value metric %lld created. bucket size %lld start_time: %lld",
+ (long long)metric.id(), (long long)mBucketSizeNs, (long long)mStartTimeNs);
}
// for testing
@@ -113,12 +113,12 @@
}
void ValueMetricProducer::onSlicedConditionMayChangeLocked(const uint64_t eventTime) {
- VLOG("Metric %s onSlicedConditionMayChange", mName.c_str());
+ VLOG("Metric %lld onSlicedConditionMayChange", (long long)mMetricId);
}
void ValueMetricProducer::onDumpReportLocked(const uint64_t dumpTimeNs, StatsLogReport* report) {
flushIfNeededLocked(dumpTimeNs);
- report->set_metric_name(mName);
+ report->set_metric_id(mMetricId);
report->set_start_report_nanos(mStartTimeNs);
auto value_metrics = report->mutable_value_metrics();
for (const auto& pair : mPastBuckets) {
@@ -135,9 +135,9 @@
void ValueMetricProducer::onDumpReportLocked(const uint64_t dumpTimeNs,
ProtoOutputStream* protoOutput) {
- VLOG("metric %s dump report now...", mName.c_str());
+ VLOG("metric %lld dump report now...", (long long)mMetricId);
flushIfNeededLocked(dumpTimeNs);
- protoOutput->write(FIELD_TYPE_STRING | FIELD_ID_NAME, mName);
+ protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_ID, (long long)mMetricId);
protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_START_REPORT_NANOS, (long long)mStartTimeNs);
long long protoToken = protoOutput->start(FIELD_TYPE_MESSAGE | FIELD_ID_VALUE_METRICS);
@@ -171,7 +171,7 @@
protoOutput->end(protoToken);
protoOutput->write(FIELD_TYPE_INT64 | FIELD_ID_END_REPORT_NANOS, (long long)dumpTimeNs);
- VLOG("metric %s dump report now...", mName.c_str());
+ VLOG("metric %lld dump report now...", (long long)mMetricId);
mPastBuckets.clear();
mStartTimeNs = mCurrentBucketStartTimeNs;
// TODO: Clear mDimensionKeyMap once the report is dumped.
@@ -242,11 +242,11 @@
}
if (mCurrentSlicedBucket.size() > StatsdStats::kDimensionKeySizeSoftLimit - 1) {
size_t newTupleCount = mCurrentSlicedBucket.size() + 1;
- StatsdStats::getInstance().noteMetricDimensionSize(mConfigKey, mName, newTupleCount);
+ StatsdStats::getInstance().noteMetricDimensionSize(mConfigKey, mMetricId, newTupleCount);
// 2. Don't add more tuples, we are above the allowed threshold. Drop the data.
if (newTupleCount > StatsdStats::kDimensionKeySizeHardLimit) {
- ALOGE("ValueMetric %s dropping data for dimension key %s", mName.c_str(),
- newKey.c_str());
+ ALOGE("ValueMetric %lld dropping data for dimension key %s",
+ (long long)mMetricId, newKey.c_str());
return true;
}
}
@@ -346,7 +346,7 @@
if (numBucketsForward > 1) {
VLOG("Skipping forward %lld buckets", (long long)numBucketsForward);
}
- VLOG("metric %s: new bucket start time: %lld", mName.c_str(),
+ VLOG("metric %lld: new bucket start time: %lld", (long long)mMetricId,
(long long)mCurrentBucketStartTimeNs);
}
diff --git a/cmds/statsd/src/metrics/duration_helper/DurationTracker.h b/cmds/statsd/src/metrics/duration_helper/DurationTracker.h
index 9192d12f..842581e 100644
--- a/cmds/statsd/src/metrics/duration_helper/DurationTracker.h
+++ b/cmds/statsd/src/metrics/duration_helper/DurationTracker.h
@@ -60,12 +60,12 @@
class DurationTracker {
public:
- DurationTracker(const ConfigKey& key, const string& name, const HashableDimensionKey& eventKey,
+ DurationTracker(const ConfigKey& key, const int64_t& id, const HashableDimensionKey& eventKey,
sp<ConditionWizard> wizard, int conditionIndex, bool nesting,
uint64_t currentBucketStartNs, uint64_t bucketSizeNs,
const std::vector<sp<DurationAnomalyTracker>>& anomalyTrackers)
: mConfigKey(key),
- mName(name),
+ mTrackerId(id),
mEventKey(eventKey),
mWizard(wizard),
mConditionTrackerIndex(conditionIndex),
@@ -145,7 +145,7 @@
// A reference to the DurationMetricProducer's config key.
const ConfigKey& mConfigKey;
- const std::string mName;
+ const int64_t mTrackerId;
HashableDimensionKey mEventKey;
diff --git a/cmds/statsd/src/metrics/duration_helper/MaxDurationTracker.cpp b/cmds/statsd/src/metrics/duration_helper/MaxDurationTracker.cpp
index d8a8e23..94f98ad 100644
--- a/cmds/statsd/src/metrics/duration_helper/MaxDurationTracker.cpp
+++ b/cmds/statsd/src/metrics/duration_helper/MaxDurationTracker.cpp
@@ -24,12 +24,12 @@
namespace os {
namespace statsd {
-MaxDurationTracker::MaxDurationTracker(const ConfigKey& key, const string& name,
+MaxDurationTracker::MaxDurationTracker(const ConfigKey& key, const int64_t& id,
const HashableDimensionKey& eventKey,
sp<ConditionWizard> wizard, int conditionIndex, bool nesting,
uint64_t currentBucketStartNs, uint64_t bucketSizeNs,
const vector<sp<DurationAnomalyTracker>>& anomalyTrackers)
- : DurationTracker(key, name, eventKey, wizard, conditionIndex, nesting, currentBucketStartNs,
+ : DurationTracker(key, id, eventKey, wizard, conditionIndex, nesting, currentBucketStartNs,
bucketSizeNs, anomalyTrackers) {
}
@@ -42,12 +42,13 @@
// 1. Report the tuple count if the tuple count > soft limit
if (mInfos.size() > StatsdStats::kDimensionKeySizeSoftLimit - 1) {
size_t newTupleCount = mInfos.size() + 1;
- StatsdStats::getInstance().noteMetricDimensionSize(mConfigKey, mName + mEventKey.toString(),
- newTupleCount);
+ StatsdStats::getInstance().noteMetricDimensionSize(
+ mConfigKey, hashDimensionsValue(mTrackerId, mEventKey.getDimensionsValue()),
+ newTupleCount);
// 2. Don't add more tuples, we are above the allowed threshold. Drop the data.
if (newTupleCount > StatsdStats::kDimensionKeySizeHardLimit) {
- ALOGE("MaxDurTracker %s dropping data for dimension key %s", mName.c_str(),
- newKey.c_str());
+ ALOGE("MaxDurTracker %lld dropping data for dimension key %s",
+ (long long)mTrackerId, newKey.c_str());
return true;
}
}
diff --git a/cmds/statsd/src/metrics/duration_helper/MaxDurationTracker.h b/cmds/statsd/src/metrics/duration_helper/MaxDurationTracker.h
index 76f486e..68c48cb1 100644
--- a/cmds/statsd/src/metrics/duration_helper/MaxDurationTracker.h
+++ b/cmds/statsd/src/metrics/duration_helper/MaxDurationTracker.h
@@ -28,7 +28,7 @@
// they stop or bucket expires.
class MaxDurationTracker : public DurationTracker {
public:
- MaxDurationTracker(const ConfigKey& key, const string& name,
+ MaxDurationTracker(const ConfigKey& key, const int64_t& id,
const HashableDimensionKey& eventKey, sp<ConditionWizard> wizard,
int conditionIndex, bool nesting, uint64_t currentBucketStartNs,
uint64_t bucketSizeNs,
diff --git a/cmds/statsd/src/metrics/duration_helper/OringDurationTracker.cpp b/cmds/statsd/src/metrics/duration_helper/OringDurationTracker.cpp
index c347d5c..c77d0b7 100644
--- a/cmds/statsd/src/metrics/duration_helper/OringDurationTracker.cpp
+++ b/cmds/statsd/src/metrics/duration_helper/OringDurationTracker.cpp
@@ -25,11 +25,11 @@
using std::pair;
OringDurationTracker::OringDurationTracker(
- const ConfigKey& key, const string& name, const HashableDimensionKey& eventKey,
+ const ConfigKey& key, const int64_t& id, const HashableDimensionKey& eventKey,
sp<ConditionWizard> wizard, int conditionIndex, bool nesting, uint64_t currentBucketStartNs,
uint64_t bucketSizeNs, const vector<sp<DurationAnomalyTracker>>& anomalyTrackers)
- : DurationTracker(key, name, eventKey, wizard, conditionIndex, nesting, currentBucketStartNs,
+ : DurationTracker(key, id, eventKey, wizard, conditionIndex, nesting, currentBucketStartNs,
bucketSizeNs, anomalyTrackers),
mStarted(),
mPaused() {
@@ -44,12 +44,13 @@
}
if (mConditionKeyMap.size() > StatsdStats::kDimensionKeySizeSoftLimit - 1) {
size_t newTupleCount = mConditionKeyMap.size() + 1;
- StatsdStats::getInstance().noteMetricDimensionSize(mConfigKey, mName + mEventKey.toString(),
- newTupleCount);
+ StatsdStats::getInstance().noteMetricDimensionSize(
+ mConfigKey, hashDimensionsValue(mTrackerId, mEventKey.getDimensionsValue()),
+ newTupleCount);
// 2. Don't add more tuples, we are above the allowed threshold. Drop the data.
if (newTupleCount > StatsdStats::kDimensionKeySizeHardLimit) {
- ALOGE("OringDurTracker %s dropping data for dimension key %s", mName.c_str(),
- newKey.c_str());
+ ALOGE("OringDurTracker %lld dropping data for dimension key %s",
+ (long long)mTrackerId, newKey.c_str());
return true;
}
}
diff --git a/cmds/statsd/src/metrics/duration_helper/OringDurationTracker.h b/cmds/statsd/src/metrics/duration_helper/OringDurationTracker.h
index dcf04db..7fe649c 100644
--- a/cmds/statsd/src/metrics/duration_helper/OringDurationTracker.h
+++ b/cmds/statsd/src/metrics/duration_helper/OringDurationTracker.h
@@ -27,7 +27,7 @@
// Tracks the "Or'd" duration -- if 2 durations are overlapping, they won't be double counted.
class OringDurationTracker : public DurationTracker {
public:
- OringDurationTracker(const ConfigKey& key, const string& name,
+ OringDurationTracker(const ConfigKey& key, const int64_t& id,
const HashableDimensionKey& eventKey, sp<ConditionWizard> wizard,
int conditionIndex, bool nesting, uint64_t currentBucketStartNs,
uint64_t bucketSizeNs,
diff --git a/cmds/statsd/src/metrics/metrics_manager_util.cpp b/cmds/statsd/src/metrics/metrics_manager_util.cpp
index 97dbf7a..a4ae4d6 100644
--- a/cmds/statsd/src/metrics/metrics_manager_util.cpp
+++ b/cmds/statsd/src/metrics/metrics_manager_util.cpp
@@ -38,21 +38,21 @@
namespace os {
namespace statsd {
-bool handleMetricWithLogTrackers(const string what, const int metricIndex,
+bool handleMetricWithLogTrackers(const int64_t what, const int metricIndex,
const bool usedForDimension,
const vector<sp<LogMatchingTracker>>& allAtomMatchers,
- const unordered_map<string, int>& logTrackerMap,
+ const unordered_map<int64_t, int>& logTrackerMap,
unordered_map<int, std::vector<int>>& trackerToMetricMap,
int& logTrackerIndex) {
auto logTrackerIt = logTrackerMap.find(what);
if (logTrackerIt == logTrackerMap.end()) {
- ALOGW("cannot find the AtomMatcher \"%s\" in config", what.c_str());
+ ALOGW("cannot find the AtomMatcher \"%lld\" in config", (long long)what);
return false;
}
if (usedForDimension && allAtomMatchers[logTrackerIt->second]->getAtomIds().size() > 1) {
- ALOGE("AtomMatcher \"%s\" has more than one tag ids. When a metric has dimension, "
+ ALOGE("AtomMatcher \"%lld\" has more than one tag ids. When a metric has dimension, "
"the \"what\" can only about one atom type.",
- what.c_str());
+ (long long)what);
return false;
}
logTrackerIndex = logTrackerIt->second;
@@ -62,22 +62,22 @@
}
bool handleMetricWithConditions(
- const string condition, const int metricIndex,
- const unordered_map<string, int>& conditionTrackerMap,
+ const int64_t condition, const int metricIndex,
+ const unordered_map<int64_t, int>& conditionTrackerMap,
const ::google::protobuf::RepeatedPtrField<::android::os::statsd::MetricConditionLink>&
links,
vector<sp<ConditionTracker>>& allConditionTrackers, int& conditionIndex,
unordered_map<int, std::vector<int>>& conditionToMetricMap) {
auto condition_it = conditionTrackerMap.find(condition);
if (condition_it == conditionTrackerMap.end()) {
- ALOGW("cannot find Predicate \"%s\" in the config", condition.c_str());
+ ALOGW("cannot find Predicate \"%lld\" in the config", (long long)condition);
return false;
}
for (const auto& link : links) {
auto it = conditionTrackerMap.find(link.condition());
if (it == conditionTrackerMap.end()) {
- ALOGW("cannot find Predicate \"%s\" in the config", link.condition().c_str());
+ ALOGW("cannot find Predicate \"%lld\" in the config", (long long)link.condition());
return false;
}
allConditionTrackers[condition_it->second]->setSliced(true);
@@ -93,7 +93,7 @@
}
bool initLogTrackers(const StatsdConfig& config, const UidMap& uidMap,
- unordered_map<string, int>& logTrackerMap,
+ unordered_map<int64_t, int>& logTrackerMap,
vector<sp<LogMatchingTracker>>& allAtomMatchers, set<int>& allTagIds) {
vector<AtomMatcher> matcherConfigs;
const int atomMatcherCount = config.atom_matcher_size();
@@ -107,22 +107,22 @@
switch (logMatcher.contents_case()) {
case AtomMatcher::ContentsCase::kSimpleAtomMatcher:
allAtomMatchers.push_back(new SimpleLogMatchingTracker(
- logMatcher.name(), index, logMatcher.simple_atom_matcher(), uidMap));
+ logMatcher.id(), index, logMatcher.simple_atom_matcher(), uidMap));
break;
case AtomMatcher::ContentsCase::kCombination:
allAtomMatchers.push_back(
- new CombinationLogMatchingTracker(logMatcher.name(), index));
+ new CombinationLogMatchingTracker(logMatcher.id(), index));
break;
default:
- ALOGE("Matcher \"%s\" malformed", logMatcher.name().c_str());
+ ALOGE("Matcher \"%lld\" malformed", (long long)logMatcher.id());
return false;
// continue;
}
- if (logTrackerMap.find(logMatcher.name()) != logTrackerMap.end()) {
+ if (logTrackerMap.find(logMatcher.id()) != logTrackerMap.end()) {
ALOGE("Duplicate AtomMatcher found!");
return false;
}
- logTrackerMap[logMatcher.name()] = index;
+ logTrackerMap[logMatcher.id()] = index;
matcherConfigs.push_back(logMatcher);
}
@@ -139,8 +139,8 @@
}
bool initConditions(const ConfigKey& key, const StatsdConfig& config,
- const unordered_map<string, int>& logTrackerMap,
- unordered_map<string, int>& conditionTrackerMap,
+ const unordered_map<int64_t, int>& logTrackerMap,
+ unordered_map<int64_t, int>& conditionTrackerMap,
vector<sp<ConditionTracker>>& allConditionTrackers,
unordered_map<int, std::vector<int>>& trackerToConditionMap) {
vector<Predicate> conditionConfigs;
@@ -154,23 +154,23 @@
switch (condition.contents_case()) {
case Predicate::ContentsCase::kSimplePredicate: {
allConditionTrackers.push_back(new SimpleConditionTracker(
- key, condition.name(), index, condition.simple_predicate(), logTrackerMap));
+ key, condition.id(), index, condition.simple_predicate(), logTrackerMap));
break;
}
case Predicate::ContentsCase::kCombination: {
allConditionTrackers.push_back(
- new CombinationConditionTracker(condition.name(), index));
+ new CombinationConditionTracker(condition.id(), index));
break;
}
default:
- ALOGE("Predicate \"%s\" malformed", condition.name().c_str());
+ ALOGE("Predicate \"%lld\" malformed", (long long)condition.id());
return false;
}
- if (conditionTrackerMap.find(condition.name()) != conditionTrackerMap.end()) {
+ if (conditionTrackerMap.find(condition.id()) != conditionTrackerMap.end()) {
ALOGE("Duplicate Predicate found!");
return false;
}
- conditionTrackerMap[condition.name()] = index;
+ conditionTrackerMap[condition.id()] = index;
conditionConfigs.push_back(condition);
}
@@ -190,14 +190,15 @@
}
bool initMetrics(const ConfigKey& key, const StatsdConfig& config, const long timeBaseSec,
- const unordered_map<string, int>& logTrackerMap,
- const unordered_map<string, int>& conditionTrackerMap,
+ const unordered_map<int64_t, int>& logTrackerMap,
+ const unordered_map<int64_t, int>& conditionTrackerMap,
const vector<sp<LogMatchingTracker>>& allAtomMatchers,
vector<sp<ConditionTracker>>& allConditionTrackers,
vector<sp<MetricProducer>>& allMetricProducers,
unordered_map<int, std::vector<int>>& conditionToMetricMap,
unordered_map<int, std::vector<int>>& trackerToMetricMap,
- unordered_map<string, int>& metricMap) {
+ unordered_map<int64_t, int>& metricMap,
+ std::set<int64_t> &noReportMetricIds) {
sp<ConditionWizard> wizard = new ConditionWizard(allConditionTrackers);
const int allMetricsCount = config.count_metric_size() + config.duration_metric_size() +
config.event_metric_size() + config.value_metric_size();
@@ -219,12 +220,12 @@
for (int i = 0; i < config.count_metric_size(); i++) {
const CountMetric& metric = config.count_metric(i);
if (!metric.has_what()) {
- ALOGW("cannot find \"what\" in CountMetric \"%s\"", metric.name().c_str());
+ ALOGW("cannot find \"what\" in CountMetric \"%lld\"", (long long)metric.id());
return false;
}
int metricIndex = allMetricProducers.size();
- metricMap.insert({metric.name(), metricIndex});
+ metricMap.insert({metric.id(), metricIndex});
int trackerIndex;
if (!handleMetricWithLogTrackers(metric.what(), metricIndex, metric.has_dimensions(),
allAtomMatchers, logTrackerMap, trackerToMetricMap,
@@ -256,7 +257,7 @@
for (int i = 0; i < config.duration_metric_size(); i++) {
int metricIndex = allMetricProducers.size();
const DurationMetric& metric = config.duration_metric(i);
- metricMap.insert({metric.name(), metricIndex});
+ metricMap.insert({metric.id(), metricIndex});
auto what_it = conditionTrackerMap.find(metric.what());
if (what_it == conditionTrackerMap.end()) {
@@ -327,8 +328,8 @@
for (int i = 0; i < config.event_metric_size(); i++) {
int metricIndex = allMetricProducers.size();
const EventMetric& metric = config.event_metric(i);
- metricMap.insert({metric.name(), metricIndex});
- if (!metric.has_name() || !metric.has_what()) {
+ metricMap.insert({metric.id(), metricIndex});
+ if (!metric.has_id() || !metric.has_what()) {
ALOGW("cannot find the metric name or what in config");
return false;
}
@@ -363,12 +364,12 @@
for (int i = 0; i < config.value_metric_size(); i++) {
const ValueMetric& metric = config.value_metric(i);
if (!metric.has_what()) {
- ALOGW("cannot find \"what\" in ValueMetric \"%s\"", metric.name().c_str());
+ ALOGW("cannot find \"what\" in ValueMetric \"%lld\"", (long long)metric.id());
return false;
}
int metricIndex = allMetricProducers.size();
- metricMap.insert({metric.name(), metricIndex});
+ metricMap.insert({metric.id(), metricIndex});
int trackerIndex;
if (!handleMetricWithLogTrackers(metric.what(), metricIndex, metric.has_dimensions(),
allAtomMatchers, logTrackerMap, trackerToMetricMap,
@@ -408,25 +409,25 @@
for (int i = 0; i < config.gauge_metric_size(); i++) {
const GaugeMetric& metric = config.gauge_metric(i);
if (!metric.has_what()) {
- ALOGW("cannot find \"what\" in GaugeMetric \"%s\"", metric.name().c_str());
+ ALOGW("cannot find \"what\" in GaugeMetric \"%lld\"", (long long)metric.id());
return false;
}
if ((!metric.gauge_fields_filter().has_include_all() ||
(metric.gauge_fields_filter().include_all() == false)) &&
!hasLeafNode(metric.gauge_fields_filter().fields())) {
- ALOGW("Incorrect field filter setting in GaugeMetric %s", metric.name().c_str());
+ ALOGW("Incorrect field filter setting in GaugeMetric %lld", (long long)metric.id());
return false;
}
if ((metric.gauge_fields_filter().has_include_all() &&
metric.gauge_fields_filter().include_all() == true) &&
hasLeafNode(metric.gauge_fields_filter().fields())) {
- ALOGW("Incorrect field filter setting in GaugeMetric %s", metric.name().c_str());
+ ALOGW("Incorrect field filter setting in GaugeMetric %lld", (long long)metric.id());
return false;
}
int metricIndex = allMetricProducers.size();
- metricMap.insert({metric.name(), metricIndex});
+ metricMap.insert({metric.id(), metricIndex});
int trackerIndex;
if (!handleMetricWithLogTrackers(metric.what(), metricIndex, metric.has_dimensions(),
allAtomMatchers, logTrackerMap, trackerToMetricMap,
@@ -461,19 +462,28 @@
key, metric, conditionIndex, wizard, pullTagId, atomTagId, startTimeNs);
allMetricProducers.push_back(gaugeProducer);
}
+ for (int i = 0; i < config.no_report_metric_size(); ++i) {
+ const auto no_report_metric = config.no_report_metric(i);
+ if (metricMap.find(no_report_metric) == metricMap.end()) {
+ ALOGW("no_report_metric %lld not exist", no_report_metric);
+ return false;
+ }
+ noReportMetricIds.insert(no_report_metric);
+ }
return true;
}
bool initAlerts(const StatsdConfig& config,
- const unordered_map<string, int>& metricProducerMap,
+ const unordered_map<int64_t, int>& metricProducerMap,
vector<sp<MetricProducer>>& allMetricProducers,
vector<sp<AnomalyTracker>>& allAnomalyTrackers) {
+ unordered_map<int64_t, int> anomalyTrackerMap;
for (int i = 0; i < config.alert_size(); i++) {
const Alert& alert = config.alert(i);
- const auto& itr = metricProducerMap.find(alert.metric_name());
+ const auto& itr = metricProducerMap.find(alert.metric_id());
if (itr == metricProducerMap.end()) {
- ALOGW("alert \"%s\" has unknown metric name: \"%s\"", alert.name().c_str(),
- alert.metric_name().c_str());
+ ALOGW("alert \"%lld\" has unknown metric id: \"%lld\"", (long long)alert.id(),
+ (long long)alert.metric_id());
return false;
}
if (alert.trigger_if_sum_gt() < 0 || alert.number_of_buckets() <= 0) {
@@ -485,25 +495,44 @@
sp<MetricProducer> metric = allMetricProducers[metricIndex];
sp<AnomalyTracker> anomalyTracker = metric->addAnomalyTracker(alert);
if (anomalyTracker != nullptr) {
+ anomalyTrackerMap.insert(std::make_pair(alert.id(), allAnomalyTrackers.size()));
allAnomalyTrackers.push_back(anomalyTracker);
}
}
+ for (int i = 0; i < config.subscription_size(); ++i) {
+ const Subscription& subscription = config.subscription(i);
+ if (subscription.subscriber_information_case() ==
+ Subscription::SubscriberInformationCase::SUBSCRIBER_INFORMATION_NOT_SET) {
+ ALOGW("subscription \"%lld\" has no subscriber info.\"",
+ (long long)subscription.id());
+ return false;
+ }
+ const auto& itr = anomalyTrackerMap.find(subscription.rule_id());
+ if (itr == anomalyTrackerMap.end()) {
+ ALOGW("subscription \"%lld\" has unknown rule id: \"%lld\"",
+ (long long)subscription.id(), (long long)subscription.rule_id());
+ return false;
+ }
+ const int anomalyTrackerIndex = itr->second;
+ allAnomalyTrackers[anomalyTrackerIndex]->addSubscription(subscription);
+ }
return true;
}
bool initStatsdConfig(const ConfigKey& key, const StatsdConfig& config,
- const UidMap& uidMap,
- const long timeBaseSec, set<int>& allTagIds,
+ const UidMap& uidMap,
+ const long timeBaseSec, set<int>& allTagIds,
vector<sp<LogMatchingTracker>>& allAtomMatchers,
vector<sp<ConditionTracker>>& allConditionTrackers,
vector<sp<MetricProducer>>& allMetricProducers,
vector<sp<AnomalyTracker>>& allAnomalyTrackers,
unordered_map<int, std::vector<int>>& conditionToMetricMap,
unordered_map<int, std::vector<int>>& trackerToMetricMap,
- unordered_map<int, std::vector<int>>& trackerToConditionMap) {
- unordered_map<string, int> logTrackerMap;
- unordered_map<string, int> conditionTrackerMap;
- unordered_map<string, int> metricProducerMap;
+ unordered_map<int, std::vector<int>>& trackerToConditionMap,
+ std::set<int64_t> &noReportMetricIds) {
+ unordered_map<int64_t, int> logTrackerMap;
+ unordered_map<int64_t, int> conditionTrackerMap;
+ unordered_map<int64_t, int> metricProducerMap;
if (!initLogTrackers(config, uidMap, logTrackerMap, allAtomMatchers, allTagIds)) {
ALOGE("initLogMatchingTrackers failed");
@@ -519,7 +548,7 @@
if (!initMetrics(key, config, timeBaseSec, logTrackerMap, conditionTrackerMap, allAtomMatchers,
allConditionTrackers, allMetricProducers, conditionToMetricMap,
- trackerToMetricMap, metricProducerMap)) {
+ trackerToMetricMap, metricProducerMap, noReportMetricIds)) {
ALOGE("initMetricProducers failed");
return false;
}
diff --git a/cmds/statsd/src/metrics/metrics_manager_util.h b/cmds/statsd/src/metrics/metrics_manager_util.h
index 9ad5176..4f19ada 100644
--- a/cmds/statsd/src/metrics/metrics_manager_util.h
+++ b/cmds/statsd/src/metrics/metrics_manager_util.h
@@ -43,8 +43,8 @@
// [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,
- std::unordered_map<std::string, int>& logTrackerMap,
+ const UidMap& uidMap,
+ std::unordered_map<int64_t, int>& logTrackerMap,
std::vector<sp<LogMatchingTracker>>& allAtomMatchers,
std::set<int>& allTagIds);
@@ -59,8 +59,8 @@
// [trackerToConditionMap]: contain the mapping from index of
// log tracker to condition trackers that use the log tracker
bool initConditions(const ConfigKey& key, const StatsdConfig& config,
- const std::unordered_map<std::string, int>& logTrackerMap,
- std::unordered_map<std::string, int>& conditionTrackerMap,
+ const std::unordered_map<int64_t, int>& logTrackerMap,
+ std::unordered_map<int64_t, int>& conditionTrackerMap,
std::vector<sp<ConditionTracker>>& allConditionTrackers,
std::unordered_map<int, std::vector<int>>& trackerToConditionMap,
std::unordered_map<int, std::vector<MetricConditionLink>>& eventConditionLinks);
@@ -79,28 +79,29 @@
// [trackerToMetricMap]: contains the mapping from log tracker to MetricProducer index.
bool initMetrics(
const ConfigKey& key, const StatsdConfig& config, const long timeBaseSec,
- const std::unordered_map<std::string, int>& logTrackerMap,
- const std::unordered_map<std::string, int>& conditionTrackerMap,
+ 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,
const vector<sp<LogMatchingTracker>>& allAtomMatchers,
vector<sp<ConditionTracker>>& allConditionTrackers,
std::vector<sp<MetricProducer>>& allMetricProducers,
std::unordered_map<int, std::vector<int>>& conditionToMetricMap,
- std::unordered_map<int, std::vector<int>>& trackerToMetricMap);
+ std::unordered_map<int, std::vector<int>>& trackerToMetricMap,
+ std::set<int64_t> &noReportMetricIds);
// Initialize MetricsManager from StatsdConfig.
// Parameters are the members of MetricsManager. See MetricsManager for declaration.
bool initStatsdConfig(const ConfigKey& key, const StatsdConfig& config,
-
- const UidMap& uidMap,
- const long timeBaseSec, std::set<int>& allTagIds,
+ const UidMap& uidMap,
+ const long timeBaseSec, std::set<int>& allTagIds,
std::vector<sp<LogMatchingTracker>>& allAtomMatchers,
std::vector<sp<ConditionTracker>>& allConditionTrackers,
std::vector<sp<MetricProducer>>& allMetricProducers,
vector<sp<AnomalyTracker>>& allAnomalyTrackers,
std::unordered_map<int, std::vector<int>>& conditionToMetricMap,
std::unordered_map<int, std::vector<int>>& trackerToMetricMap,
- std::unordered_map<int, std::vector<int>>& trackerToConditionMap);
+ std::unordered_map<int, std::vector<int>>& trackerToConditionMap,
+ std::set<int64_t> &noReportMetricIds);
} // namespace statsd
} // namespace os
diff --git a/cmds/statsd/src/stats_log.proto b/cmds/statsd/src/stats_log.proto
index f5282ea..0b369bb 100644
--- a/cmds/statsd/src/stats_log.proto
+++ b/cmds/statsd/src/stats_log.proto
@@ -137,7 +137,7 @@
}
message StatsLogReport {
- optional string metric_name = 1;
+ optional int64 metric_id = 1;
optional int64 start_report_nanos = 2;
@@ -178,7 +178,7 @@
message ConfigMetricsReportList {
message ConfigKey {
optional int32 uid = 1;
- optional string name = 2;
+ optional int64 id = 2;
}
optional ConfigKey config_key = 1;
@@ -191,28 +191,28 @@
optional int32 stats_end_time_sec = 2;
message MatcherStats {
- optional string name = 1;
+ optional int64 id = 1;
optional int32 matched_times = 2;
}
message ConditionStats {
- optional string name = 1;
+ optional int64 id = 1;
optional int32 max_tuple_counts = 2;
}
message MetricStats {
- optional string name = 1;
+ optional int64 id = 1;
optional int32 max_tuple_counts = 2;
}
message AlertStats {
- optional string name = 1;
+ optional int64 id = 1;
optional int32 alerted_times = 2;
}
message ConfigStats {
optional int32 uid = 1;
- optional string name = 2;
+ optional int64 id = 2;
optional int32 creation_time_sec = 3;
optional int32 deletion_time_sec = 4;
optional int32 metric_count = 5;
diff --git a/cmds/statsd/src/stats_util.h b/cmds/statsd/src/stats_util.h
index e46b8eb..160b1f4 100644
--- a/cmds/statsd/src/stats_util.h
+++ b/cmds/statsd/src/stats_util.h
@@ -32,7 +32,7 @@
// Minimum bucket size in seconds
const long kMinBucketSizeSec = 5 * 60;
-typedef std::map<std::string, std::vector<HashableDimensionKey>> ConditionKey;
+typedef std::map<int64_t, std::vector<HashableDimensionKey>> ConditionKey;
typedef std::unordered_map<HashableDimensionKey, int64_t> DimToValMap;
diff --git a/cmds/statsd/src/statsd_config.proto b/cmds/statsd/src/statsd_config.proto
index 1ed1e05..6ac0e28 100644
--- a/cmds/statsd/src/statsd_config.proto
+++ b/cmds/statsd/src/statsd_config.proto
@@ -84,12 +84,12 @@
}
message AtomMatcher {
- optional string name = 1;
+ optional int64 id = 1;
message Combination {
optional LogicalOperation operation = 1;
- repeated string matcher = 2;
+ repeated int64 matcher = 2;
}
oneof contents {
SimpleAtomMatcher simple_atom_matcher = 2;
@@ -98,13 +98,13 @@
}
message SimplePredicate {
- optional string start = 1;
+ optional int64 start = 1;
- optional string stop = 2;
+ optional int64 stop = 2;
optional bool count_nesting = 3 [default = true];
- optional string stop_all = 4;
+ optional int64 stop_all = 4;
enum InitialValue {
UNKNOWN = 0;
@@ -116,12 +116,12 @@
}
message Predicate {
- optional string name = 1;
+ optional int64 id = 1;
message Combination {
optional LogicalOperation operation = 1;
- repeated string predicate = 2;
+ repeated int64 predicate = 2;
}
oneof contents {
@@ -135,7 +135,7 @@
}
message MetricConditionLink {
- optional string condition = 1;
+ optional int64 condition = 1;
optional FieldMatcher dimensions_in_what = 2;
@@ -148,21 +148,21 @@
}
message EventMetric {
- optional string name = 1;
+ optional int64 id = 1;
- optional string what = 2;
+ optional int64 what = 2;
- optional string condition = 3;
+ optional int64 condition = 3;
repeated MetricConditionLink links = 4;
}
message CountMetric {
- optional string name = 1;
+ optional int64 id = 1;
- optional string what = 2;
+ optional int64 what = 2;
- optional string condition = 3;
+ optional int64 condition = 3;
optional FieldMatcher dimensions = 4;
@@ -172,11 +172,11 @@
}
message DurationMetric {
- optional string name = 1;
+ optional int64 id = 1;
- optional string what = 2;
+ optional int64 what = 2;
- optional string condition = 3;
+ optional int64 condition = 3;
repeated MetricConditionLink links = 4;
@@ -193,13 +193,13 @@
}
message GaugeMetric {
- optional string name = 1;
+ optional int64 id = 1;
- optional string what = 2;
+ optional int64 what = 2;
optional FieldFilter gauge_fields_filter = 3;
- optional string condition = 4;
+ optional int64 condition = 4;
optional FieldMatcher dimensions = 5;
@@ -209,13 +209,13 @@
}
message ValueMetric {
- optional string name = 1;
+ optional int64 id = 1;
- optional string what = 2;
+ optional int64 what = 2;
optional int32 value_field = 3;
- optional string condition = 4;
+ optional int64 condition = 4;
optional FieldMatcher dimensions = 5;
@@ -228,20 +228,15 @@
}
message Alert {
- optional string name = 1;
+ optional int64 id = 1;
- optional string metric_name = 2;
+ optional int64 metric_id = 2;
- message IncidentdDetails {
- repeated int32 section = 1;
- }
- optional IncidentdDetails incidentd_details = 3;
+ optional int32 number_of_buckets = 3;
- optional int32 number_of_buckets = 4;
+ optional int32 refractory_period_secs = 4;
- optional int32 refractory_period_secs = 5;
-
- optional int64 trigger_if_sum_gt = 6;
+ optional int64 trigger_if_sum_gt = 5;
}
message AllowedLogSource {
@@ -249,8 +244,40 @@
repeated string package = 2;
}
+message Alarm {
+ optional int64 id = 1;
+ optional int64 offset_millis = 2;
+ optional int64 period_millis = 3;
+}
+
+message IncidentdDetails {
+ repeated int32 section = 1;
+}
+
+message PerfettoDetails {
+ optional int32 perfetto_stuff = 1;
+}
+
+message Subscription {
+ optional int64 id = 1;
+
+ enum RuleType {
+ RULE_TYPE_UNSPECIFIED = 0;
+ ALARM = 1;
+ ALERT = 2;
+ }
+ optional RuleType rule_type = 2;
+
+ optional int64 rule_id = 3;
+
+ oneof subscriber_information {
+ IncidentdDetails incidentd_details = 4;
+ PerfettoDetails perfetto_details = 5;
+ }
+}
+
message StatsdConfig {
- optional string name = 1;
+ optional int64 id = 1;
repeated EventMetric event_metric = 2;
@@ -268,5 +295,11 @@
repeated Alert alert = 9;
- optional AllowedLogSource log_source = 10;
+ repeated Alarm alarm = 10;
+
+ repeated Subscription subscription = 11;
+
+ optional AllowedLogSource log_source = 12;
+
+ repeated int64 no_report_metric = 13;
}
diff --git a/cmds/statsd/src/storage/StorageManager.cpp b/cmds/statsd/src/storage/StorageManager.cpp
index 9919abf..c542db2 100644
--- a/cmds/statsd/src/storage/StorageManager.cpp
+++ b/cmds/statsd/src/storage/StorageManager.cpp
@@ -124,7 +124,7 @@
}
if (index < 2) continue;
- sendBroadcast(ConfigKey(uid, configName));
+ sendBroadcast(ConfigKey(uid, StrToInt64(configName)));
}
}
@@ -198,6 +198,7 @@
index++;
}
if (index < 2) continue;
+
string file_name = StringPrintf("%s/%s", STATS_SERVICE_DIR, name);
VLOG("full file %s", file_name.c_str());
int fd = open(file_name.c_str(), O_RDONLY | O_CLOEXEC);
@@ -206,7 +207,7 @@
if (android::base::ReadFdToString(fd, &content)) {
StatsdConfig config;
if (config.ParseFromString(content)) {
- configsMap[ConfigKey(uid, configName)] = config;
+ configsMap[ConfigKey(uid, StrToInt64(configName))] = config;
VLOG("map key uid=%d|name=%s", uid, name);
}
}
diff --git a/cmds/statsd/tests/ConfigManager_test.cpp b/cmds/statsd/tests/ConfigManager_test.cpp
index 3d923e2..3eac5d2 100644
--- a/cmds/statsd/tests/ConfigManager_test.cpp
+++ b/cmds/statsd/tests/ConfigManager_test.cpp
@@ -14,6 +14,7 @@
#include "src/config/ConfigManager.h"
#include "src/metrics/MetricsManager.h"
+#include "statsd_test_util.h"
#include <gmock/gmock.h>
#include <gtest/gtest.h>
@@ -31,7 +32,7 @@
namespace statsd {
static ostream& operator<<(ostream& os, const StatsdConfig& config) {
- return os << "StatsdConfig{name=" << config.name().c_str() << "}";
+ return os << "StatsdConfig{id=" << config.id() << "}";
}
} // namespace statsd
@@ -50,19 +51,21 @@
/**
* Validate that the ConfigKey is the one we wanted.
*/
-MATCHER_P2(ConfigKeyEq, uid, name, "") {
- return arg.GetUid() == uid && arg.GetName() == name;
+MATCHER_P2(ConfigKeyEq, uid, id, "") {
+ return arg.GetUid() == uid && (long long)arg.GetId() == (long long)id;
}
/**
* Validate that the StatsdConfig is the one we wanted.
*/
-MATCHER_P(StatsdConfigEq, name, "") {
- return arg.name() == name;
+MATCHER_P(StatsdConfigEq, id, 0) {
+ return (long long)arg.id() == (long long)id;
}
+const int64_t testConfigId = 12345;
+
TEST(ConfigManagerTest, TestFakeConfig) {
- auto metricsManager = std::make_unique<MetricsManager>(ConfigKey(0, "test"),
+ auto metricsManager = std::make_unique<MetricsManager>(ConfigKey(0, testConfigId),
build_fake_config(), 1000, new UidMap());
EXPECT_TRUE(metricsManager->isConfigValid());
}
@@ -77,13 +80,13 @@
manager->AddListener(listener);
StatsdConfig config91;
- config91.set_name("91");
+ config91.set_id(91);
StatsdConfig config92;
- config92.set_name("92");
+ config92.set_id(92);
StatsdConfig config93;
- config93.set_name("93");
+ config93.set_id(93);
StatsdConfig config94;
- config94.set_name("94");
+ config94.set_id(94);
{
InSequence s;
@@ -91,42 +94,46 @@
manager->Startup();
// Add another one
- EXPECT_CALL(*(listener.get()), OnConfigUpdated(ConfigKeyEq(1, "zzz"), StatsdConfigEq("91")))
+ EXPECT_CALL(*(listener.get()), OnConfigUpdated(ConfigKeyEq(1, StringToId("zzz")),
+ StatsdConfigEq(91)))
.RetiresOnSaturation();
- manager->UpdateConfig(ConfigKey(1, "zzz"), config91);
+ manager->UpdateConfig(ConfigKey(1, StringToId("zzz")), config91);
// Update It
- EXPECT_CALL(*(listener.get()), OnConfigUpdated(ConfigKeyEq(1, "zzz"), StatsdConfigEq("92")))
+ EXPECT_CALL(*(listener.get()), OnConfigUpdated(ConfigKeyEq(1, StringToId("zzz")),
+ StatsdConfigEq(92)))
.RetiresOnSaturation();
- manager->UpdateConfig(ConfigKey(1, "zzz"), config92);
+ manager->UpdateConfig(ConfigKey(1, StringToId("zzz")), config92);
// Add one with the same uid but a different name
- EXPECT_CALL(*(listener.get()), OnConfigUpdated(ConfigKeyEq(1, "yyy"), StatsdConfigEq("93")))
+ EXPECT_CALL(*(listener.get()), OnConfigUpdated(ConfigKeyEq(1, StringToId("yyy")),
+ StatsdConfigEq(93)))
.RetiresOnSaturation();
- manager->UpdateConfig(ConfigKey(1, "yyy"), config93);
+ manager->UpdateConfig(ConfigKey(1, StringToId("yyy")), config93);
// Add one with the same name but a different uid
- EXPECT_CALL(*(listener.get()), OnConfigUpdated(ConfigKeyEq(2, "zzz"), StatsdConfigEq("94")))
+ EXPECT_CALL(*(listener.get()), OnConfigUpdated(ConfigKeyEq(2, StringToId("zzz")),
+ StatsdConfigEq(94)))
.RetiresOnSaturation();
- manager->UpdateConfig(ConfigKey(2, "zzz"), config94);
+ manager->UpdateConfig(ConfigKey(2, StringToId("zzz")), config94);
// Remove (1,yyy)
- EXPECT_CALL(*(listener.get()), OnConfigRemoved(ConfigKeyEq(1, "yyy")))
+ EXPECT_CALL(*(listener.get()), OnConfigRemoved(ConfigKeyEq(1, StringToId("yyy"))))
.RetiresOnSaturation();
- manager->RemoveConfig(ConfigKey(1, "yyy"));
+ manager->RemoveConfig(ConfigKey(1, StringToId("yyy")));
// Remove (2,zzz)
- EXPECT_CALL(*(listener.get()), OnConfigRemoved(ConfigKeyEq(2, "zzz")))
+ EXPECT_CALL(*(listener.get()), OnConfigRemoved(ConfigKeyEq(2, StringToId("zzz"))))
.RetiresOnSaturation();
- manager->RemoveConfig(ConfigKey(2, "zzz"));
+ manager->RemoveConfig(ConfigKey(2, StringToId("zzz")));
// Remove (1,zzz)
- EXPECT_CALL(*(listener.get()), OnConfigRemoved(ConfigKeyEq(1, "zzz")))
+ EXPECT_CALL(*(listener.get()), OnConfigRemoved(ConfigKeyEq(1, StringToId("zzz"))))
.RetiresOnSaturation();
- manager->RemoveConfig(ConfigKey(1, "zzz"));
+ manager->RemoveConfig(ConfigKey(1, StringToId("zzz")));
// Remove (2,zzz) again and we shouldn't get the callback
- manager->RemoveConfig(ConfigKey(2, "zzz"));
+ manager->RemoveConfig(ConfigKey(2, StringToId("zzz")));
}
}
@@ -142,16 +149,16 @@
StatsdConfig config;
EXPECT_CALL(*(listener.get()), OnConfigUpdated(_, _)).Times(5);
- EXPECT_CALL(*(listener.get()), OnConfigRemoved(ConfigKeyEq(2, "xxx")));
- EXPECT_CALL(*(listener.get()), OnConfigRemoved(ConfigKeyEq(2, "yyy")));
- EXPECT_CALL(*(listener.get()), OnConfigRemoved(ConfigKeyEq(2, "zzz")));
+ EXPECT_CALL(*(listener.get()), OnConfigRemoved(ConfigKeyEq(2, StringToId("xxx"))));
+ EXPECT_CALL(*(listener.get()), OnConfigRemoved(ConfigKeyEq(2, StringToId("yyy"))));
+ EXPECT_CALL(*(listener.get()), OnConfigRemoved(ConfigKeyEq(2, StringToId("zzz"))));
manager->Startup();
- manager->UpdateConfig(ConfigKey(1, "aaa"), config);
- manager->UpdateConfig(ConfigKey(2, "xxx"), config);
- manager->UpdateConfig(ConfigKey(2, "yyy"), config);
- manager->UpdateConfig(ConfigKey(2, "zzz"), config);
- manager->UpdateConfig(ConfigKey(3, "bbb"), config);
+ manager->UpdateConfig(ConfigKey(1, StringToId("aaa")), config);
+ manager->UpdateConfig(ConfigKey(2, StringToId("xxx")), config);
+ manager->UpdateConfig(ConfigKey(2, StringToId("yyy")), config);
+ manager->UpdateConfig(ConfigKey(2, StringToId("zzz")), config);
+ manager->UpdateConfig(ConfigKey(3, StringToId("bbb")), config);
manager->RemoveConfigs(2);
}
diff --git a/cmds/statsd/tests/MetricsManager_test.cpp b/cmds/statsd/tests/MetricsManager_test.cpp
index 6cd31dd..96ee9c5 100644
--- a/cmds/statsd/tests/MetricsManager_test.cpp
+++ b/cmds/statsd/tests/MetricsManager_test.cpp
@@ -21,6 +21,7 @@
#include "src/metrics/MetricProducer.h"
#include "src/metrics/ValueMetricProducer.h"
#include "src/metrics/metrics_manager_util.h"
+#include "statsd_test_util.h"
#include "frameworks/base/cmds/statsd/src/statsd_config.pb.h"
@@ -40,16 +41,16 @@
// TODO: ADD MORE TEST CASES.
-const ConfigKey kConfigKey(0, "test");
+const ConfigKey kConfigKey(0, 12345);
const long timeBaseSec = 1000;
StatsdConfig buildGoodConfig() {
StatsdConfig config;
- config.set_name("12345");
+ config.set_id(12345);
AtomMatcher* eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_IS_ON");
+ eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
@@ -59,7 +60,7 @@
2 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_ON*/);
eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_IS_OFF");
+ eventMatcher->set_id(StringToId("SCREEN_IS_OFF"));
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
@@ -69,23 +70,25 @@
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_OFF*/);
eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_ON_OR_OFF");
+ eventMatcher->set_id(StringToId("SCREEN_ON_OR_OFF"));
AtomMatcher_Combination* combination = eventMatcher->mutable_combination();
combination->set_operation(LogicalOperation::OR);
- combination->add_matcher("SCREEN_IS_ON");
- combination->add_matcher("SCREEN_IS_OFF");
+ combination->add_matcher(StringToId("SCREEN_IS_ON"));
+ combination->add_matcher(StringToId("SCREEN_IS_OFF"));
CountMetric* metric = config.add_count_metric();
- metric->set_name("3");
- metric->set_what("SCREEN_IS_ON");
+ metric->set_id(3);
+ metric->set_what(StringToId("SCREEN_IS_ON"));
metric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
metric->mutable_dimensions()->set_field(2 /*SCREEN_STATE_CHANGE*/);
metric->mutable_dimensions()->add_child()->set_field(1);
+ config.add_no_report_metric(3);
+
auto alert = config.add_alert();
- alert->set_name("3");
- alert->set_metric_name("3");
+ alert->set_id(3);
+ alert->set_metric_id(3);
alert->set_number_of_buckets(10);
alert->set_refractory_period_secs(100);
alert->set_trigger_if_sum_gt(100);
@@ -94,10 +97,10 @@
StatsdConfig buildCircleMatchers() {
StatsdConfig config;
- config.set_name("12345");
+ config.set_id(12345);
AtomMatcher* eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_IS_ON");
+ eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
@@ -107,34 +110,34 @@
2 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_ON*/);
eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_ON_OR_OFF");
+ eventMatcher->set_id(StringToId("SCREEN_ON_OR_OFF"));
AtomMatcher_Combination* combination = eventMatcher->mutable_combination();
combination->set_operation(LogicalOperation::OR);
- combination->add_matcher("SCREEN_IS_ON");
+ combination->add_matcher(StringToId("SCREEN_IS_ON"));
// Circle dependency
- combination->add_matcher("SCREEN_ON_OR_OFF");
+ combination->add_matcher(StringToId("SCREEN_ON_OR_OFF"));
return config;
}
StatsdConfig buildAlertWithUnknownMetric() {
StatsdConfig config;
- config.set_name("12345");
+ config.set_id(12345);
AtomMatcher* eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_IS_ON");
+ eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
CountMetric* metric = config.add_count_metric();
- metric->set_name("3");
- metric->set_what("SCREEN_IS_ON");
+ metric->set_id(3);
+ metric->set_what(StringToId("SCREEN_IS_ON"));
metric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
metric->mutable_dimensions()->set_field(2 /*SCREEN_STATE_CHANGE*/);
metric->mutable_dimensions()->add_child()->set_field(1);
auto alert = config.add_alert();
- alert->set_name("3");
- alert->set_metric_name("2");
+ alert->set_id(3);
+ alert->set_metric_id(2);
alert->set_number_of_buckets(10);
alert->set_refractory_period_secs(100);
alert->set_trigger_if_sum_gt(100);
@@ -143,10 +146,10 @@
StatsdConfig buildMissingMatchers() {
StatsdConfig config;
- config.set_name("12345");
+ config.set_id(12345);
AtomMatcher* eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_IS_ON");
+ eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
@@ -156,29 +159,29 @@
2 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_ON*/);
eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_ON_OR_OFF");
+ eventMatcher->set_id(StringToId("SCREEN_ON_OR_OFF"));
AtomMatcher_Combination* combination = eventMatcher->mutable_combination();
combination->set_operation(LogicalOperation::OR);
- combination->add_matcher("SCREEN_IS_ON");
+ combination->add_matcher(StringToId("SCREEN_IS_ON"));
// undefined matcher
- combination->add_matcher("ABC");
+ combination->add_matcher(StringToId("ABC"));
return config;
}
StatsdConfig buildMissingPredicate() {
StatsdConfig config;
- config.set_name("12345");
+ config.set_id(12345);
CountMetric* metric = config.add_count_metric();
- metric->set_name("3");
- metric->set_what("SCREEN_EVENT");
+ metric->set_id(3);
+ metric->set_what(StringToId("SCREEN_EVENT"));
metric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
- metric->set_condition("SOME_CONDITION");
+ metric->set_condition(StringToId("SOME_CONDITION"));
AtomMatcher* eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_EVENT");
+ eventMatcher->set_id(StringToId("SCREEN_EVENT"));
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(2);
@@ -188,37 +191,37 @@
StatsdConfig buildDimensionMetricsWithMultiTags() {
StatsdConfig config;
- config.set_name("12345");
+ config.set_id(12345);
AtomMatcher* eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("BATTERY_VERY_LOW");
+ 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_name("BATTERY_VERY_VERY_LOW");
+ 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_name("BATTERY_LOW");
+ eventMatcher->set_id(StringToId("BATTERY_LOW"));
AtomMatcher_Combination* combination = eventMatcher->mutable_combination();
combination->set_operation(LogicalOperation::OR);
- combination->add_matcher("BATTERY_VERY_LOW");
- combination->add_matcher("BATTERY_VERY_VERY_LOW");
+ 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_name("3");
- metric->set_what("BATTERY_LOW");
+ metric->set_id(3);
+ metric->set_what(StringToId("BATTERY_LOW"));
metric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
// This case is interesting. We want to dimension across two atoms.
metric->mutable_dimensions()->add_child()->set_field(1);
auto alert = config.add_alert();
- alert->set_name("3");
- alert->set_metric_name("3");
+ alert->set_id(103);
+ alert->set_metric_id(3);
alert->set_number_of_buckets(10);
alert->set_refractory_period_secs(100);
alert->set_trigger_if_sum_gt(100);
@@ -227,10 +230,10 @@
StatsdConfig buildCirclePredicates() {
StatsdConfig config;
- config.set_name("12345");
+ config.set_id(12345);
AtomMatcher* eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_IS_ON");
+ eventMatcher->set_id(StringToId("SCREEN_IS_ON"));
SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
@@ -240,7 +243,7 @@
2 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_ON*/);
eventMatcher = config.add_atom_matcher();
- eventMatcher->set_name("SCREEN_IS_OFF");
+ eventMatcher->set_id(StringToId("SCREEN_IS_OFF"));
simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
simpleAtomMatcher->set_atom_id(2 /*SCREEN_STATE_CHANGE*/);
@@ -250,18 +253,18 @@
1 /*SCREEN_STATE_CHANGE__DISPLAY_STATE__STATE_OFF*/);
auto condition = config.add_predicate();
- condition->set_name("SCREEN_IS_ON");
+ condition->set_id(StringToId("SCREEN_IS_ON"));
SimplePredicate* simplePredicate = condition->mutable_simple_predicate();
- simplePredicate->set_start("SCREEN_IS_ON");
- simplePredicate->set_stop("SCREEN_IS_OFF");
+ simplePredicate->set_start(StringToId("SCREEN_IS_ON"));
+ simplePredicate->set_stop(StringToId("SCREEN_IS_OFF"));
condition = config.add_predicate();
- condition->set_name("SCREEN_IS_EITHER_ON_OFF");
+ condition->set_id(StringToId("SCREEN_IS_EITHER_ON_OFF"));
Predicate_Combination* combination = condition->mutable_combination();
combination->set_operation(LogicalOperation::OR);
- combination->add_predicate("SCREEN_IS_ON");
- combination->add_predicate("SCREEN_IS_EITHER_ON_OFF");
+ combination->add_predicate(StringToId("SCREEN_IS_ON"));
+ combination->add_predicate(StringToId("SCREEN_IS_EITHER_ON_OFF"));
return config;
}
@@ -277,12 +280,15 @@
unordered_map<int, std::vector<int>> conditionToMetricMap;
unordered_map<int, std::vector<int>> trackerToMetricMap;
unordered_map<int, std::vector<int>> trackerToConditionMap;
+ std::set<int64_t> noReportMetricIds;
EXPECT_TRUE(initStatsdConfig(kConfigKey, config, uidMap, timeBaseSec, allTagIds, allAtomMatchers,
allConditionTrackers, allMetricProducers, allAnomalyTrackers,
- conditionToMetricMap, trackerToMetricMap, trackerToConditionMap));
+ conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
+ noReportMetricIds));
EXPECT_EQ(1u, allMetricProducers.size());
EXPECT_EQ(1u, allAnomalyTrackers.size());
+ EXPECT_EQ(1u, noReportMetricIds.size());
}
TEST(MetricsManagerTest, TestDimensionMetricsWithMultiTags) {
@@ -296,10 +302,12 @@
unordered_map<int, std::vector<int>> conditionToMetricMap;
unordered_map<int, std::vector<int>> trackerToMetricMap;
unordered_map<int, std::vector<int>> trackerToConditionMap;
+ std::set<int64_t> noReportMetricIds;
EXPECT_FALSE(initStatsdConfig(kConfigKey, config, uidMap, timeBaseSec, allTagIds, allAtomMatchers,
allConditionTrackers, allMetricProducers, allAnomalyTrackers,
- conditionToMetricMap, trackerToMetricMap, trackerToConditionMap));
+ conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
+ noReportMetricIds));
}
TEST(MetricsManagerTest, TestCircleLogMatcherDependency) {
@@ -313,10 +321,12 @@
unordered_map<int, std::vector<int>> conditionToMetricMap;
unordered_map<int, std::vector<int>> trackerToMetricMap;
unordered_map<int, std::vector<int>> trackerToConditionMap;
+ std::set<int64_t> noReportMetricIds;
EXPECT_FALSE(initStatsdConfig(kConfigKey, config, uidMap, timeBaseSec, allTagIds, allAtomMatchers,
allConditionTrackers, allMetricProducers, allAnomalyTrackers,
- conditionToMetricMap, trackerToMetricMap, trackerToConditionMap));
+ conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
+ noReportMetricIds));
}
TEST(MetricsManagerTest, TestMissingMatchers) {
@@ -330,9 +340,11 @@
unordered_map<int, std::vector<int>> conditionToMetricMap;
unordered_map<int, std::vector<int>> trackerToMetricMap;
unordered_map<int, std::vector<int>> trackerToConditionMap;
+ std::set<int64_t> noReportMetricIds;
EXPECT_FALSE(initStatsdConfig(kConfigKey, config, uidMap, timeBaseSec, allTagIds, allAtomMatchers,
allConditionTrackers, allMetricProducers, allAnomalyTrackers,
- conditionToMetricMap, trackerToMetricMap, trackerToConditionMap));
+ conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
+ noReportMetricIds));
}
TEST(MetricsManagerTest, TestMissingPredicate) {
@@ -346,9 +358,11 @@
unordered_map<int, std::vector<int>> conditionToMetricMap;
unordered_map<int, std::vector<int>> trackerToMetricMap;
unordered_map<int, std::vector<int>> trackerToConditionMap;
+ std::set<int64_t> noReportMetricIds;
EXPECT_FALSE(initStatsdConfig(kConfigKey, config, uidMap, timeBaseSec, allTagIds, allAtomMatchers,
allConditionTrackers, allMetricProducers, allAnomalyTrackers,
- conditionToMetricMap, trackerToMetricMap, trackerToConditionMap));
+ conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
+ noReportMetricIds));
}
TEST(MetricsManagerTest, TestCirclePredicateDependency) {
@@ -362,10 +376,12 @@
unordered_map<int, std::vector<int>> conditionToMetricMap;
unordered_map<int, std::vector<int>> trackerToMetricMap;
unordered_map<int, std::vector<int>> trackerToConditionMap;
+ std::set<int64_t> noReportMetricIds;
EXPECT_FALSE(initStatsdConfig(kConfigKey, config, uidMap, timeBaseSec, allTagIds, allAtomMatchers,
allConditionTrackers, allMetricProducers, allAnomalyTrackers,
- conditionToMetricMap, trackerToMetricMap, trackerToConditionMap));
+ conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
+ noReportMetricIds));
}
TEST(MetricsManagerTest, testAlertWithUnknownMetric) {
@@ -379,10 +395,12 @@
unordered_map<int, std::vector<int>> conditionToMetricMap;
unordered_map<int, std::vector<int>> trackerToMetricMap;
unordered_map<int, std::vector<int>> trackerToConditionMap;
+ std::set<int64_t> noReportMetricIds;
EXPECT_FALSE(initStatsdConfig(kConfigKey, config, uidMap, timeBaseSec, allTagIds, allAtomMatchers,
allConditionTrackers, allMetricProducers, allAnomalyTrackers,
- conditionToMetricMap, trackerToMetricMap, trackerToConditionMap));
+ conditionToMetricMap, trackerToMetricMap, trackerToConditionMap,
+ noReportMetricIds));
}
#else
diff --git a/cmds/statsd/tests/StatsLogProcessor_test.cpp b/cmds/statsd/tests/StatsLogProcessor_test.cpp
index a27bed5..5d053e2 100644
--- a/cmds/statsd/tests/StatsLogProcessor_test.cpp
+++ b/cmds/statsd/tests/StatsLogProcessor_test.cpp
@@ -41,7 +41,7 @@
*/
class MockMetricsManager : public MetricsManager {
public:
- MockMetricsManager() : MetricsManager(ConfigKey(1, "key"), StatsdConfig(), 1000, new UidMap()) {
+ MockMetricsManager() : MetricsManager(ConfigKey(1, 12345), StatsdConfig(), 1000, new UidMap()) {
}
MOCK_METHOD0(byteSize, size_t());
@@ -56,7 +56,7 @@
MockMetricsManager mockMetricsManager;
- ConfigKey key(100, "key");
+ ConfigKey key(100, 12345);
// Expect only the first flush to trigger a check for byte size since the last two are
// rate-limited.
EXPECT_CALL(mockMetricsManager, byteSize()).Times(1);
@@ -74,7 +74,7 @@
MockMetricsManager mockMetricsManager;
- ConfigKey key(100, "key");
+ ConfigKey key(100, 12345);
EXPECT_CALL(mockMetricsManager, byteSize())
.Times(2)
.WillRepeatedly(Return(int(StatsdStats::kMaxMetricsBytesPerConfig * .95)));
@@ -98,7 +98,7 @@
MockMetricsManager mockMetricsManager;
- ConfigKey key(100, "key");
+ ConfigKey key(100, 12345);
EXPECT_CALL(mockMetricsManager, byteSize())
.Times(1)
.WillRepeatedly(Return(int(StatsdStats::kMaxMetricsBytesPerConfig * 1.2)));
diff --git a/cmds/statsd/tests/UidMap_test.cpp b/cmds/statsd/tests/UidMap_test.cpp
index 8a394f7..945af27 100644
--- a/cmds/statsd/tests/UidMap_test.cpp
+++ b/cmds/statsd/tests/UidMap_test.cpp
@@ -18,6 +18,7 @@
#include "guardrail/StatsdStats.h"
#include "logd/LogEvent.h"
#include "statslog.h"
+#include "statsd_test_util.h"
#include <gtest/gtest.h>
@@ -156,8 +157,8 @@
TEST(UidMapTest, TestClearingOutput) {
UidMap m;
- ConfigKey config1(1, "config1");
- ConfigKey config2(1, "config2");
+ ConfigKey config1(1, StringToId("config1"));
+ ConfigKey config2(1, StringToId("config2"));
m.OnConfigUpdated(config1);
@@ -211,7 +212,7 @@
TEST(UidMapTest, TestMemoryComputed) {
UidMap m;
- ConfigKey config1(1, "config1");
+ ConfigKey config1(1, StringToId("config1"));
m.OnConfigUpdated(config1);
size_t startBytes = m.mBytesUsed;
@@ -241,7 +242,7 @@
UidMap m;
string buf;
- ConfigKey config1(1, "config1");
+ ConfigKey config1(1, StringToId("config1"));
m.OnConfigUpdated(config1);
size_t startBytes = m.mBytesUsed;
diff --git a/cmds/statsd/tests/anomaly/AnomalyTracker_test.cpp b/cmds/statsd/tests/anomaly/AnomalyTracker_test.cpp
index da872ad..751180d 100644
--- a/cmds/statsd/tests/anomaly/AnomalyTracker_test.cpp
+++ b/cmds/statsd/tests/anomaly/AnomalyTracker_test.cpp
@@ -31,7 +31,7 @@
namespace os {
namespace statsd {
-const ConfigKey kConfigKey(0, "test");
+const ConfigKey kConfigKey(0, 12345);
HashableDimensionKey getMockDimensionKey(int key, string value) {
DimensionsValue dimensionsValue;
diff --git a/cmds/statsd/tests/condition/SimpleConditionTracker_test.cpp b/cmds/statsd/tests/condition/SimpleConditionTracker_test.cpp
index 705804f..819f2be 100644
--- a/cmds/statsd/tests/condition/SimpleConditionTracker_test.cpp
+++ b/cmds/statsd/tests/condition/SimpleConditionTracker_test.cpp
@@ -11,7 +11,9 @@
// 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/condition/SimpleConditionTracker.h"
+#include "tests/statsd_test_util.h"
#include <gmock/gmock.h>
#include <gtest/gtest.h>
@@ -29,7 +31,7 @@
namespace os {
namespace statsd {
-const ConfigKey kConfigKey(0, "test");
+const ConfigKey kConfigKey(0, 12345);
const int ATTRIBUTION_NODE_FIELD_ID = 1;
const int ATTRIBUTION_UID_FIELD_ID = 1;
@@ -38,9 +40,9 @@
SimplePredicate getWakeLockHeldCondition(bool countNesting, bool defaultFalse,
bool outputSlicedUid, Position position) {
SimplePredicate simplePredicate;
- simplePredicate.set_start("WAKE_LOCK_ACQUIRE");
- simplePredicate.set_stop("WAKE_LOCK_RELEASE");
- simplePredicate.set_stop_all("RELEASE_ALL");
+ simplePredicate.set_start(StringToId("WAKE_LOCK_ACQUIRE"));
+ simplePredicate.set_stop(StringToId("WAKE_LOCK_RELEASE"));
+ simplePredicate.set_stop_all(StringToId("RELEASE_ALL"));
if (outputSlicedUid) {
simplePredicate.mutable_dimensions()->set_field(TAG_ID);
simplePredicate.mutable_dimensions()->add_child()->set_field(ATTRIBUTION_NODE_FIELD_ID);
@@ -73,10 +75,10 @@
event->init();
}
-std::map<string, std::vector<HashableDimensionKey>> getWakeLockQueryKey(
+std::map<int64_t, std::vector<HashableDimensionKey>> getWakeLockQueryKey(
const Position position,
const std::vector<int> &uids, const string& conditionName) {
- std::map<string, std::vector<HashableDimensionKey>> outputKeyMap;
+ std::map<int64_t, std::vector<HashableDimensionKey>> outputKeyMap;
std::vector<int> uid_indexes;
switch(position) {
case Position::FIRST:
@@ -96,28 +98,29 @@
for (const int idx : uid_indexes) {
DimensionsValue dimensionsValue;
dimensionsValue.set_field(TAG_ID);
- dimensionsValue.mutable_value_tuple()->add_dimensions_value()->set_field(ATTRIBUTION_NODE_FIELD_ID);
+ dimensionsValue.mutable_value_tuple()->add_dimensions_value()->set_field(
+ ATTRIBUTION_NODE_FIELD_ID);
dimensionsValue.mutable_value_tuple()->mutable_dimensions_value(0)
->mutable_value_tuple()->add_dimensions_value()->set_field(ATTRIBUTION_NODE_FIELD_ID);
dimensionsValue.mutable_value_tuple()->mutable_dimensions_value(0)
->mutable_value_tuple()->mutable_dimensions_value(0)->set_value_int(uids[idx]);
- outputKeyMap[conditionName].push_back(HashableDimensionKey(dimensionsValue));
+ outputKeyMap[StringToId(conditionName)].push_back(HashableDimensionKey(dimensionsValue));
}
return outputKeyMap;
}
TEST(SimpleConditionTrackerTest, TestNonSlicedCondition) {
SimplePredicate simplePredicate;
- simplePredicate.set_start("SCREEN_TURNED_ON");
- simplePredicate.set_stop("SCREEN_TURNED_OFF");
+ simplePredicate.set_start(StringToId("SCREEN_TURNED_ON"));
+ simplePredicate.set_stop(StringToId("SCREEN_TURNED_OFF"));
simplePredicate.set_count_nesting(false);
simplePredicate.set_initial_value(SimplePredicate_InitialValue_UNKNOWN);
- unordered_map<string, int> trackerNameIndexMap;
- trackerNameIndexMap["SCREEN_TURNED_ON"] = 0;
- trackerNameIndexMap["SCREEN_TURNED_OFF"] = 1;
+ unordered_map<int64_t, int> trackerNameIndexMap;
+ trackerNameIndexMap[StringToId("SCREEN_TURNED_ON")] = 0;
+ trackerNameIndexMap[StringToId("SCREEN_TURNED_OFF")] = 1;
- SimpleConditionTracker conditionTracker(kConfigKey, "SCREEN_IS_ON", 0 /*tracker index*/,
+ SimpleConditionTracker conditionTracker(kConfigKey, StringToId("SCREEN_IS_ON"), 0 /*tracker index*/,
simplePredicate, trackerNameIndexMap);
LogEvent event(1 /*tagId*/, 0 /*timestamp*/);
@@ -191,15 +194,15 @@
TEST(SimpleConditionTrackerTest, TestNonSlicedConditionNestCounting) {
SimplePredicate simplePredicate;
- simplePredicate.set_start("SCREEN_TURNED_ON");
- simplePredicate.set_stop("SCREEN_TURNED_OFF");
+ simplePredicate.set_start(StringToId("SCREEN_TURNED_ON"));
+ simplePredicate.set_stop(StringToId("SCREEN_TURNED_OFF"));
simplePredicate.set_count_nesting(true);
- unordered_map<string, int> trackerNameIndexMap;
- trackerNameIndexMap["SCREEN_TURNED_ON"] = 0;
- trackerNameIndexMap["SCREEN_TURNED_OFF"] = 1;
+ unordered_map<int64_t, int> trackerNameIndexMap;
+ trackerNameIndexMap[StringToId("SCREEN_TURNED_ON")] = 0;
+ trackerNameIndexMap[StringToId("SCREEN_TURNED_OFF")] = 1;
- SimpleConditionTracker conditionTracker(kConfigKey, "SCREEN_IS_ON",
+ SimpleConditionTracker conditionTracker(kConfigKey, StringToId("SCREEN_IS_ON"),
0 /*condition tracker index*/, simplePredicate,
trackerNameIndexMap);
@@ -267,12 +270,12 @@
position);
string conditionName = "WL_HELD_BY_UID2";
- unordered_map<string, int> trackerNameIndexMap;
- trackerNameIndexMap["WAKE_LOCK_ACQUIRE"] = 0;
- trackerNameIndexMap["WAKE_LOCK_RELEASE"] = 1;
- trackerNameIndexMap["RELEASE_ALL"] = 2;
+ unordered_map<int64_t, int> trackerNameIndexMap;
+ trackerNameIndexMap[StringToId("WAKE_LOCK_ACQUIRE")] = 0;
+ trackerNameIndexMap[StringToId("WAKE_LOCK_RELEASE")] = 1;
+ trackerNameIndexMap[StringToId("RELEASE_ALL")] = 2;
- SimpleConditionTracker conditionTracker(kConfigKey, conditionName,
+ SimpleConditionTracker conditionTracker(kConfigKey, StringToId(conditionName),
0 /*condition tracker index*/, simplePredicate,
trackerNameIndexMap);
std::vector<int> uids = {111, 222, 333};
@@ -371,12 +374,12 @@
Position::ANY /* position */);
string conditionName = "WL_HELD";
- unordered_map<string, int> trackerNameIndexMap;
- trackerNameIndexMap["WAKE_LOCK_ACQUIRE"] = 0;
- trackerNameIndexMap["WAKE_LOCK_RELEASE"] = 1;
- trackerNameIndexMap["RELEASE_ALL"] = 2;
+ unordered_map<int64_t, int> trackerNameIndexMap;
+ trackerNameIndexMap[StringToId("WAKE_LOCK_ACQUIRE")] = 0;
+ trackerNameIndexMap[StringToId("WAKE_LOCK_RELEASE")] = 1;
+ trackerNameIndexMap[StringToId("RELEASE_ALL")] = 2;
- SimpleConditionTracker conditionTracker(kConfigKey, conditionName,
+ SimpleConditionTracker conditionTracker(kConfigKey, StringToId(conditionName),
0 /*condition tracker index*/, simplePredicate,
trackerNameIndexMap);
@@ -461,12 +464,12 @@
position);
string conditionName = "WL_HELD_BY_UID3";
- unordered_map<string, int> trackerNameIndexMap;
- trackerNameIndexMap["WAKE_LOCK_ACQUIRE"] = 0;
- trackerNameIndexMap["WAKE_LOCK_RELEASE"] = 1;
- trackerNameIndexMap["RELEASE_ALL"] = 2;
+ unordered_map<int64_t, int> trackerNameIndexMap;
+ trackerNameIndexMap[StringToId("WAKE_LOCK_ACQUIRE")] = 0;
+ trackerNameIndexMap[StringToId("WAKE_LOCK_RELEASE")] = 1;
+ trackerNameIndexMap[StringToId("RELEASE_ALL")] = 2;
- SimpleConditionTracker conditionTracker(kConfigKey, conditionName,
+ SimpleConditionTracker conditionTracker(kConfigKey, StringToId(conditionName),
0 /*condition tracker index*/, simplePredicate,
trackerNameIndexMap);
diff --git a/cmds/statsd/tests/e2e/MetricConditionLink_e2e_test.cpp b/cmds/statsd/tests/e2e/MetricConditionLink_e2e_test.cpp
index c747016..b56b817 100644
--- a/cmds/statsd/tests/e2e/MetricConditionLink_e2e_test.cpp
+++ b/cmds/statsd/tests/e2e/MetricConditionLink_e2e_test.cpp
@@ -55,16 +55,16 @@
*config.add_predicate() = isInBackgroundPredicate;
auto combinationPredicate = config.add_predicate();
- combinationPredicate->set_name("combinationPredicate");
+ combinationPredicate->set_id(StringToId("combinationPredicate"));
combinationPredicate->mutable_combination()->set_operation(LogicalOperation::AND);
addPredicateToPredicateCombination(screenIsOffPredicate, combinationPredicate);
addPredicateToPredicateCombination(isSyncingPredicate, combinationPredicate);
addPredicateToPredicateCombination(isInBackgroundPredicate, combinationPredicate);
auto countMetric = config.add_count_metric();
- countMetric->set_name("AppCrashes");
- countMetric->set_what(appCrashMatcher.name());
- countMetric->set_condition(combinationPredicate->name());
+ countMetric->set_id(StringToId("AppCrashes"));
+ countMetric->set_what(appCrashMatcher.id());
+ countMetric->set_condition(combinationPredicate->id());
// The metric is dimensioning by uid only.
*countMetric->mutable_dimensions() =
CreateDimensions(android::util::PROCESS_LIFE_CYCLE_STATE_CHANGED, {1});
@@ -72,7 +72,7 @@
// Links between crash atom and condition of app is in syncing.
auto links = countMetric->add_links();
- links->set_condition(isSyncingPredicate.name());
+ links->set_condition(isSyncingPredicate.id());
auto dimensionWhat = links->mutable_dimensions_in_what();
dimensionWhat->set_field(android::util::PROCESS_LIFE_CYCLE_STATE_CHANGED);
dimensionWhat->add_child()->set_field(1); // uid field.
@@ -82,7 +82,7 @@
// Links between crash atom and condition of app is in background.
links = countMetric->add_links();
- links->set_condition(isInBackgroundPredicate.name());
+ links->set_condition(isInBackgroundPredicate.id());
dimensionWhat = links->mutable_dimensions_in_what();
dimensionWhat->set_field(android::util::PROCESS_LIFE_CYCLE_STATE_CHANGED);
dimensionWhat->add_child()->set_field(1); // uid field.
diff --git a/cmds/statsd/tests/e2e/WakelockDuration_e2e_test.cpp b/cmds/statsd/tests/e2e/WakelockDuration_e2e_test.cpp
index 8d7b2d5..ecdb002 100644
--- a/cmds/statsd/tests/e2e/WakelockDuration_e2e_test.cpp
+++ b/cmds/statsd/tests/e2e/WakelockDuration_e2e_test.cpp
@@ -43,9 +43,9 @@
*config.add_predicate() = holdingWakelockPredicate;
auto durationMetric = config.add_duration_metric();
- durationMetric->set_name("WakelockDuration");
- durationMetric->set_what(holdingWakelockPredicate.name());
- durationMetric->set_condition(screenIsOffPredicate.name());
+ durationMetric->set_id(StringToId("WakelockDuration"));
+ durationMetric->set_what(holdingWakelockPredicate.id());
+ durationMetric->set_condition(screenIsOffPredicate.id());
durationMetric->set_aggregation_type(aggregationType);
// The metric is dimensioning by first attribution node and only by uid.
*durationMetric->mutable_dimensions() =
diff --git a/cmds/statsd/tests/guardrail/StatsdStats_test.cpp b/cmds/statsd/tests/guardrail/StatsdStats_test.cpp
index 7658044..a134300 100644
--- a/cmds/statsd/tests/guardrail/StatsdStats_test.cpp
+++ b/cmds/statsd/tests/guardrail/StatsdStats_test.cpp
@@ -14,6 +14,7 @@
#include "src/guardrail/StatsdStats.h"
#include "statslog.h"
+#include "tests/statsd_test_util.h"
#include <gtest/gtest.h>
#include <vector>
@@ -28,8 +29,7 @@
TEST(StatsdStatsTest, TestValidConfigAdd) {
StatsdStats stats;
- string name = "StatsdTest";
- ConfigKey key(0, name);
+ ConfigKey key(0, 12345);
const int metricsCount = 10;
const int conditionsCount = 20;
const int matchersCount = 30;
@@ -45,7 +45,7 @@
EXPECT_EQ(1, report.config_stats_size());
const auto& configReport = report.config_stats(0);
EXPECT_EQ(0, configReport.uid());
- EXPECT_EQ(name, configReport.name());
+ EXPECT_EQ(12345, configReport.id());
EXPECT_EQ(metricsCount, configReport.metric_count());
EXPECT_EQ(conditionsCount, configReport.condition_count());
EXPECT_EQ(matchersCount, configReport.matcher_count());
@@ -56,8 +56,7 @@
TEST(StatsdStatsTest, TestInvalidConfigAdd) {
StatsdStats stats;
- string name = "StatsdTest";
- ConfigKey key(0, name);
+ ConfigKey key(0, 12345);
const int metricsCount = 10;
const int conditionsCount = 20;
const int matchersCount = 30;
@@ -78,8 +77,7 @@
TEST(StatsdStatsTest, TestConfigRemove) {
StatsdStats stats;
- string name = "StatsdTest";
- ConfigKey key(0, name);
+ ConfigKey key(0, 12345);
const int metricsCount = 10;
const int conditionsCount = 20;
const int matchersCount = 30;
@@ -105,22 +103,22 @@
TEST(StatsdStatsTest, TestSubStats) {
StatsdStats stats;
- ConfigKey key(0, "test");
+ ConfigKey key(0, 12345);
stats.noteConfigReceived(key, 2, 3, 4, 5, true);
- stats.noteMatcherMatched(key, "matcher1");
- stats.noteMatcherMatched(key, "matcher1");
- stats.noteMatcherMatched(key, "matcher2");
+ stats.noteMatcherMatched(key, StringToId("matcher1"));
+ stats.noteMatcherMatched(key, StringToId("matcher1"));
+ stats.noteMatcherMatched(key, StringToId("matcher2"));
- stats.noteConditionDimensionSize(key, "condition1", 250);
- stats.noteConditionDimensionSize(key, "condition1", 240);
+ stats.noteConditionDimensionSize(key, StringToId("condition1"), 250);
+ stats.noteConditionDimensionSize(key, StringToId("condition1"), 240);
- stats.noteMetricDimensionSize(key, "metric1", 201);
- stats.noteMetricDimensionSize(key, "metric1", 202);
+ stats.noteMetricDimensionSize(key, StringToId("metric1"), 201);
+ stats.noteMetricDimensionSize(key, StringToId("metric1"), 202);
- stats.noteAnomalyDeclared(key, "alert1");
- stats.noteAnomalyDeclared(key, "alert1");
- stats.noteAnomalyDeclared(key, "alert2");
+ stats.noteAnomalyDeclared(key, StringToId("alert1"));
+ stats.noteAnomalyDeclared(key, StringToId("alert1"));
+ stats.noteAnomalyDeclared(key, StringToId("alert2"));
// broadcast-> 2
stats.noteBroadcastSent(key);
@@ -147,39 +145,39 @@
EXPECT_EQ(2, configReport.matcher_stats_size());
// matcher1 is the first in the list
- if (!configReport.matcher_stats(0).name().compare("matcher1")) {
+ if (configReport.matcher_stats(0).id() == StringToId("matcher1")) {
EXPECT_EQ(2, configReport.matcher_stats(0).matched_times());
EXPECT_EQ(1, configReport.matcher_stats(1).matched_times());
- EXPECT_EQ("matcher2", configReport.matcher_stats(1).name());
+ EXPECT_EQ(StringToId("matcher2"), configReport.matcher_stats(1).id());
} else {
// matcher1 is the second in the list.
EXPECT_EQ(1, configReport.matcher_stats(0).matched_times());
- EXPECT_EQ("matcher2", configReport.matcher_stats(0).name());
+ EXPECT_EQ(StringToId("matcher2"), configReport.matcher_stats(0).id());
EXPECT_EQ(2, configReport.matcher_stats(1).matched_times());
- EXPECT_EQ("matcher1", configReport.matcher_stats(1).name());
+ EXPECT_EQ(StringToId("matcher1"), configReport.matcher_stats(1).id());
}
EXPECT_EQ(2, configReport.alert_stats_size());
- bool alert1first = !configReport.alert_stats(0).name().compare("alert1");
- EXPECT_EQ("alert1", configReport.alert_stats(alert1first ? 0 : 1).name());
+ bool alert1first = configReport.alert_stats(0).id() == StringToId("alert1");
+ EXPECT_EQ(StringToId("alert1"), configReport.alert_stats(alert1first ? 0 : 1).id());
EXPECT_EQ(2, configReport.alert_stats(alert1first ? 0 : 1).alerted_times());
- EXPECT_EQ("alert2", configReport.alert_stats(alert1first ? 1 : 0).name());
+ EXPECT_EQ(StringToId("alert2"), configReport.alert_stats(alert1first ? 1 : 0).id());
EXPECT_EQ(1, configReport.alert_stats(alert1first ? 1 : 0).alerted_times());
EXPECT_EQ(1, configReport.condition_stats_size());
- EXPECT_EQ("condition1", configReport.condition_stats(0).name());
+ EXPECT_EQ(StringToId("condition1"), configReport.condition_stats(0).id());
EXPECT_EQ(250, configReport.condition_stats(0).max_tuple_counts());
EXPECT_EQ(1, configReport.metric_stats_size());
- EXPECT_EQ("metric1", configReport.metric_stats(0).name());
+ EXPECT_EQ(StringToId("metric1"), configReport.metric_stats(0).id());
EXPECT_EQ(202, configReport.metric_stats(0).max_tuple_counts());
// after resetting the stats, some new events come
- stats.noteMatcherMatched(key, "matcher99");
- stats.noteConditionDimensionSize(key, "condition99", 300);
- stats.noteMetricDimensionSize(key, "metric99", 270);
- stats.noteAnomalyDeclared(key, "alert99");
+ stats.noteMatcherMatched(key, StringToId("matcher99"));
+ stats.noteConditionDimensionSize(key, StringToId("condition99"), 300);
+ stats.noteMetricDimensionSize(key, StringToId("metric99tion99"), 270);
+ stats.noteAnomalyDeclared(key, StringToId("alert99"));
// now the config stats should only contain the stats about the new event.
stats.dumpStats(&output, false);
@@ -188,19 +186,19 @@
EXPECT_EQ(1, report.config_stats_size());
const auto& configReport2 = report.config_stats(0);
EXPECT_EQ(1, configReport2.matcher_stats_size());
- EXPECT_EQ("matcher99", configReport2.matcher_stats(0).name());
+ EXPECT_EQ(StringToId("matcher99"), configReport2.matcher_stats(0).id());
EXPECT_EQ(1, configReport2.matcher_stats(0).matched_times());
EXPECT_EQ(1, configReport2.condition_stats_size());
- EXPECT_EQ("condition99", configReport2.condition_stats(0).name());
+ EXPECT_EQ(StringToId("condition99"), configReport2.condition_stats(0).id());
EXPECT_EQ(300, configReport2.condition_stats(0).max_tuple_counts());
EXPECT_EQ(1, configReport2.metric_stats_size());
- EXPECT_EQ("metric99", configReport2.metric_stats(0).name());
+ EXPECT_EQ(StringToId("metric99tion99"), configReport2.metric_stats(0).id());
EXPECT_EQ(270, configReport2.metric_stats(0).max_tuple_counts());
EXPECT_EQ(1, configReport2.alert_stats_size());
- EXPECT_EQ("alert99", configReport2.alert_stats(0).name());
+ EXPECT_EQ(StringToId("alert99"), configReport2.alert_stats(0).id());
EXPECT_EQ(1, configReport2.alert_stats(0).alerted_times());
}
@@ -260,7 +258,7 @@
for (int i = 0; i < StatsdStats::kMaxTimestampCount; i++) {
timestamps.push_back(i);
}
- ConfigKey key(0, "test");
+ ConfigKey key(0, 12345);
stats.noteConfigReceived(key, 2, 3, 4, 5, true);
for (int i = 0; i < StatsdStats::kMaxTimestampCount; i++) {
diff --git a/cmds/statsd/tests/metrics/CountMetricProducer_test.cpp b/cmds/statsd/tests/metrics/CountMetricProducer_test.cpp
index 6e114a6..4c2d472 100644
--- a/cmds/statsd/tests/metrics/CountMetricProducer_test.cpp
+++ b/cmds/statsd/tests/metrics/CountMetricProducer_test.cpp
@@ -15,6 +15,7 @@
#include "src/metrics/CountMetricProducer.h"
#include "src/dimension.h"
#include "metrics_test_helper.h"
+#include "tests/statsd_test_util.h"
#include <gmock/gmock.h>
#include <gtest/gtest.h>
@@ -33,7 +34,7 @@
namespace os {
namespace statsd {
-const ConfigKey kConfigKey(0, "test");
+const ConfigKey kConfigKey(0, 12345);
TEST(CountMetricProducerTest, TestNonDimensionalEvents) {
int64_t bucketStartTimeNs = 10000000000;
@@ -43,7 +44,7 @@
int tagId = 1;
CountMetric metric;
- metric.set_name("1");
+ metric.set_id(1);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
LogEvent event1(tagId, bucketStartTimeNs + 1);
@@ -100,9 +101,9 @@
int64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
CountMetric metric;
- metric.set_name("1");
+ metric.set_id(1);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
- metric.set_condition("SCREEN_ON");
+ metric.set_condition(StringToId("SCREEN_ON"));
LogEvent event1(1, bucketStartTimeNs + 1);
LogEvent event2(1, bucketStartTimeNs + 10);
@@ -142,11 +143,11 @@
int conditionTagId = 2;
CountMetric metric;
- metric.set_name("1");
+ metric.set_id(1);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
- metric.set_condition("APP_IN_BACKGROUND_PER_UID_AND_SCREEN_ON");
+ metric.set_condition(StringToId("APP_IN_BACKGROUND_PER_UID_AND_SCREEN_ON"));
MetricConditionLink* link = metric.add_links();
- link->set_condition("APP_IN_BACKGROUND_PER_UID");
+ link->set_condition(StringToId("APP_IN_BACKGROUND_PER_UID"));
*link->mutable_dimensions_in_what() = buildSimpleAtomFieldMatcher(tagId, 1);
*link->mutable_dimensions_in_condition() = buildSimpleAtomFieldMatcher(conditionTagId, 2);
@@ -154,13 +155,15 @@
event1.write("111"); // uid
event1.init();
ConditionKey key1;
- key1["APP_IN_BACKGROUND_PER_UID"] = {getMockedDimensionKey(conditionTagId, 2, "111")};
+ key1[StringToId("APP_IN_BACKGROUND_PER_UID")] =
+ {getMockedDimensionKey(conditionTagId, 2, "111")};
LogEvent event2(tagId, bucketStartTimeNs + 10);
event2.write("222"); // uid
event2.init();
ConditionKey key2;
- key2["APP_IN_BACKGROUND_PER_UID"] = {getMockedDimensionKey(conditionTagId, 2, "222")};
+ key2[StringToId("APP_IN_BACKGROUND_PER_UID")] =
+ {getMockedDimensionKey(conditionTagId, 2, "222")};
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
EXPECT_CALL(*wizard, query(_, key1)).WillOnce(Return(ConditionState::kFalse));
@@ -189,8 +192,8 @@
TEST(CountMetricProducerTest, TestAnomalyDetection) {
Alert alert;
- alert.set_name("alert");
- alert.set_metric_name("1");
+ alert.set_id(11);
+ alert.set_metric_id(1);
alert.set_trigger_if_sum_gt(2);
alert.set_number_of_buckets(2);
alert.set_refractory_period_secs(1);
@@ -201,7 +204,7 @@
int64_t bucket3StartTimeNs = bucketStartTimeNs + 2 * bucketSizeNs;
CountMetric metric;
- metric.set_name("1");
+ metric.set_id(1);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
diff --git a/cmds/statsd/tests/metrics/DurationMetricProducer_test.cpp b/cmds/statsd/tests/metrics/DurationMetricProducer_test.cpp
index 8ee94c7..a4213de 100644
--- a/cmds/statsd/tests/metrics/DurationMetricProducer_test.cpp
+++ b/cmds/statsd/tests/metrics/DurationMetricProducer_test.cpp
@@ -36,7 +36,7 @@
namespace os {
namespace statsd {
-const ConfigKey kConfigKey(0, "test");
+const ConfigKey kConfigKey(0, 12345);
TEST(DurationMetricTrackerTest, TestNoCondition) {
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
@@ -44,7 +44,7 @@
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
DurationMetric metric;
- metric.set_name("1");
+ metric.set_id(1);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
metric.set_aggregation_type(DurationMetric_AggregationType_SUM);
@@ -79,7 +79,7 @@
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
DurationMetric metric;
- metric.set_name("1");
+ metric.set_id(1);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
metric.set_aggregation_type(DurationMetric_AggregationType_SUM);
diff --git a/cmds/statsd/tests/metrics/EventMetricProducer_test.cpp b/cmds/statsd/tests/metrics/EventMetricProducer_test.cpp
index 0ba1c2f..7171de9 100644
--- a/cmds/statsd/tests/metrics/EventMetricProducer_test.cpp
+++ b/cmds/statsd/tests/metrics/EventMetricProducer_test.cpp
@@ -15,6 +15,7 @@
#include "src/metrics/EventMetricProducer.h"
#include "src/dimension.h"
#include "metrics_test_helper.h"
+#include "tests/statsd_test_util.h"
#include <gmock/gmock.h>
#include <gtest/gtest.h>
@@ -33,7 +34,7 @@
namespace os {
namespace statsd {
-const ConfigKey kConfigKey(0, "test");
+const ConfigKey kConfigKey(0, 12345);
TEST(EventMetricProducerTest, TestNoCondition) {
uint64_t bucketStartTimeNs = 10000000000;
@@ -41,7 +42,7 @@
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
EventMetric metric;
- metric.set_name("1");
+ metric.set_id(1);
LogEvent event1(1 /*tag id*/, bucketStartTimeNs + 1);
LogEvent event2(1 /*tag id*/, bucketStartTimeNs + 2);
@@ -64,8 +65,8 @@
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
EventMetric metric;
- metric.set_name("1");
- metric.set_condition("SCREEN_ON");
+ metric.set_id(1);
+ metric.set_condition(StringToId("SCREEN_ON"));
LogEvent event1(1, bucketStartTimeNs + 1);
LogEvent event2(1, bucketStartTimeNs + 10);
@@ -93,10 +94,10 @@
int conditionTagId = 2;
EventMetric metric;
- metric.set_name("1");
- metric.set_condition("APP_IN_BACKGROUND_PER_UID_AND_SCREEN_ON");
+ metric.set_id(1);
+ metric.set_condition(StringToId("APP_IN_BACKGROUND_PER_UID_AND_SCREEN_ON"));
MetricConditionLink* link = metric.add_links();
- link->set_condition("APP_IN_BACKGROUND_PER_UID");
+ link->set_condition(StringToId("APP_IN_BACKGROUND_PER_UID"));
*link->mutable_dimensions_in_what() = buildSimpleAtomFieldMatcher(tagId, 1);
*link->mutable_dimensions_in_condition() = buildSimpleAtomFieldMatcher(conditionTagId, 2);
@@ -104,13 +105,13 @@
EXPECT_TRUE(event1.write("111"));
event1.init();
ConditionKey key1;
- key1["APP_IN_BACKGROUND_PER_UID"] = {getMockedDimensionKey(conditionTagId, 2, "111")};
+ key1[StringToId("APP_IN_BACKGROUND_PER_UID")] = {getMockedDimensionKey(conditionTagId, 2, "111")};
LogEvent event2(tagId, bucketStartTimeNs + 10);
EXPECT_TRUE(event2.write("222"));
event2.init();
ConditionKey key2;
- key2["APP_IN_BACKGROUND_PER_UID"] = {getMockedDimensionKey(conditionTagId, 2, "222")};
+ key2[StringToId("APP_IN_BACKGROUND_PER_UID")] = {getMockedDimensionKey(conditionTagId, 2, "222")};
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
EXPECT_CALL(*wizard, query(_, key1)).WillOnce(Return(ConditionState::kFalse));
diff --git a/cmds/statsd/tests/metrics/GaugeMetricProducer_test.cpp b/cmds/statsd/tests/metrics/GaugeMetricProducer_test.cpp
index 359851f..cde50c1 100644
--- a/cmds/statsd/tests/metrics/GaugeMetricProducer_test.cpp
+++ b/cmds/statsd/tests/metrics/GaugeMetricProducer_test.cpp
@@ -15,6 +15,7 @@
#include "src/metrics/GaugeMetricProducer.h"
#include "logd/LogEvent.h"
#include "metrics_test_helper.h"
+#include "tests/statsd_test_util.h"
#include <gmock/gmock.h>
#include <gtest/gtest.h>
@@ -34,9 +35,9 @@
namespace os {
namespace statsd {
-const ConfigKey kConfigKey(0, "test");
+const ConfigKey kConfigKey(0, 12345);
const int tagId = 1;
-const string metricName = "test_metric";
+const int64_t metricId = 123;
const int64_t bucketStartTimeNs = 10000000000;
const int64_t bucketSizeNs = 60 * 1000 * 1000 * 1000LL;
const int64_t bucket2StartTimeNs = bucketStartTimeNs + bucketSizeNs;
@@ -45,7 +46,7 @@
TEST(GaugeMetricProducerTest, TestNoCondition) {
GaugeMetric metric;
- metric.set_name(metricName);
+ metric.set_id(metricId);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
metric.mutable_gauge_fields_filter()->set_include_all(false);
auto gaugeFieldMatcher = metric.mutable_gauge_fields_filter()->mutable_fields();
@@ -119,12 +120,12 @@
TEST(GaugeMetricProducerTest, TestWithCondition) {
GaugeMetric metric;
- metric.set_name(metricName);
+ metric.set_id(metricId);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
auto gaugeFieldMatcher = metric.mutable_gauge_fields_filter()->mutable_fields();
gaugeFieldMatcher->set_field(tagId);
gaugeFieldMatcher->add_child()->set_field(2);
- metric.set_condition("SCREEN_ON");
+ metric.set_condition(StringToId("SCREEN_ON"));
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
@@ -186,7 +187,7 @@
EXPECT_CALL(*pullerManager, UnRegisterReceiver(tagId, _)).WillOnce(Return());
GaugeMetric metric;
- metric.set_name(metricName);
+ metric.set_id(metricId);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
auto gaugeFieldMatcher = metric.mutable_gauge_fields_filter()->mutable_fields();
gaugeFieldMatcher->set_field(tagId);
@@ -195,8 +196,8 @@
tagId, tagId, bucketStartTimeNs, pullerManager);
Alert alert;
- alert.set_name("alert");
- alert.set_metric_name(metricName);
+ alert.set_id(101);
+ alert.set_metric_id(metricId);
alert.set_trigger_if_sum_gt(25);
alert.set_number_of_buckets(2);
sp<AnomalyTracker> anomalyTracker = gaugeProducer.addAnomalyTracker(alert);
diff --git a/cmds/statsd/tests/metrics/MaxDurationTracker_test.cpp b/cmds/statsd/tests/metrics/MaxDurationTracker_test.cpp
index 7843ca0..6d32329 100644
--- a/cmds/statsd/tests/metrics/MaxDurationTracker_test.cpp
+++ b/cmds/statsd/tests/metrics/MaxDurationTracker_test.cpp
@@ -13,8 +13,9 @@
// limitations under the License.
#include "src/metrics/duration_helper/MaxDurationTracker.h"
-#include "metrics_test_helper.h"
#include "src/condition/ConditionWizard.h"
+#include "metrics_test_helper.h"
+#include "tests/statsd_test_util.h"
#include <gmock/gmock.h>
#include <gtest/gtest.h>
@@ -36,7 +37,7 @@
namespace os {
namespace statsd {
-const ConfigKey kConfigKey(0, "test");
+const ConfigKey kConfigKey(0, 12345);
const int TagId = 1;
@@ -50,12 +51,13 @@
unordered_map<HashableDimensionKey, vector<DurationBucket>> buckets;
ConditionKey conditionKey1;
- conditionKey1["condition"] = conditionKey;
+ conditionKey1[StringToId("condition")] = conditionKey;
uint64_t bucketStartTimeNs = 10000000000;
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
- MaxDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, -1, false, bucketStartTimeNs,
+ int64_t metricId = 1;
+ MaxDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, -1, false, bucketStartTimeNs,
bucketSizeNs, {});
tracker.noteStart(key1, true, bucketStartTimeNs, conditionKey1);
@@ -79,12 +81,13 @@
unordered_map<HashableDimensionKey, vector<DurationBucket>> buckets;
ConditionKey conditionKey1;
- conditionKey1["condition"] = conditionKey;
+ conditionKey1[StringToId("condition")] = conditionKey;
uint64_t bucketStartTimeNs = 10000000000;
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
- MaxDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, -1, false, bucketStartTimeNs,
+ int64_t metricId = 1;
+ MaxDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, -1, false, bucketStartTimeNs,
bucketSizeNs, {});
tracker.noteStart(key1, true, bucketStartTimeNs + 1, conditionKey1);
@@ -110,12 +113,13 @@
unordered_map<HashableDimensionKey, vector<DurationBucket>> buckets;
ConditionKey conditionKey1;
- conditionKey1["condition"] = conditionKey;
+ conditionKey1[StringToId("condition")] = conditionKey;
uint64_t bucketStartTimeNs = 10000000000;
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
- MaxDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, -1, false, bucketStartTimeNs,
+ int64_t metricId = 1;
+ MaxDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, -1, false, bucketStartTimeNs,
bucketSizeNs, {});
// The event starts.
@@ -141,12 +145,13 @@
unordered_map<HashableDimensionKey, vector<DurationBucket>> buckets;
ConditionKey conditionKey1;
- conditionKey1["condition"] = conditionKey;
+ conditionKey1[StringToId("condition")] = conditionKey;
uint64_t bucketStartTimeNs = 10000000000;
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
- MaxDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, -1, true, bucketStartTimeNs,
+ int64_t metricId = 1;
+ MaxDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, -1, true, bucketStartTimeNs,
bucketSizeNs, {});
// 2 starts
@@ -177,7 +182,7 @@
ConditionKey conditionKey1;
HashableDimensionKey eventKey = getMockedDimensionKey(TagId, 2, "maps");
- conditionKey1["APP_BACKGROUND"] = conditionKey;
+ conditionKey1[StringToId("APP_BACKGROUND")] = conditionKey;
EXPECT_CALL(*wizard, query(_, conditionKey1)) // #4
.WillOnce(Return(ConditionState::kFalse));
@@ -189,7 +194,8 @@
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
int64_t durationTimeNs = 2 * 1000;
- MaxDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, 1, false, bucketStartTimeNs,
+ int64_t metricId = 1;
+ MaxDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, 1, false, bucketStartTimeNs,
bucketSizeNs, {});
EXPECT_TRUE(tracker.mAnomalyTrackers.empty());
@@ -206,9 +212,10 @@
}
TEST(MaxDurationTrackerTest, TestAnomalyDetection) {
+ int64_t metricId = 1;
Alert alert;
- alert.set_name("alert");
- alert.set_metric_name("metric");
+ alert.set_id(101);
+ alert.set_metric_id(metricId);
alert.set_trigger_if_sum_gt(32 * NS_PER_SEC);
alert.set_number_of_buckets(2);
alert.set_refractory_period_secs(1);
@@ -216,13 +223,13 @@
unordered_map<HashableDimensionKey, vector<DurationBucket>> buckets;
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
ConditionKey conditionKey1;
- conditionKey1["APP_BACKGROUND"] = conditionKey;
+ conditionKey1[StringToId("APP_BACKGROUND")] = conditionKey;
uint64_t bucketStartTimeNs = 10 * NS_PER_SEC;
uint64_t eventStartTimeNs = bucketStartTimeNs + NS_PER_SEC + 1;
uint64_t bucketSizeNs = 30 * NS_PER_SEC;
sp<DurationAnomalyTracker> anomalyTracker = new DurationAnomalyTracker(alert, kConfigKey);
- MaxDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, -1, true, bucketStartTimeNs,
+ MaxDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, -1, true, bucketStartTimeNs,
bucketSizeNs, {anomalyTracker});
tracker.noteStart(key1, true, eventStartTimeNs, conditionKey1);
diff --git a/cmds/statsd/tests/metrics/OringDurationTracker_test.cpp b/cmds/statsd/tests/metrics/OringDurationTracker_test.cpp
index 550b059..d34c85b 100644
--- a/cmds/statsd/tests/metrics/OringDurationTracker_test.cpp
+++ b/cmds/statsd/tests/metrics/OringDurationTracker_test.cpp
@@ -13,8 +13,9 @@
// limitations under the License.
#include "src/metrics/duration_helper/OringDurationTracker.h"
-#include "metrics_test_helper.h"
#include "src/condition/ConditionWizard.h"
+#include "metrics_test_helper.h"
+#include "tests/statsd_test_util.h"
#include <gmock/gmock.h>
#include <gtest/gtest.h>
@@ -34,8 +35,9 @@
namespace os {
namespace statsd {
-const ConfigKey kConfigKey(0, "test");
+const ConfigKey kConfigKey(0, 12345);
const int TagId = 1;
+const int64_t metricId = 123;
const HashableDimensionKey eventKey = getMockedDimensionKey(TagId, 0, "event");
const std::vector<HashableDimensionKey> kConditionKey1 = {getMockedDimensionKey(TagId, 1, "maps")};
@@ -46,7 +48,7 @@
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
ConditionKey key1;
- key1["APP_BACKGROUND"] = kConditionKey1;
+ key1[StringToId("APP_BACKGROUND")] = kConditionKey1;
unordered_map<HashableDimensionKey, vector<DurationBucket>> buckets;
@@ -55,7 +57,7 @@
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
uint64_t durationTimeNs = 2 * 1000;
- OringDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, 1, false,
+ OringDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, 1, false,
bucketStartTimeNs, bucketSizeNs, {});
tracker.noteStart(kEventKey1, true, eventStartTimeNs, key1);
@@ -75,7 +77,7 @@
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
ConditionKey key1;
- key1["APP_BACKGROUND"] = kConditionKey1;
+ key1[StringToId("APP_BACKGROUND")] = kConditionKey1;
unordered_map<HashableDimensionKey, vector<DurationBucket>> buckets;
@@ -83,7 +85,7 @@
uint64_t eventStartTimeNs = bucketStartTimeNs + 1;
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
- OringDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, 1, true, bucketStartTimeNs,
+ OringDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, 1, true, bucketStartTimeNs,
bucketSizeNs, {});
tracker.noteStart(kEventKey1, true, eventStartTimeNs, key1);
@@ -102,7 +104,7 @@
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
ConditionKey key1;
- key1["APP_BACKGROUND"] = kConditionKey1;
+ key1[StringToId("APP_BACKGROUND")] = kConditionKey1;
unordered_map<HashableDimensionKey, vector<DurationBucket>> buckets;
@@ -110,7 +112,7 @@
uint64_t eventStartTimeNs = bucketStartTimeNs + 1;
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
- OringDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, 1, true, bucketStartTimeNs,
+ OringDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, 1, true, bucketStartTimeNs,
bucketSizeNs, {});
tracker.noteStart(kEventKey1, true, eventStartTimeNs, key1);
@@ -128,7 +130,7 @@
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
ConditionKey key1;
- key1["APP_BACKGROUND"] = kConditionKey1;
+ key1[StringToId("APP_BACKGROUND")] = kConditionKey1;
unordered_map<HashableDimensionKey, vector<DurationBucket>> buckets;
@@ -137,7 +139,7 @@
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
uint64_t durationTimeNs = 2 * 1000;
- OringDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, 1, true, bucketStartTimeNs,
+ OringDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, 1, true, bucketStartTimeNs,
bucketSizeNs, {});
tracker.noteStart(kEventKey1, true, eventStartTimeNs, key1);
@@ -163,7 +165,7 @@
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
ConditionKey key1;
- key1["APP_BACKGROUND"] = kConditionKey1;
+ key1[StringToId("APP_BACKGROUND")] = kConditionKey1;
EXPECT_CALL(*wizard, query(_, key1)) // #4
.WillOnce(Return(ConditionState::kFalse));
@@ -175,7 +177,7 @@
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
uint64_t durationTimeNs = 2 * 1000;
- OringDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, 1, false,
+ OringDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, 1, false,
bucketStartTimeNs, bucketSizeNs, {});
tracker.noteStart(kEventKey1, true, eventStartTimeNs, key1);
@@ -194,7 +196,7 @@
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
ConditionKey key1;
- key1["APP_BACKGROUND"] = kConditionKey1;
+ key1[StringToId("APP_BACKGROUND")] = kConditionKey1;
EXPECT_CALL(*wizard, query(_, key1))
.Times(2)
@@ -208,7 +210,7 @@
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
uint64_t durationTimeNs = 2 * 1000;
- OringDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, 1, false,
+ OringDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, 1, false,
bucketStartTimeNs, bucketSizeNs, {});
tracker.noteStart(kEventKey1, true, eventStartTimeNs, key1);
@@ -229,7 +231,7 @@
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
ConditionKey key1;
- key1["APP_BACKGROUND"] = kConditionKey1;
+ key1[StringToId("APP_BACKGROUND")] = kConditionKey1;
EXPECT_CALL(*wizard, query(_, key1)) // #4
.WillOnce(Return(ConditionState::kFalse));
@@ -240,7 +242,7 @@
uint64_t eventStartTimeNs = bucketStartTimeNs + 1;
uint64_t bucketSizeNs = 30 * 1000 * 1000 * 1000LL;
- OringDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, 1, true, bucketStartTimeNs,
+ OringDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, 1, true, bucketStartTimeNs,
bucketSizeNs, {});
tracker.noteStart(kEventKey1, true, eventStartTimeNs, key1);
@@ -260,8 +262,8 @@
TEST(OringDurationTrackerTest, TestPredictAnomalyTimestamp) {
Alert alert;
- alert.set_name("alert");
- alert.set_metric_name("1");
+ alert.set_id(101);
+ alert.set_metric_id(1);
alert.set_trigger_if_sum_gt(40 * NS_PER_SEC);
alert.set_number_of_buckets(2);
alert.set_refractory_period_secs(1);
@@ -269,13 +271,13 @@
unordered_map<HashableDimensionKey, vector<DurationBucket>> buckets;
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
ConditionKey key1;
- key1["APP_BACKGROUND"] = kConditionKey1;
+ key1[StringToId("APP_BACKGROUND")] = kConditionKey1;
uint64_t bucketStartTimeNs = 10 * NS_PER_SEC;
uint64_t eventStartTimeNs = bucketStartTimeNs + NS_PER_SEC + 1;
uint64_t bucketSizeNs = 30 * NS_PER_SEC;
sp<DurationAnomalyTracker> anomalyTracker = new DurationAnomalyTracker(alert, kConfigKey);
- OringDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, 1, true, bucketStartTimeNs,
+ OringDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, 1, true, bucketStartTimeNs,
bucketSizeNs, {anomalyTracker});
// Nothing in the past bucket.
@@ -322,8 +324,8 @@
TEST(OringDurationTrackerTest, TestAnomalyDetection) {
Alert alert;
- alert.set_name("alert");
- alert.set_metric_name("1");
+ alert.set_id(101);
+ alert.set_metric_id(1);
alert.set_trigger_if_sum_gt(40 * NS_PER_SEC);
alert.set_number_of_buckets(2);
alert.set_refractory_period_secs(1);
@@ -331,13 +333,13 @@
unordered_map<HashableDimensionKey, vector<DurationBucket>> buckets;
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
ConditionKey key1;
- key1["APP_BACKGROUND"] = kConditionKey1;
+ key1[StringToId("APP_BACKGROUND")] = kConditionKey1;
uint64_t bucketStartTimeNs = 10 * NS_PER_SEC;
uint64_t eventStartTimeNs = bucketStartTimeNs + NS_PER_SEC + 1;
uint64_t bucketSizeNs = 30 * NS_PER_SEC;
sp<DurationAnomalyTracker> anomalyTracker = new DurationAnomalyTracker(alert, kConfigKey);
- OringDurationTracker tracker(kConfigKey, "metric", eventKey, wizard, 1, true /*nesting*/,
+ OringDurationTracker tracker(kConfigKey, metricId, eventKey, wizard, 1, true /*nesting*/,
bucketStartTimeNs, bucketSizeNs, {anomalyTracker});
tracker.noteStart(DEFAULT_DIMENSION_KEY, true, eventStartTimeNs, key1);
diff --git a/cmds/statsd/tests/metrics/ValueMetricProducer_test.cpp b/cmds/statsd/tests/metrics/ValueMetricProducer_test.cpp
index 12bc834..acbfbba 100644
--- a/cmds/statsd/tests/metrics/ValueMetricProducer_test.cpp
+++ b/cmds/statsd/tests/metrics/ValueMetricProducer_test.cpp
@@ -14,6 +14,7 @@
#include "src/metrics/ValueMetricProducer.h"
#include "metrics_test_helper.h"
+#include "tests/statsd_test_util.h"
#include <gmock/gmock.h>
#include <gtest/gtest.h>
@@ -34,9 +35,9 @@
namespace os {
namespace statsd {
-const ConfigKey kConfigKey(0, "test");
+const ConfigKey kConfigKey(0, 12345);
const int tagId = 1;
-const string metricName = "test_metric";
+const int64_t metricId = 123;
const int64_t bucketStartTimeNs = 10000000000;
const int64_t bucketSizeNs = 60 * 1000 * 1000 * 1000LL;
const int64_t bucket2StartTimeNs = bucketStartTimeNs + bucketSizeNs;
@@ -48,7 +49,7 @@
*/
TEST(ValueMetricProducerTest, TestNonDimensionalEvents) {
ValueMetric metric;
- metric.set_name(metricName);
+ metric.set_id(metricId);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
metric.set_value_field(2);
@@ -124,10 +125,10 @@
*/
TEST(ValueMetricProducerTest, TestEventsWithNonSlicedCondition) {
ValueMetric metric;
- metric.set_name(metricName);
+ metric.set_id(metricId);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
metric.set_value_field(2);
- metric.set_condition("SCREEN_ON");
+ metric.set_condition(StringToId("SCREEN_ON"));
sp<MockConditionWizard> wizard = new NaggyMock<MockConditionWizard>();
shared_ptr<MockStatsPullerManager> pullerManager =
@@ -200,7 +201,7 @@
TEST(ValueMetricProducerTest, TestPushedEventsWithoutCondition) {
ValueMetric metric;
- metric.set_name(metricName);
+ metric.set_id(metricId);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
metric.set_value_field(2);
@@ -240,14 +241,14 @@
TEST(ValueMetricProducerTest, TestAnomalyDetection) {
Alert alert;
- alert.set_name("alert");
- alert.set_metric_name(metricName);
+ alert.set_id(101);
+ alert.set_metric_id(metricId);
alert.set_trigger_if_sum_gt(130);
alert.set_number_of_buckets(2);
alert.set_refractory_period_secs(3);
ValueMetric metric;
- metric.set_name(metricName);
+ metric.set_id(metricId);
metric.mutable_bucket()->set_bucket_size_millis(bucketSizeNs / 1000000);
metric.set_value_field(2);
diff --git a/cmds/statsd/tests/statsd_test_util.cpp b/cmds/statsd/tests/statsd_test_util.cpp
index 39e366f..939dc1f 100644
--- a/cmds/statsd/tests/statsd_test_util.cpp
+++ b/cmds/statsd/tests/statsd_test_util.cpp
@@ -22,7 +22,7 @@
AtomMatcher CreateWakelockStateChangedAtomMatcher(const string& name,
WakelockStateChanged::State state) {
AtomMatcher atom_matcher;
- atom_matcher.set_name(name);
+ atom_matcher.set_id(StringToId(name));
auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
simple_atom_matcher->set_atom_id(android::util::WAKELOCK_STATE_CHANGED);
auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
@@ -42,7 +42,7 @@
AtomMatcher CreateScreenStateChangedAtomMatcher(
const string& name, ScreenStateChanged::State state) {
AtomMatcher atom_matcher;
- atom_matcher.set_name(name);
+ atom_matcher.set_id(StringToId(name));
auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
simple_atom_matcher->set_atom_id(android::util::SCREEN_STATE_CHANGED);
auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
@@ -62,7 +62,7 @@
AtomMatcher CreateSyncStateChangedAtomMatcher(
const string& name, SyncStateChanged::State state) {
AtomMatcher atom_matcher;
- atom_matcher.set_name(name);
+ atom_matcher.set_id(StringToId(name));
auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
simple_atom_matcher->set_atom_id(android::util::SYNC_STATE_CHANGED);
auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
@@ -82,7 +82,7 @@
AtomMatcher CreateActivityForegroundStateChangedAtomMatcher(
const string& name, ActivityForegroundStateChanged::Activity activity) {
AtomMatcher atom_matcher;
- atom_matcher.set_name(name);
+ atom_matcher.set_id(StringToId(name));
auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
simple_atom_matcher->set_atom_id(android::util::ACTIVITY_FOREGROUND_STATE_CHANGED);
auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
@@ -104,7 +104,7 @@
AtomMatcher CreateProcessLifeCycleStateChangedAtomMatcher(
const string& name, ProcessLifeCycleStateChanged::Event event) {
AtomMatcher atom_matcher;
- atom_matcher.set_name(name);
+ atom_matcher.set_id(StringToId(name));
auto simple_atom_matcher = atom_matcher.mutable_simple_atom_matcher();
simple_atom_matcher->set_atom_id(android::util::PROCESS_LIFE_CYCLE_STATE_CHANGED);
auto field_value_matcher = simple_atom_matcher->add_field_value_matcher();
@@ -121,47 +121,47 @@
Predicate CreateScreenIsOnPredicate() {
Predicate predicate;
- predicate.set_name("ScreenIsOn");
- predicate.mutable_simple_predicate()->set_start("ScreenTurnedOn");
- predicate.mutable_simple_predicate()->set_stop("ScreenTurnedOff");
+ predicate.set_id(StringToId("ScreenIsOn"));
+ predicate.mutable_simple_predicate()->set_start(StringToId("ScreenTurnedOn"));
+ predicate.mutable_simple_predicate()->set_stop(StringToId("ScreenTurnedOff"));
return predicate;
}
Predicate CreateScreenIsOffPredicate() {
Predicate predicate;
- predicate.set_name("ScreenIsOff");
- predicate.mutable_simple_predicate()->set_start("ScreenTurnedOff");
- predicate.mutable_simple_predicate()->set_stop("ScreenTurnedOn");
+ predicate.set_id(StringToId("ScreenIsOff"));
+ predicate.mutable_simple_predicate()->set_start(StringToId("ScreenTurnedOff"));
+ predicate.mutable_simple_predicate()->set_stop(StringToId("ScreenTurnedOn"));
return predicate;
}
Predicate CreateHoldingWakelockPredicate() {
Predicate predicate;
- predicate.set_name("HoldingWakelock");
- predicate.mutable_simple_predicate()->set_start("AcquireWakelock");
- predicate.mutable_simple_predicate()->set_stop("ReleaseWakelock");
+ predicate.set_id(StringToId("HoldingWakelock"));
+ predicate.mutable_simple_predicate()->set_start(StringToId("AcquireWakelock"));
+ predicate.mutable_simple_predicate()->set_stop(StringToId("ReleaseWakelock"));
return predicate;
}
Predicate CreateIsSyncingPredicate() {
Predicate predicate;
- predicate.set_name("IsSyncing");
- predicate.mutable_simple_predicate()->set_start("SyncStart");
- predicate.mutable_simple_predicate()->set_stop("SyncEnd");
+ predicate.set_id(StringToId("IsSyncing"));
+ predicate.mutable_simple_predicate()->set_start(StringToId("SyncStart"));
+ predicate.mutable_simple_predicate()->set_stop(StringToId("SyncEnd"));
return predicate;
}
Predicate CreateIsInBackgroundPredicate() {
Predicate predicate;
- predicate.set_name("IsInBackground");
- predicate.mutable_simple_predicate()->set_start("MoveToBackground");
- predicate.mutable_simple_predicate()->set_stop("MoveToForeground");
+ predicate.set_id(StringToId("IsInBackground"));
+ predicate.mutable_simple_predicate()->set_start(StringToId("MoveToBackground"));
+ predicate.mutable_simple_predicate()->set_stop(StringToId("MoveToForeground"));
return predicate;
}
void addPredicateToPredicateCombination(const Predicate& predicate,
Predicate* combinationPredicate) {
- combinationPredicate->mutable_combination()->add_predicate(predicate.name());
+ combinationPredicate->mutable_combination()->add_predicate(predicate.id());
}
FieldMatcher CreateAttributionUidDimensions(const int atomId,
@@ -316,6 +316,9 @@
});
}
+int64_t StringToId(const string& str) {
+ return static_cast<int64_t>(std::hash<std::string>()(str));
+}
} // namespace statsd
} // namespace os
} // namespace android
\ No newline at end of file
diff --git a/cmds/statsd/tests/statsd_test_util.h b/cmds/statsd/tests/statsd_test_util.h
index 282e1b2..5e19da0 100644
--- a/cmds/statsd/tests/statsd_test_util.h
+++ b/cmds/statsd/tests/statsd_test_util.h
@@ -121,6 +121,8 @@
// Util function to sort the log events by timestamp.
void sortLogEventsByTimestamp(std::vector<std::unique_ptr<LogEvent>> *events);
+int64_t StringToId(const string& str);
+
} // namespace statsd
} // namespace os
} // namespace android
\ No newline at end of file
diff --git a/cmds/statsd/tools/dogfood/src/com/android/statsd/dogfood/DisplayProtoUtils.java b/cmds/statsd/tools/dogfood/src/com/android/statsd/dogfood/DisplayProtoUtils.java
index 9294681..93dba71 100644
--- a/cmds/statsd/tools/dogfood/src/com/android/statsd/dogfood/DisplayProtoUtils.java
+++ b/cmds/statsd/tools/dogfood/src/com/android/statsd/dogfood/DisplayProtoUtils.java
@@ -26,7 +26,7 @@
sb.append("ConfigKey: ");
if (reports.hasConfigKey()) {
com.android.os.StatsLog.ConfigMetricsReportList.ConfigKey key = reports.getConfigKey();
- sb.append("\tuid: ").append(key.getUid()).append(" name: ").append(key.getName())
+ sb.append("\tuid: ").append(key.getUid()).append(" name: ").append(key.getId())
.append("\n");
}
@@ -34,7 +34,7 @@
sb.append("StatsLogReport size: ").append(report.getMetricsCount()).append("\n");
for (StatsLog.StatsLogReport log : report.getMetricsList()) {
sb.append("\n\n");
- sb.append("metric id: ").append(log.getMetricName()).append("\n");
+ sb.append("metric id: ").append(log.getMetricId()).append("\n");
sb.append("start time:").append(getDateStr(log.getStartReportNanos())).append("\n");
sb.append("end time:").append(getDateStr(log.getEndReportNanos())).append("\n");
diff --git a/cmds/statsd/tools/dogfood/src/com/android/statsd/dogfood/MainActivity.java b/cmds/statsd/tools/dogfood/src/com/android/statsd/dogfood/MainActivity.java
index 137fd4d..119d6f5 100644
--- a/cmds/statsd/tools/dogfood/src/com/android/statsd/dogfood/MainActivity.java
+++ b/cmds/statsd/tools/dogfood/src/com/android/statsd/dogfood/MainActivity.java
@@ -34,6 +34,8 @@
public class MainActivity extends Activity {
private final static String TAG = "StatsdDogfood";
+ private final static long CONFIG_ID = 987654321;
+
final int[] mUids = {11111111, 2222222};
StatsManager mStatsManager;
@@ -163,7 +165,7 @@
return;
}
if (mStatsManager != null) {
- byte[] data = mStatsManager.getData("fake");
+ byte[] data = mStatsManager.getData(CONFIG_ID);
if (data != null) {
displayData(data);
} else {
@@ -186,7 +188,7 @@
byte[] config = new byte[inputStream.available()];
inputStream.read(config);
if (mStatsManager != null) {
- if (mStatsManager.addConfiguration("fake",
+ if (mStatsManager.addConfiguration(CONFIG_ID,
config, getPackageName(), MainActivity.this.getClass().getName())) {
Toast.makeText(
MainActivity.this, "Config pushed", Toast.LENGTH_LONG).show();
diff --git a/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/ConfigFactory.java b/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/ConfigFactory.java
index f516477..4bd2844 100644
--- a/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/ConfigFactory.java
+++ b/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/ConfigFactory.java
@@ -41,7 +41,7 @@
* Creates StatsdConfig protos for loadtesting.
*/
public class ConfigFactory {
- public static final String CONFIG_NAME = "LOADTEST";
+ public static final long CONFIG_ID = 123456789;
private static final String TAG = "loadtest.ConfigFactory";
@@ -86,7 +86,7 @@
boolean includeDuration, boolean includeEvent, boolean includeValue,
boolean includeGauge) {
StatsdConfig.Builder config = StatsdConfig.newBuilder()
- .setName(CONFIG_NAME);
+ .setId(CONFIG_ID);
if (placebo) {
replication = 0; // Config will be empty, aside from a name.
}
@@ -160,7 +160,7 @@
*/
private void addEventMetric(EventMetric template, int suffix, StatsdConfig.Builder config) {
EventMetric.Builder metric = template.toBuilder()
- .setName(template.getName() + suffix)
+ .setId(template.getId() + suffix)
.setWhat(template.getWhat() + suffix);
if (template.hasCondition()) {
metric.setCondition(template.getCondition() + suffix);
@@ -186,7 +186,7 @@
private void addCountMetric(CountMetric template, int suffix, long bucketMillis,
StatsdConfig.Builder config) {
CountMetric.Builder metric = template.toBuilder()
- .setName(template.getName() + suffix)
+ .setId(template.getId() + suffix)
.setWhat(template.getWhat() + suffix);
if (template.hasCondition()) {
metric.setCondition(template.getCondition() + suffix);
@@ -207,7 +207,7 @@
private void addDurationMetric(DurationMetric template, int suffix, long bucketMillis,
StatsdConfig.Builder config) {
DurationMetric.Builder metric = template.toBuilder()
- .setName(template.getName() + suffix)
+ .setId(template.getId() + suffix)
.setWhat(template.getWhat() + suffix);
if (template.hasCondition()) {
metric.setCondition(template.getCondition() + suffix);
@@ -228,7 +228,7 @@
private void addGaugeMetric(GaugeMetric template, int suffix, long bucketMillis,
StatsdConfig.Builder config) {
GaugeMetric.Builder metric = template.toBuilder()
- .setName(template.getName() + suffix)
+ .setId(template.getId() + suffix)
.setWhat(template.getWhat() + suffix);
if (template.hasCondition()) {
metric.setCondition(template.getCondition() + suffix);
@@ -249,7 +249,7 @@
private void addValueMetric(ValueMetric template, int suffix, long bucketMillis,
StatsdConfig.Builder config) {
ValueMetric.Builder metric = template.toBuilder()
- .setName(template.getName() + suffix)
+ .setId(template.getId() + suffix)
.setWhat(template.getWhat() + suffix);
if (template.hasCondition()) {
metric.setCondition(template.getCondition() + suffix);
@@ -269,11 +269,11 @@
*/
private void addPredicate(Predicate template, int suffix, StatsdConfig.Builder config) {
Predicate.Builder predicate = template.toBuilder()
- .setName(template.getName() + suffix);
+ .setId(template.getId() + suffix);
if (template.hasCombination()) {
Predicate.Combination.Builder cb = template.getCombination().toBuilder()
.clearPredicate();
- for (String child : template.getCombination().getPredicateList()) {
+ for (long child : template.getCombination().getPredicateList()) {
cb.addPredicate(child + suffix);
}
predicate.setCombination(cb.build());
@@ -296,11 +296,11 @@
*/
private void addMatcher(AtomMatcher template, int suffix, StatsdConfig.Builder config) {
AtomMatcher.Builder matcher = template.toBuilder()
- .setName(template.getName() + suffix);
+ .setId(template.getId() + suffix);
if (template.hasCombination()) {
AtomMatcher.Combination.Builder cb = template.getCombination().toBuilder()
.clearMatcher();
- for (String child : template.getCombination().getMatcherList()) {
+ for (long child : template.getCombination().getMatcherList()) {
cb.addMatcher(child + suffix);
}
matcher.setCombination(cb);
diff --git a/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/DisplayProtoUtils.java b/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/DisplayProtoUtils.java
index ba43d57..19087d8 100644
--- a/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/DisplayProtoUtils.java
+++ b/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/DisplayProtoUtils.java
@@ -26,7 +26,7 @@
sb.append("ConfigKey: ");
if (reports.hasConfigKey()) {
com.android.os.StatsLog.ConfigMetricsReportList.ConfigKey key = reports.getConfigKey();
- sb.append("\tuid: ").append(key.getUid()).append(" name: ").append(key.getName())
+ sb.append("\tuid: ").append(key.getUid()).append(" id: ").append(key.getId())
.append("\n");
}
@@ -34,7 +34,7 @@
sb.append("StatsLogReport size: ").append(report.getMetricsCount()).append("\n");
for (StatsLog.StatsLogReport log : report.getMetricsList()) {
sb.append("\n\n");
- sb.append("metric id: ").append(log.getMetricName()).append("\n");
+ sb.append("metric id: ").append(log.getMetricId()).append("\n");
sb.append("start time:").append(getDateStr(log.getStartReportNanos())).append("\n");
sb.append("end time:").append(getDateStr(log.getEndReportNanos())).append("\n");
diff --git a/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/LoadtestActivity.java b/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/LoadtestActivity.java
index 83f4b7b..86da16c 100644
--- a/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/LoadtestActivity.java
+++ b/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/LoadtestActivity.java
@@ -294,7 +294,7 @@
return null;
}
if (mStatsManager != null) {
- byte[] data = mStatsManager.getData(ConfigFactory.CONFIG_NAME);
+ byte[] data = mStatsManager.getData(ConfigFactory.CONFIG_ID);
if (data != null) {
ConfigMetricsReportList reports = null;
try {
@@ -453,7 +453,7 @@
// TODO: Clear all configs instead of specific ones.
if (mStatsManager != null) {
if (mStarted) {
- if (!mStatsManager.removeConfiguration(ConfigFactory.CONFIG_NAME)) {
+ if (!mStatsManager.removeConfiguration(ConfigFactory.CONFIG_ID)) {
Log.d(TAG, "Removed loadtest statsd configs.");
} else {
Log.d(TAG, "Failed to remove loadtest configs.");
@@ -464,7 +464,7 @@
private boolean setConfig(byte[] config) {
if (mStatsManager != null) {
- if (mStatsManager.addConfiguration(ConfigFactory.CONFIG_NAME,
+ if (mStatsManager.addConfiguration(ConfigFactory.CONFIG_ID,
config, getPackageName(), LoadtestActivity.this.getClass().getName())) {
Log.d(TAG, "Config pushed to statsd");
return true;
diff --git a/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/ValidationRecorder.java b/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/ValidationRecorder.java
index 4b614aa..d122654 100644
--- a/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/ValidationRecorder.java
+++ b/cmds/statsd/tools/loadtest/src/com/android/statsd/loadtest/ValidationRecorder.java
@@ -59,18 +59,8 @@
Log.d(TAG, "GOT DATA");
for (ConfigMetricsReport report : reports) {
for (StatsLogReport logReport : report.getMetricsList()) {
- if (!logReport.hasMetricName()) {
+ if (!logReport.hasMetricId()) {
Log.e(TAG, "Metric missing name.");
- continue;
- }
- String metricName = logReport.getMetricName();
- if (metricName.startsWith("EVENT_BATTERY_LEVEL_CHANGES_WHILE_SCREEN_IS_ON_")) {
- validateEventBatteryLevelChangesWhileScreenIsOn(logReport);
- continue;
- }
- if (metricName.startsWith("EVENT_BATTERY_LEVEL_CHANGES_")) {
- validateEventBatteryLevelChanges(logReport);
- continue;
}
}
}
@@ -78,7 +68,7 @@
}
private void validateEventBatteryLevelChanges(StatsLogReport logReport) {
- Log.d(TAG, "Validating " + logReport.getMetricName());
+ Log.d(TAG, "Validating " + logReport.getMetricId());
if (logReport.hasEventMetrics()) {
Log.d(TAG, "Num events captured: " + logReport.getEventMetrics().getDataCount());
for (EventMetricData data : logReport.getEventMetrics().getDataList()) {
@@ -90,6 +80,6 @@
}
private void validateEventBatteryLevelChangesWhileScreenIsOn(StatsLogReport logReport) {
- Log.d(TAG, "Validating " + logReport.getMetricName());
+ Log.d(TAG, "Validating " + logReport.getMetricId());
}
}
diff --git a/core/java/android/app/ActivityManager.java b/core/java/android/app/ActivityManager.java
index 1adae7a..847f91b 100644
--- a/core/java/android/app/ActivityManager.java
+++ b/core/java/android/app/ActivityManager.java
@@ -60,6 +60,7 @@
import android.os.ServiceManager;
import android.os.SystemProperties;
import android.os.UserHandle;
+import android.os.WorkSource;
import android.text.TextUtils;
import android.util.ArrayMap;
import android.util.DisplayMetrics;
@@ -3911,10 +3912,10 @@
/**
* @hide
*/
- public static void noteWakeupAlarm(PendingIntent ps, int sourceUid, String sourcePkg,
- String tag) {
+ public static void noteWakeupAlarm(PendingIntent ps, WorkSource workSource, int sourceUid,
+ String sourcePkg, String tag) {
try {
- getService().noteWakeupAlarm((ps != null) ? ps.getTarget() : null,
+ getService().noteWakeupAlarm((ps != null) ? ps.getTarget() : null, workSource,
sourceUid, sourcePkg, tag);
} catch (RemoteException ex) {
}
@@ -3923,19 +3924,24 @@
/**
* @hide
*/
- public static void noteAlarmStart(PendingIntent ps, int sourceUid, String tag) {
+ public static void noteAlarmStart(PendingIntent ps, WorkSource workSource, int sourceUid,
+ String tag) {
try {
- getService().noteAlarmStart((ps != null) ? ps.getTarget() : null, sourceUid, tag);
+ getService().noteAlarmStart((ps != null) ? ps.getTarget() : null, workSource,
+ sourceUid, tag);
} catch (RemoteException ex) {
}
}
+
/**
* @hide
*/
- public static void noteAlarmFinish(PendingIntent ps, int sourceUid, String tag) {
+ public static void noteAlarmFinish(PendingIntent ps, WorkSource workSource, int sourceUid,
+ String tag) {
try {
- getService().noteAlarmFinish((ps != null) ? ps.getTarget() : null, sourceUid, tag);
+ getService().noteAlarmFinish((ps != null) ? ps.getTarget() : null, workSource,
+ sourceUid, tag);
} catch (RemoteException ex) {
}
}
diff --git a/core/java/android/app/ActivityManagerNative.java b/core/java/android/app/ActivityManagerNative.java
index c09403c..4c558f3 100644
--- a/core/java/android/app/ActivityManagerNative.java
+++ b/core/java/android/app/ActivityManagerNative.java
@@ -75,20 +75,20 @@
*/
static public void noteWakeupAlarm(PendingIntent ps, int sourceUid, String sourcePkg,
String tag) {
- ActivityManager.noteWakeupAlarm(ps, sourceUid, sourcePkg, tag);
+ ActivityManager.noteWakeupAlarm(ps, null, sourceUid, sourcePkg, tag);
}
/**
* @deprecated use ActivityManager.noteAlarmStart instead.
*/
static public void noteAlarmStart(PendingIntent ps, int sourceUid, String tag) {
- ActivityManager.noteAlarmStart(ps, sourceUid, tag);
+ ActivityManager.noteAlarmStart(ps, null, sourceUid, tag);
}
/**
* @deprecated use ActivityManager.noteAlarmFinish instead.
*/
static public void noteAlarmFinish(PendingIntent ps, int sourceUid, String tag) {
- ActivityManager.noteAlarmFinish(ps, sourceUid, tag);
+ ActivityManager.noteAlarmFinish(ps, null, sourceUid, tag);
}
}
diff --git a/core/java/android/app/IActivityManager.aidl b/core/java/android/app/IActivityManager.aidl
index 1278f75..a9e633f 100644
--- a/core/java/android/app/IActivityManager.aidl
+++ b/core/java/android/app/IActivityManager.aidl
@@ -63,6 +63,7 @@
import android.os.ParcelFileDescriptor;
import android.os.PersistableBundle;
import android.os.StrictMode;
+import android.os.WorkSource;
import android.service.voice.IVoiceInteractionSession;
import com.android.internal.app.IVoiceInteractor;
import com.android.internal.os.IResultReceiver;
@@ -198,7 +199,7 @@
void enterSafeMode();
boolean startNextMatchingActivity(in IBinder callingActivity,
in Intent intent, in Bundle options);
- void noteWakeupAlarm(in IIntentSender sender, int sourceUid,
+ void noteWakeupAlarm(in IIntentSender sender, in WorkSource workSource, int sourceUid,
in String sourcePkg, in String tag);
void removeContentProvider(in IBinder connection, boolean stable);
void setRequestedOrientation(in IBinder token, int requestedOrientation);
@@ -468,8 +469,8 @@
void dumpHeapFinished(in String path);
void setVoiceKeepAwake(in IVoiceInteractionSession session, boolean keepAwake);
void updateLockTaskPackages(int userId, in String[] packages);
- void noteAlarmStart(in IIntentSender sender, int sourceUid, in String tag);
- void noteAlarmFinish(in IIntentSender sender, int sourceUid, in String tag);
+ void noteAlarmStart(in IIntentSender sender, in WorkSource workSource, int sourceUid, in String tag);
+ void noteAlarmFinish(in IIntentSender sender, in WorkSource workSource, int sourceUid, in String tag);
int getPackageProcessState(in String packageName, in String callingPackage);
oneway void showLockTaskEscapeMessage(in IBinder token);
void updateDeviceOwner(in String packageName);
diff --git a/core/java/android/net/NetworkWatchlistManager.java b/core/java/android/net/NetworkWatchlistManager.java
index 42e43c8..5425bf5 100644
--- a/core/java/android/net/NetworkWatchlistManager.java
+++ b/core/java/android/net/NetworkWatchlistManager.java
@@ -59,8 +59,8 @@
/**
* Report network watchlist records if necessary.
*
- * Watchlist report process will run summarize records into a single report, then the
- * report will be processed by differential privacy framework and store it on disk.
+ * Watchlist report process will summarize records into a single report, then the
+ * report will be processed by differential privacy framework and stored on disk.
*
* @hide
*/
@@ -72,4 +72,18 @@
e.rethrowFromSystemServer();
}
}
+
+ /**
+ * Reload network watchlist.
+ *
+ * @hide
+ */
+ public void reloadWatchlist() {
+ try {
+ mNetworkWatchlistManager.reloadWatchlist();
+ } catch (RemoteException e) {
+ Log.e(TAG, "Unable to reload watchlist");
+ e.rethrowFromSystemServer();
+ }
+ }
}
diff --git a/core/java/android/os/BatteryStats.java b/core/java/android/os/BatteryStats.java
index 1e847c5..d4d74f4 100644
--- a/core/java/android/os/BatteryStats.java
+++ b/core/java/android/os/BatteryStats.java
@@ -180,6 +180,11 @@
public static final int FOREGROUND_SERVICE = 22;
/**
+ * A constant indicating an aggregate wifi multicast timer
+ */
+ public static final int WIFI_AGGREGATE_MULTICAST_ENABLED = 23;
+
+ /**
* Include all of the data in the stats, including previously saved data.
*/
public static final int STATS_SINCE_CHARGED = 0;
@@ -2334,6 +2339,22 @@
};
/**
+ * Returns total time for WiFi Multicast Wakelock timer.
+ * Note that this may be different from the sum of per uid timer values.
+ *
+ * {@hide}
+ */
+ public abstract long getWifiMulticastWakelockTime(long elapsedRealtimeUs, int which);
+
+ /**
+ * Returns total time for WiFi Multicast Wakelock timer
+ * Note that this may be different from the sum of per uid timer values.
+ *
+ * {@hide}
+ */
+ public abstract int getWifiMulticastWakelockCount(int which);
+
+ /**
* Returns the time in microseconds that wifi has been on while the device was
* running on battery.
*
@@ -3442,16 +3463,13 @@
screenDozeTime / 1000);
- // Calculate both wakelock and wifi multicast wakelock times across all uids.
+ // Calculate wakelock times across all uids.
long fullWakeLockTimeTotal = 0;
long partialWakeLockTimeTotal = 0;
- long multicastWakeLockTimeTotalMicros = 0;
- int multicastWakeLockCountTotal = 0;
for (int iu = 0; iu < NU; iu++) {
final Uid u = uidStats.valueAt(iu);
- // First calculating the wakelock stats
final ArrayMap<String, ? extends BatteryStats.Uid.Wakelock> wakelocks
= u.getWakelockStats();
for (int iw=wakelocks.size()-1; iw>=0; iw--) {
@@ -3469,13 +3487,6 @@
rawRealtime, which);
}
}
-
- // Now calculating the wifi multicast wakelock stats
- final Timer mcTimer = u.getMulticastWakelockStats();
- if (mcTimer != null) {
- multicastWakeLockTimeTotalMicros += mcTimer.getTotalTimeLocked(rawRealtime, which);
- multicastWakeLockCountTotal += mcTimer.getCountLocked(which);
- }
}
// Dump network stats
@@ -3592,6 +3603,9 @@
dumpLine(pw, 0 /* uid */, category, WIFI_SIGNAL_STRENGTH_COUNT_DATA, args);
// Dump Multicast total stats
+ final long multicastWakeLockTimeTotalMicros =
+ getWifiMulticastWakelockTime(rawRealtime, which);
+ final int multicastWakeLockCountTotal = getWifiMulticastWakelockCount(which);
dumpLine(pw, 0 /* uid */, category, WIFI_MULTICAST_TOTAL_DATA,
multicastWakeLockTimeTotalMicros / 1000,
multicastWakeLockCountTotal);
@@ -4456,18 +4470,15 @@
pw.print(" Connectivity changes: "); pw.println(connChanges);
}
- // Calculate both wakelock and wifi multicast wakelock times across all uids.
+ // Calculate wakelock times across all uids.
long fullWakeLockTimeTotalMicros = 0;
long partialWakeLockTimeTotalMicros = 0;
- long multicastWakeLockTimeTotalMicros = 0;
- int multicastWakeLockCountTotal = 0;
final ArrayList<TimerEntry> timers = new ArrayList<>();
for (int iu = 0; iu < NU; iu++) {
final Uid u = uidStats.valueAt(iu);
- // First calculate wakelock statistics
final ArrayMap<String, ? extends BatteryStats.Uid.Wakelock> wakelocks
= u.getWakelockStats();
for (int iw=wakelocks.size()-1; iw>=0; iw--) {
@@ -4495,13 +4506,6 @@
}
}
}
-
- // Next calculate wifi multicast wakelock statistics
- final Timer mcTimer = u.getMulticastWakelockStats();
- if (mcTimer != null) {
- multicastWakeLockTimeTotalMicros += mcTimer.getTotalTimeLocked(rawRealtime, which);
- multicastWakeLockCountTotal += mcTimer.getCountLocked(which);
- }
}
final long mobileRxTotalBytes = getNetworkActivityBytes(NETWORK_MOBILE_RX_DATA, which);
@@ -4531,6 +4535,9 @@
pw.println(sb.toString());
}
+ final long multicastWakeLockTimeTotalMicros =
+ getWifiMulticastWakelockTime(rawRealtime, which);
+ final int multicastWakeLockCountTotal = getWifiMulticastWakelockCount(which);
if (multicastWakeLockTimeTotalMicros != 0) {
sb.setLength(0);
sb.append(prefix);
@@ -7051,6 +7058,28 @@
}
}
}
+
+ for (int procState = 0; procState < Uid.NUM_PROCESS_STATE; ++procState) {
+ final long[] timesMs = u.getCpuFreqTimes(which, procState);
+ if (timesMs != null && timesMs.length == cpuFreqs.length) {
+ long[] screenOffTimesMs = u.getScreenOffCpuFreqTimes(which, procState);
+ if (screenOffTimesMs == null) {
+ screenOffTimesMs = new long[timesMs.length];
+ }
+ final long procToken = proto.start(UidProto.Cpu.BY_PROCESS_STATE);
+ proto.write(UidProto.Cpu.ByProcessState.PROCESS_STATE, procState);
+ for (int ic = 0; ic < timesMs.length; ++ic) {
+ long cToken = proto.start(UidProto.Cpu.ByProcessState.BY_FREQUENCY);
+ proto.write(UidProto.Cpu.ByFrequency.FREQUENCY_INDEX, ic + 1);
+ proto.write(UidProto.Cpu.ByFrequency.TOTAL_DURATION_MS,
+ timesMs[ic]);
+ proto.write(UidProto.Cpu.ByFrequency.SCREEN_OFF_DURATION_MS,
+ screenOffTimesMs[ic]);
+ proto.end(cToken);
+ }
+ proto.end(procToken);
+ }
+ }
proto.end(cpuToken);
// Flashlight (FLASHLIGHT_DATA)
@@ -7535,22 +7564,9 @@
proto.end(mToken);
// Wifi multicast wakelock total stats (WIFI_MULTICAST_WAKELOCK_TOTAL_DATA)
- // Calculate multicast wakelock stats across all uids.
- long multicastWakeLockTimeTotalUs = 0;
- int multicastWakeLockCountTotal = 0;
-
- for (int iu = 0; iu < uidStats.size(); iu++) {
- final Uid u = uidStats.valueAt(iu);
-
- final Timer mcTimer = u.getMulticastWakelockStats();
-
- if (mcTimer != null) {
- multicastWakeLockTimeTotalUs +=
- mcTimer.getTotalTimeLocked(rawRealtimeUs, which);
- multicastWakeLockCountTotal += mcTimer.getCountLocked(which);
- }
- }
-
+ final long multicastWakeLockTimeTotalUs =
+ getWifiMulticastWakelockTime(rawRealtimeUs, which);
+ final int multicastWakeLockCountTotal = getWifiMulticastWakelockCount(which);
final long wmctToken = proto.start(SystemProto.WIFI_MULTICAST_WAKELOCK_TOTAL);
proto.write(SystemProto.WifiMulticastWakelockTotal.DURATION_MS,
multicastWakeLockTimeTotalUs / 1000);
diff --git a/core/java/android/os/Handler.java b/core/java/android/os/Handler.java
index 3ca1005..5c5e351 100644
--- a/core/java/android/os/Handler.java
+++ b/core/java/android/os/Handler.java
@@ -388,6 +388,8 @@
* The runnable will be run on the thread to which this handler is attached.
*
* @param r The Runnable that will be executed.
+ * @param token An instance which can be used to cancel {@code r} via
+ * {@link #removeCallbacksAndMessages}.
* @param uptimeMillis The absolute time at which the callback should run,
* using the {@link android.os.SystemClock#uptimeMillis} time-base.
*
@@ -430,6 +432,32 @@
}
/**
+ * Causes the Runnable r to be added to the message queue, to be run
+ * after the specified amount of time elapses.
+ * The runnable will be run on the thread to which this handler
+ * is attached.
+ * <b>The time-base is {@link android.os.SystemClock#uptimeMillis}.</b>
+ * Time spent in deep sleep will add an additional delay to execution.
+ *
+ * @param r The Runnable that will be executed.
+ * @param token An instance which can be used to cancel {@code r} via
+ * {@link #removeCallbacksAndMessages}.
+ * @param delayMillis The delay (in milliseconds) until the Runnable
+ * will be executed.
+ *
+ * @return Returns true if the Runnable was successfully placed in to the
+ * message queue. Returns false on failure, usually because the
+ * looper processing the message queue is exiting. Note that a
+ * result of true does not mean the Runnable will be processed --
+ * if the looper is quit before the delivery time of the message
+ * occurs then the message will be dropped.
+ */
+ public final boolean postDelayed(Runnable r, Object token, long delayMillis)
+ {
+ return sendMessageDelayed(getPostMessage(r, token), delayMillis);
+ }
+
+ /**
* Posts a message to an object that implements Runnable.
* Causes the Runnable r to executed on the next iteration through the
* message queue. The runnable will be run on the thread to which this
diff --git a/core/java/android/os/IStatsManager.aidl b/core/java/android/os/IStatsManager.aidl
index 3db12ed..29812e8 100644
--- a/core/java/android/os/IStatsManager.aidl
+++ b/core/java/android/os/IStatsManager.aidl
@@ -71,7 +71,7 @@
* Fetches data for the specified configuration key. Returns a byte array representing proto
* wire-encoded of ConfigMetricsReportList.
*/
- byte[] getData(in String key);
+ byte[] getData(in long key);
/**
* Fetches metadata across statsd. Returns byte array representing wire-encoded proto.
@@ -86,7 +86,7 @@
*
* Returns if this configuration was correctly registered.
*/
- boolean addConfiguration(in String configKey, in byte[] config, in String pkg, in String cls);
+ boolean addConfiguration(in long configKey, in byte[] config, in String pkg, in String cls);
/**
* Removes the configuration with the matching config key. No-op if this config key does not
@@ -94,5 +94,5 @@
*
* Returns if this configuration key was removed.
*/
- boolean removeConfiguration(in String configKey);
+ boolean removeConfiguration(in long configKey);
}
diff --git a/core/java/android/util/FeatureFlagUtils.java b/core/java/android/util/FeatureFlagUtils.java
index bfb5130..d31bc1f 100644
--- a/core/java/android/util/FeatureFlagUtils.java
+++ b/core/java/android/util/FeatureFlagUtils.java
@@ -38,7 +38,6 @@
static {
DEFAULT_FLAGS = new HashMap<>();
DEFAULT_FLAGS.put("device_info_v2", "true");
- DEFAULT_FLAGS.put("new_settings_suggestion", "true");
DEFAULT_FLAGS.put("settings_search_v2", "true");
DEFAULT_FLAGS.put("settings_app_info_v2", "false");
DEFAULT_FLAGS.put("settings_connected_device_v2", "true");
diff --git a/core/java/android/util/StatsManager.java b/core/java/android/util/StatsManager.java
index 26a3c36..c25b272 100644
--- a/core/java/android/util/StatsManager.java
+++ b/core/java/android/util/StatsManager.java
@@ -53,7 +53,7 @@
* @return true if successful
*/
@RequiresPermission(Manifest.permission.DUMP)
- public boolean addConfiguration(String configKey, byte[] config, String pkg, String cls) {
+ public boolean addConfiguration(long configKey, byte[] config, String pkg, String cls) {
synchronized (this) {
try {
IStatsManager service = getIStatsManagerLocked();
@@ -76,7 +76,7 @@
* @return true if successful
*/
@RequiresPermission(Manifest.permission.DUMP)
- public boolean removeConfiguration(String configKey) {
+ public boolean removeConfiguration(long configKey) {
synchronized (this) {
try {
IStatsManager service = getIStatsManagerLocked();
@@ -100,7 +100,7 @@
* @return Serialized ConfigMetricsReportList proto. Returns null on failure.
*/
@RequiresPermission(Manifest.permission.DUMP)
- public byte[] getData(String configKey) {
+ public byte[] getData(long configKey) {
synchronized (this) {
try {
IStatsManager service = getIStatsManagerLocked();
diff --git a/core/java/com/android/internal/net/INetworkWatchlistManager.aidl b/core/java/com/android/internal/net/INetworkWatchlistManager.aidl
index 7e88369..ee01a23 100644
--- a/core/java/com/android/internal/net/INetworkWatchlistManager.aidl
+++ b/core/java/com/android/internal/net/INetworkWatchlistManager.aidl
@@ -22,5 +22,6 @@
interface INetworkWatchlistManager {
boolean startWatchlistLogging();
boolean stopWatchlistLogging();
+ void reloadWatchlist();
void reportWatchlistIfNecessary();
}
diff --git a/core/java/com/android/internal/os/BatteryStatsImpl.java b/core/java/com/android/internal/os/BatteryStatsImpl.java
index 72f07b7..1739bed 100644
--- a/core/java/com/android/internal/os/BatteryStatsImpl.java
+++ b/core/java/com/android/internal/os/BatteryStatsImpl.java
@@ -506,8 +506,8 @@
final HistoryEventTracker mActiveEvents = new HistoryEventTracker();
long mHistoryBaseTime;
- boolean mHaveBatteryLevel = false;
- boolean mRecordingHistory = false;
+ protected boolean mHaveBatteryLevel = false;
+ protected boolean mRecordingHistory = false;
int mNumHistoryItems;
final Parcel mHistoryBuffer = Parcel.obtain();
@@ -652,6 +652,14 @@
new LongSamplingCounter[NUM_NETWORK_ACTIVITY_TYPES];
/**
+ * The WiFi Overall wakelock timer
+ * This timer tracks the actual aggregate time for which MC wakelocks are enabled
+ * since addition of per UID timers would not result in an accurate value due to overlapp of
+ * per uid wakelock timers
+ */
+ StopwatchTimer mWifiMulticastWakelockTimer;
+
+ /**
* The WiFi controller activity (time in tx, rx, idle, and power consumed) for the device.
*/
ControllerActivityCounterImpl mWifiActivity;
@@ -3975,30 +3983,85 @@
addHistoryEventLocked(elapsedRealtime, uptime, HistoryItem.EVENT_JOB_FINISH, name, uid);
}
- public void noteAlarmStartLocked(String name, int uid) {
- if (!mRecordAllHistory) {
- return;
- }
- uid = mapUid(uid);
- final long elapsedRealtime = mClocks.elapsedRealtime();
- final long uptime = mClocks.uptimeMillis();
- if (!mActiveEvents.updateState(HistoryItem.EVENT_ALARM_START, name, uid, 0)) {
- return;
- }
- addHistoryEventLocked(elapsedRealtime, uptime, HistoryItem.EVENT_ALARM_START, name, uid);
+ public void noteAlarmStartLocked(String name, WorkSource workSource, int uid) {
+ noteAlarmStartOrFinishLocked(HistoryItem.EVENT_ALARM_START, name, workSource, uid);
}
- public void noteAlarmFinishLocked(String name, int uid) {
+ public void noteAlarmFinishLocked(String name, WorkSource workSource, int uid) {
+ noteAlarmStartOrFinishLocked(HistoryItem.EVENT_ALARM_FINISH, name, workSource, uid);
+ }
+
+ private void noteAlarmStartOrFinishLocked(int historyItem, String name, WorkSource workSource,
+ int uid) {
if (!mRecordAllHistory) {
return;
}
- uid = mapUid(uid);
+
final long elapsedRealtime = mClocks.elapsedRealtime();
final long uptime = mClocks.uptimeMillis();
- if (!mActiveEvents.updateState(HistoryItem.EVENT_ALARM_FINISH, name, uid, 0)) {
+
+ if (workSource != null) {
+ for (int i = 0; i < workSource.size(); ++i) {
+ uid = mapUid(workSource.get(i));
+ if (mActiveEvents.updateState(historyItem, name, uid, 0)) {
+ addHistoryEventLocked(elapsedRealtime, uptime, historyItem, name, uid);
+ }
+ }
+
+ List<WorkChain> workChains = workSource.getWorkChains();
+ if (workChains != null) {
+ for (int i = 0; i < workChains.size(); ++i) {
+ uid = mapUid(workChains.get(i).getAttributionUid());
+ if (mActiveEvents.updateState(historyItem, name, uid, 0)) {
+ addHistoryEventLocked(elapsedRealtime, uptime, historyItem, name, uid);
+ }
+ }
+ }
+ } else {
+ uid = mapUid(uid);
+
+ if (mActiveEvents.updateState(historyItem, name, uid, 0)) {
+ addHistoryEventLocked(elapsedRealtime, uptime, historyItem, name, uid);
+ }
+ }
+ }
+
+ public void noteWakupAlarmLocked(String packageName, int uid, WorkSource workSource,
+ String tag) {
+ if (!isOnBattery()) {
return;
}
- addHistoryEventLocked(elapsedRealtime, uptime, HistoryItem.EVENT_ALARM_FINISH, name, uid);
+
+ if (workSource != null) {
+ for (int i = 0; i < workSource.size(); ++i) {
+ uid = workSource.get(i);
+ final String workSourceName = workSource.getName(i);
+
+ BatteryStatsImpl.Uid.Pkg pkg = getPackageStatsLocked(uid,
+ workSourceName != null ? workSourceName : packageName);
+ pkg.noteWakeupAlarmLocked(tag);
+
+ StatsLog.write(StatsLog.WAKEUP_ALARM_OCCURRED, uid, tag);
+ }
+
+ ArrayList<WorkChain> workChains = workSource.getWorkChains();
+ if (workChains != null) {
+ for (int i = 0; i < workChains.size(); ++i) {
+ final WorkChain wc = workChains.get(i);
+ uid = wc.getAttributionUid();
+
+ BatteryStatsImpl.Uid.Pkg pkg = getPackageStatsLocked(uid, packageName);
+ pkg.noteWakeupAlarmLocked(tag);
+
+ // TODO(statsd): Log the full attribution chain here once it's available
+ StatsLog.write(StatsLog.WAKEUP_ALARM_OCCURRED, uid, tag);
+ }
+ }
+ } else {
+ BatteryStatsImpl.Uid.Pkg pkg = getPackageStatsLocked(uid, packageName);
+ pkg.noteWakeupAlarmLocked(tag);
+ StatsLog.write(StatsLog.WAKEUP_ALARM_OCCURRED, uid, tag);
+ }
}
private void requestWakelockCpuUpdate() {
@@ -5534,6 +5597,12 @@
if (DEBUG_HISTORY) Slog.v(TAG, "WIFI multicast on to: "
+ Integer.toHexString(mHistoryCur.states));
addHistoryRecordLocked(elapsedRealtime, uptime);
+
+ // Start Wifi Multicast overall timer
+ if (!mWifiMulticastWakelockTimer.isRunningLocked()) {
+ if (DEBUG_HISTORY) Slog.v(TAG, "WiFi Multicast Overall Timer Started");
+ mWifiMulticastWakelockTimer.startRunningLocked(elapsedRealtime);
+ }
}
mWifiMulticastNesting++;
getUidStatsLocked(uid).noteWifiMulticastEnabledLocked(elapsedRealtime);
@@ -5549,6 +5618,12 @@
if (DEBUG_HISTORY) Slog.v(TAG, "WIFI multicast off to: "
+ Integer.toHexString(mHistoryCur.states));
addHistoryRecordLocked(elapsedRealtime, uptime);
+
+ // Stop Wifi Multicast overall timer
+ if (mWifiMulticastWakelockTimer.isRunningLocked()) {
+ if (DEBUG_HISTORY) Slog.v(TAG, "Multicast Overall Timer Stopped");
+ mWifiMulticastWakelockTimer.stopRunningLocked(elapsedRealtime);
+ }
}
getUidStatsLocked(uid).noteWifiMulticastDisabledLocked(elapsedRealtime);
}
@@ -5835,6 +5910,16 @@
return (int)mMobileRadioActiveUnknownCount.getCountLocked(which);
}
+ @Override public long getWifiMulticastWakelockTime(
+ long elapsedRealtimeUs, int which) {
+ return mWifiMulticastWakelockTimer.getTotalTimeLocked(
+ elapsedRealtimeUs, which);
+ }
+
+ @Override public int getWifiMulticastWakelockCount(int which) {
+ return mWifiMulticastWakelockTimer.getCountLocked(which);
+ }
+
@Override public long getWifiOnTime(long elapsedRealtimeUs, int which) {
return mWifiOnTimer.getTotalTimeLocked(elapsedRealtimeUs, which);
}
@@ -9435,6 +9520,8 @@
mMobileRadioActiveAdjustedTime = new LongSamplingCounter(mOnBatteryTimeBase);
mMobileRadioActiveUnknownTime = new LongSamplingCounter(mOnBatteryTimeBase);
mMobileRadioActiveUnknownCount = new LongSamplingCounter(mOnBatteryTimeBase);
+ mWifiMulticastWakelockTimer = new StopwatchTimer(mClocks, null,
+ WIFI_AGGREGATE_MULTICAST_ENABLED, null, mOnBatteryTimeBase);
mWifiOnTimer = new StopwatchTimer(mClocks, null, -4, null, mOnBatteryTimeBase);
mGlobalWifiRunningTimer = new StopwatchTimer(mClocks, null, -5, null, mOnBatteryTimeBase);
for (int i=0; i<NUM_WIFI_STATES; i++) {
@@ -10136,6 +10223,7 @@
for (int i=0; i<NUM_WIFI_SIGNAL_STRENGTH_BINS; i++) {
mWifiSignalStrengthsTimer[i].reset(false);
}
+ mWifiMulticastWakelockTimer.reset(false);
mWifiActivity.reset(false);
mBluetoothActivity.reset(false);
mModemActivity.reset(false);
@@ -12582,6 +12670,7 @@
mMobileRadioActiveAdjustedTime.readSummaryFromParcelLocked(in);
mMobileRadioActiveUnknownTime.readSummaryFromParcelLocked(in);
mMobileRadioActiveUnknownCount.readSummaryFromParcelLocked(in);
+ mWifiMulticastWakelockTimer.readSummaryFromParcelLocked(in);
mWifiRadioPowerState = DataConnectionRealTimeInfo.DC_POWER_STATE_LOW;
mWifiOn = false;
mWifiOnTimer.readSummaryFromParcelLocked(in);
@@ -13022,6 +13111,7 @@
mMobileRadioActiveAdjustedTime.writeSummaryFromParcelLocked(out);
mMobileRadioActiveUnknownTime.writeSummaryFromParcelLocked(out);
mMobileRadioActiveUnknownCount.writeSummaryFromParcelLocked(out);
+ mWifiMulticastWakelockTimer.writeSummaryFromParcelLocked(out, NOWREAL_SYS);
mWifiOnTimer.writeSummaryFromParcelLocked(out, NOWREAL_SYS);
mGlobalWifiRunningTimer.writeSummaryFromParcelLocked(out, NOWREAL_SYS);
for (int i=0; i<NUM_WIFI_STATES; i++) {
@@ -13485,6 +13575,8 @@
mMobileRadioActiveAdjustedTime = new LongSamplingCounter(mOnBatteryTimeBase, in);
mMobileRadioActiveUnknownTime = new LongSamplingCounter(mOnBatteryTimeBase, in);
mMobileRadioActiveUnknownCount = new LongSamplingCounter(mOnBatteryTimeBase, in);
+ mWifiMulticastWakelockTimer = new StopwatchTimer(mClocks, null, -4, null,
+ mOnBatteryTimeBase, in);
mWifiRadioPowerState = DataConnectionRealTimeInfo.DC_POWER_STATE_LOW;
mWifiOn = false;
mWifiOnTimer = new StopwatchTimer(mClocks, null, -4, null, mOnBatteryTimeBase, in);
@@ -13691,6 +13783,7 @@
mMobileRadioActiveAdjustedTime.writeToParcel(out);
mMobileRadioActiveUnknownTime.writeToParcel(out);
mMobileRadioActiveUnknownCount.writeToParcel(out);
+ mWifiMulticastWakelockTimer.writeToParcel(out, uSecRealtime);
mWifiOnTimer.writeToParcel(out, uSecRealtime);
mGlobalWifiRunningTimer.writeToParcel(out, uSecRealtime);
for (int i=0; i<NUM_WIFI_STATES; i++) {
@@ -13877,6 +13970,8 @@
mMobileRadioActiveTimer.logState(pr, " ");
pr.println("*** Mobile network active adjusted timer:");
mMobileRadioActiveAdjustedTime.logState(pr, " ");
+ pr.println("*** Wifi Multicast WakeLock Timer:");
+ mWifiMulticastWakelockTimer.logState(pr, " ");
pr.println("*** mWifiRadioPowerState=" + mWifiRadioPowerState);
pr.println("*** Wifi timer:");
mWifiOnTimer.logState(pr, " ");
diff --git a/core/proto/android/os/batterystats.proto b/core/proto/android/os/batterystats.proto
index 0fa428e..da21258 100644
--- a/core/proto/android/os/batterystats.proto
+++ b/core/proto/android/os/batterystats.proto
@@ -537,7 +537,24 @@
// Screen-off CPU time in milliseconds.
optional int64 screen_off_duration_ms = 3;
}
+ // CPU times accumulated across all process states.
repeated ByFrequency by_frequency = 3;
+
+ enum ProcessState {
+ TOP = 0;
+ FOREGROUND_SERVICE = 1;
+ FOREGROUND = 2;
+ BACKGROUND = 3;
+ TOP_SLEEPING = 4;
+ HEAVY_WEIGHT = 5;
+ CACHED = 6;
+ }
+ // CPU times at different process states.
+ message ByProcessState {
+ optional ProcessState process_state = 1;
+ repeated ByFrequency by_frequency = 2;
+ }
+ repeated ByProcessState by_process_state = 4;
}
optional Cpu cpu = 7;
diff --git a/core/res/AndroidManifest.xml b/core/res/AndroidManifest.xml
index 272e3c7..52bfcde 100644
--- a/core/res/AndroidManifest.xml
+++ b/core/res/AndroidManifest.xml
@@ -3870,6 +3870,14 @@
</intent-filter>
</receiver>
+ <receiver android:name="com.android.server.updates.NetworkWatchlistInstallReceiver"
+ android:permission="android.permission.UPDATE_CONFIG">
+ <intent-filter>
+ <action android:name="android.intent.action.UPDATE_NETWORK_WATCHLIST" />
+ <data android:scheme="content" android:host="*" android:mimeType="*/*" />
+ </intent-filter>
+ </receiver>
+
<receiver android:name="com.android.server.updates.ApnDbInstallReceiver"
android:permission="android.permission.UPDATE_CONFIG">
<intent-filter>
diff --git a/core/tests/coretests/src/com/android/internal/os/BatteryStatsNoteTest.java b/core/tests/coretests/src/com/android/internal/os/BatteryStatsNoteTest.java
index 0afec34..a55563a 100644
--- a/core/tests/coretests/src/com/android/internal/os/BatteryStatsNoteTest.java
+++ b/core/tests/coretests/src/com/android/internal/os/BatteryStatsNoteTest.java
@@ -15,16 +15,19 @@
*/
package com.android.internal.os;
+import static android.os.BatteryStats.STATS_CURRENT;
import static android.os.BatteryStats.STATS_SINCE_CHARGED;
import static android.os.BatteryStats.WAKE_TYPE_PARTIAL;
import android.app.ActivityManager;
import android.os.BatteryManager;
import android.os.BatteryStats;
+import android.os.BatteryStats.HistoryItem;
import android.os.WorkSource;
import android.support.test.filters.SmallTest;
import android.view.Display;
+import com.android.internal.os.BatteryStatsImpl.Uid;
import junit.framework.TestCase;
import java.util.ArrayList;
@@ -44,11 +47,14 @@
* Run: adb shell am instrument -e class com.android.internal.os.BatteryStatsNoteTest -w \
* com.android.frameworks.coretests/android.support.test.runner.AndroidJUnitRunner
*/
-public class BatteryStatsNoteTest extends TestCase{
+public class BatteryStatsNoteTest extends TestCase {
+
private static final int UID = 10500;
private static final WorkSource WS = new WorkSource(UID);
- /** Test BatteryStatsImpl.Uid.noteBluetoothScanResultLocked. */
+ /**
+ * Test BatteryStatsImpl.Uid.noteBluetoothScanResultLocked.
+ */
@SmallTest
public void testNoteBluetoothScanResultLocked() throws Exception {
MockBatteryStatsImpl bi = new MockBatteryStatsImpl(new MockClocks());
@@ -75,7 +81,9 @@
.getCountLocked(STATS_SINCE_CHARGED));
}
- /** Test BatteryStatsImpl.Uid.noteStartWakeLocked. */
+ /**
+ * Test BatteryStatsImpl.Uid.noteStartWakeLocked.
+ */
@SmallTest
public void testNoteStartWakeLocked() throws Exception {
final MockClocks clocks = new MockClocks(); // holds realtime and uptime in ms
@@ -86,7 +94,8 @@
bi.updateTimeBasesLocked(true, Display.STATE_OFF, 0, 0);
bi.noteUidProcessStateLocked(UID, ActivityManager.PROCESS_STATE_TOP);
- bi.getUidStatsLocked(UID).noteStartWakeLocked(pid, name, WAKE_TYPE_PARTIAL, clocks.realtime);
+ bi.getUidStatsLocked(UID)
+ .noteStartWakeLocked(pid, name, WAKE_TYPE_PARTIAL, clocks.realtime);
clocks.realtime = clocks.uptime = 100;
bi.noteUidProcessStateLocked(UID, ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND);
@@ -94,7 +103,8 @@
clocks.realtime = clocks.uptime = 220;
bi.getUidStatsLocked(UID).noteStopWakeLocked(pid, name, WAKE_TYPE_PARTIAL, clocks.realtime);
- BatteryStats.Timer aggregTimer = bi.getUidStats().get(UID).getAggregatedPartialWakelockTimer();
+ BatteryStats.Timer aggregTimer = bi.getUidStats().get(UID)
+ .getAggregatedPartialWakelockTimer();
long actualTime = aggregTimer.getTotalTimeLocked(300_000, STATS_SINCE_CHARGED);
long bgTime = aggregTimer.getSubTimer().getTotalTimeLocked(300_000, STATS_SINCE_CHARGED);
assertEquals(220_000, actualTime);
@@ -102,7 +112,9 @@
}
- /** Test BatteryStatsImpl.noteUidProcessStateLocked. */
+ /**
+ * Test BatteryStatsImpl.noteUidProcessStateLocked.
+ */
@SmallTest
public void testNoteUidProcessStateLocked() throws Exception {
final MockClocks clocks = new MockClocks();
@@ -145,7 +157,6 @@
expectedRunTimeMs = stateRuntimeMap.get(ActivityManager.PROCESS_STATE_TOP);
assertEquals(expectedRunTimeMs * 1000, actualRunTimeUs);
-
actualRunTimeUs = uid.getProcessStateTime(BatteryStats.Uid.PROCESS_STATE_FOREGROUND_SERVICE,
elapsedTimeUs, STATS_SINCE_CHARGED);
expectedRunTimeMs = stateRuntimeMap.get(
@@ -153,19 +164,16 @@
+ stateRuntimeMap.get(ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE);
assertEquals(expectedRunTimeMs * 1000, actualRunTimeUs);
-
actualRunTimeUs = uid.getProcessStateTime(BatteryStats.Uid.PROCESS_STATE_TOP_SLEEPING,
elapsedTimeUs, STATS_SINCE_CHARGED);
expectedRunTimeMs = stateRuntimeMap.get(ActivityManager.PROCESS_STATE_TOP_SLEEPING);
assertEquals(expectedRunTimeMs * 1000, actualRunTimeUs);
-
actualRunTimeUs = uid.getProcessStateTime(BatteryStats.Uid.PROCESS_STATE_FOREGROUND,
elapsedTimeUs, STATS_SINCE_CHARGED);
expectedRunTimeMs = stateRuntimeMap.get(ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND);
assertEquals(expectedRunTimeMs * 1000, actualRunTimeUs);
-
actualRunTimeUs = uid.getProcessStateTime(BatteryStats.Uid.PROCESS_STATE_BACKGROUND,
elapsedTimeUs, STATS_SINCE_CHARGED);
expectedRunTimeMs = stateRuntimeMap.get(ActivityManager.PROCESS_STATE_TRANSIENT_BACKGROUND)
@@ -174,7 +182,6 @@
+ stateRuntimeMap.get(ActivityManager.PROCESS_STATE_RECEIVER);
assertEquals(expectedRunTimeMs * 1000, actualRunTimeUs);
-
actualRunTimeUs = uid.getProcessStateTime(BatteryStats.Uid.PROCESS_STATE_CACHED,
elapsedTimeUs, STATS_SINCE_CHARGED);
expectedRunTimeMs = stateRuntimeMap.get(ActivityManager.PROCESS_STATE_HOME)
@@ -191,7 +198,9 @@
assertEquals(expectedRunTimeMs * 1000, actualRunTimeUs);
}
- /** Test BatteryStatsImpl.updateTimeBasesLocked. */
+ /**
+ * Test BatteryStatsImpl.updateTimeBasesLocked.
+ */
@SmallTest
public void testUpdateTimeBasesLocked() throws Exception {
final MockClocks clocks = new MockClocks(); // holds realtime and uptime in ms
@@ -213,7 +222,9 @@
assertTrue(bi.getOnBatteryScreenOffTimeBase().isRunning());
}
- /** Test BatteryStatsImpl.noteScreenStateLocked sets timebases and screen states correctly. */
+ /**
+ * Test BatteryStatsImpl.noteScreenStateLocked sets timebases and screen states correctly.
+ */
@SmallTest
public void testNoteScreenStateLocked() throws Exception {
final MockClocks clocks = new MockClocks(); // holds realtime and uptime in ms
@@ -232,15 +243,13 @@
assertEquals(bi.getScreenState(), Display.STATE_OFF);
}
- /** Test BatteryStatsImpl.noteScreenStateLocked updates timers correctly.
+ /**
+ * Test BatteryStatsImpl.noteScreenStateLocked updates timers correctly.
*
- * Unknown and doze should both be subset of off state
+ * Unknown and doze should both be subset of off state
*
- * Timeline 0----100----200----310----400------------1000
- * Unknown -------
- * On -------
- * Off ------- ----------------------
- * Doze ----------------
+ * Timeline 0----100----200----310----400------------1000 Unknown ------- On ------- Off
+ * ------- ---------------------- Doze ----------------
*/
@SmallTest
public void testNoteScreenStateTimersLocked() throws Exception {
@@ -280,4 +289,161 @@
assertEquals(600_000, bi.getScreenDozeTime(1500_000, STATS_SINCE_CHARGED));
}
+ @SmallTest
+ public void testAlarmStartAndFinishLocked() throws Exception {
+ final MockClocks clocks = new MockClocks(); // holds realtime and uptime in ms
+ MockBatteryStatsImpl bi = new MockBatteryStatsImpl(clocks);
+ bi.setRecordAllHistoryLocked(true);
+ bi.forceRecordAllHistory();
+
+ bi.updateTimeBasesLocked(true, Display.STATE_OFF, 0, 0);
+ bi.noteUidProcessStateLocked(UID, ActivityManager.PROCESS_STATE_TOP);
+
+ clocks.realtime = clocks.uptime = 100;
+ bi.noteAlarmStartLocked("foo", null, UID);
+ clocks.realtime = clocks.uptime = 5000;
+ bi.noteAlarmFinishLocked("foo", null, UID);
+
+ HistoryItem item = new HistoryItem();
+ assertTrue(bi.startIteratingHistoryLocked());
+
+ assertTrue(bi.getNextHistoryLocked(item));
+ assertEquals(HistoryItem.EVENT_ALARM_START, item.eventCode);
+ assertEquals("foo", item.eventTag.string);
+ assertEquals(UID, item.eventTag.uid);
+
+ // TODO(narayan): Figure out why this event is written to the history buffer. See
+ // test below where it is being interspersed between multiple START events too.
+ assertTrue(bi.getNextHistoryLocked(item));
+ assertEquals(HistoryItem.EVENT_NONE, item.eventCode);
+
+ assertTrue(bi.getNextHistoryLocked(item));
+ assertEquals(HistoryItem.EVENT_ALARM_FINISH, item.eventCode);
+ assertTrue(item.isDeltaData());
+ assertEquals("foo", item.eventTag.string);
+ assertEquals(UID, item.eventTag.uid);
+
+ assertFalse(bi.getNextHistoryLocked(item));
+ }
+
+ @SmallTest
+ public void testAlarmStartAndFinishLocked_workSource() throws Exception {
+ final MockClocks clocks = new MockClocks(); // holds realtime and uptime in ms
+ MockBatteryStatsImpl bi = new MockBatteryStatsImpl(clocks);
+ bi.setRecordAllHistoryLocked(true);
+ bi.forceRecordAllHistory();
+
+ bi.updateTimeBasesLocked(true, Display.STATE_OFF, 0, 0);
+ bi.noteUidProcessStateLocked(UID, ActivityManager.PROCESS_STATE_TOP);
+
+ WorkSource ws = new WorkSource();
+ ws.add(100);
+ ws.createWorkChain().addNode(500, "tag");
+ bi.noteAlarmStartLocked("foo", ws, UID);
+ clocks.realtime = clocks.uptime = 5000;
+ bi.noteAlarmFinishLocked("foo", ws, UID);
+
+ HistoryItem item = new HistoryItem();
+ assertTrue(bi.startIteratingHistoryLocked());
+
+ assertTrue(bi.getNextHistoryLocked(item));
+ assertEquals(HistoryItem.EVENT_ALARM_START, item.eventCode);
+ assertEquals("foo", item.eventTag.string);
+ assertEquals(100, item.eventTag.uid);
+
+ assertTrue(bi.getNextHistoryLocked(item));
+ assertEquals(HistoryItem.EVENT_NONE, item.eventCode);
+
+ assertTrue(bi.getNextHistoryLocked(item));
+ assertEquals(HistoryItem.EVENT_ALARM_START, item.eventCode);
+ assertEquals("foo", item.eventTag.string);
+ assertEquals(500, item.eventTag.uid);
+
+ assertTrue(bi.getNextHistoryLocked(item));
+ assertEquals(HistoryItem.EVENT_ALARM_FINISH, item.eventCode);
+ assertEquals("foo", item.eventTag.string);
+ assertEquals(100, item.eventTag.uid);
+
+ assertTrue(bi.getNextHistoryLocked(item));
+ assertEquals(HistoryItem.EVENT_ALARM_FINISH, item.eventCode);
+ assertEquals("foo", item.eventTag.string);
+ assertEquals(500, item.eventTag.uid);
+ }
+
+ @SmallTest
+ public void testNoteWakupAlarmLocked() {
+ final MockClocks clocks = new MockClocks(); // holds realtime and uptime in ms
+ MockBatteryStatsImpl bi = new MockBatteryStatsImpl(clocks);
+ bi.setRecordAllHistoryLocked(true);
+ bi.forceRecordAllHistory();
+ bi.mForceOnBattery = true;
+
+ bi.updateTimeBasesLocked(true, Display.STATE_OFF, 0, 0);
+ bi.noteUidProcessStateLocked(UID, ActivityManager.PROCESS_STATE_TOP);
+
+ bi.noteWakupAlarmLocked("com.foo.bar", UID, null, "tag");
+
+ Uid.Pkg pkg = bi.getPackageStatsLocked(UID, "com.foo.bar");
+ assertEquals(1, pkg.getWakeupAlarmStats().get("tag").getCountLocked(STATS_CURRENT));
+ assertEquals(1, pkg.getWakeupAlarmStats().size());
+ }
+
+ @SmallTest
+ public void testNoteWakupAlarmLocked_workSource_uid() {
+ final MockClocks clocks = new MockClocks(); // holds realtime and uptime in ms
+ MockBatteryStatsImpl bi = new MockBatteryStatsImpl(clocks);
+ bi.setRecordAllHistoryLocked(true);
+ bi.forceRecordAllHistory();
+ bi.mForceOnBattery = true;
+
+ bi.updateTimeBasesLocked(true, Display.STATE_OFF, 0, 0);
+ bi.noteUidProcessStateLocked(UID, ActivityManager.PROCESS_STATE_TOP);
+
+ WorkSource ws = new WorkSource();
+ ws.add(100);
+
+ // When a WorkSource is present, "UID" should not be used - only the uids present in the
+ // WorkSource should be reported.
+ bi.noteWakupAlarmLocked("com.foo.bar", UID, ws, "tag");
+ Uid.Pkg pkg = bi.getPackageStatsLocked(UID, "com.foo.bar");
+ assertEquals(0, pkg.getWakeupAlarmStats().size());
+ pkg = bi.getPackageStatsLocked(100, "com.foo.bar");
+ assertEquals(1, pkg.getWakeupAlarmStats().size());
+
+ // If the WorkSource contains a "name", it should be interpreted as a package name and
+ // the packageName supplied as an argument must be ignored.
+ ws = new WorkSource();
+ ws.add(100, "com.foo.baz_alternate");
+ bi.noteWakupAlarmLocked("com.foo.baz", UID, ws, "tag");
+ pkg = bi.getPackageStatsLocked(100, "com.foo.baz");
+ assertEquals(0, pkg.getWakeupAlarmStats().size());
+ pkg = bi.getPackageStatsLocked(100, "com.foo.baz_alternate");
+ assertEquals(1, pkg.getWakeupAlarmStats().size());
+ }
+
+ @SmallTest
+ public void testNoteWakupAlarmLocked_workSource_workChain() {
+ final MockClocks clocks = new MockClocks(); // holds realtime and uptime in ms
+ MockBatteryStatsImpl bi = new MockBatteryStatsImpl(clocks);
+ bi.setRecordAllHistoryLocked(true);
+ bi.forceRecordAllHistory();
+ bi.mForceOnBattery = true;
+
+ bi.updateTimeBasesLocked(true, Display.STATE_OFF, 0, 0);
+ bi.noteUidProcessStateLocked(UID, ActivityManager.PROCESS_STATE_TOP);
+
+ WorkSource ws = new WorkSource();
+ ws.createWorkChain().addNode(100, "com.foo.baz_alternate");
+ bi.noteWakupAlarmLocked("com.foo.bar", UID, ws, "tag");
+
+ // For WorkChains, again we must only attribute to the uids present in the WorkSource
+ // (and not to "UID"). However, unlike the older "tags" we do not change the packagename
+ // supplied as an argument, given that we're logging the entire attribution chain.
+ Uid.Pkg pkg = bi.getPackageStatsLocked(UID, "com.foo.bar");
+ assertEquals(0, pkg.getWakeupAlarmStats().size());
+ pkg = bi.getPackageStatsLocked(100, "com.foo.bar");
+ assertEquals(1, pkg.getWakeupAlarmStats().size());
+ pkg = bi.getPackageStatsLocked(100, "com.foo.baz_alternate");
+ assertEquals(0, pkg.getWakeupAlarmStats().size());
+ }
}
diff --git a/core/tests/coretests/src/com/android/internal/os/MockBatteryStatsImpl.java b/core/tests/coretests/src/com/android/internal/os/MockBatteryStatsImpl.java
index de2fd12..f19ff67 100644
--- a/core/tests/coretests/src/com/android/internal/os/MockBatteryStatsImpl.java
+++ b/core/tests/coretests/src/com/android/internal/os/MockBatteryStatsImpl.java
@@ -16,6 +16,8 @@
package com.android.internal.os;
+import android.os.Handler;
+import android.os.Looper;
import android.util.SparseIntArray;
import java.util.ArrayList;
@@ -37,6 +39,9 @@
mOnBatteryTimeBase);
mBluetoothScanTimer = new StopwatchTimer(mClocks, null, -14, null, mOnBatteryTimeBase);
setExternalStatsSyncLocked(new DummyExternalStatsSync());
+
+ // A no-op handler.
+ mHandler = new Handler(Looper.getMainLooper()) {};
}
MockBatteryStatsImpl() {
@@ -59,6 +64,12 @@
return mForceOnBattery ? true : super.isOnBattery();
}
+ public void forceRecordAllHistory() {
+ mHaveBatteryLevel = true;
+ mRecordingHistory = true;
+ mRecordAllHistory = true;
+ }
+
public TimeBase getOnBatteryBackgroundTimeBase(int uid) {
return getUidStatsLocked(uid).mOnBatteryBackgroundTimeBase;
}
diff --git a/libs/hwui/tests/common/TestUtils.cpp b/libs/hwui/tests/common/TestUtils.cpp
index 1e42425..4a0d6ee 100644
--- a/libs/hwui/tests/common/TestUtils.cpp
+++ b/libs/hwui/tests/common/TestUtils.cpp
@@ -122,15 +122,19 @@
void TestUtils::drawUtf8ToCanvas(Canvas* canvas, const char* text, const SkPaint& paint, float x,
float y) {
auto utf16 = asciiToUtf16(text);
- canvas->drawText(utf16.get(), 0, strlen(text), strlen(text), x, y, minikin::Bidi::LTR, paint,
- nullptr);
+ SkPaint glyphPaint(paint);
+ glyphPaint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
+ canvas->drawText(utf16.get(), 0, strlen(text), strlen(text), x, y, minikin::Bidi::LTR,
+ glyphPaint, nullptr);
}
void TestUtils::drawUtf8ToCanvas(Canvas* canvas, const char* text, const SkPaint& paint,
const SkPath& path) {
auto utf16 = asciiToUtf16(text);
- canvas->drawTextOnPath(utf16.get(), strlen(text), minikin::Bidi::LTR, path, 0, 0, paint,
- nullptr);
+ SkPaint glyphPaint(paint);
+ glyphPaint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
+ canvas->drawTextOnPath(utf16.get(), strlen(text), minikin::Bidi::LTR, path, 0, 0, glyphPaint,
+ nullptr);
}
void TestUtils::TestTask::run() {
diff --git a/libs/hwui/tests/common/scenes/GlyphStressAnimation.cpp b/libs/hwui/tests/common/scenes/GlyphStressAnimation.cpp
index bf0aed9..38999cb 100644
--- a/libs/hwui/tests/common/scenes/GlyphStressAnimation.cpp
+++ b/libs/hwui/tests/common/scenes/GlyphStressAnimation.cpp
@@ -40,22 +40,18 @@
}
void doFrame(int frameNr) override {
- std::unique_ptr<uint16_t[]> text =
- TestUtils::asciiToUtf16("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ");
- ssize_t textLength = 26 * 2;
+ const char* text = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ";
std::unique_ptr<Canvas> canvas(
Canvas::create_recording_canvas(container->stagingProperties().getWidth(),
container->stagingProperties().getHeight()));
Paint paint;
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
paint.setAntiAlias(true);
paint.setColor(Color::Black);
for (int i = 0; i < 5; i++) {
paint.setTextSize(10 + (frameNr % 20) + i * 20);
- canvas->drawText(text.get(), 0, textLength, textLength, 0, 100 * (i + 2),
- minikin::Bidi::FORCE_LTR, paint, nullptr);
+ TestUtils::drawUtf8ToCanvas(canvas.get(), text, paint, 0, 100 * (i + 2));
}
container->setStagingDisplayList(canvas->finishRecording());
diff --git a/libs/hwui/tests/common/scenes/ListOfFadedTextAnimation.cpp b/libs/hwui/tests/common/scenes/ListOfFadedTextAnimation.cpp
index 6bae80c..58c9980 100644
--- a/libs/hwui/tests/common/scenes/ListOfFadedTextAnimation.cpp
+++ b/libs/hwui/tests/common/scenes/ListOfFadedTextAnimation.cpp
@@ -36,7 +36,6 @@
SkPaint textPaint;
textPaint.setTextSize(dp(20));
textPaint.setAntiAlias(true);
- textPaint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
TestUtils::drawUtf8ToCanvas(&canvas, "not that long long text", textPaint, dp(10), dp(30));
SkPoint pts[2];
diff --git a/libs/hwui/tests/common/scenes/ListViewAnimation.cpp b/libs/hwui/tests/common/scenes/ListViewAnimation.cpp
index d7ec288..fd8c252 100644
--- a/libs/hwui/tests/common/scenes/ListViewAnimation.cpp
+++ b/libs/hwui/tests/common/scenes/ListViewAnimation.cpp
@@ -83,7 +83,6 @@
canvas.drawRoundRect(0, 0, itemWidth, itemHeight, dp(6), dp(6), roundRectPaint);
SkPaint textPaint;
- textPaint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
textPaint.setColor(rand() % 2 ? Color::Black : Color::Grey_500);
textPaint.setTextSize(dp(20));
textPaint.setAntiAlias(true);
diff --git a/libs/hwui/tests/common/scenes/MagnifierAnimation.cpp b/libs/hwui/tests/common/scenes/MagnifierAnimation.cpp
index 9eddc20..aa537b4 100644
--- a/libs/hwui/tests/common/scenes/MagnifierAnimation.cpp
+++ b/libs/hwui/tests/common/scenes/MagnifierAnimation.cpp
@@ -38,7 +38,6 @@
card = TestUtils::createNode(
0, 0, width, height, [&](RenderProperties& props, Canvas& canvas) {
SkPaint paint;
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
paint.setAntiAlias(true);
paint.setTextSize(50);
diff --git a/libs/hwui/tests/common/scenes/SaveLayer2Animation.cpp b/libs/hwui/tests/common/scenes/SaveLayer2Animation.cpp
index fee0659..3befce4 100644
--- a/libs/hwui/tests/common/scenes/SaveLayer2Animation.cpp
+++ b/libs/hwui/tests/common/scenes/SaveLayer2Animation.cpp
@@ -42,10 +42,8 @@
mBluePaint.setColor(SkColorSetARGB(255, 0, 0, 255));
mBluePaint.setTextSize(padding);
- mBluePaint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
mGreenPaint.setColor(SkColorSetARGB(255, 0, 255, 0));
mGreenPaint.setTextSize(padding);
- mGreenPaint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
// interleave drawText and drawRect with saveLayer ops
for (int i = 0; i < regions; i++, top += smallRectHeight) {
@@ -54,18 +52,15 @@
canvas.drawColor(SkColorSetARGB(255, 255, 255, 0), SkBlendMode::kSrcOver);
std::string stri = std::to_string(i);
std::string offscreen = "offscreen line " + stri;
- std::unique_ptr<uint16_t[]> offtext = TestUtils::asciiToUtf16(offscreen.c_str());
- canvas.drawText(offtext.get(), 0, offscreen.length(), offscreen.length(), bounds.fLeft,
- top + padding, minikin::Bidi::FORCE_LTR, mBluePaint, nullptr);
+ TestUtils::drawUtf8ToCanvas(&canvas, offscreen.c_str(), mBluePaint, bounds.fLeft,
+ top + padding);
canvas.restore();
canvas.drawRect(bounds.fLeft, top + padding, bounds.fRight,
top + smallRectHeight - padding, mBluePaint);
std::string onscreen = "onscreen line " + stri;
- std::unique_ptr<uint16_t[]> ontext = TestUtils::asciiToUtf16(onscreen.c_str());
- canvas.drawText(ontext.get(), 0, onscreen.length(), onscreen.length(), bounds.fLeft,
- top + smallRectHeight - padding, minikin::Bidi::FORCE_LTR, mGreenPaint,
- nullptr);
+ TestUtils::drawUtf8ToCanvas(&canvas, onscreen.c_str(), mGreenPaint, bounds.fLeft,
+ top + smallRectHeight - padding);
}
}
void doFrame(int frameNr) override {}
diff --git a/libs/hwui/tests/common/scenes/TextAnimation.cpp b/libs/hwui/tests/common/scenes/TextAnimation.cpp
index a502116..a16b1784 100644
--- a/libs/hwui/tests/common/scenes/TextAnimation.cpp
+++ b/libs/hwui/tests/common/scenes/TextAnimation.cpp
@@ -29,7 +29,6 @@
card = TestUtils::createNode(0, 0, width, height, [](RenderProperties& props,
Canvas& canvas) {
SkPaint paint;
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
paint.setAntiAlias(true);
paint.setTextSize(50);
diff --git a/libs/hwui/tests/common/scenes/TvApp.cpp b/libs/hwui/tests/common/scenes/TvApp.cpp
index c845e6c..003d8e9 100644
--- a/libs/hwui/tests/common/scenes/TvApp.cpp
+++ b/libs/hwui/tests/common/scenes/TvApp.cpp
@@ -117,7 +117,6 @@
canvas.drawColor(0xFFFFEEEE, SkBlendMode::kSrcOver);
SkPaint paint;
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
paint.setAntiAlias(true);
paint.setTextSize(24);
diff --git a/libs/hwui/tests/unit/FrameBuilderTests.cpp b/libs/hwui/tests/unit/FrameBuilderTests.cpp
index e56d2f8..4eb7751 100644
--- a/libs/hwui/tests/unit/FrameBuilderTests.cpp
+++ b/libs/hwui/tests/unit/FrameBuilderTests.cpp
@@ -537,7 +537,6 @@
canvas.save(SaveFlags::MatrixClip);
canvas.clipPath(&path, SkClipOp::kIntersect);
SkPaint paint;
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
paint.setAntiAlias(true);
paint.setTextSize(50);
TestUtils::drawUtf8ToCanvas(&canvas, "Test string1", paint, 100, 100);
@@ -569,7 +568,6 @@
auto node = TestUtils::createNode<RecordingCanvas>(0, 0, 400, 400, [](RenderProperties& props,
RecordingCanvas& canvas) {
SkPaint paint;
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
paint.setAntiAlias(true);
paint.setTextSize(50);
TestUtils::drawUtf8ToCanvas(&canvas, "Test string1", paint, 100, 0); // will be top clipped
@@ -603,7 +601,6 @@
textPaint.setAntiAlias(true);
textPaint.setTextSize(20);
textPaint.setFlags(textPaint.getFlags() | SkPaint::kStrikeThruText_ReserveFlag);
- textPaint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
for (int i = 0; i < LOOPS; i++) {
TestUtils::drawUtf8ToCanvas(&canvas, "test text", textPaint, 10, 100 * (i + 1));
}
@@ -654,7 +651,6 @@
auto node = TestUtils::createNode<RecordingCanvas>(
0, 0, 400, 400, [](RenderProperties& props, RecordingCanvas& canvas) {
SkPaint paint;
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
paint.setAntiAlias(true);
paint.setTextSize(50);
paint.setStrokeWidth(10);
diff --git a/libs/hwui/tests/unit/RecordingCanvasTests.cpp b/libs/hwui/tests/unit/RecordingCanvasTests.cpp
index 5aae15f..8a9e34f 100644
--- a/libs/hwui/tests/unit/RecordingCanvasTests.cpp
+++ b/libs/hwui/tests/unit/RecordingCanvasTests.cpp
@@ -175,7 +175,6 @@
SkPaint paint;
paint.setAntiAlias(true);
paint.setTextSize(20);
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
TestUtils::drawUtf8ToCanvas(&canvas, "test text", paint, 25, 25);
});
@@ -196,7 +195,6 @@
SkPaint paint;
paint.setAntiAlias(true);
paint.setTextSize(20);
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
for (int i = 0; i < 2; i++) {
for (int j = 0; j < 2; j++) {
uint32_t flags = paint.getFlags();
@@ -238,7 +236,6 @@
SkPaint paint;
paint.setAntiAlias(true);
paint.setTextSize(20);
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
paint.setTextAlign(SkPaint::kLeft_Align);
TestUtils::drawUtf8ToCanvas(&canvas, "test text", paint, 25, 25);
paint.setTextAlign(SkPaint::kCenter_Align);
@@ -805,9 +802,7 @@
Paint paint;
paint.setAntiAlias(true);
paint.setTextSize(20);
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
- std::unique_ptr<uint16_t[]> dst = TestUtils::asciiToUtf16("HELLO");
- canvas.drawText(dst.get(), 0, 5, 5, 25, 25, minikin::Bidi::FORCE_LTR, paint, NULL);
+ TestUtils::drawUtf8ToCanvas(&canvas, "HELLO", paint, 25, 25);
});
int count = 0;
@@ -829,9 +824,7 @@
paint.setColor(SK_ColorWHITE);
paint.setAntiAlias(true);
paint.setTextSize(20);
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
- std::unique_ptr<uint16_t[]> dst = TestUtils::asciiToUtf16("HELLO");
- canvas.drawText(dst.get(), 0, 5, 5, 25, 25, minikin::Bidi::FORCE_LTR, paint, NULL);
+ TestUtils::drawUtf8ToCanvas(&canvas, "HELLO", paint, 25, 25);
});
Properties::enableHighContrastText = false;
diff --git a/libs/hwui/tests/unit/SkiaCanvasTests.cpp b/libs/hwui/tests/unit/SkiaCanvasTests.cpp
index 4138f59..1d7dc3d 100644
--- a/libs/hwui/tests/unit/SkiaCanvasTests.cpp
+++ b/libs/hwui/tests/unit/SkiaCanvasTests.cpp
@@ -36,7 +36,6 @@
SkPaint paint;
paint.setAntiAlias(true);
paint.setTextSize(20);
- paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
static const char* text = "testing text bounds";
// draw text directly into Recording canvas
diff --git a/libs/hwui/tests/unit/TextDropShadowCacheTests.cpp b/libs/hwui/tests/unit/TextDropShadowCacheTests.cpp
index 78d75d6..92d05e4 100644
--- a/libs/hwui/tests/unit/TextDropShadowCacheTests.cpp
+++ b/libs/hwui/tests/unit/TextDropShadowCacheTests.cpp
@@ -29,6 +29,7 @@
RENDERTHREAD_OPENGL_PIPELINE_TEST(TextDropShadowCache, addRemove) {
SkPaint paint;
paint.setTextSize(20);
+ paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
GammaFontRenderer gammaFontRenderer;
FontRenderer& fontRenderer = gammaFontRenderer.getFontRenderer();
diff --git a/media/java/android/media/AudioFocusInfo.java b/media/java/android/media/AudioFocusInfo.java
index 6d9c5e2..5d0c8e2 100644
--- a/media/java/android/media/AudioFocusInfo.java
+++ b/media/java/android/media/AudioFocusInfo.java
@@ -130,13 +130,11 @@
dest.writeInt(mSdkTarget);
}
- @SystemApi
@Override
public int hashCode() {
return Objects.hash(mAttributes, mClientUid, mClientId, mPackageName, mGainRequest, mFlags);
}
- @SystemApi
@Override
public boolean equals(Object obj) {
if (this == obj)
diff --git a/packages/SystemUI/src/com/android/systemui/pip/phone/PipAppOpsListener.java b/packages/SystemUI/src/com/android/systemui/pip/phone/PipAppOpsListener.java
new file mode 100644
index 0000000..f0e4ccc
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/pip/phone/PipAppOpsListener.java
@@ -0,0 +1,89 @@
+/*
+ * Copyright (C) 2017 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.
+ */
+
+package com.android.systemui.pip.phone;
+
+import static android.app.AppOpsManager.MODE_ALLOWED;
+import static android.app.AppOpsManager.OP_PICTURE_IN_PICTURE;
+
+import android.app.AppOpsManager;
+import android.app.AppOpsManager.OnOpChangedListener;
+import android.app.IActivityManager;
+import android.content.ComponentName;
+import android.content.Context;
+import android.content.pm.ApplicationInfo;
+import android.content.pm.PackageManager.NameNotFoundException;
+import android.util.Pair;
+
+public class PipAppOpsListener {
+ private static final String TAG = PipAppOpsListener.class.getSimpleName();
+
+ private Context mContext;
+ private IActivityManager mActivityManager;
+ private AppOpsManager mAppOpsManager;
+
+ private PipMotionHelper mMotionHelper;
+
+ private AppOpsManager.OnOpChangedListener mAppOpsChangedListener = new OnOpChangedListener() {
+ @Override
+ public void onOpChanged(String op, String packageName) {
+ try {
+ // Dismiss the PiP once the user disables the app ops setting for that package
+ final Pair<ComponentName, Integer> topPipActivityInfo =
+ PipUtils.getTopPinnedActivity(mContext, mActivityManager);
+ if (topPipActivityInfo.first != null) {
+ final ApplicationInfo appInfo = mContext.getPackageManager()
+ .getApplicationInfoAsUser(packageName, 0, topPipActivityInfo.second);
+ if (appInfo.packageName.equals(topPipActivityInfo.first.getPackageName()) &&
+ mAppOpsManager.checkOpNoThrow(OP_PICTURE_IN_PICTURE, appInfo.uid,
+ packageName) != MODE_ALLOWED) {
+ mMotionHelper.dismissPip();
+ }
+ }
+ } catch (NameNotFoundException e) {
+ // Unregister the listener if the package can't be found
+ unregisterAppOpsListener();
+ }
+ }
+ };
+
+ public PipAppOpsListener(Context context, IActivityManager activityManager,
+ PipMotionHelper motionHelper) {
+ mContext = context;
+ mActivityManager = activityManager;
+ mAppOpsManager = (AppOpsManager) context.getSystemService(Context.APP_OPS_SERVICE);
+ mMotionHelper = motionHelper;
+ }
+
+ public void onActivityPinned(String packageName) {
+ // Register for changes to the app ops setting for this package while it is in PiP
+ registerAppOpsListener(packageName);
+ }
+
+ public void onActivityUnpinned() {
+ // Unregister for changes to the previously PiP'ed package
+ unregisterAppOpsListener();
+ }
+
+ private void registerAppOpsListener(String packageName) {
+ mAppOpsManager.startWatchingMode(OP_PICTURE_IN_PICTURE, packageName,
+ mAppOpsChangedListener);
+ }
+
+ private void unregisterAppOpsListener() {
+ mAppOpsManager.stopWatchingMode(mAppOpsChangedListener);
+ }
+}
\ No newline at end of file
diff --git a/packages/SystemUI/src/com/android/systemui/pip/phone/PipManager.java b/packages/SystemUI/src/com/android/systemui/pip/phone/PipManager.java
index dce3e24..36531bb 100644
--- a/packages/SystemUI/src/com/android/systemui/pip/phone/PipManager.java
+++ b/packages/SystemUI/src/com/android/systemui/pip/phone/PipManager.java
@@ -65,6 +65,7 @@
private PipMenuActivityController mMenuController;
private PipMediaController mMediaController;
private PipTouchHandler mTouchHandler;
+ private PipAppOpsListener mAppOpsListener;
/**
* Handler for system task stack changes.
@@ -75,6 +76,7 @@
mTouchHandler.onActivityPinned();
mMediaController.onActivityPinned();
mMenuController.onActivityPinned();
+ mAppOpsListener.onActivityPinned(packageName);
SystemServicesProxy.getInstance(mContext).setPipVisibility(true);
}
@@ -87,6 +89,7 @@
final int userId = topActivity != null ? topPipActivityInfo.second : 0;
mMenuController.onActivityUnpinned();
mTouchHandler.onActivityUnpinned(topActivity);
+ mAppOpsListener.onActivityUnpinned();
SystemServicesProxy.getInstance(mContext).setPipVisibility(topActivity != null);
}
@@ -177,6 +180,8 @@
mInputConsumerController);
mTouchHandler = new PipTouchHandler(context, mActivityManager, mMenuController,
mInputConsumerController);
+ mAppOpsListener = new PipAppOpsListener(context, mActivityManager,
+ mTouchHandler.getMotionHelper());
EventBus.getDefault().register(this);
}
diff --git a/proto/src/metrics_constants.proto b/proto/src/metrics_constants.proto
index 935b787..1aaa538 100644
--- a/proto/src/metrics_constants.proto
+++ b/proto/src/metrics_constants.proto
@@ -5094,6 +5094,36 @@
// Tag used to report autofill field classification scores
FIELD_AUTOFILL_MATCH_SCORE = 1274;
+ // ACTION: Usb config has been changed to charging
+ // CATEGORY: SETTINGS
+ // OS: P
+ ACTION_USB_CONFIG_CHARGING = 1275;
+
+ // ACTION: Usb config has been changed to mtp (file transfer)
+ // CATEGORY: SETTINGS
+ // OS: P
+ ACTION_USB_CONFIG_MTP = 1276;
+
+ // ACTION: Usb config has been changed to ptp (photo transfer)
+ // CATEGORY: SETTINGS
+ // OS: P
+ ACTION_USB_CONFIG_PTP = 1277;
+
+ // ACTION: Usb config has been changed to rndis (usb tethering)
+ // CATEGORY: SETTINGS
+ // OS: P
+ ACTION_USB_CONFIG_RNDIS = 1278;
+
+ // ACTION: Usb config has been changed to midi
+ // CATEGORY: SETTINGS
+ // OS: P
+ ACTION_USB_CONFIG_MIDI = 1279;
+
+ // ACTION: Usb config has been changed to accessory
+ // CATEGORY: SETTINGS
+ // OS: P
+ ACTION_USB_CONFIG_ACCESSORY = 1280;
+
// ---- End P Constants, all P constants go above this line ----
// Add new aosp constants above this line.
// END OF AOSP CONSTANTS
diff --git a/services/accessibility/java/com/android/server/accessibility/MagnificationGestureHandler.java b/services/accessibility/java/com/android/server/accessibility/MagnificationGestureHandler.java
index 9b2b4eb..a219edb 100644
--- a/services/accessibility/java/com/android/server/accessibility/MagnificationGestureHandler.java
+++ b/services/accessibility/java/com/android/server/accessibility/MagnificationGestureHandler.java
@@ -229,7 +229,7 @@
}
void clearAndTransitionToStateDetecting() {
- mCurrentState = mDelegatingState;
+ mCurrentState = mDetectingState;
mDetectingState.clear();
mViewportDraggingState.clear();
mPanningScalingState.clear();
@@ -649,14 +649,19 @@
break;
case ACTION_MOVE: {
if (isFingerDown()
- && distance(mLastDown, /* move */ event) > mSwipeMinDistance
- // For convenience, viewport dragging on 3tap&hold takes precedence
- // over insta-delegating on 3tap&swipe
- // (which is a rare combo to be used aside from magnification)
- && !isMultiTapTriggered(2 /* taps */)) {
+ && distance(mLastDown, /* move */ event) > mSwipeMinDistance) {
- // Swipe detected - delegate skipping timeout
- transitionToDelegatingStateAndClear();
+ // Swipe detected - transition immediately
+
+ // For convenience, viewport dragging takes precedence
+ // over insta-delegating on 3tap&swipe
+ // (which is a rare combo to be used aside from magnification)
+ if (isMultiTapTriggered(2 /* taps */)) {
+ transitionTo(mViewportDraggingState);
+ clear();
+ } else {
+ transitionToDelegatingStateAndClear();
+ }
}
}
break;
diff --git a/services/backup/java/com/android/server/backup/RefactoredBackupManagerService.java b/services/backup/java/com/android/server/backup/RefactoredBackupManagerService.java
index 3a37459..51c44e1 100644
--- a/services/backup/java/com/android/server/backup/RefactoredBackupManagerService.java
+++ b/services/backup/java/com/android/server/backup/RefactoredBackupManagerService.java
@@ -1424,6 +1424,8 @@
final Intent notification = new Intent();
notification.setAction(BACKUP_FINISHED_ACTION);
notification.setPackage(receiver);
+ notification.addFlags(Intent.FLAG_INCLUDE_STOPPED_PACKAGES |
+ Intent.FLAG_RECEIVER_FOREGROUND);
notification.putExtra(BACKUP_FINISHED_PACKAGE_EXTRA, packageName);
mContext.sendBroadcastAsUser(notification, UserHandle.OWNER);
}
diff --git a/services/core/java/com/android/server/AlarmManagerService.java b/services/core/java/com/android/server/AlarmManagerService.java
index 06cf982..472723d 100644
--- a/services/core/java/com/android/server/AlarmManagerService.java
+++ b/services/core/java/com/android/server/AlarmManagerService.java
@@ -3035,15 +3035,8 @@
Slog.v(TAG, "sending alarm " + alarm);
}
if (RECORD_ALARMS_IN_HISTORY) {
- if (alarm.workSource != null && alarm.workSource.size() > 0) {
- for (int wi=0; wi<alarm.workSource.size(); wi++) {
- ActivityManager.noteAlarmStart(
- alarm.operation, alarm.workSource.get(wi), alarm.statsTag);
- }
- } else {
- ActivityManager.noteAlarmStart(
- alarm.operation, alarm.uid, alarm.statsTag);
- }
+ ActivityManager.noteAlarmStart(alarm.operation, alarm.workSource, alarm.uid,
+ alarm.statsTag);
}
mDeliveryTracker.deliverLocked(alarm, nowELAPSED, allowWhileIdle);
} catch (RuntimeException e) {
@@ -3553,15 +3546,8 @@
fs.aggregateTime += nowELAPSED - fs.startTime;
}
if (RECORD_ALARMS_IN_HISTORY) {
- if (inflight.mWorkSource != null && inflight.mWorkSource.size() > 0) {
- for (int wi=0; wi<inflight.mWorkSource.size(); wi++) {
- ActivityManager.noteAlarmFinish(
- inflight.mPendingIntent, inflight.mWorkSource.get(wi), inflight.mTag);
- }
- } else {
- ActivityManager.noteAlarmFinish(
- inflight.mPendingIntent, inflight.mUid, inflight.mTag);
- }
+ ActivityManager.noteAlarmFinish(inflight.mPendingIntent, inflight.mWorkSource,
+ inflight.mUid, inflight.mTag);
}
}
@@ -3771,18 +3757,9 @@
|| alarm.type == RTC_WAKEUP) {
bs.numWakeup++;
fs.numWakeup++;
- if (alarm.workSource != null && alarm.workSource.size() > 0) {
- for (int wi=0; wi<alarm.workSource.size(); wi++) {
- final String wsName = alarm.workSource.getName(wi);
- ActivityManager.noteWakeupAlarm(
- alarm.operation, alarm.workSource.get(wi),
- (wsName != null) ? wsName : alarm.packageName,
- alarm.statsTag);
- }
- } else {
- ActivityManager.noteWakeupAlarm(
- alarm.operation, alarm.uid, alarm.packageName, alarm.statsTag);
- }
+ ActivityManager.noteWakeupAlarm(
+ alarm.operation, alarm.workSource, alarm.uid, alarm.packageName,
+ alarm.statsTag);
}
}
}
diff --git a/services/core/java/com/android/server/EntropyMixer.java b/services/core/java/com/android/server/EntropyMixer.java
index 9877717..5e6e9d34 100644
--- a/services/core/java/com/android/server/EntropyMixer.java
+++ b/services/core/java/com/android/server/EntropyMixer.java
@@ -196,11 +196,14 @@
* Mixes in the output from HW RNG (if present) into the Linux RNG.
*/
private void addHwRandomEntropy() {
+ if (!new File(hwRandomDevice).exists()) {
+ // HW RNG not present/exposed -- ignore
+ return;
+ }
+
try {
RandomBlock.fromFile(hwRandomDevice).toFile(randomDevice, false);
Slog.i(TAG, "Added HW RNG output to entropy pool");
- } catch (FileNotFoundException ignored) {
- // HW RNG not present/exposed -- ignore
} catch (IOException e) {
Slog.w(TAG, "Failed to add HW RNG output to entropy pool", e);
}
diff --git a/services/core/java/com/android/server/accounts/AccountManagerService.java b/services/core/java/com/android/server/accounts/AccountManagerService.java
index 31aea63..46eea78 100644
--- a/services/core/java/com/android/server/accounts/AccountManagerService.java
+++ b/services/core/java/com/android/server/accounts/AccountManagerService.java
@@ -5595,25 +5595,26 @@
long ident = Binder.clearCallingIdentity();
try {
packages = mPackageManager.getPackagesForUid(callingUid);
+ if (packages != null) {
+ for (String name : packages) {
+ try {
+ PackageInfo packageInfo =
+ mPackageManager.getPackageInfo(name, 0 /* flags */);
+ if (packageInfo != null
+ && (packageInfo.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM)
+ != 0) {
+ return true;
+ }
+ } catch (NameNotFoundException e) {
+ Log.w(TAG, String.format("Could not find package [%s]", name), e);
+ }
+ }
+ } else {
+ Log.w(TAG, "No known packages with uid " + callingUid);
+ }
} finally {
Binder.restoreCallingIdentity(ident);
}
- if (packages != null) {
- for (String name : packages) {
- try {
- PackageInfo packageInfo = mPackageManager.getPackageInfo(name, 0 /* flags */);
- if (packageInfo != null
- && (packageInfo.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM)
- != 0) {
- return true;
- }
- } catch (NameNotFoundException e) {
- Log.w(TAG, String.format("Could not find package [%s]", name), e);
- }
- }
- } else {
- Log.w(TAG, "No known packages with uid " + callingUid);
- }
return false;
}
diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java
index d92b3b8..5936ce1 100644
--- a/services/core/java/com/android/server/am/ActivityManagerService.java
+++ b/services/core/java/com/android/server/am/ActivityManagerService.java
@@ -13858,68 +13858,100 @@
Context.WINDOW_SERVICE)).addView(v, lp);
}
- public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg, String tag) {
- if (sender != null && !(sender instanceof PendingIntentRecord)) {
- return;
+ @Override
+ public void noteWakeupAlarm(IIntentSender sender, WorkSource workSource, int sourceUid,
+ String sourcePkg, String tag) {
+ if (workSource != null && workSource.isEmpty()) {
+ workSource = null;
}
- final PendingIntentRecord rec = (PendingIntentRecord)sender;
- final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
- synchronized (stats) {
- if (mBatteryStatsService.isOnBattery()) {
- mBatteryStatsService.enforceCallingPermission();
- int MY_UID = Binder.getCallingUid();
- final int uid;
- if (sender == null) {
- uid = sourceUid;
- } else {
- uid = rec.uid == MY_UID ? SYSTEM_UID : rec.uid;
+
+ if (sourceUid <= 0 && workSource == null) {
+ // Try and derive a UID to attribute things to based on the caller.
+ if (sender != null) {
+ if (!(sender instanceof PendingIntentRecord)) {
+ return;
}
- BatteryStatsImpl.Uid.Pkg pkg =
- stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid,
- sourcePkg != null ? sourcePkg : rec.key.packageName);
- pkg.noteWakeupAlarmLocked(tag);
- StatsLog.write(StatsLog.WAKEUP_ALARM_OCCURRED, sourceUid >= 0 ? sourceUid : uid,
- tag);
+
+ final PendingIntentRecord rec = (PendingIntentRecord) sender;
+ final int callerUid = Binder.getCallingUid();
+ sourceUid = rec.uid == callerUid ? SYSTEM_UID : rec.uid;
+ } else {
+ // TODO(narayan): Should we throw an exception in this case ? It means that we
+ // haven't been able to derive a UID to attribute things to.
+ return;
}
}
+
+ if (DEBUG_POWER) {
+ Slog.w(TAG, "noteWakupAlarm[ sourcePkg=" + sourcePkg + ", sourceUid=" + sourceUid
+ + ", workSource=" + workSource + ", tag=" + tag + "]");
+ }
+
+ mBatteryStatsService.noteWakupAlarm(sourcePkg, sourceUid, workSource, tag);
}
- public void noteAlarmStart(IIntentSender sender, int sourceUid, String tag) {
- if (sender != null && !(sender instanceof PendingIntentRecord)) {
- return;
+ @Override
+ public void noteAlarmStart(IIntentSender sender, WorkSource workSource, int sourceUid,
+ String tag) {
+ if (workSource != null && workSource.isEmpty()) {
+ workSource = null;
}
- final PendingIntentRecord rec = (PendingIntentRecord)sender;
- final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
- synchronized (stats) {
- mBatteryStatsService.enforceCallingPermission();
- int MY_UID = Binder.getCallingUid();
- final int uid;
- if (sender == null) {
- uid = sourceUid;
+
+ if (sourceUid <= 0 && workSource == null) {
+ // Try and derive a UID to attribute things to based on the caller.
+ if (sender != null) {
+ if (!(sender instanceof PendingIntentRecord)) {
+ return;
+ }
+
+ final PendingIntentRecord rec = (PendingIntentRecord) sender;
+ final int callerUid = Binder.getCallingUid();
+ sourceUid = rec.uid == callerUid ? SYSTEM_UID : rec.uid;
} else {
- uid = rec.uid == MY_UID ? SYSTEM_UID : rec.uid;
+ // TODO(narayan): Should we throw an exception in this case ? It means that we
+ // haven't been able to derive a UID to attribute things to.
+ return;
}
- mBatteryStatsService.noteAlarmStart(tag, sourceUid >= 0 ? sourceUid : uid);
}
+
+ if (DEBUG_POWER) {
+ Slog.w(TAG, "noteAlarmStart[sourceUid=" + sourceUid + ", workSource=" + workSource +
+ ", tag=" + tag + "]");
+ }
+
+ mBatteryStatsService.noteAlarmStart(tag, workSource, sourceUid);
}
- public void noteAlarmFinish(IIntentSender sender, int sourceUid, String tag) {
- if (sender != null && !(sender instanceof PendingIntentRecord)) {
- return;
+ @Override
+ public void noteAlarmFinish(IIntentSender sender, WorkSource workSource, int sourceUid,
+ String tag) {
+ if (workSource != null && workSource.isEmpty()) {
+ workSource = null;
}
- final PendingIntentRecord rec = (PendingIntentRecord)sender;
- final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics();
- synchronized (stats) {
- mBatteryStatsService.enforceCallingPermission();
- int MY_UID = Binder.getCallingUid();
- final int uid;
- if (sender == null) {
- uid = sourceUid;
+
+ if (sourceUid <= 0 && workSource == null) {
+ // Try and derive a UID to attribute things to based on the caller.
+ if (sender != null) {
+ if (!(sender instanceof PendingIntentRecord)) {
+ return;
+ }
+
+ final PendingIntentRecord rec = (PendingIntentRecord) sender;
+ final int callerUid = Binder.getCallingUid();
+ sourceUid = rec.uid == callerUid ? SYSTEM_UID : rec.uid;
} else {
- uid = rec.uid == MY_UID ? SYSTEM_UID : rec.uid;
+ // TODO(narayan): Should we throw an exception in this case ? It means that we
+ // haven't been able to derive a UID to attribute things to.
+ return;
}
- mBatteryStatsService.noteAlarmFinish(tag, sourceUid >= 0 ? sourceUid : uid);
}
+
+ if (DEBUG_POWER) {
+ Slog.w(TAG, "noteAlarmFinish[sourceUid=" + sourceUid + ", workSource=" + workSource +
+ ", tag=" + tag + "]");
+ }
+
+ mBatteryStatsService.noteAlarmFinish(tag, workSource, sourceUid);
}
public boolean killPids(int[] pids, String pReason, boolean secure) {
diff --git a/services/core/java/com/android/server/am/BatteryStatsService.java b/services/core/java/com/android/server/am/BatteryStatsService.java
index 35318f6..430320a 100644
--- a/services/core/java/com/android/server/am/BatteryStatsService.java
+++ b/services/core/java/com/android/server/am/BatteryStatsService.java
@@ -38,6 +38,7 @@
import android.os.UserHandle;
import android.os.UserManagerInternal;
import android.os.WorkSource;
+import android.os.WorkSource.WorkChain;
import android.os.connectivity.CellularBatteryStats;
import android.os.health.HealthStatsParceler;
import android.os.health.HealthStatsWriter;
@@ -66,6 +67,7 @@
import java.nio.charset.CharsetDecoder;
import java.nio.charset.CodingErrorAction;
import java.nio.charset.StandardCharsets;
+import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.concurrent.ExecutionException;
@@ -446,17 +448,24 @@
}
}
- public void noteAlarmStart(String name, int uid) {
+ public void noteWakupAlarm(String name, int uid, WorkSource workSource, String tag) {
enforceCallingPermission();
synchronized (mStats) {
- mStats.noteAlarmStartLocked(name, uid);
+ mStats.noteWakupAlarmLocked(name, uid, workSource, tag);
}
}
- public void noteAlarmFinish(String name, int uid) {
+ public void noteAlarmStart(String name, WorkSource workSource, int uid) {
enforceCallingPermission();
synchronized (mStats) {
- mStats.noteAlarmFinishLocked(name, uid);
+ mStats.noteAlarmStartLocked(name, workSource, uid);
+ }
+ }
+
+ public void noteAlarmFinish(String name, WorkSource workSource, int uid) {
+ enforceCallingPermission();
+ synchronized (mStats) {
+ mStats.noteAlarmFinishLocked(name, workSource, uid);
}
}
diff --git a/services/core/java/com/android/server/connectivity/Vpn.java b/services/core/java/com/android/server/connectivity/Vpn.java
index 7715727..c7a4315 100644
--- a/services/core/java/com/android/server/connectivity/Vpn.java
+++ b/services/core/java/com/android/server/connectivity/Vpn.java
@@ -305,6 +305,7 @@
} else {
for (Network underlying : underlyingNetworks) {
final NetworkCapabilities underlyingCaps = cm.getNetworkCapabilities(underlying);
+ if (underlyingCaps == null) continue;
for (int underlyingType : underlyingCaps.getTransportTypes()) {
transportTypes = ArrayUtils.appendInt(transportTypes, underlyingType);
}
diff --git a/services/core/java/com/android/server/locksettings/recoverablekeystore/PlatformKeyManager.java b/services/core/java/com/android/server/locksettings/recoverablekeystore/PlatformKeyManager.java
index b1db6b1..ef4dbf5 100644
--- a/services/core/java/com/android/server/locksettings/recoverablekeystore/PlatformKeyManager.java
+++ b/services/core/java/com/android/server/locksettings/recoverablekeystore/PlatformKeyManager.java
@@ -116,16 +116,12 @@
/**
* Returns the current generation ID of the platform key. This increments whenever a platform
* key has to be replaced. (e.g., because the user has removed and then re-added their lock
- * screen).
+ * screen). Returns -1 if no key has been generated yet.
*
* @hide
*/
public int getGenerationId() {
- int generationId = mDatabase.getPlatformKeyGenerationId(mUserId);
- if (generationId == -1) {
- return 1;
- }
- return generationId;
+ return mDatabase.getPlatformKeyGenerationId(mUserId);
}
/**
@@ -208,14 +204,22 @@
Locale.US, "Platform key generation %d exists already.", generationId));
return;
}
- if (generationId == 1) {
+ if (generationId == -1) {
Log.i(TAG, "Generating initial platform ID.");
} else {
Log.w(TAG, String.format(Locale.US, "Platform generation ID was %d but no "
+ "entry was present in AndroidKeyStore. Generating fresh key.", generationId));
}
+ if (generationId == -1) {
+ generationId = 1;
+ } else {
+ // Had to generate a fresh key, bump the generation id
+ generationId++;
+ }
+
generateAndLoadKey(generationId);
+ mDatabase.setPlatformKeyGenerationId(mUserId, generationId);
}
/**
diff --git a/services/core/java/com/android/server/locksettings/recoverablekeystore/RecoverableKeyStoreManager.java b/services/core/java/com/android/server/locksettings/recoverablekeystore/RecoverableKeyStoreManager.java
index fe1cad4..eccf241 100644
--- a/services/core/java/com/android/server/locksettings/recoverablekeystore/RecoverableKeyStoreManager.java
+++ b/services/core/java/com/android/server/locksettings/recoverablekeystore/RecoverableKeyStoreManager.java
@@ -216,7 +216,6 @@
// Any application should be able to check status for its own keys.
// If caller is a recovery agent it can check statuses for other packages, but
// only for recoverable keys it manages.
- checkRecoverKeyStorePermission();
return mDatabase.getStatusForAllKeys(Binder.getCallingUid());
}
diff --git a/services/core/java/com/android/server/net/watchlist/NetworkWatchlistService.java b/services/core/java/com/android/server/net/watchlist/NetworkWatchlistService.java
index 171703a..f35e6ec 100644
--- a/services/core/java/com/android/server/net/watchlist/NetworkWatchlistService.java
+++ b/services/core/java/com/android/server/net/watchlist/NetworkWatchlistService.java
@@ -33,6 +33,7 @@
import android.util.Slog;
import com.android.internal.R;
+import com.android.internal.annotations.GuardedBy;
import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.util.DumpUtils;
import com.android.internal.net.INetworkWatchlistManager;
@@ -92,6 +93,7 @@
}
}
+ @GuardedBy("mLoggingSwitchLock")
private volatile boolean mIsLoggingEnabled = false;
private final Object mLoggingSwitchLock = new Object();
@@ -220,36 +222,11 @@
}
}
- /**
- * Set a new network watchlist.
- * This method should be called by ConfigUpdater only.
- *
- * @return True if network watchlist is updated.
- */
- public boolean setNetworkSecurityWatchlist(List<byte[]> domainsCrc32Digests,
- List<byte[]> domainsSha256Digests,
- List<byte[]> ipAddressesCrc32Digests,
- List<byte[]> ipAddressesSha256Digests) {
- Slog.i(TAG, "Setting network watchlist");
- if (domainsCrc32Digests == null || domainsSha256Digests == null
- || ipAddressesCrc32Digests == null || ipAddressesSha256Digests == null) {
- Slog.e(TAG, "Parameters cannot be null");
- return false;
- }
- if (domainsCrc32Digests.size() != domainsSha256Digests.size()
- || ipAddressesCrc32Digests.size() != ipAddressesSha256Digests.size()) {
- Slog.e(TAG, "Must need to have the same number of CRC32 and SHA256 digests");
- return false;
- }
- if (domainsSha256Digests.size() + ipAddressesSha256Digests.size()
- > MAX_NUM_OF_WATCHLIST_DIGESTS) {
- Slog.e(TAG, "Total watchlist size cannot exceed " + MAX_NUM_OF_WATCHLIST_DIGESTS);
- return false;
- }
- mSettings.writeSettingsToDisk(domainsCrc32Digests, domainsSha256Digests,
- ipAddressesCrc32Digests, ipAddressesSha256Digests);
- Slog.i(TAG, "Set network watchlist: Success");
- return true;
+ @Override
+ public void reloadWatchlist() throws RemoteException {
+ enforceWatchlistLoggingPermission();
+ Slog.i(TAG, "Reloading watchlist");
+ mSettings.reloadSettings();
}
@Override
diff --git a/services/core/java/com/android/server/net/watchlist/WatchlistReportDbHelper.java b/services/core/java/com/android/server/net/watchlist/WatchlistReportDbHelper.java
index f48463f..838aa53 100644
--- a/services/core/java/com/android/server/net/watchlist/WatchlistReportDbHelper.java
+++ b/services/core/java/com/android/server/net/watchlist/WatchlistReportDbHelper.java
@@ -21,10 +21,12 @@
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
+import android.os.Environment;
import android.util.Pair;
import com.android.internal.util.HexDump;
+import java.io.File;
import java.util.ArrayList;
import java.util.GregorianCalendar;
import java.util.HashMap;
@@ -83,9 +85,12 @@
HashMap<String, String> appDigestCNCList;
}
+ static File getSystemWatchlistDbFile() {
+ return new File(Environment.getDataSystemDirectory(), NAME);
+ }
+
private WatchlistReportDbHelper(Context context) {
- super(context, WatchlistSettings.getSystemWatchlistFile(NAME).getAbsolutePath(),
- null, VERSION);
+ super(context, getSystemWatchlistDbFile().getAbsolutePath(), null, VERSION);
// Memory optimization - close idle connections after 30s of inactivity
setIdleConnectionTimeout(IDLE_CONNECTION_TIMEOUT_MS);
}
diff --git a/services/core/java/com/android/server/net/watchlist/WatchlistSettings.java b/services/core/java/com/android/server/net/watchlist/WatchlistSettings.java
index c50f0d5..70002ea 100644
--- a/services/core/java/com/android/server/net/watchlist/WatchlistSettings.java
+++ b/services/core/java/com/android/server/net/watchlist/WatchlistSettings.java
@@ -19,8 +19,10 @@
import android.os.Environment;
import android.util.AtomicFile;
import android.util.Log;
+import android.util.Slog;
import android.util.Xml;
+import com.android.internal.annotations.GuardedBy;
import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.util.FastXmlSerializer;
import com.android.internal.util.HexDump;
@@ -51,10 +53,9 @@
class WatchlistSettings {
private static final String TAG = "WatchlistSettings";
- // Settings xml will be stored in /data/system/network_watchlist/watchlist_settings.xml
- static final String SYSTEM_WATCHLIST_DIR = "network_watchlist";
-
- private static final String WATCHLIST_XML_FILE = "watchlist_settings.xml";
+ // Watchlist config that pushed by ConfigUpdater.
+ private static final String NETWORK_WATCHLIST_DB_PATH =
+ "/data/misc/network_watchlist/network_watchlist.xml";
private static class XmlTags {
private static final String WATCHLIST_SETTINGS = "watchlist-settings";
@@ -65,86 +66,74 @@
private static final String HASH = "hash";
}
- private static WatchlistSettings sInstance = new WatchlistSettings();
- private final AtomicFile mXmlFile;
- private final Object mLock = new Object();
- private HarmfulDigests mCrc32DomainDigests = new HarmfulDigests(new ArrayList<>());
- private HarmfulDigests mSha256DomainDigests = new HarmfulDigests(new ArrayList<>());
- private HarmfulDigests mCrc32IpDigests = new HarmfulDigests(new ArrayList<>());
- private HarmfulDigests mSha256IpDigests = new HarmfulDigests(new ArrayList<>());
+ private static class CrcShaDigests {
+ final HarmfulDigests crc32Digests;
+ final HarmfulDigests sha256Digests;
- public static synchronized WatchlistSettings getInstance() {
+ public CrcShaDigests(HarmfulDigests crc32Digests, HarmfulDigests sha256Digests) {
+ this.crc32Digests = crc32Digests;
+ this.sha256Digests = sha256Digests;
+ }
+ }
+
+ private final static WatchlistSettings sInstance = new WatchlistSettings();
+ private final AtomicFile mXmlFile;
+
+ private volatile CrcShaDigests mDomainDigests;
+ private volatile CrcShaDigests mIpDigests;
+
+ public static WatchlistSettings getInstance() {
return sInstance;
}
private WatchlistSettings() {
- this(getSystemWatchlistFile(WATCHLIST_XML_FILE));
+ this(new File(NETWORK_WATCHLIST_DB_PATH));
}
@VisibleForTesting
protected WatchlistSettings(File xmlFile) {
mXmlFile = new AtomicFile(xmlFile);
- readSettingsLocked();
+ reloadSettings();
}
- static File getSystemWatchlistFile(String filename) {
- final File dataSystemDir = Environment.getDataSystemDirectory();
- final File systemWatchlistDir = new File(dataSystemDir, SYSTEM_WATCHLIST_DIR);
- systemWatchlistDir.mkdirs();
- return new File(systemWatchlistDir, filename);
- }
-
- private void readSettingsLocked() {
- synchronized (mLock) {
- FileInputStream stream;
- try {
- stream = mXmlFile.openRead();
- } catch (FileNotFoundException e) {
- Log.i(TAG, "No watchlist settings: " + mXmlFile.getBaseFile().getAbsolutePath());
- return;
- }
+ public void reloadSettings() {
+ try (FileInputStream stream = mXmlFile.openRead()){
final List<byte[]> crc32DomainList = new ArrayList<>();
final List<byte[]> sha256DomainList = new ArrayList<>();
final List<byte[]> crc32IpList = new ArrayList<>();
final List<byte[]> sha256IpList = new ArrayList<>();
- try {
- XmlPullParser parser = Xml.newPullParser();
- parser.setInput(stream, StandardCharsets.UTF_8.name());
- parser.nextTag();
- parser.require(XmlPullParser.START_TAG, null, XmlTags.WATCHLIST_SETTINGS);
- while (parser.nextTag() == XmlPullParser.START_TAG) {
- String tagName = parser.getName();
- switch (tagName) {
- case XmlTags.CRC32_DOMAIN:
- parseHash(parser, tagName, crc32DomainList);
- break;
- case XmlTags.CRC32_IP:
- parseHash(parser, tagName, crc32IpList);
- break;
- case XmlTags.SHA256_DOMAIN:
- parseHash(parser, tagName, sha256DomainList);
- break;
- case XmlTags.SHA256_IP:
- parseHash(parser, tagName, sha256IpList);
- break;
- default:
- Log.w(TAG, "Unknown element: " + parser.getName());
- XmlUtils.skipCurrentTag(parser);
- }
- }
- parser.require(XmlPullParser.END_TAG, null, XmlTags.WATCHLIST_SETTINGS);
- writeSettingsToMemory(crc32DomainList, sha256DomainList, crc32IpList, sha256IpList);
- } catch (IllegalStateException | NullPointerException | NumberFormatException |
- XmlPullParserException | IOException | IndexOutOfBoundsException e) {
- Log.w(TAG, "Failed parsing " + e);
- } finally {
- try {
- stream.close();
- } catch (IOException e) {
+ XmlPullParser parser = Xml.newPullParser();
+ parser.setInput(stream, StandardCharsets.UTF_8.name());
+ parser.nextTag();
+ parser.require(XmlPullParser.START_TAG, null, XmlTags.WATCHLIST_SETTINGS);
+ while (parser.nextTag() == XmlPullParser.START_TAG) {
+ String tagName = parser.getName();
+ switch (tagName) {
+ case XmlTags.CRC32_DOMAIN:
+ parseHash(parser, tagName, crc32DomainList);
+ break;
+ case XmlTags.CRC32_IP:
+ parseHash(parser, tagName, crc32IpList);
+ break;
+ case XmlTags.SHA256_DOMAIN:
+ parseHash(parser, tagName, sha256DomainList);
+ break;
+ case XmlTags.SHA256_IP:
+ parseHash(parser, tagName, sha256IpList);
+ break;
+ default:
+ Log.w(TAG, "Unknown element: " + parser.getName());
+ XmlUtils.skipCurrentTag(parser);
}
}
+ parser.require(XmlPullParser.END_TAG, null, XmlTags.WATCHLIST_SETTINGS);
+ writeSettingsToMemory(crc32DomainList, sha256DomainList, crc32IpList, sha256IpList);
+ Log.i(TAG, "Reload watchlist done");
+ } catch (IllegalStateException | NullPointerException | NumberFormatException |
+ XmlPullParserException | IOException | IndexOutOfBoundsException e) {
+ Slog.e(TAG, "Failed parsing xml", e);
}
}
@@ -161,101 +150,61 @@
}
/**
- * Write network watchlist settings to disk.
- * Adb should not use it, should use writeSettingsToMemory directly instead.
- */
- public void writeSettingsToDisk(List<byte[]> newCrc32DomainList,
- List<byte[]> newSha256DomainList,
- List<byte[]> newCrc32IpList,
- List<byte[]> newSha256IpList) {
- synchronized (mLock) {
- FileOutputStream stream;
- try {
- stream = mXmlFile.startWrite();
- } catch (IOException e) {
- Log.w(TAG, "Failed to write display settings: " + e);
- return;
- }
-
- try {
- XmlSerializer out = new FastXmlSerializer();
- out.setOutput(stream, StandardCharsets.UTF_8.name());
- out.startDocument(null, true);
- out.startTag(null, XmlTags.WATCHLIST_SETTINGS);
-
- writeHashSetToXml(out, XmlTags.SHA256_DOMAIN, newSha256DomainList);
- writeHashSetToXml(out, XmlTags.SHA256_IP, newSha256IpList);
- writeHashSetToXml(out, XmlTags.CRC32_DOMAIN, newCrc32DomainList);
- writeHashSetToXml(out, XmlTags.CRC32_IP, newCrc32IpList);
-
- out.endTag(null, XmlTags.WATCHLIST_SETTINGS);
- out.endDocument();
- mXmlFile.finishWrite(stream);
- writeSettingsToMemory(newCrc32DomainList, newSha256DomainList, newCrc32IpList,
- newSha256IpList);
- } catch (IOException e) {
- Log.w(TAG, "Failed to write display settings, restoring backup.", e);
- mXmlFile.failWrite(stream);
- }
- }
- }
-
- /**
* Write network watchlist settings to memory.
*/
public void writeSettingsToMemory(List<byte[]> newCrc32DomainList,
List<byte[]> newSha256DomainList,
List<byte[]> newCrc32IpList,
List<byte[]> newSha256IpList) {
- synchronized (mLock) {
- mCrc32DomainDigests = new HarmfulDigests(newCrc32DomainList);
- mCrc32IpDigests = new HarmfulDigests(newCrc32IpList);
- mSha256DomainDigests = new HarmfulDigests(newSha256DomainList);
- mSha256IpDigests = new HarmfulDigests(newSha256IpList);
- }
- }
-
- private static void writeHashSetToXml(XmlSerializer out, String tagName, List<byte[]> hashSet)
- throws IOException {
- out.startTag(null, tagName);
- for (byte[] hash : hashSet) {
- out.startTag(null, XmlTags.HASH);
- out.text(HexDump.toHexString(hash));
- out.endTag(null, XmlTags.HASH);
- }
- out.endTag(null, tagName);
+ mDomainDigests = new CrcShaDigests(new HarmfulDigests(newCrc32DomainList),
+ new HarmfulDigests(newSha256DomainList));
+ mIpDigests = new CrcShaDigests(new HarmfulDigests(newCrc32IpList),
+ new HarmfulDigests(newSha256IpList));
}
public boolean containsDomain(String domain) {
+ final CrcShaDigests domainDigests = mDomainDigests;
+ if (domainDigests == null) {
+ Slog.wtf(TAG, "domainDigests should not be null");
+ return false;
+ }
// First it does a quick CRC32 check.
final byte[] crc32 = getCrc32(domain);
- if (!mCrc32DomainDigests.contains(crc32)) {
+ if (!domainDigests.crc32Digests.contains(crc32)) {
return false;
}
// Now we do a slow SHA256 check.
final byte[] sha256 = getSha256(domain);
- return mSha256DomainDigests.contains(sha256);
+ return domainDigests.sha256Digests.contains(sha256);
}
public boolean containsIp(String ip) {
+ final CrcShaDigests ipDigests = mIpDigests;
+ if (ipDigests == null) {
+ Slog.wtf(TAG, "ipDigests should not be null");
+ return false;
+ }
// First it does a quick CRC32 check.
final byte[] crc32 = getCrc32(ip);
- if (!mCrc32IpDigests.contains(crc32)) {
+ if (!ipDigests.crc32Digests.contains(crc32)) {
return false;
}
// Now we do a slow SHA256 check.
final byte[] sha256 = getSha256(ip);
- return mSha256IpDigests.contains(sha256);
+ return ipDigests.sha256Digests.contains(sha256);
}
- /** Get CRC32 of a string */
+ /** Get CRC32 of a string
+ *
+ * TODO: Review if we should use CRC32 or other algorithms
+ */
private byte[] getCrc32(String str) {
final CRC32 crc = new CRC32();
crc.update(str.getBytes());
final long tmp = crc.getValue();
- return new byte[]{(byte)(tmp >> 24 & 255), (byte)(tmp >> 16 & 255),
- (byte)(tmp >> 8 & 255), (byte)(tmp & 255)};
+ return new byte[]{(byte) (tmp >> 24 & 255), (byte) (tmp >> 16 & 255),
+ (byte) (tmp >> 8 & 255), (byte) (tmp & 255)};
}
/** Get SHA256 of a string */
@@ -273,12 +222,12 @@
public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
pw.println("Domain CRC32 digest list:");
- mCrc32DomainDigests.dump(fd, pw, args);
+ mDomainDigests.crc32Digests.dump(fd, pw, args);
pw.println("Domain SHA256 digest list:");
- mSha256DomainDigests.dump(fd, pw, args);
+ mDomainDigests.sha256Digests.dump(fd, pw, args);
pw.println("Ip CRC32 digest list:");
- mCrc32IpDigests.dump(fd, pw, args);
+ mIpDigests.crc32Digests.dump(fd, pw, args);
pw.println("Ip SHA256 digest list:");
- mSha256IpDigests.dump(fd, pw, args);
+ mIpDigests.sha256Digests.dump(fd, pw, args);
}
}
diff --git a/services/core/java/com/android/server/power/PowerManagerService.java b/services/core/java/com/android/server/power/PowerManagerService.java
index 02c8f68..bc7f2e6 100644
--- a/services/core/java/com/android/server/power/PowerManagerService.java
+++ b/services/core/java/com/android/server/power/PowerManagerService.java
@@ -57,6 +57,7 @@
import android.os.UserHandle;
import android.os.UserManager;
import android.os.WorkSource;
+import android.os.WorkSource.WorkChain;
import android.provider.Settings;
import android.provider.Settings.SettingNotFoundException;
import android.service.dreams.DreamManagerInternal;
@@ -1976,6 +1977,16 @@
return true;
}
}
+
+ final ArrayList<WorkChain> workChains = wakeLock.mWorkSource.getWorkChains();
+ if (workChains != null) {
+ for (int k = 0; k < workChains.size(); k++) {
+ final int uid = workChains.get(k).getAttributionUid();
+ if (userId == UserHandle.getUserId(uid)) {
+ return true;
+ }
+ }
+ }
}
return userId == UserHandle.getUserId(wakeLock.mOwnerUid);
}
diff --git a/services/core/java/com/android/server/updates/NetworkWatchlistInstallReceiver.java b/services/core/java/com/android/server/updates/NetworkWatchlistInstallReceiver.java
new file mode 100644
index 0000000..3b7ddc2
--- /dev/null
+++ b/services/core/java/com/android/server/updates/NetworkWatchlistInstallReceiver.java
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2017 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.
+ */
+
+package com.android.server.updates;
+
+import android.content.Context;
+import android.content.Intent;
+import android.net.NetworkWatchlistManager;
+import android.os.RemoteException;
+import android.util.Slog;
+
+public class NetworkWatchlistInstallReceiver extends ConfigUpdateInstallReceiver {
+
+ public NetworkWatchlistInstallReceiver() {
+ super("/data/misc/network_watchlist/", "network_watchlist.xml", "metadata/", "version");
+ }
+
+ @Override
+ protected void postInstall(Context context, Intent intent) {
+ try {
+ context.getSystemService(NetworkWatchlistManager.class).reloadWatchlist();
+ } catch (Exception e) {
+ // Network Watchlist is not available
+ Slog.wtf("NetworkWatchlistInstallReceiver", "Unable to reload watchlist");
+ }
+ }
+}
diff --git a/services/core/java/com/android/server/wm/WindowState.java b/services/core/java/com/android/server/wm/WindowState.java
index dfb385b..863922f 100644
--- a/services/core/java/com/android/server/wm/WindowState.java
+++ b/services/core/java/com/android/server/wm/WindowState.java
@@ -2222,12 +2222,13 @@
mWinAnimator + ": " + mPolicyVisibilityAfterAnim);
}
mPolicyVisibility = mPolicyVisibilityAfterAnim;
- setDisplayLayoutNeeded();
if (!mPolicyVisibility) {
+ mWinAnimator.hide("checkPolicyVisibilityChange");
if (mService.mCurrentFocus == this) {
if (DEBUG_FOCUS_LIGHT) Slog.i(TAG,
"setAnimationLocked: setting mFocusMayChange true");
mService.mFocusMayChange = true;
+ setDisplayLayoutNeeded();
}
// Window is no longer visible -- make sure if we were waiting
// for it to be displayed before enabling the display, that
@@ -4291,8 +4292,22 @@
float9[Matrix.MSKEW_Y] = mWinAnimator.mDtDx;
float9[Matrix.MSKEW_X] = mWinAnimator.mDtDy;
float9[Matrix.MSCALE_Y] = mWinAnimator.mDsDy;
- float9[Matrix.MTRANS_X] = mSurfacePosition.x + mShownPosition.x;
- float9[Matrix.MTRANS_Y] = mSurfacePosition.y + mShownPosition.y;
+ int x = mSurfacePosition.x + mShownPosition.x;
+ int y = mSurfacePosition.y + mShownPosition.y;
+
+ // If changed, also adjust transformFrameToSurfacePosition
+ final WindowContainer parent = getParent();
+ if (isChildWindow()) {
+ final WindowState parentWindow = getParentWindow();
+ x += parentWindow.mFrame.left - parentWindow.mAttrs.surfaceInsets.left;
+ y += parentWindow.mFrame.top - parentWindow.mAttrs.surfaceInsets.top;
+ } else if (parent != null) {
+ final Rect parentBounds = parent.getBounds();
+ x += parentBounds.left;
+ y += parentBounds.top;
+ }
+ float9[Matrix.MTRANS_X] = x;
+ float9[Matrix.MTRANS_Y] = y;
float9[Matrix.MPERSP_0] = 0;
float9[Matrix.MPERSP_1] = 0;
float9[Matrix.MPERSP_2] = 1;
@@ -4439,6 +4454,8 @@
private void transformFrameToSurfacePosition(int left, int top, Point outPoint) {
outPoint.set(left, top);
+
+ // If changed, also adjust getTransformationMatrix
final WindowContainer parentWindowContainer = getParent();
if (isChildWindow()) {
// TODO: This probably falls apart at some point and we should
diff --git a/services/tests/servicestests/src/com/android/server/accessibility/MagnificationGestureHandlerTest.java b/services/tests/servicestests/src/com/android/server/accessibility/MagnificationGestureHandlerTest.java
index 8a54c4e..8d5556e 100644
--- a/services/tests/servicestests/src/com/android/server/accessibility/MagnificationGestureHandlerTest.java
+++ b/services/tests/servicestests/src/com/android/server/accessibility/MagnificationGestureHandlerTest.java
@@ -32,6 +32,7 @@
import android.annotation.NonNull;
import android.content.Context;
+import android.os.Message;
import android.support.test.InstrumentationRegistry;
import android.support.test.runner.AndroidJUnit4;
import android.util.DebugUtils;
@@ -48,6 +49,34 @@
import java.util.function.IntConsumer;
+/**
+ * Tests the state transitions of {@link MagnificationGestureHandler}
+ *
+ * Here's a dot graph describing the transitions being tested:
+ * {@code
+ * digraph {
+ * IDLE -> SHORTCUT_TRIGGERED [label="a11y\nbtn"]
+ * SHORTCUT_TRIGGERED -> IDLE [label="a11y\nbtn"]
+ * IDLE -> DOUBLE_TAP [label="2tap"]
+ * DOUBLE_TAP -> IDLE [label="timeout"]
+ * DOUBLE_TAP -> TRIPLE_TAP_AND_HOLD [label="down"]
+ * SHORTCUT_TRIGGERED -> TRIPLE_TAP_AND_HOLD [label="down"]
+ * TRIPLE_TAP_AND_HOLD -> ZOOMED [label="up"]
+ * TRIPLE_TAP_AND_HOLD -> DRAGGING_TMP [label="hold/\nswipe"]
+ * DRAGGING_TMP -> IDLE [label="release"]
+ * ZOOMED -> ZOOMED_DOUBLE_TAP [label="2tap"]
+ * ZOOMED_DOUBLE_TAP -> ZOOMED [label="timeout"]
+ * ZOOMED_DOUBLE_TAP -> DRAGGING [label="hold"]
+ * ZOOMED_DOUBLE_TAP -> IDLE [label="tap"]
+ * DRAGGING -> ZOOMED [label="release"]
+ * ZOOMED -> IDLE [label="a11y\nbtn"]
+ * ZOOMED -> PANNING [label="2hold"]
+ * PANNING -> PANNING_SCALING [label="pinch"]
+ * PANNING_SCALING -> ZOOMED [label="release"]
+ * PANNING -> ZOOMED [label="release"]
+ * }
+ * }
+ */
@RunWith(AndroidJUnit4.class)
public class MagnificationGestureHandlerTest {
@@ -76,6 +105,8 @@
private MagnificationGestureHandler mMgh;
private TestHandler mHandler;
+ private long mLastDownTime = Integer.MIN_VALUE;
+
@Before
public void setUp() {
mContext = InstrumentationRegistry.getContext();
@@ -104,7 +135,13 @@
MagnificationGestureHandler h = new MagnificationGestureHandler(
mContext, mMagnificationController,
detectTripleTap, detectShortcutTrigger);
- mHandler = new TestHandler(h.mDetectingState, mClock);
+ mHandler = new TestHandler(h.mDetectingState, mClock) {
+ @Override
+ protected String messageToString(Message m) {
+ return DebugUtils.valueToString(
+ MagnificationGestureHandler.DetectingState.class, "MESSAGE_", m.what);
+ }
+ };
h.mDetectingState.mHandler = mHandler;
h.setNext(strictMock(EventStreamTransformation.class));
return h;
@@ -184,11 +221,11 @@
fastForward1sec();
}, STATE_ZOOMED);
- // tap+tap+swipe gets delegated
- assertTransition(STATE_2TAPS, () -> {
- allowEventDelegation();
- swipe();
- }, STATE_IDLE);
+ // tap+tap+swipe doesn't get delegated
+ assertTransition(STATE_2TAPS, () -> swipe(), STATE_IDLE);
+
+ // tap+tap+swipe initiates viewport dragging immediately
+ assertTransition(STATE_2TAPS, () -> swipeAndHold(), STATE_DRAGGING_TMP);
}
@Test
@@ -439,23 +476,24 @@
}
private void tap() {
- MotionEvent downEvent = downEvent();
- send(downEvent);
- send(upEvent(downEvent.getDownTime()));
+ send(downEvent());
+ send(upEvent());
}
private void swipe() {
- MotionEvent downEvent = downEvent();
- send(downEvent);
+ swipeAndHold();
+ send(upEvent());
+ }
+
+ private void swipeAndHold() {
+ send(downEvent());
send(moveEvent(DEFAULT_X * 2, DEFAULT_Y * 2));
- send(upEvent(downEvent.getDownTime()));
}
private void longTap() {
- MotionEvent downEvent = downEvent();
- send(downEvent);
+ send(downEvent());
fastForward(2000);
- send(upEvent(downEvent.getDownTime()));
+ send(upEvent());
}
private void triggerShortcut() {
@@ -473,16 +511,17 @@
}
private MotionEvent moveEvent(float x, float y) {
- return MotionEvent.obtain(defaultDownTime(), mClock.now(), ACTION_MOVE, x, y, 0);
+ return MotionEvent.obtain(mLastDownTime, mClock.now(), ACTION_MOVE, x, y, 0);
}
private MotionEvent downEvent() {
- return MotionEvent.obtain(mClock.now(), mClock.now(),
+ mLastDownTime = mClock.now();
+ return MotionEvent.obtain(mLastDownTime, mLastDownTime,
ACTION_DOWN, DEFAULT_X, DEFAULT_Y, 0);
}
private MotionEvent upEvent() {
- return upEvent(defaultDownTime());
+ return upEvent(mLastDownTime);
}
private MotionEvent upEvent(long downTime) {
@@ -490,11 +529,6 @@
MotionEvent.ACTION_UP, DEFAULT_X, DEFAULT_Y, 0);
}
- private long defaultDownTime() {
- MotionEvent lastDown = mMgh.mDetectingState.mLastDown;
- return lastDown == null ? mClock.now() - 1 : lastDown.getDownTime();
- }
-
private MotionEvent pointerEvent(int action, float x, float y) {
MotionEvent.PointerProperties defPointerProperties = new MotionEvent.PointerProperties();
defPointerProperties.id = 0;
diff --git a/services/tests/servicestests/src/com/android/server/locksettings/recoverablekeystore/PlatformKeyManagerTest.java b/services/tests/servicestests/src/com/android/server/locksettings/recoverablekeystore/PlatformKeyManagerTest.java
index 6f13a98..97fbca2 100644
--- a/services/tests/servicestests/src/com/android/server/locksettings/recoverablekeystore/PlatformKeyManagerTest.java
+++ b/services/tests/servicestests/src/com/android/server/locksettings/recoverablekeystore/PlatformKeyManagerTest.java
@@ -205,6 +205,14 @@
}
@Test
+ public void init_savesGenerationIdToDatabase() throws Exception {
+ mPlatformKeyManager.init();
+
+ assertEquals(1,
+ mRecoverableKeyStoreDb.getPlatformKeyGenerationId(USER_ID_FIXTURE));
+ }
+
+ @Test
public void init_setsGenerationIdTo1() throws Exception {
mPlatformKeyManager.init();
@@ -212,7 +220,38 @@
}
@Test
+ public void init_incrementsGenerationIdIfKeyIsUnavailable() throws Exception {
+ mPlatformKeyManager.init();
+
+ mPlatformKeyManager.init();
+
+ assertEquals(2, mPlatformKeyManager.getGenerationId());
+ }
+
+ @Test
+ public void init_doesNotIncrementGenerationIdIfKeyAvailable() throws Exception {
+ mPlatformKeyManager.init();
+ when(mKeyStoreProxy
+ .containsAlias("com.android.server.locksettings.recoverablekeystore/"
+ + "platform/42/1/decrypt")).thenReturn(true);
+ when(mKeyStoreProxy
+ .containsAlias("com.android.server.locksettings.recoverablekeystore/"
+ + "platform/42/1/encrypt")).thenReturn(true);
+
+ mPlatformKeyManager.init();
+
+ assertEquals(1, mPlatformKeyManager.getGenerationId());
+ }
+
+ @Test
+ public void getGenerationId_returnsMinusOneIfNotInitialized() throws Exception {
+ assertEquals(-1, mPlatformKeyManager.getGenerationId());
+ }
+
+ @Test
public void getDecryptKey_getsDecryptKeyWithCorrectAlias() throws Exception {
+ mPlatformKeyManager.init();
+
mPlatformKeyManager.getDecryptKey();
verify(mKeyStoreProxy).getKey(
@@ -222,6 +261,8 @@
@Test
public void getEncryptKey_getsDecryptKeyWithCorrectAlias() throws Exception {
+ mPlatformKeyManager.init();
+
mPlatformKeyManager.getEncryptKey();
verify(mKeyStoreProxy).getKey(
diff --git a/services/tests/servicestests/src/com/android/server/net/watchlist/WatchlistSettingsTests.java b/services/tests/servicestests/src/com/android/server/net/watchlist/WatchlistSettingsTests.java
index f3cb980..212d25d 100644
--- a/services/tests/servicestests/src/com/android/server/net/watchlist/WatchlistSettingsTests.java
+++ b/services/tests/servicestests/src/com/android/server/net/watchlist/WatchlistSettingsTests.java
@@ -95,41 +95,6 @@
}
@Test
- public void testWatchlistSettings_writeSettingsToDisk() throws Exception {
- copyWatchlistSettingsXml(mContext, TEST_XML_1, mTestXmlFile);
- WatchlistSettings settings = new WatchlistSettings(mTestXmlFile);
- settings.writeSettingsToDisk(Arrays.asList(TEST_NEW_CC_DOMAIN_CRC32),
- Arrays.asList(TEST_NEW_CC_DOMAIN_SHA256), Arrays.asList(TEST_NEW_CC_IP_CRC32),
- Arrays.asList(TEST_NEW_CC_IP_SHA256));
- // Ensure old watchlist is not in memory
- assertFalse(settings.containsDomain(TEST_CC_DOMAIN));
- assertFalse(settings.containsIp(TEST_CC_IP));
- assertFalse(settings.containsDomain(TEST_NOT_EXIST_CC_DOMAIN));
- assertFalse(settings.containsIp(TEST_NOT_EXIST_CC_IP));
- assertFalse(settings.containsDomain(TEST_SHA256_ONLY_DOMAIN));
- assertFalse(settings.containsIp(TEST_SHA256_ONLY_IP));
- assertFalse(settings.containsDomain(TEST_CRC32_ONLY_DOMAIN));
- assertFalse(settings.containsIp(TEST_CRC32_ONLY_IP));
- // Ensure new watchlist is in memory
- assertTrue(settings.containsDomain(TEST_NEW_CC_DOMAIN));
- assertTrue(settings.containsIp(TEST_NEW_CC_IP));
- // Reload settings from disk and test again
- settings = new WatchlistSettings(mTestXmlFile);
- // Ensure old watchlist is not in memory
- assertFalse(settings.containsDomain(TEST_CC_DOMAIN));
- assertFalse(settings.containsIp(TEST_CC_IP));
- assertFalse(settings.containsDomain(TEST_NOT_EXIST_CC_DOMAIN));
- assertFalse(settings.containsIp(TEST_NOT_EXIST_CC_IP));
- assertFalse(settings.containsDomain(TEST_SHA256_ONLY_DOMAIN));
- assertFalse(settings.containsIp(TEST_SHA256_ONLY_IP));
- assertFalse(settings.containsDomain(TEST_CRC32_ONLY_DOMAIN));
- assertFalse(settings.containsIp(TEST_CRC32_ONLY_IP));
- // Ensure new watchlist is in memory
- assertTrue(settings.containsDomain(TEST_NEW_CC_DOMAIN));
- assertTrue(settings.containsIp(TEST_NEW_CC_IP));
- }
-
- @Test
public void testWatchlistSettings_writeSettingsToMemory() throws Exception {
copyWatchlistSettingsXml(mContext, TEST_XML_1, mTestXmlFile);
WatchlistSettings settings = new WatchlistSettings(mTestXmlFile);
diff --git a/services/tests/servicestests/src/com/android/server/testutils/TestHandler.java b/services/tests/servicestests/src/com/android/server/testutils/TestHandler.java
index 2d4bc0f..029d9f1 100644
--- a/services/tests/servicestests/src/com/android/server/testutils/TestHandler.java
+++ b/services/tests/servicestests/src/com/android/server/testutils/TestHandler.java
@@ -104,6 +104,15 @@
return new PriorityQueue<>(mMessages);
}
+ /**
+ * Optionally-overridable to allow deciphering message types
+ *
+ * @see android.util.DebugUtils#valueToString - a handy utility to use when overriding this
+ */
+ protected String messageToString(Message message) {
+ return message.toString();
+ }
+
private void dispatch(MsgInfo msg) {
int msgId = msg.message.what;
@@ -148,7 +157,7 @@
@Override
public String toString() {
return "MsgInfo{" +
- "message=" + message +
+ "message=" + messageToString(message) +
", sendTime=" + sendTime +
'}';
}
diff --git a/tests/DexLoggerIntegrationTests/Android.mk b/tests/DexLoggerIntegrationTests/Android.mk
new file mode 100644
index 0000000..7187a37
--- /dev/null
+++ b/tests/DexLoggerIntegrationTests/Android.mk
@@ -0,0 +1,49 @@
+#
+# Copyright 2017 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.
+#
+
+LOCAL_PATH:= $(call my-dir)
+
+# Build a tiny library that the test app can dynamically load
+
+include $(CLEAR_VARS)
+
+LOCAL_MODULE_TAGS := tests
+LOCAL_MODULE := DexLoggerTestLibrary
+LOCAL_SRC_FILES := $(call all-java-files-under, src/com/android/dcl)
+
+include $(BUILD_JAVA_LIBRARY)
+
+dexloggertest_jar := $(LOCAL_BUILT_MODULE)
+
+
+# Build the test app itself
+
+include $(CLEAR_VARS)
+
+LOCAL_MODULE_TAGS := tests
+LOCAL_PACKAGE_NAME := DexLoggerIntegrationTests
+LOCAL_COMPATIBILITY_SUITE := device-tests
+LOCAL_CERTIFICATE := platform
+LOCAL_SRC_FILES := $(call all-java-files-under, src/com/android/server/pm)
+
+LOCAL_STATIC_JAVA_LIBRARIES := \
+ android-support-test \
+ truth-prebuilt \
+
+# This gets us the javalib.jar built by DexLoggerTestLibrary above.
+LOCAL_JAVA_RESOURCE_FILES := $(dexloggertest_jar)
+
+include $(BUILD_PACKAGE)
diff --git a/tests/DexLoggerIntegrationTests/AndroidManifest.xml b/tests/DexLoggerIntegrationTests/AndroidManifest.xml
new file mode 100644
index 0000000..a847e8f
--- /dev/null
+++ b/tests/DexLoggerIntegrationTests/AndroidManifest.xml
@@ -0,0 +1,35 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright 2017 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.
+-->
+
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ package="com.android.frameworks.dexloggertest">
+
+ <!-- Tests feature introduced in P (27) -->
+ <uses-sdk
+ android:minSdkVersion="27"
+ android:targetSdkVersion="27" />
+
+ <uses-permission android:name="android.permission.READ_LOGS" />
+
+ <application>
+ <uses-library android:name="android.test.runner" />
+ </application>
+
+ <instrumentation
+ android:name="android.support.test.runner.AndroidJUnitRunner"
+ android:targetPackage="com.android.frameworks.dexloggertest"
+ android:label="Integration test for DexLogger" />
+</manifest>
diff --git a/tests/DexLoggerIntegrationTests/AndroidTest.xml b/tests/DexLoggerIntegrationTests/AndroidTest.xml
new file mode 100644
index 0000000..8ed19f8
--- /dev/null
+++ b/tests/DexLoggerIntegrationTests/AndroidTest.xml
@@ -0,0 +1,29 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright 2017 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.
+-->
+<configuration description="Runs DexLogger Integration Tests">
+ <target_preparer class="com.android.tradefed.targetprep.TestAppInstallSetup">
+ <option name="test-file-name" value="DexLoggerIntegrationTests.apk"/>
+ <option name="cleanup-apks" value="true"/>
+ </target_preparer>
+
+ <option name="test-suite-tag" value="apct"/>
+ <option name="test-tag" value="DexLoggerIntegrationTests"/>
+
+ <test class="com.android.tradefed.testtype.AndroidJUnitTest">
+ <option name="package" value="com.android.frameworks.dexloggertest"/>
+ <option name="runner" value="android.support.test.runner.AndroidJUnitRunner"/>
+ </test>
+</configuration>
diff --git a/tests/DexLoggerIntegrationTests/src/com/android/dcl/Simple.java b/tests/DexLoggerIntegrationTests/src/com/android/dcl/Simple.java
new file mode 100644
index 0000000..e995a26
--- /dev/null
+++ b/tests/DexLoggerIntegrationTests/src/com/android/dcl/Simple.java
@@ -0,0 +1,22 @@
+/*
+ * Copyright 2017 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.
+ */
+
+package com.android.dcl;
+
+/** Dummy class which is built into a jar purely so we can pass it to DexClassLoader. */
+public final class Simple {
+ public Simple() {}
+}
diff --git a/tests/DexLoggerIntegrationTests/src/com/android/server/pm/DexLoggerIntegrationTests.java b/tests/DexLoggerIntegrationTests/src/com/android/server/pm/DexLoggerIntegrationTests.java
new file mode 100644
index 0000000..d9f34d5
--- /dev/null
+++ b/tests/DexLoggerIntegrationTests/src/com/android/server/pm/DexLoggerIntegrationTests.java
@@ -0,0 +1,151 @@
+/*
+ * Copyright 2017 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.
+ */
+
+package com.android.server.pm;
+
+import static com.google.common.truth.Truth.assertThat;
+
+import android.content.Context;
+import android.support.test.InstrumentationRegistry;
+import android.util.EventLog;
+
+import dalvik.system.DexClassLoader;
+
+import org.junit.After;
+import org.junit.AfterClass;
+import org.junit.Before;
+import org.junit.BeforeClass;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.junit.runners.JUnit4;
+
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.security.MessageDigest;
+import java.util.ArrayList;
+import java.util.Formatter;
+import java.util.List;
+
+/**
+ * Integration tests for {@link com.android.server.pm.dex.DexLogger}.
+ *
+ * The setup for the test dynamically loads code in a jar extracted
+ * from our assets (a secondary dex file).
+ *
+ * We then use adb to trigger secondary dex file reconcilation (and
+ * wait for it to complete). As a side-effect of this DexLogger should
+ * be notified of the file and should log the hash of the file's name
+ * and content. We verify that this message appears in the event log.
+ *
+ * Run with "atest DexLoggerIntegrationTests".
+ */
+@RunWith(JUnit4.class)
+public final class DexLoggerIntegrationTests {
+
+ private static final String TAG = DexLoggerIntegrationTests.class.getSimpleName();
+
+ private static final String PACKAGE_NAME = "com.android.frameworks.dexloggertest";
+
+ private static final int SNET_TAG = 0x534e4554;
+ private static final String DCL_SUBTAG = "dcl";
+
+ // Obtained via "echo -n copied.jar | sha256sum"
+ private static final String EXPECTED_NAME_HASH =
+ "1B6C71DB26F36582867432CCA12FB6A517470C9F9AABE9198DD4C5C030D6DC0C";
+
+ private static String expectedContentHash;
+
+ @BeforeClass
+ public static void setUpAll() throws Exception {
+ Context context = InstrumentationRegistry.getTargetContext();
+ MessageDigest hasher = MessageDigest.getInstance("SHA-256");
+
+ // Copy the jar from our Java resources to a private data directory
+ File privateCopy = new File(context.getDir("jars", Context.MODE_PRIVATE), "copied.jar");
+ try (InputStream input = DexLoggerIntegrationTests.class.getResourceAsStream("/javalib.jar");
+ OutputStream output = new FileOutputStream(privateCopy)) {
+ byte[] buffer = new byte[1024];
+ while (true) {
+ int numRead = input.read(buffer);
+ if (numRead < 0) {
+ break;
+ }
+ output.write(buffer, 0, numRead);
+ hasher.update(buffer, 0, numRead);
+ }
+ }
+
+ // Remember the SHA-256 of the file content to check that it is the same as
+ // the value we see logged.
+ Formatter formatter = new Formatter();
+ for (byte b : hasher.digest()) {
+ formatter.format("%02X", b);
+ }
+ expectedContentHash = formatter.toString();
+
+ // Feed the jar to a class loader and make sure it contains what we expect.
+ ClassLoader loader =
+ new DexClassLoader(
+ privateCopy.toString(), null, null, context.getClass().getClassLoader());
+ loader.loadClass("com.android.dcl.Simple");
+ }
+
+ @Test
+ public void testDexLoggerReconcileGeneratesEvents() throws Exception {
+ int[] tagList = new int[] { SNET_TAG };
+ List<EventLog.Event> events = new ArrayList<>();
+
+ // There may already be events in the event log - figure out the most recent one
+ EventLog.readEvents(tagList, events);
+ long previousEventNanos = events.isEmpty() ? 0 : events.get(events.size() - 1).getTimeNanos();
+ events.clear();
+
+ Process process = Runtime.getRuntime().exec(
+ "cmd package reconcile-secondary-dex-files " + PACKAGE_NAME);
+ int exitCode = process.waitFor();
+ assertThat(exitCode).isEqualTo(0);
+
+ int myUid = android.os.Process.myUid();
+ String expectedMessage = EXPECTED_NAME_HASH + " " + expectedContentHash;
+
+ EventLog.readEvents(tagList, events);
+ boolean found = false;
+ for (EventLog.Event event : events) {
+ if (event.getTimeNanos() <= previousEventNanos) {
+ continue;
+ }
+ Object[] data = (Object[]) event.getData();
+
+ // We only care about DCL events that we generated.
+ String subTag = (String) data[0];
+ if (!DCL_SUBTAG.equals(subTag)) {
+ continue;
+ }
+ int uid = (int) data[1];
+ if (uid != myUid) {
+ continue;
+ }
+
+ String message = (String) data[2];
+ assertThat(message).isEqualTo(expectedMessage);
+ found = true;
+ }
+
+ assertThat(found).isTrue();
+ }
+}