* \return number of instructions removed
*/
static GLuint
-remove_instructions(struct gl_program *prog, const GLboolean *removeFlags)
+remove_instructions(struct gl_program *prog, const GLboolean *removeFlags,
+ void *mem_ctx)
{
GLint i, removeEnd = 0, removeCount = 0;
GLuint totalRemoved = 0;
/* go backward */
- for (i = prog->NumInstructions - 1; i >= 0; i--) {
+ for (i = prog->arb.NumInstructions - 1; i >= 0; i--) {
if (removeFlags[i]) {
totalRemoved++;
if (removeCount == 0) {
*/
if (removeCount > 0) {
GLint removeStart = removeEnd - removeCount + 1;
- _mesa_delete_instructions(prog, removeStart, removeCount);
+ _mesa_delete_instructions(prog, removeStart, removeCount, mem_ctx);
removeStart = removeCount = 0; /* reset removal info */
}
}
/* Finish removing if the first instruction was to be removed. */
if (removeCount > 0) {
GLint removeStart = removeEnd - removeCount + 1;
- _mesa_delete_instructions(prog, removeStart, removeCount);
+ _mesa_delete_instructions(prog, removeStart, removeCount, mem_ctx);
}
return totalRemoved;
}
{
GLuint i;
- for (i = 0; i < prog->NumInstructions; i++) {
- struct prog_instruction *inst = prog->Instructions + i;
+ for (i = 0; i < prog->arb.NumInstructions; i++) {
+ struct prog_instruction *inst = prog->arb.Instructions + i;
const GLuint numSrc = _mesa_num_inst_src_regs(inst->Opcode);
GLuint j;
for (j = 0; j < numSrc; j++) {
* write to such registers. Be careful with condition code setters.
*/
static GLboolean
-_mesa_remove_dead_code_global(struct gl_program *prog)
+_mesa_remove_dead_code_global(struct gl_program *prog, void *mem_ctx)
{
GLboolean tempRead[REG_ALLOCATE_MAX_PROGRAM_TEMPS][4];
GLboolean *removeInst; /* per-instruction removal flag */
}
removeInst =
- calloc(prog->NumInstructions, sizeof(GLboolean));
+ calloc(prog->arb.NumInstructions, sizeof(GLboolean));
/* Determine which temps are read and written */
- for (i = 0; i < prog->NumInstructions; i++) {
- const struct prog_instruction *inst = prog->Instructions + i;
+ for (i = 0; i < prog->arb.NumInstructions; i++) {
+ const struct prog_instruction *inst = prog->arb.Instructions + i;
const GLuint numSrc = _mesa_num_inst_src_regs(inst->Opcode);
GLuint j;
}
/* find instructions that write to dead registers, flag for removal */
- for (i = 0; i < prog->NumInstructions; i++) {
- struct prog_instruction *inst = prog->Instructions + i;
+ for (i = 0; i < prog->arb.NumInstructions; i++) {
+ struct prog_instruction *inst = prog->arb.Instructions + i;
const GLuint numDst = _mesa_num_inst_dst_regs(inst->Opcode);
if (numDst != 0 && inst->DstReg.File == PROGRAM_TEMPORARY) {
}
/* now remove the instructions which aren't needed */
- rem = remove_instructions(prog, removeInst);
+ rem = remove_instructions(prog, removeInst, mem_ctx);
if (dbg) {
printf("Optimize: End dead code removal.\n");
{
GLuint i;
- for (i = start; i < prog->NumInstructions; i++) {
- const struct prog_instruction *inst = prog->Instructions + i;
+ for (i = start; i < prog->arb.NumInstructions; i++) {
+ const struct prog_instruction *inst = prog->arb.Instructions + i;
switch (inst->Opcode) {
case OPCODE_BGNLOOP:
case OPCODE_BGNSUB:
* FOO tmpY, arg0, arg1;
*/
- for (i = 0; i + 1 < prog->NumInstructions; i++) {
- const struct prog_instruction *mov = prog->Instructions + i;
+ for (i = 0; i + 1 < prog->arb.NumInstructions; i++) {
+ const struct prog_instruction *mov = prog->arb.Instructions + i;
GLuint dst_mask, src_mask;
if (can_upward_mov_be_modifed(mov) == GL_FALSE)
continue;
* rewritten or we get into some flow-control, eliminating the use of
* this MOV.
*/
- for (j = i + 1; j < prog->NumInstructions; j++) {
- struct prog_instruction *inst2 = prog->Instructions + j;
+ for (j = i + 1; j < prog->arb.NumInstructions; j++) {
+ struct prog_instruction *inst2 = prog->arb.Instructions + j;
GLuint arg;
if (_mesa_is_flow_control_opcode(inst2->Opcode))
* with a proper control flow graph
*/
static GLboolean
-_mesa_remove_dead_code_local(struct gl_program *prog)
+_mesa_remove_dead_code_local(struct gl_program *prog, void *mem_ctx)
{
GLboolean *removeInst;
GLuint i, arg, rem = 0;
removeInst =
- calloc(prog->NumInstructions, sizeof(GLboolean));
+ calloc(prog->arb.NumInstructions, sizeof(GLboolean));
- for (i = 0; i < prog->NumInstructions; i++) {
- const struct prog_instruction *inst = prog->Instructions + i;
+ for (i = 0; i < prog->arb.NumInstructions; i++) {
+ const struct prog_instruction *inst = prog->arb.Instructions + i;
const GLuint index = inst->DstReg.Index;
const GLuint mask = inst->DstReg.WriteMask;
enum inst_use use;
removeInst[i] = GL_TRUE;
}
- rem = remove_instructions(prog, removeInst);
+ rem = remove_instructions(prog, removeInst, mem_ctx);
done:
free(removeInst);
* Try to remove extraneous MOV instructions from the given program.
*/
static GLboolean
-_mesa_remove_extra_moves(struct gl_program *prog)
+_mesa_remove_extra_moves(struct gl_program *prog, void *mem_ctx)
{
GLboolean *removeInst; /* per-instruction removal flag */
GLuint i, rem = 0, nesting = 0;
}
removeInst =
- calloc(prog->NumInstructions, sizeof(GLboolean));
+ calloc(prog->arb.NumInstructions, sizeof(GLboolean));
/*
* Look for sequences such as this:
* FOO tmpY, arg0, arg1;
*/
- for (i = 0; i < prog->NumInstructions; i++) {
- const struct prog_instruction *mov = prog->Instructions + i;
+ for (i = 0; i < prog->arb.NumInstructions; i++) {
+ const struct prog_instruction *mov = prog->arb.Instructions + i;
switch (mov->Opcode) {
case OPCODE_BGNLOOP:
prevI = i - 1;
while (prevI > 0 && removeInst[prevI])
prevI--;
- prevInst = prog->Instructions + prevI;
+ prevInst = prog->arb.Instructions + prevI;
if (prevInst->DstReg.File == PROGRAM_TEMPORARY &&
prevInst->DstReg.Index == id &&
}
/* now remove the instructions which aren't needed */
- rem = remove_instructions(prog, removeInst);
+ rem = remove_instructions(prog, removeInst, mem_ctx);
free(removeInst);
}
/* build intermediate arrays */
- if (!_mesa_find_temp_intervals(prog->Instructions, prog->NumInstructions,
+ if (!_mesa_find_temp_intervals(prog->arb.Instructions,
+ prog->arb.NumInstructions,
intBegin, intEnd))
return GL_FALSE;
*/
replace_regs(prog, PROGRAM_TEMPORARY, registerMap);
- prog->NumTemporaries = maxTemp + 1;
+ prog->arb.NumTemporaries = maxTemp + 1;
}
if (dbg) {
#if 0
static void
print_it(struct gl_context *ctx, struct gl_program *program, const char *txt) {
- fprintf(stderr, "%s (%u inst):\n", txt, program->NumInstructions);
+ fprintf(stderr, "%s (%u inst):\n", txt, program->arb.NumInstructions);
_mesa_print_program(program);
_mesa_print_program_parameters(ctx, program);
fprintf(stderr, "\n\n");
outputWrites[i] = 0;
}
- for (i = 0; i < program->NumInstructions; i++) {
- struct prog_instruction *inst = program->Instructions + i;
+ for (i = 0; i < program->arb.NumInstructions; i++) {
+ struct prog_instruction *inst = program->arb.Instructions + i;
GLuint prevWriteMask;
/* Give up if we encounter relative addressing or flow control. */
* instructions, temp regs, etc.
*/
void
-_mesa_optimize_program(struct gl_context *ctx, struct gl_program *program)
+_mesa_optimize_program(struct gl_context *ctx, struct gl_program *program,
+ void *mem_ctx)
{
GLboolean any_change;
do {
any_change = GL_FALSE;
_mesa_remove_extra_move_use(program);
- if (_mesa_remove_dead_code_global(program))
+ if (_mesa_remove_dead_code_global(program, mem_ctx))
any_change = GL_TRUE;
- if (_mesa_remove_extra_moves(program))
+ if (_mesa_remove_extra_moves(program, mem_ctx))
any_change = GL_TRUE;
- if (_mesa_remove_dead_code_local(program))
+ if (_mesa_remove_dead_code_local(program, mem_ctx))
any_change = GL_TRUE;
any_change = _mesa_constant_fold(program) || any_change;