From 499d8c65457620c4879f6da302f0a9859ceaa2ee Mon Sep 17 00:00:00 2001 From: Matt Turner Date: Tue, 9 Apr 2013 17:45:12 -0700 Subject: [PATCH] glsl: Add support for new bit built-ins in ARB_gpu_shader5. v2: Move use of ir_binop_bfm and ir_triop_bfi to a later patch. Reviewed-by: Chris Forbes --- src/glsl/ir.cpp | 8 ++++++- src/glsl/ir.h | 21 ++++++++++++++++- src/glsl/ir_validate.cpp | 26 ++++++++++++++++++++++ src/glsl/opt_algebraic.cpp | 6 ++--- src/mesa/program/ir_to_mesa.cpp | 9 ++++++++ src/mesa/state_tracker/st_glsl_to_tgsi.cpp | 6 +++++ 6 files changed, 71 insertions(+), 5 deletions(-) diff --git a/src/glsl/ir.cpp b/src/glsl/ir.cpp index 05b77da2c45..2c989c91678 100644 --- a/src/glsl/ir.cpp +++ b/src/glsl/ir.cpp @@ -419,7 +419,7 @@ ir_expression::get_num_operands(ir_expression_operation op) if (op <= ir_last_triop) return 3; - if (op == ir_quadop_vector) + if (op <= ir_last_quadop) return 4; assert(false); @@ -477,6 +477,10 @@ static const char *const operator_strs[] = { "unpackHalf2x16", "unpackHalf2x16_split_x", "unpackHalf2x16_split_y", + "bitfield_reverse", + "bit_count", + "find_msb", + "find_lsb", "noise", "+", "-", @@ -506,6 +510,8 @@ static const char *const operator_strs[] = { "packHalf2x16_split", "ubo_load", "lrp", + "bitfield_extract", + "bitfield_insert", "vector", }; diff --git a/src/glsl/ir.h b/src/glsl/ir.h index 878a94611a7..470c08ca00d 100644 --- a/src/glsl/ir.h +++ b/src/glsl/ir.h @@ -1033,6 +1033,16 @@ enum ir_expression_operation { ir_unop_unpack_half_2x16_split_y, /*@}*/ + /** + * \name Bit operations, part of ARB_gpu_shader5. + */ + /*@{*/ + ir_unop_bitfield_reverse, + ir_unop_bit_count, + ir_unop_find_msb, + ir_unop_find_lsb, + /*@}*/ + ir_unop_noise, /** @@ -1123,13 +1133,22 @@ enum ir_expression_operation { ir_triop_lrp, + ir_triop_bitfield_extract, + /** * A sentinel marking the last of the ternary operations. */ - ir_last_triop = ir_triop_lrp, + ir_last_triop = ir_triop_bitfield_extract, + + ir_quadop_bitfield_insert, ir_quadop_vector, + /** + * A sentinel marking the last of the ternary operations. + */ + ir_last_quadop = ir_quadop_vector, + /** * A sentinel marking the last of all operations. */ diff --git a/src/glsl/ir_validate.cpp b/src/glsl/ir_validate.cpp index 699c192cd2c..4a8df6953ee 100644 --- a/src/glsl/ir_validate.cpp +++ b/src/glsl/ir_validate.cpp @@ -361,6 +361,19 @@ ir_validate::visit_leave(ir_expression *ir) assert(ir->operands[0]->type == glsl_type::uint_type); break; + case ir_unop_bitfield_reverse: + assert(ir->operands[0]->type == ir->type); + assert(ir->type->is_integer()); + break; + + case ir_unop_bit_count: + case ir_unop_find_msb: + case ir_unop_find_lsb: + assert(ir->operands[0]->type->vector_elements == ir->type->vector_elements); + assert(ir->operands[0]->type->is_integer()); + assert(ir->type->base_type == GLSL_TYPE_INT); + break; + case ir_unop_noise: /* XXX what can we assert here? */ break; @@ -474,6 +487,19 @@ ir_validate::visit_leave(ir_expression *ir) assert(ir->operands[2]->type == ir->operands[0]->type || ir->operands[2]->type == glsl_type::float_type); break; + case ir_triop_bitfield_extract: + assert(ir->operands[0]->type == ir->type); + assert(ir->operands[1]->type == glsl_type::int_type); + assert(ir->operands[2]->type == glsl_type::int_type); + break; + + case ir_quadop_bitfield_insert: + assert(ir->operands[0]->type == ir->type); + assert(ir->operands[1]->type == ir->type); + assert(ir->operands[2]->type == glsl_type::int_type); + assert(ir->operands[3]->type == glsl_type::int_type); + break; + case ir_quadop_vector: /* The vector operator collects some number of scalars and generates a * vector from them. diff --git a/src/glsl/opt_algebraic.cpp b/src/glsl/opt_algebraic.cpp index 70e016d22aa..d706a6ad13c 100644 --- a/src/glsl/opt_algebraic.cpp +++ b/src/glsl/opt_algebraic.cpp @@ -186,12 +186,12 @@ ir_algebraic_visitor::swizzle_if_required(ir_expression *expr, ir_rvalue * ir_algebraic_visitor::handle_expression(ir_expression *ir) { - ir_constant *op_const[3] = {NULL, NULL, NULL}; - ir_expression *op_expr[3] = {NULL, NULL, NULL}; + ir_constant *op_const[4] = {NULL, NULL, NULL, NULL}; + ir_expression *op_expr[4] = {NULL, NULL, NULL, NULL}; ir_expression *temp; unsigned int i; - assert(ir->get_num_operands() <= 3); + assert(ir->get_num_operands() <= 4); for (i = 0; i < ir->get_num_operands(); i++) { if (ir->operands[i]->type->is_matrix()) return ir; diff --git a/src/mesa/program/ir_to_mesa.cpp b/src/mesa/program/ir_to_mesa.cpp index 14cf5baa77b..c6f6bf42ea0 100644 --- a/src/mesa/program/ir_to_mesa.cpp +++ b/src/mesa/program/ir_to_mesa.cpp @@ -1444,6 +1444,10 @@ ir_to_mesa_visitor::visit(ir_expression *ir) case ir_unop_unpack_half_2x16_split_x: case ir_unop_unpack_half_2x16_split_y: case ir_binop_pack_half_2x16_split: + case ir_unop_bitfield_reverse: + case ir_unop_bit_count: + case ir_unop_find_msb: + case ir_unop_find_lsb: assert(!"not supported"); break; case ir_binop_min: @@ -1485,6 +1489,11 @@ ir_to_mesa_visitor::visit(ir_expression *ir) emit(ir, OPCODE_LRP, result_dst, op[2], op[1], op[0]); break; + case ir_triop_bitfield_extract: + case ir_quadop_bitfield_insert: + assert(!"not supported"); + break; + case ir_quadop_vector: /* This operation should have already been handled. */ diff --git a/src/mesa/state_tracker/st_glsl_to_tgsi.cpp b/src/mesa/state_tracker/st_glsl_to_tgsi.cpp index f2eb3e7d912..ad936bd20d0 100644 --- a/src/mesa/state_tracker/st_glsl_to_tgsi.cpp +++ b/src/mesa/state_tracker/st_glsl_to_tgsi.cpp @@ -1969,6 +1969,12 @@ glsl_to_tgsi_visitor::visit(ir_expression *ir) case ir_unop_unpack_snorm_4x8: case ir_unop_unpack_unorm_4x8: case ir_binop_pack_half_2x16_split: + case ir_unop_bitfield_reverse: + case ir_unop_bit_count: + case ir_unop_find_msb: + case ir_unop_find_lsb: + case ir_triop_bitfield_extract: + case ir_quadop_bitfield_insert: case ir_quadop_vector: /* This operation is not supported, or should have already been handled. */ -- 2.30.2