[PATCHes] OpenSSL 0.9.6g: OBJ_txt2obj, EVP reinitialisation

2002-08-30 Thread Reddie, Steven

I've included two patches which fix issues introduced in OpenSSL 0.9.6e/f/g
(I found them when upgrading from d to g).

The first patch is a single character change that resolves ticket#260.  The
bug is that in EVP_txt2obj() the content length rather than the length of
the tag+length+content is being passed into d2i_ASN1_OBJECT().

The second patch fixes two static done flags used by
OpenSSL_add_all_ciphers() and OpenSSL_add_all_digests().  When calling these
functions the done flag is set so that subsequent calls don't add the
ciphers/digests again.  EVP_cleanup() clears these lists and when these
functions are called again they don't re-add the ciphers/digests.  This fix
makes the two flags global and clears them in EVP_cleanup().  I noticed that
the ERR_load_XXX_strings() functions also use such static flags.  These
aren't causing me any troubles at the moment but it looks like something
else that also needs fixing to allow OpenSSL to be re-initialised.

NOTE: I've cc'd [EMAIL PROTECTED] but this address seems defunct so I have
also notified the BXA about these changes seperately as their requirements
seem to have changed.  See
http://www.bxa.doc.gov/Encryption/PubAvailEncSourceCodeNofify.html for
details.

 openssl-0.9.6g-txt2obj.patch  openssl-0.9.6g-evp-reinit.patch 
Steven
--
Steven Reddie [EMAIL PROTECTED]
Senior Software Engineer
Computer Associates Pty Ltd (Australia)




openssl-0.9.6g-txt2obj.patch
Description: Binary data


openssl-0.9.6g-evp-reinit.patch
Description: Binary data


