Merge "Reducing amount of files created in dropbox for keystore" am: 60f9053686
am: cca1a25e53
Change-Id: Iac53d2afdb19ed8e2e9d76a68985959b68417b79
diff --git a/keystore/operation.cpp b/keystore/operation.cpp
index 07f9d6c..71ab340 100644
--- a/keystore/operation.cpp
+++ b/keystore/operation.cpp
@@ -63,7 +63,7 @@
if (entry == mMap.end()) return {};
auto op = entry->second;
- uploadOpAsProto(*op, wasSuccessful);
+ operationUploader.uploadOpAsProto(*op, wasSuccessful);
mMap.erase(entry);
auto lruEntry = std::find(mLru.begin(), mLru.end(), token);
diff --git a/keystore/operation.h b/keystore/operation.h
index efe791f..e0865a4 100644
--- a/keystore/operation.h
+++ b/keystore/operation.h
@@ -70,6 +70,7 @@
std::list<sp<IBinder>> mLru;
std::map<sp<IBinder>, std::vector<sp<IBinder>>> mAppTokenMap;
IBinder::DeathRecipient* mDeathRecipient;
+ OperationProtoHandler operationUploader;
};
} // namespace keystore
diff --git a/keystore/operation_config.proto b/keystore/operation_config.proto
index 37b4cbb..efbb4fe 100644
--- a/keystore/operation_config.proto
+++ b/keystore/operation_config.proto
@@ -20,6 +20,7 @@
option optimize_for = LITE_RUNTIME;
+// A single operation config
message OperationConfig {
// What type of encryption algorithm is the key being used in the op for.
optional string algorithm = 1;
@@ -61,3 +62,16 @@
// Standalone or is a file system required
optional string key_blob_usage_reqs = 12;
}
+
+message OperationConfigEvent {
+ optional OperationConfig op_config = 1;
+
+ // counts corresponds to the number of times each op_config in the above array
+ // was recorded during the collection period.
+ optional uint32 count = 2;
+}
+
+message OperationConfigEvents {
+ repeated OperationConfigEvent op_config_events = 1;
+}
+
diff --git a/keystore/operation_proto_handler.cpp b/keystore/operation_proto_handler.cpp
index 992232d..1833acb 100644
--- a/keystore/operation_proto_handler.cpp
+++ b/keystore/operation_proto_handler.cpp
@@ -25,10 +25,12 @@
#include <utils/String16.h>
#include <utils/StrongPointer.h>
-#include "operation_config.pb.h"
+using namespace std::chrono;
namespace keystore {
+constexpr auto kCollectionTime = 1h;
+
void determinePurpose(KeyPurpose purpose, OperationConfig* operationConfig) {
switch (purpose) {
case KeyPurpose::VERIFY:
@@ -103,19 +105,42 @@
}
}
-void uploadOpAsProto(Operation& op, bool wasOpSuccessful) {
+void OperationProtoHandler::uploadOpAsProto(Operation& op, bool wasOpSuccessful) {
OperationConfig operationConfig;
determinePurpose(op.purpose, &operationConfig);
checkKeyCharacteristics(op.characteristics.softwareEnforced, &operationConfig);
checkKeyCharacteristics(op.characteristics.hardwareEnforced, &operationConfig);
checkOpCharacteristics(op.params, &operationConfig);
- android::sp<android::os::DropBoxManager> dropbox(new android::os::DropBoxManager);
operationConfig.set_was_op_successful(wasOpSuccessful);
+ // Only bother with counting an hour out when an operation entry is actually
+ // added
+ if (protoMap.empty()) {
+ start_time = std::chrono::steady_clock::now();
+ }
+ auto cur_time = std::chrono::steady_clock::now();
- size_t size = operationConfig.ByteSize();
- auto data = std::make_unique<uint8_t[]>(size);
- operationConfig.SerializeWithCachedSizesToArray(data.get());
- dropbox->addData(android::String16("keymaster"), data.get(), size, 0);
+ // Add operations to a map within the time duration of an hour. Deduplicate
+ // repeated ops by incrementing the counter of the original one stored and
+ // discarding the new one.
+ protoMap[operationConfig.SerializeAsString()]++;
+
+ if (cur_time - start_time >= kCollectionTime) {
+ // Iterate through the unordered map and dump all the operation protos
+ // accumulated over the hour into the holding list proto after setting
+ // their counts.
+ OperationConfigEvents opConfigEvents;
+ for (auto elem : protoMap) {
+ OperationConfigEvent* event = opConfigEvents.add_op_config_events();
+ event->mutable_op_config()->ParseFromString(elem.first);
+ event->set_count(elem.second);
+ }
+ android::sp<android::os::DropBoxManager> dropbox(new android::os::DropBoxManager);
+ size_t size = opConfigEvents.ByteSize();
+ auto data = std::make_unique<uint8_t[]>(size);
+ opConfigEvents.SerializeWithCachedSizesToArray(data.get());
+ dropbox->addData(android::String16("keymaster"), data.get(), size, 0);
+ protoMap.clear();
+ }
}
} // namespace keystore
diff --git a/keystore/operation_proto_handler.h b/keystore/operation_proto_handler.h
index bf461b4..838f3ec 100644
--- a/keystore/operation_proto_handler.h
+++ b/keystore/operation_proto_handler.h
@@ -17,14 +17,25 @@
#ifndef KEYSTORE_OPERATION_PROTO_HANDLER_H_
#define KEYSTORE_OPERATION_PROTO_HANDLER_H_
+#include "operation_config.pb.h"
#include "operation_struct.h"
+#include <chrono>
+#include <unordered_map>
+#include <vector>
namespace keystore {
using ::android::IBinder;
using keymaster::support::Keymaster;
-void uploadOpAsProto(Operation& op, bool wasOpSuccessful);
+class OperationProtoHandler {
+ public:
+ void uploadOpAsProto(Operation& op, bool wasOpSuccessful);
+
+ private:
+ std::unordered_map<std::string, int> protoMap;
+ std::chrono::steady_clock::time_point start_time = std::chrono::steady_clock::now();
+};
} // namespace keystore