[gem5-dev] Change in gem5/gem5[develop]: arch-power: Add trap instructions

2021-06-30 Thread Boris Shingarov (Gerrit) via gem5-dev
Boris Shingarov has submitted this change. (  
https://gem5-review.googlesource.com/c/public/gem5/+/40934 )


Change subject: arch-power: Add trap instructions
..

arch-power: Add trap instructions

This introduces new classes and new formats for D and X
form instructions, the TO field that is used to encode
the trap conditions and adds the following instructions.
  * Trap Word Immediate (twi)
  * Trap Word (tw)
  * Trap Doubleword Immediate (tdi)
  * Trap Doubleword (td)

Change-Id: I029147ef643c2ee6794426e5e90af4d75f22e92e
Signed-off-by: Sandipan Das 
Reviewed-on: https://gem5-review.googlesource.com/c/public/gem5/+/40934
Reviewed-by: Boris Shingarov 
Maintainer: Boris Shingarov 
Tested-by: kokoro 
---
M src/arch/power/faults.hh
M src/arch/power/insts/integer.cc
M src/arch/power/insts/integer.hh
M src/arch/power/isa/decoder.isa
M src/arch/power/isa/formats/integer.isa
M src/arch/power/types.hh
6 files changed, 225 insertions(+), 0 deletions(-)

Approvals:
  Boris Shingarov: Looks good to me, approved; Looks good to me, approved
  kokoro: Regressions pass



diff --git a/src/arch/power/faults.hh b/src/arch/power/faults.hh
index e20ef8e..806f958 100644
--- a/src/arch/power/faults.hh
+++ b/src/arch/power/faults.hh
@@ -82,6 +82,16 @@
 }
 };

+
+class TrapFault : public PowerFault
+{
+  public:
+TrapFault()
+: PowerFault("Trap")
+{
+}
+};
+
 } // namespace PowerISA

 #endif // __ARCH_POWER_FAULTS_HH__
diff --git a/src/arch/power/insts/integer.cc  
b/src/arch/power/insts/integer.cc

index 3203507..7795b50 100644
--- a/src/arch/power/insts/integer.cc
+++ b/src/arch/power/insts/integer.cc
@@ -820,3 +820,99 @@

 return ss.str();
 }
+
+
+std::string
+IntTrapOp::generateDisassembly(
+Addr pc, const Loader::SymbolTable *symtab) const
+{
+std::string ext;
+std::stringstream ss;
+bool printSrcs = true;
+bool printCond = false;
+
+// Generate the correct mnemonic
+std::string myMnemonic(mnemonic);
+
+// Special cases
+if (myMnemonic == "tw" &&
+(srcRegIdx(0).index() == 0) && (srcRegIdx(1).index() == 0)) {
+myMnemonic = "trap";
+printSrcs = false;
+} else {
+ext = suffix();
+if (!ext.empty() &&
+(myMnemonic == "tw" || myMnemonic == "td")) {
+myMnemonic += ext;
+} else {
+printCond = true;
+}
+}
+
+ccprintf(ss, "%-10s ", myMnemonic);
+
+// Print the trap condition
+if (printCond)
+ss << (int) to;
+
+// Print the source registers
+if (printSrcs) {
+if (_numSrcRegs > 0) {
+if (printCond)
+ss << ", ";
+printReg(ss, srcRegIdx(0));
+}
+
+if (_numSrcRegs > 1) {
+ss << ", ";
+printReg(ss, srcRegIdx(1));
+}
+}
+
+return ss.str();
+}
+
+
+std::string
+IntImmTrapOp::generateDisassembly(
+Addr pc, const Loader::SymbolTable *symtab) const
+{
+std::string ext;
+std::stringstream ss;
+bool printCond = false;
+
+// Generate the correct mnemonic
+std::string myMnemonic(mnemonic);
+
+// Special cases
+ext = suffix();
+if (!ext.empty()) {
+if (myMnemonic == "twi") {
+myMnemonic = "tw" + ext + "i";
+} else if (myMnemonic == "tdi") {
+myMnemonic = "td" + ext + "i";
+} else {
+printCond = true;
+}
+} else {
+printCond = true;
+}
+
+ccprintf(ss, "%-10s ", myMnemonic);
+
+// Print the trap condition
+if (printCond)
+ss << (int) to;
+
+// Print the source registers
+if (_numSrcRegs > 0) {
+if (printCond)
+ss << ", ";
+printReg(ss, srcRegIdx(0));
+}
+
+// Print the immediate value
+ss << ", " << si;
+
+return ss.str();
+}
diff --git a/src/arch/power/insts/integer.hh  
b/src/arch/power/insts/integer.hh

index 69bc633..600fdf4 100644
--- a/src/arch/power/insts/integer.hh
+++ b/src/arch/power/insts/integer.hh
@@ -713,6 +713,82 @@
 Addr pc, const Loader::SymbolTable *symtab) const override;
 };

