QEMU: Null Pointer Failure in fdctrl_read() in hw/block/fdc.c
Affects | Status | Importance | Assigned to | Milestone | |
---|---|---|---|---|---|
QEMU |
Expired
|
High
|
Unassigned |
Bug Description
[via qemu-security list]
This is Gaoning Pan from Zhejiang University & Ant Security Light-Year Lab.
I found a Null Pointer issue locates in fdctrl_read() in hw/block/fdc.c.
This flaw allows a malicious guest user or process in a denial of service condition.
This issus was discovered in the latest Qemu-5.2.0. When using floppy device, there are several
choices to get specific drive in get_drv(), depending on fdctrl->cur_drv. But not all drives are
initialized properly, leaving fdctrl-
blk_pread(
null pointer access triggers, thus denial of service.My reproduced environment is as follows:
Host: ubuntu 18.04
Guest: ubuntu 18.04
My boot command is as follows:
qemu-
-nic user,hostfwd=
-drive id=mydrive,
ASAN output is as follows:
=======
==14688==ERROR: AddressSanitizer: SEGV on unknown address 0x00000000034c (pc 0x5636eee9bbaf bp 0x7ff2a53fdea0 sp 0x7ff2a53fde90 T3)
==14688==The signal is caused by a WRITE memory access.
==14688==Hint: address points to the zero page.
#0 0x5636eee9bbae in blk_inc_in_flight ../block/
#1 0x5636eee9b766 in blk_prw ../block/
#2 0x5636eee9cd76 in blk_pread ../block/
#3 0x5636ee1adf24 in fdctrl_read_data ../hw/block/
#4 0x5636ee1a6654 in fdctrl_read ../hw/block/
#5 0x5636eebb84c8 in portio_read ../softmmu/
#6 0x5636ee9848c5 in memory_
#7 0x5636ee9855c2 in access_
#8 0x5636ee98f0b7 in memory_
#9 0x5636ee98f311 in memory_
#10 0x5636ee8ff64a in flatview_
#11 0x5636ee8ff9e5 in flatview_read ../softmmu/
#12 0x5636ee8ffb83 in address_
#13 0x5636ee8ffdeb in address_space_rw ../softmmu/
#14 0x5636eea6a924 in kvm_handle_io ../accel/
#15 0x5636eea6c5e3 in kvm_cpu_exec ../accel/
#16 0x5636eeca492b in kvm_vcpu_thread_fn ../accel/
#17 0x5636ef1bc296 in qemu_thread_start ../util/
#18 0x7ff337c736da in start_thread (/lib/x86_
#19 0x7ff33799ca3e in __clone (/lib/x86_
AddressSanitizer can not provide additional info.
SUMMARY: AddressSanitizer: SEGV ../block/
Thread T3 created by T0 here:
#0 0x7ff33c580d2f in __interceptor_
#1 0x5636ef1bc673 in qemu_thread_create ../util/
#2 0x5636eeca4ce7 in kvm_start_
#3 0x5636ee9aa965 in qemu_init_vcpu ../softmmu/
#4 0x5636ee82a9b4 in x86_cpu_realizefn ../target/
#5 0x5636eed002f4 in device_set_realized ../hw/core/
#6 0x5636eecc59bc in property_set_bool ../qom/
#7 0x5636eecc0c28 in object_property_set ../qom/
#8 0x5636eecb6fb9 in object_
#9 0x5636eecc1175 in object_
#10 0x5636eecfc286 in qdev_realize ../hw/core/
#11 0x5636ee739b34 in x86_cpu_new ../hw/i386/
#12 0x5636ee739d6d in x86_cpus_init ../hw/i386/
#13 0x5636ee6f843e in pc_init1 ../hw/i386/
#14 0x5636ee6fab1e in pc_init_v5_2 ../hw/i386/
#15 0x5636ee1cb4a7 in machine_
#16 0x5636ee9c323d in qemu_init ../softmmu/
#17 0x5636edd92c71 in main ../softmmu/
#18 0x7ff33789cb96 in __libc_start_main (/lib/x86_
==14688==ABORTING
Reproducer is attached.
Best regards.
Gaoning Pan of Zhejiang University & Ant Security Light-Year Lab
CVE References
Changed in qemu: | |
status: | New → In Progress |
importance: | Undecided → High |
The given reproducer does not seem to work as expected to trigger this issue. DOR:fdctrl_ write_dor( ) ioport write command
IIUC, issue occurs because a privileged guest user may change the selected
floppy drive via FD_REG_
static void fdctrl_ write_dor( FDCtrl *fdctrl, uint32_t value) >cur_drv = value & FD_DOR_SELMASK; <= selected drive changes based on 'value'
{
...
/* Selected drive */
fdctrl-
...
}
Little tweaking of parameters under gdb reproduces the crash
$ gdb --args ./bin/qemu- system- x86_64 -runas test -nographic -enable-kvm -m 2048 img,format= qcow2,if= floppy, id=myfdc /var/lib/ libvirt/ images/ f27vm.qcow2 block-backend. c:1356 block-backend. c:1328 block-backend. c:1491 fdc.c:1919 fdc.c:936 ioport. c:179 region_ read_accessor ../softmmu/ memory. c:442 with_adjusted_ size ../softmmu/ memory. c:552 region_ dispatch_ read1 ../softmmu/ memory. c:1420 region_ dispatch_ read ../softmmu/ memory. c:1449 read_continue ../softmmu/ physmem. c:2822 physmem. c:2862 space_read_ full ../softmmu/ physmem. c:2875 physmem. c:2903 kvm/kvm- all.c:2285 kvm/kvm- all.c:2531 kvm/kvm- cpus.c: 49 qemu-thread- posix.c: 521 libpthread. so.0+0x93f8) libc.so. 6+0x101902)
-drive file=fdc.
...
==541702==ERROR: AddressSanitizer: SEGV on unknown address 0x00000000034c (pc 0x55555938377f bp 0x7fff6f3fdeb0 sp 0x7fff6f3fdea0 T3)
==541702==The signal is caused by a WRITE memory access.
==541702==Hint: address points to the zero page.
#0 0x55555938377f in blk_inc_in_flight ../block/
#1 0x55555938325b in blk_prw ../block/
#2 0x555559384ec5 in blk_pread ../block/
#3 0x555557d7c798 in fdctrl_read_data ../hw/block/
#4 0x555557d7207c in fdctrl_read ../hw/block/
#5 0x555558ee7c40 in portio_read ../softmmu/
#6 0x555558c9a0c1 in memory_
#7 0x555558c9af04 in access_
#8 0x555558ca7159 in memory_
#9 0x555558ca7433 in memory_
#10 0x555558f6214e in flatview_
#11 0x555558f62560 in flatview_read ../softmmu/
#12 0x555558f62700 in address_
#13 0x555558f62977 in address_space_rw ../softmmu/
#14 0x555558d037b9 in kvm_handle_io ../accel/
#15 0x555558d05a4b in kvm_cpu_exec ../accel/
#16 0x555558ee0efa in kvm_vcpu_thread_fn ../accel/
#17 0x55555977ec18 in qemu_thread_start ../util/
#18 0x7ffff63323f8 in start_thread (/lib64/
#19 0x7ffff625f902 in __GI___clone (/lib64/