Ejemplo n.º 1
0
static
void
sw_init_renderbuffers(struct sw_framebuffer *fb)
{
    _mesa_init_renderbuffer(&fb->frontbuffer.swrast.Base, 0);
    fb->frontbuffer.swrast.Base.ClassID = SW_FRONT_RENDERBUFFER_CLASS;
    fb->frontbuffer.swrast.Base.AllocStorage = sw_fb_renderbuffer_storage;
    fb->frontbuffer.swrast.Base.Delete = sw_fb_renderbuffer_delete;
    fb->frontbuffer.swrast.Base.InternalFormat = GL_RGBA;
    fb->frontbuffer.swrast.Base._BaseFormat = GL_RGBA;
    _mesa_remove_renderbuffer(fb->gl_buffer, BUFFER_FRONT_LEFT);
    _mesa_add_renderbuffer(fb->gl_buffer, BUFFER_FRONT_LEFT, &fb->frontbuffer.swrast.Base);
    
    if(fb->flags & SW_FB_DOUBLEBUFFERED)
    {
        _mesa_init_renderbuffer(&fb->backbuffer.Base, 0);
        fb->backbuffer.Base.ClassID = SW_BACK_RENDERBUFFER_CLASS;
        fb->backbuffer.Base.AllocStorage = sw_bb_renderbuffer_storage;
        fb->backbuffer.Base.Delete = sw_bb_renderbuffer_delete;
        fb->backbuffer.Base.InternalFormat = GL_RGBA;
        fb->backbuffer.Base._BaseFormat = GL_RGBA;
        _mesa_remove_renderbuffer(fb->gl_buffer, BUFFER_BACK_LEFT);
        _mesa_add_renderbuffer(fb->gl_buffer, BUFFER_BACK_LEFT, &fb->backbuffer.Base);
    }
    
    
}
Ejemplo n.º 2
0
static GLboolean
dri_create_buffer(__DRIscreen * sPriv,
		  __DRIdrawable * dPriv,
		  const struct gl_config * visual, GLboolean isPixmap)
{
    struct dri_drawable *drawable = NULL;
    struct gl_framebuffer *fb;
    struct dri_swrast_renderbuffer *frontrb, *backrb;

    TRACE;

    (void) sPriv;
    (void) isPixmap;

    drawable = CALLOC_STRUCT(dri_drawable);
    if (drawable == NULL)
	goto drawable_fail;

    dPriv->driverPrivate = drawable;
    drawable->dPriv = dPriv;

    drawable->row = malloc(SWRAST_MAX_WIDTH * 4);
    if (drawable->row == NULL)
	goto drawable_fail;

    fb = &drawable->Base;

    /* basic framebuffer setup */
    _mesa_initialize_window_framebuffer(fb, visual);

    /* add front renderbuffer */
    frontrb = swrast_new_renderbuffer(visual, dPriv, GL_TRUE);
    _mesa_add_renderbuffer(fb, BUFFER_FRONT_LEFT, &frontrb->Base.Base);

    /* add back renderbuffer */
    if (visual->doubleBufferMode) {
	backrb = swrast_new_renderbuffer(visual, dPriv, GL_FALSE);
	_mesa_add_renderbuffer(fb, BUFFER_BACK_LEFT, &backrb->Base.Base);
    }

    /* add software renderbuffers */
    _swrast_add_soft_renderbuffers(fb,
                                   GL_FALSE, /* color */
                                   visual->haveDepthBuffer,
                                   visual->haveStencilBuffer,
                                   visual->haveAccumBuffer,
                                   GL_FALSE, /* alpha */
                                   GL_FALSE /* aux bufs */);

    return GL_TRUE;

drawable_fail:

    if (drawable)
	free(drawable->row);

    free(drawable);

    return GL_FALSE;
}
Ejemplo n.º 3
0
/**
 * Add a renderbuffer to the framebuffer.
 */
static boolean
st_framebuffer_add_renderbuffer(struct st_framebuffer *stfb,
                                gl_buffer_index idx)
{
   struct gl_renderbuffer *rb;
   enum pipe_format format;
   int samples;
   boolean sw;

   if (!stfb->iface)
      return FALSE;

   /* do not distinguish depth/stencil buffers */
   if (idx == BUFFER_STENCIL)
      idx = BUFFER_DEPTH;

   switch (idx) {
   case BUFFER_DEPTH:
      format = stfb->iface->visual->depth_stencil_format;
      sw = FALSE;
      break;
   case BUFFER_ACCUM:
      format = stfb->iface->visual->accum_format;
      sw = TRUE;
      break;
   default:
      format = stfb->iface->visual->color_format;
      sw = FALSE;
      break;
   }

   if (format == PIPE_FORMAT_NONE)
      return FALSE;

   samples = stfb->iface->visual->samples;
   if (!samples)
      samples = st_get_msaa();

   rb = st_new_renderbuffer_fb(format, samples, sw);
   if (!rb)
      return FALSE;

   if (idx != BUFFER_DEPTH) {
      _mesa_add_renderbuffer(&stfb->Base, idx, rb);
   }
   else {
      if (util_format_get_component_bits(format, UTIL_FORMAT_COLORSPACE_ZS, 0))
         _mesa_add_renderbuffer(&stfb->Base, BUFFER_DEPTH, rb);
      if (util_format_get_component_bits(format, UTIL_FORMAT_COLORSPACE_ZS, 1))
         _mesa_add_renderbuffer(&stfb->Base, BUFFER_STENCIL, rb);
   }

   return TRUE;
}
Ejemplo n.º 4
0
/**
 * Add a software-based aux renderbuffer to the given framebuffer.
 * This is a helper routine for device drivers when creating a
 * window system framebuffer (not a user-created render/framebuffer).
 * Once this function is called, you can basically forget about this
 * renderbuffer; core Mesa will handle all the buffer management and
 * rendering!
 *
 * NOTE: color-index aux buffers not supported.
 */
static GLboolean
add_aux_renderbuffers(struct gl_context *ctx, struct gl_framebuffer *fb,
                      GLuint colorBits, GLuint numBuffers)
{
   GLuint i;

   if (colorBits > 16) {
      _mesa_problem(ctx,
                    "Unsupported colorBits in add_aux_renderbuffers");
      return GL_FALSE;
   }

   assert(numBuffers <= MAX_AUX_BUFFERS);

   for (i = 0; i < numBuffers; i++) {
      struct gl_renderbuffer *rb = _swrast_new_soft_renderbuffer(ctx, 0);

      assert(fb->Attachment[BUFFER_AUX0 + i].Renderbuffer == NULL);

      if (!rb) {
         _mesa_error(ctx, GL_OUT_OF_MEMORY, "Allocating aux buffer");
         return GL_FALSE;
      }

      assert (colorBits <= 8);
      rb->InternalFormat = GL_RGBA;

      rb->AllocStorage = soft_renderbuffer_storage;
      _mesa_add_renderbuffer(fb, BUFFER_AUX0 + i, rb);
   }
   return GL_TRUE;
}
Ejemplo n.º 5
0
/**
 * Add a software-based stencil renderbuffer to the given framebuffer.
 * This is a helper routine for device drivers when creating a
 * window system framebuffer (not a user-created render/framebuffer).
 * Once this function is called, you can basically forget about this
 * renderbuffer; core Mesa will handle all the buffer management and
 * rendering!
 */
static GLboolean
add_stencil_renderbuffer(struct gl_context *ctx, struct gl_framebuffer *fb,
                         GLuint stencilBits)
{
   struct gl_renderbuffer *rb;

   if (stencilBits > 16) {
      _mesa_problem(ctx,
                  "Unsupported stencilBits in add_stencil_renderbuffer");
      return GL_FALSE;
   }

   assert(fb->Attachment[BUFFER_STENCIL].Renderbuffer == NULL);

   rb = _swrast_new_soft_renderbuffer(ctx, 0);
   if (!rb) {
      _mesa_error(ctx, GL_OUT_OF_MEMORY, "Allocating stencil buffer");
      return GL_FALSE;
   }

   assert(stencilBits <= 8);
   rb->InternalFormat = GL_STENCIL_INDEX8;

   rb->AllocStorage = soft_renderbuffer_storage;
   _mesa_add_renderbuffer(fb, BUFFER_STENCIL, rb);

   return GL_TRUE;
}
Ejemplo n.º 6
0
/**
 * Add a software-based accumulation renderbuffer to the given framebuffer.
 * This is a helper routine for device drivers when creating a
 * window system framebuffer (not a user-created render/framebuffer).
 * Once this function is called, you can basically forget about this
 * renderbuffer; core Mesa will handle all the buffer management and
 * rendering!
 */
