📄 xm_api.c
字号:
/* * Mesa 3-D graphics library * Version: 6.5 * * Copyright (C) 1999-2006 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. *//* * This file contains the implementations of all the XMesa* functions. * * * NOTES: * * The window coordinate system origin (0,0) is in the lower-left corner * of the window. X11's window coordinate origin is in the upper-left * corner of the window. Therefore, most drawing functions in this * file have to flip Y coordinates. * * Define USE_XSHM in the Makefile with -DUSE_XSHM if you want to compile * in support for the MIT Shared Memory extension. If enabled, when you * use an Ximage for the back buffer in double buffered mode, the "swap" * operation will be faster. You must also link with -lXext. * * Byte swapping: If the Mesa host and the X display use a different * byte order then there's some trickiness to be aware of when using * XImages. The byte ordering used for the XImage is that of the X * display, not the Mesa host. * The color-to-pixel encoding for True/DirectColor must be done * according to the display's visual red_mask, green_mask, and blue_mask. * If XPutPixel is used to put a pixel into an XImage then XPutPixel will * do byte swapping if needed. If one wants to directly "poke" the pixel * into the XImage's buffer then the pixel must be byte swapped first. In * Mesa, when byte swapping is needed we use the PF_TRUECOLOR pixel format * and use XPutPixel everywhere except in the implementation of * glClear(GL_COLOR_BUFFER_BIT). We want this function to be fast so * instead of using XPutPixel we "poke" our values after byte-swapping * the clear pixel value if needed. * */#ifdef __CYGWIN__#undef WIN32#undef __WIN32__#endif#include "glxheader.h"#include "GL/xmesa.h"#include "xmesaP.h"#include "context.h"#include "extensions.h"#include "framebuffer.h"#include "glthread.h"#include "imports.h"#include "matrix.h"#include "mtypes.h"#include "macros.h"#include "renderbuffer.h"#include "texformat.h"#include "texobj.h"#include "texstore.h"#include "swrast/swrast.h"#include "swrast_setup/swrast_setup.h"#include "array_cache/acache.h"#include "tnl/tnl.h"#include "tnl/t_context.h"#include "tnl/t_pipeline.h"#include "drivers/common/driverfuncs.h"#ifdef XFree86Server#include <GL/glxtokens.h>#endif/* * Global X driver lock */_glthread_Mutex _xmesa_lock;/* * Lookup tables for HPCR pixel format: */static short hpcr_rgbTbl[3][256] = {{ 16, 16, 17, 17, 18, 18, 19, 19, 20, 20, 21, 21, 22, 22, 23, 23, 24, 24, 25, 25, 26, 26, 27, 27, 28, 28, 29, 29, 30, 30, 31, 31, 32, 32, 33, 33, 34, 34, 35, 35, 36, 36, 37, 37, 38, 38, 39, 39, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111,112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127,128, 129, 130, 131, 132, 133, 134, 135, 136, 137, 138, 139, 140, 141, 142, 143,144, 145, 146, 147, 148, 149, 150, 151, 152, 153, 154, 155, 156, 157, 158, 159,160, 161, 162, 163, 164, 165, 166, 167, 168, 169, 170, 171, 172, 173, 174, 175,176, 177, 178, 179, 180, 181, 182, 183, 184, 185, 186, 187, 188, 189, 190, 191,192, 193, 194, 195, 196, 197, 198, 199, 200, 201, 202, 203, 204, 205, 206, 207,208, 209, 210, 211, 212, 213, 214, 215, 216, 217, 218, 219, 220, 221, 222, 223,224, 225, 226, 227, 228, 229, 230, 231, 232, 233, 234, 235, 236, 237, 238, 239},{ 16, 16, 17, 17, 18, 18, 19, 19, 20, 20, 21, 21, 22, 22, 23, 23, 24, 24, 25, 25, 26, 26, 27, 27, 28, 28, 29, 29, 30, 30, 31, 31, 32, 32, 33, 33, 34, 34, 35, 35, 36, 36, 37, 37, 38, 38, 39, 39, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111,112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127,128, 129, 130, 131, 132, 133, 134, 135, 136, 137, 138, 139, 140, 141, 142, 143,144, 145, 146, 147, 148, 149, 150, 151, 152, 153, 154, 155, 156, 157, 158, 159,160, 161, 162, 163, 164, 165, 166, 167, 168, 169, 170, 171, 172, 173, 174, 175,176, 177, 178, 179, 180, 181, 182, 183, 184, 185, 186, 187, 188, 189, 190, 191,192, 193, 194, 195, 196, 197, 198, 199, 200, 201, 202, 203, 204, 205, 206, 207,208, 209, 210, 211, 212, 213, 214, 215, 216, 217, 218, 219, 220, 221, 222, 223,224, 225, 226, 227, 228, 229, 230, 231, 232, 233, 234, 235, 236, 237, 238, 239},{ 32, 32, 33, 33, 34, 34, 35, 35, 36, 36, 37, 37, 38, 38, 39, 39, 40, 40, 41, 41, 42, 42, 43, 43, 44, 44, 45, 45, 46, 46, 47, 47, 48, 48, 49, 49, 50, 50, 51, 51, 52, 52, 53, 53, 54, 54, 55, 55, 56, 56, 57, 57, 58, 58, 59, 59, 60, 60, 61, 61, 62, 62, 63, 63, 64, 64, 65, 65, 66, 66, 67, 67, 68, 68, 69, 69, 70, 70, 71, 71, 72, 72, 73, 73, 74, 74, 75, 75, 76, 76, 77, 77, 78, 78, 79, 79, 80, 80, 81, 81, 82, 82, 83, 83, 84, 84, 85, 85, 86, 86, 87, 87, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111,112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127,128, 129, 130, 131, 132, 133, 134, 135, 136, 137, 138, 139, 140, 141, 142, 143,144, 145, 146, 147, 148, 149, 150, 151, 152, 153, 154, 155, 156, 157, 158, 159,160, 161, 162, 163, 164, 165, 166, 167, 168, 169, 170, 171, 172, 173, 174, 175,176, 177, 178, 179, 180, 181, 182, 183, 184, 185, 186, 187, 188, 189, 190, 191,192, 193, 194, 195, 196, 197, 198, 199, 200, 201, 202, 203, 204, 205, 206, 207,208, 209, 210, 211, 212, 213, 214, 215, 216, 217, 218, 219, 220, 221, 222, 223}};/**********************************************************************//***** X Utility Functions *****//**********************************************************************//* * Return the host's byte order as LSBFirst or MSBFirst ala X. */#ifndef XFree86Serverstatic int host_byte_order( void ){ int i = 1; char *cptr = (char *) &i; return (*cptr==1) ? LSBFirst : MSBFirst;}#endif/* * Error handling. */#ifndef XFree86Serverstatic volatile int mesaXErrorFlag = 0;static int mesaHandleXError( XMesaDisplay *dpy, XErrorEvent *event ){ (void) dpy; (void) event; mesaXErrorFlag = 1; return 0;}#endif/* * Check if the X Shared Memory extension is available. * Return: 0 = not available * 1 = shared XImage support available * 2 = shared Pixmap support available also */static int check_for_xshm( XMesaDisplay *display ){#if defined(XFree86Server) return 0;#elif defined(USE_XSHM) int major, minor, ignore; Bool pixmaps; if (XQueryExtension( display, "MIT-SHM", &ignore, &ignore, &ignore )) { if (XShmQueryVersion( display, &major, &minor, &pixmaps )==True) { return (pixmaps==True) ? 2 : 1; } else { return 0; } } else { return 0; }#else /* No XSHM support */ return 0;#endif}/* * Apply gamma correction to an intensity value in [0..max]. Return the * new intensity value. */static GLint gamma_adjust( GLfloat gamma, GLint value, GLint max ){ if (gamma == 1.0) { return value; } else { double x = (double) value / (double) max; return IROUND_POS((GLfloat) max * _mesa_pow(x, 1.0F/gamma)); }}/* * Return the true number of bits per pixel for XImages. * For example, if we request a 24-bit deep visual we may actually need/get * 32bpp XImages. This function returns the appropriate bpp. * Input: dpy - the X display * visinfo - desribes the visual to be used for XImages * Return: true number of bits per pixel for XImages */#ifdef XFree86Serverstatic int bits_per_pixel( XMesaVisual xmv ){ const int depth = xmv->nplanes; int i; assert(depth > 0); for (i = 0; i < screenInfo.numPixmapFormats; i++) { if (screenInfo.formats[i].depth == depth) return screenInfo.formats[i].bitsPerPixel; } return depth; /* should never get here, but this should be safe */}#elsestatic int bits_per_pixel( XMesaVisual xmv ){ XMesaDisplay *dpy = xmv->display; XMesaVisualInfo visinfo = xmv->visinfo; XMesaImage *img; int bitsPerPixel; /* Create a temporary XImage */ img = XCreateImage( dpy, visinfo->visual, visinfo->depth, ZPixmap, 0, /*format, offset*/ (char*) MALLOC(8), /*data*/ 1, 1, /*width, height*/ 32, /*bitmap_pad*/ 0 /*bytes_per_line*/ ); assert(img); /* grab the bits/pixel value */ bitsPerPixel = img->bits_per_pixel; /* free the XImage */ _mesa_free( img->data ); img->data = NULL; XMesaDestroyImage( img ); return bitsPerPixel;}#endif/* * Determine if a given X window ID is valid (window exists). * Do this by calling XGetWindowAttributes() for the window and * checking if we catch an X error. * Input: dpy - the display * win - the window to check for existance * Return: GL_TRUE - window exists * GL_FALSE - window doesn't exist */#ifndef XFree86Serverstatic GLboolean WindowExistsFlag;static int window_exists_err_handler( XMesaDisplay* dpy, XErrorEvent* xerr ){ (void) dpy; if (xerr->error_code == BadWindow) { WindowExistsFlag = GL_FALSE; } return 0;}static GLboolean window_exists( XMesaDisplay *dpy, Window win ){ XWindowAttributes wa; int (*old_handler)( XMesaDisplay*, XErrorEvent* ); WindowExistsFlag = GL_TRUE; old_handler = XSetErrorHandler(window_exists_err_handler); XGetWindowAttributes( dpy, win, &wa ); /* dummy request */ XSetErrorHandler(old_handler); return WindowExistsFlag;}#endif/**********************************************************************//***** Linked list of XMesaBuffers *****//**********************************************************************/static XMesaBuffer XMesaBufferList = NULL;/** * Allocate a new XMesaBuffer, initialize basic fields and add to * the list of all buffers. */static XMesaBufferalloc_xmesa_buffer(XMesaVisual vis, BufferType type, XMesaColormap cmap){ XMesaBuffer b = (XMesaBuffer) CALLOC_STRUCT(xmesa_buffer); if (b) { GLboolean swAlpha; b->display = vis->display; b->xm_visual = vis; b->type = type; b->cmap = cmap; _mesa_initialize_framebuffer(&b->mesa_buffer, &vis->mesa_visual); /* Allocate the framebuffer's renderbuffers */ assert(!b->mesa_buffer.Attachment[BUFFER_FRONT_LEFT].Renderbuffer); assert(!b->mesa_buffer.Attachment[BUFFER_BACK_LEFT].Renderbuffer); /* front renderbuffer */ b->frontxrb = xmesa_new_renderbuffer(NULL, 0, &vis->mesa_visual, GL_FALSE); _mesa_add_renderbuffer(&b->mesa_buffer, BUFFER_FRONT_LEFT, &b->frontxrb->Base); /* back renderbuffer */ if (vis->mesa_visual.doubleBufferMode) { b->backxrb = xmesa_new_renderbuffer(NULL, 0, &vis->mesa_visual, GL_TRUE); /* 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); } /* determine if we need software alpha planes */ if (vis->mesa_visual.alphaBits > 0 && vis->undithered_pf != PF_8A8B8G8R && vis->undithered_pf != PF_8A8R8G8B) { /* Visual has alpha, but pixel format doesn't support it. * We'll use an alpha renderbuffer wrapper. */ swAlpha = GL_TRUE; } else { swAlpha = GL_FALSE; } _mesa_add_soft_renderbuffers(&b->mesa_buffer, GL_FALSE, /* color */ vis->mesa_visual.haveDepthBuffer, vis->mesa_visual.haveStencilBuffer, vis->mesa_visual.haveAccumBuffer, swAlpha, vis->mesa_visual.numAuxBuffers > 0 ); /* insert into linked list */ b->Next = XMesaBufferList; XMesaBufferList = b; } return b;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -