diff options
Diffstat (limited to 'arch/arm/kernel')
35 files changed, 495 insertions, 356 deletions
diff --git a/arch/arm/kernel/Makefile b/arch/arm/kernel/Makefile index 8dcbed5016ac..f290ac892a95 100644 --- a/arch/arm/kernel/Makefile +++ b/arch/arm/kernel/Makefile | |||
@@ -47,6 +47,7 @@ endif | |||
47 | obj-$(CONFIG_HAVE_ARM_SCU) += smp_scu.o | 47 | obj-$(CONFIG_HAVE_ARM_SCU) += smp_scu.o |
48 | obj-$(CONFIG_HAVE_ARM_TWD) += smp_twd.o | 48 | obj-$(CONFIG_HAVE_ARM_TWD) += smp_twd.o |
49 | obj-$(CONFIG_ARM_ARCH_TIMER) += arch_timer.o | 49 | obj-$(CONFIG_ARM_ARCH_TIMER) += arch_timer.o |
50 | obj-$(CONFIG_FUNCTION_TRACER) += entry-ftrace.o | ||
50 | obj-$(CONFIG_DYNAMIC_FTRACE) += ftrace.o insn.o | 51 | obj-$(CONFIG_DYNAMIC_FTRACE) += ftrace.o insn.o |
51 | obj-$(CONFIG_FUNCTION_GRAPH_TRACER) += ftrace.o insn.o | 52 | obj-$(CONFIG_FUNCTION_GRAPH_TRACER) += ftrace.o insn.o |
52 | obj-$(CONFIG_JUMP_LABEL) += jump_label.o insn.o patch.o | 53 | obj-$(CONFIG_JUMP_LABEL) += jump_label.o insn.o patch.o |
@@ -67,7 +68,7 @@ test-kprobes-objs += kprobes-test-arm.o | |||
67 | endif | 68 | endif |
68 | obj-$(CONFIG_OABI_COMPAT) += sys_oabi-compat.o | 69 | obj-$(CONFIG_OABI_COMPAT) += sys_oabi-compat.o |
69 | obj-$(CONFIG_ARM_THUMBEE) += thumbee.o | 70 | obj-$(CONFIG_ARM_THUMBEE) += thumbee.o |
70 | obj-$(CONFIG_KGDB) += kgdb.o | 71 | obj-$(CONFIG_KGDB) += kgdb.o patch.o |
71 | obj-$(CONFIG_ARM_UNWIND) += unwind.o | 72 | obj-$(CONFIG_ARM_UNWIND) += unwind.o |
72 | obj-$(CONFIG_HAVE_TCM) += tcm.o | 73 | obj-$(CONFIG_HAVE_TCM) += tcm.o |
73 | obj-$(CONFIG_OF) += devtree.o | 74 | obj-$(CONFIG_OF) += devtree.o |
@@ -84,6 +85,7 @@ obj-$(CONFIG_CPU_PJ4B) += pj4-cp0.o | |||
84 | obj-$(CONFIG_IWMMXT) += iwmmxt.o | 85 | obj-$(CONFIG_IWMMXT) += iwmmxt.o |
85 | obj-$(CONFIG_PERF_EVENTS) += perf_regs.o perf_callchain.o | 86 | obj-$(CONFIG_PERF_EVENTS) += perf_regs.o perf_callchain.o |
86 | obj-$(CONFIG_HW_PERF_EVENTS) += perf_event.o perf_event_cpu.o | 87 | obj-$(CONFIG_HW_PERF_EVENTS) += perf_event.o perf_event_cpu.o |
88 | CFLAGS_pj4-cp0.o := -marm | ||
87 | AFLAGS_iwmmxt.o := -Wa,-mcpu=iwmmxt | 89 | AFLAGS_iwmmxt.o := -Wa,-mcpu=iwmmxt |
88 | obj-$(CONFIG_ARM_CPU_TOPOLOGY) += topology.o | 90 | obj-$(CONFIG_ARM_CPU_TOPOLOGY) += topology.o |
89 | 91 | ||
diff --git a/arch/arm/kernel/atags_compat.c b/arch/arm/kernel/atags_compat.c index 5236ad38f417..05c28b12353c 100644 --- a/arch/arm/kernel/atags_compat.c +++ b/arch/arm/kernel/atags_compat.c | |||
@@ -97,8 +97,7 @@ static void __init build_tag_list(struct param_struct *params, void *taglist) | |||
97 | struct tag *tag = taglist; | 97 | struct tag *tag = taglist; |
98 | 98 | ||
99 | if (params->u1.s.page_size != PAGE_SIZE) { | 99 | if (params->u1.s.page_size != PAGE_SIZE) { |
100 | printk(KERN_WARNING "Warning: bad configuration page, " | 100 | pr_warn("Warning: bad configuration page, trying to continue\n"); |
101 | "trying to continue\n"); | ||
102 | return; | 101 | return; |
103 | } | 102 | } |
104 | 103 | ||
@@ -109,8 +108,7 @@ static void __init build_tag_list(struct param_struct *params, void *taglist) | |||
109 | params->u1.s.nr_pages != 0x04000 && | 108 | params->u1.s.nr_pages != 0x04000 && |
110 | params->u1.s.nr_pages != 0x08000 && | 109 | params->u1.s.nr_pages != 0x08000 && |
111 | params->u1.s.nr_pages != 0x10000) { | 110 | params->u1.s.nr_pages != 0x10000) { |
112 | printk(KERN_WARNING "Warning: bad NeTTrom parameters " | 111 | pr_warn("Warning: bad NeTTrom parameters detected, using defaults\n"); |
113 | "detected, using defaults\n"); | ||
114 | 112 | ||
115 | params->u1.s.nr_pages = 0x1000; /* 16MB */ | 113 | params->u1.s.nr_pages = 0x1000; /* 16MB */ |
116 | params->u1.s.ramdisk_size = 0; | 114 | params->u1.s.ramdisk_size = 0; |
diff --git a/arch/arm/kernel/atags_parse.c b/arch/arm/kernel/atags_parse.c index 528f8af2addb..68c6ae0b9e4c 100644 --- a/arch/arm/kernel/atags_parse.c +++ b/arch/arm/kernel/atags_parse.c | |||
@@ -167,8 +167,7 @@ static void __init parse_tags(const struct tag *t) | |||
167 | { | 167 | { |
168 | for (; t->hdr.size; t = tag_next(t)) | 168 | for (; t->hdr.size; t = tag_next(t)) |
169 | if (!parse_tag(t)) | 169 | if (!parse_tag(t)) |
170 | printk(KERN_WARNING | 170 | pr_warn("Ignoring unrecognised tag 0x%08x\n", |
171 | "Ignoring unrecognised tag 0x%08x\n", | ||
172 | t->hdr.tag); | 171 | t->hdr.tag); |
173 | } | 172 | } |
174 | 173 | ||
@@ -193,7 +192,7 @@ setup_machine_tags(phys_addr_t __atags_pointer, unsigned int machine_nr) | |||
193 | */ | 192 | */ |
194 | for_each_machine_desc(p) | 193 | for_each_machine_desc(p) |
195 | if (machine_nr == p->nr) { | 194 | if (machine_nr == p->nr) { |
196 | printk("Machine: %s\n", p->name); | 195 | pr_info("Machine: %s\n", p->name); |
197 | mdesc = p; | 196 | mdesc = p; |
198 | break; | 197 | break; |
199 | } | 198 | } |
diff --git a/arch/arm/kernel/atags_proc.c b/arch/arm/kernel/atags_proc.c index c7ff8073416f..5a3379055f55 100644 --- a/arch/arm/kernel/atags_proc.c +++ b/arch/arm/kernel/atags_proc.c | |||
@@ -41,7 +41,7 @@ static int __init init_atags_procfs(void) | |||
41 | size_t size; | 41 | size_t size; |
42 | 42 | ||
43 | if (tag->hdr.tag != ATAG_CORE) { | 43 | if (tag->hdr.tag != ATAG_CORE) { |
44 | printk(KERN_INFO "No ATAGs?"); | 44 | pr_info("No ATAGs?"); |
45 | return -EINVAL; | 45 | return -EINVAL; |
46 | } | 46 | } |
47 | 47 | ||
@@ -68,7 +68,7 @@ static int __init init_atags_procfs(void) | |||
68 | 68 | ||
69 | nomem: | 69 | nomem: |
70 | kfree(b); | 70 | kfree(b); |
71 | printk(KERN_ERR "Exporting ATAGs: not enough memory\n"); | 71 | pr_err("Exporting ATAGs: not enough memory\n"); |
72 | 72 | ||
73 | return -ENOMEM; | 73 | return -ENOMEM; |
74 | } | 74 | } |
diff --git a/arch/arm/kernel/bios32.c b/arch/arm/kernel/bios32.c index daaff73bc776..a4effd6d8f2f 100644 --- a/arch/arm/kernel/bios32.c +++ b/arch/arm/kernel/bios32.c | |||
@@ -364,7 +364,7 @@ void pcibios_fixup_bus(struct pci_bus *bus) | |||
364 | /* | 364 | /* |
365 | * Report what we did for this bus | 365 | * Report what we did for this bus |
366 | */ | 366 | */ |
367 | printk(KERN_INFO "PCI: bus%d: Fast back to back transfers %sabled\n", | 367 | pr_info("PCI: bus%d: Fast back to back transfers %sabled\n", |
368 | bus->number, (features & PCI_COMMAND_FAST_BACK) ? "en" : "dis"); | 368 | bus->number, (features & PCI_COMMAND_FAST_BACK) ? "en" : "dis"); |
369 | } | 369 | } |
370 | EXPORT_SYMBOL(pcibios_fixup_bus); | 370 | EXPORT_SYMBOL(pcibios_fixup_bus); |
diff --git a/arch/arm/kernel/dma-isa.c b/arch/arm/kernel/dma-isa.c index 360bb6d701f5..84363fe7bad2 100644 --- a/arch/arm/kernel/dma-isa.c +++ b/arch/arm/kernel/dma-isa.c | |||
@@ -213,8 +213,8 @@ void __init isa_init_dma(void) | |||
213 | for (chan = 0; chan < 8; chan++) { | 213 | for (chan = 0; chan < 8; chan++) { |
214 | int ret = isa_dma_add(chan, &isa_dma[chan]); | 214 | int ret = isa_dma_add(chan, &isa_dma[chan]); |
215 | if (ret) | 215 | if (ret) |
216 | printk(KERN_ERR "ISADMA%u: unable to register: %d\n", | 216 | pr_err("ISADMA%u: unable to register: %d\n", |
217 | chan, ret); | 217 | chan, ret); |
218 | } | 218 | } |
219 | 219 | ||
220 | request_dma(DMA_ISA_CASCADE, "cascade"); | 220 | request_dma(DMA_ISA_CASCADE, "cascade"); |
diff --git a/arch/arm/kernel/dma.c b/arch/arm/kernel/dma.c index 7b829d9663b1..e651c4d0a0d9 100644 --- a/arch/arm/kernel/dma.c +++ b/arch/arm/kernel/dma.c | |||
@@ -79,7 +79,7 @@ int request_dma(unsigned int chan, const char *device_id) | |||
79 | return ret; | 79 | return ret; |
80 | 80 | ||
81 | bad_dma: | 81 | bad_dma: |
82 | printk(KERN_ERR "dma: trying to allocate DMA%d\n", chan); | 82 | pr_err("dma: trying to allocate DMA%d\n", chan); |
83 | return -EINVAL; | 83 | return -EINVAL; |
84 | 84 | ||
85 | busy: | 85 | busy: |
@@ -100,7 +100,7 @@ void free_dma(unsigned int chan) | |||
100 | goto bad_dma; | 100 | goto bad_dma; |
101 | 101 | ||
102 | if (dma->active) { | 102 | if (dma->active) { |
103 | printk(KERN_ERR "dma%d: freeing active DMA\n", chan); | 103 | pr_err("dma%d: freeing active DMA\n", chan); |
104 | dma->d_ops->disable(chan, dma); | 104 | dma->d_ops->disable(chan, dma); |
105 | dma->active = 0; | 105 | dma->active = 0; |
106 | } | 106 | } |
@@ -111,11 +111,11 @@ void free_dma(unsigned int chan) | |||
111 | return; | 111 | return; |
112 | } | 112 | } |
113 | 113 | ||
114 | printk(KERN_ERR "dma%d: trying to free free DMA\n", chan); | 114 | pr_err("dma%d: trying to free free DMA\n", chan); |
115 | return; | 115 | return; |
116 | 116 | ||
117 | bad_dma: | 117 | bad_dma: |
118 | printk(KERN_ERR "dma: trying to free DMA%d\n", chan); | 118 | pr_err("dma: trying to free DMA%d\n", chan); |
119 | } | 119 | } |
120 | EXPORT_SYMBOL(free_dma); | 120 | EXPORT_SYMBOL(free_dma); |
121 | 121 | ||
@@ -126,8 +126,7 @@ void set_dma_sg (unsigned int chan, struct scatterlist *sg, int nr_sg) | |||
126 | dma_t *dma = dma_channel(chan); | 126 | dma_t *dma = dma_channel(chan); |
127 | 127 | ||
128 | if (dma->active) | 128 | if (dma->active) |
129 | printk(KERN_ERR "dma%d: altering DMA SG while " | 129 | pr_err("dma%d: altering DMA SG while DMA active\n", chan); |
130 | "DMA active\n", chan); | ||
131 | 130 | ||
132 | dma->sg = sg; | 131 | dma->sg = sg; |
133 | dma->sgcount = nr_sg; | 132 | dma->sgcount = nr_sg; |
@@ -144,8 +143,7 @@ void __set_dma_addr (unsigned int chan, void *addr) | |||
144 | dma_t *dma = dma_channel(chan); | 143 | dma_t *dma = dma_channel(chan); |
145 | 144 | ||
146 | if (dma->active) | 145 | if (dma->active) |
147 | printk(KERN_ERR "dma%d: altering DMA address while " | 146 | pr_err("dma%d: altering DMA address while DMA active\n", chan); |
148 | "DMA active\n", chan); | ||
149 | 147 | ||
150 | dma->sg = NULL; | 148 | dma->sg = NULL; |
151 | dma->addr = addr; | 149 | dma->addr = addr; |
@@ -162,8 +160,7 @@ void set_dma_count (unsigned int chan, unsigned long count) | |||
162 | dma_t *dma = dma_channel(chan); | 160 | dma_t *dma = dma_channel(chan); |
163 | 161 | ||
164 | if (dma->active) | 162 | if (dma->active) |
165 | printk(KERN_ERR "dma%d: altering DMA count while " | 163 | pr_err("dma%d: altering DMA count while DMA active\n", chan); |
166 | "DMA active\n", chan); | ||
167 | 164 | ||
168 | dma->sg = NULL; | 165 | dma->sg = NULL; |
169 | dma->count = count; | 166 | dma->count = count; |
@@ -178,8 +175,7 @@ void set_dma_mode (unsigned int chan, unsigned int mode) | |||
178 | dma_t *dma = dma_channel(chan); | 175 | dma_t *dma = dma_channel(chan); |
179 | 176 | ||
180 | if (dma->active) | 177 | if (dma->active) |
181 | printk(KERN_ERR "dma%d: altering DMA mode while " | 178 | pr_err("dma%d: altering DMA mode while DMA active\n", chan); |
182 | "DMA active\n", chan); | ||
183 | 179 | ||
184 | dma->dma_mode = mode; | 180 | dma->dma_mode = mode; |
185 | dma->invalid = 1; | 181 | dma->invalid = 1; |
@@ -202,7 +198,7 @@ void enable_dma (unsigned int chan) | |||
202 | return; | 198 | return; |
203 | 199 | ||
204 | free_dma: | 200 | free_dma: |
205 | printk(KERN_ERR "dma%d: trying to enable free DMA\n", chan); | 201 | pr_err("dma%d: trying to enable free DMA\n", chan); |
206 | BUG(); | 202 | BUG(); |
207 | } | 203 | } |
208 | EXPORT_SYMBOL(enable_dma); | 204 | EXPORT_SYMBOL(enable_dma); |
@@ -223,7 +219,7 @@ void disable_dma (unsigned int chan) | |||
223 | return; | 219 | return; |
224 | 220 | ||
225 | free_dma: | 221 | free_dma: |
226 | printk(KERN_ERR "dma%d: trying to disable free DMA\n", chan); | 222 | pr_err("dma%d: trying to disable free DMA\n", chan); |
227 | BUG(); | 223 | BUG(); |
228 | } | 224 | } |
229 | EXPORT_SYMBOL(disable_dma); | 225 | EXPORT_SYMBOL(disable_dma); |
@@ -240,7 +236,7 @@ EXPORT_SYMBOL(dma_channel_active); | |||
240 | 236 | ||
241 | void set_dma_page(unsigned int chan, char pagenr) | 237 | void set_dma_page(unsigned int chan, char pagenr) |
242 | { | 238 | { |
243 | printk(KERN_ERR "dma%d: trying to set_dma_page\n", chan); | 239 | pr_err("dma%d: trying to set_dma_page\n", chan); |
244 | } | 240 | } |
245 | EXPORT_SYMBOL(set_dma_page); | 241 | EXPORT_SYMBOL(set_dma_page); |
246 | 242 | ||
diff --git a/arch/arm/kernel/entry-common.S b/arch/arm/kernel/entry-common.S index 6bb09d4abdea..f8ccc21fa032 100644 --- a/arch/arm/kernel/entry-common.S +++ b/arch/arm/kernel/entry-common.S | |||
@@ -109,241 +109,6 @@ ENDPROC(ret_from_fork) | |||
109 | #undef CALL | 109 | #undef CALL |
110 | #define CALL(x) .long x | 110 | #define CALL(x) .long x |
111 | 111 | ||
112 | #ifdef CONFIG_FUNCTION_TRACER | ||
113 | /* | ||
114 | * When compiling with -pg, gcc inserts a call to the mcount routine at the | ||
115 | * start of every function. In mcount, apart from the function's address (in | ||
116 | * lr), we need to get hold of the function's caller's address. | ||
117 | * | ||
118 | * Older GCCs (pre-4.4) inserted a call to a routine called mcount like this: | ||
119 | * | ||
120 | * bl mcount | ||
121 | * | ||
122 | * These versions have the limitation that in order for the mcount routine to | ||
123 | * be able to determine the function's caller's address, an APCS-style frame | ||
124 | * pointer (which is set up with something like the code below) is required. | ||
125 | * | ||
126 | * mov ip, sp | ||
127 | * push {fp, ip, lr, pc} | ||
128 | * sub fp, ip, #4 | ||
129 | * | ||
130 | * With EABI, these frame pointers are not available unless -mapcs-frame is | ||
131 | * specified, and if building as Thumb-2, not even then. | ||
132 | * | ||
133 | * Newer GCCs (4.4+) solve this problem by introducing a new version of mcount, | ||
134 | * with call sites like: | ||
135 | * | ||
136 | * push {lr} | ||
137 | * bl __gnu_mcount_nc | ||
138 | * | ||
139 | * With these compilers, frame pointers are not necessary. | ||
140 | * | ||
141 | * mcount can be thought of as a function called in the middle of a subroutine | ||
142 | * call. As such, it needs to be transparent for both the caller and the | ||
143 | * callee: the original lr needs to be restored when leaving mcount, and no | ||
144 | * registers should be clobbered. (In the __gnu_mcount_nc implementation, we | ||
145 | * clobber the ip register. This is OK because the ARM calling convention | ||
146 | * allows it to be clobbered in subroutines and doesn't use it to hold | ||
147 | * parameters.) | ||
148 | * | ||
149 | * When using dynamic ftrace, we patch out the mcount call by a "mov r0, r0" | ||
150 | * for the mcount case, and a "pop {lr}" for the __gnu_mcount_nc case (see | ||
151 | * arch/arm/kernel/ftrace.c). | ||
152 | */ | ||
153 | |||
154 | #ifndef CONFIG_OLD_MCOUNT | ||
155 | #if (__GNUC__ < 4 || (__GNUC__ == 4 && __GNUC_MINOR__ < 4)) | ||
156 | #error Ftrace requires CONFIG_FRAME_POINTER=y with GCC older than 4.4.0. | ||
157 | #endif | ||
158 | #endif | ||
159 | |||
160 | .macro mcount_adjust_addr rd, rn | ||
161 | bic \rd, \rn, #1 @ clear the Thumb bit if present | ||
162 | sub \rd, \rd, #MCOUNT_INSN_SIZE | ||
163 | .endm | ||
164 | |||
165 | .macro __mcount suffix | ||
166 | mcount_enter | ||
167 | ldr r0, =ftrace_trace_function | ||
168 | ldr r2, [r0] | ||
169 | adr r0, .Lftrace_stub | ||
170 | cmp r0, r2 | ||
171 | bne 1f | ||
172 | |||
173 | #ifdef CONFIG_FUNCTION_GRAPH_TRACER | ||
174 | ldr r1, =ftrace_graph_return | ||
175 | ldr r2, [r1] | ||
176 | cmp r0, r2 | ||
177 | bne ftrace_graph_caller\suffix | ||
178 | |||
179 | ldr r1, =ftrace_graph_entry | ||
180 | ldr r2, [r1] | ||
181 | ldr r0, =ftrace_graph_entry_stub | ||
182 | cmp r0, r2 | ||
183 | bne ftrace_graph_caller\suffix | ||
184 | #endif | ||
185 | |||
186 | mcount_exit | ||
187 | |||
188 | 1: mcount_get_lr r1 @ lr of instrumented func | ||
189 | mcount_adjust_addr r0, lr @ instrumented function | ||
190 | adr lr, BSYM(2f) | ||
191 | mov pc, r2 | ||
192 | 2: mcount_exit | ||
193 | .endm | ||
194 | |||
195 | .macro __ftrace_caller suffix | ||
196 | mcount_enter | ||
197 | |||
198 | mcount_get_lr r1 @ lr of instrumented func | ||
199 | mcount_adjust_addr r0, lr @ instrumented function | ||
200 | |||
201 | .globl ftrace_call\suffix | ||
202 | ftrace_call\suffix: | ||
203 | bl ftrace_stub | ||
204 | |||
205 | #ifdef CONFIG_FUNCTION_GRAPH_TRACER | ||
206 | .globl ftrace_graph_call\suffix | ||
207 | ftrace_graph_call\suffix: | ||
208 | mov r0, r0 | ||
209 | #endif | ||
210 | |||
211 | mcount_exit | ||
212 | .endm | ||
213 | |||
214 | .macro __ftrace_graph_caller | ||
215 | sub r0, fp, #4 @ &lr of instrumented routine (&parent) | ||
216 | #ifdef CONFIG_DYNAMIC_FTRACE | ||
217 | @ called from __ftrace_caller, saved in mcount_enter | ||
218 | ldr r1, [sp, #16] @ instrumented routine (func) | ||
219 | mcount_adjust_addr r1, r1 | ||
220 | #else | ||
221 | @ called from __mcount, untouched in lr | ||
222 | mcount_adjust_addr r1, lr @ instrumented routine (func) | ||
223 | #endif | ||
224 | mov r2, fp @ frame pointer | ||
225 | bl prepare_ftrace_return | ||
226 | mcount_exit | ||
227 | .endm | ||
228 | |||
229 | #ifdef CONFIG_OLD_MCOUNT | ||
230 | /* | ||
231 | * mcount | ||
232 | */ | ||
233 | |||
234 | .macro mcount_enter | ||
235 | stmdb sp!, {r0-r3, lr} | ||
236 | .endm | ||
237 | |||
238 | .macro mcount_get_lr reg | ||
239 | ldr \reg, [fp, #-4] | ||
240 | .endm | ||
241 | |||
242 | .macro mcount_exit | ||
243 | ldr lr, [fp, #-4] | ||
244 | ldmia sp!, {r0-r3, pc} | ||
245 | .endm | ||
246 | |||
247 | ENTRY(mcount) | ||
248 | #ifdef CONFIG_DYNAMIC_FTRACE | ||
249 | stmdb sp!, {lr} | ||
250 | ldr lr, [fp, #-4] | ||
251 | ldmia sp!, {pc} | ||
252 | #else | ||
253 | __mcount _old | ||
254 | #endif | ||
255 | ENDPROC(mcount) | ||
256 | |||
257 | #ifdef CONFIG_DYNAMIC_FTRACE | ||
258 | ENTRY(ftrace_caller_old) | ||
259 | __ftrace_caller _old | ||
260 | ENDPROC(ftrace_caller_old) | ||
261 | #endif | ||
262 | |||
263 | #ifdef CONFIG_FUNCTION_GRAPH_TRACER | ||
264 | ENTRY(ftrace_graph_caller_old) | ||
265 | __ftrace_graph_caller | ||
266 | ENDPROC(ftrace_graph_caller_old) | ||
267 | #endif | ||
268 | |||
269 | .purgem mcount_enter | ||
270 | .purgem mcount_get_lr | ||
271 | .purgem mcount_exit | ||
272 | #endif | ||
273 | |||
274 | /* | ||
275 | * __gnu_mcount_nc | ||
276 | */ | ||
277 | |||
278 | .macro mcount_enter | ||
279 | /* | ||
280 | * This pad compensates for the push {lr} at the call site. Note that we are | ||
281 | * unable to unwind through a function which does not otherwise save its lr. | ||
282 | */ | ||
283 | UNWIND(.pad #4) | ||
284 | stmdb sp!, {r0-r3, lr} | ||
285 | UNWIND(.save {r0-r3, lr}) | ||
286 | .endm | ||
287 | |||
288 | .macro mcount_get_lr reg | ||
289 | ldr \reg, [sp, #20] | ||
290 | .endm | ||
291 | |||
292 | .macro mcount_exit | ||
293 | ldmia sp!, {r0-r3, ip, lr} | ||
294 | ret ip | ||
295 | .endm | ||
296 | |||
297 | ENTRY(__gnu_mcount_nc) | ||
298 | UNWIND(.fnstart) | ||
299 | #ifdef CONFIG_DYNAMIC_FTRACE | ||
300 | mov ip, lr | ||
301 | ldmia sp!, {lr} | ||
302 | ret ip | ||
303 | #else | ||
304 | __mcount | ||
305 | #endif | ||
306 | UNWIND(.fnend) | ||
307 | ENDPROC(__gnu_mcount_nc) | ||
308 | |||
309 | #ifdef CONFIG_DYNAMIC_FTRACE | ||
310 | ENTRY(ftrace_caller) | ||
311 | UNWIND(.fnstart) | ||
312 | __ftrace_caller | ||
313 | UNWIND(.fnend) | ||
314 | ENDPROC(ftrace_caller) | ||
315 | #endif | ||
316 | |||
317 | #ifdef CONFIG_FUNCTION_GRAPH_TRACER | ||
318 | ENTRY(ftrace_graph_caller) | ||
319 | UNWIND(.fnstart) | ||
320 | __ftrace_graph_caller | ||
321 | UNWIND(.fnend) | ||
322 | ENDPROC(ftrace_graph_caller) | ||
323 | #endif | ||
324 | |||
325 | .purgem mcount_enter | ||
326 | .purgem mcount_get_lr | ||
327 | .purgem mcount_exit | ||
328 | |||
329 | #ifdef CONFIG_FUNCTION_GRAPH_TRACER | ||
330 | .globl return_to_handler | ||
331 | return_to_handler: | ||
332 | stmdb sp!, {r0-r3} | ||
333 | mov r0, fp @ frame pointer | ||
334 | bl ftrace_return_to_handler | ||
335 | mov lr, r0 @ r0 has real ret addr | ||
336 | ldmia sp!, {r0-r3} | ||
337 | ret lr | ||
338 | #endif | ||
339 | |||
340 | ENTRY(ftrace_stub) | ||
341 | .Lftrace_stub: | ||
342 | ret lr | ||
343 | ENDPROC(ftrace_stub) | ||
344 | |||
345 | #endif /* CONFIG_FUNCTION_TRACER */ | ||
346 | |||
347 | /*============================================================================= | 112 | /*============================================================================= |
348 | * SWI handler | 113 | * SWI handler |
349 | *----------------------------------------------------------------------------- | 114 | *----------------------------------------------------------------------------- |
diff --git a/arch/arm/kernel/entry-ftrace.S b/arch/arm/kernel/entry-ftrace.S new file mode 100644 index 000000000000..fe57c73e70a4 --- /dev/null +++ b/arch/arm/kernel/entry-ftrace.S | |||
@@ -0,0 +1,243 @@ | |||
1 | /* | ||
2 | * This program is free software; you can redistribute it and/or modify | ||
3 | * it under the terms of the GNU General Public License version 2 as | ||
4 | * published by the Free Software Foundation. | ||
5 | */ | ||
6 | |||
7 | #include <asm/assembler.h> | ||
8 | #include <asm/ftrace.h> | ||
9 | #include <asm/unwind.h> | ||
10 | |||
11 | #include "entry-header.S" | ||
12 | |||
13 | /* | ||
14 | * When compiling with -pg, gcc inserts a call to the mcount routine at the | ||
15 | * start of every function. In mcount, apart from the function's address (in | ||
16 | * lr), we need to get hold of the function's caller's address. | ||
17 | * | ||
18 | * Older GCCs (pre-4.4) inserted a call to a routine called mcount like this: | ||
19 | * | ||
20 | * bl mcount | ||
21 | * | ||
22 | * These versions have the limitation that in order for the mcount routine to | ||
23 | * be able to determine the function's caller's address, an APCS-style frame | ||
24 | * pointer (which is set up with something like the code below) is required. | ||
25 | * | ||
26 | * mov ip, sp | ||
27 | * push {fp, ip, lr, pc} | ||
28 | * sub fp, ip, #4 | ||
29 | * | ||
30 | * With EABI, these frame pointers are not available unless -mapcs-frame is | ||
31 | * specified, and if building as Thumb-2, not even then. | ||
32 | * | ||
33 | * Newer GCCs (4.4+) solve this problem by introducing a new version of mcount, | ||
34 | * with call sites like: | ||
35 | * | ||
36 | * push {lr} | ||
37 | * bl __gnu_mcount_nc | ||
38 | * | ||
39 | * With these compilers, frame pointers are not necessary. | ||
40 | * | ||
41 | * mcount can be thought of as a function called in the middle of a subroutine | ||
42 | * call. As such, it needs to be transparent for both the caller and the | ||
43 | * callee: the original lr needs to be restored when leaving mcount, and no | ||
44 | * registers should be clobbered. (In the __gnu_mcount_nc implementation, we | ||
45 | * clobber the ip register. This is OK because the ARM calling convention | ||
46 | * allows it to be clobbered in subroutines and doesn't use it to hold | ||
47 | * parameters.) | ||
48 | * | ||
49 | * When using dynamic ftrace, we patch out the mcount call by a "mov r0, r0" | ||
50 | * for the mcount case, and a "pop {lr}" for the __gnu_mcount_nc case (see | ||
51 | * arch/arm/kernel/ftrace.c). | ||
52 | */ | ||
53 | |||
54 | #ifndef CONFIG_OLD_MCOUNT | ||
55 | #if (__GNUC__ < 4 || (__GNUC__ == 4 && __GNUC_MINOR__ < 4)) | ||
56 | #error Ftrace requires CONFIG_FRAME_POINTER=y with GCC older than 4.4.0. | ||
57 | #endif | ||
58 | #endif | ||
59 | |||
60 | .macro mcount_adjust_addr rd, rn | ||
61 | bic \rd, \rn, #1 @ clear the Thumb bit if present | ||
62 | sub \rd, \rd, #MCOUNT_INSN_SIZE | ||
63 | .endm | ||
64 | |||
65 | .macro __mcount suffix | ||
66 | mcount_enter | ||
67 | ldr r0, =ftrace_trace_function | ||
68 | ldr r2, [r0] | ||
69 | adr r0, .Lftrace_stub | ||
70 | cmp r0, r2 | ||
71 | bne 1f | ||
72 | |||
73 | #ifdef CONFIG_FUNCTION_GRAPH_TRACER | ||
74 | ldr r1, =ftrace_graph_return | ||
75 | ldr r2, [r1] | ||
76 | cmp r0, r2 | ||
77 | bne ftrace_graph_caller\suffix | ||
78 | |||
79 | ldr r1, =ftrace_graph_entry | ||
80 | ldr r2, [r1] | ||
81 | ldr r0, =ftrace_graph_entry_stub | ||
82 | cmp r0, r2 | ||
83 | bne ftrace_graph_caller\suffix | ||
84 | #endif | ||
85 | |||
86 | mcount_exit | ||
87 | |||
88 | 1: mcount_get_lr r1 @ lr of instrumented func | ||
89 | mcount_adjust_addr r0, lr @ instrumented function | ||
90 | adr lr, BSYM(2f) | ||
91 | mov pc, r2 | ||
92 | 2: mcount_exit | ||
93 | .endm | ||
94 | |||
95 | .macro __ftrace_caller suffix | ||
96 | mcount_enter | ||
97 | |||
98 | mcount_get_lr r1 @ lr of instrumented func | ||
99 | mcount_adjust_addr r0, lr @ instrumented function | ||
100 | |||
101 | .globl ftrace_call\suffix | ||
102 | ftrace_call\suffix: | ||
103 | bl ftrace_stub | ||
104 | |||
105 | #ifdef CONFIG_FUNCTION_GRAPH_TRACER | ||
106 | .globl ftrace_graph_call\suffix | ||
107 | ftrace_graph_call\suffix: | ||
108 | mov r0, r0 | ||
109 | #endif | ||
110 | |||
111 | mcount_exit | ||
112 | .endm | ||
113 | |||
114 | .macro __ftrace_graph_caller | ||
115 | sub r0, fp, #4 @ &lr of instrumented routine (&parent) | ||
116 | #ifdef CONFIG_DYNAMIC_FTRACE | ||
117 | @ called from __ftrace_caller, saved in mcount_enter | ||
118 | ldr r1, [sp, #16] @ instrumented routine (func) | ||
119 | mcount_adjust_addr r1, r1 | ||
120 | #else | ||
121 | @ called from __mcount, untouched in lr | ||
122 | mcount_adjust_addr r1, lr @ instrumented routine (func) | ||
123 | #endif | ||
124 | mov r2, fp @ frame pointer | ||
125 | bl prepare_ftrace_return | ||
126 | mcount_exit | ||
127 | .endm | ||
128 | |||
129 | #ifdef CONFIG_OLD_MCOUNT | ||
130 | /* | ||
131 | * mcount | ||
132 | */ | ||
133 | |||
134 | .macro mcount_enter | ||
135 | stmdb sp!, {r0-r3, lr} | ||
136 | .endm | ||
137 | |||
138 | .macro mcount_get_lr reg | ||
139 | ldr \reg, [fp, #-4] | ||
140 | .endm | ||
141 | |||
142 | .macro mcount_exit | ||
143 | ldr lr, [fp, #-4] | ||
144 | ldmia sp!, {r0-r3, pc} | ||
145 | .endm | ||
146 | |||
147 | ENTRY(mcount) | ||
148 | #ifdef CONFIG_DYNAMIC_FTRACE | ||
149 | stmdb sp!, {lr} | ||
150 | ldr lr, [fp, #-4] | ||
151 | ldmia sp!, {pc} | ||
152 | #else | ||
153 | __mcount _old | ||
154 | #endif | ||
155 | ENDPROC(mcount) | ||
156 | |||
157 | #ifdef CONFIG_DYNAMIC_FTRACE | ||
158 | ENTRY(ftrace_caller_old) | ||
159 | __ftrace_caller _old | ||
160 | ENDPROC(ftrace_caller_old) | ||
161 | #endif | ||
162 | |||
163 | #ifdef CONFIG_FUNCTION_GRAPH_TRACER | ||
164 | ENTRY(ftrace_graph_caller_old) | ||
165 | __ftrace_graph_caller | ||
166 | ENDPROC(ftrace_graph_caller_old) | ||
167 | #endif | ||
168 | |||
169 | .purgem mcount_enter | ||
170 | .purgem mcount_get_lr | ||
171 | .purgem mcount_exit | ||
172 | #endif | ||
173 | |||
174 | /* | ||
175 | * __gnu_mcount_nc | ||
176 | */ | ||
177 | |||
178 | .macro mcount_enter | ||
179 | /* | ||
180 | * This pad compensates for the push {lr} at the call site. Note that we are | ||
181 | * unable to unwind through a function which does not otherwise save its lr. | ||
182 | */ | ||
183 | UNWIND(.pad #4) | ||
184 | stmdb sp!, {r0-r3, lr} | ||
185 | UNWIND(.save {r0-r3, lr}) | ||
186 | .endm | ||
187 | |||
188 | .macro mcount_get_lr reg | ||
189 | ldr \reg, [sp, #20] | ||
190 | .endm | ||
191 | |||
192 | .macro mcount_exit | ||
193 | ldmia sp!, {r0-r3, ip, lr} | ||
194 | ret ip | ||
195 | .endm | ||
196 | |||
197 | ENTRY(__gnu_mcount_nc) | ||
198 | UNWIND(.fnstart) | ||
199 | #ifdef CONFIG_DYNAMIC_FTRACE | ||
200 | mov ip, lr | ||
201 | ldmia sp!, {lr} | ||
202 | ret ip | ||
203 | #else | ||
204 | __mcount | ||
205 | #endif | ||
206 | UNWIND(.fnend) | ||
207 | ENDPROC(__gnu_mcount_nc) | ||
208 | |||
209 | #ifdef CONFIG_DYNAMIC_FTRACE | ||
210 | ENTRY(ftrace_caller) | ||
211 | UNWIND(.fnstart) | ||
212 | __ftrace_caller | ||
213 | UNWIND(.fnend) | ||
214 | ENDPROC(ftrace_caller) | ||
215 | #endif | ||
216 | |||
217 | #ifdef CONFIG_FUNCTION_GRAPH_TRACER | ||
218 | ENTRY(ftrace_graph_caller) | ||
219 | UNWIND(.fnstart) | ||
220 | __ftrace_graph_caller | ||
221 | UNWIND(.fnend) | ||
222 | ENDPROC(ftrace_graph_caller) | ||
223 | #endif | ||
224 | |||
225 | .purgem mcount_enter | ||
226 | .purgem mcount_get_lr | ||
227 | .purgem mcount_exit | ||
228 | |||
229 | #ifdef CONFIG_FUNCTION_GRAPH_TRACER | ||
230 | .globl return_to_handler | ||
231 | return_to_handler: | ||
232 | stmdb sp!, {r0-r3} | ||
233 | mov r0, fp @ frame pointer | ||
234 | bl ftrace_return_to_handler | ||
235 | mov lr, r0 @ r0 has real ret addr | ||
236 | ldmia sp!, {r0-r3} | ||
237 | ret lr | ||
238 | #endif | ||
239 | |||
240 | ENTRY(ftrace_stub) | ||
241 | .Lftrace_stub: | ||
242 | ret lr | ||
243 | ENDPROC(ftrace_stub) | ||
diff --git a/arch/arm/kernel/etm.c b/arch/arm/kernel/etm.c index 131a6ab5f355..8b96972dcb1d 100644 --- a/arch/arm/kernel/etm.c +++ b/arch/arm/kernel/etm.c | |||
@@ -213,7 +213,7 @@ static void etm_dump(void) | |||
213 | int length; | 213 | int length; |
214 | 214 | ||
215 | if (!t->etb_regs) { | 215 | if (!t->etb_regs) { |
216 | printk(KERN_INFO "No tracing hardware found\n"); | 216 | pr_info("No tracing hardware found\n"); |
217 | return; | 217 | return; |
218 | } | 218 | } |
219 | 219 | ||
@@ -229,11 +229,11 @@ static void etm_dump(void) | |||
229 | 229 | ||
230 | etb_writel(t, first, ETBR_READADDR); | 230 | etb_writel(t, first, ETBR_READADDR); |
231 | 231 | ||
232 | printk(KERN_INFO "Trace buffer contents length: %d\n", length); | 232 | pr_info("Trace buffer contents length: %d\n", length); |
233 | printk(KERN_INFO "--- ETB buffer begin ---\n"); | 233 | pr_info("--- ETB buffer begin ---\n"); |
234 | for (; length; length--) | 234 | for (; length; length--) |
235 | printk("%08x", cpu_to_be32(etb_readl(t, ETBR_READMEM))); | 235 | printk("%08x", cpu_to_be32(etb_readl(t, ETBR_READMEM))); |
236 | printk(KERN_INFO "\n--- ETB buffer end ---\n"); | 236 | pr_info("\n--- ETB buffer end ---\n"); |
237 | 237 | ||
238 | /* deassert the overflow bit */ | 238 | /* deassert the overflow bit */ |
239 | etb_writel(t, 1, ETBR_CTRL); | 239 | etb_writel(t, 1, ETBR_CTRL); |
@@ -633,14 +633,14 @@ static int __init etm_init(void) | |||
633 | 633 | ||
634 | retval = amba_driver_register(&etb_driver); | 634 | retval = amba_driver_register(&etb_driver); |
635 | if (retval) { | 635 | if (retval) { |
636 | printk(KERN_ERR "Failed to register etb\n"); | 636 | pr_err("Failed to register etb\n"); |
637 | return retval; | 637 | return retval; |
638 | } | 638 | } |
639 | 639 | ||
640 | retval = amba_driver_register(&etm_driver); | 640 | retval = amba_driver_register(&etm_driver); |
641 | if (retval) { | 641 | if (retval) { |
642 | amba_driver_unregister(&etb_driver); | 642 | amba_driver_unregister(&etb_driver); |
643 | printk(KERN_ERR "Failed to probe etm\n"); | 643 | pr_err("Failed to probe etm\n"); |
644 | return retval; | 644 | return retval; |
645 | } | 645 | } |
646 | 646 | ||
diff --git a/arch/arm/kernel/fiq.c b/arch/arm/kernel/fiq.c index b37752a96652..059c3da0fee3 100644 --- a/arch/arm/kernel/fiq.c +++ b/arch/arm/kernel/fiq.c | |||
@@ -124,7 +124,7 @@ int claim_fiq(struct fiq_handler *f) | |||
124 | void release_fiq(struct fiq_handler *f) | 124 | void release_fiq(struct fiq_handler *f) |
125 | { | 125 | { |
126 | if (current_fiq != f) { | 126 | if (current_fiq != f) { |
127 | printk(KERN_ERR "%s FIQ trying to release %s FIQ\n", | 127 | pr_err("%s FIQ trying to release %s FIQ\n", |
128 | f->name, current_fiq->name); | 128 | f->name, current_fiq->name); |
129 | dump_stack(); | 129 | dump_stack(); |
130 | return; | 130 | return; |
diff --git a/arch/arm/kernel/ftrace.c b/arch/arm/kernel/ftrace.c index af9a8a927a4e..b8c75e45a950 100644 --- a/arch/arm/kernel/ftrace.c +++ b/arch/arm/kernel/ftrace.c | |||
@@ -15,6 +15,7 @@ | |||
15 | #include <linux/ftrace.h> | 15 | #include <linux/ftrace.h> |
16 | #include <linux/uaccess.h> | 16 | #include <linux/uaccess.h> |
17 | #include <linux/module.h> | 17 | #include <linux/module.h> |
18 | #include <linux/stop_machine.h> | ||
18 | 19 | ||
19 | #include <asm/cacheflush.h> | 20 | #include <asm/cacheflush.h> |
20 | #include <asm/opcodes.h> | 21 | #include <asm/opcodes.h> |
@@ -35,6 +36,22 @@ | |||
35 | 36 | ||
36 | #define OLD_NOP 0xe1a00000 /* mov r0, r0 */ | 37 | #define OLD_NOP 0xe1a00000 /* mov r0, r0 */ |
37 | 38 | ||
39 | static int __ftrace_modify_code(void *data) | ||
40 | { | ||
41 | int *command = data; | ||
42 | |||
43 | set_kernel_text_rw(); | ||
44 | ftrace_modify_all_code(*command); | ||
45 | set_kernel_text_ro(); | ||
46 | |||
47 | return 0; | ||
48 | } | ||
49 | |||
50 | void arch_ftrace_update_code(int command) | ||
51 | { | ||
52 | stop_machine(__ftrace_modify_code, &command, NULL); | ||
53 | } | ||
54 | |||
38 | static unsigned long ftrace_nop_replace(struct dyn_ftrace *rec) | 55 | static unsigned long ftrace_nop_replace(struct dyn_ftrace *rec) |
39 | { | 56 | { |
40 | return rec->arch.old_mcount ? OLD_NOP : NOP; | 57 | return rec->arch.old_mcount ? OLD_NOP : NOP; |
@@ -73,6 +90,8 @@ int ftrace_arch_code_modify_prepare(void) | |||
73 | int ftrace_arch_code_modify_post_process(void) | 90 | int ftrace_arch_code_modify_post_process(void) |
74 | { | 91 | { |
75 | set_all_modules_text_ro(); | 92 | set_all_modules_text_ro(); |
93 | /* Make sure any TLB misses during machine stop are cleared. */ | ||
94 | flush_tlb_all(); | ||
76 | return 0; | 95 | return 0; |
77 | } | 96 | } |
78 | 97 | ||
diff --git a/arch/arm/kernel/io.c b/arch/arm/kernel/io.c index 9203cf883330..eedefe050022 100644 --- a/arch/arm/kernel/io.c +++ b/arch/arm/kernel/io.c | |||
@@ -51,6 +51,7 @@ void _memcpy_fromio(void *to, const volatile void __iomem *from, size_t count) | |||
51 | from++; | 51 | from++; |
52 | } | 52 | } |
53 | } | 53 | } |
54 | EXPORT_SYMBOL(_memcpy_fromio); | ||
54 | 55 | ||
55 | /* | 56 | /* |
56 | * Copy data from "real" memory space to IO memory space. | 57 | * Copy data from "real" memory space to IO memory space. |
@@ -66,6 +67,7 @@ void _memcpy_toio(volatile void __iomem *to, const void *from, size_t count) | |||
66 | to++; | 67 | to++; |
67 | } | 68 | } |
68 | } | 69 | } |
70 | EXPORT_SYMBOL(_memcpy_toio); | ||
69 | 71 | ||
70 | /* | 72 | /* |
71 | * "memset" on IO memory space. | 73 | * "memset" on IO memory space. |
@@ -79,7 +81,4 @@ void _memset_io(volatile void __iomem *dst, int c, size_t count) | |||
79 | dst++; | 81 | dst++; |
80 | } | 82 | } |
81 | } | 83 | } |
82 | |||
83 | EXPORT_SYMBOL(_memcpy_fromio); | ||
84 | EXPORT_SYMBOL(_memcpy_toio); | ||
85 | EXPORT_SYMBOL(_memset_io); | 84 | EXPORT_SYMBOL(_memset_io); |
diff --git a/arch/arm/kernel/irq.c b/arch/arm/kernel/irq.c index 7c81ec428b9b..ad857bada96c 100644 --- a/arch/arm/kernel/irq.c +++ b/arch/arm/kernel/irq.c | |||
@@ -31,6 +31,7 @@ | |||
31 | #include <linux/smp.h> | 31 | #include <linux/smp.h> |
32 | #include <linux/init.h> | 32 | #include <linux/init.h> |
33 | #include <linux/seq_file.h> | 33 | #include <linux/seq_file.h> |
34 | #include <linux/ratelimit.h> | ||
34 | #include <linux/errno.h> | 35 | #include <linux/errno.h> |
35 | #include <linux/list.h> | 36 | #include <linux/list.h> |
36 | #include <linux/kallsyms.h> | 37 | #include <linux/kallsyms.h> |
@@ -82,7 +83,7 @@ void set_irq_flags(unsigned int irq, unsigned int iflags) | |||
82 | unsigned long clr = 0, set = IRQ_NOREQUEST | IRQ_NOPROBE | IRQ_NOAUTOEN; | 83 | unsigned long clr = 0, set = IRQ_NOREQUEST | IRQ_NOPROBE | IRQ_NOAUTOEN; |
83 | 84 | ||
84 | if (irq >= nr_irqs) { | 85 | if (irq >= nr_irqs) { |
85 | printk(KERN_ERR "Trying to set irq flags for IRQ%d\n", irq); | 86 | pr_err("Trying to set irq flags for IRQ%d\n", irq); |
86 | return; | 87 | return; |
87 | } | 88 | } |
88 | 89 | ||
@@ -135,7 +136,6 @@ int __init arch_probe_nr_irqs(void) | |||
135 | #endif | 136 | #endif |
136 | 137 | ||
137 | #ifdef CONFIG_HOTPLUG_CPU | 138 | #ifdef CONFIG_HOTPLUG_CPU |
138 | |||
139 | static bool migrate_one_irq(struct irq_desc *desc) | 139 | static bool migrate_one_irq(struct irq_desc *desc) |
140 | { | 140 | { |
141 | struct irq_data *d = irq_desc_get_irq_data(desc); | 141 | struct irq_data *d = irq_desc_get_irq_data(desc); |
@@ -187,8 +187,8 @@ void migrate_irqs(void) | |||
187 | affinity_broken = migrate_one_irq(desc); | 187 | affinity_broken = migrate_one_irq(desc); |
188 | raw_spin_unlock(&desc->lock); | 188 | raw_spin_unlock(&desc->lock); |
189 | 189 | ||
190 | if (affinity_broken && printk_ratelimit()) | 190 | if (affinity_broken) |
191 | pr_warn("IRQ%u no longer affine to CPU%u\n", | 191 | pr_warn_ratelimited("IRQ%u no longer affine to CPU%u\n", |
192 | i, smp_processor_id()); | 192 | i, smp_processor_id()); |
193 | } | 193 | } |
194 | 194 | ||
diff --git a/arch/arm/kernel/iwmmxt.S b/arch/arm/kernel/iwmmxt.S index ad58e565fe98..49fadbda8c63 100644 --- a/arch/arm/kernel/iwmmxt.S +++ b/arch/arm/kernel/iwmmxt.S | |||
@@ -58,6 +58,7 @@ | |||
58 | #define MMX_SIZE (0x98) | 58 | #define MMX_SIZE (0x98) |
59 | 59 | ||
60 | .text | 60 | .text |
61 | .arm | ||
61 | 62 | ||
62 | /* | 63 | /* |
63 | * Lazy switching of Concan coprocessor context | 64 | * Lazy switching of Concan coprocessor context |
@@ -182,6 +183,8 @@ concan_load: | |||
182 | tmcr wCon, r2 | 183 | tmcr wCon, r2 |
183 | ret lr | 184 | ret lr |
184 | 185 | ||
186 | ENDPROC(iwmmxt_task_enable) | ||
187 | |||
185 | /* | 188 | /* |
186 | * Back up Concan regs to save area and disable access to them | 189 | * Back up Concan regs to save area and disable access to them |
187 | * (mainly for gdb or sleep mode usage) | 190 | * (mainly for gdb or sleep mode usage) |
@@ -232,6 +235,8 @@ ENTRY(iwmmxt_task_disable) | |||
232 | 1: msr cpsr_c, ip @ restore interrupt mode | 235 | 1: msr cpsr_c, ip @ restore interrupt mode |
233 | ldmfd sp!, {r4, pc} | 236 | ldmfd sp!, {r4, pc} |
234 | 237 | ||
238 | ENDPROC(iwmmxt_task_disable) | ||
239 | |||
235 | /* | 240 | /* |
236 | * Copy Concan state to given memory address | 241 | * Copy Concan state to given memory address |
237 | * | 242 | * |
@@ -268,6 +273,8 @@ ENTRY(iwmmxt_task_copy) | |||
268 | msr cpsr_c, ip @ restore interrupt mode | 273 | msr cpsr_c, ip @ restore interrupt mode |
269 | ret r3 | 274 | ret r3 |
270 | 275 | ||
276 | ENDPROC(iwmmxt_task_copy) | ||
277 | |||
271 | /* | 278 | /* |
272 | * Restore Concan state from given memory address | 279 | * Restore Concan state from given memory address |
273 | * | 280 | * |
@@ -304,6 +311,8 @@ ENTRY(iwmmxt_task_restore) | |||
304 | msr cpsr_c, ip @ restore interrupt mode | 311 | msr cpsr_c, ip @ restore interrupt mode |
305 | ret r3 | 312 | ret r3 |
306 | 313 | ||
314 | ENDPROC(iwmmxt_task_restore) | ||
315 | |||
307 | /* | 316 | /* |
308 | * Concan handling on task switch | 317 | * Concan handling on task switch |
309 | * | 318 | * |
@@ -335,6 +344,8 @@ ENTRY(iwmmxt_task_switch) | |||
335 | mrc p15, 0, r1, c2, c0, 0 | 344 | mrc p15, 0, r1, c2, c0, 0 |
336 | sub pc, lr, r1, lsr #32 @ cpwait and return | 345 | sub pc, lr, r1, lsr #32 @ cpwait and return |
337 | 346 | ||
347 | ENDPROC(iwmmxt_task_switch) | ||
348 | |||
338 | /* | 349 | /* |
339 | * Remove Concan ownership of given task | 350 | * Remove Concan ownership of given task |
340 | * | 351 | * |
@@ -353,6 +364,8 @@ ENTRY(iwmmxt_task_release) | |||
353 | msr cpsr_c, r2 @ restore interrupts | 364 | msr cpsr_c, r2 @ restore interrupts |
354 | ret lr | 365 | ret lr |
355 | 366 | ||
367 | ENDPROC(iwmmxt_task_release) | ||
368 | |||
356 | .data | 369 | .data |
357 | concan_owner: | 370 | concan_owner: |
358 | .word 0 | 371 | .word 0 |
diff --git a/arch/arm/kernel/jump_label.c b/arch/arm/kernel/jump_label.c index 4ce4f789446d..afeeb9ea6f43 100644 --- a/arch/arm/kernel/jump_label.c +++ b/arch/arm/kernel/jump_label.c | |||
@@ -19,7 +19,7 @@ static void __arch_jump_label_transform(struct jump_entry *entry, | |||
19 | insn = arm_gen_nop(); | 19 | insn = arm_gen_nop(); |
20 | 20 | ||
21 | if (is_static) | 21 | if (is_static) |
22 | __patch_text(addr, insn); | 22 | __patch_text_early(addr, insn); |
23 | else | 23 | else |
24 | patch_text(addr, insn); | 24 | patch_text(addr, insn); |
25 | } | 25 | } |
diff --git a/arch/arm/kernel/kgdb.c b/arch/arm/kernel/kgdb.c index a74b53c1b7df..07db2f8a1b45 100644 --- a/arch/arm/kernel/kgdb.c +++ b/arch/arm/kernel/kgdb.c | |||
@@ -12,8 +12,12 @@ | |||
12 | #include <linux/irq.h> | 12 | #include <linux/irq.h> |
13 | #include <linux/kdebug.h> | 13 | #include <linux/kdebug.h> |
14 | #include <linux/kgdb.h> | 14 | #include <linux/kgdb.h> |
15 | #include <linux/uaccess.h> | ||
16 | |||
15 | #include <asm/traps.h> | 17 | #include <asm/traps.h> |
16 | 18 | ||
19 | #include "patch.h" | ||
20 | |||
17 | struct dbg_reg_def_t dbg_reg_def[DBG_MAX_REG_NUM] = | 21 | struct dbg_reg_def_t dbg_reg_def[DBG_MAX_REG_NUM] = |
18 | { | 22 | { |
19 | { "r0", 4, offsetof(struct pt_regs, ARM_r0)}, | 23 | { "r0", 4, offsetof(struct pt_regs, ARM_r0)}, |
@@ -244,6 +248,31 @@ void kgdb_arch_exit(void) | |||
244 | unregister_die_notifier(&kgdb_notifier); | 248 | unregister_die_notifier(&kgdb_notifier); |
245 | } | 249 | } |
246 | 250 | ||
251 | int kgdb_arch_set_breakpoint(struct kgdb_bkpt *bpt) | ||
252 | { | ||
253 | int err; | ||
254 | |||
255 | /* patch_text() only supports int-sized breakpoints */ | ||
256 | BUILD_BUG_ON(sizeof(int) != BREAK_INSTR_SIZE); | ||
257 | |||
258 | err = probe_kernel_read(bpt->saved_instr, (char *)bpt->bpt_addr, | ||
259 | BREAK_INSTR_SIZE); | ||
260 | if (err) | ||
261 | return err; | ||
262 | |||
263 | patch_text((void *)bpt->bpt_addr, | ||
264 | *(unsigned int *)arch_kgdb_ops.gdb_bpt_instr); | ||
265 | |||
266 | return err; | ||
267 | } | ||
268 | |||
269 | int kgdb_arch_remove_breakpoint(struct kgdb_bkpt *bpt) | ||
270 | { | ||
271 | patch_text((void *)bpt->bpt_addr, *(unsigned int *)bpt->saved_instr); | ||
272 | |||
273 | return 0; | ||
274 | } | ||
275 | |||
247 | /* | 276 | /* |
248 | * Register our undef instruction hooks with ARM undef core. | 277 | * Register our undef instruction hooks with ARM undef core. |
249 | * We regsiter a hook specifically looking for the KGB break inst | 278 | * We regsiter a hook specifically looking for the KGB break inst |
diff --git a/arch/arm/kernel/machine_kexec.c b/arch/arm/kernel/machine_kexec.c index 8cf0996aa1a8..de2b085ad753 100644 --- a/arch/arm/kernel/machine_kexec.c +++ b/arch/arm/kernel/machine_kexec.c | |||
@@ -29,6 +29,7 @@ extern unsigned long kexec_boot_atags; | |||
29 | 29 | ||
30 | static atomic_t waiting_for_crash_ipi; | 30 | static atomic_t waiting_for_crash_ipi; |
31 | 31 | ||
32 | static unsigned long dt_mem; | ||
32 | /* | 33 | /* |
33 | * Provide a dummy crash_notes definition while crash dump arrives to arm. | 34 | * Provide a dummy crash_notes definition while crash dump arrives to arm. |
34 | * This prevents breakage of crash_notes attribute in kernel/ksysfs.c. | 35 | * This prevents breakage of crash_notes attribute in kernel/ksysfs.c. |
@@ -64,7 +65,7 @@ int machine_kexec_prepare(struct kimage *image) | |||
64 | return err; | 65 | return err; |
65 | 66 | ||
66 | if (be32_to_cpu(header) == OF_DT_HEADER) | 67 | if (be32_to_cpu(header) == OF_DT_HEADER) |
67 | kexec_boot_atags = current_segment->mem; | 68 | dt_mem = current_segment->mem; |
68 | } | 69 | } |
69 | return 0; | 70 | return 0; |
70 | } | 71 | } |
@@ -126,12 +127,12 @@ void machine_crash_shutdown(struct pt_regs *regs) | |||
126 | msecs--; | 127 | msecs--; |
127 | } | 128 | } |
128 | if (atomic_read(&waiting_for_crash_ipi) > 0) | 129 | if (atomic_read(&waiting_for_crash_ipi) > 0) |
129 | printk(KERN_WARNING "Non-crashing CPUs did not react to IPI\n"); | 130 | pr_warn("Non-crashing CPUs did not react to IPI\n"); |
130 | 131 | ||
131 | crash_save_cpu(regs, smp_processor_id()); | 132 | crash_save_cpu(regs, smp_processor_id()); |
132 | machine_kexec_mask_interrupts(); | 133 | machine_kexec_mask_interrupts(); |
133 | 134 | ||
134 | printk(KERN_INFO "Loading crashdump kernel...\n"); | 135 | pr_info("Loading crashdump kernel...\n"); |
135 | } | 136 | } |
136 | 137 | ||
137 | /* | 138 | /* |
@@ -163,12 +164,12 @@ void machine_kexec(struct kimage *image) | |||
163 | reboot_code_buffer = page_address(image->control_code_page); | 164 | reboot_code_buffer = page_address(image->control_code_page); |
164 | 165 | ||
165 | /* Prepare parameters for reboot_code_buffer*/ | 166 | /* Prepare parameters for reboot_code_buffer*/ |
167 | set_kernel_text_rw(); | ||
166 | kexec_start_address = image->start; | 168 | kexec_start_address = image->start; |
167 | kexec_indirection_page = page_list; | 169 | kexec_indirection_page = page_list; |
168 | kexec_mach_type = machine_arch_type; | 170 | kexec_mach_type = machine_arch_type; |
169 | if (!kexec_boot_atags) | 171 | kexec_boot_atags = dt_mem ?: image->start - KEXEC_ARM_ZIMAGE_OFFSET |
170 | kexec_boot_atags = image->start - KEXEC_ARM_ZIMAGE_OFFSET + KEXEC_ARM_ATAGS_OFFSET; | 172 | + KEXEC_ARM_ATAGS_OFFSET; |
171 | |||
172 | 173 | ||
173 | /* copy our kernel relocation code to the control code page */ | 174 | /* copy our kernel relocation code to the control code page */ |
174 | reboot_entry = fncpy(reboot_code_buffer, | 175 | reboot_entry = fncpy(reboot_code_buffer, |
@@ -177,7 +178,7 @@ void machine_kexec(struct kimage *image) | |||
177 | reboot_entry_phys = (unsigned long)reboot_entry + | 178 | reboot_entry_phys = (unsigned long)reboot_entry + |
178 | (reboot_code_buffer_phys - (unsigned long)reboot_code_buffer); | 179 | (reboot_code_buffer_phys - (unsigned long)reboot_code_buffer); |
179 | 180 | ||
180 | printk(KERN_INFO "Bye!\n"); | 181 | pr_info("Bye!\n"); |
181 | 182 | ||
182 | if (kexec_reinit) | 183 | if (kexec_reinit) |
183 | kexec_reinit(); | 184 | kexec_reinit(); |
diff --git a/arch/arm/kernel/module.c b/arch/arm/kernel/module.c index 6a4dffefd357..bea7db9e5b80 100644 --- a/arch/arm/kernel/module.c +++ b/arch/arm/kernel/module.c | |||
@@ -251,7 +251,7 @@ apply_relocate(Elf32_Shdr *sechdrs, const char *strtab, unsigned int symindex, | |||
251 | #endif | 251 | #endif |
252 | 252 | ||
253 | default: | 253 | default: |
254 | printk(KERN_ERR "%s: unknown relocation: %u\n", | 254 | pr_err("%s: unknown relocation: %u\n", |
255 | module->name, ELF32_R_TYPE(rel->r_info)); | 255 | module->name, ELF32_R_TYPE(rel->r_info)); |
256 | return -ENOEXEC; | 256 | return -ENOEXEC; |
257 | } | 257 | } |
diff --git a/arch/arm/kernel/patch.c b/arch/arm/kernel/patch.c index 07314af47733..5038960e3c55 100644 --- a/arch/arm/kernel/patch.c +++ b/arch/arm/kernel/patch.c | |||
@@ -1,8 +1,11 @@ | |||
1 | #include <linux/kernel.h> | 1 | #include <linux/kernel.h> |
2 | #include <linux/spinlock.h> | ||
2 | #include <linux/kprobes.h> | 3 | #include <linux/kprobes.h> |
4 | #include <linux/mm.h> | ||
3 | #include <linux/stop_machine.h> | 5 | #include <linux/stop_machine.h> |
4 | 6 | ||
5 | #include <asm/cacheflush.h> | 7 | #include <asm/cacheflush.h> |
8 | #include <asm/fixmap.h> | ||
6 | #include <asm/smp_plat.h> | 9 | #include <asm/smp_plat.h> |
7 | #include <asm/opcodes.h> | 10 | #include <asm/opcodes.h> |
8 | 11 | ||
@@ -13,21 +16,77 @@ struct patch { | |||
13 | unsigned int insn; | 16 | unsigned int insn; |
14 | }; | 17 | }; |
15 | 18 | ||
16 | void __kprobes __patch_text(void *addr, unsigned int insn) | 19 | static DEFINE_SPINLOCK(patch_lock); |
20 | |||
21 | static void __kprobes *patch_map(void *addr, int fixmap, unsigned long *flags) | ||
22 | __acquires(&patch_lock) | ||
23 | { | ||
24 | unsigned int uintaddr = (uintptr_t) addr; | ||
25 | bool module = !core_kernel_text(uintaddr); | ||
26 | struct page *page; | ||
27 | |||
28 | if (module && IS_ENABLED(CONFIG_DEBUG_SET_MODULE_RONX)) | ||
29 | page = vmalloc_to_page(addr); | ||
30 | else if (!module && IS_ENABLED(CONFIG_DEBUG_RODATA)) | ||
31 | page = virt_to_page(addr); | ||
32 | else | ||
33 | return addr; | ||
34 | |||
35 | if (flags) | ||
36 | spin_lock_irqsave(&patch_lock, *flags); | ||
37 | else | ||
38 | __acquire(&patch_lock); | ||
39 | |||
40 | set_fixmap(fixmap, page_to_phys(page)); | ||
41 | |||
42 | return (void *) (__fix_to_virt(fixmap) + (uintaddr & ~PAGE_MASK)); | ||
43 | } | ||
44 | |||
45 | static void __kprobes patch_unmap(int fixmap, unsigned long *flags) | ||
46 | __releases(&patch_lock) | ||
47 | { | ||
48 | clear_fixmap(fixmap); | ||
49 | |||
50 | if (flags) | ||
51 | spin_unlock_irqrestore(&patch_lock, *flags); | ||
52 | else | ||
53 | __release(&patch_lock); | ||
54 | } | ||
55 | |||
56 | void __kprobes __patch_text_real(void *addr, unsigned int insn, bool remap) | ||
17 | { | 57 | { |
18 | bool thumb2 = IS_ENABLED(CONFIG_THUMB2_KERNEL); | 58 | bool thumb2 = IS_ENABLED(CONFIG_THUMB2_KERNEL); |
59 | unsigned int uintaddr = (uintptr_t) addr; | ||
60 | bool twopage = false; | ||
61 | unsigned long flags; | ||
62 | void *waddr = addr; | ||
19 | int size; | 63 | int size; |
20 | 64 | ||
65 | if (remap) | ||
66 | waddr = patch_map(addr, FIX_TEXT_POKE0, &flags); | ||
67 | else | ||
68 | __acquire(&patch_lock); | ||
69 | |||
21 | if (thumb2 && __opcode_is_thumb16(insn)) { | 70 | if (thumb2 && __opcode_is_thumb16(insn)) { |
22 | *(u16 *)addr = __opcode_to_mem_thumb16(insn); | 71 | *(u16 *)waddr = __opcode_to_mem_thumb16(insn); |
23 | size = sizeof(u16); | 72 | size = sizeof(u16); |
24 | } else if (thumb2 && ((uintptr_t)addr & 2)) { | 73 | } else if (thumb2 && (uintaddr & 2)) { |
25 | u16 first = __opcode_thumb32_first(insn); | 74 | u16 first = __opcode_thumb32_first(insn); |
26 | u16 second = __opcode_thumb32_second(insn); | 75 | u16 second = __opcode_thumb32_second(insn); |
27 | u16 *addrh = addr; | 76 | u16 *addrh0 = waddr; |
77 | u16 *addrh1 = waddr + 2; | ||
78 | |||
79 | twopage = (uintaddr & ~PAGE_MASK) == PAGE_SIZE - 2; | ||
80 | if (twopage && remap) | ||
81 | addrh1 = patch_map(addr + 2, FIX_TEXT_POKE1, NULL); | ||
82 | |||
83 | *addrh0 = __opcode_to_mem_thumb16(first); | ||
84 | *addrh1 = __opcode_to_mem_thumb16(second); | ||
28 | 85 | ||
29 | addrh[0] = __opcode_to_mem_thumb16(first); | 86 | if (twopage && addrh1 != addr + 2) { |
30 | addrh[1] = __opcode_to_mem_thumb16(second); | 87 | flush_kernel_vmap_range(addrh1, 2); |
88 | patch_unmap(FIX_TEXT_POKE1, NULL); | ||
89 | } | ||
31 | 90 | ||
32 | size = sizeof(u32); | 91 | size = sizeof(u32); |
33 | } else { | 92 | } else { |
@@ -36,10 +95,16 @@ void __kprobes __patch_text(void *addr, unsigned int insn) | |||
36 | else | 95 | else |
37 | insn = __opcode_to_mem_arm(insn); | 96 | insn = __opcode_to_mem_arm(insn); |
38 | 97 | ||
39 | *(u32 *)addr = insn; | 98 | *(u32 *)waddr = insn; |
40 | size = sizeof(u32); | 99 | size = sizeof(u32); |
41 | } | 100 | } |
42 | 101 | ||
102 | if (waddr != addr) { | ||
103 | flush_kernel_vmap_range(waddr, twopage ? size / 2 : size); | ||
104 | patch_unmap(FIX_TEXT_POKE0, &flags); | ||
105 | } else | ||
106 | __release(&patch_lock); | ||
107 | |||
43 | flush_icache_range((uintptr_t)(addr), | 108 | flush_icache_range((uintptr_t)(addr), |
44 | (uintptr_t)(addr) + size); | 109 | (uintptr_t)(addr) + size); |
45 | } | 110 | } |
@@ -60,16 +125,5 @@ void __kprobes patch_text(void *addr, unsigned int insn) | |||
60 | .insn = insn, | 125 | .insn = insn, |
61 | }; | 126 | }; |
62 | 127 | ||
63 | if (cache_ops_need_broadcast()) { | 128 | stop_machine(patch_text_stop_machine, &patch, NULL); |
64 | stop_machine(patch_text_stop_machine, &patch, cpu_online_mask); | ||
65 | } else { | ||
66 | bool straddles_word = IS_ENABLED(CONFIG_THUMB2_KERNEL) | ||
67 | && __opcode_is_thumb32(insn) | ||
68 | && ((uintptr_t)addr & 2); | ||
69 | |||
70 | if (straddles_word) | ||
71 | stop_machine(patch_text_stop_machine, &patch, NULL); | ||
72 | else | ||
73 | __patch_text(addr, insn); | ||
74 | } | ||
75 | } | 129 | } |
diff --git a/arch/arm/kernel/patch.h b/arch/arm/kernel/patch.h index b4731f2dac38..77e054c2f6cd 100644 --- a/arch/arm/kernel/patch.h +++ b/arch/arm/kernel/patch.h | |||
@@ -2,6 +2,16 @@ | |||
2 | #define _ARM_KERNEL_PATCH_H | 2 | #define _ARM_KERNEL_PATCH_H |
3 | 3 | ||
4 | void patch_text(void *addr, unsigned int insn); | 4 | void patch_text(void *addr, unsigned int insn); |
5 | void __patch_text(void *addr, unsigned int insn); | 5 | void __patch_text_real(void *addr, unsigned int insn, bool remap); |
6 | |||
7 | static inline void __patch_text(void *addr, unsigned int insn) | ||
8 | { | ||
9 | __patch_text_real(addr, insn, true); | ||
10 | } | ||
11 | |||
12 | static inline void __patch_text_early(void *addr, unsigned int insn) | ||
13 | { | ||
14 | __patch_text_real(addr, insn, false); | ||
15 | } | ||
6 | 16 | ||
7 | #endif | 17 | #endif |
diff --git a/arch/arm/kernel/process.c b/arch/arm/kernel/process.c index fe972a2f3df3..fdfa3a78ec8c 100644 --- a/arch/arm/kernel/process.c +++ b/arch/arm/kernel/process.c | |||
@@ -51,8 +51,8 @@ EXPORT_SYMBOL(__stack_chk_guard); | |||
51 | static const char *processor_modes[] __maybe_unused = { | 51 | static const char *processor_modes[] __maybe_unused = { |
52 | "USER_26", "FIQ_26" , "IRQ_26" , "SVC_26" , "UK4_26" , "UK5_26" , "UK6_26" , "UK7_26" , | 52 | "USER_26", "FIQ_26" , "IRQ_26" , "SVC_26" , "UK4_26" , "UK5_26" , "UK6_26" , "UK7_26" , |
53 | "UK8_26" , "UK9_26" , "UK10_26", "UK11_26", "UK12_26", "UK13_26", "UK14_26", "UK15_26", | 53 | "UK8_26" , "UK9_26" , "UK10_26", "UK11_26", "UK12_26", "UK13_26", "UK14_26", "UK15_26", |
54 | "USER_32", "FIQ_32" , "IRQ_32" , "SVC_32" , "UK4_32" , "UK5_32" , "UK6_32" , "ABT_32" , | 54 | "USER_32", "FIQ_32" , "IRQ_32" , "SVC_32" , "UK4_32" , "UK5_32" , "MON_32" , "ABT_32" , |
55 | "UK8_32" , "UK9_32" , "UK10_32", "UND_32" , "UK12_32", "UK13_32", "UK14_32", "SYS_32" | 55 | "UK8_32" , "UK9_32" , "HYP_32", "UND_32" , "UK12_32", "UK13_32", "UK14_32", "SYS_32" |
56 | }; | 56 | }; |
57 | 57 | ||
58 | static const char *isa_modes[] __maybe_unused = { | 58 | static const char *isa_modes[] __maybe_unused = { |
diff --git a/arch/arm/kernel/return_address.c b/arch/arm/kernel/return_address.c index 98ea4b7eb406..24b4a04846eb 100644 --- a/arch/arm/kernel/return_address.c +++ b/arch/arm/kernel/return_address.c | |||
@@ -39,13 +39,12 @@ void *return_address(unsigned int level) | |||
39 | { | 39 | { |
40 | struct return_address_data data; | 40 | struct return_address_data data; |
41 | struct stackframe frame; | 41 | struct stackframe frame; |
42 | register unsigned long current_sp asm ("sp"); | ||
43 | 42 | ||
44 | data.level = level + 2; | 43 | data.level = level + 2; |
45 | data.addr = NULL; | 44 | data.addr = NULL; |
46 | 45 | ||
47 | frame.fp = (unsigned long)__builtin_frame_address(0); | 46 | frame.fp = (unsigned long)__builtin_frame_address(0); |
48 | frame.sp = current_sp; | 47 | frame.sp = current_stack_pointer; |
49 | frame.lr = (unsigned long)__builtin_return_address(0); | 48 | frame.lr = (unsigned long)__builtin_return_address(0); |
50 | frame.pc = (unsigned long)return_address; | 49 | frame.pc = (unsigned long)return_address; |
51 | 50 | ||
diff --git a/arch/arm/kernel/setup.c b/arch/arm/kernel/setup.c index c03106378b49..8361652b6dab 100644 --- a/arch/arm/kernel/setup.c +++ b/arch/arm/kernel/setup.c | |||
@@ -900,6 +900,7 @@ void __init setup_arch(char **cmdline_p) | |||
900 | mdesc = setup_machine_tags(__atags_pointer, __machine_arch_type); | 900 | mdesc = setup_machine_tags(__atags_pointer, __machine_arch_type); |
901 | machine_desc = mdesc; | 901 | machine_desc = mdesc; |
902 | machine_name = mdesc->name; | 902 | machine_name = mdesc->name; |
903 | dump_stack_set_arch_desc("%s", mdesc->name); | ||
903 | 904 | ||
904 | if (mdesc->reboot_mode != REBOOT_HARD) | 905 | if (mdesc->reboot_mode != REBOOT_HARD) |
905 | reboot_mode = mdesc->reboot_mode; | 906 | reboot_mode = mdesc->reboot_mode; |
diff --git a/arch/arm/kernel/signal.c b/arch/arm/kernel/signal.c index bd1983437205..8aa6f1b87c9e 100644 --- a/arch/arm/kernel/signal.c +++ b/arch/arm/kernel/signal.c | |||
@@ -592,7 +592,6 @@ do_work_pending(struct pt_regs *regs, unsigned int thread_flags, int syscall) | |||
592 | } | 592 | } |
593 | syscall = 0; | 593 | syscall = 0; |
594 | } else if (thread_flags & _TIF_UPROBE) { | 594 | } else if (thread_flags & _TIF_UPROBE) { |
595 | clear_thread_flag(TIF_UPROBE); | ||
596 | uprobe_notify_resume(regs); | 595 | uprobe_notify_resume(regs); |
597 | } else { | 596 | } else { |
598 | clear_thread_flag(TIF_NOTIFY_RESUME); | 597 | clear_thread_flag(TIF_NOTIFY_RESUME); |
diff --git a/arch/arm/kernel/smp.c b/arch/arm/kernel/smp.c index 13396d3d600e..5e6052e18850 100644 --- a/arch/arm/kernel/smp.c +++ b/arch/arm/kernel/smp.c | |||
@@ -225,7 +225,7 @@ void __cpu_die(unsigned int cpu) | |||
225 | pr_err("CPU%u: cpu didn't die\n", cpu); | 225 | pr_err("CPU%u: cpu didn't die\n", cpu); |
226 | return; | 226 | return; |
227 | } | 227 | } |
228 | printk(KERN_NOTICE "CPU%u: shutdown\n", cpu); | 228 | pr_notice("CPU%u: shutdown\n", cpu); |
229 | 229 | ||
230 | /* | 230 | /* |
231 | * platform_cpu_kill() is generally expected to do the powering off | 231 | * platform_cpu_kill() is generally expected to do the powering off |
@@ -235,7 +235,7 @@ void __cpu_die(unsigned int cpu) | |||
235 | * the requesting CPU and the dying CPU actually losing power. | 235 | * the requesting CPU and the dying CPU actually losing power. |
236 | */ | 236 | */ |
237 | if (!platform_cpu_kill(cpu)) | 237 | if (!platform_cpu_kill(cpu)) |
238 | printk("CPU%u: unable to kill\n", cpu); | 238 | pr_err("CPU%u: unable to kill\n", cpu); |
239 | } | 239 | } |
240 | 240 | ||
241 | /* | 241 | /* |
@@ -351,7 +351,7 @@ asmlinkage void secondary_start_kernel(void) | |||
351 | 351 | ||
352 | cpu_init(); | 352 | cpu_init(); |
353 | 353 | ||
354 | printk("CPU%u: Booted secondary processor\n", cpu); | 354 | pr_debug("CPU%u: Booted secondary processor\n", cpu); |
355 | 355 | ||
356 | preempt_disable(); | 356 | preempt_disable(); |
357 | trace_hardirqs_off(); | 357 | trace_hardirqs_off(); |
@@ -387,9 +387,6 @@ asmlinkage void secondary_start_kernel(void) | |||
387 | 387 | ||
388 | void __init smp_cpus_done(unsigned int max_cpus) | 388 | void __init smp_cpus_done(unsigned int max_cpus) |
389 | { | 389 | { |
390 | printk(KERN_INFO "SMP: Total of %d processors activated.\n", | ||
391 | num_online_cpus()); | ||
392 | |||
393 | hyp_mode_check(); | 390 | hyp_mode_check(); |
394 | } | 391 | } |
395 | 392 | ||
@@ -521,7 +518,7 @@ static void ipi_cpu_stop(unsigned int cpu) | |||
521 | if (system_state == SYSTEM_BOOTING || | 518 | if (system_state == SYSTEM_BOOTING || |
522 | system_state == SYSTEM_RUNNING) { | 519 | system_state == SYSTEM_RUNNING) { |
523 | raw_spin_lock(&stop_lock); | 520 | raw_spin_lock(&stop_lock); |
524 | printk(KERN_CRIT "CPU%u: stopping\n", cpu); | 521 | pr_crit("CPU%u: stopping\n", cpu); |
525 | dump_stack(); | 522 | dump_stack(); |
526 | raw_spin_unlock(&stop_lock); | 523 | raw_spin_unlock(&stop_lock); |
527 | } | 524 | } |
@@ -615,8 +612,8 @@ void handle_IPI(int ipinr, struct pt_regs *regs) | |||
615 | break; | 612 | break; |
616 | 613 | ||
617 | default: | 614 | default: |
618 | printk(KERN_CRIT "CPU%u: Unknown IPI message 0x%x\n", | 615 | pr_crit("CPU%u: Unknown IPI message 0x%x\n", |
619 | cpu, ipinr); | 616 | cpu, ipinr); |
620 | break; | 617 | break; |
621 | } | 618 | } |
622 | 619 | ||
diff --git a/arch/arm/kernel/smp_twd.c b/arch/arm/kernel/smp_twd.c index 93090213c71c..172c6a05d27f 100644 --- a/arch/arm/kernel/smp_twd.c +++ b/arch/arm/kernel/smp_twd.c | |||
@@ -199,7 +199,7 @@ static void twd_calibrate_rate(void) | |||
199 | * the timer ticks | 199 | * the timer ticks |
200 | */ | 200 | */ |
201 | if (twd_timer_rate == 0) { | 201 | if (twd_timer_rate == 0) { |
202 | printk(KERN_INFO "Calibrating local timer... "); | 202 | pr_info("Calibrating local timer... "); |
203 | 203 | ||
204 | /* Wait for a tick to start */ | 204 | /* Wait for a tick to start */ |
205 | waitjiffies = get_jiffies_64() + 1; | 205 | waitjiffies = get_jiffies_64() + 1; |
@@ -223,7 +223,7 @@ static void twd_calibrate_rate(void) | |||
223 | 223 | ||
224 | twd_timer_rate = (0xFFFFFFFFU - count) * (HZ / 5); | 224 | twd_timer_rate = (0xFFFFFFFFU - count) * (HZ / 5); |
225 | 225 | ||
226 | printk("%lu.%02luMHz.\n", twd_timer_rate / 1000000, | 226 | pr_cont("%lu.%02luMHz.\n", twd_timer_rate / 1000000, |
227 | (twd_timer_rate / 10000) % 100); | 227 | (twd_timer_rate / 10000) % 100); |
228 | } | 228 | } |
229 | } | 229 | } |
diff --git a/arch/arm/kernel/stacktrace.c b/arch/arm/kernel/stacktrace.c index f065eb05d254..92b72375c4c7 100644 --- a/arch/arm/kernel/stacktrace.c +++ b/arch/arm/kernel/stacktrace.c | |||
@@ -134,12 +134,10 @@ static noinline void __save_stack_trace(struct task_struct *tsk, | |||
134 | frame.pc = thread_saved_pc(tsk); | 134 | frame.pc = thread_saved_pc(tsk); |
135 | #endif | 135 | #endif |
136 | } else { | 136 | } else { |
137 | register unsigned long current_sp asm ("sp"); | ||
138 | |||
139 | /* We don't want this function nor the caller */ | 137 | /* We don't want this function nor the caller */ |
140 | data.skip += 2; | 138 | data.skip += 2; |
141 | frame.fp = (unsigned long)__builtin_frame_address(0); | 139 | frame.fp = (unsigned long)__builtin_frame_address(0); |
142 | frame.sp = current_sp; | 140 | frame.sp = current_stack_pointer; |
143 | frame.lr = (unsigned long)__builtin_return_address(0); | 141 | frame.lr = (unsigned long)__builtin_return_address(0); |
144 | frame.pc = (unsigned long)__save_stack_trace; | 142 | frame.pc = (unsigned long)__save_stack_trace; |
145 | } | 143 | } |
diff --git a/arch/arm/kernel/swp_emulate.c b/arch/arm/kernel/swp_emulate.c index 587fdfe1a72c..afdd51e30bec 100644 --- a/arch/arm/kernel/swp_emulate.c +++ b/arch/arm/kernel/swp_emulate.c | |||
@@ -260,7 +260,7 @@ static int __init swp_emulation_init(void) | |||
260 | return -ENOMEM; | 260 | return -ENOMEM; |
261 | #endif /* CONFIG_PROC_FS */ | 261 | #endif /* CONFIG_PROC_FS */ |
262 | 262 | ||
263 | printk(KERN_NOTICE "Registering SWP/SWPB emulation handler\n"); | 263 | pr_notice("Registering SWP/SWPB emulation handler\n"); |
264 | register_undef_hook(&swp_hook); | 264 | register_undef_hook(&swp_hook); |
265 | 265 | ||
266 | return 0; | 266 | return 0; |
diff --git a/arch/arm/kernel/thumbee.c b/arch/arm/kernel/thumbee.c index 80f0d69205e7..8ff8dbfbe9fb 100644 --- a/arch/arm/kernel/thumbee.c +++ b/arch/arm/kernel/thumbee.c | |||
@@ -72,7 +72,7 @@ static int __init thumbee_init(void) | |||
72 | if ((pfr0 & 0x0000f000) != 0x00001000) | 72 | if ((pfr0 & 0x0000f000) != 0x00001000) |
73 | return 0; | 73 | return 0; |
74 | 74 | ||
75 | printk(KERN_INFO "ThumbEE CPU extension supported.\n"); | 75 | pr_info("ThumbEE CPU extension supported.\n"); |
76 | elf_hwcap |= HWCAP_THUMBEE; | 76 | elf_hwcap |= HWCAP_THUMBEE; |
77 | thread_register_notifier(&thumbee_notifier_block); | 77 | thread_register_notifier(&thumbee_notifier_block); |
78 | 78 | ||
diff --git a/arch/arm/kernel/topology.c b/arch/arm/kernel/topology.c index 89cfdd6e50cb..08b7847bf912 100644 --- a/arch/arm/kernel/topology.c +++ b/arch/arm/kernel/topology.c | |||
@@ -165,7 +165,7 @@ static void update_cpu_capacity(unsigned int cpu) | |||
165 | 165 | ||
166 | set_capacity_scale(cpu, cpu_capacity(cpu) / middle_capacity); | 166 | set_capacity_scale(cpu, cpu_capacity(cpu) / middle_capacity); |
167 | 167 | ||
168 | printk(KERN_INFO "CPU%u: update cpu_capacity %lu\n", | 168 | pr_info("CPU%u: update cpu_capacity %lu\n", |
169 | cpu, arch_scale_cpu_capacity(NULL, cpu)); | 169 | cpu, arch_scale_cpu_capacity(NULL, cpu)); |
170 | } | 170 | } |
171 | 171 | ||
@@ -269,7 +269,7 @@ void store_cpu_topology(unsigned int cpuid) | |||
269 | 269 | ||
270 | update_cpu_capacity(cpuid); | 270 | update_cpu_capacity(cpuid); |
271 | 271 | ||
272 | printk(KERN_INFO "CPU%u: thread %d, cpu %d, socket %d, mpidr %x\n", | 272 | pr_info("CPU%u: thread %d, cpu %d, socket %d, mpidr %x\n", |
273 | cpuid, cpu_topology[cpuid].thread_id, | 273 | cpuid, cpu_topology[cpuid].thread_id, |
274 | cpu_topology[cpuid].core_id, | 274 | cpu_topology[cpuid].core_id, |
275 | cpu_topology[cpuid].socket_id, mpidr); | 275 | cpu_topology[cpuid].socket_id, mpidr); |
diff --git a/arch/arm/kernel/traps.c b/arch/arm/kernel/traps.c index 9f5d81881eb6..788e23fe64d8 100644 --- a/arch/arm/kernel/traps.c +++ b/arch/arm/kernel/traps.c | |||
@@ -198,14 +198,14 @@ static void dump_backtrace(struct pt_regs *regs, struct task_struct *tsk) | |||
198 | } | 198 | } |
199 | 199 | ||
200 | if (!fp) { | 200 | if (!fp) { |
201 | printk("no frame pointer"); | 201 | pr_cont("no frame pointer"); |
202 | ok = 0; | 202 | ok = 0; |
203 | } else if (verify_stack(fp)) { | 203 | } else if (verify_stack(fp)) { |
204 | printk("invalid frame pointer 0x%08x", fp); | 204 | pr_cont("invalid frame pointer 0x%08x", fp); |
205 | ok = 0; | 205 | ok = 0; |
206 | } else if (fp < (unsigned long)end_of_stack(tsk)) | 206 | } else if (fp < (unsigned long)end_of_stack(tsk)) |
207 | printk("frame pointer underflow"); | 207 | pr_cont("frame pointer underflow"); |
208 | printk("\n"); | 208 | pr_cont("\n"); |
209 | 209 | ||
210 | if (ok) | 210 | if (ok) |
211 | c_backtrace(fp, mode); | 211 | c_backtrace(fp, mode); |
@@ -240,8 +240,8 @@ static int __die(const char *str, int err, struct pt_regs *regs) | |||
240 | static int die_counter; | 240 | static int die_counter; |
241 | int ret; | 241 | int ret; |
242 | 242 | ||
243 | printk(KERN_EMERG "Internal error: %s: %x [#%d]" S_PREEMPT S_SMP | 243 | pr_emerg("Internal error: %s: %x [#%d]" S_PREEMPT S_SMP S_ISA "\n", |
244 | S_ISA "\n", str, err, ++die_counter); | 244 | str, err, ++die_counter); |
245 | 245 | ||
246 | /* trap and error numbers are mostly meaningless on ARM */ | 246 | /* trap and error numbers are mostly meaningless on ARM */ |
247 | ret = notify_die(DIE_OOPS, str, regs, err, tsk->thread.trap_no, SIGSEGV); | 247 | ret = notify_die(DIE_OOPS, str, regs, err, tsk->thread.trap_no, SIGSEGV); |
@@ -250,8 +250,8 @@ static int __die(const char *str, int err, struct pt_regs *regs) | |||
250 | 250 | ||
251 | print_modules(); | 251 | print_modules(); |
252 | __show_regs(regs); | 252 | __show_regs(regs); |
253 | printk(KERN_EMERG "Process %.*s (pid: %d, stack limit = 0x%p)\n", | 253 | pr_emerg("Process %.*s (pid: %d, stack limit = 0x%p)\n", |
254 | TASK_COMM_LEN, tsk->comm, task_pid_nr(tsk), end_of_stack(tsk)); | 254 | TASK_COMM_LEN, tsk->comm, task_pid_nr(tsk), end_of_stack(tsk)); |
255 | 255 | ||
256 | if (!user_mode(regs) || in_interrupt()) { | 256 | if (!user_mode(regs) || in_interrupt()) { |
257 | dump_mem(KERN_EMERG, "Stack: ", regs->ARM_sp, | 257 | dump_mem(KERN_EMERG, "Stack: ", regs->ARM_sp, |
@@ -446,7 +446,7 @@ asmlinkage void __exception do_undefinstr(struct pt_regs *regs) | |||
446 | die_sig: | 446 | die_sig: |
447 | #ifdef CONFIG_DEBUG_USER | 447 | #ifdef CONFIG_DEBUG_USER |
448 | if (user_debug & UDBG_UNDEFINED) { | 448 | if (user_debug & UDBG_UNDEFINED) { |
449 | printk(KERN_INFO "%s (%d): undefined instruction: pc=%p\n", | 449 | pr_info("%s (%d): undefined instruction: pc=%p\n", |
450 | current->comm, task_pid_nr(current), pc); | 450 | current->comm, task_pid_nr(current), pc); |
451 | __show_regs(regs); | 451 | __show_regs(regs); |
452 | dump_instr(KERN_INFO, regs); | 452 | dump_instr(KERN_INFO, regs); |
@@ -496,7 +496,7 @@ asmlinkage void bad_mode(struct pt_regs *regs, int reason) | |||
496 | { | 496 | { |
497 | console_verbose(); | 497 | console_verbose(); |
498 | 498 | ||
499 | printk(KERN_CRIT "Bad mode in %s handler detected\n", handler[reason]); | 499 | pr_crit("Bad mode in %s handler detected\n", handler[reason]); |
500 | 500 | ||
501 | die("Oops - bad mode", regs, 0); | 501 | die("Oops - bad mode", regs, 0); |
502 | local_irq_disable(); | 502 | local_irq_disable(); |
@@ -516,7 +516,7 @@ static int bad_syscall(int n, struct pt_regs *regs) | |||
516 | 516 | ||
517 | #ifdef CONFIG_DEBUG_USER | 517 | #ifdef CONFIG_DEBUG_USER |
518 | if (user_debug & UDBG_SYSCALL) { | 518 | if (user_debug & UDBG_SYSCALL) { |
519 | printk(KERN_ERR "[%d] %s: obsolete system call %08x.\n", | 519 | pr_err("[%d] %s: obsolete system call %08x.\n", |
520 | task_pid_nr(current), current->comm, n); | 520 | task_pid_nr(current), current->comm, n); |
521 | dump_instr(KERN_ERR, regs); | 521 | dump_instr(KERN_ERR, regs); |
522 | } | 522 | } |
@@ -694,7 +694,7 @@ asmlinkage int arm_syscall(int no, struct pt_regs *regs) | |||
694 | * something catastrophic has happened | 694 | * something catastrophic has happened |
695 | */ | 695 | */ |
696 | if (user_debug & UDBG_SYSCALL) { | 696 | if (user_debug & UDBG_SYSCALL) { |
697 | printk("[%d] %s: arm syscall %d\n", | 697 | pr_err("[%d] %s: arm syscall %d\n", |
698 | task_pid_nr(current), current->comm, no); | 698 | task_pid_nr(current), current->comm, no); |
699 | dump_instr("", regs); | 699 | dump_instr("", regs); |
700 | if (user_mode(regs)) { | 700 | if (user_mode(regs)) { |
@@ -753,8 +753,8 @@ late_initcall(arm_mrc_hook_init); | |||
753 | 753 | ||
754 | void __bad_xchg(volatile void *ptr, int size) | 754 | void __bad_xchg(volatile void *ptr, int size) |
755 | { | 755 | { |
756 | printk("xchg: bad data size: pc 0x%p, ptr 0x%p, size %d\n", | 756 | pr_err("xchg: bad data size: pc 0x%p, ptr 0x%p, size %d\n", |
757 | __builtin_return_address(0), ptr, size); | 757 | __builtin_return_address(0), ptr, size); |
758 | BUG(); | 758 | BUG(); |
759 | } | 759 | } |
760 | EXPORT_SYMBOL(__bad_xchg); | 760 | EXPORT_SYMBOL(__bad_xchg); |
@@ -771,8 +771,8 @@ baddataabort(int code, unsigned long instr, struct pt_regs *regs) | |||
771 | 771 | ||
772 | #ifdef CONFIG_DEBUG_USER | 772 | #ifdef CONFIG_DEBUG_USER |
773 | if (user_debug & UDBG_BADABORT) { | 773 | if (user_debug & UDBG_BADABORT) { |
774 | printk(KERN_ERR "[%d] %s: bad data abort: code %d instr 0x%08lx\n", | 774 | pr_err("[%d] %s: bad data abort: code %d instr 0x%08lx\n", |
775 | task_pid_nr(current), current->comm, code, instr); | 775 | task_pid_nr(current), current->comm, code, instr); |
776 | dump_instr(KERN_ERR, regs); | 776 | dump_instr(KERN_ERR, regs); |
777 | show_pte(current->mm, addr); | 777 | show_pte(current->mm, addr); |
778 | } | 778 | } |
@@ -788,29 +788,29 @@ baddataabort(int code, unsigned long instr, struct pt_regs *regs) | |||
788 | 788 | ||
789 | void __readwrite_bug(const char *fn) | 789 | void __readwrite_bug(const char *fn) |
790 | { | 790 | { |
791 | printk("%s called, but not implemented\n", fn); | 791 | pr_err("%s called, but not implemented\n", fn); |
792 | BUG(); | 792 | BUG(); |
793 | } | 793 | } |
794 | EXPORT_SYMBOL(__readwrite_bug); | 794 | EXPORT_SYMBOL(__readwrite_bug); |
795 | 795 | ||
796 | void __pte_error(const char *file, int line, pte_t pte) | 796 | void __pte_error(const char *file, int line, pte_t pte) |
797 | { | 797 | { |
798 | printk("%s:%d: bad pte %08llx.\n", file, line, (long long)pte_val(pte)); | 798 | pr_err("%s:%d: bad pte %08llx.\n", file, line, (long long)pte_val(pte)); |
799 | } | 799 | } |
800 | 800 | ||
801 | void __pmd_error(const char *file, int line, pmd_t pmd) | 801 | void __pmd_error(const char *file, int line, pmd_t pmd) |
802 | { | 802 | { |
803 | printk("%s:%d: bad pmd %08llx.\n", file, line, (long long)pmd_val(pmd)); | 803 | pr_err("%s:%d: bad pmd %08llx.\n", file, line, (long long)pmd_val(pmd)); |
804 | } | 804 | } |
805 | 805 | ||
806 | void __pgd_error(const char *file, int line, pgd_t pgd) | 806 | void __pgd_error(const char *file, int line, pgd_t pgd) |
807 | { | 807 | { |
808 | printk("%s:%d: bad pgd %08llx.\n", file, line, (long long)pgd_val(pgd)); | 808 | pr_err("%s:%d: bad pgd %08llx.\n", file, line, (long long)pgd_val(pgd)); |
809 | } | 809 | } |
810 | 810 | ||
811 | asmlinkage void __div0(void) | 811 | asmlinkage void __div0(void) |
812 | { | 812 | { |
813 | printk("Division by zero in kernel.\n"); | 813 | pr_err("Division by zero in kernel.\n"); |
814 | dump_stack(); | 814 | dump_stack(); |
815 | } | 815 | } |
816 | EXPORT_SYMBOL(__div0); | 816 | EXPORT_SYMBOL(__div0); |
diff --git a/arch/arm/kernel/unwind.c b/arch/arm/kernel/unwind.c index cbb85c5fabf9..0bee233fef9a 100644 --- a/arch/arm/kernel/unwind.c +++ b/arch/arm/kernel/unwind.c | |||
@@ -471,7 +471,6 @@ int unwind_frame(struct stackframe *frame) | |||
471 | void unwind_backtrace(struct pt_regs *regs, struct task_struct *tsk) | 471 | void unwind_backtrace(struct pt_regs *regs, struct task_struct *tsk) |
472 | { | 472 | { |
473 | struct stackframe frame; | 473 | struct stackframe frame; |
474 | register unsigned long current_sp asm ("sp"); | ||
475 | 474 | ||
476 | pr_debug("%s(regs = %p tsk = %p)\n", __func__, regs, tsk); | 475 | pr_debug("%s(regs = %p tsk = %p)\n", __func__, regs, tsk); |
477 | 476 | ||
@@ -485,7 +484,7 @@ void unwind_backtrace(struct pt_regs *regs, struct task_struct *tsk) | |||
485 | frame.pc = regs->ARM_lr; | 484 | frame.pc = regs->ARM_lr; |
486 | } else if (tsk == current) { | 485 | } else if (tsk == current) { |
487 | frame.fp = (unsigned long)__builtin_frame_address(0); | 486 | frame.fp = (unsigned long)__builtin_frame_address(0); |
488 | frame.sp = current_sp; | 487 | frame.sp = current_stack_pointer; |
489 | frame.lr = (unsigned long)__builtin_return_address(0); | 488 | frame.lr = (unsigned long)__builtin_return_address(0); |
490 | frame.pc = (unsigned long)unwind_backtrace; | 489 | frame.pc = (unsigned long)unwind_backtrace; |
491 | } else { | 490 | } else { |
diff --git a/arch/arm/kernel/vmlinux.lds.S b/arch/arm/kernel/vmlinux.lds.S index 8e95aa47457a..b31aa73e8076 100644 --- a/arch/arm/kernel/vmlinux.lds.S +++ b/arch/arm/kernel/vmlinux.lds.S | |||
@@ -8,6 +8,9 @@ | |||
8 | #include <asm/thread_info.h> | 8 | #include <asm/thread_info.h> |
9 | #include <asm/memory.h> | 9 | #include <asm/memory.h> |
10 | #include <asm/page.h> | 10 | #include <asm/page.h> |
11 | #ifdef CONFIG_ARM_KERNMEM_PERMS | ||
12 | #include <asm/pgtable.h> | ||
13 | #endif | ||
11 | 14 | ||
12 | #define PROC_INFO \ | 15 | #define PROC_INFO \ |
13 | . = ALIGN(4); \ | 16 | . = ALIGN(4); \ |
@@ -90,6 +93,11 @@ SECTIONS | |||
90 | _text = .; | 93 | _text = .; |
91 | HEAD_TEXT | 94 | HEAD_TEXT |
92 | } | 95 | } |
96 | |||
97 | #ifdef CONFIG_ARM_KERNMEM_PERMS | ||
98 | . = ALIGN(1<<SECTION_SHIFT); | ||
99 | #endif | ||
100 | |||
93 | .text : { /* Real text segment */ | 101 | .text : { /* Real text segment */ |
94 | _stext = .; /* Text and read-only data */ | 102 | _stext = .; /* Text and read-only data */ |
95 | __exception_text_start = .; | 103 | __exception_text_start = .; |
@@ -112,6 +120,9 @@ SECTIONS | |||
112 | ARM_CPU_KEEP(PROC_INFO) | 120 | ARM_CPU_KEEP(PROC_INFO) |
113 | } | 121 | } |
114 | 122 | ||
123 | #ifdef CONFIG_DEBUG_RODATA | ||
124 | . = ALIGN(1<<SECTION_SHIFT); | ||
125 | #endif | ||
115 | RO_DATA(PAGE_SIZE) | 126 | RO_DATA(PAGE_SIZE) |
116 | 127 | ||
117 | . = ALIGN(4); | 128 | . = ALIGN(4); |
@@ -145,7 +156,11 @@ SECTIONS | |||
145 | _etext = .; /* End of text and rodata section */ | 156 | _etext = .; /* End of text and rodata section */ |
146 | 157 | ||
147 | #ifndef CONFIG_XIP_KERNEL | 158 | #ifndef CONFIG_XIP_KERNEL |
159 | # ifdef CONFIG_ARM_KERNMEM_PERMS | ||
160 | . = ALIGN(1<<SECTION_SHIFT); | ||
161 | # else | ||
148 | . = ALIGN(PAGE_SIZE); | 162 | . = ALIGN(PAGE_SIZE); |
163 | # endif | ||
149 | __init_begin = .; | 164 | __init_begin = .; |
150 | #endif | 165 | #endif |
151 | /* | 166 | /* |
@@ -219,7 +234,11 @@ SECTIONS | |||
219 | __data_loc = ALIGN(4); /* location in binary */ | 234 | __data_loc = ALIGN(4); /* location in binary */ |
220 | . = PAGE_OFFSET + TEXT_OFFSET; | 235 | . = PAGE_OFFSET + TEXT_OFFSET; |
221 | #else | 236 | #else |
237 | #ifdef CONFIG_ARM_KERNMEM_PERMS | ||
238 | . = ALIGN(1<<SECTION_SHIFT); | ||
239 | #else | ||
222 | . = ALIGN(THREAD_SIZE); | 240 | . = ALIGN(THREAD_SIZE); |
241 | #endif | ||
223 | __init_end = .; | 242 | __init_end = .; |
224 | __data_loc = .; | 243 | __data_loc = .; |
225 | #endif | 244 | #endif |
diff --git a/arch/arm/kernel/xscale-cp0.c b/arch/arm/kernel/xscale-cp0.c index e42adc6bcdb1..bdbb8853a19b 100644 --- a/arch/arm/kernel/xscale-cp0.c +++ b/arch/arm/kernel/xscale-cp0.c | |||
@@ -157,15 +157,14 @@ static int __init xscale_cp0_init(void) | |||
157 | 157 | ||
158 | if (cpu_has_iwmmxt()) { | 158 | if (cpu_has_iwmmxt()) { |
159 | #ifndef CONFIG_IWMMXT | 159 | #ifndef CONFIG_IWMMXT |
160 | printk(KERN_WARNING "CAUTION: XScale iWMMXt coprocessor " | 160 | pr_warn("CAUTION: XScale iWMMXt coprocessor detected, but kernel support is missing.\n"); |
161 | "detected, but kernel support is missing.\n"); | ||
162 | #else | 161 | #else |
163 | printk(KERN_INFO "XScale iWMMXt coprocessor detected.\n"); | 162 | pr_info("XScale iWMMXt coprocessor detected.\n"); |
164 | elf_hwcap |= HWCAP_IWMMXT; | 163 | elf_hwcap |= HWCAP_IWMMXT; |
165 | thread_register_notifier(&iwmmxt_notifier_block); | 164 | thread_register_notifier(&iwmmxt_notifier_block); |
166 | #endif | 165 | #endif |
167 | } else { | 166 | } else { |
168 | printk(KERN_INFO "XScale DSP coprocessor detected.\n"); | 167 | pr_info("XScale DSP coprocessor detected.\n"); |
169 | thread_register_notifier(&dsp_notifier_block); | 168 | thread_register_notifier(&dsp_notifier_block); |
170 | cp_access |= 1; | 169 | cp_access |= 1; |
171 | } | 170 | } |