硬件处理器计数器复位不正确 [英] Hardware Processor Counters Incorrectly Resetting

查看:121
本文介绍了硬件处理器计数器复位不正确的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我写了一个程序,在<一个读取芯片的英特尔(第2页的APERF / MPERF柜href=\"http://www.intel.com/content/dam/doc/manual/64-ia-32-architectures-software-developer-vol-3b-part-2-manual.pdf\" rel=\"nofollow\">http://www.intel.com/content/dam/doc/manual/64-ia-32-architectures-software-developer-vol-3b-part-2-manual.pdf).

这些计数器读通过readmsr / writemsr指令/写的,和我目前只需通过一个设备驱动程序每隔一定的时间阅读他们在Windows 7中的计数器都是64位,并且每个处理器时钟大约递增,所以你指望他们在很长的时间溢出,但是当我读了柜台,就好像它们正在被另一个程序重置其价值跳动。

有没有办法追查什么程序将重置计数器?难道别的东西会导致不正确的值被读取?有关装配和相应的C函数我使用的是附后。从RDMSR 64位结果保存到EAX:EDX,所以要确保我没有在r_x寄存器缺少任何数字,我运行命令多次检查它们的所有

C:

 长长TEST1,TEST2,TEST3,TEST4;
TEST1 = TST1();
测试2 = TST2();
TEST3 = TST3();
TEST4 = TST4();
状态= RtlStringCbPrintfA(缓冲区的sizeof(缓冲),价值:%LLU%LLU%LLU%LLU \\ n,为test1,test2的,TEST3,TEST4);

大会:

  ;;;;;;;;;;;;;;;;;;;
公共TST1
TST1 PROC
    MOV ECX,231; 0xE7
    RDMSR
    RET;回报RAX
TST1 ENDP;;;;;;;;;;;;;;;;;;;
公共TST2
TST2 PROC
    MOV ECX,231; 0xE7
    RDMSR
    MOV RAX,RBX
    RET;回报RAX
TST2 ENDP;;;;;;;;;;;;;;;;;;;
公共TST3
TST3 PROC
    MOV ECX,231; 0xE7
    RDMSR
    MOV RAX,RCX
    RET;回报RAX
TST3 ENDP;;;;;;;;;;;;;;;;;;;
公共TST4
TST4 PROC
    MOV ECX,231; 0xE7
    RDMSR
    MOV RAX,RDX
    RET;回报RAX
TST4 ENDP

这是打印出来的结果是类似下面,但都没有改变的唯一寄存器是RAX寄存器,它并不单调增加(可以跳来跳去):

 值:312664 37 231 0
价值:252576 37 231 0
价值:1051857 37 231 0


解决方案

我无法弄清楚什么是重置我的柜台,但我能够确定的频率。英特尔文档指出,当一个计数器溢出,其他计数器也将。因此,即使计数器复位不断,aperf和mperf的比例仍然不重新present处理器的频率。

I wrote a program which reads the APERF/MPERF counters on an Intel chip (page 2 on http://www.intel.com/content/dam/doc/manual/64-ia-32-architectures-software-developer-vol-3b-part-2-manual.pdf).

These counters are readable/writable via the readmsr/writemsr instructions, and I'm currently simply reading them at a regular interval via a device driver in Windows 7. The counters are 64 bits, and increment approximately with each processor clock, so you'd expect them to overflow in a very long amount of time, but when I read the counters, their value jumps around as if they are being reset by another program.

Is there any way to track down what program would be resetting the counters? Could something else be causing incorrect values to be read? The relevant assembly and corresponding C functions I'm using are attached below. The 64-bit result from rdmsr is saved into eax:edx, so to make sure I wasn't missing any numbers in the r_x registers, I run the command multiple times to check them all.

C:

long long test1, test2, test3, test4;
test1 = TST1();
test2 = TST2();
test3 = TST3();
test4 = TST4();
status = RtlStringCbPrintfA(buffer, sizeof(buffer), "Value: %llu %llu %llu %llu\n", test1, test2, test3, test4);

Assembly:

;;;;;;;;;;;;;;;;;;;
PUBLIC TST1 
TST1 proc
    mov ecx, 231 ; 0xE7
    rdmsr
    ret ; returns rax
TST1 endp

;;;;;;;;;;;;;;;;;;;
PUBLIC TST2 
TST2 proc
    mov ecx, 231 ; 0xE7
    rdmsr
    mov rax, rbx
    ret ; returns rax
TST2 endp

;;;;;;;;;;;;;;;;;;;
PUBLIC TST3 
TST3 proc
    mov ecx, 231 ; 0xE7
    rdmsr
    mov rax, rcx
    ret ; returns rax
TST3 endp

;;;;;;;;;;;;;;;;;;;
PUBLIC TST4 
TST4  proc
    mov ecx, 231 ; 0xE7
    rdmsr
    mov rax, rdx
    ret ; returns rax
TST4 endp

The result that prints out is something like below, but the only register which ever changes is the rax register, and it doesn't increase monotonically (can jump around):

Value: 312664 37 231 0
Value: 252576 37 231 0
Value: 1051857 37 231 0

解决方案

I was not able to figure out what was resetting my counters, but I was able to determine the frequency. The Intel docs state that when one counter overflows, the other counter also will. So even though the counters are constantly resetting, the ratio of aperf and mperf still does represent the processor's frequency.

这篇关于硬件处理器计数器复位不正确的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