mirror of
https://github.com/postgres/postgres.git
synced 2025-09-03 15:22:11 +03:00
Implement new 'lightweight lock manager' that's intermediate between
existing lock manager and spinlocks: it understands exclusive vs shared lock but has few other fancy features. Replace most uses of spinlocks with lightweight locks. All remaining uses of spinlocks have very short lock hold times (a few dozen instructions), so tweak spinlock backoff code to work efficiently given this assumption. All per my proposal on pghackers 26-Sep-01.
This commit is contained in:
@@ -1,42 +1,77 @@
|
||||
/*-------------------------------------------------------------------------
|
||||
*
|
||||
* spin.h
|
||||
* synchronization routines
|
||||
* Hardware-independent implementation of spinlocks.
|
||||
*
|
||||
*
|
||||
* The hardware-independent interface to spinlocks is defined by the
|
||||
* typedef "slock_t" and these macros:
|
||||
*
|
||||
* void SpinLockInit(slock_t *lock)
|
||||
* Initialize a spinlock (to the unlocked state).
|
||||
*
|
||||
* void SpinLockAcquire(slock_t *lock)
|
||||
* Acquire a spinlock, waiting if necessary.
|
||||
* Time out and abort() if unable to acquire the lock in a
|
||||
* "reasonable" amount of time --- typically ~ 1 minute.
|
||||
* Cancel/die interrupts are held off until the lock is released.
|
||||
*
|
||||
* void SpinLockRelease(slock_t *lock)
|
||||
* Unlock a previously acquired lock.
|
||||
* Release the cancel/die interrupt holdoff.
|
||||
*
|
||||
* void SpinLockAcquire_NoHoldoff(slock_t *lock)
|
||||
* void SpinLockRelease_NoHoldoff(slock_t *lock)
|
||||
* Same as above, except no interrupt holdoff processing is done.
|
||||
* This pair of macros may be used when there is a surrounding
|
||||
* interrupt holdoff.
|
||||
*
|
||||
* bool SpinLockFree(slock_t *lock)
|
||||
* Tests if the lock is free. Returns TRUE if free, FALSE if locked.
|
||||
* This does *not* change the state of the lock.
|
||||
*
|
||||
* Callers must beware that the macro argument may be evaluated multiple
|
||||
* times!
|
||||
*
|
||||
* The macros are implemented in terms of hardware-dependent macros
|
||||
* supplied by s_lock.h.
|
||||
*
|
||||
*
|
||||
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
|
||||
* Portions Copyright (c) 1994, Regents of the University of California
|
||||
*
|
||||
* $Id: spin.h,v 1.15 2001/03/22 04:01:09 momjian Exp $
|
||||
* $Id: spin.h,v 1.16 2001/09/29 04:02:27 tgl Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
#ifndef SPIN_H
|
||||
#define SPIN_H
|
||||
|
||||
#include "storage/ipc.h"
|
||||
|
||||
/*
|
||||
* two implementations of spin locks
|
||||
*
|
||||
* Where TAS instruction is available: real spin locks.
|
||||
* See src/storage/ipc/s_lock.c for details.
|
||||
*
|
||||
* Otherwise: fake spin locks using semaphores. see spin.c
|
||||
*/
|
||||
|
||||
typedef int SPINLOCK;
|
||||
|
||||
#ifdef LOCK_DEBUG
|
||||
extern bool Trace_spinlocks;
|
||||
|
||||
#endif
|
||||
#include "storage/s_lock.h"
|
||||
#include "miscadmin.h"
|
||||
|
||||
|
||||
extern int SLockShmemSize(void);
|
||||
extern void CreateSpinlocks(PGShmemHeader *seghdr);
|
||||
#define SpinLockInit(lock) S_INIT_LOCK(lock)
|
||||
|
||||
extern void SpinAcquire(SPINLOCK lockid);
|
||||
extern void SpinRelease(SPINLOCK lockid);
|
||||
#define SpinLockAcquire(lock) \
|
||||
do { \
|
||||
HOLD_INTERRUPTS(); \
|
||||
S_LOCK(lock); \
|
||||
} while (0)
|
||||
|
||||
#define SpinLockAcquire_NoHoldoff(lock) S_LOCK(lock)
|
||||
|
||||
#define SpinLockRelease(lock) \
|
||||
do { \
|
||||
S_UNLOCK(lock); \
|
||||
RESUME_INTERRUPTS(); \
|
||||
} while (0)
|
||||
|
||||
#define SpinLockRelease_NoHoldoff(lock) S_UNLOCK(lock)
|
||||
|
||||
#define SpinLockFree(lock) S_LOCK_FREE(lock)
|
||||
|
||||
|
||||
extern void CreateSpinlocks(void);
|
||||
|
||||
#endif /* SPIN_H */
|
||||
|
Reference in New Issue
Block a user