Received: by 10.223.164.221 with SMTP id h29csp1946987wrb; Thu, 2 Nov 2017 03:33:35 -0700 (PDT) X-Google-Smtp-Source: ABhQp+SBEHYvgp7U43Hds+VaWe4QqEu1RnIgayEmRa8Pw8iU6PcZ45Q1Vk5XsGeN9oD59if14luy X-Received: by 10.99.164.81 with SMTP id c17mr3135311pgp.112.1509618815315; Thu, 02 Nov 2017 03:33:35 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1509618815; cv=none; d=google.com; s=arc-20160816; b=i/D0wnHpzB/4CaKzsehqlUxyIpW59riX93DMZNhCMl3hRACTsa7RDKefj3ULeJ6MgU K38HrCae0pyo2wMl0PlbNsCfJp/pa9/SWgvp2fE3ip9jRPshxZ0eD35usMnjgcIxoNnO XPTtezaMAVYwA2Z0d+boL6xzZHCE3AD+KoVjhpydFj3zdxeeJ6iFS1JHvMZghhJfx732 dUfUzRsX9IZ/sS1+n7HkRaFPNvvFZZ0URy3VTzAWi3ZxkdXQzhVbzA53sESbLRc0o7MX 4KvfCHBEcdMuGA2Cxdbtyxkss5VrPP8cEaNI3F08yFPHF2TSlzmdYW0PhTVAVEPnUuip Rg8w== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:sender:user-agent:in-reply-to :content-disposition:mime-version:references:message-id:subject:cc :to:from:date:arc-authentication-results; bh=NuGQsraFqrbm9lFU0BOKLq1aGyH9Or0aiSUotOtZnTU=; b=GhgTZs0ZPmkFSqO5AliAyKceTPQFutMZZv8dyq61mW5MP7P1owiwRPVtQmwUAYc2sg +2jzlUS6lm9jGpM9Grbg1l8F5CxNXocnQ+a60rBLmj86z2J+n9GozCz3ltI6GxgDpBxm eNqw2Kg64gkRt2PUbpd1kJLobthgdNx2uwad+0l8luVAo40267jBsHInAM114C8DN0hW APu8Hq4Ok19sfAwNnzDSIW6BDp//UiDbmeJGrNMsuYZHQI2AHmEPBd4J31xeNz4aCRnK 51/NBPNfh4/FOJyUlvgcI5u9h1cpKtjZhpO0ztLY/n3Vh7TbrNiASxo9mWc2zApMqkN3 ooCg== ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id h184si3157230pgc.784.2017.11.02.03.33.21; Thu, 02 Nov 2017 03:33:35 -0700 (PDT) Received-SPF: pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) client-ip=209.132.180.67; Authentication-Results: mx.google.com; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1755475AbdKBKcn (ORCPT + 99 others); Thu, 2 Nov 2017 06:32:43 -0400 Received: from a.mx.secunet.com ([62.96.220.36]:35418 "EHLO a.mx.secunet.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1752632AbdKBKcl (ORCPT ); Thu, 2 Nov 2017 06:32:41 -0400 Received: from localhost (localhost [127.0.0.1]) by a.mx.secunet.com (Postfix) with ESMTP id 346A6201DA; Thu, 2 Nov 2017 11:32:40 +0100 (CET) X-Virus-Scanned: by secunet Received: from a.mx.secunet.com ([127.0.0.1]) by localhost (a.mx.secunet.com [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id moC9RepP1JQY; Thu, 2 Nov 2017 11:32:38 +0100 (CET) Received: from mail-essen-01.secunet.de (mail-essen-01.secunet.de [10.53.40.204]) (using TLSv1 with cipher ECDHE-RSA-AES256-SHA (256/256 bits)) (No client certificate requested) by a.mx.secunet.com (Postfix) with ESMTPS id E4F36201D4; Thu, 2 Nov 2017 11:32:38 +0100 (CET) Received: from gauss2.secunet.de (10.182.7.193) by mail-essen-01.secunet.de (10.53.40.204) with Microsoft SMTP Server id 14.3.361.1; Thu, 2 Nov 2017 11:32:38 +0100 Received: by gauss2.secunet.de (Postfix, from userid 1000) id E114114031E; Thu, 2 Nov 2017 11:32:37 +0100 (CET) Date: Thu, 2 Nov 2017 11:32:37 +0100 From: Steffen Klassert To: Florian Westphal CC: syzbot , , , , , , Subject: Re: KASAN: stack-out-of-bounds Read in xfrm_state_find (2) Message-ID: <20171102103237.GL11292@secunet.com> References: <20171101220608.GA9424@breakpoint.cc> MIME-Version: 1.0 Content-Type: text/plain; charset="us-ascii" Content-Disposition: inline In-Reply-To: <20171101220608.GA9424@breakpoint.cc> User-Agent: Mutt/1.5.24 (2015-08-30) X-G-Data-MailSecurity-for-Exchange-State: 0 X-G-Data-MailSecurity-for-Exchange-Error: 0 X-G-Data-MailSecurity-for-Exchange-Sender: 23 X-G-Data-MailSecurity-for-Exchange-Server: d65e63f7-5c15-413f-8f63-c0d707471c93 X-EXCLAIMER-MD-CONFIG: 2c86f778-e09b-4440-8b15-867914633a10 X-G-Data-MailSecurity-for-Exchange-Guid: A22275C0-D3B9-472E-BE98-CEAF0F44F328 Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org On Wed, Nov 01, 2017 at 11:06:08PM +0100, Florian Westphal wrote: > syzbot wrote: > > [ cc Thomas Egerer ] > > > syzkaller hit the following crash on > > 36ef71cae353f88fd6e095e2aaa3e5953af1685d > > git://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git/master > > compiler: gcc (GCC) 7.1.1 20170620 > > .config is attached > > Raw console output is attached. > > C reproducer is attached > > syzkaller reproducer is attached. See https://goo.gl/kgGztJ > > for information about syzkaller reproducers > > > > BUG: KASAN: stack-out-of-bounds in xfrm_state_find+0x303d/0x3170 > > net/xfrm/xfrm_state.c:1051 > > Read of size 4 at addr ffff88003adb7760 by task syzkaller429801/2969 > > Seems this was added in > commit 8444cf712c5f71845cba9dc30d8f530ff0d5ff83 > ("xfrm: Allow different selector family in temporary state"). > > No idea how to fix this: > > struct xfrm_state * > xfrm_state_find(const xfrm_address_t *daddr, const xfrm_address_t *saddr, > const struct flowi *fl, struct xfrm_tmpl *tmpl, > struct xfrm_policy *pol, int *err, > unsigned short family) // AF_INET > { > [..] > unsigned short encap_family = tmpl->encap_family; // AF_INET6 > [..] > h = xfrm_dst_hash(net, daddr, saddr, tmpl->reqid, encap_family); > > saddr, daddr point to ipv4 addresses inside an on-stack flowi4 struct, > i.e. they get hashed as ipv6 addresses which then results in invalid stack access. This looks like yet another IPv4 mapped IPv6 address + socket policy bug. > > What is this supposed to do if family != encap_family? This is the case for interfamily tunnels. Here family is the address family of the inner packet and encap_family is the address family for the outer one. > > I also don't understand how address comparision is supposed to work in this case, > it seems that if saddr/daddr are v4 and template v6 we compare full ipv6 addresses > (how would that succeed...?) and, if saddr/daddr is v6 add template is v4 we just > compare the first 32bit of the ipv6 addresses...? When we do tunnel or beet mode, we pass saddr and daddr from the template to xfrm_state_find(), this should be ok. On transport mode, we pass the addresses from the flowi, assuming that the IP addresses (and address family) don't change during transformation. This assumption is wrong in the IPv4 mapped IPv6 case, packet is IPv4 and template is IPv6. I'd propose to use the addresses from the template unconditionally, like the (untested) patch below does. Unfortunalely the reproducer does not work with my config, sendto returns EAGAIN. Could anybody try this patch? --- net/xfrm/xfrm_policy.c | 29 +++++++++++------------------ 1 file changed, 11 insertions(+), 18 deletions(-) diff --git a/net/xfrm/xfrm_policy.c b/net/xfrm/xfrm_policy.c index 4838329..450bdff 100644 --- a/net/xfrm/xfrm_policy.c +++ b/net/xfrm/xfrm_policy.c @@ -1360,36 +1360,29 @@ xfrm_tmpl_resolve_one(struct xfrm_policy *policy, const struct flowi *fl, struct net *net = xp_net(policy); int nx; int i, error; - xfrm_address_t *daddr = xfrm_flowi_daddr(fl, family); - xfrm_address_t *saddr = xfrm_flowi_saddr(fl, family); xfrm_address_t tmp; for (nx = 0, i = 0; i < policy->xfrm_nr; i++) { struct xfrm_state *x; - xfrm_address_t *remote = daddr; - xfrm_address_t *local = saddr; + xfrm_address_t *local; + xfrm_address_t *remote; struct xfrm_tmpl *tmpl = &policy->xfrm_vec[i]; - if (tmpl->mode == XFRM_MODE_TUNNEL || - tmpl->mode == XFRM_MODE_BEET) { - remote = &tmpl->id.daddr; - local = &tmpl->saddr; - if (xfrm_addr_any(local, tmpl->encap_family)) { - error = xfrm_get_saddr(net, fl->flowi_oif, - &tmp, remote, - tmpl->encap_family, 0); - if (error) - goto fail; - local = &tmp; - } + remote = &tmpl->id.daddr; + local = &tmpl->saddr; + if (xfrm_addr_any(local, tmpl->encap_family)) { + error = xfrm_get_saddr(net, fl->flowi_oif, + &tmp, remote, + tmpl->encap_family, 0); + if (error) + goto fail; + local = &tmp; } x = xfrm_state_find(remote, local, fl, tmpl, policy, &error, family); if (x && x->km.state == XFRM_STATE_VALID) { xfrm[nx++] = x; - daddr = remote; - saddr = local; continue; } if (x) { -- 2.7.4 From 1582903133403908144@xxx Wed Nov 01 22:07:43 +0000 2017 X-GM-THRID: 1582886692223881834 X-Gmail-Labels: Inbox,Category Forums,HistoricalUnread