static GLboolean
add_accum_renderbuffer(struct gl_context *ctx, struct gl_framebuffer *fb,
                       GLuint redBits, GLuint greenBits,
                       GLuint blueBits, GLuint alphaBits)
{
   struct gl_renderbuffer *rb;

   if (redBits > 16 || greenBits > 16 || blueBits > 16 || alphaBits > 16) {
      _mesa_problem(ctx,
                    "Unsupported accumBits in add_accum_renderbuffer");
      return GL_FALSE;
   }

   assert(fb->Attachment[BUFFER_ACCUM].Renderbuffer == NULL);

   rb = _swrast_new_soft_renderbuffer(ctx, 0);
   if (!rb) {
      _mesa_error(ctx, GL_OUT_OF_MEMORY, "Allocating accum buffer");
      return GL_FALSE;
   }

   rb->InternalFormat = GL_RGBA16_SNORM;
   rb->AllocStorage = soft_renderbuffer_storage;
   _mesa_add_renderbuffer(fb, BUFFER_ACCUM, rb);

   return GL_TRUE;
}
Ejemplo n.º 7
0
/**
 * Add a software-based depth renderbuffer to the given framebuffer.
 * This is a helper routine for device drivers when creating a
 * window system framebuffer (not a user-created render/framebuffer).
 * Once this function is called, you can basically forget about this
 * renderbuffer; core Mesa will handle all the buffer management and
 * rendering!
 */
static GLboolean
add_depth_renderbuffer(struct gl_context *ctx, struct gl_framebuffer *fb,
                       GLuint depthBits)
{
   struct gl_renderbuffer *rb;

   if (depthBits > 32) {
      _mesa_problem(ctx,
                    "Unsupported depthBits in add_depth_renderbuffer");
      return GL_FALSE;
   }

   assert(fb->Attachment[BUFFER_DEPTH].Renderbuffer == NULL);

   rb = _swrast_new_soft_renderbuffer(ctx, 0);
   if (!rb) {
      _mesa_error(ctx, GL_OUT_OF_MEMORY, "Allocating depth buffer");
      return GL_FALSE;
   }

   if (depthBits <= 16) {
      rb->InternalFormat = GL_DEPTH_COMPONENT16;
   }
   else if (depthBits <= 24) {
      rb->InternalFormat = GL_DEPTH_COMPONENT24;
   }
   else {
      rb->InternalFormat = GL_DEPTH_COMPONENT32;
   }

   rb->AllocStorage = soft_renderbuffer_storage;
   _mesa_add_renderbuffer(fb, BUFFER_DEPTH, rb);

   return GL_TRUE;
}
Ejemplo n.º 8
0
/**
 * Bind an OSMesaContext to an image buffer.  The image buffer is just a
 * block of memory which the client provides.  Its size must be at least
 * as large as width*height*sizeof(type).  Its address should be a multiple
 * of 4 if using RGBA mode.
 *
 * Image data is stored in the order of glDrawPixels:  row-major order
 * with the lower-left image pixel stored in the first array position
 * (ie. bottom-to-top).
 *
 * If the context's viewport hasn't been initialized yet, it will now be
 * initialized to (0,0,width,height).
 *
 * Input:  osmesa - the rendering context
 *         buffer - the image buffer memory
 *         type - data type for pixel components
 *            Normally, only GL_UNSIGNED_BYTE and GL_UNSIGNED_SHORT_5_6_5
 *            are supported.  But if Mesa's been compiled with CHAN_BITS==16
 *            then type may be GL_UNSIGNED_SHORT or GL_UNSIGNED_BYTE.  And if
 *            Mesa's been build with CHAN_BITS==32 then type may be GL_FLOAT,
 *            GL_UNSIGNED_SHORT or GL_UNSIGNED_BYTE.
 *         width, height - size of image buffer in pixels, at least 1
 * Return:  GL_TRUE if success, GL_FALSE if error because of invalid osmesa,
 *          invalid buffer address, invalid type, width<1, height<1,
 *          width>internal limit or height>internal limit.
 */
GLAPI GLboolean GLAPIENTRY
OSMesaMakeCurrent( OSMesaContext osmesa, void *buffer, GLenum type,
                   GLsizei width, GLsizei height )
{
   if (!osmesa || !buffer ||
       width < 1 || height < 1 ||
       width > MAX_WIDTH || height > MAX_HEIGHT) {
      return GL_FALSE;
   }

   if (osmesa->format == OSMESA_RGB_565 && type != GL_UNSIGNED_SHORT_5_6_5) {
      return GL_FALSE;
   }

#if 0
   if (!(type == GL_UNSIGNED_BYTE ||
         (type == GL_UNSIGNED_SHORT && CHAN_BITS >= 16) ||
         (type == GL_FLOAT && CHAN_BITS == 32))) {
      /* i.e. is sizeof(type) * 8 > CHAN_BITS? */
      return GL_FALSE;
   }
#endif

   osmesa_update_state( &osmesa->mesa, 0 );

   /* Call this periodically to detect when the user has begun using
    * GL rendering from multiple threads.
    */
   _glapi_check_multithread();

   /* Set renderbuffer fields.  Set width/height = 0 to force 
    * osmesa_renderbuffer_storage() being called by _mesa_resize_framebuffer()
    */
   osmesa->rb->Data = buffer;
   osmesa->rb->DataType = type;
   osmesa->rb->Width = osmesa->rb->Height = 0;

   /* Set the framebuffer's size.  This causes the
    * osmesa_renderbuffer_storage() function to get called.
    */
   _mesa_resize_framebuffer(&osmesa->mesa, osmesa->gl_buffer, width, height);
   osmesa->gl_buffer->Initialized = GL_TRUE; /* XXX TEMPORARY? */

   _mesa_make_current( &osmesa->mesa, osmesa->gl_buffer, osmesa->gl_buffer );

   /* Remove renderbuffer attachment, then re-add.  This installs the
    * renderbuffer adaptor/wrapper if needed (for bpp conversion).
    */
   _mesa_remove_renderbuffer(osmesa->gl_buffer, BUFFER_FRONT_LEFT);
   _mesa_add_renderbuffer(osmesa->gl_buffer, BUFFER_FRONT_LEFT, osmesa->rb);


   /* this updates the visual's red/green/blue/alphaBits fields */
   _mesa_update_framebuffer_visual(osmesa->gl_buffer);

   /* update the framebuffer size */
   _mesa_resize_framebuffer(&osmesa->mesa, osmesa->gl_buffer, width, height);

   return GL_TRUE;
}
Ejemplo n.º 9
0
static GLboolean
nouveau_create_buffer(__DRIscreen *dri_screen,
		      __DRIdrawable *drawable,
		      const struct gl_config *visual,
		      GLboolean is_pixmap)
{
	struct gl_renderbuffer *rb;
	struct gl_framebuffer *fb;
	GLenum color_format;

	if (is_pixmap)
		return GL_FALSE; /* not implemented */

	if (visual->redBits == 5)
		color_format = GL_RGB5;
	else if (visual->alphaBits == 0)
		color_format = GL_RGB8;
	else
		color_format = GL_RGBA8;

	fb = nouveau_framebuffer_dri_new(visual);
	if (!fb)
		return GL_FALSE;

	/* Front buffer. */
	rb = nouveau_renderbuffer_dri_new(color_format, drawable);
	_mesa_add_renderbuffer(fb, BUFFER_FRONT_LEFT, rb);

	/* Back buffer */
	if (visual->doubleBufferMode) {
		rb = nouveau_renderbuffer_dri_new(color_format, drawable);
		_mesa_add_renderbuffer(fb, BUFFER_BACK_LEFT, rb);
	}

	/* Depth/stencil buffer. */
	if (visual->depthBits == 24 && visual->stencilBits == 8) {
		rb = nouveau_renderbuffer_dri_new(GL_DEPTH24_STENCIL8_EXT, drawable);
		_mesa_add_renderbuffer(fb, BUFFER_DEPTH, rb);
		_mesa_add_renderbuffer(fb, BUFFER_STENCIL, rb);

	} else if (visual->depthBits == 24) {
		rb = nouveau_renderbuffer_dri_new(GL_DEPTH_COMPONENT24, drawable);
		_mesa_add_renderbuffer(fb, BUFFER_DEPTH, rb);

	} else if (visual->depthBits == 16) {
		rb = nouveau_renderbuffer_dri_new(GL_DEPTH_COMPONENT16, drawable);
		_mesa_add_renderbuffer(fb, BUFFER_DEPTH, rb);
	}

	/* Software renderbuffers. */
	_swrast_add_soft_renderbuffers(fb, GL_FALSE, GL_FALSE, GL_FALSE,
                                       visual->accumRedBits > 0,
                                       GL_FALSE, GL_FALSE);

	drawable->driverPrivate = fb;

	return GL_TRUE;
}
Ejemplo n.º 10
0
static GLboolean
add_depth_stencil_renderbuffer(struct gl_context *ctx,
                               struct gl_framebuffer *fb)
{
   struct gl_renderbuffer *rb;

