@@ -229,6 +229,12 @@ struct fscrypt_info {
/* Back-pointer to the inode, for infos owned by a specific inode */
struct inode *ci_inode;
+ /*
+ * Back-pointer to the info pointer in the extent, for infos owned
+ * by an extent
+ */
+ struct fscrypt_info **ci_info_ptr;
+
/* The superblock of the filesystem to which this fscrypt_info pertains */
struct super_block *ci_sb;
@@ -567,7 +567,11 @@ fscrypt_setup_encryption_info(struct inode *inode,
if (!crypt_info)
return -ENOMEM;
- crypt_info->ci_inode = inode;
+ if (fscrypt_uses_extent_encryption(inode))
+ crypt_info->ci_info_ptr = info_ptr;
+ else
+ crypt_info->ci_inode = inode;
+
crypt_info->ci_sb = inode->i_sb;
crypt_info->ci_policy = *policy;
memcpy(crypt_info->ci_nonce, nonce, FSCRYPT_FILE_NONCE_SIZE);
In order to notify extents when their info is part of a master key which is going away, the fscrypt_info must have a backpointer to the extent somehow. Similarly, if a fscrypt_info is owned by an extent, the info must not have a pointer to an inode -- multiple inodes may reference a extent, and the first inode to cause an extent's creation may have a lifetime much shorter than the extent, so there is no inode pointer safe to track in an extent-owned info. Therefore, this adds a new pointer for extent-owned infos to track their extent and updates fscrypt_setup_encryption_info() accordingly. Since it's simple to track the piece of extent memory pointing to the info, and for the extent to then go from such a pointer to the whole extent via container_of(), we store that. Although some sort of generic void * or some artificial fscrypt_extent embedded structure would also work, those would require additional plumbing which doesn't seem strictly required or clarifying. Signed-off-by: Sweet Tea Dorminy <sweettea-kernel@dorminy.me> --- fs/crypto/fscrypt_private.h | 6 ++++++ fs/crypto/keysetup.c | 6 +++++- 2 files changed, 11 insertions(+), 1 deletion(-)