radeon_kms.c revision 68105dcb
1/*
2 * Copyright © 2009 Red Hat, Inc.
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
13 * Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 * SOFTWARE.
22 *
23 * Authors:
24 *    Dave Airlie <airlied@redhat.com>
25 *
26 */
27#ifdef HAVE_CONFIG_H
28#include "config.h"
29#endif
30
31#include <errno.h>
32#include <sys/ioctl.h>
33/* Driver data structures */
34#include "radeon.h"
35#include "radeon_reg.h"
36#include "radeon_probe.h"
37#include "micmap.h"
38
39#include "shadow.h"
40
41#include "atipciids.h"
42
43
44#ifdef XF86DRM_MODE
45
46#include "radeon_chipset_gen.h"
47#include "radeon_chipinfo_gen.h"
48
49#define CURSOR_WIDTH	64
50#define CURSOR_HEIGHT	64
51
52#include "radeon_bo_gem.h"
53#include "radeon_cs_gem.h"
54#include "radeon_vbo.h"
55
56static Bool radeon_setup_kernel_mem(ScreenPtr pScreen);
57
58const OptionInfoRec RADEONOptions_KMS[] = {
59    { OPTION_NOACCEL,        "NoAccel",          OPTV_BOOLEAN, {0}, FALSE },
60    { OPTION_SW_CURSOR,      "SWcursor",         OPTV_BOOLEAN, {0}, FALSE },
61    { OPTION_PAGE_FLIP,      "EnablePageFlip",   OPTV_BOOLEAN, {0}, FALSE },
62    { OPTION_ACCEL_DFS,      "AccelDFS",         OPTV_BOOLEAN, {0}, FALSE },
63    { OPTION_IGNORE_EDID,    "IgnoreEDID",       OPTV_BOOLEAN, {0}, FALSE },
64    { OPTION_COLOR_TILING,   "ColorTiling",      OPTV_BOOLEAN, {0}, FALSE },
65    { OPTION_COLOR_TILING_2D,"ColorTiling2D",    OPTV_BOOLEAN, {0}, FALSE },
66    { OPTION_RENDER_ACCEL,   "RenderAccel",      OPTV_BOOLEAN, {0}, FALSE },
67    { OPTION_SUBPIXEL_ORDER, "SubPixelOrder",    OPTV_ANYSTR,  {0}, FALSE },
68    { OPTION_ACCELMETHOD,    "AccelMethod",      OPTV_STRING,  {0}, FALSE },
69    { OPTION_DRI,            "DRI",       	 OPTV_BOOLEAN, {0}, FALSE },
70    { OPTION_TVSTD,          "TVStandard",       OPTV_STRING,  {0}, FALSE },
71    { OPTION_EXA_VSYNC,      "EXAVSync",         OPTV_BOOLEAN, {0}, FALSE },
72    { OPTION_EXA_PIXMAPS,    "EXAPixmaps",	 OPTV_BOOLEAN,   {0}, FALSE },
73    { OPTION_ZAPHOD_HEADS,   "ZaphodHeads",      OPTV_STRING,  {0}, FALSE },
74    { OPTION_PAGE_FLIP,      "EnablePageFlip",   OPTV_BOOLEAN, {0}, FALSE },
75    { OPTION_SWAPBUFFERS_WAIT,"SwapbuffersWait", OPTV_BOOLEAN, {0}, FALSE },
76    { -1,                    NULL,               OPTV_NONE,    {0}, FALSE }
77};
78
79void radeon_cs_flush_indirect(ScrnInfoPtr pScrn)
80{
81    RADEONInfoPtr  info = RADEONPTR(pScrn);
82    struct radeon_accel_state *accel_state = info->accel_state;
83    int ret;
84
85    if (!info->cs->cdw)
86	return;
87
88    /* release the current VBO so we don't block on mapping it later */
89    if (info->accel_state->vbo.vb_offset && info->accel_state->vbo.vb_bo) {
90        radeon_vbo_put(pScrn, &info->accel_state->vbo);
91        info->accel_state->vbo.vb_start_op = -1;
92    }
93
94    /* release the current VBO so we don't block on mapping it later */
95    if (info->accel_state->cbuf.vb_bo) {
96        radeon_vbo_put(pScrn, &info->accel_state->cbuf);
97        info->accel_state->cbuf.vb_start_op = -1;
98    }
99
100    radeon_cs_emit(info->cs);
101    radeon_cs_erase(info->cs);
102
103    if (accel_state->use_vbos)
104        radeon_vbo_flush_bos(pScrn);
105
106    ret = radeon_cs_space_check_with_bo(info->cs,
107					accel_state->vbo.vb_bo,
108					RADEON_GEM_DOMAIN_GTT, 0);
109    if (ret)
110      ErrorF("space check failed in flush\n");
111
112    if (info->reemit_current2d && info->state_2d.op)
113        info->reemit_current2d(pScrn, info->state_2d.op);
114
115    if (info->dri2.enabled) {
116        info->accel_state->XInited3D = FALSE;
117        info->accel_state->engineMode = EXA_ENGINEMODE_UNKNOWN;
118    }
119
120}
121
122void radeon_ddx_cs_start(ScrnInfoPtr pScrn,
123			 int n, const char *file,
124			 const char *func, int line)
125{
126    RADEONInfoPtr  info = RADEONPTR(pScrn);
127
128    if (info->cs->cdw + n > info->cs->ndw) {
129	radeon_cs_flush_indirect(pScrn);
130
131    }
132    radeon_cs_begin(info->cs, n, file, func, line);
133}
134
135
136extern _X_EXPORT int gRADEONEntityIndex;
137
138static int getRADEONEntityIndex(void)
139{
140    return gRADEONEntityIndex;
141}
142
143static void *
144radeonShadowWindow(ScreenPtr screen, CARD32 row, CARD32 offset, int mode,
145		   CARD32 *size, void *closure)
146{
147    ScrnInfoPtr pScrn = xf86ScreenToScrn(screen);
148    RADEONInfoPtr  info   = RADEONPTR(pScrn);
149    int stride;
150
151    stride = (pScrn->displayWidth * pScrn->bitsPerPixel) / 8;
152    *size = stride;
153
154    return ((uint8_t *)info->front_bo->ptr + row * stride + offset);
155}
156
157static Bool RADEONCreateScreenResources_KMS(ScreenPtr pScreen)
158{
159    ScrnInfoPtr pScrn = xf86ScreenToScrn(pScreen);
160    RADEONInfoPtr  info   = RADEONPTR(pScrn);
161    PixmapPtr pixmap;
162    struct radeon_surface *surface;
163
164    pScreen->CreateScreenResources = info->CreateScreenResources;
165    if (!(*pScreen->CreateScreenResources)(pScreen))
166	return FALSE;
167    pScreen->CreateScreenResources = RADEONCreateScreenResources_KMS;
168
169    if (!drmmode_set_desired_modes(pScrn, &info->drmmode))
170	return FALSE;
171
172    drmmode_uevent_init(pScrn, &info->drmmode);
173
174    if (info->r600_shadow_fb) {
175	pixmap = pScreen->GetScreenPixmap(pScreen);
176
177	if (!shadowAdd(pScreen, pixmap, shadowUpdatePackedWeak(),
178		       radeonShadowWindow, 0, NULL))
179	    return FALSE;
180    }
181
182    if (info->dri2.enabled) {
183	if (info->front_bo) {
184	    PixmapPtr pPix = pScreen->GetScreenPixmap(pScreen);
185	    radeon_set_pixmap_bo(pPix, info->front_bo);
186	    surface = radeon_get_pixmap_surface(pPix);
187	    if (surface) {
188		*surface = info->front_surface;
189	    }
190	}
191    }
192    return TRUE;
193}
194
195static void RADEONBlockHandler_KMS(BLOCKHANDLER_ARGS_DECL)
196{
197    SCREEN_PTR(arg);
198    ScrnInfoPtr    pScrn   = xf86ScreenToScrn(pScreen);
199    RADEONInfoPtr  info    = RADEONPTR(pScrn);
200
201    pScreen->BlockHandler = info->BlockHandler;
202    (*pScreen->BlockHandler) (BLOCKHANDLER_ARGS);
203    pScreen->BlockHandler = RADEONBlockHandler_KMS;
204
205    if (info->VideoTimerCallback)
206	(*info->VideoTimerCallback)(pScrn, currentTime.milliseconds);
207    radeon_cs_flush_indirect(pScrn);
208}
209
210static void
211radeon_flush_callback(CallbackListPtr *list,
212		      pointer user_data, pointer call_data)
213{
214    ScrnInfoPtr pScrn = user_data;
215
216    if (pScrn->vtSema) {
217        radeon_cs_flush_indirect(pScrn);
218    }
219}
220
221static Bool RADEONIsFusionGARTWorking(ScrnInfoPtr pScrn)
222{
223    RADEONInfoPtr info = RADEONPTR(pScrn);
224    struct drm_radeon_info ginfo;
225    int r;
226    uint32_t tmp;
227
228#ifndef RADEON_INFO_FUSION_GART_WORKING
229#define RADEON_INFO_FUSION_GART_WORKING 0x0c
230#endif
231    memset(&ginfo, 0, sizeof(ginfo));
232    ginfo.request = RADEON_INFO_FUSION_GART_WORKING;
233    ginfo.value = (uintptr_t)&tmp;
234    r = drmCommandWriteRead(info->dri->drmFD, DRM_RADEON_INFO, &ginfo, sizeof(ginfo));
235    if (r) {
236	return FALSE;
237    }
238    if (tmp == 1)
239	return TRUE;
240    return FALSE;
241}
242
243static Bool RADEONIsAccelWorking(ScrnInfoPtr pScrn)
244{
245    RADEONInfoPtr info = RADEONPTR(pScrn);
246    struct drm_radeon_info ginfo;
247    int r;
248    uint32_t tmp;
249
250#ifndef RADEON_INFO_ACCEL_WORKING
251#define RADEON_INFO_ACCEL_WORKING 0x03
252#endif
253#ifndef RADEON_INFO_ACCEL_WORKING2
254#define RADEON_INFO_ACCEL_WORKING2 0x05
255#endif
256
257    memset(&ginfo, 0, sizeof(ginfo));
258    if (info->dri->pKernelDRMVersion->version_minor >= 5)
259	ginfo.request = RADEON_INFO_ACCEL_WORKING2;
260    else
261	ginfo.request = RADEON_INFO_ACCEL_WORKING;
262    ginfo.value = (uintptr_t)&tmp;
263    r = drmCommandWriteRead(info->dri->drmFD, DRM_RADEON_INFO, &ginfo, sizeof(ginfo));
264    if (r) {
265        /* If kernel is too old before 2.6.32 than assume accel is working */
266        if (r == -EINVAL) {
267            xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Kernel too old missing accel "
268                       "information, assuming accel is working\n");
269            return TRUE;
270        }
271        return FALSE;
272    }
273    if (tmp)
274        return TRUE;
275    return FALSE;
276}
277
278static Bool RADEONPreInitAccel_KMS(ScrnInfoPtr pScrn)
279{
280    RADEONInfoPtr  info = RADEONPTR(pScrn);
281
282    if (!(info->accel_state = calloc(1, sizeof(struct radeon_accel_state)))) {
283	xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Unable to allocate accel_state rec!\n");
284	return FALSE;
285    }
286
287    if (xf86ReturnOptValBool(info->Options, OPTION_NOACCEL, FALSE) ||
288	(!RADEONIsAccelWorking(pScrn))) {
289	xf86DrvMsg(pScrn->scrnIndex, X_INFO,
290		   "GPU accel disabled or not working, using shadowfb for KMS\n");
291	info->r600_shadow_fb = TRUE;
292	if (!xf86LoadSubModule(pScrn, "shadow"))
293	    info->r600_shadow_fb = FALSE;
294	return TRUE;
295    }
296
297    if (info->ChipFamily == CHIP_FAMILY_PALM) {
298	info->accel_state->allowHWDFS = RADEONIsFusionGARTWorking(pScrn);
299    } else
300	info->accel_state->allowHWDFS = TRUE;
301
302    if ((info->ChipFamily == CHIP_FAMILY_RS100) ||
303	(info->ChipFamily == CHIP_FAMILY_RS200) ||
304	(info->ChipFamily == CHIP_FAMILY_RS300) ||
305	(info->ChipFamily == CHIP_FAMILY_RS400) ||
306	(info->ChipFamily == CHIP_FAMILY_RS480) ||
307	(info->ChipFamily == CHIP_FAMILY_RS600) ||
308	(info->ChipFamily == CHIP_FAMILY_RS690) ||
309	(info->ChipFamily == CHIP_FAMILY_RS740))
310	info->accel_state->has_tcl = FALSE;
311    else {
312	info->accel_state->has_tcl = TRUE;
313    }
314
315    info->useEXA = TRUE;
316
317    if (info->useEXA) {
318	int errmaj = 0, errmin = 0;
319	info->exaReq.majorversion = EXA_VERSION_MAJOR;
320	info->exaReq.minorversion = EXA_VERSION_MINOR;
321	if (!LoadSubModule(pScrn->module, "exa", NULL, NULL, NULL,
322			   &info->exaReq, &errmaj, &errmin)) {
323	    LoaderErrorMsg(NULL, "exa", errmaj, errmin);
324	    return FALSE;
325	}
326    }
327
328    return TRUE;
329}
330
331static Bool RADEONPreInitChipType_KMS(ScrnInfoPtr pScrn)
332{
333    RADEONInfoPtr  info   = RADEONPTR(pScrn);
334    uint32_t cmd_stat;
335    int i;
336
337    info->Chipset = PCI_DEV_DEVICE_ID(info->PciInfo);
338    pScrn->chipset = (char *)xf86TokenToString(RADEONChipsets, info->Chipset);
339    if (!pScrn->chipset) {
340	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
341		   "ChipID 0x%04x is not recognized\n", info->Chipset);
342	return FALSE;
343    }
344
345    if (info->Chipset < 0) {
346	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
347		   "Chipset \"%s\" is not recognized\n", pScrn->chipset);
348	return FALSE;
349    }
350    xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
351	       "Chipset: \"%s\" (ChipID = 0x%04x)\n",
352	       pScrn->chipset,
353	       info->Chipset);
354
355    for (i = 0; i < sizeof(RADEONCards) / sizeof(RADEONCardInfo); i++) {
356	if (info->Chipset == RADEONCards[i].pci_device_id) {
357	    RADEONCardInfo *card = &RADEONCards[i];
358	    info->ChipFamily = card->chip_family;
359	    info->IsMobility = card->mobility;
360	    info->IsIGP = card->igp;
361	    break;
362	}
363    }
364
365    info->cardType = CARD_PCI;
366
367    PCI_READ_LONG(info->PciInfo, &cmd_stat, PCI_CMD_STAT_REG);
368    if (cmd_stat & RADEON_CAP_LIST) {
369	uint32_t cap_ptr, cap_id;
370
371	PCI_READ_LONG(info->PciInfo, &cap_ptr, RADEON_CAPABILITIES_PTR_PCI_CONFIG);
372	cap_ptr &= RADEON_CAP_PTR_MASK;
373
374	while(cap_ptr != RADEON_CAP_ID_NULL) {
375	    PCI_READ_LONG(info->PciInfo, &cap_id, cap_ptr);
376	    if ((cap_id & 0xff)== RADEON_CAP_ID_AGP) {
377		info->cardType = CARD_AGP;
378		break;
379	    }
380	    if ((cap_id & 0xff)== RADEON_CAP_ID_EXP) {
381		info->cardType = CARD_PCIE;
382		break;
383	    }
384	    cap_ptr = (cap_id >> 8) & RADEON_CAP_PTR_MASK;
385	}
386    }
387
388
389    xf86DrvMsg(pScrn->scrnIndex, X_INFO, "%s card detected\n",
390	       (info->cardType==CARD_PCI) ? "PCI" :
391		(info->cardType==CARD_PCIE) ? "PCIE" : "AGP");
392
393    /* treat PCIE IGP cards as PCI */
394    if (info->cardType == CARD_PCIE && info->IsIGP)
395	info->cardType = CARD_PCI;
396
397    if ((info->ChipFamily >= CHIP_FAMILY_R600) && info->IsIGP)
398	info->cardType = CARD_PCIE;
399
400    /* not sure about gart table requirements */
401    if ((info->ChipFamily == CHIP_FAMILY_RS600) && info->IsIGP)
402	info->cardType = CARD_PCIE;
403
404#ifdef RENDER
405    info->RenderAccel = xf86ReturnOptValBool(info->Options, OPTION_RENDER_ACCEL,
406					     info->Chipset != PCI_CHIP_RN50_515E &&
407					     info->Chipset != PCI_CHIP_RN50_5969);
408#endif
409    return TRUE;
410}
411
412static Bool radeon_alloc_dri(ScrnInfoPtr pScrn)
413{
414    RADEONInfoPtr  info   = RADEONPTR(pScrn);
415    if (!(info->dri = calloc(1, sizeof(struct radeon_dri)))) {
416	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,"Unable to allocate dri rec!\n");
417	return FALSE;
418    }
419
420    if (!(info->cp = calloc(1, sizeof(struct radeon_cp)))) {
421	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,"Unable to allocate cp rec!\n");
422	return FALSE;
423    }
424    return TRUE;
425}
426
427static Bool radeon_open_drm_master(ScrnInfoPtr pScrn)
428{
429    RADEONInfoPtr  info   = RADEONPTR(pScrn);
430    RADEONEntPtr pRADEONEnt = RADEONEntPriv(pScrn);
431    struct pci_device *dev = info->PciInfo;
432    char *busid;
433    drmSetVersion sv;
434    int err;
435
436    if (pRADEONEnt->fd) {
437	xf86DrvMsg(pScrn->scrnIndex, X_INFO,
438		   " reusing fd for second head\n");
439
440	info->dri2.drm_fd = pRADEONEnt->fd;
441	goto out;
442    }
443
444#if XORG_VERSION_CURRENT >= XORG_VERSION_NUMERIC(1,9,99,901,0)
445    XNFasprintf(&busid, "pci:%04x:%02x:%02x.%d",
446                dev->domain, dev->bus, dev->dev, dev->func);
447#else
448    busid = XNFprintf("pci:%04x:%02x:%02x.%d",
449		      dev->domain, dev->bus, dev->dev, dev->func);
450#endif
451
452    info->dri2.drm_fd = drmOpen("radeon", busid);
453    if (info->dri2.drm_fd == -1) {
454
455	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
456		   "[drm] Failed to open DRM device for %s: %s\n",
457		   busid, strerror(errno));
458	free(busid);
459	return FALSE;
460    }
461    free(busid);
462
463    /* Check that what we opened was a master or a master-capable FD,
464     * by setting the version of the interface we'll use to talk to it.
465     * (see DRIOpenDRMMaster() in DRI1)
466     */
467    sv.drm_di_major = 1;
468    sv.drm_di_minor = 1;
469    sv.drm_dd_major = -1;
470    sv.drm_dd_minor = -1;
471    err = drmSetInterfaceVersion(info->dri2.drm_fd, &sv);
472    if (err != 0) {
473	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
474		   "[drm] failed to set drm interface version.\n");
475	drmClose(info->dri2.drm_fd);
476	info->dri2.drm_fd = -1;
477
478	return FALSE;
479    }
480
481    pRADEONEnt->fd = info->dri2.drm_fd;
482 out:
483    info->drmmode.fd = info->dri2.drm_fd;
484    info->dri->drmFD = info->dri2.drm_fd;
485    return TRUE;
486}
487
488#ifdef EXA_MIXED_PIXMAPS
489
490static Bool r600_get_tile_config(ScrnInfoPtr pScrn)
491{
492    RADEONInfoPtr  info   = RADEONPTR(pScrn);
493    struct drm_radeon_info ginfo;
494    int r;
495    uint32_t tmp;
496
497    if (info->ChipFamily < CHIP_FAMILY_R600)
498	return FALSE;
499
500#ifndef RADEON_INFO_TILING_CONFIG
501#define RADEON_INFO_TILING_CONFIG 0x6
502#endif
503
504    memset(&ginfo, 0, sizeof(ginfo));
505    ginfo.request = RADEON_INFO_TILING_CONFIG;
506    ginfo.value = (uintptr_t)&tmp;
507    r = drmCommandWriteRead(info->dri->drmFD, DRM_RADEON_INFO, &ginfo, sizeof(ginfo));
508    if (r)
509	return FALSE;
510
511    info->tile_config = tmp;
512    info->r7xx_bank_op = 0;
513    if (info->ChipFamily >= CHIP_FAMILY_CEDAR) {
514	if (info->dri->pKernelDRMVersion->version_minor >= 7) {
515	    switch (info->tile_config & 0xf) {
516	    case 0:
517                info->num_channels = 1;
518                break;
519	    case 1:
520                info->num_channels = 2;
521                break;
522	    case 2:
523                info->num_channels = 4;
524                break;
525	    case 3:
526                info->num_channels = 8;
527                break;
528	    default:
529                return FALSE;
530	    }
531
532	    switch((info->tile_config & 0xf0) >> 4) {
533	    case 0:
534		info->num_banks = 4;
535		break;
536	    case 1:
537		info->num_banks = 8;
538		break;
539	    case 2:
540		info->num_banks = 16;
541		break;
542	    default:
543		return FALSE;
544	    }
545
546	    switch ((info->tile_config & 0xf00) >> 8) {
547	    case 0:
548                info->group_bytes = 256;
549                break;
550	    case 1:
551                info->group_bytes = 512;
552                break;
553	    default:
554                return FALSE;
555	    }
556	} else
557	    return FALSE;
558    } else {
559	switch((info->tile_config & 0xe) >> 1) {
560	case 0:
561	    info->num_channels = 1;
562	    break;
563	case 1:
564	    info->num_channels = 2;
565	    break;
566	case 2:
567	    info->num_channels = 4;
568	    break;
569	case 3:
570	    info->num_channels = 8;
571	    break;
572	default:
573	    return FALSE;
574	}
575	switch((info->tile_config & 0x30) >> 4) {
576	case 0:
577	    info->num_banks = 4;
578	    break;
579	case 1:
580	    info->num_banks = 8;
581	    break;
582	default:
583	    return FALSE;
584	}
585	switch((info->tile_config & 0xc0) >> 6) {
586	case 0:
587	    info->group_bytes = 256;
588	    break;
589	case 1:
590	    info->group_bytes = 512;
591	    break;
592	default:
593	    return FALSE;
594	}
595    }
596
597    info->have_tiling_info = TRUE;
598    return TRUE;
599}
600
601#endif /* EXA_MIXED_PIXMAPS */
602
603Bool RADEONPreInit_KMS(ScrnInfoPtr pScrn, int flags)
604{
605    RADEONInfoPtr     info;
606    RADEONEntPtr pRADEONEnt;
607    DevUnion* pPriv;
608    Gamma  zeros = { 0.0, 0.0, 0.0 };
609    uint32_t tiling = 0;
610    int cpp;
611
612    xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
613		   "RADEONPreInit_KMS\n");
614    if (pScrn->numEntities != 1) return FALSE;
615    if (!RADEONGetRec(pScrn)) return FALSE;
616
617    info               = RADEONPTR(pScrn);
618    info->MMIO         = NULL;
619    info->IsSecondary  = FALSE;
620    info->IsPrimary = FALSE;
621    info->kms_enabled = TRUE;
622    info->pEnt         = xf86GetEntityInfo(pScrn->entityList[pScrn->numEntities - 1]);
623    if (info->pEnt->location.type != BUS_PCI) goto fail;
624
625    pPriv = xf86GetEntityPrivate(pScrn->entityList[0],
626				 getRADEONEntityIndex());
627    pRADEONEnt = pPriv->ptr;
628
629    if(xf86IsEntityShared(pScrn->entityList[0]))
630    {
631        if(xf86IsPrimInitDone(pScrn->entityList[0]))
632        {
633            info->IsSecondary = TRUE;
634            pRADEONEnt->pSecondaryScrn = pScrn;
635        }
636        else
637        {
638	    info->IsPrimary = TRUE;
639            xf86SetPrimInitDone(pScrn->entityList[0]);
640            pRADEONEnt->pPrimaryScrn = pScrn;
641            pRADEONEnt->HasSecondary = FALSE;
642        }
643    }
644
645    info->PciInfo = xf86GetPciInfoForEntity(info->pEnt->index);
646    pScrn->monitor     = pScrn->confScreen->monitor;
647
648    if (!RADEONPreInitVisual(pScrn))
649	goto fail;
650
651    xf86CollectOptions(pScrn, NULL);
652    if (!(info->Options = malloc(sizeof(RADEONOptions_KMS))))
653	goto fail;
654
655    memcpy(info->Options, RADEONOptions_KMS, sizeof(RADEONOptions_KMS));
656    xf86ProcessOptions(pScrn->scrnIndex, pScrn->options, info->Options);
657
658    if (!RADEONPreInitWeight(pScrn))
659	goto fail;
660
661    if (!RADEONPreInitChipType_KMS(pScrn))
662        goto fail;
663
664    if (!radeon_alloc_dri(pScrn))
665	return FALSE;
666
667    if (radeon_open_drm_master(pScrn) == FALSE) {
668	xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Kernel modesetting setup failed\n");
669	goto fail;
670    }
671
672    info->dri2.enabled = FALSE;
673    info->dri->pKernelDRMVersion = drmGetVersion(info->dri->drmFD);
674    if (info->dri->pKernelDRMVersion == NULL) {
675	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
676		   "RADEONDRIGetVersion failed to get the DRM version\n");
677	goto fail;
678    }
679
680    if (!RADEONPreInitAccel_KMS(pScrn))              goto fail;
681
682    info->allowColorTiling2D = FALSE;
683
684#ifdef EXA_MIXED_PIXMAPS
685    /* don't enable tiling if accel is not enabled */
686    if (!info->r600_shadow_fb) {
687	Bool colorTilingDefault =
688	    xorgGetVersion() >= XORG_VERSION_NUMERIC(1,9,4,901,0) &&
689	    info->ChipFamily >= CHIP_FAMILY_R300 &&
690	    info->ChipFamily <= CHIP_FAMILY_ARUBA;
691
692	/* 2D color tiling */
693	if (info->ChipFamily >= CHIP_FAMILY_R600) {
694		info->allowColorTiling2D = xf86ReturnOptValBool(info->Options, OPTION_COLOR_TILING_2D, FALSE);
695	}
696
697	if (info->ChipFamily >= CHIP_FAMILY_R600) {
698	    /* set default group bytes, overridden by kernel info below */
699	    info->group_bytes = 256;
700	    info->have_tiling_info = FALSE;
701	    if (info->dri->pKernelDRMVersion->version_minor >= 6) {
702		if (r600_get_tile_config(pScrn)) {
703		    info->allowColorTiling = xf86ReturnOptValBool(info->Options,
704								  OPTION_COLOR_TILING, colorTilingDefault);
705		    /* need working DFS for tiling */
706		    if ((info->ChipFamily == CHIP_FAMILY_PALM) &&
707			(!info->accel_state->allowHWDFS))
708			info->allowColorTiling = FALSE;
709		} else
710		    info->allowColorTiling = FALSE;
711	    } else
712		xf86DrvMsg(pScrn->scrnIndex, X_INFO,
713			   "R6xx+ KMS Color Tiling requires radeon drm 2.6.0 or newer\n");
714	} else
715	    info->allowColorTiling = xf86ReturnOptValBool(info->Options,
716							  OPTION_COLOR_TILING, colorTilingDefault);
717    } else
718#else
719    xf86DrvMsg(pScrn->scrnIndex, X_INFO,
720	       "KMS Color Tiling requires xserver which supports EXA_MIXED_PIXMAPS\n");
721#endif
722	info->allowColorTiling = FALSE;
723
724    xf86DrvMsg(pScrn->scrnIndex, X_INFO,
725	 "KMS Color Tiling: %sabled\n", info->allowColorTiling ? "en" : "dis");
726
727    if (info->dri->pKernelDRMVersion->version_minor >= 8) {
728	info->allowPageFlip = xf86ReturnOptValBool(info->Options,
729						   OPTION_PAGE_FLIP, TRUE);
730	xf86DrvMsg(pScrn->scrnIndex, X_INFO,
731		   "KMS Pageflipping: %sabled\n", info->allowPageFlip ? "en" : "dis");
732    }
733
734    info->swapBuffersWait = xf86ReturnOptValBool(info->Options,
735						 OPTION_SWAPBUFFERS_WAIT, TRUE);
736    xf86DrvMsg(pScrn->scrnIndex, X_INFO,
737	       "SwapBuffers wait for vsync: %sabled\n", info->swapBuffersWait ? "en" : "dis");
738
739    if (drmmode_pre_init(pScrn, &info->drmmode, pScrn->bitsPerPixel / 8) == FALSE) {
740	xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Kernel modesetting setup failed\n");
741	goto fail;
742    }
743
744    if (info->drmmode.mode_res->count_crtcs == 1)
745        pRADEONEnt->HasCRTC2 = FALSE;
746    else
747        pRADEONEnt->HasCRTC2 = TRUE;
748
749
750    /* fix up cloning on rn50 cards
751     * since they only have one crtc sometimes the xserver doesn't assign
752     * a crtc to one of the outputs even though both outputs have common modes
753     * which results in only one monitor being enabled.  Assign a crtc here so
754     * that both outputs light up.
755     */
756    if (info->ChipFamily == CHIP_FAMILY_RV100 && !pRADEONEnt->HasCRTC2) {
757	xf86CrtcConfigPtr xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
758	int i;
759
760	for (i = 0; i < xf86_config->num_output; i++) {
761	    xf86OutputPtr output = xf86_config->output[i];
762
763	    /* XXX: double check crtc mode */
764	    if ((output->probed_modes != NULL) && (output->crtc == NULL))
765		output->crtc = xf86_config->crtc[0];
766	}
767    }
768
769    {
770	struct drm_radeon_gem_info mminfo;
771
772	if (!drmCommandWriteRead(info->dri->drmFD, DRM_RADEON_GEM_INFO, &mminfo, sizeof(mminfo)))
773	{
774	    info->vram_size = mminfo.vram_visible;
775	    info->gart_size = mminfo.gart_size;
776	    xf86DrvMsg(pScrn->scrnIndex, X_INFO,
777		       "mem size init: gart size :%llx vram size: s:%llx visible:%llx\n",
778		       (unsigned long long)mminfo.gart_size,
779		       (unsigned long long)mminfo.vram_size,
780		       (unsigned long long)mminfo.vram_visible);
781	}
782    }
783
784    info->exa_pixmaps = xf86ReturnOptValBool(info->Options,
785                                             OPTION_EXA_PIXMAPS,
786					     ((info->vram_size > (32 * 1024 * 1024) &&
787					      info->RenderAccel)));
788    if (info->exa_pixmaps)
789    	xf86DrvMsg(pScrn->scrnIndex, X_INFO,
790		"EXA: Driver will allow EXA pixmaps in VRAM\n");
791    else
792    	xf86DrvMsg(pScrn->scrnIndex, X_INFO,
793		"EXA: Driver will not allow EXA pixmaps in VRAM\n");
794
795    /* no tiled scanout on r6xx+ yet */
796    if (info->allowColorTiling) {
797	if (info->ChipFamily >= CHIP_FAMILY_R600)
798	    tiling |= RADEON_TILING_MICRO;
799	else
800	    tiling |= RADEON_TILING_MACRO;
801    }
802    cpp = pScrn->bitsPerPixel / 8;
803    pScrn->displayWidth =
804	RADEON_ALIGN(pScrn->virtualX, drmmode_get_pitch_align(pScrn, cpp, tiling));
805    info->CurrentLayout.displayWidth = pScrn->displayWidth;
806
807    /* Set display resolution */
808    xf86SetDpi(pScrn, 0, 0);
809
810	/* Get ScreenInit function */
811    if (!xf86LoadSubModule(pScrn, "fb")) return FALSE;
812
813    if (!xf86SetGamma(pScrn, zeros)) return FALSE;
814
815    if (!xf86ReturnOptValBool(info->Options, OPTION_SW_CURSOR, FALSE)) {
816	if (!xf86LoadSubModule(pScrn, "ramdac")) return FALSE;
817    }
818
819    if (pScrn->modes == NULL) {
820      xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "No modes.\n");
821      goto fail;
822   }
823
824    return TRUE;
825 fail:
826    RADEONFreeRec(pScrn);
827    return FALSE;
828
829}
830
831static Bool RADEONCursorInit_KMS(ScreenPtr pScreen)
832{
833    return xf86_cursors_init (pScreen, CURSOR_WIDTH, CURSOR_HEIGHT,
834			      (HARDWARE_CURSOR_TRUECOLOR_AT_8BPP |
835			       HARDWARE_CURSOR_AND_SOURCE_WITH_MASK |
836			       HARDWARE_CURSOR_SOURCE_MASK_INTERLEAVE_1 |
837			       HARDWARE_CURSOR_UPDATE_UNHIDDEN |
838			       HARDWARE_CURSOR_ARGB));
839}
840
841static Bool RADEONSaveScreen_KMS(ScreenPtr pScreen, int mode)
842{
843    ScrnInfoPtr  pScrn = xf86ScreenToScrn(pScreen);
844    Bool         unblank;
845
846    xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
847		   "RADEONSaveScreen(%d)\n", mode);
848
849    unblank = xf86IsUnblank(mode);
850    if (unblank) SetTimeSinceLastInputEvent();
851
852    if ((pScrn != NULL) && pScrn->vtSema) {
853	if (unblank)
854	    RADEONUnblank(pScrn);
855	else
856	    RADEONBlank(pScrn);
857    }
858    return TRUE;
859}
860
861/* Called at the end of each server generation.  Restore the original
862 * text mode, unmap video memory, and unwrap and call the saved
863 * CloseScreen function.
864 */
865static Bool RADEONCloseScreen_KMS(CLOSE_SCREEN_ARGS_DECL)
866{
867    ScrnInfoPtr pScrn = xf86ScreenToScrn(pScreen);
868    RADEONInfoPtr  info  = RADEONPTR(pScrn);
869
870    xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
871		   "RADEONCloseScreen\n");
872
873    drmmode_uevent_fini(pScrn, &info->drmmode);
874    if (info->cs)
875      radeon_cs_flush_indirect(pScrn);
876
877    DeleteCallback(&FlushCallback, radeon_flush_callback, pScrn);
878
879    if (info->accel_state->exa) {
880	exaDriverFini(pScreen);
881	free(info->accel_state->exa);
882	info->accel_state->exa = NULL;
883    }
884
885    if (info->accel_state->use_vbos)
886        radeon_vbo_free_lists(pScrn);
887
888    drmDropMaster(info->dri->drmFD);
889
890    if (info->cursor) xf86DestroyCursorInfoRec(info->cursor);
891    info->cursor = NULL;
892
893    if (info->dri2.enabled)
894	radeon_dri2_close_screen(pScreen);
895
896    pScrn->vtSema = FALSE;
897    xf86ClearPrimInitDone(info->pEnt->index);
898    pScreen->BlockHandler = info->BlockHandler;
899    pScreen->CloseScreen = info->CloseScreen;
900    return (*pScreen->CloseScreen)(CLOSE_SCREEN_ARGS);
901}
902
903
904void RADEONFreeScreen_KMS(FREE_SCREEN_ARGS_DECL)
905{
906    SCRN_INFO_PTR(arg);
907    RADEONInfoPtr  info  = RADEONPTR(pScrn);
908
909    xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
910		   "RADEONFreeScreen\n");
911
912    /* when server quits at PreInit, we don't need do this anymore*/
913    if (!info) return;
914
915    RADEONFreeRec(pScrn);
916}
917
918Bool RADEONScreenInit_KMS(SCREEN_INIT_ARGS_DECL)
919{
920    ScrnInfoPtr    pScrn = xf86ScreenToScrn(pScreen);
921    RADEONInfoPtr  info  = RADEONPTR(pScrn);
922    int            subPixelOrder = SubPixelUnknown;
923    char*          s;
924    void *front_ptr;
925    int ret;
926
927    pScrn->fbOffset = 0;
928
929    miClearVisualTypes();
930    if (!miSetVisualTypes(pScrn->depth,
931			  miGetDefaultVisualMask(pScrn->depth),
932			  pScrn->rgbBits,
933			  pScrn->defaultVisual)) return FALSE;
934    miSetPixmapDepths ();
935
936    ret = drmSetMaster(info->dri->drmFD);
937    if (ret) {
938        ErrorF("Unable to retrieve master\n");
939        return FALSE;
940    }
941    info->directRenderingEnabled = FALSE;
942    if (info->r600_shadow_fb == FALSE)
943        info->directRenderingEnabled = radeon_dri2_screen_init(pScreen);
944
945    front_ptr = info->FB;
946
947    info->surf_man = radeon_surface_manager_new(info->dri->drmFD);
948    if (!info->bufmgr)
949        info->bufmgr = radeon_bo_manager_gem_ctor(info->dri->drmFD);
950    if (!info->bufmgr) {
951	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
952		   "failed to initialise GEM buffer manager");
953	return FALSE;
954    }
955    drmmode_set_bufmgr(pScrn, &info->drmmode, info->bufmgr);
956
957    if (!info->csm)
958        info->csm = radeon_cs_manager_gem_ctor(info->dri->drmFD);
959    if (!info->csm) {
960	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
961		   "failed to initialise command submission manager");
962	return FALSE;
963    }
964
965    if (!info->cs)
966        info->cs = radeon_cs_create(info->csm, RADEON_BUFFER_SIZE/4);
967    if (!info->cs) {
968	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
969		   "failed to initialise command submission buffer");
970	return FALSE;
971    }
972
973    radeon_cs_set_limit(info->cs, RADEON_GEM_DOMAIN_GTT, info->gart_size);
974    radeon_cs_space_set_flush(info->cs, (void(*)(void *))radeon_cs_flush_indirect, pScrn);
975
976    if (!radeon_setup_kernel_mem(pScreen)) {
977	xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "radeon_setup_kernel_mem failed\n");
978	return FALSE;
979    }
980    front_ptr = info->front_bo->ptr;
981
982    if (info->r600_shadow_fb) {
983	info->fb_shadow = calloc(1,
984				 pScrn->displayWidth * pScrn->virtualY *
985				 ((pScrn->bitsPerPixel + 7) >> 3));
986	if (info->fb_shadow == NULL) {
987	    xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
988                       "Failed to allocate shadow framebuffer\n");
989	    info->r600_shadow_fb = FALSE;
990	} else {
991	    if (!fbScreenInit(pScreen, info->fb_shadow,
992			      pScrn->virtualX, pScrn->virtualY,
993			      pScrn->xDpi, pScrn->yDpi, pScrn->displayWidth,
994			      pScrn->bitsPerPixel))
995		return FALSE;
996	}
997    }
998
999    if (info->r600_shadow_fb == FALSE) {
1000	/* Init fb layer */
1001	if (!fbScreenInit(pScreen, front_ptr,
1002			  pScrn->virtualX, pScrn->virtualY,
1003			  pScrn->xDpi, pScrn->yDpi, pScrn->displayWidth,
1004			  pScrn->bitsPerPixel))
1005	    return FALSE;
1006    }
1007
1008    xf86SetBlackWhitePixels(pScreen);
1009
1010    if (pScrn->bitsPerPixel > 8) {
1011	VisualPtr  visual;
1012
1013	visual = pScreen->visuals + pScreen->numVisuals;
1014	while (--visual >= pScreen->visuals) {
1015	    if ((visual->class | DynamicClass) == DirectColor) {
1016		visual->offsetRed   = pScrn->offset.red;
1017		visual->offsetGreen = pScrn->offset.green;
1018		visual->offsetBlue  = pScrn->offset.blue;
1019		visual->redMask     = pScrn->mask.red;
1020		visual->greenMask   = pScrn->mask.green;
1021		visual->blueMask    = pScrn->mask.blue;
1022	    }
1023	}
1024    }
1025
1026    /* Must be after RGB order fixed */
1027    fbPictureInit (pScreen, 0, 0);
1028
1029#ifdef RENDER
1030    if ((s = xf86GetOptValString(info->Options, OPTION_SUBPIXEL_ORDER))) {
1031	if (strcmp(s, "RGB") == 0) subPixelOrder = SubPixelHorizontalRGB;
1032	else if (strcmp(s, "BGR") == 0) subPixelOrder = SubPixelHorizontalBGR;
1033	else if (strcmp(s, "NONE") == 0) subPixelOrder = SubPixelNone;
1034	PictureSetSubpixelOrder (pScreen, subPixelOrder);
1035    }
1036#endif
1037
1038    pScrn->vtSema = TRUE;
1039    /* Backing store setup */
1040    xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
1041		   "Initializing backing store\n");
1042    miInitializeBackingStore(pScreen);
1043    xf86SetBackingStore(pScreen);
1044
1045
1046    if (info->directRenderingEnabled) {
1047	xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Direct rendering enabled\n");
1048    } else {
1049	xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
1050		   "Direct rendering disabled\n");
1051    }
1052
1053    if (info->r600_shadow_fb) {
1054	xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Acceleration disabled\n");
1055	info->accelOn = FALSE;
1056    } else {
1057	xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
1058		       "Initializing Acceleration\n");
1059	if (RADEONAccelInit(pScreen)) {
1060	    xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Acceleration enabled\n");
1061	    info->accelOn = TRUE;
1062	} else {
1063	    xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1064		       "Acceleration initialization failed\n");
1065	    xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Acceleration disabled\n");
1066	    info->accelOn = FALSE;
1067	}
1068    }
1069
1070    /* Init DPMS */
1071    xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
1072		   "Initializing DPMS\n");
1073    xf86DPMSInit(pScreen, xf86DPMSSet, 0);
1074
1075    xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
1076		   "Initializing Cursor\n");
1077
1078    /* Set Silken Mouse */
1079    xf86SetSilkenMouse(pScreen);
1080
1081    /* Cursor setup */
1082    miDCInitialize(pScreen, xf86GetPointerScreenFuncs());
1083
1084    if (!xf86ReturnOptValBool(info->Options, OPTION_SW_CURSOR, FALSE)) {
1085	if (RADEONCursorInit_KMS(pScreen)) {
1086	}
1087    }
1088
1089    /* DGA setup */
1090#ifdef XFreeXDGA
1091    /* DGA is dangerous on kms as the base and framebuffer location may change:
1092     * http://lists.freedesktop.org/archives/xorg-devel/2009-September/002113.html
1093     */
1094    /* xf86DiDGAInit(pScreen, info->LinearAddr + pScrn->fbOffset); */
1095#endif
1096    if (info->r600_shadow_fb == FALSE) {
1097        /* Init Xv */
1098        xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
1099                       "Initializing Xv\n");
1100        RADEONInitVideo(pScreen);
1101    }
1102
1103    if (info->r600_shadow_fb == TRUE) {
1104        if (!shadowSetup(pScreen)) {
1105	    xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1106		       "Shadowfb initialization failed\n");
1107            return FALSE;
1108        }
1109    }
1110    pScrn->pScreen = pScreen;
1111
1112    /* Provide SaveScreen & wrap BlockHandler and CloseScreen */
1113    /* Wrap CloseScreen */
1114    info->CloseScreen    = pScreen->CloseScreen;
1115    pScreen->CloseScreen = RADEONCloseScreen_KMS;
1116    pScreen->SaveScreen  = RADEONSaveScreen_KMS;
1117    info->BlockHandler = pScreen->BlockHandler;
1118    pScreen->BlockHandler = RADEONBlockHandler_KMS;
1119
1120    if (!AddCallback(&FlushCallback, radeon_flush_callback, pScrn))
1121        return FALSE;
1122
1123    info->CreateScreenResources = pScreen->CreateScreenResources;
1124    pScreen->CreateScreenResources = RADEONCreateScreenResources_KMS;
1125
1126   if (!xf86CrtcScreenInit (pScreen))
1127       return FALSE;
1128
1129   /* Wrap pointer motion to flip touch screen around */
1130//    info->PointerMoved = pScrn->PointerMoved;
1131//    pScrn->PointerMoved = RADEONPointerMoved;
1132
1133    if (!drmmode_setup_colormap(pScreen, pScrn))
1134	return FALSE;
1135
1136   /* Note unused options */
1137    if (serverGeneration == 1)
1138	xf86ShowUnusedOptions(pScrn->scrnIndex, pScrn->options);
1139
1140    drmmode_init(pScrn, &info->drmmode);
1141
1142    xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
1143		   "RADEONScreenInit finished\n");
1144
1145    info->accel_state->XInited3D = FALSE;
1146    info->accel_state->engineMode = EXA_ENGINEMODE_UNKNOWN;
1147
1148    return TRUE;
1149}
1150
1151Bool RADEONEnterVT_KMS(VT_FUNC_ARGS_DECL)
1152{
1153    SCRN_INFO_PTR(arg);
1154    RADEONInfoPtr  info  = RADEONPTR(pScrn);
1155    int ret;
1156
1157    xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
1158		   "RADEONEnterVT_KMS\n");
1159
1160
1161    ret = drmSetMaster(info->dri->drmFD);
1162    if (ret)
1163	ErrorF("Unable to retrieve master\n");
1164    info->accel_state->XInited3D = FALSE;
1165    info->accel_state->engineMode = EXA_ENGINEMODE_UNKNOWN;
1166
1167    pScrn->vtSema = TRUE;
1168
1169    if (!drmmode_set_desired_modes(pScrn, &info->drmmode))
1170	return FALSE;
1171
1172    if (info->adaptor)
1173	RADEONResetVideo(pScrn);
1174
1175    return TRUE;
1176}
1177
1178
1179void RADEONLeaveVT_KMS(VT_FUNC_ARGS_DECL)
1180{
1181    SCRN_INFO_PTR(arg);
1182    RADEONInfoPtr  info  = RADEONPTR(pScrn);
1183
1184    xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
1185		   "RADEONLeaveVT_KMS\n");
1186
1187    drmDropMaster(info->dri->drmFD);
1188
1189#ifdef HAVE_FREE_SHADOW
1190    xf86RotateFreeShadow(pScrn);
1191#endif
1192
1193    xf86_hide_cursors (pScrn);
1194    info->accel_state->XInited3D = FALSE;
1195    info->accel_state->engineMode = EXA_ENGINEMODE_UNKNOWN;
1196
1197    xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
1198		   "Ok, leaving now...\n");
1199}
1200
1201
1202Bool RADEONSwitchMode_KMS(SWITCH_MODE_ARGS_DECL)
1203{
1204    SCRN_INFO_PTR(arg);
1205    Bool ret;
1206    ret = xf86SetSingleMode (pScrn, mode, RR_Rotate_0);
1207    return ret;
1208
1209}
1210
1211void RADEONAdjustFrame_KMS(ADJUST_FRAME_ARGS_DECL)
1212{
1213    SCRN_INFO_PTR(arg);
1214    RADEONInfoPtr  info        = RADEONPTR(pScrn);
1215    drmmode_adjust_frame(pScrn, &info->drmmode, x, y);
1216    return;
1217}
1218
1219static Bool radeon_setup_kernel_mem(ScreenPtr pScreen)
1220{
1221    ScrnInfoPtr pScrn = xf86ScreenToScrn(pScreen);
1222    RADEONInfoPtr info = RADEONPTR(pScrn);
1223    xf86CrtcConfigPtr   xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
1224    int cpp = info->CurrentLayout.pixel_bytes;
1225    int screen_size;
1226    int pitch, base_align;
1227    int total_size_bytes = 0;
1228    uint32_t tiling_flags = 0;
1229    struct radeon_surface surface;
1230
1231    if (info->accel_state->exa != NULL) {
1232	xf86DrvMsg(pScreen->myNum, X_ERROR, "Memory map already initialized\n");
1233	return FALSE;
1234    }
1235    if (info->r600_shadow_fb == FALSE) {
1236        info->accel_state->exa = exaDriverAlloc();
1237        if (info->accel_state->exa == NULL) {
1238	    xf86DrvMsg(pScreen->myNum, X_ERROR, "exaDriverAlloc failed\n");
1239	    return FALSE;
1240	}
1241    }
1242
1243    if (info->allowColorTiling) {
1244	if (info->ChipFamily >= CHIP_FAMILY_R600) {
1245		if (info->allowColorTiling2D) {
1246			tiling_flags |= RADEON_TILING_MACRO;
1247		} else {
1248			tiling_flags |= RADEON_TILING_MICRO;
1249		}
1250	} else
1251	    tiling_flags |= RADEON_TILING_MACRO;
1252    }
1253    pitch = RADEON_ALIGN(pScrn->virtualX, drmmode_get_pitch_align(pScrn, cpp, tiling_flags)) * cpp;
1254    screen_size = RADEON_ALIGN(pScrn->virtualY, drmmode_get_height_align(pScrn, tiling_flags)) * pitch;
1255    base_align = drmmode_get_base_align(pScrn, cpp, tiling_flags);
1256	if (info->ChipFamily >= CHIP_FAMILY_R600) {
1257		if(!info->surf_man) {
1258			xf86DrvMsg(pScreen->myNum, X_ERROR,
1259				   "failed to initialise surface manager\n");
1260			return FALSE;
1261		}
1262		memset(&surface, 0, sizeof(struct radeon_surface));
1263		surface.npix_x = pScrn->virtualX;
1264		surface.npix_y = pScrn->virtualY;
1265		surface.npix_z = 1;
1266		surface.blk_w = 1;
1267		surface.blk_h = 1;
1268		surface.blk_d = 1;
1269		surface.array_size = 1;
1270		surface.last_level = 0;
1271		surface.bpe = cpp;
1272		surface.nsamples = 1;
1273		surface.flags = RADEON_SURF_SCANOUT;
1274		surface.flags |= RADEON_SURF_SET(RADEON_SURF_TYPE_2D, TYPE);
1275		surface.flags |= RADEON_SURF_SET(RADEON_SURF_MODE_LINEAR_ALIGNED, MODE);
1276		if (tiling_flags & RADEON_TILING_MICRO) {
1277			surface.flags = RADEON_SURF_CLR(surface.flags, MODE);
1278			surface.flags |= RADEON_SURF_SET(RADEON_SURF_MODE_1D, MODE);
1279		}
1280		if (tiling_flags & RADEON_TILING_MACRO) {
1281			surface.flags = RADEON_SURF_CLR(surface.flags, MODE);
1282			surface.flags |= RADEON_SURF_SET(RADEON_SURF_MODE_2D, MODE);
1283		}
1284		if (radeon_surface_best(info->surf_man, &surface)) {
1285			xf86DrvMsg(pScreen->myNum, X_ERROR,
1286				   "radeon_surface_best failed\n");
1287			return FALSE;
1288		}
1289		if (radeon_surface_init(info->surf_man, &surface)) {
1290			xf86DrvMsg(pScreen->myNum, X_ERROR,
1291				   "radeon_surface_init failed\n");
1292			return FALSE;
1293		}
1294		pitch = surface.level[0].pitch_bytes;
1295		screen_size = surface.bo_size;
1296		base_align = surface.bo_alignment;
1297		tiling_flags = 0;
1298		switch (surface.level[0].mode) {
1299		case RADEON_SURF_MODE_2D:
1300			tiling_flags |= RADEON_TILING_MACRO;
1301			tiling_flags |= surface.bankw << RADEON_TILING_EG_BANKW_SHIFT;
1302			tiling_flags |= surface.bankh << RADEON_TILING_EG_BANKH_SHIFT;
1303			tiling_flags |= surface.mtilea << RADEON_TILING_EG_MACRO_TILE_ASPECT_SHIFT;
1304			tiling_flags |= eg_tile_split(surface.tile_split) << RADEON_TILING_EG_TILE_SPLIT_SHIFT;
1305			break;
1306		case RADEON_SURF_MODE_1D:
1307			tiling_flags |= RADEON_TILING_MICRO;
1308			break;
1309		default:
1310			break;
1311		}
1312		info->front_surface = surface;
1313	}
1314    {
1315	int cursor_size = 64 * 4 * 64;
1316	int c;
1317
1318	cursor_size = RADEON_ALIGN(cursor_size, RADEON_GPU_PAGE_SIZE);
1319	for (c = 0; c < xf86_config->num_crtc; c++) {
1320	    /* cursor objects */
1321            if (info->cursor_bo[c] == NULL) {
1322                info->cursor_bo[c] = radeon_bo_open(info->bufmgr, 0,
1323                                                    cursor_size, 0,
1324                                                    RADEON_GEM_DOMAIN_VRAM, 0);
1325                if (!info->cursor_bo[c]) {
1326                    ErrorF("Failed to allocate cursor buffer memory\n");
1327                    return FALSE;
1328                }
1329
1330                if (radeon_bo_map(info->cursor_bo[c], 1)) {
1331                    ErrorF("Failed to map cursor buffer memory\n");
1332                }
1333
1334                drmmode_set_cursor(pScrn, &info->drmmode, c, info->cursor_bo[c]);
1335                total_size_bytes += cursor_size;
1336            }
1337        }
1338    }
1339
1340    screen_size = RADEON_ALIGN(screen_size, RADEON_GPU_PAGE_SIZE);
1341    /* keep area front front buffer - but don't allocate it yet */
1342    total_size_bytes += screen_size;
1343
1344    info->dri->textureSize = 0;
1345
1346    if (info->front_bo == NULL) {
1347        info->front_bo = radeon_bo_open(info->bufmgr, 0, screen_size,
1348                                        base_align, RADEON_GEM_DOMAIN_VRAM, 0);
1349        if (info->r600_shadow_fb == TRUE) {
1350            if (radeon_bo_map(info->front_bo, 1)) {
1351                ErrorF("Failed to map cursor buffer memory\n");
1352            }
1353        }
1354#if X_BYTE_ORDER == X_BIG_ENDIAN
1355	switch (cpp) {
1356	case 4:
1357	    tiling_flags |= RADEON_TILING_SWAP_32BIT;
1358	    break;
1359	case 2:
1360	    tiling_flags |= RADEON_TILING_SWAP_16BIT;
1361	    break;
1362	}
1363#endif
1364	if (tiling_flags)
1365            radeon_bo_set_tiling(info->front_bo, tiling_flags, pitch);
1366    }
1367
1368    info->CurrentLayout.displayWidth = pScrn->displayWidth = pitch / cpp;
1369
1370    xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Front buffer size: %dK\n", info->front_bo->size/1024);
1371    radeon_kms_update_vram_limit(pScrn, screen_size);
1372    return TRUE;
1373}
1374
1375void radeon_kms_update_vram_limit(ScrnInfoPtr pScrn, int new_fb_size)
1376{
1377    xf86CrtcConfigPtr   xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
1378    RADEONInfoPtr info = RADEONPTR(pScrn);
1379    int remain_size_bytes;
1380    int total_size_bytes;
1381    int c;
1382
1383    for (c = 0; c < xf86_config->num_crtc; c++) {
1384	if (info->cursor_bo[c] != NULL) {
1385	    total_size_bytes += (64 * 4 * 64);
1386	}
1387    }
1388
1389    total_size_bytes += new_fb_size;
1390    remain_size_bytes = info->vram_size - new_fb_size;
1391    remain_size_bytes = (remain_size_bytes / 10) * 9;
1392    radeon_cs_set_limit(info->cs, RADEON_GEM_DOMAIN_VRAM, remain_size_bytes);
1393
1394    xf86DrvMsg(pScrn->scrnIndex, X_INFO, "VRAM usage limit set to %dK\n", remain_size_bytes / 1024);
1395}
1396
1397
1398#endif
1399