From b3809e8d4cc4ea433d644877c9d5bf57252351cb Mon Sep 17 00:00:00 2001 From: Pekka Riikonen Date: Mon, 9 Apr 2001 10:48:00 +0000 Subject: [PATCH] updates. --- apps/silc/clientutil.c | 56 ++++++++++++++++++++++++++++ lib/silccrypt/silcpkcs.c | 80 ++++++++++++++++++++++++++++++++++++---- 2 files changed, 128 insertions(+), 8 deletions(-) diff --git a/apps/silc/clientutil.c b/apps/silc/clientutil.c index 4070b419..e37eba53 100644 --- a/apps/silc/clientutil.c +++ b/apps/silc/clientutil.c @@ -711,3 +711,59 @@ int silc_client_load_keys(SilcClient client) return TRUE; } + +/* Dumps the public key on screen. Used from the command line option. */ + +int silc_client_show_key(char *keyfile) +{ + SilcPublicKey public_key; + SilcPublicKeyIdentifier ident; + char *fingerprint; + unsigned char *pk; + uint32 pk_len; + SilcPKCS pkcs; + int key_len = 0; + + if (silc_pkcs_load_public_key(keyfile, &public_key, + SILC_PKCS_FILE_PEM) == FALSE) + if (silc_pkcs_load_public_key(keyfile, &public_key, + SILC_PKCS_FILE_BIN) == FALSE) + return FALSE; + + ident = silc_pkcs_decode_identifier(public_key->identifier); + + pk = silc_pkcs_public_key_encode(public_key, &pk_len); + fingerprint = silc_hash_fingerprint(NULL, pk, pk_len); + + if (silc_pkcs_alloc(public_key->name, &pkcs)) { + key_len = silc_pkcs_public_key_set(pkcs, public_key); + silc_pkcs_free(pkcs); + } + + printf("Public key file : %s\n", keyfile); + printf("Algorithm : %s\n", public_key->name); + if (key_len) + printf("Key length (bits) : %d\n", key_len); + if (ident->realname) + printf("Real name : %s\n", ident->realname); + if (ident->username) + printf("Username : %s\n", ident->username); + if (ident->host) + printf("Hostname : %s\n", ident->host); + if (ident->email) + printf("Email : %s\n", ident->email); + if (ident->org) + printf("Organization : %s\n", ident->org); + if (ident->country) + printf("Country : %s\n", ident->country); + printf("Fingerprint (SHA1) : %s\n", fingerprint); + + fflush(stdout); + + silc_free(fingerprint); + silc_free(pk); + silc_pkcs_public_key_free(public_key); + silc_pkcs_free_identifier(ident); + + return TRUE; +} diff --git a/lib/silccrypt/silcpkcs.c b/lib/silccrypt/silcpkcs.c index 33abe8ca..1f9cb8af 100644 --- a/lib/silccrypt/silcpkcs.c +++ b/lib/silccrypt/silcpkcs.c @@ -153,18 +153,20 @@ unsigned char *silc_pkcs_get_private_key(SilcPKCS pkcs, uint32 *len) /* Sets public key from SilcPublicKey. */ -int silc_pkcs_public_key_set(SilcPKCS pkcs, SilcPublicKey public_key) +uint32 silc_pkcs_public_key_set(SilcPKCS pkcs, SilcPublicKey public_key) { - return pkcs->pkcs->set_public_key(pkcs->context, public_key->pk, - public_key->pk_len); + pkcs->key_len = pkcs->pkcs->set_public_key(pkcs->context, public_key->pk, + public_key->pk_len); + return pkcs->key_len; } /* Sets public key from data. */ -int silc_pkcs_public_key_data_set(SilcPKCS pkcs, unsigned char *pk, - uint32 pk_len) +uint32 silc_pkcs_public_key_data_set(SilcPKCS pkcs, unsigned char *pk, + uint32 pk_len) { - return pkcs->pkcs->set_public_key(pkcs->context, pk, pk_len); + pkcs->key_len = pkcs->pkcs->set_public_key(pkcs->context, pk, pk_len); + return pkcs->key_len; } /* Sets private key from SilcPrivateKey. */ @@ -358,6 +360,63 @@ char *silc_pkcs_encode_identifier(char *username, char *host, char *realname, return identifier; } +/* Decodes the provided `identifier' and returns allocated context for + the identifier. */ + +SilcPublicKeyIdentifier silc_pkcs_decode_identifier(char *identifier) +{ + SilcPublicKeyIdentifier ident; + char *cp, *item; + int len; + + ident = silc_calloc(1, sizeof(*ident)); + + cp = identifier; + while (cp) { + len = strcspn(cp, ","); + item = silc_calloc(len + 1, sizeof(char)); + memcpy(item, cp, len); + + if (strstr(item, "UN=")) + ident->username = strdup(item + 3); + else if (strstr(item, "HN=")) + ident->host = strdup(item + 3); + else if (strstr(item, "RN=")) + ident->realname = strdup(item + 3); + else if (strstr(item, "E=")) + ident->email = strdup(item + 2); + else if (strstr(item, "O=")) + ident->org = strdup(item + 2); + else if (strstr(item, "C=")) + ident->country = strdup(item + 2); + + cp += len; + if (strlen(cp) == 0) + cp = NULL; + else + cp += 2; + + if (item) + silc_free(item); + } + + return ident; +} + +/* Free's decoded public key identifier context. Call this to free the + context returned by the silc_pkcs_decode_identifier. */ + +void silc_pkcs_free_identifier(SilcPublicKeyIdentifier identifier) +{ + silc_free(identifier->username); + silc_free(identifier->host); + silc_free(identifier->realname); + silc_free(identifier->email); + silc_free(identifier->org); + silc_free(identifier->country); + silc_free(identifier); +} + /* Allocates SILC style public key formed from sent arguments. All data is duplicated. */ @@ -528,13 +587,18 @@ int silc_pkcs_public_key_decode(unsigned char *data, uint32 data_len, goto err; /* See if we support this algorithm */ - if (!silc_pkcs_is_supported(pkcs_name)) + if (!silc_pkcs_is_supported(pkcs_name)) { + SILC_LOG_DEBUG(("Unsupported PKCS %s", pkcs_name)); goto err; + } /* Protocol says that at least UN and HN must be provided as identifier, check for these. */ - if (!strstr(ident, "UN=") && !strstr(ident, "HN=")) + if (!strstr(ident, "UN=") && !strstr(ident, "HN=")) { + SILC_LOG_DEBUG(("The public does not have the required UN= and HN= " + "identifiers")); goto err; + } /* Get key data. We assume that rest of the buffer is key data. */ silc_buffer_pull(buf, 2 + pkcs_len + 2 + identifier_len); -- 2.24.0