Skip to content

CI: Create Dockerfiles for running NIXL ontop of ROCm#1936

Open
riley-dixon wants to merge 1 commit into
ai-dynamo:mainfrom
riley-dixon:feat/rocm-dockerfile
Open

CI: Create Dockerfiles for running NIXL ontop of ROCm#1936
riley-dixon wants to merge 1 commit into
ai-dynamo:mainfrom
riley-dixon:feat/rocm-dockerfile

Conversation

@riley-dixon

@riley-dixon riley-dixon commented Jul 13, 2026

Copy link
Copy Markdown

The build process introduced in this PR is based on the change introduced by #1900 .

What?

Adds 2 Dockerfiles:

  • Dockerfile.rocm.base
    • Provides a base OS image with some utilities and a minimal install of ROCm. Currently this uses the ROCm pre-release repository to target ROCm 7.14.0.
    • May be replaced once an official ROCm 7.14 image is published.
  • Dockerfile.rocm
    • Based on the existing build.sh script used by NIXL for building the CI environment, each source dependency build & install step are extracted into a separate Docker build stage to streamline the overall build.
    • Note, NIXL is not automatically built into this image.

Adds build-rocm.sh, a copy of build.sh that is slightly modified to build NIXL with ROCm support that may be used by existing tools.

Edits common.sh, tests if nvidia-smi is present prior to use to avoid emitting an error message. Provides a fallback to try amd-smi if nvidia-smi is not present.

Why?

This provides initial support for building & running NIXL in a ROCm environment.

How?

Building the base image:

$ docker buildx build -f .ci/dockerfiles/Dockerfile.rocm.base -t rocm-base-7.14-ubuntu24.04:latest .

Building the NIXL ROCm image:

$ docker buildx build -f .ci/dockerfiles/Dockerfile.rocm --build-arg ROCM_BASE_IMAGE=rocm-base-7.14-ubuntu24.04:latest -t nixl_rocm:latest .

Running the NIXL ROCm image:

$ docker run -it --rm --device=/dev/kfd --device=/dev/dri --group-add video --group-add render --security-opt seccomp=unconfined nixl_rocm:latest

Building NIXL from within the container using build-rocm.sh:

svc-nixl@e59c68830bd9:/nixl$ PRE_INSTALLED_ENV=true PRE_INSTALLED_UCX_ENV=true .gitlab/build-rocm.sh /opt/nixl

Summary by CodeRabbit

  • New Features
    • Added AMD ROCm support via new ROCm-oriented container images (runtime/dev base and full dependency build).
    • Introduced a new CI build script to provision and compile ROCm toolchains and dependencies, including OpenUCX and ROCm-enabled NIXL/bench tooling.
    • Added optional sanitizer-enabled dependency builds and configurable install locations.
  • Bug Fixes
    • Improved CI GPU detection by checking NVIDIA first, then AMD, and safely defaulting when no GPU tooling is available.

@riley-dixon riley-dixon requested review from a team as code owners July 13, 2026 22:23
@copy-pr-bot

copy-pr-bot Bot commented Jul 13, 2026

Copy link
Copy Markdown

This pull request requires additional validation before any workflows can run on NVIDIA's runners.

Pull request vetters can view their responsibilities here.

Contributors can view more details about this message here.

@github-actions

Copy link
Copy Markdown

👋 Hi riley-dixon! Thank you for contributing to ai-dynamo/nixl.

Your PR reviewers will review your contribution then trigger the CI to test your changes.

🚀

@coderabbitai

coderabbitai Bot commented Jul 13, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

📝 Walkthrough

Walkthrough

Adds ROCm base and development Docker images, parallel dependency build stages, non-root runtime assembly, ROCm CI compilation, and AMD GPU detection.

Changes

ROCm build stack

Layer / File(s) Summary
ROCm base image
.ci/dockerfiles/Dockerfile.rocm.base
Configures Ubuntu and AMD prerelease repositories, optional proxy certificates, ROCm version metadata, and ROCm runtime/development packages.
Parallel dependency stages
.ci/dockerfiles/Dockerfile.rocm
Defines the shared builder environment and independent BuildKit stages for native dependencies, UCX, and Rust, uv, Node, and Azurite tooling.
Runtime image assembly
.ci/dockerfiles/Dockerfile.rocm
Aliases dependency stages, merges dependency artifacts and toolchains into a non-root image, configures runtime paths, and defines the entrypoint.
ROCm CI orchestration
.gitlab/build-rocm.sh, .ci/scripts/common.sh
Builds dependencies, UCX, NIXL, and nixlbench with ROCm settings, supports sanitizer and preinstalled environments, and detects NVIDIA or AMD GPUs.

Estimated code review effort: 5 (Critical) | ~90 minutes

Sequence Diagram(s)

sequenceDiagram
  participant ROCmBaseImage
  participant DockerfileRocm
  participant BuildRocm
  participant NIXL
  ROCmBaseImage->>DockerfileRocm: Supply ROCm runtime and development packages
  DockerfileRocm->>BuildRocm: Provide dependency and toolchain environment
  BuildRocm->>NIXL: Build and install NIXL and nixlbench with ROCm enabled
Loading

Suggested reviewers: alexey-rivkin, isdrk, mkhazraee, ovidiusm, tomerg-nvidia

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title is concise and accurately reflects the PR’s main change: adding Dockerfiles for ROCm-based NIXL CI support.
Description check ✅ Passed The description follows the required What/Why/How template and includes the key implementation and usage details.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 11

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In @.ci/dockerfiles/Dockerfile.rocm:
- Around line 555-564: Restrict the sudoers entry created in the user setup RUN
block to only the specific elevation command(s) required by the image, following
the base image’s $SUDO pattern, rather than granting "${LOGIN}" unrestricted
passwordless access with ALL=(ALL) NOPASSWD: ALL. Keep the sudoers file
ownership and permissions unchanged.
- Line 186: Correct the spelling in the ROCm pre-release comment from
“targetting” to “targeting” so codespell and pre-commit checks pass.
- Line 558: Update the useradd invocation in the Dockerfile to include the -l
option alongside the existing high UID configuration, preventing creation of the
oversized lastlog file while preserving the current user setup.
- Line 501: Update the ARCH build-argument handling in both Dockerfile.rocm
stages so direct arm64 builds use the host architecture, preferably by deriving
it from uname -m as in .gitlab/build-rocm.sh; otherwise document the required
--build-arg ARCH value in the build instructions. Ensure the selected ARCH
controls both the Rust installer and lib/${ARCH}-linux-gnu paths.
- Around line 467-489: Update the UCX configure invocation in the ucx-build
stage to source the existing ROCm build environment and pass --with-rocm using
ROCM_INSTALL_PATH. Preserve the remaining configure options and build flow so
UCX is compiled with ROCm GPU-memory support.

In @.ci/dockerfiles/Dockerfile.rocm.base:
- Around line 16-17: Remove the stale build-context comment referencing the
`AMDRootCA.crt` `COPY`; retain the `ROCM_VERSION` image-tagging note because it
still documents the `Dockerfile.rocm` base-image pinning behavior.
- Around line 63-65: Update the ROCm apt source configuration in the
Dockerfile’s repository setup to remove trusted=yes and configure the
AMD-published ROCm GPG key via a keyring and signed-by= option. Preserve the
existing repository URL and architecture while ensuring apt validates package
signatures.

In @.ci/scripts/common.sh:
- Around line 82-83: Update the GPU detection logic in the amd-smi branch of the
common detection flow to use amd-smi’s structured device query rather than
grepping plain static output. Ensure AMD detection is attempted when nvidia-smi
is present but does not detect a usable NVIDIA GPU, instead of being skipped
solely because the command exists, while preserving HAS_GPU as a boolean result.

In @.gitlab/build-rocm.sh:
- Around line 379-381: Remove the unused UCCL_COMMIT_SHA assignment from the
ROCm build script, leaving the existing comments that document UCCL being
skipped for ROCm unchanged.
- Line 175: Remove the trailing spaces from the blank line in the build-rocm.sh
script, leaving the line empty so the trailing-whitespace check passes.
- Around line 2-3: Update the SPDX-FileCopyrightText header in build-rocm.sh to
use the repository-accepted NVIDIA-formatted copyright pattern instead of the
current Advanced Micro Devices, Inc. text, while preserving the existing
SPDX-License-Identifier line.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Enterprise

Run ID: 959f5a0c-3998-4638-a801-560616017e1e

📥 Commits

Reviewing files that changed from the base of the PR and between 619f09e and d710496.

📒 Files selected for processing (4)
  • .ci/dockerfiles/Dockerfile.rocm
  • .ci/dockerfiles/Dockerfile.rocm.base
  • .ci/scripts/common.sh
  • .gitlab/build-rocm.sh

Comment thread .ci/dockerfiles/Dockerfile.rocm Outdated
Comment thread .ci/dockerfiles/Dockerfile.rocm
Comment thread .ci/dockerfiles/Dockerfile.rocm
Comment on lines +555 to +564
RUN if ! getent group "${_GID}" > /dev/null 2>&1; then \
groupadd -g "${_GID}" "${_GROUP}"; \
fi && \
useradd -u "${_UID}" -g "${_GID}" -m -s /bin/bash "${_LOGIN}" && \
mkdir -p "${_HOME}" && \
chown -R "${_UID}":"${_GID}" "${_HOME}" && \
mkdir -p /etc/sudoers.d && \
echo "${_LOGIN} ALL=(ALL) NOPASSWD: ALL" > /etc/sudoers.d/${_LOGIN} && \
chmod 440 /etc/sudoers.d/${_LOGIN} && \
chown root:root /etc/sudoers.d/${_LOGIN}

@coderabbitai coderabbitai Bot Jul 13, 2026

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🔒 Security & Privacy | 🟠 Major | ⚖️ Poor tradeoff

Passwordless, unrestricted sudo for the "non-root" runtime user.

svc-nixl ALL=(ALL) NOPASSWD: ALL grants the runtime user root-equivalent privileges without a password, which largely negates the security benefit of running as a non-root user. If this is only meant for CI/dev convenience, consider scoping the sudoers rule to the specific commands that actually need elevation (e.g., pip install --break-system-packages per the base image's $SUDO pattern) instead of ALL.

🧰 Tools
🪛 Hadolint (2.14.0)

[warning] 555-555: useradd without flag -l and high UID will result in excessively large Image.

(DL3046)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.ci/dockerfiles/Dockerfile.rocm around lines 555 - 564, Restrict the sudoers
entry created in the user setup RUN block to only the specific elevation
command(s) required by the image, following the base image’s $SUDO pattern,
rather than granting "${LOGIN}" unrestricted passwordless access with ALL=(ALL)
NOPASSWD: ALL. Keep the sudoers file ownership and permissions unchanged.

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is based off of the existing Dockerfile.base which currently does these exact steps.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
fd -i "Dockerfile.base" .ci/dockerfiles
echo "---"
rg -n "sudoers|NOPASSWD|useradd" .ci/dockerfiles/Dockerfile.base 2>/dev/null

Length of output: 599


Confirmed — Dockerfile.base (Line 62) already uses the identical ${_LOGIN} ALL=(ALL) NOPASSWD: ALL pattern, so this is existing precedent rather than something new introduced in Dockerfile.rocm.

@riley-dixon Thanks for confirming — that checks out against .ci/dockerfiles/Dockerfile.base Line 62, which uses the exact same pattern. Since this PR is intentionally mirroring the existing base image's setup for consistency, I won't press further on this here. If you'd ever like to tighten the sudoers scope, it'd make sense to do it consistently across both Dockerfiles rather than diverging in this one.


✏️ Learnings added
Learnt from: riley-dixon
Repo: ai-dynamo/nixl PR: 1936
File: .ci/dockerfiles/Dockerfile.rocm:555-564
Timestamp: 2026-07-13T23:01:30.809Z
Learning: In the ai-dynamo/nixl repository, `.ci/dockerfiles/Dockerfile.rocm`'s `final` stage user/sudo setup (creating `svc-nixl` with `ALL=(ALL) NOPASSWD: ALL` sudoers access) intentionally mirrors the existing pattern in `.ci/dockerfiles/Dockerfile.base` (Line 61-64). This is established precedent in the codebase, not a new security regression introduced by the ROCm Dockerfile.

Note: Learnings are effective only in the context of similar code segments. To apply general coding guidelines, please configure review instructions. You can manage existing learnings in the app.

Comment thread .ci/dockerfiles/Dockerfile.rocm Outdated
Comment thread .ci/dockerfiles/Dockerfile.rocm.base
Comment thread .ci/scripts/common.sh
Comment thread .gitlab/build-rocm.sh
Comment on lines +2 to +3
# SPDX-FileCopyrightText: Copyright (c) Advanced Micro Devices, Inc. All rights reserved.
# SPDX-License-Identifier: Apache-2.0

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

📐 Maintainability & Code Quality | 🟠 Major | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Locate the copyright/SPDX check config and its expected pattern.
fd -aH -t f -i copyright .github .ci 2>/dev/null
rg -nH -i 'SPDX-FileCopyrightText|copyright' .github 2>/dev/null | head -n 40
# Show a passing header from an existing script for comparison
fd -aH 'build.sh' .gitlab 2>/dev/null -x sed -n '1,6p' {}

Repository: ai-dynamo/nixl

Length of output: 2266


Update the SPDX copyright line .gitlab/build-rocm.sh uses Advanced Micro Devices, Inc. here, but the repo’s copyright hook only accepts the NVIDIA-formatted SPDX-FileCopyrightText pattern. Align this header with the repo-accepted format before merge.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.gitlab/build-rocm.sh around lines 2 - 3, Update the SPDX-FileCopyrightText
header in build-rocm.sh to use the repository-accepted NVIDIA-formatted
copyright pattern instead of the current Advanced Micro Devices, Inc. text,
while preserving the existing SPDX-License-Identifier line.

Source: Pipeline failures

Comment thread .gitlab/build-rocm.sh Outdated
Comment thread .gitlab/build-rocm.sh Outdated
@riley-dixon riley-dixon force-pushed the feat/rocm-dockerfile branch from d710496 to bfa1aa1 Compare July 13, 2026 22:56

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In @.gitlab/build-rocm.sh:
- Around line 79-82: Define LIBFABRIC_INSTALL_DIR with the default INSTALL_DIR
value before the LD_LIBRARY_PATH, CPATH, PATH, and PKG_CONFIG_PATH export block
in the build script. Ensure these exports and any later libfabric_path usage
receive the resolved directory when PRE_INSTALLED_ENV skips other assignment
logic.
- Around line 387-398: Update the UCX configure invocation in the build script
to include the ROCm installation path via a --with-rocm option using
ROCM_INSTALL_PATH, alongside the existing verbs, dm, gdrcopy, and
UCX_CUDA_BUILD_ARGS options. Preserve the remaining configure flags unchanged.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Enterprise

Run ID: 72f12789-4d03-4772-8509-edb645132af4

📥 Commits

Reviewing files that changed from the base of the PR and between d710496 and bfa1aa1.

📒 Files selected for processing (4)
  • .ci/dockerfiles/Dockerfile.rocm
  • .ci/dockerfiles/Dockerfile.rocm.base
  • .ci/scripts/common.sh
  • .gitlab/build-rocm.sh

Comment thread .gitlab/build-rocm.sh
Comment thread .gitlab/build-rocm.sh
Comment thread .ci/dockerfiles/Dockerfile.rocm.base
The base Dockerfile creates a minimal install of ROCm, along with a few other
pre-requisites before the build image takes over. This may be replaced once
a sufficiently new official ROCm docker image is available.

Dockerfile.rocm is based on the existing build.sh script used by NIXL
for building the NIXL environment. Instead of running in a script, the
source dependency build & install steps are extracted into a multi-stage
Docker build process to streamline the overall build.

A build-rocm.sh is a copy of build.sh that is slightly modified to build
NIXL with ROCm support that may be used by existing tools.

Signed-off-by: Riley Dixon <riley.dixon@amd.com>
@riley-dixon riley-dixon force-pushed the feat/rocm-dockerfile branch from 8d11616 to a473bc2 Compare July 14, 2026 01:13

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In @.ci/dockerfiles/Dockerfile.rocm:
- Around line 583-602: Update the runtime PATH definition near ENV NVM_DIR to
include the nvm versioned bin directory under ${NVM_DIR}/versions/node, ensuring
nvm-installed node, npm, and azurite binaries are directly executable without
sourcing nvm.

In @.ci/dockerfiles/Dockerfile.rocm.base:
- Around line 62-66: Update the ROCm repository setup RUN command to create
/etc/apt/keyrings before the gpg --dearmor redirect writes amdrocm.gpg. Keep the
existing key download and repository configuration unchanged.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Enterprise

Run ID: aa1db8d2-7cac-4a85-84c2-fc031485c18b

📥 Commits

Reviewing files that changed from the base of the PR and between bfa1aa1 and a473bc2.

📒 Files selected for processing (4)
  • .ci/dockerfiles/Dockerfile.rocm
  • .ci/dockerfiles/Dockerfile.rocm.base
  • .ci/scripts/common.sh
  • .gitlab/build-rocm.sh

Comment thread .ci/dockerfiles/Dockerfile.rocm
Comment thread .ci/dockerfiles/Dockerfile.rocm.base
@riley-dixon

riley-dixon commented Jul 14, 2026

Copy link
Copy Markdown
Author

@ Reviewers The copyright check is failing on .gitlab/build-rocm.sh because it hardcodes a requirement for NVIDIA CORPORATION & AFFILIATES in the SPDX header — this file carries AMD's copyright since I authored it, with the same Apache-2.0 license as the rest of the project.

I noticed the check already exempts .ci/* and .github/*, which is why my other two new files under .ci/dockerfiles/ with the same AMD header aren't flagged — only .gitlab/build-rocm.sh is, since .gitlab/ isn't in that exemption list.

Could you please clarify how you'd like external-contributor copyright attribution handled here — e.g. extending the existing directory exemption to .gitlab/, a dual-copyright line, or something else? Thank you.

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.

1 participant