private void CommitStage3_DisposeTransactionResources() { // an exception being thrown after the transaction has been committed to disk // will corrupt the in memory state, and require us to restart (and recover) to // be in a valid state try { ValidateAllPages(); Allocator.Release(ref _txHeaderMemory); Committed = true; _env.TransactionAfterCommit(this); if (_asyncCommitNextTransaction != null) { var old = _asyncCommitNextTransaction.JournalFiles; _asyncCommitNextTransaction.JournalFiles = _env.Journal.Files; foreach (var journalFile in _asyncCommitNextTransaction.JournalFiles) { journalFile.AddRef(); } foreach (var journalFile in old) { journalFile.Release(); } } } catch (Exception e) { _env.Options.SetCatastrophicFailure(ExceptionDispatchInfo.Capture(e)); throw; } }
public void Commit() { if (_disposed) { throw new ObjectDisposedException("Transaction"); } if (Flags != (TransactionFlags.ReadWrite)) { return; // nothing to do } if (Committed) { throw new InvalidOperationException("Cannot commit already committed transaction."); } if (RolledBack) { throw new InvalidOperationException("Cannot commit rolled-back transaction."); } while (_pagesToFreeOnCommit.Count > 0) { FreePage(_pagesToFreeOnCommit.Pop()); } _txHeader->LastPageNumber = _state.NextPageNumber - 1; _state.Root.CopyTo(&_txHeader->Root); _txHeader->TxMarker |= TransactionMarker.Commit; var totalNumberOfAllocatedPages = _allocatedPagesInTransaction + _overflowPagesInTransaction; if (totalNumberOfAllocatedPages > 0 || // nothing changed in this transaction // allow call to writeToJournal for flushing lazy tx (IsLazyTransaction == false && _journal?.HasDataInLazyTxBuffer() == true)) { // In the case of non-lazy transactions, we must flush the data from older lazy transactions // to ensure the sequentiality of the data. var numberOfWrittenPages = _journal.WriteToJournal(this, totalNumberOfAllocatedPages + PagesTakenByHeader); FlushedToJournal = true; if (_requestedCommitStats != null) { _requestedCommitStats.NumberOfModifiedPages = totalNumberOfAllocatedPages + PagesTakenByHeader; _requestedCommitStats.NumberOfPagesWrittenToDisk = numberOfWrittenPages; } } // an exception being throw after the transaction has been committed to disk // will corrupt the in memory state, and require us to restart (and recover) to // be in a valid state try { ValidateAllPages(); // release scratch file page allocated for the transaction header _env.ScratchBufferPool.Free(_transactionHeaderPage.ScratchFileNumber, _transactionHeaderPage.PositionInScratchBuffer, null); Committed = true; _env.TransactionAfterCommit(this); } catch (Exception e) { _env.CatastrophicFailure = ExceptionDispatchInfo.Capture(e); throw; } OnCommit?.Invoke(this); }