#include "ssl.h"
#include "sslalloc.h"
#include "sslDebug.h"
#include "sslBER.h"
#include <Security/asn-incl.h>
#include <Security/sm_vdatypes.h>
#include <Security/asn-type.h>
#include <Security/pkcs1oids.h>
#include <Security/cdsaUtils.h>
#include <string.h>
#include <Security/cssmdata.h>
static void snaccIntToData(
const BigIntegerStr &snaccInt,
SSLBuffer *outData) {
const char *scp = snaccInt;
uint8 *cp = (uint8 *)scp;
uint32 len = snaccInt.Len();
if (*cp == 0x00) {
cp++;
len--;
}
memmove(outData->data, cp, len);
outData->length = len;
}
static void dataToSnaccInt(
const SSLBuffer *inData,
BigIntegerStr &snaccInt)
{
uint8 *cp;
int msbIsSet = 0;
if (inData->data[0] & 0x80) {
cp = (uint8 *)malloc(inData->length + 1);
*cp = 0;
memmove(cp+1, inData->data, inData->length);
msbIsSet = 1;
}
else {
cp = inData->data;
}
snaccInt.Set(reinterpret_cast<const char *>(cp),
inData->length + msbIsSet);
if(msbIsSet) {
free(cp);
}
}
SSLErr sslDecodeRsaBlob(
const SSLBuffer *blob,
SSLBuffer *modulus,
SSLBuffer *exponent)
{
SSLErr srtn;
CASSERT(blob != NULL);
CASSERT(modulus != NULL);
CASSERT(exponent != NULL);
RSAPublicKey snaccPubKey;
CssmData cssmBlob(blob->data, blob->length);
try {
SC_decodeAsnObj(cssmBlob, snaccPubKey);
}
catch(...) {
return SSLBadCert;
}
srtn = SSLAllocBuffer(modulus, snaccPubKey.modulus.Len(), NULL);
if(srtn) {
return srtn;
}
snaccIntToData(snaccPubKey.modulus, modulus);
srtn = SSLAllocBuffer(exponent, snaccPubKey.publicExponent.Len(),
NULL);
if(srtn) {
return srtn;
}
snaccIntToData(snaccPubKey.publicExponent, exponent);
return SSLNoErr;
}
SSLErr sslEncodeRsaBlob(
const SSLBuffer *modulus,
const SSLBuffer *exponent,
SSLBuffer *blob)
{
CASSERT((modulus != NULL) && (exponent != NULL));
blob->data = NULL;
blob->length = 0;
RSAPublicKey snaccPubKey;
dataToSnaccInt(modulus, snaccPubKey.modulus);
dataToSnaccInt(exponent, snaccPubKey.publicExponent);
size_t maxSize = 2 * (modulus->length + exponent->length);
CssmAllocator &alloc = CssmAllocator::standard();
CssmAutoData cblob(alloc);
try {
SC_encodeAsnObj(snaccPubKey, cblob, maxSize);
}
catch(...) {
return SSLMemoryErr;
}
SSLErr srtn = SSLAllocBuffer(blob, cblob.length(), NULL);
if(srtn) {
return srtn;
}
memmove(blob->data, cblob.data(), cblob.length());
return SSLNoErr;
}