From patchwork Thu Dec 14 00:47:52 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: andrey.konovalov@linux.dev X-Patchwork-Id: 13492154 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from kanga.kvack.org (kanga.kvack.org [205.233.56.17]) by smtp.lore.kernel.org (Postfix) with ESMTP id 2F561C4167B for ; Thu, 14 Dec 2023 00:48:05 +0000 (UTC) Received: by kanga.kvack.org (Postfix) id 249228D0080; Wed, 13 Dec 2023 19:48:04 -0500 (EST) Received: by kanga.kvack.org (Postfix, from userid 40) id F3B178D0084; Wed, 13 Dec 2023 19:48:03 -0500 (EST) X-Delivered-To: int-list-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix, from userid 63042) id DB1978D0083; Wed, 13 Dec 2023 19:48:03 -0500 (EST) X-Delivered-To: linux-mm@kvack.org Received: from relay.hostedemail.com (smtprelay0012.hostedemail.com [216.40.44.12]) by kanga.kvack.org (Postfix) with ESMTP id CABEE8D0080 for ; Wed, 13 Dec 2023 19:48:03 -0500 (EST) Received: from smtpin07.hostedemail.com (a10.router.float.18 [10.200.18.1]) by unirelay02.hostedemail.com (Postfix) with ESMTP id 9C9F31208B4 for ; Thu, 14 Dec 2023 00:48:03 +0000 (UTC) X-FDA: 81563586846.07.1A70F37 Received: from out-177.mta1.migadu.com (out-177.mta1.migadu.com [95.215.58.177]) by imf17.hostedemail.com (Postfix) with ESMTP id D7F8B40004 for ; Thu, 14 Dec 2023 00:48:01 +0000 (UTC) Authentication-Results: imf17.hostedemail.com; dkim=pass header.d=linux.dev header.s=key1 header.b=ukeh5H64; dmarc=pass (policy=none) header.from=linux.dev; spf=pass (imf17.hostedemail.com: domain of andrey.konovalov@linux.dev designates 95.215.58.177 as permitted sender) smtp.mailfrom=andrey.konovalov@linux.dev ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=hostedemail.com; s=arc-20220608; t=1702514882; h=from:from:sender:reply-to:subject:subject:date:date: message-id:message-id:to:to:cc:cc:mime-version:mime-version: content-type:content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references:dkim-signature; bh=8YssiUYIuDBfUgViHa8UWZbb+o2fPyHhfOU9iGYPOo4=; b=wzHYdFrD4xlZa3bOMt8VbPjtexvajmEgyu5FeKIUvjPurdz93/KKfFDWUrl/zGqoxZhfLi A+lWrSnJmES6MHntIFoNkqDFGbrbEa3tPg3wX1f9NXtRPgjCZRNasgBNzzJZX1r3yoG40T QkBCHOtZAF6H2AiQ81cjkTmnfrZ05Sc= ARC-Authentication-Results: i=1; imf17.hostedemail.com; dkim=pass header.d=linux.dev header.s=key1 header.b=ukeh5H64; dmarc=pass (policy=none) header.from=linux.dev; spf=pass (imf17.hostedemail.com: domain of andrey.konovalov@linux.dev designates 95.215.58.177 as permitted sender) smtp.mailfrom=andrey.konovalov@linux.dev ARC-Seal: i=1; s=arc-20220608; d=hostedemail.com; t=1702514882; a=rsa-sha256; cv=none; b=jMLMKqIp+fJ2bfVUoFrHy3cIG+sFF8eKLzazqeu93tL7U0SpgbYyLVpJu3VFnBNqKUbiE1 tIiJSm13j6wL8opnQhIPqXJfl5AS8ORwfKCO1s/ynObxlrB9Sbx/XdFqCyMPOPl9sKcbCt qndIo2O7HrVASWql3Az1R+xjcPhta/A= X-Report-Abuse: Please report any abuse attempt to abuse@migadu.com and include these headers. DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linux.dev; s=key1; t=1702514880; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=8YssiUYIuDBfUgViHa8UWZbb+o2fPyHhfOU9iGYPOo4=; b=ukeh5H64ggk42fU3s6NTf9eHd2GIMqqgZ/CqDcfXQdJSfR4jhY5GxkoRPyps3uU323JLgZ TniRsk/5uPbcuJZvJRywDrgPNugzxiX76SI4CJMOmkh/ZLwplUIxY/5qcBKDt2czbq/Gkx jFr5MxIf7T+y9Q0QrUq8z27yYq8OoyQ= From: andrey.konovalov@linux.dev To: Andrew Morton Cc: Andrey Konovalov , Marco Elver , Alexander Potapenko , Dmitry Vyukov , Vlastimil Babka , kasan-dev@googlegroups.com, Evgenii Stepanov , Tetsuo Handa , linux-mm@kvack.org, linux-kernel@vger.kernel.org, Andrey Konovalov , syzbot+186b55175d8360728234@syzkaller.appspotmail.com Subject: [PATCH -v2 mm 2/4] kasan: handle concurrent kasan_record_aux_stack calls Date: Thu, 14 Dec 2023 01:47:52 +0100 Message-Id: <88fc85e2a8cca03f2bfcae76100d1a3d54eac840.1702514411.git.andreyknvl@google.com> In-Reply-To: References: MIME-Version: 1.0 X-Migadu-Flow: FLOW_OUT X-Rspamd-Queue-Id: D7F8B40004 X-Rspam-User: X-Rspamd-Server: rspam05 X-Stat-Signature: yy9j1ykci8ggjd4w86odgmtth4yejwn8 X-HE-Tag: 1702514881-684051 X-HE-Meta: U2FsdGVkX1/DB862sgUfOEHOpcaojHkpSFB8+GX91FTK5xhHAe8HlQDe4UtuII3t4AQroR5QIVngCYOVFCuBaWlFiOUdPpCeYnb8amLUCS5yXI4Yexg2nKc8wvIjDksmbFFhh5tlv7OdCd0SVsiS0om3vVfG0z/uTes3DuQ/NC5v8ScaLghPIkSJ8LIV6rdRwnl0DDAb5ELzu5m9XtMB0PSmIXOz6/m+epouTExt6CurXPPGrDegRMJ+/EvW0CUfQHEKj6rmB3vC4WYaXXbbzexmK/voEg4S872NC5TewprPmK/tIurf/6JlxwwKuETz8eOQ3KFG1pr/7GziteShLuUs9SlvuFku9jMJmEgQO2Y/qKJCQs1rnbHkY621csWdDBsj6CxggfH4H0hNvNUC/eFKnYmu4+DYw9Tv7BVoNAjb7Egn9FzMJ1k4Wiunn6g8JeEM/6ck79PtZDDRyT9Thm+m9+8culgx3a0DFdy4obvq6XJSjZHk4/MiOk5r2Kz25uPNzIx5+IqRpkbDB0rLF99necqB6Me25oyyA6Jg4N85lcwFNbisCiV6OR1azNi+XUVtZTc7hS/PiBCnNtLyum93EYbQuj2cFwZu/O4a6wZABcqoIYva99dhjQyRUrCtxthwauE4xQWAE9BkBt3PUHgOS4Rsty8XiFMAOeca68VNHmwIakwmlnS/e3+wDeRhg1bFCsuu12W/fvUcIci5iAaeRpDj3vdcw/OXeF4UZYDVfOkRTCtVCsENT3JfvP/sJfCqPu2IwG+5BvZTyAGg4/ejnwnQmoUMQ1VdXR87HRHpbwH2ZZJIo/V1G61+2ejQapDXxj7lAfWLRIeYOkmwVAfXIbt+f+QDUU8H0t3V6sMgiOEuj3+ONSrp2aAI/YMS3J2oRbNYB6MFswcSNvlyKuCW0njsUP89epSdsoL+WZGm8CNJb0/c1R4rmmMK7WW9QZEPJwCT80J0H/uFSO/ poqW5abY 4BeZhHXrrILC9ONO6lrHs31Te2ardSQFTeQNWTmd/44qlkWuf76tVT6cARfLiYIrqKLSuoe1WiqTI0VvhSEqx8W38vg706rYTAYxjladCsOgUM5C1YYDp0WL8oF6E8an3vzgNGFWvqZgmGE+0WEOaMGt3jg7/WYiy1p2BGClERNA5dFLquMKfWu88n9EPgECGdWe8VItVrOMiUDORvNp5HyvyUiM0bD9gwYx90kh+SSSt6u0x0dLD+slUJWXfeDbIKMt/eXOuCSd5vPDahERIReDsvQS+ljH6CZ5aoHUVK/Jr2noIBDWYz3vqhzyrleFzRH29c/q7LJvSC+c= 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: List-Subscribe: List-Unsubscribe: From: Andrey Konovalov kasan_record_aux_stack can be called concurrently on the same object. This might lead to a race condition when rotating the saved aux stack trace handles, which in turns leads to incorrect accounting of stack depot handles and refcount underflows in the stack depot code. Fix by introducing a spinlock to protect the aux stack trace handles in kasan_record_aux_stack. Reported-by: Tetsuo Handa Reported-by: syzbot+186b55175d8360728234@syzkaller.appspotmail.com Closes: https://lore.kernel.org/all/000000000000784b1c060b0074a2@google.com/ Fixes: 773688a6cb24 ("kasan: use stack_depot_put for Generic mode") Signed-off-by: Andrey Konovalov --- Changes v1->v2: - Use per-object spinlock instead of a global one. --- mm/kasan/generic.c | 32 +++++++++++++++++++++++++++++--- mm/kasan/kasan.h | 2 ++ 2 files changed, 31 insertions(+), 3 deletions(-) diff --git a/mm/kasan/generic.c b/mm/kasan/generic.c index 54e20b2bc3e1..b9d41d6c70fd 100644 --- a/mm/kasan/generic.c +++ b/mm/kasan/generic.c @@ -25,6 +25,7 @@ #include #include #include +#include #include #include #include @@ -471,8 +472,18 @@ void kasan_init_object_meta(struct kmem_cache *cache, const void *object) struct kasan_free_meta *free_meta; alloc_meta = kasan_get_alloc_meta(cache, object); - if (alloc_meta) + if (alloc_meta) { __memset(alloc_meta, 0, sizeof(*alloc_meta)); + + /* + * Temporarily disable KASAN bug reporting to allow instrumented + * spin_lock_init to access aux_lock, which resides inside of a + * redzone. + */ + kasan_disable_current(); + spin_lock_init(&alloc_meta->aux_lock); + kasan_enable_current(); + } free_meta = kasan_get_free_meta(cache, object); if (free_meta) __memset(free_meta, 0, sizeof(*free_meta)); @@ -502,6 +513,8 @@ static void __kasan_record_aux_stack(void *addr, depot_flags_t depot_flags) struct kmem_cache *cache; struct kasan_alloc_meta *alloc_meta; void *object; + depot_stack_handle_t new_handle, old_handle; + unsigned long flags; if (is_kfence_address(addr) || !slab) return; @@ -512,9 +525,22 @@ static void __kasan_record_aux_stack(void *addr, depot_flags_t depot_flags) if (!alloc_meta) return; - stack_depot_put(alloc_meta->aux_stack[1]); + new_handle = kasan_save_stack(0, depot_flags); + + /* + * Temporarily disable KASAN bug reporting to allow instrumented + * spinlock functions to access aux_lock, which resides inside of a + * redzone. + */ + kasan_disable_current(); + spin_lock_irqsave(&alloc_meta->aux_lock, flags); + old_handle = alloc_meta->aux_stack[1]; alloc_meta->aux_stack[1] = alloc_meta->aux_stack[0]; - alloc_meta->aux_stack[0] = kasan_save_stack(0, depot_flags); + alloc_meta->aux_stack[0] = new_handle; + spin_unlock_irqrestore(&alloc_meta->aux_lock, flags); + kasan_enable_current(); + + stack_depot_put(old_handle); } void kasan_record_aux_stack(void *addr) diff --git a/mm/kasan/kasan.h b/mm/kasan/kasan.h index 5e298e3ac909..8b4125fecdc7 100644 --- a/mm/kasan/kasan.h +++ b/mm/kasan/kasan.h @@ -6,6 +6,7 @@ #include #include #include +#include #include #if defined(CONFIG_KASAN_SW_TAGS) || defined(CONFIG_KASAN_HW_TAGS) @@ -249,6 +250,7 @@ struct kasan_global { struct kasan_alloc_meta { struct kasan_track alloc_track; /* Free track is stored in kasan_free_meta. */ + spinlock_t aux_lock; depot_stack_handle_t aux_stack[2]; };