4 * @brief Implementation of connection_t.
9 * Copyright (C) 2005 Jan Hutter, Martin Willi
10 * Hochschule fuer Technik Rapperswil
12 * This program is free software; you can redistribute it and/or modify it
13 * under the terms of the GNU General Public License as published by the
14 * Free Software Foundation; either version 2 of the License, or (at your
15 * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>.
17 * This program is distributed in the hope that it will be useful, but
18 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
19 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
25 #include "connection.h"
27 #include <utils/linked_list.h>
28 #include <utils/logger.h>
31 * String mappings for auth_method_t.
33 mapping_t auth_method_m
[] = {
34 {RSA_DIGITAL_SIGNATURE
, "RSA"},
35 {SHARED_KEY_MESSAGE_INTEGRITY_CODE
, "SHARED_KEY"},
36 {DSS_DIGITAL_SIGNATURE
, "DSS"},
41 typedef struct private_connection_t private_connection_t
;
44 * Private data of an connection_t object
46 struct private_connection_t
{
54 * Name of the connection
59 * Does charon handle this connection? Or can he ignore it?
64 * Host information of my host.
69 * Host information of other host.
74 * Method to use for own authentication data
76 auth_method_t auth_method
;
81 linked_list_t
*proposals
;
85 * Implementation of connection_t.get_name.
87 static char *get_name (private_connection_t
*this)
93 * Implementation of connection_t.is_ikev2.
95 static bool is_ikev2 (private_connection_t
*this)
101 * Implementation of connection_t.get_my_host.
103 static host_t
*get_my_host (private_connection_t
*this)
105 return this->my_host
;
109 * Implementation of connection_t.get_other_host.
111 static host_t
*get_other_host (private_connection_t
*this)
113 return this->other_host
;
117 * Implementation of connection_t.update_my_host.
119 static void update_my_host(private_connection_t
*this, host_t
*my_host
)
121 this->my_host
->destroy(this->my_host
);
122 this->my_host
= my_host
;
126 * Implementation of connection_t.update_other_host.
128 static void update_other_host(private_connection_t
*this, host_t
*other_host
)
130 this->other_host
->destroy(this->other_host
);
131 this->other_host
= other_host
;
135 * Implementation of connection_t.get_proposals.
137 static linked_list_t
* get_proposals(private_connection_t
*this)
139 return this->proposals
;
143 * Implementation of connection_t.select_proposal.
145 static proposal_t
*select_proposal(private_connection_t
*this, linked_list_t
*proposals
)
147 iterator_t
*stored_iter
, *supplied_iter
;
148 proposal_t
*stored
, *supplied
, *selected
;
150 stored_iter
= this->proposals
->create_iterator(this->proposals
, TRUE
);
151 supplied_iter
= proposals
->create_iterator(proposals
, TRUE
);
153 /* compare all stored proposals with all supplied. Stored ones are preferred. */
154 while (stored_iter
->has_next(stored_iter
))
156 supplied_iter
->reset(supplied_iter
);
157 stored_iter
->current(stored_iter
, (void**)&stored
);
159 while (supplied_iter
->has_next(supplied_iter
))
161 supplied_iter
->current(supplied_iter
, (void**)&supplied
);
162 selected
= stored
->select(stored
, supplied
);
165 /* they match, return */
166 stored_iter
->destroy(stored_iter
);
167 supplied_iter
->destroy(supplied_iter
);
172 /* no proposal match :-(, will result in a NO_PROPOSAL_CHOSEN... */
173 stored_iter
->destroy(stored_iter
);
174 supplied_iter
->destroy(supplied_iter
);
180 * Implementation of connection_t.add_proposal.
182 static void add_proposal(private_connection_t
*this, proposal_t
*proposal
)
184 this->proposals
->insert_last(this->proposals
, proposal
);
188 * Implementation of connection_t.auth_method_t.
190 static auth_method_t
get_auth_method(private_connection_t
*this)
192 return this->auth_method
;
196 * Implementation of connection_t.get_dh_group.
198 static diffie_hellman_group_t
get_dh_group(private_connection_t
*this)
200 iterator_t
*iterator
;
201 proposal_t
*proposal
;
203 diffie_hellman_group_t dh_group
= MODP_NONE
;
205 iterator
= this->proposals
->create_iterator(this->proposals
, TRUE
);
206 while (iterator
->has_next(iterator
))
208 iterator
->current(iterator
, (void**)&proposal
);
209 if (proposal
->get_algorithm(proposal
, DIFFIE_HELLMAN_GROUP
, &algo
))
211 dh_group
= algo
->algorithm
;
215 iterator
->destroy(iterator
);
220 * Implementation of connection_t.check_dh_group.
222 static bool check_dh_group(private_connection_t
*this, diffie_hellman_group_t dh_group
)
224 iterator_t
*prop_iter
, *alg_iter
;
225 proposal_t
*proposal
;
228 prop_iter
= this->proposals
->create_iterator(this->proposals
, TRUE
);
229 while (prop_iter
->has_next(prop_iter
))
231 prop_iter
->current(prop_iter
, (void**)&proposal
);
232 alg_iter
= proposal
->create_algorithm_iterator(proposal
, DIFFIE_HELLMAN_GROUP
);
233 while (alg_iter
->has_next(alg_iter
))
235 alg_iter
->current(alg_iter
, (void**)&algo
);
236 if (algo
->algorithm
== dh_group
)
238 prop_iter
->destroy(prop_iter
);
239 alg_iter
->destroy(alg_iter
);
244 prop_iter
->destroy(prop_iter
);
245 alg_iter
->destroy(alg_iter
);
250 * Implementation of connection_t.clone.
252 static connection_t
*clone(private_connection_t
*this)
254 iterator_t
*iterator
;
255 proposal_t
*proposal
;
256 private_connection_t
*clone
= (private_connection_t
*)connection_create(
259 this->my_host
->clone(this->my_host
),
260 this->other_host
->clone(this->other_host
),
263 /* clone all proposals */
264 iterator
= this->proposals
->create_iterator(this->proposals
, TRUE
);
265 while (iterator
->has_next(iterator
))
267 iterator
->current(iterator
, (void**)&proposal
);
268 proposal
= proposal
->clone(proposal
);
269 clone
->proposals
->insert_last(clone
->proposals
, (void*)proposal
);
271 iterator
->destroy(iterator
);
273 return &clone
->public;
277 * Implementation of connection_t.destroy.
279 static void destroy(private_connection_t
*this)
281 proposal_t
*proposal
;
283 while (this->proposals
->remove_last(this->proposals
, (void**)&proposal
) == SUCCESS
)
285 proposal
->destroy(proposal
);
287 this->proposals
->destroy(this->proposals
);
289 this->my_host
->destroy(this->my_host
);
290 this->other_host
->destroy(this->other_host
);
296 * Described in header.
298 connection_t
* connection_create(char *name
, bool ikev2
, host_t
*my_host
, host_t
*other_host
, auth_method_t auth_method
)
300 private_connection_t
*this = malloc_thing(private_connection_t
);
302 /* public functions */
303 this->public.get_name
= (char*(*)(connection_t
*))get_name
;
304 this->public.is_ikev2
= (bool(*)(connection_t
*))is_ikev2
;
305 this->public.get_my_host
= (host_t
*(*)(connection_t
*))get_my_host
;
306 this->public.update_my_host
= (void(*)(connection_t
*,host_t
*))update_my_host
;
307 this->public.update_other_host
= (void(*)(connection_t
*,host_t
*))update_other_host
;
308 this->public.get_other_host
= (host_t
*(*)(connection_t
*))get_other_host
;
309 this->public.get_proposals
= (linked_list_t
*(*)(connection_t
*))get_proposals
;
310 this->public.select_proposal
= (proposal_t
*(*)(connection_t
*,linked_list_t
*))select_proposal
;
311 this->public.add_proposal
= (void(*)(connection_t
*, proposal_t
*)) add_proposal
;
312 this->public.get_auth_method
= (auth_method_t(*)(connection_t
*)) get_auth_method
;
313 this->public.get_dh_group
= (diffie_hellman_group_t(*)(connection_t
*)) get_dh_group
;
314 this->public.check_dh_group
= (bool(*)(connection_t
*,diffie_hellman_group_t
)) check_dh_group
;
315 this->public.clone
= (connection_t
*(*)(connection_t
*))clone
;
316 this->public.destroy
= (void(*)(connection_t
*))destroy
;
318 /* private variables */
319 this->name
= strdup(name
);
321 this->my_host
= my_host
;
322 this->other_host
= other_host
;
323 this->auth_method
= auth_method
;
325 this->proposals
= linked_list_create();
327 return (&this->public);