From 0fd3e515dac87287c520782f59bf840733c56218 Mon Sep 17 00:00:00 2001 From: Carl Johnsen Date: Sun, 10 Aug 2025 20:55:02 +0200 Subject: [PATCH] Ensured that an actively read volume in the volumemanager cannot be disposed --- Duplicati/Library/Main/Operation/Restore/VolumeManager.cs | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/Duplicati/Library/Main/Operation/Restore/VolumeManager.cs b/Duplicati/Library/Main/Operation/Restore/VolumeManager.cs index 086e20a31..0d8e11d1c 100644 --- a/Duplicati/Library/Main/Operation/Restore/VolumeManager.cs +++ b/Duplicati/Library/Main/Operation/Restore/VolumeManager.cs @@ -26,6 +26,7 @@ using System; using System.Collections.Generic; using System.Diagnostics; using System.Linq; +using System.Threading; using System.Threading.Tasks; #nullable enable @@ -118,6 +119,8 @@ namespace Duplicati.Library.Main.Operation.Restore Dictionary> in_flight_downloads = []; // Dictionary to keep track of volumes that are actively being accessed. Used for cache eviction. Dictionary in_flight_decompressing = []; + // Dictionary to keep track of the currently responding request to prevent auto evicting during a response. + long? responding = null; Stopwatch? sw_cache_set = options.InternalProfiling ? new() : null; Stopwatch? sw_cache_evict = options.InternalProfiling ? new() : null; @@ -145,7 +148,7 @@ namespace Duplicati.Library.Main.Operation.Restore if (dcount <= 1) { in_flight_decompressing.Remove(volume_id); - if (cache_max == 0) + if (volume_id != responding && cache_max == 0) { handle_evict(volume_id); } @@ -284,6 +287,7 @@ namespace Duplicati.Library.Main.Operation.Restore tmpfiles[volume_id] = tmpfile; sw_cache_set?.Stop(); sw_wakeup?.Start(); + responding = volume_id; foreach (var request in in_flight_downloads[volume_id]) { // Ensure ACK channel is empty to avoid deadlock @@ -304,6 +308,7 @@ namespace Duplicati.Library.Main.Operation.Restore else in_flight_decompressing[request.VolumeID] = 1; } + responding = null; in_flight_downloads.Remove(volume_id); sw_wakeup?.Stop(); break;