diff --git a/docs/source/faq.rst b/docs/source/faq.rst index 08f6a59c..ab057392 100755 --- a/docs/source/faq.rst +++ b/docs/source/faq.rst @@ -14,9 +14,9 @@ working with linear operators is indeed that you don't really need to access the of an operator. -**2. Can I have an older version of** ``cupy`` **or** ``cusignal`` **installed in my system (** ``cupy-cudaXX<8.1.0`` **or** ``cusignal>=0.16.0`` **)?** +**2. Can I have an older version of** ``cupy`` **installed in my system (** ``cupy-cudaXX<10.6.0``)?** Yes. Nevertheless you need to tell PyLops that you don't want to use its ``cupy`` -backend by setting the environment variable ``CUPY_PYLOPS=0`` or ``CUPY_SIGNAL=0``. +backend by setting the environment variable ``CUPY_PYLOPS=0``. Failing to do so will lead to an error when you import ``pylops`` because some of the ``cupyx`` routines that we use are not available in earlier version of ``cupy``. \ No newline at end of file diff --git a/docs/source/gpu.rst b/docs/source/gpu.rst index 7bc361d9..864451c4 100755 --- a/docs/source/gpu.rst +++ b/docs/source/gpu.rst @@ -5,15 +5,14 @@ GPU Support Overview -------- -From ``v1.12.0``, PyLops supports computations on GPUs powered by -`CuPy `_ (``cupy-cudaXX>=8.1.0``) and `cuSignal `_ (``cusignal>=0.16.0``). -They must be installed *before* PyLops is installed. +PyLops supports computations on GPUs powered by `CuPy `_ (``cupy-cudaXX>=10.6.0``). +This library must be installed *before* PyLops is installed. .. note:: - Set environment variables ``CUPY_PYLOPS=0`` and/or ``CUSIGNAL_PYLOPS=0`` to force PyLops to ignore - ``cupy`` and ``cusignal`` backends. - This can be also used if a previous version of ``cupy`` or ``cusignal`` is installed in your system, otherwise you will get an error when importing PyLops. + Set environment variable ``CUPY_PYLOPS=0`` to force PyLops to ignore the ``cupy`` backend. + This can be also used if a previous (or faulty) version of ``cupy`` is installed in your system, + otherwise you will get an error when importing PyLops. diff --git a/docs/source/installation.rst b/docs/source/installation.rst index 55cfec7b..563b62aa 100755 --- a/docs/source/installation.rst +++ b/docs/source/installation.rst @@ -514,16 +514,8 @@ disable this option. For more details of GPU-accelerated PyLops read :ref:`gpu`. CuPy ---- -`CuPy `_ is a library used as a drop-in replacement to NumPy -for GPU-accelerated -computations. Since many different versions of CuPy exist (based on the +`CuPy `_ is a library used as a drop-in replacement to NumPy and some parts of SciPy +for GPU-accelerated computations. Since many different versions of CuPy exist (based on the CUDA drivers of the GPU), users must install CuPy prior to installing PyLops. To do so, follow their -`installation instructions `__. - -cuSignal --------- -`cuSignal `_ is a library is used as a drop-in replacement to `SciPy Signal `_ for -GPU-accelerated computations. Similar to CuPy, users must install -cuSignal prior to installing PyLops. To do so, follow their -`installation instructions `__. +`installation instructions `__. \ No newline at end of file diff --git a/pylops/signalprocessing/convolve1d.py b/pylops/signalprocessing/convolve1d.py index 74057aa8..fd82eb91 100644 --- a/pylops/signalprocessing/convolve1d.py +++ b/pylops/signalprocessing/convolve1d.py @@ -100,7 +100,7 @@ def _matvec(self, x: NDArray) -> NDArray: if type(self.h) is not type(x): self.h = to_cupy_conditional(x, self.h) self.convfunc, self.method = _choose_convfunc( - self.h, self.method, self.dims + self.h, self.method, self.dims, self.axis ) return self.convfunc(x, self.h, mode="same") @@ -109,7 +109,7 @@ def _rmatvec(self, x: NDArray) -> NDArray: if type(self.hstar) is not type(x): self.hstar = to_cupy_conditional(x, self.hstar) self.convfunc, self.method = _choose_convfunc( - self.hstar, self.method, self.dims + self.hstar, self.method, self.dims, self.axis ) return self.convfunc(x, self.hstar, mode="same") @@ -165,7 +165,7 @@ def _matvec(self, x: NDArray) -> NDArray: if type(self.h) is not type(x): self.h = to_cupy_conditional(x, self.h) self.convfunc, self.method = _choose_convfunc( - self.h, self.method, self.dims + self.h, self.method, self.dims, self.axis ) x = np.pad(x, self.pad) y = self.convfunc(self.h, x, mode="same") @@ -177,7 +177,7 @@ def _rmatvec(self, x: NDArray) -> NDArray: if type(self.h) is not type(x): self.hstar = to_cupy_conditional(x, self.hstar) self.convfunc, self.method = _choose_convfunc( - self.hstar, self.method, self.dims + self.hstar, self.method, self.dims, self.axis ) x = np.pad(x, self.padd) y = self.convfunc(self.hstar, x) diff --git a/pylops/utils/backend.py b/pylops/utils/backend.py index ee2649f9..b727e2ef 100644 --- a/pylops/utils/backend.py +++ b/pylops/utils/backend.py @@ -37,18 +37,13 @@ import cupyx.scipy.fft as cp_fft from cupyx.scipy.linalg import block_diag as cp_block_diag from cupyx.scipy.linalg import toeplitz as cp_toeplitz + from cupyx.scipy.signal import convolve as cp_convolve + from cupyx.scipy.signal import correlate as cp_correlate + from cupyx.scipy.signal import fftconvolve as cp_fftconvolve + from cupyx.scipy.signal import oaconvolve as cp_oaconvolve from cupyx.scipy.sparse import csc_matrix as cp_csc_matrix from cupyx.scipy.sparse import eye as cp_eye -if deps.cusignal_enabled: - import cusignal - -cu_message = "cupy package not installed. Use numpy arrays of " "install cupy." - -cusignal_message = ( - "cusignal package not installed. Use numpy arrays of" "install cusignal." -) - def get_module(backend: str = "numpy") -> ModuleType: """Returns correct numerical module based on backend string @@ -138,10 +133,9 @@ def get_convolve(x: npt.ArrayLike) -> Callable: if cp.get_array_module(x) == np: return convolve else: - if deps.cusignal_enabled: - return cusignal.convolution.convolve - else: - raise ModuleNotFoundError(cusignal_message) + # import cusignal + # return cusignal.convolution.convolve + return cp_convolve def get_fftconvolve(x: npt.ArrayLike) -> Callable: @@ -164,10 +158,7 @@ def get_fftconvolve(x: npt.ArrayLike) -> Callable: if cp.get_array_module(x) == np: return fftconvolve else: - if deps.cusignal_enabled: - return cusignal.convolution.fftconvolve - else: - raise ModuleNotFoundError(cusignal_message) + return cp_fftconvolve def get_oaconvolve(x: npt.ArrayLike) -> Callable: @@ -190,11 +181,7 @@ def get_oaconvolve(x: npt.ArrayLike) -> Callable: if cp.get_array_module(x) == np: return oaconvolve else: - raise NotImplementedError( - "oaconvolve not implemented in " - "cupy/cusignal. Consider using a different" - "option..." - ) + return cp_oaconvolve def get_correlate(x: npt.ArrayLike) -> Callable: @@ -217,10 +204,7 @@ def get_correlate(x: npt.ArrayLike) -> Callable: if cp.get_array_module(x) == np: return correlate else: - if deps.cusignal_enabled: - return cusignal.convolution.correlate - else: - raise ModuleNotFoundError(cusignal_message) + return cp_correlate def get_add_at(x: npt.ArrayLike) -> Callable: diff --git a/pylops/utils/deps.py b/pylops/utils/deps.py index 3b84488c..cbd5b3e3 100644 --- a/pylops/utils/deps.py +++ b/pylops/utils/deps.py @@ -1,6 +1,5 @@ __all__ = [ "cupy_enabled", - "cusignal_enabled", "devito_enabled", "numba_enabled", "pyfftw_enabled", @@ -51,35 +50,6 @@ def cupy_import(message: Optional[str] = None) -> str: return cupy_message -def cusignal_import(message: Optional[str] = None) -> str: - cusignal_test = ( - util.find_spec("cusignal") is not None - and int(os.getenv("CUSIGNAL_PYLOPS", 1)) == 1 - ) - if cusignal_test: - try: - import_module("cusignal") # noqa: F401 - - cusignal_message = None - except (ImportError, ModuleNotFoundError) as e: - cusignal_message = ( - f"Failed to import cusignal. Falling back to CPU (error: {e}) . " - "Please ensure your CUDA environment is set up correctly; " - "for more details visit 'https://github.com/rapidsai/cusignal#installation'" - ) - print(UserWarning(cusignal_message)) - else: - cusignal_message = ( - "Cusignal not installed or os.getenv('CUSIGNAL_PYLOPS') == 0. " - f"In order to be able to use {message} " - "ensure 'os.getenv('CUSIGNAL_PYLOPS') == 1' and run " - "'conda install cusignal'; " - "for more details visit ''https://github.com/rapidsai/cusignal#installation''" - ) - - return cusignal_message - - def devito_import(message: Optional[str] = None) -> str: if devito_enabled: try: @@ -207,8 +177,8 @@ def sympy_import(message: Optional[str] = None) -> str: # Set package availability booleans -# cupy and cusignal: the package is imported to check everything is working correctly, -# if not the package is disabled. We do this here as both libraries are used as drop-in +# cupy: the package is imported to check everything is working correctly, +# if not the package is disabled. We do this here as this library is used as drop-in # replacement for many numpy and scipy routines when cupy arrays are provided. # all other libraries: we simply check if the package is available and postpone its import # to check everything is working correctly when a user tries to create an operator that requires @@ -216,11 +186,6 @@ def sympy_import(message: Optional[str] = None) -> str: cupy_enabled: bool = ( True if (cupy_import() is None and int(os.getenv("CUPY_PYLOPS", 1)) == 1) else False ) -cusignal_enabled: bool = ( - True - if (cusignal_import() is None and int(os.getenv("CUSIGNAL_PYLOPS", 1)) == 1) - else False -) devito_enabled = util.find_spec("devito") is not None numba_enabled = util.find_spec("numba") is not None pyfftw_enabled = util.find_spec("pyfftw") is not None