Skip to content
Snippets Groups Projects
Commit 0ff8ee80 authored by Andre Moreira Magalhaes's avatar Andre Moreira Magalhaes
Browse files

Merge branch 'T4802' into 'master'

Add run-aa-test

See merge request common!2
parents 5f7c5884 061cc818
No related branches found
No related tags found
No related merge requests found
# Need to source this file.
# Pass in audit string, returns formatted block as `aa_log_extract_tokens.pl`
# would have provided. Need to return:
#
# profile:/usr/bin/busctl
# sdmode:REJECTING
# denied_mask:r
# operation:open
# name:/proc/879/stat
# request_mask:r
#
# Note: apparmor uses the term "DENIED" rather than "REJECTING", but our
# expected values want "REJECTING", so tweak for now.
apparmor_parse_journal() {
awk -v event=$2 '
{
for (i = 1; i <= NF; i++) {
n = index($i, "=");
if(n) {
vars[substr($i, 1, n - 1)] = substr($i, n + 1)
# Strip quotes
gsub("\"","",vars[substr($i, 1, n - 1)])
}
}
}
{
if (vars["apparmor"] == event) {
print "===="
print "profile:"vars["profile"]
# Match old nomenclature
if (vars["apparmor"] == "DENIED") {
vars["apparmor"] = "REJECTING"
}
print "sdmode:"vars["apparmor"]
print "denied_mask:"vars["denied_mask"]
print "operation:"vars["operation"]
print "name:"vars["name"]
print "request_mask:"vars["requested_mask"]
}
}
' $1
}
#!/bin/sh
#
# Copyright © 2018 Collabora Ltd.
#
# Based on python version of run-aa-test
#
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
. common/common-apparmor.sh
ALTERNATIVE_SEPARATOR="## alternative ##"
END=2
case $(echo ${LAUNCH_DBUS} | tr [A-Z] [a-z]) in
0 | no | false)
LAUNCH_DBUS="False"
;;
*)
LAUNCH_DBUS="True"
esac
case $(echo ${RUN_AS_USER} | tr [A-Z] [a-z]) in
0 | no | false)
RUN_AS_USER="False"
;;
*)
RUN_AS_USER="True"
esac
CHAIWALA_UID=1000
CHAIWALA_USER="user"
# Check parameters
if [ $# -lt 2 ]; then
echo "Usage: run-aa-test <expectation-file> <command> <argument-1> <argument-2> …"
echo "\"export LAUNCH_DBUS=no\" in the test script to not launch a dbus session."
echo "\"export RUN_AS_USER=no\" in the test script to not run as ${CHAIWALA_USER}"
exit 1
fi
EXPECT_FILE=$1
shift
if [ ! -r ${EXPECT_FILE} ]; then
echo "Cannot read specified expectation file: ${EXPECT_FILE}"
exit 1
fi
if [ ! -x $1 ]; then
echo "Cannot execute specified test executable: $1"
exit 1
fi
# typically "normal.expected" or "malicious.expected"
TEST_TITLE=$( basename ${EXPECT_FILE} )
# Touch .bash_history, which we use in some tests, if it's not there.
bash_history="/home/${CHAIWALA_USER}/.bash_history"
if [ ! -r ${bash_history} ]; then
RET=$( sudo -u ${CHAIWALA_USER} touch ${bash_history} )
if [ $RET != 0 ]; then
echo "Failed to create .bash_history: $RET"
exit 1
fi
fi
# Create a temporary directory for files
TMP_DIR=$(mktemp -d)
# Log start time
START_TIME=$(date +"%F %T")
if [ "${LAUNCH_DBUS}" = "True" ]; then
# Start a new D-Bus session for this test
CMD="dbus-run-session -- $*"
else
CMD="$*"
fi
CMDLINE="common/run-test-in-systemd"
if [ ! -x $CMDLINE ]; then
echo "common/run-test-in-systemd not found"
exit 1
fi
CMDLINE="${CMDLINE} --no-lava"
if [ "${RUN_AA_TEST_TIMEOUT}" != "" ]; then
CMDLINE="${CMDLINE} --timeout=${RUN_AA_TEST_TIMEOUT}"
fi
if [ "${RUN_AS_USER}" = "True" ]; then
CMDLINE="${CMDLINE} --user=${CHAIWALA_UID}"
else
CMDLINE="${CMDLINE} --system"
fi
CMDLINE="${CMDLINE} ${CMD}"
echo "#=== running test script: ${CMDLINE} ==="
setsid ${CMDLINE}
RET=$?
echo "#--- end of test script, status: ${RET}"
if [ "${RET}" = "0" ]; then
echo "${TEST_TITLE}_underlying_tests: pass"
else
echo "# ${CMDLINE} exited ${RET}"
# typically "normal.expected_underlying_tests: fail"
echo "${TEST_TITLE}_underlying_tests: fail"
exit 1
fi
# Give journal time to log the entries.
sleep 3
# Get audit information from journal
AUDIT_FILE=${TMP_DIR}/AUDIT
journalctl -S "${START_TIME}" -t audit -o cat > ${AUDIT_FILE}
echo "#=== ${TEST_TITLE} ==="
echo "#---8<--- raw apparmor output from journal"
cat ${AUDIT_FILE} | sed 's/^/# /'
echo "#--->8---"
echo "#---8<--- expected parsed apparmor output from journal"
cat ${EXPECT_FILE} | sed 's/^/# /'
echo "#--->8---"
csplit ${EXPECT_FILE} -f ${TMP_DIR}/EXPECT -b "%d" "/^${ALTERNATIVE_SEPARATOR}$/" {*}
# Old versions of csplit don't provide "--suppress-matched", strip separator separately
for FILE in ${TMP_DIR}/EXPECT*; do
sed -i "/^${ALTERNATIVE_SEPARATOR}$/d" ${FILE}
done
PARSE_FILE="${TMP_DIR}/PARSE"
# TODO: There is potential for other processes to cause messages to appear in
# the journal that may lead to false failures. If this is found to be an
# issue in practice, then additional filtering of results may be required
apparmor_parse_journal ${AUDIT_FILE} DENIED > ${PARSE_FILE}
echo "#---8<--- actual parsed apparmor output from journal"
cat ${PARSE_FILE} | sed 's/^/# /'
echo "#--->8---"
MATCH_EXPECTATION="False"
# We might have alternative expectations, take that into consideration.
OUTPUT_MD5=$( cat ${PARSE_FILE} | md5sum )
COUNT=$( ls -1 ${TMP_DIR}/EXPECT* | wc -l )
NUM=0
while [ $((${NUM} < ${COUNT})) = 1 ]; do
EXPECTED_MD5=$( cat ${TMP_DIR}/EXPECT${NUM} | md5sum )
if [ "${OUTPUT_MD5}" = "${EXPECTED_MD5}" ]; then
echo "# audit log matches alternative expectation ${NUM}/${COUNT}"
MATCH_EXPECTATION="True"
fi
NUM=$((${NUM}+1))
done
if [ "${MATCH_EXPECTATION}" = "True" ]; then
echo "${TEST_TITLE}: pass"
else
echo "#---8<--- diff"
diff -urN ${TMP_DIR}/EXPECT${NUM} ${PARSE_FILE}
echo "#--->8---"
echo "${TEST_TITLE}: fail"
exit 1
fi
exit 0
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment