rbug: Fix shaders
authorJakob Bornecrantz <jakob@vmware.com>
Wed, 12 May 2010 13:38:20 +0000 (14:38 +0100)
committerJakob Bornecrantz <jakob@vmware.com>
Wed, 12 May 2010 19:15:23 +0000 (20:15 +0100)
src/gallium/drivers/rbug/rbug_context.c
src/gallium/drivers/rbug/rbug_context.h
src/gallium/drivers/rbug/rbug_core.c
src/gallium/drivers/rbug/rbug_objects.c
src/gallium/drivers/rbug/rbug_objects.h

index 0bc9b32ab906d0f51dfadd83176ef3612d6a7dcf..158904d2344c44b101464a862731828c819da26d 100644 (file)
@@ -29,6 +29,7 @@
 #include "pipe/p_context.h"
 #include "util/u_memory.h"
 #include "util/u_inlines.h"
+#include "util/u_simple_list.h"
 
 #include "rbug_context.h"
 #include "rbug_objects.h"
@@ -318,70 +319,120 @@ rbug_delete_depth_stencil_alpha_state(struct pipe_context *_pipe,
 
 static void *
 rbug_create_fs_state(struct pipe_context *_pipe,
-                     const struct pipe_shader_state *fs)
+                     const struct pipe_shader_state *state)
 {
    struct rbug_context *rb_pipe = rbug_context(_pipe);
    struct pipe_context *pipe = rb_pipe->pipe;
+   void *result;
 
-   return pipe->create_fs_state(pipe,
-                                fs);
+   result = pipe->create_fs_state(pipe, state);
+   if (!result)
+      return NULL;
+
+   return rbug_shader_create(rb_pipe, state, result, RBUG_SHADER_FRAGMENT);
 }
 
 static void
 rbug_bind_fs_state(struct pipe_context *_pipe,
-                   void *fs)
+                   void *_fs)
 {
    struct rbug_context *rb_pipe = rbug_context(_pipe);
    struct pipe_context *pipe = rb_pipe->pipe;
+   void *fs;
 
+   fs = rbug_shader_unwrap(_fs);
+   rb_pipe->curr.fs = rbug_shader(_fs);
    pipe->bind_fs_state(pipe,
                        fs);
 }
 
 static void
 rbug_delete_fs_state(struct pipe_context *_pipe,
-                     void *fs)
+                     void *_fs)
 {
    struct rbug_context *rb_pipe = rbug_context(_pipe);
-   struct pipe_context *pipe = rb_pipe->pipe;
+   struct rbug_shader *rb_shader = rbug_shader(_fs);
 
-   pipe->delete_fs_state(pipe,
-                         fs);
+   rbug_shader_destroy(rb_pipe, rb_shader);
 }
 
 static void *
 rbug_create_vs_state(struct pipe_context *_pipe,
-                     const struct pipe_shader_state *vs)
+                     const struct pipe_shader_state *state)
 {
    struct rbug_context *rb_pipe = rbug_context(_pipe);
    struct pipe_context *pipe = rb_pipe->pipe;
+   void *result;
+
+   result = pipe->create_vs_state(pipe, state);
+   if (!result)
+      return NULL;
 
-   return pipe->create_vs_state(pipe,
-                                vs);
+   return rbug_shader_create(rb_pipe, state, result, RBUG_SHADER_VERTEX);
 }
 
 static void
 rbug_bind_vs_state(struct pipe_context *_pipe,
-                   void *vs)
+                   void *_vs)
 {
    struct rbug_context *rb_pipe = rbug_context(_pipe);
    struct pipe_context *pipe = rb_pipe->pipe;
+   void *vs;
 
+   vs = rbug_shader_unwrap(_vs);
+   rb_pipe->curr.vs = rbug_shader(_vs);
    pipe->bind_vs_state(pipe,
                        vs);
 }
 
 static void
 rbug_delete_vs_state(struct pipe_context *_pipe,
-                     void *vs)
+                     void *_vs)
+{
+   struct rbug_context *rb_pipe = rbug_context(_pipe);
+   struct rbug_shader *rb_shader = rbug_shader(_vs);
+
+   rbug_shader_destroy(rb_pipe, rb_shader);
+}
+
+static void *
+rbug_create_gs_state(struct pipe_context *_pipe,
+                     const struct pipe_shader_state *state)
+{
+   struct rbug_context *rb_pipe = rbug_context(_pipe);
+   struct pipe_context *pipe = rb_pipe->pipe;
+   void *result;
+
+   result = pipe->create_gs_state(pipe, state);
+   if (!result)
+      return NULL;
+
+   return rbug_shader_create(rb_pipe, state, result, RBUG_SHADER_GEOM);
+}
+
+static void
+rbug_bind_gs_state(struct pipe_context *_pipe,
+                   void *_gs)
 {
    struct rbug_context *rb_pipe = rbug_context(_pipe);
    struct pipe_context *pipe = rb_pipe->pipe;
+   void *gs;
 
-   pipe->delete_vs_state(pipe,
-                         vs);
+   gs = rbug_shader_unwrap(_gs);
+   rb_pipe->curr.gs = rbug_shader(_gs);
+   pipe->bind_gs_state(pipe,
+                       gs);
 }
 
