mirror of
https://github.com/elwrcl/intel-hard-graphics.git
synced 2026-10-31 19:08:03 +03:00
init
This commit is contained in:
12511 files changed
+6156641
No files matched your search
@@ -0,0 +1,108 @@
|
||||
Varyings
|
||||
========
|
||||
|
||||
This is the naming convention followed by the hardware (slightly different
|
||||
from Vulkan naming):
|
||||
|
||||
- "Attribute": per-vertex data
|
||||
- "Varying": per-fragment data
|
||||
|
||||
Thus vertex shaders always interact with attributes and fragment/pixel shaders
|
||||
only interact with varyings (commonly shortened to "VAR").
|
||||
|
||||
|
||||
Hardware descriptors
|
||||
--------------------
|
||||
|
||||
Before Valhall there were two types of hardware descriptors:
|
||||
|
||||
- ``AttributeDescriptor``: Descriptor for a single attribute in a larger buffer,
|
||||
contains offset, stride and the in-memory format.
|
||||
- ``BufferDescriptor``: Buffer, when used for attributes and varyings it
|
||||
contains: pointer, size and stride
|
||||
|
||||
Midgard (v5)
|
||||
------------
|
||||
Attributes are loaded/stored using ``LD_ATTR``/``ST_ATTR``, those query the
|
||||
attribute descriptors and buffer descriptors to find the real global memory
|
||||
offset before loading/storing.
|
||||
All varyings are loaded using ``LD_VAR``, including flat attributes (using a
|
||||
modifier), and special attributes (position, psiz, ecc...). Special attributes
|
||||
require a special descriptor, that is not backed by any buffer, it generates
|
||||
data on-the-fly.
|
||||
There is a concept of in-memory format and register format, the first is written
|
||||
inside of the ``AttributeDescriptor`` while the register format is a modifier of
|
||||
the instructions, when those two disagree the hardware will try to convert them,
|
||||
this is only supported between int-int or float-float operations.
|
||||
|
||||
|
||||
Bifrost (v6)
|
||||
------------
|
||||
Changes:
|
||||
|
||||
- ``ST_ATTR`` is replaced by ``LEA_ATTR`` and ``ST_CVT`` pairs.
|
||||
|
||||
- ``LEA_ATTR`` queries memory address and format from the appropriate
|
||||
descriptor.
|
||||
- ``ST_CVT`` performs the actual conversion and memory store.
|
||||
- A new ``LD_VAR_SPECIAL`` is introduced, now special attributes do not need
|
||||
special descriptors.
|
||||
- ``LD_VAR`` only handles interpolated varyings, flat varyings are now handled
|
||||
by ``LD_VAR_FLAT``.
|
||||
|
||||
Valhall (v9)
|
||||
------------
|
||||
Valhall introduced layout-specific instructions, ``LEA_BUF`` and ``LD_VAR_BUF``,
|
||||
those do not use ``AttributeDescriptor`` but read ``BufferDescriptor`` directly.
|
||||
These new instructions bake the offset and in-memory format of the attribute
|
||||
inside of the shader code itself, saving a lookup. If all shaders in a program
|
||||
use those instructions, we can remove all ``AttributeDescriptor``. If the
|
||||
shaders aren't compiled together, one of the shaders cannot know the data layout,
|
||||
and it needs to fall back to the old ``AttributeDescriptor``-based path. We
|
||||
also have to fall back to ``AttributeDescriptor`` completely if the attribute
|
||||
offset overflows the immediate field.
|
||||
|
||||
``LD_VAR_BUF`` only supports ``.f16`` and ``.f32`` as register modifiers, we can
|
||||
also load (flat) ints with those. We need to specify no conversion
|
||||
(``.f16.src_flat16`` or ``.f32.src_flat32``), but with those we can load both
|
||||
16-bit and 32-bit integers.
|
||||
|
||||
In this architecture we assume the VS always uses IDVS, emitting attribute data
|
||||
with ``LEA_BUF`` (instead of ``LEA_ATTR``), and never emit varying
|
||||
``AttributeDescriptor`` for VS.
|
||||
|
||||
Challenges
|
||||
----------
|
||||
Theoretically, the output types from the VS and input types from the FS should
|
||||
always agree. In practice we cannot trust the varyings types given to us,
|
||||
here are some challenging examples:
|
||||
|
||||
* Shaders are allowed to use the same types with different precision modifiers.
|
||||
* ``nir_opt_varying`` erases highp flat types with "float32" and packs them
|
||||
together.
|
||||
* Some games like to play with ``intBitsToFloat`` / ``floatBitsToInt``, so it's
|
||||
possible to have VS write int and FS read float (in that case, we treat the
|
||||
underlying bits as float, allowing for NaN normalization)
|
||||
|
||||
In practice you have to follow these rules:
|
||||
|
||||
* Only FS knows a varying smoothness, VS sees everything as flat.
|
||||
* When linked together, you cannot trust highp flat types, but you can trust
|
||||
precision
|
||||
* While loading/storing data, mistaking a float for an int is ok, mistaking an
|
||||
int for a float seems to be lossy even without bit-size conversions. Be
|
||||
conservative on what you say is a float.
|
||||
* You cannot lower flat varyings after they passed through ``nir_opt_varying``
|
||||
|
||||
Current implementation rules:
|
||||
|
||||
* VS decides the memory layout
|
||||
* Descriptor formats can mismatch between stages (eg. VS int - FS float)
|
||||
* Descriptor formats always match what the instructions are using
|
||||
|
||||
|
||||
To regain the type information:
|
||||
|
||||
* in VS, every highp varying is written as U32
|
||||
* in FS, highp flat varyings are read as U32, highp smooth are read as F32
|
||||
* for mediump, we trust the original type
|
||||
Reference in new issue
Block a user