2 * Copyright (C) 2005 Aapo Tahkola.
6 * Permission is hereby granted, free of charge, to any person obtaining
7 * a copy of this software and associated documentation files (the
8 * "Software"), to deal in the Software without restriction, including
9 * without limitation the rights to use, copy, modify, merge, publish,
10 * distribute, sublicense, and/or sell copies of the Software, and to
11 * permit persons to whom the Software is furnished to do so, subject to
12 * the following conditions:
14 * The above copyright notice and this permission notice (including the
15 * next paragraph) shall be included in all copies or substantial
16 * portions of the Software.
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
19 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
21 * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE
22 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
23 * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
24 * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
30 * Aapo Tahkola <aet@rasterburn.org>
34 #include "r300_context.h"
35 #include "r300_cmdbuf.h"
36 #include "radeon_mm.h"
40 #ifdef RADEON_VTXFMT_A
42 #define CONV(a, b) rmesa->state.VB.AttribPtr[(a)].size = ctx->Array.b.Size, \
43 rmesa->state.VB.AttribPtr[(a)].data = ctx->Array.b.BufferObj->Name ? \
44 ADD_POINTERS(ctx->Array.b.Ptr, ctx->Array.b.BufferObj->Data) : ctx->Array.b.Ptr, \
45 rmesa->state.VB.AttribPtr[(a)].stride = ctx->Array.b.StrideB, \
46 rmesa->state.VB.AttribPtr[(a)].type = ctx->Array.b.Type
48 static int setup_arrays(r300ContextPtr rmesa
, GLint start
)
51 struct dt def
= { 4, GL_FLOAT
, 0, NULL
};
55 ctx
= rmesa
->radeon
.glCtx
;
56 if (r300Fallback(ctx
))
59 memset(rmesa
->state
.VB
.AttribPtr
, 0, VERT_ATTRIB_MAX
*sizeof(struct dt
));
61 CONV(VERT_ATTRIB_POS
, Vertex
);
62 if (ctx
->Array
.Vertex
.Enabled
)
63 enabled
|= 1 << VERT_ATTRIB_POS
;
65 CONV(VERT_ATTRIB_NORMAL
, Normal
);
66 if (ctx
->Array
.Normal
.Enabled
)
67 enabled
|= 1 << VERT_ATTRIB_NORMAL
;
69 CONV(VERT_ATTRIB_COLOR0
, Color
);
70 if (ctx
->Array
.Color
.Enabled
)
71 enabled
|= 1 << VERT_ATTRIB_COLOR0
;
73 CONV(VERT_ATTRIB_COLOR1
, SecondaryColor
);
74 if (ctx
->Array
.SecondaryColor
.Enabled
)
75 enabled
|= 1 << VERT_ATTRIB_COLOR1
;
77 CONV(VERT_ATTRIB_FOG
, FogCoord
);
78 if (ctx
->Array
.FogCoord
.Enabled
)
79 enabled
|= 1 << VERT_ATTRIB_FOG
;
81 for (i
=0; i
< MAX_TEXTURE_COORD_UNITS
; i
++) {
82 CONV(VERT_ATTRIB_TEX0
+ i
, TexCoord
[i
]);
84 if(ctx
->Array
.TexCoord
[i
].Enabled
) {
85 enabled
|= 1 << (VERT_ATTRIB_TEX0
+i
);
90 for (i
=0; i
< VERT_ATTRIB_MAX
; i
++) {
91 if (enabled
& (1 << i
)) {
92 rmesa
->state
.VB
.AttribPtr
[i
].data
+= rmesa
->state
.VB
.AttribPtr
[i
].stride
* start
;
94 def
.data
= ctx
->Current
.Attrib
[i
];
95 memcpy(&rmesa
->state
.VB
.AttribPtr
[i
], &def
, sizeof(struct dt
));
98 /*if(rmesa->state.VB.AttribPtr[i].data == ctx->Current.Attrib[i])
99 fprintf(stderr, "%d is default coord\n", i);*/
102 for(i
=0; i
< VERT_ATTRIB_MAX
; i
++){
103 if(rmesa
->state
.VB
.AttribPtr
[i
].type
!= GL_UNSIGNED_BYTE
&&
104 rmesa
->state
.VB
.AttribPtr
[i
].type
!= GL_FLOAT
){
105 WARN_ONCE("Unsupported format %d at index %d\n", rmesa
->state
.VB
.AttribPtr
[i
].type
, i
);
108 if(rmesa
->state
.VB
.AttribPtr
[i
].type
== GL_UNSIGNED_BYTE
&&
109 rmesa
->state
.VB
.AttribPtr
[i
].size
!= 4){
110 WARN_ONCE("Unsupported component count for ub colors\n");
114 /*fprintf(stderr, "%d: ", i);
116 switch(rmesa->state.VB.AttribPtr[i].type){
117 case GL_BYTE: fprintf(stderr, "byte "); break;
118 case GL_UNSIGNED_BYTE: fprintf(stderr, "u byte "); break;
119 case GL_SHORT: fprintf(stderr, "short "); break;
120 case GL_UNSIGNED_SHORT: fprintf(stderr, "u short "); break;
121 case GL_INT: fprintf(stderr, "int "); break;
122 case GL_UNSIGNED_INT: fprintf(stderr, "u int "); break;
123 case GL_FLOAT: fprintf(stderr, "float "); break;
124 case GL_2_BYTES: fprintf(stderr, "2 bytes "); break;
125 case GL_3_BYTES: fprintf(stderr, "3 bytes "); break;
126 case GL_4_BYTES: fprintf(stderr, "4 bytes "); break;
127 case GL_DOUBLE: fprintf(stderr, "double "); break;
128 default: fprintf(stderr, "unknown "); break;
131 fprintf(stderr, "Size %d ", rmesa->state.VB.AttribPtr[i].size);
132 fprintf(stderr, "Ptr %p ", rmesa->state.VB.AttribPtr[i].data);
133 fprintf(stderr, "Stride %d ", rmesa->state.VB.AttribPtr[i].stride);
134 fprintf(stderr, "\n");*/
139 void radeon_init_vtxfmt_a(r300ContextPtr rmesa
);
141 void radeonDrawElements( GLenum mode
, GLsizei count
, GLenum type
, const GLvoid
*c_indices
)
143 GET_CURRENT_CONTEXT(ctx
);
144 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
147 unsigned int min
= ~0, max
= 0;
148 struct tnl_prim prim
;
149 static void *ptr
= NULL
;
150 static struct r300_dma_region rvb
;
154 WARN_ONCE("Too many verts!\n");
158 if (ctx
->Array
.ElementArrayBufferObj
->Name
) {
159 /* use indices in the buffer object */
160 if (!ctx
->Array
.ElementArrayBufferObj
->Data
) {
161 _mesa_warning(ctx
, "DrawRangeElements with empty vertex elements buffer!");
164 /* actual address is the sum of pointers */
165 indices
= (const GLvoid
*)
166 ADD_POINTERS(ctx
->Array
.ElementArrayBufferObj
->Data
, (const GLubyte
*) c_indices
);
169 if (!_mesa_validate_DrawElements( ctx
, mode
, count
, type
, indices
))
172 FLUSH_CURRENT( ctx
, 0 );
174 fprintf(stderr, "dt at %s:\n", __FUNCTION__);
175 for(i=0; i < VERT_ATTRIB_MAX; i++){
176 fprintf(stderr, "dt %d:", i);
177 dump_dt(&rmesa->state.VB.AttribPtr[i], rmesa->state.VB.Count);
179 r300ReleaseDmaRegion(rmesa
, &rvb
, __FUNCTION__
);
182 case GL_UNSIGNED_BYTE
:
183 for (i
=0; i
< count
; i
++) {
184 if(((unsigned char *)indices
)[i
] < min
)
185 min
= ((unsigned char *)indices
)[i
];
186 if(((unsigned char *)indices
)[i
] > max
)
187 max
= ((unsigned char *)indices
)[i
];
192 r300AllocDmaRegion(rmesa
, &rvb
, count
* elt_size
, elt_size
);
193 rvb
.aos_offset
= GET_START(&rvb
);
194 ptr
= rvb
.address
+ rvb
.start
;
196 for (i
=0; i
< count
; i
++)
197 ((unsigned short int *)ptr
)[i
] = ((unsigned char *)indices
)[i
] - min
;
200 case GL_UNSIGNED_SHORT
:
201 for (i
=0; i
< count
; i
++) {
202 if(((unsigned short int *)indices
)[i
] < min
)
203 min
= ((unsigned short int *)indices
)[i
];
204 if(((unsigned short int *)indices
)[i
] > max
)
205 max
= ((unsigned short int *)indices
)[i
];
210 r300AllocDmaRegion(rmesa
, &rvb
, count
* elt_size
, elt_size
);
211 rvb
.aos_offset
= GET_START(&rvb
);
212 ptr
= rvb
.address
+ rvb
.start
;
214 for (i
=0; i
< count
; i
++)
215 ((unsigned short int *)ptr
)[i
] = ((unsigned short int *)indices
)[i
] - min
;
218 case GL_UNSIGNED_INT
:
219 for (i
=0; i
< count
; i
++) {
220 if(((unsigned int *)indices
)[i
] < min
)
221 min
= ((unsigned int *)indices
)[i
];
222 if(((unsigned int *)indices
)[i
] > max
)
223 max
= ((unsigned int *)indices
)[i
];
226 if (max
- min
<= 65535)
231 r300AllocDmaRegion(rmesa
, &rvb
, count
* elt_size
, elt_size
);
232 rvb
.aos_offset
= GET_START(&rvb
);
233 ptr
= rvb
.address
+ rvb
.start
;
236 if (max
- min
<= 65535)
237 for (i
=0; i
< count
; i
++)
238 ((unsigned short int *)ptr
)[i
] = ((unsigned int *)indices
)[i
] - min
;
240 for (i
=0; i
< count
; i
++)
241 ((unsigned int *)ptr
)[i
] = ((unsigned int *)indices
)[i
] - min
;
245 WARN_ONCE("Unknown elt type!\n");
250 _mesa_update_state( ctx
);
252 for (i
=_TNL_ATTRIB_MAT_FRONT_AMBIENT
; i
< _TNL_ATTRIB_INDEX
; i
++) {
253 rmesa
->temp_attrib
[i
] = TNL_CONTEXT(ctx
)->vb
.AttribPtr
[i
];
254 TNL_CONTEXT(ctx
)->vb
.AttribPtr
[i
] = &rmesa
->dummy_attrib
[i
];
256 r300UpdateShaders(rmesa
);
257 for (i
=_TNL_ATTRIB_MAT_FRONT_AMBIENT
; i
< _TNL_ATTRIB_INDEX
; i
++) {
258 TNL_CONTEXT(ctx
)->vb
.AttribPtr
[i
] = rmesa
->temp_attrib
[i
];
261 if (rmesa
->state
.VB
.LockCount
) {
262 if (rmesa
->state
.VB
.lock_uptodate
== GL_FALSE
) {
263 if (setup_arrays(rmesa
, rmesa
->state
.VB
.LockFirst
))
266 rmesa
->state
.VB
.Count
= rmesa
->state
.VB
.LockCount
;
268 r300ReleaseArrays(ctx
);
269 r300EmitArraysVtx(ctx
, GL_FALSE
);
271 rmesa
->state
.VB
.lock_uptodate
= GL_TRUE
;
274 if (min
< rmesa
->state
.VB
.LockFirst
) {
275 WARN_ONCE("Out of range min %d vs %d!\n", min
, rmesa
->state
.VB
.LockFirst
);
279 if (max
>= rmesa
->state
.VB
.LockFirst
+ rmesa
->state
.VB
.LockCount
) {
280 WARN_ONCE("Out of range max %d vs %d!\n", max
, rmesa
->state
.VB
.LockFirst
+
281 rmesa
->state
.VB
.LockCount
);
285 if (setup_arrays(rmesa
, min
))
288 rmesa
->state
.VB
.Count
= max
- min
+ 1;
291 r300UpdateShaderStates(rmesa
);
293 rmesa
->state
.VB
.Primitive
= &prim
;
294 rmesa
->state
.VB
.PrimitiveCount
= 1;
296 prim
.mode
= mode
| PRIM_BEGIN
| PRIM_END
;
297 if (rmesa
->state
.VB
.LockCount
)
298 prim
.start
= min
- rmesa
->state
.VB
.LockFirst
;
303 rmesa
->state
.VB
.Elts
= ptr
;
304 rmesa
->state
.VB
.elt_size
= elt_size
;
306 r300_run_vb_render_vtxfmt_a(ctx
, NULL
);
309 radeon_mm_use(rmesa
, rvb
.buf
->id
);
314 _tnl_array_init(ctx
);
315 _mesa_install_exec_vtxfmt( ctx
, &TNL_CONTEXT(ctx
)->exec_vtxfmt
);
316 CALL_DrawElements(GET_DISPATCH(), (mode
, count
, type
, c_indices
));
317 radeon_init_vtxfmt_a(rmesa
);
318 _mesa_install_exec_vtxfmt( ctx
, &TNL_CONTEXT(ctx
)->exec_vtxfmt
);
321 void radeonDrawRangeElements(GLenum mode
, GLuint min
, GLuint max
, GLsizei count
, GLenum type
, const GLvoid
*c_indices
)
323 GET_CURRENT_CONTEXT(ctx
);
324 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
325 struct tnl_prim prim
;
329 static struct r300_dma_region rvb
;
333 WARN_ONCE("Too many verts!\n");
337 if (ctx
->Array
.ElementArrayBufferObj
->Name
) {
338 /* use indices in the buffer object */
339 if (!ctx
->Array
.ElementArrayBufferObj
->Data
) {
340 _mesa_warning(ctx
, "DrawRangeElements with empty vertex elements buffer!");
343 /* actual address is the sum of pointers */
344 indices
= (const GLvoid
*)
345 ADD_POINTERS(ctx
->Array
.ElementArrayBufferObj
->Data
, (const GLubyte
*) c_indices
);
348 if (!_mesa_validate_DrawRangeElements( ctx
, mode
, min
, max
, count
, type
, indices
))
351 FLUSH_CURRENT( ctx
, 0 );
355 r300ReleaseDmaRegion(rmesa
, &rvb
, __FUNCTION__
);
358 case GL_UNSIGNED_BYTE
:
361 r300AllocDmaRegion(rmesa
, &rvb
, count
* elt_size
, elt_size
);
362 rvb
.aos_offset
= GET_START(&rvb
);
363 ptr
= rvb
.address
+ rvb
.start
;
365 for(i
=0; i
< count
; i
++)
366 ((unsigned short int *)ptr
)[i
] = ((unsigned char *)indices
)[i
] - min
;
369 case GL_UNSIGNED_SHORT
:
373 if (min
== 0 && ctx
->Array
.ElementArrayBufferObj
->Name
){
378 r300AllocDmaRegion(rmesa
, &rvb
, count
* elt_size
, elt_size
);
379 rvb
.aos_offset
= GET_START(&rvb
);
380 ptr
= rvb
.address
+ rvb
.start
;
382 for(i
=0; i
< count
; i
++)
383 ((unsigned short int *)ptr
)[i
] = ((unsigned short int *)indices
)[i
] - min
;
386 case GL_UNSIGNED_INT
:
387 if (max
- min
<= 65535)
392 r300AllocDmaRegion(rmesa
, &rvb
, count
* elt_size
, elt_size
);
393 rvb
.aos_offset
= GET_START(&rvb
);
394 ptr
= rvb
.address
+ rvb
.start
;
396 if (max
- min
<= 65535)
397 for (i
=0; i
< count
; i
++)
398 ((unsigned short int *)ptr
)[i
] = ((unsigned int *)indices
)[i
] - min
;
400 for (i
=0; i
< count
; i
++)
401 ((unsigned int *)ptr
)[i
] = ((unsigned int *)indices
)[i
] - min
;
405 WARN_ONCE("Unknown elt type!\n");
409 /* XXX: setup_arrays before state update? */
412 _mesa_update_state( ctx
);
414 for (i
=_TNL_ATTRIB_MAT_FRONT_AMBIENT
; i
< _TNL_ATTRIB_INDEX
; i
++) {
415 rmesa
->temp_attrib
[i
] = TNL_CONTEXT(ctx
)->vb
.AttribPtr
[i
];
416 TNL_CONTEXT(ctx
)->vb
.AttribPtr
[i
] = &rmesa
->dummy_attrib
[i
];
418 r300UpdateShaders(rmesa
);
419 for (i
=_TNL_ATTRIB_MAT_FRONT_AMBIENT
; i
< _TNL_ATTRIB_INDEX
; i
++) {
420 TNL_CONTEXT(ctx
)->vb
.AttribPtr
[i
] = rmesa
->temp_attrib
[i
];
423 if (rmesa
->state
.VB
.LockCount
) {
424 if (rmesa
->state
.VB
.lock_uptodate
== GL_FALSE
) {
425 if (setup_arrays(rmesa
, rmesa
->state
.VB
.LockFirst
))
428 rmesa
->state
.VB
.Count
= rmesa
->state
.VB
.LockCount
;
430 r300ReleaseArrays(ctx
);
431 r300EmitArraysVtx(ctx
, GL_FALSE
);
433 rmesa
->state
.VB
.lock_uptodate
= GL_TRUE
;
436 if (min
< rmesa
->state
.VB
.LockFirst
) {
437 WARN_ONCE("Out of range min %d vs %d!\n", min
, rmesa
->state
.VB
.LockFirst
);
441 /*if (max >= rmesa->state.VB.LockFirst + rmesa->state.VB.LockCount) {
442 WARN_ONCE("Out of range max %d vs %d!\n", max, rmesa->state.VB.LockFirst +
443 rmesa->state.VB.LockCount);
447 if (setup_arrays(rmesa
, min
))
450 rmesa
->state
.VB
.Count
= max
- min
+ 1;
453 r300UpdateShaderStates(rmesa
);
455 rmesa
->state
.VB
.Primitive
= &prim
;
456 rmesa
->state
.VB
.PrimitiveCount
= 1;
458 prim
.mode
= mode
| PRIM_BEGIN
| PRIM_END
;
459 if (rmesa
->state
.VB
.LockCount
)
460 prim
.start
= min
- rmesa
->state
.VB
.LockFirst
;
465 rmesa
->state
.VB
.Elts
= ptr
;
466 rmesa
->state
.VB
.elt_size
= elt_size
;
467 rmesa
->state
.VB
.elt_min
= min
;
468 rmesa
->state
.VB
.elt_max
= max
;
470 r300_run_vb_render_vtxfmt_a(ctx
, NULL
);
473 radeon_mm_use(rmesa
, rvb
.buf
->id
);
478 _tnl_array_init(ctx
);
479 _mesa_install_exec_vtxfmt( ctx
, &TNL_CONTEXT(ctx
)->exec_vtxfmt
);
480 CALL_DrawRangeElements(GET_DISPATCH(), (mode
, min
, max
, count
, type
, c_indices
));
481 radeon_init_vtxfmt_a(rmesa
);
482 _mesa_install_exec_vtxfmt( ctx
, &TNL_CONTEXT(ctx
)->exec_vtxfmt
);
485 void radeonDrawArrays( GLenum mode
, GLint start
, GLsizei count
)
487 GET_CURRENT_CONTEXT(ctx
);
488 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
489 struct tnl_prim prim
;
493 WARN_ONCE("Too many verts!\n");
497 if (!_mesa_validate_DrawArrays( ctx
, mode
, start
, count
))
500 FLUSH_CURRENT( ctx
, 0 );
503 _mesa_update_state( ctx
);
505 /* XXX: setup_arrays before state update? */
507 for (i
=_TNL_ATTRIB_MAT_FRONT_AMBIENT
; i
< _TNL_ATTRIB_INDEX
; i
++) {
508 rmesa
->temp_attrib
[i
] = TNL_CONTEXT(ctx
)->vb
.AttribPtr
[i
];
509 TNL_CONTEXT(ctx
)->vb
.AttribPtr
[i
] = &rmesa
->dummy_attrib
[i
];
511 r300UpdateShaders(rmesa
);
512 for (i
=_TNL_ATTRIB_MAT_FRONT_AMBIENT
; i
< _TNL_ATTRIB_INDEX
; i
++) {
513 TNL_CONTEXT(ctx
)->vb
.AttribPtr
[i
] = rmesa
->temp_attrib
[i
];
516 if (rmesa
->state
.VB
.LockCount
) {
517 if (rmesa
->state
.VB
.lock_uptodate
== GL_FALSE
) {
518 if (setup_arrays(rmesa
, rmesa
->state
.VB
.LockFirst
))
521 rmesa
->state
.VB
.Count
= rmesa
->state
.VB
.LockCount
;
523 r300ReleaseArrays(ctx
);
524 r300EmitArraysVtx(ctx
, GL_FALSE
);
526 rmesa
->state
.VB
.lock_uptodate
= GL_TRUE
;
529 if (start
< rmesa
->state
.VB
.LockFirst
) {
530 WARN_ONCE("Out of range min %d vs %d!\n", start
, rmesa
->state
.VB
.LockFirst
);
534 if (start
+ count
- 1 >= rmesa
->state
.VB
.LockFirst
+ rmesa
->state
.VB
.LockCount
) { /* XXX */
535 WARN_ONCE("Out of range max %d vs %d!\n", start
+ count
- 1, rmesa
->state
.VB
.LockFirst
+
536 rmesa
->state
.VB
.LockCount
);
540 if (setup_arrays(rmesa
, start
))
543 rmesa
->state
.VB
.Count
= count
;
546 r300UpdateShaderStates(rmesa
);
548 rmesa
->state
.VB
.Primitive
= &prim
;
549 rmesa
->state
.VB
.PrimitiveCount
= 1;
551 prim
.mode
= mode
| PRIM_BEGIN
| PRIM_END
;
552 if (rmesa
->state
.VB
.LockCount
)
553 prim
.start
= start
- rmesa
->state
.VB
.LockFirst
;
558 rmesa
->state
.VB
.Elts
= NULL
;
559 rmesa
->state
.VB
.elt_size
= 0;
560 rmesa
->state
.VB
.elt_min
= 0;
561 rmesa
->state
.VB
.elt_max
= 0;
563 r300_run_vb_render_vtxfmt_a(ctx
, NULL
);
568 _tnl_array_init(ctx
);
569 _mesa_install_exec_vtxfmt( ctx
, &TNL_CONTEXT(ctx
)->exec_vtxfmt
);
570 CALL_DrawArrays(GET_DISPATCH(), (mode
, start
, count
));
571 radeon_init_vtxfmt_a(rmesa
);
572 _mesa_install_exec_vtxfmt( ctx
, &TNL_CONTEXT(ctx
)->exec_vtxfmt
);
575 void radeon_init_vtxfmt_a(r300ContextPtr rmesa
)
578 GLvertexformat
*vfmt
;
580 ctx
= rmesa
->radeon
.glCtx
;
581 vfmt
= ctx
->TnlModule
.Current
;
583 vfmt
->DrawElements
= radeonDrawElements
;
584 vfmt
->DrawArrays
= radeonDrawArrays
;
585 vfmt
->DrawRangeElements
= radeonDrawRangeElements
;
592 void radeonLockArraysEXT(GLcontext
*ctx
, GLint first
, GLsizei count
)
594 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
597 /* Only when CB_DPATH is defined.
598 r300Clear tampers over the aos setup without it.
599 (r300ResetHwState cannot call r300EmitArrays)
602 first
= 0; count
= 0;
605 if (first
< 0 || count
<= 0) {
606 rmesa
->state
.VB
.LockFirst
= 0;
607 rmesa
->state
.VB
.LockCount
= 0;
608 rmesa
->state
.VB
.lock_uptodate
= GL_FALSE
;
612 rmesa
->state
.VB
.LockFirst
= first
;
613 rmesa
->state
.VB
.LockCount
= count
;
614 rmesa
->state
.VB
.lock_uptodate
= GL_FALSE
;
617 void radeonUnlockArraysEXT(GLcontext
*ctx
)
619 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
621 rmesa
->state
.VB
.LockFirst
= 0;
622 rmesa
->state
.VB
.LockCount
= 0;
623 rmesa
->state
.VB
.lock_uptodate
= GL_FALSE
;
626 struct gl_buffer_object
*
627 r300NewBufferObject(GLcontext
*ctx
, GLuint name
, GLenum target
)
629 struct r300_buffer_object
*obj
;
633 obj
= MALLOC_STRUCT(r300_buffer_object
);
634 _mesa_initialize_buffer_object(&obj
->mesa_obj
, name
, target
);
635 return &obj
->mesa_obj
;
638 void r300BufferData(GLcontext
*ctx
, GLenum target
, GLsizeiptrARB size
,
639 const GLvoid
*data
, GLenum usage
, struct gl_buffer_object
*obj
)
641 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
642 struct r300_buffer_object
*r300_obj
= (struct r300_buffer_object
*)obj
;
643 drm_radeon_mem_alloc_t alloc
;
646 /* Free previous buffer */
648 radeon_mm_free(rmesa
, r300_obj
->id
);
649 obj
->OnCard
= GL_FALSE
;
652 _mesa_free(obj
->Data
);
657 if (target
== GL_ELEMENT_ARRAY_BUFFER_ARB
) {
660 obj
->Data
= malloc(size
);
663 _mesa_memcpy(obj
->Data
, data
, size
);
665 obj
->OnCard
= GL_FALSE
;
667 r300_obj
->id
= radeon_mm_alloc(rmesa
, 4, size
);
668 if (r300_obj
->id
== 0)
671 obj
->Data
= radeon_mm_map(rmesa
, r300_obj
->id
, RADEON_MM_W
);
674 _mesa_memcpy(obj
->Data
, data
, size
);
676 radeon_mm_unmap(rmesa
, r300_obj
->id
);
677 obj
->OnCard
= GL_TRUE
;
684 void r300BufferSubData(GLcontext
*ctx
, GLenum target
, GLintptrARB offset
,
685 GLsizeiptrARB size
, const GLvoid
* data
, struct gl_buffer_object
* bufObj
)
687 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
688 struct r300_buffer_object
*r300_obj
= (struct r300_buffer_object
*)bufObj
;
689 (void) ctx
; (void) target
;
692 if (bufObj
->Data
&& ((GLuint
) (size
+ offset
) <= bufObj
->Size
)) {
694 ptr
= radeon_mm_map(rmesa
, r300_obj
->id
, RADEON_MM_W
);
696 _mesa_memcpy( (GLubyte
*) ptr
+ offset
, data
, size
);
698 radeon_mm_unmap(rmesa
, r300_obj
->id
);
700 _mesa_memcpy( (GLubyte
*) bufObj
->Data
+ offset
, data
, size
);
705 void *r300MapBuffer(GLcontext
*ctx
, GLenum target
, GLenum access
,
706 struct gl_buffer_object
*bufObj
)
708 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
709 struct r300_buffer_object
*r300_obj
= (struct r300_buffer_object
*)bufObj
;
714 //ASSERT(!bufObj->OnCard);
715 /* Just return a direct pointer to the data */
716 if (bufObj
->Pointer
) {
717 /* already mapped! */
721 if (!bufObj
->OnCard
) {
722 bufObj
->Pointer
= bufObj
->Data
;
723 return bufObj
->Pointer
;
728 bufObj
->Pointer
= radeon_mm_map(rmesa
, r300_obj
->id
, RADEON_MM_R
);
732 bufObj
->Pointer
= radeon_mm_map(rmesa
, r300_obj
->id
, RADEON_MM_W
);
736 bufObj
->Pointer
= radeon_mm_map(rmesa
, r300_obj
->id
, RADEON_MM_RW
);
740 WARN_ONCE("Unknown access type\n");
741 bufObj
->Pointer
= NULL
;
745 return bufObj
->Pointer
;
748 GLboolean
r300UnmapBuffer(GLcontext
*ctx
, GLenum target
, struct gl_buffer_object
*bufObj
)
750 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
751 struct r300_buffer_object
*r300_obj
= (struct r300_buffer_object
*)bufObj
;
755 //ASSERT(!bufObj->OnCard);
756 /* XXX we might assert here that bufObj->Pointer is non-null */
757 if (!bufObj
->OnCard
) {
758 bufObj
->Pointer
= NULL
;
761 radeon_mm_unmap(rmesa
, r300_obj
->id
);
763 bufObj
->Pointer
= NULL
;
767 void r300DeleteBuffer(GLcontext
*ctx
, struct gl_buffer_object
*obj
)
769 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
770 struct r300_buffer_object
*r300_obj
= (struct r300_buffer_object
*)obj
;
773 radeon_mm_free(rmesa
, r300_obj
->id
);
776 _mesa_delete_buffer_object(ctx
, obj
);
779 void r300_init_vbo_funcs(struct dd_function_table
*functions
)
781 functions
->NewBufferObject
= r300NewBufferObject
;
782 functions
->BufferData
= r300BufferData
;
783 functions
->BufferSubData
= r300BufferSubData
;
784 functions
->MapBuffer
= r300MapBuffer
;
785 functions
->UnmapBuffer
= r300UnmapBuffer
;
786 functions
->DeleteBuffer
= r300DeleteBuffer
;
788 /*functions->LockArraysEXT = radeonLockArraysEXT;
789 functions->UnlockArraysEXT = radeonUnlockArraysEXT;*/