Guide to HLSL System-Value Semantics (SV Prefixes)

This article provides an overview of system-generated values in DirectX High-Level Shader Language (HLSL), distinguished by their SV_ prefix. You will learn what these system-value semantics are, how the Direct3D graphics pipeline interprets them, and how common examples like SV_Position, SV_Target, and compute shader identifiers function across different rendering stages.


What Are HLSL Semantics?

In HLSL, a semantic is a string attached to a shader input or output parameter that defines how the data is used. In legacy DirectX (DirectX 9), semantics primarily mapped data between the application's vertex buffer declarations and shader inputs (such as POSITION or TEXCOORD0).

Starting with Direct3D 10 and continuing through Direct3D 11 and Direct3D 12, Microsoft introduced System-Value semantics, denoted by the SV_ prefix.


What Does the SV_ Prefix Mean?

The SV_ prefix stands for System Value. Unlike standard user-defined semantics that merely pass arbitrary data from one stage to another, system-value semantics have explicit, predefined meanings to the GPU's fixed-function pipeline and the Direct3D runtime.

When a variable uses an SV_ semantic, the GPU hardware or the shader compiler monitors or manipulates that value directly. Depending on whether it is an input or an output, an SV semantic tells the pipeline either:

  1. To feed specific hardware-generated data into the shader.
  2. To consume the shader's output to control a fixed-function hardware stage (such as the rasterizer or the output merger).

Common System-Value Semantics by Stage

1. Rasterization and Vertex Processing

  • SV_Position:
    • As an Output (Vertex/Geometry Shader): Directs the rasterizer to use this 4D vector (float4) as the homogeneous clip-space position of the vertex. The rasterizer performs perspective division and viewport clipping based on this value.
    • As an Input (Pixel Shader): Represents the screen-space pixel coordinates \((x, y, z, 1/w)\), allowing pixel shaders to know the exact pixel location currently being shaded.
  • SV_VertexID: A system-generated unsigned integer (uint) passed into a vertex shader indicating the index of the vertex currently being processed.
  • SV_InstanceID: A system-generated unsigned integer (uint) passed into a vertex shader identifying the per-instance index during instanced draw calls.

2. Pixel Shader and Output Merger

  • SV_Target (or SV_Target[n]): Instructs the Output Merger stage to write the shader's color output to a specific render target slot (where n ranges from 0 to 7).
  • SV_Depth: Allows the pixel shader to manually override the depth value written to the depth buffer for that pixel, rather than using the interpolated clip-space depth.
  • SV_Coverage: Specifies a bitmask representing MSAA (Multi-Sample Anti-Aliasing) sample coverage for the current pixel.
  • SV_IsFrontFace: A boolean input indicating whether the primitive currently being rendered is front-facing or back-facing.

3. Compute Shaders

Compute shaders rely heavily on system values to coordinate parallel thread execution:

  • SV_GroupID: The 3D index of the thread group within the overall dispatch grid.
  • SV_GroupThreadID: The 3D index of an individual thread within its specific thread group.
  • SV_DispatchThreadID: The globally unique 3D index of a thread across the entire dispatch call (calculated as GroupID * ThreadGroupSize + GroupThreadID).
  • SV_GroupIndex: A flattened 1D index of a thread within a thread group, often used to index into thread-group shared memory (groupshared).

4. Tessellation Stages

  • SV_TessFactor: Defines the tessellation factors applied to the outer edges of a patch.
  • SV_InsideTessFactor: Defines the tessellation factors applied to the interior of a patch.

Why System Values Matter

  • Hardware Communication: They bridge programmable shader stages with fixed-function pipeline hardware, such as rasterizers, depth testers, and blend units.
  • Compiler Validation: The HLSL compiler strictly validates the data types, component counts, and pipeline stages associated with SV_ prefixes. Using an invalid type with an SV semantic results in a compilation error.
  • Efficiency: Features like SV_VertexID and SV_InstanceID enable procedural drawing and geometry instancing without requiring explicit per-vertex buffer streams for IDs.