patch re-generated for kernel-3.10.0-514.6.1.el7 fixes symptom seen as https://bugs.centos.org/view.php?id=10973 Return-Path: Received: from localhost (timessq103.t.subnet.rcn.com [206.71.234.194]) by mail.linuxfoundation.org (Postfix) with ESMTPSA id 7A27949B; Sat, 29 Oct 2016 13:50:01 +0000 (UTC) From: Greg Kroah-Hartman To: linux-kernel.vger.kernel.org Subject: [PATCH 4.4 15/51] drm/i915: Account for TSEG size when determining 865G stolen base Date: Sat, 29 Oct 2016 09:49:16 -0400 Message-Id: <20161029134923.122516823@linuxfoundation.org> X-Mailer: git-send-email 2.10.1 In-Reply-To: <20161029134922.501052551@linuxfoundation.org> References: <20161029134922.501052551@linuxfoundation.org> User-Agent: quilt/0.64 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 4.4-stable review patch. If anyone has any objections, please let me know. ------------------ From: Ville Syrjälä commit d721b02fd00bf133580f431b82ef37f3b746dfb2 upstream. Looks like the TSEG lives just above TOUD, stolen comes after TSEG. The spec seems somewhat self-contradictory in places, in the ESMRAMC register desctription it says: TSEG Size: 10=(TOUD + 512 KB) to TOUD 11 =(TOUD + 1 MB) to TOUD so that agrees with TSEG being at TOUD. But the example given elsehwere in the spec says: TOUD equals 62.5 MB = 03E7FFFFh TSEG selected as 512 KB in size, Graphics local memory selected as 1 MB in size General System RAM available in system = 62.5 MB General system RAM range00000000h to 03E7FFFFh TSEG address range03F80000h to 03FFFFFFh TSEG pre-allocated from03F80000h to 03FFFFFFh Graphics local memory pre-allocated from03E80000h to 03F7FFFFh so here we have TSEG above stolen. Real world evidence agrees with the TOUD->TSEG->stolen order however, so let's fix up the code to account for the TSEG size. Fixes: 0ad98c74e093 ("drm/i915: Determine the stolen memory base address on gen2") Fixes: a4dff76924fe ("x86/gpu: Add Intel graphics stolen memory quirk for gen2 platforms") Reported-by: Taketo Kabe Tested-by: Taketo Kabe Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=96473 Signed-off-by: Ville Syrjälä Link: http://patchwork.freedesktop.org/patch/msgid/1470653919-27251-1-git-send-email-ville.syrjala.linux.intel.com Link: http://download.intel.com/design/chipsets/datashts/25251405.pdf Reviewed-by: Chris Wilson Signed-off-by: Greg Kroah-Hartman --- diff -up ./arch/x86/kernel/early-quirks.c.i815 ./arch/x86/kernel/early-quirks.c --- ./arch/x86/kernel/early-quirks.c.i815 2016-12-11 00:27:13.000000000 +0900 +++ ./arch/x86/kernel/early-quirks.c 2017-02-03 21:50:29.000000000 +0900 @@ -320,12 +320,11 @@ static u32 __init i85x_stolen_base(int n static u32 __init i865_stolen_base(int num, int slot, int func, size_t stolen_size) { - /* - * FIXME is the graphics stolen memory region - * always at TOUD? Ie. is it always the last - * one to be allocated by the BIOS? - */ - return read_pci_config_16(0, 0, 0, I865_TOUD) << 16; + u16 toud = 0; + + toud = read_pci_config_16(0, 0, 0, I865_TOUD); + + return (phys_addr_t)(toud << 16) + i845_tseg_size(); } static size_t __init i830_stolen_size(int num, int slot, int func) diff -up ./drivers/gpu/drm/i915/i915_gem_stolen.c.i815 ./drivers/gpu/drm/i915/i915_gem_stolen.c --- ./drivers/gpu/drm/i915/i915_gem_stolen.c.i815 2016-12-11 00:27:13.000000000 +0900 +++ ./drivers/gpu/drm/i915/i915_gem_stolen.c 2017-02-03 21:50:30.000000000 +0900 @@ -110,17 +110,28 @@ static unsigned long i915_stolen_to_phys pci_read_config_dword(dev->pdev, 0x5c, &base); base &= ~((1<<20) - 1); } else if (IS_I865G(dev)) { + u32 tseg_size = 0; u16 toud = 0; + u8 tmp; + + pci_bus_read_config_byte(dev->pdev->bus, PCI_DEVFN(0, 0), + I845_ESMRAMC, &tmp); + + if (tmp & TSEG_ENABLE) { + switch (tmp & I845_TSEG_SIZE_MASK) { + case I845_TSEG_SIZE_512K: + tseg_size = KB(512); + break; + case I845_TSEG_SIZE_1M: + tseg_size = MB(1); + break; + } + } - /* - * FIXME is the graphics stolen memory region - * always at TOUD? Ie. is it always the last - * one to be allocated by the BIOS? - */ pci_bus_read_config_word(dev->pdev->bus, PCI_DEVFN(0, 0), I865_TOUD, &toud); - base = toud << 16; + base = (toud << 16) + tseg_size; } else if (IS_I85X(dev)) { u32 tseg_size = 0; u32 tom;