nCine::RHI::RSX::RsxBufferObject class

Buffer object of the RSX backend (aliased as RHI::Buffer).

A vertex, index or uniform buffer keeps a resizable byte store the pipeline maps and writes into. MapBufferRange() hands back a pointer into that store and BindBufferRange() forwards a sub-range to the device.

Every store is GPU-visible memory (RsxVram), so the pipeline's writes land where the hardware can read them with no upload step at all - and every store is allocated in main memory rather than in the GPU's local GDDR3. That is the opposite of where a texture goes, for the opposite reason: these buffers are rewritten by the PPE every frame, and writing them into local memory would trade a cheap cached write for an uncached one across the bus. The GPU reads them over FlexIO instead, which is exactly the trade a streamed vertex buffer wants (see RsxVram).

  • Vertex and index buffers are read by the GPU directly from it, by the offset the block carries.
  • Uniform buffers are read either way depending on the shader. A small block is written straight into the vertex program's constant registers by the draw; a batched instance array is repacked and written into them element by element, because the RSX has no uniform buffer to bind at all (see RsxDevice::UploadInstanceArray()).

The store is grow-only: a BufferData() that fits the existing block reuses it, so the pipeline's per-frame ring buffers allocate once.

Public static functions

static void SetBoundHandle(std::uint32_t target, std::uint32_t glHandle)
Records the buffer handle bound for a target (inert).
static auto BindHandle(std::uint32_t target, std::uint32_t glHandle) -> bool
Marks a buffer handle as bound for a target (inert).

Constructors, destructors, conversion operators

RsxBufferObject(BufferTarget target) explicit
~RsxBufferObject()
RsxBufferObject(const RsxBufferObject&) deleted

Public functions

auto operator=(const RsxBufferObject&) -> RsxBufferObject& deleted
auto GetGLHandle() const -> std::uint32_t
Returns a synthetic handle uniquely identifying the buffer (used by material sort keys).
auto GetTarget() const -> BufferTarget
Returns the binding target of the buffer.
auto GetSize() const -> std::size_t
Returns the size in bytes of the data store.
auto HostData() -> std::uint8_t*
Returns the base pointer of the data store.
auto HostData() const -> const std::uint8_t*
Returns the base pointer of the data store.
auto GetGpuData() const -> const void*
Returns the GPU-visible base address of the store, or nullptr if it could not be allocated.
auto Bind() const -> bool
Marks the buffer as the currently bound one for its target (always issues the "bind").
auto Unbind() const -> bool
Marks no buffer as bound for this object's target.
void BufferData(std::size_t size, const void* data, BufferUsage usage)
(Re)creates the data store with the given size, optional initial data and usage hint
void BufferSubData(std::size_t offset, std::size_t size, const void* data)
Updates a subset of the data store starting at the given byte offset.
void BufferStorage(std::size_t size, const void* data, MapFlags flags)
(Re)creates the data store like BufferData(); there is no immutable storage, so the flags are ignored
void BindBufferBase(std::uint32_t index)
Binds the whole buffer to a uniform binding point index.
void BindBufferRange(std::uint32_t index, std::size_t offset, std::size_t size)
Binds a byte range of the buffer to a uniform binding point index (forwarded to the device).
auto MapBufferRange(std::size_t offset, std::size_t length, MapFlags access) -> void*
Returns a pointer to a byte range of the store (there is no real mapping).
void FlushMappedBufferRange(std::size_t offset, std::size_t length)
Flushes a mapped range (a no-op, the store is uncached GPU-visible memory).
auto Unmap() -> bool
Unmaps the buffer (a no-op, the store is directly addressable).
void SetObjectLabel(StringView label)
Sets a debug label for the buffer (ignored).

Function documentation

const void* nCine::RHI::RSX::RsxBufferObject::GetGpuData() const

Returns the GPU-visible base address of the store, or nullptr if it could not be allocated.

The same pointer HostData() returns, only named for the side that consumes it.