Implemented table of half open IKE_SAs without linked_list_t.
This commit is contained in:
@@ -225,14 +225,6 @@ static void half_open_destroy(half_open_t *this)
|
|||||||
free(this);
|
free(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Function that matches half_open_t objects by the given IP address chunk.
|
|
||||||
*/
|
|
||||||
static bool half_open_match(half_open_t *half_open, chunk_t *addr)
|
|
||||||
{
|
|
||||||
return chunk_equals(*addr, half_open->other);
|
|
||||||
}
|
|
||||||
|
|
||||||
typedef struct connected_peers_t connected_peers_t;
|
typedef struct connected_peers_t connected_peers_t;
|
||||||
|
|
||||||
struct connected_peers_t {
|
struct connected_peers_t {
|
||||||
@@ -354,7 +346,7 @@ struct private_ike_sa_manager_t {
|
|||||||
/**
|
/**
|
||||||
* Hash table with half_open_t objects.
|
* Hash table with half_open_t objects.
|
||||||
*/
|
*/
|
||||||
linked_list_t **half_open_table;
|
table_item_t **half_open_table;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Segments of the "half-open" hash table.
|
* Segments of the "half-open" hash table.
|
||||||
@@ -730,44 +722,43 @@ static bool wait_for_entry(private_ike_sa_manager_t *this, entry_t *entry,
|
|||||||
*/
|
*/
|
||||||
static void put_half_open(private_ike_sa_manager_t *this, entry_t *entry)
|
static void put_half_open(private_ike_sa_manager_t *this, entry_t *entry)
|
||||||
{
|
{
|
||||||
half_open_t *half_open = NULL;
|
table_item_t *item;
|
||||||
linked_list_t *list;
|
|
||||||
chunk_t addr;
|
|
||||||
u_int row, segment;
|
u_int row, segment;
|
||||||
rwlock_t *lock;
|
rwlock_t *lock;
|
||||||
|
half_open_t *half_open;
|
||||||
|
chunk_t addr;
|
||||||
|
|
||||||
addr = entry->other->get_address(entry->other);
|
addr = entry->other->get_address(entry->other);
|
||||||
row = chunk_hash(addr) & this->table_mask;
|
row = chunk_hash(addr) & this->table_mask;
|
||||||
segment = row & this->segment_mask;
|
segment = row & this->segment_mask;
|
||||||
lock = this->half_open_segments[segment].lock;
|
lock = this->half_open_segments[segment].lock;
|
||||||
lock->write_lock(lock);
|
lock->write_lock(lock);
|
||||||
list = this->half_open_table[row];
|
item = this->half_open_table[row];
|
||||||
if (list)
|
while (item)
|
||||||
{
|
{
|
||||||
half_open_t *current;
|
half_open = item->value;
|
||||||
|
|
||||||
if (list->find_first(list, (linked_list_match_t)half_open_match,
|
if (chunk_equals(addr, half_open->other))
|
||||||
(void**)¤t, &addr) == SUCCESS)
|
|
||||||
{
|
{
|
||||||
half_open = current;
|
|
||||||
half_open->count++;
|
half_open->count++;
|
||||||
this->half_open_segments[segment].count++;
|
break;
|
||||||
}
|
}
|
||||||
}
|
item = item->next;
|
||||||
else
|
|
||||||
{
|
|
||||||
list = this->half_open_table[row] = linked_list_create();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!half_open)
|
if (!item)
|
||||||
{
|
{
|
||||||
INIT(half_open,
|
INIT(half_open,
|
||||||
.other = chunk_clone(addr),
|
.other = chunk_clone(addr),
|
||||||
.count = 1,
|
.count = 1,
|
||||||
);
|
);
|
||||||
list->insert_last(list, half_open);
|
INIT(item,
|
||||||
this->half_open_segments[segment].count++;
|
.value = half_open,
|
||||||
|
.next = this->half_open_table[row],
|
||||||
|
);
|
||||||
|
this->half_open_table[row] = item;
|
||||||
}
|
}
|
||||||
|
this->half_open_segments[segment].count++;
|
||||||
lock->unlock(lock);
|
lock->unlock(lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -776,37 +767,41 @@ static void put_half_open(private_ike_sa_manager_t *this, entry_t *entry)
|
|||||||
*/
|
*/
|
||||||
static void remove_half_open(private_ike_sa_manager_t *this, entry_t *entry)
|
static void remove_half_open(private_ike_sa_manager_t *this, entry_t *entry)
|
||||||
{
|
{
|
||||||
linked_list_t *list;
|
table_item_t *item, *prev = NULL;
|
||||||
chunk_t addr;
|
|
||||||
u_int row, segment;
|
u_int row, segment;
|
||||||
rwlock_t *lock;
|
rwlock_t *lock;
|
||||||
|
chunk_t addr;
|
||||||
|
|
||||||
addr = entry->other->get_address(entry->other);
|
addr = entry->other->get_address(entry->other);
|
||||||
row = chunk_hash(addr) & this->table_mask;
|
row = chunk_hash(addr) & this->table_mask;
|
||||||
segment = row & this->segment_mask;
|
segment = row & this->segment_mask;
|
||||||
lock = this->half_open_segments[segment].lock;
|
lock = this->half_open_segments[segment].lock;
|
||||||
lock->write_lock(lock);
|
lock->write_lock(lock);
|
||||||
list = this->half_open_table[row];
|
item = this->half_open_table[row];
|
||||||
if (list)
|
while (item)
|
||||||
{
|
{
|
||||||
half_open_t *current;
|
half_open_t *half_open = item->value;
|
||||||
enumerator_t *enumerator;
|
|
||||||
|
|
||||||
enumerator = list->create_enumerator(list);
|
if (chunk_equals(addr, half_open->other))
|
||||||
while (enumerator->enumerate(enumerator, ¤t))
|
|
||||||
{
|
{
|
||||||
if (half_open_match(current, &addr))
|
if (--half_open->count == 0)
|
||||||
{
|
{
|
||||||
if (--current->count == 0)
|
if (prev)
|
||||||
{
|
{
|
||||||
list->remove_at(list, enumerator);
|
prev->next = item->next;
|
||||||
half_open_destroy(current);
|
|
||||||
}
|
}
|
||||||
this->half_open_segments[segment].count--;
|
else
|
||||||
break;
|
{
|
||||||
|
this->half_open_table[row] = item->next;
|
||||||
|
}
|
||||||
|
half_open_destroy(half_open);
|
||||||
|
free(item);
|
||||||
}
|
}
|
||||||
|
this->half_open_segments[segment].count--;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
enumerator->destroy(enumerator);
|
prev = item;
|
||||||
|
item = item->next;
|
||||||
}
|
}
|
||||||
lock->unlock(lock);
|
lock->unlock(lock);
|
||||||
}
|
}
|
||||||
@@ -1739,8 +1734,8 @@ METHOD(ike_sa_manager_t, get_count, u_int,
|
|||||||
METHOD(ike_sa_manager_t, get_half_open_count, u_int,
|
METHOD(ike_sa_manager_t, get_half_open_count, u_int,
|
||||||
private_ike_sa_manager_t *this, host_t *ip)
|
private_ike_sa_manager_t *this, host_t *ip)
|
||||||
{
|
{
|
||||||
linked_list_t *list;
|
table_item_t *item;
|
||||||
u_int segment, row;
|
u_int row, segment;
|
||||||
rwlock_t *lock;
|
rwlock_t *lock;
|
||||||
chunk_t addr;
|
chunk_t addr;
|
||||||
u_int count = 0;
|
u_int count = 0;
|
||||||
@@ -1750,16 +1745,17 @@ METHOD(ike_sa_manager_t, get_half_open_count, u_int,
|
|||||||
addr = ip->get_address(ip);
|
addr = ip->get_address(ip);
|
||||||
row = chunk_hash(addr) & this->table_mask;
|
row = chunk_hash(addr) & this->table_mask;
|
||||||
segment = row & this->segment_mask;
|
segment = row & this->segment_mask;
|
||||||
lock = this->half_open_segments[segment & this->segment_mask].lock;
|
lock = this->half_open_segments[segment].lock;
|
||||||
lock->read_lock(lock);
|
lock->read_lock(lock);
|
||||||
if ((list = this->half_open_table[row]) != NULL)
|
item = this->half_open_table[row];
|
||||||
|
while (item)
|
||||||
{
|
{
|
||||||
half_open_t *current;
|
half_open_t *half_open = item->value;
|
||||||
|
|
||||||
if (list->find_first(list, (linked_list_match_t)half_open_match,
|
if (chunk_equals(addr, half_open->other))
|
||||||
(void**)¤t, &addr) == SUCCESS)
|
|
||||||
{
|
{
|
||||||
count = current->count;
|
count = half_open->count;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
lock->unlock(lock);
|
lock->unlock(lock);
|
||||||
@@ -1768,7 +1764,7 @@ METHOD(ike_sa_manager_t, get_half_open_count, u_int,
|
|||||||
{
|
{
|
||||||
for (segment = 0; segment < this->segment_count; segment++)
|
for (segment = 0; segment < this->segment_count; segment++)
|
||||||
{
|
{
|
||||||
lock = this->half_open_segments[segment & this->segment_mask].lock;
|
lock = this->half_open_segments[segment].lock;
|
||||||
lock->read_lock(lock);
|
lock->read_lock(lock);
|
||||||
count += this->half_open_segments[segment].count;
|
count += this->half_open_segments[segment].count;
|
||||||
lock->unlock(lock);
|
lock->unlock(lock);
|
||||||
@@ -1872,7 +1868,6 @@ METHOD(ike_sa_manager_t, destroy, void,
|
|||||||
|
|
||||||
for (i = 0; i < this->table_size; i++)
|
for (i = 0; i < this->table_size; i++)
|
||||||
{
|
{
|
||||||
DESTROY_IF(this->half_open_table[i]);
|
|
||||||
DESTROY_IF(this->connected_peers_table[i]);
|
DESTROY_IF(this->connected_peers_table[i]);
|
||||||
DESTROY_IF(this->init_hashes_table[i]);
|
DESTROY_IF(this->init_hashes_table[i]);
|
||||||
}
|
}
|
||||||
@@ -1977,7 +1972,7 @@ ike_sa_manager_t *ike_sa_manager_create()
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* we use the same table parameters for the table to track half-open SAs */
|
/* we use the same table parameters for the table to track half-open SAs */
|
||||||
this->half_open_table = calloc(this->table_size, sizeof(linked_list_t*));
|
this->half_open_table = calloc(this->table_size, sizeof(table_item_t*));
|
||||||
this->half_open_segments = calloc(this->segment_count, sizeof(shareable_segment_t));
|
this->half_open_segments = calloc(this->segment_count, sizeof(shareable_segment_t));
|
||||||
for (i = 0; i < this->segment_count; i++)
|
for (i = 0; i < this->segment_count; i++)
|
||||||
{
|
{
|
||||||
|
|||||||
Reference in New Issue
Block a user