IMA can be configured to require signatures on policies before loading them. This test verifies that IMA correctly validates signatures, and rejects policies that lack signatures or have been signed by an unauthorized party (i.e. certificate is not on the appropriate keyring).
This test requires root privileges in order to write to securityfs files. Signed-off-by: David Jacobson <dav...@linux.ibm.com> --- evmtest/Makefile.am | 4 +- evmtest/files/Notes | 25 ++++++ evmtest/files/bad_privkey_ima.pem | 16 ++++ evmtest/files/policies/signed_policy | 2 + evmtest/files/policies/unknown_signed_policy | 1 + evmtest/files/policies/unsigned_policy | 1 + evmtest/functions/r_policy_sig.sh | 93 ++++++++++++++++++++ 7 files changed, 141 insertions(+), 1 deletion(-) create mode 100644 evmtest/files/Notes create mode 100644 evmtest/files/bad_privkey_ima.pem create mode 100644 evmtest/files/policies/signed_policy create mode 100644 evmtest/files/policies/unknown_signed_policy create mode 100644 evmtest/files/policies/unsigned_policy create mode 100755 evmtest/functions/r_policy_sig.sh diff --git a/evmtest/Makefile.am b/evmtest/Makefile.am index 388ead1..b537e78 100644 --- a/evmtest/Makefile.am +++ b/evmtest/Makefile.am @@ -14,9 +14,11 @@ evmtest.1: install: install -m 755 evmtest $(bindir) install -d $(datarootdir)/evmtest/files/ + install -d $(datarootdir)/evmtest/files/policies install -d $(datarootdir)/evmtest/functions/ - install -D $$(find ./files/ -not -type d) $(datarootdir)/evmtest/files/ + install -D $$(find ./files/ -not -type d -not -path "./files/policies/*") $(datarootdir)/evmtest/files/ install -D ./functions/* $(datarootdir)/evmtest/functions/ + install -D ./files/policies/* $(datarootdir)/evmtest/files/policies/ cp evmtest.1 $(datarootdir)/man/man1 mandb -q diff --git a/evmtest/files/Notes b/evmtest/files/Notes new file mode 100644 index 0000000..6b75263 --- /dev/null +++ b/evmtest/files/Notes @@ -0,0 +1,25 @@ +This file contains a description of the contents of this directory. + +1. bad_privkey_ima.pem + +This file was generated such that its corresponding public key could be placed +on the IMA Trusted Keyring, however, it has not. Therefore, any policy (or file) +signed by this key cannot be verified, and is untrusted. + +2. basic_mod.ko + +This is a kernel module that logs (to dmesg) the syscall that was used to load +it. + +3. common.sh + +This file contains useful functions and variables for evmtest scripts. + +4. load_policy.sh + +This is a script to load policies. The first time this is called, it will +replace the existing policy. Subsequent calls will append the running policy. + +5. policies/ + +This is a directory that contains IMA policies with self explanatory names. diff --git a/evmtest/files/bad_privkey_ima.pem b/evmtest/files/bad_privkey_ima.pem new file mode 100644 index 0000000..dcc0e24 --- /dev/null +++ b/evmtest/files/bad_privkey_ima.pem @@ -0,0 +1,16 @@ +-----BEGIN PRIVATE KEY----- +MIICdgIBADANBgkqhkiG9w0BAQEFAASCAmAwggJcAgEAAoGBAMOnki6OKMHExpH1 +IWgUlPWWSbsDpW1lpqXMj0/ZWo9xU5W2xZC53TVArUGOImQ5PcMNkw1VcHhKbFKO +jYT0gEE0Sv+VbePiEnhUheFOWUxNNFE3DVQaOpBN0OzsUCSGX9RKIIwkIAwJkvWA +MHzR4ZPQGGM9hMJKhEvlTG4PP96LAgMBAAECgYBKVKVCrptpUhqmZNx2MCuPSbNl +KzNz5kRzhM2FZmvzRvicTj2siBA0JQgteZQzQ1PlgIi3bhg2ev/ANYwqUMFQWZv9 +zm5d4P7Zsdyle15MDTSrQIaroeb1nbfNvaB0L4D4Inv0p6ksyIFp7TR5MLVenC5k +bxfESVWVPDseiAFKUQJBAPQ/x3LmnT0RiMeX6quCGAON7DGpV5KFwL97luWO6vH+ +qZ2W1/J0UxTbruv7rA+tj3ZXpdNOxfmq+JStY0jrJV0CQQDNEUqomnA183rX0dv8 +MWyOPmX0Z9SMSTRvflNRW85Bzbosq68uLTq3qOBj+td9zUlopsLpJlfF0Vc+moff +uq0HAkEAi/Sz47oTZXfTqZL6TBZ6jibXrck8PeBYhyBZYebX55ymMn/J88sGBFCx +VdVbTYyFRSmKAqADv0FhuUf1OUZMnQJAOayjUsgcxw+zfP+I32UHIvppslOBc/Mi +zDi7Niab2+YAdo/StSoDWaQld/kUok0aWFSOfQRLq1c1MmZD0KiwAQJANY0LopqG +pxACc4/QawxtBoV1a8j5Zui8LZPRtKwjkA30Nq8fOufzMuBeJIlLap45uD1xC7St +bsPWG5+uz18e5w== +-----END PRIVATE KEY----- diff --git a/evmtest/files/policies/signed_policy b/evmtest/files/policies/signed_policy new file mode 100644 index 0000000..87828f0 --- /dev/null +++ b/evmtest/files/policies/signed_policy @@ -0,0 +1,2 @@ +measure func=POLICY_CHECK +appraise func=POLICY_CHECK appraise_type=imasig diff --git a/evmtest/files/policies/unknown_signed_policy b/evmtest/files/policies/unknown_signed_policy new file mode 100644 index 0000000..1f8f8f4 --- /dev/null +++ b/evmtest/files/policies/unknown_signed_policy @@ -0,0 +1 @@ +audit func=POLICY_CHECK diff --git a/evmtest/files/policies/unsigned_policy b/evmtest/files/policies/unsigned_policy new file mode 100644 index 0000000..1f8f8f4 --- /dev/null +++ b/evmtest/files/policies/unsigned_policy @@ -0,0 +1 @@ +audit func=POLICY_CHECK diff --git a/evmtest/functions/r_policy_sig.sh b/evmtest/functions/r_policy_sig.sh new file mode 100755 index 0000000..7462c0a --- /dev/null +++ b/evmtest/functions/r_policy_sig.sh @@ -0,0 +1,93 @@ +#!/bin/bash +TEST="r_policy_sig" +# Author: David Jacobson <dav...@linux.ibm.com> + +ROOT="$( cd "$( dirname "${BASH_SOURCE[0]}" )" >/dev/null && pwd )/.." +source $ROOT/files/common.sh + +VERBOSE=0 +POLICY_LOAD=$ROOT/files/load_policy.sh +# This test validates that IMA measures and appraises policies. +usage() { + echo "" + echo "policy_sig -k <key> [-vh]" + echo "" + echo " This test must be run as root" + echo "" + echo " This test verifies that IMA prevents the loading of unsigned" + echo " policies" + echo "" + echo " -k,--key The key for the certificate on the IMA keyring" + echo " -h,--help Display this help message" + echo " -v,--verbose Verbose logging" +} + +TEMP=`getopt -o 'k:hv' -l 'key:,help,verbose' -n 'r_policy_sig' -- "$@"` +eval set -- "$TEMP" + +while true ; do + case "$1" in + -h|--help) usage; exit 0; shift;; + -k|--key) IMA_KEY=$2; shift 2;; + -v|--verbose) VERBOSE=1; shift;; + --) shift; break;; + *) echo "[*] Unrecognized option $1"; exit 1 ;; + esac +done + +if [[ -z $IMA_KEY ]]; then + usage + exit 1 +fi + +EVMTEST_require_root + +begin +v_out "Attempting to read current policy..." +cat $EVMTEST_SECFS/ima/policy &>> /dev/null # Don't need to output it + +if [[ $? != 0 ]]; then + fail "Could not read running policy - did you run env_validate?" +fi +v_out "Policy is readable" + +v_out "Signing policy with provided key..." +evmctl ima_sign -f $ROOT/files/policies/signed_policy -k $IMA_KEY +if [[ $? != 0 ]]; then + fail "Failed to sign policy - check key file" +fi + +v_out "Loading policy..." +$POLICY_LOAD signed_policy &>> /dev/null +if [[ $? != 0 ]]; then + fail "Failed to write policy - did you run env_validate?" +fi +v_out "Loaded" + +v_out "Attempting to load unsigned policy..." +$POLICY_LOAD unsigned_policy &>> /dev/null +if [[ $? != 1 ]]; then + fail "Failed to reject unsigned policy" +fi + +v_out "IMA Blocked unsigned policy" + +v_out "Signing policy with invalid key..." +evmctl ima_sign -f $ROOT/files/policies/unknown_signed_policy \ + -k $ROOT/files/bad_privkey_ima.pem &>> /dev/null +v_out "Attempting to load policy signed by invalid key..." +$POLICY_LOAD unknown_signed_policy &>> /dev/null + +if [[ $? != 1 ]]; then + fail "Failed to reject policy signed by unknown key" +fi + +v_out "IMA blocked policy signed by unknown key" + +v_out "Removing security.ima attribute from policies..." +setfattr -x security.ima $ROOT/files/policies/unsigned_policy &>> /dev/null +setfattr -x security.ima $ROOT/files/policies/unknown_signed_policy \ + &>> /dev/null +v_out "Done" + +passed -- 2.17.1