add qemu with gcc4 hack

git-svn-id: https://svn.disconnected-by-peer.at/svn/linamh/trunk/linamh@591 6952d904-891a-0410-993b-d76249ca496b
This commit is contained in:
geos_one
2008-12-08 11:16:27 +00:00
parent 1cae4c474e
commit 846f57bf93
31 changed files with 2200 additions and 587 deletions

View File

@@ -0,0 +1,263 @@
# ChangeLog for app-emulation/qemu-softmmu
# Copyright 1999-2008 Gentoo Foundation; Distributed under the GPL v2
# $Header: /var/cvsroot/gentoo-x86/app-emulation/qemu-softmmu/ChangeLog,v 1.55 2008/07/28 19:11:06 cardoe Exp $
28 Jul 2008; Doug Goldstein <cardoe@gentoo.org> metadata.xml:
add GLEP 56 USE flag desc from use.local.desc
14 May 2008; Markus Meier <maekke@gentoo.org>
qemu-softmmu-0.9.1-r3.ebuild:
amd64 stable, bug #221943
14 May 2008; Luca Barbato <lu_zero@gentoo.org>
qemu-softmmu-0.9.1-r3.ebuild:
Marked ppc
14 May 2008; Christian Faulhammer <opfer@gentoo.org>
qemu-softmmu-0.9.1-r3.ebuild:
stable x86, security bug 212351
*qemu-softmmu-0.9.1-r3 (14 May 2008)
14 May 2008; Luca Barbato <lu_zero@gentoo.org>
+files/qemu-softmmu-0.9.1-CVE-2008-2004.patch,
+qemu-softmmu-0.9.1-r3.ebuild:
Address CVE-2008-2004, fix bug #221943, thanks to Celso Fernandes
(icezimm) <celso.fernandes@gmail.com>
*qemu-softmmu-0.9.1-r2 (12 May 2008)
12 May 2008; Peter Volkov <pva@gentoo.org>
+files/qemu-softmmu-0.9.1-CVE-2008-0928.patch,
+qemu-softmmu-0.9.1-r2.ebuild:
Updated patch for security bug #212351 to avoid qcow2 image regression.
Filtering CFLAGS to allow building with gcc-3.4.
20 Apr 2008; Luca Barbato <lu_zero@gentoo.org>
qemu-softmmu-0.9.1-r1.ebuild:
Move the gcc check in src_unpack
09 Mar 2008; Luca Barbato <lu_zero@gentoo.org>
qemu-softmmu-0.9.1-r1.ebuild:
Marked ppc
*qemu-softmmu-0.9.1-r1 (05 Mar 2008)
05 Mar 2008; Luca Barbato <lu_zero@gentoo.org>
+files/qemu-softmmu-0.9.1-block-device-address-range.patch,
+qemu-softmmu-0.9.1-r1.ebuild:
Fix CVE-2008-0928, patch from the red hat bugzilla
01 Feb 2008; Luca Barbato <lu_zero@gentoo.org>
-files/qemu-0.8.0-gcc4-hacks.patch, -files/qemu-0.8.0-gcc4-opts.patch,
-files/qemu-0.8.2-linux-headers.patch, -files/qemu-0.8.2-sparc-fp.patch,
-qemu-softmmu-0.8.0.ebuild, -qemu-softmmu-0.8.0.20060329.ebuild,
-qemu-softmmu-0.8.1.ebuild, -qemu-softmmu-0.8.1-r1.ebuild,
-qemu-softmmu-0.8.2.ebuild, -qemu-softmmu-0.8.2-r1.ebuild:
Remove qemu-0.8 series
*qemu-softmmu-0.9.1 (25 Jan 2008)
25 Jan 2008; Luca Barbato <lu_zero@gentoo.org> +qemu-softmmu-0.9.1.ebuild:
New version, improved ebuild by Carlo Marcelo Arenas Belon
<carenas@sajinet.com.pe>, bugs #204675
13 Nov 2007; Luca Barbato <lu_zero@gentoo.org>
qemu-softmmu-0.9.0-r1.ebuild:
Mark the revision stable
*qemu-softmmu-0.9.0-r1 (12 Nov 2007)
12 Nov 2007; Luca Barbato <lu_zero@gentoo.org>
+files/qemu-softmmu-0.9.0-block-qcow2.patch,
+qemu-softmmu-0.9.0-r1.ebuild:
address qcow2 corruption, thanks to Chris Williams <gentoo@psychogeeks.com>
for the patch, see bug #187075
09 Sep 2007; Luca Barbato <lu_zero@gentoo.org>
+files/qemu-softmmu-0.9.0-ide-cd.patch, qemu-softmmu-0.9.0.ebuild:
Address a glitch in the ide/cdrom emulation, thanks to Carlo Marcelo Arenas
Belon <carenas@sajinet.com.pe> for pointing the patch and reporting the
issue
02 Jul 2007; Piotr Jaroszyński <peper@gentoo.org>
qemu-softmmu-0.8.0.ebuild, qemu-softmmu-0.8.0.20060329.ebuild,
qemu-softmmu-0.8.1.ebuild, qemu-softmmu-0.8.1-r1.ebuild,
qemu-softmmu-0.8.2.ebuild, qemu-softmmu-0.8.2-r1.ebuild,
qemu-softmmu-0.9.0.ebuild:
(QA) RESTRICT clean up.
20 May 2007; Christian Faulhammer <opfer@gentoo.org>
qemu-softmmu-0.9.0.ebuild:
stable amd64, security bug 176674
16 May 2007; Luca Barbato <lu_zero@gentoo.org> qemu-softmmu-0.9.0.ebuild:
Marked ppc
08 May 2007; Markus Ullmann <jokey@gentoo.org> qemu-softmmu-0.9.0.ebuild:
Stable on x86 wrt security bug #176674
21 Feb 2007; Piotr Jaroszyński <peper@gentoo.org> ChangeLog:
Transition to Manifest2.
10 Feb 2007; Luca Barbato <lu_zero@gentoo.org> qemu-softmmu-0.9.0.ebuild:
Fix bug #164491
10 Feb 2007; Luca Barbato <lu_zero@gentoo.org> qemu-softmmu-0.9.0.ebuild:
Minor update
*qemu-softmmu-0.9.0 (07 Feb 2007)
07 Feb 2007; Luca Barbato <lu_zero@gentoo.org> +qemu-softmmu-0.9.0.ebuild:
New version
06 Feb 2007; Simon Stelling <blubb@gentoo.org>
qemu-softmmu-0.8.2-r1.ebuild:
stable on amd64; bug 159522
02 Jan 2007; Christian Faulhammer <opfer@gentoo.org>
qemu-softmmu-0.8.2-r1.ebuild:
stable x86, bug #159522
31 Dec 2006; Mike Frysinger <vapier@gentoo.org>
+files/qemu-0.8.2-linux-headers.patch, qemu-softmmu-0.8.2-r1.ebuild:
Fix building with sanitized headers.
31 Dec 2006; Luca Barbato <lu_zero@gentoo.org>
qemu-softmmu-0.8.2-r1.ebuild:
Marked ppc
22 Nov 2006; Kevin F. Quinn <kevquinn@gentoo.org>
qemu-softmmu-0.8.2-r1.ebuild:
Add QA variables indicating which files contain textrels, require
execstack, and contain WX PT_LOAD segments. The TEXTRELs are a feature of how
qemu works. The execstack/wx_load markings are for a foreign binary.
18 Aug 2006; Luca Barbato <lu_zero@gentoo.org> qemu-softmmu-0.8.2.ebuild:
remove stray dep
17 Aug 2006; Luca Barbato <lu_zero@gentoo.org> qemu-softmmu-0.8.2.ebuild,
qemu-softmmu-0.8.2-r1.ebuild:
Remove stray bits from the older ebuild
*qemu-softmmu-0.8.2-r1 (17 Aug 2006)
17 Aug 2006; Luca Barbato <lu_zero@gentoo.org>
qemu-softmmu-0.8.2-r1.ebuild, files/digest-qemu-softmmu-0.8.2-r1:
Added alsa support as requested in bug #116599 by Ivan Yosifov <ivan@yosifov.net>
and adlib support as requested by Jan Simons <gentoo@onkos.de> on the same bug;
use tc-getCC, patch from Damien THEBAULT <damien.thebault@laposte.net> in
bug #132602, set correct kqemu deps, should solve bug #141721
01 Aug 2006; Luca Barbato <lu_zero@gentoo.org> qemu-softmmu-0.8.2.ebuild:
False hope, gcc-3 is still required.
*qemu-softmmu-0.8.2 (01 Aug 2006)
01 Aug 2006; Luca Barbato <lu_zero@gentoo.org>
+files/qemu-0.8.2-sparc-fp.patch, +qemu-softmmu-0.8.2.ebuild:
New version, should work better with gcc-4
*qemu-softmmu-0.8.1-r1 (12 Jul 2006)
12 Jul 2006; Luca Barbato <lu_zero@gentoo.org>
+files/qemu-0.8.0-gcc4-hacks.patch, +files/qemu-0.8.0-gcc4-opts.patch,
+qemu-softmmu-0.8.1-r1.ebuild:
Updated revision, with alsa and partial gcc4 support on x86 (phreak and
genstef found the patches)
09 Jun 2006; Michael Sterrett <mr_bones_@gentoo.org>
-files/qemu-softmmu-0.7.0-errno.patch, -files/kqemu-0.7.1-sysfs.patch,
-files/kqemu-sysfs.patch, -qemu-softmmu-0.7.0-r1.ebuild,
-qemu-softmmu-0.7.1.ebuild, -qemu-softmmu-0.7.1-r1.ebuild,
-qemu-softmmu-0.7.2.ebuild:
clean out old files
*qemu-softmmu-0.8.1 (06 May 2006)
06 May 2006; Luca Barbato <lu_zero@gentoo.org> +qemu-softmmu-0.8.1.ebuild:
New version
28 Apr 2006; Luca Barbato <lu_zero@gentoo.org>
qemu-softmmu-0.8.0.20060329.ebuild:
Stray epatch removed
27 Apr 2006; Marien Zwart <marienz@gentoo.org>
files/digest-qemu-softmmu-0.7.0-r1, files/digest-qemu-softmmu-0.7.1,
files/digest-qemu-softmmu-0.7.1-r1, files/digest-qemu-softmmu-0.7.2,
files/digest-qemu-softmmu-0.8.0, files/digest-qemu-softmmu-0.8.0.20060329,
Manifest:
Fixing SHA256 digest for real, pass three...
27 Apr 2006; Marien Zwart <marienz@gentoo.org>
files/digest-qemu-softmmu-0.7.0-r1, files/digest-qemu-softmmu-0.7.1,
files/digest-qemu-softmmu-0.7.1-r1, files/digest-qemu-softmmu-0.7.2,
files/digest-qemu-softmmu-0.8.0, files/digest-qemu-softmmu-0.8.0.20060329,
Manifest:
Fixing SHA256 digest, pass two.
19 Apr 2006; Daniel Gryniewicz <dang@gentoo.org> ChangeLog:
Marked stable on amd64 per bug# 123972
16 Apr 2006; Michael Hanselmann <hansmi@gentoo.org>
qemu-softmmu-0.8.0.ebuild:
Stable on ppc.
01 Apr 2006; Luca Barbato <lu_zero@gentoo.org> qemu-softmmu-0.8.0.ebuild:
Restricted test feature
29 Mar 2006; Chris White <chriswhite@gentoo.org>
qemu-softmmu-0.8.0.ebuild:
x86 stable for qemu-softmmu-0.8.0 bug #123972.
08 Jan 2006; Luca Barbato <lu_zero@gentoo.org> qemu-softmmu-0.8.0.ebuild:
Disable gcc checks, thanks to Robert Führicht <the_master_of_disaster@gmx.at>
*qemu-softmmu-0.8.0 (23 Dec 2005)
23 Dec 2005; Luca Barbato <lu_zero@gentoo.org> +qemu-softmmu-0.8.0.ebuild:
New version
01 Dec 2005; <dang@gentoo.org> qemu-softmmu-0.7.0-r1.ebuild,
qemu-softmmu-0.7.1.ebuild, qemu-softmmu-0.7.1-r1.ebuild,
qemu-softmmu-0.7.2.ebuild:
Mark 0.7.2 stable, with workign kqemu. Remove amd64 from older, nonworking
versions
*qemu-softmmu-0.7.2 (11 Sep 2005)
11 Sep 2005; Luca Barbato <lu_zero@gentoo.org> +qemu-softmmu-0.7.2.ebuild:
New release
19 Aug 2005; Aron Griffis <agriffis@gentoo.org>
qemu-softmmu-0.7.1-r1.ebuild:
Minor ebuild fixups, particularly move MODULE_NAMES setting into pkg_setup.
The kqemu-sysfs patch is not compatible with 2.6.13-rc1+ because the new
interfaces are GPL-only, so refrain from applying the patch on those
versions; http://lkml.org/lkml/2005/7/4/5
*qemu-softmmu-0.7.1-r1 (06 Aug 2005)
06 Aug 2005; Luca Barbato <lu_zero@gentoo.org>
+qemu-softmmu-0.7.1-r1.ebuild:
Fix bug #101524
26 Jul 2005; Luca Barbato <lu_zero@gentoo.org>
+files/kqemu-0.7.1-sysfs.patch, qemu-softmmu-0.7.1.ebuild:
updated the sysfs patch, thanks to Philippe Weibel <philippe.weibel@free.fr>
26 Jul 2005; Luca Barbato <lu_zero@gentoo.org> qemu-softmmu-0.7.1.ebuild:
Fixes and workarounds for the latest kernels.
*qemu-softmmu-0.7.1 (25 Jul 2005)
25 Jul 2005; Luca Barbato <lu_zero@gentoo.org> +qemu-softmmu-0.7.1.ebuild:
New version
*qemu-softmmu-0.7.0-r1 (18 Jun 2005)
18 Jun 2005; Luca Barbato <lu_zero@gentoo.org>
+files/qemu-softmmu-0.7.0-errno.patch, +files/kqemu-sysfs.patch,
+metadata.xml, +qemu-softmmu-0.7.0-r1.ebuild:
qemu split ebuild, system emulators

