mirror of
https://github.com/RsyncProject/rsync.git
synced 2026-10-31 10:08:29 -04:00
* Add IDN support rsync can now connect to IDN (internationalized domain name) hosts, and IDN names are recognized in a daemon's hosts allow/deny. * idn: convert host names label by label The IDNA mapping folds some non-ASCII characters onto ASCII ones, so running a whole hosts allow/deny token through idn2_to_ascii_8z() could hand back a pattern the admin never wrote: a "*" (U+FF0A FULLWIDTH ASTERISK) entry came back as "*" and let every host in. Convert label by label instead, keeping an ASCII label byte for byte and using a converted label only when it comes back as a bare A-label. An ASCII-only config now behaves as it did before there was IDN support, and a token that cannot be converted is left alone and so matches nothing. The client side shares the same helper, and neither side truncates a name at its 1024-byte buffer any more. strlower() folds only ASCII now, since its one caller is the hosts allow/deny list, which can hold UTF-8. Adds testsuite/daemon-access-idn and extends testsuite/idn to cover Unicode, punycode, mixed-case and invalid input on both sides. * idn: hand libidn2 the same flags on both sides The client path called idn2_lookup_ul() without IDN2_NFC_INPUT while the daemon path passed it to idn2_to_ascii_8z(). Both normalize either way -- idn2_lookup_ul() ors the flag in itself, and TR46 normalizes as it maps -- but there is no reason for the two calls to read differently, so pass one set of flags from one place. The flag asks libidn2 to normalize the label rather than promising that it already is: it gates the u32_normalize() call, and without it a decomposed label comes back IDN2_NOT_NFC. Adds composed/decomposed cases to testsuite/idn, which sees the exact host name rsync hands out, and a decomposed hosts allow token to testsuite/daemon-access-idn.
126 lines
4.7 KiB
YAML
126 lines
4.7 KiB
YAML
name: Build static rsync for Android
|
|
|
|
concurrency:
|
|
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.run_id }}
|
|
cancel-in-progress: true
|
|
|
|
# Cross-compiles statically-linked rsync binaries with the Android NDK,
|
|
# suitable for dropping onto a phone (adb push / Termux) with no shared
|
|
# libraries. arm64-v8a covers all modern phones; armeabi-v7a covers older
|
|
# 32-bit devices. The binaries are uploaded as workflow artifacts.
|
|
#
|
|
# These are cross-compiled, so the test suite can't run here; we sanity
|
|
# check that each binary is the right architecture, is static, and that
|
|
# it executes (`--version`) under qemu-user.
|
|
|
|
on:
|
|
push:
|
|
branches: [ master ]
|
|
paths-ignore:
|
|
- '.github/workflows/*.yml'
|
|
- '!.github/workflows/android-static-build.yml'
|
|
pull_request:
|
|
types: [opened, synchronize, reopened]
|
|
paths-ignore:
|
|
- '.github/workflows/*.yml'
|
|
- '!.github/workflows/android-static-build.yml'
|
|
schedule:
|
|
- cron: '42 8 * * 1'
|
|
workflow_dispatch:
|
|
|
|
env:
|
|
# Minimum supported API level. 24 (Android 7.0) runs on every modern
|
|
# phone while keeping broad reach; bump if you need newer Bionic APIs.
|
|
ANDROID_API: 24
|
|
|
|
jobs:
|
|
build:
|
|
runs-on: ubuntu-latest
|
|
name: ${{ matrix.abi }}
|
|
strategy:
|
|
fail-fast: false
|
|
matrix:
|
|
include:
|
|
- abi: arm64-v8a # modern phones
|
|
triple: aarch64-linux-android
|
|
qemu: qemu-aarch64-static
|
|
- abi: armeabi-v7a # older 32-bit phones
|
|
triple: armv7a-linux-androideabi
|
|
qemu: qemu-arm-static
|
|
steps:
|
|
- uses: actions/checkout@v4
|
|
with:
|
|
fetch-depth: 0
|
|
|
|
- name: Install build prerequisites
|
|
run: sudo apt-get update && sudo apt-get install -y autoconf automake gawk qemu-user-static
|
|
|
|
- name: Configure and build (${{ matrix.abi }})
|
|
shell: bash
|
|
run: |
|
|
set -euo pipefail
|
|
NDK="${ANDROID_NDK_LATEST_HOME:-$ANDROID_NDK_ROOT}"
|
|
TC="$NDK/toolchains/llvm/prebuilt/linux-x86_64/bin"
|
|
export CC="$TC/${{ matrix.triple }}${ANDROID_API}-clang"
|
|
export AR="$TC/llvm-ar" RANLIB="$TC/llvm-ranlib" STRIP="$TC/llvm-strip"
|
|
export CFLAGS="-O2" LDFLAGS="-static"
|
|
|
|
# Bionic doesn't declare lchmod()/lutimes() until API 36, but the
|
|
# symbols link, so configure mis-detects them -- force them off so
|
|
# rsync uses its fallbacks. The other cache vars restore values
|
|
# that configure can't probe when cross-compiling (Android runs a
|
|
# normal Linux kernel, so these match the native Linux result).
|
|
export ac_cv_func_lchmod=no ac_cv_func_lutimes=no \
|
|
rsync_cv_HAVE_SOCKETPAIR=yes \
|
|
rsync_cv_MKNOD_CREATES_FIFOS=yes \
|
|
rsync_cv_MKNOD_CREATES_SOCKETS=yes
|
|
|
|
# Self-contained build: drop optional external libraries so the
|
|
# static binary needs nothing at runtime. rsync keeps md5/md4
|
|
# checksums and its bundled zlib.
|
|
./configure --host=${{ matrix.triple }} --build=x86_64-pc-linux-gnu \
|
|
--enable-ipv6 \
|
|
--disable-zstd --disable-lz4 --disable-xxhash --disable-openssl --disable-idn \
|
|
--disable-iconv --disable-iconv-open \
|
|
--disable-acl-support --disable-xattr-support \
|
|
--disable-md2man --disable-roll-simd \
|
|
--with-included-popt --with-included-zlib
|
|
|
|
# Generate the awk-built headers serially first so the parallel
|
|
# build can't race on proto.h <- daemon-parm.h.
|
|
make proto.h
|
|
make -j"$(nproc)" rsync
|
|
"$STRIP" rsync
|
|
|
|
- name: Verify binary
|
|
shell: bash
|
|
run: |
|
|
set -euo pipefail
|
|
file rsync
|
|
# Gate: must be a statically-linked executable (no interpreter).
|
|
file rsync | grep -q "statically linked"
|
|
if file rsync | grep -q "dynamically linked"; then
|
|
echo "ERROR: binary is not static" >&2; exit 1
|
|
fi
|
|
# Best-effort: confirm it actually runs under qemu-user.
|
|
${{ matrix.qemu }} ./rsync --version | head -3 || \
|
|
echo "WARNING: qemu smoke test did not run cleanly (check on a real device)"
|
|
|
|
- name: Package
|
|
shell: bash
|
|
run: |
|
|
set -euo pipefail
|
|
VER=$(sed -n 's/.*RSYNC_VERSION "\([^"]*\)".*/\1/p' version.h)
|
|
out="rsync-${VER}-android-${{ matrix.abi }}"
|
|
mkdir -p dist
|
|
cp rsync "dist/$out"
|
|
( cd dist && sha256sum "$out" > "$out.sha256" )
|
|
echo "ARTIFACT_NAME=rsync-android-${{ matrix.abi }}" >>"$GITHUB_ENV"
|
|
|
|
- name: Upload artifact
|
|
uses: actions/upload-artifact@v4
|
|
with:
|
|
retention-days: 45
|
|
name: ${{ env.ARTIFACT_NAME }}
|
|
path: dist/
|