aboutsummaryrefslogtreecommitdiffstats
path: root/arch/mips
diff options
context:
space:
mode:
authorGregory Fong <gregory.0xf0@gmail.com>2013-06-12 13:08:54 -0400
committerRalf Baechle <ralf@linux-mips.org>2013-07-01 09:10:48 -0400
commit36ecafc5ad17861e2bc1fb12af4cc97680e25942 (patch)
tree8b1094782049660b366b417119d34a5a519e0c95 /arch/mips
parent23df34155b29674465813b327647cd79722aa659 (diff)
MIPS: initial stack protector support
Implements basic stack protector support based on ARM version in c743f38013aeff58ef6252601e397b5ba281c633 , with Kconfig option, constant canary value set at boot time, and script to check if compiler actually supports stack protector. Tested by creating a kernel module that writes past end of char[]. Signed-off-by: Gregory Fong <gregory.0xf0@gmail.com> Cc: linux-mips@linux-mips.org Cc: Filippo Arcidiacono <filippo.arcidiacono@st.com> Cc: Carmelo Amoroso <carmelo.amoroso@st.com> Patchwork: https://patchwork.linux-mips.org/patch/5448/ Signed-off-by: Ralf Baechle <ralf@linux-mips.org>
Diffstat (limited to 'arch/mips')
-rw-r--r--arch/mips/Kconfig13
-rw-r--r--arch/mips/Makefile4
-rw-r--r--arch/mips/include/asm/stackprotector.h40
-rw-r--r--arch/mips/kernel/process.c6
4 files changed, 63 insertions, 0 deletions
diff --git a/arch/mips/Kconfig b/arch/mips/Kconfig
index 69bf31062ca4..6dbeb273afc6 100644
--- a/arch/mips/Kconfig
+++ b/arch/mips/Kconfig
@@ -2367,6 +2367,19 @@ config SECCOMP
2367 2367
2368 If unsure, say Y. Only embedded should say N here. 2368 If unsure, say Y. Only embedded should say N here.
2369 2369
2370config CC_STACKPROTECTOR
2371 bool "Enable -fstack-protector buffer overflow detection (EXPERIMENTAL)"
2372 help
2373 This option turns on the -fstack-protector GCC feature. This
2374 feature puts, at the beginning of functions, a canary value on
2375 the stack just before the return address, and validates
2376 the value just before actually returning. Stack based buffer
2377 overflows (that need to overwrite this return address) now also
2378 overwrite the canary, which gets detected and the attack is then
2379 neutralized via a kernel panic.
2380
2381 This feature requires gcc version 4.2 or above.
2382
2370config USE_OF 2383config USE_OF
2371 bool 2384 bool
2372 select OF 2385 select OF
diff --git a/arch/mips/Makefile b/arch/mips/Makefile
index dd58a04ef4bc..37f9ef324f2f 100644
--- a/arch/mips/Makefile
+++ b/arch/mips/Makefile
@@ -227,6 +227,10 @@ KBUILD_CPPFLAGS += -DDATAOFFSET=$(if $(dataoffset-y),$(dataoffset-y),0)
227 227
228LDFLAGS += -m $(ld-emul) 228LDFLAGS += -m $(ld-emul)
229 229
230ifdef CONFIG_CC_STACKPROTECTOR
231 KBUILD_CFLAGS += -fstack-protector
232endif
233
230ifdef CONFIG_MIPS 234ifdef CONFIG_MIPS
231CHECKFLAGS += $(shell $(CC) $(KBUILD_CFLAGS) -dM -E -x c /dev/null | \ 235CHECKFLAGS += $(shell $(CC) $(KBUILD_CFLAGS) -dM -E -x c /dev/null | \
232 egrep -vw '__GNUC_(|MINOR_|PATCHLEVEL_)_' | \ 236 egrep -vw '__GNUC_(|MINOR_|PATCHLEVEL_)_' | \
diff --git a/arch/mips/include/asm/stackprotector.h b/arch/mips/include/asm/stackprotector.h
new file mode 100644
index 000000000000..eb9b1035e926
--- /dev/null
+++ b/arch/mips/include/asm/stackprotector.h
@@ -0,0 +1,40 @@
1/*
2 * GCC stack protector support.
3 *
4 * (This is directly adopted from the ARM implementation)
5 *
6 * Stack protector works by putting predefined pattern at the start of
7 * the stack frame and verifying that it hasn't been overwritten when
8 * returning from the function. The pattern is called stack canary
9 * and gcc expects it to be defined by a global variable called
10 * "__stack_chk_guard" on MIPS. This unfortunately means that on SMP
11 * we cannot have a different canary value per task.
12 */
13
14#ifndef _ASM_STACKPROTECTOR_H
15#define _ASM_STACKPROTECTOR_H 1
16
17#include <linux/random.h>
18#include <linux/version.h>
19
20extern unsigned long __stack_chk_guard;
21
22/*
23 * Initialize the stackprotector canary value.
24 *
25 * NOTE: this must only be called from functions that never return,
26 * and it must always be inlined.
27 */
28static __always_inline void boot_init_stack_canary(void)
29{
30 unsigned long canary;
31
32 /* Try to get a semi random initial value. */
33 get_random_bytes(&canary, sizeof(canary));
34 canary ^= LINUX_VERSION_CODE;
35
36 current->stack_canary = canary;
37 __stack_chk_guard = current->stack_canary;
38}
39
40#endif /* _ASM_STACKPROTECTOR_H */
diff --git a/arch/mips/kernel/process.c b/arch/mips/kernel/process.c
index c6a041d9d05d..7d62894f7e23 100644
--- a/arch/mips/kernel/process.c
+++ b/arch/mips/kernel/process.c
@@ -201,6 +201,12 @@ int dump_task_fpu(struct task_struct *t, elf_fpregset_t *fpr)
201 return 1; 201 return 1;
202} 202}
203 203
204#ifdef CONFIG_CC_STACKPROTECTOR
205#include <linux/stackprotector.h>
206unsigned long __stack_chk_guard __read_mostly;
207EXPORT_SYMBOL(__stack_chk_guard);
208#endif
209
204/* 210/*
205 * 211 *
206 */ 212 */