@ -795,7 +795,9 @@ dx_probe(struct ext4_filename *fname, struct inode *dir,
if ( hinfo - > hash_version < = DX_HASH_TEA )
hinfo - > hash_version + = EXT4_SB ( dir - > i_sb ) - > s_hash_unsigned ;
hinfo - > seed = EXT4_SB ( dir - > i_sb ) - > s_hash_seed ;
if ( fname & & fname_name ( fname ) )
/* hash is already computed for encrypted casefolded directory */
if ( fname & & fname_name ( fname ) & &
! ( IS_ENCRYPTED ( dir ) & & IS_CASEFOLDED ( dir ) ) )
ext4fs_dirhash ( dir , fname_name ( fname ) , fname_len ( fname ) , hinfo ) ;
hash = hinfo - > hash ;
@ -1363,19 +1365,21 @@ out:
return ret ;
}
void ext4_fname_setup_ci_filename ( struct inode * dir , const struct qstr * iname ,
struct fscrypt_str * cf_ name)
int ext4_fname_setup_ci_filename ( struct inode * dir , const struct qstr * iname ,
struct ext4_filename * name )
{
struct fscrypt_str * cf_name = & name - > cf_name ;
struct dx_hash_info * hinfo = & name - > hinfo ;
int len ;
if ( ! needs_casefold ( dir ) ) {
cf_name - > name = NULL ;
return ;
return 0 ;
}
cf_name - > name = kmalloc ( EXT4_NAME_LEN , GFP_NOFS ) ;
if ( ! cf_name - > name )
return ;
return - ENOMEM ;
len = utf8_casefold ( dir - > i_sb - > s_encoding ,
iname , cf_name - > name ,
@ -1383,10 +1387,18 @@ void ext4_fname_setup_ci_filename(struct inode *dir, const struct qstr *iname,
if ( len < = 0 ) {
kfree ( cf_name - > name ) ;
cf_name - > name = NULL ;
return ;
}
cf_name - > len = ( unsigned ) len ;
if ( ! IS_ENCRYPTED ( dir ) )
return 0 ;
hinfo - > hash_version = DX_HASH_SIPHASH ;
hinfo - > seed = NULL ;
if ( cf_name - > name )
ext4fs_dirhash ( dir , cf_name - > name , cf_name - > len , hinfo ) ;
else
ext4fs_dirhash ( dir , iname - > name , iname - > len , hinfo ) ;
return 0 ;
}
# endif
@ -1416,16 +1428,12 @@ static bool ext4_match(struct inode *parent,
struct qstr cf = { . name = fname - > cf_name . name ,
. len = fname - > cf_name . len } ;
if ( IS_ENCRYPTED ( parent ) ) {
struct dx_hash_info hinfo ;
hinfo . hash_version = DX_HASH_SIPHASH ;
hinfo . seed = NULL ;
ext4fs_dirhash ( parent , fname - > cf_name . name ,
fname_len ( fname ) , & hinfo ) ;
if ( hinfo . hash ! = EXT4_DIRENT_HASH ( de ) | |
hinfo . minor_hash ! =
EXT4_DIRENT_MINOR_HASH ( de ) )
if ( fname - > hinfo . hash ! = EXT4_DIRENT_HASH ( de ) | |
fname - > hinfo . minor_hash ! =
EXT4_DIRENT_MINOR_HASH ( de ) ) {
return 0 ;
}
}
return ! ext4_ci_compare ( parent , & cf , de - > name ,
de - > name_len , true ) ;
@ -2054,15 +2062,11 @@ void ext4_insert_dentry(struct inode *dir,
de - > name_len = fname_len ( fname ) ;
memcpy ( de - > name , fname_name ( fname ) , fname_len ( fname ) ) ;
if ( ext4_hash_in_dirent ( dir ) ) {
struct dx_hash_info hinfo ;
struct dx_hash_info * hinfo = & fname - > hinfo ;
hinfo . hash_version = DX_HASH_SIPHASH ;
hinfo . seed = NULL ;
ext4fs_dirhash ( dir , fname_usr_name ( fname ) ,
fname_len ( fname ) , & hinfo ) ;
EXT4_DIRENT_HASHES ( de ) - > hash = cpu_to_le32 ( hinfo . hash ) ;
EXT4_DIRENT_HASHES ( de ) - > hash = cpu_to_le32 ( hinfo - > hash ) ;
EXT4_DIRENT_HASHES ( de ) - > minor_hash =
cpu_to_le32 ( hinfo . minor_hash ) ;
cpu_to_le32 ( hinfo - > minor_hash ) ;
}
}
@ -2217,10 +2221,9 @@ static int make_indexed_dir(handle_t *handle, struct ext4_filename *fname,
if ( fname - > hinfo . hash_version < = DX_HASH_TEA )
fname - > hinfo . hash_version + = EXT4_SB ( dir - > i_sb ) - > s_hash_unsigned ;
fname - > hinfo . seed = EXT4_SB ( dir - > i_sb ) - > s_hash_seed ;
if ( ext4_hash_in_dirent ( dir ) )
ext4fs_dirhash ( dir , fname_usr_name ( fname ) ,
fname_len ( fname ) , & fname - > hinfo ) ;
else
/* casefolded encrypted hashes are computed on fname setup */
if ( ! ext4_hash_in_dirent ( dir ) )
ext4fs_dirhash ( dir , fname_name ( fname ) ,
fname_len ( fname ) , & fname - > hinfo ) ;