22 Commits
Author SHA1 Message Date
LibretroAdmin 8000d06bf1 Video: build the framebuffer utility shaders by calls
A generator can now build its stage through rslc's builder instead of
writing GLSL for the backend to parse: AbstractGfx::CreateShaderFromBuild
takes a build function, and each backend asks rslc for its own
destination from the built stage - SPIR-V for Vulkan, DXBC at the
device's feature level for D3D11 and D3D12, GLSL or GLSL ES at the
context's version for OpenGL, MSL for Metal. VideoCommon/ShaderBuild
carries the per-backend resource layout the shader headers' macros gave,
and builds a stage in the worker's shader arena, again from the start
where the arena has to grow.

The framebuffer utility stages move first: the screen quad, texture
copy, clear and EFB poke vertex stages, the passthrough geometry stages,
and the texture copy, color and multisample resolve pixel stages. Each
compiles to the same SPIR-V and DXBC words as its GLSL did; the text
writers are gone.

rslc prints OpenGL's GLSL without bindings, so the OpenGL backend binds
blocks, samplers, attributes and outputs by name for every program.
2026-11-10 05:03:08 +01:00
LibretroAdmin 797c5e3e90 Framebuffers with one colour attachment; fixed Vulkan object tables
Nothing made a framebuffer with additional colour attachments, so they
go from AbstractFramebuffer, CreateFramebuffer and every backend, and
FramebufferState's additional_color_attachment_count (always 0) with
them: render passes, views, clears, RTVs and blending are for one
colour attachment, in fixed arrays rather than vectors.

Vulkan samplers are kept in an open-addressed table grown by doubling
and render passes in a fixed array, so looking one up never allocates.
Play allocations on the core's thread: 62 to 58.
2026-11-09 15:53:55 +01:00
LibretroAdmin eac19c3216 VideoCommon: textures, framebuffers and vertex formats as plain pointers 2026-11-08 03:21:36 +01:00
LibretroAdmin 6f709e6686 VideoCommon: shaders and pipelines as plain pointers 2026-11-08 03:19:11 +01:00
LibretroAdmin 52b5d83816 VideoCommon: shaders compile from the generated text without copying it
A backend is handed the ShaderCode: Vulkan and D3D write their header
into the room kept in front of the text and compile the two as one span,
and GL hands the header, any prefix and the text to the driver as they
are and keeps the text's block for its link messages.
2026-11-07 21:59:49 +01:00
LibretroAdmin 106efcaf56 Video: GPU objects without virtual methods
Shaders, pipelines, textures, staging textures and framebuffers call
into the classes of the backend in use, which each backend's Gfx sets
as g_video_backend_kind; those classes are final, so the calls are
direct. A std::default_delete specialization deletes them as their own
class. The Null and Software renderers use the base shader and pipeline
types.
2026-11-07 17:05:56 +01:00
libretroadmin c878c0d818 remove LIBRETRO ifdefs 2026-11-07 14:23:51 +01:00
LibretroAdmin c265e74c05 Software renderer: pictures handed to the frontend in memory, no GL
The software and null renderers run without a hardware context. They
come up at the end of retro_load_game, where a frontend with a context
would call context_reset, and go down with the rest at unload.

The software renderer's picture goes to video_refresh straight from its
XFB texture, in one pass into XRGB8888 order, into a buffer that grows
only with the picture: no GL texture upload, no draw, no window of its
own. The GPU thread's g_gfx is the backend's own from the start.
2026-11-07 02:05:40 +01:00
LibretroAdmin 05a95eb519 VideoCommon, backends: remove the shader includer
Nothing ever made one: every backend was handed a null includer, and the
OpenGL backend's #include resolver returned the source untouched. The
parameter goes from CreateShaderFromSource and everything beneath it,
and ShaderCompileUtils with it.
2026-11-06 04:34:32 +01:00
LibretroAdmin 407a632adc Core, VideoCommon: replace the per-frame locks with atomics
CPU: the state machine drops its two mutexes and two condition
variables.  The state is one atomic word, which the JIT still reads in
place; PowerDown sticks through a CAS.  The CPU thread marks itself
active and then rechecks for a pause or a state change, and a pausing
thread stores its request and then waits for the flag to drop, a
Dekker pair, so neither misses the other.  Waits park on eventcounts.
A step request and its Event travel as one exchanged pointer, pending
jobs are an MPSC stack run in order, and SetStepping and PauseAndLock
still run one at a time, through a claimed flag.