+static void
+rbug_delete_gs_state(struct pipe_context *_pipe,
+                     void *_gs)
+{
+   struct rbug_context *rb_pipe = rbug_context(_pipe);
+   struct rbug_shader *rb_shader = rbug_shader(_gs);
+
+   rbug_shader_destroy(rb_pipe, rb_shader);
+}
 
 static void *
 rbug_create_vertex_elements_state(struct pipe_context *_pipe,
@@ -834,12 +885,20 @@ struct pipe_context *
 rbug_context_create(struct pipe_screen *_screen, struct pipe_context *pipe)
 {
    struct rbug_context *rb_pipe;
-   (void)rbug_screen(_screen);
+   struct rbug_screen *rb_screen = rbug_screen(_screen);
+
+   if (!rb_screen)
+      return NULL;
 
    rb_pipe = CALLOC_STRUCT(rbug_context);
-   if (!rb_pipe) {
+   if (!rb_pipe)
       return NULL;
-   }
+
+   pipe_mutex_init(rb_pipe->draw_mutex);
+   pipe_condvar_init(rb_pipe->draw_cond);
+   pipe_mutex_init(rb_pipe->call_mutex);
+   pipe_mutex_init(rb_pipe->list_mutex);
+   make_empty_list(&rb_pipe->shaders);
 
    rb_pipe->base.winsys = NULL;
    rb_pipe->base.screen = _screen;
@@ -874,6 +933,9 @@ rbug_context_create(struct pipe_screen *_screen, struct pipe_context *pipe)
    rb_pipe->base.create_vs_state = rbug_create_vs_state;
    rb_pipe->base.bind_vs_state = rbug_bind_vs_state;
    rb_pipe->base.delete_vs_state = rbug_delete_vs_state;
+   rb_pipe->base.create_gs_state = rbug_create_gs_state;
+   rb_pipe->base.bind_gs_state = rbug_bind_gs_state;
+   rb_pipe->base.delete_gs_state = rbug_delete_gs_state;
    rb_pipe->base.create_vertex_elements_state = rbug_create_vertex_elements_state;
    rb_pipe->base.bind_vertex_elements_state = rbug_bind_vertex_elements_state;
    rb_pipe->base.delete_vertex_elements_state = rbug_delete_vertex_elements_state;
@@ -904,5 +966,7 @@ rbug_context_create(struct pipe_screen *_screen, struct pipe_context *pipe)
 
    rb_pipe->pipe = pipe;
 
+   rbug_screen_add_to_list(rb_screen, contexts, rb_pipe);
+
    return &rb_pipe->base;
 }
index 08ff050a9a3db50e69fc0ca01a0f17d584c52535..ccba3c192542070812f93ef352b3f0df0a475cfd 100644 (file)
@@ -48,6 +48,7 @@ struct rbug_context {
    struct {
       struct rbug_shader *fs;
       struct rbug_shader *vs;
+      struct rbug_shader *gs;
 
       struct rbug_sampler_view *sampler_views[PIPE_MAX_SAMPLERS];
       unsigned num_sampler_views;
index c0b1d97f460d1f16a893abcd3ba681a5dc1836e2..13aa95a59b7e210b529b6b8e6366123ef33637be 100644 (file)
@@ -97,53 +97,71 @@ rbug_get_shader_locked(struct rbug_context *rb_context, rbug_shader_t shdr)
 
 static void *
 rbug_shader_create_locked(struct pipe_context *pipe,
-                          struct rbug_shader *tr_shdr,
+                          struct rbug_shader *rb_shader,
                           struct tgsi_token *tokens)
 {
    void *state = NULL;
    struct pipe_shader_state pss = { 0 };
    pss.tokens = tokens;
 
-#if 0
-   if (tr_shdr->type == TRACE_SHADER_FRAGMENT) {
+   switch(rb_shader->type) {
+   case RBUG_SHADER_FRAGMENT:
       state = pipe->create_fs_state(pipe, &pss);
-   } else if (tr_shdr->type == TRACE_SHADER_VERTEX) {
+      break;
+   case RBUG_SHADER_VERTEX:
       state = pipe->create_vs_state(pipe, &pss);
-   } else
+      break;
+   case RBUG_SHADER_GEOM:
+      state = pipe->create_gs_state(pipe, &pss);
+      break;
+   default:
       assert(0);
-#endif
+      break;
+   }
 
    return state;
 }
 
 static void
 rbug_shader_bind_locked(struct pipe_context *pipe,
-                        struct rbug_shader *tr_shdr,
+                        struct rbug_shader *rb_shader,
                         void *state)
 {
-#if 0
-   if (tr_shdr->type == TRACE_SHADER_FRAGMENT) {
+   switch(rb_shader->type) {
+   case RBUG_SHADER_FRAGMENT:
       pipe->bind_fs_state(pipe, state);
-   } else if (tr_shdr->type == TRACE_SHADER_VERTEX) {
+      break;
+   case RBUG_SHADER_VERTEX:
       pipe->bind_vs_state(pipe, state);
-   } else
+      break;
+   case RBUG_SHADER_GEOM:
+      pipe->bind_gs_state(pipe, state);
+      break;
+   default:
       assert(0);
-#endif
+      break;
+   }
 }
 
 static void
 rbug_shader_delete_locked(struct pipe_context *pipe,
-                          struct rbug_shader *tr_shdr,
+                          struct rbug_shader *rb_shader,
                           void *state)
 {
-#if 0
-   if (tr_shdr->type == TRACE_SHADER_FRAGMENT) {
+   switch(rb_shader->type) {
+   case RBUG_SHADER_FRAGMENT:
       pipe->delete_fs_state(pipe, state);
-   } else if (tr_shdr->type == TRACE_SHADER_VERTEX) {
+      break;
+   case RBUG_SHADER_VERTEX:
       pipe->delete_vs_state(pipe, state);
-   } else
+      break;
+   case RBUG_SHADER_GEOM:
+      pipe->delete_gs_state(pipe, state);
+      break;
+   default:
       assert(0);
-#endif
+      break;
+   }
 }
 
 /************************************************
index 4f9b23263b9a0b9f8515ddb1f8e5f43b5da9e4d9..d963baab4177a04d03cc143a547b96999ab3f46f 100644 (file)
@@ -29,6 +29,8 @@
 #include "util/u_memory.h"
 #include "util/u_simple_list.h"
 
+#include "tgsi/tgsi_parse.h"
+
 #include "rbug_screen.h"
 #include "rbug_objects.h"
 #include "rbug_context.h"
@@ -193,3 +195,53 @@ rbug_transfer_destroy(struct rbug_context *rb_context,
    FREE(rb_transfer);
 }
 
+void *
+rbug_shader_create(struct rbug_context *rb_context,
+                   const struct pipe_shader_state *state,
+                   void *result, enum rbug_shader_type type)
+{
+   struct rbug_shader *rb_shader = CALLOC_STRUCT(rbug_shader);
+
+   rb_shader->type = type;
+   rb_shader->shader = result;
+   rb_shader->tokens = tgsi_dup_tokens(state->tokens);
+
+   /* works on context as well since its just a macro */
+   rbug_screen_add_to_list(rb_context, shaders, rb_shader);
+
+   return rb_shader;
+}
+
+void
+rbug_shader_destroy(struct rbug_context *rb_context,
+                    struct rbug_shader *rb_shader)
+{
+   struct pipe_context *pipe = rb_context->pipe;
+
+   /* works on context as well since its just a macro */
+   rbug_screen_remove_from_list(rb_context, shaders, rb_shader);
+
+   switch(rb_shader->type) {
+   case RBUG_SHADER_FRAGMENT:
+      if (rb_shader->replaced_shader)
+         pipe->delete_fs_state(pipe, rb_shader->replaced_shader);
+      pipe->delete_fs_state(pipe, rb_shader->shader);
+      break;
+   case RBUG_SHADER_VERTEX:
+      if (rb_shader->replaced_shader)
+         pipe->delete_vs_state(pipe, rb_shader->replaced_shader);
+      pipe->delete_vs_state(pipe, rb_shader->shader);
+      break;
+   case RBUG_SHADER_GEOM:
+      if (rb_shader->replaced_shader)
+         pipe->delete_gs_state(pipe, rb_shader->replaced_shader);
+      pipe->delete_gs_state(pipe, rb_shader->shader);
+      break;
+   default:
+      assert(0);
+   }
+
+   FREE(rb_shader->replaced_tokens);
+   FREE(rb_shader->tokens);
+   FREE(rb_shader);
+}
index 7f48c01b57717a8fef9f7c58c576f748bd627739..49c128d3d1ace5cf416a00c57304d897b21d727a 100644 (file)
@@ -47,6 +47,13 @@ struct rbug_resource
 };
 
 
+enum rbug_shader_type
+{
+   RBUG_SHADER_GEOM,
+   RBUG_SHADER_VERTEX,
+   RBUG_SHADER_FRAGMENT,
+};
+
 struct rbug_shader
 {
    struct rbug_list list;
@@ -56,6 +63,7 @@ struct rbug_shader
    void *replaced_shader;
    void *replaced_tokens;
 
+   enum rbug_shader_type type;
    boolean disabled;
 };
 
@@ -205,5 +213,14 @@ void
 rbug_transfer_destroy(struct rbug_context *rb_context,
                       struct rbug_transfer *rb_transfer);
 
+void *
+rbug_shader_create(struct rbug_context *rb_context,
+                   const struct pipe_shader_state *state,
+                   void *result, enum rbug_shader_type type);
+
+void
+rbug_shader_destroy(struct rbug_context *rb_context,
+                    struct rbug_shader *rb_shader);
+
 
 #endif /* RBUG_OBJECTS_H */