Skip to content

Avoid scalar indexing in remove_edges - #672

Merged
CarloLucibello merged 1 commit into
JuliaGraphs:masterfrom
alonsoC1s:remove_edges_gpu
Jul 22, 2026
Merged

Avoid scalar indexing in remove_edges#672
CarloLucibello merged 1 commit into
JuliaGraphs:masterfrom
alonsoC1s:remove_edges_gpu

Conversation

@alonsoC1s

Copy link
Copy Markdown
Contributor

Fixes #668 by creating a boolean mask on GPU when the inputs are, without modifying the effects in normal CPU mode

@alonsoC1s

Copy link
Copy Markdown
Contributor Author

Failures seem unrelated

@CarloLucibello

Copy link
Copy Markdown
Member

Can you add a gpu test in GNNGraphs/test/transform.jl?

@alonsoC1s

Copy link
Copy Markdown
Contributor Author

Of course. Is it enough to add them to that file for the GPU code to be tested, or should I modify the testing configuration/flags/functions?

@CarloLucibello
CarloLucibello merged commit be0253d into JuliaGraphs:master Jul 22, 2026
5 of 10 checks passed
CarloLucibello added a commit that referenced this pull request Jul 22, 2026
* Fix GPU scalar indexing in remove_edges and getgraph

remove_edges (#668): the follow-up to #672 built the keep-mask with
`fill_like(edges_to_remove, true)`, which produced a mask of the wrong
length (that of `edges_to_remove`, not the number of edges) and wrong
eltype (Int instead of Bool) — breaking even the existing CPU tests.
Build the mask from `s` with `fill_like(s, true, Bool, length(s))` so it
lives on the graph's device and does logical indexing correctly.

getgraph (#161): the subgraph extraction uses scalar Dict lookups and
comprehensions that can't run on the GPU. Detect a non-CPU device, run
the extraction on the CPU, and move the result back to the original
device.

Also restores the indentation of the commented add_snapshot!/
remove_snapshot! exports mangled by #672, and adds :gpu-tagged
regression tests for both functions.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* Reference PR #691 in the changelog entries

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* Make getgraph GPU-native for COO graphs instead of CPU round-trip

The first cut fixed getgraph on the GPU by moving the graph to the CPU
and back. That works but forces a full device<->host sync and its cost
grows with the graph size.

Instead, express the COO path (the common case, which has a dense
graph_indicator) entirely with scatter/gather/cumsum, which run natively
on the GPU: build the node keep-mask from a per-graph boolean lookup,
relabel nodes via cumsum and graphs via a scatter, and select edges with
`node_mask[s]`. Indexing goes through the integer vectors
`kept_nodes`/`kept_edges` (one `findall` each) rather than repeated
boolean masks, to keep the number of GPU synchronizations low.

Adjacency-matrix graphs still fall back to the CPU: they need submatrix
indexing and store `graph_indicator` as a `SparseVector`, neither of
which is GPU-friendly.

The result stays on the original device and, on real hardware, avoids the
host transfer entirely; on large batches it is dramatically faster than
the round-trip. The GPU test now covers all graph types (COO native +
sparse/dense fallback), node/edge features, weights, and `nmap`.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* docs(AGENTS): document running and reproducing GPU tests

Add a local CUDA test command and note the cuDNN / allowscalar(false)
setup needed to reproduce a :gpu test item in the REPL — the gotcha being
that gpu_device() silently falls back to the CPU when cuDNN isn't loaded.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Scalar indexing triggered by remove_edges

2 participants