2 * Copyright (C) 2008-2012 Free Software Foundation, Inc.
4 * Author: Nikos Mavrogiannopoulos
6 * This file is part of GNUTLS.
8 * The GNUTLS library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Lesser General Public License
10 * as published by the Free Software Foundation; either version 3 of
11 * the License, or (at your option) any later version.
13 * This library is distributed in the hope that it will be useful, but
14 * WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Lesser General Public License for more details.
18 * You should have received a copy of the GNU Lesser General Public License
19 * along with this program. If not, see <http://www.gnu.org/licenses/>
23 /* This file provides the backend hash/mac API for nettle.
26 #include <gnutls_int.h>
27 #include <gnutls_hash_int.h>
28 #include <gnutls_errors.h>
29 #include <nettle/md5.h>
30 #include <nettle/md2.h>
31 #include <nettle/sha.h>
32 #include <nettle/hmac.h>
34 typedef void (*update_func
) (void *, unsigned, const uint8_t *);
35 typedef void (*digest_func
) (void *, unsigned, uint8_t *);
36 typedef void (*set_key_func
) (void *, unsigned, const uint8_t *);
38 static int wrap_nettle_hash_init (gnutls_digest_algorithm_t algo
, void **_ctx
);
40 struct nettle_hash_ctx
46 struct sha224_ctx sha224
;
47 struct sha256_ctx sha256
;
48 struct sha384_ctx sha384
;
49 struct sha512_ctx sha512
;
53 gnutls_digest_algorithm_t algo
;
59 struct nettle_hmac_ctx
63 struct hmac_md5_ctx md5
;
64 struct hmac_sha224_ctx sha224
;
65 struct hmac_sha256_ctx sha256
;
66 struct hmac_sha384_ctx sha384
;
67 struct hmac_sha512_ctx sha512
;
68 struct hmac_sha1_ctx sha1
;
71 /* this is the context just after
72 * the set_key. Used in reset().
76 struct hmac_md5_ctx md5
;
77 struct hmac_sha224_ctx sha224
;
78 struct hmac_sha256_ctx sha256
;
79 struct hmac_sha384_ctx sha384
;
80 struct hmac_sha512_ctx sha512
;
81 struct hmac_sha1_ctx sha1
;
84 gnutls_mac_algorithm_t algo
;
91 static int _hmac_ctx_init(gnutls_mac_algorithm_t algo
, struct nettle_hmac_ctx
*ctx
)
96 ctx
->update
= (update_func
) hmac_md5_update
;
97 ctx
->digest
= (digest_func
) hmac_md5_digest
;
98 ctx
->setkey
= (set_key_func
) hmac_md5_set_key
;
99 ctx
->ctx_ptr
= &ctx
->ctx
.md5
;
100 ctx
->length
= MD5_DIGEST_SIZE
;
102 case GNUTLS_MAC_SHA1
:
103 ctx
->update
= (update_func
) hmac_sha1_update
;
104 ctx
->digest
= (digest_func
) hmac_sha1_digest
;
105 ctx
->setkey
= (set_key_func
) hmac_sha1_set_key
;
106 ctx
->ctx_ptr
= &ctx
->ctx
.sha1
;
107 ctx
->length
= SHA1_DIGEST_SIZE
;
109 case GNUTLS_MAC_SHA224
:
110 ctx
->update
= (update_func
) hmac_sha224_update
;
111 ctx
->digest
= (digest_func
) hmac_sha224_digest
;
112 ctx
->setkey
= (set_key_func
) hmac_sha224_set_key
;
113 ctx
->ctx_ptr
= &ctx
->ctx
.sha224
;
114 ctx
->length
= SHA224_DIGEST_SIZE
;
116 case GNUTLS_MAC_SHA256
:
117 ctx
->update
= (update_func
) hmac_sha256_update
;
118 ctx
->digest
= (digest_func
) hmac_sha256_digest
;
119 ctx
->setkey
= (set_key_func
) hmac_sha256_set_key
;
120 ctx
->ctx_ptr
= &ctx
->ctx
.sha256
;
121 ctx
->length
= SHA256_DIGEST_SIZE
;
123 case GNUTLS_MAC_SHA384
:
124 ctx
->update
= (update_func
) hmac_sha384_update
;
125 ctx
->digest
= (digest_func
) hmac_sha384_digest
;
126 ctx
->setkey
= (set_key_func
) hmac_sha384_set_key
;
127 ctx
->ctx_ptr
= &ctx
->ctx
.sha384
;
128 ctx
->length
= SHA384_DIGEST_SIZE
;
130 case GNUTLS_MAC_SHA512
:
131 ctx
->update
= (update_func
) hmac_sha512_update
;
132 ctx
->digest
= (digest_func
) hmac_sha512_digest
;
133 ctx
->setkey
= (set_key_func
) hmac_sha512_set_key
;
134 ctx
->ctx_ptr
= &ctx
->ctx
.sha512
;
135 ctx
->length
= SHA512_DIGEST_SIZE
;
139 return GNUTLS_E_INVALID_REQUEST
;
145 static int wrap_nettle_hmac_fast(gnutls_mac_algorithm_t algo
,
146 const void *key
, size_t key_size
, const void* text
, size_t text_size
,
149 struct nettle_hmac_ctx ctx
;
152 ret
= _hmac_ctx_init(algo
, &ctx
);
154 return gnutls_assert_val(ret
);
156 ctx
.setkey (&ctx
, key_size
, key
);
157 ctx
.update (&ctx
, text_size
, text
);
158 ctx
.digest (&ctx
, ctx
.length
, digest
);
163 static int wrap_nettle_hmac_exists(gnutls_mac_algorithm_t algo
)
168 case GNUTLS_MAC_SHA1
:
169 case GNUTLS_MAC_SHA224
:
170 case GNUTLS_MAC_SHA256
:
171 case GNUTLS_MAC_SHA384
:
172 case GNUTLS_MAC_SHA512
:
180 wrap_nettle_hmac_init (gnutls_mac_algorithm_t algo
, void **_ctx
)
182 struct nettle_hmac_ctx
*ctx
;
185 ctx
= gnutls_calloc (1, sizeof (struct nettle_hmac_ctx
));
189 return GNUTLS_E_MEMORY_ERROR
;
194 ret
= _hmac_ctx_init(algo
, ctx
);
198 return gnutls_assert_val(ret
);
207 wrap_nettle_hmac_setkey (void *_ctx
, const void *key
, size_t keylen
)
209 struct nettle_hmac_ctx
*ctx
= _ctx
;
211 ctx
->setkey (ctx
->ctx_ptr
, keylen
, key
);
213 memcpy(&ctx
->init_ctx
, &ctx
->ctx
, sizeof(ctx
->ctx
));
215 return GNUTLS_E_SUCCESS
;
219 wrap_nettle_hmac_reset (void *_ctx
)
221 struct nettle_hmac_ctx
*ctx
= _ctx
;
223 memcpy(&ctx
->ctx
, &ctx
->init_ctx
, sizeof(ctx
->ctx
));
227 wrap_nettle_hmac_update (void *_ctx
, const void *text
, size_t textsize
)
229 struct nettle_hmac_ctx
*ctx
= _ctx
;
231 ctx
->update (ctx
->ctx_ptr
, textsize
, text
);
233 return GNUTLS_E_SUCCESS
;
237 wrap_nettle_hmac_output (void *src_ctx
, void *digest
, size_t digestsize
)
239 struct nettle_hmac_ctx
*ctx
;
242 if (digestsize
< ctx
->length
)
245 return GNUTLS_E_SHORT_MEMORY_BUFFER
;
248 ctx
->digest (ctx
->ctx_ptr
, digestsize
, digest
);
254 wrap_nettle_hmac_deinit (void *hd
)
262 wrap_nettle_hash_update (void *_ctx
, const void *text
, size_t textsize
)
264 struct nettle_hash_ctx
*ctx
= _ctx
;
266 ctx
->update (ctx
->ctx_ptr
, textsize
, text
);
268 return GNUTLS_E_SUCCESS
;
272 wrap_nettle_hash_deinit (void *hd
)
277 static int wrap_nettle_hash_exists(gnutls_digest_algorithm_t algo
)
282 case GNUTLS_DIG_SHA1
:
284 case GNUTLS_DIG_SHA224
:
285 case GNUTLS_DIG_SHA256
:
286 case GNUTLS_DIG_SHA384
:
287 case GNUTLS_DIG_SHA512
:
294 static int _ctx_init(gnutls_digest_algorithm_t algo
, struct nettle_hash_ctx
*ctx
)
299 md5_init (&ctx
->ctx
.md5
);
300 ctx
->update
= (update_func
) md5_update
;
301 ctx
->digest
= (digest_func
) md5_digest
;
302 ctx
->ctx_ptr
= &ctx
->ctx
.md5
;
303 ctx
->length
= MD5_DIGEST_SIZE
;
305 case GNUTLS_DIG_SHA1
:
306 sha1_init (&ctx
->ctx
.sha1
);
307 ctx
->update
= (update_func
) sha1_update
;
308 ctx
->digest
= (digest_func
) sha1_digest
;
309 ctx
->ctx_ptr
= &ctx
->ctx
.sha1
;
310 ctx
->length
= SHA1_DIGEST_SIZE
;
313 md2_init (&ctx
->ctx
.md2
);
314 ctx
->update
= (update_func
) md2_update
;
315 ctx
->digest
= (digest_func
) md2_digest
;
316 ctx
->ctx_ptr
= &ctx
->ctx
.md2
;
317 ctx
->length
= MD2_DIGEST_SIZE
;
319 case GNUTLS_DIG_SHA224
:
320 sha224_init (&ctx
->ctx
.sha224
);
321 ctx
->update
= (update_func
) sha224_update
;
322 ctx
->digest
= (digest_func
) sha224_digest
;
323 ctx
->ctx_ptr
= &ctx
->ctx
.sha224
;
324 ctx
->length
= SHA224_DIGEST_SIZE
;
326 case GNUTLS_DIG_SHA256
:
327 sha256_init (&ctx
->ctx
.sha256
);
328 ctx
->update
= (update_func
) sha256_update
;
329 ctx
->digest
= (digest_func
) sha256_digest
;
330 ctx
->ctx_ptr
= &ctx
->ctx
.sha256
;
331 ctx
->length
= SHA256_DIGEST_SIZE
;
333 case GNUTLS_DIG_SHA384
:
334 sha384_init (&ctx
->ctx
.sha384
);
335 ctx
->update
= (update_func
) sha384_update
;
336 ctx
->digest
= (digest_func
) sha384_digest
;
337 ctx
->ctx_ptr
= &ctx
->ctx
.sha384
;
338 ctx
->length
= SHA384_DIGEST_SIZE
;
340 case GNUTLS_DIG_SHA512
:
341 sha512_init (&ctx
->ctx
.sha512
);
342 ctx
->update
= (update_func
) sha512_update
;
343 ctx
->digest
= (digest_func
) sha512_digest
;
344 ctx
->ctx_ptr
= &ctx
->ctx
.sha512
;
345 ctx
->length
= SHA512_DIGEST_SIZE
;
349 return GNUTLS_E_INVALID_REQUEST
;
355 static int wrap_nettle_hash_fast(gnutls_digest_algorithm_t algo
,
356 const void* text
, size_t text_size
,
359 struct nettle_hash_ctx ctx
;
362 ret
= _ctx_init(algo
, &ctx
);
364 return gnutls_assert_val(ret
);
366 ctx
.update (&ctx
, text_size
, text
);
367 ctx
.digest (&ctx
, ctx
.length
, digest
);
373 wrap_nettle_hash_init (gnutls_digest_algorithm_t algo
, void **_ctx
)
375 struct nettle_hash_ctx
*ctx
;
378 ctx
= gnutls_malloc (sizeof (struct nettle_hash_ctx
));
382 return GNUTLS_E_MEMORY_ERROR
;
387 if ((ret
=_ctx_init( algo
, ctx
)) < 0)
400 wrap_nettle_hash_output (void *src_ctx
, void *digest
, size_t digestsize
)
402 struct nettle_hash_ctx
*ctx
;
405 if (digestsize
< ctx
->length
)
408 return GNUTLS_E_SHORT_MEMORY_BUFFER
;
411 ctx
->digest (ctx
->ctx_ptr
, digestsize
, digest
);
417 wrap_nettle_hash_reset (void *src_ctx
)
419 struct nettle_hash_ctx
*ctx
;
422 _ctx_init(ctx
->algo
, ctx
->ctx_ptr
);
426 gnutls_crypto_mac_st _gnutls_mac_ops
= {
427 .init
= wrap_nettle_hmac_init
,
428 .setkey
= wrap_nettle_hmac_setkey
,
429 .hash
= wrap_nettle_hmac_update
,
430 .reset
= wrap_nettle_hmac_reset
,
431 .output
= wrap_nettle_hmac_output
,
432 .deinit
= wrap_nettle_hmac_deinit
,
433 .fast
= wrap_nettle_hmac_fast
,
434 .exists
= wrap_nettle_hmac_exists
,
437 gnutls_crypto_digest_st _gnutls_digest_ops
= {
438 .init
= wrap_nettle_hash_init
,
439 .hash
= wrap_nettle_hash_update
,
440 .reset
= wrap_nettle_hash_reset
,
441 .output
= wrap_nettle_hash_output
,
442 .deinit
= wrap_nettle_hash_deinit
,
443 .fast
= wrap_nettle_hash_fast
,
444 .exists
= wrap_nettle_hash_exists
,