   assert(fb->Attachment[BUFFER_DEPTH].Renderbuffer == NULL);
   assert(fb->Attachment[BUFFER_STENCIL].Renderbuffer == NULL);

   rb = _swrast_new_soft_renderbuffer(ctx, 0);
   if (!rb) {
      _mesa_error(ctx, GL_OUT_OF_MEMORY, "Allocating depth+stencil buffer");
      return GL_FALSE;
   }

   rb->InternalFormat = GL_DEPTH_STENCIL;

   rb->AllocStorage = soft_renderbuffer_storage;
   _mesa_add_renderbuffer(fb, BUFFER_DEPTH, rb);
   _mesa_add_renderbuffer(fb, BUFFER_STENCIL, rb);

   return GL_TRUE;
}
Ejemplo n.º 11
0
/**
 * Add software-based color renderbuffers to the given framebuffer.
 * This is a helper routine for device drivers when creating a
 * window system framebuffer (not a user-created render/framebuffer).
 * Once this function is called, you can basically forget about this
 * renderbuffer; core Mesa will handle all the buffer management and
 * rendering!
 */
static GLboolean
add_color_renderbuffers(struct gl_context *ctx, struct gl_framebuffer *fb,
                        GLuint rgbBits, GLuint alphaBits,
                        GLboolean frontLeft, GLboolean backLeft,
                        GLboolean frontRight, GLboolean backRight)
{
   gl_buffer_index b;

   if (rgbBits > 16 || alphaBits > 16) {
      _mesa_problem(ctx,
                    "Unsupported bit depth in add_color_renderbuffers");
      return GL_FALSE;
   }

   assert(MAX_COLOR_ATTACHMENTS >= 4);

   for (b = BUFFER_FRONT_LEFT; b <= BUFFER_BACK_RIGHT; b++) {
      struct gl_renderbuffer *rb;

      if (b == BUFFER_FRONT_LEFT && !frontLeft)
         continue;
      else if (b == BUFFER_BACK_LEFT && !backLeft)
         continue;
      else if (b == BUFFER_FRONT_RIGHT && !frontRight)
         continue;
      else if (b == BUFFER_BACK_RIGHT && !backRight)
         continue;

      assert(fb->Attachment[b].Renderbuffer == NULL);

      rb = ctx->Driver.NewRenderbuffer(ctx, 0);
      if (!rb) {
         _mesa_error(ctx, GL_OUT_OF_MEMORY, "Allocating color buffer");
         return GL_FALSE;
      }

      rb->InternalFormat = GL_RGBA;

      rb->AllocStorage = soft_renderbuffer_storage;
      _mesa_add_renderbuffer(fb, b, rb);
   }

   return GL_TRUE;
}
Ejemplo n.º 12
0
/**
 * Create a drawing surface which can be directly displayed on a screen.
 */
static EGLSurface
fbCreateScreenSurfaceMESA(_EGLDriver *drv, EGLDisplay dpy, EGLConfig cfg,
                          const EGLint *attrib_list)
{
   _EGLConfig *config = _eglLookupConfig(drv, dpy, cfg);
   fbDisplay *display = Lookup_fbDisplay(dpy);
   fbSurface *surface;
   EGLSurface surf;
   GLvisual vis;
   GLcontext *ctx = NULL; /* this should be OK */
   int origin, bytesPerPixel;
   int width, height, stride;
   
   surface = (fbSurface *) malloc(sizeof(*surface));
   if (!surface) {
      return EGL_NO_SURFACE;
   }

   /* init base class, error check, etc. */
   surf = _eglInitScreenSurface(&surface->Base, drv, dpy, cfg, attrib_list);
   if (surf == EGL_NO_SURFACE) {
      free(surface);
      return EGL_NO_SURFACE;
   }

   /* convert EGLConfig to GLvisual */
   _eglConfigToContextModesRec(config, &vis);

   /* create Mesa framebuffer */
   surface->mesa_framebuffer = _mesa_create_framebuffer(&vis);
   if (!surface->mesa_framebuffer) {
      free(surface);
      _eglRemoveSurface(&surface->Base);
      return EGL_NO_SURFACE;
   }

   width = surface->Base.Width;
   height = surface->Base.Height;
   bytesPerPixel = vis.rgbBits / 8;
   stride = width * bytesPerPixel;
   origin = 0;

   /* front color renderbuffer */
   {
      driRenderbuffer *drb = driNewRenderbuffer(GL_RGBA, display->pFB,
                                                bytesPerPixel,
                                                origin, stride, NULL);
      fbSetSpanFunctions(drb, &vis);
      _mesa_add_renderbuffer(surface->mesa_framebuffer,
                             BUFFER_FRONT_LEFT, &drb->Base);
   }

   /* back color renderbuffer */
   if (vis.doubleBufferMode) {
      GLubyte *backBuf = _mesa_malloc(stride * height);
      driRenderbuffer *drb = driNewRenderbuffer(GL_RGBA, backBuf,
                                                bytesPerPixel,
                                                origin, stride, NULL);
      fbSetSpanFunctions(drb, &vis);
      _mesa_add_renderbuffer(surface->mesa_framebuffer,
                             BUFFER_BACK_LEFT, &drb->Base);
   }

   /* other renderbuffers- software based */
   _mesa_add_soft_renderbuffers(surface->mesa_framebuffer,
                                GL_FALSE, /* color */
                                vis.haveDepthBuffer,
                                vis.haveStencilBuffer,
                                vis.haveAccumBuffer,
                                GL_FALSE, /* alpha */
                                GL_FALSE /* aux */);
   
   _mesa_resize_framebuffer(ctx, surface->mesa_framebuffer, width, height);

   return surf;
}
Ejemplo n.º 13
0
void
sisUpdateBufferSize(sisContextPtr smesa)
{
   __GLSiSHardware *current = &smesa->current;
   __GLSiSHardware *prev = &smesa->prev;
   struct gl_framebuffer *fb = smesa->glCtx->DrawBuffer;

   if (!smesa->front.Base.InternalFormat) {
      /* do one-time init for the renderbuffers */
      sisInitRenderbuffer(&smesa->front.Base, GL_RGBA);
      sisSetSpanFunctions(&smesa->front, &fb->Visual);
      _mesa_add_renderbuffer(fb, BUFFER_FRONT_LEFT, &smesa->front.Base);

      if (fb->Visual.doubleBufferMode) {
         sisInitRenderbuffer(&smesa->back.Base, GL_RGBA);
         sisSetSpanFunctions(&smesa->back, &fb->Visual);
         _mesa_add_renderbuffer(fb, BUFFER_BACK_LEFT, &smesa->back.Base);
      }

      if (smesa->glCtx->Visual.depthBits > 0) {
         sisInitRenderbuffer(&smesa->depth.Base, 
                             (smesa->glCtx->Visual.depthBits == 16
                              ? GL_DEPTH_COMPONENT16 : GL_DEPTH_COMPONENT24));
         sisSetSpanFunctions(&smesa->depth, &fb->Visual);
         _mesa_add_renderbuffer(fb, BUFFER_DEPTH, &smesa->depth.Base);
      }

      if (smesa->glCtx->Visual.stencilBits > 0) {
         sisInitRenderbuffer(&smesa->stencil.Base, GL_STENCIL_INDEX8_EXT);
         sisSetSpanFunctions(&smesa->stencil, &fb->Visual);
         _mesa_add_renderbuffer(fb, BUFFER_STENCIL, &smesa->stencil.Base);
      }
   }

   /* Make sure initialization did what we think it should */
   assert(smesa->front.Base.InternalFormat);
   assert(smesa->front.Base.AllocStorage);
   if (fb->Visual.doubleBufferMode) {
      assert(fb->Attachment[BUFFER_BACK_LEFT].Renderbuffer);
      assert(smesa->front.Base.AllocStorage);
   }
   if (fb->Visual.depthBits) {
      assert(fb->Attachment[BUFFER_DEPTH].Renderbuffer);
      assert(smesa->depth.Base.AllocStorage);
   }

   /* XXX Should get the base offset of the frontbuffer from the X Server */
   smesa->front.offset = smesa->driDrawable->x * smesa->bytesPerPixel +
			 smesa->driDrawable->y * smesa->front.pitch;
   smesa->front.map = (char *) smesa->driScreen->pFB + smesa->front.offset;

   if ( smesa->width == smesa->driDrawable->w &&
	smesa->height == smesa->driDrawable->h )
   {
      return;
   }

   smesa->front.bpp = smesa->bytesPerPixel * 8;
   /* Front pitch set on context create */
   smesa->front.size = smesa->front.pitch * smesa->driDrawable->h;

   smesa->width = smesa->driDrawable->w;
   smesa->height = smesa->driDrawable->h;
   smesa->bottom = smesa->height - 1;

   if (smesa->back.offset)
      sisFreeBackbuffer( smesa );
   if (smesa->depth.offset)
      sisFreeZStencilBuffer( smesa );

   if ( smesa->glCtx->Visual.depthBits > 0 )
      sisAllocZStencilBuffer( smesa );
   if ( smesa->glCtx->Visual.doubleBufferMode )
      sisAllocBackbuffer( smesa );

   current->hwZ &= ~MASK_ZBufferPitch;
   current->hwZ |= smesa->depth.pitch >> 2;
   current->hwOffsetZ = smesa->depth.offset >> 2;

   if ((current->hwOffsetZ != prev->hwOffsetZ) || (current->hwZ != prev->hwZ)) {
      prev->hwOffsetZ = current->hwOffsetZ;
      prev->hwZ = current->hwZ;
      smesa->GlobalFlag |= GFLAG_ZSETTING;
   }
  
   sisUpdateClipping( smesa->glCtx );
}
Ejemplo n.º 14
0
/**
 * Bind an OSMesaContext to an image buffer.  The image buffer is just a
 * block of memory which the client provides.  Its size must be at least
 * as large as width*height*sizeof(type).  Its address should be a multiple
 * of 4 if using RGBA mode.
 *
 * Image data is stored in the order of glDrawPixels:  row-major order
 * with the lower-left image pixel stored in the first array position
 * (ie. bottom-to-top).
 *
 * If the context's viewport hasn't been initialized yet, it will now be
 * initialized to (0,0,width,height).
 *
 * Input:  osmesa - the rendering context
 *         buffer - the image buffer memory
 *         type - data type for pixel components
 *            Normally, only GL_UNSIGNED_BYTE and GL_UNSIGNED_SHORT_5_6_5
 *            are supported.  But if Mesa's been compiled with CHAN_BITS==16
 *            then type may be GL_UNSIGNED_SHORT or GL_UNSIGNED_BYTE.  And if
 *            Mesa's been build with CHAN_BITS==32 then type may be GL_FLOAT,
 *            GL_UNSIGNED_SHORT or GL_UNSIGNED_BYTE.
 *         width, height - size of image buffer in pixels, at least 1
 * Return:  GL_TRUE if success, GL_FALSE if error because of invalid osmesa,
 *          invalid buffer address, invalid type, width<1, height<1,
 *          width>internal limit or height>internal limit.
 */
