From patchwork Tue Mar 21 16:14:27 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Alexander Potapenko X-Patchwork-Id: 741649 X-Patchwork-Delegate: davem@davemloft.net Return-Path: X-Original-To: patchwork-incoming@ozlabs.org Delivered-To: patchwork-incoming@ozlabs.org Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id 3vndF440DDz9s7l for ; Wed, 22 Mar 2017 03:14:48 +1100 (AEDT) Authentication-Results: ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=google.com header.i=@google.com header.b="G8mRLeuu"; dkim-atps=neutral Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S933292AbdCUQOq (ORCPT ); Tue, 21 Mar 2017 12:14:46 -0400 Received: from mail-wr0-f169.google.com ([209.85.128.169]:35999 "EHLO mail-wr0-f169.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S933138AbdCUQOp (ORCPT ); Tue, 21 Mar 2017 12:14:45 -0400 Received: by mail-wr0-f169.google.com with SMTP id u108so115075203wrb.3 for ; Tue, 21 Mar 2017 09:14:39 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20161025; h=from:to:cc:subject:date:message-id; bh=avb8cZrulegQ90faz5VF9LGyu2nTN+jJSJEVhTU7W84=; b=G8mRLeuufTSXu85AG9pLX4XXJgzHrmwheDGl/Ag9xPvTipk5T137IgkHF1nMXM7xCa GtLGD8xKMk31dLuWgt0JV7WuidaYt9KxPo87W4vnoUIkAeiEsDiDWl1kNbOHKWSNBsbE Ys3n6n0tEl5RjWDV/zIgGg24Yu5O4eg+MUXj/oMPgpFv8n096J5pG6dEyfiLpcYLae6k YKvx/dIeVP5vIpiQigKOIslH2kTlqoMEb0yLPxIkb94ZNOC5p7Y7XNoehAwF8E1tGape qAnHfEfS7MSvY2lcl9j9Zy6iLWkIz2yTbxL6Pd377I5cDoYoTykMgDwa4cyDzez5zX98 L28Q== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id; bh=avb8cZrulegQ90faz5VF9LGyu2nTN+jJSJEVhTU7W84=; b=QBKd87F8Bnrz7Z26XfuZsfS3axGcoEldvgZMLGBga4l4KEVwREAwzZJY3OViL4SR45 b1aAZ28g/Qjq7FI/I6kgytqdzWjJF+MTCOQlOyyxJYozcT0sPdgRkIIKI64b1k5BI6NT xf1XewxbW0vDw+9lQCx/FVR7pTdCjAV0xY3yClDdIvkWzkxmyMqmMRGTJ7T3cVPTYdY5 j+G9xahIOb1TrFh8n2NfM5FL+zm33fadjpOnQzcCt4AKz1rHVTmXS9Y9y98qJYv2KFn/ 4VEsfStLPsZ/WTDeVxwboOSbxsk2ape5wP63x80dwrtoLGb16lHe80tAuOiDfNMf9Q5b aQMw== X-Gm-Message-State: AFeK/H0bltKvJE+vO9csjO+jjqutgUOC9yExXGWGgT19lMWKBRfyMzK/ycFz8x2H2xPvAKNH X-Received: by 10.223.166.244 with SMTP id t107mr30643663wrc.80.1490112872276; Tue, 21 Mar 2017 09:14:32 -0700 (PDT) Received: from glider0.muc.corp.google.com ([100.105.28.21]) by smtp.gmail.com with ESMTPSA id o15sm18207020wmd.10.2017.03.21.09.14.30 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Tue, 21 Mar 2017 09:14:31 -0700 (PDT) From: Alexander Potapenko To: dvyukov@google.com, kcc@google.com, edumazet@google.com, davem@davemloft.net, soheil@google.com, kuznet@ms2.inr.ac.ru Cc: linux-kernel@vger.kernel.org, netdev@vger.kernel.org Subject: [PATCH] ipv6: make sure to initialize sockc.tsflags before first use Date: Tue, 21 Mar 2017 17:14:27 +0100 Message-Id: <20170321161427.103713-1-glider@google.com> X-Mailer: git-send-email 2.12.1.500.gab5fba24ee-goog Sender: netdev-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org In the case udp_sk(sk)->pending is AF_INET6, udpv6_sendmsg() would jump to do_append_data, skipping the initialization of sockc.tsflags. Fix the problem by moving sockc.tsflags initialization earlier. The bug was detected with KMSAN. Signed-off-by: Alexander Potapenko Acked-by: Soheil Hassas Yeganeh --- For the record, here is the KMSAN report: ================================================================== BUG: KMSAN: use of unitialized memory CPU: 0 PID: 1027 Comm: udpv6_sendmsg Not tainted 4.8.0-rc6+ #2041 Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS Bochs 01/01/2011 0000000000000000 ffff88010c17f1a8 ffffffff825b5098 ffff88010c17f0e8 0000000000000000 ffffffff85bae870 0000000000000092 ffffffff85bae550 0000000000000000 0000000000000092 0000000000000000 0000000000000002 Call Trace: [< inline >] __dump_stack lib/dump_stack.c:15 [] dump_stack+0x238/0x290 lib/dump_stack.c:51 [] kmsan_report+0x180/0x210 mm/kmsan/kmsan.c:1022 [] __msan_warning+0x8a/0x100 mm/kmsan/kmsan_instr.c:431 [< inline >] sock_tx_timestamp ./include/net/sock.h:2162 [] __ip6_append_data+0x52e0/0x6160 net/ipv6/ip6_output.c:1336 [] ip6_append_data+0x453/0x750 net/ipv6/ip6_output.c:1599 [] udpv6_sendmsg+0x10f2/0x47f0 net/ipv6/udp.c:1261 [] inet_sendmsg+0x64e/0x930 net/ipv4/af_inet.c:740 [< inline >] sock_sendmsg_nosec net/socket.c:609 [< inline >] sock_sendmsg net/socket.c:619 [] ___sys_sendmsg+0xe10/0x14e0 net/socket.c:1943 [] __sys_sendmmsg+0x4ac/0x880 net/socket.c:2033 [] SYSC_sendmmsg+0xb8/0x130 net/socket.c:2062 [] SyS_sendmmsg+0x95/0xc0 net/socket.c:2057 [] do_syscall_64+0x58/0x70 arch/x86/entry/common.c:292 [] entry_SYSCALL64_slow_path+0x25/0x25 arch/x86/entry/entry_64.o:? chained origin: 00000000922009b8 [] save_stack_trace+0x27/0x50 arch/x86/kernel/stacktrace.c:67 [< inline >] kmsan_save_stack_with_flags mm/kmsan/kmsan.c:349 [< inline >] kmsan_save_stack mm/kmsan/kmsan.c:364 [] kmsan_internal_chain_origin+0x12e/0x1f0 mm/kmsan/kmsan.c:581 [] __msan_set_alloca_origin4+0xdc/0x160 mm/kmsan/kmsan_instr.c:386 [] udpv6_sendmsg+0x2e8/0x47f0 net/ipv6/udp.c:1014 [] inet_sendmsg+0x64e/0x930 net/ipv4/af_inet.c:740 [< inline >] sock_sendmsg_nosec net/socket.c:609 [< inline >] sock_sendmsg net/socket.c:619 [] ___sys_sendmsg+0xe10/0x14e0 net/socket.c:1943 [] __sys_sendmmsg+0x4ac/0x880 net/socket.c:2033 [] SYSC_sendmmsg+0xb8/0x130 net/socket.c:2062 [] SyS_sendmmsg+0x95/0xc0 net/socket.c:2057 [] do_syscall_64+0x58/0x70 arch/x86/entry/common.c:292 [] return_from_SYSCALL_64+0x0/0x6a arch/x86/entry/entry_64.o:? origin description: ----sockc@udpv6_sendmsg (origin=000000009e8009b7) ================================================================== and the reproducer that triggers it: ================================================================== #define _GNU_SOURCE #include #include int main() { int sock = socket(PF_INET6, SOCK_DGRAM, IPPROTO_IP); struct sockaddr_in6 addr; memset(&addr, 0, sizeof(struct sockaddr_in6)); addr.sin6_family = AF_INET6; addr.sin6_port = htons(20000); inet_pton(AF_INET6, "ffff:0:400::", &addr.sin6_addr); struct msghdr msg; memset(&msg, 0, sizeof(struct msghdr)); msg.msg_name = &addr; msg.msg_namelen = sizeof(struct sockaddr_in6); sendmsg(sock, &msg, MSG_DONTROUTE|MSG_MORE); struct mmsghdr mmsg; memset(&mmsg, 0, sizeof(struct mmsghdr)); sendmmsg(sock, &mmsg, 1, 0); return 0; } ================================================================== --- net/ipv6/udp.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/ipv6/udp.c b/net/ipv6/udp.c index 4e4c401e3bc6..e28082f0a307 100644 --- a/net/ipv6/udp.c +++ b/net/ipv6/udp.c @@ -1035,6 +1035,7 @@ int udpv6_sendmsg(struct sock *sk, struct msghdr *msg, size_t len) ipc6.hlimit = -1; ipc6.tclass = -1; ipc6.dontfrag = -1; + sockc.tsflags = sk->sk_tsflags; /* destination address check */ if (sin6) { @@ -1159,7 +1160,6 @@ int udpv6_sendmsg(struct sock *sk, struct msghdr *msg, size_t len) fl6.flowi6_mark = sk->sk_mark; fl6.flowi6_uid = sk->sk_uid; - sockc.tsflags = sk->sk_tsflags; if (msg->msg_controllen) { opt = &opt_space;