Greenbone Vulnerability Management Libraries 22.35.6
sshutils.c
Go to the documentation of this file.
1/* SPDX-FileCopyrightText: 2015-2023 Greenbone AG
2 *
3 * SPDX-License-Identifier: GPL-2.0-or-later
4 */
5
10
11#include "sshutils.h"
12
13#include <glib.h> /* for g_free, g_strdup, g_strdup_printf */
14#include <gnutls/gnutls.h> /* for gnutls_datum_t */
15#include <gnutls/x509.h> /* for gnutls_x509_privkey_deinit, gnutls_x509_p... */
16#include <libssh/libssh.h> /* for ssh_key_free, ssh_key_type, ssh_key_type_... */
17#include <string.h> /* for strcmp, strlen */
18
19#undef G_LOG_DOMAIN
23#define G_LOG_DOMAIN "libgvm util"
24
33char *
34gvm_ssh_pkcs8_decrypt (const char *pkcs8_key, const char *passphrase)
35{
36 gnutls_datum_t data;
37 gnutls_x509_privkey_t key;
38 char buffer[16 * 2048];
39 int rc;
40 size_t size = sizeof (buffer);
41
42 if (pkcs8_key == NULL)
43 return NULL;
44
45 rc = gnutls_x509_privkey_init (&key);
46 if (rc)
47 return NULL;
48 data.size = strlen (pkcs8_key);
49 data.data = (void *) g_strdup (pkcs8_key);
50 rc = gnutls_x509_privkey_import_pkcs8 (key, &data, GNUTLS_X509_FMT_PEM,
51 passphrase ? passphrase : "", 0);
52 g_free (data.data);
53 if (rc)
54 {
55 gnutls_x509_privkey_deinit (key);
56 return NULL;
57 }
58 rc = gnutls_x509_privkey_export (key, GNUTLS_X509_FMT_PEM, buffer, &size);
59 gnutls_x509_privkey_deinit (key);
60 if (rc)
61 return NULL;
62 return g_strdup (buffer);
63}
64
74char *
75gvm_ssh_public_from_private (const char *private_key, const char *passphrase)
76{
77 ssh_key priv;
78 char *pub_key, *decrypted_priv, *pub_str = NULL;
79 const char *type;
80 int ret;
81
82 if (private_key == NULL)
83 return NULL;
84 decrypted_priv = gvm_ssh_pkcs8_decrypt (private_key, passphrase);
85 ret = ssh_pki_import_privkey_base64 (decrypted_priv ? decrypted_priv
86 : private_key,
87 passphrase, NULL, NULL, &priv);
88 g_free (decrypted_priv);
89 if (ret)
90 return NULL;
91 ret = ssh_pki_export_pubkey_base64 (priv, &pub_key);
92 type = ssh_key_type_to_char (ssh_key_type (priv));
93#if LIBSSH_VERSION_INT >= SSH_VERSION_INT(0, 6, 4)
94 if (!strcmp (type, "ssh-ecdsa"))
95 type = ssh_pki_key_ecdsa_name (priv);
96#endif
97 ssh_key_free (priv);
98 if (ret)
99 return NULL;
100 pub_str = g_strdup_printf ("%s %s", type, pub_key);
101 g_free (pub_key);
102 return pub_str;
103}
104
115int
116gvm_ssh_private_key_info (const char *private_key, const char *passphrase,
117 const char **type, char **sha256_hash)
118{
119 ssh_key priv;
120 char *decrypted_priv;
121 int ret;
122
123 if (type)
124 *type = NULL;
125 if (sha256_hash)
126 *sha256_hash = NULL;
127
128 if (private_key == NULL)
129 return -1;
130 decrypted_priv = gvm_ssh_pkcs8_decrypt (private_key, passphrase);
131 ret = ssh_pki_import_privkey_base64 (decrypted_priv ? decrypted_priv
132 : private_key,
133 passphrase, NULL, NULL, &priv);
134 free (decrypted_priv);
135 if (ret)
136 return -1;
137
138 if (type)
139 {
140 *type = ssh_key_type_to_char (ssh_key_type (priv));
141 }
142
143 if (sha256_hash)
144 {
145 unsigned char *hash = NULL;
146 size_t hash_size = 0;
147 ret = ssh_get_publickey_hash (priv, SSH_PUBLICKEY_HASH_SHA256, &hash,
148 &hash_size);
149 if (ret == 0)
150 {
151 gchar *hex = g_malloc0 (hash_size * 2 + 1);
152 for (unsigned int i = 0; i < hash_size; i++)
153 {
154 g_snprintf (hex + i * 2, 3, "%02x", hash[i]);
155 }
156 ssh_clean_pubkey_hash (&hash);
157 *sha256_hash = hex;
158 }
159 }
160
161 ssh_key_free (priv);
162
163 if (ret)
164 return -1;
165 return 0;
166}
int gvm_ssh_private_key_info(const char *private_key, const char *passphrase, const char **type, char **sha256_hash)
Gets information from a SSH private key.
Definition sshutils.c:116
char * gvm_ssh_pkcs8_decrypt(const char *pkcs8_key, const char *passphrase)
Decrypts a base64 encrypted ssh private key.
Definition sshutils.c:34
char * gvm_ssh_public_from_private(const char *private_key, const char *passphrase)
Exports a base64 encoded public key from a private key and its passphrase.
Definition sshutils.c:75
SSH related API.