nv50: handle TGSI_OPCODE_IMAX,IMIN,UMAX,UMIN
This commit is contained in:
parent
607b9c2e09
commit
d550de2342
|
@ -971,6 +971,13 @@ emit_arl(struct nv50_pc *pc, struct nv50_reg *dst, struct nv50_reg *src,
|
||||||
emit(pc, e);
|
emit(pc, e);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#define NV50_MAX_F32 0x880
|
||||||
|
#define NV50_MAX_S32 0x08c
|
||||||
|
#define NV50_MAX_U32 0x084
|
||||||
|
#define NV50_MIN_F32 0x8a0
|
||||||
|
#define NV50_MIN_S32 0x0ac
|
||||||
|
#define NV50_MIN_U32 0x0a4
|
||||||
|
|
||||||
static void
|
static void
|
||||||
emit_minmax(struct nv50_pc *pc, unsigned sub, struct nv50_reg *dst,
|
emit_minmax(struct nv50_pc *pc, unsigned sub, struct nv50_reg *dst,
|
||||||
struct nv50_reg *src0, struct nv50_reg *src1)
|
struct nv50_reg *src0, struct nv50_reg *src1)
|
||||||
|
@ -978,8 +985,8 @@ emit_minmax(struct nv50_pc *pc, unsigned sub, struct nv50_reg *dst,
|
||||||
struct nv50_program_exec *e = exec(pc);
|
struct nv50_program_exec *e = exec(pc);
|
||||||
|
|
||||||
set_long(pc, e);
|
set_long(pc, e);
|
||||||
e->inst[0] |= 0xb0000000;
|
e->inst[0] |= 0x30000000 | ((sub & 0x800) << 20);
|
||||||
e->inst[1] |= (sub << 29);
|
e->inst[1] |= (sub << 24);
|
||||||
|
|
||||||
check_swap_src_0_1(pc, &src0, &src1);
|
check_swap_src_0_1(pc, &src0, &src1);
|
||||||
set_dst(pc, dst, e);
|
set_dst(pc, dst, e);
|
||||||
|
@ -1341,18 +1348,18 @@ emit_lit(struct nv50_pc *pc, struct nv50_reg **dst, unsigned mask,
|
||||||
|
|
||||||
if (mask & (3 << 1)) {
|
if (mask & (3 << 1)) {
|
||||||
tmp[0] = alloc_temp(pc, NULL);
|
tmp[0] = alloc_temp(pc, NULL);
|
||||||
emit_minmax(pc, 4, tmp[0], src[0], zero);
|
emit_minmax(pc, NV50_MAX_F32, tmp[0], src[0], zero);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mask & (1 << 2)) {
|
if (mask & (1 << 2)) {
|
||||||
set_pred_wr(pc, 1, 0, pc->p->exec_tail);
|
set_pred_wr(pc, 1, 0, pc->p->exec_tail);
|
||||||
|
|
||||||
tmp[1] = temp_temp(pc);
|
tmp[1] = temp_temp(pc);
|
||||||
emit_minmax(pc, 4, tmp[1], src[1], zero);
|
emit_minmax(pc, NV50_MAX_F32, tmp[1], src[1], zero);
|
||||||
|
|
||||||
tmp[3] = temp_temp(pc);
|
tmp[3] = temp_temp(pc);
|
||||||
emit_minmax(pc, 4, tmp[3], src[3], neg128);
|
emit_minmax(pc, NV50_MAX_F32, tmp[3], src[3], neg128);
|
||||||
emit_minmax(pc, 5, tmp[3], tmp[3], pos128);
|
emit_minmax(pc, NV50_MIN_F32, tmp[3], tmp[3], pos128);
|
||||||
|
|
||||||
emit_pow(pc, dst[2], tmp[1], tmp[3]);
|
emit_pow(pc, dst[2], tmp[1], tmp[3]);
|
||||||
emit_mov(pc, dst[2], zero);
|
emit_mov(pc, dst[2], zero);
|
||||||
|
@ -1496,8 +1503,8 @@ load_cube_tex_coords(struct nv50_pc *pc, struct nv50_reg *t[4],
|
||||||
src[1]->mod |= NV50_MOD_ABS;
|
src[1]->mod |= NV50_MOD_ABS;
|
||||||
src[2]->mod |= NV50_MOD_ABS;
|
src[2]->mod |= NV50_MOD_ABS;
|
||||||
|
|
||||||
emit_minmax(pc, 4, t[2], src[0], src[1]);
|
emit_minmax(pc, NV50_MAX_F32, t[2], src[0], src[1]);
|
||||||
emit_minmax(pc, 4, t[2], src[2], t[2]);
|
emit_minmax(pc, NV50_MAX_F32, t[2], src[2], t[2]);
|
||||||
|
|
||||||
src[0]->mod = mod[0];
|
src[0]->mod = mod[0];
|
||||||
src[1]->mod = mod[1];
|
src[1]->mod = mod[1];
|
||||||
|
@ -1872,7 +1879,11 @@ get_supported_mods(const struct tgsi_full_instruction *insn, int i)
|
||||||
case TGSI_OPCODE_U2F:
|
case TGSI_OPCODE_U2F:
|
||||||
return NV50_MOD_NEG | NV50_MOD_ABS | NV50_MOD_I32;
|
return NV50_MOD_NEG | NV50_MOD_ABS | NV50_MOD_I32;
|
||||||
case TGSI_OPCODE_SHL:
|
case TGSI_OPCODE_SHL:
|
||||||
|
case TGSI_OPCODE_IMAX:
|
||||||
|
case TGSI_OPCODE_IMIN:
|
||||||
case TGSI_OPCODE_ISHR:
|
case TGSI_OPCODE_ISHR:
|
||||||
|
case TGSI_OPCODE_UMAX:
|
||||||
|
case TGSI_OPCODE_UMIN:
|
||||||
case TGSI_OPCODE_USHR:
|
case TGSI_OPCODE_USHR:
|
||||||
return NV50_MOD_I32;
|
return NV50_MOD_I32;
|
||||||
default:
|
default:
|
||||||
|
@ -2504,6 +2515,20 @@ nv50_program_tx_insn(struct nv50_pc *pc,
|
||||||
pc->if_insn[pc->if_lvl++] = emit_branch(pc, 0, 2);;
|
pc->if_insn[pc->if_lvl++] = emit_branch(pc, 0, 2);;
|
||||||
terminate_mbb(pc);
|
terminate_mbb(pc);
|
||||||
break;
|
break;
|
||||||
|
case TGSI_OPCODE_IMAX:
|
||||||
|
for (c = 0; c < 4; c++) {
|
||||||
|
if (!(mask & (1 << c)))
|
||||||
|
continue;
|
||||||
|
emit_minmax(pc, 0x08c, dst[c], src[0][c], src[1][c]);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case TGSI_OPCODE_IMIN:
|
||||||
|
for (c = 0; c < 4; c++) {
|
||||||
|
if (!(mask & (1 << c)))
|
||||||
|
continue;
|
||||||
|
emit_minmax(pc, 0x0ac, dst[c], src[0][c], src[1][c]);
|
||||||
|
}
|
||||||
|
break;
|
||||||
case TGSI_OPCODE_INEG:
|
case TGSI_OPCODE_INEG:
|
||||||
for (c = 0; c < 4; c++) {
|
for (c = 0; c < 4; c++) {
|
||||||
if (!(mask & (1 << c)))
|
if (!(mask & (1 << c)))
|
||||||
|
@ -2576,14 +2601,14 @@ nv50_program_tx_insn(struct nv50_pc *pc,
|
||||||
for (c = 0; c < 4; c++) {
|
for (c = 0; c < 4; c++) {
|
||||||
if (!(mask & (1 << c)))
|
if (!(mask & (1 << c)))
|
||||||
continue;
|
continue;
|
||||||
emit_minmax(pc, 4, dst[c], src[0][c], src[1][c]);
|
emit_minmax(pc, 0x880, dst[c], src[0][c], src[1][c]);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case TGSI_OPCODE_MIN:
|
case TGSI_OPCODE_MIN:
|
||||||
for (c = 0; c < 4; c++) {
|
for (c = 0; c < 4; c++) {
|
||||||
if (!(mask & (1 << c)))
|
if (!(mask & (1 << c)))
|
||||||
continue;
|
continue;
|
||||||
emit_minmax(pc, 5, dst[c], src[0][c], src[1][c]);
|
emit_minmax(pc, 0x8a0, dst[c], src[0][c], src[1][c]);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case TGSI_OPCODE_MOV:
|
case TGSI_OPCODE_MOV:
|
||||||
|
@ -2712,6 +2737,20 @@ nv50_program_tx_insn(struct nv50_pc *pc,
|
||||||
emit_cvt(pc, dst[c], src[0][c], -1, CVT_F32_U32);
|
emit_cvt(pc, dst[c], src[0][c], -1, CVT_F32_U32);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case TGSI_OPCODE_UMAX:
|
||||||
|
for (c = 0; c < 4; c++) {
|
||||||
|
if (!(mask & (1 << c)))
|
||||||
|
continue;
|
||||||
|
emit_minmax(pc, 0x084, dst[c], src[0][c], src[1][c]);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case TGSI_OPCODE_UMIN:
|
||||||
|
for (c = 0; c < 4; c++) {
|
||||||
|
if (!(mask & (1 << c)))
|
||||||
|
continue;
|
||||||
|
emit_minmax(pc, 0x0a4, dst[c], src[0][c], src[1][c]);
|
||||||
|
}
|
||||||
|
break;
|
||||||
case TGSI_OPCODE_XPD:
|
case TGSI_OPCODE_XPD:
|
||||||
temp = temp_temp(pc);
|
temp = temp_temp(pc);
|
||||||
if (mask & (1 << 0)) {
|
if (mask & (1 << 0)) {
|
||||||
|
|
Loading…
Reference in New Issue