Merge branch 'new-frag-attribs'
[mesa.git] / src / mesa / drivers / dri / radeon / radeon_common_context.c
1 /**************************************************************************
2
3 Copyright 2000, 2001 ATI Technologies Inc., Ontario, Canada, and
4 VA Linux Systems Inc., Fremont, California.
5 Copyright (C) The Weather Channel, Inc. 2002. All Rights Reserved.
6
7 The Weather Channel (TM) funded Tungsten Graphics to develop the
8 initial release of the Radeon 8500 driver under the XFree86 license.
9 This notice must be preserved.
10
11 All Rights Reserved.
12
13 Permission is hereby granted, free of charge, to any person obtaining
14 a copy of this software and associated documentation files (the
15 "Software"), to deal in the Software without restriction, including
16 without limitation the rights to use, copy, modify, merge, publish,
17 distribute, sublicense, and/or sell copies of the Software, and to
18 permit persons to whom the Software is furnished to do so, subject to
19 the following conditions:
20
21 The above copyright notice and this permission notice (including the
22 next paragraph) shall be included in all copies or substantial
23 portions of the Software.
24
25 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
26 EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
27 MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
28 IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE
29 LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
30 OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
31 WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
32
33 **************************************************************************/
34
35 #include "radeon_common.h"
36 #include "xmlpool.h" /* for symbolic values of enum-type options */
37 #include "utils.h"
38 #include "vblank.h"
39 #include "drirenderbuffer.h"
40 #include "main/context.h"
41 #include "main/framebuffer.h"
42 #include "main/renderbuffer.h"
43 #include "main/state.h"
44 #include "main/simple_list.h"
45 #include "swrast/swrast.h"
46 #include "swrast_setup/swrast_setup.h"
47 #include "tnl/tnl.h"
48
49 #if RADEON_COMMON && defined(RADEON_COMMON_FOR_R600) /* +r6/r7 */
50 #include "r600_context.h"
51 #endif
52
53 #define DRIVER_DATE "20090101"
54
55 #ifndef RADEON_DEBUG
56 int RADEON_DEBUG = (0);
57 #endif
58
59
60 static const char* get_chip_family_name(int chip_family)
61 {
62 switch(chip_family) {
63 case CHIP_FAMILY_R100: return "R100";
64 case CHIP_FAMILY_RV100: return "RV100";
65 case CHIP_FAMILY_RS100: return "RS100";
66 case CHIP_FAMILY_RV200: return "RV200";
67 case CHIP_FAMILY_RS200: return "RS200";
68 case CHIP_FAMILY_R200: return "R200";
69 case CHIP_FAMILY_RV250: return "RV250";
70 case CHIP_FAMILY_RS300: return "RS300";
71 case CHIP_FAMILY_RV280: return "RV280";
72 case CHIP_FAMILY_R300: return "R300";
73 case CHIP_FAMILY_R350: return "R350";
74 case CHIP_FAMILY_RV350: return "RV350";
75 case CHIP_FAMILY_RV380: return "RV380";
76 case CHIP_FAMILY_R420: return "R420";
77 case CHIP_FAMILY_RV410: return "RV410";
78 case CHIP_FAMILY_RS400: return "RS400";
79 case CHIP_FAMILY_RS600: return "RS600";
80 case CHIP_FAMILY_RS690: return "RS690";
81 case CHIP_FAMILY_RS740: return "RS740";
82 case CHIP_FAMILY_RV515: return "RV515";
83 case CHIP_FAMILY_R520: return "R520";
84 case CHIP_FAMILY_RV530: return "RV530";
85 case CHIP_FAMILY_R580: return "R580";
86 case CHIP_FAMILY_RV560: return "RV560";
87 case CHIP_FAMILY_RV570: return "RV570";
88 case CHIP_FAMILY_R600: return "R600";
89 case CHIP_FAMILY_RV610: return "RV610";
90 case CHIP_FAMILY_RV630: return "RV630";
91 case CHIP_FAMILY_RV670: return "RV670";
92 case CHIP_FAMILY_RV620: return "RV620";
93 case CHIP_FAMILY_RV635: return "RV635";
94 case CHIP_FAMILY_RS780: return "RS780";
95 case CHIP_FAMILY_RV770: return "RV770";
96 case CHIP_FAMILY_RV730: return "RV730";
97 case CHIP_FAMILY_RV710: return "RV710";
98 case CHIP_FAMILY_RV740: return "RV740";
99 default: return "unknown";
100 }
101 }
102
103
104 /* Return various strings for glGetString().
105 */
106 static const GLubyte *radeonGetString(GLcontext * ctx, GLenum name)
107 {
108 radeonContextPtr radeon = RADEON_CONTEXT(ctx);
109 static char buffer[128];
110
111 switch (name) {
112 case GL_VENDOR:
113 if (IS_R600_CLASS(radeon->radeonScreen))
114 return (GLubyte *) "Advanced Micro Devices, Inc.";
115 else if (IS_R300_CLASS(radeon->radeonScreen))
116 return (GLubyte *) "DRI R300 Project";
117 else
118 return (GLubyte *) "Tungsten Graphics, Inc.";
119
120 case GL_RENDERER:
121 {
122 unsigned offset;
123 GLuint agp_mode = (radeon->radeonScreen->card_type==RADEON_CARD_PCI) ? 0 :
124 radeon->radeonScreen->AGPMode;
125 const char* chipclass;
126 char hardwarename[32];
127
128 if (IS_R600_CLASS(radeon->radeonScreen))
129 chipclass = "R600";
130 else if (IS_R300_CLASS(radeon->radeonScreen))
131 chipclass = "R300";
132 else if (IS_R200_CLASS(radeon->radeonScreen))
133 chipclass = "R200";
134 else
135 chipclass = "R100";
136
137 sprintf(hardwarename, "%s (%s %04X)",
138 chipclass,
139 get_chip_family_name(radeon->radeonScreen->chip_family),
140 radeon->radeonScreen->device_id);
141
142 offset = driGetRendererString(buffer, hardwarename, DRIVER_DATE,
143 agp_mode);
144
145 if (IS_R600_CLASS(radeon->radeonScreen)) {
146 sprintf(&buffer[offset], " TCL");
147 } else if (IS_R300_CLASS(radeon->radeonScreen)) {
148 sprintf(&buffer[offset], " %sTCL",
149 (radeon->radeonScreen->chip_flags & RADEON_CHIPSET_TCL)
150 ? "" : "NO-");
151 } else {
152 sprintf(&buffer[offset], " %sTCL",
153 !(radeon->TclFallback & RADEON_TCL_FALLBACK_TCL_DISABLE)
154 ? "" : "NO-");
155 }
156
157 if (radeon->radeonScreen->driScreen->dri2.enabled)
158 strcat(buffer, " DRI2");
159
160 return (GLubyte *) buffer;
161 }
162
163 default:
164 return NULL;
165 }
166 }
167
168 /* Initialize the driver's misc functions.
169 */
170 static void radeonInitDriverFuncs(struct dd_function_table *functions)
171 {
172 functions->GetString = radeonGetString;
173 }
174
175 /**
176 * Create and initialize all common fields of the context,
177 * including the Mesa context itself.
178 */
179 GLboolean radeonInitContext(radeonContextPtr radeon,
180 struct dd_function_table* functions,
181 const __GLcontextModes * glVisual,
182 __DRIcontextPrivate * driContextPriv,
183 void *sharedContextPrivate)
184 {
185 __DRIscreenPrivate *sPriv = driContextPriv->driScreenPriv;
186 radeonScreenPtr screen = (radeonScreenPtr) (sPriv->private);
187 GLcontext* ctx;
188 GLcontext* shareCtx;
189 int fthrottle_mode;
190
191 /* Fill in additional standard functions. */
192 radeonInitDriverFuncs(functions);
193
194 radeon->radeonScreen = screen;
195 /* Allocate and initialize the Mesa context */
196 if (sharedContextPrivate)
197 shareCtx = ((radeonContextPtr)sharedContextPrivate)->glCtx;
198 else
199 shareCtx = NULL;
200 radeon->glCtx = _mesa_create_context(glVisual, shareCtx,
201 functions, (void *)radeon);
202 if (!radeon->glCtx)
203 return GL_FALSE;
204
205 ctx = radeon->glCtx;
206 driContextPriv->driverPrivate = radeon;
207
208 meta_init_metaops(ctx, &radeon->meta);
209 /* DRI fields */
210 radeon->dri.context = driContextPriv;
211 radeon->dri.screen = sPriv;
212 radeon->dri.hwContext = driContextPriv->hHWContext;
213 radeon->dri.hwLock = &sPriv->pSAREA->lock;
214 radeon->dri.hwLockCount = 0;
215 radeon->dri.fd = sPriv->fd;
216 radeon->dri.drmMinor = sPriv->drm_version.minor;
217
218 radeon->sarea = (drm_radeon_sarea_t *) ((GLubyte *) sPriv->pSAREA +
219 screen->sarea_priv_offset);
220
221 /* Setup IRQs */
222 fthrottle_mode = driQueryOptioni(&radeon->optionCache, "fthrottle_mode");
223 radeon->iw.irq_seq = -1;
224 radeon->irqsEmitted = 0;
225 if (IS_R600_CLASS(radeon->radeonScreen))
226 radeon->do_irqs = 0;
227 else
228 radeon->do_irqs = (fthrottle_mode == DRI_CONF_FTHROTTLE_IRQS &&
229 radeon->radeonScreen->irq);
230
231 radeon->do_usleeps = (fthrottle_mode == DRI_CONF_FTHROTTLE_USLEEPS);
232
233 if (!radeon->do_irqs)
234 fprintf(stderr,
235 "IRQ's not enabled, falling back to %s: %d %d\n",
236 radeon->do_usleeps ? "usleeps" : "busy waits",
237 fthrottle_mode, radeon->radeonScreen->irq);
238
239 radeon->texture_depth = driQueryOptioni (&radeon->optionCache,
240 "texture_depth");
241 if (radeon->texture_depth == DRI_CONF_TEXTURE_DEPTH_FB)
242 radeon->texture_depth = ( glVisual->rgbBits > 16 ) ?
243 DRI_CONF_TEXTURE_DEPTH_32 : DRI_CONF_TEXTURE_DEPTH_16;
244
245 if (IS_R600_CLASS(radeon->radeonScreen)) {
246 radeon->texture_row_align = 256;
247 radeon->texture_rect_row_align = 256;
248 radeon->texture_compressed_row_align = 256;
249 } else if (IS_R200_CLASS(radeon->radeonScreen) ||
250 IS_R100_CLASS(radeon->radeonScreen)) {
251 radeon->texture_row_align = 32;
252 radeon->texture_rect_row_align = 64;
253 radeon->texture_compressed_row_align = 32;
254 } else { /* R300 - not sure this is all correct */
255 int chip_family = radeon->radeonScreen->chip_family;
256 if (chip_family == CHIP_FAMILY_RS600 ||
257 chip_family == CHIP_FAMILY_RS690 ||
258 chip_family == CHIP_FAMILY_RS740)
259 radeon->texture_row_align = 64;
260 else
261 radeon->texture_row_align = 32;
262 radeon->texture_rect_row_align = 64;
263 radeon->texture_compressed_row_align = 64;
264 }
265
266 return GL_TRUE;
267 }
268
269
270
271 /**
272 * Destroy the command buffer and state atoms.
273 */
274 static void radeon_destroy_atom_list(radeonContextPtr radeon)
275 {
276 struct radeon_state_atom *atom;
277
278 foreach(atom, &radeon->hw.atomlist) {
279 FREE(atom->cmd);
280 if (atom->lastcmd)
281 FREE(atom->lastcmd);
282 }
283
284 }
285
286 /**
287 * Cleanup common context fields.
288 * Called by r200DestroyContext/r300DestroyContext
289 */
290 void radeonDestroyContext(__DRIcontextPrivate *driContextPriv )
291 {
292 #ifdef RADEON_BO_TRACK
293 FILE *track;
294 #endif
295 GET_CURRENT_CONTEXT(ctx);
296 radeonContextPtr radeon = (radeonContextPtr) driContextPriv->driverPrivate;
297 radeonContextPtr current = ctx ? RADEON_CONTEXT(ctx) : NULL;
298 #if RADEON_COMMON && defined(RADEON_COMMON_FOR_R600) /* +r6/r7 */
299 __DRIscreenPrivate *sPriv = driContextPriv->driScreenPriv;
300 radeonScreenPtr screen = (radeonScreenPtr) (sPriv->private);
301 #endif
302
303 if (radeon == current) {
304 radeon_firevertices(radeon);
305 _mesa_make_current(NULL, NULL, NULL);
306 }
307
308 assert(radeon);
309 if (radeon) {
310 if (radeon->dma.current) {
311 rcommonFlushCmdBuf( radeon, __FUNCTION__ );
312 }
313
314 radeonReleaseArrays(radeon->glCtx, ~0);
315 meta_destroy_metaops(&radeon->meta);
316 if (radeon->vtbl.free_context)
317 radeon->vtbl.free_context(radeon->glCtx);
318 _swsetup_DestroyContext( radeon->glCtx );
319 _tnl_DestroyContext( radeon->glCtx );
320 _vbo_DestroyContext( radeon->glCtx );
321 _swrast_DestroyContext( radeon->glCtx );
322
323 /* free atom list */
324 /* free the Mesa context */
325 _mesa_destroy_context(radeon->glCtx);
326
327 /* _mesa_destroy_context() might result in calls to functions that
328 * depend on the DriverCtx, so don't set it to NULL before.
329 *
330 * radeon->glCtx->DriverCtx = NULL;
331 */
332 /* free the option cache */
333 driDestroyOptionCache(&radeon->optionCache);
334
335 rcommonDestroyCmdBuf(radeon);
336
337 #if RADEON_COMMON && defined(RADEON_COMMON_FOR_R600) /* +r6/r7 */
338 if (!IS_R600_CLASS(screen))
339 #endif
340 radeon_destroy_atom_list(radeon);
341
342 if (radeon->state.scissor.pClipRects) {
343 FREE(radeon->state.scissor.pClipRects);
344 radeon->state.scissor.pClipRects = 0;
345 }
346 }
347 #ifdef RADEON_BO_TRACK
348 track = fopen("/tmp/tracklog", "w");
349 if (track) {
350 radeon_tracker_print(&radeon->radeonScreen->bom->tracker, track);
351 fclose(track);
352 }
353 #endif
354 FREE(radeon);
355 }
356
357 /* Force the context `c' to be unbound from its buffer.
358 */
359 GLboolean radeonUnbindContext(__DRIcontextPrivate * driContextPriv)
360 {
361 radeonContextPtr radeon = (radeonContextPtr) driContextPriv->driverPrivate;
362
363 if (RADEON_DEBUG & DEBUG_DRI)
364 fprintf(stderr, "%s ctx %p\n", __FUNCTION__,
365 radeon->glCtx);
366
367 return GL_TRUE;
368 }
369
370
371 static void
372 radeon_make_kernel_renderbuffer_current(radeonContextPtr radeon,
373 struct radeon_framebuffer *draw)
374 {
375 /* if radeon->fake */
376 struct radeon_renderbuffer *rb;
377
378 if ((rb = (void *)draw->base.Attachment[BUFFER_FRONT_LEFT].Renderbuffer)) {
379 if (!rb->bo) {
380 #ifdef RADEON_DEBUG_BO
381 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
382 radeon->radeonScreen->frontOffset,
383 0,
384 0,
385 RADEON_GEM_DOMAIN_VRAM,
386 0,
387 "Front Buf");
388 #else
389 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
390 radeon->radeonScreen->frontOffset,
391 0,
392 0,
393 RADEON_GEM_DOMAIN_VRAM,
394 0);
395 #endif /* RADEON_DEBUG_BO */
396 }
397 rb->cpp = radeon->radeonScreen->cpp;
398 rb->pitch = radeon->radeonScreen->frontPitch * rb->cpp;
399 }
400 if ((rb = (void *)draw->base.Attachment[BUFFER_BACK_LEFT].Renderbuffer)) {
401 if (!rb->bo) {
402 #ifdef RADEON_DEBUG_BO
403 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
404 radeon->radeonScreen->backOffset,
405 0,
406 0,
407 RADEON_GEM_DOMAIN_VRAM,
408 0,
409 "Back Buf");
410 #else
411 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
412 radeon->radeonScreen->backOffset,
413 0,
414 0,
415 RADEON_GEM_DOMAIN_VRAM,
416 0);
417 #endif /* RADEON_DEBUG_BO */
418 }
419 rb->cpp = radeon->radeonScreen->cpp;
420 rb->pitch = radeon->radeonScreen->backPitch * rb->cpp;
421 }
422 if ((rb = (void *)draw->base.Attachment[BUFFER_DEPTH].Renderbuffer)) {
423 if (!rb->bo) {
424 #ifdef RADEON_DEBUG_BO
425 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
426 radeon->radeonScreen->depthOffset,
427 0,
428 0,
429 RADEON_GEM_DOMAIN_VRAM,
430 0,
431 "Z Buf");
432 #else
433 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
434 radeon->radeonScreen->depthOffset,
435 0,
436 0,
437 RADEON_GEM_DOMAIN_VRAM,
438 0);
439 #endif /* RADEON_DEBUG_BO */
440 }
441 rb->cpp = radeon->radeonScreen->cpp;
442 rb->pitch = radeon->radeonScreen->depthPitch * rb->cpp;
443 }
444 if ((rb = (void *)draw->base.Attachment[BUFFER_STENCIL].Renderbuffer)) {
445 if (!rb->bo) {
446 #ifdef RADEON_DEBUG_BO
447 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
448 radeon->radeonScreen->depthOffset,
449 0,
450 0,
451 RADEON_GEM_DOMAIN_VRAM,
452 0,
453 "Stencil Buf");
454 #else
455 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
456 radeon->radeonScreen->depthOffset,
457 0,
458 0,
459 RADEON_GEM_DOMAIN_VRAM,
460 0);
461 #endif /* RADEON_DEBUG_BO */
462 }
463 rb->cpp = radeon->radeonScreen->cpp;
464 rb->pitch = radeon->radeonScreen->depthPitch * rb->cpp;
465 }
466 }
467
468 static void
469 radeon_make_renderbuffer_current(radeonContextPtr radeon,
470 struct radeon_framebuffer *draw)
471 {
472 int size = 4096*4096*4;
473 /* if radeon->fake */
474 struct radeon_renderbuffer *rb;
475
476 if (radeon->radeonScreen->kernel_mm) {
477 radeon_make_kernel_renderbuffer_current(radeon, draw);
478 return;
479 }
480
481
482 if ((rb = (void *)draw->base.Attachment[BUFFER_FRONT_LEFT].Renderbuffer)) {
483 if (!rb->bo) {
484 #ifdef RADEON_DEBUG_BO
485 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
486 radeon->radeonScreen->frontOffset +
487 radeon->radeonScreen->fbLocation,
488 size,
489 4096,
490 RADEON_GEM_DOMAIN_VRAM,
491 0,
492 "Front Buf");
493 #else
494 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
495 radeon->radeonScreen->frontOffset +
496 radeon->radeonScreen->fbLocation,
497 size,
498 4096,
499 RADEON_GEM_DOMAIN_VRAM,
500 0);
501 #endif /* RADEON_DEBUG_BO */
502 }
503 rb->cpp = radeon->radeonScreen->cpp;
504 rb->pitch = radeon->radeonScreen->frontPitch * rb->cpp;
505 }
506 if ((rb = (void *)draw->base.Attachment[BUFFER_BACK_LEFT].Renderbuffer)) {
507 if (!rb->bo) {
508 #ifdef RADEON_DEBUG_BO
509 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
510 radeon->radeonScreen->backOffset +
511 radeon->radeonScreen->fbLocation,
512 size,
513 4096,
514 RADEON_GEM_DOMAIN_VRAM,
515 0,
516 "Back Buf");
517 #else
518 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
519 radeon->radeonScreen->backOffset +
520 radeon->radeonScreen->fbLocation,
521 size,
522 4096,
523 RADEON_GEM_DOMAIN_VRAM,
524 0);
525 #endif /* RADEON_DEBUG_BO */
526 }
527 rb->cpp = radeon->radeonScreen->cpp;
528 rb->pitch = radeon->radeonScreen->backPitch * rb->cpp;
529 }
530 if ((rb = (void *)draw->base.Attachment[BUFFER_DEPTH].Renderbuffer)) {
531 if (!rb->bo) {
532 #ifdef RADEON_DEBUG_BO
533 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
534 radeon->radeonScreen->depthOffset +
535 radeon->radeonScreen->fbLocation,
536 size,
537 4096,
538 RADEON_GEM_DOMAIN_VRAM,
539 0,
540 "Z Buf");
541 #else
542 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
543 radeon->radeonScreen->depthOffset +
544 radeon->radeonScreen->fbLocation,
545 size,
546 4096,
547 RADEON_GEM_DOMAIN_VRAM,
548 0);
549 #endif /* RADEON_DEBUG_BO */
550 }
551 rb->cpp = radeon->radeonScreen->cpp;
552 rb->pitch = radeon->radeonScreen->depthPitch * rb->cpp;
553 }
554 if ((rb = (void *)draw->base.Attachment[BUFFER_STENCIL].Renderbuffer)) {
555 if (!rb->bo) {
556 #ifdef RADEON_DEBUG_BO
557 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
558 radeon->radeonScreen->depthOffset +
559 radeon->radeonScreen->fbLocation,
560 size,
561 4096,
562 RADEON_GEM_DOMAIN_VRAM,
563 0,
564 "Stencil Buf");
565 #else
566 rb->bo = radeon_bo_open(radeon->radeonScreen->bom,
567 radeon->radeonScreen->depthOffset +
568 radeon->radeonScreen->fbLocation,
569 size,
570 4096,
571 RADEON_GEM_DOMAIN_VRAM,
572 0);
573 #endif /* RADEON_DEBUG_BO */
574 }
575 rb->cpp = radeon->radeonScreen->cpp;
576 rb->pitch = radeon->radeonScreen->depthPitch * rb->cpp;
577 }
578 }
579
580 static unsigned
581 radeon_bits_per_pixel(const struct radeon_renderbuffer *rb)
582 {
583 switch (rb->base._ActualFormat) {
584 case GL_RGB5:
585 case GL_DEPTH_COMPONENT16:
586 return 16;
587 case GL_RGB8:
588 case GL_RGBA8:
589 case GL_DEPTH_COMPONENT24:
590 case GL_DEPTH24_STENCIL8_EXT:
591 case GL_STENCIL_INDEX8_EXT:
592 return 32;
593 default:
594 return 0;
595 }
596 }
597
598 void
599 radeon_update_renderbuffers(__DRIcontext *context, __DRIdrawable *drawable)
600 {
601 unsigned int attachments[10];
602 __DRIbuffer *buffers = NULL;
603 __DRIscreen *screen;
604 struct radeon_renderbuffer *rb;
605 int i, count;
606 struct radeon_framebuffer *draw;
607 radeonContextPtr radeon;
608 char *regname;
609 struct radeon_bo *depth_bo = NULL, *bo;
610
611 if (RADEON_DEBUG & DEBUG_DRI)
612 fprintf(stderr, "enter %s, drawable %p\n", __func__, drawable);
613
614 draw = drawable->driverPrivate;
615 screen = context->driScreenPriv;
616 radeon = (radeonContextPtr) context->driverPrivate;
617
618 if (screen->dri2.loader
619 && (screen->dri2.loader->base.version > 2)
620 && (screen->dri2.loader->getBuffersWithFormat != NULL)) {
621 struct radeon_renderbuffer *depth_rb;
622 struct radeon_renderbuffer *stencil_rb;
623
624 i = 0;
625 if ((radeon->is_front_buffer_rendering ||
626 radeon->is_front_buffer_reading ||
627 !draw->color_rb[1])
628 && draw->color_rb[0]) {
629 attachments[i++] = __DRI_BUFFER_FRONT_LEFT;
630 attachments[i++] = radeon_bits_per_pixel(draw->color_rb[0]);
631 }
632
633 if (draw->color_rb[1]) {
634 attachments[i++] = __DRI_BUFFER_BACK_LEFT;
635 attachments[i++] = radeon_bits_per_pixel(draw->color_rb[1]);
636 }
637
638 depth_rb = radeon_get_renderbuffer(&draw->base, BUFFER_DEPTH);
639 stencil_rb = radeon_get_renderbuffer(&draw->base, BUFFER_STENCIL);
640
641 if ((depth_rb != NULL) && (stencil_rb != NULL)) {
642 attachments[i++] = __DRI_BUFFER_DEPTH_STENCIL;
643 attachments[i++] = radeon_bits_per_pixel(depth_rb);
644 } else if (depth_rb != NULL) {
645 attachments[i++] = __DRI_BUFFER_DEPTH;
646 attachments[i++] = radeon_bits_per_pixel(depth_rb);
647 } else if (stencil_rb != NULL) {
648 attachments[i++] = __DRI_BUFFER_STENCIL;
649 attachments[i++] = radeon_bits_per_pixel(stencil_rb);
650 }
651
652 buffers = (*screen->dri2.loader->getBuffersWithFormat)(drawable,
653 &drawable->w,
654 &drawable->h,
655 attachments, i / 2,
656 &count,
657 drawable->loaderPrivate);
658 } else if (screen->dri2.loader) {
659 i = 0;
660 if (draw->color_rb[0])
661 attachments[i++] = __DRI_BUFFER_FRONT_LEFT;
662 if (draw->color_rb[1])
663 attachments[i++] = __DRI_BUFFER_BACK_LEFT;
664 if (radeon_get_renderbuffer(&draw->base, BUFFER_DEPTH))
665 attachments[i++] = __DRI_BUFFER_DEPTH;
666 if (radeon_get_renderbuffer(&draw->base, BUFFER_STENCIL))
667 attachments[i++] = __DRI_BUFFER_STENCIL;
668
669 buffers = (*screen->dri2.loader->getBuffers)(drawable,
670 &drawable->w,
671 &drawable->h,
672 attachments, i,
673 &count,
674 drawable->loaderPrivate);
675 }
676
677 if (buffers == NULL)
678 return;
679
680 /* set one cliprect to cover the whole drawable */
681 drawable->x = 0;
682 drawable->y = 0;
683 drawable->backX = 0;
684 drawable->backY = 0;
685 drawable->numClipRects = 1;
686 drawable->pClipRects[0].x1 = 0;
687 drawable->pClipRects[0].y1 = 0;
688 drawable->pClipRects[0].x2 = drawable->w;
689 drawable->pClipRects[0].y2 = drawable->h;
690 drawable->numBackClipRects = 1;
691 drawable->pBackClipRects[0].x1 = 0;
692 drawable->pBackClipRects[0].y1 = 0;
693 drawable->pBackClipRects[0].x2 = drawable->w;
694 drawable->pBackClipRects[0].y2 = drawable->h;
695 for (i = 0; i < count; i++) {
696 switch (buffers[i].attachment) {
697 case __DRI_BUFFER_FRONT_LEFT:
698 rb = draw->color_rb[0];
699 regname = "dri2 front buffer";
700 break;
701 case __DRI_BUFFER_FAKE_FRONT_LEFT:
702 rb = draw->color_rb[0];
703 regname = "dri2 fake front buffer";
704 break;
705 case __DRI_BUFFER_BACK_LEFT:
706 rb = draw->color_rb[1];
707 regname = "dri2 back buffer";
708 break;
709 case __DRI_BUFFER_DEPTH:
710 rb = radeon_get_renderbuffer(&draw->base, BUFFER_DEPTH);
711 regname = "dri2 depth buffer";
712 break;
713 case __DRI_BUFFER_DEPTH_STENCIL:
714 rb = radeon_get_renderbuffer(&draw->base, BUFFER_DEPTH);
715 regname = "dri2 depth / stencil buffer";
716 break;
717 case __DRI_BUFFER_STENCIL:
718 rb = radeon_get_renderbuffer(&draw->base, BUFFER_STENCIL);
719 regname = "dri2 stencil buffer";
720 break;
721 case __DRI_BUFFER_ACCUM:
722 default:
723 fprintf(stderr,
724 "unhandled buffer attach event, attacment type %d\n",
725 buffers[i].attachment);
726 return;
727 }
728
729 if (rb == NULL)
730 continue;
731
732 if (rb->bo) {
733 uint32_t name = radeon_gem_name_bo(rb->bo);
734 if (name == buffers[i].name)
735 continue;
736 }
737
738 if (RADEON_DEBUG & DEBUG_DRI)
739 fprintf(stderr,
740 "attaching buffer %s, %d, at %d, cpp %d, pitch %d\n",
741 regname, buffers[i].name, buffers[i].attachment,
742 buffers[i].cpp, buffers[i].pitch);
743
744 rb->cpp = buffers[i].cpp;
745 rb->pitch = buffers[i].pitch;
746 rb->base.Width = drawable->w;
747 rb->base.Height = drawable->h;
748 rb->has_surface = 0;
749
750 if (buffers[i].attachment == __DRI_BUFFER_STENCIL && depth_bo) {
751 if (RADEON_DEBUG & DEBUG_DRI)
752 fprintf(stderr, "(reusing depth buffer as stencil)\n");
753 bo = depth_bo;
754 radeon_bo_ref(bo);
755 } else {
756 uint32_t tiling_flags = 0, pitch = 0;
757 int ret;
758 #ifdef RADEON_DEBUG_BO
759 bo = radeon_bo_open(radeon->radeonScreen->bom,
760 buffers[i].name,
761 0,
762 0,
763 RADEON_GEM_DOMAIN_VRAM,
764 buffers[i].flags,
765 regname);
766 #else
767 bo = radeon_bo_open(radeon->radeonScreen->bom,
768 buffers[i].name,
769 0,
770 0,
771 RADEON_GEM_DOMAIN_VRAM,
772 buffers[i].flags);
773 #endif /* RADEON_DEBUG_BO */
774 if (bo == NULL) {
775
776 fprintf(stderr, "failed to attach %s %d\n",
777 regname, buffers[i].name);
778
779 }
780
781 ret = radeon_bo_get_tiling(bo, &tiling_flags, &pitch);
782 if (tiling_flags & RADEON_TILING_MACRO)
783 bo->flags |= RADEON_BO_FLAGS_MACRO_TILE;
784 if (tiling_flags & RADEON_TILING_MICRO)
785 bo->flags |= RADEON_BO_FLAGS_MICRO_TILE;
786
787 }
788
789 if (buffers[i].attachment == __DRI_BUFFER_DEPTH) {
790 if (draw->base.Visual.depthBits == 16)
791 rb->cpp = 2;
792 depth_bo = bo;
793 }
794
795 radeon_renderbuffer_set_bo(rb, bo);
796 radeon_bo_unref(bo);
797
798 if (buffers[i].attachment == __DRI_BUFFER_DEPTH_STENCIL) {
799 rb = radeon_get_renderbuffer(&draw->base, BUFFER_STENCIL);
800 if (rb != NULL) {
801 struct radeon_bo *stencil_bo = NULL;
802
803 if (rb->bo) {
804 uint32_t name = radeon_gem_name_bo(rb->bo);
805 if (name == buffers[i].name)
806 continue;
807 }
808
809 stencil_bo = bo;
810 radeon_bo_ref(stencil_bo);
811 radeon_renderbuffer_set_bo(rb, stencil_bo);
812 radeon_bo_unref(stencil_bo);
813 }
814 }
815 }
816
817 driUpdateFramebufferSize(radeon->glCtx, drawable);
818 }
819
820 /* Force the context `c' to be the current context and associate with it
821 * buffer `b'.
822 */
823 GLboolean radeonMakeCurrent(__DRIcontextPrivate * driContextPriv,
824 __DRIdrawablePrivate * driDrawPriv,
825 __DRIdrawablePrivate * driReadPriv)
826 {
827 radeonContextPtr radeon;
828 struct radeon_framebuffer *drfb;
829 struct gl_framebuffer *readfb;
830
831 if (!driContextPriv) {
832 if (RADEON_DEBUG & DEBUG_DRI)
833 fprintf(stderr, "%s ctx is null\n", __FUNCTION__);
834 _mesa_make_current(NULL, NULL, NULL);
835 return GL_TRUE;
836 }
837
838 radeon = (radeonContextPtr) driContextPriv->driverPrivate;
839 drfb = driDrawPriv->driverPrivate;
840 readfb = driReadPriv->driverPrivate;
841
842 if (driContextPriv->driScreenPriv->dri2.enabled) {
843 radeon_update_renderbuffers(driContextPriv, driDrawPriv);
844 if (driDrawPriv != driReadPriv)
845 radeon_update_renderbuffers(driContextPriv, driReadPriv);
846 _mesa_reference_renderbuffer(&radeon->state.color.rb,
847 &(radeon_get_renderbuffer(&drfb->base, BUFFER_BACK_LEFT)->base));
848 _mesa_reference_renderbuffer(&radeon->state.depth.rb,
849 &(radeon_get_renderbuffer(&drfb->base, BUFFER_DEPTH)->base));
850 } else {
851 radeon_make_renderbuffer_current(radeon, drfb);
852 }
853
854 if (RADEON_DEBUG & DEBUG_DRI)
855 fprintf(stderr, "%s ctx %p dfb %p rfb %p\n", __FUNCTION__, radeon->glCtx, drfb, readfb);
856
857 driUpdateFramebufferSize(radeon->glCtx, driDrawPriv);
858 if (driReadPriv != driDrawPriv)
859 driUpdateFramebufferSize(radeon->glCtx, driReadPriv);
860
861 _mesa_make_current(radeon->glCtx, &drfb->base, readfb);
862
863 _mesa_update_state(radeon->glCtx);
864
865 if (radeon->glCtx->DrawBuffer == &drfb->base) {
866 if (driDrawPriv->swap_interval == (unsigned)-1) {
867 int i;
868 driDrawPriv->vblFlags =
869 (radeon->radeonScreen->irq != 0)
870 ? driGetDefaultVBlankFlags(&radeon->
871 optionCache)
872 : VBLANK_FLAG_NO_IRQ;
873
874 driDrawableInitVBlank(driDrawPriv);
875 drfb->vbl_waited = driDrawPriv->vblSeq;
876
877 for (i = 0; i < 2; i++) {
878 if (drfb->color_rb[i])
879 drfb->color_rb[i]->vbl_pending = driDrawPriv->vblSeq;
880 }
881
882 }
883
884 radeon_window_moved(radeon);
885 radeon_draw_buffer(radeon->glCtx, &drfb->base);
886 }
887
888
889 if (RADEON_DEBUG & DEBUG_DRI)
890 fprintf(stderr, "End %s\n", __FUNCTION__);
891
892 return GL_TRUE;
893 }
894