Skip to content

Commit 8d0ccdd

Browse files
rwgkcursoragent
andauthored
[pathfinder] Add DynamicLibUnknownError, DynamicLibNotAvailableError and prepare for v1.4.0 release (#1688)
* fix(pathfinder): restore backward-compatible dynamic lib errors Replace the short-lived ValueError validation path from 1.3.5 with DynamicLibNotFoundError subclasses so downstream exception handling remains compatible while exposing more precise failure reasons. Co-authored-by: Cursor <cursoragent@cursor.com> * docs(pathfinder): prepare 1.4.0 release notes Add the 1.4.0 pathfinder release notes entry and publish the 1.4.0 docs version link in nv-versions.json for the upcoming release. Co-authored-by: Cursor <cursoragent@cursor.com> * docs(pathfinder): add 1.3.5 yank notice Document the planned PyPI yank for cuda-pathfinder 1.3.5 in the release notes, including upgrade guidance to 1.4.0 and links to the tracking issue and PR. Co-authored-by: Cursor <cursoragent@cursor.com> * docs(pathfinder): clarify 1.3.5 exception regression notes Update the 1.3.5 and 1.4.0 release notes to remove the YANK NOTICE and document that the ValueError behavior in 1.3.5 was a regression that is fixed in 1.4.0. Co-authored-by: Cursor <cursoragent@cursor.com> --------- Co-authored-by: Cursor <cursoragent@cursor.com>
1 parent d2909f4 commit 8d0ccdd

File tree

8 files changed

+93
-7
lines changed

8 files changed

+93
-7
lines changed

cuda_pathfinder/cuda/pathfinder/__init__.py

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,13 @@
77
find_nvidia_binary_utility as find_nvidia_binary_utility,
88
)
99
from cuda.pathfinder._binaries.supported_nvidia_binaries import SUPPORTED_BINARIES as _SUPPORTED_BINARIES
10+
from cuda.pathfinder._dynamic_libs.load_dl_common import (
11+
DynamicLibNotAvailableError as DynamicLibNotAvailableError,
12+
)
1013
from cuda.pathfinder._dynamic_libs.load_dl_common import DynamicLibNotFoundError as DynamicLibNotFoundError
14+
from cuda.pathfinder._dynamic_libs.load_dl_common import (
15+
DynamicLibUnknownError as DynamicLibUnknownError,
16+
)
1117
from cuda.pathfinder._dynamic_libs.load_dl_common import LoadedDL as LoadedDL
1218
from cuda.pathfinder._dynamic_libs.load_nvidia_dynamic_lib import load_nvidia_dynamic_lib as load_nvidia_dynamic_lib
1319
from cuda.pathfinder._dynamic_libs.supported_nvidia_libs import (

cuda_pathfinder/cuda/pathfinder/_dynamic_libs/load_dl_common.py

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,14 @@ class DynamicLibNotFoundError(RuntimeError):
1111
pass
1212

1313

14+
class DynamicLibNotAvailableError(DynamicLibNotFoundError):
15+
pass
16+
17+
18+
class DynamicLibUnknownError(DynamicLibNotFoundError):
19+
pass
20+
21+
1422
@dataclass
1523
class LoadedDL:
1624
abs_path: str | None

cuda_pathfinder/cuda/pathfinder/_dynamic_libs/load_nvidia_dynamic_lib.py

Lines changed: 18 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,13 @@
1111
_FindNvidiaDynamicLib,
1212
derive_ctk_root,
1313
)
14-
from cuda.pathfinder._dynamic_libs.load_dl_common import DynamicLibNotFoundError, LoadedDL, load_dependencies
14+
from cuda.pathfinder._dynamic_libs.load_dl_common import (
15+
DynamicLibNotAvailableError,
16+
DynamicLibNotFoundError,
17+
DynamicLibUnknownError,
18+
LoadedDL,
19+
load_dependencies,
20+
)
1521
from cuda.pathfinder._dynamic_libs.supported_nvidia_libs import (
1622
_CTK_ROOT_CANARY_ANCHOR_LIBNAMES,
1723
_CTK_ROOT_CANARY_DISCOVERABLE_LIBNAMES,
@@ -41,6 +47,8 @@
4147
_ALL_SUPPORTED_LIBNAMES: frozenset[str] = frozenset(
4248
(SUPPORTED_WINDOWS_DLLS if IS_WINDOWS else SUPPORTED_LINUX_SONAMES).keys()
4349
)
50+
_ALL_KNOWN_LIBNAMES: frozenset[str] = frozenset(SUPPORTED_LINUX_SONAMES) | frozenset(SUPPORTED_WINDOWS_DLLS)
51+
_PLATFORM_NAME = "Windows" if IS_WINDOWS else "Linux"
4452

4553
# Driver libraries: shipped with the NVIDIA display driver, always on the
4654
# system linker path. These skip all CTK search steps (site-packages,
@@ -205,7 +213,9 @@ def load_nvidia_dynamic_lib(libname: str) -> LoadedDL:
205213
https://github.com/NVIDIA/cuda-python/issues/1011
206214
207215
Raises:
208-
ValueError: If ``libname`` is not a recognized library name.
216+
DynamicLibUnknownError: If ``libname`` is not a recognized library name.
217+
DynamicLibNotAvailableError: If ``libname`` is recognized but not
218+
supported on this platform.
209219
DynamicLibNotFoundError: If the library cannot be found or loaded.
210220
RuntimeError: If Python is not 64-bit.
211221
@@ -278,6 +288,11 @@ def load_nvidia_dynamic_lib(libname: str) -> LoadedDL:
278288
f" Currently running: {pointer_size_bits}-bit Python"
279289
f" {sys.version_info.major}.{sys.version_info.minor}"
280290
)
291+
if libname not in _ALL_KNOWN_LIBNAMES:
292+
raise DynamicLibUnknownError(f"Unknown library name: {libname!r}. Known names: {sorted(_ALL_KNOWN_LIBNAMES)}")
281293
if libname not in _ALL_SUPPORTED_LIBNAMES:
282-
raise ValueError(f"Unsupported library name: {libname!r}. Supported names: {sorted(_ALL_SUPPORTED_LIBNAMES)}")
294+
raise DynamicLibNotAvailableError(
295+
f"Library name {libname!r} is known but not available on {_PLATFORM_NAME}. "
296+
f"Supported names on {_PLATFORM_NAME}: {sorted(_ALL_SUPPORTED_LIBNAMES)}"
297+
)
283298
return _load_lib_no_cache(libname)

