Add render stage for unclipped vb's to fx driver.
[mesa.git] / src / mesa / array_cache / ac_import.c
1 /* $Id: ac_import.c,v 1.2 2000/12/28 22:11:05 keithw Exp $ */
2
3 /*
4 * Mesa 3-D graphics library
5 * Version: 3.5
6 *
7 * Copyright (C) 1999 Brian Paul All Rights Reserved.
8 *
9 * Permission is hereby granted, free of charge, to any person obtaining a
10 * copy of this software and associated documentation files (the "Software"),
11 * to deal in the Software without restriction, including without limitation
12 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
13 * and/or sell copies of the Software, and to permit persons to whom the
14 * Software is furnished to do so, subject to the following conditions:
15 *
16 * The above copyright notice and this permission notice shall be included
17 * in all copies or substantial portions of the Software.
18 *
19 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
20 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
22 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
23 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
24 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
25 *
26 * Author:
27 * Keith Whitwell <keithw@valinux.com>
28 */
29
30 #include "glheader.h"
31 #include "macros.h"
32 #include "mem.h"
33 #include "mmath.h"
34 #include "mtypes.h"
35
36 #include "array_cache/ac_context.h"
37
38
39
40 /* Set the array pointer back to its source when the cached data is
41 * invalidated:
42 */
43
44 static void reset_texcoord( GLcontext *ctx, GLuint unit )
45 {
46 ACcontext *ac = AC_CONTEXT(ctx);
47
48 /* fprintf(stderr, "%s %d\n", __FUNCTION__, unit); */
49
50 if (ctx->Array._Enabled & _NEW_ARRAY_TEXCOORD(unit))
51 ac->Current.TexCoord[unit] = &ctx->Array.TexCoord[unit];
52 else {
53 ac->Current.TexCoord[unit] = &ac->Fallback.TexCoord[unit];
54
55 if (ctx->Current.Texcoord[unit][4] != 1.0)
56 ac->Current.TexCoord[unit]->Size = 4;
57 else if (ctx->Current.Texcoord[unit][3] != 0.0)
58 ac->Current.TexCoord[unit]->Size = 3;
59 else
60 ac->Current.TexCoord[unit]->Size = 2;
61 }
62
63 ac->Writeable.TexCoord[unit] = GL_FALSE;
64 ac->NewArrayState &= ~_NEW_ARRAY_TEXCOORD(unit);
65 }
66
67 static void reset_vertex( GLcontext *ctx )
68 {
69 ACcontext *ac = AC_CONTEXT(ctx);
70 ASSERT(ctx->Array.Vertex.Enabled);
71 ac->Current.Vertex = &ctx->Array.Vertex;
72 ac->Writeable.Vertex = GL_FALSE;
73 ac->NewArrayState &= ~_NEW_ARRAY_VERTEX;
74
75 /* fprintf(stderr, "%s\n", __FUNCTION__); */
76 }
77
78
79 static void reset_normal( GLcontext *ctx )
80 {
81 ACcontext *ac = AC_CONTEXT(ctx);
82
83 if (ctx->Array._Enabled & _NEW_ARRAY_NORMAL) {
84 /* fprintf(stderr, "reset normal: using client array enab %d\n", */
85 /* ctx->Array.Normal.Enabled); */
86 ac->Current.Normal = &ctx->Array.Normal;
87 }
88 else {
89 /* fprintf(stderr, "reset normal: using fallback enab %d\n", */
90 /* ctx->Array.Normal.Enabled); */
91 ac->Current.Normal = &ac->Fallback.Normal;
92 }
93
94 ac->Writeable.Normal = GL_FALSE;
95 ac->NewArrayState &= ~_NEW_ARRAY_NORMAL;
96 }
97
98
99 static void reset_color( GLcontext *ctx )
100 {
101 ACcontext *ac = AC_CONTEXT(ctx);
102
103
104 if (ctx->Array._Enabled & _NEW_ARRAY_COLOR)
105 ac->Current.Color = &ctx->Array.Color;
106 else
107 ac->Current.Color = &ac->Fallback.Color;
108
109 /* fprintf(stderr, "reset_color, stride now %d\n", ac->Current.Color->StrideB); */
110
111 ac->Writeable.Color = GL_FALSE;
112 ac->NewArrayState &= ~_NEW_ARRAY_COLOR;
113 }
114
115
116 static void reset_secondarycolor( GLcontext *ctx )
117 {
118 ACcontext *ac = AC_CONTEXT(ctx);
119
120 if (ctx->Array._Enabled & _NEW_ARRAY_SECONDARYCOLOR)
121 ac->Current.SecondaryColor = &ctx->Array.SecondaryColor;
122 else
123 ac->Current.SecondaryColor = &ac->Fallback.SecondaryColor;
124
125 ac->Writeable.SecondaryColor = GL_FALSE;
126 ac->NewArrayState &= ~_NEW_ARRAY_SECONDARYCOLOR;
127 }
128
129
130 static void reset_index( GLcontext *ctx )
131 {
132 ACcontext *ac = AC_CONTEXT(ctx);
133
134 if (ctx->Array._Enabled & _NEW_ARRAY_INDEX)
135 ac->Current.Index = &ctx->Array.Index;
136 else
137 ac->Current.Index = &ac->Fallback.Index;
138
139 ac->Writeable.Index = GL_FALSE;
140 ac->NewArrayState &= ~_NEW_ARRAY_INDEX;
141 }
142
143 static void reset_fogcoord( GLcontext *ctx )
144 {
145 ACcontext *ac = AC_CONTEXT(ctx);
146
147 if (ctx->Array._Enabled & _NEW_ARRAY_FOGCOORD)
148 ac->Current.FogCoord = &ctx->Array.FogCoord;
149 else
150 ac->Current.FogCoord = &ac->Fallback.FogCoord;
151
152 ac->Writeable.FogCoord = GL_FALSE;
153 ac->NewArrayState &= ~_NEW_ARRAY_FOGCOORD;
154 }
155
156 static void reset_edgeflag( GLcontext *ctx )
157 {
158 ACcontext *ac = AC_CONTEXT(ctx);
159
160 if (ctx->Array._Enabled & _NEW_ARRAY_EDGEFLAG)
161 ac->Current.EdgeFlag = &ctx->Array.EdgeFlag;
162 else
163 ac->Current.EdgeFlag = &ac->Fallback.EdgeFlag;
164
165 ac->Writeable.EdgeFlag = GL_FALSE;
166 ac->NewArrayState &= ~_NEW_ARRAY_EDGEFLAG;
167 }
168
169
170 /* Functions to import array ranges with specified types and strides.
171 */
172 static void import_texcoord( GLcontext *ctx, GLuint unit,
173 GLenum type, GLuint stride )
174 {
175 ACcontext *ac = AC_CONTEXT(ctx);
176 struct gl_client_array *from = ac->Current.TexCoord[unit];
177 struct gl_client_array *to = &ac->Cache.TexCoord[unit];
178
179 /* Limited choices at this stage:
180 */
181 ASSERT(type == GL_FLOAT);
182 ASSERT(stride == 4*sizeof(GLfloat) || stride == 0);
183 ASSERT(ac->count - ac->start < ctx->Const.MaxArrayLockSize);
184
185 /* fprintf(stderr, "%s %d old ptr %p\n", __FUNCTION__, unit, from->Ptr); */
186
187 _math_trans_4f( to->Ptr,
188 from->Ptr,
189 from->StrideB,
190 from->Type,
191 from->Size,
192 ac->start,
193 ac->count);
194
195 to->Size = from->Size;
196 to->StrideB = 4 * sizeof(GLfloat);
197 to->Type = GL_FLOAT;
198 ac->Current.TexCoord[unit] = to;
199 ac->Writeable.TexCoord[unit] = GL_TRUE;
200
201 /* fprintf(stderr, "%s %d new ptr %p\n", __FUNCTION__, unit, to->Ptr); */
202 }
203
204 static void import_vertex( GLcontext *ctx,
205 GLenum type, GLuint stride )
206 {
207 ACcontext *ac = AC_CONTEXT(ctx);
208 struct gl_client_array *from = ac->Current.Vertex;
209 struct gl_client_array *to = &ac->Cache.Vertex;
210
211 /* fprintf(stderr, "(ac) %s\n", __FUNCTION__); */
212
213 /* Limited choices at this stage:
214 */
215 ASSERT(type == GL_FLOAT);
216 ASSERT(stride == 4*sizeof(GLfloat) || stride == 0);
217
218 _math_trans_4f( to->Ptr,
219 from->Ptr,
220 from->StrideB,
221 from->Type,
222 from->Size,
223 ac->start,
224 ac->count);
225
226 to->Size = from->Size;
227 to->StrideB = 4 * sizeof(GLfloat);
228 to->Type = GL_FLOAT;
229 ac->Current.Vertex = to;
230 ac->Writeable.Vertex = GL_TRUE;
231 }
232
233 static void import_normal( GLcontext *ctx,
234 GLenum type, GLuint stride )
235 {
236 ACcontext *ac = AC_CONTEXT(ctx);
237 struct gl_client_array *from = ac->Current.Normal;
238 struct gl_client_array *to = &ac->Cache.Normal;
239
240
241 /* fprintf(stderr, "ac: import_normal\n"); */
242
243 /* Limited choices at this stage:
244 */
245 ASSERT(type == GL_FLOAT);
246 ASSERT(stride == 3*sizeof(GLfloat) || stride == 0);
247
248 _math_trans_3f( to->Ptr,
249 from->Ptr,
250 from->StrideB,
251 from->Type,
252 ac->start,
253 ac->count);
254
255 to->StrideB = 3 * sizeof(GLfloat);
256 to->Type = GL_FLOAT;
257 ac->Current.Normal = to;
258 ac->Writeable.Normal = GL_TRUE;
259 }
260
261 static void import_color( GLcontext *ctx,
262 GLenum type, GLuint stride )
263 {
264 ACcontext *ac = AC_CONTEXT(ctx);
265 struct gl_client_array *from = ac->Current.Color;
266 struct gl_client_array *to = &ac->Cache.Color;
267
268 /* fprintf(stderr, "(ac) %s\n", __FUNCTION__); */
269
270 /* Limited choices at this stage:
271 */
272 ASSERT(type == GL_UNSIGNED_BYTE);
273 ASSERT(stride == 4*sizeof(GLubyte) || stride == 0);
274
275 _math_trans_4ub( to->Ptr,
276 from->Ptr,
277 from->StrideB,
278 from->Type,
279 from->Size,
280 ac->start,
281 ac->count);
282
283 to->Size = from->Size;
284 to->StrideB = 4 * sizeof(GLubyte);
285 to->Type = GL_FLOAT;
286 ac->Current.Color = to;
287 ac->Writeable.Color = GL_TRUE;
288 }
289
290 static void import_index( GLcontext *ctx,
291 GLenum type, GLuint stride )
292 {
293 ACcontext *ac = AC_CONTEXT(ctx);
294 struct gl_client_array *from = ac->Current.Index;
295 struct gl_client_array *to = &ac->Cache.Index;
296
297 /* Limited choices at this stage:
298 */
299 ASSERT(type == GL_UNSIGNED_INT);
300 ASSERT(stride == sizeof(GLuint) || stride == 0);
301
302 _math_trans_1ui( to->Ptr,
303 from->Ptr,
304 from->StrideB,
305 from->Type,
306 ac->start,
307 ac->count);
308
309 to->StrideB = sizeof(GLuint);
310 to->Type = GL_UNSIGNED_INT;
311 ac->Current.Index = to;
312 ac->Writeable.Index = GL_TRUE;
313 }
314
315 static void import_secondarycolor( GLcontext *ctx,
316 GLenum type, GLuint stride )
317 {
318 ACcontext *ac = AC_CONTEXT(ctx);
319 struct gl_client_array *from = ac->Current.SecondaryColor;
320 struct gl_client_array *to = &ac->Cache.SecondaryColor;
321
322 /* Limited choices at this stage:
323 */
324 ASSERT(type == GL_UNSIGNED_BYTE);
325 ASSERT(stride == 4*sizeof(GLubyte) || stride == 0);
326
327 _math_trans_4ub( to->Ptr,
328 from->Ptr,
329 from->StrideB,
330 from->Type,
331 from->Size,
332 ac->start,
333 ac->count);
334
335 to->StrideB = 4 * sizeof(GLubyte);
336 to->Type = GL_UNSIGNED_BYTE;
337 ac->Current.SecondaryColor = to;
338 ac->Writeable.SecondaryColor = GL_TRUE;
339 }
340
341 static void import_fogcoord( GLcontext *ctx,
342 GLenum type, GLuint stride )
343 {
344 ACcontext *ac = AC_CONTEXT(ctx);
345 struct gl_client_array *from = ac->Current.FogCoord;
346 struct gl_client_array *to = &ac->Cache.FogCoord;
347
348 /* Limited choices at this stage:
349 */
350 ASSERT(type == GL_FLOAT);
351 ASSERT(stride == sizeof(GLfloat) || stride == 0);
352
353 _math_trans_1f( to->Ptr,
354 from->Ptr,
355 from->StrideB,
356 from->Type,
357 ac->start,
358 ac->count);
359
360 to->StrideB = sizeof(GLfloat);
361 to->Type = GL_FLOAT;
362 ac->Current.FogCoord = to;
363 ac->Writeable.FogCoord = GL_TRUE;
364 }
365
366 static void import_edgeflag( GLcontext *ctx,
367 GLenum type, GLuint stride )
368 {
369 ACcontext *ac = AC_CONTEXT(ctx);
370 struct gl_client_array *from = ac->Current.EdgeFlag;
371 struct gl_client_array *to = &ac->Cache.EdgeFlag;
372
373 /* Limited choices at this stage:
374 */
375 ASSERT(type == GL_FLOAT);
376 ASSERT(stride == sizeof(GLfloat) || stride == 0);
377
378 _math_trans_1f( to->Ptr,
379 from->Ptr,
380 from->StrideB,
381 from->Type,
382 ac->start,
383 ac->count);
384
385 to->StrideB = sizeof(GLfloat);
386 to->Type = GL_FLOAT;
387 ac->Current.EdgeFlag = to;
388 ac->Writeable.EdgeFlag = GL_TRUE;
389 }
390
391
392
393 /* Externals to request arrays with specific properties:
394 */
395 struct gl_client_array *_ac_import_texcoord( GLcontext *ctx,
396 GLuint unit,
397 GLenum type,
398 GLuint reqstride,
399 GLuint reqsize,
400 GLboolean reqwriteable,
401 GLboolean *writeable )
402 {
403 ACcontext *ac = AC_CONTEXT(ctx);
404
405 /* Can we keep the existing version?
406 */
407 if (ac->NewArrayState & _NEW_ARRAY_TEXCOORD(unit))
408 reset_texcoord( ctx, unit );
409
410 /* Is the request impossible?
411 */
412 if (reqsize != 0 && ac->Current.TexCoord[unit]->Size > reqsize)
413 return 0;
414
415 /* Do we need to pull in a copy of the client data:
416 */
417 if (ac->Current.TexCoord[unit]->Type != type ||
418 (reqstride != 0 && ac->Current.TexCoord[unit]->StrideB != reqstride) ||
419 (reqwriteable && !ac->Writeable.TexCoord[unit]))
420 import_texcoord(ctx, unit, type, reqstride );
421
422 *writeable = ac->Writeable.TexCoord[unit];
423 return ac->Current.TexCoord[unit];
424 }
425
426 struct gl_client_array *_ac_import_vertex( GLcontext *ctx,
427 GLenum type,
428 GLuint reqstride,
429 GLuint reqsize,
430 GLboolean reqwriteable,
431 GLboolean *writeable )
432 {
433 ACcontext *ac = AC_CONTEXT(ctx);
434
435 /* Can we keep the existing version?
436 */
437 if (ac->NewArrayState & _NEW_ARRAY_VERTEX)
438 reset_vertex( ctx );
439
440 /* Is the request impossible?
441 */
442 if (reqsize != 0 && ac->Current.Vertex->Size > reqsize)
443 return 0;
444
445 /* Do we need to pull in a copy of the client data:
446 */
447 if (ac->Current.Vertex->Type != type ||
448 (reqstride != 0 && ac->Current.Vertex->StrideB != reqstride) ||
449 (reqwriteable && !ac->Writeable.Vertex))
450 import_vertex(ctx, type, reqstride );
451
452 *writeable = ac->Writeable.Vertex;
453 return ac->Current.Vertex;
454 }
455
456 struct gl_client_array *_ac_import_normal( GLcontext *ctx,
457 GLenum type,
458 GLuint reqstride,
459 GLboolean reqwriteable,
460 GLboolean *writeable )
461 {
462 ACcontext *ac = AC_CONTEXT(ctx);
463
464 /* fprintf(stderr, "%s %d\n", __FUNCTION__, ac->NewArrayState & _NEW_ARRAY_NORMAL); */
465
466 /* Can we keep the existing version?
467 */
468 if (ac->NewArrayState & _NEW_ARRAY_NORMAL)
469 reset_normal( ctx );
470
471 /* Do we need to pull in a copy of the client data:
472 */
473 if (ac->Current.Normal->Type != type ||
474 (reqstride != 0 && ac->Current.Normal->StrideB != reqstride) ||
475 (reqwriteable && !ac->Writeable.Normal))
476 import_normal(ctx, type, reqstride );
477
478 *writeable = ac->Writeable.Normal;
479 return ac->Current.Normal;
480 }
481
482 struct gl_client_array *_ac_import_color( GLcontext *ctx,
483 GLenum type,
484 GLuint reqstride,
485 GLuint reqsize,
486 GLboolean reqwriteable,
487 GLboolean *writeable )
488 {
489 ACcontext *ac = AC_CONTEXT(ctx);
490
491 /* fprintf(stderr, "%s stride %d sz %d wr %d\n", __FUNCTION__, */
492 /* reqstride, reqsize, reqwriteable); */
493
494 /* Can we keep the existing version?
495 */
496 if (ac->NewArrayState & _NEW_ARRAY_COLOR)
497 reset_color( ctx );
498
499 /* Is the request impossible?
500 */
501 if (reqsize != 0 && ac->Current.Color->Size > reqsize) {
502 /* fprintf(stderr, "%s -- failed\n", __FUNCTION__); */
503 return 0;
504 }
505
506 /* Do we need to pull in a copy of the client data:
507 */
508 if (ac->Current.Color->Type != type ||
509 (reqstride != 0 && ac->Current.Color->StrideB != reqstride) ||
510 (reqwriteable && !ac->Writeable.Color))
511 import_color(ctx, type, reqstride );
512
513 *writeable = ac->Writeable.Color;
514 return ac->Current.Color;
515 }
516
517 struct gl_client_array *_ac_import_index( GLcontext *ctx,
518 GLenum type,
519 GLuint reqstride,
520 GLboolean reqwriteable,
521 GLboolean *writeable )
522 {
523 ACcontext *ac = AC_CONTEXT(ctx);
524
525 /* Can we keep the existing version?
526 */
527 if (ac->NewArrayState & _NEW_ARRAY_INDEX)
528 reset_index( ctx );
529
530
531 /* Do we need to pull in a copy of the client data:
532 */
533 if (ac->Current.Index->Type != type ||
534 (reqstride != 0 && ac->Current.Index->StrideB != reqstride) ||
535 (reqwriteable && !ac->Writeable.Index))
536 import_index(ctx, type, reqstride );
537
538 *writeable = ac->Writeable.Index;
539 return ac->Current.Index;
540 }
541
542 struct gl_client_array *_ac_import_secondarycolor( GLcontext *ctx,
543 GLenum type,
544 GLuint reqstride,
545 GLuint reqsize,
546 GLboolean reqwriteable,
547 GLboolean *writeable )
548 {
549 ACcontext *ac = AC_CONTEXT(ctx);
550
551 /* Can we keep the existing version?
552 */
553 if (ac->NewArrayState & _NEW_ARRAY_SECONDARYCOLOR)
554 reset_secondarycolor( ctx );
555
556 /* Is the request impossible?
557 */
558 if (reqsize != 0 && ac->Current.SecondaryColor->Size > reqsize)
559 return 0;
560
561 /* Do we need to pull in a copy of the client data:
562 */
563 if (ac->Current.SecondaryColor->Type != type ||
564 (reqstride != 0 && ac->Current.SecondaryColor->StrideB != reqstride) ||
565 (reqwriteable && !ac->Writeable.SecondaryColor))
566 import_secondarycolor( ctx, type, reqstride );
567
568 *writeable = ac->Writeable.SecondaryColor;
569 return ac->Current.SecondaryColor;
570 }
571
572 struct gl_client_array *_ac_import_fogcoord( GLcontext *ctx,
573 GLenum type,
574 GLuint reqstride,
575 GLboolean reqwriteable,
576 GLboolean *writeable )
577 {
578 ACcontext *ac = AC_CONTEXT(ctx);
579
580 /* Can we keep the existing version?
581 */
582 if (ac->NewArrayState & _NEW_ARRAY_FOGCOORD)
583 reset_fogcoord( ctx );
584
585 /* Do we need to pull in a copy of the client data:
586 */
587 if (ac->Current.FogCoord->Type != type ||
588 (reqstride != 0 && ac->Current.FogCoord->StrideB != reqstride) ||
589 (reqwriteable && !ac->Writeable.FogCoord))
590 import_fogcoord(ctx, type, reqstride );
591
592 *writeable = ac->Writeable.FogCoord;
593 return ac->Current.FogCoord;
594 }
595
596
597
598
599 struct gl_client_array *_ac_import_edgeflag( GLcontext *ctx,
600 GLenum type,
601 GLuint reqstride,
602 GLboolean reqwriteable,
603 GLboolean *writeable )
604 {
605 ACcontext *ac = AC_CONTEXT(ctx);
606
607 /* Can we keep the existing version?
608 */
609 if (ac->NewArrayState & _NEW_ARRAY_EDGEFLAG)
610 reset_edgeflag( ctx );
611
612 /* Do we need to pull in a copy of the client data:
613 */
614 if (ac->Current.EdgeFlag->Type != type ||
615 (reqstride != 0 && ac->Current.EdgeFlag->StrideB != reqstride) ||
616 (reqwriteable && !ac->Writeable.EdgeFlag))
617 import_edgeflag(ctx, type, reqstride );
618
619 *writeable = ac->Writeable.EdgeFlag;
620 return ac->Current.EdgeFlag;
621 }
622
623
624
625
626
627 /* Clients must call this function to validate state and set bounds
628 * before importing any data:
629 */
630 void _ac_import_range( GLcontext *ctx, GLuint start, GLuint count )
631 {
632 ACcontext *ac = AC_CONTEXT(ctx);
633
634 /* Discard cached data which has been invalidated by state changes
635 * since last time. **ALREADY DONE**
636 if (ac->NewState)
637 _ac_update_state( ctx );
638 */
639
640 if (!ctx->Array.LockCount) {
641 /* Not locked, discard cached data. Changes to lock
642 * status are caught via. _ac_invalidate_state().
643 */
644 ac->NewArrayState = _NEW_ARRAY_ALL;
645 ac->start = start;
646 ac->count = count;
647 }
648 else {
649 /* Locked, discard data for any disabled arrays. Require that
650 * the whole locked range always be dealt with, otherwise hard to
651 * maintain cached data in the face of clipping.
652 */
653 ac->NewArrayState |= ~ctx->Array._Enabled;
654 ac->start = ctx->Array.LockFirst;
655 ac->count = ctx->Array.LockCount;
656 ASSERT(ac->start == start); /* hmm? */
657 ASSERT(ac->count == count);
658 }
659 }
660
661
662
663 /* Additional convienence function for importing a the element list
664 * for drawelements, drawrangeelements:
665 */
666 CONST void *
667 _ac_import_elements( GLcontext *ctx,
668 GLenum new_type,
669 GLuint count,
670 GLenum old_type,
671 CONST void *indices )
672 {
673 ACcontext *ac = AC_CONTEXT(ctx);
674
675 if (old_type == new_type)
676 return indices;
677
678 if (ac->elt_size < count * sizeof(GLuint)) {
679 if (ac->Elts) FREE(ac->Elts);
680 while (ac->elt_size < count * sizeof(GLuint))
681 ac->elt_size *= 2;
682 ac->Elts = MALLOC(ac->elt_size);
683 }
684
685 switch (new_type) {
686 case GL_UNSIGNED_BYTE:
687 ASSERT(0);
688 return 0;
689 case GL_UNSIGNED_SHORT:
690 ASSERT(0);
691 return 0;
692 case GL_UNSIGNED_INT: {
693 GLuint *out = (GLuint *)ac->Elts;
694 GLuint i;
695
696 switch (old_type) {
697 case GL_UNSIGNED_BYTE: {
698 CONST GLubyte *in = (CONST GLubyte *)indices;
699 for (i = 0 ; i < count ; i++)
700 out[i] = in[i];
701 break;
702 }
703 case GL_UNSIGNED_SHORT: {
704 CONST GLushort *in = (CONST GLushort *)indices;
705 for (i = 0 ; i < count ; i++)
706 out[i] = in[i];
707 break;
708 }
709 default:
710 ASSERT(0);
711 }
712
713 return (CONST void *)out;
714 }
715 default:
716 ASSERT(0);
717 break;
718 }
719
720 return 0;
721 }
722