Skip to content

Commit e56ac2f

Browse files
committed
CSPIRVIntrospector Edits + TODOs for hash and equal
1 parent 40ba05f commit e56ac2f

File tree

8 files changed

+213
-319
lines changed

8 files changed

+213
-319
lines changed

include/nbl/asset/asset.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@
4444
#include "nbl/asset/utils/ShaderRes.h"
4545
#include "nbl/asset/utils/IShaderCompiler.h"
4646
#include "nbl/asset/utils/CGLSLCompiler.h"
47-
#include "nbl/asset/utils/CShaderIntrospector.h"
47+
#include "nbl/asset/utils/CSPIRVIntrospector.h"
4848

4949
// pipelines
5050

Lines changed: 173 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,173 @@
1+
// Copyright (C) 2018-2020 - DevSH Graphics Programming Sp. z O.O.
2+
// This file is part of the "Nabla Engine".
3+
// For conditions of distribution and use, see copyright notice in nabla.h
4+
5+
#ifndef __NBL_ASSET_C_SHADER_INTROSPECTOR_H_INCLUDED__
6+
#define __NBL_ASSET_C_SHADER_INTROSPECTOR_H_INCLUDED__
7+
8+
#include "nbl/core/declarations.h"
9+
10+
#include <cstdint>
11+
#include <memory>
12+
13+
#include "nbl/asset/ICPUSpecializedShader.h"
14+
#include "nbl/asset/ICPUImageView.h"
15+
#include "nbl/asset/ICPUComputePipeline.h"
16+
#include "nbl/asset/ICPURenderpassIndependentPipeline.h"
17+
#include "nbl/asset/utils/ShaderRes.h"
18+
#include "nbl/asset/utils/CGLSLCompiler.h"
19+
20+
21+
#include "nbl/core/definitions.h"
22+
23+
24+
namespace spirv_cross
25+
{
26+
class ParsedIR;
27+
class Compiler;
28+
struct SPIRType;
29+
}
30+
31+
namespace nbl::asset
32+
{
33+
34+
class NBL_API CIntrospectionData : public core::IReferenceCounted
35+
{
36+
protected:
37+
~CIntrospectionData();
38+
39+
public:
40+
struct SSpecConstant
41+
{
42+
uint32_t id;
43+
size_t byteSize;
44+
E_GLSL_VAR_TYPE type;
45+
std::string name;
46+
union {
47+
uint64_t u64;
48+
int64_t i64;
49+
uint32_t u32;
50+
int32_t i32;
51+
double f64;
52+
float f32;
53+
} defaultValue;
54+
};
55+
//! Sorted by `id`
56+
core::vector<SSpecConstant> specConstants;
57+
//! Each vector is sorted by `binding`
58+
core::vector<SShaderResourceVariant> descriptorSetBindings[4];
59+
//! Sorted by `location`
60+
core::vector<SShaderInfoVariant> inputOutput;
61+
62+
struct {
63+
bool present;
64+
SShaderPushConstant info;
65+
} pushConstant;
66+
67+
bool canSpecializationlesslyCreateDescSetFrom() const
68+
{
69+
for (const auto& descSet : descriptorSetBindings)
70+
{
71+
auto found = std::find_if(descSet.begin(), descSet.end(), [](const SShaderResourceVariant& bnd) { return bnd.descCountIsSpecConstant; });
72+
if (found != descSet.end())
73+
return false;
74+
}
75+
return true;
76+
}
77+
};
78+
79+
class NBL_API CSPIRVIntrospector : public core::Uncopyable
80+
{
81+
using mapId2SpecConst_t = core::unordered_map<uint32_t, const CIntrospectionData::SSpecConstant*>;
82+
83+
public:
84+
struct SIntrospectionParams
85+
{
86+
std::string entryPoint;
87+
core::smart_refctd_ptr<const ICPUShader> cpuShader;
88+
89+
bool operator==(const SIntrospectionParams& rhs) const { return false; /*TODO*/ }
90+
};
91+
92+
//In the future there's also going list of enabled extensions
93+
CSPIRVIntrospector() = default;
94+
95+
//! params.cpuShader.contentType should be ECT_SPIRV
96+
//! the compiled SPIRV must be compiled with IShaderCompiler::SOptions::genDebugInfo in order to include names in introspection data
97+
const core::smart_refctd_ptr<CIntrospectionData> introspect(const SIntrospectionParams& params, bool insertToCache = true);
98+
99+
//
100+
std::pair<bool/*is shadow sampler*/, IImageView<ICPUImage>::E_TYPE> getImageInfoFromIntrospection(uint32_t set, uint32_t binding, const core::SRange<const ICPUSpecializedShader* const>& _shaders);
101+
102+
inline core::smart_refctd_dynamic_array<SPushConstantRange> createPushConstantRangesFromIntrospection(const core::SRange<const ICPUSpecializedShader* const>& _shaders)
103+
{
104+
core::smart_refctd_ptr<CIntrospectionData> introspections[MAX_STAGE_COUNT] = { nullptr };
105+
if (!introspectAllShaders(introspections,_shaders))
106+
return nullptr;
107+
108+
return createPushConstantRangesFromIntrospection_impl(introspections,_shaders);
109+
}
110+
inline core::smart_refctd_ptr<ICPUDescriptorSetLayout> createApproximateDescriptorSetLayoutFromIntrospection(uint32_t set, const core::SRange<const ICPUSpecializedShader* const>& _shaders)
111+
{
112+
core::smart_refctd_ptr<CIntrospectionData> introspections[MAX_STAGE_COUNT] = { nullptr };
113+
if (!introspectAllShaders(introspections,_shaders))
114+
return nullptr;
115+
116+
return createApproximateDescriptorSetLayoutFromIntrospection_impl(set,introspections,_shaders);
117+
}
118+
inline core::smart_refctd_ptr<ICPUPipelineLayout> createApproximatePipelineLayoutFromIntrospection(const core::SRange<const ICPUSpecializedShader* const>& _shaders)
119+
{
120+
core::smart_refctd_ptr<CIntrospectionData> introspections[MAX_STAGE_COUNT] = { nullptr };
121+
if (!introspectAllShaders(introspections,_shaders))
122+
return nullptr;
123+
124+
return createApproximatePipelineLayoutFromIntrospection_impl(introspections,_shaders);
125+
}
126+
127+
//
128+
inline core::smart_refctd_ptr<ICPUComputePipeline> createApproximateComputePipelineFromIntrospection(ICPUSpecializedShader* shader)
129+
{
130+
if (shader->getStage() != IShader::ESS_COMPUTE)
131+
return nullptr;
132+
133+
const core::SRange<const ICPUSpecializedShader* const> shaders = {&shader,&shader+1};
134+
core::smart_refctd_ptr<CIntrospectionData> introspection = nullptr;
135+
if (!introspectAllShaders(&introspection,shaders))
136+
return nullptr;
137+
138+
auto layout = createApproximatePipelineLayoutFromIntrospection_impl(&introspection,shaders);
139+
return core::make_smart_refctd_ptr<ICPUComputePipeline>(
140+
std::move(layout),
141+
core::smart_refctd_ptr<ICPUSpecializedShader>(shader)
142+
);
143+
}
144+
145+
//
146+
core::smart_refctd_ptr<ICPURenderpassIndependentPipeline> createApproximateRenderpassIndependentPipelineFromIntrospection(const core::SRange<ICPUSpecializedShader* const>& _shaders);
147+
148+
private:
149+
core::smart_refctd_dynamic_array<SPushConstantRange> createPushConstantRangesFromIntrospection_impl(core::smart_refctd_ptr<CIntrospectionData>* const introspections, const core::SRange<const ICPUSpecializedShader* const>& shaders);
150+
core::smart_refctd_ptr<ICPUDescriptorSetLayout> createApproximateDescriptorSetLayoutFromIntrospection_impl(uint32_t _set, core::smart_refctd_ptr<CIntrospectionData>* const introspections, const core::SRange<const ICPUSpecializedShader* const>& shaders);
151+
core::smart_refctd_ptr<ICPUPipelineLayout> createApproximatePipelineLayoutFromIntrospection_impl(core::smart_refctd_ptr<CIntrospectionData>* const introspections, const core::SRange<const ICPUSpecializedShader* const>& shaders);
152+
153+
_NBL_STATIC_INLINE_CONSTEXPR size_t MAX_STAGE_COUNT = 14ull;
154+
bool introspectAllShaders(core::smart_refctd_ptr<CIntrospectionData>* introspection, const core::SRange<const ICPUSpecializedShader* const>& _shaders);
155+
156+
core::smart_refctd_ptr<CIntrospectionData> doIntrospection(spirv_cross::Compiler& _comp, const std::string& entryPoint, const IShader::E_SHADER_STAGE stage) const;
157+
void shaderMemBlockIntrospection(spirv_cross::Compiler& _comp, impl::SShaderMemoryBlock& _res, uint32_t _blockBaseTypeID, uint32_t _varID, const mapId2SpecConst_t& _sortedId2sconst) const;
158+
size_t calcBytesizeforType(spirv_cross::Compiler& _comp, const spirv_cross::SPIRType& _type) const;
159+
160+
private:
161+
162+
struct KeyHasher
163+
{
164+
std::size_t operator()(const SIntrospectionParams& t) const { return 0; /*TODO*/ }
165+
};
166+
167+
using ParamsToDataMap = core::unordered_map<SIntrospectionParams,core::smart_refctd_ptr<CIntrospectionData>, KeyHasher>;
168+
ParamsToDataMap m_introspectionCache;
169+
};
170+
171+
} // nbl::asset
172+
173+
#endif

0 commit comments

Comments
 (0)