#include <netinet/in.h>
#include <string.h>
#include <stdlib.h>
#include "key.h"
#include "libcrypto.h"
#include "log.h"
#include "util.h"
#include "x509.h"
void
key_free(int type, int private, void *key)
{
switch (type) {
case ISAKMP_KEY_PASSPHRASE:
free(key);
break;
case ISAKMP_KEY_RSA:
RSA_free(key);
break;
case ISAKMP_KEY_NONE:
default:
log_error("key_free: unknown/unsupportedkey type %d", type);
break;
}
}
void
key_serialize(int type, int private, void *key, u_int8_t **data,
size_t *datalenp)
{
u_int8_t *p;
size_t datalen;
switch (type) {
case ISAKMP_KEY_PASSPHRASE:
*datalenp = strlen((char *)key);
*data = (u_int8_t *)strdup((char *)key);
break;
case ISAKMP_KEY_RSA:
switch (private) {
case ISAKMP_KEYTYPE_PUBLIC:
datalen = i2d_RSAPublicKey((RSA *)key, NULL);
*data = p = malloc(datalen);
if (!p) {
log_error("key_serialize: malloc (%lu) failed",
(unsigned long)datalen);
return;
}
*datalenp = i2d_RSAPublicKey((RSA *) key, &p);
break;
case ISAKMP_KEYTYPE_PRIVATE:
datalen = i2d_RSAPrivateKey((RSA *)key, NULL);
*data = p = malloc(datalen);
if (!p) {
log_error("key_serialize: malloc (%lu) failed",
(unsigned long)datalen);
return;
}
*datalenp = i2d_RSAPrivateKey((RSA *)key, &p);
break;
}
break;
default:
log_error("key_serialize: unknown/unsupported key type %d",
type);
break;
}
}
char *
key_printable(int type, int private, u_int8_t *data, size_t datalen)
{
switch (type) {
case ISAKMP_KEY_PASSPHRASE:
return strdup((char *)data);
case ISAKMP_KEY_RSA:
return raw2hex(data, datalen);
default:
log_error("key_printable: unknown/unsupported key type %d",
type);
return 0;
}
}
void *
key_internalize(int type, int private, u_int8_t *data, size_t datalen)
{
switch (type) {
case ISAKMP_KEY_PASSPHRASE:
return strdup((char *)data);
case ISAKMP_KEY_RSA:
switch (private) {
case ISAKMP_KEYTYPE_PUBLIC:
return d2i_RSAPublicKey(NULL,
(const u_int8_t **)&data, datalen);
case ISAKMP_KEYTYPE_PRIVATE:
return d2i_RSAPrivateKey(NULL,
(const u_int8_t **)&data, datalen);
default:
log_error("key_internalize: not public or private "
"RSA key passed");
return 0;
}
break;
default:
log_error("key_internalize: unknown/unsupported key type %d",
type);
break;
}
return 0;
}
void
key_from_printable(int type, int private, char *key, u_int8_t **data,
u_int32_t *datalenp)
{
u_int32_t datalen;
switch (type) {
case ISAKMP_KEY_PASSPHRASE:
*datalenp = strlen(key);
*data = (u_int8_t *) strdup(key);
break;
case ISAKMP_KEY_RSA:
datalen = (strlen(key) + 1) / 2;
*data = malloc(datalen);
if (!*data) {
log_error("key_from_printable: malloc (%d) failed",
datalen);
*datalenp = 0;
return;
}
if (hex2raw(key, *data, datalen)) {
log_error("key_from_printable: invalid hex key");
free(*data);
*data = NULL;
*datalenp = 0;
return;
}
*datalenp = datalen;
break;
default:
log_error("key_from_printable: "
"unknown/unsupported key type %d", type);
*data = NULL;
*datalenp = 0;
break;
}
}