List Info

Thread: Re: new pre release for 0.11.2 available




Re: new pre release for 0.11.2 available
country flaguser name
United States
2007-03-06 16:20:56
OK, I have applied Thomas's patch to the svn revision 3121
checkout a few hours ago with these changes:

    I have added #ifdef HAVE_ZLIB_H so it should compile
    without zlib. If a compressed certificate is found, it
    will call sc_error and return SC_ERROR_NOT_SUPPORTED
    But all my Unix systems have zlib, will try it on
Windows too.

    I added some code to piv-tool.c so it could write out
    a compressed certificate created by gzip.

    Change the card-piv.c to write the cert object with
    the "CertInfo" with compressed flag.

Have compiled and tested on Ubuntu, with writing a
compressed
certificate and the code can read both compressed and
uncompressed certificates.


See the attachment. svn diff output patch.


I can change the names if you want or any other changes
too.



Andreas Jellinghaus wrote:
> what would be better? release -pre4 as 0.11.2 and
create 
> 0.11.3-pre1 with that patch? or do a -pre5 with it?
> 
> Nils already gave a comment on the code a long time
ago, should
> be on the ML archive. I rely on Nils for comments, as
he knows the
> code much better than I do. but I'm currently quite
busy and have
> little time for opensc, and since Nils hasn't responded
to the thread so
> far I guess he is busy too. so if anyone can step in
and work on the
> code to address these issues, that would be great.
> 
> for example compiling without zlib support would be a
good thing.
> (most windows users might want to try without I
guess.)
> 
> Regards, Andreas
> _______________________________________________
> opensc-devel mailing list
> opensc-devellists.opensc-project.org
> http://www.opensc-project.org/mailman/listinfo/opensc
-devel
> 
> 

-- 

  Douglas E. Engert  <DEEngertanl.gov>
  Argonne National Laboratory
  9700 South Cass Avenue
  Argonne, Illinois  60439
  (630) 252-5444

_______________________________________________
opensc-devel mailing list
opensc-devellists.opensc-project.org
http://www.opensc-project.org/mailman/listinfo/opensc
-devel
  
Re: new pre release for 0.11.2 available
country flaguser name
United States
2007-03-06 16:32:44
One minor change, it looks like the #include
"internal.h"
was removed from pkcs15-piv.c. I can add that back in
with any other changes you might want.


Douglas E. Engert wrote:
> OK, I have applied Thomas's patch to the svn revision
3121
> checkout a few hours ago with these changes:
> 
>    I have added #ifdef HAVE_ZLIB_H so it should
compile
>    without zlib. If a compressed certificate is found,
it
>    will call sc_error and return
SC_ERROR_NOT_SUPPORTED
>    But all my Unix systems have zlib, will try it on
Windows too.
> 
>    I added some code to piv-tool.c so it could write
out
>    a compressed certificate created by gzip.
> 
>    Change the card-piv.c to write the cert object with
>    the "CertInfo" with compressed flag.
> 
> Have compiled and tested on Ubuntu, with writing a
compressed
> certificate and the code can read both compressed and
> uncompressed certificates.
> 
> 
> See the attachment. svn diff output patch.
> 
> 
> I can change the names if you want or any other changes
too.
> 
> 
> 
> Andreas Jellinghaus wrote:
>> what would be better? release -pre4 as 0.11.2 and
create 0.11.3-pre1 
>> with that patch? or do a -pre5 with it?
>>
>> Nils already gave a comment on the code a long time
ago, should
>> be on the ML archive. I rely on Nils for comments,
as he knows the
>> code much better than I do. but I'm currently quite
busy and have
>> little time for opensc, and since Nils hasn't
responded to the thread so
>> far I guess he is busy too. so if anyone can step
in and work on the
>> code to address these issues, that would be great.
>>
>> for example compiling without zlib support would be
a good thing.
>> (most windows users might want to try without I
guess.)
>>
>> Regards, Andreas
>> _______________________________________________
>> opensc-devel mailing list
>> opensc-devellists.opensc-project.org
>> http://www.opensc-project.org/mailman/listinfo/opensc
-devel
>>
>>
> 
> 
>
------------------------------------------------------------
------------
> 
> Index: src/tools/piv-tool.c
>
============================================================
=======
> --- src/tools/piv-tool.c	(revision 3121)
> +++ src/tools/piv-tool.c	(working copy)
>  -41,7 +41,7 
>  #include <openssl/pem.h>
>  #include <openssl/err.h>
>  
> -const char *app_name = "opensc-tool";
> +const char *app_name = "piv-tool";
>  
>  static int	opt_reader = -1,
>  		opt_wait = 0;
>  -60,6 +60,7 
>  	{ "usepin",		0, 0,		'P' }, /* some beta
cards want user pin for put_data */
>  	{ "genkey",		0, 0,		'G' },
>  	{ "cert",		0, 0,		'C' },
> +	{ "compresscert", 0, 0,		'Z' },
>  	{ "req",		0, 0, 		'R' },
>  	{ "out",	0, 0, 		'o' },
>  	{ "in",		0, 0, 		'o' },
>  -77,7 +78,8 
>  	"authenticate using default 3des key",
>  	"authenticate using user pin", 
>  	"Generate key <ref>:<alg> 9A:06 on
card, and output pubkey",
> -	"Load the AUTH cert onto card from file
<arg>",
> +	"Load a cert <ref> where <ref> is
9A,9B,9C or 9D",
> +	"Load a cert that has been gziped
<ref>",
>  	"Generate a cert req",
>  	"Output file for cert or key or req",
>  	"Inout file for cert",
>  -94,7 +96,8 
>  RSA * newkey = NULL;
>  
>  
> -static int load_cert(const char * cert_id, const char
* cert_file)
> +static int load_cert(const char * cert_id, const char
* cert_file,
> +					int compress)
>  {
>  	X509 * cert = NULL;
>  	FILE *fp;
>  -106,25 +109,39 
>  	size_t derlen;
>  	int r;
>  
> -
>      if((fp=fopen(cert_file, "r"))==NULL){
>          printf("Cannot open cert file, %s
%sn", 
>  			cert_file, strerror(errno));
>          return -1;
>      }
> -	cert = PEM_read_X509(fp, &cert, NULL, NULL);
> -    fclose(fp);
> -    if(cert == NULL){
> -        printf("file %s does not conatin
PEM-encoded certificaten",
> -			 cert_file);
> -        return-1 ;
> -    }
> +	if (compress) { /* file is gziped already */
> +		struct stat stat_buf;
>  
> -	derlen = i2d_X509(cert, NULL);
> -	der = (u8 *) malloc(derlen);
> -	p = der;
> -	i2d_X509(cert, &p);
> +		stat(cert_file, &stat_buf);
> +		derlen = stat_buf.st_size;
> +		der = malloc(derlen);
> +		if (der == NULL) {
> +			printf("file %s is too big, %dn",
cert_file, derlen);
> +			return-1 ;
> +		}
> +		if (1 != fread(der, derlen, 1, fp)) {
> +			printf("unable to read file
%sn",cert_file);
> +			return -1;
> +		}
> +	} else {
> +		cert = PEM_read_X509(fp, &cert, NULL, NULL);
> +    	if(cert == NULL){
> +        	printf("file %s does not conatin
PEM-encoded certificaten",
> +				 cert_file);
> +        	return -1 ;
> +    	}
>  
> +		derlen = i2d_X509(cert, NULL);
> +		der = (u8 *) malloc(derlen);
> +		p = der;
> +		i2d_X509(cert, &p);
> +	}
> +    fclose(fp);
>  	sc_hex_to_bin(cert_id, buf,&buflen);
>  	
>  	switch (buf[0]) {
>  -142,7 +159,8 
>  		fprintf(stderr, "select file failedn");
>  		 return -1;
>  	}
> -	r = sc_write_binary(card, 0, der, derlen, 0); 
> +	/* we pass compress as the flag to card-piv.c
write_binary */
> +	r = sc_write_binary(card, 0, der, derlen, compress);

>  	
>  	return r;
>  
>  -340,6 +358,7 
>  	int do_admin_mode = 0;
>  	int do_gen_key = 0;
>  	int do_load_cert = 0;
> +	int compress_cert = 0;
>  	int do_req = 0;
>  	int do_print_serial = 0;
>  	int do_print_name = 0;
>  -355,7 +374,7 
>  	setbuf(stdout, NULL);
>  
>  	while (1) {
> -		c = getopt_long(argc, argv,
"nA:G:C:Ri:o:fvs:c:w", options,
&long_optind);
> +		c = getopt_long(argc, argv,
"nA:G:Z:C:Ri:o:fvs:c:w", options,
&long_optind);
>  		if (c == -1)
>  			break;
>  		if (c == '?')
>  -384,6 +403,8 
>  			key_info = optarg;
>  			action_count++;
>  			break;
> +		case 'Z':
> +			compress_cert = 1;
>  		case 'C':
>  			do_load_cert = 1;
>  			cert_id = optarg;
>  -469,7 +490,7 
>  		action_count--;
>  	}
>  	if (do_load_cert) {
> -		if ((err = load_cert(cert_id, in_file)))
> +		if ((err = load_cert(cert_id, in_file,
compress_cert)))
>  			goto end;
>  		action_count--;
>  	}
> Index: src/libopensc/card-piv.c
>
============================================================
=======
> --- src/libopensc/card-piv.c	(revision 3121)
> +++ src/libopensc/card-piv.c	(working copy)
>  -4,6 +4,7 
>   *
>   * Copyright (C) 2001, 2002  Juha Yrjölä
<juha.yrjolaiki.fi>
>   * Copyright (C) 2005, Douglas E. Engert
<deengertanl.gov>
> + * Copyright (C) 2006, Identity Alliance, Thomas
Harning <thomas.harningidentityalliance.com>
>   *
>   * This library is free software; you can redistribute
it and/or
>   * modify it under the terms of the GNU Lesser General
Public
>  -29,8 +30,17 
>  #include <openssl/rsa.h>
>  #include "asn1.h"
>  #include "cardctl.h"
> +#ifdef HAVE_ZLIB_H
> +#include "compression.h"
> +#endif
>  
> -struct piv_private_data {
> +typedef struct {
> +	u8* data;
> +	size_t length;
> +	int enumtag;
> +} piv_cache_item;
> +
> +typedef struct piv_private_data {
>  	struct sc_pin_cmd_pin pin_info;
>  	sc_file_t *aid_file;
>  	int enumtag;
>  -39,9 +49,54 
>  	size_t max_recv_size; /* saved size, need to lie to
pkcs15_read_file */
>  	size_t max_send_size; 
>  	int key_ref; /* saved from set_security_env and */
> -	int alg_id;  /* used in decrypy, signature */ 
> -};
> +	int alg_id;  /* used in decrypt, signature */ 
> +	piv_cache_item* cache;
> +	int cacheLen;
> +	piv_cache_item* current_item;
> +} piv_private_data_t;
>  
> +#define PIV_DATA(card)
((piv_private_data_t*)card->drv_data)
> +
> +static int add_cache_item(piv_private_data_t* priv,
int enumtag, u8* data, size_t length) {
> +	int idx, len = priv->cacheLen;
> +	piv_cache_item* cache = priv->cache;
> +	for(idx = 0; idx < len; idx++) {
> +		if(!cache[idx].data)
> +			break;
> +		if(cache[idx].enumtag == enumtag) /* Found matching
tag */
> +			break;
> +	}
> +	if(idx == len) 
> +		return -1; /* FAILED NO FREE ROOM */
> +	if(cache[idx].data)
> +		free(cache[idx].data);
> +	cache[idx].data = data;
> +	cache[idx].length = length;
> +	cache[idx].enumtag = enumtag;
> +	return 0;
> +}
> +
> +static piv_cache_item*
get_cache_item(piv_private_data_t* priv, int enumtag) {
> +	int idx, len = priv->cacheLen;
> +	piv_cache_item* cache = priv->cache;
> +	for(idx = 0; idx < len; idx++) {
> +		if(cache[idx].enumtag == enumtag)
> +			return &cache[idx];
> +	}
> +	return NULL;
> +}
> +
> +static void free_cache_items(piv_private_data_t* priv)
{
> +	int idx, len = priv->cacheLen;
> +	piv_cache_item* cache = priv->cache;
> +	for(idx = 0; idx < len; idx++) {
> +		if(cache[idx].data) {
> +			free(cache[idx].data);
> +			cache[idx].data = NULL;
> +		}
> +	}
> +}
> +
>  struct piv_aid {
>  	int enumtag;
>  	size_t len_short;	/* min lenght without version */
>  -71,7 +126,8 
>  	PIV_OBJ_X509_CARD_AUTH,
>  	PIV_OBJ_SEC_OBJ,
>  	PIV_OBJ_9B03,
> -	PIV_OBJ_9A06
> +	PIV_OBJ_9A06,
> +	PIV_CACHE_SIZE
>  };
>  
>  struct piv_object {
>  -88,14 +144,12 
>  	{ PIV_OBJ_CCC, "Card Capability Container",

>  			"2.16.840.1.101.3.7.1.219.0", 3,
"x5FxC1x07", "xDBx00", 266},
>  	{ PIV_OBJ_CHUI, "Card Holder Unique
Identifier", 
> -			"2.16.840.1.101.3.7.2.48.0", 3,
"x5FxC1x02", "x30x00", 3377},
> +			"2.16.840.1.101.3.7.2.48.0", 3,
"x5FxC1x02", "x30x00", 3379}, /*
Updated per SP800-73-1 Errata */
>  	{ PIV_OBJ_X509_PIV_AUTH, "X.509 Certificate for
PIV Authentication", 
>  			"2.16.840.1.101.3.7.2.1.1", 3,
"x5FxC1x05", "x01x01", 1856+4+400}
, 
>  		/* extra 400 is hack for MultOS card which returns
2200 bytes  */
> -	{ PIV_OBJ_CHF1, "Card Holder Fingerprint
I",
> -			"2.16.840.1.101.3.7.2.96.16", 3,
"x5FxC1x03", "x60x01", 7768},
> -	{ PIV_OBJ_CHF2, "Card Holder Fingerprint
II",
> -			"2.16.840.1.101.3.7.2.96.17", 3,
"x5FxC1x04", "x60x11", 7768},
> +	{ PIV_OBJ_CHF1, "Card Holder
Fingerprints",
> +			"2.16.840.1.101.3.7.2.96.16", 3,
"x5FxC1x03", "x60x10", 7768},
>  	{ PIV_OBJ_PI, "Printed Information", 
>  			"2.16.840.1.101.3.7.2.48.1", 3,
"x5FxC1x09", "x30x01", 106},
>  	{ PIV_OBJ_CHFI, "Card Holder Facial
Image",
>  -184,7 +238,7 
>  	const u8 * sendbuf, size_t sendbuflen, u8 **
recvbuf,
>  	size_t * recvbuflen)
>  {
> -	struct piv_private_data * priv = (struct
piv_private_data *) card->drv_data;
> +	piv_private_data_t * priv = PIV_DATA(card);
>  	int r;
>  	sc_apdu_t apdu;
>  	u8 rbufinitbuf[20000]; /* crude way to do this  see
above comments */
>  -502,12 +556,12 
>  static int piv_get_data(sc_card_t * card, unsigned int
enumtag, 
>  			u8 **buf, size_t *buf_len)
>  {
> -	struct piv_private_data * priv = (struct
piv_private_data *) card->drv_data;
> +	piv_private_data_t * priv = PIV_DATA(card);
>  	u8 *p;
>  	int r = 0;
>  	u8 tagbuf[8];
>  	size_t tag_len;
> -		
> +	
>  	SC_FUNC_CALLED(card->ctx,1);
>  	sc_debug(card->ctx, "get_data: tag=%d
n", enumtag);
>  
>  -599,7 +653,98 
>  
>  	SC_FUNC_RETURN(card->ctx, 1, r);
>  }
> -	  
> +
> +
> +static int piv_handle_certificate_data(sc_card_t
*card,
> +		int enumtag,
> +		unsigned idx, u8* buf, size_t count,
> +		u8* data, size_t length) {
> +	piv_private_data_t * priv = PIV_DATA(card);
> +	u8* tag;
> +	size_t taglen;
> +	int compressed = 0;
> +	piv_cache_item* item;
> +	/* get the certificate out */
> +	tag = (u8 *) sc_asn1_find_tag(card->ctx, data,
length, 0x71, &taglen);
> +	if (tag && (((*tag) & 0x80) || ((*tag)
& 0x01))) {
> +		compressed = 1;
> +	}
> +	tag = (u8 *) sc_asn1_find_tag(card->ctx, data, 
length, 0x70, &taglen);
> +	if (tag == NULL) {
> +		return SC_ERROR_OBJECT_NOT_VALID;
> +	}
> +	/* Potential truncation */
> +	if(compressed) {
> +#ifdef HAVE_ZLIB_H
> +		size_t len = count;
> +		u8* newBuf = NULL;
> +		if(SC_SUCCESS != do_decompress_alloc(&newBuf,
&len, tag, taglen, COMPRESSION_AUTO)) {
> +			return SC_ERROR_OBJECT_NOT_VALID;
> +		} else {
> +			if(len < count + idx)
> +				count = len - idx;
> +			if(count <= 0)
> +				return 0;
> +			memcpy(buf, newBuf + idx, count);
> +			if(0 != add_cache_item(priv, enumtag, newBuf, len))
{
> +				/* Failed to cache item */
> +				free(newBuf);
> +			}
> +		}
> +		return count;
> +#else
> +		sc_error(card->ctx,"PIV compression not
supported, no zlib");
> +		return SC_ERROR_NOT_SUPPORTED;
> +#endif
> +	}
> +	if(taglen < count + idx)
> +		count = taglen - idx;
> +	if(count <= 0)
> +		return 0;
> +	memcpy(buf, tag, count);
> +	if(0 == add_cache_item(priv, enumtag, NULL, 0)) {
> +		/* Space available in the cache array, use it */
> +		item = get_cache_item(priv, enumtag);
> +		if(item) {
> +			item->data = malloc(taglen);
> +			if(item->data) {
> +				item->length = taglen;
> +				memcpy(item->data, tag, taglen);
> +			}
> +		}
> +	}
> +	return count;
> +}
> +
> +static int piv_handle_data(sc_card_t *card, int
enumtag, 
> +		unsigned idx, u8* buf, size_t count, u8* data,
size_t length) {
> +	/* For now get the first tag, and return the data */
> +	piv_private_data_t * priv = PIV_DATA(card);
> +	u8* tag;
> +	size_t taglen;
> +	piv_cache_item* item;
> +
> +	tag = (u8 *) sc_asn1_find_tag(card->ctx, data, 
length, *data, &taglen);
> +	if (tag == NULL) {
> +		return SC_ERROR_OBJECT_NOT_VALID;
> +	}
> +	if(taglen < count + idx)
> +		count = taglen - idx;
> +	if(count <= 0)
> +		return 0;
> +	memcpy(buf, tag + idx, count);
> +	if(0 == add_cache_item(priv, enumtag, NULL, 0)) {
> +		item = get_cache_item(priv, enumtag);
> +		if(item) {
> +			item->data = malloc(taglen);
> +			if(item->data) {
> +				item->length = taglen;
> +				memcpy(item->data, tag, taglen);
> +			}
> +		}
> +	}
> +	return count;
> +}
>  /* 
>   * Callers of this are expecting a file without tags,
>   * So we need to know what type of file this is, so we
can get the
>  -609,19 +754,32 
>  static int piv_read_binary(sc_card_t *card, unsigned
int idx,
>  		unsigned char *buf, size_t count, unsigned long
flags)
>  {
> -	struct piv_private_data * priv = (struct
piv_private_data *) card->drv_data;
> +	piv_private_data_t * priv = PIV_DATA(card);
> +	piv_cache_item* item = NULL;
> +	int enumtag;
>  	int r;
>  	u8 *rbuf = NULL;
>  	size_t rbuflen = 0;
> -	u8 *tag;
> -	size_t taglen;
>  	u8 *body;
>  	size_t bodylen;
>  
>  	SC_FUNC_CALLED(card->ctx,1);
>  	if (priv->selected_obj < 0) 
>  		 SC_FUNC_RETURN(card->ctx, 1,
SC_ERROR_INTERNAL);
> +	enumtag =
piv_objects[priv->selected_obj].enumtag;
>  
> +	/* Hit the cache */
> +	if(priv->current_item) {
> +		item = priv->current_item;
> +		if(idx + count > item->length) {
> +			count = item->length - idx;
> +		}
> +		if(count <= 0)
> +			return 0;
> +		memcpy(buf, item->data + idx, count);
> +		return count;
> +	}
> +
>  	if (priv->eof == 1)
>  		return 0;
>  
>  -629,7 +787,7 
>  	
>  	if (r >=0) {
>  		/* if tag is 0, assume card is telling us no object
on card */
> -		if (rbuf[0] == '0') {
> +		if (!rbuf || rbuf[0] == '0') {
>  			r = SC_ERROR_FILE_NOT_FOUND;
>  			goto err;
>  		}
>  -639,40 +797,18 
>  			/* if missing, assume its the body */
>  			/* DEE bug in the beta card */
>  			sc_debug(card->ctx," ***** tag 0x53 MISSING
n");
> -			body =  rbuf;
> -			bodylen = rbuflen;
> -#if 0
>  			r = SC_ERROR_INVALID_DATA;
>  			goto err;
> -#endif
>  		}
> -		switch (piv_objects[priv->selected_obj].enumtag)
{
> +		switch (enumtag) {
>  			case PIV_OBJ_X509_PIV_AUTH:
>  			case PIV_OBJ_X509_DS:
>  			case PIV_OBJ_X509_KM:
>  			case PIV_OBJ_X509_CARD_AUTH:
> -				/* get the certificate out */
> -				tag = (u8 *) sc_asn1_find_tag(card->ctx, body, 
bodylen, 0x70, &taglen);
> -				if (tag == NULL) {
> -					r = SC_ERROR_OBJECT_NOT_VALID;
> -					break;
> -				}
> -				memcpy(buf, tag, taglen); /*DEE should check
lengths */
> -				r = taglen;
> -				tag = (u8 *) sc_asn1_find_tag(card->ctx, body, 
bodylen, 0x71, &taglen);
> -				if (tag && ((*tag) & 0x80)) {
> -					sc_debug(card->ctx,0,"Cert is gziped!
%0x2.2xn",*tag);
> -				}
> +				r = piv_handle_certificate_data(card, enumtag,
idx, buf, count, body, bodylen);
>  				break;
>  			default:
> -				/* For now get the first tag, and return the data
*/
> -				tag = (u8 *) sc_asn1_find_tag(card->ctx, body, 
bodylen, *body, &taglen);
> -				if (tag == NULL) {
> -					r = SC_ERROR_OBJECT_NOT_VALID;
> -					break;
> -				}
> -				memcpy(buf, tag, taglen); /*DEE should check
lengths */
> -				r = taglen;
> +				r = piv_handle_data(card, enumtag, idx, buf,
count, body, bodylen);
>  				break;
>  		}
>  	}
>  -720,23 +856,57 
>  	SC_FUNC_RETURN(card->ctx, 1, r);
>  }
>  
> +static int piv_write_certificate(sc_card_t *card,
> +		unsigned idx, const u8* buf, size_t count,
> +		unsigned long flags) {
> +	piv_private_data_t * priv = PIV_DATA(card);
> +	int r = SC_SUCCESS;
> +	u8 *sbuf = NULL;
> +	u8 *p;
> +	size_t sbuflen;
> +	size_t taglen;
>  
> +	sc_debug(card->ctx,"DEE cert
len=%d",count);
> +	taglen = put_tag_and_len(0x70, count, NULL) 
> +		+ put_tag_and_len(0x71, 1, NULL)
> +		+ put_tag_and_len(0xFE, 0, NULL);
> +
> +	sbuflen =  put_tag_and_len(0x53, taglen, NULL);
> +
> +	sbuf = (u8*) malloc(sbuflen);
> +	if (sbuf == NULL) 
> +		SC_FUNC_RETURN(card->ctx, 1,
SC_ERROR_OUT_OF_MEMORY);
> +	p = sbuf;
> +	put_tag_and_len(0x53, taglen, &p);
> +
> +	put_tag_and_len(0x70, count, &p);
> +	memcpy(p, buf, count);
> +	p += count;
> +	put_tag_and_len(0x71, 1, &p);
> +	*p++ = (flags && 1)? 0x80:0x00; /* certinfo,
i.e. gziped? */
> +	put_tag_and_len(0xFE,0,&p); /* LRC tag */
> +
> +	sc_debug(card->ctx,"DEE buf %p len %d
%d", sbuf, p -sbuf, sbuflen);
> +
> +	r = piv_put_data(card, priv->selected_obj, sbuf,
sbuflen);
> +	if (sbuf)
> +		free(sbuf);
> +
> +	return r;
> +}
>  /* 
>   * We need to add the 0x53 tag and other specific
tags, 
>   * and call the piv_put_data 
>   * Note: the select file will have saved the object
type for us 
> + * Write is only used by piv-tool, so we will use
flags==1
> + * to indicate we are writing a compressed cert. 
>   */
>  
>  static int piv_write_binary(sc_card_t *card, unsigned
int idx,
>  		const u8 *buf, size_t count, unsigned long flags)
>  {
> -	struct piv_private_data * priv = (struct
piv_private_data *) card->drv_data;
> -	int r = 0;
> -	u8 *sbuf = NULL;
> -	u8 *p;
> -	size_t sbuflen;
> -	size_t taglen;
> -	
> +	piv_private_data_t * priv = PIV_DATA(card);
> +	/* TODO: Add cache hooks */	
>  	SC_FUNC_CALLED(card->ctx,1);
>  
>  	if (priv->selected_obj < 0)
>  -749,40 +919,12 
>  		case PIV_OBJ_X509_DS:
>  		case PIV_OBJ_X509_KM:
>  		case PIV_OBJ_X509_CARD_AUTH:
> -		sc_debug(card->ctx,"DEE cert
len=%d",count);
> -		
> -			taglen = put_tag_and_len(0x70, count, NULL) 
> -				+ put_tag_and_len(0x71, 1, NULL);
> -
> -			sbuflen =  put_tag_and_len(0x53, taglen, NULL);
> -
> -			sbuf = (u8*) malloc(sbuflen);
> -			if (sbuf == NULL) 
> -				SC_FUNC_RETURN(card->ctx, 1,
SC_ERROR_OUT_OF_MEMORY);
> -			p = sbuf;
> -			put_tag_and_len(0x53, taglen, &p);
> -
> -			put_tag_and_len(0x70, count, &p);
> -			memcpy(p, buf, count);
> -			p += count;
> -			put_tag_and_len(0x71, 1, &p);
> -			*p++ = 0x00; /* certinfo, i.e. not gziped */
> -			sc_debug(card->ctx,"DEE buf %p len %d
%d", sbuf, p -sbuf, sbuflen);
> -			break;
> -			
> +			SC_FUNC_RETURN(card->ctx, 1,
piv_write_certificate(card, idx, buf, count, flags));
>  		default:
>  		sc_debug(card->ctx, "Don't know how to write
object %sn",
>  			piv_objects[priv->selected_obj].name);
> -			r = SC_ERROR_NOT_SUPPORTED;
> -			break;
> +			SC_FUNC_RETURN(card->ctx, 1,
SC_ERROR_NOT_SUPPORTED);
>  	}
> -
> -	if (r == 0) 
> -		r = piv_put_data(card, priv->selected_obj, sbuf,
sbuflen);
> -	if (sbuf)
> -		free(sbuf);
> -
> -	SC_FUNC_RETURN(card->ctx, 1, r);
>  }
>  
>  /*
>  -954,7 +1096,7 
>  static int piv_general_external_authenticate(sc_card_t
*card, 
>  		unsigned int key_ref, unsigned int alg_id)
>  {
> -	struct piv_private_data * priv = (struct
piv_private_data *) card->drv_data;
> +	piv_private_data_t * priv = PIV_DATA(card);
>  	int r, outl;
>  	u8  *rbuf = NULL;
>  	size_t rbuflen;
>  -1109,7 +1251,7 
>                      const sc_security_env_t *env,
>                      int se_num)
>  {
> -	struct piv_private_data * priv = (struct
piv_private_data *) card->drv_data;
> +	piv_private_data_t * priv = PIV_DATA(card);
>  	
>  	SC_FUNC_CALLED(card->ctx,1);
>  
>  -1139,7 +1281,7 
>  					const u8 * data, size_t datalen,
>  					u8 * out, size_t outlen)
>  {
> -	struct piv_private_data * priv = (struct
piv_private_data *) card->drv_data;
> +	piv_private_data_t * priv = PIV_DATA(card);
>  	int r;
>  	u8 *p;
>  	u8 *tag;
>  -1228,7 +1370,8 
>  static int piv_select_file(sc_card_t *card, const
sc_path_t *in_path,
>  	sc_file_t **file_out)
>  {
> - 	struct piv_private_data * priv = (struct
piv_private_data *) card->drv_data;
> + 	piv_private_data_t * priv = PIV_DATA(card);
> +	piv_cache_item* item = NULL;
>  	int i;
>  	const u8 *path;
>  	int pathlen;
>  -1255,8 +1398,14 
>  	priv->selected_obj = i;
>  	priv->eof = 0;
>  
> +	/* check out the cache */
> +	item = get_cache_item(priv, i);
> +	if(item) {
> +		priv->current_item = item;
> +	}
> +	
>  	/* make it look like the file was found. We don't
want to read it now,. */ 
> -
> +	
>  	if (file_out) {
>  		file = sc_file_new();
>  		if (file == NULL)
>  -1266,8 +1415,13 
>  		/* this could be like the FCI */
>  		file->type =  SC_FILE_TYPE_DF;
>  		file->shareable = 0;
> -		file->ef_structure = 0; 
> -		file->size = piv_objects[i].maxlen;
> +		file->ef_structure = 0;
> +		if(item) {
> +			file->size = item->length;
> +		} else {
> +			file->size = piv_objects[i].maxlen;
> +		}
> +
>  		file->id =
(piv_objects[i].containerid[0]<<8) +
piv_objects[i].containerid[1];
>  
>  		*file_out = file;
>  -1280,12 +1434,16 
>  
>  static int piv_finish(sc_card_t *card)
>  {
> - 	struct piv_private_data * priv = (struct
piv_private_data *) card->drv_data;
> + 	piv_private_data_t * priv = PIV_DATA(card);
>  
>  	SC_FUNC_CALLED(card->ctx,1);
>  	if (priv) {
>  		if (priv->aid_file)
>  			sc_file_free(priv->aid_file);
> +		if(priv->cache) {
> +			free_cache_items(priv);
> +			free(priv->cache);
> +		}
>  		free(priv);
>  	}
>  	return 0;
>  -1294,9 +1452,18 
>  
>  static int piv_match_card(sc_card_t *card)
>  {
> +	int i;
> +	sc_file_t aidfile;
>  	SC_FUNC_CALLED(card->ctx,1);
> -	/* dee need to look at AID */
> -	return 0; /* never match */
> +	/* Since we send an APDU, the card's logout function
may be called...
> +	 * however it may be in dirty memory */
> +	card->ops->logout = NULL;
> +
> +	/* Detect by selecting applet */
> +	sc_ctx_suppress_errors_on(card->ctx);
> +	i = !(piv_find_aid(card, &aidfile));
> +	sc_ctx_suppress_errors_off(card->ctx);
> +	return i; /* never match */
>  }
>  
>  
>  -1304,16 +1471,17 
>  {
>  	int r;
>  	unsigned long flags;
> -	struct piv_private_data *priv;
> +	piv_private_data_t *priv;
>  
>  	SC_FUNC_CALLED(card->ctx,1);
> -	priv = (struct piv_private_data *) calloc(1,
sizeof(struct piv_private_data));
> +	priv = (piv_private_data_t *) calloc(1,
sizeof(piv_private_data_t));
>  
>  	if (!priv)
>  		return SC_ERROR_OUT_OF_MEMORY;
>  	priv->aid_file = sc_file_new();
>  	priv->selected_obj = -1;
> -	priv->max_recv_size = card->max_recv_size;
> +	priv->max_recv_size = 256;
> +	//priv->max_recv_size = card->max_recv_size;
>  	priv->max_send_size = card->max_send_size;
>  	card->max_recv_size = 0xffff; /* must force pkcs15
read_binary in one call */
>  	card->max_send_size = 0xffff;
>  -1339,6 +1507,9 
>  	_sc_card_add_rsa_alg(card, 3072, flags, 0); /*
optional */
>  	
>  	card->caps |= SC_CARD_CAP_RNG;
> +	
> +	priv->cache = calloc(PIV_CACHE_SIZE,
sizeof(piv_cache_item));
> +	priv->cacheLen = PIV_CACHE_SIZE;
>  
>  	if (r > 0)
>  		r = 0;
> Index: src/libopensc/pkcs15-piv.c
>
============================================================
=======
> --- src/libopensc/pkcs15-piv.c	(revision 3121)
> +++ src/libopensc/pkcs15-piv.c	(working copy)
>  -5,6 +5,9 
>   * Copyright (C) 2005, Douglas E. Engert
<deengertanl.gov> 
>   *               2004, Nils Larsch <larschtrustcenter.de>
>   *
> + * Copyright (C) 2006, Identity Alliance, 
> + *               Thomas Harning <thomas.harningidentityalliance.com>
> + *
>   * This library is free software; you can redistribute
it and/or
>   * modify it under the terms of the GNU Lesser General
Public
>   * License as published by the Free Software
Foundation; either
>  -19,7 +22,6 
>   * License along with this library; if not, write to
the Free Software
>   * Foundation, Inc., 59 Temple Place, Suite 330,
Boston, MA  02111-1307  USA
>   */
> -#include "internal.h"
>  
>  #include <stdlib.h>
>  #include <string.h>
>  -33,88 +35,12 
>  #include <openssl/rsa.h>
>  #include <openssl/pem.h>
>  #include "strlcpy.h"
> +#include "p15card-helper.h"
>  
>  #define MANU_ID		"piv_II "
>  
>  int sc_pkcs15emu_piv_init_ex(sc_pkcs15_card_t *,
sc_pkcs15emu_opt_t *);
>  
> -
> -typedef struct objdata_st {
> -	const char *id;
> -	const char *label;
> -	const char *aoid;
> -	int     authority;
> -	const char *path;
> -	int         obj_flags;
> -} objdata;
> -
> -typedef struct cdata_st {
> -	const char *id;
> -	const char *label;
> -	int	    authority;
> -	const char *path;
> -	int         obj_flags;
> -} cdata;
> -
> -typedef struct pdata_st {
> -	const char *id;
> -	const char *label;
> -	const char *path;
> -	int         ref;
> -	int         type;
> -	unsigned int maxlen;
> -	unsigned int minlen;
> -	unsigned int storedlen;
> -	int         flags;	
> -	int         tries_left;
> -	const char  pad_char;
> -	int         obj_flags;
> -} pindata; 
> -
> -typedef struct pubdata_st {
> -	const char *id;
> -	const char *label;
> -	unsigned int modulus_len;
> -	int         usage;
> -	const char *path;
> -	int         ref;
> -	const char *auth_id;
> -	int         obj_flags;
> -} pubdata;
> -
> -typedef struct prdata_st {
> -	const char *id;
> -	const char *label;
> -	unsigned int modulus_len;
> -	int         usage;
> -	const char *path;
> -	int         ref;
> -	const char *auth_id;
> -	int         obj_flags;
> -} prdata;
> -
> -typedef struct keyinfo_st {
> -	int fileid;
> -	sc_pkcs15_id_t id;
> -	unsigned int modulus_len;
> -	u8 modulus[1024/8];
> -} keyinfo;
> -
> -	
> -
> -#define
USAGE_NONREP	SC_PKCS15_PRKEY_USAGE_NONREPUDIATION
> -#define USAGE_KE	SC_PKCS15_PRKEY_USAGE_ENCRYPT | 
> -			SC_PKCS15_PRKEY_USAGE_DECRYPT | 
> -			SC_PKCS15_PRKEY_USAGE_WRAP    | 
> -			SC_PKCS15_PRKEY_USAGE_UNWRAP
> -#define USAGE_AUT	SC_PKCS15_PRKEY_USAGE_ENCRYPT | 
> -			SC_PKCS15_PRKEY_USAGE_DECRYPT | 
> -			SC_PKCS15_PRKEY_USAGE_WRAP    | 
> -			SC_PKCS15_PRKEY_USAGE_UNWRAP  | 
> -			SC_PKCS15_PRKEY_USAGE_SIGN
> -
> -
> -
>  static int piv_detect_card(sc_pkcs15_card_t *p15card)
>  {
>  	sc_card_t *card = p15card->card;
>  -126,98 +52,137 
>  	return SC_SUCCESS;
>  }
>  
> -static int sc_pkcs15emu_piv_init(sc_pkcs15_card_t
*p15card)
> -{
> -	const objdata objects[] = {
> -		{"1", "Card Capability
Container", 
> -				"2.16.840.1.101.3.7.1.219.0", 0,
"DB00", 0},
> -		{"2", "Card Holder Unique
Identifier",
> -				"2.16.840.1.101.3.7.2.48.0", 0 ,
"3000", 0},
> -		{"3", "Card Holder Fingerprint
I",
> -				"2.16.840.1.101.3.7.2.96.16", 0,
"6010", SC_PKCS15_CO_FLAG_PRIVATE},
> -		{"4", "Card Holder Fingerprint
II",
> -				"2.16.840.1.101.3.7.2.96.17", 0,
"6011", SC_PKCS15_CO_FLAG_PRIVATE},
> -		{"5", "Printed Information",
> -				"2.16.840.1.101.3.7.2.48.1", 0,
"3001", SC_PKCS15_CO_FLAG_PRIVATE},
> -		{"6", "Card Holder Facial
Image", 
> -				"2.16.840.1.101.3.7.2.96.48", 0,
"6030", SC_PKCS15_CO_FLAG_PRIVATE},
> -		{"7", "Security Object",
> -				"2.16.840.1.101.3.7.2.144.0", 0,
"9000", 0},
> -		{NULL, NULL, NULL, 0, NULL, 0}
> -	};
> +const objdata objects[] = {
> +	{"1", "Card Capability
Container", 
> +			"2.16.840.1.101.3.7.1.219.0", 0,
"DB00", 0},
> +	{"2", "Card Holder Unique
Identifier",
> +			"2.16.840.1.101.3.7.2.48.0", 0 ,
"3000", 0},
> +	{"3", "Card Holder
Fingerprints",
> +			"2.16.840.1.101.3.7.2.96.16", 0,
"6010", SC_PKCS15_CO_FLAG_PRIVATE},
> +	{"4", "Printed Information",
> +			"2.16.840.1.101.3.7.2.48.1", 0,
"3001", SC_PKCS15_CO_FLAG_PRIVATE},
> +	{"5", "Card Holder Facial Image",

> +			"2.16.840.1.101.3.7.2.96.48", 0,
"6030", SC_PKCS15_CO_FLAG_PRIVATE},
> +	{"6", "Security Object",
> +			"2.16.840.1.101.3.7.2.144.0", 0,
"9000", 0},
> +	{NULL, NULL, NULL, 0, NULL, 0}
> +};
>  
> -	/* 
> -	 * NIST 800-73-1 is proposing to lift the restriction
on 
> -	 * requering pin protected certs. Thus the default
will be to 
> -	 * not require this. But there are a number of test
cards 
> -	 * that do enforce it. Code later on will allow
SC_PKCS15_CO_FLAG_PRIVATE
> -	 * to be set. 
> -	 */
> -	const cdata certs[] = {
> -		{"1", "Certificate for PIV
Authentication", 0, "0101", 0},
> -		{"2", "Certificate for Digital
Signature", 0, "0100", 0},
> -		{"3", "Certificate for Key
Management", 0, "0102", 0},
> -		{"4", "Certificate for Card
Authentication", 0, "0500", 0},
> -		{NULL, NULL, 0, NULL, 0}
> -	};
> +/* 
> + * NIST 800-73-1 is proposing to lift the restriction
on 
> + * requering pin protected certs. Thus the default
will be to 
> + * not require this. But there are a number of test
cards 
> + * that do enforce it. Code later on will allow
SC_PKCS15_CO_FLAG_PRIVATE
> + * to be set. 
> + */
> +const cdata certs[] = {
> +	{"1", "Certificate for PIV
Authentication", 0, "0101", 0},
> +	{"2", "Certificate for Digital
Signature", 0, "0100", 0},
> +	{"3", "Certificate for Key
Management", 0, "0102", 0},
> +#if 0 /* Strange break */
> +	{"4", "Certificate for Card
Authentication", 0, "0500", 0},
> +#endif
> +	{NULL, NULL, 0, NULL, 0}
> +};
>  
> -	const pindata pins[] = {
> -		{ "1", "PIV Card Holder pin",
"", 0x80,
> -		  SC_PKCS15_PIN_TYPE_ASCII_NUMERIC,
> -		  8, 4, 8, 
> -		  SC_PKCS15_PIN_FLAG_NEEDS_PADDING |
> -		  SC_PKCS15_PIN_FLAG_LOCAL, 
> -		  -1, 0xFF,
> -		  SC_PKCS15_CO_FLAG_PRIVATE },
> -		{ "2", "PIV PUK", "",
0x81, 
> -		  SC_PKCS15_PIN_TYPE_ASCII_NUMERIC,
> -		  8, 4, 8, 
> -		  SC_PKCS15_PIN_FLAG_NEEDS_PADDING |
> -		  SC_PKCS15_PIN_FLAG_LOCAL |
SC_PKCS15_PIN_FLAG_SO_PIN |
> -		  SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN, 
> -		  -1, 0xFF, 
> -		  SC_PKCS15_CO_FLAG_PRIVATE },
> -		/* there are some more key, but dont need for now
*/
> -		/* The admin 9b might fall in here */
> -		{ NULL, NULL, NULL, 0, 0, 0, 0, 0, 0, 0, 0, 0}
> -	};
> +const pindata pins[] = {
> +	{ "1", "PIV Card Holder pin",
"", 0x80,
> +	  SC_PKCS15_PIN_TYPE_ASCII_NUMERIC,
> +	  8, 4, 8, 
> +	  SC_PKCS15_PIN_FLAG_NEEDS_PADDING |
> +	  SC_PKCS15_PIN_FLAG_LOCAL, 
> +	  -1, 0xFF,
> +	  SC_PKCS15_CO_FLAG_PRIVATE },
> +	{ "2", "PIV PUK", "",
0x81, 
> +	  SC_PKCS15_PIN_TYPE_ASCII_NUMERIC,
> +	  8, 4, 8, 
> +	  SC_PKCS15_PIN_FLAG_NEEDS_PADDING |
> +	  SC_PKCS15_PIN_FLAG_LOCAL |
SC_PKCS15_PIN_FLAG_SO_PIN |
> +	  SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN, 
> +	  -1, 0xFF, 
> +	  SC_PKCS15_CO_FLAG_PRIVATE },
> +	/* there are some more key, but dont need for now */
> +	/* The admin 9b might fall in here */
> +	{ NULL, NULL, NULL, 0, 0, 0, 0, 0, 0, 0, 0, 0}
> +};
>  
>  
> -	/*
> -	 * The size of the key or the algid is not really
known
> -	 * but can be derived from the certificates. 
> -	 * DEE need to fix - We will still refer to the
"key files" as 06 even of not.
> -	 * 07 is 2048, 05 is 3072. 
> -	 */
> -	const pubdata pubkeys[] = {
> +/*
> + * The size of the key or the algid is not really
known
> + * but can be derived from the certificates. 
> + * DEE need to fix - We will still refer to the
"key files" as 06 even of not.
> + * 07 is 2048, 05 is 3072. 
> + */
> +const pubdata pubkeys[] = {
>  
> -		{ "1", "AUTH pubkey", 1024,
USAGE_AUT, "9A06", 
> -		  0x9A, "1", 0},
> -		{ "2", "SIGN pubkey", 1024,
USAGE_AUT, "9C06", 
> -		  0x9C, "1", 0},
> -		{ "3", "KEY MAN pubkey", 1024,
USAGE_AUT, "9D06", 
> -		  0x9D, "1", 0},
> -		{ "4", "ADMIN pubkey", 1024,
USAGE_AUT, "9B06", 
> -		  0x9B, "1", 0},
> -		{ NULL, NULL, 0, 0, NULL, 0, NULL, 0}
> -		
> -	};
> +	{ "1", "AUTH pubkey", 1024,
USAGE_AUT, "9A06", 
> +	  0x9A, "1", 0},
> +	{ "2", "SIGN pubkey", 1024,
USAGE_AUT, "9C06", 
> +	  0x9C, "1", 0},
> +	{ "3", "KEY MAN pubkey", 1024,
USAGE_AUT, "9D06", 
> +	  0x9E, "1", 0},
> +	{ "4", "ADMIN pubkey", 1024,
USAGE_AUT, "9B06", 
> +	  0x9B, "1", 0},
> +	{ NULL, NULL, 0, 0, NULL, 0, NULL, 0}
> +	
> +};
>  
> -	const prdata prkeys[] = {
> -		{ "1", "AUTH key", 1024,
USAGE_AUT, "",
> -		  0x9A, "1", 0},
> -		{ "2", " SIGN key", 1024,
USAGE_AUT, "",
> -		  0x9B, "1", 0},
> -		{ "3", "KEY MAN key", 1024,
USAGE_AUT, "",
> -		  0x9C, "1", 0},
> -		{ "4", "ADMIN key", 1024,
USAGE_AUT, "",
> -		  0x9D, "1", 0},
> -		{ NULL, NULL, 0, 0, NULL, 0, NULL, 0}
> -	};
> +const prdata prkeys[] = {
> +	{ "1", "AUTH key", 1024,
USAGE_AUT, "",
> +	  0x9A, "1", 0},
> +	{ "2", "SIGN key", 1024,
USAGE_AUT, "",
> +	  0x9C, "1", 0},
> +	{ "3", "KEY MAN key", 1024,
USAGE_AUT, "",
> +	  0x9E, "1", 0},
> +	{ "4", "ADMIN key", 1024,
USAGE_AUT, "",
> +	  0x9B, "1", 0},
> +	{ NULL, NULL, 0, 0, NULL, 0, NULL, 0}
> +};
>  
> -	int    r, i;
> +/* TEMPORARY: Should hook into card-piv ... */
> +static int piv_load_cached_cert(sc_card_t *card, u8**
buf, size_t* count, int* should_free) {
> +	/* File already selected.. just read... */
> +	int r;
> +	u8* out = malloc(4096*2);
> +	r = sc_read_binary(card, 0, out, 4096*2, 0);
> +	if(r < 0) {
> +		free(out);
> +		*buf = NULL;
> +		*count = 0;
> +		return r;
> +	}
> +	*count = r;
> +	*buf = out;
> +	*should_free = 1;
> +	return SC_SUCCESS;
> +}
> +
> +#define CHECK_CERTIFICATES 1
> +static p15data_items items = {
> +	objects,
> +	certs,
> +	pins,
> +	NULL,
> +	prkeys,
> +#ifdef CHECK_CERTIFICATES
> +	piv_load_cached_cert,
> +#else
> +	NULL,
> +#endif
> +	default_cert_handle,
> +	1,
> +#ifdef CHECK_CERTIFICATES
> +	0,
> +#else
> +	1,
> +#endif
> +	0
> +};
> +
> +static int sc_pkcs15emu_piv_init(sc_pkcs15_card_t
*p15card)
> +{
> +	int    r;
>  	sc_card_t *card = p15card->card;
> -	int exposed_cert[4] = {1, 0, 0, 0};
>  
>  	SC_FUNC_CALLED(card->ctx, 1);
>  
>  -238,162 +203,9 
>          p15card->serial_number =
strdup("9876543210");
>  
>  	sc_debug(card->ctx, "PIV-II adding
objects...");
> -
> -	/* set other objects */
> -	for (i = 0; objects[i].label; i++) {
> -		struct sc_pkcs15_data_info obj_info;
> -		struct sc_pkcs15_object    obj_obj;
> -
> -		memset(&obj_info, 0, sizeof(obj_info));
> -		memset(&obj_obj, 0, sizeof(obj_obj));
> -		sc_pkcs15_format_id(objects[i].id,
&obj_info.id);
> -		sc_format_path(objects[i].path,
&obj_info.path);
> -		strlcpy(obj_info.app_label, objects[i].label,
sizeof(obj_info.app_label));
> -		r = sc_format_oid(&obj_info.app_oid,
objects[i].aoid);
> -		if (r != SC_SUCCESS)
> -			return r;
> -
> -		strlcpy(obj_obj.label, objects[i].label,
sizeof(obj_obj.label));
> -		obj_obj.flags = objects[i].obj_flags;
> -		
> -		r = sc_pkcs15emu_object_add(p15card,
SC_PKCS15_TYPE_DATA_OBJECT, 
> -			&obj_obj, &obj_info); 
> -		if (r < 0)
> -			SC_FUNC_RETURN(card->ctx, 1, r);
> -	}
> -
> -	/* set certs */
> -	for (i = 0; certs[i].label; i++) {
> -		struct sc_pkcs15_cert_info cert_info;
> -		struct sc_pkcs15_object    cert_obj;
> -		
> -		if ((card->flags & 0x20) && 
(exposed_cert[i] == 0))
> -			continue;
> -
> -		memset(&cert_info, 0, sizeof(cert_info));
> -		memset(&cert_obj,  0, sizeof(cert_obj));
>  	
> -		sc_pkcs15_format_id(certs[i].id,
&cert_info.id);
> -		cert_info.authority = certs[i].authority;
> -		sc_format_path(certs[i].path, &cert_info.path);
> +	r = initialize_all(p15card, &items);
>  
> -		strlcpy(cert_obj.label, certs[i].label,
sizeof(cert_obj.label));
> -		cert_obj.flags = certs[i].obj_flags;
> -
> -		/* Cards based on NIST 800-73 may enforce pin
protected certs */
> -		/* But this is being dropped in 800-73-1 */
> -		if (card->flags & 0x10) {
> -			cert_obj.flags |=  SC_PKCS15_CO_FLAG_PRIVATE;
> -		}
> -
> -		r = sc_pkcs15emu_add_x509_cert(p15card,
&cert_obj, &cert_info);
> -		if (r < 0)
> -			SC_FUNC_RETURN(card->ctx, 1, r);
> -	}
> -
> -
> -	/* set pins */
> -
> -	for (i = 0; pins[i].label; i++) {
> -		struct sc_pkcs15_pin_info pin_info;
> -		struct sc_pkcs15_object   pin_obj;
> -
> -		memset(&pin_info, 0, sizeof(pin_info));
> -		memset(&pin_obj,  0, sizeof(pin_obj));
> -
> -		sc_pkcs15_format_id(pins[i].id,
&pin_info.auth_id);
> -		pin_info.reference     = pins[i].ref;
> -		pin_info.flags         = pins[i].flags;
> -		pin_info.type          = pins[i].type;
> -		pin_info.min_length    = pins[i].minlen;
> -		pin_info.stored_length = pins[i].storedlen;
> -		pin_info.max_length    = pins[i].maxlen;
> -		pin_info.pad_char      = pins[i].pad_char;
> -		sc_format_path(pins[i].path, &pin_info.path);
> -		pin_info.tries_left    = -1;
> -
> -		strlcpy(pin_obj.label, pins[i].label,
sizeof(pin_obj.label));
> -		pin_obj.flags = pins[i].obj_flags;
> -
> -		r = sc_pkcs15emu_add_pin_obj(p15card, &pin_obj,
&pin_info);
> -		if (r < 0)
> -			SC_FUNC_RETURN(card->ctx, 1, r);
> -	}
> -
> -
> -
> -	/* set public keys */
> -	/* We may only need this during initialzation when
genkey
> -	 * gets the pubkey, but it can not be read from the
card 
> -	 * at a later time. The piv-tool can stach in file 
> -	 */ 
> -
> -	for (i = 0; pubkeys[i].label; i++) {
> -		struct sc_pkcs15_pubkey_info pubkey_info;
> -		struct sc_pkcs15_object     pubkey_obj;
> -
> -		if ((card->flags & 0x20) && 
(exposed_cert[i] == 0))
> -			continue;
> -
> -		memset(&pubkey_info, 0, sizeof(pubkey_info));
> -		memset(&pubkey_obj,  0, sizeof(pubkey_obj));
> -
> -		sc_pkcs15_format_id(pubkeys[i].id,
&pubkey_info.id);
> -		pubkey_info.usage         = pubkeys[i].usage;
> -		pubkey_info.native        = 1;
> -		pubkey_info.key_reference = pubkeys[i].ref;
> -		pubkey_info.modulus_length= pubkeys[i].modulus_len;
> -		/* we really don't know how many bits or module
length,
> -		 * we will assume 1024 for now 
> -		 */
> -		sc_format_path(pubkeys[i].path,
&pubkey_info.path);
> -
> -		strlcpy(pubkey_obj.label, pubkeys[i].label,
sizeof(pubkey_obj.label));
> -
> -		pubkey_obj.flags = pubkeys[i].obj_flags;
> -
> -		if (pubkeys[i].auth_id)
> -			sc_pkcs15_format_id(pubkeys[i].auth_id,
&pubkey_obj.auth_id);
> -
> -		r = sc_pkcs15emu_add_rsa_pubkey(p15card,
&pubkey_obj, &pubkey_info);
> -		if (r < 0)
> -			SC_FUNC_RETURN(card->ctx, 1, r);
> -	}
> -
> -
> -	/* set private keys */
> -	for (i = 0; prkeys[i].label; i++) {
> -		struct sc_pkcs15_prkey_info prkey_info;
> -		struct sc_pkcs15_object     prkey_obj;
> -
> -		if ((card->flags & 0x20) && 
(exposed_cert[i] == 0))
> -			continue;
> -
> -		memset(&prkey_info, 0, sizeof(prkey_info));
> -		memset(&prkey_obj,  0, sizeof(prkey_obj));
> -
> -		sc_pkcs15_format_id(prkeys[i].id,
&prkey_info.id);
> -		prkey_info.usage         = prkeys[i].usage;
> -		prkey_info.native        = 1;
> -		prkey_info.key_reference = prkeys[i].ref;
> -		prkey_info.modulus_length= prkeys[i].modulus_len;
> -		/* we really don't know how many bits or module
length,
> -		 * we will assume 1024 for now
> -		 */
> -		sc_format_path(prkeys[i].path,
&prkey_info.path);
> -
> -		strlcpy(prkey_obj.label, prkeys[i].label,
sizeof(prkey_obj.label));
> -
> -		prkey_obj.flags = prkeys[i].obj_flags;
> -
> -		if (prkeys[i].auth_id)
> -			sc_pkcs15_format_id(prkeys[i].auth_id,
&prkey_obj.auth_id);
> -
> -		r = sc_pkcs15emu_add_rsa_prkey(p15card,
&prkey_obj, &prkey_info);
> -		if (r < 0)
> -			SC_FUNC_RETURN(card->ctx, 1, r);
> -	}
> -
>  	SC_FUNC_RETURN(card->ctx, 1, SC_SUCCESS);
>  }
>  
> Index: src/libopensc/Makefile.mak
>
============================================================
=======
> --- src/libopensc/Makefile.mak	(revision 3121)
> +++ src/libopensc/Makefile.mak	(working copy)
>  -29,6 +29,7 
>  	card-oberthur.obj card-belpic.obj
card-atrust-acos.obj 
>  	card-incrypto34.obj card-piv.obj
>  	muscle.obj card-muscle.obj muscle-filesystem.obj 
> +	compression.obj p15card-helper.obj 
>  	
>  	pkcs15-openpgp.obj pkcs15-infocamere.obj
pkcs15-starcert.obj 
>  	pkcs15-tcos.obj pkcs15-esteid.obj
pkcs15-postecert.obj 
> Index: src/libopensc/Makefile.am
>
============================================================
=======
> --- src/libopensc/Makefile.am	(revision 3121)
> +++ src/libopensc/Makefile.am	(working copy)
>  -33,14 +33,15 
>  	
>  	pkcs15-openpgp.c pkcs15-infocamere.c
pkcs15-starcert.c 
>  	pkcs15-tcos.c pkcs15-esteid.c pkcs15-postecert.c
pkcs15-gemsafe.c 
> -	pkcs15-actalis.c pkcs15-atrust-acos.c
pkcs15-tccardos.c pkcs15-piv.c
> +	pkcs15-actalis.c pkcs15-atrust-acos.c
pkcs15-tccardos.c pkcs15-piv.c 
> +	compression.c p15card-helper.c
>  libopensc_la_LDFLAGS = -version-info OPENSC_LT_CURRENT:OPENSC_LT_REVISION:OPENSC_LT_AGE
>  libopensc_la_LIBADD = LIBSCCONF
$(OPENSSL_LIBS) $(OPENCT_LIBS) $(PCSC_LIBS) $(LTLIBLTDL)
>  
>  include_HEADERS = 
>  	opensc.h pkcs15.h emv.h 
>  	cardctl.h asn1.h log.h ui.h 
> -	errors.h types.h
> +	errors.h types.h compression.h
>  
>  noinst_HEADERS = cards.h ctbcs.h internal.h esteid.h
muscle.h muscle-filesystem.h part10.h
>  
> 
> 
>
------------------------------------------------------------
------------
> 
> _______________________________________________
> opensc-devel mailing list
> opensc-devellists.opensc-project.org
> http://www.opensc-project.org/mailman/listinfo/opensc
-devel

-- 

  Douglas E. Engert  <DEEngertanl.gov>
  Argonne National Laboratory
  9700 South Cass Avenue
  Argonne, Illinois  60439
  (630) 252-5444
_______________________________________________
opensc-devel mailing list
opensc-devellists.opensc-project.org
http://www.opensc-project.org/mailman/listinfo/opensc
-devel

[1-2]

about | contact  Other archives ( Real Estate discussion Medical topics )