1b16bcd
From 88d4c6305161338ecb1f095c92ad7c6920ac5697 Mon Sep 17 00:00:00 2001
704b8e1
From: Elliott Sales de Andrade <quantum.analyst@gmail.com>
704b8e1
Date: Mon, 22 Aug 2022 18:43:28 -0400
acd2786
Subject: [PATCH 4/5] Use old stride_windows implementation on 32-bit x86
704b8e1
704b8e1
Signed-off-by: Elliott Sales de Andrade <quantum.analyst@gmail.com>
704b8e1
---
acd2786
 lib/matplotlib/mlab.py | 39 +++++++++++++++++++++++++++++++++++----
acd2786
 1 file changed, 35 insertions(+), 4 deletions(-)
704b8e1
704b8e1
diff --git a/lib/matplotlib/mlab.py b/lib/matplotlib/mlab.py
acd2786
index 1948e6333e..158417a1c0 100644
704b8e1
--- a/lib/matplotlib/mlab.py
704b8e1
+++ b/lib/matplotlib/mlab.py
acd2786
@@ -49,6 +49,7 @@ Spectral functions
704b8e1
 
704b8e1
 import functools
704b8e1
 from numbers import Number
704b8e1
+import sys
704b8e1
 
704b8e1
 import numpy as np
704b8e1
 
acd2786
@@ -210,6 +211,30 @@ def detrend_linear(y):
acd2786
     return y - (b*x + a)
704b8e1
 
acd2786
 
acd2786
+def _stride_windows(x, n, noverlap=0):
acd2786
+    if noverlap >= n:
acd2786
+        raise ValueError('noverlap must be less than n')
acd2786
+    if n < 1:
acd2786
+        raise ValueError('n cannot be less than 1')
acd2786
+
acd2786
+    x = np.asarray(x)
acd2786
+
acd2786
+    if n == 1 and noverlap == 0:
acd2786
+        return x[np.newaxis]
acd2786
+    if n > x.size:
acd2786
+        raise ValueError('n cannot be greater than the length of x')
acd2786
+
acd2786
+    # np.lib.stride_tricks.as_strided easily leads to memory corruption for
acd2786
+    # non integer shape and strides, i.e. noverlap or n. See #3845.
acd2786
+    noverlap = int(noverlap)
acd2786
+    n = int(n)
acd2786
+
acd2786
+    step = n - noverlap
acd2786
+    shape = (n, (x.shape[-1]-noverlap)//step)
acd2786
+    strides = (x.strides[0], step*x.strides[0])
acd2786
+    return np.lib.stride_tricks.as_strided(x, shape=shape, strides=strides)
acd2786
+
acd2786
+
acd2786
 def _spectral_helper(x, y=None, NFFT=None, Fs=None, detrend_func=None,
acd2786
                      window=None, noverlap=None, pad_to=None,
acd2786
                      sides=None, scale_by_freq=None, mode=None):
acd2786
@@ -304,8 +329,11 @@ def _spectral_helper(x, y=None, NFFT=None, Fs=None, detrend_func=None,
acd2786
         raise ValueError(
acd2786
             "The window length must match the data's first dimension")
acd2786
 
acd2786
-    result = np.lib.stride_tricks.sliding_window_view(
acd2786
-        x, NFFT, axis=0)[::NFFT - noverlap].T
acd2786
+    if sys.maxsize > 2**32:  # NumPy version on 32-bit OOMs.
acd2786
+        result = np.lib.stride_tricks.sliding_window_view(
acd2786
+            x, NFFT, axis=0)[::NFFT - noverlap].T
acd2786
+    else:
acd2786
+        result = _stride_windows(x, NFFT, noverlap=noverlap)
acd2786
     result = detrend(result, detrend_func, axis=0)
acd2786
     result = result * window.reshape((-1, 1))
acd2786
     result = np.fft.fft(result, n=pad_to, axis=0)[:numFreqs, :]
acd2786
@@ -313,8 +341,11 @@ def _spectral_helper(x, y=None, NFFT=None, Fs=None, detrend_func=None,
acd2786
 
acd2786
     if not same_data:
acd2786
         # if same_data is False, mode must be 'psd'
acd2786
-        resultY = np.lib.stride_tricks.sliding_window_view(
acd2786
-            y, NFFT, axis=0)[::NFFT - noverlap].T
acd2786
+        if sys.maxsize > 2**32:  # NumPy version on 32-bit OOMs.
acd2786
+            resultY = np.lib.stride_tricks.sliding_window_view(
acd2786
+                y, NFFT, axis=0)[::NFFT - noverlap].T
acd2786
+        else:
acd2786
+            resultY = _stride_windows(y, NFFT, noverlap=noverlap)
acd2786
         resultY = detrend(resultY, detrend_func, axis=0)
acd2786
         resultY = resultY * window.reshape((-1, 1))
acd2786
         resultY = np.fft.fft(resultY, n=pad_to, axis=0)[:numFreqs, :]
704b8e1
-- 
545cd05
2.41.0
704b8e1