Commit graph

22,614 commits

Author SHA1 Message Date
stefan11111
3715cb527e [PR #3877] glamor/glamor_egl: Add a fallback path to glamor_gbm_bo_from_pixmap_internal
nvidia's gbm backend has issues dealing with importing a gbm bo directly from an EGLImage

This exports the image as dmabufs and imports a bo from dmabufs

This is needed for DRI3 export on nvidia

Fixes: https://gitlab.freedesktop.org/mesa/mesa/-/work_items/14047

v2: Don't pass usage flags

Reviewed-by: James Jones <jajones@nvidia.com>
Signed-off-by: stefan11111 <stefan11111github@gmail.com>
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2321>
(cherry picked from commit b522485155)
(cherry picked from commit 9f36f7bd50)
PR: https://github.com/X11Libre/xserver/pull/3877
(cherry picked from commit 74b69ba1b3)
(cherry picked from commit d5f91a42c49e0a251c91f0cbe214a964805d61aa)
2026-10-23 17:53:08 +02:00
Kevin.Li
c0e0e3568c [PR #3878] glamor: use highp for fill_pos UVs on GLES
Problem:
On a 2K (e.g. 2560x1440) display, WPS Office for Linux (Qt) shows
corrupted text and broken vertical lines on the right side of a
maximized window when the UI is updated by mouse movement (e.g.
hover/scroll refreshing labels). The same controls on the left side
are fine. The issue does not appear at 1080p, without glamor, or when
using desktop OpenGL shaders (non-GLES).

Root cause:
Xwayland GBM n-buffering CopyArea's window pixmap into the present
pixmap via glamor_copy (FBO texture blit). UVs are computed as
(offset + pixel) * (1/width, 1/height). GLES fragment shaders default
to mediump (~10-bit relative precision), so on wide pixmaps UVs near
the right edge can be off by about a pixel; with GL_NEAREST this
shows as shifted/broken glyphs and edges. Desktop OpenGL has no
default mediump precision qualifier, so the same shader path is fine.

Fix:
Force highp only on fillpos uniforms/ins/outs. Keep the global
mediump default for other fragment math.

Change-Id: If747516bdf787e0383b42e3579acfeab30a7cb1c
Signed-off-by: Kevin.Li <kevin.li@cixtech.com>
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2315>
(cherry picked from commit 2b9ce9f6c6)
(cherry picked from commit c01cf7767c)
PR: https://github.com/X11Libre/xserver/pull/3878
(cherry picked from commit e13fb91bc6)
(cherry picked from commit 17c1d7166ba0ea71072e0066c0de7d1fb1bd2eb0)
2026-10-23 17:53:08 +02:00
Enrico Weigelt, metux IT consult
266bb3a3c6 build: link libxserver_glx into Xorg to export xorgGlxCreateVendor
The glamor_egl backport (PR #3877) calls xorgGlxCreateVendor() which is
defined in libxserver_glx (glx/glxext.c). Without linking this library
into Xorg, the symbol is not available at runtime, causing undefined
symbol errors when loading the glamor_egl module.

Signed-off-by: Enterprise <enterprise@x11libre.org>
2026-10-23 17:53:08 +02:00
Enrico Weigelt, metux IT consult
9b5af68c9d build: export xorgGlxCreateVendor symbol for glamor_egl module
The glamor_egl backport (PR #3877) calls xorgGlxCreateVendor() which is
defined in glx/glxext.c. Without _X_EXPORT, the symbol is not exported
from libxorgserver.so, causing undefined symbol errors when loading
the glamor_egl module at runtime.

Signed-off-by: Enterprise <enterprise@x11libre.org>
2026-10-23 17:53:08 +02:00
Enrico Weigelt, metux IT consult
3d7f5f01ea build: export xorgGlxCreateVendor symbol for glamor_egl module
The glamor_egl backport (PR #3877) calls xorgGlxCreateVendor() which is
defined in glx/glxext.c. Without _X_EXPORT, the symbol is not exported
from libxorgserver.so, causing undefined symbol errors when loading
the glamor_egl module at runtime.

Signed-off-by: Enterprise <enterprise@x11libre.org>
2026-10-23 17:53:08 +02:00
Enrico Weigelt, metux IT consult
89f64b2581 glamor: add prototype for glamor_egl_create_textured_screen
This adds the missing prototype declaration for the new function
glamor_egl_create_textured_screen introduced by the PR #3877 backport.
Without it, -Werror=missing-prototypes fails the build on release/25.1.

Signed-off-by: Enterprise <enterprise@x11libre.org>
2026-10-23 17:53:08 +02:00
Alan Coopersmith
07300b543e Xi: avoid memory leak when hitting bounds check for barrier events
The fix for CVE-2026-93519 added a bounds check for barrier events in
CreatePointerBarrierClient() and if it's hit immediately returns
BadAlloc.  Unfortunately it was added after `ret` was already allocated
and before *client_out is set to `ret`, so `ret` leaks.

This fix changes it to jump to the same cleanup code to free(ret)
that the rest of the function already uses.

Fixes: 1f42cc1f0 ("Xi: add bounds check for barrier events in input_constrain_cursor")
Signed-off-by: Alan Coopersmith <alan.coopersmith@oracle.com>
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2352>
(cherry picked from commit 8e901e6013)
2026-10-19 14:12:05 +02:00
Enrico Weigelt, metux IT consult
b29895e44f test/info: run display-info tests serialised to avoid display-number race
The xvfb / xehypr / xehypr-glamor display-info tests each start their own X
server (Xvfb, or Xephyr nested inside Xvfb) via simple-xinit -displayfd. When
several of them start at the same instant, the servers race on the same display
numbers and the losing client ends up with a display it cannot open, failing the
lane intermittently:

  _XSERVTransSocketUNIXCreateListener: /tmp/.X11-unix/X0 already in use
  _XSERVTransMakeAllCOTSServerListeners: server already running
  xdpyinfo: unable to open display ":1".

This reproduces on master (run 38774811861) as well as on PRs, hitting a
different display-info subtest each time, so it is a harness race and not a
regression in the code under test. Mark these tests is_parallel:false so the
display allocation cannot collide. The tests are short, so the lost parallelism
is negligible.

Test-harness only, no production code change.

Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
(cherry picked from commit 7289b9936c)
2026-10-19 14:10:27 +02:00
Alan Coopersmith
7483cb1ec4 Xi: fix event_id & time delta in generated barrier events
The fix for CVE-2026-93519 moved the updates of pbd->last_timestamp
and pbd->barrier_event_id from after they were used to generate the
data in events to before, causing the event_id to be one too high,
and the time delta (ms - pbd->last_timestamp) to always be zero.

This fix moves them back to being after they are used to generate
the event data.

Fixes: 1f42cc1f ("Xi: add bounds check for barrier events in input_constrain_cursor")
Signed-off-by: Alan Coopersmith <alan.coopersmith@oracle.com>
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2353>
(cherry picked from commit 98aed9ddba)
2026-10-17 18:40:50 +02:00
Herman Semenoff
ef024d7629 dix, Xi: remove spurious dereference when checking function pointers
Check CursorConfinedTo and CursorWarpedTo function pointers directly without
dereferencing them in 'if' conditions in events and xiwarppointer

Signed-off-by: Herman Semenoff <GermanAizek@yandex.ru>
(cherry picked from commit 6f3a7a8b469beb43482d9e1612b2bb693ecb63ba)
2026-10-15 16:48:01 +02:00
galternat
4bbc39b3c9 xfree86: seatd-libseat: release the GPU on platform device removal
xf86_remove_platform_device() frees the attributes with
config_odev_free_attributes(), which gives a server FD back through
systemd_logind_release_fd(): a plain close() without a logind session.
seatd keeps the device open, and the tracked entry is left pointing at
an FD number that can be reused.

Close the device through libseat first. This is the only path that frees
attributes holding a seatd FD.

Backport note: closed here instead of in config_odev_free_attributes(),
because this branch lacks 65472d1964 ("xfree86: move over public SDK
headers to include/").

Assisted-by: Claude:claude-opus-5-5
Signed-off-by: galternat <galternat.twins223@simplelogin.com>
(cherry picked from commit 8dc955bf44)
2026-10-14 12:51:51 +02:00
galternat
ef53cf20e9 xfree86: seatd-libseat: release the GPU when the driver won't take the FD
seatd_libseat_open_graphics() hands the probed GPU's FD to the platform
bus as a server FD. For a driver without SUPPORTS_SERVER_FDS,
doPlatformProbe() gives it back with systemd_logind_release_fd(), which
without a logind session is a plain close(). seatd keeps its own
reference to the same open file and with it DRM master, so the driver's
own open of the node is not master which will cause it to fail.

The libseat device ID was also kept in a single slot that every
seatd_libseat_open_graphics() call overwrote, so with more than one GPU
there was no way to close the right device.

Track the libseat ID per FD and close the device through libseat before
the server FD is dropped.

Backport note: graphics_devices is initialized statically, because this
branch lacks 14a022d82f ("list: make xorg_list cope with
zero-initialized list heads").

Assisted-by: Claude:claude-opus-5-5
Signed-off-by: galternat <galternat.twins223@simplelogin.com>
(cherry picked from commit 1dc709ab7f)
2026-10-14 12:51:51 +02:00
Enrico Weigelt, metux IT consult
9f167c3da1 ci(workflows): retry the DragonFlyBSD VM step on transient boot flakes
The DragonFlyBSD lane runs the vmactions VM step exactly once. When the VM
fails to boot/provision transiently ("ssh: Could not resolve hostname
dragonflybsd"), the lane is red and nothing retries it. Add a 3-attempt
retry with continue-on-error on attempts 1-2; each attempt uses its own
guest name so a leftover domain from a failed boot does not collide with
the next attempt.

The retry `if:` uses !cancelled() instead of the implicit success() status
function - after attempt 1 fails, success() is false and would silently
skip the later attempts.

Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
2026-10-13 19:20:54 +02:00
Mason Green
c293a83a41 dix/window: fix UnmapNotify and DestroyNotify order in DestroySubwindows
The X11 protocol requires each window to be destroyed in turn.
Previously, DestroySubwindows unmapped all child windows first.
This sent all UnmapNotify events before any DestroyNotify events.
Removing the UnmapSubwindows call lets each child window be unmapped
and destroyed individually. This restores correct event ordering.

Each child now runs its own ValidateTree pass instead of sharing one.
This diverges from xorg/main, which still carries the UnmapSubwindows
shortcut and its XXX comment.

Signed-off-by: Mason Green <mason@greenm01.net>
(cherry picked from commit 12a1661046)
2026-10-13 17:20:45 +02:00
Enrico Weigelt, metux IT consult
03fe9a629f .github: retry the freebsd BSD VM step on transient boot flakes
The freebsd BSD lane runs the vmactions VM step exactly once. When the VM
fails to boot/provision transiently, the lane is red and nothing retries
it. Add a 3-attempt retry with continue-on-error on attempts 1-2; each
attempt uses its own guest name so a leftover domain from a failed boot
does not collide with the next attempt.

The retry `if:` uses !cancelled() instead of the implicit success() status
function - after attempt 1 fails, success() is false and would silently
skip the later attempts.

Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
2026-10-13 13:42:30 +02:00
Sergey Fedorov
09f30b115a xquartz: fix regression due to unconditional usage of qos APIs
Fixes breakage introduced by b4b8617fe6

Signed-off-by: Sergey Fedorov <vital.had@gmail.com>
(cherry picked from commit f7e35422e2)
2026-10-13 13:22:19 +02:00
Mason Green
9dbfd86b2e Xext: composite: take the pixmap reference before AddResource() on Xinerama
When AddResource() fails it calls the type's delete function, which for
pixmaps is dixDestroyPixmap() and drops one reference.

SingleCompositeNameWindowPixmap() increments pPixmap->refcnt before
AddResource(), so a failure only drops that extra reference. The Xinerama
path in ProcCompositeNameWindowPixmap() incremented it afterwards, so a
failure dropped the window's own reference to its backing pixmap and
could free it while still in use. Take the reference first, as the
single-screen path does.

Signed-off-by: Mason Green <mason@greenm01.net>
(cherry picked from commit 6240f6551c)
2026-10-13 12:17:45 +02:00
Enrico Weigelt, metux IT consult
d95aa15a55 .github: retry the netbsd BSD VM step on transient boot flakes
The netbsd BSD lane runs the vmactions VM step exactly once. When the VM
fails to boot/provision transiently, the lane is red and nothing retries
it. Add a 3-attempt retry with continue-on-error on attempts 1-2; each
attempt uses its own guest name so a leftover domain from a failed boot
does not collide with the next attempt.

The retry `if:` uses !cancelled() instead of the implicit success() status
function - after attempt 1 fails, success() is false and would silently
skip the later attempts.

Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
2026-10-13 12:17:43 +02:00
Mason Green
3499479d7f dix: dispatch: return DestroySubwindows() errors from ProcDestroySubwindows
ProcDestroySubwindows() ignored the result of DestroySubwindows() and
always replied Success. When an XACE hook denies destroying a child,
DestroySubwindows() stops there and returns the error, but the client
was told the request succeeded while some children were left in place.

Return the result instead. This also lets PanoramiXDestroySubwindows()
stop at the first failing screen, which it already checks for.

Signed-off-by: Mason Green <mason@greenm01.net>
(cherry picked from commit 69814ed438)
2026-10-12 19:21:49 +02:00
Mason Green
35724962f5 dix: dispatch: clear the client slot when NextAvailableClient() fails
NextAvailableClient() stores the new client in clients[i] before
InitClientResources() and InsertFakeRequest(). If either fails, the
client is freed but clients[i] still points at it.

When i is a free slot below currentMaxClients, the next incoming
connection reaches EstablishNewConnections(), which walks
clients[1..currentMaxClients) and dereferences the freed client.

Clear clients[i] on both failure paths before freeing.

Signed-off-by: Mason Green <mason@greenm01.net>
(cherry picked from commit 157b3b3b81)
2026-10-12 19:18:56 +02:00
galternat
3f490d2a92 xfree86: platform bus: don't crash on an OutputClass without ModulePath
An OutputClass with neither Driver nor Module ends up in the branch that
extends the default module search path, which dereferences
cl->modulepath without checking it. A class that only sets options, such
as PrimaryGPU, crashes the server during the bus probe.

Leave the search path alone when the class has no ModulePath, as before
per-driver search paths were introduced.

Fixes: 9f25f5d3f1 ("xfree86: make search paths configurable for certain modules")
Assisted-by: Claude:claude-opus-5-5
Signed-off-by: galternat <galternat.twins223@simplelogin.com>
(cherry picked from commit 85cb864cce)
2026-10-12 15:47:45 +02:00
Enrico Weigelt, metux IT consult
a52e74b8d5 xfree86: loader: treat empty module path as not present
Callers of LoaderSetPath(), eg. xf86PlatformProbe, might pass empty strings
instead of NULL, but those also meaning "not present" (IOW: use default path).
That's leading to spurious "Failed to store module search path" error log
messages for modules that don't have a search path yet.

Instead of adding extra complexity there for transforming empty strings
to NULL pointers, just deal with those here and so make the interface
a bit more robust.

Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
(cherry picked from commit 3c36e9029d)
2026-10-12 15:22:58 +02:00
Olivier Fourdan
019c4c4dc8 miext/sync: Handle SIGBUS from truncated shm fences
A client can truncate the shared memory backing a DRI3/xshmfence sync
fence and cause SIGBUS when the server accesses it.

Register the mapping with busfault and wrap xshmfence accesses with
sigsetjmp so truncation unwinds safely, then discard the mapping while
keeping the fence XID.

Signed-off-by: Olivier Fourdan <ofourdan@redhat.com>
Assisted-by: AI
Closes: https://gitlab.freedesktop.org/xorg/xserver/-/work_items/1911
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2270>
(cherry picked from commit cd083d9659)
(cherry picked from commit 51459413d9)
2026-10-09 11:20:06 +02:00
Lukáš Lipinský
1d80d4cbea Xi: test XIQueryDevice values for relative scroll valuators
XIQueryDevice already reports the current cumulative axisVal for relative scroll valuators. Seed nonzero vertical and horizontal values and verify their FP3232 representation for native and swapped clients.

Signed-off-by: Lukáš Lipinský <18076-Mr-Tao@users.noreply.gitlab.freedesktop.org>
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2292>
(cherry picked from commit 18dbde8971)
Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
2026-10-09 09:10:18 +02:00
Mikhail Dmitrichenko
1128987b8d xkb: use ssize_t for XKM byte counts
The ReadXkm* section readers return the number of bytes they consumed,
or -1 when they give up. That contract was spelled as int, while the
counters accumulating their results were a mix of int and unsigned, and
XkmGetCARD8/16/32() took the counter by reference as an int *.

XkmReadFile() also returns an unsigned, but that value is a bitmask of
the sections it could not read, not a byte count. Keeping byte counts in
unsigned variables right next to it makes the two easy to confuse, and
the confusion has a concrete cost: XkmReadFile() kept the readers'
results in an unsigned tmp, so the -1 that every one of the seven
readers it dispatches to can return became UINT_MAX. That passed the
tmp > 0 test below, and the section which had just failed to read was
marked as defined and cleared from the mask of sections reported as
missing.

Use ssize_t, the usual type for "a number of bytes, or -1 on failure",
for every byte count in this file: the section readers' return type, the
local counters, the counter XkmGetCARD8/16/32() take by reference, and
the return values of XkmSkipPadding() and XkmGetCountedString(). An
unsigned in this file now only ever denotes a bitmask, and a failing
section reader is no longer taken for a successful one.

ReadXkmKeyTypes() used a single tmp both for byte counts and as the
in/out element count handed to XkmInsureTypedSize(), which needs an
int *. That second use gets its own variable.

Signed-off-by: Mikhail Dmitrichenko <m.dmitrichenko222@gmail.com>
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2304>
2026-10-08 20:51:56 +02:00
Peter Hutterer
4d6f715f77 xkb: widen size_syms, num_syms, size_acts, num_acts to unsigned int
Fields in XkbClientMapRec and XkbServerMapRec that denote size/num
and are unsigned short can result in truncations. For example
when XkbResizeKeyType() computes the new size_syms value as
(nTotal * 15) / 10, the result may be implicitly truncated to 16
bits on assignment. This causes an undersized calloc allocation, and the
subsequent copy loop writes based on the actual (untruncated) key count,
resulting in a heap buffer overflow. A similar truncation may happen
in XkbResizeKeySyms() and XkbResizeKeyActions().

Widen the fields from unsigned short to unsigned int. These are internal
server structures, not wire protocol types.

This vulnerability was discovered by:
  Anonymous working with TrendAI Zero Day Initiative

ZDI-CAN-31834

CVE-2026-93518

Signed-off-by: Peter Hutterer <peter.hutterer@who-t.net>
Assisted-by: Claude:claude-opus-4-6
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2341>
(cherry picked from commit 89101a6c66)
2026-10-08 20:46:29 +02:00
Peter Hutterer
bbf68069f7 dix: remove passive grabs referencing a device on removal
Passive grabs (GrabRec) store raw DeviceIntPtr values for both the
grabbed device and the modifier device without any lifetime management.
When a device is removed via XIRemoveMaster, CloseDevice() frees the
device struct, but leaves dangling pointers in grab->modifierDevice
for any grab that used this device.

Subsequent pointer events trigger CheckPassiveGrab() which dereferences
the dangling modifierDevice pointer for XI grabs (the CORE and XI2 paths
reassign it, but the XI path does not).

This vulnerability was discovered by:
  Anonymous working with TrendAI Zero Day Initiative

ZDI-CAN-31832

CVE-2026-93516

Assisted-by: Claude:claude-opus-4-6
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2341>
Signed-off-by: Peter Hutterer <peter.hutterer@who-t.net>
2026-10-08 20:45:48 +02:00
Peter Hutterer
4776a824bf Xi: add bounds check for barrier events in input_constrain_cursor
input_constrain_cursor() writes barrier hit and leave events into the
InputEventList buffer without checking how many slots remain.
The buffer is allocated by the DDX at GetMaximumEventsNum() (100) entries
and may contain one raw event already. A client can create more than 100
pointer barriers, pre-arm them as released via XIBarrierReleasePointer,
and then trigger a single pointer motion that crosses all barriers
simultaneously. The leave event loop iterates every hit barrier and
writes one event per barrier, overflowing the 100-slot buffer.

In an ideal world we'd change the InternalEvent* pointer to a struct
that contains allocated size, number of events and the pointer itself
but we're crossing public APIs here and that requires an ABI bump.

So we make do with cutting off the number of barrier events at 64 which
should be low enough to not trigger the issue. However, for the 100+
barrier case this means we only send BarierHit events, not BarrierRelease.
Potentially leaving a client stuck.

We mitigate that problem by simply refusing to create more than 32
barriers per screen (which on its own would also fix the issue, but hey,
'doppelt gemoppelt' as they say).

This vulnerability was discovered by:
  Anonymous working with TrendAI Zero Day Initiative

ZDI-CAN-31938

CVE-2026-93519

Assisted-by: Claude:claude-opus-4-6
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2341>
Signed-off-by: Peter Hutterer <peter.hutterer@who-t.net>
2026-10-08 20:45:07 +02:00
David
0ada37532e render: free animated cursor timers on destruction
AnimCursorCreate() allocates an OsTimerRec for every animated cursor
using TimerSet(NULL, 0, 0, ...). The timer is freed on cursor creation
failure, but normal cursor destruction does not release it.

AnimCurUnrealizeCursor() already performs the once-only destruction of
the animated cursor's frame cursor references on screen 0. Free the timer
there as well.

TimerCancel() only removes a timer from the pending list. TimerFree()
also releases the allocation.

Signed-off-by: David <david@code.contractors>
2026-10-08 19:27:25 +02:00
Pierre Ossman
967afd3db8 Fix fragile check for when to build glamor_egl
It depends on the glamor module, which means it should have the same
check for when things are to be built.

Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2301>
(cherry picked from commit 84908e8db5)
Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
2026-10-08 18:14:35 +02:00
Peter Hutterer
0f63b2dcc4 Xi: validate modifier values in ProcXIPassiveUngrabDevice
ProcXIPassiveUngrabDevice() passes client-supplied modifier values
directly to DeletePassiveGrabFromList() without validating them.

DeletePassiveGrabFromList() may reach DeleteDetailFromMask() which uses
BITCLEAR(mask, modifier). The mask is allocated as 8 Mask words (256
bits). A modifier value > 255 causes BITCLEAR to index mask[modifier>>5]
past the allocation, resulting in a controlled single-bit-clear at an
attacker-chosen heap offset.

Add the same modifier validation that CheckGrabValues() uses: reject
modifiers that are not XIAnyModifier and have bits set outside
AllModifiersMask.

This vulnerability was discovered by:
  Anonymous working with TrendAI Zero Day Initiative

ZDI-CAN-32366

CVE-2026-93523

Signed-off-by: Peter Hutterer <peter.hutterer@who-t.net>
Assisted-by: Claude:claude-opus-4-6
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2341>
2026-10-08 18:14:15 +02:00
Peter Hutterer
6cdce3f362 Xi: clean up gesture sprite traces in WindowGone
Gesture sprite traces which have the same 'fixed sprite trace
for the duration of the gesture' logic as touch sprite traces.
Both copy WindowPtrs into the trace without refcounting them.

If a device supports gestures but does not have a TouchClass,
the cleanup skipped over the gesture sprite cleanup, leaving
dangling pointers in place if a sprite trace is destroyed
during an active gesture (i.e. window is removed).

DeliverOneGestureEvent() then dereferences the stale pointer via
DeepestSpriteWin(&gi->sprite)->drawable.id, causing a use-after-free.

This vulnerability was discovered by:
  4nibhal working with TrendAI Zero Day Initiative

ZDI-CAN-32753

CVE-2026-93536

Assisted-by: Claude:claude-opus-4-6
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2341>
(cherry picked from commit efcfd8acc7)
Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
2026-10-08 18:13:16 +02:00
Peter Hutterer
71dcedec03 glamor: size tmp_bits buffer for source coordinate range in upload_boxes
glamor_upload_boxes() allocates the tmp_bits buffer (used for 24-bit to
32-bit depth conversion) based on the destination pixmap height, but
indexes it using source coordinates (y1 - dy_dst + dy_src). When the
source is taller than the destination, the source-relative offset
exceeds the destination height, causing writes past the buffer end.

Size the buffer to account for the source coordinate mapping:
byte_stride * (pixmap->drawable.height - dy_dst + dy_src). This
ensures the buffer covers the full range of source rows that will be
accessed during the upload.

This vulnerability was discovered by:
  Anonymous working with TrendAI Zero Day Initiative

ZDI-CAN-32361

CVE-2026-93522

Signed-off-by: Peter Hutterer <peter.hutterer@who-t.net>
Assisted-by: Claude:claude-opus-4-6
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2341>
(cherry picked from commit ad26c26bf7)
(cherry picked from commit d05e9432e3)
2026-10-08 18:10:22 +02:00
Olivier Fourdan
19589f467c os: Add busfault_set_jmp() for SIGBUS unwind
Allow callers to arm a sigjmp_buf on a registered mapping so the
SIGBUS handler can siglongjmp instead of remapping and retrying the
faulting instruction.

Needed when the mapping contains objects that are unsafe to resume
on after a replace.

This is preparation work for the next commit where that mechanism is
used.

Signed-off-by: Olivier Fourdan <ofourdan@redhat.com>
Assisted-by: AI
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2270>
(cherry picked from commit 7a0b3e2197)
(cherry picked from commit 51d35a3e22)
Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
2026-10-08 18:07:41 +02:00
Pierre Ossman
235587fbf5 Fix incorrect uses of GLAMOR_HAS_GBM
The code is making dangerous assumptions about other features being
enabled if Glamor happens to have found libgbm. Let's change these to
check the precise features it needs instead.

Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2301>
(cherry picked from commit 5422247702)
(cherry picked from commit 0f0d3d63b6)
Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
2026-10-08 18:05:30 +02:00
Mario Kleiner
5b5380c966 modesetting: Fix RandR output leasing while TearFree is enabled.
Since commit a94dd9536 ("modesetting: add support for TearFree page flips"),
whenever TearFree and PageFlip is simultaneously enabled (which is the
default now), the driver does enable DRM universal plane support, just
as when atomic modesetting is enabled.

Leasing RandR / DRM outputs with universal planes enabled requires
also adding the drm_plane object to the set of leased objects,
otherwise the drmModeCreateLease() ioctl will fail.

Adding a drm_plane object under this condition was omitted, so fix
this omission, and thereby fix RandR output leasing.

Fixes: a94dd9536 ("modesetting: add support for TearFree page flips")
Signed-off-by: Mario Kleiner <mario.kleiner.de@gmail.com>
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2332>
(cherry picked from commit f37bd8de26)
(cherry picked from commit ba8a3ab677)
2026-10-08 17:51:35 +02:00
Peter Hutterer
3845d98f03 xkb: NULL text pointer after free in _CheckSetDoodad error path
_CheckSetDoodad() allocates doodad->text.text via _GetCountedString()
and then attempts to allocate doodad->text.font. If the font string
allocation fails (e.g. because the font string length extends past
the request boundary), the error handler frees doodad->text.text but
does not NULL the pointer. The doodad was already added to the geometry
by XkbAddGeomDoodad() before the string allocations, so when
XkbFreeGeometry() runs cleanup, _XkbClearDoodad() frees the same
dangling pointer again, resulting in a double-free.

NULL the pointer after freeing it to prevent the double-free.

This vulnerability was discovered by:
  Anonymous working with TrendAI Zero Day Initiative

ZDI-CAN-31221

CVE-2026-88812

Signed-off-by: Peter Hutterer <peter.hutterer@who-t.net>
Assisted-by: Claude:claude-opus-4-6
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2341>
(cherry picked from commit 0d1b1b0bad)
Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
2026-10-08 17:49:40 +02:00
Peter Hutterer
139b6c8bf3 xkb: fix CheckKeySyms overwriting request-range symsPerKey entries
CheckKeySyms() has two loops: the first processes keys in the SetMap
request range, the second fills in any missing keys from the existing
map.

The indexing between the two was inconsistent: the first loop
uses a zero-based index + req->firstKeySym, the second loop used it just
as zero-based index.

Example:
   req->firstKeySym = 50
   req->nKeySyms = 10

  i goes from 0 to 10,
  loop 1 checks [50, 60), changes the width but finishes with i at 10.
  loop 2 then runs over [10, 255(, copying the old keymap width

The second loop overwrites the new widths with the width of the
existing keymap. The subsequent SetKeySyms worked on the new width
and may write fewer actions than the map width.

A subsequent XkbGetMap request would then read XkbKeyNumActions()
entries (derived from the new wider key_sym_map.width) from the shorter
action allocation, causing an out-of-bounds heap read. The overread
bytes would be copied into the GetMap reply and sent back to the client,
producing a bounded heap information disclosure.

This vulnerability was discovered by:
  WONJOON HWANG (@joon1337) working with TrendAI Zero Day Initiative

ZDI-CAN-32408

CVE-2026-93524

Assisted-by: Claude:claude-opus-4-6
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2341>
(cherry picked from commit cea71d0273)
Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
2026-10-08 17:49:04 +02:00
Peter Hutterer
a7418a246a xkb: allocate names->keys to MAP_LENGTH in XkbAllocNames
Commit a3171732d ("xkb: Always use MAP_LENGTH keymap size") converted
most XKB allocation functions to use MAP_LENGTH (256) instead of
max_key_code + 1. It also removed the per-array reallocarray() calls in
XkbChangeKeycodeRange(), replacing them with a memset up to MAP_LENGTH.
However, XkbAllocNames() was missed and still allocates names->keys to
max_key_code + 1.

When a keycodes component with max_key_code < 255 is loaded (e.g.
sun(type6) with max_key_code=132) and then a SetMap request extends
maxKeyCode to 255, XkbChangeKeycodeRange() memsets names->keys from
max_key_code to MAP_LENGTH-1, writing past the undersized allocation.

Fix by allocating names->keys to MAP_LENGTH, consistent with all other
keymap arrays after a3171732d.

This vulnerability was discovered by:
  Anonymous working with TrendAI Zero Day Initiative

ZDI-CAN-31941

CVE-2026-93520

Fixes: a3171732da ("xkb: Always use MAP_LENGTH keymap size")

Signed-off-by: Peter Hutterer <peter.hutterer@who-t.net>
Assisted-by: Claude:claude-opus-4-6
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2341>
(cherry picked from commit b941a473e0)
2026-10-08 17:48:48 +02:00
Peter Hutterer
19a47e034a 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

Signed-off-by: Peter Hutterer <peter.hutterer@who-t.net>
Assisted-by: Claude:claude-opus-4-6
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2341>
(cherry picked from commit 2abe4632d7)
Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
2026-10-08 17:46:39 +02:00
Peter Hutterer
3be6db8d14 present: unlink notifies from window list in present_clear_window_notifies
When a window is destroyed, present_clear_window_notifies()
does not remove the notify list node from the window. The notify
may then be freed as part of the window_priv, leaving dangling
pointers in place.

When the vblank owning the notify is later torn down,
present_free_window_notify() calls xorg_list_del() which
writes through these dangling pointers (use-after-free write).

This happens when Present cross-window notifies are used: a
PresentPixmap on window A can reference window B as a notify target.
An untriggered wait_fence keeps the vblank alive so that B can be
destroyed first, creating the dangling-pointer window.

Fix this by calling the free function we have (and moving the window
reset into that function too). present_clear_window_notifies is only
called from one place anyway.

This vulnerability was discovered by:
  Anonymous working with TrendAI Zero Day Initiative

ZDI-CAN-31830

CVE-2026-93515

Signed-off-by: Peter Hutterer <peter.hutterer@who-t.net>
Assisted-by: Claude:claude-opus-4-6
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2341>
(cherry picked from commit 1b6955c310)
Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
2026-10-08 17:45:51 +02:00
stefan11111
eaa7a07f2c glamor: Set need_free_region immediately after pixman region allocation
Otherwise, the region would leak when the pixmap is not in gpu memory

Signed-off-by: stefan11111 <stefan11111github@gmail.com>
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2289>
(cherry picked from commit 41b3d993ba)
(cherry picked from commit 768a9d3754)
2026-10-08 16:14:14 +02:00
stefan11111
d0f5888a37 glamor: Restore GetImage proc
Signed-off-by: stefan11111 <stefan11111github@gmail.com>
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2288>
(cherry picked from commit a66b0286b3)
(cherry picked from commit a3671c861f)
2026-10-08 16:13:36 +02:00
Enrico Weigelt, metux IT consult
740928c32a render: filter: fix integer-overflow bypass of convolution size check
convolutionFilterValidateParams() derives w/h from client-supplied
xFixed values via the sign-extending xFixedToInt(), then checked
'w * h > nparams' as a plain (signed) int product. A client can choose
negative w/h so the mathematical product is huge but the signed int
product wraps to a small or negative value, defeating the bounds check
that is supposed to reject a convolution kernel larger than the actual
parameter list.

Reject negative w/h outright and compare the product as int64_t so it
cannot wrap before the comparison.

Signed-off-by: Enrico Weigelt, metux IT consult <enrico.weigelt@vnc.biz>
(cherry picked from commit 6a97f6d38e)
2026-10-08 14:50:05 +02:00
Mason Green
99e50b043e Xext/namespace: fix potential NULL-pointer dereference in select_ns()
When the configuration file is parsed at server startup, select_ns()
dynamically allocates namespace structures. However, it does not check
whether calloc() or strdup() successfully allocate memory.

If calloc() fails, the server dereferences a NULL pointer and crashes
instantly.

If strdup() fails, the namespace is added to the global list with a
NULL name. When the server later searches for a namespace, it calls
strlen() on the NULL name. This causes a delayed crash of the server
at runtime.

Fix this by adding standard FatalError() checks to handle allocation
failures safely during startup.

Signed-off-by: Mason Green <mason@greenm01.net>
(cherry picked from commit e0160fdb7d)
2026-10-08 14:49:51 +02:00
Enrico Weigelt, metux IT consult
f1d2b61642 panoramiX: zero-init xAllocColorReply to avoid leaking uninitialised bytes
The reply struct was declared bare (uninitialised auto storage) and then
filled field-by-field (red/green/blue/pixel only), leaving pad1/pad2 and
any trailing padding uninitialised. Those bytes were then sent to the
client via X_SEND_REPLY_SIMPLE, an information disclosure.

Fix it with a designated initialiser so the pad/reserved bytes are
zeroed. This block sits inside XINERAMA_FOR_EACH_SCREEN_BACKWARD(), which
took a single macro parameter — so a top-level '{ .a = x, .b = y }'
initialiser was split at its commas into multiple macro arguments (the
old "static init would confuse preprocessor" caveat). Rather than work
around that per call site, make the XINERAMA_FOR_EACH_SCREEN_* macros
variadic (pass the body as __VA_ARGS__); commas in the body are then
preserved, and an ordinary designated initialiser can be used with no
compound-literal cast or extra parentheses.

Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
(cherry picked from commit 7badd1eec2843eb060d569b4b4cc36545c67cdd2)
2026-10-08 12:54:54 +02:00
Enrico Weigelt, metux IT consult
f99f3963d5 dix: rpcbuf: write empty counted string for NULL str
x_rpcbuf_write_counted_string_pad() wrote nothing at all when str was NULL.
But a counted string is a fixed wire element - a 16-bit length, the bytes,
then padding to a 4-byte unit. The matching reader (XKB's _GetCountedString)
unconditionally consumes that 16-bit length (an empty string is length 0 +
pad = 4 bytes), and XkbSizeCountedString() budgets 4 bytes for NULL too.

Omitting the field for NULL therefore produced a short, malformed
XkbGetGeometry reply whenever a geometry string field was NULL (label_font,
a doodad text/font/logo_name, a colour spec, or a property name/value),
desyncing every following field for the reading client.

Write an empty counted string (length 0 + padding) for NULL instead, so the
writer matches the reader and the size accounting.

Signed-off-by: Enrico Weigelt, metux IT consult <info@metux.net>
(cherry picked from commit e113dab26f)
2026-10-07 16:58:17 +02:00
Enrico Weigelt, metux IT consult
32dbd3cf67 Xi: xiselectev: fix OOB read in ProcXISelectEvents' non-swapped path
The per-mask loop read evmask->mask_len to compute the next mask's
length before checking that the fixed xXIEventMask header itself was
still within the request buffer - a request with num_masks >= 1 and
insufficient trailing data reads one xXIEventMask-header's worth past
the end of the request. The byte-swapped path just above already
performs the equivalent pre-check ('len < bytes_to_int32(sizeof
(xXIEventMask))') before touching evmask->mask_len; this brings the
non-swapped path in line with it.

Signed-off-by: Enrico Weigelt, metux IT consult <enrico.weigelt@vnc.biz>
(cherry picked from commit bf6b62648d)
2026-10-07 16:56:08 +02:00
Tautvis
bed89b8bf6 hw/xfree86/glamor_egl: do not link staticaly glx library
Commit a987fc7c36 linked glx library
statically, which leaded dublicated glx extension symbols in glx.so and
glamoregl.so libraries. This commit do not link glx directly.

Signed-off-by: Tautvis <gtautvis@gmail.com>
(cherry picked from commit 6c75731752)
2026-10-07 16:55:56 +02:00
Tautvis
37a06b0397 Xext/glx: exports symbols to make extension shared
In a987fc7c36 commit glx library is
statically linked which makes all glx library variables dublicated in
glx.so and glamoregl.so files and leads 'split-brain' problem where same
symbols exist in different depending on context (this evident when it
called using functions with static attribute).

This patch exports neccesary glx symbols for glamor library.

Signed-off-by: Tautvis <gtautvis@gmail.com>

(cherry picked from commit 9b74a3a7f9)
2026-10-07 16:55:56 +02:00