From: Jeffrey Altman Date: Fri, 19 May 2006 09:18:37 +0000 (+0000) Subject: Updates of portable CCAPI sources. All code compiles X-Git-Tag: krb5-1.6-alpha1~274^2~21 X-Git-Url: http://git.tremily.us/?a=commitdiff_plain;h=4e824737afa8bb05db07d92a04855149c2fba5d8;p=krb5.git Updates of portable CCAPI sources. All code compiles git-svn-id: svn://anonsvn.mit.edu/krb5/branches/ccapi@18022 dc483132-0cff-0310-8789-dd5450dbe970 --- diff --git a/src/lib/ccapi/client/NTMakefile b/src/lib/ccapi/client/NTMakefile index 09ef9df38..57ff87416 100644 --- a/src/lib/ccapi/client/NTMakefile +++ b/src/lib/ccapi/client/NTMakefile @@ -12,11 +12,11 @@ $(CCAPI_LIB): $(CCAPI_OBJS) CCAPI_DLLFILE = krbcc32.dll - - $(CCAPI_DLLFILE): $(CCAPI_LIB) $(DLLGUILINK) -def:windows\krbcc32.def $(DLLPREP) +all: $(CCAPI_DLLFILE) + clean: del *.obj *.lib diff --git a/src/lib/ccapi/client/cacheapi.c b/src/lib/ccapi/client/cacheapi.c index 2c874bec0..704925dfd 100644 --- a/src/lib/ccapi/client/cacheapi.c +++ b/src/lib/ccapi/client/cacheapi.c @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -47,10 +47,17 @@ #include "ccache.h" #include "ccache_iterator.h" #include "context.h" +#include "cc_rpc.h" #include "msg.h" #include "msg_headers.h" -cc_int32 +/*! \fn cc_initialize + * \brief A function that initializes a ccapi context for the caller. + * \param[out] outContext a cc_context_t pointer to which is assigned the newly created context upon success. + * \param[in] inVersion a cc_int32 that specifies the + */ + +CCACHE_API cc_int32 cc_initialize ( cc_context_t* outContext, cc_int32 inVersion, cc_int32* outSupportedVersion, @@ -60,16 +67,18 @@ cc_initialize ( cc_context_t* outContext, cc_msg_t *request; ccmsg_init_t *request_header; cc_msg_t *response; + cc_uint32 type; ccmsg_init_resp_t *response_header; cc_int32 code; if ((inVersion != ccapi_version_2) && (inVersion != ccapi_version_3) && (inVersion != ccapi_version_4) && - (inVersion != ccapi_version_5)) { + (inVersion != ccapi_version_5) && + (inVersion != ccapi_version_6)) { if (outSupportedVersion != NULL) { - *outSupportedVersion = ccapi_version_5; + *outSupportedVersion = ccapi_version_6; } return ccErrBadAPIVersion; } @@ -78,7 +87,17 @@ cc_initialize ( cc_context_t* outContext, if (request_header == NULL) return ccErrNoMem; - request_header->in_version = inVersion; + /* If the version number is 2, the caller will be passing + * the structure into the v2 compatibility functions which + * in turn will call the v6 functions. Set the version to + * ccapi_version_max since that is what the compatibility + * functions will be expecting. + */ + if (inVersion == ccapi_version_2) + inVersion = ccapi_version_max; + + /* Construct the request */ + request_header->in_version = htonl(inVersion); code = cci_msg_new(ccmsg_INIT, &request); if (code != ccNoError) { @@ -90,17 +109,18 @@ cc_initialize ( cc_context_t* outContext, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { response_header = (ccmsg_init_resp_t *)response->header; - *outSupportedVersion = response_header->out_version; - code = cc_context_int_new(outContext, response_header->out_ctx, response_header->out_version); + *outSupportedVersion = ntohl(response_header->out_version); + code = cc_int_context_new(outContext, ntohl(response_header->out_ctx), ntohl(response_header->out_version)); if (!vendor[0]) { char * string; - code = cci_msg_retrieve_blob(response, response_header->vendor_offset, response_header->vendor_length, &string); + code = cci_msg_retrieve_blob(response, ntohl(response_header->vendor_offset), ntohl(response_header->vendor_length), &string); strncpy(vendor, string, sizeof(vendor)-1); vendor[sizeof(vendor)-1] = '\0'; free(string); diff --git a/src/lib/ccapi/client/cacheapi.def b/src/lib/ccapi/client/cacheapi.def new file mode 100644 index 000000000..c54cc1106 --- /dev/null +++ b/src/lib/ccapi/client/cacheapi.def @@ -0,0 +1,29 @@ +EXPORTS + ; ccapi v3 only exports one function + cc_initialize @14 + + ; ccapi v2 compatibility functions + cc_close @2 + cc_create @3 + cc_destroy @4 + cc_free_NC_info @5 + cc_free_creds @6 + cc_free_name @7 + cc_free_principal @8 + cc_get_NC_info @9 + cc_get_change_time @10 + cc_get_cred_version @11 + cc_get_name @12 + cc_get_principal @13 + cc_lock_request @15 + cc_open @16 + cc_remove_cred @17 + cc_seq_fetch_NCs_begin @18 + cc_seq_fetch_NCs_end @19 + cc_seq_fetch_NCs_next @20 + cc_seq_fetch_creds_begin @21 + cc_seq_fetch_creds_end @22 + cc_seq_fetch_creds_next @23 + cc_set_principal @24 + cc_shutdown @25 + cc_store @26 diff --git a/src/lib/ccapi/client/ccache.c b/src/lib/ccapi/client/ccache.c index 5de3880e4..42064d54d 100644 --- a/src/lib/ccapi/client/ccache.c +++ b/src/lib/ccapi/client/ccache.c @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -49,9 +49,16 @@ #include #include "credentials.h" #include "ccache.h" +#include "cc_rpc.h" #include "msg.h" #include "msg_headers.h" +/* + * cc_int_ccache_new + * + * Input parameters in host order. + */ + cc_int32 cc_int_ccache_new( cc_ccache_t * pccache, cc_handle hctx, cc_handle hccache ) { @@ -97,11 +104,12 @@ cc_int_ccache_new( cc_ccache_t * pccache, cc_handle hctx, cc_handle hccache ) cc_int32 cc_int_ccache_release( cc_ccache_t ccache ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; - ccmsg_ccache_release_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_int_ccache_t int_ccache; + cc_msg_t *request; + ccmsg_ccache_release_t *request_header; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -114,8 +122,8 @@ cc_int_ccache_release( cc_ccache_t ccache ) request_header = (ccmsg_ccache_release_t*)malloc(sizeof(ccmsg_ccache_release_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); code = cci_msg_new(ccmsg_CCACHE_RELEASE, &request); if (code != ccNoError) { @@ -127,10 +135,11 @@ cc_int_ccache_release( cc_ccache_t ccache ) code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -146,11 +155,12 @@ cc_int_ccache_release( cc_ccache_t ccache ) cc_int32 cc_int_ccache_destroy( cc_ccache_t ccache ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; - ccmsg_ccache_destroy_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_int_ccache_t int_ccache; + cc_msg_t *request; + ccmsg_ccache_destroy_t *request_header; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -163,8 +173,8 @@ cc_int_ccache_destroy( cc_ccache_t ccache ) request_header = (ccmsg_ccache_destroy_t*)malloc(sizeof(ccmsg_ccache_destroy_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); code = cci_msg_new(ccmsg_CCACHE_DESTROY, &request); if (code != ccNoError) { @@ -176,10 +186,11 @@ cc_int_ccache_destroy( cc_ccache_t ccache ) code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -194,11 +205,12 @@ cc_int_ccache_destroy( cc_ccache_t ccache ) cc_int32 cc_int_ccache_set_default( cc_ccache_t ccache ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; - ccmsg_ccache_set_default_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_int_ccache_t int_ccache; + cc_msg_t *request; + ccmsg_ccache_set_default_t *request_header; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -211,8 +223,8 @@ cc_int_ccache_set_default( cc_ccache_t ccache ) request_header = (ccmsg_ccache_set_default_t*)malloc(sizeof(ccmsg_ccache_set_default_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); code = cci_msg_new(ccmsg_CCACHE_SET_DEFAULT, &request); if (code != ccNoError) { @@ -224,10 +236,11 @@ cc_int_ccache_set_default( cc_ccache_t ccache ) code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -241,11 +254,12 @@ cc_int32 cc_int_ccache_get_credentials_version( cc_ccache_t ccache, cc_uint32* credentials_version) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; + cc_int_ccache_t int_ccache; + cc_msg_t *request; ccmsg_ccache_get_creds_version_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -258,8 +272,8 @@ cc_int_ccache_get_credentials_version( cc_ccache_t ccache, request_header = (ccmsg_ccache_get_creds_version_t*)malloc(sizeof(ccmsg_ccache_get_creds_version_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); code = cci_msg_new(ccmsg_CCACHE_GET_CREDS_VERSION, &request); if (code != ccNoError) { @@ -271,12 +285,13 @@ cc_int_ccache_get_credentials_version( cc_ccache_t ccache, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { ccmsg_ccache_get_creds_version_resp_t * response_header = (ccmsg_ccache_get_creds_version_resp_t*)response->header; - *credentials_version = response_header->version; + *credentials_version = ntohl(response_header->version); code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -287,14 +302,14 @@ cc_int_ccache_get_credentials_version( cc_ccache_t ccache, } cc_int32 -cc_int_ccache_get_name( cc_ccache_t ccache, - cc_string_t* name ) +cc_int_ccache_get_name( cc_ccache_t ccache, cc_string_t* name ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; + cc_int_ccache_t int_ccache; + cc_msg_t *request; ccmsg_ccache_get_name_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -307,8 +322,8 @@ cc_int_ccache_get_name( cc_ccache_t ccache, request_header = (ccmsg_ccache_get_name_t*)malloc(sizeof(ccmsg_ccache_get_name_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); code = cci_msg_new(ccmsg_CCACHE_GET_NAME, &request); if (code != ccNoError) { @@ -320,10 +335,11 @@ cc_int_ccache_get_name( cc_ccache_t ccache, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { char * string; ccmsg_ccache_get_name_resp_t * response_header = (ccmsg_ccache_get_name_resp_t*)response->header; code = cci_msg_retrieve_blob(response, response_header->name_offset, @@ -345,11 +361,12 @@ cc_int_ccache_get_principal( cc_ccache_t ccache, cc_uint32 credentials_version, cc_string_t* principal ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; + cc_int_ccache_t int_ccache; + cc_msg_t *request; ccmsg_ccache_get_principal_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -362,9 +379,9 @@ cc_int_ccache_get_principal( cc_ccache_t ccache, request_header = (ccmsg_ccache_get_principal_t*)malloc(sizeof(ccmsg_ccache_get_principal_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; - request_header->version = credentials_version; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); + request_header->version = htonl(credentials_version); code = cci_msg_new(ccmsg_CCACHE_GET_PRINCIPAL, &request); if (code != ccNoError) { @@ -376,10 +393,11 @@ cc_int_ccache_get_principal( cc_ccache_t ccache, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { char * string; ccmsg_ccache_get_principal_resp_t * response_header = (ccmsg_ccache_get_principal_resp_t*)response->header; code = cci_msg_retrieve_blob(response, response_header->principal_offset, @@ -401,12 +419,13 @@ cc_int_ccache_set_principal( cc_ccache_t ccache, cc_uint32 credentials_version, const char* principal ) { - cc_uint32 blob_pos; - cc_int_ccache_t int_ccache; - cc_msg_t *request; + cc_uint32 blob_pos; + cc_int_ccache_t int_ccache; + cc_msg_t *request; ccmsg_ccache_set_principal_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -419,9 +438,9 @@ cc_int_ccache_set_principal( cc_ccache_t ccache, request_header = (ccmsg_ccache_set_principal_t*)malloc(sizeof(ccmsg_ccache_set_principal_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; - request_header->version = credentials_version; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); + request_header->version = htonl(credentials_version); code = cci_msg_new(ccmsg_CCACHE_GET_PRINCIPAL, &request); if (code != ccNoError) { @@ -436,17 +455,18 @@ cc_int_ccache_set_principal( cc_ccache_t ccache, return code; } - request_header->principal_offset = blob_pos; - request_header->principal_len = strlen(principal) + 1; + request_header->principal_offset = htonl(blob_pos); + request_header->principal_len = htonl(strlen(principal) + 1); code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ccache_set_principal_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -460,11 +480,12 @@ cc_int32 cc_int_ccache_new_credentials_iterator( cc_ccache_t ccache, cc_credentials_iterator_t* iterator ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; + cc_int_ccache_t int_ccache; + cc_msg_t *request; ccmsg_ccache_creds_iterator_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -477,10 +498,10 @@ cc_int_ccache_new_credentials_iterator( cc_ccache_t ccache, request_header = (ccmsg_ccache_creds_iterator_t*)malloc(sizeof(ccmsg_ccache_creds_iterator_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); - code = cci_msg_new(ccmsg_CCACHE_CREDS_ITERATOR, &request); + code = cci_msg_new(ccmsg_CCACHE_NEW_CREDS_ITERATOR, &request); if (code != ccNoError) { free(request_header); return code; @@ -490,12 +511,14 @@ cc_int_ccache_new_credentials_iterator( cc_ccache_t ccache, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { ccmsg_ccache_creds_iterator_resp_t * response_header = (ccmsg_ccache_creds_iterator_resp_t*)response->header; - code = cc_int_credentials_iterator_new(iterator, response_header->iterator); + code = cc_int_credentials_iterator_new(iterator, int_ccache->ctx, int_ccache->handle, + ntohll(response_header->iterator)); } else { code = ccErrBadInternalMessage; } @@ -508,14 +531,15 @@ cc_int32 cc_int_ccache_store_credentials( cc_ccache_t ccache, const cc_credentials_union* credentials ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; + cc_int_ccache_t int_ccache; + cc_msg_t *request; ccmsg_ccache_store_creds_t *request_header; - cc_msg_t *response; - char *flat_cred = 0; - cc_uint32 flat_cred_len = 0; - cc_uint32 blob_pos; - cc_int32 code; + cc_msg_t *response; + char *flat_cred = 0; + cc_uint32 flat_cred_len = 0; + cc_uint32 blob_pos; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL || credentials == NULL ) return ccErrBadParam; @@ -528,8 +552,8 @@ cc_int_ccache_store_credentials( cc_ccache_t ccache, request_header = (ccmsg_ccache_store_creds_t*)malloc(sizeof(ccmsg_ccache_store_creds_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); code = cci_msg_new(ccmsg_CCACHE_STORE_CREDS, &request); if (code != ccNoError) { @@ -562,18 +586,19 @@ cc_int_ccache_store_credentials( cc_ccache_t ccache, return code; } - request_header->creds_version = credentials->version; - request_header->creds_offset = blob_pos; - request_header->creds_len = flat_cred_len; + request_header->creds_version = htonl(credentials->version); + request_header->creds_offset = htonl(blob_pos); + request_header->creds_len = htonl(flat_cred_len); code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ccache_store_creds_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -588,12 +613,13 @@ cc_int32 cc_int_ccache_remove_credentials( cc_ccache_t ccache, cc_credentials_t credentials ) { - cc_int_ccache_t int_ccache; - cc_int_credentials_t int_creds; - cc_msg_t *request; - ccmsg_ccache_rem_creds_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_int_ccache_t int_ccache; + cc_int_credentials_t int_creds; + cc_msg_t *request; + ccmsg_ccache_rem_creds_t *request_header; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL || credentials == NULL ) return ccErrBadParam; @@ -611,9 +637,9 @@ cc_int_ccache_remove_credentials( cc_ccache_t ccache, if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; - request_header->creds = int_creds->handle; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); + request_header->creds = htonll(int_creds->handle); code = cci_msg_new(ccmsg_CCACHE_REM_CREDS, &request); if (code != ccNoError) { @@ -625,10 +651,11 @@ cc_int_ccache_remove_credentials( cc_ccache_t ccache, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -643,12 +670,13 @@ cc_int32 cc_int_ccache_move( cc_ccache_t source, cc_ccache_t destination ) { - cc_int_ccache_t int_ccache_source; - cc_int_ccache_t int_ccache_dest; - cc_msg_t *request; + cc_int_ccache_t int_ccache_source; + cc_int_ccache_t int_ccache_dest; + cc_msg_t *request; ccmsg_ccache_move_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( source == NULL || destination == NULL ) return ccErrBadParam; @@ -673,18 +701,19 @@ cc_int_ccache_move( cc_ccache_t source, return code; } - request_header->ctx = int_ccache_source->ctx; - request_header->ccache_source = int_ccache_source->handle; - request_header->ccache_dest = int_ccache_dest->handle; + request_header->ctx = htonll(int_ccache_source->ctx); + request_header->ccache_source = htonll(int_ccache_source->handle); + request_header->ccache_dest = htonll(int_ccache_dest->handle); code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ccache_move_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -698,14 +727,16 @@ cc_int_ccache_lock( cc_ccache_t ccache, cc_uint32 lock_type, cc_uint32 block ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; + cc_int_ccache_t int_ccache; + cc_msg_t *request; ccmsg_ccache_lock_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL || - (lock_type != cc_lock_read && lock_type != cc_lock_write) || + (lock_type != cc_lock_read && lock_type != cc_lock_write && + lock_type != cc_lock_upgrade && lock_type != cc_lock_downgrade) || (block != cc_lock_block && block != cc_lock_noblock) ) return ccErrBadParam; @@ -724,17 +755,18 @@ cc_int_ccache_lock( cc_ccache_t ccache, return code; } - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; - request_header->lock_type; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); + request_header->lock_type = htonl(lock_type); code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ccache_lock_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; + code = ntohl(nack_header->err_code); // TODO: if (block == cc_lock_block) ..... } else if (response->type == ccmsg_ACK) { @@ -750,11 +782,12 @@ cc_int_ccache_lock( cc_ccache_t ccache, cc_int32 cc_int_ccache_unlock( cc_ccache_t ccache ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; - ccmsg_ccache_unlock_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_int_ccache_t int_ccache; + cc_msg_t *request; + ccmsg_ccache_unlock_t *request_header; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -774,17 +807,18 @@ cc_int_ccache_unlock( cc_ccache_t ccache ) return code; } - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ccache_unlock_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = htonl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = htonl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -797,13 +831,15 @@ cc_int_ccache_unlock( cc_ccache_t ccache ) cc_int32 cc_int_ccache_get_last_default_time( cc_ccache_t ccache, - cc_time_t* time_offset ) + cc_time* time_offset ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; + cc_int_ccache_t int_ccache; + cc_msg_t *request; ccmsg_ccache_get_last_default_time_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_time64 t64; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -816,8 +852,8 @@ cc_int_ccache_get_last_default_time( cc_ccache_t ccache, request_header = (ccmsg_ccache_get_last_default_time_t*)malloc(sizeof(ccmsg_ccache_get_last_default_time_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); code = cci_msg_new(ccmsg_CCACHE_GET_LAST_DEFAULT_TIME, &request); if (code != ccNoError) { @@ -829,13 +865,16 @@ cc_int_ccache_get_last_default_time( cc_ccache_t ccache, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { ccmsg_ccache_get_last_default_time_resp_t * response_header = (ccmsg_ccache_get_last_default_time_resp_t*)response->header; - *time_offset = response_header->last_default_time; - code = ccNoError; + t64 = ntohll(response_header->last_default_time); + /* TODO: validate that we do not overflow the max value of time_offset */ + *time_offset = t64; + code = ccNoError; } else { code = ccErrBadInternalMessage; } @@ -845,14 +884,15 @@ cc_int_ccache_get_last_default_time( cc_ccache_t ccache, } cc_int32 -cc_int_ccache_get_change_time( cc_ccache_t ccache, - cc_time_t* time ) +cc_int_ccache_get_change_time( cc_ccache_t ccache, cc_time* time ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; + cc_int_ccache_t int_ccache; + cc_msg_t *request; ccmsg_ccache_get_change_time_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_time64 t64; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -865,8 +905,8 @@ cc_int_ccache_get_change_time( cc_ccache_t ccache, request_header = (ccmsg_ccache_get_change_time_t*)malloc(sizeof(ccmsg_ccache_get_change_time_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); code = cci_msg_new(ccmsg_CCACHE_GET_CHANGE_TIME, &request); if (code != ccNoError) { @@ -878,12 +918,15 @@ cc_int_ccache_get_change_time( cc_ccache_t ccache, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { ccmsg_ccache_get_change_time_resp_t * response_header = (ccmsg_ccache_get_change_time_resp_t*)response->header; - *time = response_header->time; + t64 = htonll(response_header->time); + /* TODO: validate that we do not overflow 'time' */ + *time = t64; code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -898,12 +941,13 @@ cc_int_ccache_compare( cc_ccache_t ccache, cc_ccache_t compare_to, cc_uint32* equal ) { - cc_int_ccache_t int_ccache; - cc_int_ccache_t int_compare_to; - cc_msg_t *request; - ccmsg_ccache_compare_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_int_ccache_t int_ccache; + cc_int_ccache_t int_compare_to; + cc_msg_t *request; + ccmsg_ccache_compare_t *request_header; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -918,9 +962,9 @@ cc_int_ccache_compare( cc_ccache_t ccache, request_header = (ccmsg_ccache_compare_t*)malloc(sizeof(ccmsg_ccache_compare_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache1 = int_ccache->handle; - request_header->ccache2 = int_compare_to->handle; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache1 = htonll(int_ccache->handle); + request_header->ccache2 = htonll(int_compare_to->handle); code = cci_msg_new(ccmsg_CCACHE_COMPARE, &request); if (code != ccNoError) { @@ -932,12 +976,13 @@ cc_int_ccache_compare( cc_ccache_t ccache, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { ccmsg_ccache_compare_resp_t * response_header = (ccmsg_ccache_compare_resp_t*)response->header; - *equal = response_header->is_equal; + *equal = ntohl(response_header->is_equal); code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -950,13 +995,14 @@ cc_int_ccache_compare( cc_ccache_t ccache, cc_int32 cc_int_ccache_get_kdc_time_offset( cc_ccache_t ccache, cc_int32 credentials_version, - cc_time_t* time_offset ) + cc_time* time_offset ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; + cc_int_ccache_t int_ccache; + cc_msg_t *request; ccmsg_ccache_get_kdc_time_offset_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -969,9 +1015,9 @@ cc_int_ccache_get_kdc_time_offset( cc_ccache_t ccache, request_header = (ccmsg_ccache_get_kdc_time_offset_t*)malloc(sizeof(ccmsg_ccache_get_kdc_time_offset_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; - request_header->creds_version = credentials_version; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); + request_header->creds_version = htonl(credentials_version); code = cci_msg_new(ccmsg_CCACHE_GET_KDC_TIME_OFFSET, &request); if (code != ccNoError) { @@ -983,12 +1029,13 @@ cc_int_ccache_get_kdc_time_offset( cc_ccache_t ccache, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; + code = ntohl(nack_header->err_code); } else if (response->type == ccmsg_ACK) { ccmsg_ccache_get_kdc_time_offset_resp_t * response_header = (ccmsg_ccache_get_kdc_time_offset_resp_t*)response->header; - *time_offset = response_header->offset; + *time_offset = ntohll(response_header->offset); code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -1001,13 +1048,15 @@ cc_int_ccache_get_kdc_time_offset( cc_ccache_t ccache, cc_int32 cc_int_ccache_set_kdc_time_offset( cc_ccache_t ccache, cc_int32 credentials_version, - cc_time_t time_offset ) + cc_time time_offset ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; + cc_int_ccache_t int_ccache; + cc_msg_t *request; ccmsg_ccache_set_kdc_time_offset_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_int64 t64; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -1020,9 +1069,11 @@ cc_int_ccache_set_kdc_time_offset( cc_ccache_t ccache, request_header = (ccmsg_ccache_set_kdc_time_offset_t*)malloc(sizeof(ccmsg_ccache_set_kdc_time_offset_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; - request_header->creds_version = credentials_version; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); + request_header->creds_version = htonl(credentials_version); + t64 = time_offset; + request_header->offset = htonll(t64); code = cci_msg_new(ccmsg_CCACHE_SET_KDC_TIME_OFFSET, &request); if (code != ccNoError) { @@ -1034,10 +1085,11 @@ cc_int_ccache_set_kdc_time_offset( cc_ccache_t ccache, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -1051,11 +1103,12 @@ cc_int32 cc_int_ccache_clear_kdc_time_offset( cc_ccache_t ccache, cc_int32 credentials_version ) { - cc_int_ccache_t int_ccache; - cc_msg_t *request; + cc_int_ccache_t int_ccache; + cc_msg_t *request; ccmsg_ccache_clear_kdc_time_offset_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -1068,9 +1121,9 @@ cc_int_ccache_clear_kdc_time_offset( cc_ccache_t ccache, request_header = (ccmsg_ccache_clear_kdc_time_offset_t*)malloc(sizeof(ccmsg_ccache_clear_kdc_time_offset_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_ccache->ctx; - request_header->ccache = int_ccache->handle; - request_header->creds_version = credentials_version; + request_header->ctx = htonll(int_ccache->ctx); + request_header->ccache = htonll(int_ccache->handle); + request_header->creds_version = htonl(credentials_version); code = cci_msg_new(ccmsg_CCACHE_CLEAR_KDC_TIME_OFFSET, &request); if (code != ccNoError) { @@ -1082,10 +1135,11 @@ cc_int_ccache_clear_kdc_time_offset( cc_ccache_t ccache, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -1094,5 +1148,3 @@ cc_int_ccache_clear_kdc_time_offset( cc_ccache_t ccache, cci_msg_destroy(response); return code; } - - diff --git a/src/lib/ccapi/client/ccache.h b/src/lib/ccapi/client/ccache.h index e3b3993ee..0a92ebf63 100644 --- a/src/lib/ccapi/client/ccache.h +++ b/src/lib/ccapi/client/ccache.h @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -114,11 +114,11 @@ cc_int_ccache_unlock( cc_ccache_t ccache ); cc_int32 cc_int_ccache_get_last_default_time( cc_ccache_t ccache, - cc_time_t* time ); + cc_time* time ); cc_int32 cc_int_ccache_get_change_time( cc_ccache_t ccache, - cc_time_t* time ); + cc_time* time ); cc_int32 cc_int_ccache_compare( cc_ccache_t ccache, @@ -128,12 +128,12 @@ cc_int_ccache_compare( cc_ccache_t ccache, cc_int32 cc_int_ccache_get_kdc_time_offset( cc_ccache_t ccache, cc_int32 credentials_version, - cc_time_t* time_offset ); + cc_time* time_offset ); cc_int32 cc_int_ccache_set_kdc_time_offset( cc_ccache_t ccache, cc_int32 credentials_version, - cc_time_t time_offset ); + cc_time time_offset ); cc_int32 cc_int_ccache_clear_kdc_time_offset( cc_ccache_t ccache, diff --git a/src/lib/ccapi/client/ccache_iterator.c b/src/lib/ccapi/client/ccache_iterator.c index 03266b1bb..3f3e1675e 100644 --- a/src/lib/ccapi/client/ccache_iterator.c +++ b/src/lib/ccapi/client/ccache_iterator.c @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -47,6 +47,7 @@ #include #include #include "ccache_iterator.h" +#include "cc_rpc.h" #include "msg.h" #include "msg_headers.h" @@ -84,11 +85,12 @@ cc_int_ccache_iterator_new( cc_ccache_iterator_t * piter, cc_int32 cc_int_ccache_iterator_release( cc_ccache_iterator_t iter ) { - cc_int_ccache_iterator_t int_iter; - cc_msg_t *request; + cc_int_ccache_iterator_t int_iter; + cc_msg_t *request; ccmsg_ccache_iterator_release_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( iter == NULL ) @@ -102,8 +104,8 @@ cc_int_ccache_iterator_release( cc_ccache_iterator_t iter ) request_header = (ccmsg_ccache_iterator_release_t*)malloc(sizeof(ccmsg_ccache_iterator_release_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_iter->ctx; - request_header->iterator = int_iter->handle; + request_header->ctx = htonll(int_iter->ctx); + request_header->iterator = htonll(int_iter->handle); code = cci_msg_new(ccmsg_CCACHE_ITERATOR_RELEASE, &request); if (code != ccNoError) { free(request_header); @@ -114,10 +116,11 @@ cc_int_ccache_iterator_release( cc_ccache_iterator_t iter ) code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -134,11 +137,12 @@ cc_int32 cc_int_ccache_iterator_next( cc_ccache_iterator_t iter, cc_ccache_t * ccache ) { - cc_int_ccache_iterator_t int_iter; - cc_msg_t *request; + cc_int_ccache_iterator_t int_iter; + cc_msg_t *request; ccmsg_ccache_iterator_next_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( ccache == NULL ) return ccErrBadParam; @@ -151,8 +155,8 @@ cc_int_ccache_iterator_next( cc_ccache_iterator_t iter, request_header = (ccmsg_ccache_iterator_next_t*)malloc(sizeof(ccmsg_ccache_iterator_next_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_iter->ctx; - request_header->iterator = int_iter->handle; + request_header->ctx = htonll(int_iter->ctx); + request_header->iterator = htonll(int_iter->handle); code = cci_msg_new(ccmsg_CCACHE_ITERATOR_NEXT, &request); if (code != ccNoError) { @@ -164,12 +168,63 @@ cc_int_ccache_iterator_next( cc_ccache_iterator_t iter, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + } else if (type == ccmsg_ACK) { ccmsg_ccache_iterator_next_resp_t * response_header = (ccmsg_ccache_iterator_next_resp_t*)response->header; - code = cc_ccache_new(ccache, int_iter->ctx, response_header->ccache); + code = cc_int_ccache_new(ccache, int_iter->ctx, ntohll(response_header->ccache)); + } else { + code = ccErrBadInternalMessage; + } + cci_msg_destroy(request); + cci_msg_destroy(response); + return code; +} + +cc_int32 +cc_int_ccache_iterator_clone( cc_ccache_iterator_t iter, + cc_ccache_iterator_t * new_iter ) +{ + cc_int_ccache_iterator_t int_iter; + cc_msg_t *request; + ccmsg_ccache_iterator_clone_t *request_header; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; + + if ( iter == NULL || new_iter == NULL ) + return ccErrBadParam; + + int_iter = (cc_int_ccache_iterator_t)iter; + + if ( int_iter->magic != CC_CCACHE_ITER_MAGIC ) + return ccErrInvalidCCacheIterator; + + request_header = (ccmsg_ccache_iterator_clone_t*)malloc(sizeof(ccmsg_ccache_iterator_clone_t)); + if (request_header == NULL) + return ccErrNoMem; + request_header->ctx = htonll(int_iter->ctx); + request_header->iterator = htonll(int_iter->handle); + + code = cci_msg_new(ccmsg_CCACHE_ITERATOR_CLONE, &request); + if (code != ccNoError) { + free(request_header); + return code; + } + + code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ccache_iterator_clone_t)); + + code = cci_perform_rpc(request, &response); + + type = ntohl(response->type); + if (type == ccmsg_NACK) { + ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { + ccmsg_ccache_iterator_clone_resp_t * response_header = (ccmsg_ccache_iterator_clone_resp_t*)response->header; + code = cc_int_ccache_iterator_new(new_iter, int_iter->ctx, ntohll(response_header->iterator)); } else { code = ccErrBadInternalMessage; } diff --git a/src/lib/ccapi/client/ccache_iterator.h b/src/lib/ccapi/client/ccache_iterator.h index c55d72ee6..5a390b82e 100644 --- a/src/lib/ccapi/client/ccache_iterator.h +++ b/src/lib/ccapi/client/ccache_iterator.h @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -73,6 +73,10 @@ cc_int32 cc_int_ccache_iterator_next( cc_ccache_iterator_t iter, cc_ccache_t * ccache ); +cc_int32 +cc_int_ccache_iterator_clone( cc_ccache_iterator_t iter, + cc_ccache_iterator_t * iter_new ); + cc_int32 cc_int_ccache_iterator_set_repeat_count( cc_int_ccache_iterator_t iter, cc_uint32 count ); diff --git a/src/lib/ccapi/client/ccapiv2.c b/src/lib/ccapi/client/ccapiv2.c new file mode 100644 index 000000000..ffbb589a2 --- /dev/null +++ b/src/lib/ccapi/client/ccapiv2.c @@ -0,0 +1,286 @@ +/* $Copyright: + * + * Copyright 1998-2006 by the Massachusetts Institute of Technology. + * + * All rights reserved. + * + * Export of this software from the United States of America may require a + * specific license from the United States Government. It is the + * responsibility of any person or organization contemplating export to + * obtain such a license before exporting. + * + * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute + * this software and its documentation for any purpose and without fee is + * hereby granted, provided that the above copyright notice appear in all + * copies and that both that copyright notice and this permission notice + * appear in supporting documentation, and that the name of M.I.T. not be + * used in advertising or publicity pertaining to distribution of the + * software without specific, written prior permission. Furthermore if you + * modify this software you must label your software as modified software + * and not distribute it in such a fashion that it might be confused with + * the original MIT software. M.I.T. makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. + * + * Individual source code files are copyright MIT, Cygnus Support, + * OpenVision, Oracle, Sun Soft, FundsXpress, and others. + * + * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, + * and Zephyr are trademarks of the Massachusetts Institute of Technology + * (MIT). No commercial use of these trademarks may be made without prior + * written permission of MIT. + * + * "Commercial use" means use of a name in a product or other for-profit + * manner. It does NOT prevent a commercial firm from referring to the MIT + * trademarks in order to convey information (although in doing so, + * recognition of their trademark status should be given). + * $ + */ +/* + * This is backwards compatibility for CCache API v2 clients to be able to run + * against the CCache API v3 library + */ + +#include "CredentialsCache2.h" + +#ifdef __cplusplus +extern "C" { +#endif /* __cplusplus */ + +CCACHE_API cc_int32 cc_shutdown ( + apiCB** ioContext) +{ + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_get_NC_info ( + apiCB* inContext, + infoNC*** outInfo) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_get_change_time ( + apiCB* inContext, + cc_time_t* outTime) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_open ( + apiCB* inContext, + const char* inName, + cc_int32 inVersion, + cc_uint32 inFlags, + ccache_p** outCCache) +{ + if (inVersion != CC_CRED_V4 && inVersion != CC_CRED_V5) + return CC_ERR_CRED_VERSION; + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_create ( + apiCB* inContext, + const char* inName, + const char* inPrincipal, + cc_int32 inVersion, + cc_uint32 inFlags, + ccache_p** outCCache) +{ + if (inVersion != CC_CRED_V4 && inVersion != CC_CRED_V5) + return CC_ERR_CRED_VERSION; + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_close ( + apiCB* inContext, + ccache_p** ioCCache) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_destroy ( + apiCB* inContext, + ccache_p** ioCCache) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_seq_fetch_NCs_begin ( + apiCB* inContext, + ccache_cit** outIterator) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_seq_fetch_NCs_next ( + apiCB* inContext, + ccache_p** outCCache, + ccache_cit* inIterator) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_seq_fetch_NCs_end ( + apiCB* inContext, + ccache_cit** ioIterator) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_get_name ( + apiCB* inContext, + ccache_p* inCCache, + char** outName) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_get_cred_version ( + apiCB* inContext, + ccache_p* inCCache, + cc_int32* outVersion) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_set_principal ( + apiCB* inContext, + ccache_p* inCCache, + cc_int32 inVersion, + char* inPrincipal) +{ + if (inVersion != CC_CRED_V4 && inVersion != CC_CRED_V5) + return CC_ERR_CRED_VERSION; + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_get_principal ( + apiCB* inContext, + ccache_p* inCCache, + char** outPrincipal) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_store ( + apiCB* inContext, + ccache_p* inCCache, + cred_union inCredentials) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_remove_cred ( + apiCB* inContext, + ccache_p* inCCache, + cred_union inCredentials) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_seq_fetch_creds_begin ( + apiCB* inContext, + const ccache_p* inCCache, + ccache_cit** outIterator) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_seq_fetch_creds_next ( + apiCB* inContext, + cred_union** outCreds, + ccache_cit* inIterator) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_seq_fetch_creds_end ( + apiCB* inContext, + ccache_cit** ioIterator) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_free_principal ( + apiCB* inContext, + char** ioPrincipal) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_free_name ( + apiCB* inContext, + char** ioName) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_free_creds ( + apiCB* inContext, + cred_union** creds) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + +CCACHE_API cc_int32 cc_free_NC_info ( + apiCB* inContext, + infoNC*** ioInfo) +{ + + /* replace this return value when the function is implemented */ + return CC_NOT_SUPP; +} + + +#ifdef __cplusplus +} +#endif /* __cplusplus */ + diff --git a/src/lib/ccapi/client/context.c b/src/lib/ccapi/client/context.c index 86c41b8e7..efac3020c 100644 --- a/src/lib/ccapi/client/context.c +++ b/src/lib/ccapi/client/context.c @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -47,9 +47,15 @@ #include #include #include "context.h" +#include "cc_rpc.h" #include "msg.h" #include "msg_headers.h" +/* cc_int_context_new + * + * input parameters (handle, version) are in host order + */ + cc_int32 cc_int_context_new( cc_context_t * pcontext, cc_handle handle, cc_uint32 version ) { @@ -87,11 +93,13 @@ cc_int_context_new( cc_context_t * pcontext, cc_handle handle, cc_uint32 version cc_int32 cc_int_context_release( cc_context_t context ) { - cc_int_context_t int_context; - cc_msg_t *request; + cc_int_context_t int_context; + cc_msg_t *request; ccmsg_ctx_release_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_time64 t64; + cc_int32 code; if ( context == NULL ) return ccErrBadParam; @@ -104,7 +112,7 @@ cc_int_context_release( cc_context_t context ) request_header = (ccmsg_ctx_release_t*)malloc(sizeof(ccmsg_ctx_release_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_context->handle; + request_header->ctx = htonl(int_context->handle); code = cci_msg_new(ccmsg_CTX_RELEASE, &request); if (code != ccNoError) { @@ -116,10 +124,11 @@ cc_int_context_release( cc_context_t context ) code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -133,14 +142,16 @@ cc_int_context_release( cc_context_t context ) cc_int32 cc_int_context_get_change_time( cc_context_t context, - cc_time_t* time) + cc_time* time) { - cc_int_context_t int_context; - cc_msg_t *request; + cc_int_context_t int_context; + cc_msg_t *request; ccmsg_ctx_get_change_time_t *request_header; - cc_msg_t *response; + cc_msg_t *response; ccmsg_ctx_get_change_time_resp_t *response_header; - cc_int32 code; + cc_time64 t64; + cc_uint32 type; + cc_int32 code; if ( context == NULL || time == NULL ) return ccErrBadParam; @@ -153,7 +164,7 @@ cc_int_context_get_change_time( cc_context_t context, request_header = (ccmsg_ctx_get_change_time_t*)malloc(sizeof(ccmsg_ctx_get_change_time_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_context->handle; + request_header->ctx = htonll(int_context->handle); code = cci_msg_new(ccmsg_CTX_GET_CHANGE_TIME, &request); if (code != ccNoError) { @@ -165,12 +176,15 @@ cc_int_context_get_change_time( cc_context_t context, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; + code = ntohl(nack_header->err_code); } else if (response->type == ccmsg_ACK) { response_header = (ccmsg_ctx_get_change_time_resp_t*)response->header; - *time = response_header->time; + t64 = ntohll(response_header->time); + /* TODO: validate that value is not greater than can fit in cc_time */ + *time = (cc_time)t64; code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -184,12 +198,13 @@ cc_int32 cc_int_context_get_default_ccache_name( cc_context_t context, cc_string_t* name ) { - cc_int_context_t int_context; - cc_msg_t *request; + cc_int_context_t int_context; + cc_msg_t *request; ccmsg_ctx_get_default_ccache_name_t *request_header; - cc_msg_t *response; + cc_msg_t *response; ccmsg_ctx_get_default_ccache_name_resp_t *response_header; - cc_int32 code; + cc_uint32 type; + cc_int32 code; if ( context == NULL || name == NULL ) return ccErrBadParam; @@ -202,7 +217,7 @@ cc_int_context_get_default_ccache_name( cc_context_t context, request_header = (ccmsg_ctx_get_default_ccache_name_t*)malloc(sizeof(ccmsg_ctx_get_default_ccache_name_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_context->handle; + request_header->ctx = htonll(int_context->handle); code = cci_msg_new(ccmsg_CTX_GET_DEFAULT_CCACHE_NAME, &request); if (code != ccNoError) { @@ -214,10 +229,11 @@ cc_int_context_get_default_ccache_name( cc_context_t context, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { char * string; response_header = (ccmsg_ctx_get_default_ccache_name_resp_t*)response->header; code = cci_msg_retrieve_blob(response, response_header->name_offset, @@ -244,7 +260,8 @@ cc_int_context_compare( cc_context_t context, ccmsg_ctx_compare_t *request_header; cc_msg_t *response; ccmsg_ctx_compare_resp_t *response_header; - cc_int32 code; + cc_uint32 type; + cc_int32 code; if ( context == NULL || compare_to == NULL || equal == NULL ) @@ -260,8 +277,8 @@ cc_int_context_compare( cc_context_t context, request_header = (ccmsg_ctx_compare_t*)malloc(sizeof(ccmsg_ctx_compare_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx1 = int_context->handle; - request_header->ctx2 = int_compare_to->handle; + request_header->ctx1 = htonl(int_context->handle); + request_header->ctx2 = htonl(int_compare_to->handle); code = cci_msg_new(ccmsg_CTX_COMPARE, &request); if (code != ccNoError) { @@ -273,12 +290,13 @@ cc_int_context_compare( cc_context_t context, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { response_header = (ccmsg_ctx_compare_resp_t*)response->header; - *equal = response_header->is_equal; + *equal = ntohl(response_header->is_equal); code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -293,12 +311,13 @@ cc_int32 cc_int_context_new_ccache_iterator( cc_context_t context, cc_ccache_iterator_t* iterator ) { - cc_int_context_t int_context; - cc_msg_t *request; + cc_int_context_t int_context; + cc_msg_t *request; ccmsg_ctx_new_ccache_iterator_t *request_header; - cc_msg_t *response; + cc_msg_t *response; ccmsg_ctx_new_ccache_iterator_resp_t *response_header; - cc_int32 code; + cc_uint32 type; + cc_int32 code; if ( context == NULL || iterator == NULL ) return ccErrBadParam; @@ -311,7 +330,7 @@ cc_int_context_new_ccache_iterator( cc_context_t context, request_header = (ccmsg_ctx_new_ccache_iterator_t*)malloc(sizeof(ccmsg_ctx_new_ccache_iterator_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_context->handle; + request_header->ctx = htonll(int_context->handle); code = cci_msg_new(ccmsg_CTX_NEW_CCACHE_ITERATOR, &request); if (code != ccNoError) { @@ -323,12 +342,14 @@ cc_int_context_new_ccache_iterator( cc_context_t context, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { response_header = (ccmsg_ctx_new_ccache_iterator_resp_t*)response->header; - code = cc_int_ccache_iterator_new(iterator, int_context->handle, response_header->iterator); + code = cc_int_ccache_iterator_new(iterator, int_context->handle, + ntohll(response_header->iterator)); } else { code = ccErrBadInternalMessage; } @@ -342,13 +363,14 @@ cc_int_context_open_ccache( cc_context_t context, const char* name, cc_ccache_t* ccache ) { - cc_uint32 blob_pos; - cc_int_context_t int_context; - cc_msg_t *request; + cc_uint32 blob_pos; + cc_int_context_t int_context; + cc_msg_t *request; ccmsg_ccache_open_t *request_header; - cc_msg_t *response; + cc_msg_t *response; ccmsg_ccache_open_resp_t *response_header; - cc_int32 code; + cc_uint32 type; + cc_int32 code; if ( context == NULL || name == NULL || ccache == NULL ) return ccErrBadParam; @@ -362,7 +384,7 @@ cc_int_context_open_ccache( cc_context_t context, if (request_header == NULL) return ccErrNoMem; - code = cci_msg_new(ccmsg_CCACHE_OPEN, &request); + code = cci_msg_new(ccmsg_CTX_CCACHE_OPEN, &request); if (code != ccNoError) { free(request_header); return code; @@ -375,20 +397,21 @@ cc_int_context_open_ccache( cc_context_t context, return code; } - request_header->ctx = int_context->handle; - request_header->name_offset = blob_pos; - request_header->name_len = strlen(name) + 1; + request_header->ctx = htonll(int_context->handle); + request_header->name_offset = htonl(blob_pos); + request_header->name_len = htonl(strlen(name) + 1); code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ccache_open_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { response_header = (ccmsg_ccache_open_resp_t*)response->header; - code = cc_cache_new(ccache, response_header->ccache); + code = cc_int_cache_new(ccache, int_context->handle, ntohll(response_header->ccache)); } else { code = ccErrBadInternalMessage; } @@ -401,12 +424,13 @@ cc_int32 cc_int_context_open_default_ccache( cc_context_t context, cc_ccache_t* ccache) { - cc_int_context_t int_context; - cc_msg_t *request; + cc_int_context_t int_context; + cc_msg_t *request; ccmsg_ccache_open_default_t *request_header; - cc_msg_t *response; + cc_msg_t *response; ccmsg_ccache_open_resp_t *response_header; - cc_int32 code; + cc_uint32 type; + cc_int32 code; if ( context == NULL || ccache == NULL ) return ccErrBadParam; @@ -420,24 +444,25 @@ cc_int_context_open_default_ccache( cc_context_t context, if (request_header == NULL) return ccErrNoMem; - code = cci_msg_new(ccmsg_CCACHE_OPEN_DEFAULT, &request); + code = cci_msg_new(ccmsg_CTX_CCACHE_OPEN_DEFAULT, &request); if (code != ccNoError) { free(request_header); return code; } - request_header->ctx = int_context->handle; + request_header->ctx = htonll(int_context->handle); code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ccache_open_default_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { response_header = (ccmsg_ccache_open_resp_t*)response->header; - code = cc_cache_new(ccache, response_header->ccache); + code = cc_int_cache_new(ccache, int_context->handle, ntohll(response_header->ccache)); } else { code = ccErrBadInternalMessage; } @@ -453,13 +478,14 @@ cc_int_context_create_ccache( cc_context_t context, const char* principal, cc_ccache_t* ccache ) { - cc_uint32 blob_pos; - cc_int_context_t int_context; - cc_msg_t *request; + cc_uint32 blob_pos; + cc_int_context_t int_context; + cc_msg_t *request; ccmsg_ccache_create_t *request_header; - cc_msg_t *response; + cc_msg_t *response; ccmsg_ccache_create_resp_t *response_header; - cc_int32 code; + cc_uint32 type; + cc_int32 code; if ( context == NULL || name == NULL || cred_vers == 0 || cred_vers > cc_credentials_v4_v5 || @@ -475,7 +501,7 @@ cc_int_context_create_ccache( cc_context_t context, if (request_header == NULL) return ccErrNoMem; - code = cci_msg_new(ccmsg_CCACHE_CREATE, &request); + code = cci_msg_new(ccmsg_CTX_CCACHE_CREATE, &request); if (code != ccNoError) { free(request_header); return code; @@ -488,10 +514,10 @@ cc_int_context_create_ccache( cc_context_t context, return code; } - request_header->ctx = int_context->handle; - request_header->version = cred_vers; - request_header->name_offset = blob_pos; - request_header->name_len = strlen(name) + 1; + request_header->ctx = htonll(int_context->handle); + request_header->version = htonl(cred_vers); + request_header->name_offset = htonl(blob_pos); + request_header->name_len = htonl(strlen(name) + 1); code = cci_msg_add_data_blob(request, (void *)principal, strlen(principal) + 1, &blob_pos); if (code != ccNoError) { @@ -499,19 +525,20 @@ cc_int_context_create_ccache( cc_context_t context, free(request_header); return code; } - request_header->principal_offset = blob_pos; - request_header->principal_len = strlen(principal) + 1; + request_header->principal_offset = htonl(blob_pos); + request_header->principal_len = htonl(strlen(principal) + 1); code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ccache_create_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { response_header = (ccmsg_ccache_create_resp_t*)response->header; - code = cc_cache_new(ccache, response_header->ccache); + code = cc_int_cache_new(ccache, int_context->handle, ntohll(response_header->ccache)); } else { code = ccErrBadInternalMessage; } @@ -526,13 +553,14 @@ cc_int_context_create_default_ccache( cc_context_t context, const char* principal, cc_ccache_t* ccache ) { - cc_uint32 blob_pos; - cc_int_context_t int_context; - cc_msg_t *request; + cc_uint32 blob_pos; + cc_int_context_t int_context; + cc_msg_t *request; ccmsg_ccache_create_default_t *request_header; - cc_msg_t *response; + cc_msg_t *response; ccmsg_ccache_create_resp_t *response_header; - cc_int32 code; + cc_uint32 type; + cc_int32 code; if ( context == NULL || cred_vers == 0 || cred_vers > cc_credentials_v4_v5 || @@ -548,14 +576,14 @@ cc_int_context_create_default_ccache( cc_context_t context, if (request_header == NULL) return ccErrNoMem; - code = cci_msg_new(ccmsg_CCACHE_CREATE_DEFAULT, &request); + code = cci_msg_new(ccmsg_CTX_CCACHE_CREATE_DEFAULT, &request); if (code != ccNoError) { free(request_header); return code; } - request_header->ctx = int_context->handle; - request_header->version = cred_vers; + request_header->ctx = htonll(int_context->handle); + request_header->version = htonl(cred_vers); code = cci_msg_add_data_blob(request, (void *)principal, strlen(principal) + 1, &blob_pos); if (code != ccNoError) { @@ -563,19 +591,20 @@ cc_int_context_create_default_ccache( cc_context_t context, free(request_header); return code; } - request_header->principal_offset = blob_pos; - request_header->principal_len = strlen(principal) + 1; + request_header->principal_offset = htonl(blob_pos); + request_header->principal_len = htonl(strlen(principal) + 1); code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ccache_create_default_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { response_header = (ccmsg_ccache_create_resp_t*)response->header; - code = cc_cache_new(ccache, response_header->ccache); + code = cc_int_cache_new(ccache, int_context->handle, ntohll(response_header->ccache)); } else { code = ccErrBadInternalMessage; } @@ -590,13 +619,14 @@ cc_int_context_create_new_ccache( cc_context_t context, const char* principal, cc_ccache_t* ccache ) { - cc_uint32 blob_pos; - cc_int_context_t int_context; - cc_msg_t *request; + cc_uint32 blob_pos; + cc_int_context_t int_context; + cc_msg_t *request; ccmsg_ccache_create_unique_t *request_header; - cc_msg_t *response; + cc_msg_t *response; ccmsg_ccache_create_resp_t *response_header; - cc_int32 code; + cc_uint32 type; + cc_int32 code; if ( context == NULL || cred_vers == 0 || cred_vers > cc_credentials_v4_v5 || @@ -612,14 +642,14 @@ cc_int_context_create_new_ccache( cc_context_t context, if (request_header == NULL) return ccErrNoMem; - code = cci_msg_new(ccmsg_CCACHE_CREATE_UNIQUE, &request); + code = cci_msg_new(ccmsg_CTX_CCACHE_CREATE_UNIQUE, &request); if (code != ccNoError) { free(request_header); return code; } - request_header->ctx = int_context->handle; - request_header->version = cred_vers; + request_header->ctx = htonll(int_context->handle); + request_header->version = htonl(cred_vers); code = cci_msg_add_data_blob(request, (void *)principal, strlen(principal) + 1, &blob_pos); if (code != ccNoError) { @@ -627,19 +657,20 @@ cc_int_context_create_new_ccache( cc_context_t context, free(request_header); return code; } - request_header->principal_offset = blob_pos; - request_header->principal_len = strlen(principal) + 1; + request_header->principal_offset = htonl(blob_pos); + request_header->principal_len = htonl(strlen(principal) + 1); code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ccache_create_unique_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = htonl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { response_header = (ccmsg_ccache_create_resp_t*)response-> header; - code = cc_cache_new(ccache, response_header->ccache); + code = cc_int_cache_new(ccache, int_context->handle, ntohll(response_header->ccache)); } else { code = ccErrBadInternalMessage; } @@ -653,14 +684,16 @@ cc_int_context_lock( cc_context_t context, cc_uint32 lock_type, cc_uint32 block ) { - cc_int_context_t int_context; - cc_msg_t *request; - ccmsg_ctx_lock_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_int_context_t int_context; + cc_msg_t *request; + ccmsg_ctx_lock_t *request_header; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( context == NULL || - (lock_type != cc_lock_read && lock_type != cc_lock_write) || + (lock_type != cc_lock_read && lock_type != cc_lock_write && + lock_type != cc_lock_upgrade && lock_type != cc_lock_downgrade) || (block != cc_lock_block && block != cc_lock_noblock) ) return ccErrBadParam; @@ -679,19 +712,20 @@ cc_int_context_lock( cc_context_t context, return code; } - request_header->ctx = int_context->handle; - request_header->lock_type; + request_header->ctx = htonll(int_context->handle); + request_header->lock_type = htonl(lock_type); code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ctx_lock_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; + code = ntohl(nack_header->err_code); // TODO: if (block == cc_lock_block) ..... - } else if (response->type == ccmsg_ACK) { + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -704,11 +738,12 @@ cc_int_context_lock( cc_context_t context, cc_int32 cc_int_context_unlock( cc_context_t context ) { - cc_int_context_t int_context; - cc_msg_t *request; + cc_int_context_t int_context; + cc_msg_t *request; ccmsg_ctx_unlock_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( context == NULL ) return ccErrBadParam; @@ -728,16 +763,17 @@ cc_int_context_unlock( cc_context_t context ) return code; } - request_header->ctx = int_context->handle; + request_header->ctx = htonll(int_context->handle); code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ctx_unlock_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -754,20 +790,21 @@ cc_int_context_clone( cc_context_t inContext, cc_int32* supportedVersion, char const** vendor ) { - cc_int_context_t int_context, new_context; - static char vendor_st[128] = ""; - cc_msg_t *request; - ccmsg_clone_t *request_header; - cc_msg_t *response; - ccmsg_clone_resp_t *response_header; - cc_int32 code; + cc_int_context_t int_context, new_context; + static char vendor_st[128] = ""; + cc_msg_t *request; + ccmsg_ctx_clone_t *request_header; + cc_msg_t *response; + ccmsg_ctx_clone_resp_t *response_header; + cc_uint32 type; + cc_int32 code; if ( inContext == NULL || outContext == NULL || supportedVersion == NULL ) return ccErrBadParam; - int_context = (cc_int_context_t)context; + int_context = (cc_int_context_t)inContext; if ( int_context->magic != CC_CONTEXT_MAGIC ) return ccErrInvalidContext; @@ -775,20 +812,21 @@ cc_int_context_clone( cc_context_t inContext, if ((requestedVersion != ccapi_version_2) && (requestedVersion != ccapi_version_3) && (requestedVersion != ccapi_version_4) && - (requestedVersion != ccapi_version_5)) { + (requestedVersion != ccapi_version_5) && + (requestedVersion != ccapi_version_6)) { if (supportedVersion != NULL) { - *supportedVersion = ccapi_version_5; + *supportedVersion = ccapi_version_max; } return ccErrBadAPIVersion; } - request_header = (ccmsg_clone_t*)malloc(sizeof(ccmsg_clone_t)); + request_header = (ccmsg_ctx_clone_t*)malloc(sizeof(ccmsg_ctx_clone_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_context->handle; - request_header->in_version = requestedVersion; + request_header->ctx = htonll(int_context->handle); + request_header->in_version = htonl(requestedVersion); code = cci_msg_new(ccmsg_INIT, &request); if (code != ccNoError) { @@ -796,21 +834,22 @@ cc_int_context_clone( cc_context_t inContext, return code; } - code = cci_msg_add_header(request, request_header, sizeof(ccmsg_init_t)); + code = cci_msg_add_header(request, request_header, sizeof(ccmsg_ctx_clone_t)); code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { - response_header = (ccmsg_clone_resp_t *)response->header; - *supportedVersion = response_header->out_version; - code = cc_int_context_new(outContext, response_header->out_ctx, response_header->out_version); + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { + response_header = (ccmsg_ctx_clone_resp_t *)response->header; + *supportedVersion = ntohl(response_header->out_version); + code = cc_int_context_new(outContext, ntohll(response_header->out_ctx), nthol(response_header->out_version)); if (!vendor_st[0]) { char * string; - code = cci_msg_retrieve_blob(response, response_header->vendor_offset, response_header->vendor_length, &string); + code = cci_msg_retrieve_blob(response, ntohl(response_header->vendor_offset), ntohl(response_header->vendor_length), &string); strncpy(vendor_st, string, sizeof(vendor_st)-1); vendor_st[sizeof(vendor_st)-1] = '\0'; free(string); diff --git a/src/lib/ccapi/client/context.h b/src/lib/ccapi/client/context.h index cd5ca678d..6ff113a26 100644 --- a/src/lib/ccapi/client/context.h +++ b/src/lib/ccapi/client/context.h @@ -66,7 +66,7 @@ cc_int_context_release( cc_context_t context ); cc_int32 cc_int_context_get_change_time( cc_context_t context, - cc_time_t* time); + cc_time* time); cc_int32 cc_int_context_get_default_ccache_name( cc_context_t context, diff --git a/src/lib/ccapi/client/credentials.c b/src/lib/ccapi/client/credentials.c index b0a3df2b7..8b8867689 100644 --- a/src/lib/ccapi/client/credentials.c +++ b/src/lib/ccapi/client/credentials.c @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -159,23 +159,23 @@ cc_int_credentials_release( cc_credentials_t creds ) cc_int32 cc_int_credentials_compare( cc_credentials_t credentials, - cc_credentials_t compare_to, - cc_uint32* equal ) + cc_credentials_t compare_to, + cc_uint32* equal ) { cc_int_credentials_t int_credentials; cc_int_credentials_t int_compare_to; if ( credentials == NULL || compare_to == NULL || equal == NULL ) return ccErrBadParam; - + int_credentials = (cc_int_credentials_t)credentials; + int_compare_to = (cc_int_credentials_t)compare_to; + if ( int_credentials->magic != CC_CREDS_MAGIC || int_compare_to->magic != CC_CREDS_MAGIC ) return ccErrInvalidCredentials; - int_credentials = (cc_int_credentials_t)credentials; - int_compare_to = (cc_int_credentials_t)compare_to; - *equal = (int_credentials->handle == int_compare_to->handle); + return ccNoError; } diff --git a/src/lib/ccapi/client/credentials.h b/src/lib/ccapi/client/credentials.h index 320c61825..dfd589f32 100644 --- a/src/lib/ccapi/client/credentials.h +++ b/src/lib/ccapi/client/credentials.h @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -84,8 +84,8 @@ cci_creds_v5_marshall( cc_credentials_v5_t * creds, cc_int32 cci_creds_v4_unmarshall( char * flat, - cc_uint32 len, - cc_credentials_union * creds); + cc_uint32 len, + cc_credentials_union * creds); cc_int32 cci_creds_v5_unmarshall( char * flat, diff --git a/src/lib/ccapi/client/credentials_iterator.c b/src/lib/ccapi/client/credentials_iterator.c index b7333daf3..bae60ffdf 100644 --- a/src/lib/ccapi/client/credentials_iterator.c +++ b/src/lib/ccapi/client/credentials_iterator.c @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -47,6 +47,7 @@ #include #include #include "credentials_iterator.h" +#include "cc_rpc.h" #include "msg.h" #include "msg_headers.h" @@ -74,6 +75,7 @@ cc_int_credentials_iterator_new( cc_credentials_iterator_t * piter, iter->functions->release = cc_int_credentials_iterator_release; iter->functions->next = cc_int_credentials_iterator_next; + iter->functions->clone = cc_int_credentials_iterator_clone; iter->magic = CC_CREDS_ITER_MAGIC; iter->ctx = ctx; iter->ccache = ccache; @@ -87,10 +89,11 @@ cc_int32 cc_int_credentials_iterator_release( cc_credentials_iterator_t iter ) { cc_int_credentials_iterator_t int_iter; - cc_msg_t *request; + cc_msg_t *request; ccmsg_creds_iterator_release_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( iter == NULL ) return ccErrBadParam; @@ -103,9 +106,10 @@ cc_int_credentials_iterator_release( cc_credentials_iterator_t iter ) request_header = (ccmsg_creds_iterator_release_t*)malloc(sizeof(ccmsg_creds_iterator_release_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_iter->ctx; - request_header->ccache = int_iter->ccache; - request_header->iterator = int_iter->handle; + request_header->ctx = htonll(int_iter->ctx); + request_header->ccache = htonll(int_iter->ccache); + request_header->iterator = htonll(int_iter->handle); + code = cci_msg_new(ccmsg_CREDS_ITERATOR_RELEASE, &request); if (code != ccNoError) { free(request_header); @@ -116,10 +120,11 @@ cc_int_credentials_iterator_release( cc_credentials_iterator_t iter ) code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = htonl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = htonl(nack_header->err_code); + } else if (type == ccmsg_ACK) { code = ccNoError; } else { code = ccErrBadInternalMessage; @@ -137,10 +142,11 @@ cc_int_credentials_iterator_next( cc_credentials_iterator_t iter, cc_credentials_t * credentials ) { cc_int_credentials_iterator_t int_iter; - cc_msg_t *request; + cc_msg_t *request; ccmsg_creds_iterator_next_t *request_header; - cc_msg_t *response; - cc_int32 code; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; if ( credentials == NULL ) return ccErrBadParam; @@ -153,9 +159,9 @@ cc_int_credentials_iterator_next( cc_credentials_iterator_t iter, request_header = (ccmsg_creds_iterator_next_t*)malloc(sizeof(ccmsg_creds_iterator_next_t)); if (request_header == NULL) return ccErrNoMem; - request_header->ctx = int_iter->ctx; - request_header->ccache = int_iter->ccache; - request_header->iterator = int_iter->handle; + request_header->ctx = htonll(int_iter->ctx); + request_header->ccache = htonll(int_iter->ccache); + request_header->iterator = htonll(int_iter->handle); code = cci_msg_new(ccmsg_CREDS_ITERATOR_NEXT, &request); if (code != ccNoError) { @@ -167,16 +173,17 @@ cc_int_credentials_iterator_next( cc_credentials_iterator_t iter, code = cci_perform_rpc(request, &response); - if (response->type == ccmsg_NACK) { + type = ntohl(response->type); + if (type == ccmsg_NACK) { ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; - code = nack_header->err_code; - } else if (response->type == ccmsg_ACK) { + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { char * blob; ccmsg_creds_iterator_next_resp_t * response_header = (ccmsg_creds_iterator_next_resp_t*)response->header; - code = cci_msg_retrieve_blob(response, response_header->creds_offset, response_header->creds_len, &blob); - code = cc_credentials_new(credentials, response_header->version, - int_iter->ctx, int_iter->ccache, response_header->creds_handle, - blob, response_header->creds_len); + code = cci_msg_retrieve_blob(response, ntohl(response_header->creds_offset), ntohl(response_header->creds_len), &blob); + code = cc_int_credentials_new(credentials, ntohl(response_header->version), + int_iter->ctx, int_iter->ccache, ntohll(response_header->creds_handle), + blob, ntohl(response_header->creds_len)); free(blob); } else { code = ccErrBadInternalMessage; @@ -185,3 +192,54 @@ cc_int_credentials_iterator_next( cc_credentials_iterator_t iter, cci_msg_destroy(response); return code; } + +cc_int32 +cc_int_credentials_iterator_clone( cc_credentials_iterator_t iter, + cc_credentials_iterator_t* new_iter) +{ + cc_int_credentials_iterator_t int_iter; + cc_msg_t *request; + ccmsg_creds_iterator_clone_t *request_header; + cc_msg_t *response; + cc_uint32 type; + cc_int32 code; + + if ( iter == NULL || new_iter == NULL ) + return ccErrBadParam; + + int_iter = (cc_int_credentials_iterator_t)iter; + + if ( int_iter->magic != CC_CREDS_ITER_MAGIC ) + return ccErrInvalidCCacheIterator; + + request_header = (ccmsg_creds_iterator_clone_t*)malloc(sizeof(ccmsg_creds_iterator_clone_t)); + if (request_header == NULL) + return ccErrNoMem; + request_header->ctx = htonll(int_iter->ctx); + request_header->iterator = htonll(int_iter->handle); + + code = cci_msg_new(ccmsg_CREDS_ITERATOR_CLONE, &request); + if (code != ccNoError) { + free(request_header); + return code; + } + + code = cci_msg_add_header(request, request_header, sizeof(ccmsg_creds_iterator_clone_t)); + + code = cci_perform_rpc(request, &response); + + type = ntohl(response->type); + if (type == ccmsg_NACK) { + ccmsg_nack_t * nack_header = (ccmsg_nack_t *)response->header; + code = ntohl(nack_header->err_code); + } else if (type == ccmsg_ACK) { + ccmsg_creds_iterator_clone_resp_t * response_header = (ccmsg_creds_iterator_clone_resp_t*)response->header; + code = cc_int_credentials_iterator_new(new_iter, int_iter->ctx, int_iter->ccache, ntohll(response_header->iterator)); + } else { + code = ccErrBadInternalMessage; + } + cci_msg_destroy(request); + cci_msg_destroy(response); + return code; +} + diff --git a/src/lib/ccapi/client/credentials_iterator.h b/src/lib/ccapi/client/credentials_iterator.h index 2a6f8edf2..954d2f1af 100644 --- a/src/lib/ccapi/client/credentials_iterator.h +++ b/src/lib/ccapi/client/credentials_iterator.h @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -69,4 +69,8 @@ cc_int32 cc_int_credentials_iterator_next( cc_credentials_iterator_t iter, cc_credentials_t * credentials ); +cc_int32 +cc_int_credentials_iterator_clone( cc_credentials_iterator_t iter, + cc_credentials_iterator_t * new_iter ); + diff --git a/src/lib/ccapi/client/marshall.c b/src/lib/ccapi/client/marshall.c new file mode 100644 index 000000000..31ebacd7b --- /dev/null +++ b/src/lib/ccapi/client/marshall.c @@ -0,0 +1,445 @@ +/* $Copyright: + * + * Copyright 2004-2006 by the Massachusetts Institute of Technology. + * + * All rights reserved. + * + * Export of this software from the United States of America may require a + * specific license from the United States Government. It is the + * responsibility of any person or organization contemplating export to + * obtain such a license before exporting. + * + * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute + * this software and its documentation for any purpose and without fee is + * hereby granted, provided that the above copyright notice appear in all + * copies and that both that copyright notice and this permission notice + * appear in supporting documentation, and that the name of M.I.T. not be + * used in advertising or publicity pertaining to distribution of the + * software without specific, written prior permission. Furthermore if you + * modify this software you must label your software as modified software + * and not distribute it in such a fashion that it might be confused with + * the original MIT software. M.I.T. makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. + * + * Individual source code files are copyright MIT, Cygnus Support, + * OpenVision, Oracle, Sun Soft, FundsXpress, and others. + * + * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, + * and Zephyr are trademarks of the Massachusetts Institute of Technology + * (MIT). No commercial use of these trademarks may be made without prior + * written permission of MIT. + * + * "Commercial use" means use of a name in a product or other for-profit + * manner. It does NOT prevent a commercial firm from referring to the MIT + * trademarks in order to convey information (although in doing so, + * recognition of their trademark status should be given). + * $ + */ + +/* marshall.c */ + +#include +#include +#include +#include "msg.h" +#include "msg_headers.h" +#include "marshall.h" + +cc_int32 +cci_creds_v4_marshall( cc_credentials_v4_t * creds, + char ** pflat, + cc_uint32 * plen) +{ + cc_uint32 len; + char * flat; + cci_flat_creds_v4_t * header; + cc_uint32 length; + cc_time64 t64; + + if ( creds == NULL || pflat == NULL || plen == NULL ) + return ccErrBadParam; + + len = sizeof(cci_flat_creds_v4_t); + flat = (char *)malloc(len); + if ( flat == NULL ) + return ccErrNoMem; + memset(flat, 0, len); + + header = (cci_flat_creds_v4_t *)flat; + header->version = htonl(creds->version); + memcpy(header->principal, creds->principal, cc_v4_name_size); + memcpy(header->principal_instance, creds->principal_instance, cc_v4_instance_size); + memcpy(header->service, creds->service, cc_v4_name_size); + memcpy(header->service_instance, creds->service_instance, cc_v4_instance_size); + memcpy(header->realm, creds->realm, cc_v4_realm_size); + memcpy(header->session_key, creds->session_key, cc_v4_key_size); + header->kvno = htonl(creds->kvno); + header->string_to_key_type = htonl(creds->string_to_key_type); + t64 = creds->issue_date; + header->issue_date = htonll(t64); + header->lifetime = htonl(creds->lifetime); + /* TODO: verify that address is stored in host order */ + header->address = htonl(creds->address); + header->ticket_size = htonl(creds->ticket_size); + memcpy(header->ticket, creds->ticket, cc_v4_ticket_size); + + *pflat = flat; + *plen = len; + + return ccNoError; +} + +cc_int32 +cci_creds_v4_unmarshall( char * flat, + cc_uint32 len, + cc_credentials_union * creds_union) +{ + struct cci_flat_creds_v4 * header; + cc_credentials_v4_t * creds; + cc_flat_data * flat_data; + cc_time64 t64; + cc_uint32 length; + cc_int32 code; + + if ( flat == NULL || len == 0 || creds_union == NULL ) + return ccErrBadParam; + + creds_union->version = cc_credentials_v4; + + header = (cci_flat_creds_v4_t *)flat; + + creds = (cc_credentials_v4_t *)malloc(sizeof(cc_credentials_v4_t)); + if ( creds == NULL ) + return ccErrNoMem; + + creds->version = ntohl(header->version); + memcpy(creds->principal, header->principal, cc_v4_name_size); + memcpy(creds->principal_instance, header->principal_instance, cc_v4_instance_size); + memcpy(creds->service, header->service, cc_v4_name_size); + memcpy(creds->service_instance, header->service_instance, cc_v4_instance_size); + memcpy(creds->realm, header->realm, cc_v4_realm_size); + memcpy(creds->session_key, header->session_key, cc_v4_key_size); + creds->kvno = htonl(header->kvno); + creds->string_to_key_type = htonl(header->string_to_key_type); + t64 = header->issue_date; + creds->issue_date = ntohll(t64); + creds->lifetime = ntohl(header->lifetime); + /* TODO: verify that address is stored in host order */ + creds->address = ntohl(header->address); + creds->ticket_size = ntohl(header->ticket_size); + memcpy(creds->ticket, header->ticket, cc_v4_ticket_size); + + creds_union->credentials.credentials_v4 = creds; + + return ccNoError; +} + + +cc_int32 +cci_creds_cc_data_array_count_entries( cc_data ** array, cc_uint32 * pcount) +{ + cc_uint32 count; + + if (array == NULL) { + *pcount = 0; + return ccNoError; + } + + for ( count=0; array[count] != NULL ; count++) ; + + *pcount = count; + return ccNoError; +} + +cc_int32 +cci_creds_v5_compute_flat_size( cc_credentials_v5_t * creds, cc_uint32 * plen) +{ + cc_uint32 len; + cc_uint32 i, count; + + len = sizeof(struct cci_flat_creds_v5); + + if (creds->client) + len += strlen(creds->client) + 1; + + if (creds->server) + len += strlen(creds->server) + 1; + + len += creds->keyblock.length; + + cci_creds_cc_data_array_count_entries( creds->addresses, &count ); + len += count * sizeof(cc_flat_data); + for ( i=0; iaddresses[i]->length; + } + + len += creds->ticket.length; + len += creds->second_ticket.length; + + cci_creds_cc_data_array_count_entries( creds->authdata, &count ); + len += count * sizeof(cc_flat_data); + for ( i=0; iauthdata[i]->length; + } + + *plen = len; + return ccNoError; +} + +cc_int32 +cci_creds_v5_marshall( cc_credentials_v5_t * creds, + char ** pflat, + cc_uint32 * plen) +{ + cc_uint32 len; + char * flat; + struct cci_flat_creds_v5 * header; + cc_uint32 length; + cc_uint32 offset; + cc_time64 t64; + cc_uint32 count; + cc_uint32 i; + + if ( creds == NULL || pflat == NULL || plen == NULL ) + return ccErrBadParam; + + cci_creds_v5_compute_flat_size(creds, &len); + + flat = (char *)malloc(len); + if ( flat == NULL ) + return ccErrNoMem; + memset(flat, 0, len); + + offset = sizeof(struct cci_flat_creds_v5); + header = (struct cci_flat_creds_v5 *)flat; + header->version = htonl(FLAT_CREDS_V5_VERSION); + if (creds->client) { + length = strlen(creds->client) + 1; + header->client.length = htonl(length); + header->client.data = htonl(offset); + memcpy(flat + offset, creds->client, length); + offset += length; + } + + if (creds->server) { + length = strlen(creds->server) + 1; + header->server.length = htonl(length); + header->server.data = htonl(offset); + memcpy(flat + offset, creds->server, length); + offset += length; + } + + header->keyblock.type = htonl(creds->keyblock.type); + if (creds->keyblock.length) { + length = creds->keyblock.length; + header->keyblock.length = htonl(length); + header->keyblock.data = htonl(offset); + memcpy(flat + offset, creds->keyblock.data, length); + offset += length; + } + + t64 = creds->authtime; + header->authtime = htonll(t64); + t64 = creds->starttime; + header->starttime = htonll(t64); + t64 = creds->endtime; + header->endtime = htonll(t64); + t64 = creds->renew_till; + header->renew_till = htonll(t64); + + header->is_skey = htonl(creds->is_skey); + header->ticket_flags = htonl(creds->ticket_flags); + + cci_creds_cc_data_array_count_entries( creds->addresses, &count ); + if ( count ) { + cc_flat_data * addresses = (cc_flat_data *)flat + offset; + header->address_count = htonl(count); + header->addresses = htonl(offset); + offset += count * sizeof(cc_flat_data); + + for ( i=0; i < count; i++ ) { + addresses[i].type = htonl(creds->addresses[i]->type); + if (creds->addresses[i]->length) { + length = creds->addresses[i]->length; + addresses[i].length = htonl(length); + addresses[i].data = htonl(offset); + /* TODO: verify that addresses are stored in network order */ + memcpy(flat + offset, creds->addresses[i]->data, length); + offset += length; + } + } + } + + header->ticket.type = htonl(creds->ticket.type); + if (creds->ticket.length) { + length = creds->ticket.length; + header->ticket.length = htonl(length); + header->ticket.data = htonl(offset); + memcpy(flat + offset, creds->ticket.data, length); + offset += length; + } + + header->second_ticket.type = htonl(creds->second_ticket.type); + if (creds->second_ticket.length) { + length = creds->second_ticket.length; + header->second_ticket.length = htonl(length); + header->second_ticket.data = htonl(offset); + memcpy(flat + offset, creds->second_ticket.data, length); + offset += length; + } + + cci_creds_cc_data_array_count_entries( creds->authdata, &count ); + if ( count ) { + cc_flat_data * authdata = (cc_flat_data *)flat + offset; + + header->authdata_count = htonl(count); + header->authdata = (offset); + offset += count * sizeof(cc_flat_data); + + for ( i=0; i < count; i++ ) { + authdata[i].type = htonl(creds->authdata[i]->type); + if (creds->authdata[i]->length) { + length = creds->authdata[i]->length; + authdata[i].length = htonl(length); + authdata[i].data = htonl(offset); + memcpy(flat + offset, creds->authdata[i]->data, length); + offset += length; + } + } + } + + *pflat = flat; + *plen = len; + return ccNoError; +} + + +// TODO: a much better job of checking for out of memory errors +// and validating that we do not read beyond the flat input +// data buffer + +cc_int32 +cci_creds_v5_unmarshall( char * flat, + cc_uint32 len, + cc_credentials_union * creds_union) +{ + struct cci_flat_creds_v5 * header; + cc_credentials_v5_t * creds; + cc_flat_data * flat_data; + cc_time64 t64; + cc_uint32 length; + cc_uint32 count; + cc_uint32 i; + cc_int32 code; + + if ( flat == NULL || len == 0 || creds_union == NULL ) + return ccErrBadParam; + + creds_union->version = cc_credentials_v5; + + header = (struct cci_flat_creds_v5 *)flat; + + if ( ntohl(header->version) != FLAT_CREDS_V5_VERSION ) + return ccErrBadParam; + + creds = (cc_credentials_v5_t *)malloc(sizeof(cc_credentials_v5_t)); + if ( creds == NULL ) + return ccErrNoMem; + memset(creds, 0, sizeof(cc_credentials_v5_t)); + + if ( header->client.length ) { + length = ntohl(header->client.length); + creds->client = (char *)malloc(length); + memcpy(creds->client, flat + header->client.data, length); + } + + if ( header->server.length ) { + length = ntohl(header->server.length); + creds->server = (char *)malloc(length); + memcpy(creds->server, flat + header->server.data, length); + } + + creds->keyblock.type = ntohl(header->keyblock.type); + if ( header->keyblock.length ) { + length = ntohl(header->keyblock.length); + creds->keyblock.length = length; + creds->keyblock.data = malloc(length); + memcpy(creds->keyblock.data, flat + header->keyblock.data, length); + } + + /* TODO: need to perform overflow validation checks to ensure + * that we do not attempt to store too large a value into cc_time_t + * when it is a 32-bit field. + */ + t64 = ntohll(header->authtime); + creds->authtime = (cc_time)t64; + t64 = ntohll(header->starttime); + creds->starttime = (cc_time)t64; + t64 = ntohll(header->endtime); + creds->endtime = (cc_time)t64; + t64 = ntohll(header->renew_till); + creds->renew_till = (cc_time)t64; + + creds->is_skey = ntohl(header->is_skey); + creds->ticket_flags = ntohl(header->ticket_flags); + + count = ntohl(header->address_count); + creds->addresses = (cc_data **) malloc((count + 1) * sizeof(cc_data *)); + flat_data = (cc_flat_data *)flat + header->addresses; + for ( i=0 ; i < count ; i++ ) { + creds->addresses[i] = (cc_data *)malloc(sizeof(cc_data)); + creds->addresses[i]->type = ntohl(flat_data[i].type); + length = ntohl(flat_data[i].length); + creds->addresses[i]->length = length; + if ( length ) { + creds->addresses[i]->data = malloc(length); + /* TODO: verify that addresses are stored in network order */ + memcpy(creds->addresses[i]->data, flat + flat_data[i].data, length); + } else { + creds->addresses[i]->data = NULL; + } + } + creds->addresses[i] = NULL; + + creds->ticket.type = ntohl(header->ticket.type); + length = ntohl(header->ticket.length); + if ( length ) { + creds->ticket.length = length; + creds->ticket.data = malloc(length); + memcpy(creds->ticket.data, flat + header->ticket.data, length); + } + + creds->second_ticket.type = header->second_ticket.type; + if ( header->second_ticket.length ) { + creds->second_ticket.length = header->second_ticket.length; + creds->second_ticket.data = malloc(creds->second_ticket.length); + memcpy(creds->second_ticket.data, flat + header->second_ticket.data, creds->second_ticket.length); + } + + count = ntohl(header->authdata_count); + creds->authdata = (cc_data **) malloc((count + 1) * sizeof(cc_data *)); + flat_data = (cc_flat_data *)flat + header->authdata; + for ( i=0 ; i < count ; i++ ) { + creds->authdata[i] = (cc_data *)malloc(sizeof(cc_data)); + creds->authdata[i]->type = ntohl(flat_data[i].type); + length = ntohl(flat_data[i].length); + creds->authdata[i]->length = length; + if ( length ) { + creds->authdata[i]->data = malloc(length); + memcpy(creds->authdata[i]->data, flat + flat_data[i].data, length); + } else { + creds->authdata[i]->data = NULL; + } + } + creds->authdata[i] = NULL; + + creds_union->credentials.credentials_v5 = creds; + + return ccNoError; +} + diff --git a/src/lib/ccapi/msg.c b/src/lib/ccapi/client/msg.c similarity index 79% rename from src/lib/ccapi/msg.c rename to src/lib/ccapi/client/msg.c index f5f074aa0..facaffffc 100644 --- a/src/lib/ccapi/msg.c +++ b/src/lib/ccapi/client/msg.c @@ -1,582 +1,628 @@ -/* $Copyright: - * - * Copyright 2004 by the Massachusetts Institute of Technology. - * - * All rights reserved. - * - * Export of this software from the United States of America may require a - * specific license from the United States Government. It is the - * responsibility of any person or organization contemplating export to - * obtain such a license before exporting. - * - * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute - * this software and its documentation for any purpose and without fee is - * hereby granted, provided that the above copyright notice appear in all - * copies and that both that copyright notice and this permission notice - * appear in supporting documentation, and that the name of M.I.T. not be - * used in advertising or publicity pertaining to distribution of the - * software without specific, written prior permission. Furthermore if you - * modify this software you must label your software as modified software - * and not distribute it in such a fashion that it might be confused with - * the original MIT software. M.I.T. makes no representations about the - * suitability of this software for any purpose. It is provided "as is" - * without express or implied warranty. - * - * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED - * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF - * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. - * - * Individual source code files are copyright MIT, Cygnus Support, - * OpenVision, Oracle, Sun Soft, FundsXpress, and others. - * - * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, - * and Zephyr are trademarks of the Massachusetts Institute of Technology - * (MIT). No commercial use of these trademarks may be made without prior - * written permission of MIT. - * - * "Commercial use" means use of a name in a product or other for-profit - * manner. It does NOT prevent a commercial firm from referring to the MIT - * trademarks in order to convey information (although in doing so, - * recognition of their trademark status should be given). - * $ - */ - -/* - * Verifiable, extensible message format. - */ - -#include "CredentialsCache.h" -#include "msg.h" -#include "datastore.h" - -#include -#include -#include -#include - -/** - * cci_msg_new() - * - * Purpose: Allocate and initialize a new cc_msg_t structure - * - * Return: non-NULL, the msg - * NULL, failure - * - * Errors: ccErrNoMem - * - */ -cc_int32 -cci_msg_new(cc_uint32 type, cc_msg_t** msgpp) -{ - // type should be validated. If invalid set error to ccErrBadParam - cc_msg_t* msg; - - if ( type > CC_MSG_MAX_TYPE || msgpp == NULL ) - return ccErrBadParam; - - msg = (cc_msg_t*)malloc(sizeof(cc_msg_t)); - if (msg == NULL) - return ccErrNoMem; - - msg->type = type; - msg->flat = NULL; - msg->header = NULL; - msg->flat_len = 0; - msg->header_len = 0; - msg->magic = 0; - cci_generic_list_new(&msg->data_blobs); - if (msg->data_blobs == NULL) { - // pass on error from previous call - free(msg); - return ccErrNoMem; - } - - *msgpp = msg; - return ccNoError; -} - -/** - * cci_msg_calc_header_size() - * - * Purpose: Calculates the size of the header - * - * Return: the size in bytes - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_msg_calc_header_size(cc_msg_t* msg, cc_uint32 * lenp) -{ - int header_len = 12; /* header size, entire size, type */ - - if ( msg == NULL || lenp == NULL ) - return ccErrBadParam; - - header_len += msg->header_len; - *lenp = header_len; - return ccNoError; -} - -/** - * cci_msg_calc_size() - * - * Purpose: Calculates the size of the message - * (does not include the magic bytes) - * - * Return: the size in bytes - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_msg_calc_size(cc_msg_t* msg, cc_uint32 * lenp) -{ - cc_uint32 flat_len; - cc_generic_list_node_t* gen_node; - cc_generic_iterate_t* gen_iterator; - cc_int32 code; - - if ( msg == NULL || lenp == NULL ) - return ccErrBadParam; - - code = cci_msg_calc_header_size(msg, &flat_len); - if (code != ccNoError) - goto bad; - - code = cci_generic_list_iterator(msg->data_blobs, &gen_iterator); - if ( code != ccNoError ) - goto bad; - - while (cci_generic_iterate_has_next(gen_iterator)) { - code = cci_generic_iterate_next(gen_iterator, &gen_node); - if (code != ccNoError) - break; - flat_len += gen_node->len + BLOB_LEN; - } - cci_generic_free_iterator(gen_iterator); - if (code != ccNoError) - goto bad; - - flat_len += MAGIC_HEAD_LEN + MAGIC_DATA_LEN; - *lenp = flat_len; - - bad: - return code; -} - -/** - * cci_msg_add_data_blob() - * - * Purpose: Adds 'len' bytes of data to the msg - * - * Return: - * - * Errors: - * - */ -cc_int32 -cci_msg_add_data_blob(cc_msg_t* msg, void *data, cc_uint32 len, cc_uint32 *lenp) -{ - cc_int32 code; - - if (msg == NULL || data == NULL || len <= 0 || lenp == NULL) - return ccErrBadParam; - - code = cci_generic_list_append(msg->data_blobs, data, len, NULL); - if ( code != ccNoError ) - return code; - return cci_msg_calc_blob_pos(msg, data, len, lenp); -} - -/** - * cc_msg_ - * - * Purpose: - * - * Return: - * - * Errors: - * - */ -cc_int32 -cci_msg_calc_blob_pos(cc_msg_t* msg, void *data, cc_uint32 len, cc_uint32 * posp) -{ - cc_uint32 pos; - cc_generic_list_node_t* gen_node; - cc_generic_iterate_t* gen_iterator; - cc_int32 code; - - code = cci_msg_calc_header_size(msg, &pos); - pos += sizeof(cc_uint32); /*+ sizeof(cc_uint32) for magic*/ - - code = cci_generic_list_iterator(msg->data_blobs, &gen_iterator); - while (cci_generic_iterate_has_next(gen_iterator)) { - code = cci_generic_iterate_next(gen_iterator, &gen_node); - if (gen_node->len != len && gen_node->data != data) { - pos += gen_node->len + sizeof(cc_uint32); - } else { - cci_generic_free_iterator(gen_iterator); - *posp = pos + sizeof(cc_uint32); - return ccNoError; - } - } - - cci_generic_free_iterator(gen_iterator); - return ccIteratorEnd; -} - -/** - * cc_msg_ - * - * Purpose: - * - * Return: - * - * Errors: - * - */ -cc_int32 -cci_msg_add_header(cc_msg_t* msg, void *header, cc_uint32 header_len) -{ - if ( msg == NULL || header == NULL ) - return ccErrBadParam; - - msg->header = header; - msg->header_len = header_len; - return ccNoError; -} - - -/** - * cc_msg_ - * - * Purpose: - * - * Return: - * - * Errors: - * - */ -cc_int32 -cci_msg_flatten(cc_msg_t* msg, void **flatpp) -{ - cc_generic_list_node_t* gen_node; - cc_generic_iterate_t* gen_iterator; - char *cur_pos; - cc_uint32 zero = 0; - cc_uint32 magic = 0; - cc_uint32 msg_len; - cc_int32 code; - - if (msg == NULL || flatpp == NULL) - return ccErrBadParam; - - code = cci_msg_calc_size(msg,&msg->flat_len); - if ( code != ccNoError ) - return code; - - if (msg->flat_len > CC_MSG_MAX_SIZE) - return ccErrBadParam; - - msg->flat = (void *)malloc(msg->flat_len); - if (msg->flat == NULL) - return ccErrNoMem; - - cur_pos = msg->flat; - - memcpy(cur_pos,&msg->header_len,sizeof(cc_uint32)); - cur_pos+=sizeof(cc_uint32); - - memcpy(cur_pos,&msg->flat_len,sizeof(cc_uint32)); - cur_pos+=sizeof(cc_uint32); - - memcpy(cur_pos,&msg->type,sizeof(cc_uint32)); - cur_pos+=sizeof(cc_uint32); - - memcpy(cur_pos, msg->header, msg->header_len); - cur_pos += msg->header_len; - - memcpy(cur_pos, &zero, sizeof(cc_uint32)); /*will be magic number later*/ - cur_pos += sizeof(cc_uint32); - - code = cci_generic_list_iterator(msg->data_blobs,&gen_iterator); - if ( code != ccNoError ) { - free(msg->flat); - return code; - } - - while (cci_generic_iterate_has_next(gen_iterator)) { - code = cci_generic_iterate_next(gen_iterator, &gen_node); - if (code != ccNoError) { - free(gen_iterator); - free(msg->flat); - return code; - } - memcpy(cur_pos, &gen_node->len, sizeof(cc_uint32)); - cur_pos+=sizeof(cc_uint32); - - memcpy(cur_pos, gen_node->data, gen_node->len); - cur_pos += gen_node->len; - } - free(gen_iterator); - - memcpy(cur_pos, &zero, sizeof(cc_uint32)); /*magic number will go here later*/ - cur_pos += sizeof(cc_uint32); - - if (cur_pos - (char *)msg->flat != msg->flat_len) { - printf("ERRORR cur_pos - msg->flat = %d\n",msg->flat_len); - } - - cci_msg_calc_magic(msg->flat, msg->flat_len, &magic); - printf("magic = %d\n",magic); - - cci_msg_calc_header_size(msg, &msg_len); - memcpy((char *)msg->flat + msg_len, &magic, sizeof(cc_uint32)); - memcpy((char *)msg->flat + msg->flat_len - sizeof(cc_uint32), &magic, sizeof(cc_uint32)); - - if ( flatpp != NULL ) - *flatpp = msg->flat; - return ccNoError; -} - -/** - * cc_msg_ - * - * Purpose: - * - * Return: - * - * Errors: - * - */ -cc_int32 -cci_msg_calc_magic(void *flat, int flat_len, cc_uint32 * magicp) -{ - cc_uint32 magic = 0; - int i; - - for (i = 0; i < flat_len; i += sizeof(cc_uint32)) { - magic = magic ^ *(int *)((char *)flat + i); - } - *magicp = magic; - return ccNoError; -} - -/** - * cc_msg_ - * - * Purpose: - * - * Return: - * - * Errors: - * - */ -cc_int32 -cci_msg_verify(void *flat, int flat_len, cc_uint32 * validp) -{ - cc_uint32 *magic1, *magic2; - cc_uint32 *pheader_len; - cc_uint32 *ptotal_len; - cc_uint32 *pblob_len; - cc_uint32 *ptype; - cc_uint32 num_blobs = 0; - cc_uint32 zero = 0; - cc_uint32 msg_magic, msg_magic2; - - if (flat == NULL || flat_len <= 0 || validp == NULL) - return ccErrBadParam; - - pheader_len = flat; - ptotal_len = (cc_uint32 *)((char *)pheader_len + sizeof(cc_uint32)); - ptype = (cc_uint32 *)((char *)ptotal_len + sizeof(cc_uint32)); - - if (*ptotal_len != flat_len) { - *validp = 0; - return ccNoError; - } - - if (*pheader_len > flat_len) { - /*too weak. We could verify header_len against type spec header.*/ - *validp = 0; - return ccNoError; - } - if (*ptype > CC_MSG_MAX_TYPE) { - *validp = 0; - return ccNoError; - } - - magic1 = (cc_uint32 *)((char *)ptype + sizeof(cc_uint32) + *pheader_len); - if ((char *)magic1 - (char *)flat == (flat_len - 8)) { - /*There are no data blobs*/ - magic2 = (cc_uint32 *)((char *)magic1 + sizeof(cc_uint32)); - num_blobs = 0; - } else { - pblob_len = (cc_uint32 *)((char *)magic1 + sizeof(cc_uint32)); - num_blobs = 1; - - while (*pblob_len + sizeof(cc_uint32) + ((char *)pblob_len - (char *)flat) < (flat_len - sizeof(cc_uint32))) { - pblob_len = (cc_uint32 *)((char *)pblob_len + *pblob_len + sizeof(cc_uint32)); - num_blobs++; - } - - if (*pblob_len + sizeof(cc_uint32) + ((char *)pblob_len - (char *)flat) != (flat_len - sizeof(cc_uint32))) { - /*blobs didn't line up*/ - *validp = 0; - return ccNoError; - } - magic2 = (cc_uint32 *)((char *)pblob_len + *pblob_len + sizeof(cc_uint32)); /*2nd magic should be directly after the last blob*/ - } - - if (*magic1 != *magic2) { - *validp = 0; - return ccNoError; - } - msg_magic = *magic1; - - printf("%d %d\n", (char *)magic1 - (char *)flat, (char *)magic2 - (char *)flat); - - memcpy(magic1, &zero, sizeof(cc_uint32)); - memcpy(magic2, &zero, sizeof(cc_uint32)); - cci_msg_calc_magic(flat, flat_len, &msg_magic2); - if (msg_magic != msg_magic2) { - *validp = 0; - return ccNoError; - } - memcpy(magic1, &msg_magic, sizeof(cc_uint32)); - memcpy(magic2, &msg_magic, sizeof(cc_uint32)); - - *validp = 1; - return ccNoError; -} - -/** - * cc_msg_ - * - * Purpose: - * - * Return: - * - * Errors: - * - */ -cc_int32 -cci_msg_unflatten(void *flat, int flat_len, cc_msg_t** msgpp) -{ - cc_msg_t* msg; - char *cur_pos; - cc_uint32 blob_len; - char *blob; - cc_uint32 valid; - cc_int32 code; - - if ( flat == NULL || flat_len <= 0 || msgpp == NULL ) - return ccErrBadParam; - - code = cci_msg_new(0, &msg); - if (code) - return code; - - cci_msg_verify(flat, flat_len, &valid); - if (valid != 1) { - cci_msg_destroy(msg); - return ccErrBadParam; - } - - cur_pos = flat; - msg->flat = flat; - - msg->header_len = *(cc_uint32 *)cur_pos; - cur_pos += sizeof(cc_uint32); - - msg->flat_len = *(cc_uint32 *)cur_pos; - cur_pos += sizeof(cc_uint32); - - msg->type = *(cc_uint32 *)cur_pos; - cur_pos += sizeof(cc_uint32); - - msg->header = (void *)malloc(msg->header_len); - if (msg->header == NULL) { - cci_msg_destroy(msg); - return ccErrNoMem; - } - memcpy(msg->header, cur_pos, msg->header_len); - cur_pos += msg->header_len; - - msg->magic = *(cc_uint32 *)cur_pos; - cur_pos += sizeof(cc_uint32); - - if (cur_pos - (char *)flat != flat_len - 8) { /*at least 1 blob*/ - blob_len = *(cc_uint32 *)cur_pos; - while (blob_len + (cur_pos - (char *)flat) + sizeof(cc_uint32) <= flat_len - sizeof(cc_uint32)) { - blob = (void *)malloc(blob_len); - if (blob == NULL) { - cci_msg_destroy(msg); - return ccErrNoMem; - } - memcpy(blob, cur_pos + sizeof(cc_uint32), blob_len); - cci_generic_list_append(msg->data_blobs, blob, blob_len, NULL); - - cur_pos += sizeof(cc_uint32) + blob_len; - blob_len = *(int *)cur_pos; - } - } - *msgpp = msg; - return ccNoError; -} - -cc_int32 -cci_msg_retrieve_blob(cc_msg_t* msg, cc_uint32 blob_offset, cc_uint32 blob_len, void **blobp) -{ - cc_generic_iterate_t* gen_iterator; - cc_generic_list_node_t* gen_node; - void *ret; - cc_uint32 blob_pos; - cc_int32 code; - - /*Ensure that the message has been unflattened*/ - if ( msg == NULL || msg->flat == NULL || blob_offset > msg->flat_len || - blob_len > msg->flat_len - blob_offset || blobp == NULL) - return ccErrBadParam; - - code = cci_generic_list_iterator(msg->data_blobs, &gen_iterator); - while (cci_generic_iterate_has_next(gen_iterator)) { - code = cci_generic_iterate_next(gen_iterator, &gen_node); - code = cci_msg_calc_blob_pos(msg, gen_node->data, gen_node->len, &blob_pos); - if (blob_pos == blob_offset && gen_node->len == blob_len) { - free(gen_iterator); - ret = (void *)malloc(blob_len); - if (ret == NULL) - return ccErrNoMem; - memcpy(ret,(char *)msg->flat + blob_offset, blob_len); - *blobp = ret; - return ccNoError; - } - } - free(gen_iterator); - return ccIteratorEnd; -} - -/** - * cc_msg_ - * - * Purpose: - * - * Return: - * - * Errors: - * - */ -cc_int32 -cci_msg_destroy(cc_msg_t* msg) -{ - if (msg->flat != NULL) - free(msg->flat); - if (msg->header != NULL) - free(msg->flat); - cci_generic_list_destroy(msg->data_blobs); - free(msg); - return ccNoError; -} - +/* $Copyright: + * + * Copyright 2004-2006 by the Massachusetts Institute of Technology. + * + * All rights reserved. + * + * Export of this software from the United States of America may require a + * specific license from the United States Government. It is the + * responsibility of any person or organization contemplating export to + * obtain such a license before exporting. + * + * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute + * this software and its documentation for any purpose and without fee is + * hereby granted, provided that the above copyright notice appear in all + * copies and that both that copyright notice and this permission notice + * appear in supporting documentation, and that the name of M.I.T. not be + * used in advertising or publicity pertaining to distribution of the + * software without specific, written prior permission. Furthermore if you + * modify this software you must label your software as modified software + * and not distribute it in such a fashion that it might be confused with + * the original MIT software. M.I.T. makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. + * + * Individual source code files are copyright MIT, Cygnus Support, + * OpenVision, Oracle, Sun Soft, FundsXpress, and others. + * + * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, + * and Zephyr are trademarks of the Massachusetts Institute of Technology + * (MIT). No commercial use of these trademarks may be made without prior + * written permission of MIT. + * + * "Commercial use" means use of a name in a product or other for-profit + * manner. It does NOT prevent a commercial firm from referring to the MIT + * trademarks in order to convey information (although in doing so, + * recognition of their trademark status should be given). + * $ + */ + +/* + * Verifiable, extensible message format. + * + * Format: + * + * + * + * + * + * + * + * + * + * ... + * + * + * If the header has variable length data it is included in the data blobs. + * The header field has the offset from the beginning of the message of the 1st + * byte of the data and the length of the data. + */ + +#include "CredentialsCache.h" +#include "msg.h" +#include "generic_lists.h" + +#include +#include +#include +#include + +/** + * cci_msg_new() + * + * Purpose: Allocate and initialize a new cc_msg_t structure + * + * Input parameter (type) in host order + * + * Return: non-NULL, the msg + * NULL, failure + * + * Errors: ccErrNoMem + * + */ +cc_int32 +cci_msg_new(cc_uint32 type, cc_msg_t** msgpp) +{ + // type should be validated. If invalid set error to ccErrBadParam + cc_msg_t* msg; + + if ( type > CC_MSG_MAX_TYPE || msgpp == NULL ) + return ccErrBadParam; + + msg = (cc_msg_t*)malloc(sizeof(cc_msg_t)); + if (msg == NULL) + return ccErrNoMem; + + msg->type = htonl(type); + msg->flat = NULL; + msg->header = NULL; + msg->flat_len = 0; + msg->header_len = 0; + msg->magic = 0; + cci_generic_list_new(&msg->data_blobs); + if (msg->data_blobs == NULL) { + // pass on error from previous call + free(msg); + return ccErrNoMem; + } + + *msgpp = msg; + return ccNoError; +} + +/** + * cci_msg_calc_header_size() + * + * Purpose: Calculates the size of the header + * + * Return: the size in bytes + * + * Errors: ccErrBadParam + * + */ +cc_int32 +cci_msg_calc_header_size(cc_msg_t* msg, cc_uint32 * lenp) +{ + int header_len = 12; /* header size, entire size, type */ + + if ( msg == NULL || lenp == NULL ) + return ccErrBadParam; + + header_len += msg->header_len; + *lenp = header_len; + return ccNoError; +} + +/** + * cci_msg_calc_size() + * + * Purpose: Calculates the size of the message + * (does not include the magic bytes) + * + * Return: the size in bytes + * + * Errors: ccErrBadParam + * + */ +cc_int32 +cci_msg_calc_size(cc_msg_t* msg, cc_uint32 * lenp) +{ + cc_uint32 flat_len; + cc_generic_list_node_t* gen_node; + cc_generic_iterate_t* gen_iterator; + cc_int32 code; + + if ( msg == NULL || lenp == NULL ) + return ccErrBadParam; + + code = cci_msg_calc_header_size(msg, &flat_len); + if (code != ccNoError) + goto bad; + + code = cci_generic_list_iterator(msg->data_blobs, &gen_iterator); + if ( code != ccNoError ) + goto bad; + + while (cci_generic_iterate_has_next(gen_iterator)) { + code = cci_generic_iterate_next(gen_iterator, &gen_node); + if (code != ccNoError) + break; + flat_len += gen_node->len + BLOB_LEN; + } + cci_generic_free_iterator(gen_iterator); + if (code != ccNoError) + goto bad; + + flat_len += MAGIC_HEAD_LEN + MAGIC_DATA_LEN; + *lenp = flat_len; + + bad: + return code; +} + +/** + * cci_msg_add_data_blob() + * + * Purpose: Adds 'len' bytes of data to the msg + * + * Return: + * + * Errors: + * + */ +cc_int32 +cci_msg_add_data_blob(cc_msg_t* msg, void *data, cc_uint32 len, cc_uint32 *lenp) +{ + cc_int32 code; + + if (msg == NULL || data == NULL || len <= 0 || lenp == NULL) + return ccErrBadParam; + + code = cci_generic_list_append(msg->data_blobs, data, len, NULL); + if ( code != ccNoError ) + return code; + return cci_msg_calc_blob_pos(msg, data, len, lenp); +} + +/** + * cc_msg_ + * + * Purpose: + * + * Return: + * + * Errors: + * + */ +cc_int32 +cci_msg_calc_blob_pos(cc_msg_t* msg, void *data, cc_uint32 len, cc_uint32 * posp) +{ + cc_uint32 pos; + cc_generic_list_node_t* gen_node; + cc_generic_iterate_t* gen_iterator; + cc_int32 code; + + code = cci_msg_calc_header_size(msg, &pos); + pos += sizeof(cc_uint32); /*+ sizeof(cc_uint32) for magic*/ + + code = cci_generic_list_iterator(msg->data_blobs, &gen_iterator); + while (cci_generic_iterate_has_next(gen_iterator)) { + code = cci_generic_iterate_next(gen_iterator, &gen_node); + if (gen_node->len != len && gen_node->data != data) { + pos += gen_node->len + sizeof(cc_uint32); + } else { + cci_generic_free_iterator(gen_iterator); + *posp = pos + sizeof(cc_uint32); + return ccNoError; + } + } + + cci_generic_free_iterator(gen_iterator); + return ccIteratorEnd; +} + +/** + * cc_msg_ + * + * Purpose: + * + * Return: + * + * Errors: + * + */ +cc_int32 +cci_msg_add_header(cc_msg_t* msg, void *header, cc_uint32 header_len) +{ + if ( msg == NULL || header == NULL ) + return ccErrBadParam; + + msg->header = header; + msg->header_len = header_len; + return ccNoError; +} + + +/** + * cc_msg_ + * + * Purpose: + * + * Return: + * + * Errors: + * + */ +cc_int32 +cci_msg_flatten(cc_msg_t* msg, void **flatpp) +{ + cc_generic_list_node_t* gen_node; + cc_generic_iterate_t* gen_iterator; + char *cur_pos; + cc_uint32 zero = 0; + cc_uint32 magic = 0; + cc_uint32 msg_len; + cc_uint32 u32; + cc_int32 code; + + if (msg == NULL || flatpp == NULL) + return ccErrBadParam; + + code = cci_msg_calc_size(msg,&msg->flat_len); + if ( code != ccNoError ) + return code; + + if (msg->flat_len > CC_MSG_MAX_SIZE) + return ccErrBadParam; + + msg->flat = (void *)malloc(msg->flat_len); + if (msg->flat == NULL) + return ccErrNoMem; + + cur_pos = msg->flat; + + u32 = msg->header_len; + htonl(u32); + memcpy(cur_pos,&u32,sizeof(cc_uint32)); + cur_pos+=sizeof(cc_uint32); + + u32 = msg->flat_len; + htonl(u32); + memcpy(cur_pos,&u32,sizeof(cc_uint32)); + cur_pos+=sizeof(cc_uint32); + + u32 = msg->type; + htonl(u32); + memcpy(cur_pos,&u32,sizeof(cc_uint32)); + cur_pos+=sizeof(cc_uint32); + + /* header data is already in network order */ + memcpy(cur_pos, msg->header, msg->header_len); + cur_pos += msg->header_len; + + u32 = zero; + htonl(zero); + memcpy(cur_pos, &u32, sizeof(cc_uint32)); /*will be magic number later*/ + cur_pos += sizeof(cc_uint32); + + code = cci_generic_list_iterator(msg->data_blobs, &gen_iterator); + if ( code != ccNoError ) { + free(msg->flat); + return code; + } + + while (cci_generic_iterate_has_next(gen_iterator)) { + code = cci_generic_iterate_next(gen_iterator, &gen_node); + if (code != ccNoError) { + free(gen_iterator); + free(msg->flat); + return code; + } + u32 = gen_node->len; + htonl(u32); + memcpy(cur_pos, &u32, sizeof(cc_uint32)); + cur_pos+=sizeof(cc_uint32); + + /* data already in network order */ + memcpy(cur_pos, gen_node->data, gen_node->len); + cur_pos += gen_node->len; + } + free(gen_iterator); + + u32 = zero; + htonl(zero); + memcpy(cur_pos, &u32, sizeof(cc_uint32)); /*magic number will go here later*/ + cur_pos += sizeof(cc_uint32); + + if (cur_pos - (char *)msg->flat != msg->flat_len) { + fprintf(stderr, "ERROR cur_pos - msg->flat = %d\n",msg->flat_len); + } + + cci_msg_calc_magic(msg->flat, msg->flat_len, &magic); + printf("magic = %d\n",magic); + + cci_msg_calc_header_size(msg, &msg_len); + memcpy((char *)msg->flat + msg_len, &magic, sizeof(cc_uint32)); + memcpy((char *)msg->flat + msg->flat_len - sizeof(cc_uint32), &magic, sizeof(cc_uint32)); + + if ( flatpp != NULL ) + *flatpp = msg->flat; + + return ccNoError; +} + +/** + * cc_msg_ + * + * Purpose: + * + * Return: + * + * Errors: + * + */ +cc_int32 +cci_msg_calc_magic(void *flat, int flat_len, cc_uint32 * magicp) +{ + cc_uint32 magic = 0; + int i; + + for (i = 0; i < flat_len; i += sizeof(cc_uint32)) { + magic = magic ^ *(int *)((char *)flat + i); + } + *magicp = htonl(magic); + return ccNoError; +} + +/** + * cc_msg_ + * + * Purpose: + * + * Return: + * + * Errors: + * + */ +cc_int32 +cci_msg_verify(void *flat, int flat_len, cc_uint32 * validp) +{ + cc_uint32 *magic1, *magic2; + cc_uint32 *pheader_len; + cc_uint32 header_len; + cc_uint32 *ptotal_len; + cc_uint32 total_len; + cc_uint32 *pblob_len; + cc_uint32 blob_len; + cc_uint32 *ptype; + cc_uint32 type; + cc_uint32 num_blobs = 0; + cc_uint32 zero = 0; + cc_uint32 msg_magic, msg_magic2; + + if (flat == NULL || flat_len <= 0 || validp == NULL) + return ccErrBadParam; + + pheader_len = flat; + ptotal_len = (cc_uint32 *)((char *)pheader_len + sizeof(cc_uint32)); + ptype = (cc_uint32 *)((char *)ptotal_len + sizeof(cc_uint32)); + + header_len = ntohl(*pheader_len); + total_len = ntohl(*ptotal_len); + type = ntohl(*ptype); + + if (total_len != flat_len) { + *validp = 0; + return ccNoError; + } + + if (header_len > flat_len) { + /*too weak. We could verify header_len against type spec header.*/ + *validp = 0; + return ccNoError; + } + if (type > CC_MSG_MAX_TYPE) { + *validp = 0; + return ccNoError; + } + + magic1 = (cc_uint32 *)((char *)ptype + sizeof(cc_uint32) + header_len); + if ((char *)magic1 - (char *)flat == (flat_len - 8)) { + /*There are no data blobs*/ + magic2 = (cc_uint32 *)((char *)magic1 + sizeof(cc_uint32)); + num_blobs = 0; + } else { + pblob_len = (cc_uint32 *)((char *)magic1 + sizeof(cc_uint32)); + num_blobs = 1; + blob_len = nothl(*pblob_len); + + while (blob_len + sizeof(cc_uint32) + ((char *)pblob_len - (char *)flat) < (flat_len - sizeof(cc_uint32))) { + pblob_len = (cc_uint32 *)((char *)pblob_len + blob_len + sizeof(cc_uint32)); + num_blobs++; + blob_len = ntohl(*pblob_len); + } + + if (blob_len + sizeof(cc_uint32) + ((char *)pblob_len - (char *)flat) != (flat_len - sizeof(cc_uint32))) { + /*blobs didn't line up*/ + *validp = 0; + return ccNoError; + } + magic2 = (cc_uint32 *)((char *)pblob_len + blob_len + sizeof(cc_uint32)); /*2nd magic should be directly after the last blob*/ + } + + if (*magic1 != *magic2) { + *validp = 0; + return ccNoError; + } + msg_magic = *magic1; + + printf("%d %d\n", (char *)magic1 - (char *)flat, (char *)magic2 - (char *)flat); + + memcpy(magic1, &zero, sizeof(cc_uint32)); + memcpy(magic2, &zero, sizeof(cc_uint32)); + cci_msg_calc_magic(flat, flat_len, &msg_magic2); + /* both msg_magic and msg_magic2 are in network order */ + if (msg_magic != msg_magic2) { + *validp = 0; + return ccNoError; + } + memcpy(magic1, &msg_magic, sizeof(cc_uint32)); + memcpy(magic2, &msg_magic, sizeof(cc_uint32)); + + *validp = 1; + return ccNoError; +} + +/** + * cc_msg_ + * + * Purpose: + * + * Return: + * + * Errors: + * + */ +cc_int32 +cci_msg_unflatten(void *flat, int flat_len, cc_msg_t** msgpp) +{ + cc_msg_t* msg; + char *cur_pos; + cc_uint32 blob_len; + char *blob; + cc_uint32 valid; + cc_int32 code; + + if ( flat == NULL || flat_len <= 0 || msgpp == NULL ) + return ccErrBadParam; + + code = cci_msg_new(0, &msg); + if (code) + return code; + + cci_msg_verify(flat, flat_len, &valid); + if (valid != 1) { + cci_msg_destroy(msg); + return ccErrBadParam; + } + + cur_pos = flat; + msg->flat = flat; + + msg->header_len = ntohl(*(cc_uint32 *)cur_pos); + cur_pos += sizeof(cc_uint32); + + msg->flat_len = ntohl(*(cc_uint32 *)cur_pos); + cur_pos += sizeof(cc_uint32); + + msg->type = ntohl(*(cc_uint32 *)cur_pos); + cur_pos += sizeof(cc_uint32); + + msg->header = (void *)malloc(msg->header_len); + if (msg->header == NULL) { + cci_msg_destroy(msg); + return ccErrNoMem; + } + memcpy(msg->header, cur_pos, msg->header_len); + cur_pos += msg->header_len; + + msg->magic = nothl(*(cc_uint32 *)cur_pos); + cur_pos += sizeof(cc_uint32); + + if (cur_pos - (char *)flat != flat_len - 8) { /*at least 1 blob*/ + blob_len = ntohl(*(cc_uint32 *)cur_pos); + while (blob_len + (cur_pos - (char *)flat) + sizeof(cc_uint32) <= flat_len - sizeof(cc_uint32)) { + blob = (void *)malloc(blob_len); + if (blob == NULL) { + cci_msg_destroy(msg); + return ccErrNoMem; + } + memcpy(blob, cur_pos + sizeof(cc_uint32), blob_len); + cci_generic_list_append(msg->data_blobs, blob, blob_len, NULL); + + cur_pos += sizeof(cc_uint32) + blob_len; + blob_len = ntohl(*(int *)cur_pos); + } + } + *msgpp = msg; + return ccNoError; +} + +cc_int32 +cci_msg_retrieve_blob(cc_msg_t* msg, cc_uint32 blob_offset, cc_uint32 blob_len, void **blobp) +{ + cc_generic_iterate_t* gen_iterator; + cc_generic_list_node_t* gen_node; + void *ret; + cc_uint32 blob_pos; + cc_int32 code; + + /*Ensure that the message has been unflattened*/ + if ( msg == NULL || msg->flat == NULL || blob_offset > msg->flat_len || + blob_len > msg->flat_len - blob_offset || blobp == NULL) + return ccErrBadParam; + + code = cci_generic_list_iterator(msg->data_blobs, &gen_iterator); + while (cci_generic_iterate_has_next(gen_iterator)) { + code = cci_generic_iterate_next(gen_iterator, &gen_node); + code = cci_msg_calc_blob_pos(msg, gen_node->data, gen_node->len, &blob_pos); + if (blob_pos == blob_offset && gen_node->len == blob_len) { + free(gen_iterator); + ret = (void *)malloc(blob_len); + if (ret == NULL) + return ccErrNoMem; + memcpy(ret,(char *)msg->flat + blob_offset, blob_len); + *blobp = ret; + return ccNoError; + } + } + free(gen_iterator); + return ccIteratorEnd; +} + +/** + * cc_msg_ + * + * Purpose: + * + * Return: + * + * Errors: + * + */ +cc_int32 +cci_msg_destroy(cc_msg_t* msg) +{ + if (msg->flat != NULL) + free(msg->flat); + if (msg->header != NULL) + free(msg->flat); + cci_generic_list_destroy(msg->data_blobs); + free(msg); + return ccNoError; +} + diff --git a/src/lib/ccapi/include/CredentialsCache.h b/src/lib/ccapi/include/CredentialsCache.h index dd60fa46d..7143da4e2 100644 --- a/src/lib/ccapi/include/CredentialsCache.h +++ b/src/lib/ccapi/include/CredentialsCache.h @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 1998-2004 by the Massachusetts Institute of Technology. + * Copyright 1998-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -46,12 +46,12 @@ /* * Declarations for Credentials Cache API Library * - * API specification: + * API specification: * * Revision 1: Frank Dabek, 6/4/1998 * Revision 2: meeroh, 2/24/1999 * Revision 3: meeroh, 11/12/1999 - * Revision 4: jaltman, 10/27/2004 + * Revision 6: jaltman, 10/27/2004 * */ @@ -81,6 +81,17 @@ extern "C" { #pragma options align=mac68k #endif +#if defined(_WIN32) +#define CCACHE_API __declspec(dllexport) + +#if _INTEGRAL_MAX_BITS >= 64 && _MSC_VER >= 1400 && !defined(_WIN64) && !defined(_USE_32BIT_TIME_T) +#if defined(_TIME_T_DEFINED) || defined(_INC_IO) || defined(_INC_TIME) || defined(_INC_WCHAR) +#error time_t has been defined as a 64-bit integer which is incompatible with Kerberos on this platform. +#endif /* _TIME_T_DEFINED */ +#define _USE_32BIT_TIME_T +#endif +#endif + #include /* @@ -92,14 +103,16 @@ enum { ccapi_version_2 = 2, ccapi_version_3 = 3, ccapi_version_4 = 4, - ccapi_version_5 = 5 + ccapi_version_5 = 5, + ccapi_version_6 = 6, + ccapi_version_max = ccapi_version_6 }; /* Errors */ enum { - ccNoError = 0, + ccNoError = 0, - ccIteratorEnd = 201, + ccIteratorEnd = 201, ccErrBadParam, ccErrNoMem, ccErrInvalidContext, @@ -111,7 +124,7 @@ enum { ccErrInvalidCredentialsIterator, ccErrInvalidLock, - ccErrBadName, /* 211 */ + ccErrBadName, /* 211 */ ccErrBadCredentialsVersion, ccErrBadAPIVersion, ccErrContextLocked, @@ -123,7 +136,7 @@ enum { ccErrNeverDefault, ccErrCredentialsNotFound, - ccErrCCacheNotFound, /* 221 */ + ccErrCCacheNotFound, /* 221 */ ccErrContextNotFound, ccErrServerUnavailable, ccErrServerInsecure, @@ -135,20 +148,22 @@ enum { }; /* Credentials versions */ -enum { +enum cc_credential_versions { cc_credentials_v4 = 1, cc_credentials_v5 = 2, cc_credentials_v4_v5 = 3 }; /* Lock types */ -enum { - cc_lock_read = 1, - cc_lock_write = 2 +enum cc_lock_types { + cc_lock_read = 0, + cc_lock_write = 1, + cc_lock_upgrade = 2, + cc_lock_downgrade = 3 }; /* Locking Modes */ -enum { +enum cc_lock_modes { cc_lock_noblock = 0, cc_lock_block = 1 }; @@ -157,12 +172,20 @@ enum { * Basic types */ -typedef char cc_int8; -typedef unsigned char cc_uint8; -typedef int cc_int32; -typedef unsigned int cc_uint32; -typedef time_t cc_time_t; -typedef void * cc_handle; +typedef char cc_int8; +typedef unsigned char cc_uint8; +typedef int cc_int32; +typedef unsigned int cc_uint32; +#if defined (WIN32) +typedef __int64 cc_int64; +typedef unsigned __int64 cc_uint64; +#else +typedef long long cc_int64; +typedef unsigned long long cc_uint64; +#endif +typedef time_t cc_time; +typedef cc_int64 cc_time64; +typedef cc_uint64 cc_handle; /* * API types @@ -190,10 +213,11 @@ typedef struct cc_credentials_f cc_credentials_f; /* Credentials types */ enum { /* Make sure all of these are multiples of four (for alignment sanity) */ - cc_v4_name_size = 40, + cc_v4_name_size = 40, cc_v4_instance_size = 40, cc_v4_realm_size = 40, - cc_v4_ticket_size = 1254 + cc_v4_ticket_size = 1254, + cc_v4_key_size = 8 }; enum cc_string_to_key_type { @@ -211,10 +235,10 @@ struct cc_credentials_v4_t { char service [cc_v4_name_size]; char service_instance [cc_v4_instance_size]; char realm [cc_v4_realm_size]; - unsigned char session_key [8]; + unsigned char session_key [cc_v4_key_size]; cc_int32 kvno; cc_int32 string_to_key_type; - cc_time_t issue_date; + cc_time issue_date; cc_int32 lifetime; cc_uint32 address; cc_int32 ticket_size; @@ -233,10 +257,10 @@ struct cc_credentials_v5_t { char* client; char* server; cc_data keyblock; - cc_time_t authtime; - cc_time_t starttime; - cc_time_t endtime; - cc_time_t renew_till; + cc_time authtime; + cc_time starttime; + cc_time endtime; + cc_time renew_till; cc_uint32 is_skey; cc_uint32 ticket_flags; cc_data** addresses; @@ -320,7 +344,7 @@ struct cc_context_f { cc_context_t context); cc_int32 (*get_change_time) ( cc_context_t context, - cc_time_t* time); + cc_time* time); cc_int32 (*get_default_ccache_name) ( cc_context_t context, cc_string_t* name); @@ -397,16 +421,16 @@ struct cc_ccache_f { cc_ccache_t destination); cc_int32 (*lock) ( cc_ccache_t ccache, - cc_uint32 block, - cc_uint32 lock_type); + cc_uint32 lock_type, + cc_uint32 block); cc_int32 (*unlock) ( cc_ccache_t ccache); cc_int32 (*get_last_default_time) ( cc_ccache_t ccache, - cc_time_t* time); + cc_time* time); cc_int32 (*get_change_time) ( cc_ccache_t ccache, - cc_time_t* time); + cc_time* time); cc_int32 (*compare) ( cc_ccache_t ccache, cc_ccache_t compare_to, @@ -414,11 +438,11 @@ struct cc_ccache_f { cc_int32 (*get_kdc_time_offset) ( cc_ccache_t ccache, cc_int32 credentials_version, - cc_time_t* time_offset); + cc_time* time_offset); cc_int32 (*set_kdc_time_offset) ( cc_ccache_t ccache, cc_int32 credentials_version, - cc_time_t time_offset); + cc_time time_offset); cc_int32 (*clear_kdc_time_offset) ( cc_ccache_t ccache, @@ -446,6 +470,9 @@ struct cc_ccache_iterator_f { cc_int32 (*next) ( cc_ccache_iterator_t iter, cc_ccache_t* ccache); + + cc_int32 (*clone) ( cc_ccache_iterator_t iter, + cc_ccache_iterator_t* new_iter); }; struct cc_credentials_iterator_f { @@ -454,16 +481,19 @@ struct cc_credentials_iterator_f { cc_int32 (*next) ( cc_credentials_iterator_t iter, cc_credentials_t* ccache); + + cc_int32 (*clone) ( cc_credentials_iterator_t iter, + cc_credentials_iterator_t* new_iter); }; /* * API functions */ -cc_int32 cc_initialize ( +CCACHE_API cc_int32 cc_initialize ( cc_context_t* outContext, - cc_int32 inVersion, - cc_int32* outSupportedVersion, + cc_int32 inVersion, + cc_int32* outSupportedVersion, char const** outVendor); /* @@ -488,8 +518,8 @@ cc_int32 cc_initialize ( ((context) -> functions -> create_new_ccache (context, version, principal, ccache)) #define cc_context_new_ccache_iterator(context, iterator) \ ((context) -> functions -> new_ccache_iterator (context, iterator)) -#define cc_context_lock(context, type, lock) \ - ((context) -> functions -> lock (context, type, lock)) +#define cc_context_lock(context, type, block) \ + ((context) -> functions -> lock (context, type, block)) #define cc_context_unlock(context) \ ((context) -> functions -> unlock (context)) #define cc_context_compare(context, compare_to, equal) \ @@ -515,8 +545,8 @@ cc_int32 cc_initialize ( ((ccache) -> functions -> remove_credentials (ccache, credentials)) #define cc_ccache_new_credentials_iterator(ccache, iterator) \ ((ccache) -> functions -> new_credentials_iterator (ccache, iterator)) -#define cc_ccache_lock(ccache, lock) \ - ((ccache) -> functions -> lock (ccache, lock)) +#define cc_ccache_lock(ccache, type, block) \ + ((ccache) -> functions -> lock (ccache, type, block)) #define cc_ccache_unlock(ccache, unlock) \ ((ccache) -> functions -> unlock (ccache, unlock)) #define cc_ccache_get_last_default_time(ccache, time) \ @@ -528,11 +558,11 @@ cc_int32 cc_initialize ( #define cc_ccache_compare(ccache, compare_to, equal) \ ((ccache) -> functions -> compare (ccache, compare_to, equal)) #define cc_ccache_get_kdc_time_offset(ccache, version, time) \ - ((ccache) -> functions -> get_kdc_time_offset (version, time)) + ((ccache) -> functions -> get_kdc_time_offset (version, time)) #define cc_ccache_set_kdc_time_offset(ccache, version, time) \ - ((ccache) -> functions -> set_kdc_time_offset (version, time)) + ((ccache) -> functions -> set_kdc_time_offset (version, time)) #define cc_ccache_clear_kdc_time_offset(ccache, version) \ - ((ccache) -> functions -> clear_kdc_time_offset (version)) + ((ccache) -> functions -> clear_kdc_time_offset (version)) #define cc_string_release(string) \ ((string) -> functions -> release (string)) @@ -546,11 +576,15 @@ cc_int32 cc_initialize ( ((iterator) -> functions -> release (iterator)) #define cc_ccache_iterator_next(iterator, ccache) \ ((iterator) -> functions -> next (iterator, ccache)) +#define cc_ccache_iterator_clone(iterator, new_iter) \ + ((iterator) -> functions -> clone (iterator, new_iter)) #define cc_credentials_iterator_release(iterator) \ ((iterator) -> functions -> release (iterator)) #define cc_credentials_iterator_next(iterator, credentials) \ ((iterator) -> functions -> next (iterator, credentials)) +#define cc_credentials_iterator_clone(iterator, new_iter) \ + ((iterator) -> functions -> clone (iterator, new_iter)) #if TARGET_OS_MAC #if defined(__MWERKS__) diff --git a/src/lib/ccapi/include/CredentialsCache2.h b/src/lib/ccapi/include/CredentialsCache2.h index 401e093f4..214d93a02 100644 --- a/src/lib/ccapi/include/CredentialsCache2.h +++ b/src/lib/ccapi/include/CredentialsCache2.h @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 1998-2004 by the Massachusetts Institute of Technology. + * Copyright 1998-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -48,7 +48,7 @@ #ifndef __CREDENTIALSCACHE2__ #define __CREDENTIALSCACHE2__ -#include +#include "CredentialsCache.h" #if defined(macintosh) || (defined(__MACH__) && defined(__APPLE__)) #include #if TARGET_RT_MAC_CFM @@ -185,25 +185,25 @@ enum { CC_CRED_MAX }; -cc_int32 cc_shutdown ( +CCACHE_API cc_int32 cc_shutdown ( apiCB** ioContext); -cc_int32 cc_get_NC_info ( +CCACHE_API cc_int32 cc_get_NC_info ( apiCB* inContext, infoNC*** outInfo); -cc_int32 cc_get_change_time ( +CCACHE_API cc_int32 cc_get_change_time ( apiCB* inContext, cc_time_t* outTime); -cc_int32 cc_open ( +CCACHE_API cc_int32 cc_open ( apiCB* inContext, const char* inName, cc_int32 inVersion, cc_uint32 inFlags, ccache_p** outCCache); -cc_int32 cc_create ( +CCACHE_API cc_int32 cc_create ( apiCB* inContext, const char* inName, const char* inPrincipal, @@ -211,85 +211,85 @@ cc_int32 cc_create ( cc_uint32 inFlags, ccache_p** outCCache); -cc_int32 cc_close ( +CCACHE_API cc_int32 cc_close ( apiCB* inContext, ccache_p** ioCCache); -cc_int32 cc_destroy ( +CCACHE_API cc_int32 cc_destroy ( apiCB* inContext, ccache_p** ioCCache); -cc_int32 cc_seq_fetch_NCs_begin ( +CCACHE_API cc_int32 cc_seq_fetch_NCs_begin ( apiCB* inContext, - ccache_cit** outIterator); + ccache_cit** outIterator); -cc_int32 cc_seq_fetch_NCs_next ( +CCACHE_API cc_int32 cc_seq_fetch_NCs_next ( apiCB* inContext, ccache_p** outCCache, ccache_cit* inIterator); -cc_int32 cc_seq_fetch_NCs_end ( +CCACHE_API cc_int32 cc_seq_fetch_NCs_end ( apiCB* inContext, - ccache_cit** ioIterator); + ccache_cit** ioIterator); -cc_int32 cc_get_name ( +CCACHE_API cc_int32 cc_get_name ( apiCB* inContext, ccache_p* inCCache, char** outName); -cc_int32 cc_get_cred_version ( +CCACHE_API cc_int32 cc_get_cred_version ( apiCB* inContext, ccache_p* inCCache, cc_int32* outVersion); -cc_int32 cc_set_principal ( +CCACHE_API cc_int32 cc_set_principal ( apiCB* inContext, ccache_p* inCCache, cc_int32 inVersion, char* inPrincipal); -cc_int32 cc_get_principal ( +CCACHE_API cc_int32 cc_get_principal ( apiCB* inContext, ccache_p* inCCache, char** outPrincipal); -cc_int32 cc_store ( +CCACHE_API cc_int32 cc_store ( apiCB* inContext, ccache_p* inCCache, cred_union inCredentials); -cc_int32 cc_remove_cred ( +CCACHE_API cc_int32 cc_remove_cred ( apiCB* inContext, ccache_p* inCCache, cred_union inCredentials); -cc_int32 cc_seq_fetch_creds_begin ( +CCACHE_API cc_int32 cc_seq_fetch_creds_begin ( apiCB* inContext, - const ccache_p* inCCache, - ccache_cit** outIterator); + const ccache_p* inCCache, + ccache_cit** outIterator); -cc_int32 cc_seq_fetch_creds_next ( +CCACHE_API cc_int32 cc_seq_fetch_creds_next ( apiCB* inContext, - cred_union** outCreds, + cred_union** outCreds, ccache_cit* inIterator); -cc_int32 cc_seq_fetch_creds_end ( +CCACHE_API cc_int32 cc_seq_fetch_creds_end ( apiCB* inContext, - ccache_cit** ioIterator); + ccache_cit** ioIterator); -cc_int32 cc_free_principal ( +CCACHE_API cc_int32 cc_free_principal ( apiCB* inContext, char** ioPrincipal); -cc_int32 cc_free_name ( +CCACHE_API cc_int32 cc_free_name ( apiCB* inContext, char** ioName); -cc_int32 cc_free_creds ( +CCACHE_API cc_int32 cc_free_creds ( apiCB* inContext, - cred_union** creds); + cred_union** creds); -cc_int32 cc_free_NC_info ( +CCACHE_API cc_int32 cc_free_NC_info ( apiCB* inContext, infoNC*** ioInfo); diff --git a/src/lib/ccapi/include/cc_rpc.h b/src/lib/ccapi/include/cc_rpc.h new file mode 100644 index 000000000..0f14724b9 --- /dev/null +++ b/src/lib/ccapi/include/cc_rpc.h @@ -0,0 +1,52 @@ +/* $Copyright: + * + * Copyright 2004-2006 by the Massachusetts Institute of Technology. + * + * All rights reserved. + * + * Export of this software from the United States of America may require a + * specific license from the United States Government. It is the + * responsibility of any person or organization contemplating export to + * obtain such a license before exporting. + * + * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute + * this software and its documentation for any purpose and without fee is + * hereby granted, provided that the above copyright notice appear in all + * copies and that both that copyright notice and this permission notice + * appear in supporting documentation, and that the name of M.I.T. not be + * used in advertising or publicity pertaining to distribution of the + * software without specific, written prior permission. Furthermore if you + * modify this software you must label your software as modified software + * and not distribute it in such a fashion that it might be confused with + * the original MIT software. M.I.T. makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. + * + * Individual source code files are copyright MIT, Cygnus Support, + * OpenVision, Oracle, Sun Soft, FundsXpress, and others. + * + * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, + * and Zephyr are trademarks of the Massachusetts Institute of Technology + * (MIT). No commercial use of these trademarks may be made without prior + * written permission of MIT. + * + * "Commercial use" means use of a name in a product or other for-profit + * manner. It does NOT prevent a commercial firm from referring to the MIT + * trademarks in order to convey information (although in doing so, + * recognition of their trademark status should be given). + * $ + */ + + +#ifndef __CC_RPC_H__ +#define __CC_RPC_H__ + +#include "msg.h" + +cc_int32 cci_perform_rpc(cc_msg_t *request, cc_msg_t **response); + +#endif /* __CC_RPC_H__ */ diff --git a/src/lib/ccapi/include/generic_lists.h b/src/lib/ccapi/include/generic_lists.h new file mode 100644 index 000000000..4d49e276b --- /dev/null +++ b/src/lib/ccapi/include/generic_lists.h @@ -0,0 +1,95 @@ +/* $Copyright: + * + * Copyright 2004-2006 by the Massachusetts Institute of Technology. + * + * All rights reserved. + * + * Export of this software from the United States of America may require a + * specific license from the United States Government. It is the + * responsibility of any person or organization contemplating export to + * obtain such a license before exporting. + * + * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute + * this software and its documentation for any purpose and without fee is + * hereby granted, provided that the above copyright notice appear in all + * copies and that both that copyright notice and this permission notice + * appear in supporting documentation, and that the name of M.I.T. not be + * used in advertising or publicity pertaining to distribution of the + * software without specific, written prior permission. Furthermore if you + * modify this software you must label your software as modified software + * and not distribute it in such a fashion that it might be confused with + * the original MIT software. M.I.T. makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. + * + * Individual source code files are copyright MIT, Cygnus Support, + * OpenVision, Oracle, Sun Soft, FundsXpress, and others. + * + * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, + * and Zephyr are trademarks of the Massachusetts Institute of Technology + * (MIT). No commercial use of these trademarks may be made without prior + * written permission of MIT. + * + * "Commercial use" means use of a name in a product or other for-profit + * manner. It does NOT prevent a commercial firm from referring to the MIT + * trademarks in order to convey information (although in doing so, + * recognition of their trademark status should be given). + * $ + */ +/* + * Prototypes and data structures for datastore. + * + */ + + +#ifndef __CC_GENERIC_LISTS_H_ +#define __CC_GENERIC_LISTS_H_ + +struct cc_generic_list_node_t { + cc_uint8* data; + cc_uint32 len; + struct cc_generic_list_node_t* next; + struct cc_generic_list_node_t* prev; +}; +typedef struct cc_generic_list_node_t cc_generic_list_node_t; + +struct cc_generic_list_head_t { + enum cc_list_type type; + cc_generic_list_node_t* head; + cc_generic_list_node_t* tail; +}; +typedef struct cc_generic_list_head_t cc_generic_list_head_t; + + +struct cc_generic_iterate_t { + cc_generic_list_node_t* next; +}; +typedef struct cc_generic_iterate_t cc_generic_iterate_t; + +typedef cc_generic_list_head_t cc_context_list_head_t; +typedef cc_generic_list_node_t cc_context_list_node_t; + +typedef cc_generic_list_head_t cc_ccache_list_head_t; +typedef cc_generic_list_node_t cc_ccache_list_node_t; + +typedef cc_generic_list_head_t cc_credentials_list_head_t; +typedef cc_generic_list_node_t cc_credentials_list_node_t; + +cc_int32 cci_generic_iterate_has_next(cc_generic_iterate_t *iterate); +cc_int32 cci_generic_iterate_next(cc_generic_iterate_t *iterate, cc_generic_list_node_t**); + +cc_int32 cci_generic_list_new(cc_generic_list_head_t **); +cc_int32 cci_generic_list_append(cc_generic_list_head_t *head, void *data, cc_uint32 len, cc_generic_list_node_t**); +cc_int32 cci_generic_list_prepend(cc_generic_list_head_t *head, void *data, cc_uint32 len, cc_generic_list_node_t**); +cc_int32 cci_generic_list_remove_element(cc_generic_list_head_t* head, cc_generic_list_node_t* rem); +cc_int32 cci_generic_free_element(cc_generic_list_node_t* node); +cc_int32 cci_generic_list_destroy(cc_generic_list_head_t* head); +cc_int32 cci_generic_list_copy(cc_generic_list_head_t* head, cc_generic_list_head_t**); +cc_int32 cci_generic_list_iterator(cc_generic_list_head_t *head, cc_generic_iterate_t**); +cc_int32 cci_generic_free_iterator(cc_generic_iterate_t* iterator); + +#endif /* __CC_GENERIC_LISTS_H_ */ diff --git a/src/lib/ccapi/include/marshall.h b/src/lib/ccapi/include/marshall.h index 19b9463b0..ca6b12e96 100644 --- a/src/lib/ccapi/include/marshall.h +++ b/src/lib/ccapi/include/marshall.h @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -41,7 +41,6 @@ * $ */ -#define FLAT_CREDS_V5_VERSION 1 struct cc_flat_data { cc_uint32 type; cc_uint32 length; @@ -49,15 +48,16 @@ struct cc_flat_data { }; typedef struct cc_flat_data cc_flat_data; +#define FLAT_CREDS_V5_VERSION 1 struct cci_flat_creds_v5 { cc_uint32 version; /* version of this structure */ cc_flat_data client; cc_flat_data server; cc_flat_data keyblock; - cc_time_t authtime; - cc_time_t starttime; - cc_time_t endtime; - cc_time_t renew_till; + cc_time64 authtime; + cc_time64 starttime; + cc_time64 endtime; + cc_time64 renew_till; cc_uint32 is_skey; cc_uint32 ticket_flags; cc_uint32 address_count; @@ -67,6 +67,25 @@ struct cci_flat_creds_v5 { cc_uint32 authdata_count; cc_uint32 authdata; /* offset to array */ }; +typedef struct cci_flat_creds_v5 cci_flat_creds_v5_t; + +struct cci_flat_creds_v4 { + cc_uint32 version; + char principal [cc_v4_name_size]; + char principal_instance [cc_v4_instance_size]; + char service [cc_v4_name_size]; + char service_instance [cc_v4_instance_size]; + char realm [cc_v4_realm_size]; + unsigned char session_key [cc_v4_key_size]; + cc_int32 kvno; + cc_int32 string_to_key_type; + cc_time64 issue_date; + cc_int32 lifetime; + cc_uint32 address; + cc_int32 ticket_size; + unsigned char ticket [cc_v4_ticket_size]; +}; +typedef struct cci_flat_creds_v4 cci_flat_creds_v4_t; cc_int32 cci_creds_v4_marshall( cc_credentials_v4_t * creds, diff --git a/src/lib/ccapi/include/msg.h b/src/lib/ccapi/include/msg.h index 0d712d666..182ebc161 100644 --- a/src/lib/ccapi/include/msg.h +++ b/src/lib/ccapi/include/msg.h @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -43,7 +43,7 @@ /* * Verifiable, extensible message format. - * + * * Format: * * @@ -60,13 +60,13 @@ * If the header has variable length data it is included in the data blobs. * The header field has the offset from the beginning of the message of the 1st * byte of the data and the length of the data. - * */ #ifndef __CC_MSG_H__ #define __CC_MSG_H__ #include "CredentialsCache.h" +#include "generic_lists.h" struct cc_msg_t { cc_uint32 type; /*type of message*/ @@ -87,16 +87,15 @@ enum { ccmsg_CTX_RELEASE, ccmsg_CTX_GET_CHANGE_TIME, ccmsg_CTX_GET_DEFAULT_CCACHE_NAME, - ccmsg_CTX_COMPARE, + ccmsg_CTX_CCACHE_OPEN, + ccmsg_CTX_CCACHE_OPEN_DEFAULT, + ccmsg_CTX_CCACHE_CREATE, + ccmsg_CTX_CCACHE_CREATE_DEFAULT, + ccmsg_CTX_CCACHE_CREATE_UNIQUE, ccmsg_CTX_NEW_CCACHE_ITERATOR, ccmsg_CTX_LOCK, ccmsg_CTX_UNLOCK, - ccmsg_CTX_CLONE, - ccmsg_CCACHE_OPEN, - ccmsg_CCACHE_OPEN_DEFAULT, - ccmsg_CCACHE_CREATE, - ccmsg_CCACHE_CREATE_DEFAULT, - ccmsg_CCACHE_CREATE_UNIQUE, + ccmsg_CTX_COMPARE, ccmsg_CCACHE_RELEASE, ccmsg_CCACHE_DESTROY, ccmsg_CCACHE_SET_DEFAULT, @@ -104,29 +103,28 @@ enum { ccmsg_CCACHE_GET_NAME, ccmsg_CCACHE_GET_PRINCIPAL, ccmsg_CCACHE_SET_PRINCIPAL, - ccmsg_CCACHE_CREDS_ITERATOR, + ccmsg_CCACHE_NEW_CREDS_ITERATOR, ccmsg_CCACHE_STORE_CREDS, ccmsg_CCACHE_REM_CREDS, + ccmsg_CCACHE_MOVE, + ccmsg_CCACHE_LOCK, + ccmsg_CCACHE_UNLOCK, ccmsg_CCACHE_GET_LAST_DEFAULT_TIME, ccmsg_CCACHE_GET_CHANGE_TIME, - ccmsg_CCACHE_MOVE, ccmsg_CCACHE_COMPARE, ccmsg_CCACHE_GET_KDC_TIME_OFFSET, ccmsg_CCACHE_SET_KDC_TIME_OFFSET, ccmsg_CCACHE_CLEAR_KDC_TIME_OFFSET, ccmsg_CCACHE_ITERATOR_RELEASE, ccmsg_CCACHE_ITERATOR_NEXT, - ccmsg_CCACHE_LOCK, - ccmsg_CCACHE_UNLOCK, + ccmsg_CCACHE_ITERATOR_CLONE, ccmsg_CREDS_ITERATOR_RELEASE, ccmsg_CREDS_ITERATOR_NEXT, - ccmsg_CREDS_RELEASE, - ccmsg_CREDS_V4, - ccmsg_CREDS_V5 + ccmsg_CREDS_ITERATOR_CLONE }; #define CC_MSG_MAX_SIZE 1073741824 /*2^30*/ -#define CC_MSG_MAX_TYPE ccmsg_CREDS_V5 +#define CC_MSG_MAX_TYPE ccmsg_CREDS_ITERATOR_CLONE #define BLOB_LEN (sizeof(cc_uint32)) #define MAGIC_DATA_LEN (sizeof(cc_uint32)) #define MAGIC_HEAD_LEN (sizeof(cc_uint32)) @@ -143,4 +141,21 @@ cc_int32 cci_msg_verify(void* flat, int flat_len, cc_uint32 * sizep); cc_int32 cci_msg_unflatten(void *flat, int flat_len, cc_msg_t** msgpp); cc_int32 cci_msg_retrieve_blob(cc_msg_t* msg, cc_uint32 blob_offset, cc_uint32 blob_len, void **); cc_int32 cci_msg_destroy(cc_msg_t* msg); + +/* Add missing byte swapping macros for 64-bit values */ +#ifdef MAC +#define htonll(x) OSSwapHostToBigInt64(x) +#define ntohll(x) OSSwapBigToHostInt64(x) +#else +#ifdef _WIN32 +#ifdef _M_IX86 +#define htonll(x) _byteswap_uint64(x) +#define ntohll(x) _byteswap_uint64(x) +#else +#define htonll(x) (x) +#define ntohll(x) (x) +#endif +#endif +#endif + #endif /*__CC_MSG_H__*/ diff --git a/src/lib/ccapi/include/msg_headers.h b/src/lib/ccapi/include/msg_headers.h index a27c2d2f1..b5a9acd6d 100644 --- a/src/lib/ccapi/include/msg_headers.h +++ b/src/lib/ccapi/include/msg_headers.h @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -57,6 +57,8 @@ * size divisible by 4. This is to ensure correct alignment * and stop different compilers from inserting padding bytes in * different places. + * + * All values are stored in network byte order. */ struct ccmsg_ctx_only_t { @@ -81,18 +83,18 @@ struct ccmsg_init_resp_t { typedef struct ccmsg_init_t ccmsg_init_t; typedef struct ccmsg_init_resp_t ccmsg_init_resp_t; -struct ccmsg_clone_t { +struct ccmsg_ctx_clone_t { cc_handle ctx; cc_uint32 in_version; /*client API version*/ }; -struct ccmsg_clone_resp_t { +struct ccmsg_ctx_clone_resp_t { cc_handle out_ctx; /*handle on this ctx*/ cc_uint32 out_version; /*server API version*/ cc_uint32 vendor_offset; /*offset of vendor blob*/ cc_uint32 vendor_length; /*length of vendor blob*/ }; -typedef struct ccmsg_clone_t ccmsg_clone_t; -typedef struct ccmsg_clone_resp_t ccmsg_clone_resp_t; +typedef struct ccmsg_ctx_clone_t ccmsg_ctx_clone_t; +typedef struct ccmsg_ctx_clone_resp_t ccmsg_ctx_clone_resp_t; struct ccmsg_ctx_release_t { cc_handle ctx; /*# of ctx to release*/ @@ -103,7 +105,7 @@ struct ccmsg_ctx_get_change_time_t { cc_handle ctx; }; struct ccmsg_ctx_get_change_time_resp_t { - cc_time_t time; + cc_time64 time; }; typedef struct ccmsg_ctx_get_change_time_t ccmsg_ctx_get_change_time_t; typedef struct ccmsg_ctx_get_change_time_resp_t ccmsg_ctx_get_change_time_resp_t; @@ -304,7 +306,7 @@ struct ccmsg_ccache_get_last_default_time_t { cc_handle ccache; }; struct ccmsg_ccache_get_last_default_time_resp_t { - cc_time_t last_default_time; + cc_time64 last_default_time; }; typedef struct ccmsg_ccache_get_last_default_time_t ccmsg_ccache_get_last_default_time_t; typedef struct ccmsg_ccache_get_last_default_time_resp_t ccmsg_ccache_get_last_default_time_resp_t; @@ -314,7 +316,7 @@ struct ccmsg_ccache_get_change_time_t { cc_handle ccache; }; struct ccmsg_ccache_get_change_time_resp_t { - cc_time_t time; + cc_time64 time; }; typedef struct ccmsg_ccache_get_change_time_t ccmsg_ccache_get_change_time_t; typedef struct ccmsg_ccache_get_change_time_resp_t ccmsg_ccache_get_change_time_resp_t; @@ -336,7 +338,7 @@ struct ccmsg_ccache_get_kdc_time_offset_t { cc_int32 creds_version; }; struct ccmsg_ccache_get_kdc_time_offset_resp_t { - cc_time_t offset; + cc_time64 offset; }; typedef struct ccmsg_ccache_get_kdc_time_offset_t ccmsg_ccache_get_kdc_time_offset_t; typedef struct ccmsg_ccache_get_kdc_time_offset_resp_t ccmsg_ccache_get_kdc_time_offset_resp_t; @@ -344,7 +346,7 @@ typedef struct ccmsg_ccache_get_kdc_time_offset_resp_t ccmsg_ccache_get_kdc_time struct ccmsg_ccache_set_kdc_time_offset_t { cc_handle ctx; cc_handle ccache; - cc_time_t offset; + cc_time64 offset; cc_int32 creds_version; }; typedef struct ccmsg_ccache_set_kdc_time_offset_t ccmsg_ccache_set_kdc_time_offset_t; @@ -372,6 +374,16 @@ struct ccmsg_ccache_iterator_next_resp_t { typedef struct ccmsg_ccache_iterator_next_t ccmsg_ccache_iterator_next_t; typedef struct ccmsg_ccache_iterator_next_resp_t ccmsg_ccache_iterator_next_resp_t; +struct ccmsg_ccache_iterator_clone_t { + cc_handle ctx; + cc_handle iterator; +}; +struct ccmsg_ccache_iterator_clone_resp_t { + cc_handle iterator; +}; +typedef struct ccmsg_ccache_iterator_clone_t ccmsg_ccache_iterator_clone_t; +typedef struct ccmsg_ccache_iterator_clone_resp_t ccmsg_ccache_iterator_clone_resp_t; + struct ccmsg_creds_iterator_release_t { cc_handle ctx; cc_handle ccache; @@ -393,37 +405,14 @@ struct ccmsg_creds_iterator_next_resp_t { typedef struct ccmsg_creds_iterator_next_t ccmsg_creds_iterator_next_t; typedef struct ccmsg_creds_iterator_next_resp_t ccmsg_creds_iterator_next_resp_t; -struct ccmsg_creds_v4_t { - cc_uint32 offset; - cc_uint32 len; -}; -typedef struct ccmsg_creds_v4_t ccmsg_creds_v4_t; - -struct ccmsg_creds_v5_t { - cc_uint32 client_offset; - cc_uint32 client_len; - cc_uint32 server_offset; - cc_uint32 server_len; - cc_uint32 keyblock_offset; - cc_uint32 keyblock_len; - cc_time_t authtime; - cc_time_t starttime; - cc_time_t endtime; - cc_time_t renewtime; - cc_uint32 is_skey; - cc_uint32 ticket_flags; - cc_uint32 address_count; - cc_uint32 address_offset; - cc_uint32 address_len; - cc_uint32 ticket_offset; - cc_uint32 ticket_len; - cc_uint32 ticket2_offset; - cc_uint32 ticket2_len; - cc_uint32 authdata_count; - cc_uint32 authdata_offset; - cc_uint32 authdata_len; -}; -typedef struct ccmsg_creds_v5_t ccmsg_creds_v5_t; - +struct ccmsg_creds_iterator_clone_t { + cc_handle ctx; + cc_handle iterator; +}; +struct ccmsg_creds_iterator_clone_resp_t { + cc_handle iterator; +}; +typedef struct ccmsg_creds_iterator_clone_t ccmsg_creds_iterator_clone_t; +typedef struct ccmsg_creds_iterator_clone_resp_t ccmsg_creds_iterator_clone_resp_t; #endif /*__MSG_HEADERS_H__*/ diff --git a/src/lib/ccapi/marshall.c b/src/lib/ccapi/marshall.c deleted file mode 100644 index 7027d6561..000000000 --- a/src/lib/ccapi/marshall.c +++ /dev/null @@ -1,378 +0,0 @@ -/* $Copyright: - * - * Copyright 2004 by the Massachusetts Institute of Technology. - * - * All rights reserved. - * - * Export of this software from the United States of America may require a - * specific license from the United States Government. It is the - * responsibility of any person or organization contemplating export to - * obtain such a license before exporting. - * - * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute - * this software and its documentation for any purpose and without fee is - * hereby granted, provided that the above copyright notice appear in all - * copies and that both that copyright notice and this permission notice - * appear in supporting documentation, and that the name of M.I.T. not be - * used in advertising or publicity pertaining to distribution of the - * software without specific, written prior permission. Furthermore if you - * modify this software you must label your software as modified software - * and not distribute it in such a fashion that it might be confused with - * the original MIT software. M.I.T. makes no representations about the - * suitability of this software for any purpose. It is provided "as is" - * without express or implied warranty. - * - * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED - * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF - * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. - * - * Individual source code files are copyright MIT, Cygnus Support, - * OpenVision, Oracle, Sun Soft, FundsXpress, and others. - * - * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, - * and Zephyr are trademarks of the Massachusetts Institute of Technology - * (MIT). No commercial use of these trademarks may be made without prior - * written permission of MIT. - * - * "Commercial use" means use of a name in a product or other for-profit - * manner. It does NOT prevent a commercial firm from referring to the MIT - * trademarks in order to convey information (although in doing so, - * recognition of their trademark status should be given). - * $ - */ - -/* marshall.c */ - -#include -#include -#include -#include "msg.h" -#include "msg_headers.h" -#include "marshall.h" - -cc_int32 -cci_creds_v4_marshall( cc_credentials_v4_t * creds, - char ** flat, - cc_uint32 * len) -{ - cc_msg_t * msg; - ccmsg_creds_v4_t * header; - cc_uint32 blob_pos; - cc_int32 code; - - if ( creds == NULL || flat == NULL || len == NULL ) - return ccErrBadParam; - - header = (ccmsg_creds_v4_t *)malloc(sizeof(ccmsg_creds_v4_t)); - if ( header == NULL ) - return ccErrNoMem; - - code = cci_msg_new(ccmsg_CREDS_V4, &msg); - - code = cci_msg_add_header(msg, header, sizeof(ccmsg_creds_v4_t)); - - code = cci_msg_add_data_blob(msg, creds, sizeof(cc_credentials_v4_t), &blob_pos); - - header->offset = blob_pos; - header->len = sizeof(cc_credentials_v4_t); - - code = cci_msg_flatten( msg, NULL ); - - *flat = msg->flat; - *len = msg->flat_len; - msg->flat = NULL; - msg->flat_len = 0; - - cci_msg_destroy(msg); - - return ccNoError; -} - -cc_int32 -cci_creds_v4_unmarshall( char * flat, - cc_uint32 len, - cc_credentials_union * creds) -{ - cc_msg_t * msg; - ccmsg_creds_v4_t * header; - cc_int32 code; - - if ( flat == NULL || len == 0 || creds == NULL ) - return ccErrBadParam; - - code = cci_msg_unflatten( flat, len, &msg ); - - header = (ccmsg_creds_v4_t *)msg->header; - - creds->version = cc_credentials_v4; - code = cci_msg_retrieve_blob(msg, header->offset, header->len, &creds->credentials.credentials_v4); - - cci_msg_destroy(msg); - - return ccNoError; -} - - -cc_int32 -cci_creds_cc_data_array_count_entries( cc_data ** array, cc_uint32 * pcount) -{ - cc_uint32 count; - - if (array == NULL) { - *pcount = 0; - return ccNoError; - } - - for ( count=0; array[count] != NULL ; count++) ; - - *pcount = count; - return ccNoError; -} - -cc_int32 -cci_creds_v5_compute_flat_size( cc_credentials_v5_t * creds, cc_uint32 * plen) -{ - cc_uint32 len; - cc_uint32 i, count; - - len = sizeof(struct cci_flat_creds_v5); - - if (creds->client) - len += strlen(creds->client) + 1; - - if (creds->server) - len += strlen(creds->server) + 1; - - len += creds->keyblock.length; - - cci_creds_cc_data_array_count_entries( creds->addresses, &count ); - len += count * sizeof(cc_flat_data); - for ( i=0; iaddresses[i]->length; - } - - len += creds->ticket.length; - len += creds->second_ticket.length; - - cci_creds_cc_data_array_count_entries( creds->authdata, &count ); - len += count * sizeof(cc_flat_data); - for ( i=0; iauthdata[i]->length; - } - - *plen = len; - return ccNoError; -} - -cc_int32 -cci_creds_v5_marshall( cc_credentials_v5_t * creds, - char ** pflat, - cc_uint32 * plen) -{ - cc_uint32 len; - char * flat; - struct cci_flat_creds_v5 * header; - cc_uint32 offset; - cc_uint32 i; - - if ( creds == NULL || pflat == NULL || plen == NULL ) - return ccErrBadParam; - - cci_creds_v5_compute_flat_size(creds, &len); - - flat = (char *)malloc(len); - if ( flat == NULL ) - return ccErrNoMem; - memset(flat, 0, len); - - offset = sizeof(struct cci_flat_creds_v5); - header = (struct cci_flat_creds_v5 *)flat; - header->version = FLAT_CREDS_V5_VERSION; - if (creds->client) { - header->client.length = strlen(creds->client) + 1; - header->client.data = offset; - memcpy(flat + offset, creds->client, header->client.length); - offset += header->client.length; - } - - if (creds->server) { - header->server.length = strlen(creds->server) + 1; - header->server.data = offset; - memcpy(flat + offset, creds->server, header->server.length); - offset += header->server.length; - } - - header->keyblock.type = creds->keyblock.type; - if (creds->keyblock.length) { - header->keyblock.length = creds->keyblock.length; - header->keyblock.data = offset; - memcpy(flat + offset, creds->keyblock.data, header->keyblock.length); - offset += header->keyblock.length; - } - - header->authtime = creds->authtime; - header->starttime = creds->starttime; - header->endtime = creds->endtime; - header->renew_till = creds->renew_till; - header->is_skey = creds->is_skey; - header->ticket_flags = creds->ticket_flags; - - cci_creds_cc_data_array_count_entries( creds->addresses, &header->address_count ); - if ( header->address_count ) { - cc_flat_data * addresses = (cc_flat_data *)flat + offset; - header->addresses = offset; - offset += header->address_count * sizeof(cc_flat_data); - - for ( i=0; iaddress_count; i++ ) { - addresses[i].type = creds->addresses[i]->type; - if (creds->addresses[i]->length) { - addresses[i].length = creds->addresses[i]->length; - addresses[i].data = offset; - memcpy(flat + offset, creds->addresses[i]->data, addresses[i].length); - offset += addresses[i].length; - } - } - } - - header->ticket.type = creds->ticket.type; - if (creds->ticket.length) { - header->ticket.length = creds->ticket.length; - header->ticket.data = offset; - memcpy(flat + offset, creds->ticket.data, header->ticket.length); - offset += header->ticket.length; - } - - header->second_ticket.type = creds->second_ticket.type; - if (creds->second_ticket.length) { - header->second_ticket.length = creds->second_ticket.length; - header->second_ticket.data = offset; - memcpy(flat + offset, creds->second_ticket.data, header->second_ticket.length); - offset += header->second_ticket.length; - } - - cci_creds_cc_data_array_count_entries( creds->authdata, &header->authdata_count ); - if ( header->authdata_count ) { - cc_flat_data * authdata = (cc_flat_data *)flat + offset; - header->authdata = offset; - offset += header->authdata_count * sizeof(cc_flat_data); - - for ( i=0; iauthdata_count; i++ ) { - authdata[i].type = creds->authdata[i]->type; - if (creds->authdata[i]->length) { - authdata[i].length = creds->authdata[i]->length; - authdata[i].data = offset; - memcpy(flat + offset, creds->authdata[i]->data, authdata[i].length); - offset += authdata[i].length; - } - } - } - - *pflat = flat; - *plen = len; - return ccNoError; -} - - -// TODO: a much better job of checking for out of memory errors -// and validating that we do not read beyond the flat input -// data buffer - -cc_int32 -cci_creds_v5_unmarshall( char * flat, - cc_uint32 len, - cc_credentials_union * creds_union) -{ - struct cci_flat_creds_v5 * header; - cc_credentials_v5_t * creds; - cc_flat_data * flat_data; - cc_uint32 i; - cc_int32 code; - - if ( flat == NULL || len == 0 || creds_union == NULL ) - return ccErrBadParam; - - creds_union->version = cc_credentials_v5; - - header = (struct cci_flat_creds_v5 *)flat; - - if ( header->version != FLAT_CREDS_V5_VERSION ) - return ccErrBadParam; - - creds = (cc_credentials_v5_t *)malloc(sizeof(cc_credentials_v5_t)); - if ( creds == NULL ) - return ccErrNoMem; - memset(creds, 0, sizeof(ccmsg_creds_v5_t)); - - if ( header->client.length ) { - creds->client = (char *)malloc(header->client.length); - memcpy(creds->client, flat + header->client.data, header->client.length); - } - - if ( header->server.length ) { - creds->server = (char *)malloc(header->server.length); - memcpy(creds->server, flat + header->server.data, header->server.length); - } - - creds->keyblock.type = header->keyblock.type; - if ( header->keyblock.length ) { - creds->keyblock.length = header->keyblock.length; - creds->keyblock.data = malloc(creds->keyblock.length); - memcpy(creds->keyblock.data, flat + header->keyblock.data, creds->keyblock.length); - } - - creds->authtime = header->authtime; - creds->starttime = header->starttime; - creds->endtime = header->endtime; - creds->renew_till = header->renew_till; - creds->is_skey = header->is_skey; - creds->ticket_flags = header->ticket_flags; - - creds->addresses = (cc_data **) malloc((header->address_count + 1) * sizeof(cc_data *)); - flat_data = (cc_flat_data *)flat + header->addresses; - for ( i=0 ; i < header->address_count ; i++ ) { - creds->addresses[i] = (cc_data *)malloc(sizeof(cc_data)); - creds->addresses[i]->type = flat_data[i].type; - creds->addresses[i]->length = flat_data[i].length; - if ( flat_data[i].length ) { - creds->addresses[i]->data = malloc(flat_data[i].length); - memcpy(creds->addresses[i]->data, flat + flat_data[i].data, flat_data[i].length); - } else { - creds->addresses[i]->data = NULL; - } - } - creds->addresses[i] = NULL; - - creds->ticket.type = header->ticket.type; - if ( header->ticket.length ) { - creds->ticket.length = header->ticket.length; - creds->ticket.data = malloc(creds->ticket.length); - memcpy(creds->ticket.data, flat + header->ticket.data, creds->ticket.length); - } - - creds->second_ticket.type = header->second_ticket.type; - if ( header->second_ticket.length ) { - creds->second_ticket.length = header->second_ticket.length; - creds->second_ticket.data = malloc(creds->second_ticket.length); - memcpy(creds->second_ticket.data, flat + header->second_ticket.data, creds->second_ticket.length); - } - - creds->authdata = (cc_data **) malloc((header->authdata_count + 1) * sizeof(cc_data *)); - flat_data = (cc_flat_data *)flat + header->authdata; - for ( i=0 ; i < header->authdata_count ; i++ ) { - creds->authdata[i] = (cc_data *)malloc(sizeof(cc_data)); - creds->authdata[i]->type = flat_data[i].type; - creds->authdata[i]->length = flat_data[i].length; - if ( flat_data[i].length ) { - creds->authdata[i]->data = malloc(flat_data[i].length); - memcpy(creds->authdata[i]->data, flat + flat_data[i].data, flat_data[i].length); - } else { - creds->authdata[i]->data = NULL; - } - } - creds->authdata[i] = NULL; - - creds_union->credentials.credentials_v5 = creds; - - return ccNoError; -} - diff --git a/src/lib/ccapi/server/NTMakefile b/src/lib/ccapi/server/NTMakefile index 671b6905f..b221bcb94 100644 --- a/src/lib/ccapi/server/NTMakefile +++ b/src/lib/ccapi/server/NTMakefile @@ -4,23 +4,11 @@ CFLAGS = -I../include -CCAPI_LIB = ../lib/ccapi.lib +CCAPI_LIB = ../client/ccapi.lib WINLIBS = user32.lib advapi32.lib -CCSOBJS = context.obj ccache.obj lists.obj rpc_auth.obj serv_ops.obj +CCSOBJS = ccs_context.obj ccs_ccache.obj ccs_lists.obj rpc_auth.obj serv_ops.obj -all: t_lists.exe t_msg.exe t_ccache.exe t_context.exe ccapi_server.exe - -t_lists.exe: t_lists.obj $(CCSOBJS) $(CCAPI_LIB) - link -out:$@ t_lists.obj $(CCSOBJS) $(CCAPI_LIB) $(WINLIBS) - -t_msg.exe: t_msg.obj $(CCSOBJS) $(CCAPI_LIB) - link -out:$@ t_msg.obj $(CCSOBJS) $(CCAPI_LIB) $(WINLIBS) - -t_ccache.exe: t_ccache.obj $(CCSOBJS) $(CCAPI_LIB) - link -out:$@ t_ccache.obj $(CCSOBJS) $(CCAPI_LIB) $(WINLIBS) - -t_context.exe: t_context.obj $(CCSOBJS) $(CCAPI_LIB) - link -out:$@ t_context.obj $(CCSOBJS) $(CCAPI_LIB) $(WINLIBS) +all: ccapi_server.exe ccapi_server.exe: main.obj $(CCSOBJS) $(CCAPI_LIB) link -out:$@ main.obj $(CCSOBJS) $(CCAPI_LIB) $(WINLIBS) diff --git a/src/lib/ccapi/server/ccache.c b/src/lib/ccapi/server/ccs_ccache.c similarity index 83% rename from src/lib/ccapi/server/ccache.c rename to src/lib/ccapi/server/ccs_ccache.c index 2c3a745af..d632ee349 100644 --- a/src/lib/ccapi/server/ccache.c +++ b/src/lib/ccapi/server/ccs_ccache.c @@ -1,703 +1,703 @@ -/* $Copyright: - * - * Copyright 2004 by the Massachusetts Institute of Technology. - * - * All rights reserved. - * - * Export of this software from the United States of America may require a - * specific license from the United States Government. It is the - * responsibility of any person or organization contemplating export to - * obtain such a license before exporting. - * - * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute - * this software and its documentation for any purpose and without fee is - * hereby granted, provided that the above copyright notice appear in all - * copies and that both that copyright notice and this permission notice - * appear in supporting documentation, and that the name of M.I.T. not be - * used in advertising or publicity pertaining to distribution of the - * software without specific, written prior permission. Furthermore if you - * modify this software you must label your software as modified software - * and not distribute it in such a fashion that it might be confused with - * the original MIT software. M.I.T. makes no representations about the - * suitability of this software for any purpose. It is provided "as is" - * without express or implied warranty. - * - * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED - * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF - * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. - * - * Individual source code files are copyright MIT, Cygnus Support, - * OpenVision, Oracle, Sun Soft, FundsXpress, and others. - * - * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, - * and Zephyr are trademarks of the Massachusetts Institute of Technology - * (MIT). No commercial use of these trademarks may be made without prior - * written permission of MIT. - * - * "Commercial use" means use of a name in a product or other for-profit - * manner. It does NOT prevent a commercial firm from referring to the MIT - * trademarks in order to convey information (although in doing so, - * recognition of their trademark status should be given). - * $ - */ - -/* - * Manages ccache objects. - * - */ - -#include -#include -#include -#include -#include "CredentialsCache.h" -#include "datastore.h" - -/** - * ccache_new() - * - * Purpose: Allocate and initialize new credentials cache for the specified principal - * and version - * - * Return: ccNoError - success - * ccErrInvalidString - name or principal is NULL - * ccErrBadCredentialsVersion - unsupported creds type - * ccErrBadParam - outCcachepp is NULL - * ccErrNoMem - malloc failed - */ -cc_int32 -cci_ccache_new( char *name, char *principal, int cred_vers, - cc_server_ccache_t** outCCachepp) -{ - cc_server_ccache_t* ccache; - - if (name == NULL || principal == NULL) - return ccErrInvalidString; - - if (cred_vers != cc_credentials_v4 && cred_vers != cc_credentials_v5 && - cred_vers != cc_credentials_v4_v5) - return ccErrBadCredentialsVersion; - - if (outCCachepp == NULL) - return ccErrBadParam; - - ccache = (cc_server_ccache_t*)malloc(sizeof(cc_server_ccache_t)); - if (ccache == NULL) - return ccErrNoMem; - - ccache->name = name; - ccache->principal_v4 = NULL; - ccache->principal_v5 = NULL; - ccache->changed = time(NULL); - ccache->kdc_offset = 0; - ccache->last_default = 0; - cci_generic_list_new(&ccache->active_iterators); - cci_credentials_list_new(&ccache->creds); - ccache->is_default = 0; - ccache->kdc_set = 0; - ccache->versions = cred_vers; - ccache->mycontext = NULL; - - cci_ccache_set_principal(ccache, cred_vers, principal); - *outCCachepp = ccache; - return ccNoError; -} - -/** - * cci_ccache_check_version() - * - * Purpose: Check to see if the ccache and the creds have compatible versions. - * - * Return: ccNoError and compat = 1 if they are compatible - * ccNoError and compat = 0 if they are not compatible - * - * Errors: ccErrInvalidCCache - ccache is NULL - * ccErrBadParam - either creds or compat are NULL - */ -cc_int32 -cci_ccache_check_version( const cc_server_ccache_t *ccache, - const cc_credentials_union* creds, - cc_uint32* compat) -{ - if (ccache == NULL) - return ccErrInvalidCCache; - - if (creds == NULL || compat == NULL) - return ccErrBadParam; - - if (ccache->versions == cc_credentials_v4_v5) - *compat = 1; - else if (ccache->versions == creds->version) - *compat = 1; - else - *compat = 0; - - return ccNoError; -} - -/** -cci_ccache_check_principal() - -Check to see if the client principal from the credentials matches -the principal associated with the cache. - -* Return: ccNoError and compat = 1 if they are compatible -* ccNoError and compat = 0 if they are not compatible -* -* Errors: ccErrInvalidCCache - ccache is NULL -* ccErrBadParam - either creds or compat are NULL -* ccErrBadCredentialVersion - unsupported credential type -*/ -cc_int32 -cci_ccache_check_principal( const cc_server_ccache_t *ccache, - const cc_credentials_union* creds, - cc_uint32* compat) -{ - if (ccache == NULL) - return ccErrInvalidCCache; - - if (creds == NULL || compat == NULL) - return ccErrBadParam; - - if (creds->version == cc_credentials_v4) { - if (strcmp(creds->credentials.credentials_v4->principal, ccache->principal_v4) == 0) - *compat = 1; - else - *compat = 0; - } else if (creds->version == cc_credentials_v5) { - if (strcmp(creds->credentials.credentials_v5->client, ccache->principal_v5) == 0) - *compat = 1; - else - *compat = 0; - } else { - return ccErrBadCredentialsVersion; - } - return ccNoError; -} - - -/** - * cci_ccache_store_creds() - * - * Purpose: Stores the provided credentials into the provided cache. Validates the - * ability of the cache to store credentials of the given version and client - * principal. - * - * Return: 0 on success - * -1 on error - * - * Errors: ccErrNoMem - * ccErrBadCredentialsVersion - * ccErrBadInvalidCredentials - * ccErrInvalidCache - * ccErrBadParam - */ -cc_int32 -cci_ccache_store_creds(cc_server_ccache_t *ccache, const cc_credentials_union* credentials) -{ - cc_server_credentials_t* stored_cred=NULL; - cc_uint32 valid_version, valid_principal; - cc_int32 code; - - if (ccache == NULL) - return ccErrInvalidCCache; - - if (credentials == NULL) - return ccErrBadParam; - - code = cci_ccache_check_version(ccache, credentials, &valid_version); - if (code != ccNoError) { - /* pass error on to caller */ - goto bad; - } - code = cci_ccache_check_principal(ccache, credentials, &valid_principal); - if (code != ccNoError) { - /* pass error on to caller */ - goto bad; - } - if (valid_version && valid_principal) { - stored_cred = (cc_server_credentials_t*)malloc(sizeof(cc_server_credentials_t)); - if (stored_cred == NULL) { - code = ccErrNoMem; - goto bad; - } - memcpy(&stored_cred->creds, credentials, sizeof(cc_credentials_union)); - - if (credentials->version == cc_credentials_v4) { - stored_cred->creds.credentials.credentials_v4 = (cc_credentials_v4_t*)malloc(sizeof(cc_credentials_v4_t)); - if (stored_cred->creds.credentials.credentials_v4 == NULL) { - code = ccErrNoMem; - goto bad; - } - - memcpy(stored_cred->creds.credentials.credentials_v4, credentials->credentials.credentials_v4, sizeof(cc_credentials_v4_t)); - } else if (credentials->version == cc_credentials_v5) { - stored_cred->creds.credentials.credentials_v5 = (cc_credentials_v5_t*)malloc(sizeof(cc_credentials_v5_t)); - if (stored_cred->creds.credentials.credentials_v5 == NULL) { - code = ccErrNoMem; - goto bad; - } - - memcpy(stored_cred->creds.credentials.credentials_v5, credentials->credentials.credentials_v5, sizeof(cc_credentials_v5_t)); - } else { - code = ccErrBadCredentialsVersion; - goto bad; - } - - code = cci_credentials_list_append(ccache->creds, stored_cred, NULL); - if ( code != ccNoError ) { - /* pass error on to caller */ - goto bad; - } - if (ccache->creds->head->data == (cc_uint8 *)stored_cred) - stored_cred->is_default = 1; /*we're first on the list, so we're default*/ - - cci_ccache_changed(ccache); - return ccNoError; - } else { -#ifdef DEBUG - printf("vers: %d\tprincipal: %d\n", - valid_version, valid_principal); -#endif /* DEBUG */ - code = ccErrInvalidCredentials; - goto bad; - } - - bad: - if (stored_cred) - free(stored_cred); - return code; /* error */ -} - -/** - * cci_ccache_changed() - * - * Purpose: Updates the last update time for the ccache and its associated context. - * Provides a location from which interested parties should be notified - * of cache updates. - * - * Return: none - * - * Errors: none - */ -void -cci_ccache_changed(cc_server_ccache_t* ccache) -{ - ccache->changed = time(NULL); - if (ccache->mycontext != NULL) - ccache->mycontext->changed = time(NULL); - - /* XXX - notify registered listeners when implemented */ -} - -/** - * cci_ccache_rem_creds() - * - * Purpose: Removes the specified credential object from the specified cache if - * it exists - * - * Return: 0 on success (credential is not in the cache) - * -1 on error - * - * Errors: ccErrBadParam, ccErrNoMem (from cc_credentials_list_iterator) - * - * Verify: does the memory associated with stored_cred->creds need to be freed? - * - */ -cc_int32 -cci_ccache_rem_creds(cc_server_ccache_t *ccache, const cc_credentials_union* credentials) -{ - cc_credentials_iterate_t* credentials_iterator=NULL, *active; - cc_generic_iterate_t* generic_iterator=NULL; - cc_credentials_list_node_t* credentials_node; - cc_generic_list_node_t* generic_node; - cc_server_credentials_t* stored_cred; - cc_int8 changed = 0; - cc_int32 code = 0; - - if (ccache == NULL) - return ccErrInvalidCCache; - - if (credentials == NULL) - return ccErrBadParam; - - code = cci_credentials_list_iterator(ccache->creds, &credentials_iterator); - if (code != ccNoError) { - /* pass error to caller */ - goto cleanup; - } - - while (cci_credentials_iterate_has_next(credentials_iterator)) { - code = cci_credentials_iterate_next(credentials_iterator, &credentials_node); - stored_cred = (cc_server_credentials_t*)credentials_node->data; - if (memcmp(&stored_cred->creds,credentials,sizeof(cc_credentials_union)) == 0) { - /* XXX - do we need to free(stored_cred->creds) ? */ - free(credentials_node->data); - changed = 1; - - /*If any iterator's next points to the deleted node, make it point to the next node*/ - code = cci_generic_list_iterator(ccache->active_iterators, &generic_iterator); - while (cci_generic_iterate_has_next(generic_iterator)) { - code = cci_generic_iterate_next(generic_iterator, &generic_node); - active = (cc_credentials_iterate_t*)generic_node->data; - if (active->next == credentials_node) - active->next = active->next->next; - } - code = cci_generic_free_iterator(generic_iterator); - generic_iterator = NULL; - - if (credentials_node == ccache->creds->head) { /*removing the default, must make next cred default*/ - code = cci_credentials_list_remove_element(ccache->creds, credentials_node); - - if (ccache->creds->head != NULL) - ((cc_server_credentials_t*)ccache->creds->head->data)->is_default = 1; - } else { - code = cci_credentials_list_remove_element(ccache->creds, credentials_node); - } - break; - } - } - - cleanup: - if (changed) - cci_ccache_changed(ccache); - if (credentials_iterator) - cci_credentials_free_iterator(credentials_iterator); - if (generic_iterator) - cci_generic_free_iterator(generic_iterator); - return code; -} - -/** - * cci_ccache_move() - * - * Purpose: Destroys the existing contents of the destination and copies - * all credentials from the source to the destination - * - * Return: 0 on success - * -1 on error - * - * Errors: ccBadNoMem - * - */ - -cc_int32 -cci_ccache_move(cc_server_ccache_t *source, cc_server_ccache_t* destination) -{ - cc_generic_list_node_t* node; - cc_generic_iterate_t* iterator; - cc_credentials_iterate_t* cur; - cc_int32 code; - - if (source == NULL || destination == NULL) - return ccErrBadParam; - - code = cci_credentials_list_destroy(destination->creds); - if ( code != ccNoError ) - return code; - - code = cci_credentials_list_copy(source->creds, &destination->creds); - if ( code != ccNoError ) - return code; - - destination->versions = source->versions; - destination->kdc_offset = source->kdc_offset; - destination->last_default = 0; - - /*reset all active iterators to point to the head of the new creds list*/ - if (destination->active_iterators->head != NULL) { - code = cci_generic_list_iterator(destination->active_iterators, &iterator); - while (cci_generic_iterate_has_next(iterator)) { - code = cci_generic_iterate_next(iterator, &node); - cur = (cc_credentials_iterate_t*)node->data; - cur->next = destination->creds->head; - } - code = cci_generic_free_iterator(iterator); - } - - cci_ccache_changed(destination); - return code; -} - -/** - * cci_ccache_get_kdc_time_offset() - * - * Purpose: Retrieves the kdc_time_offset from the ccache if set - * - * Return: 0 on success - * -1 on error - * - * Errors: ccErrBadParam, ccErrTimeOffsetNotSet - * - */ -cc_int32 -cci_ccache_get_kdc_time_offset(cc_server_ccache_t* ccache, cc_time_t* offset) -{ - if (ccache == NULL) - return ccErrInvalidCCache; - - if (offset == NULL) - return ccErrBadParam; - - if (!ccache->kdc_set) - return ccErrTimeOffsetNotSet; - - *offset = ccache->kdc_offset; - return ccNoError; -} - -/** - * cci_ccache_set_kdc_time_offset() - * - * Purpose: Sets the kdc time offset in the designated ccache - * - * Return: 0 on success - * -1 on error - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_ccache_set_kdc_time_offset(cc_server_ccache_t* ccache, cc_time_t offset) -{ - if (ccache == NULL) - return ccErrInvalidCCache; - - ccache->kdc_offset = offset; - ccache->kdc_set = 1; - cci_ccache_changed(ccache); - - return ccNoError; -} - -/** - * cci_ccache_clear_kdc_time_offset() - * - * Purpose: Clear the kdc time offset in the designated ccache - * - * Return: 0 on success - * -1 on error - * - * Errors: ccErrBadParam - */ -cc_int32 -cci_ccache_clear_kdc_time_offset(cc_server_ccache_t* ccache) -{ - if (ccache == NULL) - return ccErrInvalidCCache; - - ccache->kdc_offset = 0; - ccache->kdc_set = 0; - cci_ccache_changed(ccache); - - return ccNoError; -} - -/** - * cci_ccache_new_iterator() - * - * Purpose: Retrieve an iterator for the designated cache - * - * Return: 0 on success - * -1 on error - * - * Errors: ccErrBadParam, ccBadNoMem - */ -cc_int32 -cci_ccache_new_iterator(cc_server_ccache_t* ccache, cc_credentials_iterate_t** iterator) -{ - cc_int32 code; - - if (ccache == NULL) - return ccErrInvalidCCache; - - if (iterator == NULL) - return ccErrBadParam; - - code = cci_credentials_list_iterator(ccache->creds, iterator); - if (code != ccNoError) - return code; - - code = cci_generic_list_prepend(ccache->active_iterators, *iterator, sizeof(cc_credentials_iterate_t), NULL); - if (code != ccNoError) - return code; - - return ccNoError; -} - -/** - * cci_ccache_get_principal() - * - * Purpose: Retrieves the client principal associated with the designated cache. - * The value is returned - * Return: - * - * Errors: - */ -cc_int32 -cci_ccache_get_principal(cc_server_ccache_t* ccache, cc_int32 version, char ** principal) -{ - char *p = NULL; - - switch ( version ) { - case cc_credentials_v4: - p = ccache->principal_v4; - break; - case cc_credentials_v5: - p = ccache->principal_v5; - break; - default: - return ccErrBadCredentialsVersion; - } - - *principal = (char *)malloc(strlen(p)+1); - if ( *principal == NULL ) - return ccErrNoMem; - - strcpy(*principal, p); - return ccNoError; -} - -/** - * Purpose: Releases the memory associated with a ccache principal - * - * Return: - * - * Errors: - * - */ -cc_int32 -cci_ccache_free_principal(char * principal) -{ - if ( principal == NULL ) - return ccErrBadParam; - - free(principal); - return ccNoError; -} - -/** - * ccache_set_principal() - * - * Purpose: Assigns a principal to the designated ccache and credential version. - * If the api version is 2, the cache is cleared of all existing - * credentials. - * - * Return: 0 on success - * -1 on error - * - * Errors: ccErrNoMem, ccErrBadCredentialsVersion - */ -cc_int32 -cci_ccache_set_principal( cc_server_ccache_t* ccache, cc_int32 cred_version, - char* principal) -{ - cc_generic_iterate_t* generic_iterator; - cc_generic_list_node_t* generic_node; - cc_ccache_iterate_t* ccache_iterator; - cc_int32 code = ccNoError; - - if (ccache == NULL) - return ccErrInvalidCCache; - - if (principal == NULL) - return ccErrInvalidString; - - switch (cred_version) { - case cc_credentials_v4: - case cc_credentials_v4_v5: - ccache->principal_v4 = (char *)malloc(strlen(principal) + 1); - if (ccache->principal_v4 == NULL) - return ccErrNoMem; - strcpy(ccache->principal_v4, principal); - if (cred_version != cc_credentials_v4_v5) - break; - /* fall-through if we are v4_v5 */ - case cc_credentials_v5: - ccache->principal_v5 = (char *)malloc(strlen(principal) + 1); - if (ccache->principal_v5 == NULL) { - if (cred_version == cc_credentials_v4_v5) { - free(ccache->principal_v4); - ccache->principal_v4 = NULL; - } - return ccErrNoMem; - } - strcpy(ccache->principal_v5, principal); - break; - default: - return ccErrBadCredentialsVersion; - } - - /*For API version 2 clients set_principal implies a flush of all creds*/ - if (ccache->mycontext != NULL && ccache->mycontext->api_version == ccapi_version_2) { - cci_credentials_list_destroy(ccache->creds); - cci_credentials_list_new(&ccache->creds); - - /*clean up active_iterators*/ - code = cci_generic_list_iterator(ccache->active_iterators, &generic_iterator); - if (code == ccNoError) { - while (cci_generic_iterate_has_next(generic_iterator)) { - code = cci_generic_iterate_next(generic_iterator, &generic_node); - ccache_iterator = (cc_ccache_iterate_t*)generic_node->data; - ccache_iterator->next = NULL; - } - } - } - - cci_ccache_changed(ccache); - - return code; -} - -/** - * cci_ccache_destroy() - * - * Purpose: Destroys an existing ccache - * - * Return: 0 on success - * -1 on errors - * - * Errors: ccErrBadParam - */ -cc_int32 -cci_ccache_destroy(cc_server_ccache_t* ccache) -{ - cc_int32 code; - - if ( ccache == NULL ) - return ccErrInvalidCCache; - - code = cci_generic_list_destroy(ccache->active_iterators); - code = cci_credentials_list_destroy(ccache->creds); - - if (ccache->mycontext != NULL) - code = cci_context_rem_ccache(ccache->mycontext, ccache); - - return code; -} - -/** - * cci_ccache_compare() - * - * Purpose: Returns a boolean value indicating if two caches are identical - * Implemented as pointer equivalence. - * - * Return: 1 if TRUE - * 0 if FALSE - * - * Errors: No errors - */ -cc_int32 -cci_ccache_compare(cc_server_ccache_t* ccache1, cc_server_ccache_t* ccache2, cc_uint32 *result) -{ - if ( ccache1 == NULL || ccache2 == NULL ) - return ccErrInvalidCCache; - - if (ccache1 == ccache2) - *result = 1; - else - *result = 0; - - return ccNoError; -} - +/* $Copyright: + * + * Copyright 2004-2006 by the Massachusetts Institute of Technology. + * + * All rights reserved. + * + * Export of this software from the United States of America may require a + * specific license from the United States Government. It is the + * responsibility of any person or organization contemplating export to + * obtain such a license before exporting. + * + * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute + * this software and its documentation for any purpose and without fee is + * hereby granted, provided that the above copyright notice appear in all + * copies and that both that copyright notice and this permission notice + * appear in supporting documentation, and that the name of M.I.T. not be + * used in advertising or publicity pertaining to distribution of the + * software without specific, written prior permission. Furthermore if you + * modify this software you must label your software as modified software + * and not distribute it in such a fashion that it might be confused with + * the original MIT software. M.I.T. makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. + * + * Individual source code files are copyright MIT, Cygnus Support, + * OpenVision, Oracle, Sun Soft, FundsXpress, and others. + * + * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, + * and Zephyr are trademarks of the Massachusetts Institute of Technology + * (MIT). No commercial use of these trademarks may be made without prior + * written permission of MIT. + * + * "Commercial use" means use of a name in a product or other for-profit + * manner. It does NOT prevent a commercial firm from referring to the MIT + * trademarks in order to convey information (although in doing so, + * recognition of their trademark status should be given). + * $ + */ + +/* + * Manages ccache objects. + * + */ + +#include +#include +#include +#include +#include "CredentialsCache.h" +#include "datastore.h" + +/** + * ccache_new() + * + * Purpose: Allocate and initialize new credentials cache for the specified principal + * and version + * + * Return: ccNoError - success + * ccErrInvalidString - name or principal is NULL + * ccErrBadCredentialsVersion - unsupported creds type + * ccErrBadParam - outCcachepp is NULL + * ccErrNoMem - malloc failed + */ +cc_int32 +ccs_ccache_new( char *name, char *principal, int cred_vers, + cc_server_ccache_t** outCCachepp) +{ + cc_server_ccache_t* ccache; + + if (name == NULL || principal == NULL) + return ccErrInvalidString; + + if (cred_vers != cc_credentials_v4 && cred_vers != cc_credentials_v5 && + cred_vers != cc_credentials_v4_v5) + return ccErrBadCredentialsVersion; + + if (outCCachepp == NULL) + return ccErrBadParam; + + ccache = (cc_server_ccache_t*)malloc(sizeof(cc_server_ccache_t)); + if (ccache == NULL) + return ccErrNoMem; + + ccache->name = name; + ccache->principal_v4 = NULL; + ccache->principal_v5 = NULL; + ccache->changed = time(NULL); + ccache->kdc_offset = 0; + ccache->last_default = 0; + cci_generic_list_new(&ccache->active_iterators); + ccs_credentials_list_new(&ccache->creds); + ccache->is_default = 0; + ccache->kdc_set = 0; + ccache->versions = cred_vers; + ccache->mycontext = NULL; + + ccs_ccache_set_principal(ccache, cred_vers, principal); + *outCCachepp = ccache; + return ccNoError; +} + +/** + * ccs_ccache_check_version() + * + * Purpose: Check to see if the ccache and the creds have compatible versions. + * + * Return: ccNoError and compat = 1 if they are compatible + * ccNoError and compat = 0 if they are not compatible + * + * Errors: ccErrInvalidCCache - ccache is NULL + * ccErrBadParam - either creds or compat are NULL + */ +cc_int32 +ccs_ccache_check_version( const cc_server_ccache_t *ccache, + const cc_credentials_union* creds, + cc_uint32* compat) +{ + if (ccache == NULL) + return ccErrInvalidCCache; + + if (creds == NULL || compat == NULL) + return ccErrBadParam; + + if (ccache->versions == cc_credentials_v4_v5) + *compat = 1; + else if (ccache->versions == creds->version) + *compat = 1; + else + *compat = 0; + + return ccNoError; +} + +/** +ccs_ccache_check_principal() + +Check to see if the client principal from the credentials matches +the principal associated with the cache. + +* Return: ccNoError and compat = 1 if they are compatible +* ccNoError and compat = 0 if they are not compatible +* +* Errors: ccErrInvalidCCache - ccache is NULL +* ccErrBadParam - either creds or compat are NULL +* ccErrBadCredentialVersion - unsupported credential type +*/ +cc_int32 +ccs_ccache_check_principal( const cc_server_ccache_t *ccache, + const cc_credentials_union* creds, + cc_uint32* compat) +{ + if (ccache == NULL) + return ccErrInvalidCCache; + + if (creds == NULL || compat == NULL) + return ccErrBadParam; + + if (creds->version == cc_credentials_v4) { + if (strcmp(creds->credentials.credentials_v4->principal, ccache->principal_v4) == 0) + *compat = 1; + else + *compat = 0; + } else if (creds->version == cc_credentials_v5) { + if (strcmp(creds->credentials.credentials_v5->client, ccache->principal_v5) == 0) + *compat = 1; + else + *compat = 0; + } else { + return ccErrBadCredentialsVersion; + } + return ccNoError; +} + + +/** + * ccs_ccache_store_creds() + * + * Purpose: Stores the provided credentials into the provided cache. Validates the + * ability of the cache to store credentials of the given version and client + * principal. + * + * Return: 0 on success + * -1 on error + * + * Errors: ccErrNoMem + * ccErrBadCredentialsVersion + * ccErrBadInvalidCredentials + * ccErrInvalidCache + * ccErrBadParam + */ +cc_int32 +ccs_ccache_store_creds(cc_server_ccache_t *ccache, const cc_credentials_union* credentials) +{ + cc_server_credentials_t* stored_cred=NULL; + cc_uint32 valid_version, valid_principal; + cc_int32 code; + + if (ccache == NULL) + return ccErrInvalidCCache; + + if (credentials == NULL) + return ccErrBadParam; + + code = ccs_ccache_check_version(ccache, credentials, &valid_version); + if (code != ccNoError) { + /* pass error on to caller */ + goto bad; + } + code = ccs_ccache_check_principal(ccache, credentials, &valid_principal); + if (code != ccNoError) { + /* pass error on to caller */ + goto bad; + } + if (valid_version && valid_principal) { + stored_cred = (cc_server_credentials_t*)malloc(sizeof(cc_server_credentials_t)); + if (stored_cred == NULL) { + code = ccErrNoMem; + goto bad; + } + memcpy(&stored_cred->creds, credentials, sizeof(cc_credentials_union)); + + if (credentials->version == cc_credentials_v4) { + stored_cred->creds.credentials.credentials_v4 = (cc_credentials_v4_t*)malloc(sizeof(cc_credentials_v4_t)); + if (stored_cred->creds.credentials.credentials_v4 == NULL) { + code = ccErrNoMem; + goto bad; + } + + memcpy(stored_cred->creds.credentials.credentials_v4, credentials->credentials.credentials_v4, sizeof(cc_credentials_v4_t)); + } else if (credentials->version == cc_credentials_v5) { + stored_cred->creds.credentials.credentials_v5 = (cc_credentials_v5_t*)malloc(sizeof(cc_credentials_v5_t)); + if (stored_cred->creds.credentials.credentials_v5 == NULL) { + code = ccErrNoMem; + goto bad; + } + + memcpy(stored_cred->creds.credentials.credentials_v5, credentials->credentials.credentials_v5, sizeof(cc_credentials_v5_t)); + } else { + code = ccErrBadCredentialsVersion; + goto bad; + } + + code = ccs_credentials_list_append(ccache->creds, stored_cred, NULL); + if ( code != ccNoError ) { + /* pass error on to caller */ + goto bad; + } + if (ccache->creds->head->data == (cc_uint8 *)stored_cred) + stored_cred->is_default = 1; /*we're first on the list, so we're default*/ + + ccs_ccache_changed(ccache); + return ccNoError; + } else { +#ifdef DEBUG + printf("vers: %d\tprincipal: %d\n", + valid_version, valid_principal); +#endif /* DEBUG */ + code = ccErrInvalidCredentials; + goto bad; + } + + bad: + if (stored_cred) + free(stored_cred); + return code; /* error */ +} + +/** + * ccs_ccache_changed() + * + * Purpose: Updates the last update time for the ccache and its associated context. + * Provides a location from which interested parties should be notified + * of cache updates. + * + * Return: none + * + * Errors: none + */ +void +ccs_ccache_changed(cc_server_ccache_t* ccache) +{ + ccache->changed = time(NULL); + if (ccache->mycontext != NULL) + ccache->mycontext->changed = time(NULL); + + /* XXX - notify registered listeners when implemented */ +} + +/** + * ccs_ccache_rem_creds() + * + * Purpose: Removes the specified credential object from the specified cache if + * it exists + * + * Return: 0 on success (credential is not in the cache) + * -1 on error + * + * Errors: ccErrBadParam, ccErrNoMem (from cc_credentials_list_iterator) + * + * Verify: does the memory associated with stored_cred->creds need to be freed? + * + */ +cc_int32 +ccs_ccache_rem_creds(cc_server_ccache_t *ccache, const cc_credentials_union* credentials) +{ + cc_credentials_iterate_t* credentials_iterator=NULL, *active; + cc_generic_iterate_t* generic_iterator=NULL; + cc_credentials_list_node_t* credentials_node; + cc_generic_list_node_t* generic_node; + cc_server_credentials_t* stored_cred; + cc_int8 changed = 0; + cc_int32 code = 0; + + if (ccache == NULL) + return ccErrInvalidCCache; + + if (credentials == NULL) + return ccErrBadParam; + + code = ccs_credentials_list_iterator(ccache->creds, &credentials_iterator); + if (code != ccNoError) { + /* pass error to caller */ + goto cleanup; + } + + while (ccs_credentials_iterate_has_next(credentials_iterator)) { + code = ccs_credentials_iterate_next(credentials_iterator, &credentials_node); + stored_cred = (cc_server_credentials_t*)credentials_node->data; + if (memcmp(&stored_cred->creds,credentials,sizeof(cc_credentials_union)) == 0) { + /* XXX - do we need to free(stored_cred->creds) ? */ + free(credentials_node->data); + changed = 1; + + /*If any iterator's next points to the deleted node, make it point to the next node*/ + code = cci_generic_list_iterator(ccache->active_iterators, &generic_iterator); + while (cci_generic_iterate_has_next(generic_iterator)) { + code = cci_generic_iterate_next(generic_iterator, &generic_node); + active = (cc_credentials_iterate_t*)generic_node->data; + if (active->next == credentials_node) + active->next = active->next->next; + } + code = cci_generic_free_iterator(generic_iterator); + generic_iterator = NULL; + + if (credentials_node == ccache->creds->head) { /*removing the default, must make next cred default*/ + code = ccs_credentials_list_remove_element(ccache->creds, credentials_node); + + if (ccache->creds->head != NULL) + ((cc_server_credentials_t*)ccache->creds->head->data)->is_default = 1; + } else { + code = ccs_credentials_list_remove_element(ccache->creds, credentials_node); + } + break; + } + } + + cleanup: + if (changed) + ccs_ccache_changed(ccache); + if (credentials_iterator) + ccs_credentials_free_iterator(credentials_iterator); + if (generic_iterator) + cci_generic_free_iterator(generic_iterator); + return code; +} + +/** + * ccs_ccache_move() + * + * Purpose: Destroys the existing contents of the destination and copies + * all credentials from the source to the destination + * + * Return: 0 on success + * -1 on error + * + * Errors: ccBadNoMem + * + */ + +cc_int32 +ccs_ccache_move(cc_server_ccache_t *source, cc_server_ccache_t* destination) +{ + cc_generic_list_node_t* node; + cc_generic_iterate_t* iterator; + cc_credentials_iterate_t* cur; + cc_int32 code; + + if (source == NULL || destination == NULL) + return ccErrBadParam; + + code = ccs_credentials_list_destroy(destination->creds); + if ( code != ccNoError ) + return code; + + code = ccs_credentials_list_copy(source->creds, &destination->creds); + if ( code != ccNoError ) + return code; + + destination->versions = source->versions; + destination->kdc_offset = source->kdc_offset; + destination->last_default = 0; + + /*reset all active iterators to point to the head of the new creds list*/ + if (destination->active_iterators->head != NULL) { + code = cci_generic_list_iterator(destination->active_iterators, &iterator); + while (cci_generic_iterate_has_next(iterator)) { + code = cci_generic_iterate_next(iterator, &node); + cur = (cc_credentials_iterate_t*)node->data; + cur->next = destination->creds->head; + } + code = cci_generic_free_iterator(iterator); + } + + ccs_ccache_changed(destination); + return code; +} + +/** + * ccs_ccache_get_kdc_time_offset() + * + * Purpose: Retrieves the kdc_time_offset from the ccache if set + * + * Return: 0 on success + * -1 on error + * + * Errors: ccErrBadParam, ccErrTimeOffsetNotSet + * + */ +cc_int32 +ccs_ccache_get_kdc_time_offset(cc_server_ccache_t* ccache, cc_time64* offset) +{ + if (ccache == NULL) + return ccErrInvalidCCache; + + if (offset == NULL) + return ccErrBadParam; + + if (!ccache->kdc_set) + return ccErrTimeOffsetNotSet; + + *offset = ccache->kdc_offset; + return ccNoError; +} + +/** + * ccs_ccache_set_kdc_time_offset() + * + * Purpose: Sets the kdc time offset in the designated ccache + * + * Return: 0 on success + * -1 on error + * + * Errors: ccErrBadParam + * + */ +cc_int32 +ccs_ccache_set_kdc_time_offset(cc_server_ccache_t* ccache, cc_time64 offset) +{ + if (ccache == NULL) + return ccErrInvalidCCache; + + ccache->kdc_offset = offset; + ccache->kdc_set = 1; + ccs_ccache_changed(ccache); + + return ccNoError; +} + +/** + * ccs_ccache_clear_kdc_time_offset() + * + * Purpose: Clear the kdc time offset in the designated ccache + * + * Return: 0 on success + * -1 on error + * + * Errors: ccErrBadParam + */ +cc_int32 +ccs_ccache_clear_kdc_time_offset(cc_server_ccache_t* ccache) +{ + if (ccache == NULL) + return ccErrInvalidCCache; + + ccache->kdc_offset = 0; + ccache->kdc_set = 0; + ccs_ccache_changed(ccache); + + return ccNoError; +} + +/** + * ccs_ccache_new_iterator() + * + * Purpose: Retrieve an iterator for the designated cache + * + * Return: 0 on success + * -1 on error + * + * Errors: ccErrBadParam, ccBadNoMem + */ +cc_int32 +ccs_ccache_new_iterator(cc_server_ccache_t* ccache, cc_credentials_iterate_t** iterator) +{ + cc_int32 code; + + if (ccache == NULL) + return ccErrInvalidCCache; + + if (iterator == NULL) + return ccErrBadParam; + + code = ccs_credentials_list_iterator(ccache->creds, iterator); + if (code != ccNoError) + return code; + + code = cci_generic_list_prepend(ccache->active_iterators, *iterator, sizeof(cc_credentials_iterate_t), NULL); + if (code != ccNoError) + return code; + + return ccNoError; +} + +/** + * ccs_ccache_get_principal() + * + * Purpose: Retrieves the client principal associated with the designated cache. + * The value is returned + * Return: + * + * Errors: + */ +cc_int32 +ccs_ccache_get_principal(cc_server_ccache_t* ccache, cc_int32 version, char ** principal) +{ + char *p = NULL; + + switch ( version ) { + case cc_credentials_v4: + p = ccache->principal_v4; + break; + case cc_credentials_v5: + p = ccache->principal_v5; + break; + default: + return ccErrBadCredentialsVersion; + } + + *principal = (char *)malloc(strlen(p)+1); + if ( *principal == NULL ) + return ccErrNoMem; + + strcpy(*principal, p); + return ccNoError; +} + +/** + * Purpose: Releases the memory associated with a ccache principal + * + * Return: + * + * Errors: + * + */ +cc_int32 +ccs_ccache_free_principal(char * principal) +{ + if ( principal == NULL ) + return ccErrBadParam; + + free(principal); + return ccNoError; +} + +/** + * ccache_set_principal() + * + * Purpose: Assigns a principal to the designated ccache and credential version. + * If the api version is 2, the cache is cleared of all existing + * credentials. + * + * Return: 0 on success + * -1 on error + * + * Errors: ccErrNoMem, ccErrBadCredentialsVersion + */ +cc_int32 +ccs_ccache_set_principal( cc_server_ccache_t* ccache, cc_int32 cred_version, + char* principal) +{ + cc_generic_iterate_t* generic_iterator; + cc_generic_list_node_t* generic_node; + cc_ccache_iterate_t* ccache_iterator; + cc_int32 code = ccNoError; + + if (ccache == NULL) + return ccErrInvalidCCache; + + if (principal == NULL) + return ccErrInvalidString; + + switch (cred_version) { + case cc_credentials_v4: + case cc_credentials_v4_v5: + ccache->principal_v4 = (char *)malloc(strlen(principal) + 1); + if (ccache->principal_v4 == NULL) + return ccErrNoMem; + strcpy(ccache->principal_v4, principal); + if (cred_version != cc_credentials_v4_v5) + break; + /* fall-through if we are v4_v5 */ + case cc_credentials_v5: + ccache->principal_v5 = (char *)malloc(strlen(principal) + 1); + if (ccache->principal_v5 == NULL) { + if (cred_version == cc_credentials_v4_v5) { + free(ccache->principal_v4); + ccache->principal_v4 = NULL; + } + return ccErrNoMem; + } + strcpy(ccache->principal_v5, principal); + break; + default: + return ccErrBadCredentialsVersion; + } + + /*For API version 2 clients set_principal implies a flush of all creds*/ + if (ccache->mycontext != NULL && ccache->mycontext->api_version == ccapi_version_2) { + ccs_credentials_list_destroy(ccache->creds); + ccs_credentials_list_new(&ccache->creds); + + /*clean up active_iterators*/ + code = cci_generic_list_iterator(ccache->active_iterators, &generic_iterator); + if (code == ccNoError) { + while (cci_generic_iterate_has_next(generic_iterator)) { + code = cci_generic_iterate_next(generic_iterator, &generic_node); + ccache_iterator = (cc_ccache_iterate_t*)generic_node->data; + ccache_iterator->next = NULL; + } + } + } + + ccs_ccache_changed(ccache); + + return code; +} + +/** + * ccs_ccache_destroy() + * + * Purpose: Destroys an existing ccache + * + * Return: 0 on success + * -1 on errors + * + * Errors: ccErrBadParam + */ +cc_int32 +ccs_ccache_destroy(cc_server_ccache_t* ccache) +{ + cc_int32 code; + + if ( ccache == NULL ) + return ccErrInvalidCCache; + + code = cci_generic_list_destroy(ccache->active_iterators); + code = ccs_credentials_list_destroy(ccache->creds); + + if (ccache->mycontext != NULL) + code = ccs_context_rem_ccache(ccache->mycontext, ccache); + + return code; +} + +/** + * ccs_ccache_compare() + * + * Purpose: Returns a boolean value indicating if two caches are identical + * Implemented as pointer equivalence. + * + * Return: 1 if TRUE + * 0 if FALSE + * + * Errors: No errors + */ +cc_int32 +ccs_ccache_compare(cc_server_ccache_t* ccache1, cc_server_ccache_t* ccache2, cc_uint32 *result) +{ + if ( ccache1 == NULL || ccache2 == NULL ) + return ccErrInvalidCCache; + + if (ccache1 == ccache2) + *result = 1; + else + *result = 0; + + return ccNoError; +} + diff --git a/src/lib/ccapi/server/context.c b/src/lib/ccapi/server/ccs_context.c similarity index 76% rename from src/lib/ccapi/server/context.c rename to src/lib/ccapi/server/ccs_context.c index f405a4def..a16814794 100644 --- a/src/lib/ccapi/server/context.c +++ b/src/lib/ccapi/server/ccs_context.c @@ -1,325 +1,325 @@ -/* $Copyright: - * - * Copyright 2004 by the Massachusetts Institute of Technology. - * - * All rights reserved. - * - * Export of this software from the United States of America may require a - * specific license from the United States Government. It is the - * responsibility of any person or organization contemplating export to - * obtain such a license before exporting. - * - * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute - * this software and its documentation for any purpose and without fee is - * hereby granted, provided that the above copyright notice appear in all - * copies and that both that copyright notice and this permission notice - * appear in supporting documentation, and that the name of M.I.T. not be - * used in advertising or publicity pertaining to distribution of the - * software without specific, written prior permission. Furthermore if you - * modify this software you must label your software as modified software - * and not distribute it in such a fashion that it might be confused with - * the original MIT software. M.I.T. makes no representations about the - * suitability of this software for any purpose. It is provided "as is" - * without express or implied warranty. - * - * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED - * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF - * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. - * - * Individual source code files are copyright MIT, Cygnus Support, - * OpenVision, Oracle, Sun Soft, FundsXpress, and others. - * - * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, - * and Zephyr are trademarks of the Massachusetts Institute of Technology - * (MIT). No commercial use of these trademarks may be made without prior - * written permission of MIT. - * - * "Commercial use" means use of a name in a product or other for-profit - * manner. It does NOT prevent a commercial firm from referring to the MIT - * trademarks in order to convey information (although in doing so, - * recognition of their trademark status should be given). - * $ - */ - -/* - * Functions to manipulate datastore layer contexts. - * - */ - -#include -#include -#include -#include - -#include "CredentialsCache.h" -#include "datastore.h" - -int cc_myversion = 5; -char cc_vendor[] = "MIT C lang CCache V5"; -char cc_default_ccache_name[] = "krb5cc"; - - -cc_int32 -cci_context_new( int api_version, cc_auth_info_t* auth_info, - cc_session_info_t* session_info, cc_server_context_t** outContextpp ) -{ - cc_server_context_t* ctx; - - if ( outContextpp == NULL ) - return ccErrBadParam; - - ctx = (cc_server_context_t*)malloc(sizeof(cc_server_context_t)); - if (ctx == NULL) - return ccErrNoMem; - - cci_ccache_list_new(&ctx->ccaches); - cci_generic_list_new(&ctx->active_iterators); - ctx->api_version = api_version; - ctx->auth_info = auth_info; - ctx->session_info = session_info; - ctx->changed = time(NULL); - - *outContextpp = ctx; - return ccNoError; -} - -cc_int32 -cci_context_get_default_ccache_name(cc_server_context_t* ctx, char ** outNamepp) -{ - cc_server_ccache_t* default_ccache; - - if (outNamepp == NULL) - return ccErrBadParam; - - if (ctx == NULL) - return ccErrInvalidContext; - - if (ctx->ccaches->head != NULL) { - default_ccache = (cc_server_ccache_t*)ctx->ccaches->head->data; - *outNamepp = default_ccache->name; - } else { - *outNamepp = cc_default_ccache_name; - } - return ccNoError; -} - - -cc_int32 -cci_context_find_ccache( cc_server_context_t* ctx, char *name, - cc_server_ccache_t** outCcachepp ) -{ - cc_ccache_iterate_t* ccache_iterator; - cc_ccache_list_node_t* ccache_node; - cc_server_ccache_t* ccache; - cc_int32 code; - - if (ctx == NULL) - return ccErrInvalidContext; - - if (name == NULL) - return ccErrInvalidString; - - if (outCcachepp == NULL) - return ccErrBadParam; - - code = cci_ccache_list_iterator(ctx->ccaches, &ccache_iterator); - while (cci_ccache_iterate_has_next(ccache_iterator)) { - code = cci_ccache_iterate_next(ccache_iterator, &ccache_node); - ccache = (cc_server_ccache_t *)ccache_node->data; - if (strcmp(ccache->name, name) == 0) { - free(ccache_iterator); - *outCcachepp = ccache; - return ccNoError; - } - } - free(ccache_iterator); - return ccErrCCacheNotFound; -} - -cc_int32 -cci_context_open_ccache( cc_server_context_t* ctx, char *name, - cc_server_ccache_t** outCcachepp ) -{ - return cci_context_find_ccache(ctx, name, outCcachepp); -} - - -cc_int32 -cci_context_create_ccache( cc_server_context_t* ctx, char *name, int creds_version, - char *principal, cc_server_ccache_t** outCcachepp ) -{ - cc_server_ccache_t* ccache; - cc_int32 code; - - if (ctx == NULL) - return ccErrInvalidContext; - - if (outCcachepp == NULL) - return ccErrBadParam; - - if (name == NULL || principal == NULL) - return ccErrInvalidString; - - if (creds_version != cc_credentials_v4 && creds_version != cc_credentials_v5 && - creds_version != cc_credentials_v4_v5) - return ccErrBadCredentialsVersion; - - code = cci_context_find_ccache(ctx, name, &ccache); - if (code == ccNoError) { - code = cci_ccache_set_principal(ccache, creds_version, principal); - } else { - code = cci_ccache_new(name, principal, creds_version, &ccache); - if (code != ccNoError) - return code; /*let caller deal with error*/ - - ccache->mycontext = ctx; - ctx->changed = time(NULL); - cci_ccache_list_append(ctx->ccaches, ccache, NULL); - - if (ctx->ccaches->head->data == (cc_uint8 *)ccache) { - ccache->is_default = 1; - } - } - *outCcachepp = ccache; - return ccNoError; -} - -cc_int32 -cci_context_create_default_ccache( cc_server_context_t* ctx, int creds_version, - char *principal, cc_server_ccache_t** outCcachepp ) -{ - cc_server_ccache_t* ccache, *old_default; - cc_int32 code; - - if (ctx == NULL) - return ccErrInvalidContext; - - if (outCcachepp == NULL) - return ccErrBadParam; - - if (principal == NULL) - return ccErrInvalidString; - - if (creds_version != cc_credentials_v4 && creds_version != cc_credentials_v5 && - creds_version != cc_credentials_v4_v5) - return ccErrBadCredentialsVersion; - - code = cci_context_find_ccache(ctx, cc_default_ccache_name, &ccache); - if (code == ccNoError) { - cci_ccache_set_principal(ccache, creds_version, principal); - } else { - code = cci_ccache_new(cc_default_ccache_name, principal, creds_version, &ccache); - if (code != ccNoError) - return code; /*let caller deal with error*/ - - ccache->mycontext = ctx; - ccache->is_default = 1; - ctx->changed = time(NULL); - - if (ctx->ccaches->head != NULL) { - old_default = (cc_server_ccache_t *)ctx->ccaches->head->data; - old_default->is_default = 0; - old_default->last_default = time(NULL); - } - - cci_ccache_list_prepend(ctx->ccaches, ccache, NULL); - } - *outCcachepp = ccache; - return ccNoError; -} - -cc_int32 -cci_context_ccache_iterator(cc_server_context_t* ctx, cc_ccache_iterate_t** iterpp) -{ - cc_ccache_iterate_t* ccache_iterator; - cc_int32 code; - - if (ctx == NULL) - return ccErrInvalidContext; - - if (iterpp == NULL) - return ccErrBadParam; - - code = cci_ccache_list_iterator(ctx->ccaches, &ccache_iterator); - if (code != ccNoError) - return code; - cci_generic_list_prepend(ctx->active_iterators, ccache_iterator, sizeof(cc_ccache_iterate_t), NULL); - - *iterpp = ccache_iterator; - return ccNoError; -} - -cc_int32 -cci_context_compare(cc_server_context_t* a, cc_server_context_t* b) -{ - if (a == b) - return 1; - else - return 0; -} - -cc_int32 -cci_context_destroy(cc_server_context_t* ctx) -{ - cc_ccache_iterate_t* ccache_iterator; - cc_ccache_list_node_t* ccache_node; - cc_server_ccache_t* ccache; - cc_int32 code; - - if (ctx == NULL) - return ccErrInvalidContext; - - cci_generic_list_destroy(ctx->active_iterators); - - code = cci_ccache_list_iterator(ctx->ccaches, &ccache_iterator); - while (cci_ccache_iterate_has_next(ccache_iterator)) { - code = cci_ccache_iterate_next(ccache_iterator, &ccache_node); - ccache = (cc_server_ccache_t *)ccache_node->data; - ccache_node->data = NULL; - cci_ccache_destroy(ccache); - } - cci_ccache_list_destroy(ctx->ccaches); - - return ccNoError; -} - -cc_int32 -cci_context_rem_ccache(cc_server_context_t* ctx, cc_server_ccache_t* ccache) -{ - cc_ccache_iterate_t* ccache_iterator; - cc_ccache_iterate_t* active_ccache_iterator; - cc_ccache_list_node_t* ccache_node; - cc_server_ccache_t* list_ccache; - cc_generic_list_node_t* gen_node; - cc_generic_iterate_t* gen_iterator; - cc_int32 code; - - if (ctx == NULL) - return ccErrInvalidContext; - - if (ccache == NULL) - return ccErrInvalidCCache; - - code = cci_ccache_list_iterator(ctx->ccaches, &ccache_iterator); - while (cci_ccache_iterate_has_next(ccache_iterator)) { - code = cci_ccache_iterate_next(ccache_iterator, &ccache_node); - list_ccache = (cc_server_ccache_t *)ccache_node->data; - - if (list_ccache == ccache) { - code = cci_generic_list_iterator(ctx->active_iterators, &gen_iterator); - while (cci_generic_iterate_has_next(gen_iterator)) { - code = cci_generic_iterate_next(gen_iterator, &gen_node); - active_ccache_iterator = (cc_server_ccache_t *)gen_node->data; - if (active_ccache_iterator->next == ccache_node) { - active_ccache_iterator->next = active_ccache_iterator->next->next; - } - } - free(gen_iterator); - code = cci_ccache_list_remove_element(ctx->ccaches, ccache_node); - break; - } - } - free(ccache_iterator); - return ccNoError; -} - +/* $Copyright: + * + * Copyright 2004-2006 by the Massachusetts Institute of Technology. + * + * All rights reserved. + * + * Export of this software from the United States of America may require a + * specific license from the United States Government. It is the + * responsibility of any person or organization contemplating export to + * obtain such a license before exporting. + * + * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute + * this software and its documentation for any purpose and without fee is + * hereby granted, provided that the above copyright notice appear in all + * copies and that both that copyright notice and this permission notice + * appear in supporting documentation, and that the name of M.I.T. not be + * used in advertising or publicity pertaining to distribution of the + * software without specific, written prior permission. Furthermore if you + * modify this software you must label your software as modified software + * and not distribute it in such a fashion that it might be confused with + * the original MIT software. M.I.T. makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. + * + * Individual source code files are copyright MIT, Cygnus Support, + * OpenVision, Oracle, Sun Soft, FundsXpress, and others. + * + * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, + * and Zephyr are trademarks of the Massachusetts Institute of Technology + * (MIT). No commercial use of these trademarks may be made without prior + * written permission of MIT. + * + * "Commercial use" means use of a name in a product or other for-profit + * manner. It does NOT prevent a commercial firm from referring to the MIT + * trademarks in order to convey information (although in doing so, + * recognition of their trademark status should be given). + * $ + */ + +/* + * Functions to manipulate datastore layer contexts. + * + */ + +#include +#include +#include +#include + +#include "CredentialsCache.h" +#include "datastore.h" + +int cc_myversion = 5; +char cc_vendor[] = "MIT C lang CCache V5"; +char cc_default_ccache_name[] = "krb5cc"; + + +cc_int32 +ccs_context_new( int api_version, cc_auth_info_t* auth_info, + cc_session_info_t* session_info, cc_server_context_t** outContextpp ) +{ + cc_server_context_t* ctx; + + if ( outContextpp == NULL ) + return ccErrBadParam; + + ctx = (cc_server_context_t*)malloc(sizeof(cc_server_context_t)); + if (ctx == NULL) + return ccErrNoMem; + + ccs_ccache_list_new(&ctx->ccaches); + cci_generic_list_new(&ctx->active_iterators); + ctx->api_version = api_version; + ctx->auth_info = auth_info; + ctx->session_info = session_info; + ctx->changed = time(NULL); + + *outContextpp = ctx; + return ccNoError; +} + +cc_int32 +ccs_context_get_default_ccache_name(cc_server_context_t* ctx, char ** outNamepp) +{ + cc_server_ccache_t* default_ccache; + + if (outNamepp == NULL) + return ccErrBadParam; + + if (ctx == NULL) + return ccErrInvalidContext; + + if (ctx->ccaches->head != NULL) { + default_ccache = (cc_server_ccache_t*)ctx->ccaches->head->data; + *outNamepp = default_ccache->name; + } else { + *outNamepp = cc_default_ccache_name; + } + return ccNoError; +} + + +cc_int32 +ccs_context_find_ccache( cc_server_context_t* ctx, char *name, + cc_server_ccache_t** outCcachepp ) +{ + cc_ccache_iterate_t* ccache_iterator; + cc_ccache_list_node_t* ccache_node; + cc_server_ccache_t* ccache; + cc_int32 code; + + if (ctx == NULL) + return ccErrInvalidContext; + + if (name == NULL) + return ccErrInvalidString; + + if (outCcachepp == NULL) + return ccErrBadParam; + + code = ccs_ccache_list_iterator(ctx->ccaches, &ccache_iterator); + while (ccs_ccache_iterate_has_next(ccache_iterator)) { + code = ccs_ccache_iterate_next(ccache_iterator, &ccache_node); + ccache = (cc_server_ccache_t *)ccache_node->data; + if (strcmp(ccache->name, name) == 0) { + free(ccache_iterator); + *outCcachepp = ccache; + return ccNoError; + } + } + free(ccache_iterator); + return ccErrCCacheNotFound; +} + +cc_int32 +ccs_context_open_ccache( cc_server_context_t* ctx, char *name, + cc_server_ccache_t** outCcachepp ) +{ + return ccs_context_find_ccache(ctx, name, outCcachepp); +} + + +cc_int32 +ccs_context_create_ccache( cc_server_context_t* ctx, char *name, int creds_version, + char *principal, cc_server_ccache_t** outCcachepp ) +{ + cc_server_ccache_t* ccache; + cc_int32 code; + + if (ctx == NULL) + return ccErrInvalidContext; + + if (outCcachepp == NULL) + return ccErrBadParam; + + if (name == NULL || principal == NULL) + return ccErrInvalidString; + + if (creds_version != cc_credentials_v4 && creds_version != cc_credentials_v5 && + creds_version != cc_credentials_v4_v5) + return ccErrBadCredentialsVersion; + + code = ccs_context_find_ccache(ctx, name, &ccache); + if (code == ccNoError) { + code = ccs_ccache_set_principal(ccache, creds_version, principal); + } else { + code = ccs_ccache_new(name, principal, creds_version, &ccache); + if (code != ccNoError) + return code; /*let caller deal with error*/ + + ccache->mycontext = ctx; + ctx->changed = time(NULL); + ccs_ccache_list_append(ctx->ccaches, ccache, NULL); + + if (ctx->ccaches->head->data == (cc_uint8 *)ccache) { + ccache->is_default = 1; + } + } + *outCcachepp = ccache; + return ccNoError; +} + +cc_int32 +ccs_context_create_default_ccache( cc_server_context_t* ctx, int creds_version, + char *principal, cc_server_ccache_t** outCcachepp ) +{ + cc_server_ccache_t* ccache, *old_default; + cc_int32 code; + + if (ctx == NULL) + return ccErrInvalidContext; + + if (outCcachepp == NULL) + return ccErrBadParam; + + if (principal == NULL) + return ccErrInvalidString; + + if (creds_version != cc_credentials_v4 && creds_version != cc_credentials_v5 && + creds_version != cc_credentials_v4_v5) + return ccErrBadCredentialsVersion; + + code = ccs_context_find_ccache(ctx, cc_default_ccache_name, &ccache); + if (code == ccNoError) { + ccs_ccache_set_principal(ccache, creds_version, principal); + } else { + code = ccs_ccache_new(cc_default_ccache_name, principal, creds_version, &ccache); + if (code != ccNoError) + return code; /*let caller deal with error*/ + + ccache->mycontext = ctx; + ccache->is_default = 1; + ctx->changed = time(NULL); + + if (ctx->ccaches->head != NULL) { + old_default = (cc_server_ccache_t *)ctx->ccaches->head->data; + old_default->is_default = 0; + old_default->last_default = time(NULL); + } + + ccs_ccache_list_prepend(ctx->ccaches, ccache, NULL); + } + *outCcachepp = ccache; + return ccNoError; +} + +cc_int32 +ccs_context_ccache_iterator(cc_server_context_t* ctx, cc_ccache_iterate_t** iterpp) +{ + cc_ccache_iterate_t* ccache_iterator; + cc_int32 code; + + if (ctx == NULL) + return ccErrInvalidContext; + + if (iterpp == NULL) + return ccErrBadParam; + + code = ccs_ccache_list_iterator(ctx->ccaches, &ccache_iterator); + if (code != ccNoError) + return code; + cci_generic_list_prepend(ctx->active_iterators, ccache_iterator, sizeof(cc_ccache_iterate_t), NULL); + + *iterpp = ccache_iterator; + return ccNoError; +} + +cc_int32 +ccs_context_compare(cc_server_context_t* a, cc_server_context_t* b) +{ + if (a == b) + return 1; + else + return 0; +} + +cc_int32 +ccs_context_destroy(cc_server_context_t* ctx) +{ + cc_ccache_iterate_t* ccache_iterator; + cc_ccache_list_node_t* ccache_node; + cc_server_ccache_t* ccache; + cc_int32 code; + + if (ctx == NULL) + return ccErrInvalidContext; + + cci_generic_list_destroy(ctx->active_iterators); + + code = ccs_ccache_list_iterator(ctx->ccaches, &ccache_iterator); + while (ccs_ccache_iterate_has_next(ccache_iterator)) { + code = ccs_ccache_iterate_next(ccache_iterator, &ccache_node); + ccache = (cc_server_ccache_t *)ccache_node->data; + ccache_node->data = NULL; + ccs_ccache_destroy(ccache); + } + ccs_ccache_list_destroy(ctx->ccaches); + + return ccNoError; +} + +cc_int32 +ccs_context_rem_ccache(cc_server_context_t* ctx, cc_server_ccache_t* ccache) +{ + cc_ccache_iterate_t* ccache_iterator; + cc_ccache_iterate_t* active_ccache_iterator; + cc_ccache_list_node_t* ccache_node; + cc_server_ccache_t* list_ccache; + cc_generic_list_node_t* gen_node; + cc_generic_iterate_t* gen_iterator; + cc_int32 code; + + if (ctx == NULL) + return ccErrInvalidContext; + + if (ccache == NULL) + return ccErrInvalidCCache; + + code = ccs_ccache_list_iterator(ctx->ccaches, &ccache_iterator); + while (ccs_ccache_iterate_has_next(ccache_iterator)) { + code = ccs_ccache_iterate_next(ccache_iterator, &ccache_node); + list_ccache = (cc_server_ccache_t *)ccache_node->data; + + if (list_ccache == ccache) { + code = cci_generic_list_iterator(ctx->active_iterators, &gen_iterator); + while (cci_generic_iterate_has_next(gen_iterator)) { + code = cci_generic_iterate_next(gen_iterator, &gen_node); + active_ccache_iterator = (cc_ccache_iterate_t *)gen_node->data; + if (active_ccache_iterator->next == ccache_node) { + active_ccache_iterator->next = active_ccache_iterator->next->next; + } + } + free(gen_iterator); + code = ccs_ccache_list_remove_element(ctx->ccaches, ccache_node); + break; + } + } + free(ccache_iterator); + return ccNoError; +} + diff --git a/src/lib/ccapi/server/lists.c b/src/lib/ccapi/server/ccs_lists.c similarity index 84% rename from src/lib/ccapi/server/lists.c rename to src/lib/ccapi/server/ccs_lists.c index 882ecb7a0..06f8ced87 100644 --- a/src/lib/ccapi/server/lists.c +++ b/src/lib/ccapi/server/ccs_lists.c @@ -1,996 +1,996 @@ -/* $Copyright: - * - * Copyright 2004 by the Massachusetts Institute of Technology. - * - * All rights reserved. - * - * Export of this software from the United States of America may require a - * specific license from the United States Government. It is the - * responsibility of any person or organization contemplating export to - * obtain such a license before exporting. - * - * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute - * this software and its documentation for any purpose and without fee is - * hereby granted, provided that the above copyright notice appear in all - * copies and that both that copyright notice and this permission notice - * appear in supporting documentation, and that the name of M.I.T. not be - * used in advertising or publicity pertaining to distribution of the - * software without specific, written prior permission. Furthermore if you - * modify this software you must label your software as modified software - * and not distribute it in such a fashion that it might be confused with - * the original MIT software. M.I.T. makes no representations about the - * suitability of this software for any purpose. It is provided "as is" - * without express or implied warranty. - * - * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED - * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF - * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. - * - * Individual source code files are copyright MIT, Cygnus Support, - * OpenVision, Oracle, Sun Soft, FundsXpress, and others. - * - * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, - * and Zephyr are trademarks of the Massachusetts Institute of Technology - * (MIT). No commercial use of these trademarks may be made without prior - * written permission of MIT. - * - * "Commercial use" means use of a name in a product or other for-profit - * manner. It does NOT prevent a commercial firm from referring to the MIT - * trademarks in order to convey information (although in doing so, - * recognition of their trademark status should be given). - * $ - */ - - -/* - * Lists implementation. - * - */ - -#include -#include -#include - -#include "CredentialsCache.h" -#include "datastore.h" - -/** - * cci_generic_iterate_has_next() - * - * Purpose: Determine if an iterator has a next element - * - * Return: 1 if another element exists - * 0 if no additional elements exist - * - * Errors: None - * - */ -cc_int32 -cci_generic_iterate_has_next(cc_generic_iterate_t *iterate) -{ - return ((iterate == NULL || iterate->next == NULL) ? 0 : 1); -} - -/** - * cci_generic_iterate_next() - * - * Purpose: Retrieve the next element from an iterator and advance - * the iterator - * - * Return: non-NULL, the next element in the iterator - * NULL, the iterator list is empty or iterator is invalid - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_generic_iterate_next(cc_generic_iterate_t *iterator, cc_generic_list_node_t** nodepp) -{ - cc_generic_list_node_t* ret; - - if (iterator == NULL || nodepp == NULL) - return ccErrBadParam; - - ret = iterator->next; - if (iterator->next != NULL) - iterator->next = iterator->next->next; - - *nodepp = ret; - return ccNoError; -} - -/** - * cci_context_iterate_has_next() - * - * Purpose: Determine if a context iterator has a next element - * - * Return: 1 if another element exists - * 0 if no additional elements exist - */ -cc_int32 -cci_context_iterate_has_next(cc_context_iterate_t *iterate) -{ - if ( iterate == NULL ) - return 0; - - return cci_generic_iterate_has_next((cc_generic_iterate_t*)iterate); -} - -/** - * cci_context_iterate_next() - * - * Purpose: Retrieve the next element from a context iterator and advance - * the iterator - * - * Return: non-NULL, the next element in the iterator - * NULL, the iterator list is empty or iterator is invalid - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_context_iterate_next(cc_context_iterate_t *iterate, cc_context_list_node_t ** nodepp) -{ - if ( iterate == NULL || nodepp == NULL) - return ccErrBadParam; - - return cci_generic_iterate_next((cc_generic_iterate_t*)iterate,(cc_context_list_node_t**)nodepp); -} - -/** - * cci_ccache_iterate_has_next() - * - * Purpose: Determine if a cache iterator has a next element - * - * Return: 1 if another element exists - * 0 if no additional elements exist - * -1 if error - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_ccache_iterate_has_next(cc_ccache_iterate_t *iterate) -{ - if ( iterate == NULL ) - return 0; - return cci_generic_iterate_has_next((cc_generic_iterate_t*)iterate); -} - -/** - * cci_ccache_iterate_next() - * - * Purpose: Retrieve the next element from a ccache iterator and advance - * the iterator - * - * Return: non-NULL, the next element in the iterator - * NULL, the iterator list is empty or iterator is invalid - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_ccache_iterate_next(cc_ccache_iterate_t *iterate, cc_ccache_list_node_t ** nodepp) -{ - if ( iterate == NULL || nodepp == NULL) - return ccErrBadParam; - - return cci_generic_iterate_next((cc_generic_iterate_t*)iterate, (cc_ccache_list_node_t**)nodepp); -} - -/** - * cci_credentials_iterate_has_next() - * - * Purpose: Determine if a credentials iterator has a next element - * - * Return: 1 if another element exists - * 0 if no additional elements exist - * -1 if error - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_credentials_iterate_has_next(cc_credentials_iterate_t *iterate) -{ - if ( iterate == NULL ) - return 0; - - return cci_generic_iterate_has_next((cc_generic_iterate_t*)iterate); -} - -/** - * cci_credentials_iterate_next() - * - * Purpose: Retrieve the next element from a credentials iterator and advance - * the iterator - * - * Return: non-NULL, the next element in the iterator - * NULL, the iterator list is empty or iterator is invalid - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_credentials_iterate_next(cc_credentials_iterate_t *iterate, cc_credentials_list_node_t** nodepp) -{ - if ( iterate == NULL || nodepp == NULL ) - return ccErrBadParam; - return cci_generic_iterate_next((cc_generic_iterate_t*)iterate, (cc_credentials_list_node_t**)nodepp); -} - -/** - * cci_generic_list_new() - * - * Purpose: Allocate new generic list - * - * Return: non-NULL, an empty list - * NULL, failure - * - * Errors: ccErrNoMem - * - */ -cc_int32 -cci_generic_list_new(cc_generic_list_head_t ** listpp) -{ - cc_generic_list_head_t* ret = (cc_generic_list_head_t *)malloc(sizeof(cc_generic_list_head_t)); - if (ret == NULL) - return ccErrNoMem; - - ret->type = generic; - ret->head = ret->tail = NULL; - *listpp = ret; - - return ccNoError; -} - -/** - * cci_generic_list_append() - * - * Purpose: Appends a new node containing a copy of 'len' bytes of 'data' - * - * Return: non-NULL, a pointer to the newly allocated node - * NULL, failure - * - * Errors: ccErrNoMem,ccErrBadParam - * - */ -cc_int32 -cci_generic_list_append(cc_generic_list_head_t *head, void *data, cc_uint32 len, cc_generic_list_node_t** nodepp) -{ - cc_generic_list_node_t* new_node; - - if ( data == NULL || len == 0 ) - return ccErrBadParam; - - new_node = (cc_generic_list_node_t *)malloc(sizeof(cc_generic_list_node_t)); - if (new_node == NULL) - return ccErrNoMem; - - new_node->data = malloc(len); - if ( new_node->data == NULL ) { - free(new_node); - return ccErrNoMem; - } - - memcpy(new_node->data,data,len); - new_node->len = len; - - if (head->head == NULL) { /*empty list*/ - head->head = new_node; - head->tail = new_node; - new_node->next = new_node->prev = NULL; - } else { - new_node->prev = head->tail; - head->tail->next = new_node; - head->tail = new_node; - new_node->next = NULL; - } - if (nodepp != NULL) - *nodepp = new_node; - return ccNoError; -} - -/** - * cci_generic_list_prepend() - * - * Purpose: Prepends a new node containing a copy of 'len' bytes of 'data' - * - * Return: non-NULL, a pointer to the newly allocated node - * NULL, failure - * - * Errors: ccErrNoMem, ccErrBadParam - * - */ -cc_int32 -cci_generic_list_prepend(cc_generic_list_head_t *head, void *data, cc_uint32 len, cc_generic_list_node_t** nodepp) -{ - cc_generic_list_node_t* new_node; - - if ( data == NULL || len == 0 ) - return ccErrBadParam; - - new_node = (cc_generic_list_node_t *)malloc(sizeof(cc_generic_list_node_t)); - if (new_node == NULL) - return ccErrNoMem; - - new_node->data = malloc(len); - if ( new_node->data == NULL ) { - free(new_node); - return ccErrNoMem; - } - - memcpy(new_node->data,data,len); - new_node->len = len; - - if (head->head == NULL) { /*empty list*/ - head->head = new_node; - head->tail = new_node; - new_node->prev = new_node->next = NULL; - } else { - new_node->next = head->head; - head->head->prev = new_node; - new_node->prev = NULL; - head->head = new_node; - } - - if (nodepp != NULL) - *nodepp = new_node; - - return ccNoError; -} - -/** - * cci_generic_list_remove_element() - * - * Purpose: Remove a node from the list - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_generic_list_remove_element(cc_generic_list_head_t* head, cc_generic_list_node_t* rem) -{ - if (head->head == NULL || rem == NULL) - return ccErrBadParam; - - if (head->head == rem && head->tail == rem) { /*removing only element of list*/ - head->head = head->tail = NULL; - } else if (head->head == rem) { /*removing head*/ - head->head = head->head->next; - } else if (head->tail == rem) { /*removing tail*/ - head->tail = head->tail->prev; - head->tail->next = NULL; - } else { - rem->prev->next = rem->next; - rem->next->prev = rem->prev; - } - free(rem); - return ccNoError; -} - -/** - * cci_generic_free_element() - * - * Purpose: Free the memory associated with a node - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_generic_free_element(cc_generic_list_node_t* node) -{ - if ( node == NULL ) - return ccErrBadParam; - - if ( node->data ) { - free(node->data); - node->data = NULL; - } - node->len = 0; - node->next = node->prev = NULL; - free(node); - return ccNoError; -} - - -/** - * cci_generic_list_destroy() - * - * Purpose: Deallocate a list and all of its contents - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - */ -cc_int32 -cci_generic_list_destroy(cc_generic_list_head_t* head) -{ - cc_generic_list_node_t *cur, *next; - cc_int32 ret = ccNoError; - - if ( head == NULL ) - return ccErrBadParam; - - for (cur = head->head; ret == ccNoError && cur != NULL; cur = next) { - next = cur->next; - ret = cci_generic_free_element(cur); - } - free(head); - return(ret); -} - -/** - * cci_context_list_destroy() - * - * Purpose: Deallocate a list and all of its contents - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - */ -cc_int32 -cci_context_list_destroy(cc_context_list_head_t* head) -{ - return cci_generic_list_destroy((cc_generic_list_head_t*)head); -} - -/** - * cci_ccache_list_destroy() - * - * Purpose: Deallocate a list and all of its contents - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - */ -cc_int32 -cci_ccache_list_destroy(cc_ccache_list_head_t* head) -{ - return cci_generic_list_destroy((cc_generic_list_head_t*)head); -} - -/** - * cci_credentials_list_destroy() - * - * Purpose: Deallocate a list and all of its contents - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - */ -cc_int32 -cci_credentials_list_destroy(cc_credentials_list_head_t* head) -{ - return cci_generic_list_destroy((cc_generic_list_head_t*)head); -} - -/** - * cci_generic_list_copy() - * - * Purpose: Copy a list - * - * Return: non-NULL, a new list - * NULL, failure - * - * Errors: ccErrBadParam, ccErrNoMem - * - */ -cc_int32 -cci_generic_list_copy(cc_generic_list_head_t* head, cc_generic_list_head_t** headpp) -{ - cc_generic_list_head_t* copy; - cc_generic_list_node_t *src_node, *dst_node; - cc_int32 code; - - if (head == NULL || headpp == NULL) - return ccErrBadParam; - - code = cci_generic_list_new(©); - if (code != ccNoError) - return code; - - for (src_node = head->head; src_node != NULL; src_node = src_node->next) { - code = cci_generic_list_append(copy, src_node->data, src_node->len, &dst_node); - if (code != ccNoError) { - cci_generic_list_destroy(copy); - return code; - } - } - *headpp = copy; - return ccNoError; -} - -/** - * cci_context_list_copy() - * - * Purpose: Copy a list - * - * Return: non-NULL, a new list - * NULL, failure - * - * Errors: ccErrBadParam, ccErrNoMem - * - */ -cc_int32 -cci_context_list_copy(cc_context_list_head_t* head, cc_context_list_head_t** headpp ) -{ - return cci_generic_list_copy((cc_generic_list_head_t*)head, (cc_context_list_head_t **)headpp); -} - -/** - * cci_ccache_list_copy() - * - * Purpose: Copy a list - * - * Return: non-NULL, a new list - * NULL, failure - * - * Errors: ccErrBadParam, ccErrNoMem - */ -cc_int32 -cci_ccache_list_copy(cc_ccache_list_head_t* head, cc_ccache_list_head_t** headpp) -{ - return cci_generic_list_copy((cc_generic_list_head_t*)head, (cc_ccache_list_head_t **)headpp); -} - -/** - * cci_credentials_list_copy() - * - * Purpose: Copy a list - * - * Return: non-NULL, a new list - * NULL, failure - * - * Errors: ccErrBadParam, ccErrNoMem - * - */ -cc_int32 -cci_credentials_list_copy(cc_credentials_list_head_t* head, cc_credentials_list_head_t** headpp) -{ - return cci_generic_list_copy((cc_generic_list_head_t*)head, (cc_credentials_list_head_t **)headpp); -} - - -/** - * cci_generic_list_iterator() - * - * Purpose: Allocate an iterator for the specified list - * - * Return: non-NULL, an iterator - * NULL, failure - * - * Errors: ccErrNoMem - * - */ -cc_int32 -cci_generic_list_iterator(cc_generic_list_head_t *head, cc_generic_iterate_t** headpp) -{ - cc_generic_iterate_t* iterator; - - if ( head == NULL || headpp == NULL ) - return ccErrBadParam; - - iterator = (cc_generic_iterate_t*)malloc(sizeof(cc_generic_iterate_t)); - if (iterator == NULL) - return ccErrNoMem; - - iterator->next = head->head; - *headpp = iterator; - return ccNoError; -} - -/** - * cci_generic_free_iterator() - * - * Purpose: Deallocate memory associated with an iterator - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_generic_free_iterator(cc_generic_iterate_t* iterator) -{ - if ( iterator == NULL ) - return ccErrBadParam; - - iterator->next = NULL; - free(iterator); - return ccNoError; -} - - -/** - * cci_context_list_new() - * - * Purpose: Allocate a new context list - * - * Return: non-NULL, a new list - * NULL, failure - * - * Errors: ccErrNoMem - * - */ -cc_int32 -cci_context_list_new(cc_context_list_head_t ** headpp) -{ - cc_context_list_head_t *ret; - - if ( headpp == NULL ) - return ccErrBadParam; - - ret = (cc_context_list_head_t *)malloc(sizeof(cc_context_list_head_t)); - if (ret == NULL) - return ccErrNoMem; - ret->head = ret->tail = NULL; - *headpp = ret; - return ccNoError; -} - -/** - * cci_context_list_append() - * - * Purpose: Appends a new node containing a copy of 'len' bytes of 'data' - * - * Return: non-NULL, a pointer to the newly allocated node - * NULL, failure - * - * Errors: ccErrNoMem,ccErrBadParam - * - */ -cc_int32 -cci_context_list_append(cc_context_list_head_t *head, cc_server_context_t *data, cc_context_list_node_t** nodepp) -{ - return cci_generic_list_append((cc_generic_list_head_t *)head, (void *)data, sizeof(cc_server_context_t), (cc_context_list_node_t**)nodepp); -} - -/** - * cci_context_list_prepend() - * - * Purpose: Prepends a new node containing a copy of 'len' bytes of 'data' - * - * Return: non-NULL, a pointer to the newly allocated node - * NULL, failure - * - * Errors: ccErrNoMem,ccErrBadParam - * - */ -cc_int32 -cci_context_list_prepend(cc_context_list_head_t *head, cc_server_context_t *data, cc_context_list_node_t** nodepp ) -{ - return cci_generic_list_prepend((cc_generic_list_head_t *)head, (void *)data, sizeof(cc_server_context_t), (cc_context_list_node_t**)nodepp); -} - -/** - * cci_context_list_remove_element - * - * Purpose: Remove a node from the list - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - */ -cc_int32 -cci_context_list_remove_element(cc_context_list_head_t* head, cc_context_list_node_t* rem) -{ - return cci_generic_list_remove_element((cc_generic_list_head_t*)head, (cc_generic_list_node_t*)rem); -} - -/** - * cci_context_list_iterator() - * - * Purpose: Allocate an iterator for the specified list - * - * Return: non-NULL, an iterator - * NULL, failure - * - * Errors: ccErrNoMem - * - */ -cc_int32 -cci_context_list_iterator(cc_context_list_head_t *head, cc_context_iterate_t** iterpp) -{ - cc_context_iterate_t* iterator; - - if ( head == NULL || iterpp == NULL ) - return ccErrBadParam; - - iterator = (cc_context_iterate_t*)malloc(sizeof(cc_context_iterate_t)); - if (iterator == NULL) - return ccErrNoMem; - - iterator->next = head->head; - *iterpp = iterator; - return ccNoError; -} - -/** - * cci_context_free_iterator() - * - * Purpose: Deallocate memory associated with an iterator - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_context_free_iterator(cc_context_iterate_t* iterator) -{ - if ( iterator == NULL ) - return ccErrBadParam; - - iterator->next = NULL; - free(iterator); - return ccNoError; -} - -/** - * cci_ccache_list_new() - * - * Purpose: Allocate a new ccache list - * - * Return: non-NULL, a new list - * NULL, failure - * - * Errors: ccErrNoMem - */ -cc_int32 -cci_ccache_list_new(cc_ccache_list_head_t ** listpp) -{ - cc_ccache_list_head_t *ret; - - if ( listpp == NULL ) - return ccErrBadParam; - - ret = (cc_ccache_list_head_t *)malloc(sizeof(cc_ccache_list_head_t)); - if (ret == NULL) - return ccErrNoMem; - - ret->head = ret->tail = NULL; - *listpp = ret; - return ccNoError; -} - -/** - * cci_ccache_list_append() - * - * Purpose: Appends a new node containing a copy of 'len' bytes of 'data' - * - * Return: non-NULL, a pointer to the newly allocated node - * NULL, failure - * - * Errors: ccErrNoMem,ccErrBadParam - * - */ -cc_int32 -cci_ccache_list_append(cc_ccache_list_head_t *head, cc_server_ccache_t *data, cc_ccache_list_node_t** nodepp) -{ - return cci_generic_list_append((cc_generic_list_head_t *)head, (void *)data, sizeof(cc_server_ccache_t), (cc_ccache_list_node_t**)nodepp); -} - -/** - * cci_ccache_list_prepend() - * - * Purpose: Prepends a new node containing a copy of 'len' bytes of 'data' - * - * Return: non-NULL, a pointer to the newly allocated node - * NULL, failure - * - * Errors: ccErrNoMem,ccErrBadParam - * - */ -cc_int32 -cci_ccache_list_prepend(cc_ccache_list_head_t *head, cc_server_ccache_t *data, cc_ccache_list_node_t** nodepp) -{ - return cci_generic_list_prepend((cc_generic_list_head_t *)head, (void *)data, sizeof(cc_server_ccache_t), (cc_ccache_list_node_t**)nodepp); -} - -/** - * cci_ccache_list_remove_element() - * - * Purpose: Remove a node from the list - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_ccache_list_remove_element(cc_ccache_list_head_t* head, cc_ccache_list_node_t* rem) -{ - return cci_generic_list_remove_element((cc_generic_list_head_t*)head, (cc_generic_list_node_t*)rem); -} - -/** - * cci_ccache_list_iterator() - * - * Purpose: Allocate an iterator for the specified list - * - * Return: non-NULL, an iterator - * NULL, failure - * - * Errors: ccErrNoMem - * - */ -cc_int32 -cci_ccache_list_iterator(cc_ccache_list_head_t *head, cc_ccache_iterate_t** iterpp) -{ - cc_ccache_iterate_t* iterator; - - if ( head == NULL || iterpp == NULL ) - return ccErrBadParam; - - iterator = (cc_ccache_iterate_t*)malloc(sizeof(cc_ccache_iterate_t)); - if (iterator == NULL) - return ccErrNoMem; - - iterator->next = head->head; - *iterpp = iterator; - return ccNoError; -} - -/** - * cci_ccache_free_iterator() - * - * Purpose: Deallocate memory associated with an iterator - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_ccache_free_iterator(cc_ccache_iterate_t* iterator) -{ - if ( iterator == NULL ) - return ccErrBadParam; - - iterator->next = NULL; - free(iterator); - return ccNoError; -} - -/** - * cci_credentials_list_new() - * - * Purpose: Allocate a new ccache list - * - * Return: non-NULL, a new list - * NULL, failure - * - * Errors: ccErrNoMem - * - */ -cc_int32 -cci_credentials_list_new(cc_credentials_list_head_t ** list) -{ - if ( list == NULL ) - return ccErrBadParam; - - *list = (cc_credentials_list_head_t *)malloc(sizeof(cc_credentials_list_head_t)); - if (*list == NULL) - return ccErrNoMem; - - (*list)->head = (*list)->tail = NULL; - return ccNoError; -} - -/** - * cci_credentials_list_append() - * - * Purpose: Appends a new node containing a copy of 'len' bytes of 'data' - * - * Return: non-NULL, a pointer to the newly allocated node - * NULL, failure - * - * Errors: ccErrNoMem,ccErrBadParam - * - */ -cc_int32 -cci_credentials_list_append(cc_credentials_list_head_t *head, cc_server_credentials_t *data, cc_credentials_list_node_t** nodepp ) -{ - return cci_generic_list_append((cc_generic_list_head_t *)head, (void *)data, sizeof(cc_server_credentials_t), (cc_credentials_list_node_t**)nodepp); -} - -/** - * cci_credentials_list_prepend() - * - * Purpose: Prepends a new node containing a copy of 'len' bytes of 'data' - * - * Return: non-NULL, a pointer to the newly allocated node - * NULL, failure - * - * Errors: ccErrNoMem,ccErrBadParam - * - */ -cc_int32 -cci_credentials_list_prepend(cc_credentials_list_head_t *head, cc_server_credentials_t *data, cc_credentials_list_node_t** nodepp) -{ - return cci_generic_list_prepend((cc_generic_list_head_t *)head, (void *)data, sizeof(cc_server_credentials_t), (cc_credentials_list_node_t**)nodepp); -} - -/** - * cci_credentials_list_remove_element() - * - * Purpose: Remove a node from the list - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_credentials_list_remove_element(cc_credentials_list_head_t* head, cc_credentials_list_node_t* rem) -{ - return cci_generic_list_remove_element((cc_generic_list_head_t*)head, (cc_generic_list_node_t*)rem); -} - -/** - * cci_credentials_list_iterator() - * - * Purpose: Allocate an iterator for the specified list - * - * Return: non-NULL, an iterator - * NULL, failure - * - * Errors: ccErrNoMem - * - */ -cc_int32 -cci_credentials_list_iterator(cc_credentials_list_head_t *head, cc_credentials_iterate_t** iterpp) -{ - cc_credentials_iterate_t* iterator; - - if ( head == NULL || iterpp == NULL ) - return ccErrBadParam; - - iterator = (cc_credentials_iterate_t*)malloc(sizeof(cc_credentials_iterate_t)); - if (iterator == NULL) - return ccErrNoMem; - - iterator->next = head->head; - *iterpp = iterator; - return ccNoError; -} - -/** - * cci_credentials_free_iterator() - * - * Purpose: Deallocate memory associated with an iterator - * - * Return: 0, success - * -1, failure - * - * Errors: ccErrBadParam - * - */ -cc_int32 -cci_credentials_free_iterator(cc_credentials_iterate_t* iterator) -{ - if ( iterator == NULL ) - return ccErrBadParam; - - iterator->next = NULL; - free(iterator); - return ccNoError; -} - +/* $Copyright: + * + * Copyright 2004-2006 by the Massachusetts Institute of Technology. + * + * All rights reserved. + * + * Export of this software from the United States of America may require a + * specific license from the United States Government. It is the + * responsibility of any person or organization contemplating export to + * obtain such a license before exporting. + * + * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and distribute + * this software and its documentation for any purpose and without fee is + * hereby granted, provided that the above copyright notice appear in all + * copies and that both that copyright notice and this permission notice + * appear in supporting documentation, and that the name of M.I.T. not be + * used in advertising or publicity pertaining to distribution of the + * software without specific, written prior permission. Furthermore if you + * modify this software you must label your software as modified software + * and not distribute it in such a fashion that it might be confused with + * the original MIT software. M.I.T. makes no representations about the + * suitability of this software for any purpose. It is provided "as is" + * without express or implied warranty. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. + * + * Individual source code files are copyright MIT, Cygnus Support, + * OpenVision, Oracle, Sun Soft, FundsXpress, and others. + * + * Project Athena, Athena, Athena MUSE, Discuss, Hesiod, Kerberos, Moira, + * and Zephyr are trademarks of the Massachusetts Institute of Technology + * (MIT). No commercial use of these trademarks may be made without prior + * written permission of MIT. + * + * "Commercial use" means use of a name in a product or other for-profit + * manner. It does NOT prevent a commercial firm from referring to the MIT + * trademarks in order to convey information (although in doing so, + * recognition of their trademark status should be given). + * $ + */ + + +/* + * Lists implementation. + * + */ + +#include +#include +#include + +#include "CredentialsCache.h" +#include "datastore.h" + +/** + * cci_generic_iterate_has_next() + * + * Purpose: Determine if an iterator has a next element + * + * Return: 1 if another element exists + * 0 if no additional elements exist + * + * Errors: None + * + */ +cc_int32 +cci_generic_iterate_has_next(cc_generic_iterate_t *iterate) +{ + return ((iterate == NULL || iterate->next == NULL) ? 0 : 1); +} + +/** + * cci_generic_iterate_next() + * + * Purpose: Retrieve the next element from an iterator and advance + * the iterator + * + * Return: non-NULL, the next element in the iterator + * NULL, the iterator list is empty or iterator is invalid + * + * Errors: ccErrBadParam + * + */ +cc_int32 +cci_generic_iterate_next(cc_generic_iterate_t *iterator, cc_generic_list_node_t** nodepp) +{ + cc_generic_list_node_t* ret; + + if (iterator == NULL || nodepp == NULL) + return ccErrBadParam; + + ret = iterator->next; + if (iterator->next != NULL) + iterator->next = iterator->next->next; + + *nodepp = ret; + return ccNoError; +} + +/** + * ccs_context_iterate_has_next() + * + * Purpose: Determine if a context iterator has a next element + * + * Return: 1 if another element exists + * 0 if no additional elements exist + */ +cc_int32 +ccs_context_iterate_has_next(cc_context_iterate_t *iterate) +{ + if ( iterate == NULL ) + return 0; + + return cci_generic_iterate_has_next((cc_generic_iterate_t*)iterate); +} + +/** + * ccs_context_iterate_next() + * + * Purpose: Retrieve the next element from a context iterator and advance + * the iterator + * + * Return: non-NULL, the next element in the iterator + * NULL, the iterator list is empty or iterator is invalid + * + * Errors: ccErrBadParam + * + */ +cc_int32 +ccs_context_iterate_next(cc_context_iterate_t *iterate, cc_context_list_node_t ** nodepp) +{ + if ( iterate == NULL || nodepp == NULL) + return ccErrBadParam; + + return cci_generic_iterate_next((cc_generic_iterate_t*)iterate,(cc_context_list_node_t**)nodepp); +} + +/** + * ccs_ccache_iterate_has_next() + * + * Purpose: Determine if a cache iterator has a next element + * + * Return: 1 if another element exists + * 0 if no additional elements exist + * -1 if error + * + * Errors: ccErrBadParam + * + */ +cc_int32 +ccs_ccache_iterate_has_next(cc_ccache_iterate_t *iterate) +{ + if ( iterate == NULL ) + return 0; + return cci_generic_iterate_has_next((cc_generic_iterate_t*)iterate); +} + +/** + * ccs_ccache_iterate_next() + * + * Purpose: Retrieve the next element from a ccache iterator and advance + * the iterator + * + * Return: non-NULL, the next element in the iterator + * NULL, the iterator list is empty or iterator is invalid + * + * Errors: ccErrBadParam + * + */ +cc_int32 +ccs_ccache_iterate_next(cc_ccache_iterate_t *iterate, cc_ccache_list_node_t ** nodepp) +{ + if ( iterate == NULL || nodepp == NULL) + return ccErrBadParam; + + return cci_generic_iterate_next((cc_generic_iterate_t*)iterate, (cc_ccache_list_node_t**)nodepp); +} + +/** + * ccs_credentials_iterate_has_next() + * + * Purpose: Determine if a credentials iterator has a next element + * + * Return: 1 if another element exists + * 0 if no additional elements exist + * -1 if error + * + * Errors: ccErrBadParam + * + */ +cc_int32 +ccs_credentials_iterate_has_next(cc_credentials_iterate_t *iterate) +{ + if ( iterate == NULL ) + return 0; + + return cci_generic_iterate_has_next((cc_generic_iterate_t*)iterate); +} + +/** + * ccs_credentials_iterate_next() + * + * Purpose: Retrieve the next element from a credentials iterator and advance + * the iterator + * + * Return: non-NULL, the next element in the iterator + * NULL, the iterator list is empty or iterator is invalid + * + * Errors: ccErrBadParam + * + */ +cc_int32 +ccs_credentials_iterate_next(cc_credentials_iterate_t *iterate, cc_credentials_list_node_t** nodepp) +{ + if ( iterate == NULL || nodepp == NULL ) + return ccErrBadParam; + return cci_generic_iterate_next((cc_generic_iterate_t*)iterate, (cc_credentials_list_node_t**)nodepp); +} + +/** + * cci_generic_list_new() + * + * Purpose: Allocate new generic list + * + * Return: non-NULL, an empty list + * NULL, failure + * + * Errors: ccErrNoMem + * + */ +cc_int32 +cci_generic_list_new(cc_generic_list_head_t ** listpp) +{ + cc_generic_list_head_t* ret = (cc_generic_list_head_t *)malloc(sizeof(cc_generic_list_head_t)); + if (ret == NULL) + return ccErrNoMem; + + ret->type = generic; + ret->head = ret->tail = NULL; + *listpp = ret; + + return ccNoError; +} + +/** + * cci_generic_list_append() + * + * Purpose: Appends a new node containing a copy of 'len' bytes of 'data' + * + * Return: non-NULL, a pointer to the newly allocated node + * NULL, failure + * + * Errors: ccErrNoMem,ccErrBadParam + * + */ +cc_int32 +cci_generic_list_append(cc_generic_list_head_t *head, void *data, cc_uint32 len, cc_generic_list_node_t** nodepp) +{ + cc_generic_list_node_t* new_node; + + if ( data == NULL || len == 0 ) + return ccErrBadParam; + + new_node = (cc_generic_list_node_t *)malloc(sizeof(cc_generic_list_node_t)); + if (new_node == NULL) + return ccErrNoMem; + + new_node->data = malloc(len); + if ( new_node->data == NULL ) { + free(new_node); + return ccErrNoMem; + } + + memcpy(new_node->data,data,len); + new_node->len = len; + + if (head->head == NULL) { /*empty list*/ + head->head = new_node; + head->tail = new_node; + new_node->next = new_node->prev = NULL; + } else { + new_node->prev = head->tail; + head->tail->next = new_node; + head->tail = new_node; + new_node->next = NULL; + } + if (nodepp != NULL) + *nodepp = new_node; + return ccNoError; +} + +/** + * cci_generic_list_prepend() + * + * Purpose: Prepends a new node containing a copy of 'len' bytes of 'data' + * + * Return: non-NULL, a pointer to the newly allocated node + * NULL, failure + * + * Errors: ccErrNoMem, ccErrBadParam + * + */ +cc_int32 +cci_generic_list_prepend(cc_generic_list_head_t *head, void *data, cc_uint32 len, cc_generic_list_node_t** nodepp) +{ + cc_generic_list_node_t* new_node; + + if ( data == NULL || len == 0 ) + return ccErrBadParam; + + new_node = (cc_generic_list_node_t *)malloc(sizeof(cc_generic_list_node_t)); + if (new_node == NULL) + return ccErrNoMem; + + new_node->data = malloc(len); + if ( new_node->data == NULL ) { + free(new_node); + return ccErrNoMem; + } + + memcpy(new_node->data,data,len); + new_node->len = len; + + if (head->head == NULL) { /*empty list*/ + head->head = new_node; + head->tail = new_node; + new_node->prev = new_node->next = NULL; + } else { + new_node->next = head->head; + head->head->prev = new_node; + new_node->prev = NULL; + head->head = new_node; + } + + if (nodepp != NULL) + *nodepp = new_node; + + return ccNoError; +} + +/** + * cci_generic_list_remove_element() + * + * Purpose: Remove a node from the list + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + * + */ +cc_int32 +cci_generic_list_remove_element(cc_generic_list_head_t* head, cc_generic_list_node_t* rem) +{ + if (head->head == NULL || rem == NULL) + return ccErrBadParam; + + if (head->head == rem && head->tail == rem) { /*removing only element of list*/ + head->head = head->tail = NULL; + } else if (head->head == rem) { /*removing head*/ + head->head = head->head->next; + } else if (head->tail == rem) { /*removing tail*/ + head->tail = head->tail->prev; + head->tail->next = NULL; + } else { + rem->prev->next = rem->next; + rem->next->prev = rem->prev; + } + free(rem); + return ccNoError; +} + +/** + * cci_generic_free_element() + * + * Purpose: Free the memory associated with a node + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + * + */ +cc_int32 +cci_generic_free_element(cc_generic_list_node_t* node) +{ + if ( node == NULL ) + return ccErrBadParam; + + if ( node->data ) { + free(node->data); + node->data = NULL; + } + node->len = 0; + node->next = node->prev = NULL; + free(node); + return ccNoError; +} + + +/** + * cci_generic_list_destroy() + * + * Purpose: Deallocate a list and all of its contents + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + */ +cc_int32 +cci_generic_list_destroy(cc_generic_list_head_t* head) +{ + cc_generic_list_node_t *cur, *next; + cc_int32 ret = ccNoError; + + if ( head == NULL ) + return ccErrBadParam; + + for (cur = head->head; ret == ccNoError && cur != NULL; cur = next) { + next = cur->next; + ret = cci_generic_free_element(cur); + } + free(head); + return(ret); +} + +/** + * ccs_context_list_destroy() + * + * Purpose: Deallocate a list and all of its contents + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + */ +cc_int32 +ccs_context_list_destroy(cc_context_list_head_t* head) +{ + return cci_generic_list_destroy((cc_generic_list_head_t*)head); +} + +/** + * ccs_ccache_list_destroy() + * + * Purpose: Deallocate a list and all of its contents + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + */ +cc_int32 +ccs_ccache_list_destroy(cc_ccache_list_head_t* head) +{ + return cci_generic_list_destroy((cc_generic_list_head_t*)head); +} + +/** + * ccs_credentials_list_destroy() + * + * Purpose: Deallocate a list and all of its contents + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + */ +cc_int32 +ccs_credentials_list_destroy(cc_credentials_list_head_t* head) +{ + return cci_generic_list_destroy((cc_generic_list_head_t*)head); +} + +/** + * cci_generic_list_copy() + * + * Purpose: Copy a list + * + * Return: non-NULL, a new list + * NULL, failure + * + * Errors: ccErrBadParam, ccErrNoMem + * + */ +cc_int32 +cci_generic_list_copy(cc_generic_list_head_t* head, cc_generic_list_head_t** headpp) +{ + cc_generic_list_head_t* copy; + cc_generic_list_node_t *src_node, *dst_node; + cc_int32 code; + + if (head == NULL || headpp == NULL) + return ccErrBadParam; + + code = cci_generic_list_new(©); + if (code != ccNoError) + return code; + + for (src_node = head->head; src_node != NULL; src_node = src_node->next) { + code = cci_generic_list_append(copy, src_node->data, src_node->len, &dst_node); + if (code != ccNoError) { + cci_generic_list_destroy(copy); + return code; + } + } + *headpp = copy; + return ccNoError; +} + +/** + * ccs_context_list_copy() + * + * Purpose: Copy a list + * + * Return: non-NULL, a new list + * NULL, failure + * + * Errors: ccErrBadParam, ccErrNoMem + * + */ +cc_int32 +ccs_context_list_copy(cc_context_list_head_t* head, cc_context_list_head_t** headpp ) +{ + return cci_generic_list_copy((cc_generic_list_head_t*)head, (cc_context_list_head_t **)headpp); +} + +/** + * ccs_ccache_list_copy() + * + * Purpose: Copy a list + * + * Return: non-NULL, a new list + * NULL, failure + * + * Errors: ccErrBadParam, ccErrNoMem + */ +cc_int32 +ccs_ccache_list_copy(cc_ccache_list_head_t* head, cc_ccache_list_head_t** headpp) +{ + return cci_generic_list_copy((cc_generic_list_head_t*)head, (cc_ccache_list_head_t **)headpp); +} + +/** + * ccs_credentials_list_copy() + * + * Purpose: Copy a list + * + * Return: non-NULL, a new list + * NULL, failure + * + * Errors: ccErrBadParam, ccErrNoMem + * + */ +cc_int32 +ccs_credentials_list_copy(cc_credentials_list_head_t* head, cc_credentials_list_head_t** headpp) +{ + return cci_generic_list_copy((cc_generic_list_head_t*)head, (cc_credentials_list_head_t **)headpp); +} + + +/** + * cci_generic_list_iterator() + * + * Purpose: Allocate an iterator for the specified list + * + * Return: non-NULL, an iterator + * NULL, failure + * + * Errors: ccErrNoMem + * + */ +cc_int32 +cci_generic_list_iterator(cc_generic_list_head_t *head, cc_generic_iterate_t** headpp) +{ + cc_generic_iterate_t* iterator; + + if ( head == NULL || headpp == NULL ) + return ccErrBadParam; + + iterator = (cc_generic_iterate_t*)malloc(sizeof(cc_generic_iterate_t)); + if (iterator == NULL) + return ccErrNoMem; + + iterator->next = head->head; + *headpp = iterator; + return ccNoError; +} + +/** + * cci_generic_free_iterator() + * + * Purpose: Deallocate memory associated with an iterator + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + * + */ +cc_int32 +cci_generic_free_iterator(cc_generic_iterate_t* iterator) +{ + if ( iterator == NULL ) + return ccErrBadParam; + + iterator->next = NULL; + free(iterator); + return ccNoError; +} + + +/** + * ccs_context_list_new() + * + * Purpose: Allocate a new context list + * + * Return: non-NULL, a new list + * NULL, failure + * + * Errors: ccErrNoMem + * + */ +cc_int32 +ccs_context_list_new(cc_context_list_head_t ** headpp) +{ + cc_context_list_head_t *ret; + + if ( headpp == NULL ) + return ccErrBadParam; + + ret = (cc_context_list_head_t *)malloc(sizeof(cc_context_list_head_t)); + if (ret == NULL) + return ccErrNoMem; + ret->head = ret->tail = NULL; + *headpp = ret; + return ccNoError; +} + +/** + * ccs_context_list_append() + * + * Purpose: Appends a new node containing a copy of 'len' bytes of 'data' + * + * Return: non-NULL, a pointer to the newly allocated node + * NULL, failure + * + * Errors: ccErrNoMem,ccErrBadParam + * + */ +cc_int32 +ccs_context_list_append(cc_context_list_head_t *head, cc_server_context_t *data, cc_context_list_node_t** nodepp) +{ + return cci_generic_list_append((cc_generic_list_head_t *)head, (void *)data, sizeof(cc_server_context_t), (cc_context_list_node_t**)nodepp); +} + +/** + * ccs_context_list_prepend() + * + * Purpose: Prepends a new node containing a copy of 'len' bytes of 'data' + * + * Return: non-NULL, a pointer to the newly allocated node + * NULL, failure + * + * Errors: ccErrNoMem,ccErrBadParam + * + */ +cc_int32 +ccs_context_list_prepend(cc_context_list_head_t *head, cc_server_context_t *data, cc_context_list_node_t** nodepp ) +{ + return cci_generic_list_prepend((cc_generic_list_head_t *)head, (void *)data, sizeof(cc_server_context_t), (cc_context_list_node_t**)nodepp); +} + +/** + * ccs_context_list_remove_element + * + * Purpose: Remove a node from the list + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + */ +cc_int32 +ccs_context_list_remove_element(cc_context_list_head_t* head, cc_context_list_node_t* rem) +{ + return cci_generic_list_remove_element((cc_generic_list_head_t*)head, (cc_generic_list_node_t*)rem); +} + +/** + * ccs_context_list_iterator() + * + * Purpose: Allocate an iterator for the specified list + * + * Return: non-NULL, an iterator + * NULL, failure + * + * Errors: ccErrNoMem + * + */ +cc_int32 +ccs_context_list_iterator(cc_context_list_head_t *head, cc_context_iterate_t** iterpp) +{ + cc_context_iterate_t* iterator; + + if ( head == NULL || iterpp == NULL ) + return ccErrBadParam; + + iterator = (cc_context_iterate_t*)malloc(sizeof(cc_context_iterate_t)); + if (iterator == NULL) + return ccErrNoMem; + + iterator->next = head->head; + *iterpp = iterator; + return ccNoError; +} + +/** + * ccs_context_free_iterator() + * + * Purpose: Deallocate memory associated with an iterator + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + * + */ +cc_int32 +ccs_context_free_iterator(cc_context_iterate_t* iterator) +{ + if ( iterator == NULL ) + return ccErrBadParam; + + iterator->next = NULL; + free(iterator); + return ccNoError; +} + +/** + * ccs_ccache_list_new() + * + * Purpose: Allocate a new ccache list + * + * Return: non-NULL, a new list + * NULL, failure + * + * Errors: ccErrNoMem + */ +cc_int32 +ccs_ccache_list_new(cc_ccache_list_head_t ** listpp) +{ + cc_ccache_list_head_t *ret; + + if ( listpp == NULL ) + return ccErrBadParam; + + ret = (cc_ccache_list_head_t *)malloc(sizeof(cc_ccache_list_head_t)); + if (ret == NULL) + return ccErrNoMem; + + ret->head = ret->tail = NULL; + *listpp = ret; + return ccNoError; +} + +/** + * ccs_ccache_list_append() + * + * Purpose: Appends a new node containing a copy of 'len' bytes of 'data' + * + * Return: non-NULL, a pointer to the newly allocated node + * NULL, failure + * + * Errors: ccErrNoMem,ccErrBadParam + * + */ +cc_int32 +ccs_ccache_list_append(cc_ccache_list_head_t *head, cc_server_ccache_t *data, cc_ccache_list_node_t** nodepp) +{ + return cci_generic_list_append((cc_generic_list_head_t *)head, (void *)data, sizeof(cc_server_ccache_t), (cc_ccache_list_node_t**)nodepp); +} + +/** + * ccs_ccache_list_prepend() + * + * Purpose: Prepends a new node containing a copy of 'len' bytes of 'data' + * + * Return: non-NULL, a pointer to the newly allocated node + * NULL, failure + * + * Errors: ccErrNoMem,ccErrBadParam + * + */ +cc_int32 +ccs_ccache_list_prepend(cc_ccache_list_head_t *head, cc_server_ccache_t *data, cc_ccache_list_node_t** nodepp) +{ + return cci_generic_list_prepend((cc_generic_list_head_t *)head, (void *)data, sizeof(cc_server_ccache_t), (cc_ccache_list_node_t**)nodepp); +} + +/** + * ccs_ccache_list_remove_element() + * + * Purpose: Remove a node from the list + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + * + */ +cc_int32 +ccs_ccache_list_remove_element(cc_ccache_list_head_t* head, cc_ccache_list_node_t* rem) +{ + return cci_generic_list_remove_element((cc_generic_list_head_t*)head, (cc_generic_list_node_t*)rem); +} + +/** + * ccs_ccache_list_iterator() + * + * Purpose: Allocate an iterator for the specified list + * + * Return: non-NULL, an iterator + * NULL, failure + * + * Errors: ccErrNoMem + * + */ +cc_int32 +ccs_ccache_list_iterator(cc_ccache_list_head_t *head, cc_ccache_iterate_t** iterpp) +{ + cc_ccache_iterate_t* iterator; + + if ( head == NULL || iterpp == NULL ) + return ccErrBadParam; + + iterator = (cc_ccache_iterate_t*)malloc(sizeof(cc_ccache_iterate_t)); + if (iterator == NULL) + return ccErrNoMem; + + iterator->next = head->head; + *iterpp = iterator; + return ccNoError; +} + +/** + * ccs_ccache_free_iterator() + * + * Purpose: Deallocate memory associated with an iterator + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + * + */ +cc_int32 +ccs_ccache_free_iterator(cc_ccache_iterate_t* iterator) +{ + if ( iterator == NULL ) + return ccErrBadParam; + + iterator->next = NULL; + free(iterator); + return ccNoError; +} + +/** + * ccs_credentials_list_new() + * + * Purpose: Allocate a new ccache list + * + * Return: non-NULL, a new list + * NULL, failure + * + * Errors: ccErrNoMem + * + */ +cc_int32 +ccs_credentials_list_new(cc_credentials_list_head_t ** list) +{ + if ( list == NULL ) + return ccErrBadParam; + + *list = (cc_credentials_list_head_t *)malloc(sizeof(cc_credentials_list_head_t)); + if (*list == NULL) + return ccErrNoMem; + + (*list)->head = (*list)->tail = NULL; + return ccNoError; +} + +/** + * ccs_credentials_list_append() + * + * Purpose: Appends a new node containing a copy of 'len' bytes of 'data' + * + * Return: non-NULL, a pointer to the newly allocated node + * NULL, failure + * + * Errors: ccErrNoMem,ccErrBadParam + * + */ +cc_int32 +ccs_credentials_list_append(cc_credentials_list_head_t *head, cc_server_credentials_t *data, cc_credentials_list_node_t** nodepp ) +{ + return cci_generic_list_append((cc_generic_list_head_t *)head, (void *)data, sizeof(cc_server_credentials_t), (cc_credentials_list_node_t**)nodepp); +} + +/** + * ccs_credentials_list_prepend() + * + * Purpose: Prepends a new node containing a copy of 'len' bytes of 'data' + * + * Return: non-NULL, a pointer to the newly allocated node + * NULL, failure + * + * Errors: ccErrNoMem,ccErrBadParam + * + */ +cc_int32 +ccs_credentials_list_prepend(cc_credentials_list_head_t *head, cc_server_credentials_t *data, cc_credentials_list_node_t** nodepp) +{ + return cci_generic_list_prepend((cc_generic_list_head_t *)head, (void *)data, sizeof(cc_server_credentials_t), (cc_credentials_list_node_t**)nodepp); +} + +/** + * ccs_credentials_list_remove_element() + * + * Purpose: Remove a node from the list + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + * + */ +cc_int32 +ccs_credentials_list_remove_element(cc_credentials_list_head_t* head, cc_credentials_list_node_t* rem) +{ + return cci_generic_list_remove_element((cc_generic_list_head_t*)head, (cc_generic_list_node_t*)rem); +} + +/** + * ccs_credentials_list_iterator() + * + * Purpose: Allocate an iterator for the specified list + * + * Return: non-NULL, an iterator + * NULL, failure + * + * Errors: ccErrNoMem + * + */ +cc_int32 +ccs_credentials_list_iterator(cc_credentials_list_head_t *head, cc_credentials_iterate_t** iterpp) +{ + cc_credentials_iterate_t* iterator; + + if ( head == NULL || iterpp == NULL ) + return ccErrBadParam; + + iterator = (cc_credentials_iterate_t*)malloc(sizeof(cc_credentials_iterate_t)); + if (iterator == NULL) + return ccErrNoMem; + + iterator->next = head->head; + *iterpp = iterator; + return ccNoError; +} + +/** + * ccs_credentials_free_iterator() + * + * Purpose: Deallocate memory associated with an iterator + * + * Return: 0, success + * -1, failure + * + * Errors: ccErrBadParam + * + */ +cc_int32 +ccs_credentials_free_iterator(cc_credentials_iterate_t* iterator) +{ + if ( iterator == NULL ) + return ccErrBadParam; + + iterator->next = NULL; + free(iterator); + return ccNoError; +} + diff --git a/src/lib/ccapi/server/datastore.h b/src/lib/ccapi/server/datastore.h index a92c60636..4f119f969 100644 --- a/src/lib/ccapi/server/datastore.h +++ b/src/lib/ccapi/server/datastore.h @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -51,6 +51,7 @@ #include "CredentialsCache.h" #include "rpc_auth.h" +#include "generic_lists.h" enum cc_list_type { generic = 0, @@ -59,36 +60,6 @@ enum cc_list_type { credentials }; -struct cc_generic_list_node_t { - cc_uint8* data; - cc_uint32 len; - struct cc_generic_list_node_t* next; - struct cc_generic_list_node_t* prev; -}; -typedef struct cc_generic_list_node_t cc_generic_list_node_t; - -struct cc_generic_list_head_t { - enum cc_list_type type; - cc_generic_list_node_t* head; - cc_generic_list_node_t* tail; -}; -typedef struct cc_generic_list_head_t cc_generic_list_head_t; - - -struct cc_generic_iterate_t { - cc_generic_list_node_t* next; -}; -typedef struct cc_generic_iterate_t cc_generic_iterate_t; - -typedef cc_generic_list_head_t cc_context_list_head_t; -typedef cc_generic_list_node_t cc_context_list_node_t; - -typedef cc_generic_list_head_t cc_ccache_list_head_t; -typedef cc_generic_list_node_t cc_ccache_list_node_t; - -typedef cc_generic_list_head_t cc_credentials_list_head_t; -typedef cc_generic_list_node_t cc_credentials_list_node_t; - struct cc_context_iterate_t { cc_context_list_node_t* next; }; @@ -104,7 +75,7 @@ struct cc_credentials_iterate_t { }; typedef struct cc_credentials_iterate_t cc_credentials_iterate_t; -struct cc_lock_t { +struct cc_lock { cc_uint32 read_locks; /* count of read locks (>= 0) */ cc_uint32 write_locks; /* count of write locks (0 or 1) */ void * platform_data; /* platform specific implementation data */ @@ -118,7 +89,7 @@ struct cc_server_context_t { cc_int32 api_version; /*Version our client passed in on init (ccapi_version_X) */ cc_auth_info_t* auth_info; /*auth info passed in from RPC*/ cc_session_info_t* session_info; /*session info passed in from RPC*/ - cc_time_t changed; /*date of last change to this context*/ + cc_time64 changed; /*date of last change to this context*/ cc_int32 error; /*last error code*/ cc_lock_t locks; /*are we locked?*/ }; @@ -129,10 +100,10 @@ struct cc_server_ccache_t { char* principal_v4; /*v4 principal associated with this cache*/ char* principal_v5; /*v5 principal associated with this cache*/ cc_uint32 versions; /*versions of creds supported (from cc_credentials enum in CredentialsCache.h)*/ - cc_time_t changed; /*date of last change to ccache*/ + cc_time64 changed; /*date of last change to ccache*/ cc_int32 kdc_set; /*is the KDC time offset initialized?*/ - cc_time_t kdc_offset; /*offset of our clock relative kdc*/ - cc_time_t last_default; /*the last date when we were default*/ + cc_time64 kdc_offset; /*offset of our clock relative kdc*/ + cc_time64 last_default; /*the last date when we were default*/ cc_int32 is_default; /*is this the default cred on this ccache?*/ cc_generic_list_head_t* active_iterators; /*iterators which clients have opened on this cache*/ cc_credentials_list_head_t* creds; /*list of creds stored in this ccache*/ @@ -150,82 +121,69 @@ typedef struct cc_server_credentials_t cc_server_credentials_t; /*Note: cci means Credential Cache Internal, to differentiate from exported API macros*/ -cc_int32 cci_generic_iterate_has_next(cc_generic_iterate_t *iterate); -cc_int32 cci_generic_iterate_next(cc_generic_iterate_t *iterate, cc_generic_list_node_t**); - -cc_int32 cci_generic_list_new(cc_generic_list_head_t **); -cc_int32 cci_generic_list_append(cc_generic_list_head_t *head, void *data, cc_uint32 len, cc_generic_list_node_t**); -cc_int32 cci_generic_list_prepend(cc_generic_list_head_t *head, void *data, cc_uint32 len, cc_generic_list_node_t**); -cc_int32 cci_generic_list_remove_element(cc_generic_list_head_t* head, cc_generic_list_node_t* rem); -cc_int32 cci_generic_free_element(cc_generic_list_node_t* node); -cc_int32 cci_generic_list_destroy(cc_generic_list_head_t* head); -cc_int32 cci_generic_list_copy(cc_generic_list_head_t* head, cc_generic_list_head_t**); -cc_int32 cci_generic_list_iterator(cc_generic_list_head_t *head, cc_generic_iterate_t**); -cc_int32 cci_generic_free_iterator(cc_generic_iterate_t* iterator); - -cc_int32 cci_context_iterate_has_next(struct cc_context_iterate_t *iterate); -cc_int32 cci_context_iterate_next(struct cc_context_iterate_t *iterate, cc_context_list_node_t**); - -cc_int32 cci_ccache_iterate_has_next(struct cc_ccache_iterate_t *iterate); -cc_int32 cci_ccache_iterate_next(struct cc_ccache_iterate_t *iterate, cc_ccache_list_node_t**); - -cc_int32 cci_credentials_iterate_has_next(cc_credentials_iterate_t *iterate); -cc_int32 cci_credentials_iterate_next(cc_credentials_iterate_t *iterate, cc_credentials_list_node_t **); - -cc_int32 cci_context_list_new(cc_context_list_head_t**); -cc_int32 cci_context_list_append(cc_context_list_head_t *head, cc_server_context_t *data, cc_context_list_node_t**); -cc_int32 cci_context_list_prepend(cc_context_list_head_t *head, cc_server_context_t *data, cc_context_list_node_t**); -cc_int32 cci_context_list_remove_element(cc_context_list_head_t* head, cc_context_list_node_t* rem); -cc_int32 cci_context_list_iterator(cc_context_list_head_t *head, struct cc_context_iterate_t**); -cc_int32 cci_context_free_iterator(struct cc_context_iterate_t *iterator); -cc_int32 cci_context_list_destroy(cc_context_list_head_t* head) ; -cc_int32 cci_context_list_copy(cc_context_list_head_t* head, cc_context_list_head_t**); - -cc_int32 cci_ccache_list_new(cc_ccache_list_head_t**); -cc_int32 cci_ccache_list_append(cc_ccache_list_head_t *head, cc_server_ccache_t *data, cc_ccache_list_node_t**); -cc_int32 cci_ccache_list_prepend(cc_ccache_list_head_t *head, cc_server_ccache_t *data, cc_ccache_list_node_t**); -cc_int32 cci_ccache_list_remove_element(cc_ccache_list_head_t* head, cc_ccache_list_node_t* rem); -cc_int32 cci_ccache_list_iterator(cc_ccache_list_head_t *head, struct cc_ccache_iterate_t**); -cc_int32 cci_ccache_free_iterator(struct cc_ccache_iterate_t *iterator); -cc_int32 cci_ccache_list_destroy(cc_ccache_list_head_t* head) ; -cc_int32 cci_ccache_list_copy(cc_ccache_list_head_t* head, cc_ccache_list_head_t**); - - -cc_int32 cci_credentials_list_new(cc_credentials_list_head_t**); -cc_int32 cci_credentials_list_append(cc_credentials_list_head_t *head, cc_server_credentials_t *data, cc_credentials_list_node_t**); -cc_int32 cci_credentials_list_prepend(cc_credentials_list_head_t *head, cc_server_credentials_t *data, cc_credentials_list_node_t**); -cc_int32 cci_credentials_list_remove_element(cc_credentials_list_head_t* head, cc_credentials_list_node_t* rem); -cc_int32 cci_credentials_list_iterator(cc_credentials_list_head_t *head, cc_credentials_iterate_t**); -cc_int32 cci_credentials_free_iterator(cc_credentials_iterate_t* iterator); -cc_int32 cci_credentials_list_destroy(cc_credentials_list_head_t* head) ; -cc_int32 cci_credentials_list_copy(cc_credentials_list_head_t* head, cc_credentials_list_head_t**) ; - - -cc_int32 cci_context_new(int api_version, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_server_context_t** ) ; -cc_int32 cci_context_get_default_ccache_name(cc_server_context_t* ctx, char **); -cc_int32 cci_context_find_ccache(cc_server_context_t* ctx, char *name, cc_server_ccache_t**); -cc_int32 cci_context_open_ccache(cc_server_context_t* ctx, char *name, cc_server_ccache_t** ); -cc_int32 cci_context_create_ccache(cc_server_context_t* ctx, char *name, int creds_version, char *principal, cc_server_ccache_t**); -cc_int32 cci_context_create_default_ccache(cc_server_context_t* ctx, int creds_version, char *principal, cc_server_ccache_t**); -cc_int32 cci_context_ccache_iterator(cc_server_context_t* ctx, cc_ccache_iterate_t**); -cc_int32 cci_context_compare(cc_server_context_t* a, cc_server_context_t* b); -cc_int32 cci_context_destroy(cc_server_context_t* ctx); -cc_int32 cci_context_rem_ccache(cc_server_context_t* ctx, cc_server_ccache_t* ccache); - -cc_int32 cci_ccache_new(char *name, char *principal, int cred_vers, cc_server_ccache_t**); -cc_int32 cci_ccache_check_version(const cc_server_ccache_t *ccache, const cc_credentials_union* creds, cc_uint32* compat); -cc_int32 cci_ccache_check_principal(const cc_server_ccache_t *ccache, const cc_credentials_union* creds, cc_uint32* compat); -cc_int32 cci_ccache_store_creds(cc_server_ccache_t *ccache, const cc_credentials_union* credentials); -cc_int32 cci_ccache_rem_creds(cc_server_ccache_t *ccache, const cc_credentials_union* credentials); -cc_int32 cci_ccache_move(cc_server_ccache_t *source, cc_server_ccache_t* destination); -cc_int32 cci_ccache_get_kdc_time_offset(cc_server_ccache_t* ccache, cc_time_t* offset); -cc_int32 cci_ccache_set_kdc_time_offset(cc_server_ccache_t* ccache, cc_time_t offset); -cc_int32 cci_ccache_clear_kdc_time_offset(cc_server_ccache_t* ccache); -cc_int32 cci_ccache_new_iterator(cc_server_ccache_t* ccache, cc_credentials_iterate_t** iterator); -cc_int32 cci_ccache_get_principal(cc_server_ccache_t* ccache, cc_int32 version, char ** principal); -cc_int32 cci_ccache_set_principal(cc_server_ccache_t* ccache, cc_int32 version, char * principal); -cc_int32 cci_ccache_free_principal(char * principal); -cc_int32 cci_ccache_destroy(cc_server_ccache_t* ccache); -void cci_ccache_changed(cc_server_ccache_t* ccache); -cc_int32 cci_ccache_compare(cc_server_ccache_t* ccache1, cc_server_ccache_t* ccache2, cc_uint32 *result); +cc_int32 ccs_context_iterate_has_next(struct cc_context_iterate_t *iterate); +cc_int32 ccs_context_iterate_next(struct cc_context_iterate_t *iterate, cc_context_list_node_t**); + +cc_int32 ccs_ccache_iterate_has_next(struct cc_ccache_iterate_t *iterate); +cc_int32 ccs_ccache_iterate_next(struct cc_ccache_iterate_t *iterate, cc_ccache_list_node_t**); + +cc_int32 ccs_credentials_iterate_has_next(cc_credentials_iterate_t *iterate); +cc_int32 ccs_credentials_iterate_next(cc_credentials_iterate_t *iterate, cc_credentials_list_node_t **); + +cc_int32 ccs_context_list_new(cc_context_list_head_t**); +cc_int32 ccs_context_list_append(cc_context_list_head_t *head, cc_server_context_t *data, cc_context_list_node_t**); +cc_int32 ccs_context_list_prepend(cc_context_list_head_t *head, cc_server_context_t *data, cc_context_list_node_t**); +cc_int32 ccs_context_list_remove_element(cc_context_list_head_t* head, cc_context_list_node_t* rem); +cc_int32 ccs_context_list_iterator(cc_context_list_head_t *head, struct cc_context_iterate_t**); +cc_int32 ccs_context_free_iterator(struct cc_context_iterate_t *iterator); +cc_int32 ccs_context_list_destroy(cc_context_list_head_t* head) ; +cc_int32 ccs_context_list_copy(cc_context_list_head_t* head, cc_context_list_head_t**); + +cc_int32 ccs_ccache_list_new(cc_ccache_list_head_t**); +cc_int32 ccs_ccache_list_append(cc_ccache_list_head_t *head, cc_server_ccache_t *data, cc_ccache_list_node_t**); +cc_int32 ccs_ccache_list_prepend(cc_ccache_list_head_t *head, cc_server_ccache_t *data, cc_ccache_list_node_t**); +cc_int32 ccs_ccache_list_remove_element(cc_ccache_list_head_t* head, cc_ccache_list_node_t* rem); +cc_int32 ccs_ccache_list_iterator(cc_ccache_list_head_t *head, struct cc_ccache_iterate_t**); +cc_int32 ccs_ccache_free_iterator(struct cc_ccache_iterate_t *iterator); +cc_int32 ccs_ccache_list_destroy(cc_ccache_list_head_t* head) ; +cc_int32 ccs_ccache_list_copy(cc_ccache_list_head_t* head, cc_ccache_list_head_t**); + + +cc_int32 ccs_credentials_list_new(cc_credentials_list_head_t**); +cc_int32 ccs_credentials_list_append(cc_credentials_list_head_t *head, cc_server_credentials_t *data, cc_credentials_list_node_t**); +cc_int32 ccs_credentials_list_prepend(cc_credentials_list_head_t *head, cc_server_credentials_t *data, cc_credentials_list_node_t**); +cc_int32 ccs_credentials_list_remove_element(cc_credentials_list_head_t* head, cc_credentials_list_node_t* rem); +cc_int32 ccs_credentials_list_iterator(cc_credentials_list_head_t *head, cc_credentials_iterate_t**); +cc_int32 ccs_credentials_free_iterator(cc_credentials_iterate_t* iterator); +cc_int32 ccs_credentials_list_destroy(cc_credentials_list_head_t* head) ; +cc_int32 ccs_credentials_list_copy(cc_credentials_list_head_t* head, cc_credentials_list_head_t**) ; + + +cc_int32 ccs_context_new(int api_version, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_server_context_t** ) ; +cc_int32 ccs_context_get_default_ccache_name(cc_server_context_t* ctx, char **); +cc_int32 ccs_context_find_ccache(cc_server_context_t* ctx, char *name, cc_server_ccache_t**); +cc_int32 ccs_context_open_ccache(cc_server_context_t* ctx, char *name, cc_server_ccache_t** ); +cc_int32 ccs_context_create_ccache(cc_server_context_t* ctx, char *name, int creds_version, char *principal, cc_server_ccache_t**); +cc_int32 ccs_context_create_default_ccache(cc_server_context_t* ctx, int creds_version, char *principal, cc_server_ccache_t**); +cc_int32 ccs_context_ccache_iterator(cc_server_context_t* ctx, cc_ccache_iterate_t**); +cc_int32 ccs_context_compare(cc_server_context_t* a, cc_server_context_t* b); +cc_int32 ccs_context_destroy(cc_server_context_t* ctx); +cc_int32 ccs_context_rem_ccache(cc_server_context_t* ctx, cc_server_ccache_t* ccache); + +cc_int32 ccs_ccache_new(char *name, char *principal, int cred_vers, cc_server_ccache_t**); +cc_int32 ccs_ccache_check_version(const cc_server_ccache_t *ccache, const cc_credentials_union* creds, cc_uint32* compat); +cc_int32 ccs_ccache_check_principal(const cc_server_ccache_t *ccache, const cc_credentials_union* creds, cc_uint32* compat); +cc_int32 ccs_ccache_store_creds(cc_server_ccache_t *ccache, const cc_credentials_union* credentials); +cc_int32 ccs_ccache_rem_creds(cc_server_ccache_t *ccache, const cc_credentials_union* credentials); +cc_int32 ccs_ccache_move(cc_server_ccache_t *source, cc_server_ccache_t* destination); +cc_int32 ccs_ccache_get_kdc_time_offset(cc_server_ccache_t* ccache, cc_time64* offset); +cc_int32 ccs_ccache_set_kdc_time_offset(cc_server_ccache_t* ccache, cc_time64 offset); +cc_int32 ccs_ccache_clear_kdc_time_offset(cc_server_ccache_t* ccache); +cc_int32 ccs_ccache_new_iterator(cc_server_ccache_t* ccache, cc_credentials_iterate_t** iterator); +cc_int32 ccs_ccache_get_principal(cc_server_ccache_t* ccache, cc_int32 version, char ** principal); +cc_int32 ccs_ccache_set_principal(cc_server_ccache_t* ccache, cc_int32 version, char * principal); +cc_int32 ccs_ccache_free_principal(char * principal); +cc_int32 ccs_ccache_destroy(cc_server_ccache_t* ccache); +void ccs_ccache_changed(cc_server_ccache_t* ccache); +cc_int32 ccs_ccache_compare(cc_server_ccache_t* ccache1, cc_server_ccache_t* ccache2, cc_uint32 *result); #endif /*__CCDATASTOREH__*/ diff --git a/src/lib/ccapi/server/main.c b/src/lib/ccapi/server/main.c new file mode 100644 index 000000000..cf69af312 --- /dev/null +++ b/src/lib/ccapi/server/main.c @@ -0,0 +1,12 @@ +#include +#include + +int main( int argc, char *argv[] ) +{ + /* we need a set of functions we want to support. + * so we can provide an abstract platform independent + * interface. + */ + + return 0; +} diff --git a/src/lib/ccapi/server/serv_ops.c b/src/lib/ccapi/server/serv_ops.c index 30a108a34..360536a92 100644 --- a/src/lib/ccapi/server/serv_ops.c +++ b/src/lib/ccapi/server/serv_ops.c @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -62,33 +62,36 @@ extern int cc_myversion; extern char cc_vendor[]; cc_int32 -cci_serv_initialize(void) +ccs_serv_initialize(void) { cc_int32 code; - code = cci_context_list_new(&AllContexts); + code = ccs_context_list_new(&AllContexts); if ( code != ccNoError ) return code; TypeToOpMapping = (type_to_op_mapping_t*)malloc(sizeof(type_to_op_mapping_t)); if (TypeToOpMapping == NULL) { - cci_context_list_destroy(AllContexts); + ccs_context_list_destroy(AllContexts); return ccErrNoMem; } +#if 0 + TypeToOpMapping->operations[ccmsg_ACK] = ccop_ACK; + TypeToOpMapping->operations[ccmsg_NACK] = ccop_NACK; +#endif TypeToOpMapping->operations[ccmsg_INIT] = ccop_INIT; TypeToOpMapping->operations[ccmsg_CTX_RELEASE] = ccop_CTX_RELEASE; TypeToOpMapping->operations[ccmsg_CTX_GET_CHANGE_TIME] = ccop_CTX_GET_CHANGE_TIME; TypeToOpMapping->operations[ccmsg_CTX_GET_DEFAULT_CCACHE_NAME] = ccop_CTX_GET_DEFAULT_CCACHE_NAME; - TypeToOpMapping->operations[ccmsg_CTX_COMPARE] = ccop_CTX_COMPARE; + TypeToOpMapping->operations[ccmsg_CTX_CCACHE_OPEN] = ccop_CTX_CCACHE_OPEN; + TypeToOpMapping->operations[ccmsg_CTX_CCACHE_OPEN_DEFAULT] = ccop_CTX_CCACHE_OPEN_DEFAULT; + TypeToOpMapping->operations[ccmsg_CTX_CCACHE_CREATE] = ccop_CTX_CCACHE_CREATE; + TypeToOpMapping->operations[ccmsg_CTX_CCACHE_CREATE_DEFAULT] = ccop_CTX_CCACHE_CREATE_DEFAULT; + TypeToOpMapping->operations[ccmsg_CTX_CCACHE_CREATE_UNIQUE] = ccop_CTX_CCACHE_CREATE_UNIQUE; TypeToOpMapping->operations[ccmsg_CTX_NEW_CCACHE_ITERATOR] = ccop_CTX_NEW_CCACHE_ITERATOR; TypeToOpMapping->operations[ccmsg_CTX_LOCK] = ccop_CTX_LOCK; TypeToOpMapping->operations[ccmsg_CTX_UNLOCK] = ccop_CTX_UNLOCK; - TypeToOpMapping->operations[ccmsg_CTX_CLONE] = ccop_CTX_CLONE; - TypeToOpMapping->operations[ccmsg_CCACHE_OPEN] = ccop_CCACHE_OPEN; - TypeToOpMapping->operations[ccmsg_CCACHE_OPEN_DEFAULT] = ccop_CCACHE_OPEN_DEFAULT; - TypeToOpMapping->operations[ccmsg_CCACHE_CREATE] = ccop_CCACHE_CREATE; - TypeToOpMapping->operations[ccmsg_CCACHE_CREATE_DEFAULT] = ccop_CCACHE_CREATE_DEFAULT; - TypeToOpMapping->operations[ccmsg_CCACHE_CREATE_UNIQUE] = ccop_CCACHE_CREATE_UNIQUE; + TypeToOpMapping->operations[ccmsg_CTX_COMPARE] = ccop_CTX_COMPARE; TypeToOpMapping->operations[ccmsg_CCACHE_RELEASE] = ccop_CCACHE_RELEASE; TypeToOpMapping->operations[ccmsg_CCACHE_DESTROY] = ccop_CCACHE_DESTROY; TypeToOpMapping->operations[ccmsg_CCACHE_SET_DEFAULT] = ccop_CCACHE_SET_DEFAULT; @@ -96,9 +99,12 @@ cci_serv_initialize(void) TypeToOpMapping->operations[ccmsg_CCACHE_GET_NAME] = ccop_CCACHE_GET_NAME; TypeToOpMapping->operations[ccmsg_CCACHE_GET_PRINCIPAL] = ccop_CCACHE_GET_PRINCIPAL; TypeToOpMapping->operations[ccmsg_CCACHE_SET_PRINCIPAL] = ccop_CCACHE_SET_PRINCIPAL; - TypeToOpMapping->operations[ccmsg_CCACHE_CREDS_ITERATOR] = ccop_CCACHE_CREDS_ITERATOR; + TypeToOpMapping->operations[ccmsg_CCACHE_NEW_CREDS_ITERATOR] = ccop_CCACHE_NEW_CREDS_ITERATOR; TypeToOpMapping->operations[ccmsg_CCACHE_STORE_CREDS] = ccop_CCACHE_STORE_CREDS; TypeToOpMapping->operations[ccmsg_CCACHE_REM_CREDS] = ccop_CCACHE_REM_CREDS; + TypeToOpMapping->operations[ccmsg_CCACHE_MOVE] = ccop_CCACHE_MOVE; + TypeToOpMapping->operations[ccmsg_CCACHE_LOCK] = ccop_CCACHE_LOCK; + TypeToOpMapping->operations[ccmsg_CCACHE_UNLOCK] = ccop_CCACHE_UNLOCK; TypeToOpMapping->operations[ccmsg_CCACHE_GET_LAST_DEFAULT_TIME] = ccop_CCACHE_GET_LAST_DEFAULT_TIME; TypeToOpMapping->operations[ccmsg_CCACHE_GET_CHANGE_TIME] = ccop_CCACHE_GET_CHANGE_TIME; TypeToOpMapping->operations[ccmsg_CCACHE_COMPARE] = ccop_CCACHE_COMPARE; @@ -107,15 +113,16 @@ cci_serv_initialize(void) TypeToOpMapping->operations[ccmsg_CCACHE_CLEAR_KDC_TIME_OFFSET] = ccop_CCACHE_CLEAR_KDC_TIME_OFFSET; TypeToOpMapping->operations[ccmsg_CCACHE_ITERATOR_RELEASE] = ccop_CCACHE_ITERATOR_RELEASE; TypeToOpMapping->operations[ccmsg_CCACHE_ITERATOR_NEXT] = ccop_CCACHE_ITERATOR_NEXT; + TypeToOpMapping->operations[ccmsg_CCACHE_ITERATOR_CLONE] = ccop_CCACHE_ITERATOR_CLONE; TypeToOpMapping->operations[ccmsg_CREDS_ITERATOR_RELEASE] = ccop_CREDS_ITERATOR_RELEASE; TypeToOpMapping->operations[ccmsg_CREDS_ITERATOR_NEXT] = ccop_CREDS_ITERATOR_NEXT; - TypeToOpMapping->operations[ccmsg_CREDS_RELEASE] = ccop_CREDS_RELEASE; + TypeToOpMapping->operations[ccmsg_CREDS_ITERATOR_CLONE] = ccop_CREDS_ITERATOR_CLONE; return ccNoError; }; cc_int32 -cci_serv_process_msg(cc_msg_t * msg, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t** resp_msg) +ccs_serv_process_msg(cc_msg_t * msg, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t** resp_msg) { cc_server_context_t* ctx; ccmsg_ctx_only_t* header = (ccmsg_ctx_only_t *)msg->header; @@ -125,7 +132,7 @@ cci_serv_process_msg(cc_msg_t * msg, cc_auth_info_t* auth_info, cc_session_info_ return ccErrBadParam; if (AllContexts == NULL) { - code = cci_serv_initialize(); + code = ccs_serv_initialize(); if ( code != ccNoError ) return code; } @@ -137,9 +144,9 @@ cci_serv_process_msg(cc_msg_t * msg, cc_auth_info_t* auth_info, cc_session_info_ return ccErrBadParam; } - code = cci_serv_find_ctx_by_handle(header->ctx, auth_info, session_info, &ctx); + code = ccs_serv_find_ctx_by_handle(header->ctx, auth_info, session_info, &ctx); if (code != ccNoError) { - cci_serv_make_nack(ccErrContextNotFound, auth_info, session_info, resp_msg); + ccs_serv_make_nack(ccErrContextNotFound, auth_info, session_info, resp_msg); return code; } return TypeToOpMapping->operations[msg->type] (ctx, auth_info, session_info, msg, resp_msg); @@ -148,7 +155,7 @@ cci_serv_process_msg(cc_msg_t * msg, cc_auth_info_t* auth_info, cc_session_info_ /*deprecated*/ cc_int32 -cci_serv_find_ctx(cc_auth_info_t* auth_info, cc_session_info_t* session_info, +ccs_serv_find_ctx(cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_server_context_t** ctxpp) { cc_context_iterate_t* ctx_iterator; @@ -157,35 +164,35 @@ cci_serv_find_ctx(cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_int32 code; cc_uint32 authorized; - code = cci_context_list_iterator(AllContexts, &ctx_iterator); + code = ccs_context_list_iterator(AllContexts, &ctx_iterator); if (code != ccNoError) return code; - while (cci_context_iterate_has_next(ctx_iterator)) { - code = cci_context_iterate_next(ctx_iterator, &ctx_node); + while (ccs_context_iterate_has_next(ctx_iterator)) { + code = ccs_context_iterate_next(ctx_iterator, &ctx_node); if (code != ccNoError) { - cci_context_free_iterator(ctx_iterator); + ccs_context_free_iterator(ctx_iterator); return code; } ctx = (cc_server_context_t *)ctx_node->data; code = cci_rpc_is_authorized(auth_info, session_info, ctx->auth_info, ctx->session_info, &authorized); if (code != ccNoError) { - cci_context_free_iterator(ctx_iterator); + ccs_context_free_iterator(ctx_iterator); return code; } if (authorized) { - cci_context_free_iterator(ctx_iterator); + ccs_context_free_iterator(ctx_iterator); *ctxpp = ctx; return ccNoError; } } - cci_context_free_iterator(ctx_iterator); + ccs_context_free_iterator(ctx_iterator); return ccIteratorEnd; } cc_int32 -cci_serv_find_ctx_by_handle(cc_handle ctx_num, cc_auth_info_t* auth, cc_session_info_t* session, cc_server_context_t** ctxpp) +ccs_serv_find_ctx_by_handle(cc_handle ctx_num, cc_auth_info_t* auth, cc_session_info_t* session, cc_server_context_t** ctxpp) { cc_server_context_t* input_ctx = (cc_server_context_t*)ctx_num; cc_context_iterate_t* ctx_iterator; @@ -194,36 +201,36 @@ cci_serv_find_ctx_by_handle(cc_handle ctx_num, cc_auth_info_t* auth, cc_session_ cc_uint32 authorized; cc_int32 code; - code = cci_context_list_iterator(AllContexts, &ctx_iterator); + code = ccs_context_list_iterator(AllContexts, &ctx_iterator); if (code != ccNoError) return code; - while (cci_context_iterate_has_next(ctx_iterator)) { - code = cci_context_iterate_next(ctx_iterator, &ctx_node); + while (ccs_context_iterate_has_next(ctx_iterator)) { + code = ccs_context_iterate_next(ctx_iterator, &ctx_node); ctx = (cc_server_context_t *)ctx_node->data; if (code != ccNoError) { - cci_context_free_iterator(ctx_iterator); + ccs_context_free_iterator(ctx_iterator); return code; } code = cci_rpc_is_authorized(auth, session, ctx->auth_info, ctx->session_info, &authorized); if (code != ccNoError) { - cci_context_free_iterator(ctx_iterator); + ccs_context_free_iterator(ctx_iterator); return code; } if (ctx == input_ctx && authorized) { - cci_context_free_iterator(ctx_iterator); + ccs_context_free_iterator(ctx_iterator); *ctxpp = ctx; return ccNoError; } } - cci_context_free_iterator(ctx_iterator); + ccs_context_free_iterator(ctx_iterator); return ccIteratorEnd; } cc_int32 -cci_serv_find_ccache_by_handle(cc_server_context_t* ctx, cc_handle ccache, cc_server_ccache_t** ccachepp ) +ccs_serv_find_ccache_by_handle(cc_server_context_t* ctx, cc_handle ccache, cc_server_ccache_t** ccachepp ) { cc_ccache_iterate_t* ccache_iterator; cc_ccache_list_node_t* ccache_node; @@ -231,31 +238,31 @@ cci_serv_find_ccache_by_handle(cc_server_context_t* ctx, cc_handle ccache, cc_se cc_server_ccache_t* target_ccache = (cc_server_ccache_t*)ccache; cc_int32 code; - code = cci_ccache_list_iterator(ctx->ccaches, &ccache_iterator); + code = ccs_ccache_list_iterator(ctx->ccaches, &ccache_iterator); if (code != ccNoError) return code; - while (cci_ccache_iterate_has_next(ccache_iterator)) { - code = cci_ccache_iterate_next(ccache_iterator, &ccache_node); + while (ccs_ccache_iterate_has_next(ccache_iterator)) { + code = ccs_ccache_iterate_next(ccache_iterator, &ccache_node); if (code != ccNoError) { - cci_ccache_free_iterator(ccache_iterator); + ccs_ccache_free_iterator(ccache_iterator); return code; } stored_ccache = (cc_server_ccache_t *)ccache_node->data; if (stored_ccache == target_ccache) { - cci_ccache_free_iterator(ccache_iterator); + ccs_ccache_free_iterator(ccache_iterator); *ccachepp = stored_ccache; return ccNoError; } } - cci_ccache_free_iterator(ccache_iterator); + ccs_ccache_free_iterator(ccache_iterator); return ccIteratorEnd; } cc_int32 -cci_serv_find_ccache_iterator_by_handle(cc_server_context_t* ctx, cc_handle iterator, cc_generic_list_node_t** nodepp ) +ccs_serv_find_ccache_iterator_by_handle(cc_server_context_t* ctx, cc_handle iterator, cc_generic_list_node_t** nodepp ) { cc_generic_iterate_t* gen_iterator; cc_generic_list_node_t* gen_node; @@ -286,7 +293,7 @@ cci_serv_find_ccache_iterator_by_handle(cc_server_context_t* ctx, cc_handle iter } cc_int32 -cci_serv_find_creds_iterator_by_handle(cc_server_ccache_t* ccache, cc_handle iterator, cc_generic_list_node_t** nodepp) +ccs_serv_find_creds_iterator_by_handle(cc_server_ccache_t* ccache, cc_handle iterator, cc_generic_list_node_t** nodepp) { cc_generic_iterate_t* gen_iterator; cc_generic_list_node_t* gen_node; @@ -317,7 +324,7 @@ cci_serv_find_creds_iterator_by_handle(cc_server_ccache_t* ccache, cc_handle ite } cc_int32 -cci_serv_make_nack(cc_int32 err_code, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t** resp_msg) +ccs_serv_make_nack(cc_int32 err_code, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t** resp_msg) { ccmsg_nack_t* nack_header; cc_int32 code; @@ -345,7 +352,7 @@ cci_serv_make_nack(cc_int32 err_code, cc_auth_info_t* auth_info, cc_session_info } cc_int32 -cci_serv_make_ack(void * header, cc_int32 header_len, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t** resp_msg) +ccs_serv_make_ack(void * header, cc_int32 header_len, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t** resp_msg) { cc_int32 code; @@ -383,46 +390,46 @@ ccop_INIT( cc_server_context_t* ctx, /* not used */ return ccErrBadParam; } - code = cci_context_new(header->in_version, auth_info, session_info, &new_ctx); + code = ccs_context_new(header->in_version, auth_info, session_info, &new_ctx); if (code != ccNoError) { return code; } - code = cci_context_list_append(AllContexts, ctx, &ctx_node); + code = ccs_context_list_append(AllContexts, ctx, &ctx_node); if (code != ccNoError) { - cci_context_destroy(new_ctx); + ccs_context_destroy(new_ctx); return code; } resp_header = (ccmsg_init_resp_t*)malloc(sizeof(ccmsg_init_resp_t)); if (resp_header == NULL) { - cci_context_destroy(new_ctx); + ccs_context_destroy(new_ctx); return ccErrNoMem; } code = cci_msg_new(ccmsg_ACK, resp_msg); if (code != ccNoError) { free(resp_header); - cci_context_destroy(new_ctx); + ccs_context_destroy(new_ctx); return code; } code = cci_msg_add_data_blob(*resp_msg, cc_vendor, strlen(cc_vendor) + 1, &blob_pos); if (code != ccNoError) { free(resp_header); - cci_context_destroy(new_ctx); + ccs_context_destroy(new_ctx); cci_msg_destroy(*resp_msg); *resp_msg = 0; return code; } - resp_header->out_ctx = new_ctx; + resp_header->out_ctx = (cc_handle) new_ctx; resp_header->out_version = cc_myversion; resp_header->vendor_offset = blob_pos; resp_header->vendor_length = strlen(cc_vendor) + 1; code = cci_msg_add_header(*resp_msg, resp_header, sizeof(ccmsg_init_resp_t)); if (code != ccNoError) { free(resp_header); - cci_context_destroy(new_ctx); + ccs_context_destroy(new_ctx); cci_msg_destroy(*resp_msg); *resp_msg = 0; return code; @@ -446,8 +453,8 @@ ccop_CTX_RELEASE( cc_server_context_t* ctx, return ccErrBadParam; } - code = cci_context_destroy(header->ctx); - return cci_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); + code = ccs_context_destroy((cc_server_context_t *)header->ctx); + return ccs_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); } cc_int32 @@ -471,7 +478,7 @@ ccop_CTX_GET_CHANGE_TIME( cc_server_context_t* ctx, } resp_header->time = ctx->changed; - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ctx_get_change_time_resp_t), auth_info, session_info, resp_msg); + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ctx_get_change_time_resp_t), auth_info, session_info, resp_msg); } cc_int32 @@ -491,7 +498,7 @@ ccop_CTX_GET_DEFAULT_CCACHE_NAME( cc_server_context_t* ctx, return ccErrBadParam; } - code = cci_context_get_default_ccache_name(ctx, &name); + code = ccs_context_get_default_ccache_name(ctx, &name); if (code != ccNoError) return code; @@ -527,14 +534,14 @@ ccop_CTX_COMPARE(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ctx_compare_t)) return ccErrBadParam; - code = cci_serv_find_ctx_by_handle(header->ctx2, auth_info, session_info, &ctx2); + code = ccs_serv_find_ctx_by_handle(header->ctx2, auth_info, session_info, &ctx2); resp_header = (ccmsg_ctx_compare_resp_t*)malloc(sizeof(ccmsg_ctx_compare_resp_t)); if (resp_header == NULL) return ccErrNoMem; - resp_header->is_equal = cci_context_compare(ctx, ctx2); - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ctx_compare_resp_t), auth_info, session_info, resp_msg); + resp_header->is_equal = ccs_context_compare(ctx, ctx2); + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ctx_compare_resp_t), auth_info, session_info, resp_msg); } cc_int32 @@ -553,15 +560,15 @@ ccop_CTX_NEW_CCACHE_ITERATOR(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ctx_new_ccache_iterator_t)) return ccErrBadParam; - code = cci_context_ccache_iterator(ctx,&ccache_iterator); + code = ccs_context_ccache_iterator(ctx,&ccache_iterator); resp_header = (ccmsg_ctx_new_ccache_iterator_resp_t*)malloc(sizeof(ccmsg_ctx_new_ccache_iterator_resp_t)); if (resp_header == NULL) return ccErrNoMem; - resp_header->iterator = ccache_iterator; + resp_header->iterator = (cc_handle) ccache_iterator; - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ctx_new_ccache_iterator_resp_t), auth_info, session_info, resp_msg); + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ctx_new_ccache_iterator_resp_t), auth_info, session_info, resp_msg); } cc_int32 @@ -571,7 +578,7 @@ ccop_CTX_LOCK( cc_server_context_t* ctx, cc_msg_t *msg, cc_msg_t **resp_msg) { // TODO - return cci_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); } cc_int32 @@ -581,7 +588,7 @@ ccop_CTX_UNLOCK( cc_server_context_t* ctx, cc_msg_t *msg, cc_msg_t **resp_msg) { // TODO - return cci_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); } cc_int32 @@ -591,11 +598,11 @@ ccop_CTX_CLONE( cc_server_context_t* ctx, cc_msg_t *msg, cc_msg_t **resp_msg) { // TODO - return cci_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); } cc_int32 -ccop_CCACHE_OPEN(cc_server_context_t* ctx, +ccop_CTX_CCACHE_OPEN(cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg) @@ -612,24 +619,24 @@ ccop_CCACHE_OPEN(cc_server_context_t* ctx, return ccErrBadParam; code = cci_msg_retrieve_blob(msg, header->name_offset, header->name_len, &name); - code = cci_context_find_ccache(ctx, name, &ccache); + code = ccs_context_find_ccache(ctx, name, &ccache); free(name); if (ccache == NULL) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); resp_header = (ccmsg_ccache_open_resp_t*)malloc(sizeof(ccmsg_ccache_open_resp_t)); if (resp_header == NULL) return ccErrNoMem; - resp_header->ccache = ccache; - cci_serv_make_ack(resp_header, sizeof(ccmsg_ccache_open_resp_t), auth_info, session_info, resp_msg); + resp_header->ccache = (cc_handle) ccache; + ccs_serv_make_ack(resp_header, sizeof(ccmsg_ccache_open_resp_t), auth_info, session_info, resp_msg); return ccNoError; } cc_int32 -ccop_CCACHE_OPEN_DEFAULT(cc_server_context_t* ctx, +ccop_CTX_CCACHE_OPEN_DEFAULT(cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg) @@ -644,7 +651,7 @@ ccop_CCACHE_OPEN_DEFAULT(cc_server_context_t* ctx, return ccErrBadParam; if (ctx->ccaches->head->data == NULL) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); ccache = (cc_server_ccache_t*) ctx->ccaches->head->data; @@ -652,12 +659,12 @@ ccop_CCACHE_OPEN_DEFAULT(cc_server_context_t* ctx, if (resp_header == NULL) return ccErrNoMem; - resp_header->ccache = ccache; - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ccache_open_resp_t), auth_info, session_info, resp_msg); + resp_header->ccache = (cc_handle) ccache; + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ccache_open_resp_t), auth_info, session_info, resp_msg); } cc_int32 -ccop_CCACHE_CREATE(cc_server_context_t* ctx, +ccop_CTX_CCACHE_CREATE(cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg) @@ -684,7 +691,7 @@ ccop_CCACHE_CREATE(cc_server_context_t* ctx, return code; name[header->name_len] = '\0'; /*Ensure null termination*/ - code = cci_context_create_ccache(ctx, name, header->version, principal, &ccache); + code = ccs_context_create_ccache(ctx, name, header->version, principal, &ccache); if (code != ccNoError) return code; @@ -692,12 +699,12 @@ ccop_CCACHE_CREATE(cc_server_context_t* ctx, if (resp_header == NULL) return ccErrNoMem; - resp_header->ccache = ccache; - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ccache_create_resp_t), auth_info, session_info, resp_msg); + resp_header->ccache = (cc_handle) ccache; + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ccache_create_resp_t), auth_info, session_info, resp_msg); } cc_int32 -ccop_CCACHE_CREATE_DEFAULT( cc_server_context_t* ctx, +ccop_CTX_CCACHE_CREATE_DEFAULT( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg) @@ -719,11 +726,11 @@ ccop_CCACHE_CREATE_DEFAULT( cc_server_context_t* ctx, return code; principal[header->principal_len] = '\0'; /*Ensure null termination*/ - code = cci_context_get_default_ccache_name(ctx, &name); + code = ccs_context_get_default_ccache_name(ctx, &name); if (code != ccNoError) return code; - code = cci_context_create_ccache(ctx, name, header->version, principal, &ccache); + code = ccs_context_create_ccache(ctx, name, header->version, principal, &ccache); if (code != ccNoError) return code; @@ -731,12 +738,12 @@ ccop_CCACHE_CREATE_DEFAULT( cc_server_context_t* ctx, if (resp_header == NULL) return ccErrNoMem; - resp_header->ccache = ccache; - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ccache_create_resp_t), auth_info, session_info, resp_msg); + resp_header->ccache = (cc_handle) ccache; + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ccache_create_resp_t), auth_info, session_info, resp_msg); } cc_int32 -ccop_CCACHE_CREATE_UNIQUE( cc_server_context_t* ctx, +ccop_CTX_CCACHE_CREATE_UNIQUE( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg) @@ -758,9 +765,10 @@ ccop_CCACHE_CREATE_UNIQUE( cc_server_context_t* ctx, return code; principal[header->principal_len] = '\0'; /*Ensure null termination*/ - // TODO: Generate a unique ccache name + // TODO: Generate a unique ccache name + name = "unique"; - code = cci_context_create_ccache(ctx, name, header->version, principal, &ccache); + code = ccs_context_create_ccache(ctx, name, header->version, principal, &ccache); if (code != ccNoError) return code; @@ -768,8 +776,8 @@ ccop_CCACHE_CREATE_UNIQUE( cc_server_context_t* ctx, if (resp_header == NULL) return ccErrNoMem; - resp_header->ccache = ccache; - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ccache_create_resp_t), auth_info, session_info, resp_msg); + resp_header->ccache = (cc_handle) ccache; + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ccache_create_resp_t), auth_info, session_info, resp_msg); } cc_int32 @@ -797,13 +805,13 @@ ccop_CCACHE_DESTROY( cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_release_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); - cci_ccache_destroy(ccache); + ccs_ccache_destroy(ccache); - return cci_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); + return ccs_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); } cc_int32 @@ -823,32 +831,32 @@ ccop_CCACHE_SET_DEFAULT(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_set_default_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); if (ccache == (cc_server_ccache_t*)ctx->ccaches->head->data) /*already default*/ - return cci_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); + return ccs_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); old_default = (cc_server_ccache_t*)ctx->ccaches->head->data; old_default->last_default = time(NULL); - code = cci_ccache_list_iterator(ctx->ccaches, &ccache_iterator); + code = ccs_ccache_list_iterator(ctx->ccaches, &ccache_iterator); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); - while (cci_ccache_iterate_has_next(ccache_iterator)) { - code = cci_ccache_iterate_next(ccache_iterator,&ccache_node); + while (ccs_ccache_iterate_has_next(ccache_iterator)) { + code = ccs_ccache_iterate_next(ccache_iterator,&ccache_node); stored_ccache = (cc_server_ccache_t*)ccache_node->data; if (stored_ccache == ccache) { ccache_node->data = NULL; /*don't want list removal code free()ing ccache*/ - cci_ccache_list_remove_element(ctx->ccaches, ccache_node); - cci_ccache_list_prepend(ctx->ccaches, ccache, NULL); + ccs_ccache_list_remove_element(ctx->ccaches, ccache_node); + ccs_ccache_list_prepend(ctx->ccaches, ccache, NULL); break; } } - return cci_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); + return ccs_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); } cc_int32 @@ -867,16 +875,16 @@ ccop_CCACHE_GET_CREDS_VERSION(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_get_creds_version_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); resp_header = (ccmsg_ccache_get_creds_version_resp_t*)malloc(sizeof(ccmsg_ccache_get_creds_version_resp_t)); if (resp_header == NULL) return ccErrNoMem; resp_header->version = ccache->versions; - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ccache_get_creds_version_resp_t), auth_info, session_info, resp_msg); + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ccache_get_creds_version_resp_t), auth_info, session_info, resp_msg); } cc_int32 @@ -895,9 +903,9 @@ ccop_CCACHE_GET_NAME(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_get_name_resp_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (ccache == NULL) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); resp_header = (ccmsg_ccache_get_name_resp_t*)malloc(sizeof(ccmsg_ccache_get_name_resp_t)); if (resp_header == NULL) @@ -931,13 +939,13 @@ ccop_CCACHE_GET_PRINCIPAL(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_get_principal_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); - code = cci_ccache_get_principal(ccache, header->version, &principal); + code = ccs_ccache_get_principal(ccache, header->version, &principal); if (code != ccNoError) - return cci_serv_make_nack(code, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(code, auth_info, session_info, resp_msg); code = cci_msg_new(ccmsg_ACK, resp_msg); if (code != ccNoError) @@ -969,26 +977,26 @@ ccop_CCACHE_SET_PRINCIPAL(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_set_principal_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); code = cci_msg_retrieve_blob(msg, header->principal_offset, header->principal_len, &principal); if (code != ccNoError) - return cci_serv_make_nack(ccErrBadParam, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrBadParam, auth_info, session_info, resp_msg); - code = cci_ccache_set_principal(ccache, header->version, principal); + code = ccs_ccache_set_principal(ccache, header->version, principal); if (code != ccNoError) - return cci_serv_make_nack(code, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(code, auth_info, session_info, resp_msg); - return cci_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); + return ccs_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); } cc_int32 -ccop_CCACHE_CREDS_ITERATOR(cc_server_context_t* ctx, - cc_auth_info_t* auth_info, - cc_session_info_t* session_info, - cc_msg_t *msg, cc_msg_t **resp_msg) +ccop_CCACHE_NEW_CREDS_ITERATOR( cc_server_context_t* ctx, + cc_auth_info_t* auth_info, + cc_session_info_t* session_info, + cc_msg_t *msg, cc_msg_t **resp_msg) { cc_server_ccache_t* ccache; cc_credentials_iterate_t* creds_iterator; @@ -1001,11 +1009,11 @@ ccop_CCACHE_CREDS_ITERATOR(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_creds_iterator_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); - code = cci_ccache_new_iterator(ccache, &creds_iterator); + code = ccs_ccache_new_iterator(ccache, &creds_iterator); if (code != ccNoError) return code; @@ -1013,13 +1021,13 @@ ccop_CCACHE_CREDS_ITERATOR(cc_server_context_t* ctx, if (resp_header == NULL) return ccErrNoMem; - resp_header->iterator = creds_iterator; - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ccache_creds_iterator_resp_t), auth_info, session_info, resp_msg); + resp_header->iterator = (cc_handle) creds_iterator; + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ccache_creds_iterator_resp_t), auth_info, session_info, resp_msg); } static cc_int32 -cci_credentials_union_release( cc_credentials_union * creds ) +ccs_credentials_union_release( cc_credentials_union * creds ) { int i; @@ -1076,9 +1084,9 @@ ccop_CCACHE_STORE_CREDS(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_store_creds_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); // TODO: This code is too simplistic. cc_credential_unions are not flat // structures and must be flattened. That means that although we can @@ -1086,7 +1094,7 @@ ccop_CCACHE_STORE_CREDS(cc_server_context_t* ctx, // into the actual object. code = cci_msg_retrieve_blob(msg, header->creds_offset, header->creds_len, &flat_creds); if (code != ccNoError) - return cci_serv_make_nack(code, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(code, auth_info, session_info, resp_msg); creds = (cc_credentials_union *)malloc(sizeof(cc_credentials_union)); if ( creds == NULL ) @@ -1100,18 +1108,18 @@ ccop_CCACHE_STORE_CREDS(cc_server_context_t* ctx, code = cci_creds_v5_unmarshall(flat_creds, header->creds_len, creds); break; default: - return cci_serv_make_nack(ccErrBadCredentialsVersion, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrBadCredentialsVersion, auth_info, session_info, resp_msg); } if (code != ccNoError) - return cci_serv_make_nack(code, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(code, auth_info, session_info, resp_msg); - code = cci_ccache_store_creds(ccache, creds); - cci_credentials_union_release(creds); + code = ccs_ccache_store_creds(ccache, creds); + ccs_credentials_union_release(creds); if (code != ccNoError) { - return cci_serv_make_nack(code, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(code, auth_info, session_info, resp_msg); } - return cci_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); + return ccs_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); } cc_int32 @@ -1129,15 +1137,15 @@ ccop_CCACHE_REM_CREDS(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_rem_creds_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); - code = cci_ccache_rem_creds(ccache, header->creds); + code = ccs_ccache_rem_creds(ccache, (const cc_credentials_union *)header->creds); if (code != ccNoError) - return cci_serv_make_nack(code, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(code, auth_info, session_info, resp_msg); - return cci_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); + return ccs_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); } cc_int32 @@ -1147,7 +1155,7 @@ ccop_CCACHE_LOCK( cc_server_context_t* ctx, cc_msg_t *msg, cc_msg_t **resp_msg) { // TODO - return cci_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); } cc_int32 @@ -1157,7 +1165,7 @@ ccop_CCACHE_UNLOCK( cc_server_context_t* ctx, cc_msg_t *msg, cc_msg_t **resp_msg) { // TODO - return cci_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); } cc_int32 @@ -1167,7 +1175,7 @@ ccop_CCACHE_MOVE( cc_server_context_t* ctx, cc_msg_t *msg, cc_msg_t **resp_msg) { // TODO - return cci_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); } @@ -1187,16 +1195,16 @@ ccop_CCACHE_GET_LAST_DEFAULT_TIME(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_get_last_default_time_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); resp_header = (ccmsg_ccache_get_last_default_time_resp_t*)malloc(sizeof(ccmsg_ccache_get_last_default_time_resp_t)); if (resp_header == NULL) return ccErrNoMem; resp_header->last_default_time = ccache->last_default; - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ccache_get_last_default_time_resp_t), auth_info, session_info, resp_msg); + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ccache_get_last_default_time_resp_t), auth_info, session_info, resp_msg); } cc_int32 @@ -1221,7 +1229,7 @@ ccop_CCACHE_GET_CHANGE_TIME( cc_server_context_t* ctx, } resp_header->time = ccache->changed; - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ccache_get_change_time_resp_t), auth_info, session_info, resp_msg); + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ccache_get_change_time_resp_t), auth_info, session_info, resp_msg); } cc_int32 @@ -1240,20 +1248,20 @@ ccop_CCACHE_COMPARE(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_compare_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache1, &ccache1); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache1, &ccache1); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); - code = cci_serv_find_ccache_by_handle(ctx, header->ccache2, &ccache2); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache2, &ccache2); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); resp_header = (ccmsg_ccache_compare_resp_t*)malloc(sizeof(ccmsg_ccache_compare_resp_t)); if (resp_header == NULL) return ccErrNoMem; - cci_ccache_compare(ccache1, ccache2, &resp_header->is_equal); - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ccache_compare_resp_t), auth_info, session_info, resp_msg); + ccs_ccache_compare(ccache1, ccache2, &resp_header->is_equal); + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ccache_compare_resp_t), auth_info, session_info, resp_msg); } cc_int32 @@ -1265,7 +1273,7 @@ ccop_CCACHE_GET_KDC_TIME_OFFSET(cc_server_context_t* ctx, ccmsg_ccache_get_kdc_time_offset_t* header = (ccmsg_ccache_get_kdc_time_offset_t*)msg->header; ccmsg_ccache_get_kdc_time_offset_resp_t* resp_header; cc_server_ccache_t* ccache; - cc_time_t offset; + cc_time64 offset; cc_int32 code; *resp_msg = 0; @@ -1273,22 +1281,22 @@ ccop_CCACHE_GET_KDC_TIME_OFFSET(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_get_kdc_time_offset_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); // TODO How is the header->creds_version supposed to be used? - code = cci_ccache_get_kdc_time_offset(ccache, &offset); + code = ccs_ccache_get_kdc_time_offset(ccache, &offset); if (code != ccNoError) - return cci_serv_make_nack(code, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(code, auth_info, session_info, resp_msg); resp_header = (ccmsg_ccache_get_kdc_time_offset_resp_t*)malloc(sizeof(ccmsg_ccache_get_kdc_time_offset_resp_t)); if (resp_header == NULL) return ccErrNoMem; resp_header->offset = offset; - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ccache_get_kdc_time_offset_resp_t), auth_info, session_info, resp_msg); + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ccache_get_kdc_time_offset_resp_t), auth_info, session_info, resp_msg); } cc_int32 @@ -1306,14 +1314,14 @@ ccop_CCACHE_SET_KDC_TIME_OFFSET(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_set_kdc_time_offset_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); // TODO How is the header->creds_version supposed to be used? - cci_ccache_set_kdc_time_offset(ccache, header->offset); - return cci_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); + ccs_ccache_set_kdc_time_offset(ccache, header->offset); + return ccs_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); } cc_int32 @@ -1331,14 +1339,14 @@ ccop_CCACHE_CLEAR_KDC_TIME_OFFSET(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_clear_kdc_time_offset_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); // TODO How is the header->creds_version supposed to be used? - cci_ccache_clear_kdc_time_offset(ccache); - return cci_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); + ccs_ccache_clear_kdc_time_offset(ccache); + return ccs_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); } cc_int32 @@ -1356,17 +1364,27 @@ ccop_CCACHE_ITERATOR_RELEASE(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_iterator_release_t)) return ccErrBadParam; - code = cci_serv_find_ccache_iterator_by_handle(ctx, header->iterator, &gen_node); + code = ccs_serv_find_ccache_iterator_by_handle(ctx, header->iterator, &gen_node); if (code != ccNoError) - return cci_serv_make_nack(ccErrBadParam, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrBadParam, auth_info, session_info, resp_msg); code = cci_generic_list_remove_element(ctx->active_iterators, gen_node); if (code != ccNoError) - return cci_serv_make_nack(code, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(code, auth_info, session_info, resp_msg); - return cci_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); + return ccs_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); } +cc_int32 +ccop_CCACHE_ITERATOR_CLONE( cc_server_context_t* ctx, + cc_auth_info_t* auth_info, + cc_session_info_t* session_info, + cc_msg_t *msg, cc_msg_t **resp_msg) +{ + // TODO + return ccs_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); +} + cc_int32 ccop_CCACHE_ITERATOR_NEXT(cc_server_context_t* ctx, cc_auth_info_t* auth_info, @@ -1385,24 +1403,24 @@ ccop_CCACHE_ITERATOR_NEXT(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_ccache_iterator_next_t)) return ccErrBadParam; - code = cci_serv_find_ccache_iterator_by_handle(ctx, header->iterator, &gen_node); + code = ccs_serv_find_ccache_iterator_by_handle(ctx, header->iterator, &gen_node); if (code != ccNoError) - return cci_serv_make_nack(ccErrBadParam, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrBadParam, auth_info, session_info, resp_msg); ccache_iterator = (cc_ccache_iterate_t*)gen_node->data; - if (cci_ccache_iterate_has_next(ccache_iterator)) { + if (ccs_ccache_iterate_has_next(ccache_iterator)) { resp_header = (ccmsg_ccache_iterator_next_resp_t*)malloc(sizeof(ccmsg_ccache_iterator_next_resp_t)); if (resp_header == NULL) return ccErrNoMem; - code = cci_ccache_iterate_next(ccache_iterator, &ccache_node); + code = ccs_ccache_iterate_next(ccache_iterator, &ccache_node); if (code != ccNoError) - return cci_serv_make_nack(code, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(code, auth_info, session_info, resp_msg); - resp_header->ccache = ccache_node; - return cci_serv_make_ack(resp_header, sizeof(ccmsg_ccache_iterator_next_resp_t), auth_info, session_info, resp_msg); + resp_header->ccache = (cc_handle) ccache_node; + return ccs_serv_make_ack(resp_header, sizeof(ccmsg_ccache_iterator_next_resp_t), auth_info, session_info, resp_msg); } else { - return cci_serv_make_nack(ccIteratorEnd, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccIteratorEnd, auth_info, session_info, resp_msg); } } @@ -1422,21 +1440,32 @@ ccop_CREDS_ITERATOR_RELEASE(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_creds_iterator_release_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); - code = cci_serv_find_creds_iterator_by_handle(ccache, header->iterator, &gen_node); + code = ccs_serv_find_creds_iterator_by_handle(ccache, header->iterator, &gen_node); if (code != ccNoError) - return cci_serv_make_nack(ccErrBadParam, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrBadParam, auth_info, session_info, resp_msg); code = cci_generic_list_remove_element(ccache->active_iterators, gen_node); if (code != ccNoError) - return cci_serv_make_nack(ccErrBadParam, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrBadParam, auth_info, session_info, resp_msg); - return cci_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); + return ccs_serv_make_ack(NULL, 0, auth_info, session_info, resp_msg); } +cc_int32 +ccop_CREDS_ITERATOR_CLONE( cc_server_context_t* ctx, + cc_auth_info_t* auth_info, + cc_session_info_t* session_info, + cc_msg_t *msg, cc_msg_t **resp_msg) +{ + // TODO + return ccs_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); +} + + cc_int32 ccop_CREDS_ITERATOR_NEXT(cc_server_context_t* ctx, cc_auth_info_t* auth_info, @@ -1458,16 +1487,16 @@ ccop_CREDS_ITERATOR_NEXT(cc_server_context_t* ctx, if (msg->header_len != sizeof(ccmsg_creds_iterator_next_t)) return ccErrBadParam; - code = cci_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); + code = ccs_serv_find_ccache_by_handle(ctx, header->ccache, &ccache); if (code != ccNoError) - return cci_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrCCacheNotFound, auth_info, session_info, resp_msg); - code = cci_serv_find_creds_iterator_by_handle(ccache, header->iterator, &gen_node); + code = ccs_serv_find_creds_iterator_by_handle(ccache, header->iterator, &gen_node); if (code != ccNoError) - return cci_serv_make_nack(ccErrBadParam, auth_info, session_info, resp_msg); + return ccs_serv_make_nack(ccErrBadParam, auth_info, session_info, resp_msg); creds_iterator = (cc_credentials_iterate_t*)gen_node->data; - if (cci_credentials_iterate_has_next(creds_iterator)) { + if (ccs_credentials_iterate_has_next(creds_iterator)) { code = cci_msg_new(ccmsg_ACK, resp_msg); if (code != ccNoError) return code; @@ -1476,14 +1505,14 @@ ccop_CREDS_ITERATOR_NEXT(cc_server_context_t* ctx, if (resp_header == NULL) return ccErrNoMem; - code = cci_credentials_iterate_next(creds_iterator, &creds_node); + code = ccs_credentials_iterate_next(creds_iterator, &creds_node); stored_creds = (cc_server_credentials_t*)creds_node->data; creds_union = &stored_creds->creds; code = cci_msg_add_data_blob(*resp_msg, creds_union, sizeof(cc_credentials_union), &resp_header->creds_offset); code = cci_msg_add_header(*resp_msg, resp_header, sizeof(ccmsg_creds_iterator_next_resp_t)); } else { - cci_serv_make_nack(ccIteratorEnd, auth_info, session_info, resp_msg); + ccs_serv_make_nack(ccIteratorEnd, auth_info, session_info, resp_msg); } return ccNoError; } @@ -1495,6 +1524,6 @@ ccop_CREDS_RELEASE( cc_server_context_t* ctx, cc_msg_t *msg, cc_msg_t **resp_msg) { - cci_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); + ccs_serv_make_nack(ccErrNotImplemented, auth_info, session_info, resp_msg); return ccNoError; } diff --git a/src/lib/ccapi/server/serv_ops.h b/src/lib/ccapi/server/serv_ops.h index f43956685..152188636 100644 --- a/src/lib/ccapi/server/serv_ops.h +++ b/src/lib/ccapi/server/serv_ops.h @@ -1,6 +1,6 @@ /* $Copyright: * - * Copyright 2004 by the Massachusetts Institute of Technology. + * Copyright 2004-2006 by the Massachusetts Institute of Technology. * * All rights reserved. * @@ -63,52 +63,88 @@ struct type_to_op_mapping_t { }; typedef struct type_to_op_mapping_t type_to_op_mapping_t; -cc_int32 cci_serv_initialize(void); -cc_int32 cci_serv_process_msg(cc_msg_t * msg, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t** resp_msg); -cc_int32 cci_serv_find_ctx(cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_server_context_t** contextp); -cc_int32 cci_serv_find_ctx_by_handle(cc_handle ctx_handle, cc_auth_info_t *auth, cc_session_info_t* session, cc_server_context_t** contextp); -cc_int32 cci_serv_find_ccache_by_handle(cc_server_context_t* ctx, cc_handle ccache_handle, cc_server_ccache_t** ccachep) ; -cc_int32 cci_serv_find_ccache_iterator_by_handle(cc_server_context_t* ctx, cc_handle iterator, cc_generic_list_node_t** nodep); -cc_int32 cci_serv_find_creds_iterator_by_handle(cc_server_ccache_t* ccache, cc_handle iterator, cc_generic_list_node_t** nodep); -cc_int32 cci_serv_make_nack(cc_int32 err_code, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t** msgp); -cc_int32 cci_serv_make_ack(void * header, cc_int32 header_len, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t** msgp); - -cc_int32 ccop_INIT( +cc_int32 ccs_serv_initialize(void); +cc_int32 ccs_serv_process_msg(cc_msg_t * msg, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t** resp_msg); +cc_int32 ccs_serv_find_ctx(cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_server_context_t** contextp); +cc_int32 ccs_serv_find_ctx_by_handle(cc_handle ctx_handle, cc_auth_info_t *auth, cc_session_info_t* session, cc_server_context_t** contextp); +cc_int32 ccs_serv_find_ccache_by_handle(cc_server_context_t* ctx, cc_handle ccache_handle, cc_server_ccache_t** ccachep) ; +cc_int32 ccs_serv_find_ccache_iterator_by_handle(cc_server_context_t* ctx, cc_handle iterator, cc_generic_list_node_t** nodep); +cc_int32 ccs_serv_find_creds_iterator_by_handle(cc_server_ccache_t* ccache, cc_handle iterator, cc_generic_list_node_t** nodep); +cc_int32 ccs_serv_make_nack(cc_int32 err_code, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t** msgp); +cc_int32 ccs_serv_make_ack(void * header, cc_int32 header_len, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t** msgp); + +cc_int32 +ccop_INIT( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CTX_RELEASE( +cc_int32 +ccop_CTX_RELEASE( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CTX_GET_CHANGE_TIME( +cc_int32 +ccop_CTX_GET_CHANGE_TIME( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CTX_GET_DEFAULT_CCACHE_NAME( +cc_int32 +ccop_CTX_GET_DEFAULT_CCACHE_NAME( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CTX_COMPARE( +cc_int32 +ccop_CTX_CCACHE_OPEN( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CTX_NEW_CCACHE_ITERATOR( +cc_int32 +ccop_CTX_CCACHE_OPEN_DEFAULT( + cc_server_context_t* ctx, + cc_auth_info_t* auth_info, + cc_session_info_t* session_info, + cc_msg_t *msg, + cc_msg_t **resp_msg); + +cc_int32 +ccop_CTX_CCACHE_CREATE( + cc_server_context_t* ctx, + cc_auth_info_t* auth_info, + cc_session_info_t* session_info, + cc_msg_t *msg, + cc_msg_t **resp_msg); + +cc_int32 +ccop_CTX_CCACHE_CREATE_DEFAULT( cc_server_context_t* ctx, + cc_auth_info_t* auth_info, + cc_session_info_t* session_info, + cc_msg_t *msg, + cc_msg_t **resp_msg); + +cc_int32 +ccop_CTX_CCACHE_CREATE_UNIQUE( cc_server_context_t* ctx, + cc_auth_info_t* auth_info, + cc_session_info_t* session_info, + cc_msg_t *msg, + cc_msg_t **resp_msg); + +cc_int32 +ccop_CTX_NEW_CCACHE_ITERATOR( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, @@ -129,28 +165,24 @@ ccop_CTX_UNLOCK( cc_server_context_t* ctx, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 -ccop_CTX_CLONE( cc_server_context_t* ctx, - cc_auth_info_t* auth_info, - cc_session_info_t* session_info, - cc_msg_t *msg, - cc_msg_t **resp_msg); - -cc_int32 ccop_CCACHE_OPEN( +cc_int32 +ccop_CTX_COMPARE( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_OPEN_DEFAULT( +cc_int32 +ccop_CCACHE_RELEASE( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_CREATE( +cc_int32 +ccop_CCACHE_DESTROY( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, @@ -158,90 +190,95 @@ cc_int32 ccop_CCACHE_CREATE( cc_msg_t **resp_msg); cc_int32 -ccop_CCACHE_CREATE_DEFAULT( cc_server_context_t* ctx, - cc_auth_info_t* auth_info, - cc_session_info_t* session_info, - cc_msg_t *msg, - cc_msg_t **resp_msg); - -cc_int32 -ccop_CCACHE_CREATE_UNIQUE( cc_server_context_t* ctx, - cc_auth_info_t* auth_info, - cc_session_info_t* session_info, - cc_msg_t *msg, - cc_msg_t **resp_msg); - -cc_int32 ccop_CCACHE_RELEASE( +ccop_CCACHE_SET_DEFAULT( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_DESTROY( +cc_int32 +ccop_CCACHE_GET_CREDS_VERSION( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_SET_DEFAULT( +cc_int32 +ccop_CCACHE_GET_NAME( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_GET_CREDS_VERSION( +cc_int32 +ccop_CCACHE_GET_PRINCIPAL( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_GET_NAME( +cc_int32 +ccop_CCACHE_SET_PRINCIPAL( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_GET_PRINCIPAL( +cc_int32 +ccop_CCACHE_STORE_CREDS( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_SET_PRINCIPAL( +cc_int32 +ccop_CCACHE_REM_CREDS( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_CREDS_ITERATOR( +cc_int32 +ccop_CCACHE_NEW_CREDS_ITERATOR( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_STORE_CREDS( +cc_int32 +ccop_CCACHE_MOVE( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_REM_CREDS( - cc_server_context_t* ctx, - cc_auth_info_t* auth_info, - cc_session_info_t* session_info, - cc_msg_t *msg, - cc_msg_t **resp_msg); +cc_int32 +ccop_CCACHE_LOCK( + cc_server_context_t* ctx, + cc_auth_info_t* auth_info, + cc_session_info_t* session_info, + cc_msg_t *msg, + cc_msg_t **resp_msg); + +cc_int32 +ccop_CCACHE_UNLOCK( + cc_server_context_t* ctx, + cc_auth_info_t* auth_info, + cc_session_info_t* session_info, + cc_msg_t *msg, + cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_GET_LAST_DEFAULT_TIME( +cc_int32 +ccop_CCACHE_GET_LAST_DEFAULT_TIME( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, @@ -256,63 +293,80 @@ ccop_CCACHE_GET_CHANGE_TIME( cc_msg_t *msg, cc_msg_t **resp_msg) ; -cc_int32 ccop_CCACHE_COMPARE( +cc_int32 +ccop_CCACHE_COMPARE( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_GET_KDC_TIME_OFFSET( +cc_int32 +ccop_CCACHE_GET_KDC_TIME_OFFSET( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_SET_KDC_TIME_OFFSET( +cc_int32 +ccop_CCACHE_SET_KDC_TIME_OFFSET( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_CLEAR_KDC_TIME_OFFSET( +cc_int32 +ccop_CCACHE_CLEAR_KDC_TIME_OFFSET( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_ITERATOR_RELEASE( +cc_int32 +ccop_CCACHE_ITERATOR_RELEASE( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CCACHE_ITERATOR_NEXT( +cc_int32 +ccop_CCACHE_ITERATOR_NEXT( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CREDS_ITERATOR_RELEASE( +cc_int32 +ccop_CCACHE_ITERATOR_CLONE( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CREDS_ITERATOR_NEXT( +cc_int32 +ccop_CREDS_ITERATOR_RELEASE( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, cc_msg_t *msg, cc_msg_t **resp_msg); -cc_int32 ccop_CREDS_RELEASE( +cc_int32 +ccop_CREDS_ITERATOR_NEXT( + cc_server_context_t* ctx, + cc_auth_info_t* auth_info, + cc_session_info_t* session_info, + cc_msg_t *msg, + cc_msg_t **resp_msg); + +cc_int32 +ccop_CREDS_ITERATOR_CLONE( cc_server_context_t* ctx, cc_auth_info_t* auth_info, cc_session_info_t* session_info, diff --git a/src/lib/ccapi/unit-test/NTMakefile b/src/lib/ccapi/unit-test/NTMakefile new file mode 100644 index 000000000..eb2fd53e2 --- /dev/null +++ b/src/lib/ccapi/unit-test/NTMakefile @@ -0,0 +1,30 @@ +# Makefile for the CCAPI Generic Server + +!INCLUDE + +CFLAGS = -I../include + +CCAPI_LIB = ../lib/ccapi.lib +WINLIBS = user32.lib advapi32.lib +CCSOBJS = context.obj ccache.obj lists.obj rpc_auth.obj serv_ops.obj + +all: t_lists.exe t_msg.exe t_ccache.exe t_context.exe ccapi_server.exe + +t_lists.exe: t_lists.obj $(CCSOBJS) $(CCAPI_LIB) + link -out:$@ t_lists.obj $(CCSOBJS) $(CCAPI_LIB) $(WINLIBS) + +t_msg.exe: t_msg.obj $(CCSOBJS) $(CCAPI_LIB) + link -out:$@ t_msg.obj $(CCSOBJS) $(CCAPI_LIB) $(WINLIBS) + +t_ccache.exe: t_ccache.obj $(CCSOBJS) $(CCAPI_LIB) + link -out:$@ t_ccache.obj $(CCSOBJS) $(CCAPI_LIB) $(WINLIBS) + +t_context.exe: t_context.obj $(CCSOBJS) $(CCAPI_LIB) + link -out:$@ t_context.obj $(CCSOBJS) $(CCAPI_LIB) $(WINLIBS) + +ccapi_server.exe: main.obj $(CCSOBJS) $(CCAPI_LIB) + link -out:$@ main.obj $(CCSOBJS) $(CCAPI_LIB) $(WINLIBS) + +clean: + del *.obj *.exe + diff --git a/src/lib/ccapi/windows/rpcsstest/NTMakefile b/src/lib/ccapi/windows/rpcsstest/NTMakefile new file mode 100644 index 000000000..0e2330707 --- /dev/null +++ b/src/lib/ccapi/windows/rpcsstest/NTMakefile @@ -0,0 +1,24 @@ + +!include + +{}.c{}.obj: + $(CC) $(cdebug) $(cflags) /Fo"$@" /c $** + +EXECONLINK=link /NOLOGO $(conlibsmt) $(ldebug) $(conlflags) /OUT:$@ $** + +CLIENTEXE=csclient.exe + +SERVEREXE=csserver.exe + +SDKLIBS=rpcrt4.lib + +cstest_c.c cstest_s.c cstest.h: cstest.idl cstest.acf + midl cstest.idl /acf cstest.acf + +$(CLIENTEXE): client.obj cstest_c.obj + $(EXECONLINK) $(SDKLIBS) + +$(SERVEREXE): server.obj cstest_s.obj + $(EXECONLINK) $(SDKLIBS) + +all: $(SERVEREXE) $(CLIENTEXE) diff --git a/src/lib/ccapi/windows/rpcsstest/client.c b/src/lib/ccapi/windows/rpcsstest/client.c new file mode 100644 index 000000000..a25e8d1ad --- /dev/null +++ b/src/lib/ccapi/windows/rpcsstest/client.c @@ -0,0 +1,87 @@ +#include +#include +#include +#include +#include"cstest.h" +#include + +void * __RPC_USER MIDL_user_allocate(size_t s) { + return malloc(s); +} + +void __RPC_USER MIDL_user_free(void * p) { + free(p); +} + +int main(int argc, char ** argv) { + RPC_STATUS status; + RPC_BINDING_HANDLE h; + TCHAR * bindstring = NULL; + RPC_SECURITY_QOS sqos; + char inbuf[256]; + char outbuf[256]; + long cb_out; + + status = RpcStringBindingCompose(NULL, + _T("ncalrpc"), + NULL, + NULL, + NULL, + &bindstring); + + if (status != RPC_S_OK) { + fprintf(stderr, "RpcStringBindingCompose failed: %d\n", + status); + return 1; + } + + status = RpcBindingFromStringBinding(bindstring, + &h); + + if (status != RPC_S_OK) { + fprintf(stderr, "RpcBindingFromStringBinding failed: %d\n", + status); + return 1; + } + + ZeroMemory(&sqos, sizeof(sqos)); + + sqos.Version = 1; + sqos.Capabilities = RPC_C_QOS_CAPABILITIES_DEFAULT; + sqos.IdentityTracking = RPC_C_QOS_IDENTITY_STATIC; + sqos.ImpersonationType = RPC_C_IMP_LEVEL_IMPERSONATE; + + status = RpcBindingSetAuthInfoEx(h, + NULL, + RPC_C_AUTHN_LEVEL_CALL, + RPC_C_AUTHN_WINNT, + NULL, + 0, + &sqos); + + if (status != RPC_S_OK) { + fprintf(stderr, "RpcBindingSetAuthInfoEx failed: %d\n", + status); + return 1; + } + + StringCbCopyA(inbuf, sizeof(inbuf), "Echo Test 1"); + StringCbCopyA(outbuf, sizeof(outbuf), "Blank blank blank"); + + printf("Before call: in[%s], out[%s]\n", inbuf, outbuf); + cb_out = 0; + + status = EchoString(h, inbuf, sizeof(outbuf), &cb_out, outbuf); + + if (status) { + printf("Call failed: status = %d\n", status); + } else { + printf("After call: out[%s], outlen[%d]\n", outbuf, cb_out); + } + + status = RpcBindingFree(&h); + + status = RpcStringFree(&bindstring); + + return 0; +} diff --git a/src/lib/ccapi/windows/rpcsstest/cstest.acf b/src/lib/ccapi/windows/rpcsstest/cstest.acf new file mode 100644 index 000000000..3c2ae73ab --- /dev/null +++ b/src/lib/ccapi/windows/rpcsstest/cstest.acf @@ -0,0 +1,8 @@ +[ + explicit_handle +] + +interface ccapi_cstest +{ + +} \ No newline at end of file diff --git a/src/lib/ccapi/windows/rpcsstest/cstest.idl b/src/lib/ccapi/windows/rpcsstest/cstest.idl new file mode 100644 index 000000000..c51b8ee82 --- /dev/null +++ b/src/lib/ccapi/windows/rpcsstest/cstest.idl @@ -0,0 +1,14 @@ +[ +uuid(c8b4a635-e9e4-4650-a073-b25610324950), + version(1.0), + pointer_default(unique) +] + +interface ccapi_cstest +{ + long EchoString([in] handle_t h, + [in, string] unsigned char * in_str, + [in] long cb_buffer, + [out] long * cb_len, + [out, string, size_is(cb_buffer)] unsigned char buffer[*]); +} diff --git a/src/lib/ccapi/windows/rpcsstest/server.c b/src/lib/ccapi/windows/rpcsstest/server.c new file mode 100644 index 000000000..f127434b5 --- /dev/null +++ b/src/lib/ccapi/windows/rpcsstest/server.c @@ -0,0 +1,537 @@ +#include +#include +#include +#include +#include +#include"cstest.h" +#include + +#define SVCNAME "CCAPICSTest" + +SERVICE_STATUS_HANDLE h_service_status = NULL; +SERVICE_STATUS service_status; +FILE * logfile = NULL; + +void begin_log(void) { + char temppath[512]; + + temppath[0] = L'\0'; + + GetTempPathA(sizeof(temppath), temppath); + StringCbCatA(temppath, sizeof(temppath), "csserverconn.log"); + logfile = fopen(temppath, "w"); +} + +void end_log(void) { + if (logfile) { + fclose(logfile); + logfile = NULL; + } +} + +BOOL report_status(DWORD state, + DWORD exit_code, + DWORD wait_hint) { + static DWORD checkpoint = 1; + BOOL rv = TRUE; + + if (state == SERVICE_START_PENDING) + service_status.dwControlsAccepted = 0; + else + service_status.dwControlsAccepted = SERVICE_ACCEPT_STOP; + + service_status.dwCurrentState = state; + service_status.dwWin32ExitCode = exit_code; + service_status.dwWaitHint = wait_hint; + + if (state == SERVICE_RUNNING || + state == SERVICE_STOPPED) + service_status.dwCheckPoint = 0; + else + service_status.dwCheckPoint = checkpoint++; + + rv = SetServiceStatus(h_service_status, &service_status); + + return rv; +} + +void service_start(DWORD argc, LPTSTR * argv) { + RPC_STATUS status; + RPC_BINDING_VECTOR * bv; + + status = RpcServerUseProtseq("ncalrpc", + RPC_C_PROTSEQ_MAX_REQS_DEFAULT, + NULL); + + if (status != RPC_S_OK) { + return; + } + + report_status(SERVICE_START_PENDING, NO_ERROR, 3000); + + status = RpcServerRegisterIf(ccapi_cstest_v1_0_s_ifspec, + 0, 0); + + if (status != RPC_S_OK) + return; + + report_status(SERVICE_START_PENDING, NO_ERROR, 3000); + + status = RpcServerInqBindings(&bv); + + if (status != RPC_S_OK) + return; + + status = RpcEpRegister(ccapi_cstest_v1_0_s_ifspec, + bv, 0, 0); + + if (status != RPC_S_OK) + return; + + report_status(SERVICE_START_PENDING, NO_ERROR, 3000); + + status = RpcServerRegisterAuthInfo(NULL, + RPC_C_AUTHN_WINNT, + 0, 0); + + if (status != RPC_S_OK) + return; + + report_status(SERVICE_START_PENDING, NO_ERROR, 3000); + + status = RpcServerListen(1, + RPC_C_LISTEN_MAX_CALLS_DEFAULT, + TRUE); + + if (status != RPC_S_OK) + return; + + report_status(SERVICE_RUNNING, NO_ERROR, 0); + + begin_log(); + + status = RpcMgmtWaitServerListen(); + + end_log(); + + RpcEpUnregister(ccapi_cstest_v1_0_s_ifspec, bv, 0); + + RpcBindingVectorFree(&bv); +} + +void service_stop(void) { + RpcMgmtStopServerListening(0); +} + +void * __RPC_USER MIDL_user_allocate(size_t s) { + return malloc(s); +} + +void __RPC_USER MIDL_user_free(void * p) { + free(p); +} + +typedef struct tag_client_info { + char client_name[512]; + LUID luid; +} client_info_t; + +RPC_STATUS check_auth(handle_t h, client_info_t * client_info) { + RPC_BINDING_HANDLE bh = (RPC_BINDING_HANDLE) h; + RPC_STATUS status; + HANDLE htoken = NULL; + char name[256]; + char domain[256]; + DWORD name_len; + DWORD domain_len; + SID_NAME_USE snu = 0; + + struct { + TOKEN_ORIGIN origin; + char pad[512]; + } torigin; + + struct { + TOKEN_OWNER owner; + char pad[4096]; + } towner; + + DWORD len; + + status = RpcImpersonateClient(bh); + + if (status != RPC_S_OK) + return status; + + if (!OpenThreadToken(GetCurrentThread(), + TOKEN_READ | TOKEN_QUERY_SOURCE, + FALSE, + &htoken)) { + status = GetLastError(); + goto _cleanup; + } + + len = 0; + + if (!GetTokenInformation(htoken, + TokenOrigin, + &torigin.origin, + sizeof(torigin), + &len)) { + status = GetLastError(); + goto _cleanup; + } + + if (!GetTokenInformation(htoken, + TokenOwner, + &towner.owner, + sizeof(towner), + &len)) { + status = GetLastError(); + goto _cleanup; + } + + + name_len = sizeof(name)/sizeof(name[0]); + domain_len = sizeof(domain)/sizeof(domain[0]); + + if (!LookupAccountSidA(NULL, + towner.owner.Owner, + name, + &name_len, + domain, + &domain_len, + &snu)) { + status = GetLastError(); + goto _cleanup; + } + + client_info->luid = torigin.origin.OriginatingLogonSession; + StringCbPrintfA(client_info->client_name, + sizeof(client_info->client_name), + "%s\\%s", domain, name); + + status = 0; + + _cleanup: + + RpcRevertToSelf(); + + return status; +} + +long EchoString( + /* [in] */ handle_t h, + /* [string][in] */ unsigned char *in_str, + /* [in] */ long cb_buffer, + /* [out] */ long *cb_len, + /* [size_is][string][out] */ unsigned char buffer[ ]) { + + size_t cb; + long rv = 0; + client_info_t client_info; + + rv = check_auth(h, &client_info); + + if (rv == 0 && logfile) { + fprintf(logfile, + "Client name [%s], LUID [%x:%x]\n", + client_info.client_name, + (client_info.luid.HighPart), + (client_info.luid.LowPart)); + fflush(logfile); + } + + if (!in_str) { + rv = 1; + if (cb_len) + *cb_len = 0; + if (buffer) + buffer[0] = '\0'; + } else { + if (FAILED(StringCbLengthA(in_str, 256, &cb))) { + rv = 2; + goto _exit_f; + } + + cb += sizeof(char); + + if (((long)cb) > cb_buffer) { + rv = 3; + goto _exit_f; + } + + *cb_len = cb; + + if (buffer) + StringCbCopyA(buffer, cb_buffer, in_str); + + rv = 0; + } + + _exit_f: + + return rv; +} + +void WINAPI service_control(DWORD ctrl_code) { + switch(ctrl_code) { + case SERVICE_CONTROL_STOP: + report_status(SERVICE_STOP_PENDING, NO_ERROR, 0); + service_stop(); + return; + + /* everything else falls through */ + } + + report_status(service_status.dwCurrentState, NO_ERROR, 0); +} + +void WINAPI service_main(DWORD argc, LPTSTR * argv) { + + h_service_status = RegisterServiceCtrlHandler( _T(SVCNAME), service_control); + + if (!h_service_status) + goto cleanup; + + ZeroMemory(&service_status, sizeof(service_status)); + + service_status.dwServiceType = SERVICE_WIN32_OWN_PROCESS; + service_status.dwServiceSpecificExitCode = 0; + + if (!report_status(SERVICE_START_PENDING, + NO_ERROR, + 3000)) + goto cleanup; + + service_start(argc, argv); + + cleanup: + + if (h_service_status) { + report_status(SERVICE_STOPPED, NO_ERROR, 0); + } +} + + +BOOL +IsInstalled() +{ + BOOL bResult = FALSE; + SC_HANDLE hSCM; + SC_HANDLE hService; + + // Open the Service Control Manager + hSCM = OpenSCManager( NULL, // local machine + NULL, // ServicesActive database + SC_MANAGER_ALL_ACCESS); // full access + if (hSCM) { + + // Try to open the service + hService = OpenService( hSCM, + SVCNAME, + SERVICE_QUERY_CONFIG); + if (hService) { + bResult = TRUE; + CloseServiceHandle(hService); + } + + CloseServiceHandle(hSCM); + } + + return bResult; +} + +BOOL +Install() +{ + char szFilePath[_MAX_PATH]; + SC_HANDLE hSCM; + SC_HANDLE hService; + TCHAR szKey[256]; + HKEY hKey = NULL; + DWORD dwData; + + // Open the Service Control Manager + hSCM = OpenSCManager( NULL, // local machine + NULL, // ServicesActive database + SC_MANAGER_ALL_ACCESS); // full access + if (!hSCM) + return FALSE; + + // Get the executable file path + GetModuleFileName(NULL, szFilePath, sizeof(szFilePath)); + + // Create the service + hService = CreateService( hSCM, + SVCNAME, + SVCNAME, + SERVICE_ALL_ACCESS, + SERVICE_WIN32_OWN_PROCESS, + SERVICE_AUTO_START, // start condition + SERVICE_ERROR_NORMAL, + szFilePath, + NULL, + NULL, + NULL, + NULL, + NULL); + if (!hService) { + CloseServiceHandle(hSCM); + return FALSE; + } + + // make registry entries to support logging messages + // Add the source name as a subkey under the Application + // key in the EventLog service portion of the registry. + StringCbCopyA(szKey, 256, "SYSTEM\\CurrentControlSet\\Services\\EventLog\\Application\\IKSD"); + if (RegCreateKey(HKEY_LOCAL_MACHINE, szKey, &hKey) != ERROR_SUCCESS) { + CloseServiceHandle(hService); + CloseServiceHandle(hSCM); + return FALSE; + } + + // Add the Event ID message-file name to the 'EventMessageFile' subkey. + RegSetValueEx( hKey, + "EventMessageFile", + 0, + REG_EXPAND_SZ, + (CONST BYTE*)szFilePath, + strlen(szFilePath) + 1); + + // Set the supported types flags. + dwData = EVENTLOG_ERROR_TYPE | EVENTLOG_WARNING_TYPE | EVENTLOG_INFORMATION_TYPE; + RegSetValueEx( hKey, + "TypesSupported", + 0, + REG_DWORD, + (CONST BYTE*)&dwData, + sizeof(DWORD)); + RegCloseKey(hKey); + + // LogEvent(EVENTLOG_INFORMATION_TYPE, EVMSG_INSTALLED, SVCNAME); + + // tidy up + CloseServiceHandle(hService); + CloseServiceHandle(hSCM); + return TRUE; +} + +BOOL +Uninstall() +{ + BOOL bResult = FALSE; + SC_HANDLE hService; + SC_HANDLE hSCM; + + // Open the Service Control Manager + hSCM = OpenSCManager( NULL, // local machine + NULL, // ServicesActive database + SC_MANAGER_ALL_ACCESS); // full access + if (!hSCM) + return FALSE; + + hService = OpenService( hSCM, + SVCNAME, + DELETE); + if (hService) { + if (DeleteService(hService)) { + // LogEvent(EVENTLOG_INFORMATION_TYPE, EVMSG_REMOVED, SVCNAME); + bResult = TRUE; + } else { + // LogEvent(EVENTLOG_ERROR_TYPE, EVMSG_NOTREMOVED, SVCNAME); + } + CloseServiceHandle(hService); + } + + CloseServiceHandle(hSCM); + return bResult; +} + + +// Returns TRUE if it found an arg it recognised, FALSE if not +// Note: processing some arguments causes output to stdout to be generated. +BOOL +ParseStandardArgs(int argc, char* argv[]) +{ + char szFilePath[_MAX_PATH]; + + // See if we have any command line args we recognize + if (argc <= 1) + return FALSE; + + if ( _stricmp(argv[1], "-h") == 0 || + _stricmp(argv[1], "-?") == 0 || + _stricmp(argv[1], "/h") == 0 || + _stricmp(argv[1], "/?") == 0) { + + // + GetModuleFileName(NULL, szFilePath, sizeof(szFilePath)); + fprintf(stderr, "usage: %s [-v | -i | -u | -h]\r\n",szFilePath); + return TRUE; + } else if (_stricmp(argv[1], "-v") == 0 || + _stricmp(argv[1], "/v") == 0 ) { + + // Spit out version info + fprintf(stderr, "%s Version 0.1\n",_T(SVCNAME)); + fprintf(stderr, "The service is %s installed\n", + IsInstalled() ? "currently" : "not"); + return TRUE; // say we processed the argument + + } else if (_stricmp(argv[1], "-i") == 0 || + _stricmp(argv[1], "/i") == 0) { + + // Request to install. + if (IsInstalled()) { + fprintf(stderr, "%s is already installed\n", _T(SVCNAME)); + } else { + // Try and install the copy that's running + if (Install()) { + fprintf(stderr, "%s installed\n", _T(SVCNAME)); + } else { + fprintf(stderr, "%s failed to install. Error %d\n", _T(SVCNAME), GetLastError()); + } + } + return TRUE; // say we processed the argument + + } else if (_stricmp(argv[1], "-u") == 0 || + _stricmp(argv[1], "/u") == 0) { + + // Request to uninstall. + if (!IsInstalled()) { + fprintf(stderr, "%s is not installed\n", _T(SVCNAME)); + } else { + // Try and remove the copy that's installed + if (Uninstall()) { + // Get the executable file path + GetModuleFileName(NULL, szFilePath, sizeof(szFilePath)); + fprintf(stderr, "%s removed. (You must delete the file (%s) yourself.)\n" + _T(SVCNAME), szFilePath); + } else { + fprintf(stderr, "Could not remove %s. Error %d\n", _T(SVCNAME), GetLastError()); + } + } + return TRUE; // say we processed the argument + + } + + // Don't recognise the args + return FALSE; +} + +int main(int argc, char ** argv) { + + SERVICE_TABLE_ENTRY dispatch_table[] = { + { _T(SVCNAME), (LPSERVICE_MAIN_FUNCTION) service_main }, + { NULL, NULL } + }; + + if ( ParseStandardArgs(argc, argv) ) + return 0; + + if (!StartServiceCtrlDispatcher(dispatch_table)) { + fprintf(stderr, "Can't start service control dispatcher\n"); + } + + return 0; +}