Skip to content

Build Skia main

Build Skia main #54

Workflow file for this run

name: Build Skia
run-name: Build Skia ${{ inputs.skia_branch || 'main' }}
on:
schedule:
# Run weekly on Monday at 9:00 AM UTC (Sunday 1:00 AM PST)
- cron: '0 9 * * 1'
workflow_dispatch:
inputs:
skia_branch:
description: 'Skia branch to build (e.g., main, chrome/m144)'
required: false
type: string
default: 'main'
skia_commit:
description: 'Specific Skia commit SHA to checkout (leave empty for branch HEAD)'
required: false
type: string
default: ''
platforms:
description: 'Platforms to build (comma-separated, or "all")'
required: false
type: string
default: 'all'
test_mode:
description: 'Run in test mode (skip Skia build)'
required: false
type: boolean
default: false
skip_release:
description: 'Skip creating release (useful for testing single platforms)'
required: false
type: boolean
default: false
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true
permissions:
contents: write
jobs:
build-skia:
strategy:
fail-fast: false
matrix:
include:
# macOS builds
- os: macos-latest
platform: mac
variant: gpu
arch: "universal"
- os: macos-latest
platform: mac
variant: gpu
arch: "arm64"
- os: macos-latest
platform: mac
variant: gpu
arch: "x86_64"
# iOS builds
- os: macos-latest
platform: ios
variant: gpu
arch: "arm64"
target: "device"
- os: macos-latest
platform: ios
variant: gpu
arch: "arm64,x86_64"
target: "simulator"
# visionOS builds
- os: macos-latest
platform: visionos
variant: gpu
arch: "arm64"
target: "device"
- os: macos-latest
platform: visionos
variant: gpu
arch: "arm64"
target: "simulator"
# Windows builds - Static CRT (/MT)
- os: windows-latest
platform: win
variant: gpu
arch: x64
config: Release
crt: static
- os: windows-latest
platform: win
variant: gpu
arch: x64
config: Debug
crt: static
# Windows builds - Dynamic CRT (/MD)
- os: windows-latest
platform: win
variant: gpu
arch: x64
config: Release
crt: dynamic
- os: windows-latest
platform: win
variant: gpu
arch: x64
config: Debug
crt: dynamic
# Linux builds
- os: ubuntu-latest
platform: linux
variant: gpu
arch: x64
# WASM builds
- os: ubuntu-latest
platform: wasm
variant: gpu
arch: "wasm32"
config: Release
# Android builds (arm64 only for now)
- os: ubuntu-latest
platform: android
variant: gpu
arch: arm64
config: Release
# Commented out: arm and x64 Android builds
# - os: ubuntu-latest
# platform: android
# variant: gpu
# arch: arm
# config: Release
# - os: ubuntu-latest
# platform: android
# variant: gpu
# arch: x64
# config: Release
runs-on: ${{ matrix.os }}
env:
SKIA_BRANCH: ${{ inputs.skia_branch || 'main' }}
SKIA_COMMIT: ${{ inputs.skia_commit || '' }}
outputs:
skia_branch: ${{ env.SKIA_BRANCH }}
skia_commit: ${{ env.SKIA_COMMIT }}
steps:
- name: Check if platform should build
id: check
shell: bash
run: |
PLATFORMS="${{ inputs.platforms || 'all' }}"
if [[ "$PLATFORMS" == "all" ]] || [[ "$PLATFORMS" == *"${{ matrix.platform }}"* ]]; then
echo "should_build=true" >> $GITHUB_OUTPUT
else
echo "should_build=false" >> $GITHUB_OUTPUT
echo "Skipping ${{ matrix.platform }} (not in platforms: $PLATFORMS)"
fi
- name: Checkout repository
if: steps.check.outputs.should_build == 'true'
uses: actions/checkout@v4
- name: Free disk space (Linux)
if: steps.check.outputs.should_build == 'true' && runner.os == 'Linux'
run: |
# Don't remove Android SDK if building for Android
if [[ "${{ matrix.platform }}" == "android" ]]; then
sudo rm -rf /usr/share/dotnet /opt/ghc /opt/hostedtoolcache/CodeQL
else
sudo rm -rf /usr/share/dotnet /usr/local/lib/android /opt/ghc /opt/hostedtoolcache/CodeQL
fi
sudo docker image prune --all --force
- name: Install Linux build dependencies
if: steps.check.outputs.should_build == 'true' && matrix.platform == 'linux'
run: |
sudo apt-get update
sudo apt-get install -y libfontconfig1-dev libgl1-mesa-dev libglu1-mesa-dev libx11-xcb-dev libxcb1-dev libxcb-xkb-dev libwayland-dev ninja-build
- name: Set up Android NDK
if: steps.check.outputs.should_build == 'true' && matrix.platform == 'android'
uses: android-actions/setup-android@v3
with:
packages: 'ndk;26.1.10909125'
- name: Set Android NDK environment
if: steps.check.outputs.should_build == 'true' && matrix.platform == 'android'
run: |
echo "ANDROID_NDK_HOME=$ANDROID_HOME/ndk/26.1.10909125" >> $GITHUB_ENV
echo "ANDROID_NDK_ROOT=$ANDROID_HOME/ndk/26.1.10909125" >> $GITHUB_ENV
- name: Set up Ninja
if: steps.check.outputs.should_build == 'true' && matrix.os != 'ubuntu-24.04-arm'
uses: seanmiddleditch/gha-setup-ninja@v5
- name: Set up Python
if: steps.check.outputs.should_build == 'true'
uses: actions/setup-python@v5
with:
python-version: '3.x'
- name: Set Git default branch
if: steps.check.outputs.should_build == 'true'
run: git config --global init.defaultBranch main
- name: Install LLVM and Clang
if: steps.check.outputs.should_build == 'true' && runner.os != 'macOS' && matrix.os != 'windows-11-arm'
uses: KyleMayes/install-llvm-action@v2
with:
version: "19.1.0"
env: true
- name: Install LLVM and Clang (Windows ARM64)
if: steps.check.outputs.should_build == 'true' && matrix.os == 'windows-11-arm'
shell: pwsh
run: |
$llvmUrl = "https://github.com/llvm/llvm-project/releases/download/llvmorg-19.1.0/LLVM-19.1.0-woa64.exe"
$installerPath = "$env:TEMP\llvm-installer.exe"
Write-Host "Downloading LLVM installer..."
Invoke-WebRequest -Uri $llvmUrl -OutFile $installerPath
Write-Host "Installing LLVM silently..."
Start-Process -FilePath $installerPath -ArgumentList "/S" -Wait
Write-Host "LLVM installed successfully"
# Add LLVM to PATH
echo "C:\Program Files\LLVM\bin" | Out-File -FilePath $env:GITHUB_PATH -Encoding utf8 -Append
- name: Set cache key arch
if: steps.check.outputs.should_build == 'true'
id: cache-key
shell: bash
run: |
# Replace commas with dashes for cache key (commas not allowed)
ARCH_SAFE=$(echo "${{ matrix.arch || 'default' }}" | tr ',' '-')
CRT_SUFFIX="${{ matrix.crt || '' }}"
echo "arch=${ARCH_SAFE}" >> $GITHUB_OUTPUT
echo "crt=${CRT_SUFFIX}" >> $GITHUB_OUTPUT
- name: Cache depot_tools and Skia source
if: steps.check.outputs.should_build == 'true'
uses: actions/cache@v4
with:
path: |
build/tmp/depot_tools
build/src/skia
key: ${{ runner.os }}-${{ steps.cache-key.outputs.arch }}-${{ steps.cache-key.outputs.crt }}-depot_tools-skia-${{ env.SKIA_BRANCH }}-${{ hashFiles('build-skia.py') }}
- name: Build Skia (${{ matrix.config || 'Release' }})
if: steps.check.outputs.should_build == 'true' && !inputs.test_mode
shell: bash
run: |
ARCH_ARG=""
if [ -n "${{ matrix.arch }}" ]; then
ARCH_ARG="-archs ${{ matrix.arch }}"
fi
TARGET_ARG=""
if [ -n "${{ matrix.target }}" ]; then
TARGET_ARG="-target ${{ matrix.target }}"
fi
CRT_ARG=""
if [ -n "${{ matrix.crt }}" ]; then
CRT_ARG="-crt ${{ matrix.crt }}"
fi
COMMIT_ARG=""
if [ -n "${{ env.SKIA_COMMIT }}" ]; then
COMMIT_ARG="-commit ${{ env.SKIA_COMMIT }}"
fi
CONFIG="${{ matrix.config || 'Release' }}"
python3 build-skia.py ${{ matrix.platform }} -variant ${{ matrix.variant }} -config $CONFIG --shallow -branch ${{ env.SKIA_BRANCH }} $ARCH_ARG $TARGET_ARG $CRT_ARG $COMMIT_ARG
- name: Set archive name
if: steps.check.outputs.should_build == 'true'
id: archive
shell: bash
run: |
CONFIG="${{ matrix.config || 'Release' }}"
CONFIG_LOWER=$(echo "$CONFIG" | tr '[:upper:]' '[:lower:]')
# Build name components
NAME="skia-build-${{ matrix.platform }}"
# Add target (device/simulator) if specified
if [ -n "${{ matrix.target }}" ]; then
NAME="${NAME}-${{ matrix.target }}"
fi
# Add architecture if specified
if [ -n "${{ matrix.arch }}" ]; then
# Replace commas with dashes for multi-arch builds
ARCH_SAFE=$(echo "${{ matrix.arch }}" | tr ',' '-')
NAME="${NAME}-${ARCH_SAFE}"
fi
# Add CRT type for Windows
if [ -n "${{ matrix.crt }}" ]; then
NAME="${NAME}-${{ matrix.crt }}"
fi
NAME="${NAME}-${{ matrix.variant }}-${CONFIG_LOWER}"
echo "name=${NAME}" >> $GITHUB_OUTPUT
- name: Create dummy files for test mode
if: steps.check.outputs.should_build == 'true' && inputs.test_mode
shell: bash
run: |
mkdir -p build/include
mkdir -p build/${{ matrix.platform }}-${{ matrix.variant }}
echo "Test file" > build/include/test.h
echo "Test lib" > build/${{ matrix.platform }}-${{ matrix.variant }}/test.lib
echo "GN args summary" > build/${{ matrix.platform }}-${{ matrix.variant }}/gn_args.txt
- name: Package binaries
if: steps.check.outputs.should_build == 'true'
shell: bash
run: |
# Include share directory if it exists (contains icudtl.dat for ICU)
SHARE_DIR=""
if [ -d "build/share" ]; then
SHARE_DIR="build/share"
fi
if [ "${{ runner.os }}" == "Windows" ]; then
7z a -tzip ${{ steps.archive.outputs.name }}.zip build/include $SHARE_DIR build/${{ matrix.platform }}-${{ matrix.variant }}*
else
zip -r ${{ steps.archive.outputs.name }}.zip build/include $SHARE_DIR build/${{ matrix.platform }}-${{ matrix.variant }}*
fi
- name: Upload artifact
if: steps.check.outputs.should_build == 'true'
uses: actions/upload-artifact@v4
with:
name: ${{ steps.archive.outputs.name }}
path: ${{ steps.archive.outputs.name }}.zip
- name: Set SKIA_BRANCH output
if: steps.check.outputs.should_build == 'true'
shell: bash
run: echo "skia_branch=${{ env.SKIA_BRANCH }}" >> $GITHUB_OUTPUT
create-xcframework:
needs: build-skia
if: ${{ !inputs.skip_release && (inputs.platforms == 'all' || inputs.platforms == '') }}
runs-on: macos-latest
steps:
- name: Download macOS artifact
uses: actions/download-artifact@v4
with:
name: skia-build-mac-universal-gpu-release
- name: Download iOS device artifact
uses: actions/download-artifact@v4
with:
name: skia-build-ios-device-arm64-gpu-release
- name: Download iOS simulator artifact
uses: actions/download-artifact@v4
with:
name: skia-build-ios-simulator-arm64-x86_64-gpu-release
- name: Download visionOS device artifact
uses: actions/download-artifact@v4
with:
name: skia-build-visionos-device-arm64-gpu-release
- name: Download visionOS simulator artifact
uses: actions/download-artifact@v4
with:
name: skia-build-visionos-simulator-arm64-gpu-release
- name: Extract artifacts
run: |
for zip in *.zip; do
echo "Extracting $zip..."
unzip -o "$zip"
done
echo "Build directory structure:"
find build -name "libSkia.a" | head -20
- name: Create XCFramework
run: |
# Merge iOS simulator architectures into a single fat library
mkdir -p build/ios-gpu/lib/Release/simulator
lipo -create \
build/ios-gpu/lib/Release/simulator-arm64/libSkia.a \
build/ios-gpu/lib/Release/simulator-x86_64/libSkia.a \
-output build/ios-gpu/lib/Release/simulator/libSkia.a
xcodebuild -create-xcframework \
-library build/mac-gpu/lib/Release/libSkia.a \
-headers build/include \
-library build/ios-gpu/lib/Release/device-arm64/libSkia.a \
-library build/ios-gpu/lib/Release/simulator/libSkia.a \
-library build/visionos-gpu/lib/Release/device-arm64/libSkia.a \
-library build/visionos-gpu/lib/Release/simulator-arm64/libSkia.a \
-output Skia.xcframework
- name: Package XCFramework
run: zip -r Skia.xcframework.zip Skia.xcframework
- name: Upload XCFramework artifact
uses: actions/upload-artifact@v4
with:
name: Skia.xcframework
path: Skia.xcframework.zip
create-release:
if: ${{ !inputs.skip_release && (inputs.platforms == 'all' || inputs.platforms == '') }}
needs: [build-skia, create-xcframework]
runs-on: ubuntu-latest
steps:
- name: Download artifacts
uses: actions/download-artifact@v4
- name: Get release tag
id: tag
run: |
BRANCH="${{ needs.build-skia.outputs.skia_branch }}"
DATE=$(date +'%Y%m%d')
if [[ "$BRANCH" == "main" ]]; then
TAG="main-${DATE}"
else
TAG="${BRANCH}"
fi
echo "tag=${TAG}" >> $GITHUB_OUTPUT
echo "Release tag: ${TAG}"
- name: Create Release
uses: softprops/action-gh-release@v2
with:
body: |
## Skia Build - ${{ steps.tag.outputs.tag }}
Built from Skia branch: `${{ needs.build-skia.outputs.skia_branch }}`
### Platforms
**Apple:**
- macOS (universal, arm64, x86_64)
- iOS (device arm64, simulator arm64+x86_64)
- visionOS (device arm64, simulator arm64)
- XCFramework (all Apple platforms combined)
**Windows x64:**
- Release/Debug with static CRT (/MT, /MTd)
- Release/Debug with dynamic CRT (/MD, /MDd)
**Linux x64:**
- Release build
**Android:**
- arm64, arm, x64 builds
**WebAssembly:**
- wasm32 build
### Notes
- Windows `/MT` builds: Use with vcpkg `x64-windows-static` triplet
- Windows `/MD` builds: Use with Dawn or other dynamic CRT dependencies
tag_name: ${{ steps.tag.outputs.tag }}${{ inputs.test_mode && '-test' || '' }}
name: Skia ${{ steps.tag.outputs.tag }}${{ inputs.test_mode && ' (Test)' || '' }}
draft: false
prerelease: ${{ inputs.test_mode }}
files: |
./skia-build-mac-universal-gpu-release/skia-build-mac-universal-gpu-release.zip
./skia-build-mac-arm64-gpu-release/skia-build-mac-arm64-gpu-release.zip
./skia-build-mac-x86_64-gpu-release/skia-build-mac-x86_64-gpu-release.zip
./skia-build-ios-device-arm64-gpu-release/skia-build-ios-device-arm64-gpu-release.zip
./skia-build-ios-simulator-arm64-x86_64-gpu-release/skia-build-ios-simulator-arm64-x86_64-gpu-release.zip
./skia-build-visionos-device-arm64-gpu-release/skia-build-visionos-device-arm64-gpu-release.zip
./skia-build-visionos-simulator-arm64-gpu-release/skia-build-visionos-simulator-arm64-gpu-release.zip
./skia-build-win-x64-static-gpu-release/skia-build-win-x64-static-gpu-release.zip
./skia-build-win-x64-static-gpu-debug/skia-build-win-x64-static-gpu-debug.zip
./skia-build-win-x64-dynamic-gpu-release/skia-build-win-x64-dynamic-gpu-release.zip
./skia-build-win-x64-dynamic-gpu-debug/skia-build-win-x64-dynamic-gpu-debug.zip
./skia-build-linux-x64-gpu-release/skia-build-linux-x64-gpu-release.zip
./skia-build-wasm-wasm32-gpu-release/skia-build-wasm-wasm32-gpu-release.zip
./skia-build-android-arm64-gpu-release/skia-build-android-arm64-gpu-release.zip
./skia-build-android-arm-gpu-release/skia-build-android-arm-gpu-release.zip
./skia-build-android-x64-gpu-release/skia-build-android-x64-gpu-release.zip
./Skia.xcframework/Skia.xcframework.zip
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}