Re: [PATCH] statmount: let unset strings be empty

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On Thu, 2025-01-30 at 13:15 +0100, Miklos Szeredi wrote:
> Just like it's normal for unset values to be zero, unset strings should be
> empty instead of containing random values.
> 
> It seems to be a typical mistake that the mask returned by statmount is not
> checked, which can result in various bugs.
> 
> With this fix, these bugs are prevented, since it is highly likely that
> userspace would just want to turn the missing mask case into an empty
> string anyway (most of the recently found cases are of this type).
> 
> Link: https://lore.kernel.org/all/CAJfpegsVCPfCn2DpM8iiYSS5DpMsLB8QBUCHecoj6s0Vxf4jzg@xxxxxxxxxxxxxx/
> Fixes: 68385d77c05b ("statmount: simplify string option retrieval")
> Fixes: 46eae99ef733 ("add statmount(2) syscall")
> Cc: <stable@xxxxxxxxxxxxxxx> # v6.8
> Signed-off-by: Miklos Szeredi <mszeredi@xxxxxxxxxx>
> ---
>  fs/namespace.c | 25 ++++++++++++++++---------
>  1 file changed, 16 insertions(+), 9 deletions(-)
> 
> diff --git a/fs/namespace.c b/fs/namespace.c
> index a3ed3f2980cb..9c4d307a82cd 100644
> --- a/fs/namespace.c
> +++ b/fs/namespace.c
> @@ -5191,39 +5191,45 @@ static int statmount_string(struct kstatmount *s, u64 flag)
>  	size_t kbufsize;
>  	struct seq_file *seq = &s->seq;
>  	struct statmount *sm = &s->sm;
> -	u32 start = seq->count;
> +	u32 start, *offp;
> +
> +	/* Reserve an empty string at the beginning for any unset offsets */
> +	if (!seq->count)
> +		seq_putc(seq, 0);
> +
> +	start = seq->count;
>  
>  	switch (flag) {
>  	case STATMOUNT_FS_TYPE:
> -		sm->fs_type = start;
> +		offp = &sm->fs_type;
>  		ret = statmount_fs_type(s, seq);
>  		break;
>  	case STATMOUNT_MNT_ROOT:
> -		sm->mnt_root = start;
> +		offp = &sm->mnt_root;
>  		ret = statmount_mnt_root(s, seq);
>  		break;
>  	case STATMOUNT_MNT_POINT:
> -		sm->mnt_point = start;
> +		offp = &sm->mnt_point;
>  		ret = statmount_mnt_point(s, seq);
>  		break;
>  	case STATMOUNT_MNT_OPTS:
> -		sm->mnt_opts = start;
> +		offp = &sm->mnt_opts;
>  		ret = statmount_mnt_opts(s, seq);
>  		break;
>  	case STATMOUNT_OPT_ARRAY:
> -		sm->opt_array = start;
> +		offp = &sm->opt_array;
>  		ret = statmount_opt_array(s, seq);
>  		break;
>  	case STATMOUNT_OPT_SEC_ARRAY:
> -		sm->opt_sec_array = start;
> +		offp = &sm->opt_sec_array;
>  		ret = statmount_opt_sec_array(s, seq);
>  		break;
>  	case STATMOUNT_FS_SUBTYPE:
> -		sm->fs_subtype = start;
> +		offp = &sm->fs_subtype;
>  		statmount_fs_subtype(s, seq);
>  		break;
>  	case STATMOUNT_SB_SOURCE:
> -		sm->sb_source = start;
> +		offp = &sm->sb_source;
>  		ret = statmount_sb_source(s, seq);
>  		break;
>  	default:
> @@ -5251,6 +5257,7 @@ static int statmount_string(struct kstatmount *s, u64 flag)
>  
>  	seq->buf[seq->count++] = '\0';
>  	sm->mask |= flag;
> +	*offp = start;
>  	return 0;
>  }
>  

That seems like a reasonable thing to do.

Reviewed-by: Jeff Layton <jlayton@xxxxxxxxxx>





[Index of Archives]     [Linux Ext4 Filesystem]     [Union Filesystem]     [Filesystem Testing]     [Ceph Users]     [Ecryptfs]     [NTFS 3]     [AutoFS]     [Kernel Newbies]     [Share Photos]     [Security]     [Netfilter]     [Bugtraq]     [Yosemite News]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux Cachefs]     [Reiser Filesystem]     [Linux RAID]     [NTFS 3]     [Samba]     [Device Mapper]     [CEPH Development]

  Powered by Linux