A flaw was found in xorg-x11-server. The GLX (OpenGL Extension to the X Window System) interface fails to verify that incoming data sizes do not exceed allocated buffer limits when handling large rendering requests. An authenticated local client can exploit this vulnerability by sending a specially crafted request, triggering a heap-based buffer overflow. Successful exploitation can result in arbitrary code execution with the privileges of the X server or cause a Denial of Service (DoS) by crashing the application.
In the GLX RenderLarge request handling, the buffer is allocated to the
size of cmdlen but the subsequent memcpy copies dataBytes into it.
There is no validation that dataBytes is less than or equal to cmdlen,
allowing an attacker to write past the end of the allocated buffer.
An authenticated X client can trigger this by sending a crafted GLX
RenderLarge request where dataBytes exceeds cmdlen, causing a
heap buffer overflow.
The heap buffer overflow can lead to arbitrary code execution or denial of
service.
Fixed in: xorg-server-21.1.25 and xwayland-24.1.14
Fix: https://gitlab.freedesktop.org/xorg/xserver/-/commit/TBD
Found by: Anonymous working with TrendAI Zero Day Initiative.
(ZDI-CAN-31833)
*** Patch
[9. text/plain; 0010-glx-validate-dataBytes-against-cmdlen-in-RenderLarge.patch]
From e9330cb8dc6571b4e1e5a0189327b6f29b81cf09 Mon Sep 17 00:00:00 2001
From: Peter Hutterer <peter.hutterer>
Date: Wed, 26 Aug 2026 17:16:49 +1000
Subject: [PATCH xserver] glx: validate dataBytes against cmdlen in RenderLarge
first request
__glXDisp_RenderLarge() allocates the large command buffer based on
cmdlen (from hdr->length, the total command size embedded in the
payload), but copies dataBytes (from req->dataBytes, the payload size
of the current sub-request) into it. The existing length check only
validates that the X11 request length is consistent with dataBytes,
not that dataBytes fits within the cmdlen-sized buffer.
A malicious client can set hdr->length to a small value (e.g. 12 bytes)
while sending a large dataBytes (up to ~256KB or more with
BIG-REQUESTS), causing the memcpy to overflow the cmdlen-sized buffer.
Add a check that dataBytes <= cmdlen before the buffer allocation and
copy on the first request.
This vulnerability was discovered by:
Anonymous working with TrendAI Zero Day Initiative
ZDI-CAN-31833
CVE-2026-93517
Assisted-by: Claude:claude-opus-4-6
---
glx/glxcmds.c | 3 +++
1 file changed, 3 insertions(+)
diff --git a/glx/glxcmds.c b/glx/glxcmds.c
index 58ef861f5d8f..39b187fd9f9f 100644
--- a/glx/glxcmds.c
+++ b/glx/glxcmds.c
@@ -2182,16 +2182,19 @@ __glXDisp_RenderLarge(__GLXclientState * cl, GLbyte * pc)
}
}
/* the +4 is safe because we know entry.bytes is small */
if (cmdlen != safe_pad(safe_add(entry.bytes + 4, extra))) {
return BadLength;
}
+ if (dataBytes > cmdlen)
+ return BadLength;
+
/*
** Make enough space in the buffer, then copy the entire request.
*/
if (glxc->largeCmdBufSize < cmdlen) {
GLbyte *newbuf = glxc->largeCmdBuf;
if (!(newbuf = realloc(newbuf, cmdlen)))
return BadAlloc;
--
In the GLX RenderLarge request handling, the buffer is allocated to the size of cmdlen but the subsequent memcpy copies dataBytes into it. There is no validation that dataBytes is less than or equal to cmdlen, allowing an attacker to write past the end of the allocated buffer. An authenticated X client can trigger this by sending a crafted GLX RenderLarge request where dataBytes exceeds cmdlen, causing a heap buffer overflow. The heap buffer overflow can lead to arbitrary code execution or denial of service. Fixed in: xorg-server-21.1.25 and xwayland-24.1.14 Fix: https://gitlab.freedesktop.org/xorg/xserver/-/commit/TBD Found by: Anonymous working with TrendAI Zero Day Initiative. (ZDI-CAN-31833) *** Patch [9. text/plain; 0010-glx-validate-dataBytes-against-cmdlen-in-RenderLarge.patch] From e9330cb8dc6571b4e1e5a0189327b6f29b81cf09 Mon Sep 17 00:00:00 2001 From: Peter Hutterer <peter.hutterer> Date: Wed, 26 Aug 2026 17:16:49 +1000 Subject: [PATCH xserver] glx: validate dataBytes against cmdlen in RenderLarge first request __glXDisp_RenderLarge() allocates the large command buffer based on cmdlen (from hdr->length, the total command size embedded in the payload), but copies dataBytes (from req->dataBytes, the payload size of the current sub-request) into it. The existing length check only validates that the X11 request length is consistent with dataBytes, not that dataBytes fits within the cmdlen-sized buffer. A malicious client can set hdr->length to a small value (e.g. 12 bytes) while sending a large dataBytes (up to ~256KB or more with BIG-REQUESTS), causing the memcpy to overflow the cmdlen-sized buffer. Add a check that dataBytes <= cmdlen before the buffer allocation and copy on the first request. This vulnerability was discovered by: Anonymous working with TrendAI Zero Day Initiative ZDI-CAN-31833 CVE-2026-93517 Assisted-by: Claude:claude-opus-4-6 --- glx/glxcmds.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/glx/glxcmds.c b/glx/glxcmds.c index 58ef861f5d8f..39b187fd9f9f 100644 --- a/glx/glxcmds.c +++ b/glx/glxcmds.c @@ -2182,16 +2182,19 @@ __glXDisp_RenderLarge(__GLXclientState * cl, GLbyte * pc) } } /* the +4 is safe because we know entry.bytes is small */ if (cmdlen != safe_pad(safe_add(entry.bytes + 4, extra))) { return BadLength; } + if (dataBytes > cmdlen) + return BadLength; + /* ** Make enough space in the buffer, then copy the entire request. */ if (glxc->largeCmdBufSize < cmdlen) { GLbyte *newbuf = glxc->largeCmdBuf; if (!(newbuf = realloc(newbuf, cmdlen))) return BadAlloc; --