From 59144885f4739c54dca8177c09bc519bc5069e30 Mon Sep 17 00:00:00 2001 From: Sewer56 Date: Tue, 23 Jul 2024 19:38:26 +0100 Subject: [PATCH] Fixed: Concurrency Issue in repacking partial SOLIDs --- .../FileProviders/FromExistingNxBlock.cs | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/NexusMods.Archives.Nx/FileProviders/FromExistingNxBlock.cs b/NexusMods.Archives.Nx/FileProviders/FromExistingNxBlock.cs index 94a05ee..4bfe0fd 100644 --- a/NexusMods.Archives.Nx/FileProviders/FromExistingNxBlock.cs +++ b/NexusMods.Archives.Nx/FileProviders/FromExistingNxBlock.cs @@ -69,6 +69,9 @@ public IFileData GetFileData(ulong start, ulong length) throw new Exception("Repeated call to GetData. This is not allowed."); _hasCalledGetData = true; + + if (start != 0 || length != FileSize) + throw new InvalidOperationException("This provider only supports reading the entire file."); #endif return new DecompressedNxBlockFileData(LazyRefCounterDecompressedNxBlock, DecompressedBlockOffset, FileSize); @@ -200,16 +203,17 @@ public void ConsiderFile(FileEntry entry) return _data; // Not much contention expected so full lock is ok, no need for extra field and 'cmpxchg' here. - lock (this) + lock (_sourceNxDataProvider) { // Another thread might have already initialized in lock. if (_data != null) return _data; - _data = AllocNativeMemory((nuint)_numBytesToDecompress); + var data = AllocNativeMemory((nuint)_numBytesToDecompress); using var rawBlockData = _sourceNxDataProvider.GetFileData(_blockOffset, _compressedBlockLength); - Compression.Decompress(_compression, rawBlockData.Data, (int)rawBlockData.DataLength, (byte*)_data, (int)_numBytesToDecompress); - return _data; + Compression.Decompress(_compression, rawBlockData.Data, (int)rawBlockData.DataLength, (byte*)data, (int)_numBytesToDecompress); + _data = data; + return data; } }