diff options
Diffstat (limited to 'src/backend/storage/lmgr/spin.c')
-rw-r--r-- | src/backend/storage/lmgr/spin.c | 50 |
1 files changed, 31 insertions, 19 deletions
diff --git a/src/backend/storage/lmgr/spin.c b/src/backend/storage/lmgr/spin.c index 08782178de9..3d116bc7a2e 100644 --- a/src/backend/storage/lmgr/spin.c +++ b/src/backend/storage/lmgr/spin.c @@ -29,6 +29,18 @@ #include "storage/spin.h" +PGSemaphore SpinlockSemaArray; + +/* + * Report the amount of shared memory needed to store semaphores for spinlock + * support. + */ +Size +SpinlockSemaSize(void) +{ + return SpinlockSemas() * sizeof(PGSemaphoreData); +} + #ifdef HAVE_SPINLOCKS /* @@ -52,22 +64,20 @@ SpinlockSemas(void) int SpinlockSemas(void) { - int nsemas; - - /* - * It would be cleaner to distribute this logic into the affected modules, - * similar to the way shmem space estimation is handled. - * - * For now, though, there are few enough users of spinlocks that we just - * keep the knowledge here. - */ - nsemas = NumLWLocks(); /* one for each lwlock */ - nsemas += NBuffers; /* one for each buffer header */ - nsemas += max_wal_senders; /* one for each wal sender process */ - nsemas += num_xloginsert_slots; /* one for each WAL insertion slot */ - nsemas += 30; /* plus a bunch for other small-scale use */ - - return nsemas; + return NUM_SPINLOCK_SEMAPHORES; +} + +/* + * Initialize semaphores. + */ +extern void +SpinlockSemaInit(PGSemaphore spinsemas) +{ + int i; + + for (i = 0; i < NUM_SPINLOCK_SEMAPHORES; ++i) + PGSemaphoreCreate(&spinsemas[i]); + SpinlockSemaArray = spinsemas; } /* @@ -77,13 +87,15 @@ SpinlockSemas(void) void s_init_lock_sema(volatile slock_t *lock) { - PGSemaphoreCreate((PGSemaphore) lock); + static int counter = 0; + + *lock = (++counter) % NUM_SPINLOCK_SEMAPHORES; } void s_unlock_sema(volatile slock_t *lock) { - PGSemaphoreUnlock((PGSemaphore) lock); + PGSemaphoreUnlock(&SpinlockSemaArray[*lock]); } bool @@ -98,7 +110,7 @@ int tas_sema(volatile slock_t *lock) { /* Note that TAS macros return 0 if *success* */ - return !PGSemaphoreTryLock((PGSemaphore) lock); + return !PGSemaphoreTryLock(&SpinlockSemaArray[*lock]); } #endif /* !HAVE_SPINLOCKS */ |