View File

@@ -0,0 +1,25 @@
-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1
AUX qemu-softmmu-0.9.0-block-qcow2.patch 346 RMD160 d9c11c082fce158e5fbdaceb5e87a327877de58c SHA1 976bd2727f8bdbad999ea2c23112dcbe550bbf4c SHA256 bfea37a8fc718bcee6f31df02c3095094c58d3ace952a7e7789784d6b3471c5a
AUX qemu-softmmu-0.9.0-ide-cd.patch 1764 RMD160 5d19bd67c74734c4e66f67dc136adb6f08fa418f SHA1 152fd0403c0644c275ac4aee539139ee5bffd262 SHA256 1f0d9d52e3ead71f0f250902993d1a7d3fb9c88be23870f5559a1596c42bdaf5
AUX qemu-softmmu-0.9.1-CVE-2008-0928.patch 9346 RMD160 79e4dbf7643d7057da4a74350833c907342fba1e SHA1 2ec9c89e6a995db97aa03cdab490fc0e5cef650c SHA256 ca040bdb401e6cdfe4f009e6874d25853103965370b19756724127b0fd4df559
AUX qemu-softmmu-0.9.1-CVE-2008-2004.patch 2002 RMD160 88f121766426b1b564d829bf6287aa0b99733ca7 SHA1 208701bd008b119f80553ff4dc441de87ddc98aa SHA256 15918d0e46a23d9b7283088489ce08be41a6ec9ced5df0f55ce1f8bcaa50fac3
AUX qemu-softmmu-0.9.1-block-device-address-range.patch 7904 RMD160 5653db42b048a0f1748b5394b7382fa3f2edc2a8 SHA1 258a10d73348683fbc7659110b0da57e0003cc46 SHA256 39268b7caebe64d11cd538974def842bedccca0894423f1d003574b8f39e9ecf
DIST qemu-0.9.0.tar.gz 1901741 RMD160 4296542b6da18a6ac93d20787330d3c1c2ac0a19 SHA1 1e57e48a06eb8729913d92601000466eecef06cb SHA256 491facf9335654967ee53d8fb3540a274bfcbdcc225506bd38c4ee8e9ab405c1
DIST qemu-0.9.1.tar.gz 2804104 RMD160 ee7bdb55a4540df2082d4bde9ebfd2f4e6f201a5 SHA1 630ea20b5989f0df00128de7f7be661c573ed041 SHA256 4756d0b4a4dc7dd88354bc6b37d381e4462dd328d0feef94803e90c0455835a5
EBUILD qemu-softmmu-0.9.0-r1.ebuild 3175 RMD160 8a7d2bc7dd359671e5350537da075fc169168b60 SHA1 681d7c1f8ff28c30a4e9135e1e54d4075cd8fe7b SHA256 a381f8a2e983e6e6266657adab2cc59605bb3efc416dec4b7f901a51e0666412
EBUILD qemu-softmmu-0.9.0.ebuild 3129 RMD160 dc0666aa7499db65af3f78d0d94a4253750927d5 SHA1 7493550b324f11ee72aa5ca994cdd207eb383c6f SHA256 ddd4eb920698c27d70a27d20eb1877b37a7824689340821f8cfe16698100942c
EBUILD qemu-softmmu-0.9.1-r1.ebuild 2904 RMD160 102b8519c20d6df891b9373e0c0f0ca13bafc82d SHA1 b9c737efb10f7bb120956d0ccf9281a3417e3f76 SHA256 ade319575b20682fdcfc0084f6234348e72fac742db179f97c2d55881a1d2a49
EBUILD qemu-softmmu-0.9.1-r2.ebuild 3449 RMD160 8710a61749937c51bc2bd8e0d089cde0bcc6c4ef SHA1 4b89d7278be7673732b7f9041b42968e0c401a80 SHA256 98c1893c363600d859cb1ba1b6c59d1aa70125d082f1fbb0ed2fae28a39bfab8
EBUILD qemu-softmmu-0.9.1-r3.ebuild 3504 RMD160 0fd34c21dbabf5f53d2327cf74edf2f2e5226244 SHA1 ff5cf3195a0cede66d4bb406031bb9e215d85e33 SHA256 7e888ccdf6018845995c392172229218702452a3abea6bd877bd9ab480464c3e
EBUILD qemu-softmmu-0.9.1.ebuild 2832 RMD160 150a50f0010d93200e611af2181cc5df76a91781 SHA1 213f88845793c90dd59e6eff978d839e9d0da3fe SHA256 2c11e38b4b501ef9300e35eeec00236feedad5bcc69decfb839ad52260609f13
MISC ChangeLog 9553 RMD160 8f8bd1c79ea13d18d2dff387cab19611114b9386 SHA1 c4648c024c2507421e212e7d4d66b723bbbbd80a SHA256 f0a6e4970b1f13ec5f2cb7f449beb0b388698e6bcfac305e1bb1ed51c52df223
MISC metadata.xml 317 RMD160 ec5f64543d9db447cef26e8c71489ec7c732385c SHA1 f159811a9bba96ae163582b6d2aea10fc238f32b SHA256 46819898b75a387dea3828f35205aa0caab4a9b6fe7b44fea8f7b694e9fcbafd
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v2.0.9 (GNU/Linux)
iEYEARECAAYFAkiOGdAACgkQoeSe8B0zEfxk/ACffZfkV8UdIs+POwo27HjRnBKj
3KkAniKqhldVnukkdgVRIkqJsHjhzHQx
=ImtA
-----END PGP SIGNATURE-----

View File

@@ -0,0 +1,38 @@
# --- T2-COPYRIGHT-NOTE-BEGIN ---
# This copyright note is auto-generated by ./scripts/Create-CopyPatch.
#
# T2 SDE: package/.../qemu/hotfix.patch
# Copyright (C) 2008 The T2 SDE Project
#
# More information can be found in the files COPYING and README.
#
# This patch file is dual-licensed. It is available under the license the
# patched project is licensed under, as long as it is an OpenSource license
# as defined at http://www.opensource.org/ (e.g. BSD, X11) or under the terms
# of the GNU General Public License as published by the Free Software
# Foundation; either version 2 of the License, or (at your option) any later
# version.
# --- T2-COPYRIGHT-NOTE-END ---
Currently not compiling architectures to due our gcc4 patchery relating to:
dyngen: Unable to replace ret with jmp in op_cmp_str_T0_T1
- Rene Rebe <rene@exactcode.de>
--- qemu-0.9.1/configure.vanilla 2008-01-22 13:56:47.000000000 +0100
+++ qemu-0.9.1/configure 2008-01-22 13:56:56.000000000 +0100
@@ -522,11 +522,11 @@
if test -z "$target_list" ; then
# these targets are portable
if [ "$softmmu" = "yes" ] ; then
- target_list="i386-softmmu sparc-softmmu x86_64-softmmu mips-softmmu mipsel-softmmu mips64-softmmu mips64el-softmmu arm-softmmu ppc-softmmu ppcemb-softmmu ppc64-softmmu m68k-softmmu sh4-softmmu sh4eb-softmmu cris-softmmu"
+ target_list="i386-softmmu x86_64-softmmu mips64-softmmu mips64el-softmmu ppc-softmmu ppc64-softmmu m68k-softmmu cris-softmmu"
fi
# the following are Linux specific
if [ "$linux_user" = "yes" ] ; then
- target_list="i386-linux-user arm-linux-user armeb-linux-user sparc-linux-user sparc64-linux-user sparc32plus-linux-user mips-linux-user mipsel-linux-user m68k-linux-user alpha-linux-user sh4-linux-user sh4eb-linux-user ppc-linux-user ppc64-linux-user ppc64abi32-linux-user x86_64-linux-user cris-linux-user $target_list"
+ target_list="i386-linux-user sparc-linux-user sparc64-linux-user sparc32plus-linux-user mips-linux-user mipsel-linux-user m68k-linux-user alpha-linux-user ppc-linux-user ppc64-linux-user ppc64abi32-linux-user x86_64-linux-user cris-linux-user $target_list"
fi
# the following are Darwin specific
if [ "$darwin_user" = "yes" ] ; then

View File

@@ -0,0 +1,42 @@
# --- T2-COPYRIGHT-NOTE-BEGIN ---
# This copyright note is auto-generated by ./scripts/Create-CopyPatch.
#
# T2 SDE: package/.../qemu/qemu-0.9.0-i386-FORCE_RET.patch
# Copyright (C) 2008 The T2 SDE Project
#
# More information can be found in the files COPYING and README.
#
# This patch file is dual-licensed. It is available under the license the
# patched project is licensed under, as long as it is an OpenSource license
# as defined at http://www.opensource.org/ (e.g. BSD, X11) or under the terms
# of the GNU General Public License as published by the Free Software
# Foundation; either version 2 of the License, or (at your option) any later
# version.
# --- T2-COPYRIGHT-NOTE-END ---
2007-02-01 Mike Kronenberg <mike.kronenberg@kronenberg.org>
* Fix for QEMU 0.9.0.
2006-06-12 Gwenole Beauchesne <gbeauchesne@mandriva.com>
* Try to enforce one exit point per synthetic opcode (gcc4).
--- qemu-0.8.0/target-i386/op.c.i386-FORCE_RET 2005-12-19 23:51:53.000000000 +0100
+++ qemu-0.8.0/target-i386/op.c 2006-02-12 17:51:40.000000000 +0100
@@ -1032,6 +1032,7 @@ void OPPROTO op_aaa(void)
}
EAX = (EAX & ~0xffff) | al | (ah << 8);
CC_SRC = eflags;
+ FORCE_RET();
}
void OPPROTO op_aas(void)
@@ -1056,6 +1057,7 @@ void OPPROTO op_aas(void)
}
EAX = (EAX & ~0xffff) | al | (ah << 8);
CC_SRC = eflags;
+ FORCE_RET();
}
/* segment handling */

