Skip to content

Build Custom Frida

Build Custom Frida #7

Workflow file for this run

name: Build Custom Frida
on:
workflow_dispatch:
inputs:
frida_version:
description: 'Frida version (e.g. 17.7.2)'
required: true
default: '17.7.2'
custom_name:
description: 'Custom name (replaces "frida" everywhere)'
required: true
default: 'ajeossida'
arch:
description: 'Target architecture(s)'
required: true
default: 'android-arm64'
type: choice
options:
- android-arm64
- android-arm
- android-arm64,android-arm
- android-arm64,android-arm,android-x86_64,android-x86
port:
description: 'Custom port (empty = keep 27042)'
required: false
default: ''
extended:
description: 'Extended anti-detection (D-Bus, symbols, binary sweep)'
required: false
type: boolean
default: true
temp_fixes:
description: 'Stability fixes (perfetto skip, cloak detach)'
required: false
type: boolean
default: false
jobs:
build:
runs-on: ubuntu-22.04
timeout-minutes: 120
steps:
- name: Checkout
uses: actions/checkout@v4
- name: System info
run: |
echo "CPUs: $(nproc)"
echo "RAM: $(free -h | grep Mem | awk '{print $2}')"
echo "Disk: $(df -h / | tail -1 | awk '{print $4}') free"
python3 --version
git --version
- name: Install dependencies
run: |
sudo apt-get update
sudo apt-get install -y build-essential curl git python3 unzip
# Cache NDK (~1.5 GB) — saves ~3 min on subsequent runs
- name: Cache NDK
uses: actions/cache@v4
id: ndk-cache
with:
path: build/android-ndk-r29
key: ndk-r29-linux
- name: Download NDK
if: steps.ndk-cache.outputs.cache-hit != 'true'
run: |
mkdir -p build
curl -L -o build/android-ndk-r29-linux.zip \
https://dl.google.com/android/repository/android-ndk-r29-linux.zip
cd build && unzip -q android-ndk-r29-linux.zip && rm android-ndk-r29-linux.zip
# Cache Frida source tree — saves ~5 min clone time
- name: Cache Frida source
uses: actions/cache@v4
id: frida-cache
with:
path: build/frida
key: frida-${{ inputs.frida_version }}-source
- name: Clone Frida
if: steps.frida-cache.outputs.cache-hit != 'true'
run: |
git clone --recurse-submodules --branch ${{ inputs.frida_version }} --depth 1 \
https://github.com/frida/frida.git build/frida
# If cache hit, we need a fresh copy (patches are destructive)
- name: Prepare fresh source from cache
if: steps.frida-cache.outputs.cache-hit == 'true'
run: |
# Restore to clean state (including build dir — patches are destructive)
cd build/frida
git checkout -- .
git submodule foreach --recursive 'git checkout -- . || true'
git clean -fdx || true
rm -rf build/
- name: Build command
id: cmd
run: |
CMD="python3 build.py --version ${{ inputs.frida_version }}"
CMD="$CMD --name ${{ inputs.custom_name }}"
CMD="$CMD --arch ${{ inputs.arch }}"
CMD="$CMD --skip-clone --ndk-path build/android-ndk-r29"
CMD="$CMD --verify"
if [ -n "${{ inputs.port }}" ]; then
CMD="$CMD --port ${{ inputs.port }}"
fi
if [ "${{ inputs.extended }}" = "true" ]; then
CMD="$CMD --extended"
fi
if [ "${{ inputs.temp_fixes }}" = "true" ]; then
CMD="$CMD --temp-fixes"
fi
echo "cmd=$CMD" >> $GITHUB_OUTPUT
echo "Will run: $CMD"
- name: Apply patches and build
run: ${{ steps.cmd.outputs.cmd }}
- name: List artifacts
run: |
echo "=== Build artifacts ==="
ls -lh output/
echo ""
echo "=== Binary verification ==="
for f in output/*; do
if [[ ! "$f" == *.gz ]]; then
count=$(strings "$f" | grep -c "frida" || true)
echo "$f: $count residual 'frida' strings"
fi
done
- name: Upload server artifacts
uses: actions/upload-artifact@v4
with:
name: ${{ inputs.custom_name }}-server-${{ inputs.frida_version }}
path: output/${{ inputs.custom_name }}-server-*.gz
retention-days: 30
if-no-files-found: warn
- name: Upload gadget artifacts
uses: actions/upload-artifact@v4
with:
name: ${{ inputs.custom_name }}-gadget-${{ inputs.frida_version }}
path: output/${{ inputs.custom_name }}-gadget-*.gz
retention-days: 30
if-no-files-found: ignore
- name: Upload uncompressed binaries
uses: actions/upload-artifact@v4
with:
name: ${{ inputs.custom_name }}-${{ inputs.frida_version }}-uncompressed
path: |
output/*
!output/*.gz
retention-days: 7