55b18a5248b3305d80b069c6d0eca199d50b04c0
[strongswan.git] / src / libstrongswan / plugins / openssl / openssl_util.c
1 /*
2 * Copyright (C) 2009 Martin Willi
3 * Copyright (C) 2008 Tobias Brunner
4 * Hochschule fuer Technik Rapperswil
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License as published by the
8 * Free Software Foundation; either version 2 of the License, or (at your
9 * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>.
10 *
11 * This program is distributed in the hope that it will be useful, but
12 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
13 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * for more details.
15 */
16
17 #include "openssl_util.h"
18
19 #include <debug.h>
20
21 #include <openssl/evp.h>
22 #include <openssl/x509.h>
23
24 /**
25 * Described in header.
26 */
27 bool openssl_hash_chunk(int hash_type, chunk_t data, chunk_t *hash)
28 {
29 EVP_MD_CTX *ctx;
30 bool ret = FALSE;
31 const EVP_MD *hasher = EVP_get_digestbynid(hash_type);
32 if (!hasher)
33 {
34 return FALSE;
35 }
36
37 ctx = EVP_MD_CTX_create();
38 if (!ctx)
39 {
40 goto error;
41 }
42
43 if (!EVP_DigestInit_ex(ctx, hasher, NULL))
44 {
45 goto error;
46 }
47
48 if (!EVP_DigestUpdate(ctx, data.ptr, data.len))
49 {
50 goto error;
51 }
52
53 *hash = chunk_alloc(hasher->md_size);
54 if (!EVP_DigestFinal_ex(ctx, hash->ptr, NULL))
55 {
56 chunk_free(hash);
57 goto error;
58 }
59
60 ret = TRUE;
61 error:
62 if (ctx)
63 {
64 EVP_MD_CTX_destroy(ctx);
65 }
66 return ret;
67 }
68
69 /**
70 * Described in header.
71 */
72 bool openssl_bn_cat(int len, BIGNUM *a, BIGNUM *b, chunk_t *chunk)
73 {
74 int offset;
75
76 chunk->len = len + (b ? len : 0);
77 chunk->ptr = malloc(chunk->len);
78 memset(chunk->ptr, 0, chunk->len);
79
80 /* convert a */
81 offset = len - BN_num_bytes(a);
82 if (!BN_bn2bin(a, chunk->ptr + offset))
83 {
84 goto error;
85 }
86
87 /* optionally convert and concatenate b */
88 if (b)
89 {
90 offset = len - BN_num_bytes(b);
91 if (!BN_bn2bin(b, chunk->ptr + len + offset))
92 {
93 goto error;
94 }
95 }
96
97 return TRUE;
98 error:
99 chunk_free(chunk);
100 return FALSE;
101 }
102
103
104 /**
105 * Described in header.
106 */
107 bool openssl_bn_split(chunk_t chunk, BIGNUM *a, BIGNUM *b)
108 {
109 int len;
110
111 if ((chunk.len % 2) != 0)
112 {
113 return FALSE;
114 }
115
116 len = chunk.len / 2;
117
118 if (!BN_bin2bn(chunk.ptr, len, a) ||
119 !BN_bin2bn(chunk.ptr + len, len, b))
120 {
121 return FALSE;
122 }
123
124 return TRUE;
125 }
126