summaryrefslogtreecommitdiff
path: root/slang.h
diff options
context:
space:
mode:
Diffstat (limited to 'slang.h')
-rw-r--r--slang.h298
1 files changed, 181 insertions, 117 deletions
diff --git a/slang.h b/slang.h
index 55c454d0d..583072686 100644
--- a/slang.h
+++ b/slang.h
@@ -1571,10 +1571,7 @@ extern "C"
typedef struct SlangProgramLayout SlangProgramLayout;
typedef struct SlangEntryPoint SlangEntryPoint;
typedef struct SlangEntryPointLayout SlangEntryPointLayout;
- typedef struct SlangEntryPointGroupLayout SlangEntryPointGroupLayout;
-// typedef struct SlangReflection SlangReflection;
-// typedef struct SlangReflectionEntryPoint SlangReflectionEntryPoint;
typedef struct SlangReflectionModifier SlangReflectionModifier;
typedef struct SlangReflectionType SlangReflectionType;
typedef struct SlangReflectionTypeLayout SlangReflectionTypeLayout;
@@ -1900,6 +1897,12 @@ extern "C"
SLANG_API int spReflectionEntryPoint_usesAnySampleRateInput(
SlangReflectionEntryPoint* entryPoint);
+ SLANG_API SlangReflectionVariableLayout* spReflectionEntryPoint_getVarLayout(
+ SlangReflectionEntryPoint* entryPoint);
+
+ SLANG_API int spReflectionEntryPoint_hasDefaultConstantBuffer(
+ SlangReflectionEntryPoint* entryPoint);
+
// SlangReflectionTypeParameter
SLANG_API char const* spReflectionTypeParameter_GetName(SlangReflectionTypeParameter* typeParam);
SLANG_API unsigned spReflectionTypeParameter_GetIndex(SlangReflectionTypeParameter* typeParam);
@@ -1922,9 +1925,6 @@ extern "C"
SLANG_API SlangReflectionEntryPoint* spReflection_getEntryPointByIndex(SlangReflection* reflection, SlangUInt index);
SLANG_API SlangReflectionEntryPoint* spReflection_findEntryPointByName(SlangReflection* reflection, char const* name);
- SLANG_API SlangInt spReflection_getEntryPointGroupCount(SlangReflection* reflection);
- SLANG_API SlangEntryPointGroupLayout* spReflection_getEntryPointGroupByIndex(SlangReflection* reflection, SlangInt index);
-
SLANG_API SlangUInt spReflection_getGlobalConstantBufferBinding(SlangReflection* reflection);
SLANG_API size_t spReflection_getGlobalConstantBufferSize(SlangReflection* reflection);
@@ -1935,16 +1935,6 @@ extern "C"
SlangReflectionType* const* specializationArgs,
ISlangBlob** outDiagnostics);
- // Entry point group reflection
-
- SLANG_API SlangInt spEntryPointGroupLayout_getEntryPointCount(SlangEntryPointGroupLayout* group);
- SLANG_API SlangReflectionEntryPoint* spEntryPointGroupLayout_getEntryPointByIndex(SlangEntryPointGroupLayout* group, SlangInt index);
- SLANG_API SlangReflectionVariableLayout* spEntryPointGroupLayout_getVarLayout(SlangEntryPointGroupLayout* group);
-
- SLANG_API SlangInt spEntryPointGroupLayout_getParameterCount(SlangEntryPointGroupLayout* group);
- SLANG_API SlangReflectionVariableLayout* spEntryPointGroupLayout_getParameterByIndex(SlangEntryPointGroupLayout* group, SlangInt index);
-
-
#ifdef __cplusplus
}
@@ -2448,36 +2438,23 @@ namespace slang
{
return 0 != spReflectionEntryPoint_usesAnySampleRateInput((SlangReflectionEntryPoint*) this);
}
- };
- typedef EntryPointReflection EntryPointLayout;
-
- struct EntryPointGroupLayout
- {
- SlangInt getEntryPointCount()
- {
- return spEntryPointGroupLayout_getEntryPointCount((SlangEntryPointGroupLayout*) this);
- }
-
- EntryPointReflection* getEntryPointByIndex(SlangInt index)
- {
- return (EntryPointReflection*) spEntryPointGroupLayout_getEntryPointByIndex((SlangEntryPointGroupLayout*) this, index);
- }
VariableLayoutReflection* getVarLayout()
{
- return (VariableLayoutReflection*) spEntryPointGroupLayout_getVarLayout((SlangEntryPointGroupLayout*) this);
+ return (VariableLayoutReflection*) spReflectionEntryPoint_getVarLayout((SlangReflectionEntryPoint*) this);
}
- SlangInt getParameterCount()
+ TypeLayoutReflection* getTypeLayout()
{
- return spEntryPointGroupLayout_getParameterCount((SlangEntryPointGroupLayout*) this);
+ return getVarLayout()->getTypeLayout();
}
- VariableLayoutReflection* getParameterByIndex(SlangInt index)
+ bool hasDefaultConstantBuffer()
{
- return (VariableLayoutReflection*) spEntryPointGroupLayout_getParameterByIndex((SlangEntryPointGroupLayout*) this, index);
+ return spReflectionEntryPoint_hasDefaultConstantBuffer((SlangReflectionEntryPoint*) this) != 0;
}
};
+ typedef EntryPointReflection EntryPointLayout;
struct TypeParameterReflection
{
@@ -2548,16 +2525,6 @@ namespace slang
return (EntryPointReflection*) spReflection_getEntryPointByIndex((SlangReflection*) this, index);
}
- SlangInt getEntryPointGroupCount()
- {
- return spReflection_getEntryPointGroupCount((SlangReflection*) this);
- }
-
- EntryPointGroupLayout* getEntryPointGroupByIndex(SlangInt index)
- {
- return (EntryPointGroupLayout*) spReflection_getEntryPointGroupByIndex((SlangReflection*) this, index);
- }
-
SlangUInt getGlobalConstantBufferBinding()
{
return spReflection_getGlobalConstantBufferBinding((SlangReflection*)this);
@@ -2609,13 +2576,12 @@ namespace slang
typedef ISlangBlob IBlob;
+ struct IComponentType;
struct IGlobalSession;
struct IModule;
- struct IProgram;
struct ISession;
struct SessionDesc;
- struct ProgramDesc;
struct SpecializationArg;
struct TargetDesc;
@@ -2759,20 +2725,39 @@ namespace slang
const char* moduleName,
IBlob** outDiagnostics = nullptr) = 0;
- /** Create a program out of existing compiled items.
- */
- virtual SLANG_NO_THROW SlangResult SLANG_MCALL createProgram(
- ProgramDesc const& desc,
- IProgram** outProgram) = 0;
+ /** Combine multiple component types to create a composite component type.
+
+ The `componentTypes` array must contain `componentTypeCount` pointers
+ to component types that were loaded or created using the same session.
+
+ The shader parameters and specialization parameters of the composite will
+ be the union of those in `componentTypes`. The relative order of child
+ component types is significant, and will affect the order in which
+ parameters are reflected and laid out.
+
+ The entry-point functions of the composite will be the union of those in
+ `componentTypes`, and will follow the ordering of `componentTypes`.
+
+ The requirements of the composite component type will be a subset of
+ those in `componentTypes`. If an entry in `componentTypes` has a requirement
+ that can be satisfied by another entry, then the composition will
+ satisfy the requirement and it will not appear as a requirement of
+ the composite. If multiple entries in `componentTypes` have a requirement
+ for the same type, then only the first such requirement will be retained
+ on the composite. The relative ordering of requirements on the composite
+ will otherwise match that of `componentTypes`.
+
+ If any diagnostics are generated during creation of the composite, they
+ will be written to `outDiagnostics`. If an error is encountered, the
+ function will return null.
- /** Specialize a program based on type arguments.
+ It is an error to create a composite component type that recursively
+ aggregates the a single module more than once.
*/
- virtual SLANG_NO_THROW SlangResult SLANG_MCALL specializeProgram(
- IProgram* program,
- SlangInt specializationArgCount,
- SpecializationArg const* specializationArgs,
- IProgram** outSpecializedProgram,
- ISlangBlob** outDiagnostics = nullptr) = 0;
+ virtual SLANG_NO_THROW IComponentType* SLANG_MCALL createCompositeComponentType(
+ IComponentType* const* componentTypes,
+ SlangInt componentTypeCount,
+ ISlangBlob** outDiagnostics = nullptr) = 0;
/** Specialize a type based on type arguments.
*/
@@ -2799,76 +2784,95 @@ namespace slang
#define SLANG_UUID_ISession { 0x67618701, 0xd116, 0x468f, { 0xab, 0x3b, 0x47, 0x4b, 0xed, 0xce, 0xe, 0x3d } }
+ /** A component type is a unit of shader code layout, reflection, and linking.
- /** A module is the granularity of shader code compilation and loading.
+ A component type is a unit of shader code that can be included into
+ a linked and compiled shader program. Each component type may have:
- In most cases a module corresponds to a single compile "translation unit."
- This will often be a single `.slang` or `.hlsl` file and everything it
- `#include`s.
+ * Zero or more uniform shader parameters, representing textures,
+ buffers, etc. that the code in the component depends on.
- Notably, a module `M` does *not* include the things it `import`s, as these
- as distinct modules that `M` depends on. There is a directed graph of
- module dependencies, and all modules in the graph must belong to the
- same session (`ISession`).
- */
- struct IModule : public ISlangUnknown
- {
- public:
- };
-
- #define SLANG_UUID_IModule { 0xc720e64, 0x8722, 0x4d31, { 0x89, 0x90, 0x63, 0x8a, 0x98, 0xb1, 0xc2, 0x79 } }
+ * Zero or more *specialization* parameters, which are type or
+ value parameters that can be used to synthesize specialized
+ versions of the component type.
+ * Zero or more entry points, which are the individually invocable
+ kernels that can have final code generated.
- /** Argument used for specialization to types/values.
- */
- struct SpecializationArg
- {
- enum class Kind : int32_t
- {
- Unknown,
- Type,
- };
- Kind kind;
- union
- {
- TypeReflection* type;
- };
- };
+ * Zero or more *requirements*, which are other component
+ types on which the component type depends.
- /** Description of a program to be created.
- */
- struct ProgramDesc
- {
- struct Item
- {
- enum class Kind : int32_t
- {
- Program,
- Module,
- };
- Kind kind;
- union
- {
- IProgram* program;
- IModule* module;
- };
- };
+ One example of a component type is a module of Slang code:
- Item const* items;
- SlangInt itemCount;
- };
+ * The global-scope shader parameters declared in the module are
+ the parameters when considered as a component type.
+
+ * Any global-scope generic or interface type parameters introduce
+ specialization parameters for the module.
+
+ * A module does not by default include any entry points when
+ considered as a component type (although the code of the
+ module might *declare* some entry points).
+
+ * Any other modules that are `import`ed in the source code
+ become requirements of the module, when considered as a
+ component type.
+
+ An entry point is another example of a component type:
+
+ * The `uniform` parameters of the entry point function are
+ its shader parameters when considered as a component type.
+
+ * Any generic or interface-type parameters of the entry point
+ introduce specialization parameters.
+
+ * An entry point component type exposes a single entry point (itself).
+
+ * An entry point has one requirement for the module in which
+ it was defined.
+
+ Component types can be manipulated in a few ways:
+
+ * Multiple component types can be combined into a composite, which
+ combines all of their code, parameters, etc.
+ * A component type can be specialized, by "plugging in" types and
+ values for its specialization parameters.
+
+ * A component type can be laid out for a particular target, giving
+ offsets/bindings to the shader parameters it contains.
+
+ * Generated kernel code can be requested for entry points.
- /** A program comprises zero or more modules, entry points, etc. that have been linked together.
*/
- struct IProgram : public ISlangUnknown
+ struct IComponentType : public ISlangUnknown
{
- public:
- /** Get the runtime session that this program belongs to.
+ /** Get the runtime session that this component type belongs to.
*/
virtual SLANG_NO_THROW ISession* SLANG_MCALL getSession() = 0;
- /** Get the layout for this program for the chosen `targetIndex`
+ /** Get the layout for this program for the chosen `targetIndex`.
+
+ The resulting layout will establish offsets/bindings for all
+ of the global and entry-point shader parameters in the
+ component type.
+
+ If this component type has specialization parameters (that is,
+ it is not fully specialized), then the resulting layout may
+ be incomplete, and plugging in arguments for generic specialization
+ parameters may result in a component type that doesn't have
+ a compatible layout. If the component type only uses
+ interface-type specialization parameters, then the layout
+ for a specialization should be compatible with an unspecialized
+ layout (all parameters in the unspecialized layout will have
+ the same offset/binding in the specialized layout).
+
+ If this component type is combined into a composite, then
+ the absolute offsets/bindings of parameters may not stay the same.
+ If the shader parameters in a component type don't make
+ use of explicit binding annotations (e.g., `register(...)`),
+ then the *relative* offset of shader parameters will stay
+ the same when it is used in a composition.
*/
virtual SLANG_NO_THROW ProgramLayout* SLANG_MCALL getLayout(
SlangInt targetIndex = 0,
@@ -2876,6 +2880,10 @@ namespace slang
/** Get the compiled code for the entry point at `entryPointIndex` for the chosen `targetIndex`
+ Entry point code can only be computed for a component type that
+ has no specialization parameters (it must be fully specialized)
+ and that has no requirements (it must be fully linked).
+
If code has not already been generated for the given entry point and target,
then a compilation error may be detected, in which case `outDiagnostics`
(if non-null) will be filled in with a blob of messages diagnosing the error.
@@ -2885,9 +2893,65 @@ namespace slang
SlangInt targetIndex,
IBlob** outCode,
IBlob** outDiagnostics = nullptr) = 0;
+
+ /** Specialize the component by binding its specialization parameters to concrete arguments.
+
+ The `specializationArgs` array must have `specializationArgCount` entries, and
+ this must match the number of specialization parameters on this component type.
+
+ If the specialization arguments are not valid, then the function will return null.
+
+ If any diagnostics (error or warnings) are produced, they will be written to `outDiagnostics`.
+ */
+ virtual SLANG_NO_THROW IComponentType* SLANG_MCALL specialize(
+ SpecializationArg const* specializationArgs,
+ SlangInt specializationArgCount,
+ ISlangBlob** outDiagnostics = nullptr) = 0;
+ };
+ #define SLANG_UUID_IComponentType { 0x5bc42be8, 0x5c50, 0x4929, { 0x9e, 0x5e, 0xd1, 0x5e, 0x7c, 0x24, 0x1, 0x5f } };
+
+ /** A module is the granularity of shader code compilation and loading.
+
+ In most cases a module corresponds to a single compile "translation unit."
+ This will often be a single `.slang` or `.hlsl` file and everything it
+ `#include`s.
+
+ Notably, a module `M` does *not* include the things it `import`s, as these
+ as distinct modules that `M` depends on. There is a directed graph of
+ module dependencies, and all modules in the graph must belong to the
+ same session (`ISession`).
+
+ A module establishes a namespace for looking up types, functions, etc.
+ */
+ struct IModule : public IComponentType
+ {
+ public:
+ /** Note: eventually operations for looking up types or entry
+ points by name should appear here.
+ */
};
- #define SLANG_UUID_IProgram { 0x5bc42be8, 0x5c50, 0x4929, { 0x9e, 0x5e, 0xd1, 0x5e, 0x7c, 0x24, 0x1, 0x5f } };
+ #define SLANG_UUID_IModule { 0xc720e64, 0x8722, 0x4d31, { 0x89, 0x90, 0x63, 0x8a, 0x98, 0xb1, 0xc2, 0x79 } }
+
+
+ /** Argument used for specialization to types/values.
+ */
+ struct SpecializationArg
+ {
+ enum class Kind : int32_t
+ {
+ Unknown, /**< An invalid specialization argument. */
+ Type, /**< Specialize to a type. */
+ };
+
+ /** The kind of specialization argument. */
+ Kind kind;
+ union
+ {
+ /** A type specialization argument, used for `Kind::Type`. */
+ TypeReflection* type;
+ };
+ };
}
#define SLANG_API_VERSION 0
@@ -2909,7 +2973,7 @@ namespace slang
*/
SLANG_API SlangResult spCompileRequest_getProgram(
SlangCompileRequest* request,
- slang::IProgram** outProgram);
+ slang::IComponentType** outProgram);
#endif