+
+/**
+ * Class for integer trap operations.
+ */
+class IntTrapOp : public IntOp
+{
+  protected:
+uint8_t to;
+
+/// Constructor
+IntTrapOp(const char *mnem, MachInst _machInst, OpClass __opClass)
+  : IntOp(mnem, _machInst, __opClass),
+to(machInst.to)
+{
+}
+
+inline bool
+checkTrap(int64_t a, int64_t b) const
+{
+if (((to & 0x10) && (a < b))  ||
+((to & 0x08) && (a > b))  ||
+((to & 0x04) && (a == b)) ||
+((to & 0x02) && ((uint64_t)a < (uint64_t)b)) ||
+((to & 0x01) && ((uint64_t)a > (uint64_t)b))) {
+return true;
+}
+
+return false;
+}
+
+inline std::string
+suffix() const
+{
+std::string str;
+
+switch (to) {
+case 

[gem5-dev] Change in gem5/gem5[develop]: arch-power: Add trap instructions

2021-02-07 Thread Sandipan Das (Gerrit) via gem5-dev
Sandipan Das has uploaded this change for review. (  
https://gem5-review.googlesource.com/c/public/gem5/+/40934 )



Change subject: arch-power: Add trap instructions
..

arch-power: Add trap instructions

This introduces new classes and new formats for D and X
form instructions, the TO field that is used to encode
the trap conditions and adds the following instructions.
  * Trap Word Immediate (twi)
  * Trap Word (tw)
  * Trap Doubleword Immediate (tdi)
  * Trap Doubleword (td)

Change-Id: I029147ef643c2ee6794426e5e90af4d75f22e92e
Signed-off-by: Sandipan Das 
---
M src/arch/power/faults.hh
M src/arch/power/insts/integer.cc
M src/arch/power/insts/integer.hh
M src/arch/power/isa/decoder.isa
M src/arch/power/isa/formats/integer.isa
M src/arch/power/types.hh
6 files changed, 229 insertions(+), 0 deletions(-)



diff --git a/src/arch/power/faults.hh b/src/arch/power/faults.hh
index e20ef8e..6932271 100644
--- a/src/arch/power/faults.hh
+++ b/src/arch/power/faults.hh
@@ -82,6 +82,15 @@
 }
 };

+class TrapFault : public PowerFault
+{
+  public:
+TrapFault()
+: PowerFault("Trap")
+{
+}
+};
+
 } // namespace PowerISA

 #endif // __ARCH_POWER_FAULTS_HH__
diff --git a/src/arch/power/insts/integer.cc  
b/src/arch/power/insts/integer.cc

index 0631749..115b867 100644
--- a/src/arch/power/insts/integer.cc
+++ b/src/arch/power/insts/integer.cc
@@ -878,3 +878,103 @@

 return ss.str();
 }
+
+
+std::string
+IntTrapOp::generateDisassembly(
+Addr pc, const Loader::SymbolTable *symtab) const
+{
+std::string ext;
+std::stringstream ss;
+bool printSrcs = true;
+bool printCond = false;
+
+// Generate the correct mnemonic
+std::string myMnemonic(mnemonic);
+
+// Special cases
+if (!myMnemonic.compare("tw") &&
+(srcRegIdx(0).index() == 0) && (srcRegIdx(1).index() == 0)) {
+myMnemonic = "trap";
+printSrcs = false;
+} else {
+ext = suffix();
+if (!ext.empty() &&
+(!myMnemonic.compare("tw") || !myMnemonic.compare("td"))) {
+myMnemonic += ext;
+} else {
+printCond = true;
+}
+}
+
+ccprintf(ss, "%-10s ", myMnemonic);
+
+// Print the trap condition
+if (printCond) {
+ss << unsigned(tcond);
+}
+
+// Print the source registers
+if (printSrcs) {
+if (_numSrcRegs > 0) {
+if (printCond) {
+ss << ", ";
+}
+printReg(ss, srcRegIdx(0));
+}
+
+if (_numSrcRegs > 1) {
+ss << ", ";
+printReg(ss, srcRegIdx(1));
+}
+}
+
+return ss.str();
+}
+
+
+std::string
+IntImmTrapOp::generateDisassembly(
+Addr pc, const Loader::SymbolTable *symtab) const
+{
+std::string ext;
+std::stringstream ss;
+bool printCond = false;
+
+// Generate the correct mnemonic
+std::string myMnemonic(mnemonic);
+
+// Special cases
+ext = suffix();
+if (!ext.empty()) {
+if (!myMnemonic.compare("twi")) {
+myMnemonic = "tw" + ext + "i";
+} else if (!myMnemonic.compare("tdi")) {
+myMnemonic = "td" + ext + "i";
+} else {
+printCond = true;
+}
+} else {
+printCond = true;
+}
+
+ccprintf(ss, "%-10s ", myMnemonic);
+
+// Print the trap condition
+if (printCond) {
+ss << unsigned(tcond);
+}
+
+// Print the source registers
+if (_numSrcRegs > 0) {
+if (printCond) {
+ss << ", ";
+}
+printReg(ss, srcRegIdx(0));
+}
+
+// Print the immediate value
+ss << ", " << simm;
+
+return ss.str();
+}
diff --git a/src/arch/power/insts/integer.hh  
b/src/arch/power/insts/integer.hh

index 59566e8..a2692e2 100644
--- a/src/arch/power/insts/integer.hh
+++ b/src/arch/power/insts/integer.hh
@@ -733,6 +733,82 @@
 Addr pc, const Loader::SymbolTable *symtab) const override;
 };

+
+/**
+ * Class for integer trap operations.
+ */
+class IntTrapOp : public IntOp
+{
+  protected:
+uint8_t tcond;
+
+/// Constructor
+IntTrapOp(const char *mnem, MachInst _machInst, OpClass __opClass)
+  : IntOp(mnem, _machInst, __opClass),
+tcond(machInst.to)
+{
+}
+
+inline bool
+checkTrap(int64_t ra, int64_t rb) const
+{
+if (((tcond & 0x10) && (ra < rb))  ||
+((tcond & 0x08) && (ra > rb))  ||
+((tcond & 0x04) && (ra == rb)) ||
+((tcond & 0x02) && ((uint64_t)ra < (uint64_t)rb)) ||
+((tcond & 0x01) && ((uint64_t)ra > (uint64_t)rb))) {
+return true;
+}
+
+return false;
+}
+
+inline std::string
+suffix() const
+{
+std::string str;
+
+switch (tcond) {
+case 1:  str = "lgt"; break;
+case 2:  str = "llt"; break;
+case 4:  str = "eq"; break;
+