potential NULL dereference in nfs4_decode_mp_ds_addr()
From: <hidden>
Date: 2025-09-05 20:40:04
In fs/nfs/pnfs_nfs.c, nfs4_decode_mp_ds_addr() says:
rlen = xdr_stream_decode_string_dup(xdr, &buf, INET6_ADDRSTRLEN +
IPV6_SCOPE_ID_LEN + 8, gfp_flags);
if (unlikely(rlen < 0))
goto out_free_netid;
/* replace port '.' with '-' */
portstr = strrchr(buf, '.');
If the string in the server's XDR message has zero length, then
xdr_stream_decode_string_dup() will set buf to NULL and return zero.
So strrchr() will be called on a NULL buf.
I've attached a demo that mounts a fake server that generates a bad
response to a GETDEVICEINFO RPC:
# uname -a
Linux ubuntu66 6.17.0-rc4-00231-gc8ed9b5c02a5 #27 SMP PREEMPT_DYNAMIC Fri Sep 5 15:07:50 EDT 2025 x86_64 x86_64 x86_64 GNU/Linux
# cc nfs138a.c
# ./a.out
...
[ 21.187101] BUG: kernel NULL pointer dereference, address: 0000000000000000
[ 21.188210] #PF: supervisor read access in kernel mode
[ 21.189040] #PF: error_code(0x0000) - not-present page
[ 21.189852] PGD 0 P4D 0
[ 21.190284] Oops: Oops: 0000 [#1] SMP PTI
[ 21.190932] CPU: 5 UID: 0 PID: 1456 Comm: a.out Not tainted 6.17.0-rc4-00231-gc8ed9b5c02a5 #27 PREEMPT(voluntary)
[ 21.192512] Hardware name: FreeBSD BHYVE/BHYVE, BIOS 14.0 10/17/2021
[ 21.193224] RIP: 0010:strrchr+0x6/0x20
[ 21.197694] Call Trace:
[ 21.197838] <TASK>
[ 21.197963] nfs4_decode_mp_ds_addr+0x90/0x2a0
[ 21.198209] nfs4_fl_alloc_deviceid_node+0x24d/0x470
[ 21.198484] nfs4_find_get_deviceid+0x29a/0x3f0
[ 21.198734] fl_pnfs_update_layout.constprop.0+0x70/0x160
[ 21.199025] filelayout_pg_init_read+0x73/0xc0
[ 21.199268] __nfs_pageio_add_request+0x18b/0x490
[ 21.199530] ? kmem_cache_alloc_noprof+0x239/0x2f0
[ 21.199799] ? nfs_page_create+0x79/0x140
[ 21.200021] nfs_pageio_add_request+0x22d/0x300
[ 21.200269] ? nfs_put_lock_context+0x24/0x80
[ 21.200516] nfs_read_add_folio+0x13a/0x1e0
[ 21.200744] nfs_readahead+0x136/0x2a0
[ 21.200955] read_pages+0x85/0x1f0
[ 21.201146] ? filemap_add_folio+0x55/0xa0
[ 21.201374] page_cache_ra_unbounded+0x120/0x1b0
[ 21.201628] filemap_get_pages+0x120/0x6a0
[ 21.201856] filemap_read+0xf6/0x3e0
[ 21.202054] nfs_file_read+0x80/0xa0
[ 21.202253] vfs_read+0x250/0x370
[ 21.202447] ksys_read+0x68/0xe0
[ 21.202633] do_syscall_64+0xa4/0x260
Robert Morris, rtm@mit.edu