nonceg: Insert id mapping when allocating nonce
[strongswan.git] / src / charon-tkm / src / tkm / tkm_chunk_map.c
1 /*
2 * Copyright (C) 2012 Reto Buerki
3 * Copyright (C) 2012 Adrian-Ken Rueegsegger
4 * Hochschule fuer Technik Rapperswil
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License as published by the
8 * Free Software Foundation; either version 2 of the License, or (at your
9 * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>.
10 *
11 * This program is distributed in the hope that it will be useful, but
12 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
13 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * for more details.
15 */
16
17 #include <collections/hashtable.h>
18 #include <threading/rwlock.h>
19 #include <utils/chunk.h>
20 #include <utils/debug.h>
21
22 #include "tkm_chunk_map.h"
23
24 typedef struct private_tkm_chunk_map_t private_tkm_chunk_map_t;
25
26 /**
27 * Private data of tkm chunk map.
28 */
29 struct private_tkm_chunk_map_t {
30
31 /**
32 * public functions
33 */
34 tkm_chunk_map_t public;
35
36 /**
37 * Hashtable to store mappings.
38 */
39 hashtable_t *mappings;
40
41 /**
42 * rwlock for table.
43 */
44 rwlock_t *lock;
45
46 };
47
48 METHOD(tkm_chunk_map_t, insert, void,
49 private_tkm_chunk_map_t * const this, const chunk_t * const data,
50 const uint64_t id)
51 {
52 uint64_t *value = malloc_thing(uint64_t);
53 *value = id;
54
55 this->lock->write_lock(this->lock);
56 value = this->mappings->put(this->mappings, (void*)data, value);
57 this->lock->unlock(this->lock);
58
59 if (value)
60 {
61 free(value);
62 }
63 }
64
65 METHOD(tkm_chunk_map_t, get_id, uint64_t,
66 private_tkm_chunk_map_t * const this, chunk_t *data)
67 {
68 uint64_t *value;
69 this->lock->read_lock(this->lock);
70 value = this->mappings->get(this->mappings, data);
71 this->lock->unlock(this->lock);
72
73 return value == NULL ? 0 : *value;
74 }
75
76 METHOD(tkm_chunk_map_t, remove_, bool,
77 private_tkm_chunk_map_t * const this, chunk_t *data)
78 {
79 this->lock->write_lock(this->lock);
80 uint64_t *value = this->mappings->remove(this->mappings, data);
81 this->lock->unlock(this->lock);
82
83 if (value)
84 {
85 free(value);
86 return TRUE;
87 }
88 else
89 {
90 return FALSE;
91 }
92 }
93
94 METHOD(tkm_chunk_map_t, destroy, void,
95 private_tkm_chunk_map_t *this)
96 {
97 uint64_t *value;
98 enumerator_t *enumerator;
99
100 this->lock->write_lock(this->lock);
101 enumerator = this->mappings->create_enumerator(this->mappings);
102 while (enumerator->enumerate(enumerator, NULL, &value))
103 {
104 this->mappings->remove_at(this->mappings, enumerator);
105 free(value);
106 }
107 enumerator->destroy(enumerator);
108 this->lock->unlock(this->lock);
109
110 this->lock->destroy(this->lock);
111 this->mappings->destroy(this->mappings);
112 free(this);
113 }
114
115 /**
116 * Hashtable hash function.
117 */
118 static u_int hash(chunk_t *key)
119 {
120 return chunk_hash(*key);
121 }
122
123 /*
124 * see header file
125 */
126 tkm_chunk_map_t *tkm_chunk_map_create()
127 {
128 private_tkm_chunk_map_t *this;
129
130 INIT(this,
131 .public = {
132 .insert = _insert,
133 .get_id = _get_id,
134 .remove = _remove_,
135 .destroy = _destroy,
136 },
137 .lock = rwlock_create(RWLOCK_TYPE_DEFAULT),
138 .mappings = hashtable_create((hashtable_hash_t)hash,
139 (hashtable_equals_t)chunk_equals_ptr, 32),
140 );
141
142 return &this->public;
143 }