f3c27d33a8136ec980e62e700e352892cc101276
[openembedded.git] /
1 From: Bill Gatliff <bgat@billgatliff.com>
2 Date: Thu, 31 May 2007 21:02:22 +0000 (+0100)
3 Subject: [ARM] 4423/1: add ATAGS support
4 X-Git-Tag: v2.6.23-rc1~1101^2^7~5
5 X-Git-Url: http://git.kernel.org/?p=linux%2Fkernel%2Fgit%2Ftorvalds%2Flinux-2.6.git;a=commitdiff_plain;h=9d20fdd58e74d4d26dc5216efaaa0f800c23dd3a
6
7 [ARM] 4423/1: add ATAGS support
8
9 Examines the ATAGS pointer (r2) at boot, and interprets
10 a nonzero value as a reference to an ATAGS structure. A
11 suitable ATAGS structure replaces the kernel's command line.
12
13 Signed-off-by: Bill Gatliff <bgat@billgatliff.com>
14 Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
15 ---
16
17 diff --git a/arch/arm/kernel/head-common.S b/arch/arm/kernel/head-common.S
18 index a52da0d..024a9cf 100644
19 --- a/arch/arm/kernel/head-common.S
20 +++ b/arch/arm/kernel/head-common.S
21 @@ -20,7 +20,8 @@ __switch_data:
22         .long   _end                            @ r7
23         .long   processor_id                    @ r4
24         .long   __machine_arch_type             @ r5
25 -       .long   cr_alignment                    @ r6
26 +       .long   __atags_pointer                 @ r6
27 +       .long   cr_alignment                    @ r7
28         .long   init_thread_union + THREAD_START_SP @ sp
29  
30  /*
31 @@ -29,6 +30,7 @@ __switch_data:
32   *
33   *  r0  = cp#15 control register
34   *  r1  = machine ID
35 + *  r2  = atags pointer
36   *  r9  = processor ID
37   */
38         .type   __mmap_switched, %function
39 @@ -47,11 +49,12 @@ __mmap_switched:
40         strcc   fp, [r6],#4
41         bcc     1b
42  
43 -       ldmia   r3, {r4, r5, r6, sp}
44 +       ldmia   r3, {r4, r5, r6, r7, sp}
45         str     r9, [r4]                        @ Save processor ID
46         str     r1, [r5]                        @ Save machine type
47 +       str     r2, [r6]                        @ Save atags pointer
48         bic     r4, r0, #CR_A                   @ Clear 'A' bit
49 -       stmia   r6, {r0, r4}                    @ Save control register values
50 +       stmia   r7, {r0, r4}                    @ Save control register values
51         b       start_kernel
52  
53  /*
54 @@ -215,3 +218,34 @@ ENTRY(lookup_machine_type)
55         bl      __lookup_machine_type
56         mov     r0, r5
57         ldmfd   sp!, {r4 - r6, pc}
58 +
59 +/* Determine validity of the r2 atags pointer.  The heuristic requires
60 + * that the pointer be aligned, in the first 16k of physical RAM and
61 + * that the ATAG_CORE marker is first and present.  Future revisions
62 + * of this function may be more lenient with the physical address and
63 + * may also be able to move the ATAGS block if necessary.
64 + *
65 + * r8  = machinfo
66 + *
67 + * Returns:
68 + *  r2 either valid atags pointer, or zero
69 + *  r5, r6 corrupted
70 + */
71 +
72 +       .type   __vet_atags, %function
73 +__vet_atags:
74 +       tst     r2, #0x3                        @ aligned?
75 +       bne     1f
76 +
77 +       ldr     r5, [r2, #0]                    @ is first tag ATAG_CORE?
78 +       subs    r5, r5, #ATAG_CORE_SIZE
79 +       bne     1f
80 +       ldr     r5, [r2, #4]
81 +       ldr     r6, =ATAG_CORE
82 +       cmp     r5, r6
83 +       bne     1f
84 +
85 +       mov     pc, lr                          @ atag pointer is ok
86 +
87 +1:     mov     r2, #0
88 +       mov     pc, lr
89 diff --git a/arch/arm/kernel/head.S b/arch/arm/kernel/head.S
90 index 41f98b4..7898cbc 100644
91 --- a/arch/arm/kernel/head.S
92 +++ b/arch/arm/kernel/head.S
93 @@ -29,6 +29,10 @@
94  #define KERNEL_RAM_VADDR       (PAGE_OFFSET + TEXT_OFFSET)
95  #define KERNEL_RAM_PADDR       (PHYS_OFFSET + TEXT_OFFSET)
96  
97 +#define ATAG_CORE 0x54410001
98 +#define ATAG_CORE_SIZE ((2*4 + 3*4) >> 2)
99 +
100 +
101  /*
102   * swapper_pg_dir is the virtual address of the initial page table.
103   * We place the page tables 16K below KERNEL_RAM_VADDR.  Therefore, we must
104 @@ -61,7 +65,7 @@
105   *
106   * This is normally called from the decompressor code.  The requirements
107   * are: MMU = off, D-cache = off, I-cache = dont care, r0 = 0,
108 - * r1 = machine nr.
109 + * r1 = machine nr, r2 = atags pointer.
110   *
111   * This code is mostly position independent, so if you link the kernel at
112   * 0xc0008000, you call this at __pa(0xc0008000).
113 @@ -85,6 +89,7 @@ ENTRY(stext)
114         bl      __lookup_machine_type           @ r5=machinfo
115         movs    r8, r5                          @ invalid machine (r5=0)?
116         beq     __error_a                       @ yes, error 'a'
117 +       bl      __vet_atags
118         bl      __create_page_tables
119  
120         /*
121 diff --git a/arch/arm/kernel/setup.c b/arch/arm/kernel/setup.c
122 index 650eac1..5be2e98 100644
123 --- a/arch/arm/kernel/setup.c
124 +++ b/arch/arm/kernel/setup.c
125 @@ -63,6 +63,8 @@ unsigned int processor_id;
126  unsigned int __machine_arch_type;
127  EXPORT_SYMBOL(__machine_arch_type);
128  
129 +unsigned int __atags_pointer __initdata;
130 +
131  unsigned int system_rev;
132  EXPORT_SYMBOL(system_rev);
133  
134 @@ -780,7 +782,9 @@ void __init setup_arch(char **cmdline_p)
135         if (mdesc->soft_reboot)
136                 reboot_setup("s");
137  
138 -       if (mdesc->boot_params)
139 +       if (__atags_pointer)
140 +               tags = phys_to_virt(__atags_pointer);
141 +       else if (mdesc->boot_params)
142                 tags = phys_to_virt(mdesc->boot_params);
143  
144         /*