summaryrefslogtreecommitdiffstats
path: root/src/mesa/drivers/dri/i965/brw_fs.cpp
diff options
context:
space:
mode:
authorEric Anholt <eric@anholt.net>2010-08-28 22:42:01 -0700
committerEric Anholt <eric@anholt.net>2010-08-30 10:26:05 -0700
commit4ff25c2106fb981334bdc1b032fcf37d8753ba62 (patch)
tree3025610eb9070dee7ba383aa2df4a23279fb8f54 /src/mesa/drivers/dri/i965/brw_fs.cpp
parent40aadafa91ef5b931436d400fedafd720d59deff (diff)
downloadexternal_mesa3d-4ff25c2106fb981334bdc1b032fcf37d8753ba62.zip
external_mesa3d-4ff25c2106fb981334bdc1b032fcf37d8753ba62.tar.gz
external_mesa3d-4ff25c2106fb981334bdc1b032fcf37d8753ba62.tar.bz2
i965: Fix the new implementation of ir_unop_sign to match brw_wm_emit.c
Like the comparison operations, this suffered from CMP only setting the low bit. Doing the AND instructions would be the same instruction count as the more obvious conditional moves, so do cond moves. Fixes glsl-fs-sign and 6 other cases, like trig functions that use sign() internally.
Diffstat (limited to 'src/mesa/drivers/dri/i965/brw_fs.cpp')
-rw-r--r--src/mesa/drivers/dri/i965/brw_fs.cpp13
1 files changed, 8 insertions, 5 deletions
diff --git a/src/mesa/drivers/dri/i965/brw_fs.cpp b/src/mesa/drivers/dri/i965/brw_fs.cpp
index 233fee4..0d29c86 100644
--- a/src/mesa/drivers/dri/i965/brw_fs.cpp
+++ b/src/mesa/drivers/dri/i965/brw_fs.cpp
@@ -655,14 +655,17 @@ fs_visitor::visit(ir_expression *ir)
case ir_unop_sign:
temp = fs_reg(this, ir->type);
- inst = emit(fs_inst(BRW_OPCODE_CMP, this->result, op[0], fs_reg(0.0f)));
+ emit(fs_inst(BRW_OPCODE_MOV, this->result, fs_reg(0.0f)));
+
+ inst = emit(fs_inst(BRW_OPCODE_CMP, reg_null, op[0], fs_reg(0.0f)));
inst->conditional_mod = BRW_CONDITIONAL_G;
+ inst = emit(fs_inst(BRW_OPCODE_MOV, this->result, fs_reg(1.0f)));
+ inst->predicated = true;
- inst = emit(fs_inst(BRW_OPCODE_CMP, temp, op[0], fs_reg(0.0f)));
+ inst = emit(fs_inst(BRW_OPCODE_CMP, reg_null, op[0], fs_reg(0.0f)));
inst->conditional_mod = BRW_CONDITIONAL_L;
-
- temp.negate = true;
- emit(fs_inst(BRW_OPCODE_ADD, this->result, this->result, temp));
+ inst = emit(fs_inst(BRW_OPCODE_MOV, this->result, fs_reg(-1.0f)));
+ inst->predicated = true;
break;
case ir_unop_rcp: