1b2441318SGreg Kroah-Hartman // SPDX-License-Identifier: GPL-2.0 2a43783aeSArnaldo Carvalho de Melo #include <errno.h> 3fd20e811SArnaldo Carvalho de Melo #include <inttypes.h> 4bc96b361SNamhyung Kim #include <unistd.h> 5bc96b361SNamhyung Kim #include <stdlib.h> 6bc96b361SNamhyung Kim #include <signal.h> 7bc96b361SNamhyung Kim #include <sys/mman.h> 8bc96b361SNamhyung Kim 9bc96b361SNamhyung Kim #include "tests.h" 10bc96b361SNamhyung Kim #include "util/evsel.h" 11bc96b361SNamhyung Kim #include "util/evlist.h" 12bc96b361SNamhyung Kim #include "util/cpumap.h" 13bc96b361SNamhyung Kim #include "util/thread_map.h" 14bc96b361SNamhyung Kim 153fe21305SAdrian Hunter #define NR_LOOPS 10000000 16bc96b361SNamhyung Kim 17bc96b361SNamhyung Kim /* 18bc96b361SNamhyung Kim * This test will open software clock events (cpu-clock, task-clock) 19bc96b361SNamhyung Kim * then check their frequency -> period conversion has no artifact of 20bc96b361SNamhyung Kim * setting period to 1 forcefully. 21bc96b361SNamhyung Kim */ 22bc96b361SNamhyung Kim static int __test__sw_clock_freq(enum perf_sw_ids clock_id) 23bc96b361SNamhyung Kim { 24bc96b361SNamhyung Kim int i, err = -1; 25bc96b361SNamhyung Kim volatile int tmp = 0; 26bc96b361SNamhyung Kim u64 total_periods = 0; 27bc96b361SNamhyung Kim int nr_samples = 0; 28ba3dfff8SMasami Hiramatsu char sbuf[STRERR_BUFSIZE]; 29bc96b361SNamhyung Kim union perf_event *event; 3032dcd021SJiri Olsa struct evsel *evsel; 31*63503dbaSJiri Olsa struct evlist *evlist; 32bc96b361SNamhyung Kim struct perf_event_attr attr = { 33bc96b361SNamhyung Kim .type = PERF_TYPE_SOFTWARE, 34bc96b361SNamhyung Kim .config = clock_id, 35bc96b361SNamhyung Kim .sample_type = PERF_SAMPLE_PERIOD, 36bc96b361SNamhyung Kim .exclude_kernel = 1, 37bc96b361SNamhyung Kim .disabled = 1, 38bc96b361SNamhyung Kim .freq = 1, 39bc96b361SNamhyung Kim }; 40f854839bSJiri Olsa struct perf_cpu_map *cpus; 419749b90eSJiri Olsa struct perf_thread_map *threads; 425d0007cdSKan Liang struct perf_mmap *md; 43bc96b361SNamhyung Kim 4467c1e4a5SArnaldo Carvalho de Melo attr.sample_freq = 500; 45bc96b361SNamhyung Kim 46bc96b361SNamhyung Kim evlist = perf_evlist__new(); 47bc96b361SNamhyung Kim if (evlist == NULL) { 48bc96b361SNamhyung Kim pr_debug("perf_evlist__new\n"); 49bc96b361SNamhyung Kim return -1; 50bc96b361SNamhyung Kim } 51bc96b361SNamhyung Kim 52ef503831SArnaldo Carvalho de Melo evsel = perf_evsel__new(&attr); 53bc96b361SNamhyung Kim if (evsel == NULL) { 54bc96b361SNamhyung Kim pr_debug("perf_evsel__new\n"); 5503ad9747SArnaldo Carvalho de Melo goto out_delete_evlist; 56bc96b361SNamhyung Kim } 57bc96b361SNamhyung Kim perf_evlist__add(evlist, evsel); 58bc96b361SNamhyung Kim 59c5e6bd2eSAdrian Hunter cpus = cpu_map__dummy_new(); 60c5e6bd2eSAdrian Hunter threads = thread_map__new_by_tid(getpid()); 61c5e6bd2eSAdrian Hunter if (!cpus || !threads) { 62bc96b361SNamhyung Kim err = -ENOMEM; 63bc96b361SNamhyung Kim pr_debug("Not enough memory to create thread/cpu maps\n"); 64c5e6bd2eSAdrian Hunter goto out_free_maps; 65bc96b361SNamhyung Kim } 66bc96b361SNamhyung Kim 67c5e6bd2eSAdrian Hunter perf_evlist__set_maps(evlist, cpus, threads); 68c5e6bd2eSAdrian Hunter 69c5e6bd2eSAdrian Hunter cpus = NULL; 70c5e6bd2eSAdrian Hunter threads = NULL; 71c5e6bd2eSAdrian Hunter 72d0b849e9SArnaldo Carvalho de Melo if (perf_evlist__open(evlist)) { 7367c1e4a5SArnaldo Carvalho de Melo const char *knob = "/proc/sys/kernel/perf_event_max_sample_rate"; 7467c1e4a5SArnaldo Carvalho de Melo 75d0b849e9SArnaldo Carvalho de Melo err = -errno; 7667c1e4a5SArnaldo Carvalho de Melo pr_debug("Couldn't open evlist: %s\nHint: check %s, using %" PRIu64 " in this test.\n", 77c8b5f2c9SArnaldo Carvalho de Melo str_error_r(errno, sbuf, sizeof(sbuf)), 78ba3dfff8SMasami Hiramatsu knob, (u64)attr.sample_freq); 7903ad9747SArnaldo Carvalho de Melo goto out_delete_evlist; 80d0b849e9SArnaldo Carvalho de Melo } 81bc96b361SNamhyung Kim 82f74b9d3aSWang Nan err = perf_evlist__mmap(evlist, 128); 83bc96b361SNamhyung Kim if (err < 0) { 84bc96b361SNamhyung Kim pr_debug("failed to mmap event: %d (%s)\n", errno, 85c8b5f2c9SArnaldo Carvalho de Melo str_error_r(errno, sbuf, sizeof(sbuf))); 86f26e1c7cSArnaldo Carvalho de Melo goto out_delete_evlist; 87bc96b361SNamhyung Kim } 88bc96b361SNamhyung Kim 89bc96b361SNamhyung Kim perf_evlist__enable(evlist); 90bc96b361SNamhyung Kim 91bc96b361SNamhyung Kim /* collect samples */ 92bc96b361SNamhyung Kim for (i = 0; i < NR_LOOPS; i++) 93bc96b361SNamhyung Kim tmp++; 94bc96b361SNamhyung Kim 95bc96b361SNamhyung Kim perf_evlist__disable(evlist); 96bc96b361SNamhyung Kim 975d0007cdSKan Liang md = &evlist->mmap[0]; 98b9bae2c8SKan Liang if (perf_mmap__read_init(md) < 0) 995d0007cdSKan Liang goto out_init; 1005d0007cdSKan Liang 1010019dc87SKan Liang while ((event = perf_mmap__read_event(md)) != NULL) { 102bc96b361SNamhyung Kim struct perf_sample sample; 103bc96b361SNamhyung Kim 104bc96b361SNamhyung Kim if (event->header.type != PERF_RECORD_SAMPLE) 1058e50d384SZhouyi Zhou goto next_event; 106bc96b361SNamhyung Kim 107bc96b361SNamhyung Kim err = perf_evlist__parse_sample(evlist, event, &sample); 108bc96b361SNamhyung Kim if (err < 0) { 109bc96b361SNamhyung Kim pr_debug("Error during parse sample\n"); 110983874d1SArnaldo Carvalho de Melo goto out_delete_evlist; 111bc96b361SNamhyung Kim } 112bc96b361SNamhyung Kim 113bc96b361SNamhyung Kim total_periods += sample.period; 114bc96b361SNamhyung Kim nr_samples++; 1158e50d384SZhouyi Zhou next_event: 116d6ace3dfSKan Liang perf_mmap__consume(md); 117bc96b361SNamhyung Kim } 1185d0007cdSKan Liang perf_mmap__read_done(md); 119bc96b361SNamhyung Kim 1205d0007cdSKan Liang out_init: 121bc96b361SNamhyung Kim if ((u64) nr_samples == total_periods) { 122bc96b361SNamhyung Kim pr_debug("All (%d) samples have period value of 1!\n", 123bc96b361SNamhyung Kim nr_samples); 124bc96b361SNamhyung Kim err = -1; 125bc96b361SNamhyung Kim } 126bc96b361SNamhyung Kim 127c5e6bd2eSAdrian Hunter out_free_maps: 128c5e6bd2eSAdrian Hunter cpu_map__put(cpus); 129c5e6bd2eSAdrian Hunter thread_map__put(threads); 13003ad9747SArnaldo Carvalho de Melo out_delete_evlist: 131bc96b361SNamhyung Kim perf_evlist__delete(evlist); 132bc96b361SNamhyung Kim return err; 133bc96b361SNamhyung Kim } 134bc96b361SNamhyung Kim 13581f17c90SArnaldo Carvalho de Melo int test__sw_clock_freq(struct test *test __maybe_unused, int subtest __maybe_unused) 136bc96b361SNamhyung Kim { 137bc96b361SNamhyung Kim int ret; 138bc96b361SNamhyung Kim 139bc96b361SNamhyung Kim ret = __test__sw_clock_freq(PERF_COUNT_SW_CPU_CLOCK); 140bc96b361SNamhyung Kim if (!ret) 141bc96b361SNamhyung Kim ret = __test__sw_clock_freq(PERF_COUNT_SW_TASK_CLOCK); 142bc96b361SNamhyung Kim 143bc96b361SNamhyung Kim return ret; 144bc96b361SNamhyung Kim } 145