crypto_openssl.c revision 1c71527b277e2dc256262da2ed2169c566c5bf4d
1/*	$NetBSD: crypto_openssl.c,v 1.11.6.5 2009/04/20 13:33:30 tteras Exp $	*/
2
3/* Id: crypto_openssl.c,v 1.47 2006/05/06 20:42:09 manubsd Exp */
4
5/*
6 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
7 * All rights reserved.
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions
11 * are met:
12 * 1. Redistributions of source code must retain the above copyright
13 *    notice, this list of conditions and the following disclaimer.
14 * 2. Redistributions in binary form must reproduce the above copyright
15 *    notice, this list of conditions and the following disclaimer in the
16 *    documentation and/or other materials provided with the distribution.
17 * 3. Neither the name of the project nor the names of its contributors
18 *    may be used to endorse or promote products derived from this software
19 *    without specific prior written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
22 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED.  IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
25 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31 * SUCH DAMAGE.
32 */
33
34#include "config.h"
35
36#include <sys/types.h>
37#include <sys/param.h>
38
39#include <stdlib.h>
40#include <stdio.h>
41#include <limits.h>
42#include <string.h>
43
44/* get openssl/ssleay version number */
45#include <openssl/opensslv.h>
46
47#if !defined(OPENSSL_VERSION_NUMBER) || (OPENSSL_VERSION_NUMBER < 0x0090602fL)
48#error OpenSSL version 0.9.6 or later required.
49#endif
50
51#include <openssl/pem.h>
52#include <openssl/evp.h>
53#include <openssl/x509.h>
54#include <openssl/x509v3.h>
55#include <openssl/x509_vfy.h>
56#include <openssl/bn.h>
57#include <openssl/dh.h>
58#include <openssl/md5.h>
59#include <openssl/sha.h>
60#include <openssl/hmac.h>
61#include <openssl/des.h>
62#include <openssl/crypto.h>
63#ifdef HAVE_OPENSSL_ENGINE_H
64#include <openssl/engine.h>
65#endif
66#include <openssl/blowfish.h>
67#include <openssl/cast.h>
68#include <openssl/err.h>
69#ifdef HAVE_OPENSSL_RC5_H
70#include <openssl/rc5.h>
71#endif
72#ifdef HAVE_OPENSSL_IDEA_H
73#include <openssl/idea.h>
74#endif
75#if defined(HAVE_OPENSSL_AES_H)
76#include <openssl/aes.h>
77#elif defined(HAVE_OPENSSL_RIJNDAEL_H)
78#include <openssl/rijndael.h>
79#else
80#include "crypto/rijndael/rijndael-api-fst.h"
81#endif
82#if defined(HAVE_OPENSSL_CAMELLIA_H)
83#include <openssl/camellia.h>
84#endif
85#ifdef WITH_SHA2
86#ifdef HAVE_OPENSSL_SHA2_H
87#include <openssl/sha2.h>
88#else
89#include "crypto/sha2/sha2.h"
90#endif
91#endif
92#include "plog.h"
93
94/* 0.9.7 stuff? */
95#if OPENSSL_VERSION_NUMBER < 0x0090700fL
96typedef STACK_OF(GENERAL_NAME) GENERAL_NAMES;
97#else
98#define USE_NEW_DES_API
99#endif
100
101#define OpenSSL_BUG()	do { plog(LLV_ERROR, LOCATION, NULL, "OpenSSL function failed\n"); } while(0)
102
103#include "var.h"
104#include "misc.h"
105#include "vmbuf.h"
106#include "plog.h"
107#include "crypto_openssl.h"
108#include "debug.h"
109#include "gcmalloc.h"
110
111/*
112 * I hate to cast every parameter to des_xx into void *, but it is
113 * necessary for SSLeay/OpenSSL portability.  It sucks.
114 */
115
116static int cb_check_cert_local __P((int, X509_STORE_CTX *));
117static int cb_check_cert_remote __P((int, X509_STORE_CTX *));
118static X509 *mem2x509 __P((vchar_t *));
119
120static caddr_t eay_hmac_init __P((vchar_t *, const EVP_MD *));
121
122/* X509 Certificate */
123/*
124 * convert the string of the subject name into DER
125 * e.g. str = "C=JP, ST=Kanagawa";
126 */
127vchar_t *
128eay_str2asn1dn(str, len)
129	const char *str;
130	int len;
131{
132	X509_NAME *name;
133	char *buf;
134	char *field, *value;
135	int i, j;
136	vchar_t *ret = NULL;
137	caddr_t p;
138
139	if (len == -1)
140		len = strlen(str);
141
142	buf = racoon_malloc(len + 1);
143	if (!buf) {
144		plog(LLV_WARNING, LOCATION, NULL,"failed to allocate buffer\n");
145		return NULL;
146	}
147	memcpy(buf, str, len);
148
149	name = X509_NAME_new();
150
151	field = &buf[0];
152	value = NULL;
153	for (i = 0; i < len; i++) {
154		if (!value && buf[i] == '=') {
155			buf[i] = '\0';
156			value = &buf[i + 1];
157			continue;
158		} else if (buf[i] == ',' || buf[i] == '/') {
159			buf[i] = '\0';
160
161			plog(LLV_DEBUG, LOCATION, NULL, "DN: %s=%s\n",
162			     field, value);
163
164			if (!value) goto err;
165			if (!X509_NAME_add_entry_by_txt(name, field,
166					(value[0] == '*' && value[1] == 0) ?
167						V_ASN1_PRINTABLESTRING : MBSTRING_ASC,
168					(unsigned char *) value, -1, -1, 0)) {
169				plog(LLV_ERROR, LOCATION, NULL,
170				     "Invalid DN field: %s=%s\n",
171				     field, value);
172				plog(LLV_ERROR, LOCATION, NULL,
173				     "%s\n", eay_strerror());
174				goto err;
175			}
176			for (j = i + 1; j < len; j++) {
177				if (buf[j] != ' ')
178					break;
179			}
180			field = &buf[j];
181			value = NULL;
182			continue;
183		}
184	}
185	buf[len] = '\0';
186
187	plog(LLV_DEBUG, LOCATION, NULL, "DN: %s=%s\n",
188	     field, value);
189
190	if (!value) goto err;
191	if (!X509_NAME_add_entry_by_txt(name, field,
192			(value[0] == '*' && value[1] == 0) ?
193				V_ASN1_PRINTABLESTRING : MBSTRING_ASC,
194			(unsigned char *) value, -1, -1, 0)) {
195		plog(LLV_ERROR, LOCATION, NULL,
196		     "Invalid DN field: %s=%s\n",
197		     field, value);
198		plog(LLV_ERROR, LOCATION, NULL,
199		     "%s\n", eay_strerror());
200		goto err;
201	}
202
203	i = i2d_X509_NAME(name, NULL);
204	if (!i)
205		goto err;
206	ret = vmalloc(i);
207	if (!ret)
208		goto err;
209	p = ret->v;
210	i = i2d_X509_NAME(name, (void *)&p);
211	if (!i)
212		goto err;
213
214	return ret;
215
216    err:
217	if (buf)
218		racoon_free(buf);
219	if (name)
220		X509_NAME_free(name);
221	if (ret)
222		vfree(ret);
223	return NULL;
224}
225
226/*
227 * convert the hex string of the subject name into DER
228 */
229vchar_t *
230eay_hex2asn1dn(const char *hex, int len)
231{
232	BIGNUM *bn = BN_new();
233	char *binbuf;
234	size_t binlen;
235	vchar_t *ret = NULL;
236
237	if (len == -1)
238		len = strlen(hex);
239
240	if (BN_hex2bn(&bn, hex) != len) {
241		plog(LLV_ERROR, LOCATION, NULL,
242		     "conversion of Hex-encoded ASN1 string to binary failed: %s\n",
243		     eay_strerror());
244		goto out;
245	}
246
247	binlen = BN_num_bytes(bn);
248	ret = vmalloc(binlen);
249	if (!ret) {
250		plog(LLV_WARNING, LOCATION, NULL,"failed to allocate buffer\n");
251		return NULL;
252	}
253	binbuf = ret->v;
254
255	BN_bn2bin(bn, (unsigned char *) binbuf);
256
257out:
258	BN_free(bn);
259
260	return ret;
261}
262
263/*
264 * The following are derived from code in crypto/x509/x509_cmp.c
265 * in OpenSSL0.9.7c:
266 * X509_NAME_wildcmp() adds wildcard matching to the original
267 * X509_NAME_cmp(), nocase_cmp() and nocase_spacenorm_cmp() are as is.
268 */
269#include <ctype.h>
270/* Case insensitive string comparision */
271static int nocase_cmp(const ASN1_STRING *a, const ASN1_STRING *b)
272{
273	int i;
274
275	if (a->length != b->length)
276		return (a->length - b->length);
277
278	for (i=0; i<a->length; i++)
279	{
280		int ca, cb;
281
282		ca = tolower(a->data[i]);
283		cb = tolower(b->data[i]);
284
285		if (ca != cb)
286			return(ca-cb);
287	}
288	return 0;
289}
290
291/* Case insensitive string comparision with space normalization
292 * Space normalization - ignore leading, trailing spaces,
293 *       multiple spaces between characters are replaced by single space
294 */
295static int nocase_spacenorm_cmp(const ASN1_STRING *a, const ASN1_STRING *b)
296{
297	unsigned char *pa = NULL, *pb = NULL;
298	int la, lb;
299
300	la = a->length;
301	lb = b->length;
302	pa = a->data;
303	pb = b->data;
304
305	/* skip leading spaces */
306	while (la > 0 && isspace(*pa))
307	{
308		la--;
309		pa++;
310	}
311	while (lb > 0 && isspace(*pb))
312	{
313		lb--;
314		pb++;
315	}
316
317	/* skip trailing spaces */
318	while (la > 0 && isspace(pa[la-1]))
319		la--;
320	while (lb > 0 && isspace(pb[lb-1]))
321		lb--;
322
323	/* compare strings with space normalization */
324	while (la > 0 && lb > 0)
325	{
326		int ca, cb;
327
328		/* compare character */
329		ca = tolower(*pa);
330		cb = tolower(*pb);
331		if (ca != cb)
332			return (ca - cb);
333
334		pa++; pb++;
335		la--; lb--;
336
337		if (la <= 0 || lb <= 0)
338			break;
339
340		/* is white space next character ? */
341		if (isspace(*pa) && isspace(*pb))
342		{
343			/* skip remaining white spaces */
344			while (la > 0 && isspace(*pa))
345			{
346				la--;
347				pa++;
348			}
349			while (lb > 0 && isspace(*pb))
350			{
351				lb--;
352				pb++;
353			}
354		}
355	}
356	if (la > 0 || lb > 0)
357		return la - lb;
358
359	return 0;
360}
361
362static int X509_NAME_wildcmp(const X509_NAME *a, const X509_NAME *b)
363{
364    int i,j;
365    X509_NAME_ENTRY *na,*nb;
366
367    if (sk_X509_NAME_ENTRY_num(a->entries)
368	!= sk_X509_NAME_ENTRY_num(b->entries))
369	    return sk_X509_NAME_ENTRY_num(a->entries)
370	      -sk_X509_NAME_ENTRY_num(b->entries);
371    for (i=sk_X509_NAME_ENTRY_num(a->entries)-1; i>=0; i--)
372    {
373	    na=sk_X509_NAME_ENTRY_value(a->entries,i);
374	    nb=sk_X509_NAME_ENTRY_value(b->entries,i);
375	    j=OBJ_cmp(na->object,nb->object);
376	    if (j) return(j);
377	    if ((na->value->length == 1 && na->value->data[0] == '*')
378	     || (nb->value->length == 1 && nb->value->data[0] == '*'))
379		    continue;
380	    j=na->value->type-nb->value->type;
381	    if (j) return(j);
382	    if (na->value->type == V_ASN1_PRINTABLESTRING)
383		    j=nocase_spacenorm_cmp(na->value, nb->value);
384	    else if (na->value->type == V_ASN1_IA5STRING
385		    && OBJ_obj2nid(na->object) == NID_pkcs9_emailAddress)
386		    j=nocase_cmp(na->value, nb->value);
387	    else
388		    {
389		    j=na->value->length-nb->value->length;
390		    if (j) return(j);
391		    j=memcmp(na->value->data,nb->value->data,
392			    na->value->length);
393		    }
394	    if (j) return(j);
395	    j=na->set-nb->set;
396	    if (j) return(j);
397    }
398
399    return(0);
400}
401
402/*
403 * compare two subjectNames.
404 * OUT:        0: equal
405 *	positive:
406 *	      -1: other error.
407 */
408int
409eay_cmp_asn1dn(n1, n2)
410	vchar_t *n1, *n2;
411{
412	X509_NAME *a = NULL, *b = NULL;
413	caddr_t p;
414	int i = -1;
415
416	p = n1->v;
417	if (!d2i_X509_NAME(&a, (void *)&p, n1->l))
418		goto end;
419	p = n2->v;
420	if (!d2i_X509_NAME(&b, (void *)&p, n2->l))
421		goto end;
422
423	i = X509_NAME_wildcmp(a, b);
424
425    end:
426	if (a)
427		X509_NAME_free(a);
428	if (b)
429		X509_NAME_free(b);
430	return i;
431}
432
433/*
434 * this functions is derived from apps/verify.c in OpenSSL0.9.5
435 */
436int
437eay_check_x509cert(cert, CApath, CAfile, local)
438	vchar_t *cert;
439	char *CApath;
440	char *CAfile;
441	int local;
442{
443	X509_STORE *cert_ctx = NULL;
444	X509_LOOKUP *lookup = NULL;
445	X509 *x509 = NULL;
446	X509_STORE_CTX *csc;
447	int error = -1;
448
449	cert_ctx = X509_STORE_new();
450	if (cert_ctx == NULL)
451		goto end;
452
453	if (local)
454		X509_STORE_set_verify_cb_func(cert_ctx, cb_check_cert_local);
455	else
456		X509_STORE_set_verify_cb_func(cert_ctx, cb_check_cert_remote);
457
458	lookup = X509_STORE_add_lookup(cert_ctx, X509_LOOKUP_file());
459	if (lookup == NULL)
460		goto end;
461
462	X509_LOOKUP_load_file(lookup, CAfile,
463	    (CAfile == NULL) ? X509_FILETYPE_DEFAULT : X509_FILETYPE_PEM);
464
465	lookup = X509_STORE_add_lookup(cert_ctx, X509_LOOKUP_hash_dir());
466	if (lookup == NULL)
467		goto end;
468	error = X509_LOOKUP_add_dir(lookup, CApath, X509_FILETYPE_PEM);
469	if(!error) {
470		error = -1;
471		goto end;
472	}
473	error = -1;	/* initialized */
474
475	/* read the certificate to be verified */
476	x509 = mem2x509(cert);
477	if (x509 == NULL)
478		goto end;
479
480	csc = X509_STORE_CTX_new();
481	if (csc == NULL)
482		goto end;
483	X509_STORE_CTX_init(csc, cert_ctx, x509, NULL);
484#if OPENSSL_VERSION_NUMBER >= 0x00907000L
485	X509_STORE_CTX_set_flags (csc, X509_V_FLAG_CRL_CHECK);
486	X509_STORE_CTX_set_flags (csc, X509_V_FLAG_CRL_CHECK_ALL);
487#endif
488	error = X509_verify_cert(csc);
489	X509_STORE_CTX_cleanup(csc);
490
491	/*
492	 * if x509_verify_cert() is successful then the value of error is
493	 * set non-zero.
494	 */
495	error = error ? 0 : -1;
496
497end:
498	if (error)
499		plog(LLV_WARNING, LOCATION, NULL,"%s\n", eay_strerror());
500	if (cert_ctx != NULL)
501		X509_STORE_free(cert_ctx);
502	if (x509 != NULL)
503		X509_free(x509);
504
505	return(error);
506}
507
508/*
509 * callback function for verifing certificate.
510 * this function is derived from cb() in openssl/apps/s_server.c
511 */
512static int
513cb_check_cert_local(ok, ctx)
514	int ok;
515	X509_STORE_CTX *ctx;
516{
517	char buf[256];
518	int log_tag;
519
520	if (!ok) {
521		X509_NAME_oneline(
522				X509_get_subject_name(ctx->current_cert),
523				buf,
524				256);
525		/*
526		 * since we are just checking the certificates, it is
527		 * ok if they are self signed. But we should still warn
528		 * the user.
529 		 */
530		switch (ctx->error) {
531		case X509_V_ERR_CERT_HAS_EXPIRED:
532		case X509_V_ERR_DEPTH_ZERO_SELF_SIGNED_CERT:
533		case X509_V_ERR_INVALID_CA:
534		case X509_V_ERR_PATH_LENGTH_EXCEEDED:
535		case X509_V_ERR_INVALID_PURPOSE:
536		case X509_V_ERR_UNABLE_TO_GET_CRL:
537			ok = 1;
538			log_tag = LLV_WARNING;
539			break;
540		default:
541			log_tag = LLV_ERROR;
542		}
543		plog(log_tag, LOCATION, NULL,
544			"%s(%d) at depth:%d SubjectName:%s\n",
545			X509_verify_cert_error_string(ctx->error),
546			ctx->error,
547			ctx->error_depth,
548			buf);
549	}
550	ERR_clear_error();
551
552	return ok;
553}
554
555/*
556 * callback function for verifing remote certificates.
557 * this function is derived from cb() in openssl/apps/s_server.c
558 */
559static int
560cb_check_cert_remote(ok, ctx)
561	int ok;
562	X509_STORE_CTX *ctx;
563{
564	char buf[256];
565	int log_tag;
566
567	if (!ok) {
568		X509_NAME_oneline(
569				X509_get_subject_name(ctx->current_cert),
570				buf,
571				256);
572		switch (ctx->error) {
573		case X509_V_ERR_UNABLE_TO_GET_CRL:
574			ok = 1;
575			log_tag = LLV_WARNING;
576			break;
577		default:
578			log_tag = LLV_ERROR;
579		}
580		plog(log_tag, LOCATION, NULL,
581			"%s(%d) at depth:%d SubjectName:%s\n",
582			X509_verify_cert_error_string(ctx->error),
583			ctx->error,
584			ctx->error_depth,
585			buf);
586	}
587	ERR_clear_error();
588
589	return ok;
590}
591
592/*
593 * get a subjectAltName from X509 certificate.
594 */
595vchar_t *
596eay_get_x509asn1subjectname(cert)
597	vchar_t *cert;
598{
599	X509 *x509 = NULL;
600	u_char *bp;
601	vchar_t *name = NULL;
602	int len;
603
604	bp = (unsigned char *) cert->v;
605
606	x509 = mem2x509(cert);
607	if (x509 == NULL)
608		goto error;
609
610	/* get the length of the name */
611	len = i2d_X509_NAME(x509->cert_info->subject, NULL);
612	name = vmalloc(len);
613	if (!name)
614		goto error;
615	/* get the name */
616	bp = (unsigned char *) name->v;
617	len = i2d_X509_NAME(x509->cert_info->subject, &bp);
618
619	X509_free(x509);
620
621	return name;
622
623error:
624	plog(LLV_ERROR, LOCATION, NULL, "%s\n", eay_strerror());
625
626	if (name != NULL)
627		vfree(name);
628
629	if (x509 != NULL)
630		X509_free(x509);
631
632	return NULL;
633}
634
635/*
636 * get the subjectAltName from X509 certificate.
637 * the name must be terminated by '\0'.
638 */
639int
640eay_get_x509subjectaltname(cert, altname, type, pos)
641	vchar_t *cert;
642	char **altname;
643	int *type;
644	int pos;
645{
646	X509 *x509 = NULL;
647	GENERAL_NAMES *gens = NULL;
648	GENERAL_NAME *gen;
649	int len;
650	int error = -1;
651
652	*altname = NULL;
653	*type = GENT_OTHERNAME;
654
655	x509 = mem2x509(cert);
656	if (x509 == NULL)
657		goto end;
658
659	gens = X509_get_ext_d2i(x509, NID_subject_alt_name, NULL, NULL);
660	if (gens == NULL)
661		goto end;
662
663	/* there is no data at "pos" */
664	if (pos > sk_GENERAL_NAME_num(gens))
665		goto end;
666
667	gen = sk_GENERAL_NAME_value(gens, pos - 1);
668
669	/* read DNSName / Email */
670	if (gen->type == GEN_DNS	||
671		gen->type == GEN_EMAIL	||
672		gen->type == GEN_URI )
673	{
674		/* make sure if the data is terminated by '\0'. */
675		if (gen->d.ia5->data[gen->d.ia5->length] != '\0')
676		{
677			plog(LLV_ERROR, LOCATION, NULL,
678				 "data is not terminated by NUL.");
679			racoon_hexdump(gen->d.ia5->data, gen->d.ia5->length + 1);
680			goto end;
681		}
682
683		len = gen->d.ia5->length + 1;
684		*altname = racoon_malloc(len);
685		if (!*altname)
686			goto end;
687
688		strlcpy(*altname, (char *) gen->d.ia5->data, len);
689		*type = gen->type;
690		error = 0;
691	}
692	/* read IP address */
693	else if (gen->type == GEN_IPADD)
694	{
695		unsigned char p[5], *ip;
696		ip = p;
697
698		/* only support IPv4 */
699		if (gen->d.ip->length != 4)
700			goto end;
701
702		/* convert Octet String to String
703		 * XXX ???????
704		 */
705		/*i2d_ASN1_OCTET_STRING(gen->d.ip,&ip);*/
706		ip = gen->d.ip->data;
707
708		/* XXX Magic, enough for an IPv4 address
709		 */
710		*altname = racoon_malloc(20);
711		if (!*altname)
712			goto end;
713
714		sprintf(*altname, "%u.%u.%u.%u", ip[0], ip[1], ip[2], ip[3]);
715		*type = gen->type;
716		error = 0;
717	}
718	/* XXX other possible types ?
719	 * For now, error will be -1 if unsupported type
720	 */
721
722end:
723	if (error) {
724		if (*altname) {
725			racoon_free(*altname);
726			*altname = NULL;
727		}
728		plog(LLV_ERROR, LOCATION, NULL, "%s\n", eay_strerror());
729	}
730	if (x509)
731		X509_free(x509);
732	if (gens)
733		/* free the whole stack. */
734		sk_GENERAL_NAME_pop_free(gens, GENERAL_NAME_free);
735
736	return error;
737}
738
739
740/*
741 * decode a X509 certificate and make a readable text terminated '\n'.
742 * return the buffer allocated, so must free it later.
743 */
744char *
745eay_get_x509text(cert)
746	vchar_t *cert;
747{
748	X509 *x509 = NULL;
749	BIO *bio = NULL;
750	char *text = NULL;
751	u_char *bp = NULL;
752	int len = 0;
753	int error = -1;
754
755	x509 = mem2x509(cert);
756	if (x509 == NULL)
757		goto end;
758
759	bio = BIO_new(BIO_s_mem());
760	if (bio == NULL)
761		goto end;
762
763	error = X509_print(bio, x509);
764	if (error != 1) {
765		error = -1;
766		goto end;
767	}
768
769	len = BIO_get_mem_data(bio, &bp);
770	text = racoon_malloc(len + 1);
771	if (text == NULL)
772		goto end;
773	memcpy(text, bp, len);
774	text[len] = '\0';
775
776	error = 0;
777
778    end:
779	if (error) {
780		if (text) {
781			racoon_free(text);
782			text = NULL;
783		}
784		plog(LLV_ERROR, LOCATION, NULL, "%s\n", eay_strerror());
785	}
786	if (bio)
787		BIO_free(bio);
788	if (x509)
789		X509_free(x509);
790
791	return text;
792}
793
794/* get X509 structure from buffer. */
795static X509 *
796mem2x509(cert)
797	vchar_t *cert;
798{
799	X509 *x509;
800
801#ifndef EAYDEBUG
802    {
803	u_char *bp;
804
805	bp = (unsigned char *) cert->v;
806
807	x509 = d2i_X509(NULL, (void *)&bp, cert->l);
808    }
809#else
810    {
811	BIO *bio;
812	int len;
813
814	bio = BIO_new(BIO_s_mem());
815	if (bio == NULL)
816		return NULL;
817	len = BIO_write(bio, cert->v, cert->l);
818	if (len == -1)
819		return NULL;
820	x509 = PEM_read_bio_X509(bio, NULL, NULL, NULL);
821	BIO_free(bio);
822    }
823#endif
824	return x509;
825}
826
827/*
828 * get a X509 certificate from local file.
829 * a certificate must be PEM format.
830 * Input:
831 *	path to a certificate.
832 * Output:
833 *	NULL if error occured
834 *	other is the cert.
835 */
836vchar_t *
837eay_get_x509cert(path)
838	char *path;
839{
840	FILE *fp;
841	X509 *x509;
842	vchar_t *cert;
843	u_char *bp;
844	int len;
845	int error;
846
847	/* Read private key */
848	fp = fopen(path, "r");
849	if (fp == NULL)
850		return NULL;
851	x509 = PEM_read_X509(fp, NULL, NULL, NULL);
852	fclose (fp);
853
854	if (x509 == NULL)
855		return NULL;
856
857	len = i2d_X509(x509, NULL);
858	cert = vmalloc(len);
859	if (cert == NULL) {
860		X509_free(x509);
861		return NULL;
862	}
863	bp = (unsigned char *) cert->v;
864	error = i2d_X509(x509, &bp);
865	X509_free(x509);
866
867	if (error == 0) {
868		vfree(cert);
869		return NULL;
870	}
871
872	return cert;
873}
874
875/*
876 * check a X509 signature
877 *	XXX: to be get hash type from my cert ?
878 *		to be handled EVP_dss().
879 * OUT: return -1 when error.
880 *	0
881 */
882int
883eay_check_x509sign(source, sig, cert)
884	vchar_t *source;
885	vchar_t *sig;
886	vchar_t *cert;
887{
888	X509 *x509;
889	u_char *bp;
890	EVP_PKEY *evp;
891	int res;
892
893	bp = (unsigned char *) cert->v;
894
895	x509 = d2i_X509(NULL, (void *)&bp, cert->l);
896	if (x509 == NULL) {
897		plog(LLV_ERROR, LOCATION, NULL, "d2i_X509(): %s\n", eay_strerror());
898		return -1;
899	}
900
901	evp = X509_get_pubkey(x509);
902	if (! evp) {
903		plog(LLV_ERROR, LOCATION, NULL, "X509_get_pubkey(): %s\n", eay_strerror());
904		X509_free(x509);
905		return -1;
906	}
907
908	res = eay_rsa_verify(source, sig, evp->pkey.rsa);
909
910	EVP_PKEY_free(evp);
911	X509_free(x509);
912
913	return res;
914}
915
916/*
917 * check RSA signature
918 * OUT: return -1 when error.
919 *	0 on success
920 */
921int
922eay_check_rsasign(source, sig, rsa)
923	vchar_t *source;
924	vchar_t *sig;
925	RSA *rsa;
926{
927	return eay_rsa_verify(source, sig, rsa);
928}
929
930/*
931 * get PKCS#1 Private Key of PEM format from local file.
932 */
933vchar_t *
934eay_get_pkcs1privkey(path)
935	char *path;
936{
937	FILE *fp;
938	EVP_PKEY *evp = NULL;
939	vchar_t *pkey = NULL;
940	u_char *bp;
941	int pkeylen;
942	int error = -1;
943
944	/* Read private key */
945	fp = fopen(path, "r");
946	if (fp == NULL)
947		return NULL;
948
949	evp = PEM_read_PrivateKey(fp, NULL, NULL, NULL);
950
951	fclose (fp);
952
953	if (evp == NULL)
954		return NULL;
955
956	pkeylen = i2d_PrivateKey(evp, NULL);
957	if (pkeylen == 0)
958		goto end;
959	pkey = vmalloc(pkeylen);
960	if (pkey == NULL)
961		goto end;
962	bp = (unsigned char *) pkey->v;
963	pkeylen = i2d_PrivateKey(evp, &bp);
964	if (pkeylen == 0)
965		goto end;
966
967	error = 0;
968
969end:
970	if (evp != NULL)
971		EVP_PKEY_free(evp);
972	if (error != 0 && pkey != NULL) {
973		vfree(pkey);
974		pkey = NULL;
975	}
976
977	return pkey;
978}
979
980/*
981 * get PKCS#1 Public Key of PEM format from local file.
982 */
983vchar_t *
984eay_get_pkcs1pubkey(path)
985	char *path;
986{
987	FILE *fp;
988	EVP_PKEY *evp = NULL;
989	vchar_t *pkey = NULL;
990	X509 *x509 = NULL;
991	u_char *bp;
992	int pkeylen;
993	int error = -1;
994
995	/* Read private key */
996	fp = fopen(path, "r");
997	if (fp == NULL)
998		return NULL;
999
1000	x509 = PEM_read_X509(fp, NULL, NULL, NULL);
1001
1002	fclose (fp);
1003
1004	if (x509 == NULL)
1005		return NULL;
1006
1007	/* Get public key - eay */
1008	evp = X509_get_pubkey(x509);
1009	if (evp == NULL)
1010		return NULL;
1011
1012	pkeylen = i2d_PublicKey(evp, NULL);
1013	if (pkeylen == 0)
1014		goto end;
1015	pkey = vmalloc(pkeylen);
1016	if (pkey == NULL)
1017		goto end;
1018	bp = (unsigned char *) pkey->v;
1019	pkeylen = i2d_PublicKey(evp, &bp);
1020	if (pkeylen == 0)
1021		goto end;
1022
1023	error = 0;
1024end:
1025	if (evp != NULL)
1026		EVP_PKEY_free(evp);
1027	if (error != 0 && pkey != NULL) {
1028		vfree(pkey);
1029		pkey = NULL;
1030	}
1031
1032	return pkey;
1033}
1034
1035vchar_t *
1036eay_get_x509sign(src, privkey)
1037	vchar_t *src, *privkey;
1038{
1039	EVP_PKEY *evp;
1040	u_char *bp = (unsigned char *) privkey->v;
1041	vchar_t *sig = NULL;
1042	int len;
1043	int pad = RSA_PKCS1_PADDING;
1044
1045	/* XXX to be handled EVP_PKEY_DSA */
1046	evp = d2i_PrivateKey(EVP_PKEY_RSA, NULL, (void *)&bp, privkey->l);
1047	if (evp == NULL)
1048		return NULL;
1049
1050	sig = eay_rsa_sign(src, evp->pkey.rsa);
1051
1052	EVP_PKEY_free(evp);
1053
1054	return sig;
1055}
1056
1057vchar_t *
1058eay_get_rsasign(src, rsa)
1059	vchar_t *src;
1060	RSA *rsa;
1061{
1062	return eay_rsa_sign(src, rsa);
1063}
1064
1065vchar_t *
1066eay_rsa_sign(vchar_t *src, RSA *rsa)
1067{
1068	int len;
1069	vchar_t *sig = NULL;
1070	int pad = RSA_PKCS1_PADDING;
1071
1072	len = RSA_size(rsa);
1073
1074	sig = vmalloc(len);
1075	if (sig == NULL)
1076		return NULL;
1077
1078	len = RSA_private_encrypt(src->l, (unsigned char *) src->v,
1079			(unsigned char *) sig->v, rsa, pad);
1080
1081	if (len == 0 || len != sig->l) {
1082		vfree(sig);
1083		sig = NULL;
1084	}
1085
1086	return sig;
1087}
1088
1089int
1090eay_rsa_verify(src, sig, rsa)
1091	vchar_t *src, *sig;
1092	RSA *rsa;
1093{
1094	vchar_t *xbuf = NULL;
1095	int pad = RSA_PKCS1_PADDING;
1096	int len = 0;
1097	int error;
1098
1099	len = RSA_size(rsa);
1100	xbuf = vmalloc(len);
1101	if (xbuf == NULL) {
1102		plog(LLV_ERROR, LOCATION, NULL, "%s\n", eay_strerror());
1103		return -1;
1104	}
1105
1106	len = RSA_public_decrypt(sig->l, (unsigned char *) sig->v,
1107			(unsigned char *) xbuf->v, rsa, pad);
1108	if (len == 0 || len != src->l) {
1109		plog(LLV_ERROR, LOCATION, NULL, "%s\n", eay_strerror());
1110		vfree(xbuf);
1111		return -1;
1112	}
1113
1114	error = memcmp(src->v, xbuf->v, src->l);
1115	vfree(xbuf);
1116	if (error != 0)
1117		return -1;
1118
1119	return 0;
1120}
1121
1122/*
1123 * get error string
1124 * MUST load ERR_load_crypto_strings() first.
1125 */
1126char *
1127eay_strerror()
1128{
1129	static char ebuf[512];
1130	int len = 0, n;
1131	unsigned long l;
1132	char buf[200];
1133	const char *file, *data;
1134	int line, flags;
1135	unsigned long es;
1136
1137	es = CRYPTO_thread_id();
1138
1139	while ((l = ERR_get_error_line_data(&file, &line, &data, &flags)) != 0){
1140		n = snprintf(ebuf + len, sizeof(ebuf) - len,
1141				"%lu:%s:%s:%d:%s ",
1142				es, ERR_error_string(l, buf), file, line,
1143				(flags & ERR_TXT_STRING) ? data : "");
1144		if (n < 0 || n >= sizeof(ebuf) - len)
1145			break;
1146		len += n;
1147		if (sizeof(ebuf) < len)
1148			break;
1149	}
1150
1151	return ebuf;
1152}
1153
1154vchar_t *
1155evp_crypt(vchar_t *data, vchar_t *key, vchar_t *iv, const EVP_CIPHER *e, int enc)
1156{
1157	vchar_t *res;
1158	EVP_CIPHER_CTX ctx;
1159
1160	if (!e)
1161		return NULL;
1162
1163	if (data->l % EVP_CIPHER_block_size(e))
1164		return NULL;
1165
1166	if ((res = vmalloc(data->l)) == NULL)
1167		return NULL;
1168
1169	EVP_CIPHER_CTX_init(&ctx);
1170
1171	switch(EVP_CIPHER_nid(e)){
1172	case NID_bf_cbc:
1173	case NID_bf_ecb:
1174	case NID_bf_cfb64:
1175	case NID_bf_ofb64:
1176	case NID_cast5_cbc:
1177	case NID_cast5_ecb:
1178	case NID_cast5_cfb64:
1179	case NID_cast5_ofb64:
1180		/* XXX: can we do that also for algos with a fixed key size ?
1181		 */
1182		/* init context without key/iv
1183         */
1184        if (!EVP_CipherInit(&ctx, e, NULL, NULL, enc))
1185        {
1186            OpenSSL_BUG();
1187            vfree(res);
1188            return NULL;
1189        }
1190
1191        /* update key size
1192         */
1193        if (!EVP_CIPHER_CTX_set_key_length(&ctx, key->l))
1194        {
1195            OpenSSL_BUG();
1196            vfree(res);
1197            return NULL;
1198        }
1199
1200        /* finalize context init with desired key size
1201         */
1202        if (!EVP_CipherInit(&ctx, NULL, (u_char *) key->v,
1203							(u_char *) iv->v, enc))
1204        {
1205            OpenSSL_BUG();
1206            vfree(res);
1207            return NULL;
1208		}
1209		break;
1210	default:
1211		if (!EVP_CipherInit(&ctx, e, (u_char *) key->v,
1212							(u_char *) iv->v, enc)) {
1213			OpenSSL_BUG();
1214			vfree(res);
1215			return NULL;
1216		}
1217	}
1218
1219	/* disable openssl padding */
1220	EVP_CIPHER_CTX_set_padding(&ctx, 0);
1221
1222	if (!EVP_Cipher(&ctx, (u_char *) res->v, (u_char *) data->v, data->l)) {
1223		OpenSSL_BUG();
1224		vfree(res);
1225		return NULL;
1226	}
1227
1228	EVP_CIPHER_CTX_cleanup(&ctx);
1229
1230	return res;
1231}
1232
1233int
1234evp_weakkey(vchar_t *key, const EVP_CIPHER *e)
1235{
1236	return 0;
1237}
1238
1239int
1240evp_keylen(int len, const EVP_CIPHER *e)
1241{
1242	if (!e)
1243		return -1;
1244	/* EVP functions return lengths in bytes, ipsec-tools
1245	 * uses lengths in bits, therefore conversion is required. --AK
1246	 */
1247	if (len != 0 && len != (EVP_CIPHER_key_length(e) << 3))
1248		return -1;
1249
1250	return EVP_CIPHER_key_length(e) << 3;
1251}
1252
1253/*
1254 * DES-CBC
1255 */
1256vchar_t *
1257eay_des_encrypt(data, key, iv)
1258	vchar_t *data, *key, *iv;
1259{
1260	return evp_crypt(data, key, iv, EVP_des_cbc(), 1);
1261}
1262
1263vchar_t *
1264eay_des_decrypt(data, key, iv)
1265	vchar_t *data, *key, *iv;
1266{
1267	return evp_crypt(data, key, iv, EVP_des_cbc(), 0);
1268}
1269
1270int
1271eay_des_weakkey(key)
1272	vchar_t *key;
1273{
1274#ifdef USE_NEW_DES_API
1275	return DES_is_weak_key((void *)key->v);
1276#else
1277	return des_is_weak_key((void *)key->v);
1278#endif
1279}
1280
1281int
1282eay_des_keylen(len)
1283	int len;
1284{
1285	return evp_keylen(len, EVP_des_cbc());
1286}
1287
1288#ifdef HAVE_OPENSSL_IDEA_H
1289/*
1290 * IDEA-CBC
1291 */
1292vchar_t *
1293eay_idea_encrypt(data, key, iv)
1294	vchar_t *data, *key, *iv;
1295{
1296	vchar_t *res;
1297	IDEA_KEY_SCHEDULE ks;
1298
1299	idea_set_encrypt_key((unsigned char *)key->v, &ks);
1300
1301	/* allocate buffer for result */
1302	if ((res = vmalloc(data->l)) == NULL)
1303		return NULL;
1304
1305	/* decryption data */
1306	idea_cbc_encrypt((unsigned char *)data->v, (unsigned char *)res->v, data->l,
1307			&ks, (unsigned char *)iv->v, IDEA_ENCRYPT);
1308
1309	return res;
1310}
1311
1312vchar_t *
1313eay_idea_decrypt(data, key, iv)
1314	vchar_t *data, *key, *iv;
1315{
1316	vchar_t *res;
1317	IDEA_KEY_SCHEDULE ks, dks;
1318
1319	idea_set_encrypt_key((unsigned char *)key->v, &ks);
1320	idea_set_decrypt_key(&ks, &dks);
1321
1322	/* allocate buffer for result */
1323	if ((res = vmalloc(data->l)) == NULL)
1324		return NULL;
1325
1326	/* decryption data */
1327	idea_cbc_encrypt((unsigned char *)data->v, (unsigned char *)res->v, data->l,
1328			&dks, (unsigned char *)iv->v, IDEA_DECRYPT);
1329
1330	return res;
1331}
1332
1333int
1334eay_idea_weakkey(key)
1335	vchar_t *key;
1336{
1337	return 0;       /* XXX */
1338}
1339
1340int
1341eay_idea_keylen(len)
1342	int len;
1343{
1344	if (len != 0 && len != 128)
1345		return -1;
1346	return 128;
1347}
1348#endif
1349
1350/*
1351 * BLOWFISH-CBC
1352 */
1353vchar_t *
1354eay_bf_encrypt(data, key, iv)
1355	vchar_t *data, *key, *iv;
1356{
1357	return evp_crypt(data, key, iv, EVP_bf_cbc(), 1);
1358}
1359
1360vchar_t *
1361eay_bf_decrypt(data, key, iv)
1362	vchar_t *data, *key, *iv;
1363{
1364	return evp_crypt(data, key, iv, EVP_bf_cbc(), 0);
1365}
1366
1367int
1368eay_bf_weakkey(key)
1369	vchar_t *key;
1370{
1371	return 0;	/* XXX to be done. refer to RFC 2451 */
1372}
1373
1374int
1375eay_bf_keylen(len)
1376	int len;
1377{
1378	if (len == 0)
1379		return 448;
1380	if (len < 40 || len > 448)
1381		return -1;
1382	return len;
1383}
1384
1385#ifdef HAVE_OPENSSL_RC5_H
1386/*
1387 * RC5-CBC
1388 */
1389vchar_t *
1390eay_rc5_encrypt(data, key, iv)
1391	vchar_t *data, *key, *iv;
1392{
1393	vchar_t *res;
1394	RC5_32_KEY ks;
1395
1396	/* in RFC 2451, there is information about the number of round. */
1397	RC5_32_set_key(&ks, key->l, (unsigned char *)key->v, 16);
1398
1399	/* allocate buffer for result */
1400	if ((res = vmalloc(data->l)) == NULL)
1401		return NULL;
1402
1403	/* decryption data */
1404	RC5_32_cbc_encrypt((unsigned char *)data->v, (unsigned char *)res->v, data->l,
1405		&ks, (unsigned char *)iv->v, RC5_ENCRYPT);
1406
1407	return res;
1408}
1409
1410vchar_t *
1411eay_rc5_decrypt(data, key, iv)
1412	vchar_t *data, *key, *iv;
1413{
1414	vchar_t *res;
1415	RC5_32_KEY ks;
1416
1417	/* in RFC 2451, there is information about the number of round. */
1418	RC5_32_set_key(&ks, key->l, (unsigned char *)key->v, 16);
1419
1420	/* allocate buffer for result */
1421	if ((res = vmalloc(data->l)) == NULL)
1422		return NULL;
1423
1424	/* decryption data */
1425	RC5_32_cbc_encrypt((unsigned char *)data->v, (unsigned char *)res->v, data->l,
1426		&ks, (unsigned char *)iv->v, RC5_DECRYPT);
1427
1428	return res;
1429}
1430
1431int
1432eay_rc5_weakkey(key)
1433	vchar_t *key;
1434{
1435	return 0;       /* No known weak keys when used with 16 rounds. */
1436
1437}
1438
1439int
1440eay_rc5_keylen(len)
1441	int len;
1442{
1443	if (len == 0)
1444		return 128;
1445	if (len < 40 || len > 2040)
1446		return -1;
1447	return len;
1448}
1449#endif
1450
1451/*
1452 * 3DES-CBC
1453 */
1454vchar_t *
1455eay_3des_encrypt(data, key, iv)
1456	vchar_t *data, *key, *iv;
1457{
1458	return evp_crypt(data, key, iv, EVP_des_ede3_cbc(), 1);
1459}
1460
1461vchar_t *
1462eay_3des_decrypt(data, key, iv)
1463	vchar_t *data, *key, *iv;
1464{
1465	return evp_crypt(data, key, iv, EVP_des_ede3_cbc(), 0);
1466}
1467
1468int
1469eay_3des_weakkey(key)
1470	vchar_t *key;
1471{
1472#ifdef USE_NEW_DES_API
1473	return (DES_is_weak_key((void *)key->v) ||
1474	    DES_is_weak_key((void *)(key->v + 8)) ||
1475	    DES_is_weak_key((void *)(key->v + 16)));
1476#else
1477	if (key->l < 24)
1478		return 0;
1479
1480	return (des_is_weak_key((void *)key->v) ||
1481	    des_is_weak_key((void *)(key->v + 8)) ||
1482	    des_is_weak_key((void *)(key->v + 16)));
1483#endif
1484}
1485
1486int
1487eay_3des_keylen(len)
1488	int len;
1489{
1490	if (len != 0 && len != 192)
1491		return -1;
1492	return 192;
1493}
1494
1495/*
1496 * CAST-CBC
1497 */
1498vchar_t *
1499eay_cast_encrypt(data, key, iv)
1500	vchar_t *data, *key, *iv;
1501{
1502	return evp_crypt(data, key, iv, EVP_cast5_cbc(), 1);
1503}
1504
1505vchar_t *
1506eay_cast_decrypt(data, key, iv)
1507	vchar_t *data, *key, *iv;
1508{
1509	return evp_crypt(data, key, iv, EVP_cast5_cbc(), 0);
1510}
1511
1512int
1513eay_cast_weakkey(key)
1514	vchar_t *key;
1515{
1516	return 0;	/* No known weak keys. */
1517}
1518
1519int
1520eay_cast_keylen(len)
1521	int len;
1522{
1523	if (len == 0)
1524		return 128;
1525	if (len < 40 || len > 128)
1526		return -1;
1527	return len;
1528}
1529
1530/*
1531 * AES(RIJNDAEL)-CBC
1532 */
1533#ifndef HAVE_OPENSSL_AES_H
1534vchar_t *
1535eay_aes_encrypt(data, key, iv)
1536	vchar_t *data, *key, *iv;
1537{
1538	vchar_t *res;
1539	keyInstance k;
1540	cipherInstance c;
1541
1542	memset(&k, 0, sizeof(k));
1543	if (rijndael_makeKey(&k, DIR_ENCRYPT, key->l << 3, key->v) < 0)
1544		return NULL;
1545
1546	/* allocate buffer for result */
1547	if ((res = vmalloc(data->l)) == NULL)
1548		return NULL;
1549
1550	/* encryption data */
1551	memset(&c, 0, sizeof(c));
1552	if (rijndael_cipherInit(&c, MODE_CBC, iv->v) < 0){
1553		vfree(res);
1554		return NULL;
1555	}
1556	if (rijndael_blockEncrypt(&c, &k, data->v, data->l << 3, res->v) < 0){
1557		vfree(res);
1558		return NULL;
1559	}
1560
1561	return res;
1562}
1563
1564vchar_t *
1565eay_aes_decrypt(data, key, iv)
1566	vchar_t *data, *key, *iv;
1567{
1568	vchar_t *res;
1569	keyInstance k;
1570	cipherInstance c;
1571
1572	memset(&k, 0, sizeof(k));
1573	if (rijndael_makeKey(&k, DIR_DECRYPT, key->l << 3, key->v) < 0)
1574		return NULL;
1575
1576	/* allocate buffer for result */
1577	if ((res = vmalloc(data->l)) == NULL)
1578		return NULL;
1579
1580	/* decryption data */
1581	memset(&c, 0, sizeof(c));
1582	if (rijndael_cipherInit(&c, MODE_CBC, iv->v) < 0){
1583		vfree(res);
1584		return NULL;
1585	}
1586	if (rijndael_blockDecrypt(&c, &k, data->v, data->l << 3, res->v) < 0){
1587		vfree(res);
1588		return NULL;
1589	}
1590
1591	return res;
1592}
1593#else
1594static inline const EVP_CIPHER *
1595aes_evp_by_keylen(int keylen)
1596{
1597	switch(keylen) {
1598		case 16:
1599		case 128:
1600			return EVP_aes_128_cbc();
1601		case 24:
1602		case 192:
1603			return EVP_aes_192_cbc();
1604		case 32:
1605		case 256:
1606			return EVP_aes_256_cbc();
1607		default:
1608			return NULL;
1609	}
1610}
1611
1612vchar_t *
1613eay_aes_encrypt(data, key, iv)
1614       vchar_t *data, *key, *iv;
1615{
1616	return evp_crypt(data, key, iv, aes_evp_by_keylen(key->l), 1);
1617}
1618
1619vchar_t *
1620eay_aes_decrypt(data, key, iv)
1621       vchar_t *data, *key, *iv;
1622{
1623	return evp_crypt(data, key, iv, aes_evp_by_keylen(key->l), 0);
1624}
1625#endif
1626
1627int
1628eay_aes_weakkey(key)
1629	vchar_t *key;
1630{
1631	return 0;
1632}
1633
1634int
1635eay_aes_keylen(len)
1636	int len;
1637{
1638	if (len == 0)
1639		return 128;
1640	if (len != 128 && len != 192 && len != 256)
1641		return -1;
1642	return len;
1643}
1644
1645#if defined(HAVE_OPENSSL_CAMELLIA_H)
1646/*
1647 * CAMELLIA-CBC
1648 */
1649static inline const EVP_CIPHER *
1650camellia_evp_by_keylen(int keylen)
1651{
1652	switch(keylen) {
1653		case 16:
1654		case 128:
1655			return EVP_camellia_128_cbc();
1656		case 24:
1657		case 192:
1658			return EVP_camellia_192_cbc();
1659		case 32:
1660		case 256:
1661			return EVP_camellia_256_cbc();
1662		default:
1663			return NULL;
1664	}
1665}
1666
1667vchar_t *
1668eay_camellia_encrypt(data, key, iv)
1669       vchar_t *data, *key, *iv;
1670{
1671	return evp_crypt(data, key, iv, camellia_evp_by_keylen(key->l), 1);
1672}
1673
1674vchar_t *
1675eay_camellia_decrypt(data, key, iv)
1676       vchar_t *data, *key, *iv;
1677{
1678	return evp_crypt(data, key, iv, camellia_evp_by_keylen(key->l), 0);
1679}
1680
1681int
1682eay_camellia_weakkey(key)
1683	vchar_t *key;
1684{
1685	return 0;
1686}
1687
1688int
1689eay_camellia_keylen(len)
1690	int len;
1691{
1692	if (len == 0)
1693		return 128;
1694	if (len != 128 && len != 192 && len != 256)
1695		return -1;
1696	return len;
1697}
1698
1699#endif
1700
1701/* for ipsec part */
1702int
1703eay_null_hashlen()
1704{
1705	return 0;
1706}
1707
1708int
1709eay_kpdk_hashlen()
1710{
1711	return 0;
1712}
1713
1714int
1715eay_twofish_keylen(len)
1716	int len;
1717{
1718	if (len < 0 || len > 256)
1719		return -1;
1720	return len;
1721}
1722
1723int
1724eay_null_keylen(len)
1725	int len;
1726{
1727	return 0;
1728}
1729
1730/*
1731 * HMAC functions
1732 */
1733static caddr_t
1734eay_hmac_init(key, md)
1735	vchar_t *key;
1736	const EVP_MD *md;
1737{
1738	HMAC_CTX *c = racoon_malloc(sizeof(*c));
1739
1740	HMAC_Init(c, key->v, key->l, md);
1741
1742	return (caddr_t)c;
1743}
1744
1745#ifdef WITH_SHA2
1746/*
1747 * HMAC SHA2-512
1748 */
1749vchar_t *
1750eay_hmacsha2_512_one(key, data)
1751	vchar_t *key, *data;
1752{
1753	vchar_t *res;
1754	caddr_t ctx;
1755
1756	ctx = eay_hmacsha2_512_init(key);
1757	eay_hmacsha2_512_update(ctx, data);
1758	res = eay_hmacsha2_512_final(ctx);
1759
1760	return(res);
1761}
1762
1763caddr_t
1764eay_hmacsha2_512_init(key)
1765	vchar_t *key;
1766{
1767	return eay_hmac_init(key, EVP_sha2_512());
1768}
1769
1770void
1771eay_hmacsha2_512_update(c, data)
1772	caddr_t c;
1773	vchar_t *data;
1774{
1775	HMAC_Update((HMAC_CTX *)c, (unsigned char *) data->v, data->l);
1776}
1777
1778vchar_t *
1779eay_hmacsha2_512_final(c)
1780	caddr_t c;
1781{
1782	vchar_t *res;
1783	unsigned int l;
1784
1785	if ((res = vmalloc(SHA512_DIGEST_LENGTH)) == 0)
1786		return NULL;
1787
1788	HMAC_Final((HMAC_CTX *)c, (unsigned char *) res->v, &l);
1789	res->l = l;
1790	HMAC_cleanup((HMAC_CTX *)c);
1791	(void)racoon_free(c);
1792
1793	if (SHA512_DIGEST_LENGTH != res->l) {
1794		plog(LLV_ERROR, LOCATION, NULL,
1795			"hmac sha2_512 length mismatch %zd.\n", res->l);
1796		vfree(res);
1797		return NULL;
1798	}
1799
1800	return(res);
1801}
1802
1803/*
1804 * HMAC SHA2-384
1805 */
1806vchar_t *
1807eay_hmacsha2_384_one(key, data)
1808	vchar_t *key, *data;
1809{
1810	vchar_t *res;
1811	caddr_t ctx;
1812
1813	ctx = eay_hmacsha2_384_init(key);
1814	eay_hmacsha2_384_update(ctx, data);
1815	res = eay_hmacsha2_384_final(ctx);
1816
1817	return(res);
1818}
1819
1820caddr_t
1821eay_hmacsha2_384_init(key)
1822	vchar_t *key;
1823{
1824	return eay_hmac_init(key, EVP_sha2_384());
1825}
1826
1827void
1828eay_hmacsha2_384_update(c, data)
1829	caddr_t c;
1830	vchar_t *data;
1831{
1832	HMAC_Update((HMAC_CTX *)c, (unsigned char *) data->v, data->l);
1833}
1834
1835vchar_t *
1836eay_hmacsha2_384_final(c)
1837	caddr_t c;
1838{
1839	vchar_t *res;
1840	unsigned int l;
1841
1842	if ((res = vmalloc(SHA384_DIGEST_LENGTH)) == 0)
1843		return NULL;
1844
1845	HMAC_Final((HMAC_CTX *)c, (unsigned char *) res->v, &l);
1846	res->l = l;
1847	HMAC_cleanup((HMAC_CTX *)c);
1848	(void)racoon_free(c);
1849
1850	if (SHA384_DIGEST_LENGTH != res->l) {
1851		plog(LLV_ERROR, LOCATION, NULL,
1852			"hmac sha2_384 length mismatch %zd.\n", res->l);
1853		vfree(res);
1854		return NULL;
1855	}
1856
1857	return(res);
1858}
1859
1860/*
1861 * HMAC SHA2-256
1862 */
1863vchar_t *
1864eay_hmacsha2_256_one(key, data)
1865	vchar_t *key, *data;
1866{
1867	vchar_t *res;
1868	caddr_t ctx;
1869
1870	ctx = eay_hmacsha2_256_init(key);
1871	eay_hmacsha2_256_update(ctx, data);
1872	res = eay_hmacsha2_256_final(ctx);
1873
1874	return(res);
1875}
1876
1877caddr_t
1878eay_hmacsha2_256_init(key)
1879	vchar_t *key;
1880{
1881	return eay_hmac_init(key, EVP_sha2_256());
1882}
1883
1884void
1885eay_hmacsha2_256_update(c, data)
1886	caddr_t c;
1887	vchar_t *data;
1888{
1889	HMAC_Update((HMAC_CTX *)c, (unsigned char *) data->v, data->l);
1890}
1891
1892vchar_t *
1893eay_hmacsha2_256_final(c)
1894	caddr_t c;
1895{
1896	vchar_t *res;
1897	unsigned int l;
1898
1899	if ((res = vmalloc(SHA256_DIGEST_LENGTH)) == 0)
1900		return NULL;
1901
1902	HMAC_Final((HMAC_CTX *)c, (unsigned char *) res->v, &l);
1903	res->l = l;
1904	HMAC_cleanup((HMAC_CTX *)c);
1905	(void)racoon_free(c);
1906
1907	if (SHA256_DIGEST_LENGTH != res->l) {
1908		plog(LLV_ERROR, LOCATION, NULL,
1909			"hmac sha2_256 length mismatch %zd.\n", res->l);
1910		vfree(res);
1911		return NULL;
1912	}
1913
1914	return(res);
1915}
1916#endif	/* WITH_SHA2 */
1917
1918/*
1919 * HMAC SHA1
1920 */
1921vchar_t *
1922eay_hmacsha1_one(key, data)
1923	vchar_t *key, *data;
1924{
1925	vchar_t *res;
1926	caddr_t ctx;
1927
1928	ctx = eay_hmacsha1_init(key);
1929	eay_hmacsha1_update(ctx, data);
1930	res = eay_hmacsha1_final(ctx);
1931
1932	return(res);
1933}
1934
1935caddr_t
1936eay_hmacsha1_init(key)
1937	vchar_t *key;
1938{
1939	return eay_hmac_init(key, EVP_sha1());
1940}
1941
1942void
1943eay_hmacsha1_update(c, data)
1944	caddr_t c;
1945	vchar_t *data;
1946{
1947	HMAC_Update((HMAC_CTX *)c, (unsigned char *) data->v, data->l);
1948}
1949
1950vchar_t *
1951eay_hmacsha1_final(c)
1952	caddr_t c;
1953{
1954	vchar_t *res;
1955	unsigned int l;
1956
1957	if ((res = vmalloc(SHA_DIGEST_LENGTH)) == 0)
1958		return NULL;
1959
1960	HMAC_Final((HMAC_CTX *)c, (unsigned char *) res->v, &l);
1961	res->l = l;
1962	HMAC_cleanup((HMAC_CTX *)c);
1963	(void)racoon_free(c);
1964
1965	if (SHA_DIGEST_LENGTH != res->l) {
1966		plog(LLV_ERROR, LOCATION, NULL,
1967			"hmac sha1 length mismatch %zd.\n", res->l);
1968		vfree(res);
1969		return NULL;
1970	}
1971
1972	return(res);
1973}
1974
1975/*
1976 * HMAC MD5
1977 */
1978vchar_t *
1979eay_hmacmd5_one(key, data)
1980	vchar_t *key, *data;
1981{
1982	vchar_t *res;
1983	caddr_t ctx;
1984
1985	ctx = eay_hmacmd5_init(key);
1986	eay_hmacmd5_update(ctx, data);
1987	res = eay_hmacmd5_final(ctx);
1988
1989	return(res);
1990}
1991
1992caddr_t
1993eay_hmacmd5_init(key)
1994	vchar_t *key;
1995{
1996	return eay_hmac_init(key, EVP_md5());
1997}
1998
1999void
2000eay_hmacmd5_update(c, data)
2001	caddr_t c;
2002	vchar_t *data;
2003{
2004	HMAC_Update((HMAC_CTX *)c, (unsigned char *) data->v, data->l);
2005}
2006
2007vchar_t *
2008eay_hmacmd5_final(c)
2009	caddr_t c;
2010{
2011	vchar_t *res;
2012	unsigned int l;
2013
2014	if ((res = vmalloc(MD5_DIGEST_LENGTH)) == 0)
2015		return NULL;
2016
2017	HMAC_Final((HMAC_CTX *)c, (unsigned char *) res->v, &l);
2018	res->l = l;
2019	HMAC_cleanup((HMAC_CTX *)c);
2020	(void)racoon_free(c);
2021
2022	if (MD5_DIGEST_LENGTH != res->l) {
2023		plog(LLV_ERROR, LOCATION, NULL,
2024			"hmac md5 length mismatch %zd.\n", res->l);
2025		vfree(res);
2026		return NULL;
2027	}
2028
2029	return(res);
2030}
2031
2032#ifdef WITH_SHA2
2033/*
2034 * SHA2-512 functions
2035 */
2036caddr_t
2037eay_sha2_512_init()
2038{
2039	SHA512_CTX *c = racoon_malloc(sizeof(*c));
2040
2041	SHA512_Init(c);
2042
2043	return((caddr_t)c);
2044}
2045
2046void
2047eay_sha2_512_update(c, data)
2048	caddr_t c;
2049	vchar_t *data;
2050{
2051	SHA512_Update((SHA512_CTX *)c, (unsigned char *) data->v, data->l);
2052
2053	return;
2054}
2055
2056vchar_t *
2057eay_sha2_512_final(c)
2058	caddr_t c;
2059{
2060	vchar_t *res;
2061
2062	if ((res = vmalloc(SHA512_DIGEST_LENGTH)) == 0)
2063		return(0);
2064
2065	SHA512_Final((unsigned char *) res->v, (SHA512_CTX *)c);
2066	(void)racoon_free(c);
2067
2068	return(res);
2069}
2070
2071vchar_t *
2072eay_sha2_512_one(data)
2073	vchar_t *data;
2074{
2075	caddr_t ctx;
2076	vchar_t *res;
2077
2078	ctx = eay_sha2_512_init();
2079	eay_sha2_512_update(ctx, data);
2080	res = eay_sha2_512_final(ctx);
2081
2082	return(res);
2083}
2084
2085int
2086eay_sha2_512_hashlen()
2087{
2088	return SHA512_DIGEST_LENGTH << 3;
2089}
2090#endif
2091
2092#ifdef WITH_SHA2
2093/*
2094 * SHA2-384 functions
2095 */
2096caddr_t
2097eay_sha2_384_init()
2098{
2099	SHA384_CTX *c = racoon_malloc(sizeof(*c));
2100
2101	SHA384_Init(c);
2102
2103	return((caddr_t)c);
2104}
2105
2106void
2107eay_sha2_384_update(c, data)
2108	caddr_t c;
2109	vchar_t *data;
2110{
2111	SHA384_Update((SHA384_CTX *)c, (unsigned char *) data->v, data->l);
2112
2113	return;
2114}
2115
2116vchar_t *
2117eay_sha2_384_final(c)
2118	caddr_t c;
2119{
2120	vchar_t *res;
2121
2122	if ((res = vmalloc(SHA384_DIGEST_LENGTH)) == 0)
2123		return(0);
2124
2125	SHA384_Final((unsigned char *) res->v, (SHA384_CTX *)c);
2126	(void)racoon_free(c);
2127
2128	return(res);
2129}
2130
2131vchar_t *
2132eay_sha2_384_one(data)
2133	vchar_t *data;
2134{
2135	caddr_t ctx;
2136	vchar_t *res;
2137
2138	ctx = eay_sha2_384_init();
2139	eay_sha2_384_update(ctx, data);
2140	res = eay_sha2_384_final(ctx);
2141
2142	return(res);
2143}
2144
2145int
2146eay_sha2_384_hashlen()
2147{
2148	return SHA384_DIGEST_LENGTH << 3;
2149}
2150#endif
2151
2152#ifdef WITH_SHA2
2153/*
2154 * SHA2-256 functions
2155 */
2156caddr_t
2157eay_sha2_256_init()
2158{
2159	SHA256_CTX *c = racoon_malloc(sizeof(*c));
2160
2161	SHA256_Init(c);
2162
2163	return((caddr_t)c);
2164}
2165
2166void
2167eay_sha2_256_update(c, data)
2168	caddr_t c;
2169	vchar_t *data;
2170{
2171	SHA256_Update((SHA256_CTX *)c, (unsigned char *) data->v, data->l);
2172
2173	return;
2174}
2175
2176vchar_t *
2177eay_sha2_256_final(c)
2178	caddr_t c;
2179{
2180	vchar_t *res;
2181
2182	if ((res = vmalloc(SHA256_DIGEST_LENGTH)) == 0)
2183		return(0);
2184
2185	SHA256_Final((unsigned char *) res->v, (SHA256_CTX *)c);
2186	(void)racoon_free(c);
2187
2188	return(res);
2189}
2190
2191vchar_t *
2192eay_sha2_256_one(data)
2193	vchar_t *data;
2194{
2195	caddr_t ctx;
2196	vchar_t *res;
2197
2198	ctx = eay_sha2_256_init();
2199	eay_sha2_256_update(ctx, data);
2200	res = eay_sha2_256_final(ctx);
2201
2202	return(res);
2203}
2204
2205int
2206eay_sha2_256_hashlen()
2207{
2208	return SHA256_DIGEST_LENGTH << 3;
2209}
2210#endif
2211
2212/*
2213 * SHA functions
2214 */
2215caddr_t
2216eay_sha1_init()
2217{
2218	SHA_CTX *c = racoon_malloc(sizeof(*c));
2219
2220	SHA1_Init(c);
2221
2222	return((caddr_t)c);
2223}
2224
2225void
2226eay_sha1_update(c, data)
2227	caddr_t c;
2228	vchar_t *data;
2229{
2230	SHA1_Update((SHA_CTX *)c, data->v, data->l);
2231
2232	return;
2233}
2234
2235vchar_t *
2236eay_sha1_final(c)
2237	caddr_t c;
2238{
2239	vchar_t *res;
2240
2241	if ((res = vmalloc(SHA_DIGEST_LENGTH)) == 0)
2242		return(0);
2243
2244	SHA1_Final((unsigned char *) res->v, (SHA_CTX *)c);
2245	(void)racoon_free(c);
2246
2247	return(res);
2248}
2249
2250vchar_t *
2251eay_sha1_one(data)
2252	vchar_t *data;
2253{
2254	caddr_t ctx;
2255	vchar_t *res;
2256
2257	ctx = eay_sha1_init();
2258	eay_sha1_update(ctx, data);
2259	res = eay_sha1_final(ctx);
2260
2261	return(res);
2262}
2263
2264int
2265eay_sha1_hashlen()
2266{
2267	return SHA_DIGEST_LENGTH << 3;
2268}
2269
2270/*
2271 * MD5 functions
2272 */
2273caddr_t
2274eay_md5_init()
2275{
2276	MD5_CTX *c = racoon_malloc(sizeof(*c));
2277
2278	MD5_Init(c);
2279
2280	return((caddr_t)c);
2281}
2282
2283void
2284eay_md5_update(c, data)
2285	caddr_t c;
2286	vchar_t *data;
2287{
2288	MD5_Update((MD5_CTX *)c, data->v, data->l);
2289
2290	return;
2291}
2292
2293vchar_t *
2294eay_md5_final(c)
2295	caddr_t c;
2296{
2297	vchar_t *res;
2298
2299	if ((res = vmalloc(MD5_DIGEST_LENGTH)) == 0)
2300		return(0);
2301
2302	MD5_Final((unsigned char *) res->v, (MD5_CTX *)c);
2303	(void)racoon_free(c);
2304
2305	return(res);
2306}
2307
2308vchar_t *
2309eay_md5_one(data)
2310	vchar_t *data;
2311{
2312	caddr_t ctx;
2313	vchar_t *res;
2314
2315	ctx = eay_md5_init();
2316	eay_md5_update(ctx, data);
2317	res = eay_md5_final(ctx);
2318
2319	return(res);
2320}
2321
2322int
2323eay_md5_hashlen()
2324{
2325	return MD5_DIGEST_LENGTH << 3;
2326}
2327
2328/*
2329 * eay_set_random
2330 *   size: number of bytes.
2331 */
2332vchar_t *
2333eay_set_random(size)
2334	u_int32_t size;
2335{
2336	BIGNUM *r = NULL;
2337	vchar_t *res = 0;
2338
2339	if ((r = BN_new()) == NULL)
2340		goto end;
2341	BN_rand(r, size * 8, 0, 0);
2342	eay_bn2v(&res, r);
2343
2344end:
2345	if (r)
2346		BN_free(r);
2347	return(res);
2348}
2349
2350/* DH */
2351int
2352eay_dh_generate(prime, g, publen, pub, priv)
2353	vchar_t *prime, **pub, **priv;
2354	u_int publen;
2355	u_int32_t g;
2356{
2357	BIGNUM *p = NULL;
2358	DH *dh = NULL;
2359	int error = -1;
2360
2361	/* initialize */
2362	/* pre-process to generate number */
2363	if (eay_v2bn(&p, prime) < 0)
2364		goto end;
2365
2366	if ((dh = DH_new()) == NULL)
2367		goto end;
2368	dh->p = p;
2369	p = NULL;	/* p is now part of dh structure */
2370	dh->g = NULL;
2371	if ((dh->g = BN_new()) == NULL)
2372		goto end;
2373	if (!BN_set_word(dh->g, g))
2374		goto end;
2375
2376	if (publen != 0)
2377		dh->length = publen;
2378
2379	/* generate public and private number */
2380	if (!DH_generate_key(dh))
2381		goto end;
2382
2383	/* copy results to buffers */
2384	if (eay_bn2v(pub, dh->pub_key) < 0)
2385		goto end;
2386	if (eay_bn2v(priv, dh->priv_key) < 0) {
2387		vfree(*pub);
2388		goto end;
2389	}
2390
2391	error = 0;
2392
2393end:
2394	if (dh != NULL)
2395		DH_free(dh);
2396	if (p != 0)
2397		BN_free(p);
2398	return(error);
2399}
2400
2401int
2402eay_dh_compute(prime, g, pub, priv, pub2, key)
2403	vchar_t *prime, *pub, *priv, *pub2, **key;
2404	u_int32_t g;
2405{
2406	BIGNUM *dh_pub = NULL;
2407	DH *dh = NULL;
2408	int l;
2409	unsigned char *v = NULL;
2410	int error = -1;
2411
2412	/* make public number to compute */
2413	if (eay_v2bn(&dh_pub, pub2) < 0)
2414		goto end;
2415
2416	/* make DH structure */
2417	if ((dh = DH_new()) == NULL)
2418		goto end;
2419	if (eay_v2bn(&dh->p, prime) < 0)
2420		goto end;
2421	if (eay_v2bn(&dh->pub_key, pub) < 0)
2422		goto end;
2423	if (eay_v2bn(&dh->priv_key, priv) < 0)
2424		goto end;
2425	dh->length = pub2->l * 8;
2426
2427	dh->g = NULL;
2428	if ((dh->g = BN_new()) == NULL)
2429		goto end;
2430	if (!BN_set_word(dh->g, g))
2431		goto end;
2432
2433	if ((v = racoon_calloc(prime->l, sizeof(u_char))) == NULL)
2434		goto end;
2435	if ((l = DH_compute_key(v, dh_pub, dh)) == -1)
2436		goto end;
2437	memcpy((*key)->v + (prime->l - l), v, l);
2438
2439	error = 0;
2440
2441end:
2442	if (dh_pub != NULL)
2443		BN_free(dh_pub);
2444	if (dh != NULL)
2445		DH_free(dh);
2446	if (v != NULL)
2447		racoon_free(v);
2448	return(error);
2449}
2450
2451/*
2452 * convert vchar_t <-> BIGNUM.
2453 *
2454 * vchar_t: unit is u_char, network endian, most significant byte first.
2455 * BIGNUM: unit is BN_ULONG, each of BN_ULONG is in host endian,
2456 *	least significant BN_ULONG must come first.
2457 *
2458 * hex value of "0x3ffe050104" is represented as follows:
2459 *	vchar_t: 3f fe 05 01 04
2460 *	BIGNUM (BN_ULONG = u_int8_t): 04 01 05 fe 3f
2461 *	BIGNUM (BN_ULONG = u_int16_t): 0x0104 0xfe05 0x003f
2462 *	BIGNUM (BN_ULONG = u_int32_t_t): 0xfe050104 0x0000003f
2463 */
2464int
2465eay_v2bn(bn, var)
2466	BIGNUM **bn;
2467	vchar_t *var;
2468{
2469	if ((*bn = BN_bin2bn((unsigned char *) var->v, var->l, NULL)) == NULL)
2470		return -1;
2471
2472	return 0;
2473}
2474
2475int
2476eay_bn2v(var, bn)
2477	vchar_t **var;
2478	BIGNUM *bn;
2479{
2480	*var = vmalloc(bn->top * BN_BYTES);
2481	if (*var == NULL)
2482		return(-1);
2483
2484	(*var)->l = BN_bn2bin(bn, (unsigned char *) (*var)->v);
2485
2486	return 0;
2487}
2488
2489void
2490eay_init()
2491{
2492	OpenSSL_add_all_algorithms();
2493	ERR_load_crypto_strings();
2494#ifdef HAVE_OPENSSL_ENGINE_H
2495	ENGINE_load_builtin_engines();
2496	ENGINE_register_all_complete();
2497#endif
2498}
2499
2500vchar_t *
2501base64_decode(char *in, long inlen)
2502{
2503	BIO *bio=NULL, *b64=NULL;
2504	vchar_t *res = NULL;
2505	char *outb;
2506	long outlen;
2507
2508	outb = malloc(inlen * 2);
2509	if (outb == NULL)
2510		goto out;
2511	bio = BIO_new_mem_buf(in, inlen);
2512	b64 = BIO_new(BIO_f_base64());
2513	BIO_set_flags(b64, BIO_FLAGS_BASE64_NO_NL);
2514	bio = BIO_push(b64, bio);
2515
2516	outlen = BIO_read(bio, outb, inlen * 2);
2517	if (outlen <= 0) {
2518		plog(LLV_ERROR, LOCATION, NULL, "%s\n", eay_strerror());
2519		goto out;
2520	}
2521
2522	res = vmalloc(outlen);
2523	if (!res)
2524		goto out;
2525
2526	memcpy(res->v, outb, outlen);
2527
2528out:
2529	if (outb)
2530		free(outb);
2531	if (bio)
2532		BIO_free_all(bio);
2533
2534	return res;
2535}
2536
2537vchar_t *
2538base64_encode(char *in, long inlen)
2539{
2540	BIO *bio=NULL, *b64=NULL;
2541	char *ptr;
2542	long plen = -1;
2543	vchar_t *res = NULL;
2544
2545	bio = BIO_new(BIO_s_mem());
2546	b64 = BIO_new(BIO_f_base64());
2547	BIO_set_flags(b64, BIO_FLAGS_BASE64_NO_NL);
2548	bio = BIO_push(b64, bio);
2549
2550	BIO_write(bio, in, inlen);
2551	BIO_flush(bio);
2552
2553	plen = BIO_get_mem_data(bio, &ptr);
2554	res = vmalloc(plen+1);
2555	if (!res)
2556		goto out;
2557
2558	memcpy (res->v, ptr, plen);
2559	res->v[plen] = '\0';
2560
2561out:
2562	if (bio)
2563		BIO_free_all(bio);
2564
2565	return res;
2566}
2567
2568static RSA *
2569binbuf_pubkey2rsa(vchar_t *binbuf)
2570{
2571	BIGNUM *exp, *mod;
2572	RSA *rsa_pub = NULL;
2573
2574	if (binbuf->v[0] > binbuf->l - 1) {
2575		plog(LLV_ERROR, LOCATION, NULL, "Plain RSA pubkey format error: decoded string doesn't make sense.\n");
2576		goto out;
2577	}
2578
2579	exp = BN_bin2bn((unsigned char *) (binbuf->v + 1), binbuf->v[0], NULL);
2580	mod = BN_bin2bn((unsigned char *) (binbuf->v + binbuf->v[0] + 1),
2581			binbuf->l - binbuf->v[0] - 1, NULL);
2582	rsa_pub = RSA_new();
2583
2584	if (!exp || !mod || !rsa_pub) {
2585		plog(LLV_ERROR, LOCATION, NULL, "Plain RSA pubkey parsing error: %s\n", eay_strerror());
2586		if (exp)
2587			BN_free(exp);
2588		if (mod)
2589			BN_free(exp);
2590		if (rsa_pub)
2591			RSA_free(rsa_pub);
2592		rsa_pub = NULL;
2593		goto out;
2594	}
2595
2596	rsa_pub->n = mod;
2597	rsa_pub->e = exp;
2598
2599out:
2600	return rsa_pub;
2601}
2602
2603RSA *
2604base64_pubkey2rsa(char *in)
2605{
2606	BIGNUM *exp, *mod;
2607	RSA *rsa_pub = NULL;
2608	vchar_t *binbuf;
2609
2610	if (strncmp(in, "0s", 2) != 0) {
2611		plog(LLV_ERROR, LOCATION, NULL, "Plain RSA pubkey format error: doesn't start with '0s'\n");
2612		return NULL;
2613	}
2614
2615	binbuf = base64_decode(in + 2, strlen(in + 2));
2616	if (!binbuf) {
2617		plog(LLV_ERROR, LOCATION, NULL, "Plain RSA pubkey format error: Base64 decoding failed.\n");
2618		return NULL;
2619	}
2620
2621	if (binbuf->v[0] > binbuf->l - 1) {
2622		plog(LLV_ERROR, LOCATION, NULL, "Plain RSA pubkey format error: decoded string doesn't make sense.\n");
2623		goto out;
2624	}
2625
2626	rsa_pub = binbuf_pubkey2rsa(binbuf);
2627
2628out:
2629	if (binbuf)
2630		vfree(binbuf);
2631
2632	return rsa_pub;
2633}
2634
2635RSA *
2636bignum_pubkey2rsa(BIGNUM *in)
2637{
2638	RSA *rsa_pub = NULL;
2639	vchar_t *binbuf;
2640
2641	binbuf = vmalloc(BN_num_bytes(in));
2642	if (!binbuf) {
2643		plog(LLV_ERROR, LOCATION, NULL, "Plain RSA pubkey conversion: memory allocation failed..\n");
2644		return NULL;
2645	}
2646
2647	BN_bn2bin(in, (unsigned char *) binbuf->v);
2648
2649	rsa_pub = binbuf_pubkey2rsa(binbuf);
2650
2651out:
2652	if (binbuf)
2653		vfree(binbuf);
2654
2655	return rsa_pub;
2656}
2657
2658u_int32_t
2659eay_random()
2660{
2661	u_int32_t result;
2662	vchar_t *vrand;
2663
2664	vrand = eay_set_random(sizeof(result));
2665	memcpy(&result, vrand->v, sizeof(result));
2666	vfree(vrand);
2667
2668	return result;
2669}
2670
2671const char *
2672eay_version()
2673{
2674	return SSLeay_version(SSLEAY_VERSION);
2675}
2676