From: Nikos Mavrogiannopoulos Date: Mon, 24 May 2010 14:58:31 +0000 (+0200) Subject: Added a modified pakchois library (to open arbitrary pkcs11 modules). X-Git-Tag: gnutls_2_11_3~250 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=e4cceb23547c8dc8394f58fd087e0f17c8add2ca;p=thirdparty%2Fgnutls.git Added a modified pakchois library (to open arbitrary pkcs11 modules). Current gnutls works only with this one. --- diff --git a/lib/Makefile.am b/lib/Makefile.am index 12b686bb03..d795fa7a29 100644 --- a/lib/Makefile.am +++ b/lib/Makefile.am @@ -88,6 +88,7 @@ if ENABLE_PKCS11 COBJECTS += pkcs11.c pkcs11_privkey.c endif + if ENABLE_NETTLE SUBDIRS += nettle else @@ -125,6 +126,11 @@ HFILES = debug.h gnutls_compress.h gnutls_cipher.h gnutls_buffers.h \ ext_session_ticket.h ext_signature.h gnutls_cryptodev.h \ ext_safe_renegotiation.h +if ENABLE_LOCAL_PAKCHOIS +COBJECTS+=pakchois/pakchois.c pakchois/errors.c +HFILES+=pakchois/pakchois.h pakchois/pakchois11.h +endif + # Separate so we can create the documentation libgnutls_la_SOURCES = $(HFILES) $(COBJECTS) $(SRP_COBJECTS) \ @@ -154,9 +160,7 @@ else libgnutls_la_LDFLAGS += $(LTLIBTASN1) endif -if ENABLE_PAKCHOIS libgnutls_la_LDFLAGS += $(LTLIBPAKCHOIS) -endif if ENABLE_NETTLE libgnutls_la_LDFLAGS += $(LTLIBNETTLE) -lgmp -lpthread -lhogweed diff --git a/lib/configure.ac b/lib/configure.ac index 0918742d52..35fa0d4ee4 100644 --- a/lib/configure.ac +++ b/lib/configure.ac @@ -79,19 +79,6 @@ else AC_MSG_RESULT(no) fi -AC_ARG_WITH(pakchois, AS_HELP_STRING([--without-pakchois], - [disable pakchois PKCS11 support]), - ac_pakchois=$withval, ac_pakchois=yes) -AC_MSG_CHECKING([whether to include pakchois PKCS11 support]) -if test x$ac_pakchois != xno; then - AC_MSG_RESULT(yes) - AC_LIB_HAVE_LINKFLAGS(pakchois,, [#include ], [pakchois_module_load(0,0);]) - if test "$ac_cv_libpakchois" != yes; then - AC_MSG_ERROR( -*** -*** Pakchois was not found. This is required for PKCS11 support.) -AM_CONDITIONAL(ENABLE_PAKCHOIS, test "$ac_cv_libpakchois" = "yes") - lgl_INIT LIBGNUTLS_LIBS="-L${libdir} -lgnutls $LIBS" diff --git a/lib/m4/hooks.m4 b/lib/m4/hooks.m4 index 316bf8229e..aaf95c6b8d 100644 --- a/lib/m4/hooks.m4 +++ b/lib/m4/hooks.m4 @@ -92,6 +92,35 @@ AC_DEFUN([LIBGNUTLS_HOOKS], AC_MSG_RESULT($included_libtasn1) AM_CONDITIONAL(ENABLE_MINITASN1, test "$included_libtasn1" = "yes") + AC_ARG_WITH(included-pakchois, + AS_HELP_STRING([--with-included-pakchois], [use the included pakchois]), + included_pakchois=$withval, + included_pakchois=no) + if test "$included_pakchois" = "no"; then + AC_LIB_HAVE_LINKFLAGS(pakchois,, [#include ], + [pakchois_module_load(0,0);]) + if test "$ac_cv_pakchois" != yes; then + included_pakchois=yes + AC_MSG_WARN([[ + *** + *** Pakchois was not found. Will use the included one. + ]]) + fi + fi + AC_MSG_CHECKING([whether to use the included pakchois]) + AC_MSG_RESULT($included_pakchois) + AM_CONDITIONAL(ENABLE_LOCAL_PAKCHOIS, test "$included_pakchois" = "yes") + if test "$included_pakchois" = "yes";then + AC_CHECK_LIB(pthread, pthread_mutex_lock,, + [AC_MSG_ERROR([could not find pthread_mutex_lock])]) + AC_CHECK_LIB(dl, dlopen,, + [AC_MSG_ERROR([could not find dlopen])]) + + module_path="${libdir}:${libdir}/pkcs11" + + CPPFLAGS="$CPPFLAGS -DPAKCHOIS_MODPATH=\\\"${module_path}\\\"" + fi + AC_ARG_WITH(lzo, AS_HELP_STRING([--with-lzo], [use experimental LZO compression]), use_lzo=$withval, use_lzo=no) diff --git a/lib/pakchois/errors.c b/lib/pakchois/errors.c new file mode 100644 index 0000000000..de09b92d53 --- /dev/null +++ b/lib/pakchois/errors.c @@ -0,0 +1,146 @@ +/* + pakchois PKCS#11 interface -- error mapping + Copyright (C) 2008, Joe Orton + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public + License along with this library; if not, write to the Free + Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, + MA 02111-1307, USA +*/ + +/* + This code is directly derived from the scute.org PKCS#11 cryptoki + interface, which is: + + Copyright 2006, 2007 g10 Code GmbH + Copyright 2006 Andreas Jellinghaus + + This file is free software; as a special exception the author gives + unlimited permission to copy and/or distribute it, with or without + modifications, as long as this notice is preserved. + + This file is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY, to the extent permitted by law; without even + the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + PURPOSE. +*/ + +#include "config.h" + +#include "pakchois.h" + +#ifdef ENABLE_NLS +#include +#define _(x) dgettext(PACKAGE_NAME, x) +#else +#define _(x) x +#endif + +const char *pakchois_error(ck_rv_t rv) +{ + if (rv >= CKR_VENDOR_DEFINED) { + return _("Vendor defined error"); + } + + switch (rv) { + case CKR_OK: return _("OK"); + case CKR_CANCEL: return _("Cancel"); + case CKR_HOST_MEMORY: return _("Host memory"); + case CKR_SLOT_ID_INVALID: return _("Slot id invalid"); + case CKR_GENERAL_ERROR: return _("General error"); + case CKR_FUNCTION_FAILED: return _("Function failed"); + case CKR_ARGUMENTS_BAD: return _("Arguments bad"); + case CKR_NO_EVENT: return _("No event"); + case CKR_NEED_TO_CREATE_THREADS: return _("Need to create threads"); + case CKR_CANT_LOCK: return _("Can't lock"); + case CKR_ATTRIBUTE_READ_ONLY: return _("Attribute read only"); + case CKR_ATTRIBUTE_SENSITIVE: return _("Attribute sensitive"); + case CKR_ATTRIBUTE_TYPE_INVALID: return _("Attribute type invalid"); + case CKR_ATTRIBUTE_VALUE_INVALID: return _("Attribute value invalid"); + case CKR_DATA_INVALID: return _("Data invalid"); + case CKR_DATA_LEN_RANGE: return _("Data len range"); + case CKR_DEVICE_ERROR: return _("Device error"); + case CKR_DEVICE_MEMORY: return _("Device memory"); + case CKR_DEVICE_REMOVED: return _("Device removed"); + case CKR_ENCRYPTED_DATA_INVALID: return _("Encrypted data invalid"); + case CKR_ENCRYPTED_DATA_LEN_RANGE: return _("Encrypted data len range"); + case CKR_FUNCTION_CANCELED: return _("Function canceled"); + case CKR_FUNCTION_NOT_PARALLEL: return _("Function not parallel"); + case CKR_FUNCTION_NOT_SUPPORTED: return _("Function not supported"); + case CKR_KEY_HANDLE_INVALID: return _("Key handle invalid"); + case CKR_KEY_SIZE_RANGE: return _("Key size range"); + case CKR_KEY_TYPE_INCONSISTENT: return _("Key type inconsistent"); + case CKR_KEY_NOT_NEEDED: return _("Key not needed"); + case CKR_KEY_CHANGED: return _("Key changed"); + case CKR_KEY_NEEDED: return _("Key needed"); + case CKR_KEY_INDIGESTIBLE: return _("Key indigestible"); + case CKR_KEY_FUNCTION_NOT_PERMITTED: return _("Key function not permitted"); + case CKR_KEY_NOT_WRAPPABLE: return _("Key not wrappable"); + case CKR_KEY_UNEXTRACTABLE: return _("Key unextractable"); + case CKR_MECHANISM_INVALID: return _("Mechanism invalid"); + case CKR_MECHANISM_PARAM_INVALID: return _("Mechanism param invalid"); + case CKR_OBJECT_HANDLE_INVALID: return _("Object handle invalid"); + case CKR_OPERATION_ACTIVE: return _("Operation active"); + case CKR_OPERATION_NOT_INITIALIZED: return _("Operation not initialized"); + case CKR_PIN_INCORRECT: return _("PIN incorrect"); + case CKR_PIN_INVALID: return _("PIN invalid"); + case CKR_PIN_LEN_RANGE: return _("PIN len range"); + case CKR_PIN_EXPIRED: return _("PIN expired"); + case CKR_PIN_LOCKED: return _("PIN locked"); + case CKR_SESSION_CLOSED: return _("Session closed"); + case CKR_SESSION_COUNT: return _("Session count"); + case CKR_SESSION_HANDLE_INVALID: return _("Session handle invalid"); + case CKR_SESSION_PARALLEL_NOT_SUPPORTED: return _("Session parallel not supported"); + case CKR_SESSION_READ_ONLY: return _("Session read only"); + case CKR_SESSION_EXISTS: return _("Session exists"); + case CKR_SESSION_READ_ONLY_EXISTS: return _("Session read only exists"); + case CKR_SESSION_READ_WRITE_SO_EXISTS: return _("Session read write so exists"); + case CKR_SIGNATURE_INVALID: return _("Signature invalid"); + case CKR_SIGNATURE_LEN_RANGE: return _("Signature length range"); + case CKR_TEMPLATE_INCOMPLETE: return _("Template incomplete"); + case CKR_TEMPLATE_INCONSISTENT: return _("Template inconsistent"); + case CKR_TOKEN_NOT_PRESENT: return _("Token not present"); + case CKR_TOKEN_NOT_RECOGNIZED: return _("Token not recognized"); + case CKR_TOKEN_WRITE_PROTECTED: return _("Token write protected"); + case CKR_UNWRAPPING_KEY_HANDLE_INVALID: return _("Unwrapping key handle invalid"); + case CKR_UNWRAPPING_KEY_SIZE_RANGE: return _("Unwrapping key size range"); + case CKR_UNWRAPPING_KEY_TYPE_INCONSISTENT: return _("Unwrapping key type inconsistent"); + case CKR_USER_ALREADY_LOGGED_IN: return _("User already logged in"); + case CKR_USER_NOT_LOGGED_IN: return _("User not logged in"); + case CKR_USER_PIN_NOT_INITIALIZED: return _("User PIN not initialized"); + case CKR_USER_TYPE_INVALID: return _("User type invalid"); + case CKR_USER_ANOTHER_ALREADY_LOGGED_IN: return _("Another user already logged in"); + case CKR_USER_TOO_MANY_TYPES: return _("User too many types"); + case CKR_WRAPPED_KEY_INVALID: return _("Wrapped key invalid"); + case CKR_WRAPPED_KEY_LEN_RANGE: return _("Wrapped key length range"); + case CKR_WRAPPING_KEY_HANDLE_INVALID: return _("Wrapping key handle invalid"); + case CKR_WRAPPING_KEY_SIZE_RANGE: return _("Wrapping key size range"); + case CKR_WRAPPING_KEY_TYPE_INCONSISTENT: return _("Wrapping key type inconsistent"); + case CKR_RANDOM_SEED_NOT_SUPPORTED: return _("Random seed not supported"); + case CKR_RANDOM_NO_RNG: return _("Random no rng"); + case CKR_DOMAIN_PARAMS_INVALID: return _("Domain params invalid"); + case CKR_BUFFER_TOO_SMALL: return _("Buffer too small"); + case CKR_SAVED_STATE_INVALID: return _("Saved state invalid"); + case CKR_INFORMATION_SENSITIVE: return _("Information sensitive"); + case CKR_STATE_UNSAVEABLE: return _("State unsaveable"); + case CKR_CRYPTOKI_NOT_INITIALIZED: return _("Cryptoki not initialized"); + case CKR_CRYPTOKI_ALREADY_INITIALIZED: return _("Cryptoki already initialized"); + case CKR_MUTEX_BAD: return _("Mutex bad"); + case CKR_MUTEX_NOT_LOCKED: return _("Mutex not locked"); + case CKR_FUNCTION_REJECTED: return _("Function rejected"); + default: + break; + } + + return _("Unknown error"); +} diff --git a/lib/pakchois/pakchois.c b/lib/pakchois/pakchois.c new file mode 100644 index 0000000000..a69dfb0190 --- /dev/null +++ b/lib/pakchois/pakchois.c @@ -0,0 +1,982 @@ +/* + pakchois PKCS#11 interface + Copyright (C) 2008, Joe Orton + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public + License along with this library; if not, write to the Free + Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, + MA 02111-1307, USA +*/ + +/* + The interface is directly derived from the scute.org PKCS#11 + cryptoki interface, which is: + + Copyright 2006, 2007 g10 Code GmbH + Copyright 2006 Andreas Jellinghaus + + This file is free software; as a special exception the author gives + unlimited permission to copy and/or distribute it, with or without + modifications, as long as this notice is preserved. + + This file is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY, to the extent permitted by law; without even + the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + PURPOSE. +*/ + +#include "config.h" + +#include +#include +#include +#include +#include +#include +#include +#include "pakchois.h" + +struct provider { + char *name; + void *handle; + pthread_mutex_t mutex; + const struct ck_function_list *fns; + unsigned int refcount; + struct provider *next, **prevref; +}; + +struct pakchois_module_s { + struct slot *slots; + struct provider *provider; +}; + +static pthread_mutex_t provider_mutex = PTHREAD_MUTEX_INITIALIZER; + +/* List of loaded providers; any modification to the list or any + * individual module must performed whilst holding this mutex. */ +static struct provider *provider_list; + +struct pakchois_session_s { + pakchois_module_t *module; + ck_session_handle_t id; + pakchois_notify_t notify; + void *notify_data; + /* Doubly-linked list. Either prevref = &previous->next or else + * prevref = &slot->sessions for the list head. */ + pakchois_session_t **prevref; + pakchois_session_t *next; +}; + +struct slot { + ck_slot_id_t id; + pakchois_session_t *sessions; + struct slot *next; +}; + +#define DIR_DELIMITER '/' + +char* pkcs11ize(const char* name) +{ + int len; + char* oname; + char *base; + char *suffix; + + oname = strdup(name); + if (oname == NULL) { + return NULL; + } + + /* basename has too many ifs to use */ + base = strrchr(oname, DIR_DELIMITER); + if (base == NULL) { + base = oname; + } else { + base++; + } + + suffix = strchr(base, '.'); + if (suffix != NULL) { + if (strncmp(suffix, ".so", 3)==0) { + suffix[0] = 0; /* null terminate before . */ + } + } + + /* check and remove for -p11 or -pkcs11 */ + suffix = base; + while((suffix=strchr(suffix, '-')) != NULL) { + if (strncasecmp(suffix, "-p11", 4)==0 || + strncasecmp(suffix, "-pkcs11", 7)==0) { + suffix[0] = 0; + break; + } + suffix++; + } + + len = strlen(base); + + memmove(oname, base, len); + oname[len] = 0; + + return oname; +} + +static const char *suffix_prefixes[][2] = { + { "lib", "pk11.so" }, + { "", "-pkcs11.so" }, + { "", ".so" }, + { "lib", ".so" }, + { NULL, NULL } +}; + +#define CALL(name, args) (mod->provider->fns->C_ ## name) args +#define CALLS(name, args) (sess->module->provider->fns->C_ ## name) args +#define CALLS1(n, a) CALLS(n, (sess->id, a)) +#define CALLS2(n, a, b) CALLS(n, (sess->id, a, b)) +#define CALLS3(n, a, b, c) CALLS(n, (sess->id, a, b, c)) +#define CALLS4(n, a, b, c, d) CALLS(n, (sess->id, a, b, c, d)) +#define CALLS5(n, a, b, c, d, e) CALLS(n, (sess->id, a, b, c, d, e)) +#define CALLS7(n, a, b, c, d, e, f, g) CALLS(n, (sess->id, a, b, c, d, e, f, g)) + +static void *find_pkcs11_module(const char *name, CK_C_GetFunctionList *gfl) +{ + char module_path[] = PAKCHOIS_MODPATH; + char *next = module_path; + void *h; + + /* try the plain name first */ + h = dlopen(name, RTLD_LOCAL|RTLD_NOW); + if (h != NULL) { + *gfl = dlsym(h, "C_GetFunctionList"); + if (*gfl) { + return h; + } + dlclose(h); + } + + while (next) { + char *dir = next, *sep = strchr(next, ':'); + unsigned i; + + if (sep) { + *sep++ = '\0'; + next = sep; + } + else { + next = NULL; + } + + + for (i = 0; suffix_prefixes[i][0]; i++) { + char path[PATH_MAX]; + + snprintf(path, sizeof path, "%s/%s%s%s", dir, + suffix_prefixes[i][0], name, suffix_prefixes[i][1]); + + h = dlopen(path, RTLD_LOCAL|RTLD_NOW); + if (h != NULL) { + *gfl = dlsym(h, "C_GetFunctionList"); + if (*gfl) { + return h; + } + dlclose(h); + } + } + } + + return NULL; +} + +static struct provider *find_provider(const char *name) +{ + struct provider *p; + + for (p = provider_list; p; p = p->next) { + if (strcmp(name, p->name) == 0) { + return p; + } + } + + return NULL; +} + +static ck_rv_t load_provider(struct provider **provider, const char *name, + void *reserved) +{ + CK_C_GetFunctionList gfl; + struct provider *prov; + struct ck_function_list *fns; + struct ck_c_initialize_args args; + void *h; + ck_rv_t rv; + char *cname = NULL; + + if (pthread_mutex_lock(&provider_mutex) != 0) { + return CKR_CANT_LOCK; + } + + cname = pkcs11ize(name); + if (cname == NULL) { + rv = CKR_HOST_MEMORY; + goto fail_locked; + } + +fprintf(stderr, "found name: %s\n", cname); + + prov = find_provider(cname); + if (prov) { + prov->refcount++; + *provider = prov; + free(cname); + pthread_mutex_unlock(&provider_mutex); + return CKR_OK; + } + + h = find_pkcs11_module(name, &gfl); + if (!h) { + rv = CKR_GENERAL_ERROR; + goto fail_ndup; + } + + rv = gfl(&fns); + if (rv != CKR_OK) { + goto fail_dso; + } + + *provider = prov = malloc(sizeof *prov); + if (prov == NULL) { + rv = CKR_HOST_MEMORY; + goto fail_dso; + } + + if (pthread_mutex_init(&prov->mutex, NULL)) { + rv = CKR_GENERAL_ERROR; + goto fail_ctx; + } + + prov->name = cname; + prov->handle = h; + prov->fns = fns; + prov->refcount = 1; + + /* Require OS locking, the only sane option. */ + memset(&args, 0, sizeof args); + args.flags = CKF_OS_LOCKING_OK; + args.reserved = reserved; + + rv = fns->C_Initialize(&args); + if (rv != CKR_OK) { + goto fail_ctx; + } + + prov->next = provider_list; + prov->prevref = &provider_list; + if (prov->next) { + prov->next->prevref = &prov->next; + } + provider_list = prov; + + pthread_mutex_unlock(&provider_mutex); + + return CKR_OK; +fail_ctx: + free(prov); +fail_dso: + dlclose(h); +fail_ndup: + free(cname); +fail_locked: + pthread_mutex_unlock(&provider_mutex); + *provider = NULL; + return rv; +} + +static ck_rv_t load_module(pakchois_module_t **module, const char *name, + void *reserved) +{ + ck_rv_t rv; + pakchois_module_t *pm = malloc(sizeof *pm); + + if (!pm) { + return CKR_HOST_MEMORY; + } + + rv = load_provider(&pm->provider, name, reserved); + if (rv) { + return rv; + } + + *module = pm; + pm->slots = NULL; + + return CKR_OK; +} + +ck_rv_t pakchois_module_load(pakchois_module_t **module, const char *name) +{ + return load_module(module, name, NULL); +} + +ck_rv_t pakchois_module_nssload(pakchois_module_t **module, + const char *name, + const char *directory, + const char *cert_prefix, + const char *key_prefix, + const char *secmod_db) +{ + char buf[256]; + + snprintf(buf, sizeof buf, + "configdir='%s' certPrefix='%s' keyPrefix='%s' secmod='%s'", + directory, cert_prefix ? cert_prefix : "", + key_prefix ? key_prefix : "", + secmod_db ? secmod_db : "secmod.db"); + + return load_module(module, name, buf); +} + +/* Unreference a provider structure and destoy if, if necessary. Must + * be called WIHTOUT the provider mutex held. */ +static void provider_unref(struct provider *prov) +{ + assert(pthread_mutex_lock(&provider_mutex) == 0); + + if (--prov->refcount == 0) { + prov->fns->C_Finalize(NULL); + dlclose(prov->handle); + *prov->prevref = prov->next; + if (prov->next) { + prov->next->prevref = prov->prevref; + } + free(prov->name); + free(prov); + } + pthread_mutex_unlock(&provider_mutex); +} + +void pakchois_module_destroy(pakchois_module_t *mod) +{ + provider_unref(mod->provider); + + while (mod->slots) { + struct slot *slot = mod->slots; + pakchois_close_all_sessions(mod, slot->id); + mod->slots = slot->next; + free(slot); + } + + free(mod); +} + +#ifdef __GNUC__ +static void pakchois_destructor(void) + __attribute__((destructor)); + +static void pakchois_destructor(void) +{ + pthread_mutex_destroy(&provider_mutex); +} +#else +#warning need destructor support +#endif + +ck_rv_t pakchois_get_info(pakchois_module_t *mod, struct ck_info *info) +{ + return CALL(GetInfo, (info)); +} + +ck_rv_t pakchois_get_slot_list(pakchois_module_t *mod, + unsigned char token_present, + ck_slot_id_t *slot_list, + unsigned long *count) +{ + return CALL(GetSlotList, (token_present, slot_list, count)); +} + +ck_rv_t pakchois_get_slot_info(pakchois_module_t *mod, + ck_slot_id_t slot_id, + struct ck_slot_info *info) +{ + return CALL(GetSlotInfo, (slot_id, info)); +} + +ck_rv_t pakchois_get_token_info(pakchois_module_t *mod, + ck_slot_id_t slot_id, + struct ck_token_info *info) +{ + return CALL(GetTokenInfo, (slot_id, info)); +} + +ck_rv_t pakchois_wait_for_slot_event(pakchois_module_t *mod, + ck_flags_t flags, ck_slot_id_t *slot, + void *reserved) +{ + ck_rv_t rv; + + if (pthread_mutex_lock(&mod->provider->mutex)) { + return CKR_CANT_LOCK; + } + + rv = CALL(WaitForSlotEvent, (flags, slot, reserved)); + pthread_mutex_unlock(&mod->provider->mutex); + return rv; +} + +ck_rv_t pakchois_get_mechanism_list(pakchois_module_t *mod, + ck_slot_id_t slot_id, + ck_mechanism_type_t *mechanism_list, + unsigned long *count) +{ + return CALL(GetMechanismList, (slot_id, mechanism_list, count)); +} + +ck_rv_t pakchois_get_mechanism_info(pakchois_module_t *mod, + ck_slot_id_t slot_id, + ck_mechanism_type_t type, + struct ck_mechanism_info *info) +{ + return CALL(GetMechanismInfo, (slot_id, type, info)); +} + +ck_rv_t pakchois_init_token(pakchois_module_t *mod, + ck_slot_id_t slot_id, unsigned char *pin, + unsigned long pin_len, unsigned char *label) +{ + return CALL(InitToken, (slot_id, pin, pin_len, label)); +} + +ck_rv_t pakchois_init_pin(pakchois_session_t *sess, unsigned char *pin, + unsigned long pin_len) +{ + return CALLS2(InitPIN, pin, pin_len); +} + +ck_rv_t pakchois_set_pin(pakchois_session_t *sess, unsigned char *old_pin, + unsigned long old_len, unsigned char *new_pin, + unsigned long new_len) +{ + return CALLS4(SetPIN, old_pin, old_len, new_pin, new_len); +} + +static ck_rv_t notify_thunk(ck_session_handle_t session, + ck_notification_t event, void *application) +{ + pakchois_session_t *sess = application; + + return sess->notify(sess, event, sess->notify_data); +} + +static struct slot *find_slot(pakchois_module_t *mod, ck_slot_id_t id) +{ + struct slot *slot; + + for (slot = mod->slots; slot; slot = slot->next) + if (slot->id == id) + return slot; + + return NULL; +} + +static struct slot *find_or_create_slot(pakchois_module_t *mod, + ck_slot_id_t id) +{ + struct slot *slot = find_slot(mod, id); + + if (slot) { + return slot; + } + + slot = malloc(sizeof *slot); + if (!slot) { + return NULL; + } + + slot->id = id; + slot->sessions = NULL; + slot->next = mod->slots; + mod->slots = slot; + + return slot; +} + +static ck_rv_t insert_session(pakchois_module_t *mod, + pakchois_session_t *session, + ck_slot_id_t id) +{ + struct slot *slot = find_or_create_slot(mod, id); + + if (!slot) { + return CKR_HOST_MEMORY; + } + + session->prevref = &slot->sessions; + session->next = slot->sessions; + if (session->next) { + session->next->prevref = session->prevref; + } + slot->sessions = session; + + return CKR_OK; +} + +ck_rv_t pakchois_open_session(pakchois_module_t *mod, + ck_slot_id_t slot_id, ck_flags_t flags, + void *application, pakchois_notify_t notify, + pakchois_session_t **session) +{ + ck_session_handle_t sh; + pakchois_session_t *sess; + ck_rv_t rv; + + sess = calloc(1, sizeof *sess); + if (sess == NULL) { + return CKR_HOST_MEMORY; + } + + rv = CALL(OpenSession, (slot_id, flags, sess, notify_thunk, &sh)); + if (rv != CKR_OK) { + free(sess); + return rv; + } + + *session = sess; + sess->module = mod; + sess->id = sh; + + return insert_session(mod, sess, slot_id); +} + +ck_rv_t pakchois_close_session(pakchois_session_t *sess) +{ + /* PKCS#11 says that all bets are off on failure, so destroy the + * session object and just return the error code. */ + ck_rv_t rv = CALLS(CloseSession, (sess->id)); + *sess->prevref = sess->next; + if (sess->next) { + sess->next->prevref = sess->prevref; + } + free(sess); + return rv; +} + +ck_rv_t pakchois_close_all_sessions(pakchois_module_t *mod, + ck_slot_id_t slot_id) +{ + struct slot *slot; + ck_rv_t rv, frv = CKR_OK; + + slot = find_slot(mod, slot_id); + + if (!slot) { + return CKR_SLOT_ID_INVALID; + } + + while (slot->sessions) { + rv = pakchois_close_session(slot->sessions); + if (rv != CKR_OK) { + frv = rv; + } + } + + return frv; +} + +ck_rv_t pakchois_get_session_info(pakchois_session_t *sess, + struct ck_session_info *info) +{ + return CALLS1(GetSessionInfo, info); +} + +ck_rv_t pakchois_get_operation_state(pakchois_session_t *sess, + unsigned char *operation_state, + unsigned long *operation_state_len) +{ + return CALLS2(GetOperationState, operation_state, + operation_state_len); +} + +ck_rv_t pakchois_set_operation_state(pakchois_session_t *sess, + unsigned char *operation_state, + unsigned long operation_state_len, + ck_object_handle_t encryption_key, + ck_object_handle_t authentiation_key) +{ + return CALLS4(SetOperationState, operation_state, operation_state_len, + encryption_key, authentiation_key); +} + +ck_rv_t pakchois_login(pakchois_session_t *sess, ck_user_type_t user_type, + unsigned char *pin, unsigned long pin_len) +{ + return CALLS3(Login, user_type, pin, pin_len); +} + +ck_rv_t pakchois_logout(pakchois_session_t *sess) +{ + return CALLS(Logout, (sess->id)); +} + +ck_rv_t pakchois_create_object(pakchois_session_t *sess, + struct ck_attribute *templ, + unsigned long count, + ck_object_handle_t *object) +{ + return CALLS3(CreateObject, templ, count, object); +} + +ck_rv_t pakchois_copy_object(pakchois_session_t *sess, + ck_object_handle_t object, + struct ck_attribute *templ, unsigned long count, + ck_object_handle_t *new_object) +{ + return CALLS4(CopyObject, object, templ, count, new_object); +} + +ck_rv_t pakchois_destroy_object(pakchois_session_t *sess, + ck_object_handle_t object) +{ + return CALLS1(DestroyObject, object); +} + +ck_rv_t pakchois_get_object_size(pakchois_session_t *sess, + ck_object_handle_t object, + unsigned long *size) +{ + return CALLS2(GetObjectSize, object, size); +} + +ck_rv_t pakchois_get_attribute_value(pakchois_session_t *sess, + ck_object_handle_t object, + struct ck_attribute *templ, + unsigned long count) +{ + return CALLS3(GetAttributeValue, object, templ, count); +} + +ck_rv_t pakchois_set_attribute_value(pakchois_session_t *sess, + ck_object_handle_t object, + struct ck_attribute *templ, + unsigned long count) +{ + return CALLS3(SetAttributeValue, object, templ, count); +} + +ck_rv_t pakchois_find_objects_init(pakchois_session_t *sess, + struct ck_attribute *templ, + unsigned long count) +{ + return CALLS2(FindObjectsInit, templ, count); +} + +ck_rv_t pakchois_find_objects(pakchois_session_t *sess, + ck_object_handle_t *object, + unsigned long max_object_count, + unsigned long *object_count) +{ + return CALLS3(FindObjects, object, max_object_count, object_count); +} + +ck_rv_t pakchois_find_objects_final(pakchois_session_t *sess) +{ + return CALLS(FindObjectsFinal, (sess->id)); +} + +ck_rv_t pakchois_encrypt_init(pakchois_session_t *sess, + struct ck_mechanism *mechanism, + ck_object_handle_t key) +{ + return CALLS2(EncryptInit, mechanism, key); +} + +ck_rv_t pakchois_encrypt(pakchois_session_t *sess, + unsigned char *data, unsigned long data_len, + unsigned char *encrypted_data, + unsigned long *encrypted_data_len) +{ + return CALLS4(Encrypt, data, data_len, + encrypted_data, encrypted_data_len); +} + +ck_rv_t pakchois_encrypt_update(pakchois_session_t *sess, + unsigned char *part, unsigned long part_len, + unsigned char *encrypted_part, + unsigned long *encrypted_part_len) +{ + return CALLS4(EncryptUpdate, part, part_len, + encrypted_part, encrypted_part_len); +} + +ck_rv_t pakchois_encrypt_final(pakchois_session_t *sess, + unsigned char *last_encrypted_part, + unsigned long *last_encrypted_part_len) +{ + return CALLS2(EncryptFinal, last_encrypted_part, last_encrypted_part_len); +} + +ck_rv_t pakchois_decrypt_init(pakchois_session_t *sess, + struct ck_mechanism *mechanism, + ck_object_handle_t key) +{ + return CALLS2(DecryptInit, mechanism, key); +} + +ck_rv_t pakchois_decrypt(pakchois_session_t *sess, + unsigned char *encrypted_data, + unsigned long encrypted_data_len, + unsigned char *data, unsigned long *data_len) +{ + return CALLS4(Decrypt, encrypted_data, encrypted_data_len, data, data_len); +} + +ck_rv_t pakchois_decrypt_update(pakchois_session_t *sess, + unsigned char *encrypted_part, + unsigned long encrypted_part_len, + unsigned char *part, unsigned long *part_len) +{ + return CALLS4(DecryptUpdate, encrypted_part, encrypted_part_len, + part, part_len); +} + +ck_rv_t pakchois_decrypt_final(pakchois_session_t *sess, + unsigned char *last_part, + unsigned long *last_part_len) +{ + return CALLS2(DecryptFinal, last_part, last_part_len); +} + +ck_rv_t pakchois_digest_init(pakchois_session_t *sess, + struct ck_mechanism *mechanism) +{ + return CALLS1(DigestInit, mechanism); +} + +ck_rv_t pakchois_digest(pakchois_session_t *sess, unsigned char *data, + unsigned long data_len, unsigned char *digest, + unsigned long *digest_len) +{ + return CALLS4(Digest, data, data_len, digest, digest_len); +} + +ck_rv_t pakchois_digest_update(pakchois_session_t *sess, + unsigned char *part, unsigned long part_len) +{ + return CALLS2(DigestUpdate, part, part_len); +} + +ck_rv_t pakchois_digest_key(pakchois_session_t *sess, + ck_object_handle_t key) +{ + return CALLS1(DigestKey, key); +} + +ck_rv_t pakchois_digest_final(pakchois_session_t *sess, + unsigned char *digest, + unsigned long *digest_len) +{ + return CALLS2(DigestFinal, digest, digest_len); +} + +ck_rv_t pakchois_sign_init(pakchois_session_t *sess, + struct ck_mechanism *mechanism, + ck_object_handle_t key) +{ + return CALLS2(SignInit, mechanism, key); +} + +ck_rv_t pakchois_sign(pakchois_session_t *sess, unsigned char *data, + unsigned long data_len, unsigned char *signature, + unsigned long *signature_len) +{ + return CALLS4(Sign, data, data_len, signature, signature_len); +} + +ck_rv_t pakchois_sign_update(pakchois_session_t *sess, + unsigned char *part, unsigned long part_len) +{ + return CALLS2(SignUpdate, part, part_len); +} + +ck_rv_t pakchois_sign_final(pakchois_session_t *sess, + unsigned char *signature, + unsigned long *signature_len) +{ + return CALLS2(SignFinal, signature, signature_len); +} + +ck_rv_t pakchois_sign_recover_init(pakchois_session_t *sess, + struct ck_mechanism *mechanism, + ck_object_handle_t key) +{ + return CALLS2(SignRecoverInit, mechanism, key); +} + +ck_rv_t pakchois_sign_recover(pakchois_session_t *sess, + unsigned char *data, unsigned long data_len, + unsigned char *signature, + unsigned long *signature_len) +{ + return CALLS4(SignRecover, data, data_len, signature, signature_len); +} + +ck_rv_t pakchois_verify_init(pakchois_session_t *sess, + struct ck_mechanism *mechanism, + ck_object_handle_t key) +{ + return CALLS2(VerifyInit, mechanism, key); +} + +ck_rv_t pakchois_verify(pakchois_session_t *sess, unsigned char *data, + unsigned long data_len, unsigned char *signature, + unsigned long signature_len) +{ + return CALLS4(Verify, data, data_len, signature, signature_len); +} + +ck_rv_t pakchois_verify_update(pakchois_session_t *sess, + unsigned char *part, unsigned long part_len) +{ + return CALLS2(VerifyUpdate, part, part_len); +} + +ck_rv_t pakchois_verify_final(pakchois_session_t *sess, + unsigned char *signature, + unsigned long signature_len) +{ + return CALLS2(VerifyFinal, signature, signature_len); +} + +ck_rv_t pakchois_verify_recover_init(pakchois_session_t *sess, + struct ck_mechanism *mechanism, + ck_object_handle_t key) +{ + return CALLS2(VerifyRecoverInit, mechanism, key); +} + +ck_rv_t pakchois_verify_recover(pakchois_session_t *sess, + unsigned char *signature, + unsigned long signature_len, + unsigned char *data, unsigned long *data_len) +{ + return CALLS4(VerifyRecover, signature, signature_len, data, data_len); +} + +ck_rv_t pakchois_digest_encrypt_update(pakchois_session_t *sess, + unsigned char *part, + unsigned long part_len, + unsigned char *encrypted_part, + unsigned long *encrypted_part_len) +{ + return CALLS4(DigestEncryptUpdate, part, part_len, + encrypted_part, encrypted_part_len); +} + +ck_rv_t pakchois_decrypt_digest_update(pakchois_session_t *sess, + unsigned char *encrypted_part, + unsigned long encrypted_part_len, + unsigned char *part, + unsigned long *part_len) +{ + return CALLS4(DecryptDigestUpdate, encrypted_part, encrypted_part_len, + part, part_len); +} + +ck_rv_t pakchois_sign_encrypt_update(pakchois_session_t *sess, + unsigned char *part, + unsigned long part_len, + unsigned char *encrypted_part, + unsigned long *encrypted_part_len) +{ + return CALLS4(SignEncryptUpdate, part, part_len, + encrypted_part, encrypted_part_len); +} + +ck_rv_t pakchois_decrypt_verify_update(pakchois_session_t *sess, + unsigned char *encrypted_part, + unsigned long encrypted_part_len, + unsigned char *part, + unsigned long *part_len) +{ + return CALLS4(DecryptVerifyUpdate, encrypted_part, encrypted_part_len, + part, part_len); +} + +ck_rv_t pakchois_generate_key(pakchois_session_t *sess, + struct ck_mechanism *mechanism, + struct ck_attribute *templ, + unsigned long count, ck_object_handle_t *key) +{ + return CALLS4(GenerateKey, mechanism, templ, count, key); +} + +ck_rv_t pakchois_generate_key_pair(pakchois_session_t *sess, + struct ck_mechanism *mechanism, + struct ck_attribute *public_key_template, + unsigned long public_key_attribute_count, + struct ck_attribute *private_key_template, + unsigned long private_key_attribute_count, + ck_object_handle_t *public_key, + ck_object_handle_t *private_key) +{ + return CALLS7(GenerateKeyPair, mechanism, + public_key_template, public_key_attribute_count, + private_key_template, private_key_attribute_count, + public_key, private_key); +} + +ck_rv_t pakchois_wrap_key(pakchois_session_t *sess, + struct ck_mechanism *mechanism, + ck_object_handle_t wrapping_key, + ck_object_handle_t key, unsigned char *wrapped_key, + unsigned long *wrapped_key_len) +{ + return CALLS5(WrapKey, mechanism, wrapping_key, + key, wrapped_key, wrapped_key_len); +} + +ck_rv_t pakchois_unwrap_key(pakchois_session_t *sess, + struct ck_mechanism *mechanism, + ck_object_handle_t unwrapping_key, + unsigned char *wrapped_key, + unsigned long wrapped_key_len, + struct ck_attribute *templ, + unsigned long attribute_count, + ck_object_handle_t *key) +{ + return CALLS7(UnwrapKey, mechanism, unwrapping_key, + wrapped_key, wrapped_key_len, templ, attribute_count, + key); +} + +ck_rv_t pakchois_derive_key(pakchois_session_t *sess, + struct ck_mechanism *mechanism, + ck_object_handle_t base_key, + struct ck_attribute *templ, + unsigned long attribute_count, + ck_object_handle_t *key) +{ + return CALLS5(DeriveKey, mechanism, base_key, templ, attribute_count, key); +} + + +ck_rv_t pakchois_seed_random(pakchois_session_t *sess, + unsigned char *seed, unsigned long seed_len) +{ + return CALLS2(SeedRandom, seed, seed_len); +} + +ck_rv_t pakchois_generate_random(pakchois_session_t *sess, + unsigned char *random_data, + unsigned long random_len) +{ + return CALLS2(GenerateRandom, random_data, random_len); +} diff --git a/lib/pakchois/pakchois.h b/lib/pakchois/pakchois.h new file mode 100644 index 0000000000..76999ef41c --- /dev/null +++ b/lib/pakchois/pakchois.h @@ -0,0 +1,361 @@ +/* + pakchois PKCS#11 interface + Copyright (C) 2008, Joe Orton + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public + License along with this library; if not, write to the Free + Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, + MA 02111-1307, USA + +*/ + +/* + This interface is directly derived from the scute.org PKCS#11 + cryptoki interface, which is: + + Copyright 2006, 2007 g10 Code GmbH + Copyright 2006 Andreas Jellinghaus + + This file is free software; as a special exception the author gives + unlimited permission to copy and/or distribute it, with or without + modifications, as long as this notice is preserved. + + This file is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY, to the extent permitted by law; without even + the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + PURPOSE. +*/ + +#ifndef PAKCHOIS_H +#define PAKCHOIS_H + +#define CRYPTOKI_GNU + +#include "pakchois11.h" + +/* API version: major is bumped for any backwards-incompatible + * changes. minor is bumped for any new interfaces. Note that the API + * is versioned independent of the project release version. */ +#define PAKCHOIS_API_MAJOR (0) +#define PAKCHOIS_API_MINOR (2) + +/* API version history (note that API versions do not map directly to + the project version!): + + 0.1: Initial release + 0.2: Addition of pakchois_error() + Concurrent access guarantee added for pakchois_module_load() + Thread-safety guarantee added for pakchois_wait_for_slot_event() +*/ + +typedef struct pakchois_module_s pakchois_module_t; +typedef struct pakchois_session_s pakchois_session_t; + +/* Load a PKCS#11 module by name (for example "opensc" or + * "gnome-keyring"). Returns CKR_OK on success. Any module of given + * name may be safely loaded multiple times within an application; the + * underlying PKCS#11 provider will be loaded only once. */ +ck_rv_t pakchois_module_load(pakchois_module_t **module, const char *name); + +/* Load an NSS "softokn" which violates the PKCS#11 standard in + * initialization, with given name (e.g. "softokn3"). The directory + * in which the NSS database resides must be specified; the other + * arguments may be NULL to use defaults. Returns CKR_OK on + * success. */ +ck_rv_t pakchois_module_nssload(pakchois_module_t **module, + const char *name, + const char *directory, + const char *cert_prefix, + const char *key_prefix, + const char *secmod_db); + +/* Destroy a PKCS#11 module. */ +void pakchois_module_destroy(pakchois_module_t *module); + +/* Return the error string corresponding to the given return value. + * Never returns NULL. */ +const char *pakchois_error(ck_rv_t rv); + +/* All following interfaces model the PKCS#11 equivalents, without the + camel-cased naming convention. The PKCS#11 specification has + detailed interface descriptions: + + http://www.rsa.com/rsalabs/node.asp?id=2133 + + The differences between this interface and PKCS#11 are: + + 1. some interfaces take a module pointer as first argument + + 2. session handlers are represented as opaque objects + + 3. the notify callback type has changed accordingly + + 4. the C_Initialize, C_Finalize, and C_GetFunctionList interfaces + are not exposed (these are called internally by + pakchois_module_load and pakchois_module_destroy) + + 5. pakchois_wait_for_slot_event() is thread-safe against other + callers of pakchois_wait_for_slot_event(); the call to the + underlying provider's WaitForSlotEvent function is protected by a + mutex. + + 6. pakchois_close_all_sessions() only closes sessions associated + with the given module instance; any sessions opened by other users + of the underlying provider are unaffected. + + If a module object is used concurrently from separate threads, + undefined behaviour results. If a session object is used + concurrently from separate threads, undefined behavioure results. + +*/ +ck_rv_t pakchois_get_info(pakchois_module_t *module, struct ck_info *info); + +ck_rv_t pakchois_get_slot_list(pakchois_module_t *module, + unsigned char token_present, + ck_slot_id_t *slot_list, + unsigned long *count); + +ck_rv_t pakchois_get_slot_info(pakchois_module_t *module, + ck_slot_id_t slot_id, + struct ck_slot_info *info); + +ck_rv_t pakchois_get_token_info(pakchois_module_t *module, + ck_slot_id_t slot_id, + struct ck_token_info *info); + +ck_rv_t pakchois_wait_for_slot_event(pakchois_module_t *module, + ck_flags_t flags, ck_slot_id_t *slot, + void *reserved); + +ck_rv_t pakchois_get_mechanism_list(pakchois_module_t *module, + ck_slot_id_t slot_id, + ck_mechanism_type_t *mechanism_list, + unsigned long *count); + +ck_rv_t pakchois_get_mechanism_info(pakchois_module_t *module, + ck_slot_id_t slot_id, + ck_mechanism_type_t type, + struct ck_mechanism_info *info); + +ck_rv_t pakchois_init_token(pakchois_module_t *module, + ck_slot_id_t slot_id, unsigned char *pin, + unsigned long pin_len, unsigned char *label); + +ck_rv_t pakchois_init_pin(pakchois_session_t *session, unsigned char *pin, + unsigned long pin_len); + +ck_rv_t pakchois_set_pin(pakchois_session_t *session, unsigned char *old_pin, + unsigned long old_len, unsigned char *new_pin, + unsigned long new_len); + +typedef ck_rv_t (*pakchois_notify_t) (pakchois_session_t *sess, + ck_notification_t event, + void *application); + +ck_rv_t pakchois_open_session(pakchois_module_t *module, + ck_slot_id_t slot_id, ck_flags_t flags, + void *application, pakchois_notify_t notify, + pakchois_session_t **session); + +ck_rv_t pakchois_close_session(pakchois_session_t *session); + +ck_rv_t pakchois_close_all_sessions(pakchois_module_t *module, + ck_slot_id_t slot_id); + +ck_rv_t pakchois_get_session_info(pakchois_session_t *session, + struct ck_session_info *info); +ck_rv_t pakchois_get_operation_state(pakchois_session_t *session, + unsigned char *operation_state, + unsigned long *operation_state_len); +ck_rv_t pakchois_set_operation_state(pakchois_session_t *session, + unsigned char *operation_state, + unsigned long operation_state_len, + ck_object_handle_t encryption_key, + ck_object_handle_t authentiation_key); + +ck_rv_t pakchois_login(pakchois_session_t *session, ck_user_type_t user_type, + unsigned char *pin, unsigned long pin_len); +ck_rv_t pakchois_logout(pakchois_session_t *session); + +ck_rv_t pakchois_create_object(pakchois_session_t *session, + struct ck_attribute *templ, + unsigned long count, + ck_object_handle_t *object); +ck_rv_t pakchois_copy_object(pakchois_session_t *session, + ck_object_handle_t object, + struct ck_attribute *templ, unsigned long count, + ck_object_handle_t *new_object); +ck_rv_t pakchois_destroy_object(pakchois_session_t *session, + ck_object_handle_t object); +ck_rv_t pakchois_get_object_size(pakchois_session_t *session, + ck_object_handle_t object, + unsigned long *size); + +ck_rv_t pakchois_get_attribute_value(pakchois_session_t *session, + ck_object_handle_t object, + struct ck_attribute *templ, + unsigned long count); +ck_rv_t pakchois_set_attribute_value(pakchois_session_t *session, + ck_object_handle_t object, + struct ck_attribute *templ, + unsigned long count); +ck_rv_t pakchois_find_objects_init(pakchois_session_t *session, + struct ck_attribute *templ, + unsigned long count); +ck_rv_t pakchois_find_objects(pakchois_session_t *session, + ck_object_handle_t *object, + unsigned long max_object_count, + unsigned long *object_count); +ck_rv_t pakchois_find_objects_final(pakchois_session_t *session); + +ck_rv_t pakchois_encrypt_init(pakchois_session_t *session, + struct ck_mechanism *mechanism, + ck_object_handle_t key); +ck_rv_t pakchois_encrypt(pakchois_session_t *session, + unsigned char *data, unsigned long data_len, + unsigned char *encrypted_data, + unsigned long *encrypted_data_len); +ck_rv_t pakchois_encrypt_update(pakchois_session_t *session, + unsigned char *part, unsigned long part_len, + unsigned char *encrypted_part, + unsigned long *encrypted_part_len); +ck_rv_t pakchois_encrypt_final(pakchois_session_t *session, + unsigned char *last_encrypted_part, + unsigned long *last_encrypted_part_len); + +ck_rv_t pakchois_decrypt_init(pakchois_session_t *session, + struct ck_mechanism *mechanism, + ck_object_handle_t key); +ck_rv_t pakchois_decrypt(pakchois_session_t *session, + unsigned char *encrypted_data, + unsigned long encrypted_data_len, + unsigned char *data, unsigned long *data_len); +ck_rv_t pakchois_decrypt_update(pakchois_session_t *session, + unsigned char *encrypted_part, + unsigned long encrypted_part_len, + unsigned char *part, unsigned long *part_len); +ck_rv_t pakchois_decrypt_final(pakchois_session_t *session, + unsigned char *last_part, + unsigned long *last_part_len); +ck_rv_t pakchois_digest_init(pakchois_session_t *session, + struct ck_mechanism *mechanism); +ck_rv_t pakchois_digest(pakchois_session_t *session, unsigned char *data, + unsigned long data_len, unsigned char *digest, + unsigned long *digest_len); +ck_rv_t pakchois_digest_update(pakchois_session_t *session, + unsigned char *part, unsigned long part_len); +ck_rv_t pakchois_digest_key(pakchois_session_t *session, + ck_object_handle_t key); +ck_rv_t pakchois_digest_final(pakchois_session_t *session, + unsigned char *digest, + unsigned long *digest_len); + +ck_rv_t pakchois_sign_init(pakchois_session_t *session, + struct ck_mechanism *mechanism, + ck_object_handle_t key); +ck_rv_t pakchois_sign(pakchois_session_t *session, unsigned char *data, + unsigned long data_len, unsigned char *signature, + unsigned long *signature_len); +ck_rv_t pakchois_sign_update(pakchois_session_t *session, + unsigned char *part, unsigned long part_len); +ck_rv_t pakchois_sign_final(pakchois_session_t *session, + unsigned char *signature, + unsigned long *signature_len); +ck_rv_t pakchois_sign_recover_init(pakchois_session_t *session, + struct ck_mechanism *mechanism, + ck_object_handle_t key); +ck_rv_t pakchois_sign_recover(pakchois_session_t *session, + unsigned char *data, unsigned long data_len, + unsigned char *signature, + unsigned long *signature_len); + +ck_rv_t pakchois_verify_init(pakchois_session_t *session, + struct ck_mechanism *mechanism, + ck_object_handle_t key); +ck_rv_t pakchois_verify(pakchois_session_t *session, unsigned char *data, + unsigned long data_len, unsigned char *signature, + unsigned long signature_len); +ck_rv_t pakchois_verify_update(pakchois_session_t *session, + unsigned char *part, unsigned long part_len); +ck_rv_t pakchois_verify_final(pakchois_session_t *session, + unsigned char *signature, + unsigned long signature_len); +ck_rv_t pakchois_verify_recover_init(pakchois_session_t *session, + struct ck_mechanism *mechanism, + ck_object_handle_t key); +ck_rv_t pakchois_verify_recover(pakchois_session_t *session, + unsigned char *signature, + unsigned long signature_len, + unsigned char *data, unsigned long *data_len); + +ck_rv_t pakchois_digest_encrypt_update(pakchois_session_t *session, + unsigned char *part, + unsigned long part_len, + unsigned char *encrypted_part, + unsigned long *encrypted_part_len); +ck_rv_t pakchois_decrypt_digest_update(pakchois_session_t *session, + unsigned char *encrypted_part, + unsigned long encrypted_part_len, + unsigned char *part, + unsigned long *part_len); +ck_rv_t pakchois_sign_encrypt_update(pakchois_session_t *session, + unsigned char *part, + unsigned long part_len, + unsigned char *encrypted_part, + unsigned long *encrypted_part_len); +ck_rv_t pakchois_decrypt_verify_update(pakchois_session_t *session, + unsigned char *encrypted_part, + unsigned long encrypted_part_len, + unsigned char *part, + unsigned long *part_len); + +ck_rv_t pakchois_generate_key(pakchois_session_t *session, + struct ck_mechanism *mechanism, + struct ck_attribute *templ, + unsigned long count, ck_object_handle_t *key); +ck_rv_t pakchois_generate_key_pair(pakchois_session_t *session, + struct ck_mechanism *mechanism, + struct ck_attribute *public_key_template, + unsigned long public_key_attribute_count, + struct ck_attribute *private_key_template, + unsigned long private_key_attribute_count, + ck_object_handle_t *public_key, + ck_object_handle_t *private_key); + +ck_rv_t pakchois_wrap_key(pakchois_session_t *session, + struct ck_mechanism *mechanism, + ck_object_handle_t wrapping_key, + ck_object_handle_t key, unsigned char *wrapped_key, + unsigned long *wrapped_key_len); +ck_rv_t pakchois_unwrap_key(pakchois_session_t *session, + struct ck_mechanism *mechanism, + ck_object_handle_t unwrapping_key, + unsigned char *wrapped_key, + unsigned long wrapped_key_len, + struct ck_attribute *templ, + unsigned long attribute_count, + ck_object_handle_t *key); +ck_rv_t pakchois_derive_key(pakchois_session_t *session, + struct ck_mechanism *mechanism, + ck_object_handle_t base_key, + struct ck_attribute *templ, + unsigned long attribute_count, + ck_object_handle_t *key); + +ck_rv_t pakchois_seed_random(pakchois_session_t *session, + unsigned char *seed, unsigned long seed_len); +ck_rv_t pakchois_generate_random(pakchois_session_t *session, + unsigned char *random_data, + unsigned long random_len); + +#endif /* PAKCHOIS_H */ diff --git a/lib/pakchois/pakchois11.h b/lib/pakchois/pakchois11.h new file mode 100644 index 0000000000..2e6a1e3ed3 --- /dev/null +++ b/lib/pakchois/pakchois11.h @@ -0,0 +1,1357 @@ +/* pkcs11.h + Copyright 2006, 2007 g10 Code GmbH + Copyright 2006 Andreas Jellinghaus + + This file is free software; as a special exception the author gives + unlimited permission to copy and/or distribute it, with or without + modifications, as long as this notice is preserved. + + This file is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY, to the extent permitted by law; without even + the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + PURPOSE. */ + +/* Please submit changes back to the Scute project at + http://www.scute.org/ (or send them to marcus@g10code.com), so that + they can be picked up by other projects from there as well. */ + +/* This file is a modified implementation of the PKCS #11 standard by + RSA Security Inc. It is mostly a drop-in replacement, with the + following change: + + This header file does not require any macro definitions by the user + (like CK_DEFINE_FUNCTION etc). In fact, it defines those macros + for you (if useful, some are missing, let me know if you need + more). + + There is an additional API available that does comply better to the + GNU coding standard. It can be switched on by defining + CRYPTOKI_GNU before including this header file. For this, the + following changes are made to the specification: + + All structure types are changed to a "struct ck_foo" where CK_FOO + is the type name in PKCS #11. + + All non-structure types are changed to ck_foo_t where CK_FOO is the + lowercase version of the type name in PKCS #11. The basic types + (CK_ULONG et al.) are removed without substitute. + + All members of structures are modified in the following way: Type + indication prefixes are removed, and underscore characters are + inserted before words. Then the result is lowercased. + + Note that function names are still in the original case, as they + need for ABI compatibility. + + CK_FALSE, CK_TRUE and NULL_PTR are removed without substitute. Use + . + + If CRYPTOKI_COMPAT is defined before including this header file, + then none of the API changes above take place, and the API is the + one defined by the PKCS #11 standard. */ + +#ifndef PKCS11_H +#define PKCS11_H 1 + +#if defined(__cplusplus) +extern "C" { +#endif + + +/* The version of cryptoki we implement. The revision is changed with + each modification of this file. If you do not use the "official" + version of this file, please consider deleting the revision macro + (you may use a macro with a different name to keep track of your + versions). */ +#define CRYPTOKI_VERSION_MAJOR 2 +#define CRYPTOKI_VERSION_MINOR 20 +#define CRYPTOKI_VERSION_REVISION 6 + + +/* Compatibility interface is default, unless CRYPTOKI_GNU is + given. */ +#ifndef CRYPTOKI_GNU +#ifndef CRYPTOKI_COMPAT +#define CRYPTOKI_COMPAT 1 +#endif +#endif + +/* System dependencies. */ + +#if defined(_WIN32) || defined(CRYPTOKI_FORCE_WIN32) + +/* There is a matching pop below. */ +#pragma pack(push, cryptoki, 1) + +#ifdef CRYPTOKI_EXPORTS +#define CK_SPEC __declspec(dllexport) +#else +#define CK_SPEC __declspec(dllimport) +#endif + +#else + +#define CK_SPEC + +#endif + + +#ifdef CRYPTOKI_COMPAT + /* If we are in compatibility mode, switch all exposed names to the + PKCS #11 variant. There are corresponding #undefs below. */ + +#define ck_flags_t CK_FLAGS +#define ck_version _CK_VERSION + +#define ck_info _CK_INFO +#define cryptoki_version cryptokiVersion +#define manufacturer_id manufacturerID +#define library_description libraryDescription +#define library_version libraryVersion + +#define ck_notification_t CK_NOTIFICATION +#define ck_slot_id_t CK_SLOT_ID + +#define ck_slot_info _CK_SLOT_INFO +#define slot_description slotDescription +#define hardware_version hardwareVersion +#define firmware_version firmwareVersion + +#define ck_token_info _CK_TOKEN_INFO +#define serial_number serialNumber +#define max_session_count ulMaxSessionCount +#define session_count ulSessionCount +#define max_rw_session_count ulMaxRwSessionCount +#define rw_session_count ulRwSessionCount +#define max_pin_len ulMaxPinLen +#define min_pin_len ulMinPinLen +#define total_public_memory ulTotalPublicMemory +#define free_public_memory ulFreePublicMemory +#define total_private_memory ulTotalPrivateMemory +#define free_private_memory ulFreePrivateMemory +#define utc_time utcTime + +#define ck_session_handle_t CK_SESSION_HANDLE +#define ck_user_type_t CK_USER_TYPE +#define ck_state_t CK_STATE + +#define ck_session_info _CK_SESSION_INFO +#define slot_id slotID +#define device_error ulDeviceError + +#define ck_object_handle_t CK_OBJECT_HANDLE +#define ck_object_class_t CK_OBJECT_CLASS +#define ck_hw_feature_type_t CK_HW_FEATURE_TYPE +#define ck_key_type_t CK_KEY_TYPE +#define ck_certificate_type_t CK_CERTIFICATE_TYPE +#define ck_attribute_type_t CK_ATTRIBUTE_TYPE + +#define ck_attribute _CK_ATTRIBUTE +#define value pValue +#define value_len ulValueLen + +#define ck_date _CK_DATE + +#define ck_mechanism_type_t CK_MECHANISM_TYPE + +#define ck_mechanism _CK_MECHANISM +#define parameter pParameter +#define parameter_len ulParameterLen + +#define ck_mechanism_info _CK_MECHANISM_INFO +#define min_key_size ulMinKeySize +#define max_key_size ulMaxKeySize + +#define ck_rv_t CK_RV +#define ck_notify_t CK_NOTIFY + +#define ck_function_list _CK_FUNCTION_LIST + +#define ck_createmutex_t CK_CREATEMUTEX +#define ck_destroymutex_t CK_DESTROYMUTEX +#define ck_lockmutex_t CK_LOCKMUTEX +#define ck_unlockmutex_t CK_UNLOCKMUTEX + +#define ck_c_initialize_args _CK_C_INITIALIZE_ARGS +#define create_mutex CreateMutex +#define destroy_mutex DestroyMutex +#define lock_mutex LockMutex +#define unlock_mutex UnlockMutex +#define reserved pReserved + +#endif /* CRYPTOKI_COMPAT */ + + + +typedef unsigned long ck_flags_t; + +struct ck_version +{ + unsigned char major; + unsigned char minor; +}; + + +struct ck_info +{ + struct ck_version cryptoki_version; + unsigned char manufacturer_id[32]; + ck_flags_t flags; + unsigned char library_description[32]; + struct ck_version library_version; +}; + + +typedef unsigned long ck_notification_t; + +#define CKN_SURRENDER (0) + + +typedef unsigned long ck_slot_id_t; + + +struct ck_slot_info +{ + unsigned char slot_description[64]; + unsigned char manufacturer_id[32]; + ck_flags_t flags; + struct ck_version hardware_version; + struct ck_version firmware_version; +}; + + +#define CKF_TOKEN_PRESENT (1 << 0) +#define CKF_REMOVABLE_DEVICE (1 << 1) +#define CKF_HW_SLOT (1 << 2) +#define CKF_ARRAY_ATTRIBUTE (1 << 30) + + +struct ck_token_info +{ + unsigned char label[32]; + unsigned char manufacturer_id[32]; + unsigned char model[16]; + unsigned char serial_number[16]; + ck_flags_t flags; + unsigned long max_session_count; + unsigned long session_count; + unsigned long max_rw_session_count; + unsigned long rw_session_count; + unsigned long max_pin_len; + unsigned long min_pin_len; + unsigned long total_public_memory; + unsigned long free_public_memory; + unsigned long total_private_memory; + unsigned long free_private_memory; + struct ck_version hardware_version; + struct ck_version firmware_version; + unsigned char utc_time[16]; +}; + + +#define CKF_RNG (1 << 0) +#define CKF_WRITE_PROTECTED (1 << 1) +#define CKF_LOGIN_REQUIRED (1 << 2) +#define CKF_USER_PIN_INITIALIZED (1 << 3) +#define CKF_RESTORE_KEY_NOT_NEEDED (1 << 5) +#define CKF_CLOCK_ON_TOKEN (1 << 6) +#define CKF_PROTECTED_AUTHENTICATION_PATH (1 << 8) +#define CKF_DUAL_CRYPTO_OPERATIONS (1 << 9) +#define CKF_TOKEN_INITIALIZED (1 << 10) +#define CKF_SECONDARY_AUTHENTICATION (1 << 11) +#define CKF_USER_PIN_COUNT_LOW (1 << 16) +#define CKF_USER_PIN_FINAL_TRY (1 << 17) +#define CKF_USER_PIN_LOCKED (1 << 18) +#define CKF_USER_PIN_TO_BE_CHANGED (1 << 19) +#define CKF_SO_PIN_COUNT_LOW (1 << 20) +#define CKF_SO_PIN_FINAL_TRY (1 << 21) +#define CKF_SO_PIN_LOCKED (1 << 22) +#define CKF_SO_PIN_TO_BE_CHANGED (1 << 23) + +#define CK_UNAVAILABLE_INFORMATION ((unsigned long) -1) +#define CK_EFFECTIVELY_INFINITE (0) + + +typedef unsigned long ck_session_handle_t; + +#define CK_INVALID_HANDLE (0) + + +typedef unsigned long ck_user_type_t; + +#define CKU_SO (0) +#define CKU_USER (1) +#define CKU_CONTEXT_SPECIFIC (2) + + +typedef unsigned long ck_state_t; + +#define CKS_RO_PUBLIC_SESSION (0) +#define CKS_RO_USER_FUNCTIONS (1) +#define CKS_RW_PUBLIC_SESSION (2) +#define CKS_RW_USER_FUNCTIONS (3) +#define CKS_RW_SO_FUNCTIONS (4) + + +struct ck_session_info +{ + ck_slot_id_t slot_id; + ck_state_t state; + ck_flags_t flags; + unsigned long device_error; +}; + +#define CKF_RW_SESSION (1 << 1) +#define CKF_SERIAL_SESSION (1 << 2) + + +typedef unsigned long ck_object_handle_t; + + +typedef unsigned long ck_object_class_t; + +#define CKO_DATA (0) +#define CKO_CERTIFICATE (1) +#define CKO_PUBLIC_KEY (2) +#define CKO_PRIVATE_KEY (3) +#define CKO_SECRET_KEY (4) +#define CKO_HW_FEATURE (5) +#define CKO_DOMAIN_PARAMETERS (6) +#define CKO_MECHANISM (7) +#define CKO_VENDOR_DEFINED ((unsigned long) (1 << 31)) + + +typedef unsigned long ck_hw_feature_type_t; + +#define CKH_MONOTONIC_COUNTER (1) +#define CKH_CLOCK (2) +#define CKH_USER_INTERFACE (3) +#define CKH_VENDOR_DEFINED ((unsigned long) (1 << 31)) + + +typedef unsigned long ck_key_type_t; + +#define CKK_RSA (0) +#define CKK_DSA (1) +#define CKK_DH (2) +#define CKK_ECDSA (3) +#define CKK_EC (3) +#define CKK_X9_42_DH (4) +#define CKK_KEA (5) +#define CKK_GENERIC_SECRET (0x10) +#define CKK_RC2 (0x11) +#define CKK_RC4 (0x12) +#define CKK_DES (0x13) +#define CKK_DES2 (0x14) +#define CKK_DES3 (0x15) +#define CKK_CAST (0x16) +#define CKK_CAST3 (0x17) +#define CKK_CAST128 (0x18) +#define CKK_RC5 (0x19) +#define CKK_IDEA (0x1a) +#define CKK_SKIPJACK (0x1b) +#define CKK_BATON (0x1c) +#define CKK_JUNIPER (0x1d) +#define CKK_CDMF (0x1e) +#define CKK_AES (0x1f) +#define CKK_BLOWFISH (0x20) +#define CKK_TWOFISH (0x21) +#define CKK_VENDOR_DEFINED ((unsigned long) (1 << 31)) + + +typedef unsigned long ck_certificate_type_t; + +#define CKC_X_509 (0) +#define CKC_X_509_ATTR_CERT (1) +#define CKC_WTLS (2) +#define CKC_VENDOR_DEFINED ((unsigned long) (1 << 31)) + + +typedef unsigned long ck_attribute_type_t; + +#define CKA_CLASS (0) +#define CKA_TOKEN (1) +#define CKA_PRIVATE (2) +#define CKA_LABEL (3) +#define CKA_APPLICATION (0x10) +#define CKA_VALUE (0x11) +#define CKA_OBJECT_ID (0x12) +#define CKA_CERTIFICATE_TYPE (0x80) +#define CKA_ISSUER (0x81) +#define CKA_SERIAL_NUMBER (0x82) +#define CKA_AC_ISSUER (0x83) +#define CKA_OWNER (0x84) +#define CKA_ATTR_TYPES (0x85) +#define CKA_TRUSTED (0x86) +#define CKA_CERTIFICATE_CATEGORY (0x87) +#define CKA_JAVA_MIDP_SECURITY_DOMAIN (0x88) +#define CKA_URL (0x89) +#define CKA_HASH_OF_SUBJECT_PUBLIC_KEY (0x8a) +#define CKA_HASH_OF_ISSUER_PUBLIC_KEY (0x8b) +#define CKA_CHECK_VALUE (0x90) +#define CKA_KEY_TYPE (0x100) +#define CKA_SUBJECT (0x101) +#define CKA_ID (0x102) +#define CKA_SENSITIVE (0x103) +#define CKA_ENCRYPT (0x104) +#define CKA_DECRYPT (0x105) +#define CKA_WRAP (0x106) +#define CKA_UNWRAP (0x107) +#define CKA_SIGN (0x108) +#define CKA_SIGN_RECOVER (0x109) +#define CKA_VERIFY (0x10a) +#define CKA_VERIFY_RECOVER (0x10b) +#define CKA_DERIVE (0x10c) +#define CKA_START_DATE (0x110) +#define CKA_END_DATE (0x111) +#define CKA_MODULUS (0x120) +#define CKA_MODULUS_BITS (0x121) +#define CKA_PUBLIC_EXPONENT (0x122) +#define CKA_PRIVATE_EXPONENT (0x123) +#define CKA_PRIME_1 (0x124) +#define CKA_PRIME_2 (0x125) +#define CKA_EXPONENT_1 (0x126) +#define CKA_EXPONENT_2 (0x127) +#define CKA_COEFFICIENT (0x128) +#define CKA_PRIME (0x130) +#define CKA_SUBPRIME (0x131) +#define CKA_BASE (0x132) +#define CKA_PRIME_BITS (0x133) +#define CKA_SUB_PRIME_BITS (0x134) +#define CKA_VALUE_BITS (0x160) +#define CKA_VALUE_LEN (0x161) +#define CKA_EXTRACTABLE (0x162) +#define CKA_LOCAL (0x163) +#define CKA_NEVER_EXTRACTABLE (0x164) +#define CKA_ALWAYS_SENSITIVE (0x165) +#define CKA_KEY_GEN_MECHANISM (0x166) +#define CKA_MODIFIABLE (0x170) +#define CKA_ECDSA_PARAMS (0x180) +#define CKA_EC_PARAMS (0x180) +#define CKA_EC_POINT (0x181) +#define CKA_SECONDARY_AUTH (0x200) +#define CKA_AUTH_PIN_FLAGS (0x201) +#define CKA_ALWAYS_AUTHENTICATE (0x202) +#define CKA_WRAP_WITH_TRUSTED (0x210) +#define CKA_HW_FEATURE_TYPE (0x300) +#define CKA_RESET_ON_INIT (0x301) +#define CKA_HAS_RESET (0x302) +#define CKA_PIXEL_X (0x400) +#define CKA_PIXEL_Y (0x401) +#define CKA_RESOLUTION (0x402) +#define CKA_CHAR_ROWS (0x403) +#define CKA_CHAR_COLUMNS (0x404) +#define CKA_COLOR (0x405) +#define CKA_BITS_PER_PIXEL (0x406) +#define CKA_CHAR_SETS (0x480) +#define CKA_ENCODING_METHODS (0x481) +#define CKA_MIME_TYPES (0x482) +#define CKA_MECHANISM_TYPE (0x500) +#define CKA_REQUIRED_CMS_ATTRIBUTES (0x501) +#define CKA_DEFAULT_CMS_ATTRIBUTES (0x502) +#define CKA_SUPPORTED_CMS_ATTRIBUTES (0x503) +#define CKA_WRAP_TEMPLATE (CKF_ARRAY_ATTRIBUTE | 0x211) +#define CKA_UNWRAP_TEMPLATE (CKF_ARRAY_ATTRIBUTE | 0x212) +#define CKA_ALLOWED_MECHANISMS (CKF_ARRAY_ATTRIBUTE | 0x600) +#define CKA_VENDOR_DEFINED ((unsigned long) (1 << 31)) + + +struct ck_attribute +{ + ck_attribute_type_t type; + void *value; + unsigned long value_len; +}; + + +struct ck_date +{ + unsigned char year[4]; + unsigned char month[2]; + unsigned char day[2]; +}; + + +typedef unsigned long ck_mechanism_type_t; + +#define CKM_RSA_PKCS_KEY_PAIR_GEN (0) +#define CKM_RSA_PKCS (1) +#define CKM_RSA_9796 (2) +#define CKM_RSA_X_509 (3) +#define CKM_MD2_RSA_PKCS (4) +#define CKM_MD5_RSA_PKCS (5) +#define CKM_SHA1_RSA_PKCS (6) +#define CKM_RIPEMD128_RSA_PKCS (7) +#define CKM_RIPEMD160_RSA_PKCS (8) +#define CKM_RSA_PKCS_OAEP (9) +#define CKM_RSA_X9_31_KEY_PAIR_GEN (0xa) +#define CKM_RSA_X9_31 (0xb) +#define CKM_SHA1_RSA_X9_31 (0xc) +#define CKM_RSA_PKCS_PSS (0xd) +#define CKM_SHA1_RSA_PKCS_PSS (0xe) +#define CKM_DSA_KEY_PAIR_GEN (0x10) +#define CKM_DSA (0x11) +#define CKM_DSA_SHA1 (0x12) +#define CKM_DH_PKCS_KEY_PAIR_GEN (0x20) +#define CKM_DH_PKCS_DERIVE (0x21) +#define CKM_X9_42_DH_KEY_PAIR_GEN (0x30) +#define CKM_X9_42_DH_DERIVE (0x31) +#define CKM_X9_42_DH_HYBRID_DERIVE (0x32) +#define CKM_X9_42_MQV_DERIVE (0x33) +#define CKM_SHA256_RSA_PKCS (0x40) +#define CKM_SHA384_RSA_PKCS (0x41) +#define CKM_SHA512_RSA_PKCS (0x42) +#define CKM_SHA256_RSA_PKCS_PSS (0x43) +#define CKM_SHA384_RSA_PKCS_PSS (0x44) +#define CKM_SHA512_RSA_PKCS_PSS (0x45) +#define CKM_RC2_KEY_GEN (0x100) +#define CKM_RC2_ECB (0x101) +#define CKM_RC2_CBC (0x102) +#define CKM_RC2_MAC (0x103) +#define CKM_RC2_MAC_GENERAL (0x104) +#define CKM_RC2_CBC_PAD (0x105) +#define CKM_RC4_KEY_GEN (0x110) +#define CKM_RC4 (0x111) +#define CKM_DES_KEY_GEN (0x120) +#define CKM_DES_ECB (0x121) +#define CKM_DES_CBC (0x122) +#define CKM_DES_MAC (0x123) +#define CKM_DES_MAC_GENERAL (0x124) +#define CKM_DES_CBC_PAD (0x125) +#define CKM_DES2_KEY_GEN (0x130) +#define CKM_DES3_KEY_GEN (0x131) +#define CKM_DES3_ECB (0x132) +#define CKM_DES3_CBC (0x133) +#define CKM_DES3_MAC (0x134) +#define CKM_DES3_MAC_GENERAL (0x135) +#define CKM_DES3_CBC_PAD (0x136) +#define CKM_CDMF_KEY_GEN (0x140) +#define CKM_CDMF_ECB (0x141) +#define CKM_CDMF_CBC (0x142) +#define CKM_CDMF_MAC (0x143) +#define CKM_CDMF_MAC_GENERAL (0x144) +#define CKM_CDMF_CBC_PAD (0x145) +#define CKM_MD2 (0x200) +#define CKM_MD2_HMAC (0x201) +#define CKM_MD2_HMAC_GENERAL (0x202) +#define CKM_MD5 (0x210) +#define CKM_MD5_HMAC (0x211) +#define CKM_MD5_HMAC_GENERAL (0x212) +#define CKM_SHA_1 (0x220) +#define CKM_SHA_1_HMAC (0x221) +#define CKM_SHA_1_HMAC_GENERAL (0x222) +#define CKM_RIPEMD128 (0x230) +#define CKM_RIPEMD128_HMAC (0x231) +#define CKM_RIPEMD128_HMAC_GENERAL (0x232) +#define CKM_RIPEMD160 (0x240) +#define CKM_RIPEMD160_HMAC (0x241) +#define CKM_RIPEMD160_HMAC_GENERAL (0x242) +#define CKM_SHA256 (0x250) +#define CKM_SHA256_HMAC (0x251) +#define CKM_SHA256_HMAC_GENERAL (0x252) +#define CKM_SHA384 (0x260) +#define CKM_SHA384_HMAC (0x261) +#define CKM_SHA384_HMAC_GENERAL (0x262) +#define CKM_SHA512 (0x270) +#define CKM_SHA512_HMAC (0x271) +#define CKM_SHA512_HMAC_GENERAL (0x272) +#define CKM_CAST_KEY_GEN (0x300) +#define CKM_CAST_ECB (0x301) +#define CKM_CAST_CBC (0x302) +#define CKM_CAST_MAC (0x303) +#define CKM_CAST_MAC_GENERAL (0x304) +#define CKM_CAST_CBC_PAD (0x305) +#define CKM_CAST3_KEY_GEN (0x310) +#define CKM_CAST3_ECB (0x311) +#define CKM_CAST3_CBC (0x312) +#define CKM_CAST3_MAC (0x313) +#define CKM_CAST3_MAC_GENERAL (0x314) +#define CKM_CAST3_CBC_PAD (0x315) +#define CKM_CAST5_KEY_GEN (0x320) +#define CKM_CAST128_KEY_GEN (0x320) +#define CKM_CAST5_ECB (0x321) +#define CKM_CAST128_ECB (0x321) +#define CKM_CAST5_CBC (0x322) +#define CKM_CAST128_CBC (0x322) +#define CKM_CAST5_MAC (0x323) +#define CKM_CAST128_MAC (0x323) +#define CKM_CAST5_MAC_GENERAL (0x324) +#define CKM_CAST128_MAC_GENERAL (0x324) +#define CKM_CAST5_CBC_PAD (0x325) +#define CKM_CAST128_CBC_PAD (0x325) +#define CKM_RC5_KEY_GEN (0x330) +#define CKM_RC5_ECB (0x331) +#define CKM_RC5_CBC (0x332) +#define CKM_RC5_MAC (0x333) +#define CKM_RC5_MAC_GENERAL (0x334) +#define CKM_RC5_CBC_PAD (0x335) +#define CKM_IDEA_KEY_GEN (0x340) +#define CKM_IDEA_ECB (0x341) +#define CKM_IDEA_CBC (0x342) +#define CKM_IDEA_MAC (0x343) +#define CKM_IDEA_MAC_GENERAL (0x344) +#define CKM_IDEA_CBC_PAD (0x345) +#define CKM_GENERIC_SECRET_KEY_GEN (0x350) +#define CKM_CONCATENATE_BASE_AND_KEY (0x360) +#define CKM_CONCATENATE_BASE_AND_DATA (0x362) +#define CKM_CONCATENATE_DATA_AND_BASE (0x363) +#define CKM_XOR_BASE_AND_DATA (0x364) +#define CKM_EXTRACT_KEY_FROM_KEY (0x365) +#define CKM_SSL3_PRE_MASTER_KEY_GEN (0x370) +#define CKM_SSL3_MASTER_KEY_DERIVE (0x371) +#define CKM_SSL3_KEY_AND_MAC_DERIVE (0x372) +#define CKM_SSL3_MASTER_KEY_DERIVE_DH (0x373) +#define CKM_TLS_PRE_MASTER_KEY_GEN (0x374) +#define CKM_TLS_MASTER_KEY_DERIVE (0x375) +#define CKM_TLS_KEY_AND_MAC_DERIVE (0x376) +#define CKM_TLS_MASTER_KEY_DERIVE_DH (0x377) +#define CKM_SSL3_MD5_MAC (0x380) +#define CKM_SSL3_SHA1_MAC (0x381) +#define CKM_MD5_KEY_DERIVATION (0x390) +#define CKM_MD2_KEY_DERIVATION (0x391) +#define CKM_SHA1_KEY_DERIVATION (0x392) +#define CKM_PBE_MD2_DES_CBC (0x3a0) +#define CKM_PBE_MD5_DES_CBC (0x3a1) +#define CKM_PBE_MD5_CAST_CBC (0x3a2) +#define CKM_PBE_MD5_CAST3_CBC (0x3a3) +#define CKM_PBE_MD5_CAST5_CBC (0x3a4) +#define CKM_PBE_MD5_CAST128_CBC (0x3a4) +#define CKM_PBE_SHA1_CAST5_CBC (0x3a5) +#define CKM_PBE_SHA1_CAST128_CBC (0x3a5) +#define CKM_PBE_SHA1_RC4_128 (0x3a6) +#define CKM_PBE_SHA1_RC4_40 (0x3a7) +#define CKM_PBE_SHA1_DES3_EDE_CBC (0x3a8) +#define CKM_PBE_SHA1_DES2_EDE_CBC (0x3a9) +#define CKM_PBE_SHA1_RC2_128_CBC (0x3aa) +#define CKM_PBE_SHA1_RC2_40_CBC (0x3ab) +#define CKM_PKCS5_PBKD2 (0x3b0) +#define CKM_PBA_SHA1_WITH_SHA1_HMAC (0x3c0) +#define CKM_KEY_WRAP_LYNKS (0x400) +#define CKM_KEY_WRAP_SET_OAEP (0x401) +#define CKM_SKIPJACK_KEY_GEN (0x1000) +#define CKM_SKIPJACK_ECB64 (0x1001) +#define CKM_SKIPJACK_CBC64 (0x1002) +#define CKM_SKIPJACK_OFB64 (0x1003) +#define CKM_SKIPJACK_CFB64 (0x1004) +#define CKM_SKIPJACK_CFB32 (0x1005) +#define CKM_SKIPJACK_CFB16 (0x1006) +#define CKM_SKIPJACK_CFB8 (0x1007) +#define CKM_SKIPJACK_WRAP (0x1008) +#define CKM_SKIPJACK_PRIVATE_WRAP (0x1009) +#define CKM_SKIPJACK_RELAYX (0x100a) +#define CKM_KEA_KEY_PAIR_GEN (0x1010) +#define CKM_KEA_KEY_DERIVE (0x1011) +#define CKM_FORTEZZA_TIMESTAMP (0x1020) +#define CKM_BATON_KEY_GEN (0x1030) +#define CKM_BATON_ECB128 (0x1031) +#define CKM_BATON_ECB96 (0x1032) +#define CKM_BATON_CBC128 (0x1033) +#define CKM_BATON_COUNTER (0x1034) +#define CKM_BATON_SHUFFLE (0x1035) +#define CKM_BATON_WRAP (0x1036) +#define CKM_ECDSA_KEY_PAIR_GEN (0x1040) +#define CKM_EC_KEY_PAIR_GEN (0x1040) +#define CKM_ECDSA (0x1041) +#define CKM_ECDSA_SHA1 (0x1042) +#define CKM_ECDH1_DERIVE (0x1050) +#define CKM_ECDH1_COFACTOR_DERIVE (0x1051) +#define CKM_ECMQV_DERIVE (0x1052) +#define CKM_JUNIPER_KEY_GEN (0x1060) +#define CKM_JUNIPER_ECB128 (0x1061) +#define CKM_JUNIPER_CBC128 (0x1062) +#define CKM_JUNIPER_COUNTER (0x1063) +#define CKM_JUNIPER_SHUFFLE (0x1064) +#define CKM_JUNIPER_WRAP (0x1065) +#define CKM_FASTHASH (0x1070) +#define CKM_AES_KEY_GEN (0x1080) +#define CKM_AES_ECB (0x1081) +#define CKM_AES_CBC (0x1082) +#define CKM_AES_MAC (0x1083) +#define CKM_AES_MAC_GENERAL (0x1084) +#define CKM_AES_CBC_PAD (0x1085) +#define CKM_DSA_PARAMETER_GEN (0x2000) +#define CKM_DH_PKCS_PARAMETER_GEN (0x2001) +#define CKM_X9_42_DH_PARAMETER_GEN (0x2002) +#define CKM_VENDOR_DEFINED ((unsigned long) (1 << 31)) + + +struct ck_mechanism +{ + ck_mechanism_type_t mechanism; + void *parameter; + unsigned long parameter_len; +}; + + +struct ck_mechanism_info +{ + unsigned long min_key_size; + unsigned long max_key_size; + ck_flags_t flags; +}; + +#define CKF_HW (1 << 0) +#define CKF_ENCRYPT (1 << 8) +#define CKF_DECRYPT (1 << 9) +#define CKF_DIGEST (1 << 10) +#define CKF_SIGN (1 << 11) +#define CKF_SIGN_RECOVER (1 << 12) +#define CKF_VERIFY (1 << 13) +#define CKF_VERIFY_RECOVER (1 << 14) +#define CKF_GENERATE (1 << 15) +#define CKF_GENERATE_KEY_PAIR (1 << 16) +#define CKF_WRAP (1 << 17) +#define CKF_UNWRAP (1 << 18) +#define CKF_DERIVE (1 << 19) +#define CKF_EXTENSION ((unsigned long) (1 << 31)) + + +/* Flags for C_WaitForSlotEvent. */ +#define CKF_DONT_BLOCK (1) + + +typedef unsigned long ck_rv_t; + + +typedef ck_rv_t (*ck_notify_t) (ck_session_handle_t session, + ck_notification_t event, void *application); + +/* Forward reference. */ +struct ck_function_list; + +#define _CK_DECLARE_FUNCTION(name, args) \ +typedef ck_rv_t (*CK_ ## name) args; \ +ck_rv_t CK_SPEC name args + +_CK_DECLARE_FUNCTION (C_Initialize, (void *init_args)); +_CK_DECLARE_FUNCTION (C_Finalize, (void *reserved)); +_CK_DECLARE_FUNCTION (C_GetInfo, (struct ck_info *info)); +_CK_DECLARE_FUNCTION (C_GetFunctionList, + (struct ck_function_list **function_list)); + +_CK_DECLARE_FUNCTION (C_GetSlotList, + (unsigned char token_present, ck_slot_id_t *slot_list, + unsigned long *count)); +_CK_DECLARE_FUNCTION (C_GetSlotInfo, + (ck_slot_id_t slot_id, struct ck_slot_info *info)); +_CK_DECLARE_FUNCTION (C_GetTokenInfo, + (ck_slot_id_t slot_id, struct ck_token_info *info)); +_CK_DECLARE_FUNCTION (C_WaitForSlotEvent, + (ck_flags_t flags, ck_slot_id_t *slot, void *reserved)); +_CK_DECLARE_FUNCTION (C_GetMechanismList, + (ck_slot_id_t slot_id, + ck_mechanism_type_t *mechanism_list, + unsigned long *count)); +_CK_DECLARE_FUNCTION (C_GetMechanismInfo, + (ck_slot_id_t slot_id, ck_mechanism_type_t type, + struct ck_mechanism_info *info)); +_CK_DECLARE_FUNCTION (C_InitToken, + (ck_slot_id_t slot_id, unsigned char *pin, + unsigned long pin_len, unsigned char *label)); +_CK_DECLARE_FUNCTION (C_InitPIN, + (ck_session_handle_t session, unsigned char *pin, + unsigned long pin_len)); +_CK_DECLARE_FUNCTION (C_SetPIN, + (ck_session_handle_t session, unsigned char *old_pin, + unsigned long old_len, unsigned char *new_pin, + unsigned long new_len)); + +_CK_DECLARE_FUNCTION (C_OpenSession, + (ck_slot_id_t slot_id, ck_flags_t flags, + void *application, ck_notify_t notify, + ck_session_handle_t *session)); +_CK_DECLARE_FUNCTION (C_CloseSession, (ck_session_handle_t session)); +_CK_DECLARE_FUNCTION (C_CloseAllSessions, (ck_slot_id_t slot_id)); +_CK_DECLARE_FUNCTION (C_GetSessionInfo, + (ck_session_handle_t session, + struct ck_session_info *info)); +_CK_DECLARE_FUNCTION (C_GetOperationState, + (ck_session_handle_t session, + unsigned char *operation_state, + unsigned long *operation_state_len)); +_CK_DECLARE_FUNCTION (C_SetOperationState, + (ck_session_handle_t session, + unsigned char *operation_state, + unsigned long operation_state_len, + ck_object_handle_t encryption_key, + ck_object_handle_t authentiation_key)); +_CK_DECLARE_FUNCTION (C_Login, + (ck_session_handle_t session, ck_user_type_t user_type, + unsigned char *pin, unsigned long pin_len)); +_CK_DECLARE_FUNCTION (C_Logout, (ck_session_handle_t session)); + +_CK_DECLARE_FUNCTION (C_CreateObject, + (ck_session_handle_t session, + struct ck_attribute *templ, + unsigned long count, ck_object_handle_t *object)); +_CK_DECLARE_FUNCTION (C_CopyObject, + (ck_session_handle_t session, ck_object_handle_t object, + struct ck_attribute *templ, unsigned long count, + ck_object_handle_t *new_object)); +_CK_DECLARE_FUNCTION (C_DestroyObject, + (ck_session_handle_t session, + ck_object_handle_t object)); +_CK_DECLARE_FUNCTION (C_GetObjectSize, + (ck_session_handle_t session, + ck_object_handle_t object, + unsigned long *size)); +_CK_DECLARE_FUNCTION (C_GetAttributeValue, + (ck_session_handle_t session, + ck_object_handle_t object, + struct ck_attribute *templ, + unsigned long count)); +_CK_DECLARE_FUNCTION (C_SetAttributeValue, + (ck_session_handle_t session, + ck_object_handle_t object, + struct ck_attribute *templ, + unsigned long count)); +_CK_DECLARE_FUNCTION (C_FindObjectsInit, + (ck_session_handle_t session, + struct ck_attribute *templ, + unsigned long count)); +_CK_DECLARE_FUNCTION (C_FindObjects, + (ck_session_handle_t session, + ck_object_handle_t *object, + unsigned long max_object_count, + unsigned long *object_count)); +_CK_DECLARE_FUNCTION (C_FindObjectsFinal, + (ck_session_handle_t session)); + +_CK_DECLARE_FUNCTION (C_EncryptInit, + (ck_session_handle_t session, + struct ck_mechanism *mechanism, + ck_object_handle_t key)); +_CK_DECLARE_FUNCTION (C_Encrypt, + (ck_session_handle_t session, + unsigned char *data, unsigned long data_len, + unsigned char *encrypted_data, + unsigned long *encrypted_data_len)); +_CK_DECLARE_FUNCTION (C_EncryptUpdate, + (ck_session_handle_t session, + unsigned char *part, unsigned long part_len, + unsigned char *encrypted_part, + unsigned long *encrypted_part_len)); +_CK_DECLARE_FUNCTION (C_EncryptFinal, + (ck_session_handle_t session, + unsigned char *last_encrypted_part, + unsigned long *last_encrypted_part_len)); + +_CK_DECLARE_FUNCTION (C_DecryptInit, + (ck_session_handle_t session, + struct ck_mechanism *mechanism, + ck_object_handle_t key)); +_CK_DECLARE_FUNCTION (C_Decrypt, + (ck_session_handle_t session, + unsigned char *encrypted_data, + unsigned long encrypted_data_len, + unsigned char *data, unsigned long *data_len)); +_CK_DECLARE_FUNCTION (C_DecryptUpdate, + (ck_session_handle_t session, + unsigned char *encrypted_part, + unsigned long encrypted_part_len, + unsigned char *part, unsigned long *part_len)); +_CK_DECLARE_FUNCTION (C_DecryptFinal, + (ck_session_handle_t session, + unsigned char *last_part, + unsigned long *last_part_len)); + +_CK_DECLARE_FUNCTION (C_DigestInit, + (ck_session_handle_t session, + struct ck_mechanism *mechanism)); +_CK_DECLARE_FUNCTION (C_Digest, + (ck_session_handle_t session, + unsigned char *data, unsigned long data_len, + unsigned char *digest, + unsigned long *digest_len)); +_CK_DECLARE_FUNCTION (C_DigestUpdate, + (ck_session_handle_t session, + unsigned char *part, unsigned long part_len)); +_CK_DECLARE_FUNCTION (C_DigestKey, + (ck_session_handle_t session, ck_object_handle_t key)); +_CK_DECLARE_FUNCTION (C_DigestFinal, + (ck_session_handle_t session, + unsigned char *digest, + unsigned long *digest_len)); + +_CK_DECLARE_FUNCTION (C_SignInit, + (ck_session_handle_t session, + struct ck_mechanism *mechanism, + ck_object_handle_t key)); +_CK_DECLARE_FUNCTION (C_Sign, + (ck_session_handle_t session, + unsigned char *data, unsigned long data_len, + unsigned char *signature, + unsigned long *signature_len)); +_CK_DECLARE_FUNCTION (C_SignUpdate, + (ck_session_handle_t session, + unsigned char *part, unsigned long part_len)); +_CK_DECLARE_FUNCTION (C_SignFinal, + (ck_session_handle_t session, + unsigned char *signature, + unsigned long *signature_len)); +_CK_DECLARE_FUNCTION (C_SignRecoverInit, + (ck_session_handle_t session, + struct ck_mechanism *mechanism, + ck_object_handle_t key)); +_CK_DECLARE_FUNCTION (C_SignRecover, + (ck_session_handle_t session, + unsigned char *data, unsigned long data_len, + unsigned char *signature, + unsigned long *signature_len)); + +_CK_DECLARE_FUNCTION (C_VerifyInit, + (ck_session_handle_t session, + struct ck_mechanism *mechanism, + ck_object_handle_t key)); +_CK_DECLARE_FUNCTION (C_Verify, + (ck_session_handle_t session, + unsigned char *data, unsigned long data_len, + unsigned char *signature, + unsigned long signature_len)); +_CK_DECLARE_FUNCTION (C_VerifyUpdate, + (ck_session_handle_t session, + unsigned char *part, unsigned long part_len)); +_CK_DECLARE_FUNCTION (C_VerifyFinal, + (ck_session_handle_t session, + unsigned char *signature, + unsigned long signature_len)); +_CK_DECLARE_FUNCTION (C_VerifyRecoverInit, + (ck_session_handle_t session, + struct ck_mechanism *mechanism, + ck_object_handle_t key)); +_CK_DECLARE_FUNCTION (C_VerifyRecover, + (ck_session_handle_t session, + unsigned char *signature, + unsigned long signature_len, + unsigned char *data, + unsigned long *data_len)); + +_CK_DECLARE_FUNCTION (C_DigestEncryptUpdate, + (ck_session_handle_t session, + unsigned char *part, unsigned long part_len, + unsigned char *encrypted_part, + unsigned long *encrypted_part_len)); +_CK_DECLARE_FUNCTION (C_DecryptDigestUpdate, + (ck_session_handle_t session, + unsigned char *encrypted_part, + unsigned long encrypted_part_len, + unsigned char *part, + unsigned long *part_len)); +_CK_DECLARE_FUNCTION (C_SignEncryptUpdate, + (ck_session_handle_t session, + unsigned char *part, unsigned long part_len, + unsigned char *encrypted_part, + unsigned long *encrypted_part_len)); +_CK_DECLARE_FUNCTION (C_DecryptVerifyUpdate, + (ck_session_handle_t session, + unsigned char *encrypted_part, + unsigned long encrypted_part_len, + unsigned char *part, + unsigned long *part_len)); + +_CK_DECLARE_FUNCTION (C_GenerateKey, + (ck_session_handle_t session, + struct ck_mechanism *mechanism, + struct ck_attribute *templ, + unsigned long count, + ck_object_handle_t *key)); +_CK_DECLARE_FUNCTION (C_GenerateKeyPair, + (ck_session_handle_t session, + struct ck_mechanism *mechanism, + struct ck_attribute *public_key_template, + unsigned long public_key_attribute_count, + struct ck_attribute *private_key_template, + unsigned long private_key_attribute_count, + ck_object_handle_t *public_key, + ck_object_handle_t *private_key)); +_CK_DECLARE_FUNCTION (C_WrapKey, + (ck_session_handle_t session, + struct ck_mechanism *mechanism, + ck_object_handle_t wrapping_key, + ck_object_handle_t key, + unsigned char *wrapped_key, + unsigned long *wrapped_key_len)); +_CK_DECLARE_FUNCTION (C_UnwrapKey, + (ck_session_handle_t session, + struct ck_mechanism *mechanism, + ck_object_handle_t unwrapping_key, + unsigned char *wrapped_key, + unsigned long wrapped_key_len, + struct ck_attribute *templ, + unsigned long attribute_count, + ck_object_handle_t *key)); +_CK_DECLARE_FUNCTION (C_DeriveKey, + (ck_session_handle_t session, + struct ck_mechanism *mechanism, + ck_object_handle_t base_key, + struct ck_attribute *templ, + unsigned long attribute_count, + ck_object_handle_t *key)); + +_CK_DECLARE_FUNCTION (C_SeedRandom, + (ck_session_handle_t session, unsigned char *seed, + unsigned long seed_len)); +_CK_DECLARE_FUNCTION (C_GenerateRandom, + (ck_session_handle_t session, + unsigned char *random_data, + unsigned long random_len)); + +_CK_DECLARE_FUNCTION (C_GetFunctionStatus, (ck_session_handle_t session)); +_CK_DECLARE_FUNCTION (C_CancelFunction, (ck_session_handle_t session)); + + +struct ck_function_list +{ + struct ck_version version; + CK_C_Initialize C_Initialize; + CK_C_Finalize C_Finalize; + CK_C_GetInfo C_GetInfo; + CK_C_GetFunctionList C_GetFunctionList; + CK_C_GetSlotList C_GetSlotList; + CK_C_GetSlotInfo C_GetSlotInfo; + CK_C_GetTokenInfo C_GetTokenInfo; + CK_C_GetMechanismList C_GetMechanismList; + CK_C_GetMechanismInfo C_GetMechanismInfo; + CK_C_InitToken C_InitToken; + CK_C_InitPIN C_InitPIN; + CK_C_SetPIN C_SetPIN; + CK_C_OpenSession C_OpenSession; + CK_C_CloseSession C_CloseSession; + CK_C_CloseAllSessions C_CloseAllSessions; + CK_C_GetSessionInfo C_GetSessionInfo; + CK_C_GetOperationState C_GetOperationState; + CK_C_SetOperationState C_SetOperationState; + CK_C_Login C_Login; + CK_C_Logout C_Logout; + CK_C_CreateObject C_CreateObject; + CK_C_CopyObject C_CopyObject; + CK_C_DestroyObject C_DestroyObject; + CK_C_GetObjectSize C_GetObjectSize; + CK_C_GetAttributeValue C_GetAttributeValue; + CK_C_SetAttributeValue C_SetAttributeValue; + CK_C_FindObjectsInit C_FindObjectsInit; + CK_C_FindObjects C_FindObjects; + CK_C_FindObjectsFinal C_FindObjectsFinal; + CK_C_EncryptInit C_EncryptInit; + CK_C_Encrypt C_Encrypt; + CK_C_EncryptUpdate C_EncryptUpdate; + CK_C_EncryptFinal C_EncryptFinal; + CK_C_DecryptInit C_DecryptInit; + CK_C_Decrypt C_Decrypt; + CK_C_DecryptUpdate C_DecryptUpdate; + CK_C_DecryptFinal C_DecryptFinal; + CK_C_DigestInit C_DigestInit; + CK_C_Digest C_Digest; + CK_C_DigestUpdate C_DigestUpdate; + CK_C_DigestKey C_DigestKey; + CK_C_DigestFinal C_DigestFinal; + CK_C_SignInit C_SignInit; + CK_C_Sign C_Sign; + CK_C_SignUpdate C_SignUpdate; + CK_C_SignFinal C_SignFinal; + CK_C_SignRecoverInit C_SignRecoverInit; + CK_C_SignRecover C_SignRecover; + CK_C_VerifyInit C_VerifyInit; + CK_C_Verify C_Verify; + CK_C_VerifyUpdate C_VerifyUpdate; + CK_C_VerifyFinal C_VerifyFinal; + CK_C_VerifyRecoverInit C_VerifyRecoverInit; + CK_C_VerifyRecover C_VerifyRecover; + CK_C_DigestEncryptUpdate C_DigestEncryptUpdate; + CK_C_DecryptDigestUpdate C_DecryptDigestUpdate; + CK_C_SignEncryptUpdate C_SignEncryptUpdate; + CK_C_DecryptVerifyUpdate C_DecryptVerifyUpdate; + CK_C_GenerateKey C_GenerateKey; + CK_C_GenerateKeyPair C_GenerateKeyPair; + CK_C_WrapKey C_WrapKey; + CK_C_UnwrapKey C_UnwrapKey; + CK_C_DeriveKey C_DeriveKey; + CK_C_SeedRandom C_SeedRandom; + CK_C_GenerateRandom C_GenerateRandom; + CK_C_GetFunctionStatus C_GetFunctionStatus; + CK_C_CancelFunction C_CancelFunction; + CK_C_WaitForSlotEvent C_WaitForSlotEvent; +}; + + +typedef ck_rv_t (*ck_createmutex_t) (void **mutex); +typedef ck_rv_t (*ck_destroymutex_t) (void *mutex); +typedef ck_rv_t (*ck_lockmutex_t) (void *mutex); +typedef ck_rv_t (*ck_unlockmutex_t) (void *mutex); + + +struct ck_c_initialize_args +{ + ck_createmutex_t create_mutex; + ck_destroymutex_t destroy_mutex; + ck_lockmutex_t lock_mutex; + ck_unlockmutex_t unlock_mutex; + ck_flags_t flags; + void *reserved; +}; + + +#define CKF_LIBRARY_CANT_CREATE_OS_THREADS (1 << 0) +#define CKF_OS_LOCKING_OK (1 << 1) + +#define CKR_OK (0) +#define CKR_CANCEL (1) +#define CKR_HOST_MEMORY (2) +#define CKR_SLOT_ID_INVALID (3) +#define CKR_GENERAL_ERROR (5) +#define CKR_FUNCTION_FAILED (6) +#define CKR_ARGUMENTS_BAD (7) +#define CKR_NO_EVENT (8) +#define CKR_NEED_TO_CREATE_THREADS (9) +#define CKR_CANT_LOCK (0xa) +#define CKR_ATTRIBUTE_READ_ONLY (0x10) +#define CKR_ATTRIBUTE_SENSITIVE (0x11) +#define CKR_ATTRIBUTE_TYPE_INVALID (0x12) +#define CKR_ATTRIBUTE_VALUE_INVALID (0x13) +#define CKR_DATA_INVALID (0x20) +#define CKR_DATA_LEN_RANGE (0x21) +#define CKR_DEVICE_ERROR (0x30) +#define CKR_DEVICE_MEMORY (0x31) +#define CKR_DEVICE_REMOVED (0x32) +#define CKR_ENCRYPTED_DATA_INVALID (0x40) +#define CKR_ENCRYPTED_DATA_LEN_RANGE (0x41) +#define CKR_FUNCTION_CANCELED (0x50) +#define CKR_FUNCTION_NOT_PARALLEL (0x51) +#define CKR_FUNCTION_NOT_SUPPORTED (0x54) +#define CKR_KEY_HANDLE_INVALID (0x60) +#define CKR_KEY_SIZE_RANGE (0x62) +#define CKR_KEY_TYPE_INCONSISTENT (0x63) +#define CKR_KEY_NOT_NEEDED (0x64) +#define CKR_KEY_CHANGED (0x65) +#define CKR_KEY_NEEDED (0x66) +#define CKR_KEY_INDIGESTIBLE (0x67) +#define CKR_KEY_FUNCTION_NOT_PERMITTED (0x68) +#define CKR_KEY_NOT_WRAPPABLE (0x69) +#define CKR_KEY_UNEXTRACTABLE (0x6a) +#define CKR_MECHANISM_INVALID (0x70) +#define CKR_MECHANISM_PARAM_INVALID (0x71) +#define CKR_OBJECT_HANDLE_INVALID (0x82) +#define CKR_OPERATION_ACTIVE (0x90) +#define CKR_OPERATION_NOT_INITIALIZED (0x91) +#define CKR_PIN_INCORRECT (0xa0) +#define CKR_PIN_INVALID (0xa1) +#define CKR_PIN_LEN_RANGE (0xa2) +#define CKR_PIN_EXPIRED (0xa3) +#define CKR_PIN_LOCKED (0xa4) +#define CKR_SESSION_CLOSED (0xb0) +#define CKR_SESSION_COUNT (0xb1) +#define CKR_SESSION_HANDLE_INVALID (0xb3) +#define CKR_SESSION_PARALLEL_NOT_SUPPORTED (0xb4) +#define CKR_SESSION_READ_ONLY (0xb5) +#define CKR_SESSION_EXISTS (0xb6) +#define CKR_SESSION_READ_ONLY_EXISTS (0xb7) +#define CKR_SESSION_READ_WRITE_SO_EXISTS (0xb8) +#define CKR_SIGNATURE_INVALID (0xc0) +#define CKR_SIGNATURE_LEN_RANGE (0xc1) +#define CKR_TEMPLATE_INCOMPLETE (0xd0) +#define CKR_TEMPLATE_INCONSISTENT (0xd1) +#define CKR_TOKEN_NOT_PRESENT (0xe0) +#define CKR_TOKEN_NOT_RECOGNIZED (0xe1) +#define CKR_TOKEN_WRITE_PROTECTED (0xe2) +#define CKR_UNWRAPPING_KEY_HANDLE_INVALID (0xf0) +#define CKR_UNWRAPPING_KEY_SIZE_RANGE (0xf1) +#define CKR_UNWRAPPING_KEY_TYPE_INCONSISTENT (0xf2) +#define CKR_USER_ALREADY_LOGGED_IN (0x100) +#define CKR_USER_NOT_LOGGED_IN (0x101) +#define CKR_USER_PIN_NOT_INITIALIZED (0x102) +#define CKR_USER_TYPE_INVALID (0x103) +#define CKR_USER_ANOTHER_ALREADY_LOGGED_IN (0x104) +#define CKR_USER_TOO_MANY_TYPES (0x105) +#define CKR_WRAPPED_KEY_INVALID (0x110) +#define CKR_WRAPPED_KEY_LEN_RANGE (0x112) +#define CKR_WRAPPING_KEY_HANDLE_INVALID (0x113) +#define CKR_WRAPPING_KEY_SIZE_RANGE (0x114) +#define CKR_WRAPPING_KEY_TYPE_INCONSISTENT (0x115) +#define CKR_RANDOM_SEED_NOT_SUPPORTED (0x120) +#define CKR_RANDOM_NO_RNG (0x121) +#define CKR_DOMAIN_PARAMS_INVALID (0x130) +#define CKR_BUFFER_TOO_SMALL (0x150) +#define CKR_SAVED_STATE_INVALID (0x160) +#define CKR_INFORMATION_SENSITIVE (0x170) +#define CKR_STATE_UNSAVEABLE (0x180) +#define CKR_CRYPTOKI_NOT_INITIALIZED (0x190) +#define CKR_CRYPTOKI_ALREADY_INITIALIZED (0x191) +#define CKR_MUTEX_BAD (0x1a0) +#define CKR_MUTEX_NOT_LOCKED (0x1a1) +#define CKR_FUNCTION_REJECTED (0x200) +#define CKR_VENDOR_DEFINED ((unsigned long) (1 << 31)) + + + +/* Compatibility layer. */ + +#ifdef CRYPTOKI_COMPAT + +#undef CK_DEFINE_FUNCTION +#define CK_DEFINE_FUNCTION(retval, name) retval CK_SPEC name + +/* For NULL. */ +#include + +typedef unsigned char CK_BYTE; +typedef unsigned char CK_CHAR; +typedef unsigned char CK_UTF8CHAR; +typedef unsigned char CK_BBOOL; +typedef unsigned long int CK_ULONG; +typedef long int CK_LONG; +typedef CK_BYTE *CK_BYTE_PTR; +typedef CK_CHAR *CK_CHAR_PTR; +typedef CK_UTF8CHAR *CK_UTF8CHAR_PTR; +typedef CK_ULONG *CK_ULONG_PTR; +typedef void *CK_VOID_PTR; +typedef void **CK_VOID_PTR_PTR; +#define CK_FALSE 0 +#define CK_TRUE 1 +#ifndef CK_DISABLE_TRUE_FALSE +#ifndef FALSE +#define FALSE 0 +#endif +#ifndef TRUE +#define TRUE 1 +#endif +#endif + +typedef struct ck_version CK_VERSION; +typedef struct ck_version *CK_VERSION_PTR; + +typedef struct ck_info CK_INFO; +typedef struct ck_info *CK_INFO_PTR; + +typedef ck_slot_id_t *CK_SLOT_ID_PTR; + +typedef struct ck_slot_info CK_SLOT_INFO; +typedef struct ck_slot_info *CK_SLOT_INFO_PTR; + +typedef struct ck_token_info CK_TOKEN_INFO; +typedef struct ck_token_info *CK_TOKEN_INFO_PTR; + +typedef ck_session_handle_t *CK_SESSION_HANDLE_PTR; + +typedef struct ck_session_info CK_SESSION_INFO; +typedef struct ck_session_info *CK_SESSION_INFO_PTR; + +typedef ck_object_handle_t *CK_OBJECT_HANDLE_PTR; + +typedef ck_object_class_t *CK_OBJECT_CLASS_PTR; + +typedef struct ck_attribute CK_ATTRIBUTE; +typedef struct ck_attribute *CK_ATTRIBUTE_PTR; + +typedef struct ck_date CK_DATE; +typedef struct ck_date *CK_DATE_PTR; + +typedef ck_mechanism_type_t *CK_MECHANISM_TYPE_PTR; + +typedef struct ck_mechanism CK_MECHANISM; +typedef struct ck_mechanism *CK_MECHANISM_PTR; + +typedef struct ck_mechanism_info CK_MECHANISM_INFO; +typedef struct ck_mechanism_info *CK_MECHANISM_INFO_PTR; + +typedef struct ck_function_list CK_FUNCTION_LIST; +typedef struct ck_function_list *CK_FUNCTION_LIST_PTR; +typedef struct ck_function_list **CK_FUNCTION_LIST_PTR_PTR; + +typedef struct ck_c_initialize_args CK_C_INITIALIZE_ARGS; +typedef struct ck_c_initialize_args *CK_C_INITIALIZE_ARGS_PTR; + +#define NULL_PTR NULL + +/* Delete the helper macros defined at the top of the file. */ +#undef ck_flags_t +#undef ck_version + +#undef ck_info +#undef cryptoki_version +#undef manufacturer_id +#undef library_description +#undef library_version + +#undef ck_notification_t +#undef ck_slot_id_t + +#undef ck_slot_info +#undef slot_description +#undef hardware_version +#undef firmware_version + +#undef ck_token_info +#undef serial_number +#undef max_session_count +#undef session_count +#undef max_rw_session_count +#undef rw_session_count +#undef max_pin_len +#undef min_pin_len +#undef total_public_memory +#undef free_public_memory +#undef total_private_memory +#undef free_private_memory +#undef utc_time + +#undef ck_session_handle_t +#undef ck_user_type_t +#undef ck_state_t + +#undef ck_session_info +#undef slot_id +#undef device_error + +#undef ck_object_handle_t +#undef ck_object_class_t +#undef ck_hw_feature_type_t +#undef ck_key_type_t +#undef ck_certificate_type_t +#undef ck_attribute_type_t + +#undef ck_attribute +#undef value +#undef value_len + +#undef ck_date + +#undef ck_mechanism_type_t + +#undef ck_mechanism +#undef parameter +#undef parameter_len + +#undef ck_mechanism_info +#undef min_key_size +#undef max_key_size + +#undef ck_rv_t +#undef ck_notify_t + +#undef ck_function_list + +#undef ck_createmutex_t +#undef ck_destroymutex_t +#undef ck_lockmutex_t +#undef ck_unlockmutex_t + +#undef ck_c_initialize_args +#undef create_mutex +#undef destroy_mutex +#undef lock_mutex +#undef unlock_mutex +#undef reserved + +#endif /* CRYPTOKI_COMPAT */ + + +/* System dependencies. */ +#if defined(_WIN32) || defined(CRYPTOKI_FORCE_WIN32) +#pragma pack(pop, cryptoki) +#endif + +#if defined(__cplusplus) +} +#endif + +#endif /* PKCS11_H */