Skip to content

Commit

Permalink
zsh: add firejail completion
Browse files Browse the repository at this point in the history
  • Loading branch information
nrdxp committed Feb 13, 2021
1 parent 6d7d950 commit da69f34
Show file tree
Hide file tree
Showing 2 changed files with 249 additions and 1 deletion.
246 changes: 246 additions & 0 deletions profiles/develop/zsh/completions/_firejail
Original file line number Diff line number Diff line change
@@ -0,0 +1,246 @@
#compdef firejail

_all_firejails() {
local -a _all_firejails_list
for jail in ${(f)"$(_call_program modules_tag "firejail --list 2> /dev/null | cut -d: -f1")"}; do
_all_firejails_list+=${jail%% *}
done
_describe 'firejails list' _all_firejails_list
}

_all_cpus() {
_cpu_count=$(getconf _NPROCESSORS_ONLN)
for i in {0..$((_cpu_count-1))} ; do
print $i
done
}

_profiles() {
print $1/*.profile | sed -E "s;^$1/;;g;s;\.profile$;;g;"
}
_profiles_with_ext() {
print $1/*.profile
}

_all_profiles() {
_values 'profiles' $(_profiles _SYSCONFDIR_/firejail) $(_profiles $HOME/.config/firejail) $(_profiles_with_ext .)
}

_firejail_args=(
'*::arguments:_normal'
'(--profile)'{--profile=,--profile=}'[use a custom profile]: :_all_profiles'
'--caps[enable default Linux capabilities filter]'
'(--caps.drop)'{--caps.drop=,--caps.drop=}'[drop capabilities: all|cap1,cap2,...]: :->caps_drop'
'(--caps.keep)'{--caps.keep=,--caps.keep=}'[keep capabilities: cap1,cap2,...]: :->caps_keep'
'(--caps.print)'{--caps.print=,--caps.print=}'[print the caps filter name|pid]:firejail:_all_firejails'
'--allow-debuggers[allow tools such as strace and gdb inside the sandbox]'
'(--debug)'{--debug,--debug}'[print sandbox debug messages]'
'--debug-blacklists[debug blacklisting]'
'--debug-caps[print all recognized capabilities]'
'--debug-errnos[print all recognized error numbers]'
'--debug-private-lib[debug for --private-lib option]'
'--debug-protocols[print all recognized protocols]'
'--debug-syscalls[print all recognized system calls]'
'--debug-syscalls32[print all recognized 32 bit system calls]'
'--debug-whitelists[debug whitelisting]'
# Ignore that you can do -? too as it's the only short option
'(--help)'{--help,--help}'[this help screen]'
'--allusers[all user home directories are visible inside the sandbox]'
'--appimage[sandbox an AppImage application]'
'--private[temporary home directory]'
'(--private)'{--private=,--private=}'[use directory as user home]: : _files -/'
'--seccomp[enable seccomp filter and apply the default blacklist]'
'(--seccomp=)'{--seccomp=,--seccomp=}'[enable seccomp filter, blacklist the default syscall list and the syscalls specified by the command]:'
'(--seccomp.print)'{--seccomp.print=,--seccomp.print=}'[print the seccomp filter for the sandbox identified by name|pid]: : _all_firejails'
'--seccomp.block-secondary[build only the native architecture filters]'
'(--seccomp.drop)'{--seccomp.drop=,--seccomp.drop=}'[enable seccomp filter, and blacklist the syscalls specified by the command]: :'
'(--seccomp.keep)'{--seccomp.keep=,--seccomp.keep=}'[enable seccomp filter, and whitelist the syscalls specified by the command]: :'
'(--seccomp.32.drop)'{--seccomp.32.drop=,--seccomp.32.drop=}'[enable seccomp filter, and blacklist the 32 bit syscalls specified by the command]: :'
'(--seccomp.32.keep)'{--seccomp.32.keep=,--seccomp.32.keep=}'[enable seccomp filter, and whitelist the 32 bit syscalls specified by the command]: :'
'(--seccomp-error-action)'{--seccomp-error-action=,--seccomp-error-action=}'[change error code, kill process or log the attempt]: :(ERRNO kill log)'
'--memory-deny-write-execute[seccomp filter to block attempts to create memory mappings that are both writable and executable]'
'*'{--blacklist=,--blacklist=}'[blacklist directory or file]: : _files'
'--writable-etc[/etc directory is mounted read-write]'
'--writable-run-user[allow access to /run/user/$UID/systemd and /run/user/$UID/gnupg]'
'--writable-var[/var directory is mounted read-write]'
'--writable-var-log[use the real /var/log directory, not a clone]'
'--build[build a whitelisted profile for the application and print it on stdout]'
'(--build)'{--build=,--build=}'[build a whitelisted profile for the application and save it]: : _files'
'(--fs.print)'{--fs.print=,--fs.print=}'[print the filesystem log name|pid]: : _all_firejails'
'(--join)'{--join=,--join=}'[join the sandbox name|pid]: : _all_firejails'
'(--join-filesystem)'{--join-filesystem=,--join-filesystem=}'[join the mount namespace name|pid]: : _all_firejails'
'(--profile.print)'{--profile.print=,--profile.print=}'[print the name of profile file name|pid]: : _all_firejails'
'(--protocol.print)'{--protocol.print=,--protocol.print=}'[print the protocol filter name|pid]: : _all_firejails'
'(--shutdown)'{--shutdown=,--shutdown=}'[shutdown the sandbox identified by name|pid]: : _all_firejails'
'(--cat)'{--cat=,--cat=}'[print content of file from sandbox container name|pid]: : _all_firejails'
'(--cpu.print)'{--cpu.print=,--cpu.print=}'[print the cpus in use name|pid]: : _all_firejails'
'--list[list all sandboxes]'
'(--dns)'{--dns=,--dns=}'[set DNS server]: :'
'(--protocol)'{--protocol=,--protocol=}'[enable protocol filter]: :'
'(--join-or-start)'{--join-or-start=,--join-or-start=}'[join the sandbox or start a new one name|pid]: : _all_firejails'
'(--hosts-file)'{--hosts-file=,--hosts-file=}'[use file as /etc/hosts]: : _files'
'--shell=none[run the program directly without a user shell]'
'(--shell)'{--shell=,--shell=}'[set default user shell]: : _files -g "*(*)"'
'(--output)'{--output=,--output=}'[stdout logging and log rotation]: : _files'
'(--output-stderr)'{--output-stderr=,--output-stderr=}'[stdout and stderr logging and log rotation]: : _files'
'--no3d[disable 3D hardware acceleration]'
'--nodvd[disable DVD and audio CD devices]'
'--nogroups[disable supplementary groups]'
'--nonewprivs[sets the NO_NEW_PRIVS prctl]'
'--noprofile[do not use a security profile]'
'(--noexec)'{--noexec=,--noexec=}'[remount the file or directory noexec nosuid and nodev]: : _files'
'--ipc-namespace[enable a new IPC namespace]'
'--keep-dev-shm[/dev/shm directory is untouched (even with --private-dev)]'
'--keep-var-tmp[/var/tmp directory is untouched]'
'--top[monitor the most CPU-intensive sandboxes]'
'--trace[trace open, access and connect system calls]'
'--tracelog[add a syslog message for every access to files or directories blacklisted by the security profile]'
'--tree[print a tree of all sandboxed processes]'
'(--cpu)'{--cpu=,--cpu=}'[set cpu affinity]: :->cpus'
'--private-dev[create a new /dev directory with a small number of common device files]'
'--private-tmp[mount a tmpfs on top of /tmp directory]'
'--private-cwd[do not inherit working directory inside jail]'
'(--private-cwd)'{--private-cwd=,--private-cwd=}'[set working directory inside jail]: : _files -/'
'*'{--read-only=,--read-only=}'[set directory or file read-only]: : _files'
'*'{--read-write=,--read-write=}'[set directory or file read-write]: : _files'
'(--tmpfs)'{--tmpfs=,--tmpfs=}'[mount a tmpfs filesystem on directory dirname]: : _files -/'
'(--private-etc)'{--private-etc=,--private-etc=}'[build a new /etc in a temporary filesystem, and copy the files and directories in the list]: : _files'
"--deterministic-exit-code[always exit with first child's status code]"
'--machine-id[preserve /etc/machine-id]'
# Sample values as I don't think
# many would enjoy getting a list from -20..20
'(--nice)'{--nice=,--nice=}'[set nice value]: :(1 10 15 20)'
# Should be _files, a comma and files or files -/
'*'{--bind=,--bind=}'[mount-bind dirname1/filename1 on top of dirname2/filename2]: :(file1,file2 dir1,dir2)'
'--audit[audit the sandbox]'
'(--audit)'{--audit=,--audit=}'[audit the sandbox with a test-program]: :'
'(--cgroup)'{--cgroup=,--cgroup=}'[place the sandbox in the specified control group]: :'
'*'{--env=,--env=}'[set environment variable]: :'
'(--hostname)'{--hostname=,--hostname=}'[set sandbox hostname]: :'
'(--ignore)'{--ignore=,--ignore=}'[ignore command in profile files]: :'
'(--name)'{--name=,--name=}'[set sandbox name]: :'
'(--rlimit-as)'{--rlimit-as=,--rlimit-as=}"[set the maximum size of the process's virtual memory (address space) in bytes]: :"
'(--rlimit-cpu)'{--rlimit-cpu=,--rlimit-cpu=}'[set the maximum CPU time in seconds]: :'
'(--rlimit-fsize)'{--rlimit-fsize=,--rlimit-fsize=}'[set the maximum file size that can be created by a process]: :'
'(--rlimit-nofile)'{--rlimit-nofile=,--rlimit-nofile=}'[set the maximum number of files that can be opened by a process]: :'
'(--rlimit-nproc)'{--rlimit-nproc=,--rlimit-nproc=}'[set the maximum number of processes that can be created for the real user ID of the calling process]: :'
'(--rlimit-sigpending)'{--rlimit-sigpending=,--rlimit-sigpending=}'[set the maximum number of pending signals for a process]: :'
'*'{--rmenv=,--rmenv=}'[remove environment variable in the new sandbox]: :'
'(--timeout)'{--timeout=,--timeout=}'[kill the sandbox automatically after the time has elapsed]: :(hh\:mm\:ss)'
"--quiet[turn off Firejail's output.]"
'--version[print program version and exit]'
#ifdef HAVE_APPARMOR
'--apparmor[enable AppArmor confinement]'
'(--apparmor.print=)'{--apparmor.print=,--apparmor.print=}'[print apparmor status name|pid]:firejail:_all_firejails'
#endif
#ifdef HAVE_CHROOT
'(--chroot)'{--chroot=,--chroot=}'[chroot into directory]: : _files -/'
#endif
#ifdef HAVE_FILE_TRANSFER
'(--get)'{--get=,--get=}'[get a file from sandbox container name|pid]: : _all_firejails'
# --put=name|pid src-filename dest-filename - put a file in sandbox container.
'(--put)'{--put=,--put=}'[put a file in sandbox container]: :'
'(--ls)'{--ls=,--ls=}'[list files in sandbox container name|pid]: : _all_firejails'
#endif
#ifdef HAVE_NETWORK
# '--net=none[enable a new, unconnected network namespace]'
'(--net)'{--net=,--net=}'[enable network namespaces and connect to this bridge or Ethernet interface (or none to disable)]: :->net_or_none'
'(--net.print)'{--net.print=,--net.print=}'[print network interface configuration name|pid]: : _all_firejails'
'(--netfilter.print)'{--netfilter.print=,--netfilter.print=}'[print the firewall name|pid]: : _all_firejails'
'(--netfilter6.print)'{--netfilter6.print=,--netfilter6.print=}'[print the IPv6 firewall name|pid]: : _all_firejails'
'--netstats[monitor network statistics]'
'(--netmask)'{--netmask=,--netmask=}'[define a network mask when dealing with unconfigured parrent interfaces]: :'
'(--netns)'{--netns=,--netns=}'[Run the program in a named, persistent network namespace]: :'
'(--netfilter)'{--netfilter=,--netfilter=}'[enable firewall]: :'
'(--netfilter6)'{--netfilter6=,--netfilter6=}'[enable IPv6 firewall]: :'
'(--veth-name)'{--veth-name=,--veth-name=}'[use this name for the interface connected to the bridge]: :'
'(--join-network)'{--join-network=,--join-network=}'[join the network namespace name|pid]: : _all_firejails'
'(--defaultgw)'{--defaultgw=,--defaultgw=}'[configure default gateway]: :'
'(--ip)'{--ip=,--ip=}'[set interface IP address none|dhcp|ADDRESS]: :(none dhcp)'
'(--dns.print)'{--dns.print=,--dns.print=}'[print DNS configuration name|pid]: : _all_firejails'
'(--interface)'{--interface=,--interface=}'[move interface in sandbox]: :'
'(--ip6)'{--ip6=,--ip6=}'[set interface IPv6 address or use dhcp via dhclient]: :(dhcp)'
'(--iprange)'{--iprange=,--iprange=}'[configure an IP address in this range]: :'
'(--mac)'{--mac=,--mac=}'[set interface MAC address]: :(xx\:xx\:xx\:xx\:xx\:xx)'
'(--mtu)'{--mtu=,--mtu=}'[set interface MTU]: :'
'--scan[ARP-scan all the networks from inside a network namespace]'
'(--bandwidth)'{--bandwidth=,--bandwidth=}'[set bandwidth limits name|pid]: : _all_firejails'
#endif
#ifdef HAVE_X11
'--x11[enable X11 sandboxing. The software checks first if Xpra is installed, then it checks if Xephyr is installed. If all fails, it will attempt to use X11 security extension]'
'(--x11)'{--x11=,--x11=}'[disable or enable specific X11 server]: :(none xephyr xorg xpra xvfb)'
'(--xephyr-screen)'{--xephyr-screen=,--xephyr-screen=}'[set screen size for --x11=xephyr]: :(WIDTHxHEIGHT)'
#endif
#ifdef HAVE_USERNS
'--noroot[install a user namespace with only the current user]'
#endif
'--nosound[disable sound system]'
'--noautopulse[disable automatic ~/.config/pulse init]'
'--novideo[disable video devices]'
'--nou2f[disable U2F devices]'
#ifdef HAVE_OVERLAYFS
'--overlay[mount a filesystem overlay on top of the current filesystem]'
'(--overlay-named)'{--overlay-named=,--overlay-named=}'[mount a filesystem overlay on top of the current filesystem, and store it in name directory]: : _files -/'
'--overlay-tmpfs[mount a temporary filesystem overlay on top of the current filesystem]'
'--overlay-clean[clean all overlays stored in $HOME/.firejail directory]'
#endif
#ifdef HAVE_WHITELIST
'(--nowhitelist)'{--nowhitelist=,--nowhitelist=}'[disable whitelist for file or directory]: : _files'
'*'{--whitelist=,--whitelist=}'[whitelist directory or file]: : _files'
#endif
'(--noblacklist)'{--noblacklist=,--noblacklist=}'[disable blacklist for file or directory]: : _files'
#ifdef HAVE_DBUSPROXY
'(--dbus-system)'{--dbus-system=,--dbus-system=}'[set system DBus access policy or none]: :'
'(--dbus-system.broadcast)'{--dbus-system.broadcast=,--dbus-system.broadcast=}'[allow signals on the system DBus according to rule]: :'
'(--dbus-system.call)'{--dbus-system.call=,--dbus-system.call=}'[allow calls on the system DBus according to rule]: :'
'(--dbus-system.own)'{--dbus-system.own=,--dbus-system.own=}'[allow ownership of name on the system DBus]: :'
'(--dbus-system.see)'{--dbus-system.see=,--dbus-system.see=}'[allow seeing name on the system DBus]: :'
'(--dbus-system.talk)'{--dbus-system.talk=,--dbus-system.talk=}'[allow talking to name on the system DBus]: :'
'(--dbus-user)'{--dbus-user=,--dbus-user=}'[set session DBus access policy or none]: :'
'(--dbus-user.broadcast)'{--dbus-user.broadcast=,--dbus-user.broadcast=}'[allow signals on the session DBus according to rule]: :'
'(--dbus-user.call)'{--dbus-user.call=,--dbus-user.call=}'[allow calls on the session DBus according to rule]: :'
'(--dbus-user.see)'{--dbus-user.see=,--dbus-user.see=}'[allow seeing name on the session DBus]: :'
'(--dbus-user.talk)'{--dbus-user.talk=,--dbus-user.talk=}'[allow talking to name on the session DBus]: :'
'(--dbus-log)'{--dbus-log=,--dbus-log=}'[set DBus log file location]: : _files'
'(--dbus-system)'{--dbus-system=,--dbus-system=}'[set system DBus access policy]: :(filter none)'
'--dbus-user.log[turn on logging for the user DBus]'
'(--dbus-user.own)'{--dbus-user.own=,--dbus-user.own=}'[allow ownership of name on the session DBus]: :'
'--dbus-system.log[turn on logging for the system DBus]'
'--nodbus[disable D-Bus access]'
#endif
#ifdef HAVE_PRIVATE_HOME
'(--private-home)'{--private-home=,--private-home=}'[build a new user home in a temporary filesystem, and copy the files and directories in the list in the new home]: :'
#endif
'(--private-bin)'{--private-bin=,--private-bin=}'[build a new /bin in a temporary filesystem, and copy the programs in the list]: :'
'(--private-opt)'{--private-opt=,--private-opt=}'[build a new /opt in a temporary filesystem]: :'
'(--private-srv)'{--private-srv=,--private-srv=}'[build a new /srv in a temporary filesystem]: :'
#ifdef HAVE_USERTMPFS
'--private-cache[temporary ~/.cache directory]'
#endif
#ifdef HAVE_FIRETUNNEL
'(--tunnel)'{--tunnel=,--tunnel=}'[connect the sandbox to a tunnel created by firetunnel utility]: :'
#endif
)


_firejail() {
_arguments -S $_firejail_args
case "$state" in
caps_drop)
local caps_and_all=(all $(firejail --debug-caps | awk '/[0-9]+\s*- /{print $3}'))
_values -s "," 'caps_drop' $caps_and_all
;;
caps_keep)
local caps=($(firejail --debug-caps | awk '/[0-9]+\s*- /{print $3}'))
_values -s "," 'caps_keep' $caps
;;
cpus)
_values -s "," 'cpus' $(_all_cpus)
;;
net_or_none)
local netdevs=($(ip link | awk '{print $2}' | grep '^.*:$' | tr -d ':'))
local net_and_none=(none $netdevs)
_values 'net' $net_and_none
;;
esac
}
4 changes: 3 additions & 1 deletion profiles/develop/zsh/default.nix
Original file line number Diff line number Diff line change
Expand Up @@ -144,11 +144,13 @@ in
"${pkgs.any-nix-shell}/bin/any-nix-shell zsh --info-right | source /dev/stdin"
] ++ source);

localCompletions = toString ./completions;

in
''
${plugins}
fpath+=( ${functions} )
fpath+=( ${functions} ${localCompletions} )
autoload -Uz ${functions}/*(:t)
${zshrc}
Expand Down

0 comments on commit da69f34

Please sign in to comment.