Merge commit 'refs/top-bases/linux-kernel-mem' into linux-kernel-mem

This commit is contained in:
Brian Behlendorf 2010-07-23 11:42:48 -07:00
commit fd7a0e109c
4 changed files with 72 additions and 1 deletions

View File

@ -0,0 +1,56 @@
dnl #
dnl # Check if the glibc NPTL threading implementation includes the guard area
dnl # within the stack size allocation, rather than allocating extra space at
dnl # the end of the stack, as POSIX.1 requires.
dnl #
AC_DEFUN([ZFS_AC_CONFIG_USER_STACK_GUARD], [
AC_MSG_CHECKING([whether pthread stack includes guard])
saved_CFLAGS="$CFLAGS"
CFLAGS="-fstack-check"
saved_LDFLAGS="$LDFLAGS"
LDFLAGS="-lpthread"
AC_RUN_IFELSE(AC_LANG_PROGRAM(
[
#include <pthread.h>
#include <sys/resource.h>
#include <unistd.h>
#include <bits/local_lim.h>
#define PAGESIZE (sysconf(_SC_PAGESIZE))
#define STACK_SIZE 8192
#define BUFSIZE 4096
void * func(void *arg)
{
char buf[[[BUFSIZE]]];
}
],
[
pthread_t tid;
pthread_attr_t attr;
struct rlimit l;
l.rlim_cur = 0;
l.rlim_max = 0;
setrlimit(RLIMIT_CORE, &l);
pthread_attr_init(&attr);
pthread_attr_setstacksize(&attr, PTHREAD_STACK_MIN + STACK_SIZE);
pthread_attr_setguardsize(&attr, PAGESIZE);
pthread_create(&tid, &attr, func, NULL);
pthread_join(tid, NULL);
]),
[
AC_MSG_RESULT([no])
],
[
AC_DEFINE([NPTL_GUARD_WITHIN_STACK], 1,
[Define to 1 if NPTL threading implementation includes
guard area in stack allocation])
AC_MSG_RESULT([yes])
])
CFLAGS="$saved_CFLAGS"
LDFLAGS="$saved_LDFLAGS"
])

View File

@ -9,4 +9,5 @@ AC_DEFUN([ZFS_AC_CONFIG_USER], [
ZFS_AC_CONFIG_USER_LIBUUID ZFS_AC_CONFIG_USER_LIBUUID
ZFS_AC_CONFIG_USER_LIBBLKID ZFS_AC_CONFIG_USER_LIBBLKID
ZFS_AC_CONFIG_USER_FRAME_LARGER_THAN ZFS_AC_CONFIG_USER_FRAME_LARGER_THAN
ZFS_AC_CONFIG_USER_STACK_GUARD
]) ])

View File

@ -211,6 +211,12 @@ _NOTE(CONSTCOND) } while (0)
#define STACK_SIZE 24576 /* Solaris */ #define STACK_SIZE 24576 /* Solaris */
#endif #endif
#ifdef NPTL_GUARD_WITHIN_STACK
#define EXTRA_GUARD_BYTES PAGESIZE
#else
#define EXTRA_GUARD_BYTES 0
#endif
/* in libzpool, p0 exists only to have its address taken */ /* in libzpool, p0 exists only to have its address taken */
typedef struct proc { typedef struct proc {
uintptr_t this_is_never_used_dont_dereference_it; uintptr_t this_is_never_used_dont_dereference_it;

View File

@ -162,8 +162,16 @@ zk_thread_create(caddr_t stk, size_t stksize, thread_func_t func, void *arg,
* kernel space. PTHREAD_STACK_MIN is the minimum stack * kernel space. PTHREAD_STACK_MIN is the minimum stack
* required for a NULL procedure in user space and is added * required for a NULL procedure in user space and is added
* in to the stack requirements. * in to the stack requirements.
*
* Some buggy NPTL threading implementations include the
* guard area within the stack size allocations. In
* this case we allocate an extra page to account for the
* guard area since we only have two pages of usable stack
* on Linux.
*/ */
stack = PTHREAD_STACK_MIN + MAX(stksize, STACK_SIZE);
stack = PTHREAD_STACK_MIN + MAX(stksize, STACK_SIZE) +
EXTRA_GUARD_BYTES;
VERIFY3S(pthread_attr_init(&attr), ==, 0); VERIFY3S(pthread_attr_init(&attr), ==, 0);
VERIFY3S(pthread_attr_setstacksize(&attr, stack), ==, 0); VERIFY3S(pthread_attr_setstacksize(&attr, stack), ==, 0);