Browse Source

[sim,xcc,pk,opcodes] static rounding modes for FP insns

Now, you can either use the RM in the FSR or specify it in the insn.

(Except for FP->int; no dynamic for that.)
cs250
Andrew Waterman 16 years ago
parent
commit
2c9a832352
  1. 1
      riscv/decode.h
  2. 274
      riscv/execute.h
  3. 4
      riscv/insns/add_d_rm.h
  4. 4
      riscv/insns/add_s_rm.h
  5. 5
      riscv/insns/cvt_d_l_rm.h
  6. 4
      riscv/insns/cvt_d_s_rm.h
  7. 4
      riscv/insns/cvt_d_w_rm.h
  8. 1
      riscv/insns/cvt_l_d_rm.h
  9. 1
      riscv/insns/cvt_l_s_rm.h
  10. 4
      riscv/insns/cvt_s_d_rm.h
  11. 5
      riscv/insns/cvt_s_l_rm.h
  12. 4
      riscv/insns/cvt_s_w_rm.h
  13. 1
      riscv/insns/cvt_w_d_rm.h
  14. 1
      riscv/insns/cvt_w_s_rm.h
  15. 5
      riscv/insns/cvtu_d_l_rm.h
  16. 4
      riscv/insns/cvtu_d_w_rm.h
  17. 1
      riscv/insns/cvtu_l_d_rm.h
  18. 1
      riscv/insns/cvtu_l_s_rm.h
  19. 5
      riscv/insns/cvtu_s_l_rm.h
  20. 4
      riscv/insns/cvtu_s_w_rm.h
  21. 1
      riscv/insns/cvtu_w_d_rm.h
  22. 1
      riscv/insns/cvtu_w_s_rm.h
  23. 4
      riscv/insns/div_d_rm.h
  24. 4
      riscv/insns/div_s_rm.h
  25. 4
      riscv/insns/madd_d_rm.h
  26. 4
      riscv/insns/madd_s_rm.h
  27. 4
      riscv/insns/msub_d_rm.h
  28. 4
      riscv/insns/msub_s_rm.h
  29. 4
      riscv/insns/mul_d_rm.h
  30. 4
      riscv/insns/mul_s_rm.h
  31. 4
      riscv/insns/nmadd_d_rm.h
  32. 4
      riscv/insns/nmadd_s_rm.h
  33. 4
      riscv/insns/nmsub_d_rm.h
  34. 4
      riscv/insns/nmsub_s_rm.h
  35. 4
      riscv/insns/sqrt_d_rm.h
  36. 4
      riscv/insns/sqrt_s_rm.h
  37. 4
      riscv/insns/sub_d_rm.h
  38. 4
      riscv/insns/sub_s_rm.h

1
riscv/decode.h

@ -175,6 +175,7 @@ private:
#define TARGET insn.jtype.target
#define BRANCH_TARGET (npc + (SIMM << BRANCH_ALIGN_BITS))
#define JUMP_TARGET ((npc & ~((1<<(TARGET_BITS+JUMP_ALIGN_BITS))-1)) + (TARGET << JUMP_ALIGN_BITS))
#define RM ((insn.ftype.ffunct >> 1) & 3)
#define require_supervisor if(!(sr & SR_S)) throw trap_privileged_instruction
#define require64 if(gprlen != 64) throw trap_illegal_instruction

274
riscv/execute.h

