*/
SHADER_OPCODE_SEND,
+ /**
+ * An "undefined" write which does nothing but indicates to liveness that
+ * we don't care about any values in the register which predate this
+ * instruction. Used to prevent partial writes from causing issues with
+ * live ranges.
+ */
+ SHADER_OPCODE_UNDEF,
+
/**
* Texture sampling opcodes.
*
return inst;
}
+ instruction *
+ UNDEF(const dst_reg &dst) const
+ {
+ assert(dst.file == VGRF);
+ instruction *inst = emit(SHADER_OPCODE_UNDEF,
+ retype(dst, BRW_REGISTER_TYPE_UD));
+ inst->size_written = shader->alloc.sizes[dst.nr] * REG_SIZE;
+
+ return inst;
+ }
+
backend_shader *shader;
private:
struct disasm_info *disasm_info = disasm_initialize(devinfo, cfg);
foreach_block_and_inst (block, fs_inst, inst, cfg) {
+ if (inst->opcode == SHADER_OPCODE_UNDEF)
+ continue;
+
struct brw_reg src[4], dst;
unsigned int last_insn_offset = p->next_insn_offset;
bool multiple_instructions_emitted = false;
const unsigned stride =
type_sz(inst->dst.type) * inst->dst.stride <= type_sz(type) ? 1 :
type_sz(inst->dst.type) * inst->dst.stride / type_sz(type);
- const fs_reg tmp = horiz_stride(ibld.vgrf(type, stride), stride);
+ fs_reg tmp = ibld.vgrf(type, stride);
+ ibld.UNDEF(tmp);
+ tmp = horiz_stride(tmp, stride);
/* Emit a MOV taking care of all the destination modifiers. */
fs_inst *mov = ibld.at(block, inst->next).MOV(inst->dst, tmp);
const unsigned stride = type_sz(inst->dst.type) * inst->dst.stride /
type_sz(inst->src[i].type);
assert(stride > 0);
- const fs_reg tmp = horiz_stride(ibld.vgrf(inst->src[i].type, stride),
- stride);
+ fs_reg tmp = ibld.vgrf(inst->src[i].type, stride);
+ ibld.UNDEF(tmp);
+ tmp = horiz_stride(tmp, stride);
/* Emit a series of 32-bit integer copies with any source modifiers
* cleaned up (because their semantics are dependent on the type).
const unsigned stride = required_dst_byte_stride(inst) /
type_sz(inst->dst.type);
assert(stride > 0);
- const fs_reg tmp = horiz_stride(ibld.vgrf(inst->dst.type, stride),
- stride);
+ fs_reg tmp = ibld.vgrf(inst->dst.type, stride);
+ ibld.UNDEF(tmp);
+ tmp = horiz_stride(tmp, stride);
/* Emit a series of 32-bit integer copies from the temporary into the
* original destination.
BRW_REGISTER_TYPE_F);
nir_ssa_values[dest.ssa.index] =
bld.vgrf(reg_type, dest.ssa.num_components);
+ bld.UNDEF(nir_ssa_values[dest.ssa.index]);
return nir_ssa_values[dest.ssa.index];
} else {
/* We don't handle indirects on locals */