Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/linux/28.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Linux替代Windows高分辨率性能计数器API_Linux_Performancecounter - Fatal编程技术网

Linux替代Windows高分辨率性能计数器API

Linux替代Windows高分辨率性能计数器API,linux,performancecounter,Linux,Performancecounter,我正在寻找Linux替代Windows高分辨率性能计数器API,特别是以下API函数: 谢谢。随内核提供的perf工具现在可能满足了您的需要。它有大量的选项,因此请仔细研究;) 编辑:算了吧,我还以为你说的是CPU性能计数器。请参阅带有时钟\u单调\u原始标志和 下面是一个如何使用它的示例: Linuxperf\u event\u open系统调用 此系统调用以完全不可知的方式公开多个性能计数器 man perf_event_open记录了可用的计数器,其中包括您期望的所有最基本

我正在寻找Linux替代Windows高分辨率性能计数器API,特别是以下API函数:


谢谢。

随内核提供的
perf
工具现在可能满足了您的需要。它有大量的选项,因此请仔细研究;)

编辑:算了吧,我还以为你说的是CPU性能计数器。

请参阅带有
时钟\u单调\u原始
标志和

下面是一个如何使用它的示例:


Linux
perf\u event\u open
系统调用

此系统调用以完全不可知的方式公开多个性能计数器

man perf_event_open
记录了可用的计数器,其中包括您期望的所有最基本的内容:

  • 周期计数(
    config=PERF\u count\u HW\u CPU\u周期
  • 缓存命中和未命中(
    type=PERF\u type\u HW\u缓存
  • 分支未命中(
    config=PERF\u COUNT\u HW\u分支未命中
  • 内核软件可见事件,如页面错误(
    PERF\u COUNT\u SW\u page\u faults
    )和上下文开关(
    PERF\u COUNT\u SW\u context\u switches
我已在以下位置给出了循环计数的计算公式:

性能事件打开。c

#include <asm/unistd.h>
#include <linux/perf_event.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/ioctl.h>
#include <unistd.h>

#include <inttypes.h>

static long
perf_event_open(struct perf_event_attr *hw_event, pid_t pid,
                int cpu, int group_fd, unsigned long flags)
{
    int ret;

    ret = syscall(__NR_perf_event_open, hw_event, pid, cpu,
                    group_fd, flags);
    return ret;
}

int
main(int argc, char **argv)
{
    struct perf_event_attr pe;
    long long count;
    int fd;

    uint64_t n;
    if (argc > 1) {
        n = strtoll(argv[1], NULL, 0);
    } else {
        n = 10000;
    }

    memset(&pe, 0, sizeof(struct perf_event_attr));
    pe.type = PERF_TYPE_HARDWARE;
    pe.size = sizeof(struct perf_event_attr);
    pe.config = PERF_COUNT_HW_CPU_CYCLES;
    pe.disabled = 1;
    pe.exclude_kernel = 1;
    // Don't count hypervisor events.
    pe.exclude_hv = 1;

    fd = perf_event_open(&pe, 0, -1, -1, 0);
    if (fd == -1) {
        fprintf(stderr, "Error opening leader %llx\n", pe.config);
        exit(EXIT_FAILURE);
    }

    ioctl(fd, PERF_EVENT_IOC_RESET, 0);
    ioctl(fd, PERF_EVENT_IOC_ENABLE, 0);

    /* Loop n times, should be good enough for -O0. */
    __asm__ (
        "1:;\n"
        "sub $1, %[n];\n"
        "jne 1b;\n"
        : [n] "+r" (n)
        :
        :
    );

    ioctl(fd, PERF_EVENT_IOC_DISABLE, 0);
    read(fd, &count, sizeof(long long));

    printf("%lld\n", count);

    close(fd);
}
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#包括
静长
性能事件打开(结构性能事件属性*硬件事件,pid,
int cpu、int group_fd、无符号长标志)
{
int ret;
ret=syscall(_unr_perf_event_open,hw_event,pid,cpu,
组(fd,flags),;
返回ret;
}
int
主(内部argc,字符**argv)
{
结构性能事件属性;
长计数;
int-fd;
uint64\u t n;
如果(argc>1){
n=strtoll(argv[1],NULL,0);
}否则{
n=10000;
}
memset(&pe,0,sizeof(struct perf_event_attr));
pe.type=性能类型硬件;
pe.size=sizeof(结构性能事件属性);
pe.config=性能计数\u硬件\u CPU \u周期;
pe.disabled=1;
pe.exclude_kernel=1;
//不要计算虚拟机监控程序事件。
pe.hv=1;
fd=性能事件打开(&pe,0,-1,-1,0);
如果(fd==-1){
fprintf(stderr,“打开引线%llx\n时出错”,pe.config);
退出(退出失败);
}
ioctl(fd,性能事件IOC重置,0);
ioctl(fd,性能事件IOC启用,0);
/*循环n次,对于-O0应该足够好*/
__阿斯马(
“1:;\n”
“子$1,%[n];\n”
“jne 1b;\n”
:[n]“+r”(n)
:
:
);
ioctl(fd,性能事件IOC禁用,0);
读取(fd、计数和大小(长));
printf(“%lld\n”,计数);
关闭(fd);
}

感谢您的快速回复。我需要在cpp程序中使用这些函数。我该怎么做?@user1087995:
perf
是一个分析工具,它可以为您获取许多指标,但它甚至不接近Windows上的
QueryPerformanceCounter
功能。因此,
perf
不是答案
clock_gettime()
为您提供高精度(硬件)墙壁时间。使用它。嗯,好吧,当我看到“性能计数器”时,我真的认为CPU性能计数器是指,但这里似乎不是这样。我仍然无法理解:当我尝试使用clock\u gettime(clock\u id,&tp);tp只返回所经过的时间(以微秒和秒为单位),我需要的是周期数(=tickes)。@user1087995:CPU周期?但是什么呢?您的程序可以安排在不同的CPU上,除非您显式地设置CPU相关性。这种衡量绩效的方法几乎已经过时。但如果你仍然想这样做,看看RDTSC——但为了获得精度,你必须知道CPU频率,以便将周期数转换成时间。然而,CPU频率可能是非恒定的,即Intel有用于节能的Turbo Boost技术。换句话说,Windows有问题。@ScrollerBlaster:谢谢你的提示。我提供了一个新链接。虽然现在它略为C,并且也移植到了OS X。如果你想用C99支持编译秒表,你必须使用gcc标志
-std=gnu99
,而不是
-std=C99
,它才能工作。只是因为我花了一个小时才加上:)