summaryrefslogtreecommitdiff
path: root/src/mesa/pipe/i915simple
diff options
context:
space:
mode:
authorBrian <brian.paul@tungstengraphics.com>2007-08-22 12:24:51 -0600
committerBrian <brian.paul@tungstengraphics.com>2007-08-22 12:26:46 -0600
commitc0bb4ba9e665e40a325d82aa2ee48d7b8abd603b (patch)
tree48338074f07042599856e95b4529e0ffbca4be63 /src/mesa/pipe/i915simple
parentd1fbf621dc48a488c0f860c5851332d269e6d637 (diff)
Rework of shader constant buffers.
They're now totally independent of the actual shaders. Also, implemented in terms of pipe_buffer_handles/objects.
Diffstat (limited to 'src/mesa/pipe/i915simple')
-rw-r--r--src/mesa/pipe/i915simple/i915_context.c3
-rw-r--r--src/mesa/pipe/i915simple/i915_context.h16
-rw-r--r--src/mesa/pipe/i915simple/i915_fpc.h8
-rw-r--r--src/mesa/pipe/i915simple/i915_fpc_emit.c81
-rw-r--r--src/mesa/pipe/i915simple/i915_fpc_translate.c20
-rw-r--r--src/mesa/pipe/i915simple/i915_state.c40
-rw-r--r--src/mesa/pipe/i915simple/i915_state_emit.c6
7 files changed, 93 insertions, 81 deletions
diff --git a/src/mesa/pipe/i915simple/i915_context.c b/src/mesa/pipe/i915simple/i915_context.c
index 9856c7c10c..f4121419f7 100644
--- a/src/mesa/pipe/i915simple/i915_context.c
+++ b/src/mesa/pipe/i915simple/i915_context.c
@@ -186,6 +186,9 @@ static boolean i915_draw_elements( struct pipe_context *pipe,
draw_set_mapped_element_buffer(draw, 0, NULL);
}
+ draw_set_mapped_constant_buffer(draw,
+ i915->current.constants[PIPE_SHADER_VERTEX]);
+
/* draw! */
draw_arrays(i915->draw, prim, start, count);
diff --git a/src/mesa/pipe/i915simple/i915_context.h b/src/mesa/pipe/i915simple/i915_context.h
index b40dfa695b..a037b20289 100644
--- a/src/mesa/pipe/i915simple/i915_context.h
+++ b/src/mesa/pipe/i915simple/i915_context.h
@@ -30,10 +30,10 @@
#include "pipe/p_context.h"
+#include "pipe/p_defines.h"
#include "pipe/p_state.h"
-
#define I915_TEX_UNITS 8
#define I915_DYNAMIC_MODES4 0
@@ -74,6 +74,7 @@
#define I915_CACHE_CONSTANTS 5
#define I915_MAX_CACHE 6
+#define I915_MAX_CONSTANT 32
struct i915_cache_context;
@@ -85,10 +86,14 @@ struct i915_state
unsigned immediate[I915_MAX_IMMEDIATE];
unsigned dynamic[I915_MAX_DYNAMIC];
+ float constants[PIPE_SHADER_TYPES][I915_MAX_CONSTANT][4];
+ /** number of constants passed in through a constant buffer */
+ uint num_user_constants[PIPE_SHADER_TYPES];
+ /** user constants, plus extra constants from shader translation */
+ uint num_constants[PIPE_SHADER_TYPES];
+
uint *program;
uint program_len;
- uint *constants;
- uint num_constants;
unsigned sampler[I915_TEX_UNITS][3];
unsigned sampler_enable_flags;
@@ -112,6 +117,7 @@ struct i915_context
struct pipe_blend_color blend_color;
struct pipe_clear_color_state clear_color;
struct pipe_clip_state clip;
+ struct pipe_constant_buffer constants[PIPE_SHADER_TYPES];
struct pipe_depth_state depth_test;
struct pipe_framebuffer_state framebuffer;
struct pipe_shader_state fs;
@@ -124,8 +130,6 @@ struct i915_context
struct pipe_viewport_state viewport;
struct pipe_vertex_buffer vertex_buffer[PIPE_ATTRIB_MAX];
- struct pipe_constant_buffer temp_constants; /*XXX temporary*/
-
unsigned dirty;
unsigned *batch_start;
@@ -156,6 +160,8 @@ struct i915_context
#define I915_NEW_SAMPLER 0x400
#define I915_NEW_TEXTURE 0x800
#define I915_NEW_STENCIL 0x1000
+#define I915_NEW_CONSTANTS 0x2000
+
/* Driver's internally generated state flags:
*/
diff --git a/src/mesa/pipe/i915simple/i915_fpc.h b/src/mesa/pipe/i915simple/i915_fpc.h
index 30bc290ad8..afef706418 100644
--- a/src/mesa/pipe/i915simple/i915_fpc.h
+++ b/src/mesa/pipe/i915simple/i915_fpc.h
@@ -37,7 +37,6 @@
#define I915_PROGRAM_SIZE 192
-#define I915_MAX_CONSTANT 32
#define MAX_VARYING 8
@@ -99,9 +98,10 @@ struct i915_fp_compile {
uint declarations[I915_PROGRAM_SIZE];
uint program[I915_PROGRAM_SIZE];
- uint constant_flags[I915_MAX_CONSTANT];
-
- struct pipe_constant_buffer *constants;
+ /** points into the i915->current.constants array: */
+ float (*constants)[4];
+ uint num_constants;
+ uint constant_flags[I915_MAX_CONSTANT]; /**< status of each constant */
uint *csr; /* Cursor, points into program.
*/
diff --git a/src/mesa/pipe/i915simple/i915_fpc_emit.c b/src/mesa/pipe/i915simple/i915_fpc_emit.c
index 26a4f36e71..dfbc5f180c 100644
--- a/src/mesa/pipe/i915simple/i915_fpc_emit.c
+++ b/src/mesa/pipe/i915simple/i915_fpc_emit.c
@@ -244,25 +244,14 @@ i915_emit_const1f(struct i915_fp_compile * p, float c0)
if (p->constant_flags[reg] == I915_CONSTFLAG_PARAM)
continue;
for (idx = 0; idx < 4; idx++) {
-#if 0
- if (!(p->constant_flags[reg] & (1 << idx)) ||
- p->fp->constant[reg][idx] == c0) {
- p->fp->constant[reg][idx] = c0;
- p->constant_flags[reg] |= 1 << idx;
- if (reg + 1 > p->fp->nr_constants)
- p->fp->nr_constants = reg + 1;
- return swizzle(UREG(REG_TYPE_CONST, reg), idx, ZERO, ZERO, ONE);
- }
-#else
if (!(p->constant_flags[reg] & (1 << idx)) ||
- p->constants->constant[reg][idx] == c0) {
- p->constants->constant[reg][idx] = c0;
+ p->constants[reg][idx] == c0) {
+ p->constants[reg][idx] = c0;
p->constant_flags[reg] |= 1 << idx;
- if (reg + 1 > p->constants->nr_constants)
- p->constants->nr_constants = reg + 1;
+ if (reg + 1 > p->num_constants)
+ p->num_constants = reg + 1;
return swizzle(UREG(REG_TYPE_CONST, reg), idx, ZERO, ZERO, ONE);
}
-#endif
}
}
@@ -291,23 +280,12 @@ i915_emit_const2f(struct i915_fp_compile * p, float c0, float c1)
continue;
for (idx = 0; idx < 3; idx++) {
if (!(p->constant_flags[reg] & (3 << idx))) {
-#if 0
- p->fp->constant[reg][idx] = c0;
- p->fp->constant[reg][idx + 1] = c1;
+ p->constants[reg][idx + 0] = c0;
+ p->constants[reg][idx + 1] = c1;
p->constant_flags[reg] |= 3 << idx;
- if (reg + 1 > p->fp->nr_constants)
- p->fp->nr_constants = reg + 1;
- return swizzle(UREG(REG_TYPE_CONST, reg), idx, idx + 1, ZERO,
- ONE);
-#else
- p->constants->constant[reg][idx + 0] = c0;
- p->constants->constant[reg][idx + 1] = c1;
- p->constant_flags[reg] |= 3 << idx;
- if (reg + 1 > p->constants->nr_constants)
- p->constants->nr_constants = reg + 1;
- return swizzle(UREG(REG_TYPE_CONST, reg), idx, idx + 1, ZERO,
- ONE);
-#endif
+ if (reg + 1 > p->num_constants)
+ p->num_constants = reg + 1;
+ return swizzle(UREG(REG_TYPE_CONST, reg), idx, idx + 1, ZERO, ONE);
}
}
}
@@ -326,40 +304,21 @@ i915_emit_const4f(struct i915_fp_compile * p,
for (reg = 0; reg < I915_MAX_CONSTANT; reg++) {
if (p->constant_flags[reg] == 0xf &&
-#if 0
- p->fp->constant[reg][0] == c0 &&
- p->fp->constant[reg][1] == c1 &&
- p->fp->constant[reg][2] == c2 &&
- p->fp->constant[reg][3] == c3
-#else
- p->constants->constant[reg][0] == c0 &&
- p->constants->constant[reg][1] == c1 &&
- p->constants->constant[reg][2] == c2 &&
- p->constants->constant[reg][3] == c3
-#endif
- ) {
+ p->constants[reg][0] == c0 &&
+ p->constants[reg][1] == c1 &&
+ p->constants[reg][2] == c2 &&
+ p->constants[reg][3] == c3) {
return UREG(REG_TYPE_CONST, reg);
}
else if (p->constant_flags[reg] == 0) {
-#if 0
- p->fp->constant[reg][0] = c0;
- p->fp->constant[reg][1] = c1;
- p->fp->constant[reg][2] = c2;
- p->fp->constant[reg][3] = c3;
-#else
- p->constants->constant[reg][0] = c0;
- p->constants->constant[reg][1] = c1;
- p->constants->constant[reg][2] = c2;
- p->constants->constant[reg][3] = c3;
-#endif
+
+ p->constants[reg][0] = c0;
+ p->constants[reg][1] = c1;
+ p->constants[reg][2] = c2;
+ p->constants[reg][3] = c3;
p->constant_flags[reg] = 0xf;
-#if 0
- if (reg + 1 > p->fp->nr_constants)
- p->fp->nr_constants = reg + 1;
-#else
- if (reg + 1 > p->constants->nr_constants)
- p->constants->nr_constants = reg + 1;
-#endif
+ if (reg + 1 > p->num_constants)
+ p->num_constants = reg + 1;
return UREG(REG_TYPE_CONST, reg);
}
}
diff --git a/src/mesa/pipe/i915simple/i915_fpc_translate.c b/src/mesa/pipe/i915simple/i915_fpc_translate.c
index db2691ebe1..dcf0d18f4e 100644
--- a/src/mesa/pipe/i915simple/i915_fpc_translate.c
+++ b/src/mesa/pipe/i915simple/i915_fpc_translate.c
@@ -102,8 +102,8 @@ i915_use_passthrough_shader(struct i915_context *i915)
i915->current.program_len = Elements(passthrough);
}
- i915->current.constants = NULL;
- i915->current.num_constants = 0;
+ i915->current.num_constants[PIPE_SHADER_FRAGMENT] = 0;
+ i915->current.num_user_constants[PIPE_SHADER_FRAGMENT] = 0;
}
@@ -870,11 +870,11 @@ i915_init_compile(struct i915_context *i915,
p->shader = &i915->fs;
- /* a bit of a hack, need to improve constant buffer infrastructure */
- if (i915->fs.constants)
- p->constants = i915->fs.constants;
- else
- p->constants = &i915->temp_constants;
+ /* new constants found during translation get appended after the
+ * user-provided constants.
+ */
+ p->constants = i915->current.constants[PIPE_SHADER_FRAGMENT];
+ p->num_constants = i915->current.num_user_constants[PIPE_SHADER_FRAGMENT];
p->nr_tex_indirect = 1; /* correct? */
p->nr_tex_insn = 0;
@@ -960,8 +960,10 @@ i915_fini_compile(struct i915_context *i915, struct i915_fp_compile *p)
program_size * sizeof(uint));
}
- i915->current.constants = (uint *) p->constants->constant;
- i915->current.num_constants = p->constants->nr_constants;
+ /* update number of constants */
+ i915->current.num_constants[PIPE_SHADER_FRAGMENT] = p->num_constants;
+ assert(i915->current.num_constants[PIPE_SHADER_FRAGMENT]
+ >= i915->current.num_user_constants[PIPE_SHADER_FRAGMENT]);
}
/* Release the compilation struct:
diff --git a/src/mesa/pipe/i915simple/i915_state.c b/src/mesa/pipe/i915simple/i915_state.c
index e8ffd1fd7b..8f8b13253d 100644
--- a/src/mesa/pipe/i915simple/i915_state.c
+++ b/src/mesa/pipe/i915simple/i915_state.c
@@ -30,6 +30,7 @@
#include "pipe/draw/draw_context.h"
+#include "pipe/p_winsys.h"
#include "i915_context.h"
#include "i915_state.h"
@@ -131,6 +132,44 @@ static void i915_set_vs_state( struct pipe_context *pipe,
}
+static void i915_set_constant_buffer(struct pipe_context *pipe,
+ uint shader, uint index,
+ const struct pipe_constant_buffer *buf)
+{
+ struct i915_context *i915 = i915_context(pipe);
+ struct pipe_winsys *ws = pipe->winsys;
+
+ assert(shader < PIPE_SHADER_TYPES);
+ assert(index == 0);
+
+ /* Make a copy of shader constants.
+ * During fragment program translation we may add additional
+ * constants to the array.
+ *
+ * We want to consider the situation where some user constants
+ * (ex: a material color) may change frequently but the shader program
+ * stays the same. In that case we should only be updating the first
+ * N constants, leaving any extras from shader translation alone.
+ */
+ {
+ void *mapped;
+ if (buf->size &&
+ (mapped = ws->buffer_map(ws, buf->buffer, PIPE_BUFFER_FLAG_READ))) {
+ memcpy(i915->current.constants[shader], mapped, buf->size);
+ fprintf(stderr, "i915 problem: map of constant buffer failed\n");
+ ws->buffer_unmap(ws, buf->buffer);
+ i915->current.num_user_constants[shader]
+ = buf->size / (4 * sizeof(float));
+ }
+ else {
+ i915->current.num_user_constants[shader] = 0;
+ }
+ }
+
+ i915->dirty |= I915_NEW_CONSTANTS;
+}
+
+
static void i915_set_sampler_state(struct pipe_context *pipe,
unsigned unit,
const struct pipe_sampler_state *sampler)
@@ -256,6 +295,7 @@ i915_init_state_functions( struct i915_context *i915 )
i915->pipe.set_blend_state = i915_set_blend_state;
i915->pipe.set_clip_state = i915_set_clip_state;
i915->pipe.set_clear_color_state = i915_set_clear_color_state;
+ i915->pipe.set_constant_buffer = i915_set_constant_buffer;
i915->pipe.set_depth_state = i915_set_depth_test_state;
i915->pipe.set_framebuffer_state = i915_set_framebuffer_state;
i915->pipe.set_fs_state = i915_set_fs_state;
diff --git a/src/mesa/pipe/i915simple/i915_state_emit.c b/src/mesa/pipe/i915simple/i915_state_emit.c
index dcf02abb14..dff9d40a83 100644
--- a/src/mesa/pipe/i915simple/i915_state_emit.c
+++ b/src/mesa/pipe/i915simple/i915_state_emit.c
@@ -216,9 +216,11 @@ i915_emit_hardware_state(struct i915_context *i915 )
/* constants */
if (i915->hardware_dirty & I915_HW_PROGRAM)
{
- const uint nr = i915->current.num_constants;
+ const uint nr = i915->current.num_constants[PIPE_SHADER_FRAGMENT];
+ assert(nr <= I915_MAX_CONSTANT);
if (nr > 0) {
- const uint *c = (const uint *) i915->current.constants;
+ const uint *c
+ = (const uint *) i915->current.constants[PIPE_SHADER_FRAGMENT];
uint i;
OUT_BATCH( _3DSTATE_PIXEL_SHADER_CONSTANTS | (nr * 4) );
OUT_BATCH( (1 << (nr - 1)) | ((1 << (nr - 1)) - 1) );