~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

TOMOYO Linux Cross Reference
Linux/tools/perf/tests/backward-ring-buffer.c

Version: ~ [ linux-6.11.5 ] ~ [ linux-6.10.14 ] ~ [ linux-6.9.12 ] ~ [ linux-6.8.12 ] ~ [ linux-6.7.12 ] ~ [ linux-6.6.58 ] ~ [ linux-6.5.13 ] ~ [ linux-6.4.16 ] ~ [ linux-6.3.13 ] ~ [ linux-6.2.16 ] ~ [ linux-6.1.114 ] ~ [ linux-6.0.19 ] ~ [ linux-5.19.17 ] ~ [ linux-5.18.19 ] ~ [ linux-5.17.15 ] ~ [ linux-5.16.20 ] ~ [ linux-5.15.169 ] ~ [ linux-5.14.21 ] ~ [ linux-5.13.19 ] ~ [ linux-5.12.19 ] ~ [ linux-5.11.22 ] ~ [ linux-5.10.228 ] ~ [ linux-5.9.16 ] ~ [ linux-5.8.18 ] ~ [ linux-5.7.19 ] ~ [ linux-5.6.19 ] ~ [ linux-5.5.19 ] ~ [ linux-5.4.284 ] ~ [ linux-5.3.18 ] ~ [ linux-5.2.21 ] ~ [ linux-5.1.21 ] ~ [ linux-5.0.21 ] ~ [ linux-4.20.17 ] ~ [ linux-4.19.322 ] ~ [ linux-4.18.20 ] ~ [ linux-4.17.19 ] ~ [ linux-4.16.18 ] ~ [ linux-4.15.18 ] ~ [ linux-4.14.336 ] ~ [ linux-4.13.16 ] ~ [ linux-4.12.14 ] ~ [ linux-4.11.12 ] ~ [ linux-4.10.17 ] ~ [ linux-4.9.337 ] ~ [ linux-4.4.302 ] ~ [ linux-3.10.108 ] ~ [ linux-2.6.32.71 ] ~ [ linux-2.6.0 ] ~ [ linux-2.4.37.11 ] ~ [ unix-v6-master ] ~ [ ccs-tools-1.8.9 ] ~ [ policy-sample ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

  1 // SPDX-License-Identifier: GPL-2.0
  2 /*
  3  * Test backward bit in event attribute, read ring buffer from end to
  4  * beginning
  5  */
  6 
  7 #include <evlist.h>
  8 #include <sys/prctl.h>
  9 #include "record.h"
 10 #include "tests.h"
 11 #include "debug.h"
 12 #include "parse-events.h"
 13 #include "util/mmap.h"
 14 #include <errno.h>
 15 #include <linux/string.h>
 16 #include <perf/mmap.h>
 17 
 18 #define NR_ITERS 111
 19 
 20 static void testcase(void)
 21 {
 22         int i;
 23 
 24         for (i = 0; i < NR_ITERS; i++) {
 25                 char proc_name[15];
 26 
 27                 snprintf(proc_name, sizeof(proc_name), "p:%d\n", i);
 28                 prctl(PR_SET_NAME, proc_name);
 29         }
 30 }
 31 
 32 static int count_samples(struct evlist *evlist, int *sample_count,
 33                          int *comm_count)
 34 {
 35         int i;
 36 
 37         for (i = 0; i < evlist->core.nr_mmaps; i++) {
 38                 struct mmap *map = &evlist->overwrite_mmap[i];
 39                 union perf_event *event;
 40 
 41                 perf_mmap__read_init(&map->core);
 42                 while ((event = perf_mmap__read_event(&map->core)) != NULL) {
 43                         const u32 type = event->header.type;
 44 
 45                         switch (type) {
 46                         case PERF_RECORD_SAMPLE:
 47                                 (*sample_count)++;
 48                                 break;
 49                         case PERF_RECORD_COMM:
 50                                 (*comm_count)++;
 51                                 break;
 52                         default:
 53                                 pr_err("Unexpected record of type %d\n", type);
 54                                 return TEST_FAIL;
 55                         }
 56                 }
 57                 perf_mmap__read_done(&map->core);
 58         }
 59         return TEST_OK;
 60 }
 61 
 62 static int do_test(struct evlist *evlist, int mmap_pages,
 63                    int *sample_count, int *comm_count)
 64 {
 65         int err;
 66         char sbuf[STRERR_BUFSIZE];
 67 
 68         err = evlist__mmap(evlist, mmap_pages);
 69         if (err < 0) {
 70                 pr_debug("evlist__mmap: %s\n",
 71                          str_error_r(errno, sbuf, sizeof(sbuf)));
 72                 return TEST_FAIL;
 73         }
 74 
 75         evlist__enable(evlist);
 76         testcase();
 77         evlist__disable(evlist);
 78 
 79         err = count_samples(evlist, sample_count, comm_count);
 80         evlist__munmap(evlist);
 81         return err;
 82 }
 83 
 84 
 85 static int test__backward_ring_buffer(struct test_suite *test __maybe_unused, int subtest __maybe_unused)
 86 {
 87         int ret = TEST_SKIP, err, sample_count = 0, comm_count = 0;
 88         char pid[16], sbuf[STRERR_BUFSIZE];
 89         struct evlist *evlist;
 90         struct evsel *evsel __maybe_unused;
 91         struct parse_events_error parse_error;
 92         struct record_opts opts = {
 93                 .target = {
 94                         .uid = UINT_MAX,
 95                         .uses_mmap = true,
 96                 },
 97                 .freq         = 0,
 98                 .mmap_pages   = 256,
 99                 .default_interval = 1,
100         };
101 
102         snprintf(pid, sizeof(pid), "%d", getpid());
103         pid[sizeof(pid) - 1] = '\0';
104         opts.target.tid = opts.target.pid = pid;
105 
106         evlist = evlist__new();
107         if (!evlist) {
108                 pr_debug("Not enough memory to create evlist\n");
109                 return TEST_FAIL;
110         }
111 
112         err = evlist__create_maps(evlist, &opts.target);
113         if (err < 0) {
114                 pr_debug("Not enough memory to create thread/cpu maps\n");
115                 goto out_delete_evlist;
116         }
117 
118         parse_events_error__init(&parse_error);
119         /*
120          * Set backward bit, ring buffer should be writing from end. Record
121          * it in aux evlist
122          */
123         err = parse_events(evlist, "syscalls:sys_enter_prctl/overwrite/", &parse_error);
124         parse_events_error__exit(&parse_error);
125         if (err) {
126                 pr_debug("Failed to parse tracepoint event, try use root\n");
127                 ret = TEST_SKIP;
128                 goto out_delete_evlist;
129         }
130 
131         evlist__config(evlist, &opts, NULL);
132 
133         err = evlist__open(evlist);
134         if (err < 0) {
135                 pr_debug("perf_evlist__open: %s\n",
136                          str_error_r(errno, sbuf, sizeof(sbuf)));
137                 goto out_delete_evlist;
138         }
139 
140         ret = TEST_FAIL;
141         err = do_test(evlist, opts.mmap_pages, &sample_count,
142                       &comm_count);
143         if (err != TEST_OK)
144                 goto out_delete_evlist;
145 
146         if ((sample_count != NR_ITERS) || (comm_count != NR_ITERS)) {
147                 pr_err("Unexpected counter: sample_count=%d, comm_count=%d\n",
148                        sample_count, comm_count);
149                 goto out_delete_evlist;
150         }
151 
152         evlist__close(evlist);
153 
154         err = evlist__open(evlist);
155         if (err < 0) {
156                 pr_debug("perf_evlist__open: %s\n",
157                          str_error_r(errno, sbuf, sizeof(sbuf)));
158                 goto out_delete_evlist;
159         }
160 
161         err = do_test(evlist, 1, &sample_count, &comm_count);
162         if (err != TEST_OK)
163                 goto out_delete_evlist;
164 
165         ret = TEST_OK;
166 out_delete_evlist:
167         evlist__delete(evlist);
168         return ret;
169 }
170 
171 DEFINE_SUITE("Read backward ring buffer", backward_ring_buffer);
172 

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

kernel.org | git.kernel.org | LWN.net | Project Home | SVN repository | Mail admin

Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.

sflogo.php