blob: e7368dc4e7fcbb6284ae96ad1e60604cb166fcf1 [file] [log] [blame]
/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License (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
* or http://www.opensolaris.org/os/licensing.
* 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 2006 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
* Copyright 2018, Joyent, Inc.
*/
#include <cryptoutil.h>
#include <strings.h>
#include <stdio.h>
#include <tzfile.h>
#include <sys/crypto/common.h>
/*
* In order to fit everything on one line, the 'CRYPTO_' prefix
* has been dropped from the KCF #defines, e.g.
* CRYPTO_SUCCESS becomes SUCCESS.
*/
static CK_RV error_number_table[CRYPTO_LAST_ERROR + 1] = {
CKR_OK, /* SUCCESS */
CKR_CANCEL, /* CANCEL */
CKR_HOST_MEMORY, /* HOST_MEMORY */
CKR_GENERAL_ERROR, /* GENERAL_ERROR */
CKR_FUNCTION_FAILED, /* FAILED */
CKR_ARGUMENTS_BAD, /* ARGUMENTS_BAD */
CKR_ATTRIBUTE_READ_ONLY, /* ATTRIBUTE_READ_ONLY */
CKR_ATTRIBUTE_SENSITIVE, /* ATTRIBUTE_SENSITIVE */
CKR_ATTRIBUTE_TYPE_INVALID, /* ATTRIBUTE_TYPE_INVALID */
CKR_ATTRIBUTE_VALUE_INVALID, /* ATTRIBUTE_VALUE_INVALID */
CKR_FUNCTION_FAILED, /* CANCELED */
CKR_DATA_INVALID, /* DATA_INVALID */
CKR_DATA_LEN_RANGE, /* DATA_LEN_RANGE */
CKR_DEVICE_ERROR, /* DEVICE_ERROR */
CKR_DEVICE_MEMORY, /* DEVICE_MEMORY */
CKR_DEVICE_REMOVED, /* DEVICE_REMOVED */
CKR_ENCRYPTED_DATA_INVALID, /* ENCRYPTED_DATA_INVALID */
CKR_ENCRYPTED_DATA_LEN_RANGE, /* ENCRYPTED_DATA_LEN_RANGE */
CKR_KEY_HANDLE_INVALID, /* KEY_HANDLE_INVALID */
CKR_KEY_SIZE_RANGE, /* KEY_SIZE_RANGE */
CKR_KEY_TYPE_INCONSISTENT, /* KEY_TYPE_INCONSISTENT */
CKR_KEY_NOT_NEEDED, /* KEY_NOT_NEEDED */
CKR_KEY_CHANGED, /* KEY_CHANGED */
CKR_KEY_NEEDED, /* KEY_NEEDED */
CKR_KEY_INDIGESTIBLE, /* KEY_INDIGESTIBLE */
CKR_KEY_FUNCTION_NOT_PERMITTED, /* KEY_FUNCTION_NOT_PERMITTED */
CKR_KEY_NOT_WRAPPABLE, /* KEY_NOT_WRAPPABLE */
CKR_KEY_UNEXTRACTABLE, /* KEY_UNEXTRACTABLE */
CKR_MECHANISM_INVALID, /* MECHANISM_INVALID */
CKR_MECHANISM_PARAM_INVALID, /* MECHANISM_PARAM_INVALID */
CKR_OBJECT_HANDLE_INVALID, /* OBJECT_HANDLE_INVALID */
CKR_OPERATION_ACTIVE, /* OPERATION_ACTIVE */
CKR_OPERATION_NOT_INITIALIZED, /* OPERATION_NOT_INITIALIZED */
CKR_PIN_INCORRECT, /* PIN_INCORRECT */
CKR_PIN_INVALID, /* PIN_INVALID */
CKR_PIN_LEN_RANGE, /* PIN_LEN_RANGE */
CKR_PIN_EXPIRED, /* PIN_EXPIRED */
CKR_PIN_LOCKED, /* PIN_LOCKED */
CKR_SESSION_CLOSED, /* SESSION_CLOSED */
CKR_SESSION_COUNT, /* SESSION_COUNT */
CKR_SESSION_HANDLE_INVALID, /* SESSION_HANDLE_INVALID */
CKR_SESSION_READ_ONLY, /* SESSION_READ_ONLY */
CKR_SESSION_EXISTS, /* SESSION_EXISTS */
CKR_SESSION_READ_ONLY_EXISTS, /* SESSION_READ_ONLY_EXISTS */
CKR_SESSION_READ_WRITE_SO_EXISTS, /* SESSION_READ_WRITE_SO_EXISTS */
CKR_SIGNATURE_INVALID, /* SIGNATURE_INVALID */
CKR_SIGNATURE_LEN_RANGE, /* SIGNATURE_LEN_RANGE */
CKR_TEMPLATE_INCOMPLETE, /* TEMPLATE_INCOMPLETE */
CKR_TEMPLATE_INCONSISTENT, /* TEMPLATE_INCONSISTENT */
CKR_UNWRAPPING_KEY_HANDLE_INVALID, /* UNWRAPPING_KEY_HANDLE_INVALID */
CKR_UNWRAPPING_KEY_SIZE_RANGE, /* UNWRAPPING_KEY_SIZE_RANGE */
CKR_UNWRAPPING_KEY_TYPE_INCONSISTENT, /* UNWRAPPING_KEY_TYPE_INCONSISTENT */
CKR_USER_ALREADY_LOGGED_IN, /* USER_ALREADY_LOGGED_IN */
CKR_USER_NOT_LOGGED_IN, /* USER_NOT_LOGGED_IN */
CKR_USER_PIN_NOT_INITIALIZED, /* USER_PIN_NOT_INITIALIZED */
CKR_USER_TYPE_INVALID, /* USER_TYPE_INVALID */
CKR_USER_ANOTHER_ALREADY_LOGGED_IN, /* USER_ANOTHER_ALREADY_LOGGED_IN */
CKR_USER_TOO_MANY_TYPES, /* USER_TOO_MANY_TYPES */
CKR_WRAPPED_KEY_INVALID, /* WRAPPED_KEY_INVALID */
CKR_WRAPPED_KEY_LEN_RANGE, /* WRAPPED_KEY_LEN_RANGE */
CKR_WRAPPING_KEY_HANDLE_INVALID, /* WRAPPING_KEY_HANDLE_INVALID */
CKR_WRAPPING_KEY_SIZE_RANGE, /* WRAPPING_KEY_SIZE_RANGE */
CKR_WRAPPING_KEY_TYPE_INCONSISTENT, /* WRAPPING_KEY_TYPE_INCONSISTENT */
CKR_RANDOM_SEED_NOT_SUPPORTED, /* RANDOM_SEED_NOT_SUPPORTED */
CKR_RANDOM_NO_RNG, /* RANDOM_NO_RNG */
CKR_DOMAIN_PARAMS_INVALID, /* DOMAIN_PARAMS_INVALID */
CKR_BUFFER_TOO_SMALL, /* BUFFER_TOO_SMALL */
CKR_INFORMATION_SENSITIVE, /* INFORMATION_SENSITIVE */
CKR_FUNCTION_NOT_SUPPORTED, /* NOT_SUPPORTED */
CKR_GENERAL_ERROR, /* QUEUED */
CKR_GENERAL_ERROR, /* BUFFER_TOO_BIG */
CKR_OPERATION_NOT_INITIALIZED, /* INVALID_CONTEXT */
CKR_GENERAL_ERROR, /* INVALID_MAC */
CKR_GENERAL_ERROR, /* MECH_NOT_SUPPORTED */
CKR_GENERAL_ERROR, /* INCONSISTENT_ATTRIBUTE */
CKR_GENERAL_ERROR, /* NO_PERMISSION */
CKR_SLOT_ID_INVALID, /* INVALID_PROVIDER_ID */
CKR_GENERAL_ERROR, /* VERSION_MISMATCH */
CKR_GENERAL_ERROR, /* BUSY */
CKR_GENERAL_ERROR, /* UNKNOWN_PROVIDER */
CKR_GENERAL_ERROR, /* MODVERIFICATION_FAILED */
CKR_GENERAL_ERROR, /* OLD_CTX_TEMPLATE */
CKR_GENERAL_ERROR, /* WEAK_KEY */
CKR_GENERAL_ERROR /* FIPS140_ERROR */
};
#if CRYPTO_LAST_ERROR != CRYPTO_FIPS140_ERROR
#error "Crypto to PKCS11 error mapping table needs to be updated!"
#endif
/*
* This function returns a fullpath based on the "dir" and "filepath" input
* arugments.
* - If the filepath specified does not start with a "/" and the directory
* is also given, prepend the directory to the filename.
* - If only dir or filepath is given, this function returns a copy of the
* given argument.
* - If the filepath is fully qualified already and the "dir" is also
* given, return NULL to indicate an error.
*/
char *
get_fullpath(char *dir, char *filepath)
{
char *fullpath = NULL;
int pathlen = 0;
int dirlen = 0;
if (filepath != NULL)
pathlen = strlen(filepath);
if (dir != NULL)
dirlen = strlen(dir);
if (pathlen > 0 && dirlen > 0) {
if (filepath[0] != '/') {
int len = pathlen + dirlen + 2;
fullpath = (char *)malloc(len);
if (fullpath != NULL)
(void) snprintf(fullpath, len, "%s/%s",
dir, filepath);
} else {
return (NULL);
}
} else if (pathlen > 0) {
fullpath = (char *)strdup(filepath);
} else if (dirlen > 0) {
fullpath = (char *)strdup(dir);
}
return (fullpath);
}
/*
* This function converts the input string to the value of time
* in seconds.
* - If the input string is NULL, return zero second.
* - The input string needs to be in the form of:
* number-second(s), number-minute(s), number-hour(s) or
* number-day(s).
*/
int
str2lifetime(char *ltimestr, uint32_t *ltime)
{
int num;
char timetok[10];
if (ltimestr == NULL || !strlen(ltimestr)) {
*ltime = 0;
return (0);
}
(void) memset(timetok, 0, sizeof (timetok));
if (sscanf(ltimestr, "%d-%08s", &num, timetok) != 2)
return (-1);
if (!strcasecmp(timetok, "second") ||
!strcasecmp(timetok, "seconds")) {
*ltime = num;
} else if (!strcasecmp(timetok, "minute") ||
!strcasecmp(timetok, "minutes")) {
*ltime = num * SECSPERMIN;
} else if (!strcasecmp(timetok, "day") ||
!strcasecmp(timetok, "days")) {
*ltime = num * SECSPERDAY;
} else if (!strcasecmp(timetok, "hour") ||
!strcasecmp(timetok, "hours")) {
*ltime = num * SECSPERHOUR;
} else {
*ltime = 0;
return (-1);
}
return (0);
}
/*
* Map KCF error codes into PKCS11 error codes.
*/
CK_RV
crypto2pkcs11_error_number(uint_t n)
{
if (n >= sizeof (error_number_table) / sizeof (error_number_table[0]))
return (CKR_GENERAL_ERROR);
return (error_number_table[n]);
}