* Fix:
+ Do not break zero-copy traffic on Linux (#732 and #733)
+ Fix crash on rapid addition/removal of interfaces (#744)
+ + Fix management address selection when pattern is a negative IP address
lldpd (1.0.19)
* Changes:
#undef IN6_IS_ADDR_GLOBAL
#define IN6_IS_ADDR_GLOBAL(a) (!IN6_IS_ADDR_LOOPBACK(a) && !IN6_IS_ADDR_LINKLOCAL(a))
+static int
+interfaces_allowed_mgt(struct lldpd *cfg, struct interfaces_device_list *interfaces,
+ struct interfaces_address *addr, char *addrstrbuf, int allnegative)
+{
+ struct interfaces_device *device;
+ int addr_match, device_match;
+ if (cfg->g_config.c_mgmt_pattern == NULL) {
+ return 1;
+ }
+ device = interfaces_indextointerface(interfaces, addr->index);
+ if (allnegative) {
+ addr_match = pattern_match(addrstrbuf, cfg->g_config.c_mgmt_pattern, PATTERN_MATCH_ALLOWED);
+ device_match = device && pattern_match(device->name, cfg->g_config.c_mgmt_pattern, PATTERN_MATCH_ALLOWED);
+ return addr_match && device_match;
+ }
+ addr_match = pattern_match(addrstrbuf, cfg->g_config.c_mgmt_pattern, PATTERN_MATCH_DENIED);
+ device_match = device && pattern_match(device->name, cfg->g_config.c_mgmt_pattern, PATTERN_MATCH_DENIED);
+ return addr_match || device_match;
+}
+
/* Add management addresses for the given family. We only take one of each
address family, unless a pattern is provided and is not all negative. For
- example !*:*,!10.* will only deny addresses. We will pick the first IPv4
+ example !*:*,!10.* will only deny IPv6 addresses. We will pick the first IPv4
address not matching 10.*.
*/
static int
int global, int allnegative)
{
struct interfaces_address *addr;
- struct interfaces_device *device;
struct lldpd_mgmt *mgmt;
char addrstrbuf[INET6_ADDRSTRLEN];
int found = 0;
"unable to convert IP address to a string");
continue;
}
- if (cfg->g_config.c_mgmt_pattern == NULL ||
- /* Match on IP address */
- pattern_match(addrstrbuf, cfg->g_config.c_mgmt_pattern,
- allnegative) ||
- /* Match on interface name */
- ((device = interfaces_indextointerface(interfaces, addr->index)) &&
- pattern_match(device->name, cfg->g_config.c_mgmt_pattern,
- allnegative))) {
+ if (interfaces_allowed_mgt(cfg, interfaces, addr, addrstrbuf, allnegative)) {
mgmt =
lldpd_alloc_mgmt(af, &in_addr, in_addr_size, addr->index);
if (mgmt == NULL) {
* case, it is allowed back. Each pattern will then be
* matched against `fnmatch()` function.
* @param found Value to return if the pattern isn't found. Should be either
- * PATTERN_MATCH_DENIED or PATTERN_MACTH_DENIED.
+ * PATTERN_MATCH_ALLOWED or PATTERN_MACTH_DENIED.
*
* If a pattern is found matching and denied at the same time, it
* will be denied. If it is both allowed and denied, it
assert out["lldp.eth0.chassis.mgmt-iface"] == "2"
+def test_negative_management_address(lldpd1, lldpd, lldpcli, links, namespaces):
+ with namespaces(2):
+ with pyroute2.IPRoute() as ipr:
+ idx = ipr.link_lookup(ifname="eth1")[0]
+ ipr.addr("add", index=idx, address="192.168.14.2", prefixlen=24)
+ ipr.addr("add", index=idx, address="172.25.21.47", prefixlen=24)
+ lldpd("-m", "!192.168.14.2,!*:*")
+ with namespaces(1):
+ out = lldpcli("-f", "keyvalue", "show", "neighbors")
+ assert out["lldp.eth0.chassis.mgmt-ip"] == "172.25.21.47"
+ assert out["lldp.eth0.chassis.mgmt-iface"] == "2"
+
+
+def test_negative_unknown_management_address(lldpd1, lldpd, lldpcli, namespaces):
+ with namespaces(2):
+ with pyroute2.IPRoute() as ipr:
+ idx = ipr.link_lookup(ifname="eth1")[0]
+ ipr.addr("add", index=idx, address="192.168.14.2", prefixlen=24)
+ ipr.addr("add", index=idx, address="172.25.21.47", prefixlen=24)
+ lldpd("-m", "!192.168.14.2,!*:*,192.0.2.15")
+ with namespaces(1):
+ out = lldpcli("-f", "keyvalue", "show", "neighbors")
+ assert "lldp.eth0.chassis.mgmt-ip" not in out
+ assert "lldp.eth0.chassis.mgmt-iface" not in out
+
+
def test_management_interface(lldpd1, lldpd, lldpcli, links, namespaces):
links(namespaces(1), namespaces(2), 4)
with namespaces(2):