summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLennart Poettering <lennart@poettering.net>2016-02-19 20:43:03 +0100
committerLennart Poettering <lennart@poettering.net>2016-02-21 20:40:57 +0100
commitb295beea88a7f2c48897b2887acbe99937335c8f (patch)
tree944f3498c7e8aaa35a5010910987100033b39992
parent7cececb2ea707a6d9b063538cf986fd27edd8cd3 (diff)
networkd: rework how carrier bindings are serialized
Instead of serializing the interface name, expose the interface index, since that's the only stable identifier.
-rw-r--r--src/libsystemd/sd-network/sd-network.c62
-rw-r--r--src/network/networkctl.c31
-rw-r--r--src/network/networkd-link.c52
-rw-r--r--src/systemd/sd-network.h10
4 files changed, 117 insertions, 38 deletions
diff --git a/src/libsystemd/sd-network/sd-network.c b/src/libsystemd/sd-network/sd-network.c
index 26b283f60d..037ffb6e75 100644
--- a/src/libsystemd/sd-network/sd-network.c
+++ b/src/libsystemd/sd-network/sd-network.c
@@ -207,12 +207,66 @@ _public_ int sd_network_link_get_route_domains(int ifindex, char ***ret) {
return network_link_get_strv(ifindex, "ROUTE_DOMAINS", ret);
}
-_public_ int sd_network_link_get_carrier_bound_to(int ifindex, char ***ret) {
- return network_link_get_strv(ifindex, "CARRIER_BOUND_TO", ret);
+static int network_link_get_ifindexes(int ifindex, const char *key, int **ret) {
+ _cleanup_free_ char *p = NULL, *s = NULL;
+ _cleanup_strv_free_ char **a = NULL;
+ _cleanup_free_ int *ifis = NULL;
+ size_t allocated = 0, c = 0;
+ const char *x;
+ int r;
+
+ assert_return(ifindex > 0, -EINVAL);
+ assert_return(ret, -EINVAL);
+
+ if (asprintf(&p, "/run/systemd/netif/links/%d", ifindex) < 0)
+ return -ENOMEM;
+
+ r = parse_env_file(p, NEWLINE, key, &s, NULL);
+ if (r == -ENOENT)
+ return -ENODATA;
+ if (r < 0)
+ return r;
+ if (isempty(s)) {
+ *ret = NULL;
+ return 0;
+ }
+
+ x = s;
+ for (;;) {
+ _cleanup_free_ char *word = NULL;
+
+ r = extract_first_word(&x, &word, NULL, 0);
+ if (r < 0)
+ return r;
+ if (r == 0)
+ break;
+
+ r = parse_ifindex(word, &ifindex);
+ if (r < 0)
+ return r;
+
+ if (!GREEDY_REALLOC(ifis, allocated, c + 1))
+ return -ENOMEM;
+
+ ifis[c++] = ifindex;
+ }
+
+ if (!GREEDY_REALLOC(ifis, allocated, c + 1))
+ return -ENOMEM;
+ ifis[c] = 0; /* Let's add a 0 ifindex to the end, to be nice*/
+
+ *ret = ifis;
+ ifis = NULL;
+
+ return c;
+}
+
+_public_ int sd_network_link_get_carrier_bound_to(int ifindex, int **ret) {
+ return network_link_get_ifindexes(ifindex, "CARRIER_BOUND_TO", ret);
}
-_public_ int sd_network_link_get_carrier_bound_by(int ifindex, char ***ret) {
- return network_link_get_strv(ifindex, "CARRIER_BOUND_BY", ret);
+_public_ int sd_network_link_get_carrier_bound_by(int ifindex, int **ret) {
+ return network_link_get_ifindexes(ifindex, "CARRIER_BOUND_BY", ret);
}
static inline int MONITOR_TO_FD(sd_network_monitor *m) {
diff --git a/src/network/networkctl.c b/src/network/networkctl.c
index c5da24e75b..8abb1eff9a 100644
--- a/src/network/networkctl.c
+++ b/src/network/networkctl.c
@@ -662,6 +662,30 @@ static int dump_lldp_neighbors(const char *prefix, int ifindex) {
return c;
}
+static void dump_ifindexes(const char *prefix, const int *ifindexes) {
+ unsigned c;
+
+ assert(prefix);
+
+ if (!ifindexes || ifindexes[0] <= 0)
+ return;
+
+ for (c = 0; ifindexes[c] > 0; c++) {
+ char name[IF_NAMESIZE+1];
+
+ printf("%*s",
+ (int) strlen(prefix),
+ c == 0 ? prefix : "");
+
+ if (if_indextoname(ifindexes[c], name))
+ fputs(name, stdout);
+ else
+ printf("%i", ifindexes[c]);
+
+ fputc('\n', stdout);
+ }
+}
+
static void dump_list(const char *prefix, char **l) {
char **i;
@@ -689,8 +713,7 @@ static int link_status_one(
const char *driver = NULL, *path = NULL, *vendor = NULL, *model = NULL, *link = NULL;
const char *on_color_operational, *off_color_operational,
*on_color_setup, *off_color_setup;
- _cleanup_strv_free_ char **carrier_bound_to = NULL;
- _cleanup_strv_free_ char **carrier_bound_by = NULL;
+ _cleanup_free_ int *carrier_bound_to = NULL, *carrier_bound_by = NULL;
int r;
assert(rtnl);
@@ -777,8 +800,8 @@ static int link_status_one(
dump_list(" NTP: ", ntp);
- dump_list("Carrier Bound To: ", carrier_bound_to);
- dump_list("Carrier Bound By: ", carrier_bound_by);
+ dump_ifindexes("Carrier Bound To: ", carrier_bound_to);
+ dump_ifindexes("Carrier Bound By: ", carrier_bound_by);
(void) sd_network_link_get_timezone(info->ifindex, &tz);
if (tz)
diff --git a/src/network/networkd-link.c b/src/network/networkd-link.c
index 02fb04e0cb..32437d2195 100644
--- a/src/network/networkd-link.c
+++ b/src/network/networkd-link.c
@@ -1622,7 +1622,7 @@ static int link_new_bound_by_list(Link *link) {
m = link->manager;
- HASHMAP_FOREACH (carrier, m->links, i) {
+ HASHMAP_FOREACH(carrier, m->links, i) {
if (!carrier->network)
continue;
@@ -1641,7 +1641,7 @@ static int link_new_bound_by_list(Link *link) {
if (list_updated)
link_dirty(link);
- HASHMAP_FOREACH (carrier, link->bound_by_links, i) {
+ HASHMAP_FOREACH(carrier, link->bound_by_links, i) {
r = link_put_carrier(carrier, link, &carrier->bound_to_links);
if (r < 0)
return r;
@@ -2631,7 +2631,6 @@ int link_carrier_reset(Link *link) {
return 0;
}
-
int link_update(Link *link, sd_netlink_message *m) {
struct ether_addr mac;
const char *ifname;
@@ -2752,12 +2751,34 @@ int link_update(Link *link, sd_netlink_message *m) {
r = link_carrier_lost(link);
if (r < 0)
return r;
-
}
return 0;
}
+static void print_link_hashmap(FILE *f, const char *prefix, Hashmap* h) {
+ bool space = false;
+ Iterator i;
+ Link *link;
+
+ assert(f);
+ assert(prefix);
+
+ if (hashmap_isempty(h))
+ return;
+
+ fputs(prefix, f);
+ HASHMAP_FOREACH(link, h, i) {
+ if (space)
+ fputc(' ', f);
+
+ fprintf(f, "%i", link->ifindex);
+ space = true;
+ }
+
+ fputc('\n', f);
+}
+
int link_save(Link *link) {
_cleanup_free_ char *temp_path = NULL;
_cleanup_fclose_ FILE *f = NULL;
@@ -2958,27 +2979,8 @@ int link_save(Link *link) {
fputc('\n', f);
}
- if (!hashmap_isempty(link->bound_to_links)) {
- Link *carrier;
- bool space = false;
-
- fputs("CARRIER_BOUND_TO=", f);
- HASHMAP_FOREACH(carrier, link->bound_to_links, i)
- fputs_with_space(f, carrier->ifname, NULL, &space);
-
- fputc('\n', f);
- }
-
- if (!hashmap_isempty(link->bound_by_links)) {
- Link *carrier;
- bool space = false;
-
- fputs("CARRIER_BOUND_BY=", f);
- HASHMAP_FOREACH(carrier, link->bound_by_links, i)
- fputs_with_space(f, carrier->ifname, NULL, &space);
-
- fputc('\n', f);
- }
+ print_link_hashmap(f, "CARRIER_BOUND_TO=", link->bound_to_links);
+ print_link_hashmap(f, "CARRIER_BOUND_BY=", link->bound_by_links);
if (link->dhcp_lease) {
struct in_addr address;
diff --git a/src/systemd/sd-network.h b/src/systemd/sd-network.h
index 56986c984d..0f13e2bae7 100644
--- a/src/systemd/sd-network.h
+++ b/src/systemd/sd-network.h
@@ -99,11 +99,11 @@ int sd_network_link_get_network_file(int ifindex, char **filename);
/* Get DNS entries for a given link. These are string representations of
* IP addresses */
-int sd_network_link_get_dns(int ifindex, char ***addr);
+int sd_network_link_get_dns(int ifindex, char ***ret);
/* Get NTP entries for a given link. These are domain names or string
* representations of IP addresses */
-int sd_network_link_get_ntp(int ifindex, char ***addr);
+int sd_network_link_get_ntp(int ifindex, char ***ret);
/* Indicates whether or not LLMNR should be enabled for the link
* Possible levels of support: yes, no, resolve
@@ -139,11 +139,11 @@ int sd_network_link_get_search_domains(int ifindex, char ***domains);
/* Get the route DNS domain names for a given link. */
int sd_network_link_get_route_domains(int ifindex, char ***domains);
-/* Get the CARRIERS to which current link is bound to. */
-int sd_network_link_get_carrier_bound_to(int ifindex, char ***carriers);
+/* Get the carrier interface indexes to which current link is bound to. */
+int sd_network_link_get_carrier_bound_to(int ifindex, int **ifindexes);
/* Get the CARRIERS that are bound to current link. */
-int sd_network_link_get_carrier_bound_by(int ifindex, char ***carriers);
+int sd_network_link_get_carrier_bound_by(int ifindex, int **ifindexes);
/* Get the timezone that was learnt on a specific link. */
int sd_network_link_get_timezone(int ifindex, char **timezone);