OSDN Git Service

intel/radeon: add common metaops code.
authorDave Airlie <airlied@redhat.com>
Tue, 14 Jul 2009 23:35:09 +0000 (09:35 +1000)
committerDave Airlie <airlied@redhat.com>
Wed, 15 Jul 2009 00:30:23 +0000 (10:30 +1000)
Move all the metaops to a dri_metaops file and port radeon/intel
to use the new common meta ops code.

18 files changed:
src/mesa/drivers/dri/Makefile.template
src/mesa/drivers/dri/common/dri_metaops.c [new file with mode: 0644]
src/mesa/drivers/dri/common/dri_metaops.h [new file with mode: 0644]
src/mesa/drivers/dri/intel/intel_clear.c
src/mesa/drivers/dri/intel/intel_context.c
src/mesa/drivers/dri/intel/intel_context.h
src/mesa/drivers/dri/intel/intel_generatemipmap.c
src/mesa/drivers/dri/intel/intel_pixel.c
src/mesa/drivers/dri/intel/intel_pixel.h
src/mesa/drivers/dri/intel/intel_pixel_bitmap.c
src/mesa/drivers/dri/intel/intel_pixel_draw.c
src/mesa/drivers/dri/r200/r200_ioctl.c
src/mesa/drivers/dri/r300/r300_ioctl.c
src/mesa/drivers/dri/radeon/radeon_common.c
src/mesa/drivers/dri/radeon/radeon_common.h
src/mesa/drivers/dri/radeon/radeon_common_context.c
src/mesa/drivers/dri/radeon/radeon_common_context.h
src/mesa/drivers/dri/radeon/radeon_ioctl.c

index bd38e3b..18dbeba 100644 (file)
@@ -11,7 +11,8 @@ COMMON_GALLIUM_SOURCES = \
 COMMON_SOURCES = $(COMMON_GALLIUM_SOURCES) \
         ../../common/driverfuncs.c \
         ../common/texmem.c \
-        ../common/drirenderbuffer.c
+        ../common/drirenderbuffer.c \
+       ../common/dri_metaops.c
 
 ifeq ($(WINDOW_SYSTEM),dri)
 WINOBJ=