RE: [openssl.org #260] OBJ_txt2nid not working after upgrading to 0.9.6g

2002-08-29 Thread Reddie, Steven

I've traced this down to ASN1_get_object.  It fails at line 128 which had
previously been ifdef'd out:

if (*plength  (omax - (p - *pp)))
{
ASN1err(ASN1_F_ASN1_GET_OBJECT,ASN1_R_TOO_LONG);
/* Set this so that even if things are not long enough
 * the values are set correctly */
ret|=0x80;
}

In my case of trying to lookup an oid, plength=3, omax=3, (p-*pp)=2.  The
passed in buffer at *pp is:

06 03 55 1D 11  - subject alt name oid

OBJ_txt2obj which calls d2i_ASN1_OBJECT which calls ASN1_get_object passes
in 3 as the length.  The content length is 3, but the length of the
tag+length+content is 5.  Not knowing this code very well I'm not yet sure
where the problem lies.  Any clues?

Steven

-Original Message-
From: [EMAIL PROTECTED] [mailto:[EMAIL PROTECTED]]
Sent: Thursday, 29 August 2002 6:46 PM
Cc: [EMAIL PROTECTED]
Subject: [openssl.org #260] OBJ_txt2nid not working after upgrading to
0.9.6g 



We have some code that was working with OpenSSL 0.9.6d this morning.  Now
that I've upgraded to 0.9.6g it's failing.

OBJ_txt2nid(2.5.29.17) is now returning 0 instead of the expected 85
(NID_subject_alt_name).

OBJ_nid2sn(NID_subject_alt_name) does return subjectAltName.

It seems that the mapping is only broken in one direction.  Is this a known
problem?

Steven
--
Steven Reddie [EMAIL PROTECTED]
Senior Software Engineer
Computer Associates Pty Ltd (Australia)

__
OpenSSL Project http://www.openssl.org
User Support Mailing List[EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



RE: [openssl.org #260] OBJ_txt2nid not working after upgrading to 0.9.6g

2002-08-29 Thread Reddie, Steven

The bug is in OBJ_txt2obj at obj_dat.c:420.  The 'i' in line:

op=d2i_ASN1_OBJECT(NULL,p,i);

should be replaced with 'j':

op=d2i_ASN1_OBJECT(NULL,p,j);

In the case of subject alt name (06 03 55 1D 11), i=3 and j=5.  My guess is
that the code in ASN1_get_object which had previously been indef'd out had
been disabled due to this bug, ie. the symptom fixed rather than the
cause.

Steven

-Original Message-
From: Reddie, Steven 
Sent: Friday, 30 August 2002 11:09 AM
To: [EMAIL PROTECTED]
Subject: RE: [openssl.org #260] OBJ_txt2nid not working after upgrading
to 0.9.6g 


I've traced this down to ASN1_get_object.  It fails at line 128 which had
previously been ifdef'd out:

if (*plength  (omax - (p - *pp)))
{
ASN1err(ASN1_F_ASN1_GET_OBJECT,ASN1_R_TOO_LONG);
/* Set this so that even if things are not long enough
 * the values are set correctly */
ret|=0x80;
}

In my case of trying to lookup an oid, plength=3, omax=3, (p-*pp)=2.  The
passed in buffer at *pp is:

06 03 55 1D 11  - subject alt name oid

OBJ_txt2obj which calls d2i_ASN1_OBJECT which calls ASN1_get_object passes
in 3 as the length.  The content length is 3, but the length of the
tag+length+content is 5.  Not knowing this code very well I'm not yet sure
where the problem lies.  Any clues?

Steven

-Original Message-
From: [EMAIL PROTECTED] [mailto:[EMAIL PROTECTED]]
Sent: Thursday, 29 August 2002 6:46 PM
Cc: [EMAIL PROTECTED]
Subject: [openssl.org #260] OBJ_txt2nid not working after upgrading to
0.9.6g 



We have some code that was working with OpenSSL 0.9.6d this morning.  Now
that I've upgraded to 0.9.6g it's failing.

OBJ_txt2nid(2.5.29.17) is now returning 0 instead of the expected 85
(NID_subject_alt_name).

OBJ_nid2sn(NID_subject_alt_name) does return subjectAltName.

It seems that the mapping is only broken in one direction.  Is this a known
problem?

Steven
--
Steven Reddie [EMAIL PROTECTED]
Senior Software Engineer
Computer Associates Pty Ltd (Australia)

__
OpenSSL Project http://www.openssl.org
User Support Mailing List[EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



Differences between BSAFE keys and OpenSSL keys

2001-08-30 Thread Reddie, Steven

I'm not clear on the problem here (I'm asking on behalf of someone).  They
claim that keys created with OpenSSL are not useable with BSAFE.  They are
also calling them BER keys.  My understanding is that DER, being a subset of
BER, is used for encoding all keys.  Therefore a DER file is a BER file, and
OpenSSL shouldn't have a problem with them.  Are there any known
issues/workarounds for dealing with BSAFE?

Regards,

Steven
--
Steven Reddie [EMAIL PROTECTED]
Senior Software Engineer
Computer Associates Pty Ltd (Australia)

__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



RE: PKCS#11 engine support

2001-05-03 Thread Reddie, Steven

Zoran, I'd be happy to test your implementation.  The PKCS#11 devices that I
have at my disposal are:
Eracom CSA7001/7002
nCipher nFast SCSI HSM
GemPlus PC410 smartcard reader
Litronic Netsignia 210 smartcard reader
and I think there may be a Rainbow HSM and Rainbow iKey's floating around
somewhere.

I was gearing up to submit the OpenSSL/PKCS#11 integration that I've been
developing/using for the last 18 months.  It works with the devices listed
above, and the Rainbow CryptoSwift 300.  It's taken me this long to get
approval from above.  I've only implemented RSA operations though, so
perhaps yours is more complete.  Mine is implemented using the RSA_METHOD
hook rather than as an ENGINE component, so yours may be more relevant.

Regards,

Steven

 -Original Message-
 From: Zoran Radenkovic [SMTP:[EMAIL PROTECTED]]
 Sent: Thursday, May 03, 2001 11:42 AM
 To:   [EMAIL PROTECTED]
 Cc:   [EMAIL PROTECTED]
 Subject:  PKCS#11 engine support
 
 Hi,
 
 We are currently producing an OpenSSL/mod_ssl/Apache solution that uses
 our
 new h/w accelerator
 card CSA8000. This card talks to the host using PKCS#11 interface and it
 plugs-in to OpenSSL
 via engine API. Currently it supports 0.9.6 version (in next few days we
 will look
 in 0.9.6a as well). Engine support is completely PKCS#11 based (it's not
 h/w specific as other engines)
 and should work with any cryptoki implementation. We tested it with
 cryptoki for CSA7000, CSA8000
 adapters and s/w based cryptoki. We don't have available any non-Eracom
 cryptoki.
 
 We got approval from management to opensource this patch for openssl if
 there is an interest. It would
 be great if we can catch the train for 0.9.7. How far is it?
 
 I have few questions if we go further:
 a)   How much is engine API changed in 0.9.7. Will 0.9.6a port will work
 or
 is demanding significant
 change?
 
 b)   Does openssl development team have any means to test it with criptoki
 implementation.
 Because CSA8000 will be released in next few weeks it will be very hard to
 get handle to one adapter.
 We can maybe provide Eracom's s/w criptoki implementation for
 openssl-development team.
 
 c)   Is it sufficient to give you a patch for 0.9.6a or we need to port it
 on 0.9.7 shapshot  first.
 
 
 Cheers,
 Zoran Radenkovic
 
 
 
 ERACOM Products meeting today's security needs.
 Visit our Website at: http://www.eracom.com.au
 Or call ERACOM Pty. Ltd. on: +61 7 5593 4911
 
 __
 OpenSSL Project http://www.openssl.org
 Development Mailing List   [EMAIL PROTECTED]
 Automated List Manager   [EMAIL PROTECTED]
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



RE: PKCS#11 engine support

2001-05-03 Thread Reddie, Steven

I've only used the two smartcard readers listed below, with Schlumberger and
GemPlus/GemPKCS cards.  I understand what you're saying, but I initially had
problems using the Schlumberger card with the GemPlus reader and concluded
that the complete PKCS#11 view of the token was influenced by the drivers
for the reader.  However, I'm now using a different batch of Schlumberger
cards with the same reader (although the reader drivers have been updated).
So, perhaps compatibility issues make it necessary to list the readers as
well as the tokens that are supported.

 -Original Message-
 From: Erwann ABALEA [SMTP:[EMAIL PROTECTED]]
 Sent: Thursday, May 03, 2001 6:58 PM
 To:   [EMAIL PROTECTED]
 Subject:  RE: PKCS#11 engine support
 
 On Thu, 3 May 2001, Reddie, Steven wrote:
 
  Zoran, I'd be happy to test your implementation.  The PKCS#11 devices
 that I
  have at my disposal are:
  Eracom CSA7001/7002
  nCipher nFast SCSI HSM
 
  GemPlus PC410 smartcard reader
  Litronic Netsignia 210 smartcard reader
 
 Please don't say that a smartcard reader is a PKCS#11 token... The token
 is the smartcard, not the reader. I think you're talking about a GemSAFE
 card accessed with a PC410 reader, right? You could use the same card with
 the Litronic reader, as soon as you splitted the code between
 reader-dependant and card-dependant. The best way to do this is to use the
 PC/SC API.
 
  and I think there may be a Rainbow HSM and Rainbow iKey's floating
 around
  somewhere.
 
  I was gearing up to submit the OpenSSL/PKCS#11 integration that I've
  been developing/using for the last 18 months.  It works with the
  devices listed above, and the Rainbow CryptoSwift 300.  It's taken me
  this long to get approval from above.  I've only implemented RSA
  operations though, so perhaps yours is more complete.  Mine is
  implemented using the RSA_METHOD hook rather than as an ENGINE
  component, so yours may be more relevant.
 
  Regards,
 
  Steven
 
   -Original Message-
   From: Zoran Radenkovic [SMTP:[EMAIL PROTECTED]]
   Sent: Thursday, May 03, 2001 11:42 AM
   To:   [EMAIL PROTECTED]
   Cc:   [EMAIL PROTECTED]
   Subject:  PKCS#11 engine support
  
   Hi,
  
   We are currently producing an OpenSSL/mod_ssl/Apache solution that
 uses
   our
   new h/w accelerator
   card CSA8000. This card talks to the host using PKCS#11 interface and
 it
   plugs-in to OpenSSL
   via engine API. Currently it supports 0.9.6 version (in next few days
 we
   will look
   in 0.9.6a as well). Engine support is completely PKCS#11 based (it's
 not
   h/w specific as other engines)
   and should work with any cryptoki implementation. We tested it with
   cryptoki for CSA7000, CSA8000
   adapters and s/w based cryptoki. We don't have available any
 non-Eracom
   cryptoki.
  
   We got approval from management to opensource this patch for openssl
 if
   there is an interest. It would
   be great if we can catch the train for 0.9.7. How far is it?
  
   I have few questions if we go further:
   a)   How much is engine API changed in 0.9.7. Will 0.9.6a port will
 work
   or
   is demanding significant
   change?
  
   b)   Does openssl development team have any means to test it with
 criptoki
   implementation.
   Because CSA8000 will be released in next few weeks it will be very
 hard to
   get handle to one adapter.
   We can maybe provide Eracom's s/w criptoki implementation for
   openssl-development team.
  
   c)   Is it sufficient to give you a patch for 0.9.6a or we need to
 port it
   on 0.9.7 shapshot  first.
  
  
   Cheers,
   Zoran Radenkovic
  
  
  
   ERACOM Products meeting today's security needs.
   Visit our Website at: http://www.eracom.com.au
   Or call ERACOM Pty. Ltd. on: +61 7 5593 4911
  
   __
   OpenSSL Project http://www.openssl.org
   Development Mailing List   [EMAIL PROTECTED]
   Automated List Manager   [EMAIL PROTECTED]
  __
  OpenSSL Project http://www.openssl.org
  Development Mailing List   [EMAIL PROTECTED]
  Automated List Manager   [EMAIL PROTECTED]
 
 
 -- 
 Erwann ABALEA
 [EMAIL PROTECTED]
 RSA PGP Key ID: 0x2D0EABD5
 -
 When uncertain, or in doubt, run in circles and scream.
 
 __
 OpenSSL Project http://www.openssl.org
 Development Mailing List   [EMAIL PROTECTED]
 Automated List Manager   [EMAIL PROTECTED]
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List

