lxc-test-apparmor-mount revision 3a5495cf2f6c1806f5a91d699448b15b510f146e
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte#!/bin/sh
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# apparmor_mount: test proper handling of apparmor in kernels
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# without mount features
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# These require the ubuntu lxc package to be installed.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# This program is free software; you can redistribute it and/or
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# modify it under the terms of the GNU Lesser General Public
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# License as published by the Free Software Foundation; either
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# version 2.1 of the License, or (at your option) any later version.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# This library is distributed in the hope that it will be useful,
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# but WITHOUT ANY WARRANTY; without even the implied warranty of
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# Lesser General Public License for more details.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# You should have received a copy of the GNU Lesser General Public
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# License along with this library; if not, write to the Free Software
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# This test assumes an Ubuntu host
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteset -e
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteif [ -f /proc/self/ns/cgroup ]; then
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte default_profile="lxc-container-default-cgns (enforce)"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteelse
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte default_profile="lxc-container-default (enforce)"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortefi
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn ForteFAIL() {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte echo -n "Failed " >&2
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte echo "$*" >&2
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte exit 1
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forterun_cmd() {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sudo -i -u $TUSER \
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte env http_proxy=${http_proxy:-} https_proxy=${https_proxy:-} \
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte XDG_RUNTIME_DIR=/run/user/$(id -u $TUSER) $*
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn ForteDONE=0
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn ForteKNOWN_RELEASES="precise trusty xenial yakkety zesty"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn ForteMOUNTSR=/sys/kernel/security/apparmor/features/mount
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortednam=`mktemp -d`
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortecname=`basename $dnam`
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortecleanup() {
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte run_cmd lxc-destroy -f -n $cname || true
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte umount -l $MOUNTSR || true
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte rmdir $dnam || true
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte pkill -u $(id -u $TUSER) -9
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sed -i '/lxcunpriv/d' /run/lxc/nics /etc/lxc/lxc-usernet
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte sed -i '/^lxcunpriv:/d' /etc/subuid /etc/subgid
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte rm -Rf $HDIR /run/user/$(id -u $TUSER)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte deluser $TUSER
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte if [ $DONE -eq 0 ]; then
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte echo "FAIL"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte exit 1
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte fi
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte echo "PASS"
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte}
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortetrap cleanup exit
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# Only run on a normally configured ubuntu lxc system
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteif [ ! -d /sys/class/net/lxcbr0 ]; then
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte echo "lxcbr0 is not configured."
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte exit 1
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortefi
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteif [ "$(id -u)" != "0" ]; then
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte echo "ERROR: Must run as root."
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte exit 1
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortefi
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# This would be much simpler if we could run it as
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# root. However, in order to not have the bind mount
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# of an empty directory over the securitfs 'mount' directory
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# be removed, we need to do this as non-root.
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortewhich newuidmap >/dev/null 2>&1 || { echo "'newuidmap' command is missing" >&2; exit 1; }
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte# create a test user
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn ForteTUSER=lxcunpriv
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn ForteHDIR=/home/$TUSER
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn ForteARCH=i386
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteif type dpkg >/dev/null 2>&1; then
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte ARCH=$(dpkg --print-architecture)
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortefi
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortedeluser $TUSER && rm -Rf $HDIR || true
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteuseradd $TUSER
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forte
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Fortemkdir -p $HDIR
fcf3ce441efd61da9bb2884968af01cb7c1452ccJohn Forteecho "$TUSER veth lxcbr0 2" >> /etc/lxc/lxc-usernet
sed -i '/^lxcunpriv:/d' /etc/subuid /etc/subgid
usermod -v 910000-919999 -w 910000-919999 $TUSER
mkdir -p $HDIR/.config/lxc/
cat > $HDIR/.config/lxc/default.conf << EOF
lxc.network.type = veth
lxc.network.link = lxcbr0
lxc.id_map = u 0 910000 9999
lxc.id_map = g 0 910000 9999
EOF
chown -R $TUSER: $HDIR
mkdir -p /run/user/$(id -u $TUSER)
chown -R $TUSER: /run/user/$(id -u $TUSER)
cd $HDIR
if which cgm >/dev/null 2>&1; then
cgm create all $TUSER
cgm chown all $TUSER $(id -u $TUSER) $(id -g $TUSER)
cgm movepid all $TUSER $$
elif [ -e /sys/fs/cgroup/cgmanager/sock ]; then
for d in $(cut -d : -f 2 /proc/self/cgroup); do
dbus-send --print-reply --address=unix:path=/sys/fs/cgroup/cgmanager/sock \
--type=method_call /org/linuxcontainers/cgmanager org.linuxcontainers.cgmanager0_0.Create \
string:$d string:$TUSER >/dev/null
dbus-send --print-reply --address=unix:path=/sys/fs/cgroup/cgmanager/sock \
--type=method_call /org/linuxcontainers/cgmanager org.linuxcontainers.cgmanager0_0.Chown \
string:$d string:$TUSER int32:$(id -u $TUSER) int32:$(id -g $TUSER) >/dev/null
dbus-send --print-reply --address=unix:path=/sys/fs/cgroup/cgmanager/sock \
--type=method_call /org/linuxcontainers/cgmanager org.linuxcontainers.cgmanager0_0.MovePid \
string:$d string:$TUSER int32:$$ >/dev/null
done
else
for d in /sys/fs/cgroup/*; do
[ -f $d/cgroup.clone_children ] && echo 1 > $d/cgroup.clone_children
[ ! -d $d/lxctest ] && mkdir $d/lxctest
chown -R $TUSER: $d/lxctest
echo $$ > $d/lxctest/tasks
done
fi
run_cmd mkdir -p $HDIR/.cache/lxc
[ -d /var/cache/lxc/download ] && \
cp -R /var/cache/lxc/download $HDIR/.cache/lxc && \
chown -R $TUSER: $HDIR/.cache/lxc
# default release is trusty, or the systems release if recognized
release=trusty
if [ -f /etc/lsb-release ]; then
. /etc/lsb-release
rels=$(ubuntu-distro-info --supported 2>/dev/null) ||
rels="$KNOWN_RELEASES"
for r in $rels; do
[ "$DISTRIB_CODENAME" = "$r" ] && release="$r"
done
fi
run_cmd lxc-create -t download -n $cname -- -d ubuntu -r $release -a $ARCH
echo "test default confined container"
run_cmd lxc-start -n $cname -d
run_cmd lxc-wait -n $cname -s RUNNING
pid=`run_cmd lxc-info -p -H -n $cname`
profile=`cat /proc/$pid/attr/current`
if [ "x$profile" != "x${default_profile}" ]; then
echo "FAIL: confined container was in profile $profile"
exit 1
fi
run_cmd lxc-stop -n $cname
echo "test regular unconfined container"
echo "lxc.aa_profile = unconfined" >> $HDIR/.local/share/lxc/$cname/config
run_cmd lxc-start -n $cname -d
run_cmd lxc-wait -n $cname -s RUNNING
pid=`run_cmd lxc-info -p -H -n $cname`
profile=`cat /proc/$pid/attr/current`
if [ "x$profile" != "xunconfined" ]; then
echo "FAIL: unconfined container was in profile $profile"
exit 1
fi
run_cmd lxc-stop -n $cname
echo "masking $MOUNTSR"
mount --bind $dnam $MOUNTSR
echo "test default confined container"
sed -i '/aa_profile/d' $HDIR/.local/share/lxc/$cname/config
run_cmd lxc-start -n $cname -d || true
sleep 3
pid=`run_cmd lxc-info -p -H -n $cname` || true
if [ -n "$pid" -a "$pid" != "-1" ]; then
echo "FAIL: confined container started without mount restrictions"
echo "pid was $pid"
exit 1
fi
echo "test regular unconfined container"
echo "lxc.aa_profile = unconfined" >> $HDIR/.local/share/lxc/$cname/config
run_cmd lxc-start -n $cname -d
run_cmd lxc-wait -n $cname -s RUNNING
pid=`run_cmd lxc-info -p -H -n $cname`
if [ "$pid" = "-1" ]; then
echo "FAIL: unconfined container failed to start without mount restrictions"
exit 1
fi
profile=`cat /proc/$pid/attr/current`
if [ "x$profile" != "xunconfined" ]; then
echo "FAIL: confined container was in profile $profile"
exit 1
fi
run_cmd lxc-stop -n $cname
echo "testing override"
sed -i '/aa_profile/d' $HDIR/.local/share/lxc/$cname/config
echo "lxc.aa_allow_incomplete = 1" >> $HDIR/.local/share/lxc/$cname/config
run_cmd lxc-start -n $cname -d
run_cmd lxc-wait -n $cname -s RUNNING
pid=`run_cmd lxc-info -p -H -n $cname`
if [ "$pid" = "-1" ]; then
echo "FAIL: excepted container failed to start without mount restrictions"
exit 1
fi
profile=`cat /proc/$pid/attr/current`
if [ "x$profile" != "x${default_profile}" ]; then
echo "FAIL: confined container was in profile $profile"
exit 1
fi
run_cmd lxc-stop -n $cname
DONE=1