]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/blame - releases/4.9.170/9p-do-not-trust-pdu-content-for-stat-item-size.patch
Linux 4.9.170
[thirdparty/kernel/stable-queue.git] / releases / 4.9.170 / 9p-do-not-trust-pdu-content-for-stat-item-size.patch
CommitLineData
5ddacef6
SLM
1From d9c2bb7a7089a59537024534b38adf6fa58c5ba4 Mon Sep 17 00:00:00 2001
2From: Gertjan Halkes <gertjan@google.com>
3Date: Wed, 5 Sep 2018 15:41:29 +0900
4Subject: 9p: do not trust pdu content for stat item size
5
6[ Upstream commit 2803cf4379ed252894f046cb8812a48db35294e3 ]
7
8v9fs_dir_readdir() could deadloop if a struct was sent with a size set
9to -2
10
11Link: http://lkml.kernel.org/r/1536134432-11997-1-git-send-email-asmadeus@codewreck.org
12Bugzilla: https://bugzilla.kernel.org/show_bug.cgi?id=88021
13Signed-off-by: Gertjan Halkes <gertjan@google.com>
14Signed-off-by: Dominique Martinet <dominique.martinet@cea.fr>
15Signed-off-by: Sasha Levin <sashal@kernel.org>
16---
17 fs/9p/vfs_dir.c | 8 +++-----
18 net/9p/protocol.c | 3 ++-
19 2 files changed, 5 insertions(+), 6 deletions(-)
20
21diff --git a/fs/9p/vfs_dir.c b/fs/9p/vfs_dir.c
22index 48db9a9f13f9..cb6c4031af55 100644
23--- a/fs/9p/vfs_dir.c
24+++ b/fs/9p/vfs_dir.c
25@@ -105,7 +105,6 @@ static int v9fs_dir_readdir(struct file *file, struct dir_context *ctx)
26 int err = 0;
27 struct p9_fid *fid;
28 int buflen;
29- int reclen = 0;
30 struct p9_rdir *rdir;
31 struct kvec kvec;
32
33@@ -138,11 +137,10 @@ static int v9fs_dir_readdir(struct file *file, struct dir_context *ctx)
34 while (rdir->head < rdir->tail) {
35 err = p9stat_read(fid->clnt, rdir->buf + rdir->head,
36 rdir->tail - rdir->head, &st);
37- if (err) {
38+ if (err <= 0) {
39 p9_debug(P9_DEBUG_VFS, "returned %d\n", err);
40 return -EIO;
41 }
42- reclen = st.size+2;
43
44 over = !dir_emit(ctx, st.name, strlen(st.name),
45 v9fs_qid2ino(&st.qid), dt_type(&st));
46@@ -150,8 +148,8 @@ static int v9fs_dir_readdir(struct file *file, struct dir_context *ctx)
47 if (over)
48 return 0;
49
50- rdir->head += reclen;
51- ctx->pos += reclen;
52+ rdir->head += err;
53+ ctx->pos += err;
54 }
55 }
56 }
57diff --git a/net/9p/protocol.c b/net/9p/protocol.c
58index 145f80518064..7f1b45c082c9 100644
59--- a/net/9p/protocol.c
60+++ b/net/9p/protocol.c
61@@ -570,9 +570,10 @@ int p9stat_read(struct p9_client *clnt, char *buf, int len, struct p9_wstat *st)
62 if (ret) {
63 p9_debug(P9_DEBUG_9P, "<<< p9stat_read failed: %d\n", ret);
64 trace_9p_protocol_dump(clnt, &fake_pdu);
65+ return ret;
66 }
67
68- return ret;
69+ return fake_pdu.offset;
70 }
71 EXPORT_SYMBOL(p9stat_read);
72
73--
742.19.1
75