View File

@@ -0,0 +1,41 @@
# --- T2-COPYRIGHT-NOTE-BEGIN ---
# This copyright note is auto-generated by ./scripts/Create-CopyPatch.
#
# T2 SDE: package/.../qemu/qemu-0.9.1-always_inline.patch
# Copyright (C) 2008 The T2 SDE Project
#
# More information can be found in the files COPYING and README.
#
# This patch file is dual-licensed. It is available under the license the
# patched project is licensed under, as long as it is an OpenSource license
# as defined at http://www.opensource.org/ (e.g. BSD, X11) or under the terms
# of the GNU General Public License as published by the Free Software
# Foundation; either version 2 of the License, or (at your option) any later
# version.
# --- T2-COPYRIGHT-NOTE-END ---
--- a/host-utils.h
+++ b/host-utils.h
@@ -23,6 +23,8 @@
* THE SOFTWARE.
*/
+#include "osdep.h"
+
#if defined(__x86_64__)
#define __HAVE_FAST_MULU64__
static always_inline void mulu64 (uint64_t *plow, uint64_t *phigh,
diff --git a/osdep.h b/osdep.h
index bc513ad..2f56f2b 100644
--- a/osdep.h
+++ b/osdep.h
@@ -33,7 +33,9 @@
#define always_inline __attribute__ (( always_inline )) __inline__
#endif
#endif
+#if !((__GNUC__ < 3) || defined(__APPLE__))
#define inline always_inline
+#endif
#ifdef __i386__
#define REGPARM(n) __attribute((regparm(n)))

View File

@@ -0,0 +1,39 @@
# --- T2-COPYRIGHT-NOTE-BEGIN ---
# This copyright note is auto-generated by ./scripts/Create-CopyPatch.
#
# T2 SDE: package/.../qemu/qemu-0.9.1-enforce-16byte-stack-boundary.patch
# Copyright (C) 2008 The T2 SDE Project
#
# More information can be found in the files COPYING and README.
#
# This patch file is dual-licensed. It is available under the license the
# patched project is licensed under, as long as it is an OpenSource license
# as defined at http://www.opensource.org/ (e.g. BSD, X11) or under the terms
# of the GNU General Public License as published by the Free Software
# Foundation; either version 2 of the License, or (at your option) any later
# version.
# --- T2-COPYRIGHT-NOTE-END ---
2008-01-12 Mike kronenberg <mike.kronenberg@kronenberg.org>
* Fix for QEMU 0.9.1.
2007-02-01 Mike kronenberg <mike.kronenberg@kronenberg.org>
* Fix for QEMU 0.9.0.
2006-02-12 Gwenole Beauchesne <gbeauchesne@mandriva.com>
* Enforce 16-byte boundaries.
--- qemu-0.8.0/Makefile.target.enforce-16byte-stack-boundary 2006-02-12 17:46:54.000000000 +0100
+++ qemu-0.8.0/Makefile.target 2006-02-12 17:55:24.000000000 +0100
@@ -67,7 +67,7 @@ endif
ifeq ($(ARCH),i386)
HELPER_CFLAGS+=-fomit-frame-pointer
-OP_CFLAGS+=-mpreferred-stack-boundary=2 -fomit-frame-pointer
+OP_CFLAGS+=-fomit-frame-pointer
ifdef TARGET_GPROF
USE_I386_LD=y
endif

View File

@@ -0,0 +1,138 @@
# --- T2-COPYRIGHT-NOTE-BEGIN ---
# This copyright note is auto-generated by ./scripts/Create-CopyPatch.
#
# T2 SDE: package/.../qemu/qemu-0.9.1-gcc4-hacks.patch
# Copyright (C) 2008 The T2 SDE Project
#
# More information can be found in the files COPYING and README.
#
# This patch file is dual-licensed. It is available under the license the
# patched project is licensed under, as long as it is an OpenSource license
# as defined at http://www.opensource.org/ (e.g. BSD, X11) or under the terms
# of the GNU General Public License as published by the Free Software
# Foundation; either version 2 of the License, or (at your option) any later
# version.
# --- T2-COPYRIGHT-NOTE-END ---
2008-01-12 Mike Kronenberg <mike.kronenberg@kronenberg.org>
* softmmu_header.h: Fix for QEMU 0.9.1.
2005-10-28 Gwenole Beauchesne <gbeauchesne@mandriva.com>
* Various additional hacks for GCC4.
--- qemu-0.7.2/target-i386/ops_sse.h.gcc4-hacks 2005-09-04 19:11:31.000000000 +0200
+++ qemu-0.7.2/target-i386/ops_sse.h 2005-10-28 10:09:21.000000000 +0200
@@ -34,6 +34,12 @@
#define Q(n) XMM_Q(n)
#define SUFFIX _xmm
#endif
+#if defined(__i386__) && __GNUC__ >= 4
+#define RegCopy(d, s) __builtin_memcpy(&(d), &(s), sizeof(d))
+#endif
+#ifndef RegCopy
+#define RegCopy(d, s) d = s
+#endif
void OPPROTO glue(op_psrlw, SUFFIX)(void)
{
@@ -570,7 +576,7 @@ void OPPROTO glue(op_pshufw, SUFFIX) (vo
r.W(1) = s->W((order >> 2) & 3);
r.W(2) = s->W((order >> 4) & 3);
r.W(3) = s->W((order >> 6) & 3);
- *d = r;
+ RegCopy(*d, r);
}
#else
void OPPROTO op_shufps(void)
--- qemu-0.7.2/target-i386/helper.c.gcc4-hacks 2005-09-04 19:11:31.000000000 +0200
+++ qemu-0.7.2/target-i386/helper.c 2005-10-28 10:09:21.000000000 +0200
@@ -3130,8 +3130,15 @@ void helper_fxrstor(target_ulong ptr, in
nb_xmm_regs = 8 << data64;
addr = ptr + 0xa0;
for(i = 0; i < nb_xmm_regs; i++) {
+#if defined(__i386__) && __GNUC__ >= 4
+ env->xmm_regs[i].XMM_L(0) = ldl(addr);
+ env->xmm_regs[i].XMM_L(1) = ldl(addr + 4);
+ env->xmm_regs[i].XMM_L(2) = ldl(addr + 8);
+ env->xmm_regs[i].XMM_L(3) = ldl(addr + 12);
+#else
env->xmm_regs[i].XMM_Q(0) = ldq(addr);
env->xmm_regs[i].XMM_Q(1) = ldq(addr + 8);
+#endif
addr += 16;
}
}
--- qemu-0.7.2/cpu-all.h.gcc4-hacks 2005-09-04 19:11:31.000000000 +0200
+++ qemu-0.7.2/cpu-all.h 2005-10-28 10:09:21.000000000 +0200
@@ -339,7 +339,13 @@
static inline void stq_le_p(void *ptr, uint64_t v)
{
+#if defined(__i386__) && __GNUC__ >= 4
+ const union { uint64_t v; uint32_t p[2]; } x = { .v = v };
+ ((uint32_t *)ptr)[0] = x.p[0];
+ ((uint32_t *)ptr)[1] = x.p[1];
+#else
*(uint64_t *)ptr = v;
+#endif
}
/* float access */
--- qemu-0.7.2/softmmu_header.h.gcc4-hacks 2005-10-28 10:08:08.000000000 +0200
+++ qemu-0.7.2/softmmu_header.h 2005-10-28 10:09:21.000000000 +0200
@@ -104,7 +104,7 @@
void REGPARM(2) glue(glue(__st, SUFFIX), MMUSUFFIX)(target_ulong addr, DATA_TYPE v, int mmu_idx);
#if (DATA_SIZE <= 4) && (TARGET_LONG_BITS == 32) && defined(__i386__) && \
- (ACCESS_TYPE < NB_MMU_MODES) && defined(ASM_SOFTMMU)
+ (ACCESS_TYPE < NB_MMU_MODES) && defined(ASM_SOFTMMU) && (__GNUC__ < 4)
#define CPU_TLB_ENTRY_BITS 4
@@ -131,7 +131,7 @@ static inline RES_TYPE glue(glue(ld, USU
"m" (*(uint32_t *)offsetof(CPUState, tlb_read[CPU_MEM_INDEX][0].address)),
"i" (CPU_MEM_INDEX),
"m" (*(uint8_t *)&glue(glue(__ld, SUFFIX), MMUSUFFIX))
- : "%eax", "%ecx", "%edx", "memory", "cc");
+ : "%eax", "%edx", "memory", "cc");
return res;
}
@@ -178,13 +178,14 @@ static inline int glue(glue(lds, SUFFIX)
"m" (*(uint32_t *)offsetof(CPUState, tlb_read[CPU_MEM_INDEX][0].address)),
"i" (CPU_MEM_INDEX),
"m" (*(uint8_t *)&glue(glue(__ld, SUFFIX), MMUSUFFIX))
- : "%eax", "%ecx", "%edx", "memory", "cc");
+ : "%eax", "%edx", "memory", "cc");
return res;
}
#endif
-static inline void glue(glue(st, SUFFIX), MEMSUFFIX)(target_ulong ptr, RES_TYPE v)
+static inline void glue(glue(st, SUFFIX), MEMSUFFIX)(target_ulong ptr, RES_TYPE val)
{
+ RES_TYPE v = val;
asm volatile ("movl %0, %%edx\n"
"movl %0, %%eax\n"
"shrl %3, %%edx\n"
@@ -236,16 +237,14 @@
"2:\n"
:
: "r" (ptr),
-/* NOTE: 'q' would be needed as constraint, but we could not use it
- with T1 ! */
- "r" (v),
+ "q" (v),
"i" ((CPU_TLB_SIZE - 1) << CPU_TLB_ENTRY_BITS),
"i" (TARGET_PAGE_BITS - CPU_TLB_ENTRY_BITS),
"i" (TARGET_PAGE_MASK | (DATA_SIZE - 1)),
"m" (*(uint32_t *)offsetof(CPUState, tlb_table[CPU_MMU_INDEX][0].addr_write)),
"i" (CPU_MMU_INDEX),
"m" (*(uint8_t *)&glue(glue(__st, SUFFIX), MMUSUFFIX))
- : "%eax", "%ecx", "%edx", "memory", "cc");
+ : "%eax", "%edx", "memory", "cc");
}
#else

View File

