qcow2: Fix L1 allocation size in qcow2_snapshot_load_tmp() (CVE-2014-0145)

For the L1 table to loaded for an internal snapshot, the code allocated
only enough memory to hold the currently active L1 table. If the
snapshot's L1 table is actually larger than the current one, this leads
to a buffer overflow.

Signed-off-by: Kevin Wolf <kwolf@redhat.com>
Reviewed-by: Max Reitz <mreitz@redhat.com>
Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
This commit is contained in:
Kevin Wolf 2014-03-26 13:06:05 +01:00 committed by Stefan Hajnoczi
parent 11b128f406
commit c05e4667be
3 changed files with 22 additions and 2 deletions

View file

@ -680,7 +680,7 @@ int qcow2_snapshot_load_tmp(BlockDriverState *bs,
sn = &s->snapshots[snapshot_index];
/* Allocate and read in the snapshot's L1 table */
new_l1_bytes = s->l1_size * sizeof(uint64_t);
new_l1_bytes = sn->l1_size * sizeof(uint64_t);
new_l1_table = g_malloc0(align_offset(new_l1_bytes, 512));
ret = bdrv_pread(bs->file, sn->l1_table_offset, new_l1_table, new_l1_bytes);

View file

@ -30,7 +30,8 @@ status=1 # failure is the default!
_cleanup()
{
_cleanup_test_img
rm -f $TEST_IMG.snap
_cleanup_test_img
}
trap "_cleanup; exit \$status" 0 1 2 3 15
@ -44,6 +45,9 @@ _supported_fmt qcow2
_supported_proto generic
_supported_os Linux
offset_size=24
offset_l1_size=36
echo
echo Test loading internal snapshots where the L1 table of the snapshot
echo is smaller than the current L1 table.
@ -77,6 +81,18 @@ _make_test_img 64M
_check_test_img
echo
echo "qcow2_snapshot_load_tmp() should take the L1 size from the snapshot"
echo
CLUSTER_SIZE=512
_make_test_img 64M
{ $QEMU_IMG snapshot -c foo $TEST_IMG; } 2>&1 | _filter_qemu_io | _filter_testdir
poke_file "$TEST_IMG" "$offset_size" "\x00\x00\x00\x00\x00\x00\x02\x00"
poke_file "$TEST_IMG" "$offset_l1_size" "\x00\x00\x00\x01"
{ $QEMU_IMG convert -s foo $TEST_IMG $TEST_IMG.snap; } 2>&1 | _filter_qemu_io | _filter_testdir
# success, all done
echo "*** done"
rm -f $seq.full

View file

@ -20,4 +20,8 @@ wrote 4096/4096 bytes at offset 1099511627776
read 4096/4096 bytes at offset 1099511627776
4 KiB, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
No errors were found on the image.
qcow2_snapshot_load_tmp() should take the L1 size from the snapshot
Formatting 'TEST_DIR/t.IMGFMT', fmt=IMGFMT size=67108864
*** done