@ -124,9 +124,14 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/cvt_s_w.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4000140)
if((insn.bits & 0xfff067e0) == 0xd40005e0)
{
#include "insns/trunc_w_s.h"
#include "insns/cvtu_s_w_rm.h"
break;
}
if((insn.bits & 0xfff067e0) == 0xd4000500)
{
#include "insns/cvt_l_s_rm.h"
break;
}
if((insn.bits & 0xfe007fe0) == 0xd4000000)
@ -134,6 +139,11 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/add_s.h"
break;
}
if((insn.bits & 0xfff067e0) == 0xd40005a0)
{
#include "insns/cvtu_s_l_rm.h"
break;
}
if((insn.bits & 0xfe0fffe0) == 0xd4000b00)
{
#include "insns/mff_s.h"
@ -149,19 +159,24 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/sgninjn_s.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4000100)
if((insn.bits & 0xfe0067e0) == 0xd4000440)
{
#include "insns/trunc_l_s.h"
#include "insns/mul_s_rm.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd40001e0)
if((insn.bits & 0xfff067e0) == 0xd4000520)
{
#include "insns/cvtu_s_w.h"
#include "insns/cvtu_l_s_rm.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4000120)
if((insn.bits & 0xfff067e0) == 0xd40005c0)
{
#include "insns/truncu_l_s.h"
#include "insns/cvt_s_w_rm.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd40001e0)
{
#include "insns/cvtu_s_w.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd40001a0)
@ -169,11 +184,41 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/cvtu_s_l.h"
break;
}
if((insn.bits & 0xfff067e0) == 0xd4000480)
{
#include "insns/sqrt_s_rm.h"
break;
}
if((insn.bits & 0xfff067e0) == 0xd4000660)
{
#include "insns/cvt_s_d_rm.h"
break;
}
if((insn.bits & 0xfe0067e0) == 0xd4000420)
{
#include "insns/sub_s_rm.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4000180)
{
#include "insns/cvt_s_l.h"
break;
}
if((insn.bits & 0xfe0067e0) == 0xd4000460)
{
#include "insns/div_s_rm.h"
break;
}
if((insn.bits & 0xfe007fe0) == 0xd4000020)
{
#include "insns/sub_s.h"
break;
}
if((insn.bits & 0xfff067e0) == 0xd4000580)
{
#include "insns/cvt_s_l_rm.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4000080)
{
#include "insns/sqrt_s.h"
@ -184,14 +229,14 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/c_lt_s.h"
break;
}
if((insn.bits & 0xfe007fe0) == 0xd40000e0)
if((insn.bits & 0xfe0067e0) == 0xd4000400)
{
#include "insns/sgnmul_s.h"
#include "insns/add_s_rm.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4000180)
if((insn.bits & 0xfe007fe0) == 0xd40000e0)
{
#include "insns/cvt_s_l.h"
#include "insns/sgnmul_s.h"
break;
}
if((insn.bits & 0xfe007fe0) == 0xd4000060)
@ -199,7 +244,7 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/div_s.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4000660)
if((insn.bits & 0xfff07fe0) == 0xd4000260)
{
#include "insns/cvt_s_d.h"
break;
@ -214,9 +259,14 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/mul_s.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4000160)
if((insn.bits & 0xfff067e0) == 0xd4000540)
{
#include "insns/cvt_w_s_rm.h"
break;
}
if((insn.bits & 0xfff067e0) == 0xd4000560)
{
#include "insns/truncu_w_s.h"
#include "insns/cvtu_w_s_rm.h"
break;
}
#include "insns/unimp.h"
@ -233,6 +283,11 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/sgninj_d.h"
break;
}
if((insn.bits & 0xfff067e0) == 0xd4006580)
{
#include "insns/cvt_d_l_rm.h"
break;
}
if((insn.bits & 0xfe007fe0) == 0xd4006060)
{
#include "insns/div_d.h"
@ -248,9 +303,9 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/cvtu_d_l.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4006140)
if((insn.bits & 0xfff067e0) == 0xd4006540)
{
#include "insns/trunc_w_d.h"
#include "insns/cvt_w_d_rm.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd40061e0)
@ -283,29 +338,49 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/sgnmul_d.h"
break;
}
if((insn.bits & 0xfff067e0) == 0xd4006560)
{
#include "insns/cvtu_w_d_rm.h"
break;
}
if((insn.bits & 0xfff067e0) == 0xd4006480)
{
#include "insns/sqrt_d_rm.h"
break;
}
if((insn.bits & 0xfe007fe0) == 0xd40060c0)
{
#include "insns/sgninjn_d.h"
break;
}
if((insn.bits & 0xfe007fe0) == 0xd4006f80)
if((insn.bits & 0xfff067e0) == 0xd40065a0)
{
#include "insns/mtflh_d.h"
#include "insns/cvtu_d_l_rm.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4006600)
if((insn.bits & 0xfe0067e0) == 0xd4006400)
{
#include "insns/cvt_d_s.h"
#include "insns/add_d_rm.h"
break;
}
if((insn.bits & 0xfff067e0) == 0xd4006500)
{
#include "insns/cvt_l_d_rm.h"
break;
}
if((insn.bits & 0xfe007fe0) == 0xd4006f80)
{
#include "insns/mtflh_d.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4006100)
if((insn.bits & 0xfff067e0) == 0xd4006520)
{
#include "insns/trunc_l_d.h"
#include "insns/cvtu_l_d_rm.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4006120)
if((insn.bits & 0xfe0067e0) == 0xd4006440)
{
#include "insns/truncu_l_d.h"
#include "insns/mul_d_rm.h"
break;
}
if((insn.bits & 0xfe007fe0) == 0xd4006020)
@ -323,6 +398,16 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/sqrt_d.h"
break;
}
if((insn.bits & 0xfe0067e0) == 0xd4006460)
{
#include "insns/div_d_rm.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4006200)
{
#include "insns/cvt_d_s.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd40061c0)
{
#include "insns/cvt_d_w.h"
@ -333,11 +418,6 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/cvt_d_l.h"
break;
}
if((insn.bits & 0xfff07fe0) == 0xd4006160)
{
#include "insns/truncu_w_d.h"
break;
}
if((insn.bits & 0xfe007fe0) == 0xd4006040)
{
#include "insns/mul_d.h"
@ -348,6 +428,11 @@ switch((insn.bits >> 0x19) & 0x7f)
#include "insns/c_lt_d.h"
break;
}
if((insn.bits & 0xfe0067e0) == 0xd4006420)
{
#include "insns/sub_d_rm.h"
break;
}
#include "insns/unimp.h"
}
default:
@ -357,54 +442,151 @@ switch((insn.bits >> 0x19) & 0x7f)
}
break;
}
case 0x6b:
case 0x6c:
{
switch((insn.bits >> 0xc) & 0x7)
{
case 0x0:
{
if((insn.bits & 0xfe007c00) == 0xd6000c00)
if((insn.bits & 0xfe006400) == 0xd8000400)
{
#include "insns/nmadd_s.h"
#include "insns/madd_s_rm.h"
break;
}
if((insn.bits & 0xfe007c00) == 0xd6000800)
if((insn.bits & 0xfe007c00) == 0xd8000000)
{
#include "insns/nmsub_s.h"
#include "insns/madd_s.h"
break;
}
if((insn.bits & 0xfe007c00) == 0xd6000400)
#include "insns/unimp.h"
}
case 0x6:
{
if((insn.bits & 0xfe006400) == 0xd8006400)
{
#include "insns/msub_s.h"
#include "insns/madd_d_rm.h"
break;
}
if((insn.bits & 0xfe007c00) == 0xd6000000)
if((insn.bits & 0xfe007c00) == 0xd8006000)
{
#include "insns/madd_s.h"
#include "insns/madd_d.h"
break;
}
#include "insns/unimp.h"
}
default:
{
#include "insns/unimp.h"
}
}
break;
}
case 0x6d:
{
switch((insn.bits >> 0xc) & 0x7)
{
case 0x0:
{
if((insn.bits & 0xfe006400) == 0xda000400)
{
#include "insns/msub_s_rm.h"
break;
}
if((insn.bits & 0xfe007c00) == 0xda000000)
{
#include "insns/msub_s.h"
break;
}
#include "insns/unimp.h"
}
case 0x6:
{
if((insn.bits & 0xfe007c00) == 0xd6006c00)
if((insn.bits & 0xfe007c00) == 0xda006000)
{
#include "insns/nmadd_d.h"
#include "insns/msub_d.h"
break;
}
if((insn.bits & 0xfe007c00) == 0xd6006800)
if((insn.bits & 0xfe006400) == 0xda006400)
{
#include "insns/msub_d_rm.h"
break;
}
#include "insns/unimp.h"
}
default:
{
#include "insns/unimp.h"
}
}
break;
}
case 0x6e:
{
switch((insn.bits >> 0xc) & 0x7)
{
case 0x0:
{
if((insn.bits & 0xfe007c00) == 0xdc000000)
{
#include "insns/nmsub_s.h"
break;
}
if((insn.bits & 0xfe006400) == 0xdc000400)
{
#include "insns/nmsub_s_rm.h"
break;
}
#include "insns/unimp.h"
}
case 0x6:
{
if((insn.bits & 0xfe007c00) == 0xdc006000)
{
#include "insns/nmsub_d.h"
break;
}
if((insn.bits & 0xfe007c00) == 0xd6006400)
if((insn.bits & 0xfe006400) == 0xdc006400)
{
#include "insns/msub_d.h"
#include "insns/nmsub_d_rm.h"
break;
}
if((insn.bits & 0xfe007c00) == 0xd6006000)
#include "insns/unimp.h"
}
default:
{
#include "insns/unimp.h"
}
}
break;
}
case 0x6f:
{
switch((insn.bits >> 0xc) & 0x7)
{
case 0x0:
{
if((insn.bits & 0xfe007c00) == 0xde000000)
{
#include "insns/madd_d.h"
#include "insns/nmadd_s.h"
break;
}
if((insn.bits & 0xfe006400) == 0xde000400)
{
#include "insns/nmadd_s_rm.h"
break;
}
#include "insns/unimp.h"
}
case 0x6:
{
if((insn.bits & 0xfe007c00) == 0xde006000)
{
#include "insns/nmadd_d.h"
break;
}
if((insn.bits & 0xfe006400) == 0xde006400)
{
#include "insns/nmadd_d_rm.h"
break;
}
#include "insns/unimp.h"

4
riscv/insns/add_d_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f64_add(FRS1, FRS2);
set_fp_exceptions;

4
riscv/insns/add_s_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f32_add(FRS1, FRS2);
set_fp_exceptions;

5
riscv/insns/cvt_d_l_rm.h

@ -0,0 +1,5 @@
require64;
require_fp;
softfloat_roundingMode = RM;
FRDR = i64_to_f64(RS1);
set_fp_exceptions;

4
riscv/insns/cvt_d_s_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f32_to_f64(FRS1);
set_fp_exceptions;

4
riscv/insns/cvt_d_w_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = i32_to_f64(RS1);
set_fp_exceptions;

1
riscv/insns/trunc_l_d.h → riscv/insns/cvt_l_d_rm.h

@ -1,4 +1,5 @@
require64;
require_fp;
softfloat_roundingMode = RM;
RDR = f64_to_i64_r_minMag(FRS1,true);
set_fp_exceptions;

1
riscv/insns/trunc_l_s.h → riscv/insns/cvt_l_s_rm.h

@ -1,4 +1,5 @@
require64;
require_fp;
softfloat_roundingMode = RM;
RDR = f32_to_i64_r_minMag(FRS1,true);
set_fp_exceptions;

4
riscv/insns/cvt_s_d_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f64_to_f32(FRS1);
set_fp_exceptions;

5
riscv/insns/cvt_s_l_rm.h

@ -0,0 +1,5 @@
require64;
require_fp;
softfloat_roundingMode = RM;
FRDR = i64_to_f32(RS1);
set_fp_exceptions;

4
riscv/insns/cvt_s_w_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = i32_to_f32(RS1);
set_fp_exceptions;

1
riscv/insns/trunc_w_d.h → riscv/insns/cvt_w_d_rm.h

@ -1,3 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
RDR = f64_to_i32_r_minMag(FRS1,true);
set_fp_exceptions;

1
riscv/insns/trunc_w_s.h → riscv/insns/cvt_w_s_rm.h

@ -1,3 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
RDR = f32_to_i32_r_minMag(FRS1,true);
set_fp_exceptions;

5
riscv/insns/cvtu_d_l_rm.h

@ -0,0 +1,5 @@
require64;
require_fp;
softfloat_roundingMode = RM;
FRDR = i64_to_f64(RS1);
set_fp_exceptions;

4
riscv/insns/cvtu_d_w_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = ui32_to_f64(RS1);
set_fp_exceptions;

1
riscv/insns/truncu_l_d.h → riscv/insns/cvtu_l_d_rm.h

@ -1,4 +1,5 @@
require64;
require_fp;
softfloat_roundingMode = RM;
RDR = f64_to_i64_r_minMag(FRS1,true);
set_fp_exceptions;

1
riscv/insns/truncu_l_s.h → riscv/insns/cvtu_l_s_rm.h

@ -1,4 +1,5 @@
require64;
require_fp;
softfloat_roundingMode = RM;
RDR = f32_to_i64_r_minMag(FRS1,true);
set_fp_exceptions;

5
riscv/insns/cvtu_s_l_rm.h

@ -0,0 +1,5 @@
require64;
require_fp;
softfloat_roundingMode = RM;
FRDR = i64_to_f32(RS1);
set_fp_exceptions;

4
riscv/insns/cvtu_s_w_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = ui32_to_f32(RS1);
set_fp_exceptions;

1
riscv/insns/truncu_w_d.h → riscv/insns/cvtu_w_d_rm.h

@ -1,3 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
RDR = f64_to_ui32_r_minMag(FRS1,true);
set_fp_exceptions;

1
riscv/insns/truncu_w_s.h → riscv/insns/cvtu_w_s_rm.h

@ -1,3 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
RDR = f32_to_ui32_r_minMag(FRS1,true);
set_fp_exceptions;

4
riscv/insns/div_d_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f64_div(FRS1, FRS2);
set_fp_exceptions;

4
riscv/insns/div_s_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f32_div(FRS1, FRS2);
set_fp_exceptions;

4
riscv/insns/madd_d_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f64_mulAdd(FRS1, FRS2, FRS3);
set_fp_exceptions;

4
riscv/insns/madd_s_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f32_mulAdd(FRS1, FRS2, FRS3);
set_fp_exceptions;

4
riscv/insns/msub_d_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f64_mulAdd(FRS1, FRS2, FRS3 ^ (uint64_t)INT64_MIN);
set_fp_exceptions;

4
riscv/insns/msub_s_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f32_mulAdd(FRS1, FRS2, FRS3 ^ (uint32_t)INT32_MIN);
set_fp_exceptions;

4
riscv/insns/mul_d_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f64_mul(FRS1, FRS2);
set_fp_exceptions;

4
riscv/insns/mul_s_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f32_mul(FRS1, FRS2);
set_fp_exceptions;

4
riscv/insns/nmadd_d_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f64_mulAdd(FRS1, FRS2, FRS3) ^ (uint64_t)INT64_MIN;
set_fp_exceptions;

4
riscv/insns/nmadd_s_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f32_mulAdd(FRS1, FRS2, FRS3) ^ (uint32_t)INT32_MIN;
set_fp_exceptions;

4
riscv/insns/nmsub_d_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f64_mulAdd(FRS1, FRS2, FRS3 ^ (uint64_t)INT64_MIN) ^ (uint64_t)INT64_MIN;
set_fp_exceptions;

4
riscv/insns/nmsub_s_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f32_mulAdd(FRS1, FRS2, FRS3 ^ (uint32_t)INT32_MIN) ^ (uint32_t)INT32_MIN;
set_fp_exceptions;

4
riscv/insns/sqrt_d_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f64_sqrt(FRS1);
set_fp_exceptions;

4
riscv/insns/sqrt_s_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f32_sqrt(FRS1);
set_fp_exceptions;

4
riscv/insns/sub_d_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f64_sub(FRS1, FRS2);
set_fp_exceptions;

4
riscv/insns/sub_s_rm.h

@ -0,0 +1,4 @@
require_fp;
softfloat_roundingMode = RM;
FRDR = f32_sub(FRS1, FRS2);
set_fp_exceptions;
Loading…
Cancel
Save