summaryrefslogtreecommitdiffstats
path: root/arch/arm/kernel/process.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/arm/kernel/process.c')
-rw-r--r--arch/arm/kernel/process.c42
1 files changed, 37 insertions, 5 deletions
diff --git a/arch/arm/kernel/process.c b/arch/arm/kernel/process.c
index a4a9cc88bec..401e38be1f7 100644
--- a/arch/arm/kernel/process.c
+++ b/arch/arm/kernel/process.c
@@ -28,7 +28,9 @@
#include <linux/tick.h>
#include <linux/utsname.h>
#include <linux/uaccess.h>
+#include <linux/random.h>
+#include <asm/cacheflush.h>
#include <asm/leds.h>
#include <asm/processor.h>
#include <asm/system.h>
@@ -36,6 +38,12 @@
#include <asm/stacktrace.h>
#include <asm/mach/time.h>
+#ifdef CONFIG_CC_STACKPROTECTOR
+#include <linux/stackprotector.h>
+unsigned long __stack_chk_guard __read_mostly;
+EXPORT_SYMBOL(__stack_chk_guard);
+#endif
+
static const char *processor_modes[] = {
"USER_26", "FIQ_26" , "IRQ_26" , "SVC_26" , "UK4_26" , "UK5_26" , "UK6_26" , "UK7_26" ,
"UK8_26" , "UK9_26" , "UK10_26", "UK11_26", "UK12_26", "UK13_26", "UK14_26", "UK15_26",
@@ -84,10 +92,9 @@ __setup("hlt", hlt_setup);
void arm_machine_restart(char mode, const char *cmd)
{
- /*
- * Clean and disable cache, and turn off interrupts
- */
- cpu_proc_fin();
+ /* Disable interrupts first */
+ local_irq_disable();
+ local_fiq_disable();
/*
* Tell the mm system that we are going to reboot -
@@ -96,6 +103,15 @@ void arm_machine_restart(char mode, const char *cmd)
*/
setup_mm_for_reboot(mode);
+ /* Clean and invalidate caches */
+ flush_cache_all();
+
+ /* Turn off caching */
+ cpu_proc_fin();
+
+ /* Push out any further dirty data, and ensure cache is empty */
+ flush_cache_all();
+
/*
* Now call the architecture specific reboot code.
*/
@@ -189,19 +205,29 @@ int __init reboot_setup(char *str)
__setup("reboot=", reboot_setup);
-void machine_halt(void)
+void machine_shutdown(void)
{
+#ifdef CONFIG_SMP
+ smp_send_stop();
+#endif
}
+void machine_halt(void)
+{
+ machine_shutdown();
+ while (1);
+}
void machine_power_off(void)
{
+ machine_shutdown();
if (pm_power_off)
pm_power_off();
}
void machine_restart(char *cmd)
{
+ machine_shutdown();
arm_pm_restart(reboot_mode, cmd);
}
@@ -426,3 +452,9 @@ unsigned long get_wchan(struct task_struct *p)
} while (count ++ < 16);
return 0;
}
+
+unsigned long arch_randomize_brk(struct mm_struct *mm)
+{
+ unsigned long range_end = mm->brk + 0x02000000;
+ return randomize_range(mm->brk, range_end, 0) ? : mm->brk;
+}