Skip to content

Commit

Permalink
sokol: Don't request vs/fs slot by string each command
Browse files Browse the repository at this point in the history
Also put compare code behind ifdef for testing
  • Loading branch information
IonAgorria committed Nov 1, 2024
1 parent 95fe86a commit c7631f3
Show file tree
Hide file tree
Showing 3 changed files with 126 additions and 131 deletions.
159 changes: 71 additions & 88 deletions Source/Render/sokol/SokolRenderPipeline.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -227,93 +227,6 @@ void cSokolRender::RegisterPipeline(SokolPipelineContext context) {
fprintf(stderr, "RegisterPipeline: invalid shader ID pipeline '%s'\n", desc.label);
return;
}
SOKOL_SHADER_ID shader_id = context.shader_funcs->get_id();
switch (shader_id) {
case SOKOL_SHADER_ID_mesh_color_tex1:
case SOKOL_SHADER_ID_mesh_color_tex2:
if (0 > context.shader_funcs->uniformblock_slot(SG_SHADERSTAGE_VS, "mesh_color_texture_vs_params")) {
fprintf(stderr, "RegisterPipeline: 'mesh_color_texture_vs_params' uniform slot not found at pipeline '%s'\n", desc.label);
xassert(0);
return;
} else if (context.shader_funcs->uniformblock_size(SG_SHADERSTAGE_VS, "mesh_color_texture_vs_params") != sizeof(mesh_color_texture_vs_params_t)) {
fprintf(stderr, "RegisterPipeline: 'mesh_color_texture_vs_params' uniform size doesnt match at pipeline '%s'\n", desc.label);
xassert(0);
return;
} else if (0 > context.shader_funcs->uniformblock_slot(SG_SHADERSTAGE_FS, "mesh_color_texture_fs_params")) {
fprintf(stderr, "RegisterPipeline: 'mesh_color_texture_fs_params' uniform slot not found at pipeline '%s'\n", desc.label);
xassert(0);
return;
} else if (context.shader_funcs->uniformblock_size(SG_SHADERSTAGE_FS, "mesh_color_texture_fs_params") != sizeof(mesh_color_texture_fs_params_t)) {
fprintf(stderr, "RegisterPipeline: 'mesh_color_texture_fs_params' uniform size doesnt match at pipeline '%s'\n", desc.label);
xassert(0);
return;
}
break;
case SOKOL_SHADER_ID_mesh_normal_tex1:
if (0 > context.shader_funcs->uniformblock_slot(SG_SHADERSTAGE_VS, "mesh_normal_texture_vs_params")) {
fprintf(stderr, "RegisterPipeline: 'mesh_normal_texture_vs_params' uniform slot not found at pipeline '%s'\n", desc.label);
xassert(0);
return;
} else if (context.shader_funcs->uniformblock_size(SG_SHADERSTAGE_VS, "mesh_normal_texture_vs_params") != sizeof(mesh_normal_texture_vs_params_t)) {
fprintf(stderr, "RegisterPipeline: 'mesh_normal_texture_vs_params' uniform size doesnt match at pipeline '%s'\n", desc.label);
xassert(0);
return;
}
break;
case SOKOL_SHADER_ID_shadow_tex1:
case SOKOL_SHADER_ID_shadow_normal_tex1:
if (0 > context.shader_funcs->uniformblock_slot(SG_SHADERSTAGE_VS, "shadow_texture_vs_params")) {
fprintf(stderr, "RegisterPipeline: 'shadow_texture_vs_params' uniform slot not found at pipeline '%s'\n", desc.label);
xassert(0);
return;
} else if (context.shader_funcs->uniformblock_size(SG_SHADERSTAGE_VS, "shadow_texture_vs_params") != sizeof(shadow_texture_vs_params_t)) {
fprintf(stderr, "RegisterPipeline: 'shadow_texture_vs_params' uniform size doesnt match at pipeline '%s'\n", desc.label);
xassert(0);
return;
} else if (0 > context.shader_funcs->uniformblock_slot(SG_SHADERSTAGE_FS, "shadow_texture_fs_params")) {
fprintf(stderr, "RegisterPipeline: 'shadow_texture_fs_params' uniform slot not found at pipeline '%s'\n", desc.label);
xassert(0);
return;
} else if (context.shader_funcs->uniformblock_size(SG_SHADERSTAGE_FS, "shadow_texture_fs_params") != sizeof(mesh_color_texture_fs_params_t)) {
fprintf(stderr, "RegisterPipeline: 'shadow_texture_fs_params' uniform size doesnt match at pipeline '%s'\n", desc.label);
xassert(0);
return;
}
break;
case SOKOL_SHADER_ID_mesh_tex1:
if (0 > context.shader_funcs->uniformblock_slot(SG_SHADERSTAGE_VS, "mesh_texture_vs_params")) {
fprintf(stderr, "RegisterPipeline: 'mesh_texture_vs_params' uniform slot not found at pipeline '%s'\n", desc.label);
xassert(0);
return;
} else if (context.shader_funcs->uniformblock_size(SG_SHADERSTAGE_VS, "mesh_texture_vs_params") != sizeof(mesh_texture_vs_params_t)) {
fprintf(stderr, "RegisterPipeline: 'mesh_texture_vs_params' uniform size doesnt match at pipeline '%s'\n", desc.label);
xassert(0);
return;
}
break;
case SOKOL_SHADER_ID_tile_map:
if (0 > context.shader_funcs->uniformblock_slot(SG_SHADERSTAGE_VS, "tile_map_vs_params")) {
fprintf(stderr, "RegisterPipeline: 'tile_map_vs_params' uniform slot not found at pipeline '%s'\n", desc.label);
xassert(0);
return;
} else if (context.shader_funcs->uniformblock_size(SG_SHADERSTAGE_VS, "tile_map_vs_params") != sizeof(tile_map_vs_params_t)) {
fprintf(stderr, "RegisterPipeline: 'tile_map_vs_params' uniform size doesnt match at pipeline '%s'\n", desc.label);
xassert(0);
return;
} else if (0 > context.shader_funcs->uniformblock_slot(SG_SHADERSTAGE_FS, "tile_map_fs_params")) {
fprintf(stderr, "RegisterPipeline: 'tile_map_fs_params' uniform slot not found at pipeline '%s'\n", desc.label);
xassert(0);
return;
} else if (context.shader_funcs->uniformblock_size(SG_SHADERSTAGE_FS, "tile_map_fs_params") != sizeof(tile_map_fs_params_t)) {
fprintf(stderr, "RegisterPipeline: 'tile_map_fs_params' uniform size doesnt match at pipeline '%s'\n", desc.label);
xassert(0);
return;
}
break;
default:
fprintf(stderr, "RegisterPipeline: Unknown shader id '%d' at pipeline '%s'\n", shader_id, desc.label);
return;
}

