Update frun script generation to find frun.bash #5
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: Build forkrun_ring.so (multiarch) and update frun | |
| on: | |
| push: | |
| paths: | |
| - 'ring_loadables/forkrun_ring.c' | |
| - 'ring_loadables/frun.bash' | |
| - 'META' | |
| - '.github/workflows/forkrun_release.yml' | |
| workflow_dispatch: | |
| jobs: | |
| build: | |
| name: Build (${{ matrix.arch }}) | |
| runs-on: ubuntu-latest | |
| strategy: | |
| fail-fast: false | |
| matrix: | |
| include: | |
| # x86_64: Triple Build | |
| - arch: x86_64 | |
| platform: linux/amd64 | |
| docker_image: fedora:latest | |
| # AArch64 | |
| - arch: aarch64 | |
| platform: linux/arm64 | |
| docker_image: fedora:latest | |
| extra_flags: "-march=armv8-a+crc" | |
| # PPC64LE | |
| - arch: ppc64le | |
| platform: linux/ppc64le | |
| docker_image: fedora:latest | |
| # S390X | |
| - arch: s390x | |
| platform: linux/s390x | |
| docker_image: fedora:latest | |
| # RISC-V 64 | |
| - arch: riscv64 | |
| platform: linux/riscv64 | |
| docker_image: fedorariscv/base:latest | |
| steps: | |
| - name: Checkout repository | |
| uses: actions/checkout@v4 | |
| - name: Set up QEMU | |
| uses: docker/setup-qemu-action@v3 | |
| - name: Build in Docker (${{ matrix.arch }}) | |
| run: | | |
| mkdir -p artifacts | |
| # 1. Define Flags in Host Shell (Clean definition) | |
| OPT_FLAGS="-O3 -flto=auto -fno-strict-aliasing -fno-semantic-interposition -fno-math-errno -ftree-loop-im -ftree-loop-ivcanon -fPIC" | |
| WARN_FLAGS="-DNDEBUG -Wall -Wextra" | |
| LINK_FLAGS="-Wl,-z,relro" | |
| INCLUDES="-I/usr/include/bash -I/usr/include/bash/include -I/usr/include/bash/builtins" | |
| # 2. Run Docker with Env Vars | |
| docker run --rm \ | |
| -v $PWD:/src \ | |
| -w /src \ | |
| --platform=${{ matrix.platform }} \ | |
| -e TARGET_ARCH="${{ matrix.arch }}" \ | |
| -e EXTRA_FLAGS="${{ matrix.extra_flags }}" \ | |
| -e OPT_FLAGS="$OPT_FLAGS" \ | |
| -e WARN_FLAGS="$WARN_FLAGS" \ | |
| -e LINK_FLAGS="$LINK_FLAGS" \ | |
| -e INCLUDES="$INCLUDES" \ | |
| ${{ matrix.docker_image }} \ | |
| bash -c ' | |
| # --- SETUP --- | |
| # Using @development-tools for full build environment | |
| # Using coreutils to provide "truncate" and "od" | |
| echo ">>> Installing dependencies..." | |
| if command -v dnf &>/dev/null; then | |
| dnf install -y @development-tools bash-devel git grep sed coreutils | |
| else | |
| apt-get update && apt-get install -y build-essential libbash-dev git grep sed coreutils | |
| fi | |
| # --- FIND forkrun_ring.c --- | |
| if [[ -f "ring_loadables/forkrun_ring.c" ]]; then | |
| FR_C_PATH="ring_loadables/forkrun_ring.c" | |
| elif [[ -f "forkrun_ring.c" ]]; then | |
| FR_C_PATH="forkrun_ring.c" | |
| else | |
| FR_C_PATH="$(find ./ -type f -name 'forkrun_ring.c' -print -quit)" | |
| fi | |
| { [[ ${FR_C_PATH} ]] && [[ -f "${FR_C_PATH}" ]]; } || { echo "ERROR: could not find path to forkrun_ring.c...ABORTING!" >&2 ; exit 1; } | |
| # --- VERSION EXTRACTION --- | |
| FR_VERSION="unknown" | |
| if [ -f "ring_loadables/META" ]; then | |
| FR_VERSION=$(grep -E "^VERSION:" "ring_loadables/META" | sed -E "s/^VERSION:[ \t]*//") | |
| elif [ -f META ]; then | |
| FR_VERSION=$(grep -E "^VERSION:" META | sed -E "s/^VERSION:[ \t]*//") | |
| fi | |
| echo "Compiling Version: $FR_VERSION" | |
| # --- COMPILATION HELPER --- | |
| compile_target() { | |
| local arch_name="$1" | |
| local march_arg="$2" | |
| local out_file="artifacts/forkrun_ring.${arch_name}.so" | |
| echo ">>> Building $arch_name..." | |
| # 1. Build Array of Definitions | |
| declare -a DEFS | |
| DEFS+=("-DSHELL") | |
| DEFS+=("-DHAVE_CONFIG_H") | |
| DEFS+=("-DBUILD_OS=\"Linux\"") | |
| DEFS+=("-DBUILD_ARCH=\"$arch_name\"") | |
| DEFS+=("-DFORKRUN_RING_VERSION=\"$FR_VERSION\"") | |
| # Quoting magic for spaces inside flags | |
| DEFS+=("-DCOMPILER_FLAGS=\"$OPT_FLAGS $WARN_FLAGS $LINK_FLAGS\"") | |
| # 2. Build Full Command Array | |
| declare -a CMD | |
| CMD+=(gcc "$FR_C_PATH") | |
| CMD+=($OPT_FLAGS $WARN_FLAGS $LINK_FLAGS $INCLUDES) | |
| CMD+=("${DEFS[@]}") | |
| CMD+=(-shared) | |
| if [[ -n "$march_arg" ]]; then | |
| CMD+=($march_arg) | |
| fi | |
| CMD+=(-o "$out_file") | |
| # 3. Execute | |
| "${CMD[@]}" | |
| strip --strip-unneeded "$out_file" | |
| # 4. Verify | |
| enable -f "$out_file" ring_version && ring_version -a || exit 1 | |
| enable -d ring_version | |
| } | |
| # --- EXECUTE --- | |
| if [ "$TARGET_ARCH" == "x86_64" ]; then | |
| compile_target "x86-64-v2" "-march=x86-64-v2" | |
| compile_target "x86-64-v3" "-march=x86-64-v3" | |
| compile_target "x86-64-v4" "-march=x86-64-v4" | |
| else | |
| compile_target "$TARGET_ARCH" "$EXTRA_FLAGS" | |
| fi | |
| ' | |
| - name: Upload Artifacts | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: forkrun-libs-${{ matrix.arch }} | |
| path: artifacts/*.so | |
| embed: | |
| name: Embed Base64 into frun | |
| needs: build | |
| runs-on: ubuntu-latest | |
| permissions: | |
| contents: write | |
| pull-requests: write | |
| steps: | |
| - name: Checkout repository | |
| uses: actions/checkout@v4 | |
| - name: Download all artifacts | |
| uses: actions/download-artifact@v4 | |
| with: | |
| path: all_artifacts | |
| - name: Flatten Artifacts | |
| run: | | |
| mkdir -p artifacts | |
| find all_artifacts -name "*.so" -exec mv {} artifacts/ \; | |
| ls -l artifacts/ | |
| - name: Extract Encoding Function | |
| run: | | |
| - name: Generate New frun Script | |
| shell: bash | |
| run: | | |
| # find the path to frun.bash | |
| # --- FIND frun.bash --- | |
| if [[ -f "ring_loadables/frun.bash" ]]; then | |
| FR_BASH_PATH="ring_loadables/frun.bash" | |
| elif [[ -f "frun.bash" ]]; then | |
| FR_BASH_PATH="frun.bash" | |
| else | |
| FR_BASH_PATH="$(find ./ -type f -name 'frun.bash' -print -quit)" | |
| fi | |
| { [[ ${FR_BASH_PATH} ]] && [[ -f "${FR_BASH_PATH}" ]]; } || { echo "ERROR: could not find path to frun.bash...ABORTING!" >&2 ; exit 1; } | |
| # Pull the helper function out of frun so we can source it | |
| sed -n '/^_forkrun_file_to_base64() {/,/^}/p' "${FR_BASH_PATH}" > encoder.sh | |
| # Source the helper | |
| source encoder.sh | |
| # Initialize buffers | |
| a0='' | |
| a1='' | |
| # 1. Read frun.bash using your logic (Top Half) | |
| { | |
| IFS= | |
| while true; do | |
| read -r -u 3 a | |
| if [[ "$a" == '_forkrun_file_to_base64() {'* ]]; then | |
| a1+="${a}"$'\n' | |
| break | |
| else | |
| a0+="${a}"$'\n' | |
| fi | |
| done | |
| # Read function body (Middle) | |
| while true; do | |
| read -r -u 3 a | |
| a1+="${a}"$'\n' | |
| [[ "$a" == '# <@@@@@< _BASE64_START_ >@@@@@> #'* ]] && break | |
| done | |
| } 3<"${FR_BASH_PATH}" | |
| # 2. Encode Artifacts | |
| unset b64 | |
| declare -A b64 | |
| for f in artifacts/*.so; do | |
| fname=$(basename "$f") | |
| # Extract key: forkrun_ring.x86-64-v_.so -> x86-64-v_ | |
| key="${fname#forkrun_ring.}" | |
| key="${key%.so}" | |
| # Normalize keys to underscores (x86_64_v3) | |
| # to match bash variable safety conventions if desired, | |
| # matching your local script logic. | |
| key="${key//-/_}" | |
| [[ "$key" == "native" ]] && key="native" | |
| echo "Encoding $key..." | |
| b64[${key}]="$(_forkrun_file_to_base64 "$f")" | |
| done | |
| # 3. Reconstruct | |
| { | |
| printf '%s\n%s' "$a0" "$a1" | |
| declare -p b64 | |
| printf '\n\n_forkrun_bootstrap_setup --force\n\n' | |
| } >./frun.new | |
| mv frun.new "${FR_BASH_PATH}" | |
| chmod +x "${FR_BASH_PATH}" | |
| \rm encoder.sh | |
| - name: Verify Final Script | |
| run: | | |
| # Sanity check | |
| ./frun.bash ring_version -a | |
| - name: Create Pull Request | |
| uses: peter-evans/create-pull-request@v6 | |
| with: | |
| token: ${{ secrets.GITHUB_TOKEN }} | |
| commit-message: "build: update embedded ring loadables" | |
| title: "🤖 Auto-Build: Update Ring Loadables" | |
| body: | | |
| This PR updates the embedded `forkrun_ring` binaries. | |
| Generated by GitHub Actions Run: [${{ github.run_id }}](https://github.com/${{ github.repository }}/actions/runs/${{ github.run_id }}) | |
| **Architectures:** | |
| - x86_64 (v2, v3, v4) | |
| - aarch64, ppc64le, s390x, riscv64 | |
| branch: "auto-build/update-loadables" | |
| delete-branch: true |