Optimizations for Windows

- Set opt_lg_chunk based on run-time OS setting
- Verify LG_PAGE is compatible with run-time OS setting
- When targeting Windows Vista or newer, use SRWLOCK instead of CRITICAL_SECTION
- When targeting Windows Vista or newer, statically initialize init_lock
This commit is contained in:
Matthijs 2015-06-25 22:53:58 +02:00
parent 241abc601b
commit a1aaf949a5
4 changed files with 36 additions and 2 deletions

View File

@ -26,7 +26,11 @@ typedef struct malloc_mutex_s malloc_mutex_t;
struct malloc_mutex_s { struct malloc_mutex_s {
#ifdef _WIN32 #ifdef _WIN32
# if _WIN32_WINNT >= 0x0600
SRWLOCK lock;
# else
CRITICAL_SECTION lock; CRITICAL_SECTION lock;
# endif
#elif (defined(JEMALLOC_OSSPIN)) #elif (defined(JEMALLOC_OSSPIN))
OSSpinLock lock; OSSpinLock lock;
#elif (defined(JEMALLOC_MUTEX_INIT_CB)) #elif (defined(JEMALLOC_MUTEX_INIT_CB))
@ -70,7 +74,11 @@ malloc_mutex_lock(malloc_mutex_t *mutex)
if (isthreaded) { if (isthreaded) {
#ifdef _WIN32 #ifdef _WIN32
# if _WIN32_WINNT >= 0x0600
AcquireSRWLockExclusive(&mutex->lock);
# else
EnterCriticalSection(&mutex->lock); EnterCriticalSection(&mutex->lock);
# endif
#elif (defined(JEMALLOC_OSSPIN)) #elif (defined(JEMALLOC_OSSPIN))
OSSpinLockLock(&mutex->lock); OSSpinLockLock(&mutex->lock);
#else #else
@ -85,7 +93,11 @@ malloc_mutex_unlock(malloc_mutex_t *mutex)
if (isthreaded) { if (isthreaded) {
#ifdef _WIN32 #ifdef _WIN32
# if _WIN32_WINNT >= 0x0600
ReleaseSRWLockExclusive(&mutex->lock);
# else
LeaveCriticalSection(&mutex->lock); LeaveCriticalSection(&mutex->lock);
# endif
#elif (defined(JEMALLOC_OSSPIN)) #elif (defined(JEMALLOC_OSSPIN))
OSSpinLockUnlock(&mutex->lock); OSSpinLockUnlock(&mutex->lock);
#else #else

View File

@ -5,7 +5,7 @@
/* Data. */ /* Data. */
const char *opt_dss = DSS_DEFAULT; const char *opt_dss = DSS_DEFAULT;
size_t opt_lg_chunk = LG_CHUNK_DEFAULT; size_t opt_lg_chunk = 0;
/* Used exclusively for gdump triggering. */ /* Used exclusively for gdump triggering. */
static size_t curchunks; static size_t curchunks;
@ -535,6 +535,21 @@ chunks_rtree_node_alloc(size_t nelms)
bool bool
chunk_boot(void) chunk_boot(void)
{ {
#ifdef _WIN32
SYSTEM_INFO info;
GetSystemInfo(&info);
/* Verify actual page size is equal to or an integral multiple of configured page size */
if (info.dwPageSize & ((1U << LG_PAGE) - 1))
return (true);
/* Configure chunksize (if not set) to match granularity (usually 64K), so pages_map will always take fast path */
if (!opt_lg_chunk)
opt_lg_chunk = ffs((int)info.dwAllocationGranularity) - 1;
#else
if (!opt_lg_chunk)
opt_lg_chunk = LG_CHUNK_DEFAULT;
#endif
/* Set variables according to the value of opt_lg_chunk. */ /* Set variables according to the value of opt_lg_chunk. */
chunksize = (ZU(1) << opt_lg_chunk); chunksize = (ZU(1) << opt_lg_chunk);

View File

@ -175,6 +175,9 @@ static bool malloc_initializer = NO_INITIALIZER;
/* Used to avoid initialization races. */ /* Used to avoid initialization races. */
#ifdef _WIN32 #ifdef _WIN32
#if _WIN32_WINNT >= 0x0600
static malloc_mutex_t init_lock = SRWLOCK_INIT;
#else
static malloc_mutex_t init_lock; static malloc_mutex_t init_lock;
JEMALLOC_ATTR(constructor) JEMALLOC_ATTR(constructor)
@ -190,7 +193,7 @@ _init_init_lock(void)
JEMALLOC_SECTION(".CRT$XCU") JEMALLOC_ATTR(used) JEMALLOC_SECTION(".CRT$XCU") JEMALLOC_ATTR(used)
static const void (WINAPI *init_init_lock)(void) = _init_init_lock; static const void (WINAPI *init_init_lock)(void) = _init_init_lock;
#endif #endif
#endif
#else #else
static malloc_mutex_t init_lock = MALLOC_MUTEX_INITIALIZER; static malloc_mutex_t init_lock = MALLOC_MUTEX_INITIALIZER;
#endif #endif

View File

@ -73,9 +73,13 @@ malloc_mutex_init(malloc_mutex_t *mutex)
{ {
#ifdef _WIN32 #ifdef _WIN32
# if _WIN32_WINNT >= 0x0600
InitializeSRWLock(&mutex->lock);
# else
if (!InitializeCriticalSectionAndSpinCount(&mutex->lock, if (!InitializeCriticalSectionAndSpinCount(&mutex->lock,
_CRT_SPINCOUNT)) _CRT_SPINCOUNT))
return (true); return (true);
# endif
#elif (defined(JEMALLOC_OSSPIN)) #elif (defined(JEMALLOC_OSSPIN))
mutex->lock = 0; mutex->lock = 0;
#elif (defined(JEMALLOC_MUTEX_INIT_CB)) #elif (defined(JEMALLOC_MUTEX_INIT_CB))