Re: [PATCH 3/3] ovl: Use real disk UUID for origin file handles
From: Amir Goldstein
Date: Wed Jan 14 2026 - 12:54:51 EST
On Wed, Jan 14, 2026 at 5:32 AM André Almeida <andrealmeid@xxxxxxxxxx> wrote:
>
> Some filesystem, like btrfs, supports mounting cloned images, but assign
> random UUIDs for them to avoid conflicts. This breaks overlayfs "index"
> check, given that every time the same image is mounted, it get's
> assigned a new UUID.
>
> Fix this assigning the disk UUID for filesystem that implements the
> export operation get_disk_uuid(), so overlayfs check is also against the
> same value.
>
> Signed-off-by: André Almeida <andrealmeid@xxxxxxxxxx>
> ---
> fs/overlayfs/copy_up.c | 22 ++++++++++++++++++++--
> 1 file changed, 20 insertions(+), 2 deletions(-)
>
> diff --git a/fs/overlayfs/copy_up.c b/fs/overlayfs/copy_up.c
> index 758611ee4475..8551681fffd3 100644
> --- a/fs/overlayfs/copy_up.c
> +++ b/fs/overlayfs/copy_up.c
> @@ -421,8 +421,26 @@ struct ovl_fh *ovl_encode_real_fh(struct ovl_fs *ofs, struct inode *realinode,
> struct ovl_fh *fh;
> int fh_type, dwords;
> int buflen = MAX_HANDLE_SZ;
> - uuid_t *uuid = &realinode->i_sb->s_uuid;
> - int err;
> + struct super_block *real_sb = realinode->i_sb;
> + uuid_t *uuid = &real_sb->s_uuid, real_uuid;
> + u32 len = sizeof(uuid_t);
> + int err, ret;
> + u64 offset;
> +
> + /*
> + * Some filesystems that support cloned devices may expose random UUIDs
> + * for userspace, which will cause the upper root origin check to fail
> + * during a remount. To avoid this, store the real disk UUID.
> + *
> + * ENODATA means that the filesystem implements get_disk_uuid(), but
> + * this instance is using the real UUID so we can skip the operation.
> + */
> + if (real_sb->s_export_op && real_sb->s_export_op->get_disk_uuid) {
> + ret = real_sb->s_export_op->get_disk_uuid(real_sb, real_uuid.b, &len, &offset);
> +
> + if (!ret || ret != ENODATA)
> + uuid = &real_uuid;
> + }
>
Perhaps this is the wrong way to abstract what overlayfs needs from real fs.
Maybe better to extend ->encode_fh() to take a flags argument (see similar
suggested patch at [1]) and let overlayfs do something like:
fh_type = 0;
if (ovl_origin_uuid(ofs))
fh_type = exportfs_encode_inode_fh(realinode, (void *)fh->fb.uuid.b,
&dwords, NULL, EXPORT_FH_WITH_UUID);
if (fh_type <= 0)
fh_type = exportfs_encode_inode_fh(realinode, (void *)fh->fb.fid,
&dwords, NULL, 0);
Similarly, in ovl_decode_real_fh() overlayfs won't verify the UUID,
this will be also delegated to the filesystem via exportfs_decode_fh()
whose fh->fb.type already has the EXPORT_FH_WITH_UUID flag.
This is very rough hand waving and details need to be worked out,
but it essentially delegates the encoding of a "globally unique file handle"
to the filesystem without specifying this or that version of uuid.
Thanks,
Amir.
[1] https://lore.kernel.org/linux-fsdevel/CAOQ4uxj=XOFqHBmYY1aBFAnJtSkxzSyPu5G3xP1rx=ZfPfe-kg@xxxxxxxxxxxxxx/