diff --git a/src/mesa/drivers/dri/common/dri_metaops.c b/src/mesa/drivers/dri/common/dri_metaops.c
new file mode 100644 (file)
index 0000000..fe183c2
--- /dev/null
@@ -0,0 +1,541 @@
+/**************************************************************************
+ *
+ * Copyright 2006 Tungsten Graphics, Inc., Cedar Park, Texas.
+ * Copyright 2009 Intel Corporation.
+ * 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 above copyright notice and this permission notice (including the
+ * next paragraph) 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 NON-INFRINGEMENT.
+ * IN NO EVENT SHALL TUNGSTEN GRAPHICS 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.
+ *
+ **************************************************************************/
+
+#include "main/arrayobj.h"
+#include "main/attrib.h"
+#include "main/blend.h"
+#include "main/bufferobj.h"
+#include "main/buffers.h"
+#include "main/depth.h"
+#include "main/enable.h"
+#include "main/matrix.h"
+#include "main/macros.h"
+#include "main/polygon.h"
+#include "main/shaders.h"
+#include "main/stencil.h"
+#include "main/texstate.h"
+#include "main/varray.h"
+#include "main/viewport.h"
+#include "shader/arbprogram.h"
+#include "shader/program.h"
+#include "dri_metaops.h"
+
+void
+meta_set_passthrough_transform(struct dri_metaops *meta)
+{
+   GLcontext *ctx = meta->ctx;
+
+   meta->saved_vp_x = ctx->Viewport.X;
+   meta->saved_vp_y = ctx->Viewport.Y;
+   meta->saved_vp_width = ctx->Viewport.Width;
+   meta->saved_vp_height = ctx->Viewport.Height;
+   meta->saved_matrix_mode = ctx->Transform.MatrixMode;
+
+   meta->internal_viewport_call = GL_TRUE;
+   _mesa_Viewport(0, 0, ctx->DrawBuffer->Width, ctx->DrawBuffer->Height);
+   meta->internal_viewport_call = GL_FALSE;
+
+   _mesa_MatrixMode(GL_PROJECTION);
+   _mesa_PushMatrix();
+   _mesa_LoadIdentity();
+   _mesa_Ortho(0, ctx->DrawBuffer->Width, 0, ctx->DrawBuffer->Height, 1, -1);
+
+   _mesa_MatrixMode(GL_MODELVIEW);
+   _mesa_PushMatrix();
+   _mesa_LoadIdentity();
+}
+
+void
+meta_restore_transform(struct dri_metaops *meta)
+{
+   _mesa_MatrixMode(GL_PROJECTION);
+   _mesa_PopMatrix();
+   _mesa_MatrixMode(GL_MODELVIEW);
+   _mesa_PopMatrix();
+
+   _mesa_MatrixMode(meta->saved_matrix_mode);
+
+   meta->internal_viewport_call = GL_TRUE;
+   _mesa_Viewport(meta->saved_vp_x, meta->saved_vp_y,
+                 meta->saved_vp_width, meta->saved_vp_height);
+   meta->internal_viewport_call = GL_FALSE;
+}
+
+
+/**
+ * Set up a vertex program to pass through the position and first texcoord
+ * for pixel path.
+ */
+void
+meta_set_passthrough_vertex_program(struct dri_metaops *meta)
+{
+   GLcontext *ctx = meta->ctx;
+   static const char *vp =
+      "!!ARBvp1.0\n"
+      "TEMP vertexClip;\n"
+      "DP4 vertexClip.x, state.matrix.mvp.row[0], vertex.position;\n"
+      "DP4 vertexClip.y, state.matrix.mvp.row[1], vertex.position;\n"
+      "DP4 vertexClip.z, state.matrix.mvp.row[2], vertex.position;\n"
+      "DP4 vertexClip.w, state.matrix.mvp.row[3], vertex.position;\n"
+      "MOV result.position, vertexClip;\n"
+      "MOV result.texcoord[0], vertex.texcoord[0];\n"
+      "MOV result.color, vertex.color;\n"
+      "END\n";
+
+   assert(meta->saved_vp == NULL);
+
+   _mesa_reference_vertprog(ctx, &meta->saved_vp,
+                           ctx->VertexProgram.Current);
+   if (meta->passthrough_vp == NULL) {
+      GLuint prog_name;
+      _mesa_GenPrograms(1, &prog_name);
+      _mesa_BindProgram(GL_VERTEX_PROGRAM_ARB, prog_name);
+      _mesa_ProgramStringARB(GL_VERTEX_PROGRAM_ARB,
+                            GL_PROGRAM_FORMAT_ASCII_ARB,
+                            strlen(vp), (const GLubyte *)vp);
+      _mesa_reference_vertprog(ctx, &meta->passthrough_vp,
+                              ctx->VertexProgram.Current);
+      _mesa_DeletePrograms(1, &prog_name);
+   }
+
+   FLUSH_VERTICES(ctx, _NEW_PROGRAM);
+   _mesa_reference_vertprog(ctx, &ctx->VertexProgram.Current,
+                           meta->passthrough_vp);
+   ctx->Driver.BindProgram(ctx, GL_VERTEX_PROGRAM_ARB,
+                          &meta->passthrough_vp->Base);
+
+   meta->saved_vp_enable = ctx->VertexProgram.Enabled;
+   _mesa_Enable(GL_VERTEX_PROGRAM_ARB);
+}
+
+/**
+ * Restores the previous vertex program after
+ * meta_set_passthrough_vertex_program()
+ */
+void
+meta_restore_vertex_program(struct dri_metaops *meta)
+{
+   GLcontext *ctx = meta->ctx;
+
+   FLUSH_VERTICES(ctx, _NEW_PROGRAM);
+   _mesa_reference_vertprog(ctx, &ctx->VertexProgram.Current,
+                           meta->saved_vp);
+   _mesa_reference_vertprog(ctx, &meta->saved_vp, NULL);
+   ctx->Driver.BindProgram(ctx, GL_VERTEX_PROGRAM_ARB,
+                          &ctx->VertexProgram.Current->Base);
+
+   if (!meta->saved_vp_enable)
+      _mesa_Disable(GL_VERTEX_PROGRAM_ARB);
+}
+
+/**
+ * Binds the given program string to GL_FRAGMENT_PROGRAM_ARB, caching the
+ * program object.
+ */
+void
+meta_set_fragment_program(struct dri_metaops *meta,
+                         struct gl_fragment_program **prog,
+                         const char *prog_string)
+{
+   GLcontext *ctx = meta->ctx;
+   assert(meta->saved_fp == NULL);
+
+   _mesa_reference_fragprog(ctx, &meta->saved_fp,
+                           ctx->FragmentProgram.Current);
+   if (*prog == NULL) {
+      GLuint prog_name;
+      _mesa_GenPrograms(1, &prog_name);
+      _mesa_BindProgram(GL_FRAGMENT_PROGRAM_ARB, prog_name);
+      _mesa_ProgramStringARB(GL_FRAGMENT_PROGRAM_ARB,
+                            GL_PROGRAM_FORMAT_ASCII_ARB,
+                            strlen(prog_string), (const GLubyte *)prog_string);
+      _mesa_reference_fragprog(ctx, prog, ctx->FragmentProgram.Current);
+      /* Note that DeletePrograms unbinds the program on us */
+      _mesa_DeletePrograms(1, &prog_name);
+   }
+
+   FLUSH_VERTICES(ctx, _NEW_PROGRAM);
+   _mesa_reference_fragprog(ctx, &ctx->FragmentProgram.Current, *prog);
+   ctx->Driver.BindProgram(ctx, GL_FRAGMENT_PROGRAM_ARB, &((*prog)->Base));
+
+   meta->saved_fp_enable = ctx->FragmentProgram.Enabled;
+   _mesa_Enable(GL_FRAGMENT_PROGRAM_ARB);
+}
+
+/**
+ * Restores the previous fragment program after
+ * meta_set_fragment_program()
+ */
+void
+meta_restore_fragment_program(struct dri_metaops *meta)
+{
+   GLcontext *ctx = meta->ctx;
+
+   FLUSH_VERTICES(ctx, _NEW_PROGRAM);
+   _mesa_reference_fragprog(ctx, &ctx->FragmentProgram.Current,
+                           meta->saved_fp);
+   _mesa_reference_fragprog(ctx, &meta->saved_fp, NULL);
+   ctx->Driver.BindProgram(ctx, GL_FRAGMENT_PROGRAM_ARB,
+                          &ctx->FragmentProgram.Current->Base);
+
+   if (!meta->saved_fp_enable)
+      _mesa_Disable(GL_FRAGMENT_PROGRAM_ARB);
+}
+
+static const float default_texcoords[4][2] = { { 0.0, 0.0 },
+                                              { 1.0, 0.0 },
+                                              { 1.0, 1.0 },
+                                              { 0.0, 1.0 } };
+
+void
+meta_set_default_texrect(struct dri_metaops *meta)
+{
+   GLcontext *ctx = meta->ctx;
+   struct gl_client_array *old_texcoord_array;
+
+   meta->saved_active_texture = ctx->Texture.CurrentUnit;
+   if (meta->saved_array_vbo == NULL) {
+      _mesa_reference_buffer_object(ctx, &meta->saved_array_vbo,
+                                   ctx->Array.ArrayBufferObj);
+   }
+
+   old_texcoord_array = &ctx->Array.ArrayObj->TexCoord[0];
+   meta->saved_texcoord_type = old_texcoord_array->Type;
+   meta->saved_texcoord_size = old_texcoord_array->Size;
+   meta->saved_texcoord_stride = old_texcoord_array->Stride;
+   meta->saved_texcoord_enable = old_texcoord_array->Enabled;
+   meta->saved_texcoord_ptr = old_texcoord_array->Ptr;
+   _mesa_reference_buffer_object(ctx, &meta->saved_texcoord_vbo,
+                                old_texcoord_array->BufferObj);
+
+   _mesa_ClientActiveTextureARB(GL_TEXTURE0);
+
+   if (meta->texcoord_vbo == NULL) {
+      GLuint vbo_name;
+
+      _mesa_GenBuffersARB(1, &vbo_name);
+      _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB, vbo_name);
+      _mesa_BufferDataARB(GL_ARRAY_BUFFER_ARB, sizeof(default_texcoords),
+                         default_texcoords, GL_STATIC_DRAW_ARB);
+      _mesa_reference_buffer_object(ctx, &meta->texcoord_vbo,
+                                   ctx->Array.ArrayBufferObj);
+   } else {
+      _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB,
+                         meta->texcoord_vbo->Name);
+   }
+   _mesa_TexCoordPointer(2, GL_FLOAT, 2 * sizeof(GLfloat), NULL);
+
+   _mesa_Enable(GL_TEXTURE_COORD_ARRAY);
+}
+
+void
+meta_restore_texcoords(struct dri_metaops *meta)
+{
+   GLcontext *ctx = meta->ctx;
+
+   /* Restore the old TexCoordPointer */
+   if (meta->saved_texcoord_vbo) {
+      _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB,
+                         meta->saved_texcoord_vbo->Name);
+      _mesa_reference_buffer_object(ctx, &meta->saved_texcoord_vbo, NULL);
+   } else {
+      _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
+   }
+
+   _mesa_TexCoordPointer(meta->saved_texcoord_size,
+                        meta->saved_texcoord_type,
+                        meta->saved_texcoord_stride,
+                        meta->saved_texcoord_ptr);
+   if (!meta->saved_texcoord_enable)
+      _mesa_Disable(GL_TEXTURE_COORD_ARRAY);
+
+   _mesa_ClientActiveTextureARB(GL_TEXTURE0 +
+                               meta->saved_active_texture);
+
+   if (meta->saved_array_vbo) {
+      _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB,
+                         meta->saved_array_vbo->Name);
+      _mesa_reference_buffer_object(ctx, &meta->saved_array_vbo, NULL);
+   } else {
+      _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
+   }
+}
+
+
+/**
+ * Perform glClear where mask contains only color, depth, and/or stencil.
+ *
+ * The implementation is based on calling into Mesa to set GL state and
+ * performing normal triangle rendering.  The intent of this path is to
+ * have as generic a path as possible, so that any driver could make use of
+ * it.
+ */
+
+/**
+ * Per-context one-time init of things for intl_clear_tris().
+ * Basically set up a private array object for vertex/color arrays.
+ */
+static void
+meta_init_clear(struct dri_metaops *meta)
+{
+   GLcontext *ctx = meta->ctx;
+   struct gl_array_object *arraySave = NULL;
+   const GLuint arrayBuffer = ctx->Array.ArrayBufferObj->Name;
+   const GLuint elementBuffer = ctx->Array.ElementArrayBufferObj->Name;
+
+   /* create new array object */
+   meta->clear.arrayObj = _mesa_new_array_object(ctx, ~0);
+
+   /* save current array object, bind new one */
+   _mesa_reference_array_object(ctx, &arraySave, ctx->Array.ArrayObj);
+   ctx->NewState |= _NEW_ARRAY;
+   ctx->Array.NewState |= _NEW_ARRAY_ALL;
+   _mesa_reference_array_object(ctx, &ctx->Array.ArrayObj, meta->clear.arrayObj);
+
+   /* one-time setup of vertex arrays (pos, color) */
+   _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
+   _mesa_BindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, 0);
+   _mesa_ColorPointer(4, GL_FLOAT, 4 * sizeof(GLfloat), meta->clear.color);
+   _mesa_VertexPointer(3, GL_FLOAT, 3 * sizeof(GLfloat), meta->clear.vertices);
+   _mesa_Enable(GL_COLOR_ARRAY);
+   _mesa_Enable(GL_VERTEX_ARRAY);
+
+   /* restore original array object */
+   ctx->NewState |= _NEW_ARRAY;
+   ctx->Array.NewState |= _NEW_ARRAY_ALL;
+   _mesa_reference_array_object(ctx, &ctx->Array.ArrayObj, arraySave);
+   _mesa_reference_array_object(ctx, &arraySave, NULL);
+
+   /* restore original buffer objects */
+   _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB, arrayBuffer);
+   _mesa_BindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, elementBuffer);
+}
+
+
+
+/**
+ * Perform glClear where mask contains only color, depth, and/or stencil.
+ *
+ * The implementation is based on calling into Mesa to set GL state and
+ * performing normal triangle rendering.  The intent of this path is to
+ * have as generic a path as possible, so that any driver could make use of
+ * it.
+ */
+void
+meta_clear_tris(struct dri_metaops *meta, GLbitfield mask)
+{
+   GLcontext *ctx = meta->ctx;
+   GLfloat dst_z;
+   struct gl_framebuffer *fb = ctx->DrawBuffer;
+   int i;
+   GLboolean saved_fp_enable = GL_FALSE, saved_vp_enable = GL_FALSE;
+   GLuint saved_shader_program = 0;
+   unsigned int saved_active_texture;
+   struct gl_array_object *arraySave = NULL;
+
+   if (!meta->clear.arrayObj)
+      meta_init_clear(meta);
+
+   assert((mask & ~(TRI_CLEAR_COLOR_BITS | BUFFER_BIT_DEPTH |
+                   BUFFER_BIT_STENCIL)) == 0);
+
+   _mesa_PushAttrib(GL_COLOR_BUFFER_BIT |
+                   GL_DEPTH_BUFFER_BIT |
+                   GL_ENABLE_BIT |
+                   GL_POLYGON_BIT |
+                   GL_STENCIL_BUFFER_BIT |
+                   GL_TRANSFORM_BIT |
+                   GL_CURRENT_BIT |
+                   GL_VIEWPORT_BIT);
+   saved_active_texture = ctx->Texture.CurrentUnit;
+
+   /* Disable existing GL state we don't want to apply to a clear. */
+   _mesa_Disable(GL_ALPHA_TEST);
+   _mesa_Disable(GL_BLEND);
+   _mesa_Disable(GL_CULL_FACE);
+   _mesa_Disable(GL_FOG);
+   _mesa_Disable(GL_POLYGON_SMOOTH);
+   _mesa_Disable(GL_POLYGON_STIPPLE);
+   _mesa_Disable(GL_POLYGON_OFFSET_FILL);
+   _mesa_Disable(GL_LIGHTING);
+   _mesa_Disable(GL_CLIP_PLANE0);
+   _mesa_Disable(GL_CLIP_PLANE1);
+   _mesa_Disable(GL_CLIP_PLANE2);
+   _mesa_Disable(GL_CLIP_PLANE3);
+   _mesa_Disable(GL_CLIP_PLANE4);
+   _mesa_Disable(GL_CLIP_PLANE5);
+   _mesa_PolygonMode(GL_FRONT_AND_BACK, GL_FILL);
+   if (ctx->Extensions.ARB_fragment_program && ctx->FragmentProgram.Enabled) {
+      saved_fp_enable = GL_TRUE;
+      _mesa_Disable(GL_FRAGMENT_PROGRAM_ARB);
+   }
+   if (ctx->Extensions.ARB_vertex_program && ctx->VertexProgram.Enabled) {
+      saved_vp_enable = GL_TRUE;
+      _mesa_Disable(GL_VERTEX_PROGRAM_ARB);
+   }
+   if (ctx->Extensions.ARB_shader_objects && ctx->Shader.CurrentProgram) {
+      saved_shader_program = ctx->Shader.CurrentProgram->Name;
+      _mesa_UseProgramObjectARB(0);
+   }
+
+   if (ctx->Texture._EnabledUnits != 0) {
+      int i;
+
+      for (i = 0; i < ctx->Const.MaxTextureUnits; i++) {
+        _mesa_ActiveTextureARB(GL_TEXTURE0 + i);
+        _mesa_Disable(GL_TEXTURE_1D);
+        _mesa_Disable(GL_TEXTURE_2D);
+        _mesa_Disable(GL_TEXTURE_3D);
+        if (ctx->Extensions.ARB_texture_cube_map)
+           _mesa_Disable(GL_TEXTURE_CUBE_MAP_ARB);
+        if (ctx->Extensions.NV_texture_rectangle)
+           _mesa_Disable(GL_TEXTURE_RECTANGLE_NV);
+        if (ctx->Extensions.MESA_texture_array) {
+           _mesa_Disable(GL_TEXTURE_1D_ARRAY_EXT);
+           _mesa_Disable(GL_TEXTURE_2D_ARRAY_EXT);
+        }
+      }
+   }
+
+   /* save current array object, bind our private one */
+   _mesa_reference_array_object(ctx, &arraySave, ctx->Array.ArrayObj);
+   ctx->NewState |= _NEW_ARRAY;
+   ctx->Array.NewState |= _NEW_ARRAY_ALL;
+   _mesa_reference_array_object(ctx, &ctx->Array.ArrayObj, meta->clear.arrayObj);
+
+   meta_set_passthrough_transform(meta);
+
+   for (i = 0; i < 4; i++) {
+      COPY_4FV(meta->clear.color[i], ctx->Color.ClearColor);
+   }
+
+   /* convert clear Z from [0,1] to NDC coord in [-1,1] */
+   dst_z = -1.0 + 2.0 * ctx->Depth.Clear;
+
+   /* The ClearDepth value is unaffected by DepthRange, so do a default
+    * mapping.
+    */
+   _mesa_DepthRange(0.0, 1.0);
+
+   /* Prepare the vertices, which are the same regardless of which buffer we're
+    * drawing to.
+    */
+   meta->clear.vertices[0][0] = fb->_Xmin;
+   meta->clear.vertices[0][1] = fb->_Ymin;
+   meta->clear.vertices[0][2] = dst_z;
+   meta->clear.vertices[1][0] = fb->_Xmax;
+   meta->clear.vertices[1][1] = fb->_Ymin;
+   meta->clear.vertices[1][2] = dst_z;
+   meta->clear.vertices[2][0] = fb->_Xmax;
+   meta->clear.vertices[2][1] = fb->_Ymax;
+   meta->clear.vertices[2][2] = dst_z;
+   meta->clear.vertices[3][0] = fb->_Xmin;
+   meta->clear.vertices[3][1] = fb->_Ymax;
+   meta->clear.vertices[3][2] = dst_z;
+
+   while (mask != 0) {
+      GLuint this_mask = 0;
+      GLuint color_bit;
+
+      color_bit = _mesa_ffs(mask & TRI_CLEAR_COLOR_BITS);
+      if (color_bit != 0)
+        this_mask |= (1 << (color_bit - 1));
+
+      /* Clear depth/stencil in the same pass as color. */
+      this_mask |= (mask & (BUFFER_BIT_DEPTH | BUFFER_BIT_STENCIL));
+
+      /* Select the current color buffer and use the color write mask if
+       * we have one, otherwise don't write any color channels.
+       */
+      if (this_mask & BUFFER_BIT_FRONT_LEFT)
+        _mesa_DrawBuffer(GL_FRONT_LEFT);
+      else if (this_mask & BUFFER_BIT_BACK_LEFT)
+        _mesa_DrawBuffer(GL_BACK_LEFT);
+      else if (color_bit != 0)
+        _mesa_DrawBuffer(GL_COLOR_ATTACHMENT0 +
+                         (color_bit - BUFFER_COLOR0 - 1));
+      else
+        _mesa_ColorMask(GL_FALSE, GL_FALSE, GL_FALSE, GL_FALSE);
+
+      /* Control writing of the depth clear value to depth. */
+      if (this_mask & BUFFER_BIT_DEPTH) {
+        _mesa_DepthFunc(GL_ALWAYS);
+        _mesa_Enable(GL_DEPTH_TEST);
+      } else {
+        _mesa_Disable(GL_DEPTH_TEST);
+        _mesa_DepthMask(GL_FALSE);
+      }
+
+      /* Control writing of the stencil clear value to stencil. */
+      if (this_mask & BUFFER_BIT_STENCIL) {
+        _mesa_Enable(GL_STENCIL_TEST);
+        _mesa_StencilOpSeparate(GL_FRONT_AND_BACK,
+                                GL_REPLACE, GL_REPLACE, GL_REPLACE);
+        _mesa_StencilFuncSeparate(GL_FRONT_AND_BACK, GL_ALWAYS,
+                                  ctx->Stencil.Clear & 0x7fffffff,
+                                  ctx->Stencil.WriteMask[0]);
+      } else {
+        _mesa_Disable(GL_STENCIL_TEST);
+      }
+
+      _mesa_DrawArrays(GL_TRIANGLE_FAN, 0, 4);
+
+      mask &= ~this_mask;
+   }
+
+   meta_restore_transform(meta);
+
+   _mesa_ActiveTextureARB(GL_TEXTURE0 + saved_active_texture);
+   if (saved_fp_enable)
+      _mesa_Enable(GL_FRAGMENT_PROGRAM_ARB);
+   if (saved_vp_enable)
+      _mesa_Enable(GL_VERTEX_PROGRAM_ARB);
+
+   if (saved_shader_program)
+      _mesa_UseProgramObjectARB(saved_shader_program);
+
+   _mesa_PopAttrib();
+
+   /* restore current array object */
+   ctx->NewState |= _NEW_ARRAY;
+   ctx->Array.NewState |= _NEW_ARRAY_ALL;
+   _mesa_reference_array_object(ctx, &ctx->Array.ArrayObj, arraySave);
+   _mesa_reference_array_object(ctx, &arraySave, NULL);
+}
+
+void meta_init_metaops(GLcontext *ctx, struct dri_metaops *meta)
+{
+   meta->ctx = ctx;
+}
+
+void meta_destroy_metaops(struct dri_metaops *meta)
+{
+  if (meta->clear.arrayObj)
+    _mesa_delete_array_object(meta->ctx, meta->clear.arrayObj);
+
+}
diff --git a/src/mesa/drivers/dri/common/dri_metaops.h b/src/mesa/drivers/dri/common/dri_metaops.h
new file mode 100644 (file)
index 0000000..bb4079d
--- /dev/null
@@ -0,0 +1,99 @@
+/**************************************************************************
+ *
+ * Copyright 2006 Tungsten Graphics, Inc., Cedar Park, Texas.
+ * Copyright 2009 Intel Corporation.
+ * 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 above copyright notice and this permission notice (including the
+ * next paragraph) 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 NON-INFRINGEMENT.
+ * IN NO EVENT SHALL TUNGSTEN GRAPHICS 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.
+ *
+ **************************************************************************/
+#ifndef DRI_METAOPS_H
+#define DRI_METAOPS_H
+
+#define TRI_CLEAR_COLOR_BITS (BUFFER_BIT_BACK_LEFT |                   \
+                             BUFFER_BIT_FRONT_LEFT |                   \
+                             BUFFER_BIT_COLOR0 |                       \
+                             BUFFER_BIT_COLOR1 |                       \
+                             BUFFER_BIT_COLOR2 |                       \
+                             BUFFER_BIT_COLOR3 |                       \
+                             BUFFER_BIT_COLOR4 |                       \
+                             BUFFER_BIT_COLOR5 |                       \
+                             BUFFER_BIT_COLOR6 |                       \
+                             BUFFER_BIT_COLOR7)
+
+struct dri_meta_clear {
+    struct gl_array_object *arrayObj;
+    GLfloat vertices[4][3];
+    GLfloat color[4][4];
+};
+
+struct dri_metaops {
+    GLcontext *ctx;
+    GLboolean internal_viewport_call;
+    struct gl_fragment_program *bitmap_fp;
+    struct gl_vertex_program *passthrough_vp;
+    struct gl_buffer_object *texcoord_vbo;
+    
+    struct gl_fragment_program *saved_fp;
+    GLboolean saved_fp_enable;
+    struct gl_vertex_program *saved_vp;
+    GLboolean saved_vp_enable;
+
+    struct gl_fragment_program *tex2d_fp;
+    
+    GLboolean saved_texcoord_enable;
+    struct gl_buffer_object *saved_array_vbo, *saved_texcoord_vbo;
+    GLenum saved_texcoord_type;
+    GLsizei saved_texcoord_size, saved_texcoord_stride;
+    const void *saved_texcoord_ptr;
+    int saved_active_texture;
+
+    GLint saved_vp_x, saved_vp_y;
+    GLsizei saved_vp_width, saved_vp_height;
+    GLenum saved_matrix_mode;
+    
+    struct dri_meta_clear clear;
+};
+
+
+void meta_set_passthrough_transform(struct dri_metaops *meta);
+
+void meta_restore_transform(struct dri_metaops *meta);
+
+void meta_set_passthrough_vertex_program(struct dri_metaops *meta);
+
+void meta_restore_vertex_program(struct dri_metaops *meta);
+
+void meta_set_fragment_program(struct dri_metaops *meta,
+                         struct gl_fragment_program **prog,
+                         const char *prog_string);
+
+void meta_restore_fragment_program(struct dri_metaops *meta);
+
+void meta_set_default_texrect(struct dri_metaops *meta);
+
+void meta_restore_texcoords(struct dri_metaops *meta);
+void meta_clear_tris(struct dri_metaops *meta, GLbitfield mask);
+
+void meta_init_metaops(GLcontext *ctx, struct dri_metaops *meta);
+void meta_destroy_metaops(struct dri_metaops *meta);
+#endif
+
index 13b433d..cfddabd 100644 (file)
 
 #define FILE_DEBUG_FLAG DEBUG_BLIT
 
