commit 1b3a83bd57065aa015d5251f44bea0b710838581 Author: chr Date: Sat May 16 16:39:38 2009 +0200 - Make TXP do what it's supposed to (centroid not yet honored, could store interpolation mode in some per register flag maybe). - FIX: don't set perspect_load = FALSE if we encounter a centroid attribute, instead make perspect/centroid_load counters. diff --git a/src/gallium/drivers/nv50/nv50_program.c b/src/gallium/drivers/nv50/nv50_program.c index 3a00c90..3116735 100644 --- a/src/gallium/drivers/nv50/nv50_program.c +++ b/src/gallium/drivers/nv50/nv50_program.c @@ -1497,14 +1497,33 @@ nv50_program_tx_insn(struct nv50_pc *pc, const union tgsi_full_token *tok) } break; case TGSI_OPCODE_TEX: - case TGSI_OPCODE_TXP: /* XXX: TXP should use w-component as iv on interp */ + case TGSI_OPCODE_TXP: { struct nv50_reg *t[4]; struct nv50_program_exec *e; alloc_temp4(pc, t, 0); - emit_mov(pc, t[0], src[0][0]); - emit_mov(pc, t[1], src[0][1]); + + if (inst->Instruction.Opcode == TGSI_OPCODE_TXP) { + if (src[0][0]->type == P_TEMP && src[0][0]->rhw != -1) { + /* XXX: centroid is not honored here */ + t[1]->rhw = src[0][3]->rhw; + emit_interp(pc, t[1], NULL, INTERP_LINEAR); + emit_flop(pc, 0, t[1], t[1]); + t[0]->rhw = src[0][0]->rhw; + t[1]->rhw = src[0][1]->rhw; + emit_interp(pc, t[0], t[1], INTERP_PERSPECTIVE); + emit_interp(pc, t[1], t[1], INTERP_PERSPECTIVE); + } else { + emit_mov(pc, t[1], src[0][3]); + emit_flop(pc, 0, t[1], t[1]); + emit_mul(pc, t[0], src[0][0], t[1]); + emit_mul(pc, t[1], src[0][1], t[1]); + } + } else { + emit_mov(pc, t[0], src[0][0]); + emit_mov(pc, t[1], src[0][1]); + } e = exec(pc); e->inst[0] = 0xf6400000; @@ -1514,6 +1533,7 @@ nv50_program_tx_insn(struct nv50_pc *pc, const union tgsi_full_token *tok) set_dst(pc, t[0], e); emit(pc, e); + /* XXX: without these MOVs, it can happen that TEX has no effect */ if (mask & (1 << 0)) emit_mov(pc, dst[0], t[0]); if (mask & (1 << 1)) emit_mov(pc, dst[1], t[1]); if (mask & (1 << 2)) emit_mov(pc, dst[2], t[2]); @@ -1636,8 +1656,8 @@ nv50_program_tx_prep(struct nv50_pc *pc) unsigned fcol, bcol, fcrd, depr; /* record interpolation mode from declaration */ - boolean centroid_load = FALSE; - boolean perspect_load = FALSE; + unsigned centroid_load = 0; + unsigned perspect_load = 0; unsigned interp_mode[32]; /* track register usage for temps and attrs */ @@ -1721,38 +1741,45 @@ nv50_program_tx_prep(struct nv50_pc *pc) break; case TGSI_INTERPOLATE_PERSPECTIVE: mode = INTERP_PERSPECTIVE; - perspect_load = TRUE; + if (!d->Declaration.Centroid) + perspect_load++; break; default: mode = INTERP_LINEAR; break; } + if (d->Declaration.Centroid) { + mode |= INTERP_CENTROID; + centroid_load++; + } + if (d->Declaration.Semantic) { switch (d->Semantic.SemanticName) { case TGSI_SEMANTIC_POSITION: fcrd = first; break; + /* XXX: FLAT and LINEAR don't seem to behave correctly: */ case TGSI_SEMANTIC_COLOR: fcol = first; - mode = INTERP_PERSPECTIVE; - perspect_load = TRUE; + if (!(mode & INTERP_PERSPECTIVE)) { + mode &= INTERP_CENTROID; + mode |= INTERP_PERSPECTIVE; + perspect_load++; + } break; case TGSI_SEMANTIC_BCOLOR: bcol = first; - mode = INTERP_PERSPECTIVE; - perspect_load = TRUE; + if (!(mode & INTERP_PERSPECTIVE)) { + mode &= INTERP_CENTROID; + mode |= INTERP_PERSPECTIVE; + perspect_load++; + } break; default: break; } } - - if (d->Declaration.Centroid) { - mode |= INTERP_CENTROID; - centroid_load = TRUE; - perspect_load = FALSE; - } assert(last < 32); for (i = first; i <= last; i++)