Vendor the Shockolate engine and build it via a Docker image with every
build / build (push) Failing after 5s
build / build (push) Failing after 5s
dependency (SDL2, SDL2_mixer, fluidsynth-lite, a MIDI soundfont) prebuilt, so compiling the engine needs no network access - just the image and the engine source. Add res/assets/extract_assets.sh to pull the game's data files out of a purchased GOG installer, and a Makefile that assembles a runnable dist/ from the two. Also add `make package`, which builds a redistributable tarball that omits the proprietary game assets (shipping res/GET_ASSETS.txt instead) plus license information for both the MIT tooling and the GPLv3 engine, and a Gitea Actions workflow that builds and publishes it to dl.ladkau.de on every push.
This commit is contained in:
@@ -0,0 +1,99 @@
|
||||
# Build environment for the Shockolate (System Shock) engine snapshot in
|
||||
# engine/. Everything the engine build needs from the network - SDL2,
|
||||
# SDL2_mixer, the fluidsynth-lite MIDI synth, and a General MIDI soundfont -
|
||||
# is fetched and built once, here, at image-build time. Rebuild with
|
||||
# ../build-image.sh whenever a version below changes.
|
||||
#
|
||||
# The resulting image needs no network access to compile engine/: the
|
||||
# in-container build script (build-image/build-engine.sh) copies the
|
||||
# prebuilt pieces below straight into engine/build_ext/, matching the paths
|
||||
# engine/CMakeLists.txt's BUNDLED dependency mode expects.
|
||||
FROM ubuntu:22.04
|
||||
|
||||
ARG SDL2_VERSION=2.0.9
|
||||
ARG SDL2_MIXER_VERSION=2.0.4
|
||||
# EtherTyper/fluidsynth-lite has no releases/tags; pin by commit so the image
|
||||
# is reproducible instead of silently picking up upstream changes.
|
||||
ARG FLUIDSYNTH_LITE_REF=c539a8d9270ba5a3f7d6e460606483fc2ab1eb61
|
||||
# Soundfont used for MIDI music, matching what engine/build_deps.sh itself
|
||||
# fetches (a free substitute for the Windows default GM soundfont).
|
||||
ARG SOUNDFONT_URL=http://rancid.kapsi.fi/windows.sf2
|
||||
|
||||
ENV DEBIAN_FRONTEND=noninteractive
|
||||
|
||||
# build-essential/cmake/make: engine/ itself (CMake) and SDL2/SDL2_mixer
|
||||
# (autotools).
|
||||
# git: fetches fluidsynth-lite; also used by engine/CMakeLists.txt's own
|
||||
# `git describe` version string (harmless no-op if engine/ isn't a repo).
|
||||
# curl/ca-certificates: fetches SDL2/SDL2_mixer tarballs and the soundfont.
|
||||
# pkg-config: SDL2_mixer's configure and engine/CMakeLists.txt's
|
||||
# pkg_check_modules() calls.
|
||||
# gosu: docker-entrypoint.sh drops from root to a HOST_UID/GID user so
|
||||
# build output isn't left root-owned on the bind-mounted repo.
|
||||
# libgl1-mesa-dev/libglx-dev/libxext-dev/libx11-dev/libxrandr-dev/libxi-dev/
|
||||
# libxfixes-dev/libxss-dev/libxinerama-dev/libxcursor-dev: SDL2's video
|
||||
# backend (X11 + GL).
|
||||
# libogg-dev/libvorbis-dev: SDL2_mixer's OGG Vorbis music decoder.
|
||||
# libasound2-dev: engine/CMakeLists.txt's optional native ALSA MIDI output.
|
||||
# openssh-client: the CI workflow's `sftp` publish step.
|
||||
RUN apt-get update && apt-get install -y --no-install-recommends \
|
||||
build-essential cmake make git curl ca-certificates pkg-config gosu \
|
||||
libgl1-mesa-dev libglx-dev libxext-dev libx11-dev libxrandr-dev \
|
||||
libxi-dev libxfixes-dev libxss-dev libxinerama-dev libxcursor-dev \
|
||||
libogg-dev libvorbis-dev libasound2-dev openssh-client \
|
||||
&& rm -rf /var/lib/apt/lists/*
|
||||
|
||||
WORKDIR /opt/prebuilt
|
||||
|
||||
# SDL2, built the same way engine/build_deps.sh builds it (BUNDLED mode),
|
||||
# just at image-build time instead of every game build.
|
||||
RUN curl -sSLO "https://www.libsdl.org/release/SDL2-${SDL2_VERSION}.tar.gz" \
|
||||
&& tar xf "SDL2-${SDL2_VERSION}.tar.gz" \
|
||||
&& cd "SDL2-${SDL2_VERSION}" \
|
||||
&& ./configure --prefix=/opt/prebuilt/built_sdl \
|
||||
&& make -j"$(nproc)" \
|
||||
&& make install \
|
||||
&& cd .. && rm -rf "SDL2-${SDL2_VERSION}" "SDL2-${SDL2_VERSION}.tar.gz"
|
||||
|
||||
# SDL2_mixer, linked against the SDL2 build above via SDL2_CONFIG - same as
|
||||
# engine/build_deps.sh's build_sdl_mixer().
|
||||
RUN curl -sSLO "https://www.libsdl.org/projects/SDL_mixer/release/SDL2_mixer-${SDL2_MIXER_VERSION}.tar.gz" \
|
||||
&& tar xf "SDL2_mixer-${SDL2_MIXER_VERSION}.tar.gz" \
|
||||
&& cd "SDL2_mixer-${SDL2_MIXER_VERSION}" \
|
||||
&& SDL2_CONFIG=/opt/prebuilt/built_sdl/bin/sdl2-config \
|
||||
./configure --prefix=/opt/prebuilt/built_sdl_mixer \
|
||||
&& make -j"$(nproc)" \
|
||||
&& make install \
|
||||
&& cd .. && rm -rf "SDL2_mixer-${SDL2_MIXER_VERSION}" "SDL2_mixer-${SDL2_MIXER_VERSION}.tar.gz"
|
||||
|
||||
# fluidsynth-lite: the stripped-down FluidSynth fork engine/CMakeLists.txt's
|
||||
# BUNDLED FluidSynth mode expects at build_ext/fluidsynth-lite. Built
|
||||
# in-source (its own CMake setup expects that), forcing a shared library
|
||||
# the same way engine/build_deps.sh's sed does.
|
||||
RUN git clone https://github.com/EtherTyper/fluidsynth-lite.git \
|
||||
&& cd fluidsynth-lite \
|
||||
&& git checkout "${FLUIDSYNTH_LITE_REF}" \
|
||||
&& sed -i 's/DLL"\ off/DLL"\ on/' CMakeLists.txt \
|
||||
&& cmake . \
|
||||
&& cmake --build . -j"$(nproc)" \
|
||||
&& rm -rf .git
|
||||
|
||||
# General MIDI soundfont for fluidsynth playback - engine/build_deps.sh
|
||||
# fetches the same file and drops it into engine/res/.
|
||||
RUN mkdir -p soundfont \
|
||||
&& curl -sSL -o soundfont/default.sf2 "${SOUNDFONT_URL}"
|
||||
|
||||
COPY build-image/docker-entrypoint.sh /usr/local/bin/docker-entrypoint.sh
|
||||
COPY build-image/build-engine.sh /usr/local/bin/build-engine.sh
|
||||
RUN chmod +x /usr/local/bin/docker-entrypoint.sh /usr/local/bin/build-engine.sh
|
||||
|
||||
# Marks a shell as already running inside this image (with every engine
|
||||
# build dependency prebuilt above) - lets the Makefile's `engine` target
|
||||
# compile directly instead of shelling out to ./run-image.sh's `docker
|
||||
# run`, which matters for CI jobs that already run inside this image
|
||||
# (nested docker-in-docker isn't available there).
|
||||
ENV QUESTSHOCK_BUILD_IMAGE=1
|
||||
|
||||
WORKDIR /workspace
|
||||
ENTRYPOINT ["/usr/local/bin/docker-entrypoint.sh"]
|
||||
CMD ["/usr/local/bin/build-engine.sh"]
|
||||
@@ -0,0 +1 @@
|
||||
1
|
||||
Executable
+47
@@ -0,0 +1,47 @@
|
||||
#!/usr/bin/env bash
|
||||
# Compiles engine/ (the vendored Shockolate snapshot) against the
|
||||
# dependencies prebuilt into this image at /opt/prebuilt - no network
|
||||
# access needed. Must be run with the repo root as the working directory
|
||||
# - either via ../run-image.sh (which docker-runs this image with the
|
||||
# repo bind-mounted at /workspace and WORKDIR set there), or directly
|
||||
# when already inside this image (e.g. a CI job using this image as its
|
||||
# container - see the Makefile's `engine` target, which picks whichever
|
||||
# of these applies).
|
||||
#
|
||||
# Output lands in engine/.build-output/: the systemshock binary, the
|
||||
# shared libraries it needs at runtime (lib/), and a default MIDI
|
||||
# soundfont - everything the root Makefile needs to assemble dist/.
|
||||
set -euo pipefail
|
||||
|
||||
REPO_ROOT="$(pwd)"
|
||||
ENGINE_DIR="$REPO_ROOT/engine"
|
||||
OUT_DIR="$ENGINE_DIR/.build-output"
|
||||
|
||||
cd "$ENGINE_DIR"
|
||||
|
||||
echo "== Wiring up prebuilt SDL2/SDL2_mixer/fluidsynth-lite from the image =="
|
||||
rm -rf build_ext
|
||||
mkdir -p build_ext
|
||||
cp -a /opt/prebuilt/built_sdl build_ext/
|
||||
cp -a /opt/prebuilt/built_sdl_mixer build_ext/
|
||||
cp -a /opt/prebuilt/fluidsynth-lite build_ext/
|
||||
|
||||
echo "== Configuring (CMake, BUNDLED SDL2/SDL2_mixer/FluidSynth) =="
|
||||
rm -f CMakeCache.txt
|
||||
cmake -DENABLE_SDL2=BUNDLED -DENABLE_SOUND=BUNDLED -DENABLE_FLUIDSYNTH=BUNDLED .
|
||||
|
||||
echo "== Compiling =="
|
||||
make -j"$(nproc)" systemshock
|
||||
|
||||
echo "== Assembling engine/.build-output =="
|
||||
rm -rf "$OUT_DIR"
|
||||
mkdir -p "$OUT_DIR/lib"
|
||||
cp systemshock "$OUT_DIR/"
|
||||
find build_ext/built_sdl/lib build_ext/built_sdl_mixer/lib build_ext/fluidsynth-lite/src \
|
||||
-name '*.so*' -not -name '*.la' -exec cp -a {} "$OUT_DIR/lib/" \;
|
||||
cp /opt/prebuilt/soundfont/default.sf2 "$OUT_DIR/soundfont.sf2"
|
||||
|
||||
echo "== Done =="
|
||||
echo "Binary: $OUT_DIR/systemshock"
|
||||
echo "Libraries: $OUT_DIR/lib/"
|
||||
echo "Soundfont: $OUT_DIR/soundfont.sf2"
|
||||
Executable
+14
@@ -0,0 +1,14 @@
|
||||
#!/usr/bin/env bash
|
||||
# Drops from root (needed to read the prebuilt toolchain under /opt) to a
|
||||
# user matching the host's UID/GID, so anything written into the
|
||||
# bind-mounted repo (engine/build_ext, engine/.build-output, ...) is owned
|
||||
# by the host user instead of root.
|
||||
set -euo pipefail
|
||||
|
||||
USER_UID="${HOST_UID:-1000}"
|
||||
USER_GID="${HOST_GID:-1000}"
|
||||
|
||||
groupadd -g "$USER_GID" builder 2>/dev/null || true
|
||||
useradd -u "$USER_UID" -g "$USER_GID" -m -s /bin/bash builder 2>/dev/null || true
|
||||
|
||||
exec gosu builder "$@"
|
||||
Reference in New Issue
Block a user