System-wide sandboxing framework - sandbox-app-launcher

What is the difference between this sandbox and the sandbox in Flatpak or Snaps?

Flatpak and Snap don’t provide meaningful sandboxes. They fully trust the apps and allow them to specify their own policy. The security is optional and apps can just choose not to be sufficiently sandboxed.

Flatpak is especially bad since its permissions are far too vague. One example is the fact that many apps come with the filesystem=home permission which is read-write access to the user’s entire home directory, giving access to all of your personal files and allowing trivial escapes via writing to ~/.bashrc or similar. Another example would be the lack of any restrictions over /sys or /proc (kernel interfaces known for info leaks). etc.

Snap at least has the potential for the policy to be more restrictive but I highly doubt it’s used properly and again, the app decides it.

With sandbox-app-launcher, there is 1 restrictive policy for all apps and the user can control a few important permissions per app.

1 Like

Pipewire is supposed to be a security conscious successor for Pulseaudio that places restrictions on access. While it was written for Flatpak I don’t see any reason why we couldn’t take advantage of it:

1 Like

RebeccaBlackOS is a Debian based distro for prototyping all Wayland supporting DEs and window managers. Let’s see if there’s anything on there that is available in Debian and that can be used in XFCE (or maybe in its place if this is important enough).

2 Likes
1 Like

There is 1 issue with this though and that’s that we need unprivileged user namespaces enabled for it to work. bubblewrap sets the no_new_privs flag which prevents executing setuid binaries (which Firefox/Chromium fallback to when there are no user namespaces). So, we need to set the kernel.unprivileged_userns_clone=1 sysctl for sandbox-app-launcher to work with the Firefox/Chromium sandbox.

Chromium fails with an error when starting it without user namespaces:

The setuid sandbox is not running as root. Common causes:
  * An unprivileged process using ptrace on it, like a debugger.
  * A parent process set prctl(PR_SET_NO_NEW_PRIVS, ...)
Failed to move to new namespace: PID namespaces supported, Network namespace supported, but failed: errno = Operation not permitted
[9:9:0528/021452.679452:FATAL:zygote_host_impl_linux.cc(186)] Check failed: ReceiveFixedMessage(fds[0], kZygoteBootMessage, sizeof(kZygoteBootMessage), &boot_pid).

Firefox however goes on fine while the sandbox silently fails and it pretends that it’s active.

I don’t know how to workaround this other than setting the sysctl above (which exposes tons of kernel attack surface so it’s not a good solution at all).

2 Likes

I read that programs like lxc and docker depend on kernel.unprivileged_userns_clone and apparently browser sandboxes too despite the enrmous security risks this opens. One can intercept and emulate system calls with ptrace, but this opens up another can of worms.

This seems like a showstopper.

2 Likes

They do if you’re running them as an unprivileged user but you can just create the container as root then drop privileges.

Browser sandboxes fallback to a setuid binary if user namespaces aren’t available but sandbox-app-launcher breaks that fallback.

I don’t think that’s a viable approach.

2 Likes
1 Like
1 Like

Killing sandbox-app-launcher from the terminal with Ctrl + C doesn’t kill the apps started in it. Should we add something like this to fix it?

exit_handler() {
  ## Don't leave any left-over processes.
  killall -9 -u "${app_user}"
  exit
}

trap "exit_handler" INT

We can replace sandbox-app-launcher/sandbox-app-launcher at 8ee5d5b43eaa785fb48547d07eade48196aaaeab · Kicksecure/sandbox-app-launcher · GitHub with exit_handler.

1 Like

It’s an option but perhaps there’s a better solution. kill -9 doesn’t let the application shutdown gracefully. Data loss might happen. Would be better to ask to shutdown gracefully (sigterm) first and then after timeout forcefully kill (sigkill). Also doesn’t handle other signals. Gets quite complex to implement.

Could you try try replace please sudo with exec sudo. Then sandbox-app-launcher would be gone. It doesn’t need to do anything after application exited. The executed application would become tty controlling application and process signals (sigterm / ctrl + c; etc.) as if it was started directly.

Quote:

exec is a builtin command of the Bash shell. It allows you to execute a command that completely replaces the current process. The current shell process is destroyed, and entirely replaced by the command you specify.

Or do you suppose a feature for sandbox-app-launcher which helps with termination and enforces application is really gone?

1 Like

That didn’t change anything.

I want the applications to die when sandbox-app-launcher does. It’s annoying having tons of left-over processes.

I just remembered bubblewrap has a --die-with-parent flag which does this. When bubblewrap’s parent (sandbox-app-launcher) dies, it kills everything in the sandbox although it does this with sigkill rather than sigterm which may be problematic.

