Corrected bugs in record parsing.
[gnutls.git] / lib / algorithms / mac.c
blobbcaffb8a05b03e2a8656003aa36495eeeebc5e84
1 /*
2 * Copyright (C) 2011-2012 Free Software Foundation, Inc.
4 * Author: Nikos Mavrogiannopoulos
6 * This file is part of GnuTLS.
8 * The GnuTLS 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 #include <gnutls_int.h>
24 #include <algorithms.h>
25 #include <gnutls_errors.h>
26 #include <x509/common.h>
28 struct gnutls_hash_entry
30 const char *name;
31 const char *oid;
32 gnutls_mac_algorithm_t id;
33 size_t key_size; /* in case of mac */
34 unsigned placeholder; /* if set, then not a real MAC */
35 unsigned secure; /* if set the this algorithm is secure as hash */
37 typedef struct gnutls_hash_entry gnutls_hash_entry;
39 static const gnutls_hash_entry hash_algorithms[] = {
40 {"SHA1", HASH_OID_SHA1, GNUTLS_MAC_SHA1, 20, 0, 1},
41 {"MD5", HASH_OID_MD5, GNUTLS_MAC_MD5, 16, 0, 0},
42 {"SHA256", HASH_OID_SHA256, GNUTLS_MAC_SHA256, 32, 0, 1},
43 {"SHA384", HASH_OID_SHA384, GNUTLS_MAC_SHA384, 48, 0, 1},
44 {"SHA512", HASH_OID_SHA512, GNUTLS_MAC_SHA512, 64, 0, 1},
45 {"SHA224", HASH_OID_SHA224, GNUTLS_MAC_SHA224, 28, 0, 1},
46 {"AEAD", NULL, GNUTLS_MAC_AEAD, 0, 1, 1},
47 {"MD2", HASH_OID_MD2, GNUTLS_MAC_MD2, 0, 0, 0}, /* not used as MAC */
48 {"RIPEMD160", HASH_OID_RMD160, GNUTLS_MAC_RMD160, 20, 0, 1},
49 {"MAC-NULL", NULL, GNUTLS_MAC_NULL, 0, 0, 0},
50 {0, 0, 0, 0, 0}
54 #define GNUTLS_HASH_LOOP(b) \
55 const gnutls_hash_entry *p; \
56 for(p = hash_algorithms; p->name != NULL; p++) { b ; }
58 #define GNUTLS_HASH_ALG_LOOP(a) \
59 GNUTLS_HASH_LOOP( if(p->id == algorithm) { a; break; } )
61 int
62 _gnutls_mac_priority (gnutls_session_t session,
63 gnutls_mac_algorithm_t algorithm)
64 { /* actually returns the priority */
65 unsigned int i;
66 for (i = 0; i < session->internals.priorities.mac.algorithms; i++)
68 if (session->internals.priorities.mac.priority[i] == algorithm)
69 return i;
71 return -1;
74 /**
75 * gnutls_mac_get_name:
76 * @algorithm: is a MAC algorithm
78 * Convert a #gnutls_mac_algorithm_t value to a string.
80 * Returns: a string that contains the name of the specified MAC
81 * algorithm, or %NULL.
82 **/
83 const char *
84 gnutls_mac_get_name (gnutls_mac_algorithm_t algorithm)
86 const char *ret = NULL;
88 /* avoid prefix */
89 GNUTLS_HASH_ALG_LOOP (ret = p->name);
91 return ret;
94 /**
95 * gnutls_mac_get_id:
96 * @name: is a MAC algorithm name
98 * Convert a string to a #gnutls_mac_algorithm_t value. The names are
99 * compared in a case insensitive way.
101 * Returns: a #gnutls_mac_algorithm_t id of the specified MAC
102 * algorithm string, or %GNUTLS_MAC_UNKNOWN on failures.
104 gnutls_mac_algorithm_t
105 gnutls_mac_get_id (const char *name)
107 gnutls_mac_algorithm_t ret = GNUTLS_MAC_UNKNOWN;
109 GNUTLS_HASH_LOOP (
110 if (strcasecmp (p->name, name) == 0)
112 ret = p->id;
113 break;
117 return ret;
121 * gnutls_mac_get_key_size:
122 * @algorithm: is an encryption algorithm
124 * Get size of MAC key.
126 * Returns: length (in bytes) of the given MAC key size, or 0 if the
127 * given MAC algorithm is invalid.
129 size_t
130 gnutls_mac_get_key_size (gnutls_mac_algorithm_t algorithm)
132 size_t ret = 0;
134 /* avoid prefix */
135 GNUTLS_HASH_ALG_LOOP (ret = p->key_size);
137 return ret;
141 * gnutls_mac_list:
143 * Get a list of hash algorithms for use as MACs. Note that not
144 * necessarily all MACs are supported in TLS cipher suites. For
145 * example, MD2 is not supported as a cipher suite, but is supported
146 * for other purposes (e.g., X.509 signature verification or similar).
148 * This function is not thread safe.
150 * Returns: Return a (0)-terminated list of #gnutls_mac_algorithm_t
151 * integers indicating the available MACs.
153 const gnutls_mac_algorithm_t *
154 gnutls_mac_list (void)
156 static gnutls_mac_algorithm_t supported_macs[MAX_ALGOS] = { 0 };
158 if (supported_macs[0] == 0)
160 int i = 0;
162 GNUTLS_HASH_LOOP (
163 if (p->placeholder != 0 || _gnutls_hmac_exists(p->id))
164 supported_macs[i++]=p->id;
166 supported_macs[i++]=0;
169 return supported_macs;
172 const char *
173 _gnutls_x509_mac_to_oid (gnutls_mac_algorithm_t algorithm)
175 const char *ret = NULL;
177 /* avoid prefix */
178 GNUTLS_HASH_ALG_LOOP (ret = p->oid);
180 return ret;
183 gnutls_digest_algorithm_t
184 _gnutls_x509_oid_to_digest (const char *oid)
186 gnutls_digest_algorithm_t ret = 0;
188 GNUTLS_HASH_LOOP (if (p->oid && strcmp (oid, p->oid) == 0)
190 ret = (gnutls_digest_algorithm_t)p->id;
191 break;
195 if (ret == 0)
196 return GNUTLS_DIG_UNKNOWN;
197 return ret;
200 const char *
201 _gnutls_x509_digest_to_oid (gnutls_digest_algorithm_t algorithm)
203 return _gnutls_x509_mac_to_oid ((gnutls_mac_algorithm_t) algorithm);
206 const char *
207 _gnutls_digest_get_name (gnutls_digest_algorithm_t algorithm)
209 return gnutls_mac_get_name ((gnutls_mac_algorithm_t) algorithm);
213 _gnutls_mac_is_ok (gnutls_mac_algorithm_t algorithm)
215 ssize_t ret = -1;
216 GNUTLS_HASH_ALG_LOOP (ret = p->id);
217 if (ret >= 0)
218 ret = 0;
219 else
220 ret = 1;
221 return ret;
225 _gnutls_digest_is_secure (gnutls_digest_algorithm_t algo)
227 ssize_t ret = 0;
228 gnutls_mac_algorithm_t algorithm = algo;
230 GNUTLS_HASH_ALG_LOOP (ret = p->secure);
232 return ret;