diff options
Diffstat (limited to 'src/mesa/drivers/x11')
-rw-r--r-- | src/mesa/drivers/x11/xm_api.c | 98 | ||||
-rw-r--r-- | src/mesa/drivers/x11/xm_buffer.c | 113 | ||||
-rw-r--r-- | src/mesa/drivers/x11/xm_dd.c | 32 | ||||
-rw-r--r-- | src/mesa/drivers/x11/xm_span.c | 334 | ||||
-rw-r--r-- | src/mesa/drivers/x11/xm_surface.c | 251 | ||||
-rw-r--r-- | src/mesa/drivers/x11/xm_tri.c | 40 | ||||
-rw-r--r-- | src/mesa/drivers/x11/xm_winsys.c | 362 | ||||
-rw-r--r-- | src/mesa/drivers/x11/xmesaP.h | 50 |
8 files changed, 1078 insertions, 202 deletions
diff --git a/src/mesa/drivers/x11/xm_api.c b/src/mesa/drivers/x11/xm_api.c index 5bae69a4720..2eb88c1557d 100644 --- a/src/mesa/drivers/x11/xm_api.c +++ b/src/mesa/drivers/x11/xm_api.c @@ -76,11 +76,18 @@ #include "swrast/swrast.h" #include "swrast_setup/swrast_setup.h" #include "vbo/vbo.h" +#if 0 #include "tnl/tnl.h" #include "tnl/t_context.h" #include "tnl/t_pipeline.h" +#endif #include "drivers/common/driverfuncs.h" +#include "state_tracker/st_public.h" +#include "state_tracker/st_context.h" +#include "softpipe/sp_context.h" +#include "pipe/p_defines.h" + /** * Global X driver lock */ @@ -381,7 +388,7 @@ create_xmesa_buffer(XMesaDrawable d, BufferType type, /* * Front renderbuffer */ - b->frontxrb = xmesa_new_renderbuffer(NULL, 0, &vis->mesa_visual, GL_FALSE); + b->frontxrb = xmesa_create_renderbuffer(NULL, 0, &vis->mesa_visual, GL_FALSE); if (!b->frontxrb) { _mesa_free(b); return NULL; @@ -390,13 +397,13 @@ create_xmesa_buffer(XMesaDrawable d, BufferType type, b->frontxrb->drawable = d; b->frontxrb->pixmap = (XMesaPixmap) d; _mesa_add_renderbuffer(&b->mesa_buffer, BUFFER_FRONT_LEFT, - &b->frontxrb->Base); + &b->frontxrb->St.Base); /* * Back renderbuffer */ if (vis->mesa_visual.doubleBufferMode) { - b->backxrb = xmesa_new_renderbuffer(NULL, 0, &vis->mesa_visual, GL_TRUE); + b->backxrb = xmesa_create_renderbuffer(NULL, 0, &vis->mesa_visual, GL_TRUE); if (!b->backxrb) { /* XXX free front xrb too */ _mesa_free(b); @@ -407,7 +414,7 @@ create_xmesa_buffer(XMesaDrawable d, BufferType type, b->db_mode = vis->ximage_flag ? BACK_XIMAGE : BACK_PIXMAP; _mesa_add_renderbuffer(&b->mesa_buffer, BUFFER_BACK_LEFT, - &b->backxrb->Base); + &b->backxrb->St.Base); } /* @@ -425,14 +432,43 @@ create_xmesa_buffer(XMesaDrawable d, BufferType type, b->swAlpha = GL_FALSE; } + if (vis->mesa_visual.depthBits > 0 && + vis->mesa_visual.stencilBits > 0) { + /* combined depth/stencil */ + struct gl_renderbuffer *rb + = st_new_renderbuffer_fb(GL_DEPTH24_STENCIL8_EXT); + _mesa_add_renderbuffer(&b->mesa_buffer, BUFFER_DEPTH, rb); + _mesa_add_renderbuffer(&b->mesa_buffer, BUFFER_STENCIL, rb); + } + else { + if (vis->mesa_visual.depthBits > 0) { + struct gl_renderbuffer *rb + = st_new_renderbuffer_fb(GL_DEPTH_COMPONENT32); + _mesa_add_renderbuffer(&b->mesa_buffer, BUFFER_DEPTH, rb); + } + + if (vis->mesa_visual.stencilBits > 0) { + struct gl_renderbuffer *rb + = st_new_renderbuffer_fb(GL_STENCIL_INDEX8_EXT); + _mesa_add_renderbuffer(&b->mesa_buffer, BUFFER_STENCIL, rb); + } + } + + if (vis->mesa_visual.accumRedBits > 0) { + struct gl_renderbuffer *rb + = st_new_renderbuffer_fb(GL_RGBA16); + _mesa_add_renderbuffer(&b->mesa_buffer, BUFFER_ACCUM, rb); + } + + /* * Other renderbuffer (depth, stencil, etc) */ _mesa_add_soft_renderbuffers(&b->mesa_buffer, - GL_FALSE, /* color */ - vis->mesa_visual.haveDepthBuffer, - vis->mesa_visual.haveStencilBuffer, - vis->mesa_visual.haveAccumBuffer, + GL_FALSE, /* color */ + GL_FALSE, /*vis->mesa_visual.haveDepthBuffer,*/ + GL_FALSE, /* stencil */ + GL_FALSE, /* accum */ b->swAlpha, vis->mesa_visual.numAuxBuffers > 0 ); @@ -1563,7 +1599,9 @@ XMesaContext XMesaCreateContext( XMesaVisual v, XMesaContext share_list ) XMesaContext c; GLcontext *mesaCtx; struct dd_function_table functions; +#if 0 TNLcontext *tnl; +#endif if (firstTime) { _glthread_INIT_MUTEX(_xmesa_lock); @@ -1580,6 +1618,15 @@ XMesaContext XMesaCreateContext( XMesaVisual v, XMesaContext share_list ) /* initialize with default driver functions, then plug in XMesa funcs */ _mesa_init_driver_functions(&functions); xmesa_init_driver_functions(v, &functions); + st_init_driver_functions(&functions); + + /* override st's function */ + functions.UpdateState = xmesa_update_state; + + /* + functions.NewRenderbuffer = xmesa_new_renderbuffer; + */ + if (!_mesa_initialize_context(mesaCtx, &v->mesa_visual, share_list ? &(share_list->mesa) : (GLcontext *) NULL, &functions, (void *) c)) { @@ -1620,22 +1667,49 @@ XMesaContext XMesaCreateContext( XMesaVisual v, XMesaContext share_list ) /* Initialize the software rasterizer and helper modules. */ - if (!_swrast_CreateContext( mesaCtx ) || - !_vbo_CreateContext( mesaCtx ) || + if (!_swrast_CreateContext( mesaCtx ) +#if 0 + || !_vbo_CreateContext( mesaCtx ) || !_tnl_CreateContext( mesaCtx ) || - !_swsetup_CreateContext( mesaCtx )) { + !_swsetup_CreateContext( mesaCtx ) +#endif + ) { _mesa_free_context_data(&c->mesa); _mesa_free(c); return NULL; } +#if 0 /* tnl setup */ tnl = TNL_CONTEXT(mesaCtx); tnl->Driver.RunPipeline = _tnl_run_pipeline; +#endif + /* swrast setup */ xmesa_register_swrast_functions( mesaCtx ); + + + st_create_context( mesaCtx, + xmesa_create_softpipe( c ) ); + + _swsetup_CreateContext( mesaCtx ); _swsetup_Wakeup(mesaCtx); + /* override these functions, as if the xlib driver were derived from + * the softpipe driver. + */ +#if 0 + mesaCtx->st->pipe->surface_alloc = xmesa_surface_alloc; +#endif + mesaCtx->st->pipe->is_format_supported = xmesa_is_format_supported; + mesaCtx->st->pipe->get_tile_rgba = xmesa_get_tile_rgba; + mesaCtx->st->pipe->put_tile_rgba = xmesa_put_tile_rgba; + + mesaCtx->st->haveFramebufferRegions = GL_FALSE; + + /* special pipe->clear function */ + mesaCtx->st->pipe->clear = xmesa_clear; + return c; } @@ -1652,8 +1726,10 @@ void XMesaDestroyContext( XMesaContext c ) _swsetup_DestroyContext( mesaCtx ); _swrast_DestroyContext( mesaCtx ); +#if 0 _tnl_DestroyContext( mesaCtx ); _vbo_DestroyContext( mesaCtx ); +#endif _mesa_free_context_data( mesaCtx ); _mesa_free( c ); } diff --git a/src/mesa/drivers/x11/xm_buffer.c b/src/mesa/drivers/x11/xm_buffer.c index 51d183bb435..09356c7329f 100644 --- a/src/mesa/drivers/x11/xm_buffer.c +++ b/src/mesa/drivers/x11/xm_buffer.c @@ -35,6 +35,10 @@ #include "imports.h" #include "framebuffer.h" #include "renderbuffer.h" +#include "pipe/p_state.h" +#include "pipe/p_defines.h" +#include "pipe/p_winsys.h" +#include "state_tracker/st_context.h" #if defined(USE_XSHM) && !defined(XFree86Server) @@ -245,6 +249,18 @@ xmesa_delete_renderbuffer(struct gl_renderbuffer *rb) } +static void +finish_surface_init(GLcontext *ctx, struct xmesa_renderbuffer *xrb) +{ + struct pipe_context *pipe = ctx->st->pipe; + if (!xrb->St.surface->region) { + int w = 1, h = 1; + xrb->St.surface->region = pipe->winsys->region_alloc(pipe->winsys, + 1, w, h, 0x0); + } +} + + /** * Reallocate renderbuffer storage for front color buffer. * Called via gl_renderbuffer::AllocStorage() @@ -268,6 +284,12 @@ xmesa_alloc_front_storage(GLcontext *ctx, struct gl_renderbuffer *rb, rb->Height = height; rb->InternalFormat = internalFormat; + if (!xrb->St.surface || !xrb->St.surface->region) + finish_surface_init(ctx, xrb); + + xrb->St.surface->width = width; + xrb->St.surface->height = height; + return GL_TRUE; } @@ -317,46 +339,103 @@ xmesa_alloc_back_storage(GLcontext *ctx, struct gl_renderbuffer *rb, xrb->origin4 = NULL; } + if (!xrb->St.surface || !xrb->St.surface->region) + finish_surface_init(ctx, xrb); + + xrb->St.surface->width = width; + xrb->St.surface->height = height; + return GL_TRUE; } +/** + * Called to create the front/back color renderbuffers, not user-created + * renderbuffers. + */ struct xmesa_renderbuffer * -xmesa_new_renderbuffer(GLcontext *ctx, GLuint name, const GLvisual *visual, - GLboolean backBuffer) +xmesa_create_renderbuffer(GLcontext *ctx, GLuint name, const GLvisual *visual, + GLboolean backBuffer) { struct xmesa_renderbuffer *xrb = CALLOC_STRUCT(xmesa_renderbuffer); + struct pipe_context *pipe = NULL;/*ctx->st->pipe;*/ if (xrb) { GLuint name = 0; - _mesa_init_renderbuffer(&xrb->Base, name); + GLuint pipeFormat = 0; + struct xmesa_surface *xms; + + _mesa_init_renderbuffer(&xrb->St.Base, name); - xrb->Base.Delete = xmesa_delete_renderbuffer; + xrb->St.Base.Delete = xmesa_delete_renderbuffer; if (backBuffer) - xrb->Base.AllocStorage = xmesa_alloc_back_storage; + xrb->St.Base.AllocStorage = xmesa_alloc_back_storage; else - xrb->Base.AllocStorage = xmesa_alloc_front_storage; + xrb->St.Base.AllocStorage = xmesa_alloc_front_storage; if (visual->rgbMode) { - xrb->Base.InternalFormat = GL_RGBA; - xrb->Base._BaseFormat = GL_RGBA; - xrb->Base.DataType = GL_UNSIGNED_BYTE; - xrb->Base.RedBits = visual->redBits; - xrb->Base.GreenBits = visual->greenBits; - xrb->Base.BlueBits = visual->blueBits; - xrb->Base.AlphaBits = visual->alphaBits; + xrb->St.Base.InternalFormat = GL_RGBA; + xrb->St.Base._BaseFormat = GL_RGBA; + xrb->St.Base.DataType = GL_UNSIGNED_BYTE; + xrb->St.Base.RedBits = visual->redBits; + xrb->St.Base.GreenBits = visual->greenBits; + xrb->St.Base.BlueBits = visual->blueBits; + xrb->St.Base.AlphaBits = visual->alphaBits; + pipeFormat = PIPE_FORMAT_U_A8_R8_G8_B8; } else { - xrb->Base.InternalFormat = GL_COLOR_INDEX; - xrb->Base._BaseFormat = GL_COLOR_INDEX; - xrb->Base.DataType = GL_UNSIGNED_INT; - xrb->Base.IndexBits = visual->indexBits; + xrb->St.Base.InternalFormat = GL_COLOR_INDEX; + xrb->St.Base._BaseFormat = GL_COLOR_INDEX; + xrb->St.Base.DataType = GL_UNSIGNED_INT; + xrb->St.Base.IndexBits = visual->indexBits; } /* only need to set Red/Green/EtcBits fields for user-created RBs */ + + xrb->St.surface = xmesa_new_color_surface(pipe, pipeFormat); + xms = (struct xmesa_surface *) xrb->St.surface; + xms->xrb = xrb; } return xrb; } +#if 0 +struct gl_renderbuffer * +xmesa_new_renderbuffer(GLcontext *ctx, struct gl_renderbuffer *rb, + GLenum internalFormat, GLuint width, GLuint height) +{ + struct xmesa_renderbuffer *xrb = CALLOC_STRUCT(xmesa_renderbuffer); + if (xrb) { + GLuint name = 0; + _mesa_init_renderbuffer(&xrb->St.Base, name); + + xrb->St.Base.Delete = xmesa_delete_renderbuffer; + if (backBuffer) + xrb->St.Base.AllocStorage = xmesa_alloc_back_storage; + else + xrb->St.Base.AllocStorage = xmesa_alloc_front_storage; + + if (visual->rgbMode) { + xrb->St.Base.InternalFormat = GL_RGBA; + xrb->St.Base._BaseFormat = GL_RGBA; + xrb->St.Base.DataType = GL_UNSIGNED_BYTE; + xrb->St.Base.RedBits = visual->redBits; + xrb->St.Base.GreenBits = visual->greenBits; + xrb->St.Base.BlueBits = visual->blueBits; + xrb->St.Base.AlphaBits = visual->alphaBits; + } + else { + xrb->St.Base.InternalFormat = GL_COLOR_INDEX; + xrb->St.Base._BaseFormat = GL_COLOR_INDEX; + xrb->St.Base.DataType = GL_UNSIGNED_INT; + xrb->St.Base.IndexBits = visual->indexBits; + } + /* only need to set Red/Green/EtcBits fields for user-created RBs */ + } + return xrb; +} +#endif + + /** * Called via gl_framebuffer::Delete() method when this buffer * is _really_ being deleted. diff --git a/src/mesa/drivers/x11/xm_dd.c b/src/mesa/drivers/x11/xm_dd.c index 54acbfe3cb8..ec094b6021d 100644 --- a/src/mesa/drivers/x11/xm_dd.c +++ b/src/mesa/drivers/x11/xm_dd.c @@ -53,6 +53,10 @@ #include "tnl/tnl.h" #include "tnl/t_context.h" +#include "softpipe/sp_context.h" +#include "state_tracker/st_public.h" +#include "state_tracker/st_context.h" +#include "state_tracker/st_draw.h" /* @@ -218,7 +222,7 @@ clear_pixmap(GLcontext *ctx, struct xmesa_renderbuffer *xrb, assert(xmbuf->cleargc); XMesaFillRectangle( xmesa->display, xrb->pixmap, xmbuf->cleargc, - x, xrb->Base.Height - y - height, + x, xrb->St.Base.Height - y - height, width, height ); } @@ -329,9 +333,9 @@ clear_32bit_ximage(GLcontext *ctx, struct xmesa_renderbuffer *xrb, | ((pixel << 24) & 0xff000000); } - if (width == xrb->Base.Width && height == xrb->Base.Height) { + if (width == xrb->St.Base.Width && height == xrb->St.Base.Height) { /* clearing whole buffer */ - const GLuint n = xrb->Base.Width * xrb->Base.Height; + const GLuint n = xrb->St.Base.Width * xrb->St.Base.Height; GLuint *ptr4 = (GLuint *) xrb->ximage->data; if (pixel == 0) { /* common case */ @@ -375,8 +379,8 @@ clear_nbit_ximage(GLcontext *ctx, struct xmesa_renderbuffer *xrb, -static void -clear_buffers(GLcontext *ctx, GLbitfield buffers) +void +xmesa_clear_buffers(GLcontext *ctx, GLbitfield buffers) { if (ctx->DrawBuffer->Name == 0) { /* this is a window system framebuffer */ @@ -779,7 +783,7 @@ get_string( GLcontext *ctx, GLenum name ) #ifdef XFree86Server return (const GLubyte *) "Mesa GLX Indirect"; #else - return (const GLubyte *) "Mesa X11"; + return (const GLubyte *) "Mesa X11 (softpipe)"; #endif case GL_VENDOR: #ifdef XFree86Server @@ -906,6 +910,9 @@ xmesa_update_state( GLcontext *ctx, GLbitfield new_state ) _vbo_InvalidateState( ctx, new_state ); _swsetup_InvalidateState( ctx, new_state ); + st_invalidate_state( ctx, new_state ); + + if (ctx->DrawBuffer->Name != 0) return; @@ -913,7 +920,7 @@ xmesa_update_state( GLcontext *ctx, GLbitfield new_state ) * GL_DITHER, GL_READ/DRAW_BUFFER, buffer binding state, etc. effect * renderbuffer span/clear funcs. */ - if (new_state & (_NEW_COLOR | _NEW_PIXEL | _NEW_BUFFERS)) { + if (new_state & (_NEW_COLOR | _NEW_BUFFERS)) { XMesaBuffer xmbuf = XMESA_BUFFER(ctx->DrawBuffer); struct xmesa_renderbuffer *front_xrb, *back_xrb; @@ -1086,9 +1093,9 @@ xmesa_new_query_object(GLcontext *ctx, GLuint id) static void -xmesa_begin_query(GLcontext *ctx, GLenum target, struct gl_query_object *q) +xmesa_begin_query(GLcontext *ctx, struct gl_query_object *q) { - if (target == GL_TIME_ELAPSED_EXT) { + if (q->Target == GL_TIME_ELAPSED_EXT) { struct xmesa_query_object *xq = (struct xmesa_query_object *) q; (void) gettimeofday(&xq->StartTime, NULL); } @@ -1113,9 +1120,9 @@ time_diff(const struct timeval *t0, const struct timeval *t1) static void -xmesa_end_query(GLcontext *ctx, GLenum target, struct gl_query_object *q) +xmesa_end_query(GLcontext *ctx, struct gl_query_object *q) { - if (target == GL_TIME_ELAPSED_EXT) { + if (q->Target == GL_TIME_ELAPSED_EXT) { struct xmesa_query_object *xq = (struct xmesa_query_object *) q; struct timeval endTime; (void) gettimeofday(&endTime, NULL); @@ -1146,7 +1153,7 @@ xmesa_init_driver_functions( XMesaVisual xmvisual, driver->IndexMask = index_mask; driver->ColorMask = color_mask; driver->Enable = enable; - driver->Clear = clear_buffers; + driver->Clear = xmesa_clear_buffers; driver->Viewport = xmesa_viewport; #ifndef XFree86Server driver->CopyPixels = xmesa_CopyPixels; @@ -1171,6 +1178,7 @@ xmesa_init_driver_functions( XMesaVisual xmvisual, driver->BeginQuery = xmesa_begin_query; driver->EndQuery = xmesa_end_query; #endif + } diff --git a/src/mesa/drivers/x11/xm_span.c b/src/mesa/drivers/x11/xm_span.c index a24966b3aeb..ce54a18a273 100644 --- a/src/mesa/drivers/x11/xm_span.c +++ b/src/mesa/drivers/x11/xm_span.c @@ -1303,6 +1303,17 @@ static void put_row_rgb_TRUEDITHER_ximage( RGB_SPAN_ARGS ) } + +static void *get_pointer_4_ximage( GLcontext *ctx, + struct gl_renderbuffer *rb, + GLint x, GLint y ) +{ + GET_XRB(xrb); + return PIXEL_ADDR4(xrb, x, y); +} + + + /* * Write a span of PF_8A8B8G8R-format pixels to an ximage. */ @@ -4528,257 +4539,260 @@ xmesa_set_renderbuffer_funcs(struct xmesa_renderbuffer *xrb, enum pixel_format pixelformat, GLint depth) { const GLboolean pixmap = xrb->pixmap ? GL_TRUE : GL_FALSE; + struct gl_renderbuffer *rb = &xrb->St.Base; switch (pixelformat) { case PF_Index: - ASSERT(xrb->Base.DataType == GL_UNSIGNED_INT); + ASSERT(rb->DataType == GL_UNSIGNED_INT); if (pixmap) { - xrb->Base.PutRow = put_row_ci_pixmap; - xrb->Base.PutRowRGB = NULL; - xrb->Base.PutMonoRow = put_mono_row_ci_pixmap; - xrb->Base.PutValues = put_values_ci_pixmap; - xrb->Base.PutMonoValues = put_mono_values_ci_pixmap; + rb->PutRow = put_row_ci_pixmap; + rb->PutRowRGB = NULL; + rb->PutMonoRow = put_mono_row_ci_pixmap; + rb->PutValues = put_values_ci_pixmap; + rb->PutMonoValues = put_mono_values_ci_pixmap; } else { - xrb->Base.PutRow = put_row_ci_ximage; - xrb->Base.PutRowRGB = NULL; - xrb->Base.PutMonoRow = put_mono_row_ci_ximage; - xrb->Base.PutValues = put_values_ci_ximage; - xrb->Base.PutMonoValues = put_mono_values_ci_ximage; + rb->PutRow = put_row_ci_ximage; + rb->PutRowRGB = NULL; + rb->PutMonoRow = put_mono_row_ci_ximage; + rb->PutValues = put_values_ci_ximage; + rb->PutMonoValues = put_mono_values_ci_ximage; } break; case PF_Truecolor: if (pixmap) { - xrb->Base.PutRow = put_row_TRUECOLOR_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_TRUECOLOR_pixmap; - xrb->Base.PutMonoRow = put_mono_row_pixmap; - xrb->Base.PutValues = put_values_TRUECOLOR_pixmap; - xrb->Base.PutMonoValues = put_mono_values_pixmap; + rb->PutRow = put_row_TRUECOLOR_pixmap; + rb->PutRowRGB = put_row_rgb_TRUECOLOR_pixmap; + rb->PutMonoRow = put_mono_row_pixmap; + rb->PutValues = put_values_TRUECOLOR_pixmap; + rb->PutMonoValues = put_mono_values_pixmap; } else { - xrb->Base.PutRow = put_row_TRUECOLOR_ximage; - xrb->Base.PutRowRGB = put_row_rgb_TRUECOLOR_ximage; - xrb->Base.PutMonoRow = put_mono_row_ximage; - xrb->Base.PutValues = put_values_TRUECOLOR_ximage; - xrb->Base.PutMonoValues = put_mono_values_ximage; + rb->PutRow = put_row_TRUECOLOR_ximage; + rb->PutRowRGB = put_row_rgb_TRUECOLOR_ximage; + rb->PutMonoRow = put_mono_row_ximage; + rb->PutValues = put_values_TRUECOLOR_ximage; + rb->PutMonoValues = put_mono_values_ximage; } break; case PF_Dither_True: if (pixmap) { - xrb->Base.PutRow = put_row_TRUEDITHER_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_TRUEDITHER_pixmap; - xrb->Base.PutMonoRow = put_mono_row_TRUEDITHER_pixmap; - xrb->Base.PutValues = put_values_TRUEDITHER_pixmap; - xrb->Base.PutMonoValues = put_mono_values_TRUEDITHER_pixmap; + rb->PutRow = put_row_TRUEDITHER_pixmap; + rb->PutRowRGB = put_row_rgb_TRUEDITHER_pixmap; + rb->PutMonoRow = put_mono_row_TRUEDITHER_pixmap; + rb->PutValues = put_values_TRUEDITHER_pixmap; + rb->PutMonoValues = put_mono_values_TRUEDITHER_pixmap; } else { - xrb->Base.PutRow = put_row_TRUEDITHER_ximage; - xrb->Base.PutRowRGB = put_row_rgb_TRUEDITHER_ximage; - xrb->Base.PutMonoRow = put_mono_row_TRUEDITHER_ximage; - xrb->Base.PutValues = put_values_TRUEDITHER_ximage; - xrb->Base.PutMonoValues = put_mono_values_TRUEDITHER_ximage; + rb->PutRow = put_row_TRUEDITHER_ximage; + rb->PutRowRGB = put_row_rgb_TRUEDITHER_ximage; + rb->PutMonoRow = put_mono_row_TRUEDITHER_ximage; + rb->PutValues = put_values_TRUEDITHER_ximage; + rb->PutMonoValues = put_mono_values_TRUEDITHER_ximage; } break; case PF_8A8B8G8R: if (pixmap) { - xrb->Base.PutRow = put_row_8A8B8G8R_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_8A8B8G8R_pixmap; - xrb->Base.PutMonoRow = put_mono_row_pixmap; - xrb->Base.PutValues = put_values_8A8B8G8R_pixmap; - xrb->Base.PutMonoValues = put_mono_values_pixmap; + rb->PutRow = put_row_8A8B8G8R_pixmap; + rb->PutRowRGB = put_row_rgb_8A8B8G8R_pixmap; + rb->PutMonoRow = put_mono_row_pixmap; + rb->PutValues = put_values_8A8B8G8R_pixmap; + rb->PutMonoValues = put_mono_values_pixmap; } else { - xrb->Base.PutRow = put_row_8A8B8G8R_ximage; - xrb->Base.PutRowRGB = put_row_rgb_8A8B8G8R_ximage; - xrb->Base.PutMonoRow = put_mono_row_8A8B8G8R_ximage; - xrb->Base.PutValues = put_values_8A8B8G8R_ximage; - xrb->Base.PutMonoValues = put_mono_values_8A8B8G8R_ximage; + rb->PutRow = put_row_8A8B8G8R_ximage; + rb->PutRowRGB = put_row_rgb_8A8B8G8R_ximage; + rb->PutMonoRow = put_mono_row_8A8B8G8R_ximage; + rb->PutValues = put_values_8A8B8G8R_ximage; + rb->PutMonoValues = put_mono_values_8A8B8G8R_ximage; + rb->GetPointer = get_pointer_4_ximage; } break; case PF_8A8R8G8B: if (pixmap) { - xrb->Base.PutRow = put_row_8A8R8G8B_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_8A8R8G8B_pixmap; - xrb->Base.PutMonoRow = put_mono_row_pixmap; - xrb->Base.PutValues = put_values_8A8R8G8B_pixmap; - xrb->Base.PutMonoValues = put_mono_values_pixmap; + rb->PutRow = put_row_8A8R8G8B_pixmap; + rb->PutRowRGB = put_row_rgb_8A8R8G8B_pixmap; + rb->PutMonoRow = put_mono_row_pixmap; + rb->PutValues = put_values_8A8R8G8B_pixmap; + rb->PutMonoValues = put_mono_values_pixmap; } else { - xrb->Base.PutRow = put_row_8A8R8G8B_ximage; - xrb->Base.PutRowRGB = put_row_rgb_8A8R8G8B_ximage; - xrb->Base.PutMonoRow = put_mono_row_8A8R8G8B_ximage; - xrb->Base.PutValues = put_values_8A8R8G8B_ximage; - xrb->Base.PutMonoValues = put_mono_values_8A8R8G8B_ximage; + rb->PutRow = put_row_8A8R8G8B_ximage; + rb->PutRowRGB = put_row_rgb_8A8R8G8B_ximage; + rb->PutMonoRow = put_mono_row_8A8R8G8B_ximage; + rb->PutValues = put_values_8A8R8G8B_ximage; + rb->PutMonoValues = put_mono_values_8A8R8G8B_ximage; + rb->GetPointer = get_pointer_4_ximage; } break; case PF_8R8G8B: if (pixmap) { - xrb->Base.PutRow = put_row_8R8G8B_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_8R8G8B_pixmap; - xrb->Base.PutMonoRow = put_mono_row_pixmap; - xrb->Base.PutValues = put_values_8R8G8B_pixmap; - xrb->Base.PutMonoValues = put_mono_values_pixmap; + rb->PutRow = put_row_8R8G8B_pixmap; + rb->PutRowRGB = put_row_rgb_8R8G8B_pixmap; + rb->PutMonoRow = put_mono_row_pixmap; + rb->PutValues = put_values_8R8G8B_pixmap; + rb->PutMonoValues = put_mono_values_pixmap; } else { - xrb->Base.PutRow = put_row_8R8G8B_ximage; - xrb->Base.PutRowRGB = put_row_rgb_8R8G8B_ximage; - xrb->Base.PutMonoRow = put_mono_row_8R8G8B_ximage; - xrb->Base.PutValues = put_values_8R8G8B_ximage; - xrb->Base.PutMonoValues = put_mono_values_8R8G8B_ximage; + rb->PutRow = put_row_8R8G8B_ximage; + rb->PutRowRGB = put_row_rgb_8R8G8B_ximage; + rb->PutMonoRow = put_mono_row_8R8G8B_ximage; + rb->PutValues = put_values_8R8G8B_ximage; + rb->PutMonoValues = put_mono_values_8R8G8B_ximage; } break; case PF_8R8G8B24: if (pixmap) { - xrb->Base.PutRow = put_row_8R8G8B24_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_8R8G8B24_pixmap; - xrb->Base.PutMonoRow = put_mono_row_pixmap; - xrb->Base.PutValues = put_values_8R8G8B24_pixmap; - xrb->Base.PutMonoValues = put_mono_values_pixmap; + rb->PutRow = put_row_8R8G8B24_pixmap; + rb->PutRowRGB = put_row_rgb_8R8G8B24_pixmap; + rb->PutMonoRow = put_mono_row_pixmap; + rb->PutValues = put_values_8R8G8B24_pixmap; + rb->PutMonoValues = put_mono_values_pixmap; } else { - xrb->Base.PutRow = put_row_8R8G8B24_ximage; - xrb->Base.PutRowRGB = put_row_rgb_8R8G8B24_ximage; - xrb->Base.PutMonoRow = put_mono_row_8R8G8B24_ximage; - xrb->Base.PutValues = put_values_8R8G8B24_ximage; - xrb->Base.PutMonoValues = put_mono_values_8R8G8B24_ximage; + rb->PutRow = put_row_8R8G8B24_ximage; + rb->PutRowRGB = put_row_rgb_8R8G8B24_ximage; + rb->PutMonoRow = put_mono_row_8R8G8B24_ximage; + rb->PutValues = put_values_8R8G8B24_ximage; + rb->PutMonoValues = put_mono_values_8R8G8B24_ximage; } break; case PF_5R6G5B: if (pixmap) { - xrb->Base.PutRow = put_row_5R6G5B_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_5R6G5B_pixmap; - xrb->Base.PutMonoRow = put_mono_row_pixmap; - xrb->Base.PutValues = put_values_5R6G5B_pixmap; - xrb->Base.PutMonoValues = put_mono_values_pixmap; + rb->PutRow = put_row_5R6G5B_pixmap; + rb->PutRowRGB = put_row_rgb_5R6G5B_pixmap; + rb->PutMonoRow = put_mono_row_pixmap; + rb->PutValues = put_values_5R6G5B_pixmap; + rb->PutMonoValues = put_mono_values_pixmap; } else { - xrb->Base.PutRow = put_row_5R6G5B_ximage; - xrb->Base.PutRowRGB = put_row_rgb_5R6G5B_ximage; - xrb->Base.PutMonoRow = put_mono_row_ximage; - xrb->Base.PutValues = put_values_5R6G5B_ximage; - xrb->Base.PutMonoValues = put_mono_values_ximage; + rb->PutRow = put_row_5R6G5B_ximage; + rb->PutRowRGB = put_row_rgb_5R6G5B_ximage; + rb->PutMonoRow = put_mono_row_ximage; + rb->PutValues = put_values_5R6G5B_ximage; + rb->PutMonoValues = put_mono_values_ximage; } break; case PF_Dither_5R6G5B: if (pixmap) { - xrb->Base.PutRow = put_row_DITHER_5R6G5B_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_DITHER_5R6G5B_pixmap; - xrb->Base.PutMonoRow = put_mono_row_TRUEDITHER_pixmap; - xrb->Base.PutValues = put_values_DITHER_5R6G5B_pixmap; - xrb->Base.PutMonoValues = put_mono_values_TRUEDITHER_pixmap; + rb->PutRow = put_row_DITHER_5R6G5B_pixmap; + rb->PutRowRGB = put_row_rgb_DITHER_5R6G5B_pixmap; + rb->PutMonoRow = put_mono_row_TRUEDITHER_pixmap; + rb->PutValues = put_values_DITHER_5R6G5B_pixmap; + rb->PutMonoValues = put_mono_values_TRUEDITHER_pixmap; } else { - xrb->Base.PutRow = put_row_DITHER_5R6G5B_ximage; - xrb->Base.PutRowRGB = put_row_rgb_DITHER_5R6G5B_ximage; - xrb->Base.PutMonoRow = put_mono_row_DITHER_5R6G5B_ximage; - xrb->Base.PutValues = put_values_DITHER_5R6G5B_ximage; - xrb->Base.PutMonoValues = put_mono_values_DITHER_5R6G5B_ximage; + rb->PutRow = put_row_DITHER_5R6G5B_ximage; + rb->PutRowRGB = put_row_rgb_DITHER_5R6G5B_ximage; + rb->PutMonoRow = put_mono_row_DITHER_5R6G5B_ximage; + rb->PutValues = put_values_DITHER_5R6G5B_ximage; + rb->PutMonoValues = put_mono_values_DITHER_5R6G5B_ximage; } break; case PF_Dither: if (pixmap) { - xrb->Base.PutRow = put_row_DITHER_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_DITHER_pixmap; - xrb->Base.PutMonoRow = put_mono_row_DITHER_pixmap; - xrb->Base.PutValues = put_values_DITHER_pixmap; - xrb->Base.PutMonoValues = put_mono_values_DITHER_pixmap; + rb->PutRow = put_row_DITHER_pixmap; + rb->PutRowRGB = put_row_rgb_DITHER_pixmap; + rb->PutMonoRow = put_mono_row_DITHER_pixmap; + rb->PutValues = put_values_DITHER_pixmap; + rb->PutMonoValues = put_mono_values_DITHER_pixmap; } else { if (depth == 8) { - xrb->Base.PutRow = put_row_DITHER8_ximage; - xrb->Base.PutRowRGB = put_row_rgb_DITHER8_ximage; - xrb->Base.PutMonoRow = put_mono_row_DITHER8_ximage; - xrb->Base.PutValues = put_values_DITHER8_ximage; - xrb->Base.PutMonoValues = put_mono_values_DITHER8_ximage; + rb->PutRow = put_row_DITHER8_ximage; + rb->PutRowRGB = put_row_rgb_DITHER8_ximage; + rb->PutMonoRow = put_mono_row_DITHER8_ximage; + rb->PutValues = put_values_DITHER8_ximage; + rb->PutMonoValues = put_mono_values_DITHER8_ximage; } else { - xrb->Base.PutRow = put_row_DITHER_ximage; - xrb->Base.PutRowRGB = put_row_rgb_DITHER_ximage; - xrb->Base.PutMonoRow = put_mono_row_DITHER_ximage; - xrb->Base.PutValues = put_values_DITHER_ximage; - xrb->Base.PutMonoValues = put_mono_values_DITHER_ximage; + rb->PutRow = put_row_DITHER_ximage; + rb->PutRowRGB = put_row_rgb_DITHER_ximage; + rb->PutMonoRow = put_mono_row_DITHER_ximage; + rb->PutValues = put_values_DITHER_ximage; + rb->PutMonoValues = put_mono_values_DITHER_ximage; } } break; case PF_1Bit: if (pixmap) { - xrb->Base.PutRow = put_row_1BIT_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_1BIT_pixmap; - xrb->Base.PutMonoRow = put_mono_row_1BIT_pixmap; - xrb->Base.PutValues = put_values_1BIT_pixmap; - xrb->Base.PutMonoValues = put_mono_values_1BIT_pixmap; + rb->PutRow = put_row_1BIT_pixmap; + rb->PutRowRGB = put_row_rgb_1BIT_pixmap; + rb->PutMonoRow = put_mono_row_1BIT_pixmap; + rb->PutValues = put_values_1BIT_pixmap; + rb->PutMonoValues = put_mono_values_1BIT_pixmap; } else { - xrb->Base.PutRow = put_row_1BIT_ximage; - xrb->Base.PutRowRGB = put_row_rgb_1BIT_ximage; - xrb->Base.PutMonoRow = put_mono_row_1BIT_ximage; - xrb->Base.PutValues = put_values_1BIT_ximage; - xrb->Base.PutMonoValues = put_mono_values_1BIT_ximage; + rb->PutRow = put_row_1BIT_ximage; + rb->PutRowRGB = put_row_rgb_1BIT_ximage; + rb->PutMonoRow = put_mono_row_1BIT_ximage; + rb->PutValues = put_values_1BIT_ximage; + rb->PutMonoValues = put_mono_values_1BIT_ximage; } break; case PF_HPCR: if (pixmap) { - xrb->Base.PutRow = put_row_HPCR_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_HPCR_pixmap; - xrb->Base.PutMonoRow = put_mono_row_pixmap; - xrb->Base.PutValues = put_values_HPCR_pixmap; - xrb->Base.PutMonoValues = put_mono_values_pixmap; + rb->PutRow = put_row_HPCR_pixmap; + rb->PutRowRGB = put_row_rgb_HPCR_pixmap; + rb->PutMonoRow = put_mono_row_pixmap; + rb->PutValues = put_values_HPCR_pixmap; + rb->PutMonoValues = put_mono_values_pixmap; } else { - xrb->Base.PutRow = put_row_HPCR_ximage; - xrb->Base.PutRowRGB = put_row_rgb_HPCR_ximage; - xrb->Base.PutMonoRow = put_mono_row_HPCR_ximage; - xrb->Base.PutValues = put_values_HPCR_ximage; - xrb->Base.PutMonoValues = put_mono_values_HPCR_ximage; + rb->PutRow = put_row_HPCR_ximage; + rb->PutRowRGB = put_row_rgb_HPCR_ximage; + rb->PutMonoRow = put_mono_row_HPCR_ximage; + rb->PutValues = put_values_HPCR_ximage; + rb->PutMonoValues = put_mono_values_HPCR_ximage; } break; case PF_Lookup: if (pixmap) { - xrb->Base.PutRow = put_row_LOOKUP_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_LOOKUP_pixmap; - xrb->Base.PutMonoRow = put_mono_row_pixmap; - xrb->Base.PutValues = put_values_LOOKUP_pixmap; - xrb->Base.PutMonoValues = put_mono_values_pixmap; + rb->PutRow = put_row_LOOKUP_pixmap; + rb->PutRowRGB = put_row_rgb_LOOKUP_pixmap; + rb->PutMonoRow = put_mono_row_pixmap; + rb->PutValues = put_values_LOOKUP_pixmap; + rb->PutMonoValues = put_mono_values_pixmap; } else { if (depth==8) { - xrb->Base.PutRow = put_row_LOOKUP8_ximage; - xrb->Base.PutRowRGB = put_row_rgb_LOOKUP8_ximage; - xrb->Base.PutMonoRow = put_mono_row_LOOKUP8_ximage; - xrb->Base.PutValues = put_values_LOOKUP8_ximage; - xrb->Base.PutMonoValues = put_mono_values_LOOKUP8_ximage; + rb->PutRow = put_row_LOOKUP8_ximage; + rb->PutRowRGB = put_row_rgb_LOOKUP8_ximage; + rb->PutMonoRow = put_mono_row_LOOKUP8_ximage; + rb->PutValues = put_values_LOOKUP8_ximage; + rb->PutMonoValues = put_mono_values_LOOKUP8_ximage; } else { - xrb->Base.PutRow = put_row_LOOKUP_ximage; - xrb->Base.PutRowRGB = put_row_rgb_LOOKUP_ximage; - xrb->Base.PutMonoRow = put_mono_row_ximage; - xrb->Base.PutValues = put_values_LOOKUP_ximage; - xrb->Base.PutMonoValues = put_mono_values_ximage; + rb->PutRow = put_row_LOOKUP_ximage; + rb->PutRowRGB = put_row_rgb_LOOKUP_ximage; + rb->PutMonoRow = put_mono_row_ximage; + rb->PutValues = put_values_LOOKUP_ximage; + rb->PutMonoValues = put_mono_values_ximage; } } break; case PF_Grayscale: if (pixmap) { - xrb->Base.PutRow = put_row_GRAYSCALE_pixmap; - xrb->Base.PutRowRGB = put_row_rgb_GRAYSCALE_pixmap; - xrb->Base.PutMonoRow = put_mono_row_pixmap; - xrb->Base.PutValues = put_values_GRAYSCALE_pixmap; - xrb->Base.PutMonoValues = put_mono_values_pixmap; + rb->PutRow = put_row_GRAYSCALE_pixmap; + rb->PutRowRGB = put_row_rgb_GRAYSCALE_pixmap; + rb->PutMonoRow = put_mono_row_pixmap; + rb->PutValues = put_values_GRAYSCALE_pixmap; + rb->PutMonoValues = put_mono_values_pixmap; } else { if (depth == 8) { - xrb->Base.PutRow = put_row_GRAYSCALE8_ximage; - xrb->Base.PutRowRGB = put_row_rgb_GRAYSCALE8_ximage; - xrb->Base.PutMonoRow = put_mono_row_GRAYSCALE8_ximage; - xrb->Base.PutValues = put_values_GRAYSCALE8_ximage; - xrb->Base.PutMonoValues = put_mono_values_GRAYSCALE8_ximage; + rb->PutRow = put_row_GRAYSCALE8_ximage; + rb->PutRowRGB = put_row_rgb_GRAYSCALE8_ximage; + rb->PutMonoRow = put_mono_row_GRAYSCALE8_ximage; + rb->PutValues = put_values_GRAYSCALE8_ximage; + rb->PutMonoValues = put_mono_values_GRAYSCALE8_ximage; } else { - xrb->Base.PutRow = put_row_GRAYSCALE_ximage; - xrb->Base.PutRowRGB = put_row_rgb_GRAYSCALE_ximage; - xrb->Base.PutMonoRow = put_mono_row_ximage; - xrb->Base.PutValues = put_values_GRAYSCALE_ximage; - xrb->Base.PutMonoValues = put_mono_values_ximage; + rb->PutRow = put_row_GRAYSCALE_ximage; + rb->PutRowRGB = put_row_rgb_GRAYSCALE_ximage; + rb->PutMonoRow = put_mono_row_ximage; + rb->PutValues = put_values_GRAYSCALE_ximage; + rb->PutMonoValues = put_mono_values_ximage; } } break; @@ -4790,12 +4804,12 @@ xmesa_set_renderbuffer_funcs(struct xmesa_renderbuffer *xrb, /* Get functions */ if (pixelformat == PF_Index) { - xrb->Base.GetRow = get_row_ci; - xrb->Base.GetValues = get_values_ci; + rb->GetRow = get_row_ci; + rb->GetValues = get_values_ci; } else { - xrb->Base.GetRow = get_row_rgba; - xrb->Base.GetValues = get_values_rgba; + rb->GetRow = get_row_rgba; + rb->GetValues = get_values_rgba; } } diff --git a/src/mesa/drivers/x11/xm_surface.c b/src/mesa/drivers/x11/xm_surface.c new file mode 100644 index 00000000000..a3f2fe7d685 --- /dev/null +++ b/src/mesa/drivers/x11/xm_surface.c @@ -0,0 +1,251 @@ +/* + * Mesa 3-D graphics library + * Version: 7.1 + * + * Copyright (C) 1999-2007 Brian Paul All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN + * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + */ + + +/** + * \file xm_surface.c + * Code to allow the softpipe code to write to X windows/buffers. + * This is a bit of a hack for now. We've basically got two different + * abstractions for color buffers: gl_renderbuffer and pipe_surface. + * They'll need to get merged someday... + * For now, they're separate things that point to each other. + */ + + +#include "glxheader.h" +#include "GL/xmesa.h" +#include "xmesaP.h" +#include "context.h" +#include "imports.h" +#include "macros.h" +#include "framebuffer.h" +#include "renderbuffer.h" + +#include "pipe/p_context.h" +#include "pipe/p_defines.h" +#include "pipe/p_winsys.h" +#include "softpipe/sp_context.h" +#include "softpipe/sp_clear.h" +#include "softpipe/sp_tile_cache.h" +#include "softpipe/sp_surface.h" +#include "state_tracker/st_context.h" + + +#define CLIP_TILE \ + do { \ + if (x + w > ps->width) \ + w = ps->width - x; \ + if (y + h > ps->height) \ + h = ps->height -y; \ + } while(0) + + +static INLINE struct xmesa_surface * +xmesa_surface(struct pipe_surface *ps) +{ + return (struct xmesa_surface *) ps; +} + + +static INLINE struct xmesa_renderbuffer * +xmesa_rb(struct pipe_surface *ps) +{ + struct xmesa_surface *xms = xmesa_surface(ps); + return xms->xrb; +} + + +#define FLIP(Y) Y = xrb->St.Base.Height - (Y) - 1; + + +void +xmesa_get_tile_rgba(struct pipe_context *pipe, struct pipe_surface *ps, + uint x, uint y, uint w, uint h, float *p) +{ + struct xmesa_surface *xms = xmesa_surface(ps); + struct xmesa_renderbuffer *xrb = xms->xrb; + + if (xrb) { + /* this is a front/back color buffer */ + GLubyte tmp[MAX_WIDTH * 4]; + GLuint i, j; + uint w0 = w; + GET_CURRENT_CONTEXT(ctx); + + CLIP_TILE; + + FLIP(y); + for (i = 0; i < h; i++) { + xrb->St.Base.GetRow(ctx, &xrb->St.Base, w, x, y - i, tmp); + for (j = 0; j < w * 4; j++) { + p[j] = UBYTE_TO_FLOAT(tmp[j]); + } + p += w0 * 4; + } + } + else { + /* other softpipe surface */ + softpipe_get_tile_rgba(ps, x, y, w, h, p); + } +} + + +void +xmesa_put_tile_rgba(struct pipe_context *pipe, struct pipe_surface *ps, + uint x, uint y, uint w, uint h, const float *p) +{ + struct xmesa_surface *xms = xmesa_surface(ps); + struct xmesa_renderbuffer *xrb = xms->xrb; + + if (xrb) { + /* this is a front/back color buffer */ + GLubyte tmp[MAX_WIDTH * 4]; + GLuint i, j; + uint w0 = w; + GET_CURRENT_CONTEXT(ctx); + CLIP_TILE; + FLIP(y); + for (i = 0; i < h; i++) { + for (j = 0; j < w * 4; j++) { + UNCLAMPED_FLOAT_TO_UBYTE(tmp[j], p[j]); + } + xrb->St.Base.PutRow(ctx, &xrb->St.Base, w, x, y - i, tmp, NULL); + p += w0 * 4; + } +#if 0 /* debug: flush */ + { + XMesaContext xm = XMESA_CONTEXT(ctx); + XSync(xm->display, 0); + } +#endif + } + else { + /* other softpipe surface */ + softpipe_put_tile_rgba(ps, x, y, w, h, p); + } +} + + + +/** + * Called to create a pipe_surface for each X renderbuffer. + * Note: this is being used instead of pipe->surface_alloc() since we + * have special/unique quad read/write functions for X. + */ +struct pipe_surface * +xmesa_new_color_surface(struct pipe_context *pipe, GLuint pipeFormat) +{ + struct xmesa_surface *xms = CALLOC_STRUCT(xmesa_surface); + + assert(pipeFormat); + + xms->surface.format = pipeFormat; + xms->surface.refcount = 1; + + /* Note, the region we allocate doesn't actually have any storage + * since we're drawing into an XImage or Pixmap. + * The region's size will get set in the xmesa_alloc_front/back_storage() + * functions. + */ + if (pipe) + xms->surface.region = pipe->winsys->region_alloc(pipe->winsys, + 1, 0, 0, 0x0); + + return &xms->surface; +} + + +/** + * Called via pipe->surface_alloc() to create new surfaces (textures, + * renderbuffers, etc. + */ +struct pipe_surface * +xmesa_surface_alloc(struct pipe_context *pipe, GLuint pipeFormat) +{ + struct xmesa_surface *xms = CALLOC_STRUCT(xmesa_surface); + + assert(pipe); + assert(pipeFormat); + + xms->surface.format = pipeFormat; + xms->surface.refcount = 1; + + return &xms->surface; +} + + +boolean +xmesa_is_format_supported(struct pipe_context *pipe, uint format) +{ + switch( format ) { + case PIPE_FORMAT_U_A8_R8_G8_B8: + case PIPE_FORMAT_S_R16_G16_B16_A16: + case PIPE_FORMAT_S8_Z24: + return TRUE; + }; + return FALSE; +} + + +/** + * Called via pipe->clear() + */ +void +xmesa_clear(struct pipe_context *pipe, struct pipe_surface *ps, GLuint value) +{ + struct xmesa_renderbuffer *xrb = xmesa_rb(ps); + + /* XXX actually, we should just discard any cached tiles from this + * surface since we don't want to accidentally re-use them after clearing. + */ + pipe->flush(pipe, 0); + + { + struct softpipe_context *sp = softpipe_context(pipe); + if (ps == sp_tile_cache_get_surface(sp->cbuf_cache[0])) { + float clear[4]; + clear[0] = 0.2; /* XXX hack */ + clear[1] = 0.2; + clear[2] = 0.2; + clear[3] = 0.2; + sp_tile_cache_clear(sp->cbuf_cache[0], clear); + } + } + + if (xrb && xrb->ximage) { + /* clearing back color buffer */ + GET_CURRENT_CONTEXT(ctx); + xmesa_clear_buffers(ctx, BUFFER_BIT_BACK_LEFT); + } + else if (xrb && xrb->pixmap) { + /* clearing front color buffer */ + GET_CURRENT_CONTEXT(ctx); + xmesa_clear_buffers(ctx, BUFFER_BIT_FRONT_LEFT); + } + else { + /* clearing other buffer */ + softpipe_clear(pipe, ps, value); + } +} + diff --git a/src/mesa/drivers/x11/xm_tri.c b/src/mesa/drivers/x11/xm_tri.c index 77fceec194c..158f284a5e2 100644 --- a/src/mesa/drivers/x11/xm_tri.c +++ b/src/mesa/drivers/x11/xm_tri.c @@ -1443,6 +1443,46 @@ do { \ #endif +#if 0 +GLboolean xmesa_get_cbuf_details( GLcontext *ctx, + void **ptr, + GLuint *cpp, + GLint *stride, + GLuint *format ) +{ + XMesaContext xmesa = XMESA_CONTEXT(ctx); + struct gl_framebuffer *fb = ctx->DrawBuffer; + struct gl_renderbuffer *crb = fb->_ColorDrawBuffers[0][0]; + struct xmesa_renderbuffer *xrb = xmesa_renderbuffer(crb->Wrapped); + + *ptr = crb->GetPointer(ctx, crb, 0, 0); + *stride = ((GLubyte *)crb->GetPointer(ctx, crb, 0, 1) - + (GLubyte *)crb->GetPointer(ctx, crb, 0, 0)); + + if (!ptr) + goto bad; + + switch (xmesa->pixelformat) { + case PF_8A8B8G8R: + case PF_8A8R8G8B: + *format = 1; /* whatever */ + *cpp = 4; + break; + default: + goto bad; + } + + return GL_TRUE; + + bad: + *ptr = NULL; + *stride = 0; + *format = 0; + return GL_FALSE; +} +#endif + + /** * Return pointer to line drawing function, or NULL if we should use a * swrast fallback. diff --git a/src/mesa/drivers/x11/xm_winsys.c b/src/mesa/drivers/x11/xm_winsys.c new file mode 100644 index 00000000000..eab9fd38521 --- /dev/null +++ b/src/mesa/drivers/x11/xm_winsys.c @@ -0,0 +1,362 @@ +/************************************************************************** + * + * Copyright 2007 Tungsten Graphics, Inc., Bismarck, ND., USA + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sub license, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDERS, AUTHORS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, + * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR + * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE + * USE OR OTHER DEALINGS IN THE SOFTWARE. + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial portions + * of the Software. + * + * + **************************************************************************/ + +/* + * Authors: + * Keith Whitwell + * Brian Paul + */ + + +#include "glxheader.h" +#include "xmesaP.h" +#include "main/macros.h" + +#include "pipe/p_winsys.h" +#include "softpipe/sp_winsys.h" + + +/** + * XMesa winsys, derived from softpipe winsys. + * NOTE: there's nothing really X-specific in this winsys layer so + * we could probably lift it up somewhere. + */ +struct xm_winsys +{ + struct softpipe_winsys sws; + int foo; /* placeholder */ +}; + + +/** + * Low-level OS/window system memory buffer + */ +struct xm_buffer +{ + boolean userBuffer; /** Is this a user-space buffer? */ + int refcount; + unsigned size; + void *data; + void *mapped; +}; + + + +/* Turn the softpipe opaque buffer pointer into a dri_bufmgr opaque + * buffer pointer... + */ +static inline struct xm_buffer * +xm_bo( struct pipe_buffer *bo ) +{ + return (struct xm_buffer *) bo; +} + +static inline struct pipe_buffer * +pipe_bo( struct xm_buffer *bo ) +{ + return (struct pipe_buffer *) bo; +} + +/* Turn a softpipe winsys into an xm/softpipe winsys: + */ +static inline struct xm_winsys * +xm_winsys(struct softpipe_winsys *sws) +{ + return (struct xm_winsys *) sws; +} + + +/* Most callbacks map direcly onto dri_bufmgr operations: + */ +static void * +xm_buffer_map(struct pipe_winsys *pws, struct pipe_buffer *buf, + unsigned flags) +{ + struct xm_buffer *xm_buf = xm_bo(buf); + xm_buf->mapped = xm_buf->data; + return xm_buf->mapped; +} + +static void +xm_buffer_unmap(struct pipe_winsys *pws, struct pipe_buffer *buf) +{ + struct xm_buffer *xm_buf = xm_bo(buf); + xm_buf->mapped = NULL; +} + +static void +xm_buffer_reference(struct pipe_winsys *pws, + struct pipe_buffer **ptr, + struct pipe_buffer *buf) +{ + if (*ptr) { + struct xm_buffer *oldBuf = xm_bo(*ptr); + oldBuf->refcount--; + assert(oldBuf->refcount >= 0); + if (oldBuf->refcount == 0) { + if (oldBuf->data) { + if (!oldBuf->userBuffer) + free(oldBuf->data); + oldBuf->data = NULL; + } + free(oldBuf); + } + *ptr = NULL; + } + + assert(!(*ptr)); + + if (buf) { + struct xm_buffer *newBuf = xm_bo(buf); + newBuf->refcount++; + *ptr = buf; + } +} + +static void +xm_buffer_data(struct pipe_winsys *pws, struct pipe_buffer *buf, + unsigned size, const void *data, unsigned usage) +{ + struct xm_buffer *xm_buf = xm_bo(buf); + assert(!xm_buf->userBuffer); + if (xm_buf->size != size) { + if (xm_buf->data) + free(xm_buf->data); + xm_buf->data = malloc(size); + xm_buf->size = size; + } + if (data) + memcpy(xm_buf->data, data, size); +} + +static void +xm_buffer_subdata(struct pipe_winsys *pws, struct pipe_buffer *buf, + unsigned long offset, unsigned long size, const void *data) +{ + struct xm_buffer *xm_buf = xm_bo(buf); + GLubyte *b = (GLubyte *) xm_buf->data; + assert(!xm_buf->userBuffer); + assert(b); + memcpy(b + offset, data, size); +} + +static void +xm_buffer_get_subdata(struct pipe_winsys *pws, struct pipe_buffer *buf, + unsigned long offset, unsigned long size, void *data) +{ + const struct xm_buffer *xm_buf = xm_bo(buf); + const GLubyte *b = (GLubyte *) xm_buf->data; + assert(!xm_buf->userBuffer); + assert(b); + memcpy(data, b + offset, size); +} + +static void +xm_flush_frontbuffer(struct pipe_winsys *pws) +{ + /* + struct intel_context *intel = intel_pipe_winsys(sws)->intel; + __DRIdrawablePrivate *dPriv = intel->driDrawable; + + intelCopyBuffer(dPriv, NULL); + */ +} + +static void +xm_wait_idle(struct pipe_winsys *pws) +{ + /* no-op */ +} + +static const char * +xm_get_name(struct pipe_winsys *pws) +{ + return "Xlib"; +} + + +static struct pipe_buffer * +xm_buffer_create(struct pipe_winsys *pws, + unsigned alignment, + unsigned flags, + unsigned hint) +{ + struct xm_buffer *buffer = CALLOC_STRUCT(xm_buffer); + buffer->refcount = 1; + return pipe_bo(buffer); +} + + +/** + * Create buffer which wraps user-space data. + */ +static struct pipe_buffer * +xm_user_buffer_create(struct pipe_winsys *pws, void *ptr, unsigned bytes) +{ + struct xm_buffer *buffer = CALLOC_STRUCT(xm_buffer); + buffer->userBuffer = TRUE; + buffer->refcount = 1; + buffer->data = ptr; + buffer->size = bytes; + return pipe_bo(buffer); +} + + + +/** + * Round n up to next multiple. + */ +static INLINE unsigned +round_up(unsigned n, unsigned multiple) +{ + return (n + multiple - 1) & ~(multiple - 1); +} + + +static struct pipe_region * +xm_region_alloc(struct pipe_winsys *winsys, + unsigned cpp, unsigned width, unsigned height, unsigned flags) +{ + struct pipe_region *region = CALLOC_STRUCT(pipe_region); + const unsigned alignment = 64; + + region->cpp = cpp; + region->pitch = round_up(width, alignment / cpp); + region->height = height; + region->refcount = 1; + + assert(region->pitch > 0); + + region->buffer = winsys->buffer_create( winsys, alignment, 0, 0 ) +; + + /* NULL data --> just allocate the space */ + winsys->buffer_data( winsys, + region->buffer, + region->pitch * cpp * height, + NULL, + PIPE_BUFFER_USAGE_PIXEL ); + return region; +} + + +static void +xm_region_release(struct pipe_winsys *winsys, struct pipe_region **region) +{ + if (!*region) + return; + + assert((*region)->refcount > 0); + (*region)->refcount--; + + if ((*region)->refcount == 0) { + assert((*region)->map_refcount == 0); + + winsys->buffer_reference( winsys, &((*region)->buffer), NULL ); + free(*region); + } + *region = NULL; +} + + +/** + * Called via pipe->surface_alloc() to create new surfaces (textures, + * renderbuffers, etc. + */ +static struct pipe_surface * +xm_surface_alloc(struct pipe_winsys *ws, GLuint pipeFormat) +{ + struct xmesa_surface *xms = CALLOC_STRUCT(xmesa_surface); + + assert(ws); + assert(pipeFormat); + + xms->surface.format = pipeFormat; + xms->surface.refcount = 1; +#if 0 + /* + * This is really just a softpipe surface, not an XImage/Pixmap surface. + */ + softpipe_init_surface_funcs(&xms->surface); +#endif + return &xms->surface; +} + + + + +struct xmesa_pipe_winsys +{ + struct pipe_winsys winsys; + XMesaContext xmesa; +}; + +static struct pipe_winsys * +xmesa_create_pipe_winsys( XMesaContext xmesa ) +{ + struct xmesa_pipe_winsys *xws = CALLOC_STRUCT(xmesa_pipe_winsys); + + /* Fill in this struct with callbacks that pipe will need to + * communicate with the window system, buffer manager, etc. + * + * Pipe would be happy with a malloc based memory manager, but + * the SwapBuffers implementation in this winsys driver requires + * that rendering be done to an appropriate _DriBufferObject. + */ + xws->winsys.buffer_create = xm_buffer_create; + xws->winsys.user_buffer_create = xm_user_buffer_create; + xws->winsys.buffer_map = xm_buffer_map; + xws->winsys.buffer_unmap = xm_buffer_unmap; + xws->winsys.buffer_reference = xm_buffer_reference; + xws->winsys.buffer_data = xm_buffer_data; + xws->winsys.buffer_subdata = xm_buffer_subdata; + xws->winsys.buffer_get_subdata = xm_buffer_get_subdata; + + xws->winsys.region_alloc = xm_region_alloc; + xws->winsys.region_release = xm_region_release; + + xws->winsys.surface_alloc = xm_surface_alloc; + + xws->winsys.flush_frontbuffer = xm_flush_frontbuffer; + xws->winsys.wait_idle = xm_wait_idle; + xws->winsys.get_name = xm_get_name; + xws->xmesa = xmesa; + + return &xws->winsys; +} + + +struct pipe_context * +xmesa_create_softpipe(XMesaContext xmesa) +{ + struct xm_winsys *xm_ws = CALLOC_STRUCT( xm_winsys ); + + /* Create the softpipe context: + */ + return softpipe_create( xmesa_create_pipe_winsys(xmesa), &xm_ws->sws ); +} diff --git a/src/mesa/drivers/x11/xmesaP.h b/src/mesa/drivers/x11/xmesaP.h index 95c41c3a41e..e0e69274d40 100644 --- a/src/mesa/drivers/x11/xmesaP.h +++ b/src/mesa/drivers/x11/xmesaP.h @@ -36,6 +36,9 @@ #ifdef XFree86Server #include "xm_image.h" #endif +#include "state_tracker/st_cb_fbo.h" +#include "softpipe/sp_context.h" +#include "softpipe/sp_surface.h" extern _glthread_Mutex _xmesa_lock; @@ -177,7 +180,11 @@ typedef enum { */ struct xmesa_renderbuffer { +#if 0 struct gl_renderbuffer Base; /* Base class */ +#else + struct st_renderbuffer St; /**< Base class */ +#endif XMesaBuffer Parent; /**< The XMesaBuffer this renderbuffer belongs to */ XMesaDrawable drawable; /* Usually the X window ID */ @@ -196,6 +203,8 @@ struct xmesa_renderbuffer GLint bottom; /* used for FLIP macro, equals height - 1 */ ClearFunc clearFunc; + + void *pSurface; /** pipe surface */ }; @@ -491,8 +500,8 @@ extern const int xmesa_kernel1[16]; */ extern struct xmesa_renderbuffer * -xmesa_new_renderbuffer(GLcontext *ctx, GLuint name, const GLvisual *visual, - GLboolean backBuffer); +xmesa_create_renderbuffer(GLcontext *ctx, GLuint name, const GLvisual *visual, + GLboolean backBuffer); extern void xmesa_delete_framebuffer(struct gl_framebuffer *fb); @@ -581,4 +590,41 @@ extern void xmesa_register_swrast_functions( GLcontext *ctx ); #define ENABLE_EXT_timer_query 0 /* may not have 64-bit GLuint64EXT */ #endif + +struct pipe_surface; +struct pipe_context; + +struct xmesa_surface +{ + struct pipe_surface surface; + struct xmesa_renderbuffer *xrb; +}; + + +extern void +xmesa_clear(struct pipe_context *pipe, struct pipe_surface *ps, GLuint value); + +extern void +xmesa_clear_buffers(GLcontext *ctx, GLbitfield buffers); + +extern struct pipe_context * +xmesa_create_softpipe(XMesaContext xm); + +extern struct pipe_surface * +xmesa_surface_alloc(struct pipe_context *pipe, GLuint format); + +extern struct pipe_surface * +xmesa_new_color_surface(struct pipe_context *pipe, GLuint format); + +extern boolean +xmesa_is_format_supported(struct pipe_context *pipe, uint format); + +extern void +xmesa_get_tile_rgba(struct pipe_context *pipe, struct pipe_surface *ps, + uint x, uint y, uint w, uint h, float *p); + +extern void +xmesa_put_tile_rgba(struct pipe_context *pipe, struct pipe_surface *ps, + uint x, uint y, uint w, uint h, const float *p); + #endif |