[Mesa-dev] [PATCH A 11/15] nir: Switch conversions to unsized opcodes
Jason Ekstrand
jason at jlekstrand.net
Fri Nov 9 03:45:12 UTC 2018
---
src/compiler/nir/nir.c | 67 ++++++++++++++++++++++++++
src/compiler/nir/nir_opcodes.py | 38 +++++++--------
src/compiler/nir/nir_opcodes_c.py | 79 -------------------------------
3 files changed, 83 insertions(+), 101 deletions(-)
diff --git a/src/compiler/nir/nir.c b/src/compiler/nir/nir.c
index 249b9357c3f..c0be8d97913 100644
--- a/src/compiler/nir/nir.c
+++ b/src/compiler/nir/nir.c
@@ -1198,6 +1198,73 @@ nir_foreach_src(nir_instr *instr, nir_foreach_src_cb cb, void *state)
return nir_foreach_dest(instr, visit_dest_indirect, &dest_state);
}
+nir_op
+nir_type_conversion_op(nir_alu_type src, nir_alu_type dst,
+ nir_rounding_mode rnd)
+{
+ nir_alu_type src_base = (nir_alu_type) nir_alu_type_get_base_type(src);
+ nir_alu_type dst_base = (nir_alu_type) nir_alu_type_get_base_type(dst);
+ unsigned src_bit_size = nir_alu_type_get_type_size(src);
+ unsigned dst_bit_size = nir_alu_type_get_type_size(dst);
+
+ if (src == dst && src_base == nir_type_float) {
+ return nir_op_fmov;
+ } else if ((src_base == nir_type_int || src_base == nir_type_uint) &&
+ (dst_base == nir_type_int || dst_base == nir_type_uint) &&
+ src_bit_size == dst_bit_size) {
+ /* Integer <-> integer conversions with the same bit-size on both
+ * ends are just no-op moves.
+ */
+ return nir_op_imov;
+ }
+
+ switch (src_base) {
+ case nir_type_float:
+ switch (dst_base) {
+ case nir_type_float:
+ switch (rnd) {
+ case nir_rounding_mode_undef: return nir_op_f2f;
+ case nir_rounding_mode_rtne: return nir_op_f2f_rtne;
+ case nir_rounding_mode_rtz: return nir_op_f2f_rtz;
+ default: unreachable("Invalid rounding mode");
+ }
+ case nir_type_int: return nir_op_f2i;
+ case nir_type_uint: return nir_op_f2u;
+ case nir_type_bool: return nir_op_f2b;
+ default: unreachable("Invalid base type");
+ }
+
+ case nir_type_int:
+ switch (dst_base) {
+ case nir_type_float: return nir_op_i2f;
+ case nir_type_int: return nir_op_i2i;
+ case nir_type_uint: return nir_op_i2i;
+ case nir_type_bool: return nir_op_i2b;
+ default: unreachable("Invalid base NIR type");
+ }
+
+ case nir_type_uint:
+ switch (dst_base) {
+ case nir_type_float: return nir_op_u2f;
+ case nir_type_int: return nir_op_u2u;
+ case nir_type_uint: return nir_op_u2u;
+ case nir_type_bool: return nir_op_i2b;
+ default: unreachable("Invalid base NIR type");
+ }
+
+ case nir_type_bool:
+ switch (dst_base) {
+ case nir_type_float: return nir_op_b2f;
+ case nir_type_int: return nir_op_b2i;
+ case nir_type_uint: return nir_op_b2i;
+ default: unreachable("Invalid base NIR type");
+ }
+
+ default:
+ unreachable("Invalid base type");
+ }
+}
+
int64_t
nir_src_comp_as_int(nir_src src, unsigned comp)
{
diff --git a/src/compiler/nir/nir_opcodes.py b/src/compiler/nir/nir_opcodes.py
index 6b00305790a..8575a4f2859 100644
--- a/src/compiler/nir/nir_opcodes.py
+++ b/src/compiler/nir/nir_opcodes.py
@@ -199,29 +199,23 @@ unop("fsqrt", tfloat, "bit_size == 64 ? sqrt(src0) : sqrtf(src0)")
unop("fexp2", tfloat, "exp2f(src0)")
unop("flog2", tfloat, "log2f(src0)")
-# Generate all of the numeric conversion opcodes
-for src_t in [tint, tuint, tfloat]:
- if src_t in (tint, tuint):
- dst_types = [tfloat, src_t]
- elif src_t == tfloat:
- dst_types = [tint, tuint, tfloat]
-
- for dst_t in dst_types:
- for bit_size in type_sizes(dst_t):
- if bit_size == 16 and dst_t == tfloat and src_t == tfloat:
- rnd_modes = ['_rtne', '_rtz', '']
- for rnd_mode in rnd_modes:
- unop_convert("{0}2{1}{2}{3}".format(src_t[0], dst_t[0],
- bit_size, rnd_mode),
- dst_t + str(bit_size), src_t, "src0")
- else:
- unop_convert("{0}2{1}{2}".format(src_t[0], dst_t[0], bit_size),
- dst_t + str(bit_size), src_t, "src0")
-
-# We'll hand-code the to/from bool conversion opcodes. Because bool doesn't
-# have multiple bit-sizes, we can always infer the size from the other type.
-unop_convert("f2b", tbool32, tfloat, "src0 != 0.0")
+
+def unsized_unop_convert(name, out_type, in_type, const_expr):
+ assert not type_has_size(out_type)
+ assert not type_has_size(in_type)
+ opcode(name, 0, out_type, [0], [in_type], True, "", const_expr)
+
+unsized_unop_convert("i2f", tfloat, tint, "src0")
+unsized_unop_convert("i2i", tint, tint, "src0")
unop_convert("i2b", tbool32, tint, "src0 != 0")
+unsized_unop_convert("u2f", tfloat, tuint, "src0")
+unsized_unop_convert("u2u", tuint, tuint, "src0")
+unsized_unop_convert("f2i", tint, tfloat, "src0")
+unsized_unop_convert("f2u", tuint, tfloat, "src0")
+unop_convert("f2b", tbool32, tfloat, "src0 != 0.0")
+unsized_unop_convert("f2f", tfloat, tfloat, "src0")
+unsized_unop_convert("f2f_rtne", tfloat, tfloat, "src0")
+unsized_unop_convert("f2f_rtz", tfloat, tfloat, "src0")
unop_convert("b2f", tfloat, tbool32, "src0 ? 1.0 : 0.0")
unop_convert("b2i", tint, tbool32, "src0 ? 1 : 0")
diff --git a/src/compiler/nir/nir_opcodes_c.py b/src/compiler/nir/nir_opcodes_c.py
index 704f100544d..6518c459dfc 100644
--- a/src/compiler/nir/nir_opcodes_c.py
+++ b/src/compiler/nir/nir_opcodes_c.py
@@ -31,85 +31,6 @@ from mako.template import Template
template = Template("""
#include "nir.h"
-nir_op
-nir_type_conversion_op(nir_alu_type src, nir_alu_type dst, nir_rounding_mode rnd)
-{
- nir_alu_type src_base = (nir_alu_type) nir_alu_type_get_base_type(src);
- nir_alu_type dst_base = (nir_alu_type) nir_alu_type_get_base_type(dst);
- unsigned src_bit_size = nir_alu_type_get_type_size(src);
- unsigned dst_bit_size = nir_alu_type_get_type_size(dst);
-
- if (src == dst && src_base == nir_type_float) {
- return nir_op_fmov;
- } else if ((src_base == nir_type_int || src_base == nir_type_uint) &&
- (dst_base == nir_type_int || dst_base == nir_type_uint) &&
- src_bit_size == dst_bit_size) {
- /* Integer <-> integer conversions with the same bit-size on both
- * ends are just no-op moves.
- */
- return nir_op_imov;
- }
-
- switch (src_base) {
-% for src_t in ['int', 'uint', 'float']:
- case nir_type_${src_t}:
- switch (dst_base) {
-% for dst_t in ['int', 'uint', 'float']:
- case nir_type_${dst_t}:
-% if src_t in ['int', 'uint'] and dst_t in ['int', 'uint']:
-% if dst_t == 'int':
-<% continue %>
-% else:
-<% dst_t = src_t %>
-% endif
-% endif
- switch (dst_bit_size) {
-% for dst_bits in type_sizes(dst_t):
- case ${dst_bits}:
-% if src_t == 'float' and dst_t == 'float' and dst_bits == 16:
- switch(rnd) {
-% for rnd_t in [('rtne', '_rtne'), ('rtz', '_rtz'), ('undef', '')]:
- case nir_rounding_mode_${rnd_t[0]}:
- return ${'nir_op_{0}2{1}{2}{3}'.format(src_t[0], dst_t[0],
- dst_bits, rnd_t[1])};
-% endfor
- default:
- unreachable("Invalid 16-bit nir rounding mode");
- }
-% else:
- assert(rnd == nir_rounding_mode_undef);
- return ${'nir_op_{0}2{1}{2}'.format(src_t[0], dst_t[0], dst_bits)};
-% endif
-% endfor
- default:
- unreachable("Invalid nir alu bit size");
- }
-% endfor
- case nir_type_bool:
-% if src_t == 'float':
- return nir_op_f2b;
-% else:
- return nir_op_i2b;
-% endif
- default:
- unreachable("Invalid nir alu base type");
- }
-% endfor
- case nir_type_bool:
- switch (dst_base) {
- case nir_type_int:
- case nir_type_uint:
- return nir_op_b2i;
- case nir_type_float:
- return nir_op_b2f;
- default:
- unreachable("Invalid nir alu base type");
- }
- default:
- unreachable("Invalid nir alu base type");
- }
-}
-
const nir_op_info nir_op_infos[nir_num_opcodes] = {
% for name, opcode in sorted(opcodes.items()):
{
--
2.19.1
More information about the mesa-dev
mailing list