1 /// X86 platform specific utils 2 module mecca.platform.x86; 3 4 // Licensed under the Boost license. Full copyright information in the AUTHORS file 5 6 /// Size in bytes of a single cache line 7 enum CACHE_LINE_SIZE = 64; 8 9 version(LDC) { 10 public import ldc.intrinsics: readTSC = llvm_readcyclecounter; 11 } 12 else version (D_InlineAsm_X86_64) { 13 ulong readTSC() nothrow @nogc @safe { 14 asm nothrow @nogc @safe { 15 naked; 16 rdtsc; // EDX(hi):EAX(lo) 17 shl RDX, 32; 18 or RAX, RDX; // RAX |= (RDX << 32) 19 ret; 20 } 21 } 22 } 23 else { 24 static assert (false, "RDTSC not supported on platform"); 25 } 26 27 unittest { 28 assert (readTSC() != 0); 29 } 30 31 /+version(LDC) { 32 private pure pragma(LDC_intrinsic, "llvm.x86.sse42.crc32.64.64") ulong crc32(ulong crc, ulong v) nothrow @safe @nogc; 33 } 34 35 uint crc32c(ulong crc, ulong v) @nogc nothrow @system { 36 if (__ctfe) { 37 return 0; 38 } else { 39 version(LDC) { 40 return cast(uint)crc32(crc, v); 41 } else { 42 return 0; 43 } 44 } 45 } 46 47 unittest { 48 ulong crc = 0x000011115555AAAA; 49 ulong v = 0x88889999EEEE3333; 50 51 assert(crc32c(crc, v) == 0x16f57621); 52 v = 0x00000000EEEE3333; 53 assert(crc32c(crc, v) == 0x8e5d3bf9); 54 } 55 +/ 56 57 version (LDC) { 58 import ldc.intrinsics; 59 60 void prefetch(const void* p) pure nothrow @trusted @nogc { 61 pragma(inline, true); 62 llvm_prefetch(cast(void*)p, 0 /*read*/, 3 /*very local*/, 1 /*data*/); 63 } 64 } 65 else version (D_InlineAsm_X86_64) { 66 void prefetch(const void* p /* RDI */) pure nothrow @safe @nogc { 67 pragma(inline, true); 68 asm pure nothrow @safe @nogc { 69 naked; 70 prefetcht0 [RDI]; 71 ret; 72 } 73 } 74 } 75 else { 76 static assert (false, "prefetch not supported"); 77 } 78 79 unittest { 80 // prefetching will not segfault 81 prefetch(null); 82 83 ulong[1000] x = void; 84 prefetch(&x[800]); 85 } 86 87 88