Tizen 2.0 Release
[profile/ivi/osmesa.git] / src / mesa / drivers / dri / radeon / radeon_maos_verts.c
1 /**************************************************************************
2
3 Copyright 2000, 2001 ATI Technologies Inc., Ontario, Canada, and
4                      Tungsten Graphics Inc., Austin, Texas.
5
6 All Rights Reserved.
7
8 Permission is hereby granted, free of charge, to any person obtaining
9 a copy of this software and associated documentation files (the
10 "Software"), to deal in the Software without restriction, including
11 without limitation the rights to use, copy, modify, merge, publish,
12 distribute, sublicense, and/or sell copies of the Software, and to
13 permit persons to whom the Software is furnished to do so, subject to
14 the following conditions:
15
16 The above copyright notice and this permission notice (including the
17 next paragraph) shall be included in all copies or substantial
18 portions of the Software.
19
20 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
21 EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
22 MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
23 IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE
24 LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
25 OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
26 WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
27
28 **************************************************************************/
29
30 /*
31  * Authors:
32  *   Keith Whitwell <keith@tungstengraphics.com>
33  */
34
35 #include "main/glheader.h"
36 #include "main/imports.h"
37 #include "main/mtypes.h"
38
39 #include "vbo/vbo.h"
40 #include "math/m_translate.h"
41 #include "tnl/tnl.h"
42 #include "tnl/t_pipeline.h"
43 #include "radeon_context.h"
44 #include "radeon_state.h"
45 #include "radeon_ioctl.h"
46 #include "radeon_tex.h"
47 #include "radeon_tcl.h"
48 #include "radeon_swtcl.h"
49 #include "radeon_maos.h"
50
51
52 #define RADEON_TCL_MAX_SETUP 19
53
54 union emit_union { float f; GLuint ui; radeon_color_t rgba; };
55
56 static struct {
57    void   (*emit)( struct gl_context *, GLuint, GLuint, void * );
58    GLuint vertex_size;
59    GLuint vertex_format;
60 } setup_tab[RADEON_TCL_MAX_SETUP];
61
62 #define DO_W    (IND & RADEON_CP_VC_FRMT_W0)
63 #define DO_RGBA (IND & RADEON_CP_VC_FRMT_PKCOLOR)
64 #define DO_SPEC_OR_FOG (IND & RADEON_CP_VC_FRMT_PKSPEC)
65 #define DO_SPEC ((IND & RADEON_CP_VC_FRMT_PKSPEC) && \
66                  (ctx->_TriangleCaps & DD_SEPARATE_SPECULAR))
67 #define DO_FOG  ((IND & RADEON_CP_VC_FRMT_PKSPEC) && ctx->Fog.Enabled && \
68                  (ctx->Fog.FogCoordinateSource == GL_FOG_COORD))
69 #define DO_TEX0 (IND & RADEON_CP_VC_FRMT_ST0)
70 #define DO_TEX1 (IND & RADEON_CP_VC_FRMT_ST1)
71 #define DO_TEX2 (IND & RADEON_CP_VC_FRMT_ST2)
72 #define DO_PTEX (IND & RADEON_CP_VC_FRMT_Q0)
73 #define DO_NORM (IND & RADEON_CP_VC_FRMT_N0)
74
75 #define DO_TEX3 0
76
77 #define GET_TEXSOURCE(n)  n
78
79 /***********************************************************************
80  *             Generate vertex emit functions               *
81  ***********************************************************************/
82
83
84 /* Defined in order of increasing vertex size:
85  */
86 #define IDX 0
87 #define IND (RADEON_CP_VC_FRMT_XY|              \
88              RADEON_CP_VC_FRMT_Z|               \
89              RADEON_CP_VC_FRMT_PKCOLOR)
90 #define TAG(x) x##_rgba
91 #include "radeon_maos_vbtmp.h"
92
93 #define IDX 1
94 #define IND (RADEON_CP_VC_FRMT_XY|              \
95              RADEON_CP_VC_FRMT_Z|               \
96              RADEON_CP_VC_FRMT_N0)
97 #define TAG(x) x##_n
98 #include "radeon_maos_vbtmp.h"
99
100 #define IDX 2
101 #define IND (RADEON_CP_VC_FRMT_XY|              \
102              RADEON_CP_VC_FRMT_Z|               \
103              RADEON_CP_VC_FRMT_PKCOLOR|         \
104              RADEON_CP_VC_FRMT_ST0)
105 #define TAG(x) x##_rgba_st
106 #include "radeon_maos_vbtmp.h"
107
108 #define IDX 3
109 #define IND (RADEON_CP_VC_FRMT_XY|              \
110              RADEON_CP_VC_FRMT_Z|               \
111              RADEON_CP_VC_FRMT_PKCOLOR|         \
112              RADEON_CP_VC_FRMT_N0)
113 #define TAG(x) x##_rgba_n
114 #include "radeon_maos_vbtmp.h"
115
116 #define IDX 4
117 #define IND (RADEON_CP_VC_FRMT_XY|              \
118              RADEON_CP_VC_FRMT_Z|               \
119              RADEON_CP_VC_FRMT_ST0|             \
120              RADEON_CP_VC_FRMT_N0)
121 #define TAG(x) x##_st_n
122 #include "radeon_maos_vbtmp.h"
123
124 #define IDX 5
125 #define IND (RADEON_CP_VC_FRMT_XY|              \
126              RADEON_CP_VC_FRMT_Z|               \
127              RADEON_CP_VC_FRMT_PKCOLOR|         \
128              RADEON_CP_VC_FRMT_ST0|             \
129              RADEON_CP_VC_FRMT_ST1)
130 #define TAG(x) x##_rgba_st_st
131 #include "radeon_maos_vbtmp.h"
132
133 #define IDX 6
134 #define IND (RADEON_CP_VC_FRMT_XY|              \
135              RADEON_CP_VC_FRMT_Z|               \
136              RADEON_CP_VC_FRMT_PKCOLOR|         \
137              RADEON_CP_VC_FRMT_ST0|             \
138              RADEON_CP_VC_FRMT_N0)
139 #define TAG(x) x##_rgba_st_n
140 #include "radeon_maos_vbtmp.h"
141
142 #define IDX 7
143 #define IND (RADEON_CP_VC_FRMT_XY|              \
144              RADEON_CP_VC_FRMT_Z|               \
145              RADEON_CP_VC_FRMT_PKCOLOR|         \
146              RADEON_CP_VC_FRMT_PKSPEC|          \
147              RADEON_CP_VC_FRMT_ST0|             \
148              RADEON_CP_VC_FRMT_ST1)
149 #define TAG(x) x##_rgba_spec_st_st
150 #include "radeon_maos_vbtmp.h"
151
152 #define IDX 8
153 #define IND (RADEON_CP_VC_FRMT_XY|              \
154              RADEON_CP_VC_FRMT_Z|               \
155              RADEON_CP_VC_FRMT_ST0|             \
156              RADEON_CP_VC_FRMT_ST1|             \
157              RADEON_CP_VC_FRMT_N0)
158 #define TAG(x) x##_st_st_n
159 #include "radeon_maos_vbtmp.h"
160
161 #define IDX 9
162 #define IND (RADEON_CP_VC_FRMT_XY|              \
163              RADEON_CP_VC_FRMT_Z|               \
164              RADEON_CP_VC_FRMT_PKCOLOR|         \
165              RADEON_CP_VC_FRMT_PKSPEC|          \
166              RADEON_CP_VC_FRMT_ST0|             \
167              RADEON_CP_VC_FRMT_ST1|             \
168              RADEON_CP_VC_FRMT_N0)
169 #define TAG(x) x##_rgba_spec_st_st_n
170 #include "radeon_maos_vbtmp.h"
171
172 #define IDX 10
173 #define IND (RADEON_CP_VC_FRMT_XY|              \
174              RADEON_CP_VC_FRMT_Z|               \
175              RADEON_CP_VC_FRMT_PKCOLOR|         \
176              RADEON_CP_VC_FRMT_ST0|             \
177              RADEON_CP_VC_FRMT_Q0)
178 #define TAG(x) x##_rgba_stq
179 #include "radeon_maos_vbtmp.h"
180
181 #define IDX 11
182 #define IND (RADEON_CP_VC_FRMT_XY|              \
183              RADEON_CP_VC_FRMT_Z|               \
184              RADEON_CP_VC_FRMT_PKCOLOR|         \
185              RADEON_CP_VC_FRMT_ST1|             \
186              RADEON_CP_VC_FRMT_Q1|              \
187              RADEON_CP_VC_FRMT_ST0|             \
188              RADEON_CP_VC_FRMT_Q0)
189 #define TAG(x) x##_rgba_stq_stq
190 #include "radeon_maos_vbtmp.h"
191
192 #define IDX 12
193 #define IND (RADEON_CP_VC_FRMT_XY|              \
194              RADEON_CP_VC_FRMT_Z|               \
195              RADEON_CP_VC_FRMT_W0|              \
196              RADEON_CP_VC_FRMT_PKCOLOR|         \
197              RADEON_CP_VC_FRMT_PKSPEC|          \
198              RADEON_CP_VC_FRMT_ST0|             \
199              RADEON_CP_VC_FRMT_Q0|              \
200              RADEON_CP_VC_FRMT_ST1|             \
201              RADEON_CP_VC_FRMT_Q1|              \
202              RADEON_CP_VC_FRMT_N0)
203 #define TAG(x) x##_w_rgba_spec_stq_stq_n
204 #include "radeon_maos_vbtmp.h"
205
206 #define IDX 13
207 #define IND (RADEON_CP_VC_FRMT_XY|              \
208              RADEON_CP_VC_FRMT_Z|               \
209              RADEON_CP_VC_FRMT_PKCOLOR|         \
210              RADEON_CP_VC_FRMT_ST0|             \
211              RADEON_CP_VC_FRMT_ST1|             \
212              RADEON_CP_VC_FRMT_ST2)
213 #define TAG(x) x##_rgba_st_st_st
214 #include "radeon_maos_vbtmp.h"
215
216 #define IDX 14
217 #define IND (RADEON_CP_VC_FRMT_XY|              \
218              RADEON_CP_VC_FRMT_Z|               \
219              RADEON_CP_VC_FRMT_PKCOLOR|         \
220              RADEON_CP_VC_FRMT_PKSPEC|          \
221              RADEON_CP_VC_FRMT_ST0|             \
222              RADEON_CP_VC_FRMT_ST1|             \
223              RADEON_CP_VC_FRMT_ST2)
224 #define TAG(x) x##_rgba_spec_st_st_st
225 #include "radeon_maos_vbtmp.h"
226
227 #define IDX 15
228 #define IND (RADEON_CP_VC_FRMT_XY|              \
229              RADEON_CP_VC_FRMT_Z|               \
230              RADEON_CP_VC_FRMT_ST0|             \
231              RADEON_CP_VC_FRMT_ST1|             \
232              RADEON_CP_VC_FRMT_ST2|             \
233              RADEON_CP_VC_FRMT_N0)
234 #define TAG(x) x##_st_st_st_n
235 #include "radeon_maos_vbtmp.h"
236
237 #define IDX 16
238 #define IND (RADEON_CP_VC_FRMT_XY|              \
239              RADEON_CP_VC_FRMT_Z|               \
240              RADEON_CP_VC_FRMT_PKCOLOR|         \
241              RADEON_CP_VC_FRMT_PKSPEC|          \
242              RADEON_CP_VC_FRMT_ST0|             \
243              RADEON_CP_VC_FRMT_ST1|             \
244              RADEON_CP_VC_FRMT_ST2|             \
245              RADEON_CP_VC_FRMT_N0)
246 #define TAG(x) x##_rgba_spec_st_st_st_n
247 #include "radeon_maos_vbtmp.h"
248
249 #define IDX 17
250 #define IND (RADEON_CP_VC_FRMT_XY|              \
251              RADEON_CP_VC_FRMT_Z|               \
252              RADEON_CP_VC_FRMT_PKCOLOR|         \
253              RADEON_CP_VC_FRMT_ST0|             \
254              RADEON_CP_VC_FRMT_Q0|              \
255              RADEON_CP_VC_FRMT_ST1|             \
256              RADEON_CP_VC_FRMT_Q1|              \
257              RADEON_CP_VC_FRMT_ST2|             \
258              RADEON_CP_VC_FRMT_Q2)
259 #define TAG(x) x##_rgba_stq_stq_stq
260 #include "radeon_maos_vbtmp.h"
261
262 #define IDX 18
263 #define IND (RADEON_CP_VC_FRMT_XY|              \
264              RADEON_CP_VC_FRMT_Z|               \
265              RADEON_CP_VC_FRMT_W0|              \
266              RADEON_CP_VC_FRMT_PKCOLOR|         \
267              RADEON_CP_VC_FRMT_PKSPEC|          \
268              RADEON_CP_VC_FRMT_ST0|             \
269              RADEON_CP_VC_FRMT_Q0|              \
270              RADEON_CP_VC_FRMT_ST1|             \
271              RADEON_CP_VC_FRMT_Q1|              \
272              RADEON_CP_VC_FRMT_ST2|             \
273              RADEON_CP_VC_FRMT_Q2|              \
274              RADEON_CP_VC_FRMT_N0)
275 #define TAG(x) x##_w_rgba_spec_stq_stq_stq_n
276 #include "radeon_maos_vbtmp.h"
277
278
279
280
281 /***********************************************************************
282  *                         Initialization 
283  ***********************************************************************/
284
285
286 static void init_tcl_verts( void )
287 {
288    init_rgba();
289    init_n();
290    init_rgba_n();
291    init_rgba_st();
292    init_st_n();
293    init_rgba_st_st();
294    init_rgba_st_n();
295    init_rgba_spec_st_st();
296    init_st_st_n();
297    init_rgba_spec_st_st_n();
298    init_rgba_stq();
299    init_rgba_stq_stq();
300    init_w_rgba_spec_stq_stq_n();
301    init_rgba_st_st_st();
302    init_rgba_spec_st_st_st();
303    init_st_st_st_n();
304    init_rgba_spec_st_st_st_n();
305    init_rgba_stq_stq_stq();
306    init_w_rgba_spec_stq_stq_stq_n();
307 }
308
309
310 void radeonEmitArrays( struct gl_context *ctx, GLuint inputs )
311 {
312    r100ContextPtr rmesa = R100_CONTEXT(ctx);
313    struct vertex_buffer *VB = &TNL_CONTEXT(ctx)->vb;
314    GLuint req = 0;
315    GLuint unit;
316    GLuint vtx = (rmesa->hw.tcl.cmd[TCL_OUTPUT_VTXFMT] &
317                  ~(RADEON_TCL_VTX_Q0|RADEON_TCL_VTX_Q1|RADEON_TCL_VTX_Q2));
318    int i;
319    static int firsttime = 1;
320
321    if (firsttime) {
322       init_tcl_verts();
323       firsttime = 0;
324    }
325
326    if (1) {
327       req |= RADEON_CP_VC_FRMT_Z;
328       if (VB->AttribPtr[_TNL_ATTRIB_POS]->size == 4) {
329          req |= RADEON_CP_VC_FRMT_W0;
330       }
331    }
332
333    if (inputs & VERT_BIT_NORMAL) {
334       req |= RADEON_CP_VC_FRMT_N0;
335    }
336
337    if (inputs & VERT_BIT_COLOR0) {
338       req |= RADEON_CP_VC_FRMT_PKCOLOR;
339    }
340
341    if (inputs & (VERT_BIT_COLOR1|VERT_BIT_FOG)) {
342       req |= RADEON_CP_VC_FRMT_PKSPEC;
343    }
344
345    for (unit = 0; unit < ctx->Const.MaxTextureUnits; unit++) {
346       if (inputs & VERT_BIT_TEX(unit)) {
347          req |= RADEON_ST_BIT(unit);
348          /* assume we need the 3rd coord if texgen is active for r/q OR at least
349             3 coords are submitted. This may not be 100% correct */
350          if (VB->AttribPtr[_TNL_ATTRIB_TEX0 + unit]->size >= 3) {
351             req |= RADEON_Q_BIT(unit);
352             vtx |= RADEON_Q_BIT(unit);
353          }
354          if ( (ctx->Texture.Unit[unit].TexGenEnabled & (R_BIT | Q_BIT)) )
355             vtx |= RADEON_Q_BIT(unit);
356          else if ((VB->AttribPtr[_TNL_ATTRIB_TEX0 + unit]->size >= 3) &&
357                   ((ctx->Texture.Unit[unit]._ReallyEnabled & (TEXTURE_CUBE_BIT)) == 0)) {
358             GLuint swaptexmatcol = (VB->AttribPtr[_TNL_ATTRIB_TEX0 + unit]->size - 3);
359             if (((rmesa->NeedTexMatrix >> unit) & 1) &&
360                  (swaptexmatcol != ((rmesa->TexMatColSwap >> unit) & 1)))
361                radeonUploadTexMatrix( rmesa, unit, swaptexmatcol ) ;
362          }
363       }
364    }
365
366    if (vtx != rmesa->hw.tcl.cmd[TCL_OUTPUT_VTXFMT]) {
367       RADEON_STATECHANGE( rmesa, tcl );
368       rmesa->hw.tcl.cmd[TCL_OUTPUT_VTXFMT] = vtx;
369    }
370
371    for (i = 0 ; i < RADEON_TCL_MAX_SETUP ; i++) 
372       if ((setup_tab[i].vertex_format & req) == req) 
373          break;
374
375    if (rmesa->tcl.vertex_format == setup_tab[i].vertex_format &&
376        rmesa->radeon.tcl.aos[0].bo)
377       return;
378
379    if (rmesa->radeon.tcl.aos[0].bo)
380       radeonReleaseArrays( ctx, ~0 );
381
382    radeonAllocDmaRegion( &rmesa->radeon,
383                          &rmesa->radeon.tcl.aos[0].bo,
384                          &rmesa->radeon.tcl.aos[0].offset,
385                          VB->Count * setup_tab[i].vertex_size * 4, 
386                          4);
387
388    /* The vertex code expects Obj to be clean to element 3.  To fix
389     * this, add more vertex code (for obj-2, obj-3) or preferably move
390     * to maos.  
391     */
392    if (VB->AttribPtr[_TNL_ATTRIB_POS]->size < 3 ||
393        (VB->AttribPtr[_TNL_ATTRIB_POS]->size == 3 &&
394         (setup_tab[i].vertex_format & RADEON_CP_VC_FRMT_W0))) {
395
396       _math_trans_4f( rmesa->tcl.ObjClean.data,
397                       VB->AttribPtr[_TNL_ATTRIB_POS]->data,
398                       VB->AttribPtr[_TNL_ATTRIB_POS]->stride,
399                       GL_FLOAT,
400                       VB->AttribPtr[_TNL_ATTRIB_POS]->size,
401                       0,
402                       VB->Count );
403
404       switch (VB->AttribPtr[_TNL_ATTRIB_POS]->size) {
405       case 1:
406             _mesa_vector4f_clean_elem(&rmesa->tcl.ObjClean, VB->Count, 1);
407       case 2:
408             _mesa_vector4f_clean_elem(&rmesa->tcl.ObjClean, VB->Count, 2);
409       case 3:
410          if (setup_tab[i].vertex_format & RADEON_CP_VC_FRMT_W0) {
411             _mesa_vector4f_clean_elem(&rmesa->tcl.ObjClean, VB->Count, 3);
412          }
413       case 4:
414       default:
415          break;
416       }
417
418       VB->AttribPtr[_TNL_ATTRIB_POS] = &rmesa->tcl.ObjClean;
419    }
420
421
422    radeon_bo_map(rmesa->radeon.tcl.aos[0].bo, 1);
423    setup_tab[i].emit( ctx, 0, VB->Count, 
424                       rmesa->radeon.tcl.aos[0].bo->ptr + rmesa->radeon.tcl.aos[0].offset);
425    radeon_bo_unmap(rmesa->radeon.tcl.aos[0].bo);
426    //   rmesa->radeon.tcl.aos[0].size = setup_tab[i].vertex_size;
427    rmesa->radeon.tcl.aos[0].stride = setup_tab[i].vertex_size;
428    rmesa->tcl.vertex_format = setup_tab[i].vertex_format;
429    rmesa->radeon.tcl.aos_count = 1;
430 }
431
432