1 /* 2 * Copyright (C) 2021 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 #ifndef STORAGE_DAEMON_CRYPTO_KEYCTL_H 16 #define STORAGE_DAEMON_CRYPTO_KEYCTL_H 17 18 #include <unistd.h> 19 #include <vector> 20 #include <map> 21 #include <string> 22 #include <linux/keyctl.h> 23 #include <linux/version.h> 24 #if LINUX_VERSION_CODE >= KERNEL_VERSION(5, 4, 0) 25 #include <linux/fscrypt.h> 26 #else 27 #include "fscrypt_uapi.h" 28 #endif 29 30 namespace OHOS { 31 namespace StorageDaemon { 32 using key_serial_t = int; 33 constexpr uint32_t CRYPTO_KEY_DESC_SIZE = FSCRYPT_KEY_DESCRIPTOR_SIZE; 34 static const std::string MNT_DATA = "/data"; 35 static const std::string PATH_LATEST = "/latest"; 36 static const std::string PATH_FSCRYPT_VER = "/fscrypt_version"; 37 static const std::string PATH_ALIAS = "/alias"; 38 static const std::string PATH_SECDISC = "/sec_discard"; 39 static const std::string PATH_ENCRYPTED = "/encrypted"; 40 static const std::string PATH_KEYID = "/key_id"; 41 static const std::string PATH_KEYDESC = "/key_desc"; 42 43 enum { 44 FSCRYPT_INVALID = 0, 45 FSCRYPT_V1 = 1, 46 FSCRYPT_V2 = 2, 47 }; 48 49 union FscryptPolicy { 50 fscrypt_policy_v1 v1; 51 fscrypt_policy_v2 v2; 52 }; 53 54 class KeyCtrl { 55 public: 56 // ------ fscrypt legacy ------ 57 static key_serial_t AddKey(const std::string &type, const std::string &description, const key_serial_t ringId); 58 static key_serial_t AddKey(const std::string &type, const std::string &description, fscrypt_key &fsKey, 59 const key_serial_t ringId); 60 static key_serial_t GetKeyring(key_serial_t id, int create); 61 static long Revoke(key_serial_t id); 62 static long Search(key_serial_t ringId, const std::string &type, const std::string &description, 63 key_serial_t destRingId); 64 static long SetPermission(key_serial_t id, int permissions); 65 static long Unlink(key_serial_t key, key_serial_t keyring); 66 static long RestrictKeyring(key_serial_t keyring, const std::string &type, const std::string &restriction); 67 static long GetSecurity(key_serial_t key, std::string &buffer); 68 69 // ------ fscrypt v2 ------ 70 static bool InstallKey(const std::string &mnt, fscrypt_add_key_arg &arg); 71 static bool RemoveKey(const std::string &mnt, fscrypt_remove_key_arg &arg); 72 static bool GetKeyStatus(const std::string &mnt, fscrypt_get_key_status_arg &arg); 73 74 static bool SetPolicy(const std::string &path, FscryptPolicy &policy); 75 static bool GetPolicy(const std::string &path, fscrypt_policy &policy); 76 static bool GetPolicy(const std::string &path, fscrypt_get_policy_ex_arg &policy); 77 static bool LoadAndSetPolicy(const std::string &keyPath, const std::string &toEncrypt); 78 static uint8_t LoadVersion(const std::string &keyPath); 79 80 static uint8_t GetFscryptVersion(const std::string &mnt); 81 static uint8_t GetEncryptedVersion(const std::string &dir); 82 static int32_t InitFscryptPolicy(); 83 static int32_t SetFscryptSyspara(const std::string &config); 84 static bool HasFscryptSyspara(); 85 static std::string CheckRealPath(const std::string &path); 86 }; 87 88 struct EncryptPolicy { 89 std::string version; 90 std::string fileName; 91 std::string content; 92 std::string flags; 93 bool hwWrappedKey { false }; 94 }; 95 96 static const EncryptPolicy DEFAULT_POLICY = { 97 .version = "2", 98 .fileName = "aes-256-cts", 99 .content = "aes-256-xts", 100 .flags = "padding-32", 101 .hwWrappedKey = false, 102 }; 103 104 static const auto ALL_VERSION = std::map<std::string, uint8_t> { 105 {"1", FSCRYPT_V1}, 106 {"2", FSCRYPT_V2}, 107 }; 108 109 static const auto FILENAME_MODES = std::map<std::string, uint8_t> { 110 {"aes-256-cts", FSCRYPT_MODE_AES_256_CTS}, 111 }; 112 113 static const auto CONTENTS_MODES = std::map<std::string, uint8_t> { 114 {"aes-256-xts", FSCRYPT_MODE_AES_256_XTS}, 115 }; 116 // To use Adiantum, CONFIG_CRYPTO_ADIANTUM must be enabled. 117 // Also, fast implementations of ChaCha and NHPoly1305 should be enabled, 118 // e.g. CONFIG_CRYPTO_CHACHA20_NEON and CONFIG_CRYPTO_NHPOLY1305_NEON for ARM. 119 120 static const auto POLICY_FLAGS = std::map<std::string, uint8_t> { 121 {"padding-4", FSCRYPT_POLICY_FLAGS_PAD_4}, 122 {"padding-8", FSCRYPT_POLICY_FLAGS_PAD_8}, 123 {"padding-16", FSCRYPT_POLICY_FLAGS_PAD_16}, 124 {"padding-32", FSCRYPT_POLICY_FLAGS_PAD_32}, 125 // "direct-key" use with adiantum 126 }; 127 128 static const auto FSCRYPT_OPTIONS_TABLE = std::vector<std::map<std::string, uint8_t>> { 129 ALL_VERSION, 130 FILENAME_MODES, 131 CONTENTS_MODES, 132 }; 133 } // namespace StorageDaemon 134 } // namespace OHOS 135 136 #endif // STORAGE_DAEMON_CRYPTO_KEYCTL_H 137