void FlushRandomBuffer()
{
if (_randBuf.Count() == 0)
{
return;
}
//First we write all data into rollback file and helper, calling flush on rollback
//then updating data of data file but dont call update
//clearing random buffer
//Creating rollback header
byte[] offset = null;
byte[] btRoll = null;
bool flushRollback = false;
//first loop for saving rollback data
foreach (var de in _randBuf.OrderBy(r => r.Key))
{
offset = ((ulong)de.Key).To_8_bytes_array_BigEndian().Substring(8 - DefaultPointerLen, DefaultPointerLen);
if (_rollbackCache.ContainsKey(de.Key))
continue;
//Reading from dataFile values which must be rolled back
btRoll = new byte[de.Value.Length];
_fsData.Position = de.Key;
_fsData.Read(btRoll, 0, btRoll.Length);
//Console.WriteLine("2;{0};{1}", de.Key, ((btRoll == null) ? -1 : btRoll.Length));
//Forming protocol for rollback
btRoll = new byte[] { 1 }
.ConcatMany(
offset,
((uint)btRoll.Length).To_4_bytes_array_BigEndian(),
btRoll
);
//Writing rollback
_fsRollback.Position = eofRollback;
_fsRollback.Write(btRoll, 0, btRoll.Length);
if (_backupIsActive)
{
this._configuration.Backup.WriteBackupElement(ulFileName, 1, eofRollback, btRoll);
}
_rollbackCache.Add(de.Key, new r { o = eofRollback + 1 + offset.Length + 4, l = de.Value.Length });
//increasing eof rollback file
eofRollback += btRoll.Length;
flushRollback = true;
}
if (flushRollback)
{
//Flushing rollback
NET_Flush(_fsRollback);
//Writing into helper
_fsRollbackHelper.Position = 0;
_fsRollbackHelper.Write(eofRollback.To_8_bytes_array_BigEndian(), 0, 8);
//Flushing rollback helper
NET_Flush(_fsRollbackHelper);
if (_backupIsActive)
{
this._configuration.Backup.WriteBackupElement(ulFileName, 2, 0, eofRollback.To_8_bytes_array_BigEndian());
this._configuration.Backup.Flush();
}
}
//second loop for saving data
foreach (var de in _randBuf.OrderBy(r => r.Key)) //sorting can mean nothing here, only takes extra time
{
_fsData.Position = de.Key;
_fsData.Write(de.Value, 0, de.Value.Length);
if (_backupIsActive)
{
this._configuration.Backup.WriteBackupElement(ulFileName, 0, de.Key, de.Value);
}
}
//No flush of data file, it will be done on Flush()
_randBuf.Clear();
usedBufferSize = 0;
}