|
|
|
@ -202,7 +202,7 @@ static KeymasterOperation begin(Keymaster& keymaster, const std::string& dir,
|
|
|
|
|
km::KeyPurpose purpose, const km::AuthorizationSet& keyParams,
|
|
|
|
|
const km::AuthorizationSet& opParams,
|
|
|
|
|
const km::HardwareAuthToken& authToken,
|
|
|
|
|
km::AuthorizationSet* outParams) {
|
|
|
|
|
km::AuthorizationSet* outParams, bool keepOld) {
|
|
|
|
|
auto kmKeyPath = dir + "/" + kFn_keymaster_key_blob;
|
|
|
|
|
std::string kmKey;
|
|
|
|
|
if (!readFileToString(kmKeyPath, &kmKey)) return KeymasterOperation();
|
|
|
|
@ -219,12 +219,14 @@ static KeymasterOperation begin(Keymaster& keymaster, const std::string& dir,
|
|
|
|
|
if (!keymaster.upgradeKey(kmKey, keyParams, &newKey)) return KeymasterOperation();
|
|
|
|
|
auto newKeyPath = dir + "/" + kFn_keymaster_key_blob_upgraded;
|
|
|
|
|
if (!writeStringToFile(newKey, newKeyPath)) return KeymasterOperation();
|
|
|
|
|
if (rename(newKeyPath.c_str(), kmKeyPath.c_str()) != 0) {
|
|
|
|
|
PLOG(ERROR) << "Unable to move upgraded key to location: " << kmKeyPath;
|
|
|
|
|
return KeymasterOperation();
|
|
|
|
|
}
|
|
|
|
|
if (!keymaster.deleteKey(kmKey)) {
|
|
|
|
|
LOG(ERROR) << "Key deletion failed during upgrade, continuing anyway: " << dir;
|
|
|
|
|
if (!keepOld) {
|
|
|
|
|
if (rename(newKeyPath.c_str(), kmKeyPath.c_str()) != 0) {
|
|
|
|
|
PLOG(ERROR) << "Unable to move upgraded key to location: " << kmKeyPath;
|
|
|
|
|
return KeymasterOperation();
|
|
|
|
|
}
|
|
|
|
|
if (!keymaster.deleteKey(kmKey)) {
|
|
|
|
|
LOG(ERROR) << "Key deletion failed during upgrade, continuing anyway: " << dir;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
kmKey = newKey;
|
|
|
|
|
LOG(INFO) << "Key upgraded: " << dir;
|
|
|
|
@ -233,12 +235,12 @@ static KeymasterOperation begin(Keymaster& keymaster, const std::string& dir,
|
|
|
|
|
|
|
|
|
|
static bool encryptWithKeymasterKey(Keymaster& keymaster, const std::string& dir,
|
|
|
|
|
const km::AuthorizationSet& keyParams,
|
|
|
|
|
const km::HardwareAuthToken& authToken,
|
|
|
|
|
const KeyBuffer& message, std::string* ciphertext) {
|
|
|
|
|
const km::HardwareAuthToken& authToken, const KeyBuffer& message,
|
|
|
|
|
std::string* ciphertext, bool keepOld) {
|
|
|
|
|
km::AuthorizationSet opParams;
|
|
|
|
|
km::AuthorizationSet outParams;
|
|
|
|
|
auto opHandle =
|
|
|
|
|
begin(keymaster, dir, km::KeyPurpose::ENCRYPT, keyParams, opParams, authToken, &outParams);
|
|
|
|
|
auto opHandle = begin(keymaster, dir, km::KeyPurpose::ENCRYPT, keyParams, opParams, authToken,
|
|
|
|
|
&outParams, keepOld);
|
|
|
|
|
if (!opHandle) return false;
|
|
|
|
|
auto nonceBlob = outParams.GetTagValue(km::TAG_NONCE);
|
|
|
|
|
if (!nonceBlob.isOk()) {
|
|
|
|
@ -262,13 +264,14 @@ static bool encryptWithKeymasterKey(Keymaster& keymaster, const std::string& dir
|
|
|
|
|
static bool decryptWithKeymasterKey(Keymaster& keymaster, const std::string& dir,
|
|
|
|
|
const km::AuthorizationSet& keyParams,
|
|
|
|
|
const km::HardwareAuthToken& authToken,
|
|
|
|
|
const std::string& ciphertext, KeyBuffer* message) {
|
|
|
|
|
const std::string& ciphertext, KeyBuffer* message,
|
|
|
|
|
bool keepOld) {
|
|
|
|
|
auto nonce = ciphertext.substr(0, GCM_NONCE_BYTES);
|
|
|
|
|
auto bodyAndMac = ciphertext.substr(GCM_NONCE_BYTES);
|
|
|
|
|
auto opParams = km::AuthorizationSetBuilder().Authorization(km::TAG_NONCE,
|
|
|
|
|
km::support::blob2hidlVec(nonce));
|
|
|
|
|
auto opHandle =
|
|
|
|
|
begin(keymaster, dir, km::KeyPurpose::DECRYPT, keyParams, opParams, authToken, nullptr);
|
|
|
|
|
auto opHandle = begin(keymaster, dir, km::KeyPurpose::DECRYPT, keyParams, opParams, authToken,
|
|
|
|
|
nullptr, keepOld);
|
|
|
|
|
if (!opHandle) return false;
|
|
|
|
|
if (!opHandle.updateCompletely(bodyAndMac, message)) return false;
|
|
|
|
|
if (!opHandle.finish(nullptr)) return false;
|
|
|
|
@ -474,7 +477,8 @@ bool storeKey(const std::string& dir, const KeyAuthentication& auth, const KeyBu
|
|
|
|
|
km::AuthorizationSet keyParams;
|
|
|
|
|
km::HardwareAuthToken authToken;
|
|
|
|
|
std::tie(keyParams, authToken) = beginParams(auth, appId);
|
|
|
|
|
if (!encryptWithKeymasterKey(keymaster, dir, keyParams, authToken, key, &encryptedKey))
|
|
|
|
|
if (!encryptWithKeymasterKey(keymaster, dir, keyParams, authToken, key, &encryptedKey,
|
|
|
|
|
false))
|
|
|
|
|
return false;
|
|
|
|
|
} else {
|
|
|
|
|
if (!encryptWithoutKeymaster(appId, key, &encryptedKey)) return false;
|
|
|
|
@ -502,7 +506,8 @@ bool storeKeyAtomically(const std::string& key_path, const std::string& tmp_path
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool retrieveKey(const std::string& dir, const KeyAuthentication& auth, KeyBuffer* key) {
|
|
|
|
|
bool retrieveKey(const std::string& dir, const KeyAuthentication& auth, KeyBuffer* key,
|
|
|
|
|
bool keepOld) {
|
|
|
|
|
std::string version;
|
|
|
|
|
if (!readFileToString(dir + "/" + kFn_version, &version)) return false;
|
|
|
|
|
if (version != kCurrentVersion) {
|
|
|
|
@ -527,7 +532,8 @@ bool retrieveKey(const std::string& dir, const KeyAuthentication& auth, KeyBuffe
|
|
|
|
|
km::AuthorizationSet keyParams;
|
|
|
|
|
km::HardwareAuthToken authToken;
|
|
|
|
|
std::tie(keyParams, authToken) = beginParams(auth, appId);
|
|
|
|
|
if (!decryptWithKeymasterKey(keymaster, dir, keyParams, authToken, encryptedMessage, key))
|
|
|
|
|
if (!decryptWithKeymasterKey(keymaster, dir, keyParams, authToken, encryptedMessage, key,
|
|
|
|
|
keepOld))
|
|
|
|
|
return false;
|
|
|
|
|
} else {
|
|
|
|
|
if (!decryptWithoutKeymaster(appId, encryptedMessage, key)) return false;
|
|
|
|
|