@@ -0,0 +1,57 @@
# --- T2-COPYRIGHT-NOTE-BEGIN ---
# This copyright note is auto-generated by ./scripts/Create-CopyPatch.
#
# T2 SDE: package/.../qemu/qemu-0.9.1-gcc4-opts.patch
# Copyright (C) 2008 The T2 SDE Project
#
# More information can be found in the files COPYING and README.
#
# This patch file is dual-licensed. It is available under the license the
# patched project is licensed under, as long as it is an OpenSource license
# as defined at http://www.opensource.org/ (e.g. BSD, X11) or under the terms
# of the GNU General Public License as published by the Free Software
# Foundation; either version 2 of the License, or (at your option) any later
# version.
# --- T2-COPYRIGHT-NOTE-END ---
2008-01-12 Mike Kronenberg <mike.kronenberg@kronenberg.org>
* cpu-exec.c: Fix for QEMU 0.9.1.
2005-11-11 Gwenole Beauchesne <gbeauchesne@mandriva.com>
* Globaaly save %ebx, %esi, %edi on entry to generated
function. This avoids some register spills in synthetic opcodes.
NOTE: this also easily fixes gcc4 compiled qemu-system-x86_64 on x86.
--- qemu-0.7.2/cpu-exec.c.gcc4-opts 2005-09-04 19:11:31.000000000 +0200
+++ qemu-0.7.2/cpu-exec.c 2005-11-11 17:40:47.000000000 +0100
@@ -561,6 +561,15 @@ int cpu_exec(CPUState *env1)
: /* no outputs */
: "r" (gen_func)
: "r1", "r2", "r3", "r8", "r9", "r10", "r12", "r14");
+#elif defined(TARGET_X86_64) && defined(__i386__)
+ asm volatile ("push %%ebx\n"
+ "push %%esi\n"
+ "push %%edi\n"
+ "call *%0\n"
+ "pop %%edi\n"
+ "pop %%esi\n"
+ "pop %%ebx\n"
+ : : "r" (gen_func) : "ebx", "esi", "edi");
#elif defined(__ia64)
struct fptr {
void *ip;
--- qemu-0.7.2/Makefile.target.gcc4-opts 2005-11-11 16:26:33.000000000 +0100
+++ qemu-0.7.2/Makefile.target 2005-11-11 17:59:56.000000000 +0100
@@ -65,6 +65,10 @@ OP_CFLAGS+= -falign-functions=0 -fno-gcs
else
OP_CFLAGS+= -malign-functions=0
endif
+ifeq ($(TARGET_ARCH), x86_64)
+# XXX globally save %ebx, %esi, %edi on entry to generated function
+OP_CFLAGS+= -fcall-used-ebx -fcall-used-esi -fcall-used-edi
+endif
ifdef TARGET_GPROF
USE_I386_LD=y

View File

@@ -0,0 +1,911 @@
# --- T2-COPYRIGHT-NOTE-BEGIN ---
# This copyright note is auto-generated by ./scripts/Create-CopyPatch.
#
# T2 SDE: package/.../qemu/qemu-0.9.1-gcc4.patch
# Copyright (C) 2008 The T2 SDE Project
#
# More information can be found in the files COPYING and README.
#
# This patch file is dual-licensed. It is available under the license the
# patched project is licensed under, as long as it is an OpenSource license
# as defined at http://www.opensource.org/ (e.g. BSD, X11) or under the terms
# of the GNU General Public License as published by the Free Software
# Foundation; either version 2 of the License, or (at your option) any later
# version.
# --- T2-COPYRIGHT-NOTE-END ---
2008-01-12 Mike Kronenberg <mike.kronenberg@kronenberg.org>
* dyngen-exec.h: Fix for QEMU 0.9.1.
* dyngen-c.h: Fix for QEMU 0.9.1.
2007-02-01 Mike Kronenberg <mike.kronenberg@kronenberg.org>
* target-ppc/exec.h: Fix for QEMU 0.9.0.
* dyngen-exec.h: Fix for QEMU 0.9.0.
2005-06-02 Gwenole Beauchesne <gbeauchesne@mandriva.com>
* dyngen.c (trace_i386_insn): Fix push/imul case with 8-bit
immediate.
2005-05-11 Paul Brook <paul@codesourcery.com>
* gcc4 host support.
--- qemu-0.7.0/target-ppc/exec.h.gcc4 2005-04-27 22:52:05.000000000 +0200
+++ qemu-0.7.0/target-ppc/exec.h 2005-06-02 21:41:51.000000000 +0200
@@ -64,11 +64,7 @@ #define FT0 (env->ft0)
#define FT1 (env->ft1)
#define FT2 (env->ft2)
-#if defined (DEBUG_OP)
-# define RETURN() __asm__ __volatile__("nop" : : : "memory");
-#else
-# define RETURN() __asm__ __volatile__("" : : : "memory");
-#endif
+#define RETURN() FORCE_RET()
#include "cpu.h"
#include "exec-all.h"
--- qemu-0.7.0/dyngen-exec.h.gcc4 2005-04-27 22:52:05.000000000 +0200
+++ qemu-0.7.0/dyngen-exec.h 2005-06-02 21:41:51.000000000 +0200
@@ -194,7 +194,12 @@ extern int printf(const char *, ...);
#endif
/* force GCC to generate only one epilog at the end of the function */
+#if defined(__i386__) || defined(__x86_64__)
+/* Also add 4 bytes of padding so that we can replace the ret with a jmp. */
+#define FORCE_RET() asm volatile ("nop;nop;nop;nop");
+#else
#define FORCE_RET() __asm__ __volatile__("" : : : "memory");
+#endif
#ifndef OPPROTO
#define OPPROTO
@@ -251,10 +256,17 @@ extern int __op_jmp0, __op_jmp1, __op_jm
#endif
#if defined(__i386__)
-#define EXIT_TB() asm volatile ("ret")
-#define GOTO_LABEL_PARAM(n) asm volatile ("jmp " ASM_NAME(__op_gen_label) #n)
+/* Dyngen will replace hlt instructions with a ret instruction. Inserting a
+ ret directly would confuse dyngen. */
+#define EXIT_TB() asm volatile ("hlt")
+/* Dyngen will replace cli with 0x9e (jmp).
+ We generate the offset manually. */
+#define GOTO_LABEL_PARAM(n) \
+ asm volatile ("cli;.long " ASM_NAME(__op_gen_label) #n " - 1f;1:")
#elif defined(__x86_64__)
-#define EXIT_TB() asm volatile ("ret")
-#define GOTO_LABEL_PARAM(n) asm volatile ("jmp " ASM_NAME(__op_gen_label) #n)
+/* The same as i386. */
+#define EXIT_TB() asm volatile ("hlt")
+#define GOTO_LABEL_PARAM(n) \
+ asm volatile ("cli;.long " ASM_NAME(__op_gen_label) #n " - 1f;1:")
#elif defined(__powerpc__)
#define EXIT_TB() asm volatile ("blr")
--- qemu-0.7.0/dyngen.c.gcc4 2005-04-27 22:52:05.000000000 +0200
+++ qemu-0.7.0/dyngen.c 2005-06-02 22:25:06.000000000 +0200
@@ -32,6 +32,8 @@
#include "config-host.h"
+//#define DEBUG_OP
+
/* NOTE: we test CONFIG_WIN32 instead of _WIN32 to enabled cross
compilation */
#if defined(CONFIG_WIN32)
@@ -1343,6 +1345,644 @@ int arm_emit_ldr_info(const char *name,
#endif
+#if defined(HOST_I386) || defined(HOST_X86_64)
+
+/* This byte is the first byte of an instruction. */
+#define FLAG_INSN (1 << 0)
+/* This byte has been processed as part of an instruction. */
+#define FLAG_SCANNED (1 << 1)
+/* This instruction is a return instruction. Gcc cometimes generates prefix
+ bytes, so may be more than one byte long. */
+#define FLAG_RET (1 << 2)
+/* This is either the target of a jump, or the preceeding instruction uses
+ a pc-relative offset. */
+#define FLAG_TARGET (1 << 3)
+/* This is a magic instruction that needs fixing up. */
+#define FLAG_EXIT (1 << 4)
+#define MAX_EXITS 5
+
+static void
+bad_opcode(const char *name, uint32_t op)
+{
+ error("Unsupported opcode %0*x in %s", (op > 0xff) ? 4 : 2, op, name);
+}
+
+/* Mark len bytes as scanned, Returns insn_size + len. Reports an error
+ if these bytes have already been scanned. */
+static int
+eat_bytes(const char *name, char *flags, int insn, int insn_size, int len)
+{
+ while (len > 0) {
+ /* This should never occur in sane code. */
+ if (flags[insn + insn_size] & FLAG_SCANNED)
+ error ("Overlapping instructions in %s", name);
+ flags[insn + insn_size] |= FLAG_SCANNED;
+ insn_size++;
+ len--;
+ }
+ return insn_size;
+}
+
+static void
+trace_i386_insn (const char *name, uint8_t *start_p, char *flags, int insn,
+ int len)
+{
+ uint8_t *ptr;
+ uint8_t op;
+ int modrm;
+ int is_prefix;
+ int op_size;
+ int addr_size;
+ int insn_size;
+ int is_ret;
+ int is_condjmp;
+ int is_jmp;
+ int is_exit;
+ int is_pcrel;
+ int immed;
+ int seen_rexw;
+ int32_t disp;
+
+ ptr = start_p + insn;
+ /* nonzero if this insn has a ModR/M byte. */
+ modrm = 1;
+ /* The size of the immediate value in this instruction. */
+ immed = 0;
+ /* The operand size. */
+ op_size = 4;
+ /* The address size */
+ addr_size = 4;
+ /* The total length of this instruction. */
+ insn_size = 0;
+ is_prefix = 1;
+ is_ret = 0;
+ is_condjmp = 0;
+ is_jmp = 0;
+ is_exit = 0;
+ seen_rexw = 0;
+ is_pcrel = 0;
+
+ while (is_prefix) {
+ op = ptr[insn_size];
+ insn_size = eat_bytes(name, flags, insn, insn_size, 1);
+ is_prefix = 0;
+ switch (op >> 4) {
+ case 0:
+ case 1:
+ case 2:
+ case 3:
+ if (op == 0x0f) {
+ /* two-byte opcode. */
+ op = ptr[insn_size];
+ insn_size = eat_bytes(name, flags, insn, insn_size, 1);
+ switch (op >> 4) {
+ case 0:
+ if ((op & 0xf) > 3)
+ modrm = 0;
+ break;
+ case 1: /* vector move or prefetch */
+ case 2: /* various moves and vector compares. */
+ case 4: /* cmov */
+ case 5: /* vector instructions */
+ case 6:
+ case 13:
+ case 14:
+ case 15:
+ break;
+ case 7: /* mmx */
+ if (op & 0x77) /* emms */
+ modrm = 0;
+ break;
+ case 3: /* wrmsr, rdtsc, rdmsr, rdpmc, sysenter, sysexit */
+ modrm = 0;
+ break;
+ case 8: /* long conditional jump */
+ is_condjmp = 1;
+ immed = op_size;
+ modrm = 0;
+ break;
+ case 9: /* setcc */
+ break;
+ case 10:
+ switch (op & 0x7) {
+ case 0: /* push fs/gs */
+ case 1: /* pop fs/gs */
+ case 2: /* cpuid/rsm */
+ modrm = 0;
+ break;
+ case 4: /* shld/shrd immediate */
+ immed = 1;
+ break;
+ default: /* Normal instructions with a ModR/M byte. */
+ break;
+ }
+ break;
+ case 11:
+ switch (op & 0xf) {
+ case 10: /* bt, bts, btr, btc */
+ immed = 1;
+ break;
+ default:
+ /* cmpxchg, lss, btr, lfs, lgs, movzx, btc, bsf, bsr
+ undefined, and movsx */
+ break;
+ }
+ break;
+ case 12:
+ if (op & 8) {
+ /* bswap */
+ modrm = 0;
+ } else {
+ switch (op & 0x7) {
+ case 2:
+ case 4:
+ case 5:
+ case 6:
+ immed = 1;
+ break;
+ default:
+ break;
+ }
+ }
+ break;
+ }
+ } else if ((op & 0x07) <= 0x3) {
+ /* General arithmentic ax. */
+ } else if ((op & 0x07) <= 0x5) {
+ /* General arithmetic ax, immediate. */
+ if (op & 0x01)
+ immed = op_size;
+ else
+ immed = 1;
+ modrm = 0;
+ } else if ((op & 0x23) == 0x22) {
+ /* Segment prefix. */
+ is_prefix = 1;
+ } else {
+ /* Segment register push/pop or DAA/AAA/DAS/AAS. */
+ modrm = 0;
+ }
+ break;
+
+#if defined(HOST_X86_64)
+ case 4: /* rex prefix. */
+ is_prefix = 1;
+ /* The address/operand size is actually 64-bit, but the immediate
+ values in the instruction are still 32-bit. */
+ op_size = 4;
+ addr_size = 4;
+ if (op & 8)
+ seen_rexw = 1;
+ break;
+#else
+ case 4: /* inc/dec register. */
+#endif
+ case 5: /* push/pop general register. */
+ modrm = 0;
+ break;
+
+ case 6:
+ switch (op & 0x0f) {
+ case 0: /* pusha */
+ case 1: /* popa */
+ modrm = 0;
+ break;
+ case 2: /* bound */
+ case 3: /* arpl */
+ break;
+ case 4: /* FS */
+ case 5: /* GS */
+ is_prefix = 1;
+ break;
+ case 6: /* opcode size prefix. */
+ op_size = 2;
+ is_prefix = 1;
+ break;
+ case 7: /* Address size prefix. */
+ addr_size = 2;
+ is_prefix = 1;
+ break;
+ case 8: /* push immediate */
+ immed = op_size;
+ modrm = 0;
+ break;
+ case 10: /* push 8-bit immediate */
+ immed = 1;
+ modrm = 0;
+ break;
+ case 9: /* imul immediate */
+ immed = op_size;
+ break;
+ case 11: /* imul 8-bit immediate */
+ immed = 1;
+ break;
+ case 12: /* insb */
+ case 13: /* insw */
+ case 14: /* outsb */
+ case 15: /* outsw */
+ modrm = 0;
+ break;
+ }
+ break;
+
+ case 7: /* Short conditional jump. */
+ is_condjmp = 1;
+ immed = 1;
+ modrm = 0;
+ break;
+
+ case 8:
+ if ((op & 0xf) <= 3) {
+ /* arithmetic immediate. */
+ if ((op & 3) == 1)
+ immed = op_size;
+ else
+ immed = 1;
+ }
+ /* else test, xchg, mov, lea or pop general. */
+ break;
+
+ case 9:
+ /* Various single-byte opcodes with no modrm byte. */
+ modrm = 0;
+ if (op == 10) {
+ /* Call */
+ immed = 4;
+ }
+ break;
+
+ case 10:
+ switch ((op & 0xe) >> 1) {
+ case 0: /* mov absoliute immediate. */
+ case 1:
+ if (seen_rexw)
+ immed = 8;
+ else
+ immed = addr_size;
+ break;
+ case 4: /* test immediate. */
+ if (op & 1)
+ immed = op_size;
+ else
+ immed = 1;
+ break;
+ default: /* Various string ops. */
+ break;
+ }
+ modrm = 0;
+ break;
+
+ case 11: /* move immediate to register */
+ if (op & 8) {
+ if (seen_rexw)
+ immed = 8;
+ else
+ immed = op_size;
+ } else {
+ immed = 1;
+ }
+ modrm = 0;
+ break;
+
+ case 12:
+ switch (op & 0xf) {
+ case 0: /* shift immediate */
+ case 1:
+ immed = 1;
+ break;
+ case 2: /* ret immediate */
+ immed = 2;
+ modrm = 0;
+ bad_opcode(name, op);
+ break;
+ case 3: /* ret */
+ modrm = 0;
+ is_ret = 1;
+ case 4: /* les */
+ case 5: /* lds */
+ break;
+ case 6: /* mov immediate byte */
+ immed = 1;
+ break;
+ case 7: /* mov immediate */
+ immed = op_size;
+ break;
+ case 8: /* enter */
+ /* TODO: Is this right? */
+ immed = 3;
+ modrm = 0;
+ break;
+ case 10: /* retf immediate */
+ immed = 2;
+ modrm = 0;
+ bad_opcode(name, op);
+ break;
+ case 13: /* int */
+ immed = 1;
+ modrm = 0;
+ break;
+ case 11: /* retf */
+ case 15: /* iret */
+ modrm = 0;
+ bad_opcode(name, op);
+ break;
+ default: /* leave, int3 or into */
+ modrm = 0;
+ break;
+ }
+ break;
+
+ case 13:
+ if ((op & 0xf) >= 8) {
+ /* Coprocessor escape. For our purposes this is just a normal
+ instruction with a ModR/M byte. */
+ } else if ((op & 0xf) >= 4) {
+ /* AAM, AAD or XLAT */
+ modrm = 0;
+ }
+ /* else shift instruction */
+ break;
+
+ case 14:
+ switch ((op & 0xc) >> 2) {
+ case 0: /* loop or jcxz */
+ is_condjmp = 1;
+ immed = 1;
+ break;
+ case 1: /* in/out immed */
+ immed = 1;
+ break;
+ case 2: /* call or jmp */
+ switch (op & 3) {
+ case 0: /* call */
+ immed = op_size;
+ break;
+ case 1: /* long jump */
+ immed = 4;
+ is_jmp = 1;
+ break;
+ case 2: /* far jmp */
+ bad_opcode(name, op);
+ break;
+ case 3: /* short jmp */
+ immed = 1;
+ is_jmp = 1;
+ break;
+ }
+ break;
+ case 3: /* in/out register */
+ break;
+ }
+ modrm = 0;
+ break;
+
+ case 15:
+ switch ((op & 0xe) >> 1) {
+ case 0:
+ case 1:
+ is_prefix = 1;
+ break;
+ case 2:
+ case 4:
+ case 5:
+ case 6:
+ modrm = 0;
+ /* Some privileged insns are used as markers. */
+ switch (op) {
+ case 0xf4: /* hlt: Exit translation block. */
+ is_exit = 1;
+ break;
+ case 0xfa: /* cli: Jump to label. */
+ is_exit = 1;
+ immed = 4;
+ break;
+ case 0xfb: /* sti: TB patch jump. */
+ /* Mark the insn for patching, but continue sscanning. */
+ flags[insn] |= FLAG_EXIT;
+ immed = 4;
+ break;
+ }
+ break;
+ case 3: /* unary grp3 */
+ if ((ptr[insn_size] & 0x38) == 0) {
+ if (op == 0xf7)
+ immed = op_size;
+ else
+ immed = 1; /* test immediate */
+ }
+ break;
+ case 7: /* inc/dec grp4/5 */
+ /* TODO: This includes indirect jumps. We should fail if we
+ encounter one of these. */
+ break;
+ }
+ break;
+ }
+ }
+
+ if (modrm) {
+ if (addr_size != 4)
+ error("16-bit addressing mode used in %s", name);
+
+ disp = 0;
+ modrm = ptr[insn_size];
+ insn_size = eat_bytes(name, flags, insn, insn_size, 1);
+ modrm &= 0xc7;
+ switch ((modrm & 0xc0) >> 6) {
+ case 0:
+ if (modrm == 5)
+ disp = 4;
+ break;
+ case 1:
+ disp = 1;
+ break;
+ case 2:
+ disp = 4;
+ break;
+ }
+ if ((modrm & 0xc0) != 0xc0 && (modrm & 0x7) == 4) {
+ /* SIB byte */
+ if (modrm == 4 && (ptr[insn_size] & 0x7) == 5) {
+ disp = 4;
+ is_pcrel = 1;
+ }
+ insn_size = eat_bytes(name, flags, insn, insn_size, 1);
+ }
+ insn_size = eat_bytes(name, flags, insn, insn_size, disp);
+ }
+ insn_size = eat_bytes(name, flags, insn, insn_size, immed);
+ if (is_condjmp || is_jmp) {
+ if (immed == 1) {
+ disp = (int8_t)*(ptr + insn_size - 1);
+ } else {
+ disp = (((int32_t)*(ptr + insn_size - 1)) << 24)
+ | (((int32_t)*(ptr + insn_size - 2)) << 16)
+ | (((int32_t)*(ptr + insn_size - 3)) << 8)
+ | *(ptr + insn_size - 4);
+ }
+ disp += insn_size;
+ /* Jumps to external symbols point to the address of the offset
+ before relocation. */
+ /* ??? These are probably a tailcall. We could fix them up by
+ replacing them with jmp to EOB + call, but it's easier to just
+ prevent the compiler generating them. */
+ if (disp == 1)
+ error("Unconditional jump (sibcall?) in %s", name);
+ disp += insn;
+ if (disp < 0 || disp > len)
+ error("Jump outside instruction in %s", name);
+
+ if ((flags[disp] & (FLAG_INSN | FLAG_SCANNED)) == FLAG_SCANNED)
+ error("Overlapping instructions in %s", name);
+
+ flags[disp] |= (FLAG_INSN | FLAG_TARGET);
+ is_pcrel = 1;
+ }
+ if (is_pcrel) {
+ /* Mark the following insn as a jump target. This will stop
+ this instruction being moved. */
+ flags[insn + insn_size] |= FLAG_TARGET;
+ }
+ if (is_ret)
+ flags[insn] |= FLAG_RET;
+
+ if (is_exit)
+ flags[insn] |= FLAG_EXIT;
+
+ if (!(is_jmp || is_ret || is_exit))
+ flags[insn + insn_size] |= FLAG_INSN;
+}
+
+/* Scan a function body. Returns the position of the return sequence.
+ Sets *patch_bytes to the number of bytes that need to be copied from that
+ location. If no patching is required (ie. the return is the last insn)
+ *patch_bytes will be set to -1. *plen is the number of code bytes to copy.
+ */
+static int trace_i386_op(const char * name, uint8_t *start_p, int *plen,
+ int *patch_bytes, int *exit_addrs)
+{
+ char *flags;
+ int more;
+ int insn;
+ int retpos;
+ int bytes;
+ int num_exits;
+ int len;
+ int last_insn;
+
+ len = *plen;
+ flags = malloc(len + 1);
+ memset(flags, 0, len + 1);
+ flags[0] |= FLAG_INSN;
+ more = 1;
+ while (more) {
+ more = 0;
+ for (insn = 0; insn < len; insn++) {
+ if ((flags[insn] & (FLAG_INSN | FLAG_SCANNED)) == FLAG_INSN) {
+ trace_i386_insn(name, start_p, flags, insn, len);
+ more = 1;
+ }
+ }
+ }
+
+ /* Strip any unused code at the end of the function. */
+ while (len > 0 && flags[len - 1] == 0)
+ len--;
+
+ retpos = -1;
+ num_exits = 0;
+ last_insn = 0;
+ for (insn = 0; insn < len; insn++) {
+ if (flags[insn] & FLAG_RET) {
+ /* ??? In theory it should be possible to handle multiple return
+ points. In practice it's not worth the effort. */
+ if (retpos != -1)
+ error("Multiple return instructions in %s", name);
+ retpos = insn;
+ }
+ if (flags[insn] & FLAG_EXIT) {
+ if (num_exits == MAX_EXITS)
+ error("Too many block exits in %s", name);
+ exit_addrs[num_exits] = insn;
+ num_exits++;
+ }
+ if (flags[insn] & FLAG_INSN)
+ last_insn = insn;
+ }
+
+ exit_addrs[num_exits] = -1;
+ if (retpos == -1) {
+ if (num_exits == 0) {
+ error ("No return instruction found in %s", name);
+ } else {
+ retpos = len;
+ last_insn = len;
+ }
+ }
+
+ /* If the return instruction is the last instruction we can just
+ remove it. */
+ if (retpos == last_insn)
+ *patch_bytes = -1;
+ else
+ *patch_bytes = 0;
+
+ /* Back up over any nop instructions. */
+ while (retpos > 0
+ && (flags[retpos] & FLAG_TARGET) == 0
+ && (flags[retpos - 1] & FLAG_INSN) != 0
+ && start_p[retpos - 1] == 0x90) {
+ retpos--;
+ }
+
+ if (*patch_bytes == -1) {
+ *plen = retpos;
+ free (flags);
+ return retpos;
+ }
+ *plen = len;
+
+ /* The ret is in the middle of the function. Find four more bytes that
+ so the ret can be replaced by a jmp. */
+ /* ??? Use a short jump where possible. */
+ bytes = 4;
+ insn = retpos + 1;
+ /* We can clobber everything up to the next jump target. */
+ while (insn < len && bytes > 0 && (flags[insn] & FLAG_TARGET) == 0) {
+ insn++;
+ bytes--;
+ }
+ if (bytes > 0) {
+ /* ???: Strip out nop blocks. */
+ /* We can't do the replacement without clobbering anything important.
+ Copy preceeding instructions(s) to give us some space. */
+ while (retpos > 0) {
+ /* If this byte is the target of a jmp we can't move it. */
+ if (flags[retpos] & FLAG_TARGET)
+ break;
+
+ (*patch_bytes)++;
+ bytes--;
+ retpos--;
+
+ /* Break out of the loop if we have enough space and this is either
+ the first byte of an instruction or a pad byte. */
+ if ((flags[retpos] & (FLAG_INSN | FLAG_SCANNED)) != FLAG_SCANNED
+ && bytes <= 0) {
+ break;
+ }
+ }
+ }
+
+ if (bytes > 0)
+ error("Unable to replace ret with jmp in %s\n", name);
+
+ free(flags);
+ return retpos;
+}
+
+#endif
+
#define MAX_ARGS 3
/* generate op code */
@@ -1356,6 +1996,11 @@ void gen_code(const char *name, host_ulo
uint8_t args_present[MAX_ARGS];
const char *sym_name, *p;
EXE_RELOC *rel;
+#if defined(HOST_I386) || defined(HOST_X86_64)
+ int patch_bytes;
+ int retpos;
+ int exit_addrs[MAX_EXITS];
+#endif
/* Compute exact size excluding prologue and epilogue instructions.
* Increment start_offset to skip epilogue instructions, then compute
@@ -1366,33 +2011,12 @@ void gen_code(const char *name, host_ulo
p_end = p_start + size;
start_offset = offset;
#if defined(HOST_I386) || defined(HOST_X86_64)
-#ifdef CONFIG_FORMAT_COFF
- {
- uint8_t *p;
- p = p_end - 1;
- if (p == p_start)
- error("empty code for %s", name);
- while (*p != 0xc3) {
- p--;
- if (p <= p_start)
- error("ret or jmp expected at the end of %s", name);
- }
- copy_size = p - p_start;
- }
-#else
{
int len;
len = p_end - p_start;
- if (len == 0)
- error("empty code for %s", name);
- if (p_end[-1] == 0xc3) {
- len--;
- } else {
- error("ret or jmp expected at the end of %s", name);
- }
+ retpos = trace_i386_op(name, p_start, &len, &patch_bytes, exit_addrs);
copy_size = len;
}
-#endif
#elif defined(HOST_PPC)
{
uint8_t *p;
@@ -1559,6 +2183,13 @@ void gen_code(const char *name, host_ulo
}
if (gen_switch == 2) {
+#if defined(HOST_I386) || defined(HOST_X86_64)
+ if (patch_bytes != -1)
+ copy_size += patch_bytes;
+#ifdef DEBUG_OP
+ copy_size += 2;
+#endif
+#endif
fprintf(outfile, "DEF(%s, %d, %d)\n", name + 3, nb_args, copy_size);
} else if (gen_switch == 1) {
@@ -1761,7 +2392,43 @@ void gen_code(const char *name, host_ulo
#error unsupport object format
#endif
}
+ }
+ /* Replace the marker instructions with the actual opcodes. */
+ for (i = 0; exit_addrs[i] != -1; i++) {
+ int op;
+ switch (p_start[exit_addrs[i]])
+ {
+ case 0xf4: op = 0xc3; break; /* hlt -> ret */
+ case 0xfa: op = 0xe9; break; /* cli -> jmp */
+ case 0xfb: op = 0xe9; break; /* sti -> jmp */
+ default: error("Internal error");
+ }
+ fprintf(outfile,
+ " *(uint8_t *)(gen_code_ptr + %d) = 0x%x;\n",
+ exit_addrs[i], op);
}
+ /* Fix up the return instruction. */
+ if (patch_bytes != -1) {
+ if (patch_bytes) {
+ fprintf(outfile, " memcpy(gen_code_ptr + %d,"
+ "gen_code_ptr + %d, %d);\n",
+ copy_size, retpos, patch_bytes);
+ }
+ fprintf(outfile,
+ " *(uint8_t *)(gen_code_ptr + %d) = 0xe9;\n",
+ retpos);
+ fprintf(outfile,
+ " *(uint32_t *)(gen_code_ptr + %d) = 0x%x;\n",
+ retpos + 1, copy_size - (retpos + 5));
+
+ copy_size += patch_bytes;
+ }
+#ifdef DEBUG_OP
+ fprintf(outfile,
+ " *(uint16_t *)(gen_code_ptr + %d) = 0x9090;\n",
+ copy_size);
+ copy_size += 2;
+#endif
}
#elif defined(HOST_X86_64)
{
@@ -1793,6 +2460,42 @@ void gen_code(const char *name, host_ulo
}
}
}
+ /* Replace the marker instructions with the actual opcodes. */
+ for (i = 0; exit_addrs[i] != -1; i++) {
+ int op;
+ switch (p_start[exit_addrs[i]])
+ {
+ case 0xf4: op = 0xc3; break; /* hlt -> ret */
+ case 0xfa: op = 0xe9; break; /* cli -> jmp */
+ case 0xfb: op = 0xe9; break; /* sti -> jmp */
+ default: error("Internal error");
+ }
+ fprintf(outfile,
+ " *(uint8_t *)(gen_code_ptr + %d) = 0x%x;\n",
+ exit_addrs[i], op);
+ }
+ /* Fix up the return instruction. */
+ if (patch_bytes != -1) {
+ if (patch_bytes) {
+ fprintf(outfile, " memcpy(gen_code_ptr + %d,"
+ "gen_code_ptr + %d, %d);\n",
+ copy_size, retpos, patch_bytes);
+ }
+ fprintf(outfile,
+ " *(uint8_t *)(gen_code_ptr + %d) = 0xe9;\n",
+ retpos);
+ fprintf(outfile,
+ " *(uint32_t *)(gen_code_ptr + %d) = 0x%x;\n",
+ retpos + 1, copy_size - (retpos + 5));
+
+ copy_size += patch_bytes;
+ }
+#ifdef DEBUG_OP
+ fprintf(outfile,
+ " *(uint16_t *)(gen_code_ptr + %d) = 0x9090;\n",
+ copy_size);
+ copy_size += 2;
+#endif
}
#elif defined(HOST_PPC)
{
--- qemu-0.7.0/exec-all.h.gcc4 2005-04-27 22:52:05.000000000 +0200
+++ qemu-0.7.0/exec-all.h 2005-06-02 21:41:51.000000000 +0200
@@ -335,14 +335,15 @@ do {\
#elif defined(__i386__) && defined(USE_DIRECT_JUMP)
-/* we patch the jump instruction directly */
+/* we patch the jump instruction directly. Use sti in place of the actual
+ jmp instruction so that dyngen can patch in the correct result. */
#define GOTO_TB(opname, tbparam, n)\
do {\
asm volatile (".section .data\n"\
ASM_OP_LABEL_NAME(n, opname) ":\n"\
".long 1f\n"\
ASM_PREVIOUS_SECTION \
- "jmp " ASM_NAME(__op_jmp) #n "\n"\
+ "sti;.long " ASM_NAME(__op_jmp) #n " - 1f\n"\
"1:\n");\
} while (0)

View File

@@ -0,0 +1,239 @@
https://bugzilla.redhat.com/show_bug.cgi?id=433560
Revised block device address range patch
The original patch adds checks to the main bdrv_XXX apis to validate that
the I/O operation does not exceed the bounds of the disk - ie beyond the
total_sectors count. This works correctly for bdrv_XXX calls from the IDE
driver. With disk formats like QCow though, bdrv_XXX is re-entrant,
because the QCow driver uses the block APIs for dealing with its underlying
file. The problem is that QCow files are grow-on-demand, so writes will
*explicitly* be beyond the end of the file. The original patch blocks any
I/O operation which would cause the QCow file to grow, resulting it more
or less catasatrophic data loss.
Basically the bounds checking needs to distinguish between checking for
the logical disk extents, vs the physical disk extents. For raw files
these are the same so initial tests showed no problems, but for QCow
format disks they are different & thus we see a problem
What follows is a revised patch which introduces a flag BDRV_O_AUTOGROW
which can be passed to bdrv_open to indicate that the files can be allowed
to automatically extend their extents. This flag should only be used by
internal block drivers such as block-qcow2.c, block-vmdk.c In my testing
this has fixed the qcow corruption, and still maintains the goal of Ian's
original patch which was to prevent the guest VM writing beyond the logical
disk extents.
diff -rup kvm-60.orig/qemu/block.c kvm-60.new/qemu/block.c
--- kvm-60.orig/qemu/block.c 2008-02-26 18:44:28.000000000 -0500
+++ kvm-60.new/qemu/block.c 2008-02-26 18:44:52.000000000 -0500
@@ -124,6 +124,60 @@ void path_combine(char *dest, int dest_s
}
}
+static int bdrv_rd_badreq_sectors(BlockDriverState *bs,
+ int64_t sector_num, int nb_sectors)
+{
+ return
+ nb_sectors < 0 ||
+ sector_num < 0 ||
+ nb_sectors > bs->total_sectors ||
+ sector_num > bs->total_sectors - nb_sectors;
+}
+
+static int bdrv_rd_badreq_bytes(BlockDriverState *bs,
+ int64_t offset, int count)
+{
+ int64_t size = bs->total_sectors << SECTOR_BITS;
+ return
+ count < 0 ||
+ size < 0 ||
+ count > size ||
+ offset > size - count;
+}
+
+static int bdrv_wr_badreq_sectors(BlockDriverState *bs,
+ int64_t sector_num, int nb_sectors)
+{
+ if (sector_num < 0 ||
+ nb_sectors < 0)
+ return 1;
+
+ if (sector_num > bs->total_sectors - nb_sectors) {
+ if (bs->autogrow)
+ bs->total_sectors = sector_num + nb_sectors;
+ else
+ return 1;
+ }
+ return 0;
+}
+
+static int bdrv_wr_badreq_bytes(BlockDriverState *bs,
+ int64_t offset, int count)
+{
+ int64_t size = bs->total_sectors << SECTOR_BITS;
+ if (count < 0 ||
+ offset < 0)
+ return 1;
+
+ if (offset > size - count) {
+ if (bs->autogrow)
+ bs->total_sectors = (offset + count + SECTOR_SIZE - 1) >> SECTOR_BITS;
+ else
+ return 1;
+ }
+ return 0;
+}
+
static void bdrv_register(BlockDriver *bdrv)
{
@@ -332,6 +386,10 @@ int bdrv_open2(BlockDriverState *bs, con
bs->read_only = 0;
bs->is_temporary = 0;
bs->encrypted = 0;
+ bs->autogrow = 0;
+
+ if (flags & BDRV_O_AUTOGROW)
+ bs->autogrow = 1;
if (flags & BDRV_O_SNAPSHOT) {
BlockDriverState *bs1;
@@ -376,6 +434,7 @@ int bdrv_open2(BlockDriverState *bs, con
}
bs->drv = drv;
bs->opaque = qemu_mallocz(drv->instance_size);
+ bs->total_sectors = 0; /* driver will set if it does not do getlength */
if (bs->opaque == NULL && drv->instance_size > 0)
return -1;
/* Note: for compatibility, we open disk image files as RDWR, and
@@ -441,6 +500,7 @@ void bdrv_close(BlockDriverState *bs)
bs->drv = NULL;
/* call the change callback */
+ bs->total_sectors = 0;
bs->media_changed = 1;
if (bs->change_cb)
bs->change_cb(bs->change_opaque);
@@ -506,6 +566,8 @@ int bdrv_read(BlockDriverState *bs, int6
if (!drv)
return -ENOMEDIUM;
+ if (bdrv_rd_badreq_sectors(bs, sector_num, nb_sectors))
+ return -EDOM;
if (sector_num == 0 && bs->boot_sector_enabled && nb_sectors > 0) {
memcpy(buf, bs->boot_sector_data, 512);
sector_num++;
@@ -546,6 +608,8 @@ int bdrv_write(BlockDriverState *bs, int
return -ENOMEDIUM;
if (bs->read_only)
return -EACCES;
+ if (bdrv_wr_badreq_sectors(bs, sector_num, nb_sectors))
+ return -EDOM;
if (sector_num == 0 && bs->boot_sector_enabled && nb_sectors > 0) {
memcpy(bs->boot_sector_data, buf, 512);
}
@@ -671,6 +735,8 @@ int bdrv_pread(BlockDriverState *bs, int
return -ENOMEDIUM;
if (!drv->bdrv_pread)
return bdrv_pread_em(bs, offset, buf1, count1);
+ if (bdrv_rd_badreq_bytes(bs, offset, count1))
+ return -EDOM;
return drv->bdrv_pread(bs, offset, buf1, count1);
}
@@ -686,6 +752,8 @@ int bdrv_pwrite(BlockDriverState *bs, in
return -ENOMEDIUM;
if (!drv->bdrv_pwrite)
return bdrv_pwrite_em(bs, offset, buf1, count1);
+ if (bdrv_wr_badreq_bytes(bs, offset, count1))
+ return -EDOM;
return drv->bdrv_pwrite(bs, offset, buf1, count1);
}
@@ -1091,6 +1159,8 @@ int bdrv_write_compressed(BlockDriverSta
return -ENOMEDIUM;
if (!drv->bdrv_write_compressed)
return -ENOTSUP;
+ if (bdrv_wr_badreq_sectors(bs, sector_num, nb_sectors))
+ return -EDOM;
return drv->bdrv_write_compressed(bs, sector_num, buf, nb_sectors);
}
@@ -1237,6 +1307,8 @@ BlockDriverAIOCB *bdrv_aio_read(BlockDri
if (!drv)
return NULL;
+ if (bdrv_rd_badreq_sectors(bs, sector_num, nb_sectors))
+ return NULL;
/* XXX: we assume that nb_sectors == 0 is suppored by the async read */
if (sector_num == 0 && bs->boot_sector_enabled && nb_sectors > 0) {
@@ -1268,6 +1340,8 @@ BlockDriverAIOCB *bdrv_aio_write(BlockDr
return NULL;
if (bs->read_only)
return NULL;
+ if (bdrv_wr_badreq_sectors(bs, sector_num, nb_sectors))
+ return NULL;
if (sector_num == 0 && bs->boot_sector_enabled && nb_sectors > 0) {
memcpy(bs->boot_sector_data, buf, 512);
}
diff -rup kvm-60.orig/qemu/block.h kvm-60.new/qemu/block.h
--- kvm-60.orig/qemu/block.h 2008-01-20 07:35:04.000000000 -0500
+++ kvm-60.new/qemu/block.h 2008-02-26 18:44:52.000000000 -0500
@@ -45,6 +45,7 @@ typedef struct QEMUSnapshotInfo {
it (default for
bdrv_file_open()) */
#define BDRV_O_DIRECT 0x0020
+#define BDRV_O_AUTOGROW 0x0040 /* Allow backing file to extend when writing past end of file */
#ifndef QEMU_IMG
void bdrv_info(void);
diff -rup kvm-60.orig/qemu/block_int.h kvm-60.new/qemu/block_int.h
--- kvm-60.orig/qemu/block_int.h 2008-01-20 07:35:04.000000000 -0500
+++ kvm-60.new/qemu/block_int.h 2008-02-26 18:44:52.000000000 -0500
@@ -97,6 +97,7 @@ struct BlockDriverState {
int locked; /* if true, the media cannot temporarily be ejected */
int encrypted; /* if true, the media is encrypted */
int sg; /* if true, the device is a /dev/sg* */
+ int autogrow; /* if true, the backing store can auto-extend to allocate new extents */
/* event callback when inserting/removing */
void (*change_cb)(void *opaque);
void *change_opaque;
diff -rup kvm-60.orig/qemu/block-qcow2.c kvm-60.new/qemu/block-qcow2.c
--- kvm-60.orig/qemu/block-qcow2.c 2008-01-20 07:35:04.000000000 -0500
+++ kvm-60.new/qemu/block-qcow2.c 2008-02-26 18:44:52.000000000 -0500
@@ -191,7 +191,7 @@ static int qcow_open(BlockDriverState *b
int len, i, shift, ret;
QCowHeader header;
- ret = bdrv_file_open(&s->hd, filename, flags);
+ ret = bdrv_file_open(&s->hd, filename, flags | BDRV_O_AUTOGROW);
if (ret < 0)
return ret;
if (bdrv_pread(s->hd, 0, &header, sizeof(header)) != sizeof(header))
diff -rup kvm-60.orig/qemu/block-qcow.c kvm-60.new/qemu/block-qcow.c
--- kvm-60.orig/qemu/block-qcow.c 2008-01-20 07:35:04.000000000 -0500
+++ kvm-60.new/qemu/block-qcow.c 2008-02-26 18:44:52.000000000 -0500
@@ -95,7 +95,7 @@ static int qcow_open(BlockDriverState *b
int len, i, shift, ret;
QCowHeader header;
- ret = bdrv_file_open(&s->hd, filename, flags);
+ ret = bdrv_file_open(&s->hd, filename, flags | BDRV_O_AUTOGROW);
if (ret < 0)
return ret;
if (bdrv_pread(s->hd, 0, &header, sizeof(header)) != sizeof(header))
diff -rup kvm-60.orig/qemu/block-vmdk.c kvm-60.new/qemu/block-vmdk.c
--- kvm-60.orig/qemu/block-vmdk.c 2008-01-20 07:35:04.000000000 -0500
+++ kvm-60.new/qemu/block-vmdk.c 2008-02-26 18:44:52.000000000 -0500
@@ -375,7 +375,7 @@ static int vmdk_open(BlockDriverState *b
flags = BDRV_O_RDONLY;
fprintf(stderr, "(VMDK) image open: flags=0x%x filename=%s\n", flags, bs->filename);
- ret = bdrv_file_open(&s->hd, filename, flags);
+ ret = bdrv_file_open(&s->hd, filename, flags | BDRV_O_AUTOGROW);
if (ret < 0)
return ret;
if (bdrv_pread(s->hd, 0, &magic, sizeof(magic)) != sizeof(magic))

View File

@@ -0,0 +1,55 @@
--- vl.c 2008-01-06 14:38:42.000000000 -0500
+++ vl.c 2008-05-13 09:56:45.000000000 -0400
@@ -4877,13 +4877,14 @@
int bus_id, unit_id;
int cyls, heads, secs, translation;
BlockDriverState *bdrv;
+ BlockDriver *drv = NULL;
int max_devs;
int index;
int cache;
int bdrv_flags;
char *params[] = { "bus", "unit", "if", "index", "cyls", "heads",
"secs", "trans", "media", "snapshot", "file",
- "cache", NULL };
+ "cache", "format", NULL };
if (check_params(buf, sizeof(buf), params, str) < 0) {
fprintf(stderr, "qemu: unknowm parameter '%s' in '%s'\n",
@@ -5051,6 +5052,14 @@
}
}
+ if (get_param_value(buf, sizeof(buf), "format", str)) {
+ drv = bdrv_find_format(buf);
+ if (!drv) {
+ fprintf(stderr, "qemu: '%s' invalid format\n", buf);
+ return -1;
+ }
+ }
+
get_param_value(file, sizeof(file), "file", str);
/* compute bus and unit according index */
@@ -5150,7 +5159,7 @@
bdrv_flags |= BDRV_O_SNAPSHOT;
if (!cache)
bdrv_flags |= BDRV_O_DIRECT;
- if (bdrv_open(bdrv, file, bdrv_flags) < 0 || qemu_key_check(bdrv, file)) {
+ if (bdrv_open2(bdrv, file, bdrv_flags, drv) < 0 || qemu_key_check(bdrv, file)) {
fprintf(stderr, "qemu: could not open disk image %s\n",
file);
return -1;
--- qemu-doc.texi 2008-01-06 14:38:42.000000000 -0500
+++ qemu-doc.texi 2008-05-13 09:57:57.000000000 -0400
@@ -252,6 +252,10 @@
@var{snapshot} is "on" or "off" and allows to enable snapshot for given drive (see @option{-snapshot}).
@item cache=@var{cache}
@var{cache} is "on" or "off" and allows to disable host cache to access data.
+@item format=@var{format}
+Specify which disk @var{format} will be used rather than detecting
+the format. Can be used to specifiy format=raw to avoid interpreting
+an untrusted format header.
@end table
Instead of @option{-cdrom} you can use:

View File

@@ -0,0 +1,212 @@
diff -rup kvm-60.orig/qemu/block.c kvm-60.new/qemu/block.c
--- kvm-60.orig/qemu/block.c 2008-02-26 18:44:28.000000000 -0500
+++ kvm-60.new/qemu/block.c 2008-02-26 18:44:52.000000000 -0500
@@ -124,6 +124,60 @@ void path_combine(char *dest, int dest_s
}
}
+static int bdrv_rd_badreq_sectors(BlockDriverState *bs,
+ int64_t sector_num, int nb_sectors)
+{
+ return
+ nb_sectors < 0 ||
+ sector_num < 0 ||
+ nb_sectors > bs->total_sectors ||
+ sector_num > bs->total_sectors - nb_sectors;
+}
+
+static int bdrv_rd_badreq_bytes(BlockDriverState *bs,
+ int64_t offset, int count)
+{
+ int64_t size = bs->total_sectors << SECTOR_BITS;
+ return
+ count < 0 ||
+ size < 0 ||
+ count > size ||
+ offset > size - count;
+}
+
+static int bdrv_wr_badreq_sectors(BlockDriverState *bs,
+ int64_t sector_num, int nb_sectors)
+{
+ if (sector_num < 0 ||
+ nb_sectors < 0)
+ return 1;
+
+ if (sector_num > bs->total_sectors - nb_sectors) {
+ if (bs->autogrow)
+ bs->total_sectors = sector_num + nb_sectors;
+ else
+ return 1;
+ }
+ return 0;
+}
+
+static int bdrv_wr_badreq_bytes(BlockDriverState *bs,
+ int64_t offset, int count)
+{
+ int64_t size = bs->total_sectors << SECTOR_BITS;
+ if (count < 0 ||
+ offset < 0)
+ return 1;
+
+ if (offset > size - count) {
+ if (bs->autogrow)
+ bs->total_sectors = (offset + count + SECTOR_SIZE - 1) >> SECTOR_BITS;
+ else
+ return 1;
+ }
+ return 0;
+}
+
static void bdrv_register(BlockDriver *bdrv)
{
@@ -332,6 +386,10 @@ int bdrv_open2(BlockDriverState *bs, con
bs->read_only = 0;
bs->is_temporary = 0;
bs->encrypted = 0;
+ bs->autogrow = 0;
+
+ if (flags & BDRV_O_AUTOGROW)
+ bs->autogrow = 1;
if (flags & BDRV_O_SNAPSHOT) {
BlockDriverState *bs1;
@@ -376,6 +434,7 @@ int bdrv_open2(BlockDriverState *bs, con
}
bs->drv = drv;
bs->opaque = qemu_mallocz(drv->instance_size);
+ bs->total_sectors = 0; /* driver will set if it does not do getlength */
if (bs->opaque == NULL && drv->instance_size > 0)
return -1;
/* Note: for compatibility, we open disk image files as RDWR, and
@@ -441,6 +500,7 @@ void bdrv_close(BlockDriverState *bs)
bs->drv = NULL;
/* call the change callback */
+ bs->total_sectors = 0;
bs->media_changed = 1;
if (bs->change_cb)
bs->change_cb(bs->change_opaque);
@@ -506,6 +566,8 @@ int bdrv_read(BlockDriverState *bs, int6
if (!drv)
return -ENOMEDIUM;
+ if (bdrv_rd_badreq_sectors(bs, sector_num, nb_sectors))
+ return -EDOM;
if (sector_num == 0 && bs->boot_sector_enabled && nb_sectors > 0) {
memcpy(buf, bs->boot_sector_data, 512);
sector_num++;
@@ -546,6 +608,8 @@ int bdrv_write(BlockDriverState *bs, int
return -ENOMEDIUM;
if (bs->read_only)
return -EACCES;
+ if (bdrv_wr_badreq_sectors(bs, sector_num, nb_sectors))
+ return -EDOM;
if (sector_num == 0 && bs->boot_sector_enabled && nb_sectors > 0) {
memcpy(bs->boot_sector_data, buf, 512);
}
@@ -671,6 +735,8 @@ int bdrv_pread(BlockDriverState *bs, int
return -ENOMEDIUM;
if (!drv->bdrv_pread)
return bdrv_pread_em(bs, offset, buf1, count1);
+ if (bdrv_rd_badreq_bytes(bs, offset, count1))
+ return -EDOM;
return drv->bdrv_pread(bs, offset, buf1, count1);
}
@@ -686,6 +752,8 @@ int bdrv_pwrite(BlockDriverState *bs, in
return -ENOMEDIUM;
if (!drv->bdrv_pwrite)
return bdrv_pwrite_em(bs, offset, buf1, count1);
+ if (bdrv_wr_badreq_bytes(bs, offset, count1))
+ return -EDOM;
return drv->bdrv_pwrite(bs, offset, buf1, count1);
}
@@ -1091,6 +1159,8 @@ int bdrv_write_compressed(BlockDriverSta
return -ENOMEDIUM;
if (!drv->bdrv_write_compressed)
return -ENOTSUP;
+ if (bdrv_wr_badreq_sectors(bs, sector_num, nb_sectors))
+ return -EDOM;
return drv->bdrv_write_compressed(bs, sector_num, buf, nb_sectors);
}
@@ -1237,6 +1307,8 @@ BlockDriverAIOCB *bdrv_aio_read(BlockDri
if (!drv)
return NULL;
+ if (bdrv_rd_badreq_sectors(bs, sector_num, nb_sectors))
+ return NULL;
/* XXX: we assume that nb_sectors == 0 is suppored by the async read */
if (sector_num == 0 && bs->boot_sector_enabled && nb_sectors > 0) {
@@ -1268,6 +1340,8 @@ BlockDriverAIOCB *bdrv_aio_write(BlockDr
return NULL;
if (bs->read_only)
return NULL;
+ if (bdrv_wr_badreq_sectors(bs, sector_num, nb_sectors))
+ return NULL;
if (sector_num == 0 && bs->boot_sector_enabled && nb_sectors > 0) {
memcpy(bs->boot_sector_data, buf, 512);
}
diff -rup kvm-60.orig/qemu/block.h kvm-60.new/qemu/block.h
--- kvm-60.orig/qemu/block.h 2008-01-20 07:35:04.000000000 -0500
+++ kvm-60.new/qemu/block.h 2008-02-26 18:44:52.000000000 -0500
@@ -45,6 +45,7 @@ typedef struct QEMUSnapshotInfo {
it (default for
bdrv_file_open()) */
#define BDRV_O_DIRECT 0x0020
+#define BDRV_O_AUTOGROW 0x0040 /* Allow backing file to extend when writing past end of file */
#ifndef QEMU_IMG
void bdrv_info(void);
diff -rup kvm-60.orig/qemu/block_int.h kvm-60.new/qemu/block_int.h
--- kvm-60.orig/qemu/block_int.h 2008-01-20 07:35:04.000000000 -0500
+++ kvm-60.new/qemu/block_int.h 2008-02-26 18:44:52.000000000 -0500
@@ -97,6 +97,7 @@ struct BlockDriverState {
int locked; /* if true, the media cannot temporarily be ejected */
int encrypted; /* if true, the media is encrypted */
int sg; /* if true, the device is a /dev/sg* */
+ int autogrow; /* if true, the backing store can auto-extend to allocate new extents */
/* event callback when inserting/removing */
void (*change_cb)(void *opaque);
void *change_opaque;
diff -rup kvm-60.orig/qemu/block-qcow2.c kvm-60.new/qemu/block-qcow2.c
--- kvm-60.orig/qemu/block-qcow2.c 2008-01-20 07:35:04.000000000 -0500
+++ kvm-60.new/qemu/block-qcow2.c 2008-02-26 18:44:52.000000000 -0500
@@ -191,7 +191,7 @@ static int qcow_open(BlockDriverState *b
int len, i, shift, ret;
QCowHeader header;
- ret = bdrv_file_open(&s->hd, filename, flags);
+ ret = bdrv_file_open(&s->hd, filename, flags | BDRV_O_AUTOGROW);
if (ret < 0)
return ret;
if (bdrv_pread(s->hd, 0, &header, sizeof(header)) != sizeof(header))
diff -rup kvm-60.orig/qemu/block-qcow.c kvm-60.new/qemu/block-qcow.c
--- kvm-60.orig/qemu/block-qcow.c 2008-01-20 07:35:04.000000000 -0500
+++ kvm-60.new/qemu/block-qcow.c 2008-02-26 18:44:52.000000000 -0500
@@ -95,7 +95,7 @@ static int qcow_open(BlockDriverState *b
int len, i, shift, ret;
QCowHeader header;
- ret = bdrv_file_open(&s->hd, filename, flags);
+ ret = bdrv_file_open(&s->hd, filename, flags | BDRV_O_AUTOGROW);
if (ret < 0)
return ret;
if (bdrv_pread(s->hd, 0, &header, sizeof(header)) != sizeof(header))
diff -rup kvm-60.orig/qemu/block-vmdk.c kvm-60.new/qemu/block-vmdk.c
--- kvm-60.orig/qemu/block-vmdk.c 2008-01-20 07:35:04.000000000 -0500
+++ kvm-60.new/qemu/block-vmdk.c 2008-02-26 18:44:52.000000000 -0500
@@ -375,7 +375,7 @@ static int vmdk_open(BlockDriverState *b
flags = BDRV_O_RDONLY;
fprintf(stderr, "(VMDK) image open: flags=0x%x filename=%s\n", flags, bs->filename);
- ret = bdrv_file_open(&s->hd, filename, flags);
+ ret = bdrv_file_open(&s->hd, filename, flags | BDRV_O_AUTOGROW);
if (ret < 0)
return ret;
if (bdrv_pread(s->hd, 0, &magic, sizeof(magic)) != sizeof(magic))

View File

@@ -0,0 +1,12 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE pkgmetadata SYSTEM "http://www.gentoo.org/dtd/metadata.dtd">
<pkgmetadata>
<herd>no-herd</herd>
<maintainer>
<email>lu_zero@gentoo.org</email>
</maintainer>
<use>
<flag name='kqemu'>Enables the kernel acceleration module on a x86
cpu</flag>
</use>
</pkgmetadata>

View File

@@ -0,0 +1,128 @@
# Copyright 1999-2008 Gentoo Foundation
# Distributed under the terms of the GNU General Public License v2
# $Header: /var/cvsroot/gentoo-x86/app-emulation/qemu-softmmu/qemu-softmmu-0.9.1-r3.ebuild,v 1.4 2008/05/14 20:25:37 maekke Exp $
inherit eutils flag-o-matic toolchain-funcs
DESCRIPTION="Multi-platform & multi-targets cpu emulator and dynamic translator"
HOMEPAGE="http://fabrice.bellard.free.fr/qemu/"
SRC_URI="${HOMEPAGE}${P/-softmmu/}.tar.gz"
LICENSE="GPL-2 LGPL-2.1"
SLOT="0"
KEYWORDS="-alpha amd64 ppc -sparc x86"
IUSE="sdl kqemu gnutls alsa"
RESTRICT="binchecks test"
DEPEND="virtual/libc
sys-libs/zlib
sdl? ( media-libs/libsdl )
!<=app-emulation/qemu-0.7.0
kqemu? ( >=app-emulation/kqemu-1.3.0_pre10 )
gnutls? (
dev-util/pkgconfig
net-libs/gnutls
)
app-text/texi2html"
RDEPEND="sys-libs/zlib
sdl? ( media-libs/libsdl )
gnutls? ( net-libs/gnutls )
alsa? ( media-libs/alsa-lib )"
S=${WORKDIR}/${P/-softmmu/}
src_unpack() {
unpack ${A}
cd "${S}"
epatch "${FILESDIR}/${P}-CVE-2008-0928.patch" #212351
epatch "${FILESDIR}/${P}-CVE-2008-2004.patch" #221943
epatch "${FILESDIR}/hotfix.patch"
epatch "${FILESDIR}/qemu-0.9.0-i386-FORCE_RET.patch"
epatch "${FILESDIR}/qemu-0.9.1-enforce-16byte-stack-boundary.patch"
epatch "${FILESDIR}/qemu-softmmu-0.9.1-block-device-address-range.patch"
epatch "${FILESDIR}/qemu-0.9.1-gcc4-hacks.patch"
epatch "${FILESDIR}/qemu-0.9.1-always_inline.patch"
epatch "${FILESDIR}/qemu-0.9.1-gcc4-opts.patch"
epatch "${FILESDIR}/qemu-0.9.1-gcc4.patch"
# Alter target makefiles to accept CFLAGS set via flag-o.
sed -i 's/^\(C\|OP_C\|HELPER_C\)FLAGS=/\1FLAGS+=/' \
Makefile Makefile.target tests/Makefile
# Ensure mprotect restrictions are relaxed for emulator binaries
[[ -x /sbin/paxctl ]] && \
sed -i 's/^VL_LDFLAGS=$/VL_LDFLAGS=-Wl,-z,execheap/' \
Makefile.target
# Prevent install of kernel module by qemu's makefile
sed -i 's/\(.\/install.sh\)/#\1/' Makefile
# avoid strip
sed -i 's:$(INSTALL) -m 755 -s:$(INSTALL) -m 755:' Makefile Makefile.target
}
src_compile() {
if use x86 ; then
# Force -march=pentium-mmx or lower. Fixes bug #212351.
local march
march=$(echo "${CFLAGS}" | sed 's:^.*-march=\([[:alnum:]-]\+\)\([[:blank:]].*\)\?$:\1:p;d')
case ${march} in
i386|i486|i586|pentium) ;;
*) # Either march is not enough low or not exists at all
case ${CHOST} in
i486-*-*) march=i486 ;;
i586-*-*) march=i586 ;;
*) march=pentium-mmx ;;
esac ;;
esac
#Let the application set its cflags
unset CFLAGS
append-flags -march=${march}
else
#Let the application set its cflags
unset CFLAGS
fi
# Switch off hardened tech
filter-flags -fpie -fstack-protector
myconf="--disable-gcc-check"
if use alsa; then
myconf="$myconf --enable-alsa"
fi
if ! use gnutls; then
myconf="$myconf --disable-vnc-tls"
fi
if ! use kqemu; then
myconf="$myconf --disable-kqemu"
fi
if ! use sdl ; then
myconf="$myconf --disable-sdl --disable-gfx-check"
fi
# econf does not work
./configure \
--prefix=/usr \
--enable-adlib \
--cc=$(tc-getCC) \
--host-cc=$(tc-getCC) \
--disable-linux-user \
--enable-system \
${myconf} \
|| die "could not configure"
emake OS_CFLAGS="${CFLAGS}" || die "make failed"
}
src_install() {
emake install \
prefix="${D}/usr" \
bindir="${D}/usr/bin" \
datadir="${D}/usr/share/qemu" \
docdir="${D}/usr/share/doc/${P}" \
mandir="${D}/usr/share/man" || die
chmod -x "${D}/usr/share/man/*/*"
}
pkg_postinst() {
einfo "You will need the Universal TUN/TAP driver compiled into"
einfo "kernel or as a module to use the virtual network device."
}