about summary refs log tree commit diff stats
path: root/src
diff options
context:
space:
mode:
authorptitSeb <sebastien.chev@gmail.com>2024-02-21 12:27:26 +0100
committerptitSeb <sebastien.chev@gmail.com>2024-02-21 12:27:53 +0100
commit0d43b16fd5b6e9dbd3b6683843d8b3c1df4f7c8b (patch)
tree81c0d88144bc07e6d60fc4fc7c8d2879b039919f /src
parentb179bd24154f890fe28e44c94dd667ea99ccbf45 (diff)
downloadbox64-0d43b16fd5b6e9dbd3b6683843d8b3c1df4f7c8b.tar.gz
box64-0d43b16fd5b6e9dbd3b6683843d8b3c1df4f7c8b.zip
[ARM64] Used Hardware counter for RDTSC emulation ([ARM64_DYNAREC] too)
Diffstat (limited to 'src')
-rw-r--r--src/dynarec/arm64/arm64_emitter.h2
-rw-r--r--src/dynarec/arm64/dynarec_arm64_0f.c7
-rw-r--r--src/emu/x64emu.c8
3 files changed, 11 insertions, 6 deletions
diff --git a/src/dynarec/arm64/arm64_emitter.h b/src/dynarec/arm64/arm64_emitter.h
index 2f3d2396..d44fa5d9 100644
--- a/src/dynarec/arm64/arm64_emitter.h
+++ b/src/dynarec/arm64/arm64_emitter.h
@@ -767,6 +767,8 @@
 // mrs    x0, fpsr : 1101010100 1 1 1 011 0100 0100 001 00000    o0=1(op0=3), op1=0b011(3) CRn=0b0100(4) CRm=0b0100(4) op2=1
 #define MRS_fpsr(Rt)                    EMIT(MRS_gen(1, 1, 3, 4, 4, 1, Rt))
 #define MSR_fpsr(Rt)                    EMIT(MRS_gen(0, 1, 3, 4, 4, 1, Rt))
+// mrs   x0, cntvct_el0     op0=0b11 op1=0b011 CRn=0b1110 CRm=0b0000 op2=0b010
+#define MRS_cntvct_el0(Rt)              EMIT(MRS_gen(1, 1, 0b011, 0b1110, 0b0000, 0b010, Rt))
 // NEON Saturation Bit
 #define FPSR_QC 27
 // NEON Input Denormal Cumulative
diff --git a/src/dynarec/arm64/dynarec_arm64_0f.c b/src/dynarec/arm64/dynarec_arm64_0f.c
index 79596c8a..57c3e400 100644
--- a/src/dynarec/arm64/dynarec_arm64_0f.c
+++ b/src/dynarec/arm64/dynarec_arm64_0f.c
@@ -482,10 +482,9 @@ uintptr_t dynarec64_0F(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
         case 0x31:

             INST_NAME("RDTSC");

             NOTEST(x1);

-            MESSAGE(LOG_DUMP, "Need Optimization\n");

-            CALL(ReadTSC, x3);    // will return the u64 in x3

-            LSRx(xRDX, x3, 32);

-            MOVw_REG(xRAX, x3);   // wipe upper part

+            MRS_cntvct_el0(x1);

+            LSRx(xRDX, x1, 32);

+            MOVw_REG(xRAX, x1);   // wipe upper part

             break;

 

         case 0x38:

diff --git a/src/emu/x64emu.c b/src/emu/x64emu.c
index 38f2f20a..77626fdc 100644
--- a/src/emu/x64emu.c
+++ b/src/emu/x64emu.c
@@ -585,9 +585,13 @@ uint64_t ReadTSC(x64emu_t* emu)
     
     //TODO: implement hardware counter read? (only available in kernel space?)
     // Read the TimeStamp Counter as 64bits.
-    // this is supposed to be the number of instructions executed since last reset
+    // this is supposed to be the number of cycle executed since last reset
     // fall back to gettime...
-#ifndef NOGETCLOCK
+#ifdef ARM64
+    uint64_t val;
+    asm volatile("mrs %0, cntvct_el0" : "=r" (val));
+    return val;
+#elif !defined(NOGETCLOCK)
     struct timespec ts;
     clock_gettime(CLOCK_MONOTONIC_COARSE, &ts);
     return (uint64_t)(ts.tv_sec) * 1000000000LL + ts.tv_nsec;