RE: Encryption Problem

2001-02-08 Thread Reddie, Steven

I don't know of rsautl, but for RSA encryption in general the data being
encrypted must be shorter than the key length (modulus length).  For PKCS1
padding, the data length must be at least 11 bytes shorted than the key
length.  It's of course possible to encrypt consecutive blocks until all
data has been encrypted, but since you're getting this error I'm guessing
that rsautl can only handle a single block.  So if you're using a 512-bit
key your data can be at most 53 bytes, and if it's a 1024-bit key your data
should be 117 bytes or less.

Steven
--
Steven Reddie [EMAIL PROTECTED]
Senior Software Engineer
Computer Associates Pty Ltd (Australia)

 -Original Message-
 From: Sergio Sagliocco [SMTP:[EMAIL PROTECTED]]
 Sent: Thursday, February 08, 2001 10:11 PM
 To:   [EMAIL PROTECTED]
 Cc:   [EMAIL PROTECTED]
 Subject:  Encryption Problem
 
 I 'm trying  to encrypt a file with rsautl so:
 
  openssl rsautl  -in text -inkey cacert.pem -certin -encrypt -out enc
 
 but it displays the following error:
 
 1840:error:0406D06E:rsa routines:RSA_padding_add_PKCS1_type_2:data too
 large for key size:rsa_pk1.c:151:
 
 I've tried to change padding but it display the same error.
 
 What is the problem?
 
 Is there a limit for the size of the file to encrypt?
 
 Regards,
 
 Sergio
 
 
 
 __
 OpenSSL Project http://www.openssl.org
 Development Mailing List   [EMAIL PROTECTED]
 Automated List Manager   [EMAIL PROTECTED]
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



RE: smartcard / openssl integration +PKCS11

2001-01-18 Thread Reddie, Steven

You're code looks correct.

To be accurate, there is no "public modulus".  The modulus is the same for
both the public and private key, and is therefore simply referred to as the
modulus.

I assume that you've also set:
template[0].type = CKA_MODULUS;
template[1].type = CKA_PUBLIC_EXPONENT;

Have you checked that the bytes of template[0].pValue and template[1].pValue
(and the lengths template[0].ulValueLen and template[1].ulValueLen) match
EXACTLY the bytes stored in the CKA_MODULUS and CKA_PUBLIC_EXPONENT
attributes of the key on the smartcard?  I guess it would be possible for
the CKA_PUBLIC_EXPONENT to be a full 32-bit value (4 bytes) even when it
only contains 3 significant bytes, and if BN_bn2bin returns only 3 bytes
then the C_FindObjects wont find a match.

Steven
--
Steven Reddie [EMAIL PROTECTED]
Senior Software Engineer
OpenDirectory Lab, Computer Associates Pty Ltd (Australia)


 -Original Message-
 From: Nenad Tomasic [SMTP:[EMAIL PROTECTED]]
 Sent: Friday, January 19, 2001 12:20 AM
 To:   [EMAIL PROTECTED]
 Subject:  smartcard / openssl integration +PKCS11
 
 Hello , 
 
 I have an RSA-key pair with the corresponding certificate in a smartcard. 
 
 I wanted to retrieve the values of the public modulus and the public
 exponent of the 
 public key to assign the values in a search template , and then to use the
 search template 
 in the PKCS11-Methods 
 C_FindObjectsInit  and C_FindObjects to get a handle to the private key. 
 
 But something went wrong, it didn't find an object at all, it matched only
 when in my 
 search-template was just the the public modulus. 
 
 Does anyone has an idea? 
 
 thanx 
 
 nenad tomasic 
   
   
   
   
 
  pN = publicKey-pkey.rsa-n;  /*public Modulus  as a *BIGNUM*/ 
  pE = publicKey-pkey.rsa-e;  /*public exponent  as a *BIGNUM*/ 
   
  pModulus = malloc(BN_num_bytes(pN)); 
  pExponent = malloc(BN_num_bytes(pE)); 
   
  template[0].pValue = pModulus; 
  template[1].pValue = pExponent; 
 
  template[0].ulValueLen = BN_bn2bin(pN, template[0].pValue); 
  template[1].ulValueLen = BN_bn2bin(pE, template[1].pValue); 
   
  rv = tokenInfo.pFunctionList-C_FindObjectsInit(hSession, template, 2); 
  if(rv != CKR_OK) { 
   return NULL; 
  } 
   
  rv = tokenInfo.pFunctionList-C_FindObjects(hSession, phPrivKey, 1,
 ulObjectCount); 
  if(rv != CKR_OK) { 
   return NULL; 
  } 
   
 
 ==   ulObjectCount == 0 
   
 -- 
 
 +-+
 | Nenad Tomasic Roentgenstr. 22 Phone: +41 1-272 6111 |
 | AdNovum InformatikCH-8005 Zuerich Fax:   +41 1-272 6312 |
 | |
 | AdNovum Software Inc. San Mateo, CA 94404 Voice: (650) 525-9322 |
 |1400 Fashion Island Boulevard #309 Fax:   (650) 525-9324 |
 +-+
 | E-MAIL : mailto:[EMAIL PROTECTED] |
 |   http://www.adnovum.ch  |
 +-+
  
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



