|
From: <sv...@va...> - 2005-09-06 10:25:49
|
Author: sewardj
Date: 2005-09-06 11:25:46 +0100 (Tue, 06 Sep 2005)
New Revision: 1371
Log:
Implement mftb{,u}.
Modified:
trunk/priv/guest-ppc32/gdefs.h
trunk/priv/guest-ppc32/ghelpers.c
trunk/priv/guest-ppc32/toIR.c
Modified: trunk/priv/guest-ppc32/gdefs.h
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D
--- trunk/priv/guest-ppc32/gdefs.h 2005-09-06 09:55:27 UTC (rev 1370)
+++ trunk/priv/guest-ppc32/gdefs.h 2005-09-06 10:25:46 UTC (rev 1371)
@@ -101,14 +101,6 @@
}
PPC32CmpF64Result;
=20
-
-/*---------------------------------------------------------*/
-/*--- ppc32 guest helpers ---*/
-/*---------------------------------------------------------*/
-
-/* --- CLEAN HELPERS --- */
-
-
/*
Enumeration for xer_ca/ov calculation helper functions
*/
@@ -129,6 +121,19 @@
};
=20
=20
+/*---------------------------------------------------------*/
+/*--- ppc32 guest helpers ---*/
+/*---------------------------------------------------------*/
+
+/* --- CLEAN HELPERS --- */
+
+/* none, right now */
+
+/* --- DIRTY HELPERS --- */
+
+extern ULong ppc32g_dirtyhelper_MFTB ( void );
+
+
#endif /* ndef __LIBVEX_GUEST_PPC32_DEFS_H */
=20
/*---------------------------------------------------------------*/
Modified: trunk/priv/guest-ppc32/ghelpers.c
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D
--- trunk/priv/guest-ppc32/ghelpers.c 2005-09-06 09:55:27 UTC (rev 1370)
+++ trunk/priv/guest-ppc32/ghelpers.c 2005-09-06 10:25:46 UTC (rev 1371)
@@ -68,7 +68,39 @@
*/
=20
=20
+/*---------------------------------------------------------------*/
+/*--- Misc integer helpers. ---*/
+/*---------------------------------------------------------------*/
=20
+/* CALLED FROM GENERATED CODE */
+/* DIRTY HELPER (non-referentially-transparent) */
+/* Horrible hack. On non-ppc32 platforms, return 1. */
+/* Reads a complete, consistent 64-bit TB value. */
+ULong ppc32g_dirtyhelper_MFTB ( void )
+{
+# if defined(__powerpc__)
+ ULong res;
+ UInt lo, hi1, hi2;
+ while (1) {
+ __asm__ __volatile__ ("\n"
+ "\tmftbu %0\n"
+ "\tmftb %1\n"
+ "\tmftbu %2\n"
+ : "=3Dr" (hi1), "=3Dr" (lo), "=3Dr" (hi2)
+ );
+ if (hi1 =3D=3D hi2) break;
+ }
+ res =3D ((ULong)hi1) << 32;
+ res |=3D (ULong)lo;
+ return res;
+# else
+ return 1ULL;
+# endif
+}
+
+
+/* Helper-function specialiser. */
+
IRExpr* guest_ppc32_spechelper ( HChar* function_name,
IRExpr** args )
{
Modified: trunk/priv/guest-ppc32/toIR.c
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D
--- trunk/priv/guest-ppc32/toIR.c 2005-09-06 09:55:27 UTC (rev 1370)
+++ trunk/priv/guest-ppc32/toIR.c 2005-09-06 10:25:46 UTC (rev 1371)
@@ -3446,7 +3446,7 @@
/* XFX-Form */
UChar Rs_addr =3D toUChar((theInstr >> 21) & 0x1F); /* theInstr[21:2=
5] */
UInt SPR =3D (theInstr >> 11) & 0x3FF; /* theInstr[11:2=
0] */
-//uu UInt TBR =3D (theInstr >> 11) & 0x3FF; /* theInstr[=
11:20] */
+ UInt TBR =3D (theInstr >> 11) & 0x3FF; /* theInstr[11:2=
0] */
UChar b20 =3D toUChar((theInstr >> 11) & 0x1); /* theInstr[11] =
*/
UInt CRM =3D (theInstr >> 12) & 0xFF; /* theInstr[12:1=
9] */
UChar b11 =3D toUChar((theInstr >> 11) & 0x1); /* theInstr[20] =
*/
@@ -3459,6 +3459,9 @@
IRTemp Rs =3D newTemp(Ity_I32);
//uu IRTemp tmp =3D newTemp(Ity_I32);
=20
+ /* Reorder TBR field as per PPC32 p475 */
+ TBR =3D ((TBR & 31) << 5) | ((TBR >> 5) & 31);
+
assign( Rs, getIReg(Rs_addr) );
=20
if (opc1 !=3D 0x1F || b0 !=3D 0) {
@@ -3569,12 +3572,34 @@
}
break;
=20
-//zz case 0x173: // mftb (Move from Time Base, PPC32 p475)
-//zz vassert(0);
-//zz=20
-//zz DIP("mftb r%d,0x%x\n", Rd_addr, TBR);
-//zz return False;
- =20
+ case 0x173: { // mftb (Move from Time Base, PPC32 p475)
+ IRTemp val =3D newTemp(Ity_I64);
+ IRExpr** args =3D mkIRExprVec_0();
+ IRDirty* d =3D unsafeIRDirty_1_N (=20
+ val,=20
+ 0/*regparms*/,=20
+ "ppc32g_dirtyhelper_MFTB",=20
+ &ppc32g_dirtyhelper_MFTB,=20
+ args=20
+ );
+ /* execute the dirty call, dumping the result in val. */
+ stmt( IRStmt_Dirty(d) );
+
+ switch (TBR) {
+ case 269:=20
+ putIReg( Rd_addr, unop(Iop_64HIto32, mkexpr(val)) );
+ DIP("mftbu r%d", Rd_addr);
+ break;
+ case 268:=20
+ putIReg( Rd_addr, unop(Iop_64to32, mkexpr(val)) );
+ DIP("mftb r%d", Rd_addr);
+ break;
+ default:
+ return False; /* illegal instruction */
+ }
+ break;
+ }
+
case 0x090: // mtcrf (Move to Condition Register Fields, PPC32 p477)
if (b11 !=3D 0 || b20 !=3D 0) {
vex_printf("dis_proc_ctl(PPC32)(mtcrf,b11|b20)\n");
|