^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0-only
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * AppArmor security module
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) * This file contains AppArmor policy loading interface function definitions.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) * Copyright 2013 Canonical Ltd.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) * Fns to provide a checksum of policy that has been loaded this can be
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) * compared to userspace policy compiles to check loaded policy is what
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) * it should be.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <crypto/hash.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include "include/apparmor.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #include "include/crypto.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) static unsigned int apparmor_hash_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) static struct crypto_shash *apparmor_tfm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) unsigned int aa_hash_size(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) return apparmor_hash_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) char *aa_calc_hash(void *data, size_t len)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) SHASH_DESC_ON_STACK(desc, apparmor_tfm);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) char *hash = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) int error = -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) if (!apparmor_tfm)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) hash = kzalloc(apparmor_hash_size, GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) if (!hash)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) desc->tfm = apparmor_tfm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) error = crypto_shash_init(desc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) error = crypto_shash_update(desc, (u8 *) data, len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) error = crypto_shash_final(desc, hash);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) return hash;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) fail:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) kfree(hash);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) return ERR_PTR(error);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) int aa_calc_profile_hash(struct aa_profile *profile, u32 version, void *start,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) size_t len)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) SHASH_DESC_ON_STACK(desc, apparmor_tfm);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) int error = -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) __le32 le32_version = cpu_to_le32(version);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) if (!aa_g_hash_policy)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) if (!apparmor_tfm)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) profile->hash = kzalloc(apparmor_hash_size, GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) if (!profile->hash)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) desc->tfm = apparmor_tfm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) error = crypto_shash_init(desc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) error = crypto_shash_update(desc, (u8 *) &le32_version, 4);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) error = crypto_shash_update(desc, (u8 *) start, len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) error = crypto_shash_final(desc, profile->hash);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) fail:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) kfree(profile->hash);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) profile->hash = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) static int __init init_profile_hash(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) struct crypto_shash *tfm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) if (!apparmor_initialized)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) tfm = crypto_alloc_shash("sha1", 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) if (IS_ERR(tfm)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) int error = PTR_ERR(tfm);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) AA_ERROR("failed to setup profile sha1 hashing: %d\n", error);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) apparmor_tfm = tfm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) apparmor_hash_size = crypto_shash_digestsize(apparmor_tfm);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) aa_info_message("AppArmor sha1 policy hashing enabled");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) late_initcall(init_profile_hash);