#include "main/core.h"
#include "main/context.h"
-#include "ir.h"
-#include "ir_uniform.h"
-#include "program/hash_table.h"
-#include "../glsl/program.h"
-#include "../glsl/ir_uniform.h"
-#include "../glsl/glsl_parser_extras.h"
#include "main/shaderapi.h"
#include "main/shaderobj.h"
-#include "uniforms.h"
+#include "main/uniforms.h"
+#include "compiler/glsl/ir.h"
+#include "compiler/glsl/ir_uniform.h"
+#include "compiler/glsl/glsl_parser_extras.h"
+#include "compiler/glsl/program.h"
+#include "program/hash_table.h"
extern "C" void GLAPIENTRY
return;
}
- if ((uni->type->base_type == GLSL_TYPE_DOUBLE &&
- returnType != GLSL_TYPE_DOUBLE) ||
- (uni->type->base_type != GLSL_TYPE_DOUBLE &&
- returnType == GLSL_TYPE_DOUBLE)) {
- _mesa_error( ctx, GL_INVALID_OPERATION,
- "glGetnUniform*vARB(incompatible uniform types)");
- return;
- }
{
unsigned elements = (uni->type->is_sampler())
? 1 : uni->type->components();
const int dmul = uni->type->base_type == GLSL_TYPE_DOUBLE ? 2 : 1;
+ const int rmul = returnType == GLSL_TYPE_DOUBLE ? 2 : 1;
/* Calculate the source base address *BEFORE* modifying elements to
* account for the size of the user's buffer.
returnType == GLSL_TYPE_UINT || returnType == GLSL_TYPE_DOUBLE);
/* doubles have a different size than the other 3 types */
- unsigned bytes = sizeof(src[0]) * elements * dmul;
+ unsigned bytes = sizeof(src[0]) * elements * rmul;
if (bufSize < 0 || bytes > (unsigned) bufSize) {
_mesa_error( ctx, GL_INVALID_OPERATION,
"glGetnUniform*vARB(out of bounds: bufSize is %d,"
} else {
union gl_constant_value *const dst =
(union gl_constant_value *) paramsOut;
-
/* This code could be optimized by putting the loop inside the switch
* statements. However, this is not expected to be
* performance-critical code.
*/
for (unsigned i = 0; i < elements; i++) {
+ int sidx = i * dmul;
+ int didx = i * rmul;
+
switch (returnType) {
case GLSL_TYPE_FLOAT:
switch (uni->type->base_type) {
case GLSL_TYPE_UINT:
- dst[i].f = (float) src[i].u;
+ dst[didx].f = (float) src[sidx].u;
break;
case GLSL_TYPE_INT:
case GLSL_TYPE_SAMPLER:
case GLSL_TYPE_IMAGE:
- dst[i].f = (float) src[i].i;
+ dst[didx].f = (float) src[sidx].i;
break;
case GLSL_TYPE_BOOL:
- dst[i].f = src[i].i ? 1.0f : 0.0f;
+ dst[didx].f = src[sidx].i ? 1.0f : 0.0f;
+ break;
+ case GLSL_TYPE_DOUBLE:
+ dst[didx].f = *(double *)&src[sidx].f;
+ break;
+ default:
+ assert(!"Should not get here.");
+ break;
+ }
+ break;
+ case GLSL_TYPE_DOUBLE:
+ switch (uni->type->base_type) {
+ case GLSL_TYPE_UINT:
+ *(double *)&dst[didx].f = (double) src[sidx].u;
+ break;
+ case GLSL_TYPE_INT:
+ case GLSL_TYPE_SAMPLER:
+ case GLSL_TYPE_IMAGE:
+ *(double *)&dst[didx].f = (double) src[sidx].i;
+ break;
+ case GLSL_TYPE_BOOL:
+ *(double *)&dst[didx].f = src[sidx].i ? 1.0f : 0.0f;
+ break;
+ case GLSL_TYPE_FLOAT:
+ *(double *)&dst[didx].f = (double) src[sidx].f;
break;
default:
assert(!"Should not get here.");
break;
}
break;
-
case GLSL_TYPE_INT:
case GLSL_TYPE_UINT:
switch (uni->type->base_type) {
* a floating-point value is rounded to the
* nearest integer..."
*/
- dst[i].i = IROUND(src[i].f);
+ dst[didx].i = IROUND(src[sidx].f);
break;
case GLSL_TYPE_BOOL:
- dst[i].i = src[i].i ? 1 : 0;
+ dst[didx].i = src[sidx].i ? 1 : 0;
+ break;
+ case GLSL_TYPE_DOUBLE:
+ dst[didx].i = IROUNDD(*(double *)&src[sidx].f);
break;
default:
assert(!"Should not get here.");
return;
}
}
+ /* We need to reset the validate flag on changes to samplers in case
+ * two different sampler types are set to the same texture unit.
+ */
+ ctx->_Shader->Validated = GL_FALSE;
}
if (uni->type->is_image()) {
}
}
- uni->initialized = true;
-
_mesa_propagate_uniforms_to_driver_storage(uni, offset, count);
/* If the uniform is a sampler, do the extra magic necessary to propagate
/* If the shader stage doesn't use the sampler uniform, skip this.
*/
- if (sh == NULL || !uni->sampler[i].active)
+ if (sh == NULL || !uni->opaque[i].active)
continue;
for (int j = 0; j < count; j++) {
- sh->SamplerUnits[uni->sampler[i].index + offset + j] =
+ sh->SamplerUnits[uni->opaque[i].index + offset + j] =
((unsigned *) values)[j];
}
*/
if (uni->type->is_image()) {
for (int i = 0; i < MESA_SHADER_STAGES; i++) {
- if (uni->image[i].active) {
+ if (uni->opaque[i].active) {
struct gl_shader *sh = shProg->_LinkedShaders[i];
for (int j = 0; j < count; j++)
- sh->ImageUnits[uni->image[i].index + offset + j] =
+ sh->ImageUnits[uni->opaque[i].index + offset + j] =
((GLint *) values)[j];
}
}
elements = components * vectors;
if (!transpose) {
- memcpy(&uni->storage[elements * offset], values,
+ memcpy(&uni->storage[size_mul * elements * offset], values,
sizeof(uni->storage[0]) * elements * count * size_mul);
} else if (basicType == GLSL_TYPE_FLOAT) {
/* Copy and transpose the matrix.
}
}
- uni->initialized = true;
-
_mesa_propagate_uniforms_to_driver_storage(uni, offset, count);
}