aboutsummaryrefslogtreecommitdiffstats
path: root/arch/xtensa/kernel
diff options
context:
space:
mode:
Diffstat (limited to 'arch/xtensa/kernel')
-rw-r--r--arch/xtensa/kernel/irq.c10
-rw-r--r--arch/xtensa/kernel/setup.c143
2 files changed, 128 insertions, 25 deletions
diff --git a/arch/xtensa/kernel/irq.c b/arch/xtensa/kernel/irq.c
index e90d78211195..6f4f9749cff7 100644
--- a/arch/xtensa/kernel/irq.c
+++ b/arch/xtensa/kernel/irq.c
@@ -19,6 +19,7 @@
19#include <linux/irq.h> 19#include <linux/irq.h>
20#include <linux/kernel_stat.h> 20#include <linux/kernel_stat.h>
21#include <linux/irqdomain.h> 21#include <linux/irqdomain.h>
22#include <linux/of.h>
22 23
23#include <asm/uaccess.h> 24#include <asm/uaccess.h>
24#include <asm/platform.h> 25#include <asm/platform.h>
@@ -199,8 +200,17 @@ void __init init_IRQ(void)
199 cached_irq_mask = 0; 200 cached_irq_mask = 0;
200 set_sr(~0, intclear); 201 set_sr(~0, intclear);
201 202
203#ifdef CONFIG_OF
204 /* The interrupt controller device node is mandatory */
205 intc = of_find_compatible_node(NULL, NULL, "xtensa,pic");
206 BUG_ON(!intc);
207
208 root_domain = irq_domain_add_linear(intc, NR_IRQS,
209 &xtensa_irq_domain_ops, NULL);
210#else
202 root_domain = irq_domain_add_legacy(intc, NR_IRQS, 0, 0, 211 root_domain = irq_domain_add_legacy(intc, NR_IRQS, 0, 0,
203 &xtensa_irq_domain_ops, NULL); 212 &xtensa_irq_domain_ops, NULL);
213#endif
204 irq_set_default_host(root_domain); 214 irq_set_default_host(root_domain);
205 215
206 variant_init_irq(); 216 variant_init_irq();
diff --git a/arch/xtensa/kernel/setup.c b/arch/xtensa/kernel/setup.c
index 45217617c60d..64d80e4b0bd4 100644
--- a/arch/xtensa/kernel/setup.c
+++ b/arch/xtensa/kernel/setup.c
@@ -22,6 +22,11 @@
22#include <linux/bootmem.h> 22#include <linux/bootmem.h>
23#include <linux/kernel.h> 23#include <linux/kernel.h>
24 24
25#ifdef CONFIG_OF
26#include <linux/of_fdt.h>
27#include <linux/of_platform.h>
28#endif
29
25#if defined(CONFIG_VGA_CONSOLE) || defined(CONFIG_DUMMY_CONSOLE) 30#if defined(CONFIG_VGA_CONSOLE) || defined(CONFIG_DUMMY_CONSOLE)
26# include <linux/console.h> 31# include <linux/console.h>
27#endif 32#endif
@@ -65,6 +70,11 @@ int initrd_is_mapped = 0;
65extern int initrd_below_start_ok; 70extern int initrd_below_start_ok;
66#endif 71#endif
67 72
73#ifdef CONFIG_OF
74extern u32 __dtb_start[];
75void *dtb_start = __dtb_start;
76#endif
77
68unsigned char aux_device_present; 78unsigned char aux_device_present;
69extern unsigned long loops_per_jiffy; 79extern unsigned long loops_per_jiffy;
70 80
@@ -84,6 +94,8 @@ extern void init_mmu(void);
84static inline void init_mmu(void) { } 94static inline void init_mmu(void) { }
85#endif 95#endif
86 96
97extern int mem_reserve(unsigned long, unsigned long, int);
98extern void bootmem_init(void);
87extern void zones_init(void); 99extern void zones_init(void);
88 100
89/* 101/*
@@ -105,28 +117,33 @@ typedef struct tagtable {
105 117
106/* parse current tag */ 118/* parse current tag */
107 119
108static int __init parse_tag_mem(const bp_tag_t *tag) 120static int __init add_sysmem_bank(unsigned long type, unsigned long start,
121 unsigned long end)
109{ 122{
110 meminfo_t *mi = (meminfo_t*)(tag->data);
111
112 if (mi->type != MEMORY_TYPE_CONVENTIONAL)
113 return -1;
114
115 if (sysmem.nr_banks >= SYSMEM_BANKS_MAX) { 123 if (sysmem.nr_banks >= SYSMEM_BANKS_MAX) {
116 printk(KERN_WARNING 124 printk(KERN_WARNING
117 "Ignoring memory bank 0x%08lx size %ldKB\n", 125 "Ignoring memory bank 0x%08lx size %ldKB\n",
118 (unsigned long)mi->start, 126 start, end - start);
119 (unsigned long)mi->end - (unsigned long)mi->start);
120 return -EINVAL; 127 return -EINVAL;
121 } 128 }
122 sysmem.bank[sysmem.nr_banks].type = mi->type; 129 sysmem.bank[sysmem.nr_banks].type = type;
123 sysmem.bank[sysmem.nr_banks].start = PAGE_ALIGN(mi->start); 130 sysmem.bank[sysmem.nr_banks].start = PAGE_ALIGN(start);
124 sysmem.bank[sysmem.nr_banks].end = mi->end & PAGE_MASK; 131 sysmem.bank[sysmem.nr_banks].end = end & PAGE_MASK;
125 sysmem.nr_banks++; 132 sysmem.nr_banks++;
126 133
127 return 0; 134 return 0;
128} 135}
129 136
137static int __init parse_tag_mem(const bp_tag_t *tag)
138{
139 meminfo_t *mi = (meminfo_t *)(tag->data);
140
141 if (mi->type != MEMORY_TYPE_CONVENTIONAL)
142 return -1;
143
144 return add_sysmem_bank(mi->type, mi->start, mi->end);
145}
146
130__tagtable(BP_TAG_MEMORY, parse_tag_mem); 147__tagtable(BP_TAG_MEMORY, parse_tag_mem);
131 148
132#ifdef CONFIG_BLK_DEV_INITRD 149#ifdef CONFIG_BLK_DEV_INITRD
@@ -143,12 +160,31 @@ static int __init parse_tag_initrd(const bp_tag_t* tag)
143 160
144__tagtable(BP_TAG_INITRD, parse_tag_initrd); 161__tagtable(BP_TAG_INITRD, parse_tag_initrd);
145 162
163#ifdef CONFIG_OF
164
165static int __init parse_tag_fdt(const bp_tag_t *tag)
166{
167 dtb_start = (void *)(tag->data[0]);
168 return 0;
169}
170
171__tagtable(BP_TAG_FDT, parse_tag_fdt);
172
173void __init early_init_dt_setup_initrd_arch(unsigned long start,
174 unsigned long end)
175{
176 initrd_start = (void *)__va(start);
177 initrd_end = (void *)__va(end);
178 initrd_below_start_ok = 1;
179}
180
181#endif /* CONFIG_OF */
182
146#endif /* CONFIG_BLK_DEV_INITRD */ 183#endif /* CONFIG_BLK_DEV_INITRD */
147 184
148static int __init parse_tag_cmdline(const bp_tag_t* tag) 185static int __init parse_tag_cmdline(const bp_tag_t* tag)
149{ 186{
150 strncpy(command_line, (char*)(tag->data), COMMAND_LINE_SIZE); 187 strlcpy(command_line, (char *)(tag->data), COMMAND_LINE_SIZE);
151 command_line[COMMAND_LINE_SIZE - 1] = '\0';
152 return 0; 188 return 0;
153} 189}
154 190
@@ -186,6 +222,58 @@ static int __init parse_bootparam(const bp_tag_t* tag)
186 return 0; 222 return 0;
187} 223}
188 224
225#ifdef CONFIG_OF
226
227void __init early_init_dt_add_memory_arch(u64 base, u64 size)
228{
229 size &= PAGE_MASK;
230 add_sysmem_bank(MEMORY_TYPE_CONVENTIONAL, base, base + size);
231}
232
233void * __init early_init_dt_alloc_memory_arch(u64 size, u64 align)
234{
235 return __alloc_bootmem(size, align, 0);
236}
237
238void __init early_init_devtree(void *params)
239{
240 /* Setup flat device-tree pointer */
241 initial_boot_params = params;
242
243 /* Retrieve various informations from the /chosen node of the
244 * device-tree, including the platform type, initrd location and
245 * size, TCE reserve, and more ...
246 */
247 if (!command_line[0])
248 of_scan_flat_dt(early_init_dt_scan_chosen, command_line);
249
250 /* Scan memory nodes and rebuild MEMBLOCKs */
251 of_scan_flat_dt(early_init_dt_scan_root, NULL);
252 if (sysmem.nr_banks == 0)
253 of_scan_flat_dt(early_init_dt_scan_memory, NULL);
254}
255
256static void __init copy_devtree(void)
257{
258 void *alloc = early_init_dt_alloc_memory_arch(
259 be32_to_cpu(initial_boot_params->totalsize), 0);
260 if (alloc) {
261 memcpy(alloc, initial_boot_params,
262 be32_to_cpu(initial_boot_params->totalsize));
263 initial_boot_params = alloc;
264 }
265}
266
267static int __init xtensa_device_probe(void)
268{
269 of_platform_populate(NULL, NULL, NULL, NULL);
270 return 0;
271}
272
273device_initcall(xtensa_device_probe);
274
275#endif /* CONFIG_OF */
276
189/* 277/*
190 * Initialize architecture. (Early stage) 278 * Initialize architecture. (Early stage)
191 */ 279 */
@@ -194,14 +282,14 @@ void __init init_arch(bp_tag_t *bp_start)
194{ 282{
195 sysmem.nr_banks = 0; 283 sysmem.nr_banks = 0;
196 284
197#ifdef CONFIG_CMDLINE_BOOL
198 strcpy(command_line, default_command_line);
199#endif
200
201 /* Parse boot parameters */ 285 /* Parse boot parameters */
202 286
203 if (bp_start) 287 if (bp_start)
204 parse_bootparam(bp_start); 288 parse_bootparam(bp_start);
289
290#ifdef CONFIG_OF
291 early_init_devtree(dtb_start);
292#endif
205 293
206 if (sysmem.nr_banks == 0) { 294 if (sysmem.nr_banks == 0) {
207 sysmem.nr_banks = 1; 295 sysmem.nr_banks = 1;
@@ -210,6 +298,11 @@ void __init init_arch(bp_tag_t *bp_start)
210 + PLATFORM_DEFAULT_MEM_SIZE; 298 + PLATFORM_DEFAULT_MEM_SIZE;
211 } 299 }
212 300
301#ifdef CONFIG_CMDLINE_BOOL
302 if (!command_line[0])
303 strlcpy(command_line, default_command_line, COMMAND_LINE_SIZE);
304#endif
305
213 /* Early hook for platforms */ 306 /* Early hook for platforms */
214 307
215 platform_init(bp_start); 308 platform_init(bp_start);
@@ -355,11 +448,7 @@ void __init check_s32c1i(void)
355 448
356void __init setup_arch(char **cmdline_p) 449void __init setup_arch(char **cmdline_p)
357{ 450{
358 extern int mem_reserve(unsigned long, unsigned long, int); 451 strlcpy(boot_command_line, command_line, COMMAND_LINE_SIZE);
359 extern void bootmem_init(void);
360
361 memcpy(boot_command_line, command_line, COMMAND_LINE_SIZE);
362 boot_command_line[COMMAND_LINE_SIZE-1] = '\0';
363 *cmdline_p = command_line; 452 *cmdline_p = command_line;
364 453
365 check_s32c1i(); 454 check_s32c1i();
@@ -395,8 +484,12 @@ void __init setup_arch(char **cmdline_p)
395 484
396 bootmem_init(); 485 bootmem_init();
397 486
398 platform_setup(cmdline_p); 487#ifdef CONFIG_OF
488 copy_devtree();
489 unflatten_device_tree();
490#endif
399 491
492 platform_setup(cmdline_p);
400 493
401 paging_init(); 494 paging_init();
402 zones_init(); 495 zones_init();