瀏覽代碼

Move LensFlareSprite and LensFlareUpdateIndirectInfo to the new format

Panagiotis Christopoulos Charitos 5 年之前
父節點
當前提交
2a7de0abbc

+ 2 - 4
shaders/LensFlareSprite.glslp → shaders/LensFlareSprite.ankiprog

@@ -3,16 +3,14 @@
 // Code licensed under the BSD License.
 // http://www.anki3d.org/LICENSE
 
-#pragma anki input const U32 MAX_SPRITES
-
 #pragma anki start vert
 #include <shaders/Common.glsl>
 #include <shaders/glsl_cpp_common/LensFlareSprite.h>
 
 // The block contains data for all flares
-layout(std140, set = 0, binding = 0) uniform _blk
+layout(std140, set = 0, binding = 0) readonly buffer ssbo00
 {
-	LensFlareSprite u_sprites[MAX_SPRITES];
+	LensFlareSprite u_sprites[];
 };
 
 layout(location = 0) out Vec3 out_uv;

+ 2 - 2
shaders/LensFlareUpdateIndirectInfo.glslp → shaders/LensFlareUpdateIndirectInfo.ankiprog

@@ -3,7 +3,7 @@
 // Code licensed under the BSD License.
 // http://www.anki3d.org/LICENSE
 
-#pragma anki input const Vec2 IN_DEPTH_MAP_SIZE
+ANKI_SPECIALIZATION_CONSTANT_UVEC2(IN_DEPTH_MAP_SIZE, 0, UVec2(1.0));
 
 #pragma anki start comp
 #include <shaders/Common.glsl>
@@ -54,7 +54,7 @@ void main()
 	// Compute the UVs to sample the depth map
 	// Belongs to [-WORKGROUP_SIZE, WORKGROUP_SIZE]
 	const Vec2 displacement = Vec2(gl_LocalInvocationID.xy) - Vec2(WORKGROUP_SIZE / 2u);
-	const Vec2 TEXEL_SIZE = 1.0 / IN_DEPTH_MAP_SIZE;
+	const Vec2 TEXEL_SIZE = 1.0 / Vec2(IN_DEPTH_MAP_SIZE);
 	const Vec2 uv = NDC_TO_UV(posNdc.xy) + displacement * TEXEL_SIZE;
 
 	// Sample and store depth

+ 16 - 8
src/anki/gr/vulkan/DescriptorSet.cpp

@@ -767,16 +767,24 @@ Error DSLayoutCacheEntry::getOrCreateThreadAllocator(ThreadId tid, DSThreadAlloc
 
 		WLockGuard<RWMutex> lock(m_threadAllocsMtx);
 
-		alloc = m_factory->m_alloc.newInstance<DSThreadAllocator>(this, tid);
-		ANKI_CHECK(alloc->init());
+		// Search again
+		auto it = binarySearch(m_threadAllocs.getBegin(), m_threadAllocs.getEnd(), tid, Comp());
+		alloc = (it != m_threadAllocs.getEnd()) ? *it : nullptr;
 
-		m_threadAllocs.resize(m_factory->m_alloc, m_threadAllocs.getSize() + 1);
-		m_threadAllocs[m_threadAllocs.getSize() - 1] = alloc;
+		// Create
+		if(alloc == nullptr)
+		{
+			alloc = m_factory->m_alloc.newInstance<DSThreadAllocator>(this, tid);
+			ANKI_CHECK(alloc->init());
 
-		// Sort for fast find
-		std::sort(m_threadAllocs.getBegin(),
-			m_threadAllocs.getEnd(),
-			[](const DSThreadAllocator* a, const DSThreadAllocator* b) { return a->m_tid < b->m_tid; });
+			m_threadAllocs.resize(m_factory->m_alloc, m_threadAllocs.getSize() + 1);
+			m_threadAllocs[m_threadAllocs.getSize() - 1] = alloc;
+
+			// Sort for fast find
+			std::sort(m_threadAllocs.getBegin(),
+				m_threadAllocs.getEnd(),
+				[](const DSThreadAllocator* a, const DSThreadAllocator* b) { return a->m_tid < b->m_tid; });
+		}
 	}
 
 	ANKI_ASSERT(alloc);

