pds_upload_out);
}
+/* pbe_cs_words must be an array of length emit_count with
+ * ROGUE_NUM_PBESTATE_STATE_WORDS entries
+ */
static VkResult pvr_sub_cmd_gfx_per_job_fragment_programs_create_and_upload(
struct pvr_cmd_buffer *const cmd_buffer,
- const uint32_t pbe_cs_words[static const ROGUE_NUM_PBESTATE_STATE_WORDS],
+ const uint32_t emit_count,
+ const uint32_t *pbe_cs_words,
struct pvr_pds_upload *const pds_upload_out)
{
struct pvr_pds_event_program pixel_event_program = {
uint32_t usc_temp_count;
VkResult result;
- pvr_uscgen_per_job_eot(pbe_cs_words[0],
- pbe_cs_words[1],
+ assert(emit_count > 0);
+
+ pvr_uscgen_per_job_eot(emit_count,
+ pbe_cs_words,
&usc_temp_count,
&eot_program_bin);
emit_state.pbe_reg_words,
sizeof(emit_state.pbe_reg_words));
- /* FIXME: The fragment program only supports a single surface at present. */
- assert(emit_state.emit_count == 1);
result = pvr_sub_cmd_gfx_per_job_fragment_programs_create_and_upload(
cmd_buffer,
+ emit_state.emit_count,
emit_state.pbe_cs_words[0],
&pds_pixel_event_program);
if (result != VK_SUCCESS)
#include <stdbool.h>
-void pvr_uscgen_per_job_eot(uint32_t state0,
- uint32_t state1,
+void pvr_uscgen_per_job_eot(uint32_t emit_count,
+ const uint32_t *emit_state, /* Expects emit_count *
+ ROGUE_NUM_PBESTATE_STATE_WORDS
+ entries */
unsigned *temps_used,
struct util_dynarray *binary)
{
rogue_builder b;
rogue_shader *shader = rogue_shader_create(NULL, MESA_SHADER_NONE);
+ rogue_reg *state_word_0 = rogue_temp_reg(shader, 0);
+ rogue_reg *state_word_1 = rogue_temp_reg(shader, 1);
+ rogue_backend_instr *emitpix = NULL;
+
rogue_set_shader_name(shader, "per-job EOT");
rogue_builder_init(&b, shader);
rogue_push_block(&b);
- rogue_reg *state_word_0 = rogue_ssa_reg(shader, 0);
- rogue_reg *state_word_1 = rogue_ssa_reg(shader, 1);
+ for (unsigned u = 0; u < emit_count; u++) {
+ if (u > 0)
+ rogue_WOP(&b);
- rogue_MOV(&b, rogue_ref_reg(state_word_0), rogue_ref_imm(state0));
- rogue_MOV(&b, rogue_ref_reg(state_word_1), rogue_ref_imm(state1));
+ rogue_MOV(&b, rogue_ref_reg(state_word_0), rogue_ref_imm(emit_state[0]));
+ rogue_MOV(&b, rogue_ref_reg(state_word_1), rogue_ref_imm(emit_state[1]));
- rogue_backend_instr *emitpix = rogue_EMITPIX(&b,
- rogue_ref_reg(state_word_0),
- rogue_ref_reg(state_word_1));
- rogue_set_backend_op_mod(emitpix, ROGUE_BACKEND_OP_MOD_FREEP);
+ emitpix = rogue_EMITPIX(&b,
+ rogue_ref_reg(state_word_0),
+ rogue_ref_reg(state_word_1));
- rogue_END(&b);
+ emit_state += 2;
+ }
+
+ assert(emitpix);
+
+ rogue_set_backend_op_mod(emitpix, ROGUE_BACKEND_OP_MOD_FREEP);
+ emitpix->instr.end = true;
rogue_shader_passes(shader);
rogue_encode_shader(NULL, shader, binary);