#DPATCHLEVEL=0 --- lib/direct/cpu_accel.c 2005-07-31 12:34:22.000000000 +0300 +++ lib/direct/cpu_accel.c 2006-06-14 09:31:03.000000000 +0300 @@ -106,11 +106,14 @@ AMD = (ebx == 0x68747541) && (ecx == 0x444d4163) && (edx == 0x69746e65); cpuid (0x00000001, eax, ebx, ecx, edx); - if (! (edx & 0x00800000)) /* no MMX */ - return 0; + + if (edx & 0x00000010) + caps |= MM_ACCEL_X86_TSC; #ifdef USE_MMX - caps = MM_ACCEL_X86_MMX; + if (edx & 0x00800000) /* MMX */ + caps |= MM_ACCEL_X86_MMX; + #ifdef USE_SSE if (edx & 0x02000000) /* SSE - identical to AMD MMX extensions */ caps |= MM_ACCEL_X86_SSE | MM_ACCEL_X86_MMXEXT; --- lib/direct/cpu_accel.h 2004-03-30 12:31:23.000000000 +0300 +++ lib/direct/cpu_accel.h 2006-06-14 08:46:24.000000000 +0300 @@ -70,6 +70,7 @@ #define MM_ACCEL_X86_MMXEXT 0x20000000 #define MM_ACCEL_X86_SSE 0x10000000 #define MM_ACCEL_X86_SSE2 0x08000000 +#define MM_ACCEL_X86_TSC 0x02000000 /* powerpc accelerations */ #define MM_ACCEL_PPC_ALTIVEC 0x04000000 /* x86 compat defines */ --- lib/direct/memcpy.c 2005-07-31 21:07:59.000000000 +0300 +++ lib/direct/memcpy.c 2006-06-14 09:50:58.000000000 +0300 @@ -517,22 +517,21 @@ #ifdef ARCH_X86 -static inline unsigned long long int rdtsc() +static inline unsigned long long int x86_rdtsc() { unsigned long long int x; __asm__ volatile (".byte 0x0f, 0x31" : "=A" (x)); return x; } -#else -static inline unsigned long long int rdtsc() +#endif + +static inline unsigned long long int generic_rdtsc() { struct timeval tv; gettimeofday (&tv, NULL); return (tv.tv_sec * 1000000 + tv.tv_usec); } -#endif - memcpy_func direct_memcpy = (memcpy_func) memcpy; @@ -548,6 +547,9 @@ char *buf1, *buf2; int i, j, best = 0; __u32 config_flags = direct_mm_accel(); +#ifdef ARCH_X86 + __u32 has_tsc = config_flags & MM_ACCEL_X86_TSC; +#endif if (direct_config->memcpy) { for (i=1; memcpy_method[i].name; i++) { @@ -582,12 +584,23 @@ if (memcpy_method[i].cpu_require & ~config_flags) continue; - t = rdtsc(); +#ifdef ARCH_X86 + if (has_tsc) + t = x86_rdtsc(); + else +#endif + t = generic_rdtsc(); for (j=0; j<2000; j++) memcpy_method[i].function( buf1 + j*BUFSIZE, buf2 + j*BUFSIZE, BUFSIZE ); - t = rdtsc() - t; +#ifdef ARCH_X86 + if (has_tsc) + t = x86_rdtsc() - t; + else +#endif + t = generic_rdtsc() - t; + memcpy_method[i].time = t; D_DEBUG_AT( Direct_Memcpy, "\t%-10s %20lld\n", memcpy_method[i].name, t );