get predicated-vectorised branch working
[riscv-isa-sim.git] / riscv / sv.cc
index c06bdd5575751829352c396664c74778e8f24fa9..ba4fd53a0bcfa2fc80ca84d84d34d6ec31a6ea0b 100644 (file)
@@ -191,9 +191,8 @@ uint64_t sv_insn_t::_rvc_spoffs_imm(uint64_t elwidth, uint64_t offs)
 }
 
 // for use in predicated branches. sets bit N if val=true; clears bit N if false
-uint64_t sv_insn_t::rd_bitset(uint64_t bit, bool set)
+uint64_t sv_insn_t::rd_bitset(reg_t reg, uint64_t bit, bool set)
 {
-    reg_t reg = rd();
     uint64_t val = READ_REG(reg);
     if (set) {
         val |= (1<<bit);
@@ -205,7 +204,7 @@ uint64_t sv_insn_t::rd_bitset(uint64_t bit, bool set)
 }
 
 void sv_insn_t::setpc(int xlen, int vlen, reg_t &npc, reg_t addr, uint64_t offs,
-                      uint64_t predicate)
+                      reg_t *target_reg)
 {
     save_branch_addr = addr;
     if (not at_least_one_reg_vectorised)
@@ -213,6 +212,20 @@ void sv_insn_t::setpc(int xlen, int vlen, reg_t &npc, reg_t addr, uint64_t offs,
         _set_pc(addr);
         return;
     }
-    save_branch_rd = rd_bitset(offs, true);
+    if (target_reg != NULL) {
+        fprintf(stderr, "setpc pre rd %ld v %lx pred %lx\n",
+                        *target_reg, READ_REG(*target_reg), prs1);
+    }
+    if ((1<<offs) & prs1)
+    {
+        if (target_reg) {
+            save_branch_rd = rd_bitset(*target_reg, offs, true);
+        } else {
+            save_branch_rd |= (1<<offs);
+        }
+    }
+    fprintf(stderr, "setpc %lx offs %ld predicate %lx rs1 %ld rs2 %ld\n",
+            save_branch_rd, offs, prs1,
+            READ_REG(rs1()), READ_REG(rs2()));
 }