GLAPI GLboolean GLAPIENTRY
OSMesaMakeCurrent( OSMesaContext osmesa, void *buffer, GLenum type,
                   GLsizei width, GLsizei height )
{
   if (!osmesa || !buffer ||
       width < 1 || height < 1 ||
       width > SWRAST_MAX_WIDTH || height > SWRAST_MAX_HEIGHT) {
      return GL_FALSE;
   }

   if (osmesa->format == OSMESA_RGB_565 && type != GL_UNSIGNED_SHORT_5_6_5) {
      return GL_FALSE;
   }

#if 0
   if (!(type == GL_UNSIGNED_BYTE ||
         (type == GL_UNSIGNED_SHORT && CHAN_BITS >= 16) ||
         (type == GL_FLOAT && CHAN_BITS == 32))) {
      /* i.e. is sizeof(type) * 8 > CHAN_BITS? */
      return GL_FALSE;
   }
#endif

   osmesa_update_state( &osmesa->mesa, 0 );

   /* Call this periodically to detect when the user has begun using
    * GL rendering from multiple threads.
    */
   _glapi_check_multithread();


   /* Create a front/left color buffer which wraps the user-provided buffer.
    * There is no back color buffer.
    * If the user tries to use a 8, 16 or 32-bit/channel buffer that
    * doesn't match what Mesa was compiled for (CHAN_BITS) the
    * _mesa_add_renderbuffer() function will create a "wrapper" renderbuffer
    * that converts rendering from CHAN_BITS to the user-requested channel
    * size.
    */
   if (!osmesa->srb) {
      osmesa->srb = new_osmesa_renderbuffer(&osmesa->mesa, osmesa->format, type);
      _mesa_remove_renderbuffer(osmesa->gl_buffer, BUFFER_FRONT_LEFT);
      _mesa_add_renderbuffer(osmesa->gl_buffer, BUFFER_FRONT_LEFT,
                             &osmesa->srb->Base);
      assert(osmesa->srb->Base.RefCount == 2);
   }

   osmesa->DataType = type;

   /* Set renderbuffer fields.  Set width/height = 0 to force 
    * osmesa_renderbuffer_storage() being called by _mesa_resize_framebuffer()
    */
   osmesa->srb->Buffer = buffer;
   osmesa->srb->Base.Width = osmesa->srb->Base.Height = 0;

   /* Set the framebuffer's size.  This causes the
    * osmesa_renderbuffer_storage() function to get called.
    */
   _mesa_resize_framebuffer(&osmesa->mesa, osmesa->gl_buffer, width, height);
   osmesa->gl_buffer->Initialized = GL_TRUE; /* XXX TEMPORARY? */

   _mesa_make_current( &osmesa->mesa, osmesa->gl_buffer, osmesa->gl_buffer );

   /* Remove renderbuffer attachment, then re-add.  This installs the
    * renderbuffer adaptor/wrapper if needed (for bpp conversion).
    */
   _mesa_remove_renderbuffer(osmesa->gl_buffer, BUFFER_FRONT_LEFT);
   _mesa_add_renderbuffer(osmesa->gl_buffer, BUFFER_FRONT_LEFT,
                          &osmesa->srb->Base);


   /* this updates the visual's red/green/blue/alphaBits fields */
   _mesa_update_framebuffer_visual(&osmesa->mesa, osmesa->gl_buffer);

   /* update the framebuffer size */
   _mesa_resize_framebuffer(&osmesa->mesa, osmesa->gl_buffer, width, height);

   return GL_TRUE;
}
Ejemplo n.º 15
0
/*
 * New in Mesa 3.5
 *
 * Create context and specify size of ancillary buffers.
 */
