OSDN Git Service

Merge branch 'register-negate'
authorBrian Paul <brianp@vmware.com>
Fri, 17 Apr 2009 04:02:54 +0000 (22:02 -0600)
committerBrian Paul <brianp@vmware.com>
Fri, 17 Apr 2009 04:02:54 +0000 (22:02 -0600)
70 files changed:
Makefile
progs/fp/swz3.txt [new file with mode: 0644]
progs/samples/blendeq.c
progs/tests/texcompress2.c
src/egl/main/Makefile
src/gallium/auxiliary/util/Makefile
src/gallium/auxiliary/util/SConscript
src/gallium/auxiliary/util/u_surface.c [new file with mode: 0644]
src/gallium/auxiliary/util/u_surface.h [new file with mode: 0644]
src/gallium/drivers/cell/ppu/cell_context.c
src/gallium/drivers/failover/fo_context.c
src/gallium/drivers/i915simple/i915_context.c
src/gallium/drivers/i965simple/brw_context.c
src/gallium/drivers/nv04/nv04_context.c
src/gallium/drivers/nv10/nv10_context.c
src/gallium/drivers/nv20/nv20_context.c
src/gallium/drivers/nv30/nv30_context.c
src/gallium/drivers/nv40/nv40_context.c
src/gallium/drivers/nv50/nv50_context.c
src/gallium/drivers/r300/r300_context.c
src/gallium/drivers/r300/r300_render.c
src/gallium/drivers/r300/r300_state.c
src/gallium/drivers/r300/r300_state_derived.c
src/gallium/drivers/r300/r300_state_tcl.c
src/gallium/drivers/r300/r300_state_tcl.h
src/gallium/drivers/softpipe/sp_context.c
src/gallium/drivers/trace/tr_context.c
src/gallium/include/pipe/p_context.h
src/gallium/include/pipe/p_defines.h
src/glx/x11/glxcmds.c
src/mesa/drivers/dri/common/spantmp2.h
src/mesa/drivers/dri/i915/Makefile
src/mesa/drivers/dri/i915/i830_context.c
src/mesa/drivers/dri/i915/i830_tex.c [deleted file]
src/mesa/drivers/dri/i915/i830_vtbl.c
src/mesa/drivers/dri/i915/i915_context.c
src/mesa/drivers/dri/i915/i915_fragprog.c
src/mesa/drivers/dri/i915/i915_tex.c [deleted file]
src/mesa/drivers/dri/i915/i915_vtbl.c
src/mesa/drivers/dri/i965/brw_curbe.c
src/mesa/drivers/dri/i965/brw_eu.h
src/mesa/drivers/dri/i965/brw_eu_emit.c
src/mesa/drivers/dri/i965/brw_state_dump.c
src/mesa/drivers/dri/i965/brw_vs_emit.c
src/mesa/drivers/dri/i965/brw_wm_glsl.c
src/mesa/drivers/dri/i965/brw_wm_surface_state.c
src/mesa/drivers/dri/intel/intel_blit.c
src/mesa/drivers/dri/intel/intel_context.h
src/mesa/drivers/dri/intel/intel_decode.c
src/mesa/drivers/dri/intel/intel_fbo.c
src/mesa/drivers/dri/intel/intel_fbo.h
src/mesa/drivers/dri/intel/intel_span.c
src/mesa/drivers/dri/intel/intel_tex_image.c
src/mesa/main/attrib.c
src/mesa/main/state.c
src/mesa/main/texcompress_s3tc.c
src/mesa/state_tracker/st_cb_accum.c
src/mesa/state_tracker/st_cb_bufferobjects.c
src/mesa/state_tracker/st_cb_drawpixels.c
src/mesa/state_tracker/st_cb_readpixels.c
src/mesa/state_tracker/st_cb_texture.c
src/mesa/state_tracker/st_format.c
src/mesa/state_tracker/st_format.h
src/mesa/state_tracker/st_gen_mipmap.c
src/mesa/state_tracker/st_program.c
src/mesa/state_tracker/st_texture.c
src/mesa/state_tracker/st_texture.h
src/mesa/vbo/vbo_save.h
src/mesa/vbo/vbo_save_api.c
src/mesa/vbo/vbo_save_draw.c

index 59f0a07..a77825e 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -37,6 +37,9 @@ realclean: clean
          -name depend -o -name depend.bak ')' -exec rm -f '{}' ';'
 
 
+distclean: realclean
+
+
 install:
        @for dir in $(SUBDIRS) ; do \
                if [ -d $$dir ] ; then \
@@ -45,7 +48,7 @@ install:
        done
 
 
-.PHONY: default doxygen clean realclean install linux-directfb-install
+.PHONY: default doxygen clean realclean distclean install linux-directfb-install
 
 # If there's no current configuration file
 $(TOP)/configs/current:
