2 * Mesa 3-D graphics library
5 * Copyright (C) 2006 Brian Paul All Rights Reserved.
7 * Permission is hereby granted, free of charge, to any person obtaining a
8 * copy of this software and associated documentation files (the "Software"),
9 * to deal in the Software without restriction, including without limitation
10 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
11 * and/or sell copies of the Software, and to permit persons to whom the
12 * Software is furnished to do so, subject to the following conditions:
14 * The above copyright notice and this permission notice shall be included
15 * in all copies or substantial portions of the Software.
17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
18 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
20 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
21 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
22 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
31 #include "shaderobjects.h"
32 #include "shaderobjects_3dlabs.h"
33 #include "t_pipeline.h"
34 #include "slang_utility.h"
35 #include "slang_link.h"
37 #if FEATURE_ARB_vertex_shader
41 GLvector4f outputs
[VERT_RESULT_MAX
];
42 GLvector4f varyings
[MAX_VARYING_VECTORS
];
43 GLvector4f ndc_coords
;
49 #define ARBVS_STAGE_DATA(stage) ((arbvs_stage_data *) stage->privatePtr)
51 static GLboolean
construct_arb_vertex_shader (GLcontext
*ctx
, struct tnl_pipeline_stage
*stage
)
53 TNLcontext
*tnl
= TNL_CONTEXT(ctx
);
54 struct vertex_buffer
*vb
= &tnl
->vb
;
55 arbvs_stage_data
*store
;
56 GLuint size
= vb
->Size
;
59 stage
->privatePtr
= _mesa_malloc (sizeof (arbvs_stage_data
));
60 store
= ARBVS_STAGE_DATA(stage
);
64 for (i
= 0; i
< VERT_RESULT_MAX
; i
++)
66 _mesa_vector4f_alloc (&store
->outputs
[i
], 0, size
, 32);
67 store
->outputs
[i
].size
= 4;
69 for (i
= 0; i
< MAX_VARYING_VECTORS
; i
++)
71 _mesa_vector4f_alloc (&store
->varyings
[i
], 0, size
, 32);
72 store
->varyings
[i
].size
= 4;
74 _mesa_vector4f_alloc (&store
->ndc_coords
, 0, size
, 32);
75 store
->clipmask
= (GLubyte
*) ALIGN_MALLOC (size
, 32);
80 static void destruct_arb_vertex_shader (struct tnl_pipeline_stage
*stage
)
82 arbvs_stage_data
*store
= ARBVS_STAGE_DATA(stage
);
88 for (i
= 0; i
< VERT_RESULT_MAX
; i
++)
89 _mesa_vector4f_free (&store
->outputs
[i
]);
90 for (i
= 0; i
< MAX_VARYING_VECTORS
; i
++)
91 _mesa_vector4f_free (&store
->varyings
[i
]);
92 _mesa_vector4f_free (&store
->ndc_coords
);
93 ALIGN_FREE (store
->clipmask
);
96 stage
->privatePtr
= NULL
;
100 static void validate_arb_vertex_shader (GLcontext
*ctx
, struct tnl_pipeline_stage
*stage
)
104 static GLvoid
fetch_input_float (struct gl2_program_intf
**pro
, GLuint index
, GLuint attr
, GLuint i
,
105 struct vertex_buffer
*vb
)
107 const GLubyte
*ptr
= (const GLubyte
*) vb
->AttribPtr
[attr
]->data
;
108 const GLuint stride
= vb
->AttribPtr
[attr
]->stride
;
109 GLfloat
*data
= (GLfloat
*) (ptr
+ stride
* i
);
111 (**pro
).UpdateFixedAttrib (pro
, index
, data
, 0, sizeof (GLfloat
), GL_TRUE
);
114 static GLvoid
fetch_input_vec3 (struct gl2_program_intf
**pro
, GLuint index
, GLuint attr
, GLuint i
,
115 struct vertex_buffer
*vb
)
117 const GLubyte
*ptr
= (const GLubyte
*) vb
->AttribPtr
[attr
]->data
;
118 const GLuint stride
= vb
->AttribPtr
[attr
]->stride
;
119 GLfloat
*data
= (GLfloat
*) (ptr
+ stride
* i
);
121 (**pro
).UpdateFixedAttrib (pro
, index
, data
, 0, 3 * sizeof (GLfloat
), GL_TRUE
);
124 static void fetch_input_vec4 (struct gl2_program_intf
**pro
, GLuint index
, GLuint attr
, GLuint i
,
125 struct vertex_buffer
*vb
)
127 const GLubyte
*ptr
= (const GLubyte
*) vb
->AttribPtr
[attr
]->data
;
128 const GLuint size
= vb
->AttribPtr
[attr
]->size
;
129 const GLuint stride
= vb
->AttribPtr
[attr
]->stride
;
130 const GLfloat
*data
= (const GLfloat
*) (ptr
+ stride
* i
);
154 (**pro
).UpdateFixedAttrib (pro
, index
, vec
, 0, 4 * sizeof (GLfloat
), GL_TRUE
);
158 fetch_gen_attrib (struct gl2_program_intf
**pro
, GLuint index
, GLuint i
, struct vertex_buffer
*vb
)
160 const GLuint attr
= _TNL_ATTRIB_GENERIC0
+ index
;
161 const GLubyte
*ptr
= (const GLubyte
*) (vb
->AttribPtr
[attr
]->data
);
162 const GLuint stride
= vb
->AttribPtr
[attr
]->stride
;
163 const GLfloat
*data
= (const GLfloat
*) (ptr
+ stride
* i
);
165 (**pro
).WriteAttrib (pro
, index
, data
);
168 static GLvoid
fetch_output_float (struct gl2_program_intf
**pro
, GLuint index
, GLuint attr
, GLuint i
,
169 arbvs_stage_data
*store
)
171 (**pro
).UpdateFixedAttrib (pro
, index
, &store
->outputs
[attr
].data
[i
], 0, sizeof (GLfloat
),
175 static void fetch_output_vec4 (struct gl2_program_intf
**pro
, GLuint index
, GLuint attr
, GLuint i
,
176 GLuint offset
, arbvs_stage_data
*store
)
178 (**pro
).UpdateFixedAttrib (pro
, index
, &store
->outputs
[attr
].data
[i
], offset
,
179 4 * sizeof (GLfloat
), GL_FALSE
);
182 static GLboolean
run_arb_vertex_shader (GLcontext
*ctx
, struct tnl_pipeline_stage
*stage
)
184 TNLcontext
*tnl
= TNL_CONTEXT(ctx
);
185 struct vertex_buffer
*vb
= &tnl
->vb
;
186 arbvs_stage_data
*store
= ARBVS_STAGE_DATA(stage
);
187 struct gl2_program_intf
**pro
;
190 if (!ctx
->ShaderObjects
._VertexShaderPresent
)
193 pro
= ctx
->ShaderObjects
.CurrentProgram
;
194 (**pro
).UpdateFixedUniforms (pro
);
196 for (i
= 0; i
< vb
->Count
; i
++)
198 fetch_input_vec4 (pro
, SLANG_VERTEX_FIXED_VERTEX
, _TNL_ATTRIB_POS
, i
, vb
);
199 fetch_input_vec3 (pro
, SLANG_VERTEX_FIXED_NORMAL
, _TNL_ATTRIB_NORMAL
, i
, vb
);
200 fetch_input_vec4 (pro
, SLANG_VERTEX_FIXED_COLOR
, _TNL_ATTRIB_COLOR0
, i
, vb
);
201 fetch_input_vec4 (pro
, SLANG_VERTEX_FIXED_SECONDARYCOLOR
, _TNL_ATTRIB_COLOR1
, i
, vb
);
202 fetch_input_float (pro
, SLANG_VERTEX_FIXED_FOGCOORD
, _TNL_ATTRIB_FOG
, i
, vb
);
203 fetch_input_vec4 (pro
, SLANG_VERTEX_FIXED_MULTITEXCOORD0
, _TNL_ATTRIB_TEX0
, i
, vb
);
204 fetch_input_vec4 (pro
, SLANG_VERTEX_FIXED_MULTITEXCOORD1
, _TNL_ATTRIB_TEX1
, i
, vb
);
205 fetch_input_vec4 (pro
, SLANG_VERTEX_FIXED_MULTITEXCOORD2
, _TNL_ATTRIB_TEX2
, i
, vb
);
206 fetch_input_vec4 (pro
, SLANG_VERTEX_FIXED_MULTITEXCOORD3
, _TNL_ATTRIB_TEX3
, i
, vb
);
207 fetch_input_vec4 (pro
, SLANG_VERTEX_FIXED_MULTITEXCOORD4
, _TNL_ATTRIB_TEX4
, i
, vb
);
208 fetch_input_vec4 (pro
, SLANG_VERTEX_FIXED_MULTITEXCOORD5
, _TNL_ATTRIB_TEX5
, i
, vb
);
209 fetch_input_vec4 (pro
, SLANG_VERTEX_FIXED_MULTITEXCOORD6
, _TNL_ATTRIB_TEX6
, i
, vb
);
210 fetch_input_vec4 (pro
, SLANG_VERTEX_FIXED_MULTITEXCOORD7
, _TNL_ATTRIB_TEX7
, i
, vb
);
211 for (j
= 0; j
< MAX_VERTEX_ATTRIBS
; j
++)
212 fetch_gen_attrib (pro
, j
, i
, vb
);
214 _slang_exec_vertex_shader (pro
);
216 fetch_output_vec4 (pro
, SLANG_VERTEX_FIXED_POSITION
, VERT_RESULT_HPOS
, i
, 0, store
);
217 fetch_output_vec4 (pro
, SLANG_VERTEX_FIXED_FRONTCOLOR
, VERT_RESULT_COL0
, i
, 0, store
);
218 fetch_output_vec4 (pro
, SLANG_VERTEX_FIXED_FRONTSECONDARYCOLOR
, VERT_RESULT_COL1
, i
, 0, store
);
219 fetch_output_float (pro
, SLANG_VERTEX_FIXED_FOGFRAGCOORD
, VERT_RESULT_FOGC
, i
, store
);
220 for (j
= 0; j
< 8; j
++)
221 fetch_output_vec4 (pro
, SLANG_VERTEX_FIXED_TEXCOORD
, VERT_RESULT_TEX0
+ j
, i
, j
, store
);
222 fetch_output_float (pro
, SLANG_VERTEX_FIXED_POINTSIZE
, VERT_RESULT_PSIZ
, i
, store
);
223 fetch_output_vec4 (pro
, SLANG_VERTEX_FIXED_BACKCOLOR
, VERT_RESULT_BFC0
, i
, 0, store
);
224 fetch_output_vec4 (pro
, SLANG_VERTEX_FIXED_BACKSECONDARYCOLOR
, VERT_RESULT_BFC1
, i
, 0, store
);
225 /* XXX: fetch output SLANG_VERTEX_FIXED_CLIPVERTEX */
227 for (j
= 0; j
< MAX_VARYING_VECTORS
; j
++)
231 for (k
= 0; k
< VARYINGS_PER_VECTOR
; k
++)
233 (**pro
).UpdateVarying (pro
, j
* VARYINGS_PER_VECTOR
+ k
,
234 &store
->varyings
[j
].data
[i
][k
], GL_TRUE
);
239 vb
->ClipPtr
= &store
->outputs
[VERT_RESULT_HPOS
];
240 vb
->ClipPtr
->count
= vb
->Count
;
242 vb
->ColorPtr
[0] = &store
->outputs
[VERT_RESULT_COL0
];
243 vb
->AttribPtr
[VERT_ATTRIB_COLOR0
] = vb
->ColorPtr
[0];
244 vb
->ColorPtr
[1] = &store
->outputs
[VERT_RESULT_BFC0
];
246 vb
->SecondaryColorPtr
[0] =
247 vb
->AttribPtr
[VERT_ATTRIB_COLOR1
] = &store
->outputs
[VERT_RESULT_COL1
];
249 vb
->SecondaryColorPtr
[1] = &store
->outputs
[VERT_RESULT_BFC1
];
251 for (i
= 0; i
< ctx
->Const
.MaxTextureCoordUnits
; i
++) {
253 vb
->AttribPtr
[VERT_ATTRIB_TEX0
+ i
] = &store
->outputs
[VERT_RESULT_TEX0
+ i
];
257 vb
->AttribPtr
[VERT_ATTRIB_FOG
] = &store
->outputs
[VERT_RESULT_FOGC
];
259 vb
->AttribPtr
[_TNL_ATTRIB_POINTSIZE
] = &store
->outputs
[VERT_RESULT_PSIZ
];
261 for (i
= 0; i
< MAX_VARYING_VECTORS
; i
++) {
262 vb
->VaryingPtr
[i
] = &store
->varyings
[i
];
263 vb
->AttribPtr
[_TNL_ATTRIB_GENERIC0
+ i
] = vb
->VaryingPtr
[i
];
267 store
->andmask
= CLIP_FRUSTUM_BITS
;
269 if (tnl
->NeedNdcCoords
)
271 vb
->NdcPtr
= _mesa_clip_tab
[vb
->ClipPtr
->size
] (vb
->ClipPtr
, &store
->ndc_coords
,
272 store
->clipmask
, &store
->ormask
, &store
->andmask
);
277 _mesa_clip_np_tab
[vb
->ClipPtr
->size
] (vb
->ClipPtr
, NULL
, store
->clipmask
, &store
->ormask
,
284 vb
->ClipAndMask
= store
->andmask
;
285 vb
->ClipOrMask
= store
->ormask
;
286 vb
->ClipMask
= store
->clipmask
;
291 const struct tnl_pipeline_stage _tnl_arb_vertex_shader_stage
= {
294 construct_arb_vertex_shader
,
295 destruct_arb_vertex_shader
,
296 validate_arb_vertex_shader
,
297 run_arb_vertex_shader
300 #endif /* FEATURE_ARB_vertex_shader */