gmp: Support of SHA-3 RSA signatures
[strongswan.git] / src / libcharon / sa / ikev2 / authenticators / pubkey_authenticator.c
1 /*
2 * Copyright (C) 2008-2015 Tobias Brunner
3 * Copyright (C) 2005-2009 Martin Willi
4 * Copyright (C) 2005 Jan Hutter
5 * Hochschule fuer Technik Rapperswil
6 *
7 * This program is free software; you can redistribute it and/or modify it
8 * under the terms of the GNU General Public License as published by the
9 * Free Software Foundation; either version 2 of the License, or (at your
10 * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>.
11 *
12 * This program is distributed in the hope that it will be useful, but
13 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
14 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15 * for more details.
16 */
17
18 #include "pubkey_authenticator.h"
19
20 #include <daemon.h>
21 #include <encoding/payloads/auth_payload.h>
22 #include <sa/ikev2/keymat_v2.h>
23 #include <asn1/asn1.h>
24 #include <asn1/oid.h>
25 #include <collections/array.h>
26
27 typedef struct private_pubkey_authenticator_t private_pubkey_authenticator_t;
28
29 /**
30 * Private data of an pubkey_authenticator_t object.
31 */
32 struct private_pubkey_authenticator_t {
33
34 /**
35 * Public authenticator_t interface.
36 */
37 pubkey_authenticator_t public;
38
39 /**
40 * Assigned IKE_SA
41 */
42 ike_sa_t *ike_sa;
43
44 /**
45 * nonce to include in AUTH calculation
46 */
47 chunk_t nonce;
48
49 /**
50 * IKE_SA_INIT message data to include in AUTH calculation
51 */
52 chunk_t ike_sa_init;
53
54 /**
55 * Reserved bytes of ID payload
56 */
57 char reserved[3];
58 };
59
60 /**
61 * Parse authentication data used for Signature Authentication as per RFC 7427
62 */
63 static bool parse_signature_auth_data(chunk_t *auth_data, key_type_t *key_type,
64 signature_scheme_t *scheme)
65 {
66 uint8_t len;
67 int oid;
68
69 if (!auth_data->len)
70 {
71 return FALSE;
72 }
73 len = auth_data->ptr[0];
74 *auth_data = chunk_skip(*auth_data, 1);
75 /* we currently don't support schemes that require parameters */
76 oid = asn1_parse_algorithmIdentifier(*auth_data, 1, NULL);
77 *scheme = signature_scheme_from_oid(oid);
78 if (*scheme == SIGN_UNKNOWN)
79 {
80 return FALSE;
81 }
82 *key_type = key_type_from_signature_scheme(*scheme);
83 *auth_data = chunk_skip(*auth_data, len);
84 return TRUE;
85 }
86
87 /**
88 * Build authentication data used for Signature Authentication as per RFC 7427
89 */
90 static bool build_signature_auth_data(chunk_t *auth_data,
91 signature_scheme_t scheme)
92 {
93 chunk_t data;
94 uint8_t len;
95 int oid;
96
97 oid = signature_scheme_to_oid(scheme);
98 if (oid == OID_UNKNOWN)
99 {
100 return FALSE;
101 }
102 data = asn1_algorithmIdentifier(oid);
103 len = data.len;
104 *auth_data = chunk_cat("cmm", chunk_from_thing(len), data, *auth_data);
105 return TRUE;
106 }
107
108 /**
109 * Selects possible signature schemes based on our configuration, the other
110 * peer's capabilities and the private key
111 */
112 static array_t *select_signature_schemes(keymat_v2_t *keymat,
113 auth_cfg_t *auth, private_key_t *private)
114 {
115 enumerator_t *enumerator;
116 signature_scheme_t scheme;
117 uintptr_t config;
118 auth_rule_t rule;
119 key_type_t key_type;
120 bool have_config = FALSE;
121 array_t *selected;
122
123 selected = array_create(sizeof(signature_scheme_t), 0);
124 key_type = private->get_type(private);
125 enumerator = auth->create_enumerator(auth);
126 while (enumerator->enumerate(enumerator, &rule, &config))
127 {
128 if (rule != AUTH_RULE_IKE_SIGNATURE_SCHEME)
129 {
130 continue;
131 }
132 have_config = TRUE;
133 if (key_type == key_type_from_signature_scheme(config) &&
134 keymat->hash_algorithm_supported(keymat,
135 hasher_from_signature_scheme(config)))
136 {
137 scheme = config;
138 array_insert(selected, ARRAY_TAIL, &scheme);
139 }
140 }
141 enumerator->destroy(enumerator);
142
143 if (!have_config)
144 {
145 /* if no specific configuration, find schemes appropriate for the key
146 * and supported by the other peer */
147 enumerator = signature_schemes_for_key(key_type,
148 private->get_keysize(private));
149 while (enumerator->enumerate(enumerator, &scheme))
150 {
151 if (keymat->hash_algorithm_supported(keymat,
152 hasher_from_signature_scheme(scheme)))
153 {
154 array_insert(selected, ARRAY_TAIL, &scheme);
155 }
156 }
157 enumerator->destroy(enumerator);
158
159 /* for RSA we tried at least SHA-512, also try other schemes down to
160 * what we'd use with classic authentication */
161 if (key_type == KEY_RSA)
162 {
163 signature_scheme_t schemes[] = {
164 SIGN_RSA_EMSA_PKCS1_SHA2_384,
165 SIGN_RSA_EMSA_PKCS1_SHA2_256,
166 SIGN_RSA_EMSA_PKCS1_SHA1,
167 }, contained;
168 bool found;
169 int i, j;
170
171 for (i = 0; i < countof(schemes); i++)
172 {
173 scheme = schemes[i];
174 found = FALSE;
175 for (j = 0; j < array_count(selected); j++)
176 {
177 array_get(selected, j, &contained);
178 if (scheme == contained)
179 {
180 found = TRUE;
181 break;
182 }
183 }
184 if (!found && keymat->hash_algorithm_supported(keymat,
185 hasher_from_signature_scheme(scheme)))
186 {
187 array_insert(selected, ARRAY_TAIL, &scheme);
188 }
189 }
190 }
191 }
192 return selected;
193 }
194
195 /**
196 * Create a signature using RFC 7427 signature authentication
197 */
198 static status_t sign_signature_auth(private_pubkey_authenticator_t *this,
199 auth_cfg_t *auth, private_key_t *private,
200 identification_t *id, chunk_t *auth_data)
201 {
202 enumerator_t *enumerator;
203 keymat_v2_t *keymat;
204 signature_scheme_t scheme = SIGN_UNKNOWN, *schemep;
205 array_t *schemes;
206 chunk_t octets = chunk_empty;
207 status_t status = FAILED;
208
209 keymat = (keymat_v2_t*)this->ike_sa->get_keymat(this->ike_sa);
210 schemes = select_signature_schemes(keymat, auth, private);
211 if (!array_count(schemes))
212 {
213 DBG1(DBG_IKE, "no common hash algorithm found to create signature "
214 "with %N key", key_type_names, private->get_type(private));
215 array_destroy(schemes);
216 return FAILED;
217 }
218
219 if (keymat->get_auth_octets(keymat, FALSE, this->ike_sa_init,
220 this->nonce, id, this->reserved, &octets))
221 {
222 enumerator = array_create_enumerator(schemes);
223 while (enumerator->enumerate(enumerator, &schemep))
224 {
225 scheme = *schemep;
226 if (private->sign(private, scheme, octets, auth_data) &&
227 build_signature_auth_data(auth_data, scheme))
228 {
229 status = SUCCESS;
230 break;
231 }
232 else
233 {
234 DBG2(DBG_IKE, "unable to create %N signature for %N key",
235 signature_scheme_names, scheme, key_type_names,
236 private->get_type(private));
237 }
238 }
239 enumerator->destroy(enumerator);
240 }
241 DBG1(DBG_IKE, "authentication of '%Y' (myself) with %N %s", id,
242 signature_scheme_names, scheme,
243 status == SUCCESS ? "successful" : "failed");
244 array_destroy(schemes);
245 chunk_free(&octets);
246 return status;
247 }
248
249 /**
250 * Create a classic IKEv2 signature
251 */
252 static status_t sign_classic(private_pubkey_authenticator_t *this,
253 auth_cfg_t *auth, private_key_t *private,
254 identification_t *id, auth_method_t *auth_method,
255 chunk_t *auth_data)
256 {
257 signature_scheme_t scheme;
258 keymat_v2_t *keymat;
259 chunk_t octets = chunk_empty;
260 status_t status = FAILED;
261
262 switch (private->get_type(private))
263 {
264 case KEY_RSA:
265 scheme = SIGN_RSA_EMSA_PKCS1_SHA1;
266 *auth_method = AUTH_RSA;
267 break;
268 case KEY_ECDSA:
269 /* deduct the signature scheme from the keysize */
270 switch (private->get_keysize(private))
271 {
272 case 256:
273 scheme = SIGN_ECDSA_256;
274 *auth_method = AUTH_ECDSA_256;
275 break;
276 case 384:
277 scheme = SIGN_ECDSA_384;
278 *auth_method = AUTH_ECDSA_384;
279 break;
280 case 521:
281 scheme = SIGN_ECDSA_521;
282 *auth_method = AUTH_ECDSA_521;
283 break;
284 default:
285 DBG1(DBG_IKE, "%d bit ECDSA private key size not supported",
286 private->get_keysize(private));
287 return FAILED;
288 }
289 break;
290 default:
291 DBG1(DBG_IKE, "private key of type %N not supported",
292 key_type_names, private->get_type(private));
293 return FAILED;
294 }
295
296 keymat = (keymat_v2_t*)this->ike_sa->get_keymat(this->ike_sa);
297 if (keymat->get_auth_octets(keymat, FALSE, this->ike_sa_init,
298 this->nonce, id, this->reserved, &octets) &&
299 private->sign(private, scheme, octets, auth_data))
300 {
301 status = SUCCESS;
302 }
303 DBG1(DBG_IKE, "authentication of '%Y' (myself) with %N %s", id,
304 auth_method_names, *auth_method,
305 status == SUCCESS ? "successful" : "failed");
306 chunk_free(&octets);
307 return status;
308 }
309
310 METHOD(authenticator_t, build, status_t,
311 private_pubkey_authenticator_t *this, message_t *message)
312 {
313 private_key_t *private;
314 identification_t *id;
315 auth_cfg_t *auth;
316 chunk_t auth_data;
317 status_t status;
318 auth_payload_t *auth_payload;
319 auth_method_t auth_method = AUTH_NONE;
320
321 id = this->ike_sa->get_my_id(this->ike_sa);
322 auth = this->ike_sa->get_auth_cfg(this->ike_sa, TRUE);
323 private = lib->credmgr->get_private(lib->credmgr, KEY_ANY, id, auth);
324 if (!private)
325 {
326 DBG1(DBG_IKE, "no private key found for '%Y'", id);
327 return NOT_FOUND;
328 }
329
330 if (this->ike_sa->supports_extension(this->ike_sa, EXT_SIGNATURE_AUTH))
331 {
332 auth_method = AUTH_DS;
333 status = sign_signature_auth(this, auth, private, id, &auth_data);
334 }
335 else
336 {
337 status = sign_classic(this, auth, private, id, &auth_method,
338 &auth_data);
339 }
340 private->destroy(private);
341
342 if (status == SUCCESS)
343 {
344 auth_payload = auth_payload_create();
345 auth_payload->set_auth_method(auth_payload, auth_method);
346 auth_payload->set_data(auth_payload, auth_data);
347 chunk_free(&auth_data);
348 message->add_payload(message, (payload_t*)auth_payload);
349 }
350 return status;
351 }
352
353 METHOD(authenticator_t, process, status_t,
354 private_pubkey_authenticator_t *this, message_t *message)
355 {
356 public_key_t *public;
357 auth_method_t auth_method;
358 auth_payload_t *auth_payload;
359 chunk_t auth_data, octets;
360 identification_t *id;
361 auth_cfg_t *auth, *current_auth;
362 enumerator_t *enumerator;
363 key_type_t key_type = KEY_ECDSA;
364 signature_scheme_t scheme;
365 status_t status = NOT_FOUND;
366 keymat_v2_t *keymat;
367 const char *reason = "unsupported";
368 bool online;
369
370 auth_payload = (auth_payload_t*)message->get_payload(message, PLV2_AUTH);
371 if (!auth_payload)
372 {
373 return FAILED;
374 }
375 auth_method = auth_payload->get_auth_method(auth_payload);
376 auth_data = auth_payload->get_data(auth_payload);
377 switch (auth_method)
378 {
379 case AUTH_RSA:
380 key_type = KEY_RSA;
381 scheme = SIGN_RSA_EMSA_PKCS1_SHA1;
382 break;
383 case AUTH_ECDSA_256:
384 scheme = SIGN_ECDSA_256;
385 break;
386 case AUTH_ECDSA_384:
387 scheme = SIGN_ECDSA_384;
388 break;
389 case AUTH_ECDSA_521:
390 scheme = SIGN_ECDSA_521;
391 break;
392 case AUTH_DS:
393 if (parse_signature_auth_data(&auth_data, &key_type, &scheme))
394 {
395 break;
396 }
397 reason = "payload invalid";
398 /* fall-through */
399 default:
400 DBG1(DBG_IKE, "%N authentication %s", auth_method_names,
401 auth_method, reason);
402 return INVALID_ARG;
403 }
404 id = this->ike_sa->get_other_id(this->ike_sa);
405 keymat = (keymat_v2_t*)this->ike_sa->get_keymat(this->ike_sa);
406 if (!keymat->get_auth_octets(keymat, TRUE, this->ike_sa_init,
407 this->nonce, id, this->reserved, &octets))
408 {
409 return FAILED;
410 }
411 auth = this->ike_sa->get_auth_cfg(this->ike_sa, FALSE);
412 online = !this->ike_sa->has_condition(this->ike_sa,
413 COND_ONLINE_VALIDATION_SUSPENDED);
414 enumerator = lib->credmgr->create_public_enumerator(lib->credmgr,
415 key_type, id, auth, online);
416 while (enumerator->enumerate(enumerator, &public, &current_auth))
417 {
418 if (public->verify(public, scheme, octets, auth_data))
419 {
420 DBG1(DBG_IKE, "authentication of '%Y' with %N successful", id,
421 auth_method == AUTH_DS ? signature_scheme_names : auth_method_names,
422 auth_method == AUTH_DS ? scheme : auth_method);
423 status = SUCCESS;
424 auth->merge(auth, current_auth, FALSE);
425 auth->add(auth, AUTH_RULE_AUTH_CLASS, AUTH_CLASS_PUBKEY);
426 auth->add(auth, AUTH_RULE_IKE_SIGNATURE_SCHEME, (uintptr_t)scheme);
427 if (!online)
428 {
429 auth->add(auth, AUTH_RULE_CERT_VALIDATION_SUSPENDED, TRUE);
430 }
431 break;
432 }
433 else
434 {
435 status = FAILED;
436 DBG1(DBG_IKE, "signature validation failed, looking for another key");
437 }
438 }
439 enumerator->destroy(enumerator);
440 chunk_free(&octets);
441 if (status == NOT_FOUND)
442 {
443 DBG1(DBG_IKE, "no trusted %N public key found for '%Y'",
444 key_type_names, key_type, id);
445 }
446 return status;
447 }
448
449 METHOD(authenticator_t, destroy, void,
450 private_pubkey_authenticator_t *this)
451 {
452 free(this);
453 }
454
455 /*
456 * Described in header.
457 */
458 pubkey_authenticator_t *pubkey_authenticator_create_builder(ike_sa_t *ike_sa,
459 chunk_t received_nonce, chunk_t sent_init,
460 char reserved[3])
461 {
462 private_pubkey_authenticator_t *this;
463
464 INIT(this,
465 .public = {
466 .authenticator = {
467 .build = _build,
468 .process = (void*)return_failed,
469 .is_mutual = (void*)return_false,
470 .destroy = _destroy,
471 },
472 },
473 .ike_sa = ike_sa,
474 .ike_sa_init = sent_init,
475 .nonce = received_nonce,
476 );
477 memcpy(this->reserved, reserved, sizeof(this->reserved));
478
479 return &this->public;
480 }
481
482 /*
483 * Described in header.
484 */
485 pubkey_authenticator_t *pubkey_authenticator_create_verifier(ike_sa_t *ike_sa,
486 chunk_t sent_nonce, chunk_t received_init,
487 char reserved[3])
488 {
489 private_pubkey_authenticator_t *this;
490
491 INIT(this,
492 .public = {
493 .authenticator = {
494 .build = (void*)return_failed,
495 .process = _process,
496 .is_mutual = (void*)return_false,
497 .destroy = _destroy,
498 },
499 },
500 .ike_sa = ike_sa,
501 .ike_sa_init = received_init,
502 .nonce = sent_nonce,
503 );
504 memcpy(this->reserved, reserved, sizeof(this->reserved));
505
506 return &this->public;
507 }