+ 1 - 1
src/anki/renderer/ClusterBin.cpp

@@ -712,7 +712,7 @@ void ClusterBin::writeTypedObjectsToGpuBuffers(BinCtx& ctx) const
 			out.m_texProjectionMat = in.m_textureMatrix;
 		}
 
-		ANKI_ASSERT(diffuseAtlas && specularRoughnessAtlas);
+		ANKI_ASSERT(diffuseAtlas || specularRoughnessAtlas);
 		ctx.m_out->m_diffDecalTexView.reset(diffuseAtlas);
 		ctx.m_out->m_specularRoughnessDecalTexView.reset(specularRoughnessAtlas);
 	}

+ 9 - 13
src/anki/renderer/LensFlare.cpp

@@ -53,12 +53,9 @@ Error LensFlare::initSprite(const ConfigSet& config)
 	m_maxSprites = U16(m_maxSpritesPerFlare * m_maxFlares);
 
 	// Load prog
-	ANKI_CHECK(getResourceManager().loadResource("shaders/LensFlareSprite.glslp", m_realProg));
-
-	ShaderProgramResourceConstantValueInitList<1> consts(m_realProg);
-	consts.add("MAX_SPRITES", U32(m_maxSprites));
-	const ShaderProgramResourceVariant* variant;
-	m_realProg->getOrCreateVariant(consts.get(), variant);
+	ANKI_CHECK(getResourceManager().loadResource("shaders/LensFlareSprite.ankiprog", m_realProg));
+	const ShaderProgramResourceVariant2* variant;
+	m_realProg->getOrCreateVariant(variant);
 	m_realGrProg = variant->getProgram();
 
 	return Error::NONE;
@@ -74,13 +71,12 @@ Error LensFlare::initOcclusion(const ConfigSet& config)
 		"LensFlares"));
 
 	ANKI_CHECK(
-		getResourceManager().loadResource("shaders/LensFlareUpdateIndirectInfo.glslp", m_updateIndirectBuffProg));
-
-	ShaderProgramResourceConstantValueInitList<1> consts(m_updateIndirectBuffProg);
-	consts.add("IN_DEPTH_MAP_SIZE", Vec2(F32(m_r->getWidth() / 2 / 2), F32(m_r->getHeight() / 2 / 2)));
+		getResourceManager().loadResource("shaders/LensFlareUpdateIndirectInfo.ankiprog", m_updateIndirectBuffProg));
 
-	const ShaderProgramResourceVariant* variant;
-	m_updateIndirectBuffProg->getOrCreateVariant(consts.get(), variant);
+	ShaderProgramResourceVariantInitInfo2 variantInitInfo(m_updateIndirectBuffProg);
+	variantInitInfo.addConstant("IN_DEPTH_MAP_SIZE", UVec2(m_r->getWidth() / 2 / 2, m_r->getHeight() / 2 / 2));
+	const ShaderProgramResourceVariant2* variant;
+	m_updateIndirectBuffProg->getOrCreateVariant(variantInitInfo, variant);
 	m_updateIndirectBuffGrProg = variant->getProgram();
 
 	return Error::NONE;
@@ -175,7 +171,7 @@ void LensFlare::runDrawFlares(const RenderingContext& ctx, CommandBufferPtr& cmd
 
 		// Get uniform memory
 		LensFlareSprite* tmpSprites =
-			allocateAndBindUniforms<LensFlareSprite*>(spritesCount * sizeof(LensFlareSprite), cmdb, 0, 0);
+			allocateAndBindStorage<LensFlareSprite*>(spritesCount * sizeof(LensFlareSprite), cmdb, 0, 0);
 		WeakArray<LensFlareSprite> sprites(tmpSprites, spritesCount);
 
 		// misc

+ 2 - 2
src/anki/renderer/LensFlare.h

@@ -41,11 +41,11 @@ public:
 private:
 	// Occlusion test
 	BufferPtr m_indirectBuff;
-	ShaderProgramResourcePtr m_updateIndirectBuffProg;
+	ShaderProgramResource2Ptr m_updateIndirectBuffProg;
 	ShaderProgramPtr m_updateIndirectBuffGrProg;
 
 	// Sprite billboards
-	ShaderProgramResourcePtr m_realProg;
+	ShaderProgramResource2Ptr m_realProg;
 	ShaderProgramPtr m_realGrProg;
 	U8 m_maxSpritesPerFlare;
 	U8 m_maxFlares;

+ 6 - 0
src/anki/resource/MaterialResource2.cpp

@@ -652,6 +652,12 @@ const MaterialVariant2& MaterialResource2::getOrCreateVariant(const RenderingKey
 	// Not initialized, init it
 	WLockGuard<RWMutex> lock(m_variantMatrixMtx);
 
+	// Check again
+	if(variant.m_prog.isCreated())
+	{
+		return variant;
+	}
+
 	ShaderProgramResourceVariantInitInfo2 initInfo(m_prog);
 
 	for(const SubMutation& m : m_nonBuiltinsMutation)

+ 13 - 3
src/anki/resource/ShaderProgramResource2.cpp

@@ -219,17 +219,27 @@ void ShaderProgramResource2::getOrCreateVariant(
 
 		auto it = m_variants.find(hash);
 		variant = (it != m_variants.getEnd()) ? *it : nullptr;
+
+		if(variant != nullptr)
+		{
+			// Done
+			return;
+		}
 	}
 
+	// Create the variant
+	WLockGuard<RWMutex> lock(m_mtx);
+
+	// Check again
+	auto it = m_variants.find(hash);
+	variant = (it != m_variants.getEnd()) ? *it : nullptr;
 	if(variant != nullptr)
 	{
 		// Done
 		return;
 	}
 
-	// Create the variant
-	WLockGuard<RWMutex> lock(m_mtx);
-
+	// Create
 	ShaderProgramResourceVariant2* v = getAllocator().newInstance<ShaderProgramResourceVariant2>();
 	initVariant(info, *v);
 	m_variants.emplace(getAllocator(), hash, v);

+ 4 - 3
src/anki/shader_compiler/ShaderProgramReflection.cpp

@@ -180,10 +180,11 @@ Error SpirvReflector::blockVariableReflection(
 					return Error::USER_DATA;
 				}
 
-				const Bool specConstantArray = memberType.array_size_literal[0];
-				if(specConstantArray)
+				const Bool notSpecConstantArraySize = memberType.array_size_literal[0];
+				if(notSpecConstantArraySize)
 				{
-					var.m_blockInfo.m_arraySize = I16(memberType.array[0]);
+					// Have a min to acount for unsized arrays of SSBOs
+					var.m_blockInfo.m_arraySize = max<I16>(I16(memberType.array[0]), 1);
 				}
 				else
 				{

+ 6 - 1
tests/shader_compiler/ShaderProgramCompiler.cpp

@@ -36,6 +36,11 @@ layout(set = 0, binding = 1) uniform texture2D u_tex2d;
 layout(set = 0, binding = 1) uniform texture3D u_tex3d;
 layout(set = 0, binding = 2) uniform sampler u_sampler;
 
+layout(set = 0, binding = 3) buffer ssbo
+{
+	Foo u_mats[];
+};
+
 #pragma anki start vert
 out gl_PerVertex
 {
@@ -44,7 +49,7 @@ out gl_PerVertex
 
 void main()
 {
-	gl_Position = u_ankiPerInstance[gl_InstanceID].m_ankiMvp * Vec4(gl_VertexID);
+	gl_Position = u_ankiPerInstance[gl_InstanceID].m_ankiMvp * u_mats[gl_InstanceID].m_mat * Vec4(gl_VertexID);
 }
 #pragma anki end