All of lore.kernel.org
 help / color / mirror / Atom feed
From: Aaron Esau <aaron1esau@gmail.com>
To: qemu-devel@nongnu.org
Cc: Jonathan.Cameron@huawei.com, jic23@kernel.org,
	berrange@redhat.com, Aaron Esau <aaron1esau@gmail.com>,
	qemu-stable@nongnu.org
Subject: [PATCH 2/2] hw/cxl: add missing bounds checks in Set Feature for PPR and sparing
Date: Thu, 16 Apr 2026 15:07:02 -0500	[thread overview]
Message-ID: <20260416200702.2374709-3-git@aaronesau.com> (raw)
In-Reply-To: <20260416200702.2374709-1-git@aaronesau.com>

From: Aaron Esau <aaron1esau@gmail.com>

cmd_features_set_feature() is missing bounds validation on the offset and
data length for several feature UUIDs before their memcpy calls. The
patrol_scrub and ecs cases correctly check:

    if ((uint32_t)hdr->offset + bytes_to_copy >
        sizeof(ct3d->..._wr_attrs))
        return CXL_MBOX_INVALID_PAYLOAD_LENGTH;

But the soft_ppr, hard_ppr, cacheline_sparing, row_sparing,
bank_sparing, and rank_sparing cases are missing this check. Since
bytes_to_copy is derived from the full mailbox payload length (up to
2048 bytes) and the write-attribute structs are only a few bytes each,
a guest can overflow into adjacent CXLType3Dev fields.

Add the same bounds check pattern to all six affected feature handlers.

Cc: qemu-stable@nongnu.org
Fixes: 5e5a86bab8 ("hw/cxl: Add support for Maintenance command and Post Package Repair (PPR)")
Fixes: da5cafdc4d ("hw/cxl: Add emulation for memory sparing control feature")
Reported-by: Aaron Esau <aaron1esau@gmail.com>
Signed-off-by: Aaron Esau <aaron1esau@gmail.com>
---
 hw/cxl/cxl-mailbox-utils.c | 30 ++++++++++++++++++++++++++++++
 1 file changed, 30 insertions(+)

diff --git a/hw/cxl/cxl-mailbox-utils.c b/hw/cxl/cxl-mailbox-utils.c
index 0adf1e72c8..5fabfcbbab 100644
--- a/hw/cxl/cxl-mailbox-utils.c
+++ b/hw/cxl/cxl-mailbox-utils.c
@@ -1814,6 +1814,11 @@ static CXLRetCode cmd_features_set_feature(const struct cxl_cmd *cmd,
             return CXL_MBOX_UNSUPPORTED;
         }
 
+        if ((uint32_t)hdr->offset + bytes_to_copy >
+            sizeof(ct3d->soft_ppr_wr_attrs)) {
+            return CXL_MBOX_INVALID_PAYLOAD_LENGTH;
+        }
+
         memcpy((uint8_t *)&ct3d->soft_ppr_wr_attrs + hdr->offset,
                sppr_write_attrs, bytes_to_copy);
         set_feat_info->data_size += bytes_to_copy;
@@ -1833,6 +1838,11 @@ static CXLRetCode cmd_features_set_feature(const struct cxl_cmd *cmd,
             return CXL_MBOX_UNSUPPORTED;
         }
 
+        if ((uint32_t)hdr->offset + bytes_to_copy >
+            sizeof(ct3d->hard_ppr_wr_attrs)) {
+            return CXL_MBOX_INVALID_PAYLOAD_LENGTH;
+        }
+
         memcpy((uint8_t *)&ct3d->hard_ppr_wr_attrs + hdr->offset,
                hppr_write_attrs, bytes_to_copy);
         set_feat_info->data_size += bytes_to_copy;
@@ -1852,6 +1862,11 @@ static CXLRetCode cmd_features_set_feature(const struct cxl_cmd *cmd,
             return CXL_MBOX_UNSUPPORTED;
         }
 
+        if ((uint32_t)hdr->offset + bytes_to_copy >
+            sizeof(ct3d->cacheline_sparing_wr_attrs)) {
+            return CXL_MBOX_INVALID_PAYLOAD_LENGTH;
+        }
+
         memcpy((uint8_t *)&ct3d->cacheline_sparing_wr_attrs + hdr->offset,
                mem_sparing_write_attrs, bytes_to_copy);
         set_feat_info->data_size += bytes_to_copy;
@@ -1870,6 +1885,11 @@ static CXLRetCode cmd_features_set_feature(const struct cxl_cmd *cmd,
             return CXL_MBOX_UNSUPPORTED;
         }
 
+        if ((uint32_t)hdr->offset + bytes_to_copy >
+            sizeof(ct3d->row_sparing_wr_attrs)) {
+            return CXL_MBOX_INVALID_PAYLOAD_LENGTH;
+        }
+
         memcpy((uint8_t *)&ct3d->row_sparing_wr_attrs + hdr->offset,
                mem_sparing_write_attrs, bytes_to_copy);
         set_feat_info->data_size += bytes_to_copy;
@@ -1888,6 +1908,11 @@ static CXLRetCode cmd_features_set_feature(const struct cxl_cmd *cmd,
             return CXL_MBOX_UNSUPPORTED;
         }
 
+        if ((uint32_t)hdr->offset + bytes_to_copy >
+            sizeof(ct3d->bank_sparing_wr_attrs)) {
+            return CXL_MBOX_INVALID_PAYLOAD_LENGTH;
+        }
+
         memcpy((uint8_t *)&ct3d->bank_sparing_wr_attrs + hdr->offset,
                mem_sparing_write_attrs, bytes_to_copy);
         set_feat_info->data_size += bytes_to_copy;
@@ -1906,6 +1931,11 @@ static CXLRetCode cmd_features_set_feature(const struct cxl_cmd *cmd,
             return CXL_MBOX_UNSUPPORTED;
         }
 
+        if ((uint32_t)hdr->offset + bytes_to_copy >
+            sizeof(ct3d->rank_sparing_wr_attrs)) {
+            return CXL_MBOX_INVALID_PAYLOAD_LENGTH;
+        }
+
         memcpy((uint8_t *)&ct3d->rank_sparing_wr_attrs + hdr->offset,
                mem_sparing_write_attrs, bytes_to_copy);
         set_feat_info->data_size += bytes_to_copy;
-- 
2.53.0



      parent reply	other threads:[~2026-04-16 22:38 UTC|newest]

Thread overview: 5+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-04-16 20:07 [PATCH 0/2] hw/cxl: Fix two OOB access bugs in CXL mailbox commands Aaron Esau
2026-04-16 20:07 ` [PATCH 1/2] hw/cxl: fix OOB read in Get Log command due to incorrect pointer arithmetic Aaron Esau
2026-05-13  6:35   ` Michael Tokarev
2026-05-13 21:41     ` Aaron Esau
2026-04-16 20:07 ` Aaron Esau [this message]

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20260416200702.2374709-3-git@aaronesau.com \
    --to=aaron1esau@gmail.com \
    --cc=Jonathan.Cameron@huawei.com \
    --cc=berrange@redhat.com \
    --cc=jic23@kernel.org \
    --cc=qemu-devel@nongnu.org \
    --cc=qemu-stable@nongnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
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.