From 4e54f08543d05e519e601368571cc3787fefae96 Mon Sep 17 00:00:00 2001 From: David Howells Date: Thu, 29 Jun 2006 02:24:28 -0700 Subject: [PATCH] Keys: Allow in-kernel key requestor to pass auxiliary data to upcaller The proposed NFS key type uses its own method of passing key requests to userspace (upcalling) rather than invoking /sbin/request-key. This is because the responsible userspace daemon should already be running and will be contacted through rpc_pipefs. This patch permits the NFS filesystem to pass auxiliary data to the upcall operation (struct key_type::request_key) so that the upcaller can use a pre-existing communications channel more easily. Signed-off-by: David Howells Acked-By: Kevin Coffman Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- security/keys/internal.h | 1 + security/keys/keyctl.c | 2 +- security/keys/request_key.c | 44 ++++++++++++++++++++++++++++++++++---------- 3 files changed, 36 insertions(+), 11 deletions(-) (limited to 'security/keys') diff --git a/security/keys/internal.h b/security/keys/internal.h index 3c2877f0663e..1bb416f4bbce 100644 --- a/security/keys/internal.h +++ b/security/keys/internal.h @@ -99,6 +99,7 @@ extern int install_process_keyring(struct task_struct *tsk); extern struct key *request_key_and_link(struct key_type *type, const char *description, const char *callout_info, + void *aux, struct key *dest_keyring, unsigned long flags); diff --git a/security/keys/keyctl.c b/security/keys/keyctl.c index 329411cf8768..d9ca15c109cc 100644 --- a/security/keys/keyctl.c +++ b/security/keys/keyctl.c @@ -183,7 +183,7 @@ asmlinkage long sys_request_key(const char __user *_type, } /* do the search */ - key = request_key_and_link(ktype, description, callout_info, + key = request_key_and_link(ktype, description, callout_info, NULL, key_ref_to_ptr(dest_ref), KEY_ALLOC_IN_QUOTA); if (IS_ERR(key)) { diff --git a/security/keys/request_key.c b/security/keys/request_key.c index 58d1efd4fc2c..f573ac189a0a 100644 --- a/security/keys/request_key.c +++ b/security/keys/request_key.c @@ -1,6 +1,6 @@ /* request_key.c: request a key from userspace * - * Copyright (C) 2004-5 Red Hat, Inc. All Rights Reserved. + * Copyright (C) 2004-6 Red Hat, Inc. All Rights Reserved. * Written by David Howells (dhowells@redhat.com) * * This program is free software; you can redistribute it and/or @@ -33,7 +33,8 @@ DECLARE_WAIT_QUEUE_HEAD(request_key_conswq); */ static int call_sbin_request_key(struct key *key, struct key *authkey, - const char *op) + const char *op, + void *aux) { struct task_struct *tsk = current; key_serial_t prkey, sskey; @@ -127,6 +128,7 @@ error_alloc: static struct key *__request_key_construction(struct key_type *type, const char *description, const char *callout_info, + void *aux, unsigned long flags) { request_key_actor_t actor; @@ -164,7 +166,7 @@ static struct key *__request_key_construction(struct key_type *type, actor = call_sbin_request_key; if (type->request_key) actor = type->request_key; - ret = actor(key, authkey, "create"); + ret = actor(key, authkey, "create", aux); if (ret < 0) goto request_failed; @@ -258,8 +260,9 @@ alloc_failed: */ static struct key *request_key_construction(struct key_type *type, const char *description, - struct key_user *user, const char *callout_info, + void *aux, + struct key_user *user, unsigned long flags) { struct key_construction *pcons; @@ -284,7 +287,7 @@ static struct key *request_key_construction(struct key_type *type, } /* see about getting userspace to construct the key */ - key = __request_key_construction(type, description, callout_info, + key = __request_key_construction(type, description, callout_info, aux, flags); error: kleave(" = %p", key); @@ -392,6 +395,7 @@ static void request_key_link(struct key *key, struct key *dest_keyring) struct key *request_key_and_link(struct key_type *type, const char *description, const char *callout_info, + void *aux, struct key *dest_keyring, unsigned long flags) { @@ -399,8 +403,9 @@ struct key *request_key_and_link(struct key_type *type, struct key *key; key_ref_t key_ref; - kenter("%s,%s,%s,%p,%lx", - type->name, description, callout_info, dest_keyring, flags); + kenter("%s,%s,%s,%p,%p,%lx", + type->name, description, callout_info, aux, + dest_keyring, flags); /* search all the process keyrings for a key */ key_ref = search_process_keyrings(type, description, type->match, @@ -433,8 +438,8 @@ struct key *request_key_and_link(struct key_type *type, /* ask userspace (returns NULL if it waited on a key * being constructed) */ key = request_key_construction(type, description, - user, callout_info, - flags); + callout_info, aux, + user, flags); if (key) break; @@ -491,8 +496,27 @@ struct key *request_key(struct key_type *type, const char *callout_info) { return request_key_and_link(type, description, callout_info, NULL, - KEY_ALLOC_IN_QUOTA); + NULL, KEY_ALLOC_IN_QUOTA); } /* end request_key() */ EXPORT_SYMBOL(request_key); + +/*****************************************************************************/ +/* + * request a key with auxiliary data for the upcaller + * - search the process's keyrings + * - check the list of keys being created or updated + * - call out to userspace for a key if supplementary info was provided + */ +struct key *request_key_with_auxdata(struct key_type *type, + const char *description, + const char *callout_info, + void *aux) +{ + return request_key_and_link(type, description, callout_info, aux, + NULL, KEY_ALLOC_IN_QUOTA); + +} /* end request_key_with_auxdata() */ + +EXPORT_SYMBOL(request_key_with_auxdata); -- cgit v1.2.3-59-g8ed1b