From 233b88eab9d8095523ebae3c4be1dbf2e2bd856a Mon Sep 17 00:00:00 2001 From: Kenneth Graunke Date: Fri, 25 Feb 2011 14:29:36 -0800 Subject: [PATCH] glsl: Explicitly specify a type when reading/printing ir_texture. This is necessary for GLSL 1.30+ shadow sampling functions, which return a single float rather than splatting the value to a vec4 based on GL_DEPTH_TEXTURE_MODE. --- src/glsl/builtins/tools/texture_builtins.py | 11 ++++++----- src/glsl/ir.cpp | 20 ++++++++------------ src/glsl/ir.h | 24 ++++++++++++------------ src/glsl/ir_print_visitor.cpp | 3 +++ src/glsl/ir_reader.cpp | 17 +++++++++++++---- 5 files changed, 42 insertions(+), 33 deletions(-) diff --git a/src/glsl/builtins/tools/texture_builtins.py b/src/glsl/builtins/tools/texture_builtins.py index 2792dd8..2fbe790 100755 --- a/src/glsl/builtins/tools/texture_builtins.py +++ b/src/glsl/builtins/tools/texture_builtins.py @@ -49,12 +49,13 @@ def generate_sigs(g, tex_inst, sampler_type, variant = 0, unused_fields = 0): extra_dim = get_extra_dim(sampler_type, variant & Proj, unused_fields) offset_dim = get_sampler_dim(sampler_type) - # Print parameters - print " (signature", if variant & Single: - print "float" + return_type = "float" else: - print g + "vec4" + return_type = g + "vec4" + + # Print parameters + print " (signature", return_type print " (parameters" print " (declare (in) " + g + "sampler" + sampler_type + " sampler)" print " (declare (in) " + vec_type("i" if tex_inst == "txf" else "", coord_dim + extra_dim) + " P)", @@ -72,7 +73,7 @@ def generate_sigs(g, tex_inst, sampler_type, variant = 0, unused_fields = 0): if tex_inst == "txb": print "\n (declare (in) float bias)", - print ")\n ((return (" + tex_inst + " (var_ref sampler)", + print ")\n ((return (" + tex_inst, return_type, "(var_ref sampler)", # Coordinate if extra_dim > 0: diff --git a/src/glsl/ir.cpp b/src/glsl/ir.cpp index fc356ba..a55b7ef 100644 --- a/src/glsl/ir.cpp +++ b/src/glsl/ir.cpp @@ -1150,22 +1150,18 @@ ir_texture::get_opcode(const char *str) void -ir_texture::set_sampler(ir_dereference *sampler) +ir_texture::set_sampler(ir_dereference *sampler, const glsl_type *type) { assert(sampler != NULL); + assert(type != NULL); this->sampler = sampler; + this->type = type; - switch (sampler->type->sampler_type) { - case GLSL_TYPE_FLOAT: - this->type = glsl_type::vec4_type; - break; - case GLSL_TYPE_INT: - this->type = glsl_type::ivec4_type; - break; - case GLSL_TYPE_UINT: - this->type = glsl_type::uvec4_type; - break; - } + assert(sampler->type->sampler_type == type->base_type); + if (sampler->type->sampler_shadow) + assert(type->vector_elements == 4 || type->vector_elements == 1); + else + assert(type->vector_elements == 4); } diff --git a/src/glsl/ir.h b/src/glsl/ir.h index f2f902c..39d4ebc 100644 --- a/src/glsl/ir.h +++ b/src/glsl/ir.h @@ -1191,16 +1191,16 @@ enum ir_texture_opcode { * selected from \c ir_texture_opcodes. In the printed IR, these will * appear as: * - * Texel offset (0 or an expression) - * | Projection divisor - * | | Shadow comparitor - * | | | - * v v v - * (tex 0 1 ( )) - * (txb 0 1 ( ) ) - * (txl 0 1 ( ) ) - * (txd 0 1 ( ) (dPdx dPdy)) - * (txf 0 ) + * Texel offset (0 or an expression) + * | Projection divisor + * | | Shadow comparitor + * | | | + * v v v + * (tex 0 1 ( )) + * (txb 0 1 ( ) ) + * (txl 0 1 ( ) ) + * (txd 0 1 ( ) (dPdx dPdy)) + * (txf 0 ) */ class ir_texture : public ir_rvalue { public: @@ -1226,8 +1226,8 @@ public: */ const char *opcode_string(); - /** Set the sampler and infer the type. */ - void set_sampler(ir_dereference *sampler); + /** Set the sampler and type. */ + void set_sampler(ir_dereference *sampler, const glsl_type *type); /** * Do a reverse-lookup to translate a string into an ir_texture_opcode. diff --git a/src/glsl/ir_print_visitor.cpp b/src/glsl/ir_print_visitor.cpp index 82ccc72..a84f8df 100644 --- a/src/glsl/ir_print_visitor.cpp +++ b/src/glsl/ir_print_visitor.cpp @@ -187,6 +187,9 @@ void ir_print_visitor::visit(ir_texture *ir) { printf("(%s ", ir->opcode_string()); + print_type(ir->type); + printf(" "); + ir->sampler->accept(this); printf(" "); diff --git a/src/glsl/ir_reader.cpp b/src/glsl/ir_reader.cpp index af85e06..30df257 100644 --- a/src/glsl/ir_reader.cpp +++ b/src/glsl/ir_reader.cpp @@ -869,6 +869,7 @@ ir_texture * ir_reader::read_texture(s_expression *expr) { s_symbol *tag = NULL; + s_expression *s_type = NULL; s_expression *s_sampler = NULL; s_expression *s_coord = NULL; s_expression *s_offset = NULL; @@ -879,11 +880,11 @@ ir_reader::read_texture(s_expression *expr) ir_texture_opcode op = ir_tex; /* silence warning */ s_pattern tex_pattern[] = - { "tex", s_sampler, s_coord, s_offset, s_proj, s_shadow }; + { "tex", s_type, s_sampler, s_coord, s_offset, s_proj, s_shadow }; s_pattern txf_pattern[] = - { "txf", s_sampler, s_coord, s_offset, s_lod }; + { "txf", s_type, s_sampler, s_coord, s_offset, s_lod }; s_pattern other_pattern[] = - { tag, s_sampler, s_coord, s_offset, s_proj, s_shadow, s_lod }; + { tag, s_type, s_sampler, s_coord, s_offset, s_proj, s_shadow, s_lod }; if (MATCH(expr, tex_pattern)) { op = ir_tex; @@ -900,6 +901,14 @@ ir_reader::read_texture(s_expression *expr) ir_texture *tex = new(mem_ctx) ir_texture(op); + // Read return type + const glsl_type *type = read_type(s_type); + if (type == NULL) { + ir_read_error(NULL, "when reading type in (%s ...)", + tex->opcode_string()); + return NULL; + } + // Read sampler (must be a deref) ir_dereference *sampler = read_dereference(s_sampler); if (sampler == NULL) { @@ -907,7 +916,7 @@ ir_reader::read_texture(s_expression *expr) tex->opcode_string()); return NULL; } - tex->set_sampler(sampler); + tex->set_sampler(sampler, type); // Read coordinate (any rvalue) tex->coordinate = read_rvalue(s_coord); -- 2.7.4