diff options
author | Nayna Jain <nayna@linux.ibm.com> | 2018-12-08 15:27:00 -0500 |
---|---|---|
committer | Mimi Zohar <zohar@linux.ibm.com> | 2018-12-12 22:02:54 -0500 |
commit | 60740accf78494e166ec76bdc39b7d75fc2fe1c7 (patch) | |
tree | a6793622667cca9eb606cbc098808bc8753524cc /security | |
parent | 9dc92c45177ab70e20ae94baa2f2e558da63a9c7 (diff) |
integrity: Load certs to the platform keyring
The patch refactors integrity_load_x509(), making it a wrapper for a new
function named integrity_add_key(). This patch also defines a new
function named integrity_load_cert() for loading the platform keys.
Signed-off-by: Nayna Jain <nayna@linux.ibm.com>
Reviewed-by: Mimi Zohar <zohar@linux.ibm.com>
Acked-by: Serge Hallyn <serge@hallyn.com>
Reviewed-by: James Morris <james.morris@microsoft.com>
Reviewed-by: Thiago Jung Bauermann <bauerman@linux.ibm.com>
Signed-off-by: Mimi Zohar <zohar@linux.ibm.com>
Diffstat (limited to 'security')
-rw-r--r-- | security/integrity/digsig.c | 67 | ||||
-rw-r--r-- | security/integrity/integrity.h | 20 | ||||
-rw-r--r-- | security/integrity/platform_certs/platform_keyring.c | 23 |
3 files changed, 86 insertions, 24 deletions
diff --git a/security/integrity/digsig.c b/security/integrity/digsig.c index 4a22730e0cc6..71c3200521d6 100644 --- a/security/integrity/digsig.c +++ b/security/integrity/digsig.c | |||
@@ -82,8 +82,7 @@ static int __integrity_init_keyring(const unsigned int id, key_perm_t perm, | |||
82 | 82 | ||
83 | keyring[id] = keyring_alloc(keyring_name[id], KUIDT_INIT(0), | 83 | keyring[id] = keyring_alloc(keyring_name[id], KUIDT_INIT(0), |
84 | KGIDT_INIT(0), cred, perm, | 84 | KGIDT_INIT(0), cred, perm, |
85 | KEY_ALLOC_NOT_IN_QUOTA, | 85 | KEY_ALLOC_NOT_IN_QUOTA, restriction, NULL); |
86 | restriction, NULL); | ||
87 | if (IS_ERR(keyring[id])) { | 86 | if (IS_ERR(keyring[id])) { |
88 | err = PTR_ERR(keyring[id]); | 87 | err = PTR_ERR(keyring[id]); |
89 | pr_info("Can't allocate %s keyring (%d)\n", | 88 | pr_info("Can't allocate %s keyring (%d)\n", |
@@ -121,16 +120,38 @@ out: | |||
121 | return __integrity_init_keyring(id, perm, restriction); | 120 | return __integrity_init_keyring(id, perm, restriction); |
122 | } | 121 | } |
123 | 122 | ||
124 | int __init integrity_load_x509(const unsigned int id, const char *path) | 123 | int __init integrity_add_key(const unsigned int id, const void *data, |
124 | off_t size, key_perm_t perm) | ||
125 | { | 125 | { |
126 | key_ref_t key; | 126 | key_ref_t key; |
127 | void *data; | 127 | int rc = 0; |
128 | loff_t size; | ||
129 | int rc; | ||
130 | 128 | ||
131 | if (!keyring[id]) | 129 | if (!keyring[id]) |
132 | return -EINVAL; | 130 | return -EINVAL; |
133 | 131 | ||
132 | key = key_create_or_update(make_key_ref(keyring[id], 1), "asymmetric", | ||
133 | NULL, data, size, perm, | ||
134 | KEY_ALLOC_NOT_IN_QUOTA); | ||
135 | if (IS_ERR(key)) { | ||
136 | rc = PTR_ERR(key); | ||
137 | pr_err("Problem loading X.509 certificate %d\n", rc); | ||
138 | } else { | ||
139 | pr_notice("Loaded X.509 cert '%s'\n", | ||
140 | key_ref_to_ptr(key)->description); | ||
141 | key_ref_put(key); | ||
142 | } | ||
143 | |||
144 | return rc; | ||
145 | |||
146 | } | ||
147 | |||
148 | int __init integrity_load_x509(const unsigned int id, const char *path) | ||
149 | { | ||
150 | void *data; | ||
151 | loff_t size; | ||
152 | int rc; | ||
153 | key_perm_t perm; | ||
154 | |||
134 | rc = kernel_read_file_from_path(path, &data, &size, 0, | 155 | rc = kernel_read_file_from_path(path, &data, &size, 0, |
135 | READING_X509_CERTIFICATE); | 156 | READING_X509_CERTIFICATE); |
136 | if (rc < 0) { | 157 | if (rc < 0) { |
@@ -138,23 +159,21 @@ int __init integrity_load_x509(const unsigned int id, const char *path) | |||
138 | return rc; | 159 | return rc; |
139 | } | 160 | } |
140 | 161 | ||
141 | key = key_create_or_update(make_key_ref(keyring[id], 1), | 162 | perm = (KEY_POS_ALL & ~KEY_POS_SETATTR) | KEY_USR_VIEW | KEY_USR_READ; |
142 | "asymmetric", | 163 | |
143 | NULL, | 164 | pr_info("Loading X.509 certificate: %s\n", path); |
144 | data, | 165 | rc = integrity_add_key(id, (const void *)data, size, perm); |
145 | size, | 166 | |
146 | ((KEY_POS_ALL & ~KEY_POS_SETATTR) | | ||
147 | KEY_USR_VIEW | KEY_USR_READ), | ||
148 | KEY_ALLOC_NOT_IN_QUOTA); | ||
149 | if (IS_ERR(key)) { | ||
150 | rc = PTR_ERR(key); | ||
151 | pr_err("Problem loading X.509 certificate (%d): %s\n", | ||
152 | rc, path); | ||
153 | } else { | ||
154 | pr_notice("Loaded X.509 cert '%s': %s\n", | ||
155 | key_ref_to_ptr(key)->description, path); | ||
156 | key_ref_put(key); | ||
157 | } | ||
158 | vfree(data); | 167 | vfree(data); |
159 | return 0; | 168 | return rc; |
169 | } | ||
170 | |||
171 | int __init integrity_load_cert(const unsigned int id, const char *source, | ||
172 | const void *data, size_t len, key_perm_t perm) | ||
173 | { | ||
174 | if (!data) | ||
175 | return -EINVAL; | ||
176 | |||
177 | pr_info("Loading X.509 certificate: %s\n", source); | ||
178 | return integrity_add_key(id, data, len, perm); | ||
160 | } | 179 | } |
diff --git a/security/integrity/integrity.h b/security/integrity/integrity.h index c2332a44799e..3517d2852a07 100644 --- a/security/integrity/integrity.h +++ b/security/integrity/integrity.h | |||
@@ -154,6 +154,8 @@ int integrity_digsig_verify(const unsigned int id, const char *sig, int siglen, | |||
154 | 154 | ||
155 | int __init integrity_init_keyring(const unsigned int id); | 155 | int __init integrity_init_keyring(const unsigned int id); |
156 | int __init integrity_load_x509(const unsigned int id, const char *path); | 156 | int __init integrity_load_x509(const unsigned int id, const char *path); |
157 | int __init integrity_load_cert(const unsigned int id, const char *source, | ||
158 | const void *data, size_t len, key_perm_t perm); | ||
157 | #else | 159 | #else |
158 | 160 | ||
159 | static inline int integrity_digsig_verify(const unsigned int id, | 161 | static inline int integrity_digsig_verify(const unsigned int id, |
@@ -167,6 +169,14 @@ static inline int integrity_init_keyring(const unsigned int id) | |||
167 | { | 169 | { |
168 | return 0; | 170 | return 0; |
169 | } | 171 | } |
172 | |||
173 | static inline int __init integrity_load_cert(const unsigned int id, | ||
174 | const char *source, | ||
175 | const void *data, size_t len, | ||
176 | key_perm_t perm) | ||
177 | { | ||
178 | return 0; | ||
179 | } | ||
170 | #endif /* CONFIG_INTEGRITY_SIGNATURE */ | 180 | #endif /* CONFIG_INTEGRITY_SIGNATURE */ |
171 | 181 | ||
172 | #ifdef CONFIG_INTEGRITY_ASYMMETRIC_KEYS | 182 | #ifdef CONFIG_INTEGRITY_ASYMMETRIC_KEYS |
@@ -223,3 +233,13 @@ integrity_audit_log_start(struct audit_context *ctx, gfp_t gfp_mask, int type) | |||
223 | } | 233 | } |
224 | 234 | ||
225 | #endif | 235 | #endif |
236 | |||
237 | #ifdef CONFIG_INTEGRITY_PLATFORM_KEYRING | ||
238 | void __init add_to_platform_keyring(const char *source, const void *data, | ||
239 | size_t len); | ||
240 | #else | ||
241 | static inline void __init add_to_platform_keyring(const char *source, | ||
242 | const void *data, size_t len) | ||
243 | { | ||
244 | } | ||
245 | #endif | ||
diff --git a/security/integrity/platform_certs/platform_keyring.c b/security/integrity/platform_certs/platform_keyring.c index 79f80af5b470..bcafd7387729 100644 --- a/security/integrity/platform_certs/platform_keyring.c +++ b/security/integrity/platform_certs/platform_keyring.c | |||
@@ -14,6 +14,29 @@ | |||
14 | #include <linux/slab.h> | 14 | #include <linux/slab.h> |
15 | #include "../integrity.h" | 15 | #include "../integrity.h" |
16 | 16 | ||
17 | /** | ||
18 | * add_to_platform_keyring - Add to platform keyring without validation. | ||
19 | * @source: Source of key | ||
20 | * @data: The blob holding the key | ||
21 | * @len: The length of the data blob | ||
22 | * | ||
23 | * Add a key to the platform keyring without checking its trust chain. This | ||
24 | * is available only during kernel initialisation. | ||
25 | */ | ||
26 | void __init add_to_platform_keyring(const char *source, const void *data, | ||
27 | size_t len) | ||
28 | { | ||
29 | key_perm_t perm; | ||
30 | int rc; | ||
31 | |||
32 | perm = (KEY_POS_ALL & ~KEY_POS_SETATTR) | KEY_USR_VIEW; | ||
33 | |||
34 | rc = integrity_load_cert(INTEGRITY_KEYRING_PLATFORM, source, data, len, | ||
35 | perm); | ||
36 | if (rc) | ||
37 | pr_info("Error adding keys to platform keyring %s\n", source); | ||
38 | } | ||
39 | |||
17 | /* | 40 | /* |
18 | * Create the trusted keyrings. | 41 | * Create the trusted keyrings. |
19 | */ | 42 | */ |