Initial revision
git-svn-id: svn://svn.h5l.se/heimdal/trunk/heimdal@15716 ec53bebd-3082-4978-b11e-865c3cabbd6b
This commit is contained in:
		
							
								
								
									
										52
									
								
								lib/hx509/Makefile.am
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										52
									
								
								lib/hx509/Makefile.am
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,52 @@
 | 
			
		||||
# $Id$
 | 
			
		||||
 | 
			
		||||
include $(top_srcdir)/Makefile.am.common
 | 
			
		||||
 | 
			
		||||
lib_LTLIBRARIES = libhx509.la
 | 
			
		||||
libhx509_la_LDFLAGS = -version-info 1:0:0
 | 
			
		||||
 | 
			
		||||
BUILT_SOURCES = hx509_err.c hx509_err.h
 | 
			
		||||
 | 
			
		||||
libhx509_la_LIBADD = ../asn1/libasn1.la
 | 
			
		||||
 | 
			
		||||
libhx509_la_CPPFLAGS = -I$(srcdir)/ref $(INCLUDE_des)
 | 
			
		||||
 | 
			
		||||
libhx509_la_SOURCES = \
 | 
			
		||||
	cert.c \
 | 
			
		||||
	cms.c \
 | 
			
		||||
	crypto.c \
 | 
			
		||||
	file.c \
 | 
			
		||||
	hx509.h \
 | 
			
		||||
	hx509_err.c \
 | 
			
		||||
	hx509_err.h \
 | 
			
		||||
	keyset.c \
 | 
			
		||||
	ks_mem.c \
 | 
			
		||||
	ks_file.c \
 | 
			
		||||
	ks_null.c \
 | 
			
		||||
	ks_p12.c \
 | 
			
		||||
	lock.c \
 | 
			
		||||
	name.c \
 | 
			
		||||
	p11.c \
 | 
			
		||||
	print.c
 | 
			
		||||
 | 
			
		||||
$(libhx509_la_OBJECTS): $(srcdir)/hx509-protos.h $(srcdir)/hx509-private.h
 | 
			
		||||
 | 
			
		||||
$(srcdir)/hx509-protos.h:
 | 
			
		||||
	cd $(srcdir) && perl ../../cf/make-proto.pl -E HX509_LIB_FUNCTION -q -P comment -o hx509-protos.h $(libhx509_la_SOURCES) || rm -f hx509-protos.h
 | 
			
		||||
 | 
			
		||||
$(srcdir)/hx509-private.h:
 | 
			
		||||
	cd $(srcdir) && perl ../../cf/make-proto.pl -q -P comment -p hx509-private.h $(libhx509_la_SOURCES) || rm -f hx509-private.h
 | 
			
		||||
 | 
			
		||||
include_HEADERS = hx509.h hx509-protos.h hx509_err.h
 | 
			
		||||
 | 
			
		||||
noinst_PROGRAMS = hxtool
 | 
			
		||||
 | 
			
		||||
hxtool_SOURCES = hxtool.c
 | 
			
		||||
 | 
			
		||||
hxtool_CPPFLAGS = $(INCLUDE_des)
 | 
			
		||||
hxtool_LDADD = libhx509.la $(LIB_roken) ../sl/libsl.la $(LIB_des)
 | 
			
		||||
hxtool_LDFLAGS = -pthread
 | 
			
		||||
 | 
			
		||||
EXTRA_DIST = hx509_err.et
 | 
			
		||||
 | 
			
		||||
CLEANFILES = hx509_err.c hx509_err.h
 | 
			
		||||
							
								
								
									
										1232
									
								
								lib/hx509/cert.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										1232
									
								
								lib/hx509/cert.c
									
									
									
									
									
										Normal file
									
								
							
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							
							
								
								
									
										1010
									
								
								lib/hx509/cms.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										1010
									
								
								lib/hx509/cms.c
									
									
									
									
									
										Normal file
									
								
							
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							
							
								
								
									
										1312
									
								
								lib/hx509/crypto.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										1312
									
								
								lib/hx509/crypto.c
									
									
									
									
									
										Normal file
									
								
							
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							
							
								
								
									
										84
									
								
								lib/hx509/file.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										84
									
								
								lib/hx509/file.c
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,84 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "hx_locl.h"
 | 
			
		||||
