diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2013-06-08 11:35:20 -0700 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2013-06-08 11:35:20 -0700 |
commit | 6ea31c56a54ef79b46b56ad35a308db474d600d3 (patch) | |
tree | 1638f054f31493806b3c0ab25c4a412851d2d630 /drivers/gpu/drm/radeon/r600.c | |
parent | d7a39e300d0cea54379a7d92e11f2c8e5e5e2142 (diff) | |
parent | 0e32fde96bb9c1fa8fa477e52c1d6ae2f4995cea (diff) |
Merge branch 'drm-fixes' of git://people.freedesktop.org/~airlied/linux
Pull drm fixes from Dave Airlie:
"Regression fixers for the big 3:
- nouveau: hdmi audio, dac load detect, s/r regressions fixed
- radeon: long standing system hang fixed, hdmi audio and rs780 fast
fb fixes
- intel: one old regression, a WARN removal, and a stop X dying fix
Otherwise one mgag200 fix, a couple of arm build fixes, and a core use
after free fix."
* 'drm-fixes' of git://people.freedesktop.org/~airlied/linux:
drm/nv50/kms: use dac loadval from vbios, where it's available
drm/nv50/disp: force dac power state during load detect
drm/nv50-nv84/fifo: fix resume regression introduced by playlist race fix
drm/nv84/disp: Fix HDMI audio regression
drm/i915/sdvo: Use &intel_sdvo->ddc instead of intel_sdvo->i2c for DDC.
drm/radeon: don't allow audio on DCE6
drm/radeon: Use direct mapping for fast fb access on RS780/RS880 (v2)
radeon: Fix system hang issue when using KMS with older cards
drm/i915: no lvds quirk for hp t5740
drm/i915: Quirk the pipe A quirk in the modeset state checker
drm/i915: Fix spurious -EIO/SIGBUS on wedged gpus
drm/mgag200: Add missing write to index before accessing data register
drm/nouveau: use mdelay instead of large udelay constants
drm/tilcd: select BACKLIGHT_LCD_SUPPORT
drm: fix a use-after-free when GPU acceleration disabled
Diffstat (limited to 'drivers/gpu/drm/radeon/r600.c')
-rw-r--r-- | drivers/gpu/drm/radeon/r600.c | 53 |
1 files changed, 49 insertions, 4 deletions
diff --git a/drivers/gpu/drm/radeon/r600.c b/drivers/gpu/drm/radeon/r600.c index b45e6484867..0e534169592 100644 --- a/drivers/gpu/drm/radeon/r600.c +++ b/drivers/gpu/drm/radeon/r600.c @@ -1046,6 +1046,24 @@ int r600_mc_wait_for_idle(struct radeon_device *rdev) return -1; } +uint32_t rs780_mc_rreg(struct radeon_device *rdev, uint32_t reg) +{ + uint32_t r; + + WREG32(R_0028F8_MC_INDEX, S_0028F8_MC_IND_ADDR(reg)); + r = RREG32(R_0028FC_MC_DATA); + WREG32(R_0028F8_MC_INDEX, ~C_0028F8_MC_IND_ADDR); + return r; +} + +void rs780_mc_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v) +{ + WREG32(R_0028F8_MC_INDEX, S_0028F8_MC_IND_ADDR(reg) | + S_0028F8_MC_IND_WR_EN(1)); + WREG32(R_0028FC_MC_DATA, v); + WREG32(R_0028F8_MC_INDEX, 0x7F); +} + static void r600_mc_program(struct radeon_device *rdev) { struct rv515_mc_save save; @@ -1181,6 +1199,8 @@ static int r600_mc_init(struct radeon_device *rdev) { u32 tmp; int chansize, numchan; + uint32_t h_addr, l_addr; + unsigned long long k8_addr; /* Get VRAM informations */ rdev->mc.vram_is_ddr = true; @@ -1221,7 +1241,30 @@ static int r600_mc_init(struct radeon_device *rdev) if (rdev->flags & RADEON_IS_IGP) { rs690_pm_info(rdev); rdev->mc.igp_sideport_enabled = radeon_atombios_sideport_present(rdev); + + if (rdev->family == CHIP_RS780 || rdev->family == CHIP_RS880) { + /* Use K8 direct mapping for fast fb access. */ + rdev->fastfb_working = false; + h_addr = G_000012_K8_ADDR_EXT(RREG32_MC(R_000012_MC_MISC_UMA_CNTL)); + l_addr = RREG32_MC(R_000011_K8_FB_LOCATION); + k8_addr = ((unsigned long long)h_addr) << 32 | l_addr; +#if defined(CONFIG_X86_32) && !defined(CONFIG_X86_PAE) + if (k8_addr + rdev->mc.visible_vram_size < 0x100000000ULL) +#endif + { + /* FastFB shall be used with UMA memory. Here it is simply disabled when sideport + * memory is present. + */ + if (rdev->mc.igp_sideport_enabled == false && radeon_fastfb == 1) { + DRM_INFO("Direct mapping: aper base at 0x%llx, replaced by direct mapping base 0x%llx.\n", + (unsigned long long)rdev->mc.aper_base, k8_addr); + rdev->mc.aper_base = (resource_size_t)k8_addr; + rdev->fastfb_working = true; + } + } + } } + radeon_update_bandwidth_info(rdev); return 0; } @@ -3202,6 +3245,12 @@ static int r600_startup(struct radeon_device *rdev) } /* Enable IRQ */ + if (!rdev->irq.installed) { + r = radeon_irq_kms_init(rdev); + if (r) + return r; + } + r = r600_irq_init(rdev); if (r) { DRM_ERROR("radeon: IH init failed (%d).\n", r); @@ -3356,10 +3405,6 @@ int r600_init(struct radeon_device *rdev) if (r) return r; - r = radeon_irq_kms_init(rdev); - if (r) - return r; - rdev->ring[RADEON_RING_TYPE_GFX_INDEX].ring_obj = NULL; r600_ring_init(rdev, &rdev->ring[RADEON_RING_TYPE_GFX_INDEX], 1024 * 1024); |