summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorZou Nan hai <[email protected]>2008-03-13 14:46:38 +0800
committerZou Nan hai <[email protected]>2008-03-13 14:46:38 +0800
commitfcb7cb9e72ecac7c165a3a6ed7a033e2e6793a26 (patch)
tree8508705f5659c61d28f972307faacae97bfa5795
parent9110425c72e45f618131b559eba883fd6c5536b4 (diff)
[i965] multiple rendering target support
-rw-r--r--src/mesa/drivers/dri/i915/i830_vtbl.c7
-rw-r--r--src/mesa/drivers/dri/i915/i915_vtbl.c7
-rw-r--r--src/mesa/drivers/dri/i965/brw_context.h7
-rw-r--r--src/mesa/drivers/dri/i965/brw_fallback.c10
-rw-r--r--src/mesa/drivers/dri/i965/brw_metaops.c12
-rw-r--r--src/mesa/drivers/dri/i965/brw_vtbl.c15
-rw-r--r--src/mesa/drivers/dri/i965/brw_wm.c5
-rw-r--r--src/mesa/drivers/dri/i965/brw_wm.h2
-rw-r--r--src/mesa/drivers/dri/i965/brw_wm_emit.c24
-rw-r--r--src/mesa/drivers/dri/i965/brw_wm_fp.c28
-rw-r--r--src/mesa/drivers/dri/i965/brw_wm_glsl.c23
-rw-r--r--src/mesa/drivers/dri/i965/brw_wm_pass0.c2
-rw-r--r--src/mesa/drivers/dri/i965/brw_wm_surface_state.c54
-rw-r--r--src/mesa/drivers/dri/intel/intel_buffers.c32
-rw-r--r--src/mesa/drivers/dri/intel/intel_context.h5
15 files changed, 135 insertions, 98 deletions
diff --git a/src/mesa/drivers/dri/i915/i830_vtbl.c b/src/mesa/drivers/dri/i915/i830_vtbl.c
index 9bc868b043b..1f4bc91d77e 100644
--- a/src/mesa/drivers/dri/i915/i830_vtbl.c
+++ b/src/mesa/drivers/dri/i915/i830_vtbl.c
@@ -609,11 +609,12 @@ i830_state_draw_region(struct intel_context *intel,
static void
i830_set_draw_region(struct intel_context *intel,
- struct intel_region *color_region,
- struct intel_region *depth_region)
+ struct intel_region *color_regions[],
+ struct intel_region *depth_region,
+ GLuint num_regions)
{
struct i830_context *i830 = i830_context(&intel->ctx);
- i830_state_draw_region(intel, &i830->state, color_region, depth_region);
+ i830_state_draw_region(intel, &i830->state, color_regions[0], depth_region);
}
#if 0
diff --git a/src/mesa/drivers/dri/i915/i915_vtbl.c b/src/mesa/drivers/dri/i915/i915_vtbl.c
index c856a8627de..40c5de26c63 100644
--- a/src/mesa/drivers/dri/i915/i915_vtbl.c
+++ b/src/mesa/drivers/dri/i915/i915_vtbl.c
@@ -532,11 +532,12 @@ i915_state_draw_region(struct intel_context *intel,
static void
i915_set_draw_region(struct intel_context *intel,
- struct intel_region *color_region,
- struct intel_region *depth_region)
+ struct intel_region *color_regions[],
+ struct intel_region *depth_region,
+ GLuint num_regions)
{
struct i915_context *i915 = i915_context(&intel->ctx);
- i915_state_draw_region(intel, &i915->state, color_region, depth_region);
+ i915_state_draw_region(intel, &i915->state, color_regions[0], depth_region);
}
diff --git a/src/mesa/drivers/dri/i965/brw_context.h b/src/mesa/drivers/dri/i965/brw_context.h
index 49e739b0ad8..4e6b471fdde 100644
--- a/src/mesa/drivers/dri/i965/brw_context.h
+++ b/src/mesa/drivers/dri/i965/brw_context.h
@@ -240,7 +240,7 @@ struct brw_vs_ouput_sizes {
#define BRW_MAX_TEX_UNIT 8
-#define BRW_WM_MAX_SURF BRW_MAX_TEX_UNIT + 1
+#define BRW_WM_MAX_SURF BRW_MAX_TEX_UNIT + MAX_DRAW_BUFFERS
enum brw_cache_id {
BRW_CC_VP,
@@ -425,8 +425,8 @@ struct brw_context
struct brw_tracked_state **atoms;
GLuint nr_atoms;
-
- struct intel_region *draw_region;
+ GLuint nr_draw_regions;
+ struct intel_region *draw_regions[MAX_DRAW_BUFFERS];
struct intel_region *depth_region;
} state;
@@ -461,6 +461,7 @@ struct brw_context
struct gl_buffer_object *vbo;
struct intel_region *saved_draw_region;
+ GLuint saved_nr_draw_regions;
struct intel_region *saved_depth_region;
GLuint restore_draw_buffers[MAX_DRAW_BUFFERS];
diff --git a/src/mesa/drivers/dri/i965/brw_fallback.c b/src/mesa/drivers/dri/i965/brw_fallback.c
index 58aeeb4228c..ce0df0357b6 100644
--- a/src/mesa/drivers/dri/i965/brw_fallback.c
+++ b/src/mesa/drivers/dri/i965/brw_fallback.c
@@ -57,16 +57,6 @@ static GLboolean do_check_fallback(struct brw_context *brw)
return GL_TRUE;
}
- /* _NEW_BUFFERS
- */
- /* We can only handle a single draw buffer at the moment, and only as the
- * first color buffer.
- */
- if (fb->_NumColorDrawBuffers > 1) {
- DBG("FALLBACK: multiple color draw buffers\n");
- return GL_TRUE;
- }
-
/* _NEW_RENDERMODE
*
* XXX: need to save/restore RenderMode in metaops state, or
diff --git a/src/mesa/drivers/dri/i965/brw_metaops.c b/src/mesa/drivers/dri/i965/brw_metaops.c
index 7b34f0f3bd6..252a8996e26 100644
--- a/src/mesa/drivers/dri/i965/brw_metaops.c
+++ b/src/mesa/drivers/dri/i965/brw_metaops.c
@@ -362,11 +362,13 @@ static void meta_draw_region( struct intel_context *intel,
struct brw_context *brw = brw_context(&intel->ctx);
if (!brw->metaops.saved_draw_region) {
- brw->metaops.saved_draw_region = brw->state.draw_region;
+ brw->metaops.saved_draw_region = brw->state.draw_regions[0];
+ brw->metaops.saved_nr_draw_regions = brw->state.nr_draw_regions;
brw->metaops.saved_depth_region = brw->state.depth_region;
}
- brw->state.draw_region = draw_region;
+ brw->state.draw_regions[0] = draw_region;
+ brw->state.nr_draw_regions = 1;
brw->state.depth_region = depth_region;
if (intel->frame_buffer_texobj != NULL)
@@ -509,7 +511,8 @@ static void install_meta_state( struct intel_context *intel )
/* This works without adjusting refcounts. Fix later?
*/
- brw->metaops.saved_draw_region = brw->state.draw_region;
+ brw->metaops.saved_draw_region = brw->state.draw_regions[0];
+ brw->metaops.saved_nr_draw_regions = brw->state.nr_draw_regions;
brw->metaops.saved_depth_region = brw->state.depth_region;
brw->metaops.active = 1;
@@ -532,7 +535,8 @@ static void leave_meta_state( struct intel_context *intel )
ctx->FragmentProgram.Current = brw->metaops.restore_fp;
- brw->state.draw_region = brw->metaops.saved_draw_region;
+ brw->state.draw_regions[0] = brw->metaops.saved_draw_region;
+ brw->state.nr_draw_regions = brw->metaops.saved_nr_draw_regions;
brw->state.depth_region = brw->metaops.saved_depth_region;
brw->metaops.saved_draw_region = NULL;
brw->metaops.saved_depth_region = NULL;
diff --git a/src/mesa/drivers/dri/i965/brw_vtbl.c b/src/mesa/drivers/dri/i965/brw_vtbl.c
index cdbbe7b6994..31e96a250ac 100644
--- a/src/mesa/drivers/dri/i965/brw_vtbl.c
+++ b/src/mesa/drivers/dri/i965/brw_vtbl.c
@@ -70,18 +70,21 @@ static void brw_destroy_context( struct intel_context *intel )
/* called from intelDrawBuffer()
*/
static void brw_set_draw_region( struct intel_context *intel,
- struct intel_region *draw_region,
- struct intel_region *depth_region)
+ struct intel_region *draw_regions[],
+ struct intel_region *depth_region,
+ GLuint num_regions)
{
struct brw_context *brw = brw_context(&intel->ctx);
-
+ int i;
if (brw->state.depth_region != depth_region)
brw->state.dirty.brw |= BRW_NEW_DEPTH_BUFFER;
-
- intel_region_release(&brw->state.draw_region);
+ for (i = 0; i < brw->state.nr_draw_regions; i++)
+ intel_region_release(&brw->state.draw_regions[i]);
intel_region_release(&brw->state.depth_region);
- intel_region_reference(&brw->state.draw_region, draw_region);
+ for (i = 0; i < num_regions; i++)
+ intel_region_reference(&brw->state.draw_regions[i], draw_regions[i]);
intel_region_reference(&brw->state.depth_region, depth_region);
+ brw->state.nr_draw_regions = num_regions;
}
diff --git a/src/mesa/drivers/dri/i965/brw_wm.c b/src/mesa/drivers/dri/i965/brw_wm.c
index 47665692e3b..abdc92bf014 100644
--- a/src/mesa/drivers/dri/i965/brw_wm.c
+++ b/src/mesa/drivers/dri/i965/brw_wm.c
@@ -139,6 +139,7 @@ static void do_wm_prog( struct brw_context *brw,
c->fp = fp;
c->env_param = brw->intel.ctx.FragmentProgram.Parameters;
+ brw_init_compile(brw, &c->func);
if (brw_wm_is_glsl(&c->fp->program)) {
brw_wm_glsl_emit(brw, c);
} else {
@@ -160,10 +161,6 @@ static void do_wm_prog( struct brw_context *brw,
*/
c->grf_limit = BRW_WM_MAX_GRF/2;
- /* This is where we start emitting gen4 code:
- */
- brw_init_compile(brw, &c->func);
-
brw_wm_pass2(c);
c->prog_data.total_grf = c->max_wm_grf;
diff --git a/src/mesa/drivers/dri/i965/brw_wm.h b/src/mesa/drivers/dri/i965/brw_wm.h
index 441fbd33fb4..5ca2a634c07 100644
--- a/src/mesa/drivers/dri/i965/brw_wm.h
+++ b/src/mesa/drivers/dri/i965/brw_wm.h
@@ -143,6 +143,8 @@ struct brw_wm_instruction {
GLuint writemask:4;
GLuint tex_unit:4; /* texture unit for TEX, TXD, TXP instructions */
GLuint tex_idx:3; /* TEXTURE_1D,2D,3D,CUBE,RECT_INDEX source target */
+ GLuint eot:1; /* End of thread indicator for FB_WRITE*/
+ GLuint target:10; /* target binding table index for FB_WRITE*/
};
diff --git a/src/mesa/drivers/dri/i965/brw_wm_emit.c b/src/mesa/drivers/dri/i965/brw_wm_emit.c
index df51f73dd84..4c0bd67c923 100644
--- a/src/mesa/drivers/dri/i965/brw_wm_emit.c
+++ b/src/mesa/drivers/dri/i965/brw_wm_emit.c
@@ -696,7 +696,7 @@ static void emit_tex( struct brw_wm_compile *c,
retype(vec16(dst[0]), BRW_REGISTER_TYPE_UW),
1,
retype(c->payload.depth[0].hw_reg, BRW_REGISTER_TYPE_UW),
- inst->tex_unit + 1, /* surface */
+ inst->tex_unit + MAX_DRAW_BUFFERS, /* surface */
inst->tex_unit, /* sampler */
inst->writemask,
(shadow ?
@@ -749,7 +749,7 @@ static void emit_txb( struct brw_wm_compile *c,
retype(vec16(dst[0]), BRW_REGISTER_TYPE_UW),
1,
retype(c->payload.depth[0].hw_reg, BRW_REGISTER_TYPE_UW),
- inst->tex_unit + 1, /* surface */
+ inst->tex_unit + MAX_DRAW_BUFFERS, /* surface */
inst->tex_unit, /* sampler */
inst->writemask,
BRW_SAMPLER_MESSAGE_SIMD16_SAMPLE_BIAS,
@@ -822,7 +822,9 @@ static void emit_kil( struct brw_wm_compile *c,
static void fire_fb_write( struct brw_wm_compile *c,
GLuint base_reg,
- GLuint nr )
+ GLuint nr,
+ GLuint target,
+ GLuint eot )
{
struct brw_compile *p = &c->func;
@@ -845,10 +847,10 @@ static void fire_fb_write( struct brw_wm_compile *c,
retype(vec16(brw_null_reg()), BRW_REGISTER_TYPE_UW),
base_reg,
retype(brw_vec8_grf(0, 0), BRW_REGISTER_TYPE_UW),
- 0, /* render surface always 0 */
+ target,
nr,
0,
- 1);
+ eot);
}
static void emit_aa( struct brw_wm_compile *c,
@@ -873,7 +875,9 @@ static void emit_aa( struct brw_wm_compile *c,
static void emit_fb_write( struct brw_wm_compile *c,
struct brw_reg *arg0,
struct brw_reg *arg1,
- struct brw_reg *arg2)
+ struct brw_reg *arg2,
+ GLuint target,
+ GLuint eot)
{
struct brw_compile *p = &c->func;
GLuint nr = 2;
@@ -946,7 +950,7 @@ static void emit_fb_write( struct brw_wm_compile *c,
if (c->key.aa_dest_stencil_reg)
emit_aa(c, arg1, 2);
- fire_fb_write(c, 0, nr);
+ fire_fb_write(c, 0, nr, target, eot);
}
else {
struct brw_reg v1_null_ud = vec1(retype(brw_null_reg(), BRW_REGISTER_TYPE_UD));
@@ -963,14 +967,14 @@ static void emit_fb_write( struct brw_wm_compile *c,
jmp = brw_JMPI(p, ip, ip, brw_imm_w(0));
{
emit_aa(c, arg1, 2);
- fire_fb_write(c, 0, nr);
+ fire_fb_write(c, 0, nr, target, eot);
/* note - thread killed in subroutine */
}
brw_land_fwd_jump(p, jmp);
/* ELSE: Shuffle up one register to fill in the hole left for AA:
*/
- fire_fb_write(c, 1, nr-1);
+ fire_fb_write(c, 1, nr-1, target, eot);
}
}
@@ -1138,7 +1142,7 @@ void brw_wm_emit( struct brw_wm_compile *c )
break;
case WM_FB_WRITE:
- emit_fb_write(c, args[0], args[1], args[2]);
+ emit_fb_write(c, args[0], args[1], args[2], inst->target, inst->eot);
break;
/* Straightforward arithmetic:
diff --git a/src/mesa/drivers/dri/i965/brw_wm_fp.c b/src/mesa/drivers/dri/i965/brw_wm_fp.c
index 77cb3b27e3e..682b16d74dd 100644
--- a/src/mesa/drivers/dri/i965/brw_wm_fp.c
+++ b/src/mesa/drivers/dri/i965/brw_wm_fp.c
@@ -861,14 +861,28 @@ static void emit_fb_write( struct brw_wm_compile *c )
struct prog_src_register outcolor = src_reg(PROGRAM_OUTPUT, FRAG_RESULT_COLR);
struct prog_src_register payload_r0_depth = src_reg(PROGRAM_PAYLOAD, PAYLOAD_DEPTH);
struct prog_src_register outdepth = src_reg(PROGRAM_OUTPUT, FRAG_RESULT_DEPR);
+ GLuint i;
- emit_op(c,
- WM_FB_WRITE,
- dst_mask(dst_undef(),0),
- 0, 0, 0,
- outcolor,
- payload_r0_depth,
- outdepth);
+ struct prog_instruction *inst;
+ struct brw_context *brw = c->func.brw;
+
+ /* inst->Sampler is not used by backend,
+ use it for fb write target and eot */
+
+ inst = emit_op(c, WM_FB_WRITE, dst_mask(dst_undef(),0),
+ 0, 0, 0, outcolor, payload_r0_depth, outdepth);
+ inst->Sampler = (brw->state.nr_draw_regions > 1 ? 0: 1)|(0<<1);
+
+ if (brw->state.nr_draw_regions > 1) {
+ for (i = 0 ; i < brw->state.nr_draw_regions; i++) {
+ outcolor = src_reg(PROGRAM_OUTPUT, FRAG_RESULT_DATA0 + i);
+ inst = emit_op(c,
+ WM_FB_WRITE, dst_mask(dst_undef(),0), 0, 0, 0,
+ outcolor, payload_r0_depth, outdepth);
+ inst->Sampler = ((i == brw->state.nr_draw_regions - 1) ? 1: 0);
+ inst->Sampler |= (i<<1);
+ }
+ }
}
diff --git a/src/mesa/drivers/dri/i965/brw_wm_glsl.c b/src/mesa/drivers/dri/i965/brw_wm_glsl.c
index fd237ee0287..58520838826 100644
--- a/src/mesa/drivers/dri/i965/brw_wm_glsl.c
+++ b/src/mesa/drivers/dri/i965/brw_wm_glsl.c
@@ -274,10 +274,11 @@ static void emit_delta_xy(struct brw_wm_compile *c,
static void fire_fb_write( struct brw_wm_compile *c,
GLuint base_reg,
- GLuint nr )
+ GLuint nr,
+ GLuint target,
+ GLuint eot)
{
struct brw_compile *p = &c->func;
-
/* Pass through control information:
*/
/* mov (8) m1.0<1>:ud r1.0<8;8,1>:ud { Align1 NoMask } */
@@ -294,10 +295,10 @@ static void fire_fb_write( struct brw_wm_compile *c,
retype(vec8(brw_null_reg()), BRW_REGISTER_TYPE_UW),
base_reg,
retype(brw_vec8_grf(0, 0), BRW_REGISTER_TYPE_UW),
- 0, /* render surface always 0 */
+ target,
nr,
0,
- 1);
+ eot);
}
static void emit_fb_write(struct brw_wm_compile *c,
@@ -306,7 +307,8 @@ static void emit_fb_write(struct brw_wm_compile *c,
struct brw_compile *p = &c->func;
int nr = 2;
int channel;
- struct brw_reg src0;//, src1, src2, dst;
+ GLuint target, eot;
+ struct brw_reg src0;
/* Reserve a space for AA - may not be needed:
*/
@@ -337,8 +339,9 @@ static void emit_fb_write(struct brw_wm_compile *c,
nr += 2;
}
-
- fire_fb_write(c, 0, nr);
+ target = inst->Sampler >> 1;
+ eot = inst->Sampler & 1;
+ fire_fb_write(c, 0, nr, target, eot);
}
static void emit_pixel_w( struct brw_wm_compile *c,
@@ -1026,7 +1029,7 @@ static void emit_txb(struct brw_wm_compile *c,
retype(vec8(dst[0]), BRW_REGISTER_TYPE_UW),
1,
retype(payload_reg, BRW_REGISTER_TYPE_UW),
- inst->TexSrcUnit + 1, /* surface */
+ inst->TexSrcUnit + MAX_DRAW_BUFFERS, /* surface */
inst->TexSrcUnit, /* sampler */
inst->DstReg.WriteMask,
BRW_SAMPLER_MESSAGE_SIMD16_SAMPLE_BIAS,
@@ -1088,7 +1091,7 @@ static void emit_tex(struct brw_wm_compile *c,
retype(vec8(dst[0]), BRW_REGISTER_TYPE_UW),
1,
retype(payload_reg, BRW_REGISTER_TYPE_UW),
- inst->TexSrcUnit + 1, /* surface */
+ inst->TexSrcUnit + MAX_DRAW_BUFFERS, /* surface */
inst->TexSrcUnit, /* sampler */
inst->DstReg.WriteMask,
BRW_SAMPLER_MESSAGE_SIMD8_SAMPLE,
@@ -1125,7 +1128,6 @@ static void post_wm_emit( struct brw_wm_compile *c )
}
static void brw_wm_emit_glsl(struct brw_context *brw, struct brw_wm_compile *c)
-
{
#define MAX_IFSN 32
#define MAX_LOOP_DEPTH 32
@@ -1135,7 +1137,6 @@ static void brw_wm_emit_glsl(struct brw_context *brw, struct brw_wm_compile *c)
struct brw_compile *p = &c->func;
struct brw_indirect stack_index = brw_indirect(0, 0);
- brw_init_compile(brw, &c->func);
c->reg_index = 0;
prealloc_reg(c);
brw_set_compression_control(p, BRW_COMPRESSION_NONE);
diff --git a/src/mesa/drivers/dri/i965/brw_wm_pass0.c b/src/mesa/drivers/dri/i965/brw_wm_pass0.c
index 1bfae5a069b..205a7160d39 100644
--- a/src/mesa/drivers/dri/i965/brw_wm_pass0.c
+++ b/src/mesa/drivers/dri/i965/brw_wm_pass0.c
@@ -348,6 +348,8 @@ static struct brw_wm_instruction *translate_insn( struct brw_wm_compile *c,
out->saturate = (inst->SaturateMode != SATURATE_OFF);
out->tex_unit = inst->TexSrcUnit;
out->tex_idx = inst->TexSrcTarget;
+ out->eot = inst->Sampler & 1;
+ out->target = inst->Sampler>>1;
/* Args:
*/
diff --git a/src/mesa/drivers/dri/i965/brw_wm_surface_state.c b/src/mesa/drivers/dri/i965/brw_wm_surface_state.c
index f2ae210c386..d0f86b5687b 100644
--- a/src/mesa/drivers/dri/i965/brw_wm_surface_state.c
+++ b/src/mesa/drivers/dri/i965/brw_wm_surface_state.c
@@ -226,13 +226,13 @@ brw_update_texture_surface( GLcontext *ctx, GLuint unit )
key.depth = firstImage->Depth;
key.tiled = intelObj->mt->region->tiled;
- dri_bo_unreference(brw->wm.surf_bo[unit + 1]);
- brw->wm.surf_bo[unit + 1] = brw_search_cache(&brw->cache, BRW_SS_SURFACE,
+ dri_bo_unreference(brw->wm.surf_bo[unit + MAX_DRAW_BUFFERS]);
+ brw->wm.surf_bo[unit + MAX_DRAW_BUFFERS] = brw_search_cache(&brw->cache, BRW_SS_SURFACE,
&key, sizeof(key),
&key.bo, 1,
NULL);
- if (brw->wm.surf_bo[unit + 1] == NULL)
- brw->wm.surf_bo[unit + 1] = brw_create_texture_surface(brw, &key);
+ if (brw->wm.surf_bo[unit + MAX_DRAW_BUFFERS] == NULL)
+ brw->wm.surf_bo[unit + MAX_DRAW_BUFFERS] = brw_create_texture_surface(brw, &key);
}
/**
@@ -242,7 +242,7 @@ brw_update_texture_surface( GLcontext *ctx, GLuint unit )
*/
static void
brw_update_region_surface(struct brw_context *brw, struct intel_region *region,
- unsigned int unit)
+ unsigned int unit, GLboolean cached)
{
dri_bo *region_bo = NULL;
@@ -254,8 +254,6 @@ brw_update_region_surface(struct brw_context *brw, struct intel_region *region,
GLboolean tiled, color_blend;
} key;
- memset(&key, 0, sizeof(key));
-
if (region != NULL) {
region_bo = region->buffer;
@@ -276,17 +274,19 @@ brw_update_region_surface(struct brw_context *brw, struct intel_region *region,
key.height = 1;
key.cpp = 4;
}
-
memcpy(key.color_mask, brw->attribs.Color->ColorMask,
sizeof(key.color_mask));
key.color_blend = (!brw->attribs.Color->_LogicOpEnabled &&
brw->attribs.Color->BlendEnabled);
dri_bo_unreference(brw->wm.surf_bo[unit]);
- brw->wm.surf_bo[unit] = brw_search_cache(&brw->cache, BRW_SS_SURFACE,
- &key, sizeof(key),
- &region_bo, 1,
- NULL);
+ brw->wm.surf_bo[unit] = NULL;
+ if (cached)
+ brw->wm.surf_bo[unit] = brw_search_cache(&brw->cache, BRW_SS_SURFACE,
+ &key, sizeof(key),
+ &region_bo, 1,
+ NULL);
+
if (brw->wm.surf_bo[unit] == NULL) {
struct brw_surface_state surf;
@@ -312,11 +312,10 @@ brw_update_region_surface(struct brw_context *brw, struct intel_region *region,
/* Key size will never match key size for textures, so we're safe. */
brw->wm.surf_bo[unit] = brw_upload_cache(&brw->cache, BRW_SS_SURFACE,
- &key, sizeof(key),
+ &key, sizeof(key),
&region_bo, 1,
&surf, sizeof(surf),
NULL, NULL);
-
if (region_bo != NULL) {
dri_emit_reloc(brw->wm.surf_bo[unit],
DRM_BO_FLAG_MEM_TT |
@@ -345,7 +344,7 @@ brw_wm_get_binding_table(struct brw_context *brw)
NULL);
if (bind_bo == NULL) {
- GLuint data_size = brw->wm.nr_surfaces * 4;
+ GLuint data_size = brw->wm.nr_surfaces * sizeof(GLuint);
uint32_t *data = malloc(data_size);
int i;
@@ -369,7 +368,7 @@ brw_wm_get_binding_table(struct brw_context *brw)
DRM_BO_FLAG_READ |
DRM_BO_FLAG_WRITE,
0,
- i * 4,
+ i * sizeof(GLuint),
brw->wm.surf_bo[i]);
}
}
@@ -385,9 +384,14 @@ static void upload_wm_surfaces(struct brw_context *brw )
GLcontext *ctx = &brw->intel.ctx;
struct intel_context *intel = &brw->intel;
GLuint i;
+ if (brw->state.nr_draw_regions > 1) {
+ for (i = 0; i < brw->state.nr_draw_regions; i++)
+ brw_update_region_surface(brw, brw->state.draw_regions[i], i,
+ GL_FALSE);
+ }else
+ brw_update_region_surface(brw, brw->state.draw_regions[0], 0, GL_TRUE);
- brw_update_region_surface(brw, brw->state.draw_region, 0);
- brw->wm.nr_surfaces = 1;
+ brw->wm.nr_surfaces = MAX_DRAW_BUFFERS;
for (i = 0; i < BRW_MAX_TEX_UNIT; i++) {
struct gl_texture_unit *texUnit = &brw->attribs.Texture->Unit[i];
@@ -396,16 +400,16 @@ static void upload_wm_surfaces(struct brw_context *brw )
if(texUnit->_ReallyEnabled &&
texUnit->_Current == intel->frame_buffer_texobj)
{
- dri_bo_unreference(brw->wm.surf_bo[i+1]);
- brw->wm.surf_bo[i+1] = brw->wm.surf_bo[0];
- dri_bo_reference(brw->wm.surf_bo[i+1]);
- brw->wm.nr_surfaces = i+2;
+ dri_bo_unreference(brw->wm.surf_bo[i+MAX_DRAW_BUFFERS]);
+ brw->wm.surf_bo[i+MAX_DRAW_BUFFERS] = brw->wm.surf_bo[0];
+ dri_bo_reference(brw->wm.surf_bo[i+MAX_DRAW_BUFFERS]);
+ brw->wm.nr_surfaces = i + MAX_DRAW_BUFFERS + 1;
} else if (texUnit->_ReallyEnabled) {
brw_update_texture_surface(ctx, i);
- brw->wm.nr_surfaces = i+2;
+ brw->wm.nr_surfaces = i + MAX_DRAW_BUFFERS + 1;
} else {
- dri_bo_unreference(brw->wm.surf_bo[i+1]);
- brw->wm.surf_bo[i+1] = NULL;
+ dri_bo_unreference(brw->wm.surf_bo[i+MAX_DRAW_BUFFERS]);
+ brw->wm.surf_bo[i+MAX_DRAW_BUFFERS] = NULL;
}
}
diff --git a/src/mesa/drivers/dri/intel/intel_buffers.c b/src/mesa/drivers/dri/intel/intel_buffers.c
index 5199f833e2c..2a25f079e95 100644
--- a/src/mesa/drivers/dri/intel/intel_buffers.c
+++ b/src/mesa/drivers/dri/intel/intel_buffers.c
@@ -300,6 +300,7 @@ intelWindowMoved(struct intel_context *intel)
default:
intelSetFrontClipRects(intel);
}
+
}
if (!intel->intelScreen->driScrnPriv->dri2.enabled &&
@@ -894,7 +895,7 @@ void
intel_draw_buffer(GLcontext * ctx, struct gl_framebuffer *fb)
{
struct intel_context *intel = intel_context(ctx);
- struct intel_region *colorRegion, *depthRegion = NULL;
+ struct intel_region *colorRegions[MAX_DRAW_BUFFERS], *depthRegion = NULL;
struct intel_renderbuffer *irbDepth = NULL, *irbStencil = NULL;
int front = 0; /* drawing to front color buffer? */
@@ -933,14 +934,24 @@ intel_draw_buffer(GLcontext * ctx, struct gl_framebuffer *fb)
/*
* How many color buffers are we drawing into?
*/
- if (fb->_NumColorDrawBuffers != 1) {
- /* writing to 0 or 2 or 4 color buffers */
- /*_mesa_debug(ctx, "Software rendering\n");*/
+ if (fb->_NumColorDrawBuffers == 0) {
+ /* writing to 0 */
FALLBACK(intel, INTEL_FALLBACK_DRAW_BUFFER, GL_TRUE);
- colorRegion = NULL;
+ colorRegions[0] = NULL;
if (fb->Name != 0)
intelSetRenderbufferClipRects(intel);
+ } else if (fb->_NumColorDrawBuffers > 1) {
+ int i;
+ struct intel_renderbuffer *irb;
+ FALLBACK(intel, INTEL_FALLBACK_DRAW_BUFFER, GL_FALSE);
+
+ if (fb->Name != 0)
+ intelSetRenderbufferClipRects(intel);
+ for (i = 0; i < fb->_NumColorDrawBuffers; i++) {
+ irb = intel_renderbuffer(fb->_ColorDrawBuffers[i]);
+ colorRegions[i] = (irb && irb->region) ? irb->region : NULL;
+ }
}
else {
/* draw to exactly one color buffer */
@@ -958,11 +969,11 @@ intel_draw_buffer(GLcontext * ctx, struct gl_framebuffer *fb)
/* drawing to window system buffer */
if (front) {
intelSetFrontClipRects(intel);
- colorRegion = intel_get_rb_region(fb, BUFFER_FRONT_LEFT);
+ colorRegions[0] = intel_get_rb_region(fb, BUFFER_FRONT_LEFT);
}
else {
intelSetBackClipRects(intel);
- colorRegion = intel_get_rb_region(fb, BUFFER_BACK_LEFT);
+ colorRegions[0]= intel_get_rb_region(fb, BUFFER_BACK_LEFT);
}
}
else {
@@ -970,7 +981,7 @@ intel_draw_buffer(GLcontext * ctx, struct gl_framebuffer *fb)
struct intel_renderbuffer *irb;
intelSetRenderbufferClipRects(intel);
irb = intel_renderbuffer(fb->_ColorDrawBuffers[0]);
- colorRegion = (irb && irb->region) ? irb->region : NULL;
+ colorRegions[0] = (irb && irb->region) ? irb->region : NULL;
}
}
@@ -982,7 +993,7 @@ intel_draw_buffer(GLcontext * ctx, struct gl_framebuffer *fb)
else
ctx->NewState |= _NEW_POLYGON;
- if (!colorRegion) {
+ if (!colorRegions[0]) {
FALLBACK(intel, INTEL_FALLBACK_DRAW_BUFFER, GL_TRUE);
}
else {
@@ -1055,7 +1066,8 @@ intel_draw_buffer(GLcontext * ctx, struct gl_framebuffer *fb)
ctx->NewState |= _NEW_DEPTH;
}
- intel->vtbl.set_draw_region(intel, colorRegion, depthRegion);
+ intel->vtbl.set_draw_region(intel, colorRegions, depthRegion,
+ fb->_NumColorDrawBuffers);
/* update viewport since it depends on window size */
if (ctx->Driver.Viewport) {
diff --git a/src/mesa/drivers/dri/intel/intel_context.h b/src/mesa/drivers/dri/intel/intel_context.h
index 809cb6ea578..1348b0adcf0 100644
--- a/src/mesa/drivers/dri/intel/intel_context.h
+++ b/src/mesa/drivers/dri/intel/intel_context.h
@@ -94,8 +94,9 @@ struct intel_context
void (*render_start) (struct intel_context * intel);
void (*render_prevalidate) (struct intel_context * intel);
void (*set_draw_region) (struct intel_context * intel,
- struct intel_region * draw_region,
- struct intel_region * depth_region);
+ struct intel_region * draw_regions[],
+ struct intel_region * depth_region,
+ GLuint num_regions);
GLuint (*flush_cmd) (void);
void (*emit_flush) (struct intel_context *intel, GLuint unused);