1
0
mirror of https://github.com/postgres/postgres.git synced 2025-07-27 12:41:57 +03:00

Split the buffer mapping table into multiple separately lockable

partitions, as per discussion.  Passes functionality checks, but
I don't have any performance data yet.
This commit is contained in:
Tom Lane
2006-07-23 03:07:58 +00:00
parent 51ee9fa157
commit 10b9ca3d05
8 changed files with 198 additions and 75 deletions

View File

@ -3,7 +3,7 @@
* pg_buffercache_pages.c
* display some contents of the buffer cache
*
* $PostgreSQL: pgsql/contrib/pg_buffercache/pg_buffercache_pages.c,v 1.7 2006/05/30 22:12:13 tgl Exp $
* $PostgreSQL: pgsql/contrib/pg_buffercache/pg_buffercache_pages.c,v 1.8 2006/07/23 03:07:57 tgl Exp $
*-------------------------------------------------------------------------
*/
#include "postgres.h"
@ -74,7 +74,7 @@ pg_buffercache_pages(PG_FUNCTION_ARGS)
if (SRF_IS_FIRSTCALL())
{
uint32 i;
int i;
volatile BufferDesc *bufHdr;
funcctx = SRF_FIRSTCALL_INIT();
@ -108,7 +108,6 @@ pg_buffercache_pages(PG_FUNCTION_ARGS)
funcctx->max_calls = NBuffers;
funcctx->user_fctx = fctx;
/* Allocate NBuffers worth of BufferCachePagesRec records. */
fctx->record = (BufferCachePagesRec *) palloc(sizeof(BufferCachePagesRec) * NBuffers);
@ -120,17 +119,21 @@ pg_buffercache_pages(PG_FUNCTION_ARGS)
fctx->values[4] = (char *) palloc(3 * sizeof(uint32) + 1);
fctx->values[5] = (char *) palloc(2);
/* Return to original context when allocating transient memory */
MemoryContextSwitchTo(oldcontext);
/*
* To get a consistent picture of the buffer state, we must lock
* all partitions of the buffer map. Needless to say, this is
* horrible for concurrency...
*/
for (i = 0; i < NUM_BUFFER_PARTITIONS; i++)
LWLockAcquire(FirstBufMappingLock + i, LW_SHARED);
/*
* Lock Buffer map and scan though all the buffers, saving the
* relevant fields in the fctx->record structure.
* Scan though all the buffers, saving the relevant fields in the
* fctx->record structure.
*/
LWLockAcquire(BufMappingLock, LW_SHARED);
for (i = 0, bufHdr = BufferDescriptors; i < NBuffers; i++, bufHdr++)
{
/* Lock each buffer header before inspecting. */
@ -157,7 +160,8 @@ pg_buffercache_pages(PG_FUNCTION_ARGS)
}
/* Release Buffer map. */
LWLockRelease(BufMappingLock);
for (i = 0; i < NUM_BUFFER_PARTITIONS; i++)
LWLockRelease(FirstBufMappingLock + i);
}
funcctx = SRF_PERCALL_SETUP();
@ -165,7 +169,6 @@ pg_buffercache_pages(PG_FUNCTION_ARGS)
/* Get the saved state */
fctx = funcctx->user_fctx;
if (funcctx->call_cntr < funcctx->max_calls)
{
uint32 i = funcctx->call_cntr;