From 4ac7c8341c660db654821ed2dc0273645dc19645 Mon Sep 17 00:00:00 2001 From: Ondrej Zajicek Date: Mon, 9 Nov 2009 23:22:53 +0100 Subject: [PATCH] Use IPv6 checksums in OSPFv3. --- lib/socket.h | 4 ++++ proto/ospf/iface.c | 6 ++++++ proto/ospf/packet.c | 1 - sysdep/unix/io.c | 19 ++++++++++++++++++- 4 files changed, 28 insertions(+), 2 deletions(-) diff --git a/lib/socket.h b/lib/socket.h index f44e8e88..c642bdf9 100644 --- a/lib/socket.h +++ b/lib/socket.h @@ -60,6 +60,10 @@ int sk_setup_multicast(sock *s); int sk_join_group(sock *s, ip_addr maddr); int sk_leave_group(sock *s, ip_addr maddr); +#ifdef IPV6 +int sk_set_ipv6_checksum(sock *s, int offset); +#endif + static inline int sk_send_buffer_empty(sock *sk) { diff --git a/proto/ospf/iface.c b/proto/ospf/iface.c index 9b65961d..e98414f2 100644 --- a/proto/ospf/iface.c +++ b/proto/ospf/iface.c @@ -89,6 +89,12 @@ ospf_open_socket(struct ospf_iface *ifa, int mc) if (sk_open(ipsk) != 0) goto err; +#ifdef OSPFv3 + /* 12 is an offset of the checksum in an OSPF packet */ + if (sk_set_ipv6_checksum(ipsk, 12) < 0) + goto err; +#endif + if (mc) { if (sk_setup_multicast(ipsk) < 0) diff --git a/proto/ospf/packet.c b/proto/ospf/packet.c index 9422a9f3..94ec0109 100644 --- a/proto/ospf/packet.c +++ b/proto/ospf/packet.c @@ -320,7 +320,6 @@ ospf_rx_hook(sock * sk, int size) return 1; } - /* FIXME - handle checksums in OSPFv3 */ #ifdef OSPFv2 if ((ps->autype != htons(OSPF_AUTH_CRYPT)) && (!ipsum_verify(ps, 16, (void *) ps + sizeof(struct ospf_packet), diff --git a/sysdep/unix/io.c b/sysdep/unix/io.c index 3eb2e03c..cd5c5db7 100644 --- a/sysdep/unix/io.c +++ b/sysdep/unix/io.c @@ -782,12 +782,29 @@ int sk_set_broadcast(sock *s, int enable) { if (setsockopt(s->fd, SOL_SOCKET, SO_BROADCAST, &enable, sizeof(enable)) < 0) - log(L_ERR "sk_set_broadcast: SO_BROADCAST: %m"); + { + log(L_ERR "sk_set_broadcast: SO_BROADCAST: %m"); + return -1; + } + + return 0; } #ifdef IPV6 +int +sk_set_ipv6_checksum(sock *s, int offset) +{ + if (setsockopt(s->fd, IPPROTO_IPV6, IPV6_CHECKSUM, &offset, sizeof(offset)) < 0) + { + log(L_ERR "sk_set_ipv6_checksum: IPV6_CHECKSUM: %m"); + return -1; + } + + return 0; +} + int sk_setup_multicast(sock *s) {