fscrypt: : Use wrapped key for metadata encryption
Importing of this commit:
https://github.com/LineageOS/android_system_vold/commit/944c48d5a4c6df1eb751b04f52c06adac35ebab6
Change-Id: I048a6c2aeff2591135f47223a99af5ddd215703c
diff --git a/crypto/fscrypt/FsCrypt.cpp b/crypto/fscrypt/FsCrypt.cpp
index 46df2b6..e967339 100755
--- a/crypto/fscrypt/FsCrypt.cpp
+++ b/crypto/fscrypt/FsCrypt.cpp
@@ -230,6 +230,18 @@
return false;
}
+bool is_metadata_wrapped_key_supported() {
+ LOG(DEBUG) << "Determining metadata wrapped-key support for " << mount_point;
+ std::string wrapped_key_supported = android::base::GetProperty("fbe.metadata.wrappedkey", "false");
+ LOG(DEBUG) << "fbe.metadata.wrappedkey = " << wrapped_key_supported;
+ if (mount_point == METADATA_MNT_POINT && wrapped_key_supported == "true") {
+ LOG(DEBUG) << "Wrapped key supported on " << mount_point;
+ return true;
+ } else {
+ return false;
+ }
+}
+
static bool read_and_install_user_ce_key(userid_t user_id,
const android::vold::KeyAuthentication& auth) {
if (s_ce_key_raw_refs.count(user_id) != 0) return true;
diff --git a/crypto/fscrypt/FsCrypt.h b/crypto/fscrypt/FsCrypt.h
index 11a338f..c63e11f 100755
--- a/crypto/fscrypt/FsCrypt.h
+++ b/crypto/fscrypt/FsCrypt.h
@@ -42,5 +42,6 @@
bool fscrypt_destroy_volume_keys(const std::string& volume_uuid);
bool is_wrapped_key_supported();
bool is_wrapped_key_supported_external();
+bool is_metadata_wrapped_key_supported();
bool lookup_key_ref(const std::map<userid_t, std::string>& key_map, userid_t user_id,
std::string* raw_ref);
\ No newline at end of file
diff --git a/crypto/fscrypt/KeyStorage.cpp b/crypto/fscrypt/KeyStorage.cpp
index 9457591..068c069 100755
--- a/crypto/fscrypt/KeyStorage.cpp
+++ b/crypto/fscrypt/KeyStorage.cpp
@@ -146,7 +146,7 @@
paramBuilder.push_back(param1);
km::KeyParameter param2;
- if ((key_type == KeyType::DE_USER) || (key_type == KeyType::DE_SYS)) {
+ if ((key_type == KeyType::DE_USER) || (key_type == KeyType::DE_SYS || (key_type == KeyType::ME))) {
param2.tag = (km::Tag) (android::hardware::keymaster::V4_0::KM_TAG_KEY_TYPE);
param2.f.integer = 0;
} else if (key_type == KeyType::CE_USER) {
diff --git a/crypto/fscrypt/KeyStorage.h b/crypto/fscrypt/KeyStorage.h
index 72ddfc4..9959ce6 100755
--- a/crypto/fscrypt/KeyStorage.h
+++ b/crypto/fscrypt/KeyStorage.h
@@ -43,7 +43,8 @@
enum class KeyType {
DE_SYS,
DE_USER,
- CE_USER
+ CE_USER,
+ ME,
};
extern const KeyAuthentication kEmptyAuthentication;
diff --git a/crypto/fscrypt/KeyUtil.cpp b/crypto/fscrypt/KeyUtil.cpp
index 70a551c..fa40640 100755
--- a/crypto/fscrypt/KeyUtil.cpp
+++ b/crypto/fscrypt/KeyUtil.cpp
@@ -199,15 +199,36 @@
if (pathExists(key_path)) {
LOG(ERROR) << "Key exists, using: " << key_path;
if (!retrieveKey(key_path, kEmptyAuthentication, key, keepOld)) return false;
+ if (is_metadata_wrapped_key_supported()) {
+ KeyBuffer ephemeral_wrapped_key;
+ if (!getEphemeralWrappedKey(KeyFormat::RAW, *key, &ephemeral_wrapped_key)) {
+ LOG(ERROR) << "Failed to export key for retrieved key";
+ return false;
+ }
+ *key = std::move(ephemeral_wrapped_key);
+ }
} else {
if (!create_if_absent) {
LOG(ERROR) << "No key found in " << key_path;
return false;
}
LOG(ERROR) << "Creating new key in " << key_path;
- if (!randomKey(key)) return false;
- LOG(ERROR) << "retrieveKey1";
- if (!storeKeyAtomically(key_path, tmp_path, kEmptyAuthentication, *key)) return false;
+ if (is_metadata_wrapped_key_supported()) {
+ if(!generateWrappedKey(MAX_USER_ID, KeyType::ME, key)) return false;
+ } else {
+ if (!randomKey(key)) return false;
+ }
+ LOG(ERROR) << "retrieveKey1";
+ if (!storeKeyAtomically(key_path, tmp_path,
+ kEmptyAuthentication, *key)) return false;
+ if (is_metadata_wrapped_key_supported()) {
+ KeyBuffer ephemeral_wrapped_key;
+ if (!getEphemeralWrappedKey(KeyFormat::RAW, *key, &ephemeral_wrapped_key)) {
+ LOG(ERROR) << "Failed to export key for generated key";
+ return false;
+ }
+ *key = std::move(ephemeral_wrapped_key);
+ }
}
return true;
}
diff --git a/crypto/fscrypt/cryptfs.h b/crypto/fscrypt/cryptfs.h
index 692d7ee..a4fe87b 100644
--- a/crypto/fscrypt/cryptfs.h
+++ b/crypto/fscrypt/cryptfs.h
@@ -200,6 +200,7 @@
};
#define DATA_MNT_POINT "/data"
+#define METADATA_MNT_POINT "/metadata"
/* Return values for cryptfs_crypto_complete */
#define CRYPTO_COMPLETE_NOT_ENCRYPTED 1