RE: cvs commit: openssl/crypto/rsa rsa_eay.c

2000-12-19 Thread Reddie, Steven

The problem with only locking during the assignment is that potentially
mutliple threads will be doing [extensive] work that will be thrown away
when they discover that another thread beat them to it.  The result could be
that the lock is held for less time, but all threads do more work and
therefore the system is slower anyway.

I'm not sure that I understand your alternative to per-object locks.  In the
case of the new locks in rsa_eay.c, it is necessary to make all threads that
are trying to initialize and then use the montgomery values wait until the
values have been initialized.  Therefore competing threads still need to
wait on something, so if it's not a class-lock, it would have to be a
per-object lock.  Or maybe I'm missing something here.

Until per-object locking (or similar) is implemented, I think it's best to
allocate a new lock for this particular operation, say
CRYPTO_LOCK_RSA_LAZY_INIT.  Then at least it wont delay the reference
counting that CRYPTO_LOCK_RSA is used for.

Better to be safe and potentially slower than fast and out of control.

Steven

 -Original Message-
 From: Geoff Thorpe [SMTP:[EMAIL PROTECTED]]
 Sent: Tuesday, December 19, 2000 7:56 AM
 To:   [EMAIL PROTECTED]
 Subject:  Re: cvs commit: openssl/crypto/rsa rsa_eay.c
 
 Hi Bodo (and anyone else interested),
 
 Just a thought I was having about locking and things. Rather than us
 worrying so much about how to do per-object locking (as opposed to our
 current per-class locking), I wonder if it's worth considering how to
 minimize the number and complexity of operations that happen under this
 global locking. Anyway, "per-object" locking can be manufactured out of
 per-class locking by simply using the class locks to sychronise access to
 integers in the objects that themselves measure on/off mutexing, semaphore
 counters, or whatever. I won't say it's a great idea, but it's possible.
 My idea though is that the same principle could at least gain us some
 better mileage with the per-class locking if we use those locks only to
 flick switches and the like, but otherwise try and put all the meaty
 structural operations *outside* such locking.
 
 This seems to be one such case;
 
 On Mon, 18 Dec 2000 [EMAIL PROTECTED] wrote:
 
Obtain lock CRYPTO_LOCK_RSA before creating BN_MONT_CTX
structures and setting rsa-_method_mod_{n,p,q}.
 
 Rather than creating the BN_MONT_CTX structures inside a lock, surely it's
 a better idea to compete via a lock for *who* will assign the per-computed
 data to the structures. Doing the actual computations, allocations, etc
 should not need to happen inside a lock. I think ... perhaps you or anyone
 else can put me straight if I'm missing something salient.
 
 Eg.
 
