}
+/*
+ * GetStableLatestTransactionIdIfAny
+ *
+ * Get the latest XID once and then return same value for rest of transaction.
+ * Acts as a useful reference point for maintenance tasks.
+ */
+TransactionId
+GetStableLatestTransactionId(void)
+{
+ static LocalTransactionId lxid = InvalidLocalTransactionId;
+ static TransactionId stablexid = InvalidTransactionId;
+
+ if (lxid != MyProc->lxid ||
+ !TransactionIdIsValid(stablexid))
+ {
+ lxid = MyProc->lxid;
+ stablexid = ReadNewTransactionId();
+ }
+
+ return stablexid;
+}
+
/*
* AssignTransactionId
*
#include "access/transam.h"
#include "access/xact.h"
#include "libpq/pqformat.h"
+#include "storage/proc.h"
#include "utils/builtins.h"
#define PG_GETARG_TRANSACTIONID(n) DatumGetTransactionId(PG_GETARG_DATUM(n))
}
/*
- * xid_age - compute age of an XID (relative to current xact)
+ * xid_age - compute age of an XID (relative to latest stable xid)
*/
Datum
xid_age(PG_FUNCTION_ARGS)
{
TransactionId xid = PG_GETARG_TRANSACTIONID(0);
- TransactionId now = GetTopTransactionIdIfAny();
-
- if (!TransactionIdIsValid(now))
- now = ReadNewTransactionId();
+ TransactionId now = GetStableLatestTransactionId();
/* Permanent XIDs are always infinitely old */
if (!TransactionIdIsNormal(xid))
extern TransactionId GetTopTransactionIdIfAny(void);
extern TransactionId GetCurrentTransactionId(void);
extern TransactionId GetCurrentTransactionIdIfAny(void);
+extern TransactionId GetStableLatestTransactionId(void);
extern SubTransactionId GetCurrentSubTransactionId(void);
extern CommandId GetCurrentCommandId(bool used);
extern TimestampTz GetCurrentTransactionStartTimestamp(void);