summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJerome Glisse <jglisse@redhat.com>2009-09-16 15:18:40 +0200
committerJerome Glisse <jglisse@redhat.com>2009-09-30 23:03:49 +0200
commitd302481493ff61eb7f8648b7afe7407b6b653cf7 (patch)
tree3f555a7c4553317d1061711202c3ea2517e06f71
parent7968e1fb89f6b59d1654df48249bf4b81990c008 (diff)
radeon/kms: fallback to shadowfb if kernel report acceleration is off
This will fallback to shadowfb is GPU accel failed somewhere during KMS kernel init.
-rw-r--r--src/drmmode_display.c2
-rw-r--r--src/radeon_kms.c45
2 files changed, 34 insertions, 13 deletions
diff --git a/src/drmmode_display.c b/src/drmmode_display.c
index e6b948c4..c9037b4e 100644
--- a/src/drmmode_display.c
+++ b/src/drmmode_display.c
@@ -183,7 +183,7 @@ void drmmode_copy_fb(ScrnInfoPtr pScrn, drmmode_ptr drmmode)
int i;
int pitch = pScrn->displayWidth * info->CurrentLayout.pixel_bytes;
- if (info->ChipFamily >= CHIP_FAMILY_R600)
+ if (info->accelOn == FALSE)
return;
for (i = 0; i < xf86_config->num_crtc; i++) {
diff --git a/src/radeon_kms.c b/src/radeon_kms.c
index e2f716e9..fa493926 100644
--- a/src/radeon_kms.c
+++ b/src/radeon_kms.c
@@ -172,6 +172,24 @@ static void RADEONBlockHandler_KMS(int i, pointer blockData,
radeon_cs_flush_indirect(pScrn);
}
+static Bool RADEONIsAccelWorking(ScrnInfoPtr pScrn)
+{
+ RADEONInfoPtr info = RADEONPTR(pScrn);
+ struct drm_radeon_info ginfo;
+ int r;
+ uint32_t tmp;
+
+ memset(&ginfo, 0, sizeof(ginfo));
+ ginfo.request = 0x3;
+ ginfo.value = (uint64_t)&tmp;
+ r = drmCommandWriteRead(info->dri->drmFD, DRM_RADEON_INFO, &ginfo, sizeof(ginfo));
+ if (r)
+ return FALSE;
+ if (tmp)
+ return TRUE;
+ return FALSE;
+}
+
static Bool RADEONPreInitAccel_KMS(ScrnInfoPtr pScrn)
{
RADEONInfoPtr info = RADEONPTR(pScrn);
@@ -180,16 +198,14 @@ static Bool RADEONPreInitAccel_KMS(ScrnInfoPtr pScrn)
xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Unable to allocate accel_state rec!\n");
return FALSE;
}
-#if 0
- if (info->ChipFamily >= CHIP_FAMILY_R600) {
+ if (!RADEONIsAccelWorking(pScrn)) {
xf86DrvMsg(pScrn->scrnIndex, X_INFO,
- "Using shadowfb for KMS on R600+\n");
+ "GPU accel not working, using shadowfb for KMS\n");
info->r600_shadow_fb = TRUE;
if (!xf86LoadSubModule(pScrn, "shadow"))
info->r600_shadow_fb = FALSE;
return TRUE;
}
-#endif
if ((info->ChipFamily == CHIP_FAMILY_RS100) ||
(info->ChipFamily == CHIP_FAMILY_RS200) ||
@@ -421,12 +437,12 @@ Bool RADEONPreInit_KMS(ScrnInfoPtr pScrn, int flags)
mminfo.gart_size, mminfo.vram_size, mminfo.vram_visible);
}
}
-
+#if 0
if (info->ChipFamily < CHIP_FAMILY_R600) {
info->useEXA = TRUE;
info->directRenderingEnabled = TRUE;
}
-
+#endif
RADEONSetPitch(pScrn);
/* Set display resolution */
@@ -663,6 +679,10 @@ Bool RADEONScreenInit_KMS(int scrnIndex, ScreenPtr pScreen,
"Direct rendering disabled\n");
}
+ if (info->r600_shadow_fb) {
+ xf86DrvMsg(scrnIndex, X_INFO, "Acceleration disabled\n");
+ info->accelOn = FALSE;
+ } else {
if (!xf86ReturnOptValBool(info->Options, OPTION_NOACCEL, FALSE)) {
xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
"Initializing Acceleration\n");
@@ -679,6 +699,7 @@ Bool RADEONScreenInit_KMS(int scrnIndex, ScreenPtr pScreen,
xf86DrvMsg(scrnIndex, X_INFO, "Acceleration disabled\n");
info->accelOn = FALSE;
}
+ }
/* Init DPMS */
xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
@@ -706,11 +727,12 @@ Bool RADEONScreenInit_KMS(int scrnIndex, ScreenPtr pScreen,
*/
/* xf86DiDGAInit(pScreen, info->LinearAddr + pScrn->fbOffset); */
#endif
-
- /* Init Xv */
- xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
- "Initializing Xv\n");
- RADEONInitVideo(pScreen);
+ if (info->r600_shadow_fb == FALSE) {
+ /* Init Xv */
+ xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, RADEON_LOGLEVEL_DEBUG,
+ "Initializing Xv\n");
+ RADEONInitVideo(pScreen);
+ }
if (info->r600_shadow_fb == TRUE) {
if (!shadowSetup(pScreen)) {
@@ -770,7 +792,6 @@ Bool RADEONEnterVT_KMS(int scrnIndex, int flags)
ret = drmSetMaster(info->dri->drmFD);
if (ret)
ErrorF("Unable to retrieve master\n");
-
info->accel_state->XInited3D = FALSE;
info->accel_state->engineMode = EXA_ENGINEMODE_UNKNOWN;