-#define TRI_CLEAR_COLOR_BITS (BUFFER_BIT_BACK_LEFT |                   \
-                             BUFFER_BIT_FRONT_LEFT |                   \
-                             BUFFER_BIT_COLOR0 |                       \
-                             BUFFER_BIT_COLOR1 |                       \
-                             BUFFER_BIT_COLOR2 |                       \
-                             BUFFER_BIT_COLOR3 |                       \
-                             BUFFER_BIT_COLOR4 |                       \
-                             BUFFER_BIT_COLOR5 |                       \
-                             BUFFER_BIT_COLOR6 |                       \
-                             BUFFER_BIT_COLOR7)
-
-
-/**
- * Per-context one-time init of things for intl_clear_tris().
- * Basically set up a private array object for vertex/color arrays.
- */
-static void
-init_clear(GLcontext *ctx)
-{
-   struct intel_context *intel = intel_context(ctx);
-   struct gl_array_object *arraySave = NULL;
-   const GLuint arrayBuffer = ctx->Array.ArrayBufferObj->Name;
-   const GLuint elementBuffer = ctx->Array.ElementArrayBufferObj->Name;
-
-   /* create new array object */
-   intel->clear.arrayObj = _mesa_new_array_object(ctx, ~0);
-
-   /* save current array object, bind new one */
-   _mesa_reference_array_object(ctx, &arraySave, ctx->Array.ArrayObj);
-   ctx->NewState |= _NEW_ARRAY;
-   ctx->Array.NewState |= _NEW_ARRAY_ALL;
-   _mesa_reference_array_object(ctx, &ctx->Array.ArrayObj, intel->clear.arrayObj);
-
-   /* one-time setup of vertex arrays (pos, color) */
-   _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
-   _mesa_BindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, 0);
-   _mesa_ColorPointer(4, GL_FLOAT, 4 * sizeof(GLfloat), intel->clear.color);
-   _mesa_VertexPointer(3, GL_FLOAT, 3 * sizeof(GLfloat), intel->clear.vertices);
-   _mesa_Enable(GL_COLOR_ARRAY);
-   _mesa_Enable(GL_VERTEX_ARRAY);
-
-   /* restore original array object */
-   ctx->NewState |= _NEW_ARRAY;
-   ctx->Array.NewState |= _NEW_ARRAY_ALL;
-   _mesa_reference_array_object(ctx, &ctx->Array.ArrayObj, arraySave);
-   _mesa_reference_array_object(ctx, &arraySave, NULL);
-
-   /* restore original buffer objects */
-   _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB, arrayBuffer);
-   _mesa_BindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, elementBuffer);
-}
-
-
-
-/**
- * Perform glClear where mask contains only color, depth, and/or stencil.
- *
- * The implementation is based on calling into Mesa to set GL state and
- * performing normal triangle rendering.  The intent of this path is to
- * have as generic a path as possible, so that any driver could make use of
- * it.
- */
-void
-intel_clear_tris(GLcontext *ctx, GLbitfield mask)
-{
-   struct intel_context *intel = intel_context(ctx);
-   GLfloat dst_z;
-   struct gl_framebuffer *fb = ctx->DrawBuffer;
-   int i;
-   GLboolean saved_fp_enable = GL_FALSE, saved_vp_enable = GL_FALSE;
-   GLuint saved_shader_program = 0;
-   unsigned int saved_active_texture;
-   struct gl_array_object *arraySave = NULL;
-
-   if (!intel->clear.arrayObj)
-      init_clear(ctx);
-
-   assert((mask & ~(TRI_CLEAR_COLOR_BITS | BUFFER_BIT_DEPTH |
-                   BUFFER_BIT_STENCIL)) == 0);
-
-   _mesa_PushAttrib(GL_COLOR_BUFFER_BIT |
-                   GL_DEPTH_BUFFER_BIT |
-                   GL_ENABLE_BIT |
-                   GL_POLYGON_BIT |
-                   GL_STENCIL_BUFFER_BIT |
-                   GL_TRANSFORM_BIT |
-                   GL_CURRENT_BIT |
-                   GL_VIEWPORT_BIT);
-   saved_active_texture = ctx->Texture.CurrentUnit;
-
-   /* Disable existing GL state we don't want to apply to a clear. */
-   _mesa_Disable(GL_ALPHA_TEST);
-   _mesa_Disable(GL_BLEND);
-   _mesa_Disable(GL_CULL_FACE);
-   _mesa_Disable(GL_FOG);
-   _mesa_Disable(GL_POLYGON_SMOOTH);
-   _mesa_Disable(GL_POLYGON_STIPPLE);
-   _mesa_Disable(GL_POLYGON_OFFSET_FILL);
-   _mesa_Disable(GL_LIGHTING);
-   _mesa_Disable(GL_CLIP_PLANE0);
-   _mesa_Disable(GL_CLIP_PLANE1);
-   _mesa_Disable(GL_CLIP_PLANE2);
-   _mesa_Disable(GL_CLIP_PLANE3);
-   _mesa_Disable(GL_CLIP_PLANE4);
-   _mesa_Disable(GL_CLIP_PLANE5);
-   _mesa_PolygonMode(GL_FRONT_AND_BACK, GL_FILL);
-   if (ctx->Extensions.ARB_fragment_program && ctx->FragmentProgram.Enabled) {
-      saved_fp_enable = GL_TRUE;
-      _mesa_Disable(GL_FRAGMENT_PROGRAM_ARB);
-   }
-   if (ctx->Extensions.ARB_vertex_program && ctx->VertexProgram.Enabled) {
-      saved_vp_enable = GL_TRUE;
-      _mesa_Disable(GL_VERTEX_PROGRAM_ARB);
-   }
-   if (ctx->Extensions.ARB_shader_objects && ctx->Shader.CurrentProgram) {
-      saved_shader_program = ctx->Shader.CurrentProgram->Name;
-      _mesa_UseProgramObjectARB(0);
-   }
-
-   if (ctx->Texture._EnabledUnits != 0) {
-      int i;
-
-      for (i = 0; i < ctx->Const.MaxTextureUnits; i++) {
-        _mesa_ActiveTextureARB(GL_TEXTURE0 + i);
-        _mesa_Disable(GL_TEXTURE_1D);
-        _mesa_Disable(GL_TEXTURE_2D);
-        _mesa_Disable(GL_TEXTURE_3D);
-        if (ctx->Extensions.ARB_texture_cube_map)
-           _mesa_Disable(GL_TEXTURE_CUBE_MAP_ARB);
-        if (ctx->Extensions.NV_texture_rectangle)
-           _mesa_Disable(GL_TEXTURE_RECTANGLE_NV);
-        if (ctx->Extensions.MESA_texture_array) {
-           _mesa_Disable(GL_TEXTURE_1D_ARRAY_EXT);
-           _mesa_Disable(GL_TEXTURE_2D_ARRAY_EXT);
-        }
-      }
-   }
-
-   /* save current array object, bind our private one */
-   _mesa_reference_array_object(ctx, &arraySave, ctx->Array.ArrayObj);
-   ctx->NewState |= _NEW_ARRAY;
-   ctx->Array.NewState |= _NEW_ARRAY_ALL;
-   _mesa_reference_array_object(ctx, &ctx->Array.ArrayObj, intel->clear.arrayObj);
-
-   intel_meta_set_passthrough_transform(intel);
-
-   for (i = 0; i < 4; i++) {
-      COPY_4FV(intel->clear.color[i], ctx->Color.ClearColor);
-   }
-
-   /* convert clear Z from [0,1] to NDC coord in [-1,1] */
-   dst_z = -1.0 + 2.0 * ctx->Depth.Clear;
-
-   /* The ClearDepth value is unaffected by DepthRange, so do a default
-    * mapping.
-    */
-   _mesa_DepthRange(0.0, 1.0);
-
-   /* Prepare the vertices, which are the same regardless of which buffer we're
-    * drawing to.
-    */
-   intel->clear.vertices[0][0] = fb->_Xmin;
-   intel->clear.vertices[0][1] = fb->_Ymin;
-   intel->clear.vertices[0][2] = dst_z;
-   intel->clear.vertices[1][0] = fb->_Xmax;
-   intel->clear.vertices[1][1] = fb->_Ymin;
-   intel->clear.vertices[1][2] = dst_z;
-   intel->clear.vertices[2][0] = fb->_Xmax;
-   intel->clear.vertices[2][1] = fb->_Ymax;
-   intel->clear.vertices[2][2] = dst_z;
-   intel->clear.vertices[3][0] = fb->_Xmin;
-   intel->clear.vertices[3][1] = fb->_Ymax;
-   intel->clear.vertices[3][2] = dst_z;
-
-   while (mask != 0) {
-      GLuint this_mask = 0;
-      GLuint color_bit;
-
-      color_bit = _mesa_ffs(mask & TRI_CLEAR_COLOR_BITS);
-      if (color_bit != 0)
-        this_mask |= (1 << (color_bit - 1));
-
-      /* Clear depth/stencil in the same pass as color. */
-      this_mask |= (mask & (BUFFER_BIT_DEPTH | BUFFER_BIT_STENCIL));
-
-      /* Select the current color buffer and use the color write mask if
-       * we have one, otherwise don't write any color channels.
-       */
-      if (this_mask & BUFFER_BIT_FRONT_LEFT)
-        _mesa_DrawBuffer(GL_FRONT_LEFT);
-      else if (this_mask & BUFFER_BIT_BACK_LEFT)
-        _mesa_DrawBuffer(GL_BACK_LEFT);
-      else if (color_bit != 0)
-        _mesa_DrawBuffer(GL_COLOR_ATTACHMENT0 +
-                         (color_bit - BUFFER_COLOR0 - 1));
-      else
-        _mesa_ColorMask(GL_FALSE, GL_FALSE, GL_FALSE, GL_FALSE);
-
-      /* Control writing of the depth clear value to depth. */
-      if (this_mask & BUFFER_BIT_DEPTH) {
-        _mesa_DepthFunc(GL_ALWAYS);
-        _mesa_Enable(GL_DEPTH_TEST);
-      } else {
-        _mesa_Disable(GL_DEPTH_TEST);
-        _mesa_DepthMask(GL_FALSE);
-      }
-
-      /* Control writing of the stencil clear value to stencil. */
-      if (this_mask & BUFFER_BIT_STENCIL) {
-        _mesa_Enable(GL_STENCIL_TEST);
-        _mesa_StencilOpSeparate(GL_FRONT_AND_BACK,
-                                GL_REPLACE, GL_REPLACE, GL_REPLACE);
-        _mesa_StencilFuncSeparate(GL_FRONT_AND_BACK, GL_ALWAYS,
-                                  ctx->Stencil.Clear,
-                                  ctx->Stencil.WriteMask[0]);
-      } else {
-        _mesa_Disable(GL_STENCIL_TEST);
-      }
-
-      _mesa_DrawArrays(GL_TRIANGLE_FAN, 0, 4);
-
-      mask &= ~this_mask;
-   }
-
-   intel_meta_restore_transform(intel);
-
-   _mesa_ActiveTextureARB(GL_TEXTURE0 + saved_active_texture);
-   if (saved_fp_enable)
-      _mesa_Enable(GL_FRAGMENT_PROGRAM_ARB);
-   if (saved_vp_enable)
-      _mesa_Enable(GL_VERTEX_PROGRAM_ARB);
-
-   if (saved_shader_program)
-      _mesa_UseProgramObjectARB(saved_shader_program);
-
-   _mesa_PopAttrib();
-
-   /* restore current array object */
-   ctx->NewState |= _NEW_ARRAY;
-   ctx->Array.NewState |= _NEW_ARRAY_ALL;
-   _mesa_reference_array_object(ctx, &ctx->Array.ArrayObj, arraySave);
-   _mesa_reference_array_object(ctx, &arraySave, NULL);
-}
-
 static const char *buffer_names[] = {
    [BUFFER_FRONT_LEFT] = "front",
    [BUFFER_BACK_LEFT] = "back",
@@ -326,6 +82,7 @@ static const char *buffer_names[] = {
 static void
 intelClear(GLcontext *ctx, GLbitfield mask)
 {
+   struct intel_context *intel = intel_context(ctx);
    const GLuint colorMask = *((GLuint *) & ctx->Color.ColorMask);
    GLbitfield tri_mask = 0;
    GLbitfield blit_mask = 0;
@@ -425,7 +182,7 @@ intelClear(GLcontext *ctx, GLbitfield mask)
         }
         DBG("\n");
       }
-      intel_clear_tris(ctx, tri_mask);
+      meta_clear_tris(&intel->meta, tri_mask);
    }
 
    if (swrast_mask) {
index edf422c..4abb525 100644 (file)
@@ -404,7 +404,7 @@ intel_viewport(GLcontext *ctx, GLint x, GLint y, GLsizei w, GLsizei h)
     if (!driContext->driScreenPriv->dri2.enabled)
        return;
 
-    if (!intel->internal_viewport_call && ctx->DrawBuffer->Name == 0) {
+    if (!intel->meta.internal_viewport_call && ctx->DrawBuffer->Name == 0) {
        /* If we're rendering to the fake front buffer, make sure all the pending
        * drawing has landed on the real front buffer.  Otherwise when we
        * eventually get to DRI2GetBuffersWithFormat the stale real front
@@ -672,6 +672,7 @@ intelInitContext(struct intel_context *intel,
     */
    _mesa_init_point(ctx);
 
+   meta_init_metaops(ctx, &intel->meta);
    ctx->Const.MaxColorAttachments = 4;  /* XXX FBO: review this */
    if (IS_965(intelScreen->deviceID)) {
       if (MAX_WIDTH > 8192)
@@ -794,8 +795,7 @@ intelDestroyContext(__DRIcontextPrivate * driContextPriv)
 
       INTEL_FIREVERTICES(intel);
 
-      if (intel->clear.arrayObj)
-         _mesa_delete_array_object(&intel->ctx, intel->clear.arrayObj);
+      meta_destroy_metaops(&intel->meta);
 
       intel->vtbl.destroy(intel);
 
index 6761193..08bea88 100644 (file)
@@ -33,6 +33,7 @@
 #include "main/mtypes.h"
 #include "main/mm.h"
 #include "texmem.h"
+#include "dri_metaops.h"
 #include "drm.h"
 #include "intel_bufmgr.h"
 
@@ -157,29 +158,7 @@ struct intel_context
       void (*debug_batch)(struct intel_context *intel);
    } vtbl;
 
-   struct {
-      struct gl_fragment_program *bitmap_fp;
-      struct gl_vertex_program *passthrough_vp;
-      struct gl_buffer_object *texcoord_vbo;
-
-      struct gl_fragment_program *saved_fp;
-      GLboolean saved_fp_enable;
-      struct gl_vertex_program *saved_vp;
-      GLboolean saved_vp_enable;
-
-      struct gl_fragment_program *tex2d_fp;
-
-      GLboolean saved_texcoord_enable;
-      struct gl_buffer_object *saved_array_vbo, *saved_texcoord_vbo;
-      GLenum saved_texcoord_type;
-      GLsizei saved_texcoord_size, saved_texcoord_stride;
-      const void *saved_texcoord_ptr;
-      int saved_active_texture;
-
-      GLint saved_vp_x, saved_vp_y;
-      GLsizei saved_vp_width, saved_vp_height;
-      GLenum saved_matrix_mode;
-   } meta;
+   struct dri_metaops meta;
 
    GLint refcount;
    GLuint Fallback;
@@ -191,7 +170,6 @@ struct intel_context
    struct intel_region *front_region;
    struct intel_region *back_region;
    struct intel_region *depth_region;
-   GLboolean internal_viewport_call;
 
    /**
     * This value indicates that the kernel memory manager is being used
@@ -224,13 +202,6 @@ struct intel_context
    GLuint ClearColor565;
    GLuint ClearColor8888;
 
-   /* info for intel_clear_tris() */
-   struct
-   {
-      struct gl_array_object *arrayObj;
-      GLfloat vertices[4][3];
-      GLfloat color[4][4];
-   } clear;
 
    /* Offsets of fields within the current vertex:
     */
index b00f801..fe98609 100644 (file)
@@ -88,7 +88,7 @@ intel_generate_mipmap_level(GLcontext *ctx, GLuint tex_name,
    if (status != GL_FRAMEBUFFER_COMPLETE_EXT)
       return GL_FALSE;
 
-   intel_meta_set_passthrough_transform(intel);
+   meta_set_passthrough_transform(&intel->meta);
 
    /* XXX: Doing it right would involve setting up the transformation to do
     * 0-1 mapping or something, and not changing the vertex data.
@@ -104,12 +104,12 @@ intel_generate_mipmap_level(GLcontext *ctx, GLuint tex_name,
 
    _mesa_VertexPointer(2, GL_FLOAT, 2 * sizeof(GLfloat), &vertices);
    _mesa_Enable(GL_VERTEX_ARRAY);
-   intel_meta_set_default_texrect(intel);
+   meta_set_default_texrect(&intel->meta);
 
    _mesa_DrawArrays(GL_TRIANGLE_FAN, 0, 4);
 
-   intel_meta_restore_texcoords(intel);
-   intel_meta_restore_transform(intel);
+   meta_restore_texcoords(&intel->meta);
+   meta_restore_transform(&intel->meta);
 
    return GL_TRUE;
 }
@@ -153,9 +153,9 @@ intel_generate_mipmap_2d(GLcontext *ctx,
    _mesa_GenFramebuffersEXT(1, &fb_name);
    _mesa_BindFramebufferEXT(GL_FRAMEBUFFER_EXT, fb_name);
 
-   intel_meta_set_fragment_program(intel, &intel->meta.tex2d_fp,
-                                  intel_fp_tex2d);
-   intel_meta_set_passthrough_vertex_program(intel);
+   meta_set_fragment_program(&intel->meta, &intel->meta.tex2d_fp,
+                            intel_fp_tex2d);
+   meta_set_passthrough_vertex_program(&intel->meta);
 
    max_levels = _mesa_max_texture_levels(ctx, texObj->Target);
    start_level = texObj->BaseLevel;
@@ -202,8 +202,8 @@ intel_generate_mipmap_2d(GLcontext *ctx,
    success = GL_TRUE;
 
 fail:
-   intel_meta_restore_fragment_program(intel);
-   intel_meta_restore_vertex_program(intel);
+   meta_restore_fragment_program(&intel->meta);
+   meta_restore_vertex_program(&intel->meta);
 
    _mesa_DeleteFramebuffersEXT(1, &fb_name);
    _mesa_ActiveTextureARB(GL_TEXTURE0_ARB + old_active_texture);
index da9ccb2..a300141 100644 (file)
@@ -177,246 +177,6 @@ intel_check_blit_format(struct intel_region * region,
 }
 
 void
-intel_meta_set_passthrough_transform(struct intel_context *intel)
-{
-   GLcontext *ctx = &intel->ctx;
-
-   intel->meta.saved_vp_x = ctx->Viewport.X;
-   intel->meta.saved_vp_y = ctx->Viewport.Y;
-   intel->meta.saved_vp_width = ctx->Viewport.Width;
-   intel->meta.saved_vp_height = ctx->Viewport.Height;
-   intel->meta.saved_matrix_mode = ctx->Transform.MatrixMode;
-
-   intel->internal_viewport_call = GL_TRUE;
-   _mesa_Viewport(0, 0, ctx->DrawBuffer->Width, ctx->DrawBuffer->Height);
-   intel->internal_viewport_call = GL_FALSE;
-
-   _mesa_MatrixMode(GL_PROJECTION);
-   _mesa_PushMatrix();
-   _mesa_LoadIdentity();
-   _mesa_Ortho(0, ctx->DrawBuffer->Width, 0, ctx->DrawBuffer->Height, 1, -1);
-
-   _mesa_MatrixMode(GL_MODELVIEW);
-   _mesa_PushMatrix();
-   _mesa_LoadIdentity();
-}
-
-void
-intel_meta_restore_transform(struct intel_context *intel)
-{
-   _mesa_MatrixMode(GL_PROJECTION);
-   _mesa_PopMatrix();
-   _mesa_MatrixMode(GL_MODELVIEW);
-   _mesa_PopMatrix();
-
-   _mesa_MatrixMode(intel->meta.saved_matrix_mode);
-
-   intel->internal_viewport_call = GL_TRUE;
-   _mesa_Viewport(intel->meta.saved_vp_x, intel->meta.saved_vp_y,
-                 intel->meta.saved_vp_width, intel->meta.saved_vp_height);
-   intel->internal_viewport_call = GL_FALSE;
-}
-
-/**
- * Set up a vertex program to pass through the position and first texcoord
- * for pixel path.
- */
-void
-intel_meta_set_passthrough_vertex_program(struct intel_context *intel)
-{
-   GLcontext *ctx = &intel->ctx;
-   static const char *vp =
-      "!!ARBvp1.0\n"
-      "TEMP vertexClip;\n"
-      "DP4 vertexClip.x, state.matrix.mvp.row[0], vertex.position;\n"
-      "DP4 vertexClip.y, state.matrix.mvp.row[1], vertex.position;\n"
-      "DP4 vertexClip.z, state.matrix.mvp.row[2], vertex.position;\n"
-      "DP4 vertexClip.w, state.matrix.mvp.row[3], vertex.position;\n"
-      "MOV result.position, vertexClip;\n"
-      "MOV result.texcoord[0], vertex.texcoord[0];\n"
-      "MOV result.color, vertex.color;\n"
-      "END\n";
-
-   assert(intel->meta.saved_vp == NULL);
-
-   _mesa_reference_vertprog(ctx, &intel->meta.saved_vp,
-                           ctx->VertexProgram.Current);
-   if (intel->meta.passthrough_vp == NULL) {
-      GLuint prog_name;
-      _mesa_GenPrograms(1, &prog_name);
-      _mesa_BindProgram(GL_VERTEX_PROGRAM_ARB, prog_name);
-      _mesa_ProgramStringARB(GL_VERTEX_PROGRAM_ARB,
-                            GL_PROGRAM_FORMAT_ASCII_ARB,
-                            strlen(vp), (const GLubyte *)vp);
-      _mesa_reference_vertprog(ctx, &intel->meta.passthrough_vp,
-                              ctx->VertexProgram.Current);
-      _mesa_DeletePrograms(1, &prog_name);
-   }
-
-   FLUSH_VERTICES(ctx, _NEW_PROGRAM);
-   _mesa_reference_vertprog(ctx, &ctx->VertexProgram.Current,
-                           intel->meta.passthrough_vp);
-   ctx->Driver.BindProgram(ctx, GL_VERTEX_PROGRAM_ARB,
-                          &intel->meta.passthrough_vp->Base);
-
-   intel->meta.saved_vp_enable = ctx->VertexProgram.Enabled;
-   _mesa_Enable(GL_VERTEX_PROGRAM_ARB);
-}
-
-/**
- * Restores the previous vertex program after
- * intel_meta_set_passthrough_vertex_program()
- */
-void
-intel_meta_restore_vertex_program(struct intel_context *intel)
-{
-   GLcontext *ctx = &intel->ctx;
-
-   FLUSH_VERTICES(ctx, _NEW_PROGRAM);
-   _mesa_reference_vertprog(ctx, &ctx->VertexProgram.Current,
-                           intel->meta.saved_vp);
-   _mesa_reference_vertprog(ctx, &intel->meta.saved_vp, NULL);
-   ctx->Driver.BindProgram(ctx, GL_VERTEX_PROGRAM_ARB,
-                          &ctx->VertexProgram.Current->Base);
-
-   if (!intel->meta.saved_vp_enable)
-      _mesa_Disable(GL_VERTEX_PROGRAM_ARB);
-}
-
-/**
- * Binds the given program string to GL_FRAGMENT_PROGRAM_ARB, caching the
- * program object.
- */
-void
-intel_meta_set_fragment_program(struct intel_context *intel,
-                               struct gl_fragment_program **prog,
-                               const char *prog_string)
-{
-   GLcontext *ctx = &intel->ctx;
-   assert(intel->meta.saved_fp == NULL);
-
-   _mesa_reference_fragprog(ctx, &intel->meta.saved_fp,
-                           ctx->FragmentProgram.Current);
-   if (*prog == NULL) {
-      GLuint prog_name;
-      _mesa_GenPrograms(1, &prog_name);
-      _mesa_BindProgram(GL_FRAGMENT_PROGRAM_ARB, prog_name);
-      _mesa_ProgramStringARB(GL_FRAGMENT_PROGRAM_ARB,
-                            GL_PROGRAM_FORMAT_ASCII_ARB,
-                            strlen(prog_string), (const GLubyte *)prog_string);
-      _mesa_reference_fragprog(ctx, prog, ctx->FragmentProgram.Current);
-      /* Note that DeletePrograms unbinds the program on us */
-      _mesa_DeletePrograms(1, &prog_name);
-   }
-
-   FLUSH_VERTICES(ctx, _NEW_PROGRAM);
-   _mesa_reference_fragprog(ctx, &ctx->FragmentProgram.Current, *prog);
-   ctx->Driver.BindProgram(ctx, GL_FRAGMENT_PROGRAM_ARB, &((*prog)->Base));
-
-   intel->meta.saved_fp_enable = ctx->FragmentProgram.Enabled;
-   _mesa_Enable(GL_FRAGMENT_PROGRAM_ARB);
-}
-
-/**
- * Restores the previous fragment program after
- * intel_meta_set_fragment_program()
- */
-void
-intel_meta_restore_fragment_program(struct intel_context *intel)
-{
-   GLcontext *ctx = &intel->ctx;
-
-   FLUSH_VERTICES(ctx, _NEW_PROGRAM);
-   _mesa_reference_fragprog(ctx, &ctx->FragmentProgram.Current,
-                           intel->meta.saved_fp);
-   _mesa_reference_fragprog(ctx, &intel->meta.saved_fp, NULL);
-   ctx->Driver.BindProgram(ctx, GL_FRAGMENT_PROGRAM_ARB,
-                          &ctx->FragmentProgram.Current->Base);
-
-   if (!intel->meta.saved_fp_enable)
-      _mesa_Disable(GL_FRAGMENT_PROGRAM_ARB);
-}
-
-static const float default_texcoords[4][2] = { { 0.0, 0.0 },
-                                              { 1.0, 0.0 },
-                                              { 1.0, 1.0 },
-                                              { 0.0, 1.0 } };
-
-void
-intel_meta_set_default_texrect(struct intel_context *intel)
-{
-   GLcontext *ctx = &intel->ctx;
-   struct gl_client_array *old_texcoord_array;
-
-   intel->meta.saved_active_texture = ctx->Texture.CurrentUnit;
-   if (intel->meta.saved_array_vbo == NULL) {
-      _mesa_reference_buffer_object(ctx, &intel->meta.saved_array_vbo,
-                                   ctx->Array.ArrayBufferObj);
-   }
-
-   old_texcoord_array = &ctx->Array.ArrayObj->TexCoord[0];
-   intel->meta.saved_texcoord_type = old_texcoord_array->Type;
-   intel->meta.saved_texcoord_size = old_texcoord_array->Size;
-   intel->meta.saved_texcoord_stride = old_texcoord_array->Stride;
-   intel->meta.saved_texcoord_enable = old_texcoord_array->Enabled;
-   intel->meta.saved_texcoord_ptr = old_texcoord_array->Ptr;
-   _mesa_reference_buffer_object(ctx, &intel->meta.saved_texcoord_vbo,
-                                old_texcoord_array->BufferObj);
-
-   _mesa_ClientActiveTextureARB(GL_TEXTURE0);
-
-   if (intel->meta.texcoord_vbo == NULL) {
-      GLuint vbo_name;
-
-      _mesa_GenBuffersARB(1, &vbo_name);
-      _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB, vbo_name);
-      _mesa_BufferDataARB(GL_ARRAY_BUFFER_ARB, sizeof(default_texcoords),
-                         default_texcoords, GL_STATIC_DRAW_ARB);
-      _mesa_reference_buffer_object(ctx, &intel->meta.texcoord_vbo,
-                                   ctx->Array.ArrayBufferObj);
-   } else {
-      _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB,
-                         intel->meta.texcoord_vbo->Name);
-   }
-   _mesa_TexCoordPointer(2, GL_FLOAT, 2 * sizeof(GLfloat), NULL);
-
-   _mesa_Enable(GL_TEXTURE_COORD_ARRAY);
-}
-
-void
-intel_meta_restore_texcoords(struct intel_context *intel)
-{
-   GLcontext *ctx = &intel->ctx;
-
-   /* Restore the old TexCoordPointer */
-   if (intel->meta.saved_texcoord_vbo) {
-      _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB,
-                         intel->meta.saved_texcoord_vbo->Name);
-      _mesa_reference_buffer_object(ctx, &intel->meta.saved_texcoord_vbo, NULL);
-   } else {
-      _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
-   }
-
-   _mesa_TexCoordPointer(intel->meta.saved_texcoord_size,
-                        intel->meta.saved_texcoord_type,
-                        intel->meta.saved_texcoord_stride,
-                        intel->meta.saved_texcoord_ptr);
-   if (!intel->meta.saved_texcoord_enable)
-      _mesa_Disable(GL_TEXTURE_COORD_ARRAY);
-
-   _mesa_ClientActiveTextureARB(GL_TEXTURE0 +
-                               intel->meta.saved_active_texture);
-
-   if (intel->meta.saved_array_vbo) {
-      _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB,
-                         intel->meta.saved_array_vbo->Name);
-      _mesa_reference_buffer_object(ctx, &intel->meta.saved_array_vbo, NULL);
-   } else {
-      _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
-   }
-}
-
-void
 intelInitPixelFuncs(struct dd_function_table *functions)
 {
    functions->Accum = _swrast_Accum;
@@ -428,14 +188,3 @@ intelInitPixelFuncs(struct dd_function_table *functions)
    functions->ReadPixels = intelReadPixels;
 }
 
