Skip to content

Commit dbc06dd

Browse files
really solid draft now
1 parent 3863e29 commit dbc06dd

File tree

4 files changed

+201
-157
lines changed

4 files changed

+201
-157
lines changed

09_DepthBufferAndCamera/CAssetConverter.cpp

Lines changed: 101 additions & 61 deletions
Original file line numberDiff line numberDiff line change
@@ -5,99 +5,135 @@
55

66
namespace nbl::video
77
{
8-
9-
10-
struct dep_gather_hash
11-
{
12-
template<asset::Asset AssetType>
13-
inline size_t operator()(const CAssetConverter::root_t<AssetType>& in) const
14-
{
15-
return std::hash<const void*>{}(in.asset)^(in.unique ? (~0x0ull):0x0ull);
16-
}
17-
};
18-
template<asset::Asset AssetType>
19-
using dep_gather_cache_t = core::unordered_multimap<CAssetConverter::root_t<AssetType>,typename asset_traits<AssetType>::patch_t,dep_gather_hash>;
8+
using namespace nbl::core;
9+
using namespace nbl::asset;
2010

2111
auto CAssetConverter::reserve(const SInput& input) -> SResults
2212
{
2313
SResults retval = {};
24-
if (input.readCache->m_params.device!=m_params.device)
14+
if (input.readCache && input.readCache->m_params.device!=m_params.device)
2515
return retval;
2616

27-
core::tuple_transform_t<dep_gather_cache_t,supported_asset_types> dep_gather_caches;
28-
// gather all dependencies (DFS graph search) and patch
17+
// gather all dependencies (DFS graph search) and patch, this happens top-down
2918
// do not deduplicate/merge assets at this stage, only patch GPU creation parameters
3019
{
31-
core::stack<const asset::IAsset*> dfsStack;
32-
auto push = [&]<asset::Asset AssetType>(const CAssetConverter::input_t<AssetType>& in)->void
20+
core::stack<const IAsset*> dfsStack;
21+
// returns true if new element was inserted
22+
auto cache = [&]<Asset AssetType>(const CAssetConverter::SInput::input_t<AssetType>& in)->bool
3323
{
34-
using cache_t = dep_gather_cache_t<AssetType>;
35-
auto& cache = std::get<cache_t>(dep_gather_caches);
36-
auto found = cache.equal_range(in);
24+
if (!in.key.asset)
25+
return false;
26+
27+
using cache_t = SResults::dag_cache_t<AssetType>;
28+
auto& cache = std::get<cache_t>(retval.m_typedDagNodes);
29+
auto found = cache.equal_range(in.key);
3730
if (found.first!=found.second)
3831
{
3932
#if 0
4033
// found the thing, combine patches
4134
const auto& cachedPatch = found->patch;
4235
if (auto combined=in.patch; combined)
36+
{
4337
const_cast<asset_traits<AssetType>::patch_t&>(cachedPatch) = combined;
38+
return false;
39+
}
4440
#endif
41+
// check whether the item is creatable after patching, else duplicate/de-alias
4542
}
4643
// insert a new entry
47-
cache.insert(found.first,{in,{}/*in.patch*/});
44+
cache.insert(found.first,{in.key,{.patch=in.patch}});
45+
return true;
4846
};
49-
core::visit([&push]<asset::Asset AssetType>(const SInput::span_t<AssetType> assets)->void{
50-
for (auto& asset : assets)
51-
push(asset);
47+
// initialize stacks
48+
core::visit([&]<Asset AssetType>(const SInput::span_t<AssetType> inputs)->void{
49+
for (auto& in : inputs)
50+
if (cache(in) && AssetType::HasDependents)
51+
dfsStack.push(in.key.asset);
5252
},input.assets);
53-
/*
54-
auto pushAll = [&push]()->void
55-
{
56-
};
53+
// everything that's not explicit has `!unique` and default patch params
5754
while (!dfsStack.empty())
5855
{
5956
const auto* asset = dfsStack.top();
6057
dfsStack.pop();
61-
62-
auto found = std::get<dep_gather_cache_t<asset::ICPUShader>>(dep_gather_caches).find(asset);
63-
if (!=end())
58+
// everything we popped, has already been cached, now time to go over dependents
59+
switch (asset->getAssetType())
6460
{
61+
#if 0
62+
case ICPUPipelineLayout::AssetType:
63+
{
64+
auto pplnLayout = static_cast<const ICPUPipelineLayout*>(asset);
65+
for (auto i=0; i<ICPUPipelineLayout::DESCRIPTOR_SET_COUNT; i++)
66+
if (auto layout=pplnLayout->getDescriptorSetLayout(i); layout)
67+
if (cache({/*TODO*/}))
68+
dfsStack.push(layout);
69+
break;
70+
}
71+
case ICPUDescriptorSetLayout::AssetType:
72+
{
73+
auto layout = static_cast<const ICPUDescriptorSetLayout*>(asset);
74+
for (const auto& sampler : layout->getImmutableSamplers())
75+
cache({/*TODO*/});
76+
break;
77+
}
78+
#endif
79+
case ICPUDescriptorSet::AssetType:
80+
{
81+
_NBL_TODO();
82+
break;
83+
}
84+
case ICPUImageView::AssetType:
85+
{
86+
_NBL_TODO();
87+
break;
88+
}
89+
case ICPUBufferView::AssetType:
90+
{
91+
_NBL_TODO();
92+
break;
93+
}
94+
// these assets have no dependants, should have never been pushed on the stack
95+
default:
96+
assert(false);
97+
break;
6598
}
6699
}
67-
*/
68100
}
101+
// now we have a set of implicit gpu creation parameters we want to create resources with
102+
// and a mapping from (Asset,Patch) -> UniqueAsset
69103

70-
// check whether the item is creatable after patching, else duplicate/de-alias
71-
72-
// now we have a list of gpu creation parameters we want to create resources with
73-
74-
#if 0
75-
auto stuff = [&]<typename AssetType>(const input_t<AssetType>& key)->void
104+
auto dedup = [&]<Asset AssetType>()->void
76105
{
77-
//
78-
CCache::search_t<AssetType> s = key;
79-
if (!s.patch.has_value())
80-
s.patch = asset_traits<AssetType>::defaultPatch(key.asset);
81-
const size_t hash = CCache::Hash{}(s);
82-
83-
// search by the {asset+patch} in read cache
84-
if (auto found=input.readCache->find(s,hash); found!=input.readCache->end<AssetType>())
106+
using cache_t = SResults::dag_cache_t<AssetType>;
107+
core::unordered_set<typename cache_t::value_type*/*TODO: Hash,Equals*/> conser;
108+
for (auto& asset : std::get<cache_t>(retval.m_typedDagNodes))
85109
{
86-
//
110+
auto [it, inserted] = conser.insert(&asset);
111+
if (inserted)
112+
{
113+
if (input.readCache)
114+
continue; // TODO: below
115+
// if (auto found=input.readCache->find(); found!=input.readCache->end())
116+
// asset.second.result = found->result;
117+
}
118+
else
119+
{
120+
assert(!asset.second.canonical);
121+
asset.second.canonical = &(*it)->second;
122+
}
87123
}
88-
89-
// reserve in write cache
90124
};
91-
#endif
92-
93-
// if read cache
94-
// find deps in read cache
95-
// mark deps as ready/found
96-
// if not ready/found
97-
// find dep in transient cache
98-
// if not found, insert and recurse
99-
100-
// see what can be patched/combined
125+
// Lets see if we can collapse any of the (Asset Content) into the same thing,
126+
// to correctly de-dup we need to go bottom-up!!!
127+
dedup.operator()<ICPUShader>();
128+
// Shader, DSLayout, PipelineLayout, Compute Pipeline
129+
// Renderpass, Graphics Pipeline
130+
// Buffer, BufferView, Sampler, Image, Image View, Bottom Level AS, Top Level AS, Descriptor Set, Framebuffer
131+
// Buffer -> SRange, patched usage, owner(s)
132+
// BufferView -> SRange, promoted format
133+
// Sampler -> Clamped Params (only aniso, really)
134+
// Image -> this, patched usage, promoted format
135+
// Image View -> ref to patched Image, patched usage, promoted format
136+
// Descriptor Set -> unique layout,
101137

102138
return retval;
103139
}
@@ -140,9 +176,13 @@ bool CAssetConverter::convert(SResults& reservations, SConvertParams& params)
140176
.writeCache = m_params.compilerCache.get()
141177
};
142178

179+
for (auto& shader : std::get<SResults::dag_cache_t<ICPUShader>>(reservations.m_typedDagNodes))
180+
if (!shader.second.canonical)
143181
{
144-
params.cpushader = nullptr; // TODO
145-
reservations.get<asset::ICPUShader>().emplace_back(device->createShader(params));
182+
assert(!shader.second.result);
183+
// custom code start
184+
params.cpushader = shader.first.asset;
185+
shader.second.result = device->createShader(params);
146186
}
147187
}
148188

0 commit comments

Comments
 (0)