Tracking down bug #12503, looking for comment on my theory
Alex Villacís Lasso
a_villacis at palosanto.com
Wed Jan 16 11:24:20 PST 2008
I post this so that the experts on the mailing list can tell me whether
my understanding of the problem is sane (or insane). All comments apply
to my home machine, which reserves 16M for video memory reports the
following on lspci -v:
01:00.0 VGA compatible controller: S3 Inc. VT8375 [ProSavage8 KM266/KL266]
(prog-if 00 [VGA])
Subsystem: S3 Inc. VT8375 [ProSavage8 KM266/KL266]
Flags: bus master, 66MHz, medium devsel, latency 32, IRQ 11
Memory at dfe80000 (32-bit, non-prefetchable) [size=512K]
Memory at d0000000 (32-bit, prefetchable) [size=128M]
Expansion ROM at dfe70000 [disabled] [size=64K]
Capabilities: [dc] Power Management version 2
Capabilities: [80] AGP version 2.0
First, there is a serious regression in the current git of
xf86-video-savage, in which HEAD
(9c959f53ca8376aa136a9d434c3383cdb20487c2) will reliably lock up the
machine on X server startup whenever XSERVER_LIBPCIACCESS is *not* set
(as is the case in Fedora 8), so that a hard reset is needed to fix it.
I filed bug 12503 for it at bugs.freedesktop.org. After some tests, I
found that 1eec792391d9ce9127817107100a53382f167749 still works in my
case, but 514dc647d108e179965adb1377b1d4c011afa367 does not. I have
enabled tracing in the driver, and I have seen the following:
As I understand it, the driver needs three main memory areas:
- Framebuffer memory
- Memory-mapped I/O (MMIO)
- AGP aperture
It seems that some savages report three separate memory areas for all
three roles. Others, like my chipset, report only two, and use different
areas inside the bigger one (128M at 0xd0000000 in my case) for both the
framebuffer and the aperture.
Before the commit at 514dc647d108e179965adb1377b1d4c011afa367, the
driver does one memory mapping for every PCI area, and then hands out
the addresses for the memory roles. In my setup, the driver did one big
128M mapping for the framebuffer, then calculated an offset for the
aperture within the mapping:
(**) SAVAGE(0): Option: Enable use of the BCI for Xv
SavageMapMem()
-PHYS: MmioBase.........at 0xdfe80000, 524288 bytes
-PHYS: FrameBufferBase..at 0xd0000000, 134217728 bytes
-PHYS: ApertureBase.....at 0xd2000000, 134217728 bytes
-(==) SAVAGE(0): Write-combining range (0xd0000000,0x8000000)
SavageEnableMMIO
-MAP: MapBase (MMIO)..at 0xb7c17000
-MAP: FBBase..........at 0xafc17000
-MAP: ApertureMap.....at 0xb1c17000
(==) SAVAGE(0): Using gamma correction (1.0, 1.0, 1.0)
-(--) SAVAGE(0): probed videoram: 16384k
...
-(--) SAVAGE(0): Detected current MCLK value of 14.318 MHz
...
SavageMapMem()
-PHYS: MmioBase.........at 0xdfe80000, 524288 bytes
-PHYS: FrameBufferBase..at 0xd0000000, 134217728 bytes
-PHYS: ApertureBase.....at 0xd2000000, 134217728 bytes
-(==) SAVAGE(0): Write-combining range (0xd0000000,0x8000000)
-SavageEnableMMIO
-MAP: MapBase (MMIO)..at 0xafb06000
-MAP: FBBase..........at 0xa7b06000
-MAP: ApertureMap.....at 0xa9b06000
SavageSave()
-(II) SAVAGE(0): 4740 kB of Videoram needed for 3D; 16384 kB of Videoram
available
-(II) SAVAGE(0): Sufficient Videoram available for 3D
-(II) SAVAGE(0): [drm] bpp: 16 depth: 16
-(II) SAVAGE(0): [drm] Sarea 2200+284: 2484
SavageMapMem is called twice on startup. More on this later.
Please note that the videoram is correctly detected as 16M and the MCLK
value appears to be correct.
After the commit, the driver does not make one mapping per memory area,
but one mapping per memory role, with different sizes and offsets. In my
setup, instead of two mappings (one for shared framebuffer/aperture, one
for MMIO), it ends up doing three:
(**) SAVAGE(0): Option: Enable use of the BCI for Xv
SavageMapMem()
+PHYS: MmioRegion.base...at 0xdfe80000, 524288 bytes
+PHYS: FbRegion.base..at 0xd0000000, 0 bytes
+PHYS: ApertureRegion.base.....at 0xd2000000, 83886080 bytes
+(II) SAVAGE(0): Splitting WC range: base: 0xd2000000, size: 0x5000000
+(II) SAVAGE(0): Splitting WC range: base: 0xd4000000, size: 0x3000000
+(==) SAVAGE(0): Write-combining range (0xd6000000,0x1000000)
+(==) SAVAGE(0): Write-combining range (0xd4000000,0x3000000)
+(==) SAVAGE(0): Write-combining range (0xd2000000,0x5000000)
+MAP: ApertureMap.....at 0xb3cec000
+(==) SAVAGE(0): Write-combining range (0xdfe80000,0x80000)
+MAP: MapBase.........at 0xb2c6c000
SavageEnableMMIO
+MAP: (ends here)
(==) SAVAGE(0): Using gamma correction (1.0, 1.0, 1.0)
+(--) SAVAGE(0): probed videoram: 4096k
(II) Loading sub module "ddc"
...
+(--) SAVAGE(0): Detected current MCLK value of 3.580 MHz
...
SavageMapMem()
+PHYS: MmioRegion.base...at 0xdfe80000, 524288 bytes
+PHYS: FbRegion.base..at 0xd0000000, 4194304 bytes
+PHYS: ApertureRegion.base.....at 0xd2000000, 83886080 bytes
+(==) SAVAGE(0): Write-combining range (0xd0000000,0x400000)
+MAP: FBBase..........at 0xb27db000
+MAP: (ends here)
SavageSave()
+(WW) SAVAGE(0): Cannot read colourmap from VGA. Will restore with default
+(II) SAVAGE(0): 4740 kB of Videoram needed for 3D; 4096 kB of Videoram
available
+(EE) SAVAGE(0): Insufficient Videoram available for 3D -- Try a lower
color depth or smaller desktop. For integrated savages try increasing
the videoram in the BIOS.
+(EE) SAVAGE(0): DRI isn't enabled
SavageModeInit(1024x768, 65000Hz)
For starters, both MCLK and videoram size are now incorrectly detected.
Then the colormap cannot be retrieved. Finally the hang happens.
Looking at the code, there are several things that might be wrong with this:
1) Previously, all the areas got mapped with xf86MapPciMem() and the
VIDMEM_MMIO flag, and the function sorted out the write-combining later.
The proof is that the message (==) SAVAGE(0): Write-combining range
(0xd0000000,0x8000000) eventually appeared. Now, all the areas
(including MMIO) are being mapped as VIDMEM_FRAMEBUFFER. This can't be
right... or is it?
src/savage_driver.c line 3163
-------------------
if (psav->MmioRegion.memory == NULL) {
#ifdef XSERVER_LIBPCIACCESS
err = pci_device_map_range(psav->PciInfo, psav->MmioRegion.base,
psav->MmioRegion.size,
(PCI_DEV_MAP_FLAG_WRITABLE),
& psav->MmioRegion.memory);
#else
psav->MmioRegion.memory =
xf86MapPciMem(pScrn->scrnIndex, VIDMEM_FRAMEBUFFER, /* <---
Should this be VIDMEM_MMIO instead? */
psav->PciTag, psav->MmioRegion.base,
psav->MmioRegion.size);
err = (psav->MmioRegion.memory == NULL) ? errno : 0;
#endif
-------------------
In my opinion, this is the most likely cause of the hang, since videoram
detection, MCLK detection, and colormap all require register (MMIO)
access, and all of these are affected prior to the hang.
2) Previously, there were just two big mmaps, starting at the beginning
of the PCI areas. Now there are three, and none of them cover all of the
area, and one of them starts at an offset from the beginning of the PCI
area. In addition, all mmaps were previously powers of two, and now they
are not (at least the aperture one).
Personally I am leaning towards 1, but I would like to know your opinion
on this. Feel free to ask questions.
Alex Villacís Lasso
--
perl -e '$x=2.4;print sprintf("%.0f + %.0f = %.0f\n",$x,$x,$x+$x);'
More information about the xorg
mailing list