|
@@ -2473,24 +2473,37 @@ static void disable_second_display_channel(void)
|
|
|
viafb_write_reg_mask(CR6A, VIACR, BIT6, BIT6);
|
|
|
}
|
|
|
|
|
|
+static u_int16_t via_function3[] = {
|
|
|
+ CLE266_FUNCTION3, KM400_FUNCTION3, CN400_FUNCTION3, CN700_FUNCTION3,
|
|
|
+ CX700_FUNCTION3, KM800_FUNCTION3, KM890_FUNCTION3, P4M890_FUNCTION3,
|
|
|
+ P4M900_FUNCTION3, VX800_FUNCTION3, VX855_FUNCTION3,
|
|
|
+};
|
|
|
+
|
|
|
+/* Get the BIOS-configured framebuffer size from PCI configuration space
|
|
|
+ * of function 3 in the respective chipset */
|
|
|
int viafb_get_fb_size_from_pci(void)
|
|
|
{
|
|
|
- unsigned long configid, deviceid, FBSize = 0;
|
|
|
- int VideoMemSize;
|
|
|
- int DeviceFound = false;
|
|
|
-
|
|
|
- for (configid = 0x80000000; configid < 0x80010800; configid += 0x100) {
|
|
|
- outl(configid, (unsigned long)0xCF8);
|
|
|
- deviceid = (inl((unsigned long)0xCFC) >> 16) & 0xffff;
|
|
|
-
|
|
|
- switch (deviceid) {
|
|
|
- case CLE266:
|
|
|
- case KM400:
|
|
|
- outl(configid + 0xE0, (unsigned long)0xCF8);
|
|
|
- FBSize = inl((unsigned long)0xCFC);
|
|
|
- DeviceFound = true; /* Found device id */
|
|
|
- break;
|
|
|
+ int i;
|
|
|
+ u_int8_t offset = 0;
|
|
|
+ u_int32_t FBSize;
|
|
|
+ u_int32_t VideoMemSize;
|
|
|
+
|
|
|
+ /* search for the "FUNCTION3" device in this chipset */
|
|
|
+ for (i = 0; i < ARRAY_SIZE(via_function3); i++) {
|
|
|
+ struct pci_dev *pdev;
|
|
|
+
|
|
|
+ pdev = pci_get_device(PCI_VENDOR_ID_VIA, via_function3[i],
|
|
|
+ NULL);
|
|
|
+ if (!pdev)
|
|
|
+ continue;
|
|
|
+
|
|
|
+ DEBUG_MSG(KERN_INFO "Device ID = %x\n", pdev->device);
|
|
|
|
|
|
+ switch (pdev->device) {
|
|
|
+ case CLE266_FUNCTION3:
|
|
|
+ case KM400_FUNCTION3:
|
|
|
+ offset = 0xE0;
|
|
|
+ break;
|
|
|
case CN400_FUNCTION3:
|
|
|
case CN700_FUNCTION3:
|
|
|
case CX700_FUNCTION3:
|
|
@@ -2500,21 +2513,22 @@ int viafb_get_fb_size_from_pci(void)
|
|
|
case P4M900_FUNCTION3:
|
|
|
case VX800_FUNCTION3:
|
|
|
case VX855_FUNCTION3:
|
|
|
- /*case CN750_FUNCTION3: */
|
|
|
- outl(configid + 0xA0, (unsigned long)0xCF8);
|
|
|
- FBSize = inl((unsigned long)0xCFC);
|
|
|
- DeviceFound = true; /* Found device id */
|
|
|
- break;
|
|
|
-
|
|
|
- default:
|
|
|
+ /*case CN750_FUNCTION3: */
|
|
|
+ offset = 0xA0;
|
|
|
break;
|
|
|
}
|
|
|
|
|
|
- if (DeviceFound)
|
|
|
+ if (!offset)
|
|
|
break;
|
|
|
+
|
|
|
+ pci_read_config_dword(pdev, offset, &FBSize);
|
|
|
+ pci_dev_put(pdev);
|
|
|
}
|
|
|
|
|
|
- DEBUG_MSG(KERN_INFO "Device ID = %lx\n", deviceid);
|
|
|
+ if (!offset) {
|
|
|
+ printk(KERN_ERR "cannot determine framebuffer size\n");
|
|
|
+ return -EIO;
|
|
|
+ }
|
|
|
|
|
|
FBSize = FBSize & 0x00007000;
|
|
|
DEBUG_MSG(KERN_INFO "FB Size = %x\n", FBSize);
|