nv10: fix stuff and things.
authorStephane Marchesin <marchesin@icps.u-strasbg.fr>
Wed, 2 Apr 2008 03:10:18 +0000 (05:10 +0200)
committerStephane Marchesin <marchesin@icps.u-strasbg.fr>
Wed, 2 Apr 2008 03:10:18 +0000 (05:10 +0200)
src/gallium/drivers/nouveau/nouveau_class.h
src/gallium/drivers/nv10/nv10_context.c
src/gallium/drivers/nv10/nv10_context.h
src/gallium/drivers/nv10/nv10_miptree.c
src/gallium/drivers/nv10/nv10_prim_vbuf.c
src/gallium/drivers/nv10/nv10_screen.c
src/gallium/drivers/nv10/nv10_screen.h
src/gallium/drivers/nv10/nv10_state.c
src/gallium/drivers/nv10/nv10_state_emit.c

index dc202086d2c6bfe9063eff9303deb49339ab0c1b..880afe6ce082ef0f281f8673c82ccd209e4bcee9 100644 (file)
@@ -2804,6 +2804,16 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 #define  NV10TCL_VERTEX_WGH_1F                                                         0x00000ce4
 #define  NV10TCL_EDGEFLAG_ENABLE                                                       0x00000cec
 #define  NV10TCL_VERTEX_ARRAY_VALIDATE                                                 0x00000cf0
+#define  NV10TCL_VERTEX_ARRAY_ATTRIB_OFFSET(x)                                         (0x00000d00+((x)*8))
+#define  NV10TCL_VERTEX_ARRAY_ATTRIB_OFFSET__SIZE                                      0x00000008
+#define  NV10TCL_VERTEX_ARRAY_ATTRIB_FORMAT(x)                                         (0x00000d04+((x)*8))
+#define  NV10TCL_VERTEX_ARRAY_ATTRIB_FORMAT__SIZE                                      0x00000008
+#define   NV10TCL_VERTEX_ARRAY_ATTRIB_FORMAT_TYPE_SHIFT                                        0
+#define   NV10TCL_VERTEX_ARRAY_ATTRIB_FORMAT_TYPE_MASK                                 0x0000000f
+#define   NV10TCL_VERTEX_ARRAY_ATTRIB_FORMAT_FIELDS_SHIFT                              4
+#define   NV10TCL_VERTEX_ARRAY_ATTRIB_FORMAT_FIELDS_MASK                               0x000000f0
+#define   NV10TCL_VERTEX_ARRAY_ATTRIB_FORMAT_STRIDE_SHIFT                              8
+#define   NV10TCL_VERTEX_ARRAY_ATTRIB_FORMAT_STRIDE_MASK                               0x0000ff00
 #define  NV10TCL_VERTEX_ARRAY_OFFSET_POS                                               0x00000d00
 #define  NV10TCL_VERTEX_ARRAY_FORMAT_POS                                               0x00000d04
 #define   NV10TCL_VERTEX_ARRAY_FORMAT_POS_TYPE_SHIFT                                   0
@@ -4249,6 +4259,7 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 #define   NV34TCL_VERTEX_ARRAY_FORMAT_TYPE_MASK                                                0x0000000f
 #define    NV34TCL_VERTEX_ARRAY_FORMAT_TYPE_FLOAT                                      0x00000002
 #define    NV34TCL_VERTEX_ARRAY_FORMAT_TYPE_UBYTE                                      0x00000004
+#define    NV34TCL_VERTEX_ARRAY_FORMAT_TYPE_USHORT                                     0x00000005
 #define   NV34TCL_VERTEX_ARRAY_FORMAT_SIZE_SHIFT                                       4
 #define   NV34TCL_VERTEX_ARRAY_FORMAT_SIZE_MASK                                                0x000000f0
 #define   NV34TCL_VERTEX_ARRAY_FORMAT_STRIDE_SHIFT                                     8
@@ -4963,12 +4974,12 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 #define  NV40TCL_VP_UPLOAD_INST(x)                                                     (0x00000b80+((x)*4))
 #define  NV40TCL_VP_UPLOAD_INST__SIZE                                                  0x00000004
 #define  NV40TCL_CLIP_PLANE_ENABLE                                                     0x00001478
-#define   NV40TCL_CLIP_PLANE_ENABLE_PLANE0                                             (1 <<  2)
-#define   NV40TCL_CLIP_PLANE_ENABLE_PLANE1                                             (1 <<  6)
-#define   NV40TCL_CLIP_PLANE_ENABLE_PLANE2                                             (1 << 10)
-#define   NV40TCL_CLIP_PLANE_ENABLE_PLANE3                                             (1 << 14)
-#define   NV40TCL_CLIP_PLANE_ENABLE_PLANE4                                             (1 << 18)
-#define   NV40TCL_CLIP_PLANE_ENABLE_PLANE5                                             (1 << 22)
+#define   NV40TCL_CLIP_PLANE_ENABLE_PLANE0                                             (1 <<  1)
+#define   NV40TCL_CLIP_PLANE_ENABLE_PLANE1                                             (1 <<  5)
+#define   NV40TCL_CLIP_PLANE_ENABLE_PLANE2                                             (1 <<  9)
+#define   NV40TCL_CLIP_PLANE_ENABLE_PLANE3                                             (1 << 13)
+#define   NV40TCL_CLIP_PLANE_ENABLE_PLANE4                                             (1 << 17)
+#define   NV40TCL_CLIP_PLANE_ENABLE_PLANE5                                             (1 << 21)
 #define  NV40TCL_POLYGON_STIPPLE_ENABLE                                                        0x0000147c
 #define  NV40TCL_POLYGON_STIPPLE_PATTERN(x)                                            (0x00001480+((x)*4))
 #define  NV40TCL_POLYGON_STIPPLE_PATTERN__SIZE                                         0x00000020
