1 /* Copyright (C) 2009, 2010 Simon Josefsson
2 * Copyright (C) 2006, 2007 The Written Word, Inc. All rights reserved.
3 * Copyright (c) 2004-2006, Sara Golemon <sarag@libssh2.org>
4 *
5 * Author: Simon Josefsson
6 *
7 * Redistribution and use in source and binary forms,
8 * with or without modification, are permitted provided
9 * that the following conditions are met:
10 *
11 * Redistributions of source code must retain the above
12 * copyright notice, this list of conditions and the
13 * following disclaimer.
14 *
15 * Redistributions in binary form must reproduce the above
16 * copyright notice, this list of conditions and the following
17 * disclaimer in the documentation and/or other materials
18 * provided with the distribution.
19 *
20 * Neither the name of the copyright holder nor the names
21 * of any other contributors may be used to endorse or
22 * promote products derived from this software without
23 * specific prior written permission.
24 *
25 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
26 * CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
27 * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
28 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
29 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
30 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
31 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
32 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
33 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
34 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
35 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
36 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
37 * USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
38 * OF SUCH DAMAGE.
39 */
40
41 #include "libssh2_priv.h"
42
43 #ifdef LIBSSH2_OPENSSL /* compile only if we build with openssl */
44
45 #include <string.h>
46 #include "misc.h"
47
48 #ifndef EVP_MAX_BLOCK_LENGTH
49 #define EVP_MAX_BLOCK_LENGTH 32
50 #endif
51
52 int
53 read_openssh_private_key_from_memory(void **key_ctx, LIBSSH2_SESSION *session,
54 const char *key_type,
55 const char *filedata,
56 size_t filedata_len,
57 unsigned const char *passphrase);
58
59 static unsigned char *
write_bn(unsigned char * buf,const BIGNUM * bn,int bn_bytes)60 write_bn(unsigned char *buf, const BIGNUM *bn, int bn_bytes)
61 {
62 unsigned char *p = buf;
63
64 /* Left space for bn size which will be written below. */
65 p += 4;
66
67 *p = 0;
68 BN_bn2bin(bn, p + 1);
69 if(!(*(p + 1) & 0x80)) {
70 memmove(p, p + 1, --bn_bytes);
71 }
72 _libssh2_htonu32(p - 4, bn_bytes); /* Post write bn size. */
73
74 return p + bn_bytes;
75 }
76
77 int
_libssh2_rsa_new(libssh2_rsa_ctx ** rsa,const unsigned char * edata,unsigned long elen,const unsigned char * ndata,unsigned long nlen,const unsigned char * ddata,unsigned long dlen,const unsigned char * pdata,unsigned long plen,const unsigned char * qdata,unsigned long qlen,const unsigned char * e1data,unsigned long e1len,const unsigned char * e2data,unsigned long e2len,const unsigned char * coeffdata,unsigned long coefflen)78 _libssh2_rsa_new(libssh2_rsa_ctx ** rsa,
79 const unsigned char *edata,
80 unsigned long elen,
81 const unsigned char *ndata,
82 unsigned long nlen,
83 const unsigned char *ddata,
84 unsigned long dlen,
85 const unsigned char *pdata,
86 unsigned long plen,
87 const unsigned char *qdata,
88 unsigned long qlen,
89 const unsigned char *e1data,
90 unsigned long e1len,
91 const unsigned char *e2data,
92 unsigned long e2len,
93 const unsigned char *coeffdata, unsigned long coefflen)
94 {
95 BIGNUM * e;
96 BIGNUM * n;
97 BIGNUM * d = 0;
98 BIGNUM * p = 0;
99 BIGNUM * q = 0;
100 BIGNUM * dmp1 = 0;
101 BIGNUM * dmq1 = 0;
102 BIGNUM * iqmp = 0;
103
104 e = BN_new();
105 BN_bin2bn(edata, elen, e);
106
107 n = BN_new();
108 BN_bin2bn(ndata, nlen, n);
109
110 if(ddata) {
111 d = BN_new();
112 BN_bin2bn(ddata, dlen, d);
113
114 p = BN_new();
115 BN_bin2bn(pdata, plen, p);
116
117 q = BN_new();
118 BN_bin2bn(qdata, qlen, q);
119
120 dmp1 = BN_new();
121 BN_bin2bn(e1data, e1len, dmp1);
122
123 dmq1 = BN_new();
124 BN_bin2bn(e2data, e2len, dmq1);
125
126 iqmp = BN_new();
127 BN_bin2bn(coeffdata, coefflen, iqmp);
128 }
129
130 *rsa = RSA_new();
131 #ifdef HAVE_OPAQUE_STRUCTS
132 RSA_set0_key(*rsa, n, e, d);
133 #else
134 (*rsa)->e = e;
135 (*rsa)->n = n;
136 (*rsa)->d = d;
137 #endif
138
139 #ifdef HAVE_OPAQUE_STRUCTS
140 RSA_set0_factors(*rsa, p, q);
141 #else
142 (*rsa)->p = p;
143 (*rsa)->q = q;
144 #endif
145
146 #ifdef HAVE_OPAQUE_STRUCTS
147 RSA_set0_crt_params(*rsa, dmp1, dmq1, iqmp);
148 #else
149 (*rsa)->dmp1 = dmp1;
150 (*rsa)->dmq1 = dmq1;
151 (*rsa)->iqmp = iqmp;
152 #endif
153 return 0;
154 }
155
156 int
_libssh2_rsa_sha1_verify(libssh2_rsa_ctx * rsactx,const unsigned char * sig,unsigned long sig_len,const unsigned char * m,unsigned long m_len)157 _libssh2_rsa_sha1_verify(libssh2_rsa_ctx * rsactx,
158 const unsigned char *sig,
159 unsigned long sig_len,
160 const unsigned char *m, unsigned long m_len)
161 {
162 unsigned char hash[SHA_DIGEST_LENGTH];
163 int ret;
164
165 if(_libssh2_sha1(m, m_len, hash))
166 return -1; /* failure */
167 ret = RSA_verify(NID_sha1, hash, SHA_DIGEST_LENGTH,
168 (unsigned char *) sig, sig_len, rsactx);
169 return (ret == 1) ? 0 : -1;
170 }
171
172 #if LIBSSH2_DSA
173 int
_libssh2_dsa_new(libssh2_dsa_ctx ** dsactx,const unsigned char * p,unsigned long p_len,const unsigned char * q,unsigned long q_len,const unsigned char * g,unsigned long g_len,const unsigned char * y,unsigned long y_len,const unsigned char * x,unsigned long x_len)174 _libssh2_dsa_new(libssh2_dsa_ctx ** dsactx,
175 const unsigned char *p,
176 unsigned long p_len,
177 const unsigned char *q,
178 unsigned long q_len,
179 const unsigned char *g,
180 unsigned long g_len,
181 const unsigned char *y,
182 unsigned long y_len,
183 const unsigned char *x, unsigned long x_len)
184 {
185 BIGNUM * p_bn;
186 BIGNUM * q_bn;
187 BIGNUM * g_bn;
188 BIGNUM * pub_key;
189 BIGNUM * priv_key = NULL;
190
191 p_bn = BN_new();
192 BN_bin2bn(p, p_len, p_bn);
193
194 q_bn = BN_new();
195 BN_bin2bn(q, q_len, q_bn);
196
197 g_bn = BN_new();
198 BN_bin2bn(g, g_len, g_bn);
199
200 pub_key = BN_new();
201 BN_bin2bn(y, y_len, pub_key);
202
203 if(x_len) {
204 priv_key = BN_new();
205 BN_bin2bn(x, x_len, priv_key);
206 }
207
208 *dsactx = DSA_new();
209
210 #ifdef HAVE_OPAQUE_STRUCTS
211 DSA_set0_pqg(*dsactx, p_bn, q_bn, g_bn);
212 #else
213 (*dsactx)->p = p_bn;
214 (*dsactx)->g = g_bn;
215 (*dsactx)->q = q_bn;
216 #endif
217
218 #ifdef HAVE_OPAQUE_STRUCTS
219 DSA_set0_key(*dsactx, pub_key, priv_key);
220 #else
221 (*dsactx)->pub_key = pub_key;
222 (*dsactx)->priv_key = priv_key;
223 #endif
224 return 0;
225 }
226
227 int
_libssh2_dsa_sha1_verify(libssh2_dsa_ctx * dsactx,const unsigned char * sig,const unsigned char * m,unsigned long m_len)228 _libssh2_dsa_sha1_verify(libssh2_dsa_ctx * dsactx,
229 const unsigned char *sig,
230 const unsigned char *m, unsigned long m_len)
231 {
232 unsigned char hash[SHA_DIGEST_LENGTH];
233 DSA_SIG * dsasig;
234 BIGNUM * r;
235 BIGNUM * s;
236 int ret = -1;
237
238 r = BN_new();
239 BN_bin2bn(sig, 20, r);
240 s = BN_new();
241 BN_bin2bn(sig + 20, 20, s);
242
243 dsasig = DSA_SIG_new();
244 #ifdef HAVE_OPAQUE_STRUCTS
245 DSA_SIG_set0(dsasig, r, s);
246 #else
247 dsasig->r = r;
248 dsasig->s = s;
249 #endif
250 if(!_libssh2_sha1(m, m_len, hash))
251 /* _libssh2_sha1() succeeded */
252 ret = DSA_do_verify(hash, SHA_DIGEST_LENGTH, dsasig, dsactx);
253
254 DSA_SIG_free(dsasig);
255
256 return (ret == 1) ? 0 : -1;
257 }
258 #endif /* LIBSSH_DSA */
259
260 #if LIBSSH2_ECDSA
261
262 /* _libssh2_ecdsa_key_get_curve_type
263 *
264 * returns key curve type that maps to libssh2_curve_type
265 *
266 */
267
268 libssh2_curve_type
_libssh2_ecdsa_key_get_curve_type(_libssh2_ec_key * key)269 _libssh2_ecdsa_key_get_curve_type(_libssh2_ec_key *key)
270 {
271 const EC_GROUP *group = EC_KEY_get0_group(key);
272 return EC_GROUP_get_curve_name(group);
273 }
274
275 /* _libssh2_ecdsa_curve_type_from_name
276 *
277 * returns 0 for success, key curve type that maps to libssh2_curve_type
278 *
279 */
280
281 int
_libssh2_ecdsa_curve_type_from_name(const char * name,libssh2_curve_type * out_type)282 _libssh2_ecdsa_curve_type_from_name(const char *name,
283 libssh2_curve_type *out_type)
284 {
285 int ret = 0;
286 libssh2_curve_type type;
287
288 if(name == NULL || strlen(name) != 19)
289 return -1;
290
291 if(strcmp(name, "ecdsa-sha2-nistp256") == 0)
292 type = LIBSSH2_EC_CURVE_NISTP256;
293 else if(strcmp(name, "ecdsa-sha2-nistp384") == 0)
294 type = LIBSSH2_EC_CURVE_NISTP384;
295 else if(strcmp(name, "ecdsa-sha2-nistp521") == 0)
296 type = LIBSSH2_EC_CURVE_NISTP521;
297 else {
298 ret = -1;
299 }
300
301 if(ret == 0 && out_type) {
302 *out_type = type;
303 }
304
305 return ret;
306 }
307
308 /* _libssh2_ecdsa_curve_name_with_octal_new
309 *
310 * Creates a new public key given an octal string, length and type
311 *
312 */
313
314 int
_libssh2_ecdsa_curve_name_with_octal_new(libssh2_ecdsa_ctx ** ec_ctx,const unsigned char * k,size_t k_len,libssh2_curve_type curve)315 _libssh2_ecdsa_curve_name_with_octal_new(libssh2_ecdsa_ctx ** ec_ctx,
316 const unsigned char *k,
317 size_t k_len, libssh2_curve_type curve)
318 {
319
320 int ret = 0;
321 const EC_GROUP *ec_group = NULL;
322 EC_KEY *ec_key = EC_KEY_new_by_curve_name(curve);
323 EC_POINT *point = NULL;
324
325 if(ec_key) {
326 ec_group = EC_KEY_get0_group(ec_key);
327 point = EC_POINT_new(ec_group);
328 ret = EC_POINT_oct2point(ec_group, point, k, k_len, NULL);
329 ret = EC_KEY_set_public_key(ec_key, point);
330
331 if(point != NULL)
332 EC_POINT_free(point);
333
334 if(ec_ctx != NULL)
335 *ec_ctx = ec_key;
336 }
337
338 return (ret == 1) ? 0 : -1;
339 }
340
341 #define LIBSSH2_ECDSA_VERIFY(digest_type) \
342 { \
343 unsigned char hash[SHA##digest_type##_DIGEST_LENGTH]; \
344 libssh2_sha##digest_type(m, m_len, hash); \
345 ret = ECDSA_do_verify(hash, SHA##digest_type##_DIGEST_LENGTH, \
346 ecdsa_sig, ec_key); \
347 \
348 }
349
350 int
_libssh2_ecdsa_verify(libssh2_ecdsa_ctx * ctx,const unsigned char * r,size_t r_len,const unsigned char * s,size_t s_len,const unsigned char * m,size_t m_len)351 _libssh2_ecdsa_verify(libssh2_ecdsa_ctx * ctx,
352 const unsigned char *r, size_t r_len,
353 const unsigned char *s, size_t s_len,
354 const unsigned char *m, size_t m_len)
355 {
356 int ret = 0;
357 EC_KEY *ec_key = (EC_KEY*)ctx;
358 libssh2_curve_type type = _libssh2_ecdsa_key_get_curve_type(ec_key);
359
360 #ifdef HAVE_OPAQUE_STRUCTS
361 ECDSA_SIG *ecdsa_sig = ECDSA_SIG_new();
362 BIGNUM *pr = BN_new();
363 BIGNUM *ps = BN_new();
364
365 BN_bin2bn(r, r_len, pr);
366 BN_bin2bn(s, s_len, ps);
367 ECDSA_SIG_set0(ecdsa_sig, pr, ps);
368
369 #else
370 ECDSA_SIG ecdsa_sig_;
371 ECDSA_SIG *ecdsa_sig = &ecdsa_sig_;
372 ecdsa_sig_.r = BN_new();
373 BN_bin2bn(r, r_len, ecdsa_sig_.r);
374 ecdsa_sig_.s = BN_new();
375 BN_bin2bn(s, s_len, ecdsa_sig_.s);
376 #endif
377
378 if(type == LIBSSH2_EC_CURVE_NISTP256) {
379 LIBSSH2_ECDSA_VERIFY(256);
380 }
381 else if(type == LIBSSH2_EC_CURVE_NISTP384) {
382 LIBSSH2_ECDSA_VERIFY(384);
383 }
384 else if(type == LIBSSH2_EC_CURVE_NISTP521) {
385 LIBSSH2_ECDSA_VERIFY(512);
386 }
387
388 #ifdef HAVE_OPAQUE_STRUCTS
389 if(ecdsa_sig)
390 ECDSA_SIG_free(ecdsa_sig);
391 #else
392 BN_clear_free(ecdsa_sig_.s);
393 BN_clear_free(ecdsa_sig_.r);
394 #endif
395
396 return (ret == 1) ? 0 : -1;
397 }
398
399 #endif /* LIBSSH2_ECDSA */
400
401 int
_libssh2_cipher_init(_libssh2_cipher_ctx * h,_libssh2_cipher_type (algo),unsigned char * iv,unsigned char * secret,int encrypt)402 _libssh2_cipher_init(_libssh2_cipher_ctx * h,
403 _libssh2_cipher_type(algo),
404 unsigned char *iv, unsigned char *secret, int encrypt)
405 {
406 #ifdef HAVE_OPAQUE_STRUCTS
407 *h = EVP_CIPHER_CTX_new();
408 return !EVP_CipherInit(*h, algo(), secret, iv, encrypt);
409 #else
410 EVP_CIPHER_CTX_init(h);
411 return !EVP_CipherInit(h, algo(), secret, iv, encrypt);
412 #endif
413 }
414
415 int
_libssh2_cipher_crypt(_libssh2_cipher_ctx * ctx,_libssh2_cipher_type (algo),int encrypt,unsigned char * block,size_t blocksize)416 _libssh2_cipher_crypt(_libssh2_cipher_ctx * ctx,
417 _libssh2_cipher_type(algo),
418 int encrypt, unsigned char *block, size_t blocksize)
419 {
420 unsigned char buf[EVP_MAX_BLOCK_LENGTH];
421 int ret;
422 (void) algo;
423 (void) encrypt;
424
425 #ifdef HAVE_OPAQUE_STRUCTS
426 ret = EVP_Cipher(*ctx, buf, block, blocksize);
427 #else
428 ret = EVP_Cipher(ctx, buf, block, blocksize);
429 #endif
430 if(ret == 1) {
431 memcpy(block, buf, blocksize);
432 }
433 return ret == 1 ? 0 : 1;
434 }
435
436 #if LIBSSH2_AES_CTR && !defined(HAVE_EVP_AES_128_CTR)
437
438 #include <openssl/aes.h>
439 #include <openssl/evp.h>
440
441 typedef struct
442 {
443 AES_KEY key;
444 EVP_CIPHER_CTX *aes_ctx;
445 unsigned char ctr[AES_BLOCK_SIZE];
446 } aes_ctr_ctx;
447
448 static int
aes_ctr_init(EVP_CIPHER_CTX * ctx,const unsigned char * key,const unsigned char * iv,int enc)449 aes_ctr_init(EVP_CIPHER_CTX *ctx, const unsigned char *key,
450 const unsigned char *iv, int enc) /* init key */
451 {
452 /*
453 * variable "c" is leaked from this scope, but is later freed
454 * in aes_ctr_cleanup
455 */
456 aes_ctr_ctx *c;
457 const EVP_CIPHER *aes_cipher;
458 (void) enc;
459
460 switch(EVP_CIPHER_CTX_key_length(ctx)) {
461 case 16:
462 aes_cipher = EVP_aes_128_ecb();
463 break;
464 case 24:
465 aes_cipher = EVP_aes_192_ecb();
466 break;
467 case 32:
468 aes_cipher = EVP_aes_256_ecb();
469 break;
470 default:
471 return 0;
472 }
473
474 c = malloc(sizeof(*c));
475 if(c == NULL)
476 return 0;
477
478 #ifdef HAVE_OPAQUE_STRUCTS
479 c->aes_ctx = EVP_CIPHER_CTX_new();
480 #else
481 c->aes_ctx = malloc(sizeof(EVP_CIPHER_CTX));
482 #endif
483 if(c->aes_ctx == NULL) {
484 free(c);
485 return 0;
486 }
487
488 if(EVP_EncryptInit(c->aes_ctx, aes_cipher, key, NULL) != 1) {
489 #ifdef HAVE_OPAQUE_STRUCTS
490 EVP_CIPHER_CTX_free(c->aes_ctx);
491 #else
492 free(c->aes_ctx);
493 #endif
494 free(c);
495 return 0;
496 }
497
498 EVP_CIPHER_CTX_set_padding(c->aes_ctx, 0);
499
500 memcpy(c->ctr, iv, AES_BLOCK_SIZE);
501
502 EVP_CIPHER_CTX_set_app_data(ctx, c);
503
504 return 1;
505 }
506
507 static int
aes_ctr_do_cipher(EVP_CIPHER_CTX * ctx,unsigned char * out,const unsigned char * in,size_t inl)508 aes_ctr_do_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
509 const unsigned char *in,
510 size_t inl) /* encrypt/decrypt data */
511 {
512 aes_ctr_ctx *c = EVP_CIPHER_CTX_get_app_data(ctx);
513 unsigned char b1[AES_BLOCK_SIZE];
514 int outlen = 0;
515
516 if(inl != 16) /* libssh2 only ever encrypt one block */
517 return 0;
518
519 if(c == NULL) {
520 return 0;
521 }
522
523 /*
524 To encrypt a packet P=P1||P2||...||Pn (where P1, P2, ..., Pn are each
525 blocks of length L), the encryptor first encrypts <X> with <cipher>
526 to obtain a block B1. The block B1 is then XORed with P1 to generate
527 the ciphertext block C1. The counter X is then incremented
528 */
529
530 if(EVP_EncryptUpdate(c->aes_ctx, b1, &outlen,
531 c->ctr, AES_BLOCK_SIZE) != 1) {
532 return 0;
533 }
534
535 _libssh2_xor_data(out, in, b1, AES_BLOCK_SIZE);
536 _libssh2_aes_ctr_increment(c->ctr, AES_BLOCK_SIZE);
537
538 return 1;
539 }
540
541 static int
aes_ctr_cleanup(EVP_CIPHER_CTX * ctx)542 aes_ctr_cleanup(EVP_CIPHER_CTX *ctx) /* cleanup ctx */
543 {
544 aes_ctr_ctx *c = EVP_CIPHER_CTX_get_app_data(ctx);
545
546 if(c == NULL) {
547 return 1;
548 }
549
550 if(c->aes_ctx != NULL) {
551 #ifdef HAVE_OPAQUE_STRUCTS
552 EVP_CIPHER_CTX_free(c->aes_ctx);
553 #else
554 _libssh2_cipher_dtor(c->aes_ctx);
555 free(c->aes_ctx);
556 #endif
557 }
558
559 free(c);
560
561 return 1;
562 }
563
564 static const EVP_CIPHER *
make_ctr_evp(size_t keylen,EVP_CIPHER ** aes_ctr_cipher,int type)565 make_ctr_evp (size_t keylen, EVP_CIPHER **aes_ctr_cipher, int type)
566 {
567 #ifdef HAVE_OPAQUE_STRUCTS
568 *aes_ctr_cipher = EVP_CIPHER_meth_new(type, 16, keylen);
569 if(*aes_ctr_cipher) {
570 EVP_CIPHER_meth_set_iv_length(*aes_ctr_cipher, 16);
571 EVP_CIPHER_meth_set_init(*aes_ctr_cipher, aes_ctr_init);
572 EVP_CIPHER_meth_set_do_cipher(*aes_ctr_cipher, aes_ctr_do_cipher);
573 EVP_CIPHER_meth_set_cleanup(*aes_ctr_cipher, aes_ctr_cleanup);
574 }
575 #else
576 (*aes_ctr_cipher)->nid = type;
577 (*aes_ctr_cipher)->block_size = 16;
578 (*aes_ctr_cipher)->key_len = keylen;
579 (*aes_ctr_cipher)->iv_len = 16;
580 (*aes_ctr_cipher)->init = aes_ctr_init;
581 (*aes_ctr_cipher)->do_cipher = aes_ctr_do_cipher;
582 (*aes_ctr_cipher)->cleanup = aes_ctr_cleanup;
583 #endif
584
585 return *aes_ctr_cipher;
586 }
587
588 const EVP_CIPHER *
_libssh2_EVP_aes_128_ctr(void)589 _libssh2_EVP_aes_128_ctr(void)
590 {
591 #ifdef HAVE_OPAQUE_STRUCTS
592 static EVP_CIPHER * aes_ctr_cipher;
593 return !aes_ctr_cipher ?
594 make_ctr_evp(16, &aes_ctr_cipher, NID_aes_128_ctr) : aes_ctr_cipher;
595 #else
596 static EVP_CIPHER aes_ctr_cipher;
597 static EVP_CIPHER * aes_ctr_cipher_ptr = &aes_ctr_cipher;
598 return !aes_ctr_cipher.key_len ?
599 make_ctr_evp(16, &aes_ctr_cipher_ptr, 0) : &aes_ctr_cipher;
600 #endif
601 }
602
603 const EVP_CIPHER *
_libssh2_EVP_aes_192_ctr(void)604 _libssh2_EVP_aes_192_ctr(void)
605 {
606 #ifdef HAVE_OPAQUE_STRUCTS
607 static EVP_CIPHER * aes_ctr_cipher;
608 return !aes_ctr_cipher ?
609 make_ctr_evp(24, &aes_ctr_cipher, NID_aes_192_ctr) : aes_ctr_cipher;
610 #else
611 static EVP_CIPHER aes_ctr_cipher;
612 static EVP_CIPHER * aes_ctr_cipher_ptr = &aes_ctr_cipher;
613 return !aes_ctr_cipher.key_len ?
614 make_ctr_evp(24, &aes_ctr_cipher_ptr, 0) : &aes_ctr_cipher;
615 #endif
616 }
617
618 const EVP_CIPHER *
_libssh2_EVP_aes_256_ctr(void)619 _libssh2_EVP_aes_256_ctr(void)
620 {
621 #ifdef HAVE_OPAQUE_STRUCTS
622 static EVP_CIPHER * aes_ctr_cipher;
623 return !aes_ctr_cipher ?
624 make_ctr_evp(32, &aes_ctr_cipher, NID_aes_256_ctr) : aes_ctr_cipher;
625 #else
626 static EVP_CIPHER aes_ctr_cipher;
627 static EVP_CIPHER * aes_ctr_cipher_ptr = &aes_ctr_cipher;
628 return !aes_ctr_cipher.key_len ?
629 make_ctr_evp(32, &aes_ctr_cipher_ptr, 0) : &aes_ctr_cipher;
630 #endif
631 }
632
633 #endif /* LIBSSH2_AES_CTR */
634
635 #ifndef HAVE_EVP_AES_128_CTR
636 static EVP_CIPHER * aes_128_ctr_cipher = NULL;
637 static EVP_CIPHER * aes_192_ctr_cipher = NULL;
638 static EVP_CIPHER * aes_256_ctr_cipher = NULL;
639 #endif
640
_libssh2_openssl_crypto_init(void)641 void _libssh2_openssl_crypto_init(void)
642 {
643 #if OPENSSL_VERSION_NUMBER >= 0x10100000L && \
644 !defined(LIBRESSL_VERSION_NUMBER)
645 #ifndef OPENSSL_NO_ENGINE
646 ENGINE_load_builtin_engines();
647 ENGINE_register_all_complete();
648 #endif
649 #else
650 OpenSSL_add_all_algorithms();
651 OpenSSL_add_all_ciphers();
652 OpenSSL_add_all_digests();
653 #ifndef OPENSSL_NO_ENGINE
654 ENGINE_load_builtin_engines();
655 ENGINE_register_all_complete();
656 #endif
657 #endif
658 #ifndef HAVE_EVP_AES_128_CTR
659 aes_128_ctr_cipher = (EVP_CIPHER *)_libssh2_EVP_aes_128_ctr();
660 aes_192_ctr_cipher = (EVP_CIPHER *)_libssh2_EVP_aes_192_ctr();
661 aes_256_ctr_cipher = (EVP_CIPHER *)_libssh2_EVP_aes_256_ctr();
662 #endif
663 }
664
_libssh2_openssl_crypto_exit(void)665 void _libssh2_openssl_crypto_exit(void)
666 {
667 #ifndef HAVE_EVP_AES_128_CTR
668 #ifdef HAVE_OPAQUE_STRUCTS
669 if(aes_128_ctr_cipher) {
670 EVP_CIPHER_meth_free(aes_128_ctr_cipher);
671 }
672
673 if(aes_192_ctr_cipher) {
674 EVP_CIPHER_meth_free(aes_192_ctr_cipher);
675 }
676
677 if(aes_256_ctr_cipher) {
678 EVP_CIPHER_meth_free(aes_256_ctr_cipher);
679 }
680 #endif
681
682 aes_128_ctr_cipher = NULL;
683 aes_192_ctr_cipher = NULL;
684 aes_256_ctr_cipher = NULL;
685 #endif
686 }
687
688 /* TODO: Optionally call a passphrase callback specified by the
689 * calling program
690 */
691 static int
passphrase_cb(char * buf,int size,int rwflag,char * passphrase)692 passphrase_cb(char *buf, int size, int rwflag, char *passphrase)
693 {
694 int passphrase_len = strlen(passphrase);
695 (void) rwflag;
696
697 if(passphrase_len > (size - 1)) {
698 passphrase_len = size - 1;
699 }
700 memcpy(buf, passphrase, passphrase_len);
701 buf[passphrase_len] = '\0';
702
703 return passphrase_len;
704 }
705
706 typedef void * (*pem_read_bio_func)(BIO *, void **, pem_password_cb *,
707 void *u);
708
709 static int
read_private_key_from_memory(void ** key_ctx,pem_read_bio_func read_private_key,const char * filedata,size_t filedata_len,unsigned const char * passphrase)710 read_private_key_from_memory(void **key_ctx,
711 pem_read_bio_func read_private_key,
712 const char *filedata,
713 size_t filedata_len,
714 unsigned const char *passphrase)
715 {
716 BIO * bp;
717
718 *key_ctx = NULL;
719
720 bp = BIO_new_mem_buf((char *)filedata, filedata_len);
721 if(!bp) {
722 return -1;
723 }
724 *key_ctx = read_private_key(bp, NULL, (pem_password_cb *) passphrase_cb,
725 (void *) passphrase);
726
727 BIO_free(bp);
728 return (*key_ctx) ? 0 : -1;
729 }
730
731
732
733 static int
read_private_key_from_file(void ** key_ctx,pem_read_bio_func read_private_key,const char * filename,unsigned const char * passphrase)734 read_private_key_from_file(void **key_ctx,
735 pem_read_bio_func read_private_key,
736 const char *filename,
737 unsigned const char *passphrase)
738 {
739 BIO * bp;
740
741 *key_ctx = NULL;
742
743 bp = BIO_new_file(filename, "r");
744 if(!bp) {
745 return -1;
746 }
747
748 *key_ctx = read_private_key(bp, NULL, (pem_password_cb *) passphrase_cb,
749 (void *) passphrase);
750
751 BIO_free(bp);
752 return (*key_ctx) ? 0 : -1;
753 }
754
755 int
_libssh2_rsa_new_private_frommemory(libssh2_rsa_ctx ** rsa,LIBSSH2_SESSION * session,const char * filedata,size_t filedata_len,unsigned const char * passphrase)756 _libssh2_rsa_new_private_frommemory(libssh2_rsa_ctx ** rsa,
757 LIBSSH2_SESSION * session,
758 const char *filedata, size_t filedata_len,
759 unsigned const char *passphrase)
760 {
761 int rc;
762
763 pem_read_bio_func read_rsa =
764 (pem_read_bio_func) &PEM_read_bio_RSAPrivateKey;
765 (void) session;
766
767 _libssh2_init_if_needed();
768
769 rc = read_private_key_from_memory((void **) rsa, read_rsa,
770 filedata, filedata_len, passphrase);
771
772 if(rc) {
773 rc = read_openssh_private_key_from_memory((void **)rsa, session,
774 "ssh-rsa", filedata, filedata_len, passphrase);
775 }
776
777 return rc;
778 }
779
780 static unsigned char *
gen_publickey_from_rsa(LIBSSH2_SESSION * session,RSA * rsa,size_t * key_len)781 gen_publickey_from_rsa(LIBSSH2_SESSION *session, RSA *rsa,
782 size_t *key_len)
783 {
784 int e_bytes, n_bytes;
785 unsigned long len;
786 unsigned char *key;
787 unsigned char *p;
788 const BIGNUM * e;
789 const BIGNUM * n;
790 #ifdef HAVE_OPAQUE_STRUCTS
791 RSA_get0_key(rsa, &n, &e, NULL);
792 #else
793 e = rsa->e;
794 n = rsa->n;
795 #endif
796 e_bytes = BN_num_bytes(e) + 1;
797 n_bytes = BN_num_bytes(n) + 1;
798
799 /* Key form is "ssh-rsa" + e + n. */
800 len = 4 + 7 + 4 + e_bytes + 4 + n_bytes;
801
802 key = LIBSSH2_ALLOC(session, len);
803 if(key == NULL) {
804 return NULL;
805 }
806
807 /* Process key encoding. */
808 p = key;
809
810 _libssh2_htonu32(p, 7); /* Key type. */
811 p += 4;
812 memcpy(p, "ssh-rsa", 7);
813 p += 7;
814
815 p = write_bn(p, e, e_bytes);
816 p = write_bn(p, n, n_bytes);
817
818 *key_len = (size_t)(p - key);
819 return key;
820 }
821
822 static int
gen_publickey_from_rsa_evp(LIBSSH2_SESSION * session,unsigned char ** method,size_t * method_len,unsigned char ** pubkeydata,size_t * pubkeydata_len,EVP_PKEY * pk)823 gen_publickey_from_rsa_evp(LIBSSH2_SESSION *session,
824 unsigned char **method,
825 size_t *method_len,
826 unsigned char **pubkeydata,
827 size_t *pubkeydata_len,
828 EVP_PKEY *pk)
829 {
830 RSA* rsa = NULL;
831 unsigned char *key;
832 unsigned char *method_buf = NULL;
833 size_t key_len;
834
835 _libssh2_debug(session,
836 LIBSSH2_TRACE_AUTH,
837 "Computing public key from RSA private key envelop");
838
839 rsa = EVP_PKEY_get1_RSA(pk);
840 if(rsa == NULL) {
841 /* Assume memory allocation error... what else could it be ? */
842 goto __alloc_error;
843 }
844
845 method_buf = LIBSSH2_ALLOC(session, 7); /* ssh-rsa. */
846 if(method_buf == NULL) {
847 goto __alloc_error;
848 }
849
850 key = gen_publickey_from_rsa(session, rsa, &key_len);
851 if(key == NULL) {
852 goto __alloc_error;
853 }
854 RSA_free(rsa);
855
856 memcpy(method_buf, "ssh-rsa", 7);
857 *method = method_buf;
858 *method_len = 7;
859 *pubkeydata = key;
860 *pubkeydata_len = key_len;
861 return 0;
862
863 __alloc_error:
864 if(rsa != NULL) {
865 RSA_free(rsa);
866 }
867 if(method_buf != NULL) {
868 LIBSSH2_FREE(session, method_buf);
869 }
870
871 return _libssh2_error(session,
872 LIBSSH2_ERROR_ALLOC,
873 "Unable to allocate memory for private key data");
874 }
875
_libssh2_rsa_new_additional_parameters(RSA * rsa)876 static int _libssh2_rsa_new_additional_parameters(RSA *rsa)
877 {
878 BN_CTX *ctx = NULL;
879 BIGNUM *aux = NULL;
880 BIGNUM *dmp1 = NULL;
881 BIGNUM *dmq1 = NULL;
882 const BIGNUM *p = NULL;
883 const BIGNUM *q = NULL;
884 const BIGNUM *d = NULL;
885 int rc = 0;
886
887 #ifdef HAVE_OPAQUE_STRUCTS
888 RSA_get0_key(rsa, NULL, NULL, &d);
889 RSA_get0_factors(rsa, &p, &q);
890 #else
891 d = (*rsa).d;
892 p = (*rsa).p;
893 q = (*rsa).q;
894 #endif
895
896 ctx = BN_CTX_new();
897 if(ctx == NULL)
898 return -1;
899
900 aux = BN_new();
901 if(aux == NULL) {
902 rc = -1;
903 goto out;
904 }
905
906 dmp1 = BN_new();
907 if(dmp1 == NULL) {
908 rc = -1;
909 goto out;
910 }
911
912 dmq1 = BN_new();
913 if(dmq1 == NULL) {
914 rc = -1;
915 goto out;
916 }
917
918 if((BN_sub(aux, q, BN_value_one()) == 0) ||
919 (BN_mod(dmq1, d, aux, ctx) == 0) ||
920 (BN_sub(aux, p, BN_value_one()) == 0) ||
921 (BN_mod(dmp1, d, aux, ctx) == 0)) {
922 rc = -1;
923 goto out;
924 }
925
926 #ifdef HAVE_OPAQUE_STRUCTS
927 RSA_set0_crt_params(rsa, dmp1, dmq1, NULL);
928 #else
929 (*rsa).dmp1 = dmp1;
930 (*rsa).dmq1 = dmq1;
931 #endif
932
933 out:
934 if(aux)
935 BN_clear_free(aux);
936 BN_CTX_free(ctx);
937
938 if(rc != 0) {
939 if(dmp1)
940 BN_clear_free(dmp1);
941 if(dmq1)
942 BN_clear_free(dmq1);
943 }
944
945 return rc;
946 }
947
948 static int
gen_publickey_from_rsa_openssh_priv_data(LIBSSH2_SESSION * session,struct string_buf * decrypted,unsigned char ** method,size_t * method_len,unsigned char ** pubkeydata,size_t * pubkeydata_len,libssh2_rsa_ctx ** rsa_ctx)949 gen_publickey_from_rsa_openssh_priv_data(LIBSSH2_SESSION *session,
950 struct string_buf *decrypted,
951 unsigned char **method,
952 size_t *method_len,
953 unsigned char **pubkeydata,
954 size_t *pubkeydata_len,
955 libssh2_rsa_ctx **rsa_ctx)
956 {
957 int rc = 0;
958 size_t nlen, elen, dlen, plen, qlen, coefflen, commentlen;
959 unsigned char *n, *e, *d, *p, *q, *coeff, *comment;
960 RSA *rsa = NULL;
961
962 _libssh2_debug(session,
963 LIBSSH2_TRACE_AUTH,
964 "Computing RSA keys from private key data");
965
966 /* public key data */
967 if(_libssh2_get_bignum_bytes(decrypted, &n, &nlen)) {
968 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
969 "RSA no n");
970 return -1;
971 }
972
973 if(_libssh2_get_bignum_bytes(decrypted, &e, &elen)) {
974 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
975 "RSA no e");
976 return -1;
977 }
978
979 /* private key data */
980 if(_libssh2_get_bignum_bytes(decrypted, &d, &dlen)) {
981 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
982 "RSA no d");
983 return -1;
984 }
985
986 if(_libssh2_get_bignum_bytes(decrypted, &coeff, &coefflen)) {
987 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
988 "RSA no coeff");
989 return -1;
990 }
991
992 if(_libssh2_get_bignum_bytes(decrypted, &p, &plen)) {
993 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
994 "RSA no p");
995 return -1;
996 }
997
998 if(_libssh2_get_bignum_bytes(decrypted, &q, &qlen)) {
999 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1000 "RSA no q");
1001 return -1;
1002 }
1003
1004 if(_libssh2_get_string(decrypted, &comment, &commentlen)) {
1005 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1006 "RSA no comment");
1007 return -1;
1008 }
1009
1010 if((rc = _libssh2_rsa_new(&rsa, e, elen, n, nlen, d, dlen, p, plen,
1011 q, qlen, NULL, 0, NULL, 0,
1012 coeff, coefflen)) != 0) {
1013 _libssh2_debug(session,
1014 LIBSSH2_TRACE_AUTH,
1015 "Could not create RSA private key");
1016 goto fail;
1017 }
1018
1019 if(rsa != NULL)
1020 rc = _libssh2_rsa_new_additional_parameters(rsa);
1021
1022 if(rsa != NULL && pubkeydata != NULL && method != NULL) {
1023 EVP_PKEY *pk = EVP_PKEY_new();
1024 EVP_PKEY_set1_RSA(pk, rsa);
1025
1026 rc = gen_publickey_from_rsa_evp(session, method, method_len,
1027 pubkeydata, pubkeydata_len,
1028 pk);
1029
1030 if(pk)
1031 EVP_PKEY_free(pk);
1032 }
1033
1034 if(rsa_ctx != NULL)
1035 *rsa_ctx = rsa;
1036 else
1037 RSA_free(rsa);
1038
1039 return rc;
1040
1041 fail:
1042
1043 if(rsa != NULL)
1044 RSA_free(rsa);
1045
1046 return _libssh2_error(session,
1047 LIBSSH2_ERROR_ALLOC,
1048 "Unable to allocate memory for private key data");
1049 }
1050
1051 static int
_libssh2_rsa_new_openssh_private(libssh2_rsa_ctx ** rsa,LIBSSH2_SESSION * session,const char * filename,unsigned const char * passphrase)1052 _libssh2_rsa_new_openssh_private(libssh2_rsa_ctx ** rsa,
1053 LIBSSH2_SESSION * session,
1054 const char *filename,
1055 unsigned const char *passphrase)
1056 {
1057 FILE *fp;
1058 int rc;
1059 unsigned char *buf = NULL;
1060 struct string_buf *decrypted = NULL;
1061
1062 if(session == NULL) {
1063 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1064 "Session is required");
1065 return -1;
1066 }
1067
1068 _libssh2_init_if_needed();
1069
1070 fp = fopen(filename, "r");
1071 if(!fp) {
1072 _libssh2_error(session, LIBSSH2_ERROR_FILE,
1073 "Unable to open OpenSSH RSA private key file");
1074 return -1;
1075 }
1076
1077 rc = _libssh2_openssh_pem_parse(session, passphrase, fp, &decrypted);
1078 fclose(fp);
1079 if(rc) {
1080 return rc;
1081 }
1082
1083 /* We have a new key file, now try and parse it using supported types */
1084 rc = _libssh2_get_string(decrypted, &buf, NULL);
1085
1086 if(rc != 0 || buf == NULL) {
1087 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1088 "Public key type in decrypted key data not found");
1089 return -1;
1090 }
1091
1092 if(strcmp("ssh-rsa", (const char *)buf) == 0) {
1093 rc = gen_publickey_from_rsa_openssh_priv_data(session, decrypted,
1094 NULL, 0,
1095 NULL, 0, rsa);
1096 }
1097 else {
1098 rc = -1;
1099 }
1100
1101 if(decrypted)
1102 _libssh2_string_buf_free(session, decrypted);
1103
1104 return rc;
1105 }
1106
1107 int
_libssh2_rsa_new_private(libssh2_rsa_ctx ** rsa,LIBSSH2_SESSION * session,const char * filename,unsigned const char * passphrase)1108 _libssh2_rsa_new_private(libssh2_rsa_ctx ** rsa,
1109 LIBSSH2_SESSION * session,
1110 const char *filename, unsigned const char *passphrase)
1111 {
1112 int rc;
1113
1114 pem_read_bio_func read_rsa =
1115 (pem_read_bio_func) &PEM_read_bio_RSAPrivateKey;
1116 (void) session;
1117
1118 _libssh2_init_if_needed();
1119
1120 rc = read_private_key_from_file((void **) rsa, read_rsa,
1121 filename, passphrase);
1122
1123 if(rc) {
1124 rc = _libssh2_rsa_new_openssh_private(rsa, session,
1125 filename, passphrase);
1126 }
1127
1128 return rc;
1129 }
1130
1131 #if LIBSSH2_DSA
1132 int
_libssh2_dsa_new_private_frommemory(libssh2_dsa_ctx ** dsa,LIBSSH2_SESSION * session,const char * filedata,size_t filedata_len,unsigned const char * passphrase)1133 _libssh2_dsa_new_private_frommemory(libssh2_dsa_ctx ** dsa,
1134 LIBSSH2_SESSION * session,
1135 const char *filedata, size_t filedata_len,
1136 unsigned const char *passphrase)
1137 {
1138 int rc;
1139
1140 pem_read_bio_func read_dsa =
1141 (pem_read_bio_func) &PEM_read_bio_DSAPrivateKey;
1142 (void) session;
1143
1144 _libssh2_init_if_needed();
1145
1146 rc = read_private_key_from_memory((void **)dsa, read_dsa,
1147 filedata, filedata_len, passphrase);
1148
1149 if(rc) {
1150 rc = read_openssh_private_key_from_memory((void **)dsa, session,
1151 "ssh-dsa", filedata, filedata_len, passphrase);
1152 }
1153
1154 return rc;
1155 }
1156
1157 static unsigned char *
gen_publickey_from_dsa(LIBSSH2_SESSION * session,DSA * dsa,size_t * key_len)1158 gen_publickey_from_dsa(LIBSSH2_SESSION* session, DSA *dsa,
1159 size_t *key_len)
1160 {
1161 int p_bytes, q_bytes, g_bytes, k_bytes;
1162 unsigned long len;
1163 unsigned char *key;
1164 unsigned char *p;
1165
1166 const BIGNUM * p_bn;
1167 const BIGNUM * q;
1168 const BIGNUM * g;
1169 const BIGNUM * pub_key;
1170 #ifdef HAVE_OPAQUE_STRUCTS
1171 DSA_get0_pqg(dsa, &p_bn, &q, &g);
1172 #else
1173 p_bn = dsa->p;
1174 q = dsa->q;
1175 g = dsa->g;
1176 #endif
1177
1178 #ifdef HAVE_OPAQUE_STRUCTS
1179 DSA_get0_key(dsa, &pub_key, NULL);
1180 #else
1181 pub_key = dsa->pub_key;
1182 #endif
1183 p_bytes = BN_num_bytes(p_bn) + 1;
1184 q_bytes = BN_num_bytes(q) + 1;
1185 g_bytes = BN_num_bytes(g) + 1;
1186 k_bytes = BN_num_bytes(pub_key) + 1;
1187
1188 /* Key form is "ssh-dss" + p + q + g + pub_key. */
1189 len = 4 + 7 + 4 + p_bytes + 4 + q_bytes + 4 + g_bytes + 4 + k_bytes;
1190
1191 key = LIBSSH2_ALLOC(session, len);
1192 if(key == NULL) {
1193 return NULL;
1194 }
1195
1196 /* Process key encoding. */
1197 p = key;
1198
1199 _libssh2_htonu32(p, 7); /* Key type. */
1200 p += 4;
1201 memcpy(p, "ssh-dss", 7);
1202 p += 7;
1203
1204 p = write_bn(p, p_bn, p_bytes);
1205 p = write_bn(p, q, q_bytes);
1206 p = write_bn(p, g, g_bytes);
1207 p = write_bn(p, pub_key, k_bytes);
1208
1209 *key_len = (size_t)(p - key);
1210 return key;
1211 }
1212
1213 static int
gen_publickey_from_dsa_evp(LIBSSH2_SESSION * session,unsigned char ** method,size_t * method_len,unsigned char ** pubkeydata,size_t * pubkeydata_len,EVP_PKEY * pk)1214 gen_publickey_from_dsa_evp(LIBSSH2_SESSION *session,
1215 unsigned char **method,
1216 size_t *method_len,
1217 unsigned char **pubkeydata,
1218 size_t *pubkeydata_len,
1219 EVP_PKEY *pk)
1220 {
1221 DSA* dsa = NULL;
1222 unsigned char *key;
1223 unsigned char *method_buf = NULL;
1224 size_t key_len;
1225
1226 _libssh2_debug(session,
1227 LIBSSH2_TRACE_AUTH,
1228 "Computing public key from DSA private key envelop");
1229
1230 dsa = EVP_PKEY_get1_DSA(pk);
1231 if(dsa == NULL) {
1232 /* Assume memory allocation error... what else could it be ? */
1233 goto __alloc_error;
1234 }
1235
1236 method_buf = LIBSSH2_ALLOC(session, 7); /* ssh-dss. */
1237 if(method_buf == NULL) {
1238 goto __alloc_error;
1239 }
1240
1241 key = gen_publickey_from_dsa(session, dsa, &key_len);
1242 if(key == NULL) {
1243 goto __alloc_error;
1244 }
1245 DSA_free(dsa);
1246
1247 memcpy(method_buf, "ssh-dss", 7);
1248 *method = method_buf;
1249 *method_len = 7;
1250 *pubkeydata = key;
1251 *pubkeydata_len = key_len;
1252 return 0;
1253
1254 __alloc_error:
1255 if(dsa != NULL) {
1256 DSA_free(dsa);
1257 }
1258 if(method_buf != NULL) {
1259 LIBSSH2_FREE(session, method_buf);
1260 }
1261
1262 return _libssh2_error(session,
1263 LIBSSH2_ERROR_ALLOC,
1264 "Unable to allocate memory for private key data");
1265 }
1266
1267 static int
gen_publickey_from_dsa_openssh_priv_data(LIBSSH2_SESSION * session,struct string_buf * decrypted,unsigned char ** method,size_t * method_len,unsigned char ** pubkeydata,size_t * pubkeydata_len,libssh2_dsa_ctx ** dsa_ctx)1268 gen_publickey_from_dsa_openssh_priv_data(LIBSSH2_SESSION *session,
1269 struct string_buf *decrypted,
1270 unsigned char **method,
1271 size_t *method_len,
1272 unsigned char **pubkeydata,
1273 size_t *pubkeydata_len,
1274 libssh2_dsa_ctx **dsa_ctx)
1275 {
1276 int rc = 0;
1277 size_t plen, qlen, glen, pub_len, priv_len;
1278 unsigned char *p, *q, *g, *pub_key, *priv_key;
1279 DSA *dsa = NULL;
1280
1281 _libssh2_debug(session,
1282 LIBSSH2_TRACE_AUTH,
1283 "Computing DSA keys from private key data");
1284
1285 if(_libssh2_get_bignum_bytes(decrypted, &p, &plen)) {
1286 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1287 "DSA no p");
1288 return -1;
1289 }
1290
1291 if(_libssh2_get_bignum_bytes(decrypted, &q, &qlen)) {
1292 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1293 "DSA no q");
1294 return -1;
1295 }
1296
1297 if(_libssh2_get_bignum_bytes(decrypted, &g, &glen)) {
1298 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1299 "DSA no g");
1300 return -1;
1301 }
1302
1303 if(_libssh2_get_bignum_bytes(decrypted, &pub_key, &pub_len)) {
1304 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1305 "DSA no public key");
1306 return -1;
1307 }
1308
1309 if(_libssh2_get_bignum_bytes(decrypted, &priv_key, &priv_len)) {
1310 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1311 "DSA no private key");
1312 return -1;
1313 }
1314
1315 rc = _libssh2_dsa_new(&dsa, p, plen, q, qlen, g, glen, pub_key, pub_len,
1316 priv_key, priv_len);
1317 if(rc != 0) {
1318 _libssh2_debug(session,
1319 LIBSSH2_ERROR_PROTO,
1320 "Could not create DSA private key");
1321 goto fail;
1322 }
1323
1324 if(dsa != NULL && pubkeydata != NULL && method != NULL) {
1325 EVP_PKEY *pk = EVP_PKEY_new();
1326 EVP_PKEY_set1_DSA(pk, dsa);
1327
1328 rc = gen_publickey_from_dsa_evp(session, method, method_len,
1329 pubkeydata, pubkeydata_len,
1330 pk);
1331
1332 if(pk)
1333 EVP_PKEY_free(pk);
1334 }
1335
1336 if(dsa_ctx != NULL)
1337 *dsa_ctx = dsa;
1338 else
1339 DSA_free(dsa);
1340
1341 return rc;
1342
1343 fail:
1344
1345 if(dsa != NULL)
1346 DSA_free(dsa);
1347
1348 return _libssh2_error(session,
1349 LIBSSH2_ERROR_ALLOC,
1350 "Unable to allocate memory for private key data");
1351 }
1352
1353 static int
_libssh2_dsa_new_openssh_private(libssh2_dsa_ctx ** dsa,LIBSSH2_SESSION * session,const char * filename,unsigned const char * passphrase)1354 _libssh2_dsa_new_openssh_private(libssh2_dsa_ctx ** dsa,
1355 LIBSSH2_SESSION * session,
1356 const char *filename,
1357 unsigned const char *passphrase)
1358 {
1359 FILE *fp;
1360 int rc;
1361 unsigned char *buf = NULL;
1362 struct string_buf *decrypted = NULL;
1363
1364 if(session == NULL) {
1365 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1366 "Session is required");
1367 return -1;
1368 }
1369
1370 _libssh2_init_if_needed();
1371
1372 fp = fopen(filename, "r");
1373 if(!fp) {
1374 _libssh2_error(session, LIBSSH2_ERROR_FILE,
1375 "Unable to open OpenSSH DSA private key file");
1376 return -1;
1377 }
1378
1379 rc = _libssh2_openssh_pem_parse(session, passphrase, fp, &decrypted);
1380 fclose(fp);
1381 if(rc) {
1382 return rc;
1383 }
1384
1385 /* We have a new key file, now try and parse it using supported types */
1386 rc = _libssh2_get_string(decrypted, &buf, NULL);
1387
1388 if(rc != 0 || buf == NULL) {
1389 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1390 "Public key type in decrypted key data not found");
1391 return -1;
1392 }
1393
1394 if(strcmp("ssh-dss", (const char *)buf) == 0) {
1395 rc = gen_publickey_from_dsa_openssh_priv_data(session, decrypted,
1396 NULL, 0,
1397 NULL, 0, dsa);
1398 }
1399 else {
1400 rc = -1;
1401 }
1402
1403 if(decrypted)
1404 _libssh2_string_buf_free(session, decrypted);
1405
1406 return rc;
1407 }
1408
1409 int
_libssh2_dsa_new_private(libssh2_dsa_ctx ** dsa,LIBSSH2_SESSION * session,const char * filename,unsigned const char * passphrase)1410 _libssh2_dsa_new_private(libssh2_dsa_ctx ** dsa,
1411 LIBSSH2_SESSION * session,
1412 const char *filename, unsigned const char *passphrase)
1413 {
1414 int rc;
1415
1416 pem_read_bio_func read_dsa =
1417 (pem_read_bio_func) &PEM_read_bio_DSAPrivateKey;
1418 (void) session;
1419
1420 _libssh2_init_if_needed();
1421
1422 rc = read_private_key_from_file((void **) dsa, read_dsa,
1423 filename, passphrase);
1424
1425 if(rc) {
1426 rc = _libssh2_dsa_new_openssh_private(dsa, session,
1427 filename, passphrase);
1428 }
1429
1430 return rc;
1431 }
1432
1433 #endif /* LIBSSH_DSA */
1434
1435 #if LIBSSH2_ECDSA
1436
1437 int
_libssh2_ecdsa_new_private_frommemory(libssh2_ecdsa_ctx ** ec_ctx,LIBSSH2_SESSION * session,const char * filedata,size_t filedata_len,unsigned const char * passphrase)1438 _libssh2_ecdsa_new_private_frommemory(libssh2_ecdsa_ctx ** ec_ctx,
1439 LIBSSH2_SESSION * session,
1440 const char *filedata, size_t filedata_len,
1441 unsigned const char *passphrase)
1442 {
1443 int rc;
1444
1445 pem_read_bio_func read_ec =
1446 (pem_read_bio_func) &PEM_read_bio_ECPrivateKey;
1447 (void) session;
1448
1449 _libssh2_init_if_needed();
1450
1451 rc = read_private_key_from_memory((void **) ec_ctx, read_ec,
1452 filedata, filedata_len, passphrase);
1453
1454 if(rc) {
1455 rc = read_openssh_private_key_from_memory((void **)ec_ctx, session,
1456 "ssh-ecdsa", filedata,
1457 filedata_len, passphrase);
1458 }
1459
1460 return rc;
1461 }
1462
1463 #endif /* LIBSSH2_ECDSA */
1464
1465
1466 #if LIBSSH2_ED25519
1467
1468 int
_libssh2_curve25519_new(LIBSSH2_SESSION * session,libssh2_x25519_ctx ** out_ctx,unsigned char ** out_public_key,unsigned char ** out_private_key)1469 _libssh2_curve25519_new(LIBSSH2_SESSION *session, libssh2_x25519_ctx **out_ctx,
1470 unsigned char **out_public_key,
1471 unsigned char **out_private_key)
1472 {
1473 EVP_PKEY *key = NULL;
1474 EVP_PKEY_CTX *pctx = NULL;
1475 PKCS8_PRIV_KEY_INFO *info = NULL;
1476 ASN1_OCTET_STRING *oct = NULL;
1477 X509_PUBKEY *pubkey = NULL;
1478 libssh2_ed25519_ctx *ctx = NULL;
1479 const unsigned char *pkcs, *priv, *pub;
1480 int privLen, pubLen, pkcsLen;
1481 int rc = -1;
1482
1483 pctx = EVP_PKEY_CTX_new_id(EVP_PKEY_X25519, NULL);
1484 if(pctx == NULL)
1485 return -1;
1486
1487 EVP_PKEY_keygen_init(pctx);
1488 EVP_PKEY_keygen(pctx, &key);
1489 info = EVP_PKEY2PKCS8(key);
1490
1491 if(info == NULL || !PKCS8_pkey_get0(NULL, &pkcs, &pkcsLen, NULL, info))
1492 goto cleanExit;
1493
1494 oct = d2i_ASN1_OCTET_STRING(NULL, &pkcs, pkcsLen);
1495 if(oct == NULL) {
1496 goto cleanExit;
1497 }
1498
1499 priv = ASN1_STRING_get0_data(oct);
1500 privLen = ASN1_STRING_length(oct);
1501
1502 if(privLen != LIBSSH2_ED25519_KEY_LEN)
1503 goto cleanExit;
1504
1505 pubkey = X509_PUBKEY_new();
1506 if(pubkey == NULL || !X509_PUBKEY_set(&pubkey, key))
1507 goto cleanExit;
1508
1509 if(!X509_PUBKEY_get0_param(NULL, &pub, &pubLen, NULL, pubkey))
1510 goto cleanExit;
1511
1512 if(pubLen != LIBSSH2_ED25519_KEY_LEN)
1513 goto cleanExit;
1514
1515 if(out_private_key != NULL) {
1516 *out_private_key = LIBSSH2_ALLOC(session, LIBSSH2_ED25519_KEY_LEN);
1517 if(*out_private_key == NULL)
1518 goto cleanExit;
1519
1520 memcpy(*out_private_key, priv, LIBSSH2_ED25519_KEY_LEN);
1521 }
1522
1523 if(out_public_key != NULL) {
1524 *out_public_key = LIBSSH2_ALLOC(session, LIBSSH2_ED25519_KEY_LEN);
1525 if(*out_public_key == NULL)
1526 goto cleanExit;
1527
1528 memcpy(*out_public_key, pub, LIBSSH2_ED25519_KEY_LEN);
1529 }
1530
1531 if(out_ctx != NULL) {
1532 ctx = malloc(sizeof(libssh2_x25519_ctx));
1533 if(ctx == NULL)
1534 goto cleanExit;
1535
1536 ctx->private_key =
1537 EVP_PKEY_new_raw_private_key(EVP_PKEY_X25519, NULL,
1538 (const unsigned char *)priv,
1539 LIBSSH2_ED25519_KEY_LEN);
1540
1541 ctx->public_key =
1542 EVP_PKEY_new_raw_public_key(EVP_PKEY_X25519, NULL,
1543 (const unsigned char *)pub,
1544 LIBSSH2_ED25519_KEY_LEN);
1545
1546 if(ctx->public_key == NULL || ctx->private_key == NULL) {
1547 _libssh2_x25519_free(ctx);
1548 goto cleanExit;
1549 }
1550
1551 *out_ctx = ctx;
1552 }
1553
1554 /* success */
1555 rc = 0;
1556
1557 cleanExit:
1558
1559 if(info)
1560 PKCS8_PRIV_KEY_INFO_free(info);
1561 if(pctx)
1562 EVP_PKEY_CTX_free(pctx);
1563 if(oct)
1564 ASN1_OCTET_STRING_free(oct);
1565 if(pubkey)
1566 X509_PUBKEY_free(pubkey);
1567 if(key)
1568 EVP_PKEY_free(key);
1569
1570 return rc;
1571 }
1572
1573 static int
gen_publickey_from_ed25519_openssh_priv_data(LIBSSH2_SESSION * session,struct string_buf * decrypted,unsigned char ** method,size_t * method_len,unsigned char ** pubkeydata,size_t * pubkeydata_len,libssh2_ed25519_ctx ** out_ctx)1574 gen_publickey_from_ed25519_openssh_priv_data(LIBSSH2_SESSION *session,
1575 struct string_buf *decrypted,
1576 unsigned char **method,
1577 size_t *method_len,
1578 unsigned char **pubkeydata,
1579 size_t *pubkeydata_len,
1580 libssh2_ed25519_ctx **out_ctx)
1581 {
1582 libssh2_ed25519_ctx *ctx = NULL;
1583 unsigned char *method_buf = NULL;
1584 unsigned char *key = NULL;
1585 int i, ret = 0;
1586 unsigned char *pub_key, *priv_key, *buf;
1587 size_t key_len = 0, tmp_len = 0;
1588 unsigned char *p;
1589
1590 _libssh2_debug(session,
1591 LIBSSH2_TRACE_AUTH,
1592 "Computing ED25519 keys from private key data");
1593
1594 if(_libssh2_get_string(decrypted, &pub_key, &tmp_len) ||
1595 tmp_len != LIBSSH2_ED25519_KEY_LEN) {
1596 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1597 "Wrong public key length");
1598 return -1;
1599 }
1600
1601 if(_libssh2_get_string(decrypted, &priv_key, &tmp_len) ||
1602 tmp_len != LIBSSH2_ED25519_PRIVATE_KEY_LEN) {
1603 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1604 "Wrong private key length");
1605 ret = -1;
1606 goto clean_exit;
1607 }
1608
1609 ctx = _libssh2_ed25519_new_ctx();
1610 if(ctx == NULL) {
1611 _libssh2_error(session, LIBSSH2_ERROR_ALLOC,
1612 "Unable to allocate memory for ed25519 key");
1613 ret = -1;
1614 goto clean_exit;
1615 }
1616
1617 /* first 32 bytes of priv_key is the private key, the last 32 bytes are
1618 the public key */
1619 ctx->private_key =
1620 EVP_PKEY_new_raw_private_key(EVP_PKEY_ED25519, NULL,
1621 (const unsigned char *)priv_key,
1622 LIBSSH2_ED25519_KEY_LEN);
1623
1624 ctx->public_key =
1625 EVP_PKEY_new_raw_public_key(EVP_PKEY_ED25519, NULL,
1626 (const unsigned char *)pub_key,
1627 LIBSSH2_ED25519_KEY_LEN);
1628
1629 /* comment */
1630 if(_libssh2_get_string(decrypted, &buf, &tmp_len)) {
1631 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1632 "Unable to read comment");
1633 ret = -1;
1634 goto clean_exit;
1635 }
1636
1637 if(tmp_len > 0) {
1638 unsigned char *comment = LIBSSH2_CALLOC(session, tmp_len + 1);
1639 if(comment != NULL) {
1640 memcpy(comment, buf, tmp_len);
1641 memcpy(comment + tmp_len, "\0", 1);
1642
1643 _libssh2_debug(session, LIBSSH2_TRACE_AUTH, "Key comment: %s",
1644 comment);
1645
1646 LIBSSH2_FREE(session, comment);
1647 }
1648 }
1649
1650 /* Padding */
1651 i = 1;
1652 while(decrypted->dataptr < decrypted->data + decrypted->len) {
1653 if(*decrypted->dataptr != i) {
1654 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1655 "Wrong padding");
1656 ret = -1;
1657 goto clean_exit;
1658 }
1659 i++;
1660 decrypted->dataptr++;
1661 }
1662
1663 if(ret == 0) {
1664 _libssh2_debug(session,
1665 LIBSSH2_TRACE_AUTH,
1666 "Computing public key from ED25519 "
1667 "private key envelop");
1668
1669 method_buf = LIBSSH2_ALLOC(session, 11); /* ssh-ed25519. */
1670 if(method_buf == NULL) {
1671 goto clean_exit;
1672 }
1673
1674 /* Key form is: type_len(4) + type(11) + pub_key_len(4) +
1675 pub_key(32). */
1676 key_len = LIBSSH2_ED25519_KEY_LEN + 19;
1677 key = LIBSSH2_CALLOC(session, key_len);
1678 if(key == NULL) {
1679 goto clean_exit;
1680 }
1681
1682 p = key;
1683
1684 _libssh2_store_str(&p, "ssh-ed25519", 11);
1685 _libssh2_store_str(&p, (const char *)pub_key, LIBSSH2_ED25519_KEY_LEN);
1686
1687 memcpy(method_buf, "ssh-ed25519", 11);
1688
1689 if(method != NULL)
1690 *method = method_buf;
1691 else
1692 LIBSSH2_FREE(session, method_buf);
1693
1694 if(method_len != NULL)
1695 *method_len = 11;
1696
1697 if(pubkeydata != NULL)
1698 *pubkeydata = key;
1699 else
1700 LIBSSH2_FREE(session, key);
1701
1702 if(pubkeydata_len != NULL)
1703 *pubkeydata_len = key_len;
1704
1705 if(out_ctx != NULL)
1706 *out_ctx = ctx;
1707 else if(ctx != NULL)
1708 _libssh2_ed25519_free(ctx);
1709
1710 return 0;
1711 }
1712
1713 clean_exit:
1714
1715 if(ctx)
1716 _libssh2_ed25519_free(ctx);
1717
1718 if(method_buf)
1719 LIBSSH2_FREE(session, method_buf);
1720
1721 if(key)
1722 LIBSSH2_FREE(session, key);
1723
1724 return -1;
1725 }
1726
1727 int
_libssh2_ed25519_new_private(libssh2_ed25519_ctx ** ed_ctx,LIBSSH2_SESSION * session,const char * filename,const uint8_t * passphrase)1728 _libssh2_ed25519_new_private(libssh2_ed25519_ctx ** ed_ctx,
1729 LIBSSH2_SESSION * session,
1730 const char *filename, const uint8_t *passphrase)
1731 {
1732 int rc;
1733 FILE *fp;
1734 unsigned char *buf;
1735 struct string_buf *decrypted = NULL;
1736 libssh2_ed25519_ctx *ctx = NULL;
1737
1738 if(session == NULL) {
1739 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1740 "Session is required");
1741 return -1;
1742 }
1743
1744 _libssh2_init_if_needed();
1745
1746 fp = fopen(filename, "r");
1747 if(!fp) {
1748 _libssh2_error(session, LIBSSH2_ERROR_FILE,
1749 "Unable to open ED25519 private key file");
1750 return -1;
1751 }
1752
1753 rc = _libssh2_openssh_pem_parse(session, passphrase, fp, &decrypted);
1754 fclose(fp);
1755 if(rc) {
1756 return rc;
1757 }
1758
1759 /* We have a new key file, now try and parse it using supported types */
1760 rc = _libssh2_get_string(decrypted, &buf, NULL);
1761
1762 if(rc != 0 || buf == NULL) {
1763 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1764 "Public key type in decrypted key data not found");
1765 return -1;
1766 }
1767
1768 if(strcmp("ssh-ed25519", (const char *)buf) == 0) {
1769 rc = gen_publickey_from_ed25519_openssh_priv_data(session,
1770 decrypted,
1771 NULL,
1772 NULL,
1773 NULL,
1774 NULL,
1775 &ctx);
1776 }
1777 else {
1778 rc = -1;
1779 }
1780
1781 if(decrypted)
1782 _libssh2_string_buf_free(session, decrypted);
1783
1784 if(rc == 0) {
1785 if(ed_ctx != NULL)
1786 *ed_ctx = ctx;
1787 else if(ctx != NULL)
1788 _libssh2_ed25519_free(ctx);
1789 }
1790
1791 return rc;
1792 }
1793
1794 int
_libssh2_ed25519_new_private_frommemory(libssh2_ed25519_ctx ** ed_ctx,LIBSSH2_SESSION * session,const char * filedata,size_t filedata_len,unsigned const char * passphrase)1795 _libssh2_ed25519_new_private_frommemory(libssh2_ed25519_ctx ** ed_ctx,
1796 LIBSSH2_SESSION * session,
1797 const char *filedata,
1798 size_t filedata_len,
1799 unsigned const char *passphrase)
1800 {
1801 return read_openssh_private_key_from_memory((void **)ed_ctx, session,
1802 "ssh-ed25519",
1803 filedata, filedata_len,
1804 passphrase);
1805 }
1806
1807 int
_libssh2_ed25519_new_public(libssh2_ed25519_ctx ** ed_ctx,LIBSSH2_SESSION * session,const unsigned char * raw_pub_key,const uint8_t key_len)1808 _libssh2_ed25519_new_public(libssh2_ed25519_ctx ** ed_ctx,
1809 LIBSSH2_SESSION * session,
1810 const unsigned char *raw_pub_key,
1811 const uint8_t key_len)
1812 {
1813 libssh2_ed25519_ctx *ctx = NULL;
1814 EVP_PKEY *public_key = NULL;
1815
1816 if(ed_ctx == NULL)
1817 return -1;
1818
1819 public_key =
1820 EVP_PKEY_new_raw_public_key(EVP_PKEY_ED25519, NULL,
1821 (const unsigned char *)raw_pub_key,
1822 key_len);
1823 if(public_key == NULL) {
1824 return _libssh2_error(session, LIBSSH2_ERROR_PROTO,
1825 "could not create ED25519 public key");
1826 }
1827
1828 ctx = _libssh2_ed25519_new_ctx();
1829 if(ctx == NULL) {
1830 return _libssh2_error(session, LIBSSH2_ERROR_ALLOC,
1831 "could not alloc public/private key");
1832 }
1833
1834 ctx->public_key = public_key;
1835
1836 if(ed_ctx != NULL)
1837 *ed_ctx = ctx;
1838 else if(ctx != NULL)
1839 _libssh2_ed25519_free(ctx);
1840
1841 return 0;
1842 }
1843
1844 #endif /* LIBSSH2_ED25519 */
1845
1846 int
_libssh2_rsa_sha1_sign(LIBSSH2_SESSION * session,libssh2_rsa_ctx * rsactx,const unsigned char * hash,size_t hash_len,unsigned char ** signature,size_t * signature_len)1847 _libssh2_rsa_sha1_sign(LIBSSH2_SESSION * session,
1848 libssh2_rsa_ctx * rsactx,
1849 const unsigned char *hash,
1850 size_t hash_len,
1851 unsigned char **signature, size_t *signature_len)
1852 {
1853 int ret;
1854 unsigned char *sig;
1855 unsigned int sig_len;
1856
1857 sig_len = RSA_size(rsactx);
1858 sig = LIBSSH2_ALLOC(session, sig_len);
1859
1860 if(!sig) {
1861 return -1;
1862 }
1863
1864 ret = RSA_sign(NID_sha1, hash, hash_len, sig, &sig_len, rsactx);
1865
1866 if(!ret) {
1867 LIBSSH2_FREE(session, sig);
1868 return -1;
1869 }
1870
1871 *signature = sig;
1872 *signature_len = sig_len;
1873
1874 return 0;
1875 }
1876
1877 #if LIBSSH2_DSA
1878 int
_libssh2_dsa_sha1_sign(libssh2_dsa_ctx * dsactx,const unsigned char * hash,unsigned long hash_len,unsigned char * signature)1879 _libssh2_dsa_sha1_sign(libssh2_dsa_ctx * dsactx,
1880 const unsigned char *hash,
1881 unsigned long hash_len, unsigned char *signature)
1882 {
1883 DSA_SIG *sig;
1884 const BIGNUM * r;
1885 const BIGNUM * s;
1886 int r_len, s_len;
1887 (void) hash_len;
1888
1889 sig = DSA_do_sign(hash, SHA_DIGEST_LENGTH, dsactx);
1890 if(!sig) {
1891 return -1;
1892 }
1893
1894 #ifdef HAVE_OPAQUE_STRUCTS
1895 DSA_SIG_get0(sig, &r, &s);
1896 #else
1897 r = sig->r;
1898 s = sig->s;
1899 #endif
1900 r_len = BN_num_bytes(r);
1901 if(r_len < 1 || r_len > 20) {
1902 DSA_SIG_free(sig);
1903 return -1;
1904 }
1905 s_len = BN_num_bytes(s);
1906 if(s_len < 1 || s_len > 20) {
1907 DSA_SIG_free(sig);
1908 return -1;
1909 }
1910
1911 memset(signature, 0, 40);
1912
1913 BN_bn2bin(r, signature + (20 - r_len));
1914 BN_bn2bin(s, signature + 20 + (20 - s_len));
1915
1916 DSA_SIG_free(sig);
1917
1918 return 0;
1919 }
1920 #endif /* LIBSSH_DSA */
1921
1922 #if LIBSSH2_ECDSA
1923
1924 int
_libssh2_ecdsa_sign(LIBSSH2_SESSION * session,libssh2_ecdsa_ctx * ec_ctx,const unsigned char * hash,unsigned long hash_len,unsigned char ** signature,size_t * signature_len)1925 _libssh2_ecdsa_sign(LIBSSH2_SESSION * session, libssh2_ecdsa_ctx * ec_ctx,
1926 const unsigned char *hash, unsigned long hash_len,
1927 unsigned char **signature, size_t *signature_len)
1928 {
1929 int r_len, s_len;
1930 int rc = 0;
1931 size_t out_buffer_len = 0;
1932 unsigned char *sp;
1933 const BIGNUM *pr = NULL, *ps = NULL;
1934 unsigned char *temp_buffer = NULL;
1935 unsigned char *out_buffer = NULL;
1936
1937 ECDSA_SIG *sig = ECDSA_do_sign(hash, hash_len, ec_ctx);
1938 if(sig == NULL)
1939 return -1;
1940 #ifdef HAVE_OPAQUE_STRUCTS
1941 ECDSA_SIG_get0(sig, &pr, &ps);
1942 #else
1943 pr = sig->r;
1944 ps = sig->s;
1945 #endif
1946
1947 r_len = BN_num_bytes(pr) + 1;
1948 s_len = BN_num_bytes(ps) + 1;
1949
1950 temp_buffer = malloc(r_len + s_len + 8);
1951 if(temp_buffer == NULL) {
1952 rc = -1;
1953 goto clean_exit;
1954 }
1955
1956 sp = temp_buffer;
1957 sp = write_bn(sp, pr, r_len);
1958 sp = write_bn(sp, ps, s_len);
1959
1960 out_buffer_len = (size_t)(sp - temp_buffer);
1961
1962 out_buffer = LIBSSH2_CALLOC(session, out_buffer_len);
1963 if(out_buffer == NULL) {
1964 rc = -1;
1965 goto clean_exit;
1966 }
1967
1968 memcpy(out_buffer, temp_buffer, out_buffer_len);
1969
1970 *signature = out_buffer;
1971 *signature_len = out_buffer_len;
1972
1973 clean_exit:
1974
1975 if(temp_buffer != NULL)
1976 free(temp_buffer);
1977
1978 if(sig)
1979 ECDSA_SIG_free(sig);
1980
1981 return rc;
1982 }
1983 #endif /* LIBSSH2_ECDSA */
1984
1985 int
_libssh2_sha1_init(libssh2_sha1_ctx * ctx)1986 _libssh2_sha1_init(libssh2_sha1_ctx *ctx)
1987 {
1988 #ifdef HAVE_OPAQUE_STRUCTS
1989 *ctx = EVP_MD_CTX_new();
1990
1991 if(*ctx == NULL)
1992 return 0;
1993
1994 if(EVP_DigestInit(*ctx, EVP_get_digestbyname("sha1")))
1995 return 1;
1996
1997 EVP_MD_CTX_free(*ctx);
1998 *ctx = NULL;
1999
2000 return 0;
2001 #else
2002 EVP_MD_CTX_init(ctx);
2003 return EVP_DigestInit(ctx, EVP_get_digestbyname("sha1"));
2004 #endif
2005 }
2006
2007 int
_libssh2_sha1(const unsigned char * message,unsigned long len,unsigned char * out)2008 _libssh2_sha1(const unsigned char *message, unsigned long len,
2009 unsigned char *out)
2010 {
2011 #ifdef HAVE_OPAQUE_STRUCTS
2012 EVP_MD_CTX * ctx = EVP_MD_CTX_new();
2013
2014 if(ctx == NULL)
2015 return 1; /* error */
2016
2017 if(EVP_DigestInit(ctx, EVP_get_digestbyname("sha1"))) {
2018 EVP_DigestUpdate(ctx, message, len);
2019 EVP_DigestFinal(ctx, out, NULL);
2020 EVP_MD_CTX_free(ctx);
2021 return 0; /* success */
2022 }
2023 EVP_MD_CTX_free(ctx);
2024 #else
2025 EVP_MD_CTX ctx;
2026
2027 EVP_MD_CTX_init(&ctx);
2028 if(EVP_DigestInit(&ctx, EVP_get_digestbyname("sha1"))) {
2029 EVP_DigestUpdate(&ctx, message, len);
2030 EVP_DigestFinal(&ctx, out, NULL);
2031 return 0; /* success */
2032 }
2033 #endif
2034 return 1; /* error */
2035 }
2036
2037 int
_libssh2_sha256_init(libssh2_sha256_ctx * ctx)2038 _libssh2_sha256_init(libssh2_sha256_ctx *ctx)
2039 {
2040 #ifdef HAVE_OPAQUE_STRUCTS
2041 *ctx = EVP_MD_CTX_new();
2042
2043 if(*ctx == NULL)
2044 return 0;
2045
2046 if(EVP_DigestInit(*ctx, EVP_get_digestbyname("sha256")))
2047 return 1;
2048
2049 EVP_MD_CTX_free(*ctx);
2050 *ctx = NULL;
2051
2052 return 0;
2053 #else
2054 EVP_MD_CTX_init(ctx);
2055 return EVP_DigestInit(ctx, EVP_get_digestbyname("sha256"));
2056 #endif
2057 }
2058
2059 int
_libssh2_sha256(const unsigned char * message,unsigned long len,unsigned char * out)2060 _libssh2_sha256(const unsigned char *message, unsigned long len,
2061 unsigned char *out)
2062 {
2063 #ifdef HAVE_OPAQUE_STRUCTS
2064 EVP_MD_CTX * ctx = EVP_MD_CTX_new();
2065
2066 if(ctx == NULL)
2067 return 1; /* error */
2068
2069 if(EVP_DigestInit(ctx, EVP_get_digestbyname("sha256"))) {
2070 EVP_DigestUpdate(ctx, message, len);
2071 EVP_DigestFinal(ctx, out, NULL);
2072 EVP_MD_CTX_free(ctx);
2073 return 0; /* success */
2074 }
2075 EVP_MD_CTX_free(ctx);
2076 #else
2077 EVP_MD_CTX ctx;
2078
2079 EVP_MD_CTX_init(&ctx);
2080 if(EVP_DigestInit(&ctx, EVP_get_digestbyname("sha256"))) {
2081 EVP_DigestUpdate(&ctx, message, len);
2082 EVP_DigestFinal(&ctx, out, NULL);
2083 return 0; /* success */
2084 }
2085 #endif
2086 return 1; /* error */
2087 }
2088
2089 int
_libssh2_sha384_init(libssh2_sha384_ctx * ctx)2090 _libssh2_sha384_init(libssh2_sha384_ctx *ctx)
2091 {
2092 #ifdef HAVE_OPAQUE_STRUCTS
2093 *ctx = EVP_MD_CTX_new();
2094
2095 if(*ctx == NULL)
2096 return 0;
2097
2098 if(EVP_DigestInit(*ctx, EVP_get_digestbyname("sha384")))
2099 return 1;
2100
2101 EVP_MD_CTX_free(*ctx);
2102 *ctx = NULL;
2103
2104 return 0;
2105 #else
2106 EVP_MD_CTX_init(ctx);
2107 return EVP_DigestInit(ctx, EVP_get_digestbyname("sha384"));
2108 #endif
2109 }
2110
2111 int
_libssh2_sha384(const unsigned char * message,unsigned long len,unsigned char * out)2112 _libssh2_sha384(const unsigned char *message, unsigned long len,
2113 unsigned char *out)
2114 {
2115 #ifdef HAVE_OPAQUE_STRUCTS
2116 EVP_MD_CTX * ctx = EVP_MD_CTX_new();
2117
2118 if(ctx == NULL)
2119 return 1; /* error */
2120
2121 if(EVP_DigestInit(ctx, EVP_get_digestbyname("sha384"))) {
2122 EVP_DigestUpdate(ctx, message, len);
2123 EVP_DigestFinal(ctx, out, NULL);
2124 EVP_MD_CTX_free(ctx);
2125 return 0; /* success */
2126 }
2127 EVP_MD_CTX_free(ctx);
2128 #else
2129 EVP_MD_CTX ctx;
2130
2131 EVP_MD_CTX_init(&ctx);
2132 if(EVP_DigestInit(&ctx, EVP_get_digestbyname("sha384"))) {
2133 EVP_DigestUpdate(&ctx, message, len);
2134 EVP_DigestFinal(&ctx, out, NULL);
2135 return 0; /* success */
2136 }
2137 #endif
2138 return 1; /* error */
2139 }
2140
2141 int
_libssh2_sha512_init(libssh2_sha512_ctx * ctx)2142 _libssh2_sha512_init(libssh2_sha512_ctx *ctx)
2143 {
2144 #ifdef HAVE_OPAQUE_STRUCTS
2145 *ctx = EVP_MD_CTX_new();
2146
2147 if(*ctx == NULL)
2148 return 0;
2149
2150 if(EVP_DigestInit(*ctx, EVP_get_digestbyname("sha512")))
2151 return 1;
2152
2153 EVP_MD_CTX_free(*ctx);
2154 *ctx = NULL;
2155
2156 return 0;
2157 #else
2158 EVP_MD_CTX_init(ctx);
2159 return EVP_DigestInit(ctx, EVP_get_digestbyname("sha512"));
2160 #endif
2161 }
2162
2163 int
_libssh2_sha512(const unsigned char * message,unsigned long len,unsigned char * out)2164 _libssh2_sha512(const unsigned char *message, unsigned long len,
2165 unsigned char *out)
2166 {
2167 #ifdef HAVE_OPAQUE_STRUCTS
2168 EVP_MD_CTX * ctx = EVP_MD_CTX_new();
2169
2170 if(ctx == NULL)
2171 return 1; /* error */
2172
2173 if(EVP_DigestInit(ctx, EVP_get_digestbyname("sha512"))) {
2174 EVP_DigestUpdate(ctx, message, len);
2175 EVP_DigestFinal(ctx, out, NULL);
2176 EVP_MD_CTX_free(ctx);
2177 return 0; /* success */
2178 }
2179 EVP_MD_CTX_free(ctx);
2180 #else
2181 EVP_MD_CTX ctx;
2182
2183 EVP_MD_CTX_init(&ctx);
2184 if(EVP_DigestInit(&ctx, EVP_get_digestbyname("sha512"))) {
2185 EVP_DigestUpdate(&ctx, message, len);
2186 EVP_DigestFinal(&ctx, out, NULL);
2187 return 0; /* success */
2188 }
2189 #endif
2190 return 1; /* error */
2191 }
2192
2193 int
_libssh2_md5_init(libssh2_md5_ctx * ctx)2194 _libssh2_md5_init(libssh2_md5_ctx *ctx)
2195 {
2196 #ifdef HAVE_OPAQUE_STRUCTS
2197 *ctx = EVP_MD_CTX_new();
2198
2199 if(*ctx == NULL)
2200 return 0;
2201
2202 if(EVP_DigestInit(*ctx, EVP_get_digestbyname("md5")))
2203 return 1;
2204
2205 EVP_MD_CTX_free(*ctx);
2206 *ctx = NULL;
2207
2208 return 0;
2209 #else
2210 EVP_MD_CTX_init(ctx);
2211 return EVP_DigestInit(ctx, EVP_get_digestbyname("md5"));
2212 #endif
2213 }
2214
2215 #if LIBSSH2_ECDSA
2216
2217 static int
gen_publickey_from_ec_evp(LIBSSH2_SESSION * session,unsigned char ** method,size_t * method_len,unsigned char ** pubkeydata,size_t * pubkeydata_len,EVP_PKEY * pk)2218 gen_publickey_from_ec_evp(LIBSSH2_SESSION *session,
2219 unsigned char **method,
2220 size_t *method_len,
2221 unsigned char **pubkeydata,
2222 size_t *pubkeydata_len,
2223 EVP_PKEY *pk)
2224 {
2225 int rc = 0;
2226 EC_KEY *ec = NULL;
2227 unsigned char *p;
2228 unsigned char *method_buf = NULL;
2229 unsigned char *key;
2230 size_t key_len = 0;
2231 unsigned char *octal_value = NULL;
2232 size_t octal_len;
2233 const EC_POINT *public_key;
2234 const EC_GROUP *group;
2235 BN_CTX *bn_ctx;
2236 libssh2_curve_type type;
2237
2238 _libssh2_debug(session,
2239 LIBSSH2_TRACE_AUTH,
2240 "Computing public key from EC private key envelop");
2241
2242 bn_ctx = BN_CTX_new();
2243 if(bn_ctx == NULL)
2244 return -1;
2245
2246 ec = EVP_PKEY_get1_EC_KEY(pk);
2247 if(ec == NULL) {
2248 rc = -1;
2249 goto clean_exit;
2250 }
2251
2252 public_key = EC_KEY_get0_public_key(ec);
2253 group = EC_KEY_get0_group(ec);
2254 type = _libssh2_ecdsa_key_get_curve_type(ec);
2255
2256 method_buf = LIBSSH2_ALLOC(session, 19);
2257 if(method_buf == NULL) {
2258 return _libssh2_error(session, LIBSSH2_ERROR_ALLOC,
2259 "out of memory");
2260 }
2261
2262 if(type == LIBSSH2_EC_CURVE_NISTP256)
2263 memcpy(method_buf, "ecdsa-sha2-nistp256", 19);
2264 else if(type == LIBSSH2_EC_CURVE_NISTP384)
2265 memcpy(method_buf, "ecdsa-sha2-nistp384", 19);
2266 else if(type == LIBSSH2_EC_CURVE_NISTP521)
2267 memcpy(method_buf, "ecdsa-sha2-nistp521", 19);
2268 else {
2269 _libssh2_debug(session,
2270 LIBSSH2_TRACE_ERROR,
2271 "Unsupported EC private key type");
2272 rc = -1;
2273 goto clean_exit;
2274 }
2275
2276 /* get length */
2277 octal_len = EC_POINT_point2oct(group, public_key,
2278 POINT_CONVERSION_UNCOMPRESSED,
2279 NULL, 0, bn_ctx);
2280 if(octal_len > EC_MAX_POINT_LEN) {
2281 rc = -1;
2282 goto clean_exit;
2283 }
2284
2285 octal_value = malloc(octal_len);
2286 if(octal_value == NULL) {
2287 rc = -1;
2288 goto clean_exit;
2289 }
2290
2291 /* convert to octal */
2292 if(EC_POINT_point2oct(group, public_key, POINT_CONVERSION_UNCOMPRESSED,
2293 octal_value, octal_len, bn_ctx) != octal_len) {
2294 rc = -1;
2295 goto clean_exit;
2296 }
2297
2298 /* Key form is: type_len(4) + type(19) + domain_len(4) + domain(8) +
2299 pub_key_len(4) + pub_key(~65). */
2300 key_len = 4 + 19 + 4 + 8 + 4 + octal_len;
2301 key = LIBSSH2_ALLOC(session, key_len);
2302 if(key == NULL) {
2303 rc = -1;
2304 goto clean_exit;
2305 }
2306
2307 /* Process key encoding. */
2308 p = key;
2309
2310 /* Key type */
2311 _libssh2_store_str(&p, (const char *)method_buf, 19);
2312
2313 /* Name domain */
2314 _libssh2_store_str(&p, (const char *)method_buf + 11, 8);
2315
2316 /* Public key */
2317 _libssh2_store_str(&p, (const char *)octal_value, octal_len);
2318
2319 *method = method_buf;
2320 *method_len = 19;
2321 *pubkeydata = key;
2322 *pubkeydata_len = key_len;
2323
2324 clean_exit:
2325
2326 if(ec != NULL)
2327 EC_KEY_free(ec);
2328
2329 if(bn_ctx != NULL) {
2330 BN_CTX_free(bn_ctx);
2331 }
2332
2333 if(octal_value != NULL)
2334 free(octal_value);
2335
2336 if(rc == 0)
2337 return 0;
2338
2339 if(method_buf != NULL)
2340 LIBSSH2_FREE(session, method_buf);
2341
2342 return -1;
2343 }
2344
2345 static int
gen_publickey_from_ecdsa_openssh_priv_data(LIBSSH2_SESSION * session,libssh2_curve_type curve_type,struct string_buf * decrypted,unsigned char ** method,size_t * method_len,unsigned char ** pubkeydata,size_t * pubkeydata_len,libssh2_ecdsa_ctx ** ec_ctx)2346 gen_publickey_from_ecdsa_openssh_priv_data(LIBSSH2_SESSION *session,
2347 libssh2_curve_type curve_type,
2348 struct string_buf *decrypted,
2349 unsigned char **method,
2350 size_t *method_len,
2351 unsigned char **pubkeydata,
2352 size_t *pubkeydata_len,
2353 libssh2_ecdsa_ctx **ec_ctx)
2354 {
2355 int rc = 0;
2356 size_t curvelen, exponentlen, pointlen;
2357 unsigned char *curve, *exponent, *point_buf;
2358 EC_KEY *ec_key = NULL;
2359 BIGNUM *bn_exponent;
2360
2361 _libssh2_debug(session,
2362 LIBSSH2_TRACE_AUTH,
2363 "Computing ECDSA keys from private key data");
2364
2365 if(_libssh2_get_string(decrypted, &curve, &curvelen) ||
2366 curvelen == 0) {
2367 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
2368 "ECDSA no curve");
2369 return -1;
2370 }
2371
2372 if(_libssh2_get_string(decrypted, &point_buf, &pointlen)) {
2373 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
2374 "ECDSA no point");
2375 return -1;
2376 }
2377
2378 if(_libssh2_get_bignum_bytes(decrypted, &exponent, &exponentlen)) {
2379 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
2380 "ECDSA no exponent");
2381 return -1;
2382 }
2383
2384 if((rc = _libssh2_ecdsa_curve_name_with_octal_new(&ec_key, point_buf,
2385 pointlen, curve_type)) != 0) {
2386 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
2387 "ECDSA could not create key");
2388 goto fail;
2389 }
2390
2391 bn_exponent = BN_new();
2392 if(bn_exponent == NULL) {
2393 rc = -1;
2394 goto fail;
2395 }
2396
2397 BN_bin2bn(exponent, exponentlen, bn_exponent);
2398 rc = (EC_KEY_set_private_key(ec_key, bn_exponent) != 1);
2399
2400 if(rc == 0 && ec_key != NULL && pubkeydata != NULL && method != NULL) {
2401 EVP_PKEY *pk = EVP_PKEY_new();
2402 EVP_PKEY_set1_EC_KEY(pk, ec_key);
2403
2404 rc = gen_publickey_from_ec_evp(session, method, method_len,
2405 pubkeydata, pubkeydata_len,
2406 pk);
2407
2408 if(pk)
2409 EVP_PKEY_free(pk);
2410 }
2411
2412 if(ec_ctx != NULL)
2413 *ec_ctx = ec_key;
2414 else
2415 EC_KEY_free(ec_key);
2416
2417 return rc;
2418
2419 fail:
2420
2421 if(ec_key != NULL)
2422 EC_KEY_free(ec_key);
2423
2424 return _libssh2_error(session,
2425 LIBSSH2_ERROR_ALLOC,
2426 "Unable to allocate memory for private key data");
2427
2428
2429 }
2430
2431 static int
_libssh2_ecdsa_new_openssh_private(libssh2_ecdsa_ctx ** ec_ctx,LIBSSH2_SESSION * session,const char * filename,unsigned const char * passphrase)2432 _libssh2_ecdsa_new_openssh_private(libssh2_ecdsa_ctx ** ec_ctx,
2433 LIBSSH2_SESSION * session,
2434 const char *filename,
2435 unsigned const char *passphrase)
2436 {
2437 FILE *fp;
2438 int rc;
2439 unsigned char *buf = NULL;
2440 libssh2_curve_type type;
2441 struct string_buf *decrypted = NULL;
2442
2443 if(session == NULL) {
2444 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
2445 "Session is required");
2446 return -1;
2447 }
2448
2449 _libssh2_init_if_needed();
2450
2451 fp = fopen(filename, "r");
2452 if(!fp) {
2453 _libssh2_error(session, LIBSSH2_ERROR_FILE,
2454 "Unable to open OpenSSH ECDSA private key file");
2455 return -1;
2456 }
2457
2458 rc = _libssh2_openssh_pem_parse(session, passphrase, fp, &decrypted);
2459 fclose(fp);
2460 if(rc) {
2461 return rc;
2462 }
2463
2464 /* We have a new key file, now try and parse it using supported types */
2465 rc = _libssh2_get_string(decrypted, &buf, NULL);
2466
2467 if(rc != 0 || buf == NULL) {
2468 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
2469 "Public key type in decrypted key data not found");
2470 return -1;
2471 }
2472
2473 rc = _libssh2_ecdsa_curve_type_from_name((const char *)buf, &type);
2474
2475 if(rc == 0) {
2476 rc = gen_publickey_from_ecdsa_openssh_priv_data(session, type,
2477 decrypted, NULL, 0,
2478 NULL, 0, ec_ctx);
2479 }
2480 else {
2481 rc = -1;
2482 }
2483
2484 if(decrypted)
2485 _libssh2_string_buf_free(session, decrypted);
2486
2487 return rc;
2488 }
2489
2490 int
_libssh2_ecdsa_new_private(libssh2_ecdsa_ctx ** ec_ctx,LIBSSH2_SESSION * session,const char * filename,unsigned const char * passphrase)2491 _libssh2_ecdsa_new_private(libssh2_ecdsa_ctx ** ec_ctx,
2492 LIBSSH2_SESSION * session,
2493 const char *filename, unsigned const char *passphrase)
2494 {
2495 int rc;
2496
2497 pem_read_bio_func read_ec = (pem_read_bio_func) &PEM_read_bio_ECPrivateKey;
2498 (void) session;
2499
2500 _libssh2_init_if_needed();
2501
2502 rc = read_private_key_from_file((void **) ec_ctx, read_ec,
2503 filename, passphrase);
2504
2505 if(rc) {
2506 return _libssh2_ecdsa_new_openssh_private(ec_ctx, session,
2507 filename, passphrase);
2508 }
2509
2510 return rc;
2511 }
2512
2513 /*
2514 * _libssh2_ecdsa_create_key
2515 *
2516 * Creates a local private key based on input curve
2517 * and returns octal value and octal length
2518 *
2519 */
2520
2521 int
_libssh2_ecdsa_create_key(LIBSSH2_SESSION * session,_libssh2_ec_key ** out_private_key,unsigned char ** out_public_key_octal,size_t * out_public_key_octal_len,libssh2_curve_type curve_type)2522 _libssh2_ecdsa_create_key(LIBSSH2_SESSION *session,
2523 _libssh2_ec_key **out_private_key,
2524 unsigned char **out_public_key_octal,
2525 size_t *out_public_key_octal_len,
2526 libssh2_curve_type curve_type)
2527 {
2528 int ret = 1;
2529 size_t octal_len = 0;
2530 unsigned char octal_value[EC_MAX_POINT_LEN];
2531 const EC_POINT *public_key = NULL;
2532 EC_KEY *private_key = NULL;
2533 const EC_GROUP *group = NULL;
2534
2535 /* create key */
2536 BN_CTX *bn_ctx = BN_CTX_new();
2537 if(!bn_ctx)
2538 return -1;
2539
2540 private_key = EC_KEY_new_by_curve_name(curve_type);
2541 group = EC_KEY_get0_group(private_key);
2542
2543 EC_KEY_generate_key(private_key);
2544 public_key = EC_KEY_get0_public_key(private_key);
2545
2546 /* get length */
2547 octal_len = EC_POINT_point2oct(group, public_key,
2548 POINT_CONVERSION_UNCOMPRESSED,
2549 NULL, 0, bn_ctx);
2550 if(octal_len > EC_MAX_POINT_LEN) {
2551 ret = -1;
2552 goto clean_exit;
2553 }
2554
2555 /* convert to octal */
2556 if(EC_POINT_point2oct(group, public_key, POINT_CONVERSION_UNCOMPRESSED,
2557 octal_value, octal_len, bn_ctx) != octal_len) {
2558 ret = -1;
2559 goto clean_exit;
2560 }
2561
2562 if(out_private_key != NULL)
2563 *out_private_key = private_key;
2564
2565 if(out_public_key_octal) {
2566 *out_public_key_octal = LIBSSH2_ALLOC(session, octal_len);
2567 if(*out_public_key_octal == NULL) {
2568 ret = -1;
2569 goto clean_exit;
2570 }
2571
2572 memcpy(*out_public_key_octal, octal_value, octal_len);
2573 }
2574
2575 if(out_public_key_octal_len != NULL)
2576 *out_public_key_octal_len = octal_len;
2577
2578 clean_exit:
2579
2580 if(bn_ctx)
2581 BN_CTX_free(bn_ctx);
2582
2583 return (ret == 1) ? 0 : -1;
2584 }
2585
2586 /* _libssh2_ecdh_gen_k
2587 *
2588 * Computes the shared secret K given a local private key,
2589 * remote public key and length
2590 */
2591
2592 int
_libssh2_ecdh_gen_k(_libssh2_bn ** k,_libssh2_ec_key * private_key,const unsigned char * server_public_key,size_t server_public_key_len)2593 _libssh2_ecdh_gen_k(_libssh2_bn **k, _libssh2_ec_key *private_key,
2594 const unsigned char *server_public_key, size_t server_public_key_len)
2595 {
2596 int ret = 0;
2597 int rc;
2598 size_t secret_len;
2599 unsigned char *secret = NULL;
2600 const EC_GROUP *private_key_group;
2601 EC_POINT *server_public_key_point;
2602
2603 BN_CTX *bn_ctx = BN_CTX_new();
2604
2605 if(!bn_ctx)
2606 return -1;
2607
2608 if(k == NULL)
2609 return -1;
2610
2611 private_key_group = EC_KEY_get0_group(private_key);
2612
2613 server_public_key_point = EC_POINT_new(private_key_group);
2614 if(server_public_key_point == NULL)
2615 return -1;
2616
2617 rc = EC_POINT_oct2point(private_key_group, server_public_key_point,
2618 server_public_key, server_public_key_len, bn_ctx);
2619 if(rc != 1) {
2620 ret = -1;
2621 goto clean_exit;
2622 }
2623
2624 secret_len = (EC_GROUP_get_degree(private_key_group) + 7) / 8;
2625 secret = malloc(secret_len);
2626 if(!secret) {
2627 ret = -1;
2628 goto clean_exit;
2629 }
2630
2631 secret_len = ECDH_compute_key(secret, secret_len, server_public_key_point,
2632 private_key, NULL);
2633
2634 if(secret_len <= 0 || secret_len > EC_MAX_POINT_LEN) {
2635 ret = -1;
2636 goto clean_exit;
2637 }
2638
2639 BN_bin2bn(secret, secret_len, *k);
2640
2641 clean_exit:
2642
2643 if(server_public_key_point != NULL)
2644 EC_POINT_free(server_public_key_point);
2645
2646 if(bn_ctx != NULL)
2647 BN_CTX_free(bn_ctx);
2648
2649 if(secret != NULL)
2650 free(secret);
2651
2652 return ret;
2653 }
2654
2655
2656 #endif /* LIBSSH2_ECDSA */
2657
2658 #if LIBSSH2_ED25519
2659
2660 int
_libssh2_ed25519_sign(libssh2_ed25519_ctx * ctx,LIBSSH2_SESSION * session,uint8_t ** out_sig,size_t * out_sig_len,const uint8_t * message,size_t message_len)2661 _libssh2_ed25519_sign(libssh2_ed25519_ctx *ctx, LIBSSH2_SESSION *session,
2662 uint8_t **out_sig, size_t *out_sig_len,
2663 const uint8_t *message, size_t message_len)
2664 {
2665 int rc = -1;
2666 EVP_MD_CTX *md_ctx = EVP_MD_CTX_new();
2667 size_t sig_len = 0;
2668 unsigned char *sig = NULL;
2669
2670 if(md_ctx != NULL) {
2671 if(EVP_DigestSignInit(md_ctx, NULL, NULL, NULL, ctx->private_key) != 1)
2672 goto clean_exit;
2673 if(EVP_DigestSign(md_ctx, NULL, &sig_len, message, message_len) != 1)
2674 goto clean_exit;
2675
2676 if(sig_len != LIBSSH2_ED25519_SIG_LEN)
2677 goto clean_exit;
2678
2679 sig = LIBSSH2_CALLOC(session, sig_len);
2680 if(sig == NULL)
2681 goto clean_exit;
2682
2683 rc = EVP_DigestSign(md_ctx, sig, &sig_len, message, message_len);
2684 }
2685
2686 if(rc == 1) {
2687 *out_sig = sig;
2688 *out_sig_len = sig_len;
2689 }
2690 else {
2691 *out_sig_len = 0;
2692 *out_sig = NULL;
2693 LIBSSH2_FREE(session, sig);
2694 }
2695
2696 clean_exit:
2697
2698 if(md_ctx)
2699 EVP_MD_CTX_free(md_ctx);
2700
2701 return (rc == 1 ? 0 : -1);
2702 }
2703
2704 int
_libssh2_curve25519_gen_k(_libssh2_bn ** k,uint8_t private_key[LIBSSH2_ED25519_KEY_LEN],uint8_t server_public_key[LIBSSH2_ED25519_KEY_LEN])2705 _libssh2_curve25519_gen_k(_libssh2_bn **k,
2706 uint8_t private_key[LIBSSH2_ED25519_KEY_LEN],
2707 uint8_t server_public_key[LIBSSH2_ED25519_KEY_LEN])
2708 {
2709 int rc = -1;
2710 unsigned char out_shared_key[LIBSSH2_ED25519_KEY_LEN];
2711 EVP_PKEY *peer_key = NULL, *server_key = NULL;
2712 EVP_PKEY_CTX *server_key_ctx = NULL;
2713 BN_CTX *bn_ctx = NULL;
2714 size_t out_len = 0;
2715
2716 if(k == NULL || *k == NULL)
2717 return -1;
2718
2719 bn_ctx = BN_CTX_new();
2720 if(bn_ctx == NULL)
2721 return -1;
2722
2723 peer_key = EVP_PKEY_new_raw_public_key(EVP_PKEY_X25519, NULL,
2724 server_public_key,
2725 LIBSSH2_ED25519_KEY_LEN);
2726
2727 server_key = EVP_PKEY_new_raw_private_key(EVP_PKEY_X25519, NULL,
2728 private_key,
2729 LIBSSH2_ED25519_KEY_LEN);
2730
2731 if(peer_key == NULL || server_key == NULL) {
2732 goto cleanExit;
2733 }
2734
2735 server_key_ctx = EVP_PKEY_CTX_new(server_key, NULL);
2736 if(server_key_ctx == NULL) {
2737 goto cleanExit;
2738 }
2739
2740 rc = EVP_PKEY_derive_init(server_key_ctx);
2741 if(rc <= 0) goto cleanExit;
2742
2743 rc = EVP_PKEY_derive_set_peer(server_key_ctx, peer_key);
2744 if(rc <= 0) goto cleanExit;
2745
2746 rc = EVP_PKEY_derive(server_key_ctx, NULL, &out_len);
2747 if(rc <= 0) goto cleanExit;
2748
2749 if(out_len != LIBSSH2_ED25519_KEY_LEN) {
2750 rc = -1;
2751 goto cleanExit;
2752 }
2753
2754 rc = EVP_PKEY_derive(server_key_ctx, out_shared_key, &out_len);
2755
2756 if(rc == 1 && out_len == LIBSSH2_ED25519_KEY_LEN) {
2757 BN_bin2bn(out_shared_key, LIBSSH2_ED25519_KEY_LEN, *k);
2758 }
2759 else {
2760 rc = -1;
2761 }
2762
2763 cleanExit:
2764
2765 if(server_key_ctx)
2766 EVP_PKEY_CTX_free(server_key_ctx);
2767 if(peer_key)
2768 EVP_PKEY_free(peer_key);
2769 if(server_key)
2770 EVP_PKEY_free(server_key);
2771 if(bn_ctx != NULL)
2772 BN_CTX_free(bn_ctx);
2773
2774 return (rc == 1) ? 0 : -1;
2775 }
2776
2777
2778 int
_libssh2_ed25519_verify(libssh2_ed25519_ctx * ctx,const uint8_t * s,size_t s_len,const uint8_t * m,size_t m_len)2779 _libssh2_ed25519_verify(libssh2_ed25519_ctx *ctx, const uint8_t *s,
2780 size_t s_len, const uint8_t *m, size_t m_len)
2781 {
2782 int ret = -1;
2783
2784 EVP_MD_CTX *md_ctx = EVP_MD_CTX_new();
2785 if(NULL == md_ctx)
2786 return -1;
2787
2788 ret = EVP_DigestVerifyInit(md_ctx, NULL, NULL, NULL, ctx->public_key);
2789 if(ret != 1)
2790 goto clean_exit;
2791
2792 ret = EVP_DigestVerify(md_ctx, s, s_len, m, m_len);
2793
2794 clean_exit:
2795
2796 EVP_MD_CTX_free(md_ctx);
2797
2798 return (ret == 1) ? 0 : -1;
2799 }
2800
2801 #endif /* LIBSSH2_ED25519 */
2802
2803 static int
_libssh2_pub_priv_openssh_keyfile(LIBSSH2_SESSION * session,unsigned char ** method,size_t * method_len,unsigned char ** pubkeydata,size_t * pubkeydata_len,const char * privatekey,const char * passphrase)2804 _libssh2_pub_priv_openssh_keyfile(LIBSSH2_SESSION *session,
2805 unsigned char **method,
2806 size_t *method_len,
2807 unsigned char **pubkeydata,
2808 size_t *pubkeydata_len,
2809 const char *privatekey,
2810 const char *passphrase)
2811 {
2812 FILE *fp;
2813 unsigned char *buf = NULL;
2814 struct string_buf *decrypted = NULL;
2815 int rc = 0;
2816
2817 if(session == NULL) {
2818 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
2819 "Session is required");
2820 return -1;
2821 }
2822
2823 _libssh2_init_if_needed();
2824
2825 fp = fopen(privatekey, "r");
2826 if(!fp) {
2827 _libssh2_error(session, LIBSSH2_ERROR_FILE,
2828 "Unable to open private key file");
2829 return -1;
2830 }
2831
2832 rc = _libssh2_openssh_pem_parse(session, (const unsigned char *)passphrase,
2833 fp, &decrypted);
2834 fclose(fp);
2835 if(rc) {
2836 _libssh2_error(session, LIBSSH2_ERROR_FILE,
2837 "Not an OpenSSH key file");
2838 return rc;
2839 }
2840
2841 /* We have a new key file, now try and parse it using supported types */
2842 rc = _libssh2_get_string(decrypted, &buf, NULL);
2843
2844 if(rc != 0 || buf == NULL) {
2845 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
2846 "Public key type in decrypted key data not found");
2847 return -1;
2848 }
2849
2850 rc = -1;
2851
2852 #if LIBSSH2_ED25519
2853 if(strcmp("ssh-ed25519", (const char *)buf) == 0) {
2854 rc = gen_publickey_from_ed25519_openssh_priv_data(session, decrypted,
2855 method, method_len,
2856 pubkeydata,
2857 pubkeydata_len,
2858 NULL);
2859 }
2860 #endif
2861 #if LIBSSH2_RSA
2862 if(strcmp("ssh-rsa", (const char *)buf) == 0) {
2863 rc = gen_publickey_from_rsa_openssh_priv_data(session, decrypted,
2864 method, method_len,
2865 pubkeydata,
2866 pubkeydata_len,
2867 NULL);
2868 }
2869 #endif
2870 #if LIBSSH2_DSA
2871 if(strcmp("ssh-dss", (const char *)buf) == 0) {
2872 rc = gen_publickey_from_dsa_openssh_priv_data(session, decrypted,
2873 method, method_len,
2874 pubkeydata,
2875 pubkeydata_len,
2876 NULL);
2877 }
2878 #endif
2879 #if LIBSSH2_ECDSA
2880 {
2881 libssh2_curve_type type;
2882
2883 if(_libssh2_ecdsa_curve_type_from_name((const char *)buf,
2884 &type) == 0) {
2885 rc = gen_publickey_from_ecdsa_openssh_priv_data(session, type,
2886 decrypted,
2887 method, method_len,
2888 pubkeydata,
2889 pubkeydata_len,
2890 NULL);
2891 }
2892 }
2893 #endif
2894
2895 if(decrypted)
2896 _libssh2_string_buf_free(session, decrypted);
2897
2898 if(rc != 0) {
2899 _libssh2_error(session, LIBSSH2_ERROR_FILE,
2900 "Unsupported OpenSSH key type");
2901 }
2902
2903 return rc;
2904 }
2905
2906 int
_libssh2_pub_priv_keyfile(LIBSSH2_SESSION * session,unsigned char ** method,size_t * method_len,unsigned char ** pubkeydata,size_t * pubkeydata_len,const char * privatekey,const char * passphrase)2907 _libssh2_pub_priv_keyfile(LIBSSH2_SESSION *session,
2908 unsigned char **method,
2909 size_t *method_len,
2910 unsigned char **pubkeydata,
2911 size_t *pubkeydata_len,
2912 const char *privatekey,
2913 const char *passphrase)
2914 {
2915 int st;
2916 BIO* bp;
2917 EVP_PKEY* pk;
2918 int pktype;
2919 int rc;
2920
2921 _libssh2_debug(session,
2922 LIBSSH2_TRACE_AUTH,
2923 "Computing public key from private key file: %s",
2924 privatekey);
2925
2926 bp = BIO_new_file(privatekey, "r");
2927 if(bp == NULL) {
2928 return _libssh2_error(session,
2929 LIBSSH2_ERROR_FILE,
2930 "Unable to extract public key from private key "
2931 "file: Unable to open private key file");
2932 }
2933
2934 BIO_reset(bp);
2935 pk = PEM_read_bio_PrivateKey(bp, NULL, NULL, (void *)passphrase);
2936 BIO_free(bp);
2937
2938 if(pk == NULL) {
2939
2940 /* Try OpenSSH format */
2941 rc = _libssh2_pub_priv_openssh_keyfile(session,
2942 method,
2943 method_len,
2944 pubkeydata, pubkeydata_len,
2945 privatekey, passphrase);
2946 if(rc != 0) {
2947 return _libssh2_error(session,
2948 LIBSSH2_ERROR_FILE,
2949 "Unable to extract public key "
2950 "from private key file: "
2951 "Wrong passphrase or invalid/unrecognized "
2952 "private key file format");
2953 }
2954
2955 return 0;
2956 }
2957
2958 #ifdef HAVE_OPAQUE_STRUCTS
2959 pktype = EVP_PKEY_id(pk);
2960 #else
2961 pktype = pk->type;
2962 #endif
2963
2964 switch(pktype) {
2965 case EVP_PKEY_RSA :
2966 st = gen_publickey_from_rsa_evp(
2967 session, method, method_len, pubkeydata, pubkeydata_len, pk);
2968 break;
2969
2970 #if LIBSSH2_DSA
2971 case EVP_PKEY_DSA :
2972 st = gen_publickey_from_dsa_evp(
2973 session, method, method_len, pubkeydata, pubkeydata_len, pk);
2974 break;
2975 #endif /* LIBSSH_DSA */
2976
2977 #if LIBSSH2_ECDSA
2978 case EVP_PKEY_EC :
2979 st = gen_publickey_from_ec_evp(
2980 session, method, method_len, pubkeydata, pubkeydata_len, pk);
2981 break;
2982 #endif
2983
2984 default :
2985 st = _libssh2_error(session,
2986 LIBSSH2_ERROR_FILE,
2987 "Unable to extract public key "
2988 "from private key file: "
2989 "Unsupported private key file format");
2990 break;
2991 }
2992
2993 EVP_PKEY_free(pk);
2994 return st;
2995 }
2996
2997 static int
_libssh2_pub_priv_openssh_keyfilememory(LIBSSH2_SESSION * session,void ** key_ctx,const char * key_type,unsigned char ** method,size_t * method_len,unsigned char ** pubkeydata,size_t * pubkeydata_len,const char * privatekeydata,size_t privatekeydata_len,unsigned const char * passphrase)2998 _libssh2_pub_priv_openssh_keyfilememory(LIBSSH2_SESSION *session,
2999 void **key_ctx,
3000 const char *key_type,
3001 unsigned char **method,
3002 size_t *method_len,
3003 unsigned char **pubkeydata,
3004 size_t *pubkeydata_len,
3005 const char *privatekeydata,
3006 size_t privatekeydata_len,
3007 unsigned const char *passphrase)
3008 {
3009 int rc;
3010 unsigned char *buf = NULL;
3011 struct string_buf *decrypted = NULL;
3012
3013 if(key_ctx != NULL)
3014 *key_ctx = NULL;
3015
3016 if(session == NULL) {
3017 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
3018 "Session is required");
3019 return -1;
3020 }
3021
3022 if(key_type != NULL && (strlen(key_type) > 11 || strlen(key_type) < 7)) {
3023 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
3024 "type is invalid");
3025 return -1;
3026 }
3027
3028 _libssh2_init_if_needed();
3029
3030 rc = _libssh2_openssh_pem_parse_memory(session, passphrase,
3031 privatekeydata,
3032 privatekeydata_len, &decrypted);
3033
3034 if(rc) {
3035 return rc;
3036 }
3037
3038 /* We have a new key file, now try and parse it using supported types */
3039 rc = _libssh2_get_string(decrypted, &buf, NULL);
3040
3041 if(rc != 0 || buf == NULL) {
3042 _libssh2_error(session, LIBSSH2_ERROR_PROTO,
3043 "Public key type in decrypted key data not found");
3044 return -1;
3045 }
3046
3047 rc = -1;
3048
3049 #if LIBSSH2_ED25519
3050 if(strcmp("ssh-ed25519", (const char *)buf) == 0) {
3051 if(key_type == NULL || strcmp("ssh-ed25519", key_type) == 0) {
3052 rc = gen_publickey_from_ed25519_openssh_priv_data(session,
3053 decrypted,
3054 method,
3055 method_len,
3056 pubkeydata,
3057 pubkeydata_len,
3058 (libssh2_ed25519_ctx**)key_ctx);
3059 }
3060 }
3061 #endif
3062 #if LIBSSH2_RSA
3063 if(strcmp("ssh-rsa", (const char *)buf) == 0) {
3064 if(key_type == NULL || strcmp("ssh-rsa", key_type) == 0) {
3065 rc = gen_publickey_from_rsa_openssh_priv_data(session, decrypted,
3066 method, method_len,
3067 pubkeydata,
3068 pubkeydata_len,
3069 (libssh2_rsa_ctx**)key_ctx);
3070 }
3071 }
3072 #endif
3073 #if LIBSSH2_DSA
3074 if(strcmp("ssh-dss", (const char *)buf) == 0) {
3075 if(key_type == NULL || strcmp("ssh-dss", key_type) == 0) {
3076 rc = gen_publickey_from_dsa_openssh_priv_data(session, decrypted,
3077 method, method_len,
3078 pubkeydata,
3079 pubkeydata_len,
3080 (libssh2_dsa_ctx**)key_ctx);
3081 }
3082 }
3083 #endif
3084 #if LIBSSH2_ECDSA
3085 {
3086 libssh2_curve_type type;
3087
3088 if(_libssh2_ecdsa_curve_type_from_name((const char *)buf, &type) == 0) {
3089 if(key_type == NULL || strcmp("ssh-ecdsa", key_type) == 0) {
3090 rc = gen_publickey_from_ecdsa_openssh_priv_data(session, type,
3091 decrypted,
3092 method, method_len,
3093 pubkeydata,
3094 pubkeydata_len,
3095 (libssh2_ecdsa_ctx**)key_ctx);
3096 }
3097 }
3098 }
3099 #endif
3100
3101 if(decrypted)
3102 _libssh2_string_buf_free(session, decrypted);
3103
3104 return rc;
3105 }
3106
3107 int
read_openssh_private_key_from_memory(void ** key_ctx,LIBSSH2_SESSION * session,const char * key_type,const char * filedata,size_t filedata_len,unsigned const char * passphrase)3108 read_openssh_private_key_from_memory(void **key_ctx, LIBSSH2_SESSION *session,
3109 const char *key_type,
3110 const char *filedata,
3111 size_t filedata_len,
3112 unsigned const char *passphrase)
3113 {
3114 return _libssh2_pub_priv_openssh_keyfilememory(session, key_ctx, key_type,
3115 NULL, NULL, NULL, NULL,
3116 filedata, filedata_len,
3117 passphrase);
3118 }
3119
3120 int
_libssh2_pub_priv_keyfilememory(LIBSSH2_SESSION * session,unsigned char ** method,size_t * method_len,unsigned char ** pubkeydata,size_t * pubkeydata_len,const char * privatekeydata,size_t privatekeydata_len,const char * passphrase)3121 _libssh2_pub_priv_keyfilememory(LIBSSH2_SESSION *session,
3122 unsigned char **method,
3123 size_t *method_len,
3124 unsigned char **pubkeydata,
3125 size_t *pubkeydata_len,
3126 const char *privatekeydata,
3127 size_t privatekeydata_len,
3128 const char *passphrase)
3129 {
3130 int st;
3131 BIO* bp;
3132 EVP_PKEY* pk;
3133 int pktype;
3134
3135 _libssh2_debug(session,
3136 LIBSSH2_TRACE_AUTH,
3137 "Computing public key from private key.");
3138
3139 bp = BIO_new_mem_buf((char *)privatekeydata, privatekeydata_len);
3140 if(!bp) {
3141 return -1;
3142 }
3143
3144 BIO_reset(bp);
3145 pk = PEM_read_bio_PrivateKey(bp, NULL, NULL, (void *)passphrase);
3146 BIO_free(bp);
3147
3148 if(pk == NULL) {
3149 /* Try OpenSSH format */
3150 st = _libssh2_pub_priv_openssh_keyfilememory(session, NULL, NULL,
3151 method,
3152 method_len,
3153 pubkeydata,
3154 pubkeydata_len,
3155 privatekeydata,
3156 privatekeydata_len,
3157 (unsigned const char *)passphrase);
3158 if(st != 0) {
3159 return _libssh2_error(session,
3160 LIBSSH2_ERROR_FILE,
3161 "Unable to extract public key "
3162 "from private key file: "
3163 "Wrong passphrase or invalid/unrecognized "
3164 "private key file format");
3165 }
3166
3167 return 0;
3168 }
3169
3170 #ifdef HAVE_OPAQUE_STRUCTS
3171 pktype = EVP_PKEY_id(pk);
3172 #else
3173 pktype = pk->type;
3174 #endif
3175
3176 switch(pktype) {
3177 case EVP_PKEY_RSA :
3178 st = gen_publickey_from_rsa_evp(session, method, method_len,
3179 pubkeydata, pubkeydata_len, pk);
3180 break;
3181 #if LIBSSH2_DSA
3182 case EVP_PKEY_DSA :
3183 st = gen_publickey_from_dsa_evp(session, method, method_len,
3184 pubkeydata, pubkeydata_len, pk);
3185 break;
3186 #endif /* LIBSSH_DSA */
3187 #if LIBSSH2_ECDSA
3188 case EVP_PKEY_EC :
3189 st = gen_publickey_from_ec_evp(session, method, method_len,
3190 pubkeydata, pubkeydata_len, pk);
3191 break;
3192 #endif /* LIBSSH2_ECDSA */
3193 default :
3194 st = _libssh2_error(session,
3195 LIBSSH2_ERROR_FILE,
3196 "Unable to extract public key "
3197 "from private key file: "
3198 "Unsupported private key file format");
3199 break;
3200 }
3201
3202 EVP_PKEY_free(pk);
3203 return st;
3204 }
3205
3206 void
_libssh2_dh_init(_libssh2_dh_ctx * dhctx)3207 _libssh2_dh_init(_libssh2_dh_ctx *dhctx)
3208 {
3209 *dhctx = BN_new(); /* Random from client */
3210 }
3211
3212 int
_libssh2_dh_key_pair(_libssh2_dh_ctx * dhctx,_libssh2_bn * public,_libssh2_bn * g,_libssh2_bn * p,int group_order,_libssh2_bn_ctx * bnctx)3213 _libssh2_dh_key_pair(_libssh2_dh_ctx *dhctx, _libssh2_bn *public,
3214 _libssh2_bn *g, _libssh2_bn *p, int group_order,
3215 _libssh2_bn_ctx *bnctx)
3216 {
3217 /* Generate x and e */
3218 BN_rand(*dhctx, group_order * 8 - 1, 0, -1);
3219 BN_mod_exp(public, g, *dhctx, p, bnctx);
3220 return 0;
3221 }
3222
3223 int
_libssh2_dh_secret(_libssh2_dh_ctx * dhctx,_libssh2_bn * secret,_libssh2_bn * f,_libssh2_bn * p,_libssh2_bn_ctx * bnctx)3224 _libssh2_dh_secret(_libssh2_dh_ctx *dhctx, _libssh2_bn *secret,
3225 _libssh2_bn *f, _libssh2_bn *p,
3226 _libssh2_bn_ctx *bnctx)
3227 {
3228 /* Compute the shared secret */
3229 BN_mod_exp(secret, f, *dhctx, p, bnctx);
3230 return 0;
3231 }
3232
3233 void
_libssh2_dh_dtor(_libssh2_dh_ctx * dhctx)3234 _libssh2_dh_dtor(_libssh2_dh_ctx *dhctx)
3235 {
3236 BN_clear_free(*dhctx);
3237 *dhctx = NULL;
3238 }
3239
3240 #endif /* LIBSSH2_OPENSSL */
3241