usbredir/0002-Skip-empty-write-buffers-when-unserializing-parser.patch
wguanghao b5a2872a57 fix timeout and abort of fuzz-test
(cherry picked from commit d346b28367f2d3663cdce669e59727c08d4cd3c6)
2021-12-08 15:44:13 +08:00

75 lines
2.3 KiB
Diff

From cd919def3bf5efeae24976752143cefc9ffc58fa Mon Sep 17 00:00:00 2001
From: Michael Hanselmann <public@hansmi.ch>
Date: Sun, 22 Aug 2021 21:07:36 +0200
Subject: [PATCH] Skip empty write buffers when unserializing parser
At commit 8490a7ac101d the following `fuzzing/usbredirparserfuzz` input causes
the instantiation of empty write buffers:
$ base64 -d <<'EOF' > testcase6474540506021888
QAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAYAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQAAAAG
AAAAAN7/AAAACAA=
EOF
Empty write buffers trigger all kinds of issues, in part because they cause
calls to write(2) with a zero length.
Signed-off-by: Michael Hanselmann <public@hansmi.ch>
---
usbredirparser/usbredirparser.c | 26 ++++++++++++++++++++++----
1 file changed, 22 insertions(+), 4 deletions(-)
diff --git a/usbredirparser/usbredirparser.c b/usbredirparser/usbredirparser.c
index edfdfd2..f08a43a 100644
--- a/usbredirparser/usbredirparser.c
+++ b/usbredirparser/usbredirparser.c
@@ -1673,6 +1673,12 @@ int usbredirparser_unserialize(struct usbredirparser *parser_pub,
return -1;
}
+ if (parser->write_buf_count != 0 || parser->write_buf != NULL ||
+ parser->data != NULL) {
+ ERROR("unserialization must use a pristine parser");
+ return -1;
+ }
+
if (unserialize_int(parser, &state, &remain, &i, "length"))
return -1;
if (i != len) {
@@ -1763,16 +1769,28 @@ int usbredirparser_unserialize(struct usbredirparser *parser_pub,
return -1;
next = &parser->write_buf;
while (i) {
+ uint8_t *buf = NULL;
+
+ l = 0;
+ if (unserialize_data(parser, &state, &remain, &buf, &l, "wbuf")) {
+ return -1;
+ }
+
+ if (l == 0) {
+ free(buf);
+ ERROR("write buffer %d is empty", i);
+ return -1;
+ }
+
wbuf = calloc(1, sizeof(*wbuf));
if (!wbuf) {
+ free(buf);
ERROR("Out of memory allocating unserialize buffer");
return -1;
}
- *next = wbuf;
- l = 0;
- if (unserialize_data(parser, &state, &remain, &wbuf->buf, &l, "wbuf"))
- return -1;
+ wbuf->buf = buf;
wbuf->len = l;
+ *next = wbuf;
next = &wbuf->next;
i--;
}
--
1.8.3.1