Index: rsa_eay.c
===
RCS file: /e/openssl/cvs/openssl/crypto/rsa/rsa_eay.c,v
retrieving revision 1.14
retrieving revision 1.14.2.1
diff -u -r1.14 -r1.14.2.1
--- rsa_eay.c 2000/06/01 22:18:44 1.14
+++ rsa_eay.c 2000/12/18 16:36:07 1.14.2.1
@@ -138,9 +138,24 @@
  
  if ((rsa-_method_mod_n == NULL)  (rsa-flags 
 RSA_FLAG_CACHE_PUBLIC))
  {
- if ((rsa-_method_mod_n=BN_MONT_CTX_new()) != NULL)
- if (!BN_MONT_CTX_set(rsa-_method_mod_n,rsa-n,ctx))
- goto err;
+ CRYPTO_w_lock(CRYPTO_LOCK_RSA);
+ if (rsa-_method_mod_n == NULL)
+ {
+ BN_MONT_CTX* bn_mont_ctx;
+ if ((bn_mont_ctx=BN_MONT_CTX_new()) == NULL)
+ {
+ CRYPTO_w_unlock(CRYPTO_LOCK_RSA);
+ goto err;
+ }
+ if (!BN_MONT_CTX_set(bn_mont_ctx,rsa-n,ctx))
+ {
+ BN_MONT_CTX_free(bn_mont_ctx);
+ CRYPTO_w_unlock(CRYPTO_LOCK_RSA);
+ goto err;
+ }
+ rsa-_method_mod_n = bn_mont_ctx;
+ }
+ CRYPTO_w_unlock(CRYPTO_LOCK_RSA);
  }
 
 [snip]
 
 What if the code was structured as follows;
 
 if((rsa-_method_mod_n == NULL)  [etc])
 {
 BN_MONT_CTX *bn_mont_ctx;
 int bailout;
 if((bn_mont_ctx=BN_MONT_CTX_new()) == NULL)
 [do error stuff]
 if(!BN_MONT_CTX_set())
 [do error stuff]
 bailout = 0;
 /* Only now do we grab the lock to ensure threads don't race to
  * assign montgomery stuff to the RSA structure. */
 CRYPTO_w_lock(CRYPTO_LOCK_RSA);
 /* Now we check the _method_mod_n and stuff *inside* the lock */
 if((rsa-_method_mod_n == NULL)  [etc])
  rsa-_method_mod_n = bn_mont_ctx;
 else
  bailout = 1;
 CRYPTO_w_unlock(CRYPTO_LOCK_RSA);
 

RE: cvs commit: openssl/crypto/rsa rsa_eay.c

2000-12-19 Thread Reddie, Steven

Thanks for the clarification Geoff.  I see where you're coming from.  In my
application it is only the single instance of the application's private key
that really needs protecting.  The per-worker-thread public keys are never
shared across threads and therefore don't need to incur the cost of the
per-class thread.  As you point out the private key is only initialized
once, whereas the per-thread keys get initialized over and over again.  So I
agree, better to waste those cycles on the once-only initialization only.

Steven

 -Original Message-
 From: Geoff Thorpe [SMTP:[EMAIL PROTECTED]]
 Sent: Wednesday, December 20, 2000 7:38 AM
 To:   [EMAIL PROTECTED]
 Subject:  RE: cvs commit: openssl/crypto/rsa rsa_eay.c
 
 Hi,
 
 On Wed, 20 Dec 2000, Reddie, Steven wrote:
 
  The problem with only locking during the assignment is that potentially
  mutliple threads will be doing [extensive] work that will be thrown away
  when they discover that another thread beat them to it.  The result
 could be
  that the lock is held for less time, but all threads do more work and
  therefore the system is slower anyway.
 
 Yes, but that's a per-object race you're talking about there - in fact
 it's a per-object *initialisation* race ... once those montgomery forms
 are set up, this problem goes away for the rest of the object's lifetime.
 However, if you put a lock around the entire montgomery setup, then you've
 got computationally intensive operations blocking all access to the
 per-class lock (CRYPTO_LOCK_RSA in this case). If you have an 8-CPU
 machine running loads of threads doing SSL (or some other RSA-based
 protocol), then every RSA key that gets received (eg. from a peer
 certificate, an ephemeral key, or whatever) will grab the global lock and
 do computationally expensive operations inside it during its first use.
 The result could be that threads on the other 7 CPUs sit there blocking on
 the same global lock, and sadly that "first" use may even be the only use!
 So you'd effectively have the performance of a 1-thread 1-CPU system
 running perverse (for single-threaded) program logic.
 
  I'm not sure that I understand your alternative to per-object locks.  In
 the
  case of the new locks in rsa_eay.c, it is necessary to make all threads
 that
  are trying to initialize and then use the montgomery values wait until
 the
  values have been initialized.  Therefore competing threads still need to
  wait on something, so if it's not a class-lock, it would have to be a
  per-object lock.  Or maybe I'm missing something here.
 
 Nope - I will post something about a locking idea in the near future but
 it's not directly relevant right here and now (in particular, it's not
 going to address what we do right now with this montgomery-setup stuff
 anyhow! :-). However, there is an alternative that gives better
 concurrency than class-locking yet doesn't require one to necessarily give
 each object its own lock ... more to come.
 
  Until per-object locking (or similar) is implemented, I think it's best
 to
  allocate a new lock for this particular operation, say
  CRYPTO_LOCK_RSA_LAZY_INIT.  Then at least it wont delay the reference
  counting that CRYPTO_LOCK_RSA is used for.
 
 Hm, but it still grabs a global lock during an expensive operation - I
 really think here that the risk of multiple threads going for the same
 object at the same time is less than multiple threads trying the same
 operation on different objects at the same time. Using per-object locking
 makes this go away (but introduces a number of other potential problems)
 but whilst we have per-class locking, it's pretty unacceptable to do
 computational work inside such a global lock.
 
  Better to be safe and potentially slower than fast and out of control.
 
 Which this is - if 3 threads go for the same uninitialised RSA key at the
 same time, it's probably because that RSA key is going to be around a
 while (eg. perhaps it's the key belonging to the host's X509
 certificate/key-pair or some such thing). Even if all 3 calculate the
 montgomery forms and only one does the assignment - it's not really a
 biggee in the general scheme of things and again it's just a first-use
 issue. At least it's not a biggee compared to the current alternative
 IMHO. However, putting the global RSA lock around the entire montgomery
 setup could continue to risk contention throughout the life of the
 application even when multiple threads are operating on multiple distinct
 (and perhaps one-off and unrelated) keys.
 
 When you start to consider the implications of this on SMP systems, global
 locking becomes evil incarnate and as such should only be held for the
 absolute minimum work necessary.
 
 Cheers,
 Geoff
 
 
 __
 OpenSSL Project http://www.openssl.org
 Development Mailing List   [EMAIL PROTECTED]
 Automated Li

RE: My patch to rsa_eay.c didn't seem to get accepted

2000-12-14 Thread Reddie, Steven

I thought that in this case it was simply a matter of using the existing
CRYPTO_LOCK_RSA.  I had a look at the other few references and can't see any
way that a deadlock could occur due to this reuse.  Or is this lock only
supposed to be used for thread-safe reference counting?

Since the use of these locks can already be enabled/disabled at
compile-time, I don't think that the flags are required, or am I missing
something here?

Steven

 -Original Message-
 From: Geoff Thorpe [SMTP:[EMAIL PROTECTED]]
 Sent: Thursday, December 14, 2000 8:09 PM
 To:   [EMAIL PROTECTED]
 Subject:  Re: My patch to rsa_eay.c didn't seem to get accepted
 
 On Thu, 14 Dec 2000, Richard Levitte - VMS Whacker wrote:
 
  From: "Reddie, Steven" [EMAIL PROTECTED]
  
  Steven.Reddie I've come across four race conditions in the following
  Steven.Reddie functions in rsa_eay.c:
  Steven.Reddie  RSA_public_encrypt
  Steven.Reddie  RSA_public_decrypt
  Steven.Reddie  RSA_eay_mod_exp (x2)
  Steven.Reddie 
  Steven.Reddie These can cause unexpected failure of the RSA_eay_
  Steven.Reddie encryption/decryption functions for both public and
  Steven.Reddie private key operations.  The problem occurs when more
  Steven.Reddie than one thread simultaneously uses the same RSA key
  
  Hmm, someone else needs to tell us if this is meant to be supported or
  not for now.  However, when it comes to the locking part, for now
  CRYPTO_LOCK_RSA is probably the more appropriate one, but what we
  really should have is a lock for each instance of the RSA structure
  (or any structure).  I've talked about this some time ago, perhaps
  it's time to do more than just talking...
 
 Well, this one at least would be relatively straightforward. Steven is
 right (I think) that by locking the first-time initialisation of per-RSA
 cached variables (montgomery stuff in this case) that basically the rest
 becomes implicitly thread safe. So the obvious thing to me seems to
 include a flag (RSA, DSA, and a truck load of other structures already
 have a flag variable) to indicate whether these initialisations should
 take place under the CRYPTO_LOCK_RSA lock or not.
 
 By changing the flag value in the [RSA|DSA|...]_METHOD itself, the default
 behaviour could be switched between "default to locking" and "default to
 no locking", and then of course one still has the option to change it per
 key if they choose. In fact another level up; the default flag that is
 *compiled* into the ..._METHODs could also be configurable - presumably in
 the same way that other locking stuff is configurable for compilation.
 
 What d'y'all think?
 
 Cheers,
 Geoff
 
 __
 OpenSSL Project http://www.openssl.org
 Development Mailing List   [EMAIL PROTECTED]
 Automated List Manager   [EMAIL PROTECTED]
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



