mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2025-01-06 05:13:18 +00:00
[SPARC64]: Use in-kernel PROM tree for EBUS and ISA.
Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
de8d28b16f
commit
690c8fd31f
@ -136,7 +136,7 @@ void __init auxio_probe(void)
|
||||
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (!strcmp(edev->prom_name, "auxio"))
|
||||
if (!strcmp(edev->prom_node->name, "auxio"))
|
||||
goto ebus_done;
|
||||
}
|
||||
}
|
||||
|
@ -285,36 +285,38 @@ static inline void *ebus_alloc(size_t size)
|
||||
|
||||
static void __init ebus_ranges_init(struct linux_ebus *ebus)
|
||||
{
|
||||
int success;
|
||||
struct linux_prom_ebus_ranges *rngs;
|
||||
int len;
|
||||
|
||||
ebus->num_ebus_ranges = 0;
|
||||
success = prom_getproperty(ebus->prom_node, "ranges",
|
||||
(char *)ebus->ebus_ranges,
|
||||
sizeof(ebus->ebus_ranges));
|
||||
if (success != -1)
|
||||
ebus->num_ebus_ranges = (success/sizeof(struct linux_prom_ebus_ranges));
|
||||
rngs = of_get_property(ebus->prom_node, "ranges", &len);
|
||||
if (rngs) {
|
||||
memcpy(ebus->ebus_ranges, rngs, len);
|
||||
ebus->num_ebus_ranges =
|
||||
(len / sizeof(struct linux_prom_ebus_ranges));
|
||||
}
|
||||
}
|
||||
|
||||
static void __init ebus_intmap_init(struct linux_ebus *ebus)
|
||||
{
|
||||
int success;
|
||||
struct linux_prom_ebus_intmap *imap;
|
||||
struct linux_prom_ebus_intmask *imask;
|
||||
int len;
|
||||
|
||||
ebus->num_ebus_intmap = 0;
|
||||
success = prom_getproperty(ebus->prom_node, "interrupt-map",
|
||||
(char *)ebus->ebus_intmap,
|
||||
sizeof(ebus->ebus_intmap));
|
||||
if (success == -1)
|
||||
imap = of_get_property(ebus->prom_node, "interrupt-map", &len);
|
||||
if (!imap)
|
||||
return;
|
||||
|
||||
ebus->num_ebus_intmap = (success/sizeof(struct linux_prom_ebus_intmap));
|
||||
memcpy(ebus->ebus_intmap, imap, len);
|
||||
ebus->num_ebus_intmap = (len / sizeof(struct linux_prom_ebus_intmap));
|
||||
|
||||
success = prom_getproperty(ebus->prom_node, "interrupt-map-mask",
|
||||
(char *)&ebus->ebus_intmask,
|
||||
sizeof(ebus->ebus_intmask));
|
||||
if (success == -1) {
|
||||
prom_printf("%s: can't get interrupt-map-mask\n", __FUNCTION__);
|
||||
imask = of_get_property(ebus->prom_node, "interrupt-map-mask", &len);
|
||||
if (!imask) {
|
||||
prom_printf("EBUS: can't get interrupt-map-mask\n");
|
||||
prom_halt();
|
||||
}
|
||||
memcpy(&ebus->ebus_intmask, imask, sizeof(ebus->ebus_intmask));
|
||||
}
|
||||
|
||||
int __init ebus_intmap_match(struct linux_ebus *ebus,
|
||||
@ -341,19 +343,23 @@ int __init ebus_intmap_match(struct linux_ebus *ebus,
|
||||
return -1;
|
||||
}
|
||||
|
||||
void __init fill_ebus_child(int node, struct linux_prom_registers *preg,
|
||||
struct linux_ebus_child *dev, int non_standard_regs)
|
||||
void __init fill_ebus_child(struct device_node *dp,
|
||||
struct linux_prom_registers *preg,
|
||||
struct linux_ebus_child *dev,
|
||||
int non_standard_regs)
|
||||
{
|
||||
int regs[PROMREG_MAX];
|
||||
int irqs[PROMREG_MAX];
|
||||
int *regs;
|
||||
int *irqs;
|
||||
int i, len;
|
||||
|
||||
dev->prom_node = node;
|
||||
prom_getstring(node, "name", dev->prom_name, sizeof(dev->prom_name));
|
||||
printk(" (%s)", dev->prom_name);
|
||||
dev->prom_node = dp;
|
||||
printk(" (%s)", dp->name);
|
||||
|
||||
len = prom_getproperty(node, "reg", (void *)regs, sizeof(regs));
|
||||
dev->num_addrs = len / sizeof(regs[0]);
|
||||
regs = of_get_property(dp, "reg", &len);
|
||||
if (!regs)
|
||||
dev->num_addrs = 0;
|
||||
else
|
||||
dev->num_addrs = len / sizeof(regs[0]);
|
||||
|
||||
if (non_standard_regs) {
|
||||
/* This is to handle reg properties which are not
|
||||
@ -370,21 +376,21 @@ void __init fill_ebus_child(int node, struct linux_prom_registers *preg,
|
||||
int rnum = regs[i];
|
||||
if (rnum >= dev->parent->num_addrs) {
|
||||
prom_printf("UGH: property for %s was %d, need < %d\n",
|
||||
dev->prom_name, len, dev->parent->num_addrs);
|
||||
panic(__FUNCTION__);
|
||||
dp->name, len, dev->parent->num_addrs);
|
||||
prom_halt();
|
||||
}
|
||||
dev->resource[i].start = dev->parent->resource[i].start;
|
||||
dev->resource[i].end = dev->parent->resource[i].end;
|
||||
dev->resource[i].flags = IORESOURCE_MEM;
|
||||
dev->resource[i].name = dev->prom_name;
|
||||
dev->resource[i].name = dp->name;
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < PROMINTR_MAX; i++)
|
||||
dev->irqs[i] = PCI_IRQ_NONE;
|
||||
|
||||
len = prom_getproperty(node, "interrupts", (char *)&irqs, sizeof(irqs));
|
||||
if ((len == -1) || (len == 0)) {
|
||||
irqs = of_get_property(dp, "interrupts", &len);
|
||||
if (!irqs) {
|
||||
dev->num_irqs = 0;
|
||||
/*
|
||||
* Oh, well, some PROMs don't export interrupts
|
||||
@ -392,8 +398,8 @@ void __init fill_ebus_child(int node, struct linux_prom_registers *preg,
|
||||
*
|
||||
* Be smart about PS/2 keyboard and mouse.
|
||||
*/
|
||||
if (!strcmp(dev->parent->prom_name, "8042")) {
|
||||
if (!strcmp(dev->prom_name, "kb_ps2")) {
|
||||
if (!strcmp(dev->parent->prom_node->name, "8042")) {
|
||||
if (!strcmp(dev->prom_node->name, "kb_ps2")) {
|
||||
dev->num_irqs = 1;
|
||||
dev->irqs[0] = dev->parent->irqs[0];
|
||||
} else {
|
||||
@ -423,32 +429,32 @@ void __init fill_ebus_child(int node, struct linux_prom_registers *preg,
|
||||
|
||||
static int __init child_regs_nonstandard(struct linux_ebus_device *dev)
|
||||
{
|
||||
if (!strcmp(dev->prom_name, "i2c") ||
|
||||
!strcmp(dev->prom_name, "SUNW,lombus"))
|
||||
if (!strcmp(dev->prom_node->name, "i2c") ||
|
||||
!strcmp(dev->prom_node->name, "SUNW,lombus"))
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
void __init fill_ebus_device(int node, struct linux_ebus_device *dev)
|
||||
void __init fill_ebus_device(struct device_node *dp, struct linux_ebus_device *dev)
|
||||
{
|
||||
struct linux_prom_registers regs[PROMREG_MAX];
|
||||
struct linux_prom_registers *regs;
|
||||
struct linux_ebus_child *child;
|
||||
int irqs[PROMINTR_MAX];
|
||||
int *irqs;
|
||||
int i, n, len;
|
||||
|
||||
dev->prom_node = node;
|
||||
prom_getstring(node, "name", dev->prom_name, sizeof(dev->prom_name));
|
||||
printk(" [%s", dev->prom_name);
|
||||
dev->prom_node = dp;
|
||||
|
||||
len = prom_getproperty(node, "reg", (void *)regs, sizeof(regs));
|
||||
if (len == -1) {
|
||||
printk(" [%s", dp->name);
|
||||
|
||||
regs = of_get_property(dp, "reg", &len);
|
||||
if (!regs) {
|
||||
dev->num_addrs = 0;
|
||||
goto probe_interrupts;
|
||||
}
|
||||
|
||||
if (len % sizeof(struct linux_prom_registers)) {
|
||||
prom_printf("UGH: proplen for %s was %d, need multiple of %d\n",
|
||||
dev->prom_name, len,
|
||||
dev->prom_node->name, len,
|
||||
(int)sizeof(struct linux_prom_registers));
|
||||
prom_halt();
|
||||
}
|
||||
@ -466,7 +472,7 @@ void __init fill_ebus_device(int node, struct linux_ebus_device *dev)
|
||||
dev->resource[i].end =
|
||||
(dev->resource[i].start + (unsigned long)regs[i].reg_size - 1UL);
|
||||
dev->resource[i].flags = IORESOURCE_MEM;
|
||||
dev->resource[i].name = dev->prom_name;
|
||||
dev->resource[i].name = dev->prom_node->name;
|
||||
request_resource(&dev->bus->self->resource[n],
|
||||
&dev->resource[i]);
|
||||
}
|
||||
@ -475,8 +481,8 @@ void __init fill_ebus_device(int node, struct linux_ebus_device *dev)
|
||||
for (i = 0; i < PROMINTR_MAX; i++)
|
||||
dev->irqs[i] = PCI_IRQ_NONE;
|
||||
|
||||
len = prom_getproperty(node, "interrupts", (char *)&irqs, sizeof(irqs));
|
||||
if ((len == -1) || (len == 0)) {
|
||||
irqs = of_get_property(dp, "interrupts", &len);
|
||||
if (!irqs) {
|
||||
dev->num_irqs = 0;
|
||||
} else {
|
||||
dev->num_irqs = len / sizeof(irqs[0]);
|
||||
@ -497,7 +503,8 @@ void __init fill_ebus_device(int node, struct linux_ebus_device *dev)
|
||||
}
|
||||
}
|
||||
|
||||
if ((node = prom_getchild(node))) {
|
||||
dp = dp->child;
|
||||
if (dp) {
|
||||
printk(" ->");
|
||||
dev->children = ebus_alloc(sizeof(struct linux_ebus_child));
|
||||
|
||||
@ -505,18 +512,18 @@ void __init fill_ebus_device(int node, struct linux_ebus_device *dev)
|
||||
child->next = NULL;
|
||||
child->parent = dev;
|
||||
child->bus = dev->bus;
|
||||
fill_ebus_child(node, ®s[0],
|
||||
child, child_regs_nonstandard(dev));
|
||||
fill_ebus_child(dp, regs, child,
|
||||
child_regs_nonstandard(dev));
|
||||
|
||||
while ((node = prom_getsibling(node)) != 0) {
|
||||
while ((dp = dp->sibling) != NULL) {
|
||||
child->next = ebus_alloc(sizeof(struct linux_ebus_child));
|
||||
|
||||
child = child->next;
|
||||
child->next = NULL;
|
||||
child->parent = dev;
|
||||
child->bus = dev->bus;
|
||||
fill_ebus_child(node, ®s[0],
|
||||
child, child_regs_nonstandard(dev));
|
||||
fill_ebus_child(dp, regs, child,
|
||||
child_regs_nonstandard(dev));
|
||||
}
|
||||
}
|
||||
printk("]");
|
||||
@ -543,7 +550,8 @@ void __init ebus_init(void)
|
||||
struct linux_ebus *ebus;
|
||||
struct pci_dev *pdev;
|
||||
struct pcidev_cookie *cookie;
|
||||
int nd, ebusnd, is_rio;
|
||||
struct device_node *dp;
|
||||
int is_rio;
|
||||
int num_ebus = 0;
|
||||
|
||||
pdev = find_next_ebus(NULL, &is_rio);
|
||||
@ -553,20 +561,22 @@ void __init ebus_init(void)
|
||||
}
|
||||
|
||||
cookie = pdev->sysdata;
|
||||
ebusnd = cookie->prom_node->node;
|
||||
dp = cookie->prom_node;
|
||||
|
||||
ebus_chain = ebus = ebus_alloc(sizeof(struct linux_ebus));
|
||||
ebus->next = NULL;
|
||||
ebus->is_rio = is_rio;
|
||||
|
||||
while (ebusnd) {
|
||||
while (dp) {
|
||||
struct device_node *child;
|
||||
|
||||
/* SUNW,pci-qfe uses four empty ebuses on it.
|
||||
I think we should not consider them here,
|
||||
as they have half of the properties this
|
||||
code expects and once we do PCI hot-plug,
|
||||
we'd have to tweak with the ebus_chain
|
||||
in the runtime after initialization. -jj */
|
||||
if (!prom_getchild (ebusnd)) {
|
||||
if (!dp->child) {
|
||||
pdev = find_next_ebus(pdev, &is_rio);
|
||||
if (!pdev) {
|
||||
if (ebus == ebus_chain) {
|
||||
@ -578,22 +588,21 @@ void __init ebus_init(void)
|
||||
}
|
||||
ebus->is_rio = is_rio;
|
||||
cookie = pdev->sysdata;
|
||||
ebusnd = cookie->prom_node->node;
|
||||
dp = cookie->prom_node;
|
||||
continue;
|
||||
}
|
||||
printk("ebus%d:", num_ebus);
|
||||
|
||||
prom_getstring(ebusnd, "name", ebus->prom_name, sizeof(ebus->prom_name));
|
||||
ebus->index = num_ebus;
|
||||
ebus->prom_node = ebusnd;
|
||||
ebus->prom_node = dp;
|
||||
ebus->self = pdev;
|
||||
ebus->parent = pbm = cookie->pbm;
|
||||
|
||||
ebus_ranges_init(ebus);
|
||||
ebus_intmap_init(ebus);
|
||||
|
||||
nd = prom_getchild(ebusnd);
|
||||
if (!nd)
|
||||
child = dp->child;
|
||||
if (!child)
|
||||
goto next_ebus;
|
||||
|
||||
ebus->devices = ebus_alloc(sizeof(struct linux_ebus_device));
|
||||
@ -602,16 +611,16 @@ void __init ebus_init(void)
|
||||
dev->next = NULL;
|
||||
dev->children = NULL;
|
||||
dev->bus = ebus;
|
||||
fill_ebus_device(nd, dev);
|
||||
fill_ebus_device(child, dev);
|
||||
|
||||
while ((nd = prom_getsibling(nd)) != 0) {
|
||||
while ((child = child->sibling) != NULL) {
|
||||
dev->next = ebus_alloc(sizeof(struct linux_ebus_device));
|
||||
|
||||
dev = dev->next;
|
||||
dev->next = NULL;
|
||||
dev->children = NULL;
|
||||
dev->bus = ebus;
|
||||
fill_ebus_device(nd, dev);
|
||||
fill_ebus_device(child, dev);
|
||||
}
|
||||
|
||||
next_ebus:
|
||||
@ -622,7 +631,7 @@ void __init ebus_init(void)
|
||||
break;
|
||||
|
||||
cookie = pdev->sysdata;
|
||||
ebusnd = cookie->prom_node->node;
|
||||
dp = cookie->prom_node;
|
||||
|
||||
ebus->next = ebus_alloc(sizeof(struct linux_ebus));
|
||||
ebus = ebus->next;
|
||||
|
@ -15,23 +15,19 @@ static void __init fatal_err(const char *reason)
|
||||
static void __init report_dev(struct sparc_isa_device *isa_dev, int child)
|
||||
{
|
||||
if (child)
|
||||
printk(" (%s)", isa_dev->prom_name);
|
||||
printk(" (%s)", isa_dev->prom_node->name);
|
||||
else
|
||||
printk(" [%s", isa_dev->prom_name);
|
||||
printk(" [%s", isa_dev->prom_node->name);
|
||||
}
|
||||
|
||||
static void __init isa_dev_get_resource(struct sparc_isa_device *isa_dev,
|
||||
struct linux_prom_registers *pregs,
|
||||
int pregs_size)
|
||||
static struct linux_prom_registers * __init
|
||||
isa_dev_get_resource(struct sparc_isa_device *isa_dev)
|
||||
{
|
||||
struct linux_prom_registers *pregs;
|
||||
unsigned long base, len;
|
||||
int prop_len;
|
||||
|
||||
prop_len = prom_getproperty(isa_dev->prom_node, "reg",
|
||||
(char *) pregs, pregs_size);
|
||||
|
||||
if (prop_len <= 0)
|
||||
return;
|
||||
pregs = of_get_property(isa_dev->prom_node, "reg", &prop_len);
|
||||
|
||||
/* Only the first one is interesting. */
|
||||
len = pregs[0].reg_size;
|
||||
@ -42,10 +38,12 @@ static void __init isa_dev_get_resource(struct sparc_isa_device *isa_dev,
|
||||
isa_dev->resource.start = base;
|
||||
isa_dev->resource.end = (base + len - 1UL);
|
||||
isa_dev->resource.flags = IORESOURCE_IO;
|
||||
isa_dev->resource.name = isa_dev->prom_name;
|
||||
isa_dev->resource.name = isa_dev->prom_node->name;
|
||||
|
||||
request_resource(&isa_dev->bus->parent->io_space,
|
||||
&isa_dev->resource);
|
||||
|
||||
return pregs;
|
||||
}
|
||||
|
||||
/* I can't believe they didn't put a real INO in the isa device
|
||||
@ -98,8 +96,8 @@ static void __init isa_dev_get_irq(struct sparc_isa_device *isa_dev,
|
||||
{
|
||||
int irq_prop;
|
||||
|
||||
irq_prop = prom_getintdefault(isa_dev->prom_node,
|
||||
"interrupts", -1);
|
||||
irq_prop = of_getintprop_default(isa_dev->prom_node,
|
||||
"interrupts", -1);
|
||||
if (irq_prop <= 0) {
|
||||
goto no_irq;
|
||||
} else {
|
||||
@ -141,16 +139,15 @@ static void __init isa_dev_get_irq(struct sparc_isa_device *isa_dev,
|
||||
|
||||
static void __init isa_fill_children(struct sparc_isa_device *parent_isa_dev)
|
||||
{
|
||||
int node = prom_getchild(parent_isa_dev->prom_node);
|
||||
struct device_node *dp = parent_isa_dev->prom_node->child;
|
||||
|
||||
if (node == 0)
|
||||
if (!dp)
|
||||
return;
|
||||
|
||||
printk(" ->");
|
||||
while (node != 0) {
|
||||
struct linux_prom_registers regs[PROMREG_MAX];
|
||||
while (dp) {
|
||||
struct linux_prom_registers *regs;
|
||||
struct sparc_isa_device *isa_dev;
|
||||
int prop_len;
|
||||
|
||||
isa_dev = kmalloc(sizeof(*isa_dev), GFP_KERNEL);
|
||||
if (!isa_dev) {
|
||||
@ -165,40 +162,24 @@ static void __init isa_fill_children(struct sparc_isa_device *parent_isa_dev)
|
||||
parent_isa_dev->child = isa_dev;
|
||||
|
||||
isa_dev->bus = parent_isa_dev->bus;
|
||||
isa_dev->prom_node = node;
|
||||
prop_len = prom_getproperty(node, "name",
|
||||
(char *) isa_dev->prom_name,
|
||||
sizeof(isa_dev->prom_name));
|
||||
if (prop_len <= 0) {
|
||||
fatal_err("cannot get child isa_dev OBP node name");
|
||||
prom_halt();
|
||||
}
|
||||
isa_dev->prom_node = dp;
|
||||
|
||||
prop_len = prom_getproperty(node, "compatible",
|
||||
(char *) isa_dev->compatible,
|
||||
sizeof(isa_dev->compatible));
|
||||
|
||||
/* Not having this is OK. */
|
||||
if (prop_len <= 0)
|
||||
isa_dev->compatible[0] = '\0';
|
||||
|
||||
isa_dev_get_resource(isa_dev, regs, sizeof(regs));
|
||||
regs = isa_dev_get_resource(isa_dev);
|
||||
isa_dev_get_irq(isa_dev, regs);
|
||||
|
||||
report_dev(isa_dev, 1);
|
||||
|
||||
node = prom_getsibling(node);
|
||||
dp = dp->sibling;
|
||||
}
|
||||
}
|
||||
|
||||
static void __init isa_fill_devices(struct sparc_isa_bridge *isa_br)
|
||||
{
|
||||
int node = prom_getchild(isa_br->prom_node);
|
||||
struct device_node *dp = isa_br->prom_node->child;
|
||||
|
||||
while (node != 0) {
|
||||
struct linux_prom_registers regs[PROMREG_MAX];
|
||||
while (dp) {
|
||||
struct linux_prom_registers *regs;
|
||||
struct sparc_isa_device *isa_dev;
|
||||
int prop_len;
|
||||
|
||||
isa_dev = kmalloc(sizeof(*isa_dev), GFP_KERNEL);
|
||||
if (!isa_dev) {
|
||||
@ -222,24 +203,9 @@ static void __init isa_fill_devices(struct sparc_isa_bridge *isa_br)
|
||||
}
|
||||
|
||||
isa_dev->bus = isa_br;
|
||||
isa_dev->prom_node = node;
|
||||
prop_len = prom_getproperty(node, "name",
|
||||
(char *) isa_dev->prom_name,
|
||||
sizeof(isa_dev->prom_name));
|
||||
if (prop_len <= 0) {
|
||||
fatal_err("cannot get isa_dev OBP node name");
|
||||
prom_halt();
|
||||
}
|
||||
isa_dev->prom_node = dp;
|
||||
|
||||
prop_len = prom_getproperty(node, "compatible",
|
||||
(char *) isa_dev->compatible,
|
||||
sizeof(isa_dev->compatible));
|
||||
|
||||
/* Not having this is OK. */
|
||||
if (prop_len <= 0)
|
||||
isa_dev->compatible[0] = '\0';
|
||||
|
||||
isa_dev_get_resource(isa_dev, regs, sizeof(regs));
|
||||
regs = isa_dev_get_resource(isa_dev);
|
||||
isa_dev_get_irq(isa_dev, regs);
|
||||
|
||||
report_dev(isa_dev, 0);
|
||||
@ -248,10 +214,40 @@ static void __init isa_fill_devices(struct sparc_isa_bridge *isa_br)
|
||||
|
||||
printk("]");
|
||||
|
||||
node = prom_getsibling(node);
|
||||
dp = dp->sibling;
|
||||
}
|
||||
}
|
||||
|
||||
static void __init get_bridge_props(struct sparc_isa_bridge *isa_br)
|
||||
{
|
||||
struct device_node *dp = isa_br->prom_node;
|
||||
void *pval;
|
||||
int len;
|
||||
|
||||
pval = of_get_property(dp, "ranges", &len);
|
||||
if (pval) {
|
||||
memcpy(isa_br->isa_ranges, pval, len);
|
||||
isa_br->num_isa_ranges =
|
||||
len / sizeof(struct linux_prom_isa_ranges);
|
||||
} else {
|
||||
isa_br->num_isa_ranges = 0;
|
||||
}
|
||||
|
||||
pval = of_get_property(dp, "interrupt-map", &len);
|
||||
if (pval) {
|
||||
memcpy(isa_br->isa_intmap, pval, len);
|
||||
isa_br->num_isa_intmap =
|
||||
(len / sizeof(struct linux_prom_isa_intmap));
|
||||
} else {
|
||||
isa_br->num_isa_intmap = 0;
|
||||
}
|
||||
|
||||
pval = of_get_property(dp, "interrupt-map-mask", &len);
|
||||
if (pval)
|
||||
memcpy(&isa_br->isa_intmask, pval,
|
||||
sizeof(isa_br->isa_intmask));
|
||||
}
|
||||
|
||||
void __init isa_init(void)
|
||||
{
|
||||
struct pci_dev *pdev;
|
||||
@ -266,7 +262,6 @@ void __init isa_init(void)
|
||||
struct pcidev_cookie *pdev_cookie;
|
||||
struct pci_pbm_info *pbm;
|
||||
struct sparc_isa_bridge *isa_br;
|
||||
int prop_len;
|
||||
|
||||
pdev_cookie = pdev->sysdata;
|
||||
if (!pdev_cookie) {
|
||||
@ -291,34 +286,9 @@ void __init isa_init(void)
|
||||
isa_br->parent = pbm;
|
||||
isa_br->self = pdev;
|
||||
isa_br->index = index++;
|
||||
isa_br->prom_node = pdev_cookie->prom_node->node;
|
||||
strncpy(isa_br->prom_name, pdev_cookie->prom_node->name,
|
||||
sizeof(isa_br->prom_name));
|
||||
isa_br->prom_node = pdev_cookie->prom_node;
|
||||
|
||||
prop_len = prom_getproperty(isa_br->prom_node,
|
||||
"ranges",
|
||||
(char *) isa_br->isa_ranges,
|
||||
sizeof(isa_br->isa_ranges));
|
||||
if (prop_len <= 0)
|
||||
isa_br->num_isa_ranges = 0;
|
||||
else
|
||||
isa_br->num_isa_ranges =
|
||||
(prop_len / sizeof(struct linux_prom_isa_ranges));
|
||||
|
||||
prop_len = prom_getproperty(isa_br->prom_node,
|
||||
"interrupt-map",
|
||||
(char *) isa_br->isa_intmap,
|
||||
sizeof(isa_br->isa_intmap));
|
||||
if (prop_len <= 0)
|
||||
isa_br->num_isa_intmap = 0;
|
||||
else
|
||||
isa_br->num_isa_intmap =
|
||||
(prop_len / sizeof(struct linux_prom_isa_intmap));
|
||||
|
||||
prop_len = prom_getproperty(isa_br->prom_node,
|
||||
"interrupt-map-mask",
|
||||
(char *) &(isa_br->isa_intmask),
|
||||
sizeof(isa_br->isa_intmask));
|
||||
get_bridge_props(isa_br);
|
||||
|
||||
printk("isa%d:", isa_br->index);
|
||||
|
||||
|
@ -105,24 +105,24 @@ static int powerd(void *__unused)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int __init has_button_interrupt(unsigned int irq, int prom_node)
|
||||
static int __init has_button_interrupt(unsigned int irq, struct device_node *dp)
|
||||
{
|
||||
if (irq == PCI_IRQ_NONE)
|
||||
return 0;
|
||||
if (!prom_node_has_property(prom_node, "button"))
|
||||
if (!of_find_property(dp, "button", NULL))
|
||||
return 0;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int __init power_probe_ebus(struct resource **resp, unsigned int *irq_p, int *prom_node_p)
|
||||
static int __init power_probe_ebus(struct resource **resp, unsigned int *irq_p, struct device_node **prom_node_p)
|
||||
{
|
||||
struct linux_ebus *ebus;
|
||||
struct linux_ebus_device *edev;
|
||||
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (!strcmp(edev->prom_name, "power")) {
|
||||
if (!strcmp(edev->prom_node->name, "power")) {
|
||||
*resp = &edev->resource[0];
|
||||
*irq_p = edev->irqs[0];
|
||||
*prom_node_p = edev->prom_node;
|
||||
@ -133,14 +133,14 @@ static int __init power_probe_ebus(struct resource **resp, unsigned int *irq_p,
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
static int __init power_probe_isa(struct resource **resp, unsigned int *irq_p, int *prom_node_p)
|
||||
static int __init power_probe_isa(struct resource **resp, unsigned int *irq_p, struct device_node **prom_node_p)
|
||||
{
|
||||
struct sparc_isa_bridge *isa_bus;
|
||||
struct sparc_isa_device *isa_dev;
|
||||
|
||||
for_each_isa(isa_bus) {
|
||||
for_each_isadev(isa_dev, isa_bus) {
|
||||
if (!strcmp(isa_dev->prom_name, "power")) {
|
||||
if (!strcmp(isa_dev->prom_node->name, "power")) {
|
||||
*resp = &isa_dev->resource;
|
||||
*irq_p = isa_dev->irq;
|
||||
*prom_node_p = isa_dev->prom_node;
|
||||
@ -155,17 +155,17 @@ void __init power_init(void)
|
||||
{
|
||||
struct resource *res = NULL;
|
||||
unsigned int irq;
|
||||
int prom_node;
|
||||
struct device_node *dp;
|
||||
static int invoked;
|
||||
|
||||
if (invoked)
|
||||
return;
|
||||
invoked = 1;
|
||||
|
||||
if (!power_probe_ebus(&res, &irq, &prom_node))
|
||||
if (!power_probe_ebus(&res, &irq, &dp))
|
||||
goto found;
|
||||
|
||||
if (!power_probe_isa(&res, &irq, &prom_node))
|
||||
if (!power_probe_isa(&res, &irq, &dp))
|
||||
goto found;
|
||||
|
||||
return;
|
||||
@ -174,7 +174,7 @@ void __init power_init(void)
|
||||
power_reg = ioremap(res->start, 0x4);
|
||||
printk("power: Control reg at %p ... ", power_reg);
|
||||
poweroff_method = machine_halt; /* able to use the standard halt */
|
||||
if (has_button_interrupt(irq, prom_node)) {
|
||||
if (has_button_interrupt(irq, dp)) {
|
||||
if (kernel_thread(powerd, NULL, CLONE_FS) < 0) {
|
||||
printk("Failed to start power daemon.\n");
|
||||
return;
|
||||
|
@ -63,6 +63,7 @@ struct device_node *of_find_node_by_path(const char *path)
|
||||
|
||||
return np;
|
||||
}
|
||||
EXPORT_SYMBOL(of_find_node_by_path);
|
||||
|
||||
struct device_node *of_find_node_by_phandle(phandle handle)
|
||||
{
|
||||
|
@ -756,24 +756,200 @@ static int hypervisor_set_time(u32 secs)
|
||||
return -EOPNOTSUPP;
|
||||
}
|
||||
|
||||
void __init clock_probe(void)
|
||||
static int __init clock_model_matches(char *model)
|
||||
{
|
||||
if (strcmp(model, "mk48t02") &&
|
||||
strcmp(model, "mk48t08") &&
|
||||
strcmp(model, "mk48t59") &&
|
||||
strcmp(model, "m5819") &&
|
||||
strcmp(model, "m5819p") &&
|
||||
strcmp(model, "m5823") &&
|
||||
strcmp(model, "ds1287"))
|
||||
return 0;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void __init __clock_assign_common(void __iomem *addr, char *model)
|
||||
{
|
||||
if (model[5] == '0' && model[6] == '2') {
|
||||
mstk48t02_regs = addr;
|
||||
} else if(model[5] == '0' && model[6] == '8') {
|
||||
mstk48t08_regs = addr;
|
||||
mstk48t02_regs = mstk48t08_regs + MOSTEK_48T08_48T02;
|
||||
} else {
|
||||
mstk48t59_regs = addr;
|
||||
mstk48t02_regs = mstk48t59_regs + MOSTEK_48T59_48T02;
|
||||
}
|
||||
}
|
||||
|
||||
static void __init clock_assign_clk_reg(struct linux_prom_registers *clk_reg,
|
||||
char *model)
|
||||
{
|
||||
unsigned long addr;
|
||||
|
||||
addr = ((unsigned long) clk_reg[0].phys_addr |
|
||||
(((unsigned long) clk_reg[0].which_io) << 32UL));
|
||||
|
||||
__clock_assign_common((void __iomem *) addr, model);
|
||||
}
|
||||
|
||||
static int __init clock_probe_central(void)
|
||||
{
|
||||
struct linux_prom_registers clk_reg[2];
|
||||
char model[128];
|
||||
int node, busnd = -1, err;
|
||||
unsigned long flags;
|
||||
struct linux_central *cbus;
|
||||
char model[64];
|
||||
int node;
|
||||
|
||||
if (!central_bus)
|
||||
return 0;
|
||||
|
||||
/* Get Central FHC's prom node. */
|
||||
node = central_bus->child->prom_node;
|
||||
|
||||
/* Then get the first child device below it. */
|
||||
node = prom_getchild(node);
|
||||
|
||||
while (node) {
|
||||
prom_getstring(node, "model", model, sizeof(model));
|
||||
if (!clock_model_matches(model))
|
||||
goto next_sibling;
|
||||
|
||||
prom_getproperty(node, "reg", (char *)clk_reg,
|
||||
sizeof(clk_reg));
|
||||
|
||||
apply_fhc_ranges(central_bus->child, clk_reg, 1);
|
||||
apply_central_ranges(central_bus, clk_reg, 1);
|
||||
|
||||
clock_assign_clk_reg(clk_reg, model);
|
||||
return 1;
|
||||
|
||||
next_sibling:
|
||||
node = prom_getsibling(node);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_PCI
|
||||
struct linux_ebus *ebus = NULL;
|
||||
struct sparc_isa_bridge *isa_br = NULL;
|
||||
static void __init clock_isa_ebus_assign_regs(struct resource *res, char *model)
|
||||
{
|
||||
if (!strcmp(model, "ds1287") ||
|
||||
!strcmp(model, "m5819") ||
|
||||
!strcmp(model, "m5819p") ||
|
||||
!strcmp(model, "m5823")) {
|
||||
ds1287_regs = res->start;
|
||||
} else {
|
||||
mstk48t59_regs = (void __iomem *) res->start;
|
||||
mstk48t02_regs = mstk48t59_regs + MOSTEK_48T59_48T02;
|
||||
}
|
||||
}
|
||||
|
||||
static int __init clock_probe_one_ebus_dev(struct linux_ebus_device *edev)
|
||||
{
|
||||
struct device_node *dp = edev->prom_node;
|
||||
char *model;
|
||||
|
||||
model = of_get_property(dp, "model", NULL);
|
||||
if (!clock_model_matches(model))
|
||||
return 0;
|
||||
|
||||
clock_isa_ebus_assign_regs(&edev->resource[0], model);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int __init clock_probe_ebus(void)
|
||||
{
|
||||
struct linux_ebus *ebus;
|
||||
|
||||
for_each_ebus(ebus) {
|
||||
struct linux_ebus_device *edev;
|
||||
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (clock_probe_one_ebus_dev(edev))
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int __init clock_probe_one_isa_dev(struct sparc_isa_device *idev)
|
||||
{
|
||||
struct device_node *dp = idev->prom_node;
|
||||
char *model;
|
||||
|
||||
model = of_get_property(dp, "model", NULL);
|
||||
if (!clock_model_matches(model))
|
||||
return 0;
|
||||
|
||||
clock_isa_ebus_assign_regs(&idev->resource, model);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int __init clock_probe_isa(void)
|
||||
{
|
||||
struct sparc_isa_bridge *isa_br;
|
||||
|
||||
for_each_isa(isa_br) {
|
||||
struct sparc_isa_device *isa_dev;
|
||||
|
||||
for_each_isadev(isa_dev, isa_br) {
|
||||
if (clock_probe_one_isa_dev(isa_dev))
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
#endif /* CONFIG_PCI */
|
||||
|
||||
#ifdef CONFIG_SBUS
|
||||
static int __init clock_probe_one_sbus_dev(struct sbus_bus *sbus, struct sbus_dev *sdev)
|
||||
{
|
||||
struct resource *res;
|
||||
char model[64];
|
||||
void __iomem *addr;
|
||||
|
||||
prom_getstring(sdev->prom_node, "model", model, sizeof(model));
|
||||
if (!clock_model_matches(model))
|
||||
return 0;
|
||||
|
||||
res = &sdev->resource[0];
|
||||
addr = sbus_ioremap(res, 0, 0x800UL, "eeprom");
|
||||
|
||||
__clock_assign_common(addr, model);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int __init clock_probe_sbus(void)
|
||||
{
|
||||
struct sbus_bus *sbus;
|
||||
|
||||
for_each_sbus(sbus) {
|
||||
struct sbus_dev *sdev;
|
||||
|
||||
for_each_sbusdev(sdev, sbus) {
|
||||
if (clock_probe_one_sbus_dev(sbus, sdev))
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
void __init clock_probe(void)
|
||||
{
|
||||
static int invoked;
|
||||
unsigned long flags;
|
||||
|
||||
if (invoked)
|
||||
return;
|
||||
invoked = 1;
|
||||
|
||||
|
||||
if (this_is_starfire) {
|
||||
xtime.tv_sec = starfire_get_time();
|
||||
xtime.tv_nsec = (INITIAL_JIFFIES % HZ) * (NSEC_PER_SEC / HZ);
|
||||
@ -789,182 +965,26 @@ void __init clock_probe(void)
|
||||
return;
|
||||
}
|
||||
|
||||
local_irq_save(flags);
|
||||
|
||||
cbus = central_bus;
|
||||
if (cbus != NULL)
|
||||
busnd = central_bus->child->prom_node;
|
||||
|
||||
/* Check FHC Central then EBUSs then ISA bridges then SBUSs.
|
||||
* That way we handle the presence of multiple properly.
|
||||
*
|
||||
* As a special case, machines with Central must provide the
|
||||
* timer chip there.
|
||||
*/
|
||||
if (!clock_probe_central() &&
|
||||
#ifdef CONFIG_PCI
|
||||
if (ebus_chain != NULL) {
|
||||
ebus = ebus_chain;
|
||||
if (busnd == -1)
|
||||
busnd = ebus->prom_node;
|
||||
}
|
||||
if (isa_chain != NULL) {
|
||||
isa_br = isa_chain;
|
||||
if (busnd == -1)
|
||||
busnd = isa_br->prom_node;
|
||||
}
|
||||
!clock_probe_ebus() &&
|
||||
!clock_probe_isa() &&
|
||||
#endif
|
||||
if (sbus_root != NULL && busnd == -1)
|
||||
busnd = sbus_root->prom_node;
|
||||
|
||||
if (busnd == -1) {
|
||||
prom_printf("clock_probe: problem, cannot find bus to search.\n");
|
||||
prom_halt();
|
||||
#ifdef CONFIG_SBUS
|
||||
!clock_probe_sbus()
|
||||
#endif
|
||||
) {
|
||||
printk(KERN_WARNING "No clock chip found.\n");
|
||||
return;
|
||||
}
|
||||
|
||||
node = prom_getchild(busnd);
|
||||
|
||||
while (1) {
|
||||
if (!node)
|
||||
model[0] = 0;
|
||||
else
|
||||
prom_getstring(node, "model", model, sizeof(model));
|
||||
if (strcmp(model, "mk48t02") &&
|
||||
strcmp(model, "mk48t08") &&
|
||||
strcmp(model, "mk48t59") &&
|
||||
strcmp(model, "m5819") &&
|
||||
strcmp(model, "m5819p") &&
|
||||
strcmp(model, "m5823") &&
|
||||
strcmp(model, "ds1287")) {
|
||||
if (cbus != NULL) {
|
||||
prom_printf("clock_probe: Central bus lacks timer chip.\n");
|
||||
prom_halt();
|
||||
}
|
||||
|
||||
if (node != 0)
|
||||
node = prom_getsibling(node);
|
||||
#ifdef CONFIG_PCI
|
||||
while ((node == 0) && ebus != NULL) {
|
||||
ebus = ebus->next;
|
||||
if (ebus != NULL) {
|
||||
busnd = ebus->prom_node;
|
||||
node = prom_getchild(busnd);
|
||||
}
|
||||
}
|
||||
while ((node == 0) && isa_br != NULL) {
|
||||
isa_br = isa_br->next;
|
||||
if (isa_br != NULL) {
|
||||
busnd = isa_br->prom_node;
|
||||
node = prom_getchild(busnd);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
if (node == 0) {
|
||||
prom_printf("clock_probe: Cannot find timer chip\n");
|
||||
prom_halt();
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
err = prom_getproperty(node, "reg", (char *)clk_reg,
|
||||
sizeof(clk_reg));
|
||||
if(err == -1) {
|
||||
prom_printf("clock_probe: Cannot get Mostek reg property\n");
|
||||
prom_halt();
|
||||
}
|
||||
|
||||
if (cbus != NULL) {
|
||||
apply_fhc_ranges(central_bus->child, clk_reg, 1);
|
||||
apply_central_ranges(central_bus, clk_reg, 1);
|
||||
}
|
||||
#ifdef CONFIG_PCI
|
||||
else if (ebus != NULL) {
|
||||
struct linux_ebus_device *edev;
|
||||
|
||||
for_each_ebusdev(edev, ebus)
|
||||
if (edev->prom_node == node)
|
||||
break;
|
||||
if (edev == NULL) {
|
||||
if (isa_chain != NULL)
|
||||
goto try_isa_clock;
|
||||
prom_printf("%s: Mostek not probed by EBUS\n",
|
||||
__FUNCTION__);
|
||||
prom_halt();
|
||||
}
|
||||
|
||||
if (!strcmp(model, "ds1287") ||
|
||||
!strcmp(model, "m5819") ||
|
||||
!strcmp(model, "m5819p") ||
|
||||
!strcmp(model, "m5823")) {
|
||||
ds1287_regs = edev->resource[0].start;
|
||||
} else {
|
||||
mstk48t59_regs = (void __iomem *)
|
||||
edev->resource[0].start;
|
||||
mstk48t02_regs = mstk48t59_regs + MOSTEK_48T59_48T02;
|
||||
}
|
||||
break;
|
||||
}
|
||||
else if (isa_br != NULL) {
|
||||
struct sparc_isa_device *isadev;
|
||||
|
||||
try_isa_clock:
|
||||
for_each_isadev(isadev, isa_br)
|
||||
if (isadev->prom_node == node)
|
||||
break;
|
||||
if (isadev == NULL) {
|
||||
prom_printf("%s: Mostek not probed by ISA\n");
|
||||
prom_halt();
|
||||
}
|
||||
if (!strcmp(model, "ds1287") ||
|
||||
!strcmp(model, "m5819") ||
|
||||
!strcmp(model, "m5819p") ||
|
||||
!strcmp(model, "m5823")) {
|
||||
ds1287_regs = isadev->resource.start;
|
||||
} else {
|
||||
mstk48t59_regs = (void __iomem *)
|
||||
isadev->resource.start;
|
||||
mstk48t02_regs = mstk48t59_regs + MOSTEK_48T59_48T02;
|
||||
}
|
||||
break;
|
||||
}
|
||||
#endif
|
||||
else {
|
||||
if (sbus_root->num_sbus_ranges) {
|
||||
int nranges = sbus_root->num_sbus_ranges;
|
||||
int rngc;
|
||||
|
||||
for (rngc = 0; rngc < nranges; rngc++)
|
||||
if (clk_reg[0].which_io ==
|
||||
sbus_root->sbus_ranges[rngc].ot_child_space)
|
||||
break;
|
||||
if (rngc == nranges) {
|
||||
prom_printf("clock_probe: Cannot find ranges for "
|
||||
"clock regs.\n");
|
||||
prom_halt();
|
||||
}
|
||||
clk_reg[0].which_io =
|
||||
sbus_root->sbus_ranges[rngc].ot_parent_space;
|
||||
clk_reg[0].phys_addr +=
|
||||
sbus_root->sbus_ranges[rngc].ot_parent_base;
|
||||
}
|
||||
}
|
||||
|
||||
if(model[5] == '0' && model[6] == '2') {
|
||||
mstk48t02_regs = (void __iomem *)
|
||||
(((u64)clk_reg[0].phys_addr) |
|
||||
(((u64)clk_reg[0].which_io)<<32UL));
|
||||
} else if(model[5] == '0' && model[6] == '8') {
|
||||
mstk48t08_regs = (void __iomem *)
|
||||
(((u64)clk_reg[0].phys_addr) |
|
||||
(((u64)clk_reg[0].which_io)<<32UL));
|
||||
mstk48t02_regs = mstk48t08_regs + MOSTEK_48T08_48T02;
|
||||
} else {
|
||||
mstk48t59_regs = (void __iomem *)
|
||||
(((u64)clk_reg[0].phys_addr) |
|
||||
(((u64)clk_reg[0].which_io)<<32UL));
|
||||
mstk48t02_regs = mstk48t59_regs + MOSTEK_48T59_48T02;
|
||||
}
|
||||
break;
|
||||
}
|
||||
local_irq_save(flags);
|
||||
|
||||
if (mstk48t02_regs != NULL) {
|
||||
/* Report a low battery voltage condition. */
|
||||
|
@ -928,7 +928,7 @@ static int __init rtc_init(void)
|
||||
#ifdef __sparc__
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if(strcmp(edev->prom_name, "rtc") == 0) {
|
||||
if(strcmp(edev->prom_node->name, "rtc") == 0) {
|
||||
rtc_port = edev->resource[0].start;
|
||||
rtc_irq = edev->irqs[0];
|
||||
goto found;
|
||||
@ -938,7 +938,7 @@ static int __init rtc_init(void)
|
||||
#ifdef __sparc_v9__
|
||||
for_each_isa(isa_br) {
|
||||
for_each_isadev(isa_dev, isa_br) {
|
||||
if (strcmp(isa_dev->prom_name, "rtc") == 0) {
|
||||
if (strcmp(isa_dev->prom_node->name, "rtc") == 0) {
|
||||
rtc_port = isa_dev->resource.start;
|
||||
rtc_irq = isa_dev->irq;
|
||||
goto found;
|
||||
|
@ -199,7 +199,7 @@ static int __init sparcspkr_init(void)
|
||||
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (!strcmp(edev->prom_name, "beep")) {
|
||||
if (!strcmp(edev->prom_node->name, "beep")) {
|
||||
beep_name = "Sparc EBUS Speaker";
|
||||
beep_event = ebus_spkr_event;
|
||||
beep_iobase = edev->resource[0].start;
|
||||
@ -213,7 +213,7 @@ static int __init sparcspkr_init(void)
|
||||
/* A hack, the beep device's base lives in
|
||||
* the DMA isa node.
|
||||
*/
|
||||
if (!strcmp(isa_dev->prom_name, "dma")) {
|
||||
if (!strcmp(isa_dev->prom_node->name, "dma")) {
|
||||
beep_name = "Sparc ISA Speaker";
|
||||
beep_event = isa_spkr_event,
|
||||
beep_iobase = isa_dev->resource.start;
|
||||
|
@ -74,7 +74,7 @@ static int __init i8042_platform_init(void)
|
||||
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (!strcmp(edev->prom_name, "8042"))
|
||||
if (!strcmp(edev->prom_node->name, "8042"))
|
||||
goto edev_found;
|
||||
}
|
||||
}
|
||||
@ -82,14 +82,14 @@ static int __init i8042_platform_init(void)
|
||||
|
||||
edev_found:
|
||||
for_each_edevchild(edev, child) {
|
||||
if (!strcmp(child->prom_name, OBP_PS2KBD_NAME1) ||
|
||||
!strcmp(child->prom_name, OBP_PS2KBD_NAME2)) {
|
||||
if (!strcmp(child->prom_node->name, OBP_PS2KBD_NAME1) ||
|
||||
!strcmp(child->prom_node->name, OBP_PS2KBD_NAME2)) {
|
||||
i8042_kbd_irq = child->irqs[0];
|
||||
kbd_iobase =
|
||||
ioremap(child->resource[0].start, 8);
|
||||
}
|
||||
if (!strcmp(child->prom_name, OBP_PS2MS_NAME1) ||
|
||||
!strcmp(child->prom_name, OBP_PS2MS_NAME2))
|
||||
if (!strcmp(child->prom_node->name, OBP_PS2MS_NAME1) ||
|
||||
!strcmp(child->prom_node->name, OBP_PS2MS_NAME2))
|
||||
i8042_aux_irq = child->irqs[0];
|
||||
}
|
||||
if (i8042_kbd_irq == -1 ||
|
||||
|
@ -575,9 +575,9 @@ int bbc_envctrl_init(void)
|
||||
int devidx = 0;
|
||||
|
||||
while ((echild = bbc_i2c_getdev(devidx++)) != NULL) {
|
||||
if (!strcmp(echild->prom_name, "temperature"))
|
||||
if (!strcmp(echild->prom_node->name, "temperature"))
|
||||
attach_one_temp(echild, temp_index++);
|
||||
if (!strcmp(echild->prom_name, "fan-control"))
|
||||
if (!strcmp(echild->prom_node->name, "fan-control"))
|
||||
attach_one_fan(echild, fan_index++);
|
||||
}
|
||||
if (temp_index != 0 && fan_index != 0) {
|
||||
|
@ -423,7 +423,7 @@ static int __init bbc_present(void)
|
||||
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (!strcmp(edev->prom_name, "bbc"))
|
||||
if (!strcmp(edev->prom_node->name, "bbc"))
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
@ -446,7 +446,7 @@ static int __init bbc_i2c_init(void)
|
||||
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (!strcmp(edev->prom_name, "i2c")) {
|
||||
if (!strcmp(edev->prom_node->name, "i2c")) {
|
||||
if (!attach_one_i2c(edev, index))
|
||||
index++;
|
||||
}
|
||||
|
@ -184,7 +184,7 @@ static int __init d7s_init(void)
|
||||
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (!strcmp(edev->prom_name, D7S_OBPNAME))
|
||||
if (!strcmp(edev->prom_node->name, D7S_OBPNAME))
|
||||
goto ebus_done;
|
||||
}
|
||||
}
|
||||
|
@ -768,16 +768,14 @@ static void envctrl_set_mon(struct i2c_child_t *pchild,
|
||||
* decoding tables, monitor type, optional properties.
|
||||
* Return: None.
|
||||
*/
|
||||
static void envctrl_init_adc(struct i2c_child_t *pchild, int node)
|
||||
static void envctrl_init_adc(struct i2c_child_t *pchild, struct device_node *dp)
|
||||
{
|
||||
char chnls_desc[CHANNEL_DESC_SZ];
|
||||
int i = 0, len;
|
||||
char *pos = chnls_desc;
|
||||
char *pos;
|
||||
unsigned int *pval;
|
||||
|
||||
/* Firmware describe channels into a stream separated by a '\0'. */
|
||||
len = prom_getproperty(node, "channels-description", chnls_desc,
|
||||
CHANNEL_DESC_SZ);
|
||||
chnls_desc[CHANNEL_DESC_SZ - 1] = '\0';
|
||||
pos = of_get_property(dp, "channels-description", &len);
|
||||
|
||||
while (len > 0) {
|
||||
int l = strlen(pos) + 1;
|
||||
@ -787,10 +785,13 @@ static void envctrl_init_adc(struct i2c_child_t *pchild, int node)
|
||||
}
|
||||
|
||||
/* Get optional properties. */
|
||||
len = prom_getproperty(node, "warning-temp", (char *)&warning_temperature,
|
||||
sizeof(warning_temperature));
|
||||
len = prom_getproperty(node, "shutdown-temp", (char *)&shutdown_temperature,
|
||||
sizeof(shutdown_temperature));
|
||||
pval = of_get_property(dp, "warning-temp", NULL);
|
||||
if (pval)
|
||||
warning_temperature = *pval;
|
||||
|
||||
pval = of_get_property(dp, "shutdown-temp", NULL);
|
||||
if (pval)
|
||||
shutdown_temperature = *pval;
|
||||
}
|
||||
|
||||
/* Function Description: Initialize child device monitoring fan status.
|
||||
@ -864,21 +865,18 @@ static void envctrl_init_voltage_status(struct i2c_child_t *pchild)
|
||||
static void envctrl_init_i2c_child(struct linux_ebus_child *edev_child,
|
||||
struct i2c_child_t *pchild)
|
||||
{
|
||||
int node, len, i, tbls_size = 0;
|
||||
|
||||
node = edev_child->prom_node;
|
||||
int len, i, tbls_size = 0;
|
||||
struct device_node *dp = edev_child->prom_node;
|
||||
void *pval;
|
||||
|
||||
/* Get device address. */
|
||||
len = prom_getproperty(node, "reg",
|
||||
(char *) &(pchild->addr),
|
||||
sizeof(pchild->addr));
|
||||
pval = of_get_property(dp, "reg", &len);
|
||||
memcpy(&pchild->addr, pval, len);
|
||||
|
||||
/* Get tables property. Read firmware temperature tables. */
|
||||
len = prom_getproperty(node, "translation",
|
||||
(char *) pchild->tblprop_array,
|
||||
(PCF8584_MAX_CHANNELS *
|
||||
sizeof(struct pcf8584_tblprop)));
|
||||
if (len > 0) {
|
||||
pval = of_get_property(dp, "translation", &len);
|
||||
if (pval && len > 0) {
|
||||
memcpy(pchild->tblprop_array, pval, len);
|
||||
pchild->total_tbls = len / sizeof(struct pcf8584_tblprop);
|
||||
for (i = 0; i < pchild->total_tbls; i++) {
|
||||
if ((pchild->tblprop_array[i].size + pchild->tblprop_array[i].offset) > tbls_size) {
|
||||
@ -891,12 +889,12 @@ static void envctrl_init_i2c_child(struct linux_ebus_child *edev_child,
|
||||
printk("envctrl: Failed to allocate table.\n");
|
||||
return;
|
||||
}
|
||||
len = prom_getproperty(node, "tables",
|
||||
(char *) pchild->tables, tbls_size);
|
||||
if (len <= 0) {
|
||||
pval = of_get_property(dp, "tables", &len);
|
||||
if (!pval || len <= 0) {
|
||||
printk("envctrl: Failed to get table.\n");
|
||||
return;
|
||||
}
|
||||
memcpy(pchild->tables, pval, len);
|
||||
}
|
||||
|
||||
/* SPARCengine ASM Reference Manual (ref. SMI doc 805-7581-04)
|
||||
@ -907,12 +905,11 @@ static void envctrl_init_i2c_child(struct linux_ebus_child *edev_child,
|
||||
* 'NULL' monitor type.
|
||||
*/
|
||||
if (ENVCTRL_CPCI_IGNORED_NODE == pchild->addr) {
|
||||
struct device_node *root_node;
|
||||
int len;
|
||||
char prop[56];
|
||||
|
||||
len = prom_getproperty(prom_root_node, "name", prop, sizeof(prop));
|
||||
if (0 < len && (0 == strncmp(prop, "SUNW,UltraSPARC-IIi-cEngine", len)))
|
||||
{
|
||||
root_node = of_find_node_by_path("/");
|
||||
if (!strcmp(root_node->name, "SUNW,UltraSPARC-IIi-cEngine")) {
|
||||
for (len = 0; len < PCF8584_MAX_CHANNELS; ++len) {
|
||||
pchild->mon_type[len] = ENVCTRL_NOMON;
|
||||
}
|
||||
@ -921,16 +918,14 @@ static void envctrl_init_i2c_child(struct linux_ebus_child *edev_child,
|
||||
}
|
||||
|
||||
/* Get the monitor channels. */
|
||||
len = prom_getproperty(node, "channels-in-use",
|
||||
(char *) pchild->chnl_array,
|
||||
(PCF8584_MAX_CHANNELS *
|
||||
sizeof(struct pcf8584_channel)));
|
||||
pval = of_get_property(dp, "channels-in-use", &len);
|
||||
memcpy(pchild->chnl_array, pval, len);
|
||||
pchild->total_chnls = len / sizeof(struct pcf8584_channel);
|
||||
|
||||
for (i = 0; i < pchild->total_chnls; i++) {
|
||||
switch (pchild->chnl_array[i].type) {
|
||||
case PCF8584_TEMP_TYPE:
|
||||
envctrl_init_adc(pchild, node);
|
||||
envctrl_init_adc(pchild, dp);
|
||||
break;
|
||||
|
||||
case PCF8584_GLOBALADDR_TYPE:
|
||||
@ -945,7 +940,7 @@ static void envctrl_init_i2c_child(struct linux_ebus_child *edev_child,
|
||||
|
||||
case PCF8584_VOLTAGE_TYPE:
|
||||
if (pchild->i2ctype == I2C_ADC) {
|
||||
envctrl_init_adc(pchild,node);
|
||||
envctrl_init_adc(pchild,dp);
|
||||
} else {
|
||||
envctrl_init_voltage_status(pchild);
|
||||
}
|
||||
@ -1046,7 +1041,7 @@ static int __init envctrl_init(void)
|
||||
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (!strcmp(edev->prom_name, "bbc")) {
|
||||
if (!strcmp(edev->prom_node->name, "bbc")) {
|
||||
/* If we find a boot-bus controller node,
|
||||
* then this envctrl driver is not for us.
|
||||
*/
|
||||
@ -1060,14 +1055,14 @@ static int __init envctrl_init(void)
|
||||
*/
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (!strcmp(edev->prom_name, "i2c")) {
|
||||
if (!strcmp(edev->prom_node->name, "i2c")) {
|
||||
i2c = ioremap(edev->resource[0].start, 0x2);
|
||||
for_each_edevchild(edev, edev_child) {
|
||||
if (!strcmp("gpio", edev_child->prom_name)) {
|
||||
if (!strcmp("gpio", edev_child->prom_node->name)) {
|
||||
i2c_childlist[i].i2ctype = I2C_GPIO;
|
||||
envctrl_init_i2c_child(edev_child, &(i2c_childlist[i++]));
|
||||
}
|
||||
if (!strcmp("adc", edev_child->prom_name)) {
|
||||
if (!strcmp("adc", edev_child->prom_node->name)) {
|
||||
i2c_childlist[i].i2ctype = I2C_ADC;
|
||||
envctrl_init_i2c_child(edev_child, &(i2c_childlist[i++]));
|
||||
}
|
||||
|
@ -192,9 +192,11 @@ static int __init flash_init(void)
|
||||
}
|
||||
if (!sdev) {
|
||||
#ifdef CONFIG_PCI
|
||||
struct linux_prom_registers *ebus_regs;
|
||||
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (!strcmp(edev->prom_name, "flashprom"))
|
||||
if (!strcmp(edev->prom_node->name, "flashprom"))
|
||||
goto ebus_done;
|
||||
}
|
||||
}
|
||||
@ -202,23 +204,23 @@ static int __init flash_init(void)
|
||||
if (!edev)
|
||||
return -ENODEV;
|
||||
|
||||
len = prom_getproperty(edev->prom_node, "reg", (void *)regs, sizeof(regs));
|
||||
if ((len % sizeof(regs[0])) != 0) {
|
||||
ebus_regs = of_get_property(edev->prom_node, "reg", &len);
|
||||
if (!ebus_regs || (len % sizeof(regs[0])) != 0) {
|
||||
printk("flash: Strange reg property size %d\n", len);
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
nregs = len / sizeof(regs[0]);
|
||||
nregs = len / sizeof(ebus_regs[0]);
|
||||
|
||||
flash.read_base = edev->resource[0].start;
|
||||
flash.read_size = regs[0].reg_size;
|
||||
flash.read_size = ebus_regs[0].reg_size;
|
||||
|
||||
if (nregs == 1) {
|
||||
flash.write_base = edev->resource[0].start;
|
||||
flash.write_size = regs[0].reg_size;
|
||||
flash.write_size = ebus_regs[0].reg_size;
|
||||
} else if (nregs == 2) {
|
||||
flash.write_base = edev->resource[1].start;
|
||||
flash.write_size = regs[1].reg_size;
|
||||
flash.write_size = ebus_regs[1].reg_size;
|
||||
} else {
|
||||
printk("flash: Strange number of regs %d\n", nregs);
|
||||
return -ENODEV;
|
||||
|
@ -984,19 +984,19 @@ static void __init for_each_sab_edev(void (*callback)(struct linux_ebus_device *
|
||||
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (!strcmp(edev->prom_name, "se")) {
|
||||
if (!strcmp(edev->prom_node->name, "se")) {
|
||||
callback(edev, arg);
|
||||
continue;
|
||||
} else if (!strcmp(edev->prom_name, "serial")) {
|
||||
char compat[32];
|
||||
} else if (!strcmp(edev->prom_node->name, "serial")) {
|
||||
char *compat;
|
||||
int clen;
|
||||
|
||||
/* On RIO this can be an SE, check it. We could
|
||||
* just check ebus->is_rio, but this is more portable.
|
||||
*/
|
||||
clen = prom_getproperty(edev->prom_node, "compatible",
|
||||
compat, sizeof(compat));
|
||||
if (clen > 0) {
|
||||
compat = of_get_property(edev->prom_node,
|
||||
"compatible", &clen);
|
||||
if (compat && clen > 0) {
|
||||
if (strncmp(compat, "sab82532", 8) == 0) {
|
||||
callback(edev, arg);
|
||||
continue;
|
||||
|
@ -1053,7 +1053,7 @@ static void sunsu_autoconfig(struct uart_sunsu_port *up)
|
||||
*/
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(dev, ebus) {
|
||||
if (dev->prom_node == up->port_node) {
|
||||
if (dev->prom_node->node == up->port_node) {
|
||||
/*
|
||||
* The EBus is broken on sparc; it delivers
|
||||
* virtual addresses in resources. Oh well...
|
||||
@ -1073,7 +1073,7 @@ static void sunsu_autoconfig(struct uart_sunsu_port *up)
|
||||
#ifdef CONFIG_SPARC64
|
||||
for_each_isa(isa_br) {
|
||||
for_each_isadev(isa_dev, isa_br) {
|
||||
if (isa_dev->prom_node == up->port_node) {
|
||||
if (isa_dev->prom_node->node == up->port_node) {
|
||||
/* Same on sparc64. Cool architecure... */
|
||||
up->port.membase = (char *) isa_dev->resource.start;
|
||||
up->port.mapbase = isa_dev->resource.start;
|
||||
|
@ -10,13 +10,13 @@
|
||||
|
||||
#include <asm/pbm.h>
|
||||
#include <asm/oplib.h>
|
||||
#include <asm/prom.h>
|
||||
|
||||
struct linux_ebus_child {
|
||||
struct linux_ebus_child *next;
|
||||
struct linux_ebus_device *parent;
|
||||
struct linux_ebus *bus;
|
||||
int prom_node;
|
||||
char prom_name[64];
|
||||
struct device_node *prom_node;
|
||||
struct resource resource[PROMREG_MAX];
|
||||
int num_addrs;
|
||||
unsigned int irqs[PROMINTR_MAX];
|
||||
@ -27,8 +27,7 @@ struct linux_ebus_device {
|
||||
struct linux_ebus_device *next;
|
||||
struct linux_ebus_child *children;
|
||||
struct linux_ebus *bus;
|
||||
int prom_node;
|
||||
char prom_name[64];
|
||||
struct device_node *prom_node;
|
||||
struct resource resource[PROMREG_MAX];
|
||||
int num_addrs;
|
||||
unsigned int irqs[PROMINTR_MAX];
|
||||
@ -42,8 +41,7 @@ struct linux_ebus {
|
||||
struct pci_dev *self;
|
||||
int index;
|
||||
int is_rio;
|
||||
int prom_node;
|
||||
char prom_name[64];
|
||||
struct device_node *prom_node;
|
||||
struct linux_prom_ebus_ranges ebus_ranges[PROMREG_MAX];
|
||||
int num_ebus_ranges;
|
||||
struct linux_prom_ebus_intmap ebus_intmap[PROMREG_MAX];
|
||||
|
@ -498,15 +498,14 @@ static int sun_pci_fd_test_drive(unsigned long port, int drive)
|
||||
#ifdef CONFIG_PCI
|
||||
static int __init ebus_fdthree_p(struct linux_ebus_device *edev)
|
||||
{
|
||||
if (!strcmp(edev->prom_name, "fdthree"))
|
||||
if (!strcmp(edev->prom_node->name, "fdthree"))
|
||||
return 1;
|
||||
if (!strcmp(edev->prom_name, "floppy")) {
|
||||
char compat[16];
|
||||
prom_getstring(edev->prom_node,
|
||||
"compatible",
|
||||
compat, sizeof(compat));
|
||||
compat[15] = '\0';
|
||||
if (!strcmp(compat, "fdthree"))
|
||||
if (!strcmp(edev->prom_node->name, "floppy")) {
|
||||
char *compat;
|
||||
|
||||
compat = of_get_property(edev->prom_node,
|
||||
"compatible", NULL);
|
||||
if (compat && !strcmp(compat, "fdthree"))
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
@ -524,12 +523,12 @@ static unsigned long __init isa_floppy_init(void)
|
||||
|
||||
for_each_isa(isa_br) {
|
||||
for_each_isadev(isa_dev, isa_br) {
|
||||
if (!strcmp(isa_dev->prom_name, "dma")) {
|
||||
if (!strcmp(isa_dev->prom_node->name, "dma")) {
|
||||
struct sparc_isa_device *child =
|
||||
isa_dev->child;
|
||||
|
||||
while (child) {
|
||||
if (!strcmp(child->prom_name,
|
||||
if (!strcmp(child->prom_node->name,
|
||||
"floppy")) {
|
||||
isa_dev = child;
|
||||
goto isa_done;
|
||||
@ -614,6 +613,7 @@ static unsigned long __init sun_floppy_init(void)
|
||||
struct linux_ebus_device *edev = NULL;
|
||||
unsigned long config = 0;
|
||||
void __iomem *auxio_reg;
|
||||
char *state_prop;
|
||||
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
@ -630,9 +630,8 @@ static unsigned long __init sun_floppy_init(void)
|
||||
#endif
|
||||
}
|
||||
|
||||
prom_getproperty(edev->prom_node, "status",
|
||||
state, sizeof(state));
|
||||
if (!strncmp(state, "disabled", 8))
|
||||
state_prop = of_get_property(edev->prom_node, "status", NULL);
|
||||
if (state_prop && !strncmp(state_prop, "disabled", 8))
|
||||
return 0;
|
||||
|
||||
FLOPPY_IRQ = edev->irqs[0];
|
||||
@ -703,7 +702,7 @@ static unsigned long __init sun_floppy_init(void)
|
||||
*/
|
||||
for_each_ebus(ebus) {
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
if (!strcmp(edev->prom_name, "ecpp")) {
|
||||
if (!strcmp(edev->prom_node->name, "ecpp")) {
|
||||
config = edev->resource[1].start;
|
||||
goto config_done;
|
||||
}
|
||||
|
@ -9,6 +9,7 @@
|
||||
|
||||
#include <asm/pbm.h>
|
||||
#include <asm/oplib.h>
|
||||
#include <asm/prom.h>
|
||||
|
||||
struct sparc_isa_bridge;
|
||||
|
||||
@ -16,9 +17,7 @@ struct sparc_isa_device {
|
||||
struct sparc_isa_device *next;
|
||||
struct sparc_isa_device *child;
|
||||
struct sparc_isa_bridge *bus;
|
||||
int prom_node;
|
||||
char prom_name[64];
|
||||
char compatible[64];
|
||||
struct device_node *prom_node;
|
||||
struct resource resource;
|
||||
unsigned int irq;
|
||||
};
|
||||
@ -29,8 +28,7 @@ struct sparc_isa_bridge {
|
||||
struct pci_pbm_info *parent;
|
||||
struct pci_dev *self;
|
||||
int index;
|
||||
int prom_node;
|
||||
char prom_name[64];
|
||||
struct device_node *prom_node;
|
||||
#define linux_prom_isa_ranges linux_prom_ebus_ranges
|
||||
struct linux_prom_isa_ranges isa_ranges[PROMREG_MAX];
|
||||
int num_isa_ranges;
|
||||
|
@ -67,18 +67,17 @@ static __inline__ unsigned int get_dma_residue(unsigned int dmanr)
|
||||
|
||||
static int ebus_ecpp_p(struct linux_ebus_device *edev)
|
||||
{
|
||||
if (!strcmp(edev->prom_name, "ecpp"))
|
||||
if (!strcmp(edev->prom_node->name, "ecpp"))
|
||||
return 1;
|
||||
if (!strcmp(edev->prom_name, "parallel")) {
|
||||
char compat[19];
|
||||
prom_getstring(edev->prom_node,
|
||||
"compatible",
|
||||
compat, sizeof(compat));
|
||||
compat[18] = '\0';
|
||||
if (!strcmp(compat, "ecpp"))
|
||||
return 1;
|
||||
if (!strcmp(compat, "ns87317-ecpp") &&
|
||||
!strcmp(compat + 13, "ecpp"))
|
||||
if (!strcmp(edev->prom_node->name, "parallel")) {
|
||||
char *compat;
|
||||
|
||||
compat = of_get_property(edev->prom_node,
|
||||
"compatible", NULL);
|
||||
if (compat &&
|
||||
(!strcmp(compat, "ecpp") ||
|
||||
!strcmp(compat, "ns87317-ecpp") ||
|
||||
!strcmp(compat + 13, "ecpp")))
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
@ -94,12 +93,12 @@ static int parport_isa_probe(int count)
|
||||
struct sparc_isa_device *child;
|
||||
unsigned long base;
|
||||
|
||||
if (strcmp(isa_dev->prom_name, "dma"))
|
||||
if (strcmp(isa_dev->prom_node->name, "dma"))
|
||||
continue;
|
||||
|
||||
child = isa_dev->child;
|
||||
while (child) {
|
||||
if (!strcmp(child->prom_name, "parallel"))
|
||||
if (!strcmp(child->prom_node->name, "parallel"))
|
||||
break;
|
||||
child = child->next;
|
||||
}
|
||||
|
@ -2284,15 +2284,14 @@ static int __init cs4231_init(void)
|
||||
for_each_ebusdev(edev, ebus) {
|
||||
int match = 0;
|
||||
|
||||
if (!strcmp(edev->prom_name, "SUNW,CS4231")) {
|
||||
if (!strcmp(edev->prom_node->name, "SUNW,CS4231")) {
|
||||
match = 1;
|
||||
} else if (!strcmp(edev->prom_name, "audio")) {
|
||||
char compat[16];
|
||||
} else if (!strcmp(edev->prom_node->name, "audio")) {
|
||||
char *compat;
|
||||
|
||||
prom_getstring(edev->prom_node, "compatible",
|
||||
compat, sizeof(compat));
|
||||
compat[15] = '\0';
|
||||
if (!strcmp(compat, "SUNW,CS4231"))
|
||||
compat = of_get_property(edev->prom_node,
|
||||
"compatible", NULL);
|
||||
if (compat && !strcmp(compat, "SUNW,CS4231"))
|
||||
match = 1;
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user