Skip to content

Commit b92d525

Browse files
authored
add options to allow FUSE and nested capabilities, improve usage with runimage (#28)
1 parent 4626b63 commit b92d525

File tree

3 files changed

+70
-35
lines changed

3 files changed

+70
-35
lines changed

.github/workflows/appimage.yml

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -31,16 +31,18 @@ jobs:
3131
UPINFO="gh-releases-zsync|$(echo $GITHUB_REPOSITORY | tr '/' '|')|latest|*$ARCH.AppImage.zsync"
3232
3333
BWRAP_URL="https://pkgs.pkgforge.dev/dl/bincache/$ARCH-linux/bubblewrap/official/bwrap/raw.dl"
34+
BWRAP_PATCHED_URL="https://pkgs.pkgforge.dev/dl/bincache/x86_64-linux/bubblewrap/patched/bwrap/raw.dl"
3435
AWK_URL="https://pkgs.pkgforge.dev/dl/bincache/$ARCH-linux/mawk/mawk/raw.dl"
3536
SQUASHFUSE_URL="https://pkgs.pkgforge.dev/dl/bincache/$ARCH-linux/squashfuse/nixpkgs/squashfuse/raw.dl"
3637
3738
mkdir -p ./AppDir/bin
3839
cp -v ./sas.sh ./AppDir/AppRun
3940
cd ./AppDir
4041
41-
wget --retry-connrefused --tries=30 "$AWK_URL" -O ./bin/awk
42-
wget --retry-connrefused --tries=30 "$BWRAP_URL" -O ./bin/bwrap
43-
wget --retry-connrefused --tries=30 "$SQUASHFUSE_URL" -O ./bin/squashfuse
42+
wget --retry-connrefused --tries=30 "$AWK_URL" -O ./bin/awk
43+
wget --retry-connrefused --tries=30 "$BWRAP_URL" -O ./bin/bwrap
44+
wget --retry-connrefused --tries=30 "$BWRAP_PATCHED_URL" -O ./bin/bwrap.patched
45+
wget --retry-connrefused --tries=30 "$SQUASHFUSE_URL" -O ./bin/squashfuse
4446
4547
chmod +x ./AppRun ./bin/*
4648

README.md

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,12 +11,12 @@ Supports DwarFS and SquashFS filesystems.
1111

1212
# Usage
1313

14-
`./sas.sh [OPTIONS] /path/to/app`
14+
`./sas.AppImage [OPTIONS] /path/to/app`
1515

1616
Example:
1717

1818
```
19-
./sas.sh --rm-socket network --add-dir ~/"My randomdir" --add-dir xdg-download:rw ./My-random.AppImage
19+
./sas.AppImage --rm-socket network --add-dir ~/"My randomdir" --add-dir xdg-download:rw ./My-random.AppImage
2020
```
2121

2222
Options:
@@ -30,6 +30,10 @@ Options:
3030

3131
* `--add-dir`, `--add-file` directory/file to give read access to. In order to add write access add `:rw` to the file, example `--add-dir /media/drive:rw`.
3232

33+
* `--allow-fuse` Enables using FUSE inside the sandbox, only recommended for apps like Steam that need to launch other big AppImages, when this option is NOT used `APPIMAGE_EXTRACT_AND_RUN=1` is set inside the sandbox so that AppImages can still work, albeit less efficiently.
34+
35+
* `--allow-nested-caps` Using this option will switch the `bwrap` in the AppImage builds of `sas` to a [patched](https://github.com/VHSgunzo/bubblewrap-static/blob/main/bwrap.patch) bubblewrap that allows nested bwrap sessions.
36+
3337
* `--no-config` Don't use existing configuration files, by default we try to give access to a directory matching the name of the given application in the following locations:
3438

3539
```
@@ -43,6 +47,7 @@ XDG_DATA_HOME
4347
```
4448
$XDG_DATA_HOME/icons
4549
$XDG_DATA_HOME/themes
50+
$XDG_DATA_HOME/fonts
4651
$XDG_CONFIG_HOME/dconf
4752
$XDG_CONFIG_HOME/fontconfig
4853
$XDG_CONFIG_HOME/gtk-3.0

sas.sh

100644100755
Lines changed: 58 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,10 @@ if [ "$SAS_DEBUG" = 1 ]; then
1212
set -x
1313
fi
1414

15-
VERSION=1.0
15+
VERSION=1.1
1616

1717
ADD_DIR=""
18+
ALLOW_FUSE=0
1819
ALLOW_BINDIR=0
1920
ALLOW_DATADIR=0
2021
ALLOW_CONFIGDIR=0
@@ -32,6 +33,8 @@ ALLOW_PUBLICSHAREDIR=0
3233
ALLOW_TEMPLATESDIR=0
3334
ALLOW_VIDEOSDIR=0
3435

36+
BWRAPCMD="bwrap"
37+
3538
SHARE_APP_CONFIG=1
3639
SHARE_APP_THEME=1
3740
SHARE_APP_NETWORK=1
@@ -134,6 +137,7 @@ _get_sys_info() {
134137
case "$1" in
135138
home) i=6 ;;
136139
id) i=3 ;;
140+
gid) i=4 ;;
137141
''|*) exit 1;;
138142
esac
139143
awk -F':' -v U="$USER" -v F="$i" '$1==U {print $F; exit}' /etc/passwd
@@ -245,7 +249,8 @@ _is_spooky() {
245249
}
246250

247251
_is_appimage() {
248-
if [ "$SAS_SANDBOX" = 1 ]; then
252+
# do not check if in nested sandbox or allowing fuse
253+
if [ "$SAS_SANDBOX" = 1 ] || [ "$ALLOW_FUSE" = 1 ]; then
249254
return 1
250255
fi
251256

@@ -254,7 +259,7 @@ _is_appimage() {
254259
*ELF*RI|\
255260
*ELF*AB) IS_APPIMAGE=1;;
256261
''|*) return 1 ;;
257-
esac
262+
esac 2>/dev/null
258263
}
259264

260265
_check_xdgbase() {
@@ -305,7 +310,7 @@ _make_fakehome() {
305310
FAKEHOME="$(dirname "$TARGET")/$APPNAME.home"
306311
fi
307312

308-
mkdir -p "$FAKEHOME" 2>/dev/null || true
313+
mkdir -p "$FAKEHOME"/.app 2>/dev/null || true
309314

310315
if ! _is_spooky "$FAKEHOME"; then
311316
_error "Cannot use $1 as sandboxed home"
@@ -382,36 +387,43 @@ _make_mountpoint() {
382387
mkdir -p "$MOUNT_POINT"
383388
fi
384389

385-
( squashfuse -o offset="$offset" "$TARGET" "$MOUNT_POINT" 2>/dev/null \
386-
|| dwarfs -o offset="$offset" "$TARGET" "$MOUNT_POINT" ) &
390+
# common flags for squashfuse and dwarfs
391+
set -- \
392+
-o ro,nodev,uid="$ID",gid="$GID" \
393+
-o offset="$offset" "$TARGET" "$MOUNT_POINT"
394+
( squashfuse "$@" 2>/dev/null || dwarfs "$@" ) &
387395
mountcheck=$!
388396
}
389397

390398
_make_bwrap_array() {
391399
set -u
392400
set -- \
393-
--dir /app \
394-
--perms 0700 \
395-
--dir /run/user/"$ID" \
396-
--bind "$FAKEHOME" "$HOME" \
397-
--dev /dev \
398-
--proc /proc \
399-
--unshare-user-try \
400-
--unshare-pid \
401-
--unshare-uts \
402-
--die-with-parent \
403-
--unshare-cgroup-try \
404-
--new-session \
405-
--unshare-ipc \
406-
--setenv TMPDIR /tmp \
407-
--setenv HOME "$HOME" \
408-
--ro-bind "$TARGET" /app/"$APPNAME" \
401+
--dir /app \
402+
--perms 0700 \
403+
--dir /run/user/"$ID" \
404+
--bind "$FAKEHOME" "$HOME" \
405+
--bind "$FAKEHOME"/.app /app \
406+
--ro-bind "$TARGET" /app/"$APPNAME" \
407+
--proc /proc \
408+
--unshare-user-try \
409+
--unshare-pid \
410+
--unshare-uts \
411+
--die-with-parent \
412+
--unshare-cgroup-try \
413+
--new-session \
414+
--unshare-ipc \
415+
--setenv SAS_SANDBOX 1 \
416+
--setenv TMPDIR /tmp \
417+
--setenv HOME "$HOME" \
409418
--setenv XDG_RUNTIME_DIR /run/user/"$ID"
410419

411-
# TODO, add an option to allow FUSE in bwrap
412-
set -- "$@" \
413-
--setenv SAS_SANDBOX 1 \
414-
--setenv APPIMAGE_EXTRACT_AND_RUN 1
420+
if [ "$ALLOW_FUSE" = 1 ]; then
421+
# CAP_SYS_ADMIN needed when allowing FUSE inside sandbox
422+
set -- "$@" --cap-add CAP_SYS_ADMIN
423+
else
424+
# lets appimages run inside container without FUSE
425+
set -- "$@" --setenv APPIMAGE_EXTRACT_AND_RUN 1
426+
fi
415427

416428
for d in $DEFAULT_SYS_DIRS; do
417429
if [ -d "$d" ]; then
@@ -423,15 +435,17 @@ _make_bwrap_array() {
423435
SHARE_DEV_DRI=1
424436
SHARE_DEV_INPUT=1
425437
set -- "$@" --dev-bind-try /dev /dev
438+
else
439+
set -- "$@" --dev /dev
426440
fi
427441
if [ "$SHARE_DEV_DRI" = 1 ]; then
428442
set -- "$@" \
429443
--ro-bind-try /usr/share/glvnd /usr/share/glvnd \
430444
--ro-bind-try /usr/share/vulkan /usr/share/vulkan \
445+
--ro-bind-try /sys/dev/char /sys/dev/char \
431446
--dev-bind-try /dev/nvidiactl /dev/nvidiactl \
432447
--dev-bind-try /dev/nvidia0 /dev/nvidia0 \
433448
--dev-bind-try /dev/nvidia-modeset /dev/nvidia-modeset \
434-
--ro-bind-try /sys/dev/char /sys/dev/char \
435449
--ro-bind-try /sys/devices/pci0000:00 /sys/devices/pci0000:00
436450
fi
437451
if [ "$SHARE_DEV_INPUT" = 1 ]; then
@@ -536,15 +550,17 @@ USER="${LOGNAME:-${USER:-${USERNAME}}}"
536550
if [ -f '/etc/passwd' ]; then
537551
SAS_HOME="$(_get_sys_info home)"
538552
SAS_ID="$(_get_sys_info id)"
553+
SAS_GID="$(_get_sys_info gid)"
539554
# export internal variables this way apps with
540555
# restricted access to /etc can still use this
541-
export SAS_HOME SAS_ID
556+
export SAS_HOME SAS_ID SAS_GID
542557
fi
543558

544559
HOME="$SAS_HOME"
545560
ID="$SAS_ID"
561+
GID="$SAS_GID"
546562

547-
if [ -z "$USER" ] || [ ! -d "$HOME" ] || [ -z "$ID" ]; then
563+
if [ -z "$USER" ] || [ ! -d "$HOME" ] || [ -z "$ID" ] || [ -z "$GID" ]; then
548564
_error "This system is fucked up"
549565
fi
550566

@@ -620,6 +636,18 @@ while :; do
620636
SHARE_APP_TMPDIR=0
621637
shift
622638
;;
639+
--allow-fuse)
640+
ALLOW_FUSE=1
641+
shift
642+
;;
643+
--allow-nested-caps)
644+
if command -v bwrap.patched 1>/dev/null; then
645+
BWRAPCMD="bwrap.patched"
646+
else
647+
_error "Missing patched bwrap needed for $1"
648+
fi
649+
shift
650+
;;
623651
--keep-mount|--preload)
624652
SAS_PRELOAD=1
625653
shift
@@ -818,4 +846,4 @@ if [ ! -x "$TARGET" ] && [ "$IS_TRUSTED_ONCE" = 1 ]; then
818846
fi
819847

820848
# Do the thing!
821-
bwrap "$@"
849+
"$BWRAPCMD" "$@"

0 commit comments

Comments
 (0)