Skip to content

feat(cco): merge dev/cco — Collective Communication Object (CCO) module#449

Open
jhchouuu wants to merge 56 commits into
mainfrom
dev/cco
Open

feat(cco): merge dev/cco — Collective Communication Object (CCO) module#449
jhchouuu wants to merge 56 commits into
mainfrom
dev/cco

Conversation

@jhchouuu

@jhchouuu jhchouuu commented Jul 6, 2026

Copy link
Copy Markdown
Collaborator

Summary

Merges the dev/cco development branch into main, landing the CCO (Collective Communication Object) module — mori's self-contained collective/communication layer (formerly xshmem). Highlights:

  • Host + device API: device API, DevCommRequirements, connection types, Team API, resource/window pattern; single-header consolidation and shmem decoupling with a self-contained bootstrap.
  • GDA scale-out: BNXT GDA (per-packet PSN + per-peer doorbell grouping), ionic doorbell-ring impl, mlx5; compile-time per-NIC GDA dispatch; GDA barrier + counter impls and device-API unit tests.
  • LSA intra-node: flat symmetric-VA P2P, LSA barrier API, LSA tests under tests/cpp/cco.
  • FlyDSL device bindings (feat(cco): FlyDSL device bindings + C++/Python examples + pip packaging #426) + C++/Python examples + pip packaging.
  • CCO Python runtime API (feat(cco): add support for cco python runtime api #422): Communicator (alloc_mem / register_window / create_dev_comm / barrier), UniqueId, resources.
  • Bench + tests + CI: cco p2p benches, cco unit-test harness, ci_cco workflow, and docker/Dockerfile.cco.
  • Docs: user-facing docs/MORI-CCO-GUIDE.md (linked from the docs index).

Merge status — conflicts resolved ✅

dev/cco had been kept current with main via a squash-sync (#410) rather than a merge, so main was merged into dev/cco here and the resulting divergence resolved. The branch is now MERGEABLE (no conflicts). How the ~57 conflicts + a few clean-but-wrong auto-merges were handled:

  • Squash artifacts in non-cco areas (src/umbp, src/io, src/application internals, tests, docs, CI, tuning_configs) → took main's current version.
  • umbp/master_client.h: the squash auto-merge produced duplicate declarations (semantic dup, no textual conflict) → reset to main.
  • src/ops/dispatch_combine/intranode.hpp: a stale copy still defined EpDispatchIntraNodeLLKernel_body that main had moved to intranode_ll.hpp (duplicate definition under AOT ops build) → reset to main.
  • RegisterRdmaMemoryRegionDmabufIova0 (cco's iova=0 dmabuf MR for the BNXT-GDA flat-VA path) is a genuine cco addition to the application RDMA layer that a naive "take main" dropped → re-applied onto main's rdma.hpp / rdma.cpp.
  • Verified symmetric_memory.cpp / ibverbs.cpp / anvil.cpp had no genuine cco change (take-main correct); shmem_ibgda_kernels.hpp bugfix: shm spike bandwidth #431 fix already in main.
  • src/cco merged cleanly and is unchanged.

Validation: full pip install . build (incl. AOT ops, examples) succeeds in the Dockerfile.cco container after the merge; mori.cco imports.

Self-contained libmori_cco.so

libmori_cco.so now absorbs the application layer statically, so cco consumers link only libmori_cco.so (no runtime dependency on libmori_application.so) with no application-symbol leakage:

  • application sources → a shared OBJECT library feeding both mori_application (SHARED, unchanged for shmem/io/ops/…) and a new mori_application_static.
  • mori_cco absorbs the static archive via --whole-archive and localizes all absorbed static-archive symbols with --exclude-libs,ALL; only the cco* API stays exported (exported symbols dropped 151 → 15). The ibverbs dlopen shim is embedded, so cco links neither libmori_application.so nor libibverbs.
  • cco-only C++ targets (tests/cpp/cco, cco benchmarks, cco examples) link only mori_cco.

For the LSA scenario this means: include only mori/cco/cco.hpp and link only libmori_cco.so (verified end-to-end).

Style / pre-commit ✅

The cco files had been committed without the pre-commit gate; applied it here (missing license headers, black + clang-format, ruff), and trimmed verbose comments / dropped stale references.

CI ✅

  • ci_cco.yml triggers on main (was the temporary dev/cco branch) and chowns the workspace back to the runner in Cleanup.
  • src/umbp/CMakeLists.txt gates its tests subdir behind BUILD_TESTS so non-test builds (e.g. BUILD_EXAMPLES=ON) no longer FetchContent googletest and fail on github-less runners.

Not included (intentional)

  • The FlyDSL dispatch/combine kernel (dispatch_combine_v2, cco-LSA intranode MoE ops v2) is not part of this PR — it lands in a follow-up PR on top of merged dev/cco.

Test plan

  • Conflicts resolved; branch MERGEABLE
  • Full mori build (incl. AOT ops + examples) in docker/Dockerfile.cco container
  • LSA scenario: only cco.hpp + libmori_cco.so
  • pre-commit clean
  • CCO unit tests: tools/run_cco_tests.sh <build> 4 (the ci_cco workflow)
  • Regression on umbp/io/application main test suite

jhchouuu and others added 30 commits May 25, 2026 02:16
XSHMEM provides explicit comm-handle-based GPU communication with three
transport paths (P2P/RDMA/SDMA), replacing the singleton-based SHMEM design.

Host API (Phase 1 complete):
- XshmemCommCreate/Destroy: VMM flat VA reservation, RDMA QP setup via
  Context, SDMA device handles, internal sync, groupId for LocalBootstrap
- XshmemMemAlloc/Free: VMM alloc (hipMemCreate + hipMemMap), local only
- XshmemWindowRegister/Deregister: P2P FD exchange + peer mapping, RDMA MR
  registration (ibv_reg_dmabuf_mr iova=0), rkey Allgather, SDMA signals,
  GPU-side XshmemWindowDevice construction
- XshmemDevCommCreate/Destroy: IBGDA context (QP endpoints + signal/counter
  buffers + MR registration), window lookup table, H2D copy

Key design decisions:
- iova=0 RDMA: raddr = offset within window, no remote VA needed
- Flat VA addressing: winBase + pe * stride4G << 32 (NCCL-compatible)
- Per-window MR with XshmemIbgdaWin{peerRkeys, lkey}
- XshmemIbgdaContext bundles QP endpoints + signal/counter resources
- Window table (linked list) for XshmemFindWindow pointer lookup
- One DevComm per Comm (QP state safety)
- BUILD_TORCH_BOOTSTRAP default OFF

Also adds RegisterRdmaMemoryRegionDmabufIova0 to mori_application RDMA layer.

Tests: single-process multi-thread, fork multi-process, MPI — all 8-GPU on
MI355X + AINIC verified.
Each XshmemDevCommCreate now creates fresh QPs via
Context::CreateAdditionalEndpoints + ConnectAdditionalEndpoints,
instead of copying the original QP set from CommCreate.
- add XshmemGda object define
- add xshmem gda device api define
Module-wide rename. No functional changes.

- Directories: include/mori/xshmem -> include/mori/cco,
  src/xshmem -> src/cco, tests/cpp/xshmem -> tests/cpp/cco
- Files: xshmem_*.{hpp,cpp} -> cco_*.{hpp,cpp},
  test_xshmem_*.cpp -> test_cco_*.cpp, xshmem.md -> cco.md
- Identifiers: XSHMEM -> CCO, Xshmem -> Cco, xshmem -> cco
  (namespace mori::cco, CcoComm, CcoDevComm, CcoWindowDevice,
   CcoCommCreate, CcoMemAlloc, CcoWindowRegister, CcoDevCommCreate,
   CcoBarrierAll, CcoIbgdaContext, CcoIbgdaWin, CcoGda*, etc.)
- CMake: BUILD_XSHMEM -> BUILD_CCO, target mori_xshmem -> mori_cco

Co-authored-by: Cursor <cursoragent@cursor.com>
* gda_device_api.hpp: include path was "mori/Cco/gda/gda_device_common.hpp"
  (capital C) — actual directory is lowercase cco/. Originated from a typo
  in the initial xshmem commit (4f3aac9) where it wrote "mori/Xshmem/..."
  with a capital X; carried into cco by the module rename.
* gda_device_common.hpp: was missing #pragma once, would break under
  multiple includes. Added license header for consistency too.

Co-authored-by: Cursor <cursoragent@cursor.com>
…nvention

Codify the naming split that already emerged organically in the codebase:

  * Host API (CommCreate / MemAlloc / WindowRegister / DevCommCreate / ...)
    keeps mori's Google C++ style: PascalCase free fns with Cco prefix,
    camelCase fields, SCREAMING_SNAKE constants.

  * Device API (CcoGda / CcoLsa / CcoSdma / CcoLsaBarrierSession) follows
    NCCL device API style (nccl_device/gin.h, nccl_device/lsa_barrier.h):
      - PascalCase session class with Cco prefix
      - camelCase member methods (put, flushAsync, readSignal)
      - Cco<Module>_<Tag> tag types with underscore separator
      - Cco<...>_t typedefs for handles, _ prefix for internal members
      - namespace-internal free functions are camelCase WITHOUT Cco prefix
        (the namespace already disambiguates)

This split mirrors the existing layering: host operates over
mori_application primitives, device operates over per-backend session
contexts. The convention is documented in cco.md so future contributors
don't have to guess.

Concretely:

* cco.md: new "命名约定 (Naming Convention)" section right after 背景,
  with full rule tables for host vs device and 4 共同约定 bullets;
  Device API section rewritten from outdated mori-style CcoP2pPutThread/
  CcoRdmaPutThread free fns to NCCL-style CcoGda / CcoLsa / CcoSdma
  session classes with a user-facing kernel usage example; file
  structure diagram extended with future lsa/ and sdma/ subdirs.

* cco_device_api.hpp: dropped redundant Cco{Rdma,P2p,Sdma}PutThread,
  CcoReadSignal/WaitSignal/Counter, CcoBarrierAllBlock — all subsumed
  by per-backend session classes. Kept the genuinely common helpers
  (findWindow, getPeerPtr, getLocalPtr) and renamed to camelCase
  without Cco prefix to match the new convention. Phase 2 session
  classes (CcoLsa, CcoSdma, CcoLsaBarrierSession) are noted in a
  placeholder block.

* cco_device.hpp: umbrella header now pulls in both the common device
  helpers and the GDA backend; removed redundant include of
  gda_device_common.hpp (transitively pulled by gda_device_api.hpp).

No source files (.cpp) are touched; this is a header + docs change only.

Co-authored-by: Cursor <cursoragent@cursor.com>
…ce Window pattern (#336)

Brings CCO host API to the Phase 1 + Phase 2 surface. After this PR, CCO has:
- Stable user-facing API: `CcoCommCreate/Destroy`, `CcoMemAlloc/Free`, `CcoWindowRegister/Deregister` (two overloads), `CcoDevCommCreate/Destroy`, `CcoBarrierAll`.
- Forward-compatible `CcoDevCommRequirements` (size/magic/version triplet) driving GDA connection type + per-DevComm resource sizing.
- All four `CcoGdaConnectionType` modes implemented and tested: `NONE`, `CROSSNODE` (default), `FULL`, `RAIL` (same-lsaRank cross-node).
- **Resource window** pattern: a single symmetric, dma-buf-MR registered, P2P-imported buffer backing every per-DevComm session resource (IBGDA signal pool + LSA barrier slabs). Allocated via VMM (`hipMemCreate` + `hipMemMap`), NOT `hipMalloc`, to satisfy LSA flat-VA addressing.
- Four barrier handles in `CcoDevComm`:
  - `lsaBarrier` — standalone LSA barrier (resource window slab)
  - `hybridLsaBarrier` — hybrid LSA half (resource window slab)
  - `railGdaBarrier` — standalone rail GDA (IBGDA signal slots)
  - `hybridRailGdaBarrier` — hybrid rail half (IBGDA signal slots)
- `resourceWindow` + `resourceWindow_inlined` (32B kernel-cmem copy) in `CcoDevComm`. Kernels read `winBase` / `stride4G` / `ibgdaWin.{lkey,peerRkeys}` directly from cmem with no GPU global memory dereference.
- `Context` refactored into capability discovery (`PeerCapabilities`) + policy (`peerMask`), letting CCO drive QP setup without touching Context's defaults.
- `HeapVAManager` replaces the original inline slot allocator for flat-VA management.
- SPMT (single-process multi-thread) safe across bootstrap / Context / anvil / SDMA signal pool. `Context::SameProcessP2P(peer)` switches SDMA signal exchange between IPC handle and raw VA + `hipDeviceEnablePeerAccess`.
* feat(cco): typo and add gda primitive impl
ROCm 7.0 introduced a regression in `hipMemSetAccess`: when validating
sub-buffer coverage for a hipMemAddressReserve parent containing multiple
hipMemMap'd sub-buffers, the driver iterates from the parent's sub-buffer
0 (ignoring the ptr argument), so the call fails with hipErrorInvalidValue
whenever size != prefix sum starting at sub-buffer 0.

This affects CCO's symmetric flat-VA pattern (one reserve + many maps).
Reproducible: alloc(4 MiB) then alloc(4 KiB) → 2nd hipMemSetAccess fails.

Status:
  - Bug present in all released ROCm 7.x (verified 7.0 → 7.2.3).
  - Fix merged to clr/develop on 2026-01-26 as rocm-systems#2451
    (commit be8bcd059); not yet cherry-picked to any release branch.
  - External report: rocm-systems#2516 (open since 2026-01).

This commit patches the dev docker image to build a fixed libamdhip64.so
from the base image's matching rocm-X.Y.Z release branch plus the
cherry-picked fix. Auto-detects ROCm version from /opt/rocm/.info/version
and the target so-stamp from the libamdhip64.so.7 symlink, so the same
RUN block works across ROCm 7.2.0/1/2/3 on Ubuntu 22.04/24.04. ROCm 6.x
base images skip the patch (no bug).

Verified (cherry-pick + build + CCO test pass):
  - rocm-7.2.0 / 7.2.1 / 7.2.2 / 7.2.3 × Ubuntu 22.04 / 24.04
* Implement lsa barrier API (#338)

Co-authored-by: Qizhou Zhang <qizzhang@smci355-ccs-aus-n06-21.prov.aus.ccs.cpe.ice.amd.com>
* feat(cco): add device api ut and refactor the gda code hierarchy to decouple low-level nic operations from high-level window-base api

* fix sigal mr offset

* fix ut building failed
rm multimem in lsa (#350)

Co-authored-by: Qizhou Zhang <qizzhang@smci355-ccs-aus-n06-21.prov.aus.ccs.cpe.ice.amd.com>
* add lsa mem check example & fix double unmap in ccoCommDestroy
* Hip mem leak will be resolved by this PR: ROCm/rocm-systems#4363

Co-authored-by: Qizhou Zhang <qizzhang@smci355-ccs-aus-n06-21.prov.aus.ccs.cpe.ice.amd.com>
(format) fmt source files

Co-authored-by: Qizhou Zhang <qizzhang@smci355-ccs-aus-n08-25.prov.aus.ccs.cpe.ice.amd.com>
* Add uts for host and lsa api 

Co-authored-by: Qizhou Zhang <qizzhang@smci355-ccs-aus-n06-21.prov.aus.ccs.cpe.ice.amd.com>
* reorganize device header

Co-authored-by: Qizhou Zhang <qizzhang@smci355-ccs-aus-n06-21.prov.aus.ccs.cpe.ice.amd.com>
* add support for gda coop group

* add signal test
…contained bootstrap (#375)

- Consolidate the CCO surface into one header (include/mori/cco/cco.hpp);
  delete the split headers. GDA impl moved to mori::cco::impl; gda namespace
  dropped.
- Decouple cco from shmem via application::RdmaEndpointDevice.
- Add ccoUniqueId + ccoGetUniqueId + ccoCommCreate(uid, nRanks, rank, ...):
  bootstrap with only cco.hpp; BootstrapNetwork* overload kept.
- LSA examples bootstrap via ccoUniqueId; extend host-API + barrier coverage.

Verified on MI300X+BNXT: builds; cco tests pass single-node & 2-node; LSA
examples pass.
…loc / copies)

ccoDevCommCreate now fills a caller-provided host ccoDevComm in place
  int ccoDevCommCreate(ccoComm*, const ccoDevCommRequirements*, ccoDevComm* outDevComm);
instead of allocating one on the device and returning a pointer. The struct
holds device pointers but lives on the host, so kernels take it by value (it
lands in kernel-arg space — no per-access GPU-memory dereference). This drops
the device allocation + HostToDevice copy in create, and the DeviceToHost copy
every consumer previously did to obtain a by-value snapshot.

ccoDevCommDestroy reads the host struct directly (no copy-back) and no longer
frees a device struct; it still releases the device resources the struct
references (QP endpoints, SDMA pools, window table).
…#377)

* feat(cco): support BNXT for GDA + runtime provider dispatch in gda tests
* refactor(cco): split GDA device layer into cco_scale_out.hpp
* test(cco): move LSA examples into the cco test suite
Add some gda UTs & abstract the common component of cco tests
---------

Co-authored-by: Qizhou Zhang <qizzhang@smci355-ccs-aus-n06-21.prov.aus.ccs.cpe.ice.amd.com>
quietUntil polls the CQ in a nested loop until doneIdx reaches targetIdx. The inner loop breaks when a poll yields no new CQE — which happens normally while a transfer is still in flight — and the outer loop then hit an unconditional break, exiting the whole function without re-checking whether the target was actually reached. So when the CQE wasn't ready yet, quietUntil returned early and ccoGda::flush() returned mid-transfer, stopping the timer too soon

Co-authored-by: Qizhou Zhang <qizzhang@smci355-ccs-aus-n06-21.prov.aus.ccs.cpe.ice.amd.com>
…#393)

* refactor(cco): make cco.hpp self-contained and HIP-runtime-header-free
* feat(cco): compile-time per-NIC GDA provider dispatch
* refactor(cco): keep GDA provider as an informational ccoComm field
Motivation
Add a CCO p2p microbenchmark suite (put/get × bw/latency) mirroring benchmark/shmem/, covering both transports: LSA (intra-node P2P) and IGBDA (cross-node RDMA).

Technical Details
New benchmark/cco/ with 4 binaries; transport chosen via MORI_DISABLE_P2P. Issues found & fixed:

quietUntil (PSD) returned mid-transfer — unconditional break abandoned the CQ wait, inflating BW to multi-TB/s. Now breaks only on error.
LSA bw cache absorption — added per-iter __threadfence_system().
32-QP doorbell contention destabilized mid-size BW.
Build: BUILD_BENCHMARK now implies MPI; util.cpp builds as CXX.

Test Result
LSA/IGBDA saturate near NIC limit; GDA tests pas

Co-authored-by: Qizhou Zhang <qizzhang@smci355-ccs-aus-n06-21.prov.aus.ccs.cpe.ice.amd.com>
QizhouZhang97 and others added 21 commits June 17, 2026 15:55
minor fix benchmark

Co-authored-by: Qizhou Zhang <qizzhang@smci355-ccs-aus-n06-21.prov.aus.ccs.cpe.ice.amd.com>
…son (#407)

LSA scope & sync aligned with shmem:
all block threads now always participate — scope_size only sets copy granularity (block strides the whole chunk, warp per-wavefront, thread copies its own contiguous segment), instead of the old behavior that wrongly cut the thread count for thread/warp scope. Added a per-round cross-block barrier (mirrors shmem's bw_cross_block_barrier_round) so the timed window includes the same synchronization, removing the artificial mid-size speedup.

---------

Co-authored-by: Qizhou Zhang <qizzhang@smci355-ccs-aus-n06-21.prov.aus.ccs.cpe.ice.amd.com>
Merge latest `main` into `dev/cco` and adapt cco's GDA layer to the changes it
brings (notably #395 bnxt collapsed-CQ + #405 include-hygiene refactor).
- BNXT GDA: advance PSN by packet count (not WQE count) on the
  warp-aggregate path; reserve-gate drains to the doorbelled snapshot
  to avoid SQ self-deadlock. MLX5/Ionic unchanged.
- Group GDA doorbells per peer (__ballot) so mixed-peer thread/warp
  scope rings once per peer instead of coalescing into a dropped
  doorbell — unblocks thread/warp-scope bandwidth.
- Rename WarpMode→ThreadMode (sub-mode is thread-scope, per-thread
  work unit): ccoGdaThreadIndependent / ccoGdaThreadAggregate.
- Bench: per-message size + unit count, thread_agg scope, Mpps column.
* feat(cco): add support for cco python runtime api

* add example

* add cco decomm device bak for kernel launch

* fix device ptr issue

* remove host binding workaround
…lti-thread mode

# Root cause
ExchangeFileDescriptors bound each server socket lazily inside a per-peer
loop and called a blocking accept() before binding later peers. A client
could only connect once the server's loop reached it. In fork mode ranks enter
near-simultaneously and win the race; in thread mode they serialize on HIP
locks, so a server stuck in accept() hadn't yet bound the socket a later
client needed → ENOENT, 5s timeout, then a cascading bail.

Fix
local_bootstrap.cpp: bind+listen all server sockets up front, then
accept/connect; widen the connect retry window.
cco_init.cpp: drop the leader-side blanket unlink (could delete a live
socket) and add a per-clique discriminator to the socket path.
Fix GDA barrier hang on MLX5
The barrier deadlocked on MLX5: a rank rang all N atomic-signal doorbells, but
peers saw only one and spun forever in the phase-2 wait.

Cause: the multi-lane path assumed MLX5's per-QP dbrAddr made doorbell stores
independent, so lanes rang directly. On this GPU the per-QP doorbell stores
issued in one SIMT step coalesce — only one survives, the rest are dropped, so
those QPs' WQEs are never fetched and peers hang.

Fix: route MLX5 through the same per-lane serialized ringDoorbellWalk PSD/BNXT
already use.
…ng (#426)

- FlyDSL GDA/LSA device-IR bindings: scalar FFI, template axes monomorphized into tagged symbols (no runtime dispatch), bitcode JIT per arch+NIC.
- C++ examples (examples/cco/cpp) + examples/cco split into python/ + cpp/.
- End-to-end pip packaging: optional flydsl extra; BUILD_EXAMPLES / BUILD_BENCHMARK install binaries into the package.
- fix: ccoCommDestroy unmaps symmetric allocations before freeing the flat VA.
Fix MLX5 collapsed-CQ completion reconstruction (stale-read / 16-bit wrap)
Problem
Mlx5CollapsedCqDrain (and the cco quietUntil equivalent) reconstructed the
32-bit completion counter from the CQE's low 16 bits by patching the high bits and
adding 0x10000 on an apparent wrap. On a shared QP, a stale/concurrent CQE read
(counter just behind doneIdx) looks like a 64K wrap, so doneIdx gets shoved
past postIdx — after which every quiet early-exits and stops waiting for real
completions.

Fix
Reconstruct as cons + forward 16-bit distance, accepting the advance only if it
falls inside the in-flight window (cons, dbTouchIdx]:

Handles 16-bit wrap automatically (small delta added to the full 32-bit cons).
Rejects stale/torn reads (they produce a near-65536 delta, outside the window).
window is signed: once doneIdx catches up to dbTouchIdx (window <= 0)
every delta is rejected — avoids the unsigned underflow that defeated the bound
when cons races ahead of a stale dbTouchIdx read.
Changes
shmem/shmem_ibgda_kernels.hpp, cco/cco_scale_out.hpp: windowed signed
reconstruction (+ low-volume [DRAIN-BUG] tripwire).
Bench default iters 10 → 100 (shmem & cco) to average out a hardware-level
small-transfer timing jitter.
Testing
shmem/cco p2p_get_bw and p2p_put_bw stable across many runs; tripwire never
fires; data verified correct.
Resolve the squash-sync divergence: dev/cco was previously kept current
with main via a squash (#410) rather than a merge, so main's later commits
conflicted against the stale snapshot. All 57 conflicts were in non-cco
areas (src/umbp, src/io, src/application, tests, docs, CI, tuning_configs);
resolved by taking main's current version for every one. src/cco (the
module) merged cleanly and is unchanged.
…ang-format, ruff)

The cco module files were committed without the pre-commit gate; apply it now
so the dev/cco->main PR passes CI: insert missing license headers, black +
clang-format reformat, and drop an unused `win` binding (ruff F841) in the
barrier example.
Condense the redundant header/self-contained/intrinsic-wrapper blocks and the
over-explained resource-window notes; keep the safety guards, HARD-CONTRACT
invariants, and addressing formulas. Remove stray external-project references.
cco.md was an internal agent handoff doc (not a user guide) accidentally
committed to the repo root; it also carried external references. Remove it.
…ide symbols)

Absorb the application layer statically into libmori_cco.so so consumers link
only libmori_cco.so with no runtime dependency on libmori_application.so, and
no application-symbol leakage.

- application sources -> shared OBJECT library feeding both mori_application
  (SHARED, unchanged interface for shmem/io/ops/…) and a new
  mori_application_static.
- mori_cco absorbs the static archive via --whole-archive and localizes all
  absorbed static-archive symbols with --exclude-libs,ALL; only cco* API stays
  exported. Drops the mori_application/ibverbs links (ibv dlopen shim embedded).
- cco-only C++ targets (tests/cpp/cco, cco benchmarks) link only mori_cco;
  add find_package(MPI) where MPI was previously pulled in transitively via
  mori_application. cco examples already linked only mori_cco.
The privileged container runs as root and leaves root-owned files in
GITHUB_WORKSPACE, breaking the runner's later cleanup/checkout. chown the
workspace back to the runner uid:gid before removing the container.
Comment thread .github/workflows/ci_cco.yml Outdated
jhchouuu added 5 commits July 6, 2026 15:22
The dev/cco<-main merge left a stale copy of EpDispatchIntraNodeLLKernel_body in
intranode.hpp (a squash-sync artifact); main had moved it to intranode_ll.hpp.
Building AOT ops (BUILD_OPS_DEVICE=ON, as the JAX CI does) pulled in both headers
and failed with duplicate-definition / redefined-default-argument. Take main's
intranode.hpp so the body lives only in intranode_ll.hpp.
dev/cco is merging into main, so the cco CI (originally a temp job for the
dev/cco branch) should run on push to main and PRs targeting main.
umbp added its tests subdir unconditionally, so any BUILD_UMBP=ON build (even
BUILD_TESTS=OFF, e.g. BUILD_EXAMPLES=ON) configured umbp tests and FetchContent'd
googletest from github — breaking builds on github-less runners. Gate it behind
BUILD_TESTS like the top-level tests/cpp.
…emented

Drop the stale 'TODO: not yet enforced' on FULL/RAIL: ccoDevCommCreate builds a
distinct peerMask per connType and creates the matching QPs (no silent fallback
to CROSSNODE). Note that FULL allocates intra-node QPs but the device GDA barrier
path still prefers LSA for intra-node peers.
dev/cco renamed the shmem p2p benchmarks to shmem_p2p_* (to sit alongside the
new cco_p2p_* ones), but ci.yml's shmem_benchmark step runs ./build/benchmark/
p2p_{put,get}_{bw,latency} — so mpirun failed with "could not access or execute".
cco benchmarks keep the cco_ prefix (no clash); rename shmem ones back to the
unprefixed names main's CI expects.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants