summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKenneth Graunke <[email protected]>2015-04-17 14:08:14 -0700
committerKenneth Graunke <[email protected]>2015-04-21 12:01:36 -0700
commit44461e70985278464f5c2ce89bda2336c7299b0b (patch)
treece44a23e51844ffcc3c36da5949277baffc50559
parented10f9cfad1a01226725d542155a240bcf70e9cb (diff)
nir: Fix per-component negation in prog_to_nir's SWZ handling.
I missed the fact that the ARB_fragment_program SWZ instruction allows per-component negation. To fix this, move Abs/Negate handling into both the simple case and the SWZ case's per-component loop. Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=90000 Signed-off-by: Kenneth Graunke <[email protected]> Reviewed-by: Matt Turner <[email protected]>
-rw-r--r--src/mesa/program/prog_to_nir.c25
1 files changed, 18 insertions, 7 deletions
diff --git a/src/mesa/program/prog_to_nir.c b/src/mesa/program/prog_to_nir.c
index c738f5073b8..ff3d9f3beed 100644
--- a/src/mesa/program/prog_to_nir.c
+++ b/src/mesa/program/prog_to_nir.c
@@ -222,12 +222,23 @@ ptn_get_src(struct ptn_compile *c, const struct prog_src_register *prog_src)
}
nir_ssa_def *def;
- if (!HAS_EXTENDED_SWIZZLE(prog_src->Swizzle)) {
+ if (!HAS_EXTENDED_SWIZZLE(prog_src->Swizzle) &&
+ (prog_src->Negate == NEGATE_NONE || prog_src->Negate == NEGATE_XYZW)) {
+ /* The simple non-SWZ case. */
for (int i = 0; i < 4; i++)
src.swizzle[i] = GET_SWZ(prog_src->Swizzle, i);
def = nir_fmov_alu(b, src, 4);
+
+ if (prog_src->Abs)
+ def = nir_fabs(b, def);
+
+ if (prog_src->Negate)
+ def = nir_fneg(b, def);
} else {
+ /* The SWZ instruction allows per-component zero/one swizzles, and also
+ * per-component negation.
+ */
nir_ssa_def *chans[4];
for (int i = 0; i < 4; i++) {
int swizzle = GET_SWZ(prog_src->Swizzle, i);
@@ -246,16 +257,16 @@ ptn_get_src(struct ptn_compile *c, const struct prog_src_register *prog_src)
chans[i] = &mov->dest.dest.ssa;
}
+
+ if (prog_src->Abs)
+ chans[i] = nir_fabs(b, chans[i]);
+
+ if (prog_src->Negate & (1 << i))
+ chans[i] = nir_fneg(b, chans[i]);
}
def = nir_vec4(b, chans[0], chans[1], chans[2], chans[3]);
}
- if (prog_src->Abs)
- def = nir_fabs(b, def);
-
- if (prog_src->Negate)
- def = nir_fneg(b, def);
-
return def;
}