mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
From: Hui Peng <benquike@gmail.com>
To: hansg@kernel.org, tzimmermann@suse.de, simona@ffwll.ch,
	airlied@redhat.com
Cc: dri-devel@lists.freedesktop.org, linux-kernel@vger.kernel.org
Subject: [PATCH] drm/vboxvideo: validate VBVA ring buffer offsets and cursor dimensions
Date: Sat, 19 Sep 2026 22:35:12 +0000	[thread overview]
Message-ID: <20260919223512.3889313-1-benquike@gmail.com> (raw)

In drivers/gpu/drm/vboxvideo/ (vbox_main.c, vbox_mode.c, vbva_base.c),
validate VBVA ring buffer offsets against buffer_length and check cursor
dimensions before copying cursor data into HGSMI buffers.

Fixes: 131abc56e1ba ("drm/vboxvideo: Move the vboxvideo driver out of staging")
Assisted-by: LLM
Signed-off-by: Hui Peng <benquike@gmail.com>
---
diff --git a/drivers/gpu/drm/vboxvideo/vbox_main.c b/drivers/gpu/drm/vboxvideo/vbox_main.c
index aa6664542b20..8cf326661b57 100644
--- a/drivers/gpu/drm/vboxvideo/vbox_main.c
+++ b/drivers/gpu/drm/vboxvideo/vbox_main.c
@@ -115,6 +115,10 @@ int vbox_hw_init(struct vbox_private *vbox)
 
 	DRM_INFO("VRAM %08x\n", vbox->full_vram_size);
 
+	if (vbox->full_vram_size < VBVA_ADAPTER_INFORMATION_SIZE +
+				   vbox->num_crtcs * VBVA_MIN_BUFFER_SIZE)
+		return -EINVAL;
+
 	ret = pcim_request_region(pdev, 0, "vboxvideo");
 	if (ret)
 		return ret;
