[llvm] [DirectX][DXIL] Update DXIL Op TableGen Specification (PR #95807)
Chris B via llvm-commits
llvm-commits at lists.llvm.org
Wed Jun 19 08:30:21 PDT 2024
================
@@ -14,147 +14,254 @@ Introduction
encapsulates, among other information, various DXIL Operations in
`hctdb.py <https://github.com/microsoft/DirectXShaderCompiler/blob/main/utils/hct/hctdb.py>`_.
DXIL Operations are represented in one of the following `two ways
-<https://github.com/microsoft/DirectXShaderCompiler/blob/130877392c263888ef06bab768856d3dab1f1c9a/docs/DXIL.rst#L1978>`_:
+<https://github.com/microsoft/DirectXShaderCompiler/blob/main/docs/DXIL.rst#operations>`_:
#. Using LLVM instructions.
#. Using LLVM External functions. These are represented in LLVM IR as follows:
+
* "Standard" LLVM intrinsics (e.g., ``llvm.sin.*``) and
* HLSL intrinsics (defined as LLVM intrinsics in ``llvm/include/llvm/IR/IntrinsicsDirectX.td``, e.g., ``llvm.dx.*``)
These are collectively referred to as `LLVM Intrinsics` in this note.
-Following is the complete list of properties of DXIL Ops with the corresponding field name
-as used in ``hctdb.py``. A DXIL Op is represented by a set of associated properties. These
-are categorized into two groups - viz., those that are (1) consumed in DXIL backend passes
-and (2) consumed in other usage scenarios such as validation, DXIL reader, etc.
+Following is the complete list of attributes of DXIL Ops with the corresponding field name
+as used in ``hctdb.py``. A DXIL Op is represented by a set of associated attributes. These
+are consumed in DXIL backend passes as well as in other usage scenarios such as validation,
+DXIL reader, etc.
-A. Properties consumed in DXIL backend passes
+A. Attributes consumed in DXIL backend passes
1. Name of operation (``dxil_op``)
- 2. The generic or HLSL-specific intrinsic that maps to the operation (``llvm_name``).
- 3. Unique Integer ID (``dxil_opid``)
- 4. Operation Class signifying the name and function signature of the operation (``dxil_class``).
- This string is an integral part of the DXIL Op function name and is constructed in
- the format ``dx.op.<class-name>.<overload-type>``. The DXIL validator checks for any
- deviation from this for each of the DXIL Op call.
- 5. List of valid overload types for the operation (``oload_types``).
- 6. Required DXIL Version with support for the operation.
- 7. A string that documents the operation (``doc``) - This is not strictly necessary but is included
+ 2. A string that documents the operation (``doc``) - This is not strictly necessary but is included
for readability and documentation of the operation.
-
-B. Properties consumed in other usage scenarios
-
- 1. Required minimum Shader Model (``shader_model``).
- 2. Minimum shader model required with translation by linker (``shader_model_translated``)
- 3. List of shader stages applicable to (``shader_stages``), empty for all.
- 4. Memory access attributes of the operation (``fn_attr``).
- 5. Boolean attributes of operation to indicate if it
-
- * is some kind of a derivative (``is_derivative``)
- * requires gradient calculation (``is_gradient``)
- * is a sampler feedback (``is_feedback``)
- * requires in-wave, cross-lane functionality (``is_wave``)
- * requires that all of its inputs are uniform across the wave (``requires_uniform_inputs``).
- * is a barrier operation (``is_barrier``).
+ 3. The generic or HLSL-specific intrinsic that maps to the operation (``llvm_name``).
+ 4. Unique Integer ID (``dxil_opid``)
+ 5. Operation Class signifying the name and function signature of the operation (``dxil_class``).
+ This string is an integral part of the DXIL Op function name and is constructed in
+ the format ``dx.op.<class-name>.<overload-type>``. Each DXIL Op call target function name
+ is required to conform to this format per existing contract with the driver.
+ 6. List of valid overload types for the operation (``oload_types``).
+ 7. Required DXIL Version with support for the operation.
+ 8. Required minimum Shader Model (``shader_model``).
+ 9. Minimum shader model required with translation by linker (``shader_model_translated``)
+ 10. List of shader stages applicable to (``shader_stages``), empty, if applicable to all stages.
+ 11. Memory access attributes of the operation (``fn_attr``).
+ 12. Boolean attributes of operation to indicate if it
+
+ * is some kind of a derivative (``is_derivative``)
+ * requires gradient calculation (``is_gradient``)
+ * is a sampler feedback (``is_feedback``)
+ * requires in-wave, cross-lane functionality (``is_wave``)
+ * requires that all of its inputs are uniform across the wave (``requires_uniform_inputs``).
+ * is a barrier operation (``is_barrier``).
Motivation
==========
-DXIL backend passes depend on various properties of DXIL Operations. For example, ``DXILLowering``
+DXIL backend passes depend on various attributes of DXIL Operations. For example, ``DXIOpLLowering``
pass will need information such as the DXIL operation an LLVM intrinsic is to be lowered to,
along with valid overload and parameter types etc. The TableGen file -
``llvm/lib/Target/DirectX/DXIL.td`` - is used to represent DXIL Operations
-by specifying their properties listed above. ``DXIL.td`` is designed to be the single source
-of reference of DXIL Operations for DXIL backend implementation in ``llvm-project`` repo -
-analogous to ``hctdb.py`` for ``DirectXShadeCompiler`` repo. It needs to have a rich
-representation capabilities that TableGen backends (such as ``DXILEmitter``) can rely on.
-Additionally, the DXIL Op specification should be easy to read and comprehend.
+by specifying their attributes listed above. ``DXIL.td`` is designed to be the single source
+of reference of DXIL Operations primarily for the implementation of passes in DXIL backend in
+``llvm-project`` repo - analogous to ``hctdb.py`` for ``DirectXShadeCompiler`` repo. However,
+the current design does not intend to encapsulate various validation rules, present in ``hctdb.py``,
+but do not pertain to DXIL Operations. It needs to have a rich representation capabilities that
+TableGen backends (such as ``DXILEmitter``) can rely on. Additionally, the DXIL Op specification
+should be easy to read and comprehend.
-This note focuses on specification of the set of properties consumed by DXIL backend
-passes identified above in category A. Any of the properties from category B are expected to be
-included as deemed necessary during implementation.
+This note provides the design of the specification DXIL Ops as TableGen class ``DXILOp``
+by specifying its attributes identified above.
-Design
-======
+DXIL Operation Specification
+============================
+
+The DXIL Operation is represented using the TableGen class ``DXILOp``. The DXIL operation
+attributes are specified as fields of the ``DXILOp`` class as described below.
1. Each DXIL Operation is represented as a TableGen record. The name of each of the records
signifies operation name.
-2. The LLVM Intrinsic that maps to the operation is represented using ``Intrinsic::*``.
-3. The unique operation id is represented by an integer.
-4. DXIL Operation Class is represented as follows
+2. A documentation string for the operation.
+3. The LLVM Intrinsic that maps to the operation is represented as ``Intrinsic`` defined in
+ `Intrinsics.td <https://github.com/llvm/llvm-project/blob/main/llvm/include/llvm/IR/Intrinsics.td>`_.
+4. The unique operation id is represented by an integer.
+5. DXIL Operation Class is represented as follows
.. code-block::
// Abstraction of DXIL Operation class.
- // It encapsulates an associated function signature viz.,
- // returnTy(param1Ty, param2Ty, ...) represented as a list of LLVMTypes.
- // DXIL Ops that belong to a DXILOpClass record the signature of that DXILOpClass
-
- class DXILOpClass<list<LLVMType> OpSig> {
- list<LLVMType> OpSignature = OpSig;
- }
+ class DXILOpClass;
- Concrete operation classes, such as ``unary`` are defined inheriting from ``DXILOpClass``.
-5. Valid overload types are represented as a list of ``LLVMType``.
-6. Concrete records of DXIL versions and are defined by inheriting from the class
+ Concrete operation records, such as ``unary`` are defined by inheriting from ``DXILOpClass``.
+6. Return and argument types of the operation are represented as ``dag``s using the
+ special markers ``out`` and ``ins``. An overload type, if supported by the operation, is
+ denoted as the positional type ``dxil_overload_ty`` in the argument or in the result, where
+ ``dxil_overload_ty`` is defined to be synonymous to ``llvm_any_ty``.
.. code-block::
- // Abstract class to represent major and minor version values
- class Version<int major, int minor> {
- int Major = major;
- int Minor = minor;
- }
+ defvar dxil_overload_ty = llvm_any_ty
-7. A documentation string for the operation.
+7. Valid overload types and shader stages predicated on Shader Model version are specified
+ as a list of ``Constraint`` records. Representation of ``Constraints`` class is described
+ a later section.
+8. Various attributes of the DXIL Operation that are not predicated on Shader Model version
+ are represented as a ``dag`` using the special marker ``attrs``. Representation of ``Attributes``
+ class is described in a later section.
A DXIL Operation is represented by the following TableGen class by encapsulating the various
-TableGen representations of its properties described above.
+TableGen representations of its attributes described above.
+
+.. code-block::
+
+ // Abstraction DXIL Operation
+ class DXILOp {
+ // A short description of the operation
+ string Doc = "";
+
+ // Opcode of DXIL Operation
+ int OpCode = 0;
+
+ // Class of DXIL Operation.
+ DXILOpClass OpClass = UnknownOpClass;
+
+ // LLVM Intrinsic DXIL Operation maps to
+ Intrinsic LLVMIntrinsic = ?;
+
+ // Dag containing the arguments of the op. Default to 0 arguments.
+ dag arguments = (ins);
----------------
llvm-beanz wrote:
It might be nice to have an example that actually sets the `arguments` and `result` fields so that we can see what it looks like.
https://github.com/llvm/llvm-project/pull/95807
More information about the llvm-commits
mailing list