show name of created CHILD_SA
[strongswan.git] / src / charon / sa / transactions / ike_auth.c
1 /**
2 * @file ike_auth.c
3 *
4 * @brief Implementation of ike_auth_t transaction.
5 *
6 */
7
8 /*
9 * Copyright (C) 2006 Tobias Brunner, Daniel Roethlisberger
10 * Copyright (C) 2005-2006 Martin Willi
11 * Copyright (C) 2005 Jan Hutter
12 * Hochschule fuer Technik Rapperswil
13 *
14 * This program is free software; you can redistribute it and/or modify it
15 * under the terms of the GNU General Public License as published by the
16 * Free Software Foundation; either version 2 of the License, or (at your
17 * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>.
18 *
19 * This program is distributed in the hope that it will be useful, but
20 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
21 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
22 * for more details.
23 */
24
25 #include "ike_auth.h"
26
27 #include <string.h>
28
29 #include <daemon.h>
30 #include <encoding/payloads/sa_payload.h>
31 #include <encoding/payloads/id_payload.h>
32 #include <encoding/payloads/cert_payload.h>
33 #include <encoding/payloads/certreq_payload.h>
34 #include <encoding/payloads/auth_payload.h>
35 #include <encoding/payloads/ts_payload.h>
36 #include <sa/authenticators/authenticator.h>
37 #include <sa/child_sa.h>
38
39
40 typedef struct private_ike_auth_t private_ike_auth_t;
41
42 /**
43 * Private members of a ike_auth_t object..
44 */
45 struct private_ike_auth_t {
46
47 /**
48 * Public methods and transaction_t interface.
49 */
50 ike_auth_t public;
51
52 /**
53 * Assigned IKE_SA.
54 */
55 ike_sa_t *ike_sa;
56
57 /**
58 * Message sent by our peer, if already generated
59 */
60 message_t *message;
61
62 /**
63 * Message ID this transaction uses
64 */
65 u_int32_t message_id;
66
67 /**
68 * Times we did send the request
69 */
70 u_int32_t requested;
71
72 /**
73 * initiator chosen nonce
74 */
75 chunk_t nonce_i;
76
77 /**
78 * responder chosen nonce
79 */
80 chunk_t nonce_r;
81
82 /**
83 * encoded request message of ike_sa_init transaction
84 */
85 chunk_t init_request;
86
87 /**
88 * encoded response message of ike_sa_init transaction
89 */
90 chunk_t init_response;
91
92 /**
93 * connection definition used for IKE_SA setup
94 */
95 connection_t *connection;
96
97 /**
98 * policy definition used CHILD_SA creation
99 */
100 policy_t *policy;
101
102 /**
103 * Negotiated proposal used for CHILD_SA
104 */
105 proposal_t *proposal;
106
107 /**
108 * Negotiated traffic selectors for initiator
109 */
110 linked_list_t *tsi;
111
112 /**
113 * Negotiated traffic selectors for responder
114 */
115 linked_list_t *tsr;
116
117 /**
118 * CHILD_SA created along with IKE_AUTH
119 */
120 child_sa_t *child_sa;
121
122 /**
123 * did other peer create a CHILD_SA?
124 */
125 bool build_child;
126
127 /**
128 * reqid to use for CHILD_SA setup
129 */
130 u_int32_t reqid;
131
132 /**
133 * mode the CHILD_SA uses: tranport, tunnel, BEET
134 */
135 mode_t mode;
136 };
137
138 /**
139 * Implementation of transaction_t.get_message_id.
140 */
141 static u_int32_t get_message_id(private_ike_auth_t *this)
142 {
143 return this->message_id;
144 }
145
146 /**
147 * Implementation of transaction_t.requested.
148 */
149 static u_int32_t requested(private_ike_auth_t *this)
150 {
151 return this->requested++;
152 }
153
154 /**
155 * Implementation of transaction_t.set_config.
156 */
157 static void set_config(private_ike_auth_t *this,
158 connection_t *connection, policy_t *policy)
159 {
160 this->connection = connection;
161 this->policy = policy;
162 }
163
164 /**
165 * Implementation of transaction_t.set_reqid.
166 */
167 static void set_reqid(private_ike_auth_t *this, u_int32_t reqid)
168 {
169 this->reqid = reqid;
170 }
171
172 /**
173 * Implementation of transaction_t.set_nonces.
174 */
175 static void set_nonces(private_ike_auth_t *this, chunk_t nonce_i, chunk_t nonce_r)
176 {
177 this->nonce_i = nonce_i;
178 this->nonce_r = nonce_r;
179 }
180
181 /**
182 * Implementation of transaction_t.set_init_messages.
183 */
184 static void set_init_messages(private_ike_auth_t *this, chunk_t init_request, chunk_t init_response)
185 {
186 this->init_request = init_request;
187 this->init_response = init_response;
188 }
189
190 /**
191 * Build a notify message.
192 */
193 static void build_notify(notify_type_t type, message_t *message, bool flush_message)
194 {
195 notify_payload_t *notify;
196
197 if (flush_message)
198 {
199 payload_t *payload;
200 iterator_t *iterator = message->get_payload_iterator(message);
201 while (iterator->iterate(iterator, (void**)&payload))
202 {
203 payload->destroy(payload);
204 iterator->remove(iterator);
205 }
206 iterator->destroy(iterator);
207 }
208
209 notify = notify_payload_create();
210 notify->set_notify_type(notify, type);
211 message->add_payload(message, (payload_t*)notify);
212 }
213
214 /**
215 * Implementation of transaction_t.get_request.
216 */
217 static status_t get_request(private_ike_auth_t *this, message_t **result)
218 {
219 message_t *request;
220 host_t *me, *other;
221 identification_t *my_id, *other_id;
222 id_payload_t *my_id_payload;
223
224 /* check if we already have built a message (retransmission) */
225 if (this->message)
226 {
227 *result = this->message;
228 return SUCCESS;
229 }
230
231 me = this->ike_sa->get_my_host(this->ike_sa);
232 other = this->ike_sa->get_other_host(this->ike_sa);
233 my_id = this->policy->get_my_id(this->policy);
234 other_id = this->policy->get_other_id(this->policy);
235
236 /* build the request */
237 request = message_create();
238 request->set_source(request, me->clone(me));
239 request->set_destination(request, other->clone(other));
240 request->set_exchange_type(request, IKE_AUTH);
241 request->set_request(request, TRUE);
242 request->set_ike_sa_id(request, this->ike_sa->get_id(this->ike_sa));
243 /* apply for caller */
244 *result = request;
245 /* store for retransmission */
246 this->message = request;
247
248 { /* build ID payload */
249 my_id_payload = id_payload_create_from_identification(TRUE, my_id);
250 request->add_payload(request, (payload_t*)my_id_payload);
251 }
252
253 /* build certificate request payload */
254 if (this->connection->get_certreq_policy(this->connection) != CERT_NEVER_SEND)
255 {
256 certreq_payload_t *certreq_payload;
257 identification_t *other_ca = this->policy->get_other_ca(this->policy);
258
259 if (other_ca)
260 {
261 if (other_ca->get_type(other_ca) == ID_ANY)
262 {
263 certreq_payload = certreq_payload_create_from_cacerts();
264 }
265 else
266 {
267 certreq_payload = certreq_payload_create_from_cacert(other_ca);
268 }
269 if (certreq_payload != NULL)
270 {
271 request->add_payload(request, (payload_t*)certreq_payload);
272 }
273 }
274 }
275
276 /* build certificate payload. TODO: Handle certreq from init_ike_sa. */
277 if (this->policy->get_auth_method(this->policy) == AUTH_RSA
278 && this->connection->get_cert_policy(this->connection) != CERT_NEVER_SEND)
279 {
280 cert_payload_t *cert_payload;
281
282 x509_t *cert = charon->credentials->get_certificate(charon->credentials, my_id);
283
284 if (cert)
285 {
286 cert_payload = cert_payload_create_from_x509(cert);
287 request->add_payload(request, (payload_t*)cert_payload);
288 }
289 else
290 {
291 DBG1(DBG_IKE, "could not find my certificate, certificate payload omitted");
292 }
293 }
294
295 { /* build IDr payload, if other_id defined */
296 id_payload_t *id_payload;
297 if (!other_id->contains_wildcards(other_id))
298 {
299 id_payload = id_payload_create_from_identification(FALSE, other_id);
300 request->add_payload(request, (payload_t*)id_payload);
301 }
302 }
303
304 { /* build auth payload */
305 authenticator_t *authenticator;
306 auth_payload_t *auth_payload;
307 auth_method_t auth_method;
308 status_t status;
309
310 auth_method = this->policy->get_auth_method(this->policy);
311 authenticator = authenticator_create(this->ike_sa, auth_method);
312 if (authenticator == NULL)
313 {
314 SIG(IKE_UP_FAILED, "auth method %N not supported, deleting IKE_SA",
315 auth_method_names, auth_method);
316 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
317 return DESTROY_ME;
318 }
319 status = authenticator->build(authenticator, this->init_request,
320 this->nonce_r, &auth_payload);
321 authenticator->destroy(authenticator);
322 if (status != SUCCESS)
323 {
324 SIG(IKE_UP_FAILED, "could not generate AUTH data, deleting IKE_SA");
325 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
326 return DESTROY_ME;
327 }
328 request->add_payload(request, (payload_t*)auth_payload);
329 }
330
331 { /* build SA payload for CHILD_SA */
332 linked_list_t *proposal_list;
333 sa_payload_t *sa_payload;
334 u_int32_t soft_lifetime, hard_lifetime;
335 bool enable_natt;
336
337 proposal_list = this->policy->get_proposals(this->policy);
338 soft_lifetime = this->policy->get_soft_lifetime(this->policy);
339 hard_lifetime = this->policy->get_hard_lifetime(this->policy);
340 enable_natt = this->ike_sa->is_natt_enabled(this->ike_sa);
341 this->child_sa = child_sa_create(this->reqid, me, other, my_id, other_id,
342 soft_lifetime, hard_lifetime,
343 this->policy->get_updown(this->policy),
344 this->policy->get_hostaccess(this->policy),
345 enable_natt);
346 this->child_sa->set_name(this->child_sa, this->policy->get_name(this->policy));
347 if (this->child_sa->alloc(this->child_sa, proposal_list) != SUCCESS)
348 {
349 SIG(IKE_UP_FAILED, "could not install CHILD_SA, deleting IKE_SA");
350 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
351 return DESTROY_ME;
352 }
353 sa_payload = sa_payload_create_from_proposal_list(proposal_list);
354 proposal_list->destroy_offset(proposal_list, offsetof(proposal_t, destroy));
355 request->add_payload(request, (payload_t*)sa_payload);
356 }
357
358 /* notify for transport/BEET mode, we propose it
359 * independent of the traffic selectors */
360 switch (this->policy->get_mode(this->policy))
361 {
362 case MODE_TUNNEL:
363 /* is the default */
364 break;
365 case MODE_TRANSPORT:
366 if (this->ike_sa->is_natt_enabled(this->ike_sa))
367 {
368 DBG1(DBG_IKE, "not using tranport mode, as connection NATed");
369 }
370 else
371 {
372 build_notify(USE_TRANSPORT_MODE, request, FALSE);
373 }
374 break;
375 case MODE_BEET:
376 build_notify(USE_BEET_MODE, request, FALSE);
377 break;
378 }
379
380 { /* build TSi payload */
381 linked_list_t *ts_list;
382 ts_payload_t *ts_payload;
383
384 ts_list = this->policy->get_my_traffic_selectors(this->policy, me);
385 ts_payload = ts_payload_create_from_traffic_selectors(TRUE, ts_list);
386 ts_list->destroy_offset(ts_list, offsetof(traffic_selector_t, destroy));
387
388 request->add_payload(request, (payload_t*)ts_payload);
389 }
390
391 { /* build TSr payload */
392 linked_list_t *ts_list;
393 ts_payload_t *ts_payload;
394
395 ts_list = this->policy->get_other_traffic_selectors(this->policy, other);
396 ts_payload = ts_payload_create_from_traffic_selectors(FALSE, ts_list);
397 ts_list->destroy_offset(ts_list, offsetof(traffic_selector_t, destroy));
398
399 request->add_payload(request, (payload_t*)ts_payload);
400 }
401
402 this->message_id = this->ike_sa->get_next_message_id(this->ike_sa);
403 request->set_message_id(request, this->message_id);
404 return SUCCESS;
405 }
406
407 /**
408 * Handle all kind of notifies
409 */
410 static status_t process_notifies(private_ike_auth_t *this, notify_payload_t *notify_payload)
411 {
412 notify_type_t notify_type = notify_payload->get_notify_type(notify_payload);
413
414 DBG2(DBG_IKE, "process notify type %N", notify_type_names, notify_type);
415
416 switch (notify_type)
417 {
418 /* these notifies are not critical. no child_sa is built, but IKE stays alive */
419 case SINGLE_PAIR_REQUIRED:
420 {
421 SIG(CHILD_UP_FAILED, "received a SINGLE_PAIR_REQUIRED notify");
422 this->build_child = FALSE;
423 return SUCCESS;
424 }
425 case TS_UNACCEPTABLE:
426 {
427 SIG(CHILD_UP_FAILED, "received TS_UNACCEPTABLE notify");
428 this->build_child = FALSE;
429 return SUCCESS;
430 }
431 case NO_PROPOSAL_CHOSEN:
432 {
433 SIG(CHILD_UP_FAILED, "received NO_PROPOSAL_CHOSEN notify");
434 this->build_child = FALSE;
435 return SUCCESS;
436 }
437 case USE_TRANSPORT_MODE:
438 {
439 this->mode = MODE_TRANSPORT;
440 return SUCCESS;
441 }
442 case USE_BEET_MODE:
443 {
444 this->mode = MODE_BEET;
445 return SUCCESS;
446 }
447 default:
448 {
449 if (notify_type < 16383)
450 {
451 SIG(IKE_UP_FAILED, "received %N notify error, deleting IKE_SA",
452 notify_type_names, notify_type);
453 return DESTROY_ME;
454 }
455 else
456 {
457 DBG1(DBG_IKE, "received %N notify, ignored",
458 notify_type_names, notify_type);
459 return SUCCESS;
460 }
461 }
462 }
463 }
464
465 /**
466 * Import certificate requests from a certreq payload
467 */
468 static void add_certificate_request(certreq_payload_t *certreq_payload,
469 linked_list_t *requested_ca_keyids)
470 {
471 chunk_t keyids;
472
473 cert_encoding_t encoding = certreq_payload->get_cert_encoding(certreq_payload);
474
475 if (encoding != CERT_X509_SIGNATURE)
476 {
477 DBG1(DBG_IKE, "certreq payload %N not supported, ignored",
478 cert_encoding_names, encoding);
479 return;
480 }
481
482 keyids = certreq_payload->get_data(certreq_payload);
483
484 while (keyids.len >= HASH_SIZE_SHA1)
485 {
486 chunk_t keyid = { keyids.ptr, HASH_SIZE_SHA1};
487 x509_t *cacert = charon->credentials->get_ca_certificate_by_keyid(charon->credentials, keyid);
488
489 if (cacert)
490 {
491 DBG2(DBG_IKE, "request for certificate issued by ca '%D'", cacert->get_subject(cacert));
492 requested_ca_keyids->insert_last(requested_ca_keyids, (void *)&keyid);
493 }
494 else
495 {
496 DBG2(DBG_IKE, "request for certificate issued by unknown ca");
497 }
498 DBG2(DBG_IKE, " with keyid %#B", &keyid);
499
500 keyids.ptr += HASH_SIZE_SHA1;
501 keyids.len -= HASH_SIZE_SHA1;
502 }
503 }
504
505 /**
506 * Import a certificate from a cert payload
507 */
508 static void import_certificate(cert_payload_t *cert_payload)
509 {
510 bool found;
511 x509_t *cert;
512 cert_encoding_t encoding;
513
514 encoding = cert_payload->get_cert_encoding(cert_payload);
515 if (encoding != CERT_X509_SIGNATURE)
516 {
517 DBG1(DBG_IKE, "certificate payload %N not supported, ignored",
518 cert_encoding_names, encoding);
519 return;
520 }
521 cert = x509_create_from_chunk(cert_payload->get_data_clone(cert_payload));
522 if (cert)
523 {
524 if (charon->credentials->verify(charon->credentials, cert, &found))
525 {
526 DBG2(DBG_IKE, "received end entity certificate is trusted, added to store");
527 if (!found)
528 {
529 charon->credentials->add_end_certificate(charon->credentials, cert);
530 }
531 else
532 {
533 cert->destroy(cert);
534 }
535 }
536 else
537 {
538 DBG1(DBG_IKE, "received end entity certificate is not trusted, discarded");
539 cert->destroy(cert);
540 }
541 }
542 else
543 {
544 DBG1(DBG_IKE, "parsing of received certificate failed, discarded");
545 }
546 }
547
548 /**
549 * Check a list of traffic selectors if any selector belongs to host
550 */
551 static bool ts_list_is_host(linked_list_t *list, host_t *host)
552 {
553 traffic_selector_t *ts;
554 bool is_host = TRUE;
555 iterator_t *iterator = list->create_iterator(list, TRUE);
556
557 while (is_host && iterator->iterate(iterator, (void**)&ts))
558 {
559 is_host = is_host && ts->is_host(ts, host);
560 }
561 iterator->destroy(iterator);
562 return is_host;
563 }
564
565 /**
566 * Install a CHILD_SA for usage
567 */
568 static status_t install_child_sa(private_ike_auth_t *this, bool initiator)
569 {
570 prf_plus_t *prf_plus;
571 chunk_t seed;
572 status_t status;
573
574 seed = chunk_alloc(this->nonce_i.len + this->nonce_r.len);
575 memcpy(seed.ptr, this->nonce_i.ptr, this->nonce_i.len);
576 memcpy(seed.ptr + this->nonce_i.len, this->nonce_r.ptr, this->nonce_r.len);
577 prf_plus = prf_plus_create(this->ike_sa->get_child_prf(this->ike_sa), seed);
578 chunk_free(&seed);
579
580 if (initiator)
581 {
582 status = this->child_sa->update(this->child_sa, this->proposal,
583 this->mode, prf_plus);
584 }
585 else
586 {
587 status = this->child_sa->add(this->child_sa, this->proposal,
588 this->mode, prf_plus);
589 }
590 prf_plus->destroy(prf_plus);
591 if (status != SUCCESS)
592 {
593 return DESTROY_ME;
594 }
595 if (initiator)
596 {
597 status = this->child_sa->add_policies(this->child_sa, this->tsi,
598 this->tsr, this->mode);
599 }
600 else
601 {
602 status = this->child_sa->add_policies(this->child_sa, this->tsr,
603 this->tsi, this->mode);
604 }
605 if (status != SUCCESS)
606 {
607 return DESTROY_ME;
608 }
609
610 /* add to IKE_SA, and remove from transaction */
611 this->child_sa->set_state(this->child_sa, CHILD_INSTALLED);
612 this->ike_sa->add_child_sa(this->ike_sa, this->child_sa);
613 this->child_sa = NULL;
614 return SUCCESS;
615 }
616
617 /**
618 * Implementation of transaction_t.get_response.
619 */
620 static status_t get_response(private_ike_auth_t *this, message_t *request,
621 message_t **result, transaction_t **next)
622 {
623 host_t *me, *other;
624 identification_t *my_id, *other_id;
625 linked_list_t *requested_ca_keyids;
626 message_t *response;
627 status_t status;
628 iterator_t *payloads;
629 payload_t *payload;
630 id_payload_t *idi_request = NULL;
631 id_payload_t *idr_request = NULL;
632 auth_payload_t *auth_request = NULL;
633 certreq_payload_t *certreq_request = NULL;
634 cert_payload_t *cert_request = NULL;
635 sa_payload_t *sa_request = NULL;
636 ts_payload_t *tsi_request = NULL;
637 ts_payload_t *tsr_request = NULL;
638 id_payload_t *idr_response;
639
640 /* check if we already have built a response (retransmission) */
641 if (this->message)
642 {
643 *result = this->message;
644 return SUCCESS;
645 }
646
647 SIG(CHILD_UP_START, "setting up CHILD_SA along with IKE_AUTH");
648
649 me = this->ike_sa->get_my_host(this->ike_sa);
650 other = this->ike_sa->get_other_host(this->ike_sa);
651 this->message_id = request->get_message_id(request);
652
653 /* set up response */
654 response = message_create();
655 response->set_source(response, me->clone(me));
656 response->set_destination(response, other->clone(other));
657 response->set_exchange_type(response, IKE_AUTH);
658 response->set_request(response, FALSE);
659 response->set_message_id(response, this->message_id);
660 response->set_ike_sa_id(response, this->ike_sa->get_id(this->ike_sa));
661 this->message = response;
662 *result = response;
663
664 /* check message type */
665 if (request->get_exchange_type(request) != IKE_AUTH)
666 {
667 SIG(IKE_UP_FAILED, "IKE_AUTH response of invalid type, deleting IKE_SA");
668 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
669 return DESTROY_ME;
670 }
671
672 /* initialize list of requested ca keyids */
673 requested_ca_keyids = linked_list_create();
674
675 /* Iterate over all payloads. */
676 payloads = request->get_payload_iterator(request);
677 while (payloads->iterate(payloads, (void**)&payload))
678 {
679 switch (payload->get_type(payload))
680 {
681 case ID_INITIATOR:
682 idi_request = (id_payload_t*)payload;
683 break;
684 case ID_RESPONDER:
685 idr_request = (id_payload_t*)payload;
686 break;
687 case AUTHENTICATION:
688 auth_request = (auth_payload_t*)payload;
689 break;
690 case CERTIFICATE_REQUEST:
691 certreq_request = (certreq_payload_t*)payload;
692 add_certificate_request(certreq_request, requested_ca_keyids);
693 break;
694 case CERTIFICATE:
695 cert_request = (cert_payload_t*)payload;
696 break;
697 case SECURITY_ASSOCIATION:
698 sa_request = (sa_payload_t*)payload;
699 break;
700 case TRAFFIC_SELECTOR_INITIATOR:
701 tsi_request = (ts_payload_t*)payload;
702 break;
703 case TRAFFIC_SELECTOR_RESPONDER:
704 tsr_request = (ts_payload_t*)payload;
705 break;
706 case NOTIFY:
707 {
708 status = process_notifies(this, (notify_payload_t*)payload);
709 if (status == FAILED)
710 {
711 payloads->destroy(payloads);
712 requested_ca_keyids->destroy(requested_ca_keyids);
713 /* we return SUCCESS, returned FAILED means do next transaction */
714 return SUCCESS;
715 }
716 if (status == DESTROY_ME)
717 {
718 payloads->destroy(payloads);
719 requested_ca_keyids->destroy(requested_ca_keyids);
720 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
721 return DESTROY_ME;
722 }
723 break;
724 }
725 default:
726 {
727 DBG1(DBG_IKE, "ignoring %N payload",
728 payload_type_names, payload->get_type(payload));
729 break;
730 }
731 }
732 }
733 payloads->destroy(payloads);
734
735 /* check if we have all payloads */
736 if (!(idi_request && auth_request && sa_request && tsi_request && tsr_request))
737 {
738 build_notify(INVALID_SYNTAX, response, TRUE);
739 SIG(IKE_UP_FAILED, "request message incomplete, deleting IKE_SA");
740 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
741 requested_ca_keyids->destroy(requested_ca_keyids);
742 return DESTROY_ME;
743 }
744
745 { /* process ID payload */
746 other_id = idi_request->get_identification(idi_request);
747 if (idr_request)
748 {
749 my_id = idr_request->get_identification(idr_request);
750 }
751 else
752 {
753 my_id = identification_create_from_encoding(ID_ANY, chunk_empty);
754 }
755 }
756
757
758 { /* get a policy and process traffic selectors */
759 linked_list_t *my_ts, *other_ts;
760
761 my_ts = tsr_request->get_traffic_selectors(tsr_request);
762 other_ts = tsi_request->get_traffic_selectors(tsi_request);
763
764 this->policy = charon->policies->get_policy(charon->policies,
765 my_id, other_id,
766 my_ts, other_ts,
767 me, other,
768 requested_ca_keyids);
769 requested_ca_keyids->destroy(requested_ca_keyids);
770
771 if (this->policy)
772 {
773 this->tsr = this->policy->select_my_traffic_selectors(this->policy, my_ts, me);
774 this->tsi = this->policy->select_other_traffic_selectors(this->policy, other_ts, other);
775 }
776 my_ts->destroy_offset(my_ts, offsetof(traffic_selector_t, destroy));
777 other_ts->destroy_offset(other_ts, offsetof(traffic_selector_t, destroy));
778
779 /* TODO: We should check somehow if we have a policy, but with other
780 * traffic selectors. Then we would create a IKE_SA without a CHILD_SA. */
781 if (this->policy == NULL)
782 {
783 SIG(IKE_UP_FAILED, "no acceptable policy for IDs %D - %D found, "
784 "deleting IKE_SA", my_id, other_id);
785 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
786 my_id->destroy(my_id);
787 other_id->destroy(other_id);
788 build_notify(AUTHENTICATION_FAILED, response, TRUE);
789 return DESTROY_ME;
790 }
791 my_id->destroy(my_id);
792
793 /* get my id from policy, which must contain a fully qualified valid id */
794 my_id = this->policy->get_my_id(this->policy);
795 this->ike_sa->set_my_id(this->ike_sa, my_id->clone(my_id));
796 this->ike_sa->set_other_id(this->ike_sa, other_id);
797
798 idr_response = id_payload_create_from_identification(FALSE, my_id);
799 response->add_payload(response, (payload_t*)idr_response);
800 }
801
802 if (this->policy->get_auth_method(this->policy) == AUTH_RSA
803 && this->connection->get_cert_policy(this->connection) != CERT_NEVER_SEND)
804 { /* build certificate payload */
805 x509_t *cert;
806 cert_payload_t *cert_payload;
807
808 cert = charon->credentials->get_certificate(charon->credentials, my_id);
809 if (cert)
810 {
811 cert_payload = cert_payload_create_from_x509(cert);
812 response->add_payload(response, (payload_t *)cert_payload);
813 }
814 else
815 {
816 DBG1(DBG_IKE, "could not find my certificate, cert payload omitted");
817 }
818 }
819
820 if (cert_request)
821 { /* process certificate payload */
822 import_certificate(cert_request);
823 }
824
825 { /* process auth payload */
826 authenticator_t *authenticator;
827 auth_payload_t *auth_response;
828 auth_method_t auth_method;
829 status_t status;
830
831 auth_method = auth_request->get_auth_method(auth_request);
832 authenticator = authenticator_create(this->ike_sa, auth_method);
833 if (authenticator == NULL)
834 {
835 SIG(IKE_UP_FAILED, "auth method %N not supported, deleting IKE_SA",
836 auth_method_names, auth_method);
837 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
838 return DESTROY_ME;
839 }
840 status = authenticator->verify(authenticator, this->init_request,
841 this->nonce_r, auth_request);
842 authenticator->destroy(authenticator);
843 if (status != SUCCESS)
844 {
845 SIG(IKE_UP_FAILED, "authentication failed, deleting IKE_SA");
846 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
847 build_notify(AUTHENTICATION_FAILED, response, TRUE);
848 return DESTROY_ME;
849 }
850
851 auth_method = this->policy->get_auth_method(this->policy);
852 authenticator = authenticator_create(this->ike_sa, auth_method);
853 if (authenticator == NULL)
854 {
855 SIG(IKE_UP_FAILED, "auth method %N not supported, deleting IKE_SA",
856 auth_method_names, auth_method);
857 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
858 return DESTROY_ME;
859 }
860 status = authenticator->build(authenticator, this->init_response,
861 this->nonce_i, &auth_response);
862 authenticator->destroy(authenticator);
863 if (status != SUCCESS)
864 {
865 SIG(IKE_UP_FAILED, "authentication data generation failed, deleting IKE_SA");
866 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
867 build_notify(AUTHENTICATION_FAILED, response, TRUE);
868 return DESTROY_ME;
869 }
870 response->add_payload(response, (payload_t*)auth_response);
871 }
872
873 SIG(IKE_UP_SUCCESS, "IKE_SA '%s' established between %H[%D]...%H[%D]",
874 this->ike_sa->get_name(this->ike_sa), me, my_id, other, other_id);
875
876 { /* process SA payload */
877 linked_list_t *proposal_list;
878 sa_payload_t *sa_response;
879 ts_payload_t *ts_response;
880 bool use_natt;
881 u_int32_t soft_lifetime, hard_lifetime;
882
883 /* prepare reply */
884 sa_response = sa_payload_create();
885
886 /* get proposals from request, and select one with ours */
887 proposal_list = sa_request->get_proposals(sa_request);
888 DBG2(DBG_IKE, "selecting proposals:");
889 this->proposal = this->policy->select_proposal(this->policy, proposal_list);
890 proposal_list->destroy_offset(proposal_list, offsetof(proposal_t, destroy));
891
892 /* do we have a proposal? */
893 if (this->proposal == NULL)
894 {
895 SIG(CHILD_UP_FAILED, "CHILD_SA proposals unacceptable, no CHILD_SA created");
896 DBG1(DBG_IKE, "adding NO_PROPOSAL_CHOSEN notify to response");
897 build_notify(NO_PROPOSAL_CHOSEN, response, FALSE);
898 }
899 /* do we have traffic selectors? */
900 else if (this->tsi->get_count(this->tsi) == 0 || this->tsr->get_count(this->tsr) == 0)
901 {
902 SIG(CHILD_UP_FAILED, "CHILD_SA traffic selectors unacceptable, no CHILD_SA created");
903 DBG1(DBG_IKE, "adding TS_UNACCEPTABLE notify to response");
904 build_notify(TS_UNACCEPTABLE, response, FALSE);
905 }
906 else
907 {
908 /* create child sa */
909 soft_lifetime = this->policy->get_soft_lifetime(this->policy);
910 hard_lifetime = this->policy->get_hard_lifetime(this->policy);
911 use_natt = this->ike_sa->is_natt_enabled(this->ike_sa);
912 this->child_sa = child_sa_create(this->reqid, me, other, my_id, other_id,
913 soft_lifetime, hard_lifetime,
914 this->policy->get_updown(this->policy),
915 this->policy->get_hostaccess(this->policy),
916 use_natt);
917 this->child_sa->set_name(this->child_sa, this->policy->get_name(this->policy));
918
919 /* check mode, and include notify into reply */
920 switch (this->mode)
921 {
922 case MODE_TUNNEL:
923 /* is the default */
924 break;
925 case MODE_TRANSPORT:
926 if (!ts_list_is_host(this->tsi, other) ||
927 !ts_list_is_host(this->tsr, me))
928 {
929 this->mode = MODE_TUNNEL;
930 DBG1(DBG_IKE, "not using tranport mode, not host-to-host");
931 }
932 else if (this->ike_sa->is_natt_enabled(this->ike_sa))
933 {
934 this->mode = MODE_TUNNEL;
935 DBG1(DBG_IKE, "not using tranport mode, as connection NATed");
936 }
937 else
938 {
939 build_notify(USE_TRANSPORT_MODE, response, FALSE);
940 }
941 break;
942 case MODE_BEET:
943 if (!ts_list_is_host(this->tsi, NULL) ||
944 !ts_list_is_host(this->tsr, NULL))
945 {
946 this->mode = MODE_TUNNEL;
947 DBG1(DBG_IKE, "not using BEET mode, not host-to-host");
948 }
949 else
950 {
951 build_notify(USE_BEET_MODE, response, FALSE);
952 }
953 break;
954 }
955
956 if (install_child_sa(this, FALSE) != SUCCESS)
957 {
958 SIG(CHILD_UP_FAILED, "installing CHILD_SA '%s' failed, no CHILD_SA created",
959 this->policy->get_name(this->policy));
960 DBG1(DBG_IKE, "adding NO_PROPOSAL_CHOSEN notify to response");
961 build_notify(NO_PROPOSAL_CHOSEN, response, FALSE);
962 }
963 else
964 {
965 /* add proposal to sa payload */
966 sa_response->add_proposal(sa_response, this->proposal);
967 SIG(CHILD_UP_SUCCESS, "CHILD_SA '%s' created",
968 this->policy->get_name(this->policy));
969 }
970 }
971 response->add_payload(response, (payload_t*)sa_response);
972
973 /* add ts payload after sa payload */
974 ts_response = ts_payload_create_from_traffic_selectors(TRUE, this->tsi);
975 response->add_payload(response, (payload_t*)ts_response);
976 ts_response = ts_payload_create_from_traffic_selectors(FALSE, this->tsr);
977 response->add_payload(response, (payload_t*)ts_response);
978 }
979 /* set established state */
980 this->ike_sa->set_state(this->ike_sa, IKE_ESTABLISHED);
981 return SUCCESS;
982 }
983
984
985 /**
986 * Implementation of transaction_t.conclude
987 */
988 static status_t conclude(private_ike_auth_t *this, message_t *response,
989 transaction_t **transaction)
990 {
991 iterator_t *payloads;
992 payload_t *payload;
993 host_t *me, *other;
994 identification_t *other_id, *my_id;
995 ts_payload_t *tsi_payload = NULL;
996 ts_payload_t *tsr_payload = NULL;
997 id_payload_t *idr_payload = NULL;
998 cert_payload_t *cert_payload = NULL;
999 auth_payload_t *auth_payload = NULL;
1000 sa_payload_t *sa_payload = NULL;
1001 status_t status;
1002
1003 /* check message type */
1004 if (response->get_exchange_type(response) != IKE_AUTH)
1005 {
1006 SIG(IKE_UP_FAILED, "IKE_AUTH response of invalid type, deleting IKE_SA");
1007 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
1008 return DESTROY_ME;
1009 }
1010
1011 me = this->ike_sa->get_my_host(this->ike_sa);
1012 other = this->ike_sa->get_other_host(this->ike_sa);
1013
1014 /* Iterate over all payloads to collect them */
1015 payloads = response->get_payload_iterator(response);
1016 while (payloads->iterate(payloads, (void**)&payload))
1017 {
1018 switch (payload->get_type(payload))
1019 {
1020 case ID_RESPONDER:
1021 idr_payload = (id_payload_t*)payload;
1022 break;
1023 case AUTHENTICATION:
1024 auth_payload = (auth_payload_t*)payload;
1025 break;
1026 case CERTIFICATE:
1027 cert_payload = (cert_payload_t*)payload;
1028 break;
1029 case SECURITY_ASSOCIATION:
1030 sa_payload = (sa_payload_t*)payload;
1031 break;
1032 case TRAFFIC_SELECTOR_INITIATOR:
1033 tsi_payload = (ts_payload_t*)payload;
1034 break;
1035 case TRAFFIC_SELECTOR_RESPONDER:
1036 tsr_payload = (ts_payload_t*)payload;
1037 break;
1038 case NOTIFY:
1039 {
1040 status = process_notifies(this, (notify_payload_t*)payload);
1041 if (status == FAILED)
1042 {
1043 payloads->destroy(payloads);
1044 /* we return SUCCESS, as transaction completet */
1045 return SUCCESS;
1046 }
1047 if (status == DESTROY_ME)
1048 {
1049 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
1050 payloads->destroy(payloads);
1051 return status;
1052 }
1053 break;
1054 }
1055 default:
1056 {
1057 DBG1(DBG_IKE, "ignoring payload %N",
1058 payload_type_names, payload->get_type(payload));
1059 break;
1060 }
1061 }
1062 }
1063 payloads->destroy(payloads);
1064
1065 if (!(idr_payload && auth_payload && sa_payload && tsi_payload && tsr_payload))
1066 {
1067 SIG(IKE_UP_FAILED, "response message incomplete, deleting IKE_SA");
1068 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
1069 return DESTROY_ME;
1070 }
1071
1072 { /* process idr payload */
1073 identification_t *configured_other_id;
1074 int wildcards;
1075
1076 other_id = idr_payload->get_identification(idr_payload);
1077 configured_other_id = this->policy->get_other_id(this->policy);
1078
1079 if (!other_id->matches(other_id, configured_other_id, &wildcards))
1080 {
1081 other_id->destroy(other_id);
1082 SIG(IKE_UP_FAILED, "other peer uses unacceptable ID (%D, excepted "
1083 "%D), deleting IKE_SA", other_id, configured_other_id);
1084 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
1085 return DESTROY_ME;
1086 }
1087 /* update other ID. It was already set, but may contain wildcards */
1088 this->ike_sa->set_other_id(this->ike_sa, other_id);
1089 }
1090
1091 if (cert_payload)
1092 { /* process cert payload */
1093 import_certificate(cert_payload);
1094 }
1095
1096 { /* authenticate peer */
1097 authenticator_t *authenticator;
1098 auth_method_t auth_method;
1099 status_t status;
1100
1101 my_id = this->policy->get_my_id(this->policy);
1102 auth_method = auth_payload->get_auth_method(auth_payload);
1103 authenticator = authenticator_create(this->ike_sa, auth_method);
1104 if (authenticator == NULL)
1105 {
1106 SIG(IKE_UP_FAILED, "auth method %N not supported, deleting IKE_SA",
1107 auth_method_names, auth_method);
1108 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
1109 return DESTROY_ME;
1110 }
1111 status = authenticator->verify(authenticator, this->init_response,
1112 this->nonce_i, auth_payload);
1113 authenticator->destroy(authenticator);
1114 if (status != SUCCESS)
1115 {
1116 SIG(IKE_UP_FAILED, "authentication of '%D' with %N failed, "
1117 "deleting IKE_SA", other_id, auth_method_names, auth_method);
1118 SIG(CHILD_UP_FAILED, "initiating CHILD_SA failed, unable to create IKE_SA");
1119 return DESTROY_ME;
1120 }
1121 }
1122
1123 SIG(IKE_UP_SUCCESS, "IKE_SA '%s' established between %H[%D]...%H[%D]",
1124 this->ike_sa->get_name(this->ike_sa), me, my_id, other, other_id);
1125
1126 { /* process traffic selectors for us */
1127 linked_list_t *ts_received = tsi_payload->get_traffic_selectors(tsi_payload);
1128 this->tsi = this->policy->select_my_traffic_selectors(this->policy, ts_received, me);
1129 ts_received->destroy_offset(ts_received, offsetof(traffic_selector_t, destroy));
1130 }
1131
1132 { /* process traffic selectors for other */
1133 linked_list_t *ts_received = tsr_payload->get_traffic_selectors(tsr_payload);
1134 this->tsr = this->policy->select_other_traffic_selectors(this->policy, ts_received, other);
1135 ts_received->destroy_offset(ts_received, offsetof(traffic_selector_t, destroy));
1136 }
1137
1138 { /* process sa payload */
1139 linked_list_t *proposal_list;
1140
1141 proposal_list = sa_payload->get_proposals(sa_payload);
1142 /* we have to re-check here if other's selection is valid */
1143 this->proposal = this->policy->select_proposal(this->policy, proposal_list);
1144 proposal_list->destroy_offset(proposal_list, offsetof(proposal_t, destroy));
1145
1146 /* everything fine to create CHILD? */
1147 if (this->proposal == NULL ||
1148 this->tsi->get_count(this->tsi) == 0 ||
1149 this->tsr->get_count(this->tsr) == 0 ||
1150 !this->build_child)
1151 {
1152 SIG(CHILD_UP_FAILED, "CHILD_SA negotiation failed, no CHILD_SA built");
1153 }
1154 else
1155 {
1156 /* check mode if it is acceptable */
1157 switch (this->mode)
1158 {
1159 case MODE_TUNNEL:
1160 /* is the default */
1161 break;
1162 case MODE_TRANSPORT:
1163 /* TODO: we should close the CHILD_SA if negotiated
1164 * mode is not acceptable for us */
1165 if (!ts_list_is_host(this->tsi, me) ||
1166 !ts_list_is_host(this->tsr, other))
1167 {
1168 this->mode = MODE_TUNNEL;
1169 DBG1(DBG_IKE, "not using tranport mode, not host-to-host");
1170 }
1171 else if (this->ike_sa->is_natt_enabled(this->ike_sa))
1172 {
1173 this->mode = MODE_TUNNEL;
1174 DBG1(DBG_IKE, "not using tranport mode, as connection NATed");
1175 }
1176 break;
1177 case MODE_BEET:
1178 if (!ts_list_is_host(this->tsi, NULL) ||
1179 !ts_list_is_host(this->tsr, NULL))
1180 {
1181 this->mode = MODE_TUNNEL;
1182 DBG1(DBG_IKE, "not using BEET mode, not host-to-host");
1183 }
1184 break;
1185 }
1186
1187 if (install_child_sa(this, TRUE) != SUCCESS)
1188 {
1189 SIG(CHILD_UP_FAILED, "installing CHILD_SA '%s' failed, no CHILD_SA built",
1190 this->policy->get_name(this->policy));
1191 /* TODO: we should send a DELETE for that CHILD to stay
1192 * synchronous with the peer */
1193 }
1194 else
1195 {
1196 SIG(CHILD_UP_SUCCESS, "CHILD_SA '%s' created",
1197 this->policy->get_name(this->policy));
1198 }
1199 }
1200 }
1201 /* set new state */
1202 this->ike_sa->set_state(this->ike_sa, IKE_ESTABLISHED);
1203 return SUCCESS;
1204 }
1205
1206 /**
1207 * implements transaction_t.destroy
1208 */
1209 static void destroy(private_ike_auth_t *this)
1210 {
1211 DESTROY_IF(this->message);
1212 DESTROY_IF(this->proposal);
1213 DESTROY_IF(this->child_sa);
1214 DESTROY_IF(this->policy);
1215 DESTROY_IF(this->connection);
1216 if (this->tsi)
1217 {
1218 this->tsi->destroy_offset(this->tsi, offsetof(traffic_selector_t, destroy));
1219 }
1220 if (this->tsr)
1221 {
1222 this->tsr->destroy_offset(this->tsr, offsetof(traffic_selector_t, destroy));
1223 }
1224 chunk_free(&this->nonce_i);
1225 chunk_free(&this->nonce_r);
1226 chunk_free(&this->init_request);
1227 chunk_free(&this->init_response);
1228 free(this);
1229 }
1230
1231 /*
1232 * Described in header.
1233 */
1234 ike_auth_t *ike_auth_create(ike_sa_t *ike_sa)
1235 {
1236 private_ike_auth_t *this = malloc_thing(private_ike_auth_t);
1237
1238 /* transaction interface functions */
1239 this->public.transaction.get_request = (status_t(*)(transaction_t*,message_t**))get_request;
1240 this->public.transaction.get_response = (status_t(*)(transaction_t*,message_t*,message_t**,transaction_t**))get_response;
1241 this->public.transaction.conclude = (status_t(*)(transaction_t*,message_t*,transaction_t**))conclude;
1242 this->public.transaction.get_message_id = (u_int32_t(*)(transaction_t*))get_message_id;
1243 this->public.transaction.requested = (u_int32_t(*)(transaction_t*))requested;
1244 this->public.transaction.destroy = (void(*)(transaction_t*))destroy;
1245
1246 /* public functions */
1247 this->public.set_config = (void(*)(ike_auth_t*,connection_t*,policy_t*))set_config;
1248 this->public.set_reqid = (void(*)(ike_auth_t*,u_int32_t))set_reqid;
1249 this->public.set_nonces = (void(*)(ike_auth_t*,chunk_t,chunk_t))set_nonces;
1250 this->public.set_init_messages = (void(*)(ike_auth_t*,chunk_t,chunk_t))set_init_messages;
1251
1252 /* private data */
1253 this->ike_sa = ike_sa;
1254 this->message_id = 0;
1255 this->message = NULL;
1256 this->requested = 0;
1257 this->nonce_i = chunk_empty;
1258 this->nonce_r = chunk_empty;
1259 this->init_request = chunk_empty;
1260 this->init_response = chunk_empty;
1261 this->child_sa = NULL;
1262 this->proposal = NULL;
1263 this->tsi = NULL;
1264 this->tsr = NULL;
1265 this->build_child = TRUE;
1266 this->reqid = 0;
1267 this->mode = MODE_TUNNEL;
1268
1269 return &this->public;
1270 }