162306a36Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0 */ 262306a36Sopenharmony_ci/* 362306a36Sopenharmony_ci * fscrypt_private.h 462306a36Sopenharmony_ci * 562306a36Sopenharmony_ci * Copyright (C) 2015, Google, Inc. 662306a36Sopenharmony_ci * 762306a36Sopenharmony_ci * Originally written by Michael Halcrow, Ildar Muslukhov, and Uday Savagaonkar. 862306a36Sopenharmony_ci * Heavily modified since then. 962306a36Sopenharmony_ci */ 1062306a36Sopenharmony_ci 1162306a36Sopenharmony_ci#ifndef _FSCRYPT_PRIVATE_H 1262306a36Sopenharmony_ci#define _FSCRYPT_PRIVATE_H 1362306a36Sopenharmony_ci 1462306a36Sopenharmony_ci#include <linux/fscrypt.h> 1562306a36Sopenharmony_ci#include <linux/siphash.h> 1662306a36Sopenharmony_ci#include <crypto/hash.h> 1762306a36Sopenharmony_ci#include <linux/blk-crypto.h> 1862306a36Sopenharmony_ci 1962306a36Sopenharmony_ci#define CONST_STRLEN(str) (sizeof(str) - 1) 2062306a36Sopenharmony_ci 2162306a36Sopenharmony_ci#define FSCRYPT_FILE_NONCE_SIZE 16 2262306a36Sopenharmony_ci 2362306a36Sopenharmony_ci/* 2462306a36Sopenharmony_ci * Minimum size of an fscrypt master key. Note: a longer key will be required 2562306a36Sopenharmony_ci * if ciphers with a 256-bit security strength are used. This is just the 2662306a36Sopenharmony_ci * absolute minimum, which applies when only 128-bit encryption is used. 2762306a36Sopenharmony_ci */ 2862306a36Sopenharmony_ci#define FSCRYPT_MIN_KEY_SIZE 16 2962306a36Sopenharmony_ci 3062306a36Sopenharmony_ci#define FSCRYPT_CONTEXT_V1 1 3162306a36Sopenharmony_ci#define FSCRYPT_CONTEXT_V2 2 3262306a36Sopenharmony_ci 3362306a36Sopenharmony_ci/* Keep this in sync with include/uapi/linux/fscrypt.h */ 3462306a36Sopenharmony_ci#define FSCRYPT_MODE_MAX FSCRYPT_MODE_AES_256_HCTR2 3562306a36Sopenharmony_ci 3662306a36Sopenharmony_cistruct fscrypt_context_v1 { 3762306a36Sopenharmony_ci u8 version; /* FSCRYPT_CONTEXT_V1 */ 3862306a36Sopenharmony_ci u8 contents_encryption_mode; 3962306a36Sopenharmony_ci u8 filenames_encryption_mode; 4062306a36Sopenharmony_ci u8 flags; 4162306a36Sopenharmony_ci u8 master_key_descriptor[FSCRYPT_KEY_DESCRIPTOR_SIZE]; 4262306a36Sopenharmony_ci u8 nonce[FSCRYPT_FILE_NONCE_SIZE]; 4362306a36Sopenharmony_ci}; 4462306a36Sopenharmony_ci 4562306a36Sopenharmony_cistruct fscrypt_context_v2 { 4662306a36Sopenharmony_ci u8 version; /* FSCRYPT_CONTEXT_V2 */ 4762306a36Sopenharmony_ci u8 contents_encryption_mode; 4862306a36Sopenharmony_ci u8 filenames_encryption_mode; 4962306a36Sopenharmony_ci u8 flags; 5062306a36Sopenharmony_ci u8 __reserved[4]; 5162306a36Sopenharmony_ci u8 master_key_identifier[FSCRYPT_KEY_IDENTIFIER_SIZE]; 5262306a36Sopenharmony_ci u8 nonce[FSCRYPT_FILE_NONCE_SIZE]; 5362306a36Sopenharmony_ci}; 5462306a36Sopenharmony_ci 5562306a36Sopenharmony_ci/* 5662306a36Sopenharmony_ci * fscrypt_context - the encryption context of an inode 5762306a36Sopenharmony_ci * 5862306a36Sopenharmony_ci * This is the on-disk equivalent of an fscrypt_policy, stored alongside each 5962306a36Sopenharmony_ci * encrypted file usually in a hidden extended attribute. It contains the 6062306a36Sopenharmony_ci * fields from the fscrypt_policy, in order to identify the encryption algorithm 6162306a36Sopenharmony_ci * and key with which the file is encrypted. It also contains a nonce that was 6262306a36Sopenharmony_ci * randomly generated by fscrypt itself; this is used as KDF input or as a tweak 6362306a36Sopenharmony_ci * to cause different files to be encrypted differently. 6462306a36Sopenharmony_ci */ 6562306a36Sopenharmony_ciunion fscrypt_context { 6662306a36Sopenharmony_ci u8 version; 6762306a36Sopenharmony_ci struct fscrypt_context_v1 v1; 6862306a36Sopenharmony_ci struct fscrypt_context_v2 v2; 6962306a36Sopenharmony_ci}; 7062306a36Sopenharmony_ci 7162306a36Sopenharmony_ci/* 7262306a36Sopenharmony_ci * Return the size expected for the given fscrypt_context based on its version 7362306a36Sopenharmony_ci * number, or 0 if the context version is unrecognized. 7462306a36Sopenharmony_ci */ 7562306a36Sopenharmony_cistatic inline int fscrypt_context_size(const union fscrypt_context *ctx) 7662306a36Sopenharmony_ci{ 7762306a36Sopenharmony_ci switch (ctx->version) { 7862306a36Sopenharmony_ci case FSCRYPT_CONTEXT_V1: 7962306a36Sopenharmony_ci BUILD_BUG_ON(sizeof(ctx->v1) != 28); 8062306a36Sopenharmony_ci return sizeof(ctx->v1); 8162306a36Sopenharmony_ci case FSCRYPT_CONTEXT_V2: 8262306a36Sopenharmony_ci BUILD_BUG_ON(sizeof(ctx->v2) != 40); 8362306a36Sopenharmony_ci return sizeof(ctx->v2); 8462306a36Sopenharmony_ci } 8562306a36Sopenharmony_ci return 0; 8662306a36Sopenharmony_ci} 8762306a36Sopenharmony_ci 8862306a36Sopenharmony_ci/* Check whether an fscrypt_context has a recognized version number and size */ 8962306a36Sopenharmony_cistatic inline bool fscrypt_context_is_valid(const union fscrypt_context *ctx, 9062306a36Sopenharmony_ci int ctx_size) 9162306a36Sopenharmony_ci{ 9262306a36Sopenharmony_ci return ctx_size >= 1 && ctx_size == fscrypt_context_size(ctx); 9362306a36Sopenharmony_ci} 9462306a36Sopenharmony_ci 9562306a36Sopenharmony_ci/* Retrieve the context's nonce, assuming the context was already validated */ 9662306a36Sopenharmony_cistatic inline const u8 *fscrypt_context_nonce(const union fscrypt_context *ctx) 9762306a36Sopenharmony_ci{ 9862306a36Sopenharmony_ci switch (ctx->version) { 9962306a36Sopenharmony_ci case FSCRYPT_CONTEXT_V1: 10062306a36Sopenharmony_ci return ctx->v1.nonce; 10162306a36Sopenharmony_ci case FSCRYPT_CONTEXT_V2: 10262306a36Sopenharmony_ci return ctx->v2.nonce; 10362306a36Sopenharmony_ci } 10462306a36Sopenharmony_ci WARN_ON_ONCE(1); 10562306a36Sopenharmony_ci return NULL; 10662306a36Sopenharmony_ci} 10762306a36Sopenharmony_ci 10862306a36Sopenharmony_ciunion fscrypt_policy { 10962306a36Sopenharmony_ci u8 version; 11062306a36Sopenharmony_ci struct fscrypt_policy_v1 v1; 11162306a36Sopenharmony_ci struct fscrypt_policy_v2 v2; 11262306a36Sopenharmony_ci}; 11362306a36Sopenharmony_ci 11462306a36Sopenharmony_ci/* 11562306a36Sopenharmony_ci * Return the size expected for the given fscrypt_policy based on its version 11662306a36Sopenharmony_ci * number, or 0 if the policy version is unrecognized. 11762306a36Sopenharmony_ci */ 11862306a36Sopenharmony_cistatic inline int fscrypt_policy_size(const union fscrypt_policy *policy) 11962306a36Sopenharmony_ci{ 12062306a36Sopenharmony_ci switch (policy->version) { 12162306a36Sopenharmony_ci case FSCRYPT_POLICY_V1: 12262306a36Sopenharmony_ci return sizeof(policy->v1); 12362306a36Sopenharmony_ci case FSCRYPT_POLICY_V2: 12462306a36Sopenharmony_ci return sizeof(policy->v2); 12562306a36Sopenharmony_ci } 12662306a36Sopenharmony_ci return 0; 12762306a36Sopenharmony_ci} 12862306a36Sopenharmony_ci 12962306a36Sopenharmony_ci/* Return the contents encryption mode of a valid encryption policy */ 13062306a36Sopenharmony_cistatic inline u8 13162306a36Sopenharmony_cifscrypt_policy_contents_mode(const union fscrypt_policy *policy) 13262306a36Sopenharmony_ci{ 13362306a36Sopenharmony_ci switch (policy->version) { 13462306a36Sopenharmony_ci case FSCRYPT_POLICY_V1: 13562306a36Sopenharmony_ci return policy->v1.contents_encryption_mode; 13662306a36Sopenharmony_ci case FSCRYPT_POLICY_V2: 13762306a36Sopenharmony_ci return policy->v2.contents_encryption_mode; 13862306a36Sopenharmony_ci } 13962306a36Sopenharmony_ci BUG(); 14062306a36Sopenharmony_ci} 14162306a36Sopenharmony_ci 14262306a36Sopenharmony_ci/* Return the filenames encryption mode of a valid encryption policy */ 14362306a36Sopenharmony_cistatic inline u8 14462306a36Sopenharmony_cifscrypt_policy_fnames_mode(const union fscrypt_policy *policy) 14562306a36Sopenharmony_ci{ 14662306a36Sopenharmony_ci switch (policy->version) { 14762306a36Sopenharmony_ci case FSCRYPT_POLICY_V1: 14862306a36Sopenharmony_ci return policy->v1.filenames_encryption_mode; 14962306a36Sopenharmony_ci case FSCRYPT_POLICY_V2: 15062306a36Sopenharmony_ci return policy->v2.filenames_encryption_mode; 15162306a36Sopenharmony_ci } 15262306a36Sopenharmony_ci BUG(); 15362306a36Sopenharmony_ci} 15462306a36Sopenharmony_ci 15562306a36Sopenharmony_ci/* Return the flags (FSCRYPT_POLICY_FLAG*) of a valid encryption policy */ 15662306a36Sopenharmony_cistatic inline u8 15762306a36Sopenharmony_cifscrypt_policy_flags(const union fscrypt_policy *policy) 15862306a36Sopenharmony_ci{ 15962306a36Sopenharmony_ci switch (policy->version) { 16062306a36Sopenharmony_ci case FSCRYPT_POLICY_V1: 16162306a36Sopenharmony_ci return policy->v1.flags; 16262306a36Sopenharmony_ci case FSCRYPT_POLICY_V2: 16362306a36Sopenharmony_ci return policy->v2.flags; 16462306a36Sopenharmony_ci } 16562306a36Sopenharmony_ci BUG(); 16662306a36Sopenharmony_ci} 16762306a36Sopenharmony_ci 16862306a36Sopenharmony_ci/* 16962306a36Sopenharmony_ci * For encrypted symlinks, the ciphertext length is stored at the beginning 17062306a36Sopenharmony_ci * of the string in little-endian format. 17162306a36Sopenharmony_ci */ 17262306a36Sopenharmony_cistruct fscrypt_symlink_data { 17362306a36Sopenharmony_ci __le16 len; 17462306a36Sopenharmony_ci char encrypted_path[]; 17562306a36Sopenharmony_ci} __packed; 17662306a36Sopenharmony_ci 17762306a36Sopenharmony_ci/** 17862306a36Sopenharmony_ci * struct fscrypt_prepared_key - a key prepared for actual encryption/decryption 17962306a36Sopenharmony_ci * @tfm: crypto API transform object 18062306a36Sopenharmony_ci * @blk_key: key for blk-crypto 18162306a36Sopenharmony_ci * 18262306a36Sopenharmony_ci * Normally only one of the fields will be non-NULL. 18362306a36Sopenharmony_ci */ 18462306a36Sopenharmony_cistruct fscrypt_prepared_key { 18562306a36Sopenharmony_ci struct crypto_skcipher *tfm; 18662306a36Sopenharmony_ci#ifdef CONFIG_FS_ENCRYPTION_INLINE_CRYPT 18762306a36Sopenharmony_ci struct blk_crypto_key *blk_key; 18862306a36Sopenharmony_ci#endif 18962306a36Sopenharmony_ci}; 19062306a36Sopenharmony_ci 19162306a36Sopenharmony_ci/* 19262306a36Sopenharmony_ci * fscrypt_info - the "encryption key" for an inode 19362306a36Sopenharmony_ci * 19462306a36Sopenharmony_ci * When an encrypted file's key is made available, an instance of this struct is 19562306a36Sopenharmony_ci * allocated and stored in ->i_crypt_info. Once created, it remains until the 19662306a36Sopenharmony_ci * inode is evicted. 19762306a36Sopenharmony_ci */ 19862306a36Sopenharmony_cistruct fscrypt_info { 19962306a36Sopenharmony_ci 20062306a36Sopenharmony_ci /* The key in a form prepared for actual encryption/decryption */ 20162306a36Sopenharmony_ci struct fscrypt_prepared_key ci_enc_key; 20262306a36Sopenharmony_ci 20362306a36Sopenharmony_ci /* True if ci_enc_key should be freed when this fscrypt_info is freed */ 20462306a36Sopenharmony_ci bool ci_owns_key; 20562306a36Sopenharmony_ci 20662306a36Sopenharmony_ci#ifdef CONFIG_FS_ENCRYPTION_INLINE_CRYPT 20762306a36Sopenharmony_ci /* 20862306a36Sopenharmony_ci * True if this inode will use inline encryption (blk-crypto) instead of 20962306a36Sopenharmony_ci * the traditional filesystem-layer encryption. 21062306a36Sopenharmony_ci */ 21162306a36Sopenharmony_ci bool ci_inlinecrypt; 21262306a36Sopenharmony_ci#endif 21362306a36Sopenharmony_ci 21462306a36Sopenharmony_ci /* 21562306a36Sopenharmony_ci * Encryption mode used for this inode. It corresponds to either the 21662306a36Sopenharmony_ci * contents or filenames encryption mode, depending on the inode type. 21762306a36Sopenharmony_ci */ 21862306a36Sopenharmony_ci struct fscrypt_mode *ci_mode; 21962306a36Sopenharmony_ci 22062306a36Sopenharmony_ci /* Back-pointer to the inode */ 22162306a36Sopenharmony_ci struct inode *ci_inode; 22262306a36Sopenharmony_ci 22362306a36Sopenharmony_ci /* 22462306a36Sopenharmony_ci * The master key with which this inode was unlocked (decrypted). This 22562306a36Sopenharmony_ci * will be NULL if the master key was found in a process-subscribed 22662306a36Sopenharmony_ci * keyring rather than in the filesystem-level keyring. 22762306a36Sopenharmony_ci */ 22862306a36Sopenharmony_ci struct fscrypt_master_key *ci_master_key; 22962306a36Sopenharmony_ci 23062306a36Sopenharmony_ci /* 23162306a36Sopenharmony_ci * Link in list of inodes that were unlocked with the master key. 23262306a36Sopenharmony_ci * Only used when ->ci_master_key is set. 23362306a36Sopenharmony_ci */ 23462306a36Sopenharmony_ci struct list_head ci_master_key_link; 23562306a36Sopenharmony_ci 23662306a36Sopenharmony_ci /* 23762306a36Sopenharmony_ci * If non-NULL, then encryption is done using the master key directly 23862306a36Sopenharmony_ci * and ci_enc_key will equal ci_direct_key->dk_key. 23962306a36Sopenharmony_ci */ 24062306a36Sopenharmony_ci struct fscrypt_direct_key *ci_direct_key; 24162306a36Sopenharmony_ci 24262306a36Sopenharmony_ci /* 24362306a36Sopenharmony_ci * This inode's hash key for filenames. This is a 128-bit SipHash-2-4 24462306a36Sopenharmony_ci * key. This is only set for directories that use a keyed dirhash over 24562306a36Sopenharmony_ci * the plaintext filenames -- currently just casefolded directories. 24662306a36Sopenharmony_ci */ 24762306a36Sopenharmony_ci siphash_key_t ci_dirhash_key; 24862306a36Sopenharmony_ci bool ci_dirhash_key_initialized; 24962306a36Sopenharmony_ci 25062306a36Sopenharmony_ci /* The encryption policy used by this inode */ 25162306a36Sopenharmony_ci union fscrypt_policy ci_policy; 25262306a36Sopenharmony_ci 25362306a36Sopenharmony_ci /* This inode's nonce, copied from the fscrypt_context */ 25462306a36Sopenharmony_ci u8 ci_nonce[FSCRYPT_FILE_NONCE_SIZE]; 25562306a36Sopenharmony_ci 25662306a36Sopenharmony_ci /* Hashed inode number. Only set for IV_INO_LBLK_32 */ 25762306a36Sopenharmony_ci u32 ci_hashed_ino; 25862306a36Sopenharmony_ci}; 25962306a36Sopenharmony_ci 26062306a36Sopenharmony_citypedef enum { 26162306a36Sopenharmony_ci FS_DECRYPT = 0, 26262306a36Sopenharmony_ci FS_ENCRYPT, 26362306a36Sopenharmony_ci} fscrypt_direction_t; 26462306a36Sopenharmony_ci 26562306a36Sopenharmony_ci/* crypto.c */ 26662306a36Sopenharmony_ciextern struct kmem_cache *fscrypt_info_cachep; 26762306a36Sopenharmony_ciint fscrypt_initialize(struct super_block *sb); 26862306a36Sopenharmony_ciint fscrypt_crypt_block(const struct inode *inode, fscrypt_direction_t rw, 26962306a36Sopenharmony_ci u64 lblk_num, struct page *src_page, 27062306a36Sopenharmony_ci struct page *dest_page, unsigned int len, 27162306a36Sopenharmony_ci unsigned int offs, gfp_t gfp_flags); 27262306a36Sopenharmony_cistruct page *fscrypt_alloc_bounce_page(gfp_t gfp_flags); 27362306a36Sopenharmony_ci 27462306a36Sopenharmony_civoid __printf(3, 4) __cold 27562306a36Sopenharmony_cifscrypt_msg(const struct inode *inode, const char *level, const char *fmt, ...); 27662306a36Sopenharmony_ci 27762306a36Sopenharmony_ci#define fscrypt_warn(inode, fmt, ...) \ 27862306a36Sopenharmony_ci fscrypt_msg((inode), KERN_WARNING, fmt, ##__VA_ARGS__) 27962306a36Sopenharmony_ci#define fscrypt_err(inode, fmt, ...) \ 28062306a36Sopenharmony_ci fscrypt_msg((inode), KERN_ERR, fmt, ##__VA_ARGS__) 28162306a36Sopenharmony_ci 28262306a36Sopenharmony_ci#define FSCRYPT_MAX_IV_SIZE 32 28362306a36Sopenharmony_ci 28462306a36Sopenharmony_ciunion fscrypt_iv { 28562306a36Sopenharmony_ci struct { 28662306a36Sopenharmony_ci /* logical block number within the file */ 28762306a36Sopenharmony_ci __le64 lblk_num; 28862306a36Sopenharmony_ci 28962306a36Sopenharmony_ci /* per-file nonce; only set in DIRECT_KEY mode */ 29062306a36Sopenharmony_ci u8 nonce[FSCRYPT_FILE_NONCE_SIZE]; 29162306a36Sopenharmony_ci }; 29262306a36Sopenharmony_ci u8 raw[FSCRYPT_MAX_IV_SIZE]; 29362306a36Sopenharmony_ci __le64 dun[FSCRYPT_MAX_IV_SIZE / sizeof(__le64)]; 29462306a36Sopenharmony_ci}; 29562306a36Sopenharmony_ci 29662306a36Sopenharmony_civoid fscrypt_generate_iv(union fscrypt_iv *iv, u64 lblk_num, 29762306a36Sopenharmony_ci const struct fscrypt_info *ci); 29862306a36Sopenharmony_ci 29962306a36Sopenharmony_ci/* fname.c */ 30062306a36Sopenharmony_cibool __fscrypt_fname_encrypted_size(const union fscrypt_policy *policy, 30162306a36Sopenharmony_ci u32 orig_len, u32 max_len, 30262306a36Sopenharmony_ci u32 *encrypted_len_ret); 30362306a36Sopenharmony_ci 30462306a36Sopenharmony_ci/* hkdf.c */ 30562306a36Sopenharmony_cistruct fscrypt_hkdf { 30662306a36Sopenharmony_ci struct crypto_shash *hmac_tfm; 30762306a36Sopenharmony_ci}; 30862306a36Sopenharmony_ci 30962306a36Sopenharmony_ciint fscrypt_init_hkdf(struct fscrypt_hkdf *hkdf, const u8 *master_key, 31062306a36Sopenharmony_ci unsigned int master_key_size); 31162306a36Sopenharmony_ci 31262306a36Sopenharmony_ci/* 31362306a36Sopenharmony_ci * The list of contexts in which fscrypt uses HKDF. These values are used as 31462306a36Sopenharmony_ci * the first byte of the HKDF application-specific info string to guarantee that 31562306a36Sopenharmony_ci * info strings are never repeated between contexts. This ensures that all HKDF 31662306a36Sopenharmony_ci * outputs are unique and cryptographically isolated, i.e. knowledge of one 31762306a36Sopenharmony_ci * output doesn't reveal another. 31862306a36Sopenharmony_ci */ 31962306a36Sopenharmony_ci#define HKDF_CONTEXT_KEY_IDENTIFIER 1 /* info=<empty> */ 32062306a36Sopenharmony_ci#define HKDF_CONTEXT_PER_FILE_ENC_KEY 2 /* info=file_nonce */ 32162306a36Sopenharmony_ci#define HKDF_CONTEXT_DIRECT_KEY 3 /* info=mode_num */ 32262306a36Sopenharmony_ci#define HKDF_CONTEXT_IV_INO_LBLK_64_KEY 4 /* info=mode_num||fs_uuid */ 32362306a36Sopenharmony_ci#define HKDF_CONTEXT_DIRHASH_KEY 5 /* info=file_nonce */ 32462306a36Sopenharmony_ci#define HKDF_CONTEXT_IV_INO_LBLK_32_KEY 6 /* info=mode_num||fs_uuid */ 32562306a36Sopenharmony_ci#define HKDF_CONTEXT_INODE_HASH_KEY 7 /* info=<empty> */ 32662306a36Sopenharmony_ci 32762306a36Sopenharmony_ciint fscrypt_hkdf_expand(const struct fscrypt_hkdf *hkdf, u8 context, 32862306a36Sopenharmony_ci const u8 *info, unsigned int infolen, 32962306a36Sopenharmony_ci u8 *okm, unsigned int okmlen); 33062306a36Sopenharmony_ci 33162306a36Sopenharmony_civoid fscrypt_destroy_hkdf(struct fscrypt_hkdf *hkdf); 33262306a36Sopenharmony_ci 33362306a36Sopenharmony_ci/* inline_crypt.c */ 33462306a36Sopenharmony_ci#ifdef CONFIG_FS_ENCRYPTION_INLINE_CRYPT 33562306a36Sopenharmony_ciint fscrypt_select_encryption_impl(struct fscrypt_info *ci); 33662306a36Sopenharmony_ci 33762306a36Sopenharmony_cistatic inline bool 33862306a36Sopenharmony_cifscrypt_using_inline_encryption(const struct fscrypt_info *ci) 33962306a36Sopenharmony_ci{ 34062306a36Sopenharmony_ci return ci->ci_inlinecrypt; 34162306a36Sopenharmony_ci} 34262306a36Sopenharmony_ci 34362306a36Sopenharmony_ciint fscrypt_prepare_inline_crypt_key(struct fscrypt_prepared_key *prep_key, 34462306a36Sopenharmony_ci const u8 *raw_key, 34562306a36Sopenharmony_ci const struct fscrypt_info *ci); 34662306a36Sopenharmony_ci 34762306a36Sopenharmony_civoid fscrypt_destroy_inline_crypt_key(struct super_block *sb, 34862306a36Sopenharmony_ci struct fscrypt_prepared_key *prep_key); 34962306a36Sopenharmony_ci 35062306a36Sopenharmony_ci/* 35162306a36Sopenharmony_ci * Check whether the crypto transform or blk-crypto key has been allocated in 35262306a36Sopenharmony_ci * @prep_key, depending on which encryption implementation the file will use. 35362306a36Sopenharmony_ci */ 35462306a36Sopenharmony_cistatic inline bool 35562306a36Sopenharmony_cifscrypt_is_key_prepared(struct fscrypt_prepared_key *prep_key, 35662306a36Sopenharmony_ci const struct fscrypt_info *ci) 35762306a36Sopenharmony_ci{ 35862306a36Sopenharmony_ci /* 35962306a36Sopenharmony_ci * The two smp_load_acquire()'s here pair with the smp_store_release()'s 36062306a36Sopenharmony_ci * in fscrypt_prepare_inline_crypt_key() and fscrypt_prepare_key(). 36162306a36Sopenharmony_ci * I.e., in some cases (namely, if this prep_key is a per-mode 36262306a36Sopenharmony_ci * encryption key) another task can publish blk_key or tfm concurrently, 36362306a36Sopenharmony_ci * executing a RELEASE barrier. We need to use smp_load_acquire() here 36462306a36Sopenharmony_ci * to safely ACQUIRE the memory the other task published. 36562306a36Sopenharmony_ci */ 36662306a36Sopenharmony_ci if (fscrypt_using_inline_encryption(ci)) 36762306a36Sopenharmony_ci return smp_load_acquire(&prep_key->blk_key) != NULL; 36862306a36Sopenharmony_ci return smp_load_acquire(&prep_key->tfm) != NULL; 36962306a36Sopenharmony_ci} 37062306a36Sopenharmony_ci 37162306a36Sopenharmony_ci#else /* CONFIG_FS_ENCRYPTION_INLINE_CRYPT */ 37262306a36Sopenharmony_ci 37362306a36Sopenharmony_cistatic inline int fscrypt_select_encryption_impl(struct fscrypt_info *ci) 37462306a36Sopenharmony_ci{ 37562306a36Sopenharmony_ci return 0; 37662306a36Sopenharmony_ci} 37762306a36Sopenharmony_ci 37862306a36Sopenharmony_cistatic inline bool 37962306a36Sopenharmony_cifscrypt_using_inline_encryption(const struct fscrypt_info *ci) 38062306a36Sopenharmony_ci{ 38162306a36Sopenharmony_ci return false; 38262306a36Sopenharmony_ci} 38362306a36Sopenharmony_ci 38462306a36Sopenharmony_cistatic inline int 38562306a36Sopenharmony_cifscrypt_prepare_inline_crypt_key(struct fscrypt_prepared_key *prep_key, 38662306a36Sopenharmony_ci const u8 *raw_key, 38762306a36Sopenharmony_ci const struct fscrypt_info *ci) 38862306a36Sopenharmony_ci{ 38962306a36Sopenharmony_ci WARN_ON_ONCE(1); 39062306a36Sopenharmony_ci return -EOPNOTSUPP; 39162306a36Sopenharmony_ci} 39262306a36Sopenharmony_ci 39362306a36Sopenharmony_cistatic inline void 39462306a36Sopenharmony_cifscrypt_destroy_inline_crypt_key(struct super_block *sb, 39562306a36Sopenharmony_ci struct fscrypt_prepared_key *prep_key) 39662306a36Sopenharmony_ci{ 39762306a36Sopenharmony_ci} 39862306a36Sopenharmony_ci 39962306a36Sopenharmony_cistatic inline bool 40062306a36Sopenharmony_cifscrypt_is_key_prepared(struct fscrypt_prepared_key *prep_key, 40162306a36Sopenharmony_ci const struct fscrypt_info *ci) 40262306a36Sopenharmony_ci{ 40362306a36Sopenharmony_ci return smp_load_acquire(&prep_key->tfm) != NULL; 40462306a36Sopenharmony_ci} 40562306a36Sopenharmony_ci#endif /* !CONFIG_FS_ENCRYPTION_INLINE_CRYPT */ 40662306a36Sopenharmony_ci 40762306a36Sopenharmony_ci/* keyring.c */ 40862306a36Sopenharmony_ci 40962306a36Sopenharmony_ci/* 41062306a36Sopenharmony_ci * fscrypt_master_key_secret - secret key material of an in-use master key 41162306a36Sopenharmony_ci */ 41262306a36Sopenharmony_cistruct fscrypt_master_key_secret { 41362306a36Sopenharmony_ci 41462306a36Sopenharmony_ci /* 41562306a36Sopenharmony_ci * For v2 policy keys: HKDF context keyed by this master key. 41662306a36Sopenharmony_ci * For v1 policy keys: not set (hkdf.hmac_tfm == NULL). 41762306a36Sopenharmony_ci */ 41862306a36Sopenharmony_ci struct fscrypt_hkdf hkdf; 41962306a36Sopenharmony_ci 42062306a36Sopenharmony_ci /* 42162306a36Sopenharmony_ci * Size of the raw key in bytes. This remains set even if ->raw was 42262306a36Sopenharmony_ci * zeroized due to no longer being needed. I.e. we still remember the 42362306a36Sopenharmony_ci * size of the key even if we don't need to remember the key itself. 42462306a36Sopenharmony_ci */ 42562306a36Sopenharmony_ci u32 size; 42662306a36Sopenharmony_ci 42762306a36Sopenharmony_ci /* For v1 policy keys: the raw key. Wiped for v2 policy keys. */ 42862306a36Sopenharmony_ci u8 raw[FSCRYPT_MAX_KEY_SIZE]; 42962306a36Sopenharmony_ci 43062306a36Sopenharmony_ci} __randomize_layout; 43162306a36Sopenharmony_ci 43262306a36Sopenharmony_ci/* 43362306a36Sopenharmony_ci * fscrypt_master_key - an in-use master key 43462306a36Sopenharmony_ci * 43562306a36Sopenharmony_ci * This represents a master encryption key which has been added to the 43662306a36Sopenharmony_ci * filesystem and can be used to "unlock" the encrypted files which were 43762306a36Sopenharmony_ci * encrypted with it. 43862306a36Sopenharmony_ci */ 43962306a36Sopenharmony_cistruct fscrypt_master_key { 44062306a36Sopenharmony_ci 44162306a36Sopenharmony_ci /* 44262306a36Sopenharmony_ci * Link in ->s_master_keys->key_hashtable. 44362306a36Sopenharmony_ci * Only valid if ->mk_active_refs > 0. 44462306a36Sopenharmony_ci */ 44562306a36Sopenharmony_ci struct hlist_node mk_node; 44662306a36Sopenharmony_ci 44762306a36Sopenharmony_ci /* Semaphore that protects ->mk_secret and ->mk_users */ 44862306a36Sopenharmony_ci struct rw_semaphore mk_sem; 44962306a36Sopenharmony_ci 45062306a36Sopenharmony_ci /* 45162306a36Sopenharmony_ci * Active and structural reference counts. An active ref guarantees 45262306a36Sopenharmony_ci * that the struct continues to exist, continues to be in the keyring 45362306a36Sopenharmony_ci * ->s_master_keys, and that any embedded subkeys (e.g. 45462306a36Sopenharmony_ci * ->mk_direct_keys) that have been prepared continue to exist. 45562306a36Sopenharmony_ci * A structural ref only guarantees that the struct continues to exist. 45662306a36Sopenharmony_ci * 45762306a36Sopenharmony_ci * There is one active ref associated with ->mk_secret being present, 45862306a36Sopenharmony_ci * and one active ref for each inode in ->mk_decrypted_inodes. 45962306a36Sopenharmony_ci * 46062306a36Sopenharmony_ci * There is one structural ref associated with the active refcount being 46162306a36Sopenharmony_ci * nonzero. Finding a key in the keyring also takes a structural ref, 46262306a36Sopenharmony_ci * which is then held temporarily while the key is operated on. 46362306a36Sopenharmony_ci */ 46462306a36Sopenharmony_ci refcount_t mk_active_refs; 46562306a36Sopenharmony_ci refcount_t mk_struct_refs; 46662306a36Sopenharmony_ci 46762306a36Sopenharmony_ci struct rcu_head mk_rcu_head; 46862306a36Sopenharmony_ci 46962306a36Sopenharmony_ci /* 47062306a36Sopenharmony_ci * The secret key material. After FS_IOC_REMOVE_ENCRYPTION_KEY is 47162306a36Sopenharmony_ci * executed, this is wiped and no new inodes can be unlocked with this 47262306a36Sopenharmony_ci * key; however, there may still be inodes in ->mk_decrypted_inodes 47362306a36Sopenharmony_ci * which could not be evicted. As long as some inodes still remain, 47462306a36Sopenharmony_ci * FS_IOC_REMOVE_ENCRYPTION_KEY can be retried, or 47562306a36Sopenharmony_ci * FS_IOC_ADD_ENCRYPTION_KEY can add the secret again. 47662306a36Sopenharmony_ci * 47762306a36Sopenharmony_ci * While ->mk_secret is present, one ref in ->mk_active_refs is held. 47862306a36Sopenharmony_ci * 47962306a36Sopenharmony_ci * Locking: protected by ->mk_sem. The manipulation of ->mk_active_refs 48062306a36Sopenharmony_ci * associated with this field is protected by ->mk_sem as well. 48162306a36Sopenharmony_ci */ 48262306a36Sopenharmony_ci struct fscrypt_master_key_secret mk_secret; 48362306a36Sopenharmony_ci 48462306a36Sopenharmony_ci /* 48562306a36Sopenharmony_ci * For v1 policy keys: an arbitrary key descriptor which was assigned by 48662306a36Sopenharmony_ci * userspace (->descriptor). 48762306a36Sopenharmony_ci * 48862306a36Sopenharmony_ci * For v2 policy keys: a cryptographic hash of this key (->identifier). 48962306a36Sopenharmony_ci */ 49062306a36Sopenharmony_ci struct fscrypt_key_specifier mk_spec; 49162306a36Sopenharmony_ci 49262306a36Sopenharmony_ci /* 49362306a36Sopenharmony_ci * Keyring which contains a key of type 'key_type_fscrypt_user' for each 49462306a36Sopenharmony_ci * user who has added this key. Normally each key will be added by just 49562306a36Sopenharmony_ci * one user, but it's possible that multiple users share a key, and in 49662306a36Sopenharmony_ci * that case we need to keep track of those users so that one user can't 49762306a36Sopenharmony_ci * remove the key before the others want it removed too. 49862306a36Sopenharmony_ci * 49962306a36Sopenharmony_ci * This is NULL for v1 policy keys; those can only be added by root. 50062306a36Sopenharmony_ci * 50162306a36Sopenharmony_ci * Locking: protected by ->mk_sem. (We don't just rely on the keyrings 50262306a36Sopenharmony_ci * subsystem semaphore ->mk_users->sem, as we need support for atomic 50362306a36Sopenharmony_ci * search+insert along with proper synchronization with ->mk_secret.) 50462306a36Sopenharmony_ci */ 50562306a36Sopenharmony_ci struct key *mk_users; 50662306a36Sopenharmony_ci 50762306a36Sopenharmony_ci /* 50862306a36Sopenharmony_ci * List of inodes that were unlocked using this key. This allows the 50962306a36Sopenharmony_ci * inodes to be evicted efficiently if the key is removed. 51062306a36Sopenharmony_ci */ 51162306a36Sopenharmony_ci struct list_head mk_decrypted_inodes; 51262306a36Sopenharmony_ci spinlock_t mk_decrypted_inodes_lock; 51362306a36Sopenharmony_ci 51462306a36Sopenharmony_ci /* 51562306a36Sopenharmony_ci * Per-mode encryption keys for the various types of encryption policies 51662306a36Sopenharmony_ci * that use them. Allocated and derived on-demand. 51762306a36Sopenharmony_ci */ 51862306a36Sopenharmony_ci struct fscrypt_prepared_key mk_direct_keys[FSCRYPT_MODE_MAX + 1]; 51962306a36Sopenharmony_ci struct fscrypt_prepared_key mk_iv_ino_lblk_64_keys[FSCRYPT_MODE_MAX + 1]; 52062306a36Sopenharmony_ci struct fscrypt_prepared_key mk_iv_ino_lblk_32_keys[FSCRYPT_MODE_MAX + 1]; 52162306a36Sopenharmony_ci 52262306a36Sopenharmony_ci /* Hash key for inode numbers. Initialized only when needed. */ 52362306a36Sopenharmony_ci siphash_key_t mk_ino_hash_key; 52462306a36Sopenharmony_ci bool mk_ino_hash_key_initialized; 52562306a36Sopenharmony_ci 52662306a36Sopenharmony_ci} __randomize_layout; 52762306a36Sopenharmony_ci 52862306a36Sopenharmony_cistatic inline bool 52962306a36Sopenharmony_ciis_master_key_secret_present(const struct fscrypt_master_key_secret *secret) 53062306a36Sopenharmony_ci{ 53162306a36Sopenharmony_ci /* 53262306a36Sopenharmony_ci * The READ_ONCE() is only necessary for fscrypt_drop_inode(). 53362306a36Sopenharmony_ci * fscrypt_drop_inode() runs in atomic context, so it can't take the key 53462306a36Sopenharmony_ci * semaphore and thus 'secret' can change concurrently which would be a 53562306a36Sopenharmony_ci * data race. But fscrypt_drop_inode() only need to know whether the 53662306a36Sopenharmony_ci * secret *was* present at the time of check, so READ_ONCE() suffices. 53762306a36Sopenharmony_ci */ 53862306a36Sopenharmony_ci return READ_ONCE(secret->size) != 0; 53962306a36Sopenharmony_ci} 54062306a36Sopenharmony_ci 54162306a36Sopenharmony_cistatic inline const char *master_key_spec_type( 54262306a36Sopenharmony_ci const struct fscrypt_key_specifier *spec) 54362306a36Sopenharmony_ci{ 54462306a36Sopenharmony_ci switch (spec->type) { 54562306a36Sopenharmony_ci case FSCRYPT_KEY_SPEC_TYPE_DESCRIPTOR: 54662306a36Sopenharmony_ci return "descriptor"; 54762306a36Sopenharmony_ci case FSCRYPT_KEY_SPEC_TYPE_IDENTIFIER: 54862306a36Sopenharmony_ci return "identifier"; 54962306a36Sopenharmony_ci } 55062306a36Sopenharmony_ci return "[unknown]"; 55162306a36Sopenharmony_ci} 55262306a36Sopenharmony_ci 55362306a36Sopenharmony_cistatic inline int master_key_spec_len(const struct fscrypt_key_specifier *spec) 55462306a36Sopenharmony_ci{ 55562306a36Sopenharmony_ci switch (spec->type) { 55662306a36Sopenharmony_ci case FSCRYPT_KEY_SPEC_TYPE_DESCRIPTOR: 55762306a36Sopenharmony_ci return FSCRYPT_KEY_DESCRIPTOR_SIZE; 55862306a36Sopenharmony_ci case FSCRYPT_KEY_SPEC_TYPE_IDENTIFIER: 55962306a36Sopenharmony_ci return FSCRYPT_KEY_IDENTIFIER_SIZE; 56062306a36Sopenharmony_ci } 56162306a36Sopenharmony_ci return 0; 56262306a36Sopenharmony_ci} 56362306a36Sopenharmony_ci 56462306a36Sopenharmony_civoid fscrypt_put_master_key(struct fscrypt_master_key *mk); 56562306a36Sopenharmony_ci 56662306a36Sopenharmony_civoid fscrypt_put_master_key_activeref(struct super_block *sb, 56762306a36Sopenharmony_ci struct fscrypt_master_key *mk); 56862306a36Sopenharmony_ci 56962306a36Sopenharmony_cistruct fscrypt_master_key * 57062306a36Sopenharmony_cifscrypt_find_master_key(struct super_block *sb, 57162306a36Sopenharmony_ci const struct fscrypt_key_specifier *mk_spec); 57262306a36Sopenharmony_ci 57362306a36Sopenharmony_ciint fscrypt_get_test_dummy_key_identifier( 57462306a36Sopenharmony_ci u8 key_identifier[FSCRYPT_KEY_IDENTIFIER_SIZE]); 57562306a36Sopenharmony_ci 57662306a36Sopenharmony_ciint fscrypt_add_test_dummy_key(struct super_block *sb, 57762306a36Sopenharmony_ci struct fscrypt_key_specifier *key_spec); 57862306a36Sopenharmony_ci 57962306a36Sopenharmony_ciint fscrypt_verify_key_added(struct super_block *sb, 58062306a36Sopenharmony_ci const u8 identifier[FSCRYPT_KEY_IDENTIFIER_SIZE]); 58162306a36Sopenharmony_ci 58262306a36Sopenharmony_ciint __init fscrypt_init_keyring(void); 58362306a36Sopenharmony_ci 58462306a36Sopenharmony_ci/* keysetup.c */ 58562306a36Sopenharmony_ci 58662306a36Sopenharmony_cistruct fscrypt_mode { 58762306a36Sopenharmony_ci const char *friendly_name; 58862306a36Sopenharmony_ci const char *cipher_str; 58962306a36Sopenharmony_ci int keysize; /* key size in bytes */ 59062306a36Sopenharmony_ci int security_strength; /* security strength in bytes */ 59162306a36Sopenharmony_ci int ivsize; /* IV size in bytes */ 59262306a36Sopenharmony_ci int logged_cryptoapi_impl; 59362306a36Sopenharmony_ci int logged_blk_crypto_native; 59462306a36Sopenharmony_ci int logged_blk_crypto_fallback; 59562306a36Sopenharmony_ci enum blk_crypto_mode_num blk_crypto_mode; 59662306a36Sopenharmony_ci}; 59762306a36Sopenharmony_ci 59862306a36Sopenharmony_ciextern struct fscrypt_mode fscrypt_modes[]; 59962306a36Sopenharmony_ci 60062306a36Sopenharmony_ciint fscrypt_prepare_key(struct fscrypt_prepared_key *prep_key, 60162306a36Sopenharmony_ci const u8 *raw_key, const struct fscrypt_info *ci); 60262306a36Sopenharmony_ci 60362306a36Sopenharmony_civoid fscrypt_destroy_prepared_key(struct super_block *sb, 60462306a36Sopenharmony_ci struct fscrypt_prepared_key *prep_key); 60562306a36Sopenharmony_ci 60662306a36Sopenharmony_ciint fscrypt_set_per_file_enc_key(struct fscrypt_info *ci, const u8 *raw_key); 60762306a36Sopenharmony_ci 60862306a36Sopenharmony_ciint fscrypt_derive_dirhash_key(struct fscrypt_info *ci, 60962306a36Sopenharmony_ci const struct fscrypt_master_key *mk); 61062306a36Sopenharmony_ci 61162306a36Sopenharmony_civoid fscrypt_hash_inode_number(struct fscrypt_info *ci, 61262306a36Sopenharmony_ci const struct fscrypt_master_key *mk); 61362306a36Sopenharmony_ci 61462306a36Sopenharmony_ciint fscrypt_get_encryption_info(struct inode *inode, bool allow_unsupported); 61562306a36Sopenharmony_ci 61662306a36Sopenharmony_ci/** 61762306a36Sopenharmony_ci * fscrypt_require_key() - require an inode's encryption key 61862306a36Sopenharmony_ci * @inode: the inode we need the key for 61962306a36Sopenharmony_ci * 62062306a36Sopenharmony_ci * If the inode is encrypted, set up its encryption key if not already done. 62162306a36Sopenharmony_ci * Then require that the key be present and return -ENOKEY otherwise. 62262306a36Sopenharmony_ci * 62362306a36Sopenharmony_ci * No locks are needed, and the key will live as long as the struct inode --- so 62462306a36Sopenharmony_ci * it won't go away from under you. 62562306a36Sopenharmony_ci * 62662306a36Sopenharmony_ci * Return: 0 on success, -ENOKEY if the key is missing, or another -errno code 62762306a36Sopenharmony_ci * if a problem occurred while setting up the encryption key. 62862306a36Sopenharmony_ci */ 62962306a36Sopenharmony_cistatic inline int fscrypt_require_key(struct inode *inode) 63062306a36Sopenharmony_ci{ 63162306a36Sopenharmony_ci if (IS_ENCRYPTED(inode)) { 63262306a36Sopenharmony_ci int err = fscrypt_get_encryption_info(inode, false); 63362306a36Sopenharmony_ci 63462306a36Sopenharmony_ci if (err) 63562306a36Sopenharmony_ci return err; 63662306a36Sopenharmony_ci if (!fscrypt_has_encryption_key(inode)) 63762306a36Sopenharmony_ci return -ENOKEY; 63862306a36Sopenharmony_ci } 63962306a36Sopenharmony_ci return 0; 64062306a36Sopenharmony_ci} 64162306a36Sopenharmony_ci 64262306a36Sopenharmony_ci/* keysetup_v1.c */ 64362306a36Sopenharmony_ci 64462306a36Sopenharmony_civoid fscrypt_put_direct_key(struct fscrypt_direct_key *dk); 64562306a36Sopenharmony_ci 64662306a36Sopenharmony_ciint fscrypt_setup_v1_file_key(struct fscrypt_info *ci, 64762306a36Sopenharmony_ci const u8 *raw_master_key); 64862306a36Sopenharmony_ci 64962306a36Sopenharmony_ciint fscrypt_setup_v1_file_key_via_subscribed_keyrings(struct fscrypt_info *ci); 65062306a36Sopenharmony_ci 65162306a36Sopenharmony_ci/* policy.c */ 65262306a36Sopenharmony_ci 65362306a36Sopenharmony_cibool fscrypt_policies_equal(const union fscrypt_policy *policy1, 65462306a36Sopenharmony_ci const union fscrypt_policy *policy2); 65562306a36Sopenharmony_ciint fscrypt_policy_to_key_spec(const union fscrypt_policy *policy, 65662306a36Sopenharmony_ci struct fscrypt_key_specifier *key_spec); 65762306a36Sopenharmony_ciconst union fscrypt_policy *fscrypt_get_dummy_policy(struct super_block *sb); 65862306a36Sopenharmony_cibool fscrypt_supported_policy(const union fscrypt_policy *policy_u, 65962306a36Sopenharmony_ci const struct inode *inode); 66062306a36Sopenharmony_ciint fscrypt_policy_from_context(union fscrypt_policy *policy_u, 66162306a36Sopenharmony_ci const union fscrypt_context *ctx_u, 66262306a36Sopenharmony_ci int ctx_size); 66362306a36Sopenharmony_ciconst union fscrypt_policy *fscrypt_policy_to_inherit(struct inode *dir); 66462306a36Sopenharmony_ci 66562306a36Sopenharmony_ci#endif /* _FSCRYPT_PRIVATE_H */ 666