Implementid basic signing functionality.

git-svn-id: https://www.opensc-project.org/svnp/opensc/trunk@24 c6295689-39f2-0310-b995-f0e70906c6a9
This commit is contained in:
fabled 2001-10-22 21:09:17 +00:00
parent a1af155018
commit 2f086f5261
3 changed files with 157 additions and 15 deletions

View File

@ -1,5 +1,24 @@
#include <stdio.h>
#include <ctype.h>
#include "sc-pkcs11.h"
static void hex_dump(const unsigned char *buf, int count)
{
int i;
for (i = 0; i < count; i++) {
unsigned char c = buf[i];
int printch = 0;
if (!isalnum(c) && !ispunct(c) && !isspace(c))
printch = 0;
if (printch)
LOG("%02X%c ", c, c);
else
LOG("%02X ", c);
}
LOG("\n");
}
CK_RV C_DigestInit(CK_SESSION_HANDLE hSession, /* the session's handle */
CK_MECHANISM_PTR pMechanism) /* the digesting mechanism */
{
@ -44,8 +63,41 @@ CK_RV C_SignInit(CK_SESSION_HANDLE hSession, /* the session's handle */
CK_MECHANISM_PTR pMechanism, /* the signature mechanism */
CK_OBJECT_HANDLE hKey) /* handle of the signature key */
{
LOG("C_SignInit\n");
return CKR_FUNCTION_NOT_SUPPORTED;
struct pkcs11_slot *slt;
struct pkcs11_session *ses;
struct pkcs11_object *object;
LOG("C_SignInit(%d, {%d, 0x%x, %d}, %d)\n",
hSession,
pMechanism->mechanism, pMechanism->pParameter, pMechanism->ulParameterLen,
hKey);
if (hSession < 1 || hSession > PKCS11_MAX_SESSIONS || session[hSession] == NULL)
return CKR_SESSION_HANDLE_INVALID;
ses = session[hSession];
slt = &slot[ses->slot];
if (hKey < 1 || hKey > slt->num_objects)
return CKR_OBJECT_HANDLE_INVALID;
object = slt->object[hKey];
if (object->object_type != CKO_PRIVATE_KEY)
return CKR_OBJECT_HANDLE_INVALID;
switch (pMechanism->mechanism) {
case CKM_RSA_PKCS:
// Signing according to PKCS#1 standard
LOG("CKM_RSA_PKCS mechanism requested\n");
ses->sign.algorithm_ref = 0x02;
break;
default:
LOG("Requested mechanism #d not supported\n", pMechanism->mechanism);
break;
}
LOG("Token id is %d\n", object->token_id);
ses->sign.private_key_id = object->token_id;
return CKR_OK;
}
CK_RV C_Sign(CK_SESSION_HANDLE hSession, /* the session's handle */
@ -54,15 +106,57 @@ CK_RV C_Sign(CK_SESSION_HANDLE hSession, /* the session's handle */
CK_BYTE_PTR pSignature, /* receives the signature */
CK_ULONG_PTR pulSignatureLen) /* receives byte count of signature */
{
LOG("C_Sign\n");
return CKR_FUNCTION_NOT_SUPPORTED;
char signature[1024];
struct sc_pkcs15_card *p15card;
struct sc_security_env senv;
struct pkcs11_session *ses;
int i, c;
LOG("C_Sign(%d, 0x%x, %d, 0x%x, 0x%x)\n",
hSession, pData, ulDataLen, pSignature, pulSignatureLen);
hex_dump(pData, ulDataLen);
if (hSession < 1 || hSession > PKCS11_MAX_SESSIONS || session[hSession] == NULL)
return CKR_SESSION_HANDLE_INVALID;
ses = session[hSession];
p15card = slot[ses->slot].p15card;
senv.signature = 1;
senv.algorithm_ref = ses->sign.algorithm_ref; //0x02;
senv.key_ref = 0;
senv.key_file_id = p15card->prkey_info[ses->sign.private_key_id].file_id;
senv.app_df_path = p15card->file_app.path;
i = sc_set_security_env(p15card->card, &senv);
if (i) {
LOG("Security environment set failed: %s\n", sc_strerror(i));
return CKR_DEVICE_ERROR;
}
c = sc_compute_signature(p15card->card, pData, ulDataLen, signature, sizeof(signature));
if (c < 0) {
LOG("Compute signature failed: (%d) %s\n", c, sc_strerror(c));
return CKR_DEVICE_ERROR;
}
if (*pulSignatureLen < c) {
LOG("Buffer too small, %d < %d\n", *pulSignatureLen, c);
return CKR_BUFFER_TOO_SMALL;
}
LOG("Got signature, %d bytes (buffer was %d)\n", c, *pulSignatureLen);
hex_dump(signature, c);
memcpy(pSignature, signature, c);
*pulSignatureLen = c;
return CKR_OK;
}
CK_RV C_SignUpdate(CK_SESSION_HANDLE hSession, /* the session's handle */
CK_BYTE_PTR pPart, /* the data (digest) to be signed */
CK_ULONG ulPartLen) /* count of bytes to be signed */
{
LOG("C_SignUpdate\n");
LOG("C_SignUpdate(%d, 0x%x, %d)\n",
hSession, pPart, ulPartLen);
return CKR_FUNCTION_NOT_SUPPORTED;
}
@ -70,7 +164,8 @@ CK_RV C_SignFinal(CK_SESSION_HANDLE hSession, /* the session's handle */
CK_BYTE_PTR pSignature, /* receives the signature */
CK_ULONG_PTR pulSignatureLen) /* receives byte count of signature */
{
LOG("C_SignFinal\n");
LOG("C_SignFinal(%d, 0x%x, %d)\n",
hSession, pSignature, pulSignatureLen);
return CKR_FUNCTION_NOT_SUPPORTED;
}

View File

@ -5,6 +5,7 @@
#include "pkcs11/pkcs11.h"
#include "../sc.h"
#include "../sc-pkcs15.h"
#define PKCS11_MAX_SLOTS 4
#define PKCS11_MAX_SESSIONS 8
@ -12,6 +13,7 @@
// Object information
struct pkcs11_object {
int object_type, token_id;
int num_attributes;
CK_ATTRIBUTE_PTR attribute;
};
@ -21,6 +23,11 @@ struct pkcs11_search_context {
int num_matches, position;
CK_OBJECT_HANDLE handles[PKCS11_MAX_OBJECTS];
};
// Signing information
struct pkcs11_sign_context {
int private_key_id;
int algorithm_ref;
};
// Per session information; "context"
struct pkcs11_session {
@ -31,6 +38,7 @@ struct pkcs11_session {
CK_VOID_PTR notify_parameter;
struct pkcs11_search_context search;
struct pkcs11_sign_context sign;
//...
};

View File

@ -2,6 +2,30 @@
#include <malloc.h>
#include "sc-pkcs11.h"
static CK_BYTE modulus[] =
#if 0
"\x00\xc7\x50\xbb\x9e\xf7\x43\x18\x7e\x8d\xb5\xe3\xa1\x6e\x4c"
"\x8c\x0f\x0f\xc7\x9a\xce\xad\x05\x1b\x16\xf0\x30\x25\xdb\x1f"
"\xbd\xf3\x68\x76\x29\xee\x75\x97\xba\x20\x1a\x48\xa8\x55\xa1"
"\x50\x91\x45\x0e\x64\x70\xcd\xda\x52\x0b\x67\x94\x16\x89\x73"
"\x7d\xa1\x7c\x5b\xa9\x29\xd8\xe2\x38\xc8\x24\x73\xaa\xc1\x7a"
"\x99\x6f\x4f\xe9\xa6\xcc\x9e\x02\xd4\xb2\xf1\xf5\xe5\x94\x1f"
"\x30\x70\x6c\x29\xe6\x65\x06\x55\x67\xc5\xa7\x35\x82\x5c\x6d"
"\x4d\xe7\x60\x83\xf4\x0c\xed\xbe\x6b\xb1\xc3\xe4\x55\x99\x7f"
"\x79\x07\x99\x2f\x65\x8b\xe5\x89\xe5";
#else
"\x00\xba\xb3\xc3\x65\xfb\xab\xd3\x4f\xf1\xe8\x72\xb8\xaa\x48"
"\x6a\x82\x31\x43\xc9\x3e\xe6\xff\x6b\xb6\x0e\xa3\x82\xb4\xda"
"\x3f\xed\xa6\x0b\xbc\xf2\xd3\xad\x53\x88\x88\x14\x14\x3f\x2b"
"\x24\x8d\xd7\x3f\x4b\xb3\xe6\xc1\xb9\xb1\x4d\x3a\x10\xc4\x65"
"\xdc\xe2\xa1\x27\xd2\x8f\xb2\x67\x54\x34\x73\x53\xeb\xec\x84"
"\xab\xdd\xc1\x76\xc9\x73\x49\x4c\x7c\x18\x98\xd3\x40\xc4\x1c"
"\xfd\x0d\x6b\xae\xb7\x9f\x44\xc6\x0a\x5a\x89\x91\xb8\x6e\x20"
"\x38\x2b\xff\x42\xf7\xfe\x95\xc0\x1f\xa5\xca\x07\x2e\x4a\xb0"
"\x9c\x07\x60\x02\x61\xe1\x8b\x25\x01";
#endif
void set_attribute(CK_ATTRIBUTE_PTR attr, CK_OBJECT_CLASS oc, void *ptr, int len)
{
attr->type = oc;
@ -10,35 +34,50 @@ void set_attribute(CK_ATTRIBUTE_PTR attr, CK_OBJECT_CLASS oc, void *ptr, int len
attr->ulValueLen = len;
}
int slot_add_object(int id, CK_ATTRIBUTE_PTR object, int num_attrs)
int slot_add_object(int id, int token_id, CK_ATTRIBUTE_PTR object, int num_attrs)
{
struct pkcs11_slot *slt = &slot[id];
int idx;
int idx, i;
if (slt->num_objects >= PKCS11_MAX_OBJECTS)
return CKR_BUFFER_TOO_SMALL;
idx = ++slt->num_objects;
slt->object[idx] = (struct pkcs11_object*) malloc(sizeof(struct pkcs11_object));
slt->object[idx]->object_type = -1;
slt->object[idx]->token_id = token_id;
slt->object[idx]->num_attributes = num_attrs;
slt->object[idx]->attribute = object;
for (i = 0; i < num_attrs; i++) {
if (object[i].type == CKA_CLASS && object[i].ulValueLen == 4) {
slt->object[idx]->object_type = *(int*)object[i].pValue;
break;
}
}
return CKR_OK;
}
int slot_add_private_key_object(int id, struct sc_pkcs15_prkey_info *key)
int slot_add_private_key_object(int id, int token_id, struct sc_pkcs15_prkey_info *key)
{
static CK_OBJECT_CLASS key_class = CKO_PRIVATE_KEY;
CK_ATTRIBUTE_PTR object = (CK_ATTRIBUTE_PTR) malloc(sizeof(CK_ATTRIBUTE) * 3);
static CK_BBOOL btrue = 1;
static CK_KEY_TYPE rsakey = CKK_RSA;
CK_ATTRIBUTE_PTR object = (CK_ATTRIBUTE_PTR) malloc(sizeof(CK_ATTRIBUTE) * 6);
set_attribute(&object[0], CKA_CLASS, &key_class, sizeof(key_class));
set_attribute(&object[1], CKA_LABEL, key->com_attr.label, strlen(key->com_attr.label));
set_attribute(&object[2], CKA_ID, key->id.value, key->id.len);
set_attribute(&object[3], CKA_TOKEN, &btrue, sizeof(btrue));
set_attribute(&object[4], CKA_KEY_TYPE, &rsakey, sizeof(rsakey));
set_attribute(&object[5], CKA_MODULUS, modulus, sizeof(modulus)-1);
return slot_add_object(id, object, 3);
return slot_add_object(id, token_id, object, 6);
}
int slot_add_certificate_object(int id, struct sc_pkcs15_cert_info *cert,
int slot_add_certificate_object(int id, int token_id,
struct sc_pkcs15_cert_info *cert,
u8 *x509data, int x509length)
{
static CK_OBJECT_CLASS cert_class = CKO_CERTIFICATE;
@ -49,7 +88,7 @@ int slot_add_certificate_object(int id, struct sc_pkcs15_cert_info *cert,
set_attribute(&object[2], CKA_ID, cert->id.value, cert->id.len);
set_attribute(&object[3], CKA_VALUE, x509data, x509length);
return slot_add_object(id, object, 4);
return slot_add_object(id, token_id, object, 4);
}
int slot_connect(int id)
@ -96,7 +135,7 @@ int slot_connect(int id)
return len;
LOG("Adding '%s' certificate object.\n", p15card->cert_info[c].com_attr.label);
slot_add_certificate_object(id, &p15card->cert_info[c],
slot_add_certificate_object(id, c, &p15card->cert_info[c],
buf, len);
}
@ -107,7 +146,7 @@ int slot_connect(int id)
LOG("Found total of %d private keys.\n", r);
for (c = 0; c < r; c++) {
LOG("Adding '%s' private key object.\n", p15card->prkey_info[c].com_attr.label);
slot_add_private_key_object(id, &p15card->prkey_info[c]);
slot_add_private_key_object(id, c, &p15card->prkey_info[c]);
}
return CKR_OK;