Re: [Qemu-devel] BUG: 0.14.0 -device usb-host supports only one device

2011-05-17 Thread Gerd Hoffmann

Hi Gerd,

hm, if I add it multiple times and plug in a USB flashdrive, then all
slots are filled up with this device (duplicated)...
And Windows detects them with the result, that the "not first" devices
are marked with a yellow exclamation mark in the device manager.
And the next device plugged in gets then not detected because all
preallocated slots are full :-(

Any ideas?


The upcoming usb patches will add the option to assign devices by 
physical host port, that is probably the best solution for the issue.


I don't have an idea offhand for stable-0.14 though.

cheers,
  Gerd




Re: [Qemu-devel] [PATCH 3/3] powerpc-virtio: virtio support introduced (block, network, serial, balloon, 9p-fs), both fullemu and power-kvm

2011-05-17 Thread Alexander Graf

On 17.05.2011, at 08:47, David Gibson wrote:

> From: Alexey Kardashevskiy 
> 
> The recently added pseries machine does not currently support PCI
> emulation.  For the (upcoming) kvm case, this is quite difficult to do
> because the preferred HV mode for the host kernel does not allow MMIO
> emulation (a hardware limitation).
> 
> Therefore, to support virtio devices, we implement a new virtio setup
> protocol for PAPR guests.  This is based loosely on the s390 and lguest
> methods, using the PAPR hcalls for the virtio primitive operations,
> and the PAPR device tree to advertise the virtio device resources to the
> guest.
> 
> This patch includes support for the virtio block, network, serial, and
> balloon devices, and the 9p filesystem.
> 
> The guest linux kernel should be updated as well in order to
> support a new virtio setup.
> 
> Supported devices are (below are QEMU command line switches):
> 
> - virtio-blk - block device, at the moment works as "IDE":
>usage: -drive file=test-virtio-blk.img,if=ide
> 
> - virtio-net - network device
>usage: -net nic,model=virtio-net
> 
> - virtio-balloon - memory hot-swap device (at the moment of commit, power-kvm
> did not support balloon)
>usage: -device virtio-balloon-spapr
> 
> - virtio-serial - serial bus controller
>usage: -device virtio-serial-spapr \
>   -chardev socket,id=CONSOLE,host=localhost,port=,server,telnet \
>   -device virtconsole,chardev=CONSOLE
>The first switch tells QEMU to create a serial bus device and next
>2 switches create "chardev" and virtual console device connected to
>that "chardev".
> 
> - virtio-9p - plan9 filesystem with ability to work over virtio transport
>usage: -fsdev fstype=local,id=TAG,path=/home/aik/,security_model=none \
>   -device virtio-9p-spapr,fsdev=TAG,mount_tag=TAG
>where TAG is a tag which should be used later when mounting is linux as:
>   mount -t 9p -o trans=virtio TAG /mnt
> 
>Configure for full emulation as:
>   ./configure --target-list=ppc64-softmmu --enable-attr
> 
>Configure for power-kvm as:
>   ./configure --enable-kvm  --target-list=ppc64-softmmu --enable-fdt \
>--cc="gcc -m64" \
>--kerneldir=/root/kheaders --enable-io-thread --enable-attr
> 
> Note: --enable-attr is required for 9p support. On ppc64 systems, libattr
> should be compiled and installed manually as it is not distributes in
> 64bit packages.

Before including such a patch, we should really discuss the desired interface 
for virtio on sPAPR. I personally would prefer if we could have a generic MMIO 
hypercall that the guest issues, so that we can simply use virtio-pci on sPAPR 
(and all the other PCI hardware).

But at the end of the day, the steps should be as follows:

  1) Discuss this on the virtualization ML
  2) Send patches for the virtio documentation so the protocol has a spec 
(which we're lacking for s390 still)
  3) Implement Linux side, upstream it
  4) Upstream Qemu side

Since I haven't seen 1-3, I'd like to defer this patch until the other points 
are good :)


Alex




Re: [Qemu-devel] [PATCH 12/18] usb-linux: split large xfers

2011-05-17 Thread Gerd Hoffmann

  Hi,


More specifically:
http://www.mail-archive.com/qemu-devel@nongnu.org/msg30337.html


Reference added to the commit message.

cheers,
  Gerd




Re: [Qemu-devel] [PATCH 00/26] q35 chipset support for native pci express support

2011-05-17 Thread Jan Kiszka
On 2011-05-16 23:55, Adnan Khaleel wrote:
> I finally got this work after I realised that the AHCI driver was not being 
> loaded in my disk image and that ACHI was not being enabled in the Seabios 
> .config file.
> This is really good work Yamahata, thanks.
> 
> 
> As far as I can tell, everything works like the stock Qemu 0.14 except 
> networking. The guest OS sees the network device and initialises it but I 
> think the Qemu DHCP server/firewall never gets back, since the network device 
> doesn't even get a 10.0.2.15 ip address during bootup and the guest dhcp 
> client never gets an ip address, 
> 
> 
> eth0   device: Intel Corporation 82540EM Gigabit Ethernet Controller (rev 03)
> eth0   Starting DHCP4 client. . . . . . . .
> eth0   DHCP4 continues in background 
> eth0   device: Intel Corporation 82540EM Gigabit Ethernet Controller (rev 03)
> eth0   DHCP4 client (dhcpcd) is running
> eth0   . . . but is still waiting for data
> eth0   interface could not be set up until now
> 
> 
> So doing an ifconfig later on just shows
> 
> 
> eth0   Link encap:Ethernet  HWaddr 52:54:00:12:34:56
>  UP BROADCAST MULTICAST  MTU:1500  Metric:1
>  RX packets:0 errors:0 dropped:0 overruns:0 frame:0
>  TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
>  collisions:0 txqueuelen:1000
>  RX bytes:0 (0.0 b)   TX bytes:0 (0.0 b)
> 
> 
> 
> lo  Link encap:Local loopback  
>  inet addr:127.0.0.1  Mask:255.0.0.0
>  inet6 addr: ::1/128 Scope:Host
>  UP LOOPBACK RUNING  MTU:16436  Metric:1
>  RX packets:0 errors:0 dropped:0 overruns:0 frame:0
>  TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
>  collisions:0 txqueuelen:1000
>  RX bytes:0 (0.0 b)   TX bytes:0 (0.0 b)
> 
> 
> I'm going to start a separate thread to see what the possible cause might be 
> and what might be the best way to debug this. Do you have any idea if this 
> q35 chipset going to be committed to Qemu upstream?

I've recently hacked a bit on q35, rebased it over current master, found
and fixed a few bugs to allow booting of WinXP and Win7, and
particularly added kvm support to improve testability significantly. You
can find my current work at

git://git.kiszka.org/qemu.git q35-test
git://git.kiszka.org/seabios.git q35-test

There are some issues remaining, e.g. usb appeared broken to me. Now I
just tested your scenario (e1000+usernet) with a Win7 guest, and I do
not get an IP either. There is no traffic on the vlan (I attached a dump
device to verify). Looking closer, it seems PCI bar mapping is failing,
at least partially, see 'info pci'. I hope it's not yet another ACPI
issue. Fixing the polarity bug already forced me to dig way too deep
into this horrible domain.

Jan

-- 
Siemens AG, Corporate Technology, CT T DE IT 1
Corporate Competence Center Embedded Linux



[Qemu-devel] KVM guest doesn't recongize its network by NAT

2011-05-17 Thread Ryan Wang
Hi all,

I created one guest on Ubuntu 10.10:
=
sudo virt-install --connect qemu:///system -n ubuntu-10.10-guest -r 1024
--vcpus=1 -c /tmp/ubuntu-10.10-desktop-i386.iso --os-type=linux
--disk=/var/lib/libvirt/images/ubuntu-10.10-guest.img,size=10 --vnc
--accelerate

After the installation done, I can see the virtual network adapters on host:
=
virbr0Link encap:Ethernet  HWaddr fe:54:00:43:f2:f2
  inet addr:192.168.122.1  Bcast:192.168.122.255  Mask:255.255.255.0
  inet6 addr: fe80::9cfc:d9ff:fe82:f273/64 Scope:Link
  UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
  RX packets:0 errors:0 dropped:0 overruns:0 frame:0
  TX packets:61 errors:0 dropped:0 overruns:0 carrier:0
  collisions:0 txqueuelen:0
  RX bytes:0 (0.0 B)  TX bytes:10802 (10.8 KB)
...
vnet0 Link encap:Ethernet  HWaddr fe:54:00:43:f2:f2
  inet6 addr: fe80::fc54:ff:fe43:f2f2/64 Scope:Link
  UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
  RX packets:0 errors:0 dropped:0 overruns:0 frame:0
  TX packets:100 errors:0 dropped:0 overruns:0 carrier:0
  collisions:0 txqueuelen:500
  RX bytes:0 (0.0 B)  TX bytes:9325 (9.3 KB)


sudo iptables -t nat -L
=
Chain POSTROUTING (policy ACCEPT)
target prot opt source   destination
MASQUERADE  tcp  --  192.168.122.0/24!192.168.122.0/24masq
ports: 1024-65535
MASQUERADE  udp  --  192.168.122.0/24!192.168.122.0/24masq
ports: 1024-65535
MASQUERADE  all  --  192.168.122.0/24!192.168.122.0/24



But on guest, I can only see the lo network.

Does anyone know how to configure KVM with NAT?

thanks,


Re: [Qemu-devel] [PATCH 18/18] usb: add ehci adapter

2011-05-17 Thread Gerd Hoffmann

On 05/16/11 13:56, Gerd Hoffmann wrote:

This patch finally merges the EHCI host adapter aka USB 2.0 support.

Based on git://git.kiszka.org/qemu.git ehci

Changes:
   - Adapt to recent changes in the usb subsystem.
   - Don't create device automagically, use -device instead.
   - Add quickstart text file, see docs/usb2.txt.
   - A bunch of codestyle fixups.
   - Add authors+contributers list.
   - Zap EHCI_NOMICROFRAMES, qemu can't handle a 8 kHz
 wakeup rate anyway.
   - A few bug fixes.

Signed-off-by: Gerd Hoffmann


As someone who spent a significant amount of time working on the EHCI
code last year I am absolutely not ok with this. The entire contribution
history for EHCI lost - and for no reason.


There is a reason.  I've tried to keep the history, but it was a big 
mess with conflicts and build errors due to ehci being out-of-tree for a 
loong time.



The inclusion of EHCI into
qemu can be done in such a way as to maintain the history.


Prove it.  Give me a git tree with ehci history I can use as replacement 
for patch 18 and I'll pull it in.


cheers,
  Gerd



Re: [Qemu-devel] [PATCH 00/18] usb patch queue: add usb 2.0

2011-05-17 Thread Gerd Hoffmann

  Hi,


git://git.kraxel.org/qemu usb.11.pull


Cool! I'm glad to see someone actively working in this space.

Any specific areas where testing would be helpful?


All over the place ;)

Current state:

usb device emulation:
  - usb-storage should work fine on high speed.
  - all others do either emulate 1.1 devices (hid for example)
or are not yet updated (net for example).

usb passthrough (linux):
  - my usb sticks seem to work ok, didn't test that much though,
also seeing resets now and then, better don't play with sticks
holding important data ...
  - the lenovo t500 internal usb camera doesn't work.

Known issues:

"lsusb -v" in the guest often hangs when it tries to query the (not 
existing) debug descriptor.  Most likely a flaw in the ehci error 
handling, maybe not raising a error IRQ where it should.


cheers,
  Gerd




Re: [Qemu-devel] [regression] qemu-system-arm: segfault in lsi_do_command

2011-05-17 Thread Kevin Wolf
Am 16.05.2011 18:26, schrieb Paolo Bonzini:
> On 05/16/2011 05:58 PM, Kevin Wolf wrote:
>> Thanks. Still doesn't make much sense to me, the patch shouldn't change
>> anything with respect to a malloc, but I can reproduce a segfault now. I
>> think I'll have a closer look tomorrow.
> 
> This fixes it on top of my SCSI refactoring series.  Should I send v3
> with this one squashed in appropriately?  Or should this be sent later?

I think I would just include it in your series (and while you're at it,
I think you could include Jonathan's cleanup as well).

Kevin



Re: [Qemu-devel] Why does -device qxl-vga not suppress default vga?

2011-05-17 Thread Markus Armbruster
Jan Kiszka  writes:

> On 2011-05-16 09:28, Gerd Hoffmann wrote:
>> On 05/13/11 16:18, Markus Armbruster wrote:
>>> VGA, cirrus-vga and vmware-svga do.  Gerd, you added it (commit
>>> a19cbfb3), care to explain?
>> 
>> Just forgot to add it to the list when merging.
>> I'll go stuff a patch into the spice patch queue.
>> 
>> Does "-device VGA" work these days btw?
>> Last time I tries it didn't due to some init order issues.
>
> I've (mostly) fixed the PAM/SMRAM stuff that still breaks this. Will
> post the series soon.

Good to know, thanks!



[Qemu-devel] Invitation to connect on LinkedIn

2011-05-17 Thread Paulo Silva via LinkedIn
LinkedIn
Paulo Silva requested to add you as a connection on LinkedIn:
--

Jiajun,

I'd like to add you to my professional network on LinkedIn.

- Paulo

Accept invitation from Paulo Silva
http://www.linkedin.com/e/-kkb1ec-gnsl5q5u-64/qTMmi8QEI_f3FNXUkL1mvZgy00BGYniwg3/blk/I127323819_11/1BpC5vrmRLoRZcjkkZt5YCpnlOt3RApnhMpmdzgmhxrSNBszYNclYVcjwPczcTcz59bTtUe5sOt35FbPkVc38Uc3kMej8LrCBxbOYWrSlI/EML_comm_afe/

View invitation from Paulo Silva
http://www.linkedin.com/e/-kkb1ec-gnsl5q5u-64/qTMmi8QEI_f3FNXUkL1mvZgy00BGYniwg3/blk/I127323819_11/34NnPANe3cOcPsOckALqnpPbOYWrSlI/svi/

--

Why might connecting with Paulo Silva be a good idea?

Have a question? Paulo Silva's network will probably have an answer:
You can use LinkedIn Answers to distribute your professional questions to Paulo 
Silva and your extended network. You can get high-quality answers from 
experienced professionals.

http://www.linkedin.com/e/-kkb1ec-gnsl5q5u-64/ash/inv19_ayn/

 
-- 
(c) 2011, LinkedIn Corporation

Re: [Qemu-devel] [RFC Patch 1/3]Qemu: Enhance "info block" to display cache setting

2011-05-17 Thread Kevin Wolf
Am 16.05.2011 20:10, schrieb Supriya Kannery:
> Enhance "info block" to display cache setting
> 
> Example:
> (qemu) info block
> ide0-hd0: type=hd removable=0 file=../rhel6-32.qcow2 ro=0 drv=qcow2 
> encrypted=0
> 
> Enhanced to include "cache" setting:
> (qemu) info block
> ide0-hd0: type=hd removable=0 cache=none file=../rhel6-32.qcow2 ro=0 
> drv=qcow2 encrypted=0
> 
> Signed-off-by: Supriya Kannery 
> Signed-off-by: Prerna Saxena 
> 
> ---
>  block.c |   18 --
>  1 file changed, 16 insertions(+), 2 deletions(-)
> 
> Index: qemu/block.c
> ===
> --- qemu.orig/block.c
> +++ qemu/block.c
> @@ -1713,6 +1713,19 @@ static void bdrv_print_dict(QObject *obj
>  monitor_printf(mon, " locked=%d", qdict_get_bool(bs_dict, "locked"));
>  }
>  
> +if (qdict_haskey(bs_dict, "open_flags")) {
> +int open_flags = qdict_get_int(bs_dict, "open_flags");
> +if (open_flags & BDRV_O_NOCACHE) {
> +monitor_printf(mon, " cache=none");
> +} else if (open_flags & BDRV_O_CACHE_WB) {
> +if (open_flags & BDRV_O_NO_FLUSH)
> +monitor_printf(mon, " cache=unsafe");
> +else
> +monitor_printf(mon, " cache=writeback");
> +} else
> +monitor_printf(mon, " cache=writethrough");
> +}
> +
>  if (qdict_haskey(bs_dict, "inserted")) {
>  QDict *qdict = qobject_to_qdict(qdict_get(bs_dict, "inserted"));
>  
> @@ -1762,9 +1775,10 @@ void bdrv_info(Monitor *mon, QObject **r
>  }
>  
>  bs_obj = qobject_from_jsonf("{ 'device': %s, 'type': %s, "
> -"'removable': %i, 'locked': %i }",
> +"'removable': %i, 'locked': %i, "
> +"'open_flags': %d }",
>  bs->device_name, type, bs->removable,
> -bs->locked);
> +bs->locked, bs->open_flags);
>  
>  if (bs->drv) {
>  QObject *obj;

bs->open_flags is a purely internal thing and its meaning is not
guaranteed to be stable. Exposing it to the user is wrong.

Kevin



Re: [Qemu-devel] [RFC Patch 1/3]Qemu: Enhance "info block" to display cache setting

2011-05-17 Thread supriya kannery

Kevin Wolf wrote:

Am 16.05.2011 20:10, schrieb Supriya Kannery:
  

Enhance "info block" to display cache setting

Example:
(qemu) info block
ide0-hd0: type=hd removable=0 file=../rhel6-32.qcow2 ro=0 drv=qcow2 
encrypted=0


Enhanced to include "cache" setting:
(qemu) info block
ide0-hd0: type=hd removable=0 cache=none file=../rhel6-32.qcow2 ro=0 
drv=qcow2 encrypted=0





 
 bs_obj = qobject_from_jsonf("{ 'device': %s, 'type': %s, "

-"'removable': %i, 'locked': %i }",
+"'removable': %i, 'locked': %i, "
+"'open_flags': %d }",
 bs->device_name, type, bs->removable,
-bs->locked);
+bs->locked, bs->open_flags);
 
 if (bs->drv) {

 QObject *obj;



bs->open_flags is a purely internal thing and its meaning is not
guaranteed to be stable. Exposing it to the user is wrong.

  

ok. Pls suggest what could a better approach to expose the cache setting.

Kevin

  





Re: [Qemu-devel] [RFC Patch 0/3]Qemu: Enable dynamic cache change through qemu monitor

2011-05-17 Thread supriya kannery

Christoph Hellwig wrote:
Why are you even trying this again?  
Enabling control of cache setting from qemu monitor will help 
users/admins to

accomplish cache value change without depending on the guest.

As explained very clearly last time you
can't change from a writeback-style to a write-through style I/O from
the monitor without creating massive data integrity problems.  See my
patchset that allows changing this from the guest for how it should be
done - I just need to get back and revisit the virtio protocol support
for it.


  

ok, sure, I will go through your related patches and work further on this.




Re: [Qemu-devel] [RFC Patch 0/3]Qemu: Enable dynamic cache change through qemu monitor

2011-05-17 Thread supriya kannery

Anthony Liguori wrote:

On 05/16/2011 03:23 PM, Christoph Hellwig wrote:
Why are you even trying this again?  As explained very clearly last 
time you

can't change from a writeback-style to a write-through style I/O from
the monitor without creating massive data integrity problems.


To further clarify:

Today cache=none|writethrough|writeback does two things.  It:

1) Changes the WCE flag that's visible to the guest

2) Determines whether the host page cache is used for doing guest I/O

As Christoph is very correct in pointing out, we cannot change (1) at 
run time because this is guest visible.  You will break a guest if you 
do this.



ok
But it's still desirable to be able to change (2) at run time.  Before 
we can do this properly though, we need to separate out the logic for 
setting (1) vs. (2).



Will go through the code in detail to understand handling of (1) and (2).
And ideally, we would allow (1) to be changed by the guest itself at 
run time which allows for full dynamic control.  This is what he's 
referring to below.


Regards,

Anthony Liguori

  See my

patchset that allows changing this from the guest for how it should be
done - I just need to get back and revisit the virtio protocol support
for it.










[Qemu-devel] [PATCH] ccid-card-emulated: handle no backend (fixes segfault)

2011-05-17 Thread Alon Levy
During initialization if no "backend=something" attribute is supplied
don't try to call strcmp with second argument being NULL.

Signed-off-by: Alon Levy 
---
 hw/ccid-card-emulated.c |3 +++
 1 files changed, 3 insertions(+), 0 deletions(-)

diff --git a/hw/ccid-card-emulated.c b/hw/ccid-card-emulated.c
index 0b07184..ba56dca 100644
--- a/hw/ccid-card-emulated.c
+++ b/hw/ccid-card-emulated.c
@@ -476,6 +476,9 @@ static uint32_t parse_enumeration(char *str,
 {
 uint32_t ret = not_found_value;
 
+if (!str) {
+return ret;
+}
 while (table->name != NULL) {
 if (strcmp(table->name, str) == 0) {
 ret = table->value;
-- 
1.7.5.1




Re: [Qemu-devel] Should new USB devices such as usb-ccid support legacy -usbdevice?

2011-05-17 Thread Kevin Wolf
Am 16.05.2011 10:33, schrieb Markus Armbruster:
> Anthony Liguori  writes:
> 
>> On 05/13/2011 11:36 AM, Markus Armbruster wrote:
>>> When Gerd qdevified USB, he kept legacy -usbdevice working (commit
>>> 0958b4cc...).  What about new USB devices?  Should they get a legacy
>>> syntax, too?
>>>
>>> The only existing new device is usb-ccid, and it got one in commit
>>> 36707144.
>>
>> What keeps -usbdevice from being a light wrapper to -device such that
>> no future code is needed for this?
> 
> What would that buy us?  Inhowfar is -usbdevice any lighter than
> -device?

One difference is that it automagically gives you an USB host
controller, whereas with -device you need to specify one explicitly.

Kevin



[Qemu-devel] [PATCH v3 00/21] SCSI subsystem improvements

2011-05-17 Thread Paolo Bonzini
This series includes the following improvements to the SCSI subsystem:

1) introduction of SCSIBusOps that generalize the existing
command_complete callback;

2) widespread use of the SCSIRequest abstraction, with simpler memory
management (refcounting) and with various common idioms converted into
simple C functions instead of duplicating them all over the place;

3) support for autosense.

Some patches are from Hannes Reinecke's megasas patchset posted last
November, forward ported and applied to the new vSCSI controller as
well.

I already planned the following two series too:

1) adding support for zerocopy.  Previous attempts were rejected
because they were applied to real devices (thus making for example an
IOMMU hard to impossible).  However, for PV devices zerocopy should be
uncontroversial---and it is a must to get competitive performance WRT
virtio-blk.  I'll use vmw-pvscsi for the first implementation and for
benchmarking.

2) adding support for multiple LUNs.  I plan to add a fake "scsi-target"
device for this.

After this I'll work on the virtio-scsi device model.

Testing:
- RHEL6.1 install complete to scsi-disk with lsi, from scsi-generic CD
- iozone run with lsi on scsi-disk target
- RHEL6.1 install to usb-msd from IDE CD is too slow, but it manages to
  format /boot in ~10 minutes with or without the patch
- RHEL6.1 install started with vscsi, from scsi-generic CD including
  playing with opening/closing the tray (to exercise autosense), complete
  test not done yet

esp is only compile tested.

Please review and apply; I do not think this should go in through the
block branch.

v2->v3:
included fixes for Jonathan Nieder's recently reported bug

v1->v2:
rebased, added patch 21

Hannes Reinecke (4):
  scsi: Use 'SCSIRequest' directly
  scsi: Update sense code handling
  scsi: Implement 'get_sense' callback
  scsi-disk: add data direction checking

Paolo Bonzini (17):
  scsi: add tracing of scsi requests
  scsi-generic: Remove bogus double complete
  scsi: introduce scsi_req_data
  scsi: introduce SCSIBusOps
  scsi: reference-count requests
  lsi: extract lsi_find_by_tag
  scsi: commonize purging requests
  scsi: introduce scsi_req_abort
  scsi: introduce scsi_req_cancel
  scsi: use scsi_req_complete
  scsi: do not call send_command directly
  scsi: introduce scsi_req_new
  scsi: introduce scsi_req_kick
  scsi: introduce scsi_req_get_buf
  scsi: make write_data return void
  scsi-generic: Handle queue full
  scsi: split command_complete callback in two

 hw/esp.c  |  111 +-
 hw/lsi53c895a.c   |  189 +++---
 hw/scsi-bus.c |  209 +++---
 hw/scsi-disk.c|  264 ++---
 hw/scsi-generic.c |  218 +---
 hw/scsi.h |   91 ++
 hw/spapr_vscsi.c  |  180 
 hw/usb-msd.c  |  118 ++--
 trace-events  |8 ++
 9 files changed, 836 insertions(+), 552 deletions(-)

-- 
1.7.4.4




[Qemu-devel] [PATCH v3 02/21] scsi-generic: Remove bogus double complete

2011-05-17 Thread Paolo Bonzini
scsi-generic scsi_read_complete() should not -both- call the client
complete callback with SCSI_REASON_DATA -and- call
scsi_command_complete().  The former will cause the client to queue a
new read or write request, while the later will free the request data
structure, thus causing the new read or write request to use a
freed/stale structure when it completes.

This patch fixes the bug, fixing a crash with scsi-generic & RHEL5.5
installer.

Cc: Benjamin Herrenschmidt 
Cc: David Gibson 
Signed-off-by: Paolo Bonzini 
---
 hw/scsi-generic.c |6 --
 1 files changed, 4 insertions(+), 2 deletions(-)

diff --git a/hw/scsi-generic.c b/hw/scsi-generic.c
index 9be1cca..102f1da 100644
--- a/hw/scsi-generic.c
+++ b/hw/scsi-generic.c
@@ -172,9 +172,11 @@ static void scsi_read_complete(void * opaque, int ret)
 DPRINTF("Data ready tag=0x%x len=%d\n", r->req.tag, len);
 
 r->len = -1;
-r->req.bus->complete(r->req.bus, SCSI_REASON_DATA, r->req.tag, len);
-if (len == 0)
+if (len == 0) {
 scsi_command_complete(r, 0);
+} else {
+r->req.bus->complete(r->req.bus, SCSI_REASON_DATA, r->req.tag, len);
+}
 }
 
 /* Read more data from scsi device into buffer.  */
-- 
1.7.4.4





[Qemu-devel] [PATCH v3 04/21] scsi: introduce SCSIBusOps

2011-05-17 Thread Paolo Bonzini
There are more operations than a SCSI bus can handle, besides completing
commands.  One example, which this series will introduce, is cleaning up
after a request is cancelled.

More long term, a "SCSI bus" can represent the LUNs attached to a
target; in this case, while all commands will ultimately reach a logical
unit, it is the target who is in charge of answering REPORT LUNs.

Signed-off-by: Paolo Bonzini 
---
 hw/esp.c  |6 +-
 hw/lsi53c895a.c   |6 +-
 hw/scsi-bus.c |   12 ++--
 hw/scsi-generic.c |2 +-
 hw/scsi.h |   13 +++--
 hw/spapr_vscsi.c  |6 +-
 hw/usb-msd.c  |6 +-
 7 files changed, 34 insertions(+), 17 deletions(-)

diff --git a/hw/esp.c b/hw/esp.c
index fa9d2a2..d8bba7a 100644
--- a/hw/esp.c
+++ b/hw/esp.c
@@ -714,6 +714,10 @@ void esp_init(target_phys_addr_t espaddr, int it_shift,
 *dma_enable = qdev_get_gpio_in(dev, 1);
 }
 
+static struct SCSIBusOps esp_scsi_ops = {
+.complete = esp_command_complete
+};
+
 static int esp_init1(SysBusDevice *dev)
 {
 ESPState *s = FROM_SYSBUS(ESPState, dev);
@@ -728,7 +732,7 @@ static int esp_init1(SysBusDevice *dev)
 
 qdev_init_gpio_in(&dev->qdev, esp_gpio_demux, 2);
 
-scsi_bus_new(&s->bus, &dev->qdev, 0, ESP_MAX_DEVS, esp_command_complete);
+scsi_bus_new(&s->bus, &dev->qdev, 0, ESP_MAX_DEVS, &esp_scsi_ops);
 return scsi_bus_legacy_handle_cmdline(&s->bus);
 }
 
diff --git a/hw/lsi53c895a.c b/hw/lsi53c895a.c
index 2ce38a9..ccea6ad 100644
--- a/hw/lsi53c895a.c
+++ b/hw/lsi53c895a.c
@@ -2205,6 +2205,10 @@ static int lsi_scsi_uninit(PCIDevice *d)
 return 0;
 }
 
+static struct SCSIBusOps lsi_scsi_ops = {
+.complete = lsi_command_complete
+};
+
 static int lsi_scsi_init(PCIDevice *dev)
 {
 LSIState *s = DO_UPCAST(LSIState, dev, dev);
@@ -2241,7 +2245,7 @@ static int lsi_scsi_init(PCIDevice *dev)
PCI_BASE_ADDRESS_SPACE_MEMORY, lsi_ram_mapfunc);
 QTAILQ_INIT(&s->queue);
 
-scsi_bus_new(&s->bus, &dev->qdev, 1, LSI_MAX_DEVS, lsi_command_complete);
+scsi_bus_new(&s->bus, &dev->qdev, 1, LSI_MAX_DEVS, &lsi_scsi_ops);
 if (!dev->qdev.hotplugged) {
 return scsi_bus_legacy_handle_cmdline(&s->bus);
 }
diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index 0afe3fb..63d9a68 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -21,13 +21,13 @@ static int next_scsi_bus;
 
 /* Create a scsi bus, and attach devices to it.  */
 void scsi_bus_new(SCSIBus *bus, DeviceState *host, int tcq, int ndev,
-  scsi_completionfn complete)
+  SCSIBusOps *ops)
 {
 qbus_create_inplace(&bus->qbus, &scsi_bus_info, host, NULL);
 bus->busnr = next_scsi_bus++;
 bus->tcq = tcq;
 bus->ndev = ndev;
-bus->complete = complete;
+bus->ops = *ops;
 bus->qbus.allow_hotplug = 1;
 }
 
@@ -498,7 +498,7 @@ static const char *scsi_command_name(uint8_t cmd)
 void scsi_req_data(SCSIRequest *req, int len)
 {
 trace_scsi_req_data(req->dev->id, req->lun, req->tag, len);
-req->bus->complete(req->bus, SCSI_REASON_DATA, req->tag, len);
+req->bus->ops.complete(req->bus, SCSI_REASON_DATA, req->tag, len);
 }
 
 void scsi_req_print(SCSIRequest *req)
@@ -533,9 +533,9 @@ void scsi_req_complete(SCSIRequest *req)
 {
 assert(req->status != -1);
 scsi_req_dequeue(req);
-req->bus->complete(req->bus, SCSI_REASON_DONE,
-   req->tag,
-   req->status);
+req->bus->ops.complete(req->bus, SCSI_REASON_DONE,
+   req->tag,
+   req->status);
 }
 
 static char *scsibus_get_fw_dev_path(DeviceState *dev)
diff --git a/hw/scsi-generic.c b/hw/scsi-generic.c
index e4f1f30..3db734a 100644
--- a/hw/scsi-generic.c
+++ b/hw/scsi-generic.c
@@ -335,7 +335,7 @@ static int32_t scsi_send_command(SCSIDevice *d, uint32_t 
tag,
 s->senselen = 7;
 s->driver_status = SG_ERR_DRIVER_SENSE;
 bus = scsi_bus_from_device(d);
-bus->complete(bus, SCSI_REASON_DONE, tag, CHECK_CONDITION);
+bus->ops.complete(bus, SCSI_REASON_DONE, tag, CHECK_CONDITION);
 return 0;
 }
 