RCSID("$ID$");
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
_hx509_map_file(const char *fn, void **data, size_t *length)
 | 
			
		||||
{
 | 
			
		||||
    struct stat sb;
 | 
			
		||||
    size_t len;
 | 
			
		||||
    ssize_t l;
 | 
			
		||||
    int ret;
 | 
			
		||||
    void *d;
 | 
			
		||||
    int fd;
 | 
			
		||||
 | 
			
		||||
    *data = NULL;
 | 
			
		||||
    *length = 0;
 | 
			
		||||
 | 
			
		||||
    fd = open(fn, O_RDONLY);
 | 
			
		||||
    if (fd < 0)
 | 
			
		||||
	return errno;
 | 
			
		||||
    
 | 
			
		||||
    if (fstat(fd, &sb) < 0) {
 | 
			
		||||
	ret = errno;
 | 
			
		||||
	close(fd);
 | 
			
		||||
	return ret;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    len = sb.st_size;
 | 
			
		||||
 | 
			
		||||
    d = malloc(len);
 | 
			
		||||
    if (d == NULL) {
 | 
			
		||||
	close(fd);
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
    }
 | 
			
		||||
    
 | 
			
		||||
    l = read(fd, d, len);
 | 
			
		||||
    close(fd);
 | 
			
		||||
    if (l < 0 || l != len) {
 | 
			
		||||
	free(d);
 | 
			
		||||
	return EINVAL;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    *data = d;
 | 
			
		||||
    *length = len;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
_hx509_unmap_file(void *data, size_t len)
 | 
			
		||||
{
 | 
			
		||||
    free(data);
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										77
									
								
								lib/hx509/hx509.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										77
									
								
								lib/hx509/hx509.h
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,77 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2004 - 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
/* $Id$ */
 | 
			
		||||
 | 
			
		||||
typedef struct hx509_verify_ctx_data *hx509_verify_ctx;
 | 
			
		||||
typedef struct hx509_certs_data *hx509_certs;
 | 
			
		||||
typedef struct hx509_cert_data *hx509_cert;
 | 
			
		||||
typedef struct hx509_cert_attribute_data *hx509_cert_attribute;
 | 
			
		||||
typedef struct hx509_validate_ctx_data *hx509_validate_ctx;
 | 
			
		||||
typedef struct hx509_name_data *hx509_name;
 | 
			
		||||
typedef void * hx509_cursor;
 | 
			
		||||
typedef struct hx509_lock_data *hx509_lock;
 | 
			
		||||
typedef struct hx509_private_key *hx509_private_key;
 | 
			
		||||
 | 
			
		||||
/* current unused */
 | 
			
		||||
typedef struct hx509_crypto_data *hx509_crypto;
 | 
			
		||||
typedef struct hx509_digest_data *hx509_digest;
 | 
			
		||||
 | 
			
		||||
typedef void (*hx509_vprint_func)(void *, const char *, va_list);
 | 
			
		||||
 | 
			
		||||
enum {
 | 
			
		||||
    HX509_VALIDATE_F_VALIDATE = 1,
 | 
			
		||||
    HX509_VALIDATE_F_VERBOSE = 2
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct hx509_cert_attribute_data {
 | 
			
		||||
    heim_oid oid;
 | 
			
		||||
    heim_octet_string data;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
typedef enum {
 | 
			
		||||
    HX509_PROMPT_TYPE_PASSWORD		= 0x1,
 | 
			
		||||
    HX509_PROMPT_TYPE_QUESTION		= 0x2,
 | 
			
		||||
    HX509_PROMPT_TYPE_CONFIRMATION	= 0x4
 | 
			
		||||
} hx509_prompt_type;
 | 
			
		||||
 | 
			
		||||
typedef struct hx509_prompt {
 | 
			
		||||
    const char *prompt;
 | 
			
		||||
    int hidden;
 | 
			
		||||
    hx509_prompt_type type;
 | 
			
		||||
    heim_octet_string *reply;
 | 
			
		||||
} hx509_prompt;
 | 
			
		||||
 | 
			
		||||
typedef int (*hx509_prompter_fct)(void *, const hx509_prompt *);
 | 
			
		||||
 | 
			
		||||
#include <hx509-protos.h>
 | 
			
		||||
							
								
								
									
										49
									
								
								lib/hx509/hx509_err.et
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										49
									
								
								lib/hx509/hx509_err.et
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,49 @@
 | 
			
		||||
#
 | 
			
		||||
# Error messages for the hx509 library
 | 
			
		||||
#
 | 
			
		||||
# This might look like a com_err file, but is not
 | 
			
		||||
#
 | 
			
		||||
id "$Id$"
 | 
			
		||||
 | 
			
		||||
error_table hx
 | 
			
		||||
prefix HX509
 | 
			
		||||
 | 
			
		||||
error_code BAD_TIMEFORMAT,	"ASN.1 failed call to system time library"
 | 
			
		||||
error_code EXTENSION_NOT_FOUND,	"Extension not found"
 | 
			
		||||
error_code NO_PATH,		"Certification path not found"
 | 
			
		||||
error_code PARENT_NOT_CA,	"Parent certificate is not a CA"
 | 
			
		||||
error_code CA_PATH_TOO_DEEP,	"CA path too deep"
 | 
			
		||||
error_code SIG_ALG_NO_SUPPORTED, "Signature algorithm not supported"
 | 
			
		||||
error_code SIG_ALG_DONT_MATCH_KEY_ALG, "Signature algorithm doesn't match certificate key"
 | 
			
		||||
error_code CERT_USED_BEFORE_TIME, "Certificate used before it became valid"
 | 
			
		||||
error_code CERT_USED_AFTER_TIME, "Certificate used after it became invalid"
 | 
			
		||||
error_code PRIVATE_KEY_MISSING,	"Private key required for the operation is missing"
 | 
			
		||||
error_code ALG_NOT_SUPP, 	"Algorithm not supported"
 | 
			
		||||
error_code ISSUER_NOT_FOUND, 	"Issuer couldn't be found"
 | 
			
		||||
error_code VERIFY_CONSTRAINTS,	"Error verifing constraints"
 | 
			
		||||
error_code RANGE,		"Number too large"
 | 
			
		||||
error_code NAME_CONSTRAINT_ERROR, "Error while verifing name constraints"
 | 
			
		||||
error_code PATH_TOO_LONG, "Path is too long, failed to find valid anchor"
 | 
			
		||||
 | 
			
		||||
index 32
 | 
			
		||||
prefix HX509_CMS
 | 
			
		||||
error_code FAILED_CREATE_SIGATURE, "Failed to create signature"
 | 
			
		||||
error_code MISSING_SIGNER_DATA, "Missing signer data"
 | 
			
		||||
error_code SIGNER_NOT_FOUND, "Couldn't find signers certificate"
 | 
			
		||||
error_code NO_DATA_AVAILABLE, "No data to perform the operation on"
 | 
			
		||||
error_code INVALID_DATA, "Data in the message is invalid"
 | 
			
		||||
error_code PADDING_ERROR, "Padding in the message invalid"
 | 
			
		||||
error_code NO_RECIPIENT_CERTIFICATE, "Couldn't find recipient certificate"
 | 
			
		||||
error_code DATA_OID_MISMATCH, "Mismatch bewteen signed type and unsigned type"
 | 
			
		||||
 | 
			
		||||
index 64
 | 
			
		||||
prefix HX509_CRYPTO
 | 
			
		||||
error_code INTERNAL_ERROR, "Internal error in the crypto engine"
 | 
			
		||||
error_code EXTERNAL_ERROR, "External error in the crypto engine"
 | 
			
		||||
error_code SIGNATURE_MISSING, "Signature missing for data"
 | 
			
		||||
error_code BAD_SIGNATURE, "Signature is not valid"
 | 
			
		||||
error_code SIG_NO_CONF, "Sigature doesn't provide confidentiality"
 | 
			
		||||
error_code SIG_INVALID_FORMAT, "Invalid format on signature"
 | 
			
		||||
error_code OID_MISMATCH, "Mismatch bewteen oids"
 | 
			
		||||
 | 
			
		||||
end
 | 
			
		||||
							
								
								
									
										126
									
								
								lib/hx509/hx_locl.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										126
									
								
								lib/hx509/hx_locl.h
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,126 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2004 - 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
/* $Id$ */
 | 
			
		||||
 | 
			
		||||
#ifdef HAVE_CONFIG_H
 | 
			
		||||
#include <config.h>
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
#include <stdio.h>
 | 
			
		||||
#include <stdlib.h>
 | 
			
		||||
#include <errno.h>
 | 
			
		||||
#include <strings.h>
 | 
			
		||||
#include <assert.h>
 | 
			
		||||
#include <stdarg.h>
 | 
			
		||||
#include <err.h>
 | 
			
		||||
#include <getarg.h>
 | 
			
		||||
#include <base64.h>
 | 
			
		||||
#include <roken.h>
 | 
			
		||||
 | 
			
		||||
#include <heim_asn1.h>
 | 
			
		||||
#include <rfc2459_asn1.h>
 | 
			
		||||
#include <cms_asn1.h>
 | 
			
		||||
#include <pkcs8_asn1.h>
 | 
			
		||||
#include <pkcs9_asn1.h>
 | 
			
		||||
#include <pkcs12_asn1.h>
 | 
			
		||||
#include <asn1_err.h>
 | 
			
		||||
 | 
			
		||||
#include <der.h>
 | 
			
		||||
 | 
			
		||||
struct hx509_query_data;
 | 
			
		||||
typedef struct hx509_query_data hx509_query;
 | 
			
		||||
 | 
			
		||||
struct hx509_keyset_ops;
 | 
			
		||||
 | 
			
		||||
#include <hx509.h>
 | 
			
		||||
#include <hx509-private.h>
 | 
			
		||||
#include <hx509_err.h>
 | 
			
		||||
 | 
			
		||||
#define HX509_CERTS_FIND_SERIALNUMBER		1
 | 
			
		||||
#define HX509_CERTS_FIND_ISSUER			2
 | 
			
		||||
#define HX509_CERTS_FIND_SUBJECT		4
 | 
			
		||||
#define HX509_CERTS_FIND_ISSUER_KEY_ID		8
 | 
			
		||||
#define HX509_CERTS_FIND_SUBJECT_KEY_ID		16
 | 
			
		||||
 | 
			
		||||
struct hx509_name_data {
 | 
			
		||||
    Name der_name;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
typedef struct hx509_path {
 | 
			
		||||
    size_t len;
 | 
			
		||||
    hx509_cert *val;
 | 
			
		||||
} hx509_path;
 | 
			
		||||
 | 
			
		||||
struct hx509_query_data {
 | 
			
		||||
    int match;
 | 
			
		||||
#define HX509_QUERY_FIND_ISSUER_CERT	0x001
 | 
			
		||||
#define HX509_QUERY_MATCH_SERIALNUMBER	0x002
 | 
			
		||||
#define HX509_QUERY_MATCH_ISSUER_NAME	0x004
 | 
			
		||||
#define HX509_QUERY_MATCH_SUBJECT_NAME	0x008
 | 
			
		||||
#define HX509_QUERY_MATCH_SUBJECT_ID	0x010
 | 
			
		||||
#define HX509_QUERY_MATCH_ISSUER_ID	0x020
 | 
			
		||||
#define HX509_QUERY_PRIVATE_KEY		0x040
 | 
			
		||||
#define HX509_QUERY_ANCHOR		0x080
 | 
			
		||||
#define HX509_QUERY_MATCH_CERTIFICATE	0x100
 | 
			
		||||
#define HX509_QUERY_MATCH_LOCAL_KEY_ID	0x200
 | 
			
		||||
#define HX509_QUERY_NO_MATCH_PATH	0x400
 | 
			
		||||
#define HX509_QUERY_MASK		0x7ff
 | 
			
		||||
    Certificate *subject;
 | 
			
		||||
    Certificate *certificate;
 | 
			
		||||
    heim_integer *serial;
 | 
			
		||||
    heim_octet_string *subject_id;
 | 
			
		||||
    heim_octet_string *local_key_id;
 | 
			
		||||
    Name *issuer_name;
 | 
			
		||||
    Name *subject_name;
 | 
			
		||||
    hx509_path *path;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct hx509_keyset_ops {
 | 
			
		||||
    char *name;
 | 
			
		||||
    int flags;
 | 
			
		||||
    int (*init)(hx509_certs, void **, int, const char *, hx509_lock);
 | 
			
		||||
    int (*free)(hx509_certs, void *);
 | 
			
		||||
    int (*add)(hx509_certs, void *, hx509_cert);
 | 
			
		||||
    int (*query)(hx509_certs, void *, const hx509_query *, hx509_cert *);
 | 
			
		||||
    int (*iter_start)(hx509_certs, void *, void **);
 | 
			
		||||
    int (*iter)(hx509_certs, void *, void *, hx509_cert *);
 | 
			
		||||
    int (*iter_end)(hx509_certs, void *, void *);
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct _hx509_password {
 | 
			
		||||
    size_t len;
 | 
			
		||||
    char **val;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
extern hx509_lock _hx509_empty_lock;
 | 
			
		||||
							
								
								
									
										549
									
								
								lib/hx509/hxtool.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										549
									
								
								lib/hx509/hxtool.c
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,549 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2004 - 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "hx_locl.h"
 | 
			
		||||
RCSID("$ID$");
 | 
			
		||||
 | 
			
		||||
#include <sl.h>
 | 
			
		||||
 | 
			
		||||
static int version_flag;
 | 
			
		||||
static int help_flag;
 | 
			
		||||
 | 
			
		||||
struct getargs args[] = {
 | 
			
		||||
    { "version", 0, arg_flag, &version_flag },
 | 
			
		||||
    { "help", 0, arg_flag, &help_flag }
 | 
			
		||||
};
 | 
			
		||||
int num_args = sizeof(args) / sizeof(args[0]);
 | 
			
		||||
 | 
			
		||||
static void
 | 
			
		||||
usage(int code)
 | 
			
		||||
{
 | 
			
		||||
    arg_printusage(args, num_args, NULL, "command");
 | 
			
		||||
    exit(code);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
cms_verify_sd(int argc, char **argv)
 | 
			
		||||
{
 | 
			
		||||
    int ret;
 | 
			
		||||
    hx509_verify_ctx ctx = NULL;
 | 
			
		||||
    heim_oid type;
 | 
			
		||||
    heim_octet_string c;
 | 
			
		||||
    hx509_certs signers = NULL;
 | 
			
		||||
    hx509_certs anchors = NULL;
 | 
			
		||||
 | 
			
		||||
    ssize_t sz;
 | 
			
		||||
    void *p;
 | 
			
		||||
    int fd;
 | 
			
		||||
 | 
			
		||||
    argc--;
 | 
			
		||||
    argv++;
 | 
			
		||||
 | 
			
		||||
    if (argc < 2)
 | 
			
		||||
	errx(1, "argc < 2");
 | 
			
		||||
 | 
			
		||||
    printf("cms verify signed data\n");
 | 
			
		||||
 | 
			
		||||
    fd = open(argv[0], O_RDONLY, 0);
 | 
			
		||||
    if (fd < 0)
 | 
			
		||||
	err(1, "open %s", argv[0]);
 | 
			
		||||
 | 
			
		||||
    p = malloc(10000);
 | 
			
		||||
    if (p == NULL)
 | 
			
		||||
	;
 | 
			
		||||
 | 
			
		||||
    sz = read(fd, p, 10000);
 | 
			
		||||
    if (sz < 0)
 | 
			
		||||
	err(1, "read");
 | 
			
		||||
    close(fd);
 | 
			
		||||
 | 
			
		||||
    
 | 
			
		||||
    ret = hx509_verify_init_ctx(&ctx);
 | 
			
		||||
 | 
			
		||||
    argc--;
 | 
			
		||||
    argv++;
 | 
			
		||||
 | 
			
		||||
    ret = hx509_certs_init("MEMORY:cms-anchors", 0, NULL, &anchors);
 | 
			
		||||
 | 
			
		||||
    while (argc > 0) {
 | 
			
		||||
 | 
			
		||||
	ret = hx509_certs_append(anchors, argv[0]);
 | 
			
		||||
	if (ret)
 | 
			
		||||
	    errx(1, "hx509_certs_append: %d", ret);
 | 
			
		||||
 | 
			
		||||
	argc--;
 | 
			
		||||
	argv++;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    hx509_verify_attach_anchors(ctx, anchors);
 | 
			
		||||
 | 
			
		||||
    ret = hx509_cms_verify_signed(ctx, p, sz, &type, &c, &signers);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	errx(1, "hx509_cms_verify_signed: %d", ret);
 | 
			
		||||
 | 
			
		||||
    printf("signers:\n");
 | 
			
		||||
    hx509_certs_iter(signers, hx509_ci_print_names, stdout);
 | 
			
		||||
 | 
			
		||||
    hx509_certs_free(&anchors);
 | 
			
		||||
    hx509_certs_free(&signers);
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
cms_create_sd(int argc, char **argv)
 | 
			
		||||
{
 | 
			
		||||
    const heim_oid *contentType;
 | 
			
		||||
    heim_octet_string o;
 | 
			
		||||
    hx509_query q;
 | 
			
		||||
    hx509_lock lock;
 | 
			
		||||
    hx509_certs s;
 | 
			
		||||
    hx509_cert cert;
 | 
			
		||||
    ssize_t sz;
 | 
			
		||||
    void *p;
 | 
			
		||||
    int fd;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    contentType = oid_id_pkcs7_data();
 | 
			
		||||
 | 
			
		||||
    argc--;
 | 
			
		||||
    argv++;
 | 
			
		||||
 | 
			
		||||
    if (argc < 3)
 | 
			
		||||
	errx(1, "argc < 3");
 | 
			
		||||
 | 
			
		||||
    printf("cms create signed data\n");
 | 
			
		||||
 | 
			
		||||
    hx509_lock_init(&lock);
 | 
			
		||||
    hx509_lock_add_password(lock, "foobar");
 | 
			
		||||
 | 
			
		||||
    fd = open(argv[0], O_RDONLY, 0);
 | 
			
		||||
    if (fd < 0)
 | 
			
		||||
	err(1, "open %s", argv[0]);
 | 
			
		||||
 | 
			
		||||
    p = malloc(10000);
 | 
			
		||||
    if (p == NULL)
 | 
			
		||||
	;
 | 
			
		||||
 | 
			
		||||
    sz = read(fd, p, 10000);
 | 
			
		||||
    if (sz < 0)
 | 
			
		||||
	err(1, "read");
 | 
			
		||||
    close(fd);
 | 
			
		||||
    
 | 
			
		||||
    ret = hx509_certs_init(argv[2], 0, lock, &s);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	errx(1, "hx509_certs_init: %d", ret);
 | 
			
		||||
 | 
			
		||||
    _hx509_query_clear(&q);
 | 
			
		||||
    q.match |= HX509_QUERY_PRIVATE_KEY;
 | 
			
		||||
 | 
			
		||||
    ret = _hx509_certs_find(s, &q, &cert);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	errx(1, "hx509_certs_find: %d", ret);
 | 
			
		||||
 | 
			
		||||
    ret = hx509_cms_create_signed_1(contentType,
 | 
			
		||||
				    p,
 | 
			
		||||
				    sz, 
 | 
			
		||||
				    NULL,
 | 
			
		||||
				    cert,
 | 
			
		||||
				    &o);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	errx(1, "hx509_cms_create_signed: %d", ret);
 | 
			
		||||
 | 
			
		||||
    fd = open(argv[1], O_WRONLY|O_TRUNC|O_CREAT, 0644);
 | 
			
		||||
    if (fd < 0)
 | 
			
		||||
	err(1, "open %s", argv[1]);
 | 
			
		||||
 | 
			
		||||
    write(fd, o.data, o.length);
 | 
			
		||||
    close(fd);
 | 
			
		||||
 | 
			
		||||
    hx509_lock_free(lock);
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
cms_unenvelope(int argc, char **argv)
 | 
			
		||||
{
 | 
			
		||||
    heim_oid contentType = { 0, NULL };
 | 
			
		||||
    heim_octet_string o;
 | 
			
		||||
    hx509_certs certs;
 | 
			
		||||
    ssize_t sz;
 | 
			
		||||
    void *p;
 | 
			
		||||
    int fd;
 | 
			
		||||
    int ret;
 | 
			
		||||
    hx509_lock lock;
 | 
			
		||||
 | 
			
		||||
    argc--;
 | 
			
		||||
    argv++;
 | 
			
		||||
 | 
			
		||||
    if (argc != 3)
 | 
			
		||||
	errx(1, "argc != 3");
 | 
			
		||||
 | 
			
		||||
    printf("cms unenvelope data\n");
 | 
			
		||||
 | 
			
		||||
    hx509_lock_init(&lock);
 | 
			
		||||
    hx509_lock_add_password(lock, "foobar");
 | 
			
		||||
 | 
			
		||||
    fd = open(argv[1], O_RDONLY, 0);
 | 
			
		||||
    if (fd < 0)
 | 
			
		||||
	err(1, "open %s", argv[1]);
 | 
			
		||||
 | 
			
		||||
    p = malloc(10000);
 | 
			
		||||
    if (p == NULL)
 | 
			
		||||
	;
 | 
			
		||||
 | 
			
		||||
    sz = read(fd, p, 10000);
 | 
			
		||||
    if (sz < 0)
 | 
			
		||||
	err(1, "read");
 | 
			
		||||
    close(fd);
 | 
			
		||||
    
 | 
			
		||||
    ret = hx509_certs_init("MEMORY:cert-store", 0, NULL, &certs);
 | 
			
		||||
 | 
			
		||||
    ret = hx509_certs_init(argv[0], 0, lock, &certs);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	errx(1, "hx509_certs_init: %d", ret);
 | 
			
		||||
 | 
			
		||||
    ret = hx509_cms_unenvelope(certs, p, sz, &contentType, &o);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	errx(1, "hx509_cms_unenvelope: %d", ret);
 | 
			
		||||
 | 
			
		||||
    fd = open(argv[2], O_WRONLY|O_TRUNC|O_CREAT, 0644);
 | 
			
		||||
    if (fd < 0)
 | 
			
		||||
	err(1, "open %s", argv[2]);
 | 
			
		||||
 | 
			
		||||
    write(fd, o.data, o.length);
 | 
			
		||||
    close(fd);
 | 
			
		||||
 | 
			
		||||
    hx509_lock_free(lock);
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
cms_create_enveloped(int argc, char **argv)
 | 
			
		||||
{
 | 
			
		||||
    heim_octet_string o;
 | 
			
		||||
    heim_oid contentType = { 0, NULL };
 | 
			
		||||
    hx509_query q;
 | 
			
		||||
    hx509_certs certs;
 | 
			
		||||
    hx509_cert cert;
 | 
			
		||||
    int ret;
 | 
			
		||||
    ssize_t sz;
 | 
			
		||||
    void *p;
 | 
			
		||||
    int fd;
 | 
			
		||||
 | 
			
		||||
    argc--;
 | 
			
		||||
    argv++;
 | 
			
		||||
 | 
			
		||||
    if (argc != 3)
 | 
			
		||||
	errx(1, "argc ! = 3");
 | 
			
		||||
 | 
			
		||||
    printf("cms create enveloped\n");
 | 
			
		||||
 | 
			
		||||
    fd = open(argv[0], O_RDONLY, 0);
 | 
			
		||||
    if (fd < 0)
 | 
			
		||||
	err(1, "open %s", argv[0]);
 | 
			
		||||
 | 
			
		||||
    p = malloc(10000);
 | 
			
		||||
    if (p == NULL)
 | 
			
		||||
	;
 | 
			
		||||
 | 
			
		||||
    sz = read(fd, p, 10000);
 | 
			
		||||
    if (sz < 0)
 | 
			
		||||
	err(1, "read");
 | 
			
		||||
    close(fd);
 | 
			
		||||
    
 | 
			
		||||
    ret = hx509_certs_init(argv[2], 0, NULL, &certs);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	errx(1, "hx509_certs_init: %d", ret);
 | 
			
		||||
 | 
			
		||||
    _hx509_query_clear(&q);
 | 
			
		||||
    ret = _hx509_certs_find(certs, &q, &cert);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	errx(1, "hx509_certs_find: %d", ret);
 | 
			
		||||
 | 
			
		||||
    ret = hx509_cms_envelope_1(cert, p, sz, NULL, &contentType, &o);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	errx(1, "hx509_cms_unenvelope: %d", ret);
 | 
			
		||||
 | 
			
		||||
    fd = open(argv[1], O_WRONLY|O_TRUNC|O_CREAT, 0644);
 | 
			
		||||
    if (fd < 0)
 | 
			
		||||
	err(1, "open %s", argv[1]);
 | 
			
		||||
 | 
			
		||||
    write(fd, o.data, o.length);
 | 
			
		||||
    close(fd);
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
validate_print_f(void *ctx, hx509_cert c)
 | 
			
		||||
{
 | 
			
		||||
    hx509_validate_cert(ctx, c);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
validate_print(int argc, char **argv, int flags)
 | 
			
		||||
{
 | 
			
		||||
    hx509_validate_ctx ctx;
 | 
			
		||||
    hx509_certs certs;
 | 
			
		||||
    hx509_lock lock;
 | 
			
		||||
 | 
			
		||||
    argc--;
 | 
			
		||||
    argv++;
 | 
			
		||||
 | 
			
		||||
    if (argc < 1)
 | 
			
		||||
	errx(1, "argc");
 | 
			
		||||
 | 
			
		||||
    hx509_lock_init(&lock);
 | 
			
		||||
    hx509_lock_add_password(lock, "foobar");
 | 
			
		||||
 | 
			
		||||
    hx509_validate_ctx_init(&ctx);
 | 
			
		||||
    hx509_validate_ctx_set_print(ctx, hx509_print_stdout, stdout);
 | 
			
		||||
    hx509_validate_ctx_add_flags(ctx, flags);
 | 
			
		||||
 | 
			
		||||
    while(argc--) {
 | 
			
		||||
	int ret;
 | 
			
		||||
	ret = hx509_certs_init(argv[0], 0, lock, &certs);
 | 
			
		||||
	if (ret)
 | 
			
		||||
	    errx(1, "hx509_certs_init");
 | 
			
		||||
	hx509_certs_iter(certs, validate_print_f, ctx);
 | 
			
		||||
	hx509_certs_free(&certs);
 | 
			
		||||
	argv++;
 | 
			
		||||
    }
 | 
			
		||||
    hx509_validate_ctx_free(ctx);
 | 
			
		||||
 | 
			
		||||
    hx509_lock_free(lock);
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
pcert_print(int argc, char **argv)
 | 
			
		||||
{
 | 
			
		||||
    return validate_print(argc, argv, HX509_VALIDATE_F_VERBOSE);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
pcert_validate(int argc, char **argv)
 | 
			
		||||
{
 | 
			
		||||
    return validate_print(argc, argv, HX509_VALIDATE_F_VALIDATE);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
struct verify {
 | 
			
		||||
    hx509_verify_ctx ctx;
 | 
			
		||||
    hx509_certs chain;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
verify_f(void *ctx, hx509_cert c)
 | 
			
		||||
{
 | 
			
		||||
    struct verify *v = ctx;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    ret = hx509_verify_path(v->ctx, c, v->chain);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	printf("verify_path returned %d\n", ret);
 | 
			
		||||
    else
 | 
			
		||||
	printf("path ok\n");
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
pcert_verify(int argc, char **argv)
 | 
			
		||||
{
 | 
			
		||||
    hx509_certs anchors, chain, certs;
 | 
			
		||||
    hx509_verify_ctx ctx;
 | 
			
		||||
    struct verify v;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    argc--;
 | 
			
		||||
    argv++;
 | 
			
		||||
 | 
			
		||||
    ret = hx509_verify_init_ctx(&ctx);
 | 
			
		||||
    ret = hx509_certs_init("MEMORY:anchors", 0, NULL, &anchors);
 | 
			
		||||
    ret = hx509_certs_init("MEMORY:chain", 0, NULL, &chain);
 | 
			
		||||
    ret = hx509_certs_init("MEMORY:certs", 0, NULL, &certs);
 | 
			
		||||
 | 
			
		||||
    if (argc < 1)
 | 
			
		||||
	errx(1, "argc");
 | 
			
		||||
 | 
			
		||||
    while(argc--) {
 | 
			
		||||
	char *s = *argv++;
 | 
			
		||||
 | 
			
		||||
	if (strncmp(s, "chain:", 6) == 0) {
 | 
			
		||||
	    s += 6;
 | 
			
		||||
 | 
			
		||||
	    ret = hx509_certs_append(chain, s);
 | 
			
		||||
	    if (ret)
 | 
			
		||||
		errx(1, "hx509_certs_append: chain: %d", ret);
 | 
			
		||||
 | 
			
		||||
	} else if (strncmp(s, "anchor:", 7) == 0) {
 | 
			
		||||
	    s += 7;
 | 
			
		||||
 | 
			
		||||
	    ret = hx509_certs_append(anchors, s);
 | 
			
		||||
	    if (ret)
 | 
			
		||||
		errx(1, "hx509_certs_append: anchor: %d", ret);
 | 
			
		||||
 | 
			
		||||
	} else if (strncmp(s, "cert:", 5) == 0) {
 | 
			
		||||
	    s += 5;
 | 
			
		||||
 | 
			
		||||
	    ret = hx509_certs_append(certs, s);
 | 
			
		||||
	    if (ret)
 | 
			
		||||
		errx(1, "hx509_certs_append: certs: %d", ret);
 | 
			
		||||
 | 
			
		||||
	} else {
 | 
			
		||||
	    errx(1, "unknown option to verify: `%s'\n", s);
 | 
			
		||||
	}
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    hx509_verify_attach_anchors(ctx, anchors);
 | 
			
		||||
 | 
			
		||||
    v.ctx = ctx;
 | 
			
		||||
    v.chain = chain;
 | 
			
		||||
 | 
			
		||||
    hx509_certs_iter(certs, verify_f, &v);
 | 
			
		||||
 | 
			
		||||
    hx509_certs_free(&anchors);
 | 
			
		||||
    hx509_certs_free(&certs);
 | 
			
		||||
    hx509_certs_free(&chain);
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
pcert_pkcs11(int argc, char **argv)
 | 
			
		||||
{
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    argc--;
 | 
			
		||||
    argv++;
 | 
			
		||||
 | 
			
		||||
    if (argc < 1)
 | 
			
		||||
	errx(1, "argc");
 | 
			
		||||
 | 
			
		||||
    ret = hx509_keyset_init(argv[0], NULL);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	printf("hx509_keyset_init: %d\n", ret);
 | 
			
		||||
	return 0;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int help(int, char **);
 | 
			
		||||
 | 
			
		||||
static SL_cmd cmds[] = {
 | 
			
		||||
    { "cms-create-sd",
 | 
			
		||||
      cms_create_sd,
 | 
			
		||||
      "in-file out-file cert ...",
 | 
			
		||||
      "create signed data"
 | 
			
		||||
    },
 | 
			
		||||
    { "cms-verify-sd",
 | 
			
		||||
      cms_verify_sd,
 | 
			
		||||
      "file cert ...",
 | 
			
		||||
      "verify signed data"
 | 
			
		||||
    },
 | 
			
		||||
    { "cms-unenvelope",
 | 
			
		||||
      cms_unenvelope,
 | 
			
		||||
      "cert key in-file out-file",
 | 
			
		||||
      "unenvelope data"
 | 
			
		||||
    },
 | 
			
		||||
    { "cms-create-envelope",
 | 
			
		||||
      cms_create_enveloped,
 | 
			
		||||
      "cert in-file out-file",
 | 
			
		||||
      "envelope data"
 | 
			
		||||
    },
 | 
			
		||||
 | 
			
		||||
    { "print",
 | 
			
		||||
      pcert_print,
 | 
			
		||||
      "cert ...",
 | 
			
		||||
      "print certificates"
 | 
			
		||||
    },
 | 
			
		||||
    { "validate",
 | 
			
		||||
      pcert_validate,
 | 
			
		||||
      "cert ...",
 | 
			
		||||
      "validate certificates"
 | 
			
		||||
    },
 | 
			
		||||
    { "verify",
 | 
			
		||||
      pcert_verify,
 | 
			
		||||
      "cert:foo chain:cert1 chain:cert2 anchor:anchor1 anchor:anchor2",
 | 
			
		||||
      "verify certificates"
 | 
			
		||||
    },
 | 
			
		||||
    { "pkcs11",
 | 
			
		||||
      pcert_pkcs11,
 | 
			
		||||
      "...",
 | 
			
		||||
      "deal with pkcs11 devices"
 | 
			
		||||
    },
 | 
			
		||||
    { "help", help, "help" },
 | 
			
		||||
    { "?" },
 | 
			
		||||
    { NULL }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
help(int argc, char **argv)
 | 
			
		||||
{
 | 
			
		||||
    sl_help(cmds, argc, argv);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
main(int argc, char **argv)
 | 
			
		||||
{
 | 
			
		||||
    int ret, optidx = 0;
 | 
			
		||||
 | 
			
		||||
    setprogname (argv[0]);
 | 
			
		||||
 | 
			
		||||
    if(getarg(args, num_args, argc, argv, &optidx))
 | 
			
		||||
	usage(1);
 | 
			
		||||
    if(help_flag)
 | 
			
		||||
	usage(0);
 | 
			
		||||
    if(version_flag) {
 | 
			
		||||
	print_version(NULL);
 | 
			
		||||
	exit(0);
 | 
			
		||||
    }
 | 
			
		||||
    argv += optidx;
 | 
			
		||||
    argc -= optidx;
 | 
			
		||||
 | 
			
		||||
    if (argc == 0)
 | 
			
		||||
	usage(1);
 | 
			
		||||
 | 
			
		||||
    ret = sl_command(cmds, argc, argv);
 | 
			
		||||
    if(ret == -1)
 | 
			
		||||
	warnx ("unrecognized command: %s", argv[0]);
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										281
									
								
								lib/hx509/keyset.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										281
									
								
								lib/hx509/keyset.c
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,281 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2004 - 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "hx_locl.h"
 | 
			
		||||
RCSID("$ID$");
 | 
			
		||||
 | 
			
		||||
static struct hx509_keyset_ops **ks_ops;
 | 
			
		||||
static int ks_num_ops;
 | 
			
		||||
 | 
			
		||||
struct hx509_certs_data {
 | 
			
		||||
    struct hx509_keyset_ops *ops;
 | 
			
		||||
    void *ops_data;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
static struct hx509_keyset_ops *
 | 
			
		||||
_hx509_ks_type(const char *type)
 | 
			
		||||
{
 | 
			
		||||
    int i;
 | 
			
		||||
 | 
			
		||||
    for (i = 0; i < ks_num_ops; i++)
 | 
			
		||||
	if (strcasecmp(type, ks_ops[i]->name) == 0)
 | 
			
		||||
	    return ks_ops[i];
 | 
			
		||||
 | 
			
		||||
    return NULL;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
_hx509_ks_register(struct hx509_keyset_ops *ops)
 | 
			
		||||
{
 | 
			
		||||
    struct hx509_keyset_ops **val;
 | 
			
		||||
 | 
			
		||||
    if (_hx509_ks_type(ops->name))
 | 
			
		||||
	return;
 | 
			
		||||
 | 
			
		||||
    val = realloc(ks_ops, (ks_num_ops + 1) * sizeof(ks_ops[0]));
 | 
			
		||||
    if (val == NULL)
 | 
			
		||||
	return;
 | 
			
		||||
    val[ks_num_ops] = ops;
 | 
			
		||||
    ks_ops = val;
 | 
			
		||||
    ks_num_ops++;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_certs_init(const char *name, int flags,
 | 
			
		||||
		 hx509_lock lock, hx509_certs *certs)
 | 
			
		||||
{
 | 
			
		||||
    struct hx509_keyset_ops *ops;
 | 
			
		||||
    const char *residue;
 | 
			
		||||
    hx509_certs c;
 | 
			
		||||
    char *type;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    *certs = NULL;
 | 
			
		||||
 | 
			
		||||
    if (ks_ops == NULL) {
 | 
			
		||||
	_hx509_ks_mem_register();
 | 
			
		||||
	_hx509_ks_file_register();
 | 
			
		||||
	_hx509_ks_pkcs12_register();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    residue = strchr(name, ':');
 | 
			
		||||
    if (residue) {
 | 
			
		||||
	type = strndup(name, residue - name);
 | 
			
		||||
	residue++;
 | 
			
		||||
	if (residue[0] == '\0')
 | 
			
		||||
	    residue = NULL;
 | 
			
		||||
    } else {
 | 
			
		||||
	type = strdup("MEMORY");
 | 
			
		||||
	residue = name;
 | 
			
		||||
    }
 | 
			
		||||
    if (type == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
    
 | 
			
		||||
    ops = _hx509_ks_type(type);
 | 
			
		||||
    free(type);
 | 
			
		||||
    if (ops == NULL)
 | 
			
		||||
	return ENOENT;
 | 
			
		||||
 | 
			
		||||
    c = calloc(1, sizeof(*c));
 | 
			
		||||
    if (c == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
 | 
			
		||||
    c->ops = ops;
 | 
			
		||||
 | 
			
		||||
    ret = (*ops->init)(c, &c->ops_data, flags, residue, lock);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	free(c);
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    *certs = c;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_certs_free(hx509_certs *certs)
 | 
			
		||||
{
 | 
			
		||||
    (*(*certs)->ops->free)(*certs, (*certs)->ops_data);
 | 
			
		||||
 | 
			
		||||
    free(*certs);
 | 
			
		||||
    *certs = NULL;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_certs_start_seq(hx509_certs certs, hx509_cursor cursor)
 | 
			
		||||
{
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    if (certs->ops->iter_start == NULL)
 | 
			
		||||
	return ENOENT;
 | 
			
		||||
 | 
			
		||||
    ret = (*certs->ops->iter_start)(certs, certs->ops_data, cursor);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	return ret;
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_certs_next_cert(hx509_certs certs, hx509_cursor cursor,
 | 
			
		||||
		      hx509_cert *cert)
 | 
			
		||||
{
 | 
			
		||||
    *cert = NULL;
 | 
			
		||||
    return (*certs->ops->iter)(certs, certs->ops_data, cursor, cert);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_certs_end_seq(hx509_certs certs, hx509_cursor cursor)
 | 
			
		||||
{
 | 
			
		||||
    (*certs->ops->iter_end)(certs, certs->ops_data, cursor);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_certs_iter(hx509_certs certs, int (*fn)(void *, hx509_cert), void *ctx)
 | 
			
		||||
{
 | 
			
		||||
    hx509_cursor cursor;
 | 
			
		||||
    hx509_cert c;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    ret = hx509_certs_start_seq(certs, &cursor);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	return ret;
 | 
			
		||||
    
 | 
			
		||||
    while (1) {
 | 
			
		||||
	ret = hx509_certs_next_cert(certs, cursor, &c);
 | 
			
		||||
	if (ret)
 | 
			
		||||
	    break;
 | 
			
		||||
	if (c == NULL)
 | 
			
		||||
	    break;
 | 
			
		||||
	ret = (*fn)(ctx, c);
 | 
			
		||||
	hx509_cert_free(c);
 | 
			
		||||
	if (ret)
 | 
			
		||||
	    break;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    hx509_certs_end_seq(certs, cursor);
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_ci_print_names(void *ctx, hx509_cert c)
 | 
			
		||||
{
 | 
			
		||||
    Certificate *cert;
 | 
			
		||||
    hx509_name n;
 | 
			
		||||
    char *str;
 | 
			
		||||
 | 
			
		||||
    cert = _hx509_get_cert(c);
 | 
			
		||||
 | 
			
		||||
    _hx509_name_from_Name(&cert->tbsCertificate.subject, &n);
 | 
			
		||||
    hx509_name_to_string(n, &str);
 | 
			
		||||
    hx509_name_free(&n);
 | 
			
		||||
    fprintf(ctx, "%s\n", str);
 | 
			
		||||
    free(str);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_certs_add(hx509_certs certs, hx509_cert cert)
 | 
			
		||||
{
 | 
			
		||||
    if (certs->ops->add == NULL)
 | 
			
		||||
	return ENOENT;
 | 
			
		||||
 | 
			
		||||
    return (*certs->ops->add)(certs, certs->ops_data, cert);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
_hx509_certs_find(hx509_certs certs, const hx509_query *q, hx509_cert *r)
 | 
			
		||||
{
 | 
			
		||||
    hx509_cursor cursor;
 | 
			
		||||
    hx509_cert c;
 | 
			
		||||
    int ret, found = 0;
 | 
			
		||||
 | 
			
		||||
    *r = NULL;
 | 
			
		||||
 | 
			
		||||
    if (certs->ops->query)
 | 
			
		||||
	return (*certs->ops->query)(certs, certs->ops_data, q, r);
 | 
			
		||||
 | 
			
		||||
    ret = hx509_certs_start_seq(certs, &cursor);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	return ret;
 | 
			
		||||
 | 
			
		||||
    while (1) {
 | 
			
		||||
	ret = hx509_certs_next_cert(certs, cursor, &c);
 | 
			
		||||
	if (ret)
 | 
			
		||||
	    break;
 | 
			
		||||
	if (c == NULL)
 | 
			
		||||
	    break;
 | 
			
		||||
	found = _hx509_query_match_cert(q, c);
 | 
			
		||||
	if (found) {
 | 
			
		||||
	    *r = c;
 | 
			
		||||
	    break;
 | 
			
		||||
	}
 | 
			
		||||
	hx509_cert_free(c);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    hx509_certs_end_seq(certs, cursor);
 | 
			
		||||
 | 
			
		||||
    if (!found)
 | 
			
		||||
	return ENOENT;
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
certs_merge_func(void *ctx, hx509_cert c)
 | 
			
		||||
{
 | 
			
		||||
    return hx509_certs_add((hx509_certs)ctx, c);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_certs_merge(hx509_certs to, hx509_certs from)
 | 
			
		||||
{
 | 
			
		||||
    return hx509_certs_iter(from, certs_merge_func, to);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_certs_append(hx509_certs to, const char *name)
 | 
			
		||||
{
 | 
			
		||||
    hx509_certs s;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    ret = hx509_certs_init(name, 0, NULL, &s);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	return ret;
 | 
			
		||||
    ret = hx509_certs_merge(to, s);
 | 
			
		||||
    hx509_certs_free(&s);
 | 
			
		||||
    return ret;
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										233
									
								
								lib/hx509/ks_file.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										233
									
								
								lib/hx509/ks_file.c
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,233 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "hx_locl.h"
 | 
			
		||||
RCSID("$ID$");
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
parse_certificate(const char *fn, int use_pem, Certificate *t)
 | 
			
		||||
{
 | 
			
		||||
    char buf[1024];
 | 
			
		||||
    void *data = NULL;
 | 
			
		||||
    size_t size, len = 0;
 | 
			
		||||
    int in_cert = 0;
 | 
			
		||||
    FILE *f;
 | 
			
		||||
    int i, ret;
 | 
			
		||||
 | 
			
		||||
    memset(t, 0, sizeof(*t));
 | 
			
		||||
 | 
			
		||||
    if ((f = fopen(fn, "r")) == NULL)
 | 
			
		||||
	return ENOENT;
 | 
			
		||||
 | 
			
		||||
    if (use_pem) {
 | 
			
		||||
	while (fgets(buf, sizeof(buf), f) != NULL) {
 | 
			
		||||
	    char *p;
 | 
			
		||||
 | 
			
		||||
	    i = strcspn(buf, "\n");
 | 
			
		||||
	    if (buf[i] == '\n') buf[i--] = '\0';
 | 
			
		||||
	    if (buf[i] == '\r') buf[i--] = '\0';
 | 
			
		||||
	    
 | 
			
		||||
	    if (i == 26
 | 
			
		||||
		&& strcmp("-----BEGIN CERTIFICATE-----", buf) == 0)
 | 
			
		||||
	    {
 | 
			
		||||
		in_cert = 1;
 | 
			
		||||
		continue;
 | 
			
		||||
	    } else if (i == 24 &&
 | 
			
		||||
		       strcmp("-----END CERTIFICATE-----", buf) == 0)
 | 
			
		||||
	    {
 | 
			
		||||
		in_cert = 0;
 | 
			
		||||
		continue;
 | 
			
		||||
	    }
 | 
			
		||||
	    if (in_cert == 0)
 | 
			
		||||
		continue;
 | 
			
		||||
 | 
			
		||||
	    p = malloc(i);
 | 
			
		||||
	    i = base64_decode(buf, p);
 | 
			
		||||
	    
 | 
			
		||||
	    data = erealloc(data, len + i);
 | 
			
		||||
	    memcpy(((char *)data) + len, p, i);
 | 
			
		||||
	    free(p);
 | 
			
		||||
	    len += i;
 | 
			
		||||
	}
 | 
			
		||||
    } else {
 | 
			
		||||
	while((i = fread(buf, 1, sizeof(buf), f)) > 0) {
 | 
			
		||||
	    data = erealloc(data, len + i);
 | 
			
		||||
	    memcpy(((char *)data) + len, buf, i);
 | 
			
		||||
	    len += i;
 | 
			
		||||
	}
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fclose(f);
 | 
			
		||||
 | 
			
		||||
    if (data == NULL)
 | 
			
		||||
	return 1;
 | 
			
		||||
 | 
			
		||||
    if (data && in_cert) {
 | 
			
		||||
	free(data);
 | 
			
		||||
	return 1;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    ret = decode_Certificate(data, len, t, &size);
 | 
			
		||||
    free(data);
 | 
			
		||||
    if (ret != 0) {
 | 
			
		||||
	return 1;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
file_init(hx509_certs certs, void **data, int flags, 
 | 
			
		||||
	  const char *residue, hx509_lock lock)
 | 
			
		||||
{
 | 
			
		||||
    char *certfn, *keyfn, *friendlyname = NULL;
 | 
			
		||||
    hx509_cert cert;
 | 
			
		||||
 | 
			
		||||
    *data = NULL;
 | 
			
		||||
 | 
			
		||||
    certfn = strdup(residue);
 | 
			
		||||
    if (certfn == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
    keyfn = strchr(certfn, ',');
 | 
			
		||||
    if (keyfn) {
 | 
			
		||||
	*keyfn++ = '\0';
 | 
			
		||||
	friendlyname = strchr(keyfn, ',');
 | 
			
		||||
	if (friendlyname)
 | 
			
		||||
	    *friendlyname++ = '\0';
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    {
 | 
			
		||||
	Certificate t;
 | 
			
		||||
	int ret;
 | 
			
		||||
 | 
			
		||||
	ret = parse_certificate(certfn, 1, &t);
 | 
			
		||||
	if (ret)
 | 
			
		||||
	    ret = parse_certificate(certfn, 0, &t);
 | 
			
		||||
	if (ret) {
 | 
			
		||||
	    free(certfn);
 | 
			
		||||
	    return ret;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	ret = hx509_cert_init(&t, &cert);
 | 
			
		||||
	free_Certificate(&t);
 | 
			
		||||
	if (ret) {
 | 
			
		||||
	    free(certfn);
 | 
			
		||||
	    return ret;
 | 
			
		||||
	}
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    if (keyfn) {
 | 
			
		||||
	int ret;
 | 
			
		||||
	ret = _hx509_cert_assign_private_key_file(cert, lock, keyfn);
 | 
			
		||||
	if (ret) {
 | 
			
		||||
	    hx509_cert_free(cert);
 | 
			
		||||
	    free(certfn);
 | 
			
		||||
	    return ret;
 | 
			
		||||
	}
 | 
			
		||||
    }
 | 
			
		||||
    if (friendlyname) {
 | 
			
		||||
	int ret;
 | 
			
		||||
	ret = hx509_cert_set_friendly_name(cert, friendlyname);
 | 
			
		||||
	if (ret) {
 | 
			
		||||
	    hx509_cert_free(cert);
 | 
			
		||||
	    free(certfn);
 | 
			
		||||
	    return ret;
 | 
			
		||||
	}
 | 
			
		||||
    }
 | 
			
		||||
    free(certfn);
 | 
			
		||||
 | 
			
		||||
    *data = cert;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
file_free(hx509_certs certs, void *data)
 | 
			
		||||
{
 | 
			
		||||
    hx509_cert_free(data);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
static int 
 | 
			
		||||
file_iter_start(hx509_certs certs, void *data, void **cursor)
 | 
			
		||||
{
 | 
			
		||||
    int *i;
 | 
			
		||||
 | 
			
		||||
    i = malloc(sizeof(*i));
 | 
			
		||||
    if (i == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
    *i = 0;
 | 
			
		||||
    *cursor = i;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
file_iter(hx509_certs certs, void *data, void *iter, hx509_cert *cert)
 | 
			
		||||
{
 | 
			
		||||
    int *i = iter;
 | 
			
		||||
    if (*i != 0)
 | 
			
		||||
	return 0;
 | 
			
		||||
    *cert = hx509_cert_ref((hx509_cert)data);
 | 
			
		||||
    (*i)++;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
file_iter_end(hx509_certs certs,
 | 
			
		||||
	      void *data,
 | 
			
		||||
	      void *cursor)
 | 
			
		||||
{
 | 
			
		||||
    free(cursor);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
static struct hx509_keyset_ops keyset_file = {
 | 
			
		||||
    "FILE",
 | 
			
		||||
    0,
 | 
			
		||||
    file_init,
 | 
			
		||||
    file_free,
 | 
			
		||||
    NULL,
 | 
			
		||||
    NULL,
 | 
			
		||||
    file_iter_start,
 | 
			
		||||
    file_iter,
 | 
			
		||||
    file_iter_end
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
_hx509_ks_file_register(void)
 | 
			
		||||
{
 | 
			
		||||
    _hx509_ks_register(&keyset_file);
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										150
									
								
								lib/hx509/ks_mem.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										150
									
								
								lib/hx509/ks_mem.c
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,150 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "hx_locl.h"
 | 
			
		||||
RCSID("$ID$");
 | 
			
		||||
 | 
			
		||||
struct mem_data {
 | 
			
		||||
    char *name;
 | 
			
		||||
    unsigned long len;
 | 
			
		||||
    hx509_cert *val;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
mem_init(hx509_certs certs, void **data, int flags,
 | 
			
		||||
	 const char *residue, hx509_lock lock)
 | 
			
		||||
{
 | 
			
		||||
    struct mem_data *mem;
 | 
			
		||||
    mem = calloc(1, sizeof(*mem));
 | 
			
		||||
    if (mem == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
    if (residue == NULL || residue[0] == '\0')
 | 
			
		||||
	residue = "anonymous";
 | 
			
		||||
    mem->name = strdup(residue);
 | 
			
		||||
    if (mem->name == NULL) {
 | 
			
		||||
	free(mem);
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
    }
 | 
			
		||||
    *data = mem;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
mem_free(hx509_certs certs, void *data)
 | 
			
		||||
{
 | 
			
		||||
    struct mem_data *mem = data;
 | 
			
		||||
    unsigned long i;
 | 
			
		||||
    
 | 
			
		||||
    for (i = 0; i < mem->len; i++)
 | 
			
		||||
	hx509_cert_free(mem->val[i]);
 | 
			
		||||
    free(mem->val);
 | 
			
		||||
    free(mem->name);
 | 
			
		||||
    free(mem);
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int 
 | 
			
		||||
mem_add(hx509_certs certs, void *data, hx509_cert c)
 | 
			
		||||
{
 | 
			
		||||
    struct mem_data *mem = data;
 | 
			
		||||
    hx509_cert *val;
 | 
			
		||||
 | 
			
		||||
    val = realloc(mem->val, (mem->len + 1) * sizeof(mem->val[0]));
 | 
			
		||||
    if (val == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
 | 
			
		||||
    mem->val = val;
 | 
			
		||||
    mem->val[mem->len] = hx509_cert_ref(c);
 | 
			
		||||
    mem->len++;
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int 
 | 
			
		||||
mem_iter_start(hx509_certs certs, void *data, void **cursor)
 | 
			
		||||
{
 | 
			
		||||
    unsigned long *iter = malloc(sizeof(*iter));
 | 
			
		||||
 | 
			
		||||
    if (iter == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
 | 
			
		||||
    *iter = 0;
 | 
			
		||||
    *cursor = iter;
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
mem_iter(hx509_certs certs,
 | 
			
		||||
	 void *data, 
 | 
			
		||||
	 void *cursor,
 | 
			
		||||
	 hx509_cert *cert)
 | 
			
		||||
{
 | 
			
		||||
    unsigned long *iter = cursor;
 | 
			
		||||
    struct mem_data *mem = data;
 | 
			
		||||
 | 
			
		||||
    if (*iter >= mem->len)
 | 
			
		||||
	return ENOENT;
 | 
			
		||||
 | 
			
		||||
    *cert = hx509_cert_ref(mem->val[*iter]);
 | 
			
		||||
    (*iter)++;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
mem_iter_end(hx509_certs certs,
 | 
			
		||||
	     void *data,
 | 
			
		||||
	     void *cursor)
 | 
			
		||||
{
 | 
			
		||||
    free(cursor);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static struct hx509_keyset_ops keyset_mem = {
 | 
			
		||||
    "MEMORY",
 | 
			
		||||
    0,
 | 
			
		||||
    mem_init,
 | 
			
		||||
    mem_free,
 | 
			
		||||
    mem_add,
 | 
			
		||||
    NULL,
 | 
			
		||||
    mem_iter_start,
 | 
			
		||||
    mem_iter,
 | 
			
		||||
    mem_iter_end
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
_hx509_ks_mem_register(void)
 | 
			
		||||
{
 | 
			
		||||
    _hx509_ks_register(&keyset_mem);
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										89
									
								
								lib/hx509/ks_null.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										89
									
								
								lib/hx509/ks_null.c
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,89 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "hx_locl.h"
 | 
			
		||||
RCSID("$ID$");
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
null_init(hx509_certs certs, void **data, int flags,
 | 
			
		||||
	  const char *residue, hx509_lock lock)
 | 
			
		||||
{
 | 
			
		||||
    *data = NULL;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
null_free(hx509_certs certs, void *data)
 | 
			
		||||
{
 | 
			
		||||
    assert(data == NULL);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int 
 | 
			
		||||
null_iter_start(hx509_certs certs, void *data, void **cursor)
 | 
			
		||||
{
 | 
			
		||||
    *cursor = NULL;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
null_iter(hx509_certs certs, void *data, void *iter, hx509_cert *cert)
 | 
			
		||||
{
 | 
			
		||||
    *cert = NULL;
 | 
			
		||||
    return ENOENT;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
null_iter_end(hx509_certs certs,
 | 
			
		||||
	      void *data,
 | 
			
		||||
	      void *cursor)
 | 
			
		||||
{
 | 
			
		||||
    assert(cursor == NULL);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
struct hx509_keyset_ops keyset_null = {
 | 
			
		||||
    "NULL",
 | 
			
		||||
    0,
 | 
			
		||||
    null_init,
 | 
			
		||||
    null_free,
 | 
			
		||||
    NULL,
 | 
			
		||||
    NULL,
 | 
			
		||||
    null_iter_start,
 | 
			
		||||
    null_iter,
 | 
			
		||||
    null_iter_end
 | 
			
		||||
};
 | 
			
		||||
							
								
								
									
										526
									
								
								lib/hx509/ks_p12.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										526
									
								
								lib/hx509/ks_p12.c
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,526 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2004 - 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "hx_locl.h"
 | 
			
		||||
RCSID("$Id$");
 | 
			
		||||
 | 
			
		||||
struct ks_pkcs12 {
 | 
			
		||||
    hx509_certs certs;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct private_key {
 | 
			
		||||
    AlgorithmIdentifier alg;
 | 
			
		||||
    heim_octet_string data;
 | 
			
		||||
    heim_octet_string localKeyId;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct collector {
 | 
			
		||||
    hx509_lock lock;
 | 
			
		||||
    hx509_certs unenvelop_certs;
 | 
			
		||||
    hx509_certs certs;
 | 
			
		||||
    struct {
 | 
			
		||||
	struct private_key **data;
 | 
			
		||||
	size_t len;
 | 
			
		||||
    } val;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
typedef int (*collector_func)(struct collector *, const void *, size_t,
 | 
			
		||||
			      const PKCS12_Attributes *);
 | 
			
		||||
 | 
			
		||||
struct type {
 | 
			
		||||
    const heim_oid * (*oid)(void);
 | 
			
		||||
    collector_func func;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
parse_pkcs12_type(struct collector *, const heim_oid *, 
 | 
			
		||||
		  const void *, size_t, const PKCS12_Attributes *);
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
static const PKCS12_Attribute *
 | 
			
		||||
find_attribute(const PKCS12_Attributes *attrs, const heim_oid *oid)
 | 
			
		||||
{
 | 
			
		||||
    int i;
 | 
			
		||||
    if (attrs == NULL)
 | 
			
		||||
	return NULL;
 | 
			
		||||
    for (i = 0; i < attrs->len; i++)
 | 
			
		||||
	if (heim_oid_cmp(oid, &attrs->val[i].attrId) == 0)
 | 
			
		||||
	    return &attrs->val[i];
 | 
			
		||||
    return NULL;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
ShroudedKeyBag_parser(struct collector *c, const void *data, size_t length,
 | 
			
		||||
		      const PKCS12_Attributes *attrs)
 | 
			
		||||
{
 | 
			
		||||
    struct private_key *key;
 | 
			
		||||
    const PKCS12_Attribute *attr;
 | 
			
		||||
    PKCS8EncryptedPrivateKeyInfo pk;
 | 
			
		||||
    PKCS8PrivateKeyInfo ki;
 | 
			
		||||
    heim_octet_string content;
 | 
			
		||||
    const struct _hx509_password *pw;
 | 
			
		||||
    int i;
 | 
			
		||||
    int ret;
 | 
			
		||||
    
 | 
			
		||||
    printf("pkcs8ShroudedKeyBag\n");
 | 
			
		||||
    memset(&pk, 0, sizeof(pk));
 | 
			
		||||
    
 | 
			
		||||
    attr = find_attribute(attrs, oid_id_pkcs_9_at_localKeyId());
 | 
			
		||||
    if (attr == NULL) {
 | 
			
		||||
	printf("no localKeyId, ignoreing private key\n");
 | 
			
		||||
	return 0;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    ret = decode_PKCS8EncryptedPrivateKeyInfo(data, length, &pk, NULL);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	printf("PKCS8EncryptedPrivateKeyInfo returned %d\n", ret);
 | 
			
		||||
	return ret;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    pw = _hx509_lock_get_passwords(c->lock);
 | 
			
		||||
 | 
			
		||||
    ret = HX509_CRYPTO_INTERNAL_ERROR;
 | 
			
		||||
    for (i = 0; i < pw->len; i++) {
 | 
			
		||||
	ret = _hx509_pbe_decrypt(pw->val[i],
 | 
			
		||||
				 &pk.encryptionAlgorithm,
 | 
			
		||||
				 &pk.encryptedData,
 | 
			
		||||
				 &content);
 | 
			
		||||
	if (ret == 0)
 | 
			
		||||
	    break;
 | 
			
		||||
    }
 | 
			
		||||
    free_PKCS8EncryptedPrivateKeyInfo(&pk);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	printf("decrypt encryped failed %d\n", ret);
 | 
			
		||||
	return ret;
 | 
			
		||||
    }
 | 
			
		||||
    ret = decode_PKCS8PrivateKeyInfo(content.data, content.length,
 | 
			
		||||
				     &ki, NULL);
 | 
			
		||||
    free_octet_string(&content);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	printf("PKCS8PrivateKeyInfo returned %d\n", ret);
 | 
			
		||||
	return ret;
 | 
			
		||||
    }
 | 
			
		||||
    
 | 
			
		||||
    key = malloc(sizeof(*key));
 | 
			
		||||
    if (key == NULL) {
 | 
			
		||||
	free_PKCS8PrivateKeyInfo(&ki);
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    copy_AlgorithmIdentifier(&ki.privateKeyAlgorithm, &key->alg);
 | 
			
		||||
    copy_octet_string(&ki.privateKey, &key->data);
 | 
			
		||||
    copy_octet_string(&attr->attrValues, &key->localKeyId);
 | 
			
		||||
    free_PKCS8PrivateKeyInfo(&ki);
 | 
			
		||||
 | 
			
		||||
    {
 | 
			
		||||
	void *d;
 | 
			
		||||
	d = realloc(c->val.data, (c->val.len + 1) * sizeof(c->val.data[0]));
 | 
			
		||||
	if (d == NULL) {
 | 
			
		||||
	    abort();
 | 
			
		||||
	}
 | 
			
		||||
	c->val.data = d;
 | 
			
		||||
	c->val.data[c->val.len] = key;
 | 
			
		||||
	c->val.len++;
 | 
			
		||||
    }
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
certBag_parser(struct collector *c, const void *data, size_t length,
 | 
			
		||||
	       const PKCS12_Attributes *attrs)
 | 
			
		||||
{
 | 
			
		||||
    heim_octet_string os;
 | 
			
		||||
    Certificate t;
 | 
			
		||||
    hx509_cert cert;
 | 
			
		||||
    PKCS12_CertBag cb;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    printf("certBag\n");
 | 
			
		||||
 | 
			
		||||
    ret = decode_PKCS12_CertBag(data, length, &cb, NULL);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	return ret;
 | 
			
		||||
 | 
			
		||||
    {
 | 
			
		||||
	char *str;
 | 
			
		||||
	hx509_oid_sprint(&cb.certType, &str);
 | 
			
		||||
	printf("oid: %s\n", str);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    ret = decode_PKCS12_OctetString(cb.certValue.data, 
 | 
			
		||||
				    cb.certValue.length,
 | 
			
		||||
				    &os,
 | 
			
		||||
				    NULL);
 | 
			
		||||
    free_PKCS12_CertBag(&cb);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	printf("failed with %d\n", ret);
 | 
			
		||||
	return 1;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    ret = decode_Certificate(os.data, os.length, &t, NULL);
 | 
			
		||||
    free_octet_string(&os);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	printf("failed with %d\n", ret);
 | 
			
		||||
	return 1;
 | 
			
		||||
    }
 | 
			
		||||
    printf("cert parsed ok\n");
 | 
			
		||||
 | 
			
		||||
    ret = hx509_cert_init(&t, &cert);
 | 
			
		||||
    free_Certificate(&t);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	return ret;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    ret = hx509_certs_add(c->certs, cert);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	hx509_cert_free(cert);
 | 
			
		||||
	return ret;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    {
 | 
			
		||||
	const PKCS12_Attribute *attr;
 | 
			
		||||
	const heim_oid * (*oids[])(void) = {
 | 
			
		||||
	    oid_id_pkcs_9_at_localKeyId, oid_id_pkcs_9_at_friendlyName
 | 
			
		||||
	};
 | 
			
		||||
	int i;
 | 
			
		||||
 | 
			
		||||
	for (i = 0; i < sizeof(oids)/sizeof(oids[0]); i++) {
 | 
			
		||||
	    const heim_oid *oid = (*(oids[i]))();
 | 
			
		||||
	    attr = find_attribute(attrs, oid);
 | 
			
		||||
	    if (attr)
 | 
			
		||||
		_hx509_set_cert_attribute(cert, oid, &attr->attrValues);
 | 
			
		||||
	}	
 | 
			
		||||
    }
 | 
			
		||||
    {
 | 
			
		||||
	const char *s = hx509_cert_get_friendly_name(cert);
 | 
			
		||||
	printf("cert name: %s\n", s ? s : "no name set");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
parse_safe_content(struct collector *c, const unsigned char *p, size_t len)
 | 
			
		||||
{
 | 
			
		||||
    PKCS12_SafeContents sc;
 | 
			
		||||
    int ret, i;
 | 
			
		||||
 | 
			
		||||
    memset(&sc, 0, sizeof(sc));
 | 
			
		||||
 | 
			
		||||
    ret = decode_PKCS12_SafeContents(p, len, &sc, NULL);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	return ret;
 | 
			
		||||
 | 
			
		||||
    for (i = 0; i < sc.len ; i++)
 | 
			
		||||
	parse_pkcs12_type(c,
 | 
			
		||||
			  &sc.val[i].bagId,
 | 
			
		||||
			  sc.val[i].bagValue.data,
 | 
			
		||||
			  sc.val[i].bagValue.length,
 | 
			
		||||
			  sc.val[i].bagAttributes);
 | 
			
		||||
 | 
			
		||||
    free_PKCS12_SafeContents(&sc);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
safeContent_parser(struct collector *c, const void *data, size_t length,
 | 
			
		||||
	       const PKCS12_Attributes *attrs)
 | 
			
		||||
{
 | 
			
		||||
    heim_octet_string os;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    printf("safeContent\n");
 | 
			
		||||
 | 
			
		||||
    ret = decode_PKCS12_OctetString(data, length, &os, NULL);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	return 1;
 | 
			
		||||
    ret = parse_safe_content(c, os.data, os.length);
 | 
			
		||||
    free_octet_string(&os);
 | 
			
		||||
    return ret;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
encryptedData_parser(struct collector *c, const void *data, size_t length,
 | 
			
		||||
	       const PKCS12_Attributes *attrs)
 | 
			
		||||
{
 | 
			
		||||
    heim_octet_string content;
 | 
			
		||||
    heim_oid contentType;
 | 
			
		||||
    int ret;
 | 
			
		||||
		
 | 
			
		||||
    memset(&contentType, 0, sizeof(contentType));
 | 
			
		||||
 | 
			
		||||
    ret = hx509_cms_decrypt_encrypted(c->lock,
 | 
			
		||||
				      data, length,
 | 
			
		||||
				      &contentType,
 | 
			
		||||
				      &content);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	printf("decrypt encryped failed %d\n", ret);
 | 
			
		||||
    else {
 | 
			
		||||
	if (content.length == 0) {
 | 
			
		||||
	    printf("no content in encryped data\n");
 | 
			
		||||
	} else if (heim_oid_cmp(&contentType, oid_id_pkcs7_data()) == 0) {
 | 
			
		||||
	    ret = parse_safe_content(c, content.data, content.length);
 | 
			
		||||
	    if (ret)
 | 
			
		||||
		printf("parse_safe_content failed with %d\n", ret);
 | 
			
		||||
	}
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
envelopedData_parser(struct collector *c, const void *data, size_t length,
 | 
			
		||||
		     const PKCS12_Attributes *attrs)
 | 
			
		||||
{
 | 
			
		||||
    heim_octet_string content;
 | 
			
		||||
    heim_oid contentType;
 | 
			
		||||
    int ret;
 | 
			
		||||
		
 | 
			
		||||
    memset(&contentType, 0, sizeof(contentType));
 | 
			
		||||
 | 
			
		||||
    ret = hx509_cms_unenvelope(c->unenvelop_certs,
 | 
			
		||||
			       data, length,
 | 
			
		||||
			       &contentType,
 | 
			
		||||
			       &content);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	printf("unenveloped failed %d\n", ret);
 | 
			
		||||
    else {
 | 
			
		||||
	if (content.length == 0) {
 | 
			
		||||
	    printf("no content enveloped data\n");
 | 
			
		||||
	} else if (heim_oid_cmp(&contentType, oid_id_pkcs7_data()) == 0) {
 | 
			
		||||
	    ret = parse_safe_content(c, content.data, content.length);
 | 
			
		||||
	    if (ret)
 | 
			
		||||
		printf("parse_safe_content failed with %d\n", ret);
 | 
			
		||||
	}
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
struct type bagtypes[] = {
 | 
			
		||||
    { oid_id_pkcs12_pkcs8ShroudedKeyBag, ShroudedKeyBag_parser },
 | 
			
		||||
    { oid_id_pkcs12_certBag, certBag_parser },
 | 
			
		||||
    { oid_id_pkcs7_data, safeContent_parser },
 | 
			
		||||
    { oid_id_pkcs7_encryptedData, encryptedData_parser },
 | 
			
		||||
    { oid_id_pkcs7_envelopedData, envelopedData_parser }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
parse_pkcs12_type(struct collector *c, const heim_oid *oid, 
 | 
			
		||||
		  const void *data, size_t length,
 | 
			
		||||
		  const PKCS12_Attributes *attrs)
 | 
			
		||||
{
 | 
			
		||||
    int i;
 | 
			
		||||
 | 
			
		||||
    for (i = 0; i < sizeof(bagtypes)/sizeof(bagtypes[0]); i++) {
 | 
			
		||||
	if (heim_oid_cmp((*bagtypes[i].oid)(), oid) == 0) {
 | 
			
		||||
	    (*bagtypes[i].func)(c, data, length, attrs);
 | 
			
		||||
	    return 0;
 | 
			
		||||
	}
 | 
			
		||||
    }
 | 
			
		||||
    return 1;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
p12_init(hx509_certs certs, void **data, int flags, 
 | 
			
		||||
	 const char *residue, hx509_lock lock)
 | 
			
		||||
{
 | 
			
		||||
    size_t len;
 | 
			
		||||
    void *buf;
 | 
			
		||||
    PKCS12_PFX pfx;
 | 
			
		||||
    PKCS12_AuthenticatedSafe as;
 | 
			
		||||
    int ret, i;
 | 
			
		||||
    struct collector c;
 | 
			
		||||
 | 
			
		||||
    *data = NULL;
 | 
			
		||||
 | 
			
		||||
    if (lock == NULL)
 | 
			
		||||
	lock = _hx509_empty_lock;
 | 
			
		||||
 | 
			
		||||
    ret = _hx509_map_file(residue, &buf, &len);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	return ret;
 | 
			
		||||
 | 
			
		||||
    ret = decode_PKCS12_PFX(buf, len, &pfx, NULL);
 | 
			
		||||
    _hx509_unmap_file(buf, len);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	return ret;
 | 
			
		||||
 | 
			
		||||
    if (heim_oid_cmp(&pfx.authSafe.contentType, oid_id_pkcs7_data()) != 0) {
 | 
			
		||||
	free_PKCS12_PFX(&pfx);
 | 
			
		||||
	ret = EINVAL;
 | 
			
		||||
	goto out;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    if (pfx.authSafe.content == NULL) {
 | 
			
		||||
	free_PKCS12_PFX(&pfx);
 | 
			
		||||
	ret = EINVAL;
 | 
			
		||||
	goto out;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    {
 | 
			
		||||
	heim_octet_string asdata;
 | 
			
		||||
 | 
			
		||||
	ret = decode_PKCS12_OctetString(pfx.authSafe.content->data,
 | 
			
		||||
					pfx.authSafe.content->length,
 | 
			
		||||
					&asdata,
 | 
			
		||||
					NULL);
 | 
			
		||||
	free_PKCS12_PFX(&pfx);
 | 
			
		||||
	if (ret)
 | 
			
		||||
	    goto out;
 | 
			
		||||
	ret = decode_PKCS12_AuthenticatedSafe(asdata.data, 
 | 
			
		||||
					      asdata.length,
 | 
			
		||||
					      &as,
 | 
			
		||||
					      NULL);
 | 
			
		||||
	free_octet_string(&asdata);
 | 
			
		||||
	if (ret)
 | 
			
		||||
	    goto out;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    c.lock = lock;
 | 
			
		||||
    hx509_certs_init("MEMORY:dummy", 0, NULL, &c.unenvelop_certs);
 | 
			
		||||
    c.val.data = NULL;
 | 
			
		||||
    c.val.len = 0;
 | 
			
		||||
    hx509_certs_init("MEMORY:pkcs12-store", 0, NULL, &c.certs);
 | 
			
		||||
 | 
			
		||||
    for (i = 0; i < as.len; i++) {
 | 
			
		||||
	parse_pkcs12_type(&c,
 | 
			
		||||
			  &as.val[i].contentType,
 | 
			
		||||
			  as.val[i].content->data,
 | 
			
		||||
			  as.val[i].content->length,
 | 
			
		||||
			  NULL);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    free_PKCS12_AuthenticatedSafe(&as);
 | 
			
		||||
 | 
			
		||||
    printf("found %d private keys\n", c.val.len);
 | 
			
		||||
 | 
			
		||||
    for (i = 0; i < c.val.len; i++) {
 | 
			
		||||
	hx509_cert cert;
 | 
			
		||||
	hx509_query q;
 | 
			
		||||
 | 
			
		||||
	_hx509_query_clear(&q);
 | 
			
		||||
	q.match |= HX509_QUERY_MATCH_LOCAL_KEY_ID;
 | 
			
		||||
 | 
			
		||||
	q.local_key_id = &c.val.data[i]->localKeyId;
 | 
			
		||||
 | 
			
		||||
	ret = _hx509_certs_find(c.certs, &q, &cert);
 | 
			
		||||
	if (ret == 0) {
 | 
			
		||||
	    hx509_private_key key;
 | 
			
		||||
 | 
			
		||||
	    ret = _hx509_parse_private_key(&c.val.data[i]->alg.algorithm,
 | 
			
		||||
					   c.val.data[i]->data.data,
 | 
			
		||||
					   c.val.data[i]->data.length,
 | 
			
		||||
					   &key);
 | 
			
		||||
	    if (ret == 0)
 | 
			
		||||
		_hx509_cert_assign_key(cert, key);
 | 
			
		||||
	    else
 | 
			
		||||
		printf("failed to parse key: %d\n", ret);
 | 
			
		||||
 | 
			
		||||
	    hx509_cert_free(cert);
 | 
			
		||||
	}
 | 
			
		||||
	free_octet_string(&c.val.data[i]->localKeyId);
 | 
			
		||||
	free_octet_string(&c.val.data[i]->data);
 | 
			
		||||
	free_AlgorithmIdentifier(&c.val.data[i]->alg);
 | 
			
		||||
	free(c.val.data[i]);
 | 
			
		||||
    }
 | 
			
		||||
    free(c.val.data);
 | 
			
		||||
 | 
			
		||||
    {
 | 
			
		||||
	struct ks_pkcs12 *p12;
 | 
			
		||||
	p12 = malloc(sizeof(*p12));
 | 
			
		||||
	if (p12 == NULL) {
 | 
			
		||||
	    abort();
 | 
			
		||||
	}
 | 
			
		||||
	memset(p12, 0, sizeof(*p12));
 | 
			
		||||
	p12->certs = c.certs;
 | 
			
		||||
	*data = p12;
 | 
			
		||||
    }
 | 
			
		||||
    ret = 0;
 | 
			
		||||
 out:
 | 
			
		||||
    return ret;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
p12_free(hx509_certs certs, void *data)
 | 
			
		||||
{
 | 
			
		||||
    struct ks_pkcs12 *p12 = data;
 | 
			
		||||
    hx509_certs_free(&p12->certs);
 | 
			
		||||
    free(p12);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int 
 | 
			
		||||
p12_iter_start(hx509_certs certs, void *data, void **cursor)
 | 
			
		||||
{
 | 
			
		||||
    struct ks_pkcs12 *p12 = data;
 | 
			
		||||
    return hx509_certs_start_seq(p12->certs, cursor);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
p12_iter(hx509_certs certs, void *data, void *cursor, hx509_cert *cert)
 | 
			
		||||
{
 | 
			
		||||
    struct ks_pkcs12 *p12 = data;
 | 
			
		||||
    return hx509_certs_next_cert(p12->certs, cursor, cert);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
p12_iter_end(hx509_certs certs,
 | 
			
		||||
	      void *data,
 | 
			
		||||
	      void *cursor)
 | 
			
		||||
{
 | 
			
		||||
    struct ks_pkcs12 *p12 = data;
 | 
			
		||||
    return hx509_certs_end_seq(p12->certs, cursor);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
static struct hx509_keyset_ops keyset_pkcs12 = {
 | 
			
		||||
    "PKCS12",
 | 
			
		||||
    0,
 | 
			
		||||
    p12_init,
 | 
			
		||||
    p12_free,
 | 
			
		||||
    NULL,
 | 
			
		||||
    NULL,
 | 
			
		||||
    p12_iter_start,
 | 
			
		||||
    p12_iter,
 | 
			
		||||
    p12_iter_end
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
_hx509_ks_pkcs12_register(void)
 | 
			
		||||
{
 | 
			
		||||
    _hx509_ks_register(&keyset_pkcs12);
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										187
									
								
								lib/hx509/lock.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										187
									
								
								lib/hx509/lock.c
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,187 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "hx_locl.h"
 | 
			
		||||
RCSID("$ID$");
 | 
			
		||||
 | 
			
		||||
struct hx509_lock_data {
 | 
			
		||||
    struct _hx509_password password;
 | 
			
		||||
    hx509_certs certs;
 | 
			
		||||
    hx509_prompter_fct *prompt;
 | 
			
		||||
    void *prompt_data;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
static struct hx509_lock_data empty_lock_data = {
 | 
			
		||||
    { 0, NULL }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
hx509_lock _hx509_empty_lock = &empty_lock_data;
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 *
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_lock_init(hx509_lock *lock)
 | 
			
		||||
{
 | 
			
		||||
    hx509_lock l;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    *lock = NULL;
 | 
			
		||||
 | 
			
		||||
    l = calloc(1, sizeof(*l));
 | 
			
		||||
    if (l == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
 | 
			
		||||
    ret = hx509_certs_init("MEMORY:locks-internal", 0, NULL, &l->certs);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	free(l);
 | 
			
		||||
	return ret;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    *lock = l;
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_lock_add_password(hx509_lock lock, const char *password)
 | 
			
		||||
{
 | 
			
		||||
    void *d;
 | 
			
		||||
    char *s;
 | 
			
		||||
 | 
			
		||||
    s = strdup(password);
 | 
			
		||||
    if (s == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
 | 
			
		||||
    d = realloc(lock->password.val,
 | 
			
		||||
		(lock->password.len + 1) * sizeof(lock->password.val[0]));
 | 
			
		||||
    if (d == NULL) {
 | 
			
		||||
	free(s);
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
    }
 | 
			
		||||
    lock->password.val = d;
 | 
			
		||||
    lock->password.val[lock->password.len] = s;
 | 
			
		||||
    lock->password.len++;
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const struct _hx509_password *
 | 
			
		||||
_hx509_lock_get_passwords(hx509_lock lock)
 | 
			
		||||
{
 | 
			
		||||
    return &lock->password;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_lock_reset_passwords(hx509_lock lock)
 | 
			
		||||
{
 | 
			
		||||
    int i;
 | 
			
		||||
    for (i = 0; i < lock->password.len; i++)
 | 
			
		||||
	free(lock->password.val[i]);
 | 
			
		||||
    free(lock->password.val);
 | 
			
		||||
    lock->password.val = NULL;
 | 
			
		||||
    lock->password.len = 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_lock_add_cert(hx509_lock lock, hx509_cert cert)
 | 
			
		||||
{
 | 
			
		||||
    return hx509_certs_add(lock->certs, cert);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_lock_add_certs(hx509_lock lock, hx509_certs certs)
 | 
			
		||||
{
 | 
			
		||||
    return hx509_certs_merge(lock->certs, certs);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_lock_reset_certs(hx509_lock lock)
 | 
			
		||||
{
 | 
			
		||||
    hx509_certs certs = lock->certs;
 | 
			
		||||
    int ret;
 | 
			
		||||
    
 | 
			
		||||
    ret = hx509_certs_init("MEMORY:locks-internal", 0, NULL, &lock->certs);
 | 
			
		||||
    if (ret == 0)
 | 
			
		||||
	hx509_certs_free(&certs);
 | 
			
		||||
    else
 | 
			
		||||
	lock->certs = certs;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
_hx509_lock_find_cert(hx509_lock lock, const hx509_query *q, hx509_cert *c)
 | 
			
		||||
{
 | 
			
		||||
    *c = NULL;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_lock_set_prompter(hx509_lock lock, hx509_prompter_fct *prompt)
 | 
			
		||||
{
 | 
			
		||||
    lock->prompt = prompt;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_lock_set_prompter_data(hx509_lock lock, void *data)
 | 
			
		||||
{
 | 
			
		||||
    lock->prompt_data = data;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_lock_reset_promper(hx509_lock lock)
 | 
			
		||||
{
 | 
			
		||||
    lock->prompt = NULL;
 | 
			
		||||
    lock->prompt_data = NULL;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_lock_prompt(hx509_lock lock, hx509_prompt *prompt)
 | 
			
		||||
{
 | 
			
		||||
    if (lock->prompt == NULL) {
 | 
			
		||||
	strlcpy(prompt->reply->data, "", prompt->reply->length);
 | 
			
		||||
	return 0;
 | 
			
		||||
    }
 | 
			
		||||
    return (*lock->prompt)(lock->prompt_data, prompt);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_lock_free(hx509_lock lock)
 | 
			
		||||
{
 | 
			
		||||
    hx509_certs_free(&lock->certs);
 | 
			
		||||
    hx509_lock_reset_passwords(lock);
 | 
			
		||||
    memset(lock, 0, sizeof(*lock));
 | 
			
		||||
    free(lock);
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										322
									
								
								lib/hx509/name.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										322
									
								
								lib/hx509/name.c
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,322 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2004 - 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "hx_locl.h"
 | 
			
		||||
RCSID("$ID$");
 | 
			
		||||
 | 
			
		||||
/* 
 | 
			
		||||
 * name parsing from rfc2253
 | 
			
		||||
 * fix so parsing rfc1779 works too 
 | 
			
		||||
 * rfc3280
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#define oid_enc(n) { sizeof(n)/sizeof(n[0]), n }
 | 
			
		||||
 | 
			
		||||
static unsigned country_num[] = { 2, 5, 4, 6 };
 | 
			
		||||
static heim_oid country_oid = oid_enc(country_num);
 | 
			
		||||
static unsigned organizationName_num[] = { 2, 5, 4, 10 };
 | 
			
		||||
static heim_oid organizationName_oid = oid_enc(organizationName_num);
 | 
			
		||||
static unsigned commonName_num[] = { 2, 5, 4, 3 };
 | 
			
		||||
static heim_oid commonName_oid = oid_enc(commonName_num);
 | 
			
		||||
static unsigned localityName_num[] = { 2, 5, 4, 7 };
 | 
			
		||||
static heim_oid localityName_oid = oid_enc(localityName_num);
 | 
			
		||||
static unsigned email_num[] = { 1, 2, 840, 113549, 1, 9, 1 };
 | 
			
		||||
static heim_oid email_oid = oid_enc(email_num);
 | 
			
		||||
static unsigned uid_num[] = { 0, 9, 2342, 19200300, 100, 1, 1 };
 | 
			
		||||
static heim_oid uid_oid = oid_enc(uid_num);
 | 
			
		||||
 | 
			
		||||
static const struct {
 | 
			
		||||
    char *n;
 | 
			
		||||
    heim_oid *o;
 | 
			
		||||
} no[] = {
 | 
			
		||||
    { "C", &country_oid },
 | 
			
		||||
    { "CN", &commonName_oid },
 | 
			
		||||
    { "O", &organizationName_oid },
 | 
			
		||||
    { "L", &localityName_oid },
 | 
			
		||||
    { "Email", &email_oid },
 | 
			
		||||
    { "UID", &uid_oid }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
static char *
 | 
			
		||||
quote_string(const char *f, size_t len, size_t *rlen)
 | 
			
		||||
{
 | 
			
		||||
    size_t i, j, tolen;
 | 
			
		||||
    const unsigned char *from = f;
 | 
			
		||||
    unsigned char *to;
 | 
			
		||||
 | 
			
		||||
    tolen = len * 3 + 1;
 | 
			
		||||
    to = malloc(tolen);
 | 
			
		||||
    if (to == NULL)
 | 
			
		||||
	return NULL;
 | 
			
		||||
 | 
			
		||||
    for (i = 0, j = 0; i < len; i++) {
 | 
			
		||||
	if (from[i] == ' ' && i + 1 < len)
 | 
			
		||||
	    to[j++] = from[i];
 | 
			
		||||
	else if (from[i] == ',' || from[i] == '=' || from[i] == '+' ||
 | 
			
		||||
		 from[i] == '<' || from[i] == '>' || from[i] == '#' ||
 | 
			
		||||
		 from[i] == ';' || from[i] == ' ')
 | 
			
		||||
	{
 | 
			
		||||
	    to[j++] = '\\';
 | 
			
		||||
	    to[j++] = from[i];
 | 
			
		||||
	} else if (from[i] >= 32 && from[i] <= 127) {
 | 
			
		||||
	    to[j++] = from[i];
 | 
			
		||||
	} else {
 | 
			
		||||
	    int l = snprintf(&to[j], tolen - j - 1,
 | 
			
		||||
			     "#%02x", (unsigned int)from[i]);
 | 
			
		||||
	    j += l;
 | 
			
		||||
	}
 | 
			
		||||
    }
 | 
			
		||||
    to[j] = '\0';
 | 
			
		||||
    *rlen = j;
 | 
			
		||||
    return to;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
append_string(char **str, size_t *total_len, char *ss, size_t len, int quote)
 | 
			
		||||
{
 | 
			
		||||
    char *s, *qs;
 | 
			
		||||
 | 
			
		||||
    if (quote)
 | 
			
		||||
	qs = quote_string(ss, len, &len);
 | 
			
		||||
    else
 | 
			
		||||
	qs = ss;
 | 
			
		||||
 | 
			
		||||
    s = realloc(*str, len + *total_len + 1);
 | 
			
		||||
    if (s == NULL)
 | 
			
		||||
	abort();
 | 
			
		||||
    memcpy(s + *total_len, qs, len);
 | 
			
		||||
    if (qs != ss)
 | 
			
		||||
	free(qs);
 | 
			
		||||
    s[*total_len + len] = '\0';
 | 
			
		||||
    *str = s;
 | 
			
		||||
    *total_len += len;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static char *
 | 
			
		||||
oidtostring(const heim_oid *type)
 | 
			
		||||
{
 | 
			
		||||
    char *s = NULL, *ss;
 | 
			
		||||
    size_t i, total_len = 0;
 | 
			
		||||
    
 | 
			
		||||
    for (i = 0; i < sizeof(no)/sizeof(no[0]); i++) {
 | 
			
		||||
	if (heim_oid_cmp(no[i].o, type) == 0)
 | 
			
		||||
	    return strdup(no[i].n);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    for (i = 0; i < type->length; i++) {
 | 
			
		||||
	asprintf(&ss, "%u", type->components[i]);
 | 
			
		||||
	append_string(&s, &total_len, ss, strlen(ss), 0);
 | 
			
		||||
	if (i + 1 < type->length)
 | 
			
		||||
	    append_string(&s, &total_len, ".", 1, 0);
 | 
			
		||||
    }
 | 
			
		||||
    return s;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_name_to_string(const hx509_name name, char **str)
 | 
			
		||||
{
 | 
			
		||||
    const Name *n = &name->der_name;
 | 
			
		||||
    ssize_t total_len = 0;
 | 
			
		||||
    int i, j;
 | 
			
		||||
 | 
			
		||||
    *str = strdup("");
 | 
			
		||||
    if (*str == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
 | 
			
		||||
    for (i = 0 ; i < n->u.rdnSequence.len; i++) {
 | 
			
		||||
	char *ss;
 | 
			
		||||
	int len;
 | 
			
		||||
 | 
			
		||||
	for (j = 0; j < n->u.rdnSequence.val[i].len; j++) {
 | 
			
		||||
	    DirectoryString *ds = &n->u.rdnSequence.val[i].val[j].value;
 | 
			
		||||
	    char *oidname;
 | 
			
		||||
	    
 | 
			
		||||
	    oidname = oidtostring(&n->u.rdnSequence.val[i].val[j].type);
 | 
			
		||||
 | 
			
		||||
	    switch(ds->element) {
 | 
			
		||||
	    case choice_DirectoryString_ia5String:
 | 
			
		||||
		ss = ds->u.ia5String;
 | 
			
		||||
		break;
 | 
			
		||||
	    case choice_DirectoryString_printableString:
 | 
			
		||||
		ss = ds->u.ia5String;
 | 
			
		||||
		break;
 | 
			
		||||
	    case choice_DirectoryString_utf8String:
 | 
			
		||||
		ss = ds->u.ia5String;
 | 
			
		||||
		break;
 | 
			
		||||
#if 0
 | 
			
		||||
	    case choice_DirectoryString_bmpstring:
 | 
			
		||||
		ss = ds->u.bmpstring;
 | 
			
		||||
		break;
 | 
			
		||||
#endif
 | 
			
		||||
	    default:
 | 
			
		||||
		abort();
 | 
			
		||||
	    }
 | 
			
		||||
	    append_string(str, &total_len, oidname, strlen(oidname), 0);
 | 
			
		||||
	    free(oidname);
 | 
			
		||||
	    append_string(str, &total_len, "=", 1, 0);
 | 
			
		||||
	    len = strlen(ss);
 | 
			
		||||
	    append_string(str, &total_len, ss, len, 1);
 | 
			
		||||
	    if (j + 1 < n->u.rdnSequence.val[i].len)
 | 
			
		||||
		append_string(str, &total_len, "+", 1, 0);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if (i + 1 < n->u.rdnSequence.len)
 | 
			
		||||
	    append_string(str, &total_len, ", ", 2, 0);
 | 
			
		||||
    }
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 * XXX this function is broken, it needs to compare code points, not
 | 
			
		||||
 * bytes.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
_hx509_name_ds_cmp(const DirectoryString *ds1, const DirectoryString *ds2)
 | 
			
		||||
{
 | 
			
		||||
    int c;
 | 
			
		||||
 | 
			
		||||
    c = ds1->element - ds2->element;
 | 
			
		||||
    if (c)
 | 
			
		||||
	return c;
 | 
			
		||||
 | 
			
		||||
    switch(ds1->element) {
 | 
			
		||||
    case choice_DirectoryString_ia5String:
 | 
			
		||||
	c = strcmp(ds1->u.ia5String, ds2->u.ia5String);
 | 
			
		||||
	break;
 | 
			
		||||
    case choice_DirectoryString_teletexString:
 | 
			
		||||
	c = heim_octet_string_cmp(&ds1->u.teletexString,
 | 
			
		||||
				  &ds2->u.teletexString);
 | 
			
		||||
	break;
 | 
			
		||||
    case choice_DirectoryString_printableString:
 | 
			
		||||
	c = strcmp(ds1->u.printableString, ds2->u.printableString);
 | 
			
		||||
	break;
 | 
			
		||||
    case choice_DirectoryString_utf8String:
 | 
			
		||||
	c = strcmp(ds1->u.utf8String, ds2->u.utf8String);
 | 
			
		||||
	break;
 | 
			
		||||
    case choice_DirectoryString_universalString:
 | 
			
		||||
	c = heim_universal_string_cmp(&ds1->u.universalString,
 | 
			
		||||
				      &ds2->u.universalString);
 | 
			
		||||
	break;
 | 
			
		||||
    case choice_DirectoryString_bmpString:
 | 
			
		||||
	c = heim_bmp_string_cmp(&ds1->u.bmpString,
 | 
			
		||||
				  &ds2->u.bmpString);
 | 
			
		||||
	break;
 | 
			
		||||
    default:
 | 
			
		||||
	return 1;
 | 
			
		||||
    }
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
_hx509_name_cmp(const Name *n1, const Name *n2)
 | 
			
		||||
{
 | 
			
		||||
    int i, j, c;
 | 
			
		||||
 | 
			
		||||
    c = n1->u.rdnSequence.len - n2->u.rdnSequence.len;
 | 
			
		||||
    if (c)
 | 
			
		||||
	return c;
 | 
			
		||||
 | 
			
		||||
    for (i = 0 ; i < n1->u.rdnSequence.len; i++) {
 | 
			
		||||
	c = n1->u.rdnSequence.val[i].len - n2->u.rdnSequence.val[i].len;
 | 
			
		||||
	if (c)
 | 
			
		||||
	    return c;
 | 
			
		||||
 | 
			
		||||
	for (j = 0; j < n1->u.rdnSequence.val[i].len; j++) {
 | 
			
		||||
	    c = heim_oid_cmp(&n1->u.rdnSequence.val[i].val[j].type,
 | 
			
		||||
			     &n1->u.rdnSequence.val[i].val[j].type);
 | 
			
		||||
	    if (c)
 | 
			
		||||
		return c;
 | 
			
		||||
			     
 | 
			
		||||
	    c = _hx509_name_ds_cmp(&n1->u.rdnSequence.val[i].val[j].value,
 | 
			
		||||
				   &n2->u.rdnSequence.val[i].val[j].value);
 | 
			
		||||
	    if (c)
 | 
			
		||||
		return c;
 | 
			
		||||
	}
 | 
			
		||||
    }
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
_hx509_name_from_Name(const Name *n, hx509_name *name)
 | 
			
		||||
{
 | 
			
		||||
    int ret;
 | 
			
		||||
    *name = calloc(1, sizeof(**name));
 | 
			
		||||
    if (*name == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
    ret = copy_Name(n, &(*name)->der_name);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	free(*name);
 | 
			
		||||
	*name = NULL;
 | 
			
		||||
    }
 | 
			
		||||
    return ret;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
hx509_der_parse_name(const void *data, size_t length, hx509_name *name)
 | 
			
		||||
{
 | 
			
		||||
    int ret;
 | 
			
		||||
    Name n;
 | 
			
		||||
 | 
			
		||||
    *name = NULL;
 | 
			
		||||
    ret = decode_Name(data, length, &n, NULL);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	return ret;
 | 
			
		||||
    return _hx509_name_from_Name(&n, name);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_name_free(hx509_name *name)
 | 
			
		||||
{
 | 
			
		||||
    free_Name(&(*name)->der_name);
 | 
			
		||||
    memset(*name, 0, sizeof(**name));
 | 
			
		||||
    free(*name);
 | 
			
		||||
    *name = NULL;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_parse_name(const void *data, size_t length, char **str)
 | 
			
		||||
{
 | 
			
		||||
    hx509_name name;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    ret = hx509_der_parse_name(data, length, &name);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	return ret;
 | 
			
		||||
    
 | 
			
		||||
    ret = hx509_name_to_string(name, str);
 | 
			
		||||
    hx509_name_free(&name);
 | 
			
		||||
    return ret;
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										576
									
								
								lib/hx509/p11.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										576
									
								
								lib/hx509/p11.c
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,576 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2004 - 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "hx_locl.h"
 | 
			
		||||
RCSID("$ID$");
 | 
			
		||||
 | 
			
		||||
/* http://developer.netscape.com/support/faqs/pkcs_11.html */
 | 
			
		||||
 | 
			
		||||
#include <openssl/ui.h>
 | 
			
		||||
 | 
			
		||||
#include <dlfcn.h>
 | 
			
		||||
 | 
			
		||||
#include "pkcs11u.h"
 | 
			
		||||
#include "pkcs11.h"
 | 
			
		||||
 | 
			
		||||
typedef struct hx509_security_device_data *hx509_security_device;
 | 
			
		||||
typedef struct hx509_keyset_data *hx509_keyset;
 | 
			
		||||
 | 
			
		||||
struct p11_slot {
 | 
			
		||||
    int flags;
 | 
			
		||||
#define P11_SESSION		1
 | 
			
		||||
#define P11_LOGIN_REQ		2
 | 
			
		||||
#define P11_LOGIN_DONE		4
 | 
			
		||||
    CK_SESSION_HANDLE session;
 | 
			
		||||
    CK_SLOT_ID id;
 | 
			
		||||
    CK_BBOOL token;
 | 
			
		||||
    char *name;
 | 
			
		||||
    char *pin;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct hx509_security_device_data {
 | 
			
		||||
    int refcount;
 | 
			
		||||
    void *handle;
 | 
			
		||||
    CK_FUNCTION_LIST_PTR funcs;
 | 
			
		||||
    CK_ULONG num_slots;
 | 
			
		||||
    struct p11_slot *slots;
 | 
			
		||||
    int selected_slot; /* XXX */
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
#define P11SESSION(module) ((module)->slots[(module)->selected_slot].session)
 | 
			
		||||
#define P11FUNC(module,f,args) (*(module)->funcs->C_##f)args
 | 
			
		||||
 | 
			
		||||
struct hx509_keyset_data {
 | 
			
		||||
    hx509_security_device device;
 | 
			
		||||
    hx509_certs certs;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
typedef struct hx509_key_data *hx509_key;
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
hx509_p11_load_module(const char *fn, hx509_security_device *module)
 | 
			
		||||
{
 | 
			
		||||
    CK_C_GetFunctionList getFuncs;
 | 
			
		||||
    hx509_security_device p;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    *module = NULL;
 | 
			
		||||
 | 
			
		||||
    p = calloc(1, sizeof(*p));
 | 
			
		||||
    if (p == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
 | 
			
		||||
    p->selected_slot = 0;
 | 
			
		||||
 | 
			
		||||
    p->handle = dlopen(fn, RTLD_NOW);
 | 
			
		||||
    if (p->handle == NULL) {
 | 
			
		||||
	ret = EINVAL; /* XXX */
 | 
			
		||||
	goto out;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    getFuncs = dlsym(p->handle, "C_GetFunctionList");
 | 
			
		||||
    if (getFuncs == NULL) {
 | 
			
		||||
	ret = EINVAL;
 | 
			
		||||
	goto out;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    ret = (*getFuncs)(&p->funcs);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	ret = EINVAL;
 | 
			
		||||
	goto out;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    ret = P11FUNC(p, Initialize, (NULL_PTR));
 | 
			
		||||
    if (ret != CKR_OK) {
 | 
			
		||||
	ret = EINVAL;
 | 
			
		||||
	goto out;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    {
 | 
			
		||||
	CK_INFO info;
 | 
			
		||||
 | 
			
		||||
	ret = P11FUNC(p, GetInfo, (&info));
 | 
			
		||||
	if (ret != CKR_OK) {
 | 
			
		||||
	    ret = EINVAL;
 | 
			
		||||
	    goto out;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	printf("module information:\n");
 | 
			
		||||
	printf("version: %04x.%04x\n",
 | 
			
		||||
	       (unsigned int)info.cryptokiVersion.major,
 | 
			
		||||
	       (unsigned int)info.cryptokiVersion.minor);
 | 
			
		||||
	printf("manufacturer: %.*s\n",
 | 
			
		||||
	       (int)sizeof(info.manufacturerID) - 1,
 | 
			
		||||
	       info.manufacturerID);
 | 
			
		||||
	printf("flags: 0x%04x\n", (unsigned int)info.flags);
 | 
			
		||||
	printf("library description: %.*s\n",
 | 
			
		||||
	       (int)sizeof(info.libraryDescription) - 1,
 | 
			
		||||
	       info.libraryDescription);
 | 
			
		||||
	printf("version: %04x.%04x\n",
 | 
			
		||||
	       (unsigned int)info.libraryVersion.major,
 | 
			
		||||
	       (unsigned int)info.libraryVersion.minor);
 | 
			
		||||
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    ret = P11FUNC(p, GetSlotList, (FALSE, NULL, &p->num_slots));
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	ret = EINVAL;
 | 
			
		||||
	goto out;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    printf("num slots: %ld\n", (long)p->num_slots);
 | 
			
		||||
 | 
			
		||||
    {
 | 
			
		||||
	CK_SLOT_ID_PTR slot_ids;
 | 
			
		||||
	int i, j;
 | 
			
		||||
 | 
			
		||||
	slot_ids = malloc(p->num_slots * sizeof(*slot_ids));
 | 
			
		||||
	if (slot_ids == NULL) {
 | 
			
		||||
	    ret = ENOMEM;
 | 
			
		||||
	    goto out;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	ret = P11FUNC(p, GetSlotList, (FALSE, slot_ids, &p->num_slots));
 | 
			
		||||
	if (ret) {
 | 
			
		||||
	    free(slot_ids);
 | 
			
		||||
	    ret = EINVAL;
 | 
			
		||||
	    goto out;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	p->slots = calloc(p->num_slots, sizeof(p->slots[0]));
 | 
			
		||||
	if (p->slots == NULL) {
 | 
			
		||||
	    free(slot_ids);
 | 
			
		||||
	    ret = ENOMEM;
 | 
			
		||||
	    goto out;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	for (i = 0; i < p->num_slots; i++) {
 | 
			
		||||
	    CK_SLOT_INFO slot_info;
 | 
			
		||||
	    CK_TOKEN_INFO token_info;
 | 
			
		||||
 | 
			
		||||
	    printf("slot %d = id %d\n", i, (int)slot_ids[i]);
 | 
			
		||||
 | 
			
		||||
	    p->slots[i].id = slot_ids[i];
 | 
			
		||||
 | 
			
		||||
	    ret = P11FUNC(p, GetSlotInfo, (slot_ids[i], &slot_info));
 | 
			
		||||
	    if (ret)
 | 
			
		||||
		continue;
 | 
			
		||||
 | 
			
		||||
	    for (j = sizeof(slot_info.slotDescription) - 1; j > 0; j--) {
 | 
			
		||||
		char c = slot_info.slotDescription[j];
 | 
			
		||||
		if (c == ' ' || c == '\t' || c == '\n' || c == '\r' || c == '\0')
 | 
			
		||||
		    continue;
 | 
			
		||||
		j++;
 | 
			
		||||
		break;
 | 
			
		||||
	    }
 | 
			
		||||
 | 
			
		||||
	    asprintf(&p->slots[i].name, "%.*s (slot %d)",
 | 
			
		||||
		     j, slot_info.slotDescription, i);
 | 
			
		||||
 | 
			
		||||
	    printf("description: %s\n", p->slots[i].name);
 | 
			
		||||
 | 
			
		||||
	    printf("manufacturer: %.*s\n",
 | 
			
		||||
		   (int)sizeof(slot_info.manufacturerID),
 | 
			
		||||
		   slot_info.manufacturerID);
 | 
			
		||||
 | 
			
		||||
	    if ((slot_info.flags & CKF_TOKEN_PRESENT) == 0) {
 | 
			
		||||
		printf("no token present\n");
 | 
			
		||||
		continue;
 | 
			
		||||
	    }
 | 
			
		||||
 | 
			
		||||
	    ret = P11FUNC(p, GetTokenInfo, (slot_ids[i], &token_info));
 | 
			
		||||
	    if (ret)
 | 
			
		||||
		continue;
 | 
			
		||||
 | 
			
		||||
	    printf("token present\n");
 | 
			
		||||
 | 
			
		||||
	    printf("label: %.*s\n",
 | 
			
		||||
		   (int)sizeof(token_info.label),
 | 
			
		||||
		   token_info.label);
 | 
			
		||||
	    printf("manufacturer: %.*s\n",
 | 
			
		||||
		   (int)sizeof(token_info.manufacturerID),
 | 
			
		||||
		   token_info.manufacturerID);
 | 
			
		||||
	    printf("model: %.*s\n",
 | 
			
		||||
		   (int)sizeof(token_info.model),
 | 
			
		||||
		   token_info.model);
 | 
			
		||||
	    printf("serialNumber: %.*s\n",
 | 
			
		||||
		   (int)sizeof(token_info.serialNumber),
 | 
			
		||||
		   token_info.serialNumber);
 | 
			
		||||
 | 
			
		||||
	    printf("flags: 0x%04x\n", (unsigned int)token_info.flags);
 | 
			
		||||
 | 
			
		||||
	    printf("slotinfo.flags 0x%x & 0x%x = 0x%x\n",
 | 
			
		||||
		   (int)slot_info.flags, (int)CKF_LOGIN_REQUIRED,
 | 
			
		||||
		   (int)(slot_info.flags & CKF_LOGIN_REQUIRED));
 | 
			
		||||
	    if (token_info.flags & CKF_LOGIN_REQUIRED) {
 | 
			
		||||
		printf("login required\n");
 | 
			
		||||
		p->slots[i].flags |= P11_LOGIN_REQ;
 | 
			
		||||
	    }
 | 
			
		||||
	}	
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    *module = p;
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
 out:    
 | 
			
		||||
    if (p->slots)
 | 
			
		||||
	free(p->slots);
 | 
			
		||||
    if (p->handle)
 | 
			
		||||
	dlclose(p->handle);
 | 
			
		||||
    free(p);
 | 
			
		||||
    return ret;
 | 
			
		||||
    
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
p11_get_session(hx509_security_device module, const char *conf, int slot)
 | 
			
		||||
{
 | 
			
		||||
    CK_RV ret;
 | 
			
		||||
 | 
			
		||||
    module->selected_slot = slot;
 | 
			
		||||
 | 
			
		||||
    if (slot >= module->num_slots)
 | 
			
		||||
	return EINVAL;
 | 
			
		||||
 | 
			
		||||
    if (module->slots[slot].flags & P11_SESSION)
 | 
			
		||||
	return EINVAL; /* XXX */
 | 
			
		||||
 | 
			
		||||
    ret = P11FUNC(module, OpenSession, (module->slots[slot].id, 
 | 
			
		||||
					CKF_SERIAL_SESSION,
 | 
			
		||||
					NULL,
 | 
			
		||||
					NULL,
 | 
			
		||||
					&module->slots[slot].session));
 | 
			
		||||
    if (ret != CKR_OK)
 | 
			
		||||
	return EINVAL;
 | 
			
		||||
    
 | 
			
		||||
    module->slots[slot].flags |= P11_SESSION;
 | 
			
		||||
    
 | 
			
		||||
    if ((module->slots[slot].flags & P11_LOGIN_REQ) &&
 | 
			
		||||
	(module->slots[slot].flags & P11_LOGIN_DONE) == 0) {
 | 
			
		||||
	char pin[20];
 | 
			
		||||
	char *prompt;
 | 
			
		||||
 | 
			
		||||
	module->slots[slot].flags |= P11_LOGIN_DONE;
 | 
			
		||||
 | 
			
		||||
	asprintf(&prompt, "PIN code for %s: ", module->slots[slot].name);
 | 
			
		||||
 | 
			
		||||
	if (UI_UTIL_read_pw_string(pin, sizeof(pin), prompt, 0)) {
 | 
			
		||||
	    printf("no pin");
 | 
			
		||||
	    goto out;
 | 
			
		||||
	}
 | 
			
		||||
	free(prompt);
 | 
			
		||||
 | 
			
		||||
	ret = P11FUNC(module, Login,
 | 
			
		||||
		      (P11SESSION(module), CKU_USER, "3962", 4));
 | 
			
		||||
	if (ret != CKR_OK)
 | 
			
		||||
	    printf("login failed\n");
 | 
			
		||||
	else
 | 
			
		||||
	    module->slots[slot].pin = strdup(pin);
 | 
			
		||||
    out:;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
p11_put_session(hx509_security_device module, int slot)
 | 
			
		||||
{
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    if (module->slots[slot].flags & P11_SESSION)
 | 
			
		||||
	return EINVAL;
 | 
			
		||||
    ret = P11FUNC(module, CloseSession, (module->slots[slot].session));
 | 
			
		||||
    if (ret != CKR_OK)
 | 
			
		||||
	return EINVAL;
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
iterate_entries(hx509_security_device module, hx509_certs ks,
 | 
			
		||||
		CK_ATTRIBUTE *search_data, int num_search_data,
 | 
			
		||||
		CK_ATTRIBUTE *query, int num_query,
 | 
			
		||||
		int (*func)(void *, CK_ATTRIBUTE *, int), void *ptr)
 | 
			
		||||
{
 | 
			
		||||
    CK_OBJECT_HANDLE object;
 | 
			
		||||
    CK_ULONG object_count;
 | 
			
		||||
    int ret, i;
 | 
			
		||||
 | 
			
		||||
    printf("current slot: %d\n", module->selected_slot);
 | 
			
		||||
    
 | 
			
		||||
    ret = P11FUNC(module, FindObjectsInit,
 | 
			
		||||
		  (P11SESSION(module), search_data, num_search_data));
 | 
			
		||||
    if (ret != CKR_OK) {
 | 
			
		||||
	return -1;
 | 
			
		||||
    }
 | 
			
		||||
    while (1) {
 | 
			
		||||
	ret = P11FUNC(module, FindObjects, 
 | 
			
		||||
		      (P11SESSION(module), &object, 1, &object_count));
 | 
			
		||||
	if (ret != CKR_OK) {
 | 
			
		||||
	    return -1;
 | 
			
		||||
	}
 | 
			
		||||
	printf("object count = %d\n", (int)object_count);
 | 
			
		||||
	if (object_count == 0)
 | 
			
		||||
	    break;
 | 
			
		||||
	
 | 
			
		||||
	for (i = 0; i < num_query; i++)
 | 
			
		||||
	    query[i].pValue = NULL;
 | 
			
		||||
 | 
			
		||||
	ret = P11FUNC(module, GetAttributeValue, 
 | 
			
		||||
		      (P11SESSION(module), object, query, num_query));
 | 
			
		||||
	if (ret != CKR_OK) {
 | 
			
		||||
	    return -1;
 | 
			
		||||
	}
 | 
			
		||||
	for (i = 0; i < num_query; i++) {
 | 
			
		||||
	    printf("id %d len = %d\n", i, (int)query[i].ulValueLen);
 | 
			
		||||
	    query[i].pValue = malloc(query[i].ulValueLen);
 | 
			
		||||
	    if (query[i].pValue == NULL) {
 | 
			
		||||
		ret = ENOMEM;
 | 
			
		||||
		goto out;
 | 
			
		||||
	    }
 | 
			
		||||
	}
 | 
			
		||||
	ret = P11FUNC(module, GetAttributeValue,
 | 
			
		||||
		      (P11SESSION(module), object, query, num_query));
 | 
			
		||||
	if (ret != CKR_OK) {
 | 
			
		||||
	    ret = -1;
 | 
			
		||||
	    goto out;
 | 
			
		||||
	}
 | 
			
		||||
	
 | 
			
		||||
	ret = (*func)(ptr, query, num_query);
 | 
			
		||||
	if (ret)
 | 
			
		||||
	    goto out;
 | 
			
		||||
 | 
			
		||||
	for (i = 0; i < num_query; i++) {
 | 
			
		||||
	    if (query[i].pValue)
 | 
			
		||||
		free(query[i].pValue);
 | 
			
		||||
	    query[i].pValue = NULL;
 | 
			
		||||
	}
 | 
			
		||||
    }
 | 
			
		||||
 out:
 | 
			
		||||
 | 
			
		||||
    for (i = 0; i < num_query; i++) {
 | 
			
		||||
	if (query[i].pValue)
 | 
			
		||||
	    free(query[i].pValue);
 | 
			
		||||
	query[i].pValue = NULL;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    ret = P11FUNC(module, FindObjectsFinal, (P11SESSION(module)));
 | 
			
		||||
    if (ret != CKR_OK) {
 | 
			
		||||
	return -2;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
		
 | 
			
		||||
static int
 | 
			
		||||
print_id(void *ptr, CK_ATTRIBUTE *query, int num_query)
 | 
			
		||||
{
 | 
			
		||||
    printf("id: %.*s\n", (int)query[0].ulValueLen, (char *)query[0].pValue);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
print_cert(void *ptr, CK_ATTRIBUTE *query, int num_query)
 | 
			
		||||
{
 | 
			
		||||
    hx509_validate_ctx ctx;
 | 
			
		||||
    hx509_cert cert;
 | 
			
		||||
    Certificate c;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    printf("id: %d\n", (int)query[0].ulValueLen);
 | 
			
		||||
 | 
			
		||||
    memset(&c, 0, sizeof(c));
 | 
			
		||||
    ret = decode_Certificate(query[1].pValue, query[1].ulValueLen,
 | 
			
		||||
			     &c, NULL);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	printf("decode_Certificate failed with %d\n", ret);
 | 
			
		||||
	return 0;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    ret = hx509_cert_init(&c, &cert);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	abort();
 | 
			
		||||
    free_Certificate(&c);
 | 
			
		||||
 | 
			
		||||
    hx509_validate_ctx_init(&ctx);
 | 
			
		||||
    hx509_validate_ctx_set_print(ctx, hx509_print_stdout, stdout);
 | 
			
		||||
    hx509_validate_ctx_add_flags(ctx, HX509_VALIDATE_F_VERBOSE);
 | 
			
		||||
 | 
			
		||||
    hx509_validate_cert(ctx, cert);
 | 
			
		||||
 | 
			
		||||
    hx509_validate_ctx_free(ctx);
 | 
			
		||||
    hx509_cert_free(cert);
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
p11_list_keys(hx509_security_device module, hx509_certs ks)
 | 
			
		||||
{
 | 
			
		||||
    CK_OBJECT_CLASS key_class;
 | 
			
		||||
    CK_ATTRIBUTE search_data[] = {
 | 
			
		||||
	{CKA_CLASS, &key_class, sizeof(key_class)},
 | 
			
		||||
    };
 | 
			
		||||
    CK_ATTRIBUTE query_data[2] = {
 | 
			
		||||
	{CKA_ID, NULL, 0},
 | 
			
		||||
	{CKA_VALUE, NULL, 0}
 | 
			
		||||
    };
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    printf("---- private\n");
 | 
			
		||||
    key_class = CKO_PRIVATE_KEY;
 | 
			
		||||
    ret = iterate_entries(module, ks, search_data, 1,
 | 
			
		||||
			  query_data, 1,
 | 
			
		||||
			  print_id, NULL);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	return ret;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    printf("---- public\n");
 | 
			
		||||
    key_class = CKO_PUBLIC_KEY;
 | 
			
		||||
    ret = iterate_entries(module, ks, search_data, 1,
 | 
			
		||||
			  query_data, 1,
 | 
			
		||||
			  print_id, NULL);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	return ret;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    printf("---- cert\n");
 | 
			
		||||
    key_class = CKO_CERTIFICATE;
 | 
			
		||||
    ret = iterate_entries(module, ks, search_data, 1,
 | 
			
		||||
			  query_data, 2,
 | 
			
		||||
			  print_cert, NULL);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	return ret;
 | 
			
		||||
    }
 | 
			
		||||
    printf("----\n");
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
security_device_add(hx509_security_device *device, const char *conf)
 | 
			
		||||
{
 | 
			
		||||
    hx509_security_device module;
 | 
			
		||||
    char *c, *fn;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    *device = NULL;
 | 
			
		||||
 | 
			
		||||
    c = strdup(conf);
 | 
			
		||||
    if (c == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
 | 
			
		||||
    fn = strchr(c, ':');
 | 
			
		||||
    if (fn)
 | 
			
		||||
	*fn++ = '\0';
 | 
			
		||||
    else
 | 
			
		||||
	fn = "/usr/lib/default-pkcs11.so";
 | 
			
		||||
 | 
			
		||||
    if (strcasecmp(c, "PKCS11") != 0) {
 | 
			
		||||
	free(c);
 | 
			
		||||
	return EINVAL;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    ret = hx509_p11_load_module(fn, &module);
 | 
			
		||||
    free(c);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	return ret;
 | 
			
		||||
 | 
			
		||||
    *device = module;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_keyset_init(const char *file, const char *conf)
 | 
			
		||||
{
 | 
			
		||||
    hx509_security_device module;
 | 
			
		||||
    hx509_keyset ks;
 | 
			
		||||
    int ret, slot;
 | 
			
		||||
		  
 | 
			
		||||
    ret = security_device_add(&module, file);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	printf("security_device_add: %d\n", ret);
 | 
			
		||||
	return 0;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    module->refcount++;
 | 
			
		||||
 | 
			
		||||
    ks = calloc(1, sizeof(*ks));
 | 
			
		||||
    if (ks == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
 | 
			
		||||
    ks->device = module;
 | 
			
		||||
 | 
			
		||||
    ret = hx509_certs_init("MEMORY:pkcs-11-store", 0, NULL, &ks->certs);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	goto out;
 | 
			
		||||
 | 
			
		||||
    /* 
 | 
			
		||||
     * XXX just check if the device change changed, and if that case
 | 
			
		||||
     * refresh contents of cache
 | 
			
		||||
     */
 | 
			
		||||
 | 
			
		||||
    slot = 0;
 | 
			
		||||
 | 
			
		||||
    ret = p11_get_session(module, conf, slot);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	goto out;
 | 
			
		||||
 | 
			
		||||
    /* fetch certificates and keys */
 | 
			
		||||
    ret = p11_list_keys(module, ks->certs);
 | 
			
		||||
    if (ret)
 | 
			
		||||
	goto out_session;
 | 
			
		||||
 | 
			
		||||
 out_session:
 | 
			
		||||
 | 
			
		||||
    ret = p11_put_session(module, slot);
 | 
			
		||||
 | 
			
		||||
 out:
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	hx509_certs_free(&ks->certs);
 | 
			
		||||
	memset(ks, 0, sizeof(ks));
 | 
			
		||||
	free(ks);
 | 
			
		||||
	module->refcount--;
 | 
			
		||||
    } else {
 | 
			
		||||
	hx509_certs_iter(ks->certs, hx509_ci_print_names, stdout);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										387
									
								
								lib/hx509/print.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										387
									
								
								lib/hx509/print.c
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,387 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2004 - 2005 Kungliga Tekniska H<>gskolan
 | 
			
		||||
 * (Royal Institute of Technology, Stockholm, Sweden). 
 | 
			
		||||
 * All rights reserved. 
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms, with or without 
 | 
			
		||||
 * modification, are permitted provided that the following conditions 
 | 
			
		||||
 * are met: 
 | 
			
		||||
 *
 | 
			
		||||
 * 1. Redistributions of source code must retain the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer. 
 | 
			
		||||
 *
 | 
			
		||||
 * 2. Redistributions in binary form must reproduce the above copyright 
 | 
			
		||||
 *    notice, this list of conditions and the following disclaimer in the 
 | 
			
		||||
 *    documentation and/or other materials provided with the distribution. 
 | 
			
		||||
 *
 | 
			
		||||
 * 3. Neither the name of the Institute nor the names of its contributors 
 | 
			
		||||
 *    may be used to endorse or promote products derived from this software 
 | 
			
		||||
 *    without specific prior written permission. 
 | 
			
		||||
 *
 | 
			
		||||
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 | 
			
		||||
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 | 
			
		||||
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 | 
			
		||||
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 | 
			
		||||
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 | 
			
		||||
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 | 
			
		||||
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 | 
			
		||||
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 | 
			
		||||
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 | 
			
		||||
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 | 
			
		||||
 * SUCH DAMAGE. 
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "hx_locl.h"
 | 
			
		||||
RCSID("$ID$");
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
struct hx509_validate_ctx_data {
 | 
			
		||||
    int flags;
 | 
			
		||||
    hx509_vprint_func vprint_func;
 | 
			
		||||
    void *ctx;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 *
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
Time2string(const Time *T, char **str)
 | 
			
		||||
{
 | 
			
		||||
    time_t t;
 | 
			
		||||
    char *s;
 | 
			
		||||
    struct tm *tm;
 | 
			
		||||
 | 
			
		||||
    *str = NULL;
 | 
			
		||||
    t = _hx509_Time2time_t(T);
 | 
			
		||||
    tm = gmtime (&t);
 | 
			
		||||
    s = malloc(30);
 | 
			
		||||
    if (s == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
    strftime(s, 30, "%Y-%m-%d %M:%M:%S", tm);
 | 
			
		||||
    *str = s;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_print_stdout(void *ctx, const char *fmt, va_list va)
 | 
			
		||||
{
 | 
			
		||||
    FILE *f = ctx;
 | 
			
		||||
    vfprintf(f, fmt, va);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_print_func(hx509_vprint_func func, void *ctx, const char *fmt, ...)
 | 
			
		||||
{
 | 
			
		||||
    va_list va;
 | 
			
		||||
    va_start(va, fmt);
 | 
			
		||||
    (*func)(ctx, fmt, va);
 | 
			
		||||
    va_end(va);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_oid_sprint(const heim_oid *oid, char **str)
 | 
			
		||||
{
 | 
			
		||||
    char *s, *r;
 | 
			
		||||
    int i;
 | 
			
		||||
    s = strdup("");
 | 
			
		||||
    for (i = 0; i < oid->length; i++) {
 | 
			
		||||
	asprintf(&r, "%s%d%s", s, oid->components[i],
 | 
			
		||||
		 i < oid->length - 1 ? "." : "");
 | 
			
		||||
	free(s);
 | 
			
		||||
	s = r;
 | 
			
		||||
    }
 | 
			
		||||
    *str = s;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_oid_print(const heim_oid *oid, hx509_vprint_func func, void *ctx)
 | 
			
		||||
{
 | 
			
		||||
    char *str;
 | 
			
		||||
    hx509_oid_sprint(oid, &str);
 | 
			
		||||
    hx509_print_func(func, ctx, "%s", str);
 | 
			
		||||
    free(str);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_bitstring_print(const heim_bit_string *b,
 | 
			
		||||
		      hx509_vprint_func func, void *ctx)
 | 
			
		||||
{
 | 
			
		||||
    int i;
 | 
			
		||||
    hx509_print_func(func, ctx, "\tlength: %d\n\t", b->length);
 | 
			
		||||
    for (i = 0; i < (b->length + 7) / 8; i++)
 | 
			
		||||
	hx509_print_func(func, ctx, "%02x%s%s",
 | 
			
		||||
			 ((unsigned char *)b->data)[i], 
 | 
			
		||||
			 i < (b->length - 7) / 8
 | 
			
		||||
			 && (i == 0 || (i % 16) != 15) ? ":" : "",
 | 
			
		||||
			 i != 0 && (i % 16) == 15 ?
 | 
			
		||||
			 (i <= ((b->length + 7) / 8 - 2) ? "\n\t" : "\n"):"");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 *
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
static void
 | 
			
		||||
validate_vprint(void *c, const char *fmt, va_list va)
 | 
			
		||||
{
 | 
			
		||||
    hx509_validate_ctx ctx = c;
 | 
			
		||||
    if (ctx->vprint_func == NULL)
 | 
			
		||||
	return;
 | 
			
		||||
    (ctx->vprint_func)(ctx->ctx, fmt, va);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static void
 | 
			
		||||
validate_print(hx509_validate_ctx ctx, int flags, const char *fmt, ...)
 | 
			
		||||
{
 | 
			
		||||
    va_list va;
 | 
			
		||||
    if ((ctx->flags & flags) == 0)
 | 
			
		||||
	return;
 | 
			
		||||
    va_start(va, fmt);
 | 
			
		||||
    validate_vprint(ctx, fmt, va);
 | 
			
		||||
    va_end(va);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
enum critical_flag { D_C = 0, S_C, S_N_C, M_C, M_N_C };
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
check_Null(hx509_validate_ctx ctx, enum critical_flag cf, const Extension *e)
 | 
			
		||||
{
 | 
			
		||||
    switch(cf) {
 | 
			
		||||
    case D_C:
 | 
			
		||||
	break;
 | 
			
		||||
    case S_C:
 | 
			
		||||
	if (!e->critical)
 | 
			
		||||
	    validate_print(ctx, HX509_VALIDATE_F_VALIDATE,
 | 
			
		||||
			   "\tCritical not set on SHOULD\n");
 | 
			
		||||
	break;
 | 
			
		||||
    case S_N_C:
 | 
			
		||||
	if (e->critical)
 | 
			
		||||
	    validate_print(ctx, HX509_VALIDATE_F_VALIDATE,
 | 
			
		||||
			   "\tCritical set on SHOULD NOT\n");
 | 
			
		||||
	break;
 | 
			
		||||
    case M_C:
 | 
			
		||||
	if (!e->critical)
 | 
			
		||||
	    validate_print(ctx, HX509_VALIDATE_F_VALIDATE,
 | 
			
		||||
			   "\tCritical not set on MUST\n");
 | 
			
		||||
	break;
 | 
			
		||||
    case M_N_C:
 | 
			
		||||
	if (e->critical)
 | 
			
		||||
	    validate_print(ctx, HX509_VALIDATE_F_VALIDATE,
 | 
			
		||||
			   "\tCritical set on MUST NOT\n");
 | 
			
		||||
	break;
 | 
			
		||||
    default:
 | 
			
		||||
	abort();
 | 
			
		||||
    }
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
check_subjectKeyIdentifier(hx509_validate_ctx ctx, 
 | 
			
		||||
			   enum critical_flag cf,
 | 
			
		||||
			   const Extension *e)
 | 
			
		||||
{
 | 
			
		||||
    check_Null(ctx, cf, e);
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
check_subjectAltName(hx509_validate_ctx ctx, 
 | 
			
		||||
		     enum critical_flag cf,
 | 
			
		||||
		     const Extension *e)
 | 
			
		||||
{
 | 
			
		||||
    GeneralNames gn;
 | 
			
		||||
    size_t size;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    check_Null(ctx, cf, e);
 | 
			
		||||
 | 
			
		||||
    ret = decode_GeneralNames(e->extnValue.data, e->extnValue.length,
 | 
			
		||||
			      &gn, &size);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	printf("\tret = %d while decoding GeneralNames\n", ret);
 | 
			
		||||
	return 0;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    free_GeneralNames(&gn);
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
check_basicConstraints(hx509_validate_ctx ctx, 
 | 
			
		||||
		       enum critical_flag cf, 
 | 
			
		||||
		       const Extension *e)
 | 
			
		||||
{
 | 
			
		||||
    BasicConstraints b;
 | 
			
		||||
    size_t size;
 | 
			
		||||
    int ret;
 | 
			
		||||
 | 
			
		||||
    check_Null(ctx, cf, e);
 | 
			
		||||
    
 | 
			
		||||
    ret = decode_BasicConstraints(e->extnValue.data, e->extnValue.length,
 | 
			
		||||
				  &b, &size);
 | 
			
		||||
    if (ret) {
 | 
			
		||||
	printf("\tret = %d while decoding BasicConstraints\n", ret);
 | 
			
		||||
	return 0;
 | 
			
		||||
    }
 | 
			
		||||
    if (size != e->extnValue.length)
 | 
			
		||||
	printf("\tlength of der data isn't same as extension\n");
 | 
			
		||||
 | 
			
		||||
    validate_print(ctx, HX509_VALIDATE_F_VERBOSE,
 | 
			
		||||
		   "\tis %sa CA\n", b.cA && *b.cA ? "" : "NOT ");
 | 
			
		||||
    if (b.pathLenConstraint)
 | 
			
		||||
	validate_print(ctx, HX509_VALIDATE_F_VERBOSE,
 | 
			
		||||
		       "\tpathLenConstraint: %d\n", *b.pathLenConstraint);
 | 
			
		||||
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
struct {
 | 
			
		||||
    const char *name;
 | 
			
		||||
    const heim_oid *(*oid)(void);
 | 
			
		||||
    int (*func)(hx509_validate_ctx ctx, 
 | 
			
		||||
		enum critical_flag cf, 
 | 
			
		||||
		const Extension *);
 | 
			
		||||
    enum critical_flag cf;
 | 
			
		||||
} check_extension[] = {
 | 
			
		||||
#define ext(name, checkname) #name, &oid_id_x509_ce_##name, check_##checkname 
 | 
			
		||||
    { ext(subjectDirectoryAttributes, Null), M_N_C },
 | 
			
		||||
    { ext(subjectKeyIdentifier, subjectKeyIdentifier), M_N_C },
 | 
			
		||||
    { ext(keyUsage, Null), S_C },
 | 
			
		||||
    { ext(subjectAltName, subjectAltName), M_N_C },
 | 
			
		||||
    { ext(issuerAltName, Null), S_N_C },
 | 
			
		||||
    { ext(basicConstraints, basicConstraints), M_C },
 | 
			
		||||
    { ext(cRLNumber, Null), M_N_C },
 | 
			
		||||
    { ext(cRLReasons, Null), M_N_C },
 | 
			
		||||
    { ext(holdInstructionCode, Null), M_N_C },
 | 
			
		||||
    { ext(invalidityDate, Null), M_N_C },
 | 
			
		||||
    { ext(deltaCRLIndicator, Null), M_C },
 | 
			
		||||
    { ext(issuingDistributionPoint, Null), M_C },
 | 
			
		||||
    { ext(certificateIssuer, Null), M_C },
 | 
			
		||||
    { ext(nameConstraints, Null), M_C },
 | 
			
		||||
    { ext(cRLDistributionPoints, Null), S_N_C },
 | 
			
		||||
    { ext(certificatePolicies, Null) },
 | 
			
		||||
    { ext(policyMappings, Null), M_N_C },
 | 
			
		||||
    { ext(authorityKeyIdentifier, Null), M_N_C },
 | 
			
		||||
    { ext(policyConstraints, Null), D_C },
 | 
			
		||||
    { ext(extKeyUsage, Null), D_C },
 | 
			
		||||
    { ext(freshestCRL, Null), M_N_C },
 | 
			
		||||
    { ext(inhibitAnyPolicy, Null), M_C },
 | 
			
		||||
    { NULL }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_validate_ctx_init(hx509_validate_ctx *ctx)
 | 
			
		||||
{
 | 
			
		||||
    *ctx = malloc(sizeof(**ctx));
 | 
			
		||||
    if (*ctx == NULL)
 | 
			
		||||
	return ENOMEM;
 | 
			
		||||
    memset(*ctx, 0, sizeof(**ctx));
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_validate_ctx_set_print(hx509_validate_ctx ctx, 
 | 
			
		||||
			     hx509_vprint_func func,
 | 
			
		||||
			     void *c)
 | 
			
		||||
{
 | 
			
		||||
    ctx->vprint_func = func;
 | 
			
		||||
    ctx->ctx = c;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_validate_ctx_add_flags(hx509_validate_ctx ctx, int flags)
 | 
			
		||||
{
 | 
			
		||||
    ctx->flags |= flags;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void
 | 
			
		||||
hx509_validate_ctx_free(hx509_validate_ctx ctx)
 | 
			
		||||
{
 | 
			
		||||
    free(ctx);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
hx509_validate_cert(hx509_validate_ctx ctx, hx509_cert cert)
 | 
			
		||||
{
 | 
			
		||||
    Certificate *c = _hx509_get_cert(cert);
 | 
			
		||||
    TBSCertificate *t = &c->tbsCertificate;
 | 
			
		||||
    hx509_name name;
 | 
			
		||||
    char *str;
 | 
			
		||||
 | 
			
		||||
    if (_hx509_cert_get_version(c) != 3)
 | 
			
		||||
	validate_print(ctx, HX509_VALIDATE_F_VERBOSE,
 | 
			
		||||
		       "Not version 3 certificate\n");
 | 
			
		||||
    
 | 
			
		||||
    if (t->version && *t->version < 2 && t->extensions)
 | 
			
		||||
	validate_print(ctx, HX509_VALIDATE_F_VALIDATE,
 | 
			
		||||
		       "Not version 3 certificate with extensions\n");
 | 
			
		||||
	
 | 
			
		||||
    _hx509_name_from_Name(&t->subject, &name);
 | 
			
		||||
    hx509_name_to_string(name, &str);
 | 
			
		||||
    hx509_name_free(&name);
 | 
			
		||||
    validate_print(ctx, HX509_VALIDATE_F_VERBOSE,
 | 
			
		||||
		   "subject name: %s\n", str);
 | 
			
		||||
    free(str);
 | 
			
		||||
 | 
			
		||||
    _hx509_name_from_Name(&t->issuer, &name);
 | 
			
		||||
    hx509_name_to_string(name, &str);
 | 
			
		||||
    hx509_name_free(&name);
 | 
			
		||||
    validate_print(ctx, HX509_VALIDATE_F_VERBOSE,
 | 
			
		||||
		   "issuer name: %s\n", str);
 | 
			
		||||
    free(str);
 | 
			
		||||
 | 
			
		||||
    validate_print(ctx, HX509_VALIDATE_F_VERBOSE,
 | 
			
		||||
		   "Validity:\n");
 | 
			
		||||
 | 
			
		||||
    Time2string(&t->validity.notBefore, &str);
 | 
			
		||||
    validate_print(ctx, HX509_VALIDATE_F_VERBOSE, "\tnotBefore %s\n", str);
 | 
			
		||||
    free(str);
 | 
			
		||||
    Time2string(&t->validity.notAfter, &str);
 | 
			
		||||
    validate_print(ctx, HX509_VALIDATE_F_VERBOSE, "\tnotAfter  %s\n", str);
 | 
			
		||||
    free(str);
 | 
			
		||||
 | 
			
		||||
    if (t->extensions) {
 | 
			
		||||
	int i, j;
 | 
			
		||||
 | 
			
		||||
	if (t->extensions->len == 0) {
 | 
			
		||||
	    validate_print(ctx,
 | 
			
		||||
			   HX509_VALIDATE_F_VALIDATE|HX509_VALIDATE_F_VERBOSE,
 | 
			
		||||
			   "The empty extensions list is not "
 | 
			
		||||
			   "allowed by PKIX\n");
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	for (i = 0; i < t->extensions->len; i++) {
 | 
			
		||||
 | 
			
		||||
	    for (j = 0; check_extension[j].name; j++)
 | 
			
		||||
		if (heim_oid_cmp((*check_extension[j].oid)(),
 | 
			
		||||
				 &t->extensions->val[i].extnID) == 0)
 | 
			
		||||
		    break;
 | 
			
		||||
	    if (check_extension[j].name == NULL) {
 | 
			
		||||
		int flags = HX509_VALIDATE_F_VERBOSE;
 | 
			
		||||
		if (t->extensions->val[i].critical)
 | 
			
		||||
		    flags |= HX509_VALIDATE_F_VALIDATE;
 | 
			
		||||
		validate_print(ctx, flags, "don't know what ");
 | 
			
		||||
		if (t->extensions->val[i].critical)
 | 
			
		||||
		    validate_print(ctx, flags, "and is CRITICAL ");
 | 
			
		||||
		if (ctx->flags & flags)
 | 
			
		||||
		    hx509_oid_print(&t->extensions->val[i].extnID, 
 | 
			
		||||
				    validate_vprint, ctx);
 | 
			
		||||
		validate_print(ctx, flags, " is\n");
 | 
			
		||||
		continue;
 | 
			
		||||
	    }
 | 
			
		||||
	    validate_print(ctx,
 | 
			
		||||
			   HX509_VALIDATE_F_VALIDATE|HX509_VALIDATE_F_VERBOSE,
 | 
			
		||||
			   "checking extention: %s\n",
 | 
			
		||||
			   check_extension[j].name);
 | 
			
		||||
	    (*check_extension[j].func)(ctx,
 | 
			
		||||
				       check_extension[j].cf,
 | 
			
		||||
				       &t->extensions->val[i]);
 | 
			
		||||
	}
 | 
			
		||||
    } else
 | 
			
		||||
	validate_print(ctx, HX509_VALIDATE_F_VERBOSE, "no extentions\n");
 | 
			
		||||
	
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										299
									
								
								lib/hx509/ref/pkcs11.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										299
									
								
								lib/hx509/ref/pkcs11.h
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,299 @@
 | 
			
		||||
/* pkcs11.h include file for PKCS #11. */
 | 
			
		||||
/* $Revision$ */
 | 
			
		||||
 | 
			
		||||
/* License to copy and use this software is granted provided that it is
 | 
			
		||||
 * identified as "RSA Security Inc. PKCS #11 Cryptographic Token Interface
 | 
			
		||||
 * (Cryptoki)" in all material mentioning or referencing this software.
 | 
			
		||||
 | 
			
		||||
 * License is also granted to make and use derivative works provided that
 | 
			
		||||
 * such works are identified as "derived from the RSA Security Inc. PKCS #11
 | 
			
		||||
 * Cryptographic Token Interface (Cryptoki)" in all material mentioning or 
 | 
			
		||||
 * referencing the derived work.
 | 
			
		||||
 | 
			
		||||
 * RSA Security Inc. makes no representations concerning either the 
 | 
			
		||||
 * merchantability of this software or the suitability of this software for
 | 
			
		||||
 * any particular purpose. It is provided "as is" without express or implied
 | 
			
		||||
 * warranty of any kind.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#ifndef _PKCS11_H_
 | 
			
		||||
#define _PKCS11_H_ 1
 | 
			
		||||
 | 
			
		||||
#ifdef __cplusplus
 | 
			
		||||
extern "C" {
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
/* Before including this file (pkcs11.h) (or pkcs11t.h by
 | 
			
		||||
 * itself), 6 platform-specific macros must be defined.  These
 | 
			
		||||
 * macros are described below, and typical definitions for them
 | 
			
		||||
 * are also given.  Be advised that these definitions can depend
 | 
			
		||||
 * on both the platform and the compiler used (and possibly also
 | 
			
		||||
 * on whether a Cryptoki library is linked statically or
 | 
			
		||||
 * dynamically).
 | 
			
		||||
 *
 | 
			
		||||
 * In addition to defining these 6 macros, the packing convention
 | 
			
		||||
 * for Cryptoki structures should be set.  The Cryptoki
 | 
			
		||||
 * convention on packing is that structures should be 1-byte
 | 
			
		||||
 * aligned.
 | 
			
		||||
 *
 | 
			
		||||
 * If you're using Microsoft Developer Studio 5.0 to produce
 | 
			
		||||
 * Win32 stuff, this might be done by using the following
 | 
			
		||||
 * preprocessor directive before including pkcs11.h or pkcs11t.h:
 | 
			
		||||
 *
 | 
			
		||||
 * #pragma pack(push, cryptoki, 1)
 | 
			
		||||
 *
 | 
			
		||||
 * and using the following preprocessor directive after including
 | 
			
		||||
 * pkcs11.h or pkcs11t.h:
 | 
			
		||||
 *
 | 
			
		||||
 * #pragma pack(pop, cryptoki)
 | 
			
		||||
 *
 | 
			
		||||
 * If you're using an earlier version of Microsoft Developer
 | 
			
		||||
 * Studio to produce Win16 stuff, this might be done by using
 | 
			
		||||
 * the following preprocessor directive before including
 | 
			
		||||
 * pkcs11.h or pkcs11t.h:
 | 
			
		||||
 *
 | 
			
		||||
 * #pragma pack(1)
 | 
			
		||||
 *
 | 
			
		||||
 * In a UNIX environment, you're on your own for this.  You might
 | 
			
		||||
 * not need to do (or be able to do!) anything.
 | 
			
		||||
 *
 | 
			
		||||
 *
 | 
			
		||||
 * Now for the macros:
 | 
			
		||||
 *
 | 
			
		||||
 *
 | 
			
		||||
 * 1. CK_PTR: The indirection string for making a pointer to an
 | 
			
		||||
 * object.  It can be used like this:
 | 
			
		||||
 *
 | 
			
		||||
 * typedef CK_BYTE CK_PTR CK_BYTE_PTR;
 | 
			
		||||
 *
 | 
			
		||||
 * If you're using Microsoft Developer Studio 5.0 to produce
 | 
			
		||||
 * Win32 stuff, it might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_PTR *
 | 
			
		||||
 *
 | 
			
		||||
 * If you're using an earlier version of Microsoft Developer
 | 
			
		||||
 * Studio to produce Win16 stuff, it might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_PTR far *
 | 
			
		||||
 *
 | 
			
		||||
 * In a typical UNIX environment, it might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_PTR *
 | 
			
		||||
 *
 | 
			
		||||
 *
 | 
			
		||||
 * 2. CK_DEFINE_FUNCTION(returnType, name): A macro which makes
 | 
			
		||||
 * an exportable Cryptoki library function definition out of a
 | 
			
		||||
 * return type and a function name.  It should be used in the
 | 
			
		||||
 * following fashion to define the exposed Cryptoki functions in
 | 
			
		||||
 * a Cryptoki library:
 | 
			
		||||
 *
 | 
			
		||||
 * CK_DEFINE_FUNCTION(CK_RV, C_Initialize)(
 | 
			
		||||
 *   CK_VOID_PTR pReserved
 | 
			
		||||
 * )
 | 
			
		||||
 * {
 | 
			
		||||
 *   ...
 | 
			
		||||
 * }
 | 
			
		||||
 *
 | 
			
		||||
 * If you're using Microsoft Developer Studio 5.0 to define a
 | 
			
		||||
 * function in a Win32 Cryptoki .dll, it might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_DEFINE_FUNCTION(returnType, name) \
 | 
			
		||||
 *   returnType __declspec(dllexport) name
 | 
			
		||||
 *
 | 
			
		||||
 * If you're using an earlier version of Microsoft Developer
 | 
			
		||||
 * Studio to define a function in a Win16 Cryptoki .dll, it
 | 
			
		||||
 * might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_DEFINE_FUNCTION(returnType, name) \
 | 
			
		||||
 *   returnType __export _far _pascal name
 | 
			
		||||
 *
 | 
			
		||||
 * In a UNIX environment, it might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_DEFINE_FUNCTION(returnType, name) \
 | 
			
		||||
 *   returnType name
 | 
			
		||||
 *
 | 
			
		||||
 *
 | 
			
		||||
 * 3. CK_DECLARE_FUNCTION(returnType, name): A macro which makes
 | 
			
		||||
 * an importable Cryptoki library function declaration out of a
 | 
			
		||||
 * return type and a function name.  It should be used in the
 | 
			
		||||
 * following fashion:
 | 
			
		||||
 *
 | 
			
		||||
 * extern CK_DECLARE_FUNCTION(CK_RV, C_Initialize)(
 | 
			
		||||
 *   CK_VOID_PTR pReserved
 | 
			
		||||
 * );
 | 
			
		||||
 *
 | 
			
		||||
 * If you're using Microsoft Developer Studio 5.0 to declare a
 | 
			
		||||
 * function in a Win32 Cryptoki .dll, it might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_DECLARE_FUNCTION(returnType, name) \
 | 
			
		||||
 *   returnType __declspec(dllimport) name
 | 
			
		||||
 *
 | 
			
		||||
 * If you're using an earlier version of Microsoft Developer
 | 
			
		||||
 * Studio to declare a function in a Win16 Cryptoki .dll, it
 | 
			
		||||
 * might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_DECLARE_FUNCTION(returnType, name) \
 | 
			
		||||
 *   returnType __export _far _pascal name
 | 
			
		||||
 *
 | 
			
		||||
 * In a UNIX environment, it might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_DECLARE_FUNCTION(returnType, name) \
 | 
			
		||||
 *   returnType name
 | 
			
		||||
 *
 | 
			
		||||
 *
 | 
			
		||||
 * 4. CK_DECLARE_FUNCTION_POINTER(returnType, name): A macro
 | 
			
		||||
 * which makes a Cryptoki API function pointer declaration or
 | 
			
		||||
 * function pointer type declaration out of a return type and a
 | 
			
		||||
 * function name.  It should be used in the following fashion:
 | 
			
		||||
 *
 | 
			
		||||
 * // Define funcPtr to be a pointer to a Cryptoki API function
 | 
			
		||||
 * // taking arguments args and returning CK_RV.
 | 
			
		||||
 * CK_DECLARE_FUNCTION_POINTER(CK_RV, funcPtr)(args);
 | 
			
		||||
 *
 | 
			
		||||
 * or
 | 
			
		||||
 *
 | 
			
		||||
 * // Define funcPtrType to be the type of a pointer to a
 | 
			
		||||
 * // Cryptoki API function taking arguments args and returning
 | 
			
		||||
 * // CK_RV, and then define funcPtr to be a variable of type
 | 
			
		||||
 * // funcPtrType.
 | 
			
		||||
 * typedef CK_DECLARE_FUNCTION_POINTER(CK_RV, funcPtrType)(args);
 | 
			
		||||
 * funcPtrType funcPtr;
 | 
			
		||||
 *
 | 
			
		||||
 * If you're using Microsoft Developer Studio 5.0 to access
 | 
			
		||||
 * functions in a Win32 Cryptoki .dll, in might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_DECLARE_FUNCTION_POINTER(returnType, name) \
 | 
			
		||||
 *   returnType __declspec(dllimport) (* name)
 | 
			
		||||
 *
 | 
			
		||||
 * If you're using an earlier version of Microsoft Developer
 | 
			
		||||
 * Studio to access functions in a Win16 Cryptoki .dll, it might
 | 
			
		||||
 * be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_DECLARE_FUNCTION_POINTER(returnType, name) \
 | 
			
		||||
 *   returnType __export _far _pascal (* name)
 | 
			
		||||
 *
 | 
			
		||||
 * In a UNIX environment, it might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_DECLARE_FUNCTION_POINTER(returnType, name) \
 | 
			
		||||
 *   returnType (* name)
 | 
			
		||||
 *
 | 
			
		||||
 *
 | 
			
		||||
 * 5. CK_CALLBACK_FUNCTION(returnType, name): A macro which makes
 | 
			
		||||
 * a function pointer type for an application callback out of
 | 
			
		||||
 * a return type for the callback and a name for the callback.
 | 
			
		||||
 * It should be used in the following fashion:
 | 
			
		||||
 *
 | 
			
		||||
 * CK_CALLBACK_FUNCTION(CK_RV, myCallback)(args);
 | 
			
		||||
 *
 | 
			
		||||
 * to declare a function pointer, myCallback, to a callback
 | 
			
		||||
 * which takes arguments args and returns a CK_RV.  It can also
 | 
			
		||||
 * be used like this:
 | 
			
		||||
 *
 | 
			
		||||
 * typedef CK_CALLBACK_FUNCTION(CK_RV, myCallbackType)(args);
 | 
			
		||||
 * myCallbackType myCallback;
 | 
			
		||||
 *
 | 
			
		||||
 * If you're using Microsoft Developer Studio 5.0 to do Win32
 | 
			
		||||
 * Cryptoki development, it might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_CALLBACK_FUNCTION(returnType, name) \
 | 
			
		||||
 *   returnType (* name)
 | 
			
		||||
 *
 | 
			
		||||
 * If you're using an earlier version of Microsoft Developer
 | 
			
		||||
 * Studio to do Win16 development, it might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_CALLBACK_FUNCTION(returnType, name) \
 | 
			
		||||
 *   returnType _far _pascal (* name)
 | 
			
		||||
 *
 | 
			
		||||
 * In a UNIX environment, it might be defined by:
 | 
			
		||||
 *
 | 
			
		||||
 * #define CK_CALLBACK_FUNCTION(returnType, name) \
 | 
			
		||||
 *   returnType (* name)
 | 
			
		||||
 *
 | 
			
		||||
 *
 | 
			
		||||
 * 6. NULL_PTR: This macro is the value of a NULL pointer.
 | 
			
		||||
 *
 | 
			
		||||
 * In any ANSI/ISO C environment (and in many others as well),
 | 
			
		||||
 * this should best be defined by
 | 
			
		||||
 *
 | 
			
		||||
 * #ifndef NULL_PTR
 | 
			
		||||
 * #define NULL_PTR 0
 | 
			
		||||
 * #endif
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* All the various Cryptoki types and #define'd values are in the
 | 
			
		||||
 * file pkcs11t.h. */
 | 
			
		||||
#include "pkcs11t.h"
 | 
			
		||||
 | 
			
		||||
#define __PASTE(x,y)      x##y
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* ==============================================================
 | 
			
		||||
 * Define the "extern" form of all the entry points.
 | 
			
		||||
 * ==============================================================
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#define CK_NEED_ARG_LIST  1
 | 
			
		||||
#define CK_PKCS11_FUNCTION_INFO(name) \
 | 
			
		||||
  extern CK_DECLARE_FUNCTION(CK_RV, name)
 | 
			
		||||
 | 
			
		||||
/* pkcs11f.h has all the information about the Cryptoki
 | 
			
		||||
 * function prototypes. */
 | 
			
		||||
#include "pkcs11f.h"
 | 
			
		||||
 | 
			
		||||
#undef CK_NEED_ARG_LIST
 | 
			
		||||
#undef CK_PKCS11_FUNCTION_INFO
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* ==============================================================
 | 
			
		||||
 * Define the typedef form of all the entry points.  That is, for
 | 
			
		||||
 * each Cryptoki function C_XXX, define a type CK_C_XXX which is
 | 
			
		||||
 * a pointer to that kind of function.
 | 
			
		||||
 * ==============================================================
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#define CK_NEED_ARG_LIST  1
 | 
			
		||||
#define CK_PKCS11_FUNCTION_INFO(name) \
 | 
			
		||||
  typedef CK_DECLARE_FUNCTION_POINTER(CK_RV, __PASTE(CK_,name))
 | 
			
		||||
 | 
			
		||||
/* pkcs11f.h has all the information about the Cryptoki
 | 
			
		||||
 * function prototypes. */
 | 
			
		||||
#include "pkcs11f.h"
 | 
			
		||||
 | 
			
		||||
#undef CK_NEED_ARG_LIST
 | 
			
		||||
#undef CK_PKCS11_FUNCTION_INFO
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* ==============================================================
 | 
			
		||||
 * Define structed vector of entry points.  A CK_FUNCTION_LIST
 | 
			
		||||
 * contains a CK_VERSION indicating a library's Cryptoki version
 | 
			
		||||
 * and then a whole slew of function pointers to the routines in
 | 
			
		||||
 * the library.  This type was declared, but not defined, in
 | 
			
		||||
 * pkcs11t.h.
 | 
			
		||||
 * ==============================================================
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#define CK_PKCS11_FUNCTION_INFO(name) \
 | 
			
		||||
  __PASTE(CK_,name) name;
 | 
			
		||||
  
 | 
			
		||||
struct CK_FUNCTION_LIST {
 | 
			
		||||
 | 
			
		||||
  CK_VERSION    version;  /* Cryptoki version */
 | 
			
		||||
 | 
			
		||||
/* Pile all the function pointers into the CK_FUNCTION_LIST. */
 | 
			
		||||
/* pkcs11f.h has all the information about the Cryptoki
 | 
			
		||||
 * function prototypes. */
 | 
			
		||||
#include "pkcs11f.h"
 | 
			
		||||
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
#undef CK_PKCS11_FUNCTION_INFO
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
#undef __PASTE
 | 
			
		||||
 | 
			
		||||
#ifdef __cplusplus
 | 
			
		||||
}
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
#endif
 | 
			
		||||
							
								
								
									
										912
									
								
								lib/hx509/ref/pkcs11f.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										912
									
								
								lib/hx509/ref/pkcs11f.h
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,912 @@
 | 
			
		||||
/* pkcs11f.h include file for PKCS #11. */
 | 
			
		||||
/* $Revision$ */
 | 
			
		||||
 | 
			
		||||
/* License to copy and use this software is granted provided that it is
 | 
			
		||||
 * identified as "RSA Security Inc. PKCS #11 Cryptographic Token Interface
 | 
			
		||||
 * (Cryptoki)" in all material mentioning or referencing this software.
 | 
			
		||||
 | 
			
		||||
 * License is also granted to make and use derivative works provided that
 | 
			
		||||
 * such works are identified as "derived from the RSA Security Inc. PKCS #11
 | 
			
		||||
 * Cryptographic Token Interface (Cryptoki)" in all material mentioning or 
 | 
			
		||||
 * referencing the derived work.
 | 
			
		||||
 | 
			
		||||
 * RSA Security Inc. makes no representations concerning either the 
 | 
			
		||||
 * merchantability of this software or the suitability of this software for
 | 
			
		||||
 * any particular purpose. It is provided "as is" without express or implied
 | 
			
		||||
 * warranty of any kind.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
/* This header file contains pretty much everything about all the */
 | 
			
		||||
/* Cryptoki function prototypes.  Because this information is */
 | 
			
		||||
/* used for more than just declaring function prototypes, the */
 | 
			
		||||
/* order of the functions appearing herein is important, and */
 | 
			
		||||
/* should not be altered. */
 | 
			
		||||
 | 
			
		||||
/* General-purpose */
 | 
			
		||||
 | 
			
		||||
/* C_Initialize initializes the Cryptoki library. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_Initialize)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_VOID_PTR   pInitArgs  /* if this is not NULL_PTR, it gets
 | 
			
		||||
                            * cast to CK_C_INITIALIZE_ARGS_PTR
 | 
			
		||||
                            * and dereferenced */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_Finalize indicates that an application is done with the
 | 
			
		||||
 * Cryptoki library. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_Finalize)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_VOID_PTR   pReserved  /* reserved.  Should be NULL_PTR */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_GetInfo returns general information about Cryptoki. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GetInfo)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_INFO_PTR   pInfo  /* location that receives information */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_GetFunctionList returns the function list. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GetFunctionList)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_FUNCTION_LIST_PTR_PTR ppFunctionList  /* receives pointer to
 | 
			
		||||
                                            * function list */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* Slot and token management */
 | 
			
		||||
 | 
			
		||||
/* C_GetSlotList obtains a list of slots in the system. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GetSlotList)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_BBOOL       tokenPresent,  /* only slots with tokens? */
 | 
			
		||||
  CK_SLOT_ID_PTR pSlotList,     /* receives array of slot IDs */
 | 
			
		||||
  CK_ULONG_PTR   pulCount       /* receives number of slots */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_GetSlotInfo obtains information about a particular slot in
 | 
			
		||||
 * the system. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GetSlotInfo)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SLOT_ID       slotID,  /* the ID of the slot */
 | 
			
		||||
  CK_SLOT_INFO_PTR pInfo    /* receives the slot information */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_GetTokenInfo obtains information about a particular token
 | 
			
		||||
 * in the system. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GetTokenInfo)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SLOT_ID        slotID,  /* ID of the token's slot */
 | 
			
		||||
  CK_TOKEN_INFO_PTR pInfo    /* receives the token information */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_GetMechanismList obtains a list of mechanism types
 | 
			
		||||
 * supported by a token. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GetMechanismList)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SLOT_ID            slotID,          /* ID of token's slot */
 | 
			
		||||
  CK_MECHANISM_TYPE_PTR pMechanismList,  /* gets mech. array */
 | 
			
		||||
  CK_ULONG_PTR          pulCount         /* gets # of mechs. */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_GetMechanismInfo obtains information about a particular
 | 
			
		||||
 * mechanism possibly supported by a token. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GetMechanismInfo)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SLOT_ID            slotID,  /* ID of the token's slot */
 | 
			
		||||
  CK_MECHANISM_TYPE     type,    /* type of mechanism */
 | 
			
		||||
  CK_MECHANISM_INFO_PTR pInfo    /* receives mechanism info */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_InitToken initializes a token. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_InitToken)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
/* pLabel changed from CK_CHAR_PTR to CK_UTF8CHAR_PTR for v2.10 */
 | 
			
		||||
(
 | 
			
		||||
  CK_SLOT_ID      slotID,    /* ID of the token's slot */
 | 
			
		||||
  CK_UTF8CHAR_PTR pPin,      /* the SO's initial PIN */
 | 
			
		||||
  CK_ULONG        ulPinLen,  /* length in bytes of the PIN */
 | 
			
		||||
  CK_UTF8CHAR_PTR pLabel     /* 32-byte token label (blank padded) */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_InitPIN initializes the normal user's PIN. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_InitPIN)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,  /* the session's handle */
 | 
			
		||||
  CK_UTF8CHAR_PTR   pPin,      /* the normal user's PIN */
 | 
			
		||||
  CK_ULONG          ulPinLen   /* length in bytes of the PIN */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_SetPIN modifies the PIN of the user who is logged in. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_SetPIN)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,  /* the session's handle */
 | 
			
		||||
  CK_UTF8CHAR_PTR   pOldPin,   /* the old PIN */
 | 
			
		||||
  CK_ULONG          ulOldLen,  /* length of the old PIN */
 | 
			
		||||
  CK_UTF8CHAR_PTR   pNewPin,   /* the new PIN */
 | 
			
		||||
  CK_ULONG          ulNewLen   /* length of the new PIN */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* Session management */
 | 
			
		||||
 | 
			
		||||
/* C_OpenSession opens a session between an application and a
 | 
			
		||||
 * token. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_OpenSession)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SLOT_ID            slotID,        /* the slot's ID */
 | 
			
		||||
  CK_FLAGS              flags,         /* from CK_SESSION_INFO */
 | 
			
		||||
  CK_VOID_PTR           pApplication,  /* passed to callback */
 | 
			
		||||
  CK_NOTIFY             Notify,        /* callback function */
 | 
			
		||||
  CK_SESSION_HANDLE_PTR phSession      /* gets session handle */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_CloseSession closes a session between an application and a
 | 
			
		||||
 * token. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_CloseSession)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession  /* the session's handle */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_CloseAllSessions closes all sessions with a token. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_CloseAllSessions)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SLOT_ID     slotID  /* the token's slot */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_GetSessionInfo obtains information about the session. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GetSessionInfo)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE   hSession,  /* the session's handle */
 | 
			
		||||
  CK_SESSION_INFO_PTR pInfo      /* receives session info */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_GetOperationState obtains the state of the cryptographic operation
 | 
			
		||||
 * in a session. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GetOperationState)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,             /* session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pOperationState,      /* gets state */
 | 
			
		||||
  CK_ULONG_PTR      pulOperationStateLen  /* gets state length */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_SetOperationState restores the state of the cryptographic
 | 
			
		||||
 * operation in a session. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_SetOperationState)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,            /* session's handle */
 | 
			
		||||
  CK_BYTE_PTR      pOperationState,      /* holds state */
 | 
			
		||||
  CK_ULONG         ulOperationStateLen,  /* holds state length */
 | 
			
		||||
  CK_OBJECT_HANDLE hEncryptionKey,       /* en/decryption key */
 | 
			
		||||
  CK_OBJECT_HANDLE hAuthenticationKey    /* sign/verify key */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_Login logs a user into a token. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_Login)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,  /* the session's handle */
 | 
			
		||||
  CK_USER_TYPE      userType,  /* the user type */
 | 
			
		||||
  CK_UTF8CHAR_PTR   pPin,      /* the user's PIN */
 | 
			
		||||
  CK_ULONG          ulPinLen   /* the length of the PIN */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_Logout logs a user out from a token. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_Logout)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession  /* the session's handle */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* Object management */
 | 
			
		||||
 | 
			
		||||
/* C_CreateObject creates a new object. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_CreateObject)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,    /* the session's handle */
 | 
			
		||||
  CK_ATTRIBUTE_PTR  pTemplate,   /* the object's template */
 | 
			
		||||
  CK_ULONG          ulCount,     /* attributes in template */
 | 
			
		||||
  CK_OBJECT_HANDLE_PTR phObject  /* gets new object's handle. */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_CopyObject copies an object, creating a new object for the
 | 
			
		||||
 * copy. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_CopyObject)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE    hSession,    /* the session's handle */
 | 
			
		||||
  CK_OBJECT_HANDLE     hObject,     /* the object's handle */
 | 
			
		||||
  CK_ATTRIBUTE_PTR     pTemplate,   /* template for new object */
 | 
			
		||||
  CK_ULONG             ulCount,     /* attributes in template */
 | 
			
		||||
  CK_OBJECT_HANDLE_PTR phNewObject  /* receives handle of copy */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_DestroyObject destroys an object. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_DestroyObject)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,  /* the session's handle */
 | 
			
		||||
  CK_OBJECT_HANDLE  hObject    /* the object's handle */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_GetObjectSize gets the size of an object in bytes. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GetObjectSize)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,  /* the session's handle */
 | 
			
		||||
  CK_OBJECT_HANDLE  hObject,   /* the object's handle */
 | 
			
		||||
  CK_ULONG_PTR      pulSize    /* receives size of object */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_GetAttributeValue obtains the value of one or more object
 | 
			
		||||
 * attributes. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GetAttributeValue)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,   /* the session's handle */
 | 
			
		||||
  CK_OBJECT_HANDLE  hObject,    /* the object's handle */
 | 
			
		||||
  CK_ATTRIBUTE_PTR  pTemplate,  /* specifies attrs; gets vals */
 | 
			
		||||
  CK_ULONG          ulCount     /* attributes in template */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_SetAttributeValue modifies the value of one or more object
 | 
			
		||||
 * attributes */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_SetAttributeValue)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,   /* the session's handle */
 | 
			
		||||
  CK_OBJECT_HANDLE  hObject,    /* the object's handle */
 | 
			
		||||
  CK_ATTRIBUTE_PTR  pTemplate,  /* specifies attrs and values */
 | 
			
		||||
  CK_ULONG          ulCount     /* attributes in template */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_FindObjectsInit initializes a search for token and session
 | 
			
		||||
 * objects that match a template. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_FindObjectsInit)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,   /* the session's handle */
 | 
			
		||||
  CK_ATTRIBUTE_PTR  pTemplate,  /* attribute values to match */
 | 
			
		||||
  CK_ULONG          ulCount     /* attrs in search template */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_FindObjects continues a search for token and session
 | 
			
		||||
 * objects that match a template, obtaining additional object
 | 
			
		||||
 * handles. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_FindObjects)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
 CK_SESSION_HANDLE    hSession,          /* session's handle */
 | 
			
		||||
 CK_OBJECT_HANDLE_PTR phObject,          /* gets obj. handles */
 | 
			
		||||
 CK_ULONG             ulMaxObjectCount,  /* max handles to get */
 | 
			
		||||
 CK_ULONG_PTR         pulObjectCount     /* actual # returned */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_FindObjectsFinal finishes a search for token and session
 | 
			
		||||
 * objects. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_FindObjectsFinal)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession  /* the session's handle */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* Encryption and decryption */
 | 
			
		||||
 | 
			
		||||
/* C_EncryptInit initializes an encryption operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_EncryptInit)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,    /* the session's handle */
 | 
			
		||||
  CK_MECHANISM_PTR  pMechanism,  /* the encryption mechanism */
 | 
			
		||||
  CK_OBJECT_HANDLE  hKey         /* handle of encryption key */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_Encrypt encrypts single-part data. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_Encrypt)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,            /* session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pData,               /* the plaintext data */
 | 
			
		||||
  CK_ULONG          ulDataLen,           /* bytes of plaintext */
 | 
			
		||||
  CK_BYTE_PTR       pEncryptedData,      /* gets ciphertext */
 | 
			
		||||
  CK_ULONG_PTR      pulEncryptedDataLen  /* gets c-text size */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_EncryptUpdate continues a multiple-part encryption
 | 
			
		||||
 * operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_EncryptUpdate)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,           /* session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pPart,              /* the plaintext data */
 | 
			
		||||
  CK_ULONG          ulPartLen,          /* plaintext data len */
 | 
			
		||||
  CK_BYTE_PTR       pEncryptedPart,     /* gets ciphertext */
 | 
			
		||||
  CK_ULONG_PTR      pulEncryptedPartLen /* gets c-text size */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_EncryptFinal finishes a multiple-part encryption
 | 
			
		||||
 * operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_EncryptFinal)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,                /* session handle */
 | 
			
		||||
  CK_BYTE_PTR       pLastEncryptedPart,      /* last c-text */
 | 
			
		||||
  CK_ULONG_PTR      pulLastEncryptedPartLen  /* gets last size */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_DecryptInit initializes a decryption operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_DecryptInit)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,    /* the session's handle */
 | 
			
		||||
  CK_MECHANISM_PTR  pMechanism,  /* the decryption mechanism */
 | 
			
		||||
  CK_OBJECT_HANDLE  hKey         /* handle of decryption key */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_Decrypt decrypts encrypted data in a single part. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_Decrypt)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,           /* session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pEncryptedData,     /* ciphertext */
 | 
			
		||||
  CK_ULONG          ulEncryptedDataLen, /* ciphertext length */
 | 
			
		||||
  CK_BYTE_PTR       pData,              /* gets plaintext */
 | 
			
		||||
  CK_ULONG_PTR      pulDataLen          /* gets p-text size */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_DecryptUpdate continues a multiple-part decryption
 | 
			
		||||
 * operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_DecryptUpdate)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,            /* session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pEncryptedPart,      /* encrypted data */
 | 
			
		||||
  CK_ULONG          ulEncryptedPartLen,  /* input length */
 | 
			
		||||
  CK_BYTE_PTR       pPart,               /* gets plaintext */
 | 
			
		||||
  CK_ULONG_PTR      pulPartLen           /* p-text size */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_DecryptFinal finishes a multiple-part decryption
 | 
			
		||||
 * operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_DecryptFinal)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,       /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pLastPart,      /* gets plaintext */
 | 
			
		||||
  CK_ULONG_PTR      pulLastPartLen  /* p-text size */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* Message digesting */
 | 
			
		||||
 | 
			
		||||
/* C_DigestInit initializes a message-digesting operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_DigestInit)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,   /* the session's handle */
 | 
			
		||||
  CK_MECHANISM_PTR  pMechanism  /* the digesting mechanism */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_Digest digests data in a single part. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_Digest)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,     /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pData,        /* data to be digested */
 | 
			
		||||
  CK_ULONG          ulDataLen,    /* bytes of data to digest */
 | 
			
		||||
  CK_BYTE_PTR       pDigest,      /* gets the message digest */
 | 
			
		||||
  CK_ULONG_PTR      pulDigestLen  /* gets digest length */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_DigestUpdate continues a multiple-part message-digesting
 | 
			
		||||
 * operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_DigestUpdate)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,  /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pPart,     /* data to be digested */
 | 
			
		||||
  CK_ULONG          ulPartLen  /* bytes of data to be digested */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_DigestKey continues a multi-part message-digesting
 | 
			
		||||
 * operation, by digesting the value of a secret key as part of
 | 
			
		||||
 * the data already digested. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_DigestKey)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,  /* the session's handle */
 | 
			
		||||
  CK_OBJECT_HANDLE  hKey       /* secret key to digest */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_DigestFinal finishes a multiple-part message-digesting
 | 
			
		||||
 * operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_DigestFinal)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,     /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pDigest,      /* gets the message digest */
 | 
			
		||||
  CK_ULONG_PTR      pulDigestLen  /* gets byte count of digest */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* Signing and MACing */
 | 
			
		||||
 | 
			
		||||
/* C_SignInit initializes a signature (private key encryption)
 | 
			
		||||
 * operation, where the signature is (will be) an appendix to
 | 
			
		||||
 * the data, and plaintext cannot be recovered from the
 | 
			
		||||
 *signature. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_SignInit)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,    /* the session's handle */
 | 
			
		||||
  CK_MECHANISM_PTR  pMechanism,  /* the signature mechanism */
 | 
			
		||||
  CK_OBJECT_HANDLE  hKey         /* handle of signature key */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_Sign signs (encrypts with private key) data in a single
 | 
			
		||||
 * part, where the signature is (will be) an appendix to the
 | 
			
		||||
 * data, and plaintext cannot be recovered from the signature. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_Sign)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,        /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pData,           /* the data to sign */
 | 
			
		||||
  CK_ULONG          ulDataLen,       /* count of bytes to sign */
 | 
			
		||||
  CK_BYTE_PTR       pSignature,      /* gets the signature */
 | 
			
		||||
  CK_ULONG_PTR      pulSignatureLen  /* gets signature length */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_SignUpdate continues a multiple-part signature operation,
 | 
			
		||||
 * where the signature is (will be) an appendix to the data, 
 | 
			
		||||
 * and plaintext cannot be recovered from the signature. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_SignUpdate)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,  /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pPart,     /* the data to sign */
 | 
			
		||||
  CK_ULONG          ulPartLen  /* count of bytes to sign */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_SignFinal finishes a multiple-part signature operation, 
 | 
			
		||||
 * returning the signature. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_SignFinal)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,        /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pSignature,      /* gets the signature */
 | 
			
		||||
  CK_ULONG_PTR      pulSignatureLen  /* gets signature length */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_SignRecoverInit initializes a signature operation, where
 | 
			
		||||
 * the data can be recovered from the signature. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_SignRecoverInit)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,   /* the session's handle */
 | 
			
		||||
  CK_MECHANISM_PTR  pMechanism, /* the signature mechanism */
 | 
			
		||||
  CK_OBJECT_HANDLE  hKey        /* handle of the signature key */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_SignRecover signs data in a single operation, where the
 | 
			
		||||
 * data can be recovered from the signature. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_SignRecover)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,        /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pData,           /* the data to sign */
 | 
			
		||||
  CK_ULONG          ulDataLen,       /* count of bytes to sign */
 | 
			
		||||
  CK_BYTE_PTR       pSignature,      /* gets the signature */
 | 
			
		||||
  CK_ULONG_PTR      pulSignatureLen  /* gets signature length */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* Verifying signatures and MACs */
 | 
			
		||||
 | 
			
		||||
/* C_VerifyInit initializes a verification operation, where the
 | 
			
		||||
 * signature is an appendix to the data, and plaintext cannot
 | 
			
		||||
 *  cannot be recovered from the signature (e.g. DSA). */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_VerifyInit)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,    /* the session's handle */
 | 
			
		||||
  CK_MECHANISM_PTR  pMechanism,  /* the verification mechanism */
 | 
			
		||||
  CK_OBJECT_HANDLE  hKey         /* verification key */ 
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_Verify verifies a signature in a single-part operation, 
 | 
			
		||||
 * where the signature is an appendix to the data, and plaintext
 | 
			
		||||
 * cannot be recovered from the signature. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_Verify)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,       /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pData,          /* signed data */
 | 
			
		||||
  CK_ULONG          ulDataLen,      /* length of signed data */
 | 
			
		||||
  CK_BYTE_PTR       pSignature,     /* signature */
 | 
			
		||||
  CK_ULONG          ulSignatureLen  /* signature length*/
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_VerifyUpdate continues a multiple-part verification
 | 
			
		||||
 * operation, where the signature is an appendix to the data, 
 | 
			
		||||
 * and plaintext cannot be recovered from the signature. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_VerifyUpdate)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,  /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pPart,     /* signed data */
 | 
			
		||||
  CK_ULONG          ulPartLen  /* length of signed data */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_VerifyFinal finishes a multiple-part verification
 | 
			
		||||
 * operation, checking the signature. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_VerifyFinal)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,       /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pSignature,     /* signature to verify */
 | 
			
		||||
  CK_ULONG          ulSignatureLen  /* signature length */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_VerifyRecoverInit initializes a signature verification
 | 
			
		||||
 * operation, where the data is recovered from the signature. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_VerifyRecoverInit)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,    /* the session's handle */
 | 
			
		||||
  CK_MECHANISM_PTR  pMechanism,  /* the verification mechanism */
 | 
			
		||||
  CK_OBJECT_HANDLE  hKey         /* verification key */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_VerifyRecover verifies a signature in a single-part
 | 
			
		||||
 * operation, where the data is recovered from the signature. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_VerifyRecover)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,        /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pSignature,      /* signature to verify */
 | 
			
		||||
  CK_ULONG          ulSignatureLen,  /* signature length */
 | 
			
		||||
  CK_BYTE_PTR       pData,           /* gets signed data */
 | 
			
		||||
  CK_ULONG_PTR      pulDataLen       /* gets signed data len */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* Dual-function cryptographic operations */
 | 
			
		||||
 | 
			
		||||
/* C_DigestEncryptUpdate continues a multiple-part digesting
 | 
			
		||||
 * and encryption operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_DigestEncryptUpdate)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,            /* session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pPart,               /* the plaintext data */
 | 
			
		||||
  CK_ULONG          ulPartLen,           /* plaintext length */
 | 
			
		||||
  CK_BYTE_PTR       pEncryptedPart,      /* gets ciphertext */
 | 
			
		||||
  CK_ULONG_PTR      pulEncryptedPartLen  /* gets c-text length */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_DecryptDigestUpdate continues a multiple-part decryption and
 | 
			
		||||
 * digesting operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_DecryptDigestUpdate)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,            /* session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pEncryptedPart,      /* ciphertext */
 | 
			
		||||
  CK_ULONG          ulEncryptedPartLen,  /* ciphertext length */
 | 
			
		||||
  CK_BYTE_PTR       pPart,               /* gets plaintext */
 | 
			
		||||
  CK_ULONG_PTR      pulPartLen           /* gets plaintext len */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_SignEncryptUpdate continues a multiple-part signing and
 | 
			
		||||
 * encryption operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_SignEncryptUpdate)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,            /* session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pPart,               /* the plaintext data */
 | 
			
		||||
  CK_ULONG          ulPartLen,           /* plaintext length */
 | 
			
		||||
  CK_BYTE_PTR       pEncryptedPart,      /* gets ciphertext */
 | 
			
		||||
  CK_ULONG_PTR      pulEncryptedPartLen  /* gets c-text length */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_DecryptVerifyUpdate continues a multiple-part decryption and
 | 
			
		||||
 * verify operation. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_DecryptVerifyUpdate)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,            /* session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pEncryptedPart,      /* ciphertext */
 | 
			
		||||
  CK_ULONG          ulEncryptedPartLen,  /* ciphertext length */
 | 
			
		||||
  CK_BYTE_PTR       pPart,               /* gets plaintext */
 | 
			
		||||
  CK_ULONG_PTR      pulPartLen           /* gets p-text length */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* Key management */
 | 
			
		||||
 | 
			
		||||
/* C_GenerateKey generates a secret key, creating a new key
 | 
			
		||||
 * object. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GenerateKey)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE    hSession,    /* the session's handle */
 | 
			
		||||
  CK_MECHANISM_PTR     pMechanism,  /* key generation mech. */
 | 
			
		||||
  CK_ATTRIBUTE_PTR     pTemplate,   /* template for new key */
 | 
			
		||||
  CK_ULONG             ulCount,     /* # of attrs in template */
 | 
			
		||||
  CK_OBJECT_HANDLE_PTR phKey        /* gets handle of new key */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_GenerateKeyPair generates a public-key/private-key pair, 
 | 
			
		||||
 * creating new key objects. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GenerateKeyPair)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE    hSession,                    /* session
 | 
			
		||||
                                                     * handle */
 | 
			
		||||
  CK_MECHANISM_PTR     pMechanism,                  /* key-gen
 | 
			
		||||
                                                     * mech. */
 | 
			
		||||
  CK_ATTRIBUTE_PTR     pPublicKeyTemplate,          /* template
 | 
			
		||||
                                                     * for pub.
 | 
			
		||||
                                                     * key */
 | 
			
		||||
  CK_ULONG             ulPublicKeyAttributeCount,   /* # pub.
 | 
			
		||||
                                                     * attrs. */
 | 
			
		||||
  CK_ATTRIBUTE_PTR     pPrivateKeyTemplate,         /* template
 | 
			
		||||
                                                     * for priv.
 | 
			
		||||
                                                     * key */
 | 
			
		||||
  CK_ULONG             ulPrivateKeyAttributeCount,  /* # priv.
 | 
			
		||||
                                                     * attrs. */
 | 
			
		||||
  CK_OBJECT_HANDLE_PTR phPublicKey,                 /* gets pub.
 | 
			
		||||
                                                     * key
 | 
			
		||||
                                                     * handle */
 | 
			
		||||
  CK_OBJECT_HANDLE_PTR phPrivateKey                 /* gets
 | 
			
		||||
                                                     * priv. key
 | 
			
		||||
                                                     * handle */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_WrapKey wraps (i.e., encrypts) a key. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_WrapKey)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,        /* the session's handle */
 | 
			
		||||
  CK_MECHANISM_PTR  pMechanism,      /* the wrapping mechanism */
 | 
			
		||||
  CK_OBJECT_HANDLE  hWrappingKey,    /* wrapping key */
 | 
			
		||||
  CK_OBJECT_HANDLE  hKey,            /* key to be wrapped */
 | 
			
		||||
  CK_BYTE_PTR       pWrappedKey,     /* gets wrapped key */
 | 
			
		||||
  CK_ULONG_PTR      pulWrappedKeyLen /* gets wrapped key size */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_UnwrapKey unwraps (decrypts) a wrapped key, creating a new
 | 
			
		||||
 * key object. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_UnwrapKey)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE    hSession,          /* session's handle */
 | 
			
		||||
  CK_MECHANISM_PTR     pMechanism,        /* unwrapping mech. */
 | 
			
		||||
  CK_OBJECT_HANDLE     hUnwrappingKey,    /* unwrapping key */
 | 
			
		||||
  CK_BYTE_PTR          pWrappedKey,       /* the wrapped key */
 | 
			
		||||
  CK_ULONG             ulWrappedKeyLen,   /* wrapped key len */
 | 
			
		||||
  CK_ATTRIBUTE_PTR     pTemplate,         /* new key template */
 | 
			
		||||
  CK_ULONG             ulAttributeCount,  /* template length */
 | 
			
		||||
  CK_OBJECT_HANDLE_PTR phKey              /* gets new handle */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_DeriveKey derives a key from a base key, creating a new key
 | 
			
		||||
 * object. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_DeriveKey)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE    hSession,          /* session's handle */
 | 
			
		||||
  CK_MECHANISM_PTR     pMechanism,        /* key deriv. mech. */
 | 
			
		||||
  CK_OBJECT_HANDLE     hBaseKey,          /* base key */
 | 
			
		||||
  CK_ATTRIBUTE_PTR     pTemplate,         /* new key template */
 | 
			
		||||
  CK_ULONG             ulAttributeCount,  /* template length */
 | 
			
		||||
  CK_OBJECT_HANDLE_PTR phKey              /* gets new handle */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* Random number generation */
 | 
			
		||||
 | 
			
		||||
/* C_SeedRandom mixes additional seed material into the token's
 | 
			
		||||
 * random number generator. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_SeedRandom)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,  /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       pSeed,     /* the seed material */
 | 
			
		||||
  CK_ULONG          ulSeedLen  /* length of seed material */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_GenerateRandom generates random data. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GenerateRandom)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession,    /* the session's handle */
 | 
			
		||||
  CK_BYTE_PTR       RandomData,  /* receives the random data */
 | 
			
		||||
  CK_ULONG          ulRandomLen  /* # of bytes to generate */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* Parallel function management */
 | 
			
		||||
 | 
			
		||||
/* C_GetFunctionStatus is a legacy function; it obtains an
 | 
			
		||||
 * updated status of a function running in parallel with an
 | 
			
		||||
 * application. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_GetFunctionStatus)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession  /* the session's handle */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* C_CancelFunction is a legacy function; it cancels a function
 | 
			
		||||
 * running in parallel. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_CancelFunction)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_SESSION_HANDLE hSession  /* the session's handle */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/* Functions added in for Cryptoki Version 2.01 or later */
 | 
			
		||||
 | 
			
		||||
/* C_WaitForSlotEvent waits for a slot event (token insertion,
 | 
			
		||||
 * removal, etc.) to occur. */
 | 
			
		||||
CK_PKCS11_FUNCTION_INFO(C_WaitForSlotEvent)
 | 
			
		||||
#ifdef CK_NEED_ARG_LIST
 | 
			
		||||
(
 | 
			
		||||
  CK_FLAGS flags,        /* blocking/nonblocking flag */
 | 
			
		||||
  CK_SLOT_ID_PTR pSlot,  /* location that receives the slot ID */
 | 
			
		||||
  CK_VOID_PTR pRserved   /* reserved.  Should be NULL_PTR */
 | 
			
		||||
);
 | 
			
		||||
#endif
 | 
			
		||||
							
								
								
									
										1440
									
								
								lib/hx509/ref/pkcs11t.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										1440
									
								
								lib/hx509/ref/pkcs11t.h
									
									
									
									
									
										Normal file
									
								
							
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							
							
								
								
									
										21
									
								
								lib/hx509/ref/pkcs11u.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										21
									
								
								lib/hx509/ref/pkcs11u.h
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,21 @@
 | 
			
		||||
 | 
			
		||||
/* unix version adaption file */
 | 
			
		||||
 | 
			
		||||
#define CK_PTR *
 | 
			
		||||
 | 
			
		||||
#define CK_DEFINE_FUNCTION(returnType, name) \
 | 
			
		||||
   returnType name
 | 
			
		||||
 | 
			
		||||
#define CK_DECLARE_FUNCTION(returnType, name) \
 | 
			
		||||
   returnType name
 | 
			
		||||
 | 
			
		||||
#define CK_DECLARE_FUNCTION_POINTER(returnType, name) \
 | 
			
		||||
   returnType (* name)
 | 
			
		||||
 | 
			
		||||
#define CK_CALLBACK_FUNCTION(returnType, name) \
 | 
			
		||||
   returnType (* name)
 | 
			
		||||
 | 
			
		||||
#ifndef NULL_PTR
 | 
			
		||||
#define NULL_PTR NULL
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
		Reference in New Issue
	
	Block a user