-void
-intel_free_pixel_state(struct intel_context *intel)
-{
-   GLcontext *ctx = &intel->ctx;
-
-   _mesa_reference_vertprog(ctx, &intel->meta.passthrough_vp, NULL);
-   _mesa_reference_fragprog(ctx, &intel->meta.bitmap_fp, NULL);
-   _mesa_reference_fragprog(ctx, &intel->meta.tex2d_fp, NULL);
-   _mesa_reference_buffer_object(ctx, &intel->meta.texcoord_vbo, NULL);
-}
-
index 6acf081..96a6dd1 100644 (file)
 #include "main/mtypes.h"
 
 void intelInitPixelFuncs(struct dd_function_table *functions);
-void intel_meta_set_passthrough_transform(struct intel_context *intel);
-void intel_meta_restore_transform(struct intel_context *intel);
-void intel_meta_set_passthrough_vertex_program(struct intel_context *intel);
-void intel_meta_restore_vertex_program(struct intel_context *intel);
-void intel_meta_set_fragment_program(struct intel_context *intel,
-                                    struct gl_fragment_program **prog,
-                                    const char *prog_string);
-void intel_meta_restore_fragment_program(struct intel_context *intel);
-void intel_free_pixel_state(struct intel_context *intel);
-void intel_meta_set_default_texrect(struct intel_context *intel);
-void intel_meta_set_default_texrect(struct intel_context *intel);
-void intel_meta_restore_texcoords(struct intel_context *intel);
-
 GLboolean intel_check_blit_fragment_ops(GLcontext * ctx,
                                        GLboolean src_alpha_is_one);
 
@@ -79,6 +66,4 @@ void intelBitmap(GLcontext * ctx,
                 const struct gl_pixelstore_attrib *unpack,
                 const GLubyte * pixels);
 
-void intel_clear_tris(GLcontext *ctx, GLbitfield mask);
-
 #endif
index ebba6aa..540e762 100644 (file)
@@ -476,11 +476,11 @@ intel_texture_bitmap(GLcontext * ctx,
                    GL_ALPHA, GL_UNSIGNED_BYTE, a8_bitmap);
    _mesa_free(a8_bitmap);
 
-   intel_meta_set_fragment_program(intel, &intel->meta.bitmap_fp, fp);
+   meta_set_fragment_program(&intel->meta, &intel->meta.bitmap_fp, fp);
    _mesa_ProgramLocalParameter4fvARB(GL_FRAGMENT_PROGRAM_ARB, 0,
                                     ctx->Current.RasterColor);
-   intel_meta_set_passthrough_vertex_program(intel);
-   intel_meta_set_passthrough_transform(intel);
+   meta_set_passthrough_vertex_program(&intel->meta);
+   meta_set_passthrough_transform(&intel->meta);
 
    /* convert rasterpos Z from [0,1] to NDC coord in [-1,1] */
    dst_z = -1.0 + 2.0 * ctx->Current.RasterPos[2];
@@ -507,13 +507,13 @@ intel_texture_bitmap(GLcontext * ctx,
 
    _mesa_VertexPointer(4, GL_FLOAT, 4 * sizeof(GLfloat), &vertices);
    _mesa_Enable(GL_VERTEX_ARRAY);
-   intel_meta_set_default_texrect(intel);
+   meta_set_default_texrect(&intel->meta);
    _mesa_DrawArrays(GL_TRIANGLE_FAN, 0, 4);
 
-   intel_meta_restore_texcoords(intel);
-   intel_meta_restore_transform(intel);
-   intel_meta_restore_fragment_program(intel);
-   intel_meta_restore_vertex_program(intel);
+   meta_restore_texcoords(&intel->meta);
+   meta_restore_transform(&intel->meta);
+   meta_restore_fragment_program(&intel->meta);
+   meta_restore_vertex_program(&intel->meta);
 
    _mesa_PopClientAttrib();
    _mesa_Disable(GL_TEXTURE_2D); /* asserted that it was disabled at entry */
index dfc9e15..a6b6824 100644 (file)
@@ -150,7 +150,7 @@ intel_texture_drawpixels(GLcontext * ctx,
    _mesa_TexImage2D(GL_TEXTURE_2D, 0, internalFormat, width, height, 0, format,
                    type, pixels);
 
-   intel_meta_set_passthrough_transform(intel);
+   meta_set_passthrough_transform(&intel->meta);
 
    /* convert rasterpos Z from [0,1] to NDC coord in [-1,1] */
    z = -1.0 + 2.0 * ctx->Current.RasterPos[2];
@@ -182,12 +182,12 @@ intel_texture_drawpixels(GLcontext * ctx,
 
    _mesa_VertexPointer(4, GL_FLOAT, 4 * sizeof(GLfloat), &vertices);
    _mesa_Enable(GL_VERTEX_ARRAY);
-   intel_meta_set_default_texrect(intel);
+   meta_set_default_texrect(&intel->meta);
 
    _mesa_DrawArrays(GL_TRIANGLE_FAN, 0, 4);
 
-   intel_meta_restore_texcoords(intel);
-   intel_meta_restore_transform(intel);
+   meta_restore_texcoords(&intel->meta);
+   meta_restore_transform(&intel->meta);
 
    _mesa_ActiveTextureARB(GL_TEXTURE0_ARB + old_active_texture);
    _mesa_PopClientAttrib();
@@ -352,7 +352,7 @@ intel_stencil_drawpixels(GLcontext * ctx,
    ctx->Unpack = old_unpack;
    _mesa_free(stencil_pixels);
 
-   intel_meta_set_passthrough_transform(intel);
+   meta_set_passthrough_transform(&intel->meta);
 
    /* Since we're rendering to the framebuffer as if it was an FBO,
     * if it's the window system we have to flip the coordinates.
@@ -375,12 +375,12 @@ intel_stencil_drawpixels(GLcontext * ctx,
 
    _mesa_VertexPointer(2, GL_FLOAT, 2 * sizeof(GLfloat), &vertices);
    _mesa_Enable(GL_VERTEX_ARRAY);
-   intel_meta_set_default_texrect(intel);
+   meta_set_default_texrect(&intel->meta);
 
    _mesa_DrawArrays(GL_TRIANGLE_FAN, 0, 4);
 
-   intel_meta_restore_texcoords(intel);
-   intel_meta_restore_transform(intel);
+   meta_restore_texcoords(&intel->meta);
+   meta_restore_transform(&intel->meta);
 
    _mesa_ActiveTextureARB(GL_TEXTURE0_ARB + old_active_texture);
    _mesa_BindFramebufferEXT(GL_FRAMEBUFFER_EXT, old_fb_name);
index 6560efd..4dbda39 100644 (file)
@@ -58,11 +58,6 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 #define R200_TIMEOUT             512
 #define R200_IDLE_RETRY           16
 
-static void r200UserClear(GLcontext *ctx, GLuint mask)
-{
-   radeon_clear_tris(ctx, mask);
-}
-
 static void r200KernelClear(GLcontext *ctx, GLuint flags)
 {
    r200ContextPtr rmesa = R200_CONTEXT(ctx);
@@ -253,7 +248,7 @@ static void r200Clear( GLcontext *ctx, GLbitfield mask )
    }
 
    if (rmesa->radeon.radeonScreen->kernel_mm)
-      r200UserClear(ctx, orig_mask);
+      radeonUserClear(ctx, orig_mask);
    else {
       r200KernelClear(ctx, flags);
       rmesa->radeon.hw.all_dirty = GL_TRUE;
index 4e913db..ddabd53 100644 (file)
@@ -68,11 +68,6 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 
 static void r300EmitClearState(GLcontext * ctx);
 
-static void r300UserClear(GLcontext *ctx, GLuint mask)
-{
-       radeon_clear_tris(ctx, mask);
-}
-
 static void r300ClearBuffer(r300ContextPtr r300, int flags,
                            struct radeon_renderbuffer *rrb,
                            struct radeon_renderbuffer *rrbd)
@@ -680,7 +675,7 @@ static void r300Clear(GLcontext * ctx, GLbitfield mask)
        ret = 0;
        if (tri_mask) {
                if (r300->radeon.radeonScreen->kernel_mm)
-                       r300UserClear(ctx, tri_mask);
+                       radeonUserClear(ctx, tri_mask);
                else {
                        /* if kernel clear fails due to size restraints fallback */
                        ret = r300KernelClear(ctx, tri_mask);
index 0a8d8b0..3bf42e9 100644 (file)
@@ -877,7 +877,7 @@ void radeon_viewport(GLcontext *ctx, GLint x, GLint y, GLsizei width, GLsizei he
        if (!driContext->driScreenPriv->dri2.enabled)
                return;
 
-       if (!radeon->internal_viewport_call && ctx->DrawBuffer->Name == 0) {
+       if (!radeon->meta.internal_viewport_call && ctx->DrawBuffer->Name == 0) {
                if (radeon->is_front_buffer_rendering) {
                        radeonFlush(ctx);
                }
@@ -1258,254 +1258,8 @@ void rcommonBeginBatch(radeonContextPtr rmesa, int n,
 
 }
 
-
-
-static void
-radeon_meta_set_passthrough_transform(radeonContextPtr radeon)
-{
-   GLcontext *ctx = radeon->glCtx;
-
-   radeon->meta.saved_vp_x = ctx->Viewport.X;
-   radeon->meta.saved_vp_y = ctx->Viewport.Y;
-   radeon->meta.saved_vp_width = ctx->Viewport.Width;
-   radeon->meta.saved_vp_height = ctx->Viewport.Height;
-   radeon->meta.saved_matrix_mode = ctx->Transform.MatrixMode;
-
-   radeon->internal_viewport_call = GL_TRUE;
-   _mesa_Viewport(0, 0, ctx->DrawBuffer->Width, ctx->DrawBuffer->Height);
-   radeon->internal_viewport_call = GL_FALSE;
-
-   _mesa_MatrixMode(GL_PROJECTION);
-   _mesa_PushMatrix();
-   _mesa_LoadIdentity();
-   _mesa_Ortho(0, ctx->DrawBuffer->Width, 0, ctx->DrawBuffer->Height, 1, -1);
-
-   _mesa_MatrixMode(GL_MODELVIEW);
-   _mesa_PushMatrix();
-   _mesa_LoadIdentity();
-}
-
-static void
-radeon_meta_restore_transform(radeonContextPtr radeon)
-{
-   _mesa_MatrixMode(GL_PROJECTION);
-   _mesa_PopMatrix();
-   _mesa_MatrixMode(GL_MODELVIEW);
-   _mesa_PopMatrix();
-
-   _mesa_MatrixMode(radeon->meta.saved_matrix_mode);
-
-   radeon->internal_viewport_call = GL_TRUE;
-   _mesa_Viewport(radeon->meta.saved_vp_x, radeon->meta.saved_vp_y,
-                 radeon->meta.saved_vp_width, radeon->meta.saved_vp_height);
-   radeon->internal_viewport_call = GL_FALSE;
-}
-
-
-/**
- * Perform glClear where mask contains only color, depth, and/or stencil.
- *
- * The implementation is based on calling into Mesa to set GL state and
- * performing normal triangle rendering.  The intent of this path is to
- * have as generic a path as possible, so that any driver could make use of
- * it.
- */
-
-static void radeon_clear_init(GLcontext *ctx)
-{
-    radeonContextPtr rmesa = RADEON_CONTEXT(ctx);
-    struct gl_array_object *arraySave = NULL;
-    const GLuint arrayBuffer = ctx->Array.ArrayBufferObj->Name;
-    const GLuint elementBuffer = ctx->Array.ElementArrayBufferObj->Name;
-
-    /* create new array object */
-    rmesa->clear.arrayObj = _mesa_new_array_object(ctx, ~0);
-    _mesa_reference_array_object(ctx, &arraySave, ctx->Array.ArrayObj);
-    _mesa_reference_array_object(ctx, &ctx->Array.ArrayObj, rmesa->clear.arrayObj);
-
-    /* one time setup of vertex arrays (pos, color) */
-    _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
-    _mesa_BindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, 0);
-    _mesa_ColorPointer(4, GL_FLOAT, 4 * sizeof(GLfloat), rmesa->clear.color);
-    _mesa_VertexPointer(3, GL_FLOAT, 3 * sizeof(GLfloat), rmesa->clear.vertices);
-    _mesa_Enable(GL_COLOR_ARRAY);
-    _mesa_Enable(GL_VERTEX_ARRAY);
-
-    /* restore original array object */
-    _mesa_reference_array_object(ctx, &ctx->Array.ArrayObj, arraySave);
-    _mesa_reference_array_object(ctx, &arraySave, NULL);
-
-    /* restore original buffer objects */
-    _mesa_BindBufferARB(GL_ARRAY_BUFFER_ARB, arrayBuffer);
-    _mesa_BindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, elementBuffer);
-}
-
-
-void radeon_clear_tris(GLcontext *ctx, GLbitfield mask)
+void radeonUserClear(GLcontext *ctx, GLuint mask)
 {
    radeonContextPtr rmesa = RADEON_CONTEXT(ctx);
-   GLfloat dst_z;
-   struct gl_framebuffer *fb = ctx->DrawBuffer;
-   int i;
-   GLboolean saved_fp_enable = GL_FALSE, saved_vp_enable = GL_FALSE;
-   GLboolean saved_shader_program = 0;
-   unsigned int saved_active_texture;
-   struct gl_array_object *arraySave = NULL;
-
-   if (!rmesa->clear.arrayObj)
-       radeon_clear_init(ctx);
-
-   assert((mask & ~(TRI_CLEAR_COLOR_BITS | BUFFER_BIT_DEPTH |
-                   BUFFER_BIT_STENCIL)) == 0);
-
-   _mesa_PushAttrib(GL_COLOR_BUFFER_BIT |
-                   GL_DEPTH_BUFFER_BIT |
-                   GL_ENABLE_BIT |
-                   GL_POLYGON_BIT |
-                   GL_STENCIL_BUFFER_BIT |
-                   GL_TRANSFORM_BIT |
-                   GL_CURRENT_BIT);
-   saved_active_texture = ctx->Texture.CurrentUnit;
-
-  /* Disable existing GL state we don't want to apply to a clear. */
-   _mesa_Disable(GL_ALPHA_TEST);
-   _mesa_Disable(GL_BLEND);
-   _mesa_Disable(GL_CULL_FACE);
-   _mesa_Disable(GL_FOG);
-   _mesa_Disable(GL_POLYGON_SMOOTH);
-   _mesa_Disable(GL_POLYGON_STIPPLE);
-   _mesa_Disable(GL_POLYGON_OFFSET_FILL);
-   _mesa_Disable(GL_LIGHTING);
-   _mesa_Disable(GL_CLIP_PLANE0);
-   _mesa_Disable(GL_CLIP_PLANE1);
-   _mesa_Disable(GL_CLIP_PLANE2);
-   _mesa_Disable(GL_CLIP_PLANE3);
-   _mesa_Disable(GL_CLIP_PLANE4);
-   _mesa_Disable(GL_CLIP_PLANE5);
-   _mesa_PolygonMode(GL_FRONT_AND_BACK, GL_FILL);
-   if (ctx->Extensions.ARB_fragment_program && ctx->FragmentProgram.Enabled) {
-      saved_fp_enable = GL_TRUE;
-      _mesa_Disable(GL_FRAGMENT_PROGRAM_ARB);
-   }
-   if (ctx->Extensions.ARB_vertex_program && ctx->VertexProgram.Enabled) {
-      saved_vp_enable = GL_TRUE;
-      _mesa_Disable(GL_VERTEX_PROGRAM_ARB);
-   }
-   if (ctx->Extensions.ARB_shader_objects && ctx->Shader.CurrentProgram) {
-      saved_shader_program = ctx->Shader.CurrentProgram->Name;
-      _mesa_UseProgramObjectARB(0);
-   }
-
-   if (ctx->Texture._EnabledUnits != 0) {
-      int i;
-
-      for (i = 0; i < ctx->Const.MaxTextureUnits; i++) {
-        _mesa_ActiveTextureARB(GL_TEXTURE0 + i);
-        _mesa_Disable(GL_TEXTURE_1D);
-        _mesa_Disable(GL_TEXTURE_2D);
-        _mesa_Disable(GL_TEXTURE_3D);
-        if (ctx->Extensions.ARB_texture_cube_map)
-           _mesa_Disable(GL_TEXTURE_CUBE_MAP_ARB);
-        if (ctx->Extensions.NV_texture_rectangle)
-           _mesa_Disable(GL_TEXTURE_RECTANGLE_NV);
-        if (ctx->Extensions.MESA_texture_array) {
-           _mesa_Disable(GL_TEXTURE_1D_ARRAY_EXT);
-           _mesa_Disable(GL_TEXTURE_2D_ARRAY_EXT);
-        }
-      }
-   }
-
-   /* save current array object, bind our private one */
-   _mesa_reference_array_object(ctx, &arraySave, ctx->Array.ArrayObj);
-   _mesa_reference_array_object(ctx, &ctx->Array.ArrayObj, rmesa->clear.arrayObj);
-
-   radeon_meta_set_passthrough_transform(rmesa);
-
-   for (i = 0; i < 4; i++) {
-      COPY_4FV(rmesa->clear.color[i], ctx->Color.ClearColor);
-   }
-
-   /* convert clear Z from [0,1] to NDC coord in [-1,1] */
-
-   dst_z = -1.0 + 2.0 * ctx->Depth.Clear;
-   /* Prepare the vertices, which are the same regardless of which buffer we're
-    * drawing to.
-    */
-   rmesa->clear.vertices[0][0] = fb->_Xmin;
-   rmesa->clear.vertices[0][1] = fb->_Ymin;
-   rmesa->clear.vertices[0][2] = dst_z;
-   rmesa->clear.vertices[1][0] = fb->_Xmax;
-   rmesa->clear.vertices[1][1] = fb->_Ymin;
-   rmesa->clear.vertices[1][2] = dst_z;
-   rmesa->clear.vertices[2][0] = fb->_Xmax;
-   rmesa->clear.vertices[2][1] = fb->_Ymax;
-   rmesa->clear.vertices[2][2] = dst_z;
-   rmesa->clear.vertices[3][0] = fb->_Xmin;
-   rmesa->clear.vertices[3][1] = fb->_Ymax;
-   rmesa->clear.vertices[3][2] = dst_z;
-
-   while (mask != 0) {
-      GLuint this_mask = 0;
-      GLuint color_bit;
-
-      color_bit = _mesa_ffs(mask & TRI_CLEAR_COLOR_BITS);
-      if (color_bit != 0)
-        this_mask |= (1 << (color_bit - 1));
-
-      /* Clear depth/stencil in the same pass as color. */
-      this_mask |= (mask & (BUFFER_BIT_DEPTH | BUFFER_BIT_STENCIL));
-
-      /* Select the current color buffer and use the color write mask if
-       * we have one, otherwise don't write any color channels.
-       */
-      if (this_mask & BUFFER_BIT_FRONT_LEFT)
-        _mesa_DrawBuffer(GL_FRONT_LEFT);
-      else if (this_mask & BUFFER_BIT_BACK_LEFT)
-        _mesa_DrawBuffer(GL_BACK_LEFT);
-      else if (color_bit != 0)
-        _mesa_DrawBuffer(GL_COLOR_ATTACHMENT0 +
-                         (color_bit - BUFFER_COLOR0 - 1));
-      else
-        _mesa_ColorMask(GL_FALSE, GL_FALSE, GL_FALSE, GL_FALSE);
-
-      /* Control writing of the depth clear value to depth. */
-      if (this_mask & BUFFER_BIT_DEPTH) {
-        _mesa_DepthFunc(GL_ALWAYS);
-        _mesa_DepthMask(GL_TRUE);
-        _mesa_Enable(GL_DEPTH_TEST);
-      } else {
-        _mesa_Disable(GL_DEPTH_TEST);
-        _mesa_DepthMask(GL_FALSE);
-      }
-
-      /* Control writing of the stencil clear value to stencil. */
-      if (this_mask & BUFFER_BIT_STENCIL) {
-        _mesa_Enable(GL_STENCIL_TEST);
-        _mesa_StencilOp(GL_REPLACE, GL_REPLACE, GL_REPLACE);
-        _mesa_StencilFuncSeparate(GL_FRONT_AND_BACK, GL_ALWAYS, (GLint)ctx->Stencil.Clear,
-                                  ctx->Stencil.WriteMask[0]);
-      } else {
-        _mesa_Disable(GL_STENCIL_TEST);
-      }
-
-      _mesa_DrawArrays(GL_TRIANGLE_FAN, 0, 4);
-
-      mask &= ~this_mask;
-   }
-
-   radeon_meta_restore_transform(rmesa);
-
-   _mesa_ActiveTextureARB(GL_TEXTURE0 + saved_active_texture);
-   if (saved_fp_enable)
-      _mesa_Enable(GL_FRAGMENT_PROGRAM_ARB);
-   if (saved_vp_enable)
-      _mesa_Enable(GL_VERTEX_PROGRAM_ARB);
-
-   if (saved_shader_program)
-      _mesa_UseProgramObjectARB(saved_shader_program);
-
-   _mesa_PopAttrib();
-     /* restore current array object */
-   _mesa_reference_array_object(ctx, &ctx->Array.ArrayObj, arraySave);
-   _mesa_reference_array_object(ctx, &arraySave, NULL);
+   meta_clear_tris(&rmesa->meta, mask);
 }
index ba6c7c5..cebae18 100644 (file)
@@ -5,18 +5,7 @@
 #include "radeon_dma.h"
 #include "radeon_texture.h"
 
-
-#define TRI_CLEAR_COLOR_BITS (BUFFER_BIT_BACK_LEFT |                   \
-                             BUFFER_BIT_FRONT_LEFT |                   \
-                             BUFFER_BIT_COLOR0 |                       \
-                             BUFFER_BIT_COLOR1 |                       \
-                             BUFFER_BIT_COLOR2 |                       \
-                             BUFFER_BIT_COLOR3 |                       \
-                             BUFFER_BIT_COLOR4 |                       \
-                             BUFFER_BIT_COLOR5 |                       \
-                             BUFFER_BIT_COLOR6 |                       \
-                             BUFFER_BIT_COLOR7)
-
+void radeonUserClear(GLcontext *ctx, GLuint mask);
 void radeonRecalcScissorRects(radeonContextPtr radeon);
 void radeonSetCliprects(radeonContextPtr radeon);
 void radeonUpdateScissor( GLcontext *ctx );
index 828d647..9add50b 100644 (file)
@@ -184,6 +184,7 @@ GLboolean radeonInitContext(radeonContextPtr radeon,
        ctx = radeon->glCtx;
        driContextPriv->driverPrivate = radeon;
 
+       meta_init_metaops(ctx, &radeon->meta);
        /* DRI fields */
        radeon->dri.context = driContextPriv;
        radeon->dri.screen = sPriv;
@@ -264,7 +265,7 @@ void radeonDestroyContext(__DRIcontextPrivate *driContextPriv )
                }
 
                radeonReleaseArrays(radeon->glCtx, ~0);
-
+               meta_destroy_metaops(&radeon->meta);
                if (radeon->vtbl.free_context)
                        radeon->vtbl.free_context(radeon->glCtx);
                _swsetup_DestroyContext( radeon->glCtx );
index 036d265..07ac85f 100644 (file)
@@ -13,6 +13,7 @@
 #include "dri_util.h"
 #include "tnl/t_vertex.h"
 
+#include "dri_metaops.h"
 struct radeon_context;
 
 #include "radeon_bocs_wrapper.h"
@@ -476,27 +477,7 @@ struct radeon_context {
     */
    GLboolean is_front_buffer_reading;
 
-   /* info for radeon_clear_tris() */
-   struct {
-      struct gl_array_object *arrayObj;
-      GLfloat vertices[4][3];
-      GLfloat color[4][4];
-   } clear;
-   GLboolean internal_viewport_call;
-
-  struct {
-      struct gl_fragment_program *bitmap_fp;
-      struct gl_vertex_program *passthrough_vp;
-
-      struct gl_fragment_program *saved_fp;
-      GLboolean saved_fp_enable;
-      struct gl_vertex_program *saved_vp;
-      GLboolean saved_vp_enable;
-
-      GLint saved_vp_x, saved_vp_y;
-      GLsizei saved_vp_width, saved_vp_height;
-      GLenum saved_matrix_mode;
-   } meta;
+   struct dri_metaops meta;
 
    struct {
           void (*get_lock)(radeonContextPtr radeon);
index 01c45df..a5e4df7 100644 (file)
@@ -445,11 +445,6 @@ void radeonEmitAOS( r100ContextPtr rmesa,
  */
 #define RADEON_MAX_CLEARS      256
 
-static void radeonUserClear(GLcontext *ctx, GLuint mask)
-{
-   radeon_clear_tris(ctx, mask);
-}
-
 static void radeonKernelClear(GLcontext *ctx, GLuint flags)
 {
      r100ContextPtr rmesa = R100_CONTEXT(ctx);