From a760147457f890f28bea7d1d894111d3b0db0369 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Love=20H=C3=B6rnquist=20=C3=85strand?= Date: Tue, 25 Mar 2008 12:20:55 +0000 Subject: [PATCH] first implementation of kcm-move-cache git-svn-id: svn://svn.h5l.se/heimdal/trunk/heimdal@22777 ec53bebd-3082-4978-b11e-865c3cabbd6b --- kcm/protocol.c | 83 +++++++++++++++++++++++++++++++++++++++++++++++++- lib/krb5/kcm.c | 28 +++++++++++++++-- lib/krb5/kcm.h | 1 + 3 files changed, 108 insertions(+), 4 deletions(-) diff --git a/kcm/protocol.c b/kcm/protocol.c index e35ea6ebe..0b7181192 100644 --- a/kcm/protocol.c +++ b/kcm/protocol.c @@ -950,6 +950,86 @@ kcm_op_get_ticket(krb5_context context, return ret; } +/* + * Request: + * OldNameZ + * NewNameZ + * + * Repsonse: + * + */ +static krb5_error_code +kcm_op_move_cache(krb5_context context, + kcm_client *client, + kcm_operation opcode, + krb5_storage *request, + krb5_storage *response) +{ + krb5_error_code ret; + kcm_ccache oldid, newid; + char *oldname, *newname; + + ret = krb5_ret_stringz(request, &oldname); + if (ret) + return ret; + + KCM_LOG_REQUEST_NAME(context, client, opcode, oldname); + + ret = krb5_ret_stringz(request, &newname); + if (ret) { + free(oldname); + return ret; + } + + ret = kcm_ccache_resolve_client(context, client, opcode, oldname, &oldid); + if (ret) { + free(oldname); + free(newname); + return ret; + } + + ret = kcm_ccache_resolve_client(context, client, opcode, newname, &newid); + free(newname); + if (ret) { + free(oldname); + kcm_release_ccache(context, &oldid); + return ret; + } + + HEIMDAL_MUTEX_lock(&oldid->mutex); + HEIMDAL_MUTEX_lock(&newid->mutex); + + /* move content */ + { + kcm_ccache_data tmp; + +#define MOVE(n,o,f) { tmp.f = n->f ; n->f = o->f; o->f = tmp.f; } + + MOVE(newid, oldid, flags); + MOVE(newid, oldid, client); + MOVE(newid, oldid, server); + MOVE(newid, oldid, creds); + MOVE(newid, oldid, tkt_life); + MOVE(newid, oldid, renew_life); + MOVE(newid, oldid, key); + MOVE(newid, oldid, key); +#undef MOVE + } + + HEIMDAL_MUTEX_unlock(&oldid->mutex); + HEIMDAL_MUTEX_unlock(&newid->mutex); + + kcm_release_ccache(context, &oldid); + kcm_release_ccache(context, &newid); + + ret = kcm_ccache_destroy_client(context, client, oldname); + + free(oldname); + + return ret; +} + + static struct kcm_op kcm_ops[] = { { "NOOP", kcm_op_noop }, { "GET_NAME", kcm_op_get_name }, @@ -968,7 +1048,8 @@ static struct kcm_op kcm_ops[] = { { "CHOWN", kcm_op_chown }, { "CHMOD", kcm_op_chmod }, { "GET_INITIAL_TICKET", kcm_op_get_initial_ticket }, - { "GET_TICKET", kcm_op_get_ticket } + { "GET_TICKET", kcm_op_get_ticket }, + { "MOVE_CACHE", kcm_op_move_cache } }; diff --git a/lib/krb5/kcm.c b/lib/krb5/kcm.c index e19dda896..3b6daba6a 100644 --- a/lib/krb5/kcm.c +++ b/lib/krb5/kcm.c @@ -832,8 +832,31 @@ kcm_get_version(krb5_context context, static krb5_error_code kcm_move(krb5_context context, krb5_ccache from, krb5_ccache to) { - krb5_set_error_string(context, "kcm_move not implemented"); - return EINVAL; + krb5_error_code ret; + krb5_kcmcache *oldk = KCMCACHE(from); + krb5_kcmcache *newk = KCMCACHE(to); + krb5_storage *request; + + ret = kcm_storage_request(context, KCM_OP_MOVE_CACHE, &request); + if (ret) + return ret; + + ret = krb5_store_stringz(request, oldk->name); + if (ret) { + krb5_storage_free(request); + return ret; + } + + ret = krb5_store_stringz(request, newk->name); + if (ret) { + krb5_storage_free(request); + return ret; + } + + ret = kcm_call(context, k, request, NULL, NULL); + + krb5_storage_free(request); + return ret; } static krb5_error_code @@ -1118,5 +1141,4 @@ _krb5_kcm_get_ticket(krb5_context context, return ret; } - #endif /* HAVE_KCM */ diff --git a/lib/krb5/kcm.h b/lib/krb5/kcm.h index 10dfa440f..3588d8312 100644 --- a/lib/krb5/kcm.h +++ b/lib/krb5/kcm.h @@ -59,6 +59,7 @@ typedef enum kcm_operation { KCM_OP_CHMOD, KCM_OP_GET_INITIAL_TICKET, KCM_OP_GET_TICKET, + KCM_OP_MOVE_CACHE, KCM_OP_MAX } kcm_operation;