// Copyright 2022 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/enterprise/connectors/device_trust/key_management/core/mac/metrics_util.h"
#include "base/metrics/histogram_functions.h"
#include "base/strings/stringprintf.h"
namespace enterprise_connectors {
namespace {
constexpr char kSecureEnclaveOperationHistogramFormat[] =
"Enterprise.DeviceTrust.Mac.SecureEnclaveOperation.%s";
constexpr char kKeychainOSStatusHistogramFormat[] =
"Enterprise.DeviceTrust.Mac.KeychainOSStatus.%s.%s";
std::optional<SecureEnclaveOperationStatus> ConvertOperationToStatus(
KeychainOperation operation) {
switch (operation) {
case KeychainOperation::kCreate:
return SecureEnclaveOperationStatus::kCreateSecureKeyFailed;
case KeychainOperation::kCopy:
return SecureEnclaveOperationStatus::
kCopySecureKeyRefDataProtectionKeychainFailed;
case KeychainOperation::kDelete:
return SecureEnclaveOperationStatus::
kDeleteSecureKeyDataProtectionKeychainFailed;
case KeychainOperation::kUpdate:
return SecureEnclaveOperationStatus::
kUpdateSecureKeyLabelDataProtectionKeychainFailed;
default:
return std::nullopt;
}
}
std::string KeyTypeToString(SecureEnclaveClient::KeyType type) {
switch (type) {
case SecureEnclaveClient::KeyType::kPermanent:
return "Permanent";
case SecureEnclaveClient::KeyType::kTemporary:
return "Temporary";
}
}
std::string OperationToString(KeychainOperation operation) {
switch (operation) {
case KeychainOperation::kCreate:
return "Create";
case KeychainOperation::kCopy:
return "Copy";
case KeychainOperation::kDelete:
return "Delete";
case KeychainOperation::kUpdate:
return "Update";
case KeychainOperation::kExportPublicKey:
return "ExportPublicKey";
case KeychainOperation::kSignPayload:
return "SignPayload";
}
}
} // namespace
void RecordKeyOperationStatus(KeychainOperation operation,
SecureEnclaveClient::KeyType type,
OSStatus error_code) {
auto type_string = KeyTypeToString(type);
auto operation_status = ConvertOperationToStatus(operation);
if (operation_status) {
base::UmaHistogramEnumeration(
base::StringPrintf(kSecureEnclaveOperationHistogramFormat,
type_string.c_str()),
operation_status.value());
}
base::UmaHistogramSparse(
base::StringPrintf(kKeychainOSStatusHistogramFormat, type_string.c_str(),
OperationToString(operation).c_str()),
error_code);
}
} // namespace enterprise_connectors