On 11/07/2016 06:59 PM, Laurent Vivier wrote:
+    } else {
+        /* We're executing in a serial context -- no need to be atomic.  */
+#ifdef CONFIG_USER_ONLY
+        int16_t *ha1 = g2h(a1);
+        int16_t *ha2 = g2h(a2);
+        l1 = lduw_be_p(ha1);
+        l2 = lduw_be_p(ha2);
+        if (l1 == c1 && l2 == c2) {
+            stw_be_p(ha1, u1);
+            stw_be_p(ha2, u2);
+        }
+#else
+        int mmu_idx = cpu_mmu_index(env, 0);
+        TCGMemOpIdx oi = make_memop_idx(MO_BESW, mmu_idx);
+        l1 = helper_be_lduw_mmu(env, a1, oi, ra);
+        l2 = helper_be_lduw_mmu(env, a2, oi, ra);
+        if (l1 == c1 && l2 == c2) {
+            helper_be_stw_mmu(env, a1, u1, oi, ra);
+            helper_be_stw_mmu(env, a2, u2, oi, ra);
+        }
+#endif
+    }

I think I gave you bad advice earlier. For the non-atomic parts we can combine these by using the <exec/cpu_ldst.h> functions:

  cpu_lduw_data_ra
  cpu_ldl_data_ra
  cpu_stw_data_ra
  cpu_stl_data_ra

+DISAS_INSN(cas)
+{
+    int opsize;
+    TCGv addr;
+    uint16_t ext;
+    TCGv load;
+    TCGv cmp;
+    TCGMemOp opc;
+
+    switch ((insn >> 9) & 3) {
+    case 1:
+        opsize = OS_BYTE;
+        opc = MO_UB;
+        break;
+    case 2:
+        opsize = OS_WORD;
+        opc = MO_TEUW;
+        break;
+    case 3:
+        opsize = OS_LONG;
+        opc = MO_TEUL;
+        break;
+    default:
+        g_assert_not_reached();
+    }

Return illegal opcode here, or 3 decode lines in register_m68k_insns.


r~


Reply via email to