我是否正确实现了时钟漂移?

时间:2010-05-29 07:33:37

标签: c++ c windows random

我无法在任何地方找到适用于Windows的任何时钟漂移RNG代码,所以我试图自己实现它。我还没有通过entDIEHARD运行这些数字,而我只是想知道这是否是远程正确的...

void QueryRDTSC(__int64* tick) {
 __asm {
  xor eax, eax
  cpuid
  rdtsc
  mov edi, dword ptr tick
  mov dword ptr [edi], eax
  mov dword ptr [edi+4], edx
 }
}

__int64 clockDriftRNG() {
 __int64 CPU_start, CPU_end, OS_start, OS_end;

 // get CPU ticks -- uses RDTSC on the Processor
 QueryRDTSC(&CPU_start);
 Sleep(1);
 QueryRDTSC(&CPU_end);


 // get OS ticks -- uses the Motherboard clock
 QueryPerformanceCounter((LARGE_INTEGER*)&OS_start);
 Sleep(1);
 QueryPerformanceCounter((LARGE_INTEGER*)&OS_end);

 // CPU clock is ~1000x faster than mobo clock    
    // return raw
 return ((CPU_end - CPU_start)/(OS_end - OS_start));

    // or
 // return a random number from 0 to 9
 // return ((CPU_end - CPU_start)/(OS_end - OS_start)%10);
}

如果你想知道为什么我Sleep(1),那是因为如果我不这样做,OS_end - OS_start会一直返回0(因为定时器分辨率不好,我认为)。

基本上,(CPU_end - CPU_start)/(OS_end - OS_start)总是返回围绕 1000,并根据CPU负载的熵略有变化,可能是温度,石英晶体振动不完善等等。

无论如何,这些数字的分布相当不错,但这可能是完全错误的。我不知道。

编辑:根据Stephen Nutt的说法,Sleep(1)可能没有做我期望的事情,所以我试图使用以下代替Sleep(1)

void loop() {
 __asm {
  mov ecx, 1000
  cylcles:
  nop
  loop cylcles
 }
}

2 个答案:

答案 0 :(得分:1)

考虑一些乘法来增加范围。然后使用结果为PRNG播种。

答案 1 :(得分:1)

Sleep功能受系统时钟分辨率的限制,因此Sleep (1)可能无法满足您的需求。