Simplify ctx->_NumColorDrawBuffers, _ColorDrawBuffers and fix bug 13835.

These fields are no longer indexed by shader output.  Now, we just have
a simple array of renderbuffer pointers.

If the shader writes to gl_FragData[i], send those colors to the N
_ColorDrawBuffers.  Otherwise, replicate the single gl_FragColor (or
the fixed-function color) to the N _ColorDrawBuffers.

A few more changes and simplifications can follow from this...
This commit is contained in:
Brian
2008-01-06 10:43:20 -07:00
parent 9f6022d056
commit ff73c783cc
26 changed files with 214 additions and 219 deletions

View File

@@ -234,7 +234,7 @@ intelCalcViewport(GLcontext * ctx)
if (ctx->DrawBuffer->Name) {
/* User created FBO */
struct intel_renderbuffer *irb
= intel_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0][0]);
= intel_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0]);
if (irb && !irb->RenderToTexture) {
/* y=0=top */
yScale = -1.0;

View File

@@ -62,12 +62,9 @@ static GLboolean do_check_fallback(struct brw_context *brw)
/* We can only handle a single draw buffer at the moment, and only as the
* first color buffer.
*/
for (i = 0; i < MAX_DRAW_BUFFERS; i++) {
if (fb->_NumColorDrawBuffers[i] > (i == 0 ? 1 : 0)) {
DBG("FALLBACK: draw buffer %d: 0x%08x\n",
i, ctx->DrawBuffer->_ColorDrawBufferMask[i]);
return GL_TRUE;
}
if (fb->_NumColorDrawBuffers > 1) {
DBG("FALLBACK: multiple color draw buffers\n");
return GL_TRUE;
}
/* _NEW_RENDERMODE

View File

@@ -43,7 +43,7 @@ static void upload_sf_vp(struct brw_context *brw)
const GLfloat depth_scale = 1.0F / ctx->DrawBuffer->_DepthMaxF;
struct brw_sf_viewport sfv;
struct intel_renderbuffer *irb =
intel_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0][0]);
intel_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0]);
GLfloat y_scale, y_bias;
memset(&sfv, 0, sizeof(sfv));

View File

@@ -102,7 +102,7 @@ struct intel_region *
intel_drawbuf_region(struct intel_context *intel)
{
struct intel_renderbuffer *irbColor =
intel_renderbuffer(intel->ctx.DrawBuffer->_ColorDrawBuffers[0][0]);
intel_renderbuffer(intel->ctx.DrawBuffer->_ColorDrawBuffers[0]);
if (irbColor)
return irbColor->region;
else
@@ -931,7 +931,7 @@ intel_draw_buffer(GLcontext * ctx, struct gl_framebuffer *fb)
/*
* How many color buffers are we drawing into?
*/
if (fb->_NumColorDrawBuffers[0] != 1) {
if (fb->_NumColorDrawBuffers != 1) {
/* writing to 0 or 2 or 4 color buffers */
/*_mesa_debug(ctx, "Software rendering\n");*/
FALLBACK(intel, INTEL_FALLBACK_DRAW_BUFFER, GL_TRUE);
@@ -967,7 +967,7 @@ intel_draw_buffer(GLcontext * ctx, struct gl_framebuffer *fb)
/* drawing to user-created FBO */
struct intel_renderbuffer *irb;
intelSetRenderbufferClipRects(intel);
irb = intel_renderbuffer(fb->_ColorDrawBuffers[0][0]);
irb = intel_renderbuffer(fb->_ColorDrawBuffers[0]);
colorRegion = (irb && irb->region) ? irb->region : NULL;
}
}

View File

@@ -186,21 +186,18 @@ intel_map_unmap_buffers(struct intel_context *intel, GLboolean map)
struct intel_renderbuffer *irb;
/* color draw buffers */
for (i = 0; i < ctx->Const.MaxDrawBuffers; i++) {
for (j = 0; j < ctx->DrawBuffer->_NumColorDrawBuffers[i]; j++) {
struct gl_renderbuffer *rb =
ctx->DrawBuffer->_ColorDrawBuffers[i][j];
irb = intel_renderbuffer(rb);
if (irb) {
/* this is a user-created intel_renderbuffer */
if (irb->region) {
if (map)
intel_region_map(intel, irb->region);
else
intel_region_unmap(intel, irb->region);
irb->pfMap = irb->region->map;
irb->pfPitch = irb->region->pitch;
}
for (j = 0; j < ctx->DrawBuffer->_NumColorDrawBuffers; j++) {
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[j];
irb = intel_renderbuffer(rb);
if (irb) {
/* this is a user-created intel_renderbuffer */
if (irb->region) {
if (map)
intel_region_map(intel, irb->region);
else
intel_region_unmap(intel, irb->region);
irb->pfMap = irb->region->map;
irb->pfPitch = irb->region->pitch;
}
}
}

View File

@@ -149,12 +149,12 @@ static void nouveauClear( GLcontext *ctx, GLbitfield mask )
clear_value = PACK_COLOR_8888(c[3],c[0],c[1],c[2]);
if (ctx->DrawBuffer) {
/* FIXME: find correct color buffer, instead of [0][0] */
if (ctx->DrawBuffer->_ColorDrawBuffers[0][0]) {
color_bits = ctx->DrawBuffer->_ColorDrawBuffers[0][0]->RedBits;
color_bits += ctx->DrawBuffer->_ColorDrawBuffers[0][0]->GreenBits;
color_bits += ctx->DrawBuffer->_ColorDrawBuffers[0][0]->BlueBits;
color_bits += ctx->DrawBuffer->_ColorDrawBuffers[0][0]->AlphaBits;
/* FIXME: find correct color buffer, instead of [0] */
if (ctx->DrawBuffer->_ColorDrawBuffers[0]) {
color_bits = ctx->DrawBuffer->_ColorDrawBuffers[0]->RedBits;
color_bits += ctx->DrawBuffer->_ColorDrawBuffers[0]->GreenBits;
color_bits += ctx->DrawBuffer->_ColorDrawBuffers[0]->BlueBits;
color_bits += ctx->DrawBuffer->_ColorDrawBuffers[0]->AlphaBits;
}
}

View File

@@ -177,8 +177,7 @@ nouveau_window_moved(GLcontext * ctx)
nouveauContextPtr nmesa = NOUVEAU_CONTEXT(ctx);
nouveau_renderbuffer_t *nrb;
nrb = (nouveau_renderbuffer_t *)
ctx->DrawBuffer->_ColorDrawBuffers[0][0];
nrb = (nouveau_renderbuffer_t *) ctx->DrawBuffer->_ColorDrawBuffers[0];
if (!nrb)
return;
@@ -204,7 +203,7 @@ nouveau_build_framebuffer(GLcontext *ctx, struct gl_framebuffer *fb)
_mesa_update_framebuffer(ctx);
_mesa_update_draw_buffer_bounds(ctx);
color[0] = (nouveau_renderbuffer_t *) fb->_ColorDrawBuffers[0][0];
color[0] = (nouveau_renderbuffer_t *) fb->_ColorDrawBuffers[0];
if (fb->_DepthBuffer && fb->_DepthBuffer->Wrapped)
depth = (nouveau_renderbuffer_t *) fb->_DepthBuffer->Wrapped;
else

View File

@@ -813,7 +813,7 @@ static void r128UpdateWindow( GLcontext *ctx )
r128ContextPtr rmesa = R128_CONTEXT(ctx);
int x = rmesa->driDrawable->x;
int y = rmesa->driDrawable->y;
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0][0];
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0];
driRenderbuffer *drb = (driRenderbuffer *) rb;
rmesa->setup.window_xy_offset = (((y & 0xFFF) << R128_WINDOW_Y_SHIFT) |

View File

@@ -294,7 +294,7 @@ static void do_draw_pix( GLcontext *ctx,
r200ContextPtr rmesa = R200_CONTEXT(ctx);
__DRIdrawablePrivate *dPriv = rmesa->dri.drawable;
drm_clip_rect_t *box = dPriv->pClipRects;
struct gl_renderbuffer *rb = ctx->ReadBuffer->_ColorDrawBuffers[0][0];
struct gl_renderbuffer *rb = ctx->ReadBuffer->_ColorDrawBuffers[0];
driRenderbuffer *drb = (driRenderbuffer *) rb;
int nbox = dPriv->numClipRects;
int i;
@@ -388,7 +388,7 @@ r200TryDrawPixels( GLcontext *ctx,
fprintf(stderr, "%s\n", __FUNCTION__);
/* check that we're drawing to exactly one color buffer */
if (ctx->DrawBuffer->_NumColorDrawBuffers[0] != 1)
if (ctx->DrawBuffer->_NumColorDrawBuffers != 1)
return GL_FALSE;
switch (format) {

View File

@@ -255,7 +255,7 @@ static void r200SpanRenderStart( GLcontext *ctx )
{
int p;
driRenderbuffer *drb =
(driRenderbuffer *) ctx->WinSysDrawBuffer->_ColorDrawBuffers[0][0];
(driRenderbuffer *) ctx->WinSysDrawBuffer->_ColorDrawBuffers[0];
volatile int *buf =
(volatile int *)(rmesa->dri.screen->pFB + drb->offset);
p = *buf;

View File

@@ -435,7 +435,7 @@ xmesa_DrawPixels_8R8G8B( GLcontext *ctx,
const GLvoid *pixels )
{
const SWcontext *swrast = SWRAST_CONTEXT( ctx );
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0][0];
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0];
struct xmesa_renderbuffer *xrb = xmesa_renderbuffer(rb->Wrapped);
if (swrast->NewState)
@@ -544,7 +544,7 @@ xmesa_DrawPixels_5R6G5B( GLcontext *ctx,
const GLvoid *pixels )
{
struct xmesa_renderbuffer *xrb
= xmesa_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0][0]->Wrapped);
= xmesa_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0]->Wrapped);
const XMesaContext xmesa = XMESA_CONTEXT(ctx);
const SWcontext *swrast = SWRAST_CONTEXT( ctx );
XMesaDisplay *dpy = xmesa->xm_visual->display;
@@ -654,7 +654,7 @@ xmesa_CopyPixels( GLcontext *ctx,
struct xmesa_renderbuffer *srcXrb
= xmesa_renderbuffer(ctx->ReadBuffer->_ColorReadBuffer->Wrapped);
struct xmesa_renderbuffer *dstXrb
= xmesa_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0][0]->Wrapped);
= xmesa_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0]->Wrapped);
ASSERT(dpy);
ASSERT(gc);

View File

@@ -121,7 +121,7 @@ void xmesa_choose_point( GLcontext *ctx )
#define GET_XRB(XRB) struct xmesa_renderbuffer *XRB = \
xmesa_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0][0]->Wrapped)
xmesa_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0]->Wrapped)
/*
@@ -598,7 +598,7 @@ get_line_func(GLcontext *ctx)
if (swrast->_RasterMask & MULTI_DRAW_BIT) return (swrast_line_func) NULL;
if (xmbuf->swAlpha) return (swrast_line_func) NULL;
xrb = xmesa_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0][0]->Wrapped);
xrb = xmesa_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0]->Wrapped);
if (xrb->ximage
&& swrast->_RasterMask==DEPTH_BIT
@@ -661,7 +661,7 @@ get_line_func(GLcontext *ctx)
}
#ifndef XFree86Server
if (ctx->DrawBuffer->_NumColorDrawBuffers[0] == 1
if (ctx->DrawBuffer->_NumColorDrawBuffers == 1
&& ctx->DrawBuffer->_ColorDrawBufferMask[0] == BUFFER_BIT_FRONT_LEFT
&& swrast->_RasterMask == LOGIC_OP_BIT
&& ctx->Color.LogicOp == GL_XOR

View File

@@ -45,7 +45,7 @@
#define GET_XRB(XRB) struct xmesa_renderbuffer *XRB = \
xmesa_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0][0]->Wrapped)
xmesa_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0]->Wrapped)
/**********************************************************************/
@@ -1479,7 +1479,7 @@ get_triangle_func(GLcontext *ctx)
if (xmbuf->swAlpha)
return (swrast_tri_func) NULL;
xrb = xmesa_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0][0]->Wrapped);
xrb = xmesa_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[0]->Wrapped);
if (xrb->ximage) {
if ( ctx->Light.ShadeModel==GL_SMOOTH

View File

@@ -508,8 +508,9 @@ set_color_output(GLcontext *ctx, GLuint output, GLenum buffer,
/* Set per-FBO state */
fb->ColorDrawBuffer[output] = buffer;
fb->_ColorDrawBufferMask[output] = destMask;
/* not really needed, will be set later */
fb->_NumColorDrawBuffers[output] = 0;
/* this will be computed later, but zero to be safe */
fb->_NumColorDrawBuffers = 0;
if (fb->Name == 0) {
/* Only set the per-context DrawBuffer state if we're currently

View File

@@ -583,6 +583,51 @@ _mesa_update_stencil_buffer(GLcontext *ctx,
}
/*
* Example DrawBuffers scenarios:
*
* 1. glDrawBuffer(GL_FRONT_AND_BACK), fixed-func or shader writes to
* "gl_FragColor" or program writes to the "result.color" register:
*
* fragment color output renderbuffer
* --------------------- ---------------
* color[0] Front, Back
*
*
* 2. glDrawBuffers(3, [GL_FRONT, GL_AUX0, GL_AUX1]), shader writes to
* gl_FragData[i] or program writes to result.color[i] registers:
*
* fragment color output renderbuffer
* --------------------- ---------------
* color[0] Front
* color[1] Aux0
* color[3] Aux1
*
*
* 3. glDrawBuffers(3, [GL_FRONT, GL_AUX0, GL_AUX1]) and shader writes to
* gl_FragColor, or fixed function:
*
* fragment color output renderbuffer
* --------------------- ---------------
* color[0] Front, Aux0, Aux1
*
*
* In either case, the list of renderbuffers is stored in the
* framebuffer->_ColorDrawBuffers[] array and
* framebuffer->_NumColorDrawBuffers indicates the number of buffers.
* The renderer (like swrast) has to look at the current fragment shader
* to see if it writes to gl_FragColor vs. gl_FragData[i] to determine
* how to map color outputs to renderbuffers.
*
* Note that these two calls are equivalent (for fixed function fragment
* shading anyway):
* a) glDrawBuffer(GL_FRONT_AND_BACK); (assuming non-stereo framebuffer)
* b) glDrawBuffers(2, [GL_FRONT_LEFT, GL_BACK_LEFT]);
*/
/**
* Update the (derived) list of color drawing renderbuffer pointers.
* Later, when we're rendering we'll loop from 0 to _NumColorDrawBuffers
@@ -591,39 +636,39 @@ _mesa_update_stencil_buffer(GLcontext *ctx,
static void
update_color_draw_buffers(GLcontext *ctx, struct gl_framebuffer *fb)
{
GLuint output;
GLuint output, count = 0;
/*
* Fragment programs can write to multiple colorbuffers with
* the GL_ARB_draw_buffers extension.
/* First, interpret _ColorDrawBufferMask[] in the manner that would be
* used if the fragment program/shader writes to gl_FragData[]
*/
for (output = 0; output < ctx->Const.MaxDrawBuffers; output++) {
GLbitfield bufferMask = fb->_ColorDrawBufferMask[output];
GLuint count = 0;
GLuint i;
if (!fb->DeletePending) {
/* We need the inner loop here because glDrawBuffer(GL_FRONT_AND_BACK)
* can specify writing to two or four color buffers (for example).
*/
for (i = 0; bufferMask && i < BUFFER_COUNT; i++) {
const GLuint bufferBit = 1 << i;
if (bufferBit & bufferMask) {
struct gl_renderbuffer *rb = fb->Attachment[i].Renderbuffer;
if (rb && rb->Width > 0 && rb->Height > 0) {
fb->_ColorDrawBuffers[output][count] = rb;
count++;
}
else {
/*
_mesa_warning(ctx, "DrawBuffer names a missing buffer!\n");
*/
}
bufferMask &= ~bufferBit;
}
}
GLuint buf = _mesa_ffs(fb->_ColorDrawBufferMask[output]);
if (buf) {
struct gl_renderbuffer *rb = fb->Attachment[buf - 1].Renderbuffer;
fb->_ColorDrawBuffers[output] = rb; /* may be NULL */
if (rb)
count = output + 1;
}
fb->_NumColorDrawBuffers[output] = count;
}
/* Second, handle the GL_FRONT_AND_BACK case, overwriting the above
* if needed.
*/
GLbitfield bufferMask = fb->_ColorDrawBufferMask[0];
if (_mesa_bitcount(bufferMask) > 1) {
GLuint i;
count = 0;
for (i = 0; bufferMask && i < BUFFER_COUNT; i++) {
if (bufferMask & (1 << i)) {
struct gl_renderbuffer *rb = fb->Attachment[i].Renderbuffer;
fb->_ColorDrawBuffers[count] = rb;
count++;
}
bufferMask &= ~(1 << i);
}
}
fb->_NumColorDrawBuffers = count;
}

View File

@@ -2400,8 +2400,8 @@ struct gl_framebuffer
GLint _ColorReadBufferIndex; /* -1 = None */
/* These are computed from _ColorDrawBufferMask and _ColorReadBufferIndex */
GLuint _NumColorDrawBuffers[MAX_DRAW_BUFFERS];
struct gl_renderbuffer *_ColorDrawBuffers[MAX_DRAW_BUFFERS][4];
GLuint _NumColorDrawBuffers;
struct gl_renderbuffer *_ColorDrawBuffers[MAX_DRAW_BUFFERS];
struct gl_renderbuffer *_ColorReadBuffer;
/** The Actual depth/stencil buffers to use. May be wrappers around the

View File

@@ -525,8 +525,8 @@ accum_return(GLcontext *ctx, GLfloat value,
}
/* store colors */
for (buffer = 0; buffer < fb->_NumColorDrawBuffers[0]; buffer++) {
struct gl_renderbuffer *rb = fb->_ColorDrawBuffers[0][buffer];
for (buffer = 0; buffer < fb->_NumColorDrawBuffers; buffer++) {
struct gl_renderbuffer *rb = fb->_ColorDrawBuffers[buffer];
if (masking) {
_swrast_mask_rgba_span(ctx, rb, &span);
}

View File

@@ -135,7 +135,7 @@ blit_nearest(GLcontext *ctx,
switch (buffer) {
case GL_COLOR_BUFFER_BIT:
readRb = ctx->ReadBuffer->_ColorReadBuffer;
drawRb = ctx->DrawBuffer->_ColorDrawBuffers[0][0];
drawRb = ctx->DrawBuffer->_ColorDrawBuffers[0];
comps = 4;
break;
case GL_DEPTH_BUFFER_BIT:
@@ -319,7 +319,7 @@ blit_linear(GLcontext *ctx,
GLint dstX0, GLint dstY0, GLint dstX1, GLint dstY1)
{
struct gl_renderbuffer *readRb = ctx->ReadBuffer->_ColorReadBuffer;
struct gl_renderbuffer *drawRb = ctx->DrawBuffer->_ColorDrawBuffers[0][0];
struct gl_renderbuffer *drawRb = ctx->DrawBuffer->_ColorDrawBuffers[0];
const GLint srcWidth = ABS(srcX1 - srcX0);
const GLint dstWidth = ABS(dstX1 - dstX0);
@@ -493,7 +493,7 @@ simple_blit(GLcontext *ctx,
switch (buffer) {
case GL_COLOR_BUFFER_BIT:
readRb = ctx->ReadBuffer->_ColorReadBuffer;
drawRb = ctx->DrawBuffer->_ColorDrawBuffers[0][0];
drawRb = ctx->DrawBuffer->_ColorDrawBuffers[0];
comps = 4;
break;
case GL_DEPTH_BUFFER_BIT:

View File

@@ -251,7 +251,7 @@ static void
clear_color_buffers(GLcontext *ctx)
{
GLboolean masking;
GLuint i;
GLuint buf;
if (ctx->Visual.rgbMode) {
if (ctx->Color.ColorMask[0] &&
@@ -265,7 +265,7 @@ clear_color_buffers(GLcontext *ctx)
}
}
else {
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0][0];
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0];
const GLuint indexBits = (1 << rb->IndexBits) - 1;
if ((ctx->Color.IndexMask & indexBits) == indexBits) {
masking = GL_FALSE;
@@ -275,8 +275,8 @@ clear_color_buffers(GLcontext *ctx)
}
}
for (i = 0; i < ctx->DrawBuffer->_NumColorDrawBuffers[0]; i++) {
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0][i];
for (buf = 0; buf < ctx->DrawBuffer->_NumColorDrawBuffers; buf++) {
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[buf];
if (ctx->Visual.rgbMode) {
if (masking) {
clear_rgba_buffer_with_masking(ctx, rb);
@@ -331,7 +331,7 @@ _swrast_Clear(GLcontext *ctx, GLbitfield buffers)
/* do software clearing here */
if (buffers) {
if (buffers & ctx->DrawBuffer->_ColorDrawBufferMask[0]) {
if (buffers & ctx->DrawBuffer->_NumColorDrawBuffers > 0) {
clear_color_buffers(ctx);
}
if (buffers & BUFFER_BIT_DEPTH) {

View File

@@ -87,7 +87,7 @@ _swrast_update_rasterflags( GLcontext *ctx )
* MULTI_DRAW_BIT flag. Also set it if we're drawing to no
* buffers or the RGBA or CI mask disables all writes.
*/
if (ctx->DrawBuffer->_NumColorDrawBuffers[0] != 1) {
if (ctx->DrawBuffer->_NumColorDrawBuffers != 1) {
/* more than one color buffer designated for writing (or zero buffers) */
rasterMask |= MULTI_DRAW_BIT;
}
@@ -596,44 +596,6 @@ _swrast_update_active_attribs(GLcontext *ctx)
}
/**
* Update the swrast->_ColorOutputsMask which indicates which color
* renderbuffers (aka rendertargets) are being written to by the current
* fragment program.
* We also take glDrawBuffers() into account to skip outputs that are
* set to GL_NONE.
*/
static void
_swrast_update_color_outputs(GLcontext *ctx)
{
SWcontext *swrast = SWRAST_CONTEXT(ctx);
const struct gl_framebuffer *fb = ctx->DrawBuffer;
swrast->_ColorOutputsMask = 0;
swrast->_NumColorOutputs = 0;
if (ctx->FragmentProgram._Current) {
const GLbitfield outputsWritten
= ctx->FragmentProgram._Current->Base.OutputsWritten;
GLuint output;
for (output = 0; output < ctx->Const.MaxDrawBuffers; output++) {
if ((outputsWritten & (1 << (FRAG_RESULT_DATA0 + output)))
&& (fb->_NumColorDrawBuffers[output] > 0)) {
swrast->_ColorOutputsMask |= (1 << output);
swrast->_NumColorOutputs = output + 1;
}
}
}
if (swrast->_ColorOutputsMask == 0x0) {
/* no fragment program, or frag prog didn't write to gl_FragData[] */
if (fb->_NumColorDrawBuffers[0] > 0) {
swrast->_ColorOutputsMask = 0x1;
swrast->_NumColorOutputs = 1;
}
}
}
void
_swrast_validate_derived( GLcontext *ctx )
{
@@ -683,9 +645,6 @@ _swrast_validate_derived( GLcontext *ctx )
_NEW_TEXTURE))
_swrast_update_active_attribs(ctx);
if (swrast->NewState & (_NEW_PROGRAM | _NEW_BUFFERS))
_swrast_update_color_outputs(ctx);
swrast->NewState = 0;
swrast->StateChanges = 0;
swrast->InvalidateState = _swrast_invalidate_state;

View File

@@ -136,10 +136,6 @@ typedef struct
GLboolean _DeferredTexture;
GLenum _FogMode; /* either GL_FOG_MODE or fragment program's fog mode */
/** Multiple render targets */
GLbitfield _ColorOutputsMask;
GLuint _NumColorOutputs;
/** List/array of the fragment attributes to interpolate */
GLuint _ActiveAttribs[FRAG_ATTRIB_MAX];
/** Same info, but as a bitmask */

View File

@@ -830,10 +830,10 @@ fast_copy_pixels(GLcontext *ctx,
}
if (type == GL_COLOR) {
if (dstFb->_NumColorDrawBuffers[0] != 1)
if (dstFb->_NumColorDrawBuffers != 1)
return GL_FALSE;
srcRb = srcFb->_ColorReadBuffer;
dstRb = dstFb->_ColorDrawBuffers[0][0];
dstRb = dstFb->_ColorDrawBuffers[0];
}
else if (type == GL_STENCIL) {
srcRb = srcFb->_StencilBuffer;

View File

@@ -53,7 +53,7 @@ fast_draw_rgba_pixels(GLcontext *ctx, GLint x, GLint y,
const GLvoid *pixels)
{
const GLint imgX = x, imgY = y;
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0][0];
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0];
const GLenum rbType = rb->DataType;
SWcontext *swrast = SWRAST_CONTEXT(ctx);
SWspan span;
@@ -608,8 +608,8 @@ draw_rgba_pixels( GLcontext *ctx, GLint x, GLint y,
IMAGE_POST_CONVOLUTION_SCALE_BIAS);
}
if (ctx->DrawBuffer->_NumColorDrawBuffers[0] > 0 &&
ctx->DrawBuffer->_ColorDrawBuffers[0][0]->DataType != GL_FLOAT &&
if (ctx->DrawBuffer->_NumColorDrawBuffers > 0 &&
ctx->DrawBuffer->_ColorDrawBuffers[0]->DataType != GL_FLOAT &&
ctx->Color.ClampFragmentColor != GL_FALSE) {
/* need to clamp colors before applying fragment ops */
transferOps |= IMAGE_CLAMP_BIT;

View File

@@ -167,11 +167,11 @@ run_program(GLcontext *ctx, SWspan *span, GLuint start, GLuint end)
* Note that colors beyond 0 and 1 will overwrite other
* attributes, such as FOGC, TEX0, TEX1, etc. That's OK.
*/
GLuint output;
for (output = 0; output < swrast->_NumColorOutputs; output++) {
if (outputsWritten & (1 << (FRAG_RESULT_DATA0 + output))) {
COPY_4V(span->array->attribs[FRAG_ATTRIB_COL0+output][i],
machine->Outputs[FRAG_RESULT_DATA0 + output]);
GLuint buf;
for (buf = 0; buf < ctx->DrawBuffer->_NumColorDrawBuffers; buf++) {
if (outputsWritten & (1 << (FRAG_RESULT_DATA0 + buf))) {
COPY_4V(span->array->attribs[FRAG_ATTRIB_COL0 + buf][i],
machine->Outputs[FRAG_RESULT_DATA0 + buf]);
}
}
}

View File

@@ -792,6 +792,7 @@ _swrast_write_index_span( GLcontext *ctx, SWspan *span)
const SWcontext *swrast = SWRAST_CONTEXT(ctx);
const GLbitfield origInterpMask = span->interpMask;
const GLbitfield origArrayMask = span->arrayMask;
struct gl_framebuffer *fb = ctx->DrawBuffer;
ASSERT(span->end <= MAX_WIDTH);
ASSERT(span->primitive == GL_POINT || span->primitive == GL_LINE ||
@@ -818,7 +819,7 @@ _swrast_write_index_span( GLcontext *ctx, SWspan *span)
}
/* Depth bounds test */
if (ctx->Depth.BoundsTest && ctx->DrawBuffer->Visual.depthBits > 0) {
if (ctx->Depth.BoundsTest && fb->Visual.depthBits > 0) {
if (!_swrast_depth_bounds_test(ctx, span)) {
return;
}
@@ -830,10 +831,10 @@ _swrast_write_index_span( GLcontext *ctx, SWspan *span)
GLuint i;
for (i = 0; i < span->end; i++) {
if (span->array->mask[i]) {
assert(span->array->x[i] >= ctx->DrawBuffer->_Xmin);
assert(span->array->x[i] < ctx->DrawBuffer->_Xmax);
assert(span->array->y[i] >= ctx->DrawBuffer->_Ymin);
assert(span->array->y[i] < ctx->DrawBuffer->_Ymax);
assert(span->array->x[i] >= fb->_Xmin);
assert(span->array->x[i] < fb->_Xmax);
assert(span->array->y[i] >= fb->_Ymin);
assert(span->array->y[i] < fb->_Ymax);
}
}
}
@@ -912,22 +913,21 @@ _swrast_write_index_span( GLcontext *ctx, SWspan *span)
* Write to renderbuffers
*/
{
struct gl_framebuffer *fb = ctx->DrawBuffer;
const GLuint output = 0; /* only frag progs can write to other outputs */
const GLuint numDrawBuffers = fb->_NumColorDrawBuffers[output];
GLuint indexSave[MAX_WIDTH];
const GLuint numBuffers = fb->_NumColorDrawBuffers;
GLuint buf;
if (numDrawBuffers > 1) {
/* save indexes for second, third renderbuffer writes */
_mesa_memcpy(indexSave, span->array->index,
span->end * sizeof(indexSave[0]));
}
for (buf = 0; buf < numBuffers; buf++) {
struct gl_renderbuffer *rb = fb->_ColorDrawBuffers[buf];
GLuint indexSave[MAX_WIDTH];
for (buf = 0; buf < fb->_NumColorDrawBuffers[output]; buf++) {
struct gl_renderbuffer *rb = fb->_ColorDrawBuffers[output][buf];
ASSERT(rb->_BaseFormat == GL_COLOR_INDEX);
if (numBuffers > 1) {
/* save indexes for second, third renderbuffer writes */
_mesa_memcpy(indexSave, span->array->index,
span->end * sizeof(indexSave[0]));
}
if (ctx->Color.IndexLogicOpEnabled) {
_swrast_logicop_ci_span(ctx, rb, span);
}
@@ -1002,7 +1002,7 @@ _swrast_write_index_span( GLcontext *ctx, SWspan *span)
}
}
if (buf + 1 < numDrawBuffers) {
if (buf + 1 < numBuffers) {
/* restore original span values */
_mesa_memcpy(span->array->index, indexSave,
span->end * sizeof(indexSave[0]));
@@ -1119,7 +1119,7 @@ clamp_colors(SWspan *span)
/**
* Convert the span's color arrays to the given type.
* The only way 'output' can be greater than one is when we have a fragment
* The only way 'output' can be greater than zero is when we have a fragment
* program that writes to gl_FragData[1] or higher.
* \param output which fragment program color output is being processed
*/
@@ -1249,7 +1249,6 @@ _swrast_write_rgba_span( GLcontext *ctx, SWspan *span)
|| ctx->ATIFragmentShader._Enabled);
const GLboolean shaderOrTexture = shader || ctx->Texture._EnabledUnits;
struct gl_framebuffer *fb = ctx->DrawBuffer;
GLuint output;
/*
printf("%s() interp 0x%x array 0x%x\n", __FUNCTION__,
@@ -1399,67 +1398,69 @@ _swrast_write_rgba_span( GLcontext *ctx, SWspan *span)
/*
* Write to renderbuffers
*/
/* Loop over color outputs (GL_ARB_draw_buffers) written by frag prog */
for (output = 0; output < swrast->_NumColorOutputs; output++) {
if (swrast->_ColorOutputsMask & (1 << output)) {
const GLuint numDrawBuffers = fb->_NumColorDrawBuffers[output];
GLchan rgbaSave[MAX_WIDTH][4];
GLuint buf;
{
const struct gl_fragment_program *fp = ctx->FragmentProgram._Current;
const GLboolean multiFragOutputs
= fp && fp->Base.InputsRead >= (1 << FRAG_RESULT_DATA0);
const GLuint numBuffers = fb->_NumColorDrawBuffers;
GLuint buf;
ASSERT(numDrawBuffers > 0);
for (buf = 0; buf < numBuffers; buf++) {
struct gl_renderbuffer *rb = fb->_ColorDrawBuffers[buf];
if (fb->_ColorDrawBuffers[output][0]->DataType
!= span->array->ChanType || output > 0) {
convert_color_type(span,
fb->_ColorDrawBuffers[output][0]->DataType,
output);
}
/* color[fragOutput] will be written to buffer[buf] */
if (numDrawBuffers > 1) {
/* save colors for second, third renderbuffer writes */
_mesa_memcpy(rgbaSave, span->array->rgba,
4 * span->end * sizeof(GLchan));
}
if (rb) {
GLchan rgbaSave[MAX_WIDTH][4];
const GLuint fragOutput = multiFragOutputs ? buf : 0;
/* Loop over renderbuffers (i.e. GL_FRONT_AND_BACK) */
for (buf = 0; buf < numDrawBuffers; buf++) {
struct gl_renderbuffer *rb = fb->_ColorDrawBuffers[output][buf];
ASSERT(rb->_BaseFormat == GL_RGBA || rb->_BaseFormat == GL_RGB);
if (rb->DataType != span->array->ChanType || fragOutput > 0) {
convert_color_type(span, rb->DataType, fragOutput);
}
if (ctx->Color._LogicOpEnabled) {
_swrast_logicop_rgba_span(ctx, rb, span);
}
else if (ctx->Color.BlendEnabled) {
_swrast_blend_span(ctx, rb, span);
}
if (!multiFragOutputs && numBuffers > 1) {
/* save colors for second, third renderbuffer writes */
_mesa_memcpy(rgbaSave, span->array->rgba,
4 * span->end * sizeof(GLchan));
}
if (colorMask != 0xffffffff) {
_swrast_mask_rgba_span(ctx, rb, span);
}
ASSERT(rb->_BaseFormat == GL_RGBA || rb->_BaseFormat == GL_RGB);
if (span->arrayMask & SPAN_XY) {
/* array of pixel coords */
ASSERT(rb->PutValues);
rb->PutValues(ctx, rb, span->end,
span->array->x, span->array->y,
span->array->rgba, span->array->mask);
}
else {
/* horizontal run of pixels */
ASSERT(rb->PutRow);
rb->PutRow(ctx, rb, span->end, span->x, span->y,
span->array->rgba,
span->writeAll ? NULL: span->array->mask);
}
if (ctx->Color._LogicOpEnabled) {
_swrast_logicop_rgba_span(ctx, rb, span);
}
else if (ctx->Color.BlendEnabled) {
_swrast_blend_span(ctx, rb, span);
}
if (buf + 1 < numDrawBuffers) {
/* restore original span values */
_mesa_memcpy(span->array->rgba, rgbaSave,
4 * span->end * sizeof(GLchan));
}
} /* for buf */
} /* if output is written to */
} /* for output */
if (colorMask != 0xffffffff) {
_swrast_mask_rgba_span(ctx, rb, span);
}
if (span->arrayMask & SPAN_XY) {
/* array of pixel coords */
ASSERT(rb->PutValues);
rb->PutValues(ctx, rb, span->end,
span->array->x, span->array->y,
span->array->rgba, span->array->mask);
}
else {
/* horizontal run of pixels */
ASSERT(rb->PutRow);
rb->PutRow(ctx, rb, span->end, span->x, span->y,
span->array->rgba,
span->writeAll ? NULL: span->array->mask);
}
if (!multiFragOutputs && numBuffers > 1) {
/* restore original span values */
_mesa_memcpy(span->array->rgba, rgbaSave,
4 * span->end * sizeof(GLchan));
}
} /* if rb */
} /* for buf */
}
end:
/* restore these values before returning */

View File

@@ -130,7 +130,7 @@ _swrast_culltriangle( GLcontext *ctx,
#define T_SCALE theight
#define SETUP_CODE \
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0][0];\
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0];\
struct gl_texture_object *obj = ctx->Texture.Unit[0].Current2D; \
const GLint b = obj->BaseLevel; \
const GLfloat twidth = (GLfloat) obj->Image[0][b]->Width; \
@@ -182,7 +182,7 @@ _swrast_culltriangle( GLcontext *ctx,
#define T_SCALE theight
#define SETUP_CODE \
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0][0];\
struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0];\
struct gl_texture_object *obj = ctx->Texture.Unit[0].Current2D; \
const GLint b = obj->BaseLevel; \
const GLfloat twidth = (GLfloat) obj->Image[0][b]->Width; \