From 670c7c6501bf81b3dcfc74ed7e58dfdd43f404ee Mon Sep 17 00:00:00 2001 From: Namjae Jeon Date: Tue, 9 Apr 2024 16:17:07 +0800 Subject: [PATCH] ksmbd: validate session id and tree id in compound request stable inclusion from stable-v5.15.81 commit 017d85c94f02090a87f4a473dbe0d6ee0da72693 category: bugfix bugzilla: https://gitee.com/src-openeuler/kernel/issues/I92OR4 CVE: CVE-2023-52442 Reference: https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/commit/?h=linux-5.15.y&id=017d85c94f02090a87f4a473dbe0d6ee0da72693 -------------------------------- [ Upstream commit 3df0411e132ee74a87aa13142dfd2b190275332e ] `smb2_get_msg()` in smb2_get_ksmbd_tcon() and smb2_check_user_session() will always return the first request smb2 header in a compound request. if `SMB2_TREE_CONNECT_HE` is the first command in compound request, will return 0, i.e. The tree id check is skipped. This patch use ksmbd_req_buf_next() to get current command in compound. Reported-by: zdi-disclosures@trendmicro.com # ZDI-CAN-21506 Signed-off-by: Namjae Jeon Signed-off-by: Steve French Signed-off-by: Greg Kroah-Hartman Signed-off-by: Long Li --- fs/ksmbd/smb2pdu.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/fs/ksmbd/smb2pdu.c b/fs/ksmbd/smb2pdu.c index b21ac851345f..b78232c063e5 100644 --- a/fs/ksmbd/smb2pdu.c +++ b/fs/ksmbd/smb2pdu.c @@ -86,9 +86,9 @@ struct channel *lookup_chann_list(struct ksmbd_session *sess, struct ksmbd_conn */ int smb2_get_ksmbd_tcon(struct ksmbd_work *work) { - struct smb2_hdr *req_hdr = smb2_get_msg(work->request_buf); + struct smb2_hdr *req_hdr = ksmbd_req_buf_next(work); unsigned int cmd = le16_to_cpu(req_hdr->Command); - int tree_id; + unsigned int tree_id; if (cmd == SMB2_TREE_CONNECT_HE || cmd == SMB2_CANCEL_HE || @@ -113,7 +113,7 @@ int smb2_get_ksmbd_tcon(struct ksmbd_work *work) pr_err("The first operation in the compound does not have tcon\n"); return -EINVAL; } - if (work->tcon->id != tree_id) { + if (tree_id != UINT_MAX && work->tcon->id != tree_id) { pr_err("tree id(%u) is different with id(%u) in first operation\n", tree_id, work->tcon->id); return -EINVAL; @@ -570,9 +570,9 @@ int smb2_allocate_rsp_buf(struct ksmbd_work *work) */ int smb2_check_user_session(struct ksmbd_work *work) { - struct smb2_hdr *req_hdr = smb2_get_msg(work->request_buf); + struct smb2_hdr *req_hdr = ksmbd_req_buf_next(work); struct ksmbd_conn *conn = work->conn; - unsigned int cmd = conn->ops->get_cmd_val(work); + unsigned int cmd = le16_to_cpu(req_hdr->Command); unsigned long long sess_id; /* @@ -598,7 +598,7 @@ int smb2_check_user_session(struct ksmbd_work *work) pr_err("The first operation in the compound does not have sess\n"); return -EINVAL; } - if (work->sess->id != sess_id) { + if (sess_id != ULLONG_MAX && work->sess->id != sess_id) { pr_err("session id(%llu) is different with the first operation(%lld)\n", sess_id, work->sess->id); return -EINVAL; -- Gitee