All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v2] drbd: validate digest size in checksum resync and verify requests
@ 2026-10-20 18:22 Yibo Liu
  0 siblings, 0 replies; only message in thread
From: Yibo Liu @ 2026-10-20 18:22 UTC (permalink / raw)
  To: Philipp Reisner, Lars Ellenberg, Christoph Böhmwalder,
	Jens Axboe
  Cc: drbd-dev, linux-block, linux-kernel, co+0845f49852fd568f,
	Yibo Liu, stable

receive_DataRequest() sizes the digest buffer of P_CSUM_RS_REQUEST and
P_OV_REPLY packets from the length the peer puts in the packet header,
without checking it against the digest size of the negotiated csums-alg
or verify-alg. w_e_end_csum_rs_req() and w_e_end_ov_reply() later
memcmp() crypto_shash_digestsize() bytes of that buffer; the D_ASSERT()
on the size only logs a message.

A peer that sends a shorter digest thus causes a slab-out-of-bounds read
in the worker, and a peer that declares a huge length makes the receiver
attempt an oversized kmalloc() that triggers a page allocator warning.

  BUG: KASAN: slab-out-of-bounds in memcmp (lib/string.c:676)
  Read of size 8 at addr ff11000007b9d630 by task drbd_w_r0/601
  Call Trace:
   memcmp (lib/string.c:676)
   w_e_end_csum_rs_req (drivers/block/drbd/drbd_worker.c:1182)
   drbd_worker (drivers/block/drbd/drbd_worker.c:2189)
   drbd_thread_setup (drivers/block/drbd/drbd_main.c:314)
   kthread (kernel/kthread.c:436)
   ret_from_fork (arch/x86/kernel/process.c:158)
   ret_from_fork_asm (arch/x86/entry/entry_64.S:245)

  Allocated by task 605:
   __kmalloc_noprof (mm/slub.c:5439)
   receive_DataRequest (drivers/block/drbd/drbd_receiver.c:2715)
   drbd_receiver (drivers/block/drbd/drbd_receiver.c:5371)
   drbd_thread_setup (drivers/block/drbd/drbd_main.c:314)
   kthread (kernel/kthread.c:436)

Reject the packet and drop the connection unless the declared digest
length matches the digest size of the corresponding transform, or if
no such transform is configured.

Fixes: b411b3637fa7 ("The DRBD driver")
Cc: stable@vger.kernel.org
Reported-by: co+0845f49852fd568f@bugs.sh
Signed-off-by: Yibo Liu <yiboliume@gmail.com>
---
Changes in v2:
- Drop patch 1/2 (P_DATA_REPLY size check); this is now a single patch.
- Check the digest length only in receive_DataRequest(), before the
  buffer is allocated, and leave drbd_worker.c unchanged: with the exact
  size enforced on receive, the sizes compared in the worker always match.

v1: https://lore.kernel.org/all/20261015222800.85928-1-yiboliume@gmail.com/

 drivers/block/drbd/drbd_receiver.c | 13 ++++++++++++-
 1 file changed, 12 insertions(+), 1 deletion(-)

diff --git a/drivers/block/drbd/drbd_receiver.c b/drivers/block/drbd/drbd_receiver.c
index 2135c14354a8..d45c4e68f83b 100644
--- a/drivers/block/drbd/drbd_receiver.c
+++ b/drivers/block/drbd/drbd_receiver.c
@@ -2711,7 +2711,17 @@ static int receive_DataRequest(struct drbd_connection *connection, struct packet
 		break;
 
 	case P_OV_REPLY:
-	case P_CSUM_RS_REQUEST:
+	case P_CSUM_RS_REQUEST: {
+		struct crypto_shash *tfm = pi->cmd == P_CSUM_RS_REQUEST ?
+			peer_device->connection->csums_tfm :
+			peer_device->connection->verify_tfm;
+
+		if (!tfm || pi->size != crypto_shash_digestsize(tfm)) {
+			drbd_err(device, "%s: unexpected digest size %u\n",
+				 cmdname(pi->cmd), pi->size);
+			goto out_free_e;
+		}
+
 		di = kmalloc(sizeof(*di) + pi->size, GFP_NOIO);
 		if (!di)
 			goto out_free_e;
@@ -2742,6 +2752,7 @@ static int receive_DataRequest(struct drbd_connection *connection, struct packet
 			goto submit_for_resync;
 		}
 		break;
+	}
 
 	case P_OV_REQUEST:
 		if (device->ov_start_sector == ~(sector_t)0 &&

base-commit: c03c1a14507dfaf8b856c2608f9ac216021fc222
-- 
2.34.1


^ permalink raw reply related	[flat|nested] only message in thread

only message in thread, other threads:[~2026-10-20 18:22 UTC | newest]

Thread overview: (only message) (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-10-20 18:22 [PATCH v2] drbd: validate digest size in checksum resync and verify requests Yibo Liu

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.