[Qemu-devel] [PATCH] target-i386: fix translation of sse {, u}comis{s, d} instructions

2013-09-25 Thread Nathan Froyd
While the generic SSE translation codepath contains special logic to use
32-bit or 64-bit memory operands for some instructions, this logic doesn't
catch the SSE {,u}comis{s,d} instructions.  This oversight leads to too
many bytes being read when those instructions use memory operands, which
can in turn lead to page faults.

The fix is simple: add a special case for these instructions.  It did not
fit cleanly into the existing case, so some cut-and-paste was necesary.

Signed-off-by: Nathan Froyd froy...@mozilla.com
---
 target-i386/translate.c |   10 ++
 1 file changed, 10 insertions(+)

diff --git a/target-i386/translate.c b/target-i386/translate.c
index be74ebc..687859a 100644
--- a/target-i386/translate.c
+++ b/target-i386/translate.c
@@ -4576,6 +4576,16 @@ static void gen_sse(CPUX86State *env, DisasContext *s, 
int b,
 /* 64 bit access */
 gen_ldq_env_A0(s-mem_index, 
offsetof(CPUX86State,xmm_t0.XMM_D(0)));
 }
+} else if (b1 = 1  (b == 0x2e || b == 0x2f)) {
+/* specific case for SSE *comis{s,d} instructions */
+if (b1 == 0) {
+/* 32 bit access */
+gen_op_ld_T0_A0(OT_LONG + s-mem_index);
+tcg_gen_st32_tl(cpu_T[0], cpu_env, 
offsetof(CPUX86State,xmm_t0.XMM_L(0)));
+} else {
+/* 64 bit access */
+gen_ldq_env_A0(s-mem_index, 
offsetof(CPUX86State,xmm_t0.XMM_D(0)));
+}
 } else {
 gen_ldo_env_A0(s-mem_index, op2_offset);
 }
-- 
1.7.10.4




Re: [Qemu-devel] Can anybody help me figure out what has been done about floating point multiply in QEMU?

2011-05-23 Thread Nathan Froyd
On 05/23/2011 01:36 PM, Guan, Qiang wrote:
 I want to figure out what is happening in emulating the floating point
 calculation in QEMU. I checked the codes in target-i386/translate.c, but I
 cannot find anything about floating point calculation, I can only find the
 emulation about integer mul or div. My question is what did QEMU do when
 they need to emulate a floating point calculation? where are these codes?

All the code for manipulating floating-point numbers is in the fpu directory.

The target-i386 code that calls into those functions is in op_helper.c.

HTH,
-Nathan



Re: [Qemu-devel] [PATCH v2 1/3] target-ppc: simplify NaN propagation for vector functions

2011-04-20 Thread Nathan Froyd
On Wed, Apr 20, 2011 at 01:04:48PM +0100, Peter Maydell wrote:
 I need to add ARM support for fused multiply-accumulate (vfma,vfms),
 so perhaps in the long run it would be better to make them softfloat
 primitives? (they are after all in the new IEEE spec, so they're in
 softfloat's domain in some sense.) That would move the 'propagate one
 of 3 NaNs' logic into softfloat.

+1 to implementing fma in softfloat.

-Nathan



Re: [Qemu-devel] [PATCH 17/19] target-ppc: fix SPE comparison functions

2011-04-12 Thread Nathan Froyd
On Tue, Apr 12, 2011 at 11:59:29PM +0200, Aurelien Jarno wrote:
 Given that float32_*() functions are IEEE754 compliant, the efscmp*()
 functions are correctly implemented, while efstst*() are not. This
 patch reverse the implementation of this two groups of functions and
 fix the comments. It also use float32_eq() instead of float32_eq_quiet()
 as qNaNs should not be ignored.

Thanks for addressing this; the E500 emulation in QEMU is more like how
we wish the hardware acted, rather than how it actually acts. :)

It's late here, but I think this change:

 -static inline uint32_t efscmplt(uint32_t op1, uint32_t op2)
 +static inline uint32_t efststlt(uint32_t op1, uint32_t op2)
  {
 -/* XXX: TODO: test special values (NaN, infinites, ...) */
 +/* XXX: TODO: ignore special values (NaN, infinites, ...) */
  return efststlt(op1, op2);
  }

is not correct, as you've just turned this into an infinite (inlined!)
loop.  You'd want to change the efststlt call into an efscmplt call.
Similarly for efstst{gt,eq}.

-Nathan



[Qemu-devel] Re: [PATCH] target-sh4: get rid of CPU_{Float, Double}U

2011-04-11 Thread Nathan Froyd
On Sun, Apr 10, 2011 at 09:13:05PM +0200, Aurelien Jarno wrote:
 SH4 is always using softfloat, so it's possible to have helpers directly
 taking float32 or float64 value. This allow to get rid of conversions
 through CPU_{Float,Double}U.

Eh, I think this punning on i32/f32 and i64/f64 values is not healthy.
But Peter's already said that the floats-as-structs bit of softfloat is
broken, so maybe it's not worth trying to ensure floats-as-structs works
(or even making it the default, to discourage people from bit-twiddling
directly).

-Nathan



Re: [Qemu-devel] MIPS64 user mode emulation Patch

2011-03-30 Thread Nathan Froyd
On Sat, Mar 26, 2011 at 11:58:37AM +0500, Khansa Butt wrote:
 Subject: [PATCH] MIPS64 user mode emulation in QEMU
  This patch adds support for Cavium Network's
  Octeon 57XX user mode instructions.  Octeon
  57xx is based on MIPS64.  So this patch is
  the first MIPS64 User Mode Emulation in QEMU
  This is the team(Khansa Butt, Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed)
  work of HPCNL Lab at KICS-UET Lahore.

Thanks for doing this.  As already noted, this patch should be split
into at least two patches: one to add Octeon-specific instructions in
target-mips/ and one adding the necessary linux-user bits.

 +extern int TARGET_OCTEON;

I don't think a global like this is the right way to go.  Perhaps the
elfload.c code should set a flag in image_info , which can then be used
to set a flag in CPUMIPSState later on.

If we must use a global variable, it should be declared in
target-mips/cpu.h.

 @@ -2013,7 +2024,8 @@ void cpu_loop(CPUMIPSState *env)
   env-active_tc.gpr[5],
   env-active_tc.gpr[6],
   env-active_tc.gpr[7],
 - arg5, arg6/*, arg7, arg8*/);
 + env-active_tc.gpr[8],
 + env-active_tc.gpr[9]/*, arg7, arg8*/);
  }
  if (ret == -TARGET_QEMU_ESIGRETURN) {
  /* Returning from a successful sigreturn syscall.

This change breaks O32 binaries; it needs to be done in a different way.

 diff --git a/linux-user/syscall.c b/linux-user/syscall.c
 index 499c4d7..47fef05 100644
 --- a/linux-user/syscall.c
 +++ b/linux-user/syscall.c
 @@ -7195,6 +7195,8 @@ abi_long do_syscall(void *cpu_env, int num, abi_long
 arg1,
  case TARGET_NR_set_thread_area:
  #if defined(TARGET_MIPS)
((CPUMIPSState *) cpu_env)-tls_value = arg1;
 +   /*tls entry is moved to k0 so that this can be used later*/
 +  ((CPUMIPSState *) cpu_env)-active_tc.gpr[26] = arg1;
ret = 0;
break;
  #elif defined(TARGET_CRIS)

I believe this is only correct for Octeon binaries; it's not how the
rest of the MIPS world works.  It therefore needs to be conditional on
Octeon-ness.

 --- a/target-mips/cpu.h
 +++ b/target-mips/cpu.h
 @@ -140,6 +140,20 @@ typedef struct mips_def_t mips_def_t;
  #define MIPS_FPU_MAX 1
  #define MIPS_DSP_ACC 4
 
 +typedef struct cavium_mul cavium_mul;
 +struct cavium_mul {
 + target_ulong MPL0;
 + target_ulong MPL1;
 + target_ulong MPL2;
 + target_ulong P0;
 + target_ulong P1;
 + target_ulong P2;
 +};
 +typedef struct cvmctl_register cvmctl_register;
 +struct cvmctl_register {
 + target_ulong cvmctl;
 +};

The indentation here needs to be fixed.  I don't think there's any
reason why these need to be defined outside TCState, either.

 diff --git a/target-mips/translate.c b/target-mips/translate.c
 index cce77be..9c3d772 100644
 --- a/target-mips/translate.c
 +++ b/target-mips/translate.c
 @@ -36,6 +36,15 @@
  #define GEN_HELPER 1
  #include helper.h
 
 +int TARGET_OCTEON;
 +#if defined(TARGET_MIPS64)
 +/*Macros for setting values of cvmctl registers*/
 +#define FUSE_START_BIT(cvmctl)(cvmctl | 0x8000)
 +#define KASUMI(cvmctl)(cvmctl | 0x2000)
 +#define IPPCI(cvmctl)(cvmctl | 0x380)
 +#define IPTI(cvmctl)(cvmctl | 0x70)
 +#endif

Please follow existing style; spaces between the comment and comment
markers (many examples in translate.c, not just here) and spaces between
the macro argument list and definition.

 @@ -779,7 +818,9 @@ static inline void gen_op_addr_add (DisasContext *ctx,
 TCGv ret, TCGv arg0, TCGv
 See the MIPS64 PRA manual, section 4.10. */
  if (((ctx-hflags  MIPS_HFLAG_KSU) == MIPS_HFLAG_UM) 
  !(ctx-hflags  MIPS_HFLAG_UX)) {
 -tcg_gen_ext32s_i64(ret, ret);
 +/*This function sign extend 32 bit value to 64 bit, was causing
 error
 +  when ld instruction came.Thats why it is commmented out*/
 +   /* tcg_gen_ext32s_i64(ret, ret);*/
  }
  #endif
  }

Um, no.  If you needed to comment this out, you have a bug someplace
else.  Don't paper over the bug here.

 +case OPC_VMULU:
 +case OPC_V3MULU:

These two are large enough that they should be done as out-of-line
helpers.

Also, since all these new instructions are Octeon-specific, there should
be checks emitted to ensure that they produce appropriate errors when
non-Octeon hardware is being simulated, similar in style to
check_mips_64.

  /* Arithmetic */
  static void gen_arith (CPUState *env, DisasContext *ctx, uint32_t opc,
 int rd, int rs, int rt)
  {
  const char *opn = arith;
 
 +target_ulong mask = 0xFF;

I don't think it's really necessary to have this, but if you feel it's
necessary, please move the declaration closer to the point of use.

 +#if defined(TARGET_MIPS64)
 +static void gen_seqsne (DisasContext *ctx, uint32_t opc,
 +int rd, int rs, int rt)
 +{
 +const char 

Re: [Qemu-devel] [PATCH 1/7] target-arm: Make Neon helper routines use correct FP status

2011-03-30 Thread Nathan Froyd
On Mon, Mar 28, 2011 at 03:15:08PM +0100, Peter Maydell wrote:
 On 14 March 2011 05:35, Nathan Froyd froy...@codesourcery.com wrote:
  Oh, right.  I am ambivalent as to whether passing env to such functions
  is the right thing to do or not.
 
 So did this amount to a request for a change to this patchset,
 or are you happy to let it pass?

I am happy to let it pass.

-Nathan



Re: [Qemu-devel] [PATCH 10/17] s390x: Adjust GDB stub

2011-03-25 Thread Nathan Froyd
On Thu, Mar 24, 2011 at 04:58:46PM +0100, Alexander Graf wrote:
 We have successfully lazilized cc computation, so we need to manually
 trigger its calculation when gdb wants to fetch it. We also changed the
 variable name, so writing it writes into a different field now.

Wouldn't you want to:

a) change the variable name in the earlier commit and just do the
   manual triggering in this commit, so as not to break bisect; or
b) combine this change with the previous lazification?

-Nathan



Re: [Qemu-devel] [PATCH] target-arm/helper.c: For float-int conversion helpers pass ints as ints

2011-03-21 Thread Nathan Froyd
On Mon, Mar 14, 2011 at 05:23:11PM +, Peter Maydell wrote:
 Correct the argument and return types for the float-int conversion helper
 functions so that integer arguments and return values are declared as
 uint32_t/uint64_t, not float32/float64. This allows us to remove the
 hand-rolled functions which were doing bitwise copies between the types
 via unions.

Reviewed-by: Nathan Froyd froy...@codesourcery.com

I like the direction this patch goes; you aren't by any chance going to
convert the passing/returning of float* to their appropriate int* types
too, are you?

-Nathan



Re: [Qemu-devel] [PATCH] target-arm/helper.c: For float-int conversion helpers pass ints as ints

2011-03-21 Thread Nathan Froyd
On Mon, Mar 21, 2011 at 02:04:31PM +, Peter Maydell wrote:
 On 21 March 2011 13:48, Nathan Froyd froy...@codesourcery.com wrote:
  I like the direction this patch goes; you aren't by any chance going to
  convert the passing/returning of float* to their appropriate int* types
  too, are you?
 
 Nope -- I think that where we're passing or returning an actual
 IEEE single/double to a helper function float* is a better type
 than uint32_t: it gives information about what the helper's argument
 semantically is, and it means we don't have every helper that takes
 or returns a float have to include ugly calls to the boxing/unboxing
 macros.

I'm just concerned about what would happen if we turned on softfloat's
float types are structure types bit; I'm pretty sure everything would
break horribly on targets that don't pass small structures in
registers.  Admittedly, several targets would be broken by doing so, so
it's not particularly urgent.

-Nathan



Re: [Qemu-devel] [PATCH] [PPC] Add support for 6 SPE instructions (evmra, evmwsmi{a{a}}, evmwumi{a{a}})

2011-03-21 Thread Nathan Froyd
On Wed, Mar 16, 2011 at 11:21:22AM +0100, Fabien Chouteau wrote:
 Signed-off-by: Fabien Chouteau chout...@adacore.com

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 1/7] target-arm: Make Neon helper routines use correct FP status

2011-03-13 Thread Nathan Froyd
On Fri, Mar 11, 2011 at 10:31:31PM +, Peter Maydell wrote:
 On 11 March 2011 18:30, Nathan Froyd froy...@codesourcery.com wrote:
  Is there a reason that you don't simply use the global env rather than
  passing in an extra parameter everywhere?
 
 Just following the pattern that generally seems to be used by
 most helper functions, ie if you want the CPU env pass it in
 as a parameter. As far as I know, you can't use the global
 env unless you're in op_helper.c because that's the only
 source file compiled with the right flags.

Oh, right.  I am ambivalent as to whether passing env to such functions
is the right thing to do or not.

  I wonder if it'd be worthwhile just to merge these functions into
  op_helper.c, since we have a proper FP status for NEON bits now.
 
 Why move these and not (for instance) the VFP helpers
 in helper.c which use the CPU env for more or less the
 same reasons?

No reason, other than that I wasn't thinking about the VFP helpers. :)

-Nathan



Re: [Qemu-devel] [PATCH 6/7] softfloat: Add float*_min() and float*_max() functions

2011-03-11 Thread Nathan Froyd
On Fri, Mar 11, 2011 at 06:12:25PM +, Peter Maydell wrote:
 Add min and max operations to softfloat. This allows us to implement
 propagation of NaNs and handling of negative zero correctly (unlike
 the approach of having target helper routines return one of the operands
 based on the result of a comparison op).

Are these useful anyplace beside ARM?  i.e. do they implement the
correct AltiVec/VSX/SSE* (any others?) semantics?

-Nathan



Re: [Qemu-devel] [PATCH 2/7] target-arm/neon_helper.c: Use make_float32/float32_val macros

2011-03-11 Thread Nathan Froyd
On Fri, Mar 11, 2011 at 06:12:21PM +, Peter Maydell wrote:
 Use the softfloat make_float32 and float32_val macros to convert between
 softfloat's float32 type and raw uint32_t types, rather than private
 conversion functions.

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 1/7] target-arm: Make Neon helper routines use correct FP status

2011-03-11 Thread Nathan Froyd
On Fri, Mar 11, 2011 at 06:12:20PM +, Peter Maydell wrote:
 Make the Neon helper routines use the correct FP status from
 the CPUEnv rather than using a dummy static one. This means
 they will correctly handle denormals and NaNs and will set
 FPSCR exception bits properly.

Is there a reason that you don't simply use the global env rather than
passing in an extra parameter everywhere?  I wonder if it'd be
worthwhile just to merge these functions into op_helper.c, since we have
a proper FP status for NEON bits now.

-Nathan



Re: [Qemu-devel] [PATCH] linux-user: bigger default stack

2011-03-03 Thread Nathan Froyd
On Thu, Mar 03, 2011 at 05:37:37PM +0200, Riku Voipio wrote:
 PTHREAD_STACK_MIN (16KB) is somewhat inadequate for a new stack. follow
 the pthread_create defaults, ie setting to RLIMIT_STACK or if unlimited
 to 2MB.

For what sort oof cases is it inadequate?  This stack is just for QEMU's
usage and QEMU shouldn't be using very much.  The target thread could
use quite a bit of course, but that's handled elsewhere.

-Nathan



Re: [Qemu-devel] [PATCH] linux-user: bigger default stack

2011-03-03 Thread Nathan Froyd
On Thu, Mar 03, 2011 at 06:15:49PM +0200, Riku Voipio wrote:
 On Thu, Mar 03, 2011 at 07:46:27AM -0800, Nathan Froyd wrote:
  On Thu, Mar 03, 2011 at 05:37:37PM +0200, Riku Voipio wrote:
   PTHREAD_STACK_MIN (16KB) is somewhat inadequate for a new stack. follow
   the pthread_create defaults, ie setting to RLIMIT_STACK or if unlimited
   to 2MB.
  
  For what sort oof cases is it inadequate?  This stack is just for QEMU's
  usage and QEMU shouldn't be using very much.  
 
 QEMU linux-user calls glibc functions which, while usually very conservative
 with memory usage, are not guaranteed not take less than 10KB (at do_syscall
 we are already around 5 functions deep).

Bleh.  OK, so it needs to be increased.  Could we get by with somewhat
less (256K?), to try and maximize the number of threads we can
potentially run?  Maybe it doesn't matter (people creating thousands of
simultaneous threads inside QEMU have other problems...), but not
gratuitously wasting memory would be good.

-Nathan



Re: [Qemu-devel] [PATCH 1/2] target-arm: Move Neon VUZP to a helper function

2011-02-11 Thread Nathan Froyd
On Fri, Feb 11, 2011 at 05:12:32PM +, Peter Maydell wrote:
 On 11 February 2011 17:03, Nathan Froyd froy...@codesourcery.com wrote:
  I do think the preferred way would be to extract rd, rm, size, and Q
  up-front, rather than having the helper twiddle instruction bits.
 
 OK. You're happy to still have the helper do the reading and
 writing of env-vfp.regs[] directly, though?

I think you can make a case either way, but you're passing enough values
already that accessing env-vfp.regs directly in the helper seems
reasonable.

-Nathan



Re: [Qemu-devel] [PATCH 1/2] target-arm: Move Neon VUZP to a helper function

