aboutsummaryrefslogtreecommitdiff
path: root/mesalib/src
diff options
context:
space:
mode:
authormarha <marha@users.sourceforge.net>2014-07-19 15:00:38 +0200
committermarha <marha@users.sourceforge.net>2014-07-19 15:00:38 +0200
commitd0c30e7945e76ac119f6d867e27137c8a76f7e15 (patch)
tree1bfb3148a6f43bdd32746c5b882f9f083076cf91 /mesalib/src
parente708bebcc029873004ade4241f347ce8c58896af (diff)
downloadvcxsrv-d0c30e7945e76ac119f6d867e27137c8a76f7e15.tar.gz
vcxsrv-d0c30e7945e76ac119f6d867e27137c8a76f7e15.tar.bz2
vcxsrv-d0c30e7945e76ac119f6d867e27137c8a76f7e15.zip
fontconfig plink libX11 libxcb mesa git update 19 July 2014
plink revision 10207 xserver commit cfa302d6224d10860e60491333950544c4fb9b04 libxcb commit 49a61c8b459ab19c7f39e653bbb0d0339ea8f00f libX11 commit 5525e8433f93bce464412f27cffa203ea628f368 fontconfig commit 6781c6baef062eeea5b5b68e4a9c31ea6cd7539b mesa commit f6fc80734533140a69b30361fe0d4773a03515db
Diffstat (limited to 'mesalib/src')
-rw-r--r--mesalib/src/glsl/ast_function.cpp35
-rw-r--r--mesalib/src/glsl/ast_to_hir.cpp87
-rw-r--r--mesalib/src/glsl/builtin_functions.cpp67
-rw-r--r--mesalib/src/glsl/glsl_parser.yy8
-rw-r--r--mesalib/src/glsl/glsl_parser_extras.cpp2
-rw-r--r--mesalib/src/glsl/glsl_parser_extras.h5
-rw-r--r--mesalib/src/glsl/ir.cpp6
-rw-r--r--mesalib/src/glsl/ir.h33
-rw-r--r--mesalib/src/glsl/ir_builder.cpp18
-rw-r--r--mesalib/src/glsl/ir_builder.h4
-rw-r--r--mesalib/src/glsl/ir_constant_expression.cpp2
-rw-r--r--mesalib/src/glsl/ir_hierarchical_visitor.cpp158
-rw-r--r--mesalib/src/glsl/ir_hierarchical_visitor.h29
-rw-r--r--mesalib/src/glsl/ir_reader.cpp7
-rw-r--r--mesalib/src/glsl/ir_validate.cpp30
-rw-r--r--mesalib/src/glsl/list.h40
-rw-r--r--mesalib/src/glsl/opt_function_inlining.cpp7
-rw-r--r--mesalib/src/glsl/opt_rebalance_tree.cpp23
-rw-r--r--mesalib/src/mapi/glapi/gen/gl_gentable.py4
-rw-r--r--mesalib/src/mesa/drivers/dri/Makefile.am3
-rw-r--r--mesalib/src/mesa/drivers/dri/common/drirc20
-rw-r--r--mesalib/src/mesa/drivers/dri/common/xmlpool/t_options.h5
-rw-r--r--mesalib/src/mesa/main/arrayobj.c15
-rw-r--r--mesalib/src/mesa/main/format_pack.c2
-rw-r--r--mesalib/src/mesa/main/mtypes.h19
-rw-r--r--mesalib/src/mesa/main/pack.c16
-rw-r--r--mesalib/src/mesa/main/texparam.c22
-rw-r--r--mesalib/src/mesa/program/ir_to_mesa.cpp8
-rw-r--r--mesalib/src/mesa/state_tracker/st_extensions.c3
-rw-r--r--mesalib/src/mesa/state_tracker/st_glsl_to_tgsi.cpp11
-rw-r--r--mesalib/src/mesa/vbo/vbo_context.h22
-rw-r--r--mesalib/src/mesa/vbo/vbo_exec.c15
32 files changed, 572 insertions, 154 deletions
diff --git a/mesalib/src/glsl/ast_function.cpp b/mesalib/src/glsl/ast_function.cpp
index cdb34cc69..4981fe174 100644
--- a/mesalib/src/glsl/ast_function.cpp
+++ b/mesalib/src/glsl/ast_function.cpp
@@ -178,6 +178,24 @@ verify_parameter_modes(_mesa_glsl_parse_state *state,
return false;
}
+ /* Verify that shader_in parameters are shader inputs */
+ if (formal->data.must_be_shader_input) {
+ ir_variable *var = actual->variable_referenced();
+ if (var && var->data.mode != ir_var_shader_in) {
+ _mesa_glsl_error(&loc, state,
+ "parameter `%s` must be a shader input",
+ formal->name);
+ return false;
+ }
+
+ if (actual->ir_type == ir_type_swizzle) {
+ _mesa_glsl_error(&loc, state,
+ "parameter `%s` must not be swizzled",
+ formal->name);
+ return false;
+ }
+ }
+
/* Verify that 'out' and 'inout' actual parameters are lvalues. */
if (formal->data.mode == ir_var_function_out
|| formal->data.mode == ir_var_function_inout) {
@@ -742,11 +760,22 @@ process_vec_mat_constructor(exec_list *instructions,
instructions->push_tail(var);
int i = 0;
+
foreach_in_list(ir_rvalue, rhs, &actual_parameters) {
- ir_rvalue *lhs = new(ctx) ir_dereference_array(var,
- new(ctx) ir_constant(i));
+ ir_instruction *assignment = NULL;
+
+ if (var->type->is_matrix()) {
+ ir_rvalue *lhs = new(ctx) ir_dereference_array(var,
+ new(ctx) ir_constant(i));
+ assignment = new(ctx) ir_assignment(lhs, rhs, NULL);
+ } else {
+ /* use writemask rather than index for vector */
+ assert(var->type->is_vector());
+ assert(i < 4);
+ ir_dereference *lhs = new(ctx) ir_dereference_variable(var);
+ assignment = new(ctx) ir_assignment(lhs, rhs, NULL, (unsigned)(1 << i));
+ }
- ir_instruction *assignment = new(ctx) ir_assignment(lhs, rhs, NULL);
instructions->push_tail(assignment);
i++;
diff --git a/mesalib/src/glsl/ast_to_hir.cpp b/mesalib/src/glsl/ast_to_hir.cpp
index 885bee547..328cd1b1b 100644
--- a/mesalib/src/glsl/ast_to_hir.cpp
+++ b/mesalib/src/glsl/ast_to_hir.cpp
@@ -4513,6 +4513,12 @@ ast_switch_statement::hir(exec_list *instructions,
instructions->push_tail(new(ctx) ir_assignment(deref_is_break_var,
is_break_val));
+ state->switch_state.run_default =
+ new(ctx) ir_variable(glsl_type::bool_type,
+ "run_default_tmp",
+ ir_var_temporary);
+ instructions->push_tail(state->switch_state.run_default);
+
/* Cache test expression.
*/
test_to_hir(instructions, state);
@@ -4567,8 +4573,71 @@ ir_rvalue *
ast_case_statement_list::hir(exec_list *instructions,
struct _mesa_glsl_parse_state *state)
{
- foreach_list_typed (ast_case_statement, case_stmt, link, & this->cases)
- case_stmt->hir(instructions, state);
+ exec_list default_case, after_default, tmp;
+
+ foreach_list_typed (ast_case_statement, case_stmt, link, & this->cases) {
+ case_stmt->hir(&tmp, state);
+
+ /* Default case. */
+ if (state->switch_state.previous_default && default_case.is_empty()) {
+ default_case.append_list(&tmp);
+ continue;
+ }
+
+ /* If default case found, append 'after_default' list. */
+ if (!default_case.is_empty())
+ after_default.append_list(&tmp);
+ else
+ instructions->append_list(&tmp);
+ }
+
+ /* Handle the default case. This is done here because default might not be
+ * the last case. We need to add checks against following cases first to see
+ * if default should be chosen or not.
+ */
+ if (!default_case.is_empty()) {
+
+ /* Default case was the last one, no checks required. */
+ if (after_default.is_empty()) {
+ instructions->append_list(&default_case);
+ return NULL;
+ }
+
+ ir_rvalue *const true_val = new (state) ir_constant(true);
+ ir_dereference_variable *deref_run_default_var =
+ new(state) ir_dereference_variable(state->switch_state.run_default);
+
+ /* Choose to run default case initially, following conditional
+ * assignments might change this.
+ */
+ ir_assignment *const init_var =
+ new(state) ir_assignment(deref_run_default_var, true_val);
+ instructions->push_tail(init_var);
+
+ foreach_in_list(ir_instruction, ir, &after_default) {
+ ir_assignment *assign = ir->as_assignment();
+
+ if (!assign)
+ continue;
+
+ /* Clone the check between case label and init expression. */
+ ir_expression *exp = (ir_expression*) assign->condition;
+ ir_expression *clone = exp->clone(state, NULL);
+
+ ir_dereference_variable *deref_var =
+ new(state) ir_dereference_variable(state->switch_state.run_default);
+ ir_rvalue *const false_val = new (state) ir_constant(false);
+
+ ir_assignment *const set_false =
+ new(state) ir_assignment(deref_var, false_val, clone);
+
+ instructions->push_tail(set_false);
+ }
+
+ /* Append default case and all cases after it. */
+ instructions->append_list(&default_case);
+ instructions->append_list(&after_default);
+ }
/* Case statements do not have r-values. */
return NULL;
@@ -4728,9 +4797,17 @@ ast_case_label::hir(exec_list *instructions,
}
state->switch_state.previous_default = this;
+ /* Set fallthru condition on 'run_default' bool. */
+ ir_dereference_variable *deref_run_default =
+ new(ctx) ir_dereference_variable(state->switch_state.run_default);
+ ir_rvalue *const cond_true = new(ctx) ir_constant(true);
+ ir_expression *test_cond = new(ctx) ir_expression(ir_binop_all_equal,
+ cond_true,
+ deref_run_default);
+
/* Set falltrhu state. */
ir_assignment *set_fallthru =
- new(ctx) ir_assignment(deref_fallthru_var, true_val);
+ new(ctx) ir_assignment(deref_fallthru_var, true_val, test_cond);
instructions->push_tail(set_fallthru);
}
@@ -5007,9 +5084,7 @@ ast_process_structure_or_interface_block(exec_list *instructions,
* 'declarations' list in each of the elements.
*/
foreach_list_typed (ast_declarator_list, decl_list, link, declarations) {
- foreach_list_typed (ast_declaration, decl, link, &decl_list->declarations) {
- decl_count++;
- }
+ decl_count += decl_list->declarations.length();
}
/* Allocate storage for the fields and process the field
diff --git a/mesalib/src/glsl/builtin_functions.cpp b/mesalib/src/glsl/builtin_functions.cpp
index 258b83142..e01742c4d 100644
--- a/mesalib/src/glsl/builtin_functions.cpp
+++ b/mesalib/src/glsl/builtin_functions.cpp
@@ -226,6 +226,14 @@ shader_packing_or_gpu_shader5(const _mesa_glsl_parse_state *state)
}
static bool
+fs_gpu_shader5(const _mesa_glsl_parse_state *state)
+{
+ return state->stage == MESA_SHADER_FRAGMENT &&
+ (state->is_version(400, 0) || state->ARB_gpu_shader5_enable);
+}
+
+
+static bool
texture_array_lod(const _mesa_glsl_parse_state *state)
{
return lod_exists_in_stage(state) &&
@@ -627,6 +635,9 @@ private:
B1(uaddCarry)
B1(usubBorrow)
B1(mulExtended)
+ B1(interpolateAtCentroid)
+ B1(interpolateAtOffset)
+ B1(interpolateAtSample)
ir_function_signature *_atomic_intrinsic(builtin_available_predicate avail);
ir_function_signature *_atomic_op(const char *intrinsic,
@@ -2186,6 +2197,24 @@ builtin_builder::create_builtins()
_mulExtended(glsl_type::uvec3_type),
_mulExtended(glsl_type::uvec4_type),
NULL);
+ add_function("interpolateAtCentroid",
+ _interpolateAtCentroid(glsl_type::float_type),
+ _interpolateAtCentroid(glsl_type::vec2_type),
+ _interpolateAtCentroid(glsl_type::vec3_type),
+ _interpolateAtCentroid(glsl_type::vec4_type),
+ NULL);
+ add_function("interpolateAtOffset",
+ _interpolateAtOffset(glsl_type::float_type),
+ _interpolateAtOffset(glsl_type::vec2_type),
+ _interpolateAtOffset(glsl_type::vec3_type),
+ _interpolateAtOffset(glsl_type::vec4_type),
+ NULL);
+ add_function("interpolateAtSample",
+ _interpolateAtSample(glsl_type::float_type),
+ _interpolateAtSample(glsl_type::vec2_type),
+ _interpolateAtSample(glsl_type::vec3_type),
+ _interpolateAtSample(glsl_type::vec4_type),
+ NULL);
add_function("atomicCounter",
_atomic_op("__intrinsic_atomic_read",
@@ -4260,6 +4289,44 @@ builtin_builder::_mulExtended(const glsl_type *type)
}
ir_function_signature *
+builtin_builder::_interpolateAtCentroid(const glsl_type *type)
+{
+ ir_variable *interpolant = in_var(type, "interpolant");
+ interpolant->data.must_be_shader_input = 1;
+ MAKE_SIG(type, fs_gpu_shader5, 1, interpolant);
+
+ body.emit(ret(interpolate_at_centroid(interpolant)));
+
+ return sig;
+}
+
+ir_function_signature *
+builtin_builder::_interpolateAtOffset(const glsl_type *type)
+{
+ ir_variable *interpolant = in_var(type, "interpolant");
+ interpolant->data.must_be_shader_input = 1;
+ ir_variable *offset = in_var(glsl_type::vec2_type, "offset");
+ MAKE_SIG(type, fs_gpu_shader5, 2, interpolant, offset);
+
+ body.emit(ret(interpolate_at_offset(interpolant, offset)));
+
+ return sig;
+}
+
+ir_function_signature *
+builtin_builder::_interpolateAtSample(const glsl_type *type)
+{
+ ir_variable *interpolant = in_var(type, "interpolant");
+ interpolant->data.must_be_shader_input = 1;
+ ir_variable *sample_num = in_var(glsl_type::int_type, "sample_num");
+ MAKE_SIG(type, fs_gpu_shader5, 2, interpolant, sample_num);
+
+ body.emit(ret(interpolate_at_sample(interpolant, sample_num)));
+
+ return sig;
+}
+
+ir_function_signature *
builtin_builder::_atomic_intrinsic(builtin_available_predicate avail)
{
ir_variable *counter = in_var(glsl_type::atomic_uint_type, "counter");
diff --git a/mesalib/src/glsl/glsl_parser.yy b/mesalib/src/glsl/glsl_parser.yy
index b9897498f..4c871633f 100644
--- a/mesalib/src/glsl/glsl_parser.yy
+++ b/mesalib/src/glsl/glsl_parser.yy
@@ -376,6 +376,14 @@ external_declaration_list:
if ($2 != NULL)
state->translation_unit.push_tail(& $2->link);
}
+ | external_declaration_list extension_statement {
+ if (!state->allow_extension_directive_midshader) {
+ _mesa_glsl_error(& @2, state,
+ "#extension directive is not allowed "
+ "in the middle of a shader");
+ YYERROR;
+ }
+ }
;
variable_identifier:
diff --git a/mesalib/src/glsl/glsl_parser_extras.cpp b/mesalib/src/glsl/glsl_parser_extras.cpp
index b327c2b43..890123ad1 100644
--- a/mesalib/src/glsl/glsl_parser_extras.cpp
+++ b/mesalib/src/glsl/glsl_parser_extras.cpp
@@ -210,6 +210,8 @@ _mesa_glsl_parse_state::_mesa_glsl_parse_state(struct gl_context *_ctx,
this->early_fragment_tests = false;
memset(this->atomic_counter_offsets, 0,
sizeof(this->atomic_counter_offsets));
+ this->allow_extension_directive_midshader =
+ ctx->Const.AllowGLSLExtensionDirectiveMidShader;
}
/**
diff --git a/mesalib/src/glsl/glsl_parser_extras.h b/mesalib/src/glsl/glsl_parser_extras.h
index 17918163e..ce66e2fa4 100644
--- a/mesalib/src/glsl/glsl_parser_extras.h
+++ b/mesalib/src/glsl/glsl_parser_extras.h
@@ -43,6 +43,9 @@ struct glsl_switch_state {
ir_variable *is_break_var;
class ast_switch_statement *switch_nesting_ast;
+ /** Used to set condition if 'default' label should be chosen. */
+ ir_variable *run_default;
+
/** Table of constant values already used in case labels */
struct hash_table *labels_ht;
class ast_case_label *previous_default;
@@ -490,6 +493,8 @@ struct _mesa_glsl_parse_state {
/** Atomic counter offsets by binding */
unsigned atomic_counter_offsets[MAX_COMBINED_ATOMIC_BUFFERS];
+
+ bool allow_extension_directive_midshader;
};
# define YYLLOC_DEFAULT(Current, Rhs, N) \
diff --git a/mesalib/src/glsl/ir.cpp b/mesalib/src/glsl/ir.cpp
index 1d8bb6e7b..28fd94b95 100644
--- a/mesalib/src/glsl/ir.cpp
+++ b/mesalib/src/glsl/ir.cpp
@@ -250,6 +250,7 @@ ir_expression::ir_expression(int op, ir_rvalue *op0)
case ir_unop_dFdx:
case ir_unop_dFdy:
case ir_unop_bitfield_reverse:
+ case ir_unop_interpolate_at_centroid:
this->type = op0->type;
break;
@@ -403,6 +404,8 @@ ir_expression::ir_expression(int op, ir_rvalue *op0, ir_rvalue *op1)
case ir_binop_rshift:
case ir_binop_bfm:
case ir_binop_ldexp:
+ case ir_binop_interpolate_at_offset:
+ case ir_binop_interpolate_at_sample:
this->type = op0->type;
break;
@@ -524,6 +527,7 @@ static const char *const operator_strs[] = {
"find_msb",
"find_lsb",
"noise",
+ "interpolate_at_centroid",
"+",
"-",
"*",
@@ -557,6 +561,8 @@ static const char *const operator_strs[] = {
"ubo_load",
"ldexp",
"vector_extract",
+ "interpolate_at_offset",
+ "interpolate_at_sample",
"fma",
"lrp",
"csel",
diff --git a/mesalib/src/glsl/ir.h b/mesalib/src/glsl/ir.h
index d5239d4de..ea19924ab 100644
--- a/mesalib/src/glsl/ir.h
+++ b/mesalib/src/glsl/ir.h
@@ -678,6 +678,12 @@ public:
unsigned from_named_ifc_block_array:1;
/**
+ * Non-zero if the variable must be a shader input. This is useful for
+ * constraints on function parameters.
+ */
+ unsigned must_be_shader_input:1;
+
+ /**
* \brief Layout qualifier for gl_FragDepth.
*
* This is not equal to \c ir_depth_layout_none if and only if this
@@ -1234,9 +1240,16 @@ enum ir_expression_operation {
ir_unop_noise,
/**
+ * Interpolate fs input at centroid
+ *
+ * operand0 is the fs input.
+ */
+ ir_unop_interpolate_at_centroid,
+
+ /**
* A sentinel marking the last of the unary operations.
*/
- ir_last_unop = ir_unop_noise,
+ ir_last_unop = ir_unop_interpolate_at_centroid,
ir_binop_add,
ir_binop_sub,
@@ -1355,9 +1368,25 @@ enum ir_expression_operation {
ir_binop_vector_extract,
/**
+ * Interpolate fs input at offset
+ *
+ * operand0 is the fs input
+ * operand1 is the offset from the pixel center
+ */
+ ir_binop_interpolate_at_offset,
+
+ /**
+ * Interpolate fs input at sample position
+ *
+ * operand0 is the fs input
+ * operand1 is the sample ID
+ */
+ ir_binop_interpolate_at_sample,
+
+ /**
* A sentinel marking the last of the binary operations.
*/
- ir_last_binop = ir_binop_vector_extract,
+ ir_last_binop = ir_binop_interpolate_at_sample,
/**
* \name Fused floating-point multiply-add, part of ARB_gpu_shader5.
diff --git a/mesalib/src/glsl/ir_builder.cpp b/mesalib/src/glsl/ir_builder.cpp
index f4a1c6efa..f03941443 100644
--- a/mesalib/src/glsl/ir_builder.cpp
+++ b/mesalib/src/glsl/ir_builder.cpp
@@ -501,6 +501,24 @@ b2f(operand a)
}
ir_expression *
+interpolate_at_centroid(operand a)
+{
+ return expr(ir_unop_interpolate_at_centroid, a);
+}
+
+ir_expression *
+interpolate_at_offset(operand a, operand b)
+{
+ return expr(ir_binop_interpolate_at_offset, a, b);
+}
+
+ir_expression *
+interpolate_at_sample(operand a, operand b)
+{
+ return expr(ir_binop_interpolate_at_sample, a, b);
+}
+
+ir_expression *
fma(operand a, operand b, operand c)
{
return expr(ir_triop_fma, a, b, c);
diff --git a/mesalib/src/glsl/ir_builder.h b/mesalib/src/glsl/ir_builder.h
index 108b53a5e..573596cf1 100644
--- a/mesalib/src/glsl/ir_builder.h
+++ b/mesalib/src/glsl/ir_builder.h
@@ -186,6 +186,10 @@ ir_expression *b2f(operand a);
ir_expression *min2(operand a, operand b);
ir_expression *max2(operand a, operand b);
+ir_expression *interpolate_at_centroid(operand a);
+ir_expression *interpolate_at_offset(operand a, operand b);
+ir_expression *interpolate_at_sample(operand a, operand b);
+
ir_expression *fma(operand a, operand b, operand c);
ir_expression *lrp(operand x, operand y, operand a);
ir_expression *csel(operand a, operand b, operand c);
diff --git a/mesalib/src/glsl/ir_constant_expression.cpp b/mesalib/src/glsl/ir_constant_expression.cpp
index 7f83eb134..5570ed46f 100644
--- a/mesalib/src/glsl/ir_constant_expression.cpp
+++ b/mesalib/src/glsl/ir_constant_expression.cpp
@@ -510,6 +510,8 @@ ir_expression::constant_expression_value(struct hash_table *variable_context)
case ir_binop_lshift:
case ir_binop_rshift:
case ir_binop_ldexp:
+ case ir_binop_interpolate_at_offset:
+ case ir_binop_interpolate_at_sample:
case ir_binop_vector_extract:
case ir_triop_csel:
case ir_triop_bitfield_extract:
diff --git a/mesalib/src/glsl/ir_hierarchical_visitor.cpp b/mesalib/src/glsl/ir_hierarchical_visitor.cpp
index d3c00ecdb..adb629414 100644
--- a/mesalib/src/glsl/ir_hierarchical_visitor.cpp
+++ b/mesalib/src/glsl/ir_hierarchical_visitor.cpp
@@ -27,16 +27,18 @@
ir_hierarchical_visitor::ir_hierarchical_visitor()
{
this->base_ir = NULL;
- this->callback = NULL;
- this->data = NULL;
+ this->callback_enter = NULL;
+ this->callback_leave = NULL;
+ this->data_enter = NULL;
+ this->data_leave = NULL;
this->in_assignee = false;
}
ir_visitor_status
ir_hierarchical_visitor::visit(ir_rvalue *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -44,8 +46,8 @@ ir_hierarchical_visitor::visit(ir_rvalue *ir)
ir_visitor_status
ir_hierarchical_visitor::visit(ir_variable *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -53,8 +55,8 @@ ir_hierarchical_visitor::visit(ir_variable *ir)
ir_visitor_status
ir_hierarchical_visitor::visit(ir_constant *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -62,8 +64,8 @@ ir_hierarchical_visitor::visit(ir_constant *ir)
ir_visitor_status
ir_hierarchical_visitor::visit(ir_loop_jump *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -71,8 +73,8 @@ ir_hierarchical_visitor::visit(ir_loop_jump *ir)
ir_visitor_status
ir_hierarchical_visitor::visit(ir_dereference_variable *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -80,8 +82,8 @@ ir_hierarchical_visitor::visit(ir_dereference_variable *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_loop *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -89,15 +91,17 @@ ir_hierarchical_visitor::visit_enter(ir_loop *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_loop *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_function_signature *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -105,15 +109,17 @@ ir_hierarchical_visitor::visit_enter(ir_function_signature *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_function_signature *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_function *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -121,15 +127,17 @@ ir_hierarchical_visitor::visit_enter(ir_function *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_function *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_expression *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -137,15 +145,17 @@ ir_hierarchical_visitor::visit_enter(ir_expression *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_expression *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_texture *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -153,15 +163,17 @@ ir_hierarchical_visitor::visit_enter(ir_texture *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_texture *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_swizzle *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -169,15 +181,17 @@ ir_hierarchical_visitor::visit_enter(ir_swizzle *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_swizzle *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_dereference_array *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -185,15 +199,17 @@ ir_hierarchical_visitor::visit_enter(ir_dereference_array *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_dereference_array *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_dereference_record *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -201,15 +217,17 @@ ir_hierarchical_visitor::visit_enter(ir_dereference_record *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_dereference_record *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_assignment *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -217,15 +235,17 @@ ir_hierarchical_visitor::visit_enter(ir_assignment *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_assignment *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_call *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -233,15 +253,17 @@ ir_hierarchical_visitor::visit_enter(ir_call *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_call *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_return *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -249,15 +271,17 @@ ir_hierarchical_visitor::visit_enter(ir_return *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_return *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_discard *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -265,15 +289,17 @@ ir_hierarchical_visitor::visit_enter(ir_discard *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_discard *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_if *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -281,15 +307,17 @@ ir_hierarchical_visitor::visit_enter(ir_if *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_if *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_emit_vertex *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -297,15 +325,17 @@ ir_hierarchical_visitor::visit_enter(ir_emit_vertex *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_emit_vertex *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
ir_visitor_status
ir_hierarchical_visitor::visit_enter(ir_end_primitive *ir)
{
- if (this->callback != NULL)
- this->callback(ir, this->data);
+ if (this->callback_enter != NULL)
+ this->callback_enter(ir, this->data_enter);
return visit_continue;
}
@@ -313,7 +343,9 @@ ir_hierarchical_visitor::visit_enter(ir_end_primitive *ir)
ir_visitor_status
ir_hierarchical_visitor::visit_leave(ir_end_primitive *ir)
{
- (void) ir;
+ if (this->callback_leave != NULL)
+ this->callback_leave(ir, this->data_leave);
+
return visit_continue;
}
@@ -326,13 +358,17 @@ ir_hierarchical_visitor::run(exec_list *instructions)
void
visit_tree(ir_instruction *ir,
- void (*callback)(class ir_instruction *ir, void *data),
- void *data)
+ void (*callback_enter)(class ir_instruction *ir, void *data),
+ void *data_enter,
+ void (*callback_leave)(class ir_instruction *ir, void *data),
+ void *data_leave)
{
ir_hierarchical_visitor v;
- v.callback = callback;
- v.data = data;
+ v.callback_enter = callback_enter;
+ v.callback_leave = callback_leave;
+ v.data_enter = data_enter;
+ v.data_leave = data_leave;
ir->accept(&v);
}
diff --git a/mesalib/src/glsl/ir_hierarchical_visitor.h b/mesalib/src/glsl/ir_hierarchical_visitor.h
index bc89a04d8..faa52fd79 100644
--- a/mesalib/src/glsl/ir_hierarchical_visitor.h
+++ b/mesalib/src/glsl/ir_hierarchical_visitor.h
@@ -163,14 +163,29 @@ public:
* \warning
* Visitor classes derived from \c ir_hierarchical_visitor \b may \b not
* invoke this function. This can be used, for example, to cause the
- * callback to be invoked on every node type execpt one.
+ * callback to be invoked on every node type except one.
*/
- void (*callback)(class ir_instruction *ir, void *data);
+ void (*callback_enter)(class ir_instruction *ir, void *data);
/**
- * Extra data parameter passed to the per-node callback function
+ * Callback function that is invoked on exit of each node visited.
+ *
+ * \warning
+ * Visitor classes derived from \c ir_hierarchical_visitor \b may \b not
+ * invoke this function. This can be used, for example, to cause the
+ * callback to be invoked on every node type except one.
+ */
+ void (*callback_leave)(class ir_instruction *ir, void *data);
+
+ /**
+ * Extra data parameter passed to the per-node callback_enter function
+ */
+ void *data_enter;
+
+ /**
+ * Extra data parameter passed to the per-node callback_leave function
*/
- void *data;
+ void *data_leave;
/**
* Currently in the LHS of an assignment?
@@ -181,8 +196,10 @@ public:
};
void visit_tree(ir_instruction *ir,
- void (*callback)(class ir_instruction *ir, void *data),
- void *data);
+ void (*callback_enter)(class ir_instruction *ir, void *data),
+ void *data_enter,
+ void (*callback_leave)(class ir_instruction *ir, void *data) = NULL,
+ void *data_leave = NULL);
ir_visitor_status visit_list_elements(ir_hierarchical_visitor *v, exec_list *l,
bool statement_list = true);
diff --git a/mesalib/src/glsl/ir_reader.cpp b/mesalib/src/glsl/ir_reader.cpp
index 4017bdd73..e3566e1d6 100644
--- a/mesalib/src/glsl/ir_reader.cpp
+++ b/mesalib/src/glsl/ir_reader.cpp
@@ -723,10 +723,9 @@ ir_reader::read_expression(s_expression *expr)
ir_read_error(expr, "invalid operator: %s", s_op->value());
return NULL;
}
-
- int num_operands = -3; /* skip "expression" <type> <operation> */
- foreach_in_list(s_expression, e, &((s_list *) expr)->subexpressions)
- ++num_operands;
+
+ /* Skip "expression" <type> <operation> by subtracting 3. */
+ int num_operands = (int) ((s_list *) expr)->subexpressions.length() - 3;
int expected_operands = ir_expression::get_num_operands(op);
if (num_operands != expected_operands) {
diff --git a/mesalib/src/glsl/ir_validate.cpp b/mesalib/src/glsl/ir_validate.cpp
index 271dbe096..37e1ce33e 100644
--- a/mesalib/src/glsl/ir_validate.cpp
+++ b/mesalib/src/glsl/ir_validate.cpp
@@ -49,8 +49,8 @@ public:
this->current_function = NULL;
- this->callback = ir_validate::validate_ir;
- this->data = ht;
+ this->callback_enter = ir_validate::validate_ir;
+ this->data_enter = ht;
}
~ir_validate()
@@ -100,7 +100,7 @@ ir_validate::visit(ir_dereference_variable *ir)
abort();
}
- this->validate_ir(ir, this->data);
+ this->validate_ir(ir, this->data_enter);
return visit_continue;
}
@@ -167,7 +167,7 @@ ir_validate::visit_enter(ir_function *ir)
*/
this->current_function = ir;
- this->validate_ir(ir, this->data);
+ this->validate_ir(ir, this->data_enter);
/* Verify that all of the things stored in the list of signatures are,
* in fact, function signatures.
@@ -211,7 +211,7 @@ ir_validate::visit_enter(ir_function_signature *ir)
abort();
}
- this->validate_ir(ir, this->data);
+ this->validate_ir(ir, this->data_enter);
return visit_continue;
}
@@ -371,6 +371,11 @@ ir_validate::visit_leave(ir_expression *ir)
/* XXX what can we assert here? */
break;
+ case ir_unop_interpolate_at_centroid:
+ assert(ir->operands[0]->type == ir->type);
+ assert(ir->operands[0]->type->is_float());
+ break;
+
case ir_binop_add:
case ir_binop_sub:
case ir_binop_mul:
@@ -510,6 +515,19 @@ ir_validate::visit_leave(ir_expression *ir)
&& ir->operands[1]->type->is_integer());
break;
+ case ir_binop_interpolate_at_offset:
+ assert(ir->operands[0]->type == ir->type);
+ assert(ir->operands[0]->type->is_float());
+ assert(ir->operands[1]->type->components() == 2);
+ assert(ir->operands[1]->type->is_float());
+ break;
+
+ case ir_binop_interpolate_at_sample:
+ assert(ir->operands[0]->type == ir->type);
+ assert(ir->operands[0]->type->is_float());
+ assert(ir->operands[1]->type == glsl_type::int_type);
+ break;
+
case ir_triop_fma:
assert(ir->type->base_type == GLSL_TYPE_FLOAT);
assert(ir->type == ir->operands[0]->type);
@@ -708,7 +726,7 @@ ir_validate::visit_enter(ir_assignment *ir)
}
}
- this->validate_ir(ir, this->data);
+ this->validate_ir(ir, this->data_enter);
return visit_continue;
}
diff --git a/mesalib/src/glsl/list.h b/mesalib/src/glsl/list.h
index a4444bda9..3ee6cdaa9 100644
--- a/mesalib/src/glsl/list.h
+++ b/mesalib/src/glsl/list.h
@@ -325,6 +325,8 @@ struct exec_list {
const exec_node *get_tail() const;
exec_node *get_tail();
+ unsigned length() const;
+
void push_head(exec_node *n);
void push_tail(exec_node *n);
void push_degenerate_list_at_head(exec_node *n);
@@ -345,9 +347,15 @@ struct exec_list {
void move_nodes_to(exec_list *target);
/**
- * Append all nodes from the source list to the target list
+ * Append all nodes from the source list to the end of the target list
*/
void append_list(exec_list *source);
+
+ /**
+ * Prepend all nodes from the source list to the beginning of the target
+ * list
+ */
+ void prepend_list(exec_list *source);
#endif
};
@@ -399,6 +407,19 @@ exec_list_get_tail(struct exec_list *list)
return !exec_list_is_empty(list) ? list->tail_pred : NULL;
}
+static inline unsigned
+exec_list_length(const struct exec_list *list)
+{
+ unsigned size = 0;
+ struct exec_node *node;
+
+ for (node = list->head; node->next != NULL; node = node->next) {
+ size++;
+ }
+
+ return size;
+}
+
static inline void
exec_list_push_head(struct exec_list *list, struct exec_node *n)
{
@@ -479,6 +500,13 @@ exec_list_append(struct exec_list *list, struct exec_list *source)
}
static inline void
+exec_list_prepend(struct exec_list *list, struct exec_list *source)
+{
+ exec_list_append(source, list);
+ exec_list_move_nodes_to(source, list);
+}
+
+static inline void
exec_node_insert_list_before(struct exec_node *n, struct exec_list *before)
{
if (exec_list_is_empty(before))
@@ -524,6 +552,11 @@ inline exec_node *exec_list::get_tail()
return exec_list_get_tail(this);
}
+inline unsigned exec_list::length() const
+{
+ return exec_list_length(this);
+}
+
inline void exec_list::push_head(exec_node *n)
{
exec_list_push_head(this, n);
@@ -554,6 +587,11 @@ inline void exec_list::append_list(exec_list *source)
exec_list_append(this, source);
}
+inline void exec_list::prepend_list(exec_list *source)
+{
+ exec_list_prepend(this, source);
+}
+
inline void exec_node::insert_before(exec_list *before)
{
exec_node_insert_list_before(this, before);
diff --git a/mesalib/src/glsl/opt_function_inlining.cpp b/mesalib/src/glsl/opt_function_inlining.cpp
index b84bb8e11..64b4907ba 100644
--- a/mesalib/src/glsl/opt_function_inlining.cpp
+++ b/mesalib/src/glsl/opt_function_inlining.cpp
@@ -100,16 +100,13 @@ ir_call::generate_inline(ir_instruction *next_ir)
{
void *ctx = ralloc_parent(this);
ir_variable **parameters;
- int num_parameters;
+ unsigned num_parameters;
int i;
struct hash_table *ht;
ht = hash_table_ctor(0, hash_table_pointer_hash, hash_table_pointer_compare);
- num_parameters = 0;
- foreach_in_list(ir_rvalue, param, &this->callee->parameters)
- num_parameters++;
-
+ num_parameters = this->callee->parameters.length();
parameters = new ir_variable *[num_parameters];
/* Generate the declarations for the parameters to our inlined code,
diff --git a/mesalib/src/glsl/opt_rebalance_tree.cpp b/mesalib/src/glsl/opt_rebalance_tree.cpp
index 773aab3f6..095f2d7d2 100644
--- a/mesalib/src/glsl/opt_rebalance_tree.cpp
+++ b/mesalib/src/glsl/opt_rebalance_tree.cpp
@@ -60,6 +60,7 @@
#include "ir_visitor.h"
#include "ir_rvalue_visitor.h"
#include "ir_optimization.h"
+#include "main/macros.h" /* for MAX2 */
/* The DSW algorithm generates a degenerate tree (really, a linked list) in
* tree_to_vine(). We'd rather not leave a binary expression with only one
@@ -216,7 +217,9 @@ is_reduction(ir_instruction *ir, void *data)
* constant fold once split up. Handling matrices will need some more
* work.
*/
- if (expr->type->is_matrix()) {
+ if (expr->type->is_matrix() ||
+ expr->operands[0]->type->is_matrix() ||
+ (expr->operands[1] && expr->operands[1]->type->is_matrix())) {
ird->is_reduction = false;
return;
}
@@ -261,6 +264,22 @@ handle_expression(ir_expression *expr)
return expr;
}
+static void
+update_types(ir_instruction *ir, void *)
+{
+ ir_expression *expr = ir->as_expression();
+ if (!expr)
+ return;
+
+ const glsl_type *const new_type =
+ glsl_type::get_instance(expr->type->base_type,
+ MAX2(expr->operands[0]->type->vector_elements,
+ expr->operands[1]->type->vector_elements),
+ 1);
+ assert(new_type != glsl_type::error_type);
+ expr->type = new_type;
+}
+
void
ir_rebalance_visitor::handle_rvalue(ir_rvalue **rvalue)
{
@@ -285,6 +304,8 @@ ir_rebalance_visitor::handle_rvalue(ir_rvalue **rvalue)
if (new_rvalue == *rvalue)
return;
+ visit_tree(new_rvalue, NULL, NULL, update_types);
+
*rvalue = new_rvalue;
this->progress = true;
}
diff --git a/mesalib/src/mapi/glapi/gen/gl_gentable.py b/mesalib/src/mapi/glapi/gen/gl_gentable.py
index d45a5e0ff..9db6a773a 100644
--- a/mesalib/src/mapi/glapi/gen/gl_gentable.py
+++ b/mesalib/src/mapi/glapi/gen/gl_gentable.py
@@ -134,7 +134,11 @@ body_template = """
if(!disp->%(name)s) {
void ** procp = (void **) &disp->%(name)s;
snprintf(symboln, sizeof(symboln), "%%s%(entry_point)s", symbol_prefix);
+#ifdef _WIN32
+ *procp = GetProcAddress(handle, symboln);
+#else
*procp = dlsym(handle, symboln);
+#endif
}
"""
diff --git a/mesalib/src/mesa/drivers/dri/Makefile.am b/mesalib/src/mesa/drivers/dri/Makefile.am
index 70039f9ad..2009da921 100644
--- a/mesalib/src/mesa/drivers/dri/Makefile.am
+++ b/mesalib/src/mesa/drivers/dri/Makefile.am
@@ -85,7 +85,6 @@ install-data-hook:
ln -f $(DESTDIR)$(dridir)/mesa_dri_drivers.so \
$(DESTDIR)$(dridir)/$$i; \
done;
- $(RM) -f $(DESTDIR)$(dridir)/mesa_dri_drivers.so
- $(RM) -f $(DESTDIR)$(dridir)/mesa_dri_drivers.la
+ $(RM) -f $(DESTDIR)$(dridir)/mesa_dri_drivers.*
endif
diff --git a/mesalib/src/mesa/drivers/dri/common/drirc b/mesalib/src/mesa/drivers/dri/common/drirc
index ebc04cd9b..4b9841bd2 100644
--- a/mesalib/src/mesa/drivers/dri/common/drirc
+++ b/mesalib/src/mesa/drivers/dri/common/drirc
@@ -11,17 +11,21 @@ Application bugs worked around in this file:
is still 1.10.
* Unigine Heaven 3.0 with ARB_texture_multisample uses a "ivec4 * vec4"
- expression, which fails to compile with GLSL 1.10.
+ expression, which is illegal in GLSL 1.10.
Adding "#version 130" fixes this.
* Unigine Heaven 3.0 with ARB_shader_bit_encoding uses the uint keyword, which
- fails to compile with GLSL 1.10.
+ is illegal in GLSL 1.10.
Adding "#version 130" fixes this.
* Unigine Heaven 3.0 with ARB_shader_bit_encoding uses a "uint & int"
- expression, which fails (and should fail) to compile with any GLSL version.
+ expression, which is illegal in any GLSL version.
Disabling ARB_shader_bit_encoding fixes this.
+* If ARB_sample_shading is supported, Unigine Heaven 4.0 and Valley 1.0 uses
+ an #extension directive in the middle of its shaders, which is illegal
+ in GLSL.
+
TODO: document the other workarounds.
-->
@@ -45,6 +49,7 @@ TODO: document the other workarounds.
<option name="disable_blend_func_extended" value="true" />
<option name="force_glsl_version" value="130" />
<option name="disable_shader_bit_encoding" value="true" />
+ <option name="allow_glsl_extension_directive_midshader" value="true" />
</application>
<application name="Unigine Heaven (64-bit)" executable="heaven_x64">
@@ -52,6 +57,15 @@ TODO: document the other workarounds.
<option name="disable_blend_func_extended" value="true" />
<option name="force_glsl_version" value="130" />
<option name="disable_shader_bit_encoding" value="true" />
+ <option name="allow_glsl_extension_directive_midshader" value="true" />
+ </application>
+
+ <application name="Unigine Valley (32-bit)" executable="valley_x86">
+ <option name="allow_glsl_extension_directive_midshader" value="true" />
+ </application>
+
+ <application name="Unigine Valley (64-bit)" executable="valley_x64">
+ <option name="allow_glsl_extension_directive_midshader" value="true" />
</application>
<application name="Unigine OilRush (32-bit)" executable="OilRush_x86">
diff --git a/mesalib/src/mesa/drivers/dri/common/xmlpool/t_options.h b/mesalib/src/mesa/drivers/dri/common/xmlpool/t_options.h
index fc9e10461..b73a6620c 100644
--- a/mesalib/src/mesa/drivers/dri/common/xmlpool/t_options.h
+++ b/mesalib/src/mesa/drivers/dri/common/xmlpool/t_options.h
@@ -105,6 +105,11 @@ DRI_CONF_OPT_BEGIN_V(force_glsl_version, int, def, "0:999") \
DRI_CONF_DESC(en,gettext("Force a default GLSL version for shaders that lack an explicit #version line")) \
DRI_CONF_OPT_END
+#define DRI_CONF_ALLOW_GLSL_EXTENSION_DIRECTIVE_MIDSHADER(def) \
+DRI_CONF_OPT_BEGIN_B(allow_glsl_extension_directive_midshader, def) \
+ DRI_CONF_DESC(en,gettext("Allow GLSL #extension directives in the middle of shaders")) \
+DRI_CONF_OPT_END
+
/**
diff --git a/mesalib/src/mesa/main/arrayobj.c b/mesalib/src/mesa/main/arrayobj.c
index efb993012..1ea319a74 100644
--- a/mesalib/src/mesa/main/arrayobj.c
+++ b/mesalib/src/mesa/main/arrayobj.c
@@ -427,6 +427,21 @@ bind_vertex_array(struct gl_context *ctx, GLuint id, GLboolean genRequired)
}
}
+ if (ctx->Array.DrawMethod == DRAW_ARRAYS) {
+ /* The _DrawArrays pointer is pointing at the VAO being unbound and
+ * that VAO may be in the process of being deleted. If it's not going
+ * to be deleted, this will have no effect, because the pointer needs
+ * to be updated by the VBO module anyway.
+ *
+ * Before the VBO module can update the pointer, we have to set it
+ * to NULL for drivers not to set up arrays which are not bound,
+ * or to prevent a crash if the VAO being unbound is going to be
+ * deleted.
+ */
+ ctx->Array._DrawArrays = NULL;
+ ctx->Array.DrawMethod = DRAW_NONE;
+ }
+
ctx->NewState |= _NEW_ARRAY;
_mesa_reference_vao(ctx, &ctx->Array.VAO, newObj);
diff --git a/mesalib/src/mesa/main/format_pack.c b/mesalib/src/mesa/main/format_pack.c
index 6b28592a6..c97c05297 100644
--- a/mesalib/src/mesa/main/format_pack.c
+++ b/mesalib/src/mesa/main/format_pack.c
@@ -888,7 +888,7 @@ pack_float_R_UNORM8(const GLfloat src[4], void *dst)
static void
pack_ubyte_R8G8_UNORM(const GLubyte src[4], void *dst)
{
- GLubyte *d = ((GLubyte *) dst);
+ GLushort *d = ((GLushort *) dst);
*d = PACK_COLOR_88(src[GCOMP], src[RCOMP]);
}
diff --git a/mesalib/src/mesa/main/mtypes.h b/mesalib/src/mesa/main/mtypes.h
index a7126fd55..91d9172f9 100644
--- a/mesalib/src/mesa/main/mtypes.h
+++ b/mesalib/src/mesa/main/mtypes.h
@@ -1640,6 +1640,17 @@ struct gl_vertex_array_object
};
+/** Used to signal when transitioning from one kind of drawing method
+ * to another.
+ */
+typedef enum {
+ DRAW_NONE, /**< Initial value only */
+ DRAW_BEGIN_END,
+ DRAW_DISPLAY_LIST,
+ DRAW_ARRAYS
+} gl_draw_method;
+
+
/**
* Vertex array state
*/
@@ -1679,6 +1690,9 @@ struct gl_array_attrib
* The array pointer is set up only by the VBO module.
*/
const struct gl_client_array **_DrawArrays; /**< 0..VERT_ATTRIB_MAX-1 */
+
+ /** One of the DRAW_xxx flags, not consumed by drivers */
+ gl_draw_method DrawMethod;
};
@@ -3349,6 +3363,11 @@ struct gl_constants
GLuint ForceGLSLVersion;
/**
+ * Allow GLSL #extension directives in the middle of shaders.
+ */
+ GLboolean AllowGLSLExtensionDirectiveMidShader;
+
+ /**
* Does the driver support real 32-bit integers? (Otherwise, integers are
* simulated via floats.)
*/
diff --git a/mesalib/src/mesa/main/pack.c b/mesalib/src/mesa/main/pack.c
index 5ebaaf6e5..649a74cce 100644
--- a/mesalib/src/mesa/main/pack.c
+++ b/mesalib/src/mesa/main/pack.c
@@ -3183,10 +3183,10 @@ extract_float_rgba(GLuint n, GLfloat rgba[][4],
PROCESS(aSrc, ACOMP, 1.0F, 255, GLubyte, UBYTE_TO_FLOAT);
break;
case GL_BYTE:
- PROCESS(rSrc, RCOMP, 0.0F, 0, GLbyte, BYTE_TO_FLOATZ);
- PROCESS(gSrc, GCOMP, 0.0F, 0, GLbyte, BYTE_TO_FLOATZ);
- PROCESS(bSrc, BCOMP, 0.0F, 0, GLbyte, BYTE_TO_FLOATZ);
- PROCESS(aSrc, ACOMP, 1.0F, 127, GLbyte, BYTE_TO_FLOATZ);
+ PROCESS(rSrc, RCOMP, 0.0F, 0, GLbyte, BYTE_TO_FLOAT_TEX);
+ PROCESS(gSrc, GCOMP, 0.0F, 0, GLbyte, BYTE_TO_FLOAT_TEX);
+ PROCESS(bSrc, BCOMP, 0.0F, 0, GLbyte, BYTE_TO_FLOAT_TEX);
+ PROCESS(aSrc, ACOMP, 1.0F, 127, GLbyte, BYTE_TO_FLOAT_TEX);
break;
case GL_UNSIGNED_SHORT:
PROCESS(rSrc, RCOMP, 0.0F, 0, GLushort, USHORT_TO_FLOAT);
@@ -3195,10 +3195,10 @@ extract_float_rgba(GLuint n, GLfloat rgba[][4],
PROCESS(aSrc, ACOMP, 1.0F, 0xffff, GLushort, USHORT_TO_FLOAT);
break;
case GL_SHORT:
- PROCESS(rSrc, RCOMP, 0.0F, 0, GLshort, SHORT_TO_FLOATZ);
- PROCESS(gSrc, GCOMP, 0.0F, 0, GLshort, SHORT_TO_FLOATZ);
- PROCESS(bSrc, BCOMP, 0.0F, 0, GLshort, SHORT_TO_FLOATZ);
- PROCESS(aSrc, ACOMP, 1.0F, 32767, GLshort, SHORT_TO_FLOATZ);
+ PROCESS(rSrc, RCOMP, 0.0F, 0, GLshort, SHORT_TO_FLOAT_TEX);
+ PROCESS(gSrc, GCOMP, 0.0F, 0, GLshort, SHORT_TO_FLOAT_TEX);
+ PROCESS(bSrc, BCOMP, 0.0F, 0, GLshort, SHORT_TO_FLOAT_TEX);
+ PROCESS(aSrc, ACOMP, 1.0F, 32767, GLshort, SHORT_TO_FLOAT_TEX);
break;
case GL_UNSIGNED_INT:
PROCESS(rSrc, RCOMP, 0.0F, 0, GLuint, UINT_TO_FLOAT);
diff --git a/mesalib/src/mesa/main/texparam.c b/mesalib/src/mesa/main/texparam.c
index dc17ea584..30dd0b9b3 100644
--- a/mesalib/src/mesa/main/texparam.c
+++ b/mesalib/src/mesa/main/texparam.c
@@ -1051,6 +1051,7 @@ get_tex_level_parameter_image(struct gl_context *ctx,
GLenum pname, GLint *params)
{
const struct gl_texture_image *img = NULL;
+ struct gl_texture_image dummy_image;
mesa_format texFormat;
img = _mesa_select_tex_image(ctx, texObj, target, level);
@@ -1062,12 +1063,12 @@ get_tex_level_parameter_image(struct gl_context *ctx,
* instead of 1. TEXTURE_COMPONENTS is deprecated; always
* use TEXTURE_INTERNAL_FORMAT."
*/
+ memset(&dummy_image, 0, sizeof(dummy_image));
+ dummy_image.TexFormat = MESA_FORMAT_NONE;
+ dummy_image.InternalFormat = GL_RGBA;
+ dummy_image._BaseFormat = GL_NONE;
- if (pname == GL_TEXTURE_INTERNAL_FORMAT)
- *params = GL_RGBA;
- else
- *params = 0;
- return;
+ img = &dummy_image;
}
texFormat = img->TexFormat;
@@ -1107,6 +1108,8 @@ get_tex_level_parameter_image(struct gl_context *ctx,
}
break;
case GL_TEXTURE_BORDER:
+ if (ctx->API != API_OPENGL_COMPAT)
+ goto invalid_pname;
*params = img->Border;
break;
case GL_TEXTURE_RED_SIZE:
@@ -1120,6 +1123,8 @@ get_tex_level_parameter_image(struct gl_context *ctx,
break;
case GL_TEXTURE_INTENSITY_SIZE:
case GL_TEXTURE_LUMINANCE_SIZE:
+ if (ctx->API != API_OPENGL_COMPAT)
+ goto invalid_pname;
if (_mesa_base_format_has_channel(img->_BaseFormat, pname)) {
*params = _mesa_get_format_bits(texFormat, pname);
if (*params == 0) {
@@ -1166,12 +1171,15 @@ get_tex_level_parameter_image(struct gl_context *ctx,
break;
/* GL_ARB_texture_float */
+ case GL_TEXTURE_LUMINANCE_TYPE_ARB:
+ case GL_TEXTURE_INTENSITY_TYPE_ARB:
+ if (ctx->API != API_OPENGL_COMPAT)
+ goto invalid_pname;
+ /* FALLTHROUGH */
case GL_TEXTURE_RED_TYPE_ARB:
case GL_TEXTURE_GREEN_TYPE_ARB:
case GL_TEXTURE_BLUE_TYPE_ARB:
case GL_TEXTURE_ALPHA_TYPE_ARB:
- case GL_TEXTURE_LUMINANCE_TYPE_ARB:
- case GL_TEXTURE_INTENSITY_TYPE_ARB:
case GL_TEXTURE_DEPTH_TYPE_ARB:
if (!ctx->Extensions.ARB_texture_float)
goto invalid_pname;
diff --git a/mesalib/src/mesa/program/ir_to_mesa.cpp b/mesalib/src/mesa/program/ir_to_mesa.cpp
index 1109051e9..2a82e9d9d 100644
--- a/mesalib/src/mesa/program/ir_to_mesa.cpp
+++ b/mesalib/src/mesa/program/ir_to_mesa.cpp
@@ -1456,6 +1456,9 @@ ir_to_mesa_visitor::visit(ir_expression *ir)
case ir_binop_carry:
case ir_binop_borrow:
case ir_binop_imul_high:
+ case ir_unop_interpolate_at_centroid:
+ case ir_binop_interpolate_at_offset:
+ case ir_binop_interpolate_at_sample:
assert(!"not supported");
break;
@@ -2814,10 +2817,7 @@ get_mesa_program(struct gl_context *ctx,
prog->NumTemporaries = v.next_temp;
- int num_instructions = 0;
- foreach_in_list(ir_instruction, node, &v.instructions) {
- num_instructions++;
- }
+ unsigned num_instructions = v.instructions.length();
mesa_instructions =
(struct prog_instruction *)calloc(num_instructions,
diff --git a/mesalib/src/mesa/state_tracker/st_extensions.c b/mesalib/src/mesa/state_tracker/st_extensions.c
index 4207cb64a..aa59fbfa9 100644
--- a/mesalib/src/mesa/state_tracker/st_extensions.c
+++ b/mesalib/src/mesa/state_tracker/st_extensions.c
@@ -772,6 +772,9 @@ void st_init_extensions(struct st_context *st)
if (st->options.disable_glsl_line_continuations)
ctx->Const.DisableGLSLLineContinuations = 1;
+ if (st->options.allow_glsl_extension_directive_midshader)
+ ctx->Const.AllowGLSLExtensionDirectiveMidShader = GL_TRUE;
+
ctx->Const.MinMapBufferAlignment =
screen->get_param(screen, PIPE_CAP_MIN_MAP_BUFFER_ALIGNMENT);
diff --git a/mesalib/src/mesa/state_tracker/st_glsl_to_tgsi.cpp b/mesalib/src/mesa/state_tracker/st_glsl_to_tgsi.cpp
index f47cd7d53..5c51e63d9 100644
--- a/mesalib/src/mesa/state_tracker/st_glsl_to_tgsi.cpp
+++ b/mesalib/src/mesa/state_tracker/st_glsl_to_tgsi.cpp
@@ -2049,6 +2049,9 @@ glsl_to_tgsi_visitor::visit(ir_expression *ir)
case ir_binop_ldexp:
case ir_binop_carry:
case ir_binop_borrow:
+ case ir_unop_interpolate_at_centroid:
+ case ir_binop_interpolate_at_offset:
+ case ir_binop_interpolate_at_sample:
/* This operation is not supported, or should have already been handled.
*/
assert(!"Invalid ir opcode in glsl_to_tgsi_visitor::visit()");
@@ -2820,7 +2823,13 @@ glsl_to_tgsi_visitor::visit(ir_texture *ir)
}
break;
case ir_txb:
- opcode = is_cube_array ? TGSI_OPCODE_TXB2 : TGSI_OPCODE_TXB;
+ if (is_cube_array ||
+ sampler_type == glsl_type::samplerCubeShadow_type) {
+ opcode = TGSI_OPCODE_TXB2;
+ }
+ else {
+ opcode = TGSI_OPCODE_TXB;
+ }
ir->lod_info.bias->accept(this);
lod_info = this->result;
if (ir->offset) {
diff --git a/mesalib/src/mesa/vbo/vbo_context.h b/mesalib/src/mesa/vbo/vbo_context.h
index 1680e23dc..e22451305 100644
--- a/mesalib/src/mesa/vbo/vbo_context.h
+++ b/mesalib/src/mesa/vbo/vbo_context.h
@@ -57,18 +57,6 @@
#include "vbo_save.h"
-/** Used to signal when transitioning from one kind of drawing method
- * to another.
- */
-enum draw_method
-{
- DRAW_NONE, /**< Initial value only */
- DRAW_BEGIN_END,
- DRAW_DISPLAY_LIST,
- DRAW_ARRAYS
-};
-
-
struct vbo_context {
struct gl_client_array currval[VBO_ATTRIB_MAX];
@@ -83,8 +71,6 @@ struct vbo_context {
* is responsible for initiating any fallback actions required:
*/
vbo_draw_func draw_prims;
-
- enum draw_method last_draw_method;
};
@@ -122,11 +108,11 @@ get_program_mode( struct gl_context *ctx )
* that arrays may be changing.
*/
static inline void
-vbo_draw_method(struct vbo_context *vbo, enum draw_method method)
+vbo_draw_method(struct vbo_context *vbo, gl_draw_method method)
{
- if (vbo->last_draw_method != method) {
- struct gl_context *ctx = vbo->exec.ctx;
+ struct gl_context *ctx = vbo->exec.ctx;
+ if (ctx->Array.DrawMethod != method) {
switch (method) {
case DRAW_ARRAYS:
ctx->Array._DrawArrays = vbo->exec.array.inputs;
@@ -142,7 +128,7 @@ vbo_draw_method(struct vbo_context *vbo, enum draw_method method)
}
ctx->NewDriverState |= ctx->DriverFlags.NewArray;
- vbo->last_draw_method = method;
+ ctx->Array.DrawMethod = method;
}
}
diff --git a/mesalib/src/mesa/vbo/vbo_exec.c b/mesalib/src/mesa/vbo/vbo_exec.c
index bd2b1b1a9..eb9035043 100644
--- a/mesalib/src/mesa/vbo/vbo_exec.c
+++ b/mesalib/src/mesa/vbo/vbo_exec.c
@@ -82,21 +82,6 @@ void vbo_exec_invalidate_state( struct gl_context *ctx, GLuint new_state )
if (!exec->validating && new_state & (_NEW_PROGRAM|_NEW_ARRAY)) {
exec->array.recalculate_inputs = GL_TRUE;
-
- /* If we ended up here because a VAO was deleted, the _DrawArrays
- * pointer which pointed to the VAO might be invalid now, so set it
- * to NULL. This prevents crashes in driver functions like Clear
- * where driver state validation might occur, but the vbo module is
- * still in an invalid state.
- *
- * Drivers should skip vertex array state validation if _DrawArrays
- * is NULL. It also has no effect on performance, because attrib
- * bindings will be recalculated anyway.
- */
- if (vbo->last_draw_method == DRAW_ARRAYS) {
- ctx->Array._DrawArrays = NULL;
- vbo->last_draw_method = DRAW_NONE;
- }
}
if (new_state & _NEW_EVAL)