From 51b280ff06c588e61afcf97b8d58d0d2904b2dfc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Timo=20Ter=C3=A4s?= Date: Tue, 23 Nov 2010 08:13:43 +0200 Subject: main/iproute2: apply patches from upstream for 2.6.35.1 release This fixes a nasty bug causing "ip route get" to not work properly. --- ...x-filtering-related-to-flushing-IP-addres.patch | 199 +++++++++++++++++++++ ...-dont-filter-cached-routes-on-iproute_get.patch | 32 ++++ main/iproute2/0003-Snapshot-for-2.6.35.1.patch | 19 ++ main/iproute2/APKBUILD | 18 +- 4 files changed, 265 insertions(+), 3 deletions(-) create mode 100644 main/iproute2/0001-iproute2-Fix-filtering-related-to-flushing-IP-addres.patch create mode 100644 main/iproute2/0002-iproute2-dont-filter-cached-routes-on-iproute_get.patch create mode 100644 main/iproute2/0003-Snapshot-for-2.6.35.1.patch diff --git a/main/iproute2/0001-iproute2-Fix-filtering-related-to-flushing-IP-addres.patch b/main/iproute2/0001-iproute2-Fix-filtering-related-to-flushing-IP-addres.patch new file mode 100644 index 0000000000..856cd93831 --- /dev/null +++ b/main/iproute2/0001-iproute2-Fix-filtering-related-to-flushing-IP-addres.patch @@ -0,0 +1,199 @@ +From 3bc1c4f29777171b484d36abf673667e3729202b Mon Sep 17 00:00:00 2001 +From: Ben Greear +Date: Mon, 16 Aug 2010 10:00:08 -0700 +Subject: [PATCH 1/3] iproute2: Fix filtering related to flushing IP addresses. + +The old 'ip addr flush' logic had several flaws: + +* It reversed logic for primary v/s secondary flags + (though, it sort of worked right anyway) + +* The code tried to remove secondaries and then primaries, + but in practice, it always removed one primary per loop, + which not at all efficient. + +* The filter logic in the core would run only the first + filter in most cases. + +* If you used '-s -s', the ifa_flags member would be + modified, which could make future filters fail + to function fine. + +This patch attempts to fix all of these issues. + +Tested-by: Brian Haley +Signed-off-by: Ben Greear +--- + ip/ipaddress.c | 34 +++++++++++++++++++++++----------- + lib/libnetlink.c | 23 ++++++++++++++++------- + 2 files changed, 39 insertions(+), 18 deletions(-) + +diff --git a/ip/ipaddress.c b/ip/ipaddress.c +index 3a411b1..19b3d6e 100644 +--- a/ip/ipaddress.c ++++ b/ip/ipaddress.c +@@ -453,6 +453,8 @@ int print_addrinfo(const struct sockaddr_nl *who, struct nlmsghdr *n, + struct ifaddrmsg *ifa = NLMSG_DATA(n); + int len = n->nlmsg_len; + int deprecated = 0; ++ /* Use local copy of ifa_flags to not interfere with filtering code */ ++ unsigned int ifa_flags; + struct rtattr * rta_tb[IFA_MAX+1]; + char abuf[256]; + SPRINT_BUF(b1); +@@ -572,40 +574,41 @@ int print_addrinfo(const struct sockaddr_nl *who, struct nlmsghdr *n, + abuf, sizeof(abuf))); + } + fprintf(fp, "scope %s ", rtnl_rtscope_n2a(ifa->ifa_scope, b1, sizeof(b1))); ++ ifa_flags = ifa->ifa_flags; + if (ifa->ifa_flags&IFA_F_SECONDARY) { +- ifa->ifa_flags &= ~IFA_F_SECONDARY; ++ ifa_flags &= ~IFA_F_SECONDARY; + if (ifa->ifa_family == AF_INET6) + fprintf(fp, "temporary "); + else + fprintf(fp, "secondary "); + } + if (ifa->ifa_flags&IFA_F_TENTATIVE) { +- ifa->ifa_flags &= ~IFA_F_TENTATIVE; ++ ifa_flags &= ~IFA_F_TENTATIVE; + fprintf(fp, "tentative "); + } + if (ifa->ifa_flags&IFA_F_DEPRECATED) { +- ifa->ifa_flags &= ~IFA_F_DEPRECATED; ++ ifa_flags &= ~IFA_F_DEPRECATED; + deprecated = 1; + fprintf(fp, "deprecated "); + } + if (ifa->ifa_flags&IFA_F_HOMEADDRESS) { +- ifa->ifa_flags &= ~IFA_F_HOMEADDRESS; ++ ifa_flags &= ~IFA_F_HOMEADDRESS; + fprintf(fp, "home "); + } + if (ifa->ifa_flags&IFA_F_NODAD) { +- ifa->ifa_flags &= ~IFA_F_NODAD; ++ ifa_flags &= ~IFA_F_NODAD; + fprintf(fp, "nodad "); + } + if (!(ifa->ifa_flags&IFA_F_PERMANENT)) { + fprintf(fp, "dynamic "); + } else +- ifa->ifa_flags &= ~IFA_F_PERMANENT; ++ ifa_flags &= ~IFA_F_PERMANENT; + if (ifa->ifa_flags&IFA_F_DADFAILED) { +- ifa->ifa_flags &= ~IFA_F_DADFAILED; ++ ifa_flags &= ~IFA_F_DADFAILED; + fprintf(fp, "dadfailed "); + } +- if (ifa->ifa_flags) +- fprintf(fp, "flags %02x ", ifa->ifa_flags); ++ if (ifa_flags) ++ fprintf(fp, "flags %02x ", ifa_flags); + if (rta_tb[IFA_LABEL]) + fprintf(fp, "%s", (char*)RTA_DATA(rta_tb[IFA_LABEL])); + if (rta_tb[IFA_CACHEINFO]) { +@@ -638,7 +641,7 @@ int print_addrinfo_primary(const struct sockaddr_nl *who, struct nlmsghdr *n, + { + struct ifaddrmsg *ifa = NLMSG_DATA(n); + +- if (!ifa->ifa_flags & IFA_F_SECONDARY) ++ if (ifa->ifa_flags & IFA_F_SECONDARY) + return 0; + + return print_addrinfo(who, n, arg); +@@ -649,7 +652,7 @@ int print_addrinfo_secondary(const struct sockaddr_nl *who, struct nlmsghdr *n, + { + struct ifaddrmsg *ifa = NLMSG_DATA(n); + +- if (ifa->ifa_flags & IFA_F_SECONDARY) ++ if (!(ifa->ifa_flags & IFA_F_SECONDARY)) + return 0; + + return print_addrinfo(who, n, arg); +@@ -849,6 +852,7 @@ static int ipaddr_list_or_flush(int argc, char **argv, int flush) + exit(1); + } + if (filter.flushed == 0) { ++flush_done: + if (show_stats) { + if (round == 0) + printf("Nothing to flush.\n"); +@@ -866,6 +870,14 @@ static int ipaddr_list_or_flush(int argc, char **argv, int flush) + printf("\n*** Round %d, deleting %d addresses ***\n", round, filter.flushed); + fflush(stdout); + } ++ ++ /* If we are flushing, and specifying primary, then we ++ * want to flush only a single round. Otherwise, we'll ++ * start flushing secondaries that were promoted to ++ * primaries. ++ */ ++ if (!(filter.flags & IFA_F_SECONDARY) && (filter.flagmask & IFA_F_SECONDARY)) ++ goto flush_done; + } + fprintf(stderr, "*** Flush remains incomplete after %d rounds. ***\n", MAX_ROUNDS); fflush(stderr); + return 1; +diff --git a/lib/libnetlink.c b/lib/libnetlink.c +index cfeb894..ee4f045 100644 +--- a/lib/libnetlink.c ++++ b/lib/libnetlink.c +@@ -189,6 +189,8 @@ int rtnl_dump_filter_l(struct rtnl_handle *rth, + while (1) { + int status; + const struct rtnl_dump_filter_arg *a; ++ int found_done = 0; ++ int msglen = 0; + + iov.iov_len = sizeof(buf); + status = recvmsg(rth->fd, &msg, 0); +@@ -208,8 +210,9 @@ int rtnl_dump_filter_l(struct rtnl_handle *rth, + + for (a = arg; a->filter; a++) { + struct nlmsghdr *h = (struct nlmsghdr*)buf; ++ msglen = status; + +- while (NLMSG_OK(h, status)) { ++ while (NLMSG_OK(h, msglen)) { + int err; + + if (nladdr.nl_pid != 0 || +@@ -224,8 +227,10 @@ int rtnl_dump_filter_l(struct rtnl_handle *rth, + goto skip_it; + } + +- if (h->nlmsg_type == NLMSG_DONE) +- return 0; ++ if (h->nlmsg_type == NLMSG_DONE) { ++ found_done = 1; ++ break; /* process next filter */ ++ } + if (h->nlmsg_type == NLMSG_ERROR) { + struct nlmsgerr *err = (struct nlmsgerr*)NLMSG_DATA(h); + if (h->nlmsg_len < NLMSG_LENGTH(sizeof(struct nlmsgerr))) { +@@ -242,15 +247,19 @@ int rtnl_dump_filter_l(struct rtnl_handle *rth, + return err; + + skip_it: +- h = NLMSG_NEXT(h, status); ++ h = NLMSG_NEXT(h, msglen); + } +- } while (0); ++ } ++ ++ if (found_done) ++ return 0; ++ + if (msg.msg_flags & MSG_TRUNC) { + fprintf(stderr, "Message truncated\n"); + continue; + } +- if (status) { +- fprintf(stderr, "!!!Remnant of size %d\n", status); ++ if (msglen) { ++ fprintf(stderr, "!!!Remnant of size %d\n", msglen); + exit(1); + } + } +-- +1.7.1 + diff --git a/main/iproute2/0002-iproute2-dont-filter-cached-routes-on-iproute_get.patch b/main/iproute2/0002-iproute2-dont-filter-cached-routes-on-iproute_get.patch new file mode 100644 index 0000000000..38be07c49b --- /dev/null +++ b/main/iproute2/0002-iproute2-dont-filter-cached-routes-on-iproute_get.patch @@ -0,0 +1,32 @@ +From c73f3e02f8ae25e5daad0367690a3069895dd8a3 Mon Sep 17 00:00:00 2001 +From: Ulrich Weber +Date: Thu, 12 Aug 2010 11:05:19 +0200 +Subject: [PATCH 2/3] iproute2: dont filter cached routes on iproute_get + +iproute_get will return cloned routes for IPv4 +and cloned as well non-cloned routes for IPv6. + +Therefore RTM_F_CLONED flag should not be checked +for iproute_get routes. Check in print_route will +always fail because valid values are 0 and 1. + +Signed-off-by: Ulrich Weber +--- + ip/iproute.c | 1 + + 1 files changed, 1 insertions(+), 0 deletions(-) + +diff --git a/ip/iproute.c b/ip/iproute.c +index 711576e..b43933c 100644 +--- a/ip/iproute.c ++++ b/ip/iproute.c +@@ -1286,6 +1286,7 @@ int iproute_get(int argc, char **argv) + memset(&req, 0, sizeof(req)); + + iproute_reset_filter(); ++ filter.cloned = 2; + + req.n.nlmsg_len = NLMSG_LENGTH(sizeof(struct rtmsg)); + req.n.nlmsg_flags = NLM_F_REQUEST; +-- +1.7.1 + diff --git a/main/iproute2/0003-Snapshot-for-2.6.35.1.patch b/main/iproute2/0003-Snapshot-for-2.6.35.1.patch new file mode 100644 index 0000000000..f5cffd6069 --- /dev/null +++ b/main/iproute2/0003-Snapshot-for-2.6.35.1.patch @@ -0,0 +1,19 @@ +From daa10c8af6031f10168639b7fd3c181a5d788ee1 Mon Sep 17 00:00:00 2001 +From: Stephen Hemminger +Date: Mon, 23 Aug 2010 08:14:38 -0700 +Subject: [PATCH 3/3] Snapshot for 2.6.35.1 + +--- + include/SNAPSHOT.h | 2 +- + 1 files changed, 1 insertions(+), 1 deletions(-) + +diff --git a/include/SNAPSHOT.h b/include/SNAPSHOT.h +index de41b1b..8f79884 100644 +--- a/include/SNAPSHOT.h ++++ b/include/SNAPSHOT.h +@@ -1 +1 @@ +-static const char SNAPSHOT[] = "100804"; ++static const char SNAPSHOT[] = "100823"; +-- +1.7.1 + diff --git a/main/iproute2/APKBUILD b/main/iproute2/APKBUILD index 2ebb7a0a23..5d1b992134 100644 --- a/main/iproute2/APKBUILD +++ b/main/iproute2/APKBUILD @@ -2,7 +2,7 @@ pkgname=iproute2 pkgver=2.6.35 _realver=$pkgver -pkgrel=1 +pkgrel=2 pkgdesc="IP Routing Utilities" url="http://www.linux-foundation.org/en/Net:Iproute2" license="GPL2" @@ -10,11 +10,20 @@ depends= install="$pkgname.post-install $pkgname.post-deinstall" makedepends="bison flex bash" subpackages="$pkgname-doc" -source="http://devresources.linux-foundation.org/dev/iproute2/download/$pkgname-$_realver.tar.bz2" +source="http://devresources.linux-foundation.org/dev/iproute2/download/$pkgname-$_realver.tar.bz2 + 0001-iproute2-Fix-filtering-related-to-flushing-IP-addres.patch + 0002-iproute2-dont-filter-cached-routes-on-iproute_get.patch + 0003-Snapshot-for-2.6.35.1.patch + " prepare() { cd "$srcdir"/$pkgname-$_realver + for i in ../*.patch; do + msg "Applying $i..." + patch -p1 -i $i || return 1 + done + sed -i '/^TARGETS=/s: arpd : :' misc/Makefile sed -i 's:/usr/local:/usr:' tc/m_ipt.c include/iptables.h || return 1 sed -i 's:=/share:=/usr/share:' Makefile || return 1 @@ -31,4 +40,7 @@ package() { make -j1 DESTDIR="$pkgdir" install } -md5sums="b0f281b3124bf04669e18f5fe16d4934 iproute2-2.6.35.tar.bz2" +md5sums="b0f281b3124bf04669e18f5fe16d4934 iproute2-2.6.35.tar.bz2 +50992f46dd2a75ececdc5e54309e6b25 0001-iproute2-Fix-filtering-related-to-flushing-IP-addres.patch +dbe155ebdb22fb2b30635c0bd2431c5b 0002-iproute2-dont-filter-cached-routes-on-iproute_get.patch +084c0ee27a955d448705bbe51b70dc11 0003-Snapshot-for-2.6.35.1.patch" -- cgit v1.2.3