2011-02-11 Thread Nathan Froyd
On Fri, Feb 11, 2011 at 04:53:30PM +, Peter Maydell wrote:
 On 11 February 2011 16:14, Peter Maydell peter.mayd...@linaro.org wrote:
  +void HELPER(neon_unzip)(CPUState *env, uint32_t insn)
  +{
  +    int rd = ((insn  18)  0x10) | ((insn  12)  0x0f);
  +    int rm = ((insn  1)  0x10) | (insn  0x0f);
  +    int size = (insn  18)  3;
  +    if (insn  0x40) { /* Q */
  +        uint64_t zm0 = float64_val(env-vfp.regs[rm]);
  +        uint64_t zm1 = float64_val(env-vfp.regs[rm + 1]);
  +        uint64_t zd0 = float64_val(env-vfp.regs[rd]);
  +        uint64_t zd1 = float64_val(env-vfp.regs[rd + 1]);
 
 I can rework these patches if people don't like the way this is
 effectively doing decoding in a helper function, incidentally,
 although I'm not convinced it would end up any nicer overall.

I do think the preferred way would be to extract rd, rm, size, and Q
up-front, rather than having the helper twiddle instruction bits.

-Nathan



[Qemu-devel] Re: [PATCH 2/2] target-ppc: fix wrong NaN tests

2011-01-13 Thread Nathan Froyd
On Wed, Jan 12, 2011 at 07:42:48PM +0100, Aurelien Jarno wrote:
 Some tests in FPU emulation code were wrongly using float64_is_nan()
 before commit 185698715dfb18c82ad2a5dbc169908602d43e81, and wrongly
 using float64_is_quiet_nan() after. Fix them by using float64_is_any_nan()
 instead.
 
 Cc: Alexander Graf ag...@suse.de
 Cc: Peter Maydell peter.mayd...@linaro.org
 Cc: Nathan Froyd froy...@codesourcery.com
 Signed-off-by: Aurelien Jarno aurel...@aurel32.net

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



[Qemu-devel] Re: [PATCH v2 1/2] target-ppc: fix sNaN propagation

2011-01-13 Thread Nathan Froyd
On Wed, Jan 12, 2011 at 07:42:47PM +0100, Aurelien Jarno wrote:
 The current FPU code returns 0.0 if one of the operand is a
 signaling NaN and the VXSNAN exception is disabled.
 
 fload_invalid_op_excp() doesn't return a qNaN in case of a VXSNAN
 exception as the operand should be propagated instead of a new
 qNaN to be generated. Fix that by calling fload_invalid_op_excp()
 only for the exception generation (if enabled), and use the softfloat
 code to correctly compute the result.
 
 Cc: Alexander Graf ag...@suse.de
 Cc: Peter Maydell peter.mayd...@linaro.org
 Cc: Nathan Froyd froy...@codesourcery.com
 Signed-off-by: Aurelien Jarno aurel...@aurel32.net

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 1/9] target-sh4: switch sh4 to softfloat

2011-01-11 Thread Nathan Froyd
On Tue, Jan 11, 2011 at 10:01:30PM +0100, Aurelien Jarno wrote:
  case $target_arch2 in
 -  
 alpha|arm|armeb|m68k|microblaze|mips|mipsel|mipsn32|mipsn32el|mips64|mips64el|ppc|ppc64|ppc64abi32|ppcemb|s390x|sparc|sparc64|sparc32plus)
 +  
 alpha|arm|armeb|m68k|microblaze|mips|mipsel|mipsn32|mipsn32el|mips64|mips64el|ppc|ppc64|ppc64abi32|ppcemb|s390x|sh4|sh4eb|sparc|sparc64|sparc32plus)
  echo CONFIG_SOFTFLOAT=y  $config_target_mak
  ;;
*)

This is obvious, I think...but it's also a little ridiculous.  Why not
make everything use softfloat and dispense with this?  How much work
would it be on the x86 side?

-Nathan



Re: [Qemu-devel] [PATCH 1/6] softfloat: remove HPPA specific code

2011-01-06 Thread Nathan Froyd
On Thu, Jan 06, 2011 at 03:34:38PM +, Peter Maydell wrote:
 Similarly I'm dubious about uses in helper_fsel, helper_fcmpu
 and helper_fcmpo, efsctsi, efsctui, efsctsiz, efsctuiz, efsctsf,
 efsctuf and all the helper_efd* functions. I haven't actually
 checked them all, but for instance efdctsi in the Power ISA
 2.03 spec says NaNs are converted as though they were zero,
 but qemu's code says:
 /* NaN are not treated the same way IEEE 754 does */
 if (unlikely(float64_is_quiet_nan(u.d)))
 return 0;
 
 which is not going to do the right thing for signaling NaNs.

I think you are correct about fsel, fcmpu, and fcmpo.

The E500 FP instructions are broken for various corner cases (and there
are a lot of them, because E500 is screwy).  I've been meaning to go
through and fix them up, but haven't taken the time to do so.

-Nathan



Re: [Qemu-devel] [PATCH 6/6] target-ppc: Implement correct NaN propagation rules

2011-01-05 Thread Nathan Froyd
On Mon, Jan 03, 2011 at 03:34:33PM +0100, Aurelien Jarno wrote:
 Implement the correct NaN propagation rules for ARM targets by
 providing an appropriate pickNaN function.
 
 Also fix the #ifdef tests for default NaN definition, the correct name
 is TARGET_PPC instead of TARGET_POWERPC.

Reviewed-by: Nathan Froyd froy...@codesourcery.com

 + * A signaling NaN is always quietened before returning it.

I think silenced is more natural here, but I can understand preferring
quiet in keeping with NaN terminology.

-Nathan



Re: [Qemu-devel] [PATCH] target-ppc: use float32_is_any_nan()

2011-01-05 Thread Nathan Froyd
On Sun, Jan 02, 2011 at 01:06:49PM +0100, Aurelien Jarno wrote:
 Use the new function float32_is_any_nan() instead of
 float32_is_quiet_nan() || float32_is_signaling_nan().
 
 Cc: Alexander Graf ag...@suse.de
 Signed-off-by: Aurelien Jarno aurel...@aurel32.net

Reviewed-by: Nathan Froyd froy...@codesourcery.com

 @@ -1938,7 +1938,7 @@ target_ulong helper_dlmzb (target_ulong high, 
 target_ulong low, uint32_t update_
  /* If X is a NaN, store the corresponding QNaN into RESULT.  Otherwise,
   * execute the following block.  */
  #define DO_HANDLE_NAN(result, x)\
 -if (float32_is_quiet_nan(x) || float32_is_signaling_nan(x)) { \
 +if (float32_is_any_nan(x)) {\
  CPU_FloatU __f; \
  __f.f = x;  \
  __f.l = __f.l | (1  22);  /* Set QNaN bit. */ \

If you were looking for other cleanups, this could stand a
maybe_silence_nan.

-Nathan



Re: [Qemu-devel] NPTL support

2010-12-21 Thread Nathan Froyd
On Mon, Dec 20, 2010 at 10:17:50PM -0800, maheen butt wrote:
 hi I 'm working with fedora core 13(64 bit) x86_64 platform. I
 configured QEMU with --enable-nptl switch but I'm not able to run
 programs containing POSIX threads or fork system call. I run this
 commandqemu-x86_64 thread it gives system call errorand qemu-x86_64
 forkfno child process createdwhat is reason behind it? is nptl support
 is in its progressive mode or it is not for x86_64.

Nobody's written the x86/x86_64-specific NPTL bits yet.

-Nathan



Re: [Qemu-devel] [PATCH V2] softfloat: Rename float*_is_nan() functions to float*_is_quiet_nan()

2010-12-18 Thread Nathan Froyd
On Sat, Dec 18, 2010 at 10:39:05AM +, Peter Maydell wrote:
 On 18 December 2010 02:30, Nathan Froyd froy...@codesourcery.com wrote:
  So adding _t suffixes in appropriate places should be a no-op, except
  for uint16/int16--and those types are never used.
 
 Eh? If you comment out the int16 typedef you'll find softfloat.c
 doesn't compile because of all the places it's used... (uint16
 isn't used, though.)

Sorry about that, I fail at grepping late at night. =/

-Nathan



Re: [Qemu-devel] [PATCH V2] softfloat: Rename float*_is_nan() functions to float*_is_quiet_nan()

2010-12-17 Thread Nathan Froyd
On Fri, Dec 17, 2010 at 11:32:03PM +, Peter Maydell wrote:
 On 17 December 2010 17:54, Andreas Färber andreas.faer...@web.de wrote:
  My patch does not touch the bits* types. I didn't notice any problem there.
 
  I replaced int32 by int32_t, int64 by int64_t etc. No sane code puts more
  than 32 bits into an int32 variable, and my guests on OSX/ppc64 host still
  appeared to work. I don't have arm guests though so please check on your
  side.
 
 Hrm. That introduces potential semantic changes, so I'm a bit wary
 of it (and my test suite is not currently comprehensive enough to be
 sure of covering all of softfloat)... I'd be happier if we just renamed
 the int32  friends to some other non-clashing name, if all we're
 trying to solve is a name clash issue.

I wouldn't be too worried:

typedef uint8_t flag;
typedef uint8_t uint8;
typedef int8_t int8;
typedef int uint16;
typedef int int16;
typedef unsigned int uint32;
typedef signed int int32;
typedef uint64_t uint64;
typedef int64_t int64;

So adding _t suffixes in appropriate places should be a no-op, except
for uint16/int16--and those types are never used.

-Nathan



[Qemu-devel] Re: arm: fix ldrexd/strexd

2010-12-07 Thread Nathan Froyd
On Thu, Nov 04, 2010 at 07:47:45AM -, Peter Maydell wrote:
 Correct ldrexd and strexd code to always read and write the
 high word of the 64-bit value from addr+4.
 Also make ldrexd and strexd agree that for a 64 bit value the
 address in env-exclusive_addr is that of the low word.
 
 This fixes the issues reported in
 https://bugs.launchpad.net/qemu/+bug/670883
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 1/8] ARM: Fix decoding of VFP forms of VCVT between float and int/fixed

2010-12-06 Thread Nathan Froyd
On Thu, Nov 11, 2010 at 06:23:55PM +, Peter Maydell wrote:
 Correct the decoding of source and destination registers
 for the VFP forms of the VCVT instructions which convert
 between floating point and integer or fixed-point.
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

I don't know how good QEMU's framework is, but it'd be nice to have your
testing code checked into the tree, in case anybody decides to do major
surgery on the ARM backend.

-Nathan



Re: [Qemu-devel] [PATCH 1/8] ARM: Fix decoding of VFP forms of VCVT between float and int/fixed

2010-12-06 Thread Nathan Froyd
On Mon, Dec 06, 2010 at 04:48:25PM +, Peter Maydell wrote:
 I'm not sure how well it would fit into being committed to qemu (yet):
 it works as a program where you run half of it on real ARM hardware
 and the other half under qemu (or valgrind) and it compares register
 results after executing instructions by looking at the sigcontext struct
 in a signal handler. Plus there's a perl script to generate random
 instruction set sequences to feed the test program. It could be made
 more automated and independent of having a reference bit of hardware
 but I haven't got round to that yet. (Also since it has utility outside of
 just testing qemu I'm not sure if it really belongs in the qemu repo.)

That does sound a little heavyweight.  Scripting gdb is also a possibility.

FWIW--and this is not particularly conducive to random insn
sequences--the approach taken when doing the AltiVec bits was to have
code that looked like:

  for each insn:
 for a suitable set of inputs:
setup interesting registers (status control registers etc.)
load inputs into registers
execute
record interesting post conditions in file.out

You'd get an output file from real hardware and an output file from the
simulator and then compare them, fixing differences as you go.  The
actual code included bits to compare the files as well as doing the
generation.

The output files can be somewhat large, but I'm sure clever engineering
could be applied to make them smaller.

Of course, the *real* problems are in undefined-behavior land. :)

-Nathan



Re: [Qemu-devel] [PATCH 04/10] softfloat: Add float*_is_any_nan() functions

2010-12-06 Thread Nathan Froyd
On Mon, Dec 06, 2010 at 05:00:05PM +, Peter Maydell wrote:
 Add float*_is_any_nan() functions which return true if the argument
 is a NaN of any kind (quiet or signalling).
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 06/10] softfloat: Add float*_maybe_silence_nan() functions

2010-12-06 Thread Nathan Froyd
On Mon, Dec 06, 2010 at 05:00:07PM +, Peter Maydell wrote:
 Add functions float*_maybe_silence_nan() which ensure that a
 value is not a signaling NaN by turning it into a quiet NaN.
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 07/10] ARM: Return correct result for single-double conversion of NaN

2010-12-06 Thread Nathan Froyd
On Mon, Dec 06, 2010 at 05:00:08PM +, Peter Maydell wrote:
 The ARM ARM defines that if the input to a single-double conversion
 is a NaN then the output is always forced to be a quiet NaN by setting
 the most significant bit of the fraction part.
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 05/10] ARM: Return correct result for float-to-integer conversion of NaN

2010-12-06 Thread Nathan Froyd
On Mon, Dec 06, 2010 at 05:00:06PM +, Peter Maydell wrote:
 The ARM architecture mandates that converting a NaN value to
 integer gives zero (if Invalid Operation FP exceptions are
 not being trapped). This isn't the behaviour of the SoftFloat
 library, so NaNs must be special-cased.
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 08/12] ARM: Return correct result for single-double conversion of NaN

2010-12-01 Thread Nathan Froyd
On Tue, Nov 30, 2010 at 11:15:56AM +, Peter Maydell wrote:
 On 29 November 2010 19:54, Nathan Froyd froy...@codesourcery.com wrote:
  Yes, this is ugly.  Are you up for running:
 
   perl -p -i -e 's/float(\d+)_is_nan/float\1_is_quiet_nan/g' target-*/*.c
 
  (and also carefully in fpu/*) or similar and moving the bit-twiddling
  float_is_nan into fpu/?
 
 I'm just compiling this up now. While I was eyeballing the results of
 the substitution, I noticed that there are some places which are almost
 certainly bugs introduced by other people not noticing that float*_is_nan()
 doesn't do what it says on the tin. Three at random:
 
 In target-ppc/op_helper.c:helper_compute_fprf():
 
 In target-alpha/op_helper.c:helper_cmptun():
 
 In target-m68k/helper.c:sub_cmp_f64:
 
 judging from the comments the author expected is_nan() to
 be true for all NaNs.
 
 I'm not sure what we should do about these -- they look wrong
 but I don't have any of the setup to actually test whether they're
 wrong.

RTH (CC'd) is the expert on the Alpha bits.  The PPC one is obviously
wrong.  I can test the m68k one.

In any event, I think the safest course is to do the simple renaming; we
can clean up broken bits after the fact.

-Nathan



Re: [Qemu-devel] [PATCH 08/12] ARM: Return correct result for single-double conversion of NaN

2010-12-01 Thread Nathan Froyd
On Wed, Dec 01, 2010 at 09:52:13AM -0800, Richard Henderson wrote:
 I think I've lost the thread a bit -- is the proposal to
 replace the existing float*_is_nan with _is_quiet_nan and
 invent a new function that returns true for both Q+S?  That
 at least would be monotonic improvement for Alpha, although
 as noted above not 100% correct.

Yes, that's the plan.  As (planned to be) implemented, doing this should
not change anything:

1. s/float*_is_nan/float*_is_quiet_nan/g
2. write new float*_is_nan
3. use new float*_is_nan in new code
4. replace bogus float*_is_quiet_nan uses with new function

-Nathan



[Qemu-devel] Re: [PATCH] softfloat: Rename float*_is_nan() functions to float*_is_quiet_nan()

2010-12-01 Thread Nathan Froyd
On Tue, Nov 30, 2010 at 11:25:33AM +, Peter Maydell wrote:
 The softfloat functions float*_is_nan() were badly misnamed,
 because they return true only for quiet NaNs, not for all NaNs.
 Rename them to float*_is_quiet_nan() to more accurately reflect
 what they do.
 
 This change was produced by:
  perl -p -i -e 's/_is_nan/_is_quiet_nan/g' $(git grep -l is_nan)
 (with the results manually checked.)
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

Thank you for doing this.

-Nathan



Re: Windows host support [was: Re: [Qemu-devel] CFP: 1st International QEMU Users Forum]

2010-11-29 Thread Nathan Froyd
On Mon, Nov 29, 2010 at 08:34:28AM -0600, Anthony Liguori wrote:
 On 11/28/2010 04:56 AM, Alexander Graf wrote:
 On 28.11.2010, at 01:17, Nathan Froyd wrote:
 We (CodeSourcery) are very interested in Windows host support.  (We
 distribute QEMU with our commerical development products for
 ARM/PowerPC/MIPS/SH/ColdFire/x86.)  Unfortunately, we've mostly been
 backporting patches lately and haven't done a full merge from upstream
 in some time, so we haven't noticed any potential breakage.  If somebody
 wanted to point out to me what the (potential) Windows issues are, we
 could take a look.
  
 Redirecting you to Anthony here for the specifics. The main problem
 is that we don't have anyone who takes the lead on Windows
 support. _If_ something breaks of _if_ we need someone to take over
 the windows specific parts, there's this huge gap.

 Uh, Windows system simulation has never worked reliably.  It doesn't  
 even have proper AIO support.

 If someone is building a product based on it, I'm amazed.

Well, technically we only support QEMU as a simple instruction set
simulator in our products, and the bits present work well enough for
that.  (It is of course possible those bits have been broken in the time
since our last upstream merge.)  If you want to venture into system
simulation and it breaks, then you get to keep both pieces.

It would, however, be better to eventually support full system
simulation, and making Windows hosts work right would be a necessary
precondition to that.

-Nathan



Re: [Qemu-devel] CFP: 1st International QEMU Users Forum

2010-11-29 Thread Nathan Froyd
On Mon, Nov 29, 2010 at 02:58:57PM +0100, Alexander Graf wrote:
  Nathan Froyd a écrit :
  I'm sorry, what are the both talks you refer to above?  Are you
  proposing an additional talk alongside your (Frédéric's) existing talk?
  
   No! I am very happy that you take over the introduction of the emulation.
   Indeed I was thinking that Alexander could be willing to introduce i.e. 
  device
   emulation (he'll tell us).
  
   Can you send a title of yours ? Or shall we keep the same one, as it
   will be along these lines ?
 
 I'm not sure I fully understand :). Peter is your man when it comes to
 ARM. I can give a general overview on qemu and know my way around most
 subsystems, but I'm not exactly strong in ARM :).

I am confused too.  Is Alexander giving the talk, or am I, or some
combination of Alexander/Peter/me?  Or were you (Frédéric) thinking that
Alexander should give a second, separate talk?

 Nathan and Peter, are you two going anyways, despite giving a talk or not?

I'm certainly going to try, yes.

-Nathan



Re: [Qemu-devel] [PATCH 06/12] ARM: Fix sense of to_integer bit in Neon VCVT float/int conversion

2010-11-29 Thread Nathan Froyd
On Tue, Nov 23, 2010 at 06:53:45PM +, Peter Maydell wrote:
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 07/12] ARM: Return correct result for float-to-integer conversion of NaN

2010-11-29 Thread Nathan Froyd
On Tue, Nov 23, 2010 at 06:53:46PM +, Peter Maydell wrote:
 The ARM architecture mandates that converting a NaN value to
 integer gives zero (if Invalid Operation FP exceptions are
 not being trapped). This isn't the behaviour of the SoftFloat
 library, so NaNs must be special-cased.
 
 +/* Helper routines to identify NaNs. Note that softfloat's
 + * floatxx_is_nan() actually only returns true for quiet NaNs.
 + * A NaN has an exponent field all 1s and a fraction field
 + * anything except all zeros. Conveniently we can detect this
 + * by masking out the sign bit and doing an unsigned comparison.
 + */
 +static int float32_is_any_nan(float32 x)
 +{
 +return ((float32_val(x)  ~(1  31))  0x7f80UL);
 +}
 +
 +static int float64_is_any_nan(float64 x)
 +{
 +return ((float64_val(x)  ~(1ULL  63))  0x7ff0ULL);
 +}

Why not just use:

static int float32_is_any_nan(float32 x)
{
  return float32_is_nan(x) || float32_is_signaling_nan(x);
}

and likewise for the 64-bit case?

-Nathan



Re: [Qemu-devel] [PATCH 07/12] ARM: Return correct result for float-to-integer conversion of NaN

2010-11-29 Thread Nathan Froyd
On Mon, Nov 29, 2010 at 04:49:24PM +, Peter Maydell wrote:
 On 29 November 2010 16:38, Nathan Froyd froy...@codesourcery.com wrote:
  Why not just use:
 
  static int float32_is_any_nan(float32 x)
  {
   return float32_is_nan(x) || float32_is_signaling_nan(x);
  }
 
  and likewise for the 64-bit case?
 
 That was what my first-pass patches did, but I
 rewrote them this way because it seemed more
 straightforward to just test for is this a NaN rather
 than calling two other functions which each test for
 is this some subset of NaN space.
 
 I suppose you could argue that softfloat ought to
 have _is_nan() [with the semantics you'd expect
 from the function name, not the ones it currently has!],
 _is_signalling_nan() and _is_quiet_nan() functions
 built in, but it doesn't...

I agree that the functions are poorly named.  I think it'd be better to
leave the bit-twiddling to the softfloat bits, though.  There's
precedent for the more verbose approach in other backends, too.

-Nathan



Re: [Qemu-devel] [PATCH 02/12] target-arm: Fix mixup in decoding of saturating add and sub

2010-11-29 Thread Nathan Froyd
On Tue, Nov 23, 2010 at 06:53:41PM +, Peter Maydell wrote:
 From: Johan Bengtsson teofrast...@gmail.com
 
 The thumb2 decoder contained a mixup between the bit controlling
 doubling and the bit controlling if the operation was an add or a sub.
 
 Signed-off-by: Johan Bengtsson teofrast...@gmail.com
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 09/12] ARM: Ignore top 16 bits when doing VCVT from 16 bit fixed point

2010-11-29 Thread Nathan Froyd
On Tue, Nov 23, 2010 at 06:53:48PM +, Peter Maydell wrote:
 VCVT of 16 bit fixed point to float should ignore the top 16 bits
 of the source register. Cast to int16_t and friends rather than
 int16 -- the former is guaranteed exactly 16 bits wide where the
 latter is merely at least 16 bits wide (and so is usually 32 bits).
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 08/12] ARM: Return correct result for single-double conversion of NaN

2010-11-29 Thread Nathan Froyd
On Tue, Nov 23, 2010 at 06:53:47PM +, Peter Maydell wrote:
 The ARM ARM defines that if the input to a single-double conversion
 is a NaN then the output is always forced to be a quiet NaN by setting
 the most significant bit of the fraction part.
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org
 
 @@ -2529,12 +2529,26 @@ float32 VFP_HELPER(tosiz, d)(float64 x, CPUState *env)
  /* floating point conversion */
  float64 VFP_HELPER(fcvtd, s)(float32 x, CPUState *env)
  {
 -return float32_to_float64(x, env-vfp.fp_status);
 +float64 r = float32_to_float64(x, env-vfp.fp_status);
 +/* ARM requires that S-D conversion of any kind of NaN generates
 + * a quiet NaN by forcing the most significant frac bit to 1.
 + */
 +if (float64_is_signaling_nan(r)) {
 +return make_float64(float64_val(r) | (1LL  51));
 +}
 +return r;
  }

As with other NaN-handling patches, I don't think the bit-twiddling here
is a good idea.  Having a float*_maybe_silence_nan function in softfloat
would be a better approach.

-Nathan



Re: [Qemu-devel] [PATCH 05/12] ARM: Fix decoding of Neon forms of VCVT between float and fixed point

2010-11-29 Thread Nathan Froyd
On Tue, Nov 23, 2010 at 06:53:44PM +, Peter Maydell wrote:
 Fix errors in the decoding of the Neon forms of fixed-point VCVT:
  * fixed-point VCVT is op 14 and 15, not 15 and 16
  * the fbits immediate field was being misinterpreted
  * the sense of the to_fixed bit was inverted
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 03/12] target-arm: Handle 'smc' as an undefined instruction

2010-11-29 Thread Nathan Froyd
On Tue, Nov 23, 2010 at 06:53:42PM +, Peter Maydell wrote:
 From: Adam Lackorzynski a...@os.inf.tu-dresden.de
 
 Refine check on bkpt so that smc and undefined instruction encodings are
 handled as an undefined instruction and trap.
 
 Signed-off-by: Adam Lackorzynski a...@os.inf.tu-dresden.de
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 01/12] target-arm: Add support for PKHxx in thumb2

2010-11-29 Thread Nathan Froyd
On Tue, Nov 23, 2010 at 06:53:40PM +, Peter Maydell wrote:
 From: Johan Bengtsson teofrast...@gmail.com
 
 The PKHxx instructions were not recognized by the thumb2 decoder. The
 solution provided in this changeset is identical to the arm-mode
 implementation.
 
 Signed-off-by: Johan Bengtsson teofrast...@gmail.com
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 10/12] softfloat: Add float/double to 16 bit integer conversion functions

2010-11-29 Thread Nathan Froyd
On Tue, Nov 23, 2010 at 06:53:49PM +, Peter Maydell wrote:
 The ARM architecture needs float/double to 16 bit integer conversions.
 (The 32 bit versions aren't sufficient because of the requirement
 to saturate at 16 bit MAXINT/MININT and to get the exception bits right.)
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 11/12] ARM: Implement VCVT to 16 bit integer using new softfloat routines

2010-11-29 Thread Nathan Froyd
On Tue, Nov 23, 2010 at 06:53:50PM +, Peter Maydell wrote:
 Use the softfloat conversion routines for conversion to 16 bit
 integers, because just casting to a 16 bit type truncates the
 value rather than saturating it at 16-bit MAXINT/MININT.
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 1/6] ARM: linux-user: Correct size of padding in target_ucontext_v2

2010-11-29 Thread Nathan Froyd
On Wed, Nov 24, 2010 at 03:20:03PM +, Peter Maydell wrote:
 The padding in the target_ucontext_v2 is defined by the size of
 the target's sigset_t type, not the host's. (This bug only causes
 problems when we start using the uc_regspace[] array to expose
 VFP registers to userspace signal handlers.)
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 2/6] ARM: Expose vfp_get_fpscr() and vfp_set_fpscr() to C code

2010-11-29 Thread Nathan Froyd
On Wed, Nov 24, 2010 at 03:20:04PM +, Peter Maydell wrote:
 Expose the vfp_get_fpscr() and vfp_set_fpscr() functions to C
 code as well as generated code, so we can use them to read and
 write the FPSCR when saving and restoring VFP registers across
 signal handlers in linux-user mode.
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 3/6] ARM: linux-user: Expose VFP registers to signal handlers

2010-11-29 Thread Nathan Froyd
On Wed, Nov 24, 2010 at 03:20:05PM +, Peter Maydell wrote:
 For ARM linux-user mode signal handlers, fill in the ucontext with
 VFP register contents in the same way that the kernel does. We only
 do this for v2 format sigframe (2.6.12 and above); this is actually
 bug-for-bug compatible with the older kernels, which don't save and
 restore VFP registers either.
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 4/6] ARM: linux-user: Restore VFP state from ucontext on sigreturn

2010-11-29 Thread Nathan Froyd
On Wed, Nov 24, 2010 at 03:20:06PM +, Peter Maydell wrote:
 Restore the VFP registers from the ucontext on return from a signal
 handler in linux-user mode. This means that signal handlers cannot
 accidentally corrupt the interrupted code's VFP state, and allows
 them to deliberately modify the state via the ucontext structure.
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 4/6] ARM: linux-user: Restore VFP state from ucontext on sigreturn

2010-11-29 Thread Nathan Froyd
On Wed, Nov 24, 2010 at 03:20:06PM +, Peter Maydell wrote:
 Restore the VFP registers from the ucontext on return from a signal
 handler in linux-user mode. This means that signal handlers cannot
 accidentally corrupt the interrupted code's VFP state, and allows
 them to deliberately modify the state via the ucontext structure.
 
 Signed-off-by: Peter Maydell peter.mayd...@linaro.org

Reviewed-by: Nathan Froyd froy...@codesourcery.com

-Nathan



Re: [Qemu-devel] [PATCH 08/12] ARM: Return correct result for single-double conversion of NaN

2010-11-29 Thread Nathan Froyd
On Mon, Nov 29, 2010 at 07:25:18PM +, Peter Maydell wrote:
 On 29 November 2010 17:49, Nathan Froyd froy...@codesourcery.com wrote:
  On Tue, Nov 23, 2010 at 06:53:47PM +, Peter Maydell wrote:
  As with other NaN-handling patches, I don't think the bit-twiddling here
  is a good idea.  Having a float*_maybe_silence_nan function in softfloat
  would be a better approach.
 
 I guess this (like the other one you commented on) boils down to how
 you want to approach the boundary between qemu proper and the
 softfloat library. There are three approaches I can see:
 
 (a) live with the softfloat API as it is, and add bit twiddling as
 necessary for particular target CPU special casing in the per-cpu
 functions (which is what I was doing here and with the 'is it a NaN?'
 function in the other patch)

Full disclosure: I did this sort of thing for PPC; see the DO_HANDLE_NAN
macro in op_helper.c.  I was young and thoughtless then and now I
am...well, older, anyway. :) I don't think it's the best approach: since
at least two CPUs now need NaN-silencing, we should provide something
generic.  And even if only one CPU requires it, I think it's better to
squirrel the logic away in fpu/.  float{32,64,80,128} should be opaque
things except for specialized cases.

(I can see an argument for CPU-confined bit twiddling to implement
things like float*_rsqrt_estimate or similar, where one function might
not work across CPU families due to precision requirements and so forth.
But we can cross that bridge when we come to it.)

 (b) add to and extend the softfloat API whenever you have some
 floating-point related thing it doesn't currently support (which I
 did with the add conversions to int16_t patch because it was
 a big chunk of bit twiddling, but which I felt was a bit invasive to
 do for this sort of minor tweak, especially since softfloat is a
 copy of a third-party library)

I think this is the best approach whenever possible.  I would not be too
worried about the third-party-ness of softfloat; it's extremely stable,
unlikely to change anytime in the near or far future, and we've already
extended in it non-trivial ways anyway.  (And would do so again if we
ever implemented, say, proper flush-to-zero denormal handling or IA64
register-precision floats--the former being more likely than the
latter. ;)

An example of where softfloat could be usefully extended and where we do
(a) sometimes is in production of CPU-default NaN values.  softfloat
knows all about this, yet there are #defines scattered about to provide
bit patterns because the softfloat API isn't extensive enough.

 (c) do something suboptimal where the softfloat API provides
 some-API-but-not-quite-the-ideal-API (which I'm not particularly
 keen on and is what I see the is_nan() || is_signalling_nan()
 approach as)

Yes, this is ugly.  Are you up for running:

  perl -p -i -e 's/float(\d+)_is_nan/float\1_is_quiet_nan/g' target-*/*.c

(and also carefully in fpu/*) or similar and moving the bit-twiddling
float_is_nan into fpu/?

-Nathan



Re: [Qemu-devel] [PATCH 08/12] ARM: Return correct result for single-double conversion of NaN

2010-11-29 Thread Nathan Froyd
On Mon, Nov 29, 2010 at 08:04:42PM +, Peter Maydell wrote:
 On 29 November 2010 19:54, Nathan Froyd froy...@codesourcery.com wrote:
  On Mon, Nov 29, 2010 at 07:25:18PM +, Peter Maydell wrote:
  (b) add to and extend the softfloat API whenever you have some
  floating-point related thing it doesn't currently support
 
  I think this is the best approach whenever possible.
 
 OK. Do we care about maintaining consistency of the API between
 softfloat and softfloat-native (the latter used only on x86, x86_64,
 cris, sh4, sh4eb)?

softfloat-native should just go away.  I would not worry about API
compatibility between native and non-native configurations there.

  (c) do something suboptimal where the softfloat API provides
  some-API-but-not-quite-the-ideal-API (which I'm not particularly
  keen on and is what I see the is_nan() || is_signalling_nan()
  approach as)
 
  Yes, this is ugly.  Are you up for running:
 
   perl -p -i -e 's/float(\d+)_is_nan/float\1_is_quiet_nan/g' target-*/*.c
 
  (and also carefully in fpu/*) or similar and moving the bit-twiddling
  float_is_nan into fpu/?
 
 I'm happy to produce a patch doing that if it will be committed :-)

Well, I can't promise the committal part... :)

-Nathan



Re: [Qemu-devel] CFP: 1st International QEMU Users Forum

2010-11-28 Thread Nathan Froyd
On Sun, Nov 28, 2010 at 09:20:25AM +0100, Frédéric Pétrot wrote:
IMHO someone from code sourcery would be great, as they (Paul Brooks in the
older versions, it seems that Nathan is now taking over) are contributing
most of the ARM emulation stuff.

Well, Paul still knows way more than I do.  I also have not done very
much of the ARM stuff; my focus has been on the MIPS and PowerPC side of
things.  I think Peter has posted more in the way of ARM patches in the
last two weeks than we have done for the last year or so. :) (FWIW, I do
plan to add Reviewed-by tags to those this week.)

We may also have both talks organized one after the other covering both
topics, but then Wolfgang and I have to see how to fit into the time and
financial envelops (we can only pay the entrance fee for one people).
This is now a choice to be made by the qemu-devel people.
Please try to converge fast, so that we are in time for the DATE booklet.

I'm sorry, what are the both talks you refer to above?  Are you
proposing an additional talk alongside your (Frédéric's) existing talk?

-Nathan



Re: [Qemu-devel] CFP: 1st International QEMU Users Forum

2010-11-27 Thread Nathan Froyd
On Sat, Nov 27, 2010 at 11:26:05PM +0100, Alexander Graf wrote:
 On 27.11.2010, at 20:00, Peter Maydell peter.mayd...@linaro.org wrote:
  On 26 November 2010 16:34, wolfgang mueller wolfg...@acm.org wrote:
  In this case is it possible to do the introductionary talk of the workshop
  with a QEMU overview.
  People are here interested in QEMU CPU (and evtl. device) emulation.
  Most of the attending people from industry (!) and universities will have
  ARM background/interests.
  
  Thanks, but really I feel like I'm just getting started with QEMU
  development myself, so I'm not sure I would be the best person
  to give a talk like that. I'm sure there's somebody else on the
  mailing list who would be better suited.
 
 My offer stands. If we don't find anyone else, I'll jump in. Generic
 qemu stuff I can always talk about ;)

I would be happy to come and give an overview talk.  I don't know that
our process for getting in patches that are non-x86+virtualization
related are really that good, but perhaps we can have a discussion about
that so that we have a better story to tell by March. :)

-Nathan



Windows host support [was: Re: [Qemu-devel] CFP: 1st International QEMU Users Forum]

2010-11-27 Thread Nathan Froyd
On Fri, Nov 26, 2010 at 01:26:31AM +0100, François Revol wrote:
  the people we are addressing and we would like to bring together is from 
  the QEMU emulation community.
  We are interested in running different ISAs mainly under Linux and Windows 
  versions. There is a huge additional
  
  You're about the first person in 1/2 year that actually said you
  care about Windows hosts. Windows support for example is currently
  on the verge of getting deprecated, because we're lacking a
  maintainer.
 
 I suppose windows users are not as much used/interested/involved into
 free software development workflows, and probably don't bother even
 lurking on the developer mailing lists. They only shout when something
 breaks :p

We (CodeSourcery) are very interested in Windows host support.  (We
distribute QEMU with our commerical development products for
ARM/PowerPC/MIPS/SH/ColdFire/x86.)  Unfortunately, we've mostly been
backporting patches lately and haven't done a full merge from upstream
in some time, so we haven't noticed any potential breakage.  If somebody
wanted to point out to me what the (potential) Windows issues are, we
could take a look.

-Nathan



Re: [Qemu-devel] [PATCH 4/8] ARM: Return correct result for float-to-integer conversion of NaN

2010-11-11 Thread Nathan Froyd
On Thu, Nov 11, 2010 at 06:23:58PM +, Peter Maydell wrote:
 The ARM architecture mandates that converting a NaN value to
 integer gives zero. This isn't the behaviour of the SoftFloat
 library, so NaNs must be special-cased.

This is correct, but it's really only correct if FP traps are disabled.

(Also, the arm routines returning float* values is just awful.  Not your
fault, just a comment.)

-Nathan



Re: [Qemu-devel] Bug report about x86 'bt' insn

2010-11-06 Thread Nathan Froyd
On Sat, Nov 06, 2010 at 07:24:39PM +0100, Torbjorn Granlund wrote:
 malc av1...@comtv.ru writes:
 
   ZF is undefined according to AMD's 24594.pdf page 69.
   
 Ah, you're right.  It seems that all existing x86 implementations leave
 ZF alone, though.  (I am not arguing that qeum is broken, the bug is in
 my code.)

FWIW, the Intel manuals (253666, June 2010) state that the ZF flag is
unaffected, not just undefined.

-Nathan



[Qemu-devel] [PATCH] target-mips: fix translation of MT instructions

2010-10-29 Thread Nathan Froyd
The translation of dmt/emt/dvpe/evpe was doing the moral equivalent of:

  int x;
  ...   /* no initialization of x */
  x = f (x);

which confused later bits of TCG rather badly, leading to crashes.

Fix the helpers to only return results (those instructions have no
inputs), and fix the translation code accordingly.

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/helper.h|8 
 target-mips/op_helper.c |   28 
 target-mips/translate.c |8 
 3 files changed, 16 insertions(+), 28 deletions(-)

diff --git a/target-mips/helper.h b/target-mips/helper.h
index cb13fb2..297ab64 100644
--- a/target-mips/helper.h
+++ b/target-mips/helper.h
@@ -154,10 +154,10 @@ DEF_HELPER_2(mttlo, void, tl, i32)
 DEF_HELPER_2(mtthi, void, tl, i32)
 DEF_HELPER_2(mttacx, void, tl, i32)
 DEF_HELPER_1(mttdsp, void, tl)
-DEF_HELPER_1(dmt, tl, tl)
-DEF_HELPER_1(emt, tl, tl)
-DEF_HELPER_1(dvpe, tl, tl)
-DEF_HELPER_1(evpe, tl, tl)
+DEF_HELPER_0(dmt, tl)
+DEF_HELPER_0(emt, tl)
+DEF_HELPER_0(dvpe, tl)
+DEF_HELPER_0(evpe, tl)
 #endif /* !CONFIG_USER_ONLY */
 
 /* microMIPS functions */
diff --git a/target-mips/op_helper.c b/target-mips/op_helper.c
index 41abd57..ec6864d 100644
--- a/target-mips/op_helper.c
+++ b/target-mips/op_helper.c
@@ -1554,40 +1554,28 @@ void helper_mttdsp(target_ulong arg1)
 }
 
 /* MIPS MT functions */
-target_ulong helper_dmt(target_ulong arg1)
+target_ulong helper_dmt(void)
 {
 // TODO
-arg1 = 0;
-// rt = arg1
-
-return arg1;
+ return 0;
 }
 
-target_ulong helper_emt(target_ulong arg1)
+target_ulong helper_emt(void)
 {
 // TODO
-arg1 = 0;
-// rt = arg1
-
-return arg1;
+return 0;
 }
 
-target_ulong helper_dvpe(target_ulong arg1)
+target_ulong helper_dvpe(void)
 {
 // TODO
-arg1 = 0;
-// rt = arg1
-
-return arg1;
+return 0;
 }
 
