summaryrefslogtreecommitdiff
path: root/src/libstrongswan/credentials/sets/mem_cred.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/libstrongswan/credentials/sets/mem_cred.c')
-rw-r--r--src/libstrongswan/credentials/sets/mem_cred.c63
1 files changed, 58 insertions, 5 deletions
diff --git a/src/libstrongswan/credentials/sets/mem_cred.c b/src/libstrongswan/credentials/sets/mem_cred.c
index e023e8443..b8da3f620 100644
--- a/src/libstrongswan/credentials/sets/mem_cred.c
+++ b/src/libstrongswan/credentials/sets/mem_cred.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2010 Tobias Brunner
+ * Copyright (C) 2010-2013 Tobias Brunner
* Hochschule fuer Technik Rapperwsil
* Copyright (C) 2010 Martin Willi
* Copyright (C) 2010 revosec AG
@@ -18,7 +18,7 @@
#include "mem_cred.h"
#include <threading/rwlock.h>
-#include <utils/linked_list.h>
+#include <collections/linked_list.h>
typedef struct private_mem_cred_t private_mem_cred_t;
@@ -555,14 +555,66 @@ METHOD(credential_set_t, create_cdp_enumerator, enumerator_t*,
}
-METHOD(mem_cred_t, clear_secrets, void,
- private_mem_cred_t *this)
+static void reset_secrets(private_mem_cred_t *this)
{
- this->lock->write_lock(this->lock);
this->keys->destroy_offset(this->keys, offsetof(private_key_t, destroy));
this->shared->destroy_function(this->shared, (void*)shared_entry_destroy);
this->keys = linked_list_create();
this->shared = linked_list_create();
+}
+
+METHOD(mem_cred_t, replace_secrets, void,
+ private_mem_cred_t *this, mem_cred_t *other_set, bool clone)
+{
+ private_mem_cred_t *other = (private_mem_cred_t*)other_set;
+ enumerator_t *enumerator;
+ shared_entry_t *entry, *new_entry;
+ private_key_t *key;
+
+ this->lock->write_lock(this->lock);
+
+ reset_secrets(this);
+
+ if (clone)
+ {
+ enumerator = other->keys->create_enumerator(other->keys);
+ while (enumerator->enumerate(enumerator, &key))
+ {
+ this->keys->insert_last(this->keys, key->get_ref(key));
+ }
+ enumerator->destroy(enumerator);
+ enumerator = other->shared->create_enumerator(other->shared);
+ while (enumerator->enumerate(enumerator, &entry))
+ {
+ INIT(new_entry,
+ .shared = entry->shared->get_ref(entry->shared),
+ .owners = entry->owners->clone_offset(entry->owners,
+ offsetof(identification_t, clone)),
+ );
+ this->shared->insert_last(this->shared, new_entry);
+ }
+ enumerator->destroy(enumerator);
+ }
+ else
+ {
+ while (other->keys->remove_first(other->keys, (void**)&key) == SUCCESS)
+ {
+ this->keys->insert_last(this->keys, key);
+ }
+ while (other->shared->remove_first(other->shared,
+ (void**)&entry) == SUCCESS)
+ {
+ this->shared->insert_last(this->shared, entry);
+ }
+ }
+ this->lock->unlock(this->lock);
+}
+
+METHOD(mem_cred_t, clear_secrets, void,
+ private_mem_cred_t *this)
+{
+ this->lock->write_lock(this->lock);
+ reset_secrets(this);
this->lock->unlock(this->lock);
}
@@ -619,6 +671,7 @@ mem_cred_t *mem_cred_create()
.add_shared = _add_shared,
.add_shared_list = _add_shared_list,
.add_cdp = _add_cdp,
+ .replace_secrets = _replace_secrets,
.clear = _clear_,
.clear_secrets = _clear_secrets,
.destroy = _destroy,