diff --git a/progs/fp/swz3.txt b/progs/fp/swz3.txt
new file mode 100644 (file)
index 0000000..382f588
--- /dev/null
@@ -0,0 +1,5 @@
+!!ARBfp1.0
+TEMP R0, R1;
+MOV R0, -fragment.color;
+SWZ result.color, R0, -y, -x, z, 1;
+END
index cd0474c..037d06f 100644 (file)
@@ -100,7 +100,7 @@ static void PrintColorStrings( void )
 {
     GLubyte ubbuf[3];
     int i, xleft, xright;
-    char colorString[18];
+    char colorString[100];
 
     xleft = 5 + windW/4;
     xright = 5 + windW/2;
index cbb8f1d..b95aca9 100644 (file)
@@ -51,7 +51,6 @@ TestSubTex(void)
    GLboolean all = 0*GL_TRUE;
    GLubyte *buffer;
    GLint size, fmt;
-   int i;
 
    glGetTexLevelParameteriv(Target, 0,
                             GL_TEXTURE_COMPRESSED_IMAGE_SIZE_ARB, &size);
@@ -83,6 +82,23 @@ TestSubTex(void)
 
 
 static void
+TestGetTex(void)
+{
+   GLubyte *buffer;
+
+   buffer = (GLubyte *) malloc(3 * ImgWidth * ImgHeight);
+
+   glGetTexImage(GL_TEXTURE_2D,
+                 0,
+                 GL_RGB,
+                 GL_UNSIGNED_BYTE,
+                 buffer);
+
+   free(buffer);
+}
+
+
+static void
 LoadCompressedImage(const char *file)
 {
    const GLenum filter = GL_LINEAR;
@@ -146,7 +162,10 @@ LoadCompressedImage(const char *file)
    glTexParameteri(Target, GL_TEXTURE_MIN_FILTER, filter);
    glTexParameteri(Target, GL_TEXTURE_MAG_FILTER, filter);
 
-   TestSubTex();
+   if (0)
+      TestSubTex();
+   else
+      TestGetTex();
 
 }
 
index 5ee246d..8cfa25c 100644 (file)
@@ -64,7 +64,7 @@ $(TOP)/$(LIB_DIR)/libEGL.so: $(OBJECTS)
                -install $(TOP)/$(LIB_DIR) \
                $(EGL_LIB_DEPS) $(OBJECTS)
 
-install:
+install: default
        $(INSTALL) -d $(DESTDIR)$(INSTALL_LIB_DIR)
        $(INSTALL) $(TOP)/$(LIB_DIR)/libEGL.so* $(DESTDIR)$(INSTALL_LIB_DIR)
 
index 5035e9c..2995aba 100644 (file)
@@ -23,6 +23,7 @@ C_SOURCES = \
        u_snprintf.c \
        u_stream_stdc.c \
        u_stream_wd.c \
+       u_surface.c \
        u_tile.c \
        u_time.c \
        u_timed_winsys.c \
index 8317263..d3ac7f7 100644 (file)
@@ -24,6 +24,7 @@ util = env.ConvenienceLibrary(
                'u_snprintf.c',
                'u_stream_stdc.c',
                'u_stream_wd.c',
+               'u_surface.c',
                'u_tile.c',
                'u_time.c',
                'u_timed_winsys.c',
diff --git a/src/gallium/auxiliary/util/u_surface.c b/src/gallium/auxiliary/util/u_surface.c
new file mode 100644 (file)
index 0000000..85e4432
--- /dev/null
@@ -0,0 +1,113 @@
+/**************************************************************************
+ *
+ * Copyright 2009 VMware, Inc.  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 VMWARE 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.
+ *
+ **************************************************************************/
+
+/**
+ * @file
+ * Surface utility functions.
+ *  
+ * @author Brian Paul
+ */
+
+
+#include "pipe/p_screen.h"
+#include "pipe/p_state.h"
+#include "pipe/p_defines.h"
+
+#include "util/u_surface.h"
+
+
+/**
+ * Helper to quickly create an RGBA rendering surface of a certain size.
+ * \param textureOut  returns the new texture
+ * \param surfaceOut  returns the new surface
+ * \return TRUE for success, FALSE if failure
+ */
+boolean
+util_create_rgba_surface(struct pipe_screen *screen,
+                         uint width, uint height,
+                         struct pipe_texture **textureOut,
+                         struct pipe_surface **surfaceOut)
+{
+   static const enum pipe_format rgbaFormats[] = {
+      PIPE_FORMAT_A8R8G8B8_UNORM,
+      PIPE_FORMAT_B8G8R8A8_UNORM,
+      PIPE_FORMAT_R8G8B8A8_UNORM,
+      PIPE_FORMAT_NONE
+   };
+   const uint target = PIPE_TEXTURE_2D;
+   const uint usage = PIPE_TEXTURE_USAGE_RENDER_TARGET;
+   enum pipe_format format = PIPE_FORMAT_NONE;
+   struct pipe_texture templ;
+   uint i;
+
+   /* Choose surface format */
+   for (i = 0; rgbaFormats[i]; i++) {
+      if (screen->is_format_supported(screen, rgbaFormats[i],
+                                      target, usage, 0)) {
+         format = rgbaFormats[i];
+         break;
+      }
+   }
+   if (format == PIPE_FORMAT_NONE)
+      return FALSE;  /* unable to get an rgba format!?! */
+
+   /* create texture */
+   memset(&templ, 0, sizeof(templ));
+   templ.target = target;
+   templ.format = format;
+   templ.last_level = 0;
+   templ.width[0] = width;
+   templ.height[0] = height;
+   templ.depth[0] = 1;
+   pf_get_block(format, &templ.block);
+   templ.tex_usage = usage;
+
+   *textureOut = screen->texture_create(screen, &templ);
+   if (!*textureOut)
+      return FALSE;
+
+   /* create surface / view into texture */
+   *surfaceOut = screen->get_tex_surface(screen, *textureOut, 0, 0, 0, PIPE_BUFFER_USAGE_GPU_WRITE);
+   if (!*surfaceOut) {
+      pipe_texture_reference(textureOut, NULL);
+      return FALSE;
+   }
+
+   return TRUE;
+}
+
+
+/**
+ * Release the surface and texture from util_create_rgba_surface().
+ */
+void
+util_destroy_rgba_surface(struct pipe_texture *texture,
+                          struct pipe_surface *surface)
+{
+   pipe_surface_reference(&surface, NULL);
+   pipe_texture_reference(&texture, NULL);
+}
+
diff --git a/src/gallium/auxiliary/util/u_surface.h b/src/gallium/auxiliary/util/u_surface.h
new file mode 100644 (file)
index 0000000..a5b73cf
--- /dev/null
@@ -0,0 +1,52 @@
+/**************************************************************************
+ *
+ * Copyright 2009 VMware, Inc.  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 VMWARE 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 U_SURFACE_H
+#define U_SURFACE_H
+
+
+#include "pipe/p_compiler.h"
+
+
+struct pipe_screen;
+struct pipe_texture;
+struct pipe_surface;
+
+
+extern boolean
+util_create_rgba_surface(struct pipe_screen *screen,
+                         uint width, uint height,
+                         struct pipe_texture **textureOut,
+                         struct pipe_surface **surfaceOut);
+
+
+extern void
+util_destroy_rgba_surface(struct pipe_texture *texture,
+                          struct pipe_surface *surface);
+
+
+#endif /* U_SURFACE_H */
index 808be58..ebb7a7a 100644 (file)
@@ -99,6 +99,28 @@ static const struct debug_named_value cell_debug_flags[] = {
    {NULL, 0}
 };
 
+static unsigned int
+cell_is_texture_referenced( struct pipe_context *pipe,
+                           struct pipe_texture *texture,
+                           unsigned face, unsigned level)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
+static unsigned int
+cell_is_buffer_referenced( struct pipe_context *pipe,
+                          struct pipe_buffer *buf)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
 
 struct pipe_context *
 cell_create_context(struct pipe_screen *screen,
@@ -122,6 +144,9 @@ cell_create_context(struct pipe_screen *screen,
    cell->pipe.clear = cell_clear;
    cell->pipe.flush = cell_flush;
 
+   cell->pipe.is_texture_referenced = cell_is_texture_referenced;
+   cell->pipe.is_buffer_referenced = cell_is_buffer_referenced;
+
 #if 0
    cell->pipe.begin_query = cell_begin_query;
    cell->pipe.end_query = cell_end_query;
index fcad717..37184ea 100644 (file)
@@ -105,7 +105,28 @@ static boolean failover_draw_arrays( struct pipe_context *pipe,
    return failover_draw_elements(pipe, NULL, 0, prim, start, count);
 }
 
+static unsigned int
+failover_is_texture_referenced( struct pipe_context *_pipe,
+                               struct pipe_texture *texture,
+                               unsigned face, unsigned level)
+{
+   struct failover_context *failover = failover_context( _pipe );
+   struct pipe_context *pipe = (failover->mode == FO_HW) ?
+      failover->hw : failover->sw;
+
+   return pipe->is_texture_referenced(pipe, texture, face, level);
+}
 
+static unsigned int
+failover_is_buffer_referenced( struct pipe_context *_pipe,
+                              struct pipe_buffer *buf)
+{
+   struct failover_context *failover = failover_context( _pipe );
+   struct pipe_context *pipe = (failover->mode == FO_HW) ?
+      failover->hw : failover->sw;
+
+   return pipe->is_buffer_referenced(pipe, buf);
+}
 
 struct pipe_context *failover_create( struct pipe_context *hw,
                                      struct pipe_context *sw )
@@ -151,6 +172,8 @@ struct pipe_context *failover_create( struct pipe_context *hw,
 #endif
 
    failover->pipe.flush = hw->flush;
+   failover->pipe.is_texture_referenced = failover_is_texture_referenced;
+   failover->pipe.is_buffer_referenced = failover_is_buffer_referenced;
 
    failover->dirty = 0;
 
index 3e3a596..ccf9bb3 100644 (file)
@@ -136,6 +136,29 @@ static boolean i915_draw_arrays( struct pipe_context *pipe,
 }
 
 
+static unsigned int
+i915_is_texture_referenced( struct pipe_context *pipe,
+                           struct pipe_texture *texture,
+                           unsigned face, unsigned level)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
+static unsigned int
+i915_is_buffer_referenced( struct pipe_context *pipe,
+                          struct pipe_buffer *buf)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
 
 struct pipe_context *i915_create_context( struct pipe_screen *screen,
                                           struct pipe_winsys *pipe_winsys,
@@ -160,6 +183,9 @@ struct pipe_context *i915_create_context( struct pipe_screen *screen,
    i915->pipe.draw_elements = i915_draw_elements;
    i915->pipe.draw_range_elements = i915_draw_range_elements;
 
+   i915->pipe.is_texture_referenced = i915_is_texture_referenced;
+   i915->pipe.is_buffer_referenced = i915_is_buffer_referenced;
+
    /*
     * Create drawing context and plug our rendering stage into it.
     */
index c74cbf8..9b33285 100644 (file)
@@ -73,6 +73,28 @@ static void brw_clear(struct pipe_context *pipe, struct pipe_surface *ps,
    pipe->surface_fill(pipe, ps, x, y, w, h, clearValue);
 }
 
+static unsigned int
+brw_is_texture_referenced( struct pipe_context *pipe,
+                          struct pipe_texture *texture,
+                          unsigned face, unsigned level)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
+static unsigned int
+brw_is_buffer_referenced( struct pipe_context *pipe,
+                         struct pipe_buffer *buf)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
 
 struct pipe_context *brw_create(struct pipe_screen *screen,
                                 struct brw_winsys *brw_winsys,
@@ -94,6 +116,9 @@ struct pipe_context *brw_create(struct pipe_screen *screen,
    brw->pipe.destroy = brw_destroy;
    brw->pipe.clear = brw_clear;
 
+   brw->pipe.is_texture_referenced = brw_is_texture_referenced;
+   brw->pipe.is_buffer_referenced = brw_is_buffer_referenced;
+
    brw_init_surface_functions(brw);
    brw_init_texture_functions(brw);
    brw_init_state_functions(brw);
index d6710cd..17166c9 100644 (file)
@@ -64,6 +64,30 @@ nv04_init_hwctx(struct nv04_context *nv04)
        return TRUE;
 }
 
+static unsigned int
+nv04_is_texture_referenced( struct pipe_context *pipe,
+                           struct pipe_texture *texture,
+                           unsigned face, unsigned level)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
+static unsigned int
+nv04_is_buffer_referenced( struct pipe_context *pipe,
+                          struct pipe_buffer *buf)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
+
 struct pipe_context *
 nv04_create(struct pipe_screen *pscreen, unsigned pctx_id)
 {
@@ -89,6 +113,9 @@ nv04_create(struct pipe_screen *pscreen, unsigned pctx_id)
        nv04->pipe.clear = nv04_clear;
        nv04->pipe.flush = nv04_flush;
 
+       nv04->pipe.is_texture_referenced = nv04_is_texture_referenced;
+       nv04->pipe.is_buffer_referenced = nv04_is_buffer_referenced;
+
        nv04_init_surface_functions(nv04);
        nv04_init_state_functions(nv04);
 
index ef2c0c5..3da8d2f 100644 (file)
@@ -257,6 +257,29 @@ nv10_set_edgeflags(struct pipe_context *pipe, const unsigned *bitfield)
 {
 }
 
+static unsigned int
+nv10_is_texture_referenced( struct pipe_context *pipe,
+                           struct pipe_texture *texture,
+                           unsigned face, unsigned level)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
+static unsigned int
+nv10_is_buffer_referenced( struct pipe_context *pipe,
+                          struct pipe_buffer *buf)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
 struct pipe_context *
 nv10_create(struct pipe_screen *pscreen, unsigned pctx_id)
 {
@@ -282,6 +305,9 @@ nv10_create(struct pipe_screen *pscreen, unsigned pctx_id)
        nv10->pipe.clear = nv10_clear;
        nv10->pipe.flush = nv10_flush;
 
+       nv10->pipe.is_texture_referenced = nv10_is_texture_referenced;
+       nv10->pipe.is_buffer_referenced = nv10_is_buffer_referenced;
+
        nv10_init_surface_functions(nv10);
        nv10_init_state_functions(nv10);
 
index 1659aec..cbc4170 100644 (file)
@@ -380,6 +380,30 @@ nv20_set_edgeflags(struct pipe_context *pipe, const unsigned *bitfield)
 {
 }
 
+
+static unsigned int
+nv20_is_texture_referenced( struct pipe_context *pipe,
+                           struct pipe_texture *texture,
+                           unsigned face, unsigned level)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
+static unsigned int
+nv20_is_buffer_referenced( struct pipe_context *pipe,
+                          struct pipe_buffer *buf)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
 struct pipe_context *
 nv20_create(struct pipe_screen *pscreen, unsigned pctx_id)
 {
@@ -405,6 +429,9 @@ nv20_create(struct pipe_screen *pscreen, unsigned pctx_id)
        nv20->pipe.clear = nv20_clear;
        nv20->pipe.flush = nv20_flush;
 
+       nv20->pipe.is_texture_referenced = nv20_is_texture_referenced;
+       nv20->pipe.is_buffer_referenced = nv20_is_buffer_referenced;
+
        nv20_init_surface_functions(nv20);
        nv20_init_state_functions(nv20);
 
index 61654f8..f827bdc 100644 (file)
@@ -31,6 +31,29 @@ nv30_destroy(struct pipe_context *pipe)
        FREE(nv30);
 }
 
+static unsigned int
+nv30_is_texture_referenced( struct pipe_context *pipe,
+                           struct pipe_texture *texture,
+                           unsigned face, unsigned level)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
+static unsigned int
+nv30_is_buffer_referenced( struct pipe_context *pipe,
+                          struct pipe_buffer *buf)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
 struct pipe_context *
 nv30_create(struct pipe_screen *pscreen, unsigned pctx_id)
 {
@@ -55,6 +78,9 @@ nv30_create(struct pipe_screen *pscreen, unsigned pctx_id)
        nv30->pipe.clear = nv30_clear;
        nv30->pipe.flush = nv30_flush;
 
+       nv30->pipe.is_texture_referenced = nv30_is_texture_referenced;
+       nv30->pipe.is_buffer_referenced = nv30_is_buffer_referenced;
+
        nv30_init_query_functions(nv30);
        nv30_init_surface_functions(nv30);
        nv30_init_state_functions(nv30);
index 5d325f5..8eba6a4 100644 (file)
@@ -31,6 +31,29 @@ nv40_destroy(struct pipe_context *pipe)
        FREE(nv40);
 }
 
+static unsigned int
+nv40_is_texture_referenced( struct pipe_context *pipe,
+                           struct pipe_texture *texture,
+                           unsigned face, unsigned level)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
+static unsigned int
+nv40_is_buffer_referenced( struct pipe_context *pipe,
+                          struct pipe_buffer *buf)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
 struct pipe_context *
 nv40_create(struct pipe_screen *pscreen, unsigned pctx_id)
 {
@@ -55,6 +78,9 @@ nv40_create(struct pipe_screen *pscreen, unsigned pctx_id)
        nv40->pipe.clear = nv40_clear;
        nv40->pipe.flush = nv40_flush;
 
+       nv40->pipe.is_texture_referenced = nv40_is_texture_referenced;
+       nv40->pipe.is_buffer_referenced = nv40_is_buffer_referenced;
+
        nv40_init_query_functions(nv40);
        nv40_init_surface_functions(nv40);
        nv40_init_state_functions(nv40);
index 565a5da..a511f65 100644 (file)
@@ -51,6 +51,29 @@ nv50_set_edgeflags(struct pipe_context *pipe, const unsigned *bitfield)
 {
 }
 
+static unsigned int
+nv50_is_texture_referenced( struct pipe_context *pipe,
+                           struct pipe_texture *texture,
+                           unsigned face, unsigned level)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
+static unsigned int
+nv50_is_buffer_referenced( struct pipe_context *pipe,
+                          struct pipe_buffer *buf)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
 struct pipe_context *
 nv50_create(struct pipe_screen *pscreen, unsigned pctx_id)
 {
@@ -76,6 +99,9 @@ nv50_create(struct pipe_screen *pscreen, unsigned pctx_id)
 
        nv50->pipe.flush = nv50_flush;
 
+       nv50->pipe.is_texture_referenced = nv50_is_texture_referenced;
+       nv50->pipe.is_buffer_referenced = nv50_is_buffer_referenced;
+
        nv50_init_surface_functions(nv50);
        nv50_init_state_functions(nv50);
        nv50_init_query_functions(nv50);
index 31efe91..6bdf544 100644 (file)
@@ -102,6 +102,29 @@ static void r300_destroy_context(struct pipe_context* context) {
     FREE(r300);
 }
 
+static unsigned int
+r300_is_texture_referenced( struct pipe_context *pipe,
+                           struct pipe_texture *texture,
+                           unsigned face, unsigned level)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
+static unsigned int
+r300_is_buffer_referenced( struct pipe_context *pipe,
+                          struct pipe_buffer *buf)
+{
+   /**
+    * FIXME: Optimize.
+    */
+
+   return PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE;
+}
+
 struct pipe_context* r300_create_context(struct pipe_screen* screen,
                                          struct r300_winsys* r300_winsys)
 {
@@ -124,6 +147,9 @@ struct pipe_context* r300_create_context(struct pipe_screen* screen,
     r300->context.draw_elements = r300_draw_elements;
     r300->context.draw_range_elements = r300_draw_range_elements;
 
+    r300->context.is_texture_referenced = r300_is_texture_referenced;
+    r300->context.is_buffer_referenced = r300_is_buffer_referenced;
+
     r300->draw = draw_create();
     draw_set_rasterize_stage(r300->draw, r300_draw_stage(r300));
 
index b7ee8fb..cbd84d7 100644 (file)
@@ -234,6 +234,8 @@ static void r300_render_draw(struct vbuf_render* render,
     struct pipe_screen* screen = r300->context.screen;
     struct pipe_buffer* index_buffer;
     void* index_map;
+    int i;
+    uint32_t index;
 
     CS_LOCALS(r300);
 
@@ -252,14 +254,24 @@ static void r300_render_draw(struct vbuf_render* render,
     pipe_buffer_unmap(screen, index_buffer);
 
     debug_printf("r300: Doing indexbuf render, count %d\n", count);
-
-    BEGIN_CS(6);
+/*
+    BEGIN_CS(8);
     OUT_CS_PKT3(R300_PACKET3_3D_DRAW_INDX_2, 0);
     OUT_CS(R300_VAP_VF_CNTL__PRIM_WALK_INDICES | (count << 16) |
            r300render->hwprim);
     OUT_CS_PKT3(R300_PACKET3_INDX_BUFFER, 2);
     OUT_CS(R300_INDX_BUFFER_ONE_REG_WR | (R300_VAP_PORT_IDX0 >> 2));
     OUT_CS_INDEX_RELOC(index_buffer, 0, count, RADEON_GEM_DOMAIN_GTT, 0, 0);
+    END_CS; */
+
+    BEGIN_CS(2 + count);
+    OUT_CS_PKT3(R300_PACKET3_3D_DRAW_INDX_2, count);
+    OUT_CS(R300_VAP_VF_CNTL__PRIM_WALK_INDICES | (count << 16) |
+           r300render->hwprim | R300_VAP_VF_CNTL__INDEX_SIZE_32bit);
+    for (i = 0; i < count; i++) {
+        index = indices[i];
+        OUT_CS(index);
+    }
     END_CS;
 }
 
index 2a77fd1..c9507ae 100644 (file)
@@ -555,25 +555,41 @@ static void r300_set_viewport_state(struct pipe_context* pipe,
 {
     struct r300_context* r300 = r300_context(pipe);
 
-    r300->viewport_state->xscale = state->scale[0];
-    r300->viewport_state->yscale = state->scale[1];
-    r300->viewport_state->zscale = state->scale[2];
-
-    r300->viewport_state->xoffset = state->translate[0];
-    r300->viewport_state->yoffset = state->translate[1];
-    r300->viewport_state->zoffset = state->translate[2];
-
-    r300->viewport_state->vte_control = 0;
     if (r300_screen(r300->context.screen)->caps->has_tcl) {
         /* Do the transform in HW. */
-        r300->viewport_state->vte_control |=
-            R300_VPORT_X_SCALE_ENA | R300_VPORT_X_OFFSET_ENA |
-            R300_VPORT_Y_SCALE_ENA | R300_VPORT_Y_OFFSET_ENA |
-            R300_VPORT_Z_SCALE_ENA | R300_VPORT_Z_OFFSET_ENA;
+        r300->viewport_state->vte_control = R300_VTX_W0_FMT;
+
+        if (state->scale[0] != 1.0f) {
+            r300->viewport_state->xscale = state->scale[0];
+            r300->viewport_state->vte_control |= R300_VPORT_X_SCALE_ENA;
+        }
+        if (state->scale[1] != 1.0f) {
+            r300->viewport_state->yscale = state->scale[1];
+            r300->viewport_state->vte_control |= R300_VPORT_Y_SCALE_ENA;
+        }
+        if (state->scale[2] != 1.0f) {
+            r300->viewport_state->zscale = state->scale[2];
+            r300->viewport_state->vte_control |= R300_VPORT_Z_SCALE_ENA;
+        }
+        if (state->translate[0] != 0.0f) {
+            r300->viewport_state->xoffset = state->translate[0];
+            r300->viewport_state->vte_control |= R300_VPORT_X_OFFSET_ENA;
+        }
+        if (state->translate[1] != 0.0f) {
+            r300->viewport_state->yoffset = state->translate[1];
+            r300->viewport_state->vte_control |= R300_VPORT_Y_OFFSET_ENA;
+        }
+        if (state->translate[2] != 0.0f) {
+            r300->viewport_state->zoffset = state->translate[2];
+            r300->viewport_state->vte_control |= R300_VPORT_Z_OFFSET_ENA;
+        }
     } else {
+        r300->viewport_state->vte_control = 0;
         /* Have Draw do the actual transform. */
         draw_set_viewport_state(r300->draw, state);
     }
+
+    r300->dirty_state |= R300_NEW_VIEWPORT;
 }
 
 static void r300_set_vertex_buffers(struct pipe_context* pipe,
index ce7ab6f..c4c9784 100644 (file)
@@ -86,7 +86,7 @@ static void r300_vs_tab_routes(struct r300_context* r300,
                     break;
                 case TGSI_SEMANTIC_PSIZE:
                     psize = TRUE;
-                    tab[i] = 1;
+                    tab[i] = 15;
                     break;
                 case TGSI_SEMANTIC_FOG:
                     fog = TRUE;
index 47d6c6d..bb96e2a 100644 (file)
@@ -40,6 +40,9 @@ static void r300_vs_declare(struct r300_vs_asm* assembler,
                     /* XXX multiple? */
                     assembler->tab[decl->DeclarationRange.First] = 6;
                     break;
+                case TGSI_SEMANTIC_PSIZE:
+                    assembler->tab[decl->DeclarationRange.First] = 15;
+                    break;
                 default:
                     debug_printf("r300: vs: Bad semantic declaration %d\n",
                         decl->Semantic.SemanticName);
@@ -117,6 +120,9 @@ static INLINE unsigned r300_vs_dst(struct r300_vs_asm* assembler,
 static uint32_t r300_vs_op(unsigned op)
 {
     switch (op) {
+        case TGSI_OPCODE_DP3:
+        case TGSI_OPCODE_DP4:
+            return R300_VE_DOT_PRODUCT;
         case TGSI_OPCODE_MUL:
             return R300_VE_MULTIPLY;
         case TGSI_OPCODE_ADD:
@@ -195,6 +201,36 @@ static void r300_vs_instruction(struct r300_vertex_shader* vs,
                     &inst->FullDstRegisters[0], inst->Instruction.Opcode,
                     2);
             break;
+        case TGSI_OPCODE_DP3:
+            /* Set alpha swizzle to zero for src0 and src1 */
+            if (!inst->FullSrcRegisters[0].SrcRegister.Extended) {
+                inst->FullSrcRegisters[0].SrcRegister.Extended = TRUE;
+                inst->FullSrcRegisters[0].SrcRegisterExtSwz.ExtSwizzleX =
+                    inst->FullSrcRegisters[0].SrcRegister.SwizzleX;
+                inst->FullSrcRegisters[0].SrcRegisterExtSwz.ExtSwizzleY =
+                    inst->FullSrcRegisters[0].SrcRegister.SwizzleY;
+                inst->FullSrcRegisters[0].SrcRegisterExtSwz.ExtSwizzleZ =
+                    inst->FullSrcRegisters[0].SrcRegister.SwizzleZ;
+            }
+            inst->FullSrcRegisters[0].SrcRegisterExtSwz.ExtSwizzleW =
+                TGSI_EXTSWIZZLE_ZERO;
+            if (!inst->FullSrcRegisters[1].SrcRegister.Extended) {
+                inst->FullSrcRegisters[1].SrcRegister.Extended = TRUE;
+                inst->FullSrcRegisters[1].SrcRegisterExtSwz.ExtSwizzleX =
+                    inst->FullSrcRegisters[1].SrcRegister.SwizzleX;
+                inst->FullSrcRegisters[1].SrcRegisterExtSwz.ExtSwizzleY =
+                    inst->FullSrcRegisters[1].SrcRegister.SwizzleY;
+                inst->FullSrcRegisters[1].SrcRegisterExtSwz.ExtSwizzleZ =
+                    inst->FullSrcRegisters[1].SrcRegister.SwizzleZ;
+            }
+            inst->FullSrcRegisters[1].SrcRegisterExtSwz.ExtSwizzleW =
+                TGSI_EXTSWIZZLE_ZERO;
+            /* Fall through */
+        case TGSI_OPCODE_DP4:
+            r300_vs_emit_inst(vs, assembler, inst->FullSrcRegisters,
+                    &inst->FullDstRegisters[0], inst->Instruction.Opcode,
+                    2);
+            break;
         case TGSI_OPCODE_MOV:
         case TGSI_OPCODE_SWZ:
             inst->FullSrcRegisters[1] = r300_constant_zero;
index 3d10e24..de94402 100644 (file)
@@ -32,6 +32,7 @@
 
 /* XXX get these to r300_reg */
 #define R300_PVS_DST_OPCODE(x)   ((x) << 0)
+#   define R300_VE_DOT_PRODUCT            1
 #   define R300_VE_MULTIPLY               2
 #   define R300_VE_ADD                    3
 #define R300_PVS_DST_MACRO_INST    (1 << 7)
index 06ace27..6ae4d1a 100644 (file)
@@ -121,6 +121,21 @@ static void softpipe_destroy( struct pipe_context *pipe )
    FREE( softpipe );
 }
 
+static unsigned int
+softpipe_is_texture_referenced( struct pipe_context *pipe,
+                               struct pipe_texture *texture,
+                               unsigned face, unsigned level,
+                               unsigned zslice)
+{
+   return PIPE_UNREFERENCED;
+}
+
+static unsigned int
+softpipe_is_buffer_referenced( struct pipe_context *pipe,
+                              struct pipe_buffer *buf)
+{
+   return PIPE_UNREFERENCED;
+}
 
 struct pipe_context *
 softpipe_create( struct pipe_screen *screen,
@@ -190,6 +205,9 @@ softpipe_create( struct pipe_screen *screen,
    softpipe->pipe.clear = softpipe_clear;
    softpipe->pipe.flush = softpipe_flush;
 
+   softpipe->pipe.is_texture_referenced = softpipe_is_texture_referenced;
+   softpipe->pipe.is_buffer_referenced = softpipe_is_buffer_referenced;
+
    softpipe_init_query_funcs( softpipe );
    softpipe_init_texture_funcs( softpipe );
 
index d8d5821..556b5e0 100644 (file)
@@ -1030,6 +1030,48 @@ trace_context_destroy(struct pipe_context *_pipe)
    FREE(tr_ctx);
 }
 
+static unsigned int
+trace_is_texture_referenced( struct pipe_context *_pipe,
+                           struct pipe_texture *texture,
+                           unsigned face, unsigned level)
+{
+   struct trace_context *tr_ctx = trace_context(_pipe);
+   struct pipe_context *pipe = tr_ctx->pipe;
+   unsigned int referenced;
+
+   trace_dump_call_begin("pipe_context", "is_texture_referenced");
+   trace_dump_arg(ptr, pipe);
+   trace_dump_arg(ptr, texture);
+   trace_dump_arg(uint, face);
+   trace_dump_arg(uint, level);
+
+   referenced = pipe->is_texture_referenced(pipe, texture, face, level);
+
+   trace_dump_ret(uint, referenced);
+   trace_dump_call_end();
+
+   return referenced;
+}
+
+static unsigned int
+trace_is_buffer_referenced( struct pipe_context *_pipe,
+                           struct pipe_buffer *buf)
+{
+   struct trace_context *tr_ctx = trace_context(_pipe);
+   struct pipe_context *pipe = tr_ctx->pipe;
+   unsigned int referenced;
+
+   trace_dump_call_begin("pipe_context", "is_buffer_referenced");
+   trace_dump_arg(ptr, pipe);
+   trace_dump_arg(ptr, buf);
+
+   referenced = pipe->is_buffer_referenced(pipe, buf);
+
+   trace_dump_ret(uint, referenced);
+   trace_dump_call_end();
+
+   return referenced;
+}
 
 struct pipe_context *
 trace_context_create(struct pipe_screen *_screen,
@@ -1096,6 +1138,8 @@ trace_context_create(struct pipe_screen *_screen,
    tr_ctx->base.surface_fill = trace_context_surface_fill;
    tr_ctx->base.clear = trace_context_clear;
    tr_ctx->base.flush = trace_context_flush;
+   tr_ctx->base.is_texture_referenced = trace_is_texture_referenced;
+   tr_ctx->base.is_buffer_referenced = trace_is_buffer_referenced;
 
    tr_ctx->pipe = pipe;
 
index c5c8397..57e966a 100644 (file)
@@ -42,7 +42,6 @@ struct pipe_state_cache;
 struct pipe_query;
 struct pipe_winsys;
 
-
 /**
  * Gallium rendering context.  Basically:
  *  - state setting functions
@@ -231,6 +230,34 @@ struct pipe_context {
    void (*flush)( struct pipe_context *pipe,
                   unsigned flags,
                   struct pipe_fence_handle **fence );
+
+   /**
+    * Check whether a texture is referenced by an unflushed hw command.
+    * The state-tracker uses this function to optimize away unnecessary
+    * flushes. It is safe (but wasteful) to always return.
+    * PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE.
+    * \param pipe  The pipe context whose unflushed hw commands will be
+    *              checked.
+    * \param level  mipmap level.
+    * \param texture  texture to check.
+    * \param face  cubemap face. Use 0 for non-cubemap texture.
+    */
+
+   unsigned int (*is_texture_referenced) (struct pipe_context *pipe,
+                                         struct pipe_texture *texture,
+                                         unsigned face, unsigned level);
+   /**
+    * Check whether a buffer is referenced by an unflushed hw command.
+    * The state-tracker uses this function to optimize away unnecessary
+    * flushes. It is safe (but wasteful) to always return
+    * PIPE_REFERENCED_FOR_READ | PIPE_REFERENCED_FOR_WRITE.
+    * \param pipe  The pipe context whose unflushed hw commands will be
+    *              checked.
+    * \param buf  Buffer to check.
+    */
+
+   unsigned int (*is_buffer_referenced) (struct pipe_context *pipe,
+                                        struct pipe_buffer *buf);
 };
 
 
index 1d2aa10..82e23c4 100644 (file)
@@ -312,6 +312,13 @@ enum pipe_transfer_usage {
 #define PIPE_CAP_MAX_VERTEX_TEXTURE_UNITS 26
 
 
+/**
+ * Referenced query flags.
+ */
+
+#define PIPE_UNREFERENCED         0
+#define PIPE_REFERENCED_FOR_READ  (1 << 0)
+#define PIPE_REFERENCED_FOR_WRITE (1 << 1)
 
 #ifdef __cplusplus
 }
index e5c0db4..b9e0706 100644 (file)
@@ -1702,7 +1702,8 @@ PUBLIC GLXFBConfig *glXGetFBConfigs(Display *dpy, int screen, int *nelements)
     int   i;
 
     *nelements = 0;
-    if ( (priv->screenConfigs != NULL)
+    if ( priv
+         && (priv->screenConfigs != NULL)
         && (screen >= 0) && (screen <= ScreenCount(dpy))
         && (priv->screenConfigs[screen].configs != NULL)
         && (priv->screenConfigs[screen].configs->fbconfigID != GLX_DONT_CARE) ) {
index f2868cb..89c8157 100644 (file)
       rgba[3] = 0xff;                                                  \
    } while (0)
 
+#elif (SPANTMP_PIXEL_FMT == GL_BGRA)  && (SPANTMP_PIXEL_TYPE == GL_UNSIGNED_SHORT_4_4_4_4_REV)
+
+/**
+ ** GL_BGRA, GL_UNSIGNED_SHORT_4_4_4_4_REV
+ **/
+
+#ifndef GET_VALUE
+#ifndef GET_PTR
+#define GET_PTR(_x, _y) (buf + (_x) * 2 + (_y) * pitch)
+#endif
+
+#define GET_VALUE(_x, _y) *(volatile GLushort *)(GET_PTR(_x, _y))
+#define PUT_VALUE(_x, _y, _v) *(volatile GLushort *)(GET_PTR(_x, _y)) = (_v)
+#endif /* GET_VALUE */
+
+#define INIT_MONO_PIXEL(p, color) \
+   p = PACK_COLOR_4444(color[3], color[0], color[1], color[2])
+
+#define WRITE_RGBA( _x, _y, r, g, b, a )                               \
+   PUT_VALUE(_x, _y, PACK_COLOR_4444(a, r, g, b))                      \
+
+#define WRITE_PIXEL( _x, _y, p ) PUT_VALUE(_x, _y, p)
+
+#define READ_RGBA( rgba, _x, _y )                                      \
+   do {                                                                        \
+      GLushort p = GET_VALUE(_x, _y);                                  \
+      rgba[0] = ((p >> 8) & 0xf) * 0x11;                               \
+      rgba[1] = ((p >> 4) & 0xf) * 0x11;                               \
+      rgba[2] = ((p >> 0) & 0xf) * 0x11;                               \
+      rgba[3] = ((p >> 12) & 0xf) * 0x11;                              \
+   } while (0)
+
+
+#elif (SPANTMP_PIXEL_FMT == GL_BGRA)  && (SPANTMP_PIXEL_TYPE == GL_UNSIGNED_SHORT_1_5_5_5_REV)
+
+/**
+ ** GL_BGRA, GL_UNSIGNED_SHORT_1_5_5_5_REV
+ **/
+
+#ifndef GET_VALUE
+#ifndef GET_PTR
+#define GET_PTR(_x, _y) (buf + (_x) * 2 + (_y) * pitch)
+#endif
+
+#define GET_VALUE(_x, _y) *(volatile GLushort *)(GET_PTR(_x, _y))
+#define PUT_VALUE(_x, _y, _v) *(volatile GLushort *)(GET_PTR(_x, _y)) = (_v)
+#endif /* GET_VALUE */
+
+#define INIT_MONO_PIXEL(p, color) \
+   p = PACK_COLOR_1555(color[3], color[0], color[1], color[2])
+
+#define WRITE_RGBA( _x, _y, r, g, b, a )                               \
+   PUT_VALUE(_x, _y, PACK_COLOR_1555(a, r, g, b))                      \
+
+#define WRITE_PIXEL( _x, _y, p ) PUT_VALUE(_x, _y, p)
+
+#define READ_RGBA( rgba, _x, _y )                                      \
+   do {                                                                        \
+      GLushort p = GET_VALUE(_x, _y);                                  \
+      rgba[0] = ((p >> 7) & 0xf8) * 255 / 0xf8;                                \
+      rgba[1] = ((p >> 2) & 0xf8) * 255 / 0xf8;                                \
+      rgba[2] = ((p << 3) & 0xf8) * 255 / 0xf8;                                \
+      rgba[3] = ((p >> 15) & 0x1) * 0xff;                              \
+   } while (0)
+
 #elif (SPANTMP_PIXEL_FMT == GL_BGRA) && (SPANTMP_PIXEL_TYPE == GL_UNSIGNED_INT_8_8_8_8_REV)
 
 /**
index 954a7e2..9f4bd16 100644 (file)
@@ -11,7 +11,6 @@ DRIVER_SOURCES = \
        i830_metaops.c \
        i830_state.c \
        i830_texblend.c \
-       i830_tex.c \
        i830_texstate.c \
        i830_vtbl.c \
        intel_render.c \
@@ -36,7 +35,6 @@ DRIVER_SOURCES = \
        intel_buffers.c \
        intel_blit.c \
        intel_swapbuffers.c \
-       i915_tex.c \
        i915_tex_layout.c \
        i915_texstate.c \
        i915_context.c \
index 9c540cb..10b9bf3 100644 (file)
@@ -47,7 +47,6 @@ i830InitDriverFunctions(struct dd_function_table *functions)
 {
    intelInitDriverFunctions(functions);
    i830InitStateFuncs(functions);
-   i830InitTextureFuncs(functions);
 }
 
 extern const struct tnl_pipeline_stage *intel_pipeline[];
diff --git a/src/mesa/drivers/dri/i915/i830_tex.c b/src/mesa/drivers/dri/i915/i830_tex.c
deleted file mode 100644 (file)
index 34ac42a..0000000
+++ /dev/null
@@ -1,100 +0,0 @@
-/**************************************************************************
- * 
- * Copyright 2003 Tungsten Graphics, Inc., Cedar Park, Texas.
- * 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/glheader.h"
-#include "main/mtypes.h"
-#include "main/imports.h"
-#include "main/simple_list.h"
-#include "main/enums.h"
-#include "main/image.h"
-#include "main/mm.h"
-#include "main/texstore.h"
-#include "main/texformat.h"
-#include "swrast/swrast.h"
-
-#include "texmem.h"
-
-#include "i830_context.h"
-#include "i830_reg.h"
-
-
-
-static void
-i830TexEnv(GLcontext * ctx, GLenum target,
-           GLenum pname, const GLfloat * param)
-{
-
-   switch (pname) {
-   case GL_TEXTURE_ENV_COLOR:
-   case GL_TEXTURE_ENV_MODE:
-   case GL_COMBINE_RGB:
-   case GL_COMBINE_ALPHA:
-   case GL_SOURCE0_RGB:
-   case GL_SOURCE1_RGB:
-   case GL_SOURCE2_RGB:
-   case GL_SOURCE0_ALPHA:
-   case GL_SOURCE1_ALPHA:
-   case GL_SOURCE2_ALPHA:
-   case GL_OPERAND0_RGB:
-   case GL_OPERAND1_RGB:
-   case GL_OPERAND2_RGB:
-   case GL_OPERAND0_ALPHA:
-   case GL_OPERAND1_ALPHA:
-   case GL_OPERAND2_ALPHA:
-   case GL_RGB_SCALE:
-   case GL_ALPHA_SCALE:
-      break;
-
-   case GL_TEXTURE_LOD_BIAS:{
-         struct i830_context *i830 = i830_context(ctx);
-         GLuint unit = ctx->Texture.CurrentUnit;
-         int b = (int) ((*param) * 16.0);
-         if (b > 63)
-            b = 63;
-         if (b < -64)
-            b = -64;
-         I830_STATECHANGE(i830, I830_UPLOAD_TEX(unit));
-         i830->lodbias_tm0s3[unit] =
-            ((b << TM0S3_LOD_BIAS_SHIFT) & TM0S3_LOD_BIAS_MASK);
-         break;
-      }
-
-   default:
-      break;
-   }
-}
-
-
-
-
-void
-i830InitTextureFuncs(struct dd_function_table *functions)
-{
-/*
-   functions->TexEnv = i830TexEnv;
-*/
-}
index 1a94921..3bf02de 100644 (file)
  **************************************************************************/
 
 #include "glapi/glapi.h"
+#include "main/texformat.h"
 
 #include "i830_context.h"
 #include "i830_reg.h"
 #include "intel_batchbuffer.h"
 #include "intel_regions.h"
 #include "intel_tris.h"
+#include "intel_fbo.h"
 #include "tnl/t_context.h"
 #include "tnl/t_vertex.h"
 
@@ -614,6 +616,8 @@ i830_state_draw_region(struct intel_context *intel,
 {
    struct i830_context *i830 = i830_context(&intel->ctx);
    GLcontext *ctx = &intel->ctx;
+   struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0];
+   struct intel_renderbuffer *irb = intel_renderbuffer(rb);
    GLuint value;
 
    ASSERT(state == &i830->state || state == &i830->meta);
@@ -651,13 +655,27 @@ i830_state_draw_region(struct intel_context *intel,
     */
    value = (DSTORG_HORT_BIAS(0x8) |     /* .5 */
             DSTORG_VERT_BIAS(0x8) | DEPTH_IS_Z);    /* .5 */
-            
-   if (color_region && color_region->cpp == 4) {
-      value |= DV_PF_8888;
-   }
-   else {
-      value |= DV_PF_565;
+
+   if (irb != NULL) {
+      switch (irb->texformat->MesaFormat) {
+      case MESA_FORMAT_ARGB8888:
+        value |= DV_PF_8888;
+        break;
+      case MESA_FORMAT_RGB565:
+        value |= DV_PF_565;
+        break;
+      case MESA_FORMAT_ARGB1555:
+        value |= DV_PF_1555;
+        break;
+      case MESA_FORMAT_ARGB4444:
+        value |= DV_PF_4444;
+        break;
+      default:
+        _mesa_problem(ctx, "Bad renderbuffer format: %d\n",
+                      irb->texformat->MesaFormat);
+      }
    }
+
    if (depth_region && depth_region->cpp == 4) {
       value |= DEPTH_FRMT_24_FIXED_8_OTHER;
    }
index 7549029..fdd2cf6 100644 (file)
@@ -83,7 +83,6 @@ i915InitDriverFunctions(struct dd_function_table *functions)
 {
    intelInitDriverFunctions(functions);
    i915InitStateFunctions(functions);
-   i915InitTextureFuncs(functions);
    i915InitFragProgFuncs(functions);
    functions->UpdateState = i915InvalidateState;
 }
index a5158de..2db10c6 100644 (file)
@@ -323,7 +323,8 @@ upload_program(struct i915_fragment_program *p)
       p->ctx->FragmentProgram._Current;
    const struct prog_instruction *inst = program->Base.Instructions;
 
-/*    _mesa_debug_fp_inst(program->Base.NumInstructions, inst); */
+   if (INTEL_DEBUG & DEBUG_WM)
+      _mesa_print_program(&program->Base);
 
    /* Is this a parse-failed program?  Ensure a valid program is
     * loaded, as the flagging of an error isn't sufficient to stop
@@ -1049,9 +1050,6 @@ i915ProgramStringNotify(GLcontext * ctx,
          _mesa_append_fog_code(ctx, &p->FragProg);
          p->FragProg.FogOption = GL_NONE;
       }
-
-      if (INTEL_DEBUG & DEBUG_STATE)
-        _mesa_print_program(prog);
    }
 
    _tnl_program_string(ctx, target, prog);
diff --git a/src/mesa/drivers/dri/i915/i915_tex.c b/src/mesa/drivers/dri/i915/i915_tex.c
deleted file mode 100644 (file)
index e38d8fe..0000000
+++ /dev/null
@@ -1,78 +0,0 @@
-/**************************************************************************
- * 
- * Copyright 2003 Tungsten Graphics, Inc., Cedar Park, Texas.
- * 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/glheader.h"
-#include "main/mtypes.h"
-#include "main/imports.h"
-#include "main/simple_list.h"
-#include "main/enums.h"
-#include "main/image.h"
-#include "main/mm.h"
-#include "main/texstore.h"
-#include "main/texformat.h"
-#include "swrast/swrast.h"
-
-#include "texmem.h"
-
-#include "i915_context.h"
-#include "i915_reg.h"
-
-
-
-static void
-i915TexEnv(GLcontext * ctx, GLenum target,
-           GLenum pname, const GLfloat * param)
-{
-   struct i915_context *i915 = I915_CONTEXT(ctx);
-
-   switch (pname) {
-   case GL_TEXTURE_LOD_BIAS:{
-         GLuint unit = ctx->Texture.CurrentUnit;
-         GLint b = (int) ((*param) * 16.0);
-         if (b > 255)
-            b = 255;
-         if (b < -256)
-            b = -256;
-         I915_STATECHANGE(i915, I915_UPLOAD_TEX(unit));
-         i915->lodbias_ss2[unit] =
-            ((b << SS2_LOD_BIAS_SHIFT) & SS2_LOD_BIAS_MASK);
-         break;
-      }
-
-   default:
-      break;
-   }
-}
-
-
-void
-i915InitTextureFuncs(struct dd_function_table *functions)
-{
-/*
-   functions->TexEnv = i915TexEnv;
-*/
-}
index 3f6d282..1150046 100644 (file)
@@ -32,6 +32,7 @@
 #include "main/imports.h"
 #include "main/macros.h"
 #include "main/colormac.h"
+#include "main/texformat.h"
 
 #include "tnl/t_context.h"
 #include "tnl/t_vertex.h"
@@ -40,6 +41,7 @@
 #include "intel_tex.h"
 #include "intel_regions.h"
 #include "intel_tris.h"
+#include "intel_fbo.h"
 
 #include "i915_reg.h"
 #include "i915_context.h"
@@ -542,6 +544,8 @@ i915_state_draw_region(struct intel_context *intel,
 {
    struct i915_context *i915 = i915_context(&intel->ctx);
    GLcontext *ctx = &intel->ctx;
+   struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[0];
+   struct intel_renderbuffer *irb = intel_renderbuffer(rb);
    GLuint value;
 
    ASSERT(state == &i915->state || state == &i915->meta);
@@ -580,12 +584,26 @@ i915_state_draw_region(struct intel_context *intel,
    value = (DSTORG_HORT_BIAS(0x8) |     /* .5 */
             DSTORG_VERT_BIAS(0x8) |     /* .5 */
             LOD_PRECLAMP_OGL | TEX_DEFAULT_COLOR_OGL);
-   if (color_region && color_region->cpp == 4) {
-      value |= DV_PF_8888;
-   }
-   else {
-      value |= (DITHER_FULL_ALWAYS | DV_PF_565);
+   if (irb != NULL) {
+      switch (irb->texformat->MesaFormat) {
+      case MESA_FORMAT_ARGB8888:
+        value |= DV_PF_8888;
+        break;
+      case MESA_FORMAT_RGB565:
+        value |= DV_PF_565 | DITHER_FULL_ALWAYS;
+        break;
+      case MESA_FORMAT_ARGB1555:
+        value |= DV_PF_1555 | DITHER_FULL_ALWAYS;
+        break;
+      case MESA_FORMAT_ARGB4444:
+        value |= DV_PF_4444 | DITHER_FULL_ALWAYS;
+        break;
+      default:
+        _mesa_problem(ctx, "Bad renderbuffer format: %d\n",
+                      irb->texformat->MesaFormat);
+      }
    }
+
    if (depth_region && depth_region->cpp == 4) {
       value |= DEPTH_FRMT_24_FIXED_8_OTHER;
    }
index dfab14a..fe1de82 100644 (file)
@@ -353,6 +353,14 @@ update_constant_buffer(struct brw_context *brw,
       map = const_buffer->virtual;
       memcpy(map, params->ParameterValues, size);
       dri_bo_unmap(const_buffer);
+
+      if (0) {
+         int i;
+         for (i = 0; i < params->NumParameters; i++) {
+            float *p = params->ParameterValues[i];
+            printf("%d: %f %f %f %f\n", i, p[0], p[1], p[2], p[3]);
+         }
+      }
    }
 }
 
@@ -363,6 +371,10 @@ update_vertex_constant_buffer(struct brw_context *brw)
 {
    struct brw_vertex_program *vp =
       (struct brw_vertex_program *) brw->vertex_program;
+   if (0) {
+      printf("update VS constants in buffer %p\n", vp->const_buffer);
+      printf("program %u\n", vp->program.Base.Id);
+   }
    update_constant_buffer(brw, vp->program.Base.Parameters, vp->const_buffer);
 }
 
index 66f8eb8..896e67d 100644 (file)
@@ -868,6 +868,7 @@ void brw_dp_READ_4( struct brw_compile *p,
 void brw_dp_READ_4_vs( struct brw_compile *p,
                        struct brw_reg dest,
                        GLboolean relAddr,
+                       struct brw_reg addrReg,
                        GLuint location,
                        GLuint bind_table_index );
 
index c731a93..df21416 100644 (file)
@@ -1003,15 +1003,18 @@ void brw_dp_READ_4( struct brw_compile *p,
 
 
 /**
- * Read float[4] constant from VS constant buffer.
+ * Read float[4] constant(s) from VS constant buffer.
+ * For relative addressing, two float[4] constants will be read into 'dest'.
+ * Otherwise, one float[4] constant will be read into the lower half of 'dest'.
  */
 void brw_dp_READ_4_vs(struct brw_compile *p,
                       struct brw_reg dest,
                       GLboolean relAddr,
+                      struct brw_reg addrReg,
                       GLuint location,
                       GLuint bind_table_index)
 {
-   const GLuint msg_reg_nr = 1;
+   GLuint msg_reg_nr = 1;
 
    /*
    printf("vs const read msg, location %u, msg_reg_nr %d\n",
@@ -1034,7 +1037,12 @@ void brw_dp_READ_4_vs(struct brw_compile *p,
       b = brw_message_reg(msg_reg_nr);
       b = retype(b, BRW_REGISTER_TYPE_UD);
       /*b = get_element_ud(b, 2);*/
-      brw_MOV(p, b, brw_imm_ud(location));
+      if (relAddr) {
+         brw_ADD(p, b, addrReg, brw_imm_ud(location));
+      }
+      else {
+         brw_MOV(p, b, brw_imm_ud(location));
+      }
 
       brw_pop_insn_state(p);
    }
@@ -1053,13 +1061,56 @@ void brw_dp_READ_4_vs(struct brw_compile *p,
 
       brw_set_dp_read_message(insn,
                              bind_table_index,
-                             0,  /* msg_control (0 means 1 Oword) */
+                             0,  /* msg_control (0 means 1 Oword, lower half) */
                              BRW_DATAPORT_READ_MESSAGE_OWORD_BLOCK_READ, /* msg_type */
                              0, /* source cache = data cache */
                              1, /* msg_length */
                              1, /* response_length (1 Oword) */
                              0); /* eot */
    }
+
+   if (relAddr) {
+      /* second read to get second constant */
+      msg_reg_nr++;
+      {
+         /* Setup MRF[1] with location/offset into const buffer */
+         struct brw_reg b;
+
+         brw_push_insn_state(p);
+         brw_set_compression_control(p, BRW_COMPRESSION_NONE);
+         brw_set_mask_control(p, BRW_MASK_DISABLE);
+         brw_set_predicate_control(p, BRW_PREDICATE_NONE);
+
+         b = brw_message_reg(msg_reg_nr);
+         b = retype(b, BRW_REGISTER_TYPE_UD);
+         addrReg = suboffset(addrReg, 1); /* upper half of addrReg */
+         brw_ADD(p, b, addrReg, brw_imm_ud(location));
+
+         brw_pop_insn_state(p);
+      }
+
+      {
+         struct brw_instruction *insn = next_insn(p, BRW_OPCODE_SEND);
+
+         insn->header.predicate_control = BRW_PREDICATE_NONE;
+         insn->header.compression_control = BRW_COMPRESSION_NONE; 
+         insn->header.destreg__conditonalmod = msg_reg_nr;
+         insn->header.mask_control = BRW_MASK_DISABLE;
+         /*insn->header.access_mode = BRW_ALIGN_16;*/
+
+         brw_set_dest(insn, dest);
+         brw_set_src0(insn, brw_null_reg());
+
+         brw_set_dp_read_message(insn,
+                                 bind_table_index,
+                                 1,  /* msg_control (1 means 1 Oword, upper half) */
+                                 BRW_DATAPORT_READ_MESSAGE_OWORD_BLOCK_READ, /* msg_type */
+                                 0, /* source cache = data cache */
+                                 1, /* msg_length */
+                                 1, /* response_length (1 Oword) */
+                                 0); /* eot */
+      }
+   }
 }
 
 
index 5d332d0..a713262 100644 (file)
@@ -84,6 +84,19 @@ get_965_surfacetype(unsigned int surfacetype)
     }
 }
 
+static const char *
+get_965_surface_format(unsigned int surface_format)
+{
+    switch (surface_format) {
+    case 0x000: return "r32g32b32a32_float";
+    case 0x0c1: return "b8g8r8a8_unorm";
+    case 0x100: return "b5g6r5_unorm";
+    case 0x102: return "b5g5r5a1_unorm";
+    case 0x104: return "b4g4r4a4_unorm";
+    default: return "unknown";
+    }
+}
+
 static void dump_wm_surface_state(struct brw_context *brw)
 {
    int i;
@@ -95,7 +108,7 @@ static void dump_wm_surface_state(struct brw_context *brw)
       char name[20];
 
       if (surf_bo == NULL) {
-        fprintf(stderr, "WM SS%d: NULL\n", i);
+        fprintf(stderr, "  WM SS%d: NULL\n", i);
         continue;
       }
       dri_bo_map(surf_bo, GL_FALSE);
@@ -103,8 +116,9 @@ static void dump_wm_surface_state(struct brw_context *brw)
       surf = (struct brw_surface_state *)(surf_bo->virtual);
 
       sprintf(name, "WM SS%d", i);
-      state_out(name, surf, surfoff, 0, "%s\n",
-               get_965_surfacetype(surf->ss0.surface_type));
+      state_out(name, surf, surfoff, 0, "%s %s\n",
+               get_965_surfacetype(surf->ss0.surface_type),
+               get_965_surface_format(surf->ss0.surface_format));
       state_out(name, surf, surfoff, 1, "offset\n");
       state_out(name, surf, surfoff, 2, "%dx%d size, %d mips\n",
                surf->ss2.width + 1, surf->ss2.height + 1, surf->ss2.mip_count);
index 42f6a99..af0f501 100644 (file)
@@ -170,6 +170,14 @@ static void brw_vs_alloc_regs( struct brw_vs_compile *c )
       reg++;
    }
 
+   if (c->use_const_buffer) {
+      for (i = 0; i < 3; i++) {
+         c->current_const[i].index = -1;
+         c->current_const[i].reg = brw_vec8_grf(reg, 0);
+         reg++;
+      }
+   }
+
    for (i = 0; i < 128; i++) {
       if (c->output_regs[i].used_in_src) {
          c->output_regs[i].reg = brw_vec8_grf(reg, 0);
@@ -194,13 +202,6 @@ static void brw_vs_alloc_regs( struct brw_vs_compile *c )
    c->prog_data.urb_entry_size = (c->nr_outputs + 2 + 3) / 4;
    c->prog_data.total_grf = reg;
 
-   if (c->use_const_buffer) {
-       for (i = 0; i < 3; i++) {
-          c->current_const[i].index = -1;
-          c->current_const[i].reg = get_tmp(c);
-       }
-   }
-
    if (INTEL_DEBUG & DEBUG_VS) {
       _mesa_printf("%s NumAddrRegs %d\n", __FUNCTION__, c->vp->program.Base.NumAddressRegs);
       _mesa_printf("%s NumTemps %d\n", __FUNCTION__, c->vp->program.Base.NumTemporaries);
@@ -655,6 +656,8 @@ static void emit_lit_noalias( struct brw_vs_compile *c,
    }
 
    brw_ENDIF(p, if_insn);
+
+   release_tmp(c, tmp);
 }
 
 static void emit_lrp_noalias(struct brw_vs_compile *c,
@@ -704,7 +707,9 @@ get_constant(struct brw_vs_compile *c,
    struct brw_compile *p = &c->func;
    struct brw_reg const_reg;
 
-   if (c->current_const[argIndex].index != src->Index) {
+   assert(argIndex < 3);
+
+   if (c->current_const[argIndex].index != src->Index || src->RelAddr) {
 
       c->current_const[argIndex].index = src->Index;
 
@@ -717,15 +722,18 @@ get_constant(struct brw_vs_compile *c,
       brw_dp_READ_4_vs(p,
                        c->current_const[argIndex].reg, /* writeback dest */
                        src->RelAddr,                   /* relative indexing? */
+                       c->regs[PROGRAM_ADDRESS][0],    /* address register */
                        16 * src->Index,                /* byte offset */
                        SURF_INDEX_VERT_CONST_BUFFER    /* binding table index */
                        );
    }
 
-   /* replicate lower four floats into upper four floats (to get XYZWXYZW) */
    const_reg = c->current_const[argIndex].reg;
-   const_reg = stride(const_reg, 0, 4, 0);
-   const_reg.subnr = 0;
+   if (!src->RelAddr) {
+      /* replicate lower four floats into upper half (to get XYZWXYZW) */
+      const_reg = stride(const_reg, 0, 4, 0);
+      const_reg.subnr = 0;
+   }
 
    return const_reg;
 }
@@ -767,6 +775,42 @@ static struct brw_reg get_reg( struct brw_vs_compile *c,
 
 
 /**
+ * Indirect addressing:  get reg[[arg] + offset].
+ */
+static struct brw_reg deref( struct brw_vs_compile *c,
+                            struct brw_reg arg,
+                            GLint offset)
+{
+   struct brw_compile *p = &c->func;
+   struct brw_reg tmp = vec4(get_tmp(c));
+   struct brw_reg addr_reg = c->regs[PROGRAM_ADDRESS][0];
+   struct brw_reg vp_address = retype(vec1(addr_reg), BRW_REGISTER_TYPE_UW);
+   GLuint byte_offset = arg.nr * 32 + arg.subnr + offset * 16;
+   struct brw_reg indirect = brw_vec4_indirect(0,0);
+
+   {
+      brw_push_insn_state(p);
+      brw_set_access_mode(p, BRW_ALIGN_1);
+
+      /* This is pretty clunky - load the address register twice and
+       * fetch each 4-dword value in turn.  There must be a way to do
+       * this in a single pass, but I couldn't get it to work.
+       */
+      brw_ADD(p, brw_address_reg(0), vp_address, brw_imm_d(byte_offset));
+      brw_MOV(p, tmp, indirect);
+
+      brw_ADD(p, brw_address_reg(0), suboffset(vp_address, 8), brw_imm_d(byte_offset));
+      brw_MOV(p, suboffset(tmp, 4), indirect);
+
+      brw_pop_insn_state(p);
+   }
+   
+   /* NOTE: tmp not released */
+   return vec8(tmp);
+}
+
+
+/**
  * Get brw reg corresponding to the instruction's [argIndex] src reg.
  * TODO: relative addressing!
  */
@@ -777,19 +821,29 @@ get_src_reg( struct brw_vs_compile *c,
 {
    const GLuint file = inst->SrcReg[argIndex].File;
    const GLint index = inst->SrcReg[argIndex].Index;
+   const GLboolean relAddr = inst->SrcReg[argIndex].RelAddr;
 
    switch (file) {
    case PROGRAM_TEMPORARY:
    case PROGRAM_INPUT:
    case PROGRAM_OUTPUT:
-      assert(c->regs[file][index].nr != 0);
-      return c->regs[file][index];
+      if (relAddr) {
+         return deref(c, c->regs[file][0], index);
+      }
+      else {
+         assert(c->regs[file][index].nr != 0);
+         return c->regs[file][index];
+      }
+
    case PROGRAM_STATE_VAR:
    case PROGRAM_CONSTANT:
    case PROGRAM_UNIFORM:
       if (c->use_const_buffer) {
          return get_constant(c, inst, argIndex);
       }
+      else if (relAddr) {
+         return deref(c, c->regs[PROGRAM_STATE_VAR][0], index);
+      }
       else {
          assert(c->regs[PROGRAM_STATE_VAR][index].nr != 0);
          return c->regs[PROGRAM_STATE_VAR][index];
@@ -812,41 +866,6 @@ get_src_reg( struct brw_vs_compile *c,
 }
 
 
-/**
- * Indirect addressing:  get reg[[arg] + offset].
- */
-static struct brw_reg deref( struct brw_vs_compile *c,
-                            struct brw_reg arg,
-                            GLint offset)
-{
-   struct brw_compile *p = &c->func;
-   struct brw_reg tmp = vec4(get_tmp(c));
-   struct brw_reg addr_reg = c->regs[PROGRAM_ADDRESS][0];
-   struct brw_reg vp_address = retype(vec1(addr_reg), BRW_REGISTER_TYPE_UW);
-   GLuint byte_offset = arg.nr * 32 + arg.subnr + offset * 16;
-   struct brw_reg indirect = brw_vec4_indirect(0,0);
-
-   {
-      brw_push_insn_state(p);
-      brw_set_access_mode(p, BRW_ALIGN_1);
-
-      /* This is pretty clunky - load the address register twice and
-       * fetch each 4-dword value in turn.  There must be a way to do
-       * this in a single pass, but I couldn't get it to work.
-       */
-      brw_ADD(p, brw_address_reg(0), vp_address, brw_imm_d(byte_offset));
-      brw_MOV(p, tmp, indirect);
-
-      brw_ADD(p, brw_address_reg(0), suboffset(vp_address, 8), brw_imm_d(byte_offset));
-      brw_MOV(p, suboffset(tmp, 4), indirect);
-
-      brw_pop_insn_state(p);
-   }
-   
-   return vec8(tmp);
-}
-
-
 static void emit_arl( struct brw_vs_compile *c,
                      struct brw_reg dst,
                      struct brw_reg arg0 )
@@ -858,8 +877,8 @@ static void emit_arl( struct brw_vs_compile *c,
    if (need_tmp) 
       tmp = get_tmp(c);
 
-   brw_RNDD(p, tmp, arg0);
-   brw_MUL(p, dst, tmp, brw_imm_d(16));
+   brw_RNDD(p, tmp, arg0);               /* tmp = round(arg0) */
+   brw_MUL(p, dst, tmp, brw_imm_d(16));  /* dst = tmp * 16 */
 
    if (need_tmp)
       release_tmp(c, tmp);
@@ -882,13 +901,7 @@ static struct brw_reg get_arg( struct brw_vs_compile *c,
    if (src->File == PROGRAM_UNDEFINED)
       return brw_null_reg();
 
-   if (src->RelAddr) {
-      /* XXX fix */
-      reg = deref(c, c->regs[PROGRAM_STATE_VAR][0], src->Index);
-   }
-   else {
-      reg = get_src_reg(c, inst, argIndex);
-   }
+   reg = get_src_reg(c, inst, argIndex);
 
    /* Convert 3-bit swizzle to 2-bit.  
     */
@@ -919,6 +932,10 @@ static struct brw_reg get_dst( struct brw_vs_compile *c,
       assert(c->regs[dst.File][dst.Index].nr != 0);
       reg = c->regs[dst.File][dst.Index];
       break;
+   case PROGRAM_ADDRESS:
+      assert(dst.Index == 0);
+      reg = c->regs[dst.File][dst.Index];
+      break;
    case PROGRAM_UNDEFINED:
       /* we may hit this for OPCODE_END, OPCODE_KIL, etc */
       reg = brw_null_reg();
@@ -979,10 +996,7 @@ static void emit_swz( struct brw_vs_compile *c,
    if (src_mask) {
       struct brw_reg arg0;
 
-      if (src.RelAddr) 
-        arg0 = deref(c, c->regs[PROGRAM_STATE_VAR][0], src.Index);
-      else
-        arg0 = get_src_reg(c, inst, argIndex);
+      arg0 = get_src_reg(c, inst, argIndex);
 
       arg0 = brw_swizzle(arg0, 
                         src_swz[0], src_swz[1], 
@@ -1178,6 +1192,11 @@ void brw_vs_emit(struct brw_vs_compile *c )
       struct brw_reg args[3], dst;
       GLuint i;
       
+#if 0
+      printf("%d: ", insn);
+      _mesa_print_instruction(inst);
+#endif
+
       /* Get argument regs.  SWZ is special and does this itself.
        */
       if (inst->Opcode != OPCODE_SWZ)
index 385efd2..2d13088 100644 (file)
@@ -346,10 +346,10 @@ get_src_reg_const(struct brw_wm_compile *c,
       const_reg = brw_abs(const_reg);
 
 #if 0
-   printf("  form const[%d] for arg %d, comp %d, reg %d\n",
+   printf("  form const[%d].%d for arg %d, reg %d\n",
           c->current_const[srcRegIndex].index,
-          srcRegIndex,
           component,
+          srcRegIndex,
           const_reg.nr);
 #endif
 
@@ -407,7 +407,7 @@ static struct brw_reg get_src_reg_imm(struct brw_wm_compile *c,
        if (src->Abs)
           value = FABSF(value);
 #if 0
-       printf("  form imm reg %f\n", value);
+       printf("  form immed value %f for chan %d\n", value, channel);
 #endif
        return brw_imm_f(value);
     }
@@ -527,7 +527,9 @@ static void emit_mov( struct brw_wm_compile *c,
        if (mask & (1<<i)) {
            struct brw_reg src, dst;
            dst = get_dst_reg(c, inst, i);
-           src = get_src_reg_imm(c, inst, 0, i);
+            /* XXX some moves from immediate value don't work reliably!!! */
+            /*src = get_src_reg_imm(c, inst, 0, i);*/
+            src = get_src_reg(c, inst, 0, i);
            brw_MOV(p, dst, src);
        }
     }
index ce5dbb3..0dc377b 100644 (file)
@@ -38,7 +38,7 @@
 #include "intel_mipmap_tree.h"
 #include "intel_batchbuffer.h"
 #include "intel_tex.h"
-
+#include "intel_fbo.h"
 
 #include "brw_context.h"
 #include "brw_state.h"
@@ -505,15 +505,18 @@ brw_update_vs_constant_surface( GLcontext *ctx,
  * usable for further buffers when doing ARB_draw_buffer support.
  */
 static void
-brw_update_region_surface(struct brw_context *brw, struct intel_region *region,
-                         unsigned int unit, GLboolean cached)
+brw_update_renderbuffer_surface(struct brw_context *brw,
+                               struct gl_renderbuffer *rb,
+                               unsigned int unit, GLboolean cached)
 {
    GLcontext *ctx = &brw->intel.ctx;
    dri_bo *region_bo = NULL;
+   struct intel_renderbuffer *irb = intel_renderbuffer(rb);
+   struct intel_region *region = irb ? irb->region : NULL;
    struct {
       unsigned int surface_type;
       unsigned int surface_format;
-      unsigned int width, height, cpp;
+      unsigned int width, height, pitch, cpp;
       GLubyte color_mask[4];
       GLboolean color_blend;
       uint32_t tiling;
@@ -525,13 +528,27 @@ brw_update_region_surface(struct brw_context *brw, struct intel_region *region,
       region_bo = region->buffer;
 
       key.surface_type = BRW_SURFACE_2D;
-      if (region->cpp == 4)
+      switch (irb->texformat->MesaFormat) {
+      case MESA_FORMAT_ARGB8888:
         key.surface_format = BRW_SURFACEFORMAT_B8G8R8A8_UNORM;
-      else
+        break;
+      case MESA_FORMAT_RGB565:
         key.surface_format = BRW_SURFACEFORMAT_B5G6R5_UNORM;
+        break;
+      case MESA_FORMAT_ARGB1555:
+        key.surface_format = BRW_SURFACEFORMAT_B5G5R5A1_UNORM;
+        break;
+      case MESA_FORMAT_ARGB4444:
+        key.surface_format = BRW_SURFACEFORMAT_B4G4R4A4_UNORM;
+        break;
+      default:
+        _mesa_problem(ctx, "Bad renderbuffer format: %d\n",
+                      irb->texformat->MesaFormat);
+      }
       key.tiling = region->tiling;
-      key.width = region->pitch; /* XXX: not really! */
-      key.height = region->height;
+      key.width = rb->Width;
+      key.height = rb->Height;
+      key.pitch = region->pitch;
       key.cpp = region->cpp;
    } else {
       key.surface_type = BRW_SURFACE_NULL;
@@ -567,7 +584,7 @@ brw_update_region_surface(struct brw_context *brw, struct intel_region *region,
       surf.ss2.width = key.width - 1;
       surf.ss2.height = key.height - 1;
       brw_set_surface_tiling(&surf, key.tiling);
-      surf.ss3.pitch = (key.width * key.cpp) - 1;
+      surf.ss3.pitch = (key.pitch * key.cpp) - 1;
 
       /* _NEW_COLOR */
       surf.ss0.color_blend = key.color_blend;
@@ -655,14 +672,17 @@ static void prepare_wm_surfaces(struct brw_context *brw )
    GLuint i;
    int old_nr_surfaces;
 
+   /* _NEW_BUFFERS */
    /* Update surfaces for drawing buffers */
-   if (brw->state.nr_color_regions > 1) {
-      for (i = 0; i < brw->state.nr_color_regions; i++) {
-         brw_update_region_surface(brw, brw->state.color_regions[i], i,
-                                  GL_FALSE);
+   if (ctx->DrawBuffer->_NumColorDrawBuffers >= 1) {
+      for (i = 0; i < ctx->DrawBuffer->_NumColorDrawBuffers; i++) {
+         brw_update_renderbuffer_surface(brw,
+                                        ctx->DrawBuffer->_ColorDrawBuffers[i],
+                                        i,
+                                        GL_FALSE);
       }
    } else {
-      brw_update_region_surface(brw, brw->state.color_regions[0], 0, GL_TRUE);
+      brw_update_renderbuffer_surface(brw, NULL, 0, GL_TRUE);
    }
 
    old_nr_surfaces = brw->wm.nr_surfaces;
index 4ae9b11..4919828 100644 (file)
@@ -32,6 +32,8 @@
 #include "main/mtypes.h"
 #include "main/context.h"
 #include "main/enums.h"
+#include "main/texformat.h"
+#include "main/colormac.h"
 
 #include "intel_blit.h"
 #include "intel_buffers.h"
@@ -484,10 +486,9 @@ intelClearWithBlit(GLcontext *ctx, GLbitfield mask)
             const GLbitfield bufBit = 1 << buf;
             if ((clearMask & bufBit) && !(bufBit & skipBuffers)) {
                /* OK, clear this renderbuffer */
-               struct intel_region *irb_region =
-                 intel_get_rb_region(fb, buf);
+              struct intel_renderbuffer *irb = intel_get_renderbuffer(fb, buf);
                dri_bo *write_buffer =
-                  intel_region_buffer(intel, irb_region,
+                  intel_region_buffer(intel, irb->region,
                                       all ? INTEL_WRITE_FULL :
                                       INTEL_WRITE_PART);
 
@@ -495,15 +496,13 @@ intelClearWithBlit(GLcontext *ctx, GLbitfield mask)
                GLint pitch, cpp;
                GLuint BR13, CMD;
 
-               ASSERT(irb_region);
-
-               pitch = irb_region->pitch;
-               cpp = irb_region->cpp;
+               pitch = irb->region->pitch;
+               cpp = irb->region->cpp;
 
                DBG("%s dst:buf(%p)/%d+%d %d,%d sz:%dx%d\n",
                    __FUNCTION__,
-                   irb_region->buffer, (pitch * cpp),
-                   irb_region->draw_offset,
+                   irb->region->buffer, (pitch * cpp),
+                   irb->region->draw_offset,
                    b.x1, b.y1, b.x2 - b.x1, b.y2 - b.y1);
 
               BR13 = 0xf0 << 16;
@@ -529,7 +528,7 @@ intelClearWithBlit(GLcontext *ctx, GLbitfield mask)
                }
 
 #ifndef I915
-              if (irb_region->tiling != I915_TILING_NONE) {
+              if (irb->region->tiling != I915_TILING_NONE) {
                  CMD |= XY_DST_TILED;
                  pitch /= 4;
               }
@@ -540,9 +539,36 @@ intelClearWithBlit(GLcontext *ctx, GLbitfield mask)
                   clearVal = clear_depth;
                }
                else {
-                  clearVal = (cpp == 4)
-                     ? intel->ClearColor8888 : intel->ClearColor565;
-               }
+                 uint8_t clear[4];
+                 GLclampf *color = ctx->Color.ClearColor;
+
+                 CLAMPED_FLOAT_TO_UBYTE(clear[0], color[0]);
+                 CLAMPED_FLOAT_TO_UBYTE(clear[1], color[1]);
+                 CLAMPED_FLOAT_TO_UBYTE(clear[2], color[2]);
+                 CLAMPED_FLOAT_TO_UBYTE(clear[3], color[3]);
+
+                 switch (irb->texformat->MesaFormat) {
+                 case MESA_FORMAT_ARGB8888:
+                    clearVal = intel->ClearColor8888;
+                    break;
+                 case MESA_FORMAT_RGB565:
+                    clearVal = intel->ClearColor565;
+                    break;
+                 case MESA_FORMAT_ARGB4444:
+                    clearVal = PACK_COLOR_4444(clear[3], clear[0],
+                                               clear[1], clear[2]);
+                    break;
+                 case MESA_FORMAT_ARGB1555:
+                    clearVal = PACK_COLOR_1555(clear[3], clear[0],
+                                               clear[1], clear[2]);
+                    break;
+                 default:
+                    _mesa_problem(ctx, "Unexpected renderbuffer format: %d\n",
+                                  irb->texformat->MesaFormat);
+                    clearVal = 0;
+                 }
+              }
+
                /*
                   _mesa_debug(ctx, "hardware blit clear buf %d rb id %d\n",
                   buf, irb->Base.Name);
@@ -558,7 +584,7 @@ intelClearWithBlit(GLcontext *ctx, GLbitfield mask)
                OUT_BATCH((b.y2 << 16) | b.x2);
                OUT_RELOC(write_buffer,
                         I915_GEM_DOMAIN_RENDER, I915_GEM_DOMAIN_RENDER,
-                         irb_region->draw_offset);
+                         irb->region->draw_offset);
                OUT_BATCH(clearVal);
                ADVANCE_BATCH();
                clearMask &= ~bufBit;    /* turn off bit, for faster loop exit */
index bd38105..d798225 100644 (file)
@@ -48,6 +48,8 @@
 #define DV_PF_555  (1<<8)
 #define DV_PF_565  (2<<8)
 #define DV_PF_8888 (3<<8)
+#define DV_PF_4444 (8<<8)
+#define DV_PF_1555 (9<<8)
 
 struct intel_region;
 struct intel_context;
@@ -337,6 +339,7 @@ extern char *__progname;
 
 #define ARRAY_SIZE(x) (sizeof(x) / sizeof(x[0]))
 #define ALIGN(value, alignment)  ((value + alignment - 1) & ~(alignment - 1))
+#define IS_POWER_OF_TWO(val) (((val) & (val - 1)) == 0)
 
 #define INTEL_FIREVERTICES(intel)              \
 do {                                           \
index f046382..a9dfe28 100644 (file)
@@ -800,6 +800,7 @@ static int
 decode_3d_1d(uint32_t *data, int count, uint32_t hw_offset, int *failures, int i830)
 {
     unsigned int len, i, c, opcode, word, map, sampler, instr;
+    char *format;
 
     struct {
        uint32_t opcode;
@@ -1001,6 +1002,35 @@ decode_3d_1d(uint32_t *data, int count, uint32_t hw_offset, int *failures, int i
            (*failures)++;
        }
        return len;
+    case 0x85:
+       len = (data[0] & 0x0000000f) + 2;
+
+       if (len != 2)
+           fprintf(out, "Bad count in 3DSTATE_DEST_BUFFER_VARIABLES\n");
+       if (count < 2)
+           BUFFER_FAIL(count, len, "3DSTATE_DEST_BUFFER_VARIABLES");
+
+       instr_out(data, hw_offset, 0,
+                 "3DSTATE_DEST_BUFFER_VARIABLES\n");
+
+       switch ((data[1] >> 8) & 0xf) {
+       case 0x0: format = "g8"; break;
+       case 0x1: format = "x1r5g5b5"; break;
+       case 0x2: format = "r5g6b5"; break;
+       case 0x3: format = "a8r8g8b8"; break;
+       case 0x4: format = "ycrcb_swapy"; break;
+       case 0x5: format = "ycrcb_normal"; break;
+       case 0x6: format = "ycrcb_swapuv"; break;
+       case 0x7: format = "ycrcb_swapuvy"; break;
+       case 0x8: format = "a4r4g4b4"; break;
+       case 0x9: format = "a1r5g5b5"; break;
+       case 0xa: format = "a2r10g10b10"; break;
+       default: format = "BAD"; break;
+       }
+       instr_out(data, hw_offset, 1, "%s format, early Z %sabled\n",
+                 format,
+                 (data[1] & (1 << 31)) ? "en" : "dis");
+       return len;
     }
 
     for (opcode = 0; opcode < sizeof(opcodes_3d_1d) / sizeof(opcodes_3d_1d[0]);
index a401f73..52647dd 100644 (file)
@@ -119,6 +119,7 @@ intel_alloc_renderbuffer_storage(GLcontext * ctx, struct gl_renderbuffer *rb,
       rb->RedBits = 5;
       rb->GreenBits = 6;
       rb->BlueBits = 5;
+      irb->texformat = &_mesa_texformat_rgb565;
       cpp = 2;
       break;
    case GL_RGB:
@@ -132,6 +133,7 @@ intel_alloc_renderbuffer_storage(GLcontext * ctx, struct gl_renderbuffer *rb,
       rb->GreenBits = 8;
       rb->BlueBits = 8;
       rb->AlphaBits = 0;
+      irb->texformat = &_mesa_texformat_argb8888; /* XXX: Need xrgb8888 */
       cpp = 4;
       break;
    case GL_RGBA:
@@ -148,6 +150,7 @@ intel_alloc_renderbuffer_storage(GLcontext * ctx, struct gl_renderbuffer *rb,
       rb->GreenBits = 8;
       rb->BlueBits = 8;
       rb->AlphaBits = 8;
+      irb->texformat = &_mesa_texformat_argb8888;
       cpp = 4;
       break;
    case GL_STENCIL_INDEX:
@@ -160,12 +163,14 @@ intel_alloc_renderbuffer_storage(GLcontext * ctx, struct gl_renderbuffer *rb,
       rb->DataType = GL_UNSIGNED_INT_24_8_EXT;
       rb->StencilBits = 8;
       cpp = 4;
+      irb->texformat = &_mesa_texformat_s8_z24;
       break;
    case GL_DEPTH_COMPONENT16:
       rb->_ActualFormat = GL_DEPTH_COMPONENT16;
       rb->DataType = GL_UNSIGNED_SHORT;
       rb->DepthBits = 16;
       cpp = 2;
+      irb->texformat = &_mesa_texformat_z16;
       break;
    case GL_DEPTH_COMPONENT:
    case GL_DEPTH_COMPONENT24:
@@ -174,6 +179,7 @@ intel_alloc_renderbuffer_storage(GLcontext * ctx, struct gl_renderbuffer *rb,
       rb->DataType = GL_UNSIGNED_INT_24_8_EXT;
       rb->DepthBits = 24;
       cpp = 4;
+      irb->texformat = &_mesa_texformat_s8_z24;
       break;
    case GL_DEPTH_STENCIL_EXT:
    case GL_DEPTH24_STENCIL8_EXT:
@@ -182,6 +188,7 @@ intel_alloc_renderbuffer_storage(GLcontext * ctx, struct gl_renderbuffer *rb,
       rb->DepthBits = 24;
       rb->StencilBits = 8;
       cpp = 4;
+      irb->texformat = &_mesa_texformat_s8_z24;
       break;
    default:
       _mesa_problem(ctx,
@@ -322,6 +329,7 @@ intel_create_renderbuffer(GLenum intFormat)
       irb->Base.GreenBits = 6;
       irb->Base.BlueBits = 5;
       irb->Base.DataType = GL_UNSIGNED_BYTE;
+      irb->texformat = &_mesa_texformat_rgb565;
       break;
    case GL_RGB8:
       irb->Base._ActualFormat = GL_RGB8;
@@ -331,6 +339,7 @@ intel_create_renderbuffer(GLenum intFormat)
       irb->Base.BlueBits = 8;
       irb->Base.AlphaBits = 0;
       irb->Base.DataType = GL_UNSIGNED_BYTE;
+      irb->texformat = &_mesa_texformat_argb8888; /* XXX: Need xrgb8888 */
       break;
    case GL_RGBA8:
       irb->Base._ActualFormat = GL_RGBA8;
@@ -340,24 +349,28 @@ intel_create_renderbuffer(GLenum intFormat)
       irb->Base.BlueBits = 8;
       irb->Base.AlphaBits = 8;
       irb->Base.DataType = GL_UNSIGNED_BYTE;
+      irb->texformat = &_mesa_texformat_argb8888;
       break;
    case GL_STENCIL_INDEX8_EXT:
       irb->Base._ActualFormat = GL_STENCIL_INDEX8_EXT;
       irb->Base._BaseFormat = GL_STENCIL_INDEX;
       irb->Base.StencilBits = 8;
       irb->Base.DataType = GL_UNSIGNED_BYTE;
+      irb->texformat = &_mesa_texformat_s8_z24;
       break;
    case GL_DEPTH_COMPONENT16:
       irb->Base._ActualFormat = GL_DEPTH_COMPONENT16;
       irb->Base._BaseFormat = GL_DEPTH_COMPONENT;
       irb->Base.DepthBits = 16;
       irb->Base.DataType = GL_UNSIGNED_SHORT;
+      irb->texformat = &_mesa_texformat_z16;
       break;
    case GL_DEPTH_COMPONENT24:
       irb->Base._ActualFormat = GL_DEPTH24_STENCIL8_EXT;
       irb->Base._BaseFormat = GL_DEPTH_COMPONENT;
       irb->Base.DepthBits = 24;
       irb->Base.DataType = GL_UNSIGNED_INT;
+      irb->texformat = &_mesa_texformat_s8_z24;
       break;
    case GL_DEPTH24_STENCIL8_EXT:
       irb->Base._ActualFormat = GL_DEPTH24_STENCIL8_EXT;
@@ -365,6 +378,7 @@ intel_create_renderbuffer(GLenum intFormat)
       irb->Base.DepthBits = 24;
       irb->Base.StencilBits = 8;
       irb->Base.DataType = GL_UNSIGNED_INT_24_8_EXT;
+      irb->texformat = &_mesa_texformat_s8_z24;
       break;
    default:
       _mesa_problem(NULL,
@@ -449,6 +463,8 @@ static GLboolean
 intel_update_wrapper(GLcontext *ctx, struct intel_renderbuffer *irb, 
                     struct gl_texture_image *texImage)
 {
+   irb->texformat = texImage->TexFormat;
+
    if (texImage->TexFormat == &_mesa_texformat_argb8888) {
       irb->Base._ActualFormat = GL_RGBA8;
       irb->Base._BaseFormat = GL_RGBA;
@@ -458,9 +474,21 @@ intel_update_wrapper(GLcontext *ctx, struct intel_renderbuffer *irb,
    else if (texImage->TexFormat == &_mesa_texformat_rgb565) {
       irb->Base._ActualFormat = GL_RGB5;
       irb->Base._BaseFormat = GL_RGB;
-      irb->Base.DataType = GL_UNSIGNED_SHORT;
+      irb->Base.DataType = GL_UNSIGNED_BYTE;
       DBG("Render to RGB5 texture OK\n");
    }
+   else if (texImage->TexFormat == &_mesa_texformat_argb1555) {
+      irb->Base._ActualFormat = GL_RGB5_A1;
+      irb->Base._BaseFormat = GL_RGBA;
+      irb->Base.DataType = GL_UNSIGNED_BYTE;
+      DBG("Render to ARGB1555 texture OK\n");
+   }
+   else if (texImage->TexFormat == &_mesa_texformat_argb4444) {
+      irb->Base._ActualFormat = GL_RGBA4;
+      irb->Base._BaseFormat = GL_RGBA;
+      irb->Base.DataType = GL_UNSIGNED_BYTE;
+      DBG("Render to ARGB4444 texture OK\n");
+   }
    else if (texImage->TexFormat == &_mesa_texformat_z16) {
       irb->Base._ActualFormat = GL_DEPTH_COMPONENT16;
       irb->Base._BaseFormat = GL_DEPTH_COMPONENT;
@@ -631,11 +659,11 @@ intel_finish_render_texture(GLcontext * ctx,
 static void
 intel_validate_framebuffer(GLcontext *ctx, struct gl_framebuffer *fb)
 {
-   struct intel_context *intel = intel_context(ctx);
    const struct intel_renderbuffer *depthRb =
       intel_get_renderbuffer(fb, BUFFER_DEPTH);
    const struct intel_renderbuffer *stencilRb =
       intel_get_renderbuffer(fb, BUFFER_STENCIL);
+   int i;
 
    if (stencilRb && stencilRb != depthRb) {
       /* we only support combined depth/stencil buffers, not separate
@@ -644,32 +672,21 @@ intel_validate_framebuffer(GLcontext *ctx, struct gl_framebuffer *fb)
       fb->_Status = GL_FRAMEBUFFER_UNSUPPORTED_EXT;
    }
 
-   /* check that texture color buffers are a format we can render into */
-   {
-      const struct gl_texture_format *supportedFormat;
-      GLuint i;
+   for (i = 0; i < ctx->Const.MaxDrawBuffers; i++) {
+      struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[i];
+      struct intel_renderbuffer *irb = intel_renderbuffer(rb);
 
-      /* The texture format we can render into seems to depend on the
-       * screen depth.  There currently seems to be a problem when
-       * rendering into a rgb565 texture when the screen is abgr8888.
-       */
+      if (rb == NULL)
+        continue;
 
-      if (intel->ctx.Visual.rgbBits >= 24)
-         supportedFormat = &_mesa_texformat_argb8888;
-      else 
-         supportedFormat = &_mesa_texformat_rgb565;
-
-      for (i = 0; i < ctx->Const.MaxDrawBuffers; i++) {
-         const struct gl_texture_object *texObj =
-            fb->Attachment[BUFFER_COLOR0 + i].Texture;
-         if (texObj) {
-            const struct gl_texture_image *texImg =
-               texObj->Image[0][texObj->BaseLevel];
-            if (texImg && texImg->TexFormat != supportedFormat) {
-               fb->_Status = GL_FRAMEBUFFER_UNSUPPORTED_EXT;
-               break;
-            }
-         }
+      switch (irb->texformat->MesaFormat) {
+      case MESA_FORMAT_ARGB8888:
+      case MESA_FORMAT_RGB565:
+      case MESA_FORMAT_ARGB1555:
+      case MESA_FORMAT_ARGB4444:
+        break;
+      default:
+        fb->_Status = GL_FRAMEBUFFER_UNSUPPORTED_EXT;
       }
    }
 }
index 7226ee0..f0665af 100644 (file)
@@ -61,6 +61,8 @@ struct intel_renderbuffer
    struct gl_renderbuffer Base;
    struct intel_region *region;
 
+   const struct gl_texture_format *texformat;
+
    GLuint vbl_pending;   /**< vblank sequence number of pending flip */
 
    uint8_t *span_cache;
index c3a873f..34b78eb 100644 (file)
@@ -29,6 +29,7 @@
 #include "main/macros.h"
 #include "main/mtypes.h"
 #include "main/colormac.h"
+#include "main/texformat.h"
 
 #include "intel_buffers.h"
 #include "intel_fbo.h"
@@ -313,6 +314,22 @@ static uint32_t y_tile_swizzle(struct intel_renderbuffer *irb,
 #define INTEL_TAG(x) x##_RGB565
 #include "intel_spantmp.h"
 
+/* a4r4g4b4 color span and pixel functions */
+#define INTEL_PIXEL_FMT GL_BGRA
+#define INTEL_PIXEL_TYPE GL_UNSIGNED_SHORT_4_4_4_4_REV
+#define INTEL_READ_VALUE(offset) pread_16(irb, offset)
+#define INTEL_WRITE_VALUE(offset, v) pwrite_16(irb, offset, v)
+#define INTEL_TAG(x) x##_ARGB4444
+#include "intel_spantmp.h"
+
+/* a1r5g5b5 color span and pixel functions */
+#define INTEL_PIXEL_FMT GL_BGRA
+#define INTEL_PIXEL_TYPE GL_UNSIGNED_SHORT_1_5_5_5_REV
+#define INTEL_READ_VALUE(offset) pread_16(irb, offset)
+#define INTEL_WRITE_VALUE(offset, v) pwrite_16(irb, offset, v)
+#define INTEL_TAG(x) x##_ARGB1555
+#include "intel_spantmp.h"
+
 /* a8r8g8b8 color span and pixel functions */
 #define INTEL_PIXEL_FMT GL_BGRA
 #define INTEL_PIXEL_TYPE GL_UNSIGNED_INT_8_8_8_8_REV
@@ -561,8 +578,8 @@ intel_set_span_functions(struct intel_context *intel,
    else
       tiling = I915_TILING_NONE;
 
-   if (rb->_ActualFormat == GL_RGB5) {
-      /* 565 RGB */
+   switch (irb->texformat->MesaFormat) {
+   case MESA_FORMAT_RGB565:
       switch (tiling) {
       case I915_TILING_NONE:
       default:
@@ -575,38 +592,67 @@ intel_set_span_functions(struct intel_context *intel,
         intel_YTile_InitPointers_RGB565(rb);
         break;
       }
-   }
-   else if (rb->_ActualFormat == GL_RGB8) {
-      /* 8888 RGBx */
+      break;
+   case MESA_FORMAT_ARGB4444:
       switch (tiling) {
       case I915_TILING_NONE:
       default:
-        intelInitPointers_xRGB8888(rb);
+        intelInitPointers_ARGB4444(rb);
         break;
       case I915_TILING_X:
-        intel_XTile_InitPointers_xRGB8888(rb);
+        intel_XTile_InitPointers_ARGB4444(rb);
         break;
       case I915_TILING_Y:
-        intel_YTile_InitPointers_xRGB8888(rb);
+        intel_YTile_InitPointers_ARGB4444(rb);
         break;
       }
-   }
-   else if (rb->_ActualFormat == GL_RGBA8) {
-      /* 8888 RGBA */
+      break;
+   case MESA_FORMAT_ARGB1555:
       switch (tiling) {
       case I915_TILING_NONE:
       default:
-        intelInitPointers_ARGB8888(rb);
+        intelInitPointers_ARGB1555(rb);
         break;
       case I915_TILING_X:
-        intel_XTile_InitPointers_ARGB8888(rb);
+        intel_XTile_InitPointers_ARGB1555(rb);
         break;
       case I915_TILING_Y:
-        intel_YTile_InitPointers_ARGB8888(rb);
+        intel_YTile_InitPointers_ARGB1555(rb);
         break;
       }
-   }
-   else if (rb->_ActualFormat == GL_DEPTH_COMPONENT16) {
+      break;
+   case MESA_FORMAT_ARGB8888:
+      if (rb->AlphaBits == 0) { /* XXX: Need xRGB8888 Mesa format */
+        /* 8888 RGBx */
+        switch (tiling) {
+        case I915_TILING_NONE:
+        default:
+           intelInitPointers_xRGB8888(rb);
+           break;
+        case I915_TILING_X:
+           intel_XTile_InitPointers_xRGB8888(rb);
+           break;
+        case I915_TILING_Y:
+           intel_YTile_InitPointers_xRGB8888(rb);
+           break;
+        }
+      } else {
+        /* 8888 RGBA */
+        switch (tiling) {
+        case I915_TILING_NONE:
+        default:
+           intelInitPointers_ARGB8888(rb);
+           break;
+        case I915_TILING_X:
+           intel_XTile_InitPointers_ARGB8888(rb);
+           break;
+        case I915_TILING_Y:
+           intel_YTile_InitPointers_ARGB8888(rb);
+           break;
+        }
+      }
+      break;
+   case MESA_FORMAT_Z16:
       switch (tiling) {
       case I915_TILING_NONE:
       default:
@@ -619,51 +665,57 @@ intel_set_span_functions(struct intel_context *intel,
         intel_YTile_InitDepthPointers_z16(rb);
         break;
       }
-   }
-   else if (rb->_ActualFormat == GL_DEPTH_COMPONENT24) {
-      switch (tiling) {
-      case I915_TILING_NONE:
-      default:
-        intelInitDepthPointers_z24(rb);
-        break;
-      case I915_TILING_X:
-        intel_XTile_InitDepthPointers_z24(rb);
-        break;
-      case I915_TILING_Y:
-        intel_YTile_InitDepthPointers_z24(rb);
-        break;
-      }
-   }
-   else if (rb->_ActualFormat == GL_DEPTH24_STENCIL8_EXT) {
-      switch (tiling) {
-      case I915_TILING_NONE:
-      default:
-        intelInitDepthPointers_z24_s8(rb);
-        break;
-      case I915_TILING_X:
-        intel_XTile_InitDepthPointers_z24_s8(rb);
-        break;
-      case I915_TILING_Y:
-        intel_YTile_InitDepthPointers_z24_s8(rb);
-        break;
-      }
-   }
-   else if (rb->_ActualFormat == GL_STENCIL_INDEX8_EXT) {
-      switch (tiling) {
-      case I915_TILING_NONE:
-      default:
-        intelInitStencilPointers_z24_s8(rb);
-        break;
-      case I915_TILING_X:
-        intel_XTile_InitStencilPointers_z24_s8(rb);
-        break;
-      case I915_TILING_Y:
-        intel_YTile_InitStencilPointers_z24_s8(rb);
-        break;
+      break;
+   case MESA_FORMAT_S8_Z24:
+      /* There are a few different ways SW asks us to access the S8Z24 data:
+       * Z24 depth-only depth reads
+       * S8Z24 depth reads
+       * S8Z24 stencil reads.
+       */
+      if (rb->_ActualFormat == GL_DEPTH_COMPONENT24) {
+        switch (tiling) {
+        case I915_TILING_NONE:
+        default:
+           intelInitDepthPointers_z24(rb);
+           break;
+        case I915_TILING_X:
+           intel_XTile_InitDepthPointers_z24(rb);
+           break;
+        case I915_TILING_Y:
+           intel_YTile_InitDepthPointers_z24(rb);
+           break;
+        }
+      } else if (rb->_ActualFormat == GL_DEPTH24_STENCIL8_EXT) {
+        switch (tiling) {
+        case I915_TILING_NONE:
+        default:
+           intelInitDepthPointers_z24_s8(rb);
+           break;
+        case I915_TILING_X:
+           intel_XTile_InitDepthPointers_z24_s8(rb);
+           break;
+        case I915_TILING_Y:
+           intel_YTile_InitDepthPointers_z24_s8(rb);
+           break;
+        }
+      } else if (rb->_ActualFormat == GL_STENCIL_INDEX8_EXT) {
+        switch (tiling) {
+        case I915_TILING_NONE:
+        default:
+           intelInitStencilPointers_z24_s8(rb);
+           break;
+        case I915_TILING_X:
+           intel_XTile_InitStencilPointers_z24_s8(rb);
+           break;
+        case I915_TILING_Y:
+           intel_YTile_InitStencilPointers_z24_s8(rb);
+           break;
+        }
       }
-   }
-   else {
+      break;
+   default:
       _mesa_problem(NULL,
-                    "Unexpected _ActualFormat in intelSetSpanFunctions");
+                    "Unexpected MesaFormat in intelSetSpanFunctions");
+      break;
    }
 }
index 71561cf..1f192da 100644 (file)
@@ -315,8 +315,8 @@ intelTexImage(GLcontext * ctx,
    GLint postConvWidth = width;
    GLint postConvHeight = height;
    GLint texelBytes, sizeInBytes;
-   GLuint dstRowStride, srcRowStride = texImage->RowStride;
-
+   GLuint dstRowStride = 0, srcRowStride = texImage->RowStride;
+   GLboolean needs_map;
 
    DBG("%s target %s level %d %dx%dx%d border %d\n", __FUNCTION__,
        _mesa_lookup_enum_by_nr(target), level, width, height, depth, border);
@@ -482,8 +482,15 @@ intelTexImage(GLcontext * ctx,
 
    LOCK_HARDWARE(intel);
 
+   /* Two cases where we need a mapping of the miptree: when the user supplied
+    * data is mapped as well (non-PBO, memcpy upload) or when we're going to do
+    * (software) mipmap generation.
+    */
+   needs_map = (pixels != NULL) || (level == texObj->BaseLevel &&
+                                 texObj->GenerateMipmap);
+
    if (intelImage->mt) {
-      if (pixels)
+      if (needs_map)
          texImage->Data = intel_miptree_image_map(intel,
                                                   intelImage->mt,
                                                   intelImage->face,
@@ -509,8 +516,9 @@ intelTexImage(GLcontext * ctx,
    }
 
    DBG("Upload image %dx%dx%d row_len %d "
-       "pitch %d\n",
-       width, height, depth, width * texelBytes, dstRowStride);
+       "pitch %d pixels %d compressed %d\n",
+       width, height, depth, width * texelBytes, dstRowStride,
+       pixels ? 1 : 0, compressed);
 
    /* Copy data.  Would like to know when it's ok for us to eg. use
     * the blitter to copy.  Or, use the hardware to do the format
@@ -523,7 +531,7 @@ intelTexImage(GLcontext * ctx,
               _mesa_copy_rect(texImage->Data, dst->cpp, dst->pitch,
                               0, 0,
                               intelImage->mt->level[level].width,
-                              intelImage->mt->level[level].height/4,
+                              (intelImage->mt->level[level].height+3)/4,
                               pixels,
                               srcRowStride,
                               0, 0);
@@ -549,7 +557,7 @@ intelTexImage(GLcontext * ctx,
    _mesa_unmap_teximage_pbo(ctx, unpack);
 
    if (intelImage->mt) {
-      if (pixels)
+      if (needs_map)
          intel_miptree_image_unmap(intel, intelImage->mt);
       texImage->Data = NULL;
    }
index d5d0a55..e43fa96 100644 (file)
@@ -1265,7 +1265,7 @@ _mesa_PopAttrib(void)
 
                /* restore clip planes */
                for (i = 0; i < MAX_CLIP_PLANES; i++) {
-                  const GLuint mask = 1 << 1;
+                  const GLuint mask = 1 << i;
                   const GLfloat *eyePlane = xform->EyeUserPlane[i];
                   COPY_4V(ctx->Transform.EyeUserPlane[i], eyePlane);
                   if (xform->ClipPlanesEnabled & mask) {
index cc37d63..4f9088d 100644 (file)
@@ -470,7 +470,8 @@ _mesa_update_state_locked( GLcontext *ctx )
 
    /* Determine which state flags effect vertex/fragment program state */
    if (ctx->FragmentProgram._MaintainTexEnvProgram) {
-      prog_flags |= (_NEW_TEXTURE | _NEW_FOG | _DD_NEW_SEPARATE_SPECULAR);
+      prog_flags |= (_NEW_TEXTURE | _NEW_FOG | _DD_NEW_SEPARATE_SPECULAR |
+                    _NEW_ARRAY);
    }
    if (ctx->VertexProgram._MaintainTnlProgram) {
       prog_flags |= (_NEW_ARRAY | _NEW_TEXTURE | _NEW_TEXTURE_MATRIX |
index d17e18d..a1c0f18 100644 (file)
@@ -205,7 +205,7 @@ texstore_rgb_dxt1(TEXSTORE_PARAMS)
                               dst, dstRowStride);
    }
    else {
-      _mesa_warning(ctx, "external dxt library not available");
+      _mesa_warning(ctx, "external dxt library not available: texstore_rgb_dxt1");
    }
 
    if (tempImage)
@@ -267,7 +267,7 @@ texstore_rgba_dxt1(TEXSTORE_PARAMS)
                               dst, dstRowStride);
    }
    else {
-      _mesa_warning(ctx, "external dxt library not available");
+      _mesa_warning(ctx, "external dxt library not available: texstore_rgba_dxt1");
    }
 
    if (tempImage)
@@ -328,7 +328,7 @@ texstore_rgba_dxt3(TEXSTORE_PARAMS)
                               dst, dstRowStride);
    }
    else {
-      _mesa_warning(ctx, "external dxt library not available");
+      _mesa_warning(ctx, "external dxt library not available: texstore_rgba_dxt3");
    }
 
    if (tempImage)
@@ -389,7 +389,7 @@ texstore_rgba_dxt5(TEXSTORE_PARAMS)
                               dst, dstRowStride);
    }
    else {
-      _mesa_warning(ctx, "external dxt library not available");
+      _mesa_warning(ctx, "external dxt library not available: texstore_rgba_dxt5");
    }
 
    if (tempImage)
@@ -410,7 +410,7 @@ fetch_texel_2d_rgb_dxt1( const struct gl_texture_image *texImage,
                          (GLubyte *)(texImage)->Data, i, j, texel);
    }
    else
-      _mesa_debug(NULL, "attempted to decode s3tc texture without library available\n");
+      _mesa_debug(NULL, "attempted to decode s3tc texture without library available: fetch_texel_2d_rgb_dxt1");
 }
 
 
@@ -438,7 +438,7 @@ fetch_texel_2d_rgba_dxt1( const struct gl_texture_image *texImage,
                           (GLubyte *)(texImage)->Data, i, j, texel);
    }
    else
-      _mesa_debug(NULL, "attempted to decode s3tc texture without library available\n");
+      _mesa_debug(NULL, "attempted to decode s3tc texture without library available: fetch_texel_2d_rgba_dxt1\n");
 }
 
 
@@ -467,7 +467,7 @@ fetch_texel_2d_rgba_dxt3( const struct gl_texture_image *texImage,
                           i, j, texel);
    }
    else
-      _mesa_debug(NULL, "attempted to decode s3tc texture without library available\n");
+      _mesa_debug(NULL, "attempted to decode s3tc texture without library available: fetch_texel_2d_rgba_dxt3\n");
 }
 
 
@@ -495,7 +495,7 @@ fetch_texel_2d_rgba_dxt5( const struct gl_texture_image *texImage,
                           i, j, texel);
    }
    else
-      _mesa_debug(NULL, "attempted to decode s3tc texture without library available\n");
+      _mesa_debug(NULL, "attempted to decode s3tc texture without library available: fetch_texel_2d_rgba_dxt5\n");
 }
 
 
index 3f9a825..1510a1e 100644 (file)
@@ -40,6 +40,7 @@
 #include "st_draw.h"
 #include "st_public.h"
 #include "st_format.h"
+#include "st_texture.h"
 #include "pipe/p_context.h"
 #include "pipe/p_defines.h"
 #include "pipe/p_inlines.h"
@@ -118,6 +119,9 @@ st_clear_accum_buffer(GLcontext *ctx, struct gl_renderbuffer *rb)
    const GLint height = ctx->DrawBuffer->_Ymax - ypos;
    GLubyte *map;
 
+   st_teximage_flush_before_map(ctx->st, acc_strb->texture, 0, 0,
+                               PIPE_TRANSFER_WRITE);
+
    acc_pt = screen->get_tex_transfer(screen, acc_strb->texture, 0, 0, 0,
                                      PIPE_TRANSFER_WRITE, xpos, ypos,
                                      width, height);
@@ -163,6 +167,9 @@ accum_mad(GLcontext *ctx, GLfloat scale, GLfloat bias,
    struct pipe_transfer *acc_pt;
    GLubyte *map;
 
+   st_teximage_flush_before_map(ctx->st, acc_strb->texture, 0, 0,
+                               PIPE_TRANSFER_READ_WRITE);
+
    acc_pt = screen->get_tex_transfer(screen, acc_strb->texture, 0, 0, 0,
                                      PIPE_TRANSFER_READ_WRITE, xpos, ypos,
                                      width, height);
@@ -192,20 +199,27 @@ accum_mad(GLcontext *ctx, GLfloat scale, GLfloat bias,
 
 
 static void
-accum_accum(struct pipe_context *pipe, GLfloat value,
+accum_accum(struct st_context *st, GLfloat value,
             GLint xpos, GLint ypos, GLint width, GLint height,
             struct st_renderbuffer *acc_strb,
             struct st_renderbuffer *color_strb)
 {
+   struct pipe_context *pipe = st->pipe;
    struct pipe_screen *screen = pipe->screen;
    struct pipe_transfer *acc_trans, *color_trans;
    GLfloat *colorBuf, *accBuf;
    GLint i;
 
+   st_teximage_flush_before_map(st, acc_strb->texture, 0, 0,
+                               PIPE_TRANSFER_READ);
+
    acc_trans = screen->get_tex_transfer(screen, acc_strb->texture, 0, 0, 0,
                                         PIPE_TRANSFER_READ, xpos, ypos,
                                         width, height);
 
+   st_teximage_flush_before_map(st, color_strb->texture, 0, 0,
+                               PIPE_TRANSFER_READ);
+
    color_trans = screen->get_tex_transfer(screen, color_strb->texture, 0, 0, 0,
                                           PIPE_TRANSFER_READ, xpos, ypos,
                                           width, height);
@@ -235,20 +249,27 @@ accum_accum(struct pipe_context *pipe, GLfloat value,
 
 
 static void
-accum_load(struct pipe_context *pipe, GLfloat value,
+accum_load(struct st_context *st, GLfloat value,
            GLint xpos, GLint ypos, GLint width, GLint height,
            struct st_renderbuffer *acc_strb,
            struct st_renderbuffer *color_strb)
 {
+   struct pipe_context *pipe = st->pipe;
    struct pipe_screen *screen = pipe->screen;
    struct pipe_transfer *acc_trans, *color_trans;
    GLfloat *buf;
    GLint i;
 
+   st_teximage_flush_before_map(st, acc_strb->texture, 0, 0,
+                               PIPE_TRANSFER_WRITE);
+
    acc_trans = screen->get_tex_transfer(screen, acc_strb->texture, 0, 0, 0,
                                         PIPE_TRANSFER_WRITE, xpos, ypos,
                                         width, height);
 
+   st_teximage_flush_before_map(st, color_strb->texture, 0, 0,
+                               PIPE_TRANSFER_READ);
+
    color_trans = screen->get_tex_transfer(screen, color_strb->texture, 0, 0, 0,
                                         PIPE_TRANSFER_READ, xpos, ypos,
                                         width, height);
@@ -284,10 +305,16 @@ accum_return(GLcontext *ctx, GLfloat value,
 
    abuf = (GLfloat *) _mesa_malloc(width * height * 4 * sizeof(GLfloat));
 
+   st_teximage_flush_before_map(ctx->st, acc_strb->texture, 0, 0,
+                               PIPE_TRANSFER_READ);
+
    acc_trans = screen->get_tex_transfer(screen, acc_strb->texture, 0, 0, 0,
                                         PIPE_TRANSFER_READ, xpos, ypos,
                                         width, height);
 
+   st_teximage_flush_before_map(ctx->st, color_strb->texture, 0, 0,
+                               PIPE_TRANSFER_READ_WRITE);
+
    color_trans = screen->get_tex_transfer(screen, color_strb->texture, 0, 0, 0,
                                           PIPE_TRANSFER_READ_WRITE, xpos, ypos,
                                           width, height);
@@ -325,7 +352,6 @@ static void
 st_Accum(GLcontext *ctx, GLenum op, GLfloat value)
 {
    struct st_context *st = ctx->st;
-   struct pipe_context *pipe = st->pipe;
    struct st_renderbuffer *acc_strb
      = st_renderbuffer(ctx->DrawBuffer->Attachment[BUFFER_ACCUM].Renderbuffer);
    struct st_renderbuffer *color_strb
@@ -352,11 +378,11 @@ st_Accum(GLcontext *ctx, GLenum op, GLfloat value)
       break;
    case GL_ACCUM:
       if (value != 0.0F) {
-         accum_accum(pipe, value, xpos, ypos, width, height, acc_strb, color_strb);
+         accum_accum(st, value, xpos, ypos, width, height, acc_strb, color_strb);
       }
       break;
    case GL_LOAD:
-      accum_load(pipe, value, xpos, ypos, width, height, acc_strb, color_strb);
+      accum_load(st, value, xpos, ypos, width, height, acc_strb, color_strb);
       break;
    case GL_RETURN:
       accum_return(ctx, value, xpos, ypos, width, height, acc_strb, color_strb);
index 3651e4a..fdb800f 100644 (file)
@@ -32,6 +32,7 @@
 
 #include "st_context.h"
 #include "st_cb_bufferobjects.h"
+#include "st_public.h"
 
 #include "pipe/p_context.h"
 #include "pipe/p_defines.h"
@@ -103,6 +104,9 @@ st_bufferobj_subdata(GLcontext *ctx,
    if (offset >= st_obj->size || size > (st_obj->size - offset))
       return;
 
+   if (pipe->is_buffer_referenced(pipe, st_obj->buffer))
+      st_flush(st_context(ctx), PIPE_FLUSH_RENDER_CACHE, NULL);
+
    pipe_buffer_write(pipe->screen, st_obj->buffer, offset, size, data);
 }
 
@@ -123,6 +127,10 @@ st_bufferobj_get_subdata(GLcontext *ctx,
    if (offset >= st_obj->size || size > (st_obj->size - offset))
       return;
 
+   if (pipe->is_buffer_referenced(pipe, st_obj->buffer) &
+       PIPE_REFERENCED_FOR_WRITE)
+      st_flush(st_context(ctx), PIPE_FLUSH_RENDER_CACHE, NULL);
+
    pipe_buffer_read(pipe->screen, st_obj->buffer, offset, size, data);
 }
 
@@ -171,7 +179,7 @@ st_bufferobj_data(GLcontext *ctx,
    st_obj->size = size;
 
    if (data)
-      st_bufferobj_subdata(ctx, target, 0, size, data, obj);
+      pipe_buffer_write(pipe->screen, st_obj->buffer, 0, size, data);
 }
 
 
@@ -185,6 +193,7 @@ st_bufferobj_map(GLcontext *ctx, GLenum target, GLenum access,
    struct pipe_context *pipe = st_context(ctx)->pipe;
    struct st_buffer_object *st_obj = st_buffer_object(obj);
    GLuint flags;
+   unsigned referenced;
 
    switch (access) {
    case GL_WRITE_ONLY:
@@ -200,6 +209,11 @@ st_bufferobj_map(GLcontext *ctx, GLenum target, GLenum access,
       break;      
    }
 
+   referenced = pipe->is_buffer_referenced(pipe, st_obj->buffer);
+   if (referenced && ((referenced & PIPE_REFERENCED_FOR_WRITE) ||
+                     (flags & PIPE_BUFFER_USAGE_CPU_WRITE)))
+      st_flush(st_context(ctx), PIPE_FLUSH_RENDER_CACHE, NULL);
+
    obj->Pointer = pipe_buffer_map(pipe->screen, st_obj->buffer, flags);
    if(obj->Pointer) {
       obj->Offset = 0;
index 0a44305..c67b026 100644 (file)
@@ -631,8 +631,6 @@ draw_stencil_pixels(GLcontext *ctx, GLint x, GLint y,
    GLint skipPixels;
    ubyte *stmap;
 
-   pipe->flush(pipe, PIPE_FLUSH_RENDER_CACHE, NULL);
-
    strb = st_renderbuffer(ctx->DrawBuffer->
                           Attachment[BUFFER_STENCIL].Renderbuffer);
 
@@ -640,6 +638,9 @@ draw_stencil_pixels(GLcontext *ctx, GLint x, GLint y,
       y = ctx->DrawBuffer->Height - y - height;
    }
 
+   st_teximage_flush_before_map(ctx->st, strb->texture, 0, 0,
+                               PIPE_TRANSFER_WRITE);
+
    pt = screen->get_tex_transfer(screen, strb->texture, 0, 0, 0,
                                  PIPE_TRANSFER_WRITE, x, y,
                                  width, height);
@@ -825,6 +826,9 @@ copy_stencil_pixels(GLcontext *ctx, GLint srcx, GLint srcy,
                           GL_STENCIL_INDEX, GL_UNSIGNED_BYTE,
                           &ctx->DefaultPacking, buffer);
 
+   st_teximage_flush_before_map(ctx->st, rbDraw->texture, 0, 0,
+                               PIPE_TRANSFER_WRITE);
+
    ptDraw = screen->get_tex_transfer(screen, rbDraw->texture, 0, 0, 0,
                                      PIPE_TRANSFER_WRITE, dstx, dsty,
                                      width, height);
index 9ce5f3f..519ad66 100644 (file)
 #include "pipe/p_defines.h"
 #include "pipe/p_inlines.h"
 #include "util/u_tile.h"
+
 #include "st_context.h"
 #include "st_cb_bitmap.h"
 #include "st_cb_readpixels.h"
 #include "st_cb_fbo.h"
 #include "st_format.h"
 #include "st_public.h"
-
+#include "st_texture.h"
 
 /**
  * Special case for reading stencil buffer.
@@ -73,6 +74,10 @@ st_read_stencil_pixels(GLcontext *ctx, GLint x, GLint y,
    }
 
    /* Create a read transfer from the renderbuffer's texture */
+
+   st_teximage_flush_before_map(ctx->st, strb->texture, 0, 0,
+                               PIPE_TRANSFER_READ);
+
    pt = screen->get_tex_transfer(screen, strb->texture,  0, 0, 0,
                                  PIPE_TRANSFER_READ, x, y, width, height);
 
@@ -240,6 +245,9 @@ st_fast_readpixels(GLcontext *ctx, struct st_renderbuffer *strb,
          y = strb->texture->height[0] - y - height;
       }
 
+      st_teximage_flush_before_map(ctx->st, strb->texture, 0, 0,
+                                  PIPE_TRANSFER_READ);
+
       trans = screen->get_tex_transfer(screen, strb->texture, 0, 0, 0,
                                        PIPE_TRANSFER_READ, x, y, width, height);
       if (!trans) {
index 1f14b37..98dc6ec 100644 (file)
@@ -26,6 +26,7 @@
  **************************************************************************/
 
 #include "main/mfeatures.h"
+#include "main/bufferobj.h"
 #if FEATURE_convolve
 #include "main/convolve.h"
 #endif
@@ -55,6 +56,7 @@
 #include "pipe/p_inlines.h"
 #include "util/u_tile.h"
 #include "util/u_blit.h"
+#include "util/u_surface.h"
 
 
 #define DBG if (0) printf
@@ -110,6 +112,25 @@ compressed_num_bytes(GLuint mesaFormat)
 }
 
 
+static GLboolean
+is_compressed_mesa_format(const struct gl_texture_format *format)
+{
+   switch (format->MesaFormat) {
+   case MESA_FORMAT_RGB_DXT1:
+   case MESA_FORMAT_RGBA_DXT1:
+   case MESA_FORMAT_RGBA_DXT3:
+   case MESA_FORMAT_RGBA_DXT5:
+   case MESA_FORMAT_SRGB_DXT1:
+   case MESA_FORMAT_SRGBA_DXT1:
+   case MESA_FORMAT_SRGBA_DXT3:
+   case MESA_FORMAT_SRGBA_DXT5:
+      return GL_TRUE;
+   default:
+      return GL_FALSE;
+   }
+}
+
+
 /** called via ctx->Driver.NewTextureImage() */
 static struct gl_texture_image *
 st_NewTextureImage(GLcontext * ctx)
@@ -379,6 +400,110 @@ strip_texture_border(GLint border,
 
 
 /**
+ * Try to do texture compression via rendering.  If the Gallium driver
+ * can render into a compressed surface this will allow us to do texture
+ * compression.
+ * \return GL_TRUE for success, GL_FALSE for failure
+ */
+static GLboolean
+compress_with_blit(GLcontext * ctx,
+                   GLenum target, GLint level,
+                   GLint xoffset, GLint yoffset, GLint zoffset,
+                   GLint width, GLint height, GLint depth,
+                   GLenum format, GLenum type, const void *pixels,
+                   const struct gl_pixelstore_attrib *unpack,
+                   struct gl_texture_image *texImage)
+{
+   const GLuint dstImageOffsets[1] = {0};
+   struct st_texture_image *stImage = st_texture_image(texImage);
+   struct pipe_screen *screen = ctx->st->pipe->screen;
+   const GLuint face = _mesa_tex_target_to_face(target);
+   const struct gl_texture_format *mesa_format;
+   struct pipe_texture templ;
+   struct pipe_texture *src_tex;
+   struct pipe_surface *dst_surface;
+   struct pipe_transfer *tex_xfer;
+   void *map;
+
+
+   if (!stImage->pt) {
+      /* XXX: Can this happen? Should we assert? */
+      return GL_FALSE;
+   }
+
+   /* get destination surface (in the compressed texture) */
+   dst_surface = screen->get_tex_surface(screen, stImage->pt,
+                                         stImage->face, stImage->level, 0,
+                                         PIPE_BUFFER_USAGE_GPU_WRITE);
+   if (!dst_surface) {
+      /* can't render into this format (or other problem) */
+      return GL_FALSE;
+   }
+
+   /* Choose format for the temporary RGBA texture image.
+    */
+   mesa_format = st_ChooseTextureFormat(ctx, GL_RGBA, format, type);
+   assert(mesa_format);
+   if (!mesa_format)
+      return GL_FALSE;
+
+   /* Create the temporary source texture
+    */
+   memset(&templ, 0, sizeof(templ));
+   templ.target = PIPE_TEXTURE_2D;
+   templ.format = st_mesa_format_to_pipe_format(mesa_format->MesaFormat);
+   pf_get_block(templ.format, &templ.block);
+   templ.width[0] = width;
+   templ.height[0] = height;
+   templ.depth[0] = 1;
+   templ.last_level = 0;
+   templ.tex_usage = PIPE_TEXTURE_USAGE_SAMPLER;
+   src_tex = screen->texture_create(screen, &templ);
+
+   if (!src_tex)
+      return GL_FALSE;
+
+   /* Put user's tex data into the temporary texture
+    */
+   tex_xfer = screen->get_tex_transfer(screen, src_tex,
+                                       face, level, 0,
+                                       PIPE_TRANSFER_WRITE,
+                                       0, 0, width, height); /* x, y, w, h */
+   map = screen->transfer_map(screen, tex_xfer);
+
+   mesa_format->StoreImage(ctx, 2, GL_RGBA, mesa_format,
+                           map,              /* dest ptr */
+                           0, 0, 0,          /* dest x/y/z offset */
+                           tex_xfer->stride, /* dest row stride (bytes) */
+                           dstImageOffsets,  /* image offsets (for 3D only) */
+                           width, height, 1, /* size */
+                           format, type,     /* source format/type */
+                           pixels,           /* source data */
+                           unpack);          /* source data packing */
+
+   screen->transfer_unmap(screen, tex_xfer);
+   screen->tex_transfer_destroy(tex_xfer);
+
+   /* copy / compress image */
+   util_blit_pixels_tex(ctx->st->blit,
+                        src_tex,          /* pipe_texture (src) */
+                        0, 0,             /* src x0, y0 */
+                        width, height,    /* src x1, y1 */
+                        dst_surface,      /* pipe_surface (dst) */
+                        xoffset, yoffset, /* dst x0, y0 */
+                        xoffset + width,  /* dst x1 */
+                        yoffset + height, /* dst y1 */
+                        0.0,              /* z */
+                        PIPE_TEX_MIPFILTER_NEAREST);
+
+   pipe_surface_reference(&dst_surface, NULL);
+   pipe_texture_reference(&src_tex, NULL);
+
+   return GL_TRUE;
+}
+
+
+/**
  * Do glTexImage1/2/3D().
  */
 static void
@@ -392,8 +517,9 @@ st_TexImage(GLcontext * ctx,
             const struct gl_pixelstore_attrib *unpack,
             struct gl_texture_object *texObj,
             struct gl_texture_image *texImage,
-            GLsizei imageSize, GLboolean compressed)
+            GLsizei imageSize, GLboolean compressed_src)
 {
+   struct pipe_screen *screen = ctx->st->pipe->screen;
    struct st_texture_object *stObj = st_texture_object(texObj);
    struct st_texture_image *stImage = st_texture_image(texImage);
    GLint postConvWidth, postConvHeight;
@@ -522,7 +648,7 @@ st_TexImage(GLcontext * ctx,
     * the expectation that the texture will be set up but nothing
     * more will be done.  This is where those calls return:
     */
-   if (compressed) {
+   if (compressed_src) {
       pixels = _mesa_validate_pbo_compressed_teximage(ctx, imageSize, pixels,
                                                      unpack,
                                                      "glCompressedTexImage");
@@ -535,6 +661,21 @@ st_TexImage(GLcontext * ctx,
    if (!pixels)
       return;
 
+   /* See if we can do texture compression with a blit/render.
+    */
+   if (!compressed_src &&
+       !ctx->Mesa_DXTn &&
+       is_compressed_mesa_format(texImage->TexFormat) &&
+       screen->is_format_supported(screen,
+                                   stImage->pt->format,
+                                   stImage->pt->target,
+                                   PIPE_TEXTURE_USAGE_RENDER_TARGET, 0)) {
+      if (compress_with_blit(ctx, target, level, 0, 0, 0, width, height, depth,
+                             format, type, pixels, unpack, texImage)) {
+         return;
+      }
+   }
+
    if (stImage->pt) {
       texImage->Data = st_texture_image_map(ctx->st, stImage, 0,
                                             PIPE_TRANSFER_WRITE, 0, 0,
@@ -570,7 +711,7 @@ st_TexImage(GLcontext * ctx,
     * the blitter to copy.  Or, use the hardware to do the format
     * conversion and copy:
     */
-   if (compressed) {
+   if (compressed_src) {
       memcpy(texImage->Data, pixels, imageSize);
    }
    else {
@@ -607,7 +748,7 @@ st_TexImage(GLcontext * ctx,
 
    _mesa_unmap_teximage_pbo(ctx, unpack);
 
-   if (stImage->pt) {
+   if (stImage->pt && texImage->Data) {
       st_texture_image_unmap(ctx->st, stImage);
       texImage->Data = NULL;
    }
@@ -678,6 +819,90 @@ st_CompressedTexImage2D(GLcontext *ctx, GLenum target, GLint level,
 }
 
 
+
+/**
+ * glGetTexImage() helper: decompress a compressed texture by rendering
+ * a textured quad.  Store the results in the user's buffer.
+ */
+static void
+decompress_with_blit(GLcontext * ctx, GLenum target, GLint level,
+                     GLenum format, GLenum type, GLvoid *pixels,
+                     struct gl_texture_object *texObj,
+                     struct gl_texture_image *texImage)
+{
+   struct pipe_screen *screen = ctx->st->pipe->screen;
+   struct st_texture_image *stImage = st_texture_image(texImage);
+   const GLuint width = texImage->Width;
+   const GLuint height = texImage->Height;
+   struct pipe_surface *dst_surface;
+   struct pipe_texture *dst_texture;
+   struct pipe_transfer *tex_xfer;
+
+   /* create temp / dest surface */
+   if (!util_create_rgba_surface(screen, width, height,
+                                 &dst_texture, &dst_surface)) {
+      _mesa_problem(ctx, "util_create_rgba_surface() failed "
+                    "in decompress_with_blit()");
+      return;
+   }
+
+   /* blit/render/decompress */
+   util_blit_pixels_tex(ctx->st->blit,
+                        stImage->pt,      /* pipe_texture (src) */
+                        0, 0,             /* src x0, y0 */
+                        width, height,    /* src x1, y1 */
+                        dst_surface,      /* pipe_surface (dst) */
+                        0, 0,             /* dst x0, y0 */
+                        width, height,    /* dst x1, y1 */
+                        0.0,              /* z */
+                        PIPE_TEX_MIPFILTER_NEAREST);
+
+   /* map the dst_surface so we can read from it */
+   tex_xfer = screen->get_tex_transfer(screen, dst_texture, 0, 0, 0,
+                                       PIPE_TRANSFER_READ,
+                                       0, 0, width, height);
+
+   pixels = _mesa_map_readpix_pbo(ctx, &ctx->Pack, pixels);
+
+   /* copy/pack data into user buffer */
+   if (st_equal_formats(stImage->pt->format, format, type)) {
+      /* memcpy */
+      const uint bytesPerRow = width * pf_get_size(stImage->pt->format);
+      ubyte *map = screen->transfer_map(screen, tex_xfer);
+      GLuint row;
+      for (row = 0; row < height; row++) {
+         GLvoid *dest = _mesa_image_address2d(&ctx->Pack, pixels, width,
+                                              height, format, type, row, 0);
+         memcpy(dest, map, bytesPerRow);
+         map += tex_xfer->stride;
+      }
+      screen->transfer_unmap(screen, tex_xfer);
+   }
+   else {
+      /* format translation via floats */
+      GLuint row;
+      for (row = 0; row < height; row++) {
+         const GLbitfield transferOps = 0x0; /* bypassed for glGetTexImage() */
+         GLfloat rgba[4 * MAX_WIDTH];
+         GLvoid *dest = _mesa_image_address2d(&ctx->Pack, pixels, width,
+                                              height, format, type, row, 0);
+
+         /* get float[4] rgba row from surface */
+         pipe_get_tile_rgba(tex_xfer, 0, row, width, 1, rgba);
+
+         _mesa_pack_rgba_span_float(ctx, width, (GLfloat (*)[4]) rgba, format,
+                                    type, dest, &ctx->Pack, transferOps);
+      }
+   }
+
+   _mesa_unmap_readpix_pbo(ctx, &ctx->Pack);
+
+   /* destroy the temp / dest surface */
+   util_destroy_rgba_surface(dst_texture, dst_surface);
+}
+
+
+
 /**
  * Need to map texture image into memory before copying image data,
  * then unmap it.
@@ -686,7 +911,7 @@ static void
 st_get_tex_image(GLcontext * ctx, GLenum target, GLint level,
                  GLenum format, GLenum type, GLvoid * pixels,
                  struct gl_texture_object *texObj,
-                 struct gl_texture_image *texImage, GLboolean compressed)
+                 struct gl_texture_image *texImage, GLboolean compressed_dst)
 {
    struct st_texture_image *stImage = st_texture_image(texImage);
    const GLuint dstImageStride =
@@ -695,11 +920,27 @@ st_get_tex_image(GLcontext * ctx, GLenum target, GLint level,
    GLuint depth, i;
    GLubyte *dest;
 
+   if (stImage->pt &&
+       pf_is_compressed(stImage->pt->format) &&
+       !compressed_dst) {
+      /* Need to decompress the texture.
+       * We'll do this by rendering a textured quad.
+       * Note that we only expect RGBA formats (no Z/depth formats).
+       */
+      decompress_with_blit(ctx, target, level, format, type, pixels,
+                           texObj, texImage);
+      return;
+   }
+
    /* Map */
    if (stImage->pt) {
       /* Image is stored in hardware format in a buffer managed by the
        * kernel.  Need to explicitly map and unmap it.
        */
+
+      st_teximage_flush_before_map(ctx->st, stImage->pt, 0, level,
+                                  PIPE_TRANSFER_READ);
+
       texImage->Data = st_texture_image_map(ctx->st, stImage, 0,
                                             PIPE_TRANSFER_READ, 0, 0,
                                             stImage->base.Width,
@@ -724,7 +965,7 @@ st_get_tex_image(GLcontext * ctx, GLenum target, GLint level,
    dest = (GLubyte *) pixels;
 
    for (i = 0; i < depth; i++) {
-      if (compressed) {
+      if (compressed_dst) {
         _mesa_get_compressed_teximage(ctx, target, level, dest,
                                       texObj, texImage);
       }
@@ -787,6 +1028,7 @@ st_TexSubimage(GLcontext *ctx, GLint dims, GLenum target, GLint level,
                struct gl_texture_object *texObj,
                struct gl_texture_image *texImage)
 {
+   struct pipe_screen *screen = ctx->st->pipe->screen;
    struct st_texture_image *stImage = st_texture_image(texImage);
    GLuint dstRowStride;
    const GLuint srcImageStride =
@@ -804,10 +1046,28 @@ st_TexSubimage(GLcontext *ctx, GLint dims, GLenum target, GLint level,
    if (!pixels)
       return;
 
+   /* See if we can do texture compression with a blit/render.
+    */
+   if (!ctx->Mesa_DXTn &&
+       is_compressed_mesa_format(texImage->TexFormat) &&
+       screen->is_format_supported(screen,
+                                   stImage->pt->format,
+                                   stImage->pt->target,
+                                   PIPE_TEXTURE_USAGE_RENDER_TARGET, 0)) {
+      if (compress_with_blit(ctx, target, level,
+                             xoffset, yoffset, zoffset,
+                             width, height, depth,
+                             format, type, pixels, packing, texImage)) {
+         return;
+      }
+   }
+
    /* Map buffer if necessary.  Need to lock to prevent other contexts
     * from uploading the buffer under us.
     */
    if (stImage->pt) {
+      st_teximage_flush_before_map(ctx->st, stImage->pt, 0, level,
+                                  PIPE_TRANSFER_WRITE);
       texImage->Data = st_texture_image_map(ctx->st, stImage, zoffset, 
                                             PIPE_TRANSFER_WRITE,
                                             xoffset, yoffset,
@@ -932,6 +1192,9 @@ fallback_copy_texsubimage(GLcontext *ctx, GLenum target, GLint level,
       srcY = strb->Base.Height - srcY - height;
    }
 
+   st_teximage_flush_before_map(ctx->st, strb->texture, 0, 0,
+                               PIPE_TRANSFER_READ);
+
    src_trans = screen->get_tex_transfer( screen,
                                          strb->texture,
                                          0, 0, 0,
@@ -939,6 +1202,9 @@ fallback_copy_texsubimage(GLcontext *ctx, GLenum target, GLint level,
                                          srcX, srcY,
                                          width, height);
 
+   st_teximage_flush_before_map(ctx->st, stImage->pt, 0, 0,
+                               PIPE_TRANSFER_WRITE);
+
    texDest = st_texture_image_map(ctx->st, stImage, 0, PIPE_TRANSFER_WRITE,
                                   destX, destY, width, height);
 
@@ -1318,6 +1584,11 @@ copy_image_data_to_texture(struct st_context *st,
 
       /* More straightforward upload.  
        */
+
+      st_teximage_flush_before_map(st, stObj->pt, stImage->face, dstLevel,
+                                  PIPE_TRANSFER_WRITE);
+
+
       st_texture_image_data(st->pipe,
                             stObj->pt,
                             stImage->face,
index 9e2d60c..d507e3e 100644 (file)
@@ -716,3 +716,23 @@ st_ChooseTextureFormat(GLcontext *ctx, GLint internalFormat,
 
    return translate_gallium_format_to_mesa_format(pFormat);
 }
+
+
+/**
+ * Test if a gallium format is equivalent to a GL format/type.
+ */
+GLboolean
+st_equal_formats(enum pipe_format pFormat, GLenum format, GLenum type)
+{
+   switch (pFormat) {
+   case PIPE_FORMAT_R8G8B8A8_UNORM:
+      return format == GL_RGBA && type == GL_UNSIGNED_BYTE;
+   case PIPE_FORMAT_B8G8R8A8_UNORM:
+      return format == GL_BGRA && type == GL_UNSIGNED_BYTE;
+   case PIPE_FORMAT_R5G6B5_UNORM:
+      return format == GL_RGB && type == GL_UNSIGNED_SHORT_5_6_5;
+   /* XXX more combos... */
+   default:
+      return GL_FALSE;
+   }
+}
index 3f5ac32..7bbbe2d 100644 (file)
@@ -76,4 +76,8 @@ st_ChooseTextureFormat(GLcontext * ctx, GLint internalFormat,
                        GLenum format, GLenum type);
 
 
+extern GLboolean
+st_equal_formats(enum pipe_format pFormat, GLenum format, GLenum type);
+
+
 #endif /* ST_CB_TEXIMAGE_H */
index 9cc2176..6e9aa52 100644 (file)
@@ -123,10 +123,17 @@ fallback_generate_mipmap(GLcontext *ctx, GLenum target,
       const ubyte *srcData;
       ubyte *dstData;
 
+      st_teximage_flush_before_map(ctx->st, pt, face, srcLevel,
+                                  PIPE_TRANSFER_READ);
+
       srcTrans = screen->get_tex_transfer(screen, pt, face, srcLevel, zslice,
                                           PIPE_TRANSFER_READ, 0, 0,
                                           pt->width[srcLevel],
                                           pt->height[srcLevel]);
+
+      st_teximage_flush_before_map(ctx->st, pt, face, dstLevel,
+                                  PIPE_TRANSFER_WRITE);
+
       dstTrans = screen->get_tex_transfer(screen, pt, face, dstLevel, zslice,
                                           PIPE_TRANSFER_WRITE, 0, 0,
                                           pt->width[dstLevel],
index 6348e83..2795570 100644 (file)
@@ -484,14 +484,14 @@ st_translate_fragment_program(struct st_context *st,
                /* handled above */
                assert(0);
                break;
-            case FRAG_RESULT_COLOR:
+            default:
+               assert(attr == FRAG_RESULT_COLOR ||
+                      (FRAG_RESULT_DATA0 <= attr && attr < FRAG_RESULT_MAX));
                fs_output_semantic_name[fs_num_outputs] = TGSI_SEMANTIC_COLOR;
                fs_output_semantic_index[fs_num_outputs] = numColors;
                outputMapping[attr] = fs_num_outputs;
                numColors++;
                break;
-            default:
-               assert(0);
             }
 
             output_flags[fs_num_outputs] = stfp->Base.Base.OutputFlags[attr];
index 19eb7e2..fcbaeb6 100644 (file)
@@ -188,8 +188,10 @@ st_texture_image_map(struct st_context *st, struct st_texture_image *stImage,
                     GLuint zoffset, enum pipe_transfer_usage usage,
                      GLuint x, GLuint y, GLuint w, GLuint h)
 {
-   struct pipe_screen *screen = st->pipe->screen;
+   struct pipe_context *pipe = st->pipe;
+   struct pipe_screen *screen = pipe->screen;
    struct pipe_texture *pt = stImage->pt;
+
    DBG("%s \n", __FUNCTION__);
 
    stImage->transfer = screen->get_tex_transfer(screen, pt, stImage->face,
@@ -265,6 +267,7 @@ st_texture_image_data(struct pipe_context *pipe,
    struct pipe_transfer *dst_transfer;
 
    DBG("%s\n", __FUNCTION__);
+
    for (i = 0; i < depth; i++) {
       dst_transfer = screen->get_tex_transfer(screen, dst, face, level, i,
                                               PIPE_TRANSFER_WRITE, 0, 0,
@@ -481,3 +484,20 @@ st_release_teximage(struct st_framebuffer *stfb, uint surfIndex,
 
    return 1;
 }
+
+void
+st_teximage_flush_before_map(struct st_context *st,
+                            struct pipe_texture *pt,
+                            unsigned int face,
+                            unsigned int level,
+                            enum pipe_transfer_usage usage)
+{
+   struct pipe_context *pipe = st->pipe;
+   unsigned referenced =
+      pipe->is_texture_referenced(pipe, pt, face, level);
+
+   if (referenced && ((referenced & PIPE_REFERENCED_FOR_WRITE) ||
+                     usage == PIPE_TRANSFER_WRITE ||
+                     usage == PIPE_TRANSFER_READ_WRITE))
+      st_flush(st, PIPE_FLUSH_RENDER_CACHE, NULL);
+}
index 60c0001..a392e3d 100644 (file)
@@ -170,5 +170,10 @@ st_texture_image_copy(struct pipe_context *pipe,
                       struct pipe_texture *src,
                       GLuint face);
 
-
+extern void
+st_teximage_flush_before_map(struct st_context *st,
+                            struct pipe_texture *pt,
+                            unsigned int face,
+                            unsigned int level,
+                            enum pipe_transfer_usage usage);
 #endif
index 9558f83..86bbd24 100644 (file)
@@ -64,6 +64,13 @@ struct vbo_save_vertex_list {
    GLubyte attrsz[VBO_ATTRIB_MAX];
    GLuint vertex_size;
 
+   /* Copy of the final vertex from node->vertex_store->bufferobj.
+    * Keep this in regular (non-VBO) memory to avoid repeated
+    * map/unmap of the VBO when updating GL current data.
+    */
+   GLfloat *current_data;
+   GLuint current_size;
+
    GLuint buffer_offset;
    GLuint count;
    GLuint wrap_count;          /* number of copied vertices at start */
index 52b6f18..8682260 100644 (file)
@@ -289,6 +289,31 @@ static void _save_compile_vertex_list( GLcontext *ctx )
    node->vertex_store->refcount++;
    node->prim_store->refcount++;
 
+
+   node->current_size = node->vertex_size - node->attrsz[0];
+   node->current_data = NULL;
+
+   if (node->current_size) {
+      /* If the malloc fails, we just pull the data out of the VBO
+       * later instead.
+       */
+      node->current_data = MALLOC( node->current_size * sizeof(GLfloat) );
+      if (node->current_data) {
+         const char *buffer = (const char *)save->vertex_store->buffer;
+         unsigned attr_offset = node->attrsz[0] * sizeof(GLfloat);
+         unsigned vertex_offset = 0;
+
+         if (node->count)
+            vertex_offset = (node->count-1) * node->vertex_size * sizeof(GLfloat);
+
+         memcpy( node->current_data,
+                 buffer + node->buffer_offset + vertex_offset + attr_offset,
+                 node->current_size * sizeof(GLfloat) );
+      }
+   }
+
+
+
    assert(node->attrsz[VBO_ATTRIB_POS] != 0 ||
          node->count == 0);
 
index f59e103..5110648 100644 (file)
@@ -46,20 +46,31 @@ static void _playback_copy_to_current( GLcontext *ctx,
                                       const struct vbo_save_vertex_list *node )
 {
    struct vbo_context *vbo = vbo_context(ctx);
-   GLfloat vertex[VBO_ATTRIB_MAX * 4], *data = vertex;
+   GLfloat vertex[VBO_ATTRIB_MAX * 4];
+   GLfloat *data;
    GLuint i, offset;
 
-   if (node->count)
-      offset = (node->buffer_offset + 
-               (node->count-1) * node->vertex_size * sizeof(GLfloat));
-   else
-      offset = node->buffer_offset;
+   if (node->current_size == 0)
+      return;
 
-   ctx->Driver.GetBufferSubData( ctx, 0, offset, 
-                                node->vertex_size * sizeof(GLfloat), 
-                                data, node->vertex_store->bufferobj );
+   if (node->current_data) {
+      data = node->current_data;
+   }
+   else {
+      data = vertex;
+
+      if (node->count)
+         offset = (node->buffer_offset + 
+                   (node->count-1) * node->vertex_size * sizeof(GLfloat));
+      else
+         offset = node->buffer_offset;
 
-   data += node->attrsz[0]; /* skip vertex position */
+      ctx->Driver.GetBufferSubData( ctx, 0, offset, 
+                                    node->vertex_size * sizeof(GLfloat), 
+                                    data, node->vertex_store->bufferobj );
+
+      data += node->attrsz[0]; /* skip vertex position */
+   }
 
    for (i = VBO_ATTRIB_POS+1 ; i < VBO_ATTRIB_MAX ; i++) {
       if (node->attrsz[i]) {