case ir_unop_f2i:
case ir_unop_b2i:
case ir_unop_u2i:
+ case ir_unop_d2i:
case ir_unop_bitcast_f2i:
case ir_unop_bit_count:
case ir_unop_find_msb:
case ir_unop_b2f:
case ir_unop_i2f:
case ir_unop_u2f:
+ case ir_unop_d2f:
case ir_unop_bitcast_i2f:
case ir_unop_bitcast_u2f:
this->type = glsl_type::get_instance(GLSL_TYPE_FLOAT,
case ir_unop_f2b:
case ir_unop_i2b:
+ case ir_unop_d2b:
this->type = glsl_type::get_instance(GLSL_TYPE_BOOL,
op0->type->vector_elements, 1);
break;
+ case ir_unop_f2d:
+ case ir_unop_i2d:
+ case ir_unop_u2d:
+ this->type = glsl_type::get_instance(GLSL_TYPE_DOUBLE,
+ op0->type->vector_elements, 1);
+ break;
+
case ir_unop_i2u:
case ir_unop_f2u:
+ case ir_unop_d2u:
case ir_unop_bitcast_f2u:
this->type = glsl_type::get_instance(GLSL_TYPE_UINT,
op0->type->vector_elements, 1);
this->type = glsl_type::float_type;
break;
+ case ir_unop_unpack_double_2x32:
+ this->type = glsl_type::uvec2_type;
+ break;
+
case ir_unop_any:
this->type = glsl_type::bool_type;
break;
this->type = glsl_type::uint_type;
break;
+ case ir_unop_pack_double_2x32:
+ this->type = glsl_type::double_type;
+ break;
+
case ir_unop_unpack_snorm_2x16:
case ir_unop_unpack_unorm_2x16:
case ir_unop_unpack_half_2x16:
this->type = glsl_type::vec4_type;
break;
+ case ir_unop_frexp_sig:
+ this->type = op0->type;
+ break;
+ case ir_unop_frexp_exp:
+ this->type = glsl_type::get_instance(GLSL_TYPE_INT,
+ op0->type->vector_elements, 1);
+ break;
+
default:
assert(!"not reached: missing automatic type setup for ir_expression");
this->type = op0->type;
break;
case ir_binop_dot:
- this->type = glsl_type::float_type;
+ this->type = op0->type->get_base_type();
break;
case ir_binop_pack_half_2x16_split:
"u2f",
"i2u",
"u2i",
+ "d2f",
+ "f2d",
+ "d2i",
+ "i2d",
+ "d2u",
+ "u2d",
+ "d2b",
"bitcast_i2f",
"bitcast_f2i",
"bitcast_u2f",
"find_msb",
"find_lsb",
"sat",
+ "packDouble2x32",
+ "unpackDouble2x32",
+ "frexp_sig",
+ "frexp_exp",
"noise",
"interpolate_at_centroid",
"+",
}
}
+ir_constant::ir_constant(double d, unsigned vector_elements)
+ : ir_rvalue(ir_type_constant)
+{
+ assert(vector_elements <= 4);
+ this->type = glsl_type::get_instance(GLSL_TYPE_DOUBLE, vector_elements, 1);
+ for (unsigned i = 0; i < vector_elements; i++) {
+ this->value.d[i] = d;
+ }
+ for (unsigned i = vector_elements; i < 16; i++) {
+ this->value.d[i] = 0.0;
+ }
+}
+
ir_constant::ir_constant(unsigned int u, unsigned vector_elements)
: ir_rvalue(ir_type_constant)
{
case GLSL_TYPE_INT: this->value.i[0] = c->value.i[i]; break;
case GLSL_TYPE_FLOAT: this->value.f[0] = c->value.f[i]; break;
case GLSL_TYPE_BOOL: this->value.b[0] = c->value.b[i]; break;
+ case GLSL_TYPE_DOUBLE: this->value.d[0] = c->value.d[i]; break;
default: assert(!"Should not get here."); break;
}
}
if (value->type->is_scalar() && value->next->is_tail_sentinel()) {
if (type->is_matrix()) {
/* Matrix - fill diagonal (rest is already set to 0) */
- assert(type->base_type == GLSL_TYPE_FLOAT);
- for (unsigned i = 0; i < type->matrix_columns; i++)
- this->value.f[i * type->vector_elements + i] = value->value.f[0];
+ assert(type->base_type == GLSL_TYPE_FLOAT ||
+ type->base_type == GLSL_TYPE_DOUBLE);
+ for (unsigned i = 0; i < type->matrix_columns; i++) {
+ if (type->base_type == GLSL_TYPE_FLOAT)
+ this->value.f[i * type->vector_elements + i] =
+ value->value.f[0];
+ else
+ this->value.d[i * type->vector_elements + i] =
+ value->value.d[0];
+ }
} else {
/* Vector or scalar - fill all components */
switch (type->base_type) {
for (unsigned i = 0; i < type->components(); i++)
this->value.f[i] = value->value.f[0];
break;
+ case GLSL_TYPE_DOUBLE:
+ for (unsigned i = 0; i < type->components(); i++)
+ this->value.d[i] = value->value.d[0];
+ break;
case GLSL_TYPE_BOOL:
for (unsigned i = 0; i < type->components(); i++)
this->value.b[i] = value->value.b[0];
case GLSL_TYPE_BOOL:
this->value.b[i] = value->get_bool_component(j);
break;
+ case GLSL_TYPE_DOUBLE:
+ this->value.d[i] = value->get_double_component(j);
+ break;
default:
/* FINISHME: What to do? Exceptions are not the answer.
*/
case GLSL_TYPE_INT: return this->value.i[i] != 0;
case GLSL_TYPE_FLOAT: return ((int)this->value.f[i]) != 0;
case GLSL_TYPE_BOOL: return this->value.b[i];
+ case GLSL_TYPE_DOUBLE: return this->value.d[i] != 0.0;
default: assert(!"Should not get here."); break;
}
case GLSL_TYPE_INT: return (float) this->value.i[i];
case GLSL_TYPE_FLOAT: return this->value.f[i];
case GLSL_TYPE_BOOL: return this->value.b[i] ? 1.0f : 0.0f;
+ case GLSL_TYPE_DOUBLE: return (float) this->value.d[i];
+ default: assert(!"Should not get here."); break;
+ }
+
+ /* Must return something to make the compiler happy. This is clearly an
+ * error case.
+ */
+ return 0.0;
+}
+
+double
+ir_constant::get_double_component(unsigned i) const
+{
+ switch (this->type->base_type) {
+ case GLSL_TYPE_UINT: return (double) this->value.u[i];
+ case GLSL_TYPE_INT: return (double) this->value.i[i];
+ case GLSL_TYPE_FLOAT: return (double) this->value.f[i];
+ case GLSL_TYPE_BOOL: return this->value.b[i] ? 1.0 : 0.0;
+ case GLSL_TYPE_DOUBLE: return this->value.d[i];
default: assert(!"Should not get here."); break;
}
case GLSL_TYPE_INT: return this->value.i[i];
case GLSL_TYPE_FLOAT: return (int) this->value.f[i];
case GLSL_TYPE_BOOL: return this->value.b[i] ? 1 : 0;
+ case GLSL_TYPE_DOUBLE: return (int) this->value.d[i];
default: assert(!"Should not get here."); break;
}
case GLSL_TYPE_INT: return this->value.i[i];
case GLSL_TYPE_FLOAT: return (unsigned) this->value.f[i];
case GLSL_TYPE_BOOL: return this->value.b[i] ? 1 : 0;
+ case GLSL_TYPE_DOUBLE: return (unsigned) this->value.d[i];
default: assert(!"Should not get here."); break;
}
case GLSL_TYPE_UINT:
case GLSL_TYPE_INT:
case GLSL_TYPE_FLOAT:
+ case GLSL_TYPE_DOUBLE:
case GLSL_TYPE_BOOL: {
unsigned int size = src->type->components();
assert (size <= this->type->components() - offset);
case GLSL_TYPE_BOOL:
value.b[i+offset] = src->get_bool_component(i);
break;
+ case GLSL_TYPE_DOUBLE:
+ value.d[i+offset] = src->get_double_component(i);
+ break;
default: // Shut up the compiler
break;
}
case GLSL_TYPE_BOOL:
value.b[i+offset] = src->get_bool_component(id++);
break;
+ case GLSL_TYPE_DOUBLE:
+ value.d[i+offset] = src->get_double_component(id++);
+ break;
default:
assert(!"Should not get here.");
return;
if (this->value.b[i] != c->value.b[i])
return false;
break;
+ case GLSL_TYPE_DOUBLE:
+ if (this->value.d[i] != c->value.d[i])
+ return false;
+ break;
default:
assert(!"Should not get here.");
return false;
if (this->value.b[c] != bool(i))
return false;
break;
+ case GLSL_TYPE_DOUBLE:
+ if (this->value.d[c] != double(f))
+ return false;
+ break;
default:
/* The only other base types are structures, arrays, and samplers.
* Samplers cannot be constants, and the others should have been
ir_unop_u2f, /**< Unsigned-to-float conversion. */
ir_unop_i2u, /**< Integer-to-unsigned conversion. */
ir_unop_u2i, /**< Unsigned-to-integer conversion. */
+ ir_unop_d2f, /**< Double-to-float conversion. */
+ ir_unop_f2d, /**< Float-to-double conversion. */
+ ir_unop_d2i, /**< Double-to-integer conversion. */
+ ir_unop_i2d, /**< Integer-to-double conversion. */
+ ir_unop_d2u, /**< Double-to-unsigned conversion. */
+ ir_unop_u2d, /**< Unsigned-to-double conversion. */
+ ir_unop_d2b, /**< Double-to-boolean conversion. */
ir_unop_bitcast_i2f, /**< Bit-identical int-to-float "conversion" */
ir_unop_bitcast_f2i, /**< Bit-identical float-to-int "conversion" */
ir_unop_bitcast_u2f, /**< Bit-identical uint-to-float "conversion" */
/*@}*/
ir_unop_saturate,
+
+ /**
+ * \name Double packing, part of ARB_gpu_shader_fp64.
+ */
+ /*@{*/
+ ir_unop_pack_double_2x32,
+ ir_unop_unpack_double_2x32,
+ /*@}*/
+
+ ir_unop_frexp_sig,
+ ir_unop_frexp_exp,
+
ir_unop_noise,
/**
int i[16];
float f[16];
bool b[16];
+ double d[16];
};
ir_constant(unsigned int u, unsigned vector_elements=1);
ir_constant(int i, unsigned vector_elements=1);
ir_constant(float f, unsigned vector_elements=1);
+ ir_constant(double d, unsigned vector_elements=1);
/**
* Construct an ir_constant from a list of ir_constant values
/*@{*/
bool get_bool_component(unsigned i) const;
float get_float_component(unsigned i) const;
+ double get_double_component(unsigned i) const;
int get_int_component(unsigned i) const;
unsigned get_uint_component(unsigned i) const;
/*@}*/
case ir_unop_ceil:
case ir_unop_floor:
case ir_unop_fract:
+ assert(ir->operands[0]->type->base_type == GLSL_TYPE_FLOAT ||
+ ir->operands[0]->type->base_type == GLSL_TYPE_DOUBLE);
+ assert(ir->operands[0]->type == ir->type);
+ break;
case ir_unop_sin:
case ir_unop_cos:
case ir_unop_sin_reduced:
assert(ir->operands[0]->type == glsl_type::vec4_type);
break;
+ case ir_unop_pack_double_2x32:
+ assert(ir->type == glsl_type::double_type);
+ assert(ir->operands[0]->type == glsl_type::uvec2_type);
+ break;
+
case ir_unop_unpack_snorm_2x16:
case ir_unop_unpack_unorm_2x16:
case ir_unop_unpack_half_2x16:
assert(ir->operands[0]->type == glsl_type::uint_type);
break;
+ case ir_unop_unpack_double_2x32:
+ assert(ir->type == glsl_type::uvec2_type);
+ assert(ir->operands[0]->type == glsl_type::double_type);
+ break;
+
case ir_unop_bitfield_reverse:
assert(ir->operands[0]->type == ir->type);
assert(ir->type->is_integer());
assert(ir->operands[0]->type->is_float());
break;
+ case ir_unop_d2f:
+ assert(ir->operands[0]->type->base_type == GLSL_TYPE_DOUBLE);
+ assert(ir->type->base_type == GLSL_TYPE_FLOAT);
+ break;
+ case ir_unop_f2d:
+ assert(ir->operands[0]->type->base_type == GLSL_TYPE_FLOAT);
+ assert(ir->type->base_type == GLSL_TYPE_DOUBLE);
+ break;
+ case ir_unop_d2i:
+ assert(ir->operands[0]->type->base_type == GLSL_TYPE_DOUBLE);
+ assert(ir->type->base_type == GLSL_TYPE_INT);
+ break;
+ case ir_unop_i2d:
+ assert(ir->operands[0]->type->base_type == GLSL_TYPE_INT);
+ assert(ir->type->base_type == GLSL_TYPE_DOUBLE);
+ break;
+ case ir_unop_d2u:
+ assert(ir->operands[0]->type->base_type == GLSL_TYPE_DOUBLE);
+ assert(ir->type->base_type == GLSL_TYPE_UINT);
+ break;
+ case ir_unop_u2d:
+ assert(ir->operands[0]->type->base_type == GLSL_TYPE_UINT);
+ assert(ir->type->base_type == GLSL_TYPE_DOUBLE);
+ break;
+ case ir_unop_d2b:
+ assert(ir->operands[0]->type->base_type == GLSL_TYPE_DOUBLE);
+ assert(ir->type->base_type == GLSL_TYPE_BOOL);
+ break;
+
+ case ir_unop_frexp_sig:
+ assert(ir->operands[0]->type->base_type == GLSL_TYPE_FLOAT ||
+ ir->operands[0]->type->base_type == GLSL_TYPE_DOUBLE);
+ assert(ir->type->base_type == GLSL_TYPE_DOUBLE);
+ break;
+ case ir_unop_frexp_exp:
+ assert(ir->operands[0]->type->base_type == GLSL_TYPE_FLOAT ||
+ ir->operands[0]->type->base_type == GLSL_TYPE_DOUBLE);
+ assert(ir->type->base_type == GLSL_TYPE_INT);
+ break;
case ir_binop_add:
case ir_binop_sub:
case ir_binop_mul:
break;
case ir_binop_dot:
- assert(ir->type == glsl_type::float_type);
- assert(ir->operands[0]->type->base_type == GLSL_TYPE_FLOAT);
+ assert(ir->type == glsl_type::float_type ||
+ ir->type == glsl_type::double_type);
+ assert(ir->operands[0]->type->base_type == GLSL_TYPE_FLOAT ||
+ ir->operands[0]->type->base_type == GLSL_TYPE_DOUBLE);
assert(ir->operands[0]->type->is_vector());
assert(ir->operands[0]->type == ir->operands[1]->type);
break;
case ir_binop_ldexp:
assert(ir->operands[0]->type == ir->type);
- assert(ir->operands[0]->type->is_float());
+ assert(ir->operands[0]->type->is_float() ||
+ ir->operands[0]->type->is_double());
assert(ir->operands[1]->type->base_type == GLSL_TYPE_INT);
assert(ir->operands[0]->type->components() ==
ir->operands[1]->type->components());
break;
case ir_triop_fma:
- assert(ir->type->base_type == GLSL_TYPE_FLOAT);
+ assert(ir->type->base_type == GLSL_TYPE_FLOAT ||
+ ir->type->base_type == GLSL_TYPE_DOUBLE);
assert(ir->type == ir->operands[0]->type);
assert(ir->type == ir->operands[1]->type);
assert(ir->type == ir->operands[2]->type);
break;
case ir_triop_lrp:
- assert(ir->operands[0]->type->base_type == GLSL_TYPE_FLOAT);
+ assert(ir->operands[0]->type->base_type == GLSL_TYPE_FLOAT ||
+ ir->operands[0]->type->base_type == GLSL_TYPE_DOUBLE);
assert(ir->operands[0]->type == ir->operands[1]->type);
- assert(ir->operands[2]->type == ir->operands[0]->type || ir->operands[2]->type == glsl_type::float_type);
+ assert(ir->operands[2]->type == ir->operands[0]->type ||
+ ir->operands[2]->type == glsl_type::float_type ||
+ ir->operands[2]->type == glsl_type::double_type);
break;
case ir_triop_csel: