Skip to content

Commit 083315c

Browse files
authored
CI: add pytest durations and skip patterngen seeds under sanitizer (NVIDIA#1400)
- Add --durations=0 to CI pytest invocations to report per-test timings. - Add cuda_python_test_helpers.under_compute_sanitizer() and use it to skip the UVM-heavy PatternGen seed test under compute-sanitizer.
1 parent 95e2885 commit 083315c

3 files changed

Lines changed: 44 additions & 5 deletions

File tree

ci/tools/run-tests

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@ if [[ "${test_module}" == "pathfinder" ]]; then
3232
echo "Running pathfinder tests with " \
3333
"LD:${CUDA_PATHFINDER_TEST_LOAD_NVIDIA_DYNAMIC_LIB_STRICTNESS} " \
3434
"FH:${CUDA_PATHFINDER_TEST_FIND_NVIDIA_HEADERS_STRICTNESS}"
35-
pytest -ra -s -v tests/ |& tee /tmp/pathfinder_test_log.txt
35+
pytest -ra -s -v --durations=0 tests/ |& tee /tmp/pathfinder_test_log.txt
3636
# Fail if no "INFO test_" lines are found; capture line count otherwise
3737
line_count=$(grep '^INFO test_' /tmp/pathfinder_test_log.txt | wc -l)
3838
echo "Number of \"INFO test_\" lines: $line_count"
@@ -46,9 +46,9 @@ elif [[ "${test_module}" == "bindings" ]]; then
4646
pip install $(ls "${CUDA_BINDINGS_ARTIFACTS_DIR}"/*.whl)[all] --group test
4747
fi
4848
echo "Running bindings tests"
49-
${SANITIZER_CMD} pytest -rxXs -v tests/
49+
${SANITIZER_CMD} pytest -rxXs -v --durations=0 tests/
5050
if [[ "${SKIP_CYTHON_TEST}" == 0 ]]; then
51-
${SANITIZER_CMD} pytest -rxXs -v tests/cython
51+
${SANITIZER_CMD} pytest -rxXs -v --durations=0 tests/cython
5252
fi
5353
popd
5454
elif [[ "${test_module}" == "core" ]]; then
@@ -79,11 +79,11 @@ elif [[ "${test_module}" == "core" ]]; then
7979
pip install $(ls "${CUDA_CORE_ARTIFACTS_DIR}"/*.whl)["cu${TEST_CUDA_MAJOR}"] --group "test-cu${TEST_CUDA_MAJOR}${FREE_THREADING}"
8080
fi
8181
echo "Running core tests"
82-
${SANITIZER_CMD} pytest -rxXs -v tests/
82+
${SANITIZER_CMD} pytest -rxXs -v --durations=0 tests/
8383
# Currently our CI always installs the latest bindings (from either major version).
8484
# This is not compatible with the test requirements.
8585
if [[ "${SKIP_CYTHON_TEST}" == 0 ]]; then
86-
${SANITIZER_CMD} pytest -rxXs -v tests/cython
86+
${SANITIZER_CMD} pytest -rxXs -v --durations=0 tests/cython
8787
fi
8888
popd
8989
fi

cuda_core/tests/test_helpers.py

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@
1111
from helpers.latch import LatchKernel
1212
from helpers.logging import TimestampedLogger
1313

14+
from cuda_python_test_helpers import under_compute_sanitizer
15+
1416
ENABLE_LOGGING = False # Set True for test debugging and development
1517
NBYTES = 64
1618

@@ -45,6 +47,10 @@ def test_latchkernel():
4547
log("done")
4648

4749

50+
@pytest.mark.skipif(
51+
under_compute_sanitizer(),
52+
reason="Too slow under compute-sanitizer (UVM-heavy test).",
53+
)
4854
def test_patterngen_seeds():
4955
"""Test PatternGen with seed argument."""
5056
device = Device()

cuda_python_test_helpers/cuda_python_test_helpers/__init__.py

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
"IS_WSL",
1717
"libc",
1818
"supports_ipc_mempool",
19+
"under_compute_sanitizer",
1920
]
2021

2122

@@ -37,6 +38,38 @@ def _detect_wsl() -> bool:
3738
libc = ctypes.CDLL("libc.so.6")
3839

3940

41+
def under_compute_sanitizer() -> bool:
42+
"""Return True if the current process is likely running under compute-sanitizer.
43+
44+
This is best-effort and primarily intended for CI, where the environment
45+
is configured by wrapper scripts.
46+
"""
47+
# Explicit override (if we ever want to set this directly in CI).
48+
if os.environ.get("CUDA_PYTHON_UNDER_SANITIZER") == "1":
49+
return True
50+
51+
# CI sets these when compute-sanitizer is enabled.
52+
if os.environ.get("SETUP_SANITIZER") == "1":
53+
return True
54+
55+
cmd = os.environ.get("SANITIZER_CMD", "")
56+
if "compute-sanitizer" in cmd or "cuda-memcheck" in cmd:
57+
return True
58+
59+
# Secondary signals: depending on how tests are invoked, the wrapper name may
60+
# appear in argv (e.g. `compute-sanitizer pytest ...`). This is not reliable
61+
# in general (often argv0 is `python`/`pytest`), but it's cheap and harmless.
62+
argv0 = os.path.basename(sys.argv[0]) if sys.argv else ""
63+
if argv0 in ("compute-sanitizer", "cuda-memcheck"):
64+
return True
65+
if any(("compute-sanitizer" in a or "cuda-memcheck" in a) for a in sys.argv):
66+
return True
67+
68+
# Another common indicator: sanitizer injectors are configured via env vars.
69+
inj = os.environ.get("CUDA_INJECTION64_PATH", "")
70+
return "compute-sanitizer" in inj or "cuda-memcheck" in inj
71+
72+
4073
@functools.cache
4174
def supports_ipc_mempool(device_id: Union[int, object]) -> bool:
4275
"""Return True if mempool IPC via POSIX file descriptor is supported.

0 commit comments

Comments
 (0)