-target_ulong helper_evpe(target_ulong arg1)
+target_ulong helper_evpe(void)
 {
 // TODO
-arg1 = 0;
-// rt = arg1
-
-return arg1;
+return 0;
 }
 #endif /* !CONFIG_USER_ONLY */
 
diff --git a/target-mips/translate.c b/target-mips/translate.c
index d62c615..c4c44c1 100644
--- a/target-mips/translate.c
+++ b/target-mips/translate.c
@@ -12033,22 +12033,22 @@ static void decode_opc (CPUState *env, DisasContext 
*ctx, int *is_branch)
 switch (op2) {
 case OPC_DMT:
 check_insn(env, ctx, ASE_MT);
-gen_helper_dmt(t0, t0);
+gen_helper_dmt(t0);
 gen_store_gpr(t0, rt);
 break;
 case OPC_EMT:
 check_insn(env, ctx, ASE_MT);
-gen_helper_emt(t0, t0);
+gen_helper_emt(t0);
 gen_store_gpr(t0, rt);
 break;
 case OPC_DVPE:
 check_insn(env, ctx, ASE_MT);
-gen_helper_dvpe(t0, t0);
+gen_helper_dvpe(t0);
 gen_store_gpr(t0, rt);
 break;
 case OPC_EVPE:
 check_insn(env, ctx, ASE_MT);
-gen_helper_evpe(t0, t0);
+gen_helper_evpe(t0);
 gen_store_gpr(t0, rt);
 break;
 case OPC_DI:
-- 
1.6.3.2




[Qemu-devel] [PATCH] linux-user: fix memory leaks with NPTL emulation

2010-10-29 Thread Nathan Froyd
Running programs that create large numbers of threads, such as this
snippet from libstdc++'s pthread7-rope.cc:

  const int max_thread_count = 4;
  const int max_loop_count = 1;
  ...
  for (int j = 0; j  max_loop_count; j++)
{
  ...
  for (int i = 0; i  max_thread_count; i++)
pthread_create (tid[i], NULL, thread_main, 0);

  for (int i = 0; i  max_thread_count; i++)
pthread_join (tid[i], NULL);
}

in user-mode emulation will quickly run out of memory.  This is caused
by a failure to free memory in do_syscall prior to thread exit:

  /* TODO: Free CPU state.  */
  pthread_exit(NULL);

The first step in fixing this is to make all TaskStates used by QEMU
dynamically allocated.  The TaskState used by the initial thread was
not, as it was allocated on main's stack.  So fix that, free the
cpu_env, free the TaskState, and we're home free, right?

Not exactly.  When we create a thread, we do:

ts = qemu_mallocz(sizeof(TaskState) + NEW_STACK_SIZE);
...
new_stack = ts-stack;
...
ret = pthread_attr_setstack(attr, new_stack, NEW_STACK_SIZE);

If we blindly free the TaskState, then, we yank the current (host)
thread's stack out from underneath it while it still has things to do,
like calling pthread_exit.  That causes problems, as you might expect.

The solution adopted here is to let the C library allocate the thread's
stack (so the C library can properly clean it up at pthread_exit) and
provide a hint that we want NEW_STACK_SIZE bytes of stack.

With those two changes, we're done, right?  Well, almost.  You see,
we're creating all these host threads and their parent threads never
bother to check that their children are finished.  There's no good place
for the parent threads to do so.  Therefore, we need to create the
threads in a detached state so the parent thread doesn't have to call
pthread_join on the child to release the child's resources; the child
does so automatically.

With those three major changes, we can comfortably run programs like the
above without exhausting memory.  We do need to delete 'stack' from the
TaskState structure.

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 linux-user/main.c|4 ++--
 linux-user/qemu.h|2 --
 linux-user/syscall.c |   11 +++
 3 files changed, 9 insertions(+), 8 deletions(-)

diff --git a/linux-user/main.c b/linux-user/main.c
index dbba8be..7d41d4a 100644
--- a/linux-user/main.c
+++ b/linux-user/main.c
@@ -2711,7 +2711,7 @@ int main(int argc, char **argv, char **envp)
 struct target_pt_regs regs1, *regs = regs1;
 struct image_info info1, *info = info1;
 struct linux_binprm bprm;
-TaskState ts1, *ts = ts1;
+TaskState *ts;
 CPUState *env;
 int optind;
 const char *r;
@@ -3038,7 +3038,7 @@ int main(int argc, char **argv, char **envp)
 }
 target_argv[target_argc] = NULL;
 
-memset(ts, 0, sizeof(TaskState));
+ts = qemu_mallocz (sizeof(TaskState));
 init_task_state(ts);
 /* build Task State */
 ts-info = info;
diff --git a/linux-user/qemu.h b/linux-user/qemu.h
index 708021e..00c6549 100644
--- a/linux-user/qemu.h
+++ b/linux-user/qemu.h
@@ -126,8 +126,6 @@ typedef struct TaskState {
 struct sigqueue sigqueue_table[MAX_SIGQUEUE_SIZE]; /* siginfo queue */
 struct sigqueue *first_free; /* first free siginfo queue entry */
 int signal_pending; /* non zero if a signal may be pending */
-
-uint8_t stack[0];
 } __attribute__((aligned(16))) TaskState;
 
 extern char *exec_path;
diff --git a/linux-user/syscall.c b/linux-user/syscall.c
index d44f512..5761106 100644
--- a/linux-user/syscall.c
+++ b/linux-user/syscall.c
@@ -3601,9 +3601,8 @@ static int do_fork(CPUState *env, unsigned int flags, 
abi_ulong newsp,
 new_thread_info info;
 pthread_attr_t attr;
 #endif
-ts = qemu_mallocz(sizeof(TaskState) + NEW_STACK_SIZE);
+ts = qemu_mallocz(sizeof(TaskState));
 init_task_state(ts);
-new_stack = ts-stack;
 /* we create a new CPU instance. */
 new_env = cpu_copy(env);
 #if defined(TARGET_I386) || defined(TARGET_SPARC) || defined(TARGET_PPC)
@@ -3639,7 +3638,8 @@ static int do_fork(CPUState *env, unsigned int flags, 
abi_ulong newsp,
 info.parent_tidptr = parent_tidptr;
 
 ret = pthread_attr_init(attr);
-ret = pthread_attr_setstack(attr, new_stack, NEW_STACK_SIZE);
+ret = pthread_attr_setstacksize(attr, NEW_STACK_SIZE);
+ret = pthread_attr_setdetachstate(attr, PTHREAD_CREATE_DETACHED);
 /* It is not safe to deliver signals until the child has finished
initializing, so temporarily block all signals.  */
 sigfillset(sigmask);
@@ -3667,6 +3667,7 @@ static int do_fork(CPUState *env, unsigned int flags, 
abi_ulong newsp,
 if (flags  CLONE_NPTL_FLAGS2)
 return -EINVAL;
 /* This is probably going to die very quickly, but do it anyway

Re: [Qemu-devel] [PATCH] Refactor flush of per-CPU virtual TB cache

2010-10-22 Thread Nathan Froyd
On Tue, Oct 19, 2010 at 09:57:13PM +0200, Lluís wrote:
 --- a/exec.c
 +++ b/exec.c
 @@ -688,6 +688,11 @@ static void page_flush_tb(void)
  }
  }
  
 +void tb_flush_jmp_cache (CPUState * env)
 +{
 +memset (env-tb_jmp_cache, 0, TB_JMP_CACHE_SIZE * sizeof (void *));
 +}
 +

This is only used in this file.  Why not make it static?

-Nathan



Re: [Qemu-devel] Re: [PATCH 10/14] Zero json struct with memset() instea of = {} to keep compiler happy.

2010-08-30 Thread Nathan Froyd
On Mon, Aug 30, 2010 at 10:48:55AM -0500, Anthony Liguori wrote:
 No, this is GCC being stupid.

 How else do you terminate a list?  IOW:

 MyDeviceInfo device_infos[] = {
   {foo, 0, 2},
   {bar, 0, 1},
   {} /* or { 0 } */
 };

 This is such a pervasive idiom that there's simply no way that GCC can  
 possibly try to warn against this.  Plus, it's entirely reasonable.

 I think this is just a false positive in GCC.  Otherwise, there's a ton  
 of code that it should be throwing warnings against.

Well, it sounds like Jes was compiling QEMU was extra warning flags, and
I doubt people do much beyond -Wall and maybe one or two others.

I could see petitioning GCC to only complain if -pedantic.

-Nathan



[Qemu-devel] [Bug 617528] Re: Incorrect translation of unary PPC/SPE instructions (efdneg etc.)

2010-08-19 Thread Nathan Froyd
Your patch needs a Signed-off-by and preferably a From: as well.

** Tags added: powerpc

-- 
Incorrect translation of unary PPC/SPE instructions (efdneg etc.)
https://bugs.launchpad.net/bugs/617528
You received this bug notification because you are a member of qemu-
devel-ml, which is subscribed to QEMU.

Status in QEMU: New

Bug description:
The translation for the following PPC/SPE (e500) instructions is wrong in QEMU 
git 6cbf4c8c:

evfsabs, evfsnabs, evfsneg
efdabs, efdnabs, efdneg
efsabs, efsnabs, efsneg

As you can see from the provided patch, these ought to write their result to 
the destination register (rD) and not modify the source register (rA) in-place.

It's rather hard to generate a test-case for this with GCC, since it likes to 
put the input and output of a unary operation into the same registers (that's 
probably also the reason why this went unnoticed). There is however a broken 
code path in the EGLIBC function for sin() when compiled for e500v2. It returns 
nonsense results for e.g. -1.0. Trivial test code follows:

#include stdio.h
#include stdlib.h
#include math.h

int main(int argc, char **argv)
{
  double x = strtod(argv[1], NULL);
  printf(%.14g\n, sin(x));
  return 0;
}

Result before the patch (WRONG):

$ qemu-ppc -cpu e500v2 sintest -1.0
-1

Result after the patch (OK):

$ qemu-ppc -cpu e500v2 sintest -1.0
-0.84147071838379

A self-contained test-case using inline assembler can be provided upon request.





Re: [Qemu-devel] Implementing atomic SWP in qemu-arm

2010-08-18 Thread Nathan Froyd
On Wed, Aug 18, 2010 at 12:15:09PM -0700, Peter W Schultz wrote:
 How would I go about modifying the qemu source to implement SWP
 atomically? I have been studying the source for a few days now, and I
 am at a loss as to what all needs to be done.

You should look at how the load/store-exclusive instructions work and
see if you can use a similar mechanism.  It should be fairly
straightforward.

 I feel it would be most desirable to add a TCG_SWAP instruction that
 is guaranteed to be an atomic compare-and-swap, and implement that as
 needed.

I believe there was an thread several months ago discussing doing this
or something similar and it was decided that mechanism was not the way
to go.

-Nathan



Re: [Qemu-devel] [PATCH 0/2] target-sh4: Add support for missing ldc stc instructions with sgr

2010-07-09 Thread Nathan Froyd
On Fri, Jul 09, 2010 at 03:38:34PM +0900, Alexandre Courbot wrote:
 This series of patch adds support for the missing ldc  stc privileged
 instructions with the sgr register. In order to take the difference
 of support between SH4A and SH4 (which does not recognize ldc with sgr),
 the LDST macro has been split into two simpler macros.

Both of your patches need a Signed-off-by line (git format-patch -s).

-Nathan



Re: [Qemu-devel] [PATCH 0/8] target-mips: add microMIPS ASE support, v3

2010-06-09 Thread Nathan Froyd
On Wed, Jun 09, 2010 at 04:10:25PM +0200, Aurelien Jarno wrote:
 On Tue, Jun 08, 2010 at 01:29:55PM -0700, Nathan Froyd wrote:
  This patch series adds support for the microMIPS ASE.  microMIPS is a
  new ASE similar to MIPS16, but re-encodes the entire instruction set
  into 16-bit and 32-bit instructions--in contrast to MIPS16, which
  re-encodes only integer instructions.  The mechanisms for going in and
  out of microMIPS mode are identical to those for MIPS16; a given chip
  cannot support both ASEs simultaneously.
 
 I have applied all patches except the 5th one, see my comments about
 it.

Thanks for applying these.  I agree with you about the 5th one and will
submit a M14K patch in the next week.

 Finally, I have made some comments about the 4th patch, that may be a
 basis for future improvements.

Indeed.  I will work on that one.

-Nathan



[Qemu-devel] [PATCH 0/8] target-mips: add microMIPS ASE support, v3

2010-06-08 Thread Nathan Froyd
This patch series adds support for the microMIPS ASE.  microMIPS is a
new ASE similar to MIPS16, but re-encodes the entire instruction set
into 16-bit and 32-bit instructions--in contrast to MIPS16, which
re-encodes only integer instructions.  The mechanisms for going in and
out of microMIPS mode are identical to those for MIPS16; a given chip
cannot support both ASEs simultaneously.

changes from v2:
  give actual name to FOP constants; assign names to FOPs for c{,abs}
  fix up coding style violations
  fix helpers for recent ldl_*/stl_* prototype changes
  split out mips16-related changes into separate patch
  group patches more logically

changes from v1:
  fix re-introduction of previously deleted code noted by rth

Nathan Froyd (8):
  target-mips: define constants for magic numbers
  target-mips: refactor c{,abs}.cond.fmt insns
  target-mips: mips16 cleanups
  target-mips: microMIPS ASE support
  target-mips: add microMIPS CPUs
  target-mips: add microMIPS exception handler support
  linux-user: honor low bit of entry PC for MIPS
  hw: honor low bit in mipssim machine

 hw/mips_mipssim.c|5 +-
 linux-user/main.c|5 +-
 target-mips/cpu.h|1 +
 target-mips/helper.c |   21 +-
 target-mips/helper.h |9 +
 target-mips/mips-defs.h  |1 +
 target-mips/op_helper.c  |  136 ++
 target-mips/translate.c  | 3015 ++
 target-mips/translate_init.c |   61 +
 9 files changed, 3009 insertions(+), 245 deletions(-)




[Qemu-devel] [PATCH 7/8] linux-user: honor low bit of entry PC for MIPS

2010-06-08 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 linux-user/main.c |5 -
 1 files changed, 4 insertions(+), 1 deletions(-)

diff --git a/linux-user/main.c b/linux-user/main.c
index 0f23fc9..ad292f1 100644
--- a/linux-user/main.c
+++ b/linux-user/main.c
@@ -3271,7 +3271,10 @@ int main(int argc, char **argv, char **envp)
 for(i = 0; i  32; i++) {
 env-active_tc.gpr[i] = regs-regs[i];
 }
-env-active_tc.PC = regs-cp0_epc;
+env-active_tc.PC = regs-cp0_epc  ~(target_ulong)1;
+if (regs-cp0_epc  1) {
+env-hflags |= MIPS_HFLAG_M16;
+}
 }
 #elif defined(TARGET_SH4)
 {
-- 
1.6.3.2




[Qemu-devel] [PATCH 8/8] hw: honor low bit in mipssim machine

2010-06-08 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 hw/mips_mipssim.c |5 -
 1 files changed, 4 insertions(+), 1 deletions(-)

diff --git a/hw/mips_mipssim.c b/hw/mips_mipssim.c
index a747de5..293d99e 100644
--- a/hw/mips_mipssim.c
+++ b/hw/mips_mipssim.c
@@ -106,7 +106,10 @@ static void main_cpu_reset(void *opaque)
 CPUState *env = s-env;
 
 cpu_reset(env);
-env-active_tc.PC = s-vector;
+env-active_tc.PC = s-vector  ~(target_ulong)1;
+if (s-vector  1) {
+env-hflags |= MIPS_HFLAG_M16;
+}
 }
 
 static void
-- 
1.6.3.2




[Qemu-devel] [PATCH 2/8] target-mips: refactor c{, abs}.cond.fmt insns

2010-06-08 Thread Nathan Froyd
Move all knowledge about coprocessor-checking and register numbering
into the gen_cmp* helper functions.

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/translate.c |  164 +++
 1 files changed, 81 insertions(+), 83 deletions(-)

diff --git a/target-mips/translate.c b/target-mips/translate.c
index 4e54940..8d532d5 100644
--- a/target-mips/translate.c
+++ b/target-mips/translate.c
@@ -676,39 +676,6 @@ static inline int get_fp_bit (int cc)
 return 23;
 }
 