GLAPI OSMesaContext GLAPIENTRY
OSMesaCreateContextExt( GLenum format, GLint depthBits, GLint stencilBits,
                        GLint accumBits, OSMesaContext sharelist )
{
   OSMesaContext osmesa;
   struct dd_function_table functions;
   GLint rind, gind, bind, aind;
   GLint indexBits = 0, redBits = 0, greenBits = 0, blueBits = 0, alphaBits =0;
   GLboolean rgbmode;

   rind = gind = bind = aind = 0;
   if (format==OSMESA_COLOR_INDEX) {
      indexBits = 8;
      rgbmode = GL_FALSE;
   }
   else if (format==OSMESA_RGBA) {
      indexBits = 0;
      redBits = CHAN_BITS;
      greenBits = CHAN_BITS;
      blueBits = CHAN_BITS;
      alphaBits = CHAN_BITS;
      rind = 0;
      gind = 1;
      bind = 2;
      aind = 3;
      rgbmode = GL_TRUE;
   }
   else if (format==OSMESA_BGRA) {
      indexBits = 0;
      redBits = CHAN_BITS;
      greenBits = CHAN_BITS;
      blueBits = CHAN_BITS;
      alphaBits = CHAN_BITS;
      bind = 0;
      gind = 1;
      rind = 2;
      aind = 3;
      rgbmode = GL_TRUE;
   }
   else if (format==OSMESA_ARGB) {
      indexBits = 0;
      redBits = CHAN_BITS;
      greenBits = CHAN_BITS;
      blueBits = CHAN_BITS;
      alphaBits = CHAN_BITS;
      aind = 0;
      rind = 1;
      gind = 2;
      bind = 3;
      rgbmode = GL_TRUE;
   }
   else if (format==OSMESA_RGB) {
      indexBits = 0;
      redBits = CHAN_BITS;
      greenBits = CHAN_BITS;
      blueBits = CHAN_BITS;
      alphaBits = 0;
      rind = 0;
      gind = 1;
      bind = 2;
      rgbmode = GL_TRUE;
   }
   else if (format==OSMESA_BGR) {
      indexBits = 0;
      redBits = CHAN_BITS;
      greenBits = CHAN_BITS;
      blueBits = CHAN_BITS;
      alphaBits = 0;
      rind = 2;
      gind = 1;
      bind = 0;
      rgbmode = GL_TRUE;
   }
#if CHAN_TYPE == GL_UNSIGNED_BYTE
   else if (format==OSMESA_RGB_565) {
      indexBits = 0;
      redBits = 5;
      greenBits = 6;
      blueBits = 5;
      alphaBits = 0;
      rind = 0; /* not used */
      gind = 0;
      bind = 0;
      rgbmode = GL_TRUE;
   }
#endif
   else {
      return NULL;
   }

   osmesa = (OSMesaContext) CALLOC_STRUCT(osmesa_context);
   if (osmesa) {
      osmesa->gl_visual = _mesa_create_visual( rgbmode,
                                               GL_FALSE,    /* double buffer */
                                               GL_FALSE,    /* stereo */
                                               redBits,
                                               greenBits,
                                               blueBits,
                                               alphaBits,
                                               indexBits,
                                               depthBits,
                                               stencilBits,
                                               accumBits,
                                               accumBits,
                                               accumBits,
                                               alphaBits ? accumBits : 0,
                                               1            /* num samples */
                                               );
      if (!osmesa->gl_visual) {
         FREE(osmesa);
         return NULL;
      }

      /* Initialize device driver function table */
      _mesa_init_driver_functions(&functions);
      /* override with our functions */
      functions.GetString = get_string;
      functions.UpdateState = osmesa_update_state;
      functions.GetBufferSize = get_buffer_size;

      if (!_mesa_initialize_context(&osmesa->mesa,
                                    osmesa->gl_visual,
                                    sharelist ? &sharelist->mesa
                                              : (GLcontext *) NULL,
                                    &functions, (void *) osmesa)) {
         _mesa_destroy_visual( osmesa->gl_visual );
         FREE(osmesa);
         return NULL;
      }

      _mesa_enable_sw_extensions(&(osmesa->mesa));
      _mesa_enable_1_3_extensions(&(osmesa->mesa));
      _mesa_enable_1_4_extensions(&(osmesa->mesa));
      _mesa_enable_1_5_extensions(&(osmesa->mesa));

      osmesa->gl_buffer = _mesa_create_framebuffer(osmesa->gl_visual);
      if (!osmesa->gl_buffer) {
         _mesa_destroy_visual( osmesa->gl_visual );
         _mesa_free_context_data( &osmesa->mesa );
         FREE(osmesa);
         return NULL;
      }

      /* create front color buffer in user-provided memory (no back buffer) */
      _mesa_add_renderbuffer(osmesa->gl_buffer, BUFFER_FRONT_LEFT,
                             new_osmesa_renderbuffer(format));
      _mesa_add_soft_renderbuffers(osmesa->gl_buffer,
                                   GL_FALSE, /* color */
                                   osmesa->gl_visual->haveDepthBuffer,
                                   osmesa->gl_visual->haveStencilBuffer,
                                   osmesa->gl_visual->haveAccumBuffer,
                                   GL_FALSE, /* alpha */
                                   GL_FALSE /* aux */ );

      osmesa->format = format;
      osmesa->buffer = NULL;
      osmesa->width = 0;
      osmesa->height = 0;
      osmesa->userRowLength = 0;
      osmesa->rowlength = 0;
      osmesa->yup = GL_TRUE;
      osmesa->rInd = rind;
      osmesa->gInd = gind;
      osmesa->bInd = bind;
      osmesa->aInd = aind;

      /* Initialize the software rasterizer and helper modules. */
      {
	 GLcontext *ctx = &osmesa->mesa;
         SWcontext *swrast;
         TNLcontext *tnl;

	 if (!_swrast_CreateContext( ctx ) ||
             !_ac_CreateContext( ctx ) ||
             !_tnl_CreateContext( ctx ) ||
             !_swsetup_CreateContext( ctx )) {
            _mesa_destroy_visual(osmesa->gl_visual);
            _mesa_free_context_data(ctx);
            _mesa_free(osmesa);
            return NULL;
         }
	
	 _swsetup_Wakeup( ctx );

         /* use default TCL pipeline */
         tnl = TNL_CONTEXT(ctx);
         tnl->Driver.RunPipeline = _tnl_run_pipeline;

         /* Extend the software rasterizer with our optimized line and triangle
          * drawing functions.
          */
         swrast = SWRAST_CONTEXT( ctx );
         swrast->choose_line = osmesa_choose_line;
         swrast->choose_triangle = osmesa_choose_triangle;
      }
   }
   return osmesa;
}
Ejemplo n.º 16
0
/* Create and initialize the Mesa and driver specific pixmap buffer
 * data.
 */
static GLboolean
fbCreateBuffer( __DRIscreenPrivate *driScrnPriv,
		__DRIdrawablePrivate *driDrawPriv,
		const __GLcontextModes *mesaVis,
		GLboolean isPixmap )
{
   struct gl_framebuffer *mesa_framebuffer;
   
   if (isPixmap) {
      return GL_FALSE; /* not implemented */
   }
   else {
      const GLboolean swDepth = mesaVis->depthBits > 0;
      const GLboolean swAlpha = mesaVis->alphaBits > 0;
      const GLboolean swAccum = mesaVis->accumRedBits > 0;
      const GLboolean swStencil = mesaVis->stencilBits > 0;
      
      mesa_framebuffer = _mesa_create_framebuffer(mesaVis);
      if (!mesa_framebuffer)
         return 0;

      /* XXX double-check these parameters (bpp vs cpp, etc) */
      {
         driRenderbuffer *drb = driNewRenderbuffer(GL_RGBA,
                                                   driScrnPriv->pFB,
                                                   driScrnPriv->fbBPP / 8,
                                                   driScrnPriv->fbOrigin,
                                                   driScrnPriv->fbStride,
                                                   driDrawPriv);
         fbSetSpanFunctions(drb, mesaVis);
         _mesa_add_renderbuffer(mesa_framebuffer,
                                BUFFER_FRONT_LEFT, &drb->Base);
      }
      if (mesaVis->doubleBufferMode) {
         /* XXX what are the correct origin/stride values? */
         GLvoid *backBuf = _mesa_malloc(driScrnPriv->fbStride
                                        * driScrnPriv->fbHeight);
         driRenderbuffer *drb = driNewRenderbuffer(GL_RGBA,
                                                   backBuf,
                                                   driScrnPriv->fbBPP /8,
                                                   driScrnPriv->fbOrigin,
                                                   driScrnPriv->fbStride,
                                                   driDrawPriv);
         fbSetSpanFunctions(drb, mesaVis);
         _mesa_add_renderbuffer(mesa_framebuffer,
                                BUFFER_BACK_LEFT, &drb->Base);
      }

      _mesa_add_soft_renderbuffers(mesa_framebuffer,
                                   GL_FALSE, /* color */
                                   swDepth,
                                   swStencil,
                                   swAccum,
                                   swAlpha, /* or always zero? */
                                   GL_FALSE /* aux */);
      
      driDrawPriv->driverPrivate = mesa_framebuffer;

      return 1;
   }
}
Ejemplo n.º 17
0
Archivo: xm_api.c Proyecto: RAOF/mesa
/**
 * Allocate a new XMesaBuffer object which corresponds to the given drawable.
 * Note that XMesaBuffer is derived from struct gl_framebuffer.
 * The new XMesaBuffer will not have any size (Width=Height=0).
 *
 * \param d  the corresponding X drawable (window or pixmap)
 * \param type  either WINDOW, PIXMAP or PBUFFER, describing d
 * \param vis  the buffer's visual
 * \param cmap  the window's colormap, if known.
 * \return new XMesaBuffer or NULL if any problem
 */
