peer-cfg: Consider security labels when selecting child configs

This commit is contained in:
Tobias Brunner
2022-04-14 18:42:01 +02:00
parent 63d4bd071f
commit 03729958db
4 changed files with 42 additions and 18 deletions
+31 -11
View File
@@ -386,13 +386,28 @@ METHOD(peer_cfg_t, create_child_cfg_enumerator, enumerator_t*,
/**
* Check how good a list of TS matches a given child config
*/
static int get_ts_match(child_cfg_t *cfg, bool local,
linked_list_t *sup_list, linked_list_t *hosts)
static u_int get_ts_match(child_cfg_t *cfg, bool local,
linked_list_t *sup_list, linked_list_t *hosts,
linked_list_t *sup_labels)
{
linked_list_t *cfg_list;
enumerator_t *sup_enum, *cfg_enum;
traffic_selector_t *sup_ts, *cfg_ts, *subset;
int match = 0, round;
sec_label_t *label;
u_int match = 0, round;
bool exact = FALSE;
if (cfg->select_label(cfg, sup_labels, TRUE, &label, &exact))
{
if (label)
{
match += exact ? 500 : 100;
}
}
else
{ /* label config doesn't match, no need to check TS */
return match;
}
/* fetch configured TS list, narrowing dynamic TS */
cfg_list = cfg->get_traffic_selectors(cfg, local, NULL, hosts, TRUE);
@@ -432,24 +447,29 @@ static int get_ts_match(child_cfg_t *cfg, bool local,
METHOD(peer_cfg_t, select_child_cfg, child_cfg_t*,
private_peer_cfg_t *this, linked_list_t *my_ts, linked_list_t *other_ts,
linked_list_t *my_hosts, linked_list_t *other_hosts)
linked_list_t *my_hosts, linked_list_t *other_hosts,
linked_list_t *my_labels, linked_list_t *other_labels)
{
child_cfg_t *current, *found = NULL;
enumerator_t *enumerator;
int best = 0;
u_int best = 0;
DBG2(DBG_CFG, "looking for a child config for %#R === %#R", my_ts, other_ts);
enumerator = create_child_cfg_enumerator(this);
while (enumerator->enumerate(enumerator, &current))
{
int my_prio, other_prio;
u_int my_prio, other_prio;
my_prio = get_ts_match(current, TRUE, my_ts, my_hosts);
other_prio = get_ts_match(current, FALSE, other_ts, other_hosts);
if (my_prio && other_prio)
my_prio = get_ts_match(current, TRUE, my_ts, my_hosts, my_labels);
if (!my_prio)
{
DBG2(DBG_CFG, " candidate \"%s\" with prio %d+%d",
continue;
}
other_prio = get_ts_match(current, FALSE, other_ts, other_hosts,
other_labels);
if (other_prio)
{
DBG2(DBG_CFG, " candidate \"%s\" with prio %u+%u",
current->get_name(current), my_prio, other_prio);
if (my_prio + other_prio > best)
{
+7 -4
View File
@@ -174,17 +174,20 @@ struct peer_cfg_t {
enumerator_t* (*create_child_cfg_enumerator) (peer_cfg_t *this);
/**
* Select a CHILD config from traffic selectors.
* Select a CHILD config from received traffic selectors.
*
* @param my_ts TS for local side
* @param other_ts TS for remote side
* @param my_hosts hosts to narrow down dynamic TS for local side
* @param other_hosts hosts to narrow down dynamic TS for remote side
* @return selected CHILD config, or NULL if no match found
* @param my_labels optional local security labels
* @param other_labels optional remove security labels
* @return selected CHILD config, or NULL if no match found
*/
child_cfg_t* (*select_child_cfg) (peer_cfg_t *this,
child_cfg_t* (*select_child_cfg)(peer_cfg_t *this,
linked_list_t *my_ts, linked_list_t *other_ts,
linked_list_t *my_hosts, linked_list_t *other_hosts);
linked_list_t *my_hosts, linked_list_t *other_hosts,
linked_list_t *my_labels, linked_list_t *other_labels);
/**
* Add an authentication config to the peer configuration.
+1 -1
View File
@@ -1096,7 +1096,7 @@ METHOD(task_t, process_r, status_t,
hostsi = get_dynamic_hosts(this->ike_sa, FALSE);
hostsr = get_dynamic_hosts(this->ike_sa, TRUE);
this->config = peer_cfg->select_child_cfg(peer_cfg, tsr, tsi,
hostsr, hostsi);
hostsr, hostsi, NULL, NULL);
hostsi->destroy(hostsi);
hostsr->destroy(hostsr);
if (this->config)
+3 -2
View File
@@ -1414,7 +1414,7 @@ static child_cfg_t* select_child_cfg(private_child_create_t *this)
listi = get_dynamic_hosts(this->ike_sa, FALSE);
child_cfg = peer_cfg->select_child_cfg(peer_cfg,
tsr ?: this->tsr, tsi ?: this->tsi,
listr, listi);
listr, listi, NULL, NULL);
if ((tsi || tsr) && child_cfg &&
child_cfg->get_mode(child_cfg) != MODE_TRANSPORT)
{
@@ -1426,7 +1426,8 @@ static child_cfg_t* select_child_cfg(private_child_create_t *this)
{
/* no match for the substituted NAT selectors, try it without */
child_cfg = peer_cfg->select_child_cfg(peer_cfg,
this->tsr, this->tsi, listr, listi);
this->tsr, this->tsi,
listr, listi, NULL, NULL);
}
listr->destroy(listr);
listi->destroy(listi);