-#define FOP_CONDS(type, fmt, bits)\
-static inline void gen_cmp ## type ## _ ## fmt(int n, TCGv_i##bits a, \
-   TCGv_i##bits b, int cc)\
-{ \
-switch (n) {  \
-case  0: gen_helper_2i(cmp ## type ## _ ## fmt ## _f, a, b, cc);break;\
-case  1: gen_helper_2i(cmp ## type ## _ ## fmt ## _un, a, b, cc);   break;\
-case  2: gen_helper_2i(cmp ## type ## _ ## fmt ## _eq, a, b, cc);   break;\
-case  3: gen_helper_2i(cmp ## type ## _ ## fmt ## _ueq, a, b, cc);  break;\
-case  4: gen_helper_2i(cmp ## type ## _ ## fmt ## _olt, a, b, cc);  break;\
-case  5: gen_helper_2i(cmp ## type ## _ ## fmt ## _ult, a, b, cc);  break;\
-case  6: gen_helper_2i(cmp ## type ## _ ## fmt ## _ole, a, b, cc);  break;\
-case  7: gen_helper_2i(cmp ## type ## _ ## fmt ## _ule, a, b, cc);  break;\
-case  8: gen_helper_2i(cmp ## type ## _ ## fmt ## _sf, a, b, cc);   break;\
-case  9: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngle, a, b, cc); break;\
-case 10: gen_helper_2i(cmp ## type ## _ ## fmt ## _seq, a, b, cc);  break;\
-case 11: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngl, a, b, cc);  break;\
-case 12: gen_helper_2i(cmp ## type ## _ ## fmt ## _lt, a, b, cc);   break;\
-case 13: gen_helper_2i(cmp ## type ## _ ## fmt ## _nge, a, b, cc);  break;\
-case 14: gen_helper_2i(cmp ## type ## _ ## fmt ## _le, a, b, cc);   break;\
-case 15: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngt, a, b, cc);  break;\
-default: abort(); \
-} \
-}
-
-FOP_CONDS(, d, 64)
-FOP_CONDS(abs, d, 64)
-FOP_CONDS(, s, 32)
-FOP_CONDS(abs, s, 32)
-FOP_CONDS(, ps, 64)
-FOP_CONDS(abs, ps, 64)
-#undef FOP_CONDS
-
 /* Tests */
 static inline void gen_save_pc(target_ulong pc)
 {
@@ -849,6 +816,69 @@ static inline void check_mips_64(DisasContext *ctx)
 generate_exception(ctx, EXCP_RI);
 }
 
+/* Define small wrappers for gen_load_fpr* so that we have a uniform
+   calling interface for 32 and 64-bit FPRs.  No sense in changing
+   all callers for gen_load_fpr32 when we need the CTX parameter for
+   this one use.  */
+#define gen_ldcmp_fpr32(ctx, x, y) gen_load_fpr32(x, y)
+#define gen_ldcmp_fpr64(ctx, x, y) gen_load_fpr64(ctx, x, y)
+#define FOP_CONDS(type, abs, fmt, ifmt, bits) \
+static inline void gen_cmp ## type ## _ ## fmt(DisasContext *ctx, int n,  \
+   int ft, int fs, int cc)\
+{ \
+TCGv_i##bits fp0 = tcg_temp_new_i##bits ();   \
+TCGv_i##bits fp1 = tcg_temp_new_i##bits ();   \
+switch (ifmt) {   \
+case FMT_PS:  \
+check_cp1_64bitmode(ctx); \
+break;\
+case FMT_D:   \
+if (abs) {\
+check_cop1x(ctx); \
+} \
+check_cp1_registers(ctx, fs | ft);\
+break;\
+case FMT_S:   \
+if (abs) {\
+check_cop1x(ctx); \
+} \
+break;\
+} \
+gen_ldcmp_fpr##bits (ctx, fp0, fs);   \
+gen_ldcmp_fpr##bits (ctx, fp1, ft

[Qemu-devel] [PATCH 1/8] target-mips: define constants for magic numbers

2010-06-08 Thread Nathan Froyd
Add FMT_* constants for the floating-point format field in opcodes and
tweak a few places to use them.  Add enums for various invocations of
FOP and tweak gen_farith and its lone caller accordingly.

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/translate.c |  437 ---
 1 files changed, 295 insertions(+), 142 deletions(-)

diff --git a/target-mips/translate.c b/target-mips/translate.c
index 2075d09..4e54940 100644
--- a/target-mips/translate.c
+++ b/target-mips/translate.c
@@ -354,6 +354,19 @@ enum {
 /* Coprocessor 1 (rs field) */
 #define MASK_CP1(op)   MASK_OP_MAJOR(op) | (op  (0x1F  21))
 
+/* Values for the fmt field in FP instructions */
+enum {
+/* 0 - 15 are reserved */
+FMT_S = 16,
+FMT_D = 17,
+FMT_E = 18,
+FMT_Q = 19,
+FMT_W = 20,
+FMT_L = 21,
+FMT_PS = 22,
+/* 23 - 31 are reserved */
+};
+
 enum {
 OPC_MFC1 = (0x00  21) | OPC_CP1,
 OPC_DMFC1= (0x01  21) | OPC_CP1,
@@ -366,13 +379,13 @@ enum {
 OPC_BC1  = (0x08  21) | OPC_CP1, /* bc */
 OPC_BC1ANY2  = (0x09  21) | OPC_CP1,
 OPC_BC1ANY4  = (0x0A  21) | OPC_CP1,
-OPC_S_FMT= (0x10  21) | OPC_CP1, /* 16: fmt=single fp */
-OPC_D_FMT= (0x11  21) | OPC_CP1, /* 17: fmt=double fp */
-OPC_E_FMT= (0x12  21) | OPC_CP1, /* 18: fmt=extended fp */
-OPC_Q_FMT= (0x13  21) | OPC_CP1, /* 19: fmt=quad fp */
-OPC_W_FMT= (0x14  21) | OPC_CP1, /* 20: fmt=32bit fixed */
-OPC_L_FMT= (0x15  21) | OPC_CP1, /* 21: fmt=64bit fixed */
-OPC_PS_FMT   = (0x16  21) | OPC_CP1, /* 22: fmt=paired single fp */
+OPC_S_FMT= (FMT_S  21) | OPC_CP1,  /* 16: fmt=single fp */
+OPC_D_FMT= (FMT_D  21) | OPC_CP1,  /* 17: fmt=double fp */
+OPC_E_FMT= (FMT_E  21) | OPC_CP1,  /* 18: fmt=extended fp */
+OPC_Q_FMT= (FMT_Q  21) | OPC_CP1,  /* 19: fmt=quad fp */
+OPC_W_FMT= (FMT_W  21) | OPC_CP1,  /* 20: fmt=32bit fixed */
+OPC_L_FMT= (FMT_L  21) | OPC_CP1,  /* 21: fmt=64bit fixed */
+OPC_PS_FMT   = (FMT_PS  21) | OPC_CP1, /* 22: fmt=paired single fp */
 };
 
 #define MASK_CP1_FUNC(op)   MASK_CP1(op) | (op  0x3F)
@@ -5714,6 +5727,146 @@ static void gen_compute_branch1 (CPUState *env, 
DisasContext *ctx, uint32_t op,
 
 #define FOP(func, fmt) (((fmt)  21) | (func))
 
+enum fopcode {
+OPC_ADD_S = FOP(0, FMT_S),
+OPC_SUB_S = FOP(1, FMT_S),
+OPC_MUL_S = FOP(2, FMT_S),
+OPC_DIV_S = FOP(3, FMT_S),
+OPC_SQRT_S = FOP(4, FMT_S),
+OPC_ABS_S = FOP(5, FMT_S),
+OPC_MOV_S = FOP(6, FMT_S),
+OPC_NEG_S = FOP(7, FMT_S),
+OPC_ROUND_L_S = FOP(8, FMT_S),
+OPC_TRUNC_L_S = FOP(9, FMT_S),
+OPC_CEIL_L_S = FOP(10, FMT_S),
+OPC_FLOOR_L_S = FOP(11, FMT_S),
+OPC_ROUND_W_S = FOP(12, FMT_S),
+OPC_TRUNC_W_S = FOP(13, FMT_S),
+OPC_CEIL_W_S = FOP(14, FMT_S),
+OPC_FLOOR_W_S = FOP(15, FMT_S),
+OPC_MOVCF_S = FOP(17, FMT_S),
+OPC_MOVZ_S = FOP(18, FMT_S),
+OPC_MOVN_S = FOP(19, FMT_S),
+OPC_RECIP_S = FOP(21, FMT_S),
+OPC_RSQRT_S = FOP(22, FMT_S),
+OPC_RECIP2_S = FOP(28, FMT_S),
+OPC_RECIP1_S = FOP(29, FMT_S),
+OPC_RSQRT1_S = FOP(30, FMT_S),
+OPC_RSQRT2_S = FOP(31, FMT_S),
+OPC_CVT_D_S = FOP(33, FMT_S),
+OPC_CVT_W_S = FOP(36, FMT_S),
+OPC_CVT_L_S = FOP(37, FMT_S),
+OPC_CVT_PS_S = FOP(38, FMT_S),
+OPC_CMP_F_S = FOP (48, FMT_S),
+OPC_CMP_UN_S = FOP (49, FMT_S),
+OPC_CMP_EQ_S = FOP (50, FMT_S),
+OPC_CMP_UEQ_S = FOP (51, FMT_S),
+OPC_CMP_OLT_S = FOP (52, FMT_S),
+OPC_CMP_ULT_S = FOP (53, FMT_S),
+OPC_CMP_OLE_S = FOP (54, FMT_S),
+OPC_CMP_ULE_S = FOP (55, FMT_S),
+OPC_CMP_SF_S = FOP (56, FMT_S),
+OPC_CMP_NGLE_S = FOP (57, FMT_S),
+OPC_CMP_SEQ_S = FOP (58, FMT_S),
+OPC_CMP_NGL_S = FOP (59, FMT_S),
+OPC_CMP_LT_S = FOP (60, FMT_S),
+OPC_CMP_NGE_S = FOP (61, FMT_S),
+OPC_CMP_LE_S = FOP (62, FMT_S),
+OPC_CMP_NGT_S = FOP (63, FMT_S),
+
+OPC_ADD_D = FOP(0, FMT_D),
+OPC_SUB_D = FOP(1, FMT_D),
+OPC_MUL_D = FOP(2, FMT_D),
+OPC_DIV_D = FOP(3, FMT_D),
+OPC_SQRT_D = FOP(4, FMT_D),
+OPC_ABS_D = FOP(5, FMT_D),
+OPC_MOV_D = FOP(6, FMT_D),
+OPC_NEG_D = FOP(7, FMT_D),
+OPC_ROUND_L_D = FOP(8, FMT_D),
+OPC_TRUNC_L_D = FOP(9, FMT_D),
+OPC_CEIL_L_D = FOP(10, FMT_D),
+OPC_FLOOR_L_D = FOP(11, FMT_D),
+OPC_ROUND_W_D = FOP(12, FMT_D),
+OPC_TRUNC_W_D = FOP(13, FMT_D),
+OPC_CEIL_W_D = FOP(14, FMT_D),
+OPC_FLOOR_W_D = FOP(15, FMT_D),
+OPC_MOVCF_D = FOP(17, FMT_D),
+OPC_MOVZ_D = FOP(18, FMT_D),
+OPC_MOVN_D = FOP(19, FMT_D),
+OPC_RECIP_D = FOP(21, FMT_D),
+OPC_RSQRT_D = FOP(22, FMT_D),
+OPC_RECIP2_D = FOP(28, FMT_D),
+OPC_RECIP1_D = FOP(29, FMT_D),
+OPC_RSQRT1_D = FOP(30, FMT_D),
+OPC_RSQRT2_D = FOP(31, FMT_D),
+OPC_CVT_S_D = FOP(32, FMT_D),
+OPC_CVT_W_D = FOP(36, FMT_D),
+OPC_CVT_L_D = FOP(37, FMT_D),
+OPC_CMP_F_D = FOP (48, FMT_D

[Qemu-devel] [PATCH 3/8] target-mips: mips16 cleanups

2010-06-08 Thread Nathan Froyd
Change code handling mips16-specific branches to use ISA-neutral special
opcodes.  Since there are several places where the delay slot
requirements for microMIPS branches differ from mips16 branches, using
opcodes is easier than checking hflags, then checking mips16
vs. microMIPS.

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/translate.c |   24 +---
 1 files changed, 17 insertions(+), 7 deletions(-)

diff --git a/target-mips/translate.c b/target-mips/translate.c
index 8d532d5..2754b2e 100644
--- a/target-mips/translate.c
+++ b/target-mips/translate.c
@@ -68,6 +68,7 @@ enum {
 /* Jump and branches */
 OPC_J= (0x02  26),
 OPC_JAL  = (0x03  26),
+OPC_JALS = OPC_JAL | 0x5,
 OPC_BEQ  = (0x04  26),  /* Unconditional if rs = rt = 0 (B) */
 OPC_BEQL = (0x14  26),
 OPC_BNE  = (0x05  26),
@@ -77,6 +78,7 @@ enum {
 OPC_BGTZ = (0x07  26),
 OPC_BGTZL= (0x17  26),
 OPC_JALX = (0x1D  26),  /* MIPS 16 only */
+OPC_JALXS= OPC_JALX | 0x5,
 /* Load and stores */
 OPC_LDL  = (0x1A  26),
 OPC_LDR  = (0x1B  26),
@@ -177,6 +179,7 @@ enum {
 OPC_JR   = 0x08 | OPC_SPECIAL, /* Also JR.HB */
 OPC_JALR = 0x09 | OPC_SPECIAL, /* Also JALR.HB */
 OPC_JALRC= OPC_JALR | (0x5  6),
+OPC_JALRS= 0x10 | OPC_SPECIAL | (0x5  6),
 /* Traps */
 OPC_TGE  = 0x30 | OPC_SPECIAL,
 OPC_TGEU = 0x31 | OPC_SPECIAL,
@@ -2466,12 +2469,15 @@ static void gen_compute_branch (DisasContext *ctx, 
uint32_t opc,
 case OPC_J:
 case OPC_JAL:
 case OPC_JALX:
+case OPC_JALS:
+case OPC_JALXS:
 /* Jump to immediate */
 btgt = ((ctx-pc + insn_bytes)  (int32_t)0xF000) | 
(uint32_t)offset;
 break;
 case OPC_JR:
 case OPC_JALR:
 case OPC_JALRC:
+case OPC_JALRS:
 /* Jump to register */
 if (offset != 0  offset != 16) {
 /* Hint = 0 is JR/JALR, hint 16 is JR.HB/JALR.HB, the
@@ -2534,29 +2540,33 @@ static void gen_compute_branch (DisasContext *ctx, 
uint32_t opc,
 ctx-hflags |= MIPS_HFLAG_B;
 MIPS_DEBUG(j  TARGET_FMT_lx, btgt);
 break;
+case OPC_JALXS:   
 case OPC_JALX:
 ctx-hflags |= MIPS_HFLAG_BX;
 /* Fallthrough */
+case OPC_JALS:
 case OPC_JAL:
 blink = 31;
 ctx-hflags |= MIPS_HFLAG_B;
-ctx-hflags |= (ctx-hflags  MIPS_HFLAG_M16
+ctx-hflags |= ((opc == OPC_JALS || opc == OPC_JALXS)
 ? MIPS_HFLAG_BDS16
 : MIPS_HFLAG_BDS32);
 MIPS_DEBUG(jal  TARGET_FMT_lx, btgt);
 break;
 case OPC_JR:
 ctx-hflags |= MIPS_HFLAG_BR;
-if (ctx-hflags  MIPS_HFLAG_M16)
-ctx-hflags |= MIPS_HFLAG_BDS16;
+if (insn_bytes == 4)
+ctx-hflags |= MIPS_HFLAG_BDS32;
 MIPS_DEBUG(jr %s, regnames[rs]);
 break;
+case OPC_JALRS:
 case OPC_JALR:
 case OPC_JALRC:
 blink = rt;
 ctx-hflags |= MIPS_HFLAG_BR;
-if (ctx-hflags  MIPS_HFLAG_M16)
-ctx-hflags |= MIPS_HFLAG_BDS16;
+ctx-hflags |= (opc == OPC_JALRS
+? MIPS_HFLAG_BDS16
+: MIPS_HFLAG_BDS32);
 MIPS_DEBUG(jalr %s, %s, regnames[rt], regnames[rs]);
 break;
 default:
@@ -8487,7 +8497,7 @@ static int decode_mips16_opc (CPUState *env, DisasContext 
*ctx,
 offset = (((ctx-opcode  0x1f)  21)
   | ((ctx-opcode  5)  0x1f)  16
   | offset)  2;
-op = ((ctx-opcode  10)  0x1) ? OPC_JALX : OPC_JAL;
+op = ((ctx-opcode  10)  0x1) ? OPC_JALXS : OPC_JALS;
 gen_compute_branch(ctx, op, 4, rx, ry, offset);
 n_bytes = 4;
 *is_branch = 1;
@@ -8726,7 +8736,7 @@ static int decode_mips16_opc (CPUState *env, DisasContext 
*ctx,
 int ra = (ctx-opcode  5)  0x1;
 
 if (link) {
-op = nd ? OPC_JALRC : OPC_JALR;
+op = nd ? OPC_JALRC : OPC_JALRS;
 } else {
 op = OPC_JR;
 }
-- 
1.6.3.2




[Qemu-devel] [PATCH 6/8] target-mips: add microMIPS exception handler support

2010-06-08 Thread Nathan Froyd
Unlike MIPS16, microMIPS lets you choose the ISA mode for your exception
handlers.  The ISA mode is selectable via a user-writable CP0.Config3
flag.

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/cpu.h|1 +
 target-mips/helper.c |   21 +++--
 2 files changed, 16 insertions(+), 6 deletions(-)

diff --git a/target-mips/cpu.h b/target-mips/cpu.h
index 7285636..c21b8e4 100644
--- a/target-mips/cpu.h
+++ b/target-mips/cpu.h
@@ -363,6 +363,7 @@ struct CPUMIPSState {
 #define CP0C2_SA   0
 int32_t CP0_Config3;
 #define CP0C3_M31
+#define CP0C3_ISA_ON_EXC 16
 #define CP0C3_DSPP 10
 #define CP0C3_LPA  7
 #define CP0C3_VEIC 6
diff --git a/target-mips/helper.c b/target-mips/helper.c
index 8102f03..ea221ab 100644
--- a/target-mips/helper.c
+++ b/target-mips/helper.c
@@ -385,6 +385,18 @@ static target_ulong exception_resume_pc (CPUState *env)
 
 return bad_pc;
 }
+
+static void set_hflags_for_handler (CPUState *env)
+{
+/* Exception handlers are entered in 32-bit mode.  */
+env-hflags = ~(MIPS_HFLAG_M16);
+/* ...except that microMIPS lets you choose.  */
+if (env-insn_flags  ASE_MICROMIPS) {
+env-hflags |= (!!(env-CP0_Config3
+(1  CP0C3_ISA_ON_EXC))
+ MIPS_HFLAG_M16_SHIFT);
+}
+}
 #endif
 
 void do_interrupt (CPUState *env)
@@ -440,8 +452,7 @@ void do_interrupt (CPUState *env)
 if (!(env-CP0_Status  (1  CP0St_EXL)))
 env-CP0_Cause = ~(1  CP0Ca_BD);
 env-active_tc.PC = (int32_t)0xBFC00480;
-/* Exception handlers are entered in 32-bit mode.  */
-env-hflags = ~(MIPS_HFLAG_M16);
+set_hflags_for_handler(env);
 break;
 case EXCP_RESET:
 cpu_reset(env);
@@ -461,8 +472,7 @@ void do_interrupt (CPUState *env)
 if (!(env-CP0_Status  (1  CP0St_EXL)))
 env-CP0_Cause = ~(1  CP0Ca_BD);
 env-active_tc.PC = (int32_t)0xBFC0;
-/* Exception handlers are entered in 32-bit mode.  */
-env-hflags = ~(MIPS_HFLAG_M16);
+set_hflags_for_handler(env);
 break;
 case EXCP_EXT_INTERRUPT:
 cause = 0;
@@ -581,8 +591,7 @@ void do_interrupt (CPUState *env)
 env-active_tc.PC = (int32_t)(env-CP0_EBase  ~0x3ff);
 }
 env-active_tc.PC += offset;
-/* Exception handlers are entered in 32-bit mode.  */
-env-hflags = ~(MIPS_HFLAG_M16);
+set_hflags_for_handler(env);
 env-CP0_Cause = (env-CP0_Cause  ~(0x1f  CP0Ca_EC)) | (cause  
CP0Ca_EC);
 break;
 default:
-- 
1.6.3.2




[Qemu-devel] [PATCH 5/8] target-mips: add microMIPS CPUs

2010-06-08 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/translate_init.c |   61 ++
 1 files changed, 61 insertions(+), 0 deletions(-)

diff --git a/target-mips/translate_init.c b/target-mips/translate_init.c
index b79ed56..8e17f4b 100644
--- a/target-mips/translate_init.c
+++ b/target-mips/translate_init.c
@@ -141,6 +141,25 @@ static const mips_def_t mips_defs[] =
 .mmu_type = MMU_TYPE_FMT,
 },
 {
+.name = 4Km-micromips,
+.CP0_PRid = 0x00018300,
+/* Config1 implemented, fixed mapping MMU,
+   no virtual icache, uncached coherency. */
+.CP0_Config0 = MIPS_CONFIG0 | (MMU_TYPE_FMT  CP0C0_MT),
+.CP0_Config1 = MIPS_CONFIG1 |
+   (0  CP0C1_IS) | (3  CP0C1_IL) | (1  CP0C1_IA) |
+   (0  CP0C1_DS) | (3  CP0C1_DL) | (1  CP0C1_DA),
+.CP0_Config2 = MIPS_CONFIG2,
+.CP0_Config3 = MIPS_CONFIG3,
+.SYNCI_Step = 32,
+.CCRes = 2,
+.CP0_Status_rw_bitmask = 0x1258FF17,
+.SEGBITS = 32,
+.PABITS = 32,
+.insn_flags = CPU_MIPS32R2 | ASE_MICROMIPS,
+.mmu_type = MMU_TYPE_FMT,
+},
+{
 .name = 4KEcR1,
 .CP0_PRid = 0x00018400,
 .CP0_Config0 = MIPS_CONFIG0 | (MMU_TYPE_R4000  CP0C0_MT),
@@ -245,6 +264,25 @@ static const mips_def_t mips_defs[] =
 .mmu_type = MMU_TYPE_R4000,
 },
 {
+.name = 24Kc-micromips,
+.CP0_PRid = 0x00019300,
+.CP0_Config0 = MIPS_CONFIG0 | (0x1  CP0C0_AR) |
+(MMU_TYPE_R4000  CP0C0_MT),
+.CP0_Config1 = MIPS_CONFIG1 | (15  CP0C1_MMU) |
+   (0  CP0C1_IS) | (3  CP0C1_IL) | (1  CP0C1_IA) |
+   (0  CP0C1_DS) | (3  CP0C1_DL) | (1  CP0C1_DA),
+.CP0_Config2 = MIPS_CONFIG2,
+.CP0_Config3 = MIPS_CONFIG3 | (0  CP0C3_VInt),
+.SYNCI_Step = 32,
+.CCRes = 2,
+/* No DSP implemented. */
+.CP0_Status_rw_bitmask = 0x1278FF1F,
+.SEGBITS = 32,
+.PABITS = 32,
+.insn_flags = CPU_MIPS32R2 | ASE_MICROMIPS,
+.mmu_type = MMU_TYPE_R4000,
+},
+{
 .name = 24Kf,
 .CP0_PRid = 0x00019300,
 .CP0_Config0 = MIPS_CONFIG0 | (0x1  CP0C0_AR) |
@@ -269,6 +307,29 @@ static const mips_def_t mips_defs[] =
 .mmu_type = MMU_TYPE_R4000,
 },
 {
+.name = 24Kf-micromips,
+.CP0_PRid = 0x00019300,
+.CP0_Config0 = MIPS_CONFIG0 | (0x1  CP0C0_AR) |
+(MMU_TYPE_R4000  CP0C0_MT),
+.CP0_Config1 = MIPS_CONFIG1 | (1  CP0C1_FP) | (15  CP0C1_MMU) |
+   (0  CP0C1_IS) | (3  CP0C1_IL) | (1  CP0C1_IA) |
+   (0  CP0C1_DS) | (3  CP0C1_DL) | (1  CP0C1_DA),
+.CP0_Config2 = MIPS_CONFIG2,
+.CP0_Config3 = MIPS_CONFIG3 | (0  CP0C3_VInt),
+.CP0_LLAddr_rw_bitmask = 0,
+.CP0_LLAddr_shift = 4,
+.SYNCI_Step = 32,
+.CCRes = 2,
+/* No DSP implemented. */
+.CP0_Status_rw_bitmask = 0x3678FF1F,
+.CP1_fcr0 = (1  FCR0_F64) | (1  FCR0_L) | (1  FCR0_W) |
+(1  FCR0_D) | (1  FCR0_S) | (0x93  FCR0_PRID),
+.SEGBITS = 32,
+.PABITS = 32,
+.insn_flags = CPU_MIPS32R2 | ASE_MICROMIPS,
+.mmu_type = MMU_TYPE_R4000,
+},
+{
 .name = 34Kf,
 .CP0_PRid = 0x00019500,
 .CP0_Config0 = MIPS_CONFIG0 | (0x1  CP0C0_AR) |
-- 
1.6.3.2




Re: [Qemu-devel] [PATCH 00/10] target-mips: add microMIPS ASE support, v2

2010-06-04 Thread Nathan Froyd
On Mon, May 24, 2010 at 09:19:34AM -0700, Nathan Froyd wrote:
 This patch series adds support for the microMIPS ASE.  microMIPS is a
 new ASE similar to MIPS16, but re-encodes the entire instruction set
 into 16-bit and 32-bit instructions--in contrast to MIPS16, which
 re-encodes only integer instructions.  The mechanisms for going in and
 out of microMIPS mode are identical to those for MIPS16; a given chip
 cannot support both ASEs simultaneously.

Ping.

-Nathan



Re: [Qemu-devel] [PATCH 03/10] target-mips: add enum constants for various invocations of FOP

2010-06-04 Thread Nathan Froyd
On Fri, Jun 04, 2010 at 10:45:32AM -0700, Richard Henderson wrote:
 On 05/24/2010 09:19 AM, Nathan Froyd wrote:
  @@ -5937,8 +6031,8 @@ static void gen_farith (DisasContext *ctx, uint32_t 
  op1,
   enum { BINOP, CMPOP, OTHEROP } optype = OTHEROP;
   uint32_t func = ctx-opcode  0x3f;
   
  -switch (ctx-opcode  FOP(0x3f, 0x1f)) {
  -case FOP(0, 16):
  +switch (opc) {
  +case OPC_ADD_S:
 
 For instance, opc would seem to be a good candidate for a variable
 to be switched to the enumeration type.
 
 ... Except that I can't seem to find the definition of opc at this
 point in patch 3?  It looks like the argument op1 should be what's
 used here.  Is this a case of patches being split incorrectly?

This is indeed supposed to be op1; the typo gets fixed in patch 6.

What's the benefit from declaring op1 as 'enum fopcode' or similar?

-Nathan



Re: [Qemu-devel] [PATCH 06/10] target-mips: add microMIPS ASE support

2010-06-04 Thread Nathan Froyd
On Fri, Jun 04, 2010 at 11:30:38AM -0700, Richard Henderson wrote:
 On 05/24/2010 09:19 AM, Nathan Froyd wrote:
  +int (*ldfun)(target_ulong);
  +
  +switch (mem_idx)
  +{
  +case 0: ldfun = ldl_kernel; break;
  +case 1: ldfun = ldl_super; break;
  +default:
  +case 2: ldfun = ldl_user; break;
  +}
 
 This *should* now be a compile error.  The return type should
 now be uint32_t, not int.

Will fix, thanks for pointing that out.

  @@ -2535,26 +2555,29 @@ static void gen_compute_branch (DisasContext *ctx, 
  uint32_t opc,
   case OPC_JALX:
   ctx-hflags |= MIPS_HFLAG_BX;
   /* Fallthrough */
  +case OPC_JALS:
   case OPC_JAL:
   blink = 31;
   ctx-hflags |= MIPS_HFLAG_B;
  -ctx-hflags |= (ctx-hflags  MIPS_HFLAG_M16
  +ctx-hflags |= (opc == OPC_JALS
   ? MIPS_HFLAG_BDS16
   : MIPS_HFLAG_BDS32);
 
 Changed semantics here?  You're no longer testing M16 bit.
 Or is that later handled by switching mips16 to JALS too?

It ought to be handled by switching mips16 to use JALS.  I see that I
didn't do that.

 And if so, perhaps this patch should be broken into two, where
 you introduce the new opcodes and hflags changes and apply them
 as-needed to the mips16 code.  Thus one can verify that the
 semantics for mips16 are the same before and after.

I don't think there are any hflags changes, but the point is
well-taken.  I'll do that.

  +if (base == 0) {
  +tcg_gen_movi_tl(t0, 0);
  +} else {
  +gen_load_gpr(t0, base);
  +}
 
 gen_load_gpr already takes care of R0.

Will fix.

  +#if 0
  +case 0x01:
  +switch (minor) {
  +case MFHI_ACC:
  +gen_HILO(ctx, OPC_MFHI, rs);
 
 New if 0 code?

Yup, will delete.

-Nathan



Re: [Qemu-devel] [PATCH 07/10] target-mips: add microMIPS CPUs

2010-06-04 Thread Nathan Froyd
On Fri, Jun 04, 2010 at 11:35:45AM -0700, Richard Henderson wrote:
 On 05/24/2010 09:19 AM, Nathan Froyd wrote:
  Signed-off-by: Nathan Froyd froy...@codesourcery.com
  ---
   target-mips/translate_init.c |   61 
  ++
   1 files changed, 61 insertions(+), 0 deletions(-)
  
 Reviewed-by: Richard Henderson r...@twiddle.net
 
 ... not that there's anything in here I could actually verify
 without hardware manuals ;-)

:)  For avoidance of doubt, the 24K*micromips variants were added for
easy testing initially; the 4Km-micromips definition is actually based
on real hardware.  I'm happy to just submit the one based on real
hardware if that would be easier.

-Nathan



[Qemu-devel] [PATCH 02/10] target-mips: add microMIPS-specific bits to mips-defs.h

2010-05-24 Thread Nathan Froyd
There's a new ASE_MICROMIPS instruction flag, and some extra CP0_Config3
fields.  The ISA and ISA_ON_EXC fields are specific to microMIPS.  The
DSP2P is for version 2 of the DSP ASE.

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/cpu.h   |3 +++
 target-mips/mips-defs.h |1 +
 2 files changed, 4 insertions(+), 0 deletions(-)

diff --git a/target-mips/cpu.h b/target-mips/cpu.h
index 7285636..986d938 100644
--- a/target-mips/cpu.h
+++ b/target-mips/cpu.h
@@ -363,6 +363,9 @@ struct CPUMIPSState {
 #define CP0C2_SA   0
 int32_t CP0_Config3;
 #define CP0C3_M31
+#define CP0C3_ISA_ON_EXC 16
+#define CP0C3_ISA  14
+#define CP0C3_DSP2P 11
 #define CP0C3_DSPP 10
 #define CP0C3_LPA  7
 #define CP0C3_VEIC 6
diff --git a/target-mips/mips-defs.h b/target-mips/mips-defs.h
index c57de02..a7f4697 100644
--- a/target-mips/mips-defs.h
+++ b/target-mips/mips-defs.h
@@ -38,6 +38,7 @@
 #defineASE_DSPR2   0x0001
 #defineASE_MT  0x0002
 #defineASE_SMARTMIPS   0x0004
+#defineASE_MICROMIPS   0x0008
 
 /* Chip specific instructions. */
 #defineINSN_VR54XX 0x8000
-- 
1.6.3.2




[Qemu-devel] [PATCH 03/10] target-mips: add enum constants for various invocations of FOP

2010-05-24 Thread Nathan Froyd
Tweak gen_farith and its caller to use them.

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/translate.c |  266 ---
 1 files changed, 180 insertions(+), 86 deletions(-)

diff --git a/target-mips/translate.c b/target-mips/translate.c
index 2075d09..2568e16 100644
--- a/target-mips/translate.c
+++ b/target-mips/translate.c
@@ -5714,6 +5714,100 @@ static void gen_compute_branch1 (CPUState *env, 
DisasContext *ctx, uint32_t op,
 
 #define FOP(func, fmt) (((fmt)  21) | (func))
 
+enum {
+OPC_ADD_S = FOP(0, FMT_S),
+OPC_SUB_S = FOP(1, FMT_S),
+OPC_MUL_S = FOP(2, FMT_S),
+OPC_DIV_S = FOP(3, FMT_S),
+OPC_SQRT_S = FOP(4, FMT_S),
+OPC_ABS_S = FOP(5, FMT_S),
+OPC_MOV_S = FOP(6, FMT_S),
+OPC_NEG_S = FOP(7, FMT_S),
+OPC_ROUND_L_S = FOP(8, FMT_S),
+OPC_TRUNC_L_S = FOP(9, FMT_S),
+OPC_CEIL_L_S = FOP(10, FMT_S),
+OPC_FLOOR_L_S = FOP(11, FMT_S),
+OPC_ROUND_W_S = FOP(12, FMT_S),
+OPC_TRUNC_W_S = FOP(13, FMT_S),
+OPC_CEIL_W_S = FOP(14, FMT_S),
+OPC_FLOOR_W_S = FOP(15, FMT_S),
+OPC_MOVCF_S = FOP(17, FMT_S),
+OPC_MOVZ_S = FOP(18, FMT_S),
+OPC_MOVN_S = FOP(19, FMT_S),
+OPC_RECIP_S = FOP(21, FMT_S),
+OPC_RSQRT_S = FOP(22, FMT_S),
+OPC_RECIP2_S = FOP(28, FMT_S),
+OPC_RECIP1_S = FOP(29, FMT_S),
+OPC_RSQRT1_S = FOP(30, FMT_S),
+OPC_RSQRT2_S = FOP(31, FMT_S),
+OPC_CVT_D_S = FOP(33, FMT_S),
+OPC_CVT_W_S = FOP(36, FMT_S),
+OPC_CVT_L_S = FOP(37, FMT_S),
+OPC_CVT_PS_S = FOP(38, FMT_S),
+/* FOP(48..63, FMT_S) used for comparisons */
+OPC_ADD_D = FOP(0, FMT_D),
+OPC_SUB_D = FOP(1, FMT_D),
+OPC_MUL_D = FOP(2, FMT_D),
+OPC_DIV_D = FOP(3, FMT_D),
+OPC_SQRT_D = FOP(4, FMT_D),
+OPC_ABS_D = FOP(5, FMT_D),
+OPC_MOV_D = FOP(6, FMT_D),
+OPC_NEG_D = FOP(7, FMT_D),
+OPC_ROUND_L_D = FOP(8, FMT_D),
+OPC_TRUNC_L_D = FOP(9, FMT_D),
+OPC_CEIL_L_D = FOP(10, FMT_D),
+OPC_FLOOR_L_D = FOP(11, FMT_D),
+OPC_ROUND_W_D = FOP(12, FMT_D),
+OPC_TRUNC_W_D = FOP(13, FMT_D),
+OPC_CEIL_W_D = FOP(14, FMT_D),
+OPC_FLOOR_W_D = FOP(15, FMT_D),
+OPC_MOVCF_D = FOP(17, FMT_D),
+OPC_MOVZ_D = FOP(18, FMT_D),
+OPC_MOVN_D = FOP(19, FMT_D),
+OPC_RECIP_D = FOP(21, FMT_D),
+OPC_RSQRT_D = FOP(22, FMT_D),
+OPC_RECIP2_D = FOP(28, FMT_D),
+OPC_RECIP1_D = FOP(29, FMT_D),
+OPC_RSQRT1_D = FOP(30, FMT_D),
+OPC_RSQRT2_D = FOP(31, FMT_D),
+OPC_CVT_S_D = FOP(32, FMT_D),
+OPC_CVT_W_D = FOP(36, FMT_D),
+OPC_CVT_L_D = FOP(37, FMT_D),
+/* FOP(48..63, FMT_D) used for comparisons */
+
+OPC_CVT_S_W = FOP(32, FMT_W),
+OPC_CVT_D_W = FOP(33, FMT_W),
+OPC_CVT_S_L = FOP(32, FMT_L),
+OPC_CVT_D_L = FOP(33, FMT_L),
+OPC_CVT_PS_PW = FOP(38, FMT_W),
+
+OPC_ADD_PS = FOP(0, FMT_PS),
+OPC_SUB_PS = FOP(1, FMT_PS),
+OPC_MUL_PS = FOP(2, FMT_PS),
+OPC_DIV_PS = FOP(3, FMT_PS),
+OPC_ABS_PS = FOP(5, FMT_PS),
+OPC_MOV_PS = FOP(6, FMT_PS),
+OPC_NEG_PS = FOP(7, FMT_PS),
+OPC_MOVCF_PS = FOP(17, FMT_PS),
+OPC_MOVZ_PS = FOP(18, FMT_PS),
+OPC_MOVN_PS = FOP(19, FMT_PS),
+OPC_ADDR_PS = FOP(24, FMT_PS),
+OPC_MULR_PS = FOP(26, FMT_PS),
+OPC_RECIP2_PS = FOP(28, FMT_PS),
+OPC_RECIP1_PS = FOP(29, FMT_PS),
+OPC_RSQRT1_PS = FOP(30, FMT_PS),
+OPC_RSQRT2_PS = FOP(31, FMT_PS),
+
+OPC_CVT_S_PU = FOP(32, FMT_PS),
+OPC_CVT_PW_PS = FOP(36, FMT_PS),
+OPC_CVT_S_PL = FOP(40, FMT_PS),
+OPC_PLL_PS = FOP(44, FMT_PS),
+OPC_PLU_PS = FOP(45, FMT_PS),
+OPC_PUL_PS = FOP(46, FMT_PS),
+OPC_PUU_PS = FOP(47, FMT_PS),
+/* FOP(48..63, FMT_PS) used for comparisons */
+};
+
 static void gen_cp1 (DisasContext *ctx, uint32_t opc, int rt, int fs)
 {
 const char *opn = cp1 move;
@@ -5937,8 +6031,8 @@ static void gen_farith (DisasContext *ctx, uint32_t op1,
 enum { BINOP, CMPOP, OTHEROP } optype = OTHEROP;
 uint32_t func = ctx-opcode  0x3f;
 
-switch (ctx-opcode  FOP(0x3f, 0x1f)) {
-case FOP(0, 16):
+switch (opc) {
+case OPC_ADD_S:
 {
 TCGv_i32 fp0 = tcg_temp_new_i32();
 TCGv_i32 fp1 = tcg_temp_new_i32();
@@ -5953,7 +6047,7 @@ static void gen_farith (DisasContext *ctx, uint32_t op1,
 opn = add.s;
 optype = BINOP;
 break;
-case FOP(1, 16):
+case OPC_SUB_S:
 {
 TCGv_i32 fp0 = tcg_temp_new_i32();
 TCGv_i32 fp1 = tcg_temp_new_i32();
@@ -5968,7 +6062,7 @@ static void gen_farith (DisasContext *ctx, uint32_t op1,
 opn = sub.s;
 optype = BINOP;
 break;
-case FOP(2, 16):
+case OPC_MUL_S:
 {
 TCGv_i32 fp0 = tcg_temp_new_i32();
 TCGv_i32 fp1 = tcg_temp_new_i32();
@@ -5983,7 +6077,7 @@ static void gen_farith (DisasContext *ctx, uint32_t op1,
 opn = mul.s;
 optype = BINOP;
 break;
-case FOP(3, 16):
+case OPC_DIV_S:
 {
 TCGv_i32 fp0

[Qemu-devel] [PATCH 01/10] target-mips: break out [ls][wd]c1 and rdhwr insn generation

2010-05-24 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/translate.c |  106 ++-
 1 files changed, 59 insertions(+), 47 deletions(-)

diff --git a/target-mips/translate.c b/target-mips/translate.c
index c95ecb1..2075d09 100644
--- a/target-mips/translate.c
+++ b/target-mips/translate.c
@@ -1220,6 +1220,17 @@ static void gen_flt_ldst (DisasContext *ctx, uint32_t 
opc, int ft,
 tcg_temp_free(t0);
 }
 
+static void gen_cop1_ldst(CPUState *env, DisasContext *ctx,
+  uint32_t op, int rt, int rs, int16_t imm)
+{
+if (env-CP0_Config1  (1  CP0C1_FP)) {
+check_cp1_enabled(ctx);
+gen_flt_ldst(ctx, op, rt, rs, imm);
+} else {
+generate_exception_err(ctx, EXCP_CpU, 1);
+}
+}
+
 /* Arithmetic with immediate operand */
 static void gen_arith_imm (CPUState *env, DisasContext *ctx, uint32_t opc,
int rt, int rs, int16_t imm)
@@ -7528,6 +7539,52 @@ static void gen_flt3_arith (DisasContext *ctx, uint32_t 
opc,
fregnames[fs], fregnames[ft]);
 }
 
+static void
+gen_rdhwr (CPUState *env, DisasContext *ctx, int rt, int rd)
+{
+TCGv t0;
+
+check_insn(env, ctx, ISA_MIPS32R2);
+t0 = tcg_temp_new();
+
+switch (rd) {
+case 0:
+save_cpu_state(ctx, 1);
+gen_helper_rdhwr_cpunum(t0);
+gen_store_gpr(t0, rt);
+break;
+case 1:
+save_cpu_state(ctx, 1);
+gen_helper_rdhwr_synci_step(t0);
+gen_store_gpr(t0, rt);
+break;
+case 2:
+save_cpu_state(ctx, 1);
+gen_helper_rdhwr_cc(t0);
+gen_store_gpr(t0, rt);
+break;
+case 3:
+save_cpu_state(ctx, 1);
+gen_helper_rdhwr_ccres(t0);
+gen_store_gpr(t0, rt);
+break;
+case 29:
+#if defined(CONFIG_USER_ONLY)
+tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, tls_value));
+gen_store_gpr(t0, rt);
+break;
+#else
+/* XXX: Some CPUs implement this in hardware.
+   Not supported yet. */
+#endif
+default:/* Invalid */
+MIPS_INVAL(rdhwr);
+generate_exception(ctx, EXCP_RI);
+break;
+}
+tcg_temp_free(t0);
+}
+
 static void handle_delay_slot (CPUState *env, DisasContext *ctx,
int insn_bytes)
 {
@@ -8999,47 +9056,7 @@ static void decode_opc (CPUState *env, DisasContext 
*ctx, int *is_branch)
 gen_bshfl(ctx, op2, rt, rd);
 break;
 case OPC_RDHWR:
-check_insn(env, ctx, ISA_MIPS32R2);
-{
-TCGv t0 = tcg_temp_new();
-
-switch (rd) {
-case 0:
-save_cpu_state(ctx, 1);
-gen_helper_rdhwr_cpunum(t0);
-gen_store_gpr(t0, rt);
-break;
-case 1:
-save_cpu_state(ctx, 1);
-gen_helper_rdhwr_synci_step(t0);
-gen_store_gpr(t0, rt);
-break;
-case 2:
-save_cpu_state(ctx, 1);
-gen_helper_rdhwr_cc(t0);
-gen_store_gpr(t0, rt);
-break;
-case 3:
-save_cpu_state(ctx, 1);
-gen_helper_rdhwr_ccres(t0);
-gen_store_gpr(t0, rt);
-break;
-case 29:
-#if defined(CONFIG_USER_ONLY)
-tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, tls_value));
-gen_store_gpr(t0, rt);
-break;
-#else
-/* XXX: Some CPUs implement this in hardware.
-   Not supported yet. */
-#endif
-default:/* Invalid */
-MIPS_INVAL(rdhwr);
-generate_exception(ctx, EXCP_RI);
-break;
-}
-tcg_temp_free(t0);
-}
+gen_rdhwr(env, ctx, rt, rd);
 break;
 case OPC_FORK:
 check_insn(env, ctx, ASE_MT);
@@ -9242,12 +9259,7 @@ static void decode_opc (CPUState *env, DisasContext 
*ctx, int *is_branch)
 case OPC_LDC1:
 case OPC_SWC1:
 case OPC_SDC1:
-if (env-CP0_Config1  (1  CP0C1_FP)) {
-check_cp1_enabled(ctx);
-gen_flt_ldst(ctx, op, rt, rs, imm);
-} else {
-generate_exception_err(ctx, EXCP_CpU, 1);
-}
+gen_cop1_ldst(env, ctx, op, rt, rs, imm);
 break;
 
 case OPC_CP1:
-- 
1.6.3.2




[Qemu-devel] [PATCH 05/10] target-mips: small changes to use new FMT_ enums

2010-05-24 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/translate.c |   17 +
 1 files changed, 9 insertions(+), 8 deletions(-)

diff --git a/target-mips/translate.c b/target-mips/translate.c
index 63844b8..cc445fb 100644
--- a/target-mips/translate.c
+++ b/target-mips/translate.c
@@ -359,7 +359,8 @@ enum {
 /* 0 - 15 are reserved */
 FMT_S = 16,
 FMT_D = 17,
-/* 18 - 19 are reserved */
+FMT_E = 18,
+FMT_Q = 19,
 FMT_W = 20,
 FMT_L = 21,
 FMT_PS = 22,
@@ -378,13 +379,13 @@ enum {
 OPC_BC1  = (0x08  21) | OPC_CP1, /* bc */
 OPC_BC1ANY2  = (0x09  21) | OPC_CP1,
 OPC_BC1ANY4  = (0x0A  21) | OPC_CP1,
-OPC_S_FMT= (0x10  21) | OPC_CP1, /* 16: fmt=single fp */
-OPC_D_FMT= (0x11  21) | OPC_CP1, /* 17: fmt=double fp */
-OPC_E_FMT= (0x12  21) | OPC_CP1, /* 18: fmt=extended fp */
-OPC_Q_FMT= (0x13  21) | OPC_CP1, /* 19: fmt=quad fp */
-OPC_W_FMT= (0x14  21) | OPC_CP1, /* 20: fmt=32bit fixed */
-OPC_L_FMT= (0x15  21) | OPC_CP1, /* 21: fmt=64bit fixed */
-OPC_PS_FMT   = (0x16  21) | OPC_CP1, /* 22: fmt=paired single fp */
+OPC_S_FMT= (FMT_S  21) | OPC_CP1,  /* 16: fmt=single fp */
+OPC_D_FMT= (FMT_D  21) | OPC_CP1,  /* 17: fmt=double fp */
+OPC_E_FMT= (FMT_E  21) | OPC_CP1,  /* 18: fmt=extended fp */
+OPC_Q_FMT= (FMT_Q  21) | OPC_CP1,  /* 19: fmt=quad fp */
+OPC_W_FMT= (FMT_W  21) | OPC_CP1,  /* 20: fmt=32bit fixed */
+OPC_L_FMT= (FMT_L  21) | OPC_CP1,  /* 21: fmt=64bit fixed */
+OPC_PS_FMT   = (FMT_PS  21) | OPC_CP1, /* 22: fmt=paired single fp */
 };
 
 #define MASK_CP1_FUNC(op)   MASK_CP1(op) | (op  0x3F)
-- 
1.6.3.2




[Qemu-devel] [PATCH 04/10] target-mips: refactor {c, abs}.cond.fmt insns

2010-05-24 Thread Nathan Froyd
Move all knowledge about coprocessor-checking and register numbering
into the gen_cmp* helper functions.

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/translate.c |  174 --
 1 files changed, 91 insertions(+), 83 deletions(-)

diff --git a/target-mips/translate.c b/target-mips/translate.c
index 2568e16..63844b8 100644
--- a/target-mips/translate.c
+++ b/target-mips/translate.c
@@ -354,6 +354,18 @@ enum {
 /* Coprocessor 1 (rs field) */
 #define MASK_CP1(op)   MASK_OP_MAJOR(op) | (op  (0x1F  21))
 
+/* Values for the fmt field in FP instructions */
+enum {
+/* 0 - 15 are reserved */
+FMT_S = 16,
+FMT_D = 17,
+/* 18 - 19 are reserved */
+FMT_W = 20,
+FMT_L = 21,
+FMT_PS = 22,
+/* 23 - 31 are reserved */
+};
+
 enum {
 OPC_MFC1 = (0x00  21) | OPC_CP1,
 OPC_DMFC1= (0x01  21) | OPC_CP1,
@@ -663,39 +675,6 @@ static inline int get_fp_bit (int cc)
 return 23;
 }
 
-#define FOP_CONDS(type, fmt, bits)\
-static inline void gen_cmp ## type ## _ ## fmt(int n, TCGv_i##bits a, \
-   TCGv_i##bits b, int cc)\
-{ \
-switch (n) {  \
-case  0: gen_helper_2i(cmp ## type ## _ ## fmt ## _f, a, b, cc);break;\
-case  1: gen_helper_2i(cmp ## type ## _ ## fmt ## _un, a, b, cc);   break;\
-case  2: gen_helper_2i(cmp ## type ## _ ## fmt ## _eq, a, b, cc);   break;\
-case  3: gen_helper_2i(cmp ## type ## _ ## fmt ## _ueq, a, b, cc);  break;\
-case  4: gen_helper_2i(cmp ## type ## _ ## fmt ## _olt, a, b, cc);  break;\
-case  5: gen_helper_2i(cmp ## type ## _ ## fmt ## _ult, a, b, cc);  break;\
-case  6: gen_helper_2i(cmp ## type ## _ ## fmt ## _ole, a, b, cc);  break;\
-case  7: gen_helper_2i(cmp ## type ## _ ## fmt ## _ule, a, b, cc);  break;\
-case  8: gen_helper_2i(cmp ## type ## _ ## fmt ## _sf, a, b, cc);   break;\
-case  9: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngle, a, b, cc); break;\
-case 10: gen_helper_2i(cmp ## type ## _ ## fmt ## _seq, a, b, cc);  break;\
-case 11: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngl, a, b, cc);  break;\
-case 12: gen_helper_2i(cmp ## type ## _ ## fmt ## _lt, a, b, cc);   break;\
-case 13: gen_helper_2i(cmp ## type ## _ ## fmt ## _nge, a, b, cc);  break;\
-case 14: gen_helper_2i(cmp ## type ## _ ## fmt ## _le, a, b, cc);   break;\
-case 15: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngt, a, b, cc);  break;\
-default: abort(); \
-} \
-}
-
-FOP_CONDS(, d, 64)
-FOP_CONDS(abs, d, 64)
-FOP_CONDS(, s, 32)
-FOP_CONDS(abs, s, 32)
-FOP_CONDS(, ps, 64)
-FOP_CONDS(abs, ps, 64)
-#undef FOP_CONDS
-
 /* Tests */
 static inline void gen_save_pc(target_ulong pc)
 {
@@ -836,6 +815,67 @@ static inline void check_mips_64(DisasContext *ctx)
 generate_exception(ctx, EXCP_RI);
 }
 
+/* Define small wrappers for gen_load_fpr* so that we have a uniform
+   calling interface for 32 and 64-bit FPRs.  No sense in changing
+   all callers for gen_load_fpr32 when we need the CTX parameter for
+   this one use.  */
+#define gen_ldcmp_fpr32(ctx, x, y) gen_load_fpr32(x, y)
+#define gen_ldcmp_fpr64(ctx, x, y) gen_load_fpr64(ctx, x, y)
+#define FOP_CONDS(type, abs, fmt, ifmt, bits) \
+static inline void gen_cmp ## type ## _ ## fmt(DisasContext *ctx, int n,  \
+   int ft, int fs, int cc)\
+{ \
+TCGv_i##bits fp0 = tcg_temp_new_i##bits ();   \
+TCGv_i##bits fp1 = tcg_temp_new_i##bits ();   \
+switch (ifmt) {   \
+case FMT_PS:  \
+check_cp1_64bitmode(ctx); \
+break;\
+case FMT_D:   \
+if (abs)  \
+check_cop1x(ctx); \
+check_cp1_registers(ctx, fs | ft);\
+break;\
+case FMT_S:   \
+if (abs)  \
+check_cop1x(ctx

[Qemu-devel] [PATCH 00/10] target-mips: add microMIPS ASE support, v2

2010-05-24 Thread Nathan Froyd
This patch series adds support for the microMIPS ASE.  microMIPS is a
new ASE similar to MIPS16, but re-encodes the entire instruction set
into 16-bit and 32-bit instructions--in contrast to MIPS16, which
re-encodes only integer instructions.  The mechanisms for going in and
out of microMIPS mode are identical to those for MIPS16; a given chip
cannot support both ASEs simultaneously.

changes from v1:
  fix re-introduction of previously deleted code noted by rth

Nathan Froyd (10):
  target-mips: break out [ls][wd]c1 and rdhwr insn generation
  target-mips: add microMIPS-specific bits to mips-defs.h
  target-mips: add enum constants for various invocations of FOP
  target-mips: refactor {c,abs}.cond.fmt insns
  target-mips: small changes to use new FMT_ enums
  target-mips: add microMIPS ASE support
  target-mips: add microMIPS CPUs
  target-mips: add microMIPS exception handler support
  linux-user: honor low bit of entry PC for MIPS
  hw: honor low bit in mipssim machine

 hw/mips_mipssim.c|4 +-
 linux-user/main.c|4 +-
 target-mips/cpu.h|3 +
 target-mips/helper.c |   21 +-
 target-mips/helper.h |9 +
 target-mips/mips-defs.h  |1 +
 target-mips/op_helper.c  |  136 ++
 target-mips/translate.c  | 3050 ++
 target-mips/translate_init.c |   61 +
 9 files changed, 3047 insertions(+), 242 deletions(-)




[Qemu-devel] [PATCH 10/10] hw: honor low bit in mipssim machine

2010-05-24 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 hw/mips_mipssim.c |4 +++-
 1 files changed, 3 insertions(+), 1 deletions(-)

diff --git a/hw/mips_mipssim.c b/hw/mips_mipssim.c
index a747de5..cd6c2be 100644
--- a/hw/mips_mipssim.c
+++ b/hw/mips_mipssim.c
@@ -106,7 +106,9 @@ static void main_cpu_reset(void *opaque)
 CPUState *env = s-env;
 
 cpu_reset(env);
-env-active_tc.PC = s-vector;
+env-active_tc.PC = s-vector  ~(target_ulong)1;
+if (s-vector  1)
+env-hflags |= MIPS_HFLAG_M16;
 }
 
 static void
-- 
1.6.3.2




[Qemu-devel] [PATCH 08/10] target-mips: add microMIPS exception handler support

2010-05-24 Thread Nathan Froyd
Unlike MIPS16, microMIPS lets you choose the ISA mode for your exception
handlers.

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/helper.c |   21 +++--
 1 files changed, 15 insertions(+), 6 deletions(-)

diff --git a/target-mips/helper.c b/target-mips/helper.c
index 8102f03..90c3b3a 100644
--- a/target-mips/helper.c
+++ b/target-mips/helper.c
@@ -385,6 +385,18 @@ static target_ulong exception_resume_pc (CPUState *env)
 
 return bad_pc;
 }
+static void set_hflags_for_handler (CPUState *env)
+{
+/* Exception handlers are entered in 32-bit mode.  */
+env-hflags = ~(MIPS_HFLAG_M16);
+/* ...except that microMIPS lets you choose.  */
+if (env-insn_flags  ASE_MICROMIPS) {
+env-hflags |= (!!(env-CP0_Config3
+(1  CP0C3_ISA_ON_EXC))
+ MIPS_HFLAG_M16_SHIFT);
+}
+}
+
 #endif
 
 void do_interrupt (CPUState *env)
@@ -440,8 +452,7 @@ void do_interrupt (CPUState *env)
 if (!(env-CP0_Status  (1  CP0St_EXL)))
 env-CP0_Cause = ~(1  CP0Ca_BD);
 env-active_tc.PC = (int32_t)0xBFC00480;
-/* Exception handlers are entered in 32-bit mode.  */
-env-hflags = ~(MIPS_HFLAG_M16);
+set_hflags_for_handler(env);
 break;
 case EXCP_RESET:
 cpu_reset(env);
@@ -461,8 +472,7 @@ void do_interrupt (CPUState *env)
 if (!(env-CP0_Status  (1  CP0St_EXL)))
 env-CP0_Cause = ~(1  CP0Ca_BD);
 env-active_tc.PC = (int32_t)0xBFC0;
-/* Exception handlers are entered in 32-bit mode.  */
-env-hflags = ~(MIPS_HFLAG_M16);
+set_hflags_for_handler(env);
 break;
 case EXCP_EXT_INTERRUPT:
 cause = 0;
@@ -581,8 +591,7 @@ void do_interrupt (CPUState *env)
 env-active_tc.PC = (int32_t)(env-CP0_EBase  ~0x3ff);
 }
 env-active_tc.PC += offset;
-/* Exception handlers are entered in 32-bit mode.  */
-env-hflags = ~(MIPS_HFLAG_M16);
+set_hflags_for_handler(env);
 env-CP0_Cause = (env-CP0_Cause  ~(0x1f  CP0Ca_EC)) | (cause  
CP0Ca_EC);
 break;
 default:
-- 
1.6.3.2




[Qemu-devel] [PATCH 07/10] target-mips: add microMIPS CPUs

2010-05-24 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/translate_init.c |   61 ++
 1 files changed, 61 insertions(+), 0 deletions(-)

diff --git a/target-mips/translate_init.c b/target-mips/translate_init.c
index b79ed56..8e17f4b 100644
--- a/target-mips/translate_init.c
+++ b/target-mips/translate_init.c
@@ -141,6 +141,25 @@ static const mips_def_t mips_defs[] =
 .mmu_type = MMU_TYPE_FMT,
 },
 {
+.name = 4Km-micromips,
+.CP0_PRid = 0x00018300,
+/* Config1 implemented, fixed mapping MMU,
+   no virtual icache, uncached coherency. */
+.CP0_Config0 = MIPS_CONFIG0 | (MMU_TYPE_FMT  CP0C0_MT),
+.CP0_Config1 = MIPS_CONFIG1 |
+   (0  CP0C1_IS) | (3  CP0C1_IL) | (1  CP0C1_IA) |
+   (0  CP0C1_DS) | (3  CP0C1_DL) | (1  CP0C1_DA),
+.CP0_Config2 = MIPS_CONFIG2,
+.CP0_Config3 = MIPS_CONFIG3,
+.SYNCI_Step = 32,
+.CCRes = 2,
+.CP0_Status_rw_bitmask = 0x1258FF17,
+.SEGBITS = 32,
+.PABITS = 32,
+.insn_flags = CPU_MIPS32R2 | ASE_MICROMIPS,
+.mmu_type = MMU_TYPE_FMT,
+},
+{
 .name = 4KEcR1,
 .CP0_PRid = 0x00018400,
 .CP0_Config0 = MIPS_CONFIG0 | (MMU_TYPE_R4000  CP0C0_MT),
@@ -245,6 +264,25 @@ static const mips_def_t mips_defs[] =
 .mmu_type = MMU_TYPE_R4000,
 },
 {
+.name = 24Kc-micromips,
+.CP0_PRid = 0x00019300,
+.CP0_Config0 = MIPS_CONFIG0 | (0x1  CP0C0_AR) |
+(MMU_TYPE_R4000  CP0C0_MT),
+.CP0_Config1 = MIPS_CONFIG1 | (15  CP0C1_MMU) |
+   (0  CP0C1_IS) | (3  CP0C1_IL) | (1  CP0C1_IA) |
+   (0  CP0C1_DS) | (3  CP0C1_DL) | (1  CP0C1_DA),
+.CP0_Config2 = MIPS_CONFIG2,
+.CP0_Config3 = MIPS_CONFIG3 | (0  CP0C3_VInt),
+.SYNCI_Step = 32,
+.CCRes = 2,
+/* No DSP implemented. */
+.CP0_Status_rw_bitmask = 0x1278FF1F,
+.SEGBITS = 32,
+.PABITS = 32,
+.insn_flags = CPU_MIPS32R2 | ASE_MICROMIPS,
+.mmu_type = MMU_TYPE_R4000,
+},
+{
 .name = 24Kf,
 .CP0_PRid = 0x00019300,
 .CP0_Config0 = MIPS_CONFIG0 | (0x1  CP0C0_AR) |
@@ -269,6 +307,29 @@ static const mips_def_t mips_defs[] =
 .mmu_type = MMU_TYPE_R4000,
 },
 {
+.name = 24Kf-micromips,
+.CP0_PRid = 0x00019300,
+.CP0_Config0 = MIPS_CONFIG0 | (0x1  CP0C0_AR) |
+(MMU_TYPE_R4000  CP0C0_MT),
+.CP0_Config1 = MIPS_CONFIG1 | (1  CP0C1_FP) | (15  CP0C1_MMU) |
+   (0  CP0C1_IS) | (3  CP0C1_IL) | (1  CP0C1_IA) |
+   (0  CP0C1_DS) | (3  CP0C1_DL) | (1  CP0C1_DA),
+.CP0_Config2 = MIPS_CONFIG2,
+.CP0_Config3 = MIPS_CONFIG3 | (0  CP0C3_VInt),
+.CP0_LLAddr_rw_bitmask = 0,
+.CP0_LLAddr_shift = 4,
+.SYNCI_Step = 32,
+.CCRes = 2,
+/* No DSP implemented. */
+.CP0_Status_rw_bitmask = 0x3678FF1F,
+.CP1_fcr0 = (1  FCR0_F64) | (1  FCR0_L) | (1  FCR0_W) |
+(1  FCR0_D) | (1  FCR0_S) | (0x93  FCR0_PRID),
+.SEGBITS = 32,
+.PABITS = 32,
+.insn_flags = CPU_MIPS32R2 | ASE_MICROMIPS,
+.mmu_type = MMU_TYPE_R4000,
+},
+{
 .name = 34Kf,
 .CP0_PRid = 0x00019500,
 .CP0_Config0 = MIPS_CONFIG0 | (0x1  CP0C0_AR) |
-- 
1.6.3.2




[Qemu-devel] [PATCH 09/10] linux-user: honor low bit of entry PC for MIPS

2010-05-24 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 linux-user/main.c |4 +++-
 1 files changed, 3 insertions(+), 1 deletions(-)

diff --git a/linux-user/main.c b/linux-user/main.c
index 18b52c0..76d443b 100644
--- a/linux-user/main.c
+++ b/linux-user/main.c
@@ -3192,7 +3192,9 @@ int main(int argc, char **argv, char **envp)
 for(i = 0; i  32; i++) {
 env-active_tc.gpr[i] = regs-regs[i];
 }
-env-active_tc.PC = regs-cp0_epc;
+env-active_tc.PC = regs-cp0_epc  ~(target_ulong)1;
+if (regs-cp0_epc  1)
+env-hflags |= MIPS_HFLAG_M16;
 }
 #elif defined(TARGET_SH4)
 {
-- 
1.6.3.2




[Qemu-devel] [PATCH 02/10] target-mips: add microMIPS-specific bits to mips-defs.h

2010-05-20 Thread Nathan Froyd
There's a new ASE_MICROMIPS instruction flag, and some extra CP0_Config3
fields.  The ISA and ISA_ON_EXC fields are specific to microMIPS.  The
DSP2P is for version 2 of the DSP ASE.

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/cpu.h   |3 +++
 target-mips/mips-defs.h |1 +
 2 files changed, 4 insertions(+), 0 deletions(-)

diff --git a/target-mips/cpu.h b/target-mips/cpu.h
index 7285636..986d938 100644
--- a/target-mips/cpu.h
+++ b/target-mips/cpu.h
@@ -363,6 +363,9 @@ struct CPUMIPSState {
 #define CP0C2_SA   0
 int32_t CP0_Config3;
 #define CP0C3_M31
+#define CP0C3_ISA_ON_EXC 16
+#define CP0C3_ISA  14
+#define CP0C3_DSP2P 11
 #define CP0C3_DSPP 10
 #define CP0C3_LPA  7
 #define CP0C3_VEIC 6
diff --git a/target-mips/mips-defs.h b/target-mips/mips-defs.h
index c57de02..a7f4697 100644
--- a/target-mips/mips-defs.h
+++ b/target-mips/mips-defs.h
@@ -38,6 +38,7 @@
 #defineASE_DSPR2   0x0001
 #defineASE_MT  0x0002
 #defineASE_SMARTMIPS   0x0004
+#defineASE_MICROMIPS   0x0008
 
 /* Chip specific instructions. */
 #defineINSN_VR54XX 0x8000
-- 
1.6.3.2




[Qemu-devel] [PATCH 10/10] hw: honor low bit in mipssim machine

2010-05-20 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 hw/mips_mipssim.c |4 +++-
 1 files changed, 3 insertions(+), 1 deletions(-)

diff --git a/hw/mips_mipssim.c b/hw/mips_mipssim.c
index a747de5..cd6c2be 100644
--- a/hw/mips_mipssim.c
+++ b/hw/mips_mipssim.c
@@ -106,7 +106,9 @@ static void main_cpu_reset(void *opaque)
 CPUState *env = s-env;
 
 cpu_reset(env);
-env-active_tc.PC = s-vector;
+env-active_tc.PC = s-vector  ~(target_ulong)1;
+if (s-vector  1)
+env-hflags |= MIPS_HFLAG_M16;
 }
 
 static void
-- 
1.6.3.2




[Qemu-devel] [PATCH 00/10] target-mips: add microMIPS ASE support

2010-05-20 Thread Nathan Froyd
This patch series adds support for the microMIPS ASE.  microMIPS is a
new ASE similar to MIPS16, but re-encodes the entire instruction set
into 16-bit and 32-bit instructions--in contrast to MIPS16, which
re-encodes only integer instructions.  The mechanisms for going in and
out of microMIPS mode are identical to those for MIPS16; a given chip
cannot support both ASEs simultaneously.

The first half of the series consists of small refactorings to make it
easier to delegate microMIPS instruction decoding to the usual gen_*
functions.  The second half adds support for microMIPS in all the
necessary places.

The patch has been tested extensively in our QEMU tree; this patch has
been tested against our compilers (GNU/Linux emulation), which include
microMIPS support.  We have obtained identical test results for MIPS32
and microMIPS testing.  (The microMIPS patch for binutils has been
posted upstream; the microMIPS patch for GCC is forthcoming.)  It is
possible to boot kernels compiled for microMIPS, but we have been
unsuccessful in consistently being able to do so, and have not yet
tracked down the root issue(s).

Nathan Froyd (10):
  target-mips: break out [ls][wd]c1 and rdhwr insn generation
  target-mips: add microMIPS-specific bits to mips-defs.h
  target-mips: add enum constants for various invocations of FOP
  target-mips: refactor {c,abs}.cond.fmt insns
  target-mips: small changes to use new FMT_ enums
  target-mips: add microMIPS ASE support
  target-mips: add microMIPS CPUs
  target-mips: add microMIPS exception handler support
  linux-user: honor low bit of entry PC for MIPS
  hw: honor low bit in mipssim machine

 hw/mips_mipssim.c|4 +-
 linux-user/main.c|4 +-
 target-mips/cpu.h|3 +
 target-mips/helper.c |   21 +-
 target-mips/helper.h |9 +
 target-mips/mips-defs.h  |1 +
 target-mips/op_helper.c  |  136 ++
 target-mips/translate.c  | 3050 ++
 target-mips/translate_init.c |   61 +
 9 files changed, 3047 insertions(+), 242 deletions(-)




[Qemu-devel] [PATCH 07/10] target-mips: add microMIPS CPUs

2010-05-20 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/translate_init.c |   61 ++
 1 files changed, 61 insertions(+), 0 deletions(-)

diff --git a/target-mips/translate_init.c b/target-mips/translate_init.c
index b79ed56..8e17f4b 100644
--- a/target-mips/translate_init.c
+++ b/target-mips/translate_init.c
@@ -141,6 +141,25 @@ static const mips_def_t mips_defs[] =
 .mmu_type = MMU_TYPE_FMT,
 },
 {
+.name = 4Km-micromips,
+.CP0_PRid = 0x00018300,
+/* Config1 implemented, fixed mapping MMU,
+   no virtual icache, uncached coherency. */
+.CP0_Config0 = MIPS_CONFIG0 | (MMU_TYPE_FMT  CP0C0_MT),
+.CP0_Config1 = MIPS_CONFIG1 |
+   (0  CP0C1_IS) | (3  CP0C1_IL) | (1  CP0C1_IA) |
+   (0  CP0C1_DS) | (3  CP0C1_DL) | (1  CP0C1_DA),
+.CP0_Config2 = MIPS_CONFIG2,
+.CP0_Config3 = MIPS_CONFIG3,
+.SYNCI_Step = 32,
+.CCRes = 2,
+.CP0_Status_rw_bitmask = 0x1258FF17,
+.SEGBITS = 32,
+.PABITS = 32,
+.insn_flags = CPU_MIPS32R2 | ASE_MICROMIPS,
+.mmu_type = MMU_TYPE_FMT,
+},
+{
 .name = 4KEcR1,
 .CP0_PRid = 0x00018400,
 .CP0_Config0 = MIPS_CONFIG0 | (MMU_TYPE_R4000  CP0C0_MT),
@@ -245,6 +264,25 @@ static const mips_def_t mips_defs[] =
 .mmu_type = MMU_TYPE_R4000,
 },
 {
+.name = 24Kc-micromips,
+.CP0_PRid = 0x00019300,
+.CP0_Config0 = MIPS_CONFIG0 | (0x1  CP0C0_AR) |
+(MMU_TYPE_R4000  CP0C0_MT),
+.CP0_Config1 = MIPS_CONFIG1 | (15  CP0C1_MMU) |
+   (0  CP0C1_IS) | (3  CP0C1_IL) | (1  CP0C1_IA) |
+   (0  CP0C1_DS) | (3  CP0C1_DL) | (1  CP0C1_DA),
+.CP0_Config2 = MIPS_CONFIG2,
+.CP0_Config3 = MIPS_CONFIG3 | (0  CP0C3_VInt),
+.SYNCI_Step = 32,
+.CCRes = 2,
+/* No DSP implemented. */
+.CP0_Status_rw_bitmask = 0x1278FF1F,
+.SEGBITS = 32,
+.PABITS = 32,
+.insn_flags = CPU_MIPS32R2 | ASE_MICROMIPS,
+.mmu_type = MMU_TYPE_R4000,
+},
+{
 .name = 24Kf,
 .CP0_PRid = 0x00019300,
 .CP0_Config0 = MIPS_CONFIG0 | (0x1  CP0C0_AR) |
@@ -269,6 +307,29 @@ static const mips_def_t mips_defs[] =
 .mmu_type = MMU_TYPE_R4000,
 },
 {
+.name = 24Kf-micromips,
+.CP0_PRid = 0x00019300,
+.CP0_Config0 = MIPS_CONFIG0 | (0x1  CP0C0_AR) |
+(MMU_TYPE_R4000  CP0C0_MT),
+.CP0_Config1 = MIPS_CONFIG1 | (1  CP0C1_FP) | (15  CP0C1_MMU) |
+   (0  CP0C1_IS) | (3  CP0C1_IL) | (1  CP0C1_IA) |
+   (0  CP0C1_DS) | (3  CP0C1_DL) | (1  CP0C1_DA),
+.CP0_Config2 = MIPS_CONFIG2,
+.CP0_Config3 = MIPS_CONFIG3 | (0  CP0C3_VInt),
+.CP0_LLAddr_rw_bitmask = 0,
+.CP0_LLAddr_shift = 4,
+.SYNCI_Step = 32,
+.CCRes = 2,
+/* No DSP implemented. */
+.CP0_Status_rw_bitmask = 0x3678FF1F,
+.CP1_fcr0 = (1  FCR0_F64) | (1  FCR0_L) | (1  FCR0_W) |
+(1  FCR0_D) | (1  FCR0_S) | (0x93  FCR0_PRID),
+.SEGBITS = 32,
+.PABITS = 32,
+.insn_flags = CPU_MIPS32R2 | ASE_MICROMIPS,
+.mmu_type = MMU_TYPE_R4000,
+},
+{
 .name = 34Kf,
 .CP0_PRid = 0x00019500,
 .CP0_Config0 = MIPS_CONFIG0 | (0x1  CP0C0_AR) |
-- 
1.6.3.2




[Qemu-devel] [PATCH 05/10] target-mips: small changes to use new FMT_ enums

2010-05-20 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/translate.c |   17 +
 1 files changed, 9 insertions(+), 8 deletions(-)

diff --git a/target-mips/translate.c b/target-mips/translate.c
index 8a7f3e9..c42d8dd 100644
--- a/target-mips/translate.c
+++ b/target-mips/translate.c
@@ -359,7 +359,8 @@ enum {
 /* 0 - 15 are reserved */
 FMT_S = 16,
 FMT_D = 17,
-/* 18 - 19 are reserved */
+FMT_E = 18,
+FMT_Q = 19,
 FMT_W = 20,
 FMT_L = 21,
 FMT_PS = 22,
@@ -378,13 +379,13 @@ enum {
 OPC_BC1  = (0x08  21) | OPC_CP1, /* bc */
 OPC_BC1ANY2  = (0x09  21) | OPC_CP1,
 OPC_BC1ANY4  = (0x0A  21) | OPC_CP1,
-OPC_S_FMT= (0x10  21) | OPC_CP1, /* 16: fmt=single fp */
-OPC_D_FMT= (0x11  21) | OPC_CP1, /* 17: fmt=double fp */
-OPC_E_FMT= (0x12  21) | OPC_CP1, /* 18: fmt=extended fp */
-OPC_Q_FMT= (0x13  21) | OPC_CP1, /* 19: fmt=quad fp */
-OPC_W_FMT= (0x14  21) | OPC_CP1, /* 20: fmt=32bit fixed */
-OPC_L_FMT= (0x15  21) | OPC_CP1, /* 21: fmt=64bit fixed */
-OPC_PS_FMT   = (0x16  21) | OPC_CP1, /* 22: fmt=paired single fp */
+OPC_S_FMT= (FMT_S  21) | OPC_CP1,  /* 16: fmt=single fp */
+OPC_D_FMT= (FMT_D  21) | OPC_CP1,  /* 17: fmt=double fp */
+OPC_E_FMT= (FMT_E  21) | OPC_CP1,  /* 18: fmt=extended fp */
+OPC_Q_FMT= (FMT_Q  21) | OPC_CP1,  /* 19: fmt=quad fp */
+OPC_W_FMT= (FMT_W  21) | OPC_CP1,  /* 20: fmt=32bit fixed */
+OPC_L_FMT= (FMT_L  21) | OPC_CP1,  /* 21: fmt=64bit fixed */
+OPC_PS_FMT   = (FMT_PS  21) | OPC_CP1, /* 22: fmt=paired single fp */
 };
 
 #define MASK_CP1_FUNC(op)   MASK_CP1(op) | (op  0x3F)
-- 
1.6.3.2




[Qemu-devel] [PATCH 01/10] target-mips: break out [ls][wd]c1 and rdhwr insn generation

2010-05-20 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 target-mips/translate.c |  106 ++-
 1 files changed, 59 insertions(+), 47 deletions(-)

diff --git a/target-mips/translate.c b/target-mips/translate.c
index c95ecb1..2075d09 100644
--- a/target-mips/translate.c
+++ b/target-mips/translate.c
@@ -1220,6 +1220,17 @@ static void gen_flt_ldst (DisasContext *ctx, uint32_t 
opc, int ft,
 tcg_temp_free(t0);
 }
 
+static void gen_cop1_ldst(CPUState *env, DisasContext *ctx,
+  uint32_t op, int rt, int rs, int16_t imm)
+{
+if (env-CP0_Config1  (1  CP0C1_FP)) {
+check_cp1_enabled(ctx);
+gen_flt_ldst(ctx, op, rt, rs, imm);
+} else {
+generate_exception_err(ctx, EXCP_CpU, 1);
+}
+}
+
 /* Arithmetic with immediate operand */
 static void gen_arith_imm (CPUState *env, DisasContext *ctx, uint32_t opc,
int rt, int rs, int16_t imm)
@@ -7528,6 +7539,52 @@ static void gen_flt3_arith (DisasContext *ctx, uint32_t 
opc,
fregnames[fs], fregnames[ft]);
 }
 
+static void
+gen_rdhwr (CPUState *env, DisasContext *ctx, int rt, int rd)
+{
+TCGv t0;
+
+check_insn(env, ctx, ISA_MIPS32R2);
+t0 = tcg_temp_new();
+
+switch (rd) {
+case 0:
+save_cpu_state(ctx, 1);
+gen_helper_rdhwr_cpunum(t0);
+gen_store_gpr(t0, rt);
+break;
+case 1:
+save_cpu_state(ctx, 1);
+gen_helper_rdhwr_synci_step(t0);
+gen_store_gpr(t0, rt);
+break;
+case 2:
+save_cpu_state(ctx, 1);
+gen_helper_rdhwr_cc(t0);
+gen_store_gpr(t0, rt);
+break;
+case 3:
+save_cpu_state(ctx, 1);
+gen_helper_rdhwr_ccres(t0);
+gen_store_gpr(t0, rt);
+break;
+case 29:
+#if defined(CONFIG_USER_ONLY)
+tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, tls_value));
+gen_store_gpr(t0, rt);
+break;
+#else
+/* XXX: Some CPUs implement this in hardware.
+   Not supported yet. */
+#endif
+default:/* Invalid */
+MIPS_INVAL(rdhwr);
+generate_exception(ctx, EXCP_RI);
+break;
+}
+tcg_temp_free(t0);
+}
+
 static void handle_delay_slot (CPUState *env, DisasContext *ctx,
int insn_bytes)
 {
@@ -8999,47 +9056,7 @@ static void decode_opc (CPUState *env, DisasContext 
*ctx, int *is_branch)
 gen_bshfl(ctx, op2, rt, rd);
 break;
 case OPC_RDHWR:
-check_insn(env, ctx, ISA_MIPS32R2);
-{
-TCGv t0 = tcg_temp_new();
-
-switch (rd) {
-case 0:
-save_cpu_state(ctx, 1);
-gen_helper_rdhwr_cpunum(t0);
-gen_store_gpr(t0, rt);
-break;
-case 1:
-save_cpu_state(ctx, 1);
-gen_helper_rdhwr_synci_step(t0);
-gen_store_gpr(t0, rt);
-break;
-case 2:
-save_cpu_state(ctx, 1);
-gen_helper_rdhwr_cc(t0);
-gen_store_gpr(t0, rt);
-break;
-case 3:
-save_cpu_state(ctx, 1);
-gen_helper_rdhwr_ccres(t0);
-gen_store_gpr(t0, rt);
-break;
-case 29:
-#if defined(CONFIG_USER_ONLY)
-tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, tls_value));
-gen_store_gpr(t0, rt);
-break;
-#else
-/* XXX: Some CPUs implement this in hardware.
-   Not supported yet. */
-#endif
-default:/* Invalid */
-MIPS_INVAL(rdhwr);
-generate_exception(ctx, EXCP_RI);
-break;
-}
-tcg_temp_free(t0);
-}
+gen_rdhwr(env, ctx, rt, rd);
 break;
 case OPC_FORK:
 check_insn(env, ctx, ASE_MT);
@@ -9242,12 +9259,7 @@ static void decode_opc (CPUState *env, DisasContext 
*ctx, int *is_branch)
 case OPC_LDC1:
 case OPC_SWC1:
 case OPC_SDC1:
-if (env-CP0_Config1  (1  CP0C1_FP)) {
-check_cp1_enabled(ctx);
-gen_flt_ldst(ctx, op, rt, rs, imm);
-} else {
-generate_exception_err(ctx, EXCP_CpU, 1);
-}
+gen_cop1_ldst(env, ctx, op, rt, rs, imm);
 break;
 
 case OPC_CP1:
-- 
1.6.3.2




[Qemu-devel] [PATCH 09/10] linux-user: honor low bit of entry PC for MIPS

2010-05-20 Thread Nathan Froyd

Signed-off-by: Nathan Froyd froy...@codesourcery.com
---
 linux-user/main.c |4 +++-
 1 files changed, 3 insertions(+), 1 deletions(-)

diff --git a/linux-user/main.c b/linux-user/main.c
index 18b52c0..76d443b 100644
--- a/linux-user/main.c
+++ b/linux-user/main.c
@@ -3192,7 +3192,9 @@ int main(int argc, char **argv, char **envp)
 for(i = 0; i  32; i++) {
 env-active_tc.gpr[i] = regs-regs[i];
 }
-env-active_tc.PC = regs-cp0_epc;
+env-active_tc.PC = regs-cp0_epc  ~(target_ulong)1;
+if (regs-cp0_epc  1)
+env-hflags |= MIPS_HFLAG_M16;
 }
 #elif defined(TARGET_SH4)
 {
-- 
1.6.3.2




  1   2   >