aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTobias Brunner <tobias@strongswan.org>2012-05-23 17:55:41 +0200
committerTobias Brunner <tobias@strongswan.org>2012-05-24 15:32:27 +0200
commit624bb24d1257e8198aabe1c8fc2bf3ea65136e2d (patch)
treef55977615e7e4cf44fb3bc4a42a785d4c58eff58
parentfda9f104b4a921bfc0ae4b47807bf3ad9d09815d (diff)
downloadstrongswan-624bb24d1257e8198aabe1c8fc2bf3ea65136e2d.tar.bz2
strongswan-624bb24d1257e8198aabe1c8fc2bf3ea65136e2d.tar.xz
Properly filter IKEv1 proposals consisting of multiple proposal payloads.
Since a proposal_t object is created for each transform contained in the proposal payload, it does not work to simply remove the last proposal_t object added to the list (there may be several other extracted from the previous proposal payload).
-rw-r--r--src/libcharon/encoding/payloads/sa_payload.c24
1 files changed, 15 insertions, 9 deletions
diff --git a/src/libcharon/encoding/payloads/sa_payload.c b/src/libcharon/encoding/payloads/sa_payload.c
index 254916c55..18b1dc7b6 100644
--- a/src/libcharon/encoding/payloads/sa_payload.c
+++ b/src/libcharon/encoding/payloads/sa_payload.c
@@ -1,4 +1,5 @@
/*
+ * Copyright (C) 2012 Tobias Brunner
* Copyright (C) 2005-2010 Martin Willi
* Copyright (C) 2005 Jan Hutter
* Hochschule fuer Technik Rapperswil
@@ -292,20 +293,19 @@ METHOD(sa_payload_t, get_proposals, linked_list_t*,
int ignore_struct_number = 0;
enumerator_t *enumerator;
proposal_substructure_t *substruct;
- proposal_t *proposal;
- linked_list_t *list;
+ linked_list_t *substructs, *list;
if (this->type == SECURITY_ASSOCIATION_V1)
{ /* IKEv1 proposals start with 0 */
struct_number = ignore_struct_number = -1;
}
- list = linked_list_create();
/* we do not support proposals split up to two proposal substructures, as
* AH+ESP bundles are not supported in RFC4301 anymore.
* To handle such structures safely, we just skip proposals with multiple
* protocols.
*/
+ substructs = linked_list_create();
enumerator = this->proposals->create_enumerator(this->proposals);
while (enumerator->enumerate(enumerator, &substruct))
{
@@ -313,20 +313,26 @@ METHOD(sa_payload_t, get_proposals, linked_list_t*,
if (substruct->get_proposal_number(substruct) == struct_number)
{
if (ignore_struct_number < struct_number)
- {
- /* remove an already added, if first of series */
- if (list->remove_last(list, (void**)&proposal) == SUCCESS)
- {
- proposal->destroy(proposal);
- }
+ { /* remove an already added, if first of series */
+ substructs->remove_last(substructs, (void**)&substruct);
ignore_struct_number = struct_number;
}
continue;
}
struct_number++;
+ substructs->insert_last(substructs, substruct);
+ }
+ enumerator->destroy(enumerator);
+
+ /* generate proposals from substructs */
+ list = linked_list_create();
+ enumerator = substructs->create_enumerator(substructs);
+ while (enumerator->enumerate(enumerator, &substruct))
+ {
substruct->get_proposals(substruct, list);
}
enumerator->destroy(enumerator);
+ substructs->destroy(substructs);
return list;
}