cuda_pathfinder/docs/nv-versions.json

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,10 @@
33
"version": "latest",
44
"url": "https://nvidia.github.io/cuda-python/cuda-pathfinder/latest/"
55
},
6+
{
7+
"version": "1.4.0",
8+
"url": "https://nvidia.github.io/cuda-python/cuda-pathfinder/1.4.0/"
9+
},
610
{
711
"version": "1.3.5",
812
"url": "https://nvidia.github.io/cuda-python/cuda-pathfinder/1.3.5/"

cuda_pathfinder/docs/source/api.rst

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,8 @@ locating NVIDIA C/C++ header directories, and finding CUDA binary utilities.
1616
load_nvidia_dynamic_lib
1717
LoadedDL
1818
DynamicLibNotFoundError
19+
DynamicLibUnknownError
20+
DynamicLibNotAvailableError
1921

2022
SUPPORTED_HEADERS_CTK
2123
SUPPORTED_HEADERS_NON_CTK

cuda_pathfinder/docs/source/release/1.3.5-notes.rst

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,12 +8,27 @@
88

99
Released on Feb 23, 2026
1010

11+
.. warning::
12+
13+
``cuda-pathfinder==1.3.5`` introduced a short-lived backward-incompatible
14+
exception regression in ``load_nvidia_dynamic_lib()`` (unsupported
15+
library names incorrectly raising ``ValueError``).
16+
17+
This bug was corrected in ``cuda-pathfinder>=1.4.0``, restoring backward-compatible
18+
``DynamicLibNotFoundError`` subclass behavior while preserving more specific
19+
error signaling.
20+
21+
See `Issue #1684 <https://github.com/NVIDIA/cuda-python/issues/1684>`_ and
22+
`PR #1688 <https://github.com/NVIDIA/cuda-python/pull/1688>`_.
23+
1124
Highlights
1225
----------
1326

1427
* Add support for loading NVIDIA driver libraries (``"cuda"``, ``"nvml"``)
1528
via ``load_nvidia_dynamic_lib()``, and reject unsupported library names
16-
with ``ValueError``.
29+
with ``ValueError`` (**EDIT:** this behavior was
30+
`a regression <https://github.com/NVIDIA/cuda-python/issues/1684>`_
31+
and was corrected in ``cuda-pathfinder>=1.4.0``).
1732
(`PR #1602 <https://github.com/NVIDIA/cuda-python/pull/1602>`_)
1833

1934
* Add bitcode library discovery helpers and public API support, including
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
.. SPDX-FileCopyrightText: Copyright (c) 2025-2026 NVIDIA CORPORATION & AFFILIATES. All rights reserved.
2+
.. SPDX-License-Identifier: Apache-2.0
3+
4+
.. py:currentmodule:: cuda.pathfinder
5+
6+
``cuda-pathfinder`` 1.4.0 Release notes
7+
=======================================
8+
9+
Released on Feb 25, 2026
10+
11+
Highlights
12+
----------
13+
14+
* Add CTK root canary probing for non-standard-path libraries in
15+
``load_nvidia_dynamic_lib()`` (notably ``nvvm``), including spawned child
16+
process isolation for the canary probe.
17+
(`PR #1595 <https://github.com/NVIDIA/cuda-python/pull/1595>`_)
18+
19+
* Restore backward-compatible exception behavior for
20+
``load_nvidia_dynamic_lib()`` argument validation by replacing the short-lived
21+
``ValueError`` introduced in ``1.3.5`` with ``DynamicLibNotFoundError``
22+
subclasses: ``DynamicLibUnknownError`` and ``DynamicLibNotAvailableError``.
23+
(`PR #1688 <https://github.com/NVIDIA/cuda-python/pull/1688>`_)

cuda_pathfinder/tests/test_load_nvidia_dynamic_lib.py

Lines changed: 16 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,8 @@
99
from child_load_nvidia_dynamic_lib_helper import build_child_process_failed_for_libname_message, child_process_func
1010
from local_helpers import have_distribution
1111

12-
from cuda.pathfinder import load_nvidia_dynamic_lib
12+
from cuda.pathfinder import DynamicLibNotAvailableError, DynamicLibUnknownError, load_nvidia_dynamic_lib
13+
from cuda.pathfinder._dynamic_libs import load_nvidia_dynamic_lib as load_nvidia_dynamic_lib_module
1314
from cuda.pathfinder._dynamic_libs import supported_nvidia_libs
1415
from cuda.pathfinder._utils.platform_aware import IS_WINDOWS, quote_for_shell
1516
from cuda.pathfinder._utils.spawned_process_runner import run_in_spawned_child_process
@@ -69,11 +70,23 @@ def test_runtime_error_on_non_64bit_python(mocker):
6970
load_nvidia_dynamic_lib("cudart")
7071

7172

72-
def test_unsupported_libname_raises_value_error():
73-
with pytest.raises(ValueError, match=r"Unsupported library name: 'not_a_real_lib'.*cudart"):
73+
def test_unknown_libname_raises_dynamic_lib_unknown_error():
74+
with pytest.raises(DynamicLibUnknownError, match=r"Unknown library name: 'not_a_real_lib'.*cudart"):
7475
load_nvidia_dynamic_lib("not_a_real_lib")
7576

7677

78+
def test_known_but_platform_unavailable_libname_raises_dynamic_lib_not_available_error(monkeypatch):
79+
load_nvidia_dynamic_lib.cache_clear()
80+
monkeypatch.setattr(load_nvidia_dynamic_lib_module, "_ALL_KNOWN_LIBNAMES", frozenset(("known_but_unavailable",)))
81+
monkeypatch.setattr(load_nvidia_dynamic_lib_module, "_ALL_SUPPORTED_LIBNAMES", frozenset())
82+
monkeypatch.setattr(load_nvidia_dynamic_lib_module, "_PLATFORM_NAME", "TestOS")
83+
with pytest.raises(
84+
DynamicLibNotAvailableError,
85+
match=r"known_but_unavailable.*not available on TestOS",
86+
):
87+
load_nvidia_dynamic_lib("known_but_unavailable")
88+
89+
7790
IMPORTLIB_METADATA_DISTRIBUTIONS_NAMES = {
7891
"cufftMp": r"^nvidia-cufftmp-.*$",
7992
"mathdx": r"^nvidia-libmathdx-.*$",

0 commit comments

Comments
 (0)