2 * OPENSSL crypto backend implementation
4 * Copyright (C) 2010-2012, Red Hat, Inc. All rights reserved.
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License
8 * version 2 as published by the Free Software Foundation.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
19 * In addition, as a special exception, the copyright holders give
20 * permission to link the code of portions of this program with the
21 * OpenSSL library under certain conditions as described in each
22 * individual source file, and distribute linked combinations
25 * You must obey the GNU General Public License in all respects
26 * for all of the code used other than OpenSSL.
31 #include <openssl/evp.h>
32 #include <openssl/hmac.h>
33 #include <openssl/rand.h>
34 #include "crypto_backend.h"
36 static int crypto_backend_initialised = 0;
40 const EVP_MD *hash_id;
46 const EVP_MD *hash_id;
50 int crypt_backend_init(struct crypt_device *ctx)
52 if (crypto_backend_initialised)
55 OpenSSL_add_all_algorithms();
57 crypto_backend_initialised = 1;
61 uint32_t crypt_backend_flags(void)
66 const char *crypt_backend_version(void)
68 return SSLeay_version(SSLEAY_VERSION);
72 int crypt_hash_size(const char *name)
74 const EVP_MD *hash_id = EVP_get_digestbyname(name);
79 return EVP_MD_size(hash_id);
82 int crypt_hash_init(struct crypt_hash **ctx, const char *name)
86 h = malloc(sizeof(*h));
90 h->hash_id = EVP_get_digestbyname(name);
96 if (EVP_DigestInit(&h->md, h->hash_id) != 1) {
101 h->hash_len = EVP_MD_size(h->hash_id);
106 static int crypt_hash_restart(struct crypt_hash *ctx)
108 if (EVP_DigestInit(&ctx->md, ctx->hash_id) != 1)
114 int crypt_hash_write(struct crypt_hash *ctx, const char *buffer, size_t length)
116 if (EVP_DigestUpdate(&ctx->md, buffer, length) != 1)
122 int crypt_hash_final(struct crypt_hash *ctx, char *buffer, size_t length)
124 unsigned char tmp[EVP_MAX_MD_SIZE];
125 unsigned int tmp_len = 0;
127 if (length > (size_t)ctx->hash_len)
130 if (EVP_DigestFinal_ex(&ctx->md, tmp, &tmp_len) != 1)
133 memcpy(buffer, tmp, length);
134 memset(tmp, 0, sizeof(tmp));
136 if (tmp_len < length)
139 if (crypt_hash_restart(ctx))
145 int crypt_hash_destroy(struct crypt_hash *ctx)
147 EVP_MD_CTX_cleanup(&ctx->md);
148 memset(ctx, 0, sizeof(*ctx));
154 int crypt_hmac_size(const char *name)
156 return crypt_hash_size(name);
159 int crypt_hmac_init(struct crypt_hmac **ctx, const char *name,
160 const void *buffer, size_t length)
162 struct crypt_hmac *h;
164 h = malloc(sizeof(*h));
168 h->hash_id = EVP_get_digestbyname(name);
174 HMAC_CTX_init(&h->md);
175 HMAC_Init_ex(&h->md, buffer, length, h->hash_id, NULL);
177 h->hash_len = EVP_MD_size(h->hash_id);
182 static void crypt_hmac_restart(struct crypt_hmac *ctx)
184 HMAC_Init_ex(&ctx->md, NULL, 0, ctx->hash_id, NULL);
187 int crypt_hmac_write(struct crypt_hmac *ctx, const char *buffer, size_t length)
189 HMAC_Update(&ctx->md, (const unsigned char *)buffer, length);
193 int crypt_hmac_final(struct crypt_hmac *ctx, char *buffer, size_t length)
195 unsigned char tmp[EVP_MAX_MD_SIZE];
196 unsigned int tmp_len = 0;
198 if (length > (size_t)ctx->hash_len)
201 HMAC_Final(&ctx->md, tmp, &tmp_len);
203 memcpy(buffer, tmp, length);
204 memset(tmp, 0, sizeof(tmp));
206 if (tmp_len < length)
209 crypt_hmac_restart(ctx);
214 int crypt_hmac_destroy(struct crypt_hmac *ctx)
216 HMAC_CTX_cleanup(&ctx->md);
217 memset(ctx, 0, sizeof(*ctx));
223 int crypt_backend_rng(char *buffer, size_t length, int quality, int fips)
228 if (RAND_bytes((unsigned char *)buffer, length) != 1)
235 int crypt_pbkdf(const char *kdf, const char *hash,
236 const char *password, size_t password_length,
237 const char *salt, size_t salt_length,
238 char *key, size_t key_length,
239 unsigned int iterations)
241 const EVP_MD *hash_id;
243 if (!kdf || strncmp(kdf, "pbkdf2", 6))
246 hash_id = EVP_get_digestbyname(hash);
250 if (!PKCS5_PBKDF2_HMAC(password, (int)password_length,
251 (unsigned char *)salt, (int)salt_length,
252 (int)iterations, hash_id, (int)key_length, (unsigned char *)key))