[PATCH] pnfs/blocklayout: reject zero chunk_size and volumes_count in GETDEVICEINFO

Michael Bommarito <[email protected]>
Newsgroups gmane.linux.kernel.stable,gmane.linux.nfs,gmane.linux.kernel
Message-ID <[email protected]>
nfs4_block_decode_volume() in fs/nfs/blocklayout/dev.c decodes stripe
parameters from GETDEVICEINFO XDR without checking for zero values.
A malicious pNFS server returning chunk_size=0 causes a division-by-
zero panic in bl_map_stripe() via div_u64(offset, dev->chunk_size).
Separately, volumes_count=0 passes the existing upper-bound check
and causes a second division-by-zero via div_u64_rem(chunk,
dev->nr_children=0).

Impact: a malicious or compromised pNFS blocklayout server can panic an
affected Linux NFS client after the client mounts/uses the server and maps
I/O through the poisoned blocklayout. An in-kernel parser/mapper KUnit
reproducer is available privately.

Reject both zero values at decode time with -EIO.

Fixes: 5c83746a0cf2 ("pnfs/blocklayout: in-kernel GETDEVICEINFO XDR parsing")
Cc: [email protected]
Assisted-by: Claude:claude-opus-4-7
Signed-off-by: Michael Bommarito <[email protected]>
---
 fs/nfs/blocklayout/dev.c | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/fs/nfs/blocklayout/dev.c b/fs/nfs/blocklayout/dev.c
index cc6327d97a91a..fc60669db3ec4 100644
--- a/fs/nfs/blocklayout/dev.c
+++ b/fs/nfs/blocklayout/dev.c
@@ -183,8 +183,11 @@ nfs4_block_decode_volume(struct xdr_stream *xdr, struct pnfs_block_volume *b)
 			return -EIO;
 
 		p = xdr_decode_hyper(p, &b->stripe.chunk_size);
+		if (!b->stripe.chunk_size)
+			return -EIO;
 		b->stripe.volumes_count = be32_to_cpup(p++);
-		if (b->stripe.volumes_count > PNFS_BLOCK_MAX_DEVICES) {
+		if (!b->stripe.volumes_count ||
+		    b->stripe.volumes_count > PNFS_BLOCK_MAX_DEVICES) {
 			dprintk("Too many volumes: %d\n", b->stripe.volumes_count);
 			return -EIO;
 		}
-- 
2.53.0
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.