8
8
*
9
9
*
10
10
* IDENTIFICATION
11
- * $PostgreSQL: pgsql/src/backend/storage/buffer/bufmgr.c,v 1.179 2004/10/16 18:05:06 tgl Exp $
11
+ * $PostgreSQL: pgsql/src/backend/storage/buffer/bufmgr.c,v 1.180 2004/10/16 18:57:23 tgl Exp $
12
12
*
13
13
*-------------------------------------------------------------------------
14
14
*/
@@ -851,35 +851,45 @@ ResetBufferUsage(void)
851
851
/*
852
852
* AtEOXact_Buffers - clean up at end of transaction.
853
853
*
854
- * During abort, we need to release any buffer pins we're holding
855
- * (this cleans up in case ereport interrupted a routine that pins a
856
- * buffer). During commit, we shouldn't need to do that, but check
857
- * anyway to see if anyone leaked a buffer reference count.
854
+ * As of PostgreSQL 8.0, buffer pins should get released by the
855
+ * ResourceOwner mechanism. This routine is just a debugging
856
+ * cross-check that no pins remain.
858
857
*/
859
858
void
860
859
AtEOXact_Buffers (bool isCommit )
861
860
{
861
+ #ifdef USE_ASSERT_CHECKING
862
862
int i ;
863
863
864
+ for (i = 0 ; i < NBuffers ; i ++ )
865
+ {
866
+ Assert (PrivateRefCount [i ] == 0 );
867
+ }
868
+
869
+ AtEOXact_LocalBuffers (isCommit );
870
+ #endif
871
+ }
872
+
873
+ /*
874
+ * Ensure we have released all shared-buffer locks and pins during backend exit
875
+ */
876
+ void
877
+ AtProcExit_Buffers (void )
878
+ {
879
+ int i ;
880
+
881
+ AbortBufferIO ();
882
+ UnlockBuffers ();
883
+
864
884
for (i = 0 ; i < NBuffers ; i ++ )
865
885
{
866
886
if (PrivateRefCount [i ] != 0 )
867
887
{
868
888
BufferDesc * buf = & (BufferDescriptors [i ]);
869
889
870
- if (isCommit )
871
- elog (WARNING ,
872
- "buffer refcount leak: [%03d] "
873
- "(rel=%u/%u/%u, blockNum=%u, flags=0x%x, refcount=%u %d)" ,
874
- i ,
875
- buf -> tag .rnode .spcNode , buf -> tag .rnode .dbNode ,
876
- buf -> tag .rnode .relNode ,
877
- buf -> tag .blockNum , buf -> flags ,
878
- buf -> refcount , PrivateRefCount [i ]);
879
-
880
890
/*
881
- * We don't worry about updating the ResourceOwner structures;
882
- * resowner.c will clear them for itself .
891
+ * We don't worry about updating ResourceOwner; if we even got
892
+ * here, it suggests that ResourceOwners are messed up .
883
893
*/
884
894
PrivateRefCount [i ] = 1 ; /* make sure we release shared pin */
885
895
LWLockAcquire (BufMgrLock , LW_EXCLUSIVE );
@@ -888,8 +898,37 @@ AtEOXact_Buffers(bool isCommit)
888
898
Assert (PrivateRefCount [i ] == 0 );
889
899
}
890
900
}
901
+ }
891
902
892
- AtEOXact_LocalBuffers (isCommit );
903
+ /*
904
+ * Helper routine to issue warnings when a buffer is unexpectedly pinned
905
+ */
906
+ void
907
+ PrintBufferLeakWarning (Buffer buffer )
908
+ {
909
+ BufferDesc * buf ;
910
+ int32 loccount ;
911
+
912
+ Assert (BufferIsValid (buffer ));
913
+ if (BufferIsLocal (buffer ))
914
+ {
915
+ buf = & LocalBufferDescriptors [- buffer - 1 ];
916
+ loccount = LocalRefCount [- buffer - 1 ];
917
+ }
918
+ else
919
+ {
920
+ buf = & BufferDescriptors [buffer - 1 ];
921
+ loccount = PrivateRefCount [buffer - 1 ];
922
+ }
923
+
924
+ elog (WARNING ,
925
+ "buffer refcount leak: [%03d] "
926
+ "(rel=%u/%u/%u, blockNum=%u, flags=0x%x, refcount=%u %d)" ,
927
+ buffer ,
928
+ buf -> tag .rnode .spcNode , buf -> tag .rnode .dbNode ,
929
+ buf -> tag .rnode .relNode ,
930
+ buf -> tag .blockNum , buf -> flags ,
931
+ buf -> refcount , loccount );
893
932
}
894
933
895
934
/*
0 commit comments