Skip to content

Commit 7ee29fa

Browse files
SinkFinderakpm00
authored andcommitted
nilfs2: fix potential use after free in nilfs_gccache_submit_read_data()
In nilfs_gccache_submit_read_data(), brelse(bh) is called to drop the reference count of bh when the call to nilfs_dat_translate() fails. If the reference count hits 0 and its owner page gets unlocked, bh may be freed. However, bh->b_page is dereferenced to put the page after that, which may result in a use-after-free bug. This patch moves the release operation after unlocking and putting the page. NOTE: The function in question is only called in GC, and in combination with current userland tools, address translation using DAT does not occur in that function, so the code path that causes this issue will not be executed. However, it is possible to run that code path by intentionally modifying the userland GC library or by calling the GC ioctl directly. [[email protected]: NOTE added to the commit log] Link: https://lkml.kernel.org/r/[email protected] Link: https://lkml.kernel.org/r/[email protected] Fixes: a3d93f7 ("nilfs2: block cache for garbage collection") Signed-off-by: Pan Bian <[email protected]> Reported-by: Ferry Meng <[email protected]> Closes: https://lkml.kernel.org/r/[email protected] Signed-off-by: Ryusuke Konishi <[email protected]> Tested-by: Ryusuke Konishi <[email protected]> Cc: <[email protected]> Signed-off-by: Andrew Morton <[email protected]>
1 parent ce60f27 commit 7ee29fa

File tree

1 file changed

+3
-3
lines changed

1 file changed

+3
-3
lines changed

fs/nilfs2/gcinode.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -73,10 +73,8 @@ int nilfs_gccache_submit_read_data(struct inode *inode, sector_t blkoff,
7373
struct the_nilfs *nilfs = inode->i_sb->s_fs_info;
7474

7575
err = nilfs_dat_translate(nilfs->ns_dat, vbn, &pbn);
76-
if (unlikely(err)) { /* -EIO, -ENOMEM, -ENOENT */
77-
brelse(bh);
76+
if (unlikely(err)) /* -EIO, -ENOMEM, -ENOENT */
7877
goto failed;
79-
}
8078
}
8179

8280
lock_buffer(bh);
@@ -102,6 +100,8 @@ int nilfs_gccache_submit_read_data(struct inode *inode, sector_t blkoff,
102100
failed:
103101
unlock_page(bh->b_page);
104102
put_page(bh->b_page);
103+
if (unlikely(err))
104+
brelse(bh);
105105
return err;
106106
}
107107

0 commit comments

Comments
 (0)