|
@@ -1237,18 +1237,17 @@ static void dx_insert_block(struct dx_frame *frame, u32 hash, ext4_lblk_t block)
|
|
|
}
|
|
|
|
|
|
/*
|
|
|
- * NOTE! unlike strncmp, ext4_match returns 1 for success, 0 for failure.
|
|
|
+ * Test whether a directory entry matches the filename being searched for.
|
|
|
*
|
|
|
- * `len <= EXT4_NAME_LEN' is guaranteed by caller.
|
|
|
- * `de != NULL' is guaranteed by caller.
|
|
|
+ * Return: %true if the directory entry matches, otherwise %false.
|
|
|
*/
|
|
|
-static inline int ext4_match(struct ext4_filename *fname,
|
|
|
- struct ext4_dir_entry_2 *de)
|
|
|
+static inline bool ext4_match(const struct ext4_filename *fname,
|
|
|
+ const struct ext4_dir_entry_2 *de)
|
|
|
{
|
|
|
struct fscrypt_name f;
|
|
|
|
|
|
if (!de->inode)
|
|
|
- return 0;
|
|
|
+ return false;
|
|
|
|
|
|
f.usr_fname = fname->usr_fname;
|
|
|
f.disk_name = fname->disk_name;
|
|
@@ -1269,48 +1268,31 @@ int ext4_search_dir(struct buffer_head *bh, char *search_buf, int buf_size,
|
|
|
struct ext4_dir_entry_2 * de;
|
|
|
char * dlimit;
|
|
|
int de_len;
|
|
|
- int res;
|
|
|
|
|
|
de = (struct ext4_dir_entry_2 *)search_buf;
|
|
|
dlimit = search_buf + buf_size;
|
|
|
while ((char *) de < dlimit) {
|
|
|
/* this code is executed quadratically often */
|
|
|
/* do minimal checking `by hand' */
|
|
|
- if ((char *) de + de->name_len <= dlimit) {
|
|
|
- res = ext4_match(fname, de);
|
|
|
- if (res < 0) {
|
|
|
- res = -1;
|
|
|
- goto return_result;
|
|
|
- }
|
|
|
- if (res > 0) {
|
|
|
- /* found a match - just to be sure, do
|
|
|
- * a full check */
|
|
|
- if (ext4_check_dir_entry(dir, NULL, de, bh,
|
|
|
- bh->b_data,
|
|
|
- bh->b_size, offset)) {
|
|
|
- res = -1;
|
|
|
- goto return_result;
|
|
|
- }
|
|
|
- *res_dir = de;
|
|
|
- res = 1;
|
|
|
- goto return_result;
|
|
|
- }
|
|
|
-
|
|
|
+ if ((char *) de + de->name_len <= dlimit &&
|
|
|
+ ext4_match(fname, de)) {
|
|
|
+ /* found a match - just to be sure, do
|
|
|
+ * a full check */
|
|
|
+ if (ext4_check_dir_entry(dir, NULL, de, bh, bh->b_data,
|
|
|
+ bh->b_size, offset))
|
|
|
+ return -1;
|
|
|
+ *res_dir = de;
|
|
|
+ return 1;
|
|
|
}
|
|
|
/* prevent looping on a bad block */
|
|
|
de_len = ext4_rec_len_from_disk(de->rec_len,
|
|
|
dir->i_sb->s_blocksize);
|
|
|
- if (de_len <= 0) {
|
|
|
- res = -1;
|
|
|
- goto return_result;
|
|
|
- }
|
|
|
+ if (de_len <= 0)
|
|
|
+ return -1;
|
|
|
offset += de_len;
|
|
|
de = (struct ext4_dir_entry_2 *) ((char *) de + de_len);
|
|
|
}
|
|
|
-
|
|
|
- res = 0;
|
|
|
-return_result:
|
|
|
- return res;
|
|
|
+ return 0;
|
|
|
}
|
|
|
|
|
|
static int is_dx_internal_node(struct inode *dir, ext4_lblk_t block,
|
|
@@ -1814,24 +1796,15 @@ int ext4_find_dest_de(struct inode *dir, struct inode *inode,
|
|
|
int nlen, rlen;
|
|
|
unsigned int offset = 0;
|
|
|
char *top;
|
|
|
- int res;
|
|
|
|
|
|
de = (struct ext4_dir_entry_2 *)buf;
|
|
|
top = buf + buf_size - reclen;
|
|
|
while ((char *) de <= top) {
|
|
|
if (ext4_check_dir_entry(dir, NULL, de, bh,
|
|
|
- buf, buf_size, offset)) {
|
|
|
- res = -EFSCORRUPTED;
|
|
|
- goto return_result;
|
|
|
- }
|
|
|
- /* Provide crypto context and crypto buffer to ext4 match */
|
|
|
- res = ext4_match(fname, de);
|
|
|
- if (res < 0)
|
|
|
- goto return_result;
|
|
|
- if (res > 0) {
|
|
|
- res = -EEXIST;
|
|
|
- goto return_result;
|
|
|
- }
|
|
|
+ buf, buf_size, offset))
|
|
|
+ return -EFSCORRUPTED;
|
|
|
+ if (ext4_match(fname, de))
|
|
|
+ return -EEXIST;
|
|
|
nlen = EXT4_DIR_REC_LEN(de->name_len);
|
|
|
rlen = ext4_rec_len_from_disk(de->rec_len, buf_size);
|
|
|
if ((de->inode ? rlen - nlen : rlen) >= reclen)
|
|
@@ -1839,15 +1812,11 @@ int ext4_find_dest_de(struct inode *dir, struct inode *inode,
|
|
|
de = (struct ext4_dir_entry_2 *)((char *)de + rlen);
|
|
|
offset += rlen;
|
|
|
}
|
|
|
-
|
|
|
if ((char *) de > top)
|
|
|
- res = -ENOSPC;
|
|
|
- else {
|
|
|
- *dest_de = de;
|
|
|
- res = 0;
|
|
|
- }
|
|
|
-return_result:
|
|
|
- return res;
|
|
|
+ return -ENOSPC;
|
|
|
+
|
|
|
+ *dest_de = de;
|
|
|
+ return 0;
|
|
|
}
|
|
|
|
|
|
int ext4_insert_dentry(struct inode *dir,
|