[Mesa-dev] [PATCH v4] glsl: Add double builtin type generation
Ilia Mirkin
imirkin at alum.mit.edu
Mon Feb 9 00:58:58 PST 2015
From: Dave Airlie <airlied at gmail.com>
Signed-off-by: Dave Airlie <airlied at redhat.com>
Reviewed-by: Matt Turner <mattst88 at gmail.com>
Reviewed-by: Ian Romanick <ian.d.romanick at intel.com>
---
Made component_slots() return 2 instead of 1 for double. Also added to
list for uniform_locations(), returning 1.
src/glsl/builtin_type_macros.h | 16 ++++++
src/glsl/builtin_types.cpp | 30 +++++++++++
src/glsl/glsl_parser_extras.h | 5 ++
src/glsl/glsl_types.cpp | 112 +++++++++++++++++++++++++++++++++--------
src/glsl/glsl_types.h | 19 ++++++-
5 files changed, 159 insertions(+), 23 deletions(-)
diff --git a/src/glsl/builtin_type_macros.h b/src/glsl/builtin_type_macros.h
index 236e1ce..bf74eb3 100644
--- a/src/glsl/builtin_type_macros.h
+++ b/src/glsl/builtin_type_macros.h
@@ -64,6 +64,22 @@ DECL_TYPE(mat3x4, GL_FLOAT_MAT3x4, GLSL_TYPE_FLOAT, 4, 3)
DECL_TYPE(mat4x2, GL_FLOAT_MAT4x2, GLSL_TYPE_FLOAT, 2, 4)
DECL_TYPE(mat4x3, GL_FLOAT_MAT4x3, GLSL_TYPE_FLOAT, 3, 4)
+DECL_TYPE(double, GL_DOUBLE, GLSL_TYPE_DOUBLE, 1, 1)
+DECL_TYPE(dvec2, GL_DOUBLE_VEC2, GLSL_TYPE_DOUBLE, 2, 1)
+DECL_TYPE(dvec3, GL_DOUBLE_VEC3, GLSL_TYPE_DOUBLE, 3, 1)
+DECL_TYPE(dvec4, GL_DOUBLE_VEC4, GLSL_TYPE_DOUBLE, 4, 1)
+
+DECL_TYPE(dmat2, GL_DOUBLE_MAT2, GLSL_TYPE_DOUBLE, 2, 2)
+DECL_TYPE(dmat3, GL_DOUBLE_MAT3, GLSL_TYPE_DOUBLE, 3, 3)
+DECL_TYPE(dmat4, GL_DOUBLE_MAT4, GLSL_TYPE_DOUBLE, 4, 4)
+
+DECL_TYPE(dmat2x3, GL_DOUBLE_MAT2x3, GLSL_TYPE_DOUBLE, 3, 2)
+DECL_TYPE(dmat2x4, GL_DOUBLE_MAT2x4, GLSL_TYPE_DOUBLE, 4, 2)
+DECL_TYPE(dmat3x2, GL_DOUBLE_MAT3x2, GLSL_TYPE_DOUBLE, 2, 3)
+DECL_TYPE(dmat3x4, GL_DOUBLE_MAT3x4, GLSL_TYPE_DOUBLE, 4, 3)
+DECL_TYPE(dmat4x2, GL_DOUBLE_MAT4x2, GLSL_TYPE_DOUBLE, 2, 4)
+DECL_TYPE(dmat4x3, GL_DOUBLE_MAT4x3, GLSL_TYPE_DOUBLE, 3, 4)
+
DECL_TYPE(sampler1D, GL_SAMPLER_1D, GLSL_TYPE_SAMPLER, GLSL_SAMPLER_DIM_1D, 0, 0, GLSL_TYPE_FLOAT)
DECL_TYPE(sampler2D, GL_SAMPLER_2D, GLSL_TYPE_SAMPLER, GLSL_SAMPLER_DIM_2D, 0, 0, GLSL_TYPE_FLOAT)
DECL_TYPE(sampler3D, GL_SAMPLER_3D, GLSL_TYPE_SAMPLER, GLSL_SAMPLER_DIM_3D, 0, 0, GLSL_TYPE_FLOAT)
diff --git a/src/glsl/builtin_types.cpp b/src/glsl/builtin_types.cpp
index 10fac0f..fef86df 100644
--- a/src/glsl/builtin_types.cpp
+++ b/src/glsl/builtin_types.cpp
@@ -159,6 +159,20 @@ const static struct builtin_type_versions {
T(mat4x2, 120, 300)
T(mat4x3, 120, 300)
+ T(double, 400, 999)
+ T(dvec2, 400, 999)
+ T(dvec3, 400, 999)
+ T(dvec4, 400, 999)
+ T(dmat2, 400, 999)
+ T(dmat3, 400, 999)
+ T(dmat4, 400, 999)
+ T(dmat2x3, 400, 999)
+ T(dmat2x4, 400, 999)
+ T(dmat3x2, 400, 999)
+ T(dmat3x4, 400, 999)
+ T(dmat4x2, 400, 999)
+ T(dmat4x3, 400, 999)
+
T(sampler1D, 110, 999)
T(sampler2D, 110, 100)
T(sampler3D, 110, 300)
@@ -361,5 +375,21 @@ _mesa_glsl_initialize_types(struct _mesa_glsl_parse_state *state)
if (state->ARB_shader_atomic_counters_enable) {
add_type(symbols, glsl_type::atomic_uint_type);
}
+
+ if (state->ARB_gpu_shader_fp64_enable) {
+ add_type(symbols, glsl_type::double_type);
+ add_type(symbols, glsl_type::dvec2_type);
+ add_type(symbols, glsl_type::dvec3_type);
+ add_type(symbols, glsl_type::dvec4_type);
+ add_type(symbols, glsl_type::dmat2_type);
+ add_type(symbols, glsl_type::dmat3_type);
+ add_type(symbols, glsl_type::dmat4_type);
+ add_type(symbols, glsl_type::dmat2x3_type);
+ add_type(symbols, glsl_type::dmat2x4_type);
+ add_type(symbols, glsl_type::dmat3x2_type);
+ add_type(symbols, glsl_type::dmat3x4_type);
+ add_type(symbols, glsl_type::dmat4x2_type);
+ add_type(symbols, glsl_type::dmat4x3_type);
+ }
}
/** @} */
diff --git a/src/glsl/glsl_parser_extras.h b/src/glsl/glsl_parser_extras.h
index dafee4e..ea53270 100644
--- a/src/glsl/glsl_parser_extras.h
+++ b/src/glsl/glsl_parser_extras.h
@@ -205,6 +205,11 @@ struct _mesa_glsl_parse_state {
|| EXT_separate_shader_objects_enable;
}
+ bool has_double() const
+ {
+ return ARB_gpu_shader_fp64_enable || is_version(400, 0);
+ }
+
void process_version_directive(YYLTYPE *locp, int version,
const char *ident);
diff --git a/src/glsl/glsl_types.cpp b/src/glsl/glsl_types.cpp
index b4223f4..f6c990f 100644
--- a/src/glsl/glsl_types.cpp
+++ b/src/glsl/glsl_types.cpp
@@ -194,6 +194,22 @@ glsl_type::contains_integer() const
}
bool
+glsl_type::contains_double() const
+{
+ if (this->is_array()) {
+ return this->fields.array->contains_double();
+ } else if (this->is_record()) {
+ for (unsigned int i = 0; i < this->length; i++) {
+ if (this->fields.structure[i].type->contains_double())
+ return true;
+ }
+ return false;
+ } else {
+ return this->is_double();
+ }
+}
+
+bool
glsl_type::contains_opaque() const {
switch (base_type) {
case GLSL_TYPE_SAMPLER:
@@ -268,6 +284,8 @@ const glsl_type *glsl_type::get_base_type() const
return int_type;
case GLSL_TYPE_FLOAT:
return float_type;
+ case GLSL_TYPE_DOUBLE:
+ return double_type;
case GLSL_TYPE_BOOL:
return bool_type;
default:
@@ -292,6 +310,8 @@ const glsl_type *glsl_type::get_scalar_type() const
return int_type;
case GLSL_TYPE_FLOAT:
return float_type;
+ case GLSL_TYPE_DOUBLE:
+ return double_type;
case GLSL_TYPE_BOOL:
return bool_type;
default:
@@ -377,6 +397,17 @@ glsl_type::vec(unsigned components)
return ts[components - 1];
}
+const glsl_type *
+glsl_type::dvec(unsigned components)
+{
+ if (components == 0 || components > 4)
+ return error_type;
+
+ static const glsl_type *const ts[] = {
+ double_type, dvec2_type, dvec3_type, dvec4_type
+ };
+ return ts[components - 1];
+}
const glsl_type *
glsl_type::ivec(unsigned components)
@@ -436,13 +467,15 @@ glsl_type::get_instance(unsigned base_type, unsigned rows, unsigned columns)
return ivec(rows);
case GLSL_TYPE_FLOAT:
return vec(rows);
+ case GLSL_TYPE_DOUBLE:
+ return dvec(rows);
case GLSL_TYPE_BOOL:
return bvec(rows);
default:
return error_type;
}
} else {
- if ((base_type != GLSL_TYPE_FLOAT) || (rows == 1))
+ if ((base_type != GLSL_TYPE_FLOAT && base_type != GLSL_TYPE_DOUBLE) || (rows == 1))
return error_type;
/* GLSL matrix types are named mat{COLUMNS}x{ROWS}. Only the following
@@ -456,17 +489,32 @@ glsl_type::get_instance(unsigned base_type, unsigned rows, unsigned columns)
*/
#define IDX(c,r) (((c-1)*3) + (r-1))
- switch (IDX(columns, rows)) {
- case IDX(2,2): return mat2_type;
- case IDX(2,3): return mat2x3_type;
- case IDX(2,4): return mat2x4_type;
- case IDX(3,2): return mat3x2_type;
- case IDX(3,3): return mat3_type;
- case IDX(3,4): return mat3x4_type;
- case IDX(4,2): return mat4x2_type;
- case IDX(4,3): return mat4x3_type;
- case IDX(4,4): return mat4_type;
- default: return error_type;
+ if (base_type == GLSL_TYPE_DOUBLE) {
+ switch (IDX(columns, rows)) {
+ case IDX(2,2): return dmat2_type;
+ case IDX(2,3): return dmat2x3_type;
+ case IDX(2,4): return dmat2x4_type;
+ case IDX(3,2): return dmat3x2_type;
+ case IDX(3,3): return dmat3_type;
+ case IDX(3,4): return dmat3x4_type;
+ case IDX(4,2): return dmat4x2_type;
+ case IDX(4,3): return dmat4x3_type;
+ case IDX(4,4): return dmat4_type;
+ default: return error_type;
+ }
+ } else {
+ switch (IDX(columns, rows)) {
+ case IDX(2,2): return mat2_type;
+ case IDX(2,3): return mat2x3_type;
+ case IDX(2,4): return mat2x4_type;
+ case IDX(3,2): return mat3x2_type;
+ case IDX(3,3): return mat3_type;
+ case IDX(3,4): return mat3x4_type;
+ case IDX(4,2): return mat4x2_type;
+ case IDX(4,3): return mat4x3_type;
+ case IDX(4,4): return mat4_type;
+ default: return error_type;
+ }
}
}
@@ -818,6 +866,9 @@ glsl_type::component_slots() const
case GLSL_TYPE_BOOL:
return this->components();
+ case GLSL_TYPE_DOUBLE:
+ return 2 * this->components();
+
case GLSL_TYPE_STRUCT:
case GLSL_TYPE_INTERFACE: {
unsigned size = 0;
@@ -853,6 +904,7 @@ glsl_type::uniform_locations() const
case GLSL_TYPE_UINT:
case GLSL_TYPE_INT:
case GLSL_TYPE_FLOAT:
+ case GLSL_TYPE_DOUBLE:
case GLSL_TYPE_BOOL:
case GLSL_TYPE_SAMPLER:
case GLSL_TYPE_IMAGE:
@@ -897,12 +949,26 @@ glsl_type::can_implicitly_convert_to(const glsl_type *desired,
desired->base_type == GLSL_TYPE_UINT && this->base_type == GLSL_TYPE_INT)
return true;
+ /* No implicit conversions from double. */
+ if ((!state || state->has_double()) && this->is_double())
+ return false;
+
+ /* Conversions from different types to double. */
+ if ((!state || state->has_double()) && desired->is_double()) {
+ if (this->is_float())
+ return true;
+ if (this->is_integer())
+ return true;
+ }
+
return false;
}
unsigned
glsl_type::std140_base_alignment(bool row_major) const
{
+ unsigned N = is_double() ? 8 : 4;
+
/* (1) If the member is a scalar consuming <N> basic machine units, the
* base alignment is <N>.
*
@@ -916,12 +982,12 @@ glsl_type::std140_base_alignment(bool row_major) const
if (this->is_scalar() || this->is_vector()) {
switch (this->vector_elements) {
case 1:
- return 4;
+ return N;
case 2:
- return 8;
+ return 2 * N;
case 3:
case 4:
- return 16;
+ return 4 * N;
}
}
@@ -970,10 +1036,10 @@ glsl_type::std140_base_alignment(bool row_major) const
int r = this->vector_elements;
if (row_major) {
- vec_type = get_instance(GLSL_TYPE_FLOAT, c, 1);
+ vec_type = get_instance(base_type, c, 1);
array_type = glsl_type::get_array_instance(vec_type, r);
} else {
- vec_type = get_instance(GLSL_TYPE_FLOAT, r, 1);
+ vec_type = get_instance(base_type, r, 1);
array_type = glsl_type::get_array_instance(vec_type, c);
}
@@ -1018,6 +1084,8 @@ glsl_type::std140_base_alignment(bool row_major) const
unsigned
glsl_type::std140_size(bool row_major) const
{
+ unsigned N = is_double() ? 8 : 4;
+
/* (1) If the member is a scalar consuming <N> basic machine units, the
* base alignment is <N>.
*
@@ -1029,7 +1097,7 @@ glsl_type::std140_size(bool row_major) const
* <N> basic machine units, the base alignment is 4<N>.
*/
if (this->is_scalar() || this->is_vector()) {
- return this->vector_elements * 4;
+ return this->vector_elements * N;
}
/* (5) If the member is a column-major matrix with <C> columns and
@@ -1064,11 +1132,12 @@ glsl_type::std140_size(bool row_major) const
}
if (row_major) {
- vec_type = get_instance(GLSL_TYPE_FLOAT,
- element_type->matrix_columns, 1);
+ vec_type = get_instance(base_type,
+ element_type->matrix_columns, 1);
+
array_len *= element_type->vector_elements;
} else {
- vec_type = get_instance(GLSL_TYPE_FLOAT,
+ vec_type = get_instance(base_type,
element_type->vector_elements, 1);
array_len *= element_type->matrix_columns;
}
@@ -1171,6 +1240,7 @@ glsl_type::count_attribute_slots() const
case GLSL_TYPE_INT:
case GLSL_TYPE_FLOAT:
case GLSL_TYPE_BOOL:
+ case GLSL_TYPE_DOUBLE:
return this->matrix_columns;
case GLSL_TYPE_STRUCT:
diff --git a/src/glsl/glsl_types.h b/src/glsl/glsl_types.h
index f0d4ea8..5dc7e45 100644
--- a/src/glsl/glsl_types.h
+++ b/src/glsl/glsl_types.h
@@ -200,6 +200,7 @@ struct glsl_type {
* @{
*/
static const glsl_type *vec(unsigned components);
+ static const glsl_type *dvec(unsigned components);
static const glsl_type *ivec(unsigned components);
static const glsl_type *uvec(unsigned components);
static const glsl_type *bvec(unsigned components);
@@ -388,7 +389,7 @@ struct glsl_type {
bool is_matrix() const
{
/* GLSL only has float matrices. */
- return (matrix_columns > 1) && (base_type == GLSL_TYPE_FLOAT);
+ return (matrix_columns > 1) && (base_type == GLSL_TYPE_FLOAT || base_type == GLSL_TYPE_DOUBLE);
}
/**
@@ -396,7 +397,7 @@ struct glsl_type {
*/
bool is_numeric() const
{
- return (base_type >= GLSL_TYPE_UINT) && (base_type <= GLSL_TYPE_FLOAT);
+ return (base_type >= GLSL_TYPE_UINT) && (base_type <= GLSL_TYPE_DOUBLE);
}
/**
@@ -414,6 +415,12 @@ struct glsl_type {
bool contains_integer() const;
/**
+ * Query whether or not type is a double type, or for struct and array
+ * types, contains a double type.
+ */
+ bool contains_double() const;
+
+ /**
* Query whether or not a type is a float type
*/
bool is_float() const
@@ -422,6 +429,14 @@ struct glsl_type {
}
/**
+ * Query whether or not a type is a double type
+ */
+ bool is_double() const
+ {
+ return base_type == GLSL_TYPE_DOUBLE;
+ }
+
+ /**
* Query whether or not a type is a non-array boolean type
*/
bool is_boolean() const
--
2.0.5
More information about the mesa-dev
mailing list