From ddd9729bc37f4b1098ef940da6e723743db3ded8 Mon Sep 17 00:00:00 2001 From: Brian Paul Date: Tue, 22 Dec 2009 14:21:07 -0700 Subject: mesa: adjust OPCODE_IF/ELSE BranchTarget fields to point to ELSE/ENDIF instr. This is a little more logical. Suggested in bug report 25654. --- src/mesa/shader/prog_execute.c | 10 ++++++++-- src/mesa/shader/slang/slang_emit.c | 22 +++++++++++++++++----- 2 files changed, 25 insertions(+), 7 deletions(-) (limited to 'src/mesa/shader') diff --git a/src/mesa/shader/prog_execute.c b/src/mesa/shader/prog_execute.c index 56d174c6ce5..7f034520cd4 100644 --- a/src/mesa/shader/prog_execute.c +++ b/src/mesa/shader/prog_execute.c @@ -910,6 +910,10 @@ _mesa_execute_program(GLcontext * ctx, case OPCODE_IF: { GLboolean cond; + ASSERT(program->Instructions[inst->BranchTarget].Opcode + == OPCODE_ELSE || + program->Instructions[inst->BranchTarget].Opcode + == OPCODE_ENDIF); /* eval condition */ if (inst->SrcReg[0].File != PROGRAM_UNDEFINED) { GLfloat a[4]; @@ -929,14 +933,16 @@ _mesa_execute_program(GLcontext * ctx, else { /* go to the instruction after ELSE or ENDIF */ assert(inst->BranchTarget >= 0); - pc = inst->BranchTarget - 1; + pc = inst->BranchTarget; } } break; case OPCODE_ELSE: /* goto ENDIF */ + ASSERT(program->Instructions[inst->BranchTarget].Opcode + == OPCODE_ENDIF); assert(inst->BranchTarget >= 0); - pc = inst->BranchTarget - 1; + pc = inst->BranchTarget; break; case OPCODE_ENDIF: /* nothing */ diff --git a/src/mesa/shader/slang/slang_emit.c b/src/mesa/shader/slang/slang_emit.c index e769d0d3ad4..ce3f6ab7ea2 100644 --- a/src/mesa/shader/slang/slang_emit.c +++ b/src/mesa/shader/slang/slang_emit.c @@ -1728,6 +1728,7 @@ emit_if(slang_emit_info *emitInfo, slang_ir_node *n) if (!inst) { return NULL; } + prog->Instructions[ifInstLoc].BranchTarget = prog->NumInstructions - 1; } else { /* jump to endif instruction */ @@ -1737,8 +1738,8 @@ emit_if(slang_emit_info *emitInfo, slang_ir_node *n) } inst_comment(inst, "else"); inst->DstReg.CondMask = COND_TR; /* always branch */ + prog->Instructions[ifInstLoc].BranchTarget = prog->NumInstructions; } - prog->Instructions[ifInstLoc].BranchTarget = prog->NumInstructions; emit(emitInfo, n->Children[2]); } else { @@ -1753,8 +1754,14 @@ emit_if(slang_emit_info *emitInfo, slang_ir_node *n) } } - if (n->Children[2]) { - prog->Instructions[elseInstLoc].BranchTarget = prog->NumInstructions; + if (elseInstLoc) { + /* point ELSE instruction BranchTarget at ENDIF */ + if (emitInfo->EmitHighLevelInstructions) { + prog->Instructions[elseInstLoc].BranchTarget = prog->NumInstructions - 1; + } + else { + prog->Instructions[elseInstLoc].BranchTarget = prog->NumInstructions; + } } return NULL; } @@ -1824,7 +1831,12 @@ emit_loop(slang_emit_info *emitInfo, slang_ir_node *n) assert(inst->Opcode == OPCODE_BRK || inst->Opcode == OPCODE_BRA); /* go to instruction at end of loop */ - inst->BranchTarget = endInstLoc; + if (emitInfo->EmitHighLevelInstructions) { + inst->BranchTarget = endInstLoc; + } + else { + inst->BranchTarget = endInstLoc + 1; + } } else { assert(ir->Opcode == IR_CONT || @@ -1942,7 +1954,7 @@ emit_cont_break_if_true(slang_emit_info *emitInfo, slang_ir_node *n) } emitInfo->prog->Instructions[ifInstLoc].BranchTarget - = emitInfo->prog->NumInstructions; + = emitInfo->prog->NumInstructions - 1; return inst; } } -- cgit v1.2.3