draw_pipe_clip.c revision cdd38d487a311e6c71b76382d428f5dc26caf067
18e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell/**************************************************************************
28e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell *
38e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * Copyright 2007 Tungsten Graphics, Inc., Cedar Park, Texas.
48e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * All Rights Reserved.
58e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell *
68e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * Permission is hereby granted, free of charge, to any person obtaining a
78e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * copy of this software and associated documentation files (the
88e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * "Software"), to deal in the Software without restriction, including
98e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * without limitation the rights to use, copy, modify, merge, publish,
108e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * distribute, sub license, and/or sell copies of the Software, and to
118e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * permit persons to whom the Software is furnished to do so, subject to
128e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * the following conditions:
138e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell *
148e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * The above copyright notice and this permission notice (including the
158e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * next paragraph) shall be included in all copies or substantial portions
168e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * of the Software.
178e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell *
188e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
198e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
208e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
218e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * IN NO EVENT SHALL TUNGSTEN GRAPHICS AND/OR ITS SUPPLIERS BE LIABLE FOR
228e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
238e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
248e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
258e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell *
268e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell **************************************************************************/
278e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
285b06424a1507dadad8832d557e79f68a3b68b9c2Brian/**
295b06424a1507dadad8832d557e79f68a3b68b9c2Brian * \brief  Clipping stage
305b06424a1507dadad8832d557e79f68a3b68b9c2Brian *
315b06424a1507dadad8832d557e79f68a3b68b9c2Brian * \author  Keith Whitwell <keith@tungstengraphics.com>
328e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell */
338e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
345b06424a1507dadad8832d557e79f68a3b68b9c2Brian
353fc926f3740da9ec27853d158243055f3cb43d43Brian#include "pipe/p_util.h"
367668e53c8c64570d66a626c96302a953164f319eBrian#include "draw_context.h"
37279ffe3f163fd6a5e7bfa108db14c81acbb06eceBrian#include "draw_private.h"
388e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
397668e53c8c64570d66a626c96302a953164f319eBrian
403fc926f3740da9ec27853d158243055f3cb43d43Brian#ifndef IS_NEGATIVE
413fc926f3740da9ec27853d158243055f3cb43d43Brian#define IS_NEGATIVE(X) ((X) < 0.0)
423fc926f3740da9ec27853d158243055f3cb43d43Brian#endif
433fc926f3740da9ec27853d158243055f3cb43d43Brian
443fc926f3740da9ec27853d158243055f3cb43d43Brian#ifndef DIFFERENT_SIGNS
453fc926f3740da9ec27853d158243055f3cb43d43Brian#define DIFFERENT_SIGNS(x, y) ((x) * (y) <= 0.0F && (x) - (y) != 0.0F)
463fc926f3740da9ec27853d158243055f3cb43d43Brian#endif
473fc926f3740da9ec27853d158243055f3cb43d43Brian
483fc926f3740da9ec27853d158243055f3cb43d43Brian#ifndef MAX_CLIPPED_VERTICES
493fc926f3740da9ec27853d158243055f3cb43d43Brian#define MAX_CLIPPED_VERTICES ((2 * (6 + PIPE_MAX_CLIP_PLANES))+1)
503fc926f3740da9ec27853d158243055f3cb43d43Brian#endif
513fc926f3740da9ec27853d158243055f3cb43d43Brian
528e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
53f9a77a3080598d03c484fa5d04c213b8a06d43d3Brian
548e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwellstruct clipper {
55ea470eec86715cd2bc9aa86d36e6ea803d0d4017Brian   struct draw_stage stage;      /**< base class */
568e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
573fc926f3740da9ec27853d158243055f3cb43d43Brian   float (*plane)[4];
588e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell};
598e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
60279ffe3f163fd6a5e7bfa108db14c81acbb06eceBrian
618e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell/* This is a bit confusing:
628e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell */
63ea470eec86715cd2bc9aa86d36e6ea803d0d4017Brianstatic INLINE struct clipper *clipper_stage( struct draw_stage *stage )
648e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
658e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   return (struct clipper *)stage;
668e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
678e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
688e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
698e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell#define LINTERP(T, OUT, IN) ((OUT) + (T) * ((IN) - (OUT)))
708e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
718e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
728e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell/* All attributes are float[4], so this is easy:
738e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell */
743fc926f3740da9ec27853d158243055f3cb43d43Brianstatic void interp_attr( float *fdst,
753fc926f3740da9ec27853d158243055f3cb43d43Brian			 float t,
763fc926f3740da9ec27853d158243055f3cb43d43Brian			 const float *fin,
773fc926f3740da9ec27853d158243055f3cb43d43Brian			 const float *fout )
788e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
798e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   fdst[0] = LINTERP( t, fout[0], fin[0] );
808e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   fdst[1] = LINTERP( t, fout[1], fin[1] );
818e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   fdst[2] = LINTERP( t, fout[2], fin[2] );
828e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   fdst[3] = LINTERP( t, fout[3], fin[3] );
838e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
848e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
858e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
868e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
878e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
888e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell/* Interpolate between two vertices to produce a third.
898e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell */
90a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brianstatic void interp( const struct clipper *clip,
918e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell		    struct vertex_header *dst,
923fc926f3740da9ec27853d158243055f3cb43d43Brian		    float t,
938e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell		    const struct vertex_header *out,
948e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell		    const struct vertex_header *in )
958e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
96d3eb25c575464bed7dbfc8be4717d85cb2928ec1Brian   const unsigned nr_attrs = clip->stage.draw->vertex_info.num_attribs;
973fc926f3740da9ec27853d158243055f3cb43d43Brian   unsigned j;
988e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
998e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   /* Vertex header.
1008e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell    */
1018e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   {
1028e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      dst->clipmask = 0;
1038e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      dst->edgeflag = 0;
1048e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      dst->pad = 0;
105a37e0daeb97bb36ba10038b12a909e22e08b52c4Keith Whitwell      dst->vertex_id = 0;
1068e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
1078e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1088e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   /* Clip coordinates:  interpolate normally
1098e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell    */
1108e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   {
1118e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      interp_attr(dst->clip, t, in->clip, out->clip);
1128e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
1138e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1148e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   /* Do the projective divide and insert window coordinates:
1158e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell    */
1168e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   {
1173fc926f3740da9ec27853d158243055f3cb43d43Brian      const float *pos = dst->clip;
1183fc926f3740da9ec27853d158243055f3cb43d43Brian      const float *scale = clip->stage.draw->viewport.scale;
1193fc926f3740da9ec27853d158243055f3cb43d43Brian      const float *trans = clip->stage.draw->viewport.translate;
120eb51761b825018bf89080855d0fa3fcb84b9c215michal      const float oow = 1.0f / pos[3];
1218e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1228e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      dst->data[0][0] = pos[0] * oow * scale[0] + trans[0];
1238e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      dst->data[0][1] = pos[1] * oow * scale[1] + trans[1];
1248e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      dst->data[0][2] = pos[2] * oow * scale[2] + trans[2];
1258e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      dst->data[0][3] = oow;
1268e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
1278e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1288e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   /* Other attributes
1292bf4a500de24347476ce96cdd48d68ddeecbb019Brian    * Note: start at 1 to skip winpos (data[0]) since we just computed
1302bf4a500de24347476ce96cdd48d68ddeecbb019Brian    * it above.
1312bf4a500de24347476ce96cdd48d68ddeecbb019Brian    * Subtract two from nr_attrs since the first two attribs (always
1322bf4a500de24347476ce96cdd48d68ddeecbb019Brian    * VF_ATTRIB_VERTEX_HEADER and VF_ATTRIB_CLIP_POS, see
1332bf4a500de24347476ce96cdd48d68ddeecbb019Brian    * draw_set_vertex_attributes()) are in the vertex_header struct,
1342bf4a500de24347476ce96cdd48d68ddeecbb019Brian    * not in the data[] array.
1358e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell    */
1362bf4a500de24347476ce96cdd48d68ddeecbb019Brian   for (j = 1; j < nr_attrs - 2; j++) {
1378e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      interp_attr(dst->data[j], t, in->data[j], out->data[j]);
1388e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
1398e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
1408e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1418e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1428e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1433fc926f3740da9ec27853d158243055f3cb43d43Brianstatic INLINE float dot4( const float *a,
1443fc926f3740da9ec27853d158243055f3cb43d43Brian			    const float *b )
1458e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
1463fc926f3740da9ec27853d158243055f3cb43d43Brian   float result = (a[0]*b[0] +
1478e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell		     a[1]*b[1] +
1488e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell		     a[2]*b[2] +
1498e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell		     a[3]*b[3]);
1508e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1518e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   return result;
1528e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
1538e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1548e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1558e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell#if 0
156ea470eec86715cd2bc9aa86d36e6ea803d0d4017Brianstatic INLINE void do_tri( struct draw_stage *next,
1578e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell			   struct prim_header *header )
1588e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
1593fc926f3740da9ec27853d158243055f3cb43d43Brian   unsigned i;
1608e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   for (i = 0; i < 3; i++) {
1613fc926f3740da9ec27853d158243055f3cb43d43Brian      float *ndc = header->v[i]->data[0];
1628e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      _mesa_printf("ndc %f %f %f\n", ndc[0], ndc[1], ndc[2]);
1638e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      assert(ndc[0] >= -1 && ndc[0] <= 641);
1648e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      assert(ndc[1] >= 30 && ndc[1] <= 481);
1658e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
1668e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   _mesa_printf("\n");
1678e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   next->tri(next, header);
1688e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
1698e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell#endif
1708e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1718e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
172ea470eec86715cd2bc9aa86d36e6ea803d0d4017Brianstatic void emit_poly( struct draw_stage *stage,
1738e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell		       struct vertex_header **inlist,
174aaf03b94861cbf5a602863e4542dd1c2e54ba365Brian		       unsigned n,
175aaf03b94861cbf5a602863e4542dd1c2e54ba365Brian                       const struct prim_header *origPrim)
1768e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
1778e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   struct prim_header header;
1783fc926f3740da9ec27853d158243055f3cb43d43Brian   unsigned i;
1798e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
180aaf03b94861cbf5a602863e4542dd1c2e54ba365Brian   /* later stages may need the determinant, but only the sign matters */
181aaf03b94861cbf5a602863e4542dd1c2e54ba365Brian   header.det = origPrim->det;
182aaf03b94861cbf5a602863e4542dd1c2e54ba365Brian
1838e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   for (i = 2; i < n; i++) {
1848e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      header.v[0] = inlist[0];
1858e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      header.v[1] = inlist[i-1];
1868e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      header.v[2] = inlist[i];
1878e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1888e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      {
1893fc926f3740da9ec27853d158243055f3cb43d43Brian	 unsigned tmp0 = header.v[0]->edgeflag;
1903fc926f3740da9ec27853d158243055f3cb43d43Brian	 unsigned tmp2 = header.v[2]->edgeflag;
1918e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
1928e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 if (i != 2)   header.v[0]->edgeflag = 0;
1938e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 if (i != n-1) header.v[2]->edgeflag = 0;
1948e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
195aaf03b94861cbf5a602863e4542dd1c2e54ba365Brian         header.edgeflags = ((header.v[0]->edgeflag << 0) |
196aaf03b94861cbf5a602863e4542dd1c2e54ba365Brian                             (header.v[1]->edgeflag << 1) |
197aaf03b94861cbf5a602863e4542dd1c2e54ba365Brian                             (header.v[2]->edgeflag << 2));
198aaf03b94861cbf5a602863e4542dd1c2e54ba365Brian
1998e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 stage->next->tri( stage->next, &header );
2008e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2018e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 header.v[0]->edgeflag = tmp0;
2028e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 header.v[2]->edgeflag = tmp2;
2038e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      }
2048e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
2058e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
2068e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2078e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2088e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell#if 0
209ea470eec86715cd2bc9aa86d36e6ea803d0d4017Brianstatic void emit_poly( struct draw_stage *stage )
2108e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
2113fc926f3740da9ec27853d158243055f3cb43d43Brian   unsigned i;
2128e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2138e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   for (i = 2; i < n; i++) {
2148e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      header->v[0] = inlist[0];
2158e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      header->v[1] = inlist[i-1];
2168e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      header->v[2] = inlist[i];
2178e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2188e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      stage->next->tri( stage->next, header );
2198e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
2208e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
2218e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell#endif
2228e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2238e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2248e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell/* Clip a triangle against the viewport and user clip planes.
2258e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell */
2268e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwellstatic void
227ea470eec86715cd2bc9aa86d36e6ea803d0d4017Briando_clip_tri( struct draw_stage *stage,
2288e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	     struct prim_header *header,
2293fc926f3740da9ec27853d158243055f3cb43d43Brian	     unsigned clipmask )
2308e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
2318e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   struct clipper *clipper = clipper_stage( stage );
2328e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   struct vertex_header *a[MAX_CLIPPED_VERTICES];
2338e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   struct vertex_header *b[MAX_CLIPPED_VERTICES];
2348e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   struct vertex_header **inlist = a;
2358e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   struct vertex_header **outlist = b;
2363fc926f3740da9ec27853d158243055f3cb43d43Brian   unsigned tmpnr = 0;
2373fc926f3740da9ec27853d158243055f3cb43d43Brian   unsigned n = 3;
2383fc926f3740da9ec27853d158243055f3cb43d43Brian   unsigned i;
2398e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2408e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   inlist[0] = header->v[0];
2418e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   inlist[1] = header->v[1];
2428e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   inlist[2] = header->v[2];
2438e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2448e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   while (clipmask && n >= 3) {
245f9a77a3080598d03c484fa5d04c213b8a06d43d3Brian      const unsigned plane_idx = ffs(clipmask)-1;
2463fc926f3740da9ec27853d158243055f3cb43d43Brian      const float *plane = clipper->plane[plane_idx];
2478e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      struct vertex_header *vert_prev = inlist[0];
2483fc926f3740da9ec27853d158243055f3cb43d43Brian      float dp_prev = dot4( vert_prev->clip, plane );
2493fc926f3740da9ec27853d158243055f3cb43d43Brian      unsigned outcount = 0;
2508e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2518e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      clipmask &= ~(1<<plane_idx);
2528e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2538e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      inlist[n] = inlist[0]; /* prevent rotation of vertices */
2548e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2558e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      for (i = 1; i <= n; i++) {
2568e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 struct vertex_header *vert = inlist[i];
2578e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2583fc926f3740da9ec27853d158243055f3cb43d43Brian	 float dp = dot4( vert->clip, plane );
2598e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2608e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 if (!IS_NEGATIVE(dp_prev)) {
2618e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	    outlist[outcount++] = vert_prev;
2628e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 }
2638e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2648e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 if (DIFFERENT_SIGNS(dp, dp_prev)) {
2658e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	    struct vertex_header *new_vert = clipper->stage.tmp[tmpnr++];
2668e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	    outlist[outcount++] = new_vert;
2678e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2688e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	    if (IS_NEGATIVE(dp)) {
2698e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	       /* Going out of bounds.  Avoid division by zero as we
2708e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell		* know dp != dp_prev from DIFFERENT_SIGNS, above.
2718e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell		*/
2723fc926f3740da9ec27853d158243055f3cb43d43Brian	       float t = dp / (dp - dp_prev);
2738e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	       interp( clipper, new_vert, t, vert, vert_prev );
2748e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2758e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	       /* Force edgeflag true in this case:
2768e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell		*/
2778e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	       new_vert->edgeflag = 1;
2788e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	    } else {
2798e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	       /* Coming back in.
2808e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell		*/
2813fc926f3740da9ec27853d158243055f3cb43d43Brian	       float t = dp_prev / (dp_prev - dp);
2828e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	       interp( clipper, new_vert, t, vert_prev, vert );
2838e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2848e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	       /* Copy starting vert's edgeflag:
2858e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell		*/
2868e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	       new_vert->edgeflag = vert_prev->edgeflag;
2878e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	    }
2888e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 }
2898e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2908e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 vert_prev = vert;
2918e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 dp_prev = dp;
2928e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      }
2938e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
2948e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      {
2958e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 struct vertex_header **tmp = inlist;
2968e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 inlist = outlist;
2978e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 outlist = tmp;
2988e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 n = outcount;
2998e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      }
3008e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
3018e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
3028e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   /* Emit the polygon as triangles to the setup stage:
3038e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell    */
3048e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   if (n >= 3)
305aaf03b94861cbf5a602863e4542dd1c2e54ba365Brian      emit_poly( stage, inlist, n, header );
3068e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
3078e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
3088e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
3098e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell/* Clip a line against the viewport and user clip planes.
3108e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell */
3118e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwellstatic void
312ea470eec86715cd2bc9aa86d36e6ea803d0d4017Briando_clip_line( struct draw_stage *stage,
3138e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	      struct prim_header *header,
3143fc926f3740da9ec27853d158243055f3cb43d43Brian	      unsigned clipmask )
3158e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
316a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian   const struct clipper *clipper = clipper_stage( stage );
3178e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   struct vertex_header *v0 = header->v[0];
3188e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   struct vertex_header *v1 = header->v[1];
3193fc926f3740da9ec27853d158243055f3cb43d43Brian   const float *pos0 = v0->clip;
3203fc926f3740da9ec27853d158243055f3cb43d43Brian   const float *pos1 = v1->clip;
321f9a77a3080598d03c484fa5d04c213b8a06d43d3Brian   float t0 = 0.0F;
322f9a77a3080598d03c484fa5d04c213b8a06d43d3Brian   float t1 = 0.0F;
323a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian   struct prim_header newprim;
3248e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
3258e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   while (clipmask) {
3263fc926f3740da9ec27853d158243055f3cb43d43Brian      const unsigned plane_idx = ffs(clipmask)-1;
3273fc926f3740da9ec27853d158243055f3cb43d43Brian      const float *plane = clipper->plane[plane_idx];
3283fc926f3740da9ec27853d158243055f3cb43d43Brian      const float dp0 = dot4( pos0, plane );
3293fc926f3740da9ec27853d158243055f3cb43d43Brian      const float dp1 = dot4( pos1, plane );
3308e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
331f9a77a3080598d03c484fa5d04c213b8a06d43d3Brian      if (dp1 < 0.0F) {
3323fc926f3740da9ec27853d158243055f3cb43d43Brian	 float t = dp1 / (dp1 - dp0);
3335b06424a1507dadad8832d557e79f68a3b68b9c2Brian         t1 = MAX2(t1, t);
3348e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      }
3358e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
336f9a77a3080598d03c484fa5d04c213b8a06d43d3Brian      if (dp0 < 0.0F) {
3373fc926f3740da9ec27853d158243055f3cb43d43Brian	 float t = dp0 / (dp0 - dp1);
3385b06424a1507dadad8832d557e79f68a3b68b9c2Brian         t0 = MAX2(t0, t);
3398e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      }
3408e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
341f9a77a3080598d03c484fa5d04c213b8a06d43d3Brian      if (t0 + t1 >= 1.0F)
3428e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	 return; /* discard */
343a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian
344a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian      clipmask &= ~(1 << plane_idx);  /* turn off this plane's bit */
3458e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
3468e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
3478e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   if (v0->clipmask) {
3488e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      interp( clipper, stage->tmp[0], t0, v0, v1 );
349a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian      newprim.v[0] = stage->tmp[0];
350a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian   }
351a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian   else {
352a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian      newprim.v[0] = v0;
3538e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
3548e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
3558e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   if (v1->clipmask) {
3568e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      interp( clipper, stage->tmp[1], t1, v1, v0 );
357a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian      newprim.v[1] = stage->tmp[1];
358a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian   }
359a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian   else {
360a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian      newprim.v[1] = v1;
3618e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
3628e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
363a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian   stage->next->line( stage->next, &newprim );
3648e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
3658e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
3668e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
367ea470eec86715cd2bc9aa86d36e6ea803d0d4017Brianstatic void clip_begin( struct draw_stage *stage )
3688e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
3692bf4a500de24347476ce96cdd48d68ddeecbb019Brian   /* sanity checks.  If these fail, review the clip/interp code! */
370d3eb25c575464bed7dbfc8be4717d85cb2928ec1Brian   assert(stage->draw->vertex_info.num_attribs >= 3);
371086734502a614e7778533018846ee66a66df9821Brian#if 0
372d8b16d416de95daa4f0ede9b839bdbf0fa6bf1b1Brian   assert(stage->draw->vertex_info.slot_to_attrib[0] == TGSI_ATTRIB_VERTEX_HEADER);
373d8b16d416de95daa4f0ede9b839bdbf0fa6bf1b1Brian   assert(stage->draw->vertex_info.slot_to_attrib[1] == TGSI_ATTRIB_CLIP_POS);
374086734502a614e7778533018846ee66a66df9821Brian#endif
3752bf4a500de24347476ce96cdd48d68ddeecbb019Brian
3768e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   stage->next->begin( stage->next );
3778e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
378a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian
379a49a23efc5e320d8c9aa6f4f39be855632aa5cb8Brian
3808e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwellstatic void
381ea470eec86715cd2bc9aa86d36e6ea803d0d4017Brianclip_point( struct draw_stage *stage,
3828e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	    struct prim_header *header )
3838e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
384cdd38d487a311e6c71b76382d428f5dc26caf067Zack Rusin   if (header->v[0]->clipmask == 0)
3858e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      stage->next->point( stage->next, header );
3868e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
3878e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
3888e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
3898e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwellstatic void
390ea470eec86715cd2bc9aa86d36e6ea803d0d4017Brianclip_line( struct draw_stage *stage,
3918e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	   struct prim_header *header )
3928e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
3933fc926f3740da9ec27853d158243055f3cb43d43Brian   unsigned clipmask = (header->v[0]->clipmask |
394f9a77a3080598d03c484fa5d04c213b8a06d43d3Brian                        header->v[1]->clipmask);
3958e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
3968e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   if (clipmask == 0) {
397279ffe3f163fd6a5e7bfa108db14c81acbb06eceBrian      /* no clipping needed */
3988e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      stage->next->line( stage->next, header );
3998e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
400cdd38d487a311e6c71b76382d428f5dc26caf067Zack Rusin   else if ((header->v[0]->clipmask &
401cdd38d487a311e6c71b76382d428f5dc26caf067Zack Rusin             header->v[1]->clipmask) == 0) {
4028e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      do_clip_line(stage, header, clipmask);
4038e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
404f9a77a3080598d03c484fa5d04c213b8a06d43d3Brian   /* else, totally clipped */
4058e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
4068e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
4078e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
4088e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwellstatic void
409ea470eec86715cd2bc9aa86d36e6ea803d0d4017Brianclip_tri( struct draw_stage *stage,
4108e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell	  struct prim_header *header )
4118e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
4123fc926f3740da9ec27853d158243055f3cb43d43Brian   unsigned clipmask = (header->v[0]->clipmask |
413f9a77a3080598d03c484fa5d04c213b8a06d43d3Brian                        header->v[1]->clipmask |
414f9a77a3080598d03c484fa5d04c213b8a06d43d3Brian                        header->v[2]->clipmask);
4158e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
4168e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   if (clipmask == 0) {
417279ffe3f163fd6a5e7bfa108db14c81acbb06eceBrian      /* no clipping needed */
4188e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      stage->next->tri( stage->next, header );
4198e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
420cdd38d487a311e6c71b76382d428f5dc26caf067Zack Rusin   else if ((header->v[0]->clipmask &
421cdd38d487a311e6c71b76382d428f5dc26caf067Zack Rusin             header->v[1]->clipmask &
422cdd38d487a311e6c71b76382d428f5dc26caf067Zack Rusin             header->v[2]->clipmask) == 0) {
4238e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell      do_clip_tri(stage, header, clipmask);
4248e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   }
4258e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
4268e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
427279ffe3f163fd6a5e7bfa108db14c81acbb06eceBrian
428ea470eec86715cd2bc9aa86d36e6ea803d0d4017Brianstatic void clip_end( struct draw_stage *stage )
4298e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
4308e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   stage->next->end( stage->next );
4318e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
4328e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
4338e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
4340360b49afbcd839f99ba0745d01cf9dc5be4d122Brianstatic void clip_reset_stipple_counter( struct draw_stage *stage )
4350360b49afbcd839f99ba0745d01cf9dc5be4d122Brian{
4360360b49afbcd839f99ba0745d01cf9dc5be4d122Brian   stage->next->reset_stipple_counter( stage->next );
4370360b49afbcd839f99ba0745d01cf9dc5be4d122Brian}
4380360b49afbcd839f99ba0745d01cf9dc5be4d122Brian
4390360b49afbcd839f99ba0745d01cf9dc5be4d122Brian
440279ffe3f163fd6a5e7bfa108db14c81acbb06eceBrian/**
441279ffe3f163fd6a5e7bfa108db14c81acbb06eceBrian * Allocate a new clipper stage.
442279ffe3f163fd6a5e7bfa108db14c81acbb06eceBrian * \return pointer to new stage object
443279ffe3f163fd6a5e7bfa108db14c81acbb06eceBrian */
444ea470eec86715cd2bc9aa86d36e6ea803d0d4017Brianstruct draw_stage *draw_clip_stage( struct draw_context *draw )
4458e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell{
4468e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   struct clipper *clipper = CALLOC_STRUCT(clipper);
4478e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
448ea470eec86715cd2bc9aa86d36e6ea803d0d4017Brian   draw_alloc_tmps( &clipper->stage, MAX_CLIPPED_VERTICES );
4498e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
450279ffe3f163fd6a5e7bfa108db14c81acbb06eceBrian   clipper->stage.draw = draw;
4518e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   clipper->stage.begin = clip_begin;
4528e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   clipper->stage.point = clip_point;
4538e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   clipper->stage.line = clip_line;
4548e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   clipper->stage.tri = clip_tri;
4558e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   clipper->stage.end = clip_end;
4560360b49afbcd839f99ba0745d01cf9dc5be4d122Brian   clipper->stage.reset_stipple_counter = clip_reset_stipple_counter;
4578e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell
458279ffe3f163fd6a5e7bfa108db14c81acbb06eceBrian   clipper->plane = draw->plane;
459279ffe3f163fd6a5e7bfa108db14c81acbb06eceBrian
4608e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell   return &clipper->stage;
4618e4a95a93d15a6707a29454cd47e10b08314cda2Keith Whitwell}
462