blob: 24fd2c5ed3e603184bf8e1d00977a2085cb8f6f2 [file] [log] [blame]
Patrick Williams92b42cb2022-09-03 06:53:57 -05001From 57a89cc36ead7234e540d0ecbe1a792ab6b04cb7 Mon Sep 17 00:00:00 2001
2From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= <philmd@redhat.com>
3Date: Thu, 18 Nov 2021 12:57:32 +0100
4Subject: [PATCH 1/2] hw/block/fdc: Prevent end-of-track overrun
5 (CVE-2021-3507)
6MIME-Version: 1.0
7Content-Type: text/plain; charset=UTF-8
8Content-Transfer-Encoding: 8bit
9
10Per the 82078 datasheet, if the end-of-track (EOT byte in
11the FIFO) is more than the number of sectors per side, the
12command is terminated unsuccessfully:
13
14* 5.2.5 DATA TRANSFER TERMINATION
15
16 The 82078 supports terminal count explicitly through
17 the TC pin and implicitly through the underrun/over-
18 run and end-of-track (EOT) functions. For full sector
19 transfers, the EOT parameter can define the last
20 sector to be transferred in a single or multisector
21 transfer. If the last sector to be transferred is a par-
22 tial sector, the host can stop transferring the data in
23 mid-sector, and the 82078 will continue to complete
24 the sector as if a hardware TC was received. The
25 only difference between these implicit functions and
26 TC is that they return "abnormal termination" result
27 status. Such status indications can be ignored if they
28 were expected.
29
30* 6.1.3 READ TRACK
31
32 This command terminates when the EOT specified
33 number of sectors have been read. If the 82078
34 does not find an I D Address Mark on the diskette
35 after the second· occurrence of a pulse on the
36 INDX# pin, then it sets the IC code in Status Regis-
37 ter 0 to "01" (Abnormal termination), sets the MA bit
38 in Status Register 1 to "1", and terminates the com-
39 mand.
40
41* 6.1.6 VERIFY
42
43 Refer to Table 6-6 and Table 6-7 for information
44 concerning the values of MT and EC versus SC and
45 EOT value.
46
47* Table 6·6. Result Phase Table
48
49* Table 6-7. Verify Command Result Phase Table
50
51Fix by aborting the transfer when EOT > # Sectors Per Side.
52
53Cc: qemu-stable@nongnu.org
54Cc: Hervé Poussineau <hpoussin@reactos.org>
55Fixes: baca51faff0 ("floppy driver: disk geometry auto detect")
56Reported-by: Alexander Bulekov <alxndr@bu.edu>
57Resolves: https://gitlab.com/qemu-project/qemu/-/issues/339
58Signed-off-by: Philippe Mathieu-Daudé <philmd@redhat.com>
59Message-Id: <20211118115733.4038610-2-philmd@redhat.com>
60Reviewed-by: Hanna Reitz <hreitz@redhat.com>
61Signed-off-by: Kevin Wolf <kwolf@redhat.com>
62
63Upstream-Status: Backport [defac5e2fbddf8423a354ff0454283a2115e1367]
64CVE: CVE-2021-3507
65
66Signed-off-by: Sakib Sajal <sakib.sajal@windriver.com>
67---
68 hw/block/fdc.c | 8 ++++++++
69 1 file changed, 8 insertions(+)
70
71diff --git a/hw/block/fdc.c b/hw/block/fdc.c
72index 347875a0c..57bb35579 100644
73--- a/hw/block/fdc.c
74+++ b/hw/block/fdc.c
75@@ -1530,6 +1530,14 @@ static void fdctrl_start_transfer(FDCtrl *fdctrl, int direction)
76 int tmp;
77 fdctrl->data_len = 128 << (fdctrl->fifo[5] > 7 ? 7 : fdctrl->fifo[5]);
78 tmp = (fdctrl->fifo[6] - ks + 1);
79+ if (tmp < 0) {
80+ FLOPPY_DPRINTF("invalid EOT: %d\n", tmp);
81+ fdctrl_stop_transfer(fdctrl, FD_SR0_ABNTERM, FD_SR1_MA, 0x00);
82+ fdctrl->fifo[3] = kt;
83+ fdctrl->fifo[4] = kh;
84+ fdctrl->fifo[5] = ks;
85+ return;
86+ }
87 if (fdctrl->fifo[0] & 0x80)
88 tmp += fdctrl->fifo[6];
89 fdctrl->data_len *= tmp;
90--
912.33.0
92