//Check for any missing slots
if (context.vertex_fmt & VERTEX_FMT_TEX1 &&
Expand All @@ -339,7 +252,8 @@ void cSokolRender::RegisterPipeline(SokolPipelineContext context) {
bind_vertex_fmt(context, VERTEX_FMT_NORMAL);

//Created, store on our pipelines
//printf("RegisterPipeline: '%s' at '%d'\n", desc.label, id);
SOKOL_SHADER_ID shader_id = context.shader_funcs->get_id();
//printf("RegisterPipeline: '%s' at '%d'\n", desc.label, shader_id);
SokolPipeline* pipeline = new SokolPipeline {
context,
sg_make_pipeline(desc),
Expand All @@ -354,6 +268,75 @@ void cSokolRender::RegisterPipeline(SokolPipelineContext context) {
xxassert(0, "RegisterPipeline: invalid pipeline vertex format " + std::string(desc.label));
return;
}
const char* vs_params_name = nullptr;
const char* fs_params_name = nullptr;
size_t vs_params_size = 0;
size_t fs_params_size = 0;
switch (shader_id) {
case SOKOL_SHADER_ID_mesh_color_tex1:
case SOKOL_SHADER_ID_mesh_color_tex2:
vs_params_name = "mesh_color_texture_vs_params";
fs_params_name = "mesh_color_texture_fs_params";
vs_params_size = sizeof(mesh_color_texture_vs_params_t);
fs_params_size = sizeof(mesh_color_texture_fs_params_t);
break;
case SOKOL_SHADER_ID_mesh_normal_tex1:
vs_params_name = "mesh_normal_texture_vs_params";
fs_params_name = "mesh_normal_texture_fs_params";
vs_params_size = sizeof(mesh_normal_texture_vs_params_t);
fs_params_size = sizeof(mesh_normal_texture_fs_params_t);
break;
case SOKOL_SHADER_ID_shadow_tex1:
case SOKOL_SHADER_ID_shadow_normal_tex1:
vs_params_name = "shadow_texture_vs_params";
fs_params_name = "shadow_texture_fs_params";
vs_params_size = sizeof(shadow_texture_vs_params_t);
fs_params_size = sizeof(shadow_texture_fs_params_t);
break;
case SOKOL_SHADER_ID_mesh_tex1:
vs_params_name = "mesh_texture_vs_params";
vs_params_size = sizeof(mesh_texture_vs_params_t);
break;
case SOKOL_SHADER_ID_tile_map:
vs_params_name = "tile_map_vs_params";
fs_params_name = "tile_map_fs_params";
vs_params_size = sizeof(tile_map_vs_params_t);
fs_params_size = sizeof(tile_map_fs_params_t);
break;
case SOKOL_SHADER_ID_NONE:
default:
fprintf(stderr, "RegisterPipeline: Unknown shader id '%d' at pipeline '%s'\n", shader_id, desc.label);
break;
}

if (vs_params_name) {
pipeline->vs_params_slot = context.shader_funcs->uniformblock_slot(SG_SHADERSTAGE_VS, vs_params_name);
if (0 > pipeline->vs_params_slot) {
fprintf(stderr, "RegisterPipeline: '%s' vs uniform slot not found at pipeline '%s'\n", vs_params_name,
desc.label);
xassert(0);
return;
} else if (context.shader_funcs->uniformblock_size(SG_SHADERSTAGE_VS, vs_params_name) != vs_params_size) {
fprintf(stderr, "RegisterPipeline: '%s' vs uniform size doesnt match at pipeline '%s'\n",
vs_params_name, desc.label);
xassert(0);
return;
}
}
if (fs_params_name) {
pipeline->fs_params_slot = context.shader_funcs->uniformblock_slot(SG_SHADERSTAGE_FS, fs_params_name);
if (0 > pipeline->fs_params_slot) {
fprintf(stderr, "RegisterPipeline: '%s' fs uniform slot not found at pipeline '%s'\n",
fs_params_name, desc.label);
xassert(0);
return;
} else if (context.shader_funcs->uniformblock_size(SG_SHADERSTAGE_FS, fs_params_name) != fs_params_size) {
fprintf(stderr, "RegisterPipeline: '%s' fs uniform size doesnt match at pipeline '%s'\n",
fs_params_name, desc.label);
xassert(0);
return;
}
}
for (int i = 0; i < PERIMETER_SOKOL_TEXTURES; ++i) {
std::string name = "un_tex" + std::to_string(i);
pipeline->shader_fs_texture_slot[i] = context.shader_funcs->image_slot(SG_SHADERSTAGE_FS, name.c_str());
Expand Down
7 changes: 5 additions & 2 deletions Source/Render/sokol/SokolRenderPipeline.h
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,11 @@ struct SokolPipeline {
//Mapping of texture slots in fragment shader
int shader_fs_texture_slot[PERIMETER_SOKOL_TEXTURES] = {};
//Sampler slot
int shader_fs_sampler_slot = 0;
int shader_fs_shadow_sampler_slot = 0;
int shader_fs_sampler_slot = -1;
int shader_fs_shadow_sampler_slot = -1;
//Uniform params slots
int vs_params_slot = -1;
int fs_params_slot = -1;

SokolPipeline() = default;
~SokolPipeline();
Expand Down
91 changes: 50 additions & 41 deletions Source/Render/sokol/SokolRenderState.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -133,18 +133,29 @@ void cSokolRender::DoSokolRendering() {
ProcessRenderPass(swapchain_pass, swapchainCommands);
}

#define CMDS_COMPARE_PREV_COMMAND
void cSokolRender::ProcessRenderPass(sg_pass& render_pass, const std::vector<SokolCommand*>& pass_commands) {
std::string pass_group_label = "pass_";
pass_group_label += render_pass.label;
sg_push_debug_group(pass_group_label.c_str());
sg_begin_pass(&render_pass);
#ifdef PERIMETER_DEBUG
//printf("@@@ %s @@@\n",pass_group_label.c_str());
#endif

//Iterate each command
#ifdef CMDS_COMPARE_PREV_COMMAND
const SokolCommand* prev_command = nullptr;
#ifdef DEBUG_TEST_SAME
int same_i = 0;
#endif
#endif
const SokolCommand* command = nullptr;
bool open_debug_group = false;
for (size_t passcmd_i = 0; passcmd_i < pass_commands.size(); ++passcmd_i) {
#ifdef CMDS_COMPARE_PREV_COMMAND
prev_command = command;
#endif
command = pass_commands[passcmd_i];

//Make/Close debug group
Expand Down Expand Up @@ -191,8 +202,8 @@ void cSokolRender::ProcessRenderPass(sg_pass& render_pass, const std::vector<Sok
xxassert(0, "cSokolRender::ProcessRenderPass missing pipeline");
continue;
}
shader_funcs* shader_funcs = pipeline->context.shader_funcs;

#ifdef CMDS_COMPARE_PREV_COMMAND
bool pipeline_diff = !prev_command || prev_command->pipeline != pipeline;
bool vs_params_diff = !prev_command || pipeline_diff
|| prev_command->vs_params_len != command->vs_params_len
Expand All @@ -209,6 +220,23 @@ void cSokolRender::ProcessRenderPass(sg_pass& render_pass, const std::vector<Sok
command->fs_params_len
));

#ifdef DEBUG_TEST_SAME
if (prev_command && prev_command->vertex_buffer && command->vertex_buffer
&& prev_command->pipeline == command->pipeline
&& prev_command->base_elements == command->base_elements
&& prev_command->indices == command->indices
&& !fs_params_diff
&& prev_command->vertex_buffer->res.id == command->vertex_buffer->res.id) {
same_i++;
continue;
} else if (0 < same_i) {
if (2< same_i) {
printf("!! Up %d\n", same_i);
}
same_i = 0;
}
#endif

if (!prev_command
|| vs_params_diff || fs_params_diff
|| prev_command->vertex_buffer != command->vertex_buffer
Expand All @@ -219,7 +247,9 @@ void cSokolRender::ProcessRenderPass(sg_pass& render_pass, const std::vector<Sok
command->sokol_images,
sizeof(SokolResourceImage*) * PERIMETER_SOKOL_TEXTURES
))
) {
)
#endif
{
#if defined(PERIMETER_DEBUG) && 0
printf("id: 0x%X fmt: 0x%X vtx: %d idx: %d\n",
command->pipeline_id, pipeline->vertex_fmt,
Expand Down Expand Up @@ -300,47 +330,27 @@ void cSokolRender::ProcessRenderPass(sg_pass& render_pass, const std::vector<Sok
sg_apply_bindings(&bindings);

//Apply VS uniforms
SOKOL_SHADER_ID shader_id = shader_funcs->get_id();
const char* vs_params_name = nullptr;
const char* fs_params_name = nullptr;
switch (shader_id) {
case SOKOL_SHADER_ID_mesh_color_tex1:
case SOKOL_SHADER_ID_mesh_color_tex2:
vs_params_name = "mesh_color_texture_vs_params";
fs_params_name = "mesh_color_texture_fs_params";
break;
case SOKOL_SHADER_ID_mesh_normal_tex1:
vs_params_name = "mesh_normal_texture_vs_params";
fs_params_name = "mesh_normal_texture_fs_params";
break;
case SOKOL_SHADER_ID_shadow_tex1:
case SOKOL_SHADER_ID_shadow_normal_tex1:
vs_params_name = "shadow_texture_vs_params";
fs_params_name = "shadow_texture_fs_params";
break;
case SOKOL_SHADER_ID_mesh_tex1:
vs_params_name = "mesh_texture_vs_params";
break;
case SOKOL_SHADER_ID_tile_map:
vs_params_name = "tile_map_vs_params";
fs_params_name = "tile_map_fs_params";
break;
default:
case SOKOL_SHADER_ID_NONE:
xassert(0);
}

if (vs_params_name && vs_params_diff) {
int vs_params_slot = shader_funcs->uniformblock_slot(SG_SHADERSTAGE_VS, vs_params_name);
xxassert(0 <= vs_params_slot, "No vs slot found");
#ifdef CMDS_COMPARE_PREV_COMMAND
if (vs_params_diff)
#endif
if (0 <= pipeline->vs_params_slot) {
xxassert(command->vs_params, "No vs parameters set in command");
sg_apply_uniforms(SG_SHADERSTAGE_VS, vs_params_slot, sg_range { command->vs_params, command->vs_params_len });
sg_apply_uniforms(
SG_SHADERSTAGE_VS,
pipeline->vs_params_slot,
sg_range { command->vs_params, command->vs_params_len }
);
}
if (fs_params_name && fs_params_diff) {
int fs_params_slot = shader_funcs->uniformblock_slot(SG_SHADERSTAGE_FS, fs_params_name);
xxassert(0 <= fs_params_slot, "No fs slot found");
#ifdef CMDS_COMPARE_PREV_COMMAND
if (fs_params_diff)
#endif
if (0 <= pipeline->fs_params_slot) {
xxassert(command->fs_params, "No fs parameters set in command");
sg_apply_uniforms(SG_SHADERSTAGE_FS, fs_params_slot, sg_range { command->fs_params, command->fs_params_len });
sg_apply_uniforms(
SG_SHADERSTAGE_FS,
pipeline->fs_params_slot,
sg_range { command->fs_params, command->fs_params_len }
);
}
}

Expand Down Expand Up @@ -834,7 +844,6 @@ void cSokolRender::CreateCommand(VertexBuffer* vb, size_t vertices, IndexBuffer*
case SOKOL_SHADER_ID_shadow_normal_tex1: {
auto vs_params = reinterpret_cast<shadow_texture_vs_params_t*>(cmd->vs_params);
auto fs_params = reinterpret_cast<shadow_texture_fs_params_t*>(cmd->fs_params);
vs_params->un_mvp = isOrthographicProjSet ? orthoVP : (activeCommandW * activeCommandVP);
shader_set_common_params(vs_params, fs_params);
break;
}
Expand Down

0 comments on commit c7631f3

Please sign in to comment.