Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
40 commits
Select commit Hold shift + click to select a range
dbf61c6
Create ci.yml
BlueInstruction Apr 14, 2026
a05dbbd
Create ci.yml
BlueInstruction Apr 14, 2026
cd765c4
Rename ci.yml to .github/workflows/ci.yml
BlueInstruction Apr 14, 2026
3d8bebb
Update ci.yml
BlueInstruction Apr 14, 2026
8080fb4
Use drv_info for optimization barriers: update Qualcomm proprietary c…
devin-ai-integration[bot] Apr 14, 2026
6364991
Fix SPIRV-Tools build: use correct CMake target names for v2024.4.rc2
devin-ai-integration[bot] Apr 14, 2026
ac738ae
Fix CI: add missing libx11-xcb-dev and libxcb-keysyms1-dev dependencies
devin-ai-integration[bot] Apr 14, 2026
55b54c6
CI: use clang for Meson configure (meson.build requires -ferror-limit…
devin-ai-integration[bot] Apr 14, 2026
ff89da3
Fix CI: define Android stub macros for non-Android host builds
devin-ai-integration[bot] Apr 14, 2026
98e7f8a
Fix CI: separate C/C++ stub args to avoid nullptr in C and __ANDROID_…
devin-ai-integration[bot] Apr 14, 2026
8bd4d59
Fix CI: include sys/syscall.h for SYS_memfd_create in anon_file.c
devin-ai-integration[bot] Apr 14, 2026
b17c13e
Fix CI: restore __ANDROID_API__=26 for WSI AHardwareBuffer code
devin-ai-integration[bot] Apr 14, 2026
5ebcaac
Fix CI: define __TERMUX__ for WSI AHardwareBuffer struct members
devin-ai-integration[bot] Apr 14, 2026
e813a54
Merge branch 'wrapper' into PR
BlueInstruction Apr 14, 2026
6e892b7
Merge pull request #1 from BlueInstruction/PR
BlueInstruction Apr 14, 2026
fcb6cf3
Remove unused variable dstDescriptorType in CmdComputeShaderForDecomp…
devin-ai-integration[bot] Apr 14, 2026
193da17
Fix CI: define native_handle_t for non-Android __TERMUX__ builds
devin-ai-integration[bot] Apr 14, 2026
eb935ae
Fix CI: add wl_display to print_param exclusion list
devin-ai-integration[bot] Apr 14, 2026
4891aeb
Fix CI: define getprogname() fallback for non-Android builds
devin-ai-integration[bot] Apr 14, 2026
e634d82
Fix CI: add missing fcntl.h and fix VK_DRIVER_ID_MESA_PANFROST
devin-ai-integration[bot] Apr 14, 2026
f43bf7d
Fix CI: define getprogname() fallback in wrapper_log.c for non-Androi…
devin-ai-integration[bot] Apr 14, 2026
7f887ba
Fix CI: define getprogname() fallback in artifacts.cpp for non-Androi…
devin-ai-integration[bot] Apr 14, 2026
8934406
Fix CI: stub adrenotools_open_libvulkan for non-Android linker
devin-ai-integration[bot] Apr 15, 2026
9e41190
Fix CI: remove static from adrenotools stub to match header declaration
devin-ai-integration[bot] Apr 15, 2026
0aed1ca
CI: add upload artifact step for libvulkan_wrapper.so and ICD JSON
devin-ai-integration[bot] Apr 15, 2026
5d79c31
Merge pull request #2 from BlueInstruction/wrapper
BlueInstruction Apr 15, 2026
34ba82f
Add ARM64 (aarch64) cross-compilation CI job for Winlator
devin-ai-integration[bot] Apr 15, 2026
2299304
Fix ARM64 build: use PKG_CONFIG_LIBDIR to isolate arm64 pkg-config se…
devin-ai-integration[bot] Apr 15, 2026
24b5140
Fix ARM64 build: replace Clang-only -ferror-limit with GCC -fmax-errors
devin-ai-integration[bot] Apr 15, 2026
705a176
Fix atomic_bool for C++ compilation with GCC in android_stub trace.h
devin-ai-integration[bot] Apr 15, 2026
0ca3aca
Fix _Nullable/_Nonnull Clang annotations for GCC cross-compilation
devin-ai-integration[bot] Apr 15, 2026
83ea82f
Fix ARM64 build: suppress GCC format-overflow warnings in generated code
devin-ai-integration[bot] Apr 15, 2026
d3fd859
Fix wrapper_checks.h: disable _Static_assert with __func__ for GCC (n…
devin-ai-integration[bot] Apr 15, 2026
6b06b11
Fix ARM64 C++ build: define _Atomic as empty for GCC C++ and suppress…
devin-ai-integration[bot] Apr 15, 2026
ccd4655
Replace GCC cross-compile with Android NDK build for production ARM64…
devin-ai-integration[bot] Apr 15, 2026
3e6a425
Build libdrm and X11/XCB libraries from source for Android NDK aarch64
devin-ai-integration[bot] Apr 15, 2026
5f2dc49
Fix X11 library builds: use full clone + checkout for annotated tags,…
devin-ai-integration[bot] Apr 15, 2026
0498e3d
Fix X11 libs: use --depth 1 from master (older tags lack meson.build)…
devin-ai-integration[bot] Apr 15, 2026
d15b5fe
Fix xcb-proto: install XML files manually (no meson.build in repo)
devin-ai-integration[bot] Apr 15, 2026
274d9ad
Replace building X11 libs from source with Termux prebuilt packages
devin-ai-integration[bot] Apr 15, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
265 changes: 265 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,265 @@
name: CI

on:
push:
branches: [wrapper, PR]
pull_request:
branches: [wrapper]

jobs:
build-wrapper:
name: Build Vulkan Wrapper (x86_64)
runs-on: ubuntu-24.04

steps:
- name: Checkout
uses: actions/checkout@v4

- name: Install system dependencies
run: |
sudo apt-get update
sudo apt-get install -y \
meson ninja-build \
python3 python3-mako python3-ply python3-yaml \
glslang-tools \
libvulkan-dev \
libwayland-dev libwayland-egl-backend-dev wayland-protocols \
libx11-dev libx11-xcb-dev libxext-dev libxfixes-dev libxcb1-dev libxcb-dri2-0-dev \
libxcb-dri3-dev libxcb-present-dev libxcb-shm0-dev libxcb-randr0-dev \
libxcb-keysyms1-dev libxshmfence-dev libxxf86vm-dev libxrandr-dev \
libdrm-dev libelf-dev \
libexpat1-dev \
zlib1g-dev \
cmake git \
clang

- name: Build SPIRV-Tools for host
run: |
git clone --depth 1 --branch v2024.4.rc2 https://github.com/KhronosGroup/SPIRV-Tools.git /tmp/SPIRV-Tools
cd /tmp/SPIRV-Tools
python3 utils/git-sync-deps
mkdir build && cd build
cmake .. -DCMAKE_BUILD_TYPE=Release -DSPIRV_SKIP_TESTS=ON
cmake --build . --config Release -j$(nproc) --target SPIRV-Tools-static SPIRV-Tools-opt
mkdir -p $GITHUB_WORKSPACE/src/vulkan/wrapper/lib
cp source/libSPIRV-Tools.a $GITHUB_WORKSPACE/src/vulkan/wrapper/lib/
cp source/opt/libSPIRV-Tools-opt.a $GITHUB_WORKSPACE/src/vulkan/wrapper/lib/
mkdir -p $GITHUB_WORKSPACE/src/vulkan/wrapper/include/spirv-tools
cp -r /tmp/SPIRV-Tools/include/* $GITHUB_WORKSPACE/src/vulkan/wrapper/include/spirv-tools/

- name: Configure Mesa (wrapper only)
env:
CC: clang
CXX: clang++
run: |
STUB_ARGS="-D__INTRODUCED_IN(x)= -D__ANDROID_API__=26 -D__TERMUX__"
STUB_C="$STUB_ARGS -include sys/syscall.h"
STUB_CXX="$STUB_ARGS -DNULL=nullptr"
meson setup _build \
-Dvulkan-drivers=wrapper \
-Dgallium-drivers= \
-Dandroid-stub=true \
-Dplatforms=x11,wayland \
-Dglx=disabled \
-Degl=disabled \
-Dgbm=disabled \
-Dopengl=false \
-Dgles1=disabled \
-Dgles2=disabled \
-Dllvm=disabled \
-Dshared-glapi=disabled \
-Dbuildtype=release \
-Dc_args="$STUB_C" \
-Dcpp_args="$STUB_CXX"

- name: Build
run: |
ninja -C _build src/vulkan/wrapper/libvulkan_wrapper.so

- name: Upload wrapper artifacts
if: success()
uses: actions/upload-artifact@v4
with:
name: vulkan-wrapper
path: |
_build/src/vulkan/wrapper/libvulkan_wrapper.so
_build/src/vulkan/wrapper/wrapper_icd.*.json

- name: Report build artifacts
if: always()
run: |
echo "=== Build log ==="
cat _build/meson-logs/meson-log.txt | tail -100 || true
echo "=== Built files ==="
find _build/src/vulkan/wrapper -name '*.so' -o -name '*.json' 2>/dev/null || true

build-wrapper-arm64-ndk:
name: Build Vulkan Wrapper (ARM64 Android NDK)
runs-on: ubuntu-24.04

env:
NDK_VERSION: r27c
ANDROID_API: 26

steps:
- name: Checkout
uses: actions/checkout@v4

- name: Install build tools
run: |
sudo apt-get update
sudo apt-get install -y \
meson ninja-build \
python3 python3-mako python3-ply python3-yaml \
glslang-tools \
cmake git \
unzip wget

- name: Setup Android NDK
run: |
wget -q https://dl.google.com/android/repository/android-ndk-${NDK_VERSION}-linux.zip -O /tmp/ndk.zip
unzip -q /tmp/ndk.zip -d /tmp
echo "ANDROID_NDK_HOME=/tmp/android-ndk-${NDK_VERSION}" >> $GITHUB_ENV
NDK_TC="/tmp/android-ndk-${NDK_VERSION}/toolchains/llvm/prebuilt/linux-x86_64"
echo "${NDK_TC}/bin" >> $GITHUB_PATH
echo "NDK_TOOLCHAIN=${NDK_TC}" >> $GITHUB_ENV
# Verify toolchain
${NDK_TC}/bin/aarch64-linux-android${ANDROID_API}-clang --version

- name: Build SPIRV-Tools for Android aarch64 (custom fork)
run: |
git clone --depth 1 https://github.com/BlueInstruction/SPIRV-Tools.git /tmp/SPIRV-Tools
cd /tmp/SPIRV-Tools
python3 utils/git-sync-deps
mkdir build && cd build
cmake .. \
-DCMAKE_BUILD_TYPE=Release \
-DSPIRV_SKIP_TESTS=ON \
-DCMAKE_SYSTEM_NAME=Android \
-DCMAKE_SYSTEM_VERSION=${ANDROID_API} \
-DCMAKE_ANDROID_ARCH_ABI=arm64-v8a \
-DCMAKE_ANDROID_NDK=${ANDROID_NDK_HOME} \
-DCMAKE_ANDROID_STL_TYPE=c++_static
cmake --build . --config Release -j$(nproc) --target SPIRV-Tools-static SPIRV-Tools-opt
mkdir -p $GITHUB_WORKSPACE/src/vulkan/wrapper/lib
cp source/libSPIRV-Tools.a $GITHUB_WORKSPACE/src/vulkan/wrapper/lib/
cp source/opt/libSPIRV-Tools-opt.a $GITHUB_WORKSPACE/src/vulkan/wrapper/lib/
# Do NOT overwrite the patched headers — they contain custom pass declarations
# Only copy headers that don't already exist in the repo
find /tmp/SPIRV-Tools/include -type f | while read src; do
rel="${src#/tmp/SPIRV-Tools/include/}"
dst="$GITHUB_WORKSPACE/src/vulkan/wrapper/include/spirv-tools/$rel"
if [ ! -f "$dst" ]; then
mkdir -p "$(dirname "$dst")"
cp "$src" "$dst"
fi
done

- name: Download Termux prebuilt packages for aarch64
run: |
set -e
SYSROOT=$GITHUB_WORKSPACE/_sysroot
mkdir -p $SYSROOT

# Termux package base URL for aarch64
TERMUX_REPO="https://packages.termux.dev/apt/termux-main/pool/main"

# Download and extract .deb packages (contains headers + .so + .pc files)
download_termux_pkg() {
local pkg=$1 letter=$2
local url="${TERMUX_REPO}/${letter}/${pkg}"
echo "Downloading ${pkg}..."
wget -q "$url" -O /tmp/pkg.deb
cd /tmp && ar x pkg.deb && tar xf data.tar.* -C $SYSROOT --strip-components=3 ./data/data/com.termux/files/usr/ 2>/dev/null || tar xf data.tar.* -C $SYSROOT --strip-components=4 2>/dev/null || true
rm -f /tmp/pkg.deb /tmp/data.tar.* /tmp/control.tar.* /tmp/debian-binary
}

# Core X11/XCB libraries needed by libvulkan_wrapper.so
download_termux_pkg "libdrm_2.4.124-1_aarch64.deb" "libd"
download_termux_pkg "libdrm-dev_2.4.124-1_aarch64.deb" "libd"
download_termux_pkg "libx11_1.8.10_aarch64.deb" "libx"
download_termux_pkg "libx11-dev_1.8.10_aarch64.deb" "libx"
download_termux_pkg "libxcb_1.17.0_aarch64.deb" "libx"
download_termux_pkg "libxcb-dev_1.17.0_aarch64.deb" "libx"
download_termux_pkg "libxau_1.0.11-1_aarch64.deb" "libx"
download_termux_pkg "libxau-dev_1.0.11-1_aarch64.deb" "libx"
download_termux_pkg "libxdmcp_1.1.5_aarch64.deb" "libx"
download_termux_pkg "libxdmcp-dev_1.1.5_aarch64.deb" "libx"
download_termux_pkg "libxext_1.3.6_aarch64.deb" "libx"
download_termux_pkg "libxext-dev_1.3.6_aarch64.deb" "libx"
download_termux_pkg "libxrandr_1.5.4_aarch64.deb" "libx"
download_termux_pkg "libxrandr-dev_1.5.4_aarch64.deb" "libx"
download_termux_pkg "libxrender_0.9.11_aarch64.deb" "libx"
download_termux_pkg "libxrender-dev_0.9.11_aarch64.deb" "libx"
download_termux_pkg "libxshmfence_1.3.2_aarch64.deb" "libx"
download_termux_pkg "libxshmfence-dev_1.3.2_aarch64.deb" "libx"
download_termux_pkg "libxfixes_6.0.1_aarch64.deb" "libx"
download_termux_pkg "libxfixes-dev_6.0.1_aarch64.deb" "libx"
download_termux_pkg "libxxf86vm_1.1.5-1_aarch64.deb" "libx"
download_termux_pkg "libxxf86vm-dev_1.1.5-1_aarch64.deb" "libx"
download_termux_pkg "xorgproto_2024.1_aarch64.deb" "xorg"
download_termux_pkg "libelf_0.192_aarch64.deb" "libe"
download_termux_pkg "libelf-dev_0.192_aarch64.deb" "libe"
download_termux_pkg "libexpat_2.6.4_aarch64.deb" "libe"
download_termux_pkg "libexpat-dev_2.6.4_aarch64.deb" "libe"
download_termux_pkg "libwayland_1.23.1_aarch64.deb" "libw"
download_termux_pkg "libwayland-dev_1.23.1_aarch64.deb" "libw"
download_termux_pkg "wayland-protocols_1.38_aarch64.deb" "wayl"

echo "=== Installed sysroot contents ==="
find $SYSROOT/lib/pkgconfig -name '*.pc' 2>/dev/null | sort || true
ls -la $SYSROOT/lib/*.so* 2>/dev/null | head -20 || true

- name: Configure Mesa (wrapper only, Android NDK aarch64)
run: |
STUB_ARGS="-D__INTRODUCED_IN(x)= -D__ANDROID_API__=${ANDROID_API} -D__TERMUX__ -DHAVE_CUSTOM_SPIRV_PASSES"
STUB_C="$STUB_ARGS"
STUB_CXX="$STUB_ARGS -DNULL=nullptr"
PKG_CONFIG_LIBDIR=$GITHUB_WORKSPACE/_sysroot/lib/pkgconfig:$GITHUB_WORKSPACE/_sysroot/share/pkgconfig \
meson setup _build \
--cross-file cross/aarch64-linux-android.txt \
-Dvulkan-drivers=wrapper \
-Dgallium-drivers= \
-Dandroid-stub=true \
-Dplatforms=x11 \
-Dglx=disabled \
-Degl=disabled \
-Dgbm=disabled \
-Dopengl=false \
-Dgles1=disabled \
-Dgles2=disabled \
-Dllvm=disabled \
-Dshared-glapi=disabled \
-Dbuildtype=release \
-Dc_args="$STUB_C" \
-Dcpp_args="$STUB_CXX"

- name: Build
run: |
ninja -C _build src/vulkan/wrapper/libvulkan_wrapper.so

- name: Verify Android ARM64 binary
run: |
file _build/src/vulkan/wrapper/libvulkan_wrapper.so
${NDK_TOOLCHAIN}/bin/llvm-readelf -h _build/src/vulkan/wrapper/libvulkan_wrapper.so
echo "=== Dynamic dependencies ==="
${NDK_TOOLCHAIN}/bin/llvm-readelf -d _build/src/vulkan/wrapper/libvulkan_wrapper.so | grep NEEDED || true
echo "=== File size ==="
ls -lh _build/src/vulkan/wrapper/libvulkan_wrapper.so

- name: Upload Android ARM64 wrapper artifacts
if: success()
uses: actions/upload-artifact@v4
with:
name: vulkan-wrapper-android-arm64
path: |
_build/src/vulkan/wrapper/libvulkan_wrapper.so
_build/src/vulkan/wrapper/wrapper_icd.*.json

- name: Report build artifacts
if: always()
run: |
echo "=== Build log (last 200 lines) ==="
cat _build/meson-logs/meson-log.txt | tail -200 || true
echo "=== Built files ==="
find _build/src/vulkan/wrapper -name '*.so' -o -name '*.json' 2>/dev/null || true
22 changes: 22 additions & 0 deletions cross/aarch64-linux-android.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
# Meson cross file for Android NDK aarch64 (ARM64)
# NDK_TOOLCHAIN env var must point to the NDK toolchain bin directory
# e.g. $ANDROID_NDK_HOME/toolchains/llvm/prebuilt/linux-x86_64

[binaries]
c = 'aarch64-linux-android26-clang'
cpp = 'aarch64-linux-android26-clang++'
ar = 'llvm-ar'
strip = 'llvm-strip'
pkgconfig = 'pkg-config'

[built-in options]
c_args = ['-fPIC']
cpp_args = ['-fPIC']
c_link_args = ['-fPIC']
cpp_link_args = ['-fPIC', '-static-libstdc++']

[host_machine]
system = 'android'
cpu_family = 'aarch64'
cpu = 'aarch64'
endian = 'little'
12 changes: 12 additions & 0 deletions cross/aarch64-linux-gnu.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
[binaries]
c = 'aarch64-linux-gnu-gcc'
cpp = 'aarch64-linux-gnu-g++'
ar = 'aarch64-linux-gnu-ar'
strip = 'aarch64-linux-gnu-strip'
pkgconfig = 'pkg-config'

[host_machine]
system = 'linux'
cpu_family = 'aarch64'
cpu = 'aarch64'
endian = 'little'
5 changes: 5 additions & 0 deletions include/android_stub/cutils/trace.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,12 @@
#define _LIBS_CUTILS_TRACE_H

#include <inttypes.h>
#ifdef __cplusplus
#include <atomic>
using std::atomic_bool;
#else
#include <stdatomic.h>
#endif
#include <stdbool.h>
#include <stdint.h>
#include <stdio.h>
Expand Down
6 changes: 6 additions & 0 deletions src/vulkan/wrapper/artifacts.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,12 @@
#include "wrapper_checks.h"
#include "vk_printers.h"

#ifndef __ANDROID__
#include <cerrno>
extern char *program_invocation_short_name;
static inline const char *getprogname() { return program_invocation_short_name; }
#endif

#define XXH_INLINE_ALL
#include "util/xxhash.h"

Expand Down
10 changes: 10 additions & 0 deletions src/vulkan/wrapper/spirv_edit.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,16 @@ extern "C" {
#include "spirv-tools/spirv-tools/optimizer.hpp"
#include "spirv-tools/spirv-tools/libspirv.hpp"

// Stub out custom SPIRV-Tools passes that only exist in the patched fork.
// These are no-ops for CI builds using upstream SPIRV-Tools v2024.4.rc2.
#ifndef HAVE_CUSTOM_SPIRV_PASSES
namespace spvtools {
static inline Optimizer::PassToken CreateRemoveClipCullDistPass() { return CreateNullPass(); }
static inline Optimizer::PassToken CreateFixMaliSpecConstantCompositePass() { return CreateNullPass(); }
static inline Optimizer::PassToken CreateMaliOptimizationBarrierPass() { return CreateNullPass(); }
}
#endif

extern "C"
void log_disassembly_to_cmd_log(const uint32_t* spirv_binary, size_t spirv_word_count) {
spvtools::SpirvTools tools(SPV_ENV_VULKAN_1_1_SPIRV_1_4);
Expand Down
1 change: 1 addition & 0 deletions src/vulkan/wrapper/spirv_edit.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

#include <stdbool.h>
#include <stdint.h>
#include <stddef.h>

#ifdef __cplusplus
extern "C" {
Expand Down
2 changes: 1 addition & 1 deletion src/vulkan/wrapper/vk_entrypoints.py
Original file line number Diff line number Diff line change
Expand Up @@ -132,7 +132,7 @@ def print_param(command, param, mode='input', log='VK_CMD_LOG_UNCONDITIONAL', vk
output.append(f" for (uint32_t i = 0; i < {count}; i++) {{")
output.append(f" {log}(\" {param.name}[%d]: {param.type} = %lx (id=%d)\", i, (int64_t){param.name}[i], cmd_id);");
output.append(f" }}")
elif param.num_pointers and not is_input and param.type not in ("void", "Display", "xcb_connection_t"):
elif param.num_pointers and not is_input and param.type not in ("void", "Display", "xcb_connection_t", "wl_display"):
output.append(f" {log}(\" {token}: *{param.name}: {param.type} = %lx (id=%d)\", (int64_t)*{param.name}, cmd_id);")
elif param.num_pointers:
output.append(f" {log}(\" {token}: {param.name}: {param.type}{'*' * param.num_pointers} = %lx (id=%d)\", (int64_t){param.name}, cmd_id);")
Expand Down
6 changes: 6 additions & 0 deletions src/vulkan/wrapper/wrapper_checks.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,10 +18,16 @@
#define CHECKV(call) __CHECKV__(wrapper_device_trampolines. call)
#define PCHECKV(call) __CHECKV__(wrapper_physical_device_trampolines. call)

#if defined(__clang__)
#define __W_WRAP__(call, expr) \
_Static_assert(__builtin_strcmp(__func__, name_of_wrapper_##call) != 0, \
"This WCHECK macro for " #call " cannot be used in the same wrapper, it will cause infinite recursion"); \
expr;
#else
/* GCC does not treat __builtin_strcmp(__func__, ...) as a constant expression */
#define __W_WRAP__(call, expr) \
expr;
#endif

#define WCHECK(call) ({__W_WRAP__(call, has_device_wrapper_##call ? __CHECK__(wrapper_device_entrypoints. call) : CHECK(call))})
#define WCHECKV(call) {__W_WRAP__(call, { if(has_device_wrapper_##call) { __CHECKV__(wrapper_device_entrypoints. call); } else { CHECKV(call); }})}
Expand Down
Loading