vserver 2.0 rc7
[linux-2.6.git] / arch / ppc / syslib / prom.c
1 /*
2  * Procedures for interfacing to the Open Firmware PROM on
3  * Power Macintosh computers.
4  *
5  * In particular, we are interested in the device tree
6  * and in using some of its services (exit, write to stdout).
7  *
8  * Paul Mackerras       August 1996.
9  * Copyright (C) 1996 Paul Mackerras.
10  */
11 #include <stdarg.h>
12 #include <linux/config.h>
13 #include <linux/kernel.h>
14 #include <linux/string.h>
15 #include <linux/init.h>
16 #include <linux/version.h>
17 #include <linux/threads.h>
18 #include <linux/spinlock.h>
19 #include <linux/ioport.h>
20 #include <linux/pci.h>
21 #include <linux/slab.h>
22 #include <linux/bitops.h>
23
24 #include <asm/sections.h>
25 #include <asm/prom.h>
26 #include <asm/page.h>
27 #include <asm/processor.h>
28 #include <asm/irq.h>
29 #include <asm/io.h>
30 #include <asm/smp.h>
31 #include <asm/bootx.h>
32 #include <asm/system.h>
33 #include <asm/mmu.h>
34 #include <asm/pgtable.h>
35 #include <asm/bootinfo.h>
36 #include <asm/btext.h>
37 #include <asm/pci-bridge.h>
38 #include <asm/open_pic.h>
39
40
41 struct pci_address {
42         unsigned a_hi;
43         unsigned a_mid;
44         unsigned a_lo;
45 };
46
47 struct pci_reg_property {
48         struct pci_address addr;
49         unsigned size_hi;
50         unsigned size_lo;
51 };
52
53 struct isa_reg_property {
54         unsigned space;
55         unsigned address;
56         unsigned size;
57 };
58
59 typedef unsigned long interpret_func(struct device_node *, unsigned long,
60                                      int, int);
61 static interpret_func interpret_pci_props;
62 static interpret_func interpret_dbdma_props;
63 static interpret_func interpret_isa_props;
64 static interpret_func interpret_macio_props;
65 static interpret_func interpret_root_props;
66
67 extern char *klimit;
68
69 /* Set for a newworld or CHRP machine */
70 int use_of_interrupt_tree;
71 struct device_node *dflt_interrupt_controller;
72 int num_interrupt_controllers;
73
74 int pmac_newworld;
75
76 extern unsigned int rtas_entry;  /* physical pointer */
77
78 extern struct device_node *allnodes;
79
80 static unsigned long finish_node(struct device_node *, unsigned long,
81                                  interpret_func *, int, int);
82 static unsigned long finish_node_interrupts(struct device_node *, unsigned long);
83 static struct device_node *find_phandle(phandle);
84
85 extern void enter_rtas(void *);
86 void phys_call_rtas(int, int, int, ...);
87
88 extern char cmd_line[512];      /* XXX */
89 extern boot_infos_t *boot_infos;
90 unsigned long dev_tree_size;
91
92 void __openfirmware
93 phys_call_rtas(int service, int nargs, int nret, ...)
94 {
95         va_list list;
96         union {
97                 unsigned long words[16];
98                 double align;
99         } u;
100         void (*rtas)(void *, unsigned long);
101         int i;
102
103         u.words[0] = service;
104         u.words[1] = nargs;
105         u.words[2] = nret;
106         va_start(list, nret);
107         for (i = 0; i < nargs; ++i)
108                 u.words[i+3] = va_arg(list, unsigned long);
109         va_end(list);
110
111         rtas = (void (*)(void *, unsigned long)) rtas_entry;
112         rtas(&u, rtas_data);
113 }
114
115 /*
116  * finish_device_tree is called once things are running normally
117  * (i.e. with text and data mapped to the address they were linked at).
118  * It traverses the device tree and fills in the name, type,
119  * {n_}addrs and {n_}intrs fields of each node.
120  */
121 void __init
122 finish_device_tree(void)
123 {
124         unsigned long mem = (unsigned long) klimit;
125         struct device_node *np;
126
127         /* All newworld pmac machines and CHRPs now use the interrupt tree */
128         for (np = allnodes; np != NULL; np = np->allnext) {
129                 if (get_property(np, "interrupt-parent", NULL)) {
130                         use_of_interrupt_tree = 1;
131                         break;
132                 }
133         }
134         if (_machine == _MACH_Pmac && use_of_interrupt_tree)
135                 pmac_newworld = 1;
136
137 #ifdef CONFIG_BOOTX_TEXT
138         if (boot_infos && pmac_newworld) {
139                 prom_print("WARNING ! BootX/miBoot booting is not supported on this machine\n");
140                 prom_print("          You should use an Open Firmware bootloader\n");
141         }
142 #endif /* CONFIG_BOOTX_TEXT */
143
144         if (use_of_interrupt_tree) {
145                 /*
146                  * We want to find out here how many interrupt-controller
147                  * nodes there are, and if we are booted from BootX,
148                  * we need a pointer to the first (and hopefully only)
149                  * such node.  But we can't use find_devices here since
150                  * np->name has not been set yet.  -- paulus
151                  */
152                 int n = 0;
153                 char *name, *ic;
154                 int iclen;
155
156                 for (np = allnodes; np != NULL; np = np->allnext) {
157                         ic = get_property(np, "interrupt-controller", &iclen);
158                         name = get_property(np, "name", NULL);
159                         /* checking iclen makes sure we don't get a false
160                            match on /chosen.interrupt_controller */
161                         if ((name != NULL
162                              && strcmp(name, "interrupt-controller") == 0)
163                             || (ic != NULL && iclen == 0 && strcmp(name, "AppleKiwi"))) {
164                                 if (n == 0)
165                                         dflt_interrupt_controller = np;
166                                 ++n;
167                         }
168                 }
169                 num_interrupt_controllers = n;
170         }
171
172         mem = finish_node(allnodes, mem, NULL, 1, 1);
173         dev_tree_size = mem - (unsigned long) allnodes;
174         klimit = (char *) mem;
175 }
176
177 static unsigned long __init
178 finish_node(struct device_node *np, unsigned long mem_start,
179             interpret_func *ifunc, int naddrc, int nsizec)
180 {
181         struct device_node *child;
182         int *ip;
183
184         np->name = get_property(np, "name", NULL);
185         np->type = get_property(np, "device_type", NULL);
186
187         if (!np->name)
188                 np->name = "<NULL>";
189         if (!np->type)
190                 np->type = "<NULL>";
191
192         /* get the device addresses and interrupts */
193         if (ifunc != NULL)
194                 mem_start = ifunc(np, mem_start, naddrc, nsizec);
195
196         if (use_of_interrupt_tree)
197                 mem_start = finish_node_interrupts(np, mem_start);
198
199         /* Look for #address-cells and #size-cells properties. */
200         ip = (int *) get_property(np, "#address-cells", NULL);
201         if (ip != NULL)
202                 naddrc = *ip;
203         ip = (int *) get_property(np, "#size-cells", NULL);
204         if (ip != NULL)
205                 nsizec = *ip;
206
207         if (np->parent == NULL)
208                 ifunc = interpret_root_props;
209         else if (np->type == 0)
210                 ifunc = NULL;
211         else if (!strcmp(np->type, "pci") || !strcmp(np->type, "vci"))
212                 ifunc = interpret_pci_props;
213         else if (!strcmp(np->type, "dbdma"))
214                 ifunc = interpret_dbdma_props;
215         else if (!strcmp(np->type, "mac-io")
216                  || ifunc == interpret_macio_props)
217                 ifunc = interpret_macio_props;
218         else if (!strcmp(np->type, "isa"))
219                 ifunc = interpret_isa_props;
220         else if (!strcmp(np->name, "uni-n") || !strcmp(np->name, "u3"))
221                 ifunc = interpret_root_props;
222         else if (!((ifunc == interpret_dbdma_props
223                     || ifunc == interpret_macio_props)
224                    && (!strcmp(np->type, "escc")
225                        || !strcmp(np->type, "media-bay"))))
226                 ifunc = NULL;
227
228         /* if we were booted from BootX, convert the full name */
229         if (boot_infos
230             && strncmp(np->full_name, "Devices:device-tree", 19) == 0) {
231                 if (np->full_name[19] == 0) {
232                         strcpy(np->full_name, "/");
233                 } else if (np->full_name[19] == ':') {
234                         char *p = np->full_name + 19;
235                         np->full_name = p;
236                         for (; *p; ++p)
237                                 if (*p == ':')
238                                         *p = '/';
239                 }
240         }
241
242         for (child = np->child; child != NULL; child = child->sibling)
243                 mem_start = finish_node(child, mem_start, ifunc,
244                                         naddrc, nsizec);
245
246         return mem_start;
247 }
248
249 /*
250  * Find the interrupt parent of a node.
251  */
252 static struct device_node * __init
253 intr_parent(struct device_node *p)
254 {
255         phandle *parp;
256
257         parp = (phandle *) get_property(p, "interrupt-parent", NULL);
258         if (parp == NULL)
259                 return p->parent;
260         p = find_phandle(*parp);
261         if (p != NULL)
262                 return p;
263         /*
264          * On a powermac booted with BootX, we don't get to know the
265          * phandles for any nodes, so find_phandle will return NULL.
266          * Fortunately these machines only have one interrupt controller
267          * so there isn't in fact any ambiguity.  -- paulus
268          */
269         if (num_interrupt_controllers == 1)
270                 p = dflt_interrupt_controller;
271         return p;
272 }
273
274 /*
275  * Find out the size of each entry of the interrupts property
276  * for a node.
277  */
278 static int __init
279 prom_n_intr_cells(struct device_node *np)
280 {
281         struct device_node *p;
282         unsigned int *icp;
283
284         for (p = np; (p = intr_parent(p)) != NULL; ) {
285                 icp = (unsigned int *)
286                         get_property(p, "#interrupt-cells", NULL);
287                 if (icp != NULL)
288                         return *icp;
289                 if (get_property(p, "interrupt-controller", NULL) != NULL
290                     || get_property(p, "interrupt-map", NULL) != NULL) {
291                         printk("oops, node %s doesn't have #interrupt-cells\n",
292                                p->full_name);
293                         return 1;
294                 }
295         }
296         printk("prom_n_intr_cells failed for %s\n", np->full_name);
297         return 1;
298 }
299
300 /*
301  * Map an interrupt from a device up to the platform interrupt
302  * descriptor.
303  */
304 static int __init
305 map_interrupt(unsigned int **irq, struct device_node **ictrler,
306               struct device_node *np, unsigned int *ints, int nintrc)
307 {
308         struct device_node *p, *ipar;
309         unsigned int *imap, *imask, *ip;
310         int i, imaplen, match;
311         int newintrc = 1, newaddrc = 1;
312         unsigned int *reg;
313         int naddrc;
314
315         reg = (unsigned int *) get_property(np, "reg", NULL);
316         naddrc = prom_n_addr_cells(np);
317         p = intr_parent(np);
318         while (p != NULL) {
319                 if (get_property(p, "interrupt-controller", NULL) != NULL)
320                         /* this node is an interrupt controller, stop here */
321                         break;
322                 imap = (unsigned int *)
323                         get_property(p, "interrupt-map", &imaplen);
324                 if (imap == NULL) {
325                         p = intr_parent(p);
326                         continue;
327                 }
328                 imask = (unsigned int *)
329                         get_property(p, "interrupt-map-mask", NULL);
330                 if (imask == NULL) {
331                         printk("oops, %s has interrupt-map but no mask\n",
332                                p->full_name);
333                         return 0;
334                 }
335                 imaplen /= sizeof(unsigned int);
336                 match = 0;
337                 ipar = NULL;
338                 while (imaplen > 0 && !match) {
339                         /* check the child-interrupt field */
340                         match = 1;
341                         for (i = 0; i < naddrc && match; ++i)
342                                 match = ((reg[i] ^ imap[i]) & imask[i]) == 0;
343                         for (; i < naddrc + nintrc && match; ++i)
344                                 match = ((ints[i-naddrc] ^ imap[i]) & imask[i]) == 0;
345                         imap += naddrc + nintrc;
346                         imaplen -= naddrc + nintrc;
347                         /* grab the interrupt parent */
348                         ipar = find_phandle((phandle) *imap++);
349                         --imaplen;
350                         if (ipar == NULL && num_interrupt_controllers == 1)
351                                 /* cope with BootX not giving us phandles */
352                                 ipar = dflt_interrupt_controller;
353                         if (ipar == NULL) {
354                                 printk("oops, no int parent %x in map of %s\n",
355                                        imap[-1], p->full_name);
356                                 return 0;
357                         }
358                         /* find the parent's # addr and intr cells */
359                         ip = (unsigned int *)
360                                 get_property(ipar, "#interrupt-cells", NULL);
361                         if (ip == NULL) {
362                                 printk("oops, no #interrupt-cells on %s\n",
363                                        ipar->full_name);
364                                 return 0;
365                         }
366                         newintrc = *ip;
367                         ip = (unsigned int *)
368                                 get_property(ipar, "#address-cells", NULL);
369                         newaddrc = (ip == NULL)? 0: *ip;
370                         imap += newaddrc + newintrc;
371                         imaplen -= newaddrc + newintrc;
372                 }
373                 if (imaplen < 0) {
374                         printk("oops, error decoding int-map on %s, len=%d\n",
375                                p->full_name, imaplen);
376                         return 0;
377                 }
378                 if (!match) {
379                         printk("oops, no match in %s int-map for %s\n",
380                                p->full_name, np->full_name);
381                         return 0;
382                 }
383                 p = ipar;
384                 naddrc = newaddrc;
385                 nintrc = newintrc;
386                 ints = imap - nintrc;
387                 reg = ints - naddrc;
388         }
389         if (p == NULL)
390                 printk("hmmm, int tree for %s doesn't have ctrler\n",
391                        np->full_name);
392         *irq = ints;
393         *ictrler = p;
394         return nintrc;
395 }
396
397 /*
398  * New version of finish_node_interrupts.
399  */
400 static unsigned long __init
401 finish_node_interrupts(struct device_node *np, unsigned long mem_start)
402 {
403         unsigned int *ints;
404         int intlen, intrcells;
405         int i, j, n, offset;
406         unsigned int *irq;
407         struct device_node *ic;
408
409         ints = (unsigned int *) get_property(np, "interrupts", &intlen);
410         if (ints == NULL)
411                 return mem_start;
412         intrcells = prom_n_intr_cells(np);
413         intlen /= intrcells * sizeof(unsigned int);
414         np->n_intrs = intlen;
415         np->intrs = (struct interrupt_info *) mem_start;
416         mem_start += intlen * sizeof(struct interrupt_info);
417
418         for (i = 0; i < intlen; ++i) {
419                 np->intrs[i].line = 0;
420                 np->intrs[i].sense = 1;
421                 n = map_interrupt(&irq, &ic, np, ints, intrcells);
422                 if (n <= 0)
423                         continue;
424                 offset = 0;
425                 /*
426                  * On a CHRP we have an 8259 which is subordinate to
427                  * the openpic in the interrupt tree, but we want the
428                  * openpic's interrupt numbers offsetted, not the 8259's.
429                  * So we apply the offset if the controller is at the
430                  * root of the interrupt tree, i.e. has no interrupt-parent.
431                  * This doesn't cope with the general case of multiple
432                  * cascaded interrupt controllers, but then neither will
433                  * irq.c at the moment either.  -- paulus
434                  * The G5 triggers that code, I add a machine test. On
435                  * those machines, we want to offset interrupts from the
436                  * second openpic by 128 -- BenH
437                  */
438                 if (_machine != _MACH_Pmac && num_interrupt_controllers > 1
439                     && ic != NULL
440                     && get_property(ic, "interrupt-parent", NULL) == NULL)
441                         offset = 16;
442                 else if (_machine == _MACH_Pmac && num_interrupt_controllers > 1
443                          && ic != NULL && ic->parent != NULL) {
444                         char *name = get_property(ic->parent, "name", NULL);
445                         if (name && !strcmp(name, "u3"))
446                                 offset = 128;
447                 }
448
449                 np->intrs[i].line = irq[0] + offset;
450                 if (n > 1)
451                         np->intrs[i].sense = irq[1];
452                 if (n > 2) {
453                         printk("hmmm, got %d intr cells for %s:", n,
454                                np->full_name);
455                         for (j = 0; j < n; ++j)
456                                 printk(" %d", irq[j]);
457                         printk("\n");
458                 }
459                 ints += intrcells;
460         }
461
462         return mem_start;
463 }
464
465 /*
466  * When BootX makes a copy of the device tree from the MacOS
467  * Name Registry, it is in the format we use but all of the pointers
468  * are offsets from the start of the tree.
469  * This procedure updates the pointers.
470  */
471 void __init
472 relocate_nodes(void)
473 {
474         unsigned long base;
475         struct device_node *np;
476         struct property *pp;
477
478 #define ADDBASE(x)      (x = (typeof (x))((x)? ((unsigned long)(x) + base): 0))
479
480         base = (unsigned long) boot_infos + boot_infos->deviceTreeOffset;
481         allnodes = (struct device_node *)(base + 4);
482         for (np = allnodes; np != 0; np = np->allnext) {
483                 ADDBASE(np->full_name);
484                 ADDBASE(np->properties);
485                 ADDBASE(np->parent);
486                 ADDBASE(np->child);
487                 ADDBASE(np->sibling);
488                 ADDBASE(np->allnext);
489                 for (pp = np->properties; pp != 0; pp = pp->next) {
490                         ADDBASE(pp->name);
491                         ADDBASE(pp->value);
492                         ADDBASE(pp->next);
493                 }
494         }
495 }
496
497 int
498 prom_n_addr_cells(struct device_node* np)
499 {
500         int* ip;
501         do {
502                 if (np->parent)
503                         np = np->parent;
504                 ip = (int *) get_property(np, "#address-cells", NULL);
505                 if (ip != NULL)
506                         return *ip;
507         } while (np->parent);
508         /* No #address-cells property for the root node, default to 1 */
509         return 1;
510 }
511
512 int
513 prom_n_size_cells(struct device_node* np)
514 {
515         int* ip;
516         do {
517                 if (np->parent)
518                         np = np->parent;
519                 ip = (int *) get_property(np, "#size-cells", NULL);
520                 if (ip != NULL)
521                         return *ip;
522         } while (np->parent);
523         /* No #size-cells property for the root node, default to 1 */
524         return 1;
525 }
526
527 static unsigned long __init
528 map_addr(struct device_node *np, unsigned long space, unsigned long addr)
529 {
530         int na;
531         unsigned int *ranges;
532         int rlen = 0;
533         unsigned int type;
534
535         type = (space >> 24) & 3;
536         if (type == 0)
537                 return addr;
538
539         while ((np = np->parent) != NULL) {
540                 if (strcmp(np->type, "pci") != 0)
541                         continue;
542                 /* PCI bridge: map the address through the ranges property */
543                 na = prom_n_addr_cells(np);
544                 ranges = (unsigned int *) get_property(np, "ranges", &rlen);
545                 while ((rlen -= (na + 5) * sizeof(unsigned int)) >= 0) {
546                         if (((ranges[0] >> 24) & 3) == type
547                             && ranges[2] <= addr
548                             && addr - ranges[2] < ranges[na+4]) {
549                                 /* ok, this matches, translate it */
550                                 addr += ranges[na+2] - ranges[2];
551                                 break;
552                         }
553                         ranges += na + 5;
554                 }
555         }
556         return addr;
557 }
558
559 static unsigned long __init
560 interpret_pci_props(struct device_node *np, unsigned long mem_start,
561                     int naddrc, int nsizec)
562 {
563         struct address_range *adr;
564         struct pci_reg_property *pci_addrs;
565         int i, l, *ip;
566
567         pci_addrs = (struct pci_reg_property *)
568                 get_property(np, "assigned-addresses", &l);
569         if (pci_addrs != 0 && l >= sizeof(struct pci_reg_property)) {
570                 i = 0;
571                 adr = (struct address_range *) mem_start;
572                 while ((l -= sizeof(struct pci_reg_property)) >= 0) {
573                         adr[i].space = pci_addrs[i].addr.a_hi;
574                         adr[i].address = map_addr(np, pci_addrs[i].addr.a_hi,
575                                                   pci_addrs[i].addr.a_lo);
576                         adr[i].size = pci_addrs[i].size_lo;
577                         ++i;
578                 }
579                 np->addrs = adr;
580                 np->n_addrs = i;
581                 mem_start += i * sizeof(struct address_range);
582         }
583
584         if (use_of_interrupt_tree)
585                 return mem_start;
586
587         ip = (int *) get_property(np, "AAPL,interrupts", &l);
588         if (ip == 0 && np->parent)
589                 ip = (int *) get_property(np->parent, "AAPL,interrupts", &l);
590         if (ip == 0)
591                 ip = (int *) get_property(np, "interrupts", &l);
592         if (ip != 0) {
593                 np->intrs = (struct interrupt_info *) mem_start;
594                 np->n_intrs = l / sizeof(int);
595                 mem_start += np->n_intrs * sizeof(struct interrupt_info);
596                 for (i = 0; i < np->n_intrs; ++i) {
597                         np->intrs[i].line = *ip++;
598                         np->intrs[i].sense = 1;
599                 }
600         }
601
602         return mem_start;
603 }
604
605 static unsigned long __init
606 interpret_dbdma_props(struct device_node *np, unsigned long mem_start,
607                       int naddrc, int nsizec)
608 {
609         struct reg_property *rp;
610         struct address_range *adr;
611         unsigned long base_address;
612         int i, l, *ip;
613         struct device_node *db;
614
615         base_address = 0;
616         for (db = np->parent; db != NULL; db = db->parent) {
617                 if (!strcmp(db->type, "dbdma") && db->n_addrs != 0) {
618                         base_address = db->addrs[0].address;
619                         break;
620                 }
621         }
622
623         rp = (struct reg_property *) get_property(np, "reg", &l);
624         if (rp != 0 && l >= sizeof(struct reg_property)) {
625                 i = 0;
626                 adr = (struct address_range *) mem_start;
627                 while ((l -= sizeof(struct reg_property)) >= 0) {
628                         adr[i].space = 2;
629                         adr[i].address = rp[i].address + base_address;
630                         adr[i].size = rp[i].size;
631                         ++i;
632                 }
633                 np->addrs = adr;
634                 np->n_addrs = i;
635                 mem_start += i * sizeof(struct address_range);
636         }
637
638         if (use_of_interrupt_tree)
639                 return mem_start;
640
641         ip = (int *) get_property(np, "AAPL,interrupts", &l);
642         if (ip == 0)
643                 ip = (int *) get_property(np, "interrupts", &l);
644         if (ip != 0) {
645                 np->intrs = (struct interrupt_info *) mem_start;
646                 np->n_intrs = l / sizeof(int);
647                 mem_start += np->n_intrs * sizeof(struct interrupt_info);
648                 for (i = 0; i < np->n_intrs; ++i) {
649                         np->intrs[i].line = *ip++;
650                         np->intrs[i].sense = 1;
651                 }
652         }
653
654         return mem_start;
655 }
656
657 static unsigned long __init
658 interpret_macio_props(struct device_node *np, unsigned long mem_start,
659                       int naddrc, int nsizec)
660 {
661         struct reg_property *rp;
662         struct address_range *adr;
663         unsigned long base_address;
664         int i, l, *ip;
665         struct device_node *db;
666
667         base_address = 0;
668         for (db = np->parent; db != NULL; db = db->parent) {
669                 if (!strcmp(db->type, "mac-io") && db->n_addrs != 0) {
670                         base_address = db->addrs[0].address;
671                         break;
672                 }
673         }
674
675         rp = (struct reg_property *) get_property(np, "reg", &l);
676         if (rp != 0 && l >= sizeof(struct reg_property)) {
677                 i = 0;
678                 adr = (struct address_range *) mem_start;
679                 while ((l -= sizeof(struct reg_property)) >= 0) {
680                         adr[i].space = 2;
681                         adr[i].address = rp[i].address + base_address;
682                         adr[i].size = rp[i].size;
683                         ++i;
684                 }
685                 np->addrs = adr;
686                 np->n_addrs = i;
687                 mem_start += i * sizeof(struct address_range);
688         }
689
690         if (use_of_interrupt_tree)
691                 return mem_start;
692
693         ip = (int *) get_property(np, "interrupts", &l);
694         if (ip == 0)
695                 ip = (int *) get_property(np, "AAPL,interrupts", &l);
696         if (ip != 0) {
697                 np->intrs = (struct interrupt_info *) mem_start;
698                 np->n_intrs = l / sizeof(int);
699                 for (i = 0; i < np->n_intrs; ++i) {
700                         np->intrs[i].line = *ip++;
701                         np->intrs[i].sense = 1;
702                 }
703                 mem_start += np->n_intrs * sizeof(struct interrupt_info);
704         }
705
706         return mem_start;
707 }
708
709 static unsigned long __init
710 interpret_isa_props(struct device_node *np, unsigned long mem_start,
711                     int naddrc, int nsizec)
712 {
713         struct isa_reg_property *rp;
714         struct address_range *adr;
715         int i, l, *ip;
716
717         rp = (struct isa_reg_property *) get_property(np, "reg", &l);
718         if (rp != 0 && l >= sizeof(struct isa_reg_property)) {
719                 i = 0;
720                 adr = (struct address_range *) mem_start;
721                 while ((l -= sizeof(struct reg_property)) >= 0) {
722                         adr[i].space = rp[i].space;
723                         adr[i].address = rp[i].address
724                                 + (adr[i].space? 0: _ISA_MEM_BASE);
725                         adr[i].size = rp[i].size;
726                         ++i;
727                 }
728                 np->addrs = adr;
729                 np->n_addrs = i;
730                 mem_start += i * sizeof(struct address_range);
731         }
732
733         if (use_of_interrupt_tree)
734                 return mem_start;
735
736         ip = (int *) get_property(np, "interrupts", &l);
737         if (ip != 0) {
738                 np->intrs = (struct interrupt_info *) mem_start;
739                 np->n_intrs = l / (2 * sizeof(int));
740                 mem_start += np->n_intrs * sizeof(struct interrupt_info);
741                 for (i = 0; i < np->n_intrs; ++i) {
742                         np->intrs[i].line = *ip++;
743                         np->intrs[i].sense = *ip++;
744                 }
745         }
746
747         return mem_start;
748 }
749
750 static unsigned long __init
751 interpret_root_props(struct device_node *np, unsigned long mem_start,
752                      int naddrc, int nsizec)
753 {
754         struct address_range *adr;
755         int i, l, *ip;
756         unsigned int *rp;
757         int rpsize = (naddrc + nsizec) * sizeof(unsigned int);
758
759         rp = (unsigned int *) get_property(np, "reg", &l);
760         if (rp != 0 && l >= rpsize) {
761                 i = 0;
762                 adr = (struct address_range *) mem_start;
763                 while ((l -= rpsize) >= 0) {
764                         adr[i].space = (naddrc >= 2? rp[naddrc-2]: 2);
765                         adr[i].address = rp[naddrc - 1];
766                         adr[i].size = rp[naddrc + nsizec - 1];
767                         ++i;
768                         rp += naddrc + nsizec;
769                 }
770                 np->addrs = adr;
771                 np->n_addrs = i;
772                 mem_start += i * sizeof(struct address_range);
773         }
774
775         if (use_of_interrupt_tree)
776                 return mem_start;
777
778         ip = (int *) get_property(np, "AAPL,interrupts", &l);
779         if (ip == 0)
780                 ip = (int *) get_property(np, "interrupts", &l);
781         if (ip != 0) {
782                 np->intrs = (struct interrupt_info *) mem_start;
783                 np->n_intrs = l / sizeof(int);
784                 mem_start += np->n_intrs * sizeof(struct interrupt_info);
785                 for (i = 0; i < np->n_intrs; ++i) {
786                         np->intrs[i].line = *ip++;
787                         np->intrs[i].sense = 1;
788                 }
789         }
790
791         return mem_start;
792 }
793
794 /*
795  * Work out the sense (active-low level / active-high edge)
796  * of each interrupt from the device tree.
797  */
798 void __init
799 prom_get_irq_senses(unsigned char *senses, int off, int max)
800 {
801         struct device_node *np;
802         int i, j;
803
804         /* default to level-triggered */
805         memset(senses, 1, max - off);
806         if (!use_of_interrupt_tree)
807                 return;
808
809         for (np = allnodes; np != 0; np = np->allnext) {
810                 for (j = 0; j < np->n_intrs; j++) {
811                         i = np->intrs[j].line;
812                         if (i >= off && i < max) {
813                                 if (np->intrs[j].sense == 1)
814                                         senses[i-off] = (IRQ_SENSE_LEVEL
815                                                 | IRQ_POLARITY_NEGATIVE);
816                                 else
817                                         senses[i-off] = (IRQ_SENSE_EDGE
818                                                 | IRQ_POLARITY_POSITIVE);
819                         }
820                 }
821         }
822 }
823
824 /*
825  * Construct and return a list of the device_nodes with a given name.
826  */
827 struct device_node *
828 find_devices(const char *name)
829 {
830         struct device_node *head, **prevp, *np;
831
832         prevp = &head;
833         for (np = allnodes; np != 0; np = np->allnext) {
834                 if (np->name != 0 && strcasecmp(np->name, name) == 0) {
835                         *prevp = np;
836                         prevp = &np->next;
837                 }
838         }
839         *prevp = NULL;
840         return head;
841 }
842
843 /*
844  * Construct and return a list of the device_nodes with a given type.
845  */
846 struct device_node *
847 find_type_devices(const char *type)
848 {
849         struct device_node *head, **prevp, *np;
850
851         prevp = &head;
852         for (np = allnodes; np != 0; np = np->allnext) {
853                 if (np->type != 0 && strcasecmp(np->type, type) == 0) {
854                         *prevp = np;
855                         prevp = &np->next;
856                 }
857         }
858         *prevp = NULL;
859         return head;
860 }
861
862 /*
863  * Returns all nodes linked together
864  */
865 struct device_node * __openfirmware
866 find_all_nodes(void)
867 {
868         struct device_node *head, **prevp, *np;
869
870         prevp = &head;
871         for (np = allnodes; np != 0; np = np->allnext) {
872                 *prevp = np;
873                 prevp = &np->next;
874         }
875         *prevp = NULL;
876         return head;
877 }
878
879 /* Checks if the given "compat" string matches one of the strings in
880  * the device's "compatible" property
881  */
882 int
883 device_is_compatible(struct device_node *device, const char *compat)
884 {
885         const char* cp;
886         int cplen, l;
887
888         cp = (char *) get_property(device, "compatible", &cplen);
889         if (cp == NULL)
890                 return 0;
891         while (cplen > 0) {
892                 if (strncasecmp(cp, compat, strlen(compat)) == 0)
893                         return 1;
894                 l = strlen(cp) + 1;
895                 cp += l;
896                 cplen -= l;
897         }
898
899         return 0;
900 }
901
902
903 /*
904  * Indicates whether the root node has a given value in its
905  * compatible property.
906  */
907 int
908 machine_is_compatible(const char *compat)
909 {
910         struct device_node *root;
911
912         root = find_path_device("/");
913         if (root == 0)
914                 return 0;
915         return device_is_compatible(root, compat);
916 }
917
918 /*
919  * Construct and return a list of the device_nodes with a given type
920  * and compatible property.
921  */
922 struct device_node *
923 find_compatible_devices(const char *type, const char *compat)
924 {
925         struct device_node *head, **prevp, *np;
926
927         prevp = &head;
928         for (np = allnodes; np != 0; np = np->allnext) {
929                 if (type != NULL
930                     && !(np->type != 0 && strcasecmp(np->type, type) == 0))
931                         continue;
932                 if (device_is_compatible(np, compat)) {
933                         *prevp = np;
934                         prevp = &np->next;
935                 }
936         }
937         *prevp = NULL;
938         return head;
939 }
940
941 /*
942  * Find the device_node with a given full_name.
943  */
944 struct device_node *
945 find_path_device(const char *path)
946 {
947         struct device_node *np;
948
949         for (np = allnodes; np != 0; np = np->allnext)
950                 if (np->full_name != 0 && strcasecmp(np->full_name, path) == 0)
951                         return np;
952         return NULL;
953 }
954
955 /*******
956  *
957  * New implementation of the OF "find" APIs, return a refcounted
958  * object, call of_node_put() when done. Currently, still lacks
959  * locking as old implementation, this is beeing done for ppc64.
960  *
961  * Note that property management will need some locking as well,
962  * this isn't dealt with yet
963  *
964  *******/
965
966 /**
967  *      of_find_node_by_name - Find a node by it's "name" property
968  *      @from:  The node to start searching from or NULL, the node
969  *              you pass will not be searched, only the next one
970  *              will; typically, you pass what the previous call
971  *              returned. of_node_put() will be called on it
972  *      @name:  The name string to match against
973  *
974  *      Returns a node pointer with refcount incremented, use
975  *      of_node_put() on it when done.
976  */
977 struct device_node *of_find_node_by_name(struct device_node *from,
978         const char *name)
979 {
980         struct device_node *np = from ? from->allnext : allnodes;
981
982         for (; np != 0; np = np->allnext)
983                 if (np->name != 0 && strcasecmp(np->name, name) == 0)
984                         break;
985         if (from)
986                 of_node_put(from);
987         return of_node_get(np);
988 }
989
990 /**
991  *      of_find_node_by_type - Find a node by it's "device_type" property
992  *      @from:  The node to start searching from or NULL, the node
993  *              you pass will not be searched, only the next one
994  *              will; typically, you pass what the previous call
995  *              returned. of_node_put() will be called on it
996  *      @name:  The type string to match against
997  *
998  *      Returns a node pointer with refcount incremented, use
999  *      of_node_put() on it when done.
1000  */
1001 struct device_node *of_find_node_by_type(struct device_node *from,
1002         const char *type)
1003 {
1004         struct device_node *np = from ? from->allnext : allnodes;
1005
1006         for (; np != 0; np = np->allnext)
1007                 if (np->type != 0 && strcasecmp(np->type, type) == 0)
1008                         break;
1009         if (from)
1010                 of_node_put(from);
1011         return of_node_get(np);
1012 }
1013
1014 /**
1015  *      of_find_compatible_node - Find a node based on type and one of the
1016  *                                tokens in it's "compatible" property
1017  *      @from:          The node to start searching from or NULL, the node
1018  *                      you pass will not be searched, only the next one
1019  *                      will; typically, you pass what the previous call
1020  *                      returned. of_node_put() will be called on it
1021  *      @type:          The type string to match "device_type" or NULL to ignore
1022  *      @compatible:    The string to match to one of the tokens in the device
1023  *                      "compatible" list.
1024  *
1025  *      Returns a node pointer with refcount incremented, use
1026  *      of_node_put() on it when done.
1027  */
1028 struct device_node *of_find_compatible_node(struct device_node *from,
1029         const char *type, const char *compatible)
1030 {
1031         struct device_node *np = from ? from->allnext : allnodes;
1032
1033         for (; np != 0; np = np->allnext) {
1034                 if (type != NULL
1035                     && !(np->type != 0 && strcasecmp(np->type, type) == 0))
1036                         continue;
1037                 if (device_is_compatible(np, compatible))
1038                         break;
1039         }
1040         if (from)
1041                 of_node_put(from);
1042         return of_node_get(np);
1043 }
1044
1045 /**
1046  *      of_find_node_by_path - Find a node matching a full OF path
1047  *      @path:  The full path to match
1048  *
1049  *      Returns a node pointer with refcount incremented, use
1050  *      of_node_put() on it when done.
1051  */
1052 struct device_node *of_find_node_by_path(const char *path)
1053 {
1054         struct device_node *np = allnodes;
1055
1056         for (; np != 0; np = np->allnext)
1057                 if (np->full_name != 0 && strcasecmp(np->full_name, path) == 0)
1058                         break;
1059         return of_node_get(np);
1060 }
1061
1062 /**
1063  *      of_find_all_nodes - Get next node in global list
1064  *      @prev:  Previous node or NULL to start iteration
1065  *              of_node_put() will be called on it
1066  *
1067  *      Returns a node pointer with refcount incremented, use
1068  *      of_node_put() on it when done.
1069  */
1070 struct device_node *of_find_all_nodes(struct device_node *prev)
1071 {
1072         return of_node_get(prev ? prev->allnext : allnodes);
1073 }
1074
1075 /**
1076  *      of_get_parent - Get a node's parent if any
1077  *      @node:  Node to get parent
1078  *
1079  *      Returns a node pointer with refcount incremented, use
1080  *      of_node_put() on it when done.
1081  */
1082 struct device_node *of_get_parent(const struct device_node *node)
1083 {
1084         return node ? of_node_get(node->parent) : NULL;
1085 }
1086
1087 /**
1088  *      of_get_next_child - Iterate a node childs
1089  *      @node:  parent node
1090  *      @prev:  previous child of the parent node, or NULL to get first
1091  *
1092  *      Returns a node pointer with refcount incremented, use
1093  *      of_node_put() on it when done.
1094  */
1095 struct device_node *of_get_next_child(const struct device_node *node,
1096                                       struct device_node *prev)
1097 {
1098         struct device_node *next = prev ? prev->sibling : node->child;
1099
1100         for (; next != 0; next = next->sibling)
1101                 if (of_node_get(next))
1102                         break;
1103         if (prev)
1104                 of_node_put(prev);
1105         return next;
1106 }
1107
1108 /**
1109  *      of_node_get - Increment refcount of a node
1110  *      @node:  Node to inc refcount, NULL is supported to
1111  *              simplify writing of callers
1112  *
1113  *      Returns the node itself or NULL if gone. Current implementation
1114  *      does nothing as we don't yet do dynamic node allocation on ppc32
1115  */
1116 struct device_node *of_node_get(struct device_node *node)
1117 {
1118         return node;
1119 }
1120
1121 /**
1122  *      of_node_put - Decrement refcount of a node
1123  *      @node:  Node to dec refcount, NULL is supported to
1124  *              simplify writing of callers
1125  *
1126  *      Current implementation does nothing as we don't yet do dynamic node
1127  *      allocation on ppc32
1128  */
1129 void  of_node_put(struct device_node *node)
1130 {
1131 }
1132
1133 /*
1134  * Find the device_node with a given phandle.
1135  */
1136 static struct device_node * __init
1137 find_phandle(phandle ph)
1138 {
1139         struct device_node *np;
1140
1141         for (np = allnodes; np != 0; np = np->allnext)
1142                 if (np->node == ph)
1143                         return np;
1144         return NULL;
1145 }
1146
1147 /*
1148  * Find a property with a given name for a given node
1149  * and return the value.
1150  */
1151 unsigned char *
1152 get_property(struct device_node *np, const char *name, int *lenp)
1153 {
1154         struct property *pp;
1155
1156         for (pp = np->properties; pp != 0; pp = pp->next)
1157                 if (pp->name != NULL && strcmp(pp->name, name) == 0) {
1158                         if (lenp != 0)
1159                                 *lenp = pp->length;
1160                         return pp->value;
1161                 }
1162         return NULL;
1163 }
1164
1165 /*
1166  * Add a property to a node
1167  */
1168 void __openfirmware
1169 prom_add_property(struct device_node* np, struct property* prop)
1170 {
1171         struct property **next = &np->properties;
1172
1173         prop->next = NULL;
1174         while (*next)
1175                 next = &(*next)->next;
1176         *next = prop;
1177 }
1178
1179 /* I quickly hacked that one, check against spec ! */
1180 static inline unsigned long __openfirmware
1181 bus_space_to_resource_flags(unsigned int bus_space)
1182 {
1183         u8 space = (bus_space >> 24) & 0xf;
1184         if (space == 0)
1185                 space = 0x02;
1186         if (space == 0x02)
1187                 return IORESOURCE_MEM;
1188         else if (space == 0x01)
1189                 return IORESOURCE_IO;
1190         else {
1191                 printk(KERN_WARNING "prom.c: bus_space_to_resource_flags(), space: %x\n",
1192                         bus_space);
1193                 return 0;
1194         }
1195 }
1196
1197 static struct resource* __openfirmware
1198 find_parent_pci_resource(struct pci_dev* pdev, struct address_range *range)
1199 {
1200         unsigned long mask;
1201         int i;
1202
1203         /* Check this one */
1204         mask = bus_space_to_resource_flags(range->space);
1205         for (i=0; i<DEVICE_COUNT_RESOURCE; i++) {
1206                 if ((pdev->resource[i].flags & mask) == mask &&
1207                         pdev->resource[i].start <= range->address &&
1208                         pdev->resource[i].end > range->address) {
1209                                 if ((range->address + range->size - 1) > pdev->resource[i].end) {
1210                                         /* Add better message */
1211                                         printk(KERN_WARNING "PCI/OF resource overlap !\n");
1212                                         return NULL;
1213                                 }
1214                                 break;
1215                         }
1216         }
1217         if (i == DEVICE_COUNT_RESOURCE)
1218                 return NULL;
1219         return &pdev->resource[i];
1220 }
1221
1222 /*
1223  * Request an OF device resource. Currently handles child of PCI devices,
1224  * or other nodes attached to the root node. Ultimately, put some
1225  * link to resources in the OF node.
1226  */
1227 struct resource* __openfirmware
1228 request_OF_resource(struct device_node* node, int index, const char* name_postfix)
1229 {
1230         struct pci_dev* pcidev;
1231         u8 pci_bus, pci_devfn;
1232         unsigned long iomask;
1233         struct device_node* nd;
1234         struct resource* parent;
1235         struct resource *res = NULL;
1236         int nlen, plen;
1237
1238         if (index >= node->n_addrs)
1239                 goto fail;
1240
1241         /* Sanity check on bus space */
1242         iomask = bus_space_to_resource_flags(node->addrs[index].space);
1243         if (iomask & IORESOURCE_MEM)
1244                 parent = &iomem_resource;
1245         else if (iomask & IORESOURCE_IO)
1246                 parent = &ioport_resource;
1247         else
1248                 goto fail;
1249
1250         /* Find a PCI parent if any */
1251         nd = node;
1252         pcidev = NULL;
1253         while(nd) {
1254                 if (!pci_device_from_OF_node(nd, &pci_bus, &pci_devfn))
1255                         pcidev = pci_find_slot(pci_bus, pci_devfn);
1256                 if (pcidev) break;
1257                 nd = nd->parent;
1258         }
1259         if (pcidev)
1260                 parent = find_parent_pci_resource(pcidev, &node->addrs[index]);
1261         if (!parent) {
1262                 printk(KERN_WARNING "request_OF_resource(%s), parent not found\n",
1263                         node->name);
1264                 goto fail;
1265         }
1266
1267         res = __request_region(parent, node->addrs[index].address, node->addrs[index].size, NULL);
1268         if (!res)
1269                 goto fail;
1270         nlen = strlen(node->name);
1271         plen = name_postfix ? strlen(name_postfix) : 0;
1272         res->name = (const char *)kmalloc(nlen+plen+1, GFP_KERNEL);
1273         if (res->name) {
1274                 strcpy((char *)res->name, node->name);
1275                 if (plen)
1276                         strcpy((char *)res->name+nlen, name_postfix);
1277         }
1278         return res;
1279 fail:
1280         return NULL;
1281 }
1282
1283 int __openfirmware
1284 release_OF_resource(struct device_node* node, int index)
1285 {
1286         struct pci_dev* pcidev;
1287         u8 pci_bus, pci_devfn;
1288         unsigned long iomask, start, end;
1289         struct device_node* nd;
1290         struct resource* parent;
1291         struct resource *res = NULL;
1292
1293         if (index >= node->n_addrs)
1294                 return -EINVAL;
1295
1296         /* Sanity check on bus space */
1297         iomask = bus_space_to_resource_flags(node->addrs[index].space);
1298         if (iomask & IORESOURCE_MEM)
1299                 parent = &iomem_resource;
1300         else if (iomask & IORESOURCE_IO)
1301                 parent = &ioport_resource;
1302         else
1303                 return -EINVAL;
1304
1305         /* Find a PCI parent if any */
1306         nd = node;
1307         pcidev = NULL;
1308         while(nd) {
1309                 if (!pci_device_from_OF_node(nd, &pci_bus, &pci_devfn))
1310                         pcidev = pci_find_slot(pci_bus, pci_devfn);
1311                 if (pcidev) break;
1312                 nd = nd->parent;
1313         }
1314         if (pcidev)
1315                 parent = find_parent_pci_resource(pcidev, &node->addrs[index]);
1316         if (!parent) {
1317                 printk(KERN_WARNING "release_OF_resource(%s), parent not found\n",
1318                         node->name);
1319                 return -ENODEV;
1320         }
1321
1322         /* Find us in the parent and its childs */
1323         res = parent->child;
1324         start = node->addrs[index].address;
1325         end = start + node->addrs[index].size - 1;
1326         while (res) {
1327                 if (res->start == start && res->end == end &&
1328                     (res->flags & IORESOURCE_BUSY))
1329                         break;
1330                 if (res->start <= start && res->end >= end)
1331                         res = res->child;
1332                 else
1333                         res = res->sibling;
1334         }
1335         if (!res)
1336                 return -ENODEV;
1337
1338         if (res->name) {
1339                 kfree(res->name);
1340                 res->name = NULL;
1341         }
1342         release_resource(res);
1343         kfree(res);
1344
1345         return 0;
1346 }
1347
1348 #if 0
1349 void __openfirmware
1350 print_properties(struct device_node *np)
1351 {
1352         struct property *pp;
1353         char *cp;
1354         int i, n;
1355
1356         for (pp = np->properties; pp != 0; pp = pp->next) {
1357                 printk(KERN_INFO "%s", pp->name);
1358                 for (i = strlen(pp->name); i < 16; ++i)
1359                         printk(" ");
1360                 cp = (char *) pp->value;
1361                 for (i = pp->length; i > 0; --i, ++cp)
1362                         if ((i > 1 && (*cp < 0x20 || *cp > 0x7e))
1363                             || (i == 1 && *cp != 0))
1364                                 break;
1365                 if (i == 0 && pp->length > 1) {
1366                         /* looks like a string */
1367                         printk(" %s\n", (char *) pp->value);
1368                 } else {
1369                         /* dump it in hex */
1370                         n = pp->length;
1371                         if (n > 64)
1372                                 n = 64;
1373                         if (pp->length % 4 == 0) {
1374                                 unsigned int *p = (unsigned int *) pp->value;
1375
1376                                 n /= 4;
1377                                 for (i = 0; i < n; ++i) {
1378                                         if (i != 0 && (i % 4) == 0)
1379                                                 printk("\n                ");
1380                                         printk(" %08x", *p++);
1381                                 }
1382                         } else {
1383                                 unsigned char *bp = pp->value;
1384
1385                                 for (i = 0; i < n; ++i) {
1386                                         if (i != 0 && (i % 16) == 0)
1387                                                 printk("\n                ");
1388                                         printk(" %02x", *bp++);
1389                                 }
1390                         }
1391                         printk("\n");
1392                         if (pp->length > 64)
1393                                 printk("                 ... (length = %d)\n",
1394                                        pp->length);
1395                 }
1396         }
1397 }
1398 #endif
1399
1400 static DEFINE_SPINLOCK(rtas_lock);
1401
1402 /* this can be called after setup -- Cort */
1403 int __openfirmware
1404 call_rtas(const char *service, int nargs, int nret,
1405           unsigned long *outputs, ...)
1406 {
1407         va_list list;
1408         int i;
1409         unsigned long s;
1410         struct device_node *rtas;
1411         int *tokp;
1412         union {
1413                 unsigned long words[16];
1414                 double align;
1415         } u;
1416
1417         rtas = find_devices("rtas");
1418         if (rtas == NULL)
1419                 return -1;
1420         tokp = (int *) get_property(rtas, service, NULL);
1421         if (tokp == NULL) {
1422                 printk(KERN_ERR "No RTAS service called %s\n", service);
1423                 return -1;
1424         }
1425         u.words[0] = *tokp;
1426         u.words[1] = nargs;
1427         u.words[2] = nret;
1428         va_start(list, outputs);
1429         for (i = 0; i < nargs; ++i)
1430                 u.words[i+3] = va_arg(list, unsigned long);
1431         va_end(list);
1432
1433         /*
1434          * RTAS doesn't use floating point.
1435          * Or at least, according to the CHRP spec we enter RTAS
1436          * with FP disabled, and it doesn't change the FP registers.
1437          *  -- paulus.
1438          */
1439         spin_lock_irqsave(&rtas_lock, s);
1440         enter_rtas((void *)__pa(&u));
1441         spin_unlock_irqrestore(&rtas_lock, s);
1442
1443         if (nret > 1 && outputs != NULL)
1444                 for (i = 0; i < nret-1; ++i)
1445                         outputs[i] = u.words[i+nargs+4];
1446         return u.words[nargs+3];
1447 }