From 9106aba861aa0de900e08711a7182d4a25b2acb7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bence=20Sg=C3=A1netz?= Date: Tue, 17 Oct 2023 21:15:24 +0200 Subject: [PATCH] FFTCache pooling --- Cavern/Utilities/FFTCache.cs | 2 +- Cavern/Utilities/FFTCachePool.cs | 56 ++++++++++++++++++++++++++++++++ 2 files changed, 57 insertions(+), 1 deletion(-) create mode 100644 Cavern/Utilities/FFTCachePool.cs diff --git a/Cavern/Utilities/FFTCache.cs b/Cavern/Utilities/FFTCache.cs index 5b03b61a..7bfbef0c 100644 --- a/Cavern/Utilities/FFTCache.cs +++ b/Cavern/Utilities/FFTCache.cs @@ -71,6 +71,7 @@ public FFTCache(int size) { } for (int i = 0, c = QMath.Log2(size); i < c; i++) { + Interlocked.Increment(ref refcounts[i]); if (cos[i] != null) { continue; } @@ -89,7 +90,6 @@ public FFTCache(int size) { thisSin[j + 1] = sinValue; } } - Interlocked.Increment(ref refcounts[i]); } float[] maskSource = new float[Vector.Count + 1]; diff --git a/Cavern/Utilities/FFTCachePool.cs b/Cavern/Utilities/FFTCachePool.cs new file mode 100644 index 00000000..90933876 --- /dev/null +++ b/Cavern/Utilities/FFTCachePool.cs @@ -0,0 +1,56 @@ +using System; +using System.Collections.Generic; + +namespace Cavern.Utilities { + /// + /// When performing a large amount of FFTs across multiple threads, use this pool for optimizing allocation performance + /// by reusing caches that are not used anymore by their thread. + /// + public class FFTCachePool : IDisposable { + /// + /// Caches not currently leased. + /// + readonly Stack caches = new Stack(); + + /// + /// Size of the used FFTs. + /// + readonly int size; + + /// + /// Create an pool for this FFT size. + /// + public FFTCachePool(int size) => this.size = size; + + /// + /// Get an to work with. + /// + public FFTCache Lease() { + lock (this) { + if (caches.Count == 0) { + return new ThreadSafeFFTCache(size); + } else { + return caches.Pop(); + } + } + } + + /// + /// Store the for later reuse. + /// + public void Return(FFTCache cache) { + lock (this) { + caches.Push(cache); + } + } + + /// + /// Free all resources used by the allocated . + /// + public void Dispose() { + while (caches.Count != 0) { + caches.Pop().Dispose(); + } + } + } +} \ No newline at end of file