Re: [Qemu-devel] [PATCHv3 1/6] ui/vnc: introduce VNC_DIRTY_PIXELS_PER_BIT macro

2014-01-06 Thread Peter Lieven
On 06.01.2014 07:52, Wenchao Xia wrote:
 @@ -781,10 +784,10 @@ static void vnc_dpy_copy(DisplayChangeListener *dcl,
   if ((s = w - w_lim) == 0)
   break;
   } else if (!x) {
 -s = (16 - (dst_x % 16));
 +s = (16 - (dst_x % VNC_DIRTY_PIXELS_PER_BIT));
 Should it be
 s = (VNC_DIRTY_PIXELS_PER_BIT - (dst_x % VNC_DIRTY_PIXELS_PER_BIT));
 ?


Thanks, you are right.

Peter



Re: [Qemu-devel] [PATCH] hw/misc/blob-loader: add a generic blob loader

2014-01-06 Thread Peter Maydell
On 6 January 2014 07:56, Peter Crosthwaite peter.crosthwa...@xilinx.com wrote:
 On Mon, Jan 6, 2014 at 5:41 PM, Peter Maydell peter.mayd...@linaro.org 
 wrote:
 That raises some more general design questions:
  * how is this expected to interact with rom blob loading, -machine 
 firmware=,
etc?

 I guess it's not. The behavior of -machine firmware= is machine
 specific, so a machine specific undefined behavior will occur if you
 have overlap issues. The two should not in any way inhibit each other.
 They are independent mechanisms.

 What are the guidelines for when to use one or the other?

 -machine firmware= if you want to load a firmware blob in a board
 specific way. This if you want to place a blob in memory at an
 arbitrary location on reset.

I guess I don't much like the way we're solving a problem by
adding yet another mechanism here rather than trying to produce
a design for blob loading that works for all the use cases we have.

thanks
-- PMM



Re: [Qemu-devel] [PATCH v1 2/3] qcow2: fix offset overflow

2014-01-06 Thread Hu Tao
On Mon, Dec 30, 2013 at 01:29:08PM +0800, Hu Tao wrote:
 When cluster size is big enough it can lead offset overflow
 in qcow2_alloc_clusters_at(). This patch fixes it.

ping. and be more descriptive:

The allocation each time is stopped at L2 table boundary(see handle_alloc()),
so the possible maximum bytes could be

  2^(cluster_bits - 3 + cluster_bits)

so int is safe for cluster_bits=17, unsafe otherwise.


 
 Signed-off-by: Hu Tao hu...@cn.fujitsu.com
 ---
  block/qcow2-refcount.c | 7 ++-
  1 file changed, 6 insertions(+), 1 deletion(-)
 
 diff --git a/block/qcow2-refcount.c b/block/qcow2-refcount.c
 index c974abe..b3ebb7f 100644
 --- a/block/qcow2-refcount.c
 +++ b/block/qcow2-refcount.c
 @@ -676,7 +676,12 @@ int qcow2_alloc_clusters_at(BlockDriverState *bs, 
 uint64_t offset,
  BDRVQcowState *s = bs-opaque;
  uint64_t cluster_index;
  uint64_t old_free_cluster_index;
 -int i, refcount, ret;
 +uint64_t i;
 +int refcount, ret;
 +
 +if (nb_clusters = 0) {
 +return 0;
 +}
  
  /* Check how many clusters there are free */
  cluster_index = offset  s-cluster_bits;
 -- 
 1.7.11.7
 



Re: [Qemu-devel] [PATCH resend] linux-user: Support the accept4 socketcall

2014-01-06 Thread Laurent Vivier

 Le 6 janvier 2014 à 02:57, André Hentschel n...@dawncrow.de a écrit :


 From: André Hentschel n...@dawncrow.de
 Cc: Riku Voipio riku.voi...@iki.fi
 Signed-off-by: André Hentschel n...@dawncrow.de
[...]
 diff --git a/linux-user/syscall_defs.h b/linux-user/syscall_defs.h
 index cf08db5..b36f99c 100644
 --- a/linux-user/syscall_defs.h
 +++ b/linux-user/syscall_defs.h
 @@ -27,6 +27,9 @@
 #define SOCKOP_getsockopt 15
 #define SOCKOP_sendmsg 16
 #define SOCKOP_recvmsg 17
 +#define SOCKOP_accept4 18
 +#define SOCKOP_recvmmsg 19
 +#define SOCKOP_sendmmsg 20

Don't add these both defines here as they are not used in this patch.

Regards,
Laurent

Re: [Qemu-devel] [PULL 0/2] OpenRISC patch queue for 1.8

2014-01-06 Thread Jia Liu
ping~~

On Sat, Dec 21, 2013 at 9:47 AM, Jia Liu pro...@gmail.com wrote:
 Hi Anthony,

 This is my OpenRISC patch queue for 1.8, it have been well tested, please 
 pull.

 Thanks to Richard Henderson, he made the LD/ST updated.
 Thanks to Stefan Weil, he fixed a typo.


 Regards,
 Jia


 The following changes since commit f8251db121c3f051b22a7536b97d160c30bcccd4:

   Merge remote-tracking branch 'agraf/tags/signed-ppc-for-upstream' into 
 staging (2013-12-19 17:03:17 -0800)

 are available in the git repository at:


   git://github.com/J-Liu/qemu.git or32

 for you to fetch changes up to 31ab4c235b7f7342f727fd835e732623753e1ffb:

   target-openrisc: Use new qemu_ld/st opcodes (2013-12-21 09:38:18 +0800)

 
 Richard Henderson (1):
   target-openrisc: Use new qemu_ld/st opcodes

 Stefan Weil (1):
   openrisc: Fix spelling in comment (transaltion - translation)

  target-openrisc/translate.c | 101 
 +++-
  1 file changed, 33 insertions(+), 68 deletions(-)



Re: [Qemu-devel] [PATCH resend] linux-user: Support the accept4 socketcall

2014-01-06 Thread Peter Maydell
On 6 January 2014 08:45, Laurent Vivier laur...@vivier.eu wrote:

 Le 6 janvier 2014 à 02:57, André Hentschel n...@dawncrow.de a écrit :
 diff --git a/linux-user/syscall_defs.h b/linux-user/syscall_defs.h
 index cf08db5..b36f99c 100644
 --- a/linux-user/syscall_defs.h
 +++ b/linux-user/syscall_defs.h
 @@ -27,6 +27,9 @@
 #define SOCKOP_getsockopt 15
 #define SOCKOP_sendmsg 16
 #define SOCKOP_recvmsg 17
 +#define SOCKOP_accept4 18
 +#define SOCKOP_recvmmsg 19
 +#define SOCKOP_sendmmsg 20

 Don't add these both defines here as they are not used in this patch.

It doesn't seem that unreasonable to add them. We add things
to the main syscall number #define list even if we aren't
actually implementing them, for example.

thanks
-- PMM



[Qemu-devel] [Bug 1265998] Re: vfio-pci passed Radeon 7870XT is unstable on first boot of a Windows 8.1 guest

2014-01-06 Thread Michał Węgrzynek
Sorry, I propably just was lucky. It doesn't work without hugepages
also. The only thing I can do to make the 7870XT operate correclty under
guest is to make it show

qemu-system-x86_64: vfio_dma_map(0x7f01db7deec0, 0xc, 0xaff4,
0x2aaac00c) = -16 (Device or resource busy)

errors on start.

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

Title:
  vfio-pci passed Radeon 7870XT is unstable on first boot of a Windows
  8.1 guest

Status in QEMU:
  New

Bug description:
  I'm passing a Radeon 7870XT to a Windows 8.1 guest. It works
  flawlessly (I tested it by a 12 hour Furmark run), but only on second
  lauch of the guest. On first launch after I get screen corruption on
  any 3D operation in guest (even showing a search box in Chrome) and
  the guest becomes unusable with constant driver resets to a point,
  when it grinds to a halt. At that moment I get about ~1K of log
  entries similar to

  sty 04 11:12:57 miner kernel: AMD-Vi: Event logged [IO_PAGE_FAULT 
device=01:00.0 domain=0x0002 address=0x7bc4c100 flags=0x0010]
  sty 04 11:12:57 miner kernel: AMD-Vi: Event logged [IO_PAGE_FAULT 
device=01:00.0 domain=0x0002 

  When I abort first launch of the quest with a monitor quit command
  during during guest BIOS initialisation, on a second launch I get the
  following errors in Qemu monitor:

  qemu-system-x86_64: vfio_dma_map(0x7f4b93fbbd40, 0x0, 0xb000, 
0x2aaac000) = -16 (Device or resource busy) 
 
  qemu-system-x86_64: vfio_dma_map(0x7f4b93fbbd40, 0xc, 0xaff4, 
0x2aaac00c) = -16 (Device or resource busy) 
 
  qemu-system-x86_64: vfio_dma_map(0x7f4b93fbbd40, 0xc8000, 0xaff38000, 
0x2aaac00c8000) = -16 (Device or resource busy) 
 
  qemu-system-x86_64: vfio_dma_map(0x7f4b93fbbd40, 0xd, 0xaff3, 
0x2aaac00d) = -16 (Device or resource busy) 

  and the following entries in the kernel log

  sty 01 22:04:53 miner kernel: vfio_ecap_init: :01:00.0 hiding ecap 
0x1b@0x2d0  

  sty 01 22:04:55 miner kernel: [ cut here ]

 
  sty 01 22:04:55 miner kernel: WARNING: CPU: 3 PID: 1012 at 
drivers/vfio/vfio_iommu_type1.c:685 vfio_dma_do_map+0x43c/0x838 
[vfio_iommu_type1]()
  sty 01 22:04:55 miner kernel: Modules linked in: tun bridge stp llc bnep 
vfio_pci vfio_iommu_type1 vfio fuse ts2020 ds3000 dvb_usb_dw2102 kvm_amd kvm 
crc32_pclmul c...luetooth rc_
  sty 01 22:04:55 miner kernel: CPU: 3 PID: 1012 Comm: qemu-system-x86 Not 
tainted 3.13.0-2-mainline #1
  
  sty 01 22:04:55 miner kernel: Hardware name: To Be Filled By O.E.M. To Be 
Filled By O.E.M./FM2A85X Extreme6, BIOS P2.30 07/11/2013
 
  sty 01 22:04:55 miner kernel:  0009 8804311b9d20 
814ddc72    
  
  sty 01 22:04:55 miner kernel:  8804311b9d58 8105f2ed 
fff0 b000   
  
  sty 01 22:04:55 miner kernel:  000b b000 
 8804311b9d68   
  
  sty 01 22:04:55 miner kernel: Call Trace: 

 
  sty 01 22:04:55 miner kernel:  [814ddc72] dump_stack+0x4d/0x6f  

 
  sty 01 22:04:55 miner kernel:  [8105f2ed] 
warn_slowpath_common+0x7d/0xa0  
   
  sty 01 22:04:55 miner kernel:  [8105f3ca] 
warn_slowpath_null+0x1a/0x20
   
  sty 01 22:04:55 miner kernel:  [a0ce9dec] 
vfio_dma_do_map+0x43c/0x838 [vfio_iommu_type1]  
   
  sty 01 22:04:55 miner kernel:  [a0cea3f9] 
vfio_iommu_type1_ioctl+0x211/0x288 [vfio_iommu_type1]   
   
  sty 01 22:04:55 miner kernel:  [a0ce0e28] 
vfio_fops_unl_ioctl+0x78/0x340 

Re: [Qemu-devel] [PATCH v3 3/3] qmp: full introspection support for QMP

2014-01-06 Thread Fam Zheng

On 2014年01月05日 20:02, Amos Kong wrote:

This patch introduces a new monitor command to query QMP schema
information, the return data is a range of schema structs, which
contains the useful metadata to help management to check supported
features, QMP commands detail, etc.

It parses all json definition in qapi-schema.json, and generate a
dynamic struct tree, QMP infrastructure will convert the tree to
json string and return to QMP client.

I defined a 'DataObject' union in qapi-schema.json, it's used to
describe the dynamic data struct.

I also added a document about QMP full introspection support
(docs/qmp-full-introspection.txt), it helps to use the new interface
and understand the abstract method in describing the dynamic struct.

TODO:
Wenchao Xia is working to convert QMP events to qapi-schema.json,
then event can also be queried by this interface.

I will introduce another command 'query-qga-schema' to query QGA
schema information, it's easy to add this support based on this
patch.

Signed-off-by: Amos Kong ak...@redhat.com
---


I have a few comments on the current implementation below, there are a 
few things to improve. However I agree to what Eric suggested in reply 
to V2: it may be better to generate most of the response data in python 
code at compile time and simplify the logic in C. Because this 
implementation is slow and it is unnecessary runtime computation. It 
also duplicates much of existing qapi.py logic (data types and other 
semantics parsing).



  docs/qmp-full-introspection.txt |  97 ++
  qapi-schema.json| 150 
  qmp-commands.hx |  43 -
  qmp.c   | 382 
  4 files changed, 671 insertions(+), 1 deletion(-)
  create mode 100644 docs/qmp-full-introspection.txt

diff --git a/docs/qmp-full-introspection.txt b/docs/qmp-full-introspection.txt
new file mode 100644
index 000..1617df7
--- /dev/null
+++ b/docs/qmp-full-introspection.txt
@@ -0,0 +1,97 @@
+= Full introspection support for QMP =
+
+
+== Purpose ==
+
+Add a new monitor command for management to  query QMP schema
+information, it returns a range of schema structs, which contain the
+useful metadata to help management to check supported features, QMP
+commands detail, etc.
+
+== Usage ==
+
+Json schema:
+  { 'type': 'NameInfo', 'data': {'*name': 'str'} }
+  { 'command': 'query-name', 'returns': 'NameInfo' }
+
+Execute QMP command:
+
+  { execute: query-qmp-schema }
+
+Returns:
+
+  { return: [
+  {
+  name: query-name,
+  type: command,
+  returns: {
+  name: NameInfo,
+  type: type,
+  data: [
+  {
+  name: name,
+  optional: true,
+  recursive: false,
+  type: str
+  }
+  ]
+  }
+  },
+  ...
+   }
+
+The whole schema information will be returned in one go, it contains
+all the schema entries. It doesn't support to be filtered by type
+or name. Currently it takes about 5 seconds to return about 1.5M string.
+
+== 'DataObject' union ==
+
+{ 'union': 'DataObject',
+  'base': 'DataObjectBase',
+  'discriminator': 'type',
+  'data': {
+'anonymous-struct': 'DataObjectAnonymousStruct',
+'command': 'DataObjectCommand',
+'enumeration': 'DataObjectEnumeration',
+'reference-type': 'String',
+'type': 'DataObjectType',
+'unionobj': 'DataObjectUnion' } }
+
+Currently we have schema difinitions for type, command, enumeration,
+union. Some arbitrary structs (dictionary, list or string) and native
+types are also used in the body of definitions.
+
+Here we use DataObject union to abstract all above schema. We want
+to provide more useful metadata, and used some enum/unions to indicate
+the dynamic type. In the output, some simple data is processed too
+unwieldy. In another side, some complex data is described clearly.
+It's also caused by some limitation of QAPI infrastructure.
+
+So we define 'DataObject' to be an union, it always has an object name
+except anonymous struct.
+
+'command', 'enumeration', 'type', 'unionobj' are common schema type,
+'union' is a build-in type, so I used unionobj here.
+
+'reference-type' will be used to describe native types and unextended
+types.
+
+'anonymous-struct' will be used to describe arbitrary structs
+(dictionary, list or string).
+
+== Avoid dead loop in recursive extending ==
+
+We have four types (ImageInfo, BlockStats, PciDeviceInfo, ObjectData)
+that uses themself in their own define data directly or indirectly,
+we will not repeatedly extend them to avoid dead loop.
+
+We use a string to record the visit path, type index of each node
+will be saved to the string, indexes are split by ':'.
+
+Push index to visit_path_str before extending, and pop index from
+visit_path_str after extending.
+
+If the type was already extended in parent node, we 

Re: [Qemu-devel] vhost-net issue: does not survive reboot on ppc64

2014-01-06 Thread Alexey Kardashevskiy
On 12/27/2013 12:44 PM, Alexey Kardashevskiy wrote:
 On 12/27/2013 02:12 AM, Michael S. Tsirkin wrote:
 On Fri, Dec 27, 2013 at 01:59:19AM +1100, Alexey Kardashevskiy wrote:
 On 12/27/2013 12:48 AM, Michael S. Tsirkin wrote:
 On Thu, Dec 26, 2013 at 11:51:04PM +1100, Alexey Kardashevskiy wrote:
 On 12/26/2013 09:49 PM, Michael S. Tsirkin wrote:
 On Thu, Dec 26, 2013 at 09:13:31PM +1100, Alexey Kardashevskiy wrote:
 On 12/25/2013 08:52 PM, Michael S. Tsirkin wrote:
 On Wed, Dec 25, 2013 at 12:36:12PM +1100, Alexey Kardashevskiy wrote:
 On 12/25/2013 02:43 AM, Michael S. Tsirkin wrote:
 On Wed, Dec 25, 2013 at 01:15:29AM +1100, Alexey Kardashevskiy wrote:
 On 12/24/2013 08:40 PM, Michael S. Tsirkin wrote:
 On Tue, Dec 24, 2013 at 02:09:07PM +1100, Alexey Kardashevskiy 
 wrote:
 On 12/24/2013 03:24 AM, Michael S. Tsirkin wrote:
 On Mon, Dec 23, 2013 at 02:01:13AM +1100, Alexey Kardashevskiy 
 wrote:
 On 12/23/2013 01:46 AM, Alexey Kardashevskiy wrote:
 On 12/22/2013 09:56 PM, Michael S. Tsirkin wrote:
 On Sun, Dec 22, 2013 at 02:01:23AM +1100, Alexey 
 Kardashevskiy wrote:
 Hi!

 I am having a problem with virtio-net + vhost on POWER7 
 machine - it does
 not survive reboot of the guest.

 Steps to reproduce:
 1. boot the guest
 2. configure eth0 and do ping - everything works
 3. reboot the guest (i.e. type reboot)
 4. when it is booted, eth0 can be configured but will not 
 work at all.

 The test is:
 ifconfig eth0 172.20.1.2 up
 ping 172.20.1.23

 If to run tcpdump on the host's tap-id3 interface, it 
 shows no trafic
 coming from the guest. If to compare how it works before and 
 after reboot,
 I can see the guest doing an ARP request for 172.20.1.23 and 
 receives the
 response and it does the same after reboot but the answer 
 does not come.

 So you see the arp packet in guest but not in host?

 Yes.


 One thing to try is to boot debug kernel - where pr_debug is
 enabled - then you might see some errors in the kernel log.

 Tried and added lot more debug printk myself, not clear at all 
 what is
 happening there.

 One more hint - if I boot the guest and the guest does not 
 bring eth0 up
 AND wait more than 200 seconds (and less than 210 seconds), 
 then eth0 will
 not work at all. I.e. this script produces not-working-eth0:


 ifconfig eth0 172.20.1.2 down
 sleep 210
 ifconfig eth0 172.20.1.2 up
 ping 172.20.1.23

 s/210/200/ - and it starts working. No reboot is required to 
 reproduce.

 No vhost == always works. The only difference I can see here 
 is vhost's
 thread which may get suspended if not used for a while after 
 the start and
 does not wake up but this is almost a blind guess.


 Yet another clue - this host kernel patch seems to help with 
 the guest
 reboot but does not help with the initial 210 seconds delay:

 diff --git a/drivers/vhost/vhost.c b/drivers/vhost/vhost.c
 index 69068e0..5e67650 100644
 --- a/drivers/vhost/vhost.c
 +++ b/drivers/vhost/vhost.c
 @@ -162,10 +162,10 @@ void vhost_work_queue(struct vhost_dev 
 *dev, struct
 vhost_work *work)
 list_add_tail(work-node, dev-work_list);
 work-queue_seq++;
 spin_unlock_irqrestore(dev-work_lock, flags);
 -   wake_up_process(dev-worker);
 } else {
 spin_unlock_irqrestore(dev-work_lock, flags);
 }
 +   wake_up_process(dev-worker);
  }
  EXPORT_SYMBOL_GPL(vhost_work_queue);



 Interesting. Some kind of race? A missing memory barrier 
 somewhere?

 I do not see how. I boot the guest and just wait 210 seconds, 
 nothing
 happens to cause races.


 Since it's all around startup,
 you can try kicking the host eventfd in
 vhost_net_start.


 How exactly? This did not help. Thanks.

 diff --git a/hw/net/vhost_net.c b/hw/net/vhost_net.c
 index 006576d..407ecf2 100644
 --- a/hw/net/vhost_net.c
 +++ b/hw/net/vhost_net.c
 @@ -229,6 +229,17 @@ int vhost_net_start(VirtIODevice *dev, 
 NetClientState
 *ncs,
  if (r  0) {
  goto err;
  }
 +
 +VHostNetState *vn = tap_get_vhost_net(ncs[i].peer);
 +struct vhost_vring_file file = {
 +.index = i
 +};
 +file.fd =
 event_notifier_get_fd(virtio_queue_get_host_notifier(dev-vq));
 +r = ioctl(vn-dev.control, VHOST_SET_VRING_KICK, file);

 No, this sets the notifier, it does not kick.
 To kick you write 1 there:
uint6_t  v = 1;
write(fd, v, sizeof v);


 Please, be precise. How/where do I get that @fd? Is what I do 
 correct?

 Yes.

 What
 is uint6_t - uint8_t or uint16_t (neither works)?

 Sorry, should have been uint64_t.


 Oh, that I missed :-) Anyway, this does not make any difference. Is 
 there
 any cheapdirty way to make vhost-net kernel thread always awake? 
 Sending
 it signals from the user space does not work...

 You can run a timer in qemu and signal the eventfd from there
 periodically.

 Just to restate, tcpdump in guest shows that guest sends arp packet,
 but tcpdump in host on tun device does not show any 

Re: [Qemu-devel] [PATCHv3 3/6] ui/vnc: optimize dirty bitmap tracking

2014-01-06 Thread Wenchao Xia
于 2014/1/6 2:02, Peter Lieven 写道:
 vnc_update_client currently scans the dirty bitmap of each client
 bitwise which is a very costly operation if only few bits are dirty.
 vnc_refresh_server_surface does almost the same.
 this patch optimizes both by utilizing the heavily optimized
 function find_next_bit to find the offset of the next dirty
 bit in the dirty bitmaps.
 
 The following artifical test (just the bitmap operation part) running
 vnc_update_client 65536 times on a 2560x2048 surface illustrates the
 performance difference:
 
 All bits clean - vnc_update_client_new: 0.07 secs
   vnc_update_client_old: 10.98 secs
 
 All bits dirty - vnc_update_client_new: 11.26 secs
   vnc_update_client_old: 20.19 secs
 
 Few bits dirty - vnc_update_client_new: 0.08 secs
   vnc_update_client_old: 10.98 secs
 
 The case for all bits dirty is still rather slow, this
 is due to the implementation of find_and_clear_dirty_height.
 This will be addresses in a separate patch.
 
 Signed-off-by: Peter Lieven p...@kamp.de
 ---
   ui/vnc.c |  154 
 +-
   ui/vnc.h |4 ++
   2 files changed, 87 insertions(+), 71 deletions(-)
 
 diff --git a/ui/vnc.c b/ui/vnc.c
 index 1d2aa1a..6a0c03e 100644
 --- a/ui/vnc.c
 +++ b/ui/vnc.c
 @@ -572,6 +572,14 @@ void *vnc_server_fb_ptr(VncDisplay *vd, int x, int y)
   ptr += x * VNC_SERVER_FB_BYTES;
   return ptr;
   }
 +/* this sets only the visible pixels of a dirty bitmap */
 +#define VNC_SET_VISIBLE_PIXELS_DIRTY(bitmap, w, h) {\
 +int y;\
 +memset(bitmap, 0x00, sizeof(bitmap));\
 +for (y = 0; y  h; y++) {\
 +bitmap_set(bitmap[y], 0, w / VNC_DIRTY_PIXELS_PER_BIT);\

  Will it be a problem when vnc's width % VNC_DIRTY_PIXELS_PER_BIT != 0?
Although it is a rare case, but I think it is better round it up, since
v and VNC_DIRTY_PIXELS_PER_BIT are variables. A macro computing it
would be nice:

#define VNC_DIRTY_BITS_FROM_WIDTH(w) (w + VNC_DIRTY_PIXELS_PER_BIT - 1/
VNC_DIRTY_PIXELS_PER_BIT)
#define VNC_DIRTY_BITS (VNC_DIRTY_BITS_FROM_WIDTH(VNC_MAX_WIDTH)

then here:
bitmap_set(bitmap[y], 0, VNC_DIRTY_BITS_FROM_WIDTH(w));

Or simply warn or coredump when v % VNC_DIRTY_PIXELS_PER_BIT != 0.

Also, in vnc.h:
/* VNC_MAX_WIDTH must be a multiple of 16. */
#define VNC_MAX_WIDTH 2560
#define VNC_MAX_HEIGHT 2048

Maybe it should be updated as:
/* VNC_MAX_WIDTH must be a multiple of VNC_DIRTY_PIXELS_PER_BIT. */

 +} \
 +}
 
   static void vnc_dpy_switch(DisplayChangeListener *dcl,
  DisplaySurface *surface)
 @@ -597,7 +605,9 @@ static void vnc_dpy_switch(DisplayChangeListener *dcl,
   qemu_pixman_image_unref(vd-guest.fb);
   vd-guest.fb = pixman_image_ref(surface-image);
   vd-guest.format = surface-format;
 -memset(vd-guest.dirty, 0xFF, sizeof(vd-guest.dirty));
 +VNC_SET_VISIBLE_PIXELS_DIRTY(vd-guest.dirty,
 + surface_width(vd-ds),
 + surface_height(vd-ds));
 
   QTAILQ_FOREACH(vs, vd-clients, next) {
   vnc_colordepth(vs);
 @@ -605,7 +615,9 @@ static void vnc_dpy_switch(DisplayChangeListener *dcl,
   if (vs-vd-cursor) {
   vnc_cursor_define(vs);
   }
 -memset(vs-dirty, 0xFF, sizeof(vs-dirty));
 +VNC_SET_VISIBLE_PIXELS_DIRTY(vs-dirty,
 + surface_width(vd-ds),
 + surface_height(vd-ds));
   }
   }
 
 @@ -889,10 +901,9 @@ static int vnc_update_client(VncState *vs, int has_dirty)
   VncDisplay *vd = vs-vd;
   VncJob *job;
   int y;
 -int width, height;
 +int height;
   int n = 0;
 
 -
   if (vs-output.offset  !vs-audio_cap  !vs-force_update)
   /* kernel send buffers are full - drop frames to throttle */
   return 0;
 @@ -908,39 +919,27 @@ static int vnc_update_client(VncState *vs, int 
 has_dirty)
*/
   job = vnc_job_new(vs);
 
 -width = MIN(pixman_image_get_width(vd-server), vs-client_width);
   height = MIN(pixman_image_get_height(vd-server), 
 vs-client_height);
 
 -for (y = 0; y  height; y++) {
 -int x;
 -int last_x = -1;
 -for (x = 0; x  width / VNC_DIRTY_PIXELS_PER_BIT; x++) {
 -if (test_and_clear_bit(x, vs-dirty[y])) {
 -if (last_x == -1) {
 -last_x = x;
 -}
 -} else {
 -if (last_x != -1) {
 -int h = find_and_clear_dirty_height(vs, y, last_x, x,
 -height);
 -
 -n += vnc_job_add_rect(job,
 -  last_x * 
 VNC_DIRTY_PIXELS_PER_BIT,
 -  

Re: [Qemu-devel] [PATCHv2 04/18] qemu-iotests: fix test 013 to work with any protocol

2014-01-06 Thread Fam Zheng

On 2014年01月06日 14:48, Peter Lieven wrote:

On 06.01.2014 06:31, Fam Zheng wrote:

On 2014年01月06日 01:21, Peter Lieven wrote:

Signed-off-by: Peter Lieven p...@kamp.de
---
  tests/qemu-iotests/013 |9 -
  tests/qemu-iotests/013.out |2 +-
  2 files changed, 5 insertions(+), 6 deletions(-)

diff --git a/tests/qemu-iotests/013 b/tests/qemu-iotests/013
index ea3cab9..0dbc934 100755
--- a/tests/qemu-iotests/013
+++ b/tests/qemu-iotests/013
@@ -41,14 +41,14 @@ trap _cleanup; exit \$status 0 1 2 3 15

  # much of this could be generic for any format supporting compression.
  _supported_fmt qcow qcow2
-_supported_proto file
+_supported_proto generic
  _supported_os Linux

  TEST_OFFSETS=0 4294967296
  TEST_OPS=writev read write readv
  CLUSTER_SIZE=4096



I think dropping these three TEST_IMG overriding change...


-_make_test_img 6G
+TEST_IMG=$TEST_IMG.orig _make_test_img 6G


#1



  echo Testing empty image
  echo
@@ -56,16 +56,15 @@ echo
  for offset in $TEST_OFFSETS; do
  echo At offset $offset:
  for op in $TEST_OPS; do
-io_test $op $offset $CLUSTER_SIZE 8
+TEST_IMG=$TEST_IMG.orig io_test $op $offset $CLUSTER_SIZE 8


#2


  done
-_check_test_img
+TEST_IMG=$TEST_IMG.orig _check_test_img


#3


  done


  echo Compressing image
  echo

-mv $TEST_IMG $TEST_IMG.orig


and changing this to

TEST_IMG=$TEST_IMG.orig _make_test_img 6G

Should work.

Unfortunately it doesn't. All subsequent commands will then work
on $TEST_IMG.orig altough they shouldn't. In case of
013 this is io_test, _check_test_img and the cleanup at the end.



Why? The overriding is temporary and subsequent commands are not affected.

My proposal above doesn't work, though, because an empty new image 
doesn't contain the right data, what is needed here is copy. So maybe 
change the mv line to:


$QEMU_IMG convert -f $IMGFMT -O $IMGFMT $TEST_IMG $TEST_IMG.orig

could do the work, but I'm not sure if this fits every case.


There are 3 options:
  - override it in every line that should use an alternate $TEST_IMG
  - save the original $TEST_IMG and restore it.
  - rework all commands to take the file as parameter and not use
a global variable for it.

I choosed the first one because it makes clear which $TEST_IMG is acutally
used. You see from the output and the code that you are dealing with the
file that is later used as $TEST_IMG.orig. If you see $TEST_IMG there you
can't distinguish if its the backing or original file or the actual image.

But I thought that this would be controversal. This is I why I splitted
the patch
into individual ones. So its possible to drop all these patches and
still be able
to proceed with the integration of the NFS protocol driver.


I'll leave maintainers to decide.

Fam




Re: [Qemu-devel] Communication between Windows 7 host and Linux guest

2014-01-06 Thread Gripon Sébastien
This is the command line:

qemu-system-armw -M versatilepb -kernel ..\BaseQemu\zImage -hda 
..\BaseQemu\rootfs.squashfs -hdb ..\BaseQemu\flash.ext3 -append root=/dev/sda 
r -net tap,ifname=TAP,script=no -net nic 

I talked with the developer here and it seems that the bad speed is mainly due 
to latency. We are investigating also on our side because we use a special 
environment: in fact, we use VisualGDB to debug from Visual studio into qemu. 
It seems that VisualGDB's ssh client has poor performances but I don't know yet 
where the latency come from.

Sebastien

-Message d'origine-
De : Stefan Hajnoczi [mailto:stefa...@gmail.com] 
Envoyé : lundi 6 janvier 2014 03:15
À : Gripon Sébastien
Cc : qemu-devel@nongnu.org
Objet : Re: [Qemu-devel] Communication between Windows 7 host and Linux guest

On Sun, Dec 22, 2013 at 07:15:18PM +, Gripon Sébastien wrote:
 I have the need to communicate efficiently between Windows 7 host and linux 
 guest. I tried first to use an IP socket communication using TAP driver on 
 Windows. Unfortunately, we reach a maximum of 4 Mbits/s where I would need 
 faster communication (more than 10 Mb/s). I don’t know yet if the TAP driver 
 is slow.

That seems very slow, 100 Mbit/s should definitely be achievable.  But I have 
never tried TAP on Windows.

Can you share the QEMU command-line and the benchmark used to measure this 
result?

Stefan


Re: [Qemu-devel] [PATCH v3 2/3] qapi: change qapi to convert schema json

2014-01-06 Thread Fam Zheng

On 2014年01月05日 20:02, Amos Kong wrote:

QMP schema is defined in a json file, it will be parsed by
qapi scripts and generate C files.

We want to return the schema information to management,
this patch converts the json file to a string table in a
C head file, then we can use the json content in QEMU code.

eg: (qmp-schema.h)
   const char *const qmp_schema_table[] = {
 { 'type': 'NameInfo', 'data': {'*name': 'str'} },
 { 'command': 'query-name', 'returns': 'NameInfo' },
 ...
   }

Signed-off-by: Amos Kong ak...@redhat.com
---
  Makefile |  5 -
  scripts/qapi-commands.py |  2 +-
  scripts/qapi-types.py| 48 +---
  scripts/qapi-visit.py|  2 +-
  scripts/qapi.py  | 20 +++-
  5 files changed, 66 insertions(+), 11 deletions(-)

diff --git a/Makefile b/Makefile
index bdff4e4..2c29755 100644
--- a/Makefile
+++ b/Makefile
@@ -45,7 +45,7 @@ endif
  endif

  GENERATED_HEADERS = config-host.h qemu-options.def
-GENERATED_HEADERS += qmp-commands.h qapi-types.h qapi-visit.h
+GENERATED_HEADERS += qmp-commands.h qapi-types.h qapi-visit.h qmp-schema.h
  GENERATED_SOURCES += qmp-marshal.c qapi-types.c qapi-visit.c

  GENERATED_HEADERS += trace/generated-events.h
@@ -229,6 +229,9 @@ $(SRC_PATH)/qapi-schema.json 
$(SRC_PATH)/scripts/qapi-visit.py $(qapi-py)
  qmp-commands.h qmp-marshal.c :\
  $(SRC_PATH)/qapi-schema.json $(SRC_PATH)/scripts/qapi-commands.py $(qapi-py)
$(call quiet-command,$(PYTHON) $(SRC_PATH)/scripts/qapi-commands.py $(gen-out-type) -m -o 
.  $,   GEN   $@)
+qmp-schema.h:\
+$(SRC_PATH)/qapi-schema.json $(SRC_PATH)/scripts/qapi-types.py $(qapi-py)
+   $(call quiet-command,$(PYTHON) $(SRC_PATH)/scripts/qapi-types.py $(gen-out-type) -o . -s 
$@  $,   GEN   $@)



It would be nice to also add this file to .gitignore together with this 
patch.


Fam



Re: [Qemu-devel] [PATCH target-arm v2 00/11] Cadence UART cleanups and Tx path fixes

2014-01-06 Thread Peter Maydell
On 2 January 2014 01:57, Peter Crosthwaite peter.crosthwa...@xilinx.com wrote:

 When using QEMU in some terminal environments, char back-ends for serial
 devices can return EAGAIN for non trivial periods. This coupled with use
 of qemu_chr_fe_write_all() is a leading cause of:

 main-loop: WARNING: I/O thread spun for 1000 iterations

 This series fixes this for cadence_uart by replacing the open loop
 tx-write logic with a proper closed-loop that is responsive to the
 back-end short return.

Thanks; applied all to target-arm.next.

-- PMM



Re: [Qemu-devel] [PATCH resend] linux-user: Support the accept4 socketcall

2014-01-06 Thread Laurent Vivier

 Le 6 janvier 2014 à 10:14, Peter Maydell peter.mayd...@linaro.org a écrit :


 On 6 January 2014 08:45, Laurent Vivier laur...@vivier.eu wrote:
 
  Le 6 janvier 2014 à 02:57, André Hentschel n...@dawncrow.de a écrit :
  diff --git a/linux-user/syscall_defs.h b/linux-user/syscall_defs.h
  index cf08db5..b36f99c 100644
  --- a/linux-user/syscall_defs.h
  +++ b/linux-user/syscall_defs.h
  @@ -27,6 +27,9 @@
  #define SOCKOP_getsockopt 15
  #define SOCKOP_sendmsg 16
  #define SOCKOP_recvmsg 17
  +#define SOCKOP_accept4 18
  +#define SOCKOP_recvmmsg 19
  +#define SOCKOP_sendmmsg 20
 
  Don't add these both defines here as they are not used in this patch.

 It doesn't seem that unreasonable to add them. We add things
 to the main syscall number #define list even if we aren't
 actually implementing them, for example.

IMHO, you should not : if you implement these syscalls and then revert this
patch (because it is broken, for instance), you will break the build. The
defines must come with the implementation.

Regards,
Laurent

Re: [Qemu-devel] [RFC PATCH v4 0/8] Support arm-gic-kvm save/restore

2014-01-06 Thread Peter Maydell
On 21 December 2013 06:09, Christoffer Dall christoffer.d...@linaro.org wrote:
 Implement support to save/restore the ARM KVM VGIC state from the
 kernel.  The basic appraoch is to transfer state from the in-kernel VGIC
 to the emulated arm-gic state representation and let the standard QEMU
 vmstate save/restore handle saving the arm-gic state.  Restore works by
 reversing the process.

 The first patches adds missing features and fixes issues with the
 arm-gic implementation in qemu in preparation for the actual
 save/restore logic.

I still need to review this series, but I'm going to take the
first two patches into target-arm.next now since they're already
reviewed and they're straightforward cleanup.

thanks
-- PMM



Re: [Qemu-devel] [PATCH] spapr-pci: remove io ports workaround

2014-01-06 Thread Greg Kurz
On Fri, 03 Jan 2014 09:08:21 +1100
Alexey Kardashevskiy a...@ozlabs.ru wrote:
 
 Please read the rest of this thread. It does not visibly break things but
 with this patch QEMU starts calling unassigned_mem_accepts() (normally
 silent) which is not a good sign.
 
 
 

Hmm... this is only because this patch moves the PHB io region from the
system IO to the system memory space, but the bogus(?) write to unassigned
memory already exists.

I have tested against the current ppc-next (62d529a), with no
additional patch:

qemu-system-ppc64 \
-snapshot -S -monitor stdio -serial pty \
-nographic -nodefaults \
-machine type=pseries,accel=kvm -smp 1 -m 4G \
-device virtio-blk-pci,id=virtioiblk0,drive=drive0,bootindex=20,ioeventfd=on \
-drive file=/local/greg/qemu/fedora-be.qcow2,if=none,id=drive0,readonly=off,\
   format=qcow2,media=disk,werror=stop,rerror=stop,discard=on

where fedora-be.qcow2 contains a stock fedora 19 for ppc64.

I have attached gdb to qemu and set a breakpoint in unassigned_io_write(), and
here is what I get again:

(gdb) b unassigned_io_write 
Breakpoint 1 at 0x1045d308: file /home/greg/Work/ibm/linux/qemu-agraf/ioport.c, 
line 54.
(gdb) c
Continuing.
[Thread 0x1c5deef0 (LWP 11946) exited]
[New Thread 0x1c5deef0 (LWP 11955)]
[Switching to Thread 0x1bdaeef0 (LWP 11947)]

Breakpoint 1, unassigned_io_write (opaque=0x0, addr=82, val=128, size=1) at 
/home/greg/Work/ibm/linux/qemu-agraf/ioport.c:54
54  {
(gdb) where
#0  unassigned_io_write (opaque=0x0, addr=82, val=128, size=1) at 
/home/greg/Work/ibm/linux/qemu-agraf/ioport.c:54
#1  0x10468f38 in memory_region_write_accessor (mr=0x10027615940, 
addr=82, value=0x1bdadd68, size=1, shift=0, mask=255) at 
/home/greg/Work/ibm/linux/qemu-agraf/memory.c:440
#2  0x104690c4 in access_with_adjusted_size (addr=82, 
value=0x1bdadd68, size=1, access_size_min=1, access_size_max=4, 
access=@0x107ca670: 0x10468e5c memory_region_write_accessor, mr=0x10027615940)
at /home/greg/Work/ibm/linux/qemu-agraf/memory.c:472
#3  0x1046bc64 in memory_region_dispatch_write (mr=0x10027615940, 
addr=82, data=128, size=1) at /home/greg/Work/ibm/linux/qemu-agraf/memory.c:984
#4  0x1046fdc4 in io_mem_write (mr=0x10027615940, addr=82, val=128, 
size=1) at /home/greg/Work/ibm/linux/qemu-agraf/memory.c:1749
#5  0x103aca0c in address_space_rw (as=0x10c19638 
address_space_memory, addr=1101659111506, buf=0x1bdae117 \200, len=1, 
is_write=true) at /home/greg/Work/ibm/linux/qemu-agraf/exec.c:2002
#6  0x103acf3c in cpu_physical_memory_rw (addr=1101659111506, 
buf=0x1bdae117 \200, len=1, is_write=1) at 
/home/greg/Work/ibm/linux/qemu-agraf/exec.c:2071
#7  0x103a44c4 in cpu_physical_memory_write (addr=1101659111506, 
buf=0x1bdae117, len=1) at 
/home/greg/Work/ibm/linux/qemu-agraf/include/exec/cpu-common.h:68
#8  0x103aeb2c in stb_phys (addr=1101659111506, val=128) at 
/home/greg/Work/ibm/linux/qemu-agraf/exec.c:2600
#9  0x10438550 in h_logical_store (cpu=0x10027d0f0d0, 
spapr=0x100276bb210, opcode=64, args=0x1ff80030) at 
/home/greg/Work/ibm/linux/qemu-agraf/hw/ppc/spapr_hcall.c:564
#10 0x10438e74 in spapr_hypercall (cpu=0x10027d0f0d0, opcode=64, 
args=0x1ff80030) at 
/home/greg/Work/ibm/linux/qemu-agraf/hw/ppc/spapr_hcall.c:737
#11 0x104cf424 in kvm_arch_handle_exit (cs=0x10027d0f0d0, 
run=0x1ff8) at 
/home/greg/Work/ibm/linux/qemu-agraf/target-ppc/kvm.c:1223
#12 0x104648a4 in kvm_cpu_exec (cpu=0x10027d0f0d0) at 
/home/greg/Work/ibm/linux/qemu-agraf/kvm-all.c:1736
#13 0x10397f00 in qemu_kvm_cpu_thread_fn (arg=0x10027d0f0d0) at 
/home/greg/Work/ibm/linux/qemu-agraf/cpus.c:874
#14 0x1f92c29c in start_thread (arg=0x1bdaeef0) at 
pthread_create.c:310
#15 0x1de5de10 in .__clone ()
at ../sysdeps/unix/sysv/linux/powerpc/powerpc64/clone.S:111

All I can say for the moment, is that I don't get that if I run qemu with
-kernel/-append/-initrd instead of following the grub2 path.

Any clue ?

Thanks.

-- 
Gregory Kurz kurzg...@fr.ibm.com
 gk...@linux.vnet.ibm.com
Software Engineer @ IBM/Meiosys  http://www.ibm.com
Tel +33 (0)562 165 496

Anarchy is about taking complete responsibility for yourself.
Alan Moore.




[Qemu-devel] [PULL 15/52] target-arm: A64: Implement minimal set of EL0-visible sysregs

2014-01-06 Thread Peter Maydell
Implement an initial minimal set of EL0-visible system registers:
 * NZCV
 * FPCR
 * FPSR
 * CTR_EL0
 * DCZID_EL0

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
Reviewed-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
---
 target-arm/cpu.h   |  3 ++-
 target-arm/helper.c| 61 ++
 target-arm/translate-a64.c | 52 +++
 3 files changed, 115 insertions(+), 1 deletion(-)

diff --git a/target-arm/cpu.h b/target-arm/cpu.h
index b091426..ab8ef17 100644
--- a/target-arm/cpu.h
+++ b/target-arm/cpu.h
@@ -660,7 +660,8 @@ static inline uint64_t cpreg_to_kvm_id(uint32_t cpregid)
 #define ARM_CP_IO 64
 #define ARM_CP_NOP (ARM_CP_SPECIAL | (1  8))
 #define ARM_CP_WFI (ARM_CP_SPECIAL | (2  8))
-#define ARM_LAST_SPECIAL ARM_CP_WFI
+#define ARM_CP_NZCV (ARM_CP_SPECIAL | (3  8))
+#define ARM_LAST_SPECIAL ARM_CP_NZCV
 /* Used only as a terminator for ARMCPRegInfo lists */
 #define ARM_CP_SENTINEL 0x
 /* Mask of only the flag bits in a type field */
diff --git a/target-arm/helper.c b/target-arm/helper.c
index 66214293..868493d 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -1560,6 +1560,64 @@ static const ARMCPRegInfo lpae_cp_reginfo[] = {
 REGINFO_SENTINEL
 };
 
+static int aa64_fpcr_read(CPUARMState *env, const ARMCPRegInfo *ri,
+  uint64_t *value)
+{
+*value = vfp_get_fpcr(env);
+return 0;
+}
+
+static int aa64_fpcr_write(CPUARMState *env, const ARMCPRegInfo *ri,
+   uint64_t value)
+{
+vfp_set_fpcr(env, value);
+return 0;
+}
+
+static int aa64_fpsr_read(CPUARMState *env, const ARMCPRegInfo *ri,
+  uint64_t *value)
+{
+*value = vfp_get_fpsr(env);
+return 0;
+}
+
+static int aa64_fpsr_write(CPUARMState *env, const ARMCPRegInfo *ri,
+   uint64_t value)
+{
+vfp_set_fpsr(env, value);
+return 0;
+}
+
+static const ARMCPRegInfo v8_cp_reginfo[] = {
+/* Minimal set of EL0-visible registers. This will need to be expanded
+ * significantly for system emulation of AArch64 CPUs.
+ */
+{ .name = NZCV, .state = ARM_CP_STATE_AA64,
+  .opc0 = 3, .opc1 = 3, .opc2 = 0, .crn = 4, .crm = 2,
+  .access = PL0_RW, .type = ARM_CP_NZCV },
+{ .name = FPCR, .state = ARM_CP_STATE_AA64,
+  .opc0 = 3, .opc1 = 3, .opc2 = 0, .crn = 4, .crm = 4,
+  .access = PL0_RW, .readfn = aa64_fpcr_read, .writefn = aa64_fpcr_write },
+{ .name = FPSR, .state = ARM_CP_STATE_AA64,
+  .opc0 = 3, .opc1 = 3, .opc2 = 1, .crn = 4, .crm = 4,
+  .access = PL0_RW, .readfn = aa64_fpsr_read, .writefn = aa64_fpsr_write },
+/* This claims a 32 byte cacheline size for icache and dcache, VIPT icache.
+ * It will eventually need to have a CPU-specified reset value.
+ */
+{ .name = CTR_EL0, .state = ARM_CP_STATE_AA64,
+  .opc0 = 3, .opc1 = 3, .opc2 = 1, .crn = 0, .crm = 0,
+  .access = PL0_R, .type = ARM_CP_CONST,
+  .resetvalue = 0x80030003 },
+/* Prohibit use of DC ZVA. OPTME: implement DC ZVA and allow its use.
+ * For system mode the DZP bit here will need to be computed, not constant.
+ */
+{ .name = DCZID_EL0, .state = ARM_CP_STATE_AA64,
+  .opc0 = 3, .opc1 = 3, .opc2 = 7, .crn = 0, .crm = 0,
+  .access = PL0_R, .type = ARM_CP_CONST,
+  .resetvalue = 0x10 },
+REGINFO_SENTINEL
+};
+
 static int sctlr_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t 
value)
 {
 env-cp15.c1_sys = value;
@@ -1662,6 +1720,9 @@ void register_cp_regs_for_features(ARMCPU *cpu)
 } else {
 define_arm_cp_regs(cpu, not_v7_cp_reginfo);
 }
+if (arm_feature(env, ARM_FEATURE_V8)) {
+define_arm_cp_regs(cpu, v8_cp_reginfo);
+}
 if (arm_feature(env, ARM_FEATURE_MPU)) {
 /* These are the MPU registers prior to PMSAv6. Any new
  * PMSA core later than the ARM946 will require that we
diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 7a9ee82..c8ed799 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -733,6 +733,50 @@ static void handle_msr_i(DisasContext *s, uint32_t insn,
 unsupported_encoding(s, insn);
 }
 
+static void gen_get_nzcv(TCGv_i64 tcg_rt)
+{
+TCGv_i32 tmp = tcg_temp_new_i32();
+TCGv_i32 nzcv = tcg_temp_new_i32();
+
+/* build bit 31, N */
+tcg_gen_andi_i32(nzcv, cpu_NF, (1  31));
+/* build bit 30, Z */
+tcg_gen_setcondi_i32(TCG_COND_EQ, tmp, cpu_ZF, 0);
+tcg_gen_deposit_i32(nzcv, nzcv, tmp, 30, 1);
+/* build bit 29, C */
+tcg_gen_deposit_i32(nzcv, nzcv, cpu_CF, 29, 1);
+/* build bit 28, V */
+tcg_gen_shri_i32(tmp, cpu_VF, 31);
+tcg_gen_deposit_i32(nzcv, nzcv, tmp, 28, 1);
+/* generate result */
+tcg_gen_extu_i32_i64(tcg_rt, nzcv);
+
+tcg_temp_free_i32(nzcv);
+tcg_temp_free_i32(tmp);
+}
+
+static void gen_set_nzcv(TCGv_i64 

[Qemu-devel] [PULL 18/52] target-arm: A64: add support for conditional compare insns

2014-01-06 Thread Peter Maydell
From: Claudio Fontana claudio.font...@linaro.org

this patch adds support for C3.5.4 - C3.5.5
Conditional compare (both immediate and register)

Signed-off-by: Claudio Fontana claudio.font...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 73 +-
 1 file changed, 60 insertions(+), 13 deletions(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 9f508b9..538d69e 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -2483,16 +2483,67 @@ static void disas_adc_sbc(DisasContext *s, uint32_t 
insn)
 }
 }
 
-/* Conditional compare (immediate) */
-static void disas_cc_imm(DisasContext *s, uint32_t insn)
+/* C3.5.4 - C3.5.5 Conditional compare (immediate / register)
+ *  31 30 29 28 27 26 25 24 23 22 21  2016 15  12  11  10  9   5  4 3   0
+ * +--+--+--+++--++--+--+--+-+
+ * |sf|op| S| 1  1  0  1  0  0  1  0 |imm5/rm | cond |i/r |o2|  Rn  |o3|nzcv |
+ * +--+--+--+++--++--+--+--+-+
+ *[1] y[0]   [0]
+ */
+static void disas_cc(DisasContext *s, uint32_t insn)
 {
-unsupported_encoding(s, insn);
-}
+unsigned int sf, op, y, cond, rn, nzcv, is_imm;
+int label_continue = -1;
+TCGv_i64 tcg_tmp, tcg_y, tcg_rn;
 
-/* Conditional compare (register) */
-static void disas_cc_reg(DisasContext *s, uint32_t insn)
-{
-unsupported_encoding(s, insn);
+if (!extract32(insn, 29, 1)) {
+unallocated_encoding(s);
+return;
+}
+if (insn  (1  10 | 1  4)) {
+unallocated_encoding(s);
+return;
+}
+sf = extract32(insn, 31, 1);
+op = extract32(insn, 30, 1);
+is_imm = extract32(insn, 11, 1);
+y = extract32(insn, 16, 5); /* y = rm (reg) or imm5 (imm) */
+cond = extract32(insn, 12, 4);
+rn = extract32(insn, 5, 5);
+nzcv = extract32(insn, 0, 4);
+
+if (cond  0x0e) { /* not always */
+int label_match = gen_new_label();
+label_continue = gen_new_label();
+arm_gen_test_cc(cond, label_match);
+/* nomatch: */
+tcg_tmp = tcg_temp_new_i64();
+tcg_gen_movi_i64(tcg_tmp, nzcv  28);
+gen_set_nzcv(tcg_tmp);
+tcg_temp_free_i64(tcg_tmp);
+tcg_gen_br(label_continue);
+gen_set_label(label_match);
+}
+/* match, or condition is always */
+if (is_imm) {
+tcg_y = new_tmp_a64(s);
+tcg_gen_movi_i64(tcg_y, y);
+} else {
+tcg_y = cpu_reg(s, y);
+}
+tcg_rn = cpu_reg(s, rn);
+
+tcg_tmp = tcg_temp_new_i64();
+if (op) {
+gen_sub_CC(sf, tcg_tmp, tcg_rn, tcg_y);
+} else {
+gen_add_CC(sf, tcg_tmp, tcg_rn, tcg_y);
+}
+tcg_temp_free_i64(tcg_tmp);
+
+if (cond  0x0e) { /* continue */
+gen_set_label(label_continue);
+}
 }
 
 /* C3.5.6 Conditional select
@@ -2846,11 +2897,7 @@ static void disas_data_proc_reg(DisasContext *s, 
uint32_t insn)
 disas_adc_sbc(s, insn);
 break;
 case 0x2: /* Conditional compare */
-if (insn  (1  11)) { /* (immediate) */
-disas_cc_imm(s, insn);
-} else {/* (register) */
-disas_cc_reg(s, insn);
-}
+disas_cc(s, insn); /* both imm and reg forms */
 break;
 case 0x4: /* Conditional select */
 disas_cond_select(s, insn);
-- 
1.8.5




[Qemu-devel] [PULL 49/52] arm/xilinx_zynq: Always instantiate the GEMs

2014-01-06 Thread Peter Maydell
From: Peter Crosthwaite peter.crosthwa...@xilinx.com

Don't conditionalise GEM instantiation on networking attachments. The
device should always be present even if not attached to a network.

This allows for probing of the device by expectant guests (such as
OS's).  This is needed because sysbus (or AXI in Xilinx's real hw case)
is not self identifying so the guest has no dynamic way of detecting
device absence.

Also allows for testing of the GEM in loopback mode with -net none.

Signed-off-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
Reviewed-by: Peter Maydell peter.mayd...@linaro.org
Message-id: 
55649779a68ee3ff54b24c339b6fdbdccd1f0ed7.1388800598.git.peter.crosthwa...@xilinx.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 hw/arm/xilinx_zynq.c | 17 ++---
 1 file changed, 6 insertions(+), 11 deletions(-)

diff --git a/hw/arm/xilinx_zynq.c b/hw/arm/xilinx_zynq.c
index 17251c7..98e0958 100644
--- a/hw/arm/xilinx_zynq.c
+++ b/hw/arm/xilinx_zynq.c
@@ -49,9 +49,11 @@ static void gem_init(NICInfo *nd, uint32_t base, qemu_irq 
irq)
 DeviceState *dev;
 SysBusDevice *s;
 
-qemu_check_nic_model(nd, cadence_gem);
 dev = qdev_create(NULL, cadence_gem);
-qdev_set_nic_properties(dev, nd);
+if (nd-used) {
+qemu_check_nic_model(nd, cadence_gem);
+qdev_set_nic_properties(dev, nd);
+}
 qdev_init_nofail(dev);
 s = SYS_BUS_DEVICE(dev);
 sysbus_mmio_map(s, 0, base);
@@ -113,7 +115,6 @@ static void zynq_init(QEMUMachineInitArgs *args)
 DeviceState *dev;
 SysBusDevice *busdev;
 qemu_irq pic[64];
-NICInfo *nd;
 Error *err = NULL;
 int n;
 
@@ -190,14 +191,8 @@ static void zynq_init(QEMUMachineInitArgs *args)
 sysbus_create_varargs(cadence_ttc, 0xF8002000,
 pic[69-IRQ_OFFSET], pic[70-IRQ_OFFSET], pic[71-IRQ_OFFSET], NULL);
 
-for (n = 0; n  nb_nics; n++) {
-nd = nd_table[n];
-if (n == 0) {
-gem_init(nd, 0xE000B000, pic[54-IRQ_OFFSET]);
-} else if (n == 1) {
-gem_init(nd, 0xE000C000, pic[77-IRQ_OFFSET]);
-}
-}
+gem_init(nd_table[0], 0xE000B000, pic[54-IRQ_OFFSET]);
+gem_init(nd_table[1], 0xE000C000, pic[77-IRQ_OFFSET]);
 
 dev = qdev_create(NULL, generic-sdhci);
 qdev_init_nofail(dev);
-- 
1.8.5




[Qemu-devel] [PULL 51/52] arm_gic: Rename GIC_X_TRIGGER to GIC_X_EDGE_TRIGGER

2014-01-06 Thread Peter Maydell
From: Christoffer Dall christoffer.d...@linaro.org

TRIGGER can really mean mean anything (e.g. was it triggered, is it
level-triggered, is it edge-triggered, etc.).  Rename to EDGE_TRIGGER to
make the code comprehensible without looking up the data structure.

Reviewed-by: Peter Maydell peter.mayd...@linaro.org
Signed-off-by: Christoffer Dall christoffer.d...@linaro.org
Message-id: 1387606179-22709-2-git-send-email-christoffer.d...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 hw/intc/arm_gic.c| 12 ++--
 hw/intc/arm_gic_common.c |  4 ++--
 hw/intc/gic_internal.h   |  6 +++---
 include/hw/intc/arm_gic_common.h |  2 +-
 4 files changed, 12 insertions(+), 12 deletions(-)

diff --git a/hw/intc/arm_gic.c b/hw/intc/arm_gic.c
index d431b7a..27c258a 100644
--- a/hw/intc/arm_gic.c
+++ b/hw/intc/arm_gic.c
@@ -128,7 +128,7 @@ static void gic_set_irq(void *opaque, int irq, int level)
 
 if (level) {
 GIC_SET_LEVEL(irq, cm);
-if (GIC_TEST_TRIGGER(irq) || GIC_TEST_ENABLED(irq, cm)) {
+if (GIC_TEST_EDGE_TRIGGER(irq) || GIC_TEST_ENABLED(irq, cm)) {
 DPRINTF(Set %d pending mask %x\n, irq, target);
 GIC_SET_PENDING(irq, target);
 }
@@ -188,7 +188,7 @@ void gic_complete_irq(GICState *s, int cpu, int irq)
 return; /* No active IRQ.  */
 /* Mark level triggered interrupts as pending if they are still
raised.  */
-if (!GIC_TEST_TRIGGER(irq)  GIC_TEST_ENABLED(irq, cm)
+if (!GIC_TEST_EDGE_TRIGGER(irq)  GIC_TEST_ENABLED(irq, cm)
  GIC_TEST_LEVEL(irq, cm)  (GIC_TARGET(irq)  cm) != 0) {
 DPRINTF(Set %d pending mask %x\n, irq, cm);
 GIC_SET_PENDING(irq, cm);
@@ -311,7 +311,7 @@ static uint32_t gic_dist_readb(void *opaque, hwaddr offset)
 for (i = 0; i  4; i++) {
 if (GIC_TEST_MODEL(irq + i))
 res |= (1  (i * 2));
-if (GIC_TEST_TRIGGER(irq + i))
+if (GIC_TEST_EDGE_TRIGGER(irq + i))
 res |= (2  (i * 2));
 }
 } else if (offset  0xfe0) {
@@ -386,7 +386,7 @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
 /* If a raised level triggered IRQ enabled then mark
is as pending.  */
 if (GIC_TEST_LEVEL(irq + i, mask)
- !GIC_TEST_TRIGGER(irq + i)) {
+ !GIC_TEST_EDGE_TRIGGER(irq + i)) {
 DPRINTF(Set %d pending mask %x\n, irq + i, mask);
 GIC_SET_PENDING(irq + i, mask);
 }
@@ -478,9 +478,9 @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
 GIC_CLEAR_MODEL(irq + i);
 }
 if (value  (2  (i * 2))) {
-GIC_SET_TRIGGER(irq + i);
+GIC_SET_EDGE_TRIGGER(irq + i);
 } else {
-GIC_CLEAR_TRIGGER(irq + i);
+GIC_CLEAR_EDGE_TRIGGER(irq + i);
 }
 }
 } else {
diff --git a/hw/intc/arm_gic_common.c b/hw/intc/arm_gic_common.c
index c765850..710607b 100644
--- a/hw/intc/arm_gic_common.c
+++ b/hw/intc/arm_gic_common.c
@@ -51,7 +51,7 @@ static const VMStateDescription vmstate_gic_irq_state = {
 VMSTATE_UINT8(active, gic_irq_state),
 VMSTATE_UINT8(level, gic_irq_state),
 VMSTATE_BOOL(model, gic_irq_state),
-VMSTATE_BOOL(trigger, gic_irq_state),
+VMSTATE_BOOL(edge_trigger, gic_irq_state),
 VMSTATE_END_OF_LIST()
 }
 };
@@ -126,7 +126,7 @@ static void arm_gic_common_reset(DeviceState *dev)
 }
 for (i = 0; i  16; i++) {
 GIC_SET_ENABLED(i, ALL_CPU_MASK);
-GIC_SET_TRIGGER(i);
+GIC_SET_EDGE_TRIGGER(i);
 }
 if (s-num_cpu == 1) {
 /* For uniprocessor GICs all interrupts always target the sole CPU */
diff --git a/hw/intc/gic_internal.h b/hw/intc/gic_internal.h
index 3989fd1..efac78d 100644
--- a/hw/intc/gic_internal.h
+++ b/hw/intc/gic_internal.h
@@ -44,9 +44,9 @@
 #define GIC_SET_LEVEL(irq, cm) s-irq_state[irq].level = (cm)
 #define GIC_CLEAR_LEVEL(irq, cm) s-irq_state[irq].level = ~(cm)
 #define GIC_TEST_LEVEL(irq, cm) ((s-irq_state[irq].level  (cm)) != 0)
-#define GIC_SET_TRIGGER(irq) s-irq_state[irq].trigger = true
-#define GIC_CLEAR_TRIGGER(irq) s-irq_state[irq].trigger = false
-#define GIC_TEST_TRIGGER(irq) s-irq_state[irq].trigger
+#define GIC_SET_EDGE_TRIGGER(irq) s-irq_state[irq].edge_trigger = true
+#define GIC_CLEAR_EDGE_TRIGGER(irq) s-irq_state[irq].edge_trigger = false
+#define GIC_TEST_EDGE_TRIGGER(irq) (s-irq_state[irq].edge_trigger)
 #define GIC_GET_PRIORITY(irq, cpu) (((irq)  GIC_INTERNAL) ?\
 s-priority1[irq][cpu] :\
 s-priority2[(irq) - GIC_INTERNAL])
diff --git a/include/hw/intc/arm_gic_common.h b/include/hw/intc/arm_gic_common.h
index 4f381bd..0d232df 100644
--- a/include/hw/intc/arm_gic_common.h

[Qemu-devel] [PULL 46/52] char/cadence_uart: Implement Tx flow control

2014-01-06 Thread Peter Maydell
From: Peter Crosthwaite peter.crosthwa...@xilinx.com

If the UART back-end blocks, buffer in the Tx FIFO to try again later.
This stops the IO-thread busy waiting on char back-ends (which causes
all sorts of performance problems).

Signed-off-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
Message-id: 
4bea048b3ab38425701d82ccc1ab92545c26b79c.1388626249.git.peter.crosthwa...@xilinx.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 hw/char/cadence_uart.c | 31 +--
 1 file changed, 29 insertions(+), 2 deletions(-)

diff --git a/hw/char/cadence_uart.c b/hw/char/cadence_uart.c
index 8a9ef81..1012f1a 100644
--- a/hw/char/cadence_uart.c
+++ b/hw/char/cadence_uart.c
@@ -286,6 +286,34 @@ static void uart_write_rx_fifo(void *opaque, const uint8_t 
*buf, int size)
 uart_update_status(s);
 }
 
+static gboolean cadence_uart_xmit(GIOChannel *chan, GIOCondition cond,
+  void *opaque)
+{
+UartState *s = opaque;
+int ret;
+
+/* instant drain the fifo when there's no back-end */
+if (!s-chr) {
+s-tx_count = 0;
+}
+
+if (!s-tx_count) {
+return FALSE;
+}
+
+ret = qemu_chr_fe_write(s-chr, s-tx_fifo, s-tx_count);
+s-tx_count -= ret;
+memmove(s-tx_fifo, s-tx_fifo + ret, s-tx_count);
+
+if (s-tx_count) {
+int r = qemu_chr_fe_add_watch(s-chr, G_IO_OUT, cadence_uart_xmit, s);
+assert(r);
+}
+
+uart_update_status(s);
+return FALSE;
+}
+
 static void uart_write_tx_fifo(UartState *s, const uint8_t *buf, int size)
 {
 if ((s-r[R_CR]  UART_CR_TX_DIS) || !(s-r[R_CR]  UART_CR_TX_EN)) {
@@ -306,8 +334,7 @@ static void uart_write_tx_fifo(UartState *s, const uint8_t 
*buf, int size)
 memcpy(s-tx_fifo + s-tx_count, buf, size);
 s-tx_count += size;
 
-qemu_chr_fe_write_all(s-chr, s-tx_fifo, s-tx_count);
-s-tx_count = 0;
+cadence_uart_xmit(NULL, G_IO_OUT, s);
 }
 
 static void uart_receive(void *opaque, const uint8_t *buf, int size)
-- 
1.8.5




[Qemu-devel] [PULL 52/52] hw: arm_gic: Introduce gic_set_priority function

2014-01-06 Thread Peter Maydell
From: Christoffer Dall christoffer.d...@linaro.org

To make the code slightly cleaner to look at and make the save/restore
code easier to understand, introduce this function to set the priority of
interrupts.

Reviewed-by: Peter Maydell peter.mayd...@linaro.org
Signed-off-by: Christoffer Dall christoffer.d...@linaro.org
Message-id: 1387606179-22709-3-git-send-email-christoffer.d...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 hw/intc/arm_gic.c  | 15 ++-
 hw/intc/gic_internal.h |  1 +
 2 files changed, 11 insertions(+), 5 deletions(-)

diff --git a/hw/intc/arm_gic.c b/hw/intc/arm_gic.c
index 27c258a..6c59650 100644
--- a/hw/intc/arm_gic.c
+++ b/hw/intc/arm_gic.c
@@ -168,6 +168,15 @@ uint32_t gic_acknowledge_irq(GICState *s, int cpu)
 return new_irq;
 }
 
+void gic_set_priority(GICState *s, int cpu, int irq, uint8_t val)
+{
+if (irq  GIC_INTERNAL) {
+s-priority1[irq][cpu] = val;
+} else {
+s-priority2[(irq) - GIC_INTERNAL] = val;
+}
+}
+
 void gic_complete_irq(GICState *s, int cpu, int irq)
 {
 int update = 0;
@@ -443,11 +452,7 @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
 irq = (offset - 0x400) + GIC_BASE_IRQ;
 if (irq = s-num_irq)
 goto bad_reg;
-if (irq  GIC_INTERNAL) {
-s-priority1[irq][cpu] = value;
-} else {
-s-priority2[irq - GIC_INTERNAL] = value;
-}
+gic_set_priority(s, cpu, irq, value);
 } else if (offset  0xc00) {
 /* Interrupt CPU Target. RAZ/WI on uniprocessor GICs, with the
  * annoying exception of the 11MPCore's GIC.
diff --git a/hw/intc/gic_internal.h b/hw/intc/gic_internal.h
index efac78d..8c02d58 100644
--- a/hw/intc/gic_internal.h
+++ b/hw/intc/gic_internal.h
@@ -61,5 +61,6 @@ uint32_t gic_acknowledge_irq(GICState *s, int cpu);
 void gic_complete_irq(GICState *s, int cpu, int irq);
 void gic_update(GICState *s);
 void gic_init_irqs_and_distributor(GICState *s, int num_irq);
+void gic_set_priority(GICState *s, int cpu, int irq, uint8_t val);
 
 #endif /* !QEMU_ARM_GIC_INTERNAL_H */
-- 
1.8.5




[Qemu-devel] [PULL 48/52] target-arm: remove raw_read|write duplication

2014-01-06 Thread Peter Maydell
From: Peter Crosthwaite peter.crosthwa...@xilinx.com

There is an inline duplication of the raw_read and raw_write function
bodies. Fix by just calling raw_read/raw_write instead.

Signed-off-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
Reviewed-by: Peter Maydell peter.mayd...@linaro.org
Message-id: 
e69281b7e1462b346cb313cf0b89eedc0568125f.1388649290.git.peter.crosthwa...@xilinx.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 target-arm/helper.c | 12 ++--
 1 file changed, 2 insertions(+), 10 deletions(-)

diff --git a/target-arm/helper.c b/target-arm/helper.c
index 4af2f9c..d27e528 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -142,11 +142,7 @@ static bool read_raw_cp_reg(CPUARMState *env, const 
ARMCPRegInfo *ri,
 } else if (ri-readfn) {
 return (ri-readfn(env, ri, v) == 0);
 } else {
-if (ri-type  ARM_CP_64BIT) {
-*v = CPREG_FIELD64(env, ri);
-} else {
-*v = CPREG_FIELD32(env, ri);
-}
+raw_read(env, ri, v);
 }
 return true;
 }
@@ -167,11 +163,7 @@ static bool write_raw_cp_reg(CPUARMState *env, const 
ARMCPRegInfo *ri,
 } else if (ri-writefn) {
 return (ri-writefn(env, ri, v) == 0);
 } else {
-if (ri-type  ARM_CP_64BIT) {
-CPREG_FIELD64(env, ri) = v;
-} else {
-CPREG_FIELD32(env, ri) = v;
-}
+raw_write(env, ri, v);
 }
 return true;
 }
-- 
1.8.5




[Qemu-devel] [PULL 50/52] target-arm: fix build with gcc 4.8.2

2014-01-06 Thread Peter Maydell
From: Michael S. Tsirkin m...@redhat.com

commit 5ce4f35781028ce1aee3341e6002f925fdc7aaf3
target-arm: A64: add set_pc cpu method

introduces an array aarch64_cpus which is zero
size if this code is built without CONFIG_USER_ONLY.
In particular an attempt to iterate over this array produces a warning
under gcc 4.8.2:

 CCaarch64-softmmu/target-arm/cpu64.o
/scm/qemu/target-arm/cpu64.c: In function ‘aarch64_cpu_register_types’:
/scm/qemu/target-arm/cpu64.c:124:5: error: comparison of unsigned
expression  0 is always false [-Werror=type-limits]
 for (i = 0; i  ARRAY_SIZE(aarch64_cpus); i++) {
 ^
cc1: all warnings being treated as errors

This is the result of ARRAY_SIZE being an unsigned type,
causing i to be promoted to unsigned int as well.

As zero size arrays are a gcc extension, it seems
cleanest to add a dummy element with NULL name,
and test for it during registration.

We'll be able to drop this when we add more CPUs.

Cc: Alexander Graf ag...@suse.de
Cc: Peter Maydell peter.mayd...@linaro.org
Cc: Richard Henderson r...@twiddle.net
Signed-off-by: Michael S. Tsirkin m...@redhat.com
Reviewed-by: Stefan Weil s...@weilnetz.de
Reviewed-by: Peter Maydell peter.mayd...@linaro.org
Message-id: 20131223145216.ga22...@redhat.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 target-arm/cpu64.c | 6 ++
 1 file changed, 6 insertions(+)

diff --git a/target-arm/cpu64.c b/target-arm/cpu64.c
index 04ce879..60acd24 100644
--- a/target-arm/cpu64.c
+++ b/target-arm/cpu64.c
@@ -58,6 +58,7 @@ static const ARMCPUInfo aarch64_cpus[] = {
 #ifdef CONFIG_USER_ONLY
 { .name = any, .initfn = aarch64_any_initfn },
 #endif
+{ .name = NULL } /* TODO: drop when we support more CPUs */
 };
 
 static void aarch64_cpu_initfn(Object *obj)
@@ -100,6 +101,11 @@ static void aarch64_cpu_register(const ARMCPUInfo *info)
 .class_init = info-class_init,
 };
 
+/* TODO: drop when we support more CPUs - all entries will have name set */
+if (!info-name) {
+return;
+}
+
 type_info.name = g_strdup_printf(%s- TYPE_ARM_CPU, info-name);
 type_register(type_info);
 g_free((void *)type_info.name);
-- 
1.8.5




[Qemu-devel] [PULL 45/52] char/cadence_uart: Delete redundant rx rst logic

2014-01-06 Thread Peter Maydell
From: Peter Crosthwaite peter.crosthwa...@xilinx.com

uart_rx_reset() called immediately above already does this. Remove.

Signed-off-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
Message-id: 
05e30826496cf2579084ed801ac0b2c0d0a3071f.1388626249.git.peter.crosthwa...@xilinx.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 hw/char/cadence_uart.c | 2 --
 1 file changed, 2 deletions(-)

diff --git a/hw/char/cadence_uart.c b/hw/char/cadence_uart.c
index be32126..8a9ef81 100644
--- a/hw/char/cadence_uart.c
+++ b/hw/char/cadence_uart.c
@@ -438,8 +438,6 @@ static void cadence_uart_reset(DeviceState *dev)
 uart_rx_reset(s);
 uart_tx_reset(s);
 
-s-rx_count = 0;
-s-rx_wpos = 0;
 uart_update_status(s);
 }
 
-- 
1.8.5




[Qemu-devel] [PULL 31/52] target-arm: A64: Add fmov (scalar, immediate) instruction

2014-01-06 Thread Peter Maydell
From: Alexander Graf ag...@suse.de

This patch adds emulation for the fmov instruction working on scalars
with an immediate payload.

Signed-off-by: Alexander Graf ag...@suse.de
[WN: Commit message tweak, rebase and use new infrastructure.]
Signed-off-by: Will Newton will.new...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 32 +++-
 1 file changed, 31 insertions(+), 1 deletion(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 84497dc..bb36a66 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -3479,7 +3479,37 @@ static void disas_fp_3src(DisasContext *s, uint32_t insn)
  */
 static void disas_fp_imm(DisasContext *s, uint32_t insn)
 {
-unsupported_encoding(s, insn);
+int rd = extract32(insn, 0, 5);
+int imm8 = extract32(insn, 13, 8);
+int is_double = extract32(insn, 22, 2);
+uint64_t imm;
+TCGv_i64 tcg_res;
+
+if (is_double  1) {
+unallocated_encoding(s);
+return;
+}
+
+/* The imm8 encodes the sign bit, enough bits to represent
+ * an exponent in the range 011xx to 100xx,
+ * and the most significant 4 bits of the mantissa; see
+ * VFPExpandImm() in the v8 ARM ARM.
+ */
+if (is_double) {
+imm = (extract32(imm8, 7, 1) ? 0x8000 : 0) |
+(extract32(imm8, 6, 1) ? 0x3fc0 : 0x4000) |
+extract32(imm8, 0, 6);
+imm = 48;
+} else {
+imm = (extract32(imm8, 7, 1) ? 0x8000 : 0) |
+(extract32(imm8, 6, 1) ? 0x3e00 : 0x4000) |
+(extract32(imm8, 0, 6)  3);
+imm = 16;
+}
+
+tcg_res = tcg_const_i64(imm);
+write_fp_dreg(s, rd, tcg_res);
+tcg_temp_free_i64(tcg_res);
 }
 
 /* C3.6.29 Floating point - fixed point conversions
-- 
1.8.5




[Qemu-devel] [PULL 44/52] char/cadence_uart: Use the TX fifo for transmission

2014-01-06 Thread Peter Maydell
From: Peter Crosthwaite peter.crosthwa...@xilinx.com

Populate the TxFIFO with the Tx data before sending. Prepares
support for proper Tx flow control implementation.

Signed-off-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
Message-id: 
bdf7f8af2ef02839bea18665701bc2612f7baa6f.1388626249.git.peter.crosthwa...@xilinx.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 hw/char/cadence_uart.c | 17 -
 1 file changed, 16 insertions(+), 1 deletion(-)

diff --git a/hw/char/cadence_uart.c b/hw/char/cadence_uart.c
index 3bcaf29..be32126 100644
--- a/hw/char/cadence_uart.c
+++ b/hw/char/cadence_uart.c
@@ -292,7 +292,22 @@ static void uart_write_tx_fifo(UartState *s, const uint8_t 
*buf, int size)
 return;
 }
 
-qemu_chr_fe_write_all(s-chr, buf, size);
+if (size  TX_FIFO_SIZE - s-tx_count) {
+size = TX_FIFO_SIZE - s-tx_count;
+/*
+ * This can only be a guest error via a bad tx fifo register push,
+ * as can_receive() should stop remote loop and echo modes ever getting
+ * us to here.
+ */
+qemu_log_mask(LOG_GUEST_ERROR, cadence_uart: TxFIFO overflow);
+s-r[R_CISR] |= UART_INTR_ROVR;
+}
+
+memcpy(s-tx_fifo + s-tx_count, buf, size);
+s-tx_count += size;
+
+qemu_chr_fe_write_all(s-chr, s-tx_fifo, s-tx_count);
+s-tx_count = 0;
 }
 
 static void uart_receive(void *opaque, const uint8_t *buf, int size)
-- 
1.8.5




[Qemu-devel] [PULL 30/52] target-arm: A64: Add Floating-point data-processing (3 source) insns

2014-01-06 Thread Peter Maydell
From: Alexander Graf ag...@suse.de

This patch adds emulation for the Floating-point data-processing (3 source)
group of instructions.

Signed-off-by: Alexander Graf ag...@suse.de
[WN: Commit message tweak, merged single and double precision patches.
 Implement using muladd as suggested by Richard Henderson.]
Signed-off-by: Will Newton will.new...@linaro.org
[PMM: pull field decode up a level, use register accessors]
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 95 +-
 1 file changed, 94 insertions(+), 1 deletion(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index c406e2a..84497dc 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -3367,6 +3367,82 @@ static void disas_fp_2src(DisasContext *s, uint32_t insn)
 }
 }
 
+/* C3.6.27 Floating-point data-processing (3 source) - single precision */
+static void handle_fp_3src_single(DisasContext *s, bool o0, bool o1,
+  int rd, int rn, int rm, int ra)
+{
+TCGv_i32 tcg_op1, tcg_op2, tcg_op3;
+TCGv_i32 tcg_res = tcg_temp_new_i32();
+TCGv_ptr fpst = get_fpstatus_ptr();
+
+tcg_op1 = read_fp_sreg(s, rn);
+tcg_op2 = read_fp_sreg(s, rm);
+tcg_op3 = read_fp_sreg(s, ra);
+
+/* These are fused multiply-add, and must be done as one
+ * floating point operation with no rounding between the
+ * multiplication and addition steps.
+ * NB that doing the negations here as separate steps is
+ * correct : an input NaN should come out with its sign bit
+ * flipped if it is a negated-input.
+ */
+if (o1 == true) {
+gen_helper_vfp_negs(tcg_op3, tcg_op3);
+}
+
+if (o0 != o1) {
+gen_helper_vfp_negs(tcg_op1, tcg_op1);
+}
+
+gen_helper_vfp_muladds(tcg_res, tcg_op1, tcg_op2, tcg_op3, fpst);
+
+write_fp_sreg(s, rd, tcg_res);
+
+tcg_temp_free_ptr(fpst);
+tcg_temp_free_i32(tcg_op1);
+tcg_temp_free_i32(tcg_op2);
+tcg_temp_free_i32(tcg_op3);
+tcg_temp_free_i32(tcg_res);
+}
+
+/* C3.6.27 Floating-point data-processing (3 source) - double precision */
+static void handle_fp_3src_double(DisasContext *s, bool o0, bool o1,
+  int rd, int rn, int rm, int ra)
+{
+TCGv_i64 tcg_op1, tcg_op2, tcg_op3;
+TCGv_i64 tcg_res = tcg_temp_new_i64();
+TCGv_ptr fpst = get_fpstatus_ptr();
+
+tcg_op1 = read_fp_dreg(s, rn);
+tcg_op2 = read_fp_dreg(s, rm);
+tcg_op3 = read_fp_dreg(s, ra);
+
+/* These are fused multiply-add, and must be done as one
+ * floating point operation with no rounding between the
+ * multiplication and addition steps.
+ * NB that doing the negations here as separate steps is
+ * correct : an input NaN should come out with its sign bit
+ * flipped if it is a negated-input.
+ */
+if (o1 == true) {
+gen_helper_vfp_negd(tcg_op3, tcg_op3);
+}
+
+if (o0 != o1) {
+gen_helper_vfp_negd(tcg_op1, tcg_op1);
+}
+
+gen_helper_vfp_muladdd(tcg_res, tcg_op1, tcg_op2, tcg_op3, fpst);
+
+write_fp_dreg(s, rd, tcg_res);
+
+tcg_temp_free_ptr(fpst);
+tcg_temp_free_i64(tcg_op1);
+tcg_temp_free_i64(tcg_op2);
+tcg_temp_free_i64(tcg_op3);
+tcg_temp_free_i64(tcg_res);
+}
+
 /* C3.6.27 Floating point data-processing (3 source)
  *   31  30  29 28   24 23  22  21  20  16  15  14  10 95 40
  * +---+---+---+---+--++--++--+--+--+
@@ -3375,7 +3451,24 @@ static void disas_fp_2src(DisasContext *s, uint32_t insn)
  */
 static void disas_fp_3src(DisasContext *s, uint32_t insn)
 {
-unsupported_encoding(s, insn);
+int type = extract32(insn, 22, 2);
+int rd = extract32(insn, 0, 5);
+int rn = extract32(insn, 5, 5);
+int ra = extract32(insn, 10, 5);
+int rm = extract32(insn, 16, 5);
+bool o0 = extract32(insn, 15, 1);
+bool o1 = extract32(insn, 21, 1);
+
+switch (type) {
+case 0:
+handle_fp_3src_single(s, o0, o1, rd, rn, rm, ra);
+break;
+case 1:
+handle_fp_3src_double(s, o0, o1, rd, rn, rm, ra);
+break;
+default:
+unallocated_encoding(s);
+}
 }
 
 /* C3.6.28 Floating point immediate
-- 
1.8.5




[Qemu-devel] [PULL 39/52] char/cadence_uart: s/r_fifo/rx_fifo

2014-01-06 Thread Peter Maydell
From: Peter Crosthwaite peter.crosthwa...@xilinx.com

Rename this field to match the many other uses of rx. Xilinx
docmentation (UG585) also refers to this as RxFIFO.

Signed-off-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
Message-id: 
7386d7cee0ea175f7e53ed5ff045265528d34e32.1388626249.git.peter.crosthwa...@xilinx.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 hw/char/cadence_uart.c | 8 
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/hw/char/cadence_uart.c b/hw/char/cadence_uart.c
index 7edc119..d6abc5b 100644
--- a/hw/char/cadence_uart.c
+++ b/hw/char/cadence_uart.c
@@ -116,7 +116,7 @@ typedef struct {
 
 MemoryRegion iomem;
 uint32_t r[R_MAX];
-uint8_t r_fifo[RX_FIFO_SIZE];
+uint8_t rx_fifo[RX_FIFO_SIZE];
 uint32_t rx_wpos;
 uint32_t rx_count;
 uint64_t char_tx_time;
@@ -280,7 +280,7 @@ static void uart_write_rx_fifo(void *opaque, const uint8_t 
*buf, int size)
 s-r[R_CISR] |= UART_INTR_ROVR;
 } else {
 for (i = 0; i  size; i++) {
-s-r_fifo[s-rx_wpos] = buf[i];
+s-rx_fifo[s-rx_wpos] = buf[i];
 s-rx_wpos = (s-rx_wpos + 1) % RX_FIFO_SIZE;
 s-rx_count++;
 
@@ -344,7 +344,7 @@ static void uart_read_rx_fifo(UartState *s, uint32_t *c)
 if (s-rx_count) {
 uint32_t rx_rpos =
 (RX_FIFO_SIZE + s-rx_wpos - s-rx_count) % RX_FIFO_SIZE;
-*c = s-r_fifo[rx_rpos];
+*c = s-rx_fifo[rx_rpos];
 s-rx_count--;
 
 if (!s-rx_count) {
@@ -492,7 +492,7 @@ static const VMStateDescription vmstate_cadence_uart = {
 .post_load = cadence_uart_post_load,
 .fields = (VMStateField[]) {
 VMSTATE_UINT32_ARRAY(r, UartState, R_MAX),
-VMSTATE_UINT8_ARRAY(r_fifo, UartState, RX_FIFO_SIZE),
+VMSTATE_UINT8_ARRAY(rx_fifo, UartState, RX_FIFO_SIZE),
 VMSTATE_UINT32(rx_count, UartState),
 VMSTATE_UINT32(rx_wpos, UartState),
 VMSTATE_TIMER(fifo_trigger_handle, UartState),
-- 
1.8.5




[Qemu-devel] [PULL 04/52] target-arm: A64: add support for ld/st with index

2014-01-06 Thread Peter Maydell
From: Alex Bennée alex.ben...@linaro.org

This adds support for the pre/post-index ld/st forms with immediate
offsets as well as the un-scaled immediate form (which are all
variations on the same 9-bit immediate instruction form).

Signed-off-by: Alex Bennée alex.ben...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 125 -
 1 file changed, 124 insertions(+), 1 deletion(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 67efcf9..a2cc9f0 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -950,6 +950,110 @@ static void disas_ldst_pair(DisasContext *s, uint32_t 
insn)
 }
 
 /*
+ * C3.3.8 Load/store (immediate post-indexed)
+ * C3.3.9 Load/store (immediate pre-indexed)
+ * C3.3.12 Load/store (unscaled immediate)
+ *
+ * 31 30 29   27  26 25 24 23 22 21  2012 11 10 95 40
+ * ++---+---+-+-+---++-+--+--+
+ * |size| 1 1 1 | V | 0 0 | opc | 0 |  imm9  | idx |  Rn  |  Rt  |
+ * ++---+---+-+-+---++-+--+--+
+ *
+ * idx = 01 - post-indexed, 11 pre-indexed, 00 unscaled imm. (no writeback)
+ * V = 0 - non-vector
+ * size: 00 - 8 bit, 01 - 16 bit, 10 - 32 bit, 11 - 64bit
+ * opc: 00 - store, 01 - loadu, 10 - loads 64, 11 - loads 32
+ */
+static void disas_ldst_reg_imm9(DisasContext *s, uint32_t insn)
+{
+int rt = extract32(insn, 0, 5);
+int rn = extract32(insn, 5, 5);
+int imm9 = sextract32(insn, 12, 9);
+int opc = extract32(insn, 22, 2);
+int size = extract32(insn, 30, 2);
+int idx = extract32(insn, 10, 2);
+bool is_signed = false;
+bool is_store = false;
+bool is_extended = false;
+bool is_vector = extract32(insn, 26, 1);
+bool post_index;
+bool writeback;
+
+TCGv_i64 tcg_addr;
+
+if (is_vector) {
+size |= (opc  2)  1;
+if (size  4) {
+unallocated_encoding(s);
+return;
+}
+is_store = ((opc  1) == 0);
+} else {
+if (size == 3  opc == 2) {
+/* PRFM - prefetch */
+return;
+}
+if (opc == 3  size  1) {
+unallocated_encoding(s);
+return;
+}
+is_store = (opc == 0);
+is_signed = opc  (11);
+is_extended = (size  3)  (opc  1);
+}
+
+switch (idx) {
+case 0:
+post_index = false;
+writeback = false;
+break;
+case 1:
+post_index = true;
+writeback = true;
+break;
+case 3:
+post_index = false;
+writeback = true;
+break;
+case 2:
+g_assert(false);
+break;
+}
+
+if (rn == 31) {
+gen_check_sp_alignment(s);
+}
+tcg_addr = read_cpu_reg_sp(s, rn, 1);
+
+if (!post_index) {
+tcg_gen_addi_i64(tcg_addr, tcg_addr, imm9);
+}
+
+if (is_vector) {
+if (is_store) {
+do_fp_st(s, rt, tcg_addr, size);
+} else {
+do_fp_ld(s, rt, tcg_addr, size);
+}
+} else {
+TCGv_i64 tcg_rt = cpu_reg(s, rt);
+if (is_store) {
+do_gpr_st(s, tcg_rt, tcg_addr, size);
+} else {
+do_gpr_ld(s, tcg_rt, tcg_addr, size, is_signed, is_extended);
+}
+}
+
+if (writeback) {
+TCGv_i64 tcg_rn = cpu_reg_sp(s, rn);
+if (post_index) {
+tcg_gen_addi_i64(tcg_addr, tcg_addr, imm9);
+}
+tcg_gen_mov_i64(tcg_rn, tcg_addr);
+}
+}
+
+/*
  * C3.3.10 Load/store (register offset)
  *
  * 31 30 29   27  26 25 24 23 22 21  20  16 15 13 12 11 10 9  5 4  0
@@ -1116,6 +1220,25 @@ static void disas_ldst_reg_unsigned_imm(DisasContext *s, 
uint32_t insn)
 }
 }
 
+/* Load/store register (immediate forms) */
+static void disas_ldst_reg_imm(DisasContext *s, uint32_t insn)
+{
+switch (extract32(insn, 10, 2)) {
+case 0: case 1: case 3:
+/* Load/store register (unscaled immediate) */
+/* Load/store immediate pre/post-indexed */
+disas_ldst_reg_imm9(s, insn);
+break;
+case 2:
+/* Load/store register unprivileged */
+unsupported_encoding(s, insn);
+break;
+default:
+unallocated_encoding(s);
+break;
+}
+}
+
 /* Load/store register (all forms) */
 static void disas_ldst_reg(DisasContext *s, uint32_t insn)
 {
@@ -1124,7 +1247,7 @@ static void disas_ldst_reg(DisasContext *s, uint32_t insn)
 if (extract32(insn, 21, 1) == 1  extract32(insn, 10, 2) == 2) {
 disas_ldst_reg_roffset(s, insn);
 } else {
-unsupported_encoding(s, insn);
+disas_ldst_reg_imm(s, insn);
 }
 break;
 case 1:
-- 
1.8.5




[Qemu-devel] [PULL 26/52] target-arm: A64: Add support for dumping AArch64 VFP register state

2014-01-06 Thread Peter Maydell
From: Alexander Graf ag...@suse.de

When dumping the current CPU state, we can also get a request
to dump the FPU state along with the CPU's integer state.

Add support to dump the VFP state when that flag is set, so that
we can properly debug code that modifies floating point registers.

Signed-off-by: Alexander Graf ag...@suse.de
[WN: Commit message tweak, rebased. Output all registers, two per-line.]
Signed-off-by: Will Newton will.new...@linaro.org
Reviewed-by: Peter Maydell peter.mayd...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 16 
 1 file changed, 16 insertions(+)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 40c6fc4..326f36d 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -119,6 +119,22 @@ void aarch64_cpu_dump_state(CPUState *cs, FILE *f,
 psr  PSTATE_C ? 'C' : '-',
 psr  PSTATE_V ? 'V' : '-');
 cpu_fprintf(f, \n);
+
+if (flags  CPU_DUMP_FPU) {
+int numvfpregs = 32;
+for (i = 0; i  numvfpregs; i += 2) {
+uint64_t vlo = float64_val(env-vfp.regs[i * 2]);
+uint64_t vhi = float64_val(env-vfp.regs[(i * 2) + 1]);
+cpu_fprintf(f, q%02d=%016 PRIx64 :%016 PRIx64  ,
+i, vhi, vlo);
+vlo = float64_val(env-vfp.regs[(i + 1) * 2]);
+vhi = float64_val(env-vfp.regs[((i + 1) * 2) + 1]);
+cpu_fprintf(f, q%02d=%016 PRIx64 :%016 PRIx64 \n,
+i + 1, vhi, vlo);
+}
+cpu_fprintf(f, FPCR: %08x  FPSR: %08x\n,
+vfp_get_fpcr(env), vfp_get_fpsr(env));
+}
 }
 
 static int get_mem_index(DisasContext *s)
-- 
1.8.5




[Qemu-devel] [PULL 09/52] target-arm: A64: Add decoder skeleton for FP instructions

2014-01-06 Thread Peter Maydell
Add a top level decoder skeleton for FP instructions.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 170 -
 1 file changed, 169 insertions(+), 1 deletion(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 9ca6460..079c2f7 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -2670,10 +2670,178 @@ static void disas_data_proc_reg(DisasContext *s, 
uint32_t insn)
 }
 }
 
+/* C3.6.22 Floating point compare
+ *   31  30  29 28   24 23  22  21 20  16 15 14 13  1095 4 0
+ * +---+---+---+---+--+---+--+-+-+--+---+
+ * | M | 0 | S | 1 1 1 1 0 | type | 1 |  Rm  | op  | 1 0 0 0 |  Rn  |  op2  |
+ * +---+---+---+---+--+---+--+-+-+--+---+
+ */
+static void disas_fp_compare(DisasContext *s, uint32_t insn)
+{
+unsupported_encoding(s, insn);
+}
+
+/* C3.6.23 Floating point conditional compare
+ *   31  30  29 28   24 23  22  21 20  16 15  12 11 10 95  4   30
+ * +---+---+---+---+--+---+--+--+-+--++--+
+ * | M | 0 | S | 1 1 1 1 0 | type | 1 |  Rm  | cond | 0 1 |  Rn  | op | nzcv |
+ * +---+---+---+---+--+---+--+--+-+--++--+
+ */
+static void disas_fp_ccomp(DisasContext *s, uint32_t insn)
+{
+unsupported_encoding(s, insn);
+}
+
+/* C3.6.24 Floating point conditional select
+ *   31  30  29 28   24 23  22  21 20  16 15  12 11 10 95 40
+ * +---+---+---+---+--+---+--+--+-+--+--+
+ * | M | 0 | S | 1 1 1 1 0 | type | 1 |  Rm  | cond | 1 1 |  Rn  |  Rd  |
+ * +---+---+---+---+--+---+--+--+-+--+--+
+ */
+static void disas_fp_csel(DisasContext *s, uint32_t insn)
+{
+unsupported_encoding(s, insn);
+}
+
+/* C3.6.25 Floating point data-processing (1 source)
+ *   31  30  29 28   24 23  22  21 2015 14   10 95 40
+ * +---+---+---+---+--+---++---+--+--+
+ * | M | 0 | S | 1 1 1 1 0 | type | 1 | opcode | 1 0 0 0 0 |  Rn  |  Rd  |
+ * +---+---+---+---+--+---++---+--+--+
+ */
+static void disas_fp_1src(DisasContext *s, uint32_t insn)
+{
+unsupported_encoding(s, insn);
+}
+
+/* C3.6.26 Floating point data-processing (2 source)
+ *   31  30  29 28   24 23  22  21 20  16 1512 11 10 95 40
+ * +---+---+---+---+--+---+--++-+--+--+
+ * | M | 0 | S | 1 1 1 1 0 | type | 1 |  Rm  | opcode | 1 0 |  Rn  |  Rd  |
+ * +---+---+---+---+--+---+--++-+--+--+
+ */
+static void disas_fp_2src(DisasContext *s, uint32_t insn)
+{
+unsupported_encoding(s, insn);
+}
+
+/* C3.6.27 Floating point data-processing (3 source)
+ *   31  30  29 28   24 23  22  21  20  16  15  14  10 95 40
+ * +---+---+---+---+--++--++--+--+--+
+ * | M | 0 | S | 1 1 1 1 1 | type | o1 |  Rm  | o0 |  Ra  |  Rn  |  Rd  |
+ * +---+---+---+---+--++--++--+--+--+
+ */
+static void disas_fp_3src(DisasContext *s, uint32_t insn)
+{
+unsupported_encoding(s, insn);
+}
+
+/* C3.6.28 Floating point immediate
+ *   31  30  29 28   24 23  22  21 2013 12   10 95 40
+ * +---+---+---+---+--+---++---+--+--+
+ * | M | 0 | S | 1 1 1 1 0 | type | 1 |imm8| 1 0 0 | imm5 |  Rd  |
+ * +---+---+---+---+--+---++---+--+--+
+ */
+static void disas_fp_imm(DisasContext *s, uint32_t insn)
+{
+unsupported_encoding(s, insn);
+}
+
+/* C3.6.29 Floating point - fixed point conversions
+ *   31   30  29 28   24 23  22  21 20   19 1816 15   10 95 40
+ * ++---+---+---+--+---+---++---+--+--+
+ * | sf | 0 | S | 1 1 1 1 0 | type | 0 | rmode | opcode | scale |  Rn  |  Rd  |
+ * ++---+---+---+--+---+---++---+--+--+
+ */
+static void disas_fp_fixed_conv(DisasContext *s, uint32_t insn)
+{
+unsupported_encoding(s, insn);
+}
+
+/* C3.6.30 Floating point - integer conversions
+ *   31   30  29 28   24 23  22  21 20   19 18 16 15 10 9  5 4  0
+ * ++---+---+---+--+---+---+-+-+++
+ * | sf | 0 | S | 1 1 1 1 0 | type | 0 | rmode | opc | 0 0 0 0 0 0 | Rn | Rd |
+ * ++---+---+---+--+---+---+-+-+++
+ */
+static void disas_fp_int_conv(DisasContext *s, uint32_t insn)
+{
+unsupported_encoding(s, insn);
+}
+
+/* FP-specific subcases of table C3-6 (SIMD and FP data processing)
+ *   31  30  29 28 25 24  0
+ * +---+---+---+-+-+
+ * |   | 0 |   | 1 1 1 1 |

[Qemu-devel] [PULL 47/52] target-arm: use c13_context field for CONTEXTIDR

2014-01-06 Thread Peter Maydell
From: Sergey Fedorov s.fedo...@samsung.com

Use c13_context field instead of c13_fcse for CONTEXTIDR register
definition.

Signed-off-by: Sergey Fedorov s.fedo...@samsung.com
Reviewed-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
Reviewed-by: Peter Maydell peter.mayd...@linaro.org
Message-id: 1387521191-15350-1-git-send-email-s.fedo...@samsung.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 target-arm/helper.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/target-arm/helper.c b/target-arm/helper.c
index 265675d..4af2f9c 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -397,7 +397,7 @@ static const ARMCPRegInfo cp_reginfo[] = {
   .access = PL1_RW, .fieldoffset = offsetof(CPUARMState, cp15.c13_fcse),
   .resetvalue = 0, .writefn = fcse_write, .raw_writefn = raw_write, },
 { .name = CONTEXTIDR, .cp = 15, .crn = 13, .crm = 0, .opc1 = 0, .opc2 = 
1,
-  .access = PL1_RW, .fieldoffset = offsetof(CPUARMState, cp15.c13_fcse),
+  .access = PL1_RW, .fieldoffset = offsetof(CPUARMState, cp15.c13_context),
   .resetvalue = 0, .writefn = contextidr_write, .raw_writefn = raw_write, 
},
 /* ??? This covers not just the impdef TLB lockdown registers but also
  * some v7VMSA registers relating to TEX remap, so it is overly broad.
-- 
1.8.5




[Qemu-devel] [PULL 36/52] char/cadence_uart: Mark struct fields as public/private

2014-01-06 Thread Peter Maydell
From: Peter Crosthwaite peter.crosthwa...@xilinx.com

As per current QOM conventions.

Signed-off-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
Message-id: 
a1e31bd62e9709ffb9b3efc6c120f83f30b7a660.1388626249.git.peter.crosthwa...@xilinx.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 hw/char/cadence_uart.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/hw/char/cadence_uart.c b/hw/char/cadence_uart.c
index f18db53..a7b2f21 100644
--- a/hw/char/cadence_uart.c
+++ b/hw/char/cadence_uart.c
@@ -110,7 +110,9 @@
 #define CADENCE_UART(obj) OBJECT_CHECK(UartState, (obj), TYPE_CADENCE_UART)
 
 typedef struct {
+/* private */
 SysBusDevice parent_obj;
+/* public */
 
 MemoryRegion iomem;
 uint32_t r[R_MAX];
-- 
1.8.5




[Qemu-devel] [PULL 42/52] char/cadence_uart: Remove TX timer add TX FIFO state

2014-01-06 Thread Peter Maydell
From: Peter Crosthwaite peter.crosthwa...@xilinx.com

This tx timer implementation is flawed. Despite the controller
attempting to time the guest visable assertion of the TX-empty status
bit (and corresponding interrupt) the controller is still transmitting
characters instantaneously. There is also no sense of multiple character
delay.

The only side effect of this timer is assertion of tx-empty status. So
just remove the timer completely and hold tx-empty as permanently
asserted (its reset status). This matches the actual behaviour of
instantaneous transmission.

While we are VMSD version bumping, add the tx_fifo as device state to
prepare for upcomming TxFIFO flow control. Implement the interrupt
generation logic for the TxFIFO occupancy.

Signed-off-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
Message-id: 
7a208a7eb8d79d6429fe28b1396c3104371807b2.1388626249.git.peter.crosthwa...@xilinx.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 hw/char/cadence_uart.c | 44 +---
 1 file changed, 13 insertions(+), 31 deletions(-)

diff --git a/hw/char/cadence_uart.c b/hw/char/cadence_uart.c
index 216eed7..3eeadb1 100644
--- a/hw/char/cadence_uart.c
+++ b/hw/char/cadence_uart.c
@@ -121,13 +121,14 @@ typedef struct {
 MemoryRegion iomem;
 uint32_t r[R_MAX];
 uint8_t rx_fifo[RX_FIFO_SIZE];
+uint8_t tx_fifo[TX_FIFO_SIZE];
 uint32_t rx_wpos;
 uint32_t rx_count;
+uint32_t tx_count;
 uint64_t char_tx_time;
 CharDriverState *chr;
 qemu_irq irq;
 QEMUTimer *fifo_trigger_handle;
-QEMUTimer *tx_time_handle;
 } UartState;
 
 static void uart_update_status(UartState *s)
@@ -138,8 +139,12 @@ static void uart_update_status(UartState *s)
 s-r[R_SR] |= !s-rx_count ? UART_SR_INTR_REMPTY : 0;
 s-r[R_SR] |= s-rx_count = s-r[R_RTRIG] ? UART_SR_INTR_RTRIG : 0;
 
-s-r[R_SR] |= UART_SR_INTR_TEMPTY;
+s-r[R_SR] |= s-tx_count == TX_FIFO_SIZE ? UART_SR_INTR_TFUL : 0;
+s-r[R_SR] |= !s-tx_count ? UART_SR_INTR_TEMPTY : 0;
+s-r[R_SR] |= s-tx_count = s-r[R_TTRIG] ? UART_SR_TTRIG : 0;
+
 s-r[R_CISR] |= s-r[R_SR]  UART_SR_TO_CISR_MASK;
+s-r[R_CISR] |= s-r[R_SR]  UART_SR_TTRIG ? UART_INTR_TTRIG : 0;
 qemu_set_irq(s-irq, !!(s-r[R_IMR]  s-r[R_CISR]));
 }
 
@@ -152,24 +157,6 @@ static void fifo_trigger_update(void *opaque)
 uart_update_status(s);
 }
 
-static void uart_tx_redo(UartState *s)
-{
-uint64_t new_tx_time = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
-
-timer_mod(s-tx_time_handle, new_tx_time + s-char_tx_time);
-
-s-r[R_SR] |= UART_SR_INTR_TEMPTY;
-
-uart_update_status(s);
-}
-
-static void uart_tx_write(void *opaque)
-{
-UartState *s = (UartState *)opaque;
-
-uart_tx_redo(s);
-}
-
 static void uart_rx_reset(UartState *s)
 {
 s-rx_wpos = 0;
@@ -181,6 +168,7 @@ static void uart_rx_reset(UartState *s)
 
 static void uart_tx_reset(UartState *s)
 {
+s-tx_count = 0;
 }
 
 static void uart_send_breaks(UartState *s)
@@ -261,10 +249,6 @@ static void uart_ctrl_update(UartState *s)
 
 s-r[R_CR] = ~(UART_CR_TXRST | UART_CR_RXRST);
 
-if ((s-r[R_CR]  UART_CR_TX_EN)  !(s-r[R_CR]  UART_CR_TX_DIS)) {
-uart_tx_redo(s);
-}
-
 if (s-r[R_CR]  UART_CR_STARTBRK  !(s-r[R_CR]  UART_CR_STOPBRK)) {
 uart_send_breaks(s);
 }
@@ -447,9 +431,6 @@ static int cadence_uart_init(SysBusDevice *dev)
 s-fifo_trigger_handle = timer_new_ns(QEMU_CLOCK_VIRTUAL,
 (QEMUTimerCB *)fifo_trigger_update, s);
 
-s-tx_time_handle = timer_new_ns(QEMU_CLOCK_VIRTUAL,
-(QEMUTimerCB *)uart_tx_write, s);
-
 s-char_tx_time = (get_ticks_per_sec() / 9600) * 10;
 
 s-chr = qemu_char_get_next_serial();
@@ -473,17 +454,18 @@ static int cadence_uart_post_load(void *opaque, int 
version_id)
 
 static const VMStateDescription vmstate_cadence_uart = {
 .name = cadence_uart,
-.version_id = 1,
-.minimum_version_id = 1,
-.minimum_version_id_old = 1,
+.version_id = 2,
+.minimum_version_id = 2,
+.minimum_version_id_old = 2,
 .post_load = cadence_uart_post_load,
 .fields = (VMStateField[]) {
 VMSTATE_UINT32_ARRAY(r, UartState, R_MAX),
 VMSTATE_UINT8_ARRAY(rx_fifo, UartState, RX_FIFO_SIZE),
+VMSTATE_UINT8_ARRAY(tx_fifo, UartState, RX_FIFO_SIZE),
 VMSTATE_UINT32(rx_count, UartState),
+VMSTATE_UINT32(tx_count, UartState),
 VMSTATE_UINT32(rx_wpos, UartState),
 VMSTATE_TIMER(fifo_trigger_handle, UartState),
-VMSTATE_TIMER(tx_time_handle, UartState),
 VMSTATE_END_OF_LIST()
 }
 };
-- 
1.8.5




[Qemu-devel] [PULL 35/52] target-arm: Give the FPSCR rounding modes names

2014-01-06 Thread Peter Maydell
From: Alexander Graf ag...@suse.de

When setting rounding modes we currently just hardcode the numeric values
for rounding modes in a big switch statement.

With AArch64 support coming, we will need to refer to these rounding modes
at different places throughout the code though, so let's better give them
names so we don't get confused by accident.

Signed-off-by: Alexander Graf ag...@suse.de
[WN: Commit message tweak, use names from ARM ARM.]
Signed-off-by: Will Newton will.new...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/cpu.h| 9 +
 target-arm/helper.c | 8 
 2 files changed, 13 insertions(+), 4 deletions(-)

diff --git a/target-arm/cpu.h b/target-arm/cpu.h
index 7084a74..43ca572 100644
--- a/target-arm/cpu.h
+++ b/target-arm/cpu.h
@@ -487,6 +487,15 @@ static inline void vfp_set_fpcr(CPUARMState *env, uint32_t 
val)
 vfp_set_fpscr(env, new_fpscr);
 }
 
+enum arm_fprounding {
+FPROUNDING_TIEEVEN,
+FPROUNDING_POSINF,
+FPROUNDING_NEGINF,
+FPROUNDING_ZERO,
+FPROUNDING_TIEAWAY,
+FPROUNDING_ODD
+};
+
 enum arm_cpu_mode {
   ARM_CPU_MODE_USR = 0x10,
   ARM_CPU_MODE_FIQ = 0x11,
diff --git a/target-arm/helper.c b/target-arm/helper.c
index 74042b8..265675d 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -3815,16 +3815,16 @@ void HELPER(vfp_set_fpscr)(CPUARMState *env, uint32_t 
val)
 if (changed  (3  22)) {
 i = (val  22)  3;
 switch (i) {
-case 0:
+case FPROUNDING_TIEEVEN:
 i = float_round_nearest_even;
 break;
-case 1:
+case FPROUNDING_POSINF:
 i = float_round_up;
 break;
-case 2:
+case FPROUNDING_NEGINF:
 i = float_round_down;
 break;
-case 3:
+case FPROUNDING_ZERO:
 i = float_round_to_zero;
 break;
 }
-- 
1.8.5




[Qemu-devel] [PULL 22/52] linux-user: AArch64: define TARGET_CLONE_BACKWARDS

2014-01-06 Thread Peter Maydell
From: Claudio Fontana claudio.font...@linaro.org

The AArch64 linux-user support was written before but merged after
commit 4ce6243dc621 which cleaned up the handling of the clone()
syscall argument order, so we failed to notice that AArch64 also needs
TARGET_CLONE_BACKWARDS to be defined. Add this define so that clone
and fork syscalls work correctly.

Signed-off-by: Claudio Fontana claudio.font...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 linux-user/aarch64/syscall.h | 1 +
 1 file changed, 1 insertion(+)

diff --git a/linux-user/aarch64/syscall.h b/linux-user/aarch64/syscall.h
index aef419e..18f44a8 100644
--- a/linux-user/aarch64/syscall.h
+++ b/linux-user/aarch64/syscall.h
@@ -7,3 +7,4 @@ struct target_pt_regs {
 
 #define UNAME_MACHINE aarch64
 #define UNAME_MINIMUM_RELEASE 3.8.0
+#define TARGET_CLONE_BACKWARDS
-- 
1.8.5




[Qemu-devel] [PULL 34/52] target-arm: A64: Add support for floating point cond select

2014-01-06 Thread Peter Maydell
From: Claudio Fontana claudio.font...@linaro.org

This adds decoding support for C3.6.24 FP conditional select.

Signed-off-by: Claudio Fontana claudio.font...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 45 -
 1 file changed, 44 insertions(+), 1 deletion(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 44d8a09..c9fbf0f 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -3304,6 +3304,20 @@ static void disas_fp_ccomp(DisasContext *s, uint32_t 
insn)
 }
 }
 
+/* copy src FP register to dst FP register; type specifies single or double */
+static void gen_mov_fp2fp(DisasContext *s, int type, int dst, int src)
+{
+if (type) {
+TCGv_i64 v = read_fp_dreg(s, src);
+write_fp_dreg(s, dst, v);
+tcg_temp_free_i64(v);
+} else {
+TCGv_i32 v = read_fp_sreg(s, src);
+write_fp_sreg(s, dst, v);
+tcg_temp_free_i32(v);
+}
+}
+
 /* C3.6.24 Floating point conditional select
  *   31  30  29 28   24 23  22  21 20  16 15  12 11 10 95 40
  * +---+---+---+---+--+---+--+--+-+--+--+
@@ -3312,7 +3326,36 @@ static void disas_fp_ccomp(DisasContext *s, uint32_t 
insn)
  */
 static void disas_fp_csel(DisasContext *s, uint32_t insn)
 {
-unsupported_encoding(s, insn);
+unsigned int mos, type, rm, cond, rn, rd;
+int label_continue = -1;
+
+mos = extract32(insn, 29, 3);
+type = extract32(insn, 22, 2); /* 0 = single, 1 = double */
+rm = extract32(insn, 16, 5);
+cond = extract32(insn, 12, 4);
+rn = extract32(insn, 5, 5);
+rd = extract32(insn, 0, 5);
+
+if (mos || type  1) {
+unallocated_encoding(s);
+return;
+}
+
+if (cond  0x0e) { /* not always */
+int label_match = gen_new_label();
+label_continue = gen_new_label();
+arm_gen_test_cc(cond, label_match);
+/* nomatch: */
+gen_mov_fp2fp(s, type, rd, rm);
+tcg_gen_br(label_continue);
+gen_set_label(label_match);
+}
+
+gen_mov_fp2fp(s, type, rd, rn);
+
+if (cond  0x0e) { /* continue */
+gen_set_label(label_continue);
+}
 }
 
 /* C3.6.25 Floating point data-processing (1 source)
-- 
1.8.5




[Qemu-devel] [PULL 08/52] target-arm: A64: implement SVC, BRK

2014-01-06 Thread Peter Maydell
From: Alexander Graf ag...@suse.de

Add decoding for the exception generating instructions, and implement
SVC (syscalls) and BRK (software breakpoint).

Signed-off-by: Alexander Graf ag...@suse.de
Signed-off-by: Alex Bennée alex.ben...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 51 --
 1 file changed, 49 insertions(+), 2 deletions(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 3a9ffdf..9ca6460 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -808,10 +808,57 @@ static void disas_system(DisasContext *s, uint32_t insn)
 }
 }
 
-/* Exception generation */
+/* C3.2.3 Exception generation
+ *
+ *  31 24 23 21 20 5 4   2 1  0
+ * +-+-++-++
+ * | 1 1 0 1 0 1 0 0 | opc |  imm16 | op2 | LL |
+ * +---++--+
+ */
 static void disas_exc(DisasContext *s, uint32_t insn)
 {
-unsupported_encoding(s, insn);
+int opc = extract32(insn, 21, 3);
+int op2_ll = extract32(insn, 0, 5);
+
+switch (opc) {
+case 0:
+/* SVC, HVC, SMC; since we don't support the Virtualization
+ * or TrustZone extensions these all UNDEF except SVC.
+ */
+if (op2_ll != 1) {
+unallocated_encoding(s);
+break;
+}
+gen_exception_insn(s, 0, EXCP_SWI);
+break;
+case 1:
+if (op2_ll != 0) {
+unallocated_encoding(s);
+break;
+}
+/* BRK */
+gen_exception_insn(s, 0, EXCP_BKPT);
+break;
+case 2:
+if (op2_ll != 0) {
+unallocated_encoding(s);
+break;
+}
+/* HLT */
+unsupported_encoding(s, insn);
+break;
+case 5:
+if (op2_ll  1 || op2_ll  3) {
+unallocated_encoding(s);
+break;
+}
+/* DCPS1, DCPS2, DCPS3 */
+unsupported_encoding(s, insn);
+break;
+default:
+unallocated_encoding(s);
+break;
+}
 }
 
 /* C3.2.7 Unconditional branch (register)
-- 
1.8.5




[Qemu-devel] [PULL 14/52] target-arm: A64: Implement MRS/MSR/SYS/SYSL

2014-01-06 Thread Peter Maydell
The AArch64 equivalent of the traditional AArch32
cp15 coprocessor registers is the set of instructions
MRS/MSR/SYS/SYSL, which cover between them both true
system registers and the operations with side effects
such as cache maintenance which in AArch32 are mixed
in with other cp15 registers. Implement these instructions
to look in the cpregs hashtable for the register or
operation.

Since we don't yet populate the cpregs hashtable with
any registers with the AA64 bit set, everything will
still UNDEF at this point.

MSR/MRS is the first user of is_jmp = DISAS_UPDATE, so
fix an infelicity in its handling where the main loop
was requiring the caller to do the update of PC rather
than just doing it itself.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 112 +
 1 file changed, 82 insertions(+), 30 deletions(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index e35d2f3..7a9ee82 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -733,28 +733,88 @@ static void handle_msr_i(DisasContext *s, uint32_t insn,
 unsupported_encoding(s, insn);
 }
 
-/* C5.6.204 SYS */
-static void handle_sys(DisasContext *s, uint32_t insn, unsigned int l,
-   unsigned int op1, unsigned int op2,
+/* C5.6.129 MRS - move from system register
+ * C5.6.131 MSR (register) - move to system register
+ * C5.6.204 SYS
+ * C5.6.205 SYSL
+ * These are all essentially the same insn in 'read' and 'write'
+ * versions, with varying op0 fields.
+ */
+static void handle_sys(DisasContext *s, uint32_t insn, bool isread,
+   unsigned int op0, unsigned int op1, unsigned int op2,
unsigned int crn, unsigned int crm, unsigned int rt)
 {
-unsupported_encoding(s, insn);
-}
+const ARMCPRegInfo *ri;
+TCGv_i64 tcg_rt;
 
-/* C5.6.129 MRS - move from system register */
-static void handle_mrs(DisasContext *s, uint32_t insn, unsigned int op0,
-   unsigned int op1, unsigned int op2,
-   unsigned int crn, unsigned int crm, unsigned int rt)
-{
-unsupported_encoding(s, insn);
-}
+ri = get_arm_cp_reginfo(s-cp_regs,
+ENCODE_AA64_CP_REG(CP_REG_ARM64_SYSREG_CP,
+   crn, crm, op0, op1, op2));
 
-/* C5.6.131 MSR (register) - move to system register */
-static void handle_msr(DisasContext *s, uint32_t insn, unsigned int op0,
-   unsigned int op1, unsigned int op2,
-   unsigned int crn, unsigned int crm, unsigned int rt)
-{
-unsupported_encoding(s, insn);
+if (!ri) {
+/* Unknown register */
+unallocated_encoding(s);
+return;
+}
+
+/* Check access permissions */
+if (!cp_access_ok(s-current_pl, ri, isread)) {
+unallocated_encoding(s);
+return;
+}
+
+/* Handle special cases first */
+switch (ri-type  ~(ARM_CP_FLAG_MASK  ~ARM_CP_SPECIAL)) {
+case ARM_CP_NOP:
+return;
+default:
+break;
+}
+
+if (use_icount  (ri-type  ARM_CP_IO)) {
+gen_io_start();
+}
+
+tcg_rt = cpu_reg(s, rt);
+
+if (isread) {
+if (ri-type  ARM_CP_CONST) {
+tcg_gen_movi_i64(tcg_rt, ri-resetvalue);
+} else if (ri-readfn) {
+TCGv_ptr tmpptr;
+gen_a64_set_pc_im(s-pc - 4);
+tmpptr = tcg_const_ptr(ri);
+gen_helper_get_cp_reg64(tcg_rt, cpu_env, tmpptr);
+tcg_temp_free_ptr(tmpptr);
+} else {
+tcg_gen_ld_i64(tcg_rt, cpu_env, ri-fieldoffset);
+}
+} else {
+if (ri-type  ARM_CP_CONST) {
+/* If not forbidden by access permissions, treat as WI */
+return;
+} else if (ri-writefn) {
+TCGv_ptr tmpptr;
+gen_a64_set_pc_im(s-pc - 4);
+tmpptr = tcg_const_ptr(ri);
+gen_helper_set_cp_reg64(cpu_env, tmpptr, tcg_rt);
+tcg_temp_free_ptr(tmpptr);
+} else {
+tcg_gen_st_i64(tcg_rt, cpu_env, ri-fieldoffset);
+}
+}
+
+if (use_icount  (ri-type  ARM_CP_IO)) {
+/* I/O operations must end the TB here (whether read or write) */
+gen_io_end();
+s-is_jmp = DISAS_UPDATE;
+} else if (!isread  !(ri-type  ARM_CP_SUPPRESS_TB_END)) {
+/* We default to ending the TB on a coprocessor register write,
+ * but allow this to be suppressed by the register definition
+ * (usually only necessary to work around guest bugs).
+ */
+s-is_jmp = DISAS_UPDATE;
+}
 }
 
 /* C3.2.4 System
@@ -795,17 +855,7 @@ static void disas_system(DisasContext *s, uint32_t insn)
 }
 return;
 }
-
-if (op0 == 1) {
-/* C5.6.204 SYS */
-handle_sys(s, insn, l, op1, op2, crn, crm, rt);
-} else 

[Qemu-devel] [PULL 25/52] default-configs: Add config for aarch64-linux-user

2014-01-06 Thread Peter Maydell
Add a config for aarch64-linux-user, thereby enabling it as
a valid target.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Signed-off-by: Alexander Graf ag...@suse.de
Reviewed-by: Richard Henderson r...@twiddle.net
---
 default-configs/aarch64-linux-user.mak | 3 +++
 1 file changed, 3 insertions(+)
 create mode 100644 default-configs/aarch64-linux-user.mak

diff --git a/default-configs/aarch64-linux-user.mak 
b/default-configs/aarch64-linux-user.mak
new file mode 100644
index 000..3df7de5
--- /dev/null
+++ b/default-configs/aarch64-linux-user.mak
@@ -0,0 +1,3 @@
+# Default configuration for aarch64-linux-user
+
+CONFIG_GDBSTUB_XML=y
-- 
1.8.5




[Qemu-devel] [PULL 33/52] target-arm: A64: Add support for floating point conditional compare

2014-01-06 Thread Peter Maydell
From: Claudio Fontana claudio.font...@linaro.org

This adds decoding support for C3.6.23 FP Conditional Compare.

Signed-off-by: Claudio Fontana claudio.font...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 35 ++-
 1 file changed, 34 insertions(+), 1 deletion(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index dc9cc14..44d8a09 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -3268,7 +3268,40 @@ static void disas_fp_compare(DisasContext *s, uint32_t 
insn)
  */
 static void disas_fp_ccomp(DisasContext *s, uint32_t insn)
 {
-unsupported_encoding(s, insn);
+unsigned int mos, type, rm, cond, rn, op, nzcv;
+TCGv_i64 tcg_flags;
+int label_continue = -1;
+
+mos = extract32(insn, 29, 3);
+type = extract32(insn, 22, 2); /* 0 = single, 1 = double */
+rm = extract32(insn, 16, 5);
+cond = extract32(insn, 12, 4);
+rn = extract32(insn, 5, 5);
+op = extract32(insn, 4, 1);
+nzcv = extract32(insn, 0, 4);
+
+if (mos || type  1) {
+unallocated_encoding(s);
+return;
+}
+
+if (cond  0x0e) { /* not always */
+int label_match = gen_new_label();
+label_continue = gen_new_label();
+arm_gen_test_cc(cond, label_match);
+/* nomatch: */
+tcg_flags = tcg_const_i64(nzcv  28);
+gen_set_nzcv(tcg_flags);
+tcg_temp_free_i64(tcg_flags);
+tcg_gen_br(label_continue);
+gen_set_label(label_match);
+}
+
+handle_fp_compare(s, type, rn, rm, false, op);
+
+if (cond  0x0e) {
+gen_set_label(label_continue);
+}
 }
 
 /* C3.6.24 Floating point conditional select
-- 
1.8.5




[Qemu-devel] [PULL 03/52] target-arm: A64: add support for ld/st with reg offset

2014-01-06 Thread Peter Maydell
From: Alex Bennée alex.ben...@linaro.org

This adds support for the load/store forms using a register offset.

Signed-off-by: Alex Bennée alex.ben...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 144 -
 1 file changed, 143 insertions(+), 1 deletion(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 0edcee1..67efcf9 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -404,6 +404,54 @@ static void do_fp_ld(DisasContext *s, int destidx, 
TCGv_i64 tcg_addr, int size)
 tcg_temp_free_i64(tmphi);
 }
 
+/*
+ * This utility function is for doing register extension with an
+ * optional shift. You will likely want to pass a temporary for the
+ * destination register. See DecodeRegExtend() in the ARM ARM.
+ */
+static void ext_and_shift_reg(TCGv_i64 tcg_out, TCGv_i64 tcg_in,
+  int option, unsigned int shift)
+{
+int extsize = extract32(option, 0, 2);
+bool is_signed = extract32(option, 2, 1);
+
+if (is_signed) {
+switch (extsize) {
+case 0:
+tcg_gen_ext8s_i64(tcg_out, tcg_in);
+break;
+case 1:
+tcg_gen_ext16s_i64(tcg_out, tcg_in);
+break;
+case 2:
+tcg_gen_ext32s_i64(tcg_out, tcg_in);
+break;
+case 3:
+tcg_gen_mov_i64(tcg_out, tcg_in);
+break;
+}
+} else {
+switch (extsize) {
+case 0:
+tcg_gen_ext8u_i64(tcg_out, tcg_in);
+break;
+case 1:
+tcg_gen_ext16u_i64(tcg_out, tcg_in);
+break;
+case 2:
+tcg_gen_ext32u_i64(tcg_out, tcg_in);
+break;
+case 3:
+tcg_gen_mov_i64(tcg_out, tcg_in);
+break;
+}
+}
+
+if (shift) {
+tcg_gen_shli_i64(tcg_out, tcg_out, shift);
+}
+}
+
 static inline void gen_check_sp_alignment(DisasContext *s)
 {
 /* The AArch64 architecture mandates that (if enabled via PSTATE
@@ -902,6 +950,96 @@ static void disas_ldst_pair(DisasContext *s, uint32_t insn)
 }
 
 /*
+ * C3.3.10 Load/store (register offset)
+ *
+ * 31 30 29   27  26 25 24 23 22 21  20  16 15 13 12 11 10 9  5 4  0
+ * ++---+---+-+-+---+--+-+--+-+++
+ * |size| 1 1 1 | V | 0 0 | opc | 1 |  Rm  | opt | S| 1 0 | Rn | Rt |
+ * ++---+---+-+-+---+--+-+--+-+++
+ *
+ * For non-vector:
+ *   size: 00- byte, 01 - 16 bit, 10 - 32bit, 11 - 64bit
+ *   opc: 00 - store, 01 - loadu, 10 - loads 64, 11 - loads 32
+ * For vector:
+ *   size is opc1:size1:0 so 100 - 128 bit; 110 and 111 unallocated
+ *   opc0: 0 - store, 1 - load
+ * V: 1 - vector/simd
+ * opt: extend encoding (see DecodeRegExtend)
+ * S: if S=1 then scale (essentially index by sizeof(size))
+ * Rt: register to transfer into/out of
+ * Rn: address register or SP for base
+ * Rm: offset register or ZR for offset
+ */
+static void disas_ldst_reg_roffset(DisasContext *s, uint32_t insn)
+{
+int rt = extract32(insn, 0, 5);
+int rn = extract32(insn, 5, 5);
+int shift = extract32(insn, 12, 1);
+int rm = extract32(insn, 16, 5);
+int opc = extract32(insn, 22, 2);
+int opt = extract32(insn, 13, 3);
+int size = extract32(insn, 30, 2);
+bool is_signed = false;
+bool is_store = false;
+bool is_extended = false;
+bool is_vector = extract32(insn, 26, 1);
+
+TCGv_i64 tcg_rm;
+TCGv_i64 tcg_addr;
+
+if (extract32(opt, 1, 1) == 0) {
+unallocated_encoding(s);
+return;
+}
+
+if (is_vector) {
+size |= (opc  2)  1;
+if (size  4) {
+unallocated_encoding(s);
+return;
+}
+is_store = !extract32(opc, 0, 1);
+} else {
+if (size == 3  opc == 2) {
+/* PRFM - prefetch */
+return;
+}
+if (opc == 3  size  1) {
+unallocated_encoding(s);
+return;
+}
+is_store = (opc == 0);
+is_signed = extract32(opc, 1, 1);
+is_extended = (size  3)  extract32(opc, 0, 1);
+}
+
+if (rn == 31) {
+gen_check_sp_alignment(s);
+}
+tcg_addr = read_cpu_reg_sp(s, rn, 1);
+
+tcg_rm = read_cpu_reg(s, rm, 1);
+ext_and_shift_reg(tcg_rm, tcg_rm, opt, shift ? size : 0);
+
+tcg_gen_add_i64(tcg_addr, tcg_addr, tcg_rm);
+
+if (is_vector) {
+if (is_store) {
+do_fp_st(s, rt, tcg_addr, size);
+} else {
+do_fp_ld(s, rt, tcg_addr, size);
+}
+} else {
+TCGv_i64 tcg_rt = cpu_reg(s, rt);
+if (is_store) {
+do_gpr_st(s, tcg_rt, tcg_addr, size);
+} else {
+do_gpr_ld(s, tcg_rt, tcg_addr, size, is_signed, is_extended);
+}
+}
+}
+
+/*
  * C3.3.13 Load/store (unsigned 

[Qemu-devel] [PULL 06/52] target-arm: A64: add support for move wide instructions

2014-01-06 Thread Peter Maydell
From: Alex Bennée alex.ben...@linaro.org

This patch adds emulation for the mov wide instructions
(MOVN, MOVZ, MOVK).

Signed-off-by: Alex Bennée alex.ben...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 51 --
 1 file changed, 49 insertions(+), 2 deletions(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index c0057a2..dbc865a 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -1644,10 +1644,57 @@ static void disas_logic_imm(DisasContext *s, uint32_t 
insn)
 }
 }
 
-/* Move wide (immediate) */
+/*
+ * C3.4.5 Move wide (immediate)
+ *
+ *  31 30 29 28 23 22 21 20 5 40
+ * +--+-+-+-++--+
+ * |sf| opc | 1 0 0 1 0 1 |  hw |  imm16 |  Rd  |
+ * +--+-+-+-++--+
+ *
+ * sf: 0 - 32 bit, 1 - 64 bit
+ * opc: 00 - N, 10 - Z, 11 - K
+ * hw: shift/16 (0,16, and sf only 32, 48)
+ */
 static void disas_movw_imm(DisasContext *s, uint32_t insn)
 {
-unsupported_encoding(s, insn);
+int rd = extract32(insn, 0, 5);
+uint64_t imm = extract32(insn, 5, 16);
+int sf = extract32(insn, 31, 1);
+int opc = extract32(insn, 29, 2);
+int pos = extract32(insn, 21, 2)  4;
+TCGv_i64 tcg_rd = cpu_reg(s, rd);
+TCGv_i64 tcg_imm;
+
+if (!sf  (pos = 32)) {
+unallocated_encoding(s);
+return;
+}
+
+switch (opc) {
+case 0: /* MOVN */
+case 2: /* MOVZ */
+imm = pos;
+if (opc == 0) {
+imm = ~imm;
+}
+if (!sf) {
+imm = 0xu;
+}
+tcg_gen_movi_i64(tcg_rd, imm);
+break;
+case 3: /* MOVK */
+tcg_imm = tcg_const_i64(imm);
+tcg_gen_deposit_i64(tcg_rd, tcg_rd, tcg_imm, pos, 16);
+tcg_temp_free_i64(tcg_imm);
+if (!sf) {
+tcg_gen_ext32u_i64(tcg_rd, tcg_rd);
+}
+break;
+default:
+unallocated_encoding(s);
+break;
+}
 }
 
 /* C3.4.2 Bitfield
-- 
1.8.5




[Qemu-devel] [PULL 20/52] target-arm: Widen exclusive-access support struct fields to 64 bits

2014-01-06 Thread Peter Maydell
In preparation for adding support for A64 load/store exclusive instructions,
widen the fields in the CPU state struct that deal with address and data values
for exclusives from 32 to 64 bits. Although in practice AArch64 and AArch32
exclusive accesses will be generally separate there are some odd theoretical
corner cases (eg you should be able to do the exclusive load in AArch32, take
an exception to AArch64 and successfully do the store exclusive there), and it's
also easier to reason about.

The changes in semantics for the variables are:
 exclusive_addr  - extended to 64 bits; -1ULL for monitor lost,
   otherwise always  2^32 for AArch32
 exclusive_val   - extended to 64 bits. 64 bit exclusives in AArch32 now
   use the high half of exclusive_val instead of a separate exclusive_high
 exclusive_high  - is no longer used in AArch32; extended to 64 bits as
   it will be needed for AArch64's pair-of-64-bit-values exclusives.
 exclusive_test  - extended to 64 bits, as it is an address. Since this is
   a linux-user-only field, in arm-linux-user it will always have the top
   32 bits zero.
 exclusive_info  - stays 32 bits, as it is neither data nor address, but
   simply holds register indexes etc. AArch64 will be able to fit all its
   information into 32 bits as well.

Note that the refactoring of gen_store_exclusive() coincidentally fixes
a minor bug where ldrexd would incorrectly update the first CPU register
even if the load for the second register faulted.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 linux-user/main.c  | 25 +++
 target-arm/cpu.h   |  8 +++
 target-arm/machine.c   | 12 +-
 target-arm/translate.c | 65 ++
 4 files changed, 64 insertions(+), 46 deletions(-)

diff --git a/linux-user/main.c b/linux-user/main.c
index c0df8b5..20f9832 100644
--- a/linux-user/main.c
+++ b/linux-user/main.c
@@ -589,16 +589,21 @@ do_kernel_trap(CPUARMState *env)
 
 static int do_strex(CPUARMState *env)
 {
-uint32_t val;
+uint64_t val;
 int size;
 int rc = 1;
 int segv = 0;
 uint32_t addr;
 start_exclusive();
-addr = env-exclusive_addr;
-if (addr != env-exclusive_test) {
+if (env-exclusive_addr != env-exclusive_test) {
 goto fail;
 }
+/* We know we're always AArch32 so the address is in uint32_t range
+ * unless it was the -1 exclusive-monitor-lost value (which won't
+ * match exclusive_test above).
+ */
+assert(extract64(env-exclusive_addr, 32, 32) == 0);
+addr = env-exclusive_addr;
 size = env-exclusive_info  0xf;
 switch (size) {
 case 0:
@@ -618,19 +623,19 @@ static int do_strex(CPUARMState *env)
 env-cp15.c6_data = addr;
 goto done;
 }
-if (val != env-exclusive_val) {
-goto fail;
-}
 if (size == 3) {
-segv = get_user_u32(val, addr + 4);
+uint32_t valhi;
+segv = get_user_u32(valhi, addr + 4);
 if (segv) {
 env-cp15.c6_data = addr + 4;
 goto done;
 }
-if (val != env-exclusive_high) {
-goto fail;
-}
+val = deposit64(val, 32, 32, valhi);
+}
+if (val != env-exclusive_val) {
+goto fail;
 }
+
 val = env-regs[(env-exclusive_info  8)  0xf];
 switch (size) {
 case 0:
diff --git a/target-arm/cpu.h b/target-arm/cpu.h
index fc36514..7084a74 100644
--- a/target-arm/cpu.h
+++ b/target-arm/cpu.h
@@ -278,11 +278,11 @@ typedef struct CPUARMState {
 float_status fp_status;
 float_status standard_fp_status;
 } vfp;
-uint32_t exclusive_addr;
-uint32_t exclusive_val;
-uint32_t exclusive_high;
+uint64_t exclusive_addr;
+uint64_t exclusive_val;
+uint64_t exclusive_high;
 #if defined(CONFIG_USER_ONLY)
-uint32_t exclusive_test;
+uint64_t exclusive_test;
 uint32_t exclusive_info;
 #endif
 
diff --git a/target-arm/machine.c b/target-arm/machine.c
index 74f010f..8f9e7d4 100644
--- a/target-arm/machine.c
+++ b/target-arm/machine.c
@@ -222,9 +222,9 @@ static int cpu_post_load(void *opaque, int version_id)
 
 const VMStateDescription vmstate_arm_cpu = {
 .name = cpu,
-.version_id = 13,
-.minimum_version_id = 13,
-.minimum_version_id_old = 13,
+.version_id = 14,
+.minimum_version_id = 14,
+.minimum_version_id_old = 14,
 .pre_save = cpu_pre_save,
 .post_load = cpu_post_load,
 .fields = (VMStateField[]) {
@@ -253,9 +253,9 @@ const VMStateDescription vmstate_arm_cpu = {
 VMSTATE_VARRAY_INT32(cpreg_vmstate_values, ARMCPU,
  cpreg_vmstate_array_len,
  0, vmstate_info_uint64, uint64_t),
-VMSTATE_UINT32(env.exclusive_addr, ARMCPU),
-VMSTATE_UINT32(env.exclusive_val, ARMCPU),
-VMSTATE_UINT32(env.exclusive_high, ARMCPU),
+VMSTATE_UINT64(env.exclusive_addr, 

[Qemu-devel] [PULL 27/52] target-arm: A64: Fix vector register access on bigendian hosts

2014-01-06 Thread Peter Maydell
The A64 128 bit vector registers are stored as a pair of
uint64_t values in the register array. This means that if
we're directly loading or storing a value of size less than
64 bits we must adjust the offset appropriately to account
for whether the host is bigendian or not. Provide utility
functions to abstract away the offsetof() calculations for
the FP registers.

For do_fp_st() we can sidestep most of the issues for 64 bit
and smaller reg-to-mem transfers by always doing a 64 bit
load from the register and writing just the piece we need
to memory.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 69 +++---
 1 file changed, 35 insertions(+), 34 deletions(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 326f36d..ba9573a 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -308,6 +308,26 @@ static TCGv_i64 read_cpu_reg_sp(DisasContext *s, int reg, 
int sf)
 return v;
 }
 
+/* Return the offset into CPUARMState of a slice (from
+ * the least significant end) of FP register Qn (ie
+ * Dn, Sn, Hn or Bn).
+ * (Note that this is not the same mapping as for A32; see cpu.h)
+ */
+static inline int fp_reg_offset(int regno, TCGMemOp size)
+{
+int offs = offsetof(CPUARMState, vfp.regs[regno * 2]);
+#ifdef HOST_WORDS_BIGENDIAN
+offs += (8 - (1  size));
+#endif
+return offs;
+}
+
+/* Offset of the high half of the 128 bit vector Qn */
+static inline int fp_reg_hi_offset(int regno)
+{
+return offsetof(CPUARMState, vfp.regs[regno * 2 + 1]);
+}
+
 /* Set ZF and NF based on a 64 bit result. This is alas fiddlier
  * than the 32 bit equivalent.
  */
@@ -538,31 +558,15 @@ static void do_gpr_ld(DisasContext *s, TCGv_i64 dest, 
TCGv_i64 tcg_addr,
 static void do_fp_st(DisasContext *s, int srcidx, TCGv_i64 tcg_addr, int size)
 {
 /* This writes the bottom N bits of a 128 bit wide vector to memory */
-int freg_offs = offsetof(CPUARMState, vfp.regs[srcidx * 2]);
 TCGv_i64 tmp = tcg_temp_new_i64();
-
+tcg_gen_ld_i64(tmp, cpu_env, fp_reg_offset(srcidx, MO_64));
 if (size  4) {
-switch (size) {
-case 0:
-tcg_gen_ld8u_i64(tmp, cpu_env, freg_offs);
-break;
-case 1:
-tcg_gen_ld16u_i64(tmp, cpu_env, freg_offs);
-break;
-case 2:
-tcg_gen_ld32u_i64(tmp, cpu_env, freg_offs);
-break;
-case 3:
-tcg_gen_ld_i64(tmp, cpu_env, freg_offs);
-break;
-}
 tcg_gen_qemu_st_i64(tmp, tcg_addr, get_mem_index(s), MO_TE + size);
 } else {
 TCGv_i64 tcg_hiaddr = tcg_temp_new_i64();
-tcg_gen_ld_i64(tmp, cpu_env, freg_offs);
 tcg_gen_qemu_st_i64(tmp, tcg_addr, get_mem_index(s), MO_TEQ);
 tcg_gen_qemu_st64(tmp, tcg_addr, get_mem_index(s));
-tcg_gen_ld_i64(tmp, cpu_env, freg_offs + sizeof(float64));
+tcg_gen_ld_i64(tmp, cpu_env, fp_reg_hi_offset(srcidx));
 tcg_gen_addi_i64(tcg_hiaddr, tcg_addr, 8);
 tcg_gen_qemu_st_i64(tmp, tcg_hiaddr, get_mem_index(s), MO_TEQ);
 tcg_temp_free_i64(tcg_hiaddr);
@@ -577,7 +581,6 @@ static void do_fp_st(DisasContext *s, int srcidx, TCGv_i64 
tcg_addr, int size)
 static void do_fp_ld(DisasContext *s, int destidx, TCGv_i64 tcg_addr, int size)
 {
 /* This always zero-extends and writes to a full 128 bit wide vector */
-int freg_offs = offsetof(CPUARMState, vfp.regs[destidx * 2]);
 TCGv_i64 tmplo = tcg_temp_new_i64();
 TCGv_i64 tmphi;
 
@@ -596,8 +599,8 @@ static void do_fp_ld(DisasContext *s, int destidx, TCGv_i64 
tcg_addr, int size)
 tcg_temp_free_i64(tcg_hiaddr);
 }
 
-tcg_gen_st_i64(tmplo, cpu_env, freg_offs);
-tcg_gen_st_i64(tmphi, cpu_env, freg_offs + sizeof(float64));
+tcg_gen_st_i64(tmplo, cpu_env, fp_reg_offset(destidx, MO_64));
+tcg_gen_st_i64(tmphi, cpu_env, fp_reg_hi_offset(destidx));
 
 tcg_temp_free_i64(tmplo);
 tcg_temp_free_i64(tmphi);
@@ -3224,7 +3227,6 @@ static void handle_fmov(DisasContext *s, int rd, int rn, 
int type, bool itof)
  */
 
 if (itof) {
-int freg_offs = offsetof(CPUARMState, vfp.regs[rd * 2]);
 TCGv_i64 tcg_rn = cpu_reg(s, rn);
 
 switch (type) {
@@ -3233,9 +3235,9 @@ static void handle_fmov(DisasContext *s, int rd, int rn, 
int type, bool itof)
 /* 32 bit */
 TCGv_i64 tmp = tcg_temp_new_i64();
 tcg_gen_ext32u_i64(tmp, tcg_rn);
-tcg_gen_st_i64(tmp, cpu_env, freg_offs);
+tcg_gen_st_i64(tmp, cpu_env, fp_reg_offset(rd, MO_64));
 tcg_gen_movi_i64(tmp, 0);
-tcg_gen_st_i64(tmp, cpu_env, freg_offs + sizeof(float64));
+tcg_gen_st_i64(tmp, cpu_env, fp_reg_hi_offset(rd));
 tcg_temp_free_i64(tmp);
 break;
 }
@@ -3243,32 +3245,31 @@ static void 

[Qemu-devel] [PULL 32/52] target-arm: A64: Add support for floating point compare

2014-01-06 Thread Peter Maydell
From: Claudio Fontana claudio.font...@linaro.org

Add decoding support for C3.6.22 Floating-point compare.

Signed-off-by: Claudio Fontana claudio.font...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/helper-a64.c| 45 
 target-arm/helper-a64.h|  4 +++
 target-arm/translate-a64.c | 65 +-
 3 files changed, 113 insertions(+), 1 deletion(-)

diff --git a/target-arm/helper-a64.c b/target-arm/helper-a64.c
index d3f7067..4ce0d01 100644
--- a/target-arm/helper-a64.c
+++ b/target-arm/helper-a64.c
@@ -77,3 +77,48 @@ uint64_t HELPER(rbit64)(uint64_t x)
 
 return x;
 }
+
+/* Convert a softfloat float_relation_ (as returned by
+ * the float*_compare functions) to the correct ARM
+ * NZCV flag state.
+ */
+static inline uint32_t float_rel_to_flags(int res)
+{
+uint64_t flags;
+switch (res) {
+case float_relation_equal:
+flags = PSTATE_Z | PSTATE_C;
+break;
+case float_relation_less:
+flags = PSTATE_N;
+break;
+case float_relation_greater:
+flags = PSTATE_C;
+break;
+case float_relation_unordered:
+default:
+flags = PSTATE_C | PSTATE_V;
+break;
+}
+return flags;
+}
+
+uint64_t HELPER(vfp_cmps_a64)(float32 x, float32 y, void *fp_status)
+{
+return float_rel_to_flags(float32_compare_quiet(x, y, fp_status));
+}
+
+uint64_t HELPER(vfp_cmpes_a64)(float32 x, float32 y, void *fp_status)
+{
+return float_rel_to_flags(float32_compare(x, y, fp_status));
+}
+
+uint64_t HELPER(vfp_cmpd_a64)(float64 x, float64 y, void *fp_status)
+{
+return float_rel_to_flags(float64_compare_quiet(x, y, fp_status));
+}
+
+uint64_t HELPER(vfp_cmped_a64)(float64 x, float64 y, void *fp_status)
+{
+return float_rel_to_flags(float64_compare(x, y, fp_status));
+}
diff --git a/target-arm/helper-a64.h b/target-arm/helper-a64.h
index a163a94..bca19f3 100644
--- a/target-arm/helper-a64.h
+++ b/target-arm/helper-a64.h
@@ -22,3 +22,7 @@ DEF_HELPER_FLAGS_1(clz64, TCG_CALL_NO_RWG_SE, i64, i64)
 DEF_HELPER_FLAGS_1(cls64, TCG_CALL_NO_RWG_SE, i64, i64)
 DEF_HELPER_FLAGS_1(cls32, TCG_CALL_NO_RWG_SE, i32, i32)
 DEF_HELPER_FLAGS_1(rbit64, TCG_CALL_NO_RWG_SE, i64, i64)
+DEF_HELPER_3(vfp_cmps_a64, i64, f32, f32, ptr)
+DEF_HELPER_3(vfp_cmpes_a64, i64, f32, f32, ptr)
+DEF_HELPER_3(vfp_cmpd_a64, i64, f64, f64, ptr)
+DEF_HELPER_3(vfp_cmped_a64, i64, f64, f64, ptr)
diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index bb36a66..dc9cc14 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -3186,6 +3186,54 @@ static void disas_data_proc_reg(DisasContext *s, 
uint32_t insn)
 }
 }
 
+static void handle_fp_compare(DisasContext *s, bool is_double,
+  unsigned int rn, unsigned int rm,
+  bool cmp_with_zero, bool signal_all_nans)
+{
+TCGv_i64 tcg_flags = tcg_temp_new_i64();
+TCGv_ptr fpst = get_fpstatus_ptr();
+
+if (is_double) {
+TCGv_i64 tcg_vn, tcg_vm;
+
+tcg_vn = read_fp_dreg(s, rn);
+if (cmp_with_zero) {
+tcg_vm = tcg_const_i64(0);
+} else {
+tcg_vm = read_fp_dreg(s, rm);
+}
+if (signal_all_nans) {
+gen_helper_vfp_cmped_a64(tcg_flags, tcg_vn, tcg_vm, fpst);
+} else {
+gen_helper_vfp_cmpd_a64(tcg_flags, tcg_vn, tcg_vm, fpst);
+}
+tcg_temp_free_i64(tcg_vn);
+tcg_temp_free_i64(tcg_vm);
+} else {
+TCGv_i32 tcg_vn, tcg_vm;
+
+tcg_vn = read_fp_sreg(s, rn);
+if (cmp_with_zero) {
+tcg_vm = tcg_const_i32(0);
+} else {
+tcg_vm = read_fp_sreg(s, rm);
+}
+if (signal_all_nans) {
+gen_helper_vfp_cmpes_a64(tcg_flags, tcg_vn, tcg_vm, fpst);
+} else {
+gen_helper_vfp_cmps_a64(tcg_flags, tcg_vn, tcg_vm, fpst);
+}
+tcg_temp_free_i32(tcg_vn);
+tcg_temp_free_i32(tcg_vm);
+}
+
+tcg_temp_free_ptr(fpst);
+
+gen_set_nzcv(tcg_flags);
+
+tcg_temp_free_i64(tcg_flags);
+}
+
 /* C3.6.22 Floating point compare
  *   31  30  29 28   24 23  22  21 20  16 15 14 13  1095 4 0
  * +---+---+---+---+--+---+--+-+-+--+---+
@@ -3194,7 +3242,22 @@ static void disas_data_proc_reg(DisasContext *s, 
uint32_t insn)
  */
 static void disas_fp_compare(DisasContext *s, uint32_t insn)
 {
-unsupported_encoding(s, insn);
+unsigned int mos, type, rm, op, rn, opc, op2r;
+
+mos = extract32(insn, 29, 3);
+type = extract32(insn, 22, 2); /* 0 = single, 1 = double */
+rm = extract32(insn, 16, 5);
+op = extract32(insn, 14, 2);
+rn = extract32(insn, 5, 5);
+opc = extract32(insn, 3, 2);
+op2r = extract32(insn, 0, 3);
+
+if (mos || op || op2r || type  1) {
+

Re: [Qemu-devel] [PATCH] acpi unit-test: resolved iasl crash

2014-01-06 Thread Michael S. Tsirkin
On Sun, Dec 29, 2013 at 02:32:50PM +0200, Marcel Apfelbaum wrote:
 It seems that iasl has an issue when disassembles
 some ACPI tables using the command line:
 iasl -e DSDT -e SSDT -d HPET
 I opened a bug on iasl project:
 https://github.com/acpica/acpica/issues/20
 
 Modified the iasl command line to iasl -d HPET
 until the problem is solved. The command line
 remained the same for DSDT and SSDT tables.
 
 Reported-by:Michael S. Tsirkin m...@redhat.com

space needed after :

 Signed-off-by: Marcel Apfelbaum marce...@redhat.com
 ---
  tests/acpi-test.c | 16 +---
  1 file changed, 9 insertions(+), 7 deletions(-)
 
 diff --git a/tests/acpi-test.c b/tests/acpi-test.c
 index 2d32b69..26d2e26 100644
 --- a/tests/acpi-test.c
 +++ b/tests/acpi-test.c
 @@ -403,7 +403,7 @@ static void dump_aml_files(test_data *data, bool rebuild)
  }
  }
  
 -static void load_asl(GArray *sdts, AcpiSdtTable *sdt)
 +static void load_asl(GArray *sdts, AcpiSdtTable *sdt, bool referenceDsdt)
  {
  AcpiSdtTable *temp;
  GError *error = NULL;
 @@ -419,9 +419,11 @@ static void load_asl(GArray *sdts, AcpiSdtTable *sdt)
  
  /* build command line */
  g_string_append_printf(command_line,  -p %s , sdt-asl_file);
 -for (i = 0; i  2; ++i) { /* reference DSDT and SSDT */
 -temp = g_array_index(sdts, AcpiSdtTable, i);
 -g_string_append_printf(command_line, -e %s , temp-aml_file);
 +if (referenceDsdt) {
 +for (i = 0; i  2; ++i) { /* reference DSDT and SSDT */
 +temp = g_array_index(sdts, AcpiSdtTable, i);
 +g_string_append_printf(command_line, -e %s , temp-aml_file);
 +}
  }
  g_string_append_printf(command_line, -d %s, sdt-aml_file);
  
 @@ -510,14 +512,14 @@ static void test_acpi_asl(test_data *data)
  dump_aml_files(data, false);
  for (i = 0; i  data-ssdt_tables-len; ++i) {
  GString *asl, *exp_asl;
 -
 +bool referenceDsdt = (i  2); /* only for DSDT and SSDT */


Please don't use camelCase for variables.
Can we check the table signature instead of looking at the index?

  sdt = g_array_index(data-ssdt_tables, AcpiSdtTable, i);
  exp_sdt = g_array_index(exp_data.ssdt_tables, AcpiSdtTable, i);
  
 -load_asl(data-ssdt_tables, sdt);
 +load_asl(data-ssdt_tables, sdt, referenceDsdt);
  asl = normalize_asl(sdt-asl);
  
 -load_asl(exp_data.ssdt_tables, exp_sdt);
 +load_asl(exp_data.ssdt_tables, exp_sdt, referenceDsdt);
  exp_asl = normalize_asl(exp_sdt-asl);
  
  g_assert(!g_strcmp0(asl-str, exp_asl-str));
 -- 
 1.8.3.1



[Qemu-devel] [PULL 19/52] target-arm: aarch64: add support for ld lit

2014-01-06 Thread Peter Maydell
From: Alexander Graf ag...@suse.de

Adds support for Load Register (literal), both normal
and SIMD/FP forms.

Signed-off-by: Alexander Graf ag...@suse.de
Signed-off-by: Alex Bennée alex.ben...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 47 --
 1 file changed, 45 insertions(+), 2 deletions(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 538d69e..6197441 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -1112,10 +1112,53 @@ static void disas_ldst_excl(DisasContext *s, uint32_t 
insn)
 unsupported_encoding(s, insn);
 }
 
-/* Load register (literal) */
+/*
+ * C3.3.5 Load register (literal)
+ *
+ *  31 30 29   27  26 25 24 235 4 0
+ * +-+---+---+-+---+---+
+ * | opc | 0 1 1 | V | 0 0 | imm19 |  Rt   |
+ * +-+---+---+-+---+---+
+ *
+ * V: 1 - vector (simd/fp)
+ * opc (non-vector): 00 - 32 bit, 01 - 64 bit,
+ *   10- 32 bit signed, 11 - prefetch
+ * opc (vector): 00 - 32 bit, 01 - 64 bit, 10 - 128 bit (11 unallocated)
+ */
 static void disas_ld_lit(DisasContext *s, uint32_t insn)
 {
-unsupported_encoding(s, insn);
+int rt = extract32(insn, 0, 5);
+int64_t imm = sextract32(insn, 5, 19)  2;
+bool is_vector = extract32(insn, 26, 1);
+int opc = extract32(insn, 30, 2);
+bool is_signed = false;
+int size = 2;
+TCGv_i64 tcg_rt, tcg_addr;
+
+if (is_vector) {
+if (opc == 3) {
+unallocated_encoding(s);
+return;
+}
+size = 2 + opc;
+} else {
+if (opc == 3) {
+/* PRFM (literal) : prefetch */
+return;
+}
+size = 2 + extract32(opc, 0, 1);
+is_signed = extract32(opc, 1, 1);
+}
+
+tcg_rt = cpu_reg(s, rt);
+
+tcg_addr = tcg_const_i64((s-pc - 4) + imm);
+if (is_vector) {
+do_fp_ld(s, rt, tcg_addr, size);
+} else {
+do_gpr_ld(s, tcg_rt, tcg_addr, size, is_signed, false);
+}
+tcg_temp_free_i64(tcg_addr);
 }
 
 /*
-- 
1.8.5




Re: [Qemu-devel] [PATCH] hw/misc/blob-loader: add a generic blob loader

2014-01-06 Thread Paolo Bonzini
Il 06/01/2014 06:36, Li Guang ha scritto:
 dma_memory_write() work?
 
 what about cpu_physical_memory_write_rom ?

Sorry, I missed that load_image_targphys is already doing the right
thing on reset.

Paolo



Re: [Qemu-devel] [PATCH] hw/misc/blob-loader: add a generic blob loader

2014-01-06 Thread Paolo Bonzini
Il 06/01/2014 08:56, Peter Crosthwaite ha scritto:
  What are the guidelines for when to use one or the other?
 
 -machine firmware= if you want to load a firmware blob in a board
 specific way. This if you want to place a blob in memory at an
 arbitrary location on reset.

-machine firmware= is also a pretty bad design because it's not
extensible and doesn't apply to most boards.  We really should get
per-board -machine options, so that you can have a less generic name
than firmware.

Paolo



Re: [Qemu-devel] [PATCHv2 04/18] qemu-iotests: fix test 013 to work with any protocol

2014-01-06 Thread Peter Lieven

On 06.01.2014 11:09, Fam Zheng wrote:

On 2014年01月06日 14:48, Peter Lieven wrote:

On 06.01.2014 06:31, Fam Zheng wrote:

On 2014年01月06日 01:21, Peter Lieven wrote:

Signed-off-by: Peter Lieven p...@kamp.de
---
  tests/qemu-iotests/013 |9 -
  tests/qemu-iotests/013.out |2 +-
  2 files changed, 5 insertions(+), 6 deletions(-)

diff --git a/tests/qemu-iotests/013 b/tests/qemu-iotests/013
index ea3cab9..0dbc934 100755
--- a/tests/qemu-iotests/013
+++ b/tests/qemu-iotests/013
@@ -41,14 +41,14 @@ trap _cleanup; exit \$status 0 1 2 3 15

  # much of this could be generic for any format supporting compression.
  _supported_fmt qcow qcow2
-_supported_proto file
+_supported_proto generic
  _supported_os Linux

  TEST_OFFSETS=0 4294967296
  TEST_OPS=writev read write readv
  CLUSTER_SIZE=4096



I think dropping these three TEST_IMG overriding change...


-_make_test_img 6G
+TEST_IMG=$TEST_IMG.orig _make_test_img 6G


#1



  echo Testing empty image
  echo
@@ -56,16 +56,15 @@ echo
  for offset in $TEST_OFFSETS; do
  echo At offset $offset:
  for op in $TEST_OPS; do
-io_test $op $offset $CLUSTER_SIZE 8
+TEST_IMG=$TEST_IMG.orig io_test $op $offset $CLUSTER_SIZE 8


#2


  done
-_check_test_img
+TEST_IMG=$TEST_IMG.orig _check_test_img


#3


  done


  echo Compressing image
  echo

-mv $TEST_IMG $TEST_IMG.orig


and changing this to

TEST_IMG=$TEST_IMG.orig _make_test_img 6G

Should work.

Unfortunately it doesn't. All subsequent commands will then work
on $TEST_IMG.orig altough they shouldn't. In case of
013 this is io_test, _check_test_img and the cleanup at the end.



Why? The overriding is temporary and subsequent commands are not affected.

If you put in a singe

TEST_IMG=$TEST_IMG.orig

line, this affects all further commands in the same test script.

If you put the TEST_IMG=$TEST_IMG.orig before a command it affectes only this 
single command.



My proposal above doesn't work, though, because an empty new image doesn't contain the 
right data, what is needed here is copy. So maybe change the mv line to:

$QEMU_IMG convert -f $IMGFMT -O $IMGFMT $TEST_IMG $TEST_IMG.orig

could do the work, but I'm not sure if this fits every case.

This is unnecessary (copy) overhead and in some cases it could falsify the 
test. The convert process
does not guarantee to create identical copies. You could use raw format, but in 
this case the image
can only be a multiple of 512 byte.



There are 3 options:
  - override it in every line that should use an alternate $TEST_IMG
  - save the original $TEST_IMG and restore it.
  - rework all commands to take the file as parameter and not use
a global variable for it.

I choosed the first one because it makes clear which $TEST_IMG is acutally
used. You see from the output and the code that you are dealing with the
file that is later used as $TEST_IMG.orig. If you see $TEST_IMG there you
can't distinguish if its the backing or original file or the actual image.

But I thought that this would be controversal. This is I why I splitted
the patch
into individual ones. So its possible to drop all these patches and
still be able
to proceed with the integration of the NFS protocol driver.


I'll leave maintainers to decide.

That is the best. I from my perspective have checked that the NFS driver is 
working great and provided fixes for a lot
of tests to make the iotests work with NFS and QCOW2/VMDK. Most of the tests 
are there to test the formats actually
and errors are likely to happen with every protocol. I would be totally fine if 
maintainers pick up patches 1,2,3,16,17
and leave the rest as is.

Peter



[Qemu-devel] [PATCH] xenfb: map framebuffer read-only and handle unmap errors

2014-01-06 Thread Stefano Stabellini
The framebuffer is needlessly mapped (PROT_READ | PROT_WRITE), map it
PROT_READ instead.

The framebuffer is unmapped by replacing the framebuffer pages with
anonymous shared memory, calling mmap. Check for return errors and print
a warning.

Signed-off-by: Stefano Stabellini stefano.stabell...@eu.citrix.com
CC: Gerd Hoffmann kra...@redhat.com
CC: Paolo Bonzini pbonz...@redhat.com
CC: Anthony Liguori anth...@codemonkey.ws
CC: phco...@gmail.com

diff --git a/hw/display/xenfb.c b/hw/display/xenfb.c
index f0333a0..cb9d456 100644
--- a/hw/display/xenfb.c
+++ b/hw/display/xenfb.c
@@ -495,7 +495,7 @@ static int xenfb_map_fb(struct XenFB *xenfb)
 munmap(map, n_fbdirs * XC_PAGE_SIZE);
 
 xenfb-pixels = xc_map_foreign_pages(xen_xc, xenfb-c.xendev.dom,
-PROT_READ | PROT_WRITE, fbmfns, 
xenfb-fbpages);
+PROT_READ, fbmfns, xenfb-fbpages);
 if (xenfb-pixels == NULL)
goto out;
 
@@ -903,6 +903,11 @@ static void fb_disconnect(struct XenDevice *xendev)
 fb-pixels = mmap(fb-pixels, fb-fbpages * XC_PAGE_SIZE,
   PROT_READ | PROT_WRITE, MAP_SHARED | MAP_ANON,
   -1, 0);
+if (fb-pixels == MAP_FAILED) {
+xen_be_printf(xendev, 0,
+Couldn't replace the framebuffer with anonymous memory 
errno=%d\n,
+errno);
+}
 common_unbind(fb-c);
 fb-feature_update = 0;
 fb-bug_trigger= 0;



[Qemu-devel] [PULL 12/52] target-arm: Update generic cpreg code for AArch64

2014-01-06 Thread Peter Maydell
Update the generic cpreg support code to also handle AArch64:
AArch64-visible registers coexist in the same hash table with
AArch32-visible ones, with a bit in the hash key distinguishing
them.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
---
 target-arm/cpu.h|  78 ---
 target-arm/helper.c | 105 ++--
 target-arm/kvm-consts.h |  37 +
 3 files changed, 211 insertions(+), 9 deletions(-)

diff --git a/target-arm/cpu.h b/target-arm/cpu.h
index 56ed591..9430464 100644
--- a/target-arm/cpu.h
+++ b/target-arm/cpu.h
@@ -572,18 +572,43 @@ void armv7m_nvic_complete_irq(void *opaque, int irq);
  *or via MRRC/MCRR?)
  * We allow 4 bits for opc1 because MRRC/MCRR have a 4 bit field.
  * (In this case crn and opc2 should be zero.)
+ * For AArch64, there is no 32/64 bit size distinction;
+ * instead all registers have a 2 bit op0, 3 bit op1 and op2,
+ * and 4 bit CRn and CRm. The encoding patterns are chosen
+ * to be easy to convert to and from the KVM encodings, and also
+ * so that the hashtable can contain both AArch32 and AArch64
+ * registers (to allow for interprocessing where we might run
+ * 32 bit code on a 64 bit core).
  */
+/* This bit is private to our hashtable cpreg; in KVM register
+ * IDs the AArch64/32 distinction is the KVM_REG_ARM/ARM64
+ * in the upper bits of the 64 bit ID.
+ */
+#define CP_REG_AA64_SHIFT 28
+#define CP_REG_AA64_MASK (1  CP_REG_AA64_SHIFT)
+
 #define ENCODE_CP_REG(cp, is64, crn, crm, opc1, opc2)   \
 (((cp)  16) | ((is64)  15) | ((crn)  11) |\
  ((crm)  7) | ((opc1)  3) | (opc2))
 
+#define ENCODE_AA64_CP_REG(cp, crn, crm, op0, op1, op2) \
+(CP_REG_AA64_MASK | \
+ ((cp)  CP_REG_ARM_COPROC_SHIFT) |\
+ ((op0)  CP_REG_ARM64_SYSREG_OP0_SHIFT) | \
+ ((op1)  CP_REG_ARM64_SYSREG_OP1_SHIFT) | \
+ ((crn)  CP_REG_ARM64_SYSREG_CRN_SHIFT) | \
+ ((crm)  CP_REG_ARM64_SYSREG_CRM_SHIFT) | \
+ ((op2)  CP_REG_ARM64_SYSREG_OP2_SHIFT))
+
 /* Convert a full 64 bit KVM register ID to the truncated 32 bit
  * version used as a key for the coprocessor register hashtable
  */
 static inline uint32_t kvm_to_cpreg_id(uint64_t kvmid)
 {
 uint32_t cpregid = kvmid;
-if ((kvmid  CP_REG_SIZE_MASK) == CP_REG_SIZE_U64) {
+if ((kvmid  CP_REG_ARCH_MASK) == CP_REG_ARM64) {
+cpregid |= CP_REG_AA64_MASK;
+} else if ((kvmid  CP_REG_SIZE_MASK) == CP_REG_SIZE_U64) {
 cpregid |= (1  15);
 }
 return cpregid;
@@ -594,11 +619,18 @@ static inline uint32_t kvm_to_cpreg_id(uint64_t kvmid)
  */
 static inline uint64_t cpreg_to_kvm_id(uint32_t cpregid)
 {
-uint64_t kvmid = cpregid  ~(1  15);
-if (cpregid  (1  15)) {
-kvmid |= CP_REG_SIZE_U64 | CP_REG_ARM;
+uint64_t kvmid;
+
+if (cpregid  CP_REG_AA64_MASK) {
+kvmid = cpregid  ~CP_REG_AA64_MASK;
+kvmid |= CP_REG_SIZE_U64 | CP_REG_ARM64;
 } else {
-kvmid |= CP_REG_SIZE_U32 | CP_REG_ARM;
+kvmid = cpregid  ~(1  15);
+if (cpregid  (1  15)) {
+kvmid |= CP_REG_SIZE_U64 | CP_REG_ARM;
+} else {
+kvmid |= CP_REG_SIZE_U32 | CP_REG_ARM;
+}
 }
 return kvmid;
 }
@@ -634,6 +666,21 @@ static inline uint64_t cpreg_to_kvm_id(uint32_t cpregid)
 /* Mask of only the flag bits in a type field */
 #define ARM_CP_FLAG_MASK 0x7f
 
+/* Valid values for ARMCPRegInfo state field, indicating which of
+ * the AArch32 and AArch64 execution states this register is visible in.
+ * If the reginfo doesn't explicitly specify then it is AArch32 only.
+ * If the reginfo is declared to be visible in both states then a second
+ * reginfo is synthesised for the AArch32 view of the AArch64 register,
+ * such that the AArch32 view is the lower 32 bits of the AArch64 one.
+ * Note that we rely on the values of these enums as we iterate through
+ * the various states in some places.
+ */
+enum {
+ARM_CP_STATE_AA32 = 0,
+ARM_CP_STATE_AA64 = 1,
+ARM_CP_STATE_BOTH = 2,
+};
+
 /* Return true if cptype is a valid type field. This is used to try to
  * catch errors where the sentinel has been accidentally left off the end
  * of a list of registers.
@@ -655,6 +702,8 @@ static inline bool cptype_valid(int cptype)
  * (ie anything visible in PL2 is visible in S-PL1, some things are only
  * visible in S-PL1) but Secure PL1 is a bit of a mouthful, we bend the
  * terminology a little and call this PL3.
+ * In AArch64 things are somewhat simpler as the PLx bits line up exactly
+ * with the ELx exception levels.
  *
  * If access permissions for a register are more complex than can be
  * described with these bits, then use a laxer set of restrictions, and
@@ -676,6 +725,10 @@ static inline bool cptype_valid(int cptype)
 
 static inline int arm_current_pl(CPUARMState *env)
 {
+

[Qemu-devel] [PULL 21/52] target-arm: A64: support for ld/st/cl exclusive

2014-01-06 Thread Peter Maydell
From: Michael Matz m...@suse.de

This implement exclusive loads/stores for aarch64 along the lines of
arm32 and ppc implementations. The exclusive load remembers the address
and loaded value. The exclusive store throws an an exception which uses
those values to check for equality in a proper exclusive region.

This is not actually the architecture mandated semantics (for either
AArch32 or AArch64) but it is close enough for typical guest code
sequences to work correctly, and saves us from having to monitor all
guest stores. It's fairly easy to come up with test cases where we
don't behave like hardware - we don't for example model cache line
behaviour. However in the common patterns this works, and the existing
32 bit ARM exclusive access implementation has the same limitations.

AArch64 also implements new acquire/release loads/stores (which may be
either exclusive or non-exclusive). These imposes extra ordering
constraints on memory operations (ie they act as if they have an implicit
barrier built into them). As TCG is single-threaded all our barriers
are no-ops, so these just behave like normal loads and stores.

Signed-off-by: Michael Matz m...@suse.de
Signed-off-by: Alex Bennée alex.ben...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 linux-user/main.c  | 127 +++-
 target-arm/translate-a64.c | 156 -
 2 files changed, 277 insertions(+), 6 deletions(-)

diff --git a/linux-user/main.c b/linux-user/main.c
index 20f9832..cabc9e1 100644
--- a/linux-user/main.c
+++ b/linux-user/main.c
@@ -585,8 +585,8 @@ do_kernel_trap(CPUARMState *env)
 
 return 0;
 }
-#endif
 
+/* Store exclusive handling for AArch32 */
 static int do_strex(CPUARMState *env)
 {
 uint64_t val;
@@ -670,7 +670,6 @@ done:
 return segv;
 }
 
-#ifdef TARGET_ABI32
 void cpu_loop(CPUARMState *env)
 {
 CPUState *cs = CPU(arm_env_get_cpu(env));
@@ -885,6 +884,122 @@ void cpu_loop(CPUARMState *env)
 
 #else
 
+/*
+ * Handle AArch64 store-release exclusive
+ *
+ * rs = gets the status result of store exclusive
+ * rt = is the register that is stored
+ * rt2 = is the second register store (in STP)
+ *
+ */
+static int do_strex_a64(CPUARMState *env)
+{
+uint64_t val;
+int size;
+bool is_pair;
+int rc = 1;
+int segv = 0;
+uint64_t addr;
+int rs, rt, rt2;
+
+start_exclusive();
+/* size | is_pair  2 | (rs  4) | (rt  9) | (rt2  14)); */
+size = extract32(env-exclusive_info, 0, 2);
+is_pair = extract32(env-exclusive_info, 2, 1);
+rs = extract32(env-exclusive_info, 4, 5);
+rt = extract32(env-exclusive_info, 9, 5);
+rt2 = extract32(env-exclusive_info, 14, 5);
+
+addr = env-exclusive_addr;
+
+if (addr != env-exclusive_test) {
+goto finish;
+}
+
+switch (size) {
+case 0:
+segv = get_user_u8(val, addr);
+break;
+case 1:
+segv = get_user_u16(val, addr);
+break;
+case 2:
+segv = get_user_u32(val, addr);
+break;
+case 3:
+segv = get_user_u64(val, addr);
+break;
+default:
+abort();
+}
+if (segv) {
+env-cp15.c6_data = addr;
+goto error;
+}
+if (val != env-exclusive_val) {
+goto finish;
+}
+if (is_pair) {
+if (size == 2) {
+segv = get_user_u32(val, addr + 4);
+} else {
+segv = get_user_u64(val, addr + 8);
+}
+if (segv) {
+env-cp15.c6_data = addr + (size == 2 ? 4 : 8);
+goto error;
+}
+if (val != env-exclusive_high) {
+goto finish;
+}
+}
+val = env-xregs[rt];
+switch (size) {
+case 0:
+segv = put_user_u8(val, addr);
+break;
+case 1:
+segv = put_user_u16(val, addr);
+break;
+case 2:
+segv = put_user_u32(val, addr);
+break;
+case 3:
+segv = put_user_u64(val, addr);
+break;
+}
+if (segv) {
+goto error;
+}
+if (is_pair) {
+val = env-xregs[rt2];
+if (size == 2) {
+segv = put_user_u32(val, addr + 4);
+} else {
+segv = put_user_u64(val, addr + 8);
+}
+if (segv) {
+env-cp15.c6_data = addr + (size == 2 ? 4 : 8);
+goto error;
+}
+}
+rc = 0;
+finish:
+env-pc += 4;
+/* rs == 31 encodes a write to the ZR, thus throwing away
+ * the status return. This is rather silly but valid.
+ */
+if (rs  31) {
+env-xregs[rs] = rc;
+}
+error:
+/* instruction faulted, PC does not advance */
+/* either way a strex releases any exclusive lock we have */
+env-exclusive_addr = -1;
+end_exclusive();
+return segv;
+}
+
 /* AArch64 main loop */
 void cpu_loop(CPUARMState *env)
 {
@@ -944,7 +1059,7 @@ void cpu_loop(CPUARMState *env)
   

[Qemu-devel] [PULL 05/52] target-arm: A64: add support for add, addi, sub, subi

2014-01-06 Thread Peter Maydell
From: Alex Bennée alex.ben...@linaro.org

Implement the non-carry forms of addition and subtraction
(immediate, extended register and shifted register).
This includes the code to calculate NZCV if the instruction
calls for setting the flags.

Signed-off-by: Alex Bennée alex.ben...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 292 -
 1 file changed, 286 insertions(+), 6 deletions(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index a2cc9f0..c0057a2 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -297,6 +297,102 @@ static inline void gen_logic_CC(int sf, TCGv_i64 result)
 tcg_gen_movi_i32(cpu_VF, 0);
 }
 
+/* dest = T0 + T1; compute C, N, V and Z flags */
+static void gen_add_CC(int sf, TCGv_i64 dest, TCGv_i64 t0, TCGv_i64 t1)
+{
+if (sf) {
+TCGv_i64 result, flag, tmp;
+result = tcg_temp_new_i64();
+flag = tcg_temp_new_i64();
+tmp = tcg_temp_new_i64();
+
+tcg_gen_movi_i64(tmp, 0);
+tcg_gen_add2_i64(result, flag, t0, tmp, t1, tmp);
+
+tcg_gen_trunc_i64_i32(cpu_CF, flag);
+
+gen_set_NZ64(result);
+
+tcg_gen_xor_i64(flag, result, t0);
+tcg_gen_xor_i64(tmp, t0, t1);
+tcg_gen_andc_i64(flag, flag, tmp);
+tcg_temp_free_i64(tmp);
+tcg_gen_shri_i64(flag, flag, 32);
+tcg_gen_trunc_i64_i32(cpu_VF, flag);
+
+tcg_gen_mov_i64(dest, result);
+tcg_temp_free_i64(result);
+tcg_temp_free_i64(flag);
+} else {
+/* 32 bit arithmetic */
+TCGv_i32 t0_32 = tcg_temp_new_i32();
+TCGv_i32 t1_32 = tcg_temp_new_i32();
+TCGv_i32 tmp = tcg_temp_new_i32();
+
+tcg_gen_movi_i32(tmp, 0);
+tcg_gen_trunc_i64_i32(t0_32, t0);
+tcg_gen_trunc_i64_i32(t1_32, t1);
+tcg_gen_add2_i32(cpu_NF, cpu_CF, t0_32, tmp, t1_32, tmp);
+tcg_gen_mov_i32(cpu_ZF, cpu_NF);
+tcg_gen_xor_i32(cpu_VF, cpu_NF, t0_32);
+tcg_gen_xor_i32(tmp, t0_32, t1_32);
+tcg_gen_andc_i32(cpu_VF, cpu_VF, tmp);
+tcg_gen_extu_i32_i64(dest, cpu_NF);
+
+tcg_temp_free_i32(tmp);
+tcg_temp_free_i32(t0_32);
+tcg_temp_free_i32(t1_32);
+}
+}
+
+/* dest = T0 - T1; compute C, N, V and Z flags */
+static void gen_sub_CC(int sf, TCGv_i64 dest, TCGv_i64 t0, TCGv_i64 t1)
+{
+if (sf) {
+/* 64 bit arithmetic */
+TCGv_i64 result, flag, tmp;
+
+result = tcg_temp_new_i64();
+flag = tcg_temp_new_i64();
+tcg_gen_sub_i64(result, t0, t1);
+
+gen_set_NZ64(result);
+
+tcg_gen_setcond_i64(TCG_COND_GEU, flag, t0, t1);
+tcg_gen_trunc_i64_i32(cpu_CF, flag);
+
+tcg_gen_xor_i64(flag, result, t0);
+tmp = tcg_temp_new_i64();
+tcg_gen_xor_i64(tmp, t0, t1);
+tcg_gen_and_i64(flag, flag, tmp);
+tcg_temp_free_i64(tmp);
+tcg_gen_shri_i64(flag, flag, 32);
+tcg_gen_trunc_i64_i32(cpu_VF, flag);
+tcg_gen_mov_i64(dest, result);
+tcg_temp_free_i64(flag);
+tcg_temp_free_i64(result);
+} else {
+/* 32 bit arithmetic */
+TCGv_i32 t0_32 = tcg_temp_new_i32();
+TCGv_i32 t1_32 = tcg_temp_new_i32();
+TCGv_i32 tmp;
+
+tcg_gen_trunc_i64_i32(t0_32, t0);
+tcg_gen_trunc_i64_i32(t1_32, t1);
+tcg_gen_sub_i32(cpu_NF, t0_32, t1_32);
+tcg_gen_mov_i32(cpu_ZF, cpu_NF);
+tcg_gen_setcond_i32(TCG_COND_GEU, cpu_CF, t0_32, t1_32);
+tcg_gen_xor_i32(cpu_VF, cpu_NF, t0_32);
+tmp = tcg_temp_new_i32();
+tcg_gen_xor_i32(tmp, t0_32, t1_32);
+tcg_temp_free_i32(t0_32);
+tcg_temp_free_i32(t1_32);
+tcg_gen_and_i32(cpu_VF, cpu_VF, tmp);
+tcg_temp_free_i32(tmp);
+tcg_gen_extu_i32_i64(dest, cpu_NF);
+}
+}
+
 /*
  * Load/Store generators
  */
@@ -1328,10 +1424,68 @@ static void disas_pc_rel_adr(DisasContext *s, uint32_t 
insn)
 tcg_gen_movi_i64(cpu_reg(s, rd), base + offset);
 }
 
-/* Add/subtract (immediate) */
+/*
+ * C3.4.1 Add/subtract (immediate)
+ *
+ *  31 30 29 28   24 23 22 21 10 9   5 4   0
+ * +--+--+--+---+-+-+-+-+
+ * |sf|op| S| 1 0 0 0 1 |shift|imm12|  Rn | Rd  |
+ * +--+--+--+---+-+-+-+-+
+ *
+ *sf: 0 - 32bit, 1 - 64bit
+ *op: 0 - add  , 1 - sub
+ * S: 1 - set flags
+ * shift: 00 - LSL imm by 0, 01 - LSL imm by 12
+ */
 static void disas_add_sub_imm(DisasContext *s, uint32_t insn)
 {
-unsupported_encoding(s, insn);
+int rd = extract32(insn, 0, 5);
+int rn = extract32(insn, 5, 5);
+uint64_t imm = extract32(insn, 10, 12);
+int shift = extract32(insn, 22, 2);
+bool setflags = extract32(insn, 29, 1);
+bool sub_op = extract32(insn, 30, 1);
+bool is_64bit = extract32(insn, 31, 1);

Re: [Qemu-devel] [PATCHv2 04/18] qemu-iotests: fix test 013 to work with any protocol

2014-01-06 Thread Fam Zheng

On 2014年01月06日 20:21, Peter Lieven wrote:

On 06.01.2014 11:09, Fam Zheng wrote:

On 2014年01月06日 14:48, Peter Lieven wrote:

On 06.01.2014 06:31, Fam Zheng wrote:

On 2014年01月06日 01:21, Peter Lieven wrote:

Signed-off-by: Peter Lieven p...@kamp.de
---
  tests/qemu-iotests/013 |9 -
  tests/qemu-iotests/013.out |2 +-
  2 files changed, 5 insertions(+), 6 deletions(-)

diff --git a/tests/qemu-iotests/013 b/tests/qemu-iotests/013
index ea3cab9..0dbc934 100755
--- a/tests/qemu-iotests/013
+++ b/tests/qemu-iotests/013
@@ -41,14 +41,14 @@ trap _cleanup; exit \$status 0 1 2 3 15

  # much of this could be generic for any format supporting
compression.
  _supported_fmt qcow qcow2
-_supported_proto file
+_supported_proto generic
  _supported_os Linux

  TEST_OFFSETS=0 4294967296
  TEST_OPS=writev read write readv
  CLUSTER_SIZE=4096



I think dropping these three TEST_IMG overriding change...


-_make_test_img 6G
+TEST_IMG=$TEST_IMG.orig _make_test_img 6G


#1



  echo Testing empty image
  echo
@@ -56,16 +56,15 @@ echo
  for offset in $TEST_OFFSETS; do
  echo At offset $offset:
  for op in $TEST_OPS; do
-io_test $op $offset $CLUSTER_SIZE 8
+TEST_IMG=$TEST_IMG.orig io_test $op $offset $CLUSTER_SIZE 8


#2


  done
-_check_test_img
+TEST_IMG=$TEST_IMG.orig _check_test_img


#3


  done


  echo Compressing image
  echo

-mv $TEST_IMG $TEST_IMG.orig


and changing this to

TEST_IMG=$TEST_IMG.orig _make_test_img 6G

Should work.

Unfortunately it doesn't. All subsequent commands will then work
on $TEST_IMG.orig altough they shouldn't. In case of
013 this is io_test, _check_test_img and the cleanup at the end.



Why? The overriding is temporary and subsequent commands are not
affected.

If you put in a singe

TEST_IMG=$TEST_IMG.orig

line, this affects all further commands in the same test script.

If you put the TEST_IMG=$TEST_IMG.orig before a command it affectes only
this single command.



My proposal above doesn't work, though, because an empty new image
doesn't contain the right data, what is needed here is copy. So maybe
change the mv line to:

$QEMU_IMG convert -f $IMGFMT -O $IMGFMT $TEST_IMG $TEST_IMG.orig

could do the work, but I'm not sure if this fits every case.

This is unnecessary (copy) overhead and in some cases it could falsify
the test. The convert process
does not guarantee to create identical copies. You could use raw format,
but in this case the image
can only be a multiple of 512 byte.


OK, thanks for clarification.

Fam




[Qemu-devel] [PULL 29/52] target-arm: A64: Add Floating-point data-processing (2 source) insns

2014-01-06 Thread Peter Maydell
From: Alexander Graf ag...@suse.de

This patch adds emulation for the Floating-point data-processing (2 source)
group of instructions.

Signed-off-by: Alexander Graf ag...@suse.de
[WN: Commit message tweak, merge single and double precision patches. Rebase
 and update to new infrastructure. Incorporate FMIN/FMAX support patch by
 Michael Matz.]
Signed-off-by: Will Newton will.new...@linaro.org
[PMM:
 * added convenience accessors for FP s and d regs
 * pulled the field decode and opcode validity check up a level]
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 182 -
 1 file changed, 181 insertions(+), 1 deletion(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index ba9573a..c406e2a 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -328,6 +328,60 @@ static inline int fp_reg_hi_offset(int regno)
 return offsetof(CPUARMState, vfp.regs[regno * 2 + 1]);
 }
 
+/* Convenience accessors for reading and writing single and double
+ * FP registers. Writing clears the upper parts of the associated
+ * 128 bit vector register, as required by the architecture.
+ * Note that unlike the GP register accessors, the values returned
+ * by the read functions must be manually freed.
+ */
+static TCGv_i64 read_fp_dreg(DisasContext *s, int reg)
+{
+TCGv_i64 v = tcg_temp_new_i64();
+
+tcg_gen_ld_i64(v, cpu_env, fp_reg_offset(reg, MO_64));
+return v;
+}
+
+static TCGv_i32 read_fp_sreg(DisasContext *s, int reg)
+{
+TCGv_i32 v = tcg_temp_new_i32();
+
+tcg_gen_ld_i32(v, cpu_env, fp_reg_offset(reg, MO_32));
+return v;
+}
+
+static void write_fp_dreg(DisasContext *s, int reg, TCGv_i64 v)
+{
+TCGv_i64 tcg_zero = tcg_const_i64(0);
+
+tcg_gen_st_i64(v, cpu_env, fp_reg_offset(reg, MO_64));
+tcg_gen_st_i64(tcg_zero, cpu_env, fp_reg_hi_offset(reg));
+tcg_temp_free_i64(tcg_zero);
+}
+
+static void write_fp_sreg(DisasContext *s, int reg, TCGv_i32 v)
+{
+TCGv_i64 tmp = tcg_temp_new_i64();
+
+tcg_gen_extu_i32_i64(tmp, v);
+write_fp_dreg(s, reg, tmp);
+tcg_temp_free_i64(tmp);
+}
+
+static TCGv_ptr get_fpstatus_ptr(void)
+{
+TCGv_ptr statusptr = tcg_temp_new_ptr();
+int offset;
+
+/* In A64 all instructions (both FP and Neon) use the FPCR;
+ * there is no equivalent of the A32 Neon standard FPSCR value
+ * and all operations use vfp.fp_status.
+ */
+offset = offsetof(CPUARMState, vfp.fp_status);
+tcg_gen_addi_ptr(statusptr, cpu_env, offset);
+return statusptr;
+}
+
 /* Set ZF and NF based on a 64 bit result. This is alas fiddlier
  * than the 32 bit equivalent.
  */
@@ -3176,6 +3230,112 @@ static void disas_fp_1src(DisasContext *s, uint32_t 
insn)
 unsupported_encoding(s, insn);
 }
 
+/* C3.6.26 Floating-point data-processing (2 source) - single precision */
+static void handle_fp_2src_single(DisasContext *s, int opcode,
+  int rd, int rn, int rm)
+{
+TCGv_i32 tcg_op1;
+TCGv_i32 tcg_op2;
+TCGv_i32 tcg_res;
+TCGv_ptr fpst;
+
+tcg_res = tcg_temp_new_i32();
+fpst = get_fpstatus_ptr();
+tcg_op1 = read_fp_sreg(s, rn);
+tcg_op2 = read_fp_sreg(s, rm);
+
+switch (opcode) {
+case 0x0: /* FMUL */
+gen_helper_vfp_muls(tcg_res, tcg_op1, tcg_op2, fpst);
+break;
+case 0x1: /* FDIV */
+gen_helper_vfp_divs(tcg_res, tcg_op1, tcg_op2, fpst);
+break;
+case 0x2: /* FADD */
+gen_helper_vfp_adds(tcg_res, tcg_op1, tcg_op2, fpst);
+break;
+case 0x3: /* FSUB */
+gen_helper_vfp_subs(tcg_res, tcg_op1, tcg_op2, fpst);
+break;
+case 0x4: /* FMAX */
+gen_helper_vfp_maxs(tcg_res, tcg_op1, tcg_op2, fpst);
+break;
+case 0x5: /* FMIN */
+gen_helper_vfp_mins(tcg_res, tcg_op1, tcg_op2, fpst);
+break;
+case 0x6: /* FMAXNM */
+gen_helper_vfp_maxnums(tcg_res, tcg_op1, tcg_op2, fpst);
+break;
+case 0x7: /* FMINNM */
+gen_helper_vfp_minnums(tcg_res, tcg_op1, tcg_op2, fpst);
+break;
+case 0x8: /* FNMUL */
+gen_helper_vfp_muls(tcg_res, tcg_op1, tcg_op2, fpst);
+gen_helper_vfp_negs(tcg_res, tcg_res);
+break;
+}
+
+write_fp_sreg(s, rd, tcg_res);
+
+tcg_temp_free_ptr(fpst);
+tcg_temp_free_i32(tcg_op1);
+tcg_temp_free_i32(tcg_op2);
+tcg_temp_free_i32(tcg_res);
+}
+
+/* C3.6.26 Floating-point data-processing (2 source) - double precision */
+static void handle_fp_2src_double(DisasContext *s, int opcode,
+  int rd, int rn, int rm)
+{
+TCGv_i64 tcg_op1;
+TCGv_i64 tcg_op2;
+TCGv_i64 tcg_res;
+TCGv_ptr fpst;
+
+tcg_res = tcg_temp_new_i64();
+fpst = get_fpstatus_ptr();
+tcg_op1 = read_fp_dreg(s, rn);
+tcg_op2 = read_fp_dreg(s, rm);
+
+switch (opcode) {
+case 0x0: /* FMUL */
+ 

[Qemu-devel] [PATCH] Makefile: properly install bios-256k.bin

2014-01-06 Thread Peter Lieven
Commit bcf2b7d introduced new 256k seabios files. However,
they were not installed.

Signed-off-by: Peter Lieven p...@kamp.de
---
 Makefile |2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Makefile b/Makefile
index bdff4e4..807054b 100644
--- a/Makefile
+++ b/Makefile
@@ -290,7 +290,7 @@ common  de-ch  es fo  fr-ca  hu ja  mk  nl-be  
pt  sl tr \
 bepocz
 
 ifdef INSTALL_BLOBS
-BLOBS=bios.bin sgabios.bin vgabios.bin vgabios-cirrus.bin \
+BLOBS=bios.bin bios-256k.bin sgabios.bin vgabios.bin vgabios-cirrus.bin \
 vgabios-stdvga.bin vgabios-vmware.bin vgabios-qxl.bin \
 acpi-dsdt.aml q35-acpi-dsdt.aml \
 ppc_rom.bin openbios-sparc32 openbios-sparc64 openbios-ppc QEMU,tcx.bin \
-- 
1.7.9.5




Re: [Qemu-devel] [V5 PATCH 02/22] softfloat: Add float32_to_uint64()

2014-01-06 Thread Peter Maydell
On 2 January 2014 22:21, Tom Musta tommu...@gmail.com wrote:
 This patch adds the float32_to_uint64() routine, which converts a
 32-bit floating point number to an unsigned 64 bit number.

 This contribution can be licensed under either the softfloat-2a or -2b
 license.

 Signed-off-by: Tom Musta tommu...@gmail.com

Reviewed-by: Peter Maydell peter.mayd...@linaro.org

thanks
-- PMM



[Qemu-devel] Project idea: make QEMU more flexible

2014-01-06 Thread Wei Liu
Hi all

This idea is to modify QEMU's Makefiles, plus implementing some stubs to
make it possible to tailor QEMU to a smaller binary.

The current setup for Xen on X86 is to build i386-softmmu, and uses this
single binary for two purposes:
1. serves as device emulator for HVM guest.
2. serves as PV driver backend for PV guest.

Either case CPU emulation is never used because Xen handles that
already. So we are in fact having a load of unused code in QEMU build.

What I have in mind is to build a QEMU binary which:
1. does not include CPU emulation code at all.
2. only includes components that's useful (what's useful is TBD).

And the rationales behind this idea are:

1. Reduce memory footprint. One usecase would be running Xen on embedded
   platform (X86 or ARM). We would expect the system has very limited
   resources. The smaller the binary, the better.

2. It doesn't make sense to have i386 emulation on ARM platform.
   Arguably nobody can prevent user from running i386 emulator on ARM
   platform, but it doesn't make sense in Xen's setup where QEMU is
   only used as PV device backend on ARM.

3. Security concern. It's much easier to audit small code base.

Please note that I'm not proposing to invalidate all the other usecases.
I'm only speaking with my Xen developer's hat on, aiming to make QEMU
more flexible.

Down to implementation level I only need to (hopefully) add a few stubs
and create some new CONFIG_* options and move a few things around. It
might not be as intrusive as one thinks.

In fact I've already hacked a prototype during Christmas. What's I've
done so far:

1. create target-null which only has some stubs to CPU emulation
   framework.

2. add a few lines to configure / Makefiles*, create
   default-configs/null-softmmu

Finally I got a qemu-system-null. And the effect is immediately visible
-- the size of QEMU binary shrinked from 13MB to 7.6MB. I haven't really
looked at what device emulation code can be removed so the size can even
be made smaller.

What do you think about this idea?

Thanks
Wei.



[Qemu-devel] [PULL 43/52] char/cadence_uart: Fix can_receive logic

2014-01-06 Thread Peter Maydell
From: Peter Crosthwaite peter.crosthwa...@xilinx.com

The can_receive logic was only taking into account the RxFIFO
occupancy. RxFIFO population is only used for the echo and normal modes
however. Improve the logic to correctly return the true number of
receivable characters based on the current mode:

Normal mode: RxFIFO vacancy.
Remote loopback: TxFIFO vacancy.
Echo mode: The min of the TxFIFO and RxFIFO vacancies.
Local Loopback: Return non-zero (to implement droppage)

Signed-off-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
Message-id: 
36a58440c9ca5080151e95765c2c81342de8a8df.1388626249.git.peter.crosthwa...@xilinx.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 hw/char/cadence_uart.c | 10 +-
 1 file changed, 9 insertions(+), 1 deletion(-)

diff --git a/hw/char/cadence_uart.c b/hw/char/cadence_uart.c
index 3eeadb1..3bcaf29 100644
--- a/hw/char/cadence_uart.c
+++ b/hw/char/cadence_uart.c
@@ -233,8 +233,16 @@ static void uart_parameters_setup(UartState *s)
 static int uart_can_receive(void *opaque)
 {
 UartState *s = (UartState *)opaque;
+int ret = MAX(RX_FIFO_SIZE, TX_FIFO_SIZE);
+uint32_t ch_mode = s-r[R_MR]  UART_MR_CHMODE;
 
-return RX_FIFO_SIZE - s-rx_count;
+if (ch_mode == NORMAL_MODE || ch_mode == ECHO_MODE) {
+ret = MIN(ret, RX_FIFO_SIZE - s-rx_count);
+}
+if (ch_mode == REMOTE_LOOPBACK || ch_mode == ECHO_MODE) {
+ret = MIN(ret, TX_FIFO_SIZE - s-tx_count);
+}
+return ret;
 }
 
 static void uart_ctrl_update(UartState *s)
-- 
1.8.5




[Qemu-devel] [PULL 37/52] char/cadence_uart: Add missing uart_update_state

2014-01-06 Thread Peter Maydell
From: Peter Crosthwaite peter.crosthwa...@xilinx.com

This should be rechecked on bus write accesses as such accesses may
change the underlying state that generates the interrupt. Particular
relevant for when the guest touches the interrupt status or mask.

Signed-off-by: Peter Crosthwaite peter.crosthwa...@xilinx.com
Message-id: 
1c250cd61b7b8de492fbc8b79b8370958a56d83b.1388626249.git.peter.crosthwa...@xilinx.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 hw/char/cadence_uart.c | 1 +
 1 file changed, 1 insertion(+)

diff --git a/hw/char/cadence_uart.c b/hw/char/cadence_uart.c
index a7b2f21..fb9db89 100644
--- a/hw/char/cadence_uart.c
+++ b/hw/char/cadence_uart.c
@@ -403,6 +403,7 @@ static void uart_write(void *opaque, hwaddr offset,
 uart_parameters_setup(s);
 break;
 }
+uart_update_status(s);
 }
 
 static uint64_t uart_read(void *opaque, hwaddr offset,
-- 
1.8.5




[Qemu-devel] [PULL 24/52] .travis.yml: Add aarch64-* targets

2014-01-06 Thread Peter Maydell
From: Alex Bennée alex.ben...@linaro.org

Now the AArch64 targets are in mainline we can include them in our
Travis test matrix.

Signed-off-by: Alex Bennée alex.ben...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 .travis.yml | 1 +
 1 file changed, 1 insertion(+)

diff --git a/.travis.yml b/.travis.yml
index 90f1676..c7ff4da 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -16,6 +16,7 @@ env:
   matrix:
   - TARGETS=alpha-softmmu,alpha-linux-user
   - TARGETS=arm-softmmu,arm-linux-user
+  - TARGETS=aarch64-softmmu,aarch64-linux-user
   - TARGETS=cris-softmmu
   - TARGETS=i386-softmmu,x86_64-softmmu
   - TARGETS=lm32-softmmu
-- 
1.8.5




[Qemu-devel] [PATCH v2 15/24] softfloat: Refactor code handling various rounding modes

2014-01-06 Thread Peter Maydell
Refactor the code in various functions which calculates rounding
increments given the current rounding mode, so that instead of a
set of nested if statements we have a simple switch statement.
This will give us a clean place to add the case for the new
tiesAway rounding mode.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 fpu/softfloat.c | 405 +---
 1 file changed, 241 insertions(+), 164 deletions(-)

diff --git a/fpu/softfloat.c b/fpu/softfloat.c
index 78f680f..42cb705 100644
--- a/fpu/softfloat.c
+++ b/fpu/softfloat.c
@@ -42,6 +42,9 @@ these four paragraphs for those parts of this code that are 
retained.
 
 #include fpu/softfloat.h
 
+/* We only need stdlib for abort() */
+#include stdlib.h
+
 /*
 | Primitive arithmetic functions, including multi-word arithmetic, and
 | division and square root approximations.  (Can be specialized to target if
@@ -106,20 +109,21 @@ static int32 roundAndPackInt32( flag zSign, uint64_t absZ 
STATUS_PARAM)
 
 roundingMode = STATUS(float_rounding_mode);
 roundNearestEven = ( roundingMode == float_round_nearest_even );
-roundIncrement = 0x40;
-if ( ! roundNearestEven ) {
-if ( roundingMode == float_round_to_zero ) {
-roundIncrement = 0;
-}
-else {
-roundIncrement = 0x7F;
-if ( zSign ) {
-if ( roundingMode == float_round_up ) roundIncrement = 0;
-}
-else {
-if ( roundingMode == float_round_down ) roundIncrement = 0;
-}
-}
+switch (roundingMode) {
+case float_round_nearest_even:
+roundIncrement = 0x40;
+break;
+case float_round_to_zero:
+roundIncrement = 0;
+break;
+case float_round_up:
+roundIncrement = zSign ? 0 : 0x7f;
+break;
+case float_round_down:
+roundIncrement = zSign ? 0x7f : 0;
+break;
+default:
+abort();
 }
 roundBits = absZ  0x7F;
 absZ = ( absZ + roundIncrement )7;
@@ -155,19 +159,21 @@ static int64 roundAndPackInt64( flag zSign, uint64_t 
absZ0, uint64_t absZ1 STATU
 
 roundingMode = STATUS(float_rounding_mode);
 roundNearestEven = ( roundingMode == float_round_nearest_even );
-increment = ( (int64_t) absZ1  0 );
-if ( ! roundNearestEven ) {
-if ( roundingMode == float_round_to_zero ) {
-increment = 0;
-}
-else {
-if ( zSign ) {
-increment = ( roundingMode == float_round_down )  absZ1;
-}
-else {
-increment = ( roundingMode == float_round_up )  absZ1;
-}
-}
+switch (roundingMode) {
+case float_round_nearest_even:
+increment = ((int64_t) absZ1  0);
+break;
+case float_round_to_zero:
+increment = 0;
+break;
+case float_round_up:
+increment = !zSign  absZ1;
+break;
+case float_round_down:
+increment = zSign  absZ1;
+break;
+default:
+abort();
 }
 if ( increment ) {
 ++absZ0;
@@ -206,17 +212,21 @@ static int64 roundAndPackUint64(flag zSign, uint64_t 
absZ0,
 
 roundingMode = STATUS(float_rounding_mode);
 roundNearestEven = (roundingMode == float_round_nearest_even);
-increment = ((int64_t)absZ1  0);
-if (!roundNearestEven) {
-if (roundingMode == float_round_to_zero) {
-increment = 0;
-} else if (absZ1) {
-if (zSign) {
-increment = (roundingMode == float_round_down)  absZ1;
-} else {
-increment = (roundingMode == float_round_up)  absZ1;
-}
-}
+switch (roundingMode) {
+case float_round_nearest_even:
+increment = ((int64_t)absZ1  0);
+break;
+case float_round_to_zero:
+increment = 0;
+break;
+case float_round_up:
+increment = !zSign  absZ1;
+break;
+case float_round_down:
+increment = zSign  absZ1;
+break;
+default:
+abort();
 }
 if (increment) {
 ++absZ0;
@@ -354,20 +364,22 @@ static float32 roundAndPackFloat32(flag zSign, 
int_fast16_t zExp, uint32_t zSig
 
 roundingMode = STATUS(float_rounding_mode);
 roundNearestEven = ( roundingMode == float_round_nearest_even );
-roundIncrement = 0x40;
-if ( ! roundNearestEven ) {
-if ( roundingMode == float_round_to_zero ) {
-roundIncrement = 0;
-}
-else {
-roundIncrement = 0x7F;
-if ( zSign ) {
-if ( roundingMode == float_round_up ) roundIncrement = 0;
-}
-else {
-if ( roundingMode == float_round_down ) roundIncrement = 0;
-}
-}
+switch (roundingMode) {
+case float_round_nearest_even:
+

Re: [Qemu-devel] [PATCH] Makefile: properly install bios-256k.bin

2014-01-06 Thread Peter Maydell
On 6 January 2014 12:54, Peter Lieven p...@kamp.de wrote:
 Commit bcf2b7d introduced new 256k seabios files. However,
 they were not installed.

This is a dup of this patch by Eduardo from last month:
http://patchwork.ozlabs.org/patch/299233/

thanks
-- PMM



Re: [Qemu-devel] [PATCH] Add bios-256k.bin to BLOBS on Makefile

2014-01-06 Thread Peter Maydell
Ping -- who's going to take this patch? Maybe it should
go via -trivial?

thanks
-- PMM

On 9 December 2013 23:33, Eduardo Habkost ehabk...@redhat.com wrote:
 The default machine-type (pc-i440fx-2.0) now requires bios-256k.bin, but
 make install isn't installing it, so qemu-system-x86_64 won't run out
 of the box. Add it to BLOBS so it gets installed.

 Signed-off-by: Eduardo Habkost ehabk...@redhat.com
 ---
  Makefile | 2 +-
  1 file changed, 1 insertion(+), 1 deletion(-)

 diff --git a/Makefile b/Makefile
 index bdff4e4..807054b 100644
 --- a/Makefile
 +++ b/Makefile
 @@ -290,7 +290,7 @@ common  de-ch  es fo  fr-ca  hu ja  mk  nl-be 
  pt  sl tr \
  bepocz

  ifdef INSTALL_BLOBS
 -BLOBS=bios.bin sgabios.bin vgabios.bin vgabios-cirrus.bin \
 +BLOBS=bios.bin bios-256k.bin sgabios.bin vgabios.bin vgabios-cirrus.bin \
  vgabios-stdvga.bin vgabios-vmware.bin vgabios-qxl.bin \
  acpi-dsdt.aml q35-acpi-dsdt.aml \
  ppc_rom.bin openbios-sparc32 openbios-sparc64 openbios-ppc QEMU,tcx.bin \
 --
 1.8.3.1



Re: [Qemu-devel] [PATCH] docs: qcow2 compat=1.1 is now the default

2014-01-06 Thread Eric Blake
On 01/05/2014 09:39 PM, Stefan Hajnoczi wrote:
 Commit 9117b47717ad208b12786ce88eacb013f9b3dd1c (qcow2: Change default
 for new images to compat=1.1) changed the default qcow2 image format
 version but forgot to update qemu-doc.texi and qemu-img.texi.
 
 Signed-off-by: Stefan Hajnoczi stefa...@redhat.com
 ---
  qemu-doc.texi | 8 
  qemu-img.texi | 8 
  2 files changed, 8 insertions(+), 8 deletions(-)

Reviewed-by: Eric Blake ebl...@redhat.com

-- 
Eric Blake   eblake redhat com+1-919-301-3266
Libvirt virtualization library http://libvirt.org



signature.asc
Description: OpenPGP digital signature


Re: [Qemu-devel] [PATCH] Makefile: properly install bios-256k.bin

2014-01-06 Thread Peter Maydell
On 6 January 2014 13:17, Peter Lieven p...@kamp.de wrote:
 On 06.01.2014 14:12, Peter Maydell wrote:

 On 6 January 2014 12:54, Peter Lieven p...@kamp.de wrote:

 Commit bcf2b7d introduced new 256k seabios files. However,
 they were not installed.

 This is a dup of this patch by Eduardo from last month:
 http://patchwork.ozlabs.org/patch/299233/

 Thanks for the pointer. However, this patch is not in master atm.

Yes, that's why I quoted a patchwork URL rather than
a commit hash :-)

In general, the first of several identical patches for a
fix is the one that should be committed, and there's not
much point in sending in duplicates (especially when the
first patch already has review tags.)

thanks
-- PMM



Re: [Qemu-devel] [PATCH] Makefile: properly install bios-256k.bin

2014-01-06 Thread Peter Lieven

On 06.01.2014 14:17, Peter Maydell wrote:

On 6 January 2014 13:17, Peter Lieven p...@kamp.de wrote:

On 06.01.2014 14:12, Peter Maydell wrote:

On 6 January 2014 12:54, Peter Lieven p...@kamp.de wrote:

Commit bcf2b7d introduced new 256k seabios files. However,
they were not installed.

This is a dup of this patch by Eduardo from last month:
http://patchwork.ozlabs.org/patch/299233/

Thanks for the pointer. However, this patch is not in master atm.

Yes, that's why I quoted a patchwork URL rather than
a commit hash :-)

In general, the first of several identical patches for a
fix is the one that should be committed, and there's not
much point in sending in duplicates (especially when the
first patch already has review tags.)

thats clear.
I did not want to have credit for this I have just not realized
that there is already a patch.

Peter




Re: [Qemu-devel] [PATCH] acpi unit-test: resolved iasl crash

2014-01-06 Thread Marcel Apfelbaum
On Mon, 2014-01-06 at 13:43 +0200, Michael S. Tsirkin wrote:
 On Sun, Dec 29, 2013 at 02:32:50PM +0200, Marcel Apfelbaum wrote:
  It seems that iasl has an issue when disassembles
  some ACPI tables using the command line:
  iasl -e DSDT -e SSDT -d HPET
  I opened a bug on iasl project:
  https://github.com/acpica/acpica/issues/20
  
  Modified the iasl command line to iasl -d HPET
  until the problem is solved. The command line
  remained the same for DSDT and SSDT tables.
  
  Reported-by:Michael S. Tsirkin m...@redhat.com
 
 space needed after :
Sure, missed that
 
  Signed-off-by: Marcel Apfelbaum marce...@redhat.com
  ---
   tests/acpi-test.c | 16 +---
   1 file changed, 9 insertions(+), 7 deletions(-)
  
  diff --git a/tests/acpi-test.c b/tests/acpi-test.c
  index 2d32b69..26d2e26 100644
  --- a/tests/acpi-test.c
  +++ b/tests/acpi-test.c
  @@ -403,7 +403,7 @@ static void dump_aml_files(test_data *data, bool 
  rebuild)
   }
   }
   
  -static void load_asl(GArray *sdts, AcpiSdtTable *sdt)
  +static void load_asl(GArray *sdts, AcpiSdtTable *sdt, bool referenceDsdt)
   {
   AcpiSdtTable *temp;
   GError *error = NULL;
  @@ -419,9 +419,11 @@ static void load_asl(GArray *sdts, AcpiSdtTable *sdt)
   
   /* build command line */
   g_string_append_printf(command_line,  -p %s , sdt-asl_file);
  -for (i = 0; i  2; ++i) { /* reference DSDT and SSDT */
  -temp = g_array_index(sdts, AcpiSdtTable, i);
  -g_string_append_printf(command_line, -e %s , temp-aml_file);
  +if (referenceDsdt) {
  +for (i = 0; i  2; ++i) { /* reference DSDT and SSDT */
  +temp = g_array_index(sdts, AcpiSdtTable, i);
  +g_string_append_printf(command_line, -e %s , temp-aml_file);
  +}
   }
   g_string_append_printf(command_line, -d %s, sdt-aml_file);
   
  @@ -510,14 +512,14 @@ static void test_acpi_asl(test_data *data)
   dump_aml_files(data, false);
   for (i = 0; i  data-ssdt_tables-len; ++i) {
   GString *asl, *exp_asl;
  -
  +bool referenceDsdt = (i  2); /* only for DSDT and SSDT */
 
 
 Please don't use camelCase for variables.
Sure, no idea why I did that in the first place...

 Can we check the table signature instead of looking at the index?
It is possible, but not really necessary because:
 1. The array of expected tables it is created as a shadow of the
original tables. (We load the expected tables in the exact order as the 
originals)
 2. The loading is done based on table signatures.
So going over the index in *this* case it means going over the signatures.

Thanks for the review,
Marcel 

 
   sdt = g_array_index(data-ssdt_tables, AcpiSdtTable, i);
   exp_sdt = g_array_index(exp_data.ssdt_tables, AcpiSdtTable, i);
   
  -load_asl(data-ssdt_tables, sdt);
  +load_asl(data-ssdt_tables, sdt, referenceDsdt);
   asl = normalize_asl(sdt-asl);
   
  -load_asl(exp_data.ssdt_tables, exp_sdt);
  +load_asl(exp_data.ssdt_tables, exp_sdt, referenceDsdt);
   exp_asl = normalize_asl(exp_sdt-asl);
   
   g_assert(!g_strcmp0(asl-str, exp_asl-str));
  -- 
  1.8.3.1






Re: [Qemu-devel] Project idea: make QEMU more flexible

2014-01-06 Thread Peter Crosthwaite
On Mon, Jan 6, 2014 at 10:54 PM, Wei Liu wei.l...@citrix.com wrote:
 Hi all

 This idea is to modify QEMU's Makefiles, plus implementing some stubs to
 make it possible to tailor QEMU to a smaller binary.

 The current setup for Xen on X86 is to build i386-softmmu, and uses this
 single binary for two purposes:
 1. serves as device emulator for HVM guest.
 2. serves as PV driver backend for PV guest.

 Either case CPU emulation is never used because Xen handles that
 already. So we are in fact having a load of unused code in QEMU build.

 What I have in mind is to build a QEMU binary which:
 1. does not include CPU emulation code at all.
 2. only includes components that's useful (what's useful is TBD).

 And the rationales behind this idea are:

 1. Reduce memory footprint. One usecase would be running Xen on embedded
platform (X86 or ARM). We would expect the system has very limited
resources. The smaller the binary, the better.

 2. It doesn't make sense to have i386 emulation on ARM platform.
Arguably nobody can prevent user from running i386 emulator on ARM
platform, but it doesn't make sense in Xen's setup where QEMU is
only used as PV device backend on ARM.

 3. Security concern. It's much easier to audit small code base.

 Please note that I'm not proposing to invalidate all the other usecases.
 I'm only speaking with my Xen developer's hat on, aiming to make QEMU
 more flexible.

 Down to implementation level I only need to (hopefully) add a few stubs
 and create some new CONFIG_* options and move a few things around. It
 might not be as intrusive as one thinks.

 In fact I've already hacked a prototype during Christmas. What's I've
 done so far:

 1. create target-null which only has some stubs to CPU emulation
framework.

 2. add a few lines to configure / Makefiles*, create
default-configs/null-softmmu


Your idea of aggressively reducing binary size may not really fit a
defconfig at all. If you are going lean-and-mean based on a specific
use-case I think you need to bring your own config.

 Finally I got a qemu-system-null. And the effect is immediately visible

qemu-system-null has been on my wish-list in the past, although my
reasons were slightly different to yours. Specifically, the goal was
to test CPUs in an RTL simulator interacting with RAM and peripheral
devices hosted in QEMU.

 -- the size of QEMU binary shrinked from 13MB to 7.6MB. I haven't really
 looked at what device emulation code can be removed so the size can even
 be made smaller.


So what exactly is an appropriate device-suite for qemu-system-null is
an open question. I would suggest that the correct default config
for such a QEMU would actually be the full suite of devices, not less
that whats already in i386. Free of CPU/arch restrictions, all devices
are fair game.

Regards,
Peter

 What do you think about this idea?

 Thanks
 Wei.




Re: [Qemu-devel] [Xen-devel] Project idea: make QEMU more flexible

2014-01-06 Thread Frediano Ziglio
On Mon, 2014-01-06 at 12:54 +, Wei Liu wrote:
 Hi all
 
 This idea is to modify QEMU's Makefiles, plus implementing some stubs to
 make it possible to tailor QEMU to a smaller binary.
 
 The current setup for Xen on X86 is to build i386-softmmu, and uses this
 single binary for two purposes:
 1. serves as device emulator for HVM guest.
 2. serves as PV driver backend for PV guest.
 

Perhaps even KVM would benefit too.
Are you sure we don't emulate any instruction for other purposes?

 Either case CPU emulation is never used because Xen handles that
 already. So we are in fact having a load of unused code in QEMU build.
 
 What I have in mind is to build a QEMU binary which:
 1. does not include CPU emulation code at all.
 2. only includes components that's useful (what's useful is TBD).
 
 And the rationales behind this idea are:
 
 1. Reduce memory footprint. One usecase would be running Xen on embedded
platform (X86 or ARM). We would expect the system has very limited
resources. The smaller the binary, the better.
 
 2. It doesn't make sense to have i386 emulation on ARM platform.
Arguably nobody can prevent user from running i386 emulator on ARM
platform, but it doesn't make sense in Xen's setup where QEMU is
only used as PV device backend on ARM.
 
 3. Security concern. It's much easier to audit small code base.
 
 Please note that I'm not proposing to invalidate all the other usecases.
 I'm only speaking with my Xen developer's hat on, aiming to make QEMU
 more flexible.
 
 Down to implementation level I only need to (hopefully) add a few stubs
 and create some new CONFIG_* options and move a few things around. It
 might not be as intrusive as one thinks.
 
 In fact I've already hacked a prototype during Christmas. What's I've
 done so far:
 
 1. create target-null which only has some stubs to CPU emulation
framework.
 
 2. add a few lines to configure / Makefiles*, create
default-configs/null-softmmu
 
 Finally I got a qemu-system-null. And the effect is immediately visible
 -- the size of QEMU binary shrinked from 13MB to 7.6MB. I haven't really
 looked at what device emulation code can be removed so the size can even
 be made smaller.
 

Well, I would prefer something like a i386-nocpu. The system qemu
emulate is still specific to a given architecture. You can't emulate ARM
with the same executable. So we'd add default-configs/arm-nocpu.mak and
default-config/x86_64-nocpu.mak (i386 don't make much sense anymore).

 What do you think about this idea?
 
 Thanks
 Wei.
 

Frediano





[Qemu-devel] [PULL 07/52] target-arm: A64: add support for 3 src data proc insns

2014-01-06 Thread Peter Maydell
From: Alexander Graf ag...@suse.de

This patch adds emulation for the Data-processing (3 source)
family of instructions, namely MADD, MSUB, SMADDL, SMSUBL, SMULH,
UMADDL, UMSUBL, UMULH.

Signed-off-by: Alexander Graf ag...@suse.de
Signed-off-by: Alex Bennée alex.ben...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 97 +-
 1 file changed, 95 insertions(+), 2 deletions(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index dbc865a..3a9ffdf 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -2128,10 +2128,103 @@ static void disas_add_sub_reg(DisasContext *s, 
uint32_t insn)
 tcg_temp_free_i64(tcg_result);
 }
 
-/* Data-processing (3 source) */
+/* C3.5.9 Data-processing (3 source)
+
+   31 30  29 28   24 23 21  20  16  15  14  10 95 40
+  +--+--+---+--+--++--+--+--+
+  |sf| op54 | 1 1 0 1 1 | op31 |  Rm  | o0 |  Ra  |  Rn  |  Rd  |
+  +--+--+---+--+--++--+--+--+
+
+ */
 static void disas_data_proc_3src(DisasContext *s, uint32_t insn)
 {
-unsupported_encoding(s, insn);
+int rd = extract32(insn, 0, 5);
+int rn = extract32(insn, 5, 5);
+int ra = extract32(insn, 10, 5);
+int rm = extract32(insn, 16, 5);
+int op_id = (extract32(insn, 29, 3)  4) |
+(extract32(insn, 21, 3)  1) |
+extract32(insn, 15, 1);
+bool sf = extract32(insn, 31, 1);
+bool is_sub = extract32(op_id, 0, 1);
+bool is_high = extract32(op_id, 2, 1);
+bool is_signed = false;
+TCGv_i64 tcg_op1;
+TCGv_i64 tcg_op2;
+TCGv_i64 tcg_tmp;
+
+/* Note that op_id is sf:op54:op31:o0 so it includes the 32/64 size flag */
+switch (op_id) {
+case 0x42: /* SMADDL */
+case 0x43: /* SMSUBL */
+case 0x44: /* SMULH */
+is_signed = true;
+break;
+case 0x0: /* MADD (32bit) */
+case 0x1: /* MSUB (32bit) */
+case 0x40: /* MADD (64bit) */
+case 0x41: /* MSUB (64bit) */
+case 0x4a: /* UMADDL */
+case 0x4b: /* UMSUBL */
+case 0x4c: /* UMULH */
+break;
+default:
+unallocated_encoding(s);
+return;
+}
+
+if (is_high) {
+TCGv_i64 low_bits = tcg_temp_new_i64(); /* low bits discarded */
+TCGv_i64 tcg_rd = cpu_reg(s, rd);
+TCGv_i64 tcg_rn = cpu_reg(s, rn);
+TCGv_i64 tcg_rm = cpu_reg(s, rm);
+
+if (is_signed) {
+tcg_gen_muls2_i64(low_bits, tcg_rd, tcg_rn, tcg_rm);
+} else {
+tcg_gen_mulu2_i64(low_bits, tcg_rd, tcg_rn, tcg_rm);
+}
+
+tcg_temp_free_i64(low_bits);
+return;
+}
+
+tcg_op1 = tcg_temp_new_i64();
+tcg_op2 = tcg_temp_new_i64();
+tcg_tmp = tcg_temp_new_i64();
+
+if (op_id  0x42) {
+tcg_gen_mov_i64(tcg_op1, cpu_reg(s, rn));
+tcg_gen_mov_i64(tcg_op2, cpu_reg(s, rm));
+} else {
+if (is_signed) {
+tcg_gen_ext32s_i64(tcg_op1, cpu_reg(s, rn));
+tcg_gen_ext32s_i64(tcg_op2, cpu_reg(s, rm));
+} else {
+tcg_gen_ext32u_i64(tcg_op1, cpu_reg(s, rn));
+tcg_gen_ext32u_i64(tcg_op2, cpu_reg(s, rm));
+}
+}
+
+if (ra == 31  !is_sub) {
+/* Special-case MADD with rA == XZR; it is the standard MUL alias */
+tcg_gen_mul_i64(cpu_reg(s, rd), tcg_op1, tcg_op2);
+} else {
+tcg_gen_mul_i64(tcg_tmp, tcg_op1, tcg_op2);
+if (is_sub) {
+tcg_gen_sub_i64(cpu_reg(s, rd), cpu_reg(s, ra), tcg_tmp);
+} else {
+tcg_gen_add_i64(cpu_reg(s, rd), cpu_reg(s, ra), tcg_tmp);
+}
+}
+
+if (!sf) {
+tcg_gen_ext32u_i64(cpu_reg(s, rd), cpu_reg(s, rd));
+}
+
+tcg_temp_free_i64(tcg_op1);
+tcg_temp_free_i64(tcg_op2);
+tcg_temp_free_i64(tcg_tmp);
 }
 
 /* Add/subtract (with carry) */
-- 
1.8.5




[Qemu-devel] [PATCH v2 22/24] target-arm: A64: Add floating-point-integer conversion instructions

2014-01-06 Thread Peter Maydell
From: Will Newton will.new...@linaro.org

Add support for the AArch64 floating-point - integer conversion
instructions to disas_fpintconv. In the process we can rearrange
and simplify the detection of unallocated encodings a little.
We also correct a typo in the instruction encoding diagram for this
instruction group: bit 21 is 1, not 0.

Signed-off-by: Will Newton will.new...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 target-arm/translate-a64.c | 23 ---
 1 file changed, 20 insertions(+), 3 deletions(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index ec8abc7..9b23d37 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -3904,7 +3904,7 @@ static void handle_fmov(DisasContext *s, int rd, int rn, 
int type, bool itof)
 /* C3.6.30 Floating point - integer conversions
  *   31   30  29 28   24 23  22  21 20   19 18 16 15 10 9  5 4  0
  * ++---+---+---+--+---+---+-+-+++
- * | sf | 0 | S | 1 1 1 1 0 | type | 0 | rmode | opc | 0 0 0 0 0 0 | Rn | Rd |
+ * | sf | 0 | S | 1 1 1 1 0 | type | 1 | rmode | opc | 0 0 0 0 0 0 | Rn | Rd |
  * ++---+---+---+--+---+---+-+-+++
  */
 static void disas_fp_int_conv(DisasContext *s, uint32_t insn)
@@ -3917,10 +3917,20 @@ static void disas_fp_int_conv(DisasContext *s, uint32_t 
insn)
 bool sbit = extract32(insn, 29, 1);
 bool sf = extract32(insn, 31, 1);
 
-if (!sbit  (rmode  2)  (opcode  5)) {
+if (sbit) {
+unallocated_encoding(s);
+return;
+}
+
+if (opcode  5) {
 /* FMOV */
 bool itof = opcode  1;
 
+if (rmode = 2) {
+unallocated_encoding(s);
+return;
+}
+
 switch (sf  3 | type  1 | rmode) {
 case 0x0: /* 32 bit */
 case 0xa: /* 64 bit */
@@ -3935,7 +3945,14 @@ static void disas_fp_int_conv(DisasContext *s, uint32_t 
insn)
 handle_fmov(s, rd, rn, type, itof);
 } else {
 /* actual FP conversions */
-unsupported_encoding(s, insn);
+bool itof = extract32(opcode, 1, 1);
+
+if (type  1 || (rmode != 0  opcode  1)) {
+unallocated_encoding(s);
+return;
+}
+
+handle_fpfpcvt(s, rd, rn, opcode, itof, rmode, 64, sf, type);
 }
 }
 
-- 
1.8.5




[Qemu-devel] [PATCH v2 23/24] target-arm: A64: Add 1-source 32-to-32 and 64-to-64 FP instructions

2014-01-06 Thread Peter Maydell
This patch adds support for those instructions in the  Floating-point
data-processing (1 source) group which are simple 32-bit-to-32-bit
or 64-bit-to-64-bit operations (ie everything except FCVT between
single/double/half precision).

We put the new round-to-int helpers in helper.c because they will
also be used by the new ARMv8 A32/T32 rounding instructions.

Signed-off-by: Alexander Graf ag...@suse.de
[WN: Commit message tweak, merged single and double precision patches,
 updated to new infrastructure.]
Signed-off-by: Will Newton will.new...@linaro.org
[PMM: reworked decode, split FCVT out into their own patch]
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 target-arm/helper.c|  45 ++
 target-arm/helper.h|   5 ++
 target-arm/translate-a64.c | 142 -
 3 files changed, 191 insertions(+), 1 deletion(-)

diff --git a/target-arm/helper.c b/target-arm/helper.c
index b832908..a0c1646 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -4353,3 +4353,48 @@ float64 VFP_HELPER(muladd, d)(float64 a, float64 b, 
float64 c, void *fpstp)
 float_status *fpst = fpstp;
 return float64_muladd(a, b, c, 0, fpst);
 }
+
+/* ARMv8 round to integral */
+float32 HELPER(rints_exact)(float32 x, void *fp_status)
+{
+return float32_round_to_int(x, fp_status);
+}
+
+float64 HELPER(rintd_exact)(float64 x, void *fp_status)
+{
+return float64_round_to_int(x, fp_status);
+}
+
+float32 HELPER(rints)(float32 x, void *fp_status)
+{
+int old_flags = get_float_exception_flags(fp_status), new_flags;
+float32 ret;
+
+ret = float32_round_to_int(x, fp_status);
+
+/* Suppress any inexact exceptions the conversion produced */
+if (!(old_flags  float_flag_inexact)) {
+new_flags = get_float_exception_flags(fp_status);
+set_float_exception_flags(new_flags  ~float_flag_inexact, fp_status);
+}
+
+return ret;
+}
+
+float64 HELPER(rintd)(float64 x, void *fp_status)
+{
+int old_flags = get_float_exception_flags(fp_status), new_flags;
+float64 ret;
+
+ret = float64_round_to_int(x, fp_status);
+
+new_flags = get_float_exception_flags(fp_status);
+
+/* Suppress any inexact exceptions the conversion produced */
+if (!(old_flags  float_flag_inexact)) {
+new_flags = get_float_exception_flags(fp_status);
+set_float_exception_flags(new_flags  ~float_flag_inexact, fp_status);
+}
+
+return ret;
+}
diff --git a/target-arm/helper.h b/target-arm/helper.h
index 25b6b4f..832ec12 100644
--- a/target-arm/helper.h
+++ b/target-arm/helper.h
@@ -171,6 +171,11 @@ DEF_HELPER_3(shr_cc, i32, env, i32, i32)
 DEF_HELPER_3(sar_cc, i32, env, i32, i32)
 DEF_HELPER_3(ror_cc, i32, env, i32, i32)
 
+DEF_HELPER_FLAGS_2(rints_exact, TCG_CALL_NO_RWG_SE, f32, f32, ptr)
+DEF_HELPER_FLAGS_2(rintd_exact, TCG_CALL_NO_RWG_SE, f64, f64, ptr)
+DEF_HELPER_FLAGS_2(rints, TCG_CALL_NO_RWG_SE, f32, f32, ptr)
+DEF_HELPER_FLAGS_2(rintd, TCG_CALL_NO_RWG_SE, f64, f64, ptr)
+
 /* neon_helper.c */
 DEF_HELPER_3(neon_qadd_u8, i32, env, i32, i32)
 DEF_HELPER_3(neon_qadd_s8, i32, env, i32, i32)
diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 9b23d37..345a47b 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -3386,6 +3386,118 @@ static void disas_fp_csel(DisasContext *s, uint32_t 
insn)
 }
 }
 
+/* C3.6.25 Floating-point data-processing (1 source) - single precision */
+static void handle_fp_1src_single(DisasContext *s, int opcode, int rd, int rn)
+{
+TCGv_ptr fpst;
+TCGv_i32 tcg_op;
+TCGv_i32 tcg_res;
+
+fpst = get_fpstatus_ptr();
+tcg_op = read_fp_sreg(s, rn);
+tcg_res = tcg_temp_new_i32();
+
+switch (opcode) {
+case 0x0: /* FMOV */
+tcg_gen_mov_i32(tcg_res, tcg_op);
+break;
+case 0x1: /* FABS */
+gen_helper_vfp_abss(tcg_res, tcg_op);
+break;
+case 0x2: /* FNEG */
+gen_helper_vfp_negs(tcg_res, tcg_op);
+break;
+case 0x3: /* FSQRT */
+gen_helper_vfp_sqrts(tcg_res, tcg_op, cpu_env);
+break;
+case 0x8: /* FRINTN */
+case 0x9: /* FRINTP */
+case 0xa: /* FRINTM */
+case 0xb: /* FRINTZ */
+case 0xc: /* FRINTA */
+{
+TCGv_i32 tcg_rmode = tcg_const_i32(arm_rmode_to_sf(opcode  7));
+
+gen_helper_set_rmode(tcg_rmode, tcg_rmode, cpu_env);
+gen_helper_rints(tcg_res, tcg_op, fpst);
+
+gen_helper_set_rmode(tcg_rmode, tcg_rmode, cpu_env);
+tcg_temp_free_i32(tcg_rmode);
+break;
+}
+case 0xe: /* FRINTX */
+gen_helper_rints_exact(tcg_res, tcg_op, fpst);
+break;
+case 0xf: /* FRINTI */
+gen_helper_rints(tcg_res, tcg_op, fpst);
+break;
+default:
+abort();
+}
+
+write_fp_sreg(s, rd, tcg_res);
+
+tcg_temp_free_ptr(fpst);
+tcg_temp_free_i32(tcg_op);
+tcg_temp_free_i32(tcg_res);
+}
+
+/* C3.6.25 Floating-point data-processing (1 

[Qemu-devel] [PULL 23/52] linux-user: AArch64: Use correct values for FPSR/FPCR in sigcontext

2014-01-06 Thread Peter Maydell
From: Will Newton will.new...@linaro.org

Use the helpers provided for getting the correct FPSR and FPCR
values for the signal context.

Signed-off-by: Will Newton will.new...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 linux-user/signal.c | 10 +++---
 1 file changed, 7 insertions(+), 3 deletions(-)

diff --git a/linux-user/signal.c b/linux-user/signal.c
index 4e7148a..6c74b18 100644
--- a/linux-user/signal.c
+++ b/linux-user/signal.c
@@ -1189,8 +1189,8 @@ static int target_setup_sigframe(struct 
target_rt_sigframe *sf,
 __put_user(env-vfp.regs[i * 2 + 1], aux-fpsimd.vregs[i * 2 + 1]);
 #endif
 }
-__put_user(/*env-fpsr*/0, aux-fpsimd.fpsr);
-__put_user(/*env-fpcr*/0, aux-fpsimd.fpcr);
+__put_user(vfp_get_fpsr(env), aux-fpsimd.fpsr);
+__put_user(vfp_get_fpcr(env), aux-fpsimd.fpcr);
 __put_user(TARGET_FPSIMD_MAGIC, aux-fpsimd.head.magic);
 __put_user(sizeof(struct target_fpsimd_context),
 aux-fpsimd.head.size);
@@ -1209,7 +1209,7 @@ static int target_restore_sigframe(CPUARMState *env,
 int i;
 struct target_aux_context *aux =
 (struct target_aux_context *)sf-uc.tuc_mcontext.__reserved;
-uint32_t magic, size;
+uint32_t magic, size, fpsr, fpcr;
 uint64_t pstate;
 
 target_to_host_sigset(set, sf-uc.tuc_sigmask);
@@ -1235,6 +1235,10 @@ static int target_restore_sigframe(CPUARMState *env,
 for (i = 0; i  32 * 2; i++) {
 __get_user(env-vfp.regs[i], aux-fpsimd.vregs[i]);
 }
+__get_user(fpsr, aux-fpsimd.fpsr);
+vfp_set_fpsr(env, fpsr);
+__get_user(fpcr, aux-fpsimd.fpcr);
+vfp_set_fpcr(env, fpcr);
 
 return 0;
 }
-- 
1.8.5




[Qemu-devel] [PATCH v2 21/24] target-arm: A64: Add Floating-point-fixed-point instructions

2014-01-06 Thread Peter Maydell
From: Alexander Graf ag...@suse.de

This patch adds emulation for the instruction group labeled
Floating-point - fixed-point conversions in the ARM ARM.

Namely this includes the instructions SCVTF, UCVTF, FCVTZS, FCVTZU
(scalar, fixed-point).

Signed-off-by: Alexander Graf ag...@suse.de
[WN: Commit message tweak, rebased, updated to new infrastructure.
 Applied bug fixes from Michael Matz and Janne Grunau.]
Signed-off-by: Will Newton will.new...@linaro.org
[PMM: significant cleanup]
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 target-arm/helper.c|  13 
 target-arm/helper.h|   2 +
 target-arm/translate-a64.c | 186 -
 3 files changed, 200 insertions(+), 1 deletion(-)

diff --git a/target-arm/helper.c b/target-arm/helper.c
index 677db3f..b832908 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -4035,6 +4035,19 @@ VFP_CONV_FIX_A64(uq, s, 32, 64, uint64)
 #undef VFP_CONV_FIX_FLOAT
 #undef VFP_CONV_FLOAT_FIX_ROUND
 
+/* Set the current fp rounding mode and return the old one.
+ * The argument is a softfloat float_round_ value.
+ */
+uint32_t HELPER(set_rmode)(uint32_t rmode, CPUARMState *env)
+{
+float_status *fp_status = env-vfp.fp_status;
+
+uint32_t prev_rmode = get_float_rounding_mode(fp_status);
+set_float_rounding_mode(rmode, fp_status);
+
+return prev_rmode;
+}
+
 /* Half precision conversions.  */
 static float32 do_fcvt_f16_to_f32(uint32_t a, CPUARMState *env, float_status 
*s)
 {
diff --git a/target-arm/helper.h b/target-arm/helper.h
index 2e1af46..25b6b4f 100644
--- a/target-arm/helper.h
+++ b/target-arm/helper.h
@@ -148,6 +148,8 @@ DEF_HELPER_3(vfp_uhtod, f64, i64, i32, ptr)
 DEF_HELPER_3(vfp_ultod, f64, i64, i32, ptr)
 DEF_HELPER_3(vfp_uqtod, f64, i64, i32, ptr)
 
+DEF_HELPER_FLAGS_2(set_rmode, TCG_CALL_NO_RWG, i32, i32, env)
+
 DEF_HELPER_2(vfp_fcvt_f16_to_f32, f32, i32, env)
 DEF_HELPER_2(vfp_fcvt_f32_to_f16, i32, f32, env)
 DEF_HELPER_2(neon_fcvt_f16_to_f32, f32, i32, env)
diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index c9fbf0f..ec8abc7 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -3186,6 +3186,34 @@ static void disas_data_proc_reg(DisasContext *s, 
uint32_t insn)
 }
 }
 
+/* Convert ARM rounding mode to softfloat */
+static inline int arm_rmode_to_sf(int rmode)
+{
+switch (rmode) {
+case FPROUNDING_TIEAWAY:
+rmode = float_round_ties_away;
+break;
+case FPROUNDING_ODD:
+/* FIXME: add support for TIEAWAY and ODD */
+qemu_log_mask(LOG_UNIMP, arm: unimplemented rounding mode: %d\n,
+  rmode);
+case FPROUNDING_TIEEVEN:
+default:
+rmode = float_round_nearest_even;
+break;
+case FPROUNDING_POSINF:
+rmode = float_round_up;
+break;
+case FPROUNDING_NEGINF:
+rmode = float_round_down;
+break;
+case FPROUNDING_ZERO:
+rmode = float_round_to_zero;
+break;
+}
+return rmode;
+}
+
 static void handle_fp_compare(DisasContext *s, bool is_double,
   unsigned int rn, unsigned int rm,
   bool cmp_with_zero, bool signal_all_nans)
@@ -3651,6 +3679,132 @@ static void disas_fp_imm(DisasContext *s, uint32_t insn)
 tcg_temp_free_i64(tcg_res);
 }
 
+/* Handle floating point = fixed point conversions. Note that we can
+ * also deal with fp = integer conversions as a special case (scale == 64)
+ * OPTME: consider handling that special case specially or at least skipping
+ * the call to scalbn in the helpers for zero shifts.
+ */
+static void handle_fpfpcvt(DisasContext *s, int rd, int rn, int opcode,
+   bool itof, int rmode, int scale, int sf, int type)
+{
+bool is_signed = !(opcode  1);
+bool is_double = type;
+TCGv_ptr tcg_fpstatus;
+TCGv_i32 tcg_shift;
+
+tcg_fpstatus = get_fpstatus_ptr();
+
+tcg_shift = tcg_const_i32(64 - scale);
+
+if (itof) {
+TCGv_i64 tcg_int = cpu_reg(s, rn);
+if (!sf) {
+TCGv_i64 tcg_extend = new_tmp_a64(s);
+
+if (is_signed) {
+tcg_gen_ext32s_i64(tcg_extend, tcg_int);
+} else {
+tcg_gen_ext32u_i64(tcg_extend, tcg_int);
+}
+
+tcg_int = tcg_extend;
+}
+
+if (is_double) {
+TCGv_i64 tcg_double = tcg_temp_new_i64();
+if (is_signed) {
+gen_helper_vfp_sqtod(tcg_double, tcg_int,
+ tcg_shift, tcg_fpstatus);
+} else {
+gen_helper_vfp_uqtod(tcg_double, tcg_int,
+ tcg_shift, tcg_fpstatus);
+}
+write_fp_dreg(s, rd, tcg_double);
+tcg_temp_free_i64(tcg_double);
+} else {
+TCGv_i32 tcg_single = tcg_temp_new_i32();
+if (is_signed) {
+

[Qemu-devel] [PATCH v2 03/24] softfloat: Add 16 bit integer to float conversions

2014-01-06 Thread Peter Maydell
Add the float to 16 bit integer conversion routines. These can be
trivially implemented in terms of the int32_to_float* routines, but
providing them makes our API more symmetrical and can simplify callers.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 include/fpu/softfloat.h | 21 +
 1 file changed, 21 insertions(+)

diff --git a/include/fpu/softfloat.h b/include/fpu/softfloat.h
index a9b8cd9..926d849 100644
--- a/include/fpu/softfloat.h
+++ b/include/fpu/softfloat.h
@@ -239,6 +239,27 @@ floatx80 int64_to_floatx80( int64 STATUS_PARAM );
 float128 int64_to_float128( int64 STATUS_PARAM );
 float128 uint64_to_float128( uint64 STATUS_PARAM );
 
+/* We provide the int16 versions for symmetry of API with float-to-int */
+INLINE float32 int16_to_float32(int16_t v STATUS_PARAM)
+{
+return int32_to_float32(v STATUS_VAR);
+}
+
+INLINE float32 uint16_to_float32(uint16_t v STATUS_PARAM)
+{
+return uint32_to_float32(v STATUS_VAR);
+}
+
+INLINE float64 int16_to_float64(int16_t v STATUS_PARAM)
+{
+return int32_to_float64(v STATUS_VAR);
+}
+
+INLINE float64 uint16_to_float64(uint16_t v STATUS_PARAM)
+{
+return uint32_to_float64(v STATUS_VAR);
+}
+
 /*
 | Software half-precision conversion routines.
 **/
-- 
1.8.5




[Qemu-devel] [PULL 02/52] target-arm: A64: add support for ld/st unsigned imm

2014-01-06 Thread Peter Maydell
From: Alex Bennée alex.ben...@linaro.org

This adds support for the forms of ld/st with a 12 bit
unsigned immediate offset.

Signed-off-by: Alex Bennée alex.ben...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/translate-a64.c | 89 +-
 1 file changed, 88 insertions(+), 1 deletion(-)

diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 0c3b994..0edcee1 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -901,10 +901,97 @@ static void disas_ldst_pair(DisasContext *s, uint32_t 
insn)
 }
 }
 
+/*
+ * C3.3.13 Load/store (unsigned immediate)
+ *
+ * 31 30 29   27  26 25 24 23 22 2110 9 5
+ * ++---+---+-+-++---+--+
+ * |size| 1 1 1 | V | 0 1 | opc |   imm12|  Rn   |  Rt  |
+ * ++---+---+-+-++---+--+
+ *
+ * For non-vector:
+ *   size: 00- byte, 01 - 16 bit, 10 - 32bit, 11 - 64bit
+ *   opc: 00 - store, 01 - loadu, 10 - loads 64, 11 - loads 32
+ * For vector:
+ *   size is opc1:size1:0 so 100 - 128 bit; 110 and 111 unallocated
+ *   opc0: 0 - store, 1 - load
+ * Rn: base address register (inc SP)
+ * Rt: target register
+ */
+static void disas_ldst_reg_unsigned_imm(DisasContext *s, uint32_t insn)
+{
+int rt = extract32(insn, 0, 5);
+int rn = extract32(insn, 5, 5);
+unsigned int imm12 = extract32(insn, 10, 12);
+bool is_vector = extract32(insn, 26, 1);
+int size = extract32(insn, 30, 2);
+int opc = extract32(insn, 22, 2);
+unsigned int offset;
+
+TCGv_i64 tcg_addr;
+
+bool is_store;
+bool is_signed = false;
+bool is_extended = false;
+
+if (is_vector) {
+size |= (opc  2)  1;
+if (size  4) {
+unallocated_encoding(s);
+return;
+}
+is_store = !extract32(opc, 0, 1);
+} else {
+if (size == 3  opc == 2) {
+/* PRFM - prefetch */
+return;
+}
+if (opc == 3  size  1) {
+unallocated_encoding(s);
+return;
+}
+is_store = (opc == 0);
+is_signed = extract32(opc, 1, 1);
+is_extended = (size  3)  extract32(opc, 0, 1);
+}
+
+if (rn == 31) {
+gen_check_sp_alignment(s);
+}
+tcg_addr = read_cpu_reg_sp(s, rn, 1);
+offset = imm12  size;
+tcg_gen_addi_i64(tcg_addr, tcg_addr, offset);
+
+if (is_vector) {
+if (is_store) {
+do_fp_st(s, rt, tcg_addr, size);
+} else {
+do_fp_ld(s, rt, tcg_addr, size);
+}
+} else {
+TCGv_i64 tcg_rt = cpu_reg(s, rt);
+if (is_store) {
+do_gpr_st(s, tcg_rt, tcg_addr, size);
+} else {
+do_gpr_ld(s, tcg_rt, tcg_addr, size, is_signed, is_extended);
+}
+}
+}
+
 /* Load/store register (all forms) */
 static void disas_ldst_reg(DisasContext *s, uint32_t insn)
 {
-unsupported_encoding(s, insn);
+switch (extract32(insn, 24, 2)) {
+case 0:
+unsupported_encoding(s, insn);
+break;
+case 1:
+disas_ldst_reg_unsigned_imm(s, insn);
+break;
+default:
+unallocated_encoding(s);
+break;
+}
 }
 
 /* AdvSIMD load/store multiple structures */
-- 
1.8.5




[Qemu-devel] [PATCH v2 20/24] target-arm: A64: Add extra VFP fixed point conversion helpers

2014-01-06 Thread Peter Maydell
From: Will Newton will.new...@linaro.org

Define the full set of floating point to fixed point conversion
helpers required to support AArch64.

Signed-off-by: Will Newton will.new...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/helper.c | 11 ++-
 target-arm/helper.h | 16 
 2 files changed, 26 insertions(+), 1 deletion(-)

diff --git a/target-arm/helper.c b/target-arm/helper.c
index 00476a8..677db3f 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -4012,16 +4012,25 @@ uint##isz##_t HELPER(vfp_to##name##p##round)(float##fsz 
x, \
 
 #define VFP_CONV_FIX(name, p, fsz, isz, itype)   \
 VFP_CONV_FIX_FLOAT(name, p, fsz, isz, itype) \
-VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype, _round_to_zero)
+VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype, _round_to_zero) \
+VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype, )
+
+#define VFP_CONV_FIX_A64(name, p, fsz, isz, itype)   \
+VFP_CONV_FIX_FLOAT(name, p, fsz, isz, itype) \
+VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype, )
 
 VFP_CONV_FIX(sh, d, 64, 64, int16)
 VFP_CONV_FIX(sl, d, 64, 64, int32)
+VFP_CONV_FIX_A64(sq, d, 64, 64, int64)
 VFP_CONV_FIX(uh, d, 64, 64, uint16)
 VFP_CONV_FIX(ul, d, 64, 64, uint32)
+VFP_CONV_FIX_A64(uq, d, 64, 64, uint64)
 VFP_CONV_FIX(sh, s, 32, 32, int16)
 VFP_CONV_FIX(sl, s, 32, 32, int32)
+VFP_CONV_FIX_A64(sq, s, 32, 64, int64)
 VFP_CONV_FIX(uh, s, 32, 32, uint16)
 VFP_CONV_FIX(ul, s, 32, 32, uint32)
+VFP_CONV_FIX_A64(uq, s, 32, 64, uint64)
 #undef VFP_CONV_FIX
 #undef VFP_CONV_FIX_FLOAT
 #undef VFP_CONV_FLOAT_FIX_ROUND
diff --git a/target-arm/helper.h b/target-arm/helper.h
index b785623..2e1af46 100644
--- a/target-arm/helper.h
+++ b/target-arm/helper.h
@@ -123,14 +123,30 @@ DEF_HELPER_3(vfp_toshd_round_to_zero, i64, f64, i32, ptr)
 DEF_HELPER_3(vfp_tosld_round_to_zero, i64, f64, i32, ptr)
 DEF_HELPER_3(vfp_touhd_round_to_zero, i64, f64, i32, ptr)
 DEF_HELPER_3(vfp_tould_round_to_zero, i64, f64, i32, ptr)
+DEF_HELPER_3(vfp_toshs, i32, f32, i32, ptr)
+DEF_HELPER_3(vfp_tosls, i32, f32, i32, ptr)
+DEF_HELPER_3(vfp_tosqs, i64, f32, i32, ptr)
+DEF_HELPER_3(vfp_touhs, i32, f32, i32, ptr)
+DEF_HELPER_3(vfp_touls, i32, f32, i32, ptr)
+DEF_HELPER_3(vfp_touqs, i64, f32, i32, ptr)
+DEF_HELPER_3(vfp_toshd, i64, f64, i32, ptr)
+DEF_HELPER_3(vfp_tosld, i64, f64, i32, ptr)
+DEF_HELPER_3(vfp_tosqd, i64, f64, i32, ptr)
+DEF_HELPER_3(vfp_touhd, i64, f64, i32, ptr)
+DEF_HELPER_3(vfp_tould, i64, f64, i32, ptr)
+DEF_HELPER_3(vfp_touqd, i64, f64, i32, ptr)
 DEF_HELPER_3(vfp_shtos, f32, i32, i32, ptr)
 DEF_HELPER_3(vfp_sltos, f32, i32, i32, ptr)
+DEF_HELPER_3(vfp_sqtos, f32, i64, i32, ptr)
 DEF_HELPER_3(vfp_uhtos, f32, i32, i32, ptr)
 DEF_HELPER_3(vfp_ultos, f32, i32, i32, ptr)
+DEF_HELPER_3(vfp_uqtos, f32, i64, i32, ptr)
 DEF_HELPER_3(vfp_shtod, f64, i64, i32, ptr)
 DEF_HELPER_3(vfp_sltod, f64, i64, i32, ptr)
+DEF_HELPER_3(vfp_sqtod, f64, i64, i32, ptr)
 DEF_HELPER_3(vfp_uhtod, f64, i64, i32, ptr)
 DEF_HELPER_3(vfp_ultod, f64, i64, i32, ptr)
+DEF_HELPER_3(vfp_uqtod, f64, i64, i32, ptr)
 
 DEF_HELPER_2(vfp_fcvt_f16_to_f32, f32, i32, env)
 DEF_HELPER_2(vfp_fcvt_f32_to_f16, i32, f32, env)
-- 
1.8.5




[Qemu-devel] [PATCH v2 08/24] softfloat: Add float32_to_uint64()

2014-01-06 Thread Peter Maydell
From: Tom Musta tommu...@gmail.com

This patch adds the float32_to_uint64() routine, which converts a
32-bit floating point number to an unsigned 64 bit number.

This contribution can be licensed under either the softfloat-2a or -2b
license.

Signed-off-by: Tom Musta tommu...@gmail.com
Reviewed-by: Peter Maydell peter.mayd...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 fpu/softfloat.c | 46 ++
 include/fpu/softfloat.h |  1 +
 2 files changed, 47 insertions(+)

diff --git a/fpu/softfloat.c b/fpu/softfloat.c
index d2e9095..55c3ce1 100644
--- a/fpu/softfloat.c
+++ b/fpu/softfloat.c
@@ -1559,6 +1559,52 @@ int64 float32_to_int64( float32 a STATUS_PARAM )
 
 /*
 | Returns the result of converting the single-precision floating-point value
+| `a' to the 64-bit unsigned integer format.  The conversion is
+| performed according to the IEC/IEEE Standard for Binary Floating-Point
+| Arithmetic---which means in particular that the conversion is rounded
+| according to the current rounding mode.  If `a' is a NaN, the largest
+| unsigned integer is returned.  Otherwise, if the conversion overflows, the
+| largest unsigned integer is returned.  If the 'a' is negative, the result
+| is rounded and zero is returned; values that do not round to zero will
+| raise the inexact exception flag.
+**/
+
+uint64 float32_to_uint64(float32 a STATUS_PARAM)
+{
+flag aSign;
+int_fast16_t aExp, shiftCount;
+uint32_t aSig;
+uint64_t aSig64, aSigExtra;
+a = float32_squash_input_denormal(a STATUS_VAR);
+
+aSig = extractFloat32Frac(a);
+aExp = extractFloat32Exp(a);
+aSign = extractFloat32Sign(a);
+if ((aSign)  (aExp  126)) {
+float_raise(float_flag_invalid STATUS_VAR);
+if (float32_is_any_nan(a)) {
+return (int64_t)LIT64(0x);
+} else {
+return 0;
+}
+}
+shiftCount = 0xBE - aExp;
+if (aExp) {
+aSig |= 0x0080;
+}
+if (shiftCount  0) {
+float_raise(float_flag_invalid STATUS_VAR);
+return (int64_t)LIT64(0x);
+}
+
+aSig64 = aSig;
+aSig64 = 40;
+shift64ExtraRightJamming(aSig64, 0, shiftCount, aSig64, aSigExtra);
+return roundAndPackUint64(aSign, aSig64, aSigExtra STATUS_VAR);
+}
+
+/*
+| Returns the result of converting the single-precision floating-point value
 | `a' to the 64-bit two's complement integer format.  The conversion is
 | performed according to the IEC/IEEE Standard for Binary Floating-Point
 | Arithmetic, except that the conversion is always rounded toward zero.  If
diff --git a/include/fpu/softfloat.h b/include/fpu/softfloat.h
index 78b1656..eb81c3b 100644
--- a/include/fpu/softfloat.h
+++ b/include/fpu/softfloat.h
@@ -295,6 +295,7 @@ int32 float32_to_int32_round_to_zero( float32 STATUS_PARAM 
);
 uint32 float32_to_uint32( float32 STATUS_PARAM );
 uint32 float32_to_uint32_round_to_zero( float32 STATUS_PARAM );
 int64 float32_to_int64( float32 STATUS_PARAM );
+uint64 float32_to_uint64(float32 STATUS_PARAM);
 int64 float32_to_int64_round_to_zero( float32 STATUS_PARAM );
 float64 float32_to_float64( float32 STATUS_PARAM );
 floatx80 float32_to_floatx80( float32 STATUS_PARAM );
-- 
1.8.5




[Qemu-devel] [PULL 00/52] target-arm queue

2014-01-06 Thread Peter Maydell
First target-arm pull request of the year; please pull.

(Incidentally I like the way these pull requests have a
broad distribution of patch authors. The last 62-patch
monster had 9 different authors, this one has 10, and the
one from earlier in December had 9...)

thanks
-- PMM

The following changes since commit f976b09ea2493fd41c98aaf6512908db0bae:

  PPC: Fix compilation with TCG debug (2013-12-22 19:15:55 +0100)

are available in the git repository at:

  git://git.linaro.org/people/pmaydell/qemu-arm.git 
tags/pull-target-arm-20140106

for you to fetch changes up to 449d14c182dd5d2d8d06bc1c36074533309274b6:

  hw: arm_gic: Introduce gic_set_priority function (2014-01-06 11:16:48 +)


target-arm queue:
 * further A64 decoder patches, including enabling the aarch64-linux-user
   target, since we can now run at least some programs (FP and Neon
   instruction support is not yet complete)
 * cadence UART model fixes
 * some minor bug fixes and cleanups


Alex Bennée (6):
  target-arm: A64: add support for ld/st unsigned imm
  target-arm: A64: add support for ld/st with reg offset
  target-arm: A64: add support for ld/st with index
  target-arm: A64: add support for add, addi, sub, subi
  target-arm: A64: add support for move wide instructions
  .travis.yml: Add aarch64-* targets

Alexander Graf (8):
  target-arm: A64: add support for 3 src data proc insns
  target-arm: A64: implement SVC, BRK
  target-arm: aarch64: add support for ld lit
  target-arm: A64: Add support for dumping AArch64 VFP register state
  target-arm: A64: Add Floating-point data-processing (2 source) insns
  target-arm: A64: Add Floating-point data-processing (3 source) insns
  target-arm: A64: Add fmov (scalar, immediate) instruction
  target-arm: Give the FPSCR rounding modes names

Christoffer Dall (2):
  arm_gic: Rename GIC_X_TRIGGER to GIC_X_EDGE_TRIGGER
  hw: arm_gic: Introduce gic_set_priority function

Claudio Fontana (6):
  target-arm: A64: add support for add/sub with carry
  target-arm: A64: add support for conditional compare insns
  linux-user: AArch64: define TARGET_CLONE_BACKWARDS
  target-arm: A64: Add support for floating point compare
  target-arm: A64: Add support for floating point conditional compare
  target-arm: A64: Add support for floating point cond select

Michael Matz (1):
  target-arm: A64: support for ld/st/cl exclusive

Michael S. Tsirkin (1):
  target-arm: fix build with gcc 4.8.2

Peter Crosthwaite (13):
  char/cadence_uart: Mark struct fields as public/private
  char/cadence_uart: Add missing uart_update_state
  char/cadence_uart: Fix reset.
  char/cadence_uart: s/r_fifo/rx_fifo
  char/cadence_uart: Simplify status generation
  char/cadence_uart: Define Missing SR/ISR fields
  char/cadence_uart: Remove TX timer  add TX FIFO state
  char/cadence_uart: Fix can_receive logic
  char/cadence_uart: Use the TX fifo for transmission
  char/cadence_uart: Delete redundant rx rst logic
  char/cadence_uart: Implement Tx flow control
  target-arm: remove raw_read|write duplication
  arm/xilinx_zynq: Always instantiate the GEMs

Peter Maydell (13):
  target-arm: A64: add support for ld/st pair
  target-arm: A64: Add decoder skeleton for FP instructions
  target-arm: A64: implement FMOV
  target-arm: Pull add one cpreg to hashtable into its own function
  target-arm: Update generic cpreg code for AArch64
  target-arm: Remove ARMCPU/CPUARMState from cpregs APIs used by decoder
  target-arm: A64: Implement MRS/MSR/SYS/SYSL
  target-arm: A64: Implement minimal set of EL0-visible sysregs
  target-arm: Widen thread-local register state fields to 64 bits
  target-arm: Widen exclusive-access support struct fields to 64 bits
  default-configs: Add config for aarch64-linux-user
  target-arm: A64: Fix vector register access on bigendian hosts
  target-arm: Use VFP_BINOP macro for min, max, minnum, maxnum

Sergey Fedorov (1):
  target-arm: use c13_context field for CONTEXTIDR

Will Newton (1):
  linux-user: AArch64: Use correct values for FPSR/FPCR in sigcontext

 .travis.yml|1 +
 default-configs/aarch64-linux-user.mak |3 +
 hw/arm/xilinx_zynq.c   |   17 +-
 hw/char/cadence_uart.c |  153 +-
 hw/intc/arm_gic.c  |   27 +-
 hw/intc/arm_gic_common.c   |4 +-
 hw/intc/gic_internal.h |7 +-
 include/hw/intc/arm_gic_common.h   |2 +-
 linux-user/aarch64/syscall.h   |1 +
 linux-user/aarch64/target_cpu.h|5 +-
 linux-user/arm/target_cpu.h|2 +-
 linux-user/main.c  |  154 +-
 linux-user/signal.c

[Qemu-devel] [PULL 16/52] target-arm: Widen thread-local register state fields to 64 bits

2014-01-06 Thread Peter Maydell
The common pattern for system registers in a 64-bit capable ARM
CPU is that when in AArch32 the cp15 register is a view of the
bottom 32 bits of the 64-bit AArch64 system register; writes in
AArch32 leave the top half unchanged. The most natural way to
model this is to have the state field in the CPU struct be a
64 bit value, and simply have the AArch32 TCG code operate on
a pointer to its lower half.

For aarch64-linux-user the only registers we need to share like
this are the thread-local-storage ones. Widen their fields to
64 bits and provide the 64 bit reginfo struct to make them
visible in AArch64 state. Note that minor cleanup of the AArch64
system register encoding space means We can share the TPIDR_EL1
reginfo but need split encodings for TPIDR_EL0 and TPIDRRO_EL0.

Since we're touching almost every line in QEMU that uses the
c13_tls* fields in this patch anyway, we take the opportunity
to rename them in line with the standard ARM architectural names
for these registers.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 linux-user/aarch64/target_cpu.h |  5 -
 linux-user/arm/target_cpu.h |  2 +-
 linux-user/main.c   |  2 +-
 target-arm/cpu.h| 18 +++---
 target-arm/helper.c | 22 +++---
 5 files changed, 36 insertions(+), 13 deletions(-)

diff --git a/linux-user/aarch64/target_cpu.h b/linux-user/aarch64/target_cpu.h
index 6f5539b..21560ef 100644
--- a/linux-user/aarch64/target_cpu.h
+++ b/linux-user/aarch64/target_cpu.h
@@ -29,7 +29,10 @@ static inline void cpu_clone_regs(CPUARMState *env, 
target_ulong newsp)
 
 static inline void cpu_set_tls(CPUARMState *env, target_ulong newtls)
 {
-env-sr.tpidr_el0 = newtls;
+/* Note that AArch64 Linux keeps the TLS pointer in TPIDR; this is
+ * different from AArch32 Linux, which uses TPIDRRO.
+ */
+env-cp15.tpidr_el0 = newtls;
 }
 
 #endif
diff --git a/linux-user/arm/target_cpu.h b/linux-user/arm/target_cpu.h
index ed323c0..39d65b6 100644
--- a/linux-user/arm/target_cpu.h
+++ b/linux-user/arm/target_cpu.h
@@ -29,7 +29,7 @@ static inline void cpu_clone_regs(CPUARMState *env, 
target_ulong newsp)
 
 static inline void cpu_set_tls(CPUARMState *env, target_ulong newtls)
 {
-env-cp15.c13_tls2 = newtls;
+env-cp15.tpidrro_el0 = newtls;
 }
 
 #endif
diff --git a/linux-user/main.c b/linux-user/main.c
index 54f71fe..c0df8b5 100644
--- a/linux-user/main.c
+++ b/linux-user/main.c
@@ -566,7 +566,7 @@ do_kernel_trap(CPUARMState *env)
 end_exclusive();
 break;
 case 0x0fe0: /* __kernel_get_tls */
-env-regs[0] = env-cp15.c13_tls2;
+env-regs[0] = env-cp15.tpidrro_el0;
 break;
 case 0x0f60: /* __kernel_cmpxchg64 */
 arm_kernel_cmpxchg64_helper(env);
diff --git a/target-arm/cpu.h b/target-arm/cpu.h
index ab8ef17..fc36514 100644
--- a/target-arm/cpu.h
+++ b/target-arm/cpu.h
@@ -66,6 +66,18 @@
 /* ARM-specific interrupt pending bits.  */
 #define CPU_INTERRUPT_FIQ   CPU_INTERRUPT_TGT_EXT_1
 
+/* The usual mapping for an AArch64 system register to its AArch32
+ * counterpart is for the 32 bit world to have access to the lower
+ * half only (with writes leaving the upper half untouched). It's
+ * therefore useful to be able to pass TCG the offset of the least
+ * significant half of a uint64_t struct member.
+ */
+#ifdef HOST_WORDS_BIGENDIAN
+#define offsetoflow32(S, M) (offsetof(S, M + sizeof(uint32_t))
+#else
+#define offsetoflow32(S, M) offsetof(S, M)
+#endif
+
 /* Meanings of the ARMCPU object's two inbound GPIO lines */
 #define ARM_CPU_IRQ 0
 #define ARM_CPU_FIQ 1
@@ -188,9 +200,9 @@ typedef struct CPUARMState {
 uint32_t c12_vbar; /* vector base address register */
 uint32_t c13_fcse; /* FCSE PID.  */
 uint32_t c13_context; /* Context ID.  */
-uint32_t c13_tls1; /* User RW Thread register.  */
-uint32_t c13_tls2; /* User RO Thread register.  */
-uint32_t c13_tls3; /* Privileged Thread register.  */
+uint64_t tpidr_el0; /* User RW Thread register.  */
+uint64_t tpidrro_el0; /* User RO Thread register.  */
+uint64_t tpidr_el1; /* Privileged Thread register.  */
 uint32_t c14_cntfrq; /* Counter Frequency register */
 uint32_t c14_cntkctl; /* Timer Control register */
 ARMGenericTimer c14_timer[NUM_GTIMERS];
diff --git a/target-arm/helper.c b/target-arm/helper.c
index 868493d..e7d88ea 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -740,18 +740,26 @@ static const ARMCPRegInfo t2ee_cp_reginfo[] = {
 };
 
 static const ARMCPRegInfo v6k_cp_reginfo[] = {
+{ .name = TPIDR_EL0, .state = ARM_CP_STATE_AA64,
+  .opc0 = 3, .opc1 = 3, .opc2 = 2, .crn = 13, .crm = 0,
+  .access = PL0_RW,
+  .fieldoffset = offsetof(CPUARMState, cp15.tpidr_el0), .resetvalue = 0 },
 { .name = TPIDRURW, .cp = 15, .crn = 13, .crm = 0, .opc1 = 0, .opc2 = 2,
   

[Qemu-devel] [PATCH v2 10/24] softfloat: Fix float64_to_uint32

2014-01-06 Thread Peter Maydell
From: Tom Musta tommu...@gmail.com

The float64_to_uint32 has several flaws:

 - for numbers between 2**32 and 2**64, the inexact exception flag
   may get incorrectly set.  In this case, only the invalid flag
   should be set.

   test pattern: 425F81378DC0CD1F / 0x1.f81378dc0cd1fp+38

 - for numbers between 2**63 and 2**64, incorrect results may
   be produced:

   test pattern: 43EAAF73F1F0B8BD / 0x1.aaf73f1f0b8bdp+63

This patch re-implements float64_to_uint32 to re-use the
float64_to_uint64 routine (instead of float64_to_int64).  For the
saturation case, we ignore any flags which the conversion routine
has set and raise only the invalid flag.

This contribution can be licensed under either the softfloat-2a or -2b
license.

Signed-off-by: Tom Musta tommu...@gmail.com
Message-id: 1387397961-4894-5-git-send-email-tommu...@gmail.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 fpu/softfloat.c | 15 +++
 1 file changed, 7 insertions(+), 8 deletions(-)

diff --git a/fpu/softfloat.c b/fpu/softfloat.c
index c8e19b4..814cd01 100644
--- a/fpu/softfloat.c
+++ b/fpu/softfloat.c
@@ -6650,19 +6650,18 @@ uint_fast16_t float32_to_uint16_round_to_zero(float32 a 
STATUS_PARAM)
 
 uint32 float64_to_uint32( float64 a STATUS_PARAM )
 {
-int64_t v;
+uint64_t v;
 uint32 res;
+int old_exc_flags = get_float_exception_flags(status);
 
-v = float64_to_int64(a STATUS_VAR);
-if (v  0) {
-res = 0;
-float_raise( float_flag_invalid STATUS_VAR);
-} else if (v  0x) {
+v = float64_to_uint64(a STATUS_VAR);
+if (v  0x) {
 res = 0x;
-float_raise( float_flag_invalid STATUS_VAR);
 } else {
-res = v;
+return v;
 }
+set_float_exception_flags(old_exc_flags, status);
+float_raise(float_flag_invalid STATUS_VAR);
 return res;
 }
 
-- 
1.8.5




[Qemu-devel] [PATCH v2 05/24] softfloat: Fix float64_to_uint64

2014-01-06 Thread Peter Maydell
From: Tom Musta tommu...@gmail.com

The comment preceding the float64_to_uint64 routine suggests that
the implementation is broken.  And this is, indeed, the case.

This patch properly implements the conversion of a 64-bit floating
point number to an unsigned, 64 bit integer.

This contribution can be licensed under either the softfloat-2a or -2b
license.

Signed-off-by: Tom Musta tommu...@gmail.com
Reviewed-by: Peter Maydell peter.mayd...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 fpu/softfloat.c | 101 +++-
 1 file changed, 93 insertions(+), 8 deletions(-)

diff --git a/fpu/softfloat.c b/fpu/softfloat.c
index 3170b88..2364513 100644
--- a/fpu/softfloat.c
+++ b/fpu/softfloat.c
@@ -204,6 +204,56 @@ static int64 roundAndPackInt64( flag zSign, uint64_t 
absZ0, uint64_t absZ1 STATU
 }
 
 /*
+| Takes the 128-bit fixed-point value formed by concatenating `absZ0' and
+| `absZ1', with binary point between bits 63 and 64 (between the input words),
+| and returns the properly rounded 64-bit unsigned integer corresponding to the
+| input.  Ordinarily, the fixed-point input is simply rounded to an integer,
+| with the inexact exception raised if the input cannot be represented exactly
+| as an integer.  However, if the fixed-point input is too large, the invalid
+| exception is raised and the largest unsigned integer is returned.
+**/
+
+static int64 roundAndPackUint64(flag zSign, uint64_t absZ0,
+uint64_t absZ1 STATUS_PARAM)
+{
+int8 roundingMode;
+flag roundNearestEven, increment;
+
+roundingMode = STATUS(float_rounding_mode);
+roundNearestEven = (roundingMode == float_round_nearest_even);
+increment = ((int64_t)absZ1  0);
+if (!roundNearestEven) {
+if (roundingMode == float_round_to_zero) {
+increment = 0;
+} else if (absZ1) {
+if (zSign) {
+increment = (roundingMode == float_round_down)  absZ1;
+} else {
+increment = (roundingMode == float_round_up)  absZ1;
+}
+}
+}
+if (increment) {
+++absZ0;
+if (absZ0 == 0) {
+float_raise(float_flag_invalid STATUS_VAR);
+return LIT64(0x);
+}
+absZ0 = ~(((uint64_t)(absZ11) == 0)  roundNearestEven);
+}
+
+if (zSign  absZ0) {
+float_raise(float_flag_invalid STATUS_VAR);
+return 0;
+}
+
+if (absZ1) {
+STATUS(float_exception_flags) |= float_flag_inexact;
+}
+return absZ0;
+}
+
+/*
 | Returns the fraction bits of the single-precision floating-point value `a'.
 **/
 
@@ -6643,16 +6693,51 @@ uint_fast16_t float64_to_uint16_round_to_zero(float64 a 
STATUS_PARAM)
 return res;
 }
 
-/* FIXME: This looks broken.  */
-uint64_t float64_to_uint64 (float64 a STATUS_PARAM)
-{
-int64_t v;
+/*
+| Returns the result of converting the double-precision floating-point value
+| `a' to the 64-bit unsigned integer format.  The conversion is
+| performed according to the IEC/IEEE Standard for Binary Floating-Point
+| Arithmetic---which means in particular that the conversion is rounded
+| according to the current rounding mode.  If `a' is a NaN, the largest
+| positive integer is returned.  If the conversion overflows, the
+| largest unsigned integer is returned.  If 'a' is negative, the value is
+| rounded and zero is returned; negative values that do not round to zero
+| will raise the inexact exception.
+**/
 
-v = float64_val(int64_to_float64(INT64_MIN STATUS_VAR));
-v += float64_val(a);
-v = float64_to_int64(make_float64(v) STATUS_VAR);
+uint64_t float64_to_uint64(float64 a STATUS_PARAM)
+{
+flag aSign;
+int_fast16_t aExp, shiftCount;
+uint64_t aSig, aSigExtra;
+a = float64_squash_input_denormal(a STATUS_VAR);
 
-return v - INT64_MIN;
+aSig = extractFloat64Frac(a);
+aExp = extractFloat64Exp(a);
+aSign = extractFloat64Sign(a);
+if (aSign  (aExp  1022)) {
+float_raise(float_flag_invalid STATUS_VAR);
+if (float64_is_any_nan(a)) {
+return LIT64(0x);
+} else {
+return 0;
+}
+}
+if (aExp) {
+aSig |= LIT64(0x0010);
+}
+shiftCount = 0x433 - aExp;
+if (shiftCount = 0) {
+if (0x43E  aExp) {
+float_raise(float_flag_invalid STATUS_VAR);
+return LIT64(0x);
+}
+aSigExtra = 0;
+ 

[Qemu-devel] [PATCH v2 13/24] softfloat: Factor out RoundAndPackFloat16 and NormalizeFloat16Subnormal

2014-01-06 Thread Peter Maydell
In preparation for adding conversions between float16 and float64,
factor out code currently done inline in the float16=float32
conversion functions into functions RoundAndPackFloat16 and
NormalizeFloat16Subnormal along the lines of the existing versions
for the other float types.

Note that we change the handling of zExp from the inline code
to match the API of the other RoundAndPackFloat functions; however
we leave the positioning of the binary point between bits 22 and 23
rather than shifting it up to the high end of the word.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 fpu/softfloat.c | 209 +---
 1 file changed, 125 insertions(+), 84 deletions(-)

diff --git a/fpu/softfloat.c b/fpu/softfloat.c
index fa78f42..f095f82 100644
--- a/fpu/softfloat.c
+++ b/fpu/softfloat.c
@@ -3086,6 +3086,127 @@ static float16 packFloat16(flag zSign, int_fast16_t 
zExp, uint16_t zSig)
 (((uint32_t)zSign)  15) + (((uint32_t)zExp)  10) + zSig);
 }
 
+/*
+| Takes an abstract floating-point value having sign `zSign', exponent `zExp',
+| and significand `zSig', and returns the proper half-precision floating-
+| point value corresponding to the abstract input.  Ordinarily, the abstract
+| value is simply rounded and packed into the half-precision format, with
+| the inexact exception raised if the abstract input cannot be represented
+| exactly.  However, if the abstract value is too large, the overflow and
+| inexact exceptions are raised and an infinity or maximal finite value is
+| returned.  If the abstract value is too small, the input value is rounded to
+| a subnormal number, and the underflow and inexact exceptions are raised if
+| the abstract input cannot be represented exactly as a subnormal half-
+| precision floating-point number.
+| The `ieee' flag indicates whether to use IEEE standard half precision, or
+| ARM-style alternative representation, which omits the NaN and Inf
+| encodings in order to raise the maximum representable exponent by one.
+| The input significand `zSig' has its binary point between bits 22
+| and 23, which is 13 bits to the left of the usual location.  This shifted
+| significand must be normalized or smaller.  If `zSig' is not normalized,
+| `zExp' must be 0; in that case, the result returned is a subnormal number,
+| and it must not require rounding.  In the usual case that `zSig' is
+| normalized, `zExp' must be 1 less than the ``true'' floating-point exponent.
+| Note the slightly odd position of the binary point in zSig compared with the
+| other roundAndPackFloat functions. This should probably be fixed if we
+| need to implement more float16 routines than just conversion.
+| The handling of underflow and overflow follows the IEC/IEEE Standard for
+| Binary Floating-Point Arithmetic.
+**/
+
+static float32 roundAndPackFloat16(flag zSign, int_fast16_t zExp,
+   uint32_t zSig, flag ieee STATUS_PARAM)
+{
+int maxexp = ieee ? 29 : 30;
+uint32_t mask;
+uint32_t increment;
+int8 roundingMode;
+bool rounding_bumps_exp;
+bool is_tiny = false;
+
+/* Calculate the mask of bits of the mantissa which are not
+ * representable in half-precision and will be lost.
+ */
+if (zExp  1) {
+/* Will be denormal in halfprec */
+mask = 0x00ff;
+if (zExp = -11) {
+mask = 11 + zExp;
+}
+} else {
+/* Normal number in halfprec */
+mask = 0x1fff;
+}
+
+roundingMode = STATUS(float_rounding_mode);
+switch (roundingMode) {
+case float_round_nearest_even:
+increment = (mask + 1)  1;
+if ((zSig  mask) == increment) {
+increment = zSig  (increment  1);
+}
+break;
+case float_round_up:
+increment = zSign ? 0 : mask;
+break;
+case float_round_down:
+increment = zSign ? mask : 0;
+break;
+default: /* round_to_zero */
+increment = 0;
+break;
+}
+
+rounding_bumps_exp = (zSig + increment = 0x0100);
+
+if (zExp  maxexp || (zExp == maxexp  rounding_bumps_exp)) {
+if (ieee) {
+float_raise(float_flag_overflow | float_flag_inexact STATUS_VAR);
+return packFloat16(zSign, 0x1f, 0);
+} else {
+float_raise(float_flag_invalid STATUS_VAR);
+return packFloat16(zSign, 0x1f, 0x3ff);
+}
+}
+
+if (zExp  0) {
+/* Note that flush-to-zero does not affect half-precision results */
+is_tiny =
+(STATUS(float_detect_tininess) == float_tininess_before_rounding)
+|| (zExp  -1)
+|| (!rounding_bumps_exp);
+}
+if (zSig  mask) {
+float_raise(float_flag_inexact STATUS_VAR);
+if (is_tiny) {
+  

[Qemu-devel] [PATCH v2 11/24] softfloat: Fix float64_to_uint32_round_to_zero

2014-01-06 Thread Peter Maydell
From: Tom Musta tommu...@gmail.com

The float64_to_uint32_round_to_zero routine is incorrect.

For example, the following test pattern:

425F81378DC0CD1F / 0x1.f81378dc0cd1fp+38

will erroneously set the inexact flag.

This patch re-implements the routine to use the float64_to_uint64_round_to_zero
routine.  If saturation occurs we ignore any flags set by the
conversion function and raise only Invalid.

This contribution can be licensed under either the softfloat-2a or -2b
license.

Signed-off-by: Tom Musta tommu...@gmail.com
Message-id: 1387397961-4894-6-git-send-email-tommu...@gmail.com
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 fpu/softfloat.c | 15 +++
 1 file changed, 7 insertions(+), 8 deletions(-)

diff --git a/fpu/softfloat.c b/fpu/softfloat.c
index 814cd01..758022c 100644
--- a/fpu/softfloat.c
+++ b/fpu/softfloat.c
@@ -6667,19 +6667,18 @@ uint32 float64_to_uint32( float64 a STATUS_PARAM )
 
 uint32 float64_to_uint32_round_to_zero( float64 a STATUS_PARAM )
 {
-int64_t v;
+uint64_t v;
 uint32 res;
+int old_exc_flags = get_float_exception_flags(status);
 
-v = float64_to_int64_round_to_zero(a STATUS_VAR);
-if (v  0) {
-res = 0;
-float_raise( float_flag_invalid STATUS_VAR);
-} else if (v  0x) {
+v = float64_to_uint64_round_to_zero(a STATUS_VAR);
+if (v  0x) {
 res = 0x;
-float_raise( float_flag_invalid STATUS_VAR);
 } else {
-res = v;
+return v;
 }
+set_float_exception_flags(old_exc_flags, status);
+float_raise(float_flag_invalid STATUS_VAR);
 return res;
 }
 
-- 
1.8.5




[Qemu-devel] [PATCH v2 18/24] target-arm: Rename A32 VFP conversion helpers

2014-01-06 Thread Peter Maydell
From: Will Newton will.new...@linaro.org

The VFP conversion helpers for A32 round to zero as this is the only
rounding mode supported. Rename these helpers to make it clear that
they round to zero and are not suitable for use in the AArch64 code.

Signed-off-by: Will Newton will.new...@linaro.org
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/helper.c| 19 ++-
 target-arm/helper.h| 16 
 target-arm/translate.c | 24 +---
 3 files changed, 35 insertions(+), 24 deletions(-)

diff --git a/target-arm/helper.c b/target-arm/helper.c
index 501d798..905abd3 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -3976,7 +3976,7 @@ float32 VFP_HELPER(fcvts, d)(float64 x, CPUARMState *env)
 }
 
 /* VFP3 fixed point conversion.  */
-#define VFP_CONV_FIX(name, p, fsz, isz, itype) \
+#define VFP_CONV_FIX_FLOAT(name, p, fsz, isz, itype) \
 float##fsz HELPER(vfp_##name##to##p)(uint##isz##_t  x, uint32_t shift, \
  void *fpstp) \
 { \
@@ -3984,9 +3984,12 @@ float##fsz HELPER(vfp_##name##to##p)(uint##isz##_t  x, 
uint32_t shift, \
 float##fsz tmp; \
 tmp = itype##_to_##float##fsz(x, fpst); \
 return float##fsz##_scalbn(tmp, -(int)shift, fpst); \
-} \
-uint##isz##_t HELPER(vfp_to##name##p)(float##fsz x, uint32_t shift, \
-  void *fpstp) \
+}
+
+#define VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype, round) \
+uint##isz##_t HELPER(vfp_to##name##p##round)(float##fsz x, \
+ uint32_t shift, \
+ void *fpstp) \
 { \
 float_status *fpst = fpstp; \
 float##fsz tmp; \
@@ -3995,9 +3998,13 @@ uint##isz##_t HELPER(vfp_to##name##p)(float##fsz x, 
uint32_t shift, \
 return 0; \
 } \
 tmp = float##fsz##_scalbn(x, shift, fpst); \
-return float##fsz##_to_##itype##_round_to_zero(tmp, fpst); \
+return float##fsz##_to_##itype##round(tmp, fpst); \
 }
 
+#define VFP_CONV_FIX(name, p, fsz, isz, itype)   \
+VFP_CONV_FIX_FLOAT(name, p, fsz, isz, itype) \
+VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype, _round_to_zero)
+
 VFP_CONV_FIX(sh, d, 64, 64, int16)
 VFP_CONV_FIX(sl, d, 64, 64, int32)
 VFP_CONV_FIX(uh, d, 64, 64, uint16)
@@ -4007,6 +4014,8 @@ VFP_CONV_FIX(sl, s, 32, 32, int32)
 VFP_CONV_FIX(uh, s, 32, 32, uint16)
 VFP_CONV_FIX(ul, s, 32, 32, uint32)
 #undef VFP_CONV_FIX
+#undef VFP_CONV_FIX_FLOAT
+#undef VFP_CONV_FLOAT_FIX_ROUND
 
 /* Half precision conversions.  */
 static float32 do_fcvt_f16_to_f32(uint32_t a, CPUARMState *env, float_status 
*s)
diff --git a/target-arm/helper.h b/target-arm/helper.h
index dd1160e..b785623 100644
--- a/target-arm/helper.h
+++ b/target-arm/helper.h
@@ -115,14 +115,14 @@ DEF_HELPER_2(vfp_tosid, i32, f64, ptr)
 DEF_HELPER_2(vfp_tosizs, i32, f32, ptr)
 DEF_HELPER_2(vfp_tosizd, i32, f64, ptr)
 
-DEF_HELPER_3(vfp_toshs, i32, f32, i32, ptr)
-DEF_HELPER_3(vfp_tosls, i32, f32, i32, ptr)
-DEF_HELPER_3(vfp_touhs, i32, f32, i32, ptr)
-DEF_HELPER_3(vfp_touls, i32, f32, i32, ptr)
-DEF_HELPER_3(vfp_toshd, i64, f64, i32, ptr)
-DEF_HELPER_3(vfp_tosld, i64, f64, i32, ptr)
-DEF_HELPER_3(vfp_touhd, i64, f64, i32, ptr)
-DEF_HELPER_3(vfp_tould, i64, f64, i32, ptr)
+DEF_HELPER_3(vfp_toshs_round_to_zero, i32, f32, i32, ptr)
+DEF_HELPER_3(vfp_tosls_round_to_zero, i32, f32, i32, ptr)
+DEF_HELPER_3(vfp_touhs_round_to_zero, i32, f32, i32, ptr)
+DEF_HELPER_3(vfp_touls_round_to_zero, i32, f32, i32, ptr)
+DEF_HELPER_3(vfp_toshd_round_to_zero, i64, f64, i32, ptr)
+DEF_HELPER_3(vfp_tosld_round_to_zero, i64, f64, i32, ptr)
+DEF_HELPER_3(vfp_touhd_round_to_zero, i64, f64, i32, ptr)
+DEF_HELPER_3(vfp_tould_round_to_zero, i64, f64, i32, ptr)
 DEF_HELPER_3(vfp_shtos, f32, i32, i32, ptr)
 DEF_HELPER_3(vfp_sltos, f32, i32, i32, ptr)
 DEF_HELPER_3(vfp_uhtos, f32, i32, i32, ptr)
diff --git a/target-arm/translate.c b/target-arm/translate.c
index d04fc9f..8d240e1 100644
--- a/target-arm/translate.c
+++ b/target-arm/translate.c
@@ -1098,27 +1098,29 @@ VFP_GEN_FTOI(tosi)
 VFP_GEN_FTOI(tosiz)
 #undef VFP_GEN_FTOI
 
-#define VFP_GEN_FIX(name) \
+#define VFP_GEN_FIX(name, round) \
 static inline void gen_vfp_##name(int dp, int shift, int neon) \
 { \
 TCGv_i32 tmp_shift = tcg_const_i32(shift); \
 TCGv_ptr statusptr = get_fpstatus_ptr(neon); \
 if (dp) { \
-gen_helper_vfp_##name##d(cpu_F0d, cpu_F0d, tmp_shift, statusptr); \
+gen_helper_vfp_##name##d##round(cpu_F0d, cpu_F0d, tmp_shift, \
+statusptr); \
 } else { \
-gen_helper_vfp_##name##s(cpu_F0s, cpu_F0s, tmp_shift, statusptr); \
+gen_helper_vfp_##name##s##round(cpu_F0s, cpu_F0s, tmp_shift, \
+statusptr); \
 } \
 tcg_temp_free_i32(tmp_shift); \
 

[Qemu-devel] [PATCH v2 24/24] target-arm: A64: Add support for FCVT between half, single and double

2014-01-06 Thread Peter Maydell
Add support for FCVT between half, single and double precision.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 target-arm/helper.c| 20 +
 target-arm/helper.h|  2 ++
 target-arm/translate-a64.c | 75 +-
 3 files changed, 96 insertions(+), 1 deletion(-)

diff --git a/target-arm/helper.c b/target-arm/helper.c
index a0c1646..59e6208 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -4089,6 +4089,26 @@ uint32_t HELPER(vfp_fcvt_f32_to_f16)(float32 a, 
CPUARMState *env)
 return do_fcvt_f32_to_f16(a, env, env-vfp.fp_status);
 }
 
+float64 HELPER(vfp_fcvt_f16_to_f64)(uint32_t a, CPUARMState *env)
+{
+int ieee = (env-vfp.xregs[ARM_VFP_FPSCR]  (1  26)) == 0;
+float64 r = float16_to_float64(make_float16(a), ieee, env-vfp.fp_status);
+if (ieee) {
+return float64_maybe_silence_nan(r);
+}
+return r;
+}
+
+uint32_t HELPER(vfp_fcvt_f64_to_f16)(float64 a, CPUARMState *env)
+{
+int ieee = (env-vfp.xregs[ARM_VFP_FPSCR]  (1  26)) == 0;
+float16 r = float64_to_float16(a, ieee, env-vfp.fp_status);
+if (ieee) {
+r = float16_maybe_silence_nan(r);
+}
+return float16_val(r);
+}
+
 #define float32_two make_float32(0x4000)
 #define float32_three make_float32(0x4040)
 #define float32_one_point_five make_float32(0x3fc0)
diff --git a/target-arm/helper.h b/target-arm/helper.h
index 832ec12..213ccc6 100644
--- a/target-arm/helper.h
+++ b/target-arm/helper.h
@@ -154,6 +154,8 @@ DEF_HELPER_2(vfp_fcvt_f16_to_f32, f32, i32, env)
 DEF_HELPER_2(vfp_fcvt_f32_to_f16, i32, f32, env)
 DEF_HELPER_2(neon_fcvt_f16_to_f32, f32, i32, env)
 DEF_HELPER_2(neon_fcvt_f32_to_f16, i32, f32, env)
+DEF_HELPER_FLAGS_2(vfp_fcvt_f16_to_f64, TCG_CALL_NO_RWG, f64, i32, env)
+DEF_HELPER_FLAGS_2(vfp_fcvt_f64_to_f16, TCG_CALL_NO_RWG, i32, f64, env)
 
 DEF_HELPER_4(vfp_muladdd, f64, f64, f64, f64, ptr)
 DEF_HELPER_4(vfp_muladds, f32, f32, f32, f32, ptr)
diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
index 345a47b..cf80c46 100644
--- a/target-arm/translate-a64.c
+++ b/target-arm/translate-a64.c
@@ -3498,6 +3498,72 @@ static void handle_fp_1src_double(DisasContext *s, int 
opcode, int rd, int rn)
 tcg_temp_free_i64(tcg_res);
 }
 
+static void handle_fp_fcvt(DisasContext *s, int opcode,
+   int rd, int rn, int dtype, int ntype)
+{
+switch (ntype) {
+case 0x0:
+{
+TCGv_i32 tcg_rn = read_fp_sreg(s, rn);
+if (dtype == 1) {
+/* Single to double */
+TCGv_i64 tcg_rd = tcg_temp_new_i64();
+gen_helper_vfp_fcvtds(tcg_rd, tcg_rn, cpu_env);
+write_fp_dreg(s, rd, tcg_rd);
+tcg_temp_free_i64(tcg_rd);
+} else {
+/* Single to half */
+TCGv_i32 tcg_rd = tcg_temp_new_i32();
+gen_helper_vfp_fcvt_f32_to_f16(tcg_rd, tcg_rn, cpu_env);
+/* write_fp_sreg is OK here because top half of tcg_rd is zero */
+write_fp_sreg(s, rd, tcg_rd);
+tcg_temp_free_i32(tcg_rd);
+}
+tcg_temp_free_i32(tcg_rn);
+break;
+}
+case 0x1:
+{
+TCGv_i64 tcg_rn = read_fp_dreg(s, rn);
+TCGv_i32 tcg_rd = tcg_temp_new_i32();
+if (dtype == 0) {
+/* Double to single */
+gen_helper_vfp_fcvtsd(tcg_rd, tcg_rn, cpu_env);
+} else {
+/* Double to half */
+gen_helper_vfp_fcvt_f64_to_f16(tcg_rd, tcg_rn, cpu_env);
+/* write_fp_sreg is OK here because top half of tcg_rd is zero */
+}
+write_fp_sreg(s, rd, tcg_rd);
+tcg_temp_free_i32(tcg_rd);
+tcg_temp_free_i64(tcg_rn);
+break;
+}
+case 0x3:
+{
+TCGv_i32 tcg_rn = read_fp_sreg(s, rn);
+tcg_gen_ext16u_i32(tcg_rn, tcg_rn);
+if (dtype == 0) {
+/* Half to single */
+TCGv_i32 tcg_rd = tcg_temp_new_i32();
+gen_helper_vfp_fcvt_f16_to_f32(tcg_rd, tcg_rn, cpu_env);
+write_fp_sreg(s, rd, tcg_rd);
+tcg_temp_free_i32(tcg_rd);
+} else {
+/* Half to double */
+TCGv_i64 tcg_rd = tcg_temp_new_i64();
+gen_helper_vfp_fcvt_f16_to_f64(tcg_rd, tcg_rn, cpu_env);
+write_fp_dreg(s, rd, tcg_rd);
+tcg_temp_free_i64(tcg_rd);
+}
+tcg_temp_free_i32(tcg_rn);
+break;
+}
+default:
+abort();
+}
+}
+
 /* C3.6.25 Floating point data-processing (1 source)
  *   31  30  29 28   24 23  22  21 2015 14   10 95 40
  * +---+---+---+---+--+---++---+--+--+
@@ -3513,9 +3579,16 @@ static void disas_fp_1src(DisasContext *s, uint32_t insn)
 
 switch (opcode) {
 case 0x4: case 0x5: case 0x7:
+{
 /* FCVT between half, single and double precision */
-unsupported_encoding(s, insn);
+int dtype = 

[Qemu-devel] [PATCH v2 00/24] A64 decoder patchset 6: rest of floating point

2014-01-06 Thread Peter Maydell

This patchset completes the FP emulation, leaving us with only
Neon (and CRC32) to go to complete the user-mode emulation.
Most of this is fixing issues and adding new features to softfloat.
(As usual, all Linaro authored softfloat patches are licensed under
either softfloat-2a or softfloat-2b, at your option.)
We need Tom Musta's softfloat patches too, so I have included them
here (updated to the latest versions with the issues fixed).

Changes v1-v2:
 * updated versions of Tom Musta's patches Fix float64_to_uint64
   and Add float32_to_uint64
 * 16 bit int-to-float fns now take exact-width types
 * new patch: softfloat: Make the int-to-float functions take
   exact-width types, to make the other int-to-float functions
   consistent
 * Prepare VFP_CONV_FIX helpers for A64 uses now also drops the
   cast in the int_to_float call, since the above changes make it
   unnecessary
 * use 32 bit type as the intermediate when doing float-to-16-bit-int
   conversions
 * new patch: softfloat: Refactor code handling various rounding modes
   which is a pure refactoring of the rounding mode code to
   consistently use switches; this makes the ties-away support
   patch nicer and ends up with more readable code

Alex: we should coordinate about whether these softfloat patches
should go through my tree or yours, otherwise there's going to be
a clash...

thanks
-- PMM

Alexander Graf (1):
  target-arm: A64: Add Floating-point-fixed-point instructions

Peter Maydell (13):
  softfloat: Fix exception flag handling for float32_to_float16()
  softfloat: Add 16 bit integer to float conversions
  softfloat: Make the int-to-float functions take exact-width types
  softfloat: Only raise Invalid when conversions to int are out of range
  softfloat: Fix factor 2 error for scalbn on denormal inputs
  softfloat: Provide complete set of accessors for fp state
  softfloat: Factor out RoundAndPackFloat16 and
NormalizeFloat16Subnormal
  softfloat: Add float16 = float64 conversion functions
  softfloat: Refactor code handling various rounding modes
  softfloat: Add support for ties-away rounding
  target-arm: Ignore most exceptions from scalbn when doing fixpoint
conversion
  target-arm: A64: Add 1-source 32-to-32 and 64-to-64 FP instructions
  target-arm: A64: Add support for FCVT between half, single and double

Tom Musta (5):
  softfloat: Fix float64_to_uint64
  softfloat: Add float32_to_uint64()
  softfloat: Fix float64_to_uint64_round_to_zero
  softfloat: Fix float64_to_uint32
  softfloat: Fix float64_to_uint32_round_to_zero

Will Newton (5):
  softfloat: Add float to 16bit integer conversions.
  target-arm: Prepare VFP_CONV_FIX helpers for A64 uses
  target-arm: Rename A32 VFP conversion helpers
  target-arm: A64: Add extra VFP fixed point conversion helpers
  target-arm: A64: Add floating-point-integer conversion instructions

 fpu/softfloat.c| 1055 
 include/fpu/softfloat.h|   96 +++-
 target-arm/helper.c|  141 +-
 target-arm/helper.h|   25 ++
 target-arm/translate-a64.c |  424 +-
 target-arm/translate.c |   24 +-
 6 files changed, 1428 insertions(+), 337 deletions(-)

-- 
1.8.5




[Qemu-devel] [PATCH v2 14/24] softfloat: Add float16 = float64 conversion functions

2014-01-06 Thread Peter Maydell
Add the conversion functions float16_to_float64() and
float64_to_float16(), which will be needed for the ARM
A64 instruction set.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 fpu/softfloat.c | 75 +
 include/fpu/softfloat.h |  2 ++
 2 files changed, 77 insertions(+)

diff --git a/fpu/softfloat.c b/fpu/softfloat.c
index f095f82..78f680f 100644
--- a/fpu/softfloat.c
+++ b/fpu/softfloat.c
@@ -3281,6 +3281,81 @@ float16 float32_to_float16(float32 a, flag ieee 
STATUS_PARAM)
 return roundAndPackFloat16(aSign, aExp, aSig, ieee STATUS_VAR);
 }
 
+float64 float16_to_float64(float16 a, flag ieee STATUS_PARAM)
+{
+flag aSign;
+int_fast16_t aExp;
+uint32_t aSig;
+
+aSign = extractFloat16Sign(a);
+aExp = extractFloat16Exp(a);
+aSig = extractFloat16Frac(a);
+
+if (aExp == 0x1f  ieee) {
+if (aSig) {
+return commonNaNToFloat64(
+float16ToCommonNaN(a STATUS_VAR) STATUS_VAR);
+}
+return packFloat64(aSign, 0x7ff, 0);
+}
+if (aExp == 0) {
+if (aSig == 0) {
+return packFloat64(aSign, 0, 0);
+}
+
+normalizeFloat16Subnormal(aSig, aExp, aSig);
+aExp--;
+}
+return packFloat64(aSign, aExp + 0x3f0, ((uint64_t)aSig)  42);
+}
+
+float16 float64_to_float16(float64 a, flag ieee STATUS_PARAM)
+{
+flag aSign;
+int_fast16_t aExp;
+uint64_t aSig;
+uint32_t zSig;
+
+a = float64_squash_input_denormal(a STATUS_VAR);
+
+aSig = extractFloat64Frac(a);
+aExp = extractFloat64Exp(a);
+aSign = extractFloat64Sign(a);
+if (aExp == 0x7FF) {
+if (aSig) {
+/* Input is a NaN */
+if (!ieee) {
+float_raise(float_flag_invalid STATUS_VAR);
+return packFloat16(aSign, 0, 0);
+}
+return commonNaNToFloat16(
+float64ToCommonNaN(a STATUS_VAR) STATUS_VAR);
+}
+/* Infinity */
+if (!ieee) {
+float_raise(float_flag_invalid STATUS_VAR);
+return packFloat16(aSign, 0x1f, 0x3ff);
+}
+return packFloat16(aSign, 0x1f, 0);
+}
+shift64RightJamming(aSig, 29, aSig);
+zSig = aSig;
+if (aExp == 0  zSig == 0) {
+return packFloat16(aSign, 0, 0);
+}
+/* Decimal point between bits 22 and 23. Note that we add the 1 bit
+ * even if the input is denormal; however this is harmless because
+ * the largest possible single-precision denormal is still smaller
+ * than the smallest representable half-precision denormal, and so we
+ * will end up ignoring aSig and returning via the always return zero
+ * codepath.
+ */
+zSig |= 0x0080;
+aExp -= 0x3F1;
+
+return roundAndPackFloat16(aSign, aExp, zSig, ieee STATUS_VAR);
+}
+
 /*
 | Returns the result of converting the double-precision floating-point value
 | `a' to the extended double-precision floating-point format.  The conversion
diff --git a/include/fpu/softfloat.h b/include/fpu/softfloat.h
index a634a4e..83d324a 100644
--- a/include/fpu/softfloat.h
+++ b/include/fpu/softfloat.h
@@ -298,6 +298,8 @@ INLINE float64 uint16_to_float64(uint16_t v STATUS_PARAM)
 **/
 float16 float32_to_float16( float32, flag STATUS_PARAM );
 float32 float16_to_float32( float16, flag STATUS_PARAM );
+float16 float64_to_float16(float64 a, flag ieee STATUS_PARAM);
+float64 float16_to_float64(float16 a, flag ieee STATUS_PARAM);
 
 /*
 | Software half-precision operations.
-- 
1.8.5




[Qemu-devel] [PATCH v2 04/24] softfloat: Make the int-to-float functions take exact-width types

2014-01-06 Thread Peter Maydell
Currently the int-to-float functions take types which are specified
as at least X bits wide, rather than exactly X bits wide. This is
confusing and unhelpful since it means that the callers have to include
an explicit cast to [u]intXX_t to ensure the correct behaviour. Fix
them all to take the exactly-X-bits-wide types instead.

Note that this doesn't change behaviour at all since at the moment
we happen to define the 'int32' and 'uint32' types as exactly 32 bits
wide, and the 'int64' and 'uint64' types as exactly 64 bits wide.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 fpu/softfloat.c | 26 +-
 include/fpu/softfloat.h | 26 +-
 2 files changed, 26 insertions(+), 26 deletions(-)

diff --git a/fpu/softfloat.c b/fpu/softfloat.c
index dbaa32c..3170b88 100644
--- a/fpu/softfloat.c
+++ b/fpu/softfloat.c
@@ -1121,7 +1121,7 @@ static float128
 | according to the IEC/IEEE Standard for Binary Floating-Point Arithmetic.
 **/
 
-float32 int32_to_float32( int32 a STATUS_PARAM )
+float32 int32_to_float32(int32_t a STATUS_PARAM)
 {
 flag zSign;
 
@@ -1138,7 +1138,7 @@ float32 int32_to_float32( int32 a STATUS_PARAM )
 | according to the IEC/IEEE Standard for Binary Floating-Point Arithmetic.
 **/
 
-float64 int32_to_float64( int32 a STATUS_PARAM )
+float64 int32_to_float64(int32_t a STATUS_PARAM)
 {
 flag zSign;
 uint32 absA;
@@ -1161,7 +1161,7 @@ float64 int32_to_float64( int32 a STATUS_PARAM )
 | Arithmetic.
 **/
 
-floatx80 int32_to_floatx80( int32 a STATUS_PARAM )
+floatx80 int32_to_floatx80(int32_t a STATUS_PARAM)
 {
 flag zSign;
 uint32 absA;
@@ -1183,7 +1183,7 @@ floatx80 int32_to_floatx80( int32 a STATUS_PARAM )
 | according to the IEC/IEEE Standard for Binary Floating-Point Arithmetic.
 **/
 
-float128 int32_to_float128( int32 a STATUS_PARAM )
+float128 int32_to_float128(int32_t a STATUS_PARAM)
 {
 flag zSign;
 uint32 absA;
@@ -1205,7 +1205,7 @@ float128 int32_to_float128( int32 a STATUS_PARAM )
 | according to the IEC/IEEE Standard for Binary Floating-Point Arithmetic.
 **/
 
-float32 int64_to_float32( int64 a STATUS_PARAM )
+float32 int64_to_float32(int64_t a STATUS_PARAM)
 {
 flag zSign;
 uint64 absA;
@@ -1231,7 +1231,7 @@ float32 int64_to_float32( int64 a STATUS_PARAM )
 
 }
 
-float32 uint64_to_float32( uint64 a STATUS_PARAM )
+float32 uint64_to_float32(uint64_t a STATUS_PARAM)
 {
 int8 shiftCount;
 
@@ -1258,7 +1258,7 @@ float32 uint64_to_float32( uint64 a STATUS_PARAM )
 | according to the IEC/IEEE Standard for Binary Floating-Point Arithmetic.
 **/
 
-float64 int64_to_float64( int64 a STATUS_PARAM )
+float64 int64_to_float64(int64_t a STATUS_PARAM)
 {
 flag zSign;
 
@@ -1271,7 +1271,7 @@ float64 int64_to_float64( int64 a STATUS_PARAM )
 
 }
 
-float64 uint64_to_float64(uint64 a STATUS_PARAM)
+float64 uint64_to_float64(uint64_t a STATUS_PARAM)
 {
 int exp =  0x43C;
 
@@ -1292,7 +1292,7 @@ float64 uint64_to_float64(uint64 a STATUS_PARAM)
 | Arithmetic.
 **/
 
-floatx80 int64_to_floatx80( int64 a STATUS_PARAM )
+floatx80 int64_to_floatx80(int64_t a STATUS_PARAM)
 {
 flag zSign;
 uint64 absA;
@@ -1312,7 +1312,7 @@ floatx80 int64_to_floatx80( int64 a STATUS_PARAM )
 | according to the IEC/IEEE Standard for Binary Floating-Point Arithmetic.
 **/
 
-float128 int64_to_float128( int64 a STATUS_PARAM )
+float128 int64_to_float128(int64_t a STATUS_PARAM)
 {
 flag zSign;
 uint64 absA;
@@ -1339,7 +1339,7 @@ float128 int64_to_float128( int64 a STATUS_PARAM )
 
 }
 
-float128 uint64_to_float128(uint64 a STATUS_PARAM)
+float128 uint64_to_float128(uint64_t a STATUS_PARAM)
 {
 if (a == 0) {
 return float128_zero;
@@ -6445,12 +6445,12 @@ int float128_unordered_quiet( float128 a, float128 b 
STATUS_PARAM )
 }
 
 /* misc functions */
-float32 uint32_to_float32( uint32 a STATUS_PARAM )
+float32 uint32_to_float32(uint32_t a STATUS_PARAM)
 {
 return int64_to_float32(a STATUS_VAR);
 }
 
-float64 uint32_to_float64( uint32 a STATUS_PARAM )
+float64 uint32_to_float64(uint32_t a STATUS_PARAM)
 {
 return int64_to_float64(a STATUS_VAR);
 }
diff --git a/include/fpu/softfloat.h b/include/fpu/softfloat.h
index 926d849..78b1656 100644
--- a/include/fpu/softfloat.h
+++ b/include/fpu/softfloat.h
@@ -225,19 +225,19 @@ enum {
 

[Qemu-devel] [PATCH v2 16/24] softfloat: Add support for ties-away rounding

2014-01-06 Thread Peter Maydell
IEEE754-2008 specifies a new rounding mode:

roundTiesToAway: the floating-point number nearest to the infinitely
precise result shall be delivered; if the two nearest floating-point
numbers bracketing an unrepresentable infinitely precise result are
equally near, the one with larger magnitude shall be delivered.

Implement this new mode (it is needed for ARM). The general principle
is that the required code is exactly like the ties-to-even code,
except that we do not need to do the in case of exact tie clear LSB
to round-to-even, because the rounding operation naturally causes
the exact tie to round up in magnitude.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
---
 fpu/softfloat.c | 54 +
 include/fpu/softfloat.h |  3 ++-
 2 files changed, 56 insertions(+), 1 deletion(-)

diff --git a/fpu/softfloat.c b/fpu/softfloat.c
index 42cb705..49d90ef 100644
--- a/fpu/softfloat.c
+++ b/fpu/softfloat.c
@@ -111,6 +111,7 @@ static int32 roundAndPackInt32( flag zSign, uint64_t absZ 
STATUS_PARAM)
 roundNearestEven = ( roundingMode == float_round_nearest_even );
 switch (roundingMode) {
 case float_round_nearest_even:
+case float_round_ties_away:
 roundIncrement = 0x40;
 break;
 case float_round_to_zero:
@@ -161,6 +162,7 @@ static int64 roundAndPackInt64( flag zSign, uint64_t absZ0, 
uint64_t absZ1 STATU
 roundNearestEven = ( roundingMode == float_round_nearest_even );
 switch (roundingMode) {
 case float_round_nearest_even:
+case float_round_ties_away:
 increment = ((int64_t) absZ1  0);
 break;
 case float_round_to_zero:
@@ -214,6 +216,7 @@ static int64 roundAndPackUint64(flag zSign, uint64_t absZ0,
 roundNearestEven = (roundingMode == float_round_nearest_even);
 switch (roundingMode) {
 case float_round_nearest_even:
+case float_round_ties_away:
 increment = ((int64_t)absZ1  0);
 break;
 case float_round_to_zero:
@@ -366,6 +369,7 @@ static float32 roundAndPackFloat32(flag zSign, int_fast16_t 
zExp, uint32_t zSig
 roundNearestEven = ( roundingMode == float_round_nearest_even );
 switch (roundingMode) {
 case float_round_nearest_even:
+case float_round_ties_away:
 roundIncrement = 0x40;
 break;
 case float_round_to_zero:
@@ -550,6 +554,7 @@ static float64 roundAndPackFloat64(flag zSign, int_fast16_t 
zExp, uint64_t zSig
 roundNearestEven = ( roundingMode == float_round_nearest_even );
 switch (roundingMode) {
 case float_round_nearest_even:
+case float_round_ties_away:
 roundIncrement = 0x200;
 break;
 case float_round_to_zero:
@@ -734,6 +739,7 @@ static floatx80
 zSig0 |= ( zSig1 != 0 );
 switch (roundingMode) {
 case float_round_nearest_even:
+case float_round_ties_away:
 break;
 case float_round_to_zero:
 roundIncrement = 0;
@@ -794,6 +800,7 @@ static floatx80
  precision80:
 switch (roundingMode) {
 case float_round_nearest_even:
+case float_round_ties_away:
 increment = ((int64_t)zSig1  0);
 break;
 case float_round_to_zero:
@@ -838,6 +845,7 @@ static floatx80
 if ( zSig1 ) STATUS(float_exception_flags) |= float_flag_inexact;
 switch (roundingMode) {
 case float_round_nearest_even:
+case float_round_ties_away:
 increment = ((int64_t)zSig1  0);
 break;
 case float_round_to_zero:
@@ -1052,6 +1060,7 @@ static float128
 roundNearestEven = ( roundingMode == float_round_nearest_even );
 switch (roundingMode) {
 case float_round_nearest_even:
+case float_round_ties_away:
 increment = ((int64_t)zSig2  0);
 break;
 case float_round_to_zero:
@@ -1114,6 +1123,7 @@ static float128
 if ( isTiny  zSig2 ) float_raise( float_flag_underflow 
STATUS_VAR);
 switch (roundingMode) {
 case float_round_nearest_even:
+case float_round_ties_away:
 increment = ((int64_t)zSig2  0);
 break;
 case float_round_to_zero:
@@ -1785,6 +1795,11 @@ float32 float32_round_to_int( float32 a STATUS_PARAM)
 return packFloat32( aSign, 0x7F, 0 );
 }
 break;
+case float_round_ties_away:
+if (aExp == 0x7E) {
+return packFloat32(aSign, 0x7F, 0);
+}
+break;
  case float_round_down:
 return make_float32(aSign ? 0xBF80 : 0);
  case float_round_up:
@@ -1803,6 +1818,9 @@ float32 float32_round_to_int( float32 a STATUS_PARAM)
 z = ~lastBitMask;
 }
 break;
+case float_round_ties_away:
+z += lastBitMask  1;
+break;
 case float_round_to_zero:
 break;
 case float_round_up:
@@ -3183,6 +3201,9 @@ static float32 roundAndPackFloat16(flag zSign, 
int_fast16_t 

[Qemu-devel] [PATCH v2 02/24] softfloat: Add float to 16bit integer conversions.

2014-01-06 Thread Peter Maydell
From: Will Newton will.new...@linaro.org

ARMv8 requires support for converting 32 and 64bit floating point
values to signed and unsigned 16bit integers.

Signed-off-by: Will Newton will.new...@linaro.org
[PMM: updated not to incorrectly set Inexact for Invalid inputs]
Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 fpu/softfloat.c | 80 +
 include/fpu/softfloat.h |  4 +++
 2 files changed, 84 insertions(+)

diff --git a/fpu/softfloat.c b/fpu/softfloat.c
index 6a6b656..dbaa32c 100644
--- a/fpu/softfloat.c
+++ b/fpu/softfloat.c
@@ -6491,6 +6491,46 @@ uint32 float32_to_uint32_round_to_zero( float32 a 
STATUS_PARAM )
 return res;
 }
 
+int_fast16_t float32_to_int16(float32 a STATUS_PARAM)
+{
+int32_t v;
+int_fast16_t res;
+int old_exc_flags = get_float_exception_flags(status);
+
+v = float32_to_int32(a STATUS_VAR);
+if (v  -0x8000) {
+res = -0x8000;
+} else if (v  0x7fff) {
+res = 0x7fff;
+} else {
+return v;
+}
+
+set_float_exception_flags(old_exc_flags, status);
+float_raise(float_flag_invalid STATUS_VAR);
+return res;
+}
+
+uint_fast16_t float32_to_uint16(float32 a STATUS_PARAM)
+{
+int32_t v;
+uint_fast16_t res;
+int old_exc_flags = get_float_exception_flags(status);
+
+v = float32_to_int32(a STATUS_VAR);
+if (v  0) {
+res = 0;
+} else if (v  0x) {
+res = 0x;
+} else {
+return v;
+}
+
+set_float_exception_flags(old_exc_flags, status);
+float_raise(float_flag_invalid STATUS_VAR);
+return res;
+}
+
 uint_fast16_t float32_to_uint16_round_to_zero(float32 a STATUS_PARAM)
 {
 int64_t v;
@@ -6545,6 +6585,46 @@ uint32 float64_to_uint32_round_to_zero( float64 a 
STATUS_PARAM )
 return res;
 }
 
+int_fast16_t float64_to_int16(float64 a STATUS_PARAM)
+{
+int64_t v;
+int_fast16_t res;
+int old_exc_flags = get_float_exception_flags(status);
+
+v = float64_to_int32(a STATUS_VAR);
+if (v  -0x8000) {
+res = -0x8000;
+} else if (v  0x7fff) {
+res = 0x7fff;
+} else {
+return v;
+}
+
+set_float_exception_flags(old_exc_flags, status);
+float_raise(float_flag_invalid STATUS_VAR);
+return res;
+}
+
+uint_fast16_t float64_to_uint16(float64 a STATUS_PARAM)
+{
+int64_t v;
+uint_fast16_t res;
+int old_exc_flags = get_float_exception_flags(status);
+
+v = float64_to_int32(a STATUS_VAR);
+if (v  0) {
+res = 0;
+} else if (v  0x) {
+res = 0x;
+} else {
+return v;
+}
+
+set_float_exception_flags(old_exc_flags, status);
+float_raise(float_flag_invalid STATUS_VAR);
+return res;
+}
+
 uint_fast16_t float64_to_uint16_round_to_zero(float64 a STATUS_PARAM)
 {
 int64_t v;
diff --git a/include/fpu/softfloat.h b/include/fpu/softfloat.h
index 2365274..a9b8cd9 100644
--- a/include/fpu/softfloat.h
+++ b/include/fpu/softfloat.h
@@ -265,6 +265,8 @@ extern const float16 float16_default_nan;
 /*
 | Software IEC/IEEE single-precision conversion routines.
 **/
+int_fast16_t float32_to_int16(float32 STATUS_PARAM);
+uint_fast16_t float32_to_uint16(float32 STATUS_PARAM);
 int_fast16_t float32_to_int16_round_to_zero(float32 STATUS_PARAM);
 uint_fast16_t float32_to_uint16_round_to_zero(float32 STATUS_PARAM);
 int32 float32_to_int32( float32 STATUS_PARAM );
@@ -371,6 +373,8 @@ extern const float32 float32_default_nan;
 /*
 | Software IEC/IEEE double-precision conversion routines.
 **/
+int_fast16_t float64_to_int16(float64 STATUS_PARAM);
+uint_fast16_t float64_to_uint16(float64 STATUS_PARAM);
 int_fast16_t float64_to_int16_round_to_zero(float64 STATUS_PARAM);
 uint_fast16_t float64_to_uint16_round_to_zero(float64 STATUS_PARAM);
 int32 float64_to_int32( float64 STATUS_PARAM );
-- 
1.8.5




Re: [Qemu-devel] [PATCHv3 3/6] ui/vnc: optimize dirty bitmap tracking

2014-01-06 Thread Peter Lieven
On 06.01.2014 11:08, Wenchao Xia wrote:
 于 2014/1/6 2:02, Peter Lieven 写道:
 vnc_update_client currently scans the dirty bitmap of each client
 bitwise which is a very costly operation if only few bits are dirty.
 vnc_refresh_server_surface does almost the same.
 this patch optimizes both by utilizing the heavily optimized
 function find_next_bit to find the offset of the next dirty
 bit in the dirty bitmaps.

 The following artifical test (just the bitmap operation part) running
 vnc_update_client 65536 times on a 2560x2048 surface illustrates the
 performance difference:

 All bits clean - vnc_update_client_new: 0.07 secs
   vnc_update_client_old: 10.98 secs

 All bits dirty - vnc_update_client_new: 11.26 secs
   vnc_update_client_old: 20.19 secs

 Few bits dirty - vnc_update_client_new: 0.08 secs
   vnc_update_client_old: 10.98 secs

 The case for all bits dirty is still rather slow, this
 is due to the implementation of find_and_clear_dirty_height.
 This will be addresses in a separate patch.

 Signed-off-by: Peter Lieven p...@kamp.de
 ---
   ui/vnc.c |  154 
 +-
   ui/vnc.h |4 ++
   2 files changed, 87 insertions(+), 71 deletions(-)

 diff --git a/ui/vnc.c b/ui/vnc.c
 index 1d2aa1a..6a0c03e 100644
 --- a/ui/vnc.c
 +++ b/ui/vnc.c
 @@ -572,6 +572,14 @@ void *vnc_server_fb_ptr(VncDisplay *vd, int x, int y)
   ptr += x * VNC_SERVER_FB_BYTES;
   return ptr;
   }
 +/* this sets only the visible pixels of a dirty bitmap */
 +#define VNC_SET_VISIBLE_PIXELS_DIRTY(bitmap, w, h) {\
 +int y;\
 +memset(bitmap, 0x00, sizeof(bitmap));\
 +for (y = 0; y  h; y++) {\
 +bitmap_set(bitmap[y], 0, w / VNC_DIRTY_PIXELS_PER_BIT);\
   Will it be a problem when vnc's width % VNC_DIRTY_PIXELS_PER_BIT != 0?
 Although it is a rare case, but I think it is better round it up, since
 v and VNC_DIRTY_PIXELS_PER_BIT are variables. A macro computing it
 would be nice:
Good point, I will use DIV_ROUND_UP here.

 #define VNC_DIRTY_BITS_FROM_WIDTH(w) (w + VNC_DIRTY_PIXELS_PER_BIT - 1/
 VNC_DIRTY_PIXELS_PER_BIT)
 #define VNC_DIRTY_BITS (VNC_DIRTY_BITS_FROM_WIDTH(VNC_MAX_WIDTH)

 then here:
 bitmap_set(bitmap[y], 0, VNC_DIRTY_BITS_FROM_WIDTH(w));

 Or simply warn or coredump when v % VNC_DIRTY_PIXELS_PER_BIT != 0.

 Also, in vnc.h:
 /* VNC_MAX_WIDTH must be a multiple of 16. */
 #define VNC_MAX_WIDTH 2560
 #define VNC_MAX_HEIGHT 2048

 Maybe it should be updated as:
 /* VNC_MAX_WIDTH must be a multiple of VNC_DIRTY_PIXELS_PER_BIT. */
correct. will fix as well.

 +} \
 +}

   static void vnc_dpy_switch(DisplayChangeListener *dcl,
  DisplaySurface *surface)
 @@ -597,7 +605,9 @@ static void vnc_dpy_switch(DisplayChangeListener *dcl,
   qemu_pixman_image_unref(vd-guest.fb);
   vd-guest.fb = pixman_image_ref(surface-image);
   vd-guest.format = surface-format;
 -memset(vd-guest.dirty, 0xFF, sizeof(vd-guest.dirty));
 +VNC_SET_VISIBLE_PIXELS_DIRTY(vd-guest.dirty,
 + surface_width(vd-ds),
 + surface_height(vd-ds));

   QTAILQ_FOREACH(vs, vd-clients, next) {
   vnc_colordepth(vs);
 @@ -605,7 +615,9 @@ static void vnc_dpy_switch(DisplayChangeListener *dcl,
   if (vs-vd-cursor) {
   vnc_cursor_define(vs);
   }
 -memset(vs-dirty, 0xFF, sizeof(vs-dirty));
 +VNC_SET_VISIBLE_PIXELS_DIRTY(vs-dirty,
 + surface_width(vd-ds),
 + surface_height(vd-ds));
   }
   }

 @@ -889,10 +901,9 @@ static int vnc_update_client(VncState *vs, int 
 has_dirty)
   VncDisplay *vd = vs-vd;
   VncJob *job;
   int y;
 -int width, height;
 +int height;
   int n = 0;

 -
   if (vs-output.offset  !vs-audio_cap  !vs-force_update)
   /* kernel send buffers are full - drop frames to throttle */
   return 0;
 @@ -908,39 +919,27 @@ static int vnc_update_client(VncState *vs, int 
 has_dirty)
*/
   job = vnc_job_new(vs);

 -width = MIN(pixman_image_get_width(vd-server), vs-client_width);
   height = MIN(pixman_image_get_height(vd-server), 
 vs-client_height);

 -for (y = 0; y  height; y++) {
 -int x;
 -int last_x = -1;
 -for (x = 0; x  width / VNC_DIRTY_PIXELS_PER_BIT; x++) {
 -if (test_and_clear_bit(x, vs-dirty[y])) {
 -if (last_x == -1) {
 -last_x = x;
 -}
 -} else {
 -if (last_x != -1) {
 -int h = find_and_clear_dirty_height(vs, y, last_x, 
 x,
 -height);
 -
 -n += vnc_job_add_rect(job,
 -

Re: [Qemu-devel] Project idea: make QEMU more flexible

2014-01-06 Thread Peter Maydell
On 6 January 2014 12:54, Wei Liu wei.l...@citrix.com wrote:
 In fact I've already hacked a prototype during Christmas. What's I've
 done so far:

 1. create target-null which only has some stubs to CPU emulation
framework.

 2. add a few lines to configure / Makefiles*, create
default-configs/null-softmmu

I think it would be better to add support to allow you to
configure with --disable-tcg. This would match the existing
--disable/--enable switches for KVM and Xen, and then you
could configure --disable-kvm --disable-tcg --enable-xen
and get a qemu-system-i386 or qemu-system-arm with only
the Xen support and none of the TCG emulation code.

thanks
-- PMM



[Qemu-devel] [PULL 28/52] target-arm: Use VFP_BINOP macro for min, max, minnum, maxnum

2014-01-06 Thread Peter Maydell
Use the VFP_BINOP macro to provide helpers for min, max, minnum
and maxnum, rather than hand-rolling them. (The float64 max
version is not used by A32 but will be needed for A64.)

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/helper.c  | 29 -
 target-arm/helper.h  | 15 ---
 target-arm/neon_helper.c | 12 
 target-arm/translate.c   | 16 
 4 files changed, 20 insertions(+), 52 deletions(-)

diff --git a/target-arm/helper.c b/target-arm/helper.c
index e7d88ea..74042b8 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -3864,6 +3864,10 @@ VFP_BINOP(add)
 VFP_BINOP(sub)
 VFP_BINOP(mul)
 VFP_BINOP(div)
+VFP_BINOP(min)
+VFP_BINOP(max)
+VFP_BINOP(minnum)
+VFP_BINOP(maxnum)
 #undef VFP_BINOP
 
 float32 VFP_HELPER(neg, s)(float32 a)
@@ -4317,28 +4321,3 @@ float64 VFP_HELPER(muladd, d)(float64 a, float64 b, 
float64 c, void *fpstp)
 float_status *fpst = fpstp;
 return float64_muladd(a, b, c, 0, fpst);
 }
-
-/* ARMv8 VMAXNM/VMINNM */
-float32 VFP_HELPER(maxnm, s)(float32 a, float32 b, void *fpstp)
-{
-float_status *fpst = fpstp;
-return float32_maxnum(a, b, fpst);
-}
-
-float64 VFP_HELPER(maxnm, d)(float64 a, float64 b, void *fpstp)
-{
-float_status *fpst = fpstp;
-return float64_maxnum(a, b, fpst);
-}
-
-float32 VFP_HELPER(minnm, s)(float32 a, float32 b, void *fpstp)
-{
-float_status *fpst = fpstp;
-return float32_minnum(a, b, fpst);
-}
-
-float64 VFP_HELPER(minnm, d)(float64 a, float64 b, void *fpstp)
-{
-float_status *fpst = fpstp;
-return float64_minnum(a, b, fpst);
-}
diff --git a/target-arm/helper.h b/target-arm/helper.h
index 73d67dc..dd1160e 100644
--- a/target-arm/helper.h
+++ b/target-arm/helper.h
@@ -79,6 +79,14 @@ DEF_HELPER_3(vfp_muls, f32, f32, f32, ptr)
 DEF_HELPER_3(vfp_muld, f64, f64, f64, ptr)
 DEF_HELPER_3(vfp_divs, f32, f32, f32, ptr)
 DEF_HELPER_3(vfp_divd, f64, f64, f64, ptr)
+DEF_HELPER_3(vfp_maxs, f32, f32, f32, ptr)
+DEF_HELPER_3(vfp_maxd, f64, f64, f64, ptr)
+DEF_HELPER_3(vfp_mins, f32, f32, f32, ptr)
+DEF_HELPER_3(vfp_mind, f64, f64, f64, ptr)
+DEF_HELPER_3(vfp_maxnums, f32, f32, f32, ptr)
+DEF_HELPER_3(vfp_maxnumd, f64, f64, f64, ptr)
+DEF_HELPER_3(vfp_minnums, f32, f32, f32, ptr)
+DEF_HELPER_3(vfp_minnumd, f64, f64, f64, ptr)
 DEF_HELPER_1(vfp_negs, f32, f32)
 DEF_HELPER_1(vfp_negd, f64, f64)
 DEF_HELPER_1(vfp_abss, f32, f32)
@@ -132,11 +140,6 @@ DEF_HELPER_2(neon_fcvt_f32_to_f16, i32, f32, env)
 DEF_HELPER_4(vfp_muladdd, f64, f64, f64, f64, ptr)
 DEF_HELPER_4(vfp_muladds, f32, f32, f32, f32, ptr)
 
-DEF_HELPER_3(vfp_maxnmd, f64, f64, f64, ptr)
-DEF_HELPER_3(vfp_maxnms, f32, f32, f32, ptr)
-DEF_HELPER_3(vfp_minnmd, f64, f64, f64, ptr)
-DEF_HELPER_3(vfp_minnms, f32, f32, f32, ptr)
-
 DEF_HELPER_3(recps_f32, f32, f32, f32, env)
 DEF_HELPER_3(rsqrts_f32, f32, f32, f32, env)
 DEF_HELPER_2(recpe_f32, f32, f32, env)
@@ -346,8 +349,6 @@ DEF_HELPER_2(neon_qneg_s8, i32, env, i32)
 DEF_HELPER_2(neon_qneg_s16, i32, env, i32)
 DEF_HELPER_2(neon_qneg_s32, i32, env, i32)
 
-DEF_HELPER_3(neon_min_f32, i32, i32, i32, ptr)
-DEF_HELPER_3(neon_max_f32, i32, i32, i32, ptr)
 DEF_HELPER_3(neon_abd_f32, i32, i32, i32, ptr)
 DEF_HELPER_3(neon_ceq_f32, i32, i32, i32, ptr)
 DEF_HELPER_3(neon_cge_f32, i32, i32, i32, ptr)
diff --git a/target-arm/neon_helper.c b/target-arm/neon_helper.c
index b028cc2..be6fbd9 100644
--- a/target-arm/neon_helper.c
+++ b/target-arm/neon_helper.c
@@ -1765,18 +1765,6 @@ uint32_t HELPER(neon_qneg_s32)(CPUARMState *env, 
uint32_t x)
 }
 
 /* NEON Float helpers.  */
-uint32_t HELPER(neon_min_f32)(uint32_t a, uint32_t b, void *fpstp)
-{
-float_status *fpst = fpstp;
-return float32_val(float32_min(make_float32(a), make_float32(b), fpst));
-}
-
-uint32_t HELPER(neon_max_f32)(uint32_t a, uint32_t b, void *fpstp)
-{
-float_status *fpst = fpstp;
-return float32_val(float32_max(make_float32(a), make_float32(b), fpst));
-}
-
 uint32_t HELPER(neon_abd_f32)(uint32_t a, uint32_t b, void *fpstp)
 {
 float_status *fpst = fpstp;
diff --git a/target-arm/translate.c b/target-arm/translate.c
index 4387547..d04fc9f 100644
--- a/target-arm/translate.c
+++ b/target-arm/translate.c
@@ -2725,9 +2725,9 @@ static int handle_vminmaxnm(uint32_t insn, uint32_t rd, 
uint32_t rn,
 tcg_gen_ld_f64(frn, cpu_env, vfp_reg_offset(dp, rn));
 tcg_gen_ld_f64(frm, cpu_env, vfp_reg_offset(dp, rm));
 if (vmin) {
-gen_helper_vfp_minnmd(dest, frn, frm, fpst);
+gen_helper_vfp_minnumd(dest, frn, frm, fpst);
 } else {
-gen_helper_vfp_maxnmd(dest, frn, frm, fpst);
+gen_helper_vfp_maxnumd(dest, frn, frm, fpst);
 }
 tcg_gen_st_f64(dest, cpu_env, vfp_reg_offset(dp, rd));
 tcg_temp_free_i64(frn);
@@ -2743,9 +2743,9 @@ static int handle_vminmaxnm(uint32_t insn, uint32_t rd, 
uint32_t rn,
 tcg_gen_ld_f32(frn, cpu_env, 

[Qemu-devel] [PULL 11/52] target-arm: Pull add one cpreg to hashtable into its own function

2014-01-06 Thread Peter Maydell
define_one_arm_cp_reg_with_opaque() has a set of nested loops which
insert a cpreg entry into the hashtable for each of the possible
opc/crn/crm values allowed by wildcard specifications. We're about
to add an extra loop to this nesting, so pull the core of the loop
(which adds a single entry to the hashtable) out into its own
function for clarity.

Signed-off-by: Peter Maydell peter.mayd...@linaro.org
Reviewed-by: Richard Henderson r...@twiddle.net
---
 target-arm/helper.c | 94 +
 1 file changed, 52 insertions(+), 42 deletions(-)

diff --git a/target-arm/helper.c b/target-arm/helper.c
index 6ebd7dc..d833163 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -1937,6 +1937,57 @@ CpuDefinitionInfoList *arch_query_cpu_definitions(Error 
**errp)
 return cpu_list;
 }
 
+static void add_cpreg_to_hashtable(ARMCPU *cpu, const ARMCPRegInfo *r,
+   void *opaque, int crm, int opc1, int opc2)
+{
+/* Private utility function for define_one_arm_cp_reg_with_opaque():
+ * add a single reginfo struct to the hash table.
+ */
+uint32_t *key = g_new(uint32_t, 1);
+ARMCPRegInfo *r2 = g_memdup(r, sizeof(ARMCPRegInfo));
+int is64 = (r-type  ARM_CP_64BIT) ? 1 : 0;
+*key = ENCODE_CP_REG(r-cp, is64, r-crn, crm, opc1, opc2);
+if (opaque) {
+r2-opaque = opaque;
+}
+/* Make sure reginfo passed to helpers for wildcarded regs
+ * has the correct crm/opc1/opc2 for this reg, not CP_ANY:
+ */
+r2-crm = crm;
+r2-opc1 = opc1;
+r2-opc2 = opc2;
+/* By convention, for wildcarded registers only the first
+ * entry is used for migration; the others are marked as
+ * NO_MIGRATE so we don't try to transfer the register
+ * multiple times. Special registers (ie NOP/WFI) are
+ * never migratable.
+ */
+if ((r-type  ARM_CP_SPECIAL) ||
+((r-crm == CP_ANY)  crm != 0) ||
+((r-opc1 == CP_ANY)  opc1 != 0) ||
+((r-opc2 == CP_ANY)  opc2 != 0)) {
+r2-type |= ARM_CP_NO_MIGRATE;
+}
+
+/* Overriding of an existing definition must be explicitly
+ * requested.
+ */
+if (!(r-type  ARM_CP_OVERRIDE)) {
+ARMCPRegInfo *oldreg;
+oldreg = g_hash_table_lookup(cpu-cp_regs, key);
+if (oldreg  !(oldreg-type  ARM_CP_OVERRIDE)) {
+fprintf(stderr, Register redefined: cp=%d %d bit 
+crn=%d crm=%d opc1=%d opc2=%d, 
+was %s, now %s\n, r2-cp, 32 + 32 * is64,
+r2-crn, r2-crm, r2-opc1, r2-opc2,
+oldreg-name, r2-name);
+g_assert_not_reached();
+}
+}
+g_hash_table_insert(cpu-cp_regs, key, r2);
+}
+
+
 void define_one_arm_cp_reg_with_opaque(ARMCPU *cpu,
const ARMCPRegInfo *r, void *opaque)
 {
@@ -1977,48 +2028,7 @@ void define_one_arm_cp_reg_with_opaque(ARMCPU *cpu,
 for (crm = crmmin; crm = crmmax; crm++) {
 for (opc1 = opc1min; opc1 = opc1max; opc1++) {
 for (opc2 = opc2min; opc2 = opc2max; opc2++) {
-uint32_t *key = g_new(uint32_t, 1);
-ARMCPRegInfo *r2 = g_memdup(r, sizeof(ARMCPRegInfo));
-int is64 = (r-type  ARM_CP_64BIT) ? 1 : 0;
-*key = ENCODE_CP_REG(r-cp, is64, r-crn, crm, opc1, opc2);
-if (opaque) {
-r2-opaque = opaque;
-}
-/* Make sure reginfo passed to helpers for wildcarded regs
- * has the correct crm/opc1/opc2 for this reg, not CP_ANY:
- */
-r2-crm = crm;
-r2-opc1 = opc1;
-r2-opc2 = opc2;
-/* By convention, for wildcarded registers only the first
- * entry is used for migration; the others are marked as
- * NO_MIGRATE so we don't try to transfer the register
- * multiple times. Special registers (ie NOP/WFI) are
- * never migratable.
- */
-if ((r-type  ARM_CP_SPECIAL) ||
-((r-crm == CP_ANY)  crm != 0) ||
-((r-opc1 == CP_ANY)  opc1 != 0) ||
-((r-opc2 == CP_ANY)  opc2 != 0)) {
-r2-type |= ARM_CP_NO_MIGRATE;
-}
-
-/* Overriding of an existing definition must be explicitly
- * requested.
- */
-if (!(r-type  ARM_CP_OVERRIDE)) {
-ARMCPRegInfo *oldreg;
-oldreg = g_hash_table_lookup(cpu-cp_regs, key);
-if (oldreg  !(oldreg-type  ARM_CP_OVERRIDE)) {
-fprintf(stderr, Register redefined: cp=%d %d bit 
-crn=%d crm=%d opc1=%d opc2=%d, 
-was %s, now %s\n, r2-cp, 32 + 32 * is64,
-r2-crn, 

  1   2   3   >