Initialize the /data encryption options only once
Cache the EncryptionOptions for /data in a static variable so that it
doesn't have to be repeatedly regenerated from the fstab.
Bug: 232452368
Bug: 251131631
Bug: 251147505
Ignore-AOSP-First: depends on other changes in internal master
Change-Id: I24b27190ed807f142b793d3cf250ec271d092f34
diff --git a/FsCrypt.cpp b/FsCrypt.cpp
index d964a33..477db7c 100644
--- a/FsCrypt.cpp
+++ b/FsCrypt.cpp
@@ -96,6 +96,9 @@
const std::string data_user_0_dir = std::string() + DATA_MNT_POINT + "/user/0";
const std::string media_obb_dir = std::string() + DATA_MNT_POINT + "/media/obb";
+// The file encryption options to use on the /data filesystem
+EncryptionOptions s_data_options;
+
// Some users are ephemeral; don't try to store or wipe their keys on disk.
std::set<userid_t> s_ephemeral_users;
@@ -113,6 +116,10 @@
// Returns KeyGeneration suitable for key as described in EncryptionOptions
static KeyGeneration makeGen(const EncryptionOptions& options) {
+ if (options.version == 0) {
+ LOG(ERROR) << "EncryptionOptions not initialized";
+ return android::vold::neverGen();
+ }
return KeyGeneration{FSCRYPT_MAX_KEY_SIZE, true, options.use_hw_wrapped_key};
}
@@ -242,19 +249,19 @@
StartsWith(name, "vd");
}
-// Retrieve the options to use for encryption policies on the /data filesystem.
-static bool get_data_file_encryption_options(EncryptionOptions* options) {
+// Sets s_data_options to the file encryption options for the /data filesystem.
+static bool init_data_file_encryption_options() {
auto entry = GetEntryForMountPoint(&fstab_default, DATA_MNT_POINT);
if (entry == nullptr) {
LOG(ERROR) << "No mount point entry for " << DATA_MNT_POINT;
return false;
}
- if (!ParseOptions(entry->encryption_options, options)) {
+ if (!ParseOptions(entry->encryption_options, &s_data_options)) {
LOG(ERROR) << "Unable to parse encryption options for " << DATA_MNT_POINT ": "
<< entry->encryption_options;
return false;
}
- if ((options->flags & FSCRYPT_POLICY_FLAG_IV_INO_LBLK_32) &&
+ if ((s_data_options.flags & FSCRYPT_POLICY_FLAG_IV_INO_LBLK_32) &&
!MightBeEmmcStorage(entry->blk_device)) {
LOG(ERROR) << "The emmc_optimized encryption flag is only allowed on eMMC storage. Remove "
"this flag from the device's fstab";
@@ -265,6 +272,10 @@
static bool install_storage_key(const std::string& mountpoint, const EncryptionOptions& options,
const KeyBuffer& key, EncryptionPolicy* policy) {
+ if (options.version == 0) {
+ LOG(ERROR) << "EncryptionOptions not initialized";
+ return false;
+ }
KeyBuffer ephemeral_wrapped_key;
if (options.use_hw_wrapped_key) {
if (!exportWrappedStorageKey(key, &ephemeral_wrapped_key)) {
@@ -303,12 +314,10 @@
static bool read_and_install_user_ce_key(userid_t user_id,
const android::vold::KeyAuthentication& auth) {
if (s_ce_policies.count(user_id) != 0) return true;
- EncryptionOptions options;
- if (!get_data_file_encryption_options(&options)) return false;
KeyBuffer ce_key;
if (!read_and_fixate_user_ce_key(user_id, auth, &ce_key)) return false;
EncryptionPolicy ce_policy;
- if (!install_storage_key(DATA_MNT_POINT, options, ce_key, &ce_policy)) return false;
+ if (!install_storage_key(DATA_MNT_POINT, s_data_options, ce_key, &ce_policy)) return false;
s_ce_policies[user_id] = ce_policy;
LOG(DEBUG) << "Installed ce key for user " << user_id;
return true;
@@ -360,27 +369,21 @@
}
static bool create_de_key(userid_t user_id, bool ephemeral) {
- EncryptionOptions options;
- if (!get_data_file_encryption_options(&options)) return false;
-
KeyBuffer de_key;
- if (!generateStorageKey(makeGen(options), &de_key)) return false;
+ if (!generateStorageKey(makeGen(s_data_options), &de_key)) return false;
if (!ephemeral && !android::vold::storeKeyAtomically(get_de_key_path(user_id), user_key_temp,
kEmptyAuthentication, de_key))
return false;
EncryptionPolicy de_policy;
- if (!install_storage_key(DATA_MNT_POINT, options, de_key, &de_policy)) return false;
+ if (!install_storage_key(DATA_MNT_POINT, s_data_options, de_key, &de_policy)) return false;
s_de_policies[user_id] = de_policy;
LOG(INFO) << "Created DE key for user " << user_id;
return true;
}
static bool create_ce_key(userid_t user_id, bool ephemeral) {
- EncryptionOptions options;
- if (!get_data_file_encryption_options(&options)) return false;
-
KeyBuffer ce_key;
- if (!generateStorageKey(makeGen(options), &ce_key)) return false;
+ if (!generateStorageKey(makeGen(s_data_options), &ce_key)) return false;
if (!ephemeral) {
if (!prepare_dir(get_ce_key_directory_path(user_id), 0700, AID_ROOT, AID_ROOT))
return false;
@@ -390,7 +393,7 @@
s_new_ce_keys.insert({user_id, ce_key});
}
EncryptionPolicy ce_policy;
- if (!install_storage_key(DATA_MNT_POINT, options, ce_key, &ce_policy)) return false;
+ if (!install_storage_key(DATA_MNT_POINT, s_data_options, ce_key, &ce_policy)) return false;
s_ce_policies[user_id] = ce_policy;
LOG(INFO) << "Created CE key for user " << user_id;
return true;
@@ -414,8 +417,6 @@
}
static bool load_all_de_keys() {
- EncryptionOptions options;
- if (!get_data_file_encryption_options(&options)) return false;
auto de_dir = user_key_dir + "/de";
auto dirp = std::unique_ptr<DIR, int (*)(DIR*)>(opendir(de_dir.c_str()), closedir);
if (!dirp) {
@@ -442,7 +443,7 @@
KeyBuffer de_key;
if (!retrieveKey(key_path, kEmptyAuthentication, &de_key)) return false;
EncryptionPolicy de_policy;
- if (!install_storage_key(DATA_MNT_POINT, options, de_key, &de_policy)) return false;
+ if (!install_storage_key(DATA_MNT_POINT, s_data_options, de_key, &de_policy)) return false;
auto ret = s_de_policies.insert({user_id, de_policy});
if (!ret.second && ret.first->second != de_policy) {
LOG(ERROR) << "DE policy for user" << user_id << " changed";
@@ -469,17 +470,17 @@
bool fscrypt_initialize_systemwide_keys() {
LOG(INFO) << "fscrypt_initialize_systemwide_keys";
- EncryptionOptions options;
- if (!get_data_file_encryption_options(&options)) return false;
+ if (!init_data_file_encryption_options()) return false;
KeyBuffer device_key;
if (!retrieveOrGenerateKey(device_key_path, device_key_temp, kEmptyAuthentication,
- makeGen(options), &device_key))
+ makeGen(s_data_options), &device_key))
return false;
// This initializes s_device_policy, which is a global variable so that
// fscrypt_init_user0() can access it later.
- if (!install_storage_key(DATA_MNT_POINT, options, device_key, &s_device_policy)) return false;
+ if (!install_storage_key(DATA_MNT_POINT, s_data_options, device_key, &s_device_policy))
+ return false;
std::string options_string;
if (!OptionsToString(s_device_policy.options, &options_string)) {
@@ -494,9 +495,10 @@
LOG(INFO) << "Wrote system DE key reference to:" << ref_filename;
KeyBuffer per_boot_key;
- if (!generateStorageKey(makeGen(options), &per_boot_key)) return false;
+ if (!generateStorageKey(makeGen(s_data_options), &per_boot_key)) return false;
EncryptionPolicy per_boot_policy;
- if (!install_storage_key(DATA_MNT_POINT, options, per_boot_key, &per_boot_policy)) return false;
+ if (!install_storage_key(DATA_MNT_POINT, s_data_options, per_boot_key, &per_boot_policy))
+ return false;
std::string per_boot_ref_filename = std::string("/data") + fscrypt_key_per_boot_ref;
if (!android::vold::writeStringToFile(per_boot_policy.key_raw_ref, per_boot_ref_filename))
return false;