From patchwork Tue Mar 28 23:49:54 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Yuxuan Luo X-Patchwork-Id: 1762521 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=lists.ubuntu.com (client-ip=91.189.94.19; helo=huckleberry.canonical.com; envelope-from=kernel-team-bounces@lists.ubuntu.com; receiver=) Authentication-Results: legolas.ozlabs.org; dkim=fail reason="signature verification failed" (2048-bit key; unprotected) header.d=canonical.com header.i=@canonical.com header.a=rsa-sha256 header.s=20210705 header.b=Ewu9Q8JS; dkim-atps=neutral Received: from huckleberry.canonical.com (huckleberry.canonical.com [91.189.94.19]) (using TLSv1.2 with cipher ECDHE-ECDSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4PmRJ76BwTz1yYb for ; Wed, 29 Mar 2023 10:50:14 +1100 (AEDT) Received: from localhost ([127.0.0.1] helo=huckleberry.canonical.com) by huckleberry.canonical.com with esmtp (Exim 4.86_2) (envelope-from ) id 1phJ4m-0006zL-45; Tue, 28 Mar 2023 23:50:04 +0000 Received: from smtp-relay-internal-0.internal ([10.131.114.225] helo=smtp-relay-internal-0.canonical.com) by huckleberry.canonical.com with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.86_2) (envelope-from ) id 1phJ4i-0006xT-4S for kernel-team@lists.ubuntu.com; Tue, 28 Mar 2023 23:50:00 +0000 Received: from mail-qk1-f198.google.com (mail-qk1-f198.google.com [209.85.222.198]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) by smtp-relay-internal-0.canonical.com (Postfix) with ESMTPS id C24D33F230 for ; Tue, 28 Mar 2023 23:49:59 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=canonical.com; s=20210705; t=1680047399; bh=HIjdZSAA/aiAdgiu1neP0Kqe7gjUYb2EPZW3xS5Xf94=; h=From:To:Subject:Date:Message-Id:In-Reply-To:References: MIME-Version; b=Ewu9Q8JSk/GwN5J3y6VjoOLqcj2fIWzC0UeLbbnVAa157Azw4gbgALKoZnMwi9sO4 N0Dq8zFbgeroH4/RHFlAi0s/iZ59Ea0cG7oDy3rHvfCqxO6jSZsB8UhUB2KGOHvYaL yBZjOKuxeriGHmLiQvIVgPFbondSKzGVGqxPfZO1ZfCvtktV4xpBS1n2UfLM9ZdNAy sDqUXF9jCtJYQLKidlJCtX9BURldmAljBWCcBmZ7k25fGZk5K8rqVJCT6E+L810WrE VMcLMjU+vNrNJ/4CyvttsHCzg37TSJIowEaNaa5lYz78Ieok7SQyIsmfhDU15EFM+G tPz4H25770n2g== Received: by mail-qk1-f198.google.com with SMTP id 72-20020a37064b000000b007467c5d3abeso6458812qkg.19 for ; Tue, 28 Mar 2023 16:49:59 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; t=1680047398; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=HIjdZSAA/aiAdgiu1neP0Kqe7gjUYb2EPZW3xS5Xf94=; b=1X40ORCwwh2VFWikQc/Ebo8MLhorr5DXYWZVlCuIUqTB/gMYsujFx9KHDMDTMn4JBp v7aKzNG0jCt26c5LS04wvCgkM5ksV2sGxA9qlntyB1Ay7aHSMAlu8yllkHMooyI8EvHo 6LVBgryjHx82z9RGPt9JByyTrtiDl0zK68caILhtNMS7hpYPfPxYCoBEsAPtn/IC9GcX eEw5S4A5SR48TQfM9RIoSe2lFpkiS0sOZEX/MEhJSdavphUS/jY8KCny3P6M575DBVgM oF4bYDka6IlB9g0ZAUjyER4dx84YX8rHWtn1CqGqLbpA7lqnBmfECj51HmmVnsd4Yw+e arpg== X-Gm-Message-State: AAQBX9fNMWJ1N7WLPaWEE6TE/N5AnHxafxAb8taRqgJdDIVdD/fgz0Ta eIITd6f5iSYfrvLnJzqnDFkBEn1z1iLvF09L5QA2NX888lsVzoyTwpenwcOQ9z1dbQeuHOoiTJV Deq4ZDVZrk1XGiUAipDKX5EI+z8C5ByNTiZVRE6fT9iiwKx2iGg== X-Received: by 2002:ac8:58ca:0:b0:3e4:ee15:ad44 with SMTP id u10-20020ac858ca000000b003e4ee15ad44mr11083046qta.31.1680047398019; Tue, 28 Mar 2023 16:49:58 -0700 (PDT) X-Google-Smtp-Source: AKy350a1yu9NzagL+6H1INZQ07X5s29b2DVc3xilZynPern8VRZ2IdI7ya8sK3233TMYO6IJE9SMPg== X-Received: by 2002:ac8:58ca:0:b0:3e4:ee15:ad44 with SMTP id u10-20020ac858ca000000b003e4ee15ad44mr11083028qta.31.1680047397656; Tue, 28 Mar 2023 16:49:57 -0700 (PDT) Received: from cache-ubuntu.hsd1.nj.comcast.net ([2601:86:200:98b0:3abb:6e6a:372c:5df5]) by smtp.gmail.com with ESMTPSA id s80-20020a37a953000000b00741a984943fsm10263477qke.40.2023.03.28.16.49.57 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 28 Mar 2023 16:49:57 -0700 (PDT) From: Yuxuan Luo To: kernel-team@lists.ubuntu.com Subject: [SRU][OEM-5.17/OEM-6.0][PATCH 1/1] USB: gadgetfs: Fix race between mounting and unmounting Date: Tue, 28 Mar 2023 19:49:54 -0400 Message-Id: <20230328234954.43851-2-yuxuan.luo@canonical.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20230328234954.43851-1-yuxuan.luo@canonical.com> References: <20230328234954.43851-1-yuxuan.luo@canonical.com> MIME-Version: 1.0 X-BeenThere: kernel-team@lists.ubuntu.com X-Mailman-Version: 2.1.20 Precedence: list List-Id: Kernel team discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: kernel-team-bounces@lists.ubuntu.com Sender: "kernel-team" From: Alan Stern The syzbot fuzzer and Gerald Lee have identified a use-after-free bug in the gadgetfs driver, involving processes concurrently mounting and unmounting the gadgetfs filesystem. In particular, gadgetfs_fill_super() can race with gadgetfs_kill_sb(), causing the latter to deallocate the_device while the former is using it. The output from KASAN says, in part: BUG: KASAN: use-after-free in instrument_atomic_read_write include/linux/instrumented.h:102 [inline] BUG: KASAN: use-after-free in atomic_fetch_sub_release include/linux/atomic/atomic-instrumented.h:176 [inline] BUG: KASAN: use-after-free in __refcount_sub_and_test include/linux/refcount.h:272 [inline] BUG: KASAN: use-after-free in __refcount_dec_and_test include/linux/refcount.h:315 [inline] BUG: KASAN: use-after-free in refcount_dec_and_test include/linux/refcount.h:333 [inline] BUG: KASAN: use-after-free in put_dev drivers/usb/gadget/legacy/inode.c:159 [inline] BUG: KASAN: use-after-free in gadgetfs_kill_sb+0x33/0x100 drivers/usb/gadget/legacy/inode.c:2086 Write of size 4 at addr ffff8880276d7840 by task syz-executor126/18689 CPU: 0 PID: 18689 Comm: syz-executor126 Not tainted 6.1.0-syzkaller #0 Hardware name: Google Google Compute Engine/Google Compute Engine, BIOS Google 10/26/2022 Call Trace: ... atomic_fetch_sub_release include/linux/atomic/atomic-instrumented.h:176 [inline] __refcount_sub_and_test include/linux/refcount.h:272 [inline] __refcount_dec_and_test include/linux/refcount.h:315 [inline] refcount_dec_and_test include/linux/refcount.h:333 [inline] put_dev drivers/usb/gadget/legacy/inode.c:159 [inline] gadgetfs_kill_sb+0x33/0x100 drivers/usb/gadget/legacy/inode.c:2086 deactivate_locked_super+0xa7/0xf0 fs/super.c:332 vfs_get_super fs/super.c:1190 [inline] get_tree_single+0xd0/0x160 fs/super.c:1207 vfs_get_tree+0x88/0x270 fs/super.c:1531 vfs_fsconfig_locked fs/fsopen.c:232 [inline] The simplest solution is to ensure that gadgetfs_fill_super() and gadgetfs_kill_sb() are serialized by making them both acquire a new mutex. Signed-off-by: Alan Stern Reported-and-tested-by: syzbot+33d7ad66d65044b93f16@syzkaller.appspotmail.com Reported-and-tested-by: Gerald Lee Link: https://lore.kernel.org/linux-usb/CAO3qeMVzXDP-JU6v1u5Ags6Q-bb35kg3=C6d04DjzA9ffa5x1g@mail.gmail.com/ Fixes: e5d82a7360d1 ("vfs: Convert gadgetfs to use the new mount API") CC: Link: https://lore.kernel.org/r/Y6XCPXBpn3tmjdCC@rowland.harvard.edu Signed-off-by: Greg Kroah-Hartman (cherry picked from commit d18dcfe9860e842f394e37ba01ca9440ab2178f4) CVE-2022-4382 Signed-off-by: Yuxuan Luo --- drivers/usb/gadget/legacy/inode.c | 28 +++++++++++++++++++++------- 1 file changed, 21 insertions(+), 7 deletions(-) diff --git a/drivers/usb/gadget/legacy/inode.c b/drivers/usb/gadget/legacy/inode.c index 01c3ead7d1b42..d605bc2e7e8fd 100644 --- a/drivers/usb/gadget/legacy/inode.c +++ b/drivers/usb/gadget/legacy/inode.c @@ -229,6 +229,7 @@ static void put_ep (struct ep_data *data) */ static const char *CHIP; +static DEFINE_MUTEX(sb_mutex); /* Serialize superblock operations */ /*----------------------------------------------------------------------*/ @@ -2010,13 +2011,20 @@ gadgetfs_fill_super (struct super_block *sb, struct fs_context *fc) { struct inode *inode; struct dev_data *dev; + int rc; - if (the_device) - return -ESRCH; + mutex_lock(&sb_mutex); + + if (the_device) { + rc = -ESRCH; + goto Done; + } CHIP = usb_get_gadget_udc_name(); - if (!CHIP) - return -ENODEV; + if (!CHIP) { + rc = -ENODEV; + goto Done; + } /* superblock */ sb->s_blocksize = PAGE_SIZE; @@ -2053,13 +2061,17 @@ gadgetfs_fill_super (struct super_block *sb, struct fs_context *fc) * from binding to a controller. */ the_device = dev; - return 0; + rc = 0; + goto Done; -Enomem: + Enomem: kfree(CHIP); CHIP = NULL; + rc = -ENOMEM; - return -ENOMEM; + Done: + mutex_unlock(&sb_mutex); + return rc; } /* "mount -t gadgetfs path /dev/gadget" ends up here */ @@ -2081,6 +2093,7 @@ static int gadgetfs_init_fs_context(struct fs_context *fc) static void gadgetfs_kill_sb (struct super_block *sb) { + mutex_lock(&sb_mutex); kill_litter_super (sb); if (the_device) { put_dev (the_device); @@ -2088,6 +2101,7 @@ gadgetfs_kill_sb (struct super_block *sb) } kfree(CHIP); CHIP = NULL; + mutex_unlock(&sb_mutex); } /*----------------------------------------------------------------------*/