From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-14.4 required=3.0 tests=DKIMWL_WL_MED,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_PATCH, MAILING_LIST_MULTI,SIGNED_OFF_BY,SPF_HELO_NONE,SPF_PASS,USER_IN_DEF_DKIM_WL autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 6020AC432C0 for ; Fri, 29 Nov 2019 14:15:12 +0000 (UTC) Received: from kanga.kvack.org (kanga.kvack.org [205.233.56.17]) by mail.kernel.org (Postfix) with ESMTP id 11689208E4 for ; Fri, 29 Nov 2019 14:15:11 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b="ub/D3+zO" DMARC-Filter: OpenDMARC Filter v1.3.2 mail.kernel.org 11689208E4 Authentication-Results: mail.kernel.org; dmarc=fail (p=reject dis=none) header.from=google.com Authentication-Results: mail.kernel.org; spf=pass smtp.mailfrom=owner-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix) id 9F2C36B058F; Fri, 29 Nov 2019 09:15:11 -0500 (EST) Received: by kanga.kvack.org (Postfix, from userid 40) id 9C7696B0590; Fri, 29 Nov 2019 09:15:11 -0500 (EST) X-Delivered-To: int-list-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix, from userid 63042) id 8DEEB6B0591; Fri, 29 Nov 2019 09:15:11 -0500 (EST) X-Delivered-To: linux-mm@kvack.org Received: from forelay.hostedemail.com (smtprelay0067.hostedemail.com [216.40.44.67]) by kanga.kvack.org (Postfix) with ESMTP id 78D716B058F for ; Fri, 29 Nov 2019 09:15:11 -0500 (EST) Received: from smtpin02.hostedemail.com (10.5.19.251.rfc1918.com [10.5.19.251]) by forelay03.hostedemail.com (Postfix) with SMTP id 485928205A3A for ; Fri, 29 Nov 2019 14:15:11 +0000 (UTC) X-FDA: 76209512022.02.lock60_847dddce22105 X-HE-Tag: lock60_847dddce22105 X-Filterd-Recvd-Size: 12461 Received: from mail-pl1-f194.google.com (mail-pl1-f194.google.com [209.85.214.194]) by imf40.hostedemail.com (Postfix) with ESMTP for ; Fri, 29 Nov 2019 14:15:10 +0000 (UTC) Received: by mail-pl1-f194.google.com with SMTP id s10so12961682plp.2 for ; Fri, 29 Nov 2019 06:15:10 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20161025; h=mime-version:references:in-reply-to:from:date:message-id:subject:to :cc; bh=seUr3bMaonlRl+/kapD1cEAH5JfG0c/p/QInX2B5D54=; b=ub/D3+zOY/8qWBVy8ADiBpppKdzJJguSoSrD8FemLsRnTiOVPxBBFQdMIHHrMgXAB6 jaOcOxj1DAetTewBIcm+cKVZJJr6qUBXWpeXe7wy13P6vr9P1rOtbYs8ciBQD1mMPv0n Qa3e91d8QHxePHgFFX6MzCz24glH5e6e8+m/PpzpWGpsxXM2K4B7/FIMnrHIw+oeXk22 LFpPlFIrfCurs69141RSXx2CrNuYrIzCRcqFWm5eXtvPMpLqEtn8L39N6Q0AqZE0z7HD YPlWMc/dBZKR2RICpIQq04RrZLrtiiOvsi0xDFhnCULjS8TbXuNU3VYjGUwQGXXAnMg+ wBZw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:mime-version:references:in-reply-to:from:date :message-id:subject:to:cc; bh=seUr3bMaonlRl+/kapD1cEAH5JfG0c/p/QInX2B5D54=; b=p5WtlM6JYFO2O6OOl+/tfTwi9To/lAYQpX7wqLGA+9WP92kmx7z+UH9HASTXuJA33C m62JCGorqL0JlSxjoND3MmT9UAaaD7rNN2R81mJcw4++G5HyifZul0yw7ILoEPg6970E kPlaexmba4b7fJ9LB4yzxhoZvxZj92witp3SSn9feo7jkgqOTlOSknBwdgam7Ykjw0Fb f3MpFX62e6Gz4uId6n3txKlfFLOIiyLJn1XRQshorwxJo+IlbBPSSlMbBaHNppdJ8273 ZGtfFtSuDDI66ggRkoSn/Btbpdh1DXbtL9q2MYt04/MJD39M3oJdCy16AGrRuSbNaaNu zDZQ== X-Gm-Message-State: APjAAAUKbRuh9MsW/sO4WYUwLb1WlKkJCHmB3yrOLrVoflsTTHYv0k4B 7R8NKag5T+fenHVfZnY7k77bXMJOkIEc9tTtLSUzEw== X-Google-Smtp-Source: APXvYqxoUM2QQMpN+0NP70+hh/YA7E80ck4rBHRdKpJ5Xym77jL90g4rVRQPeEJ4YkyU5uOb9+/Sg1AFk/OpqUUjYmE= X-Received: by 2002:a17:90a:1f4b:: with SMTP id y11mr18770197pjy.123.1575036908796; Fri, 29 Nov 2019 06:15:08 -0800 (PST) MIME-Version: 1.0 References: <20191122112621.204798-1-glider@google.com> <20191122112621.204798-16-glider@google.com> In-Reply-To: <20191122112621.204798-16-glider@google.com> From: Andrey Konovalov Date: Fri, 29 Nov 2019 15:14:57 +0100 Message-ID: Subject: Re: [PATCH RFC v3 15/36] kmsan: add tests for KMSAN To: Alexander Potapenko Cc: Vegard Nossum , Dmitry Vyukov , Linux Memory Management List , Alexander Viro , Andreas Dilger , Andrew Morton , Andrey Ryabinin , Andy Lutomirski , Ard Biesheuvel , Arnd Bergmann , Christoph Hellwig , Christoph Hellwig , darrick.wong@oracle.com, "David S. Miller" , Dmitry Torokhov , ebiggers@google.com, Eric Dumazet , ericvh@gmail.com, Greg Kroah-Hartman , harry.wentland@amd.com, Herbert Xu , iii@linux.ibm.com, mingo@elte.hu, Jason Wang , axboe@kernel.dk, Marek Szyprowski , Marco Elver , Mark Rutland , "Martin K. Petersen" , Martin Schwidefsky , Matthew Wilcox , "Michael S . Tsirkin" , Michal Simek , pmladek@suse.com, Qian Cai , Randy Dunlap , Robin Murphy , sergey.senozhatsky@gmail.com, Steven Rostedt , Takashi Iwai , "Theodore Ts'o" , Thomas Gleixner , gor@linux.ibm.com, wsa@the-dreams.de Content-Type: text/plain; charset="UTF-8" X-Bogosity: Ham, tests=bogofilter, spamicity=0.000000, version=1.2.4 Sender: owner-linux-mm@kvack.org Precedence: bulk X-Loop: owner-majordomo@kvack.org List-ID: Archived-At: List-Archive: List-Post: On Fri, Nov 22, 2019 at 12:27 PM wrote: > > The initial commit adds several tests that trigger KMSAN warnings in > simple cases. > To use, build the kernel with CONFIG_TEST_KMSAN and do > `insmod test_kmsan.ko` > > Signed-off-by: Alexander Potapenko > To: Alexander Potapenko > Cc: Vegard Nossum > Cc: Dmitry Vyukov > Cc: linux-mm@kvack.org > --- > v2: > - added printk_test() > > Change-Id: I287e86ae83a82b770f2baa46e5bbdce1dfa65195 > --- > lib/Makefile | 1 + > lib/test_kmsan.c | 231 +++++++++++++++++++++++++++++++++++++++++++++++ > 2 files changed, 232 insertions(+) > create mode 100644 lib/test_kmsan.c > > diff --git a/lib/Makefile b/lib/Makefile > index 58a3e1b1a868..08fcb37499a0 100644 > --- a/lib/Makefile > +++ b/lib/Makefile > @@ -65,6 +65,7 @@ CFLAGS_test_kasan.o += $(call cc-disable-warning, vla) > obj-$(CONFIG_TEST_UBSAN) += test_ubsan.o > CFLAGS_test_ubsan.o += $(call cc-disable-warning, vla) > UBSAN_SANITIZE_test_ubsan.o := y > +obj-$(CONFIG_TEST_KMSAN) += test_kmsan.o > obj-$(CONFIG_TEST_KSTRTOX) += test-kstrtox.o > obj-$(CONFIG_TEST_LIST_SORT) += test_list_sort.o > obj-$(CONFIG_TEST_LKM) += test_module.o > diff --git a/lib/test_kmsan.c b/lib/test_kmsan.c > new file mode 100644 > index 000000000000..dcbe02adbdb0 > --- /dev/null > +++ b/lib/test_kmsan.c > @@ -0,0 +1,231 @@ > +// SPDX-License-Identifier: GPL-2.0 > +/* > + * Module for testing KMSAN. > + * > + * Copyright (C) 2017-2019 Google LLC > + * Author: Alexander Potapenko > + * > + * This program is free software; you can redistribute it and/or modify > + * it under the terms of the GNU General Public License version 2 as > + * published by the Free Software Foundation. > + * > + */ > + > +/* > + * Tests below use noinline and volatile to work around compiler optimizations > + * that may mask KMSAN bugs. > + */ > +#define pr_fmt(fmt) "kmsan test: %s : " fmt, __func__ > + > +#include > +#include > +#include > +#include > +#include > + > +#define CHECK(x) \ > + do { \ > + if (x) \ > + pr_info(#x " is true\n"); \ > + else \ > + pr_info(#x " is false\n"); \ > + } while (0) > + > +noinline void use_integer(int cond) > +{ > + CHECK(cond); > +} This function seems to be unused. > + > +int signed_sum3(int a, int b, int c) > +{ > + return a + b + c; > +} > + > +noinline void uninit_kmalloc_test(void) > +{ > + int *ptr; > + > + pr_info("-----------------------------\n"); > + pr_info("uninitialized kmalloc test (UMR report)\n"); > + ptr = kmalloc(sizeof(int), GFP_KERNEL); > + pr_info("kmalloc returned %p\n", ptr); > + CHECK(*ptr); > +} > +noinline void init_kmalloc_test(void) > +{ > + int *ptr; > + > + pr_info("-----------------------------\n"); > + pr_info("initialized kmalloc test (no reports)\n"); > + ptr = kmalloc(sizeof(int), GFP_KERNEL); > + memset(ptr, 0, sizeof(int)); > + pr_info("kmalloc returned %p\n", ptr); > + CHECK(*ptr); > +} > + > +noinline void init_kzalloc_test(void) > +{ > + int *ptr; > + > + pr_info("-----------------------------\n"); > + pr_info("initialized kzalloc test (no reports)\n"); > + ptr = kzalloc(sizeof(int), GFP_KERNEL); > + pr_info("kzalloc returned %p\n", ptr); > + CHECK(*ptr); > +} > + > +noinline void uninit_multiple_args_test(void) > +{ > + volatile int a; > + volatile char b = 3, c; > + > + pr_info("-----------------------------\n"); > + pr_info("uninitialized local passed to fn (UMR report)\n"); > + CHECK(signed_sum3(a, b, c)); > +} > + > +noinline void uninit_stack_var_test(void) > +{ > + int cond; > + > + pr_info("-----------------------------\n"); > + pr_info("uninitialized stack variable (UMR report)\n"); > + CHECK(cond); > +} > + > +noinline void init_stack_var_test(void) > +{ > + volatile int cond = 1; > + > + pr_info("-----------------------------\n"); > + pr_info("initialized stack variable (no reports)\n"); > + CHECK(cond); > +} > + > +noinline void two_param_fn_2(int arg1, int arg2) > +{ > + CHECK(arg1); > + CHECK(arg2); > +} > + > +noinline void one_param_fn(int arg) > +{ > + two_param_fn_2(arg, arg); > + CHECK(arg); > +} > + > +noinline void two_param_fn(int arg1, int arg2) > +{ > + int init = 0; > + > + one_param_fn(init); > + CHECK(arg1); > + CHECK(arg2); > +} > + > +void params_test(void) > +{ > + int uninit, init = 1; > + > + two_param_fn(uninit, init); > +} This one as well. > + > +noinline void do_uninit_local_array(char *array, int start, int stop) > +{ > + int i; > + volatile char uninit; > + > + for (i = start; i < stop; i++) > + array[i] = uninit; > +} > + > +noinline void uninit_kmsan_check_memory_test(void) > +{ > + volatile char local_array[8]; > + > + pr_info("-----------------------------\n"); > + pr_info("kmsan_check_memory() called on uninit local (UMR report)\n"); > + do_uninit_local_array((char *)local_array, 5, 7); > + > + kmsan_check_memory((char *)local_array, 8); > +} > + > +noinline void init_kmsan_vmap_vunmap_test(void) > +{ > + const int npages = 2; > + struct page *pages[npages]; > + void *vbuf; > + int i; > + > + pr_info("-----------------------------\n"); > + pr_info("pages initialized via vmap (no reports)\n"); > + > + for (i = 0; i < npages; i++) > + pages[i] = alloc_page(GFP_KERNEL); > + vbuf = vmap(pages, npages, VM_MAP, PAGE_KERNEL); > + memset(vbuf, 0xfe, npages * PAGE_SIZE); > + for (i = 0; i < npages; i++) > + kmsan_check_memory(page_address(pages[i]), PAGE_SIZE); > + > + if (vbuf) > + vunmap(vbuf); > + for (i = 0; i < npages; i++) > + if (pages[i]) > + __free_page(pages[i]); > +} > + > +noinline void init_vmalloc(void) > +{ > + char *buf; > + int npages = 8, i; > + > + pr_info("-----------------------------\n"); > + pr_info("pages initialized via vmap (no reports)\n"); > + buf = vmalloc(PAGE_SIZE * npages); > + buf[0] = 1; > + memset(buf, 0xfe, PAGE_SIZE * npages); > + CHECK(buf[0]); > + for (i = 0; i < npages; i++) > + kmsan_check_memory(&buf[PAGE_SIZE * i], PAGE_SIZE); > + vfree(buf); > +} > + > +noinline void uaf_test(void) > +{ > + volatile int *var; > + > + pr_info("-----------------------------\n"); > + pr_info("use-after-free in kmalloc-ed buffer (UMR report)\n"); > + var = kmalloc(80, GFP_KERNEL); > + var[3] = 0xfeedface; > + kfree((int *)var); > + CHECK(var[3]); > +} > + > +noinline void printk_test(void) > +{ > + volatile int uninit; > + > + pr_info("-----------------------------\n"); > + pr_info("uninit local passed to pr_info() (UMR report)\n"); > + pr_info("%px contains %d\n", &uninit, uninit); > +} > + > +static noinline int __init kmsan_tests_init(void) > +{ > + uninit_kmalloc_test(); > + init_kmalloc_test(); > + init_kzalloc_test(); > + uninit_multiple_args_test(); > + uninit_stack_var_test(); > + init_stack_var_test(); > + uninit_kmsan_check_memory_test(); > + init_kmsan_vmap_vunmap_test(); > + init_vmalloc(); Perhaps s/init_vmalloc/init_vmalloc_test? > + uaf_test(); > + printk_test(); > + return -EAGAIN; > +} > + > +module_init(kmsan_tests_init); > +MODULE_LICENSE("GPL"); > -- > 2.24.0.432.g9d3f5f5b63-goog >