-
-
Save o-/e644cbb2fef3d4b55d59f3b00d3c2079 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include <unistd.h> | |
#include <linux/fcntl.h> | |
#include <errno.h> | |
#include <stdlib.h> | |
#include <stdio.h> | |
#include <unistd.h> | |
#include <string.h> | |
#include <sys/ioctl.h> | |
#include <linux/perf_event.h> | |
#include <asm/unistd.h> | |
#include <signal.h> | |
#include <stdio.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; | |
} | |
static int counter = 0; | |
static void handler(int sig, siginfo_t *si, void *data) | |
{ | |
counter++; | |
} | |
int | |
main(int argc, char **argv) | |
{ | |
struct sigaction sa; | |
sa.sa_sigaction = handler; | |
sigemptyset(&sa.sa_mask); | |
sa.sa_flags = SA_SIGINFO; | |
sigaction(SIGRTMIN + 1, &sa, NULL); | |
struct perf_event_attr pe; | |
long long count; | |
int fd; | |
memset(&pe, 0, sizeof(struct perf_event_attr)); | |
pe.type = PERF_TYPE_SOFTWARE; | |
pe.size = sizeof(struct perf_event_attr); | |
pe.config = PERF_COUNT_SW_TASK_CLOCK; | |
pe.sample_type = PERF_SAMPLE_IP; | |
pe.disabled = 1; | |
pe.exclude_kernel = 1; | |
pe.exclude_hv = 1; | |
pe.exclude_idle = 1; | |
pe.wakeup_events = 10; | |
fd = perf_event_open(&pe, 0, -1, -1, 0); | |
if (fd == -1) { | |
int e = errno; | |
fprintf(stderr, "Error %d opening leader %llx\n", e, pe.config); | |
exit(EXIT_FAILURE); | |
} | |
// fcntl(fd, F_SETFL, O_RDWR|O_NONBLOCK); | |
// fcntl(fd, F_SETSIG, SIGRTMIN + 1); | |
// fcntl(fd, F_SETOWN,getpid()); | |
if(fcntl(fd, F_SETOWN, getpid()) < 0) | |
error(EXIT_FAILURE, errno, "failed to set dnotify signal"); | |
if(fcntl(fd, F_SETSIG, SIGRTMIN + 1) < 0) | |
error(EXIT_FAILURE, errno, "failed to set dnotify signal"); | |
// if(fcntl(fd, F_NOTIFY, DN_MODIFY)) | |
// error(EXIT_FAILURE, errno, | |
// "failed to register notification for '%s'", argv[1]); | |
ioctl(fd, PERF_EVENT_IOC_RESET, 0); | |
ioctl(fd, PERF_EVENT_IOC_ENABLE, 0); | |
for (size_t i = 0; i < 10000; ++i) | |
printf("Measuring instruction count for this printf\n"); | |
ioctl(fd, PERF_EVENT_IOC_DISABLE, 0); | |
read(fd, &count, sizeof(long long)); | |
printf("Used %lld instructions\n", count); | |
printf("Triggered %lld sigs\n", counter); | |
close(fd); | |
} | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment