Merge pull request #133 from ifupdown-ng/feature/smart-stanza-merging
improve stanza merging by rewriting address properties as CIDR
This commit is contained in:
commit
3d47b34d7a
5 changed files with 87 additions and 9 deletions
|
@ -263,6 +263,12 @@ handle_iface(struct lif_interface_file_parse_state *state, char *token, char *bu
|
|||
return true;
|
||||
}
|
||||
|
||||
/* if we have a current interface, call lif_interface_finalize to finalize any
|
||||
* address properties by converting them to CIDR and flushing the netmask property.
|
||||
*/
|
||||
if (state->cur_iface != NULL)
|
||||
lif_interface_finalize(state->cur_iface);
|
||||
|
||||
state->cur_iface = lif_interface_collection_find(state->collection, ifname);
|
||||
if (state->cur_iface == NULL)
|
||||
{
|
||||
|
@ -501,6 +507,11 @@ lif_interface_file_parse(struct lif_interface_file_parse_state *state, const cha
|
|||
}
|
||||
|
||||
fclose(f);
|
||||
|
||||
/* finalize any open interface */
|
||||
if (state->cur_iface != NULL)
|
||||
lif_interface_finalize(state->cur_iface);
|
||||
|
||||
state->cur_filename = old_filename;
|
||||
state->cur_lineno = old_lineno;
|
||||
return true;
|
||||
|
|
|
@ -84,6 +84,19 @@ count_set_bits(const char *netmask)
|
|||
return r;
|
||||
}
|
||||
|
||||
static inline size_t
|
||||
determine_interface_netmask(const struct lif_interface *iface, const struct lif_address *addr)
|
||||
{
|
||||
/* if netmask is not set, default to /24 or /64, ifupdown does so too */
|
||||
size_t netmask = addr->domain == AF_INET6 ? 64 : 24;
|
||||
|
||||
struct lif_dict_entry *entry = lif_dict_find(&iface->vars, "netmask");
|
||||
if (entry != NULL)
|
||||
netmask = count_set_bits(entry->data);
|
||||
|
||||
return netmask;
|
||||
}
|
||||
|
||||
bool
|
||||
lif_address_format_cidr(const struct lif_interface *iface, struct lif_dict_entry *entry, char *buf, size_t buflen)
|
||||
{
|
||||
|
@ -91,14 +104,7 @@ lif_address_format_cidr(const struct lif_interface *iface, struct lif_dict_entry
|
|||
size_t orig_netmask = addr->netmask;
|
||||
|
||||
if (!addr->netmask)
|
||||
{
|
||||
/* if netmask is not set, default to 255.255.255.0, ifupdown does so too */
|
||||
addr->netmask = addr->domain == AF_INET6 ? 64 : 24;
|
||||
|
||||
struct lif_dict_entry *entry = lif_dict_find(&iface->vars, "netmask");
|
||||
if (entry != NULL)
|
||||
addr->netmask = count_set_bits(entry->data);
|
||||
}
|
||||
addr->netmask = determine_interface_netmask(iface, addr);
|
||||
|
||||
if (!lif_address_unparse(addr, buf, buflen, true))
|
||||
{
|
||||
|
@ -213,6 +219,36 @@ lif_interface_use_executor(struct lif_interface *interface, const char *executor
|
|||
lif_dict_add(&interface->vars, "hostname", strdup(un.nodename));
|
||||
}
|
||||
|
||||
void
|
||||
lif_interface_finalize(struct lif_interface *interface)
|
||||
{
|
||||
struct lif_node *iter;
|
||||
|
||||
/* convert all addresses to CIDR notation. */
|
||||
LIF_DICT_FOREACH(iter, &interface->vars)
|
||||
{
|
||||
struct lif_dict_entry *entry = iter->data;
|
||||
|
||||
if (strcmp(entry->key, "address"))
|
||||
continue;
|
||||
|
||||
struct lif_address *addr = entry->data;
|
||||
|
||||
if (!addr->netmask)
|
||||
addr->netmask = determine_interface_netmask(interface, addr);
|
||||
}
|
||||
|
||||
/* with all addresses converted to CIDR, netmask property is no longer needed. */
|
||||
struct lif_dict_entry *entry = lif_dict_find(&interface->vars, "netmask");
|
||||
|
||||
if (entry != NULL)
|
||||
{
|
||||
free(entry->data);
|
||||
|
||||
lif_dict_delete_entry(&interface->vars, entry);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
lif_interface_collection_init(struct lif_dict *collection)
|
||||
{
|
||||
|
|
|
@ -75,6 +75,7 @@ extern bool lif_interface_address_add(struct lif_interface *interface, const cha
|
|||
extern void lif_interface_address_delete(struct lif_interface *interface, const char *address);
|
||||
extern void lif_interface_fini(struct lif_interface *interface);
|
||||
extern void lif_interface_use_executor(struct lif_interface *interface, const char *executor);
|
||||
extern void lif_interface_finalize(struct lif_interface *interface);
|
||||
|
||||
extern void lif_interface_collection_init(struct lif_dict *collection);
|
||||
extern void lif_interface_collection_fini(struct lif_dict *collection);
|
||||
|
|
14
tests/fixtures/stanza-merging.interfaces
vendored
Normal file
14
tests/fixtures/stanza-merging.interfaces
vendored
Normal file
|
@ -0,0 +1,14 @@
|
|||
# cidr and without-cidr should be equivalent
|
||||
iface cidr
|
||||
address 203.0.113.1/32
|
||||
|
||||
iface cidr
|
||||
address 203.0.113.2/24
|
||||
|
||||
iface without-cidr
|
||||
address 203.0.113.1
|
||||
netmask 32
|
||||
|
||||
iface without-cidr
|
||||
address 203.0.113.2
|
||||
netmask 24
|
|
@ -38,7 +38,9 @@ tests_init \
|
|||
allow_undefined_positive \
|
||||
allow_undefined_negative \
|
||||
default_netmask_v4 \
|
||||
default_netmask_v6
|
||||
default_netmask_v6 \
|
||||
stanza_merging_with_cidr \
|
||||
stanza_merging_without_cidr
|
||||
|
||||
noargs_body() {
|
||||
atf_check -s exit:1 -e ignore ifquery -S/dev/null
|
||||
|
@ -256,3 +258,17 @@ default_netmask_v6_body() {
|
|||
-o match:"2001:470:1f10::1/64" \
|
||||
ifquery -i $FIXTURES/without-netmask.interfaces -p address v6
|
||||
}
|
||||
|
||||
stanza_merging_with_cidr_body() {
|
||||
atf_check -s exit:0 \
|
||||
-o match:"203.0.113.1/32" \
|
||||
-o match:"203.0.113.2/24" \
|
||||
ifquery -i $FIXTURES/stanza-merging.interfaces -p address cidr
|
||||
}
|
||||
|
||||
stanza_merging_without_cidr_body() {
|
||||
atf_check -s exit:0 \
|
||||
-o match:"203.0.113.1/32" \
|
||||
-o match:"203.0.113.2/24" \
|
||||
ifquery -i $FIXTURES/stanza-merging.interfaces -p address without-cidr
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue