common.c revision 7c478bd95313f5f23a4c958a745db2134aa03244
/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License, Version 1.0 only
* (the "License"). You may not use this file except in compliance
* with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* See the License for the specific language governing permissions
* and limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
* If applicable, add the following below this CDDL HEADER, with the
* fields enclosed by brackets "[]" replaced with your own identifying
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
/*
* Copyright 2004 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
#pragma ident "%Z%%M% %I% %E% SMI"
/*
* This file contains the functions that are shared among
* the various services this tool will ultimately provide.
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include <cryptoutil.h>
#include <security/cryptoki.h>
#include "common.h"
/* Global PKCS#11 error value. */
int pk11_errno = 0;
/*
* Gets passphrase from user, caller needs to free when done.
*/
int
{
char *phrase;
/* Prompt user for password. */
return (-1);
/* Duplicate passphrase in separate chunk of memory */
return (-1);
}
/*
* Perform any PKCS#11 setup here. Right now, this tool only
* requires C_Initialize(). Additional features planned for
* this tool will require more initialization and state info
* added here.
*/
int
init_pk11(void)
{
int rv;
cryptodebug("inside init_pk11");
/* Initialize PKCS#11 library. */
pk11_errno = rv;
return (PK_ERR_PK11INIT);
}
return (PK_ERR_NONE);
}
/*
* memcmp_pad_max() is a specialized version of memcmp() which
* compares two pieces of data up to a maximum length. If the
* the two data match up the maximum length, they are considered
* matching. Trailing blanks do not cause the match to fail if
* one of the data is shorted.
*
* Examples of matches:
* "one" |
* "one " |
* ^maximum length
*
* "Number One | X" (X is beyond maximum length)
* "Number One " |
* ^maximum length
*
* Examples of mismatches:
* " one"
* "one"
*
* "Number One X|"
* "Number One |"
* ^maximum length
*/
static int
{
char *marker;
/* No point in comparing anything beyond max_sz */
/* Find shorter of the two data. */
} else { /* d1_len > d2_len */
}
/* Have a match in the shortest length of data? */
/* CONSTCOND */
return (!0);
/* If the rest of longer data is nulls or blanks, call it a match. */
/* CONSTCOND */
return (!0);
return (0);
}
/*
* Locate a token slot whose token matches the label, manufacturer
* ID, and serial number given. Token label must be specified,
* manufacturer ID and serial number are optional.
*/
int
{
CK_ULONG slot_count = 0;
int rv;
int i;
cryptodebug("inside find_token_slot");
/*
* Get the slot count first because we don't know how many
* slots there are and how many of those slots even have tokens.
* Don't specify an arbitrary buffer size for the slot list;
* it may be too small (see section 11.5 of PKCS#11 spec).
* Also select only those slots that have tokens in them,
* because this tool has no need to know about empty slots.
*/
pk11_errno = rv;
return (PK_ERR_PK11SLOTS);
}
if (slot_count == 0)
return (PK_ERR_NOSLOTS); /* with tokens in them */
/* Allocate space for the slot list and get it. */
if ((slot_list =
return (PK_ERR_NOMEMORY);
/* NOTE: can slot_count change from previous call??? */
pk11_errno = rv;
return (PK_ERR_PK11SLOTS);
}
/* Search for the token. */
for (i = 0; i < slot_count; i++) {
if ((rv =
cryptodebug("slot %d has no token", i);
continue;
}
max_sz) == 0)
cryptodebug("slot %d:", i);
cryptodebug("\tCKF_USER_PIN_INITIALIZED = %s",
"true" : "false");
cryptodebug("\tCKF_USER_PIN_TO_BE_CHANGED = %s",
"true" : "false");
if (manuf_id) {
}
if (serial_no) {
}
if (tok_match &&
break; /* found it! */
}
if (i == slot_count) {
return (PK_ERR_NOTFOUND);
}
cryptodebug("matched token at slot %d", i);
return (PK_ERR_NONE);
}
/*
* Log into the token in given slot and create a session for it.
*/
int
{
int rv;
cryptodebug("inside login_token");
/* Create a read-write session so we can change the PIN. */
pk11_errno = rv;
return (PK_ERR_PK11SESSION);
}
/*
* If the token is newly created, there initial PIN will be "changme",
* and all subsequent PKCS#11 calls will fail with CKR_PIN_EXPIRED,
* but C_Login() will succeed.
*/
pk11_errno = rv;
(void) C_CloseSession(*hdl);
if (rv == CKR_USER_PIN_NOT_INITIALIZED)
return (PK_ERR_CHANGEPIN);
return (PK_ERR_PK11LOGIN);
}
return (PK_ERR_NONE);
}
/*
* Log out of the token and close the session.
*/
void
{
cryptodebug("inside logout_token");
if (hdl) {
(void) C_CloseSession(hdl);
}
(void) C_Finalize(NULL);
}