1 Like
1 Like

I think it’d be good to simplify the seccomp filter and create a script that auto-creates the program to generate the filter.

I’ve started working on this.

Script: Debian paste error

New whitelist: Debian paste error

To filter arguments, you need to specify the argument number (currently only 0-2 but that’s trivially expanded) then the actual argument, e.g.:

socket 0 AF_INET

The whitelist will now be much easier to fix, audit, expand, etc.

What do you think?

1 Like
1 Like
1 Like

So it should be debian/sandbox-app-launcher.postrm containing this?

#!/bin/bash

## Copyright (C) 2012 - 2020 ENCRYPTED SUPPORT LP <adrelanos@riseup.net>
## See the file COPYING for copying conditions.

if [ -f /usr/lib/helper-scripts/pre.bsh ]; then
   source /usr/lib/helper-scripts/pre.bsh
fi

set -e

true "
#####################################################################
## INFO: BEGIN: $DPKG_MAINTSCRIPT_PACKAGE $DPKG_MAINTSCRIPT_NAME $@
#####################################################################
"

rm -rf /var/cache/sandbox-app-launcher-autogenerated /etc/sandbox-app-launcher
for user in "$(getent passwd | grep "sandbox-" | sed -e 's/:.*//g')"
do
  userdel "${user}"
done

true "INFO: debhelper beginning here."

#DEBHELPER#

true "INFO: Done with debhelper."

true "
#####################################################################
## INFO: END  : $DPKG_MAINTSCRIPT_PACKAGE $DPKG_MAINTSCRIPT_NAME $@
#####################################################################
"

## Explicitly "exit 0", so eventually trapped errors can be ignored.
exit 0

This would remove everything except app data.

1 Like

Started working on the permissions prompt: Debian paste error

It supports GUI and CLI.

We still need to figure out how to actually start it though. I think we should create /etc/apt/apt.conf.d/50sandbox-app-launcher with something like:

DPkg::Post-Invoke {"/usr/share/sandbox-app-launcher/setup-permissions "${app}"";};

But I don’t know how we’d get ${app}.

We also need to implement stackable wrappers first.

1 Like

The seccomp stuff makes what once was a simple script now kinda complex. What’s the worst case if there are bugs in the seccomp or apparmor? “Only” that sandbox is weaker? That wouldn’t be catastrophic to effectively run with brap alone. Or anything worse?

  ## Needed for apps to setup further sandboxing like Firefox/Chromium.
  capability sys_admin,
  capability sys_chroot,
  capability sys_ptrace,

Maybe this could be a separate apparmor abstraction only to be included for wx?

sed -e ‘s/:.*//g’

Can you port to str_replace please?

Yes, but str_replace please.


usr/bin/sandbox-app-launcher:    mv "${auto_dir}/seccomp-filter.c" "${auto_dir}/seccomp.c"
usr/bin/sandbox-app-launcher:    mv "${auto_dir}/seccomp-filter.c" "${auto_dir}/seccomp-wx.c"

How’s ${auto_dir}/seccomp-filter.c created?

That is a bit difficult to follow in the code flow.

cat < “${seccomp_filter_path}.c”

Perhaps add some comments?

syntax of autogen-seccomp should be

autogen-seccomp path/to/seccomp-whitelist path/to/output-file

?

Or have autogen-seccomp echo to stdout and then redirect (>) to file?


"${auto_dir}/seccomp"
"${auto_dir}/seccomp-wx"

Why does it get executed? Also seems to compile and execute both every time? Could use a comment.

Please do not add /etc/sandbox-app-launcher as that’s the task for apt purge.

Yes, good for testing/cleanup purposes.

It is good to have the prompt separated from actual potential future apt integration.

When run by apt, most likely apt won’t “know” that X is running. After sudo, environment variables are scrubbed. And when apt runs dpkg, environment variables might be scrubbed again. (Unless running apt with sudo var=content apt ....)

By looking at /usr/share/applications/*.desktop files perhaps?

But covers “mostly” graphical applications.
There is also some “other” stuff there.
(example /usr/share/applications/okularApplication_fax.desktop)
That wouldn’t cover any CLI applications worth covering.

  • mechanism in config enable/disabled yes/no
  • already has sandbox config yes/no
  • desktop files that should get a corresponding sandbox config yes/no

But that could easily end in usability disaster.

  • Install application A which pulls application B as a dependency and then lots of sandbox config popups.
  • If messing up config application, how users know how to change settings for that application? (start config gui again)
    • Perhaps some apt hook should ensure that if an application is apt purgeed, it’s corresponding sandbox config is wiped too?

Yes, that is blocking many things.

1 Like