1 /*        $NetBSD: sshkey.h,v 1.22 2025/04/09 15:49:33 christos Exp $ */
2 /* $OpenBSD: sshkey.h,v 1.66 2025/04/02 04:28:03 tb Exp $ */
3 
4 /*
5  * Copyright (c) 2000, 2001 Markus Friedl.  All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
17  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
18  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
20  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
21  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
23  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
25  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26  */
27 #ifndef SSHKEY_H
28 #define SSHKEY_H
29 
30 #include "includes.h"
31 #include <sys/types.h>
32 
33 #ifdef WITH_OPENSSL
34 #include <openssl/rsa.h>
35 #ifdef WITH_DSA
36 #include <openssl/dsa.h>
37 #endif
38 #include <openssl/ec.h>
39 #include <openssl/ecdsa.h>
40 #include <openssl/evp.h>
41 #define SSH_OPENSSL_VERSION OpenSSL_version(OPENSSL_VERSION)
42 #else /* OPENSSL */
43 #define BIGNUM                void
44 #define RSA                   void
45 #define DSA                   void
46 #define EC_KEY                void
47 #define EC_GROUP    void
48 #define EC_POINT    void
49 #define EVP_PKEY    void
50 #define SSH_OPENSSL_VERSION "without OpenSSL"
51 #endif /* WITH_OPENSSL */
52 
53 #define SSH_RSA_MINIMUM_MODULUS_SIZE    1024
54 #define SSH_KEY_MAX_SIGN_DATA_SIZE      (1 << 20)
55 
56 struct sshbuf;
57 
58 /* Key types */
59 enum sshkey_types {
60           KEY_RSA,
61           KEY_DSA,
62           KEY_ECDSA,
63           KEY_ED25519,
64           KEY_RSA_CERT,
65           KEY_DSA_CERT,
66           KEY_ECDSA_CERT,
67           KEY_ED25519_CERT,
68           KEY_XMSS,
69           KEY_XMSS_CERT,
70           KEY_ECDSA_SK,
71           KEY_ECDSA_SK_CERT,
72           KEY_ED25519_SK,
73           KEY_ED25519_SK_CERT,
74           KEY_UNSPEC
75 };
76 
77 /* Default fingerprint hash */
78 #define SSH_FP_HASH_DEFAULT   SSH_DIGEST_SHA256
79 
80 /* Fingerprint representation formats */
81 enum sshkey_fp_rep {
82           SSH_FP_DEFAULT = 0,
83           SSH_FP_HEX,
84           SSH_FP_BASE64,
85           SSH_FP_BUBBLEBABBLE,
86           SSH_FP_RANDOMART
87 };
88 
89 /* Private key serialisation formats, used on the wire */
90 enum sshkey_serialize_rep {
91           SSHKEY_SERIALIZE_DEFAULT = 0,
92           SSHKEY_SERIALIZE_STATE = 1,   /* only state is serialized */
93           SSHKEY_SERIALIZE_FULL = 2,    /* include keys for saving to disk */
94           SSHKEY_SERIALIZE_SHIELD = 3,  /* everything, for encrypting in ram */
95           SSHKEY_SERIALIZE_INFO = 254,  /* minimal information */
96 };
97 
98 /* Private key disk formats */
99 enum sshkey_private_format {
100           SSHKEY_PRIVATE_OPENSSH = 0,
101           SSHKEY_PRIVATE_PEM = 1,
102           SSHKEY_PRIVATE_PKCS8 = 2,
103 };
104 
105 /* key is stored in external hardware */
106 #define SSHKEY_FLAG_EXT                 0x0001
107 
108 #define SSHKEY_CERT_MAX_PRINCIPALS      256
109 /* XXX opaquify? */
110 struct sshkey_cert {
111           struct sshbuf       *certblob; /* Kept around for use on wire */
112           u_int                type; /* SSH2_CERT_TYPE_USER or SSH2_CERT_TYPE_HOST */
113           u_int64_t  serial;
114           char                *key_id;
115           u_int                nprincipals;
116           char                **principals;
117           u_int64_t  valid_after, valid_before;
118           struct sshbuf       *critical;
119           struct sshbuf       *extensions;
120           struct sshkey       *signature_key;
121           char                *signature_type;
122 };
123 
124 /* XXX opaquify? */
125 struct sshkey {
126           int        type;
127           int        flags;
128           /* KEY_DSA */
129           DSA       *dsa;
130           /* KEY_ECDSA and KEY_ECDSA_SK */
131           int        ecdsa_nid;         /* NID of curve */
132           /* libcrypto-backed keys */
133           EVP_PKEY *pkey;
134           /* KEY_ED25519 and KEY_ED25519_SK */
135           u_char    *ed25519_sk;
136           u_char    *ed25519_pk;
137           /* KEY_XMSS */
138           char      *xmss_name;
139           char      *xmss_filename;     /* for state file updates */
140           void      *xmss_state;        /* depends on xmss_name, opaque */
141           u_char    *xmss_sk;
142           u_char    *xmss_pk;
143           /* KEY_ECDSA_SK and KEY_ED25519_SK */
144           char      *sk_application;
145           uint8_t   sk_flags;
146           struct sshbuf *sk_key_handle;
147           struct sshbuf *sk_reserved;
148           /* Certificates */
149           struct sshkey_cert *cert;
150           /* Private key shielding */
151           u_char    *shielded_private;
152           size_t    shielded_len;
153           u_char    *shield_prekey;
154           size_t    shield_prekey_len;
155 };
156 
157 #define   ED25519_SK_SZ       crypto_sign_ed25519_SECRETKEYBYTES
158 #define   ED25519_PK_SZ       crypto_sign_ed25519_PUBLICKEYBYTES
159 
160 /* Additional fields contained in signature */
161 struct sshkey_sig_details {
162           uint32_t sk_counter;          /* U2F signature counter */
163           uint8_t sk_flags;   /* U2F signature flags; see ssh-sk.h */
164 };
165 
166 struct sshkey_impl_funcs {
167           u_int (*size)(const struct sshkey *);   /* optional */
168           int (*alloc)(struct sshkey *);                    /* optional */
169           void (*cleanup)(struct sshkey *);       /* optional */
170           int (*equal)(const struct sshkey *, const struct sshkey *);
171           int (*serialize_public)(const struct sshkey *, struct sshbuf *,
172               enum sshkey_serialize_rep);
173           int (*deserialize_public)(const char *, struct sshbuf *,
174               struct sshkey *);
175           int (*serialize_private)(const struct sshkey *, struct sshbuf *,
176               enum sshkey_serialize_rep);
177           int (*deserialize_private)(const char *, struct sshbuf *,
178               struct sshkey *);
179           int (*generate)(struct sshkey *, int);  /* optional */
180           int (*copy_public)(const struct sshkey *, struct sshkey *);
181           int (*sign)(struct sshkey *, u_char **, size_t *,
182               const u_char *, size_t, const char *,
183               const char *, const char *, u_int); /* optional */
184           int (*verify)(const struct sshkey *, const u_char *, size_t,
185               const u_char *, size_t, const char *, u_int,
186               struct sshkey_sig_details **);
187 };
188 
189 struct sshkey_impl {
190           const char *name;
191           const char *shortname;
192           const char *sigalg;
193           int type;
194           int nid;
195           int cert;
196           int sigonly;
197           int keybits;
198           const struct sshkey_impl_funcs *funcs;
199 };
200 
201 struct sshkey       *sshkey_new(int);
202 void                 sshkey_free(struct sshkey *);
203 int                  sshkey_equal_public(const struct sshkey *,
204     const struct sshkey *);
205 int                  sshkey_equal(const struct sshkey *, const struct sshkey *);
206 char                *sshkey_fingerprint(const struct sshkey *,
207     int, enum sshkey_fp_rep);
208 int                  sshkey_fingerprint_raw(const struct sshkey *k,
209     int, u_char **retp, size_t *lenp);
210 const char          *sshkey_type(const struct sshkey *);
211 const char          *sshkey_cert_type(const struct sshkey *);
212 int                  sshkey_format_text(const struct sshkey *, struct sshbuf *);
213 int                  sshkey_write(const struct sshkey *, FILE *);
214 int                  sshkey_read(struct sshkey *, char **);
215 u_int                sshkey_size(const struct sshkey *);
216 
217 int                  sshkey_generate(int type, u_int bits, struct sshkey **keyp);
218 int                  sshkey_from_private(const struct sshkey *, struct sshkey **);
219 
220 int                  sshkey_is_shielded(struct sshkey *);
221 int                  sshkey_shield_private(struct sshkey *);
222 int                  sshkey_unshield_private(struct sshkey *);
223 
224 int        sshkey_type_from_name(const char *);
225 int        sshkey_type_from_shortname(const char *);
226 int        sshkey_is_cert(const struct sshkey *);
227 int        sshkey_is_sk(const struct sshkey *);
228 int        sshkey_type_is_cert(int);
229 int        sshkey_type_plain(int);
230 
231 /* Returns non-zero if key name match sigalgs pattern list. (handles RSA) */
232 int        sshkey_match_keyname_to_sigalgs(const char *, const char *);
233 
234 int        sshkey_to_certified(struct sshkey *);
235 int        sshkey_drop_cert(struct sshkey *);
236 int        sshkey_cert_copy(const struct sshkey *, struct sshkey *);
237 int        sshkey_cert_check_authority(const struct sshkey *, int, int, int,
238     uint64_t, const char *, const char **);
239 int        sshkey_cert_check_authority_now(const struct sshkey *, int, int, int,
240     const char *, const char **);
241 int        sshkey_cert_check_host(const struct sshkey *, const char *,
242     int , const char *, const char **);
243 size_t     sshkey_format_cert_validity(const struct sshkey_cert *,
244     char *, size_t) __attribute__((__bounded__(__string__, 2, 3)));
245 int        sshkey_check_cert_sigtype(const struct sshkey *, const char *);
246 
247 int        sshkey_certify(struct sshkey *, struct sshkey *,
248     const char *, const char *, const char *);
249 /* Variant allowing use of a custom signature function (e.g. for ssh-agent) */
250 typedef int sshkey_certify_signer(struct sshkey *, u_char **, size_t *,
251     const u_char *, size_t, const char *, const char *, const char *,
252     u_int, void *);
253 int        sshkey_certify_custom(struct sshkey *, struct sshkey *, const char *,
254     const char *, const char *, sshkey_certify_signer *, void *);
255 
256 int                  sshkey_ecdsa_nid_from_name(const char *);
257 int                  sshkey_curve_name_to_nid(const char *);
258 const char *         sshkey_curve_nid_to_name(int);
259 u_int                sshkey_curve_nid_to_bits(int);
260 int                  sshkey_ecdsa_bits_to_nid(int);
261 int                  sshkey_ecdsa_key_to_nid(const EC_KEY *);
262 int                  sshkey_ecdsa_pkey_to_nid(EVP_PKEY *);
263 int                  sshkey_ec_nid_to_hash_alg(int nid);
264 int                  sshkey_ec_validate_public(const EC_GROUP *, const EC_POINT *);
265 int                  sshkey_ec_validate_private(const EC_KEY *);
266 const char          *sshkey_ssh_name(const struct sshkey *);
267 const char          *sshkey_ssh_name_plain(const struct sshkey *);
268 int                  sshkey_names_valid2(const char *, int, int);
269 char                *sshkey_alg_list(int, int, int, char);
270 
271 int        sshkey_from_blob(const u_char *, size_t, struct sshkey **);
272 int        sshkey_fromb(struct sshbuf *, struct sshkey **);
273 int        sshkey_froms(struct sshbuf *, struct sshkey **);
274 int        sshkey_to_blob(const struct sshkey *, u_char **, size_t *);
275 int        sshkey_to_base64(const struct sshkey *, char **);
276 int        sshkey_putb(const struct sshkey *, struct sshbuf *);
277 int        sshkey_puts(const struct sshkey *, struct sshbuf *);
278 int        sshkey_puts_opts(const struct sshkey *, struct sshbuf *,
279     enum sshkey_serialize_rep);
280 int        sshkey_plain_to_blob(const struct sshkey *, u_char **, size_t *);
281 int        sshkey_putb_plain(const struct sshkey *, struct sshbuf *);
282 
283 int        sshkey_sign(struct sshkey *, u_char **, size_t *,
284     const u_char *, size_t, const char *, const char *, const char *, u_int);
285 int        sshkey_verify(const struct sshkey *, const u_char *, size_t,
286     const u_char *, size_t, const char *, u_int, struct sshkey_sig_details **);
287 int        sshkey_check_sigtype(const u_char *, size_t, const char *);
288 const char *sshkey_sigalg_by_name(const char *);
289 int        sshkey_get_sigtype(const u_char *, size_t, char **);
290 
291 /* Signing and verification backend for libcrypto-backed keys */
292 int       sshkey_pkey_digest_sign(EVP_PKEY*, int, u_char **,
293     size_t *, const u_char *, size_t);
294 int       sshkey_pkey_digest_verify(EVP_PKEY *, int, const u_char *,
295     size_t, u_char *, size_t);
296 
297 /* for debug */
298 void      sshkey_dump_ec_point(const EC_GROUP *, const EC_POINT *);
299 void      sshkey_dump_ec_key(const EC_KEY *);
300 
301 /* private key parsing and serialisation */
302 int       sshkey_private_serialize(struct sshkey *key, struct sshbuf *buf);
303 int       sshkey_private_serialize_opt(struct sshkey *key, struct sshbuf *buf,
304     enum sshkey_serialize_rep);
305 int       sshkey_private_deserialize(struct sshbuf *buf,  struct sshkey **keyp);
306 
307 /* private key file format parsing and serialisation */
308 int       sshkey_private_to_fileblob(struct sshkey *key, struct sshbuf *blob,
309     const char *passphrase, const char *comment,
310     int format, const char *openssh_format_cipher, int openssh_format_rounds);
311 int       sshkey_parse_private_fileblob(struct sshbuf *buffer,
312     const char *passphrase, struct sshkey **keyp, char **commentp);
313 int       sshkey_parse_private_fileblob_type(struct sshbuf *blob, int type,
314     const char *passphrase, struct sshkey **keyp, char **commentp);
315 int       sshkey_parse_pubkey_from_private_fileblob_type(struct sshbuf *blob,
316     int type, struct sshkey **pubkeyp);
317 
318 int sshkey_check_rsa_length(const struct sshkey *, int);
319 /* XXX should be internal, but used by ssh-keygen */
320 int ssh_rsa_complete_crt_parameters(const BIGNUM *, const BIGNUM *,
321     const BIGNUM *, const BIGNUM *, BIGNUM **, BIGNUM **);
322 
323 /* stateful keys (e.g. XMSS) */
324 int        sshkey_set_filename(struct sshkey *, const char *);
325 int        sshkey_enable_maxsign(struct sshkey *, u_int32_t);
326 u_int32_t sshkey_signatures_left(const struct sshkey *);
327 int        sshkey_private_serialize_maxsign(struct sshkey *key,
328     struct sshbuf *buf, u_int32_t maxsign, int);
329 
330 void       sshkey_sig_details_free(struct sshkey_sig_details *);
331 
332 #ifdef WITH_OPENSSL
333 int       sshkey_ecdsa_fixup_group(EVP_PKEY *k); /* ssh-ecdsa.c */
334 #endif
335 
336 #ifdef SSHKEY_INTERNAL
337 int       sshkey_sk_fields_equal(const struct sshkey *a, const struct sshkey *b);
338 void      sshkey_sk_cleanup(struct sshkey *k);
339 int       sshkey_serialize_sk(const struct sshkey *key, struct sshbuf *b);
340 int       sshkey_copy_public_sk(const struct sshkey *from, struct sshkey *to);
341 int       sshkey_deserialize_sk(struct sshbuf *b, struct sshkey *key);
342 int       sshkey_serialize_private_sk(const struct sshkey *key,
343     struct sshbuf *buf);
344 int       sshkey_private_deserialize_sk(struct sshbuf *buf, struct sshkey *k);
345 #ifdef WITH_OPENSSL
346 int       check_rsa_length(const RSA *rsa); /* XXX remove */
347 #endif
348 #endif
349 
350 #ifndef WITH_OPENSSL
351 #undef RSA
352 #undef DSA
353 #undef EC_KEY
354 #undef EC_GROUP
355 #undef EC_POINT
356 #undef EVP_PKEY
357 #endif /* WITH_OPENSSL */
358 
359 #endif /* SSHKEY_H */
360