xref: /linux/security/keys/request_key.c (revision 13abf8130139c2ccd4962a7e5a8902be5e6cb5a7)
1 /* request_key.c: request a key from userspace
2  *
3  * Copyright (C) 2004-5 Red Hat, Inc. All Rights Reserved.
4  * Written by David Howells (dhowells@redhat.com)
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; either version
9  * 2 of the License, or (at your option) any later version.
10  */
11 
12 #include <linux/module.h>
13 #include <linux/sched.h>
14 #include <linux/kmod.h>
15 #include <linux/err.h>
16 #include <linux/keyctl.h>
17 #include "internal.h"
18 
19 struct key_construction {
20 	struct list_head	link;	/* link in construction queue */
21 	struct key		*key;	/* key being constructed */
22 };
23 
24 /* when waiting for someone else's keys, you get added to this */
25 DECLARE_WAIT_QUEUE_HEAD(request_key_conswq);
26 
27 /*****************************************************************************/
28 /*
29  * request userspace finish the construction of a key
30  * - execute "/sbin/request-key <op> <key> <uid> <gid> <keyring> <keyring> <keyring> <info>"
31  */
32 static int call_request_key(struct key *key,
33 			    const char *op,
34 			    const char *callout_info)
35 {
36 	struct task_struct *tsk = current;
37 	key_serial_t prkey, sskey;
38 	struct key *session_keyring, *rkakey;
39 	char *argv[10], *envp[3], uid_str[12], gid_str[12];
40 	char key_str[12], keyring_str[3][12];
41 	int ret, i;
42 
43 	kenter("{%d},%s,%s", key->serial, op, callout_info);
44 
45 	/* generate a new session keyring with an auth key in it */
46 	session_keyring = request_key_auth_new(key, &rkakey);
47 	if (IS_ERR(session_keyring)) {
48 		ret = PTR_ERR(session_keyring);
49 		goto error;
50 	}
51 
52 	/* record the UID and GID */
53 	sprintf(uid_str, "%d", current->fsuid);
54 	sprintf(gid_str, "%d", current->fsgid);
55 
56 	/* we say which key is under construction */
57 	sprintf(key_str, "%d", key->serial);
58 
59 	/* we specify the process's default keyrings */
60 	sprintf(keyring_str[0], "%d",
61 		tsk->thread_keyring ? tsk->thread_keyring->serial : 0);
62 
63 	prkey = 0;
64 	if (tsk->signal->process_keyring)
65 		prkey = tsk->signal->process_keyring->serial;
66 
67 	sprintf(keyring_str[1], "%d", prkey);
68 
69 	if (tsk->signal->session_keyring) {
70 		rcu_read_lock();
71 		sskey = rcu_dereference(tsk->signal->session_keyring)->serial;
72 		rcu_read_unlock();
73 	}
74 	else {
75 		sskey = tsk->user->session_keyring->serial;
76 	}
77 
78 	sprintf(keyring_str[2], "%d", sskey);
79 
80 	/* set up a minimal environment */
81 	i = 0;
82 	envp[i++] = "HOME=/";
83 	envp[i++] = "PATH=/sbin:/bin:/usr/sbin:/usr/bin";
84 	envp[i] = NULL;
85 
86 	/* set up the argument list */
87 	i = 0;
88 	argv[i++] = "/sbin/request-key";
89 	argv[i++] = (char *) op;
90 	argv[i++] = key_str;
91 	argv[i++] = uid_str;
92 	argv[i++] = gid_str;
93 	argv[i++] = keyring_str[0];
94 	argv[i++] = keyring_str[1];
95 	argv[i++] = keyring_str[2];
96 	argv[i++] = (char *) callout_info;
97 	argv[i] = NULL;
98 
99 	/* do it */
100 	ret = call_usermodehelper_keys(argv[0], argv, envp, session_keyring, 1);
101 
102 	/* dispose of the special keys */
103 	key_revoke(rkakey);
104 	key_put(rkakey);
105 	key_put(session_keyring);
106 
107  error:
108 	kleave(" = %d", ret);
109 	return ret;
110 
111 } /* end call_request_key() */
112 
113 /*****************************************************************************/
114 /*
115  * call out to userspace for the key
116  * - called with the construction sem held, but the sem is dropped here
117  * - we ignore program failure and go on key status instead
118  */
119 static struct key *__request_key_construction(struct key_type *type,
120 					      const char *description,
121 					      const char *callout_info)
122 {
123 	struct key_construction cons;
124 	struct timespec now;
125 	struct key *key;
126 	int ret, negated;
127 
128 	kenter("%s,%s,%s", type->name, description, callout_info);
129 
130 	/* create a key and add it to the queue */
131 	key = key_alloc(type, description,
132 			current->fsuid, current->fsgid, KEY_USR_ALL, 0);
133 	if (IS_ERR(key))
134 		goto alloc_failed;
135 
136 	set_bit(KEY_FLAG_USER_CONSTRUCT, &key->flags);
137 
138 	cons.key = key;
139 	list_add_tail(&cons.link, &key->user->consq);
140 
141 	/* we drop the construction sem here on behalf of the caller */
142 	up_write(&key_construction_sem);
143 
144 	/* make the call */
145 	ret = call_request_key(key, "create", callout_info);
146 	if (ret < 0)
147 		goto request_failed;
148 
149 	/* if the key wasn't instantiated, then we want to give an error */
150 	ret = -ENOKEY;
151 	if (!test_bit(KEY_FLAG_INSTANTIATED, &key->flags))
152 		goto request_failed;
153 
154 	down_write(&key_construction_sem);
155 	list_del(&cons.link);
156 	up_write(&key_construction_sem);
157 
158 	/* also give an error if the key was negatively instantiated */
159  check_not_negative:
160 	if (test_bit(KEY_FLAG_NEGATIVE, &key->flags)) {
161 		key_put(key);
162 		key = ERR_PTR(-ENOKEY);
163 	}
164 
165  out:
166 	kleave(" = %p", key);
167 	return key;
168 
169  request_failed:
170 	/* it wasn't instantiated
171 	 * - remove from construction queue
172 	 * - mark the key as dead
173 	 */
174 	negated = 0;
175 	down_write(&key_construction_sem);
176 
177 	list_del(&cons.link);
178 
179 	/* check it didn't get instantiated between the check and the down */
180 	if (!test_bit(KEY_FLAG_INSTANTIATED, &key->flags)) {
181 		set_bit(KEY_FLAG_NEGATIVE, &key->flags);
182 		set_bit(KEY_FLAG_INSTANTIATED, &key->flags);
183 		negated = 1;
184 	}
185 
186 	clear_bit(KEY_FLAG_USER_CONSTRUCT, &key->flags);
187 
188 	up_write(&key_construction_sem);
189 
190 	if (!negated)
191 		goto check_not_negative; /* surprisingly, the key got
192 					  * instantiated */
193 
194 	/* set the timeout and store in the session keyring if we can */
195 	now = current_kernel_time();
196 	key->expiry = now.tv_sec + key_negative_timeout;
197 
198 	if (current->signal->session_keyring) {
199 		struct key *keyring;
200 
201 		rcu_read_lock();
202 		keyring = rcu_dereference(current->signal->session_keyring);
203 		atomic_inc(&keyring->usage);
204 		rcu_read_unlock();
205 
206 		key_link(keyring, key);
207 		key_put(keyring);
208 	}
209 
210 	key_put(key);
211 
212 	/* notify anyone who was waiting */
213 	wake_up_all(&request_key_conswq);
214 
215 	key = ERR_PTR(ret);
216 	goto out;
217 
218  alloc_failed:
219 	up_write(&key_construction_sem);
220 	goto out;
221 
222 } /* end __request_key_construction() */
223 
224 /*****************************************************************************/
225 /*
226  * call out to userspace to request the key
227  * - we check the construction queue first to see if an appropriate key is
228  *   already being constructed by userspace
229  */
230 static struct key *request_key_construction(struct key_type *type,
231 					    const char *description,
232 					    struct key_user *user,
233 					    const char *callout_info)
234 {
235 	struct key_construction *pcons;
236 	struct key *key, *ckey;
237 
238 	DECLARE_WAITQUEUE(myself, current);
239 
240 	kenter("%s,%s,{%d},%s",
241 	       type->name, description, user->uid, callout_info);
242 
243 	/* see if there's such a key under construction already */
244 	down_write(&key_construction_sem);
245 
246 	list_for_each_entry(pcons, &user->consq, link) {
247 		ckey = pcons->key;
248 
249 		if (ckey->type != type)
250 			continue;
251 
252 		if (type->match(ckey, description))
253 			goto found_key_under_construction;
254 	}
255 
256 	/* see about getting userspace to construct the key */
257 	key = __request_key_construction(type, description, callout_info);
258  error:
259 	kleave(" = %p", key);
260 	return key;
261 
262 	/* someone else has the same key under construction
263 	 * - we want to keep an eye on their key
264 	 */
265  found_key_under_construction:
266 	atomic_inc(&ckey->usage);
267 	up_write(&key_construction_sem);
268 
269 	/* wait for the key to be completed one way or another */
270 	add_wait_queue(&request_key_conswq, &myself);
271 
272 	for (;;) {
273 		set_current_state(TASK_INTERRUPTIBLE);
274 		if (!test_bit(KEY_FLAG_USER_CONSTRUCT, &ckey->flags))
275 			break;
276 		if (signal_pending(current))
277 			break;
278 		schedule();
279 	}
280 
281 	set_current_state(TASK_RUNNING);
282 	remove_wait_queue(&request_key_conswq, &myself);
283 
284 	/* we'll need to search this process's keyrings to see if the key is
285 	 * now there since we can't automatically assume it's also available
286 	 * there */
287 	key_put(ckey);
288 	ckey = NULL;
289 
290 	key = NULL; /* request a retry */
291 	goto error;
292 
293 } /* end request_key_construction() */
294 
295 /*****************************************************************************/
296 /*
297  * link a freshly minted key to an appropriate destination keyring
298  */
299 static void request_key_link(struct key *key, struct key *dest_keyring)
300 {
301 	struct task_struct *tsk = current;
302 	struct key *drop = NULL;
303 
304 	kenter("{%d},%p", key->serial, dest_keyring);
305 
306 	/* find the appropriate keyring */
307 	if (!dest_keyring) {
308 		switch (tsk->jit_keyring) {
309 		case KEY_REQKEY_DEFL_DEFAULT:
310 		case KEY_REQKEY_DEFL_THREAD_KEYRING:
311 			dest_keyring = tsk->thread_keyring;
312 			if (dest_keyring)
313 				break;
314 
315 		case KEY_REQKEY_DEFL_PROCESS_KEYRING:
316 			dest_keyring = tsk->signal->process_keyring;
317 			if (dest_keyring)
318 				break;
319 
320 		case KEY_REQKEY_DEFL_SESSION_KEYRING:
321 			rcu_read_lock();
322 			dest_keyring = key_get(
323 				rcu_dereference(tsk->signal->session_keyring));
324 			rcu_read_unlock();
325 			drop = dest_keyring;
326 
327 			if (dest_keyring)
328 				break;
329 
330 		case KEY_REQKEY_DEFL_USER_SESSION_KEYRING:
331 			dest_keyring = current->user->session_keyring;
332 			break;
333 
334 		case KEY_REQKEY_DEFL_USER_KEYRING:
335 			dest_keyring = current->user->uid_keyring;
336 			break;
337 
338 		case KEY_REQKEY_DEFL_GROUP_KEYRING:
339 		default:
340 			BUG();
341 		}
342 	}
343 
344 	/* and attach the key to it */
345 	key_link(dest_keyring, key);
346 
347 	key_put(drop);
348 
349 	kleave("");
350 
351 } /* end request_key_link() */
352 
353 /*****************************************************************************/
354 /*
355  * request a key
356  * - search the process's keyrings
357  * - check the list of keys being created or updated
358  * - call out to userspace for a key if supplementary info was provided
359  * - cache the key in an appropriate keyring
360  */
361 struct key *request_key_and_link(struct key_type *type,
362 				 const char *description,
363 				 const char *callout_info,
364 				 struct key *dest_keyring)
365 {
366 	struct key_user *user;
367 	struct key *key;
368 
369 	kenter("%s,%s,%s,%p",
370 	       type->name, description, callout_info, dest_keyring);
371 
372 	/* search all the process keyrings for a key */
373 	key = search_process_keyrings(type, description, type->match, current);
374 
375 	if (PTR_ERR(key) == -EAGAIN) {
376 		/* the search failed, but the keyrings were searchable, so we
377 		 * should consult userspace if we can */
378 		key = ERR_PTR(-ENOKEY);
379 		if (!callout_info)
380 			goto error;
381 
382 		/* - get hold of the user's construction queue */
383 		user = key_user_lookup(current->fsuid);
384 		if (!user)
385 			goto nomem;
386 
387 		do {
388 			if (signal_pending(current))
389 				goto interrupted;
390 
391 			/* ask userspace (returns NULL if it waited on a key
392 			 * being constructed) */
393 			key = request_key_construction(type, description,
394 						       user, callout_info);
395 			if (key)
396 				break;
397 
398 			/* someone else made the key we want, so we need to
399 			 * search again as it might now be available to us */
400 			key = search_process_keyrings(type, description,
401 						      type->match, current);
402 
403 		} while (PTR_ERR(key) == -EAGAIN);
404 
405 		key_user_put(user);
406 
407 		/* link the new key into the appropriate keyring */
408 		if (!IS_ERR(key))
409 			request_key_link(key, dest_keyring);
410 	}
411 
412 error:
413 	kleave(" = %p", key);
414 	return key;
415 
416 nomem:
417 	key = ERR_PTR(-ENOMEM);
418 	goto error;
419 
420 interrupted:
421 	key_user_put(user);
422 	key = ERR_PTR(-EINTR);
423 	goto error;
424 
425 } /* end request_key_and_link() */
426 
427 /*****************************************************************************/
428 /*
429  * request a key
430  * - search the process's keyrings
431  * - check the list of keys being created or updated
432  * - call out to userspace for a key if supplementary info was provided
433  */
434 struct key *request_key(struct key_type *type,
435 			const char *description,
436 			const char *callout_info)
437 {
438 	return request_key_and_link(type, description, callout_info, NULL);
439 
440 } /* end request_key() */
441 
442 EXPORT_SYMBOL(request_key);
443 
444 /*****************************************************************************/
445 /*
446  * validate a key
447  */
448 int key_validate(struct key *key)
449 {
450 	struct timespec now;
451 	int ret = 0;
452 
453 	if (key) {
454 		/* check it's still accessible */
455 		ret = -EKEYREVOKED;
456 		if (test_bit(KEY_FLAG_REVOKED, &key->flags) ||
457 		    test_bit(KEY_FLAG_DEAD, &key->flags))
458 			goto error;
459 
460 		/* check it hasn't expired */
461 		ret = 0;
462 		if (key->expiry) {
463 			now = current_kernel_time();
464 			if (now.tv_sec >= key->expiry)
465 				ret = -EKEYEXPIRED;
466 		}
467 	}
468 
469  error:
470 	return ret;
471 
472 } /* end key_validate() */
473 
474 EXPORT_SYMBOL(key_validate);
475