Operand op = op_.op;
if (dst.regClass() == s1 && op.size() == 1 && op.isLiteral()) {
uint32_t imm = op.constantValue();
- if (imm >= 0xffff8000 || imm <= 0x7fff) {
+ if (imm == 0x3e22f983) {
+ if (program->chip_class >= GFX8)
+ op.setFixed(PhysReg{248}); /* it can be an inline constant on GFX8+ */
+ } else if (imm >= 0xffff8000 || imm <= 0x7fff) {
return sopk(aco_opcode::s_movk_i32, dst, imm & 0xFFFFu);
} else if (util_bitreverse(imm) <= 64 || util_bitreverse(imm) >= 0xFFFFFFF0) {
uint32_t rev = util_bitreverse(imm);
Temp src = get_alu_src(ctx, instr->src[0]);
aco_ptr<Instruction> norm;
if (dst.size() == 1) {
- Temp tmp;
- Operand half_pi(0x3e22f983u);
- if (src.type() == RegType::sgpr)
- tmp = bld.vop2_e64(aco_opcode::v_mul_f32, bld.def(v1), half_pi, src);
- else
- tmp = bld.vop2(aco_opcode::v_mul_f32, bld.def(v1), half_pi, src);
+ Temp half_pi = bld.copy(bld.def(s1), Operand(0x3e22f983u));
+ Temp tmp = bld.vop2(aco_opcode::v_mul_f32, bld.def(v1), half_pi, as_vgpr(ctx, src));
/* before GFX9, v_sin_f32 and v_cos_f32 had a valid input domain of [-256, +256] */
if (ctx->options->chip_class < GFX9)
setFixed(PhysReg{246});
else if (v == 0xc0800000) /* -4.0 */
setFixed(PhysReg{247});
- else if (v == 0x3e22f983) /* 1/(2*PI) */
- setFixed(PhysReg{248});
else /* Literal Constant */
setFixed(PhysReg{255});
};
setFixed(PhysReg{246});
else if (v == 0xC010000000000000) /* -4.0 */
setFixed(PhysReg{247});
- else if (v == 0x3fc45f306dc9c882) /* 1/(2*PI) */
- setFixed(PhysReg{248});
else { /* Literal Constant: we don't know if it is a long or double.*/
isConstant_ = 0;
assert(false && "attempt to create a 64-bit literal constant");
return false;
}
+Operand get_constant_op(opt_ctx &ctx, uint32_t val)
+{
+ // TODO: this functions shouldn't be needed if we store Operand instead of value.
+ Operand op(val);
+ if (val == 0x3e22f983 && ctx.program->chip_class >= GFX8)
+ op.setFixed(PhysReg{248}); /* 1/2 PI can be an inline constant on GFX8+ */
+ return op;
+}
+
void label_instruction(opt_ctx &ctx, Block& block, aco_ptr<Instruction>& instr)
{
if (instr->isSALU() || instr->isVALU() || instr->format == Format::PSEUDO) {
}
}
if ((info.is_constant() || (info.is_literal() && instr->format == Format::PSEUDO)) && !instr->operands[i].isFixed() && can_accept_constant(instr, i)) {
- instr->operands[i] = Operand(info.val);
+ instr->operands[i] = get_constant_op(ctx, info.val);
continue;
}
}
if (info.is_constant() && can_accept_constant(instr, i)) {
perfwarn(instr->opcode == aco_opcode::v_cndmask_b32 && i == 2, "v_cndmask_b32 with a constant selector", instr.get());
if (i == 0 || instr->opcode == aco_opcode::v_readlane_b32 || instr->opcode == aco_opcode::v_writelane_b32) {
- instr->operands[i] = Operand(info.val);
+ instr->operands[i] = get_constant_op(ctx, info.val);
continue;
} else if (!instr->isVOP3() && can_swap_operands(instr)) {
instr->operands[i] = instr->operands[0];
- instr->operands[0] = Operand(info.val);
+ instr->operands[0] = get_constant_op(ctx, info.val);
continue;
} else if (can_use_VOP3(instr)) {
to_VOP3(ctx, instr);
- instr->operands[i] = Operand(info.val);
+ instr->operands[i] = get_constant_op(ctx, info.val);
continue;
}
}