Drop overlapping segments only if we have no active SAs on it
This commit is contained in:
committed by
Martin Willi
parent
a05e388540
commit
ea249cc6f0
@@ -322,25 +322,44 @@ static bool alert_hook(private_ha_segments_t *this, ike_sa_t *ike_sa,
|
|||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the number of SAs in a segment.
|
||||||
|
*/
|
||||||
|
static u_int get_sa_count(private_ha_segments_t *this)
|
||||||
|
{
|
||||||
|
enumerator_t *enumerator;
|
||||||
|
ike_sa_t *ike_sa;
|
||||||
|
u_int count = 0;
|
||||||
|
|
||||||
|
enumerator = charon->ike_sa_manager->create_enumerator(charon->ike_sa_manager);
|
||||||
|
while (enumerator->enumerate(enumerator, &ike_sa))
|
||||||
|
{
|
||||||
|
if (ike_sa->get_state(ike_sa) != IKE_ESTABLISHED)
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (this->tunnel && this->tunnel->is_sa(this->tunnel, ike_sa))
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
count++;
|
||||||
|
}
|
||||||
|
enumerator->destroy(enumerator);
|
||||||
|
return count;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Implementation of ha_segments_t.handle_status
|
* Implementation of ha_segments_t.handle_status
|
||||||
*/
|
*/
|
||||||
static void handle_status(private_ha_segments_t *this, segment_mask_t mask)
|
static void handle_status(private_ha_segments_t *this, segment_mask_t mask)
|
||||||
{
|
{
|
||||||
segment_mask_t missing, overlap;
|
segment_mask_t missing, overlap;
|
||||||
int i, active = 0;
|
int i;
|
||||||
|
|
||||||
this->mutex->lock(this->mutex);
|
this->mutex->lock(this->mutex);
|
||||||
|
|
||||||
missing = ~(this->active | mask);
|
missing = ~(this->active | mask);
|
||||||
overlap = this->active & mask;
|
overlap = this->active & mask;
|
||||||
for (i = 1; i <= this->count; i++)
|
|
||||||
{
|
|
||||||
if (this->active & SEGMENTS_BIT(i))
|
|
||||||
{
|
|
||||||
active++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Activate any missing segment. The master will disable overlapping
|
/* Activate any missing segment. The master will disable overlapping
|
||||||
* segments if both nodes activate the missing segments simultaneously. */
|
* segments if both nodes activate the missing segments simultaneously. */
|
||||||
@@ -359,16 +378,15 @@ static void handle_status(private_ha_segments_t *this, segment_mask_t mask)
|
|||||||
{
|
{
|
||||||
if (overlap & SEGMENTS_BIT(i))
|
if (overlap & SEGMENTS_BIT(i))
|
||||||
{
|
{
|
||||||
DBG1(DBG_CFG, "HA segment %d handled twice", i);
|
if (get_sa_count(this))
|
||||||
if (active > this->count)
|
|
||||||
{
|
{
|
||||||
enable_disable(this, i, FALSE, TRUE);
|
DBG1(DBG_CFG, "HA segment %d overlaps, taking over", i);
|
||||||
active--;
|
enable_disable(this, i, TRUE, TRUE);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
enable_disable(this, i, TRUE, TRUE);
|
DBG1(DBG_CFG, "HA segment %d overlaps, dropping", i);
|
||||||
active++;
|
enable_disable(this, i, FALSE, TRUE);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user