From: Ahmad Fatoum <[email protected]>

When the environment fills its whole partition, data->end is one past
the end of the mapping. The room check in create adds the length of
the new name to it and tail relocation adds one, both yielding pointers
further past the end, which C leaves undefined even if they are only
compared.

Let's compare the room left against the length instead and only step
past data->end when it is still inside the mapping. No change in
behavior with the compilers we use.

Fixes: 8daaa21b3949 ("fs: Add a driver to access U-Boot environment variables")
Fixes: 79f048173d98 ("fs: ubootvarfs: fix tail relocation length computation")
Assisted-by: Claude:opus-5.5
Signed-off-by: Ahmad Fatoum <[email protected]>
---
 fs/ubootvarfs.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/fs/ubootvarfs.c b/fs/ubootvarfs.c
index 3b5c3039e3aa..72d0627fb0cd 100644
--- a/fs/ubootvarfs.c
+++ b/fs/ubootvarfs.c
@@ -210,7 +210,7 @@ static void ubootvarfs_relocate_tail(struct 
ubootvarfs_inode *node,
         * the last entry's NUL is the final byte and data->end points
         * one past the mapping, so there is no terminator to carry along.
         */
-       tail_end = min_t(const char *, data->end + 1, data->limit);
+       tail_end = data->end == data->limit ? data->end : data->end + 1;
 
        memmove(src + delta, src, tail_end - src);
 
@@ -286,7 +286,7 @@ static int ubootvarfs_create(struct inode *dir, struct 
dentry *dentry,
         * we need to make sure there's enough room for it. Note that
         * + 3 is to accoutn for '=', and two '\0' from above
         */
-       if (data->end + len + 3 > data->limit)
+       if (len + 3 > data->limit - data->end)
                return -ENOSPC;
 
        var = xmalloc(sizeof(*var));
-- 
2.47.3


Reply via email to