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