Gentoo Archives: gentoo-commits

From: Mike Frysinger <vapier@g.o>
To: gentoo-commits@l.g.o
Subject: [gentoo-commits] repo/gentoo:master commit in: net-nds/rpcbind/files/, net-nds/rpcbind/
Date: Tue, 03 Nov 2015 15:08:28
Message-Id: 1446563286.de6d02b6cf69bec8e91b7e7e3b4a083f8b13b822.vapier@gentoo
1 commit: de6d02b6cf69bec8e91b7e7e3b4a083f8b13b822
2 Author: Mike Frysinger <vapier <AT> gentoo <DOT> org>
3 AuthorDate: Tue Nov 3 14:53:27 2015 +0000
4 Commit: Mike Frysinger <vapier <AT> gentoo <DOT> org>
5 CommitDate: Tue Nov 3 15:08:06 2015 +0000
6 URL: https://gitweb.gentoo.org/repo/gentoo.git/commit/?id=de6d02b6
7
8 net-nds/rpcbind: add upstream fix for CVE-2015-7236 #560990
9
10 .../rpcbind/files/rpcbind-0.2.3-mem-corrupt.patch | 86 ++++++++++++++++++++++
11 net-nds/rpcbind/rpcbind-0.2.3-r1.ebuild | 57 ++++++++++++++
12 2 files changed, 143 insertions(+)
13
14 diff --git a/net-nds/rpcbind/files/rpcbind-0.2.3-mem-corrupt.patch b/net-nds/rpcbind/files/rpcbind-0.2.3-mem-corrupt.patch
15 new file mode 100644
16 index 0000000..9c03bda
17 --- /dev/null
18 +++ b/net-nds/rpcbind/files/rpcbind-0.2.3-mem-corrupt.patch
19 @@ -0,0 +1,86 @@
20 +https://bugs.gentoo.org/560990
21 +
22 +fix from upstream
23 +
24 +From d5dace219953c45d26ae42db238052b68540649a Mon Sep 17 00:00:00 2001
25 +From: Olaf Kirch <okir@××××.de>
26 +Date: Fri, 30 Oct 2015 10:18:20 -0400
27 +Subject: [PATCH rpcbind] Fix memory corruption in PMAP_CALLIT code
28 +
29 + - A PMAP_CALLIT call comes in on IPv4 UDP
30 + - rpcbind duplicates the caller's address to a netbuf and stores it in
31 + FINFO[0].caller_addr. caller_addr->buf now points to a memory region A
32 + with a size of 16 bytes
33 + - rpcbind forwards the call to the local service, receives a reply
34 + - when processing the reply, it does this in xprt_set_caller:
35 + xprt->xp_rtaddr = *FINFO[0].caller_addr
36 + It sends out the reply, and then frees the netbuf caller_addr and
37 + caller_addr.buf.
38 + However, it does not clear xp_rtaddr, so xp_rtaddr.buf now refers
39 + to memory region A, which is free.
40 + - When the next call comes in on the UDP/IPv4 socket, svc_dg_recv will
41 + be called, which will set xp_rtaddr to the client's address.
42 + It will reuse the buffer inside xp_rtaddr, ie it will write a
43 + sockaddr_in to region A
44 +
45 +Some time down the road, an incoming TCP connection is accepted,
46 +allocating a fresh SVCXPRT. The memory region A is inside the
47 +new SVCXPRT
48 +
49 + - While processing the TCP call, another UDP call comes in, again
50 + overwriting region A with the client's address
51 + - TCP client closes connection. In svc_destroy, we now trip over
52 + the garbage left in region A
53 +
54 +We ran into the case where a commercial scanner was triggering
55 +occasional rpcbind segfaults. The core file that was captured showed
56 +a corrupted xprt->xp_netid pointer that was really a sockaddr_in.
57 +
58 +Signed-off-by: Olaf Kirch <okir@××××.de>
59 +Signed-off-by: Steve Dickson <steved@××××××.com>
60 +---
61 + src/rpcb_svc_com.c | 23 ++++++++++++++++++++++-
62 + 1 file changed, 22 insertions(+), 1 deletion(-)
63 +
64 +diff --git a/src/rpcb_svc_com.c b/src/rpcb_svc_com.c
65 +index ff9ce6b..4ae93f1 100644
66 +--- a/src/rpcb_svc_com.c
67 ++++ b/src/rpcb_svc_com.c
68 +@@ -1183,12 +1183,33 @@ check_rmtcalls(struct pollfd *pfds, int nfds)
69 + return (ncallbacks_found);
70 + }
71 +
72 ++/*
73 ++ * This is really a helper function defined in libtirpc,
74 ++ * but unfortunately, it hasn't been exported yet.
75 ++ */
76 ++static struct netbuf *
77 ++__rpc_set_netbuf(struct netbuf *nb, const void *ptr, size_t len)
78 ++{
79 ++ if (nb->len != len) {
80 ++ if (nb->len)
81 ++ mem_free(nb->buf, nb->len);
82 ++ nb->buf = mem_alloc(len);
83 ++ if (nb->buf == NULL)
84 ++ return NULL;
85 ++
86 ++ nb->maxlen = nb->len = len;
87 ++ }
88 ++ memcpy(nb->buf, ptr, len);
89 ++ return nb;
90 ++}
91 ++
92 + static void
93 + xprt_set_caller(SVCXPRT *xprt, struct finfo *fi)
94 + {
95 ++ const struct netbuf *caller = fi->caller_addr;
96 + u_int32_t *xidp;
97 +
98 +- *(svc_getrpccaller(xprt)) = *(fi->caller_addr);
99 ++ __rpc_set_netbuf(svc_getrpccaller(xprt), caller->buf, caller->len);
100 + xidp = __rpcb_get_dg_xidp(xprt);
101 + *xidp = fi->caller_xid;
102 + }
103 +--
104 +2.5.2
105 +
106
107 diff --git a/net-nds/rpcbind/rpcbind-0.2.3-r1.ebuild b/net-nds/rpcbind/rpcbind-0.2.3-r1.ebuild
108 new file mode 100644
109 index 0000000..937aaae
110 --- /dev/null
111 +++ b/net-nds/rpcbind/rpcbind-0.2.3-r1.ebuild
112 @@ -0,0 +1,57 @@
113 +# Copyright 1999-2015 Gentoo Foundation
114 +# Distributed under the terms of the GNU General Public License v2
115 +# $Id$
116 +
117 +EAPI="5"
118 +
119 +inherit eutils systemd
120 +
121 +if [[ ${PV} == "9999" ]] ; then
122 + EGIT_REPO_URI="git://linux-nfs.org/~steved/rpcbind.git"
123 + inherit autotools git-r3
124 +else
125 + SRC_URI="mirror://sourceforge/${PN}/${P}.tar.bz2"
126 + KEYWORDS="~alpha ~amd64 ~arm ~arm64 ~hppa ~ia64 ~mips ~ppc ~ppc64 ~s390 ~sh ~sparc ~x86"
127 +fi
128 +
129 +DESCRIPTION="portmap replacement which supports RPC over various protocols"
130 +HOMEPAGE="http://sourceforge.net/projects/rpcbind/"
131 +
132 +LICENSE="BSD"
133 +SLOT="0"
134 +IUSE="debug selinux systemd tcpd warmstarts"
135 +
136 +CDEPEND=">=net-libs/libtirpc-0.2.3:=
137 + systemd? ( sys-apps/systemd:= )
138 + tcpd? ( sys-apps/tcp-wrappers )"
139 +DEPEND="${CDEPEND}
140 + virtual/pkgconfig"
141 +RDEPEND="${CDEPEND}
142 + selinux? ( sec-policy/selinux-rpcbind )"
143 +
144 +src_prepare() {
145 + [[ ${PV} == "9999" ]] && eautoreconf
146 + epatch "${FILESDIR}"/${P}-libtirpc.patch
147 + epatch "${FILESDIR}"/${P}-mem-corrupt.patch #560990
148 + epatch_user
149 +}
150 +
151 +src_configure() {
152 + econf \
153 + --bindir="${EPREFIX}"/sbin \
154 + --with-statedir="${EPREFIX}"/run/${PN} \
155 + --with-rpcuser=root \
156 + --with-systemdsystemunitdir=$(usex systemd "$(systemd_get_unitdir)" "no") \
157 + $(use_enable tcpd libwrap) \
158 + $(use_enable debug) \
159 + $(use_enable warmstarts)
160 +}
161 +
162 +src_install() {
163 + default
164 +
165 + newinitd "${FILESDIR}"/${PN}.initd ${PN}
166 + newconfd "${FILESDIR}"/${PN}.confd ${PN}
167 +
168 + systemd_dounit "${FILESDIR}"/${PN}.service
169 +}