VServer 1.9.2 (patch-2.6.8.1-vs1.9.2.diff)
[linux-2.6.git] / arch / arm / kernel / setup.c
1 /*
2  *  linux/arch/arm/kernel/setup.c
3  *
4  *  Copyright (C) 1995-2001 Russell King
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License version 2 as
8  * published by the Free Software Foundation.
9  */
10 #include <linux/config.h>
11 #include <linux/module.h>
12 #include <linux/kernel.h>
13 #include <linux/stddef.h>
14 #include <linux/ioport.h>
15 #include <linux/delay.h>
16 #include <linux/utsname.h>
17 #include <linux/initrd.h>
18 #include <linux/console.h>
19 #include <linux/bootmem.h>
20 #include <linux/seq_file.h>
21 #include <linux/tty.h>
22 #include <linux/init.h>
23 #include <linux/root_dev.h>
24 #include <linux/cpu.h>
25 #include <linux/interrupt.h>
26
27 #include <asm/elf.h>
28 #include <asm/hardware.h>
29 #include <asm/io.h>
30 #include <asm/procinfo.h>
31 #include <asm/setup.h>
32 #include <asm/mach-types.h>
33 #include <asm/cacheflush.h>
34 #include <asm/tlbflush.h>
35
36 #include <asm/mach/arch.h>
37 #include <asm/mach/irq.h>
38 #include <asm/mach/time.h>
39
40 #ifndef MEM_SIZE
41 #define MEM_SIZE        (16*1024*1024)
42 #endif
43
44 #if defined(CONFIG_FPE_NWFPE) || defined(CONFIG_FPE_FASTFPE)
45 char fpe_type[8];
46
47 static int __init fpe_setup(char *line)
48 {
49         memcpy(fpe_type, line, 8);
50         return 1;
51 }
52
53 __setup("fpe=", fpe_setup);
54 #endif
55
56 extern unsigned int mem_fclk_21285;
57 extern void paging_init(struct meminfo *, struct machine_desc *desc);
58 extern void convert_to_tag_list(struct tag *tags);
59 extern void squash_mem_tags(struct tag *tag);
60 extern void bootmem_init(struct meminfo *);
61 extern void reboot_setup(char *str);
62 extern int root_mountflags;
63 extern int _stext, _text, _etext, _edata, _end;
64
65 unsigned int processor_id;
66 unsigned int __machine_arch_type;
67 EXPORT_SYMBOL(__machine_arch_type);
68
69 unsigned int system_rev;
70 EXPORT_SYMBOL(system_rev);
71
72 unsigned int system_serial_low;
73 EXPORT_SYMBOL(system_serial_low);
74
75 unsigned int system_serial_high;
76 EXPORT_SYMBOL(system_serial_high);
77
78 unsigned int elf_hwcap;
79 EXPORT_SYMBOL(elf_hwcap);
80
81
82 #ifdef MULTI_CPU
83 struct processor processor;
84 #endif
85 #ifdef MULTI_TLB
86 struct cpu_tlb_fns cpu_tlb;
87 #endif
88 #ifdef MULTI_USER
89 struct cpu_user_fns cpu_user;
90 #endif
91 #ifdef MULTI_CACHE
92 struct cpu_cache_fns cpu_cache;
93 #endif
94
95 unsigned char aux_device_present;
96
97 char elf_platform[ELF_PLATFORM_SIZE];
98 EXPORT_SYMBOL(elf_platform);
99
100 unsigned long phys_initrd_start __initdata = 0;
101 unsigned long phys_initrd_size __initdata = 0;
102
103 static struct meminfo meminfo __initdata = { 0, };
104 static const char *cpu_name;
105 static const char *machine_name;
106 static char command_line[COMMAND_LINE_SIZE];
107
108 static char default_command_line[COMMAND_LINE_SIZE] __initdata = CONFIG_CMDLINE;
109 static union { char c[4]; unsigned long l; } endian_test __initdata = { { 'l', '?', '?', 'b' } };
110 #define ENDIANNESS ((char)endian_test.l)
111
112 /*
113  * Standard memory resources
114  */
115 static struct resource mem_res[] = {
116         { "Video RAM",   0,     0,     IORESOURCE_MEM                   },
117         { "Kernel code", 0,     0,     IORESOURCE_MEM                   },
118         { "Kernel data", 0,     0,     IORESOURCE_MEM                   }
119 };
120
121 #define video_ram   mem_res[0]
122 #define kernel_code mem_res[1]
123 #define kernel_data mem_res[2]
124
125 static struct resource io_res[] = {
126         { "reserved",    0x3bc, 0x3be, IORESOURCE_IO | IORESOURCE_BUSY },
127         { "reserved",    0x378, 0x37f, IORESOURCE_IO | IORESOURCE_BUSY },
128         { "reserved",    0x278, 0x27f, IORESOURCE_IO | IORESOURCE_BUSY }
129 };
130
131 #define lp0 io_res[0]
132 #define lp1 io_res[1]
133 #define lp2 io_res[2]
134
135 static const char *cache_types[16] = {
136         "VIVT write-through",
137         "VIVT write-back",
138         "VIVT write-back",
139         "undefined 3",
140         "undefined 4",
141         "undefined 5",
142         "VIVT write-back",
143         "VIVT write-back",
144         "undefined 8",
145         "undefined 9",
146         "undefined 10",
147         "undefined 11",
148         "undefined 12",
149         "undefined 13",
150         "VIPT write-back",
151         "undefined 15",
152 };
153
154 static const char *cache_clean[16] = {
155         "not required",
156         "read-block",
157         "cp15 c7 ops",
158         "undefined 3",
159         "undefined 4",
160         "undefined 5",
161         "cp15 c7 ops",
162         "cp15 c7 ops",
163         "undefined 8",
164         "undefined 9",
165         "undefined 10",
166         "undefined 11",
167         "undefined 12",
168         "undefined 13",
169         "cp15 c7 ops",
170         "undefined 15",
171 };
172
173 static const char *cache_lockdown[16] = {
174         "not supported",
175         "not supported",
176         "not supported",
177         "undefined 3",
178         "undefined 4",
179         "undefined 5",
180         "format A",
181         "format B",
182         "undefined 8",
183         "undefined 9",
184         "undefined 10",
185         "undefined 11",
186         "undefined 12",
187         "undefined 13",
188         "format C",
189         "undefined 15",
190 };
191
192 static const char *proc_arch[] = {
193         "undefined/unknown",
194         "3",
195         "4",
196         "4T",
197         "5",
198         "5T",
199         "5TE",
200         "5TEJ",
201         "6TEJ",
202         "?(10)",
203         "?(11)",
204         "?(12)",
205         "?(13)",
206         "?(14)",
207         "?(15)",
208         "?(16)",
209         "?(17)",
210 };
211
212 #define CACHE_TYPE(x)   (((x) >> 25) & 15)
213 #define CACHE_S(x)      ((x) & (1 << 24))
214 #define CACHE_DSIZE(x)  (((x) >> 12) & 4095)    /* only if S=1 */
215 #define CACHE_ISIZE(x)  ((x) & 4095)
216
217 #define CACHE_SIZE(y)   (((y) >> 6) & 7)
218 #define CACHE_ASSOC(y)  (((y) >> 3) & 7)
219 #define CACHE_M(y)      ((y) & (1 << 2))
220 #define CACHE_LINE(y)   ((y) & 3)
221
222 static inline void dump_cache(const char *prefix, unsigned int cache)
223 {
224         unsigned int mult = 2 + (CACHE_M(cache) ? 1 : 0);
225
226         printk("%s: %d bytes, associativity %d, %d byte lines, %d sets\n",
227                 prefix,
228                 mult << (8 + CACHE_SIZE(cache)),
229                 (mult << CACHE_ASSOC(cache)) >> 1,
230                 8 << CACHE_LINE(cache),
231                 1 << (6 + CACHE_SIZE(cache) - CACHE_ASSOC(cache) -
232                         CACHE_LINE(cache)));
233 }
234
235 static void __init dump_cpu_info(void)
236 {
237         unsigned int info = read_cpuid(CPUID_CACHETYPE);
238
239         if (info != processor_id) {
240                 printk("CPU: D %s cache\n", cache_types[CACHE_TYPE(info)]);
241                 if (CACHE_S(info)) {
242                         dump_cache("CPU: I cache", CACHE_ISIZE(info));
243                         dump_cache("CPU: D cache", CACHE_DSIZE(info));
244                 } else {
245                         dump_cache("CPU: cache", CACHE_ISIZE(info));
246                 }
247         }
248 }
249
250 int cpu_architecture(void)
251 {
252         int cpu_arch;
253
254         if ((processor_id & 0x0000f000) == 0) {
255                 cpu_arch = CPU_ARCH_UNKNOWN;
256         } else if ((processor_id & 0x0000f000) == 0x00007000) {
257                 cpu_arch = (processor_id & (1 << 23)) ? CPU_ARCH_ARMv4T : CPU_ARCH_ARMv3;
258         } else {
259                 cpu_arch = (processor_id >> 16) & 15;
260                 if (cpu_arch)
261                         cpu_arch += CPU_ARCH_ARMv3;
262         }
263
264         return cpu_arch;
265 }
266
267 static void __init setup_processor(void)
268 {
269         extern struct proc_info_list __proc_info_begin, __proc_info_end;
270         struct proc_info_list *list;
271
272         /*
273          * locate processor in the list of supported processor
274          * types.  The linker builds this table for us from the
275          * entries in arch/arm/mm/proc-*.S
276          */
277         for (list = &__proc_info_begin; list < &__proc_info_end ; list++)
278                 if ((processor_id & list->cpu_mask) == list->cpu_val)
279                         break;
280
281         /*
282          * If processor type is unrecognised, then we
283          * can do nothing...
284          */
285         if (list >= &__proc_info_end) {
286                 printk("CPU configuration botched (ID %08x), unable "
287                        "to continue.\n", processor_id);
288                 while (1);
289         }
290
291         cpu_name = list->cpu_name;
292
293 #ifdef MULTI_CPU
294         processor = *list->proc;
295 #endif
296 #ifdef MULTI_TLB
297         cpu_tlb = *list->tlb;
298 #endif
299 #ifdef MULTI_USER
300         cpu_user = *list->user;
301 #endif
302 #ifdef MULTI_CACHE
303         cpu_cache = *list->cache;
304 #endif
305
306         printk("CPU: %s [%08x] revision %d (ARMv%s)\n",
307                cpu_name, processor_id, (int)processor_id & 15,
308                proc_arch[cpu_architecture()]);
309
310         dump_cpu_info();
311
312         sprintf(system_utsname.machine, "%s%c", list->arch_name, ENDIANNESS);
313         sprintf(elf_platform, "%s%c", list->elf_name, ENDIANNESS);
314         elf_hwcap = list->elf_hwcap;
315
316         cpu_proc_init();
317 }
318
319 static struct machine_desc * __init setup_machine(unsigned int nr)
320 {
321         extern struct machine_desc __arch_info_begin, __arch_info_end;
322         struct machine_desc *list;
323
324         /*
325          * locate architecture in the list of supported architectures.
326          */
327         for (list = &__arch_info_begin; list < &__arch_info_end; list++)
328                 if (list->nr == nr)
329                         break;
330
331         /*
332          * If the architecture type is not recognised, then we
333          * can co nothing...
334          */
335         if (list >= &__arch_info_end) {
336                 printk("Architecture configuration botched (nr %d), unable "
337                        "to continue.\n", nr);
338                 while (1);
339         }
340
341         printk("Machine: %s\n", list->name);
342
343         return list;
344 }
345
346 static void __init early_initrd(char **p)
347 {
348         unsigned long start, size;
349
350         start = memparse(*p, p);
351         if (**p == ',') {
352                 size = memparse((*p) + 1, p);
353
354                 phys_initrd_start = start;
355                 phys_initrd_size = size;
356         }
357 }
358 __early_param("initrd=", early_initrd);
359
360 /*
361  * Pick out the memory size.  We look for mem=size@start,
362  * where start and size are "size[KkMm]"
363  */
364 static void __init early_mem(char **p)
365 {
366         static int usermem __initdata = 0;
367         unsigned long size, start;
368
369         /*
370          * If the user specifies memory size, we
371          * blow away any automatically generated
372          * size.
373          */
374         if (usermem == 0) {
375                 usermem = 1;
376                 meminfo.nr_banks = 0;
377         }
378
379         start = PHYS_OFFSET;
380         size  = memparse(*p, p);
381         if (**p == '@')
382                 start = memparse(*p + 1, p);
383
384         meminfo.bank[meminfo.nr_banks].start = start;
385         meminfo.bank[meminfo.nr_banks].size  = size;
386         meminfo.bank[meminfo.nr_banks].node  = PHYS_TO_NID(start);
387         meminfo.nr_banks += 1;
388 }
389 __early_param("mem=", early_mem);
390
391 /*
392  * Initial parsing of the command line.
393  */
394 static void __init parse_cmdline(char **cmdline_p, char *from)
395 {
396         char c = ' ', *to = command_line;
397         int len = 0;
398
399         for (;;) {
400                 if (c == ' ') {
401                         extern struct early_params __early_begin, __early_end;
402                         struct early_params *p;
403
404                         for (p = &__early_begin; p < &__early_end; p++) {
405                                 int len = strlen(p->arg);
406
407                                 if (memcmp(from, p->arg, len) == 0) {
408                                         if (to != command_line)
409                                                 to -= 1;
410                                         from += len;
411                                         p->fn(&from);
412
413                                         while (*from != ' ' && *from != '\0')
414                                                 from++;
415                                         break;
416                                 }
417                         }
418                 }
419                 c = *from++;
420                 if (!c)
421                         break;
422                 if (COMMAND_LINE_SIZE <= ++len)
423                         break;
424                 *to++ = c;
425         }
426         *to = '\0';
427         *cmdline_p = command_line;
428 }
429
430 static void __init
431 setup_ramdisk(int doload, int prompt, int image_start, unsigned int rd_sz)
432 {
433 #ifdef CONFIG_BLK_DEV_RAM
434         extern int rd_size, rd_image_start, rd_prompt, rd_doload;
435
436         rd_image_start = image_start;
437         rd_prompt = prompt;
438         rd_doload = doload;
439
440         if (rd_sz)
441                 rd_size = rd_sz;
442 #endif
443 }
444
445 static void __init
446 request_standard_resources(struct meminfo *mi, struct machine_desc *mdesc)
447 {
448         struct resource *res;
449         int i;
450
451         kernel_code.start  = __virt_to_phys(init_mm.start_code);
452         kernel_code.end    = __virt_to_phys(init_mm.end_code - 1);
453         kernel_data.start  = __virt_to_phys(init_mm.end_code);
454         kernel_data.end    = __virt_to_phys(init_mm.brk - 1);
455
456         for (i = 0; i < mi->nr_banks; i++) {
457                 unsigned long virt_start, virt_end;
458
459                 if (mi->bank[i].size == 0)
460                         continue;
461
462                 virt_start = __phys_to_virt(mi->bank[i].start);
463                 virt_end   = virt_start + mi->bank[i].size - 1;
464
465                 res = alloc_bootmem_low(sizeof(*res));
466                 res->name  = "System RAM";
467                 res->start = __virt_to_phys(virt_start);
468                 res->end   = __virt_to_phys(virt_end);
469                 res->flags = IORESOURCE_MEM | IORESOURCE_BUSY;
470
471                 request_resource(&iomem_resource, res);
472
473                 if (kernel_code.start >= res->start &&
474                     kernel_code.end <= res->end)
475                         request_resource(res, &kernel_code);
476                 if (kernel_data.start >= res->start &&
477                     kernel_data.end <= res->end)
478                         request_resource(res, &kernel_data);
479         }
480
481         if (mdesc->video_start) {
482                 video_ram.start = mdesc->video_start;
483                 video_ram.end   = mdesc->video_end;
484                 request_resource(&iomem_resource, &video_ram);
485         }
486
487         /*
488          * Some machines don't have the possibility of ever
489          * possessing lp0, lp1 or lp2
490          */
491         if (mdesc->reserve_lp0)
492                 request_resource(&ioport_resource, &lp0);
493         if (mdesc->reserve_lp1)
494                 request_resource(&ioport_resource, &lp1);
495         if (mdesc->reserve_lp2)
496                 request_resource(&ioport_resource, &lp2);
497 }
498
499 /*
500  *  Tag parsing.
501  *
502  * This is the new way of passing data to the kernel at boot time.  Rather
503  * than passing a fixed inflexible structure to the kernel, we pass a list
504  * of variable-sized tags to the kernel.  The first tag must be a ATAG_CORE
505  * tag for the list to be recognised (to distinguish the tagged list from
506  * a param_struct).  The list is terminated with a zero-length tag (this tag
507  * is not parsed in any way).
508  */
509 static int __init parse_tag_core(const struct tag *tag)
510 {
511         if (tag->hdr.size > 2) {
512                 if ((tag->u.core.flags & 1) == 0)
513                         root_mountflags &= ~MS_RDONLY;
514                 ROOT_DEV = old_decode_dev(tag->u.core.rootdev);
515         }
516         return 0;
517 }
518
519 __tagtable(ATAG_CORE, parse_tag_core);
520
521 static int __init parse_tag_mem32(const struct tag *tag)
522 {
523         if (meminfo.nr_banks >= NR_BANKS) {
524                 printk(KERN_WARNING
525                        "Ignoring memory bank 0x%08x size %dKB\n",
526                         tag->u.mem.start, tag->u.mem.size / 1024);
527                 return -EINVAL;
528         }
529         meminfo.bank[meminfo.nr_banks].start = tag->u.mem.start;
530         meminfo.bank[meminfo.nr_banks].size  = tag->u.mem.size;
531         meminfo.bank[meminfo.nr_banks].node  = PHYS_TO_NID(tag->u.mem.start);
532         meminfo.nr_banks += 1;
533
534         return 0;
535 }
536
537 __tagtable(ATAG_MEM, parse_tag_mem32);
538
539 #if defined(CONFIG_VGA_CONSOLE) || defined(CONFIG_DUMMY_CONSOLE)
540 struct screen_info screen_info = {
541  .orig_video_lines      = 30,
542  .orig_video_cols       = 80,
543  .orig_video_mode       = 0,
544  .orig_video_ega_bx     = 0,
545  .orig_video_isVGA      = 1,
546  .orig_video_points     = 8
547 };
548
549 static int __init parse_tag_videotext(const struct tag *tag)
550 {
551         screen_info.orig_x            = tag->u.videotext.x;
552         screen_info.orig_y            = tag->u.videotext.y;
553         screen_info.orig_video_page   = tag->u.videotext.video_page;
554         screen_info.orig_video_mode   = tag->u.videotext.video_mode;
555         screen_info.orig_video_cols   = tag->u.videotext.video_cols;
556         screen_info.orig_video_ega_bx = tag->u.videotext.video_ega_bx;
557         screen_info.orig_video_lines  = tag->u.videotext.video_lines;
558         screen_info.orig_video_isVGA  = tag->u.videotext.video_isvga;
559         screen_info.orig_video_points = tag->u.videotext.video_points;
560         return 0;
561 }
562
563 __tagtable(ATAG_VIDEOTEXT, parse_tag_videotext);
564 #endif
565
566 static int __init parse_tag_ramdisk(const struct tag *tag)
567 {
568         setup_ramdisk((tag->u.ramdisk.flags & 1) == 0,
569                       (tag->u.ramdisk.flags & 2) == 0,
570                       tag->u.ramdisk.start, tag->u.ramdisk.size);
571         return 0;
572 }
573
574 __tagtable(ATAG_RAMDISK, parse_tag_ramdisk);
575
576 static int __init parse_tag_initrd(const struct tag *tag)
577 {
578         printk(KERN_WARNING "ATAG_INITRD is deprecated; "
579                 "please update your bootloader.\n");
580         phys_initrd_start = __virt_to_phys(tag->u.initrd.start);
581         phys_initrd_size = tag->u.initrd.size;
582         return 0;
583 }
584
585 __tagtable(ATAG_INITRD, parse_tag_initrd);
586
587 static int __init parse_tag_initrd2(const struct tag *tag)
588 {
589         phys_initrd_start = tag->u.initrd.start;
590         phys_initrd_size = tag->u.initrd.size;
591         return 0;
592 }
593
594 __tagtable(ATAG_INITRD2, parse_tag_initrd2);
595
596 static int __init parse_tag_serialnr(const struct tag *tag)
597 {
598         system_serial_low = tag->u.serialnr.low;
599         system_serial_high = tag->u.serialnr.high;
600         return 0;
601 }
602
603 __tagtable(ATAG_SERIAL, parse_tag_serialnr);
604
605 static int __init parse_tag_revision(const struct tag *tag)
606 {
607         system_rev = tag->u.revision.rev;
608         return 0;
609 }
610
611 __tagtable(ATAG_REVISION, parse_tag_revision);
612
613 static int __init parse_tag_cmdline(const struct tag *tag)
614 {
615         strlcpy(default_command_line, tag->u.cmdline.cmdline, COMMAND_LINE_SIZE);
616         return 0;
617 }
618
619 __tagtable(ATAG_CMDLINE, parse_tag_cmdline);
620
621 /*
622  * Scan the tag table for this tag, and call its parse function.
623  * The tag table is built by the linker from all the __tagtable
624  * declarations.
625  */
626 static int __init parse_tag(const struct tag *tag)
627 {
628         extern struct tagtable __tagtable_begin, __tagtable_end;
629         struct tagtable *t;
630
631         for (t = &__tagtable_begin; t < &__tagtable_end; t++)
632                 if (tag->hdr.tag == t->tag) {
633                         t->parse(tag);
634                         break;
635                 }
636
637         return t < &__tagtable_end;
638 }
639
640 /*
641  * Parse all tags in the list, checking both the global and architecture
642  * specific tag tables.
643  */
644 static void __init parse_tags(const struct tag *t)
645 {
646         for (; t->hdr.size; t = tag_next(t))
647                 if (!parse_tag(t))
648                         printk(KERN_WARNING
649                                 "Ignoring unrecognised tag 0x%08x\n",
650                                 t->hdr.tag);
651 }
652
653 /*
654  * This holds our defaults.
655  */
656 static struct init_tags {
657         struct tag_header hdr1;
658         struct tag_core   core;
659         struct tag_header hdr2;
660         struct tag_mem32  mem;
661         struct tag_header hdr3;
662 } init_tags __initdata = {
663         { tag_size(tag_core), ATAG_CORE },
664         { 1, PAGE_SIZE, 0xff },
665         { tag_size(tag_mem32), ATAG_MEM },
666         { MEM_SIZE, PHYS_OFFSET },
667         { 0, ATAG_NONE }
668 };
669
670 static void (*init_machine)(void) __initdata;
671
672 static int __init customize_machine(void)
673 {
674         /* customizes platform devices, or adds new ones */
675         if (init_machine)
676                 init_machine();
677         return 0;
678 }
679 arch_initcall(customize_machine);
680
681 void __init setup_arch(char **cmdline_p)
682 {
683         struct tag *tags = (struct tag *)&init_tags;
684         struct machine_desc *mdesc;
685         char *from = default_command_line;
686
687         setup_processor();
688         mdesc = setup_machine(machine_arch_type);
689         machine_name = mdesc->name;
690
691         if (mdesc->soft_reboot)
692                 reboot_setup("s");
693
694         if (mdesc->param_offset)
695                 tags = phys_to_virt(mdesc->param_offset);
696
697         /*
698          * If we have the old style parameters, convert them to
699          * a tag list.
700          */
701         if (tags->hdr.tag != ATAG_CORE)
702                 convert_to_tag_list(tags);
703         if (tags->hdr.tag != ATAG_CORE)
704                 tags = (struct tag *)&init_tags;
705
706         if (mdesc->fixup)
707                 mdesc->fixup(mdesc, tags, &from, &meminfo);
708
709         if (tags->hdr.tag == ATAG_CORE) {
710                 if (meminfo.nr_banks != 0)
711                         squash_mem_tags(tags);
712                 parse_tags(tags);
713         }
714
715         init_mm.start_code = (unsigned long) &_text;
716         init_mm.end_code   = (unsigned long) &_etext;
717         init_mm.end_data   = (unsigned long) &_edata;
718         init_mm.brk        = (unsigned long) &_end;
719
720         memcpy(saved_command_line, from, COMMAND_LINE_SIZE);
721         saved_command_line[COMMAND_LINE_SIZE-1] = '\0';
722         parse_cmdline(cmdline_p, from);
723         bootmem_init(&meminfo);
724         paging_init(&meminfo, mdesc);
725         request_standard_resources(&meminfo, mdesc);
726
727         /*
728          * Set up various architecture-specific pointers
729          */
730         init_arch_irq = mdesc->init_irq;
731         init_arch_time = mdesc->init_time;
732         init_machine = mdesc->init_machine;
733
734 #ifdef CONFIG_VT
735 #if defined(CONFIG_VGA_CONSOLE)
736         conswitchp = &vga_con;
737 #elif defined(CONFIG_DUMMY_CONSOLE)
738         conswitchp = &dummy_con;
739 #endif
740 #endif
741 }
742
743 static struct cpu cpu[1];
744
745 static int __init topology_init(void)
746 {
747         return register_cpu(cpu, 0, NULL);
748 }
749
750 subsys_initcall(topology_init);
751
752 static const char *hwcap_str[] = {
753         "swp",
754         "half",
755         "thumb",
756         "26bit",
757         "fastmult",
758         "fpa",
759         "vfp",
760         "edsp",
761         NULL
762 };
763
764 static void
765 c_show_cache(struct seq_file *m, const char *type, unsigned int cache)
766 {
767         unsigned int mult = 2 + (CACHE_M(cache) ? 1 : 0);
768
769         seq_printf(m, "%s size\t\t: %d\n"
770                       "%s assoc\t\t: %d\n"
771                       "%s line length\t: %d\n"
772                       "%s sets\t\t: %d\n",
773                 type, mult << (8 + CACHE_SIZE(cache)),
774                 type, (mult << CACHE_ASSOC(cache)) >> 1,
775                 type, 8 << CACHE_LINE(cache),
776                 type, 1 << (6 + CACHE_SIZE(cache) - CACHE_ASSOC(cache) -
777                             CACHE_LINE(cache)));
778 }
779
780 static int c_show(struct seq_file *m, void *v)
781 {
782         int i;
783
784         seq_printf(m, "Processor\t: %s rev %d (%s)\n",
785                    cpu_name, (int)processor_id & 15, elf_platform);
786
787         seq_printf(m, "BogoMIPS\t: %lu.%02lu\n",
788                    loops_per_jiffy / (500000/HZ),
789                    (loops_per_jiffy / (5000/HZ)) % 100);
790
791         /* dump out the processor features */
792         seq_puts(m, "Features\t: ");
793
794         for (i = 0; hwcap_str[i]; i++)
795                 if (elf_hwcap & (1 << i))
796                         seq_printf(m, "%s ", hwcap_str[i]);
797
798         seq_printf(m, "\nCPU implementer\t: 0x%02x\n", processor_id >> 24);
799         seq_printf(m, "CPU architecture: %s\n", proc_arch[cpu_architecture()]);
800
801         if ((processor_id & 0x0000f000) == 0x00000000) {
802                 /* pre-ARM7 */
803                 seq_printf(m, "CPU part\t\t: %07x\n", processor_id >> 4);
804         } else {
805                 if ((processor_id & 0x0000f000) == 0x00007000) {
806                         /* ARM7 */
807                         seq_printf(m, "CPU variant\t: 0x%02x\n",
808                                    (processor_id >> 16) & 127);
809                 } else {
810                         /* post-ARM7 */
811                         seq_printf(m, "CPU variant\t: 0x%x\n",
812                                    (processor_id >> 20) & 15);
813                 }
814                 seq_printf(m, "CPU part\t: 0x%03x\n",
815                            (processor_id >> 4) & 0xfff);
816         }
817         seq_printf(m, "CPU revision\t: %d\n", processor_id & 15);
818
819         {
820                 unsigned int cache_info = read_cpuid(CPUID_CACHETYPE);
821                 if (cache_info != processor_id) {
822                         seq_printf(m, "Cache type\t: %s\n"
823                                       "Cache clean\t: %s\n"
824                                       "Cache lockdown\t: %s\n"
825                                       "Cache format\t: %s\n",
826                                    cache_types[CACHE_TYPE(cache_info)],
827                                    cache_clean[CACHE_TYPE(cache_info)],
828                                    cache_lockdown[CACHE_TYPE(cache_info)],
829                                    CACHE_S(cache_info) ? "Harvard" : "Unified");
830
831                         if (CACHE_S(cache_info)) {
832                                 c_show_cache(m, "I", CACHE_ISIZE(cache_info));
833                                 c_show_cache(m, "D", CACHE_DSIZE(cache_info));
834                         } else {
835                                 c_show_cache(m, "Cache", CACHE_ISIZE(cache_info));
836                         }
837                 }
838         }
839
840         seq_puts(m, "\n");
841
842         seq_printf(m, "Hardware\t: %s\n", machine_name);
843         seq_printf(m, "Revision\t: %04x\n", system_rev);
844         seq_printf(m, "Serial\t\t: %08x%08x\n",
845                    system_serial_high, system_serial_low);
846
847         return 0;
848 }
849
850 static void *c_start(struct seq_file *m, loff_t *pos)
851 {
852         return *pos < 1 ? (void *)1 : NULL;
853 }
854
855 static void *c_next(struct seq_file *m, void *v, loff_t *pos)
856 {
857         ++*pos;
858         return NULL;
859 }
860
861 static void c_stop(struct seq_file *m, void *v)
862 {
863 }
864
865 struct seq_operations cpuinfo_op = {
866         .start  = c_start,
867         .next   = c_next,
868         .stop   = c_stop,
869         .show   = c_show
870 };