diff --git a/drivers/gpu/drm/vboxvideo/vbox_mode.c b/drivers/gpu/drm/vboxvideo/vbox_mode.c
index 3c41238a8268..9a1d9e1aa92b 100644
--- a/drivers/gpu/drm/vboxvideo/vbox_mode.c
+++ b/drivers/gpu/drm/vboxvideo/vbox_mode.c
@@ -141,7 +141,8 @@ static bool vbox_set_up_input_mapping(struct vbox_private *vbox)
 
 		if (!fb1) {
 			fb1 = fb;
-			if (fb1 == vbox->ddev.fb_helper->fb)
+			if (vbox->ddev.fb_helper &&
+			    fb1 == vbox->ddev.fb_helper->fb)
 				break;
 		} else if (fb != fb1) {
 			single_framebuffer = false;
@@ -363,7 +364,8 @@ static int vbox_cursor_atomic_check(struct drm_plane *plane,
 		return 0;
 
 	if (width > VBOX_MAX_CURSOR_WIDTH || height > VBOX_MAX_CURSOR_HEIGHT ||
-	    width == 0 || height == 0)
+	    width == 0 || height == 0 ||
+	    width != new_state->fb->width || height != new_state->fb->height)
 		return -EINVAL;
 
 	return 0;
@@ -380,6 +382,7 @@ static void copy_cursor_image(u8 *src, u8 *dst, u32 width, u32 height,
 	size_t line_size = (width + 7) / 8;
 	u32 i, j;
 
+	memset(dst, 0, mask_size);
 	memcpy(dst + mask_size, src, width * height * 4);
 	for (i = 0; i < height; ++i)
 		for (j = 0; j < width; ++j)
diff --git a/drivers/gpu/drm/vboxvideo/vbva_base.c b/drivers/gpu/drm/vboxvideo/vbva_base.c
index 36bc9824ec3f..3a752be06f4e 100644
--- a/drivers/gpu/drm/vboxvideo/vbva_base.c
+++ b/drivers/gpu/drm/vboxvideo/vbva_base.c
@@ -21,18 +21,35 @@
 
 static u32 vbva_buffer_available(const struct vbva_buffer *vbva)
 {
-	s32 diff = vbva->data_offset - vbva->free_offset;
+	u32 data_len = READ_ONCE(vbva->data_len);
+	u32 data_offset = READ_ONCE(vbva->data_offset);
+	u32 free_offset = READ_ONCE(vbva->free_offset);
+	s32 diff;
 
-	return diff > 0 ? diff : vbva->data_len + diff;
+	if (!data_len || data_offset >= data_len || free_offset >= data_len)
+		return 0;
+
+	diff = data_offset - free_offset;
+
+	return diff > 0 ? diff : data_len + diff;
 }
 
 static void vbva_buffer_place_data_at(struct vbva_buf_ctx *vbva_ctx,
 				      const void *p, u32 len, u32 offset)
 {
 	struct vbva_buffer *vbva = vbva_ctx->vbva;
-	u32 bytes_till_boundary = vbva->data_len - offset;
-	u8 *dst = &vbva->data[offset];
-	s32 diff = len - bytes_till_boundary;
+	u32 data_len = READ_ONCE(vbva->data_len);
+	u32 bytes_till_boundary;
+	u8 *dst;
+	s32 diff;
+
+	if (data_len > vbva_ctx->buffer_length - sizeof(*vbva) ||
+	    offset >= data_len || len > data_len)
+		return;
+
+	bytes_till_boundary = data_len - offset;
+	dst = &vbva->data[offset];
+	diff = len - bytes_till_boundary;
 
 	if (diff <= 0) {
 		/* Chunk will not cross buffer boundary. */
@@ -93,6 +110,9 @@ bool vbva_write(struct vbva_buf_ctx *vbva_ctx, struct gen_pool *ctx,
 		vbva_buffer_place_data_at(vbva_ctx, p, chunk,
 					  vbva->free_offset);
 
+		if (!vbva->data_len)
+			return false;
+
 		vbva->free_offset = (vbva->free_offset + chunk) %
 				    vbva->data_len;
 		record->len_and_flags += chunk;
@@ -165,7 +185,7 @@ bool vbva_buffer_begin_update(struct vbva_buf_ctx *vbva_ctx,
 			      struct gen_pool *ctx)
 {
 	struct vbva_record *record;
-	u32 next;
+	u32 free_idx, next;
 
 	if (!vbva_ctx->vbva ||
 	    !(vbva_ctx->vbva->host_flags.host_events & VBVA_F_MODE_ENABLED))
@@ -173,7 +193,11 @@ bool vbva_buffer_begin_update(struct vbva_buf_ctx *vbva_ctx,
 
 	WARN_ON(vbva_ctx->buffer_overflow || vbva_ctx->record);
 
-	next = (vbva_ctx->vbva->record_free_index + 1) % VBVA_MAX_RECORDS;
+	free_idx = READ_ONCE(vbva_ctx->vbva->record_free_index);
+	if (free_idx >= VBVA_MAX_RECORDS)
+		return false;
+
+	next = (free_idx + 1) % VBVA_MAX_RECORDS;
 
 	/* Flush if all slots in the records queue are used */
 	if (next == vbva_ctx->vbva->record_first_index)
@@ -183,7 +207,7 @@ bool vbva_buffer_begin_update(struct vbva_buf_ctx *vbva_ctx,
 	if (next == vbva_ctx->vbva->record_first_index)
 		return false;
 
-	record = &vbva_ctx->vbva->records[vbva_ctx->vbva->record_free_index];
+	record = &vbva_ctx->vbva->records[free_idx];
 	record->len_and_flags = VBVA_F_RECORD_PARTIAL;
 	vbva_ctx->vbva->record_free_index = next;
 	/* Remember which record we are using. */

                 reply	other threads:[~2026-09-19 22:35 UTC|newest]

Thread overview: [no followups] expand[flat|nested]  mbox.gz  Atom feed

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=20260919223512.3889313-1-benquike@gmail.com \
    --to=benquike@gmail.com \
    --cc=airlied@redhat.com \
    --cc=dri-devel@lists.freedesktop.org \
    --cc=hansg@kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=simona@ffwll.ch \
    --cc=tzimmermann@suse.de \
    /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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

all inboxes | Powered by JetHome®