perf unwind: Fix map reference counts
authorIan Rogers <irogers@google.com>
Fri, 23 Jun 2023 04:31:07 +0000 (21:31 -0700)
committerNamhyung Kim <namhyung@kernel.org>
Fri, 23 Jun 2023 05:13:13 +0000 (22:13 -0700)
The result of thread__find_map is the map in the passed in
addr_location. Calling addr_location__exit puts that map and so copies
need to do a map__get. Add in the corresponding map__puts.

v2. Add missing map__put when dso is missing.

Signed-off-by: Ian Rogers <irogers@google.com>
Acked-by: Namhyung Kim <namhyung@kernel.org>
Cc: Mark Rutland <mark.rutland@arm.com>
Cc: Ivan Babrou <ivan@cloudflare.com>
Cc: Peter Zijlstra <peterz@infradead.org>
Cc: Adrian Hunter <adrian.hunter@intel.com>
Cc: Arnaldo Carvalho de Melo <acme@kernel.org>
Cc: Jiri Olsa <jolsa@kernel.org>
Cc: Alexander Shishkin <alexander.shishkin@linux.intel.com>
Cc: Ingo Molnar <mingo@redhat.com>
Link: https://lore.kernel.org/r/20230623043107.4077510-1-irogers@google.com
Signed-off-by: Namhyung Kim <namhyung@kernel.org>
tools/perf/util/unwind-libunwind-local.c

index 36bf5100bad21c301927cda833ee5282a7fa0f56..ebfde537b99b9410fa0ef92dab62052519a7182b 100644 (file)
@@ -419,7 +419,8 @@ static struct map *find_map(unw_word_t ip, struct unwind_info *ui)
        struct map *ret;
 
        addr_location__init(&al);
-       ret = thread__find_map(ui->thread, PERF_RECORD_MISC_USER, ip, &al);
+       thread__find_map(ui->thread, PERF_RECORD_MISC_USER, ip, &al);
+       ret = map__get(al.map);
        addr_location__exit(&al);
        return ret;
 }
@@ -440,8 +441,10 @@ find_proc_info(unw_addr_space_t as, unw_word_t ip, unw_proc_info_t *pi,
                return -EINVAL;
 
        dso = map__dso(map);
-       if (!dso)
+       if (!dso) {
+               map__put(map);
                return -EINVAL;
+       }
 
        pr_debug("unwind: find_proc_info dso %s\n", dso->name);
 
@@ -476,11 +479,11 @@ find_proc_info(unw_addr_space_t as, unw_word_t ip, unw_proc_info_t *pi,
 
                memset(&di, 0, sizeof(di));
                if (dwarf_find_debug_frame(0, &di, ip, base, symfile, start, map__end(map)))
-                       return dwarf_search_unwind_table(as, ip, &di, pi,
-                                                        need_unwind_info, arg);
+                       ret = dwarf_search_unwind_table(as, ip, &di, pi,
+                                                       need_unwind_info, arg);
        }
 #endif
-
+       map__put(map);
        return ret;
 }
 
@@ -534,12 +537,14 @@ static int access_dso_mem(struct unwind_info *ui, unw_word_t addr,
 
        dso = map__dso(map);
 
-       if (!dso)
+       if (!dso) {
+               map__put(map);
                return -1;
+       }
 
        size = dso__data_read_addr(dso, map, ui->machine,
                                   addr, (u8 *) data, sizeof(*data));
-
+       map__put(map);
        return !(size == sizeof(*data));
 }