Mesa (master): r300/compiler: Don' t unroll loops that conditionally increment the counter

Tom Stellard tstellar at kemper.freedesktop.org
Sat Sep 17 00:44:47 UTC 2011


Module: Mesa
Branch: master
Commit: 96620d2275894d1e021d403c0e40007c61269563
URL:    http://cgit.freedesktop.org/mesa/mesa/commit/?id=96620d2275894d1e021d403c0e40007c61269563

Author: Tom Stellard <tstellar at gmail.com>
Date:   Thu Sep 15 18:24:55 2011 -0700

r300/compiler: Don't unroll loops that conditionally increment the counter

---

 .../drivers/r300/compiler/radeon_emulate_loops.c   |   16 ++++++++++++++--
 1 files changed, 14 insertions(+), 2 deletions(-)

diff --git a/src/gallium/drivers/r300/compiler/radeon_emulate_loops.c b/src/gallium/drivers/r300/compiler/radeon_emulate_loops.c
index 205eecd..8c46db0 100644
--- a/src/gallium/drivers/r300/compiler/radeon_emulate_loops.c
+++ b/src/gallium/drivers/r300/compiler/radeon_emulate_loops.c
@@ -51,6 +51,7 @@ struct count_inst {
 	rc_swizzle Swz;
 	float Amount;
 	int Unknown;
+	unsigned BranchDepth;
 };
 
 static float get_constant_value(struct radeon_compiler * c,
@@ -141,6 +142,14 @@ static void get_incr_amount(void * data, struct rc_instruction * inst,
 	   (1 << GET_SWZ(count_inst->Swz,0) != mask)){
 		return;
 	}
+
+	/* XXX: Give up if the counter is modified within an IF block.  We
+	 * could handle this case with better analysis. */
+	if (count_inst->BranchDepth > 0) {
+		count_inst->Unknown = 1;
+		return;
+	}
+
 	/* Find the index of the counter register. */
 	opcode = rc_get_opcode_info(inst->U.I.Opcode);
 	if(opcode->NumSrcRegs != 2){
@@ -236,6 +245,7 @@ static int try_unroll_loop(struct radeon_compiler * c, struct loop_info * loop)
 	count_inst.Swz = counter->Swizzle;
 	count_inst.Amount = 0.0f;
 	count_inst.Unknown = 0;
+	count_inst.BranchDepth = 0;
 	end_loops = 1;
 	for(inst = loop->BeginLoop->Next; end_loops > 0; inst = inst->Next){
 		switch(inst->U.I.Opcode){
@@ -258,9 +268,11 @@ static int try_unroll_loop(struct radeon_compiler * c, struct loop_info * loop)
 				return 0;
 			}
 			break;
-		/* XXX Check if the counter is modified within an if statement.
-		 */
 		case RC_OPCODE_IF:
+			count_inst.BranchDepth++;
+			break;
+		case RC_OPCODE_ENDIF:
+			count_inst.BranchDepth--;
 			break;
 		default:
 			rc_for_all_writes_mask(inst, get_incr_amount, &count_inst);




More information about the mesa-commit mailing list