aboutsummaryrefslogtreecommitdiffstats
path: root/fs/f2fs/dir.c
diff options
context:
space:
mode:
authorJaegeuk Kim <jaegeuk.kim@samsung.com>2014-02-26 23:57:53 -0500
committerJaegeuk Kim <jaegeuk.kim@samsung.com>2014-02-27 02:25:20 -0500
commit5d0c667121bfc8be76d1580f485bddbe73465d1a (patch)
treef8322c1f8231485ea6f19a815e73527777d52ca9 /fs/f2fs/dir.c
parent8b8343fa9d503894ece57acbe46cb36883646685 (diff)
f2fs: remove costly bit operations for f2fs_find_entry
It turns out that a bit operation like find_next_bit is not always fast enough for f2fs_find_entry. Instead, it is pretty much simple and fast to traverse each dentries. Signed-off-by: Jaegeuk Kim <jaegeuk.kim@samsung.com>
Diffstat (limited to 'fs/f2fs/dir.c')
-rw-r--r--fs/f2fs/dir.c32
1 files changed, 17 insertions, 15 deletions
diff --git a/fs/f2fs/dir.c b/fs/f2fs/dir.c
index d5a2c9ed9aa7..c3ea8f8cc80a 100644
--- a/fs/f2fs/dir.c
+++ b/fs/f2fs/dir.c
@@ -93,16 +93,20 @@ static struct f2fs_dir_entry *find_in_block(struct page *dentry_page,
93 f2fs_hash_t namehash, struct page **res_page) 93 f2fs_hash_t namehash, struct page **res_page)
94{ 94{
95 struct f2fs_dir_entry *de; 95 struct f2fs_dir_entry *de;
96 unsigned long bit_pos, end_pos, next_pos; 96 unsigned long bit_pos = 0;
97 struct f2fs_dentry_block *dentry_blk = kmap(dentry_page); 97 struct f2fs_dentry_block *dentry_blk = kmap(dentry_page);
98 int slots; 98 int max_len = 0;
99 99
100 bit_pos = find_next_bit_le(&dentry_blk->dentry_bitmap,
101 NR_DENTRY_IN_BLOCK, 0);
102 while (bit_pos < NR_DENTRY_IN_BLOCK) { 100 while (bit_pos < NR_DENTRY_IN_BLOCK) {
103 de = &dentry_blk->dentry[bit_pos]; 101 de = &dentry_blk->dentry[bit_pos];
104 slots = GET_DENTRY_SLOTS(le16_to_cpu(de->name_len)); 102 if (!test_bit_le(bit_pos, &dentry_blk->dentry_bitmap)) {
105 103 if (bit_pos == 0)
104 max_len = 1;
105 else if (!test_bit_le(bit_pos - 1, &dentry_blk->dentry_bitmap))
106 max_len++;
107 bit_pos++;
108 continue;
109 }
106 if (early_match_name(name, namelen, namehash, de)) { 110 if (early_match_name(name, namelen, namehash, de)) {
107 if (!memcmp(dentry_blk->filename[bit_pos], 111 if (!memcmp(dentry_blk->filename[bit_pos],
108 name, namelen)) { 112 name, namelen)) {
@@ -110,20 +114,18 @@ static struct f2fs_dir_entry *find_in_block(struct page *dentry_page,
110 goto found; 114 goto found;
111 } 115 }
112 } 116 }
113 next_pos = bit_pos + slots; 117 if (max_len > *max_slots) {
114 bit_pos = find_next_bit_le(&dentry_blk->dentry_bitmap, 118 *max_slots = max_len;
115 NR_DENTRY_IN_BLOCK, next_pos); 119 max_len = 0;
116 if (bit_pos >= NR_DENTRY_IN_BLOCK) 120 }
117 end_pos = NR_DENTRY_IN_BLOCK; 121 bit_pos += GET_DENTRY_SLOTS(le16_to_cpu(de->name_len));
118 else
119 end_pos = bit_pos;
120 if (*max_slots < end_pos - next_pos)
121 *max_slots = end_pos - next_pos;
122 } 122 }
123 123
124 de = NULL; 124 de = NULL;
125 kunmap(dentry_page); 125 kunmap(dentry_page);
126found: 126found:
127 if (max_len > *max_slots)
128 *max_slots = max_len;
127 return de; 129 return de;
128} 130}
129 131