diff options
author | Francisco Jerez <currojerez@riseup.net> | 2015-02-06 14:38:20 +0200 |
---|---|---|
committer | Francisco Jerez <currojerez@riseup.net> | 2015-02-10 19:09:25 +0200 |
commit | aef83957e1e13ecb96df436d53373ecc4cedeb08 (patch) | |
tree | a400b93bd0d32410407db97934d4e9a86358208f /src/mesa/drivers/dri/i965/brw_vec4_copy_propagation.cpp | |
parent | 64fde7b31c419685aa8ef6060828e21b9a11ef51 (diff) | |
download | external_mesa3d-aef83957e1e13ecb96df436d53373ecc4cedeb08.zip external_mesa3d-aef83957e1e13ecb96df436d53373ecc4cedeb08.tar.gz external_mesa3d-aef83957e1e13ecb96df436d53373ecc4cedeb08.tar.bz2 |
i965: Handle negated unsigned immediate values in constant propagation.
Negation of UD/UW sources behaves the same as for D/W sources, taking
the two's complement of the source, except for bitwise logical
operations on Gen8 and up which take the one's complement. Fixes
crash in a GLSL shader with subtraction of two unsigned values.
Reviewed-by: Matt Turner <mattst88@gmail.com>
Diffstat (limited to 'src/mesa/drivers/dri/i965/brw_vec4_copy_propagation.cpp')
-rw-r--r-- | src/mesa/drivers/dri/i965/brw_vec4_copy_propagation.cpp | 24 |
1 files changed, 13 insertions, 11 deletions
diff --git a/src/mesa/drivers/dri/i965/brw_vec4_copy_propagation.cpp b/src/mesa/drivers/dri/i965/brw_vec4_copy_propagation.cpp index 81567d2..4614e07 100644 --- a/src/mesa/drivers/dri/i965/brw_vec4_copy_propagation.cpp +++ b/src/mesa/drivers/dri/i965/brw_vec4_copy_propagation.cpp @@ -96,6 +96,15 @@ swizzle_vf_imm(unsigned vf4, unsigned swizzle) } static bool +is_logic_op(enum opcode opcode) +{ + return (opcode == BRW_OPCODE_AND || + opcode == BRW_OPCODE_OR || + opcode == BRW_OPCODE_XOR || + opcode == BRW_OPCODE_NOT); +} + +static bool try_constant_propagate(struct brw_context *brw, vec4_instruction *inst, int arg, struct copy_entry *entry) { @@ -114,13 +123,15 @@ try_constant_propagate(struct brw_context *brw, vec4_instruction *inst, return false; if (inst->src[arg].abs) { - if (!brw_abs_immediate(value.type, &value.fixed_hw_reg)) { + if ((brw->gen >= 8 && is_logic_op(inst->opcode)) || + !brw_abs_immediate(value.type, &value.fixed_hw_reg)) { return false; } } if (inst->src[arg].negate) { - if (!brw_negate_immediate(value.type, &value.fixed_hw_reg)) { + if ((brw->gen >= 8 && is_logic_op(inst->opcode)) || + !brw_negate_immediate(value.type, &value.fixed_hw_reg)) { return false; } } @@ -226,15 +237,6 @@ try_constant_propagate(struct brw_context *brw, vec4_instruction *inst, } static bool -is_logic_op(enum opcode opcode) -{ - return (opcode == BRW_OPCODE_AND || - opcode == BRW_OPCODE_OR || - opcode == BRW_OPCODE_XOR || - opcode == BRW_OPCODE_NOT); -} - -static bool try_copy_propagate(struct brw_context *brw, vec4_instruction *inst, int arg, struct copy_entry *entry, int reg) { |