Files
xtrain/docs/00-build-chain.md
Gahow Wang c1b204296b docs: backfill T1 build-chain
T1 shipped without a design doc; capture the Rust↔CUDA build chain
(build.rs+nvcc, no_cuda cfg pattern, RAII GpuBuffer, gitea↔dash5 flow).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-15 15:12:55 +08:00

3.2 KiB
Raw Blame History

Phase T1: Rust↔CUDA Build Chain — Design Document

回填文档T1 随 commit 92acf9f 落地scaffold + 构建链路 + vecadd 冒烟测试), 当时未写文档,此处补记,供后续 Phase 回溯。

Goal

打通「Rust 调 CUDA」的最小闭环build.rsnvcccsrc/*.cu 经手写 extern "C" FFI 链入 Rust本地无 GPU/nvcc 时仍能 cargo check。 验收以一个 vector-add kernel 冒烟通过为准。

Module Layout

xtrain/
├── Cargo.toml                  # workspace
├── csrc/
│   └── test/vecadd.cu          # 冒烟用 c[i]=a[i]+b[i]
└── crates/xtrain-cuda/
    ├── build.rs                # 检测 nvcc → 编 .cu / 链 cudart否则发 no_cuda cfg
    └── src/
        ├── ffi.rs              # extern "C" 绑定cudaMalloc/Memcpy/Free…+ kernel launch
        ├── error.rs            # CudaError + check(code)
        ├── device.rs           # device_count / set_device / synchronize
        └── memory.rs           # RAII GpuBufferalloc/H2D/D2H/Drop

Key Design Decisions

build.rs 检测 nvcc缺失则发 no_cuda cfg

if !nvcc_available(&cuda_path) {
    println!("cargo:warning=nvcc not found — skipping CUDA compilation (host-only build).");
    println!("cargo:rustc-cfg=no_cuda");
    return;                       // 不编 .cu、不链 cudart
}
// 否则cc::Build::new().cuda(true)…-gencode=arch=compute_120,code=sm_120
  • 本地机无 GPU/nvcc → 跳过 CUDA 编译host 侧 Rust 照常 cargo check
  • dash5 有 nvcc 12.9 → 实编 .cu,目标 sm_120RTX 5090
  • 必须配 println!("cargo:rustc-check-cfg=cfg(no_cuda)") 声明自定义 cfg 否则新版 rustc 报 unexpected_cfgs warning。

no_cuda cfg 门控 GPU-only 代码

GPU 专属的 kernel-launch FFI 与集成测试用 #[cfg(not(no_cuda))] 包起来:

#[cfg(not(no_cuda))]
unsafe extern "C" {
    pub fn launch_vecadd_f32(a: *const f32, b: *const f32, c: *mut f32, n: i32, stream: CudaStream);
}

测试文件顶用 #![cfg(not(no_cuda))] 整体门控。注意cudaMalloc 等 runtime 符号在 ffi.rs门控(恒声明),本地只 cargo check(不链接)所以无碍; 真正链接发生在 dash5cudart 在)。约定:本地只 check/fmt链接+测试都在 dash5

RAII GpuBuffer

alloc/copy_from_host(H2D)/copy_to_host(D2H)DropcudaFree unsafe impl Send。后续张量层在其上搭 device 存储(见 docs/01-tensor.md)。

验证方法

ssh dash5
export PATH=/usr/local/cuda/bin:/opt/wjh/.cargo/bin:$PATH
cd ~/projects/xtrain && cargo test -p xtrain-cuda -- --nocapture
# vecadd OK: a[i]+b[i]c[i]=3i 通过

本地(无 GPUcargo check 绿build.rs 发 no_cudaGPU 测试编译出局)。

gitea ↔ dash5 同步流

  • origin = git@gitea:gahow/xtrain.git,分支 maingit 身份用 ~/.gitconfig(不 -c 覆盖)。
  • 本地 git push origin main → dash5 cd ~/projects/xtrain && git pull → export PATH 后构建/测试。
  • 连 gitea 会打印无害的 Welcome to VyOS banner可忽略。