From: Stefan Berger <stef...@us.ibm.com>

Do not try to convert a zero-length file digest to a binary representation.
Zero-length file digests may stem from directory entries and symbolic links.
Return an empty signature in this case.

Returning an empty signature results in the ima.so plugin getting a sequence
of zeroes that it would write into security.ima xattr. Check for a signature
header consisting of only zeroes and do not write it into the filesystem.

Signed-off-by: Stefan Berger <stef...@linux.vnet.ibm.com>
---
 lib/rpmsignfiles.c |  4 ++++
 plugins/ima.c      | 25 ++++++++++++++++++++++++-
 2 files changed, 28 insertions(+), 1 deletion(-)

diff --git a/lib/rpmsignfiles.c b/lib/rpmsignfiles.c
index 97a5be4..3cd2b1a 100644
--- a/lib/rpmsignfiles.c
+++ b/lib/rpmsignfiles.c
@@ -82,6 +82,10 @@ const char *key, char *keypass)
 
     /* convert file digest hex to binary */
     memset(digest, 0, diglen);
+    /* some entries don't have a digest - we return an empty signature */
+    if (strlen(fdigest) != diglen * 2)
+        return strdup("");
+
     for (int i = 0; i < diglen; ++i, fdigest += 2)
        digest[i] = (rnibble(fdigest[0]) << 4) | rnibble(fdigest[1]);
 
diff --git a/plugins/ima.c b/plugins/ima.c
index 0dfdd8b..be15ecf 100644
--- a/plugins/ima.c
+++ b/plugins/ima.c
@@ -12,6 +12,29 @@
 
 #define XATTR_NAME_IMA "security.ima"
 
+/*
+ * check_zero_hdr: Check the signature for a zero header
+ *
+ * Check whether the given signature has a header with all zeros
+ *
+ * Returns -1 in case the signature is too short to compare
+ * (invalid signature), 0 in case the header is not only zeroes,
+ * and 1 if it is only zeroes.
+ */
+static int check_zero_hdr(const unsigned char *fsig, size_t siglen)
+{
+       /*
+        * Every signature has a header signature_v2_hdr as defined in
+        * Linux's (4.5) security/integrity/integtrity.h. The following
+        * 9 bytes represent this header in front of the signature.
+        */
+       static const uint8_t zero_hdr[] = {0, 0, 0, 0, 0, 0, 0, 0, 0};
+
+       if (siglen < sizeof(zero_hdr))
+               return -1;
+       return (memcmp(fsig, &zero_hdr, sizeof(zero_hdr)) == 0);
+}
+
 static rpmRC ima_psm_post(rpmPlugin plugin, rpmte te, int res)
 {
        rpmfi fi = rpmteFI(te);
@@ -30,7 +53,7 @@ static rpmRC ima_psm_post(rpmPlugin plugin, rpmte te, int res)
            if (!(rpmfiFFlags(fi) & RPMFILE_CONFIG)) {
                fpath = rpmfiFN(fi);
                fsig = rpmfiFSignature(fi, &len);
-               if (fsig) {
+               if (fsig && (check_zero_hdr(fsig, len) == 0)) {
                    lsetxattr(fpath, XATTR_NAME_IMA, fsig, len, 0);
                }
            }
-- 
2.5.5

_______________________________________________
Rpm-maint mailing list
Rpm-maint@lists.rpm.org
http://lists.rpm.org/mailman/listinfo/rpm-maint

Reply via email to