From patchwork Fri Sep 10 21:13:56 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Collingbourne X-Patchwork-Id: 12486057 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=-26.3 required=3.0 tests=BAYES_00,DKIMWL_WL_MED, DKIM_SIGNED,DKIM_VALID,DKIM_VALID_AU,HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_CR_TRAILER,INCLUDES_PATCH,MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS, USER_AGENT_GIT,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 3924EC433EF for ; Fri, 10 Sep 2021 21:14:07 +0000 (UTC) Received: from kanga.kvack.org (kanga.kvack.org [205.233.56.17]) by mail.kernel.org (Postfix) with ESMTP id BD020600D4 for ; Fri, 10 Sep 2021 21:14:06 +0000 (UTC) DMARC-Filter: OpenDMARC Filter v1.4.1 mail.kernel.org BD020600D4 Authentication-Results: mail.kernel.org; dmarc=fail (p=reject dis=none) header.from=google.com Authentication-Results: mail.kernel.org; spf=pass smtp.mailfrom=kvack.org Received: by kanga.kvack.org (Postfix) id 52D2A6B0071; Fri, 10 Sep 2021 17:14:06 -0400 (EDT) Received: by kanga.kvack.org (Postfix, from userid 40) id 4DBF9900002; Fri, 10 Sep 2021 17:14:06 -0400 (EDT) X-Delivered-To: int-list-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix, from userid 63042) id 3CCFB6B0073; Fri, 10 Sep 2021 17:14:06 -0400 (EDT) X-Delivered-To: linux-mm@kvack.org Received: from forelay.hostedemail.com (smtprelay0173.hostedemail.com [216.40.44.173]) by kanga.kvack.org (Postfix) with ESMTP id 2F3136B0071 for ; Fri, 10 Sep 2021 17:14:06 -0400 (EDT) Received: from smtpin35.hostedemail.com (10.5.19.251.rfc1918.com [10.5.19.251]) by forelay05.hostedemail.com (Postfix) with ESMTP id E9C01181EBA2A for ; Fri, 10 Sep 2021 21:14:05 +0000 (UTC) X-FDA: 78572916450.35.8304B35 Received: from mail-qt1-f201.google.com (mail-qt1-f201.google.com [209.85.160.201]) by imf29.hostedemail.com (Postfix) with ESMTP id 8E23D900024A for ; Fri, 10 Sep 2021 21:14:05 +0000 (UTC) Received: by mail-qt1-f201.google.com with SMTP id e8-20020a05622a110800b0029ecbdc1b2aso36397425qty.12 for ; Fri, 10 Sep 2021 14:14:05 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20210112; h=date:message-id:mime-version:subject:from:to:cc; bh=zI+eX0B08to4JdtZELlZxZOHyOJV5mDWBytuHVofZfk=; b=PByAfTxd87Sp+6BaR4EyWtbOGGW7Li66+JRzRjbk1vAE1B4kKv4pr8JzZRzBOsDLFV 6Ii+b9Ad0cFgwSQS7crffylQkO9YlzwEnHVIj4vcj9fuH5khf3q4XmH9TAvfferhlgYU olYcCEwo2KuSZytTpegjNY9QvG9DbR6JiezwD3zV4CIJA/Cve1wNXPPQDX6WkLozINQp Y5E3YVKqpO2gPx1BLaRMEoqCFBZ/fQjLm5djl666pIXTeGiw1sbKqYLzTS4M26rJKnSX L4cPRQq59C4dgUaXNJjn7QcJpNakrCXwznFvX5Ti6YucJFeI4+rCXrXyusRxFtqjBKv0 FhBQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; h=x-gm-message-state:date:message-id:mime-version:subject:from:to:cc; bh=zI+eX0B08to4JdtZELlZxZOHyOJV5mDWBytuHVofZfk=; b=uIBkwCXqwNkZb3TIZhKVX8I2vzLZk2etA59YKRna0ClZ6bMOq9ecIEbP1ubaqyRQNs NdEGMbqyu39yeAd1wG1K2kF/49o+vDO/wX3ffv1C90syMNsvt/kj21y0JGVobv7n3OFz /6/+keR94nXnEboSQ2ZN6cxuB5xM+X4FMhaKbmKdUbYNnNQpPkYMFBn4Wx7bDbkOpI2n A1okfAxEkRlT3vP4nkJO9KvX0/1MKrWhzN329B9PZJT+fbmjA99SJMCfY7LSN7nXXwYY V66y1fKm1AF9wjuLLq6kemzeE4YKCmybRjHkdBo3PgDcx2Dum29b982NoQOcVIFABSQm jWMg== X-Gm-Message-State: AOAM531XS5Us8Z760pQ6J3BlSHGZDrvZRiKo+zZ0oT2EaCruNwrP/ajh yug40E9z+JZZTEbDqYAmKo0WeVw= X-Google-Smtp-Source: ABdhPJzd24TkxLpkWrWYcJUC+t5TVumV6ZXoGGjEeu/XnKiSsp/KtZ8WyZErg7OfsTtObVVoxsuh3Mc= X-Received: from pcc-desktop.svl.corp.google.com ([2620:15c:2ce:200:90e5:d30e:ae0f:6c1]) (user=pcc job=sendgmr) by 2002:a05:6214:1501:: with SMTP id e1mr10688815qvy.62.1631308444780; Fri, 10 Sep 2021 14:14:04 -0700 (PDT) Date: Fri, 10 Sep 2021 14:13:56 -0700 Message-Id: <20210910211356.3603758-1-pcc@google.com> Mime-Version: 1.0 X-Mailer: git-send-email 2.33.0.309.g3052b89438-goog Subject: [PATCH v2] kasan: test: add memcpy test that avoids out-of-bounds write From: Peter Collingbourne To: Robin Murphy , Will Deacon , Catalin Marinas , Andrey Konovalov , Marco Elver Cc: Peter Collingbourne , Mark Rutland , Evgenii Stepanov , Alexander Potapenko , Linux ARM , linux-mm@kvack.org X-Rspamd-Server: rspam05 X-Rspamd-Queue-Id: 8E23D900024A X-Stat-Signature: qdjmqxzf5mg8pzr7t81p8ga1zpgp6qyi Authentication-Results: imf29.hostedemail.com; dkim=pass header.d=google.com header.s=20210112 header.b=PByAfTxd; spf=pass (imf29.hostedemail.com: domain of 3nMo7YQMKCDEcPPTbbTYR.PbZYVahk-ZZXiNPX.beT@flex--pcc.bounces.google.com designates 209.85.160.201 as permitted sender) smtp.mailfrom=3nMo7YQMKCDEcPPTbbTYR.PbZYVahk-ZZXiNPX.beT@flex--pcc.bounces.google.com; dmarc=pass (policy=reject) header.from=google.com X-HE-Tag: 1631308445-642373 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: With HW tag-based KASAN, error checks are performed implicitly by the load and store instructions in the memcpy implementation. A failed check results in tag checks being disabled and execution will keep going. As a result, under HW tag-based KASAN, prior to commit 1b0668be62cf ("kasan: test: disable kmalloc_memmove_invalid_size for HW_TAGS"), this memcpy would end up corrupting memory until it hits an inaccessible page and causes a kernel panic. This is a pre-existing issue that was revealed by commit 285133040e6c ("arm64: Import latest memcpy()/memmove() implementation") which changed the memcpy implementation from using signed comparisons (incorrectly, resulting in the memcpy being terminated early for negative sizes) to using unsigned comparisons. It is unclear how this could be handled by memcpy itself in a reasonable way. One possibility would be to add an exception handler that would force memcpy to return if a tag check fault is detected -- this would make the behavior roughly similar to generic and SW tag-based KASAN. However, this wouldn't solve the problem for asynchronous mode and also makes memcpy behavior inconsistent with manually copying data. This test was added as a part of a series that taught KASAN to detect negative sizes in memory operations, see commit 8cceeff48f23 ("kasan: detect negative size in memory operation function"). Therefore we should keep testing for negative sizes with generic and SW tag-based KASAN. But there is some value in testing small memcpy overflows, so let's add another test with memcpy that does not destabilize the kernel by performing out-of-bounds writes, and run it in all modes. Link: https://linux-review.googlesource.com/id/I048d1e6a9aff766c4a53f989fb0c83de68923882 Signed-off-by: Peter Collingbourne Reviewed-by: Andrey Konovalov Acked-by: Marco Elver --- lib/test_kasan.c | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/lib/test_kasan.c b/lib/test_kasan.c index 8835e0784578..aa8e42250219 100644 --- a/lib/test_kasan.c +++ b/lib/test_kasan.c @@ -493,7 +493,7 @@ static void kmalloc_oob_in_memset(struct kunit *test) kfree(ptr); } -static void kmalloc_memmove_invalid_size(struct kunit *test) +static void kmalloc_memmove_negative_size(struct kunit *test) { char *ptr; size_t size = 64; @@ -515,6 +515,21 @@ static void kmalloc_memmove_invalid_size(struct kunit *test) kfree(ptr); } +static void kmalloc_memmove_invalid_size(struct kunit *test) +{ + char *ptr; + size_t size = 64; + volatile size_t invalid_size = size; + + ptr = kmalloc(size, GFP_KERNEL); + KUNIT_ASSERT_NOT_ERR_OR_NULL(test, ptr); + + memset((char *)ptr, 0, 64); + KUNIT_EXPECT_KASAN_FAIL(test, + memmove((char *)ptr, (char *)ptr + 4, invalid_size)); + kfree(ptr); +} + static void kmalloc_uaf(struct kunit *test) { char *ptr; @@ -1129,6 +1144,7 @@ static struct kunit_case kasan_kunit_test_cases[] = { KUNIT_CASE(kmalloc_oob_memset_4), KUNIT_CASE(kmalloc_oob_memset_8), KUNIT_CASE(kmalloc_oob_memset_16), + KUNIT_CASE(kmalloc_memmove_negative_size), KUNIT_CASE(kmalloc_memmove_invalid_size), KUNIT_CASE(kmalloc_uaf), KUNIT_CASE(kmalloc_uaf_memset),