static XMesaBuffer
create_xmesa_buffer(XMesaDrawable d, BufferType type,
                    XMesaVisual vis, XMesaColormap cmap)
{
   XMesaBuffer b;

   ASSERT(type == WINDOW || type == PIXMAP || type == PBUFFER);

   b = (XMesaBuffer) CALLOC_STRUCT(xmesa_buffer);
   if (!b)
      return NULL;

   b->display = vis->display;
   b->xm_visual = vis;
   b->type = type;
   b->cmap = cmap;

   _mesa_initialize_window_framebuffer(&b->mesa_buffer, &vis->mesa_visual);
   b->mesa_buffer.Delete = xmesa_delete_framebuffer;

   /*
    * Front renderbuffer
    */
   b->frontxrb = xmesa_new_renderbuffer(NULL, 0, vis, GL_FALSE);
   if (!b->frontxrb) {
      free(b);
      return NULL;
   }
   b->frontxrb->Parent = b;
   b->frontxrb->drawable = d;
   b->frontxrb->pixmap = (XMesaPixmap) d;
   _mesa_add_renderbuffer(&b->mesa_buffer, BUFFER_FRONT_LEFT,
                          &b->frontxrb->Base.Base);

   /*
    * Back renderbuffer
    */
   if (vis->mesa_visual.doubleBufferMode) {
      b->backxrb = xmesa_new_renderbuffer(NULL, 0, vis, GL_TRUE);
      if (!b->backxrb) {
         /* XXX free front xrb too */
         free(b);
         return NULL;
      }
      b->backxrb->Parent = b;
      /* determine back buffer implementation */
      b->db_mode = vis->ximage_flag ? BACK_XIMAGE : BACK_PIXMAP;
      
      _mesa_add_renderbuffer(&b->mesa_buffer, BUFFER_BACK_LEFT,
                             &b->backxrb->Base.Base);
   }

   /*
    * Other renderbuffer (depth, stencil, etc)
    */
   _swrast_add_soft_renderbuffers(&b->mesa_buffer,
                                  GL_FALSE,  /* color */
                                  vis->mesa_visual.haveDepthBuffer,
                                  vis->mesa_visual.haveStencilBuffer,
                                  vis->mesa_visual.haveAccumBuffer,
                                  GL_FALSE,  /* software alpha buffer */
                                  vis->mesa_visual.numAuxBuffers > 0 );

   /* GLX_EXT_texture_from_pixmap */
   b->TextureTarget = 0;
   b->TextureFormat = GLX_TEXTURE_FORMAT_NONE_EXT;
   b->TextureMipmap = 0;

   /* insert buffer into linked list */
   b->Next = XMesaBufferList;
   XMesaBufferList = b;

   return b;
}
Ejemplo n.º 18
0
/**
 * Create the Mesa framebuffer and renderbuffers for a given window/drawable.
 *
 * \todo This function (and its interface) will need to be updated to support
 * pbuffers.
 */
static GLboolean
radeonCreateBuffer( __DRIscreen *driScrnPriv,
                    __DRIdrawable *driDrawPriv,
                    const struct gl_config *mesaVis,
                    GLboolean isPixmap )
{
    radeonScreenPtr screen = (radeonScreenPtr) driScrnPriv->driverPrivate;

    const GLboolean swDepth = GL_FALSE;
    const GLboolean swAlpha = GL_FALSE;
    const GLboolean swAccum = mesaVis->accumRedBits > 0;
    const GLboolean swStencil = mesaVis->stencilBits > 0 &&
	mesaVis->depthBits != 24;
    mesa_format rgbFormat;
    struct radeon_framebuffer *rfb;

    if (isPixmap)
      return GL_FALSE; /* not implemented */

    rfb = CALLOC_STRUCT(radeon_framebuffer);
    if (!rfb)
      return GL_FALSE;

    _mesa_initialize_window_framebuffer(&rfb->base, mesaVis);

    if (mesaVis->redBits == 5)
        rgbFormat = _mesa_little_endian() ? MESA_FORMAT_B5G6R5_UNORM : MESA_FORMAT_R5G6B5_UNORM;
    else if (mesaVis->alphaBits == 0)
        rgbFormat = _mesa_little_endian() ? MESA_FORMAT_B8G8R8X8_UNORM : MESA_FORMAT_X8R8G8B8_UNORM;
    else
        rgbFormat = _mesa_little_endian() ? MESA_FORMAT_B8G8R8A8_UNORM : MESA_FORMAT_A8R8G8B8_UNORM;

    /* front color renderbuffer */
    rfb->color_rb[0] = radeon_create_renderbuffer(rgbFormat, driDrawPriv);
    _mesa_add_renderbuffer(&rfb->base, BUFFER_FRONT_LEFT, &rfb->color_rb[0]->base.Base);
    rfb->color_rb[0]->has_surface = 1;

    /* back color renderbuffer */
    if (mesaVis->doubleBufferMode) {
      rfb->color_rb[1] = radeon_create_renderbuffer(rgbFormat, driDrawPriv);
	_mesa_add_renderbuffer(&rfb->base, BUFFER_BACK_LEFT, &rfb->color_rb[1]->base.Base);
	rfb->color_rb[1]->has_surface = 1;
    }

    if (mesaVis->depthBits == 24) {
      if (mesaVis->stencilBits == 8) {
	struct radeon_renderbuffer *depthStencilRb =
           radeon_create_renderbuffer(MESA_FORMAT_Z24_UNORM_S8_UINT, driDrawPriv);
	_mesa_add_renderbuffer(&rfb->base, BUFFER_DEPTH, &depthStencilRb->base.Base);
	_mesa_add_renderbuffer(&rfb->base, BUFFER_STENCIL, &depthStencilRb->base.Base);
	depthStencilRb->has_surface = screen->depthHasSurface;
      } else {
	/* depth renderbuffer */
	struct radeon_renderbuffer *depth =
           radeon_create_renderbuffer(MESA_FORMAT_Z24_UNORM_X8_UINT, driDrawPriv);
	_mesa_add_renderbuffer(&rfb->base, BUFFER_DEPTH, &depth->base.Base);
	depth->has_surface = screen->depthHasSurface;
      }
    } else if (mesaVis->depthBits == 16) {
        /* just 16-bit depth buffer, no hw stencil */
	struct radeon_renderbuffer *depth =
           radeon_create_renderbuffer(MESA_FORMAT_Z_UNORM16, driDrawPriv);
	_mesa_add_renderbuffer(&rfb->base, BUFFER_DEPTH, &depth->base.Base);
	depth->has_surface = screen->depthHasSurface;
    }

    _swrast_add_soft_renderbuffers(&rfb->base,
	    GL_FALSE, /* color */
	    swDepth,
	    swStencil,
	    swAccum,
	    swAlpha,
	    GL_FALSE /* aux */);
    driDrawPriv->driverPrivate = (void *) rfb;

    return (driDrawPriv->driverPrivate != NULL);
}
Ejemplo n.º 19
0
GLFBDevBufferPtr
glFBDevCreateBuffer( const struct fb_fix_screeninfo *fixInfo,
                     const struct fb_var_screeninfo *varInfo,
                     const GLFBDevVisualPtr visual,
                     void *frontBuffer, void *backBuffer, size_t size )
{
   struct GLFBDevRenderbufferRec *frontrb, *backrb;
   GLFBDevBufferPtr buf;

   ASSERT(visual);
   ASSERT(frontBuffer);
   ASSERT(size > 0);

   /* this is to update the visual if there was a resize and the
      buffer is created again */
   visual->var = *varInfo;
   visual->fix = *fixInfo;

   if (visual->fix.visual != fixInfo->visual ||
       visual->fix.type != fixInfo->type ||
       visual->var.bits_per_pixel != varInfo->bits_per_pixel ||
       visual->var.grayscale != varInfo->grayscale ||
       visual->var.red.offset != varInfo->red.offset ||
       visual->var.green.offset != varInfo->green.offset ||
       visual->var.blue.offset != varInfo->blue.offset ||
       visual->var.transp.offset != varInfo->transp.offset) {
      /* visual mismatch! */
      return NULL;
   }

   buf = CALLOC_STRUCT(GLFBDevBufferRec);
   if (!buf)
      return NULL;

   /* basic framebuffer setup */
   _mesa_initialize_window_framebuffer(&buf->glframebuffer, &visual->glvisual);
   /* add front renderbuffer */
   frontrb = new_glfbdev_renderbuffer(frontBuffer, visual);
   _mesa_add_renderbuffer(&buf->glframebuffer, BUFFER_FRONT_LEFT,
                          &frontrb->Base);
   /* add back renderbuffer */
   if (visual->glvisual.doubleBufferMode) {
      const int malloced = !backBuffer;
      if (malloced) {
         /* malloc a back buffer */
         backBuffer = malloc(size);
         if (!backBuffer) {
            _mesa_free_framebuffer_data(&buf->glframebuffer);
            free(buf);
            return NULL;
         }
      }

      backrb = new_glfbdev_renderbuffer(backBuffer, visual);
      if (!backrb) {
         /* out of mem */
         return NULL;
      }
      backrb->mallocedBuffer = malloced;

      _mesa_add_renderbuffer(&buf->glframebuffer, BUFFER_BACK_LEFT,
                             &backrb->Base);
   }
   /* add software renderbuffers */
   _mesa_add_soft_renderbuffers(&buf->glframebuffer,
                                GL_FALSE, /* color */
                                visual->glvisual.haveDepthBuffer,
                                visual->glvisual.haveStencilBuffer,
                                visual->glvisual.haveAccumBuffer,
                                GL_FALSE, /* alpha */
                                GL_FALSE /* aux bufs */);

   buf->fix = *fixInfo;   /* struct assignment */
   buf->var = *varInfo;   /* struct assignment */
   buf->visual = visual;  /* ptr assignment */
   buf->size = size;
   buf->bytesPerPixel = visual->var.bits_per_pixel / 8;

   return buf;
}
Ejemplo n.º 20
0
/**
 * This is called when we need to set up GL rendering to a new X window.
 */
