diff options
Diffstat (limited to 'arch/arm/kernel')
-rw-r--r-- | arch/arm/kernel/Makefile | 1 | ||||
-rw-r--r-- | arch/arm/kernel/calls.S | 1 | ||||
-rw-r--r-- | arch/arm/kernel/crunch.c | 1 | ||||
-rw-r--r-- | arch/arm/kernel/ecard.c | 2 | ||||
-rw-r--r-- | arch/arm/kernel/machine_kexec.c | 78 | ||||
-rw-r--r-- | arch/arm/kernel/relocate_kernel.S | 74 | ||||
-rw-r--r-- | arch/arm/kernel/setup.c | 3 | ||||
-rw-r--r-- | arch/arm/kernel/time.c | 4 |
8 files changed, 162 insertions, 2 deletions
diff --git a/arch/arm/kernel/Makefile b/arch/arm/kernel/Makefile index ab06a86e85d5..d5002889773e 100644 --- a/arch/arm/kernel/Makefile +++ b/arch/arm/kernel/Makefile | |||
@@ -19,6 +19,7 @@ obj-$(CONFIG_ARTHUR) += arthur.o | |||
19 | obj-$(CONFIG_ISA_DMA) += dma-isa.o | 19 | obj-$(CONFIG_ISA_DMA) += dma-isa.o |
20 | obj-$(CONFIG_PCI) += bios32.o isa.o | 20 | obj-$(CONFIG_PCI) += bios32.o isa.o |
21 | obj-$(CONFIG_SMP) += smp.o | 21 | obj-$(CONFIG_SMP) += smp.o |
22 | obj-$(CONFIG_KEXEC) += machine_kexec.o relocate_kernel.o | ||
22 | obj-$(CONFIG_OABI_COMPAT) += sys_oabi-compat.o | 23 | obj-$(CONFIG_OABI_COMPAT) += sys_oabi-compat.o |
23 | 24 | ||
24 | obj-$(CONFIG_CRUNCH) += crunch.o crunch-bits.o | 25 | obj-$(CONFIG_CRUNCH) += crunch.o crunch-bits.o |
diff --git a/arch/arm/kernel/calls.S b/arch/arm/kernel/calls.S index f7598cbc7ec5..ae89cdd82b16 100644 --- a/arch/arm/kernel/calls.S +++ b/arch/arm/kernel/calls.S | |||
@@ -356,6 +356,7 @@ | |||
356 | CALL(sys_move_pages) | 356 | CALL(sys_move_pages) |
357 | /* 345 */ CALL(sys_getcpu) | 357 | /* 345 */ CALL(sys_getcpu) |
358 | CALL(sys_ni_syscall) /* eventually epoll_pwait */ | 358 | CALL(sys_ni_syscall) /* eventually epoll_pwait */ |
359 | CALL(sys_kexec_load) | ||
359 | #ifndef syscalls_counted | 360 | #ifndef syscalls_counted |
360 | .equ syscalls_padding, ((NR_syscalls + 3) & ~3) - NR_syscalls | 361 | .equ syscalls_padding, ((NR_syscalls + 3) & ~3) - NR_syscalls |
361 | #define syscalls_counted | 362 | #define syscalls_counted |
diff --git a/arch/arm/kernel/crunch.c b/arch/arm/kernel/crunch.c index cec83783206e..627d79414c9d 100644 --- a/arch/arm/kernel/crunch.c +++ b/arch/arm/kernel/crunch.c | |||
@@ -75,6 +75,7 @@ static struct notifier_block crunch_notifier_block = { | |||
75 | static int __init crunch_init(void) | 75 | static int __init crunch_init(void) |
76 | { | 76 | { |
77 | thread_register_notifier(&crunch_notifier_block); | 77 | thread_register_notifier(&crunch_notifier_block); |
78 | elf_hwcap |= HWCAP_CRUNCH; | ||
78 | 79 | ||
79 | return 0; | 80 | return 0; |
80 | } | 81 | } |
diff --git a/arch/arm/kernel/ecard.c b/arch/arm/kernel/ecard.c index 71257e3d513f..f1c0fb974177 100644 --- a/arch/arm/kernel/ecard.c +++ b/arch/arm/kernel/ecard.c | |||
@@ -1009,7 +1009,7 @@ ecard_probe(int slot, card_type_t type) | |||
1009 | ec->fiqmask = 4; | 1009 | ec->fiqmask = 4; |
1010 | } | 1010 | } |
1011 | 1011 | ||
1012 | for (i = 0; i < sizeof(blacklist) / sizeof(*blacklist); i++) | 1012 | for (i = 0; i < ARRAY_SIZE(blacklist); i++) |
1013 | if (blacklist[i].manufacturer == ec->cid.manufacturer && | 1013 | if (blacklist[i].manufacturer == ec->cid.manufacturer && |
1014 | blacklist[i].product == ec->cid.product) { | 1014 | blacklist[i].product == ec->cid.product) { |
1015 | ec->card_desc = blacklist[i].type; | 1015 | ec->card_desc = blacklist[i].type; |
diff --git a/arch/arm/kernel/machine_kexec.c b/arch/arm/kernel/machine_kexec.c new file mode 100644 index 000000000000..863c66454f2b --- /dev/null +++ b/arch/arm/kernel/machine_kexec.c | |||
@@ -0,0 +1,78 @@ | |||
1 | /* | ||
2 | * machine_kexec.c - handle transition of Linux booting another kernel | ||
3 | */ | ||
4 | |||
5 | #include <linux/mm.h> | ||
6 | #include <linux/kexec.h> | ||
7 | #include <linux/delay.h> | ||
8 | #include <linux/reboot.h> | ||
9 | #include <asm/pgtable.h> | ||
10 | #include <asm/pgalloc.h> | ||
11 | #include <asm/mmu_context.h> | ||
12 | #include <asm/io.h> | ||
13 | #include <asm/cacheflush.h> | ||
14 | #include <asm/mach-types.h> | ||
15 | |||
16 | const extern unsigned char relocate_new_kernel[]; | ||
17 | const extern unsigned int relocate_new_kernel_size; | ||
18 | |||
19 | extern void setup_mm_for_reboot(char mode); | ||
20 | |||
21 | extern unsigned long kexec_start_address; | ||
22 | extern unsigned long kexec_indirection_page; | ||
23 | extern unsigned long kexec_mach_type; | ||
24 | |||
25 | /* | ||
26 | * Provide a dummy crash_notes definition while crash dump arrives to arm. | ||
27 | * This prevents breakage of crash_notes attribute in kernel/ksysfs.c. | ||
28 | */ | ||
29 | |||
30 | int machine_kexec_prepare(struct kimage *image) | ||
31 | { | ||
32 | return 0; | ||
33 | } | ||
34 | |||
35 | void machine_kexec_cleanup(struct kimage *image) | ||
36 | { | ||
37 | } | ||
38 | |||
39 | void machine_shutdown(void) | ||
40 | { | ||
41 | } | ||
42 | |||
43 | void machine_crash_shutdown(struct pt_regs *regs) | ||
44 | { | ||
45 | } | ||
46 | |||
47 | void machine_kexec(struct kimage *image) | ||
48 | { | ||
49 | unsigned long page_list; | ||
50 | unsigned long reboot_code_buffer_phys; | ||
51 | void *reboot_code_buffer; | ||
52 | |||
53 | |||
54 | page_list = image->head & PAGE_MASK; | ||
55 | |||
56 | /* we need both effective and real address here */ | ||
57 | reboot_code_buffer_phys = | ||
58 | page_to_pfn(image->control_code_page) << PAGE_SHIFT; | ||
59 | reboot_code_buffer = page_address(image->control_code_page); | ||
60 | |||
61 | /* Prepare parameters for reboot_code_buffer*/ | ||
62 | kexec_start_address = image->start; | ||
63 | kexec_indirection_page = page_list; | ||
64 | kexec_mach_type = machine_arch_type; | ||
65 | |||
66 | /* copy our kernel relocation code to the control code page */ | ||
67 | memcpy(reboot_code_buffer, | ||
68 | relocate_new_kernel, relocate_new_kernel_size); | ||
69 | |||
70 | |||
71 | flush_icache_range((unsigned long) reboot_code_buffer, | ||
72 | (unsigned long) reboot_code_buffer + KEXEC_CONTROL_CODE_SIZE); | ||
73 | printk(KERN_INFO "Bye!\n"); | ||
74 | |||
75 | cpu_proc_fin(); | ||
76 | setup_mm_for_reboot(0); /* mode is not used, so just pass 0*/ | ||
77 | cpu_reset(reboot_code_buffer_phys); | ||
78 | } | ||
diff --git a/arch/arm/kernel/relocate_kernel.S b/arch/arm/kernel/relocate_kernel.S new file mode 100644 index 000000000000..7baadae7cb27 --- /dev/null +++ b/arch/arm/kernel/relocate_kernel.S | |||
@@ -0,0 +1,74 @@ | |||
1 | /* | ||
2 | * relocate_kernel.S - put the kernel image in place to boot | ||
3 | */ | ||
4 | |||
5 | #include <asm/kexec.h> | ||
6 | |||
7 | .globl relocate_new_kernel | ||
8 | relocate_new_kernel: | ||
9 | |||
10 | ldr r0,kexec_indirection_page | ||
11 | ldr r1,kexec_start_address | ||
12 | |||
13 | |||
14 | 0: /* top, read another word for the indirection page */ | ||
15 | ldr r3, [r0],#4 | ||
16 | |||
17 | /* Is it a destination page. Put destination address to r4 */ | ||
18 | tst r3,#1,0 | ||
19 | beq 1f | ||
20 | bic r4,r3,#1 | ||
21 | b 0b | ||
22 | 1: | ||
23 | /* Is it an indirection page */ | ||
24 | tst r3,#2,0 | ||
25 | beq 1f | ||
26 | bic r0,r3,#2 | ||
27 | b 0b | ||
28 | 1: | ||
29 | |||
30 | /* are we done ? */ | ||
31 | tst r3,#4,0 | ||
32 | beq 1f | ||
33 | b 2f | ||
34 | |||
35 | 1: | ||
36 | /* is it source ? */ | ||
37 | tst r3,#8,0 | ||
38 | beq 0b | ||
39 | bic r3,r3,#8 | ||
40 | mov r6,#1024 | ||
41 | 9: | ||
42 | ldr r5,[r3],#4 | ||
43 | str r5,[r4],#4 | ||
44 | subs r6,r6,#1 | ||
45 | bne 9b | ||
46 | b 0b | ||
47 | |||
48 | 2: | ||
49 | /* Jump to relocated kernel */ | ||
50 | mov lr,r1 | ||
51 | mov r0,#0 | ||
52 | ldr r1,kexec_mach_type | ||
53 | mov r2,#0 | ||
54 | mov pc,lr | ||
55 | |||
56 | .globl kexec_start_address | ||
57 | kexec_start_address: | ||
58 | .long 0x0 | ||
59 | |||
60 | .globl kexec_indirection_page | ||
61 | kexec_indirection_page: | ||
62 | .long 0x0 | ||
63 | |||
64 | .globl kexec_mach_type | ||
65 | kexec_mach_type: | ||
66 | .long 0x0 | ||
67 | |||
68 | relocate_new_kernel_end: | ||
69 | |||
70 | .globl relocate_new_kernel_size | ||
71 | relocate_new_kernel_size: | ||
72 | .long relocate_new_kernel_end - relocate_new_kernel | ||
73 | |||
74 | |||
diff --git a/arch/arm/kernel/setup.c b/arch/arm/kernel/setup.c index bbab134cd82d..243aea458057 100644 --- a/arch/arm/kernel/setup.c +++ b/arch/arm/kernel/setup.c | |||
@@ -88,6 +88,9 @@ struct cpu_user_fns cpu_user; | |||
88 | #ifdef MULTI_CACHE | 88 | #ifdef MULTI_CACHE |
89 | struct cpu_cache_fns cpu_cache; | 89 | struct cpu_cache_fns cpu_cache; |
90 | #endif | 90 | #endif |
91 | #ifdef CONFIG_OUTER_CACHE | ||
92 | struct outer_cache_fns outer_cache; | ||
93 | #endif | ||
91 | 94 | ||
92 | struct stack { | 95 | struct stack { |
93 | u32 irq[3]; | 96 | u32 irq[3]; |
diff --git a/arch/arm/kernel/time.c b/arch/arm/kernel/time.c index 3c8cdcfe8d4a..3825acd6687d 100644 --- a/arch/arm/kernel/time.c +++ b/arch/arm/kernel/time.c | |||
@@ -40,12 +40,14 @@ | |||
40 | */ | 40 | */ |
41 | struct sys_timer *system_timer; | 41 | struct sys_timer *system_timer; |
42 | 42 | ||
43 | #if defined(CONFIG_RTC_DRV_CMOS) || defined(CONFIG_RTC_DRV_CMOS_MODULE) | ||
43 | /* this needs a better home */ | 44 | /* this needs a better home */ |
44 | DEFINE_SPINLOCK(rtc_lock); | 45 | DEFINE_SPINLOCK(rtc_lock); |
45 | 46 | ||
46 | #ifdef CONFIG_SA1100_RTC_MODULE | 47 | #ifdef CONFIG_RTC_DRV_CMOS_MODULE |
47 | EXPORT_SYMBOL(rtc_lock); | 48 | EXPORT_SYMBOL(rtc_lock); |
48 | #endif | 49 | #endif |
50 | #endif /* pc-style 'CMOS' RTC support */ | ||
49 | 51 | ||
50 | /* change this if you have some constant time drift */ | 52 | /* change this if you have some constant time drift */ |
51 | #define USECS_PER_JIFFY (1000000/HZ) | 53 | #define USECS_PER_JIFFY (1000000/HZ) |