PostgreSQL Source Code  git master
subtrans.c File Reference
#include "postgres.h"
#include "access/slru.h"
#include "access/subtrans.h"
#include "access/transam.h"
#include "pg_trace.h"
#include "utils/snapmgr.h"
Include dependency graph for subtrans.c:

Go to the source code of this file.

Macros

#define SUBTRANS_XACTS_PER_PAGE   (BLCKSZ / sizeof(TransactionId))
 
#define TransactionIdToEntry(xid)   ((xid) % (TransactionId) SUBTRANS_XACTS_PER_PAGE)
 
#define SubTransCtl   (&SubTransCtlData)
 

Functions

static int64 TransactionIdToPage (TransactionId xid)
 
static int ZeroSUBTRANSPage (int64 pageno)
 
static bool SubTransPagePrecedes (int64 page1, int64 page2)
 
void SubTransSetParent (TransactionId xid, TransactionId parent)
 
TransactionId SubTransGetParent (TransactionId xid)
 
TransactionId SubTransGetTopmostTransaction (TransactionId xid)
 
Size SUBTRANSShmemSize (void)
 
void SUBTRANSShmemInit (void)
 
void BootStrapSUBTRANS (void)
 
void StartupSUBTRANS (TransactionId oldestActiveXID)
 
void CheckPointSUBTRANS (void)
 
void ExtendSUBTRANS (TransactionId newestXact)
 
void TruncateSUBTRANS (TransactionId oldestXact)
 

Variables

static SlruCtlData SubTransCtlData
 

Macro Definition Documentation

◆ SUBTRANS_XACTS_PER_PAGE

#define SUBTRANS_XACTS_PER_PAGE   (BLCKSZ / sizeof(TransactionId))

Definition at line 52 of file subtrans.c.

◆ SubTransCtl

#define SubTransCtl   (&SubTransCtlData)

Definition at line 72 of file subtrans.c.

◆ TransactionIdToEntry

#define TransactionIdToEntry (   xid)    ((xid) % (TransactionId) SUBTRANS_XACTS_PER_PAGE)

Definition at line 64 of file subtrans.c.

Function Documentation

◆ BootStrapSUBTRANS()

void BootStrapSUBTRANS ( void  )

Definition at line 221 of file subtrans.c.

222 {
223  int slotno;
224 
225  LWLockAcquire(SubtransSLRULock, LW_EXCLUSIVE);
226 
227  /* Create and zero the first page of the subtrans log */
228  slotno = ZeroSUBTRANSPage(0);
229 
230  /* Make sure it's written out */
232  Assert(!SubTransCtl->shared->page_dirty[slotno]);
233 
234  LWLockRelease(SubtransSLRULock);
235 }
Assert(fmt[strlen(fmt) - 1] !='\n')
bool LWLockAcquire(LWLock *lock, LWLockMode mode)
Definition: lwlock.c:1168
void LWLockRelease(LWLock *lock)
Definition: lwlock.c:1781
@ LW_EXCLUSIVE
Definition: lwlock.h:116
void SimpleLruWritePage(SlruCtl ctl, int slotno)
Definition: slru.c:649
static int ZeroSUBTRANSPage(int64 pageno)
Definition: subtrans.c:246
#define SubTransCtl
Definition: subtrans.c:72

References Assert(), LW_EXCLUSIVE, LWLockAcquire(), LWLockRelease(), SimpleLruWritePage(), SubTransCtl, and ZeroSUBTRANSPage().

Referenced by BootStrapXLOG().

◆ CheckPointSUBTRANS()

void CheckPointSUBTRANS ( void  )

Definition at line 294 of file subtrans.c.

295 {
296  /*
297  * Write dirty SUBTRANS pages to disk
298  *
299  * This is not actually necessary from a correctness point of view. We do
300  * it merely to improve the odds that writing of dirty pages is done by
301  * the checkpoint process and not by backends.
302  */
303  TRACE_POSTGRESQL_SUBTRANS_CHECKPOINT_START(true);
305  TRACE_POSTGRESQL_SUBTRANS_CHECKPOINT_DONE(true);
306 }
void SimpleLruWriteAll(SlruCtl ctl, bool allow_redirtied)
Definition: slru.c:1199

References SimpleLruWriteAll(), and SubTransCtl.

Referenced by CheckPointGuts().

◆ ExtendSUBTRANS()

void ExtendSUBTRANS ( TransactionId  newestXact)

Definition at line 318 of file subtrans.c.

