19bcbdad2Sshane /* 29bcbdad2Sshane ** 2008 May 27 39bcbdad2Sshane ** 49bcbdad2Sshane ** The author disclaims copyright to this source code. In place of 59bcbdad2Sshane ** a legal notice, here is a blessing: 69bcbdad2Sshane ** 79bcbdad2Sshane ** May you do good and not evil. 89bcbdad2Sshane ** May you find forgiveness for yourself and forgive others. 99bcbdad2Sshane ** May you share freely, never taking more than you give. 109bcbdad2Sshane ** 119bcbdad2Sshane ****************************************************************************** 129bcbdad2Sshane ** 139bcbdad2Sshane ** This file contains inline asm code for retrieving "high-performance" 14*594b124fSdrh ** counters for x86 and x86_64 class CPUs. 159bcbdad2Sshane */ 1643f58d6aSdrh #ifndef SQLITE_HWTIME_H 1743f58d6aSdrh #define SQLITE_HWTIME_H 189bcbdad2Sshane 199bcbdad2Sshane /* 209bcbdad2Sshane ** The following routine only works on pentium-class (or newer) processors. 219bcbdad2Sshane ** It uses the RDTSC opcode to read the cycle count value out of the 229bcbdad2Sshane ** processor and returns that value. This can be used for high-res 239bcbdad2Sshane ** profiling. 249bcbdad2Sshane */ 25*594b124fSdrh #if !defined(__STRICT_ANSI__) && \ 26*594b124fSdrh (defined(__GNUC__) || defined(_MSC_VER)) && \ 279bcbdad2Sshane (defined(i386) || defined(__i386__) || defined(_M_IX86)) 289bcbdad2Sshane 299bcbdad2Sshane #if defined(__GNUC__) 309bcbdad2Sshane sqlite3Hwtime(void)319bcbdad2Sshane __inline__ sqlite_uint64 sqlite3Hwtime(void){ 329bcbdad2Sshane unsigned int lo, hi; 339bcbdad2Sshane __asm__ __volatile__ ("rdtsc" : "=a" (lo), "=d" (hi)); 349bcbdad2Sshane return (sqlite_uint64)hi << 32 | lo; 359bcbdad2Sshane } 369bcbdad2Sshane 379bcbdad2Sshane #elif defined(_MSC_VER) 389bcbdad2Sshane sqlite3Hwtime(void)399bcbdad2Sshane __declspec(naked) __inline sqlite_uint64 __cdecl sqlite3Hwtime(void){ 409bcbdad2Sshane __asm { 419bcbdad2Sshane rdtsc 429bcbdad2Sshane ret ; return value at EDX:EAX 439bcbdad2Sshane } 449bcbdad2Sshane } 459bcbdad2Sshane 469bcbdad2Sshane #endif 479bcbdad2Sshane 48*594b124fSdrh #elif !defined(__STRICT_ANSI__) && (defined(__GNUC__) && defined(__x86_64__)) 49b08c1d0cSshane 50b08c1d0cSshane __inline__ sqlite_uint64 sqlite3Hwtime(void){ 51b08c1d0cSshane unsigned long val; 52b08c1d0cSshane __asm__ __volatile__ ("rdtsc" : "=A" (val)); 53b08c1d0cSshane return val; 54b08c1d0cSshane } 55b08c1d0cSshane 56*594b124fSdrh #elif !defined(__STRICT_ANSI__) && (defined(__GNUC__) && defined(__ppc__)) 575cd89cfeSshane 585cd89cfeSshane __inline__ sqlite_uint64 sqlite3Hwtime(void){ 595cd89cfeSshane unsigned long long retval; 605cd89cfeSshane unsigned long junk; 615cd89cfeSshane __asm__ __volatile__ ("\n\ 625cd89cfeSshane 1: mftbu %1\n\ 635cd89cfeSshane mftb %L0\n\ 645cd89cfeSshane mftbu %0\n\ 655cd89cfeSshane cmpw %0,%1\n\ 665cd89cfeSshane bne 1b" 675cd89cfeSshane : "=r" (retval), "=r" (junk)); 685cd89cfeSshane return retval; 695cd89cfeSshane } 705cd89cfeSshane 719bcbdad2Sshane #else 729bcbdad2Sshane 739bcbdad2Sshane /* 74*594b124fSdrh ** asm() is needed for hardware timing support. Without asm(), 75*594b124fSdrh ** disable the sqlite3Hwtime() routine. 76*594b124fSdrh ** 77*594b124fSdrh ** sqlite3Hwtime() is only used for some obscure debugging 78*594b124fSdrh ** and analysis configurations, not in any deliverable, so this 79*594b124fSdrh ** should not be a great loss. 809bcbdad2Sshane */ 819bcbdad2Sshane sqlite_uint64 sqlite3Hwtime(void){ return ((sqlite_uint64)0); } 829bcbdad2Sshane 839bcbdad2Sshane #endif 849bcbdad2Sshane 8543f58d6aSdrh #endif /* !defined(SQLITE_HWTIME_H) */ 86