Linux Perf
thread-map.c
Go to the documentation of this file.
1 // SPDX-License-Identifier: GPL-2.0
2 #include <stdlib.h>
3 #include <sys/types.h>
4 #include <unistd.h>
5 #include <sys/prctl.h>
6 #include "tests.h"
7 #include "thread_map.h"
8 #include "debug.h"
9 
10 #define NAME (const char *) "perf"
11 #define NAMEUL (unsigned long) NAME
12 
13 int test__thread_map(struct test *test __maybe_unused, int subtest __maybe_unused)
14 {
15  struct thread_map *map;
16 
17  TEST_ASSERT_VAL("failed to set process name",
18  !prctl(PR_SET_NAME, NAMEUL, 0, 0, 0));
19 
20  /* test map on current pid */
21  map = thread_map__new_by_pid(getpid());
22  TEST_ASSERT_VAL("failed to alloc map", map);
23 
25 
26  TEST_ASSERT_VAL("wrong nr", map->nr == 1);
27  TEST_ASSERT_VAL("wrong pid",
28  thread_map__pid(map, 0) == getpid());
29  TEST_ASSERT_VAL("wrong comm",
30  thread_map__comm(map, 0) &&
31  !strcmp(thread_map__comm(map, 0), NAME));
32  TEST_ASSERT_VAL("wrong refcnt",
33  refcount_read(&map->refcnt) == 1);
34  thread_map__put(map);
35 
36  /* test dummy pid */
37  map = thread_map__new_dummy();
38  TEST_ASSERT_VAL("failed to alloc map", map);
39 
41 
42  TEST_ASSERT_VAL("wrong nr", map->nr == 1);
43  TEST_ASSERT_VAL("wrong pid", thread_map__pid(map, 0) == -1);
44  TEST_ASSERT_VAL("wrong comm",
45  thread_map__comm(map, 0) &&
46  !strcmp(thread_map__comm(map, 0), "dummy"));
47  TEST_ASSERT_VAL("wrong refcnt",
48  refcount_read(&map->refcnt) == 1);
49  thread_map__put(map);
50  return 0;
51 }
52 
53 static int process_event(struct perf_tool *tool __maybe_unused,
54  union perf_event *event,
55  struct perf_sample *sample __maybe_unused,
56  struct machine *machine __maybe_unused)
57 {
58  struct thread_map_event *map = &event->thread_map;
59  struct thread_map *threads;
60 
61  TEST_ASSERT_VAL("wrong nr", map->nr == 1);
62  TEST_ASSERT_VAL("wrong pid", map->entries[0].pid == (u64) getpid());
63  TEST_ASSERT_VAL("wrong comm", !strcmp(map->entries[0].comm, NAME));
64 
65  threads = thread_map__new_event(&event->thread_map);
66  TEST_ASSERT_VAL("failed to alloc map", threads);
67 
68  TEST_ASSERT_VAL("wrong nr", threads->nr == 1);
69  TEST_ASSERT_VAL("wrong pid",
70  thread_map__pid(threads, 0) == getpid());
71  TEST_ASSERT_VAL("wrong comm",
72  thread_map__comm(threads, 0) &&
73  !strcmp(thread_map__comm(threads, 0), NAME));
74  TEST_ASSERT_VAL("wrong refcnt",
75  refcount_read(&threads->refcnt) == 1);
76  thread_map__put(threads);
77  return 0;
78 }
79 
80 int test__thread_map_synthesize(struct test *test __maybe_unused, int subtest __maybe_unused)
81 {
82  struct thread_map *threads;
83 
84  TEST_ASSERT_VAL("failed to set process name",
85  !prctl(PR_SET_NAME, NAMEUL, 0, 0, 0));
86 
87  /* test map on current pid */
88  threads = thread_map__new_by_pid(getpid());
89  TEST_ASSERT_VAL("failed to alloc map", threads);
90 
91  thread_map__read_comms(threads);
92 
93  TEST_ASSERT_VAL("failed to synthesize map",
94  !perf_event__synthesize_thread_map2(NULL, threads, process_event, NULL));
95 
96  return 0;
97 }
98 
99 int test__thread_map_remove(struct test *test __maybe_unused, int subtest __maybe_unused)
100 {
101  struct thread_map *threads;
102  char *str;
103  int i;
104 
105  TEST_ASSERT_VAL("failed to allocate map string",
106  asprintf(&str, "%d,%d", getpid(), getppid()) >= 0);
107 
108  threads = thread_map__new_str(str, NULL, 0, false);
109 
110  TEST_ASSERT_VAL("failed to allocate thread_map",
111  threads);
112 
113  if (verbose > 0)
114  thread_map__fprintf(threads, stderr);
115 
116  TEST_ASSERT_VAL("failed to remove thread",
117  !thread_map__remove(threads, 0));
118 
119  TEST_ASSERT_VAL("thread_map count != 1", threads->nr == 1);
120 
121  if (verbose > 0)
122  thread_map__fprintf(threads, stderr);
123 
124  TEST_ASSERT_VAL("failed to remove thread",
125  !thread_map__remove(threads, 0));
126 
127  TEST_ASSERT_VAL("thread_map count != 0", threads->nr == 0);
128 
129  if (verbose > 0)
130  thread_map__fprintf(threads, stderr);
131 
132  TEST_ASSERT_VAL("failed to not remove thread",
133  thread_map__remove(threads, 0));
134 
135  for (i = 0; i < threads->nr; i++)
136  free(threads->map[i].comm);
137 
138  free(threads);
139  return 0;
140 }
int thread_map__remove(struct thread_map *threads, int idx)
Definition: thread_map.c:469
struct thread_map * thread_map__new_dummy(void)
Definition: thread_map.c:265
struct thread_map_event_entry entries[]
Definition: event.h:561
struct thread_map * thread_map__new_str(const char *pid, const char *tid, uid_t uid, bool all_threads)
Definition: thread_map.c:326
#define TEST_ASSERT_VAL(text, cond)
Definition: tests.h:7
int test__thread_map_synthesize(struct test *test __maybe_unused, int subtest __maybe_unused)
Definition: thread-map.c:80
char comm[16]
Definition: event.h:555
int test__thread_map_remove(struct test *test __maybe_unused, int subtest __maybe_unused)
Definition: thread-map.c:99
void thread_map__read_comms(struct thread_map *threads)
Definition: thread_map.c:423
struct thread_map * thread_map__new_by_pid(pid_t pid)
Definition: thread_map.c:55
#define PR_SET_NAME
Definition: builtin-sched.c:41
Definition: tool.h:44
static struct perf_tool tool
Definition: builtin-diff.c:362
struct thread_map * thread_map__new_event(struct thread_map_event *event)
Definition: thread_map.c:446
static int str(yyscan_t scanner, int token)
static char * thread_map__comm(struct thread_map *map, int thread)
Definition: thread_map.h:57
u64 pid
Definition: event.h:554
#define event
struct thread_map_data map[]
Definition: thread_map.h:18
size_t thread_map__fprintf(struct thread_map *threads, FILE *fp)
Definition: thread_map.c:367
refcount_t refcnt
Definition: thread_map.h:15
static struct thread_data threads[THREADS]
Definition: jevents.c:228
Definition: tests.h:30
void free(void *)
static pid_t thread_map__pid(struct thread_map *map, int thread)
Definition: thread_map.h:46
int test__thread_map(struct test *test __maybe_unused, int subtest __maybe_unused)
Definition: thread-map.c:13
void thread_map__put(struct thread_map *map)
Definition: thread_map.c:361
#define NAME
Definition: thread-map.c:10
struct thread_map_event thread_map
Definition: event.h:647
int verbose
Definition: jevents.c:53
#define NAMEUL
Definition: thread-map.c:11
static int process_event(struct perf_tool *tool __maybe_unused, union perf_event *event, struct perf_sample *sample __maybe_unused, struct machine *machine __maybe_unused)
Definition: thread-map.c:53
int perf_event__synthesize_thread_map2(struct perf_tool *tool, struct thread_map *threads, perf_event__handler_t process, struct machine *machine)
Definition: event.c:966