Re: [Qemu-devel] [PATCH v3 5/6] vga: Use linear mapping + dirty logging in chain 4 memory access mode
On 12.09.2011, at 22:21, Blue Swirl wrote: > On Mon, Sep 12, 2011 at 3:20 PM, Alexander Graf wrote: >> Jan Kiszka wrote: >>> Most VGA memory access modes require MMIO handling as they demand weird >>> logic to get a byte from or into the video RAM. However, there is one >>> exception: chain 4 mode with all memory planes enabled for writing. This >>> mode actually allows lineary mapping, which can then be combined with >>> dirty logging to accelerate KVM. >>> >>> This patch accelerates specifically VBE accesses like they are used by >>> grub in graphical mode. Not only the standard VGA adapter benefits from >>> this, also vmware and spice in VGA mode. >>> >>> CC: Gerd Hoffmann >>> CC: Avi Kivity >>> Signed-off-by: Jan Kiszka >>> >> >> [...] >> >>> +static void vga_update_memory_access(VGACommonState *s) >>> +{ >>> +MemoryRegion *region, *old_region = s->chain4_alias; >>> +target_phys_addr_t base, offset, size; >>> + >>> +s->chain4_alias = NULL; >>> + >>> +if ((s->sr[0x02] & 0xf) == 0xf && s->sr[0x04] & 0x08) { >>> +offset = 0; >>> +switch ((s->gr[6] >> 2) & 3) { >>> +case 0: >>> +base = 0xa; >>> +size = 0x2; >>> +break; >>> +case 1: >>> +base = 0xa; >>> +size = 0x1; >>> +offset = s->bank_offset; >>> +break; >>> +case 2: >>> +base = 0xb; >>> +size = 0x8000; >>> +break; >>> +case 3: >>> +base = 0xb8000; >>> +size = 0x8000; >>> +break; >>> +} >>> +region = g_malloc(sizeof(*region)); >>> +memory_region_init_alias(region, "vga.chain4", &s->vram, offset, >>> size); >>> +memory_region_add_subregion_overlap(s->legacy_address_space, base, >>> +region, 2); >>> >> >> This one eventually gives me the following in info mtree with -M g3beige >> on qemu-system-ppc: >> >> (qemu) info mtree > > :-) > >> memory >> system addr off size 7fff >> -vga.chain4 addr 000a off size 1 >> -macio addr 8088 off size 8 >> --macio-nvram addr 0006 off size 2 >> --pmac-ide addr 0002 off size 1000 >> --cuda addr 00016000 off size 2000 >> --escc-bar addr 00013000 off size 40 >> --dbdma addr 8000 off size 1000 >> --heathrow-pic addr off size 1000 >> -vga.rom addr 8080 off size 1 >> -vga.vram addr 8000 off size 80 >> -vga-lowmem addr 800a off size 2 >> -escc addr 80013000 off size 40 >> -isa-mmio addr fe00 off size 20 >> I/O >> io addr off size 1 >> -cmd646-bmdma addr 0700 off size 10 >> --cmd646-bmdma-ioport addr 000c off size 4 >> --cmd646-bmdma-bus addr 0008 off size 4 >> --cmd646-bmdma-ioport addr 0004 off size 4 >> --cmd646-bmdma-bus addr off size 4 >> -cmd646-cmd addr 0680 off size 4 >> -cmd646-data addr 0600 off size 8 >> -cmd646-cmd addr 0580 off size 4 >> -cmd646-data addr 0500 off size 8 >> -ne2000 addr 0400 off size 100 >> >> This ends up overmapping 0xa, effectively overwriting kernel data. >> If I #if 0 the offending chunk out, everything is fine. I would assume >> that chain4 really needs to be inside of lowmem? No idea about VGA, but >> I'm sure you know what's going on :). > > I had similar problems with sun4u, fixed with > f69539b14bdba7a5cd22e1f4bed439b476b17286. I think also here, PCI > should be given a memory range at 0x8000 and VGA should > automatically use that like. Yeah, usually the ISA bus is behind an ISA-PCI bridge, so it should inherit the offset from its parent. Or do you mean something different? Alex
Re: [Qemu-devel] About hotplug multifunction
On Tue, Sep 13, 2011 at 02:57:20PM +0900, Isaku Yamahata wrote: > On Sun, Sep 11, 2011 at 12:05:17PM +0300, Michael S. Tsirkin wrote: > > On Sat, Sep 10, 2011 at 02:43:11AM +0900, Isaku Yamahata wrote: > > > pci/pcie hot plug needs clean up for multifunction hotplug in long term. > > > Only single function device case works. Multifunction case is broken > > > somwehat. > > > Especially the current acpi based hotplug should be replaced by > > > the standardized hot plug controller in long term. > > > > We'll need to keep supporting windows XP, which IIUC only > > supports hotplug through ACPI. So it looks like we'll > > need both. > > Yes, we'll need both then. > It would be possible to implement acpi-based hotplug with > standardized hotplug controller. Not with qemu-specific controller. > Where is this "standardized hotplug controller" documented? > It would require a bit amount of work to write ACPI code in DSDT that > handles standardized hotplug controller. > So I'm not sure it's worth while only for windows XP support. > -- > yamahata -- Gleb.
Re: [Qemu-devel] Question on kvm_clock working ...
Hello Al, I just debugged a kvmclock bug, so I claim to have some knowledge in this area now, but please take my answer with a grain of doubt. On Monday 12 September 2011 15:21:25 al pat wrote: > Still seeking your guidance on this. Appreciate any pointers you may have. You have to distiguish between the real-time-clock (RTC), which in hardware is a battery powered clock running even when your PC is powered off. Since it's slow to access, most Linux distributions read out its value once during boot using "hwclock --hctosys --utc" and than don't care about that clock any more until shutdown, when they write back the system time to the RTC using "... --systohc ...". During runtime, other methods are used for time keeping: Either by counting regular interrupts, using the ACPI-PM clock, or the High Performance Event Timer (HPET), or the Time Stamp Counter (TSC) register, or ...; see /sys/devices/system/clocksource/clocksource0/available_clocksource for a list of available clock sources. For virtual machines there is an additional clock source named "kvmclock", which uses the host clock and the TSC: The host exports its current system time (plus some configurable offset) and a snapshot value of TSC register when doing so. Than the guest can interpolate the current time by using the exported_system_time + scale * (current_TSC_value-snapshot_TSC_value). This kvmclock doesn't have anything to do with the RTC clock as far as I know. Now to your problem: You should check the value of /sys/devices/system/clocksource/clocksource0/current_clocksource in your guest. If it is somethong other than kvmclock, you should if using "hwclock --hctosys --utc" re-synchronizes your guest clock to the host. Sincerely Philipp -- Philipp Hahn Open Source Software Engineer h...@univention.de Univention GmbHLinux for Your Businessfon: +49 421 22 232- 0 Mary-Somerville-Str.1 D-28359 Bremen fax: +49 421 22 232-99 http://www.univention.de/ Treffen Sie Univention auf der IT&Business vom 20. bis 22. September 2011 auf dem Gemeinschaftsstand der Open Source Business Alliance in Stuttgart in Halle 3 Stand 3D27-7. signature.asc Description: This is a digitally signed message part.
Re: [Qemu-devel] [PATCH V12 00/15] virtio-9p: chroot environment for passthrough security model
> I agree, regardless of libvirt's needs, p9fs needs to be secure for any > non-root user using QEMU. As non-root I should be able todo > > $ qemu -virtfs $HOME/shared > > and have strong confidence that symlink attacks can't be used by the > guest to access other locations nuder $HOME. > > > A virtfs feature that needs root therefore needs to be in a separate > > process. Either QEMU needs to fork or virtfs could use a separate > > daemon binary. > > One other idea I just had is 'fakechroot'. This is basically an LD_PRELOAD > hack which wraps the C library's native chroot(), open() etc call to do > chroot in userspace, thus avoiding a need for root privileges. > > Either you could just invoke QEMU via fakechroot, enabling your code from > these patches to be used as non-root. Or we could take the code from the > fakechroot library and use that directly in the p9fs code to apply the > path security checks > With fakechroot is that I can still do following: chroot("/etc/cups"); fd = open("../passwd", O_RDONLY); It does not check access beyond the chroot path. Also in virtio-9p case, a modified guest kernel can send a symbolic link and that could resolve outside chroot path. passthrough security model in virtio-9p needs root privilege not only for chroot() syscall but also to do chown and chmod on files created by the guest. So IMHO fakechroot can't be used in this case.
Re: [Qemu-devel] unable to access the serial port on the Vm
Hi, Thanks a lot , it resolved my problem .. I could get the data inside VM . regards Bala On Tue, Sep 13, 2011 at 10:53 AM, Stefan Hajnoczi wrote: > On Tue, Sep 13, 2011 at 5:59 AM, bala suru wrote: > > Yes, I'm connecting a USB to serial device to the host (ubuntu 11.04) and > I > > want that serial port on my VM . > > I tried the solution you have suggested but still same problem , can not > > see the virtual serial port (ttyACM0) on VM but I could see on the HOST . > > > > The following is the line I have tried . > > RAW = [ type = "kvm", > > data = " > path=\"/dev/ttyACM0\"/> > tty=\"/dev/pts/5\"> > port=\"0\"/>" ] > > Inside the guest you will see a regular serial port (/dev/ttyS0). The > guest does not know that you're using /dev/ttyACM0 on the host, but > that should not matter. > > Stefan >
Re: [Qemu-devel] About hotplug multifunction
On Sun, Sep 11, 2011 at 12:05:17PM +0300, Michael S. Tsirkin wrote: > On Sat, Sep 10, 2011 at 02:43:11AM +0900, Isaku Yamahata wrote: > > pci/pcie hot plug needs clean up for multifunction hotplug in long term. > > Only single function device case works. Multifunction case is broken > > somwehat. > > Especially the current acpi based hotplug should be replaced by > > the standardized hot plug controller in long term. > > We'll need to keep supporting windows XP, which IIUC only > supports hotplug through ACPI. So it looks like we'll > need both. Yes, we'll need both then. It would be possible to implement acpi-based hotplug with standardized hotplug controller. Not with qemu-specific controller. It would require a bit amount of work to write ACPI code in DSDT that handles standardized hotplug controller. So I'm not sure it's worth while only for windows XP support. -- yamahata
Re: [Qemu-devel] unable to access the serial port on the Vm
On Tue, Sep 13, 2011 at 5:59 AM, bala suru wrote: > Yes, I'm connecting a USB to serial device to the host (ubuntu 11.04) and I > want that serial port on my VM . > I tried the solution you have suggested but still same problem , can not > see the virtual serial port (ttyACM0) on VM but I could see on the HOST . > > The following is the line I have tried . > RAW = [ type = "kvm", > data = " path=\"/dev/ttyACM0\"/> tty=\"/dev/pts/5\"> port=\"0\"/>" ] Inside the guest you will see a regular serial port (/dev/ttyS0). The guest does not know that you're using /dev/ttyACM0 on the host, but that should not matter. Stefan
Re: [Qemu-devel] unable to access the serial port on the Vm
Yes, I'm connecting a USB to serial device to the host (ubuntu 11.04) and I want that serial port on my VM . I tried the solution you have suggested but still same problem , can not see the virtual serial port (ttyACM0) on VM but I could see on the HOST . The following is the line I have tried . RAW = [ type = "kvm", data = "" ] On Mon, Sep 12, 2011 at 11:51 PM, Stefan Hajnoczi wrote: > On Mon, Sep 12, 2011 at 12:35 PM, bala suru wrote: > > But I need to connect a some USB device which will create a virtual > > serialport called /dev/ttyACM0, I cloud not see this on the Vm running .. > > > > This XML format I used > > RAW = [ type = "kvm", > > data = " > path=\"/dev/pts/5\"/> > tty=\"/dev/pts/5\"> > port=\"0\"/>" ] > > I am not sure what you are trying to do. > > Are you attaching a USB serial device to the host and you would like > to connect that to the VM's serial port? In that case you can try > this domain XML: > > > > > > > Stefan >
[Qemu-devel] [Bug 848571] [NEW] qemu does not generate a qemu-kvm.stp tapset file
Public bug reported: To make the systemtap probing easier to use qemu generates qemu*.stp files with aliases for various events for each of the executables. The installer places these files in /usr/share/systemtap/tapset/. These files are generated by the tracetool. However, the /usr/bin/qemu-kvm is produced with a copy: cp -a x86_64-softmmu/qemu-system-x86_64 qemu-kvm No matching qemu-kvm.stp generated for the qemu-kvm executable. It would be really nice if that tapset file is generated so people can use more symbolic probe points. ** Affects: qemu Importance: Undecided Status: New -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/848571 Title: qemu does not generate a qemu-kvm.stp tapset file Status in QEMU: New Bug description: To make the systemtap probing easier to use qemu generates qemu*.stp files with aliases for various events for each of the executables. The installer places these files in /usr/share/systemtap/tapset/. These files are generated by the tracetool. However, the /usr/bin/qemu-kvm is produced with a copy: cp -a x86_64-softmmu/qemu-system-x86_64 qemu-kvm No matching qemu-kvm.stp generated for the qemu-kvm executable. It would be really nice if that tapset file is generated so people can use more symbolic probe points. To manage notifications about this bug go to: https://bugs.launchpad.net/qemu/+bug/848571/+subscriptions
[Qemu-devel] buildbot failure in qemu on trivial-patches_i386_debian_6_0
The Buildbot has detected a new failure on builder trivial-patches_i386_debian_6_0 while building qemu. Full details are available at: http://buildbot.b1-systems.de/qemu/builders/trivial-patches_i386_debian_6_0/builds/29 Buildbot URL: http://buildbot.b1-systems.de/qemu/ Buildslave for this Build: yuzuki Build Reason: The Nightly scheduler named 'nightly_trivial-patches' triggered this build Build Source Stamp: [branch trivial-patches] HEAD Blamelist: BUILD FAILED: failed git sincerely, -The Buildbot
Re: [Qemu-devel] [PATCH v8 3/4] block: add block timer and throttling algorithm
On Fri, Sep 9, 2011 at 10:44 PM, Marcelo Tosatti wrote: > On Thu, Sep 08, 2011 at 06:11:07PM +0800, Zhi Yong Wu wrote: >> Note: >> 1.) When bps/iops limits are specified to a small value such as 511 >> bytes/s, this VM will hang up. We are considering how to handle this senario. > > You can increase the length of the slice, if the request is larger than > slice_time * bps_limit. Yeah, but it is a challenge for how to increase it. Do you have some nice idea? > >> 2.) When "dd" command is issued in guest, if its option bs is set to a >> large value such as "bs=1024K", the result speed will slightly bigger than >> the limits. > > Why? This issue has not existed. I will remove it. When drive bps=100, i did some testings on guest VM. 1.) bs=1024K 18+0 records in 18+0 records out 18874368 bytes (19 MB) copied, 26.6268 s, 709 kB/s 2.) bs=2048K 18+0 records in 18+0 records out 37748736 bytes (38 MB) copied, 46.5336 s, 811 kB/s > > There is lots of debugging leftovers in the patch. sorry, i forgot to remove them. > > -- Regards, Zhi Yong Wu
Re: [Qemu-devel] Why qemu write/rw speed is so low?
This is real log when fio issued with bs=128K and bps=100(block I/O throttling): 8,201 0.0 24332 A WS 79958528 + 256 <- (253,2) 71830016 8,002 0.00912 24332 A WS 80984576 + 256 <- (8,2) 79958528 8,203 0.01778 24332 Q WS 80984576 + 256 [qemu-system-x86] 8,204 0.06527 24332 G WS 80984576 + 256 [qemu-system-x86] 8,205 0.07817 24332 P N [qemu-system-x86] 8,206 0.11234 24332 I WS 80984576 + 256 [qemu-system-x86] CPU0 (8,2): Reads Queued: 0,0KiB Writes Queued: 558, 25,244KiB Read Dispatches:0,0KiB Write Dispatches: 265, 25,440KiB Reads Requeued: 0 Writes Requeued: 0 Reads Completed:0,0KiB Writes Completed:1,027, 56,420KiB Read Merges:0,0KiB Write Merges: 19, 76KiB Read depth: 0 Write depth: 3 IO unplugs: 217 Timer unplugs: 268 CPU1 (8,2): Reads Queued: 0,0KiB Writes Queued: 483, 31,176KiB Read Dispatches:0,0KiB Write Dispatches: 262, 30,980KiB Reads Requeued: 0 Writes Requeued: 0 Reads Completed:0,0KiB Writes Completed:0,0KiB Read Merges:0,0KiB Write Merges: 20, 80KiB Read depth: 0 Write depth: 3 IO unplugs: 265 Timer unplugs: 181 Total (8,2): Reads Queued: 0,0KiB Writes Queued: 1,041, 56,420KiB Read Dispatches:0,0KiB Write Dispatches: 527, 56,420KiB Reads Requeued: 0 Writes Requeued: 0 Reads Completed:0,0KiB Writes Completed:1,027, 56,420KiB Read Merges:0,0KiB Write Merges: 39, 156KiB IO unplugs: 482 Timer unplugs: 449 Throughput (R/W): 0KiB/s / 482KiB/s Events (8,2): 17,661 entries Skips: 1,820 forward (3,918,005 - 99.6%) I found that I/O pattern host issues each time is different when fio is issued with different bs value. On Tue, Sep 13, 2011 at 10:38 AM, Zhi Yong Wu wrote: > On Fri, Sep 9, 2011 at 6:38 PM, Stefan Hajnoczi > wrote: >> On Fri, Sep 09, 2011 at 05:44:36PM +0800, Zhi Yong Wu wrote: >>> Today, i did some basical I/O testing, and suddenly found that qemu write >>> and rw speed is so low now, my qemu binary is built on commit >>> 344eecf6995f4a0ad1d887cec922f6806f91a3f8. >>> >>> Do qemu have regression? >>> >>> The testing data is shown as below: >>> >>> 1.) write >>> >>> test: (g=0): rw=write, bs=512-512/512-512, ioengine=libaio, iodepth=1 >> >> Please post your QEMU command-line. If your -drive is using >> cache=writethrough then small writes are slow because they require the >> physical disk to write and then synchronize its write cache. Typically >> cache=none is a good setting to use for local disks. >> >> The block size of 512 bytes is too small. Ext4 uses a 4 KB block size, >> so I think a 512 byte write from the guest could cause a 4 KB >> read-modify-write operation on the host filesystem. >> >> You can check this by running btrace(8) on the host during the >> benchmark. The blktrace output and the summary statistics will show >> what I/O pattern the host is issuing. > 8,2 0 1 0.0 337 A WS 425081504 + 8 <- > (253,1) 42611360 > 8,0 0 2 0.00896 337 A WS 426107552 + 8 <- > (8,2) 425081504 > 8,2 0 3 0.01772 337 Q WS 426107552 + 8 [jbd2/dm-1-8] > 8,2 0 4 0.06617 337 G WS 426107552 + 8 [jbd2/dm-1-8] > 8,2 0 5 0.07862 337 P N [jbd2/dm-1-8] > 8,2 0 6 0.10481 337 I WS 426107552 + 8 [jbd2/dm-1-8] > . > CPU0 (8,2): > Reads Queued: 11, 416KiB Writes Queued: 20, > 72KiB > Read Dispatches: 12, 440KiB Write Dispatches: 8, > 72KiB > Reads Requeued: 0 Writes Requeued: 0 > Reads Completed: 14, 448KiB Writes Completed: 12, > 72KiB > Read Merges: 0, 0KiB Write Merges: 10, > 40KiB > Read depth: 2 Write depth: 2 > IO unplugs: 11 Timer unplugs: 0 > CPU1 (8,2): > Reads Queued: 8, 32KiB Writes Queued: 0, > 0KiB > Read Dispatches: 2, 8KiB Write Dispatches: 0, > 0KiB > Reads Requeued: 0 Writes Requeued: 0 > Reads Completed: 0, 0KiB Writes Completed: 0, > 0KiB > Read Merges: 5, 20KiB Write Merges: 0, > 0Ki
Re: [Qemu-devel] Why qemu write/rw speed is so low?
On Fri, Sep 9, 2011 at 6:38 PM, Stefan Hajnoczi wrote: > On Fri, Sep 09, 2011 at 05:44:36PM +0800, Zhi Yong Wu wrote: >> Today, i did some basical I/O testing, and suddenly found that qemu write >> and rw speed is so low now, my qemu binary is built on commit >> 344eecf6995f4a0ad1d887cec922f6806f91a3f8. >> >> Do qemu have regression? >> >> The testing data is shown as below: >> >> 1.) write >> >> test: (g=0): rw=write, bs=512-512/512-512, ioengine=libaio, iodepth=1 > > Please post your QEMU command-line. If your -drive is using > cache=writethrough then small writes are slow because they require the > physical disk to write and then synchronize its write cache. Typically > cache=none is a good setting to use for local disks. > > The block size of 512 bytes is too small. Ext4 uses a 4 KB block size, > so I think a 512 byte write from the guest could cause a 4 KB > read-modify-write operation on the host filesystem. > > You can check this by running btrace(8) on the host during the > benchmark. The blktrace output and the summary statistics will show > what I/O pattern the host is issuing. 8,201 0.0 337 A WS 425081504 + 8 <- (253,1) 42611360 8,002 0.00896 337 A WS 426107552 + 8 <- (8,2) 425081504 8,203 0.01772 337 Q WS 426107552 + 8 [jbd2/dm-1-8] 8,204 0.06617 337 G WS 426107552 + 8 [jbd2/dm-1-8] 8,205 0.07862 337 P N [jbd2/dm-1-8] 8,206 0.10481 337 I WS 426107552 + 8 [jbd2/dm-1-8] . CPU0 (8,2): Reads Queued: 11, 416KiB Writes Queued: 20, 72KiB Read Dispatches: 12, 440KiB Write Dispatches:8, 72KiB Reads Requeued: 0 Writes Requeued: 0 Reads Completed: 14, 448KiB Writes Completed: 12, 72KiB Read Merges:0,0KiB Write Merges: 10, 40KiB Read depth: 2 Write depth: 2 IO unplugs:11 Timer unplugs: 0 CPU1 (8,2): Reads Queued: 8, 32KiB Writes Queued: 0,0KiB Read Dispatches:2,8KiB Write Dispatches:0,0KiB Reads Requeued: 0 Writes Requeued: 0 Reads Completed:0,0KiB Writes Completed:0,0KiB Read Merges:5, 20KiB Write Merges:0,0KiB Read depth: 2 Write depth: 2 IO unplugs: 0 Timer unplugs: 0 Total (8,2): Reads Queued: 19, 448KiB Writes Queued: 20, 72KiB Read Dispatches: 14, 448KiB Write Dispatches:8, 72KiB Reads Requeued: 0 Writes Requeued: 0 Reads Completed: 14, 448KiB Writes Completed: 12, 72KiB Read Merges:5, 20KiB Write Merges: 10, 40KiB IO unplugs:11 Timer unplugs: 0 Throughput (R/W): 69KiB/s / 11KiB/s Events (8,2): 411 entries Skips: 50 forward (5,937 - 93.5%) >From its log, host will write 8 blocks each time. what is each block's size? > > I suggest changing your fio block size to 8 KB if you want to try a > small block size. If you want a large block size, try 64 KB or 128 KB. When -drive if=virtio,cache=none,file=xxx,bps=100 is set (note that bps is in bytes). test: (g=0): rw=write, bs=512-512/512-512, ioengine=libaio, iodepth=1 Starting 1 process ^Cbs: 1 (f=1): [W] [1.9% done] [0K/61K /s] [0/120 iops] [eta 01h:00m:57s] fio: terminating on signal 2 test: (groupid=0, jobs=1): err= 0: pid=27515 write: io=3,960KB, bw=56,775B/s, iops=110, runt= 71422msec slat (usec): min=19, max=31,032, avg=65.03, stdev=844.57 clat (msec): min=1, max=353, avg= 8.93, stdev=11.91 lat (msec): min=1, max=353, avg= 8.99, stdev=12.00 bw (KB/s) : min=2, max= 60, per=102.06%, avg=56.14, stdev=10.89 cpu : usr=0.04%, sys=0.61%, ctx=7936, majf=0, minf=26 IO depths: 1=100.0%, 2=0.0%, 4=0.0%, 8=0.0%, 16=0.0%, 32=0.0%, >=64=0.0% submit: 0=0.0%, 4=100.0%, 8=0.0%, 16=0.0%, 32=0.0%, 64=0.0%, >=64=0.0% complete : 0=0.0%, 4=100.0%, 8=0.0%, 16=0.0%, 32=0.0%, 64=0.0%, >=64=0.0% issued r/w: total=0/7920, short=0/0 lat (msec): 2=0.03%, 4=0.09%, 10=98.48%, 20=0.54%, 50=0.67% lat (msec): 100=0.03%, 250=0.05%, 500=0.11% Run status group 0 (all jobs): WRITE: io=3,960KB, aggrb=55KB/s, minb=56KB/s, maxb=56KB/s, mint=71422msec, maxt=71422msec Disk stats (read/write): dm-0: ios=6/8007, merge=0/0, ticks=179/78114, in_queue=78272, util=99.58%, aggrios=4/7975, aggrmerge=0/44, aggrticks=179/75153, aggrin_queue=75304, aggrutil=99.53% vda: ios=4/7975, merge=0/44, ticks=179/75153, in_queue=75304, util=99.53% test: (g=0): rw=write, bs=8K-8K/8K-8K, ioengine=liba
Re: [Qemu-devel] [PATCH] support add-cow file format
于Mon 12 Sep 2011 03:59:07 PM CST,Kevin Wolf写到: Am 10.09.2011 02:54, schrieb Dong Xu Wang: 于Fri 09 Sep 2011 10:27:26 PM CST,Kevin Wolf写到: Am 09.09.2011 07:48, schrieb Dong Xu Wang: As raw file format does not support backing_file and copy on write feature, so I add COW to it to support backing_file option. I store dirty bitmap in an add-cow file. When executed, it looks like this: qemu-img create -f add-cow -o backing_file=ubuntu.img,image_file=test.img test.add-cow qemu -drive if=virtio,file=test.add-cow -m 1024 (test.img is a raw format file; test.add-cow stores bitmap) Signed-off-by: Dong Xu Wang You should not make any changes to generic code, except maybe add something to bdrv_get_info(). In particular you shouldn't need to touch bdrv_open() or bdrv_create() at all. The one required change in the approach for this to work is that you shouldn't view raw+add_cow as a unit, but add_cow should be treated as something separate that happens to be stacked on a raw file (which is created separately). Then you can do almost everything in block/add-cow.c. --- Makefile.objs |1 + block.c | 83 ++- block.h |2 + block/add-cow.c | 456 +++ block_int.h |6 + qemu-img.c | 10 ++ 6 files changed, 555 insertions(+), 3 deletions(-) create mode 100644 block/add-cow.c diff --git a/Makefile.objs b/Makefile.objs index 26b885b..1402f9f 100644 --- a/Makefile.objs +++ b/Makefile.objs @@ -31,6 +31,7 @@ block-obj-$(CONFIG_LINUX_AIO) += linux-aio.o block-nested-y += raw.o cow.o qcow.o vdi.o vmdk.o cloop.o dmg.o bochs.o vpc.o vvfat.o block-nested-y += qcow2.o qcow2-refcount.o qcow2-cluster.o qcow2-snapshot.o qcow2-cache.o +block-nested-y += add-cow.o block-nested-y += qed.o qed-gencb.o qed-l2-cache.o qed-table.o qed-cluster.o block-nested-y += qed-check.o block-nested-y += parallels.o nbd.o blkdebug.o sheepdog.o blkverify.o diff --git a/block.c b/block.c index a8c789a..c797cfc 100644 --- a/block.c +++ b/block.c @@ -369,7 +369,7 @@ static int find_image_format(const char *filename, BlockDriver **pdrv) { int ret, score, score_max; BlockDriver *drv1, *drv; -uint8_t buf[2048]; +uint8_t buf[4096]; BlockDriverState *bs; What's the reason for this change? The size of add_cow_header in my code is larger than 2048. Right, but the magic is in the first 8 bytes, so for probing 2048 bytes should be more than enough. diff --git a/block/add-cow.c b/block/add-cow.c new file mode 100644 index 000..f4b67e5 --- /dev/null +++ b/block/add-cow.c @@ -0,0 +1,456 @@ +#include "qemu-common.h" +#include "block_int.h" +#include "module.h" + +#define ADD_COW_MAGIC (((uint64_t)'A' << 56) | ((uint64_t)'D' << 48) | \ +((uint64_t)'D' << 40) | ((uint64_t)'_' << 32) | \ +((uint64_t)'C' << 24) | ((uint64_t)'O' << 16) | \ +((uint64_t)'W' << 8) | 0xFF) +#define ADD_COW_VERSION 1 + +struct add_cow_header { +uint64_t magic; +uint32_t version; +char backing_file[1024]; +char image_file[1024]; +uint64_t size; +uint32_t sectorsize; +} add_cow_header; QEMU_PACKED Sorry, what does QEMU_PACKED mean? This is an on-disk structure, so you need to pack the structure. Otherwise the compiler would be free to add padding between the fields in order to optimise alignment. struct add_cow_header { ... } QEMU_PACKED add_cow_header; Hm, actually, do you really want to declare a global variable here? Or is a typedef missing? Also, coding style requires the struct name to be spelled AddCowHeader. Kevin Thank you,Kevin. I will consider these advice in the second version.
Re: [Qemu-devel] [PATCH v2 09/12] sheepdog: move coroutine send/recv function to generic code
At Fri, 9 Sep 2011 10:11:38 +0200, Paolo Bonzini wrote: > > Outside coroutines, avoid busy waiting on EAGAIN by temporarily > making the socket blocking. > > The API of qemu_recvv/qemu_sendv is slightly different from > do_readv/do_writev because they do not handle coroutines. It > returns the number of bytes written before encountering an > EAGAIN. The specificity of yielding on EAGAIN is entirely in > qemu-coroutine.c. > > Cc: MORITA Kazutaka > Signed-off-by: Paolo Bonzini > --- > Thanks for the review. I checked with qemu-io that all of > > readv -v 0 524288 (x8) > readv -v 0 262144 (x16) > readv -v 0 1024 (x4096) > readv -v 0 1536 (x2730) 1024 > readv -v 0 1024 512 (x2730) 1024 > > work and produce the same output, while previously they would fail. > Looks like it's hard to trigger the code just with qemu. > > block/sheepdog.c | 225 > ++ > cutils.c | 103 + > qemu-common.h|3 + > qemu-coroutine.c | 70 + > qemu-coroutine.h | 26 ++ > 5 files changed, 225 insertions(+), 202 deletions(-) Thanks, this passed qemu-iotests on Sheepdog. Reviewed-by: MORITA Kazutaka
Re: [Qemu-devel] [PATCH V8 03/14] Add persistent state handling to TPM TIS frontend driver
On 09/12/2011 05:16 PM, Paul Moore wrote: On Sunday, September 11, 2011 12:45:05 PM Stefan Berger wrote: On 09/09/2011 05:13 PM, Paul Moore wrote: On Wednesday, August 31, 2011 10:35:54 AM Stefan Berger wrote: Index: qemu-git/hw/tpm_tis.c === --- qemu-git.orig/hw/tpm_tis.c +++ qemu-git/hw/tpm_tis.c @@ -6,6 +6,8 @@ * Author: Stefan Berger * David Safford * + * Xen 4 support: Andrease Niederl + * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation, version 2 of the @@ -839,3 +841,167 @@ static int tis_init(ISADevice *dev) err_exit: return -1; } + +/* persistent state handling */ + +static void tis_pre_save(void *opaque) +{ +TPMState *s = opaque; +uint8_t locty = s->active_locty; Is it safe to read s->active_locty without the state_lock? I'm not sure at this point but I saw it being protected by the lock elsewhere ... It cannot change anymore since no vCPU is in the TPM TIS emulation layer anymore but all we're doing is wait for the last outstanding command to be returned to use from the TPM thread. I don't mind putting this reading into the critical section, though, just to have it be consistent. [Dropping the rest of the comments since they all cover the same issue] I'm a big fan of consistency, especially when it comes to locking; inconsistent lock usage can lead to confusion and that is almost never good. If we need a lock here because there is the potential for an outstanding TPM command, then I vote for locking in this function just as you would in any other. However, if we really don't need locks here because the outstanding TPM command will have _no_ effect on the TPMState or any related structure, then just do away with the lock completely and make of note of it in the function explaining why. Let's give the consistency argument the favor and extend the locking over those parts that usually also get locked. Regards, Stefan
Re: [Qemu-devel] [PATCH V8 03/14] Add persistent state handling to TPM TIS frontend driver
On Sunday, September 11, 2011 12:45:05 PM Stefan Berger wrote: > On 09/09/2011 05:13 PM, Paul Moore wrote: > > On Wednesday, August 31, 2011 10:35:54 AM Stefan Berger wrote: > >> Index: qemu-git/hw/tpm_tis.c > >> === > >> --- qemu-git.orig/hw/tpm_tis.c > >> +++ qemu-git/hw/tpm_tis.c > >> @@ -6,6 +6,8 @@ > >> > >>* Author: Stefan Berger > >>* David Safford > >>* > >> > >> + * Xen 4 support: Andrease Niederl > >> + * > >> > >>* This program is free software; you can redistribute it and/or > >>* modify it under the terms of the GNU General Public License as > >>* published by the Free Software Foundation, version 2 of the > >> > >> @@ -839,3 +841,167 @@ static int tis_init(ISADevice *dev) > >> > >>err_exit: > >> return -1; > >> > >> } > >> > >> + > >> +/* persistent state handling */ > >> + > >> +static void tis_pre_save(void *opaque) > >> +{ > >> +TPMState *s = opaque; > >> +uint8_t locty = s->active_locty; > > > > Is it safe to read s->active_locty without the state_lock? I'm not sure > > at this point but I saw it being protected by the lock elsewhere ... > It cannot change anymore since no vCPU is in the TPM TIS emulation layer > anymore but all we're doing is wait for the last outstanding command to > be returned to use from the TPM thread. > I don't mind putting this reading into the critical section, though, > just to have it be consistent. [Dropping the rest of the comments since they all cover the same issue] I'm a big fan of consistency, especially when it comes to locking; inconsistent lock usage can lead to confusion and that is almost never good. If we need a lock here because there is the potential for an outstanding TPM command, then I vote for locking in this function just as you would in any other. However, if we really don't need locks here because the outstanding TPM command will have _no_ effect on the TPMState or any related structure, then just do away with the lock completely and make of note of it in the function explaining why. -- paul moore virtualization @ redhat
Re: [Qemu-devel] qemu virtIO blocking operation - question
On Sep 11, 2011, at 6:34 AM, Stefan Hajnoczi wrote: > > You may find these posts I wrote helpful, they explain vcpu threads and > the I/O thread: > http://blog.vmsplice.net/2011/03/qemu-internals-big-picture-overview.html > http://blog.vmsplice.net/2011/03/qemu-internals-overall-architecture-and.html > "One example user of worker threads is posix-aio-compat.c, an asynchronous file I/O implementation. When core QEMU issues an aio request it is placed on a queue. Worker threads take requests off the queue and execute them outside of core QEMU. They may perform blocking operations since they execute in their own threads and do not block Another example is ui/vnc-jobs-async.c which performs compute-intensive image compression and encoding in worker threads." I wonder why there isn't a general framework for this? Some thread that would take requests off a queue and process them without knowing the internals of the request. Ani The information contained in this message may be privileged and confidential and protected from disclosure. If the reader of this message is not the intended recipient, or an employee or agent responsible for delivering this message to the intended recipient, you are hereby notified that any reproduction, dissemination or distribution of this communication is strictly prohibited. If you have received this communication in error, please notify us immediately by replying to the message and deleting it from your computer. Thank you. Tellabs
Re: [Qemu-devel] [PATCH] PPC: Fix via-cuda memory registration
On 09/12/2011 08:53 AM, Avi Kivity wrote: On 09/12/2011 04:46 PM, Lucas Meneghel Rodrigues wrote: On 09/12/2011 06:07 AM, Avi Kivity wrote: On 09/11/2011 02:38 PM, Alexander Graf wrote: Am 11.09.2011 um 12:41 schrieb Avi Kivity: > On 09/08/2011 07:54 PM, Alexander Graf wrote: >> PS: Please test your patches. This one could have been found with an invocation >> as simple as "qemu-system-ppc". We boot into the OpenBIOS prompt by default, >> so you wouldn't even have required a guest image or kernel. >> > > > Sorry about that. > > Note that it's pretty hard to test these patches. I often don't even know which binary as the device->target relationship is not immediately visible, The patch was explicitly to convert ppc ;). Yes, in this case. Not in the general case. > and I don't really know what to expect from the guest. The very easy check-fundamentals thing to do for ppc is to execute qemu-system-ppc without arguments. It should drop you into an OF prompt. Both memory api bugs on ppc I've seen now would have been exposed with that. I agree that we should have something slightly more sophisticated, but doing such a bare minimum test is almost for free to the tester and covers at least basic functionality :). I don't mind people introducibg subtle bugs in corner cases - these things happen. But an abort() when you execute the binary? That really shouldn't happen ever. This one is almost as bad. Yeah. > It would be best if we had a kvm-autotest testset for tcg, it would probably run in just a few minutes and increase confidence in these patches. Yeah, I am using kvm-autotest today for regression testing, but it's very hard to tell it to run multiple different binaries. The target program variable can only be set for an execution job, making it impossible to run multiple targets in one autotest run. Alexander, I've started to work on this, I'm clearing out my request list, last week I've implemented ticket 50, that was related to special block configuration for the tests, now I want to make it possible to support multiple binaries. Probably best to tell autotest about the directory, and let it pick up the binary. Still need some configuration to choose between qemu-kvm and qemu-system-x86_64. Lucas? Yes, that would also work, having different variants with different qemu and qemu-img paths. Those binaries would have to be already pre-built, but then we miss the ability autotest has of building the binaries and prepare the environment. It'd be like: variant1: qemu = /path/to/qemu1 qemu-img = /path/to/qemu-img1 extra_params = "--appropriate --extra --params2" variant2: qemu = /path/to/qemu2 qemu-img = /path/to/qemu-img2 extra_params = "--appropriate --extra --params2" Something like that. It's a feasible intermediate solution until I finish work on supporting multiple userspaces. Another option is, now that the binary name 'qemu' is available for general use, make it possible to invoke everything with just one binary: qemu -system -target mips ... qemu-system -target mips ... qemu-system-mips ... I have a fancy script that I'll post soon that does something like this. It takes the git approach and expands: qemu foo --bar=baz To: qemu-foo --bar=baz Which means that you could do: qemu system-x86_64 -hda foo.img And it'd go to: qemu-system-x86_64 -hda foo.img But there is also a smarter 'run' command that let's you do: qemu run --target=x86_64 -hda foo.img I've made no attempt to unify linux-user. It's a very different executable with a different usage model. My motivation is QOM as I don't want to have command line options to create devices any more. Instead, a front end script will talk to the monitor to setup devices/machines. Regards, Anthony Liguori are all equivalent. autotest should easily be able to pass different -target based on the test being run.
Re: [Qemu-devel] [PATCH] Remove blanks before \n in output strings
On 12 September 2011 21:33, Stefan Weil wrote: > Those blanks violate the coding conventions, see > scripts/checkpatch.pl. I can see doing this if there are any cases of actual output-to-users here, but for debug printfs, it scarcely seems worth the effort. I'm not arguing against this particular patch, since you've done the work now; just wondering what the motivation was... > diff --git a/tests/test-i386.c b/tests/test-i386.c > index 9cb5b51..8e64bba 100644 > --- a/tests/test-i386.c > +++ b/tests/test-i386.c > @@ -802,7 +802,7 @@ void test_fcmp(double a, double b) > "fstsw %%ax\n" > : "=a" (fpus) > : "t" (a), "u" (b)); > - printf("fcom(%f %f)=%04lx \n", > + printf("fcom(%f %f)=%04lx\n", > a, b, fpus & (0x4500 | FPUS_EMASK)); > fpu_clear_exceptions(); > asm("fucom %2\n" (To save anybody else checking) Changing the output of this test program is OK because tests/Makefile makes the arguable assumption that we're running on an x86 box and can regenerate the "known good" output reference rather than having to keep a copy in git... thanks -- PMM
Re: [Qemu-devel] [PATCH] PPC: Fix via-cuda memory registration
On 12 September 2011 14:53, Avi Kivity wrote: > Another option is, now that the binary name 'qemu' is available for general > use, make it possible to invoke everything with just one binary: > > qemu -system -target mips ... Sounds reasonable, but we should probably make sure this (and more significantly the implied "support all the existing options of qemu-system-*" semantics) are really what we want to support in a single "qemu" binary, since it's going to be something we need to maintain compatibility to going forwards... -- PMM
[Qemu-devel] [PATCH] Remove blanks before \n in output strings
Those blanks violate the coding conventions, see scripts/checkpatch.pl. Blanks missing after colons in the changed lines were added. This patch does not try to fix tabs, long lines and other problems in the changed lines, therefore checkpatch.pl reports many violations. Signed-off-by: Stefan Weil --- block/vvfat.c |2 +- darwin-user/machload.c |4 ++-- hw/bonito.c| 24 hw/fmopl.c |2 +- hw/hpet.c |8 hw/loader.c|4 ++-- hw/mips_fulong2e.c |2 +- hw/mst_fpga.c |4 ++-- hw/vt82c686.c | 12 ++-- linux-user/syscall.c |2 +- mips-dis.c |2 +- qemu-io.c |2 +- slirp/tcp_input.c |8 slirp/tcp_subr.c |2 +- target-ppc/helper.c|2 +- tests/test-i386.c |2 +- 16 files changed, 41 insertions(+), 41 deletions(-) diff --git a/block/vvfat.c b/block/vvfat.c index 187ac96..f567c9a 100644 --- a/block/vvfat.c +++ b/block/vvfat.c @@ -1789,7 +1789,7 @@ DLOG(fprintf(stderr, "read cluster %d (sector %d)\n", (int)cluster_num, (int)clu for (i = 0; i < 0x10 * s->sectors_per_cluster; i++) { int cluster_count = 0; -DLOG(fprintf(stderr, "check direntry %d: \n", i); print_direntry(direntries + i)); +DLOG(fprintf(stderr, "check direntry %d:\n", i); print_direntry(direntries + i)); if (is_volume_label(direntries + i) || is_dot(direntries + i) || is_free(direntries + i)) continue; diff --git a/darwin-user/machload.c b/darwin-user/machload.c index 3bc3b65..0aa8282 100644 --- a/darwin-user/machload.c +++ b/darwin-user/machload.c @@ -865,11 +865,11 @@ unsigned long setup_arg_pages(void * mh, char ** argv, char ** env) page_set_flags((int)argv[i], (int)(argv[i]+strlen(argv[i])), PROT_READ | PAGE_VALID); } -DPRINTF("pushing argc %d \n", argc); +DPRINTF("pushing argc %d\n", argc); stl(stack, argc); stack--; -DPRINTF("pushing mh 0x%x \n", (int)mh); +DPRINTF("pushing mh 0x%x\n", (int)mh); stl(stack, (int) mh); /* Stack points on the mh */ diff --git a/hw/bonito.c b/hw/bonito.c index 8708e95..fdb8198 100644 --- a/hw/bonito.c +++ b/hw/bonito.c @@ -241,7 +241,7 @@ static void bonito_writel(void *opaque, target_phys_addr_t addr, uint32_t val) saddr = (addr - BONITO_REGBASE) >> 2; -DPRINTF("bonito_writel "TARGET_FMT_plx" val %x saddr %x \n", addr, val, saddr); +DPRINTF("bonito_writel "TARGET_FMT_plx" val %x saddr %x\n", addr, val, saddr); switch (saddr) { case BONITO_BONPONCFG: case BONITO_IODEVCFG: @@ -287,10 +287,10 @@ static void bonito_writel(void *opaque, target_phys_addr_t addr, uint32_t val) break; case BONITO_INTEN: case BONITO_INTISR: -DPRINTF("write to readonly bonito register %x \n", saddr); +DPRINTF("write to readonly bonito register %x\n", saddr); break; default: -DPRINTF("write to unknown bonito register %x \n", saddr); +DPRINTF("write to unknown bonito register %x\n", saddr); break; } } @@ -302,7 +302,7 @@ static uint32_t bonito_readl(void *opaque, target_phys_addr_t addr) saddr = (addr - BONITO_REGBASE) >> 2; -DPRINTF("bonito_readl "TARGET_FMT_plx" \n", addr); +DPRINTF("bonito_readl "TARGET_FMT_plx"\n", addr); switch (saddr) { case BONITO_INTISR: return s->regs[saddr]; @@ -328,7 +328,7 @@ static void bonito_pciconf_writel(void *opaque, target_phys_addr_t addr, { PCIBonitoState *s = opaque; -DPRINTF("bonito_pciconf_writel "TARGET_FMT_plx" val %x \n", addr, val); +DPRINTF("bonito_pciconf_writel "TARGET_FMT_plx" val %x\n", addr, val); s->dev.config_write(&s->dev, addr, val, 4); } @@ -443,7 +443,7 @@ static uint32_t bonito_sbridge_pciaddr(void *opaque, target_phys_addr_t addr) exit(1); } pciaddr = PCI_ADDR(pci_bus_num(s->pcihost->bus), devno, funno, regno); -DPRINTF("cfgaddr %x pciaddr %x busno %x devno %d funno %d regno %d \n", +DPRINTF("cfgaddr %x pciaddr %x busno %x devno %d funno %d regno %d\n", cfgaddr, pciaddr, pci_bus_num(s->pcihost->bus), devno, funno, regno); return pciaddr; @@ -456,7 +456,7 @@ static void bonito_spciconf_writeb(void *opaque, target_phys_addr_t addr, uint32_t pciaddr; uint16_t status; -DPRINTF("bonito_spciconf_writeb "TARGET_FMT_plx" val %x \n", addr, val); +DPRINTF("bonito_spciconf_writeb "TARGET_FMT_plx" val %x\n", addr, val); pciaddr = bonito_sbridge_pciaddr(s, addr); if (pciaddr == 0x) { @@ -480,7 +480,7 @@ static void bonito_spciconf_writew(void *opaque, target_phys_addr_t addr, uint32_t pciaddr; uint16_t status; -DPRINTF("bonito_spciconf_writew "TARGET_FMT_plx" val %x \n", addr, val); +DPRINTF("bonito_spciconf_writew "TARGET_FMT_plx" val %x\n", addr, val);
Re: [Qemu-devel] [Qemu-ppc] [PATCH 7/9] openpic: avoid a warning from clang analyzer
On Mon, Sep 12, 2011 at 5:12 PM, Scott Wood wrote: > On 09/04/2011 10:52 AM, Blue Swirl wrote: >> Avoid this warning by clang analyzer by defining a default case: >> /src/qemu/hw/openpic.c:477:5: warning: Undefined or garbage value >> returned to caller >> return retval; >> >> Signed-off-by: Blue Swirl >> --- >> hw/openpic.c | 1 + >> 1 files changed, 1 insertions(+), 0 deletions(-) >> >> diff --git a/hw/openpic.c b/hw/openpic.c >> index 26c96e2..4b883ac 100644 >> --- a/hw/openpic.c >> +++ b/hw/openpic.c >> @@ -469,6 +469,7 @@ static inline uint32_t read_IRQreg (openpic_t >> *opp, int n_IRQ, uint32_t reg) >> case IRQ_IPVP: >> retval = opp->src[n_IRQ].ipvp; >> break; >> + default: >> case IRQ_IDE: >> retval = opp->src[n_IRQ].ide; >> break; > > What's special about IDE? Shouldn't it return 0x as some other > functions (e.g. openpic_gbl_read) do with unrecognized registers? Then > there's openpic_src_read() which has still different behavior for the > same registers. :-P > > Note that this function is only ever called with a constant in "reg". > Since it's a static function and all call sites could have been > verified, this could be considered a flaw in clang's analyzer. This > workaround will prevent GCC from issuing a warning if a new caller is > added that passes a different constant value. > > The best answer is probably to just get rid of this function and have > the caller refer to opp->src[n_irq].whatever directly. write_IRQreg() > could be split into something like set_src_ipvp() and set_src_ide(). Alex posted patches to that effect: http://lists.nongnu.org/archive/html/qemu-devel/2011-09/msg00947.html http://lists.nongnu.org/archive/html/qemu-devel/2011-09/msg00948.html
Re: [Qemu-devel] [PATCH v3 5/6] vga: Use linear mapping + dirty logging in chain 4 memory access mode
On Mon, Sep 12, 2011 at 3:20 PM, Alexander Graf wrote: > Jan Kiszka wrote: >> Most VGA memory access modes require MMIO handling as they demand weird >> logic to get a byte from or into the video RAM. However, there is one >> exception: chain 4 mode with all memory planes enabled for writing. This >> mode actually allows lineary mapping, which can then be combined with >> dirty logging to accelerate KVM. >> >> This patch accelerates specifically VBE accesses like they are used by >> grub in graphical mode. Not only the standard VGA adapter benefits from >> this, also vmware and spice in VGA mode. >> >> CC: Gerd Hoffmann >> CC: Avi Kivity >> Signed-off-by: Jan Kiszka >> > > [...] > >> +static void vga_update_memory_access(VGACommonState *s) >> +{ >> + MemoryRegion *region, *old_region = s->chain4_alias; >> + target_phys_addr_t base, offset, size; >> + >> + s->chain4_alias = NULL; >> + >> + if ((s->sr[0x02] & 0xf) == 0xf && s->sr[0x04] & 0x08) { >> + offset = 0; >> + switch ((s->gr[6] >> 2) & 3) { >> + case 0: >> + base = 0xa; >> + size = 0x2; >> + break; >> + case 1: >> + base = 0xa; >> + size = 0x1; >> + offset = s->bank_offset; >> + break; >> + case 2: >> + base = 0xb; >> + size = 0x8000; >> + break; >> + case 3: >> + base = 0xb8000; >> + size = 0x8000; >> + break; >> + } >> + region = g_malloc(sizeof(*region)); >> + memory_region_init_alias(region, "vga.chain4", &s->vram, offset, >> size); >> + memory_region_add_subregion_overlap(s->legacy_address_space, base, >> + region, 2); >> > > This one eventually gives me the following in info mtree with -M g3beige > on qemu-system-ppc: > > (qemu) info mtree :-) > memory > system addr off size 7fff > -vga.chain4 addr 000a off size 1 > -macio addr 8088 off size 8 > --macio-nvram addr 0006 off size 2 > --pmac-ide addr 0002 off size 1000 > --cuda addr 00016000 off size 2000 > --escc-bar addr 00013000 off size 40 > --dbdma addr 8000 off size 1000 > --heathrow-pic addr off size 1000 > -vga.rom addr 8080 off size 1 > -vga.vram addr 8000 off size 80 > -vga-lowmem addr 800a off size 2 > -escc addr 80013000 off size 40 > -isa-mmio addr fe00 off size 20 > I/O > io addr off size 1 > -cmd646-bmdma addr 0700 off size 10 > --cmd646-bmdma-ioport addr 000c off size 4 > --cmd646-bmdma-bus addr 0008 off size 4 > --cmd646-bmdma-ioport addr 0004 off size 4 > --cmd646-bmdma-bus addr off size 4 > -cmd646-cmd addr 0680 off size 4 > -cmd646-data addr 0600 off size 8 > -cmd646-cmd addr 0580 off size 4 > -cmd646-data addr 0500 off size 8 > -ne2000 addr 0400 off size 100 > > This ends up overmapping 0xa, effectively overwriting kernel data. > If I #if 0 the offending chunk out, everything is fine. I would assume > that chain4 really needs to be inside of lowmem? No idea about VGA, but > I'm sure you know what's going on :). I had similar problems with sun4u, fixed with f69539b14bdba7a5cd22e1f4bed439b476b17286. I think also here, PCI should be given a memory range at 0x8000 and VGA should automatically use that like.
Re: [Qemu-devel] [PATCH] PPC: Fix via-cuda memory registration
On 09/12/2011 10:53 AM, Avi Kivity wrote: On 09/12/2011 04:46 PM, Lucas Meneghel Rodrigues wrote: Yes, that would also work, having different variants with different qemu and qemu-img paths. Those binaries would have to be already pre-built, but then we miss the ability autotest has of building the binaries and prepare the environment. It'd be like: variant1: qemu = /path/to/qemu1 qemu-img = /path/to/qemu-img1 extra_params = "--appropriate --extra --params2" variant2: qemu = /path/to/qemu2 qemu-img = /path/to/qemu-img2 extra_params = "--appropriate --extra --params2" Something like that. It's a feasible intermediate solution until I finish work on supporting multiple userspaces. Another option is, now that the binary name 'qemu' is available for general use, make it possible to invoke everything with just one binary: qemu -system -target mips ... qemu-system -target mips ... qemu-system-mips ... are all equivalent. autotest should easily be able to pass different -target based on the test being run. Indeed, a good idea, although there are cases where we indeed want to run different user spaces (say, a windows reactivation test for example), so it's still worth to implement the multiple userspaces thing for autotest. But in the case we just want to run multiple targets, this would be very handy indeed.
Re: [Qemu-devel] [PATCH] PPC: Fix via-cuda memory registration
On Mon, Sep 12, 2011 at 1:53 PM, Avi Kivity wrote: > On 09/12/2011 04:46 PM, Lucas Meneghel Rodrigues wrote: >> >> On 09/12/2011 06:07 AM, Avi Kivity wrote: >>> >>> On 09/11/2011 02:38 PM, Alexander Graf wrote: Am 11.09.2011 um 12:41 schrieb Avi Kivity: > On 09/08/2011 07:54 PM, Alexander Graf wrote: >> PS: Please test your patches. This one could have been found with an invocation >> as simple as "qemu-system-ppc". We boot into the OpenBIOS prompt by default, >> so you wouldn't even have required a guest image or kernel. >> > > > Sorry about that. > > Note that it's pretty hard to test these patches. I often don't even know which binary as the device->target relationship is not immediately visible, The patch was explicitly to convert ppc ;). >>> >>> Yes, in this case. Not in the general case. >>> > and I don't really know what to expect from the guest. The very easy check-fundamentals thing to do for ppc is to execute qemu-system-ppc without arguments. It should drop you into an OF prompt. Both memory api bugs on ppc I've seen now would have been exposed with that. I agree that we should have something slightly more sophisticated, but doing such a bare minimum test is almost for free to the tester and covers at least basic functionality :). I don't mind people introducibg subtle bugs in corner cases - these things happen. But an abort() when you execute the binary? That really shouldn't happen ever. This one is almost as bad. >>> >>> Yeah. >>> > It would be best if we had a kvm-autotest testset for tcg, it would probably run in just a few minutes and increase confidence in these patches. Yeah, I am using kvm-autotest today for regression testing, but it's very hard to tell it to run multiple different binaries. The target program variable can only be set for an execution job, making it impossible to run multiple targets in one autotest run. >> >> Alexander, I've started to work on this, I'm clearing out my request list, >> last week I've implemented ticket 50, that was related to special block >> configuration for the tests, now I want to make it possible to support >> multiple binaries. >> >>> Probably best to tell autotest about the directory, and let it pick up >>> the binary. Still need some configuration to choose between qemu-kvm and >>> qemu-system-x86_64. >>> >>> Lucas? >> >> Yes, that would also work, having different variants with different qemu >> and qemu-img paths. Those binaries would have to be already pre-built, but >> then we miss the ability autotest has of building the binaries and prepare >> the environment. It'd be like: >> >> variant1: >> qemu = /path/to/qemu1 >> qemu-img = /path/to/qemu-img1 >> extra_params = "--appropriate --extra --params2" >> >> >> variant2: >> qemu = /path/to/qemu2 >> qemu-img = /path/to/qemu-img2 >> extra_params = "--appropriate --extra --params2" >> >> Something like that. It's a feasible intermediate solution until I finish >> work on supporting multiple userspaces. >> > > Another option is, now that the binary name 'qemu' is available for general > use, make it possible to invoke everything with just one binary: > > qemu -system -target mips ... > qemu-system -target mips ... > qemu-system-mips ... > > are all equivalent. autotest should easily be able to pass different > -target based on the test being run. Great idea, the original goal of single binary would almost realize. With 'qemu' defaulting to '-system' and '-target i386' we'd also be compatible with previous versions too.
Re: [Qemu-devel] [PATCH] memory: simple memory tree printer
On Mon, Sep 12, 2011 at 10:53 AM, Avi Kivity wrote: > On 09/12/2011 01:37 PM, Gerd Hoffmann wrote: >>> >>> I/O >>> io addr off size 1 >>> -e1000-io addr c000 off size 40 >>> -piix-bmdma-container addr c040 off size 10 >>> --bmdma addr 000c off size 4 >>> --piix-bmdma addr 0008 off size 4 >>> --bmdma addr 0004 off size 4 >>> --piix-bmdma addr off size 4 >>> -pci-conf-data addr 0cfc off size 4 >>> -pci-conf-idx addr 0cf8 off size 4 >> >> Could you put the (variable-length) name field last? That should make the >> whole list more readable as the addresses are aligned then. >> > > Makes sense. Can adopt other features from /proc/iomem - like using > start/end instead of start/length - makes it easier to see if an address > fits in a range. Nice ideas, thanks.
Re: [Qemu-devel] [PATCH 11/15] Sparc: avoid AREG0 for CWP and PSTATE helpers
On Mon, Sep 12, 2011 at 8:29 AM, Stuart Brady wrote: > On Sun, Sep 11, 2011 at 01:31:03PM +, Blue Swirl wrote: >> Make CWP and PSTATE helpers take a parameter for CPUState instead >> of relying on global env. Move the functions to helper.c, remove >> wrapper functions. >> >> Signed-off-by: Blue Swirl >> --- >> Makefile.target | 2 +- >> target-sparc/helper.h | 32 +++--- >> target-sparc/translate.c | 34 >> target-sparc/win_helper.c | 223 >> +++- >> 4 files changed, 90 insertions(+), 201 deletions(-) > > This doesn't seem to move anything into helper.c. Looks like it might not > build, either? It builds and runs, the commit message is stale.
Re: [Qemu-devel] [PATCH 00/15] Sparc AREG0 conversion
On Mon, Sep 12, 2011 at 8:13 AM, Paolo Bonzini wrote: > On 09/12/2011 10:01 AM, Richard Henderson wrote: >> >> > > After this patch set, only load and store op helpers remain in >> > > op_helper.c. I have some patches for those but they need more >> > > thought. >> > >> > Have you benchmarked it? >> >> Asking for a benchmark without full conversion is pointless. > > Agreed. But I would not push these patches without having tried them out on > a prototype of a full conversion (i.e. with the load/store helpers > converted, for which Blue Swirl said he has patches, and with the > environment not pinned to AREG0 in TCG code). The load/store helpers are tricky. Some Sparc64 helpers now need five 32/64 bit arguments, that may be a problem on some hosts. Changing functions like tlb_fill() and do_unaligned_access() to use passed CPUState pointer instead of AREG0 needs global changes. The template system for generating the load/store functions is interesting. Then there are __ldb_mmu() and friends, called from TCG generated code. It would be highly desirable to limit the changes to only Sparc translator but I don't think global changes can be avoided. > So I hoped that he did have such a prototype, or alternatively that he > benchmarked them and showed only minor degradations. I don't see any slowdown. Maybe a real benchmark is needed. Looking at the code, there are only minor differences. On amd64 host, r14 is now available but does not get used for the new code, so that doesn't help. On i386 there are larger differences, but that is mostly because ebp is normally used for the frame pointer. Using it for a global register needs -fomit-frame-pointer. Disregarding the frame pointer issues, the changes are minor. For example i386 host, unpatched, op_helper.o: 0dc0 : dc0: 83 ec 1csub$0x1c,%esp dc3: 65 8b 0d 14 00 00 00mov%gs:0x14,%ecx dca: 89 4c 24 0c mov%ecx,0xc(%esp) dce: 31 c9 xor%ecx,%ecx dd0: 8b 44 24 20 mov0x20(%esp),%eax dd4: 8b 54 24 24 mov0x24(%esp),%edx dd8: 8b 4c 24 0c mov0xc(%esp),%ecx ddc: 65 33 0d 14 00 00 00xor%gs:0x14,%ecx de3: 75 0a jnedef de5: 31 c9 xor%ecx,%ecx de7: 83 c4 1cadd$0x1c,%esp dea: e9 f1 fe ff ff jmpce0 def: e8 fc ff ff ff call df0 df4: 8d b6 00 00 00 00 lea0x0(%esi),%esi dfa: 8d bf 00 00 00 00 lea0x0(%edi),%edi Patched, function in helper.o: 02a0 : 2a0: 55 push %ebp 2a1: 89 e5 mov%esp,%ebp 2a3: 53 push %ebx 2a4: 83 ec 14sub$0x14,%esp 2a7: 8b 45 08mov0x8(%ebp),%eax 2aa: 65 8b 1d 14 00 00 00mov%gs:0x14,%ebx 2b1: 89 5d f4mov%ebx,-0xc(%ebp) 2b4: 31 db xor%ebx,%ebx 2b6: 8b 55 0cmov0xc(%ebp),%edx 2b9: 8b 4d 10mov0x10(%ebp),%ecx 2bc: 8b 5d f4mov-0xc(%ebp),%ebx 2bf: 65 33 1d 14 00 00 00xor%gs:0x14,%ebx 2c6: 75 11 jne2d9 2c8: c7 45 08 00 00 00 00movl $0x0,0x8(%ebp) 2cf: 83 c4 14add$0x14,%esp 2d2: 5b pop%ebx 2d3: 5d pop%ebp 2d4: e9 e7 fe ff ff jmp1c0 2d9: e8 fc ff ff ff call 2da
Re: [Qemu-devel] Re-playable trace!
On Sun, Sep 11, 2011 at 11:22 PM, shbi shb wrote: > Hi, > > Is it possible to get a re-playable trace (memory snapshot) in Qemu? Do you > have any idea for adding this functionality to Qemu? > I need to get a trace of execution in the guest OS, do some modification on > the trace and run it again. > > My problem is that two execution trace of a program may not be the same. So, > I would need one trace which I can run it in Qemu again. Do you have any > clue? There is snapshot functionality, see monitor command 'info snapshots' etc.
Re: [Qemu-devel] qemu virtIO blocking operation - question
On Sep 11, 2011, at 6:34 AM, Stefan Hajnoczi wrote: > On Fri, Sep 09, 2011 at 07:45:17PM -0500, Sinha, Ani wrote: >> So I am writing a virtIO driver for a device that supports blocking calls >> like poll() etc. Now the front end paravirtualized driver mirrors the >> request to the backend "host" qemu process that then does the actual call on >> the host kernel on behalf of the guest. Now my question is, when I do a >> blocking call from within the callback that I have registered when I created >> the virtqueue, does it block the entire vcpu? If it does, do I have to >> create an async context for it? Looking at virtio-net and virtio-block, I >> can see the concept of bottom halves but I am not sure if this helps me in >> any way. > > What device are you adding? It would help to share what you are trying > to accomplish. We are trying to paravirtualize the IPMI device (/dev/ipmi0). > > QEMU has an event loop where you can register non-blocking file > descriptors. Callback functions that are invoked when the file > descriptor becomes readable/writable. This is how block I/O, > networking, VNC UI, monitor, etc work and probably what you should do > too. Hmm, I looked closely at virtio-block driver. It looks like it built on top of posix aio infrastructure (posix-aio-compat.c). I'll probably have to build something similar or use the event loop you suggested. > > You may find these posts I wrote helpful, they explain vcpu threads and > the I/O thread: > http://blog.vmsplice.net/2011/03/qemu-internals-big-picture-overview.html > http://blog.vmsplice.net/2011/03/qemu-internals-overall-architecture-and.html Thanks a lot. I will look into these articles. Cheers, ani The information contained in this message may be privileged and confidential and protected from disclosure. If the reader of this message is not the intended recipient, or an employee or agent responsible for delivering this message to the intended recipient, you are hereby notified that any reproduction, dissemination or distribution of this communication is strictly prohibited. If you have received this communication in error, please notify us immediately by replying to the message and deleting it from your computer. Thank you. Tellabs
Re: [Qemu-devel] unable to access the serial port on the Vm
On Mon, Sep 12, 2011 at 12:35 PM, bala suru wrote: > But I need to connect a some USB device which will create a virtual > serialport called /dev/ttyACM0, I cloud not see this on the Vm running .. > > This XML format I used > RAW = [ type = "kvm", > data = " path=\"/dev/pts/5\"/> tty=\"/dev/pts/5\"> port=\"0\"/>" ] I am not sure what you are trying to do. Are you attaching a USB serial device to the host and you would like to connect that to the VM's serial port? In that case you can try this domain XML: Stefan
[Qemu-devel] [Bug 818673] Re: virtio: trying to map MMIO memory
ping... I understand that Vadim must be very busy that he can't look at this - I can relate. But is there really only one person in all of Qemu and/or Spice who can be addressed to look into this? So that I can plan around the viability of Qemu for my users, I need to know if the technologies I seek will be well maintained. Thanks, -Rick -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/818673 Title: virtio: trying to map MMIO memory Status in QEMU: New Bug description: Qemu host is Core i7, running Linux. Guest is Windows XP sp3. Often, qemu will crash shortly after starting (1-5 minutes) with a statement "qemu-system-x86_64: virtio: trying to map MMIO memory" This has occured with qemu-kvm 0.14, qemu-kvm 0.14.1, qemu-0.15.0-rc0 and qemu 0.15.0-rc1. Qemu is started as such: qemu-system-x86_64 -cpu host -enable-kvm -pidfile /home/rick/qemu/hds/wxp.pid -drive file=/home/rick/qemu/hds/wxp.raw,if=virtio -m 768 -name WinXP -net nic,model=virtio -net user -localtime -usb -vga qxl -device virtio-serial -chardev spicevmc,name=vdagent,id=vdagent -device virtserialport,chardev=vdagent,name=com.redhat.spice.0 -spice port=1234,disable-ticketing -daemonize -monitor telnet:localhost:12341,server,nowait The WXP guest has virtio 1.1.16 drivers for net and scsi, and the most current spice binaries from spice-space.org. To manage notifications about this bug go to: https://bugs.launchpad.net/qemu/+bug/818673/+subscriptions
Re: [Qemu-devel] [Qemu-ppc] [RESEND][PATCH] booke timers
On 09/09/2011 09:58 AM, Alexander Graf wrote: > On 09.09.2011, at 16:22, Fabien Chouteau wrote: >> if the interrupt is already set and you clear TCR.DIE, the interrupt has to >> remain set. The only way to unset an interrupt is to clear the corresponding >> bit in TSR (currently in store_booke_tsr). > > Are you sure? I see several things in the 2.06 spec: [snip] > To me that sounds as if the decrementer interrupt gets injected only > when TSR.DIS=1, TCR.DIE=1 and MSR.EE=1. Unsetting any of these bits > stops the interrupt from being delivered. > > Scott, can you please check up with the hardware guys if this is correct? This is how I've always understood it to work (assuming the interrupt hasn't already been delivered, of course). Fabien, do you have real hardware that you see behave the way you describe? -Scott
Re: [Qemu-devel] [PATCH] tcg/arm: Remove unused tcg_out_addi()
On 12 September 2011 18:04, Stefan Weil wrote: > Am 12.09.2011 12:03, schrieb Peter Maydell: >> Remove the unused function tcg_out_addi() from the ARM TCG backend; >> this fixes a compilation failure on ARM hosts with newer gcc. > Are you sure that those functions will never be needed again? > If yes, your solution is ok. I was not sure - that's the reason > why I had sent a patch using inline. #if 0 ... #endif and > a comment might also be a solution for possible > future usage. Well, if we do need it again we'll have to resurrect the ppc version. I dislike #if 0...#endif code. I think the underlying problem here is that we don't have a well defined API which the tcg backends have to provide to the generic tcg code. So we can't really say whether tcg_out_addi() ought to be part of it or not. (Ideally all the functions provided by the backend ought to have a consistent naming scheme, eg tcg_target_*, but sadly this isn't the case. And the way tcg.c #includes the backend means you can't use presence/absence of 'static' to identify the exposed API either... Does that really gain us much, or should we just build tcg-target.c as a separate translation unit?) I think I would argue that tcg.c ought to do addition via tcg_out_op, since the target has to provide addition via that route anyway. That would be cleaner than requiring backends to implement an extra interface for "emit code to add things together". If you buy this line of reasoning then deleting the current tcg_out_addi() on platforms that don't need it internally anyhow is clearly the Right Thing :-) -- PMM
Re: [Qemu-devel] [Qemu-ppc] [PATCH 7/9] openpic: avoid a warning from clang analyzer
On 09/04/2011 10:52 AM, Blue Swirl wrote: > Avoid this warning by clang analyzer by defining a default case: > /src/qemu/hw/openpic.c:477:5: warning: Undefined or garbage value > returned to caller > return retval; > > Signed-off-by: Blue Swirl > --- > hw/openpic.c |1 + > 1 files changed, 1 insertions(+), 0 deletions(-) > > diff --git a/hw/openpic.c b/hw/openpic.c > index 26c96e2..4b883ac 100644 > --- a/hw/openpic.c > +++ b/hw/openpic.c > @@ -469,6 +469,7 @@ static inline uint32_t read_IRQreg (openpic_t > *opp, int n_IRQ, uint32_t reg) > case IRQ_IPVP: > retval = opp->src[n_IRQ].ipvp; > break; > +default: > case IRQ_IDE: > retval = opp->src[n_IRQ].ide; > break; What's special about IDE? Shouldn't it return 0x as some other functions (e.g. openpic_gbl_read) do with unrecognized registers? Then there's openpic_src_read() which has still different behavior for the same registers. :-P Note that this function is only ever called with a constant in "reg". Since it's a static function and all call sites could have been verified, this could be considered a flaw in clang's analyzer. This workaround will prevent GCC from issuing a warning if a new caller is added that passes a different constant value. The best answer is probably to just get rid of this function and have the caller refer to opp->src[n_irq].whatever directly. write_IRQreg() could be split into something like set_src_ipvp() and set_src_ide(). -Scott
Re: [Qemu-devel] [PATCH] tcg/arm: Remove unused tcg_out_addi()
Am 12.09.2011 12:03, schrieb Peter Maydell: Remove the unused function tcg_out_addi() from the ARM TCG backend; this fixes a compilation failure on ARM hosts with newer gcc. Signed-off-by: Peter Maydell --- A previous patch from Richard Henderson for this compile failure: http://patchwork.ozlabs.org/patch/110400/ was rejected, so here's another go. This simply removes the unused function, in line with the approach taken for ppc/ppc64 in commits 1a2eb162414 and c24a9c6ef94. If this is accepted I can do the equivalent patches for tcg/ia64 and tcg/s390 (although those don't cause compile failures because the unused function happens to be marked 'inline'.) tcg/arm/tcg-target.c | 15 --- 1 files changed, 0 insertions(+), 15 deletions(-) Are you sure that those functions will never be needed again? If yes, your solution is ok. I was not sure - that's the reason why I had sent a patch using inline. #if 0 ... #endif and a comment might also be a solution for possible future usage. Stefan
Re: [Qemu-devel] [PATCH] pci: Remove unused mem_base from PCIBus
On Mon, Sep 12, 2011 at 03:17:53PM +0200, Jan Kiszka wrote: > Obsoleted by f64e02b6cc. > > Signed-off-by: Jan Kiszka thanks, applied > --- > hw/pci_internals.h |1 - > 1 files changed, 0 insertions(+), 1 deletions(-) > > diff --git a/hw/pci_internals.h b/hw/pci_internals.h > index c7fd23d..10b4adf 100644 > --- a/hw/pci_internals.h > +++ b/hw/pci_internals.h > @@ -24,7 +24,6 @@ struct PCIBus { > void *irq_opaque; > PCIDevice *devices[PCI_SLOT_MAX * PCI_FUNC_MAX]; > PCIDevice *parent_dev; > -target_phys_addr_t mem_base; > MemoryRegion *address_space_mem; > MemoryRegion *address_space_io; > > -- > 1.7.3.4
[Qemu-devel] [Bug 814222] Re: kvm cannot use vhd files over 127GB
This bug was fixed in the package qemu-kvm - 0.14.1+noroms-0ubuntu5 --- qemu-kvm (0.14.1+noroms-0ubuntu5) oneiric; urgency=low * debian/patches/vpc.patch: detect vpc files which are too big (LP: #814222) -- Serge HallynMon, 12 Sep 2011 11:28:36 -0500 ** Changed in: qemu-kvm (Ubuntu) Status: Triaged => Fix Released -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/814222 Title: kvm cannot use vhd files over 127GB Status in QEMU: New Status in “qemu-kvm” package in Ubuntu: Fix Released Bug description: The primary use case for using vhds with KVM is to perform a conversion to a raw image file so that one could move from Hyper-V to Linux-KVM. See more on this http://blog.allanglesit.com/2011/03 /linux-kvm-migrating-hyper-v-vhd-images-to-kvm/ # kvm-img convert -f raw -O vpc /root/file.vhd /root/file.img The above works great if you have VHDs smaller than 127GB, however if it is larger, then no error is generated during the conversion process, but it appears to just process up to that 127GB barrier and no more. Also of note. VHDs can also be run directly using KVM if they are smaller than 127GB. VHDs can be read and function well using virtualbox as well as hyper-v, so I suspect the problem lies not with the VHD format (since that has a 2TB limitation). But instead with how qemu-kvm is interpreting them. BORING VERSION INFO: # cat /etc/issue Ubuntu 11.04 \n \l # uname -rmiv 2.6.38-8-server #42-Ubuntu SMP Mon Apr 11 03:49:04 UTC 2011 x86_64 x86_64 # apt-cache policy kvm kvm: Installed: 1:84+dfsg-0ubuntu16+0.14.0+noroms+0ubuntu4.1 Candidate: 1:84+dfsg-0ubuntu16+0.14.0+noroms+0ubuntu4.1 Version table: *** 1:84+dfsg-0ubuntu16+0.14.0+noroms+0ubuntu4.1 0 500 http://apt.sonosite.com/ubuntu/ natty-updates/main amd64 Packages 500 http://apt.sonosite.com/ubuntu/ natty-security/main amd64 Packages 100 /var/lib/dpkg/status 1:84+dfsg-0ubuntu16+0.14.0+noroms+0ubuntu4 0 500 http://apt.sonosite.com/ubuntu/ natty/main amd64 Packages # apt-cache policy libvirt-bin libvirt-bin: Installed: 0.8.8-1ubuntu6.2 Candidate: 0.8.8-1ubuntu6.2 Version table: *** 0.8.8-1ubuntu6.2 0 500 http://apt.sonosite.com/ubuntu/ natty-updates/main amd64 Packages 500 http://apt.sonosite.com/ubuntu/ natty-security/main amd64 Packages 100 /var/lib/dpkg/status 0.8.8-1ubuntu6 0 500 http://apt.sonosite.com/ubuntu/ natty/main amd64 Packages qemu-img version 0.14.0 # vboxmanage -v 4.0.12r72916 REPRODUCTION STEPS (requires Windows 7 or Windows 2008 R2 with < 1GB of free space) ## WINDOWS MACHINE ## Use Computer Management > Disk Management -Create 2 VHD files, both dynamically expanding 120GB and 140GB respectively. -Do not initialize or format. These files will need to be transferred to an Ubuntu KVM machine (pscp is what I used but usb would work as well). ## UBUNTU KVM MACHINE ## # ls *.vhd 120g-dyn.vhd 140g-dyn.vhd # kvm-img info 120g-dyn.vhd image: 120g-dyn.vhd file format: vpc virtual size: 120G (128847052800 bytes) disk size: 244K # kvm-img info 140g-dyn.vhd image: 140g-dyn.vhd file format: vpc virtual size: 127G (13683600 bytes) disk size: 284K # kvm-img info 120g-dyn.vhd | grep "virtual size" virtual size: 120G (128847052800 bytes) # kvm-img info 140g-dyn.vhd | grep "virtual size" virtual size: 127G (13683600 bytes) Regardless of how big the second vhd is I always get a virtual size of 127G Now if we use virtualbox to view the vhds we see markedly different results. # VBoxManage showhdinfo 120g-dyn.vhd UUID: e63681e0-ff12-4114-85de-7d13562b36db Accessible: yes Logical size: 122880 MBytes Current size on disk: 0 MBytes Type: normal (base) Storage format: VHD Format variant: dynamic default Location: /root/120g-dyn.vhd # VBoxManage showhdinfo 140g-dyn.vhd UUID: 94531905-46b4-469f-bb44-7a7d388fb38f Accessible: yes Logical size: 143360 MBytes Current size on disk: 0 MBytes Type: normal (base) Storage format: VHD Format variant: dynamic default Location: /root/140g-dyn.vhd # kvm-img convert -f vpc -O raw 120g-dyn.vhd 120g-dyn.img # # kvm-img convert -f vpc -O raw 140g-dyn.vhd 140g-dyn.img # # kvm-img info 120g-dyn.img image: 120g-dyn.img file format: raw virtual size: 120G (128847052800 bytes) disk size: 0 # kvm-img info 120g-dyn.img | grep "virtual size" virtual size: 120G (128847052800 bytes) # kvm-img info 140g-dyn.img image: 140g-dyn.img file format: raw virtual size: 127G (13683600 bytes) disk size: 0 # kvm-img info 140g-dyn.img |
Re: [Qemu-devel] [PATCH V12 00/15] virtio-9p: chroot environment for passthrough security model
On Tue, Sep 06, 2011 at 03:48:22PM +0100, Stefan Hajnoczi wrote: > On Mon, Sep 05, 2011 at 09:48:21PM +0530, M. Mohan Kumar wrote: > > Qemu need to be invoked by root user for using virtfs with passthrough > > security model (i.e to use chroot() syscall). > > > > Question is: Is running qemu by root user expected and allowed? Some of the > > virtfs features can be utilized only if qemu is started by root user (for > > example passthrough security model and handle based file driver need root > > privilege). > > > > This issue can be resolved by root user starting qemu and spawning a process > > with root privilege to do all privileged operations there and main qemu > > process dropping its privileges to avoid any security issue in running qemu > > in > > root mode. Privileged operations can be done similar to the chroot patchset. > > > > But how to determine to which user-id(ie non root user id) qemu needs to > > drop > > the privileges? Do we have a common user-id across all distributions/systems > > to which qemu process can be dropped down? Also it becomes too complex i.e > > when > > a new feature needing root privilege is added, a process with root privilege > > needs to be created to handle this. > > > > So is it allowed to run qemu by root user? If no, is it okay to add the > > complexity of adding a root privilege process for each feature that needs > > root > > privilege? > > I believe libvirt performs the privilege dropping itself and then > invokes QEMU. So in the context of KVM + libvirt we do not have > privileges in QEMU. Of course the administrator can edit > /etc/libvirt/qemu.conf and configure the user to run QEMU as (i.e. > root). But the intention here is to run QEMU unprivileged. > > QEMU has its own -runas switch which may be used when QEMU is run > directly by a user or by custom scripts. This switch looks up the user > and switches to their uid/gid/groups. > > We need to think carefully before adding privileged features to QEMU > since they usually require extra configuration to safely limit the group > of users who may use the feature. These features will be unavailable to > unprivileged users on a system. I agree, regardless of libvirt's needs, p9fs needs to be secure for any non-root user using QEMU. As non-root I should be able todo $ qemu -virtfs $HOME/shared and have strong confidence that symlink attacks can't be used by the guest to access other locations nuder $HOME. > A virtfs feature that needs root therefore needs to be in a separate > process. Either QEMU needs to fork or virtfs could use a separate > daemon binary. One other idea I just had is 'fakechroot'. This is basically an LD_PRELOAD hack which wraps the C library's native chroot(), open() etc call to do chroot in userspace, thus avoiding a need for root privileges. Either you could just invoke QEMU via fakechroot, enabling your code from these patches to be used as non-root. Or we could take the code from the fakechroot library and use that directly in the p9fs code to apply the path security checks Daniel -- |: http://berrange.com -o-http://www.flickr.com/photos/dberrange/ :| |: http://libvirt.org -o- http://virt-manager.org :| |: http://autobuild.org -o- http://search.cpan.org/~danberr/ :| |: http://entangle-photo.org -o- http://live.gnome.org/gtk-vnc :|
Re: [Qemu-devel] [PATCH v3 5/6] vga: Use linear mapping + dirty logging in chain 4 memory access mode
On 2011-09-12 17:49, Jan Kiszka wrote: > On 2011-09-12 17:45, Andreas Färber wrote: >> Am 12.09.2011 17:33, schrieb Jan Kiszka: >>> On 2011-09-12 17:20, Alexander Graf wrote: Jan Kiszka wrote: > Most VGA memory access modes require MMIO handling as they demand weird > logic to get a byte from or into the video RAM. However, there is one > exception: chain 4 mode with all memory planes enabled for writing. This > mode actually allows lineary mapping, which can then be combined with > dirty logging to accelerate KVM. > > This patch accelerates specifically VBE accesses like they are used by > grub in graphical mode. Not only the standard VGA adapter benefits from > this, also vmware and spice in VGA mode. > > CC: Gerd Hoffmann > CC: Avi Kivity > Signed-off-by: Jan Kiszka > [...] > +static void vga_update_memory_access(VGACommonState *s) > +{ > +MemoryRegion *region, *old_region = s->chain4_alias; > +target_phys_addr_t base, offset, size; > + > +s->chain4_alias = NULL; > + > +if ((s->sr[0x02] & 0xf) == 0xf && s->sr[0x04] & 0x08) { > +offset = 0; > +switch ((s->gr[6] >> 2) & 3) { > +case 0: > +base = 0xa; > +size = 0x2; > +break; > +case 1: > +base = 0xa; > +size = 0x1; > +offset = s->bank_offset; > +break; > +case 2: > +base = 0xb; > +size = 0x8000; > +break; > +case 3: > +base = 0xb8000; > +size = 0x8000; > +break; > +} > +region = g_malloc(sizeof(*region)); > +memory_region_init_alias(region, "vga.chain4", &s->vram, offset, > size); > +memory_region_add_subregion_overlap(s->legacy_address_space, > base, > +region, 2); > This one eventually gives me the following in info mtree with -M g3beige on qemu-system-ppc: (qemu) info mtree memory system addr off size 7fff -vga.chain4 addr 000a off size 1 -macio addr 8088 off size 8 --macio-nvram addr 0006 off size 2 --pmac-ide addr 0002 off size 1000 --cuda addr 00016000 off size 2000 --escc-bar addr 00013000 off size 40 --dbdma addr 8000 off size 1000 --heathrow-pic addr off size 1000 -vga.rom addr 8080 off size 1 -vga.vram addr 8000 off size 80 -vga-lowmem addr 800a off size 2 -escc addr 80013000 off size 40 -isa-mmio addr fe00 off size 20 I/O io addr off size 1 -cmd646-bmdma addr 0700 off size 10 --cmd646-bmdma-ioport addr 000c off size 4 --cmd646-bmdma-bus addr 0008 off size 4 --cmd646-bmdma-ioport addr 0004 off size 4 --cmd646-bmdma-bus addr off size 4 -cmd646-cmd addr 0680 off size 4 -cmd646-data addr 0600 off size 8 -cmd646-cmd addr 0580 off size 4 -cmd646-data addr 0500 off size 8 -ne2000 addr 0400 off size 100 This ends up overmapping 0xa, effectively overwriting kernel data. If I #if 0 the offending chunk out, everything is fine. I would assume that chain4 really needs to be inside of lowmem? No idea about VGA, but I'm sure you know what's going on :). >>> Does this help? >>> >>> diff --git a/hw/vga.c b/hw/vga.c >>> index 125fb29..0a0c5a6 100644 >>> --- a/hw/vga.c >>> +++ b/hw/vga.c >>> @@ -181,6 +181,7 @@ static void vga_update_memory_access(VGACommonState *s) >>> size = 0x8000; >>> break; >>> } >>> +base += isa_mem_base; >>> region = g_malloc(sizeof(*region)); >>> memory_region_init_alias(region, "vga.chain4", &s->vram, offset, >>> size); >>> memory_region_add_subregion_overlap(s->legacy_address_space, base, >> >> No longer oopses, but the screen looks chaotic now (black bar at bottom, >> part of contents at top etc.). > > Does this PPC machine map the ISA range and forward VGA accesses to the > adapter in general? If it does, please post a dump of the VGACommonState while the screen is corrupted (gdb or via device_show [1]. Maybe I missed some condition that prevents chain4 optimizations, and your guest triggers this. Jan [1] http://thread.gmane.org/gmane.comp.emulators.qemu/114853 -- Siemens AG, Corporate Technology, CT T DE IT 1 Corporate Competence Center Embedded Linux
Re: [Qemu-devel] [PATCH V12 00/15] virtio-9p: chroot environment for passthrough security model
On Tuesday, September 06, 2011 08:18:22 PM Stefan Hajnoczi wrote: > A virtfs feature that needs root therefore needs to be in a separate > process. Either QEMU needs to fork or virtfs could use a separate > daemon binary. > > You have already implemented the fork approach in the chroot patches. > Handle-based open could work in the same way. > > To summarize this architecture: all path-related operations are > performed by a separate privileged process. File descriptors are passed > to QEMU over a UNIX domain socket. This way QEMU can do the actual > read(2)/write(2) calls directly to/from guest memory. > > I think it would be nice to build a completely separate binary that QEMU > connects to. The separate binary would have a much smaller footprint > (doesn't include QEMU code). More importantly the > privileged/unprivileged boundary would be simple and could be > automatically set up by libvirt: > Hi Stefan, Thanks for your inputs. Sorry for the delayed reply. > $ sudo namespace_helper --sock /var/run/virtfs/1234.sock --export my_dir/ > $ qemu -fsdev local,id=my_fs,namespace_helper=/var/run/virtfs/1234.sock \ >-device virtio-9p-pci,fsdev=my_fs We already isolated all path related operations in a privileged process. Should we add this complexity? If we take this approach, for handle based filesystem driver, we need to ship another binary. Won't it be an usability issue for people who use qemu directly?
Re: [Qemu-devel] [PATCH v3 5/6] vga: Use linear mapping + dirty logging in chain 4 memory access mode
On 2011-09-12 17:45, Andreas Färber wrote: > Am 12.09.2011 17:33, schrieb Jan Kiszka: >> On 2011-09-12 17:20, Alexander Graf wrote: >>> Jan Kiszka wrote: Most VGA memory access modes require MMIO handling as they demand weird logic to get a byte from or into the video RAM. However, there is one exception: chain 4 mode with all memory planes enabled for writing. This mode actually allows lineary mapping, which can then be combined with dirty logging to accelerate KVM. This patch accelerates specifically VBE accesses like they are used by grub in graphical mode. Not only the standard VGA adapter benefits from this, also vmware and spice in VGA mode. CC: Gerd Hoffmann CC: Avi Kivity Signed-off-by: Jan Kiszka >>> [...] >>> +static void vga_update_memory_access(VGACommonState *s) +{ +MemoryRegion *region, *old_region = s->chain4_alias; +target_phys_addr_t base, offset, size; + +s->chain4_alias = NULL; + +if ((s->sr[0x02] & 0xf) == 0xf && s->sr[0x04] & 0x08) { +offset = 0; +switch ((s->gr[6] >> 2) & 3) { +case 0: +base = 0xa; +size = 0x2; +break; +case 1: +base = 0xa; +size = 0x1; +offset = s->bank_offset; +break; +case 2: +base = 0xb; +size = 0x8000; +break; +case 3: +base = 0xb8000; +size = 0x8000; +break; +} +region = g_malloc(sizeof(*region)); +memory_region_init_alias(region, "vga.chain4", &s->vram, offset, size); +memory_region_add_subregion_overlap(s->legacy_address_space, base, +region, 2); >>> This one eventually gives me the following in info mtree with -M g3beige >>> on qemu-system-ppc: >>> >>> (qemu) info mtree >>> memory >>> system addr off size 7fff >>> -vga.chain4 addr 000a off size 1 >>> -macio addr 8088 off size 8 >>> --macio-nvram addr 0006 off size 2 >>> --pmac-ide addr 0002 off size 1000 >>> --cuda addr 00016000 off size 2000 >>> --escc-bar addr 00013000 off size 40 >>> --dbdma addr 8000 off size 1000 >>> --heathrow-pic addr off size 1000 >>> -vga.rom addr 8080 off size 1 >>> -vga.vram addr 8000 off size 80 >>> -vga-lowmem addr 800a off size 2 >>> -escc addr 80013000 off size 40 >>> -isa-mmio addr fe00 off size 20 >>> I/O >>> io addr off size 1 >>> -cmd646-bmdma addr 0700 off size 10 >>> --cmd646-bmdma-ioport addr 000c off size 4 >>> --cmd646-bmdma-bus addr 0008 off size 4 >>> --cmd646-bmdma-ioport addr 0004 off size 4 >>> --cmd646-bmdma-bus addr off size 4 >>> -cmd646-cmd addr 0680 off size 4 >>> -cmd646-data addr 0600 off size 8 >>> -cmd646-cmd addr 0580 off size 4 >>> -cmd646-data addr 0500 off size 8 >>> -ne2000 addr 0400 off size 100 >>> >>> This ends up overmapping 0xa, effectively overwriting kernel data. >>> If I #if 0 the offending chunk out, everything is fine. I would assume >>> that chain4 really needs to be inside of lowmem? No idea about VGA, but >>> I'm sure you know what's going on :). >> Does this help? >> >> diff --git a/hw/vga.c b/hw/vga.c >> index 125fb29..0a0c5a6 100644 >> --- a/hw/vga.c >> +++ b/hw/vga.c >> @@ -181,6 +181,7 @@ static void vga_update_memory_access(VGACommonState *s) >> size = 0x8000; >> break; >> } >> +base += isa_mem_base; >> region = g_malloc(sizeof(*region)); >> memory_region_init_alias(region, "vga.chain4", &s->vram, offset, >> size); >> memory_region_add_subregion_overlap(s->legacy_address_space, base, > > No longer oopses, but the screen looks chaotic now (black bar at bottom, > part of contents at top etc.). Does this PPC machine map the ISA range and forward VGA accesses to the adapter in general? Jan -- Siemens AG, Corporate Technology, CT T DE IT 1 Corporate Competence Center Embedded Linux
[Qemu-devel] [PATCH 22/35] block: Clean up remaining users of "removable"
From: Markus Armbruster BlockDriverState member removable is a confused mess. It is true when an ide-cd, scsi-cd or floppy qdev is attached, or when the BlockDriverState was created with -drive if={floppy,sd} or -drive if={ide,scsi,xen,none},media=cdrom ("created removable"), except when an ide-hd, scsi-hd, scsi-generic or virtio-blk qdev is attached. Three users remain: 1. eject_device(), via bdrv_is_removable() uses it to determine whether a block device can eject media. 2. bdrv_info() is monitor command "info block". QMP documentation says "true if the device is removable, false otherwise". From the monitor user's point of view, the only sensible interpretation of "is removable" is "can eject media with monitor commands eject and change". A block device can eject media unless a device is attached that doesn't support it. Switch the two users over to new bdrv_dev_has_removable_media() that returns exactly that. 3. bdrv_getlength() uses to suppress its length cache when media can change (see commit 46a4e4e6). Media change is either monitor command change (updates the length cache), monitor command eject (doesn't update the length cache, easily fixable), or physical media change (invalidates length cache, not so easily fixable). I'm refraining from improving anything here, because this series is long enough already. Instead, I simply switch it over to bdrv_dev_has_removable_media() as well. This changes the behavior of the length cache and of monitor commands eject and change in two cases: a. drive not created removable, no device attached The commit makes the drive removable, and defeats the length cache. Example: -drive if=none b. drive created removable, but the attached drive is non-removable, and doesn't call bdrv_set_removable(..., 0) (most devices don't) The commit makes the drive non-removable, and enables the length cache. Example: -drive if=xen,media=cdrom -M xenpv The other non-removable devices that don't call bdrv_set_removable() can't currently use a drive created removable, either because they aren't qdevified, or because they lack a drive property. Won't stay that way. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block.c| 18 +++--- block.h|3 ++- blockdev.c |2 +- hw/scsi-disk.c |5 + 4 files changed, 19 insertions(+), 9 deletions(-) diff --git a/block.c b/block.c index 7225b15..fee45bf 100644 --- a/block.c +++ b/block.c @@ -802,6 +802,9 @@ void bdrv_set_dev_ops(BlockDriverState *bs, const BlockDevOps *ops, { bs->dev_ops = ops; bs->dev_opaque = opaque; +if (bdrv_dev_has_removable_media(bs) && bs == bs_snapshots) { +bs_snapshots = NULL; +} } static void bdrv_dev_change_media_cb(BlockDriverState *bs) @@ -811,6 +814,11 @@ static void bdrv_dev_change_media_cb(BlockDriverState *bs) } } +bool bdrv_dev_has_removable_media(BlockDriverState *bs) +{ +return !bs->dev || (bs->dev_ops && bs->dev_ops->change_media_cb); +} + static void bdrv_dev_resize_cb(BlockDriverState *bs) { if (bs->dev_ops && bs->dev_ops->resize_cb) { @@ -1329,7 +1337,7 @@ int64_t bdrv_getlength(BlockDriverState *bs) if (!drv) return -ENOMEDIUM; -if (bs->growable || bs->removable) { +if (bs->growable || bdrv_dev_has_removable_media(bs)) { if (drv->bdrv_getlength) { return drv->bdrv_getlength(bs); } @@ -1614,11 +1622,6 @@ void bdrv_set_removable(BlockDriverState *bs, int removable) } } -int bdrv_is_removable(BlockDriverState *bs) -{ -return bs->removable; -} - int bdrv_is_read_only(BlockDriverState *bs) { return bs->read_only; @@ -1897,7 +1900,8 @@ void bdrv_info(Monitor *mon, QObject **ret_data) bs_obj = qobject_from_jsonf("{ 'device': %s, 'type': 'unknown', " "'removable': %i, 'locked': %i }", -bs->device_name, bs->removable, +bs->device_name, +bdrv_dev_has_removable_media(bs), bdrv_dev_is_medium_locked(bs)); if (bs->drv) { diff --git a/block.h b/block.h index 4691090..860e30d 100644 --- a/block.h +++ b/block.h @@ -34,6 +34,7 @@ typedef struct BlockDevOps { * Runs when virtual media changed (monitor commands eject, change) * Beware: doesn't run when a host device's physical media * changes. Sure would be useful if it did. + * Device models with removable media must implement this callback. */ void (*change_media_cb)(void *opaque); /* @@ -99,6 +100,7 @@ void bdrv_detach_dev(BlockDriverState *bs, void *dev); void *bdrv_get_attached_dev(BlockDriverState *bs); void bdrv_set_dev_ops(BlockDriverState *bs, const BlockDevOps *ops, void *opaque); +bool bdrv_dev_has_removable_media(BlockDriverState *bs);
[Qemu-devel] [PATCH 24/35] block: Show whether the virtual tray is open in info block
From: Markus Armbruster Need to ask the device, so this requires new BlockDevOps member is_tray_open(). Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block.c | 18 -- block.h |6 ++ hw/ide/core.c |6 ++ hw/scsi-disk.c |6 ++ qmp-commands.hx |2 ++ 5 files changed, 36 insertions(+), 2 deletions(-) diff --git a/block.c b/block.c index d8193a3..febfd67 100644 --- a/block.c +++ b/block.c @@ -819,6 +819,14 @@ bool bdrv_dev_has_removable_media(BlockDriverState *bs) return !bs->dev || (bs->dev_ops && bs->dev_ops->change_media_cb); } +bool bdrv_dev_is_tray_open(BlockDriverState *bs) +{ +if (bs->dev_ops && bs->dev_ops->is_tray_open) { +return bs->dev_ops->is_tray_open(bs->dev_opaque); +} +return false; +} + static void bdrv_dev_resize_cb(BlockDriverState *bs) { if (bs->dev_ops && bs->dev_ops->resize_cb) { @@ -1853,8 +1861,9 @@ static void bdrv_print_dict(QObject *obj, void *opaque) if (qdict_get_bool(bs_dict, "removable")) { monitor_printf(mon, " locked=%d", qdict_get_bool(bs_dict, "locked")); +monitor_printf(mon, " tray-open=%d", + qdict_get_bool(bs_dict, "tray-open")); } - if (qdict_haskey(bs_dict, "inserted")) { QDict *qdict = qobject_to_qdict(qdict_get(bs_dict, "inserted")); @@ -1889,16 +1898,21 @@ void bdrv_info(Monitor *mon, QObject **ret_data) QTAILQ_FOREACH(bs, &bdrv_states, list) { QObject *bs_obj; +QDict *bs_dict; bs_obj = qobject_from_jsonf("{ 'device': %s, 'type': 'unknown', " "'removable': %i, 'locked': %i }", bs->device_name, bdrv_dev_has_removable_media(bs), bdrv_dev_is_medium_locked(bs)); +bs_dict = qobject_to_qdict(bs_obj); +if (bdrv_dev_has_removable_media(bs)) { +qdict_put(bs_dict, "tray-open", + qbool_from_int(bdrv_dev_is_tray_open(bs))); +} if (bs->drv) { QObject *obj; -QDict *bs_dict = qobject_to_qdict(bs_obj); obj = qobject_from_jsonf("{ 'file': %s, 'ro': %i, 'drv': %s, " "'encrypted': %i }", diff --git a/block.h b/block.h index e4b5530..9f6d02c 100644 --- a/block.h +++ b/block.h @@ -38,6 +38,11 @@ typedef struct BlockDevOps { */ void (*change_media_cb)(void *opaque); /* + * Is the virtual tray open? + * Device models implement this only when the device has a tray. + */ +bool (*is_tray_open)(void *opaque); +/* * Is the virtual medium locked into the device? * Device models implement this only when device has such a lock. */ @@ -101,6 +106,7 @@ void *bdrv_get_attached_dev(BlockDriverState *bs); void bdrv_set_dev_ops(BlockDriverState *bs, const BlockDevOps *ops, void *opaque); bool bdrv_dev_has_removable_media(BlockDriverState *bs); +bool bdrv_dev_is_tray_open(BlockDriverState *bs); bool bdrv_dev_is_medium_locked(BlockDriverState *bs); int bdrv_read(BlockDriverState *bs, int64_t sector_num, uint8_t *buf, int nb_sectors); diff --git a/hw/ide/core.c b/hw/ide/core.c index 716addc..8f719ee 100644 --- a/hw/ide/core.c +++ b/hw/ide/core.c @@ -1795,6 +1795,11 @@ void ide_bus_reset(IDEBus *bus) bus->dma->ops->reset(bus->dma); } +static bool ide_cd_is_tray_open(void *opaque) +{ +return ((IDEState *)opaque)->tray_open; +} + static bool ide_cd_is_medium_locked(void *opaque) { return ((IDEState *)opaque)->tray_locked; @@ -1802,6 +1807,7 @@ static bool ide_cd_is_medium_locked(void *opaque) static const BlockDevOps ide_cd_block_ops = { .change_media_cb = ide_cd_change_cb, +.is_tray_open = ide_cd_is_tray_open, .is_medium_locked = ide_cd_is_medium_locked, }; diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index 0f0cddc..f48ca8b 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -1176,6 +1176,11 @@ static void scsi_cd_change_media_cb(void *opaque) { } +static bool scsi_cd_is_tray_open(void *opaque) +{ +return ((SCSIDiskState *)opaque)->tray_open; +} + static bool scsi_cd_is_medium_locked(void *opaque) { return ((SCSIDiskState *)opaque)->tray_locked; @@ -1183,6 +1188,7 @@ static bool scsi_cd_is_medium_locked(void *opaque) static const BlockDevOps scsi_cd_block_ops = { .change_media_cb = scsi_cd_change_media_cb, +.is_tray_open = scsi_cd_is_tray_open, .is_medium_locked = scsi_cd_is_medium_locked, }; diff --git a/qmp-commands.hx b/qmp-commands.hx index 27cc66e..d1c2c59 100644 --- a/qmp-commands.hx +++ b/qmp-commands.hx @@ -1131,6 +1131,8 @@ Each json-object contain the following: - Possible values: "unknown" - "removable": true if the device is removable, false otherwise (json-bool) - "locked": true if the device is locked, false
Re: [Qemu-devel] [PATCH v3 5/6] vga: Use linear mapping + dirty logging in chain 4 memory access mode
Am 12.09.2011 17:33, schrieb Jan Kiszka: > On 2011-09-12 17:20, Alexander Graf wrote: >> Jan Kiszka wrote: >>> Most VGA memory access modes require MMIO handling as they demand weird >>> logic to get a byte from or into the video RAM. However, there is one >>> exception: chain 4 mode with all memory planes enabled for writing. This >>> mode actually allows lineary mapping, which can then be combined with >>> dirty logging to accelerate KVM. >>> >>> This patch accelerates specifically VBE accesses like they are used by >>> grub in graphical mode. Not only the standard VGA adapter benefits from >>> this, also vmware and spice in VGA mode. >>> >>> CC: Gerd Hoffmann >>> CC: Avi Kivity >>> Signed-off-by: Jan Kiszka >>> >> [...] >> >>> +static void vga_update_memory_access(VGACommonState *s) >>> +{ >>> +MemoryRegion *region, *old_region = s->chain4_alias; >>> +target_phys_addr_t base, offset, size; >>> + >>> +s->chain4_alias = NULL; >>> + >>> +if ((s->sr[0x02] & 0xf) == 0xf && s->sr[0x04] & 0x08) { >>> +offset = 0; >>> +switch ((s->gr[6] >> 2) & 3) { >>> +case 0: >>> +base = 0xa; >>> +size = 0x2; >>> +break; >>> +case 1: >>> +base = 0xa; >>> +size = 0x1; >>> +offset = s->bank_offset; >>> +break; >>> +case 2: >>> +base = 0xb; >>> +size = 0x8000; >>> +break; >>> +case 3: >>> +base = 0xb8000; >>> +size = 0x8000; >>> +break; >>> +} >>> +region = g_malloc(sizeof(*region)); >>> +memory_region_init_alias(region, "vga.chain4", &s->vram, offset, >>> size); >>> +memory_region_add_subregion_overlap(s->legacy_address_space, base, >>> +region, 2); >>> >> This one eventually gives me the following in info mtree with -M g3beige >> on qemu-system-ppc: >> >> (qemu) info mtree >> memory >> system addr off size 7fff >> -vga.chain4 addr 000a off size 1 >> -macio addr 8088 off size 8 >> --macio-nvram addr 0006 off size 2 >> --pmac-ide addr 0002 off size 1000 >> --cuda addr 00016000 off size 2000 >> --escc-bar addr 00013000 off size 40 >> --dbdma addr 8000 off size 1000 >> --heathrow-pic addr off size 1000 >> -vga.rom addr 8080 off size 1 >> -vga.vram addr 8000 off size 80 >> -vga-lowmem addr 800a off size 2 >> -escc addr 80013000 off size 40 >> -isa-mmio addr fe00 off size 20 >> I/O >> io addr off size 1 >> -cmd646-bmdma addr 0700 off size 10 >> --cmd646-bmdma-ioport addr 000c off size 4 >> --cmd646-bmdma-bus addr 0008 off size 4 >> --cmd646-bmdma-ioport addr 0004 off size 4 >> --cmd646-bmdma-bus addr off size 4 >> -cmd646-cmd addr 0680 off size 4 >> -cmd646-data addr 0600 off size 8 >> -cmd646-cmd addr 0580 off size 4 >> -cmd646-data addr 0500 off size 8 >> -ne2000 addr 0400 off size 100 >> >> This ends up overmapping 0xa, effectively overwriting kernel data. >> If I #if 0 the offending chunk out, everything is fine. I would assume >> that chain4 really needs to be inside of lowmem? No idea about VGA, but >> I'm sure you know what's going on :). > Does this help? > > diff --git a/hw/vga.c b/hw/vga.c > index 125fb29..0a0c5a6 100644 > --- a/hw/vga.c > +++ b/hw/vga.c > @@ -181,6 +181,7 @@ static void vga_update_memory_access(VGACommonState *s) > size = 0x8000; > break; > } > +base += isa_mem_base; > region = g_malloc(sizeof(*region)); > memory_region_init_alias(region, "vga.chain4", &s->vram, offset, > size); > memory_region_add_subregion_overlap(s->legacy_address_space, base, No longer oopses, but the screen looks chaotic now (black bar at bottom, part of contents at top etc.). Andreas
[Qemu-devel] [PATCH 01/35] qcow2: removed unused depends_on field
From: Frediano Ziglio Signed-off-by: Frediano Ziglio Signed-off-by: Kevin Wolf --- block/qcow2-cluster.c |3 +-- block/qcow2.h |1 - 2 files changed, 1 insertions(+), 3 deletions(-) diff --git a/block/qcow2-cluster.c b/block/qcow2-cluster.c index e06be64..113db8b 100644 --- a/block/qcow2-cluster.c +++ b/block/qcow2-cluster.c @@ -694,7 +694,7 @@ err: * If the offset is not found, allocate a new cluster. * * If the cluster was already allocated, m->nb_clusters is set to 0, - * m->depends_on is set to NULL and the other fields in m are meaningless. + * other fields in m are meaningless. * * If the cluster is newly allocated, m->nb_clusters is set to the number of * contiguous clusters that have been allocated. In this case, the other @@ -736,7 +736,6 @@ again: cluster_offset &= ~QCOW_OFLAG_COPIED; m->nb_clusters = 0; -m->depends_on = NULL; goto out; } diff --git a/block/qcow2.h b/block/qcow2.h index c8ca3bc..531af39 100644 --- a/block/qcow2.h +++ b/block/qcow2.h @@ -148,7 +148,6 @@ typedef struct QCowL2Meta int n_start; int nb_available; int nb_clusters; -struct QCowL2Meta *depends_on; CoQueue dependent_requests; QLIST_ENTRY(QCowL2Meta) next_in_flight; -- 1.7.6
[Qemu-devel] [PATCH 27/35] block: New bdrv_set_buffer_alignment()
From: Markus Armbruster Device models should be able to set it without an unclean include of block_int.h. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block.c |6 -- block.h |1 + hw/ide/core.c |2 +- hw/scsi-disk.c |2 +- hw/virtio-blk.c |3 +-- 5 files changed, 8 insertions(+), 6 deletions(-) diff --git a/block.c b/block.c index febfd67..e986986 100644 --- a/block.c +++ b/block.c @@ -480,7 +480,6 @@ static int bdrv_open_common(BlockDriverState *bs, const char *filename, bs->encrypted = 0; bs->valid_key = 0; bs->open_flags = flags; -/* buffer_alignment defaulted to 512, drivers can change this value */ bs->buffer_alignment = 512; pstrcpy(bs->filename, sizeof(bs->filename), filename); @@ -3115,7 +3114,10 @@ BlockDriverAIOCB *bdrv_aio_ioctl(BlockDriverState *bs, return NULL; } - +void bdrv_set_buffer_alignment(BlockDriverState *bs, int align) +{ +bs->buffer_alignment = align; +} void *qemu_blockalign(BlockDriverState *bs, size_t size) { diff --git a/block.h b/block.h index 6e0c468..4b7fa35 100644 --- a/block.h +++ b/block.h @@ -269,6 +269,7 @@ int bdrv_img_create(const char *filename, const char *fmt, const char *base_filename, const char *base_fmt, char *options, uint64_t img_size, int flags); +void bdrv_set_buffer_alignment(BlockDriverState *bs, int align); void *qemu_blockalign(BlockDriverState *bs, size_t size); #define BDRV_SECTORS_PER_DIRTY_CHUNK 2048 diff --git a/hw/ide/core.c b/hw/ide/core.c index 740ffe0..3771acb 100644 --- a/hw/ide/core.c +++ b/hw/ide/core.c @@ -1847,7 +1847,7 @@ int ide_init_drive(IDEState *s, BlockDriverState *bs, IDEDriveKind kind, s->smart_selftest_count = 0; if (kind == IDE_CD) { bdrv_set_dev_ops(bs, &ide_cd_block_ops, s); -bs->buffer_alignment = 2048; +bdrv_set_buffer_alignment(bs, 2048); } else { if (!bdrv_is_inserted(s->bs)) { error_report("Device needs media, but drive is empty"); diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index d44b3b8..b115760 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -1236,7 +1236,7 @@ static int scsi_initfn(SCSIDevice *dev, uint8_t scsi_type) return -1; } s->cluster_size = s->qdev.blocksize / 512; -s->bs->buffer_alignment = s->qdev.blocksize; +bdrv_set_buffer_alignment(s->bs, s->qdev.blocksize); s->qdev.type = scsi_type; qemu_add_vm_change_state_handler(scsi_dma_restart_cb, s); diff --git a/hw/virtio-blk.c b/hw/virtio-blk.c index 7bf684e..c2ee000 100644 --- a/hw/virtio-blk.c +++ b/hw/virtio-blk.c @@ -15,7 +15,6 @@ #include "qemu-error.h" #include "trace.h" #include "blockdev.h" -#include "block_int.h" #include "virtio-blk.h" #ifdef __linux__ # include @@ -601,7 +600,7 @@ VirtIODevice *virtio_blk_init(DeviceState *dev, BlockConf *conf, register_savevm(dev, "virtio-blk", virtio_blk_id++, 2, virtio_blk_save, virtio_blk_load, s); bdrv_set_dev_ops(s->bs, &virtio_block_ops, s); -s->bs->buffer_alignment = conf->logical_block_size; +bdrv_set_buffer_alignment(s->bs, conf->logical_block_size); add_boot_device_path(conf->bootindex, dev, "/disk@0,0"); -- 1.7.6
[Qemu-devel] [PATCH 1/1] qemu-img: async write to block device when converting image
In order to improve image conversion process, instead of synchronously writing the destingation image, we keep a window of async writes. Signed-off-by: Yehuda Sadeh --- qemu-img.c | 47 +++ 1 files changed, 43 insertions(+), 4 deletions(-) diff --git a/qemu-img.c b/qemu-img.c index 6a39731..a45f5f2 100644 --- a/qemu-img.c +++ b/qemu-img.c @@ -646,6 +646,29 @@ static int compare_sectors(const uint8_t *buf1, const uint8_t *buf2, int n, } #define IO_BUF_SIZE (2 * 1024 * 1024) +#define IO_WRITE_WINDOW_THRESHOLD (32 * 1024 * 1024) + +static int write_window = 0; +static int write_ret = 0; + +struct write_info { +int64_t sector; +QEMUIOVector qiov; +}; + +static void img_write_cb(void *opaque, int ret) +{ +struct write_info *wr = (struct write_info *)opaque; +QEMUIOVector *qiov = &wr->qiov; +if (ret < 0) { +error_report("error while writing sector %" PRId64 + ": %s", wr->sector, strerror(-ret)); +write_ret = ret; +} +write_window -= qiov->iov->iov_len / 512; +qemu_iovec_destroy(qiov); +g_free(wr); +} static int img_convert(int argc, char **argv) { @@ -1019,6 +1042,9 @@ static int img_convert(int argc, char **argv) should add a specific call to have the info to go faster */ buf1 = buf; while (n > 0) { +while (write_window > IO_WRITE_WINDOW_THRESHOLD / 512) { +qemu_aio_wait(); +} /* If the output image is being created as a copy on write image, copy all sectors even the ones containing only NUL bytes, because they may differ from the sectors in the base image. @@ -1028,12 +1054,21 @@ static int img_convert(int argc, char **argv) already there is garbage, not 0s. */ if (!has_zero_init || out_baseimg || is_allocated_sectors_min(buf1, n, &n1, min_sparse)) { -ret = bdrv_write(out_bs, sector_num, buf1, n1); -if (ret < 0) { -error_report("error while writing sector %" PRId64 - ": %s", sector_num, strerror(-ret)); +QEMUIOVector *qiov; +struct write_info *wr; +BlockDriverAIOCB *acb; +wr = g_malloc0(sizeof(struct write_info)); +qiov = &wr->qiov; +qemu_iovec_init(qiov, 1); +qemu_iovec_add(qiov, (void *)buf1, n1 * 512); +wr->sector = sector_num; +acb = bdrv_aio_writev(out_bs, sector_num, qiov, n1, img_write_cb, wr); +if (!acb) { +g_free(wr); +error_report("I/O error while writing sector %" PRId64, sector_num); goto out; } +write_window += n1; } sector_num += n1; n -= n1; @@ -1041,6 +1076,9 @@ static int img_convert(int argc, char **argv) } qemu_progress_print(local_progress, 100); } +while (write_window > 0) { +qemu_aio_wait(); +} } out: qemu_progress_end(); @@ -1048,6 +1086,7 @@ out: free_option_parameters(param); qemu_vfree(buf); if (out_bs) { +bdrv_flush(out_bs); bdrv_delete(out_bs); } if (bs) { -- 1.7.5.1
[Qemu-devel] [PATCH 05/35] ide/atapi: Clean up misleading name in cmd_start_stop_unit()
From: Markus Armbruster "eject" is misleading; it means "eject" when start is clear, but "load" when start is set. Rename to loej, because that's how MMC-5 calls it, in section 6.40. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/ide/atapi.c |8 1 files changed, 4 insertions(+), 4 deletions(-) diff --git a/hw/ide/atapi.c b/hw/ide/atapi.c index f38d289..cb0cdac 100644 --- a/hw/ide/atapi.c +++ b/hw/ide/atapi.c @@ -903,11 +903,11 @@ static void cmd_seek(IDEState *s, uint8_t* buf) static void cmd_start_stop_unit(IDEState *s, uint8_t* buf) { -int start, eject, sense, err = 0; -start = buf[4] & 1; -eject = (buf[4] >> 1) & 1; +int sense, err = 0; +bool start = buf[4] & 1; +bool loej = buf[4] & 2; /* load on start, eject on !start */ -if (eject) { +if (loej) { err = bdrv_eject(s->bs, !start); } -- 1.7.6
[Qemu-devel] [PATCH 29/35] nbd: Clean up use of block_int.h
From: Markus Armbruster Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block/nbd.c |1 + nbd.c |1 + nbd.h |2 -- 3 files changed, 2 insertions(+), 2 deletions(-) diff --git a/block/nbd.c b/block/nbd.c index 55cb2fd..70edd81 100644 --- a/block/nbd.c +++ b/block/nbd.c @@ -28,6 +28,7 @@ #include "qemu-common.h" #include "nbd.h" +#include "block_int.h" #include "module.h" #include "qemu_socket.h" diff --git a/nbd.c b/nbd.c index e7a585d..6d81cfb 100644 --- a/nbd.c +++ b/nbd.c @@ -17,6 +17,7 @@ */ #include "nbd.h" +#include "block.h" #include #include diff --git a/nbd.h b/nbd.h index 273cfa1..df7b7af 100644 --- a/nbd.h +++ b/nbd.h @@ -23,8 +23,6 @@ #include "qemu-common.h" -#include "block_int.h" - struct nbd_request { uint32_t magic; uint32_t type; -- 1.7.6
[Qemu-devel] [PATCH 18/35] rbd: fix leak in qemu_rbd_open failure paths
From: Sage Weil Fix leak of s->snap in failure path. Simplify error paths for the whole function. Reported-by: Stefan Hajnoczi Signed-off-by: Sage Weil Reviewed-by: Stefan Hajnoczi Signed-off-by: Kevin Wolf --- block/rbd.c | 28 +--- 1 files changed, 13 insertions(+), 15 deletions(-) diff --git a/block/rbd.c b/block/rbd.c index 2763092..1b78d51 100644 --- a/block/rbd.c +++ b/block/rbd.c @@ -427,10 +427,6 @@ static int qemu_rbd_open(BlockDriverState *bs, const char *filename, int flags) conf, sizeof(conf)) < 0) { return -EINVAL; } -s->snap = NULL; -if (snap_buf[0] != '\0') { -s->snap = g_strdup(snap_buf); -} clientname = qemu_rbd_parse_clientname(conf, clientname_buf); r = rados_create(&s->cluster, clientname); @@ -439,12 +435,16 @@ static int qemu_rbd_open(BlockDriverState *bs, const char *filename, int flags) return r; } +s->snap = NULL; +if (snap_buf[0] != '\0') { +s->snap = g_strdup(snap_buf); +} + if (strstr(conf, "conf=") == NULL) { r = rados_conf_read_file(s->cluster, NULL); if (r < 0) { error_report("error reading config file"); -rados_shutdown(s->cluster); -return r; +goto failed_shutdown; } } @@ -452,31 +452,26 @@ static int qemu_rbd_open(BlockDriverState *bs, const char *filename, int flags) r = qemu_rbd_set_conf(s->cluster, conf); if (r < 0) { error_report("error setting config options"); -rados_shutdown(s->cluster); -return r; +goto failed_shutdown; } } r = rados_connect(s->cluster); if (r < 0) { error_report("error connecting"); -rados_shutdown(s->cluster); -return r; +goto failed_shutdown; } r = rados_ioctx_create(s->cluster, pool, &s->io_ctx); if (r < 0) { error_report("error opening pool %s", pool); -rados_shutdown(s->cluster); -return r; +goto failed_shutdown; } r = rbd_open(s->io_ctx, s->name, &s->image, s->snap); if (r < 0) { error_report("error reading header from %s", s->name); -rados_ioctx_destroy(s->io_ctx); -rados_shutdown(s->cluster); -return r; +goto failed_open; } bs->read_only = (s->snap != NULL); @@ -497,8 +492,11 @@ static int qemu_rbd_open(BlockDriverState *bs, const char *filename, int flags) failed: rbd_close(s->image); +failed_open: rados_ioctx_destroy(s->io_ctx); +failed_shutdown: rados_shutdown(s->cluster); +g_free(s->snap); return r; } -- 1.7.6
[Qemu-devel] [PATCH 03/35] ide: Use a table to declare which drive kinds accept each command
From: Markus Armbruster No functional change. It would be nice to have handler functions in the table, like commit e1a064f9 did for ATAPI. Left for another day. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/ide/core.c | 105 +++- 1 files changed, 80 insertions(+), 25 deletions(-) diff --git a/hw/ide/core.c b/hw/ide/core.c index def0126..4a45b3e 100644 --- a/hw/ide/core.c +++ b/hw/ide/core.c @@ -901,6 +901,78 @@ void ide_ioport_write(void *opaque, uint32_t addr, uint32_t val) } } +#define HD_OK (1u << IDE_HD) +#define CD_OK (1u << IDE_CD) +#define CFA_OK (1u << IDE_CFATA) +#define HD_CFA_OK (HD_OK | CFA_OK) +#define ALL_OK (HD_OK | CD_OK | CFA_OK) + +/* See ACS-2 T13/2015-D Table B.2 Command codes */ +static const uint8_t ide_cmd_table[0x100] = { +/* NOP not implemented, mandatory for CD */ +[CFA_REQ_EXT_ERROR_CODE]= CFA_OK, +[WIN_DSM] = ALL_OK, +[WIN_DEVICE_RESET] = CD_OK, +[WIN_RECAL] = ALL_OK, +[WIN_READ] = ALL_OK, +[WIN_READ_ONCE] = ALL_OK, +[WIN_READ_EXT] = ALL_OK, +[WIN_READDMA_EXT] = ALL_OK, +[WIN_READ_NATIVE_MAX_EXT] = ALL_OK, +[WIN_MULTREAD_EXT] = ALL_OK, +[WIN_WRITE] = ALL_OK, +[WIN_WRITE_ONCE]= ALL_OK, +[WIN_WRITE_EXT] = ALL_OK, +[WIN_WRITEDMA_EXT] = ALL_OK, +[CFA_WRITE_SECT_WO_ERASE] = ALL_OK, +[WIN_MULTWRITE_EXT] = ALL_OK, +[WIN_WRITE_VERIFY] = ALL_OK, +[WIN_VERIFY]= ALL_OK, +[WIN_VERIFY_ONCE] = ALL_OK, +[WIN_VERIFY_EXT]= ALL_OK, +[WIN_SEEK] = HD_CFA_OK, +[CFA_TRANSLATE_SECTOR] = CFA_OK, +[WIN_DIAGNOSE] = ALL_OK, +[WIN_SPECIFY] = ALL_OK, +[WIN_STANDBYNOW2] = ALL_OK, +[WIN_IDLEIMMEDIATE2]= ALL_OK, +[WIN_STANDBY2] = ALL_OK, +[WIN_SETIDLE2] = ALL_OK, +[WIN_CHECKPOWERMODE2] = ALL_OK, +[WIN_SLEEPNOW2] = ALL_OK, +[WIN_PACKETCMD] = CD_OK, +[WIN_PIDENTIFY] = CD_OK, +[WIN_SMART] = HD_CFA_OK, +[CFA_ACCESS_METADATA_STORAGE] = CFA_OK, +[CFA_ERASE_SECTORS] = CFA_OK, +[WIN_MULTREAD] = ALL_OK, +[WIN_MULTWRITE] = ALL_OK, +[WIN_SETMULT] = ALL_OK, +[WIN_READDMA] = ALL_OK, +[WIN_READDMA_ONCE] = ALL_OK, +[WIN_WRITEDMA] = ALL_OK, +[WIN_WRITEDMA_ONCE] = ALL_OK, +[CFA_WRITE_MULTI_WO_ERASE] = ALL_OK, +[WIN_STANDBYNOW1] = ALL_OK, +[WIN_IDLEIMMEDIATE] = ALL_OK, +[WIN_STANDBY] = ALL_OK, +[WIN_SETIDLE1] = ALL_OK, +[WIN_CHECKPOWERMODE1] = ALL_OK, +[WIN_SLEEPNOW1] = ALL_OK, +[WIN_FLUSH_CACHE] = ALL_OK, +[WIN_FLUSH_CACHE_EXT] = ALL_OK, +[WIN_IDENTIFY] = ALL_OK, +[WIN_SETFEATURES] = ALL_OK, +[IBM_SENSE_CONDITION] = CFA_OK, +[CFA_WEAR_LEVEL]= CFA_OK, +[WIN_READ_NATIVE_MAX] = ALL_OK, +}; + +static bool ide_cmd_permitted(IDEState *s, uint32_t cmd) +{ +return cmd < ARRAY_SIZE(ide_cmd_table) +&& (ide_cmd_table[cmd] & (1u << s->drive_kind)); +} void ide_exec_cmd(IDEBus *bus, uint32_t val) { @@ -920,6 +992,10 @@ void ide_exec_cmd(IDEBus *bus, uint32_t val) if ((s->status & (BUSY_STAT|DRQ_STAT)) && val != WIN_DEVICE_RESET) return; +if (!ide_cmd_permitted(s, val)) { +goto abort_cmd; +} + switch(val) { case WIN_DSM: switch (s->feature) { @@ -1140,21 +1216,15 @@ void ide_exec_cmd(IDEBus *bus, uint32_t val) ide_set_irq(s->bus); break; case WIN_SEEK: -if(s->drive_kind == IDE_CD) -goto abort_cmd; /* XXX: Check that seek is within bounds */ s->status = READY_STAT | SEEK_STAT; ide_set_irq(s->bus); break; /* ATAPI commands */ case WIN_PIDENTIFY: -if (s->drive_kind == IDE_CD) { -ide_atapi_identify(s); -s->status = READY_STAT | SEEK_STAT; -ide_transfer_start(s, s->io_buffer, 512, ide_transfer_stop); -} else { -ide_abort_command(s); -} +ide_atapi_identify(s); +s->status = READY_
[Qemu-devel] [PATCH 11/35] ide/atapi: Track tray locked state
From: Markus Armbruster We already track it in BlockDriverState. Just like tray open/close state, we should track it in the device models instead, because it's device state. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/ide/atapi.c|4 +++- hw/ide/internal.h |1 + 2 files changed, 4 insertions(+), 1 deletions(-) diff --git a/hw/ide/atapi.c b/hw/ide/atapi.c index 0943f66..d9db6de 100644 --- a/hw/ide/atapi.c +++ b/hw/ide/atapi.c @@ -788,8 +788,9 @@ static void cmd_mode_sense(IDEState *s, uint8_t *buf) buf[12] = 0x71; buf[13] = 3 << 5; buf[14] = (1 << 0) | (1 << 3) | (1 << 5); -if (bdrv_is_locked(s->bs)) +if (s->tray_locked) { buf[6] |= 1 << 1; +} buf[15] = 0x00; cpu_to_ube16(&buf[16], 706); buf[18] = 0; @@ -831,6 +832,7 @@ static void cmd_test_unit_ready(IDEState *s, uint8_t *buf) static void cmd_prevent_allow_medium_removal(IDEState *s, uint8_t* buf) { +s->tray_locked = buf[4] & 1; bdrv_set_locked(s->bs, buf[4] & 1); ide_atapi_cmd_ok(s); } diff --git a/hw/ide/internal.h b/hw/ide/internal.h index 8a9052e..663db39 100644 --- a/hw/ide/internal.h +++ b/hw/ide/internal.h @@ -443,6 +443,7 @@ struct IDEState { uint8_t sense_key; uint8_t asc; bool tray_open; +bool tray_locked; uint8_t cdrom_changed; int packet_transfer_size; int elementary_transfer_size; -- 1.7.6
[Qemu-devel] [PATCH 17/35] rbd: clean up, fix style
From: Sage Weil No assignment in condition. Remove duplicate ret > 0 check. Signed-off-by: Sage Weil Reviewed-by: Stefan Hajnoczi Signed-off-by: Kevin Wolf --- block/rbd.c | 17 - 1 files changed, 8 insertions(+), 9 deletions(-) diff --git a/block/rbd.c b/block/rbd.c index 6135fc1..2763092 100644 --- a/block/rbd.c +++ b/block/rbd.c @@ -391,15 +391,14 @@ static void qemu_rbd_aio_event_reader(void *opaque) char *p = (char *)&s->event_rcb; /* now read the rcb pointer that was sent from a non qemu thread */ -if ((ret = read(s->fds[RBD_FD_READ], p + s->event_reader_pos, -sizeof(s->event_rcb) - s->event_reader_pos)) > 0) { -if (ret > 0) { -s->event_reader_pos += ret; -if (s->event_reader_pos == sizeof(s->event_rcb)) { -s->event_reader_pos = 0; -qemu_rbd_complete_aio(s->event_rcb); -s->qemu_aio_count--; -} +ret = read(s->fds[RBD_FD_READ], p + s->event_reader_pos, + sizeof(s->event_rcb) - s->event_reader_pos); +if (ret > 0) { +s->event_reader_pos += ret; +if (s->event_reader_pos == sizeof(s->event_rcb)) { +s->event_reader_pos = 0; +qemu_rbd_complete_aio(s->event_rcb); +s->qemu_aio_count--; } } } while (ret < 0 && errno == EINTR); -- 1.7.6
[Qemu-devel] [PATCH 33/35] ahci: Remove unused struct member
From: Stefan Weil Member variable is_read is written, but never read (contrary to its name). Remove it. Kevin Wolf Signed-off-by: Stefan Weil Signed-off-by: Kevin Wolf --- hw/ide/ahci.c |2 -- hw/ide/ahci.h |1 - 2 files changed, 0 insertions(+), 3 deletions(-) diff --git a/hw/ide/ahci.c b/hw/ide/ahci.c index f4fa154..a8659cf 100644 --- a/hw/ide/ahci.c +++ b/hw/ide/ahci.c @@ -754,7 +754,6 @@ static void process_ncq_command(AHCIState *s, int port, uint8_t *cmd_fis, case READ_FPDMA_QUEUED: DPRINTF(port, "NCQ reading %d sectors from LBA %ld, tag %d\n", ncq_tfs->sector_count-1, ncq_tfs->lba, ncq_tfs->tag); -ncq_tfs->is_read = 1; DPRINTF(port, "tag %d aio read %ld\n", ncq_tfs->tag, ncq_tfs->lba); @@ -768,7 +767,6 @@ static void process_ncq_command(AHCIState *s, int port, uint8_t *cmd_fis, case WRITE_FPDMA_QUEUED: DPRINTF(port, "NCQ writing %d sectors to LBA %ld, tag %d\n", ncq_tfs->sector_count-1, ncq_tfs->lba, ncq_tfs->tag); -ncq_tfs->is_read = 0; DPRINTF(port, "tag %d aio write %ld\n", ncq_tfs->tag, ncq_tfs->lba); diff --git a/hw/ide/ahci.h b/hw/ide/ahci.h index 3c29d93..5de986c 100644 --- a/hw/ide/ahci.h +++ b/hw/ide/ahci.h @@ -259,7 +259,6 @@ typedef struct NCQTransferState { BlockDriverAIOCB *aiocb; QEMUSGList sglist; BlockAcctCookie acct; -int is_read; uint16_t sector_count; uint64_t lba; uint8_t tag; -- 1.7.6
[Qemu-devel] [PATCH 16/35] rbd: allow client id to be specified in config string
From: Sage Weil Allow the client id to be specified in the config string via 'id=' so that users can control who they authenticate as. Currently they are stuck with the default ('admin'). This is necessary for anyone using authentication in their environment. Signed-off-by: Sage Weil Reviewed-by: Stefan Hajnoczi Signed-off-by: Kevin Wolf --- block/rbd.c | 52 1 files changed, 44 insertions(+), 8 deletions(-) diff --git a/block/rbd.c b/block/rbd.c index ce0f6ef..6135fc1 100644 --- a/block/rbd.c +++ b/block/rbd.c @@ -169,6 +169,34 @@ done: return ret; } +static char *qemu_rbd_parse_clientname(const char *conf, char *clientname) +{ +const char *p = conf; + +while (*p) { +int len; +const char *end = strchr(p, ':'); + +if (end) { +len = end - p; +} else { +len = strlen(p); +} + +if (strncmp(p, "id=", 3) == 0) { +len -= 3; +strncpy(clientname, p + 3, len); +clientname[len] = '\0'; +return clientname; +} +if (end == NULL) { +break; +} +p = end + 1; +} +return NULL; +} + static int qemu_rbd_set_conf(rados_t cluster, const char *conf) { char *p, *buf; @@ -198,17 +226,19 @@ static int qemu_rbd_set_conf(rados_t cluster, const char *conf) break; } -if (strcmp(name, "conf")) { -ret = rados_conf_set(cluster, name, value); +if (strcmp(name, "conf") == 0) { +ret = rados_conf_read_file(cluster, value); if (ret < 0) { -error_report("invalid conf option %s", name); -ret = -EINVAL; +error_report("error reading conf file %s", value); break; } +} else if (strcmp(name, "id") == 0) { +/* ignore, this is parsed by qemu_rbd_parse_clientname() */ } else { -ret = rados_conf_read_file(cluster, value); +ret = rados_conf_set(cluster, name, value); if (ret < 0) { -error_report("error reading conf file %s", value); +error_report("invalid conf option %s", name); +ret = -EINVAL; break; } } @@ -227,6 +257,8 @@ static int qemu_rbd_create(const char *filename, QEMUOptionParameter *options) char name[RBD_MAX_IMAGE_NAME_SIZE]; char snap_buf[RBD_MAX_SNAP_NAME_SIZE]; char conf[RBD_MAX_CONF_SIZE]; +char clientname_buf[RBD_MAX_CONF_SIZE]; +char *clientname; rados_t cluster; rados_ioctx_t io_ctx; int ret; @@ -259,7 +291,8 @@ static int qemu_rbd_create(const char *filename, QEMUOptionParameter *options) options++; } -if (rados_create(&cluster, NULL) < 0) { +clientname = qemu_rbd_parse_clientname(conf, clientname_buf); +if (rados_create(&cluster, clientname) < 0) { error_report("error initializing"); return -EIO; } @@ -385,6 +418,8 @@ static int qemu_rbd_open(BlockDriverState *bs, const char *filename, int flags) char pool[RBD_MAX_POOL_NAME_SIZE]; char snap_buf[RBD_MAX_SNAP_NAME_SIZE]; char conf[RBD_MAX_CONF_SIZE]; +char clientname_buf[RBD_MAX_CONF_SIZE]; +char *clientname; int r; if (qemu_rbd_parsename(filename, pool, sizeof(pool), @@ -398,7 +433,8 @@ static int qemu_rbd_open(BlockDriverState *bs, const char *filename, int flags) s->snap = g_strdup(snap_buf); } -r = rados_create(&s->cluster, NULL); +clientname = qemu_rbd_parse_clientname(conf, clientname_buf); +r = rados_create(&s->cluster, clientname); if (r < 0) { error_report("error initializing"); return r; -- 1.7.6
Re: [Qemu-devel] [PATCH v3 5/6] vga: Use linear mapping + dirty logging in chain 4 memory access mode
On 2011-09-12 17:20, Alexander Graf wrote: > Jan Kiszka wrote: >> Most VGA memory access modes require MMIO handling as they demand weird >> logic to get a byte from or into the video RAM. However, there is one >> exception: chain 4 mode with all memory planes enabled for writing. This >> mode actually allows lineary mapping, which can then be combined with >> dirty logging to accelerate KVM. >> >> This patch accelerates specifically VBE accesses like they are used by >> grub in graphical mode. Not only the standard VGA adapter benefits from >> this, also vmware and spice in VGA mode. >> >> CC: Gerd Hoffmann >> CC: Avi Kivity >> Signed-off-by: Jan Kiszka >> > > [...] > >> +static void vga_update_memory_access(VGACommonState *s) >> +{ >> +MemoryRegion *region, *old_region = s->chain4_alias; >> +target_phys_addr_t base, offset, size; >> + >> +s->chain4_alias = NULL; >> + >> +if ((s->sr[0x02] & 0xf) == 0xf && s->sr[0x04] & 0x08) { >> +offset = 0; >> +switch ((s->gr[6] >> 2) & 3) { >> +case 0: >> +base = 0xa; >> +size = 0x2; >> +break; >> +case 1: >> +base = 0xa; >> +size = 0x1; >> +offset = s->bank_offset; >> +break; >> +case 2: >> +base = 0xb; >> +size = 0x8000; >> +break; >> +case 3: >> +base = 0xb8000; >> +size = 0x8000; >> +break; >> +} >> +region = g_malloc(sizeof(*region)); >> +memory_region_init_alias(region, "vga.chain4", &s->vram, offset, >> size); >> +memory_region_add_subregion_overlap(s->legacy_address_space, base, >> +region, 2); >> > > This one eventually gives me the following in info mtree with -M g3beige > on qemu-system-ppc: > > (qemu) info mtree > memory > system addr off size 7fff > -vga.chain4 addr 000a off size 1 > -macio addr 8088 off size 8 > --macio-nvram addr 0006 off size 2 > --pmac-ide addr 0002 off size 1000 > --cuda addr 00016000 off size 2000 > --escc-bar addr 00013000 off size 40 > --dbdma addr 8000 off size 1000 > --heathrow-pic addr off size 1000 > -vga.rom addr 8080 off size 1 > -vga.vram addr 8000 off size 80 > -vga-lowmem addr 800a off size 2 > -escc addr 80013000 off size 40 > -isa-mmio addr fe00 off size 20 > I/O > io addr off size 1 > -cmd646-bmdma addr 0700 off size 10 > --cmd646-bmdma-ioport addr 000c off size 4 > --cmd646-bmdma-bus addr 0008 off size 4 > --cmd646-bmdma-ioport addr 0004 off size 4 > --cmd646-bmdma-bus addr off size 4 > -cmd646-cmd addr 0680 off size 4 > -cmd646-data addr 0600 off size 8 > -cmd646-cmd addr 0580 off size 4 > -cmd646-data addr 0500 off size 8 > -ne2000 addr 0400 off size 100 > > This ends up overmapping 0xa, effectively overwriting kernel data. > If I #if 0 the offending chunk out, everything is fine. I would assume > that chain4 really needs to be inside of lowmem? No idea about VGA, but > I'm sure you know what's going on :). Does this help? diff --git a/hw/vga.c b/hw/vga.c index 125fb29..0a0c5a6 100644 --- a/hw/vga.c +++ b/hw/vga.c @@ -181,6 +181,7 @@ static void vga_update_memory_access(VGACommonState *s) size = 0x8000; break; } +base += isa_mem_base; region = g_malloc(sizeof(*region)); memory_region_init_alias(region, "vga.chain4", &s->vram, offset, size); memory_region_add_subregion_overlap(s->legacy_address_space, base, Jan -- Siemens AG, Corporate Technology, CT T DE IT 1 Corporate Competence Center Embedded Linux
[Qemu-devel] [PATCH 21/35] ide/atapi: Preserve tray state on migration
From: Markus Armbruster Use a subsection, so that migration to older version still works, provided the tray is closed and unlocked. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/ide/core.c | 32 1 files changed, 32 insertions(+), 0 deletions(-) diff --git a/hw/ide/core.c b/hw/ide/core.c index 0403ad2..18d3c62 100644 --- a/hw/ide/core.c +++ b/hw/ide/core.c @@ -2058,6 +2058,22 @@ static bool ide_drive_pio_state_needed(void *opaque) || (s->bus->error_status & BM_STATUS_PIO_RETRY); } +static int ide_tray_state_post_load(void *opaque, int version_id) +{ +IDEState *s = opaque; + +bdrv_eject(s->bs, s->tray_open); +bdrv_lock_medium(s->bs, s->tray_locked); +return 0; +} + +static bool ide_tray_state_needed(void *opaque) +{ +IDEState *s = opaque; + +return s->tray_open || s->tray_locked; +} + static bool ide_atapi_gesn_needed(void *opaque) { IDEState *s = opaque; @@ -2085,6 +2101,19 @@ static const VMStateDescription vmstate_ide_atapi_gesn_state = { } }; +static const VMStateDescription vmstate_ide_tray_state = { +.name = "ide_drive/tray_state", +.version_id = 1, +.minimum_version_id = 1, +.minimum_version_id_old = 1, +.post_load = ide_tray_state_post_load, +.fields = (VMStateField[]) { +VMSTATE_BOOL(tray_open, IDEState), +VMSTATE_BOOL(tray_locked, IDEState), +VMSTATE_END_OF_LIST() +} +}; + static const VMStateDescription vmstate_ide_drive_pio_state = { .name = "ide_drive/pio_state", .version_id = 1, @@ -2139,6 +2168,9 @@ const VMStateDescription vmstate_ide_drive = { .vmsd = &vmstate_ide_drive_pio_state, .needed = ide_drive_pio_state_needed, }, { +.vmsd = &vmstate_ide_tray_state, +.needed = ide_tray_state_needed, +}, { .vmsd = &vmstate_ide_atapi_gesn_state, .needed = ide_atapi_gesn_needed, }, { -- 1.7.6
[Qemu-devel] Using the qemu tracepoints with SystemTap
Hi All, The RHEL-6 version of qemu-kvm makes the tracepoints available to SystemTap. I have been working on useful examples for the SystemTap tracepoints in qemu. There doesn't seem to be a great number of examples showing the utility of the tracepoints in diagnosing problems. However, I came across the following blog entry that had several examples: http://blog.vmsplice.net/2011/03/how-to-write-trace-analysis-scripts-for.html I reimplemented the VirtqueueRequestTracker example from the blog in SystemTap (the attached virtqueueleaks.stp). I can run it on RHEL-6's qemu-kvm-0.12.1.2-2.160.el6_1.8.x86_64 and get output like the following. It outputs the pid and the address of the elem that leaked when the script is stopped like the following: $ stap virtqueueleaks.stp ^C pid elem 19503 1c4af28 19503 1c56f88 19503 1c62fe8 19503 1c6f048 19503 1c7b0a8 19503 1c87108 19503 1c93168 ... I am not that familiar with the internals of qemu. The script seems to indicates qemu is leaking, but is that really the case? If there are resource leaks, what output would help debug those leaks? What enhancements can be done to this script to provide more useful information? Are there other examples of qemu probing people would like to see? -Will # virtqueueleaks.stp # # virtqueueleaks.stp is based on the VirtqueueRequestTracker from: # http://blog.vmsplice.net/2011/03/how-to-write-trace-analysis-scripts-for.html global elems probe qemu.kvm.virtqueue_pop { elems[pid(),elem] = elem } probe qemu.kvm.virtqueue_fill { delete elems[pid(),elem] } probe end { printf("\n%8s %8s\n", "pid", "elem") foreach([p+, elem] in elems) { printf("%8d %8x\n", p, elem) } }
[Qemu-devel] [PATCH 02/35] ide: Fix ATA command READ to set ATAPI signature for CD-ROM
From: Markus Armbruster Must set the ATAPI device signature, see ATA4 8.27.5.2 Outputs for PACKET Command feature set devices, and ACS-2 7.36.6 Outputs for PACKET feature set devices. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/ide/core.c |4 +++- 1 files changed, 3 insertions(+), 1 deletions(-) diff --git a/hw/ide/core.c b/hw/ide/core.c index 1806e00..def0126 100644 --- a/hw/ide/core.c +++ b/hw/ide/core.c @@ -983,8 +983,10 @@ void ide_exec_cmd(IDEBus *bus, uint32_t val) lba48 = 1; case WIN_READ: case WIN_READ_ONCE: -if (!s->bs) +if (s->drive_kind == IDE_CD) { +ide_set_signature(s); /* odd, but ATA4 8.27.5.2 requires it */ goto abort_cmd; +} ide_cmd_lba48_transform(s, lba48); s->req_nb_sectors = 1; ide_sector_read(s); -- 1.7.6
[Qemu-devel] [PATCH 06/35] ide/atapi: Track tray open/close state
From: Markus Armbruster We already track it in BlockDriverState since commit 4be9762a. As discussed in that commit's message, we should track it in the device device models instead, because it's device state. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/ide/atapi.c|6 +- hw/ide/internal.h |1 + 2 files changed, 6 insertions(+), 1 deletions(-) diff --git a/hw/ide/atapi.c b/hw/ide/atapi.c index cb0cdac..713b1fd 100644 --- a/hw/ide/atapi.c +++ b/hw/ide/atapi.c @@ -521,7 +521,7 @@ static unsigned int event_status_media(IDEState *s, uint8_t event_code, media_status; media_status = 0; -if (s->bs->tray_open) { +if (s->tray_open) { media_status = MS_TRAY_OPEN; } else if (bdrv_is_inserted(s->bs)) { media_status = MS_MEDIA_PRESENT; @@ -926,6 +926,10 @@ static void cmd_start_stop_unit(IDEState *s, uint8_t* buf) ide_atapi_cmd_error(s, SENSE_NOT_READY, ASC_MEDIUM_NOT_PRESENT); break; } + +if (loej && !err) { +s->tray_open = !start; +} } static void cmd_mechanism_status(IDEState *s, uint8_t* buf) diff --git a/hw/ide/internal.h b/hw/ide/internal.h index 1117852..8a9052e 100644 --- a/hw/ide/internal.h +++ b/hw/ide/internal.h @@ -442,6 +442,7 @@ struct IDEState { struct unreported_events events; uint8_t sense_key; uint8_t asc; +bool tray_open; uint8_t cdrom_changed; int packet_transfer_size; int elementary_transfer_size; -- 1.7.6
[Qemu-devel] [PATCH 23/35] block: Drop BlockDriverState member removable
From: Markus Armbruster It's a confused mess (see previous commit). No users remain. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block.c |8 block.h |1 - block_int.h |1 - blockdev.c|5 - hw/fdc.c |1 - hw/ide/core.c |1 - hw/scsi-disk.c|1 - hw/scsi-generic.c |1 - hw/virtio-blk.c |1 - 9 files changed, 0 insertions(+), 20 deletions(-) diff --git a/block.c b/block.c index fee45bf..d8193a3 100644 --- a/block.c +++ b/block.c @@ -1614,14 +1614,6 @@ BlockErrorAction bdrv_get_on_error(BlockDriverState *bs, int is_read) return is_read ? bs->on_read_error : bs->on_write_error; } -void bdrv_set_removable(BlockDriverState *bs, int removable) -{ -bs->removable = removable; -if (removable && bs == bs_snapshots) { -bs_snapshots = NULL; -} -} - int bdrv_is_read_only(BlockDriverState *bs) { return bs->read_only; diff --git a/block.h b/block.h index 860e30d..e4b5530 100644 --- a/block.h +++ b/block.h @@ -207,7 +207,6 @@ int bdrv_get_translation_hint(BlockDriverState *bs); void bdrv_set_on_error(BlockDriverState *bs, BlockErrorAction on_read_error, BlockErrorAction on_write_error); BlockErrorAction bdrv_get_on_error(BlockDriverState *bs, int is_read); -void bdrv_set_removable(BlockDriverState *bs, int removable); int bdrv_is_read_only(BlockDriverState *bs); int bdrv_is_sg(BlockDriverState *bs); int bdrv_enable_write_cache(BlockDriverState *bs); diff --git a/block_int.h b/block_int.h index f42af2c..f30563d 100644 --- a/block_int.h +++ b/block_int.h @@ -155,7 +155,6 @@ struct BlockDriverState { int read_only; /* if true, the media is read only */ int keep_read_only; /* if true, the media was requested to stay read only */ int open_flags; /* flags used to open the file, re-used for re-open */ -int removable; /* if true, the media can be removed */ int encrypted; /* if true, the media is encrypted */ int valid_key; /* if true, a valid encryption key has been set */ int sg;/* if true, the device is a /dev/sg* */ diff --git a/blockdev.c b/blockdev.c index ddf1f8f..154cc84 100644 --- a/blockdev.c +++ b/blockdev.c @@ -473,17 +473,12 @@ DriveInfo *drive_init(QemuOpts *opts, int default_to_scsi) } break; case MEDIA_CDROM: -bdrv_set_removable(dinfo->bdrv, 1); dinfo->media_cd = 1; break; } break; case IF_SD: -/* FIXME: This isn't really a floppy, but it's a reasonable - approximation. */ case IF_FLOPPY: -bdrv_set_removable(dinfo->bdrv, 1); -break; case IF_PFLASH: case IF_MTD: break; diff --git a/hw/fdc.c b/hw/fdc.c index 1d44bbd..edade2b 100644 --- a/hw/fdc.c +++ b/hw/fdc.c @@ -1813,7 +1813,6 @@ static int fdctrl_connect_drives(FDCtrl *fdctrl) fd_revalidate(drive); if (drive->bs) { drive->media_changed = 1; -bdrv_set_removable(drive->bs, 1); bdrv_set_dev_ops(drive->bs, &fdctrl_block_ops, drive); } } diff --git a/hw/ide/core.c b/hw/ide/core.c index 18d3c62..716addc 100644 --- a/hw/ide/core.c +++ b/hw/ide/core.c @@ -1864,7 +1864,6 @@ int ide_init_drive(IDEState *s, BlockDriverState *bs, IDEDriveKind kind, } ide_reset(s); -bdrv_set_removable(bs, s->drive_kind == IDE_CD); return 0; } diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index d6e838c..0f0cddc 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -1233,7 +1233,6 @@ static int scsi_initfn(SCSIDevice *dev, uint8_t scsi_type) s->qdev.type = scsi_type; qemu_add_vm_change_state_handler(scsi_dma_restart_cb, s); -bdrv_set_removable(s->bs, scsi_type == TYPE_ROM); add_boot_device_path(s->qdev.conf.bootindex, &dev->qdev, ",0"); return 0; } diff --git a/hw/scsi-generic.c b/hw/scsi-generic.c index cb5d4f1..5ce01af 100644 --- a/hw/scsi-generic.c +++ b/hw/scsi-generic.c @@ -450,7 +450,6 @@ static int scsi_generic_initfn(SCSIDevice *dev) } } DPRINTF("block size %d\n", s->qdev.blocksize); -bdrv_set_removable(s->bs, 0); return 0; } diff --git a/hw/virtio-blk.c b/hw/virtio-blk.c index d5d4757..6d1a7cf 100644 --- a/hw/virtio-blk.c +++ b/hw/virtio-blk.c @@ -599,7 +599,6 @@ VirtIODevice *virtio_blk_init(DeviceState *dev, BlockConf *conf, s->qdev = dev; register_savevm(dev, "virtio-blk", virtio_blk_id++, 2, virtio_blk_save, virtio_blk_load, s); -bdrv_set_removable(s->bs, 0); bdrv_set_dev_ops(s->bs, &virtio_block_ops, s); s->bs->buffer_alignment = conf->logical_block_size; -- 1.7.6
[Qemu-devel] [PATCH 32/35] qcow2: initialize metadata before inserting in cluster_allocs
From: Frediano Ziglio QCow2Meta structure was inserted into list before many fields are initialized. Currently is not a problem cause all occur in a lock but if qcow2_alloc_clusters would in a future unlock this lock some issues could arise. Initializing fields before inserting fix the problem. Signed-off-by: Frediano Ziglio Signed-off-by: Kevin Wolf --- block/qcow2-cluster.c | 10 +- 1 files changed, 5 insertions(+), 5 deletions(-) diff --git a/block/qcow2-cluster.c b/block/qcow2-cluster.c index 113db8b..428b5ad 100644 --- a/block/qcow2-cluster.c +++ b/block/qcow2-cluster.c @@ -806,6 +806,11 @@ again: abort(); } +/* save info needed for meta data update */ +m->offset = offset; +m->n_start = n_start; +m->nb_clusters = nb_clusters; + QLIST_INSERT_HEAD(&s->cluster_allocs, m, next_in_flight); /* allocate a new cluster */ @@ -816,11 +821,6 @@ again: goto fail; } -/* save info needed for meta data update */ -m->offset = offset; -m->n_start = n_start; -m->nb_clusters = nb_clusters; - out: ret = qcow2_cache_put(bs, s->l2_table_cache, (void**) &l2_table); if (ret < 0) { -- 1.7.6
[Qemu-devel] [PATCH 10/35] block: Drop tray status tracking, no longer used
From: Markus Armbruster Commit 4be9762a is now completely redone. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block.c |1 - block_int.h |1 - 2 files changed, 0 insertions(+), 2 deletions(-) diff --git a/block.c b/block.c index 6fe8add..8c86251 100644 --- a/block.c +++ b/block.c @@ -3062,7 +3062,6 @@ int bdrv_eject(BlockDriverState *bs, int eject_flag) if (drv && drv->bdrv_eject) { drv->bdrv_eject(bs, eject_flag); } -bs->tray_open = eject_flag; return 0; } diff --git a/block_int.h b/block_int.h index 5dc0074..b63c57b 100644 --- a/block_int.h +++ b/block_int.h @@ -157,7 +157,6 @@ struct BlockDriverState { int open_flags; /* flags used to open the file, re-used for re-open */ int removable; /* if true, the media can be removed */ int locked;/* if true, the media cannot temporarily be ejected */ -int tray_open; /* if true, the virtual tray is open */ int encrypted; /* if true, the media is encrypted */ int valid_key; /* if true, a valid encryption key has been set */ int sg;/* if true, the device is a /dev/sg* */ -- 1.7.6
Re: [Qemu-devel] [PATCH v3 5/6] vga: Use linear mapping + dirty logging in chain 4 memory access mode
Jan Kiszka wrote: > Most VGA memory access modes require MMIO handling as they demand weird > logic to get a byte from or into the video RAM. However, there is one > exception: chain 4 mode with all memory planes enabled for writing. This > mode actually allows lineary mapping, which can then be combined with > dirty logging to accelerate KVM. > > This patch accelerates specifically VBE accesses like they are used by > grub in graphical mode. Not only the standard VGA adapter benefits from > this, also vmware and spice in VGA mode. > > CC: Gerd Hoffmann > CC: Avi Kivity > Signed-off-by: Jan Kiszka > [...] > +static void vga_update_memory_access(VGACommonState *s) > +{ > +MemoryRegion *region, *old_region = s->chain4_alias; > +target_phys_addr_t base, offset, size; > + > +s->chain4_alias = NULL; > + > +if ((s->sr[0x02] & 0xf) == 0xf && s->sr[0x04] & 0x08) { > +offset = 0; > +switch ((s->gr[6] >> 2) & 3) { > +case 0: > +base = 0xa; > +size = 0x2; > +break; > +case 1: > +base = 0xa; > +size = 0x1; > +offset = s->bank_offset; > +break; > +case 2: > +base = 0xb; > +size = 0x8000; > +break; > +case 3: > +base = 0xb8000; > +size = 0x8000; > +break; > +} > +region = g_malloc(sizeof(*region)); > +memory_region_init_alias(region, "vga.chain4", &s->vram, offset, > size); > +memory_region_add_subregion_overlap(s->legacy_address_space, base, > +region, 2); > This one eventually gives me the following in info mtree with -M g3beige on qemu-system-ppc: (qemu) info mtree memory system addr off size 7fff -vga.chain4 addr 000a off size 1 -macio addr 8088 off size 8 --macio-nvram addr 0006 off size 2 --pmac-ide addr 0002 off size 1000 --cuda addr 00016000 off size 2000 --escc-bar addr 00013000 off size 40 --dbdma addr 8000 off size 1000 --heathrow-pic addr off size 1000 -vga.rom addr 8080 off size 1 -vga.vram addr 8000 off size 80 -vga-lowmem addr 800a off size 2 -escc addr 80013000 off size 40 -isa-mmio addr fe00 off size 20 I/O io addr off size 1 -cmd646-bmdma addr 0700 off size 10 --cmd646-bmdma-ioport addr 000c off size 4 --cmd646-bmdma-bus addr 0008 off size 4 --cmd646-bmdma-ioport addr 0004 off size 4 --cmd646-bmdma-bus addr off size 4 -cmd646-cmd addr 0680 off size 4 -cmd646-data addr 0600 off size 8 -cmd646-cmd addr 0580 off size 4 -cmd646-data addr 0500 off size 8 -ne2000 addr 0400 off size 100 This ends up overmapping 0xa, effectively overwriting kernel data. If I #if 0 the offending chunk out, everything is fine. I would assume that chain4 really needs to be inside of lowmem? No idea about VGA, but I'm sure you know what's going on :). Alex
[Qemu-devel] [PATCH 09/35] block: Revert entanglement of bdrv_is_inserted() with tray status
From: Markus Armbruster Commit 4be9762a changed bdrv_is_inserted() to fail when the tray is open. Unfortunately, there are two different kinds of users, with conflicting needs. 1. Device models using bdrv_eject(), currently ide-cd and scsi-cd. They expect bdrv_is_inserted() to reflect the tray status. Commit 4be9762a makes them happy. 2. Code that wants to know whether a BlockDriverState has media, such as find_image_format(), bdrv_flush_all(). Commit 4be9762a makes them unhappy. In particular, it breaks flush on VM stop for media ejected by the guest. Revert the change to bdrv_is_inserted(). Check the tray status in the device models instead. Note on IDE: Since only ATAPI devices have a tray, and they don't accept ATA commands since the recent commit "ide: Reject ATA commands specific to drive kinds", checking in atapi.c suffices. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block.c|7 +++ hw/ide/atapi.c | 15 --- hw/scsi-disk.c | 10 -- 3 files changed, 19 insertions(+), 13 deletions(-) diff --git a/block.c b/block.c index a8c789a..6fe8add 100644 --- a/block.c +++ b/block.c @@ -3026,13 +3026,12 @@ static int coroutine_fn bdrv_co_flush_em(BlockDriverState *bs) int bdrv_is_inserted(BlockDriverState *bs) { BlockDriver *drv = bs->drv; -int ret; + if (!drv) return 0; if (!drv->bdrv_is_inserted) -return !bs->tray_open; -ret = drv->bdrv_is_inserted(bs); -return ret; +return 1; +return drv->bdrv_is_inserted(bs); } /** diff --git a/hw/ide/atapi.c b/hw/ide/atapi.c index 713b1fd..0943f66 100644 --- a/hw/ide/atapi.c +++ b/hw/ide/atapi.c @@ -73,7 +73,7 @@ static void lba_to_msf(uint8_t *buf, int lba) static inline int media_present(IDEState *s) { -return (s->nb_sectors > 0); +return !s->tray_open && s->nb_sectors > 0; } /* XXX: DVDs that could fit on a CD will be reported as a CD */ @@ -1077,20 +1077,21 @@ static const struct { [ 0x03 ] = { cmd_request_sense, ALLOW_UA }, [ 0x12 ] = { cmd_inquiry, ALLOW_UA }, [ 0x1a ] = { cmd_mode_sense, /* (6) */ 0 }, -[ 0x1b ] = { cmd_start_stop_unit, 0 }, +[ 0x1b ] = { cmd_start_stop_unit, 0 }, /* [1] */ [ 0x1e ] = { cmd_prevent_allow_medium_removal, 0 }, [ 0x25 ] = { cmd_read_cdvd_capacity,CHECK_READY }, -[ 0x28 ] = { cmd_read, /* (10) */ 0 }, +[ 0x28 ] = { cmd_read, /* (10) */ CHECK_READY }, [ 0x2b ] = { cmd_seek, CHECK_READY }, [ 0x43 ] = { cmd_read_toc_pma_atip, CHECK_READY }, [ 0x46 ] = { cmd_get_configuration, ALLOW_UA }, [ 0x4a ] = { cmd_get_event_status_notification, ALLOW_UA }, [ 0x5a ] = { cmd_mode_sense, /* (10) */ 0 }, -[ 0xa8 ] = { cmd_read, /* (12) */ 0 }, -[ 0xad ] = { cmd_read_dvd_structure,0 }, +[ 0xa8 ] = { cmd_read, /* (12) */ CHECK_READY }, +[ 0xad ] = { cmd_read_dvd_structure,CHECK_READY }, [ 0xbb ] = { cmd_set_speed, 0 }, [ 0xbd ] = { cmd_mechanism_status, 0 }, -[ 0xbe ] = { cmd_read_cd, 0 }, +[ 0xbe ] = { cmd_read_cd, CHECK_READY }, +/* [1] handler detects and reports not ready condition itself */ }; void ide_atapi_cmd(IDEState *s) @@ -1126,7 +1127,7 @@ void ide_atapi_cmd(IDEState *s) * GET_EVENT_STATUS_NOTIFICATION to detect such tray open/close * states rely on this behavior. */ -if (bdrv_is_inserted(s->bs) && s->cdrom_changed) { +if (!s->tray_open && bdrv_is_inserted(s->bs) && s->cdrom_changed) { ide_atapi_cmd_error(s, SENSE_NOT_READY, ASC_MEDIUM_NOT_PRESENT); s->cdrom_changed = 0; diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index f18ddd7..f35ada4 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -183,6 +183,9 @@ static void scsi_read_data(SCSIRequest *req) if (n > SCSI_DMA_BUF_SIZE / 512) n = SCSI_DMA_BUF_SIZE / 512; +if (s->tray_open) { +scsi_read_complete(r, -ENOMEDIUM); +} r->iov.iov_len = n * 512; qemu_iovec_init_external(&r->qiov, &r->iov, 1); @@ -281,6 +284,9 @@ static void scsi_write_data(SCSIRequest *req) n = r->iov.iov_len / 512; if (n) { +if (s->tray_open) { +scsi_write_complete(r, -ENOMEDIUM); +} qemu_iovec_init_external(&r->qiov, &r->iov, 1); bdrv_acct_start(s->bs, &r->acct, n * BDRV_SECTOR_SIZE, BDRV_ACCT_WRITE); @@ -837,7 +843,7 @@ static int scsi_disk_emulate_command(SCSIDiskReq *r, uint8_t *outbuf) switch (req->cmd.buf[0]) { case TEST_UNIT_READY: -if (!bdrv_is_inserted(s->bs)) +if (s->tray_open || !bdrv_is_inserted(s->bs)) goto not_ready; break; case INQUIRY: @@ -957,7 +963,7 @@ st
[Qemu-devel] [PATCH 04/35] ide: Reject ATA commands specific to drive kinds
From: Markus Armbruster ACS-2 Table B.2 explicitly prohibits ATAPI devices from implementing WIN_RECAL, WIN_READ_EXT, WIN_READDMA_EXT, WIN_READ_NATIVE_MAX, WIN_MULTREAD_EXT, WIN_WRITE, WIN_WRITE_ONCE, WIN_WRITE_EXT, WIN_WRITEDMA_EXT, WIN_MULTWRITE_EXT, WIN_WRITE_VERIFY, WIN_VERIFY, WIN_VERIFY_ONCE, WIN_VERIFY_EXT, WIN_SPECIFY, WIN_MULTREAD, WIN_MULTWRITE, WIN_SETMULT, WIN_READDMA, WIN_READDMA_ONCE, WIN_WRITEDMA, WIN_WRITEDMA_ONCE, WIN_FLUSH_CACHE_EXT. Restrict them to IDE_HD and IDE_CFATA. Same for CFA_WRITE_SECT_WO_ERASE, CFA_WRITE_MULTI_WO_ERASE. Restrict them to IDE_CFATA, like the other CFA_ commands. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/ide/core.c | 50 +- 1 files changed, 25 insertions(+), 25 deletions(-) diff --git a/hw/ide/core.c b/hw/ide/core.c index 4a45b3e..b33f84e 100644 --- a/hw/ide/core.c +++ b/hw/ide/core.c @@ -913,27 +913,27 @@ static const uint8_t ide_cmd_table[0x100] = { [CFA_REQ_EXT_ERROR_CODE]= CFA_OK, [WIN_DSM] = ALL_OK, [WIN_DEVICE_RESET] = CD_OK, -[WIN_RECAL] = ALL_OK, +[WIN_RECAL] = HD_CFA_OK, [WIN_READ] = ALL_OK, [WIN_READ_ONCE] = ALL_OK, -[WIN_READ_EXT] = ALL_OK, -[WIN_READDMA_EXT] = ALL_OK, -[WIN_READ_NATIVE_MAX_EXT] = ALL_OK, -[WIN_MULTREAD_EXT] = ALL_OK, -[WIN_WRITE] = ALL_OK, -[WIN_WRITE_ONCE]= ALL_OK, -[WIN_WRITE_EXT] = ALL_OK, -[WIN_WRITEDMA_EXT] = ALL_OK, -[CFA_WRITE_SECT_WO_ERASE] = ALL_OK, -[WIN_MULTWRITE_EXT] = ALL_OK, -[WIN_WRITE_VERIFY] = ALL_OK, -[WIN_VERIFY]= ALL_OK, -[WIN_VERIFY_ONCE] = ALL_OK, -[WIN_VERIFY_EXT]= ALL_OK, +[WIN_READ_EXT] = HD_CFA_OK, +[WIN_READDMA_EXT] = HD_CFA_OK, +[WIN_READ_NATIVE_MAX_EXT] = HD_CFA_OK, +[WIN_MULTREAD_EXT] = HD_CFA_OK, +[WIN_WRITE] = HD_CFA_OK, +[WIN_WRITE_ONCE]= HD_CFA_OK, +[WIN_WRITE_EXT] = HD_CFA_OK, +[WIN_WRITEDMA_EXT] = HD_CFA_OK, +[CFA_WRITE_SECT_WO_ERASE] = CFA_OK, +[WIN_MULTWRITE_EXT] = HD_CFA_OK, +[WIN_WRITE_VERIFY] = HD_CFA_OK, +[WIN_VERIFY]= HD_CFA_OK, +[WIN_VERIFY_ONCE] = HD_CFA_OK, +[WIN_VERIFY_EXT]= HD_CFA_OK, [WIN_SEEK] = HD_CFA_OK, [CFA_TRANSLATE_SECTOR] = CFA_OK, [WIN_DIAGNOSE] = ALL_OK, -[WIN_SPECIFY] = ALL_OK, +[WIN_SPECIFY] = HD_CFA_OK, [WIN_STANDBYNOW2] = ALL_OK, [WIN_IDLEIMMEDIATE2]= ALL_OK, [WIN_STANDBY2] = ALL_OK, @@ -945,14 +945,14 @@ static const uint8_t ide_cmd_table[0x100] = { [WIN_SMART] = HD_CFA_OK, [CFA_ACCESS_METADATA_STORAGE] = CFA_OK, [CFA_ERASE_SECTORS] = CFA_OK, -[WIN_MULTREAD] = ALL_OK, -[WIN_MULTWRITE] = ALL_OK, -[WIN_SETMULT] = ALL_OK, -[WIN_READDMA] = ALL_OK, -[WIN_READDMA_ONCE] = ALL_OK, -[WIN_WRITEDMA] = ALL_OK, -[WIN_WRITEDMA_ONCE] = ALL_OK, -[CFA_WRITE_MULTI_WO_ERASE] = ALL_OK, +[WIN_MULTREAD] = HD_CFA_OK, +[WIN_MULTWRITE] = HD_CFA_OK, +[WIN_SETMULT] = HD_CFA_OK, +[WIN_READDMA] = HD_CFA_OK, +[WIN_READDMA_ONCE] = HD_CFA_OK, +[WIN_WRITEDMA] = HD_CFA_OK, +[WIN_WRITEDMA_ONCE] = HD_CFA_OK, +[CFA_WRITE_MULTI_WO_ERASE] = CFA_OK, [WIN_STANDBYNOW1] = ALL_OK, [WIN_IDLEIMMEDIATE] = ALL_OK, [WIN_STANDBY] = ALL_OK, @@ -960,7 +960,7 @@ static const uint8_t ide_cmd_table[0x100] = { [WIN_CHECKPOWERMODE1] = ALL_OK, [WIN_SLEEPNOW1] = ALL_OK, [WIN_FLUSH_CACHE] = ALL_OK, -[WIN_FLUSH_CACHE_EXT] = ALL_OK, +[WIN_FLUSH_CACHE_EXT] = HD_CFA_OK, [WIN_IDENTIFY] = ALL_OK, [WIN_SETFEATURES] = ALL_OK, [IBM_SENSE_CONDITION] = CFA_OK, -- 1.7.6
[Qemu-devel] [PATCH 13/35] block: Leave enforcing tray lock to device models
From: Markus Armbruster The device model knows best when to accept the guest's eject command. No need to detour through the block layer. bdrv_eject() can't fail anymore. Make it void. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block.c|7 +-- block.h|2 +- hw/ide/atapi.c | 29 + hw/scsi-disk.c |3 +++ 4 files changed, 14 insertions(+), 27 deletions(-) diff --git a/block.c b/block.c index 8c86251..7408fa9 100644 --- a/block.c +++ b/block.c @@ -3051,18 +3051,13 @@ int bdrv_media_changed(BlockDriverState *bs) /** * If eject_flag is TRUE, eject the media. Otherwise, close the tray */ -int bdrv_eject(BlockDriverState *bs, int eject_flag) +void bdrv_eject(BlockDriverState *bs, int eject_flag) { BlockDriver *drv = bs->drv; -if (eject_flag && bs->locked) { -return -EBUSY; -} - if (drv && drv->bdrv_eject) { drv->bdrv_eject(bs, eject_flag); } -return 0; } int bdrv_is_locked(BlockDriverState *bs) diff --git a/block.h b/block.h index 8ec409f..5d941e9 100644 --- a/block.h +++ b/block.h @@ -208,7 +208,7 @@ int bdrv_is_inserted(BlockDriverState *bs); int bdrv_media_changed(BlockDriverState *bs); int bdrv_is_locked(BlockDriverState *bs); void bdrv_set_locked(BlockDriverState *bs, int locked); -int bdrv_eject(BlockDriverState *bs, int eject_flag); +void bdrv_eject(BlockDriverState *bs, int eject_flag); void bdrv_get_format(BlockDriverState *bs, char *buf, int buf_size); BlockDriverState *bdrv_find(const char *name); BlockDriverState *bdrv_next(BlockDriverState *bs); diff --git a/hw/ide/atapi.c b/hw/ide/atapi.c index d9db6de..afb27c6 100644 --- a/hw/ide/atapi.c +++ b/hw/ide/atapi.c @@ -905,33 +905,22 @@ static void cmd_seek(IDEState *s, uint8_t* buf) static void cmd_start_stop_unit(IDEState *s, uint8_t* buf) { -int sense, err = 0; +int sense; bool start = buf[4] & 1; bool loej = buf[4] & 2; /* load on start, eject on !start */ if (loej) { -err = bdrv_eject(s->bs, !start); -} - -switch (err) { -case 0: -ide_atapi_cmd_ok(s); -break; -case -EBUSY: -sense = SENSE_NOT_READY; -if (bdrv_is_inserted(s->bs)) { -sense = SENSE_ILLEGAL_REQUEST; +if (!start && s->tray_locked) { +sense = bdrv_is_inserted(s->bs) +? SENSE_NOT_READY : SENSE_ILLEGAL_REQUEST; +ide_atapi_cmd_error(s, sense, ASC_MEDIA_REMOVAL_PREVENTED); +return; } -ide_atapi_cmd_error(s, sense, ASC_MEDIA_REMOVAL_PREVENTED); -break; -default: -ide_atapi_cmd_error(s, SENSE_NOT_READY, ASC_MEDIUM_NOT_PRESENT); -break; -} - -if (loej && !err) { +bdrv_eject(s->bs, !start); s->tray_open = !start; } + +ide_atapi_cmd_ok(s); } static void cmd_mechanism_status(IDEState *s, uint8_t* buf) diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index e7358e3..65783a7 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -830,6 +830,9 @@ static void scsi_disk_emulate_start_stop(SCSIDiskReq *r) bool loej = req->cmd.buf[4] & 2; /* load on start, eject on !start */ if (s->qdev.type == TYPE_ROM && loej) { +if (!start && s->tray_locked) { +return; +} bdrv_eject(s->bs, !start); s->tray_open = !start; } -- 1.7.6
Re: [Qemu-devel] [PATCH 0/2] versatile: cleanups to remove use of sysbus_mmio_init_cb2
Ping? On 1 September 2011 18:36, Peter Maydell wrote: > A couple of patches which do some cleanup work to versatile > devices following the recent MemoryRegion conversion. These > both remove uses of sysbus_mmio_init_cb2(), which strikes me > as kind of ugly and worth avoiding. (After these two patches > it will be used by only sh_pci.c and ppce500_pci.c...) > > Peter Maydell (2): > hw/arm11mpcore: Clean up to avoid using sysbus_mmio_init_cb2 > hw/versatile_pci: Expose multiple sysbus mmio regions > > hw/arm11mpcore.c | 13 + > hw/realview.c | 12 ++-- > hw/versatile_pci.c | 42 -- > hw/versatilepb.c | 12 ++-- > 4 files changed, 29 insertions(+), 50 deletions(-)
[Qemu-devel] [PATCH 07/35] scsi-disk: Factor out scsi_disk_emulate_start_stop()
From: Markus Armbruster Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/scsi-disk.c | 17 + 1 files changed, 13 insertions(+), 4 deletions(-) diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index 9724d0f..c8ad2e7 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -814,6 +814,18 @@ static int scsi_disk_emulate_read_toc(SCSIRequest *req, uint8_t *outbuf) return toclen; } +static void scsi_disk_emulate_start_stop(SCSIDiskReq *r) +{ +SCSIRequest *req = &r->req; +SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev); +bool start = req->cmd.buf[4] & 1; +bool loej = req->cmd.buf[4] & 2; /* load on start, eject on !start */ + +if (s->qdev.type == TYPE_ROM && loej) { +bdrv_eject(s->bs, !start); +} +} + static int scsi_disk_emulate_command(SCSIDiskReq *r, uint8_t *outbuf) { SCSIRequest *req = &r->req; @@ -859,10 +871,7 @@ static int scsi_disk_emulate_command(SCSIDiskReq *r, uint8_t *outbuf) goto illegal_request; break; case START_STOP: -if (s->qdev.type == TYPE_ROM && (req->cmd.buf[4] & 2)) { -/* load/eject medium */ -bdrv_eject(s->bs, !(req->cmd.buf[4] & 1)); -} +scsi_disk_emulate_start_stop(r); break; case ALLOW_MEDIUM_REMOVAL: bdrv_set_locked(s->bs, req->cmd.buf[4] & 1); -- 1.7.6
Re: [Qemu-devel] [PATCH 02/12] nbd: sync API definitions with upstream
On 09/12/2011 04:15 PM, Kevin Wolf wrote: > Signed-off-by: Paolo Bonzini > --- >nbd.c |2 ++ >nbd.h | 11 ++- >2 files changed, 12 insertions(+), 1 deletions(-) Which upstream? I can't find any NBD version that defines a command/flag for TRIM. Upstream userspace maintainer said he applied the patch, but apparently hasn't pushed yet. http://article.gmane.org/gmane.linux.drivers.nbd.general/1084 Paolo
[Qemu-devel] [PATCH 4/6] qed: add qed_bdrv_get_mapping()
Signed-off-by: Devin Nakamura --- block/qed.c | 29 + 1 files changed, 29 insertions(+), 0 deletions(-) diff --git a/block/qed.c b/block/qed.c index 93827db..4cde2fd 100644 --- a/block/qed.c +++ b/block/qed.c @@ -1512,6 +1512,34 @@ static int bdrv_qed_open_conversion_target(BlockDriverState *bs, return 0; } +static int bdrv_qed_get_mapping(BlockDriverState *bs, uint64_t guest_offset, +uint64_t *host_offset, +uint64_t *contiguous_bytes) +{ +BDRVQEDState *s = bs->opaque; +size_t l2_size = s->header.cluster_size * s->table_nelems; +uint64_t pos = guest_offset; +uint64_t offset; +size_t len = 0; +QEDRequest req = {.l2_table = NULL}; +int ret; + +if (pos >= s->header.image_size) { +*contiguous_bytes = 0; +return 0; +} + +ret = qed_find_cluster_sync(s, &req, guest_offset, l2_size, &offset, &len); +qed_unref_l2_cache_entry(req.l2_table); + +*host_offset = offset; +*contiguous_bytes = len; +if (ret != QED_CLUSTER_FOUND) { +return 1; +} +return 0; +} + static QEMUOptionParameter qed_create_options[] = { { .name = BLOCK_OPT_SIZE, @@ -1560,6 +1588,7 @@ static BlockDriver bdrv_qed = { .bdrv_check = bdrv_qed_check, .bdrv_get_conversion_options = bdrv_qed_get_conversion_options, .bdrv_open_conversion_target = bdrv_qed_open_conversion_target, +.bdrv_get_mapping = bdrv_qed_get_mapping, }; static void bdrv_qed_init(void) -- 1.7.6.rc1
[Qemu-devel] [PATCH 2/6] qed: add bdrv_qed_get_conversion_options()
Signed-off-by: Devin Nakamura --- block/qed.c | 13 + 1 files changed, 13 insertions(+), 0 deletions(-) diff --git a/block/qed.c b/block/qed.c index 624e261..16320f5 100644 --- a/block/qed.c +++ b/block/qed.c @@ -1444,6 +1444,18 @@ static int bdrv_qed_check(BlockDriverState *bs, BdrvCheckResult *result) return qed_check(s, result, false); } +static int bdrv_qed_get_conversion_options(BlockDriverState *bs, + BlockConversionOptions *options) +{ +BDRVQEDState* s = bs->opaque; + +options->encryption_type = 0; +options->cluster_size = s->header.cluster_size; +options->image_size = s->header.image_size; +options->nb_snapshots = 0; +return 0; +} + static QEMUOptionParameter qed_create_options[] = { { .name = BLOCK_OPT_SIZE, @@ -1490,6 +1502,7 @@ static BlockDriver bdrv_qed = { .bdrv_get_info= bdrv_qed_get_info, .bdrv_change_backing_file = bdrv_qed_change_backing_file, .bdrv_check = bdrv_qed_check, +.bdrv_get_conversion_options = bdrv_qed_get_conversion_options, }; static void bdrv_qed_init(void) -- 1.7.6.rc1
[Qemu-devel] [PATCH 4/6] qed: add qed_bdrv_get_mapping()
Signed-off-by: Devin Nakamura --- block/qed.c | 29 + 1 files changed, 29 insertions(+), 0 deletions(-) diff --git a/block/qed.c b/block/qed.c index 93827db..4cde2fd 100644 --- a/block/qed.c +++ b/block/qed.c @@ -1512,6 +1512,34 @@ static int bdrv_qed_open_conversion_target(BlockDriverState *bs, return 0; } +static int bdrv_qed_get_mapping(BlockDriverState *bs, uint64_t guest_offset, +uint64_t *host_offset, +uint64_t *contiguous_bytes) +{ +BDRVQEDState *s = bs->opaque; +size_t l2_size = s->header.cluster_size * s->table_nelems; +uint64_t pos = guest_offset; +uint64_t offset; +size_t len = 0; +QEDRequest req = {.l2_table = NULL}; +int ret; + +if (pos >= s->header.image_size) { +*contiguous_bytes = 0; +return 0; +} + +ret = qed_find_cluster_sync(s, &req, guest_offset, l2_size, &offset, &len); +qed_unref_l2_cache_entry(req.l2_table); + +*host_offset = offset; +*contiguous_bytes = len; +if (ret != QED_CLUSTER_FOUND) { +return 1; +} +return 0; +} + static QEMUOptionParameter qed_create_options[] = { { .name = BLOCK_OPT_SIZE, @@ -1560,6 +1588,7 @@ static BlockDriver bdrv_qed = { .bdrv_check = bdrv_qed_check, .bdrv_get_conversion_options = bdrv_qed_get_conversion_options, .bdrv_open_conversion_target = bdrv_qed_open_conversion_target, +.bdrv_get_mapping = bdrv_qed_get_mapping, }; static void bdrv_qed_init(void) -- 1.7.6.rc1
[Qemu-devel] [PATCH 5/6] qed: add bdrv_qed_map()
Signed-off-by: Devin Nakamura --- block/qed.c | 47 +++ 1 files changed, 47 insertions(+), 0 deletions(-) diff --git a/block/qed.c b/block/qed.c index 4cde2fd..341cf9d 100644 --- a/block/qed.c +++ b/block/qed.c @@ -1540,6 +1540,52 @@ static int bdrv_qed_get_mapping(BlockDriverState *bs, uint64_t guest_offset, return 0; } +static int bdrv_qed_map(BlockDriverState *bs, uint64_t guest_offset, +uint64_t host_offset, uint64_t contiguous_bytes) +{ +BDRVQEDState* s = bs->opaque; +if(guest_offset != qed_start_of_cluster(s, guest_offset)){ +return -EINVAL; +} + +if(contiguous_bytes % s->header.cluster_size != 0){ +return -EINVAL; +} + +while(contiguous_bytes > 0){ +uint64_t l1_index, l2_index, first_l2; +int ret; +QEDRequest req = {.l2_table = NULL}; + + +l1_index = qed_l1_index(s, guest_offset); +l2_index = qed_l2_index(s, guest_offset); +first_l2 = l2_index; +if(!s->l1_table->offsets[l1_index]){ +CachedL2Table * table = qed_new_l2_table(s); +s->l1_table->offsets[l1_index] = table->offset; +qed_write_l1_table_sync(s, l1_index, 1); +qed_commit_l2_cache_entry(&s->l2_cache, table); +} + +ret = qed_read_l2_table_sync(s, &req, s->l1_table->offsets[l1_index]); +if(ret){ +return ret; +} + +for(;l2_index < s->table_nelems && contiguous_bytes > 0; l2_index++){ +req.l2_table->table->offsets[l2_index] = host_offset; +host_offset += s->header.cluster_size; +contiguous_bytes -= s->header.cluster_size; +} + +ret = qed_write_l2_table_sync(s, &req, 0, s->table_nelems, true); +qed_unref_l2_cache_entry(req.l2_table); + +} +return 0; +} + static QEMUOptionParameter qed_create_options[] = { { .name = BLOCK_OPT_SIZE, @@ -1589,6 +1635,7 @@ static BlockDriver bdrv_qed = { .bdrv_get_conversion_options = bdrv_qed_get_conversion_options, .bdrv_open_conversion_target = bdrv_qed_open_conversion_target, .bdrv_get_mapping = bdrv_qed_get_mapping, +.bdrv_map = bdrv_qed_map, }; static void bdrv_qed_init(void) -- 1.7.6.rc1
[Qemu-devel] [PATCH 6/6] qed: add bdrv_qed_copy_header()
Signed-off-by: Devin Nakamura --- block/qed.c | 15 +++ 1 files changed, 15 insertions(+), 0 deletions(-) diff --git a/block/qed.c b/block/qed.c index 341cf9d..caecdff 100644 --- a/block/qed.c +++ b/block/qed.c @@ -1586,6 +1586,20 @@ static int bdrv_qed_map(BlockDriverState *bs, uint64_t guest_offset, return 0; } +static int bdrv_qed_copy_header(BlockDriverState *bs, char* filename) +{ +BlockDriverState *backup; +uint8_t buffer[512]; +bdrv_create_file(filename, NULL); +bdrv_file_open(&backup, filename, BDRV_O_RDWR); +bdrv_read(bs->file, 0, buffer, 1); /*TODO: check return code*/ +bdrv_write(backup, 0, buffer, 1); /*TODO: check return code*/ +bdrv_close(backup); + +qed_write_header_sync(bs->opaque); +return 0; +} + static QEMUOptionParameter qed_create_options[] = { { .name = BLOCK_OPT_SIZE, @@ -1636,6 +1650,7 @@ static BlockDriver bdrv_qed = { .bdrv_open_conversion_target = bdrv_qed_open_conversion_target, .bdrv_get_mapping = bdrv_qed_get_mapping, .bdrv_map = bdrv_qed_map, +.bdrv_copy_header= bdrv_qed_copy_header, }; static void bdrv_qed_init(void) -- 1.7.6.rc1
[Qemu-devel] [PATCH 2/6] qed: add bdrv_qed_get_conversion_options()
Signed-off-by: Devin Nakamura --- block/qed.c | 13 + 1 files changed, 13 insertions(+), 0 deletions(-) diff --git a/block/qed.c b/block/qed.c index 624e261..16320f5 100644 --- a/block/qed.c +++ b/block/qed.c @@ -1444,6 +1444,18 @@ static int bdrv_qed_check(BlockDriverState *bs, BdrvCheckResult *result) return qed_check(s, result, false); } +static int bdrv_qed_get_conversion_options(BlockDriverState *bs, + BlockConversionOptions *options) +{ +BDRVQEDState* s = bs->opaque; + +options->encryption_type = 0; +options->cluster_size = s->header.cluster_size; +options->image_size = s->header.image_size; +options->nb_snapshots = 0; +return 0; +} + static QEMUOptionParameter qed_create_options[] = { { .name = BLOCK_OPT_SIZE, @@ -1490,6 +1502,7 @@ static BlockDriver bdrv_qed = { .bdrv_get_info= bdrv_qed_get_info, .bdrv_change_backing_file = bdrv_qed_change_backing_file, .bdrv_check = bdrv_qed_check, +.bdrv_get_conversion_options = bdrv_qed_get_conversion_options, }; static void bdrv_qed_init(void) -- 1.7.6.rc1
[Qemu-devel] [PATCH 30/35] block: New change_media_cb() parameter load
From: Markus Armbruster To let device models distinguish between eject and load. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block.c| 12 ++-- block.h|3 ++- hw/fdc.c |2 +- hw/ide/core.c |2 +- hw/scsi-disk.c |2 +- hw/sd.c|2 +- 6 files changed, 12 insertions(+), 11 deletions(-) diff --git a/block.c b/block.c index b006e58..e3fe97f 100644 --- a/block.c +++ b/block.c @@ -44,7 +44,7 @@ #include #endif -static void bdrv_dev_change_media_cb(BlockDriverState *bs); +static void bdrv_dev_change_media_cb(BlockDriverState *bs, bool load); static BlockDriverAIOCB *bdrv_aio_readv_em(BlockDriverState *bs, int64_t sector_num, QEMUIOVector *qiov, int nb_sectors, BlockDriverCompletionFunc *cb, void *opaque); @@ -688,7 +688,7 @@ int bdrv_open(BlockDriverState *bs, const char *filename, int flags, } if (!bdrv_key_required(bs)) { -bdrv_dev_change_media_cb(bs); +bdrv_dev_change_media_cb(bs, true); } return 0; @@ -724,7 +724,7 @@ void bdrv_close(BlockDriverState *bs) bdrv_close(bs->file); } -bdrv_dev_change_media_cb(bs); +bdrv_dev_change_media_cb(bs, false); } } @@ -807,10 +807,10 @@ void bdrv_set_dev_ops(BlockDriverState *bs, const BlockDevOps *ops, } } -static void bdrv_dev_change_media_cb(BlockDriverState *bs) +static void bdrv_dev_change_media_cb(BlockDriverState *bs, bool load) { if (bs->dev_ops && bs->dev_ops->change_media_cb) { -bs->dev_ops->change_media_cb(bs->dev_opaque); +bs->dev_ops->change_media_cb(bs->dev_opaque, load); } } @@ -1674,7 +1674,7 @@ int bdrv_set_key(BlockDriverState *bs, const char *key) } else if (!bs->valid_key) { bs->valid_key = 1; /* call the change callback now, we skipped it on open */ -bdrv_dev_change_media_cb(bs); +bdrv_dev_change_media_cb(bs, true); } return ret; } diff --git a/block.h b/block.h index 4b7fa35..16bfa0a 100644 --- a/block.h +++ b/block.h @@ -32,11 +32,12 @@ typedef struct QEMUSnapshotInfo { typedef struct BlockDevOps { /* * Runs when virtual media changed (monitor commands eject, change) + * Argument load is true on load and false on eject. * Beware: doesn't run when a host device's physical media * changes. Sure would be useful if it did. * Device models with removable media must implement this callback. */ -void (*change_media_cb)(void *opaque); +void (*change_media_cb)(void *opaque, bool load); /* * Is the virtual tray open? * Device models implement this only when the device has a tray. diff --git a/hw/fdc.c b/hw/fdc.c index 57eda0c..433af73 100644 --- a/hw/fdc.c +++ b/hw/fdc.c @@ -1777,7 +1777,7 @@ static void fdctrl_result_timer(void *opaque) fdctrl_stop_transfer(fdctrl, 0x00, 0x00, 0x00); } -static void fdctrl_change_cb(void *opaque) +static void fdctrl_change_cb(void *opaque, bool load) { FDrive *drive = opaque; diff --git a/hw/ide/core.c b/hw/ide/core.c index 3771acb..5def25c 100644 --- a/hw/ide/core.c +++ b/hw/ide/core.c @@ -784,7 +784,7 @@ static void ide_cfata_metadata_write(IDEState *s) } /* called when the inserted state of the media has changed */ -static void ide_cd_change_cb(void *opaque) +static void ide_cd_change_cb(void *opaque, bool load) { IDEState *s = opaque; uint64_t nb_sectors; diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index b115760..f5f1d82 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -1173,7 +1173,7 @@ static void scsi_destroy(SCSIDevice *dev) blockdev_mark_auto_del(s->qdev.conf.bs); } -static void scsi_cd_change_media_cb(void *opaque) +static void scsi_cd_change_media_cb(void *opaque, bool load) { } diff --git a/hw/sd.c b/hw/sd.c index 1af62b2..10e26ad 100644 --- a/hw/sd.c +++ b/hw/sd.c @@ -419,7 +419,7 @@ static void sd_reset(SDState *sd, BlockDriverState *bdrv) sd->pwd_len = 0; } -static void sd_cardchange(void *opaque) +static void sd_cardchange(void *opaque, bool load) { SDState *sd = opaque; -- 1.7.6
[Qemu-devel] [PATCH 14/35] block: Drop medium lock tracking, ask device models instead
From: Markus Armbruster Requires new BlockDevOps member is_medium_locked(). Implement for IDE and SCSI CD-ROMs. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block.c| 16 +--- block.h|7 ++- block_int.h|1 - blockdev.c |2 +- hw/ide/core.c |6 ++ hw/scsi-disk.c | 10 ++ 6 files changed, 32 insertions(+), 10 deletions(-) diff --git a/block.c b/block.c index 7408fa9..1e4be73 100644 --- a/block.c +++ b/block.c @@ -818,6 +818,14 @@ static void bdrv_dev_resize_cb(BlockDriverState *bs) } } +bool bdrv_dev_is_medium_locked(BlockDriverState *bs) +{ +if (bs->dev_ops && bs->dev_ops->is_medium_locked) { +return bs->dev_ops->is_medium_locked(bs->dev_opaque); +} +return false; +} + /* * Run consistency checks on an image * @@ -1890,7 +1898,7 @@ void bdrv_info(Monitor *mon, QObject **ret_data) bs_obj = qobject_from_jsonf("{ 'device': %s, 'type': 'unknown', " "'removable': %i, 'locked': %i }", bs->device_name, bs->removable, -bs->locked); +bdrv_dev_is_medium_locked(bs)); if (bs->drv) { QObject *obj; @@ -3060,11 +3068,6 @@ void bdrv_eject(BlockDriverState *bs, int eject_flag) } } -int bdrv_is_locked(BlockDriverState *bs) -{ -return bs->locked; -} - /** * Lock or unlock the media (if it is locked, the user won't be able * to eject it manually). @@ -3075,7 +3078,6 @@ void bdrv_set_locked(BlockDriverState *bs, int locked) trace_bdrv_set_locked(bs, locked); -bs->locked = locked; if (drv && drv->bdrv_set_locked) { drv->bdrv_set_locked(bs, locked); } diff --git a/block.h b/block.h index 5d941e9..396ca0e 100644 --- a/block.h +++ b/block.h @@ -37,6 +37,11 @@ typedef struct BlockDevOps { */ void (*change_media_cb)(void *opaque); /* + * Is the virtual medium locked into the device? + * Device models implement this only when device has such a lock. + */ +bool (*is_medium_locked)(void *opaque); +/* * Runs when the size changed (e.g. monitor command block_resize) */ void (*resize_cb)(void *opaque); @@ -94,6 +99,7 @@ void bdrv_detach_dev(BlockDriverState *bs, void *dev); void *bdrv_get_attached_dev(BlockDriverState *bs); void bdrv_set_dev_ops(BlockDriverState *bs, const BlockDevOps *ops, void *opaque); +bool bdrv_dev_is_medium_locked(BlockDriverState *bs); int bdrv_read(BlockDriverState *bs, int64_t sector_num, uint8_t *buf, int nb_sectors); int bdrv_write(BlockDriverState *bs, int64_t sector_num, @@ -206,7 +212,6 @@ int bdrv_is_sg(BlockDriverState *bs); int bdrv_enable_write_cache(BlockDriverState *bs); int bdrv_is_inserted(BlockDriverState *bs); int bdrv_media_changed(BlockDriverState *bs); -int bdrv_is_locked(BlockDriverState *bs); void bdrv_set_locked(BlockDriverState *bs, int locked); void bdrv_eject(BlockDriverState *bs, int eject_flag); void bdrv_get_format(BlockDriverState *bs, char *buf, int buf_size); diff --git a/block_int.h b/block_int.h index b63c57b..4f7ff3b 100644 --- a/block_int.h +++ b/block_int.h @@ -156,7 +156,6 @@ struct BlockDriverState { int keep_read_only; /* if true, the media was requested to stay read only */ int open_flags; /* flags used to open the file, re-used for re-open */ int removable; /* if true, the media can be removed */ -int locked;/* if true, the media cannot temporarily be ejected */ int encrypted; /* if true, the media is encrypted */ int valid_key; /* if true, a valid encryption key has been set */ int sg;/* if true, the device is a /dev/sg* */ diff --git a/blockdev.c b/blockdev.c index 049dda5..3f00b2e 100644 --- a/blockdev.c +++ b/blockdev.c @@ -640,7 +640,7 @@ static int eject_device(Monitor *mon, BlockDriverState *bs, int force) qerror_report(QERR_DEVICE_NOT_REMOVABLE, bdrv_get_device_name(bs)); return -1; } -if (!force && bdrv_is_locked(bs)) { +if (!force && bdrv_dev_is_medium_locked(bs)) { qerror_report(QERR_DEVICE_LOCKED, bdrv_get_device_name(bs)); return -1; } diff --git a/hw/ide/core.c b/hw/ide/core.c index b33f84e..0403ad2 100644 --- a/hw/ide/core.c +++ b/hw/ide/core.c @@ -1795,8 +1795,14 @@ void ide_bus_reset(IDEBus *bus) bus->dma->ops->reset(bus->dma); } +static bool ide_cd_is_medium_locked(void *opaque) +{ +return ((IDEState *)opaque)->tray_locked; +} + static const BlockDevOps ide_cd_block_ops = { .change_media_cb = ide_cd_change_cb, +.is_medium_locked = ide_cd_is_medium_locked, }; int ide_init_drive(IDEState *s, BlockDriverState *bs, IDEDriveKind kind, diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index 65783a7..42682d0 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -1165,6 +1165,15 @@ static void s
[Qemu-devel] [PATCH 26/35] hw: Trim superfluous #include "block_int.h"
From: Markus Armbruster Including it in device models is unclean, including it without a reason adds insult to injury. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/fdc.c|1 - hw/ide/cmd646.c |1 - hw/ide/ich.c|1 - hw/ide/isa.c|1 - hw/ide/macio.c |1 - hw/ide/microdrive.c |1 - hw/ide/mmio.c |1 - hw/ide/pci.c|1 - hw/ide/via.c|1 - hw/lsi53c895a.c |1 - 10 files changed, 0 insertions(+), 10 deletions(-) diff --git a/hw/fdc.c b/hw/fdc.c index edade2b..57eda0c 100644 --- a/hw/fdc.c +++ b/hw/fdc.c @@ -36,7 +36,6 @@ #include "qdev-addr.h" #include "blockdev.h" #include "sysemu.h" -#include "block_int.h" // /* debug Floppy devices */ diff --git a/hw/ide/cmd646.c b/hw/ide/cmd646.c index 4d91e2c..5fe98b1 100644 --- a/hw/ide/cmd646.c +++ b/hw/ide/cmd646.c @@ -27,7 +27,6 @@ #include #include #include "block.h" -#include "block_int.h" #include "sysemu.h" #include "dma.h" diff --git a/hw/ide/ich.c b/hw/ide/ich.c index 5278bc4..0327d0e 100644 --- a/hw/ide/ich.c +++ b/hw/ide/ich.c @@ -66,7 +66,6 @@ #include #include #include "block.h" -#include "block_int.h" #include "dma.h" #include diff --git a/hw/ide/isa.c b/hw/ide/isa.c index 4ac7453..28b69d2 100644 --- a/hw/ide/isa.c +++ b/hw/ide/isa.c @@ -26,7 +26,6 @@ #include #include #include "block.h" -#include "block_int.h" #include "dma.h" #include diff --git a/hw/ide/macio.c b/hw/ide/macio.c index fdf5d75..c1844cb 100644 --- a/hw/ide/macio.c +++ b/hw/ide/macio.c @@ -26,7 +26,6 @@ #include #include #include "block.h" -#include "block_int.h" #include "dma.h" #include diff --git a/hw/ide/microdrive.c b/hw/ide/microdrive.c index 91c0e3c..9eee5b5 100644 --- a/hw/ide/microdrive.c +++ b/hw/ide/microdrive.c @@ -26,7 +26,6 @@ #include #include #include "block.h" -#include "block_int.h" #include "dma.h" #include diff --git a/hw/ide/mmio.c b/hw/ide/mmio.c index 132b751..2ec21b0 100644 --- a/hw/ide/mmio.c +++ b/hw/ide/mmio.c @@ -24,7 +24,6 @@ */ #include #include "block.h" -#include "block_int.h" #include "dma.h" #include diff --git a/hw/ide/pci.c b/hw/ide/pci.c index d1a14d7..9fded02 100644 --- a/hw/ide/pci.c +++ b/hw/ide/pci.c @@ -27,7 +27,6 @@ #include #include #include "block.h" -#include "block_int.h" #include "dma.h" #include diff --git a/hw/ide/via.c b/hw/ide/via.c index c0b9d43..dab8a39 100644 --- a/hw/ide/via.c +++ b/hw/ide/via.c @@ -28,7 +28,6 @@ #include #include #include "block.h" -#include "block_int.h" #include "sysemu.h" #include "dma.h" diff --git a/hw/lsi53c895a.c b/hw/lsi53c895a.c index ac284e9..dbb3bdf 100644 --- a/hw/lsi53c895a.c +++ b/hw/lsi53c895a.c @@ -15,7 +15,6 @@ #include "hw.h" #include "pci.h" #include "scsi.h" -#include "block_int.h" //#define DEBUG_LSI //#define DEBUG_LSI_REG -- 1.7.6
[Qemu-devel] [PATCH 25/35] block: Move BlockConf & friends from block_int.h to block.h
From: Markus Armbruster It's convenience stuff for block device models, so block.h isn't the ideal home either, but better than block_int.h. Permits moving some #include "block_int.h" from device model .h into .c. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block.h | 38 ++ block_int.h | 35 --- hw/ide/core.c |1 + hw/ide/internal.h |1 - hw/scsi-disk.c|1 + hw/scsi.h |1 - hw/virtio-blk.c |1 + hw/virtio.h |2 +- 8 files changed, 42 insertions(+), 38 deletions(-) diff --git a/block.h b/block.h index 9f6d02c..6e0c468 100644 --- a/block.h +++ b/block.h @@ -350,5 +350,43 @@ typedef enum { #define BLKDBG_EVENT(bs, evt) bdrv_debug_event(bs, evt) void bdrv_debug_event(BlockDriverState *bs, BlkDebugEvent event); + +/* Convenience for block device models */ + +typedef struct BlockConf { +BlockDriverState *bs; +uint16_t physical_block_size; +uint16_t logical_block_size; +uint16_t min_io_size; +uint32_t opt_io_size; +int32_t bootindex; +uint32_t discard_granularity; +} BlockConf; + +static inline unsigned int get_physical_block_exp(BlockConf *conf) +{ +unsigned int exp = 0, size; + +for (size = conf->physical_block_size; +size > conf->logical_block_size; +size >>= 1) { +exp++; +} + +return exp; +} + +#define DEFINE_BLOCK_PROPERTIES(_state, _conf) \ +DEFINE_PROP_DRIVE("drive", _state, _conf.bs), \ +DEFINE_PROP_UINT16("logical_block_size", _state,\ + _conf.logical_block_size, 512), \ +DEFINE_PROP_UINT16("physical_block_size", _state, \ + _conf.physical_block_size, 512), \ +DEFINE_PROP_UINT16("min_io_size", _state, _conf.min_io_size, 0), \ +DEFINE_PROP_UINT32("opt_io_size", _state, _conf.opt_io_size, 0),\ +DEFINE_PROP_INT32("bootindex", _state, _conf.bootindex, -1),\ +DEFINE_PROP_UINT32("discard_granularity", _state, \ + _conf.discard_granularity, 0) + #endif diff --git a/block_int.h b/block_int.h index f30563d..8c3b863 100644 --- a/block_int.h +++ b/block_int.h @@ -225,39 +225,4 @@ void qemu_aio_release(void *p); int is_windows_drive(const char *filename); #endif -typedef struct BlockConf { -BlockDriverState *bs; -uint16_t physical_block_size; -uint16_t logical_block_size; -uint16_t min_io_size; -uint32_t opt_io_size; -int32_t bootindex; -uint32_t discard_granularity; -} BlockConf; - -static inline unsigned int get_physical_block_exp(BlockConf *conf) -{ -unsigned int exp = 0, size; - -for (size = conf->physical_block_size; -size > conf->logical_block_size; -size >>= 1) { -exp++; -} - -return exp; -} - -#define DEFINE_BLOCK_PROPERTIES(_state, _conf) \ -DEFINE_PROP_DRIVE("drive", _state, _conf.bs), \ -DEFINE_PROP_UINT16("logical_block_size", _state,\ - _conf.logical_block_size, 512), \ -DEFINE_PROP_UINT16("physical_block_size", _state, \ - _conf.physical_block_size, 512), \ -DEFINE_PROP_UINT16("min_io_size", _state, _conf.min_io_size, 0), \ -DEFINE_PROP_UINT32("opt_io_size", _state, _conf.opt_io_size, 0),\ -DEFINE_PROP_INT32("bootindex", _state, _conf.bootindex, -1),\ -DEFINE_PROP_UINT32("discard_granularity", _state, \ - _conf.discard_granularity, 0) - #endif /* BLOCK_INT_H */ diff --git a/hw/ide/core.c b/hw/ide/core.c index 8f719ee..740ffe0 100644 --- a/hw/ide/core.c +++ b/hw/ide/core.c @@ -30,6 +30,7 @@ #include "sysemu.h" #include "dma.h" #include "blockdev.h" +#include "block_int.h" #include diff --git a/hw/ide/internal.h b/hw/ide/internal.h index 663db39..233915c 100644 --- a/hw/ide/internal.h +++ b/hw/ide/internal.h @@ -7,7 +7,6 @@ * non-internal declarations are in hw/ide.h */ #include -#include "block_int.h" #include "iorange.h" #include "dma.h" diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index f48ca8b..d44b3b8 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -37,6 +37,7 @@ do { fprintf(stderr, "scsi-disk: " fmt , ## __VA_ARGS__); } while (0) #include "scsi-defs.h" #include "sysemu.h" #include "blockdev.h" +#include "block_int.h" #define SCSI_DMA_BUF_SIZE131072 #define SCSI_MAX_INQUIRY_LEN 256 diff --git a/hw/scsi.h b/hw/scsi.h index a28cd68..e8dcabf 100644 --- a/hw/scsi.h +++ b/hw/scsi.h @@ -3,7 +3,6 @@ #include "qdev.h" #include "block.h" -#include "block_int.h" #define MAX_SCSI_DEVS 255 diff --git a/hw/virtio-blk.c b/hw/virtio-blk.c index 6d1a7cf..7bf684e 100644 --- a/hw/virtio-blk.c +++ b/hw/virtio-blk.c @@ -15,6 +1
[Qemu-devel] [PATCH 34/35] qcow2: align cluster_data to block to improve performance using O_DIRECT
From: Frediano Ziglio Signed-off-by: Frediano Ziglio Signed-off-by: Kevin Wolf --- block/qcow2.c | 14 +++--- 1 files changed, 7 insertions(+), 7 deletions(-) diff --git a/block/qcow2.c b/block/qcow2.c index 8aed310..510ff68 100644 --- a/block/qcow2.c +++ b/block/qcow2.c @@ -237,7 +237,7 @@ static int qcow2_open(BlockDriverState *bs, int flags) s->cluster_cache = g_malloc(s->cluster_size); /* one more sector for decompressed data alignment */ -s->cluster_data = g_malloc(QCOW_MAX_CRYPT_CLUSTERS * s->cluster_size +s->cluster_data = qemu_blockalign(bs, QCOW_MAX_CRYPT_CLUSTERS * s->cluster_size + 512); s->cluster_cache_offset = -1; @@ -296,7 +296,7 @@ static int qcow2_open(BlockDriverState *bs, int flags) qcow2_cache_destroy(bs, s->l2_table_cache); } g_free(s->cluster_cache); -g_free(s->cluster_data); +qemu_vfree(s->cluster_data); return ret; } @@ -456,7 +456,7 @@ static int qcow2_co_readv(BlockDriverState *bs, int64_t sector_num, */ if (!cluster_data) { cluster_data = -g_malloc0(QCOW_MAX_CRYPT_CLUSTERS * s->cluster_size); +qemu_blockalign(bs, QCOW_MAX_CRYPT_CLUSTERS * s->cluster_size); } assert(cur_nr_sectors <= @@ -496,7 +496,7 @@ fail: qemu_co_mutex_unlock(&s->lock); qemu_iovec_destroy(&hd_qiov); -g_free(cluster_data); +qemu_vfree(cluster_data); return ret; } @@ -566,7 +566,7 @@ static int qcow2_co_writev(BlockDriverState *bs, if (s->crypt_method) { if (!cluster_data) { -cluster_data = g_malloc0(QCOW_MAX_CRYPT_CLUSTERS * +cluster_data = qemu_blockalign(bs, QCOW_MAX_CRYPT_CLUSTERS * s->cluster_size); } @@ -611,7 +611,7 @@ fail: qemu_co_mutex_unlock(&s->lock); qemu_iovec_destroy(&hd_qiov); -g_free(cluster_data); +qemu_vfree(cluster_data); return ret; } @@ -628,7 +628,7 @@ static void qcow2_close(BlockDriverState *bs) qcow2_cache_destroy(bs, s->refcount_block_cache); g_free(s->cluster_cache); -g_free(s->cluster_data); +qemu_vfree(s->cluster_data); qcow2_refcount_close(bs); } -- 1.7.6
[Qemu-devel] [PATCH 3/6] qed: add open_conversion_target()
Signed-off-by: Devin Nakamura --- block/qed.c | 57 + 1 files changed, 57 insertions(+), 0 deletions(-) diff --git a/block/qed.c b/block/qed.c index 16320f5..93827db 100644 --- a/block/qed.c +++ b/block/qed.c @@ -1456,6 +1456,62 @@ static int bdrv_qed_get_conversion_options(BlockDriverState *bs, return 0; } +static int bdrv_qed_open_conversion_target(BlockDriverState *bs, + BlockConversionOptions *drv_options, + QEMUOptionParameter *usr_options, + bool force) +{ +BDRVQEDState *s = bs->opaque; +s->bs = bs; +if (drv_options->encryption_type != BLOCK_CRYPT_NONE) { +error_report("Encryption not supported"); +return -ENOTSUP; +} +if(drv_options->nb_snapshots && !force) { +error_report("Snapshots are not supported"); +return -ENOTSUP; +} +s->header.magic = QED_MAGIC; +s->header.table_size = QED_DEFAULT_TABLE_SIZE; +if(qed_is_cluster_size_valid(drv_options->cluster_size)) { +s->header.cluster_size = drv_options->cluster_size; +} else { +error_report("Invalid cluster size"); +return -EINVAL; +} +if(qed_is_image_size_valid(drv_options->image_size, s->header.cluster_size, + s->header.table_size)) { +s->header.image_size = drv_options->image_size; +} else { +error_report("Invalid image size"); +return -EINVAL; +} +s->file_size = qed_Start_of_cluster(s, bs->file->total_sectors + +drv_options->cluster_size -1); +s->l1_table = qed_alloc_table(s); +s->header.l1_table_offset = qed_alloc_clusters(s, s->header.table_size); +QSIMPLEQ_INIT(&s->allocating_write_reqs); + + +if (!qed_check_table_offset(s, s->header.l1_table_offset)) { +error_report("Invalid L1 table offset"); +return -EINVAL; +} + +s->table_nelems = (s->header.cluster_size * s->header.table_size) / + sizeof(uint64_t); +s->l2_shift = ffs(s->header.cluster_size) - 1; +s->l2_mask = s->table_nelems - 1; +s->l1_shift = s->l2_shift + ffs(s->table_nelems) - 1; + +qed_init_l2_cache(&s->l2_cache); + +s->need_check_timer = qemu_new_timer_ns(vm_clock, +qed_need_check_timer_cb, s); +qed_write_l1_table_sync(s, 0, s->table_nelems); +return 0; +} + static QEMUOptionParameter qed_create_options[] = { { .name = BLOCK_OPT_SIZE, @@ -1503,6 +1559,7 @@ static BlockDriver bdrv_qed = { .bdrv_change_backing_file = bdrv_qed_change_backing_file, .bdrv_check = bdrv_qed_check, .bdrv_get_conversion_options = bdrv_qed_get_conversion_options, +.bdrv_open_conversion_target = bdrv_qed_open_conversion_target, }; static void bdrv_qed_init(void) -- 1.7.6.rc1
[Qemu-devel] [PATCH 1/6] qed: add qed_find_cluster_sync()
Signed-off-by: Devin Nakamura --- block/qed-cluster.c | 33 + block/qed.h |4 2 files changed, 37 insertions(+), 0 deletions(-) diff --git a/block/qed-cluster.c b/block/qed-cluster.c index f64b2af..6e68ba7 100644 --- a/block/qed-cluster.c +++ b/block/qed-cluster.c @@ -163,3 +163,36 @@ void qed_find_cluster(BDRVQEDState *s, QEDRequest *request, uint64_t pos, qed_read_l2_table(s, request, l2_offset, qed_find_cluster_cb, find_cluster_cb); } + +typedef struct { +int ret; +uint64_t *offset; +size_t *len; +} QEDFindClusterSyncCB; + +static void qed_find_cluster_sync_cb(void *opaque, int ret, uint64_t offset, + size_t len) +{ +QEDFindClusterSyncCB *find_cluster_sync_cb = opaque; +*find_cluster_sync_cb->offset = offset; +*find_cluster_sync_cb->len = len; +find_cluster_sync_cb->ret = ret; +} + +int qed_find_cluster_sync(BDRVQEDState *s, QEDRequest *request, uint64_t pos, + size_t len, uint64_t *offset, + size_t *contiguous_bytes) +{ +QEDFindClusterSyncCB find_cluster_cb; +find_cluster_cb.ret = -EINPROGRESS; +find_cluster_cb.offset = offset; +find_cluster_cb.len = contiguous_bytes; + +qed_find_cluster(s, request, pos, len, &qed_find_cluster_sync_cb, + &find_cluster_cb); +while (find_cluster_cb.ret == -EINPROGRESS) { +qemu_aio_wait(); +} + +return find_cluster_cb.ret; +} diff --git a/block/qed.h b/block/qed.h index 388fdb3..c899c15 100644 --- a/block/qed.h +++ b/block/qed.h @@ -239,6 +239,10 @@ int qed_write_l2_table_sync(BDRVQEDState *s, QEDRequest *request, void qed_find_cluster(BDRVQEDState *s, QEDRequest *request, uint64_t pos, size_t len, QEDFindClusterFunc *cb, void *opaque); +int qed_find_cluster_sync(BDRVQEDState *s, QEDRequest *request, uint64_t pos, + size_t len, uint64_t *offset, + size_t *contiguous_bytes); + /** * Consistency check */ -- 1.7.6.rc1
[Qemu-devel] [PATCH 0/6] QED block conversion
This patch series adds support for block conversion to the qed driver. This depends on my precivious block conversion api series Devin Nakamura (6): qed: add qed_find_cluster_sync() qed: add bdrv_qed_get_conversion_options() qed: add open_conversion_target() qed: add qed_bdrv_get_mapping() qed: add bdrv_qed_map() qed: add bdrv_qed_copy_header() block/qed-cluster.c | 33 +++ block/qed.c | 161 +++ block/qed.h |4 + 3 files changed, 198 insertions(+), 0 deletions(-) -- 1.7.6.rc1
[Qemu-devel] [PATCH 19/35] ide/atapi: Don't fail eject when tray is already open
From: Markus Armbruster MMC-5 6.40.2.6 specifies that START STOP UNIT succeeds when the drive already has the requested state. cmd_start_stop_unit() fails when asked to eject while the tray is open and locked. Fix that. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/ide/atapi.c |2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diff --git a/hw/ide/atapi.c b/hw/ide/atapi.c index 06778f3..3f909c3 100644 --- a/hw/ide/atapi.c +++ b/hw/ide/atapi.c @@ -910,7 +910,7 @@ static void cmd_start_stop_unit(IDEState *s, uint8_t* buf) bool loej = buf[4] & 2; /* load on start, eject on !start */ if (loej) { -if (!start && s->tray_locked) { +if (!start && !s->tray_open && s->tray_locked) { sense = bdrv_is_inserted(s->bs) ? SENSE_NOT_READY : SENSE_ILLEGAL_REQUEST; ide_atapi_cmd_error(s, sense, ASC_MEDIA_REMOVAL_PREVENTED); -- 1.7.6
[Qemu-devel] [PATCH v2] hw/integratorcp: Fix bugs in writes to CM_CTRL system register
Fix a number of bugs in the implementation of writes to the CM_CTRL system register: * write to cm_ctrl, not cm_init ! * an '&' vs '^' typo meant we would write the inverse of the bits * handling the LED via printf() meant we spew lots of output to stdout when Linux uses the LED as a heartbeat indicator * we would hw_error() if a reset was requested rather than actually resetting Signed-off-by: Peter Maydell --- This is just a retransmit rebased following some of Avi's MemoryRegion patches landing, no other changes from v1. hw/integratorcp.c | 16 +++- 1 files changed, 11 insertions(+), 5 deletions(-) diff --git a/hw/integratorcp.c b/hw/integratorcp.c index 3c8982e..9a289b4 100644 --- a/hw/integratorcp.c +++ b/hw/integratorcp.c @@ -14,6 +14,7 @@ #include "arm-misc.h" #include "net.h" #include "exec-memory.h" +#include "sysemu.h" typedef struct { SysBusDevice busdev; @@ -126,15 +127,20 @@ static void integratorcm_do_remap(integratorcm_state *s, int flash) static void integratorcm_set_ctrl(integratorcm_state *s, uint32_t value) { if (value & 8) { -hw_error("Board reset\n"); +qemu_system_reset_request(); } -if ((s->cm_init ^ value) & 4) { +if ((s->cm_ctrl ^ value) & 4) { integratorcm_do_remap(s, (value & 4) == 0); } -if ((s->cm_init ^ value) & 1) { -printf("Green LED %s\n", (value & 1) ? "on" : "off"); +if ((s->cm_ctrl ^ value) & 1) { +/* (value & 1) != 0 means the green "MISC LED" is lit. + * We don't have any nice place to display LEDs. printf is a bad + * idea because Linux uses the LED as a heartbeat and the output + * will swamp anything else on the terminal. + */ } -s->cm_init = (s->cm_init & ~ 5) | (value ^ 5); +/* Note that the RESET bit [3] always reads as zero */ +s->cm_ctrl = (s->cm_ctrl & ~5) | (value & 5); } static void integratorcm_update(integratorcm_state *s) -- 1.7.1
[Qemu-devel] [PATCH 08/35] scsi-disk: Track tray open/close state
From: Markus Armbruster We already track it in BlockDriverState since commit 4be9762a. As discussed in that commit's message, we should track it in the device device models instead, because it's device state. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/scsi-disk.c |2 ++ 1 files changed, 2 insertions(+), 0 deletions(-) diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index c8ad2e7..f18ddd7 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -72,6 +72,7 @@ struct SCSIDiskState QEMUBH *bh; char *version; char *serial; +bool tray_open; }; static int scsi_handle_rw_error(SCSIDiskReq *r, int error, int type); @@ -823,6 +824,7 @@ static void scsi_disk_emulate_start_stop(SCSIDiskReq *r) if (s->qdev.type == TYPE_ROM && loej) { bdrv_eject(s->bs, !start); +s->tray_open = !start; } } -- 1.7.6
Re: [Qemu-devel] [PATCH 1/1] qemu-img: async write to block device when converting image
Note that I assumed qemu-img runs in a single context (like qemu), and there are no concurrency issues. If that's not the case, the callback, error handling need to be fixed. Yehuda On Mon, Sep 12, 2011 at 7:26 AM, Yehuda Sadeh wrote: > In order to improve image conversion process, instead of synchronously > writing the destingation image, we keep a window of async writes. > > Signed-off-by: Yehuda Sadeh > --- > qemu-img.c | 47 +++ > 1 files changed, 43 insertions(+), 4 deletions(-) > > diff --git a/qemu-img.c b/qemu-img.c > index 6a39731..a45f5f2 100644 > --- a/qemu-img.c > +++ b/qemu-img.c > @@ -646,6 +646,29 @@ static int compare_sectors(const uint8_t *buf1, const > uint8_t *buf2, int n, > } > > #define IO_BUF_SIZE (2 * 1024 * 1024) > +#define IO_WRITE_WINDOW_THRESHOLD (32 * 1024 * 1024) > + > +static int write_window = 0; > +static int write_ret = 0; > + > +struct write_info { > + int64_t sector; > + QEMUIOVector qiov; > +}; > + > +static void img_write_cb(void *opaque, int ret) > +{ > + struct write_info *wr = (struct write_info *)opaque; > + QEMUIOVector *qiov = &wr->qiov; > + if (ret < 0) { > + error_report("error while writing sector %" PRId64 > + ": %s", wr->sector, strerror(-ret)); > + write_ret = ret; > + } > + write_window -= qiov->iov->iov_len / 512; > + qemu_iovec_destroy(qiov); > + g_free(wr); > +} > > static int img_convert(int argc, char **argv) > { > @@ -1019,6 +1042,9 @@ static int img_convert(int argc, char **argv) > should add a specific call to have the info to go faster */ > buf1 = buf; > while (n > 0) { > + while (write_window > IO_WRITE_WINDOW_THRESHOLD / 512) { > + qemu_aio_wait(); > + } > /* If the output image is being created as a copy on write > image, > copy all sectors even the ones containing only NUL bytes, > because they may differ from the sectors in the base image. > @@ -1028,12 +1054,21 @@ static int img_convert(int argc, char **argv) > already there is garbage, not 0s. */ > if (!has_zero_init || out_baseimg || > is_allocated_sectors_min(buf1, n, &n1, min_sparse)) { > - ret = bdrv_write(out_bs, sector_num, buf1, n1); > - if (ret < 0) { > - error_report("error while writing sector %" PRId64 > - ": %s", sector_num, strerror(-ret)); > + QEMUIOVector *qiov; > + struct write_info *wr; > + BlockDriverAIOCB *acb; > + wr = g_malloc0(sizeof(struct write_info)); > + qiov = &wr->qiov; > + qemu_iovec_init(qiov, 1); > + qemu_iovec_add(qiov, (void *)buf1, n1 * 512); > + wr->sector = sector_num; > + acb = bdrv_aio_writev(out_bs, sector_num, qiov, n1, > img_write_cb, wr); > + if (!acb) { > + g_free(wr); > + error_report("I/O error while writing sector %" > PRId64, sector_num); > goto out; > } > + write_window += n1; > } > sector_num += n1; > n -= n1; > @@ -1041,6 +1076,9 @@ static int img_convert(int argc, char **argv) > } > qemu_progress_print(local_progress, 100); > } > + while (write_window > 0) { > + qemu_aio_wait(); > + } > } > out: > qemu_progress_end(); > @@ -1048,6 +1086,7 @@ out: > free_option_parameters(param); > qemu_vfree(buf); > if (out_bs) { > + bdrv_flush(out_bs); > bdrv_delete(out_bs); > } > if (bs) { > -- > 1.7.5.1 > >
[Qemu-devel] [PATCH 35/35] qcow2: fix range check
From: Frediano Ziglio QCowL2Meta::offset is not cluster aligned but only sector aligned however nb_clusters count cluster from cluster start. This fix range check. Note that old code have no corruption issues related to this check cause it only cause intersection to occur when shouldn't. Signed-off-by: Frediano Ziglio Signed-off-by: Kevin Wolf --- block/qcow2-cluster.c | 14 +++--- 1 files changed, 7 insertions(+), 7 deletions(-) diff --git a/block/qcow2-cluster.c b/block/qcow2-cluster.c index 428b5ad..2f76311 100644 --- a/block/qcow2-cluster.c +++ b/block/qcow2-cluster.c @@ -776,17 +776,17 @@ again: */ QLIST_FOREACH(old_alloc, &s->cluster_allocs, next_in_flight) { -uint64_t end_offset = offset + nb_clusters * s->cluster_size; -uint64_t old_offset = old_alloc->offset; -uint64_t old_end_offset = old_alloc->offset + -old_alloc->nb_clusters * s->cluster_size; +uint64_t start = offset >> s->cluster_bits; +uint64_t end = start + nb_clusters; +uint64_t old_start = old_alloc->offset >> s->cluster_bits; +uint64_t old_end = old_start + old_alloc->nb_clusters; -if (end_offset < old_offset || offset > old_end_offset) { +if (end < old_start || start > old_end) { /* No intersection */ } else { -if (offset < old_offset) { +if (start < old_start) { /* Stop at the start of a running allocation */ -nb_clusters = (old_offset - offset) >> s->cluster_bits; +nb_clusters = old_start - start; } else { nb_clusters = 0; } -- 1.7.6
[Qemu-devel] [PATCH 31/35] ide/atapi scsi-disk: Make monitor eject -f, then change work
From: Markus Armbruster change fails while the tray is locked by the guest. eject -f forces it open and removes any media. Unfortunately, the tray closes again instantly. Since the lock remains as it is, there is no way to insert another medium unless the guest voluntarily unlocks. Fix by leaving the tray open after monitor eject. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- blockdev.c |3 ++- hw/ide/core.c |1 + hw/scsi-disk.c |1 + 3 files changed, 4 insertions(+), 1 deletions(-) diff --git a/blockdev.c b/blockdev.c index 154cc84..0827bf7 100644 --- a/blockdev.c +++ b/blockdev.c @@ -635,7 +635,8 @@ static int eject_device(Monitor *mon, BlockDriverState *bs, int force) qerror_report(QERR_DEVICE_NOT_REMOVABLE, bdrv_get_device_name(bs)); return -1; } -if (!force && bdrv_dev_is_medium_locked(bs)) { +if (!force && !bdrv_dev_is_tray_open(bs) +&& bdrv_dev_is_medium_locked(bs)) { qerror_report(QERR_DEVICE_LOCKED, bdrv_get_device_name(bs)); return -1; } diff --git a/hw/ide/core.c b/hw/ide/core.c index 5def25c..9297b9e 100644 --- a/hw/ide/core.c +++ b/hw/ide/core.c @@ -789,6 +789,7 @@ static void ide_cd_change_cb(void *opaque, bool load) IDEState *s = opaque; uint64_t nb_sectors; +s->tray_open = !load; bdrv_get_geometry(s->bs, &nb_sectors); s->nb_sectors = nb_sectors; diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index f5f1d82..4a60820 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -1175,6 +1175,7 @@ static void scsi_destroy(SCSIDevice *dev) static void scsi_cd_change_media_cb(void *opaque, bool load) { +((SCSIDiskState *)opaque)->tray_open = !load; } static bool scsi_cd_is_tray_open(void *opaque) -- 1.7.6
[Qemu-devel] [PATCH 20/35] scsi-disk: Fix START_STOP to fail when it can't eject
From: Markus Armbruster Don't fail when tray is already open. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/scsi-bus.c | 10 ++ hw/scsi-disk.c | 15 +++ hw/scsi.h |4 3 files changed, 25 insertions(+), 4 deletions(-) diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c index 59d6ada..0248294 100644 --- a/hw/scsi-bus.c +++ b/hw/scsi-bus.c @@ -772,6 +772,11 @@ const struct SCSISense sense_code_NO_MEDIUM = { .key = NOT_READY, .asc = 0x3a, .ascq = 0x00 }; +/* LUN not ready, medium removal prevented */ +const struct SCSISense sense_code_NOT_READY_REMOVAL_PREVENTED = { +.key = NOT_READY, .asc = 0x53, .ascq = 0x00 +}; + /* Hardware error, internal target failure */ const struct SCSISense sense_code_TARGET_FAILURE = { .key = HARDWARE_ERROR, .asc = 0x44, .ascq = 0x00 @@ -807,6 +812,11 @@ const struct SCSISense sense_code_INCOMPATIBLE_MEDIUM = { .key = ILLEGAL_REQUEST, .asc = 0x30, .ascq = 0x00 }; +/* Illegal request, medium removal prevented */ +const struct SCSISense sense_code_ILLEGAL_REQ_REMOVAL_PREVENTED = { +.key = ILLEGAL_REQUEST, .asc = 0x53, .ascq = 0x00 +}; + /* Command aborted, I/O process terminated */ const struct SCSISense sense_code_IO_ERROR = { .key = ABORTED_COMMAND, .asc = 0x00, .ascq = 0x06 diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index 4e89bb1..1a49217 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -822,7 +822,7 @@ static int scsi_disk_emulate_read_toc(SCSIRequest *req, uint8_t *outbuf) return toclen; } -static void scsi_disk_emulate_start_stop(SCSIDiskReq *r) +static int scsi_disk_emulate_start_stop(SCSIDiskReq *r) { SCSIRequest *req = &r->req; SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev); @@ -830,12 +830,17 @@ static void scsi_disk_emulate_start_stop(SCSIDiskReq *r) bool loej = req->cmd.buf[4] & 2; /* load on start, eject on !start */ if (s->qdev.type == TYPE_ROM && loej) { -if (!start && s->tray_locked) { -return; +if (!start && !s->tray_open && s->tray_locked) { +scsi_check_condition(r, + bdrv_is_inserted(s->bs) + ? SENSE_CODE(ILLEGAL_REQ_REMOVAL_PREVENTED) + : SENSE_CODE(NOT_READY_REMOVAL_PREVENTED)); +return -1; } bdrv_eject(s->bs, !start); s->tray_open = !start; } +return 0; } static int scsi_disk_emulate_command(SCSIDiskReq *r, uint8_t *outbuf) @@ -883,7 +888,9 @@ static int scsi_disk_emulate_command(SCSIDiskReq *r, uint8_t *outbuf) goto illegal_request; break; case START_STOP: -scsi_disk_emulate_start_stop(r); +if (scsi_disk_emulate_start_stop(r) < 0) { +return -1; +} break; case ALLOW_MEDIUM_REMOVAL: s->tray_locked = req->cmd.buf[4] & 1; diff --git a/hw/scsi.h b/hw/scsi.h index 98fd689..a28cd68 100644 --- a/hw/scsi.h +++ b/hw/scsi.h @@ -136,6 +136,8 @@ extern const struct SCSISense sense_code_NO_SENSE; extern const struct SCSISense sense_code_LUN_NOT_READY; /* LUN not ready, Medium not present */ extern const struct SCSISense sense_code_NO_MEDIUM; +/* LUN not ready, medium removal prevented */ +extern const struct SCSISense sense_code_NOT_READY_REMOVAL_PREVENTED; /* Hardware error, internal target failure */ extern const struct SCSISense sense_code_TARGET_FAILURE; /* Illegal request, invalid command operation code */ @@ -150,6 +152,8 @@ extern const struct SCSISense sense_code_LUN_NOT_SUPPORTED; extern const struct SCSISense sense_code_SAVING_PARAMS_NOT_SUPPORTED; /* Illegal request, Incompatible format */ extern const struct SCSISense sense_code_INCOMPATIBLE_FORMAT; +/* Illegal request, medium removal prevented */ +extern const struct SCSISense sense_code_ILLEGAL_REQ_REMOVAL_PREVENTED; /* Command aborted, I/O process terminated */ extern const struct SCSISense sense_code_IO_ERROR; /* Command aborted, I_T Nexus loss occurred */ -- 1.7.6
[Qemu-devel] [PATCH 15/35] block: Rename bdrv_set_locked() to bdrv_lock_medium()
From: Markus Armbruster While there, make the locked parameter bool. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block.c |8 block.h |2 +- block/raw-posix.c |8 block/raw.c |6 +++--- block_int.h |2 +- hw/ide/atapi.c|2 +- hw/scsi-disk.c|2 +- trace-events |2 +- 8 files changed, 16 insertions(+), 16 deletions(-) diff --git a/block.c b/block.c index 1e4be73..7225b15 100644 --- a/block.c +++ b/block.c @@ -3072,14 +3072,14 @@ void bdrv_eject(BlockDriverState *bs, int eject_flag) * Lock or unlock the media (if it is locked, the user won't be able * to eject it manually). */ -void bdrv_set_locked(BlockDriverState *bs, int locked) +void bdrv_lock_medium(BlockDriverState *bs, bool locked) { BlockDriver *drv = bs->drv; -trace_bdrv_set_locked(bs, locked); +trace_bdrv_lock_medium(bs, locked); -if (drv && drv->bdrv_set_locked) { -drv->bdrv_set_locked(bs, locked); +if (drv && drv->bdrv_lock_medium) { +drv->bdrv_lock_medium(bs, locked); } } diff --git a/block.h b/block.h index 396ca0e..4691090 100644 --- a/block.h +++ b/block.h @@ -212,7 +212,7 @@ int bdrv_is_sg(BlockDriverState *bs); int bdrv_enable_write_cache(BlockDriverState *bs); int bdrv_is_inserted(BlockDriverState *bs); int bdrv_media_changed(BlockDriverState *bs); -void bdrv_set_locked(BlockDriverState *bs, int locked); +void bdrv_lock_medium(BlockDriverState *bs, bool locked); void bdrv_eject(BlockDriverState *bs, int eject_flag); void bdrv_get_format(BlockDriverState *bs, char *buf, int buf_size); BlockDriverState *bdrv_find(const char *name); diff --git a/block/raw-posix.c b/block/raw-posix.c index bcf50b2..a624f56 100644 --- a/block/raw-posix.c +++ b/block/raw-posix.c @@ -1362,7 +1362,7 @@ static void cdrom_eject(BlockDriverState *bs, int eject_flag) } } -static void cdrom_set_locked(BlockDriverState *bs, int locked) +static void cdrom_lock_medium(BlockDriverState *bs, bool locked) { BDRVRawState *s = bs->opaque; @@ -1400,7 +1400,7 @@ static BlockDriver bdrv_host_cdrom = { /* removable device support */ .bdrv_is_inserted = cdrom_is_inserted, .bdrv_eject = cdrom_eject, -.bdrv_set_locked= cdrom_set_locked, +.bdrv_lock_medium = cdrom_lock_medium, /* generic scsi device */ .bdrv_ioctl = hdev_ioctl, @@ -1481,7 +1481,7 @@ static void cdrom_eject(BlockDriverState *bs, int eject_flag) cdrom_reopen(bs); } -static void cdrom_set_locked(BlockDriverState *bs, int locked) +static void cdrom_lock_medium(BlockDriverState *bs, bool locked) { BDRVRawState *s = bs->opaque; @@ -1521,7 +1521,7 @@ static BlockDriver bdrv_host_cdrom = { /* removable device support */ .bdrv_is_inserted = cdrom_is_inserted, .bdrv_eject = cdrom_eject, -.bdrv_set_locked= cdrom_set_locked, +.bdrv_lock_medium = cdrom_lock_medium, }; #endif /* __FreeBSD__ */ diff --git a/block/raw.c b/block/raw.c index f197479..63cf2d3 100644 --- a/block/raw.c +++ b/block/raw.c @@ -85,9 +85,9 @@ static void raw_eject(BlockDriverState *bs, int eject_flag) bdrv_eject(bs->file, eject_flag); } -static void raw_set_locked(BlockDriverState *bs, int locked) +static void raw_lock_medium(BlockDriverState *bs, bool locked) { -bdrv_set_locked(bs->file, locked); +bdrv_lock_medium(bs->file, locked); } static int raw_ioctl(BlockDriverState *bs, unsigned long int req, void *buf) @@ -144,7 +144,7 @@ static BlockDriver bdrv_raw = { .bdrv_is_inserted = raw_is_inserted, .bdrv_media_changed = raw_media_changed, .bdrv_eject = raw_eject, -.bdrv_set_locked= raw_set_locked, +.bdrv_lock_medium = raw_lock_medium, .bdrv_ioctl = raw_ioctl, .bdrv_aio_ioctl = raw_aio_ioctl, diff --git a/block_int.h b/block_int.h index 4f7ff3b..f42af2c 100644 --- a/block_int.h +++ b/block_int.h @@ -120,7 +120,7 @@ struct BlockDriver { int (*bdrv_is_inserted)(BlockDriverState *bs); int (*bdrv_media_changed)(BlockDriverState *bs); void (*bdrv_eject)(BlockDriverState *bs, int eject_flag); -void (*bdrv_set_locked)(BlockDriverState *bs, int locked); +void (*bdrv_lock_medium)(BlockDriverState *bs, bool locked); /* to control generic scsi devices */ int (*bdrv_ioctl)(BlockDriverState *bs, unsigned long int req, void *buf); diff --git a/hw/ide/atapi.c b/hw/ide/atapi.c index afb27c6..06778f3 100644 --- a/hw/ide/atapi.c +++ b/hw/ide/atapi.c @@ -833,7 +833,7 @@ static void cmd_test_unit_ready(IDEState *s, uint8_t *buf) static void cmd_prevent_allow_medium_removal(IDEState *s, uint8_t* buf) { s->tray_locked = buf[4] & 1; -bdrv_set_locked(s->bs, buf[4] & 1); +bdrv_lock_medium(s->bs, buf[4] & 1); ide_atapi_cmd_ok(s); } diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index 42682d0..4e89bb1 100644 --- a/hw/scsi-disk.c +++ b/hw/s
[Qemu-devel] [PATCH 28/35] block: Reset buffer alignment on detach
From: Markus Armbruster BlockDriverState member buffer_alignment is initially 512. The device model may set them, with bdrv_set_buffer_alignment(). If the device model gets detached (hot unplug), the device's alignment is left behind. Only okay because device hot unplug automatically destroys the BlockDriverState. But that's a questionable feature, best not to rely on it. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- block.c |1 + 1 files changed, 1 insertions(+), 0 deletions(-) diff --git a/block.c b/block.c index e986986..b006e58 100644 --- a/block.c +++ b/block.c @@ -788,6 +788,7 @@ void bdrv_detach_dev(BlockDriverState *bs, void *dev) bs->dev = NULL; bs->dev_ops = NULL; bs->dev_opaque = NULL; +bs->buffer_alignment = 512; } /* TODO change to return DeviceState * when all users are qdevified */ -- 1.7.6
[Qemu-devel] [PATCH 12/35] scsi-disk: Track tray locked state
From: Markus Armbruster We already track it in BlockDriverState. Just like tray open/close state, we should track it in the device models instead, because it's device state. Signed-off-by: Markus Armbruster Signed-off-by: Kevin Wolf --- hw/scsi-disk.c |4 +++- 1 files changed, 3 insertions(+), 1 deletions(-) diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c index f35ada4..e7358e3 100644 --- a/hw/scsi-disk.c +++ b/hw/scsi-disk.c @@ -73,6 +73,7 @@ struct SCSIDiskState char *version; char *serial; bool tray_open; +bool tray_locked; }; static int scsi_handle_rw_error(SCSIDiskReq *r, int error, int type); @@ -671,7 +672,7 @@ static int mode_sense_page(SCSIDiskState *s, int page, uint8_t **p_outbuf, p[5] = 0xff; /* CD DA, DA accurate, RW supported, RW corrected, C2 errors, ISRC, UPC, Bar code */ -p[6] = 0x2d | (bdrv_is_locked(s->bs)? 2 : 0); +p[6] = 0x2d | (s->tray_locked ? 2 : 0); /* Locking supported, jumper present, eject, tray */ p[7] = 0; /* no volume & mute control, no changer */ @@ -882,6 +883,7 @@ static int scsi_disk_emulate_command(SCSIDiskReq *r, uint8_t *outbuf) scsi_disk_emulate_start_stop(r); break; case ALLOW_MEDIUM_REMOVAL: +s->tray_locked = req->cmd.buf[4] & 1; bdrv_set_locked(s->bs, req->cmd.buf[4] & 1); break; case READ_CAPACITY_10: -- 1.7.6
[Qemu-devel] [PULL 00/35] Block patches
The following changes since commit 44520db10b1b92f272348ab7028e7afc68ac3edf: Gdbstub: Fix back-trace on SPARC32 (2011-09-10 18:12:35 +) are available in the git repository at: git://repo.or.cz/qemu/kevin.git for-anthony Frediano Ziglio (4): qcow2: removed unused depends_on field qcow2: initialize metadata before inserting in cluster_allocs qcow2: align cluster_data to block to improve performance using O_DIRECT qcow2: fix range check Markus Armbruster (27): ide: Fix ATA command READ to set ATAPI signature for CD-ROM ide: Use a table to declare which drive kinds accept each command ide: Reject ATA commands specific to drive kinds ide/atapi: Clean up misleading name in cmd_start_stop_unit() ide/atapi: Track tray open/close state scsi-disk: Factor out scsi_disk_emulate_start_stop() scsi-disk: Track tray open/close state block: Revert entanglement of bdrv_is_inserted() with tray status block: Drop tray status tracking, no longer used ide/atapi: Track tray locked state scsi-disk: Track tray locked state block: Leave enforcing tray lock to device models block: Drop medium lock tracking, ask device models instead block: Rename bdrv_set_locked() to bdrv_lock_medium() ide/atapi: Don't fail eject when tray is already open scsi-disk: Fix START_STOP to fail when it can't eject ide/atapi: Preserve tray state on migration block: Clean up remaining users of "removable" block: Drop BlockDriverState member removable block: Show whether the virtual tray is open in info block block: Move BlockConf & friends from block_int.h to block.h hw: Trim superfluous #include "block_int.h" block: New bdrv_set_buffer_alignment() block: Reset buffer alignment on detach nbd: Clean up use of block_int.h block: New change_media_cb() parameter load ide/atapi scsi-disk: Make monitor eject -f, then change work Sage Weil (3): rbd: allow client id to be specified in config string rbd: clean up, fix style rbd: fix leak in qemu_rbd_open failure paths Stefan Weil (1): ahci: Remove unused struct member block.c | 104 +--- block.h | 63 +-- block/nbd.c |1 + block/qcow2-cluster.c | 27 block/qcow2.c | 14 ++-- block/qcow2.h |1 - block/raw-posix.c |8 +- block/raw.c |6 +- block/rbd.c | 97 -- block_int.h | 40 + blockdev.c| 10 +-- hw/fdc.c |4 +- hw/ide/ahci.c |2 - hw/ide/ahci.h |1 - hw/ide/atapi.c| 58 -- hw/ide/cmd646.c |1 - hw/ide/core.c | 160 - hw/ide/ich.c |1 - hw/ide/internal.h |3 +- hw/ide/isa.c |1 - hw/ide/macio.c|1 - hw/ide/microdrive.c |1 - hw/ide/mmio.c |1 - hw/ide/pci.c |1 - hw/ide/via.c |1 - hw/lsi53c895a.c |1 - hw/scsi-bus.c | 10 +++ hw/scsi-disk.c| 69 ++--- hw/scsi-generic.c |1 - hw/scsi.h |5 +- hw/sd.c |2 +- hw/virtio-blk.c |3 +- hw/virtio.h |2 +- nbd.c |1 + nbd.h |2 - qmp-commands.hx |2 + trace-events |2 +- 37 files changed, 452 insertions(+), 255 deletions(-)
Re: [Qemu-devel] [PATCH 02/12] nbd: sync API definitions with upstream
Am 08.09.2011 17:24, schrieb Paolo Bonzini: > Signed-off-by: Paolo Bonzini > --- > nbd.c |2 ++ > nbd.h | 11 ++- > 2 files changed, 12 insertions(+), 1 deletions(-) Which upstream? I can't find any NBD version that defines a command/flag for TRIM. Kevin
Re: [Qemu-devel] [PATCH] PPC: Fix via-cuda memory registration
On 09/12/2011 04:46 PM, Lucas Meneghel Rodrigues wrote: On 09/12/2011 06:07 AM, Avi Kivity wrote: On 09/11/2011 02:38 PM, Alexander Graf wrote: Am 11.09.2011 um 12:41 schrieb Avi Kivity: > On 09/08/2011 07:54 PM, Alexander Graf wrote: >> PS: Please test your patches. This one could have been found with an invocation >> as simple as "qemu-system-ppc". We boot into the OpenBIOS prompt by default, >> so you wouldn't even have required a guest image or kernel. >> > > > Sorry about that. > > Note that it's pretty hard to test these patches. I often don't even know which binary as the device->target relationship is not immediately visible, The patch was explicitly to convert ppc ;). Yes, in this case. Not in the general case. > and I don't really know what to expect from the guest. The very easy check-fundamentals thing to do for ppc is to execute qemu-system-ppc without arguments. It should drop you into an OF prompt. Both memory api bugs on ppc I've seen now would have been exposed with that. I agree that we should have something slightly more sophisticated, but doing such a bare minimum test is almost for free to the tester and covers at least basic functionality :). I don't mind people introducibg subtle bugs in corner cases - these things happen. But an abort() when you execute the binary? That really shouldn't happen ever. This one is almost as bad. Yeah. > It would be best if we had a kvm-autotest testset for tcg, it would probably run in just a few minutes and increase confidence in these patches. Yeah, I am using kvm-autotest today for regression testing, but it's very hard to tell it to run multiple different binaries. The target program variable can only be set for an execution job, making it impossible to run multiple targets in one autotest run. Alexander, I've started to work on this, I'm clearing out my request list, last week I've implemented ticket 50, that was related to special block configuration for the tests, now I want to make it possible to support multiple binaries. Probably best to tell autotest about the directory, and let it pick up the binary. Still need some configuration to choose between qemu-kvm and qemu-system-x86_64. Lucas? Yes, that would also work, having different variants with different qemu and qemu-img paths. Those binaries would have to be already pre-built, but then we miss the ability autotest has of building the binaries and prepare the environment. It'd be like: variant1: qemu = /path/to/qemu1 qemu-img = /path/to/qemu-img1 extra_params = "--appropriate --extra --params2" variant2: qemu = /path/to/qemu2 qemu-img = /path/to/qemu-img2 extra_params = "--appropriate --extra --params2" Something like that. It's a feasible intermediate solution until I finish work on supporting multiple userspaces. Another option is, now that the binary name 'qemu' is available for general use, make it possible to invoke everything with just one binary: qemu -system -target mips ... qemu-system -target mips ... qemu-system-mips ... are all equivalent. autotest should easily be able to pass different -target based on the test being run. -- error compiling committee.c: too many arguments to function
Re: [Qemu-devel] [PATCH] PPC: Fix via-cuda memory registration
On 09/12/2011 06:07 AM, Avi Kivity wrote: On 09/11/2011 02:38 PM, Alexander Graf wrote: Am 11.09.2011 um 12:41 schrieb Avi Kivity: > On 09/08/2011 07:54 PM, Alexander Graf wrote: >> PS: Please test your patches. This one could have been found with an invocation >> as simple as "qemu-system-ppc". We boot into the OpenBIOS prompt by default, >> so you wouldn't even have required a guest image or kernel. >> > > > Sorry about that. > > Note that it's pretty hard to test these patches. I often don't even know which binary as the device->target relationship is not immediately visible, The patch was explicitly to convert ppc ;). Yes, in this case. Not in the general case. > and I don't really know what to expect from the guest. The very easy check-fundamentals thing to do for ppc is to execute qemu-system-ppc without arguments. It should drop you into an OF prompt. Both memory api bugs on ppc I've seen now would have been exposed with that. I agree that we should have something slightly more sophisticated, but doing such a bare minimum test is almost for free to the tester and covers at least basic functionality :). I don't mind people introducibg subtle bugs in corner cases - these things happen. But an abort() when you execute the binary? That really shouldn't happen ever. This one is almost as bad. Yeah. > It would be best if we had a kvm-autotest testset for tcg, it would probably run in just a few minutes and increase confidence in these patches. Yeah, I am using kvm-autotest today for regression testing, but it's very hard to tell it to run multiple different binaries. The target program variable can only be set for an execution job, making it impossible to run multiple targets in one autotest run. Alexander, I've started to work on this, I'm clearing out my request list, last week I've implemented ticket 50, that was related to special block configuration for the tests, now I want to make it possible to support multiple binaries. Probably best to tell autotest about the directory, and let it pick up the binary. Still need some configuration to choose between qemu-kvm and qemu-system-x86_64. Lucas? Yes, that would also work, having different variants with different qemu and qemu-img paths. Those binaries would have to be already pre-built, but then we miss the ability autotest has of building the binaries and prepare the environment. It'd be like: variant1: qemu = /path/to/qemu1 qemu-img = /path/to/qemu-img1 extra_params = "--appropriate --extra --params2" variant2: qemu = /path/to/qemu2 qemu-img = /path/to/qemu-img2 extra_params = "--appropriate --extra --params2" Something like that. It's a feasible intermediate solution until I finish work on supporting multiple userspaces.