1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
name: CI
on:
push:
branches:
pull_request:
branches:
env:
CARGO_TERM_COLOR: always
jobs:
test:
name: Test (${{ matrix.os }})
runs-on: ${{ matrix.os }}
strategy:
fail-fast: false
matrix:
# v1.0 Item E Phase 2: 5 native platform matrix (WASM は独立 job で扱う)
# - macos-latest → aarch64-apple-darwin (Mac ARM, primary dev, golden hash baseline)
# - macos-15-intel → x86_64-apple-darwin (Mac Intel)
# - ubuntu-latest → x86_64-unknown-linux-gnu (Linux x86)
# - ubuntu-24.04-arm → aarch64-unknown-linux-gnu (Linux ARM、GA runner 2025-01+)
# - windows-latest → x86_64-pc-windows-msvc (Windows x86)
# + wasm-test job below → wasm32-wasip1 (WASI) via wasmtime
os:
steps:
- uses: actions/checkout@v5
- name: Install Rust toolchain
uses: dtolnay/rust-toolchain@stable
- uses: Swatinem/rust-cache@v2
# inline stubs は composite action に集約 (canonical CI template [[reference_alice_ci_canonical_template]])
# security-audit.yml / fuzz.yml と DRY で共有、license field 追加も一元管理
- name: Create ALICE optional bridge stubs
uses: ./.github/actions/alice-stubs
# `crate-type` includes cdylib/staticlib (FFI consumers, 1.2.0); a no_std
# cdylib needs a panic_handler + allocator, so the no_std *library* build is
# checked as rlib only (same workaround as ALICE-ML). Downstream no_std
# users always get the rlib.
- name: Build (no_std, rlib)
run: cargo rustc --lib --no-default-features --crate-type rlib
- name: Build (std only)
run: cargo build --lib --no-default-features --features "std"
- name: Build (core — default features)
run: cargo build --lib
- name: Test (unit + integration + doc)
run: cargo test
# 1.2.0: the C ABI consumers (Unity P/Invoke, unreal-plugin/) link the
# cdylib / staticlib — assert both are actually produced, not just the rlib.
# the ffi test module (goldens the Unity / UE5 bindings replay) was never
# executed in CI before 1.2.0 — only built
- name: Test (FFI, lib)
# quoted: a bare trailing `ffi::` makes YAML read the line as a mapping
# (actionlint syntax-check; two pushes were red on this, 2026-09-15)
run: 'cargo test --lib --features "ffi" "ffi::"'
- name: Build (FFI) + assert cdylib / staticlib artifacts
shell: bash
run: |
cargo build --features "ffi"
ls target/debug/
# `-f` tests, not `ls a b c | grep`: under `set -o pipefail` a missing
# sibling name makes `ls` exit 2 and fails the pipeline even when the
# platform's artifact is present (first run of this step, 2026-09-15).
cdylib=0; for f in target/debug/libalice_physics.so target/debug/libalice_physics.dylib target/debug/alice_physics.dll; do [ -f "$f" ] && cdylib=1; done
staticlib=0; for f in target/debug/libalice_physics.a target/debug/alice_physics.lib; do [ -f "$f" ] && staticlib=1; done
[ "$cdylib" = 1 ] || { echo "no cdylib produced"; exit 1; }
[ "$staticlib" = 1 ] || { echo "no staticlib produced"; exit 1; }
- name: Build (parallel)
run: cargo build --lib --features "parallel"
- name: Test (parallel — unit + integration)
run: cargo test --features "parallel"
# full native feature set: the gpu-solver-bridge tests were only linted
# (clippy), never run, before 1.2.0 — the quality-deep mutants job found
# them failing in the unmutated tree
- name: Test (full native feature set, lib)
run: cargo test --lib --features "std,simd,parallel,ffi,gpu-solver-bridge"
# test, not just build: a feature whose code is only compiled is a feature
# whose effect nobody verifies (external review 2026-09-15: the SIMD paths
# were scalar with dead intrinsics and no test caught the mismatch claim).
- name: Test (SIMD, lib)
run: cargo test --lib --features "simd"
# v1.0 Item E Phase 2: WASM determinism check
# `wasm32-wasip1` target で determinism_golden test を build → wasmtime で
# 実行 SHA-256 hash が native platform (macOS ARM baseline) と bit-exact
# 一致することを検証 Fix128 は純粋整数演算のため cross-platform bit-exact、
# SDF 経路の f32 も IEEE 754 basic ops (+/-/*/sqrt) が platform 非依存
sibling-features:
name: Test (neural / replay / analytics via crates.io siblings)
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- name: Install Rust toolchain
uses: dtolnay/rust-toolchain@stable
- uses: Swatinem/rust-cache@v2
with:
shared-key: sibling-features
# The bridge modules (alice-ml / alice-db / alice-analytics) come from
# crates.io. Their contract tests never ran in CI before 1.2.0, which is
# how alice-db 0.2.0-beta.1's archived-path stub (every replay read 0.0)
# went unnoticed; fixed in alice-db 0.2.0-beta.2.
- name: Test (lib, neural + replay + analytics)
run: cargo test --lib --features "neural,replay,analytics"
wasm-test:
name: Test (wasm32-wasip1 via wasmtime)
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- name: Install Rust toolchain (with wasm32-wasip1)
uses: dtolnay/rust-toolchain@stable
with:
targets: wasm32-wasip1
# dtolnay/rust-toolchain の targets: が rustup target 追加を silent
# fail することがある fallback として明示 rustup target add を実行
# (idempotent、既に install 済なら no-op)
- name: Ensure wasm32-wasip1 rust-std is installed
run: rustup target add wasm32-wasip1
- uses: Swatinem/rust-cache@v2
with:
shared-key: wasm-wasip1
- name: Create ALICE optional bridge stubs
uses: ./.github/actions/alice-stubs
# 2026-09-15: `curl … | bash` は curl が network error (35 Connection reset) でも
# pipeline exit が bash 側 = 0 になり step green のまま次 step で `wasmtime: command not found`
# (exit 127) になる (run 34863693753) 公式 setup action に置換 (retry 内蔵、pipefail 問題が消える)
- name: Install wasmtime
uses: bytecodealliance/actions/wasmtime/setup@v1
- name: Build determinism_golden test (wasm32-wasip1)
run: cargo test --test determinism_golden --target wasm32-wasip1 --no-run
- name: Run determinism_golden test via wasmtime
run: |
WASM_BIN=$(find target/wasm32-wasip1/debug/deps -name 'determinism_golden-*.wasm' -not -name '*.d' | head -1)
echo "Executing: $WASM_BIN"
wasmtime "$WASM_BIN"
# v1.1.0: the f32/f64 field modules are pinned too (det_math + IEEE basic ops)
- name: Build determinism_golden_f32 test (wasm32-wasip1)
run: cargo test --test determinism_golden_f32 --target wasm32-wasip1 --no-run
- name: Run determinism_golden_f32 test via wasmtime
run: |
WASM_BIN=$(find target/wasm32-wasip1/debug/deps -name 'determinism_golden_f32-*.wasm' -not -name '*.d' | head -1)
echo "Executing: $WASM_BIN"
wasmtime "$WASM_BIN"
clippy:
name: Clippy
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- name: Install Rust toolchain
uses: dtolnay/rust-toolchain@stable
with:
components: clippy
- uses: Swatinem/rust-cache@v2
- name: Clippy (default features, lib + all targets)
run: cargo clippy --all-targets -- -D warnings
# `--all-features` is not possible: `wasm` × `ffi` is a deliberate
# `compile_error!`, and `python` needs a Python toolchain. Every
# other feature is exercised here so lint drift in feature-gated
# code (parallel / neural / replay / ...) is a red gate, not a `-W`.
- name: Clippy (full native feature set, lib + all targets)
run: >-
cargo clippy
--features "std,simd,parallel,ffi,gpu-solver-bridge,neural,replay,analytics"
--all-targets -- -D warnings
# The declared `rust-version` is compiled with exactly that toolchain
# (resolver = "3" makes the fresh resolution MSRV-aware, Cargo.lock is not
# committed for this library) for the default, no_std and full native feature
# sets. Bump `rust-version` and the
# `@<version>` below in the same commit (karikari §3-1 #53 / template 罠 #27).
# The pre-1.2.0 job regenerated the lockfile with stable and checked only the
# std feature set, so the "1.70.0" claim was never actually compiled.
msrv:
name: MSRV (rust-version = 1.85)
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- name: Install MSRV toolchain
uses: dtolnay/rust-toolchain@1.85
- uses: Swatinem/rust-cache@v2
- name: cargo check on MSRV (lib, default features)
run: cargo +1.85 check --lib
- name: cargo check on MSRV (lib, no_std, rlib)
run: cargo +1.85 rustc --lib --no-default-features --crate-type rlib
# Library only: dev-dependencies (criterion / serde_derive) and the
# sibling-crate bridge features (neural / replay / analytics) follow
# their own MSRV, see README "MSRV Policy".
- name: cargo check on MSRV (lib, core native feature set)
run: >-
cargo +1.85 check --lib
--features "std,simd,parallel,ffi,gpu-solver-bridge"
fmt:
name: Format
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- name: Install Rust toolchain
uses: dtolnay/rust-toolchain@stable
with:
components: rustfmt
- name: Check formatting
run: cargo fmt -- --check
# README § Determinism scope lists the f32 / f64 modules; the list is
# generated from src/ and drifts silently when a module is added (1.2.0)
- name: README f32 module row matches src/
run: python3 scripts/f32_modules.py --check
doc:
name: Doc (RUSTDOCFLAGS=-Dwarnings)
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: dtolnay/rust-toolchain@stable
- uses: Swatinem/rust-cache@v2
# Both the default and the docs.rs feature set: feature-gated modules
# (gpu_bridge / ffi) had 9 broken intra-doc links that the default-only
# job never saw (1.2.0).
- name: cargo doc (no-deps, default features)
run: cargo doc --lib --no-deps
env:
RUSTDOCFLAGS: "-Dwarnings"
- name: cargo doc (no-deps, docs.rs feature set)
run: cargo doc --lib --no-deps --features "std,simd,parallel,ffi,gpu-solver-bridge"
env:
RUSTDOCFLAGS: "-Dwarnings"
actionlint:
name: actionlint (workflow YAML 検証)
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- name: Run actionlint
uses: reviewdog/action-actionlint@v1
with:
fail_level: error
reporter: github-check
feature-powerset:
# 2026-09-15 追加 (karikari-review §13 / CI template 手順 4.6): feature 組合せの compile 網羅
# depth 2 = 単体 + 2 個組合せ (19 通り、Mac 実測 green)
# - wasm は `std` 必須 (`compile_error!`) なので powerset から外し、std,wasm を別 step で check
# - python (pyo3 build) / neural / replay / analytics (sibling crate 実体必要) は除外
name: Feature powerset (cargo-hack)
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: dtolnay/rust-toolchain@stable
- uses: Swatinem/rust-cache@v2
- name: Create ALICE optional bridge stubs
uses: ./.github/actions/alice-stubs
- name: Install cargo-hack
uses: taiki-e/install-action@cargo-hack
# rustc --crate-type rlib: combos without `std` cannot build the cdylib
# (no panic_handler / allocator), see "Build (no_std, rlib)" above.
- name: Powerset (depth 2, wasm/python/bridge 除外)
run: cargo hack rustc --lib --crate-type rlib --feature-powerset --depth 2 --exclude-features python,neural,replay,analytics,wasm
- name: std + wasm (相互排他 ffi なし)
run: cargo check --lib --no-default-features --features std,wasm