Fixed bugs in lazy shader compilation.

This commit is contained in:
zy4n
2025-03-03 20:45:30 +01:00
parent 925125e99b
commit fde6a2fd7b
26 changed files with 234 additions and 321 deletions

View File

@@ -153,10 +153,10 @@ bool zgl::shader_program_compiler::parse_features_declaration(
) {
switch (metadata.geometry)
{
case shader_program::geometries::mesh:
case shader_program::geometry::types::mesh:
parse_feature_tokens(tokens, mesh_feature_lookup, metadata.features.mesh);
break;
case shader_program::geometries::point_cloud:
case shader_program::geometry::types::point_cloud:
parse_feature_tokens(tokens, point_cloud_feature_lookup, metadata.features.point_cloud);
break;
default:
@@ -172,11 +172,11 @@ bool zgl::shader_program_compiler::parse_feature_toggles_declaration(
) {
switch (metadata.geometry)
{
case shader_program::geometries::mesh:
parse_feature_tokens(tokens, mesh_feature_lookup, metadata.feature_toggles.mesh);
case shader_program::geometry::types::mesh:
parse_feature_tokens(tokens, mesh_feature_lookup, metadata.static_enable.mesh);
break;
case shader_program::geometries::point_cloud:
parse_feature_tokens(tokens, point_cloud_feature_lookup, metadata.feature_toggles.point_cloud);
case shader_program::geometry::types::point_cloud:
parse_feature_tokens(tokens, point_cloud_feature_lookup, metadata.static_enable.point_cloud);
break;
default:
ztu::logger::warn("Internal error: Unknown geometry index %.", static_cast<int>(metadata.geometry));
@@ -236,27 +236,28 @@ auto zgl::shader_program_compiler::find_compatible_shader_source(
&std::pair<shader_program::metadata_type, dynamic_shader_source_store::id_type>::first
);
if (lower_it == shader_lookup.end()) {
return std::nullopt;
}
const auto required_features = requirements.features.generic(requirements.geometry);
auto generic_requirement_feature_set = requirements.generic_feature_set();
const auto& required_features = generic_requirement_feature_set.features;
while (
lower_it != shader_lookup.end() and
lower_it->first.geometry == requirements.geometry and
lower_it->first.stage == requirements.stage
) {
const auto& data = lower_it->first;
const auto& [ features, feature_toggles ] = data.generic();
const auto& [ features, static_enable, dynamic_enable ] = data.generic_feature_set();
const auto missing_features = required_features & ~features;
const auto extra_features = ~required_features & features;
const auto untoggleable_extra_features = extra_features & ~feature_toggles;
const auto unwanted_features = ~required_features & features;
const auto fixed_unwanted_features = unwanted_features & ~static_enable & ~dynamic_enable;
if (missing_features == 0 and untoggleable_extra_features == 0)
if (missing_features == 0 and fixed_unwanted_features == 0)
{
const auto to_be_toggled = required_features & feature_toggles;
requirements.feature_toggles.from_generic(requirements.geometry, to_be_toggled);
// Tell caller which features need to be toggled before compilation
// and which features can still be dynamically enabled after compilation.
generic_requirement_feature_set.static_enable = required_features & static_enable;
generic_requirement_feature_set.dynamic_enable = dynamic_enable;
requirements.from_generic_feature_set(generic_requirement_feature_set);
return lower_it->second;
}
@@ -325,11 +326,11 @@ void zgl::shader_program_compiler::compile_shaders(
shader_strings.clear();
switch (requirements.geometry) {
case shader_program::geometries::mesh:
add_required_feature_defines(requirements.feature_toggles.mesh, mesh_feature_defines, shader_strings);
case shader_program::geometry::types::mesh:
add_required_feature_defines(requirements.feature_set.mesh.static_enable, mesh_feature_defines, shader_strings);
break;
case shader_program::geometries::point_cloud:
add_required_feature_defines(requirements.feature_toggles.point_cloud, point_cloud_feature_defines, shader_strings);
case shader_program::geometry::types::point_cloud:
add_required_feature_defines(requirements.feature_set.point_cloud.static_enable, point_cloud_feature_defines, shader_strings);
break;
default:
std::unreachable();
@@ -339,7 +340,7 @@ void zgl::shader_program_compiler::compile_shaders(
shader_id = glCreateShader(static_cast<GLenum>(requirements.stage));
glShaderSource(shader_id, shader_strings.size(), shader_strings.data(), nullptr);
glShaderSource(shader_id, static_cast<GLsizei>(shader_strings.size()), shader_strings.data(), nullptr);
glCompileShader(shader_id);
GLint success;
@@ -399,7 +400,7 @@ void zgl::shader_program_compiler::register_shader_sources(
const auto it = std::ranges::upper_bound(
shader_lookup,
*metadata,
shader_program::metadata_type::feature_count_less{},
std::less{},
&std::pair<shader_program::metadata_type, dynamic_shader_source_store::id_type>::first
);

View File

@@ -65,7 +65,7 @@ std::optional<mesh_batch_renderer::id_type> mesh_batch_renderer::add(
ztu::logger::debug("vertex_comps: %", std::bitset<32>{ static_cast<unsigned long long>(static_cast<int>(vertex_comps)) });
ztu::logger::debug("material_comps: %", std::bitset<32>{ static_cast<unsigned long long>(static_cast<int>(material_comps)) });
ztu::logger::debug("lit reqs: %", std::bitset<32>{ static_cast<unsigned long long>(static_cast<int>(shader_program::capabilities::mesh::lit.uniforms)) });
ztu::logger::debug("lit reqs: %", std::bitset<32>{ static_cast<unsigned long long>(static_cast<int>(shader_program::features::mesh::lit.uniforms)) });
for (std::size_t i{}; i != requirements::mesh::all.size(); ++i)

View File

@@ -19,7 +19,7 @@ void mesh_lookup::add(
std::optional<zgl::shader_program_handle> mesh_lookup::find(
requirements::mesh::flags requirements
) const {
auto capability = shader_program::capabilities::mesh::type{};
auto capability = shader_program::features::mesh::type{};
auto index = std::size_t{};
@@ -30,7 +30,7 @@ std::optional<zgl::shader_program_handle> mesh_lookup::find(
if (requirement_flags & 1)
{
const auto shader_requirements_index = requirements::mesh::all[index].shader_program_requirement_index;
const auto& [ attributes, uniforms ] = shader_program::capabilities::mesh::all[shader_requirements_index];
const auto& [ attributes, uniforms ] = shader_program::features::mesh::all[shader_requirements_index];
capability.attributes |= attributes;
capability.uniforms |= uniforms;
}

View File

@@ -17,7 +17,7 @@ void point_cloud_lookup::add(
std::optional<zgl::shader_program_handle> point_cloud_lookup::find(
requirements::point_cloud::flags requirements
) const {
auto capability = shader_program::capabilities::point_cloud::type{};
auto capability = shader_program::features::point_cloud::type{};
auto index = std::size_t{};
@@ -28,7 +28,7 @@ std::optional<zgl::shader_program_handle> point_cloud_lookup::find(
if (requirement_flags & 1)
{
const auto shader_requirements_index = requirements::point_cloud::all[index].shader_program_requirement_index;
const auto& [ attributes, uniforms ] = shader_program::capabilities::point_cloud::all[shader_requirements_index];
const auto& [ attributes, uniforms ] = shader_program::features::point_cloud::all[shader_requirements_index];
capability.attributes |= attributes;
capability.uniforms |= uniforms;
}