[Qemu-devel] buildbot failure in qemu on ppc-next_i386_debian_6_0

2011-10-21 Thread qemu
The Buildbot has detected a new failure on builder ppc-next_i386_debian_6_0 
while building qemu.
Full details are available at:
 http://buildbot.b1-systems.de/qemu/builders/ppc-next_i386_debian_6_0/builds/68

Buildbot URL: http://buildbot.b1-systems.de/qemu/

Buildslave for this Build: yuzuki

Build Reason: The Nightly scheduler named 'nightly_ppc-next' triggered this 
build
Build Source Stamp: [branch ppc-next] HEAD
Blamelist: 

BUILD FAILED: failed configure

sincerely,
 -The Buildbot



[Qemu-devel] [RFC v2 PATCH 5/4 PATCH] virtio-net: send gratuitous packet when needed

2011-10-21 Thread Jason Wang
This make let virtio-net driver can send gratituous packet by a new
config bit - VIRTIO_NET_S_ANNOUNCE in each config update
interrupt. When this bit is set by backend, the driver would schedule
a workqueue to send gratituous packet through NETDEV_NOTIFY_PEERS.

This feature is negotiated through bit VIRTIO_NET_F_GUEST_ANNOUNCE.

Signed-off-by: Jason Wang 
---
 drivers/net/virtio_net.c   |   31 ++-
 include/linux/virtio_net.h |2 ++
 2 files changed, 32 insertions(+), 1 deletions(-)

diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c
index b8225f3..1cdecf7 100644
--- a/drivers/net/virtio_net.c
+++ b/drivers/net/virtio_net.c
@@ -71,6 +71,9 @@ struct virtnet_info {
/* Work struct for refilling if we run low on memory. */
struct delayed_work refill;
 
+   /* Work struct for send gratituous packet. */
+   struct work_struct announce;
+
/* Chain pages by the private ptr. */
struct page *pages;
 
@@ -507,6 +510,13 @@ static void refill_work(struct work_struct *work)
schedule_delayed_work(&vi->refill, HZ/2);
 }
 
+static void announce_work(struct work_struct *work)
+{
+   struct virtnet_info *vi = container_of(work, struct virtnet_info,
+  announce);
+   netif_notify_peers(vi->dev);
+}
+
 static int virtnet_poll(struct napi_struct *napi, int budget)
 {
struct virtnet_info *vi = container_of(napi, struct virtnet_info, napi);
@@ -923,11 +933,22 @@ static void virtnet_update_status(struct virtnet_info *vi)
  &v, sizeof(v));
 
/* Ignore unknown (future) status bits */
-   v &= VIRTIO_NET_S_LINK_UP;
+   v &= VIRTIO_NET_S_LINK_UP | VIRTIO_NET_S_ANNOUNCE;
 
if (vi->status == v)
return;
 
+   if (v & VIRTIO_NET_S_ANNOUNCE) {
+   if ((v & VIRTIO_NET_S_LINK_UP) &&
+   virtio_has_feature(vi->vdev, VIRTIO_NET_F_GUEST_ANNOUNCE))
+   schedule_work(&vi->announce);
+   v &= ~VIRTIO_NET_S_ANNOUNCE;
+vi->vdev->config->set(vi->vdev,
+  offsetof(struct virtio_net_config,
+  status),
+  &v, sizeof(v));
+   }
+
vi->status = v;
 
if (vi->status & VIRTIO_NET_S_LINK_UP) {
@@ -937,6 +958,7 @@ static void virtnet_update_status(struct virtnet_info *vi)
netif_carrier_off(vi->dev);
netif_stop_queue(vi->dev);
}
+
 }
 
 static void virtnet_config_changed(struct virtio_device *vdev)
@@ -1016,6 +1038,8 @@ static int virtnet_probe(struct virtio_device *vdev)
goto free;
 
INIT_DELAYED_WORK(&vi->refill, refill_work);
+   if (virtio_has_feature(vdev, VIRTIO_NET_F_GUEST_ANNOUNCE))
+   INIT_WORK(&vi->announce, announce_work);
sg_init_table(vi->rx_sg, ARRAY_SIZE(vi->rx_sg));
sg_init_table(vi->tx_sg, ARRAY_SIZE(vi->tx_sg));
 
@@ -1077,6 +1101,8 @@ static int virtnet_probe(struct virtio_device *vdev)
 unregister:
unregister_netdev(dev);
cancel_delayed_work_sync(&vi->refill);
+   if (virtio_has_feature(vi->vdev, VIRTIO_NET_F_GUEST_ANNOUNCE))
+   cancel_work_sync(&vi->announce);
 free_vqs:
vdev->config->del_vqs(vdev);
 free_stats:
@@ -1118,6 +1144,8 @@ static void __devexit virtnet_remove(struct virtio_device 
*vdev)
 
unregister_netdev(vi->dev);
cancel_delayed_work_sync(&vi->refill);
+   if(virtio_has_feature(vi->vdev, VIRTIO_NET_F_GUEST_ANNOUNCE))
+   cancel_work_sync(&vi->announce);
 
/* Free unused buffers in both send and recv, if any. */
free_unused_bufs(vi);
@@ -1144,6 +1172,7 @@ static unsigned int features[] = {
VIRTIO_NET_F_GUEST_ECN, VIRTIO_NET_F_GUEST_UFO,
VIRTIO_NET_F_MRG_RXBUF, VIRTIO_NET_F_STATUS, VIRTIO_NET_F_CTRL_VQ,
VIRTIO_NET_F_CTRL_RX, VIRTIO_NET_F_CTRL_VLAN,
+   VIRTIO_NET_F_GUEST_ANNOUNCE,
 };
 
 static struct virtio_driver virtio_net_driver = {
diff --git a/include/linux/virtio_net.h b/include/linux/virtio_net.h
index 970d5a2..44a38d6 100644
--- a/include/linux/virtio_net.h
+++ b/include/linux/virtio_net.h
@@ -49,8 +49,10 @@
 #define VIRTIO_NET_F_CTRL_RX   18  /* Control channel RX mode support */
 #define VIRTIO_NET_F_CTRL_VLAN 19  /* Control channel VLAN filtering */
 #define VIRTIO_NET_F_CTRL_RX_EXTRA 20  /* Extra RX mode control support */
+#define VIRTIO_NET_F_GUEST_ANNOUNCE 21  /* Guest can send gratituous packet */
 
 #define VIRTIO_NET_S_LINK_UP   1   /* Link is up */
+#define VIRTIO_NET_S_ANNOUNCE   2   /* Announcement is needed */
 
 struct virtio_net_config {
/* The config defining mac address (if VIRTIO_NET_F_MAC) */




[Qemu-devel] [RFC v2 PATCH 3/4] net: model specific announcing support

2011-10-21 Thread Jason Wang
This patch introduce a function pointer in NetClientInfo which is
called during self announcement to do the model specific announcement
such as sending gratuitous packet. Previous method is kept when model
specific announcing fails or without it.

The first user would be virtio-net.

Signed-off-by: Jason Wang 
---
 net.h|2 ++
 savevm.c |8 +---
 2 files changed, 7 insertions(+), 3 deletions(-)

diff --git a/net.h b/net.h
index 4943d4b..1845f01 100644
--- a/net.h
+++ b/net.h
@@ -46,6 +46,7 @@ typedef ssize_t (NetReceive)(VLANClientState *, const uint8_t 
*, size_t);
 typedef ssize_t (NetReceiveIOV)(VLANClientState *, const struct iovec *, int);
 typedef void (NetCleanup) (VLANClientState *);
 typedef void (LinkStatusChanged)(VLANClientState *);
+typedef int (NetAnnounce)(VLANClientState *);
 
 typedef struct NetClientInfo {
 net_client_type type;
@@ -57,6 +58,7 @@ typedef struct NetClientInfo {
 NetCleanup *cleanup;
 LinkStatusChanged *link_status_changed;
 NetPoll *poll;
+NetAnnounce *announce;
 } NetClientInfo;
 
 struct VLANClientState {
diff --git a/savevm.c b/savevm.c
index 8293ee6..de6a01a 100644
--- a/savevm.c
+++ b/savevm.c
@@ -89,10 +89,12 @@ static void qemu_announce_self_iter(NICState *nic, void 
*opaque)
 {
 uint8_t buf[60];
 int len;
+NetAnnounce *func = nic->nc.info->announce;
 
-len = announce_self_create(buf, nic->conf->macaddr.a);
-
-qemu_send_packet_raw(&nic->nc, buf, len);
+if (func == NULL || func(&nic->nc) != 0) {
+len = announce_self_create(buf, nic->conf->macaddr.a);
+qemu_send_packet_raw(&nic->nc, buf, len);
+}
 }
 
 




[Qemu-devel] [RFC v2 PATCH 4/4] virtio-net: notify guest to annouce itself

2011-10-21 Thread Jason Wang
It's hard to track all mac address and its usage (vlan, bondings,
ipv6) in qemu to send gratituous packet in qemu side, so the better
choice is let guest do it.

The patch introduces a new rw config status bit of virtio-net,
VIRTIO_NET_S_ANNOUNCE which is used to notify guest to announce itself
( such as sending gratituous packets ) through config update
interrupt. When gust have done the annoucement, it should clear that
bit.

Signed-off-by: Jason Wang 
---
 hw/virtio-net.c |   20 +++-
 hw/virtio-net.h |2 ++
 2 files changed, 21 insertions(+), 1 deletions(-)

diff --git a/hw/virtio-net.c b/hw/virtio-net.c
index 8c2f460..7f844e7 100644
--- a/hw/virtio-net.c
+++ b/hw/virtio-net.c
@@ -95,6 +95,10 @@ static void virtio_net_set_config(VirtIODevice *vdev, const 
uint8_t *config)
 memcpy(n->mac, netcfg.mac, ETH_ALEN);
 qemu_format_nic_info_str(&n->nic->nc, n->mac);
 }
+
+if (memcmp(&netcfg.status, &n->status, sizeof(n->status))) {
+memcpy(&n->status, &netcfg.status, sizeof(n->status));
+}
 }
 
 static bool virtio_net_started(VirtIONet *n, uint8_t status)
@@ -227,7 +231,7 @@ static uint32_t virtio_net_get_features(VirtIODevice *vdev, 
uint32_t features)
 {
 VirtIONet *n = to_virtio_net(vdev);
 
-features |= (1 << VIRTIO_NET_F_MAC);
+features |= (1 << VIRTIO_NET_F_MAC | 1 << VIRTIO_NET_F_GUEST_ANNOUNCE);
 
 if (peer_has_vnet_hdr(n)) {
 tap_using_vnet_hdr(n->nic->nc.peer, 1);
@@ -983,6 +987,19 @@ static void virtio_net_cleanup(VLANClientState *nc)
 n->nic = NULL;
 }
 
+static int virtio_net_announce(VLANClientState *nc)
+{
+VirtIONet *n = DO_UPCAST(NICState, nc, nc)->opaque;
+
+if (n->vdev.guest_features & (0x1 << VIRTIO_NET_F_GUEST_ANNOUNCE)) {
+n->status |= VIRITO_NET_S_ANNOUNCE;
+virtio_notify_config(&n->vdev);
+return 0;
+}
+
+return 1;
+}
+
 static NetClientInfo net_virtio_info = {
 .type = NET_CLIENT_TYPE_NIC,
 .size = sizeof(NICState),
@@ -990,6 +1007,7 @@ static NetClientInfo net_virtio_info = {
 .receive = virtio_net_receive,
 .cleanup = virtio_net_cleanup,
 .link_status_changed = virtio_net_set_link_status,
+.announce = virtio_net_announce,
 };
 
 VirtIODevice *virtio_net_init(DeviceState *dev, NICConf *conf,
diff --git a/hw/virtio-net.h b/hw/virtio-net.h
index 4468741..c47bd52 100644
--- a/hw/virtio-net.h
+++ b/hw/virtio-net.h
@@ -44,8 +44,10 @@
 #define VIRTIO_NET_F_CTRL_RX18  /* Control channel RX mode support */
 #define VIRTIO_NET_F_CTRL_VLAN  19  /* Control channel VLAN filtering */
 #define VIRTIO_NET_F_CTRL_RX_EXTRA 20   /* Extra RX mode control support */
+#define VIRTIO_NET_F_GUEST_ANNOUNCE 21  /* Guest can announce itself */
 
 #define VIRTIO_NET_S_LINK_UP1   /* Link is up */
+#define VIRITO_NET_S_ANNOUNCE   2   /* Announcement is needed */
 
 #define TX_TIMER_INTERVAL 15 /* 150 us */
 




[Qemu-devel] [RFC v2 PATCH 2/4] net: export announce_self_create()

2011-10-21 Thread Jason Wang
Export and move announce_self_create() to net.c in order to be used by model
specific announcing function.

Signed-off-by: Jason Wang 
---
 net.c|   31 +++
 net.h|1 +
 savevm.c |   32 
 3 files changed, 32 insertions(+), 32 deletions(-)

diff --git a/net.c b/net.c
index d05930c..516ff9e 100644
--- a/net.c
+++ b/net.c
@@ -42,6 +42,37 @@ static QTAILQ_HEAD(, VLANClientState) non_vlan_clients;
 
 int default_net = 1;
 
+#ifndef ETH_P_RARP
+#define ETH_P_RARP 0x8035
+#endif
+#define ARP_HTYPE_ETH 0x0001
+#define ARP_PTYPE_IP 0x0800
+#define ARP_OP_REQUEST_REV 0x3
+
+int announce_self_create(uint8_t *buf, uint8_t *mac_addr)
+{
+/* Ethernet header. */
+memset(buf, 0xff, 6); /* destination MAC addr */
+memcpy(buf + 6, mac_addr, 6); /* source MAC addr */
+*(uint16_t *)(buf + 12) = htons(ETH_P_RARP); /* ethertype */
+
+/* RARP header. */
+*(uint16_t *)(buf + 14) = htons(ARP_HTYPE_ETH); /* hardware addr space */
+*(uint16_t *)(buf + 16) = htons(ARP_PTYPE_IP); /* protocol addr space */
+*(buf + 18) = 6; /* hardware addr length (ethernet) */
+*(buf + 19) = 4; /* protocol addr length (IPv4) */
+*(uint16_t *)(buf + 20) = htons(ARP_OP_REQUEST_REV); /* opcode */
+memcpy(buf + 22, mac_addr, 6); /* source hw addr */
+memset(buf + 28, 0x00, 4); /* source protocol addr */
+memcpy(buf + 32, mac_addr, 6); /* target hw addr */
+memset(buf + 38, 0x00, 4); /* target protocol addr */
+
+/* Padding to get up to 60 bytes (ethernet min packet size, minus FCS). */
+memset(buf + 42, 0x00, 18);
+
+return 60; /* len (FCS will be added by hardware) */
+}
+
 /***/
 /* network device redirectors */
 
diff --git a/net.h b/net.h
index 9f633f8..4943d4b 100644
--- a/net.h
+++ b/net.h
@@ -178,5 +178,6 @@ int do_netdev_del(Monitor *mon, const QDict *qdict, QObject 
**ret_data);
 void qdev_set_nic_properties(DeviceState *dev, NICInfo *nd);
 
 int net_handle_fd_param(Monitor *mon, const char *param);
+int announce_self_create(uint8_t *buf, uint8_t *mac_addr);
 
 #endif
diff --git a/savevm.c b/savevm.c
index bf4d0e7..8293ee6 100644
--- a/savevm.c
+++ b/savevm.c
@@ -85,38 +85,6 @@
 
 #define SELF_ANNOUNCE_ROUNDS 5
 
-#ifndef ETH_P_RARP
-#define ETH_P_RARP 0x8035
-#endif
-#define ARP_HTYPE_ETH 0x0001
-#define ARP_PTYPE_IP 0x0800
-#define ARP_OP_REQUEST_REV 0x3
-
-static int announce_self_create(uint8_t *buf,
-   uint8_t *mac_addr)
-{
-/* Ethernet header. */
-memset(buf, 0xff, 6); /* destination MAC addr */
-memcpy(buf + 6, mac_addr, 6); /* source MAC addr */
-*(uint16_t *)(buf + 12) = htons(ETH_P_RARP); /* ethertype */
-
-/* RARP header. */
-*(uint16_t *)(buf + 14) = htons(ARP_HTYPE_ETH); /* hardware addr space */
-*(uint16_t *)(buf + 16) = htons(ARP_PTYPE_IP); /* protocol addr space */
-*(buf + 18) = 6; /* hardware addr length (ethernet) */
-*(buf + 19) = 4; /* protocol addr length (IPv4) */
-*(uint16_t *)(buf + 20) = htons(ARP_OP_REQUEST_REV); /* opcode */
-memcpy(buf + 22, mac_addr, 6); /* source hw addr */
-memset(buf + 28, 0x00, 4); /* source protocol addr */
-memcpy(buf + 32, mac_addr, 6); /* target hw addr */
-memset(buf + 38, 0x00, 4); /* target protocol addr */
-
-/* Padding to get up to 60 bytes (ethernet min packet size, minus FCS). */
-memset(buf + 42, 0x00, 18);
-
-return 60; /* len (FCS will be added by hardware) */
-}
-
 static void qemu_announce_self_iter(NICState *nic, void *opaque)
 {
 uint8_t buf[60];




[Qemu-devel] [RFC v2 PATCH 1/4] announce self after vm start

2011-10-21 Thread Jason Wang
We send gratituous packets to let switch to update its mac address
table, this is only done after migration currently because guest may
move to the host with another port connect to switch.

Unfortunately this kind of notification is also needed for continue a
stopped vm as the mac address table entry may not existed because of
aging. This patch solve this by call qemu_announce_self() in
vm_start() instead of in process_incoming_migration(). Through this,
gratituous packets were sent each time when vm starts.

Signed-off-by: Jason Wang 
---
 migration.c |1 -
 vl.c|1 +
 2 files changed, 1 insertions(+), 1 deletions(-)

diff --git a/migration.c b/migration.c
index 77a51ad..3326b02 100644
--- a/migration.c
+++ b/migration.c
@@ -67,7 +67,6 @@ void process_incoming_migration(QEMUFile *f)
 fprintf(stderr, "load of migration failed\n");
 exit(0);
 }
-qemu_announce_self();
 DPRINTF("successfully loaded vm state\n");
 
 if (autostart) {
diff --git a/vl.c b/vl.c
index dbf7778..e4408e0 100644
--- a/vl.c
+++ b/vl.c
@@ -1262,6 +1262,7 @@ void vm_start(void)
 vm_state_notify(1, RUN_STATE_RUNNING);
 resume_all_vcpus();
 monitor_protocol_event(QEVENT_RESUME, NULL);
+qemu_announce_self();
 }
 }
 




[Qemu-devel] [RFC v2 PATCH 0/4] Support sending gratuitous by guest

2011-10-21 Thread Jason Wang
We only track primary mac address in qemu and send rarp packets after
migration to notify the switch to update its mac address table. This
may not works when guest have complicated network configurations such
as tagged vlan or ipv6, those connection may lost or stall after
migration.

One method to handle them is snooping the network traffic in qemu and
recording use of mac, but this method would hurt performance and is
impossible for network backend such as vhost.

So in order to solve this issue, the best method is to let guest
instead of qemu to send gratuitous packet. This series first add a
model specific fucntion which can let nic model to implement its own
announce function and then implement a virtio-net specific function to
let guest send the gratitous packet.

Only basic test were done.

Comments are welcomed.

Thanks

---

Jason Wang (4):
  announce self after vm start
  net: export announce_self_create()
  net: model specific announcing support
  virtio-net: notify guest to annouce itself


 hw/virtio-net.c |   20 +++-
 hw/virtio-net.h |2 ++
 migration.c |1 -
 net.c   |   31 +++
 net.h   |3 +++
 savevm.c|   40 +---
 vl.c|1 +
 7 files changed, 61 insertions(+), 37 deletions(-)

-- 
Jason Wang



[Qemu-devel] buildbot failure in qemu on ppc-next_x86_64_debian_6_0

2011-10-21 Thread qemu
The Buildbot has detected a new failure on builder ppc-next_x86_64_debian_6_0 
while building qemu.
Full details are available at:
 
http://buildbot.b1-systems.de/qemu/builders/ppc-next_x86_64_debian_6_0/builds/68

Buildbot URL: http://buildbot.b1-systems.de/qemu/

Buildslave for this Build: yuzuki

Build Reason: The Nightly scheduler named 'nightly_ppc-next' triggered this 
build
Build Source Stamp: [branch ppc-next] HEAD
Blamelist: 

BUILD FAILED: failed configure

sincerely,
 -The Buildbot



Re: [Qemu-devel] gcc auto-omit-frame-pointer vs msvc longjmp

2011-10-21 Thread xunxun

于 2011/10/22 13:13, xunxun 写道:

Hi, all

It seems that gcc's auto-omit-frame-pointer has other problems.

The example is from mingw bug tracker: 
http://sourceforge.net/tracker/?func=detail&aid=3426555&group_id=2435&atid=102435


g++ -O3 main.cpp   running will crash.
g++ -O2 main.cpp   running no crash.
g++ -O3 -fno-omit-frame-pointerrunning no crash.

I don't know in the end which optimize option defaultly contains 
this switch "-fomit-frame-pointer" on i686-pc-mingw32 or 
x86_64-w64-mingw32?



It crashes on Win7.

--
Best Regards,
xunxun




Re: [Qemu-devel] gcc auto-omit-frame-pointer vs msvc longjmp

2011-10-21 Thread xunxun

Hi, all

It seems that gcc's auto-omit-frame-pointer has other problems.

The example is from mingw bug tracker: 
http://sourceforge.net/tracker/?func=detail&aid=3426555&group_id=2435&atid=102435


g++ -O3 main.cpp   running will crash.
g++ -O2 main.cpp   running no crash.
g++ -O3 -fno-omit-frame-pointerrunning no crash.

I don't know in the end which optimize option defaultly contains 
this switch "-fomit-frame-pointer" on i686-pc-mingw32 or x86_64-w64-mingw32?


--
Best Regards,
xunxun

#include 

typedef void (*Func)(char*);

bool lie = false;
Func dummy = 0;

void moveToWindowsRecycler(const std::vector& filesToDelete = 
std::vector())  //throw FileError
{
if (!lie)
throw 1;

char errorMessage[2];

Func fun = lie ?  dummy : 0;
fun(errorMessage);

std::vector fileNames;

for (std::vector::const_iterator iter = filesToDelete.begin(); iter != 
filesToDelete.end(); ++iter)
fileNames.push_back(*iter);
}

void wgfdfsdgfsdgfsdg()  //throw FileError
{
::moveToWindowsRecycler();  //throw FileError
}

int main()
{
try
{
moveToWindowsRecycler()  ;//throw FileError
}
catch (...) {}

return 0;
}


Re: [Qemu-devel] [V2 PATCH] rtl8139: check the buffer availiability

2011-10-21 Thread Jason Wang
On 10/19/2011 09:28 AM, Michael S. Tsirkin wrote:
> On Mon, Oct 17, 2011 at 10:55:57AM +0800, Jason Wang wrote:
>> Reduce spurious packet drops on RX ring empty when in c+ mode by verifying 
>> that
>> we have at least 1 buffer ahead of the time.
>>
>> Change from v1:
>> Fix style comments from Stefan.
>>
>> Signed-off-by: Jason Wang 
>> ---
>>  hw/rtl8139.c |   44 ++--
>>  1 files changed, 30 insertions(+), 14 deletions(-)
>>
>> diff --git a/hw/rtl8139.c b/hw/rtl8139.c
>> index 3753950..bcbc5e3 100644
>> --- a/hw/rtl8139.c
>> +++ b/hw/rtl8139.c
>> @@ -84,6 +84,19 @@
>>  #define VLAN_TCI_LEN 2
>>  #define VLAN_HLEN (ETHER_TYPE_LEN + VLAN_TCI_LEN)
>>  
>> +/* w0 ownership flag */
>> +#define CP_RX_OWN (1<<31)
>> +/* w0 end of ring flag */
>> +#define CP_RX_EOR (1<<30)
>> +/* w0 bits 0...12 : buffer size */
>> +#define CP_RX_BUFFER_SIZE_MASK ((1<<13) - 1)
>> +/* w1 tag available flag */
>> +#define CP_RX_TAVA (1<<16)
>> +/* w1 bits 0...15 : VLAN tag */
>> +#define CP_RX_VLAN_TAG_MASK ((1<<16) - 1)
>> +/* w2 low  32bit of Rx buffer ptr */
>> +/* w3 high 32bit of Rx buffer ptr */
>> +
>>  #if defined (DEBUG_RTL8139)
>>  #  define DPRINTF(fmt, ...) \
>>  do { fprintf(stderr, "RTL8139: " fmt, ## __VA_ARGS__); } while (0)
>> @@ -805,6 +818,22 @@ static inline target_phys_addr_t 
>> rtl8139_addr64(uint32_t low, uint32_t high)
>>  #endif
>>  }
>>  
>> +/* Verify that we have at least one available rx buffer */
>> +static int rtl8139_cp_has_rxbuf(RTL8139State *s)
>> +{
>> +uint32_t val, rxdw0;
>> +target_phys_addr_t cplus_rx_ring_desc = rtl8139_addr64(s->RxRingAddrLO,
>> +   s->RxRingAddrHI);
>> +cplus_rx_ring_desc += 16 * s->currCPlusRxDesc;
>> +cpu_physical_memory_read(cplus_rx_ring_desc, &val, 4);
> 
> Interesting. Please note that cpu_physical_memory_read is not
> done atomically. Can guest be writing the value while
> we read it? If yes we'll get a corrupted value here,
> because CP_RX_OWN is the high bit so it is read last.
> Correct?
> 

Yes, there's a race, we need use atomic memory access method.

> I realize we have the same pattern in other places in this
> device, probably a bug as well?
> 

Yes, we need use atomic method at least for ownership check during TX/RX.

> 
>> +rxdw0 = le32_to_cpu(val);
>> +if (rxdw0 & CP_RX_OWN) {
>> +return 1;
>> +} else {
>> +return 0;
>> +}
> 
> Do we need to check that buffer size is large enough
> to include the packet like we do for non c+ mode?
> 

Not sure here is the best place, the buffer size is checked during
receiving.

>> +}
>> +
>>  static int rtl8139_can_receive(VLANClientState *nc)
>>  {
>>  RTL8139State *s = DO_UPCAST(NICState, nc, nc)->opaque;
>> @@ -819,7 +848,7 @@ static int rtl8139_can_receive(VLANClientState *nc)
>>  if (rtl8139_cp_receiver_enabled(s)) {
>>  /* ??? Flow control not implemented in c+ mode.
>> This is a hack to work around slirp deficiencies anyway.  */
>> -return 1;
>> +return rtl8139_cp_has_rxbuf(s);
>>  } else {
>>  avail = MOD2(s->RxBufferSize + s->RxBufPtr - s->RxBufAddr,
>>   s->RxBufferSize);
>> @@ -965,19 +994,6 @@ static ssize_t rtl8139_do_receive(VLANClientState *nc, 
>> const uint8_t *buf, size_
>>  
>>  /* begin C+ receiver mode */
>>  
>> -/* w0 ownership flag */
>> -#define CP_RX_OWN (1<<31)
>> -/* w0 end of ring flag */
>> -#define CP_RX_EOR (1<<30)
>> -/* w0 bits 0...12 : buffer size */
>> -#define CP_RX_BUFFER_SIZE_MASK ((1<<13) - 1)
>> -/* w1 tag available flag */
>> -#define CP_RX_TAVA (1<<16)
>> -/* w1 bits 0...15 : VLAN tag */
>> -#define CP_RX_VLAN_TAG_MASK ((1<<16) - 1)
>> -/* w2 low  32bit of Rx buffer ptr */
>> -/* w3 high 32bit of Rx buffer ptr */
>> -
>>  int descriptor = s->currCPlusRxDesc;
>>  target_phys_addr_t cplus_rx_ring_desc;
>>  




Re: [Qemu-devel] [V2 PATCH] rtl8139: check the buffer availiability

2011-10-21 Thread Jason Wang
On 10/18/2011 06:09 PM, Mark Wu wrote:
> Hi Jason,
> Could you please elaborate what problem you try to resolve by this
> patch?  And do you think we need notify I/O thread re-polling tap fd
> when receive descriptor becomes available? Otherwise, tap read polling
> will be disabled until the I/O handlers are updated by other reasons. Am
> I right?

Hi Mark, sorry for the late reply.

I think this patch may help to reduce packets dropping at the head of
the queue ( tap or netqueue in qemu) which may lead out of order packet
receiving in guest stack.

For the iothread notification, it looks impossible for 8139 as the
ownership was tracked through descriptor it self instead of a dedicated
register and there's no register which could be used to 'kick' 8139 for
packet receiving. When guest have refilled rx buffer of 8139cp,
tap_can_send() would return true and qemu would re-pool it. This may
introduce some latency when qemu is doning a block select() in
main_loop_wait().

Thanks.
> 
> 
> On 10/17/2011 10:55 AM, Jason Wang wrote:
>> Reduce spurious packet drops on RX ring empty when in c+ mode by
>> verifying that
>> we have at least 1 buffer ahead of the time.
>>
>> Change from v1:
>> Fix style comments from Stefan.
>>
>> Signed-off-by: Jason Wang
>> ---
>>   hw/rtl8139.c |   44 ++--
>>   1 files changed, 30 insertions(+), 14 deletions(-)
>>
>> diff --git a/hw/rtl8139.c b/hw/rtl8139.c
>> index 3753950..bcbc5e3 100644
>> --- a/hw/rtl8139.c
>> +++ b/hw/rtl8139.c
>> @@ -84,6 +84,19 @@
>>   #define VLAN_TCI_LEN 2
>>   #define VLAN_HLEN (ETHER_TYPE_LEN + VLAN_TCI_LEN)
>>
>> +/* w0 ownership flag */
>> +#define CP_RX_OWN (1<<31)
>> +/* w0 end of ring flag */
>> +#define CP_RX_EOR (1<<30)
>> +/* w0 bits 0...12 : buffer size */
>> +#define CP_RX_BUFFER_SIZE_MASK ((1<<13) - 1)
>> +/* w1 tag available flag */
>> +#define CP_RX_TAVA (1<<16)
>> +/* w1 bits 0...15 : VLAN tag */
>> +#define CP_RX_VLAN_TAG_MASK ((1<<16) - 1)
>> +/* w2 low  32bit of Rx buffer ptr */
>> +/* w3 high 32bit of Rx buffer ptr */
>> +
>>   #if defined (DEBUG_RTL8139)
>>   #  define DPRINTF(fmt, ...) \
>>   do { fprintf(stderr, "RTL8139: " fmt, ## __VA_ARGS__); } while (0)
>> @@ -805,6 +818,22 @@ static inline target_phys_addr_t
>> rtl8139_addr64(uint32_t low, uint32_t high)
>>   #endif
>>   }
>>
>> +/* Verify that we have at least one available rx buffer */
>> +static int rtl8139_cp_has_rxbuf(RTL8139State *s)
>> +{
>> +uint32_t val, rxdw0;
>> +target_phys_addr_t cplus_rx_ring_desc =
>> rtl8139_addr64(s->RxRingAddrLO,
>> +  
>> s->RxRingAddrHI);
>> +cplus_rx_ring_desc += 16 * s->currCPlusRxDesc;
>> +cpu_physical_memory_read(cplus_rx_ring_desc,&val, 4);
>> +rxdw0 = le32_to_cpu(val);
>> +if (rxdw0&  CP_RX_OWN) {
>> +return 1;
>> +} else {
>> +return 0;
>> +}
>> +}
>> +
>>   static int rtl8139_can_receive(VLANClientState *nc)
>>   {
>>   RTL8139State *s = DO_UPCAST(NICState, nc, nc)->opaque;
>> @@ -819,7 +848,7 @@ static int rtl8139_can_receive(VLANClientState *nc)
>>   if (rtl8139_cp_receiver_enabled(s)) {
>>   /* ??? Flow control not implemented in c+ mode.
>>  This is a hack to work around slirp deficiencies anyway.  */
>> -return 1;
>> +return rtl8139_cp_has_rxbuf(s);
>>   } else {
>>   avail = MOD2(s->RxBufferSize + s->RxBufPtr - s->RxBufAddr,
>>s->RxBufferSize);
>> @@ -965,19 +994,6 @@ static ssize_t rtl8139_do_receive(VLANClientState
>> *nc, const uint8_t *buf, size_
>>
>>   /* begin C+ receiver mode */
>>
>> -/* w0 ownership flag */
>> -#define CP_RX_OWN (1<<31)
>> -/* w0 end of ring flag */
>> -#define CP_RX_EOR (1<<30)
>> -/* w0 bits 0...12 : buffer size */
>> -#define CP_RX_BUFFER_SIZE_MASK ((1<<13) - 1)
>> -/* w1 tag available flag */
>> -#define CP_RX_TAVA (1<<16)
>> -/* w1 bits 0...15 : VLAN tag */
>> -#define CP_RX_VLAN_TAG_MASK ((1<<16) - 1)
>> -/* w2 low  32bit of Rx buffer ptr */
>> -/* w3 high 32bit of Rx buffer ptr */
>> -
>>   int descriptor = s->currCPlusRxDesc;
>>   target_phys_addr_t cplus_rx_ring_desc;
>>
>>
>>
> 
> 




[Qemu-devel] [Bug 739088] Re: I/O errors after "Save/Restore"

2011-10-21 Thread Yongjie Ren
using the following command line to restore guest, it works for me now.
qemu-system-x86_64 -m 256 -net nic,macaddr=00:16:3e:06:8a:08,model=rtl8139 -net 
tap,script=/etc/kvm/qemu-ifup -hda /root/test0320.img 
-incoming=/roo/test-save.img

** Changed in: qemu
   Status: New => Fix Released

-- 
You received this bug notification because you are a member of qemu-
devel-ml, which is subscribed to QEMU.
https://bugs.launchpad.net/bugs/739088

Title:
  I/O errors after "Save/Restore"

Status in QEMU:
  Fix Released

Bug description:
  qemu-kvm commit: b73357ecd2b14c057134cb71d29447b5b988c516
  ( Author: Marcelo Tosatti Date:   Wed Mar 16 
17:04:16 2011 -0300)
  kvm commit: a72e315c509376bbd1e121219c3ad9f23973923f

  After restoring from saved img, some I/O errors appear in dmesg and
  file system is read-only.  I'm sure that the  guest runs normally
  before saving. See the pictures attached in detail.

  Reproduce steps:
  
  1.create a guest:
qemu-img create -b /share/xvs/img/app/ia32e_SMP.img -f qcow2 
/root/test0320.img
qemu-system-x86_64  -m 256  -net 
nic,macaddr=00:16:3e:06:8a:08,model=rtl8139 -net tap,script=/etc/kvm/qemu-ifup 
-hda /root/test0320.img
  2.save the guest: 
on qemu monitor: migrate "exec:dd of=/root/test-save.img"
  3.quit from qemu: 
"q" command on qemu monitor
  4.restore from img just saved:
qemu-system-x86_64  -m 256  -net 
nic,macaddr=00:16:3e:06:8a:08,model=rtl8139 -net tap,script=/etc/kvm/qemu-ifup 
-incoming=/roo/test-save.img
  5.see dmesg in restored guest, you'll find some I/O errors. And run some
  commands such as "ps", "touch","reboot" and so on. Then some I/O errors 
appear.

To manage notifications about this bug go to:
https://bugs.launchpad.net/qemu/+bug/739088/+subscriptions



Re: [Qemu-devel] Multi heterogenous CPU archs for SoC sim?

2011-10-21 Thread Andreas Färber
Am 21.10.2011 08:58, schrieb Peter Maydell:
> On 20 October 2011 23:51, Andreas Färber  wrote:
>> Renesas announced
>> the R-Car H1 this week, a SoC with one SH4A core and four ARM Cortex-A9
>> cores.
> 
> Does it expose the SH4 to apps/OSes, or is it mostly used for
> power management or similar ignorable duties?

The predecessors were all SuperH based only, and the ARM cores don't
seem to have VFPv3 so the SH4A would feature a 128-bit FPU.
As for what automative customers may do with it once available, I have
no clue. My focus is on investigating where QEMU has architectural
shortcomings or undocumented assumptions blocking embedded development
and addressing these.

> (For several
> of the ARM boards we currently just ignore the fact that the real
> h/w has a Cortex-M3 doing power management type stuff.)

Mind to share which boards? I'm only aware of the NXP LPC43xx asymmetric
SoC (Cortex-M4 + Cortex-M0), which still is in development stage. The
datasheet doesn't really enlighten me how such a combo is supposed to
work in shared memory: Do all ARM cores share a reset vector (or what
you call it on arm) so that one has to branch based on CPUID to do
different tasks on different cores?

Andreas



[Qemu-devel] [Bug 739785] Re: qemu-i386 user mode on ARMv5 host fails (bash: fork: Invalid argument)

2011-10-21 Thread Steve
@Peter - thanks, fair enough... I don't know enough about qemu's source
to understand what you mean, but clearly it's a complex issue. For now
the patch seems to work for me-- I haven't had the issue that @Ricardo
discusses (again, I'm on armv7l, though).

-- 
You received this bug notification because you are a member of qemu-
devel-ml, which is subscribed to QEMU.
https://bugs.launchpad.net/bugs/739785

Title:
  qemu-i386 user mode on ARMv5 host fails (bash: fork: Invalid argument)

Status in QEMU:
  New

Bug description:
  Good time of day everybody,

  I have been trying to make usermode qemu on ARM with plugapps
  (archlinux) with archlinux i386 chroot to work.

  1. I installed arch linux in a virtuabox and created a chroot for it with 
mkarchroot. Transferred it to my pogo plug into /i386/
  2. I comiled qemu-i386 static and put it into /i386/usr/bin/
  ./configure --static --disable-blobs --disable-system 
--target-list=i386-linux-user
  make

  3. I also compiled linux kernel 2.6.38 with CONFIG_BINFMT_MISC=y and 
installed it.
  uname -a
  Linux Plugbox 2.6.38 #4 PREEMPT Fri Mar 18 22:19:10 CDT 2011 armv5tel 
Feroceon 88FR131 rev 1 (v5l) Marvell SheevaPlug Reference Board GNU/Linux

  4. Added the following options into /etc/rc.local
  /sbin/modprobe binfmt_misc
  /bin/mount binfmt_misc -t binfmt_misc /proc/sys/fs/binfmt_misc
  echo 
':qemu-i386:M::\x7fELF\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x03\x00:\xff\xff\xff\xff\xff\xfe\xfe\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfb\xff\xff\xff:/usr/bin/qemu-i386:'
 >/proc/sys/fs/binfmt_misc/register

  5. Also copied ld-linux.so.3 (actually ld-2.13.so because ld-
  linux.so.3 is a link to that file) from /lib/ to /i386/lib/

  6.Now i chroot into /i386 and I get this:
  [root@Plugbox i386]# chroot .
  [II aI hnve ao n@P /]# pacman -Suy
  bash: fork: Invalid argument

  7.I also downloaded linux-user-test-0.3 from qemu website and ran the test:
  [root@Plugbox linux-user-test-0.3]# make
  ./qemu-linux-user.sh
  [qemu-i386]
  ../qemu-0.14.0/i386-linux-user/qemu-i386 -L ./gnemul/qemu-i386 i386/ls -l 
dummyfile
  BUG IN DYNAMIC LINKER ld.so: dl-version.c: 210: _dl_check_map_versions: 
Assertion `needed != ((void *)0)' failed!
  make: *** [test] Error 127

To manage notifications about this bug go to:
https://bugs.launchpad.net/qemu/+bug/739785/+subscriptions



Re: [Qemu-devel] Multi heterogenous CPU archs for SoC sim?

2011-10-21 Thread Andreas
Am 21.10.2011 09:26, schrieb 陳韋任:
>   COREMU treats QEMU as an entity and lauches multiple QEMUs at the same
> time. QEMUs communicates to each other by using a underlying thin layer
> provided by COREMU.

> I think this approach is much clean than trying to
> parallelize QEMU itself.

In this case I disagree. Given shared global memory and peripherals in
the SoC case, any IPC or shared-memory setup is destined to create
performance or management overhead.

When there's independent nodes connected via CAN/LIN/FlexRay, then I
agree that multiple processes communicating via UNIX sockets make a lot
of sense.

My use case here is testing and debugging, so I think we could live with
the blocks being executed in an interleaved fashion until someone has
the ultimate parallelization solution for upstream.

Regards,
Andreas



[Qemu-devel] New message-Cheque 0000904533 on hold.

2011-10-21 Thread The Co-operative Bank
Dear Customer,

You Have One New Message 
You have a new message in online banking.

Subject: Cheque on hold.

Resolve the problem. 

We telephoned you today in relation to your Cheque payment, unfortunately we 
were unable to contact you on the telephone numbers registered for your account 
to verify the details.
You have receive a Cheque with a possible error in writing your name,
for more security verify before you cashing. 
Please click on the following link to to view a foto copy of the Cheque.
JQLHH0Y904533



Re: [Qemu-devel] [PATCH 0/2] block: Write out internal caches even with cache=unsafe

2011-10-21 Thread Paolo Bonzini

On 10/21/2011 07:08 PM, Kevin Wolf wrote:

Avi complained that not even writing out qcow2's cache on bdrv_flush() made
cache=unsafe too unsafe to be useful. He's got a point.


Why? cache=unsafe is explicitly allowing to s/data/manure/ on crash.

If you do this for raw-posix, you need to do it for all protocols.


Kevin Wolf (2):
   raw-posix: Convert to bdrv_co_flush
   block: Handle cache=unsafe only in raw-posix/win32


Paolo



[Qemu-devel] [PATCH 1/2] raw-posix: Convert to bdrv_co_flush

2011-10-21 Thread Kevin Wolf
The next patch will introduce an early return. Using a bottom half to invoke
the AIO callback wouldn't be much less code, so let's go with the native
block layer interface.

Signed-off-by: Kevin Wolf 
---
 block/raw-posix.c |   53 -
 1 files changed, 40 insertions(+), 13 deletions(-)

diff --git a/block/raw-posix.c b/block/raw-posix.c
index a3de373..dcae88a 100644
--- a/block/raw-posix.c
+++ b/block/raw-posix.c
@@ -357,15 +357,42 @@ static BlockDriverAIOCB *raw_aio_writev(BlockDriverState 
*bs,
   cb, opaque, QEMU_AIO_WRITE);
 }
 
-static BlockDriverAIOCB *raw_aio_flush(BlockDriverState *bs,
-BlockDriverCompletionFunc *cb, void *opaque)
+typedef struct CoroutineIOCompletion {
+Coroutine *coroutine;
+int ret;
+} CoroutineIOCompletion;
+
+static void raw_aio_flush_cb(void *opaque, int ret)
+{
+CoroutineIOCompletion *co = opaque;
+
+co->ret = ret;
+qemu_coroutine_enter(co->coroutine, NULL);
+}
+
+static int raw_co_flush(BlockDriverState *bs)
 {
 BDRVRawState *s = bs->opaque;
+BlockDriverAIOCB *acb;
+int ret;
 
-if (fd_open(bs) < 0)
-return NULL;
+CoroutineIOCompletion co = {
+.coroutine = qemu_coroutine_self(),
+};
 
-return paio_submit(bs, s->fd, 0, NULL, 0, cb, opaque, QEMU_AIO_FLUSH);
+ret = fd_open(bs);
+if (ret < 0) {
+return ret;
+}
+
+acb = paio_submit(bs, s->fd, 0, NULL, 0, raw_aio_flush_cb, &co, 
QEMU_AIO_FLUSH);
+if (acb == NULL) {
+return -EIO;
+}
+
+qemu_coroutine_yield();
+
+return co.ret;
 }
 
 static void raw_close(BlockDriverState *bs)
@@ -635,9 +662,9 @@ static BlockDriver bdrv_file = {
 .bdrv_create = raw_create,
 .bdrv_co_discard = raw_co_discard,
 
-.bdrv_aio_readv = raw_aio_readv,
+.bdrv_aio_readv  = raw_aio_readv,
 .bdrv_aio_writev = raw_aio_writev,
-.bdrv_aio_flush = raw_aio_flush,
+.bdrv_co_flush   = raw_co_flush,
 
 .bdrv_truncate = raw_truncate,
 .bdrv_getlength = raw_getlength,
@@ -903,9 +930,9 @@ static BlockDriver bdrv_host_device = {
 .create_options = raw_create_options,
 .bdrv_has_zero_init = hdev_has_zero_init,
 
-.bdrv_aio_readv= raw_aio_readv,
-.bdrv_aio_writev   = raw_aio_writev,
-.bdrv_aio_flush= raw_aio_flush,
+.bdrv_aio_readv = raw_aio_readv,
+.bdrv_aio_writev= raw_aio_writev,
+.bdrv_co_flush  = raw_co_flush,
 
 .bdrv_truncate  = raw_truncate,
 .bdrv_getlength= raw_getlength,
@@ -1024,7 +1051,7 @@ static BlockDriver bdrv_host_floppy = {
 
 .bdrv_aio_readv = raw_aio_readv,
 .bdrv_aio_writev= raw_aio_writev,
-.bdrv_aio_flush= raw_aio_flush,
+.bdrv_co_flush  = raw_co_flush,
 
 .bdrv_truncate  = raw_truncate,
 .bdrv_getlength= raw_getlength,
@@ -1123,7 +1150,7 @@ static BlockDriver bdrv_host_cdrom = {
 
 .bdrv_aio_readv = raw_aio_readv,
 .bdrv_aio_writev= raw_aio_writev,
-.bdrv_aio_flush= raw_aio_flush,
+.bdrv_co_flush  = raw_co_flush,
 
 .bdrv_truncate  = raw_truncate,
 .bdrv_getlength = raw_getlength,
@@ -1242,7 +1269,7 @@ static BlockDriver bdrv_host_cdrom = {
 
 .bdrv_aio_readv = raw_aio_readv,
 .bdrv_aio_writev= raw_aio_writev,
-.bdrv_aio_flush= raw_aio_flush,
+.bdrv_co_flush  = raw_co_flush,
 
 .bdrv_truncate  = raw_truncate,
 .bdrv_getlength = raw_getlength,
-- 
1.7.6.4




[Qemu-devel] [PATCH 14/19] vmdk: clean up open

2011-10-21 Thread Kevin Wolf
From: Paolo Bonzini 

Move vmdk_parent_open to vmdk_open.  There's another path how
vmdk_parent_open can be reached:

  vmdk_parse_extents() ->  vmdk_open_sparse() ->  vmdk_open_vmdk4() ->
  vmdk_open_desc_file().

If that can happen, however, the code is bogus.  vmdk_parent_open
reads from bs->file:

if (bdrv_pread(bs->file, s->desc_offset, desc, DESC_SIZE) != DESC_SIZE) {

but it is always called with s->desc_offset == 0 and with the same
bs->file.  So the data that vmdk_parent_open reads comes always from the
same place, and anyway there is only one place where it can write it,
namely bs->backing_file.

So, if it cannot happen, the patched code is okay.

It is also possible that the recursive call can happen, but only once.  In
that case there would still be a bug in vmdk_open_desc_file setting
s->desc_offset = 0, but the patched code is okay.

Finally, in the case where multiple recursive calls can happen the code
would need to be rewritten anyway.  It is likely that this would anyway
involve adding several parameters to vmdk_parent_open, and calling it from
vmdk_open_vmdk4.

Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 block/vmdk.c |   37 +++--
 1 files changed, 15 insertions(+), 22 deletions(-)

diff --git a/block/vmdk.c b/block/vmdk.c
index ea00938..ace2977 100644
--- a/block/vmdk.c
+++ b/block/vmdk.c
@@ -624,20 +624,7 @@ static int vmdk_open_desc_file(BlockDriverState *bs, int 
flags,
 return -ENOTSUP;
 }
 s->desc_offset = 0;
-ret = vmdk_parse_extents(buf, bs, bs->file->filename);
-if (ret) {
-vmdk_free_extents(bs);
-return ret;
-}
-
-/* try to open parent images, if exist */
-ret = vmdk_parent_open(bs);
-if (ret) {
-vmdk_free_extents(bs);
-return ret;
-}
-s->parent_cid = vmdk_read_cid(bs, 1);
-return 0;
+return vmdk_parse_extents(buf, bs, bs->file->filename);
 }
 
 static int vmdk_open(BlockDriverState *bs, int flags)
@@ -647,17 +634,23 @@ static int vmdk_open(BlockDriverState *bs, int flags)
 
 if (vmdk_open_sparse(bs, bs->file, flags) == 0) {
 s->desc_offset = 0x200;
-/* try to open parent images, if exist */
-ret = vmdk_parent_open(bs);
+} else {
+ret = vmdk_open_desc_file(bs, flags, 0);
 if (ret) {
-vmdk_free_extents(bs);
-return ret;
+goto fail;
 }
-s->parent_cid = vmdk_read_cid(bs, 1);
-return 0;
-} else {
-return vmdk_open_desc_file(bs, flags, 0);
 }
+/* try to open parent images, if exist */
+ret = vmdk_parent_open(bs);
+if (ret) {
+goto fail;
+}
+s->parent_cid = vmdk_read_cid(bs, 1);
+return ret;
+
+fail:
+vmdk_free_extents(bs);
+return ret;
 }
 
 static int get_whole_cluster(BlockDriverState *bs,
-- 
1.7.6.4




[Qemu-devel] [PATCH v3 13/13] simplify main loop functions

2011-10-21 Thread Paolo Bonzini
Provide a clean example of how to use the main loop in the tools.

Signed-off-by: Paolo Bonzini 
---
 cpus.c |5 
 cpus.h |1 -
 vl.c   |   79 +--
 3 files changed, 41 insertions(+), 44 deletions(-)

diff --git a/cpus.c b/cpus.c
index b9f1573..79a7656 100644
--- a/cpus.c
+++ b/cpus.c
@@ -626,11 +626,6 @@ void qemu_init_cpu_loop(void)
 qemu_thread_get_self(&io_thread);
 }
 
-void qemu_main_loop_start(void)
-{
-resume_all_vcpus();
-}
-
 void run_on_cpu(CPUState *env, void (*func)(void *data), void *data)
 {
 struct qemu_work_item wi;
diff --git a/cpus.h b/cpus.h
index 7422584..3525375 100644
--- a/cpus.h
+++ b/cpus.h
@@ -3,7 +3,6 @@
 
 /* cpus.c */
 void qemu_init_cpu_loop(void);
-void qemu_main_loop_start(void);
 void resume_all_vcpus(void);
 void pause_all_vcpus(void);
 void cpu_stop_current(void);
diff --git a/vl.c b/vl.c
index 7914df7..1ddb17b 100644
--- a/vl.c
+++ b/vl.c
@@ -1428,18 +1428,49 @@ void qemu_system_vmstop_request(RunState state)
 
 qemu_irq qemu_system_powerdown;
 
+static bool main_loop_should_exit(void)
+{
+RunState r;
+if (qemu_debug_requested()) {
+vm_stop(RUN_STATE_DEBUG);
+}
+if (qemu_shutdown_requested()) {
+qemu_kill_report();
+monitor_protocol_event(QEVENT_SHUTDOWN, NULL);
+if (no_shutdown) {
+vm_stop(RUN_STATE_SHUTDOWN);
+} else {
+return true;
+}
+}
+if (qemu_reset_requested()) {
+pause_all_vcpus();
+cpu_synchronize_all_states();
+qemu_system_reset(VMRESET_REPORT);
+resume_all_vcpus();
+if (runstate_check(RUN_STATE_INTERNAL_ERROR) ||
+runstate_check(RUN_STATE_SHUTDOWN)) {
+runstate_set(RUN_STATE_PAUSED);
+}
+}
+if (qemu_powerdown_requested()) {
+monitor_protocol_event(QEVENT_POWERDOWN, NULL);
+qemu_irq_raise(qemu_system_powerdown);
+}
+if (qemu_vmstop_requested(&r)) {
+vm_stop(r);
+}
+return false;
+}
+
 static void main_loop(void)
 {
 bool nonblocking;
-int last_io __attribute__ ((unused)) = 0;
+int last_io = 0;
 #ifdef CONFIG_PROFILER
 int64_t ti;
 #endif
-RunState r;
-
-qemu_main_loop_start();
-
-for (;;) {
+do {
 nonblocking = !kvm_enabled() && last_io > 0;
 #ifdef CONFIG_PROFILER
 ti = profile_getclock();
@@ -1448,38 +1479,7 @@ static void main_loop(void)
 #ifdef CONFIG_PROFILER
 dev_time += profile_getclock() - ti;
 #endif
-
-if (qemu_debug_requested()) {
-vm_stop(RUN_STATE_DEBUG);
-}
-if (qemu_shutdown_requested()) {
-qemu_kill_report();
-monitor_protocol_event(QEVENT_SHUTDOWN, NULL);
-if (no_shutdown) {
-vm_stop(RUN_STATE_SHUTDOWN);
-} else
-break;
-}
-if (qemu_reset_requested()) {
-pause_all_vcpus();
-cpu_synchronize_all_states();
-qemu_system_reset(VMRESET_REPORT);
-resume_all_vcpus();
-if (runstate_check(RUN_STATE_INTERNAL_ERROR) ||
-runstate_check(RUN_STATE_SHUTDOWN)) {
-runstate_set(RUN_STATE_PAUSED);
-}
-}
-if (qemu_powerdown_requested()) {
-monitor_protocol_event(QEVENT_POWERDOWN, NULL);
-qemu_irq_raise(qemu_system_powerdown);
-}
-if (qemu_vmstop_requested(&r)) {
-vm_stop(r);
-}
-}
-bdrv_close_all();
-pause_all_vcpus();
+} while (!main_loop_should_exit());
 }
 
 static void version(void)
@@ -3445,7 +3445,10 @@ int main(int argc, char **argv, char **envp)
 
 os_setup_post();
 
+resume_all_vcpus();
 main_loop();
+bdrv_close_all();
+pause_all_vcpus();
 net_cleanup();
 res_free();
 
-- 
1.7.6




[Qemu-devel] [PATCH 2/2] block: Handle cache=unsafe only in raw-posix/win32

2011-10-21 Thread Kevin Wolf
The expected meaning of cache=unsafe with qcow2 is that on a flush the metadata
caches are written out, but no fsync is performed.

Signed-off-by: Kevin Wolf 
---
 block.c   |4 +---
 block/raw-posix.c |4 
 block/raw-win32.c |4 
 3 files changed, 9 insertions(+), 3 deletions(-)

diff --git a/block.c b/block.c
index 11c7f91..0b7bc06 100644
--- a/block.c
+++ b/block.c
@@ -2908,9 +2908,7 @@ static void coroutine_fn bdrv_flush_co_entry(void *opaque)
 
 int coroutine_fn bdrv_co_flush(BlockDriverState *bs)
 {
-if (bs->open_flags & BDRV_O_NO_FLUSH) {
-return 0;
-} else if (!bs->drv) {
+if (!bs->drv) {
 return 0;
 } else if (bs->drv->bdrv_co_flush) {
 return bs->drv->bdrv_co_flush(bs);
diff --git a/block/raw-posix.c b/block/raw-posix.c
index dcae88a..9a3d3af 100644
--- a/block/raw-posix.c
+++ b/block/raw-posix.c
@@ -380,6 +380,10 @@ static int raw_co_flush(BlockDriverState *bs)
 .coroutine = qemu_coroutine_self(),
 };
 
+if (bs->open_flags & BDRV_O_NO_FLUSH) {
+return 0;
+}
+
 ret = fd_open(bs);
 if (ret < 0) {
 return ret;
diff --git a/block/raw-win32.c b/block/raw-win32.c
index f5f73bc..37a8bdb 100644
--- a/block/raw-win32.c
+++ b/block/raw-win32.c
@@ -156,6 +156,10 @@ static int raw_flush(BlockDriverState *bs)
 BDRVRawState *s = bs->opaque;
 int ret;
 
+if (bs->open_flags & BDRV_O_NO_FLUSH) {
+return 0;
+}
+
 ret = FlushFileBuffers(s->hfile);
 if (ret == 0) {
 return -EIO;
-- 
1.7.6.4




[Qemu-devel] [PATCH 0/2] block: Write out internal caches even with cache=unsafe

2011-10-21 Thread Kevin Wolf
Avi complained that not even writing out qcow2's cache on bdrv_flush() made
cache=unsafe too unsafe to be useful. He's got a point.

Kevin Wolf (2):
  raw-posix: Convert to bdrv_co_flush
  block: Handle cache=unsafe only in raw-posix/win32

 block.c   |4 +--
 block/raw-posix.c |   57 
 block/raw-win32.c |4 +++
 3 files changed, 49 insertions(+), 16 deletions(-)

-- 
1.7.6.4




[Qemu-devel] [PATCH 18/19] block: change flush to co_flush

2011-10-21 Thread Kevin Wolf
From: Paolo Bonzini 

Since coroutine operation is now mandatory, convert all bdrv_flush
implementations to coroutines.  For qcow2, this means taking the lock.
Other implementations are simpler and just forward bdrv_flush to the
underlying protocol, so they can avoid the lock.

The bdrv_flush callback is then unused and can be eliminated.

Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 block.c   |2 --
 block/cow.c   |6 +++---
 block/qcow.c  |   11 +--
 block/qcow2.c |   14 +++---
 block/raw-win32.c |4 ++--
 block/rbd.c   |4 ++--
 block/vdi.c   |6 +++---
 block/vmdk.c  |8 
 block/vpc.c   |6 +++---
 block_int.h   |1 -
 10 files changed, 29 insertions(+), 33 deletions(-)

diff --git a/block.c b/block.c
index 28508f2..81fb709 100644
--- a/block.c
+++ b/block.c
@@ -2892,8 +2892,6 @@ int coroutine_fn bdrv_co_flush(BlockDriverState *bs)
 qemu_coroutine_yield();
 return co.ret;
 }
-} else if (bs->drv->bdrv_flush) {
-return bs->drv->bdrv_flush(bs);
 } else {
 /*
  * Some block drivers always operate in either writethrough or unsafe
diff --git a/block/cow.c b/block/cow.c
index 29fa844..707c0aa 100644
--- a/block/cow.c
+++ b/block/cow.c
@@ -306,9 +306,9 @@ exit:
 return ret;
 }
 
-static int cow_flush(BlockDriverState *bs)
+static coroutine_fn int cow_co_flush(BlockDriverState *bs)
 {
-return bdrv_flush(bs->file);
+return bdrv_co_flush(bs->file);
 }
 
 static QEMUOptionParameter cow_create_options[] = {
@@ -334,7 +334,7 @@ static BlockDriver bdrv_cow = {
 .bdrv_write = cow_co_write,
 .bdrv_close= cow_close,
 .bdrv_create   = cow_create,
-.bdrv_flush= cow_flush,
+.bdrv_co_flush  = cow_co_flush,
 .bdrv_is_allocated = cow_is_allocated,
 
 .create_options = cow_create_options,
diff --git a/block/qcow.c b/block/qcow.c
index f93e3eb..ab36b29 100644
--- a/block/qcow.c
+++ b/block/qcow.c
@@ -781,10 +781,9 @@ static int qcow_write_compressed(BlockDriverState *bs, 
int64_t sector_num,
 return 0;
 }
 
-static BlockDriverAIOCB *qcow_aio_flush(BlockDriverState *bs,
-BlockDriverCompletionFunc *cb, void *opaque)
+static coroutine_fn int qcow_co_flush(BlockDriverState *bs)
 {
-return bdrv_aio_flush(bs->file, cb, opaque);
+return bdrv_co_flush(bs->file);
 }
 
 static int qcow_get_info(BlockDriverState *bs, BlockDriverInfo *bdi)
@@ -824,9 +823,9 @@ static BlockDriver bdrv_qcow = {
 .bdrv_is_allocated = qcow_is_allocated,
 .bdrv_set_key  = qcow_set_key,
 .bdrv_make_empty   = qcow_make_empty,
-.bdrv_co_readv  = qcow_co_readv,
-.bdrv_co_writev = qcow_co_writev,
-.bdrv_aio_flush= qcow_aio_flush,
+.bdrv_co_readv  = qcow_co_readv,
+.bdrv_co_writev = qcow_co_writev,
+.bdrv_co_flush  = qcow_co_flush,
 .bdrv_write_compressed = qcow_write_compressed,
 .bdrv_get_info = qcow_get_info,
 
diff --git a/block/qcow2.c b/block/qcow2.c
index 91f4f04..6ef38bf 100644
--- a/block/qcow2.c
+++ b/block/qcow2.c
@@ -1099,24 +1099,24 @@ fail:
 return ret;
 }
 
-static BlockDriverAIOCB *qcow2_aio_flush(BlockDriverState *bs,
- BlockDriverCompletionFunc *cb,
- void *opaque)
+static int qcow2_co_flush(BlockDriverState *bs)
 {
 BDRVQcowState *s = bs->opaque;
 int ret;
 
+qemu_co_mutex_lock(&s->lock);
 ret = qcow2_cache_flush(bs, s->l2_table_cache);
 if (ret < 0) {
-return NULL;
+return ret;
 }
 
 ret = qcow2_cache_flush(bs, s->refcount_block_cache);
 if (ret < 0) {
-return NULL;
+return ret;
 }
+qemu_co_mutex_unlock(&s->lock);
 
-return bdrv_aio_flush(bs->file, cb, opaque);
+return bdrv_co_flush(bs->file);
 }
 
 static int64_t qcow2_vm_state_offset(BDRVQcowState *s)
@@ -1237,7 +1237,7 @@ static BlockDriver bdrv_qcow2 = {
 
 .bdrv_co_readv  = qcow2_co_readv,
 .bdrv_co_writev = qcow2_co_writev,
-.bdrv_aio_flush = qcow2_aio_flush,
+.bdrv_co_flush  = qcow2_co_flush,
 
 .bdrv_discard   = qcow2_discard,
 .bdrv_truncate  = qcow2_truncate,
diff --git a/block/raw-win32.c b/block/raw-win32.c
index b7dd357..f5f73bc 100644
--- a/block/raw-win32.c
+++ b/block/raw-win32.c
@@ -281,7 +281,7 @@ static BlockDriver bdrv_file = {
 .bdrv_file_open= raw_open,
 .bdrv_close= raw_close,
 .bdrv_create   = raw_create,
-.bdrv_flush= raw_flush,
+.bdrv_co_flush  = raw_flush,
 .bdrv_read = raw_read,
 .bdrv_write= raw_write,
 .bdrv_truncate = raw_truncate,
@@ -409,7 +409,7 @@ static BlockDriver bdrv_host_device = {
 .bdrv_probe_device = hdev_probe_device,
 .bdrv_file_open= hdev_open,
 .bdrv_close= raw_clo

[Qemu-devel] [PATCH 01/19] sheepdog: add coroutine_fn markers

2011-10-21 Thread Kevin Wolf
From: Paolo Bonzini 

This makes the following patch easier to review.

Cc: MORITA Kazutaka 
Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 block/sheepdog.c |   14 +++---
 1 files changed, 7 insertions(+), 7 deletions(-)

diff --git a/block/sheepdog.c b/block/sheepdog.c
index ae857e2..9f80609 100644
--- a/block/sheepdog.c
+++ b/block/sheepdog.c
@@ -396,7 +396,7 @@ static inline int free_aio_req(BDRVSheepdogState *s, AIOReq 
*aio_req)
 return !QLIST_EMPTY(&acb->aioreq_head);
 }
 
-static void sd_finish_aiocb(SheepdogAIOCB *acb)
+static void coroutine_fn sd_finish_aiocb(SheepdogAIOCB *acb)
 {
 if (!acb->canceled) {
 qemu_coroutine_enter(acb->coroutine, NULL);
@@ -735,7 +735,7 @@ out:
 return ret;
 }
 
-static int add_aio_request(BDRVSheepdogState *s, AIOReq *aio_req,
+static int coroutine_fn add_aio_request(BDRVSheepdogState *s, AIOReq *aio_req,
struct iovec *iov, int niov, int create,
enum AIOCBState aiocb_type);
 
@@ -743,7 +743,7 @@ static int add_aio_request(BDRVSheepdogState *s, AIOReq 
*aio_req,
  * This function searchs pending requests to the object `oid', and
  * sends them.
  */
-static void send_pending_req(BDRVSheepdogState *s, uint64_t oid, uint32_t id)
+static void coroutine_fn send_pending_req(BDRVSheepdogState *s, uint64_t oid, 
uint32_t id)
 {
 AIOReq *aio_req, *next;
 SheepdogAIOCB *acb;
@@ -777,7 +777,7 @@ static void send_pending_req(BDRVSheepdogState *s, uint64_t 
oid, uint32_t id)
  * This function is registered as a fd handler, and called from the
  * main loop when s->fd is ready for reading responses.
  */
-static void aio_read_response(void *opaque)
+static void coroutine_fn aio_read_response(void *opaque)
 {
 SheepdogObjRsp rsp;
 BDRVSheepdogState *s = opaque;
@@ -1064,7 +1064,7 @@ out:
 return ret;
 }
 
-static int add_aio_request(BDRVSheepdogState *s, AIOReq *aio_req,
+static int coroutine_fn add_aio_request(BDRVSheepdogState *s, AIOReq *aio_req,
struct iovec *iov, int niov, int create,
enum AIOCBState aiocb_type)
 {
@@ -1517,7 +1517,7 @@ static int sd_truncate(BlockDriverState *bs, int64_t 
offset)
  * update metadata, this sends a write request to the vdi object.
  * Otherwise, this switches back to sd_co_readv/writev.
  */
-static void sd_write_done(SheepdogAIOCB *acb)
+static void coroutine_fn sd_write_done(SheepdogAIOCB *acb)
 {
 int ret;
 BDRVSheepdogState *s = acb->common.bs->opaque;
@@ -1615,7 +1615,7 @@ out:
  * Returns 1 when we need to wait a response, 0 when there is no sent
  * request and -errno in error cases.
  */
-static int sd_co_rw_vector(void *p)
+static int coroutine_fn sd_co_rw_vector(void *p)
 {
 SheepdogAIOCB *acb = p;
 int ret = 0;
-- 
1.7.6.4




[Qemu-devel] [PATCH 15/19] block: add a CoMutex to synchronous read drivers

2011-10-21 Thread Kevin Wolf
From: Paolo Bonzini 

The big conversion of bdrv_read/write to coroutines caused the two
homonymous callbacks in BlockDriver to become reentrant.  It goes
like this:

1) bdrv_read is now called in a coroutine, and calls bdrv_read or
bdrv_pread.

2) the nested bdrv_read goes through the fast path in bdrv_rw_co_entry;

3) in the common case when the protocol is file, bdrv_co_do_readv calls
bdrv_co_readv_em (and from here goes to bdrv_co_io_em), which yields
until the AIO operation is complete;

4) if bdrv_read had been called from a bottom half, the main loop
is free to iterate again: a device model or another bottom half
can then come and call bdrv_read again.

This applies to all four of read/write/flush/discard.  It would also
apply to is_allocated, but it is not used from within coroutines:
besides qemu-img.c and qemu-io.c, which operate synchronously, the
only user is the monitor.  Copy-on-read will introduce a use in the
block layer, and will require converting it.

The solution is "simply" to convert all drivers to coroutines!  We
just need to add a CoMutex that is taken around affected operations.

Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 block/bochs.c |2 ++
 block/cloop.c |2 ++
 block/cow.c   |2 ++
 block/dmg.c   |2 ++
 block/nbd.c   |2 ++
 block/parallels.c |2 ++
 block/vmdk.c  |2 ++
 block/vpc.c   |2 ++
 block/vvfat.c |2 ++
 9 files changed, 18 insertions(+), 0 deletions(-)

diff --git a/block/bochs.c b/block/bochs.c
index 3c2f8d1..b0f8072 100644
--- a/block/bochs.c
+++ b/block/bochs.c
@@ -80,6 +80,7 @@ struct bochs_header {
 };
 
 typedef struct BDRVBochsState {
+CoMutex lock;
 uint32_t *catalog_bitmap;
 int catalog_size;
 
@@ -150,6 +151,7 @@ static int bochs_open(BlockDriverState *bs, int flags)
 
 s->extent_size = le32_to_cpu(bochs.extra.redolog.extent);
 
+qemu_co_mutex_init(&s->lock);
 return 0;
  fail:
 return -1;
diff --git a/block/cloop.c b/block/cloop.c
index 8cff9f2..a91f372 100644
--- a/block/cloop.c
+++ b/block/cloop.c
@@ -27,6 +27,7 @@
 #include 
 
 typedef struct BDRVCloopState {
+CoMutex lock;
 uint32_t block_size;
 uint32_t n_blocks;
 uint64_t* offsets;
@@ -93,6 +94,7 @@ static int cloop_open(BlockDriverState *bs, int flags)
 
 s->sectors_per_block = s->block_size/512;
 bs->total_sectors = s->n_blocks*s->sectors_per_block;
+qemu_co_mutex_init(&s->lock);
 return 0;
 
 cloop_close:
diff --git a/block/cow.c b/block/cow.c
index 4cf543c..2f426e7 100644
--- a/block/cow.c
+++ b/block/cow.c
@@ -42,6 +42,7 @@ struct cow_header_v2 {
 };
 
 typedef struct BDRVCowState {
+CoMutex lock;
 int64_t cow_sectors_offset;
 } BDRVCowState;
 
@@ -84,6 +85,7 @@ static int cow_open(BlockDriverState *bs, int flags)
 
 bitmap_size = ((bs->total_sectors + 7) >> 3) + sizeof(cow_header);
 s->cow_sectors_offset = (bitmap_size + 511) & ~511;
+qemu_co_mutex_init(&s->lock);
 return 0;
  fail:
 return -1;
diff --git a/block/dmg.c b/block/dmg.c
index 64c3cce..111aeae 100644
--- a/block/dmg.c
+++ b/block/dmg.c
@@ -28,6 +28,7 @@
 #include 
 
 typedef struct BDRVDMGState {
+CoMutex lock;
 /* each chunk contains a certain number of sectors,
  * offsets[i] is the offset in the .dmg file,
  * lengths[i] is the length of the compressed chunk,
@@ -177,6 +178,7 @@ static int dmg_open(BlockDriverState *bs, int flags)
 
 s->current_chunk = s->n_chunks;
 
+qemu_co_mutex_init(&s->lock);
 return 0;
 fail:
 return -1;
diff --git a/block/nbd.c b/block/nbd.c
index 76f04d8..14ab225 100644
--- a/block/nbd.c
+++ b/block/nbd.c
@@ -47,6 +47,7 @@
 #endif
 
 typedef struct BDRVNBDState {
+CoMutex lock;
 int sock;
 uint32_t nbdflags;
 off_t size;
@@ -175,6 +176,7 @@ static int nbd_open(BlockDriverState *bs, const char* 
filename, int flags)
  */
 result = nbd_establish_connection(bs);
 
+qemu_co_mutex_init(&s->lock);
 return result;
 }
 
diff --git a/block/parallels.c b/block/parallels.c
index c64103d..b86e87e 100644
--- a/block/parallels.c
+++ b/block/parallels.c
@@ -46,6 +46,7 @@ struct parallels_header {
 } QEMU_PACKED;
 
 typedef struct BDRVParallelsState {
+CoMutex lock;
 
 uint32_t *catalog_bitmap;
 int catalog_size;
@@ -95,6 +96,7 @@ static int parallels_open(BlockDriverState *bs, int flags)
 for (i = 0; i < s->catalog_size; i++)
le32_to_cpus(&s->catalog_bitmap[i]);
 
+qemu_co_mutex_init(&s->lock);
 return 0;
 fail:
 if (s->catalog_bitmap)
diff --git a/block/vmdk.c b/block/vmdk.c
index ace2977..1ce220d 100644
--- a/block/vmdk.c
+++ b/block/vmdk.c
@@ -90,6 +90,7 @@ typedef struct VmdkExtent {
 } VmdkExtent;
 
 typedef struct BDRVVmdkState {
+CoMutex lock;
 int desc_offset;
 bool cid_updated;
 uint32_t parent_cid;
@@ -646,6 +647,7 @@ static int vmdk_open(BlockDriverState *bs, int flags)
 goto fail;
 }
 s->parent_cid = vmdk_read_cid

[Qemu-devel] [PULL 00/19] Block patches

2011-10-21 Thread Kevin Wolf
The following changes since commit c2e2343e1faae7bbc77574c12a25881b1b696808:

  hw/arm_gic.c: Fix save/load of irq_target array (2011-10-21 17:19:56 +0200)

are available in the git repository at:
  git://repo.or.cz/qemu/kevin.git for-anthony

Alex Jia (1):
  fix memory leak in aio_write_f

Kevin Wolf (5):
  xen_disk: Always set feature-barrier = 1
  fdc: Fix floppy port I/O
  qemu-img: Don't allow preallocation and compression at the same time
  qcow2: Fix bdrv_write_compressed error handling
  pc: Fix floppy drives with if=none

Paolo Bonzini (12):
  sheepdog: add coroutine_fn markers
  add socket_set_block
  block: rename bdrv_co_rw_bh
  block: unify flush implementations
  block: add bdrv_co_discard and bdrv_aio_discard support
  vmdk: fix return values of vmdk_parent_open
  vmdk: clean up open
  block: add a CoMutex to synchronous read drivers
  block: take lock around bdrv_read implementations
  block: take lock around bdrv_write implementations
  block: change flush to co_flush
  block: change discard to co_discard

Stefan Hajnoczi (1):
  block: drop redundant bdrv_flush implementation

 block.c   |  258 ++---
 block.h   |5 +
 block/blkdebug.c  |6 -
 block/blkverify.c |9 --
 block/bochs.c |   15 +++-
 block/cloop.c |   15 +++-
 block/cow.c   |   34 ++-
 block/dmg.c   |   15 +++-
 block/nbd.c   |   28 +-
 block/parallels.c |   15 +++-
 block/qcow.c  |   17 +---
 block/qcow2-cluster.c |6 +-
 block/qcow2.c |   72 ++
 block/qed.c   |6 -
 block/raw-posix.c |   23 +
 block/raw-win32.c |4 +-
 block/raw.c   |   23 ++---
 block/rbd.c   |4 +-
 block/sheepdog.c  |   14 ++--
 block/vdi.c   |6 +-
 block/vmdk.c  |   82 ++--
 block/vpc.c   |   34 ++-
 block/vvfat.c |   28 +-
 block_int.h   |9 +-
 hw/fdc.c  |   14 +++
 hw/fdc.h  |9 ++-
 hw/pc.c   |   25 +++--
 hw/pc.h   |3 +-
 hw/pc_piix.c  |5 +-
 hw/xen_disk.c |5 +-
 oslib-posix.c |7 ++
 oslib-win32.c |6 +
 qemu-img.c|   11 ++
 qemu-io.c |1 +
 qemu_socket.h |1 +
 trace-events  |1 +
 36 files changed, 524 insertions(+), 292 deletions(-)



[Qemu-devel] [PATCH v3 06/13] qemu-timer: do not refer to runstate_is_running()

2011-10-21 Thread Paolo Bonzini
Signed-off-by: Paolo Bonzini 
---
 cpus.c   |1 +
 qemu-timer.c |5 +
 2 files changed, 2 insertions(+), 4 deletions(-)

diff --git a/cpus.c b/cpus.c
index 21538e6..1328baa 100644
--- a/cpus.c
+++ b/cpus.c
@@ -1059,6 +1059,7 @@ void pause_all_vcpus(void)
 {
 CPUState *penv = first_cpu;
 
+qemu_clock_enable(vm_clock, false);
 while (penv) {
 penv->stop = 1;
 qemu_cpu_kick(penv);
diff --git a/qemu-timer.c b/qemu-timer.c
index 8129af6..d8507e3 100644
--- a/qemu-timer.c
+++ b/qemu-timer.c
@@ -504,10 +504,7 @@ void qemu_run_all_timers(void)
 }
 
 /* vm time timers */
-if (runstate_is_running()) {
-qemu_run_timers(vm_clock);
-}
-
+qemu_run_timers(vm_clock);
 qemu_run_timers(rt_clock);
 qemu_run_timers(host_clock);
 }
-- 
1.7.6





[Qemu-devel] [PATCH 17/19] block: take lock around bdrv_write implementations

2011-10-21 Thread Kevin Wolf
From: Paolo Bonzini 

This does the first part of the conversion to coroutines, by
wrapping bdrv_write implementations to take the mutex.

Drivers that implement bdrv_write rather than bdrv_co_writev can
then benefit from asynchronous operation (at least if the underlying
protocol supports it, which is not the case for raw-win32), even
though they still operate with a bounce buffer.

Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 block/cow.c   |   13 -
 block/nbd.c   |   13 -
 block/vmdk.c  |   13 -
 block/vpc.c   |   13 -
 block/vvfat.c |   13 -
 5 files changed, 60 insertions(+), 5 deletions(-)

diff --git a/block/cow.c b/block/cow.c
index a5fcd20..29fa844 100644
--- a/block/cow.c
+++ b/block/cow.c
@@ -226,6 +226,17 @@ static int cow_write(BlockDriverState *bs, int64_t 
sector_num,
 return cow_update_bitmap(bs, sector_num, nb_sectors);
 }
 
+static coroutine_fn int cow_co_write(BlockDriverState *bs, int64_t sector_num,
+ const uint8_t *buf, int nb_sectors)
+{
+int ret;
+BDRVCowState *s = bs->opaque;
+qemu_co_mutex_lock(&s->lock);
+ret = cow_write(bs, sector_num, buf, nb_sectors);
+qemu_co_mutex_unlock(&s->lock);
+return ret;
+}
+
 static void cow_close(BlockDriverState *bs)
 {
 }
@@ -320,7 +331,7 @@ static BlockDriver bdrv_cow = {
 .bdrv_probe= cow_probe,
 .bdrv_open = cow_open,
 .bdrv_read  = cow_co_read,
-.bdrv_write= cow_write,
+.bdrv_write = cow_co_write,
 .bdrv_close= cow_close,
 .bdrv_create   = cow_create,
 .bdrv_flush= cow_flush,
diff --git a/block/nbd.c b/block/nbd.c
index 6b22ae1..882b2dc 100644
--- a/block/nbd.c
+++ b/block/nbd.c
@@ -251,6 +251,17 @@ static coroutine_fn int nbd_co_read(BlockDriverState *bs, 
int64_t sector_num,
 return ret;
 }
 
+static coroutine_fn int nbd_co_write(BlockDriverState *bs, int64_t sector_num,
+ const uint8_t *buf, int nb_sectors)
+{
+int ret;
+BDRVNBDState *s = bs->opaque;
+qemu_co_mutex_lock(&s->lock);
+ret = nbd_write(bs, sector_num, buf, nb_sectors);
+qemu_co_mutex_unlock(&s->lock);
+return ret;
+}
+
 static void nbd_close(BlockDriverState *bs)
 {
 BDRVNBDState *s = bs->opaque;
@@ -272,7 +283,7 @@ static BlockDriver bdrv_nbd = {
 .instance_size = sizeof(BDRVNBDState),
 .bdrv_file_open= nbd_open,
 .bdrv_read  = nbd_co_read,
-.bdrv_write= nbd_write,
+.bdrv_write = nbd_co_write,
 .bdrv_close= nbd_close,
 .bdrv_getlength= nbd_getlength,
 .protocol_name = "nbd",
diff --git a/block/vmdk.c b/block/vmdk.c
index 0e791f2..3b376ed 100644
--- a/block/vmdk.c
+++ b/block/vmdk.c
@@ -1116,6 +1116,17 @@ static int vmdk_write(BlockDriverState *bs, int64_t 
sector_num,
 return 0;
 }
 
+static coroutine_fn int vmdk_co_write(BlockDriverState *bs, int64_t sector_num,
+  const uint8_t *buf, int nb_sectors)
+{
+int ret;
+BDRVVmdkState *s = bs->opaque;
+qemu_co_mutex_lock(&s->lock);
+ret = vmdk_write(bs, sector_num, buf, nb_sectors);
+qemu_co_mutex_unlock(&s->lock);
+return ret;
+}
+
 
 static int vmdk_create_extent(const char *filename, int64_t filesize,
   bool flat, bool compress)
@@ -1554,7 +1565,7 @@ static BlockDriver bdrv_vmdk = {
 .bdrv_probe = vmdk_probe,
 .bdrv_open  = vmdk_open,
 .bdrv_read  = vmdk_co_read,
-.bdrv_write = vmdk_write,
+.bdrv_write = vmdk_co_write,
 .bdrv_close = vmdk_close,
 .bdrv_create= vmdk_create,
 .bdrv_flush = vmdk_flush,
diff --git a/block/vpc.c b/block/vpc.c
index 0941533..74ca642 100644
--- a/block/vpc.c
+++ b/block/vpc.c
@@ -456,6 +456,17 @@ static int vpc_write(BlockDriverState *bs, int64_t 
sector_num,
 return 0;
 }
 
+static coroutine_fn int vpc_co_write(BlockDriverState *bs, int64_t sector_num,
+ const uint8_t *buf, int nb_sectors)
+{
+int ret;
+BDRVVPCState *s = bs->opaque;
+qemu_co_mutex_lock(&s->lock);
+ret = vpc_write(bs, sector_num, buf, nb_sectors);
+qemu_co_mutex_unlock(&s->lock);
+return ret;
+}
+
 static int vpc_flush(BlockDriverState *bs)
 {
 return bdrv_flush(bs->file);
@@ -653,7 +664,7 @@ static BlockDriver bdrv_vpc = {
 .bdrv_probe = vpc_probe,
 .bdrv_open  = vpc_open,
 .bdrv_read  = vpc_co_read,
-.bdrv_write = vpc_write,
+.bdrv_write = vpc_co_write,
 .bdrv_flush = vpc_flush,
 .bdrv_close = vpc_close,
 .bdrv_create= vpc_create,
diff --git a/block/vvfat.c b/block/vvfat.c
index 970cccf..e1fcdbc 100644
--- a/block/vvfat.c
+++ b/block/vvfat.c
@@ -2727,6 +2727,17 @@ DLOG(checkpoint());
 return 0;
 }
 
+static coroutine_fn int vvfa

[Qemu-devel] [PATCH 13/19] vmdk: fix return values of vmdk_parent_open

2011-10-21 Thread Kevin Wolf
From: Paolo Bonzini 

While vmdk_open_desc_file (touched by the patch) correctly changed -1
to -EINVAL, vmdk_open did not.  Fix it directly in vmdk_parent_open.

Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 block/vmdk.c |   15 +--
 1 files changed, 9 insertions(+), 6 deletions(-)

diff --git a/block/vmdk.c b/block/vmdk.c
index 5d16ec4..ea00938 100644
--- a/block/vmdk.c
+++ b/block/vmdk.c
@@ -283,10 +283,12 @@ static int vmdk_parent_open(BlockDriverState *bs)
 char *p_name;
 char desc[DESC_SIZE + 1];
 BDRVVmdkState *s = bs->opaque;
+int ret;
 
 desc[DESC_SIZE] = '\0';
-if (bdrv_pread(bs->file, s->desc_offset, desc, DESC_SIZE) != DESC_SIZE) {
-return -1;
+ret = bdrv_pread(bs->file, s->desc_offset, desc, DESC_SIZE);
+if (ret < 0) {
+return ret;
 }
 
 p_name = strstr(desc, "parentFileNameHint");
@@ -296,10 +298,10 @@ static int vmdk_parent_open(BlockDriverState *bs)
 p_name += sizeof("parentFileNameHint") + 1;
 end_name = strchr(p_name, '\"');
 if (end_name == NULL) {
-return -1;
+return -EINVAL;
 }
 if ((end_name - p_name) > sizeof(bs->backing_file) - 1) {
-return -1;
+return -EINVAL;
 }
 
 pstrcpy(bs->backing_file, end_name - p_name + 1, p_name);
@@ -629,9 +631,10 @@ static int vmdk_open_desc_file(BlockDriverState *bs, int 
flags,
 }
 
 /* try to open parent images, if exist */
-if (vmdk_parent_open(bs)) {
+ret = vmdk_parent_open(bs);
+if (ret) {
 vmdk_free_extents(bs);
-return -EINVAL;
+return ret;
 }
 s->parent_cid = vmdk_read_cid(bs, 1);
 return 0;
-- 
1.7.6.4




Re: [Qemu-devel] [PATCH 5/5] Convert remaining calls to g_malloc(sizeof(type)) to g_new()

2011-10-21 Thread Stuart Brady
On Fri, Oct 21, 2011 at 09:37:02AM +0200, Paolo Bonzini wrote:
> On 10/21/2011 02:26 AM, Stuart Brady wrote:
> >>>  They all look okay, perhaps the include path you passed to
> >>>  Coccinelle is incomplete?
> >Ah, good point!  I'm not sure what include dirs are needed, though...
> >anyone have any advice?
> >
> >Blue Swirl, I gather you're one of the few other people to have used
> >Coccinelle with Qemu's source...
> 
> I played a bit yesterday and it turns out that Coccinelle is a bit
> limited WRT handling headers, because they are very expensive.  I
> used "-I . -I +build -I hw" but it didn't help much.
> 
> Stuart/Blue, do you have a macro file?  Mine was simply "#define
> coroutine_fn".

I didn't even have that, but Coccinelle didn't seem to mind...

It did occur to me that since a lot of Qemu's source is recompiled with
different macro definitions for different targets, we need to be really
careful about what we do regarding includes.  Hopefully the names of
types that are used won't vary between targets, though.

Submitting what Coccinelle could process successfully and fixing up the
rest manually seemed reasonable, but I'd like to be as confident as
possible of these changes.

BTW, I'd thought that noone would ever do E = (T *)g_malloc(sizeof(*E)),
but from looking hw/blizzard.c, hw/cbus.c and hw/nseries.c, it seems
that this isn't quite the case afterall!  I'll be sure to include this
in my second attempt, once QEMU 1.0 has been released.

One thing that did not occur to me is use of E = malloc(sizeof(*E1)) or
E = malloc(sizeof(T1)) where E is of type void *, but E1 or T1 is not
what was intended.

I'm also somewhat astonished to find that sizeof(void) and sizeof(*E)
where E is of type void * both compile!  It would probably make sense to
check for these.

Any remaining calls to g_malloc() would be then be reviewed to make sure
that they're all correct.

We could also perhaps search for places where free() is called on memory
that is allocated with g_malloc(), as g_free() should be used instead.

---

Some background on my thinking before sending the patch series:

(T *)g_malloc(sizeof(T)) can obviously be safely replaced with
g_new(T, 1) since that's what g_new(T, 1) expands to.

Replacing E = g_malloc(sizeof(*E)) with E = g_new(T, 1) adds a cast, but
the cast does not provide any extra safety, since sizeof(*T) is pretty
much certain to be the correct size (unless T = void *).  There seems
to be some agreement that this is more readable, though.

Replacing E = g_malloc(sizeof(T)) without a cast with E = g_new(T, 1)
effectively just adds a cast to T *, which might result in additional
compilation warnings (which are turned into errors) but should have no
other effect, so this should be perfectly safe.

Other cases where g_malloc(sizeof(*E)) or g_malloc(sizeof(T)) is used
will either be due to Coccinelle not understanding the types, or due to
a bug in Qemu, and both of these cases need special consideration.

Cheers,
-- 
Stuart



[Qemu-devel] [PATCH 19/19] block: change discard to co_discard

2011-10-21 Thread Kevin Wolf
From: Paolo Bonzini 

Since coroutine operation is now mandatory, convert both bdrv_discard
implementations to coroutines.  For qcow2, this means taking the lock
around the operation.  raw-posix remains synchronous.

The bdrv_discard callback is then unused and can be eliminated.

Reviewed-by: Kevin Wolf 
Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 block.c   |2 --
 block/qcow2.c |   14 ++
 block/raw-posix.c |5 +++--
 block_int.h   |2 --
 4 files changed, 13 insertions(+), 10 deletions(-)

diff --git a/block.c b/block.c
index 81fb709..70aab63 100644
--- a/block.c
+++ b/block.c
@@ -2962,8 +2962,6 @@ int coroutine_fn bdrv_co_discard(BlockDriverState *bs, 
int64_t sector_num,
 qemu_coroutine_yield();
 return co.ret;
 }
-} else if (bs->drv->bdrv_discard) {
-return bs->drv->bdrv_discard(bs, sector_num, nb_sectors);
 } else {
 return 0;
 }
diff --git a/block/qcow2.c b/block/qcow2.c
index 6ef38bf..a181932 100644
--- a/block/qcow2.c
+++ b/block/qcow2.c
@@ -978,11 +978,17 @@ static int qcow2_make_empty(BlockDriverState *bs)
 return 0;
 }
 
-static int qcow2_discard(BlockDriverState *bs, int64_t sector_num,
-int nb_sectors)
+static coroutine_fn int qcow2_co_discard(BlockDriverState *bs,
+int64_t sector_num, int nb_sectors)
 {
-return qcow2_discard_clusters(bs, sector_num << BDRV_SECTOR_BITS,
+int ret;
+BDRVQcowState *s = bs->opaque;
+
+qemu_co_mutex_lock(&s->lock);
+ret = qcow2_discard_clusters(bs, sector_num << BDRV_SECTOR_BITS,
 nb_sectors);
+qemu_co_mutex_unlock(&s->lock);
+return ret;
 }
 
 static int qcow2_truncate(BlockDriverState *bs, int64_t offset)
@@ -1239,7 +1245,7 @@ static BlockDriver bdrv_qcow2 = {
 .bdrv_co_writev = qcow2_co_writev,
 .bdrv_co_flush  = qcow2_co_flush,
 
-.bdrv_discard   = qcow2_discard,
+.bdrv_co_discard= qcow2_co_discard,
 .bdrv_truncate  = qcow2_truncate,
 .bdrv_write_compressed  = qcow2_write_compressed,
 
diff --git a/block/raw-posix.c b/block/raw-posix.c
index afcb4c1..a3de373 100644
--- a/block/raw-posix.c
+++ b/block/raw-posix.c
@@ -602,7 +602,8 @@ static int xfs_discard(BDRVRawState *s, int64_t sector_num, 
int nb_sectors)
 }
 #endif
 
-static int raw_discard(BlockDriverState *bs, int64_t sector_num, int 
nb_sectors)
+static coroutine_fn int raw_co_discard(BlockDriverState *bs,
+int64_t sector_num, int nb_sectors)
 {
 #ifdef CONFIG_XFS
 BDRVRawState *s = bs->opaque;
@@ -632,7 +633,7 @@ static BlockDriver bdrv_file = {
 .bdrv_file_open = raw_open,
 .bdrv_close = raw_close,
 .bdrv_create = raw_create,
-.bdrv_discard = raw_discard,
+.bdrv_co_discard = raw_co_discard,
 
 .bdrv_aio_readv = raw_aio_readv,
 .bdrv_aio_writev = raw_aio_writev,
diff --git a/block_int.h b/block_int.h
index bc3b07e..dac00f5 100644
--- a/block_int.h
+++ b/block_int.h
@@ -62,8 +62,6 @@ struct BlockDriver {
   const uint8_t *buf, int nb_sectors);
 void (*bdrv_close)(BlockDriverState *bs);
 int (*bdrv_create)(const char *filename, QEMUOptionParameter *options);
-int (*bdrv_discard)(BlockDriverState *bs, int64_t sector_num,
-int nb_sectors);
 int (*bdrv_is_allocated)(BlockDriverState *bs, int64_t sector_num,
  int nb_sectors, int *pnum);
 int (*bdrv_set_key)(BlockDriverState *bs, const char *key);
-- 
1.7.6.4




[Qemu-devel] Sen Relativ fonder

2011-10-21 Thread fru7c...@snsbank.nl
 - This mail is in HTML. Some elements may be ommited in plain text. -

Vi har en outtagna portfölj av ditt avstånd Sen släkting fonder med vår bank. 
Skicka mig ett telefonnummer jag kan ringa dig eller ring mig på det här numret 
447.741.782.385.
www.snsbank.nl
Läs bifogad fil för fullständig information



[Qemu-devel] [PATCH 12/19] pc: Fix floppy drives with if=none

2011-10-21 Thread Kevin Wolf
Commit 63ffb564 broke floppy devices specified on the command line like
-drive file=...,if=none,id=floppy -global isa-fdc.driveA=floppy because it
relies on drive_get() which works only with -fda/-drive if=floppy.

This patch resembles what we're already doing for IDE, i.e. remember the floppy
device that was created and use that to extract the BlockDriverStates where
needed.

Signed-off-by: Kevin Wolf 
Reviewed-by: Markus Armbruster 
---
 hw/fdc.c |   12 
 hw/fdc.h |9 +++--
 hw/pc.c  |   25 ++---
 hw/pc.h  |3 ++-
 hw/pc_piix.c |5 +++--
 5 files changed, 38 insertions(+), 16 deletions(-)

diff --git a/hw/fdc.c b/hw/fdc.c
index f8af2de..ecaad09 100644
--- a/hw/fdc.c
+++ b/hw/fdc.c
@@ -1947,6 +1947,18 @@ static int sun4m_fdc_init1(SysBusDevice *dev)
 return fdctrl_init_common(fdctrl);
 }
 
+void fdc_get_bs(BlockDriverState *bs[], ISADevice *dev)
+{
+FDCtrlISABus *isa = DO_UPCAST(FDCtrlISABus, busdev, dev);
+FDCtrl *fdctrl = &isa->state;
+int i;
+
+for (i = 0; i < MAX_FD; i++) {
+bs[i] = fdctrl->drives[i].bs;
+}
+}
+
+
 static const VMStateDescription vmstate_isa_fdc ={
 .name = "fdc",
 .version_id = 2,
diff --git a/hw/fdc.h b/hw/fdc.h
index 09f73c6..506feb6 100644
--- a/hw/fdc.h
+++ b/hw/fdc.h
@@ -7,14 +7,15 @@
 /* fdc.c */
 #define MAX_FD 2
 
-static inline void fdctrl_init_isa(DriveInfo **fds)
+static inline ISADevice *fdctrl_init_isa(DriveInfo **fds)
 {
 ISADevice *dev;
 
 dev = isa_try_create("isa-fdc");
 if (!dev) {
-return;
+return NULL;
 }
+
 if (fds[0]) {
 qdev_prop_set_drive_nofail(&dev->qdev, "driveA", fds[0]->bdrv);
 }
@@ -22,10 +23,14 @@ static inline void fdctrl_init_isa(DriveInfo **fds)
 qdev_prop_set_drive_nofail(&dev->qdev, "driveB", fds[1]->bdrv);
 }
 qdev_init_nofail(&dev->qdev);
+
+return dev;
 }
 
 void fdctrl_init_sysbus(qemu_irq irq, int dma_chann,
 target_phys_addr_t mmio_base, DriveInfo **fds);
 void sun4m_fdctrl_init(qemu_irq irq, target_phys_addr_t io_base,
DriveInfo **fds, qemu_irq *fdc_tc);
+void fdc_get_bs(BlockDriverState *bs[], ISADevice *dev);
+
 #endif
diff --git a/hw/pc.c b/hw/pc.c
index f0802b7..eb4c2d8 100644
--- a/hw/pc.c
+++ b/hw/pc.c
@@ -331,12 +331,12 @@ static void pc_cmos_init_late(void *opaque)
 
 void pc_cmos_init(ram_addr_t ram_size, ram_addr_t above_4g_mem_size,
   const char *boot_device,
-  BusState *idebus0, BusState *idebus1,
+  ISADevice *floppy, BusState *idebus0, BusState *idebus1,
   ISADevice *s)
 {
 int val, nb, nb_heads, max_track, last_sect, i;
 FDriveType fd_type[2];
-DriveInfo *fd[2];
+BlockDriverState *fd[MAX_FD];
 static pc_cmos_init_late_arg arg;
 
 /* various important CMOS locations needed by PC/Bochs bios */
@@ -378,14 +378,16 @@ void pc_cmos_init(ram_addr_t ram_size, ram_addr_t 
above_4g_mem_size,
 }
 
 /* floppy type */
-for (i = 0; i < 2; i++) {
-fd[i] = drive_get(IF_FLOPPY, 0, i);
-if (fd[i] && bdrv_is_inserted(fd[i]->bdrv)) {
-bdrv_get_floppy_geometry_hint(fd[i]->bdrv, &nb_heads, &max_track,
-  &last_sect, FDRIVE_DRV_NONE,
-  &fd_type[i]);
-} else {
-fd_type[i] = FDRIVE_DRV_NONE;
+if (floppy) {
+fdc_get_bs(fd, floppy);
+for (i = 0; i < 2; i++) {
+if (fd[i] && bdrv_is_inserted(fd[i])) {
+bdrv_get_floppy_geometry_hint(fd[i], &nb_heads, &max_track,
+  &last_sect, FDRIVE_DRV_NONE,
+  &fd_type[i]);
+} else {
+fd_type[i] = FDRIVE_DRV_NONE;
+}
 }
 }
 val = (cmos_get_fd_drive_type(fd_type[0]) << 4) |
@@ -1124,6 +1126,7 @@ static void cpu_request_exit(void *opaque, int irq, int 
level)
 
 void pc_basic_device_init(qemu_irq *gsi,
   ISADevice **rtc_state,
+  ISADevice **floppy,
   bool no_vmport)
 {
 int i;
@@ -1188,7 +1191,7 @@ void pc_basic_device_init(qemu_irq *gsi,
 for(i = 0; i < MAX_FD; i++) {
 fd[i] = drive_get(IF_FLOPPY, 0, i);
 }
-fdctrl_init_isa(fd);
+*floppy = fdctrl_init_isa(fd);
 }
 
 void pc_pci_device_init(PCIBus *pci_bus)
diff --git a/hw/pc.h b/hw/pc.h
index b8ad9a3..4515006 100644
--- a/hw/pc.h
+++ b/hw/pc.h
@@ -142,11 +142,12 @@ qemu_irq *pc_allocate_cpu_irq(void);
 void pc_vga_init(PCIBus *pci_bus);
 void pc_basic_device_init(qemu_irq *gsi,
   ISADevice **rtc_state,
+  ISADevice **floppy,
   bool no_vmport);
 void pc_init_ne2k_isa(NICInfo *nd);
 void pc_cmos_init(ram_addr_t ram_size, ram_addr_t above_4g_mem_size,
   c

[Qemu-devel] [PATCH 06/19] block: unify flush implementations

2011-10-21 Thread Kevin Wolf
From: Paolo Bonzini 

Add coroutine support for flush and apply the same emulation that
we already do for read/write.  bdrv_aio_flush is simplified to always
go through a coroutine.

Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 block.c |  164 ++
 block.h |1 +
 block_int.h |1 +
 3 files changed, 76 insertions(+), 90 deletions(-)

diff --git a/block.c b/block.c
index 7184a0f..7b8b14d 100644
--- a/block.c
+++ b/block.c
@@ -53,17 +53,12 @@ static BlockDriverAIOCB *bdrv_aio_readv_em(BlockDriverState 
*bs,
 static BlockDriverAIOCB *bdrv_aio_writev_em(BlockDriverState *bs,
 int64_t sector_num, QEMUIOVector *qiov, int nb_sectors,
 BlockDriverCompletionFunc *cb, void *opaque);
-static BlockDriverAIOCB *bdrv_aio_flush_em(BlockDriverState *bs,
-BlockDriverCompletionFunc *cb, void *opaque);
-static BlockDriverAIOCB *bdrv_aio_noop_em(BlockDriverState *bs,
-BlockDriverCompletionFunc *cb, void *opaque);
 static int coroutine_fn bdrv_co_readv_em(BlockDriverState *bs,
  int64_t sector_num, int nb_sectors,
  QEMUIOVector *iov);
 static int coroutine_fn bdrv_co_writev_em(BlockDriverState *bs,
  int64_t sector_num, int nb_sectors,
  QEMUIOVector *iov);
-static int coroutine_fn bdrv_co_flush_em(BlockDriverState *bs);
 static int coroutine_fn bdrv_co_do_readv(BlockDriverState *bs,
 int64_t sector_num, int nb_sectors, QEMUIOVector *qiov);
 static int coroutine_fn bdrv_co_do_writev(BlockDriverState *bs,
@@ -203,9 +198,6 @@ void bdrv_register(BlockDriver *bdrv)
 }
 }
 
-if (!bdrv->bdrv_aio_flush)
-bdrv->bdrv_aio_flush = bdrv_aio_flush_em;
-
 QLIST_INSERT_HEAD(&bdrv_drivers, bdrv, list);
 }
 
@@ -1027,11 +1019,6 @@ static int bdrv_check_request(BlockDriverState *bs, 
int64_t sector_num,
nb_sectors * BDRV_SECTOR_SIZE);
 }
 
-static inline bool bdrv_has_async_flush(BlockDriver *drv)
-{
-return drv->bdrv_aio_flush != bdrv_aio_flush_em;
-}
-
 typedef struct RwCo {
 BlockDriverState *bs;
 int64_t sector_num;
@@ -1759,33 +1746,6 @@ const char *bdrv_get_device_name(BlockDriverState *bs)
 return bs->device_name;
 }
 
-int bdrv_flush(BlockDriverState *bs)
-{
-if (bs->open_flags & BDRV_O_NO_FLUSH) {
-return 0;
-}
-
-if (bs->drv && bdrv_has_async_flush(bs->drv) && qemu_in_coroutine()) {
-return bdrv_co_flush_em(bs);
-}
-
-if (bs->drv && bs->drv->bdrv_flush) {
-return bs->drv->bdrv_flush(bs);
-}
-
-/*
- * Some block drivers always operate in either writethrough or unsafe mode
- * and don't support bdrv_flush therefore. Usually qemu doesn't know how
- * the server works (because the behaviour is hardcoded or depends on
- * server-side configuration), so we can't ensure that everything is safe
- * on disk. Returning an error doesn't work because that would break guests
- * even if the server operates in writethrough mode.
- *
- * Let's hope the user knows what he's doing.
- */
-return 0;
-}
-
 void bdrv_flush_all(void)
 {
 BlockDriverState *bs;
@@ -2610,22 +2570,6 @@ fail:
 return -1;
 }
 
-BlockDriverAIOCB *bdrv_aio_flush(BlockDriverState *bs,
-BlockDriverCompletionFunc *cb, void *opaque)
-{
-BlockDriver *drv = bs->drv;
-
-trace_bdrv_aio_flush(bs, opaque);
-
-if (bs->open_flags & BDRV_O_NO_FLUSH) {
-return bdrv_aio_noop_em(bs, cb, opaque);
-}
-
-if (!drv)
-return NULL;
-return drv->bdrv_aio_flush(bs, cb, opaque);
-}
-
 void bdrv_aio_cancel(BlockDriverAIOCB *acb)
 {
 acb->pool->cancel(acb);
@@ -2785,41 +2729,28 @@ static BlockDriverAIOCB 
*bdrv_co_aio_rw_vector(BlockDriverState *bs,
 return &acb->common;
 }
 
-static BlockDriverAIOCB *bdrv_aio_flush_em(BlockDriverState *bs,
-BlockDriverCompletionFunc *cb, void *opaque)
+static void coroutine_fn bdrv_aio_flush_co_entry(void *opaque)
 {
-BlockDriverAIOCBSync *acb;
-
-acb = qemu_aio_get(&bdrv_em_aio_pool, bs, cb, opaque);
-acb->is_write = 1; /* don't bounce in the completion hadler */
-acb->qiov = NULL;
-acb->bounce = NULL;
-acb->ret = 0;
-
-if (!acb->bh)
-acb->bh = qemu_bh_new(bdrv_aio_bh_cb, acb);
+BlockDriverAIOCBCoroutine *acb = opaque;
+BlockDriverState *bs = acb->common.bs;
 
-bdrv_flush(bs);
+acb->req.error = bdrv_co_flush(bs);
+acb->bh = qemu_bh_new(bdrv_co_em_bh, acb);
 qemu_bh_schedule(acb->bh);
-return &acb->common;
 }
 
-static BlockDriverAIOCB *bdrv_aio_noop_em(BlockDriverState *bs,
+BlockDriverAIOCB *bdrv_aio_flush(BlockDriverState *bs,
 BlockDriverCompletionFunc *cb, void *opaque)
 {
-BlockDriverAIOCBSync *acb;
+trace_bdrv_aio_flush(bs, opaque);
 
-acb = qemu_aio_get(&bdrv_em_aio_po

[Qemu-devel] [PATCH 03/19] block: rename bdrv_co_rw_bh

2011-10-21 Thread Kevin Wolf
From: Paolo Bonzini 

Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 block.c |4 ++--
 1 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/block.c b/block.c
index 9873b57..7184a0f 100644
--- a/block.c
+++ b/block.c
@@ -2735,7 +2735,7 @@ static AIOPool bdrv_em_co_aio_pool = {
 .cancel = bdrv_aio_co_cancel_em,
 };
 
-static void bdrv_co_rw_bh(void *opaque)
+static void bdrv_co_em_bh(void *opaque)
 {
 BlockDriverAIOCBCoroutine *acb = opaque;
 
@@ -2758,7 +2758,7 @@ static void coroutine_fn bdrv_co_do_rw(void *opaque)
 acb->req.nb_sectors, acb->req.qiov);
 }
 
-acb->bh = qemu_bh_new(bdrv_co_rw_bh, acb);
+acb->bh = qemu_bh_new(bdrv_co_em_bh, acb);
 qemu_bh_schedule(acb->bh);
 }
 
-- 
1.7.6.4




[Qemu-devel] [PATCH 09/19] fdc: Fix floppy port I/O

2011-10-21 Thread Kevin Wolf
The floppy device was broken by commit 212ec7ba (fdc: Convert to
isa_register_portio_list). While the old interface provided the port number
relative to the floppy drive's io_base, the new one provides the real port
number, so we need to apply a bitmask now to get the register number.

Signed-off-by: Kevin Wolf 
---
 hw/fdc.c |2 ++
 1 files changed, 2 insertions(+), 0 deletions(-)

diff --git a/hw/fdc.c b/hw/fdc.c
index 4b06e04..f8af2de 100644
--- a/hw/fdc.c
+++ b/hw/fdc.c
@@ -434,6 +434,7 @@ static uint32_t fdctrl_read (void *opaque, uint32_t reg)
 FDCtrl *fdctrl = opaque;
 uint32_t retval;
 
+reg &= 7;
 switch (reg) {
 case FD_REG_SRA:
 retval = fdctrl_read_statusA(fdctrl);
@@ -471,6 +472,7 @@ static void fdctrl_write (void *opaque, uint32_t reg, 
uint32_t value)
 
 FLOPPY_DPRINTF("write reg%d: 0x%02x\n", reg & 7, value);
 
+reg &= 7;
 switch (reg) {
 case FD_REG_DOR:
 fdctrl_write_dor(fdctrl, value);
-- 
1.7.6.4




[Qemu-devel] [PATCH v3 09/13] qemu-timer: do not use RunState change handlers

2011-10-21 Thread Paolo Bonzini
Signed-off-by: Paolo Bonzini 
---
 qemu-timer.c |   12 
 1 files changed, 4 insertions(+), 8 deletions(-)

diff --git a/qemu-timer.c b/qemu-timer.c
index 58926dd..f11a28d 100644
--- a/qemu-timer.c
+++ b/qemu-timer.c
@@ -273,7 +273,11 @@ static QEMUClock *qemu_new_clock(int type)
 
 void qemu_clock_enable(QEMUClock *clock, int enabled)
 {
+bool old = clock->enabled;
 clock->enabled = enabled;
+if (enabled && !old) {
+qemu_rearm_alarm_timer(alarm_timer);
+}
 }
 
 int64_t qemu_clock_has_timers(QEMUClock *clock)
@@ -806,13 +810,6 @@ static void win32_rearm_timer(struct qemu_alarm_timer *t,
 
 #endif /* _WIN32 */
 
-static void alarm_timer_on_change_state_rearm(void *opaque, int running,
-  RunState state)
-{
-if (running)
-qemu_rearm_alarm_timer((struct qemu_alarm_timer *) opaque);
-}
-
 static void quit_timers(void)
 {
 struct qemu_alarm_timer *t = alarm_timer;
@@ -842,7 +839,6 @@ int init_timer_alarm(void)
 atexit(quit_timers);
 t->pending = 1;
 alarm_timer = t;
-qemu_add_vm_change_state_handler(alarm_timer_on_change_state_rearm, t);
 
 return 0;
 
-- 
1.7.6





[Qemu-devel] [PULL v3 00/13] allow tools to use the QEMU main loop

2011-10-21 Thread Paolo Bonzini
The following changes since commit c76eaf13975130768070ecd2d4f3107eb69ab757:

  hw/9pfs: Fix broken compilation caused by wrong trace events (2011-10-20 
15:30:59 -0500)

are available in the git repository at:
  git://github.com/bonzini/qemu.git split-main-loop-for-anthony

This patch series makes the QEMU main loop usable out of the executable,
and especially in tools and possibly unit tests.  This is cleaner because
it avoids introducing partial transitions to GIOChannel.  Interfacing with
the glib main loop is still possible.

The main loop code is currently split in cpus.c and vl.c.  Moving it
to a new file is easy; the problem is that the main loop depends on the
timer infrastructure in qemu-timer.c, and that file currently contains
the implementation of icount and the vm_clock.  This is bad for the
perspective of linking qemu-timer.c into the tools.  Luckily, it is
relatively easy to untie them and move them out of the way.  This is
what the largest part of the series does (patches 1-9).

Patches 10-13 complete the refactoring and cleanup some surrounding
code.

v2->v3
Rebased, added documentation

v1->v2
Rebased

Paolo Bonzini (13):
  remove unused function
  qemu-timer: remove active_timers array
  qemu-timer: move common code to qemu_rearm_alarm_timer
  qemu-timer: more clock functions
  qemu-timer: move icount to cpus.c
  qemu-timer: do not refer to runstate_is_running()
  qemu-timer: use atexit for quit_timers
  qemu-timer: move more stuff out of qemu-timer.c
  qemu-timer: do not use RunState change handlers
  main-loop: create main-loop.h
  main-loop: create main-loop.c
  Revert to a hand-made select loop
  simplify main loop functions

 Makefile.objs |2 +-
 async.c   |1 +
 cpus.c|  497 -
 cpus.h|3 +-
 exec-all.h|   14 ++
 exec.c|3 -
 hw/mac_dbdma.c|5 -
 hw/mac_dbdma.h|1 -
 iohandler.c   |   55 +--
 main-loop.c   |  495 
 main-loop.h   |  351 ++
 os-win32.c|  123 
 qemu-char.h   |   12 +-
 qemu-common.h |   37 +
 qemu-coroutine-lock.c |1 +
 qemu-os-posix.h   |4 -
 qemu-os-win32.h   |   17 +--
 qemu-timer.c  |  489 +---
 qemu-timer.h  |   31 +---
 savevm.c  |   25 +++
 slirp/libslirp.h  |   11 -
 sysemu.h  |3 +-
 vl.c  |  189 ---
 23 files changed, 1309 insertions(+), 1060 deletions(-)
 create mode 100644 main-loop.c
 create mode 100644 main-loop.h

-- 
1.7.6




[Qemu-devel] [PATCH v3 05/13] qemu-timer: move icount to cpus.c

2011-10-21 Thread Paolo Bonzini
None of this is needed by tools, and most of it can even be made static
inside cpus.c.

Signed-off-by: Paolo Bonzini 
---
 cpus.c|  295 +
 exec-all.h|   14 +++
 exec.c|3 -
 qemu-common.h |4 +
 qemu-timer.c  |  279 -
 qemu-timer.h  |   24 +-
 6 files changed, 296 insertions(+), 323 deletions(-)

diff --git a/cpus.c b/cpus.c
index 5f5b763..21538e6 100644
--- a/cpus.c
+++ b/cpus.c
@@ -65,6 +65,281 @@
 static CPUState *next_cpu;
 
 /***/
+/* guest cycle counter */
+
+/* Conversion factor from emulated instructions to virtual clock ticks.  */
+static int icount_time_shift;
+/* Arbitrarily pick 1MIPS as the minimum allowable speed.  */
+#define MAX_ICOUNT_SHIFT 10
+/* Compensate for varying guest execution speed.  */
+static int64_t qemu_icount_bias;
+static QEMUTimer *icount_rt_timer;
+static QEMUTimer *icount_vm_timer;
+static QEMUTimer *icount_warp_timer;
+static int64_t vm_clock_warp_start;
+static int64_t qemu_icount;
+
+typedef struct TimersState {
+int64_t cpu_ticks_prev;
+int64_t cpu_ticks_offset;
+int64_t cpu_clock_offset;
+int32_t cpu_ticks_enabled;
+int64_t dummy;
+} TimersState;
+
+TimersState timers_state;
+
+/* Return the virtual CPU time, based on the instruction counter.  */
+int64_t cpu_get_icount(void)
+{
+int64_t icount;
+CPUState *env = cpu_single_env;;
+
+icount = qemu_icount;
+if (env) {
+if (!can_do_io(env)) {
+fprintf(stderr, "Bad clock read\n");
+}
+icount -= (env->icount_decr.u16.low + env->icount_extra);
+}
+return qemu_icount_bias + (icount << icount_time_shift);
+}
+
+/* return the host CPU cycle counter and handle stop/restart */
+int64_t cpu_get_ticks(void)
+{
+if (use_icount) {
+return cpu_get_icount();
+}
+if (!timers_state.cpu_ticks_enabled) {
+return timers_state.cpu_ticks_offset;
+} else {
+int64_t ticks;
+ticks = cpu_get_real_ticks();
+if (timers_state.cpu_ticks_prev > ticks) {
+/* Note: non increasing ticks may happen if the host uses
+   software suspend */
+timers_state.cpu_ticks_offset += timers_state.cpu_ticks_prev - 
ticks;
+}
+timers_state.cpu_ticks_prev = ticks;
+return ticks + timers_state.cpu_ticks_offset;
+}
+}
+
+/* return the host CPU monotonic timer and handle stop/restart */
+int64_t cpu_get_clock(void)
+{
+int64_t ti;
+if (!timers_state.cpu_ticks_enabled) {
+return timers_state.cpu_clock_offset;
+} else {
+ti = get_clock();
+return ti + timers_state.cpu_clock_offset;
+}
+}
+
+/* enable cpu_get_ticks() */
+void cpu_enable_ticks(void)
+{
+if (!timers_state.cpu_ticks_enabled) {
+timers_state.cpu_ticks_offset -= cpu_get_real_ticks();
+timers_state.cpu_clock_offset -= get_clock();
+timers_state.cpu_ticks_enabled = 1;
+}
+}
+
+/* disable cpu_get_ticks() : the clock is stopped. You must not call
+   cpu_get_ticks() after that.  */
+void cpu_disable_ticks(void)
+{
+if (timers_state.cpu_ticks_enabled) {
+timers_state.cpu_ticks_offset = cpu_get_ticks();
+timers_state.cpu_clock_offset = cpu_get_clock();
+timers_state.cpu_ticks_enabled = 0;
+}
+}
+
+/* Correlation between real and virtual time is always going to be
+   fairly approximate, so ignore small variation.
+   When the guest is idle real and virtual time will be aligned in
+   the IO wait loop.  */
+#define ICOUNT_WOBBLE (get_ticks_per_sec() / 10)
+
+static void icount_adjust(void)
+{
+int64_t cur_time;
+int64_t cur_icount;
+int64_t delta;
+static int64_t last_delta;
+/* If the VM is not running, then do nothing.  */
+if (!runstate_is_running()) {
+return;
+}
+cur_time = cpu_get_clock();
+cur_icount = qemu_get_clock_ns(vm_clock);
+delta = cur_icount - cur_time;
+/* FIXME: This is a very crude algorithm, somewhat prone to oscillation.  
*/
+if (delta > 0
+&& last_delta + ICOUNT_WOBBLE < delta * 2
+&& icount_time_shift > 0) {
+/* The guest is getting too far ahead.  Slow time down.  */
+icount_time_shift--;
+}
+if (delta < 0
+&& last_delta - ICOUNT_WOBBLE > delta * 2
+&& icount_time_shift < MAX_ICOUNT_SHIFT) {
+/* The guest is getting too far behind.  Speed time up.  */
+icount_time_shift++;
+}
+last_delta = delta;
+qemu_icount_bias = cur_icount - (qemu_icount << icount_time_shift);
+}
+
+static void icount_adjust_rt(void *opaque)
+{
+qemu_mod_timer(icount_rt_timer,
+   qemu_get_clock_ms(rt_clock) + 1000);
+icount_adjust();
+}
+
+static void icount_adjust_vm(void *opaque)
+{
+qemu_mod_timer(icount_vm_timer,
+   qemu_get_clock_ns(vm_clock) + get

[Qemu-devel] [PATCH v3 11/13] main-loop: create main-loop.c

2011-10-21 Thread Paolo Bonzini
Signed-off-by: Paolo Bonzini 
---
 Makefile.objs|2 +-
 cpus.c   |  189 +-
 cpus.h   |1 +
 main-loop.c  |  495 ++
 main-loop.h  |   24 +++
 os-win32.c   |  123 --
 qemu-common.h|3 -
 qemu-os-posix.h  |4 -
 qemu-os-win32.h  |2 -
 slirp/libslirp.h |   11 --
 vl.c |  123 +-
 11 files changed, 523 insertions(+), 454 deletions(-)
 create mode 100644 main-loop.c

diff --git a/Makefile.objs b/Makefile.objs
index 9e20778..01587c8 100644
--- a/Makefile.objs
+++ b/Makefile.objs
@@ -81,7 +81,7 @@ common-obj-y += $(oslib-obj-y)
 common-obj-$(CONFIG_WIN32) += os-win32.o
 common-obj-$(CONFIG_POSIX) += os-posix.o
 
-common-obj-y += tcg-runtime.o host-utils.o
+common-obj-y += tcg-runtime.o host-utils.o main-loop.o
 common-obj-y += irq.o input.o
 common-obj-$(CONFIG_PTIMER) += ptimer.o
 common-obj-$(CONFIG_MAX7310) += max7310.o
diff --git a/cpus.c b/cpus.c
index 64237b4..b9f1573 100644
--- a/cpus.c
+++ b/cpus.c
@@ -542,143 +542,10 @@ static void qemu_kvm_eat_signals(CPUState *env)
 #endif /* !CONFIG_LINUX */
 
 #ifndef _WIN32
-static int io_thread_fd = -1;
-
-static void qemu_event_increment(void)
-{
-/* Write 8 bytes to be compatible with eventfd.  */
-static const uint64_t val = 1;
-ssize_t ret;
-
-if (io_thread_fd == -1) {
-return;
-}
-do {
-ret = write(io_thread_fd, &val, sizeof(val));
-} while (ret < 0 && errno == EINTR);
-
-/* EAGAIN is fine, a read must be pending.  */
-if (ret < 0 && errno != EAGAIN) {
-fprintf(stderr, "qemu_event_increment: write() failed: %s\n",
-strerror(errno));
-exit (1);
-}
-}
-
-static void qemu_event_read(void *opaque)
-{
-int fd = (intptr_t)opaque;
-ssize_t len;
-char buffer[512];
-
-/* Drain the notify pipe.  For eventfd, only 8 bytes will be read.  */
-do {
-len = read(fd, buffer, sizeof(buffer));
-} while ((len == -1 && errno == EINTR) || len == sizeof(buffer));
-}
-
-static int qemu_event_init(void)
-{
-int err;
-int fds[2];
-
-err = qemu_eventfd(fds);
-if (err == -1) {
-return -errno;
-}
-err = fcntl_setfl(fds[0], O_NONBLOCK);
-if (err < 0) {
-goto fail;
-}
-err = fcntl_setfl(fds[1], O_NONBLOCK);
-if (err < 0) {
-goto fail;
-}
-qemu_set_fd_handler2(fds[0], NULL, qemu_event_read, NULL,
- (void *)(intptr_t)fds[0]);
-
-io_thread_fd = fds[1];
-return 0;
-
-fail:
-close(fds[0]);
-close(fds[1]);
-return err;
-}
-
 static void dummy_signal(int sig)
 {
 }
 
-/* If we have signalfd, we mask out the signals we want to handle and then
- * use signalfd to listen for them.  We rely on whatever the current signal
- * handler is to dispatch the signals when we receive them.
- */
-static void sigfd_handler(void *opaque)
-{
-int fd = (intptr_t)opaque;
-struct qemu_signalfd_siginfo info;
-struct sigaction action;
-ssize_t len;
-
-while (1) {
-do {
-len = read(fd, &info, sizeof(info));
-} while (len == -1 && errno == EINTR);
-
-if (len == -1 && errno == EAGAIN) {
-break;
-}
-
-if (len != sizeof(info)) {
-printf("read from sigfd returned %zd: %m\n", len);
-return;
-}
-
-sigaction(info.ssi_signo, NULL, &action);
-if ((action.sa_flags & SA_SIGINFO) && action.sa_sigaction) {
-action.sa_sigaction(info.ssi_signo,
-(siginfo_t *)&info, NULL);
-} else if (action.sa_handler) {
-action.sa_handler(info.ssi_signo);
-}
-}
-}
-
-static int qemu_signal_init(void)
-{
-int sigfd;
-sigset_t set;
-
-/*
- * SIG_IPI must be blocked in the main thread and must not be caught
- * by sigwait() in the signal thread. Otherwise, the cpu thread will
- * not catch it reliably.
- */
-sigemptyset(&set);
-sigaddset(&set, SIG_IPI);
-pthread_sigmask(SIG_BLOCK, &set, NULL);
-
-sigemptyset(&set);
-sigaddset(&set, SIGIO);
-sigaddset(&set, SIGALRM);
-sigaddset(&set, SIGBUS);
-pthread_sigmask(SIG_BLOCK, &set, NULL);
-
-sigfd = qemu_signalfd(&set);
-if (sigfd == -1) {
-fprintf(stderr, "failed to create signalfd\n");
-return -errno;
-}
-
-fcntl_setfl(sigfd, O_NONBLOCK);
-
-qemu_set_fd_handler2(sigfd, NULL, sigfd_handler, NULL,
- (void *)(intptr_t)sigfd);
-
-return 0;
-}
-
 static void qemu_kvm_init_cpu_signals(CPUState *env)
 {
 int r;
@@ -722,38 +589,6 @@ static void qemu_tcg_init_cpu_signals(void)
 }
 
 #else /* _WIN32 */
-
-HANDLE qemu_event_handle;
-
-static void dummy_event_handler(void *opaque)
-{
-}
-
-static int qemu_event_init(void)
-{
-qemu_event_handle = CreateEvent(NULL, FALSE, FALSE, NULL);
-if (!qemu_ev

[Qemu-devel] [PATCH 08/19] block: add bdrv_co_discard and bdrv_aio_discard support

2011-10-21 Thread Kevin Wolf
From: Paolo Bonzini 

This similarly adds support for coroutine and asynchronous discard.

Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 block.c  |  102 +++--
 block.h  |4 ++
 block/raw.c  |   10 +++--
 block_int.h  |9 -
 trace-events |1 +
 5 files changed, 109 insertions(+), 17 deletions(-)

diff --git a/block.c b/block.c
index 7b8b14d..28508f2 100644
--- a/block.c
+++ b/block.c
@@ -1768,17 +1768,6 @@ int bdrv_has_zero_init(BlockDriverState *bs)
 return 1;
 }
 
-int bdrv_discard(BlockDriverState *bs, int64_t sector_num, int nb_sectors)
-{
-if (!bs->drv) {
-return -ENOMEDIUM;
-}
-if (!bs->drv->bdrv_discard) {
-return 0;
-}
-return bs->drv->bdrv_discard(bs, sector_num, nb_sectors);
-}
-
 /*
  * Returns true iff the specified sector is present in the disk image. Drivers
  * not implementing the functionality are assumed to not support backing files,
@@ -2754,6 +2743,34 @@ BlockDriverAIOCB *bdrv_aio_flush(BlockDriverState *bs,
 return &acb->common;
 }
 
+static void coroutine_fn bdrv_aio_discard_co_entry(void *opaque)
+{
+BlockDriverAIOCBCoroutine *acb = opaque;
+BlockDriverState *bs = acb->common.bs;
+
+acb->req.error = bdrv_co_discard(bs, acb->req.sector, acb->req.nb_sectors);
+acb->bh = qemu_bh_new(bdrv_co_em_bh, acb);
+qemu_bh_schedule(acb->bh);
+}
+
+BlockDriverAIOCB *bdrv_aio_discard(BlockDriverState *bs,
+int64_t sector_num, int nb_sectors,
+BlockDriverCompletionFunc *cb, void *opaque)
+{
+Coroutine *co;
+BlockDriverAIOCBCoroutine *acb;
+
+trace_bdrv_aio_discard(bs, sector_num, nb_sectors, opaque);
+
+acb = qemu_aio_get(&bdrv_em_co_aio_pool, bs, cb, opaque);
+acb->req.sector = sector_num;
+acb->req.nb_sectors = nb_sectors;
+co = qemu_coroutine_create(bdrv_aio_discard_co_entry);
+qemu_coroutine_enter(co, acb);
+
+return &acb->common;
+}
+
 void bdrv_init(void)
 {
 module_call_init(MODULE_INIT_BLOCK);
@@ -2915,6 +2932,69 @@ int bdrv_flush(BlockDriverState *bs)
 return rwco.ret;
 }
 
+static void coroutine_fn bdrv_discard_co_entry(void *opaque)
+{
+RwCo *rwco = opaque;
+
+rwco->ret = bdrv_co_discard(rwco->bs, rwco->sector_num, rwco->nb_sectors);
+}
+
+int coroutine_fn bdrv_co_discard(BlockDriverState *bs, int64_t sector_num,
+ int nb_sectors)
+{
+if (!bs->drv) {
+return -ENOMEDIUM;
+} else if (bdrv_check_request(bs, sector_num, nb_sectors)) {
+return -EIO;
+} else if (bs->read_only) {
+return -EROFS;
+} else if (bs->drv->bdrv_co_discard) {
+return bs->drv->bdrv_co_discard(bs, sector_num, nb_sectors);
+} else if (bs->drv->bdrv_aio_discard) {
+BlockDriverAIOCB *acb;
+CoroutineIOCompletion co = {
+.coroutine = qemu_coroutine_self(),
+};
+
+acb = bs->drv->bdrv_aio_discard(bs, sector_num, nb_sectors,
+bdrv_co_io_em_complete, &co);
+if (acb == NULL) {
+return -EIO;
+} else {
+qemu_coroutine_yield();
+return co.ret;
+}
+} else if (bs->drv->bdrv_discard) {
+return bs->drv->bdrv_discard(bs, sector_num, nb_sectors);
+} else {
+return 0;
+}
+}
+
+int bdrv_discard(BlockDriverState *bs, int64_t sector_num, int nb_sectors)
+{
+Coroutine *co;
+RwCo rwco = {
+.bs = bs,
+.sector_num = sector_num,
+.nb_sectors = nb_sectors,
+.ret = NOT_DONE,
+};
+
+if (qemu_in_coroutine()) {
+/* Fast-path if already in coroutine context */
+bdrv_discard_co_entry(&rwco);
+} else {
+co = qemu_coroutine_create(bdrv_discard_co_entry);
+qemu_coroutine_enter(co, &rwco);
+while (rwco.ret == NOT_DONE) {
+qemu_aio_wait();
+}
+}
+
+return rwco.ret;
+}
+
 /**/
 /* removable device support */
 
diff --git a/block.h b/block.h
index 65c5166..5a042c9 100644
--- a/block.h
+++ b/block.h
@@ -166,6 +166,9 @@ BlockDriverAIOCB *bdrv_aio_writev(BlockDriverState *bs, 
int64_t sector_num,
   BlockDriverCompletionFunc *cb, void *opaque);
 BlockDriverAIOCB *bdrv_aio_flush(BlockDriverState *bs,
  BlockDriverCompletionFunc *cb, void *opaque);
+BlockDriverAIOCB *bdrv_aio_discard(BlockDriverState *bs,
+   int64_t sector_num, int nb_sectors,
+   BlockDriverCompletionFunc *cb, void 
*opaque);
 void bdrv_aio_cancel(BlockDriverAIOCB *acb);
 
 typedef struct BlockRequest {
@@ -196,6 +199,7 @@ void bdrv_flush_all(void);
 void bdrv_close_all(void);
 
 int bdrv_discard(BlockDriverState *bs, int64_t sector_num, int nb_sectors);
+int bdrv_co_discard(BlockDriverState *bs, int64_t sector_num, int nb_sectors)

[Qemu-devel] [PATCH 02/19] add socket_set_block

2011-10-21 Thread Kevin Wolf
From: Paolo Bonzini 

Cc: MORITA Kazutaka 
Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 oslib-posix.c |7 +++
 oslib-win32.c |6 ++
 qemu_socket.h |1 +
 3 files changed, 14 insertions(+), 0 deletions(-)

diff --git a/oslib-posix.c b/oslib-posix.c
index a304fb0..dbc8ee8 100644
--- a/oslib-posix.c
+++ b/oslib-posix.c
@@ -103,6 +103,13 @@ void qemu_vfree(void *ptr)
 free(ptr);
 }
 
+void socket_set_block(int fd)
+{
+int f;
+f = fcntl(fd, F_GETFL);
+fcntl(fd, F_SETFL, f & ~O_NONBLOCK);
+}
+
 void socket_set_nonblock(int fd)
 {
 int f;
diff --git a/oslib-win32.c b/oslib-win32.c
index 5f0759f..5e3de7d 100644
--- a/oslib-win32.c
+++ b/oslib-win32.c
@@ -73,6 +73,12 @@ void qemu_vfree(void *ptr)
 VirtualFree(ptr, 0, MEM_RELEASE);
 }
 
+void socket_set_block(int fd)
+{
+unsigned long opt = 0;
+ioctlsocket(fd, FIONBIO, &opt);
+}
+
 void socket_set_nonblock(int fd)
 {
 unsigned long opt = 1;
diff --git a/qemu_socket.h b/qemu_socket.h
index 180e4db..9e32fac 100644
--- a/qemu_socket.h
+++ b/qemu_socket.h
@@ -35,6 +35,7 @@ int inet_aton(const char *cp, struct in_addr *ia);
 /* misc helpers */
 int qemu_socket(int domain, int type, int protocol);
 int qemu_accept(int s, struct sockaddr *addr, socklen_t *addrlen);
+void socket_set_block(int fd);
 void socket_set_nonblock(int fd);
 int send_all(int fd, const void *buf, int len1);
 
-- 
1.7.6.4




[Qemu-devel] [PATCH 10/19] qemu-img: Don't allow preallocation and compression at the same time

2011-10-21 Thread Kevin Wolf
Only qcow and qcow2 can do compression at all, and they require unallocated
clusters when writing the compressed data.

Signed-off-by: Kevin Wolf 
Reviewed-by: Stefan Hajnoczi 
---
 qemu-img.c |   11 +++
 1 files changed, 11 insertions(+), 0 deletions(-)

diff --git a/qemu-img.c b/qemu-img.c
index 6a39731..86127f0 100644
--- a/qemu-img.c
+++ b/qemu-img.c
@@ -824,6 +824,8 @@ static int img_convert(int argc, char **argv)
 if (compress) {
 QEMUOptionParameter *encryption =
 get_option_parameter(param, BLOCK_OPT_ENCRYPT);
+QEMUOptionParameter *preallocation =
+get_option_parameter(param, BLOCK_OPT_PREALLOC);
 
 if (!drv->bdrv_write_compressed) {
 error_report("Compression not supported for this file format");
@@ -837,6 +839,15 @@ static int img_convert(int argc, char **argv)
 ret = -1;
 goto out;
 }
+
+if (preallocation && preallocation->value.s
+&& strcmp(preallocation->value.s, "off"))
+{
+error_report("Compression and preallocation not supported at "
+ "the same time");
+ret = -1;
+goto out;
+}
 }
 
 /* Create the new image */
-- 
1.7.6.4




[Qemu-devel] [PATCH 07/19] block: drop redundant bdrv_flush implementation

2011-10-21 Thread Kevin Wolf
From: Stefan Hajnoczi 

Block drivers now only need to provide either of .bdrv_co_flush,
.bdrv_aio_flush() or for legacy drivers .bdrv_flush().  Remove
the redundant .bdrv_flush() implementations.

[Paolo Bonzini: change raw driver to bdrv_co_flush]

Signed-off-by: Stefan Hajnoczi 
Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 block/blkdebug.c  |6 --
 block/blkverify.c |9 -
 block/qcow.c  |6 --
 block/qcow2.c |   19 ---
 block/qed.c   |6 --
 block/raw-posix.c |   18 --
 block/raw.c   |   13 +++--
 7 files changed, 3 insertions(+), 74 deletions(-)

diff --git a/block/blkdebug.c b/block/blkdebug.c
index b3c5d42..9b88535 100644
--- a/block/blkdebug.c
+++ b/block/blkdebug.c
@@ -397,11 +397,6 @@ static void blkdebug_close(BlockDriverState *bs)
 }
 }
 
-static int blkdebug_flush(BlockDriverState *bs)
-{
-return bdrv_flush(bs->file);
-}
-
 static BlockDriverAIOCB *blkdebug_aio_flush(BlockDriverState *bs,
 BlockDriverCompletionFunc *cb, void *opaque)
 {
@@ -454,7 +449,6 @@ static BlockDriver bdrv_blkdebug = {
 
 .bdrv_file_open = blkdebug_open,
 .bdrv_close = blkdebug_close,
-.bdrv_flush = blkdebug_flush,
 
 .bdrv_aio_readv = blkdebug_aio_readv,
 .bdrv_aio_writev= blkdebug_aio_writev,
diff --git a/block/blkverify.c b/block/blkverify.c
index c7522b4..483f3b3 100644
--- a/block/blkverify.c
+++ b/block/blkverify.c
@@ -116,14 +116,6 @@ static void blkverify_close(BlockDriverState *bs)
 s->test_file = NULL;
 }
 
-static int blkverify_flush(BlockDriverState *bs)
-{
-BDRVBlkverifyState *s = bs->opaque;
-
-/* Only flush test file, the raw file is not important */
-return bdrv_flush(s->test_file);
-}
-
 static int64_t blkverify_getlength(BlockDriverState *bs)
 {
 BDRVBlkverifyState *s = bs->opaque;
@@ -368,7 +360,6 @@ static BlockDriver bdrv_blkverify = {
 
 .bdrv_file_open = blkverify_open,
 .bdrv_close = blkverify_close,
-.bdrv_flush = blkverify_flush,
 
 .bdrv_aio_readv = blkverify_aio_readv,
 .bdrv_aio_writev= blkverify_aio_writev,
diff --git a/block/qcow.c b/block/qcow.c
index eba5a04..f93e3eb 100644
--- a/block/qcow.c
+++ b/block/qcow.c
@@ -781,11 +781,6 @@ static int qcow_write_compressed(BlockDriverState *bs, 
int64_t sector_num,
 return 0;
 }
 
-static int qcow_flush(BlockDriverState *bs)
-{
-return bdrv_flush(bs->file);
-}
-
 static BlockDriverAIOCB *qcow_aio_flush(BlockDriverState *bs,
 BlockDriverCompletionFunc *cb, void *opaque)
 {
@@ -826,7 +821,6 @@ static BlockDriver bdrv_qcow = {
 .bdrv_open = qcow_open,
 .bdrv_close= qcow_close,
 .bdrv_create   = qcow_create,
-.bdrv_flush= qcow_flush,
 .bdrv_is_allocated = qcow_is_allocated,
 .bdrv_set_key  = qcow_set_key,
 .bdrv_make_empty   = qcow_make_empty,
diff --git a/block/qcow2.c b/block/qcow2.c
index 510ff68..4dc980c 100644
--- a/block/qcow2.c
+++ b/block/qcow2.c
@@ -1092,24 +1092,6 @@ static int qcow2_write_compressed(BlockDriverState *bs, 
int64_t sector_num,
 return 0;
 }
 
-static int qcow2_flush(BlockDriverState *bs)
-{
-BDRVQcowState *s = bs->opaque;
-int ret;
-
-ret = qcow2_cache_flush(bs, s->l2_table_cache);
-if (ret < 0) {
-return ret;
-}
-
-ret = qcow2_cache_flush(bs, s->refcount_block_cache);
-if (ret < 0) {
-return ret;
-}
-
-return bdrv_flush(bs->file);
-}
-
 static BlockDriverAIOCB *qcow2_aio_flush(BlockDriverState *bs,
  BlockDriverCompletionFunc *cb,
  void *opaque)
@@ -1242,7 +1224,6 @@ static BlockDriver bdrv_qcow2 = {
 .bdrv_open  = qcow2_open,
 .bdrv_close = qcow2_close,
 .bdrv_create= qcow2_create,
-.bdrv_flush = qcow2_flush,
 .bdrv_is_allocated  = qcow2_is_allocated,
 .bdrv_set_key   = qcow2_set_key,
 .bdrv_make_empty= qcow2_make_empty,
diff --git a/block/qed.c b/block/qed.c
index e87dc4d..2e06992 100644
--- a/block/qed.c
+++ b/block/qed.c
@@ -533,11 +533,6 @@ static void bdrv_qed_close(BlockDriverState *bs)
 qemu_vfree(s->l1_table);
 }
 
-static int bdrv_qed_flush(BlockDriverState *bs)
-{
-return bdrv_flush(bs->file);
-}
-
 static int qed_create(const char *filename, uint32_t cluster_size,
   uint64_t image_size, uint32_t table_size,
   const char *backing_file, const char *backing_fmt)
@@ -1479,7 +1474,6 @@ static BlockDriver bdrv_qed = {
 .bdrv_open= bdrv_qed_open,
 .bdrv_close   = bdrv_qed_close,
 .bdrv_create  = bdrv_qed_create,
-.bdrv_flush   = bdrv_qed_flush,
 .bdrv_is_allocated= bdrv_qed_is_allocated,
 .bdrv_make_empty  = bdrv_qed_make_empty,
 .bdrv_aio_readv   =

[Qemu-devel] [PATCH 04/19] fix memory leak in aio_write_f

2011-10-21 Thread Kevin Wolf
From: Alex Jia 

Haven't released memory of 'ctx' before return.

Signed-off-by: Alex Jia 
Signed-off-by: Kevin Wolf 
---
 qemu-io.c |1 +
 1 files changed, 1 insertions(+), 0 deletions(-)

diff --git a/qemu-io.c b/qemu-io.c
index e91af37..c45a413 100644
--- a/qemu-io.c
+++ b/qemu-io.c
@@ -1248,6 +1248,7 @@ static int aio_write_f(int argc, char **argv)
 case 'P':
 pattern = parse_pattern(optarg);
 if (pattern < 0) {
+free(ctx);
 return 0;
 }
 break;
-- 
1.7.6.4




[Qemu-devel] [PATCH 05/19] xen_disk: Always set feature-barrier = 1

2011-10-21 Thread Kevin Wolf
The synchronous .bdrv_flush callback doesn't exist any more and a device really
shouldn't poke into the block layer internals anyway. All drivers are supposed
to have a correctly working bdrv_flush, so let's just hard-code this.

Signed-off-by: Kevin Wolf 
---
 hw/xen_disk.c |5 ++---
 1 files changed, 2 insertions(+), 3 deletions(-)

diff --git a/hw/xen_disk.c b/hw/xen_disk.c
index 8a9fac4..286bbac 100644
--- a/hw/xen_disk.c
+++ b/hw/xen_disk.c
@@ -620,7 +620,7 @@ static void blk_alloc(struct XenDevice *xendev)
 static int blk_init(struct XenDevice *xendev)
 {
 struct XenBlkDev *blkdev = container_of(xendev, struct XenBlkDev, xendev);
-int index, qflags, have_barriers, info = 0;
+int index, qflags, info = 0;
 
 /* read xenstore entries */
 if (blkdev->params == NULL) {
@@ -706,7 +706,6 @@ static int blk_init(struct XenDevice *xendev)
   blkdev->bs->drv ? blkdev->bs->drv->format_name : "-");
 blkdev->file_size = 0;
 }
-have_barriers = blkdev->bs->drv && blkdev->bs->drv->bdrv_flush ? 1 : 0;
 
 xen_be_printf(xendev, 1, "type \"%s\", fileproto \"%s\", filename \"%s\","
   " size %" PRId64 " (%" PRId64 " MB)\n",
@@ -714,7 +713,7 @@ static int blk_init(struct XenDevice *xendev)
   blkdev->file_size, blkdev->file_size >> 20);
 
 /* fill info */
-xenstore_write_be_int(&blkdev->xendev, "feature-barrier", have_barriers);
+xenstore_write_be_int(&blkdev->xendev, "feature-barrier", 1);
 xenstore_write_be_int(&blkdev->xendev, "info",info);
 xenstore_write_be_int(&blkdev->xendev, "sector-size", 
blkdev->file_blk);
 xenstore_write_be_int(&blkdev->xendev, "sectors",
-- 
1.7.6.4




[Qemu-devel] [PATCH 11/19] qcow2: Fix bdrv_write_compressed error handling

2011-10-21 Thread Kevin Wolf
If during allocation of compressed clusters the cluster was already allocated
uncompressed, fail and properly release the l2_table (the latter avoids a
failed assertion).

While at it, make it return some real error numbers instead of -1.

Signed-off-by: Kevin Wolf 
Reviewed-by: Dong Xu Wang 
---
 block/qcow2-cluster.c |6 --
 block/qcow2.c |   29 ++---
 2 files changed, 22 insertions(+), 13 deletions(-)

diff --git a/block/qcow2-cluster.c b/block/qcow2-cluster.c
index 2f76311..f4e049f 100644
--- a/block/qcow2-cluster.c
+++ b/block/qcow2-cluster.c
@@ -568,8 +568,10 @@ uint64_t 
qcow2_alloc_compressed_cluster_offset(BlockDriverState *bs,
 }
 
 cluster_offset = be64_to_cpu(l2_table[l2_index]);
-if (cluster_offset & QCOW_OFLAG_COPIED)
-return cluster_offset & ~QCOW_OFLAG_COPIED;
+if (cluster_offset & QCOW_OFLAG_COPIED) {
+qcow2_cache_put(bs, s->l2_table_cache, (void**) &l2_table);
+return 0;
+}
 
 if (cluster_offset)
 qcow2_free_any_clusters(bs, cluster_offset, 1);
diff --git a/block/qcow2.c b/block/qcow2.c
index 4dc980c..91f4f04 100644
--- a/block/qcow2.c
+++ b/block/qcow2.c
@@ -1053,8 +1053,8 @@ static int qcow2_write_compressed(BlockDriverState *bs, 
int64_t sector_num,
Z_DEFLATED, -12,
9, Z_DEFAULT_STRATEGY);
 if (ret != 0) {
-g_free(out_buf);
-return -1;
+ret = -EINVAL;
+goto fail;
 }
 
 strm.avail_in = s->cluster_size;
@@ -1064,9 +1064,9 @@ static int qcow2_write_compressed(BlockDriverState *bs, 
int64_t sector_num,
 
 ret = deflate(&strm, Z_FINISH);
 if (ret != Z_STREAM_END && ret != Z_OK) {
-g_free(out_buf);
 deflateEnd(&strm);
-return -1;
+ret = -EINVAL;
+goto fail;
 }
 out_len = strm.next_out - out_buf;
 
@@ -1074,22 +1074,29 @@ static int qcow2_write_compressed(BlockDriverState *bs, 
int64_t sector_num,
 
 if (ret != Z_STREAM_END || out_len >= s->cluster_size) {
 /* could not compress: write normal cluster */
-bdrv_write(bs, sector_num, buf, s->cluster_sectors);
+ret = bdrv_write(bs, sector_num, buf, s->cluster_sectors);
+if (ret < 0) {
+goto fail;
+}
 } else {
 cluster_offset = qcow2_alloc_compressed_cluster_offset(bs,
 sector_num << 9, out_len);
-if (!cluster_offset)
-return -1;
+if (!cluster_offset) {
+ret = -EIO;
+goto fail;
+}
 cluster_offset &= s->cluster_offset_mask;
 BLKDBG_EVENT(bs->file, BLKDBG_WRITE_COMPRESSED);
-if (bdrv_pwrite(bs->file, cluster_offset, out_buf, out_len) != 
out_len) {
-g_free(out_buf);
-return -1;
+ret = bdrv_pwrite(bs->file, cluster_offset, out_buf, out_len);
+if (ret < 0) {
+goto fail;
 }
 }
 
+ret = 0;
+fail:
 g_free(out_buf);
-return 0;
+return ret;
 }
 
 static BlockDriverAIOCB *qcow2_aio_flush(BlockDriverState *bs,
-- 
1.7.6.4




[Qemu-devel] [PATCH v3 07/13] qemu-timer: use atexit for quit_timers

2011-10-21 Thread Paolo Bonzini
Signed-off-by: Paolo Bonzini 
---
 qemu-timer.c |   15 ---
 qemu-timer.h |1 -
 vl.c |1 -
 3 files changed, 8 insertions(+), 9 deletions(-)

diff --git a/qemu-timer.c b/qemu-timer.c
index d8507e3..7fa81e1 100644
--- a/qemu-timer.c
+++ b/qemu-timer.c
@@ -840,6 +840,13 @@ static void alarm_timer_on_change_state_rearm(void 
*opaque, int running,
 qemu_rearm_alarm_timer((struct qemu_alarm_timer *) opaque);
 }
 
+static void quit_timers(void)
+{
+struct qemu_alarm_timer *t = alarm_timer;
+alarm_timer = NULL;
+t->stop(t);
+}
+
 int init_timer_alarm(void)
 {
 struct qemu_alarm_timer *t = NULL;
@@ -859,6 +866,7 @@ int init_timer_alarm(void)
 }
 
 /* first event is at time 0 */
+atexit(quit_timers);
 t->pending = 1;
 alarm_timer = t;
 qemu_add_vm_change_state_handler(alarm_timer_on_change_state_rearm, t);
@@ -869,13 +877,6 @@ fail:
 return err;
 }
 
-void quit_timers(void)
-{
-struct qemu_alarm_timer *t = alarm_timer;
-alarm_timer = NULL;
-t->stop(t);
-}
-
 int qemu_calculate_timeout(void)
 {
 return 1000;
diff --git a/qemu-timer.h b/qemu-timer.h
index ce576b9..b4ea201 100644
--- a/qemu-timer.h
+++ b/qemu-timer.h
@@ -62,7 +62,6 @@ void configure_alarms(char const *opt);
 int qemu_calculate_timeout(void);
 void init_clocks(void);
 int init_timer_alarm(void);
-void quit_timers(void);
 
 int64_t cpu_get_ticks(void);
 void cpu_enable_ticks(void);
diff --git a/vl.c b/vl.c
index 66f70fb..6bd7e71 100644
--- a/vl.c
+++ b/vl.c
@@ -3565,7 +3565,6 @@ int main(int argc, char **argv, char **envp)
 os_setup_post();
 
 main_loop();
-quit_timers();
 net_cleanup();
 res_free();
 
-- 
1.7.6





[Qemu-devel] [PATCH v3 08/13] qemu-timer: move more stuff out of qemu-timer.c

2011-10-21 Thread Paolo Bonzini
Signed-off-by: Paolo Bonzini 
---
 qemu-timer.c |   35 ---
 qemu-timer.h |2 ++
 savevm.c |   25 +
 vl.c |1 +
 4 files changed, 32 insertions(+), 31 deletions(-)

diff --git a/qemu-timer.c b/qemu-timer.c
index 7fa81e1..58926dd 100644
--- a/qemu-timer.c
+++ b/qemu-timer.c
@@ -266,11 +266,8 @@ static QEMUClock *qemu_new_clock(int type)
 clock = g_malloc0(sizeof(QEMUClock));
 clock->type = type;
 clock->enabled = 1;
+clock->last = INT64_MIN;
 notifier_list_init(&clock->reset_notifiers);
-/* required to detect & report backward jumps */
-if (type == QEMU_CLOCK_HOST) {
-clock->last = get_clock_realtime();
-}
 return clock;
 }
 
@@ -344,7 +341,7 @@ void qemu_del_timer(QEMUTimer *ts)
 
 /* modify the current timer so that it will be fired when current_time
>= expire_time. The corresponding callback will be called. */
-static void qemu_mod_timer_ns(QEMUTimer *ts, int64_t expire_time)
+void qemu_mod_timer_ns(QEMUTimer *ts, int64_t expire_time)
 {
 QEMUTimer **pt, *t;
 
@@ -378,8 +375,6 @@ static void qemu_mod_timer_ns(QEMUTimer *ts, int64_t 
expire_time)
 }
 }
 
-/* modify the current timer so that it will be fired when current_time
-   >= expire_time. The corresponding callback will be called. */
 void qemu_mod_timer(QEMUTimer *ts, int64_t expire_time)
 {
 qemu_mod_timer_ns(ts, expire_time * ts->scale);
@@ -464,33 +459,11 @@ void init_clocks(void)
 rt_clock = qemu_new_clock(QEMU_CLOCK_REALTIME);
 vm_clock = qemu_new_clock(QEMU_CLOCK_VIRTUAL);
 host_clock = qemu_new_clock(QEMU_CLOCK_HOST);
-
-rtc_clock = host_clock;
 }
 
-/* save a timer */
-void qemu_put_timer(QEMUFile *f, QEMUTimer *ts)
+uint64_t qemu_timer_expire_time_ns(QEMUTimer *ts)
 {
-uint64_t expire_time;
-
-if (qemu_timer_pending(ts)) {
-expire_time = ts->expire_time;
-} else {
-expire_time = -1;
-}
-qemu_put_be64(f, expire_time);
-}
-
-void qemu_get_timer(QEMUFile *f, QEMUTimer *ts)
-{
-uint64_t expire_time;
-
-expire_time = qemu_get_be64(f);
-if (expire_time != -1) {
-qemu_mod_timer_ns(ts, expire_time);
-} else {
-qemu_del_timer(ts);
-}
+return qemu_timer_pending(ts) ? ts->expire_time : -1;
 }
 
 void qemu_run_all_timers(void)
diff --git a/qemu-timer.h b/qemu-timer.h
index b4ea201..9f4ffed 100644
--- a/qemu-timer.h
+++ b/qemu-timer.h
@@ -52,9 +52,11 @@ QEMUTimer *qemu_new_timer(QEMUClock *clock, int scale,
   QEMUTimerCB *cb, void *opaque);
 void qemu_free_timer(QEMUTimer *ts);
 void qemu_del_timer(QEMUTimer *ts);
+void qemu_mod_timer_ns(QEMUTimer *ts, int64_t expire_time);
 void qemu_mod_timer(QEMUTimer *ts, int64_t expire_time);
 int qemu_timer_pending(QEMUTimer *ts);
 int qemu_timer_expired(QEMUTimer *timer_head, int64_t current_time);
+uint64_t qemu_timer_expire_time_ns(QEMUTimer *ts);
 
 void qemu_run_all_timers(void);
 int qemu_alarm_pending(void);
diff --git a/savevm.c b/savevm.c
index cf79a56..f01838f 100644
--- a/savevm.c
+++ b/savevm.c
@@ -81,6 +81,7 @@
 #include "migration.h"
 #include "qemu_socket.h"
 #include "qemu-queue.h"
+#include "qemu-timer.h"
 #include "cpus.h"
 
 #define SELF_ANNOUNCE_ROUNDS 5
@@ -712,6 +713,30 @@ uint64_t qemu_get_be64(QEMUFile *f)
 return v;
 }
 
+
+/* timer */
+
+void qemu_put_timer(QEMUFile *f, QEMUTimer *ts)
+{
+uint64_t expire_time;
+
+expire_time = qemu_timer_expire_time_ns(ts);
+qemu_put_be64(f, expire_time);
+}
+
+void qemu_get_timer(QEMUFile *f, QEMUTimer *ts)
+{
+uint64_t expire_time;
+
+expire_time = qemu_get_be64(f);
+if (expire_time != -1) {
+qemu_mod_timer_ns(ts, expire_time);
+} else {
+qemu_del_timer(ts);
+}
+}
+
+
 /* bool */
 
 static int get_bool(QEMUFile *f, void *pv, size_t size)
diff --git a/vl.c b/vl.c
index 6bd7e71..cf25d65 100644
--- a/vl.c
+++ b/vl.c
@@ -2311,6 +2311,7 @@ int main(int argc, char **argv, char **envp)
 runstate_init();
 
 init_clocks();
+rtc_clock = host_clock;
 
 qemu_cache_utils_init(envp);
 
-- 
1.7.6





[Qemu-devel] [PATCH v3 03/13] qemu-timer: move common code to qemu_rearm_alarm_timer

2011-10-21 Thread Paolo Bonzini
Reviewed-by: Anthony Liguori 
Signed-off-by: Paolo Bonzini 
---
 qemu-timer.c |  129 --
 1 files changed, 53 insertions(+), 76 deletions(-)

diff --git a/qemu-timer.c b/qemu-timer.c
index acf7a15..e2551f3 100644
--- a/qemu-timer.c
+++ b/qemu-timer.c
@@ -153,7 +153,7 @@ struct qemu_alarm_timer {
 char const *name;
 int (*start)(struct qemu_alarm_timer *t);
 void (*stop)(struct qemu_alarm_timer *t);
-void (*rearm)(struct qemu_alarm_timer *t);
+void (*rearm)(struct qemu_alarm_timer *t, int64_t nearest_delta_ns);
 #if defined(__linux__)
 int fd;
 timer_t timer;
@@ -181,12 +181,46 @@ static inline int alarm_has_dynticks(struct 
qemu_alarm_timer *t)
 return !!t->rearm;
 }
 
+static int64_t qemu_next_alarm_deadline(void)
+{
+int64_t delta;
+int64_t rtdelta;
+
+if (!use_icount && vm_clock->active_timers) {
+delta = vm_clock->active_timers->expire_time -
+ qemu_get_clock_ns(vm_clock);
+} else {
+delta = INT32_MAX;
+}
+if (host_clock->active_timers) {
+int64_t hdelta = host_clock->active_timers->expire_time -
+ qemu_get_clock_ns(host_clock);
+if (hdelta < delta) {
+delta = hdelta;
+}
+}
+if (rt_clock->active_timers) {
+rtdelta = (rt_clock->active_timers->expire_time -
+ qemu_get_clock_ns(rt_clock));
+if (rtdelta < delta) {
+delta = rtdelta;
+}
+}
+
+return delta;
+}
+
 static void qemu_rearm_alarm_timer(struct qemu_alarm_timer *t)
 {
-if (!alarm_has_dynticks(t))
+int64_t nearest_delta_ns;
+assert(alarm_has_dynticks(t));
+if (!rt_clock->active_timers &&
+!vm_clock->active_timers &&
+!host_clock->active_timers) {
 return;
-
-t->rearm(t);
+}
+nearest_delta_ns = qemu_next_alarm_deadline();
+t->rearm(t, nearest_delta_ns);
 }
 
 /* TODO: MIN_TIMER_REARM_NS should be optimized */
@@ -196,23 +230,23 @@ static void qemu_rearm_alarm_timer(struct 
qemu_alarm_timer *t)
 
 static int mm_start_timer(struct qemu_alarm_timer *t);
 static void mm_stop_timer(struct qemu_alarm_timer *t);
-static void mm_rearm_timer(struct qemu_alarm_timer *t);
+static void mm_rearm_timer(struct qemu_alarm_timer *t, int64_t delta);
 
 static int win32_start_timer(struct qemu_alarm_timer *t);
 static void win32_stop_timer(struct qemu_alarm_timer *t);
-static void win32_rearm_timer(struct qemu_alarm_timer *t);
+static void win32_rearm_timer(struct qemu_alarm_timer *t, int64_t delta);
 
 #else
 
 static int unix_start_timer(struct qemu_alarm_timer *t);
 static void unix_stop_timer(struct qemu_alarm_timer *t);
-static void unix_rearm_timer(struct qemu_alarm_timer *t);
+static void unix_rearm_timer(struct qemu_alarm_timer *t, int64_t delta);
 
 #ifdef __linux__
 
 static int dynticks_start_timer(struct qemu_alarm_timer *t);
 static void dynticks_stop_timer(struct qemu_alarm_timer *t);
-static void dynticks_rearm_timer(struct qemu_alarm_timer *t);
+static void dynticks_rearm_timer(struct qemu_alarm_timer *t, int64_t delta);
 
 #endif /* __linux__ */
 
@@ -715,8 +749,6 @@ void qemu_run_all_timers(void)
 qemu_run_timers(host_clock);
 }
 
-static int64_t qemu_next_alarm_deadline(void);
-
 #ifdef _WIN32
 static void CALLBACK host_alarm_handler(PVOID lpParam, BOOLEAN unused)
 #else
@@ -781,33 +813,6 @@ int64_t qemu_next_icount_deadline(void)
 return delta;
 }
 
-static int64_t qemu_next_alarm_deadline(void)
-{
-int64_t delta;
-int64_t rtdelta;
-
-if (!use_icount && vm_clock->active_timers) {
-delta = vm_clock->active_timers->expire_time -
- qemu_get_clock_ns(vm_clock);
-} else {
-delta = INT32_MAX;
-}
-if (host_clock->active_timers) {
-int64_t hdelta = host_clock->active_timers->expire_time -
- qemu_get_clock_ns(host_clock);
-if (hdelta < delta)
-delta = hdelta;
-}
-if (rt_clock->active_timers) {
-rtdelta = (rt_clock->active_timers->expire_time -
- qemu_get_clock_ns(rt_clock));
-if (rtdelta < delta)
-delta = rtdelta;
-}
-
-return delta;
-}
-
 #if defined(__linux__)
 
 #include "compatfd.h"
@@ -860,20 +865,13 @@ static void dynticks_stop_timer(struct qemu_alarm_timer 
*t)
 timer_delete(host_timer);
 }
 
-static void dynticks_rearm_timer(struct qemu_alarm_timer *t)
+static void dynticks_rearm_timer(struct qemu_alarm_timer *t,
+ int64_t nearest_delta_ns)
 {
 timer_t host_timer = t->timer;
 struct itimerspec timeout;
-int64_t nearest_delta_ns = INT64_MAX;
 int64_t current_ns;
 
-assert(alarm_has_dynticks(t));
-if (!rt_clock->active_timers &&
-!vm_clock->active_timers &&
-!host_clock->active_timers)
-return;
-
-nearest_delta_ns = qemu_next_alarm_deadline();
 if (nearest_delta_ns < MIN_TIMER_

[Qemu-devel] [PATCH v3 10/13] main-loop: create main-loop.h

2011-10-21 Thread Paolo Bonzini
Signed-off-by: Paolo Bonzini 
---
 async.c   |1 +
 cpus.c|7 +-
 cpus.h|1 -
 iohandler.c   |1 +
 main-loop.h   |  327 +
 qemu-char.h   |   12 +--
 qemu-common.h |   30 -
 qemu-coroutine-lock.c |1 +
 qemu-os-win32.h   |   15 +--
 qemu-timer.h  |1 +
 sysemu.h  |3 +-
 vl.c  |1 +
 12 files changed, 336 insertions(+), 64 deletions(-)
 create mode 100644 main-loop.h

diff --git a/async.c b/async.c
index ca13962..332d511 100644
--- a/async.c
+++ b/async.c
@@ -24,6 +24,7 @@
 
 #include "qemu-common.h"
 #include "qemu-aio.h"
+#include "main-loop.h"
 
 /* Anchor of the list of Bottom Halves belonging to the context */
 static struct QEMUBH *first_bh;
diff --git a/cpus.c b/cpus.c
index 1328baa..64237b4 100644
--- a/cpus.c
+++ b/cpus.c
@@ -33,17 +33,12 @@
 
 #include "qemu-thread.h"
 #include "cpus.h"
+#include "main-loop.h"
 
 #ifndef _WIN32
 #include "compatfd.h"
 #endif
 
-#ifdef SIGRTMIN
-#define SIG_IPI (SIGRTMIN+4)
-#else
-#define SIG_IPI SIGUSR1
-#endif
-
 #ifdef CONFIG_LINUX
 
 #include 
diff --git a/cpus.h b/cpus.h
index 5885885..4ccf986 100644
--- a/cpus.h
+++ b/cpus.h
@@ -2,7 +2,6 @@
 #define QEMU_CPUS_H
 
 /* cpus.c */
-int qemu_init_main_loop(void);
 void qemu_main_loop_start(void);
 void resume_all_vcpus(void);
 void pause_all_vcpus(void);
diff --git a/iohandler.c b/iohandler.c
index 4cc1c5a..687dc56 100644
--- a/iohandler.c
+++ b/iohandler.c
@@ -26,6 +26,7 @@
 #include "qemu-common.h"
 #include "qemu-char.h"
 #include "qemu-queue.h"
+#include "main-loop.h"
 
 #ifndef _WIN32
 #include 
diff --git a/main-loop.h b/main-loop.h
new file mode 100644
index 000..a73b9c0
--- /dev/null
+++ b/main-loop.h
@@ -0,0 +1,327 @@
+/*
+ * QEMU System Emulator
+ *
+ * Copyright (c) 2003-2008 Fabrice Bellard
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to 
deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 
FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+
+#ifndef QEMU_MAIN_LOOP_H
+#define QEMU_MAIN_LOOP_H 1
+
+#ifdef SIGRTMIN
+#define SIG_IPI (SIGRTMIN+4)
+#else
+#define SIG_IPI SIGUSR1
+#endif
+
+/**
+ * qemu_init_main_loop: Set up the process so that it can run the main loop.
+ *
+ * This includes setting up signal handlers.  It should be called before
+ * any other threads are created.  In addition, threads other than the
+ * main one should block signals that are trapped by the main loop.
+ * For simplicity, you can consider these signals to be safe: SIGUSR1,
+ * SIGUSR2, thread signals (SIGFPE, SIGILL, SIGSEGV, SIGBUS) and real-time
+ * signals if available.  Remember that Windows in practice does not have
+ * signals, though.
+ */
+int qemu_init_main_loop(void);
+
+/**
+ * main_loop_wait: Run one iteration of the main loop.
+ *
+ * If @nonblocking is true, poll for events, otherwise suspend until
+ * one actually occurs.  The main loop usually consists of a loop that
+ * repeatedly calls main_loop_wait(false).
+ *
+ * Main loop services include file descriptor callbacks, bottom halves
+ * and timers (defined in qemu-timer.h).  Bottom halves are similar to timers
+ * that execute immediately, but have a lower overhead and scheduling them
+ * is wait-free, thread-safe and signal-safe.
+ *
+ * It is sometimes useful to put a whole program in a coroutine.  In this
+ * case, the coroutine actually should be started from within the main loop,
+ * so that the main loop can run whenever the coroutine yields.  To do this,
+ * you can use a bottom half to enter the coroutine as soon as the main loop
+ * starts:
+ *
+ * void enter_co_bh(void *opaque) {
+ * QEMUCoroutine *co = opaque;
+ * qemu_coroutine_enter(co, NULL);
+ * }
+ *
+ * ...
+ * QEMUCoroutine *co = qemu_coroutine_create(coroutine_entry);
+ * QEMUBH *start_bh = qemu_bh_new(enter_co_bh, co);
+ * qemu_bh_schedule(start_bh);
+ * while (...) {
+ * main_loop_wait(false);
+ * }
+ *
+ * 

[Qemu-devel] [PATCH 16/19] block: take lock around bdrv_read implementations

2011-10-21 Thread Kevin Wolf
From: Paolo Bonzini 

This does the first part of the conversion to coroutines, by
wrapping bdrv_read implementations to take the mutex.

Drivers that implement bdrv_read rather than bdrv_co_readv can
then benefit from asynchronous operation (at least if the underlying
protocol supports it, which is not the case for raw-win32), even
though they still operate with a bounce buffer.

raw-win32 does not need the lock, because it cannot yield.
nbd also doesn't probably, but better be safe.

Signed-off-by: Paolo Bonzini 
Signed-off-by: Kevin Wolf 
---
 block/bochs.c |   13 -
 block/cloop.c |   13 -
 block/cow.c   |   13 -
 block/dmg.c   |   13 -
 block/nbd.c   |   13 -
 block/parallels.c |   13 -
 block/vmdk.c  |   13 -
 block/vpc.c   |   13 -
 block/vvfat.c |   13 -
 9 files changed, 108 insertions(+), 9 deletions(-)

diff --git a/block/bochs.c b/block/bochs.c
index b0f8072..ab7944d 100644
--- a/block/bochs.c
+++ b/block/bochs.c
@@ -209,6 +209,17 @@ static int bochs_read(BlockDriverState *bs, int64_t 
sector_num,
 return 0;
 }
 
+static coroutine_fn int bochs_co_read(BlockDriverState *bs, int64_t sector_num,
+  uint8_t *buf, int nb_sectors)
+{
+int ret;
+BDRVBochsState *s = bs->opaque;
+qemu_co_mutex_lock(&s->lock);
+ret = bochs_read(bs, sector_num, buf, nb_sectors);
+qemu_co_mutex_unlock(&s->lock);
+return ret;
+}
+
 static void bochs_close(BlockDriverState *bs)
 {
 BDRVBochsState *s = bs->opaque;
@@ -220,7 +231,7 @@ static BlockDriver bdrv_bochs = {
 .instance_size = sizeof(BDRVBochsState),
 .bdrv_probe= bochs_probe,
 .bdrv_open = bochs_open,
-.bdrv_read = bochs_read,
+.bdrv_read  = bochs_co_read,
 .bdrv_close= bochs_close,
 };
 
diff --git a/block/cloop.c b/block/cloop.c
index a91f372..775f8a9 100644
--- a/block/cloop.c
+++ b/block/cloop.c
@@ -146,6 +146,17 @@ static int cloop_read(BlockDriverState *bs, int64_t 
sector_num,
 return 0;
 }
 
+static coroutine_fn int cloop_co_read(BlockDriverState *bs, int64_t sector_num,
+  uint8_t *buf, int nb_sectors)
+{
+int ret;
+BDRVCloopState *s = bs->opaque;
+qemu_co_mutex_lock(&s->lock);
+ret = cloop_read(bs, sector_num, buf, nb_sectors);
+qemu_co_mutex_unlock(&s->lock);
+return ret;
+}
+
 static void cloop_close(BlockDriverState *bs)
 {
 BDRVCloopState *s = bs->opaque;
@@ -161,7 +172,7 @@ static BlockDriver bdrv_cloop = {
 .instance_size = sizeof(BDRVCloopState),
 .bdrv_probe= cloop_probe,
 .bdrv_open = cloop_open,
-.bdrv_read = cloop_read,
+.bdrv_read  = cloop_co_read,
 .bdrv_close= cloop_close,
 };
 
diff --git a/block/cow.c b/block/cow.c
index 2f426e7..a5fcd20 100644
--- a/block/cow.c
+++ b/block/cow.c
@@ -201,6 +201,17 @@ static int cow_read(BlockDriverState *bs, int64_t 
sector_num,
 return 0;
 }
 
+static coroutine_fn int cow_co_read(BlockDriverState *bs, int64_t sector_num,
+uint8_t *buf, int nb_sectors)
+{
+int ret;
+BDRVCowState *s = bs->opaque;
+qemu_co_mutex_lock(&s->lock);
+ret = cow_read(bs, sector_num, buf, nb_sectors);
+qemu_co_mutex_unlock(&s->lock);
+return ret;
+}
+
 static int cow_write(BlockDriverState *bs, int64_t sector_num,
  const uint8_t *buf, int nb_sectors)
 {
@@ -308,7 +319,7 @@ static BlockDriver bdrv_cow = {
 .instance_size = sizeof(BDRVCowState),
 .bdrv_probe= cow_probe,
 .bdrv_open = cow_open,
-.bdrv_read = cow_read,
+.bdrv_read  = cow_co_read,
 .bdrv_write= cow_write,
 .bdrv_close= cow_close,
 .bdrv_create   = cow_create,
diff --git a/block/dmg.c b/block/dmg.c
index 111aeae..37902a4 100644
--- a/block/dmg.c
+++ b/block/dmg.c
@@ -282,6 +282,17 @@ static int dmg_read(BlockDriverState *bs, int64_t 
sector_num,
 return 0;
 }
 
+static coroutine_fn int dmg_co_read(BlockDriverState *bs, int64_t sector_num,
+uint8_t *buf, int nb_sectors)
+{
+int ret;
+BDRVDMGState *s = bs->opaque;
+qemu_co_mutex_lock(&s->lock);
+ret = dmg_read(bs, sector_num, buf, nb_sectors);
+qemu_co_mutex_unlock(&s->lock);
+return ret;
+}
+
 static void dmg_close(BlockDriverState *bs)
 {
 BDRVDMGState *s = bs->opaque;
@@ -302,7 +313,7 @@ static BlockDriver bdrv_dmg = {
 .instance_size = sizeof(BDRVDMGState),
 .bdrv_probe= dmg_probe,
 .bdrv_open = dmg_open,
-.bdrv_read = dmg_read,
+.bdrv_read  = dmg_co_read,
 .bdrv_close= dmg_close,
 };
 
diff --git a/block/nbd.c b/block/nbd.c
index 14ab225..6b22a

[Qemu-devel] [PATCH v3 02/13] qemu-timer: remove active_timers array

2011-10-21 Thread Paolo Bonzini
Embed the list in the QEMUClock instead.

Reviewed-by: Anthony Liguori 
Signed-off-by: Paolo Bonzini 
---
 qemu-timer.c |   59 +++--
 1 files changed, 28 insertions(+), 31 deletions(-)

diff --git a/qemu-timer.c b/qemu-timer.c
index ad1fc8b..acf7a15 100644
--- a/qemu-timer.c
+++ b/qemu-timer.c
@@ -134,6 +134,7 @@ struct QEMUClock {
 int enabled;
 
 QEMUTimer *warp_timer;
+QEMUTimer *active_timers;
 
 NotifierList reset_notifiers;
 int64_t last;
@@ -352,14 +353,10 @@ next:
 }
 }
 
-#define QEMU_NUM_CLOCKS 3
-
 QEMUClock *rt_clock;
 QEMUClock *vm_clock;
 QEMUClock *host_clock;
 
-static QEMUTimer *active_timers[QEMU_NUM_CLOCKS];
-
 static QEMUClock *qemu_new_clock(int type)
 {
 QEMUClock *clock;
@@ -403,7 +400,7 @@ static void icount_warp_rt(void *opaque)
 int64_t delta = cur_time - cur_icount;
 qemu_icount_bias += MIN(warp_delta, delta);
 }
-if (qemu_timer_expired(active_timers[QEMU_CLOCK_VIRTUAL],
+if (qemu_timer_expired(vm_clock->active_timers,
qemu_get_clock_ns(vm_clock))) {
 qemu_notify_event();
 }
@@ -434,7 +431,7 @@ void qemu_clock_warp(QEMUClock *clock)
  * the earliest vm_clock timer.
  */
 icount_warp_rt(NULL);
-if (!all_cpu_threads_idle() || !active_timers[clock->type]) {
+if (!all_cpu_threads_idle() || !clock->active_timers) {
 qemu_del_timer(clock->warp_timer);
 return;
 }
@@ -489,7 +486,7 @@ void qemu_del_timer(QEMUTimer *ts)
 
 /* NOTE: this code must be signal safe because
qemu_timer_expired() can be called from a signal. */
-pt = &active_timers[ts->clock->type];
+pt = &ts->clock->active_timers;
 for(;;) {
 t = *pt;
 if (!t)
@@ -513,7 +510,7 @@ static void qemu_mod_timer_ns(QEMUTimer *ts, int64_t 
expire_time)
 /* add the timer in the sorted list */
 /* NOTE: this code must be signal safe because
qemu_timer_expired() can be called from a signal. */
-pt = &active_timers[ts->clock->type];
+pt = &ts->clock->active_timers;
 for(;;) {
 t = *pt;
 if (!qemu_timer_expired_ns(t, expire_time)) {
@@ -526,7 +523,7 @@ static void qemu_mod_timer_ns(QEMUTimer *ts, int64_t 
expire_time)
 *pt = ts;
 
 /* Rearm if necessary  */
-if (pt == &active_timers[ts->clock->type]) {
+if (pt == &ts->clock->active_timers) {
 if (!alarm_timer->pending) {
 qemu_rearm_alarm_timer(alarm_timer);
 }
@@ -548,7 +545,7 @@ void qemu_mod_timer(QEMUTimer *ts, int64_t expire_time)
 int qemu_timer_pending(QEMUTimer *ts)
 {
 QEMUTimer *t;
-for(t = active_timers[ts->clock->type]; t != NULL; t = t->next) {
+for (t = ts->clock->active_timers; t != NULL; t = t->next) {
 if (t == ts)
 return 1;
 }
@@ -569,7 +566,7 @@ static void qemu_run_timers(QEMUClock *clock)
 return;
 
 current_time = qemu_get_clock_ns(clock);
-ptimer_head = &active_timers[clock->type];
+ptimer_head = &clock->active_timers;
 for(;;) {
 ts = *ptimer_head;
 if (!qemu_timer_expired_ns(ts, current_time)) {
@@ -773,8 +770,8 @@ int64_t qemu_next_icount_deadline(void)
 int64_t delta = INT32_MAX;
 
 assert(use_icount);
-if (active_timers[QEMU_CLOCK_VIRTUAL]) {
-delta = active_timers[QEMU_CLOCK_VIRTUAL]->expire_time -
+if (vm_clock->active_timers) {
+delta = vm_clock->active_timers->expire_time -
  qemu_get_clock_ns(vm_clock);
 }
 
@@ -789,20 +786,20 @@ static int64_t qemu_next_alarm_deadline(void)
 int64_t delta;
 int64_t rtdelta;
 
-if (!use_icount && active_timers[QEMU_CLOCK_VIRTUAL]) {
-delta = active_timers[QEMU_CLOCK_VIRTUAL]->expire_time -
+if (!use_icount && vm_clock->active_timers) {
+delta = vm_clock->active_timers->expire_time -
  qemu_get_clock_ns(vm_clock);
 } else {
 delta = INT32_MAX;
 }
-if (active_timers[QEMU_CLOCK_HOST]) {
-int64_t hdelta = active_timers[QEMU_CLOCK_HOST]->expire_time -
+if (host_clock->active_timers) {
+int64_t hdelta = host_clock->active_timers->expire_time -
  qemu_get_clock_ns(host_clock);
 if (hdelta < delta)
 delta = hdelta;
 }
-if (active_timers[QEMU_CLOCK_REALTIME]) {
-rtdelta = (active_timers[QEMU_CLOCK_REALTIME]->expire_time -
+if (rt_clock->active_timers) {
+rtdelta = (rt_clock->active_timers->expire_time -
  qemu_get_clock_ns(rt_clock));
 if (rtdelta < delta)
 delta = rtdelta;
@@ -871,9 +868,9 @@ static void dynticks_rearm_timer(struct qemu_alarm_timer *t)
 int64_t current_ns;
 
 assert(alarm_has_dynticks(t));
-if (!active_timers[QEMU_CLOCK_REALTIME] &&
-!active_timers[QEMU_CLOCK_VIRTUAL] &&
-!active_timers[QEMU_CLOCK_HOST])
+if (!rt_clock->act

[Qemu-devel] [PATCH v3 04/13] qemu-timer: more clock functions

2011-10-21 Thread Paolo Bonzini
These will be used when moving icount accounting to cpus.c.

Reviewed-by: Anthony Liguori 
Signed-off-by: Paolo Bonzini 
---
 qemu-timer.c |   25 +
 qemu-timer.h |3 +++
 2 files changed, 28 insertions(+), 0 deletions(-)

diff --git a/qemu-timer.c b/qemu-timer.c
index e2551f3..ebb5089 100644
--- a/qemu-timer.c
+++ b/qemu-timer.c
@@ -495,6 +495,31 @@ void qemu_clock_warp(QEMUClock *clock)
 }
 }
 
+int64_t qemu_clock_has_timers(QEMUClock *clock)
+{
+return !!clock->active_timers;
+}
+
+int64_t qemu_clock_expired(QEMUClock *clock)
+{
+return (clock->active_timers &&
+clock->active_timers->expire_time < qemu_get_clock_ns(clock));
+}
+
+int64_t qemu_clock_deadline(QEMUClock *clock)
+{
+/* To avoid problems with overflow limit this to 2^32.  */
+int64_t delta = INT32_MAX;
+
+if (clock->active_timers) {
+delta = clock->active_timers->expire_time - qemu_get_clock_ns(clock);
+}
+if (delta < 0) {
+delta = 0;
+}
+return delta;
+}
+
 QEMUTimer *qemu_new_timer(QEMUClock *clock, int scale,
   QEMUTimerCB *cb, void *opaque)
 {
diff --git a/qemu-timer.h b/qemu-timer.h
index 0a43469..4578075 100644
--- a/qemu-timer.h
+++ b/qemu-timer.h
@@ -38,6 +38,9 @@ extern QEMUClock *vm_clock;
 extern QEMUClock *host_clock;
 
 int64_t qemu_get_clock_ns(QEMUClock *clock);
+int64_t qemu_clock_has_timers(QEMUClock *clock);
+int64_t qemu_clock_expired(QEMUClock *clock);
+int64_t qemu_clock_deadline(QEMUClock *clock);
 void qemu_clock_enable(QEMUClock *clock, int enabled);
 void qemu_clock_warp(QEMUClock *clock);
 
-- 
1.7.6





[Qemu-devel] [PATCH v3 12/13] Revert to a hand-made select loop

2011-10-21 Thread Paolo Bonzini
This reverts commit c82dc29a9112f34e0a51cad9a412cf6d9d05dfb2
and 4d88a2ac8643265108ef1fb47ceee5d7b28e19f2.

Signed-off-by: Paolo Bonzini 
---
 iohandler.c |   54 +-
 1 files changed, 1 insertions(+), 53 deletions(-)

diff --git a/iohandler.c b/iohandler.c
index 687dc56..5640d49 100644
--- a/iohandler.c
+++ b/iohandler.c
@@ -81,64 +81,12 @@ int qemu_set_fd_handler2(int fd,
 return 0;
 }
 
-typedef struct IOTrampoline
-{
-GIOChannel *chan;
-IOHandler *fd_read;
-IOHandler *fd_write;
-void *opaque;
-guint tag;
-} IOTrampoline;
-
-static gboolean fd_trampoline(GIOChannel *chan, GIOCondition cond, gpointer 
opaque)
-{
-IOTrampoline *tramp = opaque;
-
-if ((cond & G_IO_IN) && tramp->fd_read) {
-tramp->fd_read(tramp->opaque);
-}
-
-if ((cond & G_IO_OUT) && tramp->fd_write) {
-tramp->fd_write(tramp->opaque);
-}
-
-return TRUE;
-}
-
 int qemu_set_fd_handler(int fd,
 IOHandler *fd_read,
 IOHandler *fd_write,
 void *opaque)
 {
-static IOTrampoline fd_trampolines[FD_SETSIZE];
-IOTrampoline *tramp = &fd_trampolines[fd];
-
-if (tramp->tag != 0) {
-g_io_channel_unref(tramp->chan);
-g_source_remove(tramp->tag);
-tramp->tag = 0;
-}
-
-if (fd_read || fd_write || opaque) {
-GIOCondition cond = 0;
-
-tramp->fd_read = fd_read;
-tramp->fd_write = fd_write;
-tramp->opaque = opaque;
-
-if (fd_read) {
-cond |= G_IO_IN | G_IO_ERR;
-}
-
-if (fd_write) {
-cond |= G_IO_OUT | G_IO_ERR;
-}
-
-tramp->chan = g_io_channel_unix_new(fd);
-tramp->tag = g_io_add_watch(tramp->chan, cond, fd_trampoline, tramp);
-}
-
-return 0;
+return qemu_set_fd_handler2(fd, NULL, fd_read, fd_write, opaque);
 }
 
 void qemu_iohandler_fill(int *pnfds, fd_set *readfds, fd_set *writefds, fd_set 
*xfds)
-- 
1.7.6





[Qemu-devel] [PATCH v3 01/13] remove unused function

2011-10-21 Thread Paolo Bonzini
Reviewed-by: Anthony Liguori 
Signed-off-by: Paolo Bonzini 
---
 hw/mac_dbdma.c |5 -
 hw/mac_dbdma.h |1 -
 2 files changed, 0 insertions(+), 6 deletions(-)

diff --git a/hw/mac_dbdma.c b/hw/mac_dbdma.c
index 5affdd1..1791ec1 100644
--- a/hw/mac_dbdma.c
+++ b/hw/mac_dbdma.c
@@ -661,11 +661,6 @@ void DBDMA_register_channel(void *dbdma, int nchan, 
qemu_irq irq,
 ch->io.channel = ch;
 }
 
-void DBDMA_schedule(void)
-{
-qemu_notify_event();
-}
-
 static void
 dbdma_control_write(DBDMA_channel *ch)
 {
diff --git a/hw/mac_dbdma.h b/hw/mac_dbdma.h
index 933e17c..6d1abe6 100644
--- a/hw/mac_dbdma.h
+++ b/hw/mac_dbdma.h
@@ -41,5 +41,4 @@ struct DBDMA_io {
 void DBDMA_register_channel(void *dbdma, int nchan, qemu_irq irq,
 DBDMA_rw rw, DBDMA_flush flush,
 void *opaque);
-void DBDMA_schedule(void);
 void* DBDMA_init (MemoryRegion **dbdma_mem);
-- 
1.7.6





Re: [Qemu-devel] [PATCH V5] Add AACI audio playback support to the ARM Versatile/PB platform

2011-10-21 Thread andrzej zaborowski
Hi Mathieu,

On 18 October 2011 23:45, Mathieu Sonet  wrote:
> This driver emulates the ARM AACI interface (PL041) connected to a LM4549
> codec.
> It enables audio playback for the Versatile/PB platform.
>
> Limitations:
> - Supports only a playback on one channel (Versatile/Vexpress)
> - Supports only one TX FIFO in compact-mode or non-compact mode.
> - Supports playback of 12, 16, 18 and 20 bits samples.
> - Record is not supported.
> - The PL041 is hardwired to a LM4549 codec.
>
> Versatile/PB test build:
> linux-2.6.38.5
> buildroot-2010.11
> alsa-lib-1.0.22
> alsa-utils-1.0.22
> mpg123-0.66
>
> Qemu host: Ubuntu 10.04 in Vmware/OS X
>
> Playback tested successfully with speaker-test/aplay/mpg123.
>
> Signed-off-by: Mathieu Sonet 
> ---
> v4->v5
>
> * Move the lm4549 post_load hook in lm4549.c
> * Fix naked debug printf in lm4549.c
> * Clarify the size of the lm4549 audio buffer
>
>  Makefile.target  |    1 +
>  hw/lm4549.c      |  336 
>  hw/lm4549.h      |   43 
>  hw/pl041.c       |  636
> ++
>  hw/pl041.h       |  135 
>  hw/pl041.hx      |   81 +++
>  hw/versatilepb.c |    8 +
>  7 files changed, 1240 insertions(+), 0 deletions(-)
>  create mode 100644 hw/lm4549.c
>  create mode 100644 hw/lm4549.h
>  create mode 100644 hw/pl041.c
>  create mode 100644 hw/pl041.h
>  create mode 100644 hw/pl041.hx
>
> diff --git a/Makefile.target b/Makefile.target
> index 417f23e..25b9fc1 100644
> --- a/Makefile.target
> +++ b/Makefile.target
> @@ -355,6 +355,7 @@ obj-arm-y += syborg_virtio.o
>  obj-arm-y += vexpress.o
>  obj-arm-y += strongarm.o
>  obj-arm-y += collie.o
> +obj-arm-y += pl041.o lm4549.o
>
>  obj-sh4-y = shix.o r2d.o sh7750.o sh7750_regnames.o tc58128.o
>  obj-sh4-y += sh_timer.o sh_serial.o sh_intc.o sh_pci.o sm501.o
> diff --git a/hw/lm4549.c b/hw/lm4549.c
> new file mode 100644
> index 000..4d5b831
> --- /dev/null
> +++ b/hw/lm4549.c
> @@ -0,0 +1,336 @@
> +/*
> + * LM4549 Audio Codec Interface
> + *
> + * Copyright (c) 2011
> + * Written by Mathieu Sonet - www.elasticsheep.com
> + *
> + * This code is licenced under the GPL.
> + *
> + * *
> + *
> + * This driver emulates the LM4549 codec.
> + *
> + * It supports only one playback voice and no record voice.
> + */
> +
> +#include "hw.h"
> +#include "audio/audio.h"
> +#include "lm4549.h"
> +
> +#if 0
> +#define LM4549_DEBUG  1
> +#endif
> +
> +#if 0
> +#define LM4549_DUMP_DAC_INPUT 1
> +#endif
> +
> +#ifdef LM4549_DEBUG
> +#define DPRINTF(fmt, ...) \
> +do { printf("lm4549: " fmt , ## __VA_ARGS__); } while (0)
> +#else
> +#define DPRINTF(fmt, ...) do {} while (0)
> +#endif
> +
> +#if defined(LM4549_DUMP_DAC_INPUT)
> +#include 
> +static FILE *fp_dac_input;
> +#endif
> +
> +/* LM4549 register list */
> +enum {
> +    LM4549_Reset                    = 0x00,
> +    LM4549_Master_Volume            = 0x02,
> +    LM4549_Line_Out_Volume          = 0x04,
> +    LM4549_Master_Volume_Mono       = 0x06,
> +    LM4549_PC_Beep_Volume           = 0x0A,
> +    LM4549_Phone_Volume             = 0x0C,
> +    LM4549_Mic_Volume               = 0x0E,
> +    LM4549_Line_In_Volume           = 0x10,
> +    LM4549_CD_Volume                = 0x12,
> +    LM4549_Video_Volume             = 0x14,
> +    LM4549_Aux_Volume               = 0x16,
> +    LM4549_PCM_Out_Volume           = 0x18,
> +    LM4549_Record_Select            = 0x1A,
> +    LM4549_Record_Gain              = 0x1C,
> +    LM4549_General_Purpose          = 0x20,
> +    LM4549_3D_Control               = 0x22,
> +    LM4549_Powerdown_Ctrl_Stat      = 0x26,
> +    LM4549_Ext_Audio_ID             = 0x28,
> +    LM4549_Ext_Audio_Stat_Ctrl      = 0x2A,
> +    LM4549_PCM_Front_DAC_Rate       = 0x2C,
> +    LM4549_PCM_ADC_Rate             = 0x32,
> +    LM4549_Vendor_ID1               = 0x7C,
> +    LM4549_Vendor_ID2               = 0x7E
> +};
> +
> +static void lm4549_reset(lm4549_state *s)
> +{
> +    uint16_t *regfile = s->regfile;
> +
> +    regfile[LM4549_Reset]               = 0x0d50;
> +    regfile[LM4549_Master_Volume]       = 0x8008;
> +    regfile[LM4549_Line_Out_Volume]     = 0x8000;
> +    regfile[LM4549_Master_Volume_Mono]  = 0x8000;
> +    regfile[LM4549_PC_Beep_Volume]      = 0x;
> +    regfile[LM4549_Phone_Volume]        = 0x8008;
> +    regfile[LM4549_Mic_Volume]          = 0x8008;
> +    regfile[LM4549_Line_In_Volume]      = 0x8808;
> +    regfile[LM4549_CD_Volume]           = 0x8808;
> +    regfile[LM4549_Video_Volume]        = 0x8808;
> +    regfile[LM4549_Aux_Volume]          = 0x8808;
> +    regfile[LM4549_PCM_Out_Volume]      = 0x8808;
> +    regfile[LM4549_Record_Select]       = 0x;
> +    regfile[LM4549_Record_Gain]         = 0x8000;
> +    regfile[LM4549_General_Purpose]     = 0x;
> +    regfile[LM4549_3D_Control]          = 0x0101;
> +    regfile[LM4549_Powerdown_Ctrl_Stat] = 0x000f;
> +    regfile[LM4549_Ext_Audio

[Qemu-devel] [PATCH] [v2] target-arm/machine.c: Fix load of floating point registers

2011-10-21 Thread Dmitry Koshelev
Fix load of floating point registers

Signed-off-by: Dmitry Koshelev 
---
 target-arm/machine.c |2 +-
 1 files changed, 1 insertions(+), 1 deletions(-)

diff --git a/target-arm/machine.c b/target-arm/machine.c
index 7d4fc54..aaee9b9 100644
--- a/target-arm/machine.c
+++ b/target-arm/machine.c
@@ -189,7 +189,7 @@ int cpu_load(QEMUFile *f, void *opaque, int version_id)
 env->vfp.vec_stride = qemu_get_be32(f);
 
 if (arm_feature(env, ARM_FEATURE_VFP3)) {
-for (i = 0;  i < 16; i++) {
+for (i = 16;  i < 32; i++) {
 CPU_DoubleU u;
 u.l.upper = qemu_get_be32(f);
 u.l.lower = qemu_get_be32(f);
-- 
1.7.1





Re: [Qemu-devel] [PATCH] compatfd.c: Don't pass NULL pointer to SYS_signalfd

2011-10-21 Thread andrzej zaborowski
On 13 October 2011 19:45, Peter Maydell  wrote:
> Don't pass a NULL pointer in to SYS_signalfd in qemu_signalfd_available():
> this isn't valid and Valgrind complains about it.

Also pushed this patch.

Cheers



Re: [Qemu-devel] [PATCH] linux-user: Fix broken "-version" option

2011-10-21 Thread andrzej zaborowski
On 29 September 2011 16:48, Peter Maydell  wrote:
> Fix the "-version" option, which was accidentally broken in commit
> fc9c541:
>  * exit after printing version information rather than proceeding
>   blithely onward (and likely printing the full usage message)
>  * correct the cut-n-paste error in the usage message for it
>  * don't insist on the presence of a following argument for
>   options which don't take an argument (this was preventing
>   'qemu-arm -version' from working)
>  * remove a spurious argc check from the beginning of main() which
>   meant 'QEMU_VERSION=1 qemu-arm' didn't work.

Thanks, I pushed this patch.

Cheers



Re: [Qemu-devel] Multi heterogenous CPU archs for SoC sim?

2011-10-21 Thread Lluís Vilanova
Peter Maydell writes:

>> The only realistic way to get started with such setups I see is to create a
>> new target-xxx for the specific mix, define TARGET_LONG_BITS etc.
>> appropriately in a new cpu.h, compile the needed target-xyz/*.c to unique
>> xxx-softmmu/xyz-*.o and dispatch from a cpu_init() to the two cpu_*_init().

> Yuck. Longer term if we want to support this kind of heterogeneity
> we should be removing all the compile-time assumptions and generally
> making the target-specifics suitably contained rather than leaking
> into the rest of the code.

Yup, this sounds like pointer tables. That's one of the main reasons I advocated
C++. Another reason is improving code maintainability through templates (without
impacting performance).


>> I'm guessing we may need to distinguish the TBs at runtime? Reserving
>> log2(#architectures) bits in the TBFLAGS might do, but feels ugly.
>> Probably a lot of other issues I'm not seeing yet.

> We may want the tb cache to be per-core anyway (and one thread per core),
> which would avoid the problem of trying to wedge everything into one set
> of tb_flags.

Well, AFAIU if targets have different ISAs, the same physical tb will never be
used by differing targets (ignoring the case of different targets but same ISA).



Lluis

-- 
 "And it's much the same thing with knowledge, for whenever you learn
 something new, the whole world becomes that much richer."
 -- The Princess of Pure Reason, as told by Norton Juster in The Phantom
 Tollbooth



[Qemu-devel] Possible SPICE/QEMU deadlock on fast client reconnect

2011-10-21 Thread Daniel P. Berrange
In testing my patches for 'add_client' support with SPICE, I noticed
deadlock in the QEMU/SPICE code. It only happens if I close a SPICE
client and then immediately reconnect within about 1 second. If I
wait a couple of seconds before reconnecting the SPICE client I don't
see the deadlock.

I'm using QEMU & SPICE git master, and GDB has this to say

(gdb) thread apply all bt

Thread 3 (Thread 0x7f269e142700 (LWP 17233)):
#0  pthread_cond_wait@@GLIBC_2.3.2 () at 
../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:165
#1  0x004e80e9 in qemu_cond_wait (cond=, 
mutex=)
at qemu-thread-posix.c:113
#2  0x00556469 in qemu_kvm_wait_io_event (env=)
at /home/berrange/src/virt/qemu/cpus.c:626
#3  qemu_kvm_cpu_thread_fn (arg=0x29217a0) at 
/home/berrange/src/virt/qemu/cpus.c:661
#4  0x003a83207b31 in start_thread (arg=0x7f269e142700) at 
pthread_create.c:305
#5  0x003a82edfd2d in clone () at 
../sysdeps/unix/sysv/linux/x86_64/clone.S:115

Thread 2 (Thread 0x7f26822fc700 (LWP 17234)):
#0  __lll_lock_wait () at 
../nptl/sysdeps/unix/sysv/linux/x86_64/lowlevellock.S:140
#1  0x003a83209ad6 in _L_lock_752 () from /lib64/libpthread.so.0
#2  0x003a832099d7 in __pthread_mutex_lock (mutex=0x1182f60) at 
pthread_mutex_lock.c:65
#3  0x004e7ec9 in qemu_mutex_lock (mutex=) at 
qemu-thread-posix.c:54
#4  0x00507df5 in channel_event (event=3, info=0x2a3c610) at 
ui/spice-core.c:234
#5  0x7f269f77be87 in reds_stream_free (s=0x2a3c590) at reds.c:4073
#6  0x7f269f75b64f in red_channel_client_disconnect (rcc=0x7f267c069ec0) at 
red_channel.c:961
#7  0x7f269f75a131 in red_peer_handle_incoming (handler=0x7f267c06a5a0, 
stream=0x2a3c590)
at red_channel.c:150
#8  red_channel_client_receive (rcc=0x7f267c069ec0) at red_channel.c:158
#9  0x7f269f761fbc in handle_channel_events (in_listener=0x7f267c06a5f8, 
events=)
at red_worker.c:9566
#10 0x7f269f776672 in red_worker_main (arg=) at 
red_worker.c:10813
#11 0x003a83207b31 in start_thread (arg=0x7f26822fc700) at 
pthread_create.c:305
#12 0x003a82edfd2d in clone () at 
../sysdeps/unix/sysv/linux/x86_64/clone.S:115

Thread 1 (Thread 0x7f269f72e9c0 (LWP 17232)):
#0  0x003a8320e01d in read () at ../sysdeps/unix/syscall-template.S:82
#1  0x7f269f75daaa in receive_data (n=4, in_buf=0x7fffe7a5a02c, fd=18) at 
red_worker.h:150
#2  read_message (message=0x7fffe7a5a02c, fd=18) at red_worker.h:163
#3  red_dispatcher_disconnect_cursor_peer (rcc=0x7f267c0c0f60) at 
red_dispatcher.c:157
#4  0x7f269f75c20d in red_client_destroy (client=0x2a35400) at 
red_channel.c:1189
#5  0x7f269f778335 in reds_client_disconnect (client=0x2a35400) at 
reds.c:624
---Type  to continue, or q  to quit---
#6  0x7f269f75a131 in red_peer_handle_incoming (handler=0x2a35b50, 
stream=0x2b037d0) at red_channel.c:150
#7  red_channel_client_receive (rcc=0x2a35470) at red_channel.c:158
#8  0x7f269f75b1e8 in red_channel_client_event (fd=, 
event=, 
data=) at red_channel.c:774
#9  0x0045e561 in fd_trampoline (chan=, cond=, opaque=)
at iohandler.c:97
#10 0x003a84e427ed in g_main_dispatch (context=0x27fc510) at gmain.c:2441
#11 g_main_context_dispatch (context=0x27fc510) at gmain.c:3014
#12 0x004c3da3 in glib_select_poll (err=false, xfds=0x7fffe7a5a2e0, 
wfds=0x7fffe7a5a260, rfds=
0x7fffe7a5a1e0) at /home/berrange/src/virt/qemu/vl.c:1495
#13 main_loop_wait (nonblocking=) at 
/home/berrange/src/virt/qemu/vl.c:1541
#14 0x0040fdd1 in main_loop () at /home/berrange/src/virt/qemu/vl.c:1570
#15 main (argc=, argv=, envp=)
at /home/berrange/src/virt/qemu/vl.c:3563
(gdb) 


-- 
|: http://berrange.com  -o-http://www.flickr.com/photos/dberrange/ :|
|: http://libvirt.org  -o- http://virt-manager.org :|
|: http://autobuild.org   -o- http://search.cpan.org/~danberr/ :|
|: http://entangle-photo.org   -o-   http://live.gnome.org/gtk-vnc :|



[Qemu-devel] [PATCH] Add SPICE support to add_client monitor command

2011-10-21 Thread Daniel P. Berrange
From: "Daniel P. Berrange" 

With the proposal of some new APIs[1] to libspice-server.so it
is possible to add support for SPICE to the 'add_client'
monitor command, bringing parity with VNC. Since SPICE can
use TLS or plain connections, the command also gains a new
'tls' parameter to specify whether TLS should be attempted
on the injected client sockets.

NB1, since there is no SPICE release with these APIs, I
have guessed the next SPICE version number in the #ifdef
to be 0x000a00 (ie 0.10.0 in hex).

NB2, obviously this should only be merged once the SPICE
developers have accepted my proposed patches to libspice-server.so

* qmp-commands.hx: Add 'tls' parameter & missing doc for
  'skipauth' parameter
* monitor.c: Wire up SPICE for 'add_client' command
* ui/qemu-spice.h, ui/spice-core.c: Add qemu_spice_display_add_client
  API to wire up from monitor

[1] http://lists.freedesktop.org/archives/spice-devel/2011-October/005834.html

Signed-off-by: Daniel P. Berrange 
---
 monitor.c   |9 +++--
 qmp-commands.hx |6 --
 ui/qemu-spice.h |1 +
 ui/spice-core.c |   13 +
 4 files changed, 25 insertions(+), 4 deletions(-)

diff --git a/monitor.c b/monitor.c
index 31b212a..cae3b12 100644
--- a/monitor.c
+++ b/monitor.c
@@ -1120,13 +1120,18 @@ static int add_graphics_client(Monitor *mon, const 
QDict *qdict, QObject **ret_d
 CharDriverState *s;
 
 if (strcmp(protocol, "spice") == 0) {
+int fd = monitor_get_fd(mon, fdname);
+int skipauth = qdict_get_try_bool(qdict, "skipauth", 0);
+int tls = qdict_get_try_bool(qdict, "tls", 0);
 if (!using_spice) {
 /* correct one? spice isn't a device ,,, */
 qerror_report(QERR_DEVICE_NOT_ACTIVE, "spice");
 return -1;
 }
-   qerror_report(QERR_ADD_CLIENT_FAILED);
-   return -1;
+if (qemu_spice_display_add_client(fd, skipauth, tls) < 0) {
+close(fd);
+}
+return 0;
 #ifdef CONFIG_VNC
 } else if (strcmp(protocol, "vnc") == 0) {
int fd = monitor_get_fd(mon, fdname);
diff --git a/qmp-commands.hx b/qmp-commands.hx
index ea96191..de1ada3 100644
--- a/qmp-commands.hx
+++ b/qmp-commands.hx
@@ -911,8 +911,8 @@ EQMP
 
 {
 .name   = "add_client",
-.args_type  = "protocol:s,fdname:s,skipauth:b?",
-.params = "protocol fdname skipauth",
+.args_type  = "protocol:s,fdname:s,skipauth:b?,tls:b?",
+.params = "protocol fdname skipauth tls",
 .help   = "add a graphics client",
 .user_print = monitor_user_noop,
 .mhandler.cmd_new = add_graphics_client,
@@ -928,6 +928,8 @@ Arguments:
 
 - "protocol": protocol name (json-string)
 - "fdname": file descriptor name (json-string)
+- "skipauth": whether to skip authentication (json-bool)
+- "tls": whether to perform TLS (json-bool)
 
 Example:
 
diff --git a/ui/qemu-spice.h b/ui/qemu-spice.h
index f34be69..a0e213c 100644
--- a/ui/qemu-spice.h
+++ b/ui/qemu-spice.h
@@ -32,6 +32,7 @@ void qemu_spice_init(void);
 void qemu_spice_input_init(void);
 void qemu_spice_audio_init(void);
 void qemu_spice_display_init(DisplayState *ds);
+int qemu_spice_display_add_client(int csock, int skipauth, int tls);
 int qemu_spice_add_interface(SpiceBaseInstance *sin);
 int qemu_spice_set_passwd(const char *passwd,
   bool fail_if_connected, bool 
disconnect_if_connected);
diff --git a/ui/spice-core.c b/ui/spice-core.c
index 3cbc721..854670e 100644
--- a/ui/spice-core.c
+++ b/ui/spice-core.c
@@ -712,6 +712,19 @@ int qemu_spice_set_pw_expire(time_t expires)
 return qemu_spice_set_ticket(false, false);
 }
 
+int qemu_spice_display_add_client(int csock, int skipauth, int tls)
+{
+#if SPICE_SERVER_VERSION >= 0x000a00
+if (tls) {
+return spice_server_add_ssl_client(spice_server, csock, skipauth);
+} else {
+return spice_server_add_client(spice_server, csock, skipauth);
+}
+#else
+return -1;
+#endif
+}
+
 static void spice_register_config(void)
 {
 qemu_add_opts(&qemu_spice_opts);
-- 
1.7.6.4




[Qemu-devel] New message-Cheque 904533.

2011-10-21 Thread The Co-operative Bank



Re: [Qemu-devel] build with trace enabled is broken by the commit c572f23a3e7180dbeab5e86583e43ea2afed6271 hw/9pfs: Introduce tracing for 9p pdu handlers

2011-10-21 Thread Aneesh Kumar K.V
On Thu, 20 Oct 2011 23:20:54 +0400, Max Filippov  wrote:
> Hi.
> 
> Current git head build with trace enabled is broken by the commit 
> c572f23a3e7180dbeab5e86583e43ea2afed6271 hw/9pfs: Introduce tracing for 9p 
> pdu handlers.
> Error messages:
> 
> In file included from trace.c:2:0:
> trace.h: In function ‘trace_v9fs_attach’:
> trace.h:2850:9: error: too many arguments for format 
> [-Werror=format-extra-args]
> trace.h: In function ‘trace_v9fs_wstat’:
> trace.h:3039:9: error: too many arguments for format 
> [-Werror=format-extra-args]
> trace.h: In function ‘trace_v9fs_mkdir’:
> trace.h:3088:9: error: too many arguments for format 
> [-Werror=format-extra-args]
> trace.h: In function ‘trace_v9fs_mkdir_return’:
> trace.h:3095:9: error: too many arguments for format 
> [-Werror=format-extra-args]
> cc1: all warnings being treated as errors
> 
> Prototypes in the trace-events do not match format strings, e.g.
> 
> v9fs_attach(uint16_t tag, uint8_t id, int32_t fid, int32_t afid, char* uname, 
> char* aname) "tag %d id %d fid %d afid %d aname %s"
> 
> The following patch fixes it, but I'm not sure the format lines are 
> appropriate.

Can you send the patch with signed-off-by: I will add it in the next
pull request.

-aneesh




[Qemu-devel] [PATCH v2 4/4] Add support for net bridge

2011-10-21 Thread Corey Bryant
The most common use of -net tap is to connect a tap device to a bridge.  This
requires the use of a script and running qemu as root in order to allocate a
tap device to pass to the script.

This model is great for portability and flexibility but it's incredibly
difficult to eliminate the need to run qemu as root.  The only really viable
mechanism is to use tunctl to create a tap device, attach it to a bridge as
root, and then hand that tap device to qemu.  The problem with this mechanism
is that it requires administrator intervention whenever a user wants to create
a guest.

By essentially writing a helper that implements the most common qemu-ifup
script that can be safely given cap_net_admin, we can dramatically simplify
things for non-privileged users.  We still support existing -net tap options
as a mechanism for advanced users and backwards compatibility.

Currently, this is very Linux centric but there's really no reason why it
couldn't be extended for other Unixes.

A typical invocation would be:

  qemu linux.img -net bridge -net nic,model=virtio

or:

  qemu linux.img -net tap,helper=/usr/local/libexec/qemu-bridge-helper
 -net nic,model=virtio

The default bridge that we attach to is br0.  The thinking is that a distro
could preconfigure such an interface to allow out-of-the-box bridged networking.

Alternatively, if a user wants to use a different bridge, they can say:

  qemu linux.img -net bridge,br=qemubr0 -net nic,model=virtio

or:

  qemu linux.img -net 
tap,helper=/usr/local/libexec/qemu-bridge-helper,br=qemubr0
 -net nic,model=virtio

Signed-off-by: Anthony Liguori 
Signed-off-by: Richa Marwaha 
Signed-off-by: Corey Bryant 
---
 configure   |2 +
 net.c   |   29 -
 net.h   |3 +
 net/tap.c   |  190 +--
 net/tap.h   |3 +
 qemu-options.hx |   73 +
 6 files changed, 279 insertions(+), 21 deletions(-)

diff --git a/configure b/configure
index fed66b0..9493d60 100755
--- a/configure
+++ b/configure
@@ -2800,6 +2800,8 @@ echo "sysconfdir=$sysconfdir" >> $config_host_mak
 echo "docdir=$docdir" >> $config_host_mak
 echo "confdir=$confdir" >> $config_host_mak
 echo "libexecdir=\${prefix}/libexec" >> $config_host_mak
+echo "CONFIG_QEMU_SHAREDIR=\"$prefix$datasuffix\"" >> $config_host_mak
+echo "CONFIG_QEMU_HELPERDIR=\"$prefix/libexec\"" >> $config_host_mak
 
 case "$cpu" in
   
i386|x86_64|alpha|cris|hppa|ia64|lm32|m68k|microblaze|mips|mips64|ppc|ppc64|s390|s390x|sparc|sparc64|unicore32)
diff --git a/net.c b/net.c
index d05930c..2dcb2d4 100644
--- a/net.c
+++ b/net.c
@@ -956,6 +956,14 @@ static const struct {
 .type = QEMU_OPT_STRING,
 .help = "script to shut down the interface",
 }, {
+.name = "br",
+.type = QEMU_OPT_STRING,
+.help = "bridge name",
+}, {
+.name = "helper",
+.type = QEMU_OPT_STRING,
+.help = "command to execute to configure bridge",
+}, {
 .name = "sndbuf",
 .type = QEMU_OPT_SIZE,
 .help = "send buffer limit"
@@ -1053,6 +1061,23 @@ static const struct {
 { /* end of list */ }
 },
 },
+[NET_CLIENT_TYPE_BRIDGE] = {
+.type = "bridge",
+.init = net_init_bridge,
+.desc = {
+NET_COMMON_PARAMS_DESC,
+{
+.name = "br",
+.type = QEMU_OPT_STRING,
+.help = "bridge name",
+}, {
+.name = "helper",
+.type = QEMU_OPT_STRING,
+.help = "command to execute to configure bridge",
+},
+{ /* end of list */ }
+},
+},
 };
 
 int net_client_init(Monitor *mon, QemuOpts *opts, int is_netdev)
@@ -1075,7 +1100,8 @@ int net_client_init(Monitor *mon, QemuOpts *opts, int 
is_netdev)
 #ifdef CONFIG_VDE
 strcmp(type, "vde") != 0 &&
 #endif
-strcmp(type, "socket") != 0) {
+strcmp(type, "socket") != 0 &&
+strcmp(type, "bridge") != 0) {
 qerror_report(QERR_INVALID_PARAMETER_VALUE, "type",
   "a netdev backend type");
 return -1;
@@ -1145,6 +1171,7 @@ static int net_host_check_device(const char *device)
 #ifdef CONFIG_VDE
,"vde"
 #endif
+   , "bridge"
 };
 for (i = 0; i < sizeof(valid_param_list) / sizeof(char *); i++) {
 if (!strncmp(valid_param_list[i], device,
diff --git a/net.h b/net.h
index 9f633f8..d1340ad 100644
--- a/net.h
+++ b/net.h
@@ -36,6 +36,7 @@ typedef enum {
 NET_CLIENT_TYPE_SOCKET,
 NET_CLIENT_TYPE_VDE,
 NET_CLIENT_TYPE_DUMP,
+NET_CLIENT_TYPE_BRIDGE,
 
 NET_CLIENT_TYPE_MAX
 } net_client_type;
@@ -174,6 +175,8 @@ int do_netdev_del

[Qemu-devel] [PATCH v2 0/4] -net bridge: rootless bridge support for qemu

2011-10-21 Thread Corey Bryant
With qemu it is possible to run a guest from an unprivileged user but if
we wanted to communicate with the outside world we had to switch
to root.

We address this problem by introducing a new network backend and a new
network option for -net tap.  This is less flexible when compared to
existing -net tap options because it relies on a helper with elevated
privileges to do the heavy lifting of allocating and attaching a tap
device to a bridge.  We use a special purpose helper because we don't
want to elevate the privileges of more generic tools like brctl.

Qemu can be run with the default network helper as follows (in these cases
attaching the tap device to the default br0 bridge):

 qemu -hda linux.img -net bridge -net nic
or:
 qemu -hda linux.img -net tap,helper=/usr/local/libexec/qemu-bridge-helper 
-net nic

The default helper uses it's own ACL mechanism for access control, but
future network helpers could be developed, for example, to support PolicyKit
for access control.

More details are included in individual patches.  The helper is broken into
a series of patches to improve reviewabilty.

v2:
 - Updated signed-off-by's
 - Updated author's email
 - Set default bridge to br0
 - Added -net bridge
 - Updated ACL example
 - Moved from libcap to libcap-ng
 - Fail helper when libcap-ng not configured

Corey Bryant (4):
  Add basic version of bridge helper
  Add access control support to qemu bridge helper
  Add cap reduction support to enable use as SUID
  Add support for net bridge

 Makefile |   12 ++-
 configure|   37 +
 net.c|   29 -
 net.h|3 +
 net/tap.c|  190 -
 net/tap.h|2 +
 qemu-bridge-helper.c |  380 ++
 qemu-options.hx  |   73 --
 8 files changed, 703 insertions(+), 23 deletions(-)
 create mode 100644 qemu-bridge-helper.c

-- 
1.7.3.4




[Qemu-devel] [PATCH v2 1/4] Add basic version of bridge helper

2011-10-21 Thread Corey Bryant
This patch adds a helper that can be used to create a tap device attached to
a bridge device.  Since this helper is minimal in what it does, it can be
given CAP_NET_ADMIN which allows qemu to avoid running as root while still
satisfying the majority of what users tend to want to do with tap devices.

The way this all works is that qemu launches this helper passing a bridge
name and the name of an inherited file descriptor.  The descriptor is one
end of a socketpair() of domain sockets.  This domain socket is used to
transmit a file descriptor of the opened tap device from the helper to qemu.

The helper can then exit and let qemu use the tap device.

Signed-off-by: Anthony Liguori 
Signed-off-by: Richa Marwaha 
Signed-off-by: Corey Bryant 
---
 Makefile |   12 +++-
 configure|1 +
 qemu-bridge-helper.c |  205 ++
 3 files changed, 216 insertions(+), 2 deletions(-)
 create mode 100644 qemu-bridge-helper.c

diff --git a/Makefile b/Makefile
index f63fc02..d9b447e 100644
--- a/Makefile
+++ b/Makefile
@@ -35,6 +35,8 @@ $(call set-vpath, $(SRC_PATH):$(SRC_PATH)/hw)
 
 LIBS+=-lz $(LIBS_TOOLS)
 
+HELPERS-$(CONFIG_LINUX) = qemu-bridge-helper$(EXESUF)
+
 ifdef BUILD_DOCS
 DOCS=qemu-doc.html qemu-tech.html qemu.1 qemu-img.1 qemu-nbd.8 
QMP/qmp-commands.txt
 else
@@ -75,7 +77,7 @@ defconfig:
 
 -include config-all-devices.mak
 
-build-all: $(DOCS) $(TOOLS) recurse-all
+build-all: $(DOCS) $(TOOLS) $(HELPERS-y) recurse-all
 
 config-host.h: config-host.h-timestamp
 config-host.h-timestamp: config-host.mak
@@ -153,6 +155,8 @@ qemu-img$(EXESUF): qemu-img.o $(tools-obj-y)
 qemu-nbd$(EXESUF): qemu-nbd.o $(tools-obj-y)
 qemu-io$(EXESUF): qemu-io.o cmd.o $(tools-obj-y)
 
+qemu-bridge-helper$(EXESUF): qemu-bridge-helper.o
+
 qemu-img-cmds.h: $(SRC_PATH)/qemu-img-cmds.hx
$(call quiet-command,sh $(SRC_PATH)/scripts/hxtool -h < $< > $@,"  GEN  
 $@")
 
@@ -221,7 +225,7 @@ 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 *.lo $(TOOLS) qemu-ga TAGS cscope.* *.pod *~ */*~
+   rm -f *.o *.d *.a *.lo $(TOOLS) $(HELPERS-y) qemu-ga 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 qapi/*.o qapi/*.d qga/*.o 
qga/*.d
rm -f qemu-img-cmds.h
@@ -289,6 +293,10 @@ install: all $(if $(BUILD_DOCS),install-doc) 
install-sysconfig
 ifneq ($(TOOLS),)
$(INSTALL_PROG) $(STRIP_OPT) $(TOOLS) "$(DESTDIR)$(bindir)"
 endif
+ifneq ($(HELPERS-y),)
+   $(INSTALL_DIR) "$(DESTDIR)$(libexecdir)"
+   $(INSTALL_PROG) $(STRIP_OPT) $(HELPERS-y) "$(DESTDIR)$(libexecdir)"
+endif
 ifneq ($(BLOBS),)
$(INSTALL_DIR) "$(DESTDIR)$(datadir)"
set -e; for x in $(BLOBS); do \
diff --git a/configure b/configure
index 4f87e0a..6c8b659 100755
--- a/configure
+++ b/configure
@@ -2768,6 +2768,7 @@ echo "datadir=$datadir" >> $config_host_mak
 echo "sysconfdir=$sysconfdir" >> $config_host_mak
 echo "docdir=$docdir" >> $config_host_mak
 echo "confdir=$confdir" >> $config_host_mak
+echo "libexecdir=\${prefix}/libexec" >> $config_host_mak
 
 case "$cpu" in
   
i386|x86_64|alpha|cris|hppa|ia64|lm32|m68k|microblaze|mips|mips64|ppc|ppc64|s390|s390x|sparc|sparc64|unicore32)
diff --git a/qemu-bridge-helper.c b/qemu-bridge-helper.c
new file mode 100644
index 000..2ce82fb
--- /dev/null
+++ b/qemu-bridge-helper.c
@@ -0,0 +1,205 @@
+/*
+ * QEMU Bridge Helper
+ *
+ * Copyright IBM, Corp. 2011
+ *
+ * Authors:
+ * Anthony Liguori   
+ *
+ * This work is licensed under the terms of the GNU GPL, version 2.  See
+ * the COPYING file in the top-level directory.
+ *
+ */
+
+#include "config-host.h"
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#include 
+
+#include 
+
+#include "net/tap-linux.h"
+
+static int has_vnet_hdr(int fd)
+{
+unsigned int features = 0;
+struct ifreq ifreq;
+
+if (ioctl(fd, TUNGETFEATURES, &features) == -1) {
+return -errno;
+}
+
+if (!(features & IFF_VNET_HDR)) {
+return -ENOTSUP;
+}
+
+if (ioctl(fd, TUNGETIFF, &ifreq) != -1 || errno != EBADFD) {
+return -ENOTSUP;
+}
+
+return 1;
+}
+
+static void prep_ifreq(struct ifreq *ifr, const char *ifname)
+{
+memset(ifr, 0, sizeof(*ifr));
+snprintf(ifr->ifr_name, IFNAMSIZ, "%s", ifname);
+}
+
+static int send_fd(int c, int fd)
+{
+char msgbuf[CMSG_SPACE(sizeof(fd))];
+struct msghdr msg = {
+.msg_control = msgbuf,
+.msg_controllen = sizeof(msgbuf),
+};
+struct cmsghdr *cmsg;
+struct iovec iov;
+char req[1] = { 0x00 };
+
+cmsg = CMSG_FIRSTHDR(&msg);
+cmsg->cmsg_level = SOL_SOCKET;
+cmsg->cmsg_type = SCM

Re: [Qemu-devel] [PATCH] hw/omap2: Wire up the IRQ for the 2430's fifth GPIO module

2011-10-21 Thread andrzej zaborowski
On 18 October 2011 17:12, Peter Maydell  wrote:
> The OMAP2430 version of the omap-gpio device has five GPIO modules,
> not four like the other OMAP2 versions; wire up the fifth module's
> IRQ line correctly.

Thanks, pushed this patch.

Cheers



[Qemu-devel] [PATCH v2 3/4] Add cap reduction support to enable use as SUID

2011-10-21 Thread Corey Bryant
The ideal way to use qemu-bridge-helper is to give it an fscap of using:

 setcap cap_net_admin=ep qemu-bridge-helper

Unfortunately, most distros still do not have a mechanism to package files
with fscaps applied.  This means they'll have to SUID the qemu-bridge-helper
binary.

To improve security, use libcap to reduce our capability set to just
cap_net_admin, then reduce privileges down to the calling user.  This is
hopefully close to equivalent to fscap support from a security perspective.

Signed-off-by: Anthony Liguori 
Signed-off-by: Richa Marwaha 
Signed-off-by: Corey Bryant 
---
 configure|   34 ++
 qemu-bridge-helper.c |   39 +++
 2 files changed, 73 insertions(+), 0 deletions(-)

diff --git a/configure b/configure
index 6c8b659..fed66b0 100755
--- a/configure
+++ b/configure
@@ -128,6 +128,7 @@ vnc_thread="no"
 xen=""
 xen_ctrl_version=""
 linux_aio=""
+cap=""
 attr=""
 xfs=""
 
@@ -653,6 +654,10 @@ for opt do
   ;;
   --enable-kvm) kvm="yes"
   ;;
+  --disable-cap)  cap="no"
+  ;;
+  --enable-cap) cap="yes"
+  ;;
   --disable-spice) spice="no"
   ;;
   --enable-spice) spice="yes"
@@ -1032,6 +1037,8 @@ echo "  --disable-vdedisable support for vde 
network"
 echo "  --enable-vde enable support for vde network"
 echo "  --disable-linux-aio  disable Linux AIO support"
 echo "  --enable-linux-aio   enable Linux AIO support"
+echo "  --disable-capdisable libcap-ng support"
+echo "  --enable-cap enable libcap-ng support"
 echo "  --disable-attr   disables attr and xattr support"
 echo "  --enable-attrenable attr and xattr support"
 echo "  --disable-blobs  disable installing provided firmware blobs"
@@ -1638,6 +1645,29 @@ EOF
 fi
 
 ##
+# libcap-ng library probe
+if test "$cap" != "no" ; then
+  cap_libs="-lcap-ng"
+  cat > $TMPC << EOF
+#include 
+int main(void)
+{
+capng_capability_to_name(CAPNG_EFFECTIVE);
+return 0;
+}
+EOF
+  if compile_prog "" "$cap_libs" ; then
+cap=yes
+libs_tools="$cap_libs $libs_tools"
+  else
+if test "$cap" = "yes" ; then
+  feature_not_found "cap"
+fi
+cap=no
+  fi
+fi
+
+##
 # Sound support libraries probe
 
 audio_drv_probe()
@@ -2735,6 +2765,7 @@ echo "fdatasync $fdatasync"
 echo "madvise   $madvise"
 echo "posix_madvise $posix_madvise"
 echo "uuid support  $uuid"
+echo "libcap-ng support $cap"
 echo "vhost-net support $vhost_net"
 echo "Trace backend $trace_backend"
 echo "Trace output file $trace_file-"
@@ -2846,6 +2877,9 @@ fi
 if test "$vde" = "yes" ; then
   echo "CONFIG_VDE=y" >> $config_host_mak
 fi
+if test "$cap" = "yes" ; then
+  echo "CONFIG_LIBCAP=y" >> $config_host_mak
+fi
 for card in $audio_card_list; do
 def=CONFIG_`echo $card | tr '[:lower:]' '[:upper:]'`
 echo "$def=y" >> $config_host_mak
diff --git a/qemu-bridge-helper.c b/qemu-bridge-helper.c
index db257d5..b1562eb 100644
--- a/qemu-bridge-helper.c
+++ b/qemu-bridge-helper.c
@@ -33,6 +33,10 @@
 
 #include "net/tap-linux.h"
 
+#ifdef CONFIG_LIBCAP
+#include 
+#endif
+
 #define MAX_ACLS (128)
 #define DEFAULT_ACL_FILE CONFIG_QEMU_CONFDIR "/bridge.conf"
 
@@ -185,6 +189,27 @@ static int send_fd(int c, int fd)
 return sendmsg(c, &msg, 0);
 }
 
+#ifdef CONFIG_LIBCAP
+static int drop_privileges(void)
+{
+/* clear all capabilities */
+capng_clear(CAPNG_SELECT_BOTH);
+
+if (capng_update(CAPNG_ADD, CAPNG_EFFECTIVE | CAPNG_PERMITTED,
+ CAP_NET_ADMIN) < 0) {
+return -1;
+}
+
+/* change to calling user's real uid and gid, retaining supplemental
+ * groups and CAP_NET_ADMIN */
+if (capng_change_id(getuid(), getgid(), CAPNG_CLEAR_BOUNDING)) {
+return -1;
+}
+
+return 0;
+}
+#endif
+
 int main(int argc, char **argv)
 {
 struct ifreq ifr;
@@ -198,6 +223,20 @@ int main(int argc, char **argv)
 int acl_count = 0;
 int i, access_allowed, access_denied;
 
+/* if we're run from an suid binary, immediately drop privileges preserving
+ * cap_net_admin -- exit immediately if libcap not configured */
+if (geteuid() == 0 && getuid() != geteuid()) {
+#ifdef CONFIG_LIBCAP
+if (drop_privileges() == -1) {
+fprintf(stderr, "failed to drop privileges\n");
+return 1;
+}
+#else
+fprintf(stderr, "failed to drop privileges\n");
+return 1;
+#endif
+}
+
 /* parse arguments */
 if (argc < 3 || argc > 4) {
 fprintf(stderr, "Usage: %s [--use-vnet] BRIDGE FD\n", argv[0]);
-- 
1.7.3.4




Re: [Qemu-devel] [PATCH] [v3] hw/arm_gic.c: Fix save/load of irq_target array

2011-10-21 Thread andrzej zaborowski
On 20 October 2011 12:48, Dmitry Koshelev  wrote:
> irq_target array saving/loading is in the wrong loop.
> Version bump.
>
> Signed-off-by: Dmitry Koshelev 

Thanks, pushed this patch.

Cheers



[Qemu-devel] [PATCH v2 2/4] Add access control support to qemu bridge helper

2011-10-21 Thread Corey Bryant
We go to great lengths to restrict ourselves to just cap_net_admin as an OS
enforced security mechanism.  However, we further restrict what we allow users
to do to simply adding a tap device to a bridge interface by virtue of the fact
that this is the only functionality we expose.

This is not good enough though.  An administrator is likely to want to restrict
the bridges that an unprivileged user can access, in particular, to restrict
an unprivileged user from putting a guest on what should be isolated networks.

This patch implements an ACL mechanism that is enforced by qemu-bridge-helper.
The ACLs are fairly simple whitelist/blacklist mechanisms with a wildcard of
'all'.  All users are blacklisted by default, and deny takes precedence over
allow.

An interesting feature of this ACL mechanism is that you can include external
ACL files.  The main reason to support this is so that you can set different
file system permissions on those external ACL files.  This allows an
administrator to implement rather sophisicated ACL policies based on user/group
policies via the file system.

As an example:

/etc/qemu/bridge.conf root:qemu 0640

 allow br0
 include /etc/qemu/alice.conf
 include /etc/qemu/bob.conf
 include /etc/qemu/charlie.conf

/etc/qemu/alice.conf root:alice 0640
 allow br1

/etc/qemu/bob.conf root:bob 0640
 allow br2

/etc/qemu/charlie.conf root:charlie 0640
 deny all

This ACL pattern allows any user in the qemu group to get a tap device
connected to br0 (which is bridged to the physical network).

Users in the alice group can additionally get a tap device connected to br1.
This allows br1 to act as a private bridge for the alice group.

Users in the bob group can additionally get a tap device connected to br2.
This allows br2 to act as a private bridge for the bob group.

Users in the charlie group cannot get a tap device connected to any bridge.

Under no circumstance can the bob group get access to br1 or can the alice
group get access to br2.  And under no cicumstance can the charlie group
get access to any bridge.

Signed-off-by: Anthony Liguori 
Signed-off-by: Richa Marwaha 
Signed-off-by: Corey Bryant 
---
 qemu-bridge-helper.c |  141 ++
 1 files changed, 141 insertions(+), 0 deletions(-)

diff --git a/qemu-bridge-helper.c b/qemu-bridge-helper.c
index 2ce82fb..db257d5 100644
--- a/qemu-bridge-helper.c
+++ b/qemu-bridge-helper.c
@@ -33,6 +33,105 @@
 
 #include "net/tap-linux.h"
 
+#define MAX_ACLS (128)
+#define DEFAULT_ACL_FILE CONFIG_QEMU_CONFDIR "/bridge.conf"
+
+enum {
+ACL_ALLOW = 0,
+ACL_ALLOW_ALL,
+ACL_DENY,
+ACL_DENY_ALL,
+};
+
+typedef struct ACLRule {
+int type;
+char iface[IFNAMSIZ];
+} ACLRule;
+
+static int parse_acl_file(const char *filename, ACLRule *acls, int *pacl_count)
+{
+int acl_count = *pacl_count;
+FILE *f;
+char line[4096];
+
+f = fopen(filename, "r");
+if (f == NULL) {
+return -1;
+}
+
+while (acl_count != MAX_ACLS &&
+fgets(line, sizeof(line), f) != NULL) {
+char *ptr = line;
+char *cmd, *arg, *argend;
+
+while (isspace(*ptr)) {
+ptr++;
+}
+
+/* skip comments and empty lines */
+if (*ptr == '#' || *ptr == 0) {
+continue;
+}
+
+cmd = ptr;
+arg = strchr(cmd, ' ');
+if (arg == NULL) {
+arg = strchr(cmd, '\t');
+}
+
+if (arg == NULL) {
+fprintf(stderr, "Invalid config line:\n  %s\n", line);
+fclose(f);
+errno = EINVAL;
+return -1;
+}
+
+*arg = 0;
+arg++;
+while (isspace(*arg)) {
+arg++;
+}
+
+argend = arg + strlen(arg);
+while (arg != argend && isspace(*(argend - 1))) {
+argend--;
+}
+*argend = 0;
+
+if (strcmp(cmd, "deny") == 0) {
+if (strcmp(arg, "all") == 0) {
+acls[acl_count].type = ACL_DENY_ALL;
+} else {
+acls[acl_count].type = ACL_DENY;
+snprintf(acls[acl_count].iface, IFNAMSIZ, "%s", arg);
+}
+acl_count++;
+} else if (strcmp(cmd, "allow") == 0) {
+if (strcmp(arg, "all") == 0) {
+acls[acl_count].type = ACL_ALLOW_ALL;
+} else {
+acls[acl_count].type = ACL_ALLOW;
+snprintf(acls[acl_count].iface, IFNAMSIZ, "%s", arg);
+}
+acl_count++;
+} else if (strcmp(cmd, "include") == 0) {
+/* ignore errors */
+parse_acl_file(arg, acls, &acl_count);
+} else {
+fprintf(stderr, "Unknown command `%s'\n", cmd);
+fclose(f);
+errno = EINVAL;
+return -1;
+}
+}
+
+*pacl_count = acl_count;
+
+fclose(f);
+
+return 0;
+}
+
 static int has_vnet_hdr(int fd)
 {
 unsigned int features = 0;

Re: [Qemu-devel] [PATCH] Mark future contributions to GPLv2-only files as GPLv2+

2011-10-21 Thread Kevin Wolf
Am 21.10.2011 16:11, schrieb Anthony Liguori:
> On 10/21/2011 09:03 AM, Paolo Bonzini wrote:
>> Even for files are licensed GPLv2-only, let's not play catch with
>> ourselves, and explicitly declare that future contributions to those
>> files will also be available as "any later version".
>>
>> Signed-off-by: Paolo Bonzini
>> diff --git a/roms/SLOF b/roms/SLOF
>> index d1d6b53..b94bde0 16
>> --- a/roms/SLOF
>> +++ b/roms/SLOF
>> @@ -1 +1 @@
>> -Subproject commit d1d6b53b713a2b7c2c25685268fa932d28a4b4c0
>> +Subproject commit b94bde008b0d49ec4bfe933e110d0952d032ac28
> 
> I think you made a mistake here.
> 
> Otherwise I'm a bit concerned about ambiguity here.  Let's say we have to 
> backport a fit to stable, we need to pull in this new copyright statement.
> 
> But then what if we later discovered we need to pull in a fix from before 
> 10/25. 
>   That will appear in the stable tree as a post-10/25 commit but it carries a 
> GPLv2 only license.
> 
> I think a per-file flag day is really the only sane approach to this.

I don't think any part of this patch should be pulled into stable. When
backporting a new fix (which is basically dual GPLv2 and GPLv3), we can
choose which of the offered licenses to use. IANAL, but nothing should
stop us from only taking the GPLv2 option.

Am I misunderstanding something here?

Kevin



Re: [Qemu-devel] [PATCH] Mark future contributions to GPLv2-only files as GPLv2+

2011-10-21 Thread Paolo Bonzini

On 10/21/2011 04:11 PM, Anthony Liguori wrote:


Otherwise I'm a bit concerned about ambiguity here.  Let's say we have
to backport a fit to stable, we need to pull in this new copyright
statement.

But then what if we later discovered we need to pull in a fix from
before 10/25.  That will appear in the stable tree as a post-10/25
commit but it carries a GPLv2 only license.


You will never need to include this patch on 0.15 and earlier stable 
branches.


It is legal to take GPLv2+ contributions and restrict them to 
GPLv2-only.  Backporting is distributing, and a distributor can choose 
under which license he does so.  So there should be no problem with 
stable backports, whoever does the backports is implicitly restricting 
the licensing to GPLv2-only.


In fact, the text is just there to inform new contributors of the 
license.  Perhaps just changing the wording satisfies you, like "By 
signing off changes to this files after 10/25 you agree that the file 
may be relicensed under GPLv2+ in the future"?



I think a per-file flag day is really the only sane approach to this.


We need to make it clear right now that, from now on, GPLv3-incompatible 
changes will not be accepted.


Paolo



Re: [Qemu-devel] [PATCH v2 5/6] target-mips: Support for Cavium specific instructions

2011-10-21 Thread Richard Henderson
On 10/21/2011 01:17 AM, kha...@kics.edu.pk wrote:
> +switch (opc) {
> +case OPC_SEQ:
> +tcg_gen_setcondi_tl(TCG_COND_LTU, cpu_gpr[rd], t0, 1);
> +opn = "seq";
> +break;
> +case OPC_SNE:
> +tcg_gen_setcondi_tl(TCG_COND_GTU, cpu_gpr[rd], t0, 0);
> +opn = "sne";

If you keep posting the same un-fixed patch set, pretty soon
no one's going to pay any attention to you whatsoever.


r~



Re: [Qemu-devel] [PATCH] [v3] hw/arm_gic.c: Fix save/load of irq_target array

2011-10-21 Thread Andreas Färber
Am 21.10.2011 15:58, schrieb Dmitry Koshelev:
> On Fri, Oct 21, 2011 at 3:42 PM, Andreas Färber  wrote:
>> Am 20.10.2011 12:48, schrieb Dmitry Koshelev:
>>> irq_target array saving/loading is in the wrong loop.
>>> Version bump.
>>>
>>> Signed-off-by: Dmitry Koshelev 
>>
>> Acked-by: Andreas Färber 

Ah sorry, habits, should've been:

Acked-by: Andreas Färber 

>> Is there a particular use case that was broken before and works now, or
>> did this turn up during code review only?
> 
> There is a use case but it's complicated and involves proprietary software.

I see. ;) Was just wondering which -M were affected.

Andreas

-- 
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg, Germany
GF: Jeff Hawn, Jennifer Guild, Felix Imendörffer; HRB 16746, AG Nürnberg



Re: [Qemu-devel] [Question] dump memory when host pci device is used by guest

2011-10-21 Thread Richard W.M. Jones
On Fri, Oct 21, 2011 at 09:02:37AM -0400, Dave Anderson wrote:
> It would be kind of cool if there was a "/dev/mem"-like interface
> to a KVM guest's physical memory, so that you could sit on a KVM host
> and enter "crash vmlinux-of-guest /dev/mem-of-guest" in order to
> run live analysis of a guest.

OT for this thread, but this sort of thing does exist, kind of.

You can send monitor commands to qemu to read physical and virtual
memory ("pmemsave" and "memsave" respectively).  At least one, and
possibly now both of these are bound through libvirt APIs:

http://libvirt.org/html/libvirt-libvirt.html#virDomainMemoryPeek

Here was your previous response about 4 years ago:

https://www.redhat.com/archives/crash-utility/2008-August/msg00032.html

Rich.

-- 
Richard Jones, Virtualization Group, Red Hat http://people.redhat.com/~rjones
libguestfs lets you edit virtual machines.  Supports shell scripting,
bindings from many languages.  http://libguestfs.org



Re: [Qemu-devel] [PATCH] Mark future contributions to GPLv2-only files as GPLv2+

2011-10-21 Thread Anthony Liguori

On 10/21/2011 09:03 AM, Paolo Bonzini wrote:

Even for files are licensed GPLv2-only, let's not play catch with
ourselves, and explicitly declare that future contributions to those
files will also be available as "any later version".

Signed-off-by: Paolo Bonzini
diff --git a/roms/SLOF b/roms/SLOF
index d1d6b53..b94bde0 16
--- a/roms/SLOF
+++ b/roms/SLOF
@@ -1 +1 @@
-Subproject commit d1d6b53b713a2b7c2c25685268fa932d28a4b4c0
+Subproject commit b94bde008b0d49ec4bfe933e110d0952d032ac28


I think you made a mistake here.

Otherwise I'm a bit concerned about ambiguity here.  Let's say we have to 
backport a fit to stable, we need to pull in this new copyright statement.


But then what if we later discovered we need to pull in a fix from before 10/25. 
 That will appear in the stable tree as a post-10/25 commit but it carries a 
GPLv2 only license.


I think a per-file flag day is really the only sane approach to this.

Regards,

Anthony Liguori


diff --git a/xen-all.c b/xen-all.c
index b5e28ab..4d6bf1a 100644
--- a/xen-all.c
+++ b/xen-all.c
@@ -4,6 +4,8 @@
   * This work is licensed under the terms of the GNU GPL, version 2.  See
   * the COPYING file in the top-level directory.
   *
+ * Contributions after 2011-10-25 are licensed under the terms of the
+ * GNU GPL, version 2 or (at your option) any later version.
   */

  #include
diff --git a/xen-mapcache.c b/xen-mapcache.c
index 7bcb86e..f66bc60 100644
--- a/xen-mapcache.c
+++ b/xen-mapcache.c
@@ -4,6 +4,8 @@
   * This work is licensed under the terms of the GNU GPL, version 2.  See
   * the COPYING file in the top-level directory.
   *
+ * Contributions after 2011-10-25 are licensed under the terms of the
+ * GNU GPL, version 2 or (at your option) any later version.
   */

  #include "config.h"
diff --git a/xen-stub.c b/xen-stub.c
index efe2ab5..d713750 100644
--- a/xen-stub.c
+++ b/xen-stub.c
@@ -4,6 +4,8 @@
   * This work is licensed under the terms of the GNU GPL, version 2.  See
   * the COPYING file in the top-level directory.
   *
+ * Contributions after 2011-10-25 are licensed under the terms of the
+ * GNU GPL, version 2 or (at your option) any later version.
   */

  #include "qemu-common.h"





[Qemu-devel] [PATCH] Mark future contributions to GPLv2-only files as GPLv2+

2011-10-21 Thread Paolo Bonzini
Even for files are licensed GPLv2-only, let's not play catch with
ourselves, and explicitly declare that future contributions to those
files will also be available as "any later version".

Signed-off-by: Paolo Bonzini 
---
 aio.c  |2 ++
 block-migration.c  |2 ++
 block/raw-posix-aio.h  |2 ++
 block/rbd.c|2 ++
 block/sheepdog.c   |3 +++
 buffered_file.c|2 ++
 compatfd.c |2 ++
 hmp.c  |2 ++
 hw/ac97.c  |3 +++
 hw/acpi.c  |3 +++
 hw/acpi_piix4.c|3 +++
 hw/ads7846.c   |3 +++
 hw/apm.c   |3 +++
 hw/bitbang_i2c.c   |3 +++
 hw/bonito.c|3 +++
 hw/collie.c|3 +++
 hw/ds1338.c|3 +++
 hw/ecc.c   |3 +++
 hw/event_notifier.c|3 +++
 hw/framebuffer.c   |3 +++
 hw/gumstix.c   |3 +++
 hw/ivshmem.c   |3 +++
 hw/kvmclock.c  |2 ++
 hw/lan9118.c   |3 +++
 hw/mainstone.c |3 +++
 hw/marvell_88w8618_audio.c |3 +++
 hw/max111x.c   |3 +++
 hw/mips_fulong2e.c |3 +++
 hw/msix.c  |3 +++
 hw/mst_fpga.c  |3 +++
 hw/musicpal.c  |3 +++
 hw/nand.c  |3 +++
 hw/pl031.c |2 ++
 hw/pxa2xx_keypad.c |3 +++
 hw/pxa2xx_lcd.c|3 +++
 hw/pxa2xx_mmci.c   |3 +++
 hw/pxa2xx_pcmcia.c |3 +++
 hw/smbios.c|2 ++
 hw/spitz.c |3 +++
 hw/ssi-sd.c|3 +++
 hw/ssi.c   |3 +++
 hw/strongarm.c |3 +++
 hw/tc6393xb.c  |3 +++
 hw/tosa.c  |3 +++
 hw/vexpress.c  |3 +++
 hw/vhost.c |3 +++
 hw/vhost_net.c |3 +++
 hw/virtio-pci.c|2 ++
 hw/virtio-serial-bus.c |3 +++
 hw/vt82c686.c  |3 +++
 hw/xen_backend.c   |3 +++
 hw/xen_disk.c  |3 +++
 hw/xen_nic.c   |3 +++
 hw/z2.c|3 +++
 iov.c  |3 +++
 memory.c   |2 ++
 migration-exec.c   |2 ++
 migration-fd.c |2 ++
 migration-tcp.c|2 ++
 migration-unix.c   |2 ++
 migration.c|2 ++
 module.c   |2 ++
 net/checksum.c |3 +++
 notify.c   |2 ++
 pflib.c|2 ++
 posix-aio-compat.c |2 ++
 qemu-tool.c|2 ++
 qmp.c  |2 ++
 roms/SLOF  |2 +-
 xen-all.c  |2 ++
 xen-mapcache.c |2 ++
 xen-stub.c |2 ++
 72 files changed, 188 insertions(+), 1 deletions(-)

diff --git a/aio.c b/aio.c
index 1239ca7..c6f3cb1 100644
--- a/aio.c
+++ b/aio.c
@@ -9,6 +9,8 @@
  * This work is licensed under the terms of the GNU GPL, version 2.  See
  * the COPYING file in the top-level directory.
  *
+ * Contributions after 2011-10-25 are licensed under the terms of the
+ * GNU GPL, version 2 or (at your option) any later version.
  */
 
 #include "qemu-common.h"
diff --git a/block-migration.c b/block-migration.c
index 0bff075..32c2eea 100644
--- a/block-migration.c
+++ b/block-migration.c
@@ -9,6 +9,8 @@
  * This work is licensed under the terms of the GNU GPL, version 2.  See
  * the COPYING file in the top-level directory.
  *
+ * Contributions after 2011-10-25 are licensed under the terms of the
+ * GNU GPL, version 2 or (at your option) any later version.
  */
 
 #include "qemu-common.h"
diff --git a/block/raw-posix-aio.h b/block/raw-posix-aio.h
index dfc63b8..d6d7275 100644
--- a/block/raw-posix-aio.h
+++ b/block/raw-posix-aio.h
@@ -9,6 +9,8 @@
  * This work is licensed under the terms of the GNU GPL, version 2.  See
  * the COPYING file in the top-level directory.
  *
+ * Contributions after 2011-10-25 are licensed under the terms of the
+ * GNU GPL, version 2 or (at your option) any later version.
  */
 #ifndef QEMU_RAW_POSIX_AIO_H
 #define QEMU_RAW_POSIX_AIO_H
diff --git a/block/rbd.c b/block/rbd.c
index 3068c82..b726c80 100644
--- a/block/rbd.c
+++ b/block/rbd.c
@@ -7,6 +7,8 @@
  * This work is licensed under the terms of the GNU GPL, version 2.  See
  * the COPYING file in the top-level directory.
  *
+ * Contributions after 2011-10-25 are licensed under the terms of the
+ * GNU GPL, version 2 or (at your option) any later version.
  */
 
 #include 
diff --git a/block/sheepdog.c b/block/sheepdog.c
index ae857e2..d69795a 100644
--- a/block/sheepdog.c
+++ b/block/sheepdog.c
@@ -7,6 +7,9 @@
  *
  * You should have received a copy of the GNU General Public License
  * along wit

Re: [Qemu-devel] [PATCH] [v3] hw/arm_gic.c: Fix save/load of irq_target array

2011-10-21 Thread Dmitry Koshelev
On Fri, Oct 21, 2011 at 3:42 PM, Andreas Färber  wrote:
> Am 20.10.2011 12:48, schrieb Dmitry Koshelev:
>> irq_target array saving/loading is in the wrong loop.
>> Version bump.
>>
>> Signed-off-by: Dmitry Koshelev 
>
> Acked-by: Andreas Färber 
>
> Applies cleanly now.
>
> Is there a particular use case that was broken before and works now, or
> did this turn up during code review only?

There is a use case but it's complicated and involves proprietary software.

>
> Andreas
>
>> ---
>>  hw/arm_gic.c |   16 
>>  1 files changed, 8 insertions(+), 8 deletions(-)
>>
>> diff --git a/hw/arm_gic.c b/hw/arm_gic.c
>> index 83213dd..8dd8742 100644
>> --- a/hw/arm_gic.c
>> +++ b/hw/arm_gic.c
>> @@ -658,9 +658,6 @@ static void gic_save(QEMUFile *f, void *opaque)
>>      qemu_put_be32(f, s->enabled);
>>      for (i = 0; i < NUM_CPU(s); i++) {
>>          qemu_put_be32(f, s->cpu_enabled[i]);
>> -#ifndef NVIC
>> -        qemu_put_be32(f, s->irq_target[i]);
>> -#endif
>>          for (j = 0; j < 32; j++)
>>              qemu_put_be32(f, s->priority1[j][i]);
>>          for (j = 0; j < GIC_NIRQ; j++)
>> @@ -674,6 +671,9 @@ static void gic_save(QEMUFile *f, void *opaque)
>>          qemu_put_be32(f, s->priority2[i]);
>>      }
>>      for (i = 0; i < GIC_NIRQ; i++) {
>> +#ifndef NVIC
>> +        qemu_put_be32(f, s->irq_target[i]);
>> +#endif
>>          qemu_put_byte(f, s->irq_state[i].enabled);
>>          qemu_put_byte(f, s->irq_state[i].pending);
>>          qemu_put_byte(f, s->irq_state[i].active);
>> @@ -689,15 +689,12 @@ static int gic_load(QEMUFile *f, void *opaque, int 
>> version_id)
>>      int i;
>>      int j;
>>
>> -    if (version_id != 1)
>> +    if (version_id != 2)
>>          return -EINVAL;
>>
>>      s->enabled = qemu_get_be32(f);
>>      for (i = 0; i < NUM_CPU(s); i++) {
>>          s->cpu_enabled[i] = qemu_get_be32(f);
>> -#ifndef NVIC
>> -        s->irq_target[i] = qemu_get_be32(f);
>> -#endif
>>          for (j = 0; j < 32; j++)
>>              s->priority1[j][i] = qemu_get_be32(f);
>>          for (j = 0; j < GIC_NIRQ; j++)
>> @@ -711,6 +708,9 @@ static int gic_load(QEMUFile *f, void *opaque, int 
>> version_id)
>>          s->priority2[i] = qemu_get_be32(f);
>>      }
>>      for (i = 0; i < GIC_NIRQ; i++) {
>> +#ifndef NVIC
>> +        s->irq_target[i] = qemu_get_be32(f);
>> +#endif
>>          s->irq_state[i].enabled = qemu_get_byte(f);
>>          s->irq_state[i].pending = qemu_get_byte(f);
>>          s->irq_state[i].active = qemu_get_byte(f);
>> @@ -739,5 +739,5 @@ static void gic_init(gic_state *s)
>>      }
>>      memory_region_init_io(&s->iomem, &gic_dist_ops, s, "gic_dist", 0x1000);
>>      gic_reset(s);
>> -    register_savevm(NULL, "arm_gic", -1, 1, gic_save, gic_load, s);
>> +    register_savevm(NULL, "arm_gic", -1, 2, gic_save, gic_load, s);
>>  }
>
>
> --
> SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg, Germany
> GF: Jeff Hawn, Jennifer Guild, Felix Imendörffer; HRB 16746, AG Nürnberg
>



Re: [Qemu-devel] [PATCH 11/35] scsi-disk: support READ DVD STRUCTURE

2011-10-21 Thread Paolo Bonzini

On 10/21/2011 03:32 PM, Kevin Wolf wrote:

2) let ide-cd create its own SCSI bus and act as an adaptor, similar to
>  USB devices.  There would still be duplication for commands that do DMA
>  in multiple steps; I think READ CD is the only one.
>
>  3) create a separate API just for the purpose of sharing code between
>  ATAPI and SCSI (your "can we share some parts even now", basically).
>
>  I think I'm leaning towards (3), but I don't think it makes sense to do
>  it now unless someone is interested in implementing for example CD
>  burning support.  However, I'm leaning towards that also because I
>  honestly have no idea how hard (2) would be.

Which gives me the impression that your feeling is (as well as mine)
that (2) would give us the nicer result and is probably the Right Thing
to do long-term.


Long term, yes.  Now, probably not (not until the QOM situation becomes 
clearer, that is).


It would also get you CD recorder passthrough, by composing scsi-generic 
or scsi-block within the IDE drive.



Though at the same time I agree that I don't have an idea of how hard
this would be and if it would be worth the effort. And with the current
qdev that doesn't allow device composition it might even get really ugly.

It's a hard question, but ignoring it is probably not a solution.


I agree.  On the other hand, the ATAPI code is changed rarely.  If it 
had been kept in sync in the past, I would not have touched it at all. 
I have never tried using >4.7 GB DVD images, but perhaps they just work 
and besides burning, they would be the only interesting use case.


Paolo



Re: [Qemu-devel] [PATCH 11/35] scsi-disk: support READ DVD STRUCTURE

2011-10-21 Thread Kevin Wolf
Am 21.10.2011 15:12, schrieb Paolo Bonzini:
> On 10/21/2011 01:42 PM, Kevin Wolf wrote:
>> There is only one 'goto fail', all other places have a direct return -1.
>> It would be good to be consistent.
>>
>> Also, as this is mostly a refactored copy from the ATAPI code, I wonder
>> what our long-term plan is. At which point will we be able to unify what
>> we're duplicating right now? Can we share some parts even now?
> 
> That's a tricky question.  I think there are three choices:
> 
> 1) use SCSI as the sole interface exposed by the block layer (with an 
> adaptor).  There would be a common implementation of SCSI for 
> SCSI-oblivious devices, and other devices (hdev, sg, iscsi) could just 
> reason in terms of SCSI.  You could stack the common implementations 
> (hard drive and CD-ROM) on top of hdev/iscsi or use passthrough.  This 
> however is wrong IMHO because some bits of SCSI code really do deal with 
> guest state, for example the tray.
> 
> 2) let ide-cd create its own SCSI bus and act as an adaptor, similar to 
> USB devices.  There would still be duplication for commands that do DMA 
> in multiple steps; I think READ CD is the only one.
> 
> 3) create a separate API just for the purpose of sharing code between 
> ATAPI and SCSI (your "can we share some parts even now", basically).
> 
> 
> I think I'm leaning towards (3), but I don't think it makes sense to do 
> it now unless someone is interested in implementing for example CD 
> burning support.  However, I'm leaning towards that also because I 
> honestly have no idea how hard (2) would be.

Which gives me the impression that your feeling is (as well as mine)
that (2) would give us the nicer result and is probably the Right Thing
to do long-term.

Though at the same time I agree that I don't have an idea of how hard
this would be and if it would be worth the effort. And with the current
qdev that doesn't allow device composition it might even get really ugly.

It's a hard question, but ignoring it is probably not a solution.

Kevin



Re: [Qemu-devel] [Question] dump memory when host pci device is used by guest

2011-10-21 Thread Jan Kiszka
On 2011-10-21 15:02, Dave Anderson wrote:
> 
> 
> - Original Message -
>> At 10/21/2011 03:11 PM, Jan Kiszka Write:
>>> On 2011-10-20 12:03, Wen Congyang wrote:
 At 10/20/2011 05:41 PM, Jan Kiszka Write:
> On 2011-10-20 03:22, Wen Congyang wrote:
 I didn't read full story but 'crash' is used for investigating kernel 
 core generated
 by kdump for several years. Considering support service guys, virsh 
 dump should support
 a format for crash because they can't work well at investigating 
 vmcore by gdb.

 crash has several functionality useful for them as 'show kerne log', 
 'focus on a cpu'
 'for-each-task', 'for-each-vma', 'extract ftrace log' etc.

 Anyway, if a man, who is not developper of qemu/kvm, should learn 2 
 tools for
 investigating kernel dump, it sounds harmful.
>>>
>>> Right, that's why everything (live debugging & crash analysis) should be
>>> consolidated on the long run over gdb. crash is architecturally obsolete
>>> today - not saying it is useless!
>>
>> I do not know why crash is obsoleted today. Is there a new better tool 
>> to instead
>> crash?
>
> I'm not aware of equally powerful (python) scripts for gdb as
> replacement, but I think it's worth starting a porting effort at
> some point.
>
>>
>> At least, I always use crash to live debugging & crash analysis.
>
> Then you may answer some questions to me:
>  - Can you attach to a remote target (kgdb, qemu, etc.) and how?

 No. crash's live debugging only can work the kernel is live. I can use it 
 get
 some var's value, or some other information from kernel. If kernel panics,
 we can use gdb to attach to a remote target as you said. But on end user 
 machine,
 we can not do it, we should dump the memory into a file and analyze it in 
 another
 machine while the end user's guest can be restart.

>  - Can you use it with latest gdb versions or is the gdb functionality
>hard-wired due to an embedded gdb core in crash (that's how I
>understood Christoph's reply to this topic)

 If I use crash, I can not use latest gdb versions. Do we always need to use
 the latest gdb versions? Currently, gdb-7.0 is embedded into crash, and it
 is enough to me. If the gdb embedded into crash cannot anaylze the vmcore, 
 I
 think we can update it and rebuild crash.
>>>
>>> crash is simply designed the wrong way around (from today's
>>> perspective): it should augment upstream gdb instead of forking it.
>>
>> Cc Dave Anderson. He knows how crash uses gdb.
>>
>> I think that crash does not fork a task to execute gdb, and gdb is a
>> part of crash.
> 
> I'm not sure what the question is, but you can consider crash as a huge
> wrapper around its embedded gdb, which it invokes as "gdb vmlinux", and
> then takes over the user interface.  It doesn't have a clue as to what
> the memory source is, i.e., whether it's one of the almost 20 different
> dumpfile formats that it supports (including "virsh dump"), or if it's
> running against a live system.  It has its own command set, although
> you can enter some gdb commands, write gdb scripts, etc.  But the main
> purpose of the embedded gdb is for the crash-level sources to be able
> to gather data structure information, disassemble text, add-symbol-file
> kernel modules, and so on.  There is no kgdb remote linkage. 
> 
> It's currently embedding gdb-7.0, although as we speak I'm updating it
> to gdb-7.3.1 because the compiler guys have decided that dwarf4 should be
> used by default.
> 
> It would be kind of cool if there was a "/dev/mem"-like interface
> to a KVM guest's physical memory, so that you could sit on a KVM host
> and enter "crash vmlinux-of-guest /dev/mem-of-guest" in order to
> run live analysis of a guest.
> 
> Anyway, sorry if it doesn't meet your needs...

Yes, I'd prefer to have the added value of crash available with standard
gdb, specifically to reuse it for remote target debugging which is
fairly common in embedded scenarios and for guest debugging (via
qemu/kvm). I do not yet see that there is anything preventing this
except that it "needs to be done" - or collected from previous work:
there should be, e.g., dozens of gdb scripts circling around that
automate kernel module symbol loading with gdb.

We do have a proper remote debugging interface already, no need to
invent a new one for crash-on-qemu. We do lack complete x86 system-level
debugging support, but that's an absolutely generic gdb problem,
independent of Linux as a debugging target. And, AFAIK, we do not have
such issues with common non-x86 targets.

Jan

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



Re: [Qemu-devel] [PATCH 15/35] scsi: remove devs array from SCSIBus

2011-10-21 Thread Paolo Bonzini

On 10/21/2011 02:31 PM, Kevin Wolf wrote:

>  diff --git a/hw/esp.c b/hw/esp.c
>  index d3fb1c6..8e17005 100644
>  --- a/hw/esp.c
>  +++ b/hw/esp.c
>  @@ -217,7 +217,8 @@ static uint32_t get_cmd(ESPState *s, uint8_t *buf)
>s->async_len = 0;
>}
>
>  -if (target>= ESP_MAX_DEVS || !s->bus.devs[target]) {
>  +s->current_dev = scsi_device_find(&s->bus, target, 0);
>  +if (!s->current_dev) {
>// No such drive
>s->rregs[ESP_RSTAT] = 0;
>s->rregs[ESP_RINTR] = INTR_DC;
>  @@ -225,7 +226,6 @@ static uint32_t get_cmd(ESPState *s, uint8_t *buf)
>esp_raise_irq(s);
>return 0;
>}
>  -s->current_dev = s->bus.devs[target];
>return dmalen;
>}
>
>  @@ -236,6 +236,7 @@ static void do_busid_cmd(ESPState *s, uint8_t *buf, 
uint8_t busid)
>
>trace_esp_do_busid_cmd(busid);
>lun = busid&  7;
>  +s->current_dev = scsi_device_find(&s->bus, s->current_dev->id, lun);

This is new, and I can't see an explanation in the commit log.


It isn't really new; up until now the lun was hard-coded to zero and so 
s->current_dev could be set in get_cmd.  Now we have to delay it until 
do_busid_cmd because we actually have a place to pass the LUN.


That said, s->current_dev is never really used outside do_busid_cmd, so 
I can instead do something like:


-   s->current_req = scsi_req_new(s->current_dev, 0, lun, buf, NULL);
+   SCSIDevice *current_lun;
+
+   current_lun = scsi_device_find(&s->bus, 0, s->current_dev->id, lun);
+   s->current_req = scsi_req_new(current_lun, 0, lun, buf, NULL);

That would be the same as the code I have above.

Paolo



Re: [Qemu-devel] [PATCH 11/35] scsi-disk: support READ DVD STRUCTURE

2011-10-21 Thread Paolo Bonzini

On 10/21/2011 01:42 PM, Kevin Wolf wrote:

There is only one 'goto fail', all other places have a direct return -1.
It would be good to be consistent.

Also, as this is mostly a refactored copy from the ATAPI code, I wonder
what our long-term plan is. At which point will we be able to unify what
we're duplicating right now? Can we share some parts even now?


That's a tricky question.  I think there are three choices:

1) use SCSI as the sole interface exposed by the block layer (with an 
adaptor).  There would be a common implementation of SCSI for 
SCSI-oblivious devices, and other devices (hdev, sg, iscsi) could just 
reason in terms of SCSI.  You could stack the common implementations 
(hard drive and CD-ROM) on top of hdev/iscsi or use passthrough.  This 
however is wrong IMHO because some bits of SCSI code really do deal with 
guest state, for example the tray.


2) let ide-cd create its own SCSI bus and act as an adaptor, similar to 
USB devices.  There would still be duplication for commands that do DMA 
in multiple steps; I think READ CD is the only one.


3) create a separate API just for the purpose of sharing code between 
ATAPI and SCSI (your "can we share some parts even now", basically).



I think I'm leaning towards (3), but I don't think it makes sense to do 
it now unless someone is interested in implementing for example CD 
burning support.  However, I'm leaning towards that also because I 
honestly have no idea how hard (2) would be.


Paolo



Re: [Qemu-devel] [PATCH 11/35] scsi-disk: support READ DVD STRUCTURE

2011-10-21 Thread Paolo Bonzini

On 10/21/2011 01:42 PM, Kevin Wolf wrote:

>  +if (s->qdev.type != TYPE_ROM || !bdrv_is_inserted(s->bs)) {
>  +return -1;
>  +}
>  +if (s->tray_open || !bdrv_is_inserted(s->bs)) {
>  +scsi_check_condition(r, SENSE_CODE(NO_MEDIUM));
>  +return -1;
>  +}

You are checking twice for bdrv_is_inserted, which one do you really mean?


The first is bogus.


Also, format = 0xff should work even without a medium.


Will move the tray_open/bdrv_is_inserted/media_is_cd tests within the 
"if (format != 0xff)".



>  +if (media_is_cd(s)) {
>  +scsi_check_condition(r, SENSE_CODE(INCOMPATIBLE_FORMAT));
>  +return -1;
>  +}
>  +if (media != 0) {
>  +scsi_check_condition(r, SENSE_CODE(INCOMPATIBLE_FORMAT));
>  +return -1;
>  +}


media != 0 should return INVALID_FIELD too.

Paolo



Re: [Qemu-devel] [PATCH 12/35] scsi-disk: report media changed via GET EVENT STATUS NOTIFICATION

2011-10-21 Thread Paolo Bonzini

On 10/21/2011 01:54 PM, Kevin Wolf wrote:

This adds support for media change notification via the GET EVENT STATUS
>  NOTIFICATION command, used by Linux versions 2.6.38 and newer.
>
>  Signed-off-by: Paolo Bonzini

Looks good, but the ATAPI version of the code is somewhat nicer to read.


Yeah, on the other hand even the ATAPI version has a mix of structs and 
buffers (in event_status_media, which also assumes sizeof 
gesn_event_header == 4).


Paolo



Re: [Qemu-devel] [Question] dump memory when host pci device is used by guest

2011-10-21 Thread Dave Anderson


- Original Message -
> At 10/21/2011 03:11 PM, Jan Kiszka Write:
> > On 2011-10-20 12:03, Wen Congyang wrote:
> >> At 10/20/2011 05:41 PM, Jan Kiszka Write:
> >>> On 2011-10-20 03:22, Wen Congyang wrote:
> >> I didn't read full story but 'crash' is used for investigating kernel 
> >> core generated
> >> by kdump for several years. Considering support service guys, virsh 
> >> dump should support
> >> a format for crash because they can't work well at investigating 
> >> vmcore by gdb.
> >>
> >> crash has several functionality useful for them as 'show kerne log', 
> >> 'focus on a cpu'
> >> 'for-each-task', 'for-each-vma', 'extract ftrace log' etc.
> >>
> >> Anyway, if a man, who is not developper of qemu/kvm, should learn 2 
> >> tools for
> >> investigating kernel dump, it sounds harmful.
> >
> > Right, that's why everything (live debugging & crash analysis) should be
> > consolidated on the long run over gdb. crash is architecturally obsolete
> > today - not saying it is useless!
> 
>  I do not know why crash is obsoleted today. Is there a new better tool 
>  to instead
>  crash?
> >>>
> >>> I'm not aware of equally powerful (python) scripts for gdb as
> >>> replacement, but I think it's worth starting a porting effort at
> >>> some point.
> >>>
> 
>  At least, I always use crash to live debugging & crash analysis.
> >>>
> >>> Then you may answer some questions to me:
> >>>  - Can you attach to a remote target (kgdb, qemu, etc.) and how?
> >>
> >> No. crash's live debugging only can work the kernel is live. I can use it 
> >> get
> >> some var's value, or some other information from kernel. If kernel panics,
> >> we can use gdb to attach to a remote target as you said. But on end user 
> >> machine,
> >> we can not do it, we should dump the memory into a file and analyze it in 
> >> another
> >> machine while the end user's guest can be restart.
> >>
> >>>  - Can you use it with latest gdb versions or is the gdb functionality
> >>>hard-wired due to an embedded gdb core in crash (that's how I
> >>>understood Christoph's reply to this topic)
> >>
> >> If I use crash, I can not use latest gdb versions. Do we always need to use
> >> the latest gdb versions? Currently, gdb-7.0 is embedded into crash, and it
> >> is enough to me. If the gdb embedded into crash cannot anaylze the vmcore, 
> >> I
> >> think we can update it and rebuild crash.
> > 
> > crash is simply designed the wrong way around (from today's
> > perspective): it should augment upstream gdb instead of forking it.
> 
> Cc Dave Anderson. He knows how crash uses gdb.
> 
> I think that crash does not fork a task to execute gdb, and gdb is a
> part of crash.

I'm not sure what the question is, but you can consider crash as a huge
wrapper around its embedded gdb, which it invokes as "gdb vmlinux", and
then takes over the user interface.  It doesn't have a clue as to what
the memory source is, i.e., whether it's one of the almost 20 different
dumpfile formats that it supports (including "virsh dump"), or if it's
running against a live system.  It has its own command set, although
you can enter some gdb commands, write gdb scripts, etc.  But the main
purpose of the embedded gdb is for the crash-level sources to be able
to gather data structure information, disassemble text, add-symbol-file
kernel modules, and so on.  There is no kgdb remote linkage. 

It's currently embedding gdb-7.0, although as we speak I'm updating it
to gdb-7.3.1 because the compiler guys have decided that dwarf4 should be
used by default.

It would be kind of cool if there was a "/dev/mem"-like interface
to a KVM guest's physical memory, so that you could sit on a KVM host
and enter "crash vmlinux-of-guest /dev/mem-of-guest" in order to
run live analysis of a guest.

Anyway, sorry if it doesn't meet your needs...

Dave



Re: [Qemu-devel] [PATCH 15/35] scsi: remove devs array from SCSIBus

2011-10-21 Thread Kevin Wolf
Am 13.10.2011 13:03, schrieb Paolo Bonzini:
> Change the devs array into a linked list, and add a scsi_device_find
> function to navigate the children list instead.  This lets the SCSI
> bus use more complex addressing.
> 
> scsi_device_find may return another LUN on the same target if none is
> found that matches exactly.
> 
> Signed-off-by: Paolo Bonzini 
> ---
>  hw/esp.c |5 +++--
>  hw/lsi53c895a.c  |   22 +++---
>  hw/qdev.h|2 +-
>  hw/scsi-bus.c|   53 ++---
>  hw/scsi.h|3 +--
>  hw/spapr_vscsi.c |   14 ++
>  6 files changed, 48 insertions(+), 51 deletions(-)
> 
> diff --git a/hw/esp.c b/hw/esp.c
> index d3fb1c6..8e17005 100644
> --- a/hw/esp.c
> +++ b/hw/esp.c
> @@ -217,7 +217,8 @@ static uint32_t get_cmd(ESPState *s, uint8_t *buf)
>  s->async_len = 0;
>  }
>  
> -if (target >= ESP_MAX_DEVS || !s->bus.devs[target]) {
> +s->current_dev = scsi_device_find(&s->bus, target, 0);
> +if (!s->current_dev) {
>  // No such drive
>  s->rregs[ESP_RSTAT] = 0;
>  s->rregs[ESP_RINTR] = INTR_DC;
> @@ -225,7 +226,6 @@ static uint32_t get_cmd(ESPState *s, uint8_t *buf)
>  esp_raise_irq(s);
>  return 0;
>  }
> -s->current_dev = s->bus.devs[target];
>  return dmalen;
>  }
>  
> @@ -236,6 +236,7 @@ static void do_busid_cmd(ESPState *s, uint8_t *buf, 
> uint8_t busid)
>  
>  trace_esp_do_busid_cmd(busid);
>  lun = busid & 7;
> +s->current_dev = scsi_device_find(&s->bus, s->current_dev->id, lun);

This is new, and I can't see an explanation in the commit log.

Kevin



Re: [Qemu-devel] [PATCH 13/35] scsi: move tcq/ndev to SCSIBusOps (now SCSIBusInfo)

2011-10-21 Thread Paolo Bonzini

On 10/21/2011 02:01 PM, Kevin Wolf wrote:

>
>  -static const struct SCSIBusOps vscsi_scsi_ops = {
>  +static const struct SCSIBusInfo vscsi_scsi_info = {
>  +.tcq = true,
>  +.ndev = 63, /* logical unit addressing format */

This is a change from VSCSI_REQ_LIMIT = 24. This may be a bugfix or not
- I don't know the hardware - but it's matter for a separate patch.


Ok, will leave 24.

Paolo



Re: [Qemu-devel] [PATCH 13/35] scsi: move tcq/ndev to SCSIBusOps (now SCSIBusInfo)

2011-10-21 Thread Kevin Wolf
Am 13.10.2011 13:03, schrieb Paolo Bonzini:
> Signed-off-by: Paolo Bonzini 
> ---
>  hw/esp.c |7 +--
>  hw/lsi53c895a.c  |9 ++---
>  hw/scsi-bus.c|   27 ---
>  hw/scsi-disk.c   |2 +-
>  hw/scsi.h|   11 +--
>  hw/spapr_vscsi.c |8 +---
>  hw/usb-msd.c |7 +--
>  7 files changed, 39 insertions(+), 32 deletions(-)
> 
> diff --git a/hw/esp.c b/hw/esp.c
> index 697c2c5..d3fb1c6 100644
> --- a/hw/esp.c
> +++ b/hw/esp.c
> @@ -720,7 +720,10 @@ void esp_init(target_phys_addr_t espaddr, int it_shift,
>  *dma_enable = qdev_get_gpio_in(dev, 1);
>  }
>  
> -static const struct SCSIBusOps esp_scsi_ops = {
> +static const struct SCSIBusInfo esp_scsi_info = {
> +.tcq = false,
> +.ndev = ESP_MAX_DEVS,
> +
>  .transfer_data = esp_transfer_data,
>  .complete = esp_command_complete,
>  .cancel = esp_request_cancelled
> @@ -740,7 +743,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_scsi_ops);
> +scsi_bus_new(&s->bus, &dev->qdev, &esp_scsi_info);
>  return scsi_bus_legacy_handle_cmdline(&s->bus);
>  }
>  
> diff --git a/hw/lsi53c895a.c b/hw/lsi53c895a.c
> index e077ec0..4eeb496 100644
> --- a/hw/lsi53c895a.c
> +++ b/hw/lsi53c895a.c
> @@ -1686,7 +1686,7 @@ static void lsi_reg_writeb(LSIState *s, int offset, 
> uint8_t val)
>  DeviceState *dev;
>  int id;
>  
> -for (id = 0; id < s->bus.ndev; id++) {
> +for (id = 0; id < LSI_MAX_DEVS; id++) {
>  if (s->bus.devs[id]) {
>  dev = &s->bus.devs[id]->qdev;
>  dev->info->reset(dev);
> @@ -2091,7 +2091,10 @@ static int lsi_scsi_uninit(PCIDevice *d)
>  return 0;
>  }
>  
> -static const struct SCSIBusOps lsi_scsi_ops = {
> +static const struct SCSIBusInfo lsi_scsi_info = {
> +.tcq = true,
> +.ndev = LSI_MAX_DEVS,
> +
>  .transfer_data = lsi_transfer_data,
>  .complete = lsi_command_complete,
>  .cancel = lsi_request_cancelled
> @@ -2118,7 +2121,7 @@ static int lsi_scsi_init(PCIDevice *dev)
>  pci_register_bar(&s->dev, 2, PCI_BASE_ADDRESS_SPACE_MEMORY, &s->ram_io);
>  QTAILQ_INIT(&s->queue);
>  
> -scsi_bus_new(&s->bus, &dev->qdev, 1, LSI_MAX_DEVS, &lsi_scsi_ops);
> +scsi_bus_new(&s->bus, &dev->qdev, &lsi_scsi_info);
>  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 867b1a8..d9d4e18 100644
> --- a/hw/scsi-bus.c
> +++ b/hw/scsi-bus.c
> @@ -24,14 +24,11 @@ static struct BusInfo scsi_bus_info = {
>  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,
> -  const SCSIBusOps *ops)
> +void scsi_bus_new(SCSIBus *bus, DeviceState *host, const SCSIBusInfo *info)
>  {
>  qbus_create_inplace(&bus->qbus, &scsi_bus_info, host, NULL);
>  bus->busnr = next_scsi_bus++;
> -bus->tcq = tcq;
> -bus->ndev = ndev;
> -bus->ops = ops;
> +bus->info = info;
>  bus->qbus.allow_hotplug = 1;
>  }
>  
> @@ -43,12 +40,12 @@ static int scsi_qdev_init(DeviceState *qdev, DeviceInfo 
> *base)
>  int rc = -1;
>  
>  if (dev->id == -1) {
> -for (dev->id = 0; dev->id < bus->ndev; dev->id++) {
> +for (dev->id = 0; dev->id < bus->info->ndev; dev->id++) {
>  if (bus->devs[dev->id] == NULL)
>  break;
>  }
>  }
> -if (dev->id >= bus->ndev) {
> +if (dev->id >= bus->info->ndev) {
>  error_report("bad scsi device id: %d", dev->id);
>  goto err;
>  }
> @@ -120,7 +117,7 @@ int scsi_bus_legacy_handle_cmdline(SCSIBus *bus)
>  int res = 0, unit;
>  
>  loc_push_none(&loc);
> -for (unit = 0; unit < bus->ndev; unit++) {
> +for (unit = 0; unit < bus->info->ndev; unit++) {
>  dinfo = drive_get(IF_SCSI, bus->busnr, unit);
>  if (dinfo == NULL) {
>  continue;
> @@ -265,7 +262,7 @@ static bool scsi_target_emulate_inquiry(SCSITargetReq *r)
>  r->buf[2] = 5; /* Version */
>  r->buf[3] = 2 | 0x10; /* HiSup, response data format */
>  r->buf[4] = r->len - 5; /* Additional Length = (Len - 1) - 4 */
> -r->buf[7] = 0x10 | (r->req.bus->tcq ? 0x02 : 0); /* Sync, TCQ.  */
> +r->buf[7] = 0x10 | (r->req.bus->info->tcq ? 0x02 : 0); /* Sync, TCQ. 
>  */
>  memcpy(&r->buf[8], "QEMU", 8);
>  memcpy(&r->buf[16], "QEMU TARGET ", 16);
>  strncpy((char *) &r->buf[32], QEMU_VERSION, 4);
> @@ -1062,7 +1059,7 @@ void scsi_req_continue(SCSIRequest *req)
>  void scsi_req_data(SCSIRequest *req, int len)
>  {
>  trace_scsi_req_data(req->dev->id, req->lun, req->tag, len);
> -req->bus->ops->transfer_d

Re: [Qemu-devel] [RFC][PATCH 28/45] qemu-kvm: msix: Drop tracking of used vectors

2011-10-21 Thread Michael S. Tsirkin
On Fri, Oct 21, 2011 at 11:27:48AM +0200, Jan Kiszka wrote:
> On 2011-10-21 09:54, Michael S. Tsirkin wrote:
> > On Fri, Oct 21, 2011 at 09:09:10AM +0200, Jan Kiszka wrote:
> >> On 2011-10-21 00:02, Michael S. Tsirkin wrote:
> > Yes. But this still makes an API for acquiring per-vector resources a 
> > requirement.
> 
>  Yes, but a different one than current use/unuse.
> >>>
> >>> What's wrong with use/unuse as an API? It's already in place
> >>> and virtio calls it.
> >>
> >> Not for that purpose.
> >> It remains a useless API in the absence of KVM's
> >> requirements.
> >>
> > 
> > Sorry, I don't understand. This can acquire whatever resources
> > necessary. It does not seem to make sense to rip it out
> > only to add a different one back in.
> > 
> >>>
>  And it will be an
>  optional one, only for those devices that need to establish irq/eventfd
>  channels.
> 
>  Jan
> >>>
> >>> Not sure this should be up to the device.
> >>
> >> The device provides the fd. At least it acquires and associates it.
> >>
> >> Jan
> > 
> > It would surely be beneficial to be able to have a uniform
> > API so that devices don't need to be recoded to be moved
> > in this way.
> 
> The point is that the current API is useless for devices that do not
> have to declare any vector to the core.

Don't assigned devices want this as well?
They handle 0-address vectors specially, and
this hack absolutely doesn't belong in pci core ...

> By forcing them to call into
> that API, we solve no current problem automatically. We rather need
> associate_vector_with_x (and the reverse). And that only for device that
> have different backends than user space models.
> 
> Jan

I'll need to think about this, would prefer this series not
to get blocked on this issue. We more or less agreed
to add _use_all/unuse_all for now?

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



Re: [Qemu-devel] [PATCH 12/35] scsi-disk: report media changed via GET EVENT STATUS NOTIFICATION

2011-10-21 Thread Kevin Wolf
Am 13.10.2011 13:03, schrieb Paolo Bonzini:
> This adds support for media change notification via the GET EVENT STATUS
> NOTIFICATION command, used by Linux versions 2.6.38 and newer.
> 
> Signed-off-by: Paolo Bonzini 

Looks good, but the ATAPI version of the code is somewhat nicer to read.

Kevin



Re: [Qemu-devel] [PATCH] [v3] hw/arm_gic.c: Fix save/load of irq_target array

2011-10-21 Thread Andreas Färber
Am 20.10.2011 12:48, schrieb Dmitry Koshelev:
> irq_target array saving/loading is in the wrong loop.
> Version bump.
> 
> Signed-off-by: Dmitry Koshelev 

Acked-by: Andreas Färber 

Applies cleanly now.

Is there a particular use case that was broken before and works now, or
did this turn up during code review only?

Andreas

> ---
>  hw/arm_gic.c |   16 
>  1 files changed, 8 insertions(+), 8 deletions(-)
> 
> diff --git a/hw/arm_gic.c b/hw/arm_gic.c
> index 83213dd..8dd8742 100644
> --- a/hw/arm_gic.c
> +++ b/hw/arm_gic.c
> @@ -658,9 +658,6 @@ static void gic_save(QEMUFile *f, void *opaque)
>  qemu_put_be32(f, s->enabled);
>  for (i = 0; i < NUM_CPU(s); i++) {
>  qemu_put_be32(f, s->cpu_enabled[i]);
> -#ifndef NVIC
> -qemu_put_be32(f, s->irq_target[i]);
> -#endif
>  for (j = 0; j < 32; j++)
>  qemu_put_be32(f, s->priority1[j][i]);
>  for (j = 0; j < GIC_NIRQ; j++)
> @@ -674,6 +671,9 @@ static void gic_save(QEMUFile *f, void *opaque)
>  qemu_put_be32(f, s->priority2[i]);
>  }
>  for (i = 0; i < GIC_NIRQ; i++) {
> +#ifndef NVIC
> +qemu_put_be32(f, s->irq_target[i]);
> +#endif
>  qemu_put_byte(f, s->irq_state[i].enabled);
>  qemu_put_byte(f, s->irq_state[i].pending);
>  qemu_put_byte(f, s->irq_state[i].active);
> @@ -689,15 +689,12 @@ static int gic_load(QEMUFile *f, void *opaque, int 
> version_id)
>  int i;
>  int j;
>  
> -if (version_id != 1)
> +if (version_id != 2)
>  return -EINVAL;
>  
>  s->enabled = qemu_get_be32(f);
>  for (i = 0; i < NUM_CPU(s); i++) {
>  s->cpu_enabled[i] = qemu_get_be32(f);
> -#ifndef NVIC
> -s->irq_target[i] = qemu_get_be32(f);
> -#endif
>  for (j = 0; j < 32; j++)
>  s->priority1[j][i] = qemu_get_be32(f);
>  for (j = 0; j < GIC_NIRQ; j++)
> @@ -711,6 +708,9 @@ static int gic_load(QEMUFile *f, void *opaque, int 
> version_id)
>  s->priority2[i] = qemu_get_be32(f);
>  }
>  for (i = 0; i < GIC_NIRQ; i++) {
> +#ifndef NVIC
> +s->irq_target[i] = qemu_get_be32(f);
> +#endif
>  s->irq_state[i].enabled = qemu_get_byte(f);
>  s->irq_state[i].pending = qemu_get_byte(f);
>  s->irq_state[i].active = qemu_get_byte(f);
> @@ -739,5 +739,5 @@ static void gic_init(gic_state *s)
>  }
>  memory_region_init_io(&s->iomem, &gic_dist_ops, s, "gic_dist", 0x1000);
>  gic_reset(s);
> -register_savevm(NULL, "arm_gic", -1, 1, gic_save, gic_load, s);
> +register_savevm(NULL, "arm_gic", -1, 2, gic_save, gic_load, s);
>  }


-- 
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg, Germany
GF: Jeff Hawn, Jennifer Guild, Felix Imendörffer; HRB 16746, AG Nürnberg



Re: [Qemu-devel] [PATCH 11/35] scsi-disk: support READ DVD STRUCTURE

2011-10-21 Thread Kevin Wolf
Am 13.10.2011 13:03, schrieb Paolo Bonzini:
> Signed-off-by: Paolo Bonzini 
> ---
>  hw/scsi-disk.c |  101 
> +++-
>  1 files changed, 100 insertions(+), 1 deletions(-)
> 
> diff --git a/hw/scsi-disk.c b/hw/scsi-disk.c
> index 1786c37..14db6a0 100644
> --- a/hw/scsi-disk.c
> +++ b/hw/scsi-disk.c
> @@ -576,10 +576,109 @@ static inline bool media_is_dvd(SCSIDiskState *s)
>  return nb_sectors > CD_MAX_SECTORS;
>  }
>  
> +static inline bool media_is_cd(SCSIDiskState *s)
> +{
> +uint64_t nb_sectors;
> +if (s->qdev.type != TYPE_ROM) {
> +return false;
> +}
> +if (!bdrv_is_inserted(s->bs)) {
> +return false;
> +}
> +bdrv_get_geometry(s->bs, &nb_sectors);
> +return nb_sectors <= CD_MAX_SECTORS;
> +}
> +
>  static int scsi_read_dvd_structure(SCSIDiskState *s, SCSIDiskReq *r,
> uint8_t *outbuf)
>  {
> -scsi_check_condition(r, SENSE_CODE(INVALID_OPCODE));
> +static const int rds_caps_size[5] = {
> +[0] = 2048 + 4,
> +[1] = 4 + 4,
> +[3] = 188 + 4,
> +[4] = 2048 + 4,
> +};
> +
> +uint8_t media = r->req.cmd.buf[1];
> +uint8_t layer = r->req.cmd.buf[6];
> +uint8_t format = r->req.cmd.buf[7];
> +int size = -1;
> +
> +if (s->qdev.type != TYPE_ROM || !bdrv_is_inserted(s->bs)) {
> +return -1;
> +}
> +if (s->tray_open || !bdrv_is_inserted(s->bs)) {
> +scsi_check_condition(r, SENSE_CODE(NO_MEDIUM));
> +return -1;
> +}

You are checking twice for bdrv_is_inserted, which one do you really mean?

Also, format = 0xff should work even without a medium.

> +if (media_is_cd(s)) {
> +scsi_check_condition(r, SENSE_CODE(INCOMPATIBLE_FORMAT));
> +return -1;
> +}
> +if (media != 0) {
> +scsi_check_condition(r, SENSE_CODE(INCOMPATIBLE_FORMAT));
> +return -1;
> +}
> +
> +if (format != 0xff) {
> +if (format >= sizeof(rds_caps_size) / sizeof(rds_caps_size[0])) {

osdep.h has an ARRAY_SIZE() macro.

> +return -1;
> +}
> +size = rds_caps_size[format];
> +memset(outbuf, 0, size);
> +}
> +
> +switch (format) {
> +case 0x00: {
> +/* Physical format information */
> +uint64_t nb_sectors;
> +if (layer != 0)
> +goto fail;

Braces

> +bdrv_get_geometry(s->bs, &nb_sectors);
> +
> +outbuf[4] = 1;   /* DVD-ROM, part version 1 */
> +outbuf[5] = 0xf; /* 120mm disc, minimum rate unspecified */
> +outbuf[6] = 1;   /* one layer, read-only (per MMC-2 spec) */
> +outbuf[7] = 0;   /* default densities */
> +
> +stl_be_p(&outbuf[12], (nb_sectors >> 2) - 1); /* end sector */
> +stl_be_p(&outbuf[16], (nb_sectors >> 2) - 1); /* l0 end sector */
> +break;
> +}
> +
> +case 0x01: /* DVD copyright information, all zeros */
> +break;
> +
> +case 0x03: /* BCA information - invalid field for no BCA info */
> +return -1;
> +
> +case 0x04: /* DVD disc manufacturing information, all zeros */
> +break;
> +
> +case 0xff: { /* List capabilities */
> +int i;
> +size = 4;
> +for (i = 0; i < sizeof(rds_caps_size) / sizeof(rds_caps_size[0]); 
> i++) {

ARRAY_SIZE() again

> +if (!rds_caps_size[i]) {
> +continue;
> +}
> +outbuf[size] = i;
> +outbuf[size + 1] = 0x40; /* Not writable, readable */
> +stw_be_p(&outbuf[size + 2], rds_caps_size[i]);
> +size += 4;
> +}
> +break;
> + }
> +
> +default:
> +return -1;
> +}
> +
> +/* Size of buffer, not including 2 byte size field */
> +stw_be_p(outbuf, size - 2);
> +return size;
> +
> +fail:
>  return -1;
>  }

There is only one 'goto fail', all other places have a direct return -1.
It would be good to be consistent.

Also, as this is mostly a refactored copy from the ATAPI code, I wonder
what our long-term plan is. At which point will we be able to unify what
we're duplicating right now? Can we share some parts even now?

Kevin



[Qemu-devel] [PATCH] fw_cfg: Use g_file_get_contents instead of multiple fread() calls

2011-10-21 Thread Pavel Borzenkov
Signed-off-by: Pavel Borzenkov 
---
 hw/fw_cfg.c |  100 ++-
 1 files changed, 37 insertions(+), 63 deletions(-)

diff --git a/hw/fw_cfg.c b/hw/fw_cfg.c
index 8df265c..d2400f5 100644
--- a/hw/fw_cfg.c
+++ b/hw/fw_cfg.c
@@ -60,71 +60,55 @@ struct FWCfgState {
 #define JPG_FILE 0
 #define BMP_FILE 1
 
-static FILE *probe_splashfile(char *filename, int *file_sizep, int *file_typep)
+static char *read_splashfile(char *filename, int *file_sizep, int *file_typep)
 {
-FILE *fp = NULL;
-int fop_ret;
-int file_size;
+GError *err = NULL;
+gboolean res;
+gchar *content;
 int file_type = -1;
-unsigned char buf[2] = {0, 0};
-unsigned int filehead_value = 0;
+unsigned int filehead = 0;
 int bmp_bpp;
 
-fp = fopen(filename, "rb");
-if (fp == NULL) {
-error_report("failed to open file '%s'.", filename);
-return fp;
+res = g_file_get_contents(filename, &content, (gsize *)file_sizep, &err);
+if (res == FALSE) {
+error_report("falied to read file '%s'", filename);
+g_error_free(err);
+return NULL;
 }
+
 /* check file size */
-fseek(fp, 0L, SEEK_END);
-file_size = ftell(fp);
-if (file_size < 2) {
-error_report("file size is less than 2 bytes '%s'.", filename);
-fclose(fp);
-fp = NULL;
-return fp;
+if (*file_sizep < 30) {
+error_report("file size is less than 30 bytes '%s'", filename);
+g_free(content);
+return NULL;
 }
+
 /* check magic ID */
-fseek(fp, 0L, SEEK_SET);
-fop_ret = fread(buf, 1, 2, fp);
-if (fop_ret != 2) {
-error_report("Could not read header from '%s': %s",
- filename, strerror(errno));
-fclose(fp);
-fp = NULL;
-return fp;
-}
-filehead_value = (buf[0] + (buf[1] << 8)) & 0x;
-if (filehead_value == 0xd8ff) {
+filehead = ((content[0] & 0xff) + (content[1] << 8)) & 0x;
+if (filehead == 0xd8ff) {
 file_type = JPG_FILE;
+} else if (filehead == 0x4d42) {
+file_type = BMP_FILE;
 } else {
-if (filehead_value == 0x4d42) {
-file_type = BMP_FILE;
-}
-}
-if (file_type < 0) {
-error_report("'%s' not jpg/bmp file,head:0x%x.",
- filename, filehead_value);
-fclose(fp);
-fp = NULL;
-return fp;
+error_report("'%s' not jpg/bmp file, head:0x%x.", filename, filehead);
+g_free(content);
+return NULL;
 }
+
 /* check BMP bpp */
 if (file_type == BMP_FILE) {
-fseek(fp, 28, SEEK_SET);
-fop_ret = fread(buf, 1, 2, fp);
-bmp_bpp = (buf[0] + (buf[1] << 8)) & 0x;
+bmp_bpp = (content[28] + (content[29] << 8)) & 0x;
 if (bmp_bpp != 24) {
 error_report("only 24bpp bmp file is supported.");
-fclose(fp);
-fp = NULL;
-return fp;
+g_free(content);
+return NULL;
 }
 }
+
 /* return values */
-*file_sizep = file_size;
 *file_typep = file_type;
-return fp;
+
+return content;
 }
 
 static void fw_cfg_bootsplash(FWCfgState *s)
@@ -132,9 +116,7 @@ static void fw_cfg_bootsplash(FWCfgState *s)
 int boot_splash_time = -1;
 const char *boot_splash_filename = NULL;
 char *p;
-char *filename;
-FILE *fp;
-int fop_ret;
+char *filename, *file_data;
 int file_size;
 int file_type = -1;
 const char *temp;
@@ -174,27 +156,19 @@ static void fw_cfg_bootsplash(FWCfgState *s)
 error_report("failed to find file '%s'.", boot_splash_filename);
 return;
 }
-/* probing the file */
-fp = probe_splashfile(filename, &file_size, &file_type);
-if (fp == NULL) {
+
+/* loading file data */
+file_data = read_splashfile(filename, &file_size, &file_type);
+if (file_data == NULL) {
 g_free(filename);
 return;
 }
-/* loading file data */
 if (boot_splash_filedata != NULL) {
 g_free(boot_splash_filedata);
 }
-boot_splash_filedata = g_malloc(file_size);
+boot_splash_filedata = (uint8_t *)file_data;
 boot_splash_filedata_size = file_size;
-fseek(fp, 0L, SEEK_SET);
-fop_ret = fread(boot_splash_filedata, 1, file_size, fp);
-if (fop_ret != file_size) {
-error_report("failed to read data from '%s'.",
- boot_splash_filename);
-fclose(fp);
-return;
-}
-fclose(fp);
+
 /* insert data */
 if (file_type == JPG_FILE) {
 fw_cfg_add_file(s, "bootsplash.jpg",
-- 
1.7.0.4




[Qemu-devel] [PATCH] block: Add !qemu_in_coroutine() assertions to synchronous functions

2011-10-21 Thread Kevin Wolf
When adding the locking, we came to the conclusion that converting
read/write/flush/discard to coroutines should be enough because everything else
isn't called in coroutine context. Add assertions to spell this assumption out
and ensure that it won't be broken accidentally.

And even if we have missed converting a valid case, aborting qemu is better
than corrupting images.

Signed-off-by: Kevin Wolf 
---
 block.c |   35 +++
 1 files changed, 35 insertions(+), 0 deletions(-)

diff --git a/block.c b/block.c
index 70aab63..11c7f91 100644
--- a/block.c
+++ b/block.c
@@ -849,6 +849,8 @@ int bdrv_check(BlockDriverState *bs, BdrvCheckResult *res)
 return -ENOTSUP;
 }
 
+assert(!qemu_in_coroutine());
+
 memset(res, 0, sizeof(*res));
 return bs->drv->bdrv_check(bs, res);
 }
@@ -867,6 +869,8 @@ int bdrv_commit(BlockDriverState *bs)
 char filename[1024];
 BlockDriverState *bs_rw, *bs_ro;
 
+assert(!qemu_in_coroutine());
+
 if (!drv)
 return -ENOMEDIUM;
 
@@ -926,6 +930,7 @@ int bdrv_commit(BlockDriverState *bs)
 }
 }
 
+assert(!qemu_in_coroutine());
 if (drv->bdrv_make_empty) {
 ret = drv->bdrv_make_empty(bs);
 bdrv_flush(bs);
@@ -983,6 +988,8 @@ int bdrv_change_backing_file(BlockDriverState *bs,
 {
 BlockDriver *drv = bs->drv;
 
+assert(!qemu_in_coroutine());
+
 if (drv->bdrv_change_backing_file != NULL) {
 return drv->bdrv_change_backing_file(bs, backing_file, backing_fmt);
 } else {
@@ -1323,6 +1330,8 @@ int bdrv_truncate(BlockDriverState *bs, int64_t offset)
 return -EACCES;
 if (bdrv_in_use(bs))
 return -EBUSY;
+
+assert(!qemu_in_coroutine());
 ret = drv->bdrv_truncate(bs, offset);
 if (ret == 0) {
 ret = refresh_total_sectors(bs, offset >> BDRV_SECTOR_BITS);
@@ -1792,6 +1801,8 @@ int bdrv_is_allocated(BlockDriverState *bs, int64_t 
sector_num, int nb_sectors,
 *pnum = (n < nb_sectors) ? (n) : (nb_sectors);
 return 1;
 }
+
+assert(!qemu_in_coroutine());
 return bs->drv->bdrv_is_allocated(bs, sector_num, nb_sectors, pnum);
 }
 
@@ -2050,12 +2061,16 @@ int bdrv_write_compressed(BlockDriverState *bs, int64_t 
sector_num,
 set_dirty_bitmap(bs, sector_num, nb_sectors, 1);
 }
 
+assert(!qemu_in_coroutine());
 return drv->bdrv_write_compressed(bs, sector_num, buf, nb_sectors);
 }
 
 int bdrv_get_info(BlockDriverState *bs, BlockDriverInfo *bdi)
 {
 BlockDriver *drv = bs->drv;
+
+assert(!qemu_in_coroutine());
+
 if (!drv)
 return -ENOMEDIUM;
 if (!drv->bdrv_get_info)
@@ -2068,6 +2083,9 @@ int bdrv_save_vmstate(BlockDriverState *bs, const uint8_t 
*buf,
   int64_t pos, int size)
 {
 BlockDriver *drv = bs->drv;
+
+assert(!qemu_in_coroutine());
+
 if (!drv)
 return -ENOMEDIUM;
 if (drv->bdrv_save_vmstate)
@@ -2081,6 +2099,9 @@ int bdrv_load_vmstate(BlockDriverState *bs, uint8_t *buf,
   int64_t pos, int size)
 {
 BlockDriver *drv = bs->drv;
+
+assert(!qemu_in_coroutine());
+
 if (!drv)
 return -ENOMEDIUM;
 if (drv->bdrv_load_vmstate)
@@ -2149,6 +2170,9 @@ int bdrv_snapshot_create(BlockDriverState *bs,
  QEMUSnapshotInfo *sn_info)
 {
 BlockDriver *drv = bs->drv;
+
+assert(!qemu_in_coroutine());
+
 if (!drv)
 return -ENOMEDIUM;
 if (drv->bdrv_snapshot_create)
@@ -2164,6 +2188,8 @@ int bdrv_snapshot_goto(BlockDriverState *bs,
 BlockDriver *drv = bs->drv;
 int ret, open_ret;
 
+assert(!qemu_in_coroutine());
+
 if (!drv)
 return -ENOMEDIUM;
 if (drv->bdrv_snapshot_goto)
@@ -2187,6 +2213,9 @@ int bdrv_snapshot_goto(BlockDriverState *bs,
 int bdrv_snapshot_delete(BlockDriverState *bs, const char *snapshot_id)
 {
 BlockDriver *drv = bs->drv;
+
+assert(!qemu_in_coroutine());
+
 if (!drv)
 return -ENOMEDIUM;
 if (drv->bdrv_snapshot_delete)
@@ -2200,6 +2229,9 @@ int bdrv_snapshot_list(BlockDriverState *bs,
QEMUSnapshotInfo **psn_info)
 {
 BlockDriver *drv = bs->drv;
+
+assert(!qemu_in_coroutine());
+
 if (!drv)
 return -ENOMEDIUM;
 if (drv->bdrv_snapshot_list)
@@ -2213,6 +2245,9 @@ int bdrv_snapshot_load_tmp(BlockDriverState *bs,
 const char *snapshot_name)
 {
 BlockDriver *drv = bs->drv;
+
+assert(!qemu_in_coroutine());
+
 if (!drv) {
 return -ENOMEDIUM;
 }
-- 
1.7.6.4




[Qemu-devel] [PATCH] xen_disk: Always set feature-barrier = 1

2011-10-21 Thread Kevin Wolf
The synchronous .bdrv_flush callback doesn't exist any more and a device really
shouldn't poke into the block layer internals anyway. All drivers are supposed
to have a correctly working bdrv_flush, so let's just hard-code this.

Signed-off-by: Kevin Wolf 
---

I'm not sure what feature-barrier really means, but this is the closest thing
to what we used to do. Should this really be dependent on whether or not we are
using a writeback cache mode?

Also, someone should really get rid of that #include "block_int.h" in xen_disk.
Things defined there are not a device's business.

 hw/xen_disk.c |5 ++---
 1 files changed, 2 insertions(+), 3 deletions(-)

diff --git a/hw/xen_disk.c b/hw/xen_disk.c
index 8a9fac4..286bbac 100644
--- a/hw/xen_disk.c
+++ b/hw/xen_disk.c
@@ -620,7 +620,7 @@ static void blk_alloc(struct XenDevice *xendev)
 static int blk_init(struct XenDevice *xendev)
 {
 struct XenBlkDev *blkdev = container_of(xendev, struct XenBlkDev, xendev);
-int index, qflags, have_barriers, info = 0;
+int index, qflags, info = 0;
 
 /* read xenstore entries */
 if (blkdev->params == NULL) {
@@ -706,7 +706,6 @@ static int blk_init(struct XenDevice *xendev)
   blkdev->bs->drv ? blkdev->bs->drv->format_name : "-");
 blkdev->file_size = 0;
 }
-have_barriers = blkdev->bs->drv && blkdev->bs->drv->bdrv_flush ? 1 : 0;
 
 xen_be_printf(xendev, 1, "type \"%s\", fileproto \"%s\", filename \"%s\","
   " size %" PRId64 " (%" PRId64 " MB)\n",
@@ -714,7 +713,7 @@ static int blk_init(struct XenDevice *xendev)
   blkdev->file_size, blkdev->file_size >> 20);
 
 /* fill info */
-xenstore_write_be_int(&blkdev->xendev, "feature-barrier", have_barriers);
+xenstore_write_be_int(&blkdev->xendev, "feature-barrier", 1);
 xenstore_write_be_int(&blkdev->xendev, "info",info);
 xenstore_write_be_int(&blkdev->xendev, "sector-size", 
blkdev->file_blk);
 xenstore_write_be_int(&blkdev->xendev, "sectors",
-- 
1.7.6.4




[Qemu-devel] [Qemu-trivial] [PATCH] exec.c: Remove useless comment

2011-10-21 Thread 陳韋任
  As phys_ram_size had been removed since QEMU 0.12. Remove the useless
comment.

Signed-off-by: Chen Wen-Ren 
---
 exec.c |1 -
 1 files changed, 0 insertions(+), 1 deletions(-)

diff --git a/exec.c b/exec.c
index d0cbf15..fb21e76 100644
--- a/exec.c
+++ b/exec.c
@@ -472,7 +472,6 @@ static void code_gen_alloc(unsigned long tb_size)
 code_gen_buffer_size = tb_size;
 if (code_gen_buffer_size == 0) {
 #if defined(CONFIG_USER_ONLY)
-/* in user mode, phys_ram_size is not meaningful */
 code_gen_buffer_size = DEFAULT_CODE_GEN_BUFFER_SIZE;
 #else
 /* XXX: needs adjustments */
-- 
1.7.3.4



  1   2   >