Thank you for your contribution! Sashiko AI review found 1 potential issue(s) 
to consider:
- [High] fsdax: incorrect size parameter in dax_range_compare_iter causes 
massive direct access requests
--

commit 65ff21563702a9036c338f4961a061d5c576d038
Author: Jianyun Gao <[email protected]>

dax: fix wrong error code returned from dax_dedupe_file_range_compare()

This commit fixes a bug in dax_dedupe_file_range_compare() where a positive
return value was incorrectly propagated on failure. It now correctly returns
the negative error code from dax_range_compare_iter().

Link: https://lore.kernel.org/lkml/[email protected]/

> diff --git a/fs/dax.c b/fs/dax.c
> index 08adeaed2baf1..97b6212bfa898 100644
> --- a/fs/dax.c
> +++ b/fs/dax.c
> @@ -2254,7 +2254,7 @@ int dax_dedupe_file_range_compare(struct inode *src, 
> loff_t srcoff,
>               status = dax_range_compare_iter(&src_iter, &dst_iter,
>                               min(src_iter.len, dst_iter.len), same);
>               if (status < 0)
> -                     return ret;
> +                     return status;

[Severity: High]
By correctly propagating the error code here, does this patch now expose a
bug in dax_range_compare_iter() that will break dedupe for large offsets?

Looking at dax_range_compare_iter() in fs/dax.c, it appears to pass an
absolute end offset instead of a length as the size parameter to
dax_iomap_direct_access():

static int dax_range_compare_iter(...)
{
        ...
        ret = dax_iomap_direct_access(smap, pos1, ALIGN(pos1 + len, PAGE_SIZE),
                                      &saddr, NULL);
        ...
}

When dax_iomap_direct_access() receives this size parameter, it converts it
via PHYS_PFN() and interprets the massive absolute offset as a relative
length:

fs/dax.c:dax_iomap_direct_access() {
        ...
        length = dax_direct_access(iomap->dax_dev, pgoff, PHYS_PFN(size),
                                   DAX_ACCESS, kaddr, pfnp);
        ...
}

This requests an out-of-bounds mapping length from the underlying block
driver (up to pos1 + len instead of just len), which typically fails with
-EINVAL or -EIO for offsets that exceed device bounds.

Since this patch changes the behavior from a silent pseudo-success to an
explicit failure, will standard deduplication at non-zero offsets now
consistently fail when dax_range_compare_iter() erroneously asks for an
enormous number of pages?

>               src_iter.status = dst_iter.status = status;
>       }
>       return ret;

-- 
Sashiko AI review ยท 
https://sashiko.dev/#/patchset/[email protected]?part=1

Reply via email to