Skip to content

Commit b7dd56d

Browse files
CI: Add initial build workflow (#2)
Co-authored-by: Dominic Koepke <koepke@aunovis.de>
1 parent 9c4ff2c commit b7dd56d

File tree

3 files changed

+388
-5
lines changed

3 files changed

+388
-5
lines changed

.github/workflows/build.yml

Lines changed: 381 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,381 @@
1+
# Copyright Dominic (DNKpp) Koepke 2025 - 2025.
2+
# Distributed under the Boost Software License, Version 1.0.
3+
# (See accompanying file LICENSE_1_0.txt or copy at
4+
# https://www.boost.org/LICENSE_1_0.txt)
5+
6+
name: build & test
7+
on:
8+
push:
9+
branches: [ main, development ]
10+
paths-ignore:
11+
- 'README.md'
12+
- 'docs/**'
13+
pull_request:
14+
branches: [ main, development ]
15+
paths-ignore:
16+
- 'README.md'
17+
- 'docs/**'
18+
19+
jobs:
20+
############
21+
#
22+
# Defines the compiler configurations for the other jobs.
23+
#
24+
#####
25+
generate-base-matrix:
26+
runs-on: ubuntu-latest
27+
28+
outputs:
29+
architectures: ${{ steps.output-options.outputs.architectures }}
30+
build_modes: ${{ steps.output-options.outputs.build_modes }}
31+
cxx_versions: ${{ steps.output-options.outputs.cxx_versions }}
32+
33+
steps:
34+
# enables debug-mode, c++20 and 64bit for all cases
35+
- name: Enable base matrix
36+
shell: bash
37+
run: |
38+
echo "ARCHITECTURES=\"64bit\", \"32bit\"" >> $GITHUB_ENV
39+
echo "BUILD_MODES=\"Debug\", \"Release\"" >> $GITHUB_ENV
40+
echo "CXX_VERSIONS=20, 23" >> $GITHUB_ENV
41+
42+
# if it's a PR from development or the main branch in general, add release-mode, c++23 and 32bit
43+
# - name: Enable extended matrix
44+
# if: ${{
45+
# (github.event_name == 'pull_request' && github.head_ref == 'development')
46+
# || github.ref_name == 'main'
47+
# }}
48+
# shell: bash
49+
# run: |
50+
# echo "ARCHITECTURES=$(echo ${ARCHITECTURES}, \"32bit\")" >> $GITHUB_ENV
51+
# echo "BUILD_MODES=$(echo ${BUILD_MODES}, \"Release\")" >> $GITHUB_ENV
52+
# echo "CXX_VERSIONS=$(echo ${CXX_VERSIONS}, 23)" >> $GITHUB_ENV
53+
54+
- name: Output architectures, build-modes and c++-versions
55+
id: output-options
56+
shell: bash
57+
run: |
58+
echo "architectures=$(echo [ ${ARCHITECTURES} ])" >> "$GITHUB_OUTPUT"
59+
echo "build_modes=$(echo [ ${BUILD_MODES} ])" >> "$GITHUB_OUTPUT"
60+
echo "cxx_versions=$(echo [ ${CXX_VERSIONS} ])" >> "$GITHUB_OUTPUT"
61+
62+
build-and-test:
63+
needs: generate-base-matrix
64+
runs-on: ${{ matrix.config.os }}
65+
container: ${{ matrix.config.container.image }}
66+
name: |
67+
${{ matrix.config.prefix }}
68+
${{ matrix.config.compiler_name }}-${{ matrix.config.compiler_version }}
69+
${{ matrix.config.suffix }}
70+
(C++${{ matrix.cxx_standard }}, ${{ matrix.build_mode }}, ${{ matrix.architecture }})
71+
72+
strategy:
73+
fail-fast: false
74+
matrix:
75+
architecture: ${{ fromJSON(needs.generate-base-matrix.outputs.architectures) }}
76+
build_mode: ${{ fromJSON(needs.generate-base-matrix.outputs.build_modes) }}
77+
cxx_standard: ${{ fromJSON(needs.generate-base-matrix.outputs.cxx_versions) }}
78+
config:
79+
# clang
80+
- prefix: "Linux"
81+
suffix: "ASan"
82+
os: "ubuntu-latest"
83+
container:
84+
image: "ghcr.io/dnkpp/clang:20"
85+
compiler_name: "clang"
86+
compiler_version: "20"
87+
asan: true
88+
89+
- prefix: "Linux"
90+
suffix: "/libc++"
91+
os: "ubuntu-latest"
92+
container:
93+
image: "ghcr.io/dnkpp/clang:20"
94+
compiler_name: "clang"
95+
compiler_version: "20"
96+
libcxx: true
97+
98+
- prefix: "Linux"
99+
os: "ubuntu-latest"
100+
container:
101+
image: "ghcr.io/dnkpp/clang:20"
102+
compiler_name: "clang"
103+
compiler_version: "20"
104+
105+
- prefix: "Linux"
106+
suffix: "/libc++"
107+
os: "ubuntu-latest"
108+
container:
109+
image: "ghcr.io/dnkpp/clang:19"
110+
compiler_name: "clang"
111+
compiler_version: "19"
112+
libcxx: true
113+
114+
- prefix: "Linux"
115+
os: "ubuntu-latest"
116+
container:
117+
image: "ghcr.io/dnkpp/clang:19"
118+
compiler_name: "clang"
119+
compiler_version: "19"
120+
121+
- prefix: "Linux"
122+
suffix: "/libc++"
123+
os: "ubuntu-latest"
124+
container:
125+
image: "ghcr.io/dnkpp/clang:18"
126+
compiler_name: "clang"
127+
compiler_version: "18"
128+
libcxx: true
129+
130+
- prefix: "Linux"
131+
os: "ubuntu-latest"
132+
container:
133+
image: "ghcr.io/dnkpp/clang:18"
134+
compiler_name: "clang"
135+
compiler_version: "18"
136+
137+
- prefix: "Linux"
138+
suffix: "/libc++"
139+
os: "ubuntu-latest"
140+
container:
141+
image: "ghcr.io/dnkpp/clang:17"
142+
compiler_name: "clang"
143+
compiler_version: "17"
144+
libcxx: true
145+
146+
- prefix: "Linux"
147+
os: "ubuntu-latest"
148+
container:
149+
image: "ghcr.io/dnkpp/clang:17"
150+
compiler_name: "clang"
151+
compiler_version: "17"
152+
153+
- prefix: "Linux"
154+
suffix: "/libc++"
155+
os: "ubuntu-latest"
156+
container:
157+
image: "ghcr.io/dnkpp/clang:16"
158+
compiler_name: "clang"
159+
compiler_version: "16"
160+
libcxx: true
161+
162+
- prefix: "Linux"
163+
os: "ubuntu-latest"
164+
container:
165+
image: "ghcr.io/dnkpp/clang:16"
166+
compiler_name: "clang"
167+
compiler_version: "16"
168+
169+
# gcc
170+
- prefix: "Linux"
171+
suffix: "ASan"
172+
os: "ubuntu-latest"
173+
container:
174+
image: "ghcr.io/dnkpp/gcc:15"
175+
compiler_name: "gcc"
176+
compiler_version: "15"
177+
asan: true
178+
179+
- prefix: "Linux"
180+
os: "ubuntu-latest"
181+
container:
182+
image: "ghcr.io/dnkpp/gcc:15"
183+
compiler_name: "gcc"
184+
compiler_version: "15"
185+
186+
- prefix: "Linux"
187+
os: "ubuntu-latest"
188+
container:
189+
image: "ghcr.io/dnkpp/gcc:14"
190+
compiler_name: "gcc"
191+
compiler_version: "14"
192+
193+
- prefix: "Linux"
194+
os: "ubuntu-latest"
195+
container:
196+
image: "ghcr.io/dnkpp/gcc:13"
197+
compiler_name: "gcc"
198+
compiler_version: "13"
199+
200+
- prefix: "Linux"
201+
os: "ubuntu-latest"
202+
container:
203+
image: "ghcr.io/dnkpp/gcc:12"
204+
compiler_name: "gcc"
205+
compiler_version: "12"
206+
207+
# msvc
208+
- prefix: "Windows 2022"
209+
os: "windows-2022"
210+
compiler_name: "msvc"
211+
compiler_version: "v143"
212+
cmake_generator: "Visual Studio 17 2022"
213+
214+
- prefix: "Windows 2022"
215+
os: "windows-2022"
216+
compiler_name: "msvc"
217+
compiler_version: "ClangCl"
218+
cmake_generator: "Visual Studio 17 2022"
219+
220+
# macOS
221+
- prefix: "macOS"
222+
os: "macos-latest"
223+
compiler_name: "AppleClang"
224+
compiler_version: "18"
225+
ldflags_workaround: "-L/opt/homebrew/opt/llvm/lib/c++ -L/opt/homebrew/opt/llvm/lib/unwind -lunwind"
226+
227+
- prefix: "macOS"
228+
os: "macos-latest"
229+
compiler_name: "AppleClang"
230+
compiler_version: "17"
231+
ldflags_workaround: "-L/opt/homebrew/opt/llvm@17/lib/c++ -Wl,-rpath,/opt/homebrew/opt/llvm@17/lib/c++"
232+
233+
- prefix: "macOS"
234+
os: "macos-latest"
235+
compiler_name: "AppleClang"
236+
compiler_version: "16"
237+
ldflags_workaround: "-L/opt/homebrew/opt/llvm@16/lib/c++ -Wl,-rpath,/opt/homebrew/opt/llvm@16/lib/c++"
238+
only_fmt: true
239+
240+
exclude:
241+
# This combination results in a compile error in ranges header.
242+
- cxx_standard: 23
243+
config:
244+
compiler_name: "clang"
245+
compiler_version: "16"
246+
libcxx: false
247+
# seems like macOS doesn't support 32bit builds
248+
- architecture: "32bit"
249+
config:
250+
prefix: "macOS"
251+
# run asan only in debug mode
252+
- build_mode: "Release"
253+
config:
254+
asan: true
255+
256+
steps:
257+
- name: Checkout code
258+
uses: actions/checkout@v4
259+
260+
- name: Setup base cmake options
261+
shell: bash
262+
# sets up common options, used by all cmake configure steps.
263+
# explicitly disable all optional features here
264+
run: |
265+
echo "CMAKE_BASE_OPTIONS=$(echo ${CMAKE_BASE_OPTIONS} \
266+
--log-level=DEBUG \
267+
-D CMAKE_VERBOSE_MAKEFILE=YES \
268+
-D CTNP_CXX_STANDARD="${{ matrix.cxx_standard }}" \
269+
)" >> $GITHUB_ENV
270+
271+
- name: Setup macOS
272+
if: startsWith(matrix.config.os, 'macOS')
273+
shell: bash
274+
run: |
275+
env brew install ninja llvm
276+
LLVM_NAME=llvm@${{ matrix.config.compiler_version }}
277+
env brew install $LLVM_NAME
278+
LLVM_PATH="$(brew --prefix $LLVM_NAME)"
279+
echo "CC=$(echo $LLVM_PATH/bin/clang)" >> $GITHUB_ENV
280+
echo "CXX=$(echo $LLVM_PATH/bin/clang++)" >> $GITHUB_ENV
281+
282+
# solves this issue: https://github.com/Homebrew/homebrew-core/issues/178435
283+
echo "LDFLAGS=$(echo $LDFLAGS ${{ matrix.config.ldflags_workaround }})" >> $GITHUB_ENV
284+
285+
echo "CMAKE_BASE_OPTIONS=$(echo ${CMAKE_BASE_OPTIONS} -DCMAKE_BUILD_TYPE=${{ matrix.build_mode }})" >> $GITHUB_ENV
286+
287+
- name: Setup linux
288+
if: ${{ matrix.config.prefix == 'Linux' }}
289+
shell: bash
290+
run: |
291+
echo "CMAKE_BASE_OPTIONS=$(echo ${CMAKE_BASE_OPTIONS} -DCMAKE_BUILD_TYPE=${{ matrix.build_mode }})" >> $GITHUB_ENV
292+
293+
- name: Setup msvc
294+
if: ${{ matrix.config.compiler_name == 'msvc' }}
295+
shell: bash
296+
run: |
297+
# translate architecture to appropriate platform config
298+
if [[ "${{ matrix.architecture }}" == "64bit" ]]; then
299+
PLATFORM="x64"
300+
elif [[ "${{ matrix.architecture }}" == "32bit" ]]; then
301+
PLATFORM="Win32"
302+
fi
303+
304+
echo "CMAKE_BASE_OPTIONS=$(echo ${CMAKE_BASE_OPTIONS} \
305+
-G\"${{ matrix.config.cmake_generator }}\" \
306+
-T\"${{ matrix.config.compiler_version }}\" \
307+
-A\"${PLATFORM}\" \
308+
)" >> $GITHUB_ENV
309+
echo "CMAKE_BUILD_EXTRA=$(echo ${CMAKE_BUILD_EXTRA} --config ${{ matrix.build_mode }})" >> $GITHUB_ENV
310+
311+
- name: Clang libc++ setup
312+
if: ${{ matrix.config.compiler_name == 'clang' && matrix.config.libcxx == true }}
313+
shell: bash
314+
run: |
315+
echo "CXXFLAGS=$(echo ${CXXFLAGS} -stdlib=libc++)" >> $GITHUB_ENV
316+
echo "LDFLAGS=$(echo ${LDFLAGS} -lc++abi)" >> $GITHUB_ENV
317+
318+
- name: Setup 32bit on Linux
319+
if: ${{ matrix.architecture == '32bit' && matrix.config.prefix == 'Linux' }}
320+
shell: bash
321+
run: |
322+
echo "CXXFLAGS=$(echo ${CXXFLAGS} -m32)" >> $GITHUB_ENV
323+
echo "CFLAGS=$(echo ${CFLAGS} -m32)" >> $GITHUB_ENV
324+
echo "LDFLAGS=$(echo ${LDFLAGS} -m32)" >> $GITHUB_ENV
325+
326+
- name: Setup 32bit libc++ on Linux
327+
if: ${{
328+
matrix.architecture == '32bit'
329+
&& matrix.config.prefix == 'Linux'
330+
&& matrix.config.libcxx == true
331+
}}
332+
shell: bash
333+
# remove 64bit binaries and install 32bit versions.
334+
# I don't know, how to install them side by side.
335+
run: |
336+
apt-get remove -y \
337+
libc++-${{ matrix.config.compiler_version }}-dev \
338+
libc++abi-${{ matrix.config.compiler_version }}-dev
339+
apt-get autoremove -y
340+
341+
dpkg --add-architecture i386
342+
apt-get update -y
343+
apt-get install -y \
344+
libc++-${{ matrix.config.compiler_version }}-dev:i386 \
345+
libc++abi-${{ matrix.config.compiler_version }}-dev:i386
346+
347+
- name: Enable Address and Undefined Sanitizer
348+
if: ${{ matrix.config.asan }}
349+
shell: bash
350+
run: |
351+
# ASan has some serious trouble with libc++ exception mechanism
352+
# see: https://github.com/llvm/llvm-project/issues/59432
353+
#if [[ "${{ matrix.config.libcxx }}" ]]; then
354+
# echo "ASAN_OPTIONS=$(echo ${ASAN_OPTIONS}:alloc_dealloc_mismatch=0)" >> $GITHUB_ENV
355+
#fi
356+
357+
echo "CMAKE_BASE_OPTIONS=$(echo ${CMAKE_BASE_OPTIONS} -DSANITIZE_ADDRESS=YES -DSANITIZE_UNDEFINED=YES)" >> $GITHUB_ENV
358+
359+
- name: Configure
360+
shell: bash
361+
run: |
362+
cmake \
363+
-S . \
364+
-B build \
365+
${{ env.CMAKE_BASE_OPTIONS }}
366+
367+
- name: Build
368+
shell: bash
369+
run: |
370+
cmake --build build \
371+
-j \
372+
${{ env.CMAKE_BUILD_EXTRA }}
373+
374+
- name: Run tests
375+
shell: bash
376+
env:
377+
CTEST_OUTPUT_ON_FAILURE: 1
378+
run: |
379+
ctest --test-dir build \
380+
-C ${{ matrix.build_mode }} \
381+
-j

0 commit comments

Comments
 (0)