OSDN Git Service

nv50: use stateobjs for sampler/image_control uploads
authorBen Skeggs <skeggsb@gmail.com>
Mon, 16 Jun 2008 12:02:02 +0000 (22:02 +1000)
committerBen Skeggs <skeggsb@gmail.com>
Sun, 29 Jun 2008 05:46:18 +0000 (15:46 +1000)
src/gallium/drivers/nouveau/nouveau_stateobj.h
src/gallium/drivers/nv50/nv50_state_validate.c

index d501b76..78b2738 100644 (file)
@@ -2,6 +2,7 @@
 #define __NOUVEAU_STATEOBJ_H__
 
 #include "pipe/p_util.h"
+#include "pipe/p_debug.h"
 
 struct nouveau_stateobj_reloc {
        struct pipe_buffer *bo;
@@ -68,6 +69,14 @@ so_data(struct nouveau_stateobj *so, unsigned data)
 }
 
 static INLINE void
+so_datap(struct nouveau_stateobj *so, unsigned *data, unsigned size)
+{
+       so->cur_packet += (4 * size);
+       while (size--)
+               (*so->cur++) = (*data++);
+}
+
+static INLINE void
 so_method(struct nouveau_stateobj *so, struct nouveau_grobj *gr,
          unsigned mthd, unsigned size)
 {
@@ -92,6 +101,15 @@ so_reloc(struct nouveau_stateobj *so, struct pipe_buffer *bo,
 }
 
 static INLINE void
+so_dump(struct nouveau_stateobj *so)
+{
+       unsigned i, nr = so->cur - so->push;
+
+       for (i = 0; i < nr; i++)
+               debug_printf("+0x%04x: 0x%08x\n", i, so->push[i]);
+}
+
+static INLINE void
 so_emit(struct nouveau_winsys *nvws, struct nouveau_stateobj *so)
 {
        struct nouveau_pushbuf *pb = nvws->channel->pushbuf;
index 63c1756..b5a9195 100644 (file)
@@ -181,34 +181,41 @@ nv50_state_validate(struct nv50_context *nv50)
        if (nv50->dirty & NV50_NEW_SAMPLER) {
                int i;
 
-               BEGIN_RING(tesla, 0x0f00, 1);
-               OUT_RING  ((NV50_CB_TSC << 0) | (0 << 8));
-               BEGIN_RING(tesla, 0x40000f04, nv50->sampler_nr * 8);
+               so = so_new(nv50->sampler_nr * 8 + 3, 0);
+               so_method(so, tesla, 0x0f00, 1);
+               so_data  (so, NV50_CB_TSC);
+               so_method(so, tesla, 0x40000f04, nv50->sampler_nr * 8);
                for (i = 0; i < nv50->sampler_nr; i++)
-                       OUT_RINGp(nv50->sampler[i], 8);
+                       so_datap (so, nv50->sampler[i], 8);
+               so_emit(nvws, so);
+               so_ref(NULL, &so);
        }
 
        if (nv50->dirty & NV50_NEW_TEXTURE) {
                int i;
 
-               BEGIN_RING(tesla, 0x0f00, 1);
-               OUT_RING  ((NV50_CB_TIC << 0) | (0 << 8));
-               BEGIN_RING(tesla, 0x40000f04, nv50->miptree_nr * 8);
-               for (i = 0; i < nv50->sampler_nr; i++) {
+               so = so_new(nv50->miptree_nr * 8 + 3, nv50->miptree_nr * 2);
+               so_method(so, tesla, 0x0f00, 1);
+               so_data  (so, NV50_CB_TIC);
+               so_method(so, tesla, 0x40000f04, nv50->miptree_nr * 8);
+               for (i = 0; i < nv50->miptree_nr; i++) {
                        struct nv50_miptree *mt = nv50->miptree[i];
 
-                       OUT_RING  (0x2a712488);
-                       OUT_RELOCl(mt->buffer, 0,
-                                  NOUVEAU_BO_VRAM | NOUVEAU_BO_LOW);
-                       OUT_RING  (0xd0c05000);
-                       OUT_RING  (0x00300000);
-                       OUT_RING  (mt->base.width[0]);
-                       OUT_RING  ((mt->base.depth[0] << 16) |
-                                   mt->base.height[0]);
-                       OUT_RING  (0x03000000);
-                       OUT_RELOCh(mt->buffer, 0,
-                                  NOUVEAU_BO_VRAM | NOUVEAU_BO_HIGH);
+                       so_data (so, 0x2a712488);
+                       so_reloc(so, mt->buffer, 0, NOUVEAU_BO_VRAM |
+                                    NOUVEAU_BO_LOW, 0, 0);
+                       so_data (so, 0xd0c05000);
+                       so_data (so, 0x00300000);
+                       so_data (so, mt->base.width[0]);
+                       so_data (so, (mt->base.depth[0] << 16) |
+                                     mt->base.height[0]);
+                       so_data (so, 0x03000000);
+                       so_reloc(so, mt->buffer, 0, NOUVEAU_BO_VRAM |
+                                    NOUVEAU_BO_HIGH, 0, 0);
                }
+               
+               so_emit(nvws, so);
+               so_ref(NULL, &so);
        }
 
        if (nv50->dirty & NV50_NEW_ARRAYS)