]> git.karo-electronics.de Git - karo-tx-linux.git/blob - drivers/nubus/nubus.c
Merge remote-tracking branches 'asoc/fix/pxa' and 'asoc/fix/tlv320aic3x' into asoc...
[karo-tx-linux.git] / drivers / nubus / nubus.c
1 /*
2  *      Macintosh Nubus Interface Code
3  *
4  *      Originally by Alan Cox
5  *
6  *      Mostly rewritten by David Huggins-Daines, C. Scott Ananian,
7  *      and others.
8  */
9
10 #include <linux/types.h>
11 #include <linux/kernel.h>
12 #include <linux/string.h>
13 #include <linux/nubus.h>
14 #include <linux/errno.h>
15 #include <linux/init.h>
16 #include <linux/delay.h>
17 #include <linux/module.h>
18 #include <linux/slab.h>
19 #include <asm/setup.h>
20 #include <asm/page.h>
21 #include <asm/hwtest.h>
22 #include <asm/mac_via.h>
23 #include <asm/mac_oss.h>
24
25 extern void via_nubus_init(void);
26 extern void oss_nubus_init(void);
27
28 /* Constants */
29
30 /* This is, of course, the size in bytelanes, rather than the size in
31    actual bytes */
32 #define FORMAT_BLOCK_SIZE 20
33 #define ROM_DIR_OFFSET 0x24
34
35 #define NUBUS_TEST_PATTERN 0x5A932BC7
36
37 /* Define this if you like to live dangerously - it is known not to
38    work on pretty much every machine except the Quadra 630 and the LC
39    III. */
40 #undef I_WANT_TO_PROBE_SLOT_ZERO
41
42 /* This sometimes helps combat failure to boot */
43 #undef TRY_TO_DODGE_WSOD
44
45 /* Globals */
46
47 struct nubus_dev*   nubus_devices;
48 struct nubus_board* nubus_boards;
49
50 /* Meaning of "bytelanes":
51
52    The card ROM may appear on any or all bytes of each long word in
53    NuBus memory.  The low 4 bits of the "map" value found in the
54    format block (at the top of the slot address space, as well as at
55    the top of the MacOS ROM) tells us which bytelanes, i.e. which byte
56    offsets within each longword, are valid.  Thus:
57
58    A map of 0x0f, as found in the MacOS ROM, means that all bytelanes
59    are valid.
60
61    A map of 0xf0 means that no bytelanes are valid (We pray that we
62    will never encounter this, but stranger things have happened)
63
64    A map of 0xe1 means that only the MSB of each long word is actually
65    part of the card ROM.  (We hope to never encounter NuBus on a
66    little-endian machine.  Again, stranger things have happened)
67
68    A map of 0x78 means that only the LSB of each long word is valid.
69
70    Etcetera, etcetera.  Hopefully this clears up some confusion over
71    what the following code actually does.  */
72  
73 static inline int not_useful(void *p, int map)
74 {
75         unsigned long pv=(unsigned long)p;
76         pv &= 3;
77         if(map & (1<<pv))
78                 return 0;
79         return 1;
80 }
81  
82 static unsigned long nubus_get_rom(unsigned char **ptr, int len, int map)
83 {
84         /* This will hold the result */
85         unsigned long v = 0;
86         unsigned char *p = *ptr;
87
88         while(len)
89         {
90                 v <<= 8;
91                 while(not_useful(p,map))
92                         p++;
93                 v |= *p++;
94                 len--;
95         }
96         *ptr = p;
97         return v;
98 }
99
100 static void nubus_rewind(unsigned char **ptr, int len, int map)
101 {
102         unsigned char *p=*ptr;
103
104         /* Sanity check */
105         if(len > 65536)
106                 printk(KERN_ERR "rewind of 0x%08x!\n", len);
107         while(len)
108         {
109                 do
110                 {
111                         p--;
112                 }
113                 while(not_useful(p, map));
114                 len--;
115         }
116         *ptr=p;
117 }
118
119 static void nubus_advance(unsigned char **ptr, int len, int map)
120 {
121         unsigned char *p = *ptr;
122         if(len>65536)
123                 printk(KERN_ERR "advance of 0x%08x!\n", len);
124         while(len)
125         {
126                 while(not_useful(p,map))
127                         p++;
128                 p++;
129                 len--;
130         }
131         *ptr = p;
132 }
133
134 static void nubus_move(unsigned char **ptr, int len, int map)
135 {
136         if(len > 0)
137                 nubus_advance(ptr, len, map);
138         else if(len < 0)
139                 nubus_rewind(ptr, -len, map);
140 }
141
142 /* Now, functions to read the sResource tree */
143
144 /* Each sResource entry consists of a 1-byte ID and a 3-byte data
145    field.  If that data field contains an offset, then obviously we
146    have to expand it from a 24-bit signed number to a 32-bit signed
147    number. */
148
149 static inline long nubus_expand32(long foo)
150 {
151         if(foo & 0x00800000)    /* 24bit negative */
152                 foo |= 0xFF000000;
153         return foo;
154 }
155
156 static inline void *nubus_rom_addr(int slot)
157 {       
158         /*
159          *      Returns the first byte after the card. We then walk
160          *      backwards to get the lane register and the config
161          */
162         return (void *)(0xF1000000+(slot<<24));
163 }
164
165 static unsigned char *nubus_dirptr(const struct nubus_dirent *nd)
166 {
167         unsigned char *p = nd->base;
168         /* Essentially, just step over the bytelanes using whatever
169            offset we might have found */
170         nubus_move(&p, nubus_expand32(nd->data), nd->mask);
171         /* And return the value */
172         return p;
173 }
174
175 /* These two are for pulling resource data blocks (i.e. stuff that's
176    pointed to with offsets) out of the card ROM. */
177
178 void nubus_get_rsrc_mem(void *dest, const struct nubus_dirent* dirent,
179                         int len)
180 {
181         unsigned char *t = (unsigned char *)dest;
182         unsigned char *p = nubus_dirptr(dirent);
183         while(len)
184         {
185                 *t++ = nubus_get_rom(&p, 1, dirent->mask);
186                 len--;
187         }
188 }
189 EXPORT_SYMBOL(nubus_get_rsrc_mem);
190
191 void nubus_get_rsrc_str(void *dest, const struct nubus_dirent* dirent,
192                         int len)
193 {
194         unsigned char *t=(unsigned char *)dest;
195         unsigned char *p = nubus_dirptr(dirent);
196         while(len)
197         {
198                 *t = nubus_get_rom(&p, 1, dirent->mask);
199                 if(!*t++)
200                         break;
201                 len--;
202         }
203 }
204 EXPORT_SYMBOL(nubus_get_rsrc_str);
205
206 int nubus_get_root_dir(const struct nubus_board* board,
207                        struct nubus_dir* dir)
208 {
209         dir->ptr = dir->base = board->directory;
210         dir->done = 0;
211         dir->mask = board->lanes;
212         return 0;
213 }
214 EXPORT_SYMBOL(nubus_get_root_dir);
215
216 /* This is a slyly renamed version of the above */
217 int nubus_get_func_dir(const struct nubus_dev* dev,
218                        struct nubus_dir* dir)
219 {
220         dir->ptr = dir->base = dev->directory;
221         dir->done = 0;
222         dir->mask = dev->board->lanes;
223         return 0;
224 }
225 EXPORT_SYMBOL(nubus_get_func_dir);
226
227 int nubus_get_board_dir(const struct nubus_board* board,
228                         struct nubus_dir* dir)
229 {
230         struct nubus_dirent ent;
231         
232         dir->ptr = dir->base = board->directory;
233         dir->done = 0;
234         dir->mask = board->lanes;
235
236         /* Now dereference it (the first directory is always the board
237            directory) */
238         if (nubus_readdir(dir, &ent) == -1)
239                 return -1;
240         if (nubus_get_subdir(&ent, dir) == -1)
241                 return -1;
242         return 0;
243 }
244 EXPORT_SYMBOL(nubus_get_board_dir);
245
246 int nubus_get_subdir(const struct nubus_dirent *ent,
247                      struct nubus_dir *dir)
248 {
249         dir->ptr = dir->base = nubus_dirptr(ent);
250         dir->done = 0;
251         dir->mask = ent->mask;
252         return 0;
253 }
254 EXPORT_SYMBOL(nubus_get_subdir);
255
256 int nubus_readdir(struct nubus_dir *nd, struct nubus_dirent *ent)
257 {
258         u32 resid;
259         if (nd->done)
260                 return -1;
261
262         /* Do this first, otherwise nubus_rewind & co are off by 4 */
263         ent->base = nd->ptr;
264
265         /* This moves nd->ptr forward */
266         resid = nubus_get_rom(&nd->ptr, 4, nd->mask);
267
268         /* EOL marker, as per the Apple docs */
269         if((resid&0xff000000) == 0xff000000)
270         {
271                 /* Mark it as done */
272                 nd->done = 1;
273                 return -1;
274         }
275
276         /* First byte is the resource ID */
277         ent->type  = resid >> 24;
278         /* Low 3 bytes might contain data (or might not) */
279         ent->data = resid & 0xffffff;
280         ent->mask  = nd->mask;
281         return 0;
282 }
283 EXPORT_SYMBOL(nubus_readdir);
284
285 int nubus_rewinddir(struct nubus_dir* dir)
286 {
287         dir->ptr = dir->base;
288         return 0;
289 }
290 EXPORT_SYMBOL(nubus_rewinddir);
291
292 /* Driver interface functions, more or less like in pci.c */
293
294 struct nubus_dev*
295 nubus_find_device(unsigned short category,
296                   unsigned short type,
297                   unsigned short dr_hw,
298                   unsigned short dr_sw,
299                   const struct nubus_dev* from)
300 {
301         struct nubus_dev* itor =
302                 from ? from->next : nubus_devices;
303
304         while (itor) {
305                 if (itor->category == category
306                     && itor->type == type
307                     && itor->dr_hw == dr_hw
308                     && itor->dr_sw == dr_sw)
309                         return itor;
310                 itor = itor->next;
311         }
312         return NULL;
313 }
314 EXPORT_SYMBOL(nubus_find_device);
315
316 struct nubus_dev*
317 nubus_find_type(unsigned short category,
318                 unsigned short type,
319                 const struct nubus_dev* from)
320 {
321         struct nubus_dev* itor =
322                 from ? from->next : nubus_devices;
323
324         while (itor) {
325                 if (itor->category == category
326                     && itor->type == type)
327                         return itor;
328                 itor = itor->next;
329         }
330         return NULL;
331 }
332 EXPORT_SYMBOL(nubus_find_type);
333
334 struct nubus_dev*
335 nubus_find_slot(unsigned int slot,
336                 const struct nubus_dev* from)
337 {
338         struct nubus_dev* itor =
339                 from ? from->next : nubus_devices;
340         
341         while (itor) {
342                 if (itor->board->slot == slot)
343                         return itor;
344                 itor = itor->next;
345         }
346         return NULL;
347 }
348 EXPORT_SYMBOL(nubus_find_slot);
349
350 int
351 nubus_find_rsrc(struct nubus_dir* dir, unsigned char rsrc_type,
352                 struct nubus_dirent* ent)
353 {
354         while (nubus_readdir(dir, ent) != -1) {
355                 if (ent->type == rsrc_type)
356                         return 0;
357         }       
358         return -1;
359 }
360 EXPORT_SYMBOL(nubus_find_rsrc);
361
362 /* Initialization functions - decide which slots contain stuff worth
363    looking at, and print out lots and lots of information from the
364    resource blocks. */
365
366 /* FIXME: A lot of this stuff will eventually be useful after
367    initialization, for intelligently probing Ethernet and video chips,
368    among other things.  The rest of it should go in the /proc code.
369    For now, we just use it to give verbose boot logs. */
370
371 static int __init nubus_show_display_resource(struct nubus_dev* dev,
372                                               const struct nubus_dirent* ent)
373 {
374         switch (ent->type) {
375         case NUBUS_RESID_GAMMADIR:
376                 printk(KERN_INFO "    gamma directory offset: 0x%06x\n", ent->data);
377                 break;
378         case 0x0080 ... 0x0085:
379                 printk(KERN_INFO "    mode %02X info offset: 0x%06x\n",
380                        ent->type, ent->data);
381                 break;
382         default:
383                 printk(KERN_INFO "    unknown resource %02X, data 0x%06x\n",
384                        ent->type, ent->data);
385         }
386         return 0;
387 }
388
389 static int __init nubus_show_network_resource(struct nubus_dev* dev,
390                                               const struct nubus_dirent* ent)
391 {
392         switch (ent->type) {
393         case NUBUS_RESID_MAC_ADDRESS:
394         {
395                 char addr[6];
396                 int i;
397                 
398                 nubus_get_rsrc_mem(addr, ent, 6);
399                 printk(KERN_INFO "    MAC address: ");
400                 for (i = 0; i < 6; i++)
401                         printk("%02x%s", addr[i] & 0xff,
402                                i == 5 ? "" : ":");
403                 printk("\n");
404                 break;
405         }
406         default:
407                 printk(KERN_INFO "    unknown resource %02X, data 0x%06x\n",
408                        ent->type, ent->data);
409         }
410         return 0;
411 }
412
413 static int __init nubus_show_cpu_resource(struct nubus_dev* dev,
414                                           const struct nubus_dirent* ent)
415 {
416         switch (ent->type) {
417         case NUBUS_RESID_MEMINFO:
418         {
419                 unsigned long meminfo[2];
420                 nubus_get_rsrc_mem(&meminfo, ent, 8);
421                 printk(KERN_INFO "    memory: [ 0x%08lx 0x%08lx ]\n",
422                        meminfo[0], meminfo[1]);
423                 break;
424         }
425         case NUBUS_RESID_ROMINFO:
426         {
427                 unsigned long rominfo[2];
428                 nubus_get_rsrc_mem(&rominfo, ent, 8);
429                 printk(KERN_INFO "    ROM:    [ 0x%08lx 0x%08lx ]\n",
430                        rominfo[0], rominfo[1]);
431                 break;
432         }
433         default:
434                 printk(KERN_INFO "    unknown resource %02X, data 0x%06x\n",
435                        ent->type, ent->data);
436         }
437         return 0;
438 }
439
440 static int __init nubus_show_private_resource(struct nubus_dev* dev,
441                                               const struct nubus_dirent* ent)
442 {
443         switch (dev->category) {
444         case NUBUS_CAT_DISPLAY:
445                 nubus_show_display_resource(dev, ent);
446                 break;
447         case NUBUS_CAT_NETWORK:
448                 nubus_show_network_resource(dev, ent);
449                 break;
450         case NUBUS_CAT_CPU:
451                 nubus_show_cpu_resource(dev, ent);
452                 break;
453         default:
454                 printk(KERN_INFO "    unknown resource %02X, data 0x%06x\n",
455                        ent->type, ent->data);
456         }
457         return 0;
458 }
459
460 static struct nubus_dev* __init
461            nubus_get_functional_resource(struct nubus_board* board,
462                                          int slot,
463                                          const struct nubus_dirent* parent)
464 {
465         struct nubus_dir    dir;
466         struct nubus_dirent ent;
467         struct nubus_dev*   dev;
468         
469         printk(KERN_INFO "  Function 0x%02x:\n", parent->type);
470         nubus_get_subdir(parent, &dir);
471
472         /* Apple seems to have botched the ROM on the IIx */
473         if (slot == 0 && (unsigned long)dir.base % 2)
474                 dir.base += 1;
475         
476         if (console_loglevel >= 10)
477                 printk(KERN_DEBUG "nubus_get_functional_resource: parent is 0x%p, dir is 0x%p\n",
478                        parent->base, dir.base);
479
480         /* Actually we should probably panic if this fails */
481         if ((dev = kzalloc(sizeof(*dev), GFP_ATOMIC)) == NULL)
482                 return NULL;    
483         dev->resid = parent->type;
484         dev->directory = dir.base;
485         dev->board = board;
486         
487         while (nubus_readdir(&dir, &ent) != -1)
488         {
489                 switch(ent.type)
490                 {
491                 case NUBUS_RESID_TYPE:
492                 {
493                         unsigned short nbtdata[4];
494                         nubus_get_rsrc_mem(nbtdata, &ent, 8);
495                         dev->category = nbtdata[0];
496                         dev->type     = nbtdata[1];
497                         dev->dr_sw    = nbtdata[2];
498                         dev->dr_hw    = nbtdata[3];
499                         printk(KERN_INFO "    type: [cat 0x%x type 0x%x hw 0x%x sw 0x%x]\n",
500                                nbtdata[0], nbtdata[1], nbtdata[2], nbtdata[3]);
501                         break;
502                 }
503                 case NUBUS_RESID_NAME:
504                 {
505                         nubus_get_rsrc_str(dev->name, &ent, 64);
506                         printk(KERN_INFO "    name: %s\n", dev->name);
507                         break;
508                 }
509                 case NUBUS_RESID_DRVRDIR:
510                 {
511                         /* MacOS driver.  If we were NetBSD we might
512                            use this :-) */
513                         struct nubus_dir drvr_dir;
514                         struct nubus_dirent drvr_ent;
515                         nubus_get_subdir(&ent, &drvr_dir);
516                         nubus_readdir(&drvr_dir, &drvr_ent);
517                         dev->driver = nubus_dirptr(&drvr_ent);
518                         printk(KERN_INFO "    driver at: 0x%p\n",
519                                dev->driver);
520                         break;
521                 }
522                 case NUBUS_RESID_MINOR_BASEOS:
523                         /* We will need this in order to support
524                            multiple framebuffers.  It might be handy
525                            for Ethernet as well */
526                         nubus_get_rsrc_mem(&dev->iobase, &ent, 4);
527                         printk(KERN_INFO "    memory offset: 0x%08lx\n",
528                                dev->iobase);
529                         break;
530                 case NUBUS_RESID_MINOR_LENGTH:
531                         /* Ditto */
532                         nubus_get_rsrc_mem(&dev->iosize, &ent, 4);
533                         printk(KERN_INFO "    memory length: 0x%08lx\n",
534                                dev->iosize);
535                         break;                  
536                 case NUBUS_RESID_FLAGS:
537                         dev->flags = ent.data;
538                         printk(KERN_INFO "    flags: 0x%06x\n", dev->flags);
539                         break;
540                 case NUBUS_RESID_HWDEVID:
541                         dev->hwdevid = ent.data;
542                         printk(KERN_INFO "    hwdevid: 0x%06x\n", dev->hwdevid);
543                         break;
544                 default:
545                         /* Local/Private resources have their own
546                            function */
547                         nubus_show_private_resource(dev, &ent);
548                 }
549         }
550                 
551         return dev;
552 }
553
554 /* This is cool. */
555 static int __init nubus_get_vidnames(struct nubus_board* board,
556                                      const struct nubus_dirent* parent)
557 {
558         struct nubus_dir    dir;
559         struct nubus_dirent ent;
560         /* FIXME: obviously we want to put this in a header file soon */
561         struct vidmode {
562                 u32 size;
563                 /* Don't know what this is yet */
564                 u16 id;
565                 /* Longest one I've seen so far is 26 characters */
566                 char name[32];
567         };
568
569         printk(KERN_INFO "    video modes supported:\n");
570         nubus_get_subdir(parent, &dir);
571         if (console_loglevel >= 10)
572                 printk(KERN_DEBUG "nubus_get_vidnames: parent is 0x%p, dir is 0x%p\n",
573                        parent->base, dir.base);
574
575         while(nubus_readdir(&dir, &ent) != -1)
576         {
577                 struct vidmode mode;
578                 u32 size;
579
580                 /* First get the length */
581                 nubus_get_rsrc_mem(&size, &ent, 4);
582                 
583                 /* Now clobber the whole thing */
584                 if (size > sizeof(mode) - 1)
585                         size = sizeof(mode) - 1;
586                 memset(&mode, 0, sizeof(mode));
587                 nubus_get_rsrc_mem(&mode, &ent, size);
588                 printk (KERN_INFO "      %02X: (%02X) %s\n", ent.type,
589                         mode.id, mode.name);
590         }
591         return 0;
592 }
593
594 /* This is *really* cool. */
595 static int __init nubus_get_icon(struct nubus_board* board,
596                                  const struct nubus_dirent* ent)
597 {
598         /* Should be 32x32 if my memory serves me correctly */
599         unsigned char icon[128];
600         int x, y;
601         
602         nubus_get_rsrc_mem(&icon, ent, 128);
603         printk(KERN_INFO "    icon:\n");
604
605         /* We should actually plot these somewhere in the framebuffer
606            init.  This is just to demonstrate that they do, in fact,
607            exist */
608         for (y = 0; y < 32; y++) {
609                 printk(KERN_INFO "      ");
610                 for (x = 0; x < 32; x++) {
611                         if (icon[y*4 + x/8]
612                             & (0x80 >> (x%8)))
613                                 printk("*");
614                         else
615                                 printk(" ");
616                 }
617                 printk("\n");
618         }
619         return 0;
620 }
621
622 static int __init nubus_get_vendorinfo(struct nubus_board* board,
623                                        const struct nubus_dirent* parent)
624 {
625         struct nubus_dir    dir;
626         struct nubus_dirent ent;
627         static char* vendor_fields[6] = {"ID", "serial", "revision",
628                                          "part", "date", "unknown field"};
629
630         printk(KERN_INFO "    vendor info:\n");
631         nubus_get_subdir(parent, &dir);
632         if (console_loglevel >= 10)
633                 printk(KERN_DEBUG "nubus_get_vendorinfo: parent is 0x%p, dir is 0x%p\n",
634                        parent->base, dir.base);
635
636         while(nubus_readdir(&dir, &ent) != -1)
637         {
638                 char name[64];
639                 
640                 /* These are all strings, we think */
641                 nubus_get_rsrc_str(name, &ent, 64);
642                 if (ent.type > 5)
643                         ent.type = 5;
644                 printk(KERN_INFO "    %s: %s\n",
645                        vendor_fields[ent.type-1], name);
646         }
647         return 0;
648 }
649
650 static int __init nubus_get_board_resource(struct nubus_board* board, int slot,
651                                            const struct nubus_dirent* parent)
652 {
653         struct nubus_dir    dir;
654         struct nubus_dirent ent;
655         
656         nubus_get_subdir(parent, &dir);
657         if (console_loglevel >= 10)
658                 printk(KERN_DEBUG "nubus_get_board_resource: parent is 0x%p, dir is 0x%p\n",
659                        parent->base, dir.base);
660
661         while(nubus_readdir(&dir, &ent) != -1)
662         {
663                 switch (ent.type) {
664                 case NUBUS_RESID_TYPE:
665                 {
666                         unsigned short nbtdata[4];
667                         /* This type is always the same, and is not
668                            useful except insofar as it tells us that
669                            we really are looking at a board resource. */
670                         nubus_get_rsrc_mem(nbtdata, &ent, 8);
671                         printk(KERN_INFO "    type: [cat 0x%x type 0x%x hw 0x%x sw 0x%x]\n",
672                                nbtdata[0], nbtdata[1], nbtdata[2],
673                                nbtdata[3]);
674                         if (nbtdata[0] != 1 || nbtdata[1] != 0 ||
675                             nbtdata[2] != 0 || nbtdata[3] != 0)
676                                 printk(KERN_ERR "this sResource is not a board resource!\n");
677                         break;
678                 }
679                 case NUBUS_RESID_NAME:
680                         nubus_get_rsrc_str(board->name, &ent, 64);
681                         printk(KERN_INFO "    name: %s\n", board->name);
682                         break;
683                 case NUBUS_RESID_ICON:
684                         nubus_get_icon(board, &ent);
685                         break;
686                 case NUBUS_RESID_BOARDID:
687                         printk(KERN_INFO "    board id: 0x%x\n", ent.data);
688                         break;
689                 case NUBUS_RESID_PRIMARYINIT:
690                         printk(KERN_INFO "    primary init offset: 0x%06x\n", ent.data);
691                         break;
692                 case NUBUS_RESID_VENDORINFO:
693                         nubus_get_vendorinfo(board, &ent);
694                         break;
695                 case NUBUS_RESID_FLAGS:
696                         printk(KERN_INFO "    flags: 0x%06x\n", ent.data);
697                         break;
698                 case NUBUS_RESID_HWDEVID:
699                         printk(KERN_INFO "    hwdevid: 0x%06x\n", ent.data);
700                         break;
701                 case NUBUS_RESID_SECONDINIT:
702                         printk(KERN_INFO "    secondary init offset: 0x%06x\n", ent.data);
703                         break;
704                         /* WTF isn't this in the functional resources? */ 
705                 case NUBUS_RESID_VIDNAMES:
706                         nubus_get_vidnames(board, &ent);
707                         break;
708                         /* Same goes for this */
709                 case NUBUS_RESID_VIDMODES:
710                         printk(KERN_INFO "    video mode parameter directory offset: 0x%06x\n",
711                                ent.data);
712                         break;                  
713                 default:
714                         printk(KERN_INFO "    unknown resource %02X, data 0x%06x\n",
715                                ent.type, ent.data);
716                 }
717         }
718         return 0;
719 }
720
721 /* Attempt to bypass the somewhat non-obvious arrangement of
722    sResources in the motherboard ROM */
723 static void __init nubus_find_rom_dir(struct nubus_board* board)
724 {
725         unsigned char* rp;
726         unsigned char* romdir;
727         struct nubus_dir dir;
728         struct nubus_dirent ent;
729
730         /* Check for the extra directory just under the format block */
731         rp = board->fblock;
732         nubus_rewind(&rp, 4, board->lanes);
733         if (nubus_get_rom(&rp, 4, board->lanes) != NUBUS_TEST_PATTERN) {
734                 /* OK, the ROM was telling the truth */
735                 board->directory = board->fblock;
736                 nubus_move(&board->directory,
737                            nubus_expand32(board->doffset),
738                            board->lanes);
739                 return;
740         }
741
742         /* On "slot zero", you have to walk down a few more
743            directories to get to the equivalent of a real card's root
744            directory.  We don't know what they were smoking when they
745            came up with this. */
746         romdir = nubus_rom_addr(board->slot);
747         nubus_rewind(&romdir, ROM_DIR_OFFSET, board->lanes);
748         dir.base = dir.ptr = romdir;
749         dir.done = 0;
750         dir.mask = board->lanes;
751
752         /* This one points to an "Unknown Macintosh" directory */
753         if (nubus_readdir(&dir, &ent) == -1)
754                 goto badrom;
755
756         if (console_loglevel >= 10)
757                 printk(KERN_INFO "nubus_get_rom_dir: entry %02x %06x\n", ent.type, ent.data);
758         /* This one takes us to where we want to go. */
759         if (nubus_readdir(&dir, &ent) == -1) 
760                 goto badrom;
761         if (console_loglevel >= 10)
762                 printk(KERN_DEBUG "nubus_get_rom_dir: entry %02x %06x\n", ent.type, ent.data);
763         nubus_get_subdir(&ent, &dir);
764
765         /* Resource ID 01, also an "Unknown Macintosh" */
766         if (nubus_readdir(&dir, &ent) == -1) 
767                 goto badrom;
768         if (console_loglevel >= 10)
769                 printk(KERN_DEBUG "nubus_get_rom_dir: entry %02x %06x\n", ent.type, ent.data);
770
771         /* FIXME: the first one is *not* always the right one.  We
772            suspect this has something to do with the ROM revision.
773            "The HORROR ROM" (LC-series) uses 0x7e, while "The HORROR
774            Continues" (Q630) uses 0x7b.  The DAFB Macs evidently use
775            something else.  Please run "Slots" on your Mac (see
776            include/linux/nubus.h for where to get this program) and
777            tell us where the 'SiDirPtr' for Slot 0 is.  If you feel
778            brave, you should also use MacsBug to walk down the ROM
779            directories like this function does and try to find the
780            path to that address... */
781         if (nubus_readdir(&dir, &ent) == -1)
782                 goto badrom;
783         if (console_loglevel >= 10)
784                 printk(KERN_DEBUG "nubus_get_rom_dir: entry %02x %06x\n", ent.type, ent.data);
785         
786         /* Bwahahahaha... */
787         nubus_get_subdir(&ent, &dir);
788         board->directory = dir.base;
789         return;
790         
791         /* Even more evil laughter... */
792  badrom:
793         board->directory = board->fblock;
794         nubus_move(&board->directory, nubus_expand32(board->doffset), board->lanes);
795         printk(KERN_ERR "nubus_get_rom_dir: ROM weirdness!  Notify the developers...\n");
796 }
797
798 /* Add a board (might be many devices) to the list */
799 static struct nubus_board* __init nubus_add_board(int slot, int bytelanes)
800 {
801         struct nubus_board* board;
802         struct nubus_board** boardp;
803
804         unsigned char *rp;
805         unsigned long dpat;
806         struct nubus_dir dir;
807         struct nubus_dirent ent;
808
809         /* Move to the start of the format block */
810         rp = nubus_rom_addr(slot);              
811         nubus_rewind(&rp, FORMAT_BLOCK_SIZE, bytelanes);
812
813         /* Actually we should probably panic if this fails */
814         if ((board = kzalloc(sizeof(*board), GFP_ATOMIC)) == NULL)
815                 return NULL;    
816         board->fblock = rp;
817
818         /* Dump the format block for debugging purposes */
819         if (console_loglevel >= 10) {
820                 int i;
821                 printk(KERN_DEBUG "Slot %X, format block at 0x%p\n",
822                        slot, rp);
823                 printk(KERN_DEBUG "Format block: ");
824                 for (i = 0; i < FORMAT_BLOCK_SIZE; i += 4) {
825                         unsigned short foo, bar;
826                         foo = nubus_get_rom(&rp, 2, bytelanes);
827                         bar = nubus_get_rom(&rp, 2, bytelanes);
828                         printk("%04x %04x  ", foo, bar);
829                 }
830                 printk("\n");
831                 rp = board->fblock;
832         }
833         
834         board->slot = slot;
835         board->slot_addr = (unsigned long) nubus_slot_addr(slot);
836         board->doffset = nubus_get_rom(&rp, 4, bytelanes);
837         /* rom_length is *supposed* to be the total length of the
838          * ROM.  In practice it is the "amount of ROM used to compute
839          * the CRC."  So some jokers decide to set it to zero and
840          * set the crc to zero so they don't have to do any math.
841          * See the Performa 460 ROM, for example.  Those Apple "engineers".
842          */
843         board->rom_length = nubus_get_rom(&rp, 4, bytelanes);
844         board->crc = nubus_get_rom(&rp, 4, bytelanes);
845         board->rev = nubus_get_rom(&rp, 1, bytelanes);
846         board->format = nubus_get_rom(&rp,1, bytelanes);
847         board->lanes = bytelanes;
848
849         /* Directory offset should be small and negative... */
850         if(!(board->doffset & 0x00FF0000))
851                 printk(KERN_WARNING "Dodgy doffset!\n");
852         dpat = nubus_get_rom(&rp, 4, bytelanes);
853         if(dpat != NUBUS_TEST_PATTERN)
854                 printk(KERN_WARNING "Wrong test pattern %08lx!\n", dpat);
855                 
856         /*
857          *      I wonder how the CRC is meant to work -
858          *              any takers ?
859          * CSA: According to MAC docs, not all cards pass the CRC anyway,
860          * since the initial Macintosh ROM releases skipped the check.
861          */
862
863         /* Attempt to work around slot zero weirdness */
864         nubus_find_rom_dir(board);
865         nubus_get_root_dir(board, &dir);        
866
867         /* We're ready to rock */
868         printk(KERN_INFO "Slot %X:\n", slot);
869
870         /* Each slot should have one board resource and any number of
871            functional resources.  So we'll fill in some fields in the
872            struct nubus_board from the board resource, then walk down
873            the list of functional resources, spinning out a nubus_dev
874            for each of them. */
875         if (nubus_readdir(&dir, &ent) == -1) {
876                 /* We can't have this! */
877                 printk(KERN_ERR "Board resource not found!\n");
878                 return NULL;
879         } else {
880                 printk(KERN_INFO "  Board resource:\n");
881                 nubus_get_board_resource(board, slot, &ent);
882         }
883
884         /* Aaaarrrrgghh!  The LC III motherboard has *two* board
885            resources.  I have no idea WTF to do about this. */
886
887         while (nubus_readdir(&dir, &ent) != -1) {
888                 struct nubus_dev*  dev;
889                 struct nubus_dev** devp;
890                 dev = nubus_get_functional_resource(board, slot, &ent);
891                 if (dev == NULL)
892                         continue;
893
894                 /* We zeroed this out above */
895                 if (board->first_dev == NULL)
896                         board->first_dev = dev;
897                 
898                 /* Put it on the global NuBus device chain. Keep entries in order. */
899                 for (devp=&nubus_devices; *devp!=NULL; devp=&((*devp)->next))
900                         /* spin */;
901                 *devp = dev;
902                 dev->next = NULL;               
903         }
904
905         /* Put it on the global NuBus board chain. Keep entries in order. */
906         for (boardp=&nubus_boards; *boardp!=NULL; boardp=&((*boardp)->next))
907                 /* spin */;
908         *boardp = board;
909         board->next = NULL;
910         
911         return board;
912 }
913
914 void __init nubus_probe_slot(int slot)
915 {
916         unsigned char dp;
917         unsigned char* rp;
918         int i;
919
920         rp = nubus_rom_addr(slot);      
921         for(i = 4; i; i--)
922         {
923                 unsigned long flags;
924                 int card_present;
925
926                 rp--;
927                 local_irq_save(flags);
928                 card_present = hwreg_present(rp);
929                 local_irq_restore(flags);
930                
931                 if (!card_present)
932                         continue;
933
934                 printk(KERN_DEBUG "Now probing slot %X at %p\n", slot, rp);
935                 dp = *rp;
936                 if(dp == 0)
937                         continue;
938
939                 /* The last byte of the format block consists of two
940                    nybbles which are "mirror images" of each other.
941                    These show us the valid bytelanes */
942                 if ((((dp>>4) ^ dp) & 0x0F) != 0x0F)
943                         continue;
944                 /* Check that this value is actually *on* one of the
945                    bytelanes it claims are valid! */
946                 if ((dp & 0x0F) >= (1<<i))
947                         continue;
948
949                 /* Looks promising.  Let's put it on the list. */
950                 nubus_add_board(slot, dp);
951
952                 return;
953         }
954 }
955
956 void __init nubus_scan_bus(void)
957 {
958         int slot;
959         /* This might not work on your machine */
960 #ifdef I_WANT_TO_PROBE_SLOT_ZERO
961         nubus_probe_slot(0);
962 #endif
963         for(slot = 9; slot < 15; slot++)
964         {
965                 nubus_probe_slot(slot);
966         }
967 }
968
969 static int __init nubus_init(void)
970 {
971         if (!MACH_IS_MAC) 
972                 return 0;
973
974         /* Initialize the NuBus interrupts */
975         if (oss_present) {
976                 oss_nubus_init();
977         } else {
978                 via_nubus_init();
979         }
980
981 #ifdef TRY_TO_DODGE_WSOD
982         /* Rogue Ethernet interrupts can kill the machine if we don't
983            do this.  Obviously this is bogus.  Hopefully the local VIA
984            gurus can fix the real cause of the problem. */
985         mdelay(1000);
986 #endif
987         
988         /* And probe */
989         printk("NuBus: Scanning NuBus slots.\n");
990         nubus_devices = NULL;
991         nubus_boards  = NULL;
992         nubus_scan_bus();
993         nubus_proc_init();
994         return 0;
995 }
996
997 subsys_initcall(nubus_init);