static GLboolean
intelCreateBuffer(__DRIscreen * driScrnPriv,
                  __DRIdrawable * driDrawPriv,
                  const struct gl_config * mesaVis, GLboolean isPixmap)
{
   struct intel_renderbuffer *rb;
   struct intel_screen *screen = (struct intel_screen*) driScrnPriv->driverPrivate;
   gl_format rgbFormat;
   unsigned num_samples = intel_quantize_num_samples(screen, mesaVis->samples);
   struct gl_framebuffer *fb;

   if (isPixmap)
      return false;

   fb = CALLOC_STRUCT(gl_framebuffer);
   if (!fb)
      return false;

   _mesa_initialize_window_framebuffer(fb, mesaVis);

   if (mesaVis->redBits == 5)
      rgbFormat = MESA_FORMAT_RGB565;
   else if (mesaVis->sRGBCapable)
      rgbFormat = MESA_FORMAT_SARGB8;
   else if (mesaVis->alphaBits == 0)
      rgbFormat = MESA_FORMAT_XRGB8888;
   else
      rgbFormat = MESA_FORMAT_ARGB8888;

   /* setup the hardware-based renderbuffers */
   rb = intel_create_renderbuffer(rgbFormat, num_samples);
   _mesa_add_renderbuffer(fb, BUFFER_FRONT_LEFT, &rb->Base.Base);

   if (mesaVis->doubleBufferMode) {
      rb = intel_create_renderbuffer(rgbFormat, num_samples);
      _mesa_add_renderbuffer(fb, BUFFER_BACK_LEFT, &rb->Base.Base);
   }

   /*
    * Assert here that the gl_config has an expected depth/stencil bit
    * combination: one of d24/s8, d16/s0, d0/s0. (See intelInitScreen2(),
    * which constructs the advertised configs.)
    */
   if (mesaVis->depthBits == 24) {
      assert(mesaVis->stencilBits == 8);

      if (screen->hw_has_separate_stencil) {
         rb = intel_create_private_renderbuffer(MESA_FORMAT_X8_Z24,
                                                num_samples);
         _mesa_add_renderbuffer(fb, BUFFER_DEPTH, &rb->Base.Base);
         rb = intel_create_private_renderbuffer(MESA_FORMAT_S8,
                                                num_samples);
         _mesa_add_renderbuffer(fb, BUFFER_STENCIL, &rb->Base.Base);
      } else {
         /*
          * Use combined depth/stencil. Note that the renderbuffer is
          * attached to two attachment points.
          */
         rb = intel_create_private_renderbuffer(MESA_FORMAT_S8_Z24,
                                                num_samples);
         _mesa_add_renderbuffer(fb, BUFFER_DEPTH, &rb->Base.Base);
         _mesa_add_renderbuffer(fb, BUFFER_STENCIL, &rb->Base.Base);
      }
   }
   else if (mesaVis->depthBits == 16) {
      assert(mesaVis->stencilBits == 0);
      rb = intel_create_private_renderbuffer(MESA_FORMAT_Z16,
                                             num_samples);
      _mesa_add_renderbuffer(fb, BUFFER_DEPTH, &rb->Base.Base);
   }
   else {
      assert(mesaVis->depthBits == 0);
      assert(mesaVis->stencilBits == 0);
   }

   /* now add any/all software-based renderbuffers we may need */
   _swrast_add_soft_renderbuffers(fb,
                                  false, /* never sw color */
                                  false, /* never sw depth */
                                  false, /* never sw stencil */
                                  mesaVis->accumRedBits > 0,
                                  false, /* never sw alpha */
                                  false  /* never sw aux */ );
   driDrawPriv->driverPrivate = fb;

   return true;
}
Ejemplo n.º 21
0
MesaSoftwareRenderer::MesaSoftwareRenderer(BGLView* view, ulong options,
		BGLDispatcher* dispatcher)
	: BGLRenderer(view, options, dispatcher),
	fBitmap(NULL),
	fDirectModeEnabled(false),
	fInfo(NULL),
	fInfoLocker("info locker"),
	fContext(NULL),
	fVisual(NULL),
	fFrameBuffer(NULL),
	fFrontRenderBuffer(NULL),
	fBackRenderBuffer(NULL),
	fColorSpace(B_NO_COLOR_SPACE)
{
	CALLED();

	fClearColor[BE_RCOMP] = 0;
	fClearColor[BE_GCOMP] = 0;
	fClearColor[BE_BCOMP] = 0;
	fClearColor[BE_ACOMP] = 0;

	fClearIndex = 0;

	fColorSpace = BScreen(GLView()->Window()).ColorSpace();

	// We force single buffering for the time being
	//options &= !BGL_DOUBLE;

	const GLboolean rgbFlag = ((options & BGL_INDEX) == 0);
	const GLboolean alphaFlag = ((options & BGL_ALPHA) == BGL_ALPHA);
	const GLboolean dblFlag = ((options & BGL_DOUBLE) == BGL_DOUBLE);
	const GLboolean stereoFlag = false;
	const GLint depth = (options & BGL_DEPTH) ? 16 : 0;
	const GLint stencil = (options & BGL_STENCIL) ? 8 : 0;
	const GLint accum = (options & BGL_ACCUM) ? 16 : 0;
	const GLint index = (options & BGL_INDEX) ? 32 : 0;
	const GLint red = rgbFlag ? 8 : 0;
	const GLint green = rgbFlag ? 8 : 0;
	const GLint blue = rgbFlag ? 8 : 0;
	const GLint alpha = alphaFlag ? 8 : 0;

	fOptions = options; // | BGL_INDIRECT;
	struct dd_function_table functions;

	fVisual = _mesa_create_visual(rgbFlag, dblFlag, stereoFlag, red, green,
		blue, alpha, index, depth, stencil, accum, accum, accum,
		alpha ? accum : 0, 1);

	// Initialize device driver function table
	_mesa_init_driver_functions(&functions);

	functions.GetString 	= _GetString;
	functions.UpdateState 	= _UpdateState;
	functions.GetBufferSize = NULL;
	functions.Error			= _Error;
	functions.Viewport		= _Viewport;
	functions.Flush			= _Flush;

	// create core context
	fContext = _mesa_create_context(fVisual, NULL, &functions, this);
	if (!fContext) {
		_mesa_destroy_visual(fVisual);
		return;
	}

	/* Initialize the software rasterizer and helper modules. */
	_swrast_CreateContext(fContext);
	_vbo_CreateContext(fContext);
	_tnl_CreateContext(fContext);
	_swsetup_CreateContext(fContext);
	_swsetup_Wakeup(fContext);

	// Use default TCL pipeline
	TNL_CONTEXT(fContext)->Driver.RunPipeline = _tnl_run_pipeline;

	_mesa_enable_sw_extensions(fContext);
	_mesa_enable_1_3_extensions(fContext);
	_mesa_enable_1_4_extensions(fContext);
	_mesa_enable_1_5_extensions(fContext);
	_mesa_enable_2_0_extensions(fContext);
	_mesa_enable_2_1_extensions(fContext);

	// create core framebuffer
	fFrameBuffer = (struct msr_framebuffer*)_mesa_calloc(
		sizeof(*fFrameBuffer));
	_mesa_initialize_framebuffer(&fFrameBuffer->Base, fVisual);

	fFrontRenderBuffer = (struct msr_renderbuffer*)_mesa_calloc(
		sizeof(*fFrontRenderBuffer));
	_mesa_init_renderbuffer(&fFrontRenderBuffer->Base, 0);

	fFrontRenderBuffer->Base.AllocStorage = _FrontRenderbufferStorage;
	fFrontRenderBuffer->Base.Data = NULL;
	fFrontRenderBuffer->Base.InternalFormat = GL_RGBA;
	fFrontRenderBuffer->Base._BaseFormat = GL_RGBA;
	fFrontRenderBuffer->Base.DataType = GL_UNSIGNED_BYTE;
	fFrontRenderBuffer->Base.RedBits   = 8 * sizeof(GLubyte);
	fFrontRenderBuffer->Base.GreenBits = 8 * sizeof(GLubyte);
	fFrontRenderBuffer->Base.BlueBits  = 8 * sizeof(GLubyte);
	fFrontRenderBuffer->Base.AlphaBits = 8 * sizeof(GLubyte);
	_SetSpanFuncs(fFrontRenderBuffer, fColorSpace);
	_mesa_add_renderbuffer(&fFrameBuffer->Base, BUFFER_FRONT_LEFT,
		&fFrontRenderBuffer->Base);

	if (dblFlag) {
		fBackRenderBuffer = (struct msr_renderbuffer*)_mesa_calloc(
			sizeof(*fBackRenderBuffer));
		_mesa_init_renderbuffer(&fBackRenderBuffer->Base, 0);

		fBackRenderBuffer->Base.AllocStorage = _BackRenderbufferStorage;
		fBackRenderBuffer->Base.Data = NULL;
		fBackRenderBuffer->Base.Delete = _DeleteBackBuffer;
		fBackRenderBuffer->Base.InternalFormat = GL_RGBA;
		fBackRenderBuffer->Base._BaseFormat = GL_RGBA;
		fBackRenderBuffer->Base.DataType = GL_UNSIGNED_BYTE;
		fBackRenderBuffer->Base.RedBits   = 8 * sizeof(GLubyte);
		fBackRenderBuffer->Base.GreenBits = 8 * sizeof(GLubyte);
		fBackRenderBuffer->Base.BlueBits  = 8 * sizeof(GLubyte);
		fBackRenderBuffer->Base.AlphaBits = 8 * sizeof(GLubyte);
		_SetSpanFuncs(fBackRenderBuffer, fColorSpace);
		_mesa_add_renderbuffer(&fFrameBuffer->Base, BUFFER_BACK_LEFT,
			&fBackRenderBuffer->Base);
	}

	_mesa_add_soft_renderbuffers(&fFrameBuffer->Base, GL_FALSE,
		fVisual->haveDepthBuffer, fVisual->haveStencilBuffer,
		fVisual->haveAccumBuffer, alphaFlag, GL_FALSE);

	BRect bounds = view->Bounds();
	fWidth = fNewWidth = (GLint)bounds.Width();
	fHeight = fNewHeight = (GLint)bounds.Height();

	// some stupid applications (Quake2) don't even think about calling LockGL()
	// before using glGetString and its glGet*() friends...
	// so make sure there is at least a valid context.

	if (!_mesa_get_current_context()) {
		LockGL();
		// not needed, we don't have a looper yet: UnlockLooper();
	}
}
MesaSoftwareRenderer::MesaSoftwareRenderer(BGLView* view, ulong options,
	BGLDispatcher* dispatcher)
	: BGLRenderer(view, options, dispatcher),
	fBitmap(NULL),
	fDirectModeEnabled(false),
	fInfo(NULL),
	fInfoLocker("info locker"),
	fContext(NULL),
	fVisual(NULL),
	fFrameBuffer(NULL),
	fFrontRenderBuffer(NULL),
	fBackRenderBuffer(NULL),
	fColorSpace(B_NO_COLOR_SPACE)
{
	CALLED();

	fClearColor[BE_RCOMP] = 0;
	fClearColor[BE_GCOMP] = 0;
	fClearColor[BE_BCOMP] = 0;
	fClearColor[BE_ACOMP] = 0;

	fClearIndex = 0;

	fColorSpace = BScreen(GLView()->Window()).ColorSpace();

	// We force single buffering for the time being
	options &= ~BGL_DOUBLE;

	const GLboolean rgbFlag = ((options & BGL_INDEX) == 0);
	const GLboolean alphaFlag = ((options & BGL_ALPHA) == BGL_ALPHA);
	const GLboolean dblFlag = ((options & BGL_DOUBLE) == BGL_DOUBLE);
	const GLboolean stereoFlag = false;
	const GLint depth = (options & BGL_DEPTH) ? 16 : 0;
	const GLint stencil = (options & BGL_STENCIL) ? 8 : 0;
	const GLint accum = (options & BGL_ACCUM) ? 16 : 0;
	const GLint red = rgbFlag ? 8 : 0;
	const GLint green = rgbFlag ? 8 : 0;
	const GLint blue = rgbFlag ? 8 : 0;
	const GLint alpha = alphaFlag ? 8 : 0;

	fOptions = options; // | BGL_INDIRECT;
	struct dd_function_table functions;

	fVisual = _mesa_create_visual(dblFlag, stereoFlag, red, green,
		blue, alpha, depth, stencil, accum, accum, accum,
		alpha ? accum : 0, 1);

	// Initialize device driver function table
	_mesa_init_driver_functions(&functions);

	functions.GetString 	= _GetString;
	functions.UpdateState 	= _UpdateState;
	functions.GetBufferSize = NULL;
	functions.Error			= _Error;
	functions.Viewport		= _Viewport;
	functions.Flush			= _Flush;

	// create core context
#if HAIKU_MESA_VER <= 708
	fContext = _mesa_create_context(fVisual, NULL, &functions, this);
#else
	fContext = _mesa_create_context(API_OPENGL, fVisual, NULL,
		&functions, this);
#endif

	if (!fContext) {
		ERROR("%s: Failed to create Mesa context!\n", __func__);
		_mesa_destroy_visual(fVisual);
		return;
	}

	/* Initialize the software rasterizer and helper modules. */
	_swrast_CreateContext(fContext);
	_vbo_CreateContext(fContext);
	_tnl_CreateContext(fContext);
	_swsetup_CreateContext(fContext);
	_swsetup_Wakeup(fContext);

	// Use default TCL pipeline
	TNL_CONTEXT(fContext)->Driver.RunPipeline = _tnl_run_pipeline;

	_mesa_meta_init(fContext);
	_mesa_enable_sw_extensions(fContext);
	_mesa_enable_1_3_extensions(fContext);
	_mesa_enable_1_4_extensions(fContext);
	_mesa_enable_1_5_extensions(fContext);
	_mesa_enable_2_0_extensions(fContext);
	_mesa_enable_2_1_extensions(fContext);

	// create core framebuffer
	fFrameBuffer = (struct msr_framebuffer*)calloc(1,
		sizeof(*fFrameBuffer));
	if (fFrameBuffer == NULL) {
		ERROR("%s: Unable to calloc GL FrameBuffer!\n", __func__);
		_mesa_destroy_visual(fVisual);
		return;
	}
	_mesa_initialize_window_framebuffer(&fFrameBuffer->base, fVisual);

	// Setup front render buffer
	fFrontRenderBuffer = _NewRenderBuffer(true);
	if (fFrontRenderBuffer == NULL) {
		ERROR("%s: FrontRenderBuffer is requested but unallocated!\n",
			__func__);
		_mesa_destroy_visual(fVisual);
		free(fFrameBuffer);
		return;
	}
	_mesa_add_renderbuffer(&fFrameBuffer->base, BUFFER_FRONT_LEFT,
		&fFrontRenderBuffer->base);

	// Setup back render buffer (if requested)
	if (fVisual->doubleBufferMode) {
		fBackRenderBuffer = _NewRenderBuffer(false);
		if (fBackRenderBuffer == NULL) {
			ERROR("%s: BackRenderBuffer is requested but unallocated!\n",
				__func__);
			_mesa_destroy_visual(fVisual);
			free(fFrameBuffer);
			return;
		}
		_mesa_add_renderbuffer(&fFrameBuffer->base, BUFFER_BACK_LEFT,
			&fBackRenderBuffer->base);
	}

#if HAIKU_MESA_VER >= 709
	// New Mesa
	_swrast_add_soft_renderbuffers(&fFrameBuffer->base, GL_FALSE,
		fVisual->haveDepthBuffer, fVisual->haveStencilBuffer,
		fVisual->haveAccumBuffer, alphaFlag, GL_FALSE);
#else
	// Old Mesa
	_mesa_add_soft_renderbuffers(&fFrameBuffer->base, GL_FALSE,
		fVisual->haveDepthBuffer, fVisual->haveStencilBuffer,
		fVisual->haveAccumBuffer, alphaFlag, GL_FALSE);
#endif

	BRect bounds = view->Bounds();
	fWidth = fNewWidth = (GLint)bounds.Width();
	fHeight = fNewHeight = (GLint)bounds.Height();

	// some stupid applications (Quake2) don't even think about calling LockGL()
	// before using glGetString and its glGet*() friends...
	// so make sure there is at least a valid context.

	if (!_mesa_get_current_context()) {
		LockGL();
		// not needed, we don't have a looper yet: UnlockLooper();
	}
}