mirror of
https://review.haiku-os.org/haiku
synced 2024-11-23 07:18:40 +01:00
Implement stack protection support
this adds kernel & libroot stack protector hooks. it uses /dev/random in userspace. A configure option --enable-stack-protector is added to activate -fstack-protector on selected system components (ATM apps, kits, servers). Change-Id: If3a2920ba9aa0a85eaff4ba6778947f8c76ade31 Reviewed-on: https://review.haiku-os.org/c/haiku/+/3895 Reviewed-by: Adrien Destugues <pulkomandy@gmail.com>
This commit is contained in:
parent
409d65c0d6
commit
04be20a75a
@ -600,6 +600,16 @@ rule ArchitectureSetupWarnings architecture
|
||||
}
|
||||
}
|
||||
|
||||
rule EnableStackProtector dirTokens : scope {
|
||||
# enable stack protector, if requested
|
||||
if $(HAIKU_USE_STACK_PROTECTOR) = 1 {
|
||||
AppendToConfigVar CCFLAGS : HAIKU_TOP $(dirTokens) :
|
||||
-fstack-protector : $(scope) ;
|
||||
AppendToConfigVar C++FLAGS : HAIKU_TOP $(dirTokens) :
|
||||
-fstack-protector : $(scope) ;
|
||||
}
|
||||
}
|
||||
|
||||
# Work-around for GCC 2 problem -- despite -Wno-multichar it reports
|
||||
# multichar warnings in headers/private/kernel/debugger_keymaps.h included
|
||||
# by src/system/kernel/arch/x86/arch_debug_console.cpp.
|
||||
@ -746,6 +756,12 @@ rule ArchitectureSetupWarnings architecture
|
||||
EnableWerror src system libroot posix locale ;
|
||||
EnableWerror src system libroot posix wchar ;
|
||||
EnableWerror src system runtime_loader ;
|
||||
|
||||
EnableStackProtector src apps ;
|
||||
EnableStackProtector src kits ;
|
||||
EnableStackProtector src preferences ;
|
||||
EnableStackProtector src servers ;
|
||||
EnableStackProtector src system kernel ;
|
||||
}
|
||||
|
||||
|
||||
|
2
configure
vendored
2
configure
vendored
@ -92,6 +92,7 @@ options:
|
||||
--with-gdb <gdb sources dir>
|
||||
specify the path to a GDB source dir, to build
|
||||
GDB for each arch we build the cross-tools for.
|
||||
--use-stack-protector Build with stack protection enabled
|
||||
|
||||
environment variables:
|
||||
CC The host compiler. Defaults to "gcc".
|
||||
@ -803,6 +804,7 @@ while [ $# -gt 0 ] ; do
|
||||
--no-full-xattr)HAIKU_HOST_USE_XATTR=0; shift 1;;
|
||||
--no-xattr) HAIKU_HOST_USE_XATTR_REF=0; shift 1;;
|
||||
--with-gdb) gdbSources=$2; shift 2;;
|
||||
--use-stack-protector) HAIKU_USE_STACK_PROTECTOR=1; shift 1;;
|
||||
*) echo Invalid argument: \`$1\'; exit 1;;
|
||||
esac
|
||||
done
|
||||
|
12
headers/private/kernel/stack_protector.h
Normal file
12
headers/private/kernel/stack_protector.h
Normal file
@ -0,0 +1,12 @@
|
||||
/*
|
||||
* Copyright 2021, Jérôme Duval, jerome.duval@gmail.com.
|
||||
* Distributed under the terms of the MIT License.
|
||||
*/
|
||||
#ifndef _KERNEL_STACK_PROTECTOR_H
|
||||
#define _KERNEL_STACK_PROTECTOR_H
|
||||
|
||||
|
||||
void stack_protector_init();
|
||||
|
||||
|
||||
#endif /* _KERNEL_STACK_PROTECTOR_H */
|
@ -55,6 +55,7 @@ void __reinit_pwd_backend_after_fork(void);
|
||||
int32 __arch_get_stack_trace(addr_t* returnAddresses, int32 maxCount,
|
||||
int32 skipFrames, addr_t stackBase, addr_t stackEnd);
|
||||
|
||||
void __init_stack_protector(void);
|
||||
void __set_stack_protection(void);
|
||||
|
||||
|
||||
|
@ -47,6 +47,7 @@ KernelMergeObject kernel_core.o :
|
||||
sem.cpp
|
||||
shutdown.cpp
|
||||
signal.cpp
|
||||
stack_protector.cpp
|
||||
system_info.cpp
|
||||
smp.cpp
|
||||
syscalls.cpp
|
||||
|
@ -51,6 +51,7 @@
|
||||
#include <real_time_clock.h>
|
||||
#include <sem.h>
|
||||
#include <smp.h>
|
||||
#include <stack_protector.h>
|
||||
#include <system_profiler.h>
|
||||
#include <team.h>
|
||||
#include <timer.h>
|
||||
@ -204,6 +205,8 @@ _start(kernel_args *bootKernelArgs, int currentCPU)
|
||||
thread_init(&sKernelArgs);
|
||||
TRACE("init kernel daemons\n");
|
||||
kernel_daemon_init();
|
||||
TRACE("init stack protector\n");
|
||||
stack_protector_init();
|
||||
arch_platform_init_post_thread(&sKernelArgs);
|
||||
|
||||
TRACE("init I/O interrupts\n");
|
||||
|
34
src/system/kernel/stack_protector.cpp
Normal file
34
src/system/kernel/stack_protector.cpp
Normal file
@ -0,0 +1,34 @@
|
||||
/*
|
||||
* Copyright 2021, Jérôme Duval, jerome.duval@gmail.com.
|
||||
* Distributed under the terms of the MIT License.
|
||||
*/
|
||||
|
||||
|
||||
#include <sys/cdefs.h>
|
||||
|
||||
#include <SupportDefs.h>
|
||||
|
||||
#include <util/Random.h>
|
||||
|
||||
|
||||
extern "C" {
|
||||
|
||||
long __stack_chk_guard;
|
||||
|
||||
|
||||
void
|
||||
__stack_chk_fail()
|
||||
{
|
||||
panic("stack smashing detected\n");
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
stack_protector_init()
|
||||
{
|
||||
__stack_chk_guard = secure_get_random<long>();
|
||||
}
|
||||
|
@ -80,6 +80,7 @@ initialize_before(image_id imageID)
|
||||
__init_heap();
|
||||
__init_env_post_heap();
|
||||
__init_pwd_backend();
|
||||
__init_stack_protector();
|
||||
__set_stack_protection();
|
||||
}
|
||||
|
||||
|
@ -34,6 +34,7 @@ for architectureObject in [ MultiArchSubDirSetup ] {
|
||||
port.c
|
||||
scheduler.c
|
||||
sem.c
|
||||
stack_protector.cpp
|
||||
system_info.cpp
|
||||
system_revision.c
|
||||
team.c
|
||||
|
58
src/system/libroot/os/stack_protector.cpp
Normal file
58
src/system/libroot/os/stack_protector.cpp
Normal file
@ -0,0 +1,58 @@
|
||||
/*
|
||||
* Copyright 2021, Jérôme Duval, jerome.duval@gmail.com.
|
||||
* Distributed under the terms of the MIT License.
|
||||
*/
|
||||
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <signal.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/cdefs.h>
|
||||
|
||||
|
||||
extern "C" {
|
||||
|
||||
long __stack_chk_guard = 0;
|
||||
|
||||
|
||||
void
|
||||
__init_stack_protector()
|
||||
{
|
||||
if (__stack_chk_guard != 0)
|
||||
return;
|
||||
|
||||
bool done = false;
|
||||
int fd = open("/dev/random", O_RDONLY, 0);
|
||||
if (fd >= 0) {
|
||||
done = read(fd, &__stack_chk_guard, sizeof(__stack_chk_guard))
|
||||
== sizeof(__stack_chk_guard);
|
||||
close(fd);
|
||||
}
|
||||
|
||||
if (!done) {
|
||||
((unsigned char *)(void *)__stack_chk_guard)[0] = 0;
|
||||
((unsigned char *)(void *)__stack_chk_guard)[1] = 0;
|
||||
((unsigned char *)(void *)__stack_chk_guard)[2] = '\n';
|
||||
((unsigned char *)(void *)__stack_chk_guard)[3] = 0xff;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
__stack_chk_fail()
|
||||
{
|
||||
sigset_t mask;
|
||||
sigfillset(&mask);
|
||||
sigdelset(&mask, SIGABRT);
|
||||
sigprocmask(SIG_BLOCK, &mask, NULL);
|
||||
|
||||
abort();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
#if __GNUC__ >= 4
|
||||
extern "C" void __stack_chk_fail_local() __attribute__((visibility("hidden")));
|
||||
__weak_reference(__stack_chk_fail, __stack_chk_fail_local);
|
||||
#endif
|
@ -28,6 +28,14 @@ SimpleTest get_cpu_num_test :
|
||||
get_cpu_num_test.cpp
|
||||
;
|
||||
|
||||
|
||||
CCFLAGS += -fstack-protector ;
|
||||
SimpleTest stack_protector_test :
|
||||
stack_protector_test.c
|
||||
;
|
||||
|
||||
|
||||
|
||||
# Tell Jam where to find these sources
|
||||
SEARCH on [ FGristFiles
|
||||
driver_settings.cpp
|
||||
|
16
src/tests/system/libroot/os/stack_protector_test.c
Normal file
16
src/tests/system/libroot/os/stack_protector_test.c
Normal file
@ -0,0 +1,16 @@
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
void get_input(char *data)
|
||||
{
|
||||
strcpy(data, "01234567");
|
||||
}
|
||||
|
||||
|
||||
int main(void)
|
||||
{
|
||||
char buffer[8];
|
||||
get_input(buffer);
|
||||
return buffer[0];
|
||||
}
|
Loading…
Reference in New Issue
Block a user