diff --git a/hw/scsi.h b/hw/scsi.h
index 7c09f32..d1753f9 100644
--- a/hw/scsi.h
+++ b/hw/scsi.h
@@ -16,10 +16,9 @@ enum scsi_reason {
 };
 
 typedef struct SCSIBus SCSIBus;
+typedef struct SCSIBusOps SCSIBusOps;
 typedef struct SCSIDevice SCSIDevice;
 typedef struct SCSIDeviceInfo SCSIDeviceInfo;
-typedef void (*scsi_completionfn)(SCSIBus *bus, int reason, uint32_t tag,
-  uint32_t arg);
 
 enum SCSIXferMode {
 SCSI_XFER_NONE,  /*  TEST_UNIT_READY, ...*/
@@ -74,20 +73,22 @@ struct SCSIDeviceInfo {
 uint8_t *(*get_buf)(SCSIDevice *s, uint32_t tag);
 };
 
-typedef void (*SCSIAttachFn)(DeviceState *host, BlockDriverState *bdrv,
-  int unit);
+struct SCSIBusOps {
+void (*complete)(SCSIBus *bus, int reason, uint32_t tag, uint32_t arg);
+};
+
 struct SCSIBus {

[Qemu-devel] [PATCH v3 01/21] scsi: add tracing of scsi requests

2011-05-17 Thread Paolo Bonzini
Signed-off-by: Paolo Bonzini 
---
 hw/scsi-bus.c |6 ++
 trace-events  |6 ++
 2 files changed, 12 insertions(+), 0 deletions(-)

diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index ceeb4ec..0fd85fc 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -4,6 +4,7 @@
 #include "scsi-defs.h"
 #include "qdev.h"
 #include "blockdev.h"
+#include "trace.h"
 
 static char *scsibus_get_fw_dev_path(DeviceState *dev);
 
@@ -141,6 +142,7 @@ SCSIRequest *scsi_req_alloc(size_t size, SCSIDevice *d, 
uint32_t tag, uint32_t l
 req->lun = lun;
 req->status = -1;
 req->enqueued = true;
+trace_scsi_req_alloc(req->dev->id, req->lun, req->tag);
 QTAILQ_INSERT_TAIL(&d->requests, req, next);
 return req;
 }
@@ -159,6 +161,7 @@ SCSIRequest *scsi_req_find(SCSIDevice *d, uint32_t tag)
 
 static void scsi_req_dequeue(SCSIRequest *req)
 {
+trace_scsi_req_dequeue(req->dev->id, req->lun, req->tag);
 if (req->enqueued) {
 QTAILQ_REMOVE(&req->dev->requests, req, next);
 req->enqueued = false;
@@ -195,6 +198,7 @@ static int scsi_req_length(SCSIRequest *req, uint8_t *cmd)
 req->cmd.len = 12;
 break;
 default:
+trace_scsi_req_parse_bad(req->dev->id, req->lun, req->tag, cmd[0]);
 return -1;
 }
 
@@ -392,6 +396,8 @@ int scsi_req_parse(SCSIRequest *req, uint8_t *buf)
 memcpy(req->cmd.buf, buf, req->cmd.len);
 scsi_req_xfer_mode(req);
 req->cmd.lba = scsi_req_lba(req);
+trace_scsi_req_parsed(req->dev->id, req->lun, req->tag, buf[0],
+  req->cmd.mode, req->cmd.xfer, req->cmd.lba);
 return 0;
 }
 
diff --git a/trace-events b/trace-events
index a00b63c..55f89b4 100644
--- a/trace-events
+++ b/trace-events
@@ -205,6 +205,12 @@ disable usb_set_config(int addr, int config, int ret) "dev 
%d, config %d, ret %d
 disable usb_clear_device_feature(int addr, int feature, int ret) "dev %d, 
feature %d, ret %d"
 disable usb_set_device_feature(int addr, int feature, int ret) "dev %d, 
feature %d, ret %d"
 
+# hw/scsi-bus.c
+disable scsi_req_alloc(int target, int lun, int tag) "target %d lun %d tag %d"
+disable scsi_req_dequeue(int target, int lun, int tag) "target %d lun %d tag 
%d"
+disable scsi_req_parsed(int target, int lun, int tag, int cmd, int mode, int 
xfer, uint64_t lba) "target %d lun %d tag %d command %d dir %d length %d lba 
%"PRIu64""
+disable scsi_req_parse_bad(int target, int lun, int tag, int cmd) "target %d 
lun %d tag %d command %d"
+
 # vl.c
 disable vm_state_notify(int running, int reason) "running %d reason %d"
 
-- 
1.7.4.4





[Qemu-devel] [PATCH v3 09/21] scsi: introduce scsi_req_abort

2011-05-17 Thread Paolo Bonzini
This covers the case of canceling a request's I/O and still
completing it.

Signed-off-by: Paolo Bonzini 
---
 hw/scsi-bus.c|9 +
 hw/scsi.h|1 +
 hw/spapr_vscsi.c |8 ++--
 3 files changed, 12 insertions(+), 6 deletions(-)

diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index e1bb494..1d7da9e 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -548,6 +548,15 @@ void scsi_req_complete(SCSIRequest *req)
 scsi_req_unref(req);
 }
 
+void scsi_req_abort(SCSIRequest *req, int status)
+{
+req->status = status;
+if (req->dev && req->dev->info->cancel_io) {
+req->dev->info->cancel_io(req);
+}
+scsi_req_complete(req);
+}
+
 void scsi_device_purge_requests(SCSIDevice *sdev)
 {
 SCSIRequest *req;
diff --git a/hw/scsi.h b/hw/scsi.h
index dee8567..6221fff 100644
--- a/hw/scsi.h
+++ b/hw/scsi.h
@@ -114,6 +114,7 @@ int scsi_req_parse(SCSIRequest *req, uint8_t *buf);
 void scsi_req_print(SCSIRequest *req);
 void scsi_req_data(SCSIRequest *req, int len);
 void scsi_req_complete(SCSIRequest *req);
+void scsi_req_abort(SCSIRequest *req, int status);
 void scsi_device_purge_requests(SCSIDevice *sdev);
 
 #endif
diff --git a/hw/spapr_vscsi.c b/hw/spapr_vscsi.c
index cf2ed73..678cd00 100644
--- a/hw/spapr_vscsi.c
+++ b/hw/spapr_vscsi.c
@@ -463,10 +463,8 @@ static void vscsi_send_request_sense(VSCSIState *s, 
vscsi_req *req)
 dprintf("VSCSI: Queued request sense tag 0x%x\n", req->qtag);
 if (n < 0) {
 fprintf(stderr, "VSCSI: REQUEST_SENSE wants write data !?!?!?\n");
-sdev->info->cancel_io(req->sreq);
 vscsi_makeup_sense(s, req, HARDWARE_ERROR, 0, 0);
-vscsi_send_rsp(s, req, CHECK_CONDITION, 0, 0);
-vscsi_put_req(s, req);
+scsi_req_abort(req->sreq, CHECK_CONDITION);
 return;
 } else if (n == 0) {
 return;
@@ -547,10 +545,8 @@ static void vscsi_command_complete(SCSIRequest *sreq, int 
reason, uint32_t arg)
 }
 if (rc < 0) {
 fprintf(stderr, "VSCSI: RDMA error rc=%d!\n", rc);
-sdev->info->cancel_io(sreq);
 vscsi_makeup_sense(s, req, HARDWARE_ERROR, 0, 0);
-vscsi_send_rsp(s, req, CHECK_CONDITION, 0, 0);
-vscsi_put_req(s, req);
+scsi_req_abort(req->sreq, CHECK_CONDITION);
 return;
 }
 
-- 
1.7.4.4





[Qemu-devel] [PATCH v3 12/21] scsi: Update sense code handling

2011-05-17 Thread Paolo Bonzini
From: Hannes Reinecke 

The SCSI spec has a quite detailed list of sense codes available.
It even mandates the use of specific ones for some failure cases.
The current implementation just has one type of generic error
which is actually a violation of the spec in certain cases.
This patch introduces various predefined sense codes to have the
sense code reporting more in line with the spec.

On top of Hannes's patch I fixed the reply to REQUEST SENSE commands
with DESC=0 and a small (<18) length.

Signed-off-by: Hannes Reinecke 
Signed-off-by: Paolo Bonzini 
Cc: Christoph Hellwig 
---
 hw/scsi-bus.c |   91 -
 hw/scsi-disk.c|   82 ++-
 hw/scsi-generic.c |   63 -
 hw/scsi.h |   39 ++-
 4 files changed, 208 insertions(+), 67 deletions(-)

diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index 6a8ea0b..b83dd88 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -154,7 +154,7 @@ void scsi_req_enqueue(SCSIRequest *req)
 QTAILQ_INSERT_TAIL(&req->dev->requests, req, next);
 }
 
-void scsi_req_dequeue(SCSIRequest *req)
+static void scsi_req_dequeue(SCSIRequest *req)
 {
 trace_scsi_req_dequeue(req->dev->id, req->lun, req->tag);
 if (req->enqueued) {
@@ -398,6 +398,95 @@ int scsi_req_parse(SCSIRequest *req, uint8_t *buf)
 return 0;
 }
 
+/*
+ * Predefined sense codes
+ */
+
+/* No sense data available */
+const struct SCSISense sense_code_NO_SENSE = {
+.key = NO_SENSE , .asc = 0x00 , .ascq = 0x00
+};
+
+/* LUN not ready, Manual intervention required */
+const struct SCSISense sense_code_LUN_NOT_READY = {
+.key = NOT_READY, .asc = 0x04, .ascq = 0x03
+};
+
+/* LUN not ready, Medium not present */
+const struct SCSISense sense_code_NO_MEDIUM = {
+.key = NOT_READY, .asc = 0x3a, .ascq = 0x00
+};
+
+/* Hardware error, internal target failure */
+const struct SCSISense sense_code_TARGET_FAILURE = {
+.key = HARDWARE_ERROR, .asc = 0x44, .ascq = 0x00
+};
+
+/* Illegal request, invalid command operation code */
+const struct SCSISense sense_code_INVALID_OPCODE = {
+.key = ILLEGAL_REQUEST, .asc = 0x20, .ascq = 0x00
+};
+
+/* Illegal request, LBA out of range */
+const struct SCSISense sense_code_LBA_OUT_OF_RANGE = {
+.key = ILLEGAL_REQUEST, .asc = 0x21, .ascq = 0x00
+};
+
+/* Illegal request, Invalid field in CDB */
+const struct SCSISense sense_code_INVALID_FIELD = {
+.key = ILLEGAL_REQUEST, .asc = 0x24, .ascq = 0x00
+};
+
+/* Illegal request, LUN not supported */
+const struct SCSISense sense_code_LUN_NOT_SUPPORTED = {
+.key = ILLEGAL_REQUEST, .asc = 0x25, .ascq = 0x00
+};
+
+/* Command aborted, I/O process terminated */
+const struct SCSISense sense_code_IO_ERROR = {
+.key = ABORTED_COMMAND, .asc = 0x00, .ascq = 0x06
+};
+
+/* Command aborted, I_T Nexus loss occurred */
+const struct SCSISense sense_code_I_T_NEXUS_LOSS = {
+.key = ABORTED_COMMAND, .asc = 0x29, .ascq = 0x07
+};
+
+/* Command aborted, Logical Unit failure */
+const struct SCSISense sense_code_LUN_FAILURE = {
+.key = ABORTED_COMMAND, .asc = 0x3e, .ascq = 0x01
+};
+
+/*
+ * scsi_build_sense
+ *
+ * Build a sense buffer
+ */
+int scsi_build_sense(SCSISense sense, uint8_t *buf, int len, int fixed)
+{
+if (!fixed && len < 8) {
+return 0;
+}
+
+memset(buf, 0, len);
+if (fixed) {
+/* Return fixed format sense buffer */
+buf[0] = 0xf0;
+buf[2] = sense.key;
+buf[7] = 7;
+buf[12] = sense.asc;
+buf[13] = sense.ascq;
+return MIN(len, 18);
+} else {
+/* Return descriptor format sense buffer */
+buf[0] = 0x72;
+buf[1] = sense.key;
+buf[2] = sense.asc;
+buf[3] = sense.ascq;
+return 8;
+}
+}
+
 static const char *scsi_command_name(uint8_t cmd)
 {
 static const char *names[] = {
diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c
index 0921c62..a82753f 100644
--- a/hw/scsi-disk.c
+++ b/hw/scsi-disk.c
@@ -49,10 +49,6 @@ do { fprintf(stderr, "scsi-disk: " fmt , ## __VA_ARGS__); } 
while (0)
 
 typedef struct SCSIDiskState SCSIDiskState;
 
-typedef struct SCSISense {
-uint8_t key;
-} SCSISense;
-
 typedef struct SCSIDiskReq {
 SCSIRequest req;
 /* ??? We should probably keep track of whether the data transfer is
@@ -109,24 +105,19 @@ static void scsi_disk_clear_sense(SCSIDiskState *s)
 memset(&s->sense, 0, sizeof(s->sense));
 }
 
-static void scsi_disk_set_sense(SCSIDiskState *s, uint8_t key)
-{
-s->sense.key = key;
-}
-
-static void scsi_req_set_status(SCSIDiskReq *r, int status, int sense_code)
+static void scsi_req_set_status(SCSIDiskReq *r, int status, SCSISense sense)
 {
 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
 
 r->req.status = status;
-scsi_disk_set_sense(s, sense_code);
+s->sense = sense;
 }
 
 /* Helper function for command completion.  */
-static void scsi_command_com

[Qemu-devel] [PATCH v3 03/21] scsi: introduce scsi_req_data

2011-05-17 Thread Paolo Bonzini
This abstracts calling the command_complete callback, reducing churn
in the following patches.

Signed-off-by: Paolo Bonzini 
---
 hw/scsi-bus.c |6 ++
 hw/scsi-disk.c|8 
 hw/scsi-generic.c |6 +++---
 hw/scsi.h |1 +
 trace-events  |1 +
 5 files changed, 15 insertions(+), 7 deletions(-)

diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index 0fd85fc..0afe3fb 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -495,6 +495,12 @@ static const char *scsi_command_name(uint8_t cmd)
 return names[cmd];
 }
 
+void scsi_req_data(SCSIRequest *req, int len)
+{
+trace_scsi_req_data(req->dev->id, req->lun, req->tag, len);
+req->bus->complete(req->bus, SCSI_REASON_DATA, req->tag, len);
+}
+
 void scsi_req_print(SCSIRequest *req)
 {
 FILE *fp = stderr;
diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c
index b05e654..2b5dc2a 100644
--- a/hw/scsi-disk.c
+++ b/hw/scsi-disk.c
@@ -167,7 +167,7 @@ static void scsi_read_complete(void * opaque, int ret)
 n = r->iov.iov_len / 512;
 r->sector += n;
 r->sector_count -= n;
-r->req.bus->complete(r->req.bus, SCSI_REASON_DATA, r->req.tag, 
r->iov.iov_len);
+scsi_req_data(&r->req, r->iov.iov_len);
 }
 
 
@@ -179,7 +179,7 @@ static void scsi_read_request(SCSIDiskReq *r)
 if (r->sector_count == (uint32_t)-1) {
 DPRINTF("Read buf_len=%zd\n", r->iov.iov_len);
 r->sector_count = 0;
-r->req.bus->complete(r->req.bus, SCSI_REASON_DATA, r->req.tag, 
r->iov.iov_len);
+scsi_req_data(&r->req, r->iov.iov_len);
 return;
 }
 DPRINTF("Read sector_count=%d\n", r->sector_count);
@@ -242,7 +242,7 @@ static int scsi_handle_rw_error(SCSIDiskReq *r, int error, 
int type)
 vm_stop(VMSTOP_DISKFULL);
 } else {
 if (type == SCSI_REQ_STATUS_RETRY_READ) {
-r->req.bus->complete(r->req.bus, SCSI_REASON_DATA, r->req.tag, 0);
+scsi_req_data(&r->req, 0);
 }
 scsi_command_complete(r, CHECK_CONDITION,
 HARDWARE_ERROR);
@@ -278,7 +278,7 @@ static void scsi_write_complete(void * opaque, int ret)
 }
 r->iov.iov_len = len;
 DPRINTF("Write complete tag=0x%x more=%d\n", r->req.tag, len);
-r->req.bus->complete(r->req.bus, SCSI_REASON_DATA, r->req.tag, len);
+scsi_req_data(&r->req, len);
 }
 }
 
diff --git a/hw/scsi-generic.c b/hw/scsi-generic.c
index 102f1da..e4f1f30 100644
--- a/hw/scsi-generic.c
+++ b/hw/scsi-generic.c
@@ -175,7 +175,7 @@ static void scsi_read_complete(void * opaque, int ret)
 if (len == 0) {
 scsi_command_complete(r, 0);
 } else {
-r->req.bus->complete(r->req.bus, SCSI_REASON_DATA, r->req.tag, len);
+scsi_req_data(&r->req, len);
 }
 }
 
@@ -212,7 +212,7 @@ static void scsi_read_data(SCSIDevice *d, uint32_t tag)
 DPRINTF("Sense: %d %d %d %d %d %d %d %d\n",
 r->buf[0], r->buf[1], r->buf[2], r->buf[3],
 r->buf[4], r->buf[5], r->buf[6], r->buf[7]);
-r->req.bus->complete(r->req.bus, SCSI_REASON_DATA, r->req.tag, 
s->senselen);
+scsi_req_data(&r->req, s->senselen);
 return;
 }
 
@@ -263,7 +263,7 @@ static int scsi_write_data(SCSIDevice *d, uint32_t tag)
 
 if (r->len == 0) {
 r->len = r->buflen;
-r->req.bus->complete(r->req.bus, SCSI_REASON_DATA, r->req.tag, r->len);
+scsi_req_data(&r->req, r->len);
 return 0;
 }
 
diff --git a/hw/scsi.h b/hw/scsi.h
index d3b5d56..7c09f32 100644
--- a/hw/scsi.h
+++ b/hw/scsi.h
@@ -105,6 +105,7 @@ void scsi_req_free(SCSIRequest *req);
 
 int scsi_req_parse(SCSIRequest *req, uint8_t *buf);
 void scsi_req_print(SCSIRequest *req);
+void scsi_req_data(SCSIRequest *req, int len);
 void scsi_req_complete(SCSIRequest *req);
 
 #endif
diff --git a/trace-events b/trace-events
index 55f89b4..98e7b2d 100644
--- a/trace-events
+++ b/trace-events
@@ -207,6 +207,7 @@ disable usb_set_device_feature(int addr, int feature, int 
ret) "dev %d, feature
 
 # hw/scsi-bus.c
 disable scsi_req_alloc(int target, int lun, int tag) "target %d lun %d tag %d"
+disable scsi_req_data(int target, int lun, int tag, int len) "target %d lun %d 
tag %d len %d"
 disable scsi_req_dequeue(int target, int lun, int tag) "target %d lun %d tag 
%d"
 disable scsi_req_parsed(int target, int lun, int tag, int cmd, int mode, int 
xfer, uint64_t lba) "target %d lun %d tag %d command %d dir %d length %d lba 
%"PRIu64""
 disable scsi_req_parse_bad(int target, int lun, int tag, int cmd) "target %d 
lun %d tag %d command %d"
-- 
1.7.4.4





[Qemu-devel] [PATCH v3 07/21] scsi: Use 'SCSIRequest' directly

2011-05-17 Thread Paolo Bonzini
From: Hannes Reinecke 

Currently the SCSIRequest structure is abstracted away and cannot accessed
directly from the driver. This requires the handler to do a lookup on
an abstract 'tag' which identifies the SCSIRequest structure.

With this patch the SCSIRequest structure is exposed to the driver. This
allows use to use it directly as an argument to the SCSIDeviceInfo
callback functions and remove the lookup.

A new callback function 'alloc_req' is introduced matching 'free
req'; unref'ing to free up resources after use is moved into the
scsi_command_complete callbacks.

This temporarily introduces a leak of requests that are cancelled,
when they are removed from the queue and not from the driver.  This
is fixed later by introducing scsi_req_cancel.  That patch in turn
depends on this one, because the argument to scsi_req_cancel is a
SCSIRequest.

Signed-off-by: Hannes Reinecke 
Signed-off-by: Paolo Bonzini 
Cc: Christoph Hellwig 
---
 hw/esp.c  |   29 -
 hw/lsi53c895a.c   |   56 +++---
 hw/scsi-bus.c |   24 ---
 hw/scsi-disk.c|  116 ++--
 hw/scsi-generic.c |  107 +++--
 hw/scsi.h |   21 +-
 hw/spapr_vscsi.c  |   44 +++-
 hw/usb-msd.c  |   27 +++-
 8 files changed, 172 insertions(+), 252 deletions(-)

diff --git a/hw/esp.c b/hw/esp.c
index d8bba7a..096f4dc 100644
--- a/hw/esp.c
+++ b/hw/esp.c
@@ -65,6 +65,7 @@ struct ESPState {
 uint32_t dma;
 SCSIBus bus;
 SCSIDevice *current_dev;
+SCSIRequest *current_req;
 uint8_t cmdbuf[TI_BUFSZ];
 uint32_t cmdlen;
 uint32_t do_cmd;
@@ -209,7 +210,7 @@ static uint32_t get_cmd(ESPState *s, uint8_t *buf)
 
 if (s->current_dev) {
 /* Started a new command before the old one finished.  Cancel it.  */
-s->current_dev->info->cancel_io(s->current_dev, 0);
+s->current_dev->info->cancel_io(s->current_req);
 s->async_len = 0;
 }
 
@@ -230,9 +231,10 @@ static void do_busid_cmd(ESPState *s, uint8_t *buf, 
uint8_t busid)
 int32_t datalen;
 int lun;
 
-DPRINTF("do_busid_cmd: busid 0x%x\n", busid);
+ DPRINTF("do_busid_cmd: busid 0x%x\n", busid);
 lun = busid & 7;
-datalen = s->current_dev->info->send_command(s->current_dev, 0, buf, lun);
+s->current_req = s->current_dev->info->alloc_req(s->current_dev, 0, lun);
+datalen = s->current_dev->info->send_command(s->current_req, buf);
 s->ti_size = datalen;
 if (datalen != 0) {
 s->rregs[ESP_RSTAT] = STAT_TC;
@@ -240,10 +242,10 @@ static void do_busid_cmd(ESPState *s, uint8_t *buf, 
uint8_t busid)
 s->dma_counter = 0;
 if (datalen > 0) {
 s->rregs[ESP_RSTAT] |= STAT_DI;
-s->current_dev->info->read_data(s->current_dev, 0);
+s->current_dev->info->read_data(s->current_req);
 } else {
 s->rregs[ESP_RSTAT] |= STAT_DO;
-s->current_dev->info->write_data(s->current_dev, 0);
+s->current_dev->info->write_data(s->current_req);
 }
 }
 s->rregs[ESP_RINTR] = INTR_BS | INTR_FC;
@@ -372,9 +374,9 @@ static void esp_do_dma(ESPState *s)
 if (s->async_len == 0) {
 if (to_device) {
 // ti_size is negative
-s->current_dev->info->write_data(s->current_dev, 0);
+s->current_dev->info->write_data(s->current_req);
 } else {
-s->current_dev->info->read_data(s->current_dev, 0);
+s->current_dev->info->read_data(s->current_req);
 /* If there is still data to be read from the device then
complete the DMA operation immediately.  Otherwise defer
until the scsi layer has completed.  */
@@ -388,10 +390,9 @@ static void esp_do_dma(ESPState *s)
 }
 }
 
-static void esp_command_complete(SCSIBus *bus, int reason, uint32_t tag,
- uint32_t arg)
+static void esp_command_complete(SCSIRequest *req, int reason, uint32_t arg)
 {
-ESPState *s = DO_UPCAST(ESPState, busdev.qdev, bus->qbus.parent);
+ESPState *s = DO_UPCAST(ESPState, busdev.qdev, req->bus->qbus.parent);
 
 if (reason == SCSI_REASON_DONE) {
 DPRINTF("SCSI Command complete\n");
@@ -405,11 +406,15 @@ static void esp_command_complete(SCSIBus *bus, int 
reason, uint32_t tag,
 s->sense = arg;
 s->rregs[ESP_RSTAT] = STAT_ST;
 esp_dma_done(s);
-s->current_dev = NULL;
+   if (s->current_req) {
+scsi_req_unref(s->current_req);
+s->current_req = NULL;
+s->current_dev = NULL;
+   }
 } else {
 DPRINTF("transfer %d/%d\n", s->dma_left, s->ti_size);
 s->async_len = arg;
-s->async_buf = s->current_dev->info->get_buf(s->current_dev, 0);
+s->async_buf = s->current_dev->info->get_buf(req);
 if (s->dma_left) {
 esp_do_dma(s);

[Qemu-devel] [PATCH v3 14/21] scsi: introduce scsi_req_new

2011-05-17 Thread Paolo Bonzini
Signed-off-by: Paolo Bonzini 
---
 hw/esp.c |2 +-
 hw/lsi53c895a.c  |3 +--
 hw/scsi-bus.c|5 +
 hw/scsi.h|1 +
 hw/spapr_vscsi.c |2 +-
 hw/usb-msd.c |2 +-
 6 files changed, 10 insertions(+), 5 deletions(-)

diff --git a/hw/esp.c b/hw/esp.c
index 3a65aed..ad364b5 100644
--- a/hw/esp.c
+++ b/hw/esp.c
@@ -244,7 +244,7 @@ static void do_busid_cmd(ESPState *s, uint8_t *buf, uint8_t 
busid)
 
  DPRINTF("do_busid_cmd: busid 0x%x\n", busid);
 lun = busid & 7;
-s->current_req = s->current_dev->info->alloc_req(s->current_dev, 0, lun);
+s->current_req = scsi_req_new(s->current_dev, 0, lun);
 datalen = scsi_req_enqueue(s->current_req, buf);
 s->ti_size = datalen;
 if (datalen != 0) {
diff --git a/hw/lsi53c895a.c b/hw/lsi53c895a.c
index b2dbcaa..e2af25f 100644
--- a/hw/lsi53c895a.c
+++ b/hw/lsi53c895a.c
@@ -788,8 +788,7 @@ static void lsi_do_command(LSIState *s)
 assert(s->current == NULL);
 s->current = qemu_mallocz(sizeof(lsi_request));
 s->current->tag = s->select_tag;
-s->current->req = dev->info->alloc_req(dev, s->current->tag,
-   s->current_lun);
+s->current->req = scsi_req_new(dev, s->current->tag, s->current_lun);
 
 n = scsi_req_enqueue(s->current->req, buf);
 if (n > 0) {
diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index 0b54a4c..c091159 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -146,6 +146,11 @@ SCSIRequest *scsi_req_alloc(size_t size, SCSIDevice *d, 
uint32_t tag, uint32_t l
 return req;
 }
 
+SCSIRequest *scsi_req_new(SCSIDevice *d, uint32_t tag, uint32_t lun)
+{
+return d->info->alloc_req(d, tag, lun);
+}
+
 int32_t scsi_req_enqueue(SCSIRequest *req, uint8_t *buf)
 {
 int32_t rc;
diff --git a/hw/scsi.h b/hw/scsi.h
index c36c5cc..e44c194 100644
--- a/hw/scsi.h
+++ b/hw/scsi.h
@@ -143,6 +143,7 @@ int scsi_build_sense(SCSISense sense, uint8_t *buf, int 
len, int fixed);
 int scsi_sense_valid(SCSISense sense);
 
 SCSIRequest *scsi_req_alloc(size_t size, SCSIDevice *d, uint32_t tag, uint32_t 
lun);
+SCSIRequest *scsi_req_new(SCSIDevice *d, uint32_t tag, uint32_t lun);
 int32_t scsi_req_enqueue(SCSIRequest *req, uint8_t *buf);
 void scsi_req_free(SCSIRequest *req);
 SCSIRequest *scsi_req_ref(SCSIRequest *req);
diff --git a/hw/spapr_vscsi.c b/hw/spapr_vscsi.c
index 307a17f..1bb4bf4 100644
--- a/hw/spapr_vscsi.c
+++ b/hw/spapr_vscsi.c
@@ -653,7 +653,7 @@ static int vscsi_queue_cmd(VSCSIState *s, vscsi_req *req)
 
 req->sdev = sdev;
 req->lun = lun;
-req->sreq = sdev->info->alloc_req(sdev, req->qtag, lun);
+req->sreq = scsi_req_new(sdev, req->qtag, lun);
 n = scsi_req_enqueue(req->sreq, srp->cmd.cdb);
 
 dprintf("VSCSI: Queued command tag 0x%x CMD 0x%x ID %d LUN %d ret: %d\n",
diff --git a/hw/usb-msd.c b/hw/usb-msd.c
index 1375e82..c52e394 100644
--- a/hw/usb-msd.c
+++ b/hw/usb-msd.c
@@ -377,7 +377,7 @@ static int usb_msd_handle_data(USBDevice *dev, USBPacket *p)
 s->tag, cbw.flags, cbw.cmd_len, s->data_len);
 s->residue = 0;
 s->scsi_len = 0;
-s->req = s->scsi_dev->info->alloc_req(s->scsi_dev, s->tag, 0);
+s->req = scsi_req_new(s->scsi_dev, s->tag, 0);
 scsi_req_enqueue(s->req, cbw.cmd);
 /* ??? Should check that USB and SCSI data transfer
directions match.  */
-- 
1.7.4.4





[Qemu-devel] [PATCH v3 13/21] scsi: do not call send_command directly

2011-05-17 Thread Paolo Bonzini
Move the common part of scsi-disk.c and scsi-generic.c to the SCSI layer.
At the same time, protect against the request being freed under the
feet of the send_command callback.

This fixes a use-after-free that happened when scsi-disk's
scsi_disk_emulate_command completed an illegal request, and still its
caller scsi_send_command accessed r->sector_count and r->iov.iov_len.
The return value from scsi_send_command was then bogus; the HBA device
model mistook the completed request for an I/O request and typically
SIGSEGVed on a NULL pointer access to the current request.

Reported-by: Jonathan Nieder 
Tested-by: Jonathan Nieder 
Signed-off-by: Paolo Bonzini 
---
 hw/esp.c  |2 +-
 hw/lsi53c895a.c   |2 +-
 hw/scsi-bus.c |9 -
 hw/scsi-disk.c|1 -
 hw/scsi-generic.c |1 -
 hw/scsi.h |2 +-
 hw/spapr_vscsi.c  |4 ++--
 hw/usb-msd.c  |2 +-
 8 files changed, 14 insertions(+), 9 deletions(-)

diff --git a/hw/esp.c b/hw/esp.c
index 46157a8..3a65aed 100644
--- a/hw/esp.c
+++ b/hw/esp.c
@@ -245,7 +245,7 @@ static void do_busid_cmd(ESPState *s, uint8_t *buf, uint8_t 
busid)
  DPRINTF("do_busid_cmd: busid 0x%x\n", busid);
 lun = busid & 7;
 s->current_req = s->current_dev->info->alloc_req(s->current_dev, 0, lun);
-datalen = s->current_dev->info->send_command(s->current_req, buf);
+datalen = scsi_req_enqueue(s->current_req, buf);
 s->ti_size = datalen;
 if (datalen != 0) {
 s->rregs[ESP_RSTAT] = STAT_TC;
diff --git a/hw/lsi53c895a.c b/hw/lsi53c895a.c
index f78b85f..b2dbcaa 100644
--- a/hw/lsi53c895a.c
+++ b/hw/lsi53c895a.c
@@ -791,7 +791,7 @@ static void lsi_do_command(LSIState *s)
 s->current->req = dev->info->alloc_req(dev, s->current->tag,
s->current_lun);
 
-n = dev->info->send_command(s->current->req, buf);
+n = scsi_req_enqueue(s->current->req, buf);
 if (n > 0) {
 lsi_set_phase(s, PHASE_DI);
 dev->info->read_data(s->current->req);
diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index b83dd88..0b54a4c 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -146,12 +146,19 @@ SCSIRequest *scsi_req_alloc(size_t size, SCSIDevice *d, 
uint32_t tag, uint32_t l
 return req;
 }
 
-void scsi_req_enqueue(SCSIRequest *req)
+int32_t scsi_req_enqueue(SCSIRequest *req, uint8_t *buf)
 {
+int32_t rc;
 assert(!req->enqueued);
 scsi_req_ref(req);
 req->enqueued = true;
 QTAILQ_INSERT_TAIL(&req->dev->requests, req, next);
+
+/* Make sure the request doesn't disappear under send_command's feet.  */
+scsi_req_ref(req);
+rc = req->dev->info->send_command(req, buf);
+scsi_req_unref(req);
+return rc;
 }
 
 static void scsi_req_dequeue(SCSIRequest *req)
diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c
index a82753f..efb953b 100644
--- a/hw/scsi-disk.c
+++ b/hw/scsi-disk.c
@@ -982,7 +982,6 @@ static int32_t scsi_send_command(SCSIRequest *req, uint8_t 
*buf)
 uint8_t *outbuf;
 int rc;
 
-scsi_req_enqueue(req);
 command = buf[0];
 outbuf = (uint8_t *)r->iov.iov_base;
 is_write = 0;
diff --git a/hw/scsi-generic.c b/hw/scsi-generic.c
index b934ba4..036ab9f 100644
--- a/hw/scsi-generic.c
+++ b/hw/scsi-generic.c
@@ -318,7 +318,6 @@ static int32_t scsi_send_command(SCSIRequest *req, uint8_t 
*cmd)
 SCSIGenericReq *r = DO_UPCAST(SCSIGenericReq, req, req);
 int ret;
 
-scsi_req_enqueue(req);
 if (cmd[0] != REQUEST_SENSE &&
 (req->lun != s->lun || (cmd[1] >> 5) != s->lun)) {
 DPRINTF("Unimplemented LUN %d\n", req->lun ? req->lun : cmd[1] >> 5);
diff --git a/hw/scsi.h b/hw/scsi.h
index 61ab7c9..c36c5cc 100644
--- a/hw/scsi.h
+++ b/hw/scsi.h
@@ -143,7 +143,7 @@ int scsi_build_sense(SCSISense sense, uint8_t *buf, int 
len, int fixed);
 int scsi_sense_valid(SCSISense sense);
 
 SCSIRequest *scsi_req_alloc(size_t size, SCSIDevice *d, uint32_t tag, uint32_t 
lun);
-void scsi_req_enqueue(SCSIRequest *req);
+int32_t scsi_req_enqueue(SCSIRequest *req, uint8_t *buf);
 void scsi_req_free(SCSIRequest *req);
 SCSIRequest *scsi_req_ref(SCSIRequest *req);
 void scsi_req_unref(SCSIRequest *req);
diff --git a/hw/spapr_vscsi.c b/hw/spapr_vscsi.c
index 5b97a83..307a17f 100644
--- a/hw/spapr_vscsi.c
+++ b/hw/spapr_vscsi.c
@@ -459,7 +459,7 @@ static void vscsi_send_request_sense(VSCSIState *s, 
vscsi_req *req)
 cdb[4] = 96;
 cdb[5] = 0;
 req->sensing = 1;
-n = sdev->info->send_command(req->sreq, cdb);
+n = scsi_req_enqueue(req->sreq, cdb);
 dprintf("VSCSI: Queued request sense tag 0x%x\n", req->qtag);
 if (n < 0) {
 fprintf(stderr, "VSCSI: REQUEST_SENSE wants write data !?!?!?\n");
@@ -654,7 +654,7 @@ static int vscsi_queue_cmd(VSCSIState *s, vscsi_req *req)
 req->sdev = sdev;
 req->lun = lun;
 req->sreq = sdev->info->alloc_req(sdev, req->qtag, lun);
-n = sdev->info->send_command(req->sreq, srp->cmd.cdb);
+n = scsi_req_enqueue(req->sreq, srp->cmd.cdb);
 
 

[Qemu-devel] [PATCH v3 06/21] lsi: extract lsi_find_by_tag

2011-05-17 Thread Paolo Bonzini
Signed-off-by: Paolo Bonzini 
---
 hw/lsi53c895a.c |   63 +-
 1 files changed, 38 insertions(+), 25 deletions(-)

diff --git a/hw/lsi53c895a.c b/hw/lsi53c895a.c
index ccea6ad..3b67155 100644
--- a/hw/lsi53c895a.c
+++ b/hw/lsi53c895a.c
@@ -652,38 +652,51 @@ static void lsi_reselect(LSIState *s, lsi_request *p)
 }
 }
 
-/* Record that data is available for a queued command.  Returns zero if
-   the device was reselected, nonzero if the IO is deferred.  */
-static int lsi_queue_tag(LSIState *s, uint32_t tag, uint32_t arg)
+static lsi_request *lsi_find_by_tag(LSIState *s, uint32_t tag)
 {
 lsi_request *p;
 
 QTAILQ_FOREACH(p, &s->queue, next) {
 if (p->tag == tag) {
-if (p->pending) {
-BADF("Multiple IO pending for tag %d\n", tag);
-}
-p->pending = arg;
-/* Reselect if waiting for it, or if reselection triggers an IRQ
-   and the bus is free.
-   Since no interrupt stacking is implemented in the emulation, it
-   is also required that there are no pending interrupts waiting
-   for service from the device driver. */
-if (s->waiting == 1 ||
-(lsi_irq_on_rsl(s) && !(s->scntl1 & LSI_SCNTL1_CON) &&
- !(s->istat0 & (LSI_ISTAT0_SIP | LSI_ISTAT0_DIP {
-/* Reselect device.  */
-lsi_reselect(s, p);
-return 0;
-} else {
-DPRINTF("Queueing IO tag=0x%x\n", tag);
-p->pending = arg;
-return 1;
-}
+return p;
 }
 }
-BADF("IO with unknown tag %d\n", tag);
-return 1;
+
+return NULL;
+}
+
+/* Record that data is available for a queued command.  Returns zero if
+   the device was reselected, nonzero if the IO is deferred.  */
+static int lsi_queue_tag(LSIState *s, uint32_t tag, uint32_t arg)
+{
+lsi_request *p;
+
+p = lsi_find_by_tag(s, tag);
+if (!p) {
+BADF("IO with unknown tag %d\n", tag);
+return 1;
+}
+
+if (p->pending) {
+BADF("Multiple IO pending for tag %d\n", tag);
+}
+p->pending = arg;
+/* Reselect if waiting for it, or if reselection triggers an IRQ
+   and the bus is free.
+   Since no interrupt stacking is implemented in the emulation, it
+   is also required that there are no pending interrupts waiting
+   for service from the device driver. */
+if (s->waiting == 1 ||
+(lsi_irq_on_rsl(s) && !(s->scntl1 & LSI_SCNTL1_CON) &&
+ !(s->istat0 & (LSI_ISTAT0_SIP | LSI_ISTAT0_DIP {
+/* Reselect device.  */
+lsi_reselect(s, p);
+return 0;
+} else {
+DPRINTF("Queueing IO tag=0x%x\n", tag);
+p->pending = arg;
+return 1;
+}
 }
 
 /* Callback to indicate that the SCSI layer has completed a transfer.  */
-- 
1.7.4.4





[Qemu-devel] [PATCH v3 11/21] scsi: use scsi_req_complete

2011-05-17 Thread Paolo Bonzini
Signed-off-by: Paolo Bonzini 
---
 hw/scsi-generic.c |5 ++---
 1 files changed, 2 insertions(+), 3 deletions(-)

diff --git a/hw/scsi-generic.c b/hw/scsi-generic.c
index 5bfbb8a..e1f8a8a 100644
--- a/hw/scsi-generic.c
+++ b/hw/scsi-generic.c
@@ -288,7 +288,6 @@ static int32_t scsi_send_command(SCSIRequest *req, uint8_t 
*cmd)
 {
 SCSIGenericState *s = DO_UPCAST(SCSIGenericState, qdev, req->dev);
 SCSIGenericReq *r = DO_UPCAST(SCSIGenericReq, req, req);
-SCSIBus *bus;
 int ret;
 
 scsi_req_enqueue(req);
@@ -305,8 +304,8 @@ static int32_t scsi_send_command(SCSIRequest *req, uint8_t 
*cmd)
 s->sensebuf[6] = 0x00;
 s->senselen = 7;
 s->driver_status = SG_ERR_DRIVER_SENSE;
-bus = scsi_bus_from_device(&s->qdev);
-bus->ops.complete(req, SCSI_REASON_DONE, CHECK_CONDITION);
+r->req.status = CHECK_CONDITION;
+scsi_req_complete(&r->req);
 return 0;
 }
 
-- 
1.7.4.4





[Qemu-devel] [PATCH v3 08/21] scsi: commonize purging requests

2011-05-17 Thread Paolo Bonzini
The code for canceling requests upon reset is already the same.  Clean
it up and move it to scsi-bus.c.

Signed-off-by: Paolo Bonzini 
---
 hw/scsi-bus.c |   12 
 hw/scsi-disk.c|   18 ++
 hw/scsi-generic.c |   18 ++
 hw/scsi.h |1 +
 4 files changed, 17 insertions(+), 32 deletions(-)

diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index a175590..e1bb494 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -548,6 +548,18 @@ void scsi_req_complete(SCSIRequest *req)
 scsi_req_unref(req);
 }
 
+void scsi_device_purge_requests(SCSIDevice *sdev)
+{
+SCSIRequest *req;
+
+while (!QTAILQ_EMPTY(&sdev->requests)) {
+req = QTAILQ_FIRST(&sdev->requests);
+sdev->info->cancel_io(req);
+scsi_req_dequeue(req);
+scsi_req_unref(req);
+}
+}
+
 static char *scsibus_get_fw_dev_path(DeviceState *dev)
 {
 SCSIDevice *d = (SCSIDevice*)dev;
diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c
index 7446115..8962c33 100644
--- a/hw/scsi-disk.c
+++ b/hw/scsi-disk.c
@@ -1145,26 +1145,12 @@ static int32_t scsi_send_command(SCSIRequest *req, 
uint8_t *buf)
 return len;
 }
 
-static void scsi_disk_purge_requests(SCSIDiskState *s)
-{
-SCSIDiskReq *r;
-
-while (!QTAILQ_EMPTY(&s->qdev.requests)) {
-r = DO_UPCAST(SCSIDiskReq, req, QTAILQ_FIRST(&s->qdev.requests));
-if (r->req.aiocb) {
-bdrv_aio_cancel(r->req.aiocb);
-}
-scsi_req_dequeue(&r->req);
-scsi_req_unref(&r->req);
-}
-}
-
 static void scsi_disk_reset(DeviceState *dev)
 {
 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev.qdev, dev);
 uint64_t nb_sectors;
 
-scsi_disk_purge_requests(s);
+scsi_device_purge_requests(&s->qdev);
 
 bdrv_get_geometry(s->bs, &nb_sectors);
 nb_sectors /= s->cluster_size;
@@ -1178,7 +1164,7 @@ static void scsi_destroy(SCSIDevice *dev)
 {
 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, dev);
 
-scsi_disk_purge_requests(s);
+scsi_device_purge_requests(&s->qdev);
 blockdev_mark_auto_del(s->qdev.conf.bs);
 }
 
diff --git a/hw/scsi-generic.c b/hw/scsi-generic.c
index e3e4187..896797c 100644
--- a/hw/scsi-generic.c
+++ b/hw/scsi-generic.c
@@ -422,32 +422,18 @@ static int get_stream_blocksize(BlockDriverState *bdrv)
 return (buf[9] << 16) | (buf[10] << 8) | buf[11];
 }
 
-static void scsi_generic_purge_requests(SCSIGenericState *s)
-{
-SCSIGenericReq *r;
-
-while (!QTAILQ_EMPTY(&s->qdev.requests)) {
-r = DO_UPCAST(SCSIGenericReq, req, QTAILQ_FIRST(&s->qdev.requests));
-if (r->req.aiocb) {
-bdrv_aio_cancel(r->req.aiocb);
-}
-scsi_req_dequeue(&r->req);
-scsi_req_unref(&r->req);
-}
-}
-
 static void scsi_generic_reset(DeviceState *dev)
 {
 SCSIGenericState *s = DO_UPCAST(SCSIGenericState, qdev.qdev, dev);
 
-scsi_generic_purge_requests(s);
+scsi_device_purge_requests(&s->qdev);
 }
 
 static void scsi_destroy(SCSIDevice *d)
 {
 SCSIGenericState *s = DO_UPCAST(SCSIGenericState, qdev, d);
 
-scsi_generic_purge_requests(s);
+scsi_device_purge_requests(&s->qdev);
 blockdev_mark_auto_del(s->qdev.conf.bs);
 }
 
diff --git a/hw/scsi.h b/hw/scsi.h
index e709989..dee8567 100644
--- a/hw/scsi.h
+++ b/hw/scsi.h
@@ -114,5 +114,6 @@ int scsi_req_parse(SCSIRequest *req, uint8_t *buf);
 void scsi_req_print(SCSIRequest *req);
 void scsi_req_data(SCSIRequest *req, int len);
 void scsi_req_complete(SCSIRequest *req);
+void scsi_device_purge_requests(SCSIDevice *sdev);
 
 #endif
-- 
1.7.4.4





[Qemu-devel] [PATCH v3 16/21] scsi: introduce scsi_req_get_buf

2011-05-17 Thread Paolo Bonzini
... and remove some SCSIDevice variables or fields that now become unused.

Signed-off-by: Paolo Bonzini 
---
 hw/esp.c |2 +-
 hw/lsi53c895a.c  |2 +-
 hw/scsi-bus.c|5 +
 hw/scsi.h|1 +
 hw/spapr_vscsi.c |8 ++--
 hw/usb-msd.c |2 +-
 6 files changed, 11 insertions(+), 9 deletions(-)

diff --git a/hw/esp.c b/hw/esp.c
index 1f342f8..051b0fa 100644
--- a/hw/esp.c
+++ b/hw/esp.c
@@ -419,7 +419,7 @@ static void esp_command_complete(SCSIRequest *req, int 
reason, uint32_t arg)
 } else {
 DPRINTF("transfer %d/%d\n", s->dma_left, s->ti_size);
 s->async_len = arg;
-s->async_buf = s->current_dev->info->get_buf(req);
+s->async_buf = scsi_req_get_buf(req);
 if (s->dma_left) {
 esp_do_dma(s);
 } else if (s->dma_counter != 0 && s->ti_size <= 0) {
diff --git a/hw/lsi53c895a.c b/hw/lsi53c895a.c
index 5458a82..3f618fa 100644
--- a/hw/lsi53c895a.c
+++ b/hw/lsi53c895a.c
@@ -569,7 +569,7 @@ static void lsi_do_dma(LSIState *s, int out)
 s->dnad += count;
 s->dbc -= count;
  if (s->current->dma_buf == NULL) {
-s->current->dma_buf = dev->info->get_buf(s->current->req);
+s->current->dma_buf = scsi_req_get_buf(s->current->req);
 }
 /* ??? Set SFBR to first data byte.  */
 if (out) {
diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index acb1ffa..94dccaf 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -151,6 +151,11 @@ SCSIRequest *scsi_req_new(SCSIDevice *d, uint32_t tag, 
uint32_t lun)
 return d->info->alloc_req(d, tag, lun);
 }
 
+uint8_t *scsi_req_get_buf(SCSIRequest *req)
+{
+return req->dev->info->get_buf(req);
+}
+
 int32_t scsi_req_enqueue(SCSIRequest *req, uint8_t *buf)
 {
 int32_t rc;
diff --git a/hw/scsi.h b/hw/scsi.h
index f659503..3af6295 100644
--- a/hw/scsi.h
+++ b/hw/scsi.h
@@ -154,6 +154,7 @@ void scsi_req_print(SCSIRequest *req);
 void scsi_req_kick(SCSIRequest *req);
 void scsi_req_data(SCSIRequest *req, int len);
 void scsi_req_complete(SCSIRequest *req);
+uint8_t *scsi_req_get_buf(SCSIRequest *req);
 void scsi_req_abort(SCSIRequest *req, int status);
 void scsi_req_cancel(SCSIRequest *req);
 void scsi_device_purge_requests(SCSIDevice *sdev);
diff --git a/hw/spapr_vscsi.c b/hw/spapr_vscsi.c
index 27c8e17..46cd1d7 100644
--- a/hw/spapr_vscsi.c
+++ b/hw/spapr_vscsi.c
@@ -74,7 +74,6 @@ typedef struct vscsi_req {
 union viosrp_iu iu;
 
 /* SCSI request tracking */
-SCSIDevice  *sdev;
 SCSIRequest *sreq;
 uint32_tqtag; /* qemu tag != srp tag */
 int lun;
@@ -476,7 +475,6 @@ static void vscsi_command_complete(SCSIRequest *sreq, int 
reason, uint32_t arg)
 {
 VSCSIState *s = DO_UPCAST(VSCSIState, vdev.qdev, sreq->bus->qbus.parent);
 vscsi_req *req = vscsi_find_req(s, sreq);
-SCSIDevice *sdev;
 uint8_t *buf;
 int32_t res_in = 0, res_out = 0;
 int len, rc = 0;
@@ -487,7 +485,6 @@ static void vscsi_command_complete(SCSIRequest *sreq, int 
reason, uint32_t arg)
 fprintf(stderr, "VSCSI: Can't find request for tag 0x%x\n", sreq->tag);
 return;
 }
-sdev = req->sdev;
 
 if (req->sensing) {
 if (reason == SCSI_REASON_DONE) {
@@ -495,7 +492,7 @@ static void vscsi_command_complete(SCSIRequest *sreq, int 
reason, uint32_t arg)
 vscsi_send_rsp(s, req, CHECK_CONDITION, 0, 0);
 vscsi_put_req(s, req);
 } else {
-uint8_t *buf = sdev->info->get_buf(sreq);
+uint8_t *buf = scsi_req_get_buf(sreq);
 
 len = MIN(arg, SCSI_SENSE_BUF_SIZE);
 dprintf("VSCSI: Sense data, %d bytes:\n", len);
@@ -539,7 +536,7 @@ static void vscsi_command_complete(SCSIRequest *sreq, int 
reason, uint32_t arg)
  * to write for writes (ie, how much is to be DMA'd)
  */
 if (arg) {
-buf = sdev->info->get_buf(sreq);
+buf = scsi_req_get_buf(sreq);
 rc = vscsi_srp_transfer_data(s, req, req->writing, buf, arg);
 }
 if (rc < 0) {
@@ -646,7 +643,6 @@ static int vscsi_queue_cmd(VSCSIState *s, vscsi_req *req)
 } return 1;
 }
 
-req->sdev = sdev;
 req->lun = lun;
 req->sreq = scsi_req_new(sdev, req->qtag, lun);
 n = scsi_req_enqueue(req->sreq, srp->cmd.cdb);
diff --git a/hw/usb-msd.c b/hw/usb-msd.c
index e307c80..14e42e5 100644
--- a/hw/usb-msd.c
+++ b/hw/usb-msd.c
@@ -247,7 +247,7 @@ static void usb_msd_command_complete(SCSIRequest *req, int 
reason, uint32_t arg)
 }
 assert((s->mode == USB_MSDM_DATAOUT) == (req->cmd.mode == 
SCSI_XFER_TO_DEV));
 s->scsi_len = arg;
-s->scsi_buf = s->scsi_dev->info->get_buf(req);
+s->scsi_buf = scsi_req_get_buf(req);
 if (p) {
 usb_msd_copy_data(s);
 if (s->usb_len == 0) {
-- 
1.7.4.4





[Qemu-devel] [PATCH v3 05/21] scsi: reference-count requests

2011-05-17 Thread Paolo Bonzini
With the next patch, a device may hold SCSIRequest for an indefinite
time.  Split a rather big patch, and protect against access errors,
by reference counting them.  One such access error in fact exists (it
is visible by testing the lsi driver with MALLOC_PERTURB_), and this
patch provides the infrastructure to fix it later.

There is some ugliness in scsi_send_command implementation due to
the need to unref the request when it fails.  This will go away
with the next patches, which move the unref'ing to the devices.

Signed-off-by: Paolo Bonzini 
---
 hw/scsi-bus.c |   22 --
 hw/scsi-disk.c|   20 +---
 hw/scsi-generic.c |   23 ---
 hw/scsi.h |5 +
 4 files changed, 54 insertions(+), 16 deletions(-)

diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index 63d9a68..c0bc275 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -136,6 +136,7 @@ SCSIRequest *scsi_req_alloc(size_t size, SCSIDevice *d, 
uint32_t tag, uint32_t l
 SCSIRequest *req;
 
 req = qemu_mallocz(size);
+req->refcount = 2;
 req->bus = scsi_bus_from_device(d);
 req->dev = d;
 req->tag = tag;
@@ -159,21 +160,23 @@ SCSIRequest *scsi_req_find(SCSIDevice *d, uint32_t tag)
 return NULL;
 }
 
-static void scsi_req_dequeue(SCSIRequest *req)
+void scsi_req_dequeue(SCSIRequest *req)
 {
 trace_scsi_req_dequeue(req->dev->id, req->lun, req->tag);
 if (req->enqueued) {
 QTAILQ_REMOVE(&req->dev->requests, req, next);
 req->enqueued = false;
+scsi_req_unref(req);
 }
 }
 
 void scsi_req_free(SCSIRequest *req)
 {
-scsi_req_dequeue(req);
+assert(req->refcount == 0);
 qemu_free(req);
 }
 
+
 static int scsi_req_length(SCSIRequest *req, uint8_t *cmd)
 {
 switch (cmd[0] >> 5) {
@@ -495,6 +498,19 @@ static const char *scsi_command_name(uint8_t cmd)
 return names[cmd];
 }
 
+SCSIRequest *scsi_req_ref(SCSIRequest *req)
+{
+req->refcount++;
+return req;
+}
+
+void scsi_req_unref(SCSIRequest *req)
+{
+if (--req->refcount == 0) {
+req->dev->info->free_req(req);
+}
+}
+
 void scsi_req_data(SCSIRequest *req, int len)
 {
 trace_scsi_req_data(req->dev->id, req->lun, req->tag, len);
@@ -532,10 +548,12 @@ void scsi_req_print(SCSIRequest *req)
 void scsi_req_complete(SCSIRequest *req)
 {
 assert(req->status != -1);
+scsi_req_ref(req);
 scsi_req_dequeue(req);
 req->bus->ops.complete(req->bus, SCSI_REASON_DONE,
req->tag,
req->status);
+scsi_req_unref(req);
 }
 
 static char *scsibus_get_fw_dev_path(DeviceState *dev)
diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c
index 2b5dc2a..ba7ffa1 100644
--- a/hw/scsi-disk.c
+++ b/hw/scsi-disk.c
@@ -95,8 +95,10 @@ static SCSIDiskReq *scsi_new_request(SCSIDiskState *s, 
uint32_t tag,
 return r;
 }
 
-static void scsi_remove_request(SCSIDiskReq *r)
+static void scsi_free_request(SCSIRequest *req)
 {
+SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
+
 qemu_vfree(r->iov.iov_base);
 scsi_req_free(&r->req);
 }
@@ -131,7 +133,6 @@ static void scsi_command_complete(SCSIDiskReq *r, int 
status, int sense)
 r->req.tag, status, sense);
 scsi_req_set_status(r, status, sense);
 scsi_req_complete(&r->req);
-scsi_remove_request(r);
 }
 
 /* Cancel a pending data transfer.  */
@@ -145,7 +146,7 @@ static void scsi_cancel_io(SCSIDevice *d, uint32_t tag)
 if (r->req.aiocb)
 bdrv_aio_cancel(r->req.aiocb);
 r->req.aiocb = NULL;
-scsi_remove_request(r);
+scsi_req_dequeue(&r->req);
 }
 }
 
@@ -1030,7 +1031,7 @@ static int32_t scsi_send_command(SCSIDevice *d, uint32_t 
tag,
  uint8_t *buf, int lun)
 {
 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, d);
-uint32_t len;
+int32_t len;
 int is_write;
 uint8_t command;
 uint8_t *outbuf;
@@ -1092,6 +1093,7 @@ static int32_t scsi_send_command(SCSIDevice *d, uint32_t 
tag,
 case REZERO_UNIT:
 rc = scsi_disk_emulate_command(r, outbuf);
 if (rc < 0) {
+scsi_req_unref(&r->req);
 return 0;
 }
 
@@ -1178,9 +1180,11 @@ static int32_t scsi_send_command(SCSIDevice *d, uint32_t 
tag,
 DPRINTF("Unknown SCSI command (%2.2x)\n", buf[0]);
 fail:
 scsi_command_complete(r, CHECK_CONDITION, ILLEGAL_REQUEST);
+scsi_req_unref(&r->req);
 return 0;
 illegal_lba:
 scsi_command_complete(r, CHECK_CONDITION, HARDWARE_ERROR);
+scsi_req_unref(&r->req);
 return 0;
 }
 if (r->sector_count == 0 && r->iov.iov_len == 0) {
@@ -1188,12 +1192,13 @@ static int32_t scsi_send_command(SCSIDevice *d, 
uint32_t tag,
 }
 len = r->sector_count * 512 + r->iov.iov_len;
 if (is_write) {
-return -len;
+len = -len;
 } else {
 if (!r->sector_count)
 r->sector_count = -1;
-return len;
 }
+ 

[Qemu-devel] [PATCH v3 15/21] scsi: introduce scsi_req_kick

2011-05-17 Thread Paolo Bonzini
Signed-off-by: Paolo Bonzini 
---
 hw/esp.c |   26 ++
 hw/lsi53c895a.c  |   22 --
 hw/scsi-bus.c|   10 ++
 hw/scsi.h|1 +
 hw/spapr_vscsi.c |   26 ++
 hw/usb-msd.c |   15 ---
 trace-events |1 +
 7 files changed, 44 insertions(+), 57 deletions(-)

diff --git a/hw/esp.c b/hw/esp.c
index ad364b5..1f342f8 100644
--- a/hw/esp.c
+++ b/hw/esp.c
@@ -253,11 +253,10 @@ static void do_busid_cmd(ESPState *s, uint8_t *buf, 
uint8_t busid)
 s->dma_counter = 0;
 if (datalen > 0) {
 s->rregs[ESP_RSTAT] |= STAT_DI;
-s->current_dev->info->read_data(s->current_req);
 } else {
 s->rregs[ESP_RSTAT] |= STAT_DO;
-s->current_dev->info->write_data(s->current_req);
 }
+scsi_req_kick(s->current_req);
 }
 s->rregs[ESP_RINTR] = INTR_BS | INTR_FC;
 s->rregs[ESP_RSEQ] = SEQ_CD;
@@ -383,22 +382,17 @@ static void esp_do_dma(ESPState *s)
 else
 s->ti_size -= len;
 if (s->async_len == 0) {
-if (to_device) {
-// ti_size is negative
-s->current_dev->info->write_data(s->current_req);
-} else {
-s->current_dev->info->read_data(s->current_req);
-/* If there is still data to be read from the device then
-   complete the DMA operation immediately.  Otherwise defer
-   until the scsi layer has completed.  */
-if (s->dma_left == 0 && s->ti_size > 0) {
-esp_dma_done(s);
-}
+scsi_req_kick(s->current_req);
+/* If there is still data to be read from the device then
+   complete the DMA operation immediately.  Otherwise defer
+   until the scsi layer has completed.  */
+if (to_device || s->dma_left != 0 || s->ti_size == 0) {
+return;
 }
-} else {
-/* Partially filled a scsi buffer. Complete immediately.  */
-esp_dma_done(s);
 }
+
+/* Partially filled a scsi buffer. Complete immediately.  */
+esp_dma_done(s);
 }
 
 static void esp_command_complete(SCSIRequest *req, int reason, uint32_t arg)
diff --git a/hw/lsi53c895a.c b/hw/lsi53c895a.c
index e2af25f..5458a82 100644
--- a/hw/lsi53c895a.c
+++ b/hw/lsi53c895a.c
@@ -580,13 +580,7 @@ static void lsi_do_dma(LSIState *s, int out)
 s->current->dma_len -= count;
 if (s->current->dma_len == 0) {
 s->current->dma_buf = NULL;
-if (out) {
-/* Write the data.  */
-dev->info->write_data(s->current->req);
-} else {
-/* Request any remaining data.  */
-dev->info->read_data(s->current->req);
-}
+scsi_req_kick(s->current->req);
 } else {
 s->current->dma_buf += count;
 lsi_resume_script(s);
@@ -791,14 +785,14 @@ static void lsi_do_command(LSIState *s)
 s->current->req = scsi_req_new(dev, s->current->tag, s->current_lun);
 
 n = scsi_req_enqueue(s->current->req, buf);
-if (n > 0) {
-lsi_set_phase(s, PHASE_DI);
-dev->info->read_data(s->current->req);
-} else if (n < 0) {
-lsi_set_phase(s, PHASE_DO);
-dev->info->write_data(s->current->req);
+if (n) {
+if (n > 0) {
+lsi_set_phase(s, PHASE_DI);
+} else if (n < 0) {
+lsi_set_phase(s, PHASE_DO);
+}
+scsi_req_kick(s->current->req);
 }
-
 if (!s->command_complete) {
 if (n) {
 /* Command did not complete immediately so disconnect.  */
diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index c091159..acb1ffa 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -606,6 +606,16 @@ void scsi_req_unref(SCSIRequest *req)
 }
 }
 
+void scsi_req_kick(SCSIRequest *req)
+{
+trace_scsi_req_kick(req->dev->id, req->lun, req->tag);
+if (req->cmd.mode == SCSI_XFER_TO_DEV) {
+req->dev->info->write_data(req);
+} else {
+req->dev->info->read_data(req);
+}
+}
+
 void scsi_req_data(SCSIRequest *req, int len)
 {
 trace_scsi_req_data(req->dev->id, req->lun, req->tag, len);
diff --git a/hw/scsi.h b/hw/scsi.h
index e44c194..f659503 100644
--- a/hw/scsi.h
+++ b/hw/scsi.h
@@ -151,6 +151,7 @@ void scsi_req_unref(SCSIRequest *req);
 
 int scsi_req_parse(SCSIRequest *req, uint8_t *buf);
 void scsi_req_print(SCSIRequest *req);
+void scsi_req_kick(SCSIRequest *req);
 void scsi_req_data(SCSIRequest *req, int len);
 void scsi_req_complete(SCSIRequest *req);
 void scsi_req_abort(SCSIRequest *req, int status);
diff --git a/hw/spapr_vscsi.c b/hw/spapr_vscsi.c
index 1bb4bf4..27c8e17 100644
--- a/hw/spapr_vscsi.c
+++ b/hw/spapr_vscsi.c
@@ -448,7 +448,6 @@ static int vscsi_preprocess_desc(vscsi_req *req)
 
 static void vscsi_send_request_sense(VSCSIState *s, vscsi_req *req)
 {
-SCSIDevice *sdev = req->sdev;
 uint8_t *cdb = req->iu.srp.cmd.cdb;
 int n;
 
@@ -469,7 +468,7 @@ static voi

[Qemu-devel] [PATCH v3 10/21] scsi: introduce scsi_req_cancel

2011-05-17 Thread Paolo Bonzini
This is for when the request must be dropped in the void,
but still memory should be freed.  To this end, the devices
register a second callback in SCSIBusOps.

Signed-off-by: Paolo Bonzini 
Signed-off-by: Jonathan Nieder 
---
 hw/esp.c  |   16 ++--
 hw/lsi53c895a.c   |   33 +
 hw/scsi-bus.c |   17 ++---
 hw/scsi-disk.c|1 -
 hw/scsi-generic.c |1 -
 hw/scsi.h |2 ++
 hw/spapr_vscsi.c  |   11 ++-
 hw/usb-msd.c  |   19 +++
 8 files changed, 80 insertions(+), 20 deletions(-)

diff --git a/hw/esp.c b/hw/esp.c
index 096f4dc..46157a8 100644
--- a/hw/esp.c
+++ b/hw/esp.c
@@ -188,6 +188,17 @@ static void esp_dma_enable(void *opaque, int irq, int 
level)
 }
 }
 
+static void esp_request_cancelled(SCSIRequest *req)
+{
+ESPState *s = DO_UPCAST(ESPState, busdev.qdev, req->bus->qbus.parent);
+
+if (req == s->current_req) {
+scsi_req_unref(s->current_req);
+s->current_req = NULL;
+s->current_dev = NULL;
+}
+}
+
 static uint32_t get_cmd(ESPState *s, uint8_t *buf)
 {
 uint32_t dmalen;
@@ -210,7 +221,7 @@ static uint32_t get_cmd(ESPState *s, uint8_t *buf)
 
 if (s->current_dev) {
 /* Started a new command before the old one finished.  Cancel it.  */
-s->current_dev->info->cancel_io(s->current_req);
+scsi_req_cancel(s->current_req);
 s->async_len = 0;
 }
 
@@ -720,7 +731,8 @@ void esp_init(target_phys_addr_t espaddr, int it_shift,
 }
 
 static struct SCSIBusOps esp_scsi_ops = {
-.complete = esp_command_complete
+.complete = esp_command_complete,
+.cancel = esp_request_cancelled
 };
 
 static int esp_init1(SysBusDevice *dev)
diff --git a/hw/lsi53c895a.c b/hw/lsi53c895a.c
index b9febae..f78b85f 100644
--- a/hw/lsi53c895a.c
+++ b/hw/lsi53c895a.c
@@ -664,6 +664,26 @@ static lsi_request *lsi_find_by_tag(LSIState *s, uint32_t 
tag)
 return NULL;
 }
 
+static void lsi_request_cancelled(SCSIRequest *req)
+{
+LSIState *s = DO_UPCAST(LSIState, dev.qdev, req->bus->qbus.parent);
+lsi_request *p;
+
+if (req == s->current->req) {
+scsi_req_unref(req);
+qemu_free(s->current);
+s->current = NULL;
+return;
+}
+
+p = lsi_find_by_tag(s, req->tag);
+if (p) {
+QTAILQ_REMOVE(&s->queue, p, next);
+scsi_req_unref(req);
+qemu_free(p);
+}
+}
+
 /* Record that data is available for a queued command.  Returns zero if
the device was reselected, nonzero if the IO is deferred.  */
 static int lsi_queue_tag(LSIState *s, uint32_t tag, uint32_t arg)
@@ -869,7 +889,6 @@ static void lsi_do_msgout(LSIState *s)
 uint8_t msg;
 int len;
 uint32_t current_tag;
-SCSIDevice *current_dev;
 lsi_request *current_req, *p, *p_next;
 int id;
 
@@ -880,8 +899,6 @@ static void lsi_do_msgout(LSIState *s)
 current_tag = s->select_tag;
 current_req = lsi_find_by_tag(s, current_tag);
 }
-id = (current_tag >> 8) & 0xf;
-current_dev = s->bus.devs[id];
 
 DPRINTF("MSG out len=%d\n", s->dbc);
 while (s->dbc) {
@@ -931,7 +948,7 @@ static void lsi_do_msgout(LSIState *s)
 /* The ABORT TAG message clears the current I/O process only. */
 DPRINTF("MSG: ABORT TAG tag=0x%x\n", current_tag);
 if (current_req) {
-current_dev->info->cancel_io(current_req->req);
+scsi_req_cancel(current_req->req);
 }
 lsi_disconnect(s);
 break;
@@ -956,7 +973,7 @@ static void lsi_do_msgout(LSIState *s)
 
 /* clear the current I/O process */
 if (s->current) {
-current_dev->info->cancel_io(s->current->req);
+scsi_req_cancel(s->current->req);
 }
 
 /* As the current implemented devices scsi_disk and scsi_generic
@@ -969,8 +986,7 @@ static void lsi_do_msgout(LSIState *s)
 id = current_tag & 0xff00;
 QTAILQ_FOREACH_SAFE(p, &s->queue, next, p_next) {
 if ((p->tag & 0xff00) == id) {
-current_dev->info->cancel_io(p->req);
-QTAILQ_REMOVE(&s->queue, p, next);
+scsi_req_cancel(p->req);
 }
 }
 
@@ -2227,7 +2243,8 @@ static int lsi_scsi_uninit(PCIDevice *d)
 }
 
 static struct SCSIBusOps lsi_scsi_ops = {
-.complete = lsi_command_complete
+.complete = lsi_command_complete,
+.cancel = lsi_request_cancelled
 };
 
 static int lsi_scsi_init(PCIDevice *dev)
diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index 1d7da9e..6a8ea0b 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -548,6 +548,19 @@ void scsi_req_complete(SCSIRequest *req)
 scsi_req_unref(req);
 }
 
+void scsi_req_cancel(SCSIRequest *req)
+{
+if (req->dev && req->dev->info->cancel_io) {
+req->dev->info->cancel_io(req);
+}
+scsi_req_ref(req);
+scsi_req_dequeue

[Qemu-devel] [PATCH v3 19/21] scsi: make write_data return void

2011-05-17 Thread Paolo Bonzini
The return value is unused anyway.

Signed-off-by: Paolo Bonzini 
---
 hw/scsi-disk.c|6 ++
 hw/scsi-generic.c |7 ++-
 hw/scsi.h |2 +-
 3 files changed, 5 insertions(+), 10 deletions(-)

diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c
index 65744c7..4c7a53e 100644
--- a/hw/scsi-disk.c
+++ b/hw/scsi-disk.c
@@ -267,7 +267,7 @@ static void scsi_write_complete(void * opaque, int ret)
 }
 }
 
-static int scsi_write_data(SCSIRequest *req)
+static void scsi_write_data(SCSIRequest *req)
 {
 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);
@@ -279,7 +279,7 @@ static int scsi_write_data(SCSIRequest *req)
 if (r->req.cmd.mode != SCSI_XFER_TO_DEV) {
 DPRINTF("Data transfer direction invalid\n");
 scsi_write_complete(r, -EINVAL);
-return 0;
+return;
 }
 
 n = r->iov.iov_len / 512;
@@ -294,8 +294,6 @@ static int scsi_write_data(SCSIRequest *req)
 /* Invoke completion routine to fetch data from host.  */
 scsi_write_complete(r, 0);
 }
-
-return 0;
 }
 
 static void scsi_dma_restart_bh(void *opaque)
diff --git a/hw/scsi-generic.c b/hw/scsi-generic.c
index a4de39d..1ea0930 100644
--- a/hw/scsi-generic.c
+++ b/hw/scsi-generic.c
@@ -275,7 +275,7 @@ static void scsi_write_complete(void * opaque, int ret)
 
 /* Write data to a scsi device.  Returns nonzero on failure.
The transfer may complete asynchronously.  */
-static int scsi_write_data(SCSIRequest *req)
+static void scsi_write_data(SCSIRequest *req)
 {
 SCSIGenericState *s = DO_UPCAST(SCSIGenericState, qdev, req->dev);
 SCSIGenericReq *r = DO_UPCAST(SCSIGenericReq, req, req);
@@ -285,16 +285,13 @@ static int scsi_write_data(SCSIRequest *req)
 if (r->len == 0) {
 r->len = r->buflen;
 scsi_req_data(&r->req, r->len);
-return 0;
+return;
 }
 
 ret = execute_command(s->bs, r, SG_DXFER_TO_DEV, scsi_write_complete);
 if (ret < 0) {
 scsi_command_complete(r, ret);
-return 1;
 }
-
-return 0;
 }
 
 /* Return a pointer to the data buffer.  */
diff --git a/hw/scsi.h b/hw/scsi.h
index dbb69ef..7eed475 100644
--- a/hw/scsi.h
+++ b/hw/scsi.h
@@ -77,7 +77,7 @@ struct SCSIDeviceInfo {
 void (*free_req)(SCSIRequest *req);
 int32_t (*send_command)(SCSIRequest *req, uint8_t *buf);
 void (*read_data)(SCSIRequest *req);
-int (*write_data)(SCSIRequest *req);
+void (*write_data)(SCSIRequest *req);
 void (*cancel_io)(SCSIRequest *req);
 uint8_t *(*get_buf)(SCSIRequest *req);
 int (*get_sense)(SCSIRequest *req, uint8_t *buf, int len);
-- 
1.7.4.4





[Qemu-devel] [PATCH v3 17/21] scsi: Implement 'get_sense' callback

2011-05-17 Thread Paolo Bonzini
From: Hannes Reinecke 

The get_sense callback copies existing sense information into
the provided buffer. This is required if sense information
should be transferred together with the command response.

Signed-off-by: Hannes Reinecke 
Signed-off-by: Paolo Bonzini 
---
 hw/scsi-bus.c |9 +
 hw/scsi-disk.c|9 +
 hw/scsi-generic.c |   18 ++
 hw/scsi.h |2 ++
 hw/spapr_vscsi.c  |   10 +-
 5 files changed, 47 insertions(+), 1 deletions(-)

diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index 94dccaf..7daa112 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -156,6 +156,15 @@ uint8_t *scsi_req_get_buf(SCSIRequest *req)
 return req->dev->info->get_buf(req);
 }
 
+int scsi_req_get_sense(SCSIRequest *req, uint8_t *buf, int len)
+{
+if (req->dev->info->get_sense) {
+return req->dev->info->get_sense(req, buf, len);
+} else {
+return 0;
+}
+}
+
 int32_t scsi_req_enqueue(SCSIRequest *req, uint8_t *buf)
 {
 int32_t rc;
diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c
index efb953b..4241fad 100644
--- a/hw/scsi-disk.c
+++ b/hw/scsi-disk.c
@@ -338,6 +338,14 @@ static uint8_t *scsi_get_buf(SCSIRequest *req)
 return (uint8_t *)r->iov.iov_base;
 }
 
+/* Copy sense information into the provided buffer */
+static int scsi_get_sense(SCSIRequest *req, uint8_t *outbuf, int len)
+{
+SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
+
+return scsi_build_sense(s->sense, outbuf, len, len > 14);
+}
+
 static int scsi_disk_emulate_inquiry(SCSIRequest *req, uint8_t *outbuf)
 {
 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
@@ -1225,6 +1233,7 @@ static SCSIDeviceInfo scsi_disk_info = {
 .write_data   = scsi_write_data,
 .cancel_io= scsi_cancel_io,
 .get_buf  = scsi_get_buf,
+.get_sense= scsi_get_sense,
 .qdev.props   = (Property[]) {
 DEFINE_BLOCK_PROPERTIES(SCSIDiskState, qdev.conf),
 DEFINE_PROP_STRING("ver",  SCSIDiskState, version),
diff --git a/hw/scsi-generic.c b/hw/scsi-generic.c
index 036ab9f..a4de39d 100644
--- a/hw/scsi-generic.c
+++ b/hw/scsi-generic.c
@@ -79,6 +79,23 @@ static void scsi_clear_sense(SCSIGenericState *s)
 s->driver_status = 0;
 }
 
+static int scsi_get_sense(SCSIRequest *req, uint8_t *outbuf, int len)
+{
+SCSIGenericState *s = DO_UPCAST(SCSIGenericState, qdev, req->dev);
+int size = SCSI_SENSE_BUF_SIZE;
+
+if (!(s->driver_status & SG_ERR_DRIVER_SENSE)) {
+size = scsi_build_sense(SENSE_CODE(NO_SENSE), s->sensebuf,
+SCSI_SENSE_BUF_SIZE, 0);
+}
+if (size > len) {
+size = len;
+}
+memcpy(outbuf, s->sensebuf, size);
+
+return size;
+}
+
 static SCSIRequest *scsi_new_request(SCSIDevice *d, uint32_t tag, uint32_t lun)
 {
 SCSIRequest *req;
@@ -533,6 +550,7 @@ static SCSIDeviceInfo scsi_generic_info = {
 .write_data   = scsi_write_data,
 .cancel_io= scsi_cancel_io,
 .get_buf  = scsi_get_buf,
+.get_sense= scsi_get_sense,
 .qdev.props   = (Property[]) {
 DEFINE_BLOCK_PROPERTIES(SCSIGenericState, qdev.conf),
 DEFINE_PROP_END_OF_LIST(),
diff --git a/hw/scsi.h b/hw/scsi.h
index 3af6295..dbb69ef 100644
--- a/hw/scsi.h
+++ b/hw/scsi.h
@@ -80,6 +80,7 @@ struct SCSIDeviceInfo {
 int (*write_data)(SCSIRequest *req);
 void (*cancel_io)(SCSIRequest *req);
 uint8_t *(*get_buf)(SCSIRequest *req);
+int (*get_sense)(SCSIRequest *req, uint8_t *buf, int len);
 };
 
 struct SCSIBusOps {
@@ -155,6 +156,7 @@ void scsi_req_kick(SCSIRequest *req);
 void scsi_req_data(SCSIRequest *req, int len);
 void scsi_req_complete(SCSIRequest *req);
 uint8_t *scsi_req_get_buf(SCSIRequest *req);
+int scsi_req_get_sense(SCSIRequest *req, uint8_t *buf, int len);
 void scsi_req_abort(SCSIRequest *req, int status);
 void scsi_req_cancel(SCSIRequest *req);
 void scsi_device_purge_requests(SCSIDevice *sdev);
diff --git a/hw/spapr_vscsi.c b/hw/spapr_vscsi.c
index 46cd1d7..8a47de0 100644
--- a/hw/spapr_vscsi.c
+++ b/hw/spapr_vscsi.c
@@ -450,6 +450,15 @@ static void vscsi_send_request_sense(VSCSIState *s, 
vscsi_req *req)
 uint8_t *cdb = req->iu.srp.cmd.cdb;
 int n;
 
+n = scsi_req_get_sense(req->sreq, req->sense, sizeof(req->sense));
+if (n) {
+req->senselen = n;
+vscsi_send_rsp(s, req, CHECK_CONDITION, 0, 0);
+vscsi_put_req(s, req);
+return;
+}
+
+dprintf("VSCSI: Got CHECK_CONDITION, requesting sense...\n");
 cdb[0] = 3;
 cdb[1] = 0;
 cdb[2] = 0;
@@ -522,7 +531,6 @@ static void vscsi_command_complete(SCSIRequest *sreq, int 
reason, uint32_t arg)
 }
 vscsi_send_rsp(s, req, 0, res_in, res_out);
 } else if (arg == CHECK_CONDITION) {
-dprintf("VSCSI: Got CHECK_CONDITION, requesting sense...\n");
 vscsi_send_request_sense(s, req);
 return;
 } else {
-- 
1.7.4.4





[Qemu-devel] [PATCH v3 21/21] scsi: split command_complete callback in two

2011-05-17 Thread Paolo Bonzini
Signed-off-by: Paolo Bonzini 
---
 hw/esp.c |   60 +---
 hw/lsi53c895a.c  |   48 +++---
 hw/scsi-bus.c|4 +-
 hw/scsi.h|9 +
 hw/spapr_vscsi.c |  101 ++
 hw/usb-msd.c |   69 +
 6 files changed, 159 insertions(+), 132 deletions(-)

diff --git a/hw/esp.c b/hw/esp.c
index 051b0fa..5a33c67 100644
--- a/hw/esp.c
+++ b/hw/esp.c
@@ -395,38 +395,41 @@ static void esp_do_dma(ESPState *s)
 esp_dma_done(s);
 }
 
-static void esp_command_complete(SCSIRequest *req, int reason, uint32_t arg)
+static void esp_command_complete(SCSIRequest *req, uint32_t arg)
 {
 ESPState *s = DO_UPCAST(ESPState, busdev.qdev, req->bus->qbus.parent);
 
-if (reason == SCSI_REASON_DONE) {
-DPRINTF("SCSI Command complete\n");
-if (s->ti_size != 0)
-DPRINTF("SCSI command completed unexpectedly\n");
-s->ti_size = 0;
-s->dma_left = 0;
-s->async_len = 0;
-if (arg)
-DPRINTF("Command failed\n");
-s->sense = arg;
-s->rregs[ESP_RSTAT] = STAT_ST;
+DPRINTF("SCSI Command complete\n");
+if (s->ti_size != 0)
+DPRINTF("SCSI command completed unexpectedly\n");
+s->ti_size = 0;
+s->dma_left = 0;
+s->async_len = 0;
+if (arg)
+DPRINTF("Command failed\n");
+s->sense = arg;
+s->rregs[ESP_RSTAT] = STAT_ST;
+esp_dma_done(s);
+if (s->current_req) {
+scsi_req_unref(s->current_req);
+s->current_req = NULL;
+s->current_dev = NULL;
+}
+}
+
+static void esp_transfer_data(SCSIRequest *req, uint32_t arg)
+{
+ESPState *s = DO_UPCAST(ESPState, busdev.qdev, req->bus->qbus.parent);
+
+DPRINTF("transfer %d/%d\n", s->dma_left, s->ti_size);
+s->async_len = arg;
+s->async_buf = scsi_req_get_buf(req);
+if (s->dma_left) {
+esp_do_dma(s);
+} else if (s->dma_counter != 0 && s->ti_size <= 0) {
+/* If this was the last part of a DMA transfer then the
+   completion interrupt is deferred to here.  */
 esp_dma_done(s);
-   if (s->current_req) {
-scsi_req_unref(s->current_req);
-s->current_req = NULL;
-s->current_dev = NULL;
-   }
-} else {
-DPRINTF("transfer %d/%d\n", s->dma_left, s->ti_size);
-s->async_len = arg;
-s->async_buf = scsi_req_get_buf(req);
-if (s->dma_left) {
-esp_do_dma(s);
-} else if (s->dma_counter != 0 && s->ti_size <= 0) {
-/* If this was the last part of a DMA transfer then the
-   completion interrupt is deferred to here.  */
-esp_dma_done(s);
-}
 }
 }
 
@@ -725,6 +728,7 @@ void esp_init(target_phys_addr_t espaddr, int it_shift,
 }
 
 static struct SCSIBusOps esp_scsi_ops = {
+.transfer_data = esp_transfer_data,
 .complete = esp_command_complete,
 .cancel = esp_request_cancelled
 };
diff --git a/hw/lsi53c895a.c b/hw/lsi53c895a.c
index 3f618fa..43de6f8 100644
--- a/hw/lsi53c895a.c
+++ b/hw/lsi53c895a.c
@@ -711,40 +711,47 @@ static int lsi_queue_tag(LSIState *s, uint32_t tag, 
uint32_t arg)
 return 1;
 }
 }
- /* Callback to indicate that the SCSI layer has completed a transfer.  */
-static void lsi_command_complete(SCSIRequest *req, int reason, uint32_t arg)
+
+ /* Callback to indicate that the SCSI layer has completed a command.  */
+static void lsi_command_complete(SCSIRequest *req, uint32_t arg)
 {
 LSIState *s = DO_UPCAST(LSIState, dev.qdev, req->bus->qbus.parent);
 int out;
 
 out = (s->sstat1 & PHASE_MASK) == PHASE_DO;
-if (reason == SCSI_REASON_DONE) {
-DPRINTF("Command complete status=%d\n", (int)arg);
-s->status = arg;
-s->command_complete = 2;
-if (s->waiting && s->dbc != 0) {
-/* Raise phase mismatch for short transfers.  */
-lsi_bad_phase(s, out, PHASE_ST);
-} else {
-lsi_set_phase(s, PHASE_ST);
-}
+DPRINTF("Command complete status=%d\n", (int)arg);
+s->status = arg;
+s->command_complete = 2;
+if (s->waiting && s->dbc != 0) {
+/* Raise phase mismatch for short transfers.  */
+lsi_bad_phase(s, out, PHASE_ST);
+} else {
+lsi_set_phase(s, PHASE_ST);
+}
 
-if (req == s->current->req) {
-scsi_req_unref(s->current->req);
-qemu_free(s->current);
-s->current = NULL;
-   }
-lsi_resume_script(s);
-return;
+if (req == s->current->req) {
+scsi_req_unref(s->current->req);
+qemu_free(s->current);
+s->current = NULL;
 }
+lsi_resume_script(s);
+}
+
+ /* Callback to indicate that the SCSI layer has completed a transfer.  */
+static void lsi_transfer_data(SCSIRequest *req, uint32_t arg)
+{
+LSIState *s = DO_UPCAST(LSIState, dev.qdev, req->bus->qbus.parent);
+

[Qemu-devel] [PATCH v3 18/21] scsi-disk: add data direction checking

2011-05-17 Thread Paolo Bonzini
From: Hannes Reinecke 

scsi_req_parse() already provides for a data direction setting,
so we should be using it to check for correct direction.
And we should return the sense code 'INVALID FIELD IN CDB'
in these cases.

Signed-off-by: Hannes Reinecke 
Signed-off-by: Paolo Bonzini 
---
 hw/scsi-disk.c |   37 +
 1 files changed, 25 insertions(+), 12 deletions(-)

diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c
index 4241fad..65744c7 100644
--- a/hw/scsi-disk.c
+++ b/hw/scsi-disk.c
@@ -49,10 +49,8 @@ do { fprintf(stderr, "scsi-disk: " fmt , ## __VA_ARGS__); } 
while (0)
 
 typedef struct SCSIDiskState SCSIDiskState;
 
-typedef struct SCSIDiskReq {
+ typedef struct SCSIDiskReq {
 SCSIRequest req;
-/* ??? We should probably keep track of whether the data transfer is
-   a read or a write.  Currently we rely on the host getting it right.  */
 /* Both sector and sector_count are in terms of qemu 512 byte blocks.  */
 uint64_t sector;
 uint32_t sector_count;
@@ -178,6 +176,12 @@ static void scsi_read_data(SCSIRequest *req)
 /* No data transfer may already be in progress */
 assert(r->req.aiocb == NULL);
 
+if (r->req.cmd.mode == SCSI_XFER_TO_DEV) {
+DPRINTF("Data transfer direction invalid\n");
+scsi_read_complete(r, -EINVAL);
+return;
+}
+
 n = r->sector_count;
 if (n > SCSI_DMA_BUF_SIZE / 512)
 n = SCSI_DMA_BUF_SIZE / 512;
@@ -214,16 +218,22 @@ static int scsi_handle_rw_error(SCSIDiskReq *r, int 
error, int type)
 if (type == SCSI_REQ_STATUS_RETRY_READ) {
 scsi_req_data(&r->req, 0);
 }
-if (error == ENOMEM) {
+switch (error) {
+case ENOMEM:
 scsi_command_complete(r, CHECK_CONDITION,
   SENSE_CODE(TARGET_FAILURE));
-} else {
+break;
+case EINVAL:
+scsi_command_complete(r, CHECK_CONDITION,
+  SENSE_CODE(INVALID_FIELD));
+break;
+default:
 scsi_command_complete(r, CHECK_CONDITION,
   SENSE_CODE(IO_ERROR));
+break;
 }
 bdrv_mon_event(s->bs, BDRV_ACTION_REPORT, is_read);
 }
-
 return 1;
 }
 
@@ -266,6 +276,12 @@ static int scsi_write_data(SCSIRequest *req)
 /* No data transfer may already be in progress */
 assert(r->req.aiocb == NULL);
 
+if (r->req.cmd.mode != SCSI_XFER_TO_DEV) {
+DPRINTF("Data transfer direction invalid\n");
+scsi_write_complete(r, -EINVAL);
+return 0;
+}
+
 n = r->iov.iov_len / 512;
 if (n) {
 qemu_iovec_init_external(&r->qiov, &r->iov, 1);
@@ -985,14 +1001,12 @@ static int32_t scsi_send_command(SCSIRequest *req, 
uint8_t *buf)
 SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);
 SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, req->dev);
 int32_t len;
-int is_write;
 uint8_t command;
 uint8_t *outbuf;
 int rc;
 
 command = buf[0];
 outbuf = (uint8_t *)r->iov.iov_base;
-is_write = 0;
 DPRINTF("Command: lun=%d tag=0x%x data=0x%02x", lun, tag, buf[0]);
 
 if (scsi_req_parse(&r->req, buf) != 0) {
@@ -1072,7 +1086,6 @@ static int32_t scsi_send_command(SCSIRequest *req, 
uint8_t *buf)
 goto illegal_lba;
 r->sector = r->req.cmd.lba * s->cluster_size;
 r->sector_count = len * s->cluster_size;
-is_write = 1;
 break;
 case MODE_SELECT:
 DPRINTF("Mode Select(6) (len %lu)\n", (long)r->req.cmd.xfer);
@@ -1138,13 +1151,13 @@ static int32_t scsi_send_command(SCSIRequest *req, 
uint8_t *buf)
 scsi_command_complete(r, GOOD, SENSE_CODE(NO_SENSE));
 }
 len = r->sector_count * 512 + r->iov.iov_len;
-if (is_write) {
-len = -len;
+if (r->req.cmd.mode == SCSI_XFER_TO_DEV) {
+return -len;
 } else {
 if (!r->sector_count)
 r->sector_count = -1;
+return len;
 }
-return len;
 }
 
 static void scsi_disk_reset(DeviceState *dev)
-- 
1.7.4.4





[Qemu-devel] [PATCH v3 20/21] scsi-generic: Handle queue full

2011-05-17 Thread Paolo Bonzini
The sg driver currently has a hardcoded limit of commands it
can handle simultaneously. When this limit is reached the
driver will return -EDOM. So we need to capture this to
enable proper return values here.

Signed-off-by: Hannes Reinecke 

Signed-off-by: Paolo Bonzini 
---
 hw/scsi-generic.c |3 +++
 1 files changed, 3 insertions(+), 0 deletions(-)

diff --git a/hw/scsi-generic.c b/hw/scsi-generic.c
index 1ea0930..0c04606 100644
--- a/hw/scsi-generic.c
+++ b/hw/scsi-generic.c
@@ -124,6 +124,9 @@ static void scsi_command_complete(void *opaque, int ret)
 
 if (ret != 0) {
 switch (ret) {
+case -EDOM:
+r->req.status = TASK_SET_FULL;
+break;
 case -EINVAL:
 r->req.status = CHECK_CONDITION;
 scsi_set_sense(s, SENSE_CODE(INVALID_FIELD));
-- 
1.7.4.4





Re: [Qemu-devel] [RESEND][PATCH 3/9] microdrive: qdevify

2011-05-17 Thread andrzej zaborowski
On 17 May 2011 07:44, Jan Kiszka  wrote:
> On 2011-05-17 03:38, andrzej zaborowski wrote:
>> On 16 May 2011 15:08, Dmitry Eremin-Solenikov  wrote:
>>> On 5/16/11, andrzej zaborowski  wrote:
 On 16 May 2011 06:54, Dmitry Eremin-Solenikov  wrote:
> Socket is required, as we have to know the QBus before creating the
> device on it.

 Let's skip the qbusification then.  It seems that qbus is a wrong
 choice for pcmcia and there are no new features or bugs fixed by the
 conversion, it's code motion?  I also don't see why the socket
 structure should be needed at the creation time of a PCI device for
 example, the BusInfo should be enough logically.
>>>
>>> Major point for qbus'ification was ability to create PCMCIA devices from
>>> command line/via other management tools. This would also allow us e.g.
>>> to move microdrive driver to common ide parts, etc.
>>
>> That would be nice but it may be better to use separate command line
>> switches / monitor commands for hotpluggable busses.
>>
>>>
>>> For creation of a DeviceState via qdev_create you need BusState (which
>>> is a part of PCMCIASocket). Of course I can make one global QBus for
>>> all PCMCIA devices and make some artificial hacks to attach/detach cards
>>> to artificial sockets, but this seems like a hack.
>>
>> I considered that for a moment too but it's uglier than current code
>> and doesn't achieve what you want, because the command line has no
>> provision for triggering attachment.  A major problem with qdev I see
>> now is that the creation and attachment of a device are one event
>> instead of two, which is the case for pcmcia.  So your patch tries to
>> merge these two events.
>
> What is the point of allowing the existence of unattached pcmcia
> devices? I think there was similar discussion about usb to allow attach
> detach without delete, but IIRC that was finally rejected as there is no
> real benefit in avoiding full creation/destruction.

It's more about being able to detach and re-attach (in the same socket
or another), migrate, savevm/loadvm separately from the machine
although this possibility is not used now anyway.  I just think it's
logical for a hotpluggable bus that this be possible and it's wrong to
require the socket structure when creating a device, although I'll
ack/push the patches if that's a general opinion.

>
> Keep in mind that there may be a day where we finally obsolete support
> for non-qdev (or whatever it's name will be then) devices.

Not allowing non-qdev devices would be difficult to do because a
"device" is just a set of memory mappings and it's a fuzzy term
altogether (in SoCs especially).  What I'd like to avoid is shuffling
a piece of code into an api it does not fit just because there's a
trend to use it, you can burn cycles endlessly reordering code with no
new features/bugs fixed.

Cheers



Re: [Qemu-devel] [PATCH] Fix a number of unused-but-set-variable warnings (new with gcc-4.6)

2011-05-17 Thread Christophe Fergeau
Hi Hans,

On Tue, May 03, 2011 at 01:03:40PM +0200, Hans de Goede wrote:
> diff --git a/target-i386/kvm.c b/target-i386/kvm.c
> index a13599d..e9e8d54 100644
> --- a/target-i386/kvm.c
> +++ b/target-i386/kvm.c
> @@ -950,7 +950,7 @@ static int kvm_get_xsave(CPUState *env)
> @@ -966,7 +966,7 @@ static int kvm_get_xsave(CPUState *env)
>  cwd = (uint16_t)xsave->region[0];
>  swd = (uint16_t)(xsave->region[0] >> 16);
>  twd = (uint16_t)xsave->region[1];
> -fop = (uint16_t)(xsave->region[1] >> 16);
> +/* fop = (uint16_t)(xsave->region[1] >> 16); */

Wouldn't it be better to drop this line?

>  env->fpstt = (swd >> 11) & 7;
>  env->fpus = swd;
>  env->fpuc = cwd;
> diff --git a/tcg/tcg.c b/tcg/tcg.c
> index 8748c05..11a8daf 100644
> --- a/tcg/tcg.c
> +++ b/tcg/tcg.c
> @@ -585,7 +585,7 @@ void tcg_register_helper(void *func, const char *name)
>  void tcg_gen_callN(TCGContext *s, TCGv_ptr func, unsigned int flags,
> int sizemask, TCGArg ret, int nargs, TCGArg *args)
>  {
> -#ifdef TCG_TARGET_I386
> +#if defined TCG_TARGET_I386 && TCG_TARGET_REG_BITS < 64 

This function uses #if defined(TCG_TARGET_I386) in other places, so I'd use
parentheses here for consistency.

>  int call_type;
>  #endif
>  int i;
> @@ -612,7 +612,7 @@ void tcg_gen_callN(TCGContext *s, TCGv_ptr func, unsigned 
> int flags,
>  
>  *gen_opc_ptr++ = INDEX_op_call;
>  nparam = gen_opparam_ptr++;
> -#ifdef TCG_TARGET_I386
> +#if defined TCG_TARGET_I386 && TCG_TARGET_REG_BITS < 64 

Same here.

Apart from that, I also need this patch to be able to build qemu on fedora
15 :)

Christophe


pgpOAaUcYjwZI.pgp
Description: PGP signature


Re: [Qemu-devel] [RESEND][PATCH 3/9] microdrive: qdevify

2011-05-17 Thread Jan Kiszka
On 2011-05-17 13:08, andrzej zaborowski wrote:
> On 17 May 2011 07:44, Jan Kiszka  wrote:
>> On 2011-05-17 03:38, andrzej zaborowski wrote:
>>> On 16 May 2011 15:08, Dmitry Eremin-Solenikov  wrote:
 On 5/16/11, andrzej zaborowski  wrote:
> On 16 May 2011 06:54, Dmitry Eremin-Solenikov  
> wrote:
>> Socket is required, as we have to know the QBus before creating the
>> device on it.
>
> Let's skip the qbusification then.  It seems that qbus is a wrong
> choice for pcmcia and there are no new features or bugs fixed by the
> conversion, it's code motion?  I also don't see why the socket
> structure should be needed at the creation time of a PCI device for
> example, the BusInfo should be enough logically.

 Major point for qbus'ification was ability to create PCMCIA devices from
 command line/via other management tools. This would also allow us e.g.
 to move microdrive driver to common ide parts, etc.
>>>
>>> That would be nice but it may be better to use separate command line
>>> switches / monitor commands for hotpluggable busses.
>>>

 For creation of a DeviceState via qdev_create you need BusState (which
 is a part of PCMCIASocket). Of course I can make one global QBus for
 all PCMCIA devices and make some artificial hacks to attach/detach cards
 to artificial sockets, but this seems like a hack.
>>>
>>> I considered that for a moment too but it's uglier than current code
>>> and doesn't achieve what you want, because the command line has no
>>> provision for triggering attachment.  A major problem with qdev I see
>>> now is that the creation and attachment of a device are one event
>>> instead of two, which is the case for pcmcia.  So your patch tries to
>>> merge these two events.
>>
>> What is the point of allowing the existence of unattached pcmcia
>> devices? I think there was similar discussion about usb to allow attach
>> detach without delete, but IIRC that was finally rejected as there is no
>> real benefit in avoiding full creation/destruction.
> 
> It's more about being able to detach and re-attach (in the same socket
> or another)

I haven't looked at the details of this particular issue, but from 1
meters I do not yet understand how qdev prevents this. Do we lack
addressability via qdev for these sockets? Then that would have to be fixed.

>, migrate, savevm/loadvm separately from the machine
> although this possibility is not used now anyway.  I just think it's
> logical for a hotpluggable bus that this be possible and it's wrong to
> require the socket structure when creating a device, although I'll
> ack/push the patches if that's a general opinion.
> 
>>
>> Keep in mind that there may be a day where we finally obsolete support
>> for non-qdev (or whatever it's name will be then) devices.
> 
> Not allowing non-qdev devices would be difficult to do because a
> "device" is just a set of memory mappings and it's a fuzzy term
> altogether (in SoCs especially).

Even in the SoC domain, I did not come across any set of "memory
mappings" that could not reasonably be abstractable to a device, thus
could be wrapped by qdev. That there is usually no chip containing such
a device in reality does not mean you can't and shouldn't handle it as
an abstract one, encapsulating separate functions in a more complex chip.

>  What I'd like to avoid is shuffling
> a piece of code into an api it does not fit just because there's a
> trend to use it, you can burn cycles endlessly reordering code with no
> new features/bugs fixed.

No longer having arbitrary, untraceable memory and io mappings but only
well organized devices is a feature worth such shuffling. Usually that
also offers the chance to clean up legacy code or complete half-done
device models.

We are good in inventing new APIs in QEMU, but so far we are not that
successful getting rid of old ones.

Jan

-- 
Siemens AG, Corporate Technology, CT T DE IT 1
Corporate Competence Center Embedded Linux



[Qemu-devel] [PATCH] libcacard: add libcacard.la target

2011-05-17 Thread Alon Levy
No flag to configure is required. Instead, added a libcacard.la target that
is not built by default, only when requested explicitly via:

mkdir build
cd build
../configure
make libcacard.la
make install-libcacard

Uses libtool to do actual linking of object files and shared library, and
installing. Tested only under linux, but supposed to work on other systems as
well.

If libtool isn't found you get a message complaining about that, only at build
time (since it is not a default target I did not add a message at configure
time).

New build artifacts:
 .libs subdirectories (at  and /libcacard)
 *.lo files (at same locations as the respective o files)

Added %.lo : %.c rule that uses libtool.
Updated clean rule to clean up those artifacts.
Added specific rule to call dtrace with libtool wrapper (note that because of
a current upstream dtrace bug fixed by systemtap b1568fd85 commit the -fPIC flag
isn't actually passed on. still current dtrace+libtool produced object links 
fine).

Tested to link and load with all tracing backends except ust (no default package
for my development computer for ust).
---
 Makefile   |   20 +++-
 Makefile.objs  |3 +++
 configure  |   12 +++-
 libcacard/Makefile |   32 
 rules.mak  |3 +++
 5 files changed, 64 insertions(+), 6 deletions(-)

diff --git a/Makefile b/Makefile
index 2b0438c..c71026c 100644
--- a/Makefile
+++ b/Makefile
@@ -119,6 +119,23 @@ version.o: $(SRC_PATH)/version.rc config-host.mak
 
 version-obj-$(CONFIG_WIN32) += version.o
 ##
+# Support building shared library libcacard
+
+.PHONY: libcacard.la install-libcacard
+ifeq ($(LIBTOOL),)
+libcacard.la:
+   @echo libtool is missing, please install and rerun configure
+
+install-libcacard:
+   @echo libtool is missing, please install and rerun configure
+else
+libcacard.la: $(GENERATED_HEADERS) $(oslib-obj-y) qemu-malloc.o 
qemu-timer-common.o $(addsuffix .lo, $(basename $(trace-obj-y)))
+   $(call quiet-command,$(MAKE) $(SUBDIR_MAKEFLAGS) -C libcacard V="$(V)" 
TARGET_DIR="$*/" libcacard.la,)
+
+install-libcacard: libcacard.la
+   $(call quiet-command,$(MAKE) $(SUBDIR_MAKEFLAGS) -C libcacard V="$(V)" 
TARGET_DIR="$*/" install-libcacard,)
+endif
+##
 
 qemu-img.o: qemu-img-cmds.h
 qemu-img.o qemu-tool.o qemu-nbd.o qemu-io.o cmd.o: $(GENERATED_HEADERS)
@@ -149,7 +166,8 @@ clean:
 # avoid old build problems by removing potentially incorrect old files
rm -f config.mak op-i386.h opc-i386.h gen-op-i386.h op-arm.h opc-arm.h 
gen-op-arm.h
rm -f qemu-options.def
-   rm -f *.o *.d *.a $(TOOLS) TAGS cscope.* *.pod *~ */*~
+   rm -f *.o *.d *.a *.lo $(TOOLS) TAGS cscope.* *.pod *~ */*~
+   rm -Rf .libs
rm -f slirp/*.o slirp/*.d audio/*.o audio/*.d block/*.o block/*.d 
net/*.o net/*.d fsdev/*.o fsdev/*.d ui/*.o ui/*.d
rm -f qemu-img-cmds.h
rm -f trace.c trace.h trace.c-timestamp trace.h-timestamp
diff --git a/Makefile.objs b/Makefile.objs
index 4478c61..850e707 100644
--- a/Makefile.objs
+++ b/Makefile.objs
@@ -344,6 +344,9 @@ trace-dtrace.dtrace-timestamp: $(SRC_PATH)/trace-events 
config-host.mak
 trace-dtrace.o: trace-dtrace.dtrace $(GENERATED_HEADERS)
$(call quiet-command,dtrace -o $@ -G -s $<, "  GEN trace-dtrace.o")
 
+trace-dtrace.lo: trace-dtrace.dtrace
+   $(call quiet-command,libtool --mode=compile --tag=CC dtrace -o $@ -G -s 
$<, "  lt GEN trace-dtrace.o")
+
 simpletrace.o: simpletrace.c $(GENERATED_HEADERS)
 
 ifeq ($(TRACE_BACKEND),dtrace)
diff --git a/configure b/configure
index 0627f1d..e62841e 100755
--- a/configure
+++ b/configure
@@ -1276,6 +1276,15 @@ if ! has $pkg_config; then
 fi
 
 ##
+# libtool probe
+
+if ! has libtool; then
+libtool=
+else
+libtool=libtool
+fi
+
+##
 # Sparse probe
 if test "$sparse" != "no" ; then
   if has cgcc; then
@@ -3060,6 +3069,7 @@ echo "AR=$ar" >> $config_host_mak
 echo "OBJCOPY=$objcopy" >> $config_host_mak
 echo "LD=$ld" >> $config_host_mak
 echo "WINDRES=$windres" >> $config_host_mak
+echo "LIBTOOL=$libtool" >> $config_host_mak
 echo "CFLAGS=$CFLAGS" >> $config_host_mak
 echo "QEMU_CFLAGS=$QEMU_CFLAGS" >> $config_host_mak
 echo "QEMU_INCLUDES=$QEMU_INCLUDES" >> $config_host_mak
@@ -3595,7 +3605,7 @@ if [ "$source_path" != `pwd` ]; then
 # out of tree build
 mkdir -p libcacard
 rm -f libcacard/Makefile
-ln -s "$source_path/libcacard/Makefile" libcacard/Makefile
+symlink "$source_path/libcacard/Makefile" libcacard/Makefile
 fi
 
 d=libuser
diff --git a/libcacard/Makefile b/libcacard/Makefile
index 1d34df0..a35bca4 100644
--- a/libcacard/Makefile
+++ b/libcacard/Makefile
@@ -4,15 +4,39 @@
 
 $(call set-vpath, $(SRC_PATH):$(SRC_PATH)/libcacard)
 
-QEMU_OBJS=$(addprefix ..

Re: [Qemu-devel] [PATCH] libcacard: add libcacard.la target

2011-05-17 Thread Alon Levy
On Tue, May 17, 2011 at 03:03:45PM +0300, Alon Levy wrote:

Forgot to mention this is the v3, with the following fixes:
 * no warning, properly use libtool to wrap dtrace (which calls gcc).
 * tested with all tracing backends but ust (and in the process of testing that)
 * moved general rule for producing .lo to rules.mak, with the exception 
(trace-dtrace.lo)
  in Makefile.objs (same as trace-dtrace.o rule)
 * fixed clean to remove the artifacts.

> No flag to configure is required. Instead, added a libcacard.la target that
> is not built by default, only when requested explicitly via:
> 
> mkdir build
> cd build
> ../configure
> make libcacard.la
> make install-libcacard
> 
> Uses libtool to do actual linking of object files and shared library, and
> installing. Tested only under linux, but supposed to work on other systems as
> well.
> 
> If libtool isn't found you get a message complaining about that, only at build
> time (since it is not a default target I did not add a message at configure
> time).
> 
> New build artifacts:
>  .libs subdirectories (at  and /libcacard)
>  *.lo files (at same locations as the respective o files)
> 
> Added %.lo : %.c rule that uses libtool.
> Updated clean rule to clean up those artifacts.
> Added specific rule to call dtrace with libtool wrapper (note that because of
> a current upstream dtrace bug fixed by systemtap b1568fd85 commit the -fPIC 
> flag
> isn't actually passed on. still current dtrace+libtool produced object links 
> fine).
> 
> Tested to link and load with all tracing backends except ust (no default 
> package
> for my development computer for ust).
> ---
>  Makefile   |   20 +++-
>  Makefile.objs  |3 +++
>  configure  |   12 +++-
>  libcacard/Makefile |   32 
>  rules.mak  |3 +++
>  5 files changed, 64 insertions(+), 6 deletions(-)
> 
> diff --git a/Makefile b/Makefile
> index 2b0438c..c71026c 100644
> --- a/Makefile
> +++ b/Makefile
> @@ -119,6 +119,23 @@ version.o: $(SRC_PATH)/version.rc config-host.mak
>  
>  version-obj-$(CONFIG_WIN32) += version.o
>  ##
> +# Support building shared library libcacard
> +
> +.PHONY: libcacard.la install-libcacard
> +ifeq ($(LIBTOOL),)
> +libcacard.la:
> + @echo libtool is missing, please install and rerun configure
> +
> +install-libcacard:
> + @echo libtool is missing, please install and rerun configure
> +else
> +libcacard.la: $(GENERATED_HEADERS) $(oslib-obj-y) qemu-malloc.o 
> qemu-timer-common.o $(addsuffix .lo, $(basename $(trace-obj-y)))
> + $(call quiet-command,$(MAKE) $(SUBDIR_MAKEFLAGS) -C libcacard V="$(V)" 
> TARGET_DIR="$*/" libcacard.la,)
> +
> +install-libcacard: libcacard.la
> + $(call quiet-command,$(MAKE) $(SUBDIR_MAKEFLAGS) -C libcacard V="$(V)" 
> TARGET_DIR="$*/" install-libcacard,)
> +endif
> +##
>  
>  qemu-img.o: qemu-img-cmds.h
>  qemu-img.o qemu-tool.o qemu-nbd.o qemu-io.o cmd.o: $(GENERATED_HEADERS)
> @@ -149,7 +166,8 @@ clean:
>  # avoid old build problems by removing potentially incorrect old files
>   rm -f config.mak op-i386.h opc-i386.h gen-op-i386.h op-arm.h opc-arm.h 
> gen-op-arm.h
>   rm -f qemu-options.def
> - rm -f *.o *.d *.a $(TOOLS) TAGS cscope.* *.pod *~ */*~
> + rm -f *.o *.d *.a *.lo $(TOOLS) TAGS cscope.* *.pod *~ */*~
> + rm -Rf .libs
>   rm -f slirp/*.o slirp/*.d audio/*.o audio/*.d block/*.o block/*.d 
> net/*.o net/*.d fsdev/*.o fsdev/*.d ui/*.o ui/*.d
>   rm -f qemu-img-cmds.h
>   rm -f trace.c trace.h trace.c-timestamp trace.h-timestamp
> diff --git a/Makefile.objs b/Makefile.objs
> index 4478c61..850e707 100644
> --- a/Makefile.objs
> +++ b/Makefile.objs
> @@ -344,6 +344,9 @@ trace-dtrace.dtrace-timestamp: $(SRC_PATH)/trace-events 
> config-host.mak
>  trace-dtrace.o: trace-dtrace.dtrace $(GENERATED_HEADERS)
>   $(call quiet-command,dtrace -o $@ -G -s $<, "  GEN trace-dtrace.o")
>  
> +trace-dtrace.lo: trace-dtrace.dtrace
> + $(call quiet-command,libtool --mode=compile --tag=CC dtrace -o $@ -G -s 
> $<, "  lt GEN trace-dtrace.o")
> +
>  simpletrace.o: simpletrace.c $(GENERATED_HEADERS)
>  
>  ifeq ($(TRACE_BACKEND),dtrace)
> diff --git a/configure b/configure
> index 0627f1d..e62841e 100755
> --- a/configure
> +++ b/configure
> @@ -1276,6 +1276,15 @@ if ! has $pkg_config; then
>  fi
>  
>  ##
> +# libtool probe
> +
> +if ! has libtool; then
> +libtool=
> +else
> +libtool=libtool
> +fi
> +
> +##
>  # Sparse probe
>  if test "$sparse" != "no" ; then
>if has cgcc; then
> @@ -3060,6 +3069,7 @@ echo "AR=$ar" >> $config_host_mak
>  echo "OBJCOPY=$objcopy" >> $config_host_mak
>  echo "LD=$ld" >> $config_host_mak
>  echo "WINDRES=$windres" >> $config_host_mak
> +echo "LIBTOOL=$libtool" >> $config_host_m

[Qemu-devel] [PATCH] linux-user: Handle images where lowest vaddr is not page aligned

2011-05-17 Thread Peter Maydell
Fix a bug in the linux-user ELF loader code where it was not correctly
handling images where the lowest vaddr to be loaded was not page aligned.
The problem was that the code to probe for a suitable guest base address
was changing the 'loaddr' variable (by rounding it to a page boundary),
which meant that the load bias would then be incorrectly calculated
unless loaddr happened to already be page-aligned.

Binaries generated by gcc with the default linker script do start with
a loadable segment at a page-aligned vaddr, so were unaffected. This
bug was noticed with a binary created by the Google Go toolchain for ARM.

We fix the bug by refactoring the "probe for guest base" code out into
its own self-contained function.

Signed-off-by: Peter Maydell 
---
 linux-user/elfload.c |  130 --
 1 files changed, 73 insertions(+), 57 deletions(-)

diff --git a/linux-user/elfload.c b/linux-user/elfload.c
index 4c399f8..930f6d3 100644
--- a/linux-user/elfload.c
+++ b/linux-user/elfload.c
@@ -1269,6 +1269,78 @@ static abi_ulong create_elf_tables(abi_ulong p, int 
argc, int envc,
 return sp;
 }
 
+static void probe_guest_base(const char *image_name,
+ abi_ulong loaddr, abi_ulong hiaddr)
+{
+/* Probe for a suitable guest base address, if the user has not set
+ * it explicitly, and set guest_base appropriately.
+ * In case of error we will print a suitable message and exit.
+ */
+#if defined(CONFIG_USE_GUEST_BASE)
+const char *errmsg;
+if (!have_guest_base && !reserved_va) {
+unsigned long host_start, real_start, host_size;
+
+/* Round addresses to page boundaries.  */
+loaddr &= qemu_host_page_mask;
+hiaddr = HOST_PAGE_ALIGN(hiaddr);
+
+if (loaddr < mmap_min_addr) {
+host_start = HOST_PAGE_ALIGN(mmap_min_addr);
+} else {
+host_start = loaddr;
+if (host_start != loaddr) {
+errmsg = "Address overflow loading ELF binary";
+goto exit_errmsg;
+}
+}
+host_size = hiaddr - loaddr;
+while (1) {
+/* Do not use mmap_find_vma here because that is limited to the
+   guest address space.  We are going to make the
+   guest address space fit whatever we're given.  */
+real_start = (unsigned long)
+mmap((void *)host_start, host_size, PROT_NONE,
+ MAP_ANONYMOUS | MAP_PRIVATE | MAP_NORESERVE, -1, 0);
+if (real_start == (unsigned long)-1) {
+goto exit_perror;
+}
+if (real_start == host_start) {
+break;
+}
+/* That address didn't work.  Unmap and try a different one.
+   The address the host picked because is typically right at
+   the top of the host address space and leaves the guest with
+   no usable address space.  Resort to a linear search.  We
+   already compensated for mmap_min_addr, so this should not
+   happen often.  Probably means we got unlucky and host
+   address space randomization put a shared library somewhere
+   inconvenient.  */
+munmap((void *)real_start, host_size);
+host_start += qemu_host_page_size;
+if (host_start == loaddr) {
+/* Theoretically possible if host doesn't have any suitably
+   aligned areas.  Normally the first mmap will fail.  */
+errmsg = "Unable to find space for application";
+goto exit_errmsg;
+}
+}
+qemu_log("Relocating guest address space from 0x"
+ TARGET_ABI_FMT_lx " to 0x%lx\n",
+ loaddr, real_start);
+guest_base = real_start - loaddr;
+}
+return;
+
+exit_perror:
+errmsg = strerror(errno);
+exit_errmsg:
+fprintf(stderr, "%s: %s\n", image_name, errmsg);
+exit(-1);
+#endif
+}
+
+
 /* Load an ELF image into the address space.
 
IMAGE_NAME is the filename of the image, to use in error messages.
@@ -1354,63 +1426,7 @@ static void load_elf_image(const char *image_name, int 
image_fd,
 /* This is the main executable.  Make sure that the low
address does not conflict with MMAP_MIN_ADDR or the
QEMU application itself.  */
-#if defined(CONFIG_USE_GUEST_BASE)
-/*
- * In case where user has not explicitly set the guest_base, we
- * probe here that should we set it automatically.
- */
-if (!have_guest_base && !reserved_va) {
-unsigned long host_start, real_start, host_size;
-
-/* Round addresses to page boundaries.  */
-loaddr &= qemu_host_page_mask;
-hiaddr = HOST_PAGE_ALIGN(hiaddr);
-
-if (loaddr < mmap_min_addr) {
-host_start = HOST_PAGE_ALIGN(mmap_min_addr);
-

Re: [Qemu-devel] [PATCH 18/18] usb: add ehci adapter

2011-05-17 Thread David Ahern


On 05/17/11 01:20, Gerd Hoffmann wrote:
>> On 05/16/11 13:56, Gerd Hoffmann wrote:
>>> This patch finally merges the EHCI host adapter aka USB 2.0 support.
>>>
>>> Based on git://git.kiszka.org/qemu.git ehci
>>>
>>> Changes:
>>>- Adapt to recent changes in the usb subsystem.
>>>- Don't create device automagically, use -device instead.
>>>- Add quickstart text file, see docs/usb2.txt.
>>>- A bunch of codestyle fixups.
>>>- Add authors+contributers list.
>>>- Zap EHCI_NOMICROFRAMES, qemu can't handle a 8 kHz
>>>  wakeup rate anyway.
>>>- A few bug fixes.
>>>
>>> Signed-off-by: Gerd Hoffmann
>>
>> As someone who spent a significant amount of time working on the EHCI
>> code last year I am absolutely not ok with this. The entire contribution
>> history for EHCI lost - and for no reason.
> 
> There is a reason.  I've tried to keep the history, but it was a big
> mess with conflicts and build errors due to ehci being out-of-tree for a
> loong time.

Not true. Back in March it took me less 2-1/2 hours to see a request for
a 0.14 version, update my git repo, merge master onto ehci, fix merges,
test and send out:

http://comments.gmane.org/gmane.comp.emulators.kvm.devel/68898

Again, most of the changes are to the EHCI code. The rest are
sprinklings to add the adapter and adhere to USB API.

> 
>> The inclusion of EHCI into
>> qemu can be done in such a way as to maintain the history.
> 
> Prove it.  Give me a git tree with ehci history I can use as replacement
> for patch 18 and I'll pull it in.

Jan's tree that was started for the EHCI development. That's my repo
locally is based on. You chose to not work with it or even get a pull
request to pull in the patches. Instead you opted to pick up the code
and plop into your repo.

David

> 
> cheers,
>   Gerd



Re: [Qemu-devel] [PatchV3] s390x: fix memory detection for guests > 64GB

2011-05-17 Thread Alexander Graf

On 12.05.2011, at 10:50, Christian Borntraeger wrote:

>> I'd definitely prefer that over the change on vl.c :)
> 
> the s390 memory detection has a 16bit field that specifies the amount of
> increments. This patch adopts the memory size to always fit into that
> scheme. This also fixes virtio detection for these guests, since the 
> descriptor page is located after the main memory.

How did you test the patch?

agraf@s390t27:/home/agraf/git/qemu> ./s390x-softmmu/qemu-system-s390x -snapshot 
-nographic /media/studio/images/SUSE/s390/sles11.raw -kernel /boot/image -m 
3600 -enable-kvm

[works]

agraf@s390t27:/home/agraf/git/qemu> ./s390x-softmmu/qemu-system-s390x -snapshot 
-nographic /media/studio/images/SUSE/s390/sles11.raw -kernel /boot/image -m 
3700 -enable-kvm
qemu_madvise: Invalid argument
Need MADV_DONTFORK in absence of synchronous KVM MMU

agraf@s390t27:/home/agraf/git/qemu> ./s390x-softmmu/qemu-system-s390x -snapshot 
-nographic /media/studio/images/SUSE/s390/sles11.raw -kernel /boot/image -m 
3700 Segmentation fault


Alex




Re: [Qemu-devel] AHCI problems.

2011-05-17 Thread Alexander Graf

On 15.05.2011, at 18:41, Alexey Zaytsev wrote:

> Hi again.
> 
> After reverting 667bb59, ahci works fine in Linux, if I boot it with
> -kernel, but grub seems to have some problems.
> Grub2 gets to the rescue prompt. The disk and its partitions seem to
> be detected correctly, but not the filesystem.
> Grub-legacy (from illumos) complains about checksum verification
> failures, supposedly in stage2.

So I just tried again and grub-legacy works just fine for me with an opensuse 
image, after rebuilding SeaBIOS to enable AHCI. I suppose you're trying this on 
Ubuntu?


Alex




Re: [Qemu-devel] [PATCH 18/18] usb: add ehci adapter

2011-05-17 Thread Gerd Hoffmann

  Hi,


As someone who spent a significant amount of time working on the EHCI
code last year I am absolutely not ok with this. The entire contribution
history for EHCI lost - and for no reason.


There is a reason.  I've tried to keep the history, but it was a big
mess with conflicts and build errors due to ehci being out-of-tree for a
loong time.


Not true. Back in March it took me less 2-1/2 hours to see a request for
a 0.14 version, update my git repo, merge master onto ehci, fix merges,
test and send out:

http://comments.gmane.org/gmane.comp.emulators.kvm.devel/68898

Again, most of the changes are to the EHCI code. The rest are
sprinklings to add the adapter and adhere to USB API.


And it totally ignores the usb changes which went into 0.14 to prepare 
the qemu usb subsystem for higher speeds.  There is no such thing like a 
v1 or v2 usb bus.


You've mailed out a single monster patch instead of a patch series. 
That is the problem with merges:  You can trivially get a full diff 
against master, but you can't easily get a nicely review-able patch series.


I've tried to rebase the ehci tree.  First, to fix the patch series 
issue.  Second to adapt patches to qemu changes, to make the patch 
series bisect-able.  Also to drop obsolete bits.  That didn't work out 
as described.  You didn't even try.


I'm not impressed.

cheers,
  Gerd




Re: [Qemu-devel] [PATCH 18/18] usb: add ehci adapter

2011-05-17 Thread David Ahern


On 05/17/11 06:42, David Ahern wrote:
> 
> 
> On 05/17/11 01:20, Gerd Hoffmann wrote:
>>> On 05/16/11 13:56, Gerd Hoffmann wrote:
 This patch finally merges the EHCI host adapter aka USB 2.0 support.

 Based on git://git.kiszka.org/qemu.git ehci

 Changes:
- Adapt to recent changes in the usb subsystem.
- Don't create device automagically, use -device instead.
- Add quickstart text file, see docs/usb2.txt.
- A bunch of codestyle fixups.
- Add authors+contributers list.
- Zap EHCI_NOMICROFRAMES, qemu can't handle a 8 kHz
  wakeup rate anyway.
- A few bug fixes.

 Signed-off-by: Gerd Hoffmann
>>>
>>> As someone who spent a significant amount of time working on the EHCI
>>> code last year I am absolutely not ok with this. The entire contribution
>>> history for EHCI lost - and for no reason.
>>
>> There is a reason.  I've tried to keep the history, but it was a big
>> mess with conflicts and build errors due to ehci being out-of-tree for a
>> loong time.
> 
> Not true. Back in March it took me less 2-1/2 hours to see a request for
> a 0.14 version, update my git repo, merge master onto ehci, fix merges,
> test and send out:
> 
> http://comments.gmane.org/gmane.comp.emulators.kvm.devel/68898
> 
> Again, most of the changes are to the EHCI code. The rest are
> sprinklings to add the adapter and adhere to USB API.
> 
>>
>>> The inclusion of EHCI into
>>> qemu can be done in such a way as to maintain the history.
>>
>> Prove it.  Give me a git tree with ehci history I can use as replacement
>> for patch 18 and I'll pull it in.
> 
> Jan's tree that was started for the EHCI development. That's my repo
> locally is based on. You chose to not work with it or even get a pull
> request to pull in the patches. Instead you opted to pick up the code
> and plop into your repo.
> 
> David

Let me turn this around. Your contributions to the EHCI code:
1. coding standards,
2. internal qemu API
3. nuking code based on 8kHz.

All of those could have been done in Jan's tree and from there have a
Jan do a pull request to the maintainers. It is not hard.

(And by the way, where are the focused patches for each, especially the
last one - nuking the 8kHz code?  We know that it worked on linux and
that printers, scanners and storage devices worked ok (mostly). Changes
made in a vacuum despite prior patches and interest from qemu users -
some of whom are using the EHCI code.)

David



> 
>>
>> cheers,
>>   Gerd
> 
> 



Re: [Qemu-devel] [PATCH 00/26] q35 chipset support for native pci express support

2011-05-17 Thread Isaku Yamahata
On Tue, May 17, 2011 at 09:15:39AM +0200, Jan Kiszka wrote:
> On 2011-05-16 23:55, Adnan Khaleel wrote:
> > I finally got this work after I realised that the AHCI driver was not being 
> > loaded in my disk image and that ACHI was not being enabled in the Seabios 
> > .config file.
> > This is really good work Yamahata, thanks.
> > 
> > 
> > As far as I can tell, everything works like the stock Qemu 0.14 except 
> > networking. The guest OS sees the network device and initialises it but I 
> > think the Qemu DHCP server/firewall never gets back, since the network 
> > device doesn't even get a 10.0.2.15 ip address during bootup and the guest 
> > dhcp client never gets an ip address, 
> > 
> > 
> > eth0   device: Intel Corporation 82540EM Gigabit Ethernet Controller (rev 
> > 03)
> > eth0   Starting DHCP4 client. . . . . . . .
> > eth0   DHCP4 continues in background 
> > eth0   device: Intel Corporation 82540EM Gigabit Ethernet Controller (rev 
> > 03)
> > eth0   DHCP4 client (dhcpcd) is running
> > eth0   . . . but is still waiting for data
> > eth0   interface could not be set up until now
> > 
> > 
> > So doing an ifconfig later on just shows
> > 
> > 
> > eth0   Link encap:Ethernet  HWaddr 52:54:00:12:34:56
> >  UP BROADCAST MULTICAST  MTU:1500  Metric:1
> >  RX packets:0 errors:0 dropped:0 overruns:0 frame:0
> >  TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
> >  collisions:0 txqueuelen:1000
> >  RX bytes:0 (0.0 b)   TX bytes:0 (0.0 b)
> > 
> > 
> > 
> > lo  Link encap:Local loopback  
> >  inet addr:127.0.0.1  Mask:255.0.0.0
> >  inet6 addr: ::1/128 Scope:Host
> >  UP LOOPBACK RUNING  MTU:16436  Metric:1
> >  RX packets:0 errors:0 dropped:0 overruns:0 frame:0
> >  TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
> >  collisions:0 txqueuelen:1000
> >  RX bytes:0 (0.0 b)   TX bytes:0 (0.0 b)
> > 
> > 
> > I'm going to start a separate thread to see what the possible cause might 
> > be and what might be the best way to debug this. Do you have any idea if 
> > this q35 chipset going to be committed to Qemu upstream?
> 
> I've recently hacked a bit on q35, rebased it over current master, found
> and fixed a few bugs to allow booting of WinXP and Win7, and
> particularly added kvm support to improve testability significantly. You
> can find my current work at
> 
> git://git.kiszka.org/qemu.git q35-test
> git://git.kiszka.org/seabios.git q35-test
> 
> There are some issues remaining, e.g. usb appeared broken to me. Now I
> just tested your scenario (e1000+usernet) with a Win7 guest, and I do
> not get an IP either. There is no traffic on the vlan (I attached a dump
> device to verify). Looking closer, it seems PCI bar mapping is failing,
> at least partially, see 'info pci'. I hope it's not yet another ACPI
> issue. Fixing the polarity bug already forced me to dig way too deep
> into this horrible domain.

Wow, very great. So is kvm working with q35?

I had a quick look at your patches.
With seabios patch of 94710189f5323034e00b510fe5a0865a7b576a9f,
you ignored MCFG area.

(start = Q35_HOST_BRIDGE_PCIEXBAR_ADDR, size = 256MB) is used
for MCFG (!= pci region), so it can't be used for PCI region.
That's why 256M is added to s.
And Q35_HOST_BRIDGE_PCIEXBAR_ADDR in dev-q35.h also needs to be adjusted.

After pushing out pci id clean up and once they are accepted,
I'll publish rebased/cleaned up one.
-- 
yamahata



Re: [Qemu-devel] [PatchV3] s390x: fix memory detection for guests > 64GB

2011-05-17 Thread Alexander Graf

On 17.05.2011, at 15:16, Alexander Graf wrote:

> 
> On 12.05.2011, at 10:50, Christian Borntraeger wrote:
> 
>>> I'd definitely prefer that over the change on vl.c :)
>> 
>> the s390 memory detection has a 16bit field that specifies the amount of
>> increments. This patch adopts the memory size to always fit into that
>> scheme. This also fixes virtio detection for these guests, since the 
>> descriptor page is located after the main memory.
> 
> How did you test the patch?
> 
> agraf@s390t27:/home/agraf/git/qemu> ./s390x-softmmu/qemu-system-s390x 
> -snapshot -nographic /media/studio/images/SUSE/s390/sles11.raw -kernel 
> /boot/image -m 3600 -enable-kvm
> 
> [works]
> 
> agraf@s390t27:/home/agraf/git/qemu> ./s390x-softmmu/qemu-system-s390x 
> -snapshot -nographic /media/studio/images/SUSE/s390/sles11.raw -kernel 
> /boot/image -m 3700 -enable-kvm
> qemu_madvise: Invalid argument
> Need MADV_DONTFORK in absence of synchronous KVM MMU
> 
> agraf@s390t27:/home/agraf/git/qemu> ./s390x-softmmu/qemu-system-s390x 
> -snapshot -nographic /media/studio/images/SUSE/s390/sles11.raw -kernel 
> /boot/image -m 3700 Segmentation fault

Ah, my fault - I had too little swap space :). Now I can even run an emulated 
VM with >64GB of RAM - yay!


Alex




Re: [Qemu-devel] AHCI problems.

2011-05-17 Thread René Rebe
Hi,
+
On 17.05.2011, at 15:46, Alexander Graf wrote:

> 
> On 15.05.2011, at 18:41, Alexey Zaytsev wrote:
> 
>> Hi again.
>> 
>> After reverting 667bb59, ahci works fine in Linux, if I boot it with
>> -kernel, but grub seems to have some problems.
>> Grub2 gets to the rescue prompt. The disk and its partitions seem to
>> be detected correctly, but not the filesystem.
>> Grub-legacy (from illumos) complains about checksum verification
>> failures, supposedly in stage2.
> 
> So I just tried again and grub-legacy works just fine for me with an opensuse 
> image, after rebuilding SeaBIOS to enable AHCI. I suppose you're trying this 
> on Ubuntu?

This is exactly the phenomena I was seeing the other week when I tested it. 
From a quick glance it looked like the BIOS returned errors when grub tried to 
read the FS.

René

-- 
  René Rebe, ExactCODE GmbH, Jaegerstr. 67, DE-10117 Berlin
  DE Legal: Amtsgericht Charlottenburg HRB 105123B, Tax-ID#: DE251602478
  Managing Directors: Susanne Klaus, René Rebe
  http://exactcode.com | http://t2-project.org | http://rene.rebe.de




Re: [Qemu-devel] AHCI problems.

2011-05-17 Thread Alexander Graf

On 17.05.2011, at 16:07, René Rebe wrote:

> Hi,
> +
> On 17.05.2011, at 15:46, Alexander Graf wrote:
> 
>> 
>> On 15.05.2011, at 18:41, Alexey Zaytsev wrote:
>> 
>>> Hi again.
>>> 
>>> After reverting 667bb59, ahci works fine in Linux, if I boot it with
>>> -kernel, but grub seems to have some problems.
>>> Grub2 gets to the rescue prompt. The disk and its partitions seem to
>>> be detected correctly, but not the filesystem.
>>> Grub-legacy (from illumos) complains about checksum verification
>>> failures, supposedly in stage2.
>> 
>> So I just tried again and grub-legacy works just fine for me with an 
>> opensuse image, after rebuilding SeaBIOS to enable AHCI. I suppose you're 
>> trying this on Ubuntu?
> 
> This is exactly the phenomena I was seeing the other week when I tested it. 
> From a quick glance it looked like the BIOS returned errors when grub tried 
> to read the FS.

Hm. Ok, I'll give Ubuntu a spin then.


Alex




Re: [Qemu-devel] [PATCH 18/18] usb: add ehci adapter

2011-05-17 Thread David Ahern


On 05/17/11 07:46, Gerd Hoffmann wrote:
> 
>   Hi,
> 
 As someone who spent a significant amount of time working on the EHCI
 code last year I am absolutely not ok with this. The entire
 contribution
 history for EHCI lost - and for no reason.
>>>
>>> There is a reason.  I've tried to keep the history, but it was a big
>>> mess with conflicts and build errors due to ehci being out-of-tree for a
>>> loong time.
>>
>> Not true. Back in March it took me less 2-1/2 hours to see a request for
>> a 0.14 version, update my git repo, merge master onto ehci, fix merges,
>> test and send out:
>>
>> http://comments.gmane.org/gmane.comp.emulators.kvm.devel/68898
>>
>> Again, most of the changes are to the EHCI code. The rest are
>> sprinklings to add the adapter and adhere to USB API.
> 
> And it totally ignores the usb changes which went into 0.14 to prepare
> the qemu usb subsystem for higher speeds.  There is no such thing like a
> v1 or v2 usb bus.
> 
> You've mailed out a single monster patch instead of a patch series. That
> is the problem with merges:  You can trivially get a full diff against
> master, but you can't easily get a nicely review-able patch series.

Come on Gerd. That was not an attempt to get it included. Someone asked
for a patch and I took the existing tree, merged with latest and through
out the patch. The v1/v2 is not in Jan's tree. That's a hack I have
locally to have mixed devices. What is shows is that is not a big deal
to move to latest code from Jan's last update in November.

> 
> I've tried to rebase the ehci tree.  First, to fix the patch series
> issue.  Second to adapt patches to qemu changes, to make the patch
> series bisect-able.  Also to drop obsolete bits.  That didn't work out
> as described.  You didn't even try.

Right, you did not even try to work with Jan's tree. There is no reason
the EHCI code could not have been brought in to qemu that way.


David


> 
> I'm not impressed.
> 
> cheers,
>   Gerd
> 



Re: [Qemu-devel] [PATCH 00/26] q35 chipset support for native pci express support

2011-05-17 Thread Jan Kiszka
On 2011-05-17 15:57, Isaku Yamahata wrote:
> On Tue, May 17, 2011 at 09:15:39AM +0200, Jan Kiszka wrote:
>> On 2011-05-16 23:55, Adnan Khaleel wrote:
>>> I finally got this work after I realised that the AHCI driver was not being 
>>> loaded in my disk image and that ACHI was not being enabled in the Seabios 
>>> .config file.
>>> This is really good work Yamahata, thanks.
>>>
>>>
>>> As far as I can tell, everything works like the stock Qemu 0.14 except 
>>> networking. The guest OS sees the network device and initialises it but I 
>>> think the Qemu DHCP server/firewall never gets back, since the network 
>>> device doesn't even get a 10.0.2.15 ip address during bootup and the guest 
>>> dhcp client never gets an ip address, 
>>>
>>>
>>> eth0   device: Intel Corporation 82540EM Gigabit Ethernet Controller (rev 
>>> 03)
>>> eth0   Starting DHCP4 client. . . . . . . .
>>> eth0   DHCP4 continues in background 
>>> eth0   device: Intel Corporation 82540EM Gigabit Ethernet Controller (rev 
>>> 03)
>>> eth0   DHCP4 client (dhcpcd) is running
>>> eth0   . . . but is still waiting for data
>>> eth0   interface could not be set up until now
>>>
>>>
>>> So doing an ifconfig later on just shows
>>>
>>>
>>> eth0   Link encap:Ethernet  HWaddr 52:54:00:12:34:56
>>>  UP BROADCAST MULTICAST  MTU:1500  Metric:1
>>>  RX packets:0 errors:0 dropped:0 overruns:0 frame:0
>>>  TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
>>>  collisions:0 txqueuelen:1000
>>>  RX bytes:0 (0.0 b)   TX bytes:0 (0.0 b)
>>>
>>>
>>>
>>> lo  Link encap:Local loopback  
>>>  inet addr:127.0.0.1  Mask:255.0.0.0
>>>  inet6 addr: ::1/128 Scope:Host
>>>  UP LOOPBACK RUNING  MTU:16436  Metric:1
>>>  RX packets:0 errors:0 dropped:0 overruns:0 frame:0
>>>  TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
>>>  collisions:0 txqueuelen:1000
>>>  RX bytes:0 (0.0 b)   TX bytes:0 (0.0 b)
>>>
>>>
>>> I'm going to start a separate thread to see what the possible cause might 
>>> be and what might be the best way to debug this. Do you have any idea if 
>>> this q35 chipset going to be committed to Qemu upstream?
>>
>> I've recently hacked a bit on q35, rebased it over current master, found
>> and fixed a few bugs to allow booting of WinXP and Win7, and
>> particularly added kvm support to improve testability significantly. You
>> can find my current work at
>>
>> git://git.kiszka.org/qemu.git q35-test
>> git://git.kiszka.org/seabios.git q35-test
>>
>> There are some issues remaining, e.g. usb appeared broken to me. Now I
>> just tested your scenario (e1000+usernet) with a Win7 guest, and I do
>> not get an IP either. There is no traffic on the vlan (I attached a dump
>> device to verify). Looking closer, it seems PCI bar mapping is failing,
>> at least partially, see 'info pci'. I hope it's not yet another ACPI
>> issue. Fixing the polarity bug already forced me to dig way too deep
>> into this horrible domain.
> 
> Wow, very great. So is kvm working with q35?

Mostly. The key was to avoid that seabios does smm initialization as
that mode is not support by kvm. I also merged the q35 into qemu-kvm to
enable in-kernel irqchip support. That finally revealed the polarity
issues (only with win7 guests). I also posted a qemu ioapic patch to
make it polarity aware as well [1][2].

I also succeeded with passing through a PCIe host device. Nicely, the
full set capabilities showed up on the guest side this way. But GPU
pass-through did not improve this way (it rather regressed, yet unclear
why).

> 
> I had a quick look at your patches.
> With seabios patch of 94710189f5323034e00b510fe5a0865a7b576a9f,
> you ignored MCFG area.
> 
> (start = Q35_HOST_BRIDGE_PCIEXBAR_ADDR, size = 256MB) is used
> for MCFG (!= pci region), so it can't be used for PCI region.
> That's why 256M is added to s.
> And Q35_HOST_BRIDGE_PCIEXBAR_ADDR in dev-q35.h also needs to be adjusted.

Confused. Where was the PCI region located without my hack?

BTW, the PCI bar mapping failures of VGA or e1000 are independent of
that seabios commit. You should see them with your tree as well.

> 
> After pushing out pci id clean up and once they are accepted,
> I'll publish rebased/cleaned up one.

Note that I dropped "simply i440fx initialization". It was a premature
cleanup that caused regressions. The good news: I'm working on PAM/SMRAM
fixes that will include such a cleanup after removing the need for the
init function. The bad news: Those patches will force you to rebase
again (to break out the new PAM/SMRAM code).

Jan

[1] http://thread.gmane.org/gmane.comp.emulators.qemu/102459
[2] http://thread.gmane.org/gmane.comp.emulators.qemu/102460

-- 
Siemens AG, Corporate Technology, CT T DE IT 1
Corporate Competence Center Embedded Linux



[Qemu-devel] [PATCH] [qemu-img] CPU consuming optimization

2011-05-17 Thread Dmitry Konishchev
Hi! I was wondering why qemu-img consumes so much CPU when it converts
one partially allocated qcow2 image to another qcow2 image and I've
written a patch which improves the situation a little.

I have an image:
> $ qemu-img info ubuntu.10.04.qcow2
> image: ubuntu.10.04.qcow2
> file format: qcow2
> virtual size: 20G (21474836480 bytes)
> disk size: 2.2G
> cluster_size: 65536

I create a new copy on write image:
> $ qemu-img create -f qcow2 -o backing_file=ubuntu.10.04.qcow2 volume.qcow2 
> 100G
... and use it for a while.

Then I want to create a non-copy on write image from it to send it to someone:
> qemu-img convert -O qcow2 volume.qcow2 snapshot.qcow2


The last operation consumes a lot of CPU, so I run qemu-img under
profiler and realized, that most of CPU time is consumed by
is_not_zero() function. I had made a couple of optimizations on it and
got the following output for `time qemu-img convert -O qcow2
volume.qcow2 snapshot.qcow2`:

x86_64 machine:

Original qemu-img:
real 0m56.159s
user 0m34.670s
sys  0m12.079s

Patched qemu-img:
real 0m34.805s
user 0m18.445s
sys  0m12.552s


x86 machine:

Original qemu-img:
real 1m13.991s
user 0m24.734s
sys  0m6.604s

Patched qemu-img:
real 1m6.898s
user 0m16.021s
sys  0m6.700s

Please, see on the consumed user CPU time. I think that the
optimization worth it, so it will be awesome if you accept this patch
(see the attachment).

Thanks for your attention.
From 61d228c0ea0d518de48a08577cd6d282e2f97759 Mon Sep 17 00:00:00 2001
From: Dmitry Konishchev 
Date: Tue, 17 May 2011 16:29:48 +0400
Subject: [PATCH] is_not_zero() optimization in qemu-img

---
 qemu-img.c |   24 +---
 1 files changed, 21 insertions(+), 3 deletions(-)

diff --git a/qemu-img.c b/qemu-img.c
index e825123..41b4e32 100644
--- a/qemu-img.c
+++ b/qemu-img.c
@@ -498,12 +498,30 @@ static int img_commit(int argc, char **argv)
 
 static int is_not_zero(const uint8_t *sector, int len)
 {
+/*
+ * Use long as the biggest available internal data type that fits into the
+ * CPU register and unroll the loop to smooth out the effect of memory
+ * latency.
+ */
+
 int i;
-len >>= 2;
-for(i = 0;i < len; i++) {
-if (((uint32_t *)sector)[i] != 0)
+len /= sizeof(long);
+
+long d0;
+long d1;
+long d2;
+long d3;
+
+for(i = 0; i < len; i += 4) {
+d0 = ((const long*) sector)[i + 0];
+d1 = ((const long*) sector)[i + 1];
+d2 = ((const long*) sector)[i + 2];
+d3 = ((const long*) sector)[i + 3];
+
+if (d0 || d1 || d2 || d3)
 return 1;
 }
+
 return 0;
 }
 
-- 
1.7.4.1



Re: [Qemu-devel] [PATCH 18/18] usb: add ehci adapter

2011-05-17 Thread Gerd Hoffmann

  Hi,


Right, you did not even try to work with Jan's tree. There is no reason
the EHCI code could not have been brought in to qemu that way.


The usual way to review & merge code is to send a patch series against 
recent master to qemu-devel, optionally with a git tree to pull from.
So I tried to do that for ehci by merging & rebasing Jan's tree.  Didn't 
work out as described multiple times.


Using Jan's tree as-is isn't an option IMHO.  The patches didn't got a 
serious review @ qemu-devel.  IIRC the tree was more meant as "collect 
bits here so they doesn't get lost" not as "this stuff is ready for merge".


cheers,
  Gerd




Re: [Qemu-devel] [PATCH 01/11] Move user emulator stuff from cpu-exec.c to user-exec.c

2011-05-17 Thread Richard Henderson
On 05/14/2011 12:36 PM, Blue Swirl wrote:
> Simplify cpu-exec.c by refactoring.
> 
> Signed-off-by: Blue Swirl 

Signed-off-by: Richard Henderson  

This ought to go in no matter what happens with the rest.


r~



Re: [Qemu-devel] [PATCH 02/11] Delete unused tb_invalidate_page_range

2011-05-17 Thread Richard Henderson
On 05/14/2011 12:37 PM, Blue Swirl wrote:
> tb_invalidate_page_range() was intended to be used to invalidate an area of a 
> TB
> which the guest explicitly flushes from i-cache. However, QEMU detects writes
> to code areas where TBs have been generated, so this has never been useful.
> 
> Delete the function, adjust callers.
> 
> Signed-off-by: Blue Swirl 

Reviewed-by: Richard Henderson 



r~



Re: [Qemu-devel] [PATCH] linux-user: Handle images where lowest vaddr is not page aligned

2011-05-17 Thread Russ Cox
Thanks for tracking this down!



Re: [Qemu-devel] [PATCH 01/11] Move user emulator stuff from cpu-exec.c to user-exec.c

2011-05-17 Thread Peter Maydell
On 14 May 2011 20:36, Blue Swirl  wrote:

> +#if defined(__i386__)

> +#elif defined(__x86_64__)

> +#elif defined(_ARCH_PPC)

> +#elif defined(__alpha__)

> +#elif defined(__sparc__)

> +#elif defined(__arm__)

> +#elif defined(__mc68000)

> +#elif defined(__ia64)

> +#elif defined(__s390__)

> +#elif defined(__mips__)

> +#elif defined(__hppa__)

...if we're moving this code about anyway would it be possible
to split the per-host-arch specific code out into separate files?
I find these source files with enormous ifdef ladders pretty hard
to read.

-- PMM



Re: [Qemu-devel] [PATCH] linux-user: Handle images where lowest vaddr is not page aligned

2011-05-17 Thread Gustavo Niemeyer
> Thanks for tracking this down!

Indeed, thanks a lot for the very fast action on this.

-- 
Gustavo Niemeyer
http://niemeyer.net
http://niemeyer.net/blog
http://niemeyer.net/twitter



Re: [Qemu-devel] [PATCH 04/11] Delegate setup of TCG temporaries to targets

2011-05-17 Thread Richard Henderson
On 05/14/2011 12:37 PM, Blue Swirl wrote:
> Delegate TCG temp_buf setup to targets, so that they can use a stack
> frame later instead.
> 
> Signed-off-by: Blue Swirl 

Reviewed-by: Richard Henderson  

I think this sub-series moving TCG temps to the stack frame should
go in.  We can tidy up the other backends in short order and get 
these things out of CPUState.


r~



Re: [Qemu-devel] [PATCH 05/11] TCG: fix negative frame offset calculations

2011-05-17 Thread Richard Henderson
On 05/14/2011 12:38 PM, Blue Swirl wrote:
> size_t is unsigned, so the frame offset calculations can be incorrect for
> negative offsets.
> 
> Signed-off-by: Blue Swirl 

Reviewed-by: Richard Henderson  


r~



Re: [Qemu-devel] [PATCH 06/11] TCG/x86: use stack for TCG temps

2011-05-17 Thread Richard Henderson
On 05/14/2011 12:38 PM, Blue Swirl wrote:
> -frame_size = push_size + TCG_STATIC_CALL_ARGS_SIZE;
> +frame_size = push_size + TCG_STATIC_CALL_ARGS_SIZE +
> +CPU_TEMP_BUF_NLONGS * sizeof(long);
>  frame_size = (frame_size + TCG_TARGET_STACK_ALIGN - 1) &
>  ~(TCG_TARGET_STACK_ALIGN - 1);
>  stack_addend = frame_size - push_size;
> +tcg_set_frame(s, TCG_REG_ESP, 0, CPU_TEMP_BUF_NLONGS * sizeof(long));
> +
> +/* Save all callee saved registers.  */
> +for (i = 0; i < ARRAY_SIZE(tcg_target_callee_save_regs); i++) {
> +tcg_out_push(s, tcg_target_callee_save_regs[i]);
> +}
> +
>  tcg_out_addi(s, TCG_REG_ESP, -stack_addend);

Wrong argument to tcg_set_frame.  The temps need to be above the
outgoing call arguments, i.e. offset TCG_STATIC_CALL_ARGS_SIZE.


r~



Re: [Qemu-devel] [PATCH 18/18] usb: add ehci adapter

2011-05-17 Thread Gerd Hoffmann

  Hi,


(And by the way, where are the focused patches for each, especially the
last one - nuking the 8kHz code?


It's squashed in, like everything else.


We know that it worked on linux and
that printers, scanners and storage devices worked ok (mostly).


8 kHz is insane.

I looked closely while trying to make 8 kHz a runtime option instead of 
a compile time option, then decided to drop it altogether as it is 
totally pointless.  qemu simply can't handle that wakeup rate.  It maxed 
out at ~3 kHz wakeups in my tests.  And it burns tons of CPU time.


I also don't see what it would buy us.  We can wakeup with 1 kHz rate 
(maybe even lower), then emulate 8 (or more) microframes each time.


Throughput issues (guess this is the reason to try 8kHz wakeups) need to 
be addressed by modeling data pipes in the usb system instead of playing 
ping-pong between EHCI and USB device emulation for each single usb 
packet, at 8 kHz.


I see the ehci merge just as very first step.  USB 2.0 (and 3.0) support 
in qemu still has a lng way to go.


cheers,
  Gerd



[Qemu-devel] KVM call of May 17th

2011-05-17 Thread Juan Quintela

Minutes of today KVM call:

- import of headers
  in marcelo hands through kvm tree
- libtool integration
  * autoconf
  * gnulib -> if we move to glib, we have something similar for free
  * recursive Makefile
  Paolo item: propose timeline & plan on wiki, and discuss from there
- SCSI integration
  * In future, this would go though Kevin
  * this time done through list
- we are in feature freeze.  No big changes allowed.  Fixes & other not
  to big things allowed.  Rest of things should wait to next release.
- QAPI statics
  * current plan: merge subset of glib branch to enable virt-agent
code generator and error reporting
  * Hoping patches for this week
  * after that, we can merge GMP conversion without woneding about the
previous item.
  * after that, qconfig if people are interested
- qdev documentation patches
  decentralized vs centralized
  Anthony wants centralized, everybody else (that spoke) wants it
  decentralized
  pros/cons:
   whatever does it, decides




[Qemu-devel] [PATCH 0/2][SPARC] Improve sparc Trap

2011-05-17 Thread Julien Grall
Hi,

I' m glad to submit my first patches to the QEMU-devel list.

This set of patches improves SPARC handling of trap and the shutdown
capability on trap 0.

Regards,

Fabien Chouteau (1) :
   Improve sparc handling of ta

Julien Grall (1) :
   Fix TA0_SHUTDOWN feature

target-sparc/helper.h    |    1 +
target-sparc/op_helper.c |   15 +++
target-sparc/translate.c |   14 --
3 files changed, 20 insertions(+), 10 deletions(-)

--
Grall Julien



[Qemu-devel] [PATCH 1/2][SPARC] Improve sparc handling of ta

2011-05-17 Thread Julien Grall
Improve sparc handling of ta

Signed-off-by: Julien Grall 
---
 target-sparc/helper.h    |    1 +
 target-sparc/op_helper.c |    6 ++
 target-sparc/translate.c |    7 ---
 3 files changed, 11 insertions(+), 3 deletions(-)

diff --git a/target-sparc/helper.h b/target-sparc/helper.h
index 12e8557..61ef03a 100644
--- a/target-sparc/helper.h
+++ b/target-sparc/helper.h
@@ -85,6 +85,7 @@ DEF_HELPER_0(fcmpeq_fcc2, void)
 DEF_HELPER_0(fcmpeq_fcc3, void)
 #endif
 DEF_HELPER_1(raise_exception, void, int)
+DEF_HELPER_1(trap_always, void, int)
 DEF_HELPER_0(shutdown, void)
 #define F_HELPER_0_0(name) DEF_HELPER_0(f ## name, void)
 #define F_HELPER_DQ_0_0(name)                   \
diff --git a/target-sparc/op_helper.c b/target-sparc/op_helper.c
index b8c..a6fabad 100644
--- a/target-sparc/op_helper.c
+++ b/target-sparc/op_helper.c
@@ -324,6 +324,12 @@ void HELPER(raise_exception)(int tt)
    raise_exception(tt);
 }

+void HELPER(trap_always)(int tt)
+{
+    env->exception_index = tt;
+    do_interrupt(env);
+}
+
 void helper_shutdown(void)
 {
 #if !defined(CONFIG_USER_ONLY)
diff --git a/target-sparc/translate.c b/target-sparc/translate.c
index 3c958b2..b30003b 100644
--- a/target-sparc/translate.c
+++ b/target-sparc/translate.c
@@ -1982,7 +1982,7 @@ static void disas_sparc_insn(DisasContext * dc)
    case 2:                     /* FPU & Logical Operations */
        {
            unsigned int xop = GET_FIELD(insn, 7, 12);
-            if (xop == 0x3a) {  /* generate trap */
+            if (xop == 0x3a) {  /* ta, tcc: generate trap */
                int cond;

                cpu_src1 = get_src1(insn, cpu_src1);
@@ -2015,7 +2015,7 @@ static void disas_sparc_insn(DisasContext * dc)
                        gen_helper_shutdown();

                    } else {
-                        gen_helper_raise_exception(cpu_tmp32);
+                        gen_helper_trap_always(cpu_tmp32);
                    }
                } else if (cond != 0) {
                    TCGv r_cond = tcg_temp_new();
@@ -2049,8 +2049,9 @@ static void disas_sparc_insn(DisasContext * dc)

                    gen_set_label(l1);
                    tcg_temp_free(r_cond);
+
+                    gen_op_next_insn();
                }
-                gen_op_next_insn();
                tcg_gen_exit_tb(0);
                dc->is_br = 1;
                goto jmp_insn;
--
1.7.4.4



[Qemu-devel] [PATCH 2/2][SPARC] Fix TA0_Shutdown feature

2011-05-17 Thread Julien Grall
Fix TA0_SHUTDOWN feature

Signed-off-by: Julien Grall 
---
 target-sparc/op_helper.c |   13 +++--
 target-sparc/translate.c |9 +
 2 files changed, 12 insertions(+), 10 deletions(-)

diff --git a/target-sparc/op_helper.c b/target-sparc/op_helper.c
index a6fabad..cb775f5 100644
--- a/target-sparc/op_helper.c
+++ b/target-sparc/op_helper.c
@@ -326,8 +326,17 @@ void HELPER(raise_exception)(int tt)

 void HELPER(trap_always)(int tt)
 {
-env->exception_index = tt;
-do_interrupt(env);
+if (tt == TT_TRAP
+&& env->def->features & CPU_FEATURE_TA0_SHUTDOWN
+#ifndef TARGET_SPARC64
+&& env->psret == 0
+#endif
+) {
+helper_shutdown();
+} else {
+env->exception_index = tt;
+do_interrupt(env);
+}
 }

 void helper_shutdown(void)
diff --git a/target-sparc/translate.c b/target-sparc/translate.c
index b30003b..a47a2de 100644
--- a/target-sparc/translate.c
+++ b/target-sparc/translate.c
@@ -2009,14 +2009,7 @@ static void disas_sparc_insn(DisasContext * dc)
 tcg_gen_addi_tl(cpu_dst, cpu_dst, TT_TRAP);
 tcg_gen_trunc_tl_i32(cpu_tmp32, cpu_dst);

-if (rs2 == 0 &&
-dc->def->features & CPU_FEATURE_TA0_SHUTDOWN) {
-
-gen_helper_shutdown();
-
-} else {
-gen_helper_trap_always(cpu_tmp32);
-}
+gen_helper_trap_always(cpu_tmp32);
 } else if (cond != 0) {
 TCGv r_cond = tcg_temp_new();
 int l1;
-- 
1.7.4.4



Re: [Qemu-devel] [PATCH] [qemu-img] CPU consuming optimization

2011-05-17 Thread Stefan Hajnoczi
On Tue, May 17, 2011 at 3:33 PM, Dmitry Konishchev  wrote:
> Hi! I was wondering why qemu-img consumes so much CPU when it converts
> one partially allocated qcow2 image to another qcow2 image and I've
> written a patch which improves the situation a little.

Please see http://wiki.qemu.org/Contribute/SubmitAPatch, which asks
that patches are sent inline (not as attachments) for easy review and
that you follow the coding style (see the CODING_STYLE file).  Patches
also need a Signed-off-by: line.

The unrolled loop makes the function rely on len being a multiple of
sizeof(long) * 4, otherwise it accesses beyond the end of sector[].
So for this use case it's okay but the function is generic anymore.

GNU cp(1) tries to detect holes in files and image formats could tell
us about unallocated regions using bdrv_is_allocated().  So I think
there are ways to avoid comparing so much data in the first place, if
you are interested in looking into that.

Stefan



Re: [Qemu-devel] [RFC Patch 0/3]Qemu: Enable dynamic cache change through qemu monitor

2011-05-17 Thread Christoph Hellwig
On Mon, May 16, 2011 at 04:10:21PM -0500, Anthony Liguori wrote:
> To further clarify:
>
> Today cache=none|writethrough|writeback does two things.  It:
>
> 1) Changes the WCE flag that's visible to the guest
>
> 2) Determines whether the host page cache is used for doing guest I/O
>
> As Christoph is very correct in pointing out, we cannot change (1) at run 
> time because this is guest visible.  You will break a guest if you do this.
>
> But it's still desirable to be able to change (2) at run time.  Before we 
> can do this properly though, we need to separate out the logic for setting 
> (1) vs. (2).
>
> And ideally, we would allow (1) to be changed by the guest itself at run 
> time which allows for full dynamic control.  This is what he's referring to 
> below.

Exactly.  Setting/clearing the BDRV_O_NO_FLUSH also seems useful, maybe
in addition to also allowing an equivalent for the writethrough modes.




Re: [Qemu-devel] [PATCH 11/11] target-i386: use floatx80_log2() to implement helper_fyl2x*()

2011-05-17 Thread Richard Henderson
On 05/15/2011 07:13 AM, Aurelien Jarno wrote:
> +temp = floatx80_add(ST0, floatx80_one, &env->fp_status);
> +if (!floatx80_is_neg(temp)) {
> +temp = floatx80_add(ST0, floatx80_one, &env->fp_status);
> +temp = floatx80_log2(temp, &env->fp_status);
> +ST1 = floatx80_mul(ST1, temp, &env->fp_status);

While this is probably better than the existing code, you really
should be using a different series expansion than for log2.  This
expansion will be wildly inaccurate for inputs near zero.


r~



[Qemu-devel] [PATCH] block: clarify the meaning of BDRV_O_NOCACHE

2011-05-17 Thread Christoph Hellwig
Change BDRV_O_NOCACHE to only imply bypassing the host OS file cache,
but no writeback semantics.  All existing callers are changed to also
specify BDRV_O_CACHE_WB to give them writeback semantics.

Signed-off-by: Christoph Hellwig 

Index: qemu/block.c
===
--- qemu.orig/block.c   2011-05-17 17:49:12.398089706 +0200
+++ qemu/block.c2011-05-17 17:50:30.590590280 +0200
@@ -439,13 +439,7 @@ static int bdrv_open_common(BlockDriverS
 bs->drv = drv;
 bs->opaque = qemu_mallocz(drv->instance_size);
 
-/*
- * Yes, BDRV_O_NOCACHE aka O_DIRECT means we have to present a
- * write cache to the guest.  We do need the fdatasync to flush
- * out transactions for block allocations, and we maybe have a
- * volatile write cache in our backing device to deal with.
- */
-if (flags & (BDRV_O_CACHE_WB|BDRV_O_NOCACHE))
+if (flags & BDRV_O_CACHE_WB)
 bs->enable_write_cache = 1;
 
 /*
Index: qemu/block/raw-posix.c
===
--- qemu.orig/block/raw-posix.c 2011-04-21 09:57:20.727842564 +0200
+++ qemu/block/raw-posix.c  2011-05-17 17:50:30.594593138 +0200
@@ -154,7 +154,7 @@ static int raw_open_common(BlockDriverSt
  * and O_DIRECT for no caching. */
 if ((bdrv_flags & BDRV_O_NOCACHE))
 s->open_flags |= O_DIRECT;
-else if (!(bdrv_flags & BDRV_O_CACHE_WB))
+if (!(bdrv_flags & BDRV_O_CACHE_WB))
 s->open_flags |= O_DSYNC;
 
 s->fd = -1;
Index: qemu/block/raw-win32.c
===
--- qemu.orig/block/raw-win32.c 2011-04-21 09:57:20.741175824 +0200
+++ qemu/block/raw-win32.c  2011-05-17 17:50:30.594593138 +0200
@@ -88,9 +88,9 @@ static int raw_open(BlockDriverState *bs
 }
 
 overlapped = FILE_ATTRIBUTE_NORMAL;
-if ((flags & BDRV_O_NOCACHE))
-overlapped |= FILE_FLAG_NO_BUFFERING | FILE_FLAG_WRITE_THROUGH;
-else if (!(flags & BDRV_O_CACHE_WB))
+if (flags & BDRV_O_NOCACHE)
+overlapped |= FILE_FLAG_NO_BUFFERING;
+if (!(flags & BDRV_O_CACHE_WB))
 overlapped |= FILE_FLAG_WRITE_THROUGH;
 s->hfile = CreateFile(filename, access_flags,
   FILE_SHARE_READ, NULL,
@@ -349,9 +349,9 @@ static int hdev_open(BlockDriverState *b
 create_flags = OPEN_EXISTING;
 
 overlapped = FILE_ATTRIBUTE_NORMAL;
-if ((flags & BDRV_O_NOCACHE))
-overlapped |= FILE_FLAG_NO_BUFFERING | FILE_FLAG_WRITE_THROUGH;
-else if (!(flags & BDRV_O_CACHE_WB))
+if (flags & BDRV_O_NOCACHE)
+overlapped |= FILE_FLAG_NO_BUFFERING;
+if (!(flags & BDRV_O_CACHE_WB))
 overlapped |= FILE_FLAG_WRITE_THROUGH;
 s->hfile = CreateFile(filename, access_flags,
   FILE_SHARE_READ, NULL,
Index: qemu/blockdev.c
===
--- qemu.orig/blockdev.c2011-04-21 09:57:43.614385242 +0200
+++ qemu/blockdev.c 2011-05-17 17:50:30.598590965 +0200
@@ -326,7 +326,7 @@ DriveInfo *drive_init(QemuOpts *opts, in
 
 if ((buf = qemu_opt_get(opts, "cache")) != NULL) {
 if (!strcmp(buf, "off") || !strcmp(buf, "none")) {
-bdrv_flags |= BDRV_O_NOCACHE;
+bdrv_flags |= BDRV_O_NOCACHE | BDRV_O_CACHE_WB;
 } else if (!strcmp(buf, "writeback")) {
 bdrv_flags |= BDRV_O_CACHE_WB;
 } else if (!strcmp(buf, "unsafe")) {
Index: qemu/qemu-io.c
===
--- qemu.orig/qemu-io.c 2011-04-21 09:57:20.771175661 +0200
+++ qemu/qemu-io.c  2011-05-17 17:50:30.602624947 +0200
@@ -1655,7 +1655,7 @@ open_f(int argc, char **argv)
flags |= BDRV_O_SNAPSHOT;
break;
case 'n':
-   flags |= BDRV_O_NOCACHE;
+   flags |= BDRV_O_NOCACHE | BDRV_O_CACHE_WB;
break;
case 'r':
readonly = 1;
@@ -1751,7 +1751,7 @@ int main(int argc, char **argv)
flags |= BDRV_O_SNAPSHOT;
break;
case 'n':
-   flags |= BDRV_O_NOCACHE;
+   flags |= BDRV_O_NOCACHE | BDRV_O_CACHE_WB;
break;
case 'c':
add_user_command(optarg);
Index: qemu/qemu-nbd.c
===
--- qemu.orig/qemu-nbd.c2011-04-21 09:57:20.784508924 +0200
+++ qemu/qemu-nbd.c 2011-05-17 17:50:30.602624947 +0200
@@ -238,7 +238,7 @@ int main(int argc, char **argv)
 flags |= BDRV_O_SNAPSHOT;
 break;
 case 'n':
-flags |= BDRV_O_NOCACHE;
+flags |= BDRV_O_NOCACHE | BDRV_O_CACHE_WB;
 break;
 case 'b':
 bindto = optarg;
Index: qemu/block

[Qemu-devel] [PATCH 3/3] tcg: don't keep dead outputs in registers

2011-05-17 Thread Aurelien Jarno
If an op with dead outputs is not removed, because it has side effects
or has multiple output arguments and only one dead, mark the TCG 
registers as dead instead of keeping them allocated. This avoid a few 
register spills on TCG targets with low register count, especially with
div2 and mul2 ops, or when a qemu_ld* result is not used (prefetch 
emulation for example).

Signed-off-by: Aurelien Jarno 
---
 tcg/tcg.c |   28 ++--
 1 files changed, 18 insertions(+), 10 deletions(-)

diff --git a/tcg/tcg.c b/tcg/tcg.c
index 82d3e1d..fad92f9 100644
--- a/tcg/tcg.c
+++ b/tcg/tcg.c
@@ -1782,12 +1782,16 @@ static void tcg_reg_alloc_op(TCGContext *s,
 if (!ts->fixed_reg) {
 if (ts->val_type == TEMP_VAL_REG)
 s->reg_to_temp[ts->reg] = -1;
-ts->val_type = TEMP_VAL_REG;
-ts->reg = reg;
-/* temp value is modified, so the value kept in memory is
-   potentially not the same */
-ts->mem_coherent = 0; 
-s->reg_to_temp[reg] = arg;
+if (IS_DEAD_ARG(i)) {
+ts->val_type = TEMP_VAL_DEAD;
+} else {
+ts->val_type = TEMP_VAL_REG;
+ts->reg = reg;
+/* temp value is modified, so the value kept in memory is
+   potentially not the same */
+ts->mem_coherent = 0;
+s->reg_to_temp[reg] = arg;
+   }
 }
 oarg_end:
 new_args[i] = reg;
@@ -1981,10 +1985,14 @@ static int tcg_reg_alloc_call(TCGContext *s, const 
TCGOpDef *def,
 } else {
 if (ts->val_type == TEMP_VAL_REG)
 s->reg_to_temp[ts->reg] = -1;
-ts->val_type = TEMP_VAL_REG;
-ts->reg = reg;
-ts->mem_coherent = 0; 
-s->reg_to_temp[reg] = arg;
+if (IS_DEAD_ARG(i)) {
+ts->val_type = TEMP_VAL_DEAD;
+} else {
+ts->val_type = TEMP_VAL_REG;
+ts->reg = reg;
+ts->mem_coherent = 0;
+s->reg_to_temp[reg] = arg;
+}
 }
 }
 
-- 
1.7.2.3




[Qemu-devel] [PATCH 1/3] tcg: replace op_dead_iargs by op_dead_args

2011-05-17 Thread Aurelien Jarno
Allow all args to be dead by replacing the input specific op_dead_iargs
variable by op_dead_args. Note this is a purely mechanical change.

Signed-off-by: Aurelien Jarno 
---
 tcg/tcg.c |   71 +++--
 tcg/tcg.h |4 +-
 2 files changed, 38 insertions(+), 37 deletions(-)

diff --git a/tcg/tcg.c b/tcg/tcg.c
index 8748c05..9a48cb9 100644
--- a/tcg/tcg.c
+++ b/tcg/tcg.c
@@ -1193,7 +1193,7 @@ static inline void tcg_la_bb_end(TCGContext *s, uint8_t 
*dead_temps)
 }
 }
 
-/* Liveness analysis : update the opc_dead_iargs array to tell if a
+/* Liveness analysis : update the opc_dead_args array to tell if a
given input arguments is dead. Instructions updating dead
temporaries are removed. */
 static void tcg_liveness_analysis(TCGContext *s)
@@ -1203,13 +1203,13 @@ static void tcg_liveness_analysis(TCGContext *s)
 TCGArg *args;
 const TCGOpDef *def;
 uint8_t *dead_temps;
-unsigned int dead_iargs;
+unsigned int dead_args;
 
 gen_opc_ptr++; /* skip end */
 
 nb_ops = gen_opc_ptr - gen_opc_buf;
 
-s->op_dead_iargs = tcg_malloc(nb_ops * sizeof(uint16_t));
+s->op_dead_args = tcg_malloc(nb_ops * sizeof(uint16_t));
 
 dead_temps = tcg_malloc(s->nb_temps);
 memset(dead_temps, 1, s->nb_temps);
@@ -1256,17 +1256,17 @@ static void tcg_liveness_analysis(TCGContext *s)
 }
 
 /* input args are live */
-dead_iargs = 0;
-for(i = 0; i < nb_iargs; i++) {
-arg = args[i + nb_oargs];
+dead_args = 0;
+for(i = nb_oargs; i < nb_iargs + nb_oargs; i++) {
+arg = args[i];
 if (arg != TCG_CALL_DUMMY_ARG) {
 if (dead_temps[arg]) {
-dead_iargs |= (1 << i);
+dead_args |= (1 << i);
 }
 dead_temps[arg] = 0;
 }
 }
-s->op_dead_iargs[op_index] = dead_iargs;
+s->op_dead_args[op_index] = dead_args;
 }
 args--;
 }
@@ -1327,15 +1327,15 @@ static void tcg_liveness_analysis(TCGContext *s)
 }
 
 /* input args are live */
-dead_iargs = 0;
-for(i = 0; i < nb_iargs; i++) {
-arg = args[i + nb_oargs];
+dead_args = 0;
+for(i = nb_oargs; i < nb_oargs + nb_iargs; i++) {
+arg = args[i];
 if (dead_temps[arg]) {
-dead_iargs |= (1 << i);
+dead_args |= (1 << i);
 }
 dead_temps[arg] = 0;
 }
-s->op_dead_iargs[op_index] = dead_iargs;
+s->op_dead_args[op_index] = dead_args;
 }
 break;
 }
@@ -1352,8 +1352,8 @@ static void tcg_liveness_analysis(TCGContext *s)
 int nb_ops;
 nb_ops = gen_opc_ptr - gen_opc_buf;
 
-s->op_dead_iargs = tcg_malloc(nb_ops * sizeof(uint16_t));
-memset(s->op_dead_iargs, 0, nb_ops * sizeof(uint16_t));
+s->op_dead_args = tcg_malloc(nb_ops * sizeof(uint16_t));
+memset(s->op_dead_args, 0, nb_ops * sizeof(uint16_t));
 }
 #endif
 
@@ -1557,7 +1557,7 @@ static void tcg_reg_alloc_bb_end(TCGContext *s, TCGRegSet 
allocated_regs)
 save_globals(s, allocated_regs);
 }
 
-#define IS_DEAD_IARG(n) ((dead_iargs >> (n)) & 1)
+#define IS_DEAD_ARG(n) ((dead_args >> (n)) & 1)
 
 static void tcg_reg_alloc_movi(TCGContext *s, const TCGArg *args)
 {
@@ -1582,7 +1582,7 @@ static void tcg_reg_alloc_movi(TCGContext *s, const 
TCGArg *args)
 
 static void tcg_reg_alloc_mov(TCGContext *s, const TCGOpDef *def,
   const TCGArg *args,
-  unsigned int dead_iargs)
+  unsigned int dead_args)
 {
 TCGTemp *ts, *ots;
 int reg;
@@ -1592,9 +1592,9 @@ static void tcg_reg_alloc_mov(TCGContext *s, const 
TCGOpDef *def,
 ts = &s->temps[args[1]];
 arg_ct = &def->args_ct[0];
 
-/* XXX: always mark arg dead if IS_DEAD_IARG(0) */
+/* XXX: always mark arg dead if IS_DEAD_ARG(1) */
 if (ts->val_type == TEMP_VAL_REG) {
-if (IS_DEAD_IARG(0) && !ts->fixed_reg && !ots->fixed_reg) {
+if (IS_DEAD_ARG(1) && !ts->fixed_reg && !ots->fixed_reg) {
 /* the mov can be suppressed */
 if (ots->val_type == TEMP_VAL_REG)
 s->reg_to_temp[ots->reg] = -1;
@@ -1642,7 +1642,7 @@ static void tcg_reg_alloc_mov(TCGContext *s, const 
TCGOpDef *def,
 static void tcg_reg_alloc_op(TCGContext *s, 
  const TCGOpDef *def, TCGOpcode opc,
  const TCGArg *args,
- uns

[Qemu-devel] [PATCH 0/3] TCG: first attempt to reduce host registers usage

2011-05-17 Thread Aurelien Jarno
This patch series is a first attempt after the TCG_AREG0 discussion to
show it's possible to easily (at least without making huge changes to
the TCG core code) spare some registers and avoid a few spills on low
register count TCG targets like i386.

On i386 hosts some TB are reduced by up to 10%, though the global TB
reduction is around 0.5%. The gain is speed is only measurable in user
mode with very specific benchmarks: sha1sum of 4GB files is 1.9% +/-0.2%
faster. On x86-64 host, some TB are one or two bytes longer, some of
them one or two bytes smaller, mainly due to different register usage,
which adds or removes some REX prefixes, but overall the size is
unchanged.

I have a few more ideas to further reduce register spill, I'll try to
implement them in the next days/weeks.


Aurelien Jarno (3):
  tcg: replace op_dead_iargs by op_dead_args
  tcg: mark dead output argument in op_dead_args
  tcg: don't keep dead outputs in registers

 tcg/tcg.c |  105 +++--
 tcg/tcg.h |4 +-
 2 files changed, 62 insertions(+), 47 deletions(-)

-- 
1.7.2.3




[Qemu-devel] [PATCH 2/3] tcg: mark dead output argument in op_dead_args

2011-05-17 Thread Aurelien Jarno
If an op is not removed and has dead output arguments, mark it
in op_dead_args similarly to what is done for input arguments.

Signed-off-by: Aurelien Jarno 
---
 tcg/tcg.c |   10 --
 1 files changed, 8 insertions(+), 2 deletions(-)

diff --git a/tcg/tcg.c b/tcg/tcg.c
index 9a48cb9..82d3e1d 100644
--- a/tcg/tcg.c
+++ b/tcg/tcg.c
@@ -1245,8 +1245,12 @@ static void tcg_liveness_analysis(TCGContext *s)
 do_not_remove_call:
 
 /* output args are dead */
+dead_args = 0;
 for(i = 0; i < nb_oargs; i++) {
 arg = args[i];
+if (dead_temps[arg]) {
+dead_args |= (1 << i);
+}
 dead_temps[arg] = 1;
 }
 
@@ -1256,7 +1260,6 @@ static void tcg_liveness_analysis(TCGContext *s)
 }
 
 /* input args are live */
-dead_args = 0;
 for(i = nb_oargs; i < nb_iargs + nb_oargs; i++) {
 arg = args[i];
 if (arg != TCG_CALL_DUMMY_ARG) {
@@ -1313,8 +1316,12 @@ static void tcg_liveness_analysis(TCGContext *s)
 do_not_remove:
 
 /* output args are dead */
+dead_args = 0;
 for(i = 0; i < nb_oargs; i++) {
 arg = args[i];
+if (dead_temps[arg]) {
+dead_args |= (1 << i);
+}
 dead_temps[arg] = 1;
 }
 
@@ -1327,7 +1334,6 @@ static void tcg_liveness_analysis(TCGContext *s)
 }
 
 /* input args are live */
-dead_args = 0;
 for(i = nb_oargs; i < nb_oargs + nb_iargs; i++) {
 arg = args[i];
 if (dead_temps[arg]) {
-- 
1.7.2.3




Re: [Qemu-devel] [PATCH 08/18] usb-linux: fix device path aka physical port handling

2011-05-17 Thread Markus Armbruster
Looks like you haven't updated this one for the last round of review,
yet.

Gerd Hoffmann  writes:

> The device path isn't just a number.  It specifies the physical port
> the device is connected to and in case the device is connected via
> usb hub you'll have two numbers there, like this: "5.1".  The first
> specifies the root port where the hub is plugged into, the second
> specifies the port number of the hub where the device is plugged in.
> With multiple hubs chained the string can become longer.
>
> This patch renames devpath to port and makes it a string.   It also
> adapts the sysfs parsing code accordingly.  The "info usbhost" monitor
> command now prints bus number, (os-assigned) device address and physical
> port for each device.

Missing here: document the fix for roots, see [*] below.

> Signed-off-by: Gerd Hoffmann 
> ---
>  usb-linux.c |   38 --
>  1 files changed, 20 insertions(+), 18 deletions(-)
>
> diff --git a/usb-linux.c b/usb-linux.c
> index 84d3a8b..2fa3591 100644
> --- a/usb-linux.c
> +++ b/usb-linux.c
> @@ -54,7 +54,7 @@ struct usb_ctrltransfer {
>  void *data;
>  };
>  
> -typedef int USBScanFunc(void *opaque, int bus_num, int addr, int devpath,
> +typedef int USBScanFunc(void *opaque, int bus_num, int addr, char *port,
>  int class_id, int vendor_id, int product_id,
>  const char *product_name, int speed);
>  
> @@ -71,6 +71,7 @@ typedef int USBScanFunc(void *opaque, int bus_num, int 
> addr, int devpath,
>  #define USBPROCBUS_PATH "/proc/bus/usb"
>  #define PRODUCT_NAME_SZ 32
>  #define MAX_ENDPOINTS 15
> +#define MAX_PORTLEN 8

Please change this to 16 to match the kernel.

>  #define USBDEVBUS_PATH "/dev/bus/usb"
>  #define USBSYSBUS_PATH "/sys/bus/usb"
>  
> @@ -123,7 +124,7 @@ typedef struct USBHostDevice {
>  /* Host side address */
>  int bus_num;
>  int addr;
> -int devpath;
> +char port[MAX_PORTLEN];
>  struct USBAutoFilter match;
>  
>  QTAILQ_ENTRY(USBHostDevice) next;
> @@ -836,7 +837,7 @@ static int usb_linux_get_configuration(USBHostDevice *s)
>  char device_name[32], line[1024];
>  int configuration;
>  
> -sprintf(device_name, "%d-%d", s->bus_num, s->devpath);
> +sprintf(device_name, "%d-%s", s->bus_num, s->port);
>  
>  if (!usb_host_read_file(line, sizeof(line), "bConfigurationValue",
>  device_name)) {
> @@ -882,7 +883,7 @@ static uint8_t usb_linux_get_alt_setting(USBHostDevice *s,
>  char device_name[64], line[1024];
>  int alt_setting;
>  
> -sprintf(device_name, "%d-%d:%d.%d", s->bus_num, s->devpath,
> +sprintf(device_name, "%d-%s:%d.%d", s->bus_num, s->port,
>  (int)configuration, (int)interface);
>  
>  if (!usb_host_read_file(line, sizeof(line), "bAlternateSetting",
> @@ -1001,7 +1002,7 @@ static int usb_linux_update_endp_table(USBHostDevice *s)
>  }
>  
>  static int usb_host_open(USBHostDevice *dev, int bus_num,
> - int addr, int devpath, const char *prod_name)
> + int addr, char *port, const char *prod_name)
>  {
>  int fd = -1, ret;
>  struct usbdevfs_connectinfo ci;
> @@ -1027,7 +1028,7 @@ static int usb_host_open(USBHostDevice *dev, int 
> bus_num,
>  
>  dev->bus_num = bus_num;
>  dev->addr = addr;
> -dev->devpath = devpath;
> +strcpy(dev->port, port);
>  dev->fd = fd;
>  
>  /* read the device description */
> @@ -1401,8 +1402,9 @@ static int usb_host_scan_sys(void *opaque, USBScanFunc 
> *func)
>  {
>  DIR *dir = NULL;
>  char line[1024];
> -int bus_num, addr, devpath, speed, class_id, product_id, vendor_id;
> +int bus_num, addr, speed, class_id, product_id, vendor_id;
>  int ret = 0;
> +char port[MAX_PORTLEN];
>  char product_name[512];
>  struct dirent *de;
>  
> @@ -1418,8 +1420,8 @@ static int usb_host_scan_sys(void *opaque, USBScanFunc 
> *func)
>  if (!strncmp(de->d_name, "usb", 3)) {
>  tmpstr += 3;
>  }

You wrote "I think this can be zapped now, the new sscanf will fail on
them and skip the entries anyway."  What about it?

> -if (sscanf(tmpstr, "%d-%d", &bus_num, &devpath) < 1) {
> -goto the_end;
> +if (sscanf(tmpstr, "%d-%7[0-9.]", &bus_num, port) < 2) {
> +continue;
>  }
>  
>  if (!usb_host_read_file(line, sizeof(line), "devnum", 
> de->d_name)) {

[*] Undocumented bug fix here.  Quoting our conversation:

> The old sscanf() succeeds if at least one item is assigned, i.e. tmpstr
> starts with an integer.  I suspect this is broken for roots.  Consider
> d_name "usb1": tmpstr is "1", sscan() returns 1, and devpath remains
> uninitialized.  It's passed to the func() callback.  Bug?  If yes, the
> commit message should mention it.

Indeed.

>

[Qemu-devel] [PATCH v2 09/38] hw/acpi_piix4.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/acpi_piix4.c |8 
 1 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/hw/acpi_piix4.c b/hw/acpi_piix4.c
index 96f5222..03d833a 100644
--- a/hw/acpi_piix4.c
+++ b/hw/acpi_piix4.c
@@ -317,13 +317,9 @@ static int piix4_pm_initfn(PCIDevice *dev)
 uint8_t *pci_conf;
 
 pci_conf = s->dev.config;
-pci_config_set_vendor_id(pci_conf, PCI_VENDOR_ID_INTEL);
-pci_config_set_device_id(pci_conf, PCI_DEVICE_ID_INTEL_82371AB_3);
 pci_conf[0x06] = 0x80;
 pci_conf[0x07] = 0x02;
-pci_conf[0x08] = 0x03; // revision number
 pci_conf[0x09] = 0x00;
-pci_config_set_class(pci_conf, PCI_CLASS_BRIDGE_OTHER);
 pci_conf[0x3d] = 0x01; // interrupt pin 1
 
 pci_conf[0x40] = 0x01; /* PM io base read only bit */
@@ -394,6 +390,10 @@ static PCIDeviceInfo piix4_pm_info = {
 .no_hotplug = 1,
 .init   = piix4_pm_initfn,
 .config_write   = pm_write_config,
+.vendor_id  = PCI_VENDOR_ID_INTEL,
+.device_id  = PCI_DEVICE_ID_INTEL_82371AB_3,
+.revision   = 0x03, // revision number
+.class_id   = PCI_CLASS_BRIDGE_OTHER,
 .qdev.props = (Property[]) {
 DEFINE_PROP_UINT32("smb_io_base", PIIX4PMState, smb_io_base, 0),
 DEFINE_PROP_END_OF_LIST(),
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 14/38] hw/grackle_pci.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/grackle_pci.c |8 
 1 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/hw/grackle_pci.c b/hw/grackle_pci.c
index d35701f..7a5221c 100644
--- a/hw/grackle_pci.c
+++ b/hw/grackle_pci.c
@@ -104,11 +104,7 @@ static int pci_grackle_init_device(SysBusDevice *dev)
 
 static int grackle_pci_host_init(PCIDevice *d)
 {
-pci_config_set_vendor_id(d->config, PCI_VENDOR_ID_MOTOROLA);
-pci_config_set_device_id(d->config, PCI_DEVICE_ID_MOTOROLA_MPC106);
-d->config[0x08] = 0x00; // revision
 d->config[0x09] = 0x01;
-pci_config_set_class(d->config, PCI_CLASS_BRIDGE_HOST);
 return 0;
 }
 
@@ -116,6 +112,10 @@ static PCIDeviceInfo grackle_pci_host_info = {
 .qdev.name = "grackle",
 .qdev.size = sizeof(PCIDevice),
 .init  = grackle_pci_host_init,
+.vendor_id = PCI_VENDOR_ID_MOTOROLA,
+.device_id = PCI_DEVICE_ID_MOTOROLA_MPC106,
+.revision  = 0x00, // revision
+.class_id  = PCI_CLASS_BRIDGE_HOST,
 };
 
 static void grackle_register_devices(void)
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 00/38] pci: initialize ids in pci common code

2011-05-17 Thread Isaku Yamahata
vender id/device id... in pci configuration space are read-only registers
which are commonly defined for all pci devices.
So initialize them in common code and it simplifies the initialization a bit.
I didn't converted virtio-pci and qxl because it determines ids dynaically.
So I'll leave those conversion (or not to convert) to the authors.

changes v1 -> v2:
- dropped header_type and prog_interface
- converted more

Isaku Yamahata (38):
  pci: move ids of config space into PCIDeviceInfo
  usb-uhci: convert to PCIDEviceInfo to initialize ids
  eepro100: convert to PCIDeviceInfo to initialize ids
  dec_pci: convert to PCIDeviceInfo to initialize ids
  apb_pci: convert to PCIDeviceInfo to initialize ids
  ide/piix: convert to PCIDeviceInfo to initialize ids
  vmware_vga.c: convert to PCIDeviceInfo to initialize ids
  hw/ac97.c: convert to PCIDeviceInfo to initialize ids
  hw/acpi_piix4.c: convert to PCIDeviceInfo to initialize ids
  hw/bonito.c: convert to PCIDeviceInfo to initialize ids
  hw/cirrus_vga.c: convert to PCIDeviceInfo to initialize ids
  hw/e1000.c: convert to PCIDeviceInfo to initialize ids
  hw/es1370.c: convert to PCIDeviceInfo to initialize ids
  hw/grackle_pci.c: convert to PCIDeviceInfo to initialize ids
  hw/gt64xxx.c: convert to PCIDeviceInfo to initialize ids
  hw/ide/cmd646.c: convert to PCIDeviceInfo to initialize ids
  hw/ide/ich.c: convert to PCIDeviceInfo to initialize ids
  hw/ide/via.c: convert to PCIDeviceInfo to initialize ids
  hw/intel-hda.c: convert to PCIDeviceInfo to initialize ids
  hw/ioh3420.c: convert to PCIDeviceInfo to initialize ids
  hw/ivshmem.c: convert to PCIDeviceInfo to initialize ids
  hw/lsi53c895a.c: convert to PCIDeviceInfo to initialize ids
  hw/ne2000.c: convert to PCIDeviceInfo to initialize ids
  hw/pcnet-pci.c: convert to PCIDeviceInfo to initialize ids
  hw/piix4.c: convert to PCIDeviceInfo to initialize ids
  hw/piix_pci.c: convert to PCIDeviceInfo to initialize ids
  hw/qxl.c: convert to PCIDeviceInfo to initialize ids
  hw/rtl8139.c: convert to PCIDeviceInfo to initialize ids
  hw/sh_pci.c: convert to PCIDeviceInfo to initialize ids
  hw/sun4u.c: convert to PCIDeviceInfo to initialize ids
  hw/unin_pci.c: convert to PCIDeviceInfo to initialize ids
  hw/usb-ohci.c: convert to PCIDeviceInfo to initialize ids
  hw/versatile_pci.c: convert to PCIDeviceInfo to initialize ids
  hw/vga-pci.c: convert to PCIDeviceInfo to initialize ids
  hw/vt82c686.c: convert to PCIDeviceInfo to initialize ids
  hw/wdt_i6300esb.c: convert to PCIDeviceInfo to initialize ids
  hw/xio3130_downstream.c: convert to PCIDeviceInfo to initialize ids
  hw/xio3130_upstream.c: convert to PCIDeviceInfo to initialize ids

 hw/ac97.c   |9 ++---
 hw/acpi_piix4.c |8 ++--
 hw/apb_pci.c|   13 
 hw/bonito.c |9 +++--
 hw/cirrus_vga.c |7 ++--
 hw/dec_pci.c|   26 
 hw/e1000.c  |8 ++--
 hw/eepro100.c   |   72 +--
 hw/es1370.c |   24 +++
 hw/grackle_pci.c|8 ++--
 hw/gt64xxx.c|8 ++--
 hw/ide/cmd646.c |   10 ++
 hw/ide/ich.c|9 ++---
 hw/ide/piix.c   |   32 ++--
 hw/ide/via.c|8 ++--
 hw/intel-hda.c  |8 ++--
 hw/ioh3420.c|7 ++--
 hw/ivshmem.c|8 ++---
 hw/lsi53c895a.c |   17 +--
 hw/ne2000.c |6 ++--
 hw/pci.c|   46 +-
 hw/pci.h|7 
 hw/pcnet-pci.c  |8 ++--
 hw/piix4.c  |   10 ++
 hw/piix_pci.c   |   19 
 hw/qxl.c|7 ++--
 hw/rtl8139.c|8 ++--
 hw/sh_pci.c |4 +-
 hw/sun4u.c  |8 ++--
 hw/unin_pci.c   |   34 +++---
 hw/usb-ohci.c   |7 ++--
 hw/usb-uhci.c   |   46 +++---
 hw/versatile_pci.c  |6 ++--
 hw/vga-pci.c|   11 +++
 hw/vmware_vga.c |   13 
 hw/vt82c686.c   |   35 ++
 hw/wdt_i6300esb.c   |6 ++--
 hw/xio3130_downstream.c |6 ++--
 hw/xio3130_upstream.c   |6 ++--
 39 files changed, 270 insertions(+), 314 deletions(-)




[Qemu-devel] [PATCH v2 10/38] hw/bonito.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/bonito.c |9 +
 1 files changed, 5 insertions(+), 4 deletions(-)

diff --git a/hw/bonito.c b/hw/bonito.c
index 65a4a63..e8c57a3 100644
--- a/hw/bonito.c
+++ b/hw/bonito.c
@@ -691,11 +691,7 @@ static int bonito_initfn(PCIDevice *dev)
 PCIBonitoState *s = DO_UPCAST(PCIBonitoState, dev, dev);
 
 /* Bonito North Bridge, built on FPGA, VENDOR_ID/DEVICE_ID are "undefined" 
*/
-pci_config_set_vendor_id(dev->config, 0xdf53);
-pci_config_set_device_id(dev->config, 0x00d5);
-pci_config_set_class(dev->config, PCI_CLASS_BRIDGE_HOST);
 pci_config_set_prog_interface(dev->config, 0x00);
-pci_config_set_revision(dev->config, 0x01);
 
 /* set the north bridge register mapping */
 s->bonito_reg_handle = cpu_register_io_memory(bonito_read, bonito_write, s,
@@ -796,6 +792,11 @@ static PCIDeviceInfo bonito_info = {
 .qdev.vmsd= &vmstate_bonito,
 .qdev.no_user = 1,
 .init = bonito_initfn,
+/*Bonito North Bridge, built on FPGA, VENDOR_ID/DEVICE_ID are "undefined"*/
+.vendor_id= 0xdf53,
+.device_id= 0x00d5,
+.revision = 0x01,
+.class_id = PCI_CLASS_BRIDGE_HOST,
 };
 
 static SysBusDeviceInfo bonito_pcihost_info = {
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 19/38] hw/intel-hda.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/intel-hda.c |8 
 1 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/hw/intel-hda.c b/hw/intel-hda.c
index 5485745..0ce 100644
--- a/hw/intel-hda.c
+++ b/hw/intel-hda.c
@@ -1138,10 +1138,6 @@ static int intel_hda_init(PCIDevice *pci)
 
 d->name = d->pci.qdev.info->name;
 
-pci_config_set_vendor_id(conf, PCI_VENDOR_ID_INTEL);
-pci_config_set_device_id(conf, 0x2668);
-pci_config_set_revision(conf, 1);
-pci_config_set_class(conf, PCI_CLASS_MULTIMEDIA_HD_AUDIO);
 pci_config_set_interrupt_pin(conf, 1);
 
 /* HDCTL off 0x40 bit 0 selects signaling mode (1-HDA, 0 - Ac97) 18.1.19 */
@@ -1265,6 +1261,10 @@ static PCIDeviceInfo intel_hda_info = {
 .init = intel_hda_init,
 .exit = intel_hda_exit,
 .config_write = intel_hda_write_config,
+.vendor_id= PCI_VENDOR_ID_INTEL,
+.device_id= 0x2668,
+.revision = 1,
+.class_id = PCI_CLASS_MULTIMEDIA_HD_AUDIO,
 .qdev.props   = (Property[]) {
 DEFINE_PROP_UINT32("debug", IntelHDAState, debug, 0),
 DEFINE_PROP_UINT32("msi", IntelHDAState, msi, 1),
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 37/38] hw/xio3130_downstream.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/xio3130_downstream.c |6 +++---
 1 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/hw/xio3130_downstream.c b/hw/xio3130_downstream.c
index 5aa6a6b..d3c387d 100644
--- a/hw/xio3130_downstream.c
+++ b/hw/xio3130_downstream.c
@@ -69,9 +69,6 @@ static int xio3130_downstream_initfn(PCIDevice *d)
 }
 
 pcie_port_init_reg(d);
-pci_config_set_vendor_id(d->config, PCI_VENDOR_ID_TI);
-pci_config_set_device_id(d->config, PCI_DEVICE_ID_TI_XIO3130D);
-d->config[PCI_REVISION_ID] = XIO3130_REVISION;
 
 rc = msi_init(d, XIO3130_MSI_OFFSET, XIO3130_MSI_NR_VECTOR,
   XIO3130_MSI_SUPPORTED_FLAGS & PCI_MSI_FLAGS_64BIT,
@@ -182,6 +179,9 @@ static PCIDeviceInfo xio3130_downstream_info = {
 .config_write = xio3130_downstream_write_config,
 .init = xio3130_downstream_initfn,
 .exit = xio3130_downstream_exitfn,
+.vendor_id = PCI_VENDOR_ID_TI,
+.device_id = PCI_DEVICE_ID_TI_XIO3130D,
+.revision = XIO3130_REVISION,
 
 .qdev.props = (Property[]) {
 DEFINE_PROP_UINT8("port", PCIESlot, port.port, 0),
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 15/38] hw/gt64xxx.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/gt64xxx.c |8 
 1 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/hw/gt64xxx.c b/hw/gt64xxx.c
index c66188f..8e1f6a0 100644
--- a/hw/gt64xxx.c
+++ b/hw/gt64xxx.c
@@ -1118,14 +1118,10 @@ static int gt64120_init(SysBusDevice *dev)
 static int gt64120_pci_init(PCIDevice *d)
 {
 /* FIXME: Malta specific hw assumptions ahead */
-pci_config_set_vendor_id(d->config, PCI_VENDOR_ID_MARVELL);
-pci_config_set_device_id(d->config, PCI_DEVICE_ID_MARVELL_GT6412X);
 pci_set_word(d->config + PCI_COMMAND, 0);
 pci_set_word(d->config + PCI_STATUS,
  PCI_STATUS_FAST_BACK | PCI_STATUS_DEVSEL_MEDIUM);
-pci_set_byte(d->config + PCI_CLASS_REVISION, 0x10);
 pci_config_set_prog_interface(d->config, 0);
-pci_config_set_class(d->config, PCI_CLASS_BRIDGE_HOST);
 pci_set_long(d->config + PCI_BASE_ADDRESS_0, 0x0008);
 pci_set_long(d->config + PCI_BASE_ADDRESS_1, 0x0108);
 pci_set_long(d->config + PCI_BASE_ADDRESS_2, 0x1c00);
@@ -1141,6 +1137,10 @@ static PCIDeviceInfo gt64120_pci_info = {
 .qdev.name = "gt64120_pci",
 .qdev.size = sizeof(PCIDevice),
 .init  = gt64120_pci_init,
+.vendor_id = PCI_VENDOR_ID_MARVELL,
+.device_id = PCI_DEVICE_ID_MARVELL_GT6412X,
+.revision  = 0x10,
+.class_id  = PCI_CLASS_BRIDGE_HOST,
 };
 
 static void gt64120_pci_register_devices(void)
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 28/38] hw/rtl8139.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/rtl8139.c |8 
 1 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/hw/rtl8139.c b/hw/rtl8139.c
index c7c7a3c..34e3a9e 100644
--- a/hw/rtl8139.c
+++ b/hw/rtl8139.c
@@ -3453,10 +3453,6 @@ static int pci_rtl8139_init(PCIDevice *dev)
 uint8_t *pci_conf;
 
 pci_conf = s->dev.config;
-pci_config_set_vendor_id(pci_conf, PCI_VENDOR_ID_REALTEK);
-pci_config_set_device_id(pci_conf, PCI_DEVICE_ID_REALTEK_8139);
-pci_conf[PCI_REVISION_ID] = RTL8139_PCI_REVID; /* >=0x20 is for 8139C+ */
-pci_config_set_class(pci_conf, PCI_CLASS_NETWORK_ETHERNET);
 pci_conf[PCI_INTERRUPT_PIN] = 1;/* interrupt pin 0 */
 /* TODO: start of capability list, but no capability
  * list bit in status register, and offset 0xdc seems unused. */
@@ -3510,6 +3506,10 @@ static PCIDeviceInfo rtl8139_info = {
 .init   = pci_rtl8139_init,
 .exit   = pci_rtl8139_uninit,
 .romfile= "pxe-rtl8139.rom",
+.vendor_id  = PCI_VENDOR_ID_REALTEK,
+.device_id  = PCI_DEVICE_ID_REALTEK_8139,
+.revision   = RTL8139_PCI_REVID, /* >=0x20 is for 8139C+ */
+.class_id   = PCI_CLASS_NETWORK_ETHERNET,
 .qdev.props = (Property[]) {
 DEFINE_NIC_PROPERTIES(RTL8139State, conf),
 DEFINE_PROP_END_OF_LIST(),
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 36/38] hw/wdt_i6300esb.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/wdt_i6300esb.c |6 +++---
 1 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/hw/wdt_i6300esb.c b/hw/wdt_i6300esb.c
index 0791721..bd57fd3 100644
--- a/hw/wdt_i6300esb.c
+++ b/hw/wdt_i6300esb.c
@@ -400,9 +400,6 @@ static int i6300esb_init(PCIDevice *dev)
 d->previous_reboot_flag = 0;
 
 pci_conf = d->dev.config;
-pci_config_set_vendor_id(pci_conf, PCI_VENDOR_ID_INTEL);
-pci_config_set_device_id(pci_conf, PCI_DEVICE_ID_INTEL_ESB_9);
-pci_config_set_class(pci_conf, PCI_CLASS_SYSTEM_OTHER);
 
 io_mem = cpu_register_io_memory(mem_read, mem_write, d,
 DEVICE_NATIVE_ENDIAN);
@@ -425,6 +422,9 @@ static PCIDeviceInfo i6300esb_info = {
 .config_read  = i6300esb_config_read,
 .config_write = i6300esb_config_write,
 .init = i6300esb_init,
+.vendor_id= PCI_VENDOR_ID_INTEL,
+.device_id= PCI_DEVICE_ID_INTEL_ESB_9,
+.class_id = PCI_CLASS_SYSTEM_OTHER,
 };
 
 static void i6300esb_register_devices(void)
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 38/38] hw/xio3130_upstream.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/xio3130_upstream.c |6 +++---
 1 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/hw/xio3130_upstream.c b/hw/xio3130_upstream.c
index a7640f5..8283695 100644
--- a/hw/xio3130_upstream.c
+++ b/hw/xio3130_upstream.c
@@ -65,9 +65,6 @@ static int xio3130_upstream_initfn(PCIDevice *d)
 }
 
 pcie_port_init_reg(d);
-pci_config_set_vendor_id(d->config, PCI_VENDOR_ID_TI);
-pci_config_set_device_id(d->config, PCI_DEVICE_ID_TI_XIO3130U);
-d->config[PCI_REVISION_ID] = XIO3130_REVISION;
 
 rc = msi_init(d, XIO3130_MSI_OFFSET, XIO3130_MSI_NR_VECTOR,
   XIO3130_MSI_SUPPORTED_FLAGS & PCI_MSI_FLAGS_64BIT,
@@ -159,6 +156,9 @@ static PCIDeviceInfo xio3130_upstream_info = {
 .config_write = xio3130_upstream_write_config,
 .init = xio3130_upstream_initfn,
 .exit = xio3130_upstream_exitfn,
+.vendor_id = PCI_VENDOR_ID_TI,
+.device_id = PCI_DEVICE_ID_TI_XIO3130U,
+.revision = XIO3130_REVISION,
 
 .qdev.props = (Property[]) {
 DEFINE_PROP_UINT8("port", PCIEPort, port, 0),
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 22/38] hw/lsi53c895a.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/lsi53c895a.c |   17 -
 1 files changed, 8 insertions(+), 9 deletions(-)

diff --git a/hw/lsi53c895a.c b/hw/lsi53c895a.c
index be4df58..af87b2c 100644
--- a/hw/lsi53c895a.c
+++ b/hw/lsi53c895a.c
@@ -2212,15 +2212,6 @@ static int lsi_scsi_init(PCIDevice *dev)
 
 pci_conf = s->dev.config;
 
-/* PCI Vendor ID (word) */
-pci_config_set_vendor_id(pci_conf, PCI_VENDOR_ID_LSI_LOGIC);
-/* PCI device ID (word) */
-pci_config_set_device_id(pci_conf, PCI_DEVICE_ID_LSI_53C895A);
-/* PCI base class code */
-pci_config_set_class(pci_conf, PCI_CLASS_STORAGE_SCSI);
-/* PCI subsystem ID */
-pci_conf[PCI_SUBSYSTEM_ID] = 0x00;
-pci_conf[PCI_SUBSYSTEM_ID + 1] = 0x10;
 /* PCI latency timer = 255 */
 pci_conf[PCI_LATENCY_TIMER] = 0xff;
 /* TODO: RST# value should be 0 */
@@ -2256,6 +2247,14 @@ static PCIDeviceInfo lsi_info = {
 .qdev.vmsd  = &vmstate_lsi_scsi,
 .init   = lsi_scsi_init,
 .exit   = lsi_scsi_uninit,
+/* PCI Vendor ID (word) */
+.vendor_id  = PCI_VENDOR_ID_LSI_LOGIC,
+/* PCI device ID (word) */
+.device_id  = PCI_DEVICE_ID_LSI_53C895A,
+/* PCI base class code */
+.class_id   = PCI_CLASS_STORAGE_SCSI,
+/* PCI subsystem ID */
+.subsystem_id = 0x1000,
 };
 
 static void lsi53c895a_register_devices(void)
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 07/38] vmware_vga.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/vmware_vga.c |   13 ++---
 1 files changed, 6 insertions(+), 7 deletions(-)

diff --git a/hw/vmware_vga.c b/hw/vmware_vga.c
index 4656767..354c221 100644
--- a/hw/vmware_vga.c
+++ b/hw/vmware_vga.c
@@ -1280,15 +1280,8 @@ static int pci_vmsvga_initfn(PCIDevice *dev)
 struct pci_vmsvga_state_s *s =
 DO_UPCAST(struct pci_vmsvga_state_s, card, dev);
 
-pci_config_set_vendor_id(s->card.config, PCI_VENDOR_ID_VMWARE);
-pci_config_set_device_id(s->card.config, SVGA_PCI_DEVICE_ID);
-pci_config_set_class(s->card.config, PCI_CLASS_DISPLAY_VGA);
 s->card.config[PCI_CACHE_LINE_SIZE]= 0x08; /* Cache line 
size */
 s->card.config[PCI_LATENCY_TIMER] = 0x40;  /* Latency timer */
-s->card.config[PCI_SUBSYSTEM_VENDOR_ID] = PCI_VENDOR_ID_VMWARE & 0xff;
-s->card.config[PCI_SUBSYSTEM_VENDOR_ID + 1]= PCI_VENDOR_ID_VMWARE 
>> 8;
-s->card.config[PCI_SUBSYSTEM_ID] = SVGA_PCI_DEVICE_ID & 0xff;
-s->card.config[PCI_SUBSYSTEM_ID + 1] = SVGA_PCI_DEVICE_ID >> 8;
 s->card.config[PCI_INTERRUPT_LINE] = 0xff; /* End */
 
 pci_register_bar(&s->card, 0, 0x10,
@@ -1316,6 +1309,12 @@ static PCIDeviceInfo vmsvga_info = {
 .no_hotplug   = 1,
 .init = pci_vmsvga_initfn,
 .romfile  = "vgabios-vmware.bin",
+
+.vendor_id=  PCI_VENDOR_ID_VMWARE,
+.device_id= SVGA_PCI_DEVICE_ID,
+.class_id = PCI_CLASS_DISPLAY_VGA,
+.subsystem_vendor_id = PCI_VENDOR_ID_VMWARE,
+.subsystem_id = SVGA_PCI_DEVICE_ID,
 };
 
 static void vmsvga_register(void)
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 29/38] hw/sh_pci.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/sh_pci.c |4 ++--
 1 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/hw/sh_pci.c b/hw/sh_pci.c
index e99d8db..a076cf2 100644
--- a/hw/sh_pci.c
+++ b/hw/sh_pci.c
@@ -137,8 +137,6 @@ static int sh_pci_init_device(SysBusDevice *dev)
 
 static int sh_pci_host_init(PCIDevice *d)
 {
-pci_config_set_vendor_id(d->config, PCI_VENDOR_ID_HITACHI);
-pci_config_set_device_id(d->config, PCI_DEVICE_ID_HITACHI_SH7751R);
 pci_set_word(d->config + PCI_COMMAND, PCI_COMMAND_WAIT);
 pci_set_word(d->config + PCI_STATUS, PCI_STATUS_CAP_LIST |
  PCI_STATUS_FAST_BACK | PCI_STATUS_DEVSEL_MEDIUM);
@@ -149,6 +147,8 @@ static PCIDeviceInfo sh_pci_host_info = {
 .qdev.name = "sh_pci_host",
 .qdev.size = sizeof(PCIDevice),
 .init  = sh_pci_host_init,
+.vendor_id = PCI_VENDOR_ID_HITACHI,
+.device_id = PCI_DEVICE_ID_HITACHI_SH7751R,
 };
 
 static void sh_pci_register_devices(void)
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 16/38] hw/ide/cmd646.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/ide/cmd646.c |   10 --
 1 files changed, 4 insertions(+), 6 deletions(-)

diff --git a/hw/ide/cmd646.c b/hw/ide/cmd646.c
index 5d5464a..56302b5 100644
--- a/hw/ide/cmd646.c
+++ b/hw/ide/cmd646.c
@@ -226,14 +226,8 @@ static int pci_cmd646_ide_initfn(PCIDevice *dev)
 qemu_irq *irq;
 int i;
 
-pci_config_set_vendor_id(pci_conf, PCI_VENDOR_ID_CMD);
-pci_config_set_device_id(pci_conf, PCI_DEVICE_ID_CMD_646);
-
-pci_conf[PCI_REVISION_ID] = 0x07; // IDE controller revision
 pci_conf[PCI_CLASS_PROG] = 0x8f;
 
-pci_config_set_class(pci_conf, PCI_CLASS_STORAGE_IDE);
-
 pci_conf[0x51] = 0x04; // enable IDE0
 if (d->secondary) {
 /* XXX: if not enabled, really disable the seconday IDE controller */
@@ -282,6 +276,10 @@ static PCIDeviceInfo cmd646_ide_info[] = {
 .qdev.name= "cmd646-ide",
 .qdev.size= sizeof(PCIIDEState),
 .init = pci_cmd646_ide_initfn,
+.vendor_id= PCI_VENDOR_ID_CMD,
+.device_id= PCI_DEVICE_ID_CMD_646,
+.revision = 0x07, // IDE controller revision
+.class_id = PCI_CLASS_STORAGE_IDE,
 .qdev.props   = (Property[]) {
 DEFINE_PROP_UINT32("secondary", PCIIDEState, secondary, 0),
 DEFINE_PROP_END_OF_LIST(),
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 04/38] dec_pci: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/dec_pci.c |   26 +++---
 1 files changed, 7 insertions(+), 19 deletions(-)

diff --git a/hw/dec_pci.c b/hw/dec_pci.c
index bf88f2a..a35f382 100644
--- a/hw/dec_pci.c
+++ b/hw/dec_pci.c
@@ -50,28 +50,16 @@ static int dec_map_irq(PCIDevice *pci_dev, int irq_num)
 return irq_num;
 }
 
-static int dec_21154_initfn(PCIDevice *dev)
-{
-int rc;
-
-rc = pci_bridge_initfn(dev);
-if (rc < 0) {
-return rc;
-}
-
-pci_config_set_vendor_id(dev->config, PCI_VENDOR_ID_DEC);
-pci_config_set_device_id(dev->config, PCI_DEVICE_ID_DEC_21154);
-return 0;
-}
-
 static PCIDeviceInfo dec_21154_pci_bridge_info = {
 .qdev.name = "dec-21154-p2p-bridge",
 .qdev.desc = "DEC 21154 PCI-PCI bridge",
 .qdev.size = sizeof(PCIBridge),
 .qdev.vmsd = &vmstate_pci_device,
 .qdev.reset = pci_bridge_reset,
-.init = dec_21154_initfn,
+.init = pci_bridge_initfn,
 .exit = pci_bridge_exitfn,
+.vendor_id = PCI_VENDOR_ID_DEC,
+.device_id = PCI_DEVICE_ID_DEC_21154,
 .config_write = pci_bridge_write_config,
 .is_bridge = 1,
 };
@@ -108,10 +96,6 @@ static int pci_dec_21154_init_device(SysBusDevice *dev)
 static int dec_21154_pci_host_init(PCIDevice *d)
 {
 /* PCI2PCI bridge same values as PearPC - check this */
-pci_config_set_vendor_id(d->config, PCI_VENDOR_ID_DEC);
-pci_config_set_device_id(d->config, PCI_DEVICE_ID_DEC_21154);
-pci_set_byte(d->config + PCI_REVISION_ID, 0x02);
-pci_config_set_class(d->config, PCI_CLASS_BRIDGE_PCI);
 return 0;
 }
 
@@ -119,6 +103,10 @@ static PCIDeviceInfo dec_21154_pci_host_info = {
 .qdev.name = "dec-21154",
 .qdev.size = sizeof(PCIDevice),
 .init  = dec_21154_pci_host_init,
+.vendor_id = PCI_VENDOR_ID_DEC,
+.device_id = PCI_DEVICE_ID_DEC_21154,
+.revision = 0x02,
+.class_id = PCI_CLASS_BRIDGE_PCI,
 .is_bridge  = 1,
 };
 
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 08/38] hw/ac97.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/ac97.c |9 -
 1 files changed, 4 insertions(+), 5 deletions(-)

diff --git a/hw/ac97.c b/hw/ac97.c
index d71072d..bf1d1d4 100644
--- a/hw/ac97.c
+++ b/hw/ac97.c
@@ -1281,9 +1281,6 @@ static int ac97_initfn (PCIDevice *dev)
 AC97LinkState *s = DO_UPCAST (AC97LinkState, dev, dev);
 uint8_t *c = s->dev.config;
 
-pci_config_set_vendor_id (c, PCI_VENDOR_ID_INTEL); /* ro */
-pci_config_set_device_id (c, PCI_DEVICE_ID_INTEL_82801AA_5); /* ro */
-
 /* TODO: no need to override */
 c[PCI_COMMAND] = 0x00;  /* pcicmd pci command rw, ro */
 c[PCI_COMMAND + 1] = 0x00;
@@ -1292,9 +1289,7 @@ static int ac97_initfn (PCIDevice *dev)
 c[PCI_STATUS] = PCI_STATUS_FAST_BACK;  /* pcists pci status rwc, ro */
 c[PCI_STATUS + 1] = PCI_STATUS_DEVSEL_MEDIUM >> 8;
 
-c[PCI_REVISION_ID] = 0x01;  /* rid revision ro */
 c[PCI_CLASS_PROG] = 0x00;  /* pi programming interface ro */
-pci_config_set_class (c, PCI_CLASS_MULTIMEDIA_AUDIO); /* ro */
 
 /* TODO set when bar is registered. no need to override. */
 /* nabmar native audio mixer base address rw */
@@ -1341,6 +1336,10 @@ static PCIDeviceInfo ac97_info = {
 .qdev.size= sizeof (AC97LinkState),
 .qdev.vmsd= &vmstate_ac97,
 .init = ac97_initfn,
+.vendor_id= PCI_VENDOR_ID_INTEL,
+.device_id= PCI_DEVICE_ID_INTEL_82801AA_5,
+.revision = 0x01,  /* rid revision ro */
+.class_id = PCI_CLASS_MULTIMEDIA_AUDIO,
 };
 
 static void ac97_register (void)
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 12/38] hw/e1000.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/e1000.c |8 
 1 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/hw/e1000.c b/hw/e1000.c
index f160bfc..96d84f9 100644
--- a/hw/e1000.c
+++ b/hw/e1000.c
@@ -1164,12 +1164,8 @@ static int pci_e1000_init(PCIDevice *pci_dev)
 
 pci_conf = d->dev.config;
 
-pci_config_set_vendor_id(pci_conf, PCI_VENDOR_ID_INTEL);
-pci_config_set_device_id(pci_conf, E1000_DEVID);
 /* TODO: we have no capabilities, so why is this bit set? */
 pci_set_word(pci_conf + PCI_STATUS, PCI_STATUS_CAP_LIST);
-pci_conf[PCI_REVISION_ID] = 0x03;
-pci_config_set_class(pci_conf, PCI_CLASS_NETWORK_ETHERNET);
 /* TODO: RST# value should be 0, PCI spec 6.2.4 */
 pci_conf[PCI_CACHE_LINE_SIZE] = 0x10;
 
@@ -1221,6 +1217,10 @@ static PCIDeviceInfo e1000_info = {
 .init   = pci_e1000_init,
 .exit   = pci_e1000_uninit,
 .romfile= "pxe-e1000.rom",
+.vendor_id  = PCI_VENDOR_ID_INTEL,
+.device_id  = E1000_DEVID,
+.revision   = 0x03,
+.class_id   = PCI_CLASS_NETWORK_ETHERNET,
 .qdev.props = (Property[]) {
 DEFINE_NIC_PROPERTIES(E1000State, conf),
 DEFINE_PROP_END_OF_LIST(),
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 11/38] hw/cirrus_vga.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/cirrus_vga.c |7 +++
 1 files changed, 3 insertions(+), 4 deletions(-)

diff --git a/hw/cirrus_vga.c b/hw/cirrus_vga.c
index 722cac7..e239e21 100644
--- a/hw/cirrus_vga.c
+++ b/hw/cirrus_vga.c
@@ -3097,7 +3097,6 @@ static int pci_cirrus_vga_initfn(PCIDevice *dev)
 {
  PCICirrusVGAState *d = DO_UPCAST(PCICirrusVGAState, dev, dev);
  CirrusVGAState *s = &d->cirrus_vga;
- uint8_t *pci_conf = d->dev.config;
  int device_id = CIRRUS_ID_CLGD5446;
 
  /* setup VGA */
@@ -3108,9 +3107,6 @@ static int pci_cirrus_vga_initfn(PCIDevice *dev)
   &s->vga);
 
  /* setup PCI */
- pci_config_set_vendor_id(pci_conf, PCI_VENDOR_ID_CIRRUS);
- pci_config_set_device_id(pci_conf, device_id);
- pci_config_set_class(pci_conf, PCI_CLASS_DISPLAY_VGA);
 
  /* setup memory space */
  /* memory #0 LFB */
@@ -3139,6 +3135,9 @@ static PCIDeviceInfo cirrus_vga_info = {
 .init = pci_cirrus_vga_initfn,
 .romfile  = VGABIOS_CIRRUS_FILENAME,
 .config_write = pci_cirrus_write_config,
+.vendor_id= PCI_VENDOR_ID_CIRRUS,
+.device_id= CIRRUS_ID_CLGD5446,
+.class_id = PCI_CLASS_DISPLAY_VGA,
 };
 
 static void cirrus_vga_register(void)
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 27/38] hw/qxl.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/qxl.c |7 ---
 1 files changed, 4 insertions(+), 3 deletions(-)

diff --git a/hw/qxl.c b/hw/qxl.c
index fe4212b..63cffc3 100644
--- a/hw/qxl.c
+++ b/hw/qxl.c
@@ -1233,7 +1233,6 @@ static int qxl_init_common(PCIQXLDevice *qxl)
 break;
 }
 
-pci_config_set_vendor_id(config, REDHAT_PCI_VENDOR_ID);
 pci_config_set_device_id(config, pci_device_id);
 pci_set_byte(&config[PCI_REVISION_ID], pci_device_rev);
 pci_set_byte(&config[PCI_INTERRUPT_PIN], 1);
@@ -1310,7 +1309,6 @@ static int qxl_init_primary(PCIDevice *dev)
 qxl0 = qxl;
 register_displaychangelistener(vga->ds, &display_listener);
 
-pci_config_set_class(dev->config, PCI_CLASS_DISPLAY_VGA);
 return qxl_init_common(qxl);
 }
 
@@ -1330,7 +1328,6 @@ static int qxl_init_secondary(PCIDevice *dev)
   qxl->vga.vram_size);
 qxl->vga.vram_ptr = qemu_get_ram_ptr(qxl->vga.vram_offset);
 
-pci_config_set_class(dev->config, PCI_CLASS_DISPLAY_OTHER);
 return qxl_init_common(qxl);
 }
 
@@ -1493,6 +1490,8 @@ static PCIDeviceInfo qxl_info_primary = {
 .init = qxl_init_primary,
 .config_write = qxl_write_config,
 .romfile  = "vgabios-qxl.bin",
+.vendor_id= REDHAT_PCI_VENDOR_ID,
+.class_id = PCI_CLASS_DISPLAY_VGA,
 .qdev.props = (Property[]) {
 DEFINE_PROP_UINT32("ram_size", PCIQXLDevice, vga.vram_size, 64 * 1024 
* 1024),
 DEFINE_PROP_UINT32("vram_size", PCIQXLDevice, vram_size, 64 * 1024 * 
1024),
@@ -1511,6 +1510,8 @@ static PCIDeviceInfo qxl_info_secondary = {
 .qdev.reset   = qxl_reset_handler,
 .qdev.vmsd= &qxl_vmstate,
 .init = qxl_init_secondary,
+.vendor_id= REDHAT_PCI_VENDOR_ID,
+.class_id = PCI_CLASS_DISPLAY_OTHER,
 .qdev.props = (Property[]) {
 DEFINE_PROP_UINT32("ram_size", PCIQXLDevice, vga.vram_size, 64 * 1024 
* 1024),
 DEFINE_PROP_UINT32("vram_size", PCIQXLDevice, vram_size, 64 * 1024 * 
1024),
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 21/38] hw/ivshmem.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/ivshmem.c |8 +++-
 1 files changed, 3 insertions(+), 5 deletions(-)

diff --git a/hw/ivshmem.c b/hw/ivshmem.c
index 7b19a81..3055dd2 100644
--- a/hw/ivshmem.c
+++ b/hw/ivshmem.c
@@ -706,12 +706,7 @@ static int pci_ivshmem_init(PCIDevice *dev)
 }
 
 pci_conf = s->dev.config;
-pci_config_set_vendor_id(pci_conf, PCI_VENDOR_ID_REDHAT_QUMRANET);
-pci_conf[0x02] = 0x10;
-pci_conf[0x03] = 0x11;
 pci_conf[PCI_COMMAND] = PCI_COMMAND_IO | PCI_COMMAND_MEMORY;
-pci_config_set_class(pci_conf, PCI_CLASS_MEMORY_RAM);
-pci_conf[PCI_HEADER_TYPE] = PCI_HEADER_TYPE_NORMAL;
 
 pci_config_set_interrupt_pin(pci_conf, 1);
 
@@ -809,6 +804,9 @@ static PCIDeviceInfo ivshmem_info = {
 .qdev.reset = ivshmem_reset,
 .init   = pci_ivshmem_init,
 .exit   = pci_ivshmem_uninit,
+.vendor_id  = PCI_VENDOR_ID_REDHAT_QUMRANET,
+.device_id  = 0x1110,
+.class_id   = PCI_CLASS_MEMORY_RAM,
 .qdev.props = (Property[]) {
 DEFINE_PROP_CHR("chardev", IVShmemState, server_chr),
 DEFINE_PROP_STRING("size", IVShmemState, sizearg),
-- 
1.7.1.1




[Qemu-devel] [PATCH v2 20/38] hw/ioh3420.c: convert to PCIDeviceInfo to initialize ids

2011-05-17 Thread Isaku Yamahata
use PCIDeviceInfo to initialize ids.

Signed-off-by: Isaku Yamahata 
---
 hw/ioh3420.c |7 +++
 1 files changed, 3 insertions(+), 4 deletions(-)

diff --git a/hw/ioh3420.c b/hw/ioh3420.c
index 95adf09..a6bfbb9 100644
--- a/hw/ioh3420.c
+++ b/hw/ioh3420.c
@@ -104,12 +104,8 @@ static int ioh3420_initfn(PCIDevice *d)
 return rc;
 }
 
-d->config[PCI_REVISION_ID] = PCI_DEVICE_ID_IOH_REV;
 pcie_port_init_reg(d);
 
-pci_config_set_vendor_id(d->config, PCI_VENDOR_ID_INTEL);
-pci_config_set_device_id(d->config, PCI_DEVICE_ID_IOH_EPORT);
-
 rc = pci_bridge_ssvid_init(d, IOH_EP_SSVID_OFFSET,
IOH_EP_SSVID_SVID, IOH_EP_SSVID_SSID);
 if (rc < 0) {
@@ -217,6 +213,9 @@ static PCIDeviceInfo ioh3420_info = {
 .config_write = ioh3420_write_config,
 .init = ioh3420_initfn,
 .exit = ioh3420_exitfn,
+.vendor_id = PCI_VENDOR_ID_INTEL,
+.device_id = PCI_DEVICE_ID_IOH_EPORT,
+.revision = PCI_DEVICE_ID_IOH_REV,
 
 .qdev.props = (Property[]) {
 DEFINE_PROP_UINT8("port", PCIESlot, port.port, 0),
-- 
1.7.1.1




  1   2   3   >