summaryrefslogtreecommitdiff
path: root/src/systemd/src/libsystemd-network
diff options
context:
space:
mode:
authorThomas Haller <thaller@redhat.com>2016-06-29 22:38:50 +0200
committerThomas Haller <thaller@redhat.com>2016-06-30 09:27:06 +0200
commit21e3aa91d85cd5eab7d35d667bb0ec0277102818 (patch)
tree0ffecd435bd158f094d4a8aa08780d89e5ec4ca2 /src/systemd/src/libsystemd-network
parent3fd08cdce5a5d641c21b8e6a9125efd36777b925 (diff)
downloadNetworkManager-21e3aa91d85cd5eab7d35d667bb0ec0277102818.tar.gz
systemd: update code from upstream
This is a direct dump from systemd git on 2016-06-29, git commit 2e0d8df13b1c1deda7b5769accae9e6cd5bf5966. ====== SYSTEMD_DIR=../systemd COMMIT=2e0d8df13b1c1deda7b5769accae9e6cd5bf5966 ( cd "$SYSTEMD_DIR" git checkout "$COMMIT" git reset --hard git clean -fdx ) git ls-files :/src/systemd/src/ | xargs -d '\n' rm -f nm_copy_sd() { mkdir -p "./src/systemd/$(dirname "$1")" cp "$SYSTEMD_DIR/$1" "./src/systemd/$1" } nm_copy_sd "src/basic/alloc-util.c" nm_copy_sd "src/basic/alloc-util.h" nm_copy_sd "src/basic/async.h" nm_copy_sd "src/basic/escape.c" nm_copy_sd "src/basic/escape.h" nm_copy_sd "src/basic/ether-addr-util.c" nm_copy_sd "src/basic/ether-addr-util.h" nm_copy_sd "src/basic/extract-word.c" nm_copy_sd "src/basic/extract-word.h" nm_copy_sd "src/basic/fileio.c" nm_copy_sd "src/basic/fileio.h" nm_copy_sd "src/basic/fd-util.c" nm_copy_sd "src/basic/fd-util.h" nm_copy_sd "src/basic/fs-util.c" nm_copy_sd "src/basic/fs-util.h" nm_copy_sd "src/basic/hash-funcs.c" nm_copy_sd "src/basic/hash-funcs.h" nm_copy_sd "src/basic/hashmap.c" nm_copy_sd "src/basic/hashmap.h" nm_copy_sd "src/basic/hexdecoct.c" nm_copy_sd "src/basic/hexdecoct.h" nm_copy_sd "src/basic/hostname-util.c" nm_copy_sd "src/basic/hostname-util.h" nm_copy_sd "src/basic/in-addr-util.c" nm_copy_sd "src/basic/in-addr-util.h" nm_copy_sd "src/basic/io-util.c" nm_copy_sd "src/basic/io-util.h" nm_copy_sd "src/basic/list.h" nm_copy_sd "src/basic/log.h" nm_copy_sd "src/basic/macro.h" nm_copy_sd "src/basic/mempool.h" nm_copy_sd "src/basic/mempool.c" nm_copy_sd "src/basic/parse-util.c" nm_copy_sd "src/basic/parse-util.h" nm_copy_sd "src/basic/path-util.c" nm_copy_sd "src/basic/path-util.h" nm_copy_sd "src/basic/prioq.h" nm_copy_sd "src/basic/prioq.c" nm_copy_sd "src/basic/random-util.c" nm_copy_sd "src/basic/random-util.h" nm_copy_sd "src/basic/refcnt.h" nm_copy_sd "src/basic/set.h" nm_copy_sd "src/basic/signal-util.h" nm_copy_sd "src/basic/siphash24.c" nm_copy_sd "src/basic/siphash24.h" nm_copy_sd "src/basic/socket-util.c" nm_copy_sd "src/basic/socket-util.h" nm_copy_sd "src/basic/sparse-endian.h" nm_copy_sd "src/basic/stdio-util.h" nm_copy_sd "src/basic/string-table.c" nm_copy_sd "src/basic/string-table.h" nm_copy_sd "src/basic/string-util.c" nm_copy_sd "src/basic/string-util.h" nm_copy_sd "src/basic/strv.c" nm_copy_sd "src/basic/strv.h" nm_copy_sd "src/basic/time-util.c" nm_copy_sd "src/basic/time-util.h" nm_copy_sd "src/basic/umask-util.h" nm_copy_sd "src/basic/unaligned.h" nm_copy_sd "src/basic/utf8.c" nm_copy_sd "src/basic/utf8.h" nm_copy_sd "src/basic/util.c" nm_copy_sd "src/basic/util.h" nm_copy_sd "src/libsystemd-network/arp-util.c" nm_copy_sd "src/libsystemd-network/arp-util.h" nm_copy_sd "src/libsystemd-network/dhcp6-internal.h" nm_copy_sd "src/libsystemd-network/dhcp6-lease-internal.h" nm_copy_sd "src/libsystemd-network/dhcp6-network.c" nm_copy_sd "src/libsystemd-network/dhcp6-option.c" nm_copy_sd "src/libsystemd-network/dhcp6-protocol.h" nm_copy_sd "src/libsystemd-network/dhcp-identifier.c" nm_copy_sd "src/libsystemd-network/dhcp-identifier.h" nm_copy_sd "src/libsystemd-network/dhcp-internal.h" nm_copy_sd "src/libsystemd-network/dhcp-lease-internal.h" nm_copy_sd "src/libsystemd-network/dhcp-network.c" nm_copy_sd "src/libsystemd-network/dhcp-option.c" nm_copy_sd "src/libsystemd-network/dhcp-packet.c" nm_copy_sd "src/libsystemd-network/dhcp-protocol.h" nm_copy_sd "src/libsystemd-network/lldp-internal.h" nm_copy_sd "src/libsystemd-network/lldp-neighbor.c" nm_copy_sd "src/libsystemd-network/lldp-neighbor.h" nm_copy_sd "src/libsystemd-network/lldp-network.c" nm_copy_sd "src/libsystemd-network/lldp-network.h" nm_copy_sd "src/libsystemd-network/network-internal.c" nm_copy_sd "src/libsystemd-network/network-internal.h" nm_copy_sd "src/libsystemd-network/sd-dhcp6-client.c" nm_copy_sd "src/libsystemd-network/sd-dhcp6-lease.c" nm_copy_sd "src/libsystemd-network/sd-dhcp-client.c" nm_copy_sd "src/libsystemd-network/sd-dhcp-lease.c" nm_copy_sd "src/libsystemd-network/sd-ipv4ll.c" nm_copy_sd "src/libsystemd-network/sd-ipv4acd.c" nm_copy_sd "src/libsystemd-network/sd-lldp.c" nm_copy_sd "src/libsystemd/sd-event/sd-event.c" nm_copy_sd "src/libsystemd/sd-id128/sd-id128.c" nm_copy_sd "src/shared/dns-domain.c" nm_copy_sd "src/shared/dns-domain.h" nm_copy_sd "src/systemd/_sd-common.h" nm_copy_sd "src/systemd/sd-dhcp6-client.h" nm_copy_sd "src/systemd/sd-dhcp6-lease.h" nm_copy_sd "src/systemd/sd-dhcp-client.h" nm_copy_sd "src/systemd/sd-dhcp-lease.h" nm_copy_sd "src/systemd/sd-event.h" nm_copy_sd "src/systemd/sd-ndisc.h" nm_copy_sd "src/systemd/sd-id128.h" nm_copy_sd "src/systemd/sd-ipv4acd.h" nm_copy_sd "src/systemd/sd-ipv4ll.h" nm_copy_sd "src/systemd/sd-lldp.h"
Diffstat (limited to 'src/systemd/src/libsystemd-network')
-rw-r--r--src/systemd/src/libsystemd-network/arp-util.c10
-rw-r--r--src/systemd/src/libsystemd-network/dhcp-network.c4
-rw-r--r--src/systemd/src/libsystemd-network/lldp-internal.h2
-rw-r--r--src/systemd/src/libsystemd-network/lldp-neighbor.c49
-rw-r--r--src/systemd/src/libsystemd-network/lldp-neighbor.h8
-rw-r--r--src/systemd/src/libsystemd-network/lldp-network.c3
-rw-r--r--src/systemd/src/libsystemd-network/network-internal.c17
-rw-r--r--src/systemd/src/libsystemd-network/sd-lldp.c105
8 files changed, 134 insertions, 64 deletions
diff --git a/src/systemd/src/libsystemd-network/arp-util.c b/src/systemd/src/libsystemd-network/arp-util.c
index 4660c7ea09..02028bf28a 100644
--- a/src/systemd/src/libsystemd-network/arp-util.c
+++ b/src/systemd/src/libsystemd-network/arp-util.c
@@ -79,7 +79,7 @@ int arp_network_bind_raw_socket(int ifindex, be32_t address, const struct ether_
};
union sockaddr_union link = {
.ll.sll_family = AF_PACKET,
- .ll.sll_protocol = htons(ETH_P_ARP),
+ .ll.sll_protocol = htobe16(ETH_P_ARP),
.ll.sll_ifindex = ifindex,
.ll.sll_halen = ETH_ALEN,
.ll.sll_addr = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff },
@@ -112,17 +112,17 @@ static int arp_send_packet(int fd, int ifindex,
bool announce) {
union sockaddr_union link = {
.ll.sll_family = AF_PACKET,
- .ll.sll_protocol = htons(ETH_P_ARP),
+ .ll.sll_protocol = htobe16(ETH_P_ARP),
.ll.sll_ifindex = ifindex,
.ll.sll_halen = ETH_ALEN,
.ll.sll_addr = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff },
};
struct ether_arp arp = {
- .ea_hdr.ar_hrd = htons(ARPHRD_ETHER), /* HTYPE */
- .ea_hdr.ar_pro = htons(ETHERTYPE_IP), /* PTYPE */
+ .ea_hdr.ar_hrd = htobe16(ARPHRD_ETHER), /* HTYPE */
+ .ea_hdr.ar_pro = htobe16(ETHERTYPE_IP), /* PTYPE */
.ea_hdr.ar_hln = ETH_ALEN, /* HLEN */
.ea_hdr.ar_pln = sizeof(be32_t), /* PLEN */
- .ea_hdr.ar_op = htons(ARPOP_REQUEST), /* REQUEST */
+ .ea_hdr.ar_op = htobe16(ARPOP_REQUEST), /* REQUEST */
};
int r;
diff --git a/src/systemd/src/libsystemd-network/dhcp-network.c b/src/systemd/src/libsystemd-network/dhcp-network.c
index fac25e0fa2..a9f5a0a5de 100644
--- a/src/systemd/src/libsystemd-network/dhcp-network.c
+++ b/src/systemd/src/libsystemd-network/dhcp-network.c
@@ -107,9 +107,9 @@ static int _bind_raw_socket(int ifindex, union sockaddr_union *link,
return -errno;
link->ll.sll_family = AF_PACKET;
- link->ll.sll_protocol = htons(ETH_P_IP);
+ link->ll.sll_protocol = htobe16(ETH_P_IP);
link->ll.sll_ifindex = ifindex;
- link->ll.sll_hatype = htons(arp_type);
+ link->ll.sll_hatype = htobe16(arp_type);
link->ll.sll_halen = mac_addr_len;
memcpy(link->ll.sll_addr, bcast_addr, mac_addr_len);
diff --git a/src/systemd/src/libsystemd-network/lldp-internal.h b/src/systemd/src/libsystemd-network/lldp-internal.h
index 7592bc4305..becc162fab 100644
--- a/src/systemd/src/libsystemd-network/lldp-internal.h
+++ b/src/systemd/src/libsystemd-network/lldp-internal.h
@@ -28,6 +28,8 @@
#include "prioq.h"
struct sd_lldp {
+ unsigned n_ref;
+
int ifindex;
int fd;
diff --git a/src/systemd/src/libsystemd-network/lldp-neighbor.c b/src/systemd/src/libsystemd-network/lldp-neighbor.c
index 6a716430e3..88f7e329b0 100644
--- a/src/systemd/src/libsystemd-network/lldp-neighbor.c
+++ b/src/systemd/src/libsystemd-network/lldp-neighbor.c
@@ -360,9 +360,16 @@ end_marker:
void lldp_neighbor_start_ttl(sd_lldp_neighbor *n) {
assert(n);
- if (n->ttl > 0)
- n->until = usec_add(now(clock_boottime_or_monotonic()), n->ttl * USEC_PER_SEC);
- else
+ if (n->ttl > 0) {
+ usec_t base;
+
+ /* Use the packet's timestamp if there is one known */
+ base = triple_timestamp_by_clock(&n->timestamp, clock_boottime_or_monotonic());
+ if (base <= 0 || base == USEC_INFINITY)
+ base = now(clock_boottime_or_monotonic()); /* Otherwise, take the current time */
+
+ n->until = usec_add(base, n->ttl * USEC_PER_SEC);
+ } else
n->until = 0;
if (n->lldp)
@@ -588,11 +595,11 @@ done:
return 0;
}
-_public_ int sd_lldp_neighbor_get_ttl(sd_lldp_neighbor *n, uint16_t *ret) {
+_public_ int sd_lldp_neighbor_get_ttl(sd_lldp_neighbor *n, uint16_t *ret_sec) {
assert_return(n, -EINVAL);
- assert_return(ret, -EINVAL);
+ assert_return(ret_sec, -EINVAL);
- *ret = n->ttl;
+ *ret_sec = n->ttl;
return 0;
}
@@ -651,7 +658,7 @@ _public_ int sd_lldp_neighbor_get_enabled_capabilities(sd_lldp_neighbor *n, uint
return 0;
}
-int sd_lldp_neighbor_from_raw(sd_lldp_neighbor **ret, const void *raw, size_t raw_size) {
+_public_ int sd_lldp_neighbor_from_raw(sd_lldp_neighbor **ret, const void *raw, size_t raw_size) {
_cleanup_(sd_lldp_neighbor_unrefp) sd_lldp_neighbor *n = NULL;
int r;
@@ -668,7 +675,7 @@ int sd_lldp_neighbor_from_raw(sd_lldp_neighbor **ret, const void *raw, size_t ra
return r;
*ret = n;
- n = 0;
+ n = NULL;
return r;
}
@@ -679,7 +686,7 @@ _public_ int sd_lldp_neighbor_tlv_rewind(sd_lldp_neighbor *n) {
assert(n->raw_size >= sizeof(struct ether_header));
n->rindex = sizeof(struct ether_header);
- return 0;
+ return n->rindex < n->raw_size;
}
_public_ int sd_lldp_neighbor_tlv_next(sd_lldp_neighbor *n) {
@@ -693,7 +700,7 @@ _public_ int sd_lldp_neighbor_tlv_next(sd_lldp_neighbor *n) {
if (n->rindex + 2 > n->raw_size) /* Truncated message */
return -EBADMSG;
- length = LLDP_NEIGHBOR_LENGTH(n);
+ length = LLDP_NEIGHBOR_TLV_LENGTH(n);
if (n->rindex + 2 + length > n->raw_size)
return -EBADMSG;
@@ -711,7 +718,7 @@ _public_ int sd_lldp_neighbor_tlv_get_type(sd_lldp_neighbor *n, uint8_t *type) {
if (n->rindex + 2 > n->raw_size)
return -EBADMSG;
- *type = LLDP_NEIGHBOR_TYPE(n);
+ *type = LLDP_NEIGHBOR_TLV_TYPE(n);
return 0;
}
@@ -743,14 +750,14 @@ _public_ int sd_lldp_neighbor_tlv_get_oui(sd_lldp_neighbor *n, uint8_t oui[3], u
if (r == 0)
return -ENXIO;
- length = LLDP_NEIGHBOR_LENGTH(n);
+ length = LLDP_NEIGHBOR_TLV_LENGTH(n);
if (length < 4)
return -EBADMSG;
if (n->rindex + 2 + length > n->raw_size)
return -EBADMSG;
- d = LLDP_NEIGHBOR_DATA(n);
+ d = LLDP_NEIGHBOR_TLV_DATA(n);
memcpy(oui, d, 3);
*subtype = d[3];
@@ -782,8 +789,7 @@ _public_ int sd_lldp_neighbor_tlv_get_raw(sd_lldp_neighbor *n, const void **ret,
if (n->rindex + 2 > n->raw_size)
return -EBADMSG;
- length = LLDP_NEIGHBOR_LENGTH(n);
-
+ length = LLDP_NEIGHBOR_TLV_LENGTH(n);
if (n->rindex + 2 + length > n->raw_size)
return -EBADMSG;
@@ -792,3 +798,16 @@ _public_ int sd_lldp_neighbor_tlv_get_raw(sd_lldp_neighbor *n, const void **ret,
return 0;
}
+
+_public_ int sd_lldp_neighbor_get_timestamp(sd_lldp_neighbor *n, clockid_t clock, uint64_t *ret) {
+ assert_return(n, -EINVAL);
+ assert_return(TRIPLE_TIMESTAMP_HAS_CLOCK(clock), -EOPNOTSUPP);
+ assert_return(clock_supported(clock), -EOPNOTSUPP);
+ assert_return(ret, -EINVAL);
+
+ if (!triple_timestamp_is_set(&n->timestamp))
+ return -ENODATA;
+
+ *ret = triple_timestamp_by_clock(&n->timestamp, clock);
+ return 0;
+}
diff --git a/src/systemd/src/libsystemd-network/lldp-neighbor.h b/src/systemd/src/libsystemd-network/lldp-neighbor.h
index f203bfa604..c1a7606d06 100644
--- a/src/systemd/src/libsystemd-network/lldp-neighbor.h
+++ b/src/systemd/src/libsystemd-network/lldp-neighbor.h
@@ -43,6 +43,8 @@ struct sd_lldp_neighbor {
sd_lldp *lldp;
unsigned n_ref;
+ triple_timestamp timestamp;
+
usec_t until;
unsigned prioq_idx;
@@ -81,18 +83,18 @@ static inline void *LLDP_NEIGHBOR_RAW(const sd_lldp_neighbor *n) {
return (uint8_t*) n + ALIGN(sizeof(sd_lldp_neighbor));
}
-static inline uint8_t LLDP_NEIGHBOR_TYPE(const sd_lldp_neighbor *n) {
+static inline uint8_t LLDP_NEIGHBOR_TLV_TYPE(const sd_lldp_neighbor *n) {
return ((uint8_t*) LLDP_NEIGHBOR_RAW(n))[n->rindex] >> 1;
}
-static inline size_t LLDP_NEIGHBOR_LENGTH(const sd_lldp_neighbor *n) {
+static inline size_t LLDP_NEIGHBOR_TLV_LENGTH(const sd_lldp_neighbor *n) {
uint8_t *p;
p = (uint8_t*) LLDP_NEIGHBOR_RAW(n) + n->rindex;
return p[1] + (((size_t) (p[0] & 1)) << 8);
}
-static inline void* LLDP_NEIGHBOR_DATA(const sd_lldp_neighbor *n) {
+static inline void* LLDP_NEIGHBOR_TLV_DATA(const sd_lldp_neighbor *n) {
return ((uint8_t*) LLDP_NEIGHBOR_RAW(n)) + n->rindex + 2;
}
diff --git a/src/systemd/src/libsystemd-network/lldp-network.c b/src/systemd/src/libsystemd-network/lldp-network.c
index f031760351..59c25598e9 100644
--- a/src/systemd/src/libsystemd-network/lldp-network.c
+++ b/src/systemd/src/libsystemd-network/lldp-network.c
@@ -57,7 +57,8 @@ int lldp_network_bind_raw_socket(int ifindex) {
assert(ifindex > 0);
- fd = socket(PF_PACKET, SOCK_RAW|SOCK_CLOEXEC|SOCK_NONBLOCK, htons(ETHERTYPE_LLDP));
+ fd = socket(PF_PACKET, SOCK_RAW|SOCK_CLOEXEC|SOCK_NONBLOCK,
+ htobe16(ETHERTYPE_LLDP));
if (fd < 0)
return -errno;
diff --git a/src/systemd/src/libsystemd-network/network-internal.c b/src/systemd/src/libsystemd-network/network-internal.c
index 046b0f9393..ce30b7fc25 100644
--- a/src/systemd/src/libsystemd-network/network-internal.c
+++ b/src/systemd/src/libsystemd-network/network-internal.c
@@ -27,7 +27,7 @@
#include "condition.h"
#include "conf-parser.h"
#include "dhcp-lease-internal.h"
-#include "ether-addr-util.c"
+#include "ether-addr-util.h"
#include "hexdecoct.h"
#include "log.h"
#include "network-internal.h"
@@ -380,18 +380,21 @@ int deserialize_in_addrs(struct in_addr **ret, const char *string) {
return size;
}
-void serialize_in6_addrs(FILE *f, const struct in6_addr *addresses,
- size_t size) {
+void serialize_in6_addrs(FILE *f, const struct in6_addr *addresses, size_t size) {
unsigned i;
assert(f);
assert(addresses);
assert(size);
- for (i = 0; i < size; i++)
- fprintf(f, SD_NDISC_ADDRESS_FORMAT_STR"%s",
- SD_NDISC_ADDRESS_FORMAT_VAL(addresses[i]),
- (i < (size - 1)) ? " ": "");
+ for (i = 0; i < size; i++) {
+ char buffer[INET6_ADDRSTRLEN];
+
+ fputs(inet_ntop(AF_INET6, addresses+i, buffer, sizeof(buffer)), f);
+
+ if (i < size - 1)
+ fputc(' ', f);
+ }
}
int deserialize_in6_addrs(struct in6_addr **ret, const char *string) {
diff --git a/src/systemd/src/libsystemd-network/sd-lldp.c b/src/systemd/src/libsystemd-network/sd-lldp.c
index 9d4587c80e..0bd1e66aa0 100644
--- a/src/systemd/src/libsystemd-network/sd-lldp.c
+++ b/src/systemd/src/libsystemd-network/sd-lldp.c
@@ -43,7 +43,6 @@ static void lldp_flush_neighbors(sd_lldp *lldp) {
static void lldp_callback(sd_lldp *lldp, sd_lldp_event event, sd_lldp_neighbor *n) {
assert(lldp);
- assert(n);
log_lldp("Invoking callback for '%c'.", event);
@@ -138,6 +137,7 @@ static int lldp_add_neighbor(sd_lldp *lldp, sd_lldp_neighbor *n) {
if (lldp_neighbor_equal(n, old)) {
/* Is this equal, then restart the TTL counter, but don't do anyting else. */
+ old->timestamp = n->timestamp;
lldp_start_timer(lldp, old);
lldp_callback(lldp, SD_LLDP_EVENT_REFRESHED, old);
return 0;
@@ -171,7 +171,7 @@ static int lldp_add_neighbor(sd_lldp *lldp, sd_lldp_neighbor *n) {
finish:
if (old)
- lldp_callback(lldp, SD_LLDP_EVENT_REMOVED, n);
+ lldp_callback(lldp, SD_LLDP_EVENT_REMOVED, old);
return r;
}
@@ -202,6 +202,7 @@ static int lldp_receive_datagram(sd_event_source *s, int fd, uint32_t revents, v
_cleanup_(sd_lldp_neighbor_unrefp) sd_lldp_neighbor *n = NULL;
ssize_t space, length;
sd_lldp *lldp = userdata;
+ struct timespec ts;
assert(fd >= 0);
assert(lldp);
@@ -215,21 +216,41 @@ static int lldp_receive_datagram(sd_event_source *s, int fd, uint32_t revents, v
return -ENOMEM;
length = recv(fd, LLDP_NEIGHBOR_RAW(n), n->raw_size, MSG_DONTWAIT);
- if (length < 0)
+ if (length < 0) {
+ if (errno == EAGAIN || errno == EINTR)
+ return 0;
+
return log_lldp_errno(errno, "Failed to read LLDP datagram: %m");
+ }
if ((size_t) length != n->raw_size) {
log_lldp("Packet size mismatch.");
return -EINVAL;
}
+ /* Try to get the timestamp of this packet if it is known */
+ if (ioctl(fd, SIOCGSTAMPNS, &ts) >= 0)
+ triple_timestamp_from_realtime(&n->timestamp, timespec_load(&ts));
+ else
+ triple_timestamp_get(&n->timestamp);
+
return lldp_handle_datagram(lldp, n);
}
+static void lldp_reset(sd_lldp *lldp) {
+ assert(lldp);
+
+ lldp->timer_event_source = sd_event_source_unref(lldp->timer_event_source);
+ lldp->io_event_source = sd_event_source_unref(lldp->io_event_source);
+ lldp->fd = safe_close(lldp->fd);
+}
+
_public_ int sd_lldp_start(sd_lldp *lldp) {
int r;
assert_return(lldp, -EINVAL);
+ assert_return(lldp->event, -EINVAL);
+ assert_return(lldp->ifindex > 0, -EINVAL);
if (lldp->fd >= 0)
return 0;
@@ -240,24 +261,21 @@ _public_ int sd_lldp_start(sd_lldp *lldp) {
if (lldp->fd < 0)
return lldp->fd;
- if (lldp->event) {
- r = sd_event_add_io(lldp->event, &lldp->io_event_source, lldp->fd, EPOLLIN, lldp_receive_datagram, lldp);
- if (r < 0)
- goto fail;
+ r = sd_event_add_io(lldp->event, &lldp->io_event_source, lldp->fd, EPOLLIN, lldp_receive_datagram, lldp);
+ if (r < 0)
+ goto fail;
- r = sd_event_source_set_priority(lldp->io_event_source, lldp->event_priority);
- if (r < 0)
- goto fail;
+ r = sd_event_source_set_priority(lldp->io_event_source, lldp->event_priority);
+ if (r < 0)
+ goto fail;
- (void) sd_event_source_set_description(lldp->io_event_source, "lldp-io");
- }
+ (void) sd_event_source_set_description(lldp->io_event_source, "lldp-io");
+ log_lldp("Started LLDP client");
return 1;
fail:
- lldp->io_event_source = sd_event_source_unref(lldp->io_event_source);
- lldp->fd = safe_close(lldp->fd);
-
+ lldp_reset(lldp);
return r;
}
@@ -267,10 +285,9 @@ _public_ int sd_lldp_stop(sd_lldp *lldp) {
if (lldp->fd < 0)
return 0;
- lldp->timer_event_source = sd_event_source_unref(lldp->timer_event_source);
- lldp->io_event_source = sd_event_source_unref(lldp->io_event_source);
- lldp->fd = safe_close(lldp->fd);
+ log_lldp("Stopping LLDP client");
+ lldp_reset(lldp);
lldp_flush_neighbors(lldp);
return 1;
@@ -305,6 +322,12 @@ _public_ int sd_lldp_detach_event(sd_lldp *lldp) {
return 0;
}
+_public_ sd_event* sd_lldp_get_event(sd_lldp *lldp) {
+ assert_return(lldp, NULL);
+
+ return lldp->event;
+}
+
_public_ int sd_lldp_set_callback(sd_lldp *lldp, sd_lldp_callback_t cb, void *userdata) {
assert_return(lldp, -EINVAL);
@@ -314,39 +337,60 @@ _public_ int sd_lldp_set_callback(sd_lldp *lldp, sd_lldp_callback_t cb, void *us
return 0;
}
+_public_ int sd_lldp_set_ifindex(sd_lldp *lldp, int ifindex) {
+ assert_return(lldp, -EINVAL);
+ assert_return(ifindex > 0, -EINVAL);
+ assert_return(lldp->fd < 0, -EBUSY);
+
+ lldp->ifindex = ifindex;
+ return 0;
+}
+
+_public_ sd_lldp* sd_lldp_ref(sd_lldp *lldp) {
+
+ if (!lldp)
+ return NULL;
+
+ assert(lldp->n_ref > 0);
+ lldp->n_ref++;
+
+ return lldp;
+}
+
_public_ sd_lldp* sd_lldp_unref(sd_lldp *lldp) {
if (!lldp)
return NULL;
+ assert(lldp->n_ref > 0);
+ lldp->n_ref --;
+
+ if (lldp->n_ref > 0)
+ return NULL;
+
+ lldp_reset(lldp);
+ sd_lldp_detach_event(lldp);
lldp_flush_neighbors(lldp);
hashmap_free(lldp->neighbor_by_id);
prioq_free(lldp->neighbor_by_expiry);
-
- sd_event_source_unref(lldp->io_event_source);
- sd_event_source_unref(lldp->timer_event_source);
- sd_event_unref(lldp->event);
- safe_close(lldp->fd);
-
free(lldp);
return NULL;
}
-_public_ int sd_lldp_new(sd_lldp **ret, int ifindex) {
+_public_ int sd_lldp_new(sd_lldp **ret) {
_cleanup_(sd_lldp_unrefp) sd_lldp *lldp = NULL;
int r;
assert_return(ret, -EINVAL);
- assert_return(ifindex > 0, -EINVAL);
lldp = new0(sd_lldp, 1);
if (!lldp)
return -ENOMEM;
+ lldp->n_ref = 1;
lldp->fd = -1;
- lldp->ifindex = ifindex;
lldp->neighbors_max = LLDP_DEFAULT_NEIGHBORS_MAX;
lldp->capability_mask = (uint16_t) -1;
@@ -486,11 +530,10 @@ _public_ int sd_lldp_set_filter_address(sd_lldp *lldp, const struct ether_addr *
/* In order to deal nicely with bridges that send back our own packets, allow one address to be filtered, so
* that our own can be filtered out here. */
- if (!addr) {
+ if (addr)
+ lldp->filter_address = *addr;
+ else
zero(lldp->filter_address);
- return 0;
- }
- lldp->filter_address = *addr;
return 0;
}