Two independent failure modes can cause the restart loop on arm64:
1. /dev/stdout may be inaccessible in some ARM container runtimes; replaced
with /proc/1/fd/1 which LSIO images already use for direct container stdout.
2. s6-notifyoncheck writes to fd 3 on check success, but s6-rc only opens
that fd when notification-fd exists in the service directory. LSIO arm64
images ship svc-qbittorrent without it, so s6-notifyoncheck exits with
EBADF and s6 restarts the service in a loop. Guard with a file check and
fall back to exec'ing qbittorrent-nox directly when the file is absent.
https://claude.ai/code/session_01F16ThtZyfXj6ZKFPkrSAAq
/dev/stdout resolves via /proc/self/fd/1 and can be inaccessible in some
ARM container runtimes, causing the exec redirect to fail and s6 to restart
the service in a loop. /proc/1/fd/1 is the path LSIO images already use
for direct container stdout (see nginx silent-mode handling) and is reliable
across architectures.
https://claude.ai/code/session_01F16ThtZyfXj6ZKFPkrSAAq
s6-rc opens fd 3 for a longrun service only when a notification-fd file is
present in the service directory. The LSIO aarch64 image ships svc-qbittorrent
without that file, so fd 3 is never opened. s6-notifyoncheck exits with EBADF
after its readiness check passes, s6 treats the supervised process as dead and
immediately restarts it — producing the infinite "Starting qBittorrent..." loop.
Check for the notification-fd file at runtime: use the full s6-notifyoncheck
path when it is present (amd64, preserving existing behaviour), and fall back
to exec'ing qbittorrent-nox directly when it is absent (aarch64).
https://claude.ai/code/session_01F16ThtZyfXj6ZKFPkrSAAq
s6-notifyoncheck writes to fd 3 when its readiness check passes, but
the LSIO aarch64 image's svc-qbittorrent service has no notification-fd
file so s6-rc never opens fd 3. s6-notifyoncheck exits with EBADF, s6
sees the supervised process die and immediately restarts it, producing
the infinite "Starting qBittorrent..." loop seen on odroid-c2 and other
aarch64 boards.
Drop s6-notifyoncheck entirely and exec qbittorrent-nox directly under
s6-setuidgid so s6 supervises the real process. Silent mode is handled
by redirecting the shell's fds before exec rather than passing a
/dev/stdout path (avoids a separate class of ARM container fd issues).
https://claude.ai/code/session_01F16ThtZyfXj6ZKFPkrSAAq
2026-05-10 16:30:23 +00:00
6 changed files with 181 additions and 23 deletions
- Fix startup loop on aarch64: drop s6-notifyoncheck wrapper so s6 supervises qbittorrent-nox directly (LSIO arm64 image has no notification-fd, causing EBADF restart loop)
- Preserve custom port in `SEAFILE_SERVER_HOSTNAME` (e.g. `seafile.example.com:8443`)
- Fix `CSRF_TRUSTED_ORIGINS` to use scheme+host[:port] only (no URL path)
- Add validation: reject newlines and quote characters in URL config values
- Replace sed address-range approach for `seafile.conf` with idempotent `awk` edit so repeated runs never produce duplicate `host =` keys
- Harden `apply_addon_urls.sh` generation: baked-in values are written to a separate sourced file using `printf %q` and the script body uses a single-quoted heredoc, eliminating any shell-injection risk from malformed config values
## 12.0.18-5 (2026-05-11)
- Fix file uploads and downloads through a reverse proxy (e.g. Nginx Proxy Manager) by:
- Writing `SEAFILE_SERVER_HOSTNAME` and `SEAFILE_SERVER_PROTOCOL` to `seafile.env` so Seafile knows its external URL
- Setting `host = 0.0.0.0` in the `[fileserver]` section of `seafile.conf` so the fileserver binds to all interfaces
- Adding `CSRF_TRUSTED_ORIGINS` to `seahub_settings.py` to prevent Django CSRF rejections on HTTPS setups
- Making `FILE_SERVER_ROOT` optional (`str?`) so it can be left empty when the reverse proxy handles `/seafhttp` routing
## 12.0.18-4 (2026-05-10)
- Fix admin account creation by writing `conf/admin.txt` and seeding `seafile.env` with `SEAFILE_ADMIN_EMAIL`/`SEAFILE_ADMIN_PASSWORD` so the upstream `check_init_admin.py` no longer falls back to an interactive prompt (#2685)
for _SCONF in "${ADDON_DATA_LOCATION}/conf/seafile.conf" \
"${ADDON_DATA_LOCATION}/seafile/conf/seafile.conf"; do
if [ -f "$_SCONF" ]; then
_seafile_set_fileserver_host "$_SCONF"
fi
done
URLEOF
Reference in New Issue
Block a user
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.