Annotation of embedaddon/strongswan/src/libcharon/sa/ikev1/phase1.c, revision 1.1.1.1
1.1 misho 1: /*
2: * Copyright (C) 2012-2017 Tobias Brunner
3: * HSR Hochschule fuer Technik Rapperswil
4: *
5: * Copyright (C) 2012 Martin Willi
6: * Copyright (C) 2012 revosec AG
7: *
8: * This program is free software; you can redistribute it and/or modify it
9: * under the terms of the GNU General Public License as published by the
10: * Free Software Foundation; either version 2 of the License, or (at your
11: * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>.
12: *
13: * This program is distributed in the hope that it will be useful, but
14: * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
15: * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16: * for more details.
17: */
18:
19: #include "phase1.h"
20:
21: #include <daemon.h>
22: #include <sa/ikev1/keymat_v1.h>
23: #include <encoding/payloads/ke_payload.h>
24: #include <encoding/payloads/nonce_payload.h>
25: #include <collections/linked_list.h>
26:
27: typedef struct private_phase1_t private_phase1_t;
28:
29: /**
30: * Private data of an phase1_t object.
31: */
32: struct private_phase1_t {
33:
34: /**
35: * Public phase1_t interface.
36: */
37: phase1_t public;
38:
39: /**
40: * IKE_SA we negotiate
41: */
42: ike_sa_t *ike_sa;
43:
44: /**
45: * Currently selected peer config
46: */
47: peer_cfg_t *peer_cfg;
48:
49: /**
50: * Other possible peer config candidates
51: */
52: linked_list_t *candidates;
53:
54: /**
55: * Acting as initiator
56: */
57: bool initiator;
58:
59: /**
60: * Extracted SA payload bytes
61: */
62: chunk_t sa_payload;
63:
64: /**
65: * DH exchange
66: */
67: diffie_hellman_t *dh;
68:
69: /**
70: * Keymat derivation (from SA)
71: */
72: keymat_v1_t *keymat;
73:
74: /**
75: * Received public DH value from peer
76: */
77: chunk_t dh_value;
78:
79: /**
80: * Initiators nonce
81: */
82: chunk_t nonce_i;
83:
84: /**
85: * Responder nonce
86: */
87: chunk_t nonce_r;
88: };
89:
90: /**
91: * Get the first authentication config from peer config
92: */
93: static auth_cfg_t *get_auth_cfg(peer_cfg_t *peer_cfg, bool local)
94: {
95: enumerator_t *enumerator;
96: auth_cfg_t *cfg = NULL;
97:
98: enumerator = peer_cfg->create_auth_cfg_enumerator(peer_cfg, local);
99: enumerator->enumerate(enumerator, &cfg);
100: enumerator->destroy(enumerator);
101: return cfg;
102: }
103:
104: /**
105: * Find a shared key for the given identities
106: */
107: static shared_key_t *find_shared_key(identification_t *my_id, host_t *me,
108: identification_t *other_id, host_t *other)
109: {
110: identification_t *any_id = NULL;
111: shared_key_t *shared_key;
112:
113: if (!other_id)
114: {
115: any_id = identification_create_from_encoding(ID_ANY, chunk_empty);
116: other_id = any_id;
117: }
118: shared_key = lib->credmgr->get_shared(lib->credmgr, SHARED_IKE,
119: my_id, other_id);
120: if (!shared_key)
121: {
122: DBG1(DBG_IKE, "no shared key found for '%Y'[%H] - '%Y'[%H]",
123: my_id, me, other_id, other);
124: }
125: DESTROY_IF(any_id);
126: return shared_key;
127: }
128:
129: /**
130: * Lookup a shared secret for this IKE_SA
131: */
132: static shared_key_t *lookup_shared_key(private_phase1_t *this,
133: peer_cfg_t *peer_cfg)
134: {
135: host_t *me, *other;
136: identification_t *my_id, *other_id;
137: shared_key_t *shared_key = NULL;
138: auth_cfg_t *my_auth, *other_auth;
139: enumerator_t *enumerator;
140:
141: me = this->ike_sa->get_my_host(this->ike_sa);
142: other = this->ike_sa->get_other_host(this->ike_sa);
143:
144: if (peer_cfg)
145: { /* as initiator or aggressive responder, use identities */
146: my_auth = get_auth_cfg(peer_cfg, TRUE);
147: other_auth = get_auth_cfg(peer_cfg, FALSE);
148: if (my_auth && other_auth)
149: {
150: my_id = my_auth->get(my_auth, AUTH_RULE_IDENTITY);
151: if (peer_cfg->use_aggressive(peer_cfg))
152: {
153: other_id = this->ike_sa->get_other_id(this->ike_sa);
154: }
155: else
156: {
157: other_id = other_auth->get(other_auth, AUTH_RULE_IDENTITY);
158: }
159: if (my_id)
160: {
161: shared_key = find_shared_key(my_id, me, other_id, other);
162: }
163: }
164: }
165: else
166: { /* as responder, we try to find a config by IP addresses and use the
167: * configured identities to find the PSK */
168: enumerator = charon->backends->create_peer_cfg_enumerator(
169: charon->backends, me, other, NULL, NULL, IKEV1);
170: while (enumerator->enumerate(enumerator, &peer_cfg))
171: {
172: my_auth = get_auth_cfg(peer_cfg, TRUE);
173: other_auth = get_auth_cfg(peer_cfg, FALSE);
174: if (my_auth && other_auth)
175: {
176: my_id = my_auth->get(my_auth, AUTH_RULE_IDENTITY);
177: other_id = other_auth->get(other_auth, AUTH_RULE_IDENTITY);
178: if (my_id)
179: {
180: shared_key = find_shared_key(my_id, me, other_id, other);
181: if (shared_key)
182: {
183: break;
184: }
185: }
186: }
187: }
188: enumerator->destroy(enumerator);
189: }
190: if (!shared_key)
191: { /* try to get a PSK for IP addresses */
192: my_id = identification_create_from_sockaddr(me->get_sockaddr(me));
193: other_id = identification_create_from_sockaddr(
194: other->get_sockaddr(other));
195: if (my_id && other_id)
196: {
197: shared_key = lib->credmgr->get_shared(lib->credmgr, SHARED_IKE,
198: my_id, other_id);
199: }
200: DESTROY_IF(my_id);
201: DESTROY_IF(other_id);
202: if (!shared_key)
203: {
204: DBG1(DBG_IKE, "no shared key found for %H - %H", me, other);
205: }
206: }
207: return shared_key;
208: }
209:
210: METHOD(phase1_t, create_hasher, bool,
211: private_phase1_t *this)
212: {
213: return this->keymat->create_hasher(this->keymat,
214: this->ike_sa->get_proposal(this->ike_sa));
215: }
216:
217: METHOD(phase1_t, create_dh, bool,
218: private_phase1_t *this, diffie_hellman_group_t group)
219: {
220: this->dh = this->keymat->keymat.create_dh(&this->keymat->keymat, group);
221: return this->dh != NULL;
222: }
223:
224: METHOD(phase1_t, derive_keys, bool,
225: private_phase1_t *this, peer_cfg_t *peer_cfg, auth_method_t method)
226: {
227: shared_key_t *shared_key = NULL;
228:
229: switch (method)
230: {
231: case AUTH_PSK:
232: case AUTH_XAUTH_INIT_PSK:
233: case AUTH_XAUTH_RESP_PSK:
234: shared_key = lookup_shared_key(this, peer_cfg);
235: if (!shared_key)
236: {
237: return FALSE;
238: }
239: break;
240: default:
241: break;
242: }
243:
244: if (!this->keymat->derive_ike_keys(this->keymat,
245: this->ike_sa->get_proposal(this->ike_sa),
246: this->dh, this->dh_value, this->nonce_i, this->nonce_r,
247: this->ike_sa->get_id(this->ike_sa), method, shared_key))
248: {
249: DESTROY_IF(shared_key);
250: DBG1(DBG_IKE, "key derivation for %N failed", auth_method_names, method);
251: return FALSE;
252: }
253: charon->bus->ike_keys(charon->bus, this->ike_sa, this->dh, this->dh_value,
254: this->nonce_i, this->nonce_r, NULL, shared_key,
255: method);
256: DESTROY_IF(shared_key);
257: return TRUE;
258: }
259:
260: /**
261: * Check if a peer skipped authentication by using Hybrid authentication
262: */
263: static bool skipped_auth(private_phase1_t *this,
264: auth_method_t method, bool local)
265: {
266: bool initiator;
267:
268: initiator = local == this->initiator;
269: if (initiator && method == AUTH_HYBRID_INIT_RSA)
270: {
271: return TRUE;
272: }
273: if (!initiator && method == AUTH_HYBRID_RESP_RSA)
274: {
275: return TRUE;
276: }
277: return FALSE;
278: }
279:
280: /**
281: * Check if remote authentication constraints fulfilled
282: */
283: static bool check_constraints(private_phase1_t *this, auth_method_t method)
284: {
285: identification_t *id;
286: auth_cfg_t *auth, *cfg;
287: peer_cfg_t *peer_cfg;
288:
289: auth = this->ike_sa->get_auth_cfg(this->ike_sa, FALSE);
290: /* auth identity to comply */
291: id = this->ike_sa->get_other_id(this->ike_sa);
292: auth->add(auth, AUTH_RULE_IDENTITY, id->clone(id));
293: if (skipped_auth(this, method, FALSE))
294: {
295: return TRUE;
296: }
297: peer_cfg = this->ike_sa->get_peer_cfg(this->ike_sa);
298: cfg = get_auth_cfg(peer_cfg, FALSE);
299: return cfg && auth->complies(auth, cfg, TRUE);
300: }
301:
302: /**
303: * Save authentication information after authentication succeeded
304: */
305: static void save_auth_cfg(private_phase1_t *this,
306: auth_method_t method, bool local)
307: {
308: auth_cfg_t *auth;
309:
310: if (skipped_auth(this, method, local))
311: {
312: return;
313: }
314: auth = auth_cfg_create();
315: /* for local config, we _copy_ entries from the config, as it contains
316: * certificates we must send later. */
317: auth->merge(auth, this->ike_sa->get_auth_cfg(this->ike_sa, local), local);
318: this->ike_sa->add_auth_cfg(this->ike_sa, local, auth);
319: }
320:
321: /**
322: * Create an authenticator instance
323: */
324: static authenticator_t* create_authenticator(private_phase1_t *this,
325: auth_method_t method, chunk_t id)
326: {
327: authenticator_t *authenticator;
328:
329: authenticator = authenticator_create_v1(this->ike_sa, this->initiator,
330: method, this->dh, this->dh_value, this->sa_payload, id);
331: if (!authenticator)
332: {
333: DBG1(DBG_IKE, "negotiated authentication method %N not supported",
334: auth_method_names, method);
335: }
336: return authenticator;
337: }
338:
339: METHOD(phase1_t, verify_auth, bool,
340: private_phase1_t *this, auth_method_t method, message_t *message,
341: chunk_t id_data)
342: {
343: authenticator_t *authenticator;
344: status_t status;
345:
346: authenticator = create_authenticator(this, method, id_data);
347: if (authenticator)
348: {
349: status = authenticator->process(authenticator, message);
350: authenticator->destroy(authenticator);
351: if (status == SUCCESS && check_constraints(this, method))
352: {
353: save_auth_cfg(this, method, FALSE);
354: return TRUE;
355: }
356: }
357: return FALSE;
358: }
359:
360: METHOD(phase1_t, build_auth, bool,
361: private_phase1_t *this, auth_method_t method, message_t *message,
362: chunk_t id_data)
363: {
364: authenticator_t *authenticator;
365: status_t status;
366:
367: authenticator = create_authenticator(this, method, id_data);
368: if (authenticator)
369: {
370: status = authenticator->build(authenticator, message);
371: authenticator->destroy(authenticator);
372: if (status == SUCCESS)
373: {
374: save_auth_cfg(this, method, TRUE);
375: return TRUE;
376: }
377: }
378: return FALSE;
379: }
380:
381: /**
382: * Get the two auth classes from local or remote config
383: */
384: static void get_auth_class(peer_cfg_t *peer_cfg, bool local,
385: auth_class_t *c1, auth_class_t *c2)
386: {
387: enumerator_t *enumerator;
388: auth_cfg_t *auth;
389:
390: *c1 = *c2 = AUTH_CLASS_ANY;
391:
392: enumerator = peer_cfg->create_auth_cfg_enumerator(peer_cfg, local);
393: while (enumerator->enumerate(enumerator, &auth))
394: {
395: if (*c1 == AUTH_CLASS_ANY)
396: {
397: *c1 = (uintptr_t)auth->get(auth, AUTH_RULE_AUTH_CLASS);
398: }
399: else
400: {
401: *c2 = (uintptr_t)auth->get(auth, AUTH_RULE_AUTH_CLASS);
402: break;
403: }
404: }
405: enumerator->destroy(enumerator);
406: }
407:
408: /**
409: * Select an auth method to use by checking what key we have
410: */
411: static auth_method_t get_pubkey_method(private_phase1_t *this, auth_cfg_t *auth)
412: {
413: auth_method_t method = AUTH_NONE;
414: identification_t *id;
415: private_key_t *private;
416:
417: if (auth)
418: {
419: id = (identification_t*)auth->get(auth, AUTH_RULE_IDENTITY);
420: if (id)
421: {
422: private = lib->credmgr->get_private(lib->credmgr, KEY_ANY, id, NULL);
423: if (private)
424: {
425: switch (private->get_type(private))
426: {
427: case KEY_RSA:
428: method = AUTH_RSA;
429: break;
430: case KEY_ECDSA:
431: switch (private->get_keysize(private))
432: {
433: case 256:
434: method = AUTH_ECDSA_256;
435: break;
436: case 384:
437: method = AUTH_ECDSA_384;
438: break;
439: case 521:
440: method = AUTH_ECDSA_521;
441: break;
442: default:
443: DBG1(DBG_IKE, "%d bit ECDSA private key size not "
444: "supported", private->get_keysize(private));
445: break;
446: }
447: break;
448: default:
449: DBG1(DBG_IKE, "private key of type %N not supported",
450: key_type_names, private->get_type(private));
451: break;
452: }
453: private->destroy(private);
454: }
455: else
456: {
457: DBG1(DBG_IKE, "no private key found for '%Y'", id);
458: }
459: }
460: }
461: return method;
462: }
463:
464: /**
465: * Calculate authentication method from a peer config
466: */
467: static auth_method_t calc_auth_method(private_phase1_t *this,
468: peer_cfg_t *peer_cfg)
469: {
470: auth_class_t i1, i2, r1, r2;
471:
472: get_auth_class(peer_cfg, this->initiator, &i1, &i2);
473: get_auth_class(peer_cfg, !this->initiator, &r1, &r2);
474:
475: if (i1 == AUTH_CLASS_PUBKEY && r1 == AUTH_CLASS_PUBKEY)
476: {
477: if (i2 == AUTH_CLASS_ANY && r2 == AUTH_CLASS_ANY)
478: {
479: /* for any pubkey method, return RSA */
480: return AUTH_RSA;
481: }
482: if (i2 == AUTH_CLASS_XAUTH)
483: {
484: return AUTH_XAUTH_INIT_RSA;
485: }
486: if (r2 == AUTH_CLASS_XAUTH)
487: {
488: return AUTH_XAUTH_RESP_RSA;
489: }
490: }
491: if (i1 == AUTH_CLASS_PSK && r1 == AUTH_CLASS_PSK)
492: {
493: if (i2 == AUTH_CLASS_ANY && r2 == AUTH_CLASS_ANY)
494: {
495: return AUTH_PSK;
496: }
497: if (i2 == AUTH_CLASS_XAUTH)
498: {
499: return AUTH_XAUTH_INIT_PSK;
500: }
501: if (r2 == AUTH_CLASS_XAUTH)
502: {
503: return AUTH_XAUTH_RESP_PSK;
504: }
505: }
506: if (i1 == AUTH_CLASS_XAUTH && r1 == AUTH_CLASS_PUBKEY &&
507: i2 == AUTH_CLASS_ANY && r2 == AUTH_CLASS_ANY)
508: {
509: return AUTH_HYBRID_INIT_RSA;
510: }
511: return AUTH_NONE;
512: }
513:
514: METHOD(phase1_t, get_auth_method, auth_method_t,
515: private_phase1_t *this, peer_cfg_t *peer_cfg)
516: {
517: auth_method_t method;
518:
519: method = calc_auth_method(this, peer_cfg);
520: if (method == AUTH_RSA)
521: {
522: return get_pubkey_method(this, get_auth_cfg(peer_cfg, TRUE));
523: }
524: return method;
525: }
526:
527: /**
528: * Check if a peer config can be used with a given auth method
529: */
530: static bool check_auth_method(private_phase1_t *this, peer_cfg_t *peer_cfg,
531: auth_method_t given)
532: {
533: auth_method_t method;
534:
535: method = calc_auth_method(this, peer_cfg);
536: switch (given)
537: {
538: case AUTH_ECDSA_256:
539: case AUTH_ECDSA_384:
540: case AUTH_ECDSA_521:
541: return method == AUTH_RSA;
542: default:
543: return method == given;
544: }
545: }
546:
547: METHOD(phase1_t, select_config, peer_cfg_t*,
548: private_phase1_t *this, auth_method_t method, bool aggressive,
549: identification_t *id)
550: {
551: enumerator_t *enumerator;
552: peer_cfg_t *current;
553: host_t *me, *other;
554: int unusable = 0;
555:
556: if (this->peer_cfg)
557: { /* try to find an alternative config */
558: if (this->candidates->remove_first(this->candidates,
559: (void**)¤t) != SUCCESS)
560: {
561: DBG1(DBG_CFG, "no alternative config found");
562: return NULL;
563: }
564: DBG1(DBG_CFG, "switching to peer config '%s'",
565: current->get_name(current));
566: return current;
567: }
568:
569: me = this->ike_sa->get_my_host(this->ike_sa);
570: other = this->ike_sa->get_other_host(this->ike_sa);
571: DBG1(DBG_CFG, "looking for %N peer configs matching %H...%H[%Y]",
572: auth_method_names, method, me, other, id);
573: enumerator = charon->backends->create_peer_cfg_enumerator(charon->backends,
574: me, other, NULL, id, IKEV1);
575: while (enumerator->enumerate(enumerator, ¤t))
576: {
577: if (check_auth_method(this, current, method) &&
578: current->use_aggressive(current) == aggressive)
579: {
580: current->get_ref(current);
581: if (!this->peer_cfg)
582: {
583: this->peer_cfg = current;
584: }
585: else
586: {
587: this->candidates->insert_last(this->candidates, current);
588: }
589: }
590: else
591: {
592: unusable++;
593: }
594: }
595: enumerator->destroy(enumerator);
596:
597: if (this->peer_cfg)
598: {
599: DBG1(DBG_CFG, "selected peer config \"%s\"",
600: this->peer_cfg->get_name(this->peer_cfg));
601: return this->peer_cfg->get_ref(this->peer_cfg);
602: }
603: if (unusable)
604: {
605: DBG1(DBG_IKE, "found %d matching config%s, but none allows %N "
606: "authentication using %s Mode", unusable, unusable > 1 ? "s" : "",
607: auth_method_names, method, aggressive ? "Aggressive" : "Main");
608: return NULL;
609: }
610: DBG1(DBG_IKE, "no peer config found");
611: return NULL;
612: }
613:
614: METHOD(phase1_t, get_id, identification_t*,
615: private_phase1_t *this, peer_cfg_t *peer_cfg, bool local)
616: {
617: identification_t *id = NULL;
618: auth_cfg_t *auth;
619:
620: auth = get_auth_cfg(peer_cfg, local);
621: if (auth)
622: {
623: id = auth->get(auth, AUTH_RULE_IDENTITY);
624: if (local && (!id || id->get_type(id) == ID_ANY))
625: { /* no ID configured, use local IP address */
626: host_t *me;
627:
628: me = this->ike_sa->get_my_host(this->ike_sa);
629: if (!me->is_anyaddr(me))
630: {
631: id = identification_create_from_sockaddr(me->get_sockaddr(me));
632: auth->add(auth, AUTH_RULE_IDENTITY, id);
633: }
634: }
635: }
636: return id;
637: }
638:
639: METHOD(phase1_t, has_virtual_ip, bool,
640: private_phase1_t *this, peer_cfg_t *peer_cfg)
641: {
642: enumerator_t *enumerator;
643: bool found = FALSE;
644: host_t *host;
645:
646: enumerator = peer_cfg->create_virtual_ip_enumerator(peer_cfg);
647: found = enumerator->enumerate(enumerator, &host);
648: enumerator->destroy(enumerator);
649:
650: return found;
651: }
652:
653: METHOD(phase1_t, has_pool, bool,
654: private_phase1_t *this, peer_cfg_t *peer_cfg)
655: {
656: enumerator_t *enumerator;
657: bool found = FALSE;
658: char *pool;
659:
660: enumerator = peer_cfg->create_pool_enumerator(peer_cfg);
661: found = enumerator->enumerate(enumerator, &pool);
662: enumerator->destroy(enumerator);
663:
664: return found;
665: }
666:
667: METHOD(phase1_t, save_sa_payload, bool,
668: private_phase1_t *this, message_t *message)
669: {
670: enumerator_t *enumerator;
671: payload_t *payload, *sa = NULL;
672: chunk_t data;
673: size_t offset = IKE_HEADER_LENGTH;
674:
675: enumerator = message->create_payload_enumerator(message);
676: while (enumerator->enumerate(enumerator, &payload))
677: {
678: if (payload->get_type(payload) == PLV1_SECURITY_ASSOCIATION)
679: {
680: sa = payload;
681: break;
682: }
683: else
684: {
685: offset += payload->get_length(payload);
686: }
687: }
688: enumerator->destroy(enumerator);
689:
690: data = message->get_packet_data(message);
691: if (sa && data.len >= offset + sa->get_length(sa))
692: {
693: /* Get SA payload without 4 byte fixed header */
694: data = chunk_skip(data, offset);
695: data.len = sa->get_length(sa);
696: data = chunk_skip(data, 4);
697: this->sa_payload = chunk_clone(data);
698: return TRUE;
699: }
700: DBG1(DBG_IKE, "unable to extract SA payload encoding");
701: return FALSE;
702: }
703:
704: METHOD(phase1_t, add_nonce_ke, bool,
705: private_phase1_t *this, message_t *message)
706: {
707: nonce_payload_t *nonce_payload;
708: ke_payload_t *ke_payload;
709: nonce_gen_t *nonceg;
710: chunk_t nonce;
711:
712: ke_payload = ke_payload_create_from_diffie_hellman(PLV1_KEY_EXCHANGE,
713: this->dh);
714: if (!ke_payload)
715: {
716: DBG1(DBG_IKE, "creating KE payload failed");
717: return FALSE;
718: }
719: message->add_payload(message, &ke_payload->payload_interface);
720:
721: nonceg = this->keymat->keymat.create_nonce_gen(&this->keymat->keymat);
722: if (!nonceg)
723: {
724: DBG1(DBG_IKE, "no nonce generator found to create nonce");
725: return FALSE;
726: }
727: if (!nonceg->allocate_nonce(nonceg, NONCE_SIZE, &nonce))
728: {
729: DBG1(DBG_IKE, "nonce allocation failed");
730: nonceg->destroy(nonceg);
731: return FALSE;
732: }
733: nonceg->destroy(nonceg);
734:
735: nonce_payload = nonce_payload_create(PLV1_NONCE);
736: nonce_payload->set_nonce(nonce_payload, nonce);
737: message->add_payload(message, &nonce_payload->payload_interface);
738:
739: if (this->initiator)
740: {
741: this->nonce_i = nonce;
742: }
743: else
744: {
745: this->nonce_r = nonce;
746: }
747: return TRUE;
748: }
749:
750: METHOD(phase1_t, get_nonce_ke, bool,
751: private_phase1_t *this, message_t *message)
752: {
753: nonce_payload_t *nonce_payload;
754: ke_payload_t *ke_payload;
755:
756: ke_payload = (ke_payload_t*)message->get_payload(message, PLV1_KEY_EXCHANGE);
757: if (!ke_payload)
758: {
759: DBG1(DBG_IKE, "KE payload missing in message");
760: return FALSE;
761: }
762: this->dh_value = chunk_clone(ke_payload->get_key_exchange_data(ke_payload));
763: if (!this->dh->set_other_public_value(this->dh, this->dh_value))
764: {
765: DBG1(DBG_IKE, "unable to apply received KE value");
766: return FALSE;
767: }
768:
769: nonce_payload = (nonce_payload_t*)message->get_payload(message, PLV1_NONCE);
770: if (!nonce_payload)
771: {
772: DBG1(DBG_IKE, "NONCE payload missing in message");
773: return FALSE;
774: }
775:
776: if (this->initiator)
777: {
778: this->nonce_r = nonce_payload->get_nonce(nonce_payload);
779: }
780: else
781: {
782: this->nonce_i = nonce_payload->get_nonce(nonce_payload);
783: }
784: return TRUE;
785: }
786:
787: METHOD(phase1_t, destroy, void,
788: private_phase1_t *this)
789: {
790: DESTROY_IF(this->peer_cfg);
791: this->candidates->destroy_offset(this->candidates,
792: offsetof(peer_cfg_t, destroy));
793: chunk_free(&this->sa_payload);
794: DESTROY_IF(this->dh);
795: free(this->dh_value.ptr);
796: free(this->nonce_i.ptr);
797: free(this->nonce_r.ptr);
798: free(this);
799: }
800:
801: /**
802: * See header
803: */
804: phase1_t *phase1_create(ike_sa_t *ike_sa, bool initiator)
805: {
806: private_phase1_t *this;
807:
808: INIT(this,
809: .public = {
810: .create_hasher = _create_hasher,
811: .create_dh = _create_dh,
812: .derive_keys = _derive_keys,
813: .get_auth_method = _get_auth_method,
814: .get_id = _get_id,
815: .select_config = _select_config,
816: .has_virtual_ip = _has_virtual_ip,
817: .has_pool = _has_pool,
818: .verify_auth = _verify_auth,
819: .build_auth = _build_auth,
820: .save_sa_payload = _save_sa_payload,
821: .add_nonce_ke = _add_nonce_ke,
822: .get_nonce_ke = _get_nonce_ke,
823: .destroy = _destroy,
824: },
825: .candidates = linked_list_create(),
826: .ike_sa = ike_sa,
827: .initiator = initiator,
828: .keymat = (keymat_v1_t*)ike_sa->get_keymat(ike_sa),
829: );
830:
831: return &this->public;
832: }
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>