From patchwork Thu Jun 29 19:44:29 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Yuxuan Luo X-Patchwork-Id: 1801611 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=pKOYmWbE; 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 4QsTS56wPYz1yhT for ; Fri, 30 Jun 2023 05:44:52 +1000 (AEST) Received: from localhost ([127.0.0.1] helo=huckleberry.canonical.com) by huckleberry.canonical.com with esmtp (Exim 4.86_2) (envelope-from ) id 1qExZH-0004PT-5U; Thu, 29 Jun 2023 19:44:39 +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 1qExZE-0004P5-UQ for kernel-team@lists.ubuntu.com; Thu, 29 Jun 2023 19:44:36 +0000 Received: from mail-qk1-f200.google.com (mail-qk1-f200.google.com [209.85.222.200]) (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 8CE8F3F18D for ; Thu, 29 Jun 2023 19:44:36 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=canonical.com; s=20210705; t=1688067876; bh=65uPUQfrbA6qpNzdZhiuUO8yVezyYFzAAyyRKp0VzxI=; h=From:To:Subject:Date:Message-Id:In-Reply-To:References: MIME-Version; b=pKOYmWbEO9FO9RbaErL801DP/XbzhnEzmCf2Vv++QA5wCcmmJ6r7DjjGPJG4mbb9o m6+DSm8HujAiTryoCw/j51b3ioLEPvppzYU8WYeHrGX6qupEGJbymhG/PYJDDOuPlL FJZ/VRogLChS1XUO3GGCl+jxIUI/CXDYL/JZfXUxAMr7DFIZVe9biO8iby8PT2XLiO M1ds0dBcoIG5q1cncP08fY+edSZ02ZvAfI8y353mMWNjflqw8R/HGgWvuyFXLax5Gf oAALUGfK7IDOa/8FrIQdiDO2jz+hn41G/t8fLkG3eXqb9xw0rmb8A2/QcC80aBDPsN al2+gkf4To3Dw== Received: by mail-qk1-f200.google.com with SMTP id af79cd13be357-7623a4864c2so119983185a.3 for ; Thu, 29 Jun 2023 12:44:36 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20221208; t=1688067875; x=1690659875; 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=65uPUQfrbA6qpNzdZhiuUO8yVezyYFzAAyyRKp0VzxI=; b=XahgJicGSOeX9QQO3qHhIuhGNbNzKwBz5qLOf9+/UP0YwYs3gEy213jQ243oY84lL+ xVN4budu3sDGWasMeqjQmZRwz0KlYGh9fapzWZulbj7AGtCWw85ZErfW5vVphJGSN707 ZWTVNNcptX7DAwMhaDHXmBlTgUk7RZmOkkq4xL4zCSFKqA5ImBAFC/NFf0dcFxznf4Hj 3I/V8LRB0XoAMUj2ZMS/F1lulnmbzBMIhtk2FuuBt3To2devGzXgI7JBxnbf4UZKJsvt xs75m427R9j2HNR7shbaDO8SlNHeOi6Iw7Q80r7cxtSJOSrlqG0WNN05+lcvNZm7YXp5 B5FQ== X-Gm-Message-State: AC+VfDwtqinnVTTCm1p8ply0kylxTp5eobZJZZa/ZlS/vKp3p+vzPb31 gDcXodrcoqUPP1ttahwrFmtfgoPdgkvWEb6Iwg2ICkwivE3jA7wexFyQwfaAIEIdwA/nlKEx3Pb 9YqUoZuxBTb8ROmAg1g/66N0uxy8apu6cRJuWt6KTlYUdUAjr9Q== X-Received: by 2002:a05:620a:3181:b0:765:a9f4:9656 with SMTP id bi1-20020a05620a318100b00765a9f49656mr329220qkb.26.1688067875151; Thu, 29 Jun 2023 12:44:35 -0700 (PDT) X-Google-Smtp-Source: ACHHUZ7yYaCrr+67nvA8XSBHx0YAo8YZ14VauTjYWAoEu/IFYxvRpao2NB6p9Rjaop3qsPoVMcQtKQ== X-Received: by 2002:a05:620a:3181:b0:765:a9f4:9656 with SMTP id bi1-20020a05620a318100b00765a9f49656mr329211qkb.26.1688067874842; Thu, 29 Jun 2023 12:44:34 -0700 (PDT) Received: from cache-ubuntu.hsd1.nj.comcast.net ([2601:86:200:98b0:d86:6265:2ec3:946]) by smtp.gmail.com with ESMTPSA id c20-20020a05620a135400b00767171e4eeasm2660445qkl.2.2023.06.29.12.44.34 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Thu, 29 Jun 2023 12:44:34 -0700 (PDT) From: Yuxuan Luo To: kernel-team@lists.ubuntu.com Subject: [SRU][Focal][PATCH 1/3] cifs: move some variables off the stack in smb2_ioctl_query_info Date: Thu, 29 Jun 2023 15:44:29 -0400 Message-Id: <20230629194431.59200-2-yuxuan.luo@canonical.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20230629194431.59200-1-yuxuan.luo@canonical.com> References: <20230629194431.59200-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: Ronnie Sahlberg Move some large data structures off the stack and into dynamically allocated memory in the function smb2_ioctl_query_info Signed-off-by: Ronnie Sahlberg Signed-off-by: Steve French (backported from commit b2ca6c2c9eddc41c09e49e8e83f8208bd80fdb8e) [yuxuan.luo: accept the incoming change and we'll handle it in later fix commits. ] CVE-2022-0168 Signed-off-by: Yuxuan Luo --- fs/cifs/smb2ops.c | 67 ++++++++++++++++++++++++++--------------------- 1 file changed, 37 insertions(+), 30 deletions(-) diff --git a/fs/cifs/smb2ops.c b/fs/cifs/smb2ops.c index 7f1a1f6f544d9..2077f15548459 100644 --- a/fs/cifs/smb2ops.c +++ b/fs/cifs/smb2ops.c @@ -1448,6 +1448,16 @@ SMB2_request_res_key(const unsigned int xid, struct cifs_tcon *tcon, return rc; } +struct iqi_vars { + struct smb_rqst rqst[3]; + struct kvec rsp_iov[3]; + struct kvec open_iov[SMB2_CREATE_IOV_SIZE]; + struct kvec qi_iov[1]; + struct kvec io_iov[SMB2_IOCTL_IOV_SIZE]; + struct kvec si_iov[SMB2_SET_INFO_IOV_SIZE]; + struct kvec close_iov[1]; +}; + static int smb2_ioctl_query_info(const unsigned int xid, struct cifs_tcon *tcon, @@ -1455,6 +1465,9 @@ smb2_ioctl_query_info(const unsigned int xid, __le16 *path, int is_dir, unsigned long p) { + struct iqi_vars *vars; + struct smb_rqst *rqst; + struct kvec *rsp_iov; struct cifs_ses *ses = tcon->ses; char __user *arg = (char __user *)p; struct smb_query_info qi; @@ -1464,50 +1477,47 @@ smb2_ioctl_query_info(const unsigned int xid, struct smb2_query_info_rsp *qi_rsp = NULL; struct smb2_ioctl_rsp *io_rsp = NULL; void *buffer = NULL; - struct smb_rqst rqst[3]; int resp_buftype[3]; - struct kvec rsp_iov[3]; - struct kvec open_iov[SMB2_CREATE_IOV_SIZE]; struct cifs_open_parms oparms; u8 oplock = SMB2_OPLOCK_LEVEL_NONE; struct cifs_fid fid; - struct kvec qi_iov[1]; - struct kvec io_iov[SMB2_IOCTL_IOV_SIZE]; - struct kvec si_iov[SMB2_SET_INFO_IOV_SIZE]; - struct kvec close_iov[1]; unsigned int size[2]; void *data[2]; int create_options = is_dir ? CREATE_NOT_FILE : CREATE_NOT_DIR; - memset(rqst, 0, sizeof(rqst)); + vars = kzalloc(sizeof(*vars), GFP_ATOMIC); + if (vars == NULL) + return -ENOMEM; + rqst = &vars->rqst[0]; + rsp_iov = &vars->rsp_iov[0]; + resp_buftype[0] = resp_buftype[1] = resp_buftype[2] = CIFS_NO_BUFFER; - memset(rsp_iov, 0, sizeof(rsp_iov)); if (copy_from_user(&qi, arg, sizeof(struct smb_query_info))) - return -EFAULT; + goto e_fault; - if (qi.output_buffer_length > 1024) + if (qi.output_buffer_length > 1024) { + kfree(vars); return -EINVAL; + } - if (!ses || !(ses->server)) + if (!ses || !(ses->server)) { + kfree(vars); return -EIO; + } if (smb3_encryption_required(tcon)) flags |= CIFS_TRANSFORM_REQ; - buffer = kmalloc(qi.output_buffer_length, GFP_KERNEL); - if (buffer == NULL) - return -ENOMEM; - - if (copy_from_user(buffer, arg + sizeof(struct smb_query_info), - qi.output_buffer_length)) { - rc = -EFAULT; - goto iqinf_exit; + buffer = memdup_user(arg + sizeof(struct smb_query_info), + qi.output_buffer_length); + if (IS_ERR(buffer)) { + kfree(vars); + return PTR_ERR(buffer); } /* Open */ - memset(&open_iov, 0, sizeof(open_iov)); - rqst[0].rq_iov = open_iov; + rqst[0].rq_iov = &vars->open_iov[0]; rqst[0].rq_nvec = SMB2_CREATE_IOV_SIZE; memset(&oparms, 0, sizeof(oparms)); @@ -1549,8 +1559,7 @@ smb2_ioctl_query_info(const unsigned int xid, if (!capable(CAP_SYS_ADMIN)) rc = -EPERM; else { - memset(&io_iov, 0, sizeof(io_iov)); - rqst[1].rq_iov = io_iov; + rqst[1].rq_iov = &vars->io_iov[0]; rqst[1].rq_nvec = SMB2_IOCTL_IOV_SIZE; rc = SMB2_ioctl_init(tcon, &rqst[1], @@ -1566,8 +1575,7 @@ smb2_ioctl_query_info(const unsigned int xid, if (!capable(CAP_SYS_ADMIN)) rc = -EPERM; else { - memset(&si_iov, 0, sizeof(si_iov)); - rqst[1].rq_iov = si_iov; + rqst[1].rq_iov = &vars->si_iov[0]; rqst[1].rq_nvec = 1; size[0] = 8; @@ -1580,8 +1588,7 @@ smb2_ioctl_query_info(const unsigned int xid, SMB2_O_INFO_FILE, 0, data, size); } } else if (qi.flags == PASSTHRU_QUERY_INFO) { - memset(&qi_iov, 0, sizeof(qi_iov)); - rqst[1].rq_iov = qi_iov; + rqst[1].rq_iov = &vars->qi_iov[0]; rqst[1].rq_nvec = 1; rc = SMB2_query_info_init(tcon, &rqst[1], COMPOUND_FID, @@ -1600,8 +1607,7 @@ smb2_ioctl_query_info(const unsigned int xid, smb2_set_related(&rqst[1]); /* Close */ - memset(&close_iov, 0, sizeof(close_iov)); - rqst[2].rq_iov = close_iov; + rqst[2].rq_iov = &vars->close_iov[0]; rqst[2].rq_nvec = 1; rc = SMB2_close_init(tcon, &rqst[2], COMPOUND_FID, COMPOUND_FID, false); @@ -1650,6 +1656,7 @@ smb2_ioctl_query_info(const unsigned int xid, } iqinf_exit: + kfree(vars); kfree(buffer); SMB2_open_free(&rqst[0]); if (qi.flags & PASSTHRU_FSCTL)