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.
This commit is contained in:
Kenneth Graunke
2011-02-25 14:29:36 -08:00
parent cb3317b85a
commit 233b88eab9
5 changed files with 42 additions and 33 deletions

View File

@@ -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) extra_dim = get_extra_dim(sampler_type, variant & Proj, unused_fields)
offset_dim = get_sampler_dim(sampler_type) offset_dim = get_sampler_dim(sampler_type)
# Print parameters
print " (signature",
if variant & Single: if variant & Single:
print "float" return_type = "float"
else: else:
print g + "vec4" return_type = g + "vec4"
# Print parameters
print " (signature", return_type
print " (parameters" print " (parameters"
print " (declare (in) " + g + "sampler" + sampler_type + " sampler)" print " (declare (in) " + g + "sampler" + sampler_type + " sampler)"
print " (declare (in) " + vec_type("i" if tex_inst == "txf" else "", coord_dim + extra_dim) + " P)", 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": if tex_inst == "txb":
print "\n (declare (in) float bias)", 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 # Coordinate
if extra_dim > 0: if extra_dim > 0:

View File

@@ -1150,22 +1150,18 @@ ir_texture::get_opcode(const char *str)
void void
ir_texture::set_sampler(ir_dereference *sampler) ir_texture::set_sampler(ir_dereference *sampler, const glsl_type *type)
{ {
assert(sampler != NULL); assert(sampler != NULL);
assert(type != NULL);
this->sampler = sampler; this->sampler = sampler;
this->type = type;
switch (sampler->type->sampler_type) { assert(sampler->type->sampler_type == type->base_type);
case GLSL_TYPE_FLOAT: if (sampler->type->sampler_shadow)
this->type = glsl_type::vec4_type; assert(type->vector_elements == 4 || type->vector_elements == 1);
break; else
case GLSL_TYPE_INT: assert(type->vector_elements == 4);
this->type = glsl_type::ivec4_type;
break;
case GLSL_TYPE_UINT:
this->type = glsl_type::uvec4_type;
break;
}
} }

View File

@@ -1196,11 +1196,11 @@ enum ir_texture_opcode {
* | | Shadow comparitor * | | Shadow comparitor
* | | | * | | |
* v v v * v v v
* (tex <sampler> <coordinate> 0 1 ( )) * (tex <type> <sampler> <coordinate> 0 1 ( ))
* (txb <sampler> <coordinate> 0 1 ( ) <bias>) * (txb <type> <sampler> <coordinate> 0 1 ( ) <bias>)
* (txl <sampler> <coordinate> 0 1 ( ) <lod>) * (txl <type> <sampler> <coordinate> 0 1 ( ) <lod>)
* (txd <sampler> <coordinate> 0 1 ( ) (dPdx dPdy)) * (txd <type> <sampler> <coordinate> 0 1 ( ) (dPdx dPdy))
* (txf <sampler> <coordinate> 0 <lod>) * (txf <type> <sampler> <coordinate> 0 <lod>)
*/ */
class ir_texture : public ir_rvalue { class ir_texture : public ir_rvalue {
public: public:
@@ -1226,8 +1226,8 @@ public:
*/ */
const char *opcode_string(); const char *opcode_string();
/** Set the sampler and infer the type. */ /** Set the sampler and type. */
void set_sampler(ir_dereference *sampler); void set_sampler(ir_dereference *sampler, const glsl_type *type);
/** /**
* Do a reverse-lookup to translate a string into an ir_texture_opcode. * Do a reverse-lookup to translate a string into an ir_texture_opcode.

View File

@@ -187,6 +187,9 @@ void ir_print_visitor::visit(ir_texture *ir)
{ {
printf("(%s ", ir->opcode_string()); printf("(%s ", ir->opcode_string());
print_type(ir->type);
printf(" ");
ir->sampler->accept(this); ir->sampler->accept(this);
printf(" "); printf(" ");

View File

@@ -869,6 +869,7 @@ ir_texture *
ir_reader::read_texture(s_expression *expr) ir_reader::read_texture(s_expression *expr)
{ {
s_symbol *tag = NULL; s_symbol *tag = NULL;
s_expression *s_type = NULL;
s_expression *s_sampler = NULL; s_expression *s_sampler = NULL;
s_expression *s_coord = NULL; s_expression *s_coord = NULL;
s_expression *s_offset = 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 */ ir_texture_opcode op = ir_tex; /* silence warning */
s_pattern tex_pattern[] = 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[] = 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[] = 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)) { if (MATCH(expr, tex_pattern)) {
op = ir_tex; op = ir_tex;
@@ -900,6 +901,14 @@ ir_reader::read_texture(s_expression *expr)
ir_texture *tex = new(mem_ctx) ir_texture(op); 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) // Read sampler (must be a deref)
ir_dereference *sampler = read_dereference(s_sampler); ir_dereference *sampler = read_dereference(s_sampler);
if (sampler == NULL) { if (sampler == NULL) {
@@ -907,7 +916,7 @@ ir_reader::read_texture(s_expression *expr)
tex->opcode_string()); tex->opcode_string());
return NULL; return NULL;
} }
tex->set_sampler(sampler); tex->set_sampler(sampler, type);
// Read coordinate (any rvalue) // Read coordinate (any rvalue)
tex->coordinate = read_rvalue(s_coord); tex->coordinate = read_rvalue(s_coord);