Skip to content

ci: run on feature/** branches (quantization/dwconv/dbcache validation) #19

ci: run on feature/** branches (quantization/dwconv/dbcache validation)

ci: run on feature/** branches (quantization/dwconv/dbcache validation) #19

Workflow file for this run

name: ci
# Multi-platform build + oudep packaging for GAME-ggml CLI.
#
# Matrix:
# linux-x64-vulkan — Ubuntu, Vulkan backend
# linux-x64-cuda — Ubuntu 22.04, CUDA backend (CUDA 12.6)
# macos-arm64-metal — Apple Silicon, Metal backend
# macos-x64-metal — Intel Mac, Metal backend (cross-compiled on ARM runner)
# windows-x64-vulkan — Windows, Vulkan backend
# windows-x64-cuda — Windows Server 2022, CUDA backend (CUDA 12.6)
#
# On tag push, artifacts are bundled into a GitHub Release.
on:
push:
branches: [main, master, 'feature/**']
tags: ['v*']
pull_request: {}
workflow_dispatch: {}
concurrency:
group: ci-${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: ${{ github.event_name == 'pull_request' }}
jobs:
prepare-model:
name: prepare medium GGUF
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Set up Python
uses: actions/setup-python@v5
with:
python-version: "3.11"
cache: pip
cache-dependency-path: scripts/requirements.txt
- name: Install conversion dependencies
run: |
python -m pip install --upgrade pip
python -m pip install -r scripts/requirements.txt
- name: Download and verify medium checkpoint
run: |
curl -fL --retry 5 --retry-all-errors \
-o GAME-1.0-medium.zip \
https://github.com/openvpi/GAME/releases/download/v1.0.0/GAME-1.0-medium.zip
echo "8c5b3e531e2905b935e664e2f533921cd637243770fab5282413bdb5051ca60c GAME-1.0-medium.zip" \
| sha256sum --check --strict
unzip -q GAME-1.0-medium.zip
- name: Convert checkpoint and prepare backend config
run: |
mkdir -p model
python scripts/convert_pt_to_gguf.py \
--model-dir GAME-1.0-medium \
-o model/game_medium.gguf
cat > model/config.json <<'EOF'
{
"samplerate": 44100,
"timestep": 0.01,
"languages": {
"en": 1,
"ja": 2,
"yue": 3,
"zh": 4
},
"loop": true
}
EOF
- name: Verify model files
run: |
test -s model/game_medium.gguf
python -m json.tool model/config.json >/dev/null
ls -lh model/
- name: Upload model artifact
uses: actions/upload-artifact@v4
with:
name: game-ggml-medium-model
path: model
if-no-files-found: error
retention-days: 7
build:
name: ${{ matrix.name }}
needs: prepare-model
runs-on: ${{ matrix.os }}
strategy:
fail-fast: false
matrix:
include:
- os: ubuntu-latest
name: linux-x64-vulkan
backend: vulkan
cmake_extra: "-DGAME_GGML_VULKAN=ON"
build_jobs: 4
pkg_ext: ""
lib_glob: "libggml*.so*"
- os: ubuntu-22.04
name: linux-x64-cuda
backend: cuda
cmake_extra: '-DGAME_GGML_CUDA=ON -DGGML_NATIVE=OFF -DCMAKE_CUDA_ARCHITECTURES=75'
build_jobs: 2
pkg_ext: ""
lib_glob: "libggml*.so*"
- os: macos-14
name: macos-arm64-metal
backend: metal
cmake_extra: "-DGAME_GGML_METAL=ON -DCMAKE_OSX_ARCHITECTURES=arm64"
build_jobs: 4
pkg_ext: ""
lib_glob: "libggml*.dylib"
- os: macos-14
name: macos-x64-metal
backend: metal
cmake_extra: "-DGAME_GGML_METAL=ON -DCMAKE_OSX_ARCHITECTURES=x86_64"
build_jobs: 4
pkg_ext: ""
lib_glob: "libggml*.dylib"
- os: windows-latest
name: windows-x64-vulkan
backend: vulkan
cmake_extra: "-DGAME_GGML_VULKAN=ON"
build_jobs: 4
pkg_ext: ".exe"
lib_glob: "ggml*.dll"
- os: windows-2022
name: windows-x64-cuda
backend: cuda
cmake_extra: '-DGAME_GGML_CUDA=ON -DGGML_NATIVE=OFF -DCMAKE_CUDA_ARCHITECTURES=75'
build_jobs: 2
pkg_ext: ".exe"
lib_glob: "ggml*.dll"
defaults:
run:
shell: bash
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Install Vulkan SDK
if: matrix.backend == 'vulkan'
uses: humbletim/install-vulkan-sdk@30ba978f977e81b72d091fc8888feb1fb26f9aff
with:
version: 1.4.309.0
cache: true
- name: Verify Vulkan shader compiler
if: matrix.backend == 'vulkan'
run: glslc --version
- name: Install CUDA Toolkit (Linux)
if: matrix.backend == 'cuda' && runner.os == 'Linux'
uses: Jimver/cuda-toolkit@1a3c14e26833ccf292b268f9a790fb47dea7b2da # v0.2.28
with:
cuda: "12.6.3"
method: network
log-file-suffix: "${{ matrix.name }}.txt"
- name: Install CUDA Toolkit (Windows)
if: matrix.backend == 'cuda' && runner.os == 'Windows'
uses: Jimver/cuda-toolkit@b8bf9c6c28f8a92fbb04dcfcaee872e60c57462d # v0.2.36
with:
cuda: "12.6.3"
method: network
sub-packages: '["nvcc", "cudart", "cublas", "cublas_dev", "visual_studio_integration"]'
log-file-suffix: "${{ matrix.name }}.txt"
- name: Verify CUDA compiler
if: matrix.backend == 'cuda'
run: nvcc --version
- name: Disable native CPU for cross-compile (macOS x86_64 only)
if: matrix.name == 'macos-x64-metal'
run: echo "GGML_NATIVE=OFF" >> "$GITHUB_ENV"
- name: Cache CMake FetchContent
uses: actions/cache@v4
with:
path: build/_deps
# FetchContent stores generator-specific subbuild state here, so do not
# share it between VS 2022/2026 runners or between different backends.
key: ${{ matrix.name }}-deps-${{ hashFiles('cmake/Dependencies.cmake') }}
restore-keys: |
${{ matrix.name }}-deps-
- name: Configure
run: |
cmake -S . -B build \
-DCMAKE_BUILD_TYPE=Release \
-DGAME_GGML_BUILD_CLI=ON \
-DGAME_GGML_BUILD_TESTS=OFF \
${GGML_NATIVE:+-DGGML_NATIVE=$GGML_NATIVE} \
${{ matrix.cmake_extra }}
- name: Build
# ggml-cuda expands many template instances. Unbounded parallel builds can
# exhaust the memory of GitHub-hosted runners and terminate nvcc.
run: cmake --build build --parallel ${{ matrix.build_jobs }} --config Release
- name: Verify binary
run: |
set -euo pipefail
ls -la build/bin/
# The CUDA CLI links ggml-cuda.dll directly (see src/backend.cpp), so
# startup requires the Toolkit runtime DLLs. Git Bash does not always
# forward its PATH to the Windows loader, so we dump the PE import
# tables and run through PowerShell with a native Windows PATH.
if [ "${{ matrix.backend }}" = "cuda" ] && [ "${{ runner.os }}" = "Windows" ]; then
echo "== CUDA_PATH=$CUDA_PATH =="
CUDA_BIN="$(cygpath -u "$CUDA_PATH")/bin"
echo "== CUDA Toolkit bin (first 60 entries) =="
ls -1 "$CUDA_BIN" 2>/dev/null | head -60 || echo "(cannot list $CUDA_BIN)"
echo "== required runtime DLLs =="
for dll in cudart64_12.dll cublas64_12.dll cublasLt64_12.dll; do
if [ -f "$CUDA_BIN/$dll" ]; then echo "OK $dll"; else echo "MISSING $dll"; fi
done
if python -m pip install --quiet pefile; then
echo "== PE import tables =="
python scripts/dump_pe_imports.py build/bin/game_ggml_cli.exe build/bin/ggml-cuda.dll
else
echo "(pefile unavailable, skipping import dump)"
fi
fi
# On Windows, ggml-cuda.dll imports nvcuda.dll (the NVIDIA driver
# library) at load time. GitHub-hosted runners have no NVIDIA driver,
# so the process cannot start there even for --version. When the
# driver is present we run the real startup smoke test; otherwise the
# PE dependency checks above are the verification and we report why.
if [ "${{ runner.os }}" = "Windows" ]; then
if [ -f "/c/Windows/System32/nvcuda.dll" ]; then
powershell -NoProfile -ExecutionPolicy Bypass -Command '
$env:PATH = "$env:CUDA_PATH\bin;" + $env:PATH
$exe = Join-Path (Get-Location) "build/bin/game_ggml_cli${{ matrix.pkg_ext }}"
& $exe --version
if ($LASTEXITCODE -ne 0) { exit $LASTEXITCODE }
'
else
echo "no NVIDIA driver on this runner (nvcuda.dll not found); startup smoke test requires a GPU machine"
fi
else
build/bin/game_ggml_cli${{ matrix.pkg_ext }} --version
fi
- name: Download medium GGUF
uses: actions/download-artifact@v4
with:
name: game-ggml-medium-model
path: model
- name: Package .oudep
run: |
set -euo pipefail
BIN="game_ggml_cli${{ matrix.pkg_ext }}"
PKG="game_ggml-${{ matrix.name }}"
mkdir -p "$PKG"
# CLI binary
cp "build/bin/$BIN" "$PKG/"
# Shared libraries
find build/bin -maxdepth 1 -name "${{ matrix.lib_glob }}" -exec cp {} "$PKG/" \;
compgen -G "$PKG/${{ matrix.lib_glob }}" >/dev/null
# macOS: include the pre-compiled Metal shader cache.
if [ "${{ runner.os }}" = "macOS" ]; then
METALLIB=$(find build -name "default.metallib" -type f -print -quit)
test -n "$METALLIB"
cp "$METALLIB" "$PKG/"
fi
# Model and OpenUtau backend config.
cp model/game_medium.gguf model/config.json "$PKG/"
# oudep manifest
cat > "$PKG/oudep.yaml" <<EOF
id: game-ggml-medium
version: 0.1.0
description: GAME GGML inference engine (${{ matrix.name }}) + medium GGUF weights
entrypoints:
- loader: Executable
path: $BIN
EOF
# OpenUtau expects all of these files at the package root.
test -x "$PKG/$BIN"
test -s "$PKG/game_medium.gguf"
test -s "$PKG/config.json"
test -s "$PKG/oudep.yaml"
grep -Fx "id: game-ggml-medium" "$PKG/oudep.yaml"
grep -Fx " path: $BIN" "$PKG/oudep.yaml"
ls -lh "$PKG/"
echo "PKG_DIR=$PKG" >> "$GITHUB_ENV"
- name: Upload build artifact
uses: actions/upload-artifact@v4
with:
name: ${{ env.PKG_DIR }}
path: ${{ env.PKG_DIR }}
if-no-files-found: error
retention-days: 30
release:
if: startsWith(github.ref, 'refs/tags/v')
needs: build
runs-on: ubuntu-latest
permissions:
contents: write
steps:
- name: Download CI artifacts
uses: actions/download-artifact@v4
with:
pattern: game_ggml-*
path: artifacts
- name: Re-package all artifacts as .oudep
run: |
set -euo pipefail
for dir in artifacts/*/; do
name=$(basename "$dir")
test -s "$dir/oudep.yaml"
test -s "$dir/game_medium.gguf"
test -s "$dir/config.json"
(
cd "$dir"
zip -r "../../${name}.oudep" .
)
done
# PackageManager requires oudep.yaml at the archive root.
for package in *.oudep; do
test "$(unzip -Z1 "$package" | grep -c '^oudep.yaml$')" -eq 1
test "$(unzip -Z1 "$package" | grep -c '^game_medium.gguf$')" -eq 1
test "$(unzip -Z1 "$package" | grep -c '^config.json$')" -eq 1
done
ls -lh *.oudep
- name: Publish release
uses: softprops/action-gh-release@v2
with:
files: "*.oudep"
generate_release_notes: true
fail_on_unmatched_files: true