Hi When we lazily assign XIDs, we gain another flag beside the existing MyXactMadeTempRelUpdates, MyXactMadeXLogEntry, MyLastRecPtr and smgr's pendingDeletes to tell what kind of actions a transaction performed. Adding TransactionIsIsValid(GetCurrentTransactionIdIfAny()) on top of that makes things quite impenetrable - at least for me. So I'm trying to wrap my head around that logic, and simplify it a bit if possible. (Nowadays, async commit even adds a bit more complexity)
Currently, we write out a COMMIT record if a transaction either created any transaction-controlled XLOG entries (MyLastRecPtr.xrecoff != 0), or scheduled the deletion of files on commit. Afterwards, the xlog is flushed to the end last record created by the session (ProcLastRecEnd) if the transaction created any xlog record at all. If we either made transaction-controlled XLOG entries, or temporary relation updates, we update the XID status in the CLOG. An ABORT record is currently created if a transaction either created transaction-controlled XLOG entries or scheduled the deletion of files on abort. If we schedules file deletions, we flush the XLOG up to the ABORT record. If we either made transaction-controlled XLOG entries, updated temporary relations, or scheduled deletions we update the XID status in the CLOG. For subtransaction commit, a COMMIT record is emitted if we either made transaction-controlled XLOG entries, or updated temporary relations. No XLOG flush is performed. Subtransaction ABORTS are handled the same way as regular transaction aborts. For toplevel transaction commits, we defer flushing the xlog if synchronous_commit = off, and we didn't schedule any file deletions. Now, with lazy XID assignment I believe the following holds true .) If we didn't assign a valid XID, we cannot have made transaction-controlled XLOG entries (Can be checked by asserting that the current transaction id is valid if XLOG_NO_TRAN isn't set in XLogInsert). .) We cannot have scheduled files for deletion (on either COMMIT or ABORT) if we don't have a valid XID, since any such deletion will happen together with a catalog update. Note that this is already assumed to be true for subtransactions, since they only call RecordSubTransaction{Commit|Abort} if they have an XID assigned. I propose to do the following in my lazy XID assignment patch - can anyone see a hole in that? .) Get rid of MyLastRecPtr and MyXactMadeTempRelUpdates. Those are superseeded by TransactionIdIsValid(GetCurrentTransactionIdIfAny()). .) Get rid of MyXactMadeXLogEntry. Instead, just reset ProcLast .) Rename ProcLastRecEnd to XactLastRecEnd, and reset when starting a new toplevel transaction. Transaction COMMIT: Write an COMMIT record if and only if we have a valid XID. Then, flush the XLOG to XactLastRecEnd if that is set, and synchronous_commit=on. Aferwards, update the CLOG if and only if we have a valid XID. Transaction ABORT: Write an ABORT record if and only if we have a valid XID. Then, flush the XLOG to XactLastRecEnd if that is set, and we scheduled on-abort deletions. Update the CLOG if and only if we have a valid XID. Subtransaction COMMIT: Update the CLOG if and only if we have a valid XID. Subtransaction ABORT: Write an ABORT record if and only if we have a valid XID. Then, flush the XLOG to XactLastRecEnd if that is set, and we scheduled on-abort deletions. Update the CLOG if and only if we have a valid XID. I think we might go even further, and *never* flush the XLOG on abort, since if we crash just before the abort won't log anything either. But if we leak the leftover files in such a case, that's probably a bad idea. greetings, Florian Pflug ---------------------------(end of broadcast)--------------------------- TIP 3: Have you checked our extensive FAQ? http://www.postgresql.org/docs/faq