[parisc-linux-cvs] Legacy inventory cleanups & Asp sound fixes
Matthew Wilcox
willy@ldl.fc.hp.com
Thu, 30 Aug 2001 10:53:59 -0600
* Put an appropriate copyright & licence on the file.
* the 715old stuff is bogus. I've tried a 715/50 & a 715/75.
* sanitise the comments, and move them outofline.
* remove some unnecessary duplicate checks from do_legacy_inventory.
* factor common code from do_legacy_inventory into legacy_create_device.
* Remove setting of stype altogether -- it wasn't getting used anywhere.
* Fill in dev->parent for subdevices of Asp -- harmony now finds an irq
on Asp-based machines.
Index: arch/parisc/kernel/inventory.c
===================================================================
RCS file: /home/cvs/parisc/linux/arch/parisc/kernel/inventory.c,v
retrieving revision 1.32
diff -u -p -r1.32 inventory.c
--- arch/parisc/kernel/inventory.c 2001/08/14 16:54:52 1.32
+++ arch/parisc/kernel/inventory.c 2001/08/30 16:44:51
@@ -1,5 +1,17 @@
-/* Copyright (c) 1999 The Puffin Group */
-/* Written by David Kennedy and Alex deVries */
+/*
+ * inventory.c
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ *
+ * Copyright (c) 1999 The Puffin Group (David Kennedy and Alex deVries)
+ * Copyright (c) 2001 Matthew Wilcox for Hewlett-Packard
+ *
+ * We query PDC for devices it knows about, and do an architected buswalk
+ * in order to find devices it won't tell us about.
+ */
#include <linux/types.h>
#include <linux/kernel.h>
@@ -393,179 +405,64 @@ static void do_system_map_memconfig(void
/* All of the older legacy box (32 bit only) code goes here */
-/* The following checks to see if the system is a 715/old. This might
-** sound a bit unusual, but there are some workarounds required for these
-** machines. These machines are the 715/33, 715/50 and 715/75.
-**
-** This function returns 1 if we are a 715/old, and 0 if we're not.
-*/
-static int check_if_715old(void)
+static struct parisc_device *legacy_create_device(struct pdc_memory_map *r_addr,
+ struct pdc_module_path *module_path)
{
- /* We trust that the CPU HVersion returned by PDC is correct.
- **
- ** Machine CPU_HVERSION real life verification
- **
- ** Scorpio (715/50): 0x310 Yes
- ** Scorpio Jr.(715/33) 0x311 Yes
- ** Strider-50 (715S/50) 0x312 No
- ** Strider-33 (715S/33) 0x313 No
- ** Trailways-50 (715T/50) 0x314 No
- ** Trailways-33 (715T/33) 0x315 No
- ** Scorpio Sr.(715/75) 0x316 Yes
- **
- */
-
- if (CPU_HVERSION >= 0x310 && CPU_HVERSION <=0x316)
- return 1;
+ struct parisc_device *hp_dev;
+ int status = pdc_mem_map_hpa(r_addr, module_path);
+ if (status != PDC_RET_OK)
+ return NULL;
+
+ hp_dev = alloc_pa_dev(r_addr->hpa);
+ if (hp_dev == NULL)
+ return NULL;
- return 0;
+ register_pa_dev(hp_dev);
+ return hp_dev;
}
+/**
+ * do_legacy_inventory
+ *
+ * Before PDC_SYSTEM_MAP was invented, the PDC_MEM_MAP call was used.
+ * To use it, we initialise the mod_path.bc to 0xff and try all values of
+ * mod to get the HPA for the top-level devices. Bus adapters may have
+ * sub-devices which are discovered by setting bc[5] to 0 and bc[4] to the
+ * module, then trying all possible functions.
+ */
int do_legacy_inventory(void)
{
- int i, mod, num = 0;
- int status;
- unsigned int hw_type;
- unsigned int func;
- unsigned long bytecnt;
- struct pdc_module_path module_path;
- struct pdc_memory_map r_addr;
- u8 iodc_data[32 * sizeof(long)];
-
- /* This is undocumented at the time of writing, but basically
- ** we're setting up mod_path so that bc[0..4]=0xff, and step
- ** through mod to get the "Path Structure for GSC Modules". If
- ** it works, use the returned HPA and determine the hardware type.
- */
-
- memset(module_path.bc, 0xff, sizeof(module_path.bc));
-
+ int mod, num = 0;
for (mod = 0; mod < 16; mod++) {
- char *stype = NULL;
-
+ struct parisc_device *dev;
+ struct pdc_module_path module_path;
+ struct pdc_memory_map r_addr;
+ unsigned int func;
+
+ memset(module_path.bc, 0xff, sizeof(module_path.bc));
module_path.mod = mod;
-
- status = pdc_mem_map_hpa(&r_addr, &module_path);
- if (status != PDC_RET_OK)
- continue;
-
- /* On 715/old systems, pdc_iodc_read() seems to fail
- ** and simply hang the system when querying the onboard
- ** graphics cards, which are at location 0xf800000. Because
- ** of this, I'm going to skip them. We might have to rewrite
- ** an exception to this so it ends up in the inventory table.
- ** In any case, this is where the hook is.
- */
- if (r_addr.hpa == 0xf8000000 && check_if_715old()) {
- printk(KERN_ERR "Using Alex's odd 715/old exception, "
- "onboard graphics won't be inventoried!\n");
+ dev = legacy_create_device(&r_addr, &module_path);
+ if (!dev)
continue;
- }
+ num++;
- status = pdc_iodc_read(&bytecnt, (void *)r_addr.hpa, 0,
- &iodc_data, 32);
- if (status != PDC_RET_OK)
+ if (dev->id.hw_type != HPHW_BA)
continue;
-
- hw_type = iodc_data[3] & 0x1f;
- switch (hw_type) {
- case HPHW_NPROC:
- stype = "Processor";
- break; /* 0 */
- case HPHW_MEMORY:
- stype = "Memory";
- break; /* 1 */
- case HPHW_B_DMA:
- stype = "Type B DMA";
- break; /* 2 */
- case HPHW_A_DMA:
- stype = "Type A DMA";
- break; /* 4 */
- case HPHW_A_DIRECT:
- stype = "Type A Direct";
- break; /* 5 */
- case HPHW_BCPORT:
- stype = "Bus Converter Port";
- break; /* 7 */
- case HPHW_CONSOLE:
- stype = "Console";
- break; /* 9 */
- case HPHW_FIO:
- stype = "Foreign I/O (Graphics)";
- break; /* 10 */
- case HPHW_BA:
- stype = "Bus Adapter";
- break; /* 11 */
- case HPHW_IOA:
- stype = "I/O Adapter";
- break; /* 12 */
- case HPHW_BRIDGE:
- stype = "Bridge";
- break; /* 13 */
- case HPHW_FABRIC:
- stype = "Fabric";
- break; /* 14 */
- case HPHW_FAULTY:
- stype = "Faulty HW";
- break; /* 31 */
- case HPHW_OTHER: /* 42 */
- default:
- printk(KERN_WARNING "Don't know this hw_type: %d\n", hw_type);
- break;
- } /* switch() */
- /* This is kluged. But don't want to replicate code for
- ** most of the above cases.
- */
- if (stype) {
- struct parisc_device *hp_dev;
-
- status = pdc_mem_map_hpa(&r_addr, &module_path);
- if (status == PDC_RET_OK
- && (hp_dev = alloc_pa_dev(r_addr.hpa))) {
-
- register_pa_dev(hp_dev);
- ++num;
- }
-
- if (hw_type == HPHW_BA) {
- /* Now, we're checking for devices for each
- ** module. I seem to think that the
- ** modules in question are Lasi (2), 2nd Lasi (6)
- ** Wax (5). To do this, set bc[5]=0, and set
- ** bc[4] to the module, and step through the
- ** functions.
- */
-
- for (i = 0; i < 4; i++) {
- module_path.bc[i] = 0xff;
- }
-
- module_path.bc[4] = mod;
- for (func = 0; func < 16; func++) {
- module_path.mod = func;
- module_path.bc[5] = 0;
-
- status = pdc_mem_map_hpa(&r_addr,
- &module_path);
- if (status != PDC_RET_OK)
- continue;
-
- hp_dev = alloc_pa_dev(r_addr.hpa);
- if (hp_dev) {
- register_pa_dev(hp_dev);
- ++num;
- }
- }
-
- } /* hw_type == HPHW_BA */
-
- /* reset module_path.bc[] */
- memset(module_path.bc, 0xff,
- sizeof(module_path.bc));
+ memset(module_path.bc, 0xff, 4);
+ module_path.bc[4] = mod;
- } /* if (stype) */
- } /* for() */
+ for (func = 0; func < 16; func++) {
+ struct parisc_device *child;
+ module_path.bc[5] = 0;
+ module_path.mod = func;
+ child = legacy_create_device(&r_addr, &module_path);
+ if (!child)
+ continue;
+ num++;
+ child->parent = dev;
+ }
+ }
return num;
}
Index: drivers/gsc/busdevice.c
===================================================================
RCS file: /home/cvs/parisc/linux/drivers/gsc/busdevice.c,v
retrieving revision 1.24
diff -u -p -r1.24 busdevice.c
--- drivers/gsc/busdevice.c 2001/08/14 16:54:54 1.24
+++ drivers/gsc/busdevice.c 2001/08/30 16:44:51
@@ -51,7 +51,12 @@ int busdevice_alloc_irq(struct parisc_de
{
struct busdevice *busdev = busdev_list;
int irq;
+ int hpa = dev->hpa;
+ if (dev->parent) {
+ hpa = dev->parent->hpa;
+ }
+
if (!busdev) {
printk(KERN_ERR "%s(0x%p): No LASI/ASP/WAX found in system yet !\n",
__FUNCTION__, dev);
@@ -62,7 +67,7 @@ int busdevice_alloc_irq(struct parisc_de
/* deller: Changed to test only the 3 highest nibbles of the
address-range, since ASP uses hpa of 0xf080yyyy, but devices are
at adress 0xf082yyyy ! */
- while (busdev && ((busdev->hpa & ~0xfffff) != (dev->hpa & ~0xfffff))) {
+ while (busdev && ((busdev->hpa & ~0xfffff) != (hpa & ~0xfffff))) {
busdev = busdev->next;
}