My patch to rsa_eay.c didn't seem to get accepted

2000-12-13 Thread Reddie, Steven

Hi core team,

On 4th October I submitted a patch to crypto/rsa/rsa_eay.c to fix some
multithreaded race conditions.  Nobody replied to my message at the time,
and I've just noticed that the latest snapshot doesn't include these fixes.

Did this just get overlooked, or was it purposely rejected?  If rejected,
could you please let me know the reason so that I can address it, as these
are real bugs still present on the HEAD.

I've appended the original message to this email.

Regards,

Steven
--
Steven Reddie [EMAIL PROTECTED]
Senior Software Engineer
OpenDirectory Lab, Computer Associates Pty Ltd (Australia)



I've come across four race conditions in the following functions in
rsa_eay.c:
RSA_public_encrypt
RSA_public_decrypt
RSA_eay_mod_exp (x2)

These can cause unexpected failure of the RSA_eay_ encryption/decryption
functions for both public and private key operations.  The problem occurs
when more than one thread simultaneously uses the same RSA key (more
specifically, when multiple threads simultaneously initialise
rsa-_method_mod_[npq] when RSA_FLAG_CACHE_PUBLIC is set).  The problems are
only easily reproduceable on a multi-processor machine, although they can
also occur on a single processor machine.

I've attached a patch for OpenSSL 0.9.6, though I've only tested it on
0.9.5a.  The patch uses CRYPTO_LOCK_RSA, but perhaps it should be rewritten
to use the dyn_locks added in 0.9.5b.  In order to not add overhead to the
non-initialisation run through the function, I test _method_mod_[npq], then
lock if it is NULL, then test again (since after aquiring the lock
_method_mod_[npq] may have been set).
 openssl-0.9.6-rsa-mt.diff 

 openssl-0.9.6-rsa-mt.diff


RE: RSA encryption. How to use xxx_PADDING.

2000-11-16 Thread Reddie, Steven

Sounds a little confusing.  If there's no easy way to tell at decryption
time which blocks use which padding type then you've got a problem.  If you
don't mind potentially having an extra block, perhaps you should use
PKCS1_PADDING for all blocks (ie. encrypt the first "key size - 11 bytes",
then the next, ...).  At least this way you know that you always use
PKCS1_PADDING.

Also, you can't just blindly encrypt a block of data that is the same size
as the key.  The data must be less than the modulus, not just in size but in
value.  For example you cannot encrypt a block when the highest significant
byte of your modulus is 0x53 and the highest significant byte of your data
is 0x54.  For this reason, it's always wise to use padding, as well as for
the increased security.  If you really must use no padding, then grabbing
the number of bytes equal to the keylength is not good enough, you will have
to then compare the BIGNUM values and drop a byte of data if it's bigger
than the modulus.

Just use padding.

 -Original Message-
 From: Fedor Utenkov [SMTP:[EMAIL PROTECTED]]
 Sent: Thursday, November 16, 2000 7:02 PM
 To:   [EMAIL PROTECTED]
 Subject:  RSA encryption. How to use xxx_PADDING.
 
 Hello all,
 
   I'm  new  to  encryption. I'm using an OpenSSL 0.9.6 to encrypt data
   using  RSA.  The  data  length  is  about  4  times  longer  against
   RSA_size()  of my key. To encrypt all data I split it to blocks with
   length  equal  to  key  size and encrypt one by one w/o PADDING. The
   last  block,  if  its  length less than key size should be encrypted
   with  XXX_PADDING.  But, for example, PKCS1_PADDING needs to have at
   least  11  bytes  difference between data and key lengths. So if for
   the  last  data  block  length difference less than 11 bytes, I must
   split   this block again to have 2 blocks with difference greater 11
   to  encrypt all data. Finally on the decryption step I don't know if
   there  are  2  or  1  PADDED  blocks at the end of data. Currently I
   decrypt  data  till the two blocks remaining. Then try decrypt block
   before  last  with  PADDING  and if error occurs (possible block was
   encrypted  without PADDING) try to decrypt it w/o PADDING (typically
   decrypts ok). The same situation with the last block.
 
   So I have a question. Is my schema write or it is another more clear
   way to use RSA cipher with OpenSSL library ?
 
 Best regards,
 Fedor Utenkov
 ABG Card Technology
 mailto:[EMAIL PROTECTED]
 
 __
 OpenSSL Project http://www.openssl.org
 Development Mailing List   [EMAIL PROTECTED]
 Automated List Manager   [EMAIL PROTECTED]
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



RE: openssl on windows CE environment?

2000-10-27 Thread Reddie, Steven

Kidding about doing it at all, or about Windows CE not having a C runtime
library?

I am doing this, though not putting much effort into it because it's just to
get a small app of mine working.  I've got libeay32.dll and the tests built,
and have verified that rsa_test.exe works.  I'm not all that interested in
the SSL stuff at the moment, but I'll get to that later.  I'm using a Compaq
iPaq PocketPC.  If you ask whether I'm kidding due to these devices being
toys, well the iPaq has a 206MHz StrongARM processor and 32MB RAM (you can
play full colour MPEG movies on these things).  The rsa_test completes in
the blink of an eye.

As far as the C runtime goes, for anyone who's interested, they do supply
many definitions in the header files though many of the functions do nothing
(there's no console, stdin, stdout, time, open, errno, and the list goes
on).  And for functions that they do supply, parameters and return types
often have different types to what's expected.  I've been writting a library
to fill the gaps, providing the missing functionality, including a console
window.  I may not have anything by next week as I first though, but soon.

Steven

 -Original Message-
 From: Ben Laurie [SMTP:[EMAIL PROTECTED]]
 Sent: Friday, October 27, 2000 5:12 PM
 To:   [EMAIL PROTECTED]
 Subject:  Re: openssl on windows CE environment?
 
 "Reddie, Steven" wrote:
  
  I've been doing this outside of work.  I'll post some patches soon
 (within
  the next week if I get the time).  The biggest problem with Windows CE
 is
  that there's no C runtime library,
 
 You have to be kidding!
 
 Cheers,
 
 Ben.
 
 --
 http://www.apache-ssl.org/ben.html
 
 "There is no limit to what a man can do or how far he can go if he
 doesn't mind who gets the credit."
 
 Robert Woodruff
 __
 OpenSSL Project http://www.openssl.org
 Development Mailing List   [EMAIL PROTECTED]
 Automated List Manager   [EMAIL PROTECTED]
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



RE: openssl on windows CE environment?

2000-10-22 Thread Reddie, Steven

I've been doing this outside of work.  I'll post some patches soon (within
the next week if I get the time).  The biggest problem with Windows CE is
that there's no C runtime library, and it doesn't support the full Win32
API.

Steven

(Note: contact me on this list or my external email address,
[EMAIL PROTECTED], if you have any further questions)

 -Original Message-
 From: [EMAIL PROTECTED] [SMTP:[EMAIL PROTECTED]]
 Sent: Friday, October 20, 2000 10:02 PM
 To:   [EMAIL PROTECTED]
 Subject:  openssl on windows CE environment?
 
 Hi.
  
 Is there anybody who have used openssl on WinCE environment?
 It's too hard for me to port openssl on WinCE
 somebody help me ..
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



RE: RSA_private_decrypt produces garbage, sometimes

2000-10-15 Thread Reddie, Steven

Not all values that fit into a 128-byte buffer can be encrypted/decrypted.
RSA doesn't treat the message merely as a buffer, but rather as a big
number.  The integer value of the message must be less than the integer
value of the modulus.  This is why PKCS#1 padding uses leading values of
0x00, 0x01, and 0x02; to force the message to be less than the modulus.

Padding is necessary for the resulting encrypted block to be less prone to
attack.  If you really don't want to use padding, perhaps you should limit
the message length to 127 bytes and prepend a 0x00.
--
Steven Reddie [EMAIL PROTECTED]
Senior Software Engineer
OpenDirectory Lab, Computer Associates Pty Ltd (Australia)

 -Original Message-
 From: Noam Ben-Yochanan [SMTP:[EMAIL PROTECTED]]
 Sent: Monday, October 16, 2000 6:00 AM
 To:   [EMAIL PROTECTED]
 Subject:  RSA_private_decrypt produces garbage, sometimes
 
 Hi all,
 
   I wrote a program which generates an RSA key pair using
 RSA_generate_key(), then I store the private and public keys in buffers
 using i2d_RSAPublicKey() and i2d_RSAPrivateKey(). I later use the
 d2i_RSAPublicKey()/d2i_RSAPrivateKey() to reproduce the keys for
 encryption and decryption - using
 RSA_private_encrypt()/RSA_public_decrypt and
 RSA_public_encrypt()/RSA_private_decrypt() - with RSA_NO_PADDING to
 encrypt/decrypt blocks of 128 bytes with 1024 bit keys.
 
   This works fine, except sometimes it doesn't. Given the same key, 2
 buffers which are the same except for the first byte will produce
 completely different results on decryption. One will produce  a perfect
 cleartext and the other will produce complete garbage. There are usually
 value ranges (per key) for the 1st byte for which the decryption will
 work perfectly, and the rest of the values give garbage.
 
 Does anyone have an idea what I could be doing wrong?
 
 Thanks in advance,
 
 Noam
 --
 Noam Ben-Yochanan
 Technologies Team Leader
 Whale Communications Ltd.
 
 Phone:  +972-3-9031101 (Ext 319)
 Fax: +972-3-9031102
 E-mail: [EMAIL PROTECTED]
 http://www.whale-com.com
 
 
 __
 OpenSSL Project http://www.openssl.org
 Development Mailing List   [EMAIL PROTECTED]
 Automated List Manager   [EMAIL PROTECTED]
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



RE: [BUG?] BIO_sock_should_retry() on Win32

2000-10-09 Thread Reddie, Steven

I've determined the exact cause of my trouble.  It is a result of using
OpenSSL in conjunction with the pthreads-win32 library, and implementing
id_callback as a call to pthread_self, and may be a gotcha for other Win32
developers.

The pthreads-win32 library implements pthread_self, and other functions,
with a call to the Win32 function TlsGetValue.  The Win32 documentation for
this function states:

"Win32 functions that return indications of failure call
SetLastError when they fail. They generally do not call SetLastError when
they succeed. The TlsGetValue function is an exception to this general rule.
The TlsGetValue function calls SetLastError to clear a thread's last error
when it succeeds."

What is occuring in my particular case is that accept returns
WSAEWOULDBLOCK, so BIO_accept calls SYSerr to log an error.  Since logging
an error results in a call to the id_callback for storing the thread id with
the error message, the act of logging an error in this case results in the
WSALastError being cleared, and further processing, such as determining if
the operation should be retried, fails.

Regards,

Steven
--
Steven Reddie [EMAIL PROTECTED]
Senior Software Engineer
OpenDirectory Lab, Computer Associates Pty Ltd (Australia)

__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



[BUG?] BIO_sock_should_retry() on Win32

2000-10-05 Thread Reddie, Steven

[Firstly, I'm working with 0.9.5a, but the relevant 0.9.6 source seems to be
unchanged.]

This may be a bigger problem than just my specific case, but here is what
I've found:

We are using BIO_do_handshake() to accept socket connections, which results
in a call to BIO_accept().  Calling BIO_accept() on a non-blocking socket
with no connections pending results in a fatal error on Win32, but not on
other platforms.  The reason for this difference seems to be in the
processing of BIO_sock_should_retry().  This function contains:

#if defined(WINDOWS)  0 /* more microsoft stupidity? perhaps not? Ben
4/1/99 */
if ((i == -1)  (err == 0))
return(1);
#endif

In the case that I'm witnessing, the above if-statement evaluates to true.
So, if the " 0" in the #ifdef is removed, the Win32 behaviour is the same
as on other platforms.  Should the " 0" be removed?

However, the correct solution may be more specific.  At the time that accept
fails, WSAGetLastError() returns WSAEWOULDBLOCK.  By the time that
BIO_sock_should_retry() is called, WSAGetLastError() returns 0, which I
guess is why the above code was added in the first place.  Obviously some
Win32 call, or socket call, between the accept, and the
BIO_sock_should_retry() is resetting the error code.

Any suggestions for the correct way to rectify this situation?

