draw: share machine
[mesa.git] / src / gallium / auxiliary / draw / draw_pt_fetch_shade_emit.c
index 9e1d1add36dc00401d20181425d548a9c9edd98e..5265a131605a35a26a87490c7cc2f24575e87731 100644 (file)
 
 struct fetch_shade_emit;
 
-struct fse_shader {
-   struct translate_key key;
-
-   void (*run_linear)( const struct fetch_shade_emit *fse,
-                       unsigned start,
-                       unsigned count,
-                       char *buffer );
-};
 
 /* Prototype fetch, shade, emit-hw-verts all in one go.
  */
 struct fetch_shade_emit {
-   struct draw_pt_front_end base;
-
+   struct draw_pt_middle_end base;
    struct draw_context *draw;
 
-   struct translate_key key;
 
    /* Temporaries:
     */
@@ -68,266 +58,62 @@ struct fetch_shade_emit {
    const ubyte *src[PIPE_MAX_ATTRIBS];
    unsigned prim;
 
-   /* Points to one of the three hardwired example shaders, below:
-    */
-   struct fse_shader *active;
-
-   /* Temporary: A list of hard-wired shaders.  Of course the plan
-    * would be to generate these for a given (vertex-shader,
-    * translate-key) pair...
-    */
-   struct fse_shader shader[10];
-   int nr_shaders;
-};
-
-
-
-/* Not quite passthrough yet -- we're still running the 'shader' here,
- * inlined into the vertex fetch function.
- */
-static void fetch_xyz_rgb_st( const struct fetch_shade_emit *fse,
-                             unsigned start,
-                             unsigned count,
-                              char *buffer )
-{
-   unsigned i;
-
-   const float *m = fse->constants;
-   const float m0 = m[0],  m4 = m[4],  m8 = m[8],  m12 = m[12];
-   const float m1 = m[1],  m5 = m[5],  m9 = m[9],  m13 = m[13];
-   const float m2 = m[2],  m6 = m[6],  m10 = m[10],  m14 = m[14];
-   const float m3 = m[3],  m7 = m[7],  m11 = m[11],  m15 = m[15];
-
-   const ubyte *xyz = fse->src[0] + start * fse->pitch[0];
-   const ubyte *st = fse->src[2] + start * fse->pitch[2];
-   
-   float *out = (float *)buffer;
-
-
-   assert(fse->pitch[1] == 0);
-
-   /* loop over vertex attributes (vertex shader inputs)
-    */
-   for (i = 0; i < count; i++) {
-      {
-        const float *in = (const float *)xyz;
-        const float ix = in[0], iy = in[1], iz = in[2];
-
-        out[0] = m0 * ix + m4 * iy + m8  * iz + m12;
-        out[1] = m1 * ix + m5 * iy + m9  * iz + m13;
-        out[2] = m2 * ix + m6 * iy + m10 * iz + m14;
-        out[3] = m3 * ix + m7 * iy + m11 * iz + m15;
-        xyz += fse->pitch[0];
-      }
-
-      {
-        out[4] = 1.0f;
-        out[5] = 1.0f;
-        out[6] = 1.0f;
-        out[7] = 1.0f;
-      }
-
-      {
-        const float *in = (const float *)st; st += fse->pitch[2];
-        out[8] = in[0];
-        out[9] = in[1];
-        out[10] = 0.0f;
-        out[11] = 1.0f;
-      }
-
-      out += 12;
-   }
-}
-
-
-
-static void fetch_xyz_rgb( const struct fetch_shade_emit *fse,
-                          unsigned start,
-                          unsigned count,
-                           char *buffer )
-{
-   unsigned i;
-
-   const float *m = (const float *)fse->constants;
-   const float m0 = m[0],  m4 = m[4],  m8 = m[8],  m12 = m[12];
-   const float m1 = m[1],  m5 = m[5],  m9 = m[9],  m13 = m[13];
-   const float m2 = m[2],  m6 = m[6],  m10 = m[10],  m14 = m[14];
-   const float m3 = m[3],  m7 = m[7],  m11 = m[11],  m15 = m[15];
-
-   const ubyte *xyz = fse->src[0] + start * fse->pitch[0];
-   const ubyte *rgb = fse->src[1] + start * fse->pitch[1];
-
-   float *out = (float *)buffer;
-
-//   debug_printf("rgb %f %f %f\n", rgb[0], rgb[1], rgb[2]);
-
-
-   for (i = 0; i < count; i++) {
-      {
-        const float *in = (const float *)xyz;
-        const float ix = in[0], iy = in[1], iz = in[2];
-
-        out[0] = m0 * ix + m4 * iy + m8  * iz + m12;
-        out[1] = m1 * ix + m5 * iy + m9  * iz + m13;
-        out[2] = m2 * ix + m6 * iy + m10 * iz + m14;
-        out[3] = m3 * ix + m7 * iy + m11 * iz + m15;
-        xyz += fse->pitch[0];
-      }
-
-      {
-        const float *in = (const float *)rgb;
-        out[4] = in[0];
-        out[5] = in[1];
-        out[6] = in[2];
-        out[7] = 1.0f;
-         rgb += fse->pitch[1];
-      }
-
-      out += 8;
-   }
-}
-
-
-
-
-static void fetch_xyz_rgb_psiz( const struct fetch_shade_emit *fse,
-                               unsigned start,
-                               unsigned count,
-                                char *buffer )
-{
-   unsigned i;
-
-   const float *m = (const float *)fse->constants;
-   const float m0 = m[0],  m4 = m[4],  m8 = m[8],  m12 = m[12];
-   const float m1 = m[1],  m5 = m[5],  m9 = m[9],  m13 = m[13];
-   const float m2 = m[2],  m6 = m[6],  m10 = m[10],  m14 = m[14];
-   const float m3 = m[3],  m7 = m[7],  m11 = m[11],  m15 = m[15];
-
-   const ubyte *xyz = fse->src[0] + start * fse->pitch[0];
-   const float *rgb = (const float *)(fse->src[1] + start * fse->pitch[1]);
-   const float psiz = 1.0;
-
-   float *out = (float *)buffer;
-
-
-   assert(fse->pitch[1] == 0);
-
-   for (i = 0; i < count; i++) {
-      {
-        const float *in = (const float *)xyz;
-        const float ix = in[0], iy = in[1], iz = in[2];
-
-        out[0] = m0 * ix + m4 * iy + m8  * iz + m12;
-        out[1] = m1 * ix + m5 * iy + m9  * iz + m13;
-        out[2] = m2 * ix + m6 * iy + m10 * iz + m14;
-        out[3] = m3 * ix + m7 * iy + m11 * iz + m15;
-        xyz += fse->pitch[0];
-      }
-
-      {
-        out[4] = rgb[0];
-        out[5] = rgb[1];
-        out[6] = rgb[2];
-        out[7] = 1.0f;
-      }
-
-      {
-        out[8] = psiz;
-      }
-
-      out += 9;
-   }
-}
-
-
-
-
-static boolean set_prim( struct fetch_shade_emit *fse,
-                         unsigned prim,
-                         unsigned count )
-{
-   struct draw_context *draw = fse->draw;
-
-   fse->prim = prim;
-
-   switch (prim) { 
-   case PIPE_PRIM_LINE_LOOP:
-      if (count > 1024)
-         return FALSE;
-      draw->render->set_primitive( draw->render, PIPE_PRIM_LINE_STRIP );
-      break;
-
-   case PIPE_PRIM_TRIANGLE_FAN:
-   case PIPE_PRIM_POLYGON:
-      if (count > 1024)
-         return FALSE;
-      draw->render->set_primitive( draw->render, prim );
-      break;
-
-   case PIPE_PRIM_QUADS:
-   case PIPE_PRIM_QUAD_STRIP:
-      draw->render->set_primitive( draw->render, PIPE_PRIM_TRIANGLES );
-      break;
-
-   default:
-      draw->render->set_primitive( draw->render, prim );
-      break;
-   }
-
-   return TRUE;
-}
+   struct draw_vs_varient_key key;
+   struct draw_vs_varient *active;
 
 
+   const struct vertex_info *vinfo;
+};
 
 
 
                               
-static void fse_prepare( struct draw_pt_front_end *fe,
-                            unsigned prim,
-                            struct draw_pt_middle_end *unused,
-                            unsigned opt )
+static void fse_prepare( struct draw_pt_middle_end *middle,
+                         unsigned prim, 
+                         unsigned opt )
 {
-   struct fetch_shade_emit *fse = (struct fetch_shade_emit *)fe;
+   struct fetch_shade_emit *fse = (struct fetch_shade_emit *)middle;
    struct draw_context *draw = fse->draw;
-   unsigned num_vs_inputs = draw->vertex_shader->info.num_inputs;
-   unsigned num_vs_outputs = draw->vertex_shader->info.num_outputs;
+   unsigned num_vs_inputs = draw->vs.vertex_shader->info.num_inputs;
    const struct vertex_info *vinfo;
    unsigned i;
-   boolean need_psize = 0;
    
 
-   if (draw->pt.user.elts) {
-      assert(0);
-      return ;
-   }
-
-   if (!set_prim(fse, prim, /*count*/1022 )) {
+   if (!draw->render->set_primitive( draw->render, 
+                                     prim )) {
       assert(0);
-      return ;
+      return;
    }
 
    /* Must do this after set_primitive() above:
     */
-   vinfo = draw->render->get_vertex_info(draw->render);
+   fse->vinfo = vinfo = draw->render->get_vertex_info(draw->render);
    
 
 
-   fse->key.nr_elements = MAX2(num_vs_outputs,     /* outputs - translate to hw format */
-                               num_vs_inputs);     /* inputs - fetch from api format */
-
    fse->key.output_stride = vinfo->size * 4;
+   fse->key.nr_outputs = vinfo->num_attribs;
+   fse->key.nr_inputs = num_vs_inputs;
+
+   fse->key.nr_elements = MAX2(fse->key.nr_outputs,     /* outputs - translate to hw format */
+                               fse->key.nr_inputs);     /* inputs - fetch from api format */
+
+   fse->key.viewport = !draw->identity_viewport;
+   fse->key.clip = !draw->bypass_clipping;
+   fse->key.pad = 0;
+
    memset(fse->key.element, 0, 
           fse->key.nr_elements * sizeof(fse->key.element[0]));
 
    for (i = 0; i < num_vs_inputs; i++) {
       const struct pipe_vertex_element *src = &draw->pt.vertex_element[i];
-      fse->key.element[i].input_format = src->src_format;
+      fse->key.element[i].in.format = src->src_format;
 
-      /* Consider ignoring these at this point, ie make generated
-       * programs independent of this state:
+      /* Consider ignoring these, ie make generated programs
+       * independent of this state:
        */
-      fse->key.element[i].input_buffer = 0; //src->vertex_buffer_index;
-      fse->key.element[i].input_offset = 0; //src->src_offset;
+      fse->key.element[i].in.buffer = src->vertex_buffer_index;
+      fse->key.element[i].in.offset = src->src_offset;
    }
    
 
@@ -336,32 +122,25 @@ static void fse_prepare( struct draw_pt_front_end *fe,
 
       for (i = 0; i < vinfo->num_attribs; i++) {
          unsigned emit_sz = 0;
-         unsigned output_format = PIPE_FORMAT_NONE;
-         unsigned vs_output = vinfo->src_index[i];
 
          switch (vinfo->emit[i]) {
          case EMIT_4F:
-            output_format = PIPE_FORMAT_R32G32B32A32_FLOAT;
             emit_sz = 4 * sizeof(float);
             break;
          case EMIT_3F:
-            output_format = PIPE_FORMAT_R32G32B32_FLOAT;
             emit_sz = 3 * sizeof(float);
             break;
          case EMIT_2F:
-            output_format = PIPE_FORMAT_R32G32_FLOAT;
             emit_sz = 2 * sizeof(float);
             break;
          case EMIT_1F:
-            output_format = PIPE_FORMAT_R32_FLOAT;
             emit_sz = 1 * sizeof(float);
             break;
          case EMIT_1F_PSIZE:
-            need_psize = 1;
-            output_format = PIPE_FORMAT_R32_FLOAT;
             emit_sz = 1 * sizeof(float);
-            vs_output = num_vs_outputs + 1;
-         
+            break;
+         case EMIT_4UB:
+            emit_sz = 4 * sizeof(ubyte);
             break;
          default:
             assert(0);
@@ -372,32 +151,15 @@ static void fse_prepare( struct draw_pt_front_end *fe,
           * numbers, not to positions in the hw vertex description --
           * that's handled by the output_offset field.
           */
-         fse->key.element[vs_output].output_format = output_format;
-         fse->key.element[vs_output].output_offset = dst_offset;
+         fse->key.element[i].out.format = vinfo->emit[i];
+         fse->key.element[i].out.vs_output = vinfo->src_index[i];
+         fse->key.element[i].out.offset = dst_offset;
       
          dst_offset += emit_sz;
          assert(fse->key.output_stride >= dst_offset);
       }
    }
 
-   /* To make psize work, really need to tell the vertex shader to
-    * copy that value from input->output.  For 'translate' this was
-    * implicit for all elements.
-    */
-#if 0
-   if (need_psize) {
-      unsigned input = num_vs_inputs + 1;
-      const struct pipe_vertex_element *src = &draw->pt.vertex_element[i];
-      fse->key.element[i].input_format = PIPE_FORMAT_R32_FLOAT;
-      fse->key.element[i].input_buffer = 0; //nr_buffers + 1;
-      fse->key.element[i].input_offset = 0; 
-
-      fse->key.nr_elements += 1;
-      
-   }
-#endif
-   
-   fse->constants = draw->pt.user.constants;
 
    /* Would normally look up a vertex shader and peruse its list of
     * varients somehow.  We omitted that step and put all the
@@ -405,11 +167,8 @@ static void fse_prepare( struct draw_pt_front_end *fe,
     * assumption that this happens to be a matching shader...  ie
     * you're running isosurf, aren't you?
     */
-   fse->active = NULL;
-   for (i = 0; i < fse->nr_shaders; i++) {
-      if (translate_key_compare( &fse->key, &fse->shader[i].key) == 0)
-         fse->active = &fse->shader[i];
-   }
+   fse->active = draw_vs_lookup_varient( draw->vs.vertex_shader, 
+                                         &fse->key );
 
    if (!fse->active) {
       assert(0);
@@ -421,218 +180,148 @@ static void fse_prepare( struct draw_pt_front_end *fe,
    for (i = 0; i < num_vs_inputs; i++) {
       unsigned buf = draw->pt.vertex_element[i].vertex_buffer_index;
 
-      fse->src[i] = ((const ubyte *) draw->pt.user.vbuffer[buf] + 
-                     draw->pt.vertex_buffer[buf].buffer_offset + 
-                     draw->pt.vertex_element[i].src_offset);
-
-      fse->pitch[i] = draw->pt.vertex_buffer[buf].pitch;
-
+      fse->active->set_input( fse->active, 
+                              i, 
+                              
+                              ((const ubyte *) draw->pt.user.vbuffer[buf] + 
+                               draw->pt.vertex_buffer[buf].buffer_offset),
+                              
+                              draw->pt.vertex_buffer[buf].pitch );
    }
 
-   
    //return TRUE;
 }
 
 
-static boolean split_prim_inplace(unsigned prim, unsigned *first, unsigned *incr)
-{
-   switch (prim) {
-   case PIPE_PRIM_POINTS:
-      *first = 1;
-      *incr = 1;
-      return TRUE;
-   case PIPE_PRIM_LINES:
-      *first = 2;
-      *incr = 2;
-      return TRUE;
-   case PIPE_PRIM_LINE_STRIP:
-      *first = 2;
-      *incr = 1;
-      return TRUE;
-   case PIPE_PRIM_TRIANGLES:
-      *first = 3;
-      *incr = 3;
-      return TRUE;
-   case PIPE_PRIM_TRIANGLE_STRIP:
-      *first = 3;
-      *incr = 1;
-      return TRUE;
-   case PIPE_PRIM_QUADS:
-      *first = 4;
-      *incr = 4;
-      return TRUE;
-   case PIPE_PRIM_QUAD_STRIP:
-      *first = 4;
-      *incr = 2;
-      return TRUE;
-   default:
-      *first = 0;
-      *incr = 1;               /* set to one so that count % incr works */
-      return FALSE;
-   }
-}
-
-
 
 
-#define INDEX(i) (start + (i))
-static void fse_render_linear( struct vbuf_render *render,
-                               unsigned prim,
-                               unsigned start,
-                               unsigned length )
-{
-   ushort *tmp = NULL;
-   unsigned i, j;
-
-   switch (prim) {
-   case PIPE_PRIM_LINE_LOOP:
-      tmp = MALLOC( sizeof(ushort) * (length + 1) );
 
-      for (i = 0; i < length; i++)
-        tmp[i] = INDEX(i);
-      tmp[length] = 0;
 
-      render->draw( render,
-                         tmp,
-                         length+1 );
-      break;
 
+static void fse_run_linear( struct draw_pt_middle_end *middle, 
+                            unsigned start, 
+                            unsigned count )
+{
+   struct fetch_shade_emit *fse = (struct fetch_shade_emit *)middle;
+   struct draw_context *draw = fse->draw;
+   unsigned alloc_count = align(count, 4);
+   char *hw_verts;
 
-   case PIPE_PRIM_QUAD_STRIP:
-      tmp = MALLOC( sizeof(ushort) * (length / 2 * 6) );
-
-      for (j = i = 0; i + 3 < length; i += 2, j += 6) {
-        tmp[j+0] = INDEX(i+0);
-        tmp[j+1] = INDEX(i+1);
-        tmp[j+2] = INDEX(i+3);
-
-        tmp[j+3] = INDEX(i+2);
-        tmp[j+4] = INDEX(i+0);
-        tmp[j+5] = INDEX(i+3);
-      }
-
-      if (j)
-        render->draw( render, tmp, j );
-      break;
-
-   case PIPE_PRIM_QUADS:
-      tmp = MALLOC( sizeof(int) * (length / 4 * 6) );
-
-      for (j = i = 0; i + 3 < length; i += 4, j += 6) {
-        tmp[j+0] = INDEX(i+0);
-        tmp[j+1] = INDEX(i+1);
-        tmp[j+2] = INDEX(i+3);
-
-        tmp[j+3] = INDEX(i+1);
-        tmp[j+4] = INDEX(i+2);
-        tmp[j+5] = INDEX(i+3);
-      }
+   /* XXX: need to flush to get prim_vbuf.c to release its allocation??
+    */
+   draw_do_flush( draw, DRAW_FLUSH_BACKEND );
 
-      if (j)
-        render->draw( render, tmp, j );
-      break;
+   hw_verts = draw->render->allocate_vertices( draw->render,
+                                               (ushort)fse->key.output_stride,
+                                               (ushort)alloc_count );
 
-   default:
-      render->draw_arrays( render,
-                                 start,
-                                 length );
-      break;
+   if (!hw_verts) {
+      assert(0);
+      return;
    }
 
-   if (tmp)
-      FREE(tmp);
-}
-
-
-
-static boolean do_draw( struct fetch_shade_emit *fse, 
-                        unsigned start, unsigned count )
-{
-   struct draw_context *draw = fse->draw;
-
-   char *hw_verts = 
-      draw->render->allocate_vertices( draw->render,
-                                       (ushort)fse->key.output_stride,
-                                       (ushort)count );
-
-   if (!hw_verts)
-      return FALSE;
-                                       
    /* Single routine to fetch vertices, run shader and emit HW verts.
-    * Clipping and viewport transformation are done on hardware.
+    * Clipping is done elsewhere -- either by the API or on hardware,
+    * or for some other reason not required...
     */
-   fse->active->run_linear( fse, 
+   fse->active->run_linear( fse->active
                             start, count,
                             hw_verts );
 
    /* Draw arrays path to avoid re-emitting index list again and
     * again.
     */
-   fse_render_linear( draw->render,
-                      fse->prim,
-                      0,
-                      count );
+   draw->render->draw_arrays( draw->render,
+                              0,
+                              count );
    
+   if (0) {
+      unsigned i;
+      for (i = 0; i < count; i++) {
+         debug_printf("\n\n%s vertex %d: (stride %d, offset %d)\n", __FUNCTION__, i,
+                      fse->key.output_stride,
+                      fse->key.output_stride * i);
+
+         draw_dump_emitted_vertex( fse->vinfo, 
+                                   (const uint8_t *)hw_verts + fse->key.output_stride * i );
+      }
+   }
+
 
    draw->render->release_vertices( draw->render, 
                                   hw_verts, 
                                   fse->key.output_stride, 
                                   count );
-
-   return TRUE;
 }
 
 
 static void
-fse_run(struct draw_pt_front_end *fe, 
-        pt_elt_func elt_func,
-        const void *elt_ptr,
-        unsigned count)
+fse_run(struct draw_pt_middle_end *middle,
+        const unsigned *fetch_elts,
+        unsigned fetch_count,
+        const ushort *draw_elts,
+        unsigned draw_count )
 {
-   struct fetch_shade_emit *fse = (struct fetch_shade_emit *)fe;
-   unsigned i = 0;
-   unsigned first, incr;
-   unsigned start = elt_func(elt_ptr, 0);
-   
-   //debug_printf("%s prim %d start %d count %d\n", __FUNCTION__, prim, start, count);
+   struct fetch_shade_emit *fse = (struct fetch_shade_emit *)middle;
+   struct draw_context *draw = fse->draw;
+   unsigned alloc_count = align(fetch_count, 4);
+   void *hw_verts;
    
-   split_prim_inplace(fse->prim, &first, &incr);
-
-   count -= (count - first) % incr; 
-
-   while (i + first <= count) {
-      int nr = MIN2( count - i, 1024 );
-
-      /* snap to prim boundary 
-       */
-      nr -= (nr - first) % incr; 
+   /* XXX: need to flush to get prim_vbuf.c to release its allocation?? 
+    */
+   draw_do_flush( draw, DRAW_FLUSH_BACKEND );
 
-      if (!do_draw( fse, start + i, nr )) {
-         assert(0);
-         return ;
+   hw_verts = draw->render->allocate_vertices( draw->render,
+                                               (ushort)fse->key.output_stride,
+                                               (ushort)alloc_count );
+   if (!hw_verts) {
+      assert(0);
+      return;
+   }
+         
+                                       
+   /* Single routine to fetch vertices, run shader and emit HW verts.
+    */
+   fse->active->run_elts( fse->active, 
+                          fetch_elts,
+                          fetch_count,
+                          hw_verts );
+
+   draw->render->draw( draw->render, 
+                       draw_elts, 
+                       draw_count );
+
+   if (0) {
+      unsigned i;
+      for (i = 0; i < fetch_count; i++) {
+         debug_printf("\n\n%s vertex %d:\n", __FUNCTION__, i);
+         draw_dump_emitted_vertex( fse->vinfo, 
+                                   (const uint8_t *)hw_verts + 
+                                   fse->key.output_stride * i );
       }
-
-      /* increment allowing for repeated vertices
-       */
-      i += nr - (first - incr);
    }
 
-   //return TRUE;
+
+   draw->render->release_vertices( draw->render, 
+                                   hw_verts, 
+                                   fse->key.output_stride, 
+                                   fetch_count );
+
 }
 
 
-static void fse_finish( struct draw_pt_front_end *frontend )
+static void fse_finish( struct draw_pt_middle_end *middle )
 {
 }
 
 
 static void
-fse_destroy( struct draw_pt_front_end *frontend ) 
+fse_destroy( struct draw_pt_middle_end *middle ) 
 {
-   FREE(frontend);
+   FREE(middle);
 }
 
-struct draw_pt_front_end *draw_pt_fetch_shade_emit( struct draw_context *draw )
+struct draw_pt_middle_end *draw_pt_middle_fse( struct draw_context *draw )
 {
    struct fetch_shade_emit *fse = CALLOC_STRUCT(fetch_shade_emit);
    if (!fse)
@@ -640,75 +329,10 @@ struct draw_pt_front_end *draw_pt_fetch_shade_emit( struct draw_context *draw )
 
    fse->base.prepare = fse_prepare;
    fse->base.run = fse_run;
+   fse->base.run_linear = fse_run_linear;
    fse->base.finish = fse_finish;
    fse->base.destroy = fse_destroy;
    fse->draw = draw;
 
-   fse->shader[0].run_linear = fetch_xyz_rgb_st;
-   fse->shader[0].key.nr_elements = 3;
-   fse->shader[0].key.output_stride = 12 * sizeof(float);
-
-   fse->shader[0].key.element[0].input_format = PIPE_FORMAT_R32G32B32_FLOAT;
-   fse->shader[0].key.element[0].input_buffer = 0; 
-   fse->shader[0].key.element[0].input_offset = 0; 
-   fse->shader[0].key.element[0].output_format = PIPE_FORMAT_R32G32B32A32_FLOAT;
-   fse->shader[0].key.element[0].output_offset = 0; 
-
-   fse->shader[0].key.element[1].input_format = PIPE_FORMAT_R32G32B32_FLOAT;
-   fse->shader[0].key.element[1].input_buffer = 0; 
-   fse->shader[0].key.element[1].input_offset = 0; 
-   fse->shader[0].key.element[1].output_format = PIPE_FORMAT_R32G32B32A32_FLOAT;
-   fse->shader[0].key.element[1].output_offset = 16; 
-
-   fse->shader[0].key.element[1].input_format = PIPE_FORMAT_R32G32_FLOAT;
-   fse->shader[0].key.element[1].input_buffer = 0; 
-   fse->shader[0].key.element[1].input_offset = 0; 
-   fse->shader[0].key.element[1].output_format = PIPE_FORMAT_R32G32B32A32_FLOAT;
-   fse->shader[0].key.element[1].output_offset = 32; 
-
-   fse->shader[1].run_linear = fetch_xyz_rgb;
-   fse->shader[1].key.nr_elements = 2;
-   fse->shader[1].key.output_stride = 8 * sizeof(float);
-
-   fse->shader[1].key.element[0].input_format = PIPE_FORMAT_R32G32B32_FLOAT;
-   fse->shader[1].key.element[0].input_buffer = 0; 
-   fse->shader[1].key.element[0].input_offset = 0; 
-   fse->shader[1].key.element[0].output_format = PIPE_FORMAT_R32G32B32A32_FLOAT;
-   fse->shader[1].key.element[0].output_offset = 0; 
-
-   fse->shader[1].key.element[1].input_format = PIPE_FORMAT_R32G32B32_FLOAT;
-   fse->shader[1].key.element[1].input_buffer = 0; 
-   fse->shader[1].key.element[1].input_offset = 0; 
-   fse->shader[1].key.element[1].output_format = PIPE_FORMAT_R32G32B32A32_FLOAT;
-   fse->shader[1].key.element[1].output_offset = 16; 
-
-   fse->shader[2].run_linear = fetch_xyz_rgb_psiz;
-   fse->shader[2].key.nr_elements = 3;
-   fse->shader[2].key.output_stride = 9 * sizeof(float);
-
-   fse->shader[2].key.element[0].input_format = PIPE_FORMAT_R32G32B32_FLOAT;
-   fse->shader[2].key.element[0].input_buffer = 0; 
-   fse->shader[2].key.element[0].input_offset = 0; 
-   fse->shader[2].key.element[0].output_format = PIPE_FORMAT_R32G32B32A32_FLOAT;
-   fse->shader[2].key.element[0].output_offset = 0; 
-
-   fse->shader[2].key.element[1].input_format = PIPE_FORMAT_R32G32B32_FLOAT;
-   fse->shader[2].key.element[1].input_buffer = 0; 
-   fse->shader[2].key.element[1].input_offset = 0; 
-   fse->shader[2].key.element[1].output_format = PIPE_FORMAT_R32G32B32A32_FLOAT;
-   fse->shader[2].key.element[1].output_offset = 16; 
-
-   /* psize is special 
-    *    -- effectively add it here as another input!?! 
-    *    -- who knows how to add it as a buffer?
-    */
-   fse->shader[2].key.element[2].input_format = PIPE_FORMAT_R32_FLOAT;
-   fse->shader[2].key.element[2].input_buffer = 0; 
-   fse->shader[2].key.element[2].input_offset = 0; 
-   fse->shader[2].key.element[2].output_format = PIPE_FORMAT_R32_FLOAT;
-   fse->shader[2].key.element[2].output_offset = 32; 
-
-   fse->nr_shaders = 3;
-
    return &fse->base;
 }