@@ -4990,6 +5001,7 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 #define   NV40TCL_VTXFMT_TYPE_MASK                                                     0x0000000f
 #define    NV40TCL_VTXFMT_TYPE_FLOAT                                                   0x00000002
 #define    NV40TCL_VTXFMT_TYPE_UBYTE                                                   0x00000004
+#define    NV40TCL_VTXFMT_TYPE_USHORT                                                  0x00000005
 #define   NV40TCL_VTXFMT_SIZE_SHIFT                                                    4
 #define   NV40TCL_VTXFMT_SIZE_MASK                                                     0x000000f0
 #define   NV40TCL_VTXFMT_STRIDE_SHIFT                                                  8
index 14042fb2fbbfa5e4a2b287ba6f8f59edba29fce0..42c496b95902a2c3fc516a1bb12bc930c0d73dda 100644 (file)
@@ -12,13 +12,6 @@ nv10_flush(struct pipe_context *pipe, unsigned flags,
 {
        struct nv10_context *nv10 = nv10_context(pipe);
 
-       if (flags & PIPE_FLUSH_TEXTURE_CACHE) {
-               BEGIN_RING(celsius, 0x1fd8, 1);
-               OUT_RING  (2);
-               BEGIN_RING(celsius, 0x1fd8, 1);
-               OUT_RING  (1);
-       }
-
        FIRE_RING(fence);
 }
 
@@ -26,36 +19,21 @@ static void
 nv10_destroy(struct pipe_context *pipe)
 {
        struct nv10_context *nv10 = nv10_context(pipe);
-       struct nouveau_winsys *nvws = nv10->nvws;
 
        if (nv10->draw)
                draw_destroy(nv10->draw);
 
-       nvws->res_free(&nv10->vertprog.exec_heap);
-       nvws->res_free(&nv10->vertprog.data_heap);
-
-       nvws->notifier_free(&nv10->sync);
-
-       nvws->grobj_free(&nv10->celsius);
-
-       free(nv10);
+       FREE(nv10);
 }
 
-static boolean
-nv10_init_hwctx(struct nv10_context *nv10, int celsius_class)
+static void nv10_init_hwctx(struct nv10_context *nv10)
 {
-       struct nouveau_winsys *nvws = nv10->nvws;
-       int ret;
+       struct nv10_screen *screen = nv10->screen;
+       struct nouveau_winsys *nvws = screen->nvws;
        int i;
 
-       ret = nvws->grobj_alloc(nvws, celsius_class, &nv10->celsius);
-       if (ret) {
-               NOUVEAU_ERR("Error creating 3D object: %d\n", ret);
-               return FALSE;
-       }
-
        BEGIN_RING(celsius, NV10TCL_DMA_NOTIFY, 1);
-       OUT_RING  (nv10->sync->handle);
+       OUT_RING  (screen->sync->handle);
        BEGIN_RING(celsius, NV10TCL_DMA_IN_MEMORY0, 2);
        OUT_RING  (nvws->channel->vram->handle);
        OUT_RING  (nvws->channel->gart->handle);
@@ -90,7 +68,7 @@ nv10_init_hwctx(struct nv10_context *nv10, int celsius_class)
        BEGIN_RING(celsius, NV10TCL_NOP, 1);
        OUT_RING  (0);
 
-       if (celsius_class != NV10TCL) {
+       if (nv10->screen->celsius->grclass != NV10TCL) {
                /* For nv11, nv17 */
                BEGIN_RING(celsius, 0x120, 3);
                OUT_RING  (0);
@@ -243,72 +221,44 @@ nv10_init_hwctx(struct nv10_context *nv10, int celsius_class)
 
 
        FIRE_RING (NULL);
-       return TRUE;
 }
 
 struct pipe_context *
-nv10_create(struct pipe_screen *screen, unsigned pctx_id)
+nv10_create(struct pipe_screen *pscreen, unsigned pctx_id)
 {
-       struct pipe_winsys *pipe_winsys = screen->winsys;
-       struct nouveau_winsys *nvws = nv10_screen(screen)->nvws;
-       unsigned chipset = nv10_screen(screen)->chipset;
+       struct nv10_screen *screen = nv10_screen(pscreen);
+       struct pipe_winsys *ws = pscreen->winsys;
        struct nv10_context *nv10;
-       int celsius_class = 0, ret;
-
-       if (chipset>=0x20)
-               celsius_class=NV11TCL;
-       else if (chipset>=0x17)
-               celsius_class=NV17TCL;
-       else if (chipset>=0x11)
-               celsius_class=NV11TCL;
-       else
-               celsius_class=NV10TCL;
-
-       nv10 = CALLOC_STRUCT(nv10_context);
+       unsigned chipset = screen->chipset;
+       struct nouveau_winsys *nvws = screen->nvws;
+
+       nv10 = CALLOC(1, sizeof(struct nv10_context));
        if (!nv10)
                return NULL;
+       nv10->screen = screen;
+       nv10->pctx_id = pctx_id;
+
        nv10->chipset = chipset;
        nv10->nvws = nvws;
 
-       /* Notifier for sync purposes */
-       ret = nvws->notifier_alloc(nvws, 1, &nv10->sync);
-       if (ret) {
-               NOUVEAU_ERR("Error creating notifier object: %d\n", ret);
-               nv10_destroy(&nv10->pipe);
-               return NULL;
-       }
-
-       /* Vtxprog resources */
-       if (nvws->res_init(&nv10->vertprog.exec_heap, 0, 512) ||
-           nvws->res_init(&nv10->vertprog.data_heap, 0, 256)) {
-               nv10_destroy(&nv10->pipe);
-               return NULL;
-       }
-
-       /* Static celsius initialisation */
-       if (!nv10_init_hwctx(nv10, celsius_class)) {
-               nv10_destroy(&nv10->pipe);
-               return NULL;
-       }
-
-       /* Pipe context setup */
-       nv10->pipe.winsys = pipe_winsys;
-
+       nv10->pipe.winsys = ws;
+       nv10->pipe.screen = pscreen;
        nv10->pipe.destroy = nv10_destroy;
-
        nv10->pipe.draw_arrays = nv10_draw_arrays;
        nv10->pipe.draw_elements = nv10_draw_elements;
        nv10->pipe.clear = nv10_clear;
-
        nv10->pipe.flush = nv10_flush;
 
        nv10_init_surface_functions(nv10);
        nv10_init_state_functions(nv10);
+       nv10_init_miptree_functions(nv10);
 
        nv10->draw = draw_create();
        assert(nv10->draw);
        draw_set_rasterize_stage(nv10->draw, nv10_draw_vbuf_stage(nv10));
 
+       nv10_init_hwctx(nv10);
+
        return &nv10->pipe;
 }
 
index 386138556e5daf34eba1ed49137d81f1f62a8b75..61eb4e6a937fce18a04f3d19ea1e4d1d5a9845fe 100644 (file)
@@ -11,7 +11,7 @@
 #include "nouveau/nouveau_gldefs.h"
 
 #define NOUVEAU_PUSH_CONTEXT(ctx)                                              \
-       struct nv10_context *ctx = nv10
+       struct nv10_screen *ctx = nv10->screen
 #include "nouveau/nouveau_push.h"
 
 #include "nv10_state.h"
 #define NV10_NEW_VERTPROG      (1 << 1)
 #define NV10_NEW_FRAGPROG      (1 << 2)
 #define NV10_NEW_ARRAYS                (1 << 3)
-#define NV10_NEW_VBO           (1 << 4)
+#define NV10_NEW_VTXFMT                (1 << 4)
+#define NV10_NEW_BLEND         (1 << 5)
+#define NV10_NEW_BLENDCOL      (1 << 6)
+#define NV10_NEW_RAST          (1 << 7)
+#define NV10_NEW_DSA           (1 << 8)
+#define NV10_NEW_VIEWPORT      (1 << 9)
+#define NV10_NEW_SCISSOR       (1 << 9)
+#define NV10_NEW_FRAMEBUFFER   (1 << 10)
+
+#include "nv10_screen.h"
 
 struct nv10_context {
        struct pipe_context pipe;
+
        struct nouveau_winsys *nvws;
+       struct nv10_screen *screen;
+       unsigned pctx_id;
 
        struct draw_context *draw;
 
        int chipset;
-       struct nouveau_grobj *celsius;
-       struct nouveau_notifier *sync;
 
        uint32_t dirty;
 
@@ -49,6 +59,14 @@ struct nv10_context {
        struct pipe_buffer *zeta;
        uint32_t lma_offset;
 
+       struct nv10_blend_state *blend;
+       struct pipe_blend_color *blend_color;
+       struct nv10_rasterizer_state *rast;
+       struct nv10_depth_stencil_alpha_state *dsa;
+       struct pipe_viewport_state *viewport;
+       struct pipe_scissor_state *scissor;
+       struct pipe_framebuffer_state *framebuffer;
+
        struct {
                struct pipe_buffer *buffer;
                uint32_t format;
@@ -91,7 +109,9 @@ nv10_context(struct pipe_context *pipe)
 
 extern void nv10_init_state_functions(struct nv10_context *nv10);
 extern void nv10_init_surface_functions(struct nv10_context *nv10);
-extern void nv10_init_miptree_functions(struct pipe_screen *screen);
+extern void nv10_init_miptree_functions(struct nv10_context *nv10);
+
+extern void nv10_screen_init_miptree_functions(struct pipe_screen *pscreen);
 
 /* nv10_clear.c */
 extern void nv10_clear(struct pipe_context *pipe, struct pipe_surface *ps,
@@ -111,6 +131,7 @@ extern void nv10_fragtex_bind(struct nv10_context *);
 
 /* nv10_prim_vbuf.c */
 struct draw_stage *nv10_draw_vbuf_stage( struct nv10_context *nv10 );
+extern void nv10_vtxbuf_bind(struct nv10_context* nv10);
 
 /* nv10_state.c and friends */
 extern void nv10_emit_hw_state(struct nv10_context *nv10);
index 7b7f39b80c9653aab9132792c6aeaa4792e09111..4dfc675a6b9143719734466d5fa81861c3a66389 100644 (file)
@@ -69,7 +69,7 @@ nv10_miptree_create(struct pipe_screen *screen, struct pipe_texture *pt)
        mt->buffer = ws->buffer_create(ws, 256, PIPE_BUFFER_USAGE_PIXEL,
                                           mt->total_size);
        if (!mt->buffer) {
-               free(mt);
+               FREE(mt);
                return NULL;
        }
        
@@ -90,12 +90,19 @@ nv10_miptree_release(struct pipe_screen *screen, struct pipe_texture **pt)
                pipe_buffer_reference(ws, &nv10mt->buffer, NULL);
                for (l = 0; l <= mt->last_level; l++) {
                        if (nv10mt->level[l].image_offset)
-                               free(nv10mt->level[l].image_offset);
+                               FREE(nv10mt->level[l].image_offset);
                }
-               free(nv10mt);
+               FREE(nv10mt);
        }
 }
 
+static void
+nv10_miptree_update(struct pipe_context *pipe, struct pipe_texture *mt,
+                   uint face, uint levels)
+{
+}
+
+
 static struct pipe_surface *
 nv10_miptree_surface_get(struct pipe_screen *screen, struct pipe_texture *pt,
                         unsigned face, unsigned level, unsigned zslice)
@@ -122,13 +129,16 @@ nv10_miptree_surface_get(struct pipe_screen *screen, struct pipe_texture *pt,
 
        return ps;
 }
-void
-nv10_init_miptree_functions(struct pipe_screen *screen)
+
+void nv10_init_miptree_functions(struct nv10_context *nv10)
 {
-       struct nv10_screen *nv10screen = nv10_screen(screen);
+       nv10->pipe.texture_update = nv10_miptree_update;
+}
 
-       nv10screen->screen.texture_create = nv10_miptree_create;
-       nv10screen->screen.texture_release = nv10_miptree_release;
-       nv10screen->screen.get_tex_surface = nv10_miptree_surface_get;
+void nv10_screen_init_miptree_functions(struct pipe_screen *pscreen)
+{
+       pscreen->texture_create = nv10_miptree_create;
+       pscreen->texture_release = nv10_miptree_release;
+       pscreen->get_tex_surface = nv10_miptree_surface_get;
 }
 
index 1526891223459b3ef9f8192073625512874cbbb8..bbcfe1a2fdd66356b171137ded01189a2dddc0e1 100644 (file)
@@ -67,6 +67,17 @@ struct nv10_vbuf_render {
 };
 
 
+void nv10_vtxbuf_bind( struct nv10_context* nv10 )
+{
+       int i;
+       for(i = 0; i < 8; i++) {
+               BEGIN_RING(celsius, NV10TCL_VERTEX_ARRAY_ATTRIB_OFFSET(i), 1);
+               OUT_RING(0/*nv10->vtxbuf*/);
+               BEGIN_RING(celsius, NV10TCL_VERTEX_ARRAY_ATTRIB_FORMAT(i) ,1);
+               OUT_RING(0/*XXX*/);
+       }
+}
+
 /**
  * Basically a cast wrapper.
  */
@@ -100,7 +111,7 @@ nv10_vbuf_render_allocate_vertices( struct vbuf_render *render,
        assert(!nv10_render->buffer);
        nv10_render->buffer = winsys->buffer_create(winsys, 64, PIPE_BUFFER_USAGE_VERTEX, size);
 
-       nv10->dirty |= NV10_NEW_VBO;
+       nv10->dirty |= NV10_NEW_ARRAYS;
 
        return winsys->buffer_map(winsys, 
                        nv10_render->buffer, 
@@ -139,8 +150,8 @@ nv10_vbuf_render_draw( struct vbuf_render *render,
        }
 
        while (nr_indices) {
-               // XXX too big ?
-               push = MIN2(nr_indices, 2047 * 2);
+               // XXX too big/small ? check the size
+               push = MIN2(nr_indices, 1200 * 2);
 
                BEGIN_RING_NI(celsius, NV10TCL_VB_ELEMENT_U16, push >> 1);
                for (i = 0; i < push; i+=2)
index 4d8e0b05ccdd772487f0eba583f590dee6e27b35..80676ead1a9036621f9fdd195663535b4531eaa1 100644 (file)
@@ -116,35 +116,71 @@ nv10_screen_is_format_supported(struct pipe_screen *screen,
 }
 
 static void
-nv10_screen_destroy(struct pipe_screen *screen)
+nv10_screen_destroy(struct pipe_screen *pscreen)
 {
-       FREE(screen);
+       struct nv10_screen *screen = nv10_screen(pscreen);
+       struct nouveau_winsys *nvws = screen->nvws;
+
+       nvws->notifier_free(&screen->sync);
+       nvws->grobj_free(&screen->celsius);
+
+       FREE(pscreen);
 }
 
 struct pipe_screen *
-nv10_screen_create(struct pipe_winsys *winsys, struct nouveau_winsys *nvws,
+nv10_screen_create(struct pipe_winsys *ws, struct nouveau_winsys *nvws,
                   unsigned chipset)
 {
-       struct nv10_screen *nv10screen = CALLOC_STRUCT(nv10_screen);
+       struct nv10_screen *screen = CALLOC_STRUCT(nv10_screen);
+       unsigned celsius_class;
+       int ret;
 
-       if (!nv10screen)
+       if (!screen)
+               return NULL;
+       screen->chipset = chipset;
+       screen->nvws = nvws;
+
+       /* 3D object */
+       if (chipset>=0x20)
+               celsius_class=NV11TCL;
+       else if (chipset>=0x17)
+               celsius_class=NV17TCL;
+       else if (chipset>=0x11)
+               celsius_class=NV11TCL;
+       else
+               celsius_class=NV10TCL;
+
+       if (!celsius_class) {
+               NOUVEAU_ERR("Unknown nv1x chipset: nv%02x\n", chipset);
                return NULL;
+       }
+
+       ret = nvws->grobj_alloc(nvws, celsius_class, &screen->celsius);
+       if (ret) {
+               NOUVEAU_ERR("Error creating 3D object: %d\n", ret);
+               return FALSE;
+       }
+
+       /* Notifier for sync purposes */
+       ret = nvws->notifier_alloc(nvws, 1, &screen->sync);
+       if (ret) {
+               NOUVEAU_ERR("Error creating notifier object: %d\n", ret);
+               nv10_screen_destroy(&screen->pipe);
+               return NULL;
+       }
 
-       nv10screen->chipset = chipset;
-       nv10screen->nvws = nvws;
+       screen->pipe.winsys = ws;
+       screen->pipe.destroy = nv10_screen_destroy;
 
-       nv10screen->screen.winsys = winsys;
+       screen->pipe.get_name = nv10_screen_get_name;
+       screen->pipe.get_vendor = nv10_screen_get_vendor;
+       screen->pipe.get_param = nv10_screen_get_param;
+       screen->pipe.get_paramf = nv10_screen_get_paramf;
 
-       nv10screen->screen.destroy = nv10_screen_destroy;
+       screen->pipe.is_format_supported = nv10_screen_is_format_supported;
 
-       nv10screen->screen.get_name = nv10_screen_get_name;
-       nv10screen->screen.get_vendor = nv10_screen_get_vendor;
-       nv10screen->screen.get_param = nv10_screen_get_param;
-       nv10screen->screen.get_paramf = nv10_screen_get_paramf;
-       nv10screen->screen.is_format_supported = 
-               nv10_screen_is_format_supported;
+       nv10_screen_init_miptree_functions(&screen->pipe);
 
-       nv10_init_miptree_functions(&nv10screen->screen);
-       return &nv10screen->screen;
+       return &screen->pipe;
 }
 
index ac8c04072ab097c7ce5054857783b1f2fcc2e1f0..4192fe11ef45b6812ad5afdee38f7a81a259ef09 100644 (file)
@@ -4,10 +4,14 @@
 #include "pipe/p_screen.h"
 
 struct nv10_screen {
-       struct pipe_screen screen;
+       struct pipe_screen pipe;
 
        struct nouveau_winsys *nvws;
        unsigned chipset;
+
+       /* HW graphics objects */
+       struct nouveau_grobj *celsius;
+       struct nouveau_notifier *sync;
 };
 
 static INLINE struct nv10_screen *
index 1ff01de1060b0aba001a80b02109098600ed8a24..12722709f6baae03f674c62b5e6cdd41efcbe398 100644 (file)
@@ -35,6 +35,8 @@ static void nv10_vertex_layout(struct pipe_context* pipe)
                }
        }
        draw_compute_vertex_size(&vinfo);
+
+       nv10->dirty |= NV10_NEW_VTXFMT;
 }
 
 static void *
@@ -62,27 +64,19 @@ nv10_blend_state_create(struct pipe_context *pipe,
 }
 
 static void
-nv10_blend_state_bind(struct pipe_context *pipe, void *hwcso)
+nv10_blend_state_bind(struct pipe_context *pipe, void *blend)
 {
        struct nv10_context *nv10 = nv10_context(pipe);
-       struct nv10_blend_state *cb = hwcso;
-
-       BEGIN_RING(celsius, NV10TCL_DITHER_ENABLE, 1);
-       OUT_RING  (cb->d_enable);
 
-       BEGIN_RING(celsius, NV10TCL_BLEND_FUNC_ENABLE, 3);
-       OUT_RING  (cb->b_enable);
-       OUT_RING  (cb->b_srcfunc);
-       OUT_RING  (cb->b_dstfunc);
+       nv10->blend = (struct nv10_blend_state*)blend;
 
-       BEGIN_RING(celsius, NV10TCL_COLOR_MASK, 1);
-       OUT_RING  (cb->c_mask);
+       nv10->dirty |= NV10_NEW_BLEND;
 }
 
 static void
 nv10_blend_state_delete(struct pipe_context *pipe, void *hwcso)
 {
-       free(hwcso);
+       FREE(hwcso);
 }
 
 
@@ -255,7 +249,7 @@ nv10_sampler_state_bind(struct pipe_context *pipe, unsigned nr, void **sampler)
 static void
 nv10_sampler_state_delete(struct pipe_context *pipe, void *hwcso)
 {
-       free(hwcso);
+       FREE(hwcso);
 }
 
 static void
@@ -347,43 +341,19 @@ nv10_rasterizer_state_create(struct pipe_context *pipe,
 }
 
 static void
-nv10_rasterizer_state_bind(struct pipe_context *pipe, void *hwcso)
+nv10_rasterizer_state_bind(struct pipe_context *pipe, void *rast)
 {
        struct nv10_context *nv10 = nv10_context(pipe);
-       struct nv10_rasterizer_state *rs = hwcso;
-
-       BEGIN_RING(celsius, NV10TCL_SHADE_MODEL, 2);
-       OUT_RING  (rs->shade_model);
-       OUT_RING  (rs->line_width);
-
-
-       BEGIN_RING(celsius, NV10TCL_POINT_SIZE, 1);
-       OUT_RING  (rs->point_size);
-
-       BEGIN_RING(celsius, NV10TCL_POLYGON_MODE_FRONT, 2);
-       OUT_RING  (rs->poly_mode_front);
-       OUT_RING  (rs->poly_mode_back);
-
 
-       BEGIN_RING(celsius, NV10TCL_CULL_FACE, 2);
-       OUT_RING  (rs->cull_face);
-       OUT_RING  (rs->front_face);
+       nv10->rast = (struct nv10_rasterizer_state*)rast;
 
-       BEGIN_RING(celsius, NV10TCL_LINE_SMOOTH_ENABLE, 2);
-       OUT_RING  (rs->line_smooth_en);
-       OUT_RING  (rs->poly_smooth_en);
-
-       BEGIN_RING(celsius, NV10TCL_CULL_FACE_ENABLE, 1);
-       OUT_RING  (rs->cull_face_en);
-
-/*     BEGIN_RING(celsius, NV10TCL_POINT_SPRITE, 1);
-       OUT_RING  (rs->point_sprite);*/
+       nv10->dirty |= NV10_NEW_RAST;
 }
 
 static void
 nv10_rasterizer_state_delete(struct pipe_context *pipe, void *hwcso)
 {
-       free(hwcso);
+       FREE(hwcso);
 }
 
 static void *
@@ -415,25 +385,19 @@ nv10_depth_stencil_alpha_state_create(struct pipe_context *pipe,
 }
 
 static void
-nv10_depth_stencil_alpha_state_bind(struct pipe_context *pipe, void *hwcso)
+nv10_depth_stencil_alpha_state_bind(struct pipe_context *pipe, void *dsa)
 {
        struct nv10_context *nv10 = nv10_context(pipe);
-       struct nv10_depth_stencil_alpha_state *hw = hwcso;
-
-       BEGIN_RING(celsius, NV10TCL_DEPTH_FUNC, 3);
-       OUT_RINGp ((uint32_t *)&hw->depth, 3);
-       BEGIN_RING(celsius, NV10TCL_STENCIL_ENABLE, 1);
-       OUT_RING (hw->stencil.enable);
-       BEGIN_RING(celsius, NV10TCL_STENCIL_MASK, 7);
-       OUT_RINGp ((uint32_t *)&(hw->stencil.wmask), 7);
-       BEGIN_RING(celsius, NV10TCL_ALPHA_FUNC_ENABLE, 3);
-       OUT_RINGp ((uint32_t *)&hw->alpha.enabled, 3);
+
+       nv10->dsa = (struct nv10_depth_stencil_alpha_state*)dsa;
+
+       nv10->dirty |= NV10_NEW_DSA;
 }
 
 static void
 nv10_depth_stencil_alpha_state_delete(struct pipe_context *pipe, void *hwcso)
 {
-       free(hwcso);
+       FREE(hwcso);
 }
 
 static void *
@@ -461,11 +425,11 @@ nv10_vp_state_bind(struct pipe_context *pipe, void *hwcso)
 static void
 nv10_vp_state_delete(struct pipe_context *pipe, void *hwcso)
 {
-       struct nv10_context *nv10 = nv10_context(pipe);
+       //struct nv10_context *nv10 = nv10_context(pipe);
        struct nv10_vertex_program *vp = hwcso;
 
        //nv10_vertprog_destroy(nv10, vp);
-       free(vp);
+       FREE(vp);
 }
 
 static void *
@@ -499,7 +463,7 @@ nv10_fp_state_delete(struct pipe_context *pipe, void *hwcso)
        struct nv10_fragment_program *fp = hwcso;
 
        nv10_fragprog_destroy(nv10, fp);
-       free(fp);
+       FREE(fp);
 }
 
 static void
@@ -508,11 +472,9 @@ nv10_set_blend_color(struct pipe_context *pipe,
 {
        struct nv10_context *nv10 = nv10_context(pipe);
 
-       BEGIN_RING(celsius, NV10TCL_BLEND_COLOR, 1);
-       OUT_RING  ((float_to_ubyte(bcol->color[3]) << 24) |
-                  (float_to_ubyte(bcol->color[0]) << 16) |
-                  (float_to_ubyte(bcol->color[1]) <<  8) |
-                  (float_to_ubyte(bcol->color[2]) <<  0));
+       nv10->blend_color = (struct pipe_blend_color*)bcol;
+
+       nv10->dirty |= NV10_NEW_BLENDCOL;
 }
 
 static void
@@ -542,58 +504,10 @@ nv10_set_framebuffer_state(struct pipe_context *pipe,
                           const struct pipe_framebuffer_state *fb)
 {
        struct nv10_context *nv10 = nv10_context(pipe);
-       struct pipe_surface *rt, *zeta;
-       uint32_t rt_format, w, h;
-       int i, colour_format = 0, zeta_format = 0;
-
-       w = fb->cbufs[0]->width;
-       h = fb->cbufs[0]->height;
-       colour_format = fb->cbufs[0]->format;
-       rt = fb->cbufs[0];
-
-       if (fb->zsbuf) {
-               if (colour_format) {
-                       assert(w == fb->zsbuf->width);
-                       assert(h == fb->zsbuf->height);
-               } else {
-                       w = fb->zsbuf->width;
-                       h = fb->zsbuf->height;
-               }
-
-               zeta_format = fb->zsbuf->format;
-               zeta = fb->zsbuf;
-       }
 
-       rt_format = NV10TCL_RT_FORMAT_TYPE_LINEAR;
+       nv10->framebuffer = (struct pipe_framebuffer_state*)fb;
 
-       switch (colour_format) {
-       case PIPE_FORMAT_A8R8G8B8_UNORM:
-       case 0:
-               rt_format |= NV10TCL_RT_FORMAT_COLOR_A8R8G8B8;
-               break;
-       case PIPE_FORMAT_R5G6B5_UNORM:
-               rt_format |= NV10TCL_RT_FORMAT_COLOR_R5G6B5;
-               break;
-       default:
-               assert(0);
-       }
-
-       BEGIN_RING(celsius, NV10TCL_RT_PITCH, 1);
-       OUT_RING  ( (rt->pitch * rt->cpp) | ( (zeta->pitch * zeta->cpp) << 16) );
-       nv10->rt[0] = rt->buffer;
-
-       if (zeta_format)
-       {
-               nv10->zeta = zeta->buffer;
-       }
-
-       BEGIN_RING(celsius, NV10TCL_RT_HORIZ, 3);
-       OUT_RING  ((w << 16) | 0);
-       OUT_RING  ((h << 16) | 0);
-       OUT_RING  (rt_format);
-       BEGIN_RING(celsius, NV10TCL_VIEWPORT_CLIP_HORIZ(0), 2);
-       OUT_RING  (((w - 1) << 16) | 0);
-       OUT_RING  (((h - 1) << 16) | 0);
+       nv10->dirty |= NV10_NEW_FRAMEBUFFER;
 }
 
 static void
@@ -609,10 +523,9 @@ nv10_set_scissor_state(struct pipe_context *pipe,
 {
        struct nv10_context *nv10 = nv10_context(pipe);
 
-       // XXX
-/*     BEGIN_RING(celsius, NV10TCL_SCISSOR_HORIZ, 2);
-       OUT_RING  (((s->maxx - s->minx) << 16) | s->minx);
-       OUT_RING  (((s->maxy - s->miny) << 16) | s->miny);*/
+       nv10->scissor = (struct pipe_scissor_state*)s;
+
+       nv10->dirty |= NV10_NEW_SCISSOR;
 }
 
 static void
@@ -621,15 +534,9 @@ nv10_set_viewport_state(struct pipe_context *pipe,
 {
        struct nv10_context *nv10 = nv10_context(pipe);
 
-/*     OUT_RINGf (vpt->translate[0]);
-       OUT_RINGf (vpt->translate[1]);
-       OUT_RINGf (vpt->translate[2]);
-       OUT_RINGf (vpt->translate[3]);*/
-       BEGIN_RING(celsius, NV10TCL_VIEWPORT_SCALE_X, 4);
-       OUT_RINGf (vpt->scale[0]);
-       OUT_RINGf (vpt->scale[1]);
-       OUT_RINGf (vpt->scale[2]);
-       OUT_RINGf (vpt->scale[3]);
+       nv10->viewport = (struct pipe_viewport_state*)vpt;
+
+       nv10->dirty |= NV10_NEW_VIEWPORT;
 }
 
 static void
index 8bf0bd2d6834940124672ebb4b40350e5dde0268..0c524963896c8fabae05b60f0e94610d09ab1444 100644 (file)
+#include "pipe/p_util.h"
+
 #include "nv10_context.h"
 #include "nv10_state.h"
 
+static void nv10_state_emit_blend(struct nv10_context* nv10)
+{
+       struct nv10_blend_state *b = nv10->blend;
+
+       BEGIN_RING(celsius, NV10TCL_DITHER_ENABLE, 1);
+       OUT_RING  (b->d_enable);
+
+       BEGIN_RING(celsius, NV10TCL_BLEND_FUNC_ENABLE, 3);
+       OUT_RING  (b->b_enable);
+       OUT_RING  (b->b_srcfunc);
+       OUT_RING  (b->b_dstfunc);
+
+       BEGIN_RING(celsius, NV10TCL_COLOR_MASK, 1);
+       OUT_RING  (b->c_mask);
+}
+
+static void nv10_state_emit_blend_color(struct nv10_context* nv10)
+{
+       struct pipe_blend_color *c = nv10->blend_color;
+
+       BEGIN_RING(celsius, NV10TCL_BLEND_COLOR, 1);
+       OUT_RING  ((float_to_ubyte(c->color[3]) << 24)|
+                  (float_to_ubyte(c->color[0]) << 16)|
+                  (float_to_ubyte(c->color[1]) << 8) |
+                  (float_to_ubyte(c->color[2]) << 0));
+}
+
+static void nv10_state_emit_rast(struct nv10_context* nv10)
+{
+       struct nv10_rasterizer_state *r = nv10->rast;
+
+       BEGIN_RING(celsius, NV10TCL_SHADE_MODEL, 2);
+       OUT_RING  (r->shade_model);
+       OUT_RING  (r->line_width);
+
+
+       BEGIN_RING(celsius, NV10TCL_POINT_SIZE, 1);
+       OUT_RING  (r->point_size);
+
+       BEGIN_RING(celsius, NV10TCL_POLYGON_MODE_FRONT, 2);
+       OUT_RING  (r->poly_mode_front);
+       OUT_RING  (r->poly_mode_back);
+
+
+       BEGIN_RING(celsius, NV10TCL_CULL_FACE, 2);
+       OUT_RING  (r->cull_face);
+       OUT_RING  (r->front_face);
+
+       BEGIN_RING(celsius, NV10TCL_LINE_SMOOTH_ENABLE, 2);
+       OUT_RING  (r->line_smooth_en);
+       OUT_RING  (r->poly_smooth_en);
+
+       BEGIN_RING(celsius, NV10TCL_CULL_FACE_ENABLE, 1);
+       OUT_RING  (r->cull_face_en);
+}
+
+static void nv10_state_emit_dsa(struct nv10_context* nv10)
+{
+       struct nv10_depth_stencil_alpha_state *d = nv10->dsa;
+
+       BEGIN_RING(celsius, NV10TCL_DEPTH_FUNC, 3);
+       OUT_RINGp ((uint32_t *)&d->depth, 3);
+       BEGIN_RING(celsius, NV10TCL_STENCIL_ENABLE, 1);
+       OUT_RING (d->stencil.enable);
+       BEGIN_RING(celsius, NV10TCL_STENCIL_MASK, 7);
+       OUT_RINGp ((uint32_t *)&(d->stencil.wmask), 7);
+       BEGIN_RING(celsius, NV10TCL_ALPHA_FUNC_ENABLE, 3);
+       OUT_RINGp ((uint32_t *)&d->alpha.enabled, 3);
+}
+
+static void nv10_state_emit_viewport(struct nv10_context* nv10)
+{
+       struct pipe_viewport_state *vpt = nv10->viewport;
+
+/*     OUT_RINGf (vpt->translate[0]);
+       OUT_RINGf (vpt->translate[1]);
+       OUT_RINGf (vpt->translate[2]);
+       OUT_RINGf (vpt->translate[3]);*/
+       BEGIN_RING(celsius, NV10TCL_VIEWPORT_SCALE_X, 4);
+       OUT_RINGf (vpt->scale[0]);
+       OUT_RINGf (vpt->scale[1]);
+       OUT_RINGf (vpt->scale[2]);
+       OUT_RINGf (vpt->scale[3]);
+}
+
+static void nv10_state_emit_scissor(struct nv10_context* nv10)
+{
+       // XXX this is so not working
+/*     struct pipe_scissor_state *s = nv10->scissor;
+       BEGIN_RING(celsius, NV10TCL_SCISSOR_HORIZ, 2);
+       OUT_RING  (((s->maxx - s->minx) << 16) | s->minx);
+       OUT_RING  (((s->maxy - s->miny) << 16) | s->miny);*/
+}
+
+static void nv10_state_emit_framebuffer(struct nv10_context* nv10)
+{
+       struct pipe_framebuffer_state* fb = nv10->framebuffer;
+       struct pipe_surface *rt, *zeta;
+       uint32_t rt_format, w, h;
+       int colour_format = 0, zeta_format = 0;
+
+       w = fb->cbufs[0]->width;
+       h = fb->cbufs[0]->height;
+       colour_format = fb->cbufs[0]->format;
+       rt = fb->cbufs[0];
+
+       if (fb->zsbuf) {
+               if (colour_format) {
+                       assert(w == fb->zsbuf->width);
+                       assert(h == fb->zsbuf->height);
+               } else {
+                       w = fb->zsbuf->width;
+                       h = fb->zsbuf->height;
+               }
+
+               zeta_format = fb->zsbuf->format;
+               zeta = fb->zsbuf;
+       }
+
+       rt_format = NV10TCL_RT_FORMAT_TYPE_LINEAR;
+
+       switch (colour_format) {
+       case PIPE_FORMAT_A8R8G8B8_UNORM:
+       case 0:
+               rt_format |= NV10TCL_RT_FORMAT_COLOR_A8R8G8B8;
+               break;
+       case PIPE_FORMAT_R5G6B5_UNORM:
+               rt_format |= NV10TCL_RT_FORMAT_COLOR_R5G6B5;
+               break;
+       default:
+               assert(0);
+       }
+
+       BEGIN_RING(celsius, NV10TCL_RT_PITCH, 1);
+       OUT_RING  ( (rt->pitch * rt->cpp) | ( (zeta->pitch * zeta->cpp) << 16) );
+       nv10->rt[0] = rt->buffer;
+
+       if (zeta_format)
+       {
+               nv10->zeta = zeta->buffer;
+       }
+
+       BEGIN_RING(celsius, NV10TCL_RT_HORIZ, 3);
+       OUT_RING  ((w << 16) | 0);
+       OUT_RING  ((h << 16) | 0);
+       OUT_RING  (rt_format);
+       BEGIN_RING(celsius, NV10TCL_VIEWPORT_CLIP_HORIZ(0), 2);
+       OUT_RING  (((w - 1) << 16) | 0);
+       OUT_RING  (((h - 1) << 16) | 0);
+}
+
 void
 nv10_emit_hw_state(struct nv10_context *nv10)
 {
        int i;
 
+       if (nv10->dirty & NV10_NEW_VERTPROG) {
+               //nv10_vertprog_bind(nv10, nv10->vertprog.current);
+               nv10->dirty &= ~NV10_NEW_VERTPROG;
+       }
+
        if (nv10->dirty & NV10_NEW_FRAGPROG) {
                nv10_fragprog_bind(nv10, nv10->fragprog.current);
                /*XXX: clear NV10_NEW_FRAGPROG if no new program uploaded */
+               nv10->dirty_samplers |= (1<<10);
+               nv10->dirty_samplers = 0;
        }
 
        if (nv10->dirty_samplers || (nv10->dirty & NV10_NEW_FRAGPROG)) {
@@ -16,16 +176,50 @@ nv10_emit_hw_state(struct nv10_context *nv10)
                nv10->dirty &= ~NV10_NEW_FRAGPROG;
        }
 
-       if (nv10->dirty & NV10_NEW_VERTPROG) {
-               //nv10_vertprog_bind(nv10, nv10->vertprog.current);
-               nv10->dirty &= ~NV10_NEW_VERTPROG;
+       if (nv10->dirty & NV10_NEW_ARRAYS) {
+               nv10->dirty &= ~NV10_NEW_ARRAYS;
+               // array state will be put here once it's not emitted at each frame
        }
 
-       if (nv10->dirty & NV10_NEW_VBO) {
-               
+       if (nv10->dirty & NV10_NEW_VTXFMT) {
+               nv10->dirty &= ~NV10_NEW_VTXFMT;
+               nv10_vtxbuf_bind(nv10);
        }
 
-       nv10->dirty_samplers = 0;
+       if (nv10->dirty & NV10_NEW_BLEND) {
+               nv10->dirty &= ~NV10_NEW_BLEND;
+               nv10_state_emit_blend(nv10);
+       }
+
+       if (nv10->dirty & NV10_NEW_BLENDCOL) {
+               nv10->dirty &= ~NV10_NEW_BLENDCOL;
+               nv10_state_emit_blend_color(nv10);
+       }
+
+       if (nv10->dirty & NV10_NEW_RAST) {
+               nv10->dirty &= ~NV10_NEW_RAST;
+               nv10_state_emit_rast(nv10);
+       }
+
+       if (nv10->dirty & NV10_NEW_DSA) {
+               nv10->dirty &= ~NV10_NEW_DSA;
+               nv10_state_emit_dsa(nv10);
+       }
+
+       if (nv10->dirty & NV10_NEW_VIEWPORT) {
+               nv10->dirty &= ~NV10_NEW_VIEWPORT;
+               nv10_state_emit_viewport(nv10);
+       }
+
+       if (nv10->dirty & NV10_NEW_SCISSOR) {
+               nv10->dirty &= ~NV10_NEW_SCISSOR;
+               nv10_state_emit_scissor(nv10);
+       }
+
+       if (nv10->dirty & NV10_NEW_FRAMEBUFFER) {
+               nv10->dirty &= ~NV10_NEW_FRAMEBUFFER;
+               nv10_state_emit_framebuffer(nv10);
+       }
 
        /* Emit relocs for every referenced buffer.
         * This is to ensure the bufmgr has an accurate idea of how
@@ -48,10 +242,16 @@ nv10_emit_hw_state(struct nv10_context *nv10)
                BEGIN_RING(celsius, NV10TCL_ZETA_OFFSET, 1);
                OUT_RELOCl(nv10->zeta, 0, NOUVEAU_BO_VRAM | NOUVEAU_BO_WR);
                /* XXX for when we allocate LMA on nv17 */
-/*             BEGIN_RING(celsius, NV10TCL_LMA_DEPTH_OFFSET, 1);
-               OUT_RELOCl(nv10->zeta+lma_offset);*/
+/*             BEGIN_RING(celsius, NV10TCL_LMA_DEPTH_BUFFER_OFFSET, 1);
+               OUT_RELOCl(nv10->zeta + lma_offset);*/
        }
 
+       /* Vertex buffer */
+       BEGIN_RING(celsius, NV10TCL_DMA_VTXBUF0, 1);
+       OUT_RELOCo(nv10->rt[0], NOUVEAU_BO_VRAM | NOUVEAU_BO_WR);
+       BEGIN_RING(celsius, NV10TCL_COLOR_OFFSET, 1);
+       OUT_RELOCl(nv10->rt[0], 0, NOUVEAU_BO_VRAM | NOUVEAU_BO_WR);
+
        /* Texture images */
        for (i = 0; i < 2; i++) {
                if (!(nv10->fp_samplers & (1 << i)))