Core: the recursive core mutex goes.  Stop moves the state with a CAS,
and PauseAndLock pairs are already serialized by the CPU's claim.  Host
jobs are an MPSC stack the host thread moves, in order, into its own
queue, which keeps HostDispatchJobs re-entrant.  RunOnCPUThread waits
on a Common::Event instead of a binary semaphore, and OneShotEvent is
removed.

State: the transferable shared mutex that counted save tasks is a
counter and an eventcount; the slot readers and the flush hook wait for
it to reach zero.  TransferableSharedMutex is removed.  WaitableFlag
parks on an eventcount.

PixelEngine: the token, its interrupt flags and the raised-event flag
are one atomic word; the video thread merges into it and schedules the
event only on the edge, the CPU thread takes the flags with a CAS.
Savestates keep the old fields.

VertexLoaderManager: the loader map is a fixed set of buckets, each a
list pushed with a CAS and read without a lock by the main and the
preprocessing thread; two threads making the same loader keep one.

AsyncShaderCompiler: the pending queue is the video thread's own.  It
hands the most urgent items to two slots per worker, and finished items
come back on an MPSC stack, so neither side takes a lock.

OSD messages are posted to an MPSC stack and taken in by the video
thread when it draws; a screenshot request is one exchanged string.

Also removed, being unreachable: the surface change and resize requests
nothing sends (and the swap mutex guarding them), the ImGui keyboard
and mouse input nothing feeds (and the ImGui mutex, as only the video
thread touches the context now), ClearMessages, and the libretro Vulkan
WaitForPresentation with its mutex and condition variable.
2026-11-05 20:11:27 +01:00
Dentomologist 34646cb9a9 Replace some [[maybe_unused]] annotations with commented names
Remove the [[maybe_unused]] annotation from various parameters that are
unconditionally unused and comment out their names instead. This makes
it unambiguous that the variables are unused, while making the remaining
[[maybe_unused]] annotations more reliable indicators that those
variables are in fact used in some contexts.

These parameters are mostly in overridden functions where the override
doesn't need that particular variable.
2026-05-03 17:09:59 -07:00
Sintendo 1e0473e44f Fix various typos and spelling mistakes 2026-01-17 20:11:38 +01:00
iwubcode 96fe6a1575 VideoBackends / VideoCommon: add support for specifying include files in shader code 2025-10-26 22:47:23 -05:00
Dr. Dystopia f240e20e3f Make overriding explicit and remove redundant virtual specifiers on overriding destructors - Core & UnitTests 2025-05-01 15:00:37 +02:00
TellowKrinkle 7e1a9490c0 VideoBackends:Vulkan: Don't try to present if swapchain acquire failed 2024-10-02 19:22:16 -05:00
Lioncash e06480a8ab Software/SWGfx: Default destructor in cpp file
Fixes a build failure with clang 17.

The destructor needs to be in the cpp file, since we have a forward
declared std::unique_ptr type as part of the class. So technically the
default inline destructor could invoke without seeing the full data type
definition.
2023-12-12 20:33:43 -05:00
iwubcode 834f8f7b5c VideoBackends: add support to allow rendering to multiple output textures 2023-06-03 14:52:31 -05:00
Pokechu22 4a2d3c83c7 Software: Implement GetSurfaceInfo()
Before, it used a fallback where it returned a default object, where the width and height were set to 0. Presenter::Initialize() used GetSurfaceInfo to set the backbuffer size, then used that size when initializing the on-screen UI (even for the software renderer, where the on-screen UI isn't currently present), which meant that ImGui got a window size of 0 and thus resulted in a failed assertion.

Although BindBackbuffer checks for size changes, it doesn't help because ImGui has already been initialized, and the size hasn't actually changed since initialization occured.

Fixes one aspect of https://bugs.dolphin-emu.org/issues/13172.
2023-03-02 11:08:49 -08:00
Scott Mansell cf9a6f8477 Lint fixes 2023-02-09 18:36:20 +13:00
Scott Mansell e009002411 Refactor ClearRegion
And fix bug where opengl was getting the wrong coordinates
2023-02-09 18:36:20 +13:00
Scott Mansell f158ff300b Handle VideoSoftware's present fallback better
Not a good idea to abuse bSupportsPostProcessing
2023-01-31 19:41:24 +13:00
Scott Mansell d37f83ffeb Implement AbstractGfx for Software & Null 2023-01-31 19:41:23 +13:00