diff options
-rw-r--r-- | tools/perf/util/map.c | 18 | ||||
-rw-r--r-- | tools/perf/util/map.h | 7 | ||||
-rw-r--r-- | tools/perf/util/session.c | 7 | ||||
-rw-r--r-- | tools/perf/util/symbol.c | 43 | ||||
-rw-r--r-- | tools/perf/util/symbol.h | 2 |
5 files changed, 70 insertions, 7 deletions
diff --git a/tools/perf/util/map.c b/tools/perf/util/map.c index 15d6a6dd50c5..801e6962b0a6 100644 --- a/tools/perf/util/map.c +++ b/tools/perf/util/map.c | |||
@@ -506,6 +506,11 @@ void maps__insert(struct rb_root *maps, struct map *map) | |||
506 | rb_insert_color(&map->rb_node, maps); | 506 | rb_insert_color(&map->rb_node, maps); |
507 | } | 507 | } |
508 | 508 | ||
509 | void maps__remove(struct rb_root *self, struct map *map) | ||
510 | { | ||
511 | rb_erase(&map->rb_node, self); | ||
512 | } | ||
513 | |||
509 | struct map *maps__find(struct rb_root *maps, u64 ip) | 514 | struct map *maps__find(struct rb_root *maps, u64 ip) |
510 | { | 515 | { |
511 | struct rb_node **p = &maps->rb_node; | 516 | struct rb_node **p = &maps->rb_node; |
@@ -551,13 +556,6 @@ static void dsos__delete(struct list_head *self) | |||
551 | 556 | ||
552 | void machine__exit(struct machine *self) | 557 | void machine__exit(struct machine *self) |
553 | { | 558 | { |
554 | struct kmap *kmap = map__kmap(self->vmlinux_maps[MAP__FUNCTION]); | ||
555 | |||
556 | if (kmap->ref_reloc_sym) { | ||
557 | free((char *)kmap->ref_reloc_sym->name); | ||
558 | free(kmap->ref_reloc_sym); | ||
559 | } | ||
560 | |||
561 | map_groups__exit(&self->kmaps); | 559 | map_groups__exit(&self->kmaps); |
562 | dsos__delete(&self->user_dsos); | 560 | dsos__delete(&self->user_dsos); |
563 | dsos__delete(&self->kernel_dsos); | 561 | dsos__delete(&self->kernel_dsos); |
@@ -565,6 +563,12 @@ void machine__exit(struct machine *self) | |||
565 | self->root_dir = NULL; | 563 | self->root_dir = NULL; |
566 | } | 564 | } |
567 | 565 | ||
566 | void machine__delete(struct machine *self) | ||
567 | { | ||
568 | machine__exit(self); | ||
569 | free(self); | ||
570 | } | ||
571 | |||
568 | struct machine *machines__add(struct rb_root *self, pid_t pid, | 572 | struct machine *machines__add(struct rb_root *self, pid_t pid, |
569 | const char *root_dir) | 573 | const char *root_dir) |
570 | { | 574 | { |
diff --git a/tools/perf/util/map.h b/tools/perf/util/map.h index 0e0984e86fce..5b51bbd2f734 100644 --- a/tools/perf/util/map.h +++ b/tools/perf/util/map.h | |||
@@ -125,6 +125,7 @@ void map__reloc_vmlinux(struct map *self); | |||
125 | size_t __map_groups__fprintf_maps(struct map_groups *self, | 125 | size_t __map_groups__fprintf_maps(struct map_groups *self, |
126 | enum map_type type, int verbose, FILE *fp); | 126 | enum map_type type, int verbose, FILE *fp); |
127 | void maps__insert(struct rb_root *maps, struct map *map); | 127 | void maps__insert(struct rb_root *maps, struct map *map); |
128 | void maps__remove(struct rb_root *self, struct map *map); | ||
128 | struct map *maps__find(struct rb_root *maps, u64 addr); | 129 | struct map *maps__find(struct rb_root *maps, u64 addr); |
129 | void map_groups__init(struct map_groups *self); | 130 | void map_groups__init(struct map_groups *self); |
130 | void map_groups__exit(struct map_groups *self); | 131 | void map_groups__exit(struct map_groups *self); |
@@ -144,6 +145,7 @@ struct machine *machines__findnew(struct rb_root *self, pid_t pid); | |||
144 | char *machine__mmap_name(struct machine *self, char *bf, size_t size); | 145 | char *machine__mmap_name(struct machine *self, char *bf, size_t size); |
145 | int machine__init(struct machine *self, const char *root_dir, pid_t pid); | 146 | int machine__init(struct machine *self, const char *root_dir, pid_t pid); |
146 | void machine__exit(struct machine *self); | 147 | void machine__exit(struct machine *self); |
148 | void machine__delete(struct machine *self); | ||
147 | 149 | ||
148 | /* | 150 | /* |
149 | * Default guest kernel is defined by parameter --guestkallsyms | 151 | * Default guest kernel is defined by parameter --guestkallsyms |
@@ -165,6 +167,11 @@ static inline void map_groups__insert(struct map_groups *self, struct map *map) | |||
165 | map->groups = self; | 167 | map->groups = self; |
166 | } | 168 | } |
167 | 169 | ||
170 | static inline void map_groups__remove(struct map_groups *self, struct map *map) | ||
171 | { | ||
172 | maps__remove(&self->maps[map->type], map); | ||
173 | } | ||
174 | |||
168 | static inline struct map *map_groups__find(struct map_groups *self, | 175 | static inline struct map *map_groups__find(struct map_groups *self, |
169 | enum map_type type, u64 addr) | 176 | enum map_type type, u64 addr) |
170 | { | 177 | { |
diff --git a/tools/perf/util/session.c b/tools/perf/util/session.c index 04a3b3db9e90..5d2fd52fe7b5 100644 --- a/tools/perf/util/session.c +++ b/tools/perf/util/session.c | |||
@@ -79,6 +79,12 @@ int perf_session__create_kernel_maps(struct perf_session *self) | |||
79 | return ret; | 79 | return ret; |
80 | } | 80 | } |
81 | 81 | ||
82 | static void perf_session__destroy_kernel_maps(struct perf_session *self) | ||
83 | { | ||
84 | machine__destroy_kernel_maps(&self->host_machine); | ||
85 | machines__destroy_guest_kernel_maps(&self->machines); | ||
86 | } | ||
87 | |||
82 | struct perf_session *perf_session__new(const char *filename, int mode, bool force, bool repipe) | 88 | struct perf_session *perf_session__new(const char *filename, int mode, bool force, bool repipe) |
83 | { | 89 | { |
84 | size_t len = filename ? strlen(filename) + 1 : 0; | 90 | size_t len = filename ? strlen(filename) + 1 : 0; |
@@ -150,6 +156,7 @@ static void perf_session__delete_threads(struct perf_session *self) | |||
150 | void perf_session__delete(struct perf_session *self) | 156 | void perf_session__delete(struct perf_session *self) |
151 | { | 157 | { |
152 | perf_header__exit(&self->header); | 158 | perf_header__exit(&self->header); |
159 | perf_session__destroy_kernel_maps(self); | ||
153 | perf_session__delete_dead_threads(self); | 160 | perf_session__delete_dead_threads(self); |
154 | perf_session__delete_threads(self); | 161 | perf_session__delete_threads(self); |
155 | machine__exit(&self->host_machine); | 162 | machine__exit(&self->host_machine); |
diff --git a/tools/perf/util/symbol.c b/tools/perf/util/symbol.c index 3b8c00506672..6f0dd90c36ce 100644 --- a/tools/perf/util/symbol.c +++ b/tools/perf/util/symbol.c | |||
@@ -2107,6 +2107,36 @@ int __machine__create_kernel_maps(struct machine *self, struct dso *kernel) | |||
2107 | return 0; | 2107 | return 0; |
2108 | } | 2108 | } |
2109 | 2109 | ||
2110 | void machine__destroy_kernel_maps(struct machine *self) | ||
2111 | { | ||
2112 | enum map_type type; | ||
2113 | |||
2114 | for (type = 0; type < MAP__NR_TYPES; ++type) { | ||
2115 | struct kmap *kmap; | ||
2116 | |||
2117 | if (self->vmlinux_maps[type] == NULL) | ||
2118 | continue; | ||
2119 | |||
2120 | kmap = map__kmap(self->vmlinux_maps[type]); | ||
2121 | map_groups__remove(&self->kmaps, self->vmlinux_maps[type]); | ||
2122 | if (kmap->ref_reloc_sym) { | ||
2123 | /* | ||
2124 | * ref_reloc_sym is shared among all maps, so free just | ||
2125 | * on one of them. | ||
2126 | */ | ||
2127 | if (type == MAP__FUNCTION) { | ||
2128 | free((char *)kmap->ref_reloc_sym->name); | ||
2129 | kmap->ref_reloc_sym->name = NULL; | ||
2130 | free(kmap->ref_reloc_sym); | ||
2131 | } | ||
2132 | kmap->ref_reloc_sym = NULL; | ||
2133 | } | ||
2134 | |||
2135 | map__delete(self->vmlinux_maps[type]); | ||
2136 | self->vmlinux_maps[type] = NULL; | ||
2137 | } | ||
2138 | } | ||
2139 | |||
2110 | int machine__create_kernel_maps(struct machine *self) | 2140 | int machine__create_kernel_maps(struct machine *self) |
2111 | { | 2141 | { |
2112 | struct dso *kernel = machine__create_kernel(self); | 2142 | struct dso *kernel = machine__create_kernel(self); |
@@ -2351,6 +2381,19 @@ failure: | |||
2351 | return ret; | 2381 | return ret; |
2352 | } | 2382 | } |
2353 | 2383 | ||
2384 | void machines__destroy_guest_kernel_maps(struct rb_root *self) | ||
2385 | { | ||
2386 | struct rb_node *next = rb_first(self); | ||
2387 | |||
2388 | while (next) { | ||
2389 | struct machine *pos = rb_entry(next, struct machine, rb_node); | ||
2390 | |||
2391 | next = rb_next(&pos->rb_node); | ||
2392 | rb_erase(&pos->rb_node, self); | ||
2393 | machine__delete(pos); | ||
2394 | } | ||
2395 | } | ||
2396 | |||
2354 | int machine__load_kallsyms(struct machine *self, const char *filename, | 2397 | int machine__load_kallsyms(struct machine *self, const char *filename, |
2355 | enum map_type type, symbol_filter_t filter) | 2398 | enum map_type type, symbol_filter_t filter) |
2356 | { | 2399 | { |
diff --git a/tools/perf/util/symbol.h b/tools/perf/util/symbol.h index 33d53ce28958..906be20011d9 100644 --- a/tools/perf/util/symbol.h +++ b/tools/perf/util/symbol.h | |||
@@ -212,11 +212,13 @@ int kallsyms__parse(const char *filename, void *arg, | |||
212 | int (*process_symbol)(void *arg, const char *name, | 212 | int (*process_symbol)(void *arg, const char *name, |
213 | char type, u64 start)); | 213 | char type, u64 start)); |
214 | 214 | ||
215 | void machine__destroy_kernel_maps(struct machine *self); | ||
215 | int __machine__create_kernel_maps(struct machine *self, struct dso *kernel); | 216 | int __machine__create_kernel_maps(struct machine *self, struct dso *kernel); |
216 | int machine__create_kernel_maps(struct machine *self); | 217 | int machine__create_kernel_maps(struct machine *self); |
217 | 218 | ||
218 | int machines__create_kernel_maps(struct rb_root *self, pid_t pid); | 219 | int machines__create_kernel_maps(struct rb_root *self, pid_t pid); |
219 | int machines__create_guest_kernel_maps(struct rb_root *self); | 220 | int machines__create_guest_kernel_maps(struct rb_root *self); |
221 | void machines__destroy_guest_kernel_maps(struct rb_root *self); | ||
220 | 222 | ||
221 | int symbol__init(void); | 223 | int symbol__init(void); |
222 | void symbol__exit(void); | 224 | void symbol__exit(void); |