Steven

--
Steven Reddie [EMAIL PROTECTED]
Senior Software Engineer
OpenDirectory Lab, Computer Associates Pty Ltd (Australia)

__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



[PATCH] Multithreaded race conditions in RSA crypto (rsa_eay.c)

2000-10-03 Thread Reddie, Steven

I've come across four race conditions in the following functions in
rsa_eay.c:
RSA_public_encrypt
RSA_public_decrypt
RSA_eay_mod_exp (x2)

These can cause unexpected failure of the RSA_eay_ encryption/decryption
functions for both public and private key operations.  The problem occurs
when more than one thread simultaneously uses the same RSA key (more
specifically, when multiple threads simultaneously initialise
rsa-_method_mod_[npq] when RSA_FLAG_CACHE_PUBLIC is set).  The problems are
only easily reproduceable on a multi-processor machine, although they can
also occur on a single processor machine.

I've attached a patch for OpenSSL 0.9.6, though I've only tested it on
0.9.5a.  The patch uses CRYPTO_LOCK_RSA, but perhaps it should be rewritten
to use the dyn_locks added in 0.9.5b.  In order to not add overhead to the
non-initialisation run through the function, I test _method_mod_[npq], then
lock if it is NULL, then test again (since after aquiring the lock
_method_mod_[npq] may have been set).

Regards,

Steven

--
Steven Reddie [EMAIL PROTECTED]
Senior Software Engineer
OpenDirectory Lab, Computer Associates Pty Ltd (Australia)

 openssl-0.9.6-rsa-mt.diff 

 openssl-0.9.6-rsa-mt.diff


RE: extern private key, smart cards, RSA_METHOD_FLAG_NO_CHECK

2000-02-25 Thread Reddie, Steven

I create my own RSA_METHOD structure which contains pointers to my RSA
public/private encrypt/decrypt functions.  It also contains a flags member
which is where I set RSA_METHOD_FLAG_NO_CHECK.  I have the private key
stored on the Hardware Security Module (HSM) and the certificate is
available to the application.  I use the Subject of the certificate to find
the private key with a matching Subject on the HSM.  When loading a key from
the HSM (ie. getting it's handle for later use) I call RSA_new_method and
pass in a pointer to my RSA_METHOD structure.  RSA_new_method copies the
flags from RSA_METHOD into the new RSA structure (key).  Another important
thing that I do is get the public modulus from the HSM key, convert it into
a BIGNUM using BN_bin2bn and then store it in RSA-n.  This is needed by
OpenSSL crypto code when determining the key length.  The _hack_ that I use
to associate the RSA key with the HSM key handle is to store the HSM key
handle in RSA-p (the private modulus).  Since my public/private
encrypt/decrypt functions are called for operations on this RSA key (via my
RSA_METHOD structure) my code knows what RSA-p really means and everything
is happy.

I'm currently chasing up what is required of me to submit code due to the
relaxed US crypto export laws.  I'll probably post some code to this list
later today.  My code is not diffs to OpenSSL, and simply needs to be linked
into your application.

Regards,

Steven
--
Steven Reddie [EMAIL PROTECTED]
Senior Software Developer
OpenDirectory Lab, Computer Associates Pty Ltd (Australia)
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]



RE: Current state of PKCS#11 support in OpenSSL?

2000-02-24 Thread Reddie, Steven

Greg, I'm not sure about the state of PKCS#11 support in relation to the
latest snapshot, however I can give you some answers in relation to the
latest release, OpenSSL 0.9.4.

Firstly, I work for a US company and I am unsure about the current state of
the export restrictions, and therefore whether or not I can provide source
code.  Can someone who has kept up-to-date with this please fill me in?  The
code that I have written requires no changes to the OpenSSL code so perhaps
it is possible for me to give you the additional source.

What I have written is only for RSA operations.  Looking at the OpenSSL
source it appears that supporting anything else would require changes to
OpenSSL.  The RSA-side of OpenSSL provides an easy way to hook-in via the
RSA_METHOD structure and the RSA_new_method function (similar hooks for DSA
et al would make extending this so much simpler).  I have written code to
allow a key to be loaded via PKCS#11 and then to be used for public/private
encrypt/decrypt operations.  Sign/Verify operations are performed by OpenSSL
by doing the digest (hash) in software and then calling
private-encrypt/public-decrypt.  It took me a while to figure things out,
but the final result is some really simple code.  Here is a general
overview:

Create your own RSA_METHOD with pointers to your own public/private
encrypt/decrypt functions, and setting flags to RSA_METHOD_FLAG_NO_CHECK.

PKCS11_get_key():
* get a handle to the PKCS#11 key (by whatever means is appropriate
to your application)
* create an RSA key (RSA structure) by calling RSA_new_method and
passing
   in pointer to your RSA_METHOD structure
* get the public modulus from the PKCS#11 key, use BN_bin2bn and
store it in RSA-n
  (this is necessary for OpenSSL code to determine the size of the
key)
* [***HACK***] set RSA-p to the handle of the PKCS#11 key
* Set the RSA_FLAG_EXT_PKEY bit in RSA-flags
* create an EVP_PKEY, set the type to EVP_PKEY_RSA, and set pkey.ptr
to point to your RSA structure
* return the EVP_PKEY

public/private encrypt/decrypt functions (callbacks in your RSA_METHOD
structure):
* get the PKCS#11 key handle from RSA-p
* use mechanism CKM_RSA_PKCS
* public encrypt is performed using C_Encrypt
* public decrypt is performed using C_VerifyRecover (note 1)
* private encrypt is performed using C_Sign (note 1)
* private decrypt is performed using C_Decrypt
* NOTE 1: Thanks to Dr Stephen Henson for explaining this to me.

The reason that I allow OpenSSL to do the digest and only do the
encrypt/decrypt via PKCS#11 is that SSL requires an encrypt of a
concatenated MD5 and SHA1 buffer which PKCS#11 does not allow via C_Sign, so
I chose to not do Sign/Verify as an atomic PKCS#11 operation.

I hope this helps.

Steven
--
Steven Reddie [EMAIL PROTECTED]
Senior Software Developer
OpenDirectory Lab, Computer Associates Pty Ltd (Australia)
__
OpenSSL Project http://www.openssl.org
Development Mailing List   [EMAIL PROTECTED]
Automated List Manager   [EMAIL PROTECTED]