319 {
320  int64 pageno;
321 
322  /*
323  * No work except at first XID of a page. But beware: just after
324  * wraparound, the first XID of page zero is FirstNormalTransactionId.
325  */
326  if (TransactionIdToEntry(newestXact) != 0 &&
328  return;
329 
330  pageno = TransactionIdToPage(newestXact);
331 
332  LWLockAcquire(SubtransSLRULock, LW_EXCLUSIVE);
333 
334  /* Zero the page */
335  ZeroSUBTRANSPage(pageno);
336 
337  LWLockRelease(SubtransSLRULock);
338 }
#define TransactionIdToEntry(xid)
Definition: subtrans.c:64
static int64 TransactionIdToPage(TransactionId xid)
Definition: subtrans.c:59
#define TransactionIdEquals(id1, id2)
Definition: transam.h:43
#define FirstNormalTransactionId
Definition: transam.h:34

References FirstNormalTransactionId, LW_EXCLUSIVE, LWLockAcquire(), LWLockRelease(), TransactionIdEquals, TransactionIdToEntry, TransactionIdToPage(), and ZeroSUBTRANSPage().

Referenced by GetNewTransactionId(), ProcArrayApplyRecoveryInfo(), and RecordKnownAssignedTransactionIds().

◆ StartupSUBTRANS()

void StartupSUBTRANS ( TransactionId  oldestActiveXID)

Definition at line 259 of file subtrans.c.

260 {
261  FullTransactionId nextXid;
262  int64 startPage;
263  int64 endPage;
264 
265  /*
266  * Since we don't expect pg_subtrans to be valid across crashes, we
267  * initialize the currently-active page(s) to zeroes during startup.
268  * Whenever we advance into a new page, ExtendSUBTRANS will likewise zero
269  * the new page without regard to whatever was previously on disk.
270  */
271  LWLockAcquire(SubtransSLRULock, LW_EXCLUSIVE);
272 
273  startPage = TransactionIdToPage(oldestActiveXID);
274  nextXid = TransamVariables->nextXid;
275  endPage = TransactionIdToPage(XidFromFullTransactionId(nextXid));
276 
277  while (startPage != endPage)
278  {
279  (void) ZeroSUBTRANSPage(startPage);
280  startPage++;
281  /* must account for wraparound */
282  if (startPage > TransactionIdToPage(MaxTransactionId))
283  startPage = 0;
284  }
285  (void) ZeroSUBTRANSPage(startPage);
286 
287  LWLockRelease(SubtransSLRULock);
288 }
FullTransactionId nextXid
Definition: transam.h:220
#define XidFromFullTransactionId(x)
Definition: transam.h:48
#define MaxTransactionId
Definition: transam.h:35
TransamVariablesData * TransamVariables
Definition: varsup.c:34

References LW_EXCLUSIVE, LWLockAcquire(), LWLockRelease(), MaxTransactionId, TransamVariablesData::nextXid, TransactionIdToPage(), TransamVariables, XidFromFullTransactionId, and ZeroSUBTRANSPage().

Referenced by StartupXLOG().

◆ SubTransGetParent()

TransactionId SubTransGetParent ( TransactionId  xid)

Definition at line 118 of file subtrans.c.

119 {
120  int64 pageno = TransactionIdToPage(xid);
121  int entryno = TransactionIdToEntry(xid);
122  int slotno;
123  TransactionId *ptr;
124  TransactionId parent;
125 
126  /* Can't ask about stuff that might not be around anymore */
128 
129  /* Bootstrap and frozen XIDs have no parent */
130  if (!TransactionIdIsNormal(xid))
131  return InvalidTransactionId;
132 
133  /* lock is acquired by SimpleLruReadPage_ReadOnly */
134 
135  slotno = SimpleLruReadPage_ReadOnly(SubTransCtl, pageno, xid);
136  ptr = (TransactionId *) SubTransCtl->shared->page_buffer[slotno];
137  ptr += entryno;
138 
139  parent = *ptr;
140 
141  LWLockRelease(SubtransSLRULock);
142 
143  return parent;
144 }
uint32 TransactionId
Definition: c.h:641
int SimpleLruReadPage_ReadOnly(SlruCtl ctl, int64 pageno, TransactionId xid)
Definition: slru.c:530
TransactionId TransactionXmin
Definition: snapmgr.c:105
bool TransactionIdFollowsOrEquals(TransactionId id1, TransactionId id2)
Definition: transam.c:329
#define InvalidTransactionId
Definition: transam.h:31
#define TransactionIdIsNormal(xid)
Definition: transam.h:42

References Assert(), InvalidTransactionId, LWLockRelease(), SimpleLruReadPage_ReadOnly(), SubTransCtl, TransactionIdFollowsOrEquals(), TransactionIdIsNormal, TransactionIdToEntry, TransactionIdToPage(), and TransactionXmin.

Referenced by SubTransGetTopmostTransaction(), TransactionIdDidAbort(), and TransactionIdDidCommit().

◆ SubTransGetTopmostTransaction()

TransactionId SubTransGetTopmostTransaction ( TransactionId  xid)

Definition at line 159 of file subtrans.c.

160 {
161  TransactionId parentXid = xid,
162  previousXid = xid;
163 
164  /* Can't ask about stuff that might not be around anymore */
166 
167  while (TransactionIdIsValid(parentXid))
168  {
169  previousXid = parentXid;
170  if (TransactionIdPrecedes(parentXid, TransactionXmin))
171  break;
172  parentXid = SubTransGetParent(parentXid);
173 
174  /*
175  * By convention the parent xid gets allocated first, so should always
176  * precede the child xid. Anything else points to a corrupted data
177  * structure that could lead to an infinite loop, so exit.
178  */
179  if (!TransactionIdPrecedes(parentXid, previousXid))
180  elog(ERROR, "pg_subtrans contains invalid entry: xid %u points to parent xid %u",
181  previousXid, parentXid);
182  }
183 
184  Assert(TransactionIdIsValid(previousXid));
185 
186  return previousXid;
187 }
#define ERROR
Definition: elog.h:39
TransactionId SubTransGetParent(TransactionId xid)
Definition: subtrans.c:118
bool TransactionIdPrecedes(TransactionId id1, TransactionId id2)
Definition: transam.c:280
#define TransactionIdIsValid(xid)
Definition: transam.h:41

References Assert(), elog(), ERROR, SubTransGetParent(), TransactionIdFollowsOrEquals(), TransactionIdIsValid, TransactionIdPrecedes(), and TransactionXmin.

Referenced by ConditionalXactLockTableWait(), HeapCheckForSerializableConflictOut(), TransactionIdIsInProgress(), XactLockTableWait(), and XidInMVCCSnapshot().

◆ SubTransPagePrecedes()

static bool SubTransPagePrecedes ( int64  page1,
int64  page2 
)
static

Definition at line 372 of file subtrans.c.

373 {
374  TransactionId xid1;
375  TransactionId xid2;
376 
377  xid1 = ((TransactionId) page1) * SUBTRANS_XACTS_PER_PAGE;
378  xid1 += FirstNormalTransactionId + 1;
379  xid2 = ((TransactionId) page2) * SUBTRANS_XACTS_PER_PAGE;
380  xid2 += FirstNormalTransactionId + 1;
381 
382  return (TransactionIdPrecedes(xid1, xid2) &&
384 }
#define SUBTRANS_XACTS_PER_PAGE
Definition: subtrans.c:52

References FirstNormalTransactionId, SUBTRANS_XACTS_PER_PAGE, and TransactionIdPrecedes().

Referenced by SUBTRANSShmemInit().

◆ SubTransSetParent()

void SubTransSetParent ( TransactionId  xid,
TransactionId  parent 
)

Definition at line 83 of file subtrans.c.

84 {
85  int64 pageno = TransactionIdToPage(xid);
86  int entryno = TransactionIdToEntry(xid);
87  int slotno;
88  TransactionId *ptr;
89 
91  Assert(TransactionIdFollows(xid, parent));
92 
93  LWLockAcquire(SubtransSLRULock, LW_EXCLUSIVE);
94 
95  slotno = SimpleLruReadPage(SubTransCtl, pageno, true, xid);
96  ptr = (TransactionId *) SubTransCtl->shared->page_buffer[slotno];
97  ptr += entryno;
98 
99  /*
100  * It's possible we'll try to set the parent xid multiple times but we
101  * shouldn't ever be changing the xid from one valid xid to another valid
102  * xid, which would corrupt the data structure.
103  */
104  if (*ptr != parent)
105  {
106  Assert(*ptr == InvalidTransactionId);
107  *ptr = parent;
108  SubTransCtl->shared->page_dirty[slotno] = true;
109  }
110 
111  LWLockRelease(SubtransSLRULock);
112 }
if(TABLE==NULL||TABLE_index==NULL)
Definition: isn.c:77
int SimpleLruReadPage(SlruCtl ctl, int64 pageno, bool write_ok, TransactionId xid)
Definition: slru.c:430
bool TransactionIdFollows(TransactionId id1, TransactionId id2)
Definition: transam.c:314

References Assert(), if(), InvalidTransactionId, LW_EXCLUSIVE, LWLockAcquire(), LWLockRelease(), SimpleLruReadPage(), SubTransCtl, TransactionIdFollows(), TransactionIdIsValid, TransactionIdToEntry, and TransactionIdToPage().

Referenced by AssignTransactionId(), ProcArrayApplyXidAssignment(), and ProcessTwoPhaseBuffer().

◆ SUBTRANSShmemInit()

void SUBTRANSShmemInit ( void  )

Definition at line 200 of file subtrans.c.

201 {
202  SubTransCtl->PagePrecedes = SubTransPagePrecedes;
204  SubtransSLRULock, "pg_subtrans",
206  false);
208 }
@ LWTRANCHE_SUBTRANS_BUFFER
Definition: lwlock.h:183
void SimpleLruInit(SlruCtl ctl, const char *name, int nslots, int nlsns, LWLock *ctllock, const char *subdir, int tranche_id, SyncRequestHandler sync_handler, bool long_segment_names)
Definition: slru.c:215
#define SlruPagePrecedesUnitTests(ctl, per_page)
Definition: slru.h:168
static bool SubTransPagePrecedes(int64 page1, int64 page2)
Definition: subtrans.c:372
#define NUM_SUBTRANS_BUFFERS
Definition: subtrans.h:15
@ SYNC_HANDLER_NONE
Definition: sync.h:42

References LWTRANCHE_SUBTRANS_BUFFER, NUM_SUBTRANS_BUFFERS, SimpleLruInit(), SlruPagePrecedesUnitTests, SUBTRANS_XACTS_PER_PAGE, SubTransCtl, SubTransPagePrecedes(), and SYNC_HANDLER_NONE.

Referenced by CreateOrAttachShmemStructs().

◆ SUBTRANSShmemSize()

Size SUBTRANSShmemSize ( void  )

Definition at line 194 of file subtrans.c.

195 {
197 }
Size SimpleLruShmemSize(int nslots, int nlsns)
Definition: slru.c:183

References NUM_SUBTRANS_BUFFERS, and SimpleLruShmemSize().

Referenced by CalculateShmemSize().

◆ TransactionIdToPage()

static int64 TransactionIdToPage ( TransactionId  xid)
inlinestatic

Definition at line 59 of file subtrans.c.

60 {
61  return xid / (int64) SUBTRANS_XACTS_PER_PAGE;
62 }

References SUBTRANS_XACTS_PER_PAGE.

Referenced by ExtendSUBTRANS(), StartupSUBTRANS(), SubTransGetParent(), SubTransSetParent(), and TruncateSUBTRANS().

◆ TruncateSUBTRANS()

void TruncateSUBTRANS ( TransactionId  oldestXact)

Definition at line 348 of file subtrans.c.

349 {
350  int64 cutoffPage;
351 
352  /*
353  * The cutoff point is the start of the segment containing oldestXact. We
354  * pass the *page* containing oldestXact to SimpleLruTruncate. We step
355  * back one transaction to avoid passing a cutoff page that hasn't been
356  * created yet in the rare case that oldestXact would be the first item on
357  * a page and oldestXact == next XID. In that case, if we didn't subtract
358  * one, we'd trigger SimpleLruTruncate's wraparound detection.
359  */
360  TransactionIdRetreat(oldestXact);
361  cutoffPage = TransactionIdToPage(oldestXact);
362 
363  SimpleLruTruncate(SubTransCtl, cutoffPage);
364 }
void SimpleLruTruncate(SlruCtl ctl, int64 cutoffPage)
Definition: slru.c:1269
#define TransactionIdRetreat(dest)
Definition: transam.h:141

References SimpleLruTruncate(), SubTransCtl, TransactionIdRetreat, and TransactionIdToPage().

Referenced by CreateCheckPoint(), and CreateRestartPoint().

◆ ZeroSUBTRANSPage()

static int ZeroSUBTRANSPage ( int64  pageno)
static

Definition at line 246 of file subtrans.c.

247 {
248  return SimpleLruZeroPage(SubTransCtl, pageno);
249 }
int SimpleLruZeroPage(SlruCtl ctl, int64 pageno)
Definition: slru.c:308

References SimpleLruZeroPage(), and SubTransCtl.

Referenced by BootStrapSUBTRANS(), ExtendSUBTRANS(), and StartupSUBTRANS().

Variable Documentation

◆ SubTransCtlData

SlruCtlData SubTransCtlData
static

Definition at line 70 of file subtrans.c.