@@ -31,6 +31,7 @@ TRACE_CMD_OBJS += trace-show.o
TRACE_CMD_OBJS += trace-list.o
TRACE_CMD_OBJS += trace-usage.o
TRACE_CMD_OBJS += trace-dump.o
+TRACE_CMD_OBJS += trace-obj-debug.o
ifeq ($(VSOCK_DEFINED), 1)
TRACE_CMD_OBJS += trace-tsync.o
endif
@@ -178,14 +178,6 @@ struct func_list {
const char *mod;
};
-struct pid_addr_maps {
- struct pid_addr_maps *next;
- struct tracecmd_proc_addr_map *lib_maps;
- unsigned int nr_lib_maps;
- char *proc_name;
- int pid;
-};
-
struct opt_list {
struct opt_list *next;
const char *option;
@@ -314,4 +306,15 @@ void *malloc_or_die(unsigned int size); /* Can be overridden */
void __noreturn __die(const char *fmt, ...);
void __noreturn _vdie(const char *fmt, va_list ap);
+/* --- Debug symbols--- */
+struct pid_addr_maps {
+ struct pid_addr_maps *next;
+ struct tracecmd_proc_addr_map *lib_maps;
+ unsigned int nr_lib_maps;
+ char *proc_name;
+ int pid;
+};
+int trace_debug_get_filemap(struct pid_addr_maps **file_maps, int pid);
+void trace_debug_free_filemap(struct pid_addr_maps *maps);
+
#endif /* __TRACE_LOCAL_H */
new file mode 100644
@@ -0,0 +1,138 @@
+// SPDX-License-Identifier: LGPL-2.1
+/*
+ * Copyright (C) 2020, VMware, Tzvetomir Stoyanov <tz.stoyanov@gmail.com>
+ *
+ */
+#include <stdlib.h>
+#include <errno.h>
+#include <unistd.h>
+
+#include "trace-local.h"
+
+#define _STRINGIFY(x) #x
+#define STRINGIFY(x) _STRINGIFY(x)
+int trace_debug_get_filemap(struct pid_addr_maps **pid_maps, int pid)
+{
+ struct pid_addr_maps *maps = *pid_maps;
+ struct tracecmd_proc_addr_map *map;
+ unsigned long long begin, end;
+ struct pid_addr_maps *m;
+ char mapname[PATH_MAX+1];
+ char fname[PATH_MAX+1];
+ char buf[PATH_MAX+100];
+ FILE *f;
+ int ret;
+ int res;
+ int i;
+
+ sprintf(fname, "/proc/%d/exe", pid);
+ ret = readlink(fname, mapname, PATH_MAX);
+ if (ret >= PATH_MAX || ret < 0)
+ return -ENOENT;
+ mapname[ret] = 0;
+
+ sprintf(fname, "/proc/%d/maps", pid);
+ f = fopen(fname, "r");
+ if (!f)
+ return -ENOENT;
+
+ while (maps) {
+ if (pid == maps->pid)
+ break;
+ maps = maps->next;
+ }
+
+ ret = -ENOMEM;
+ if (!maps) {
+ maps = calloc(1, sizeof(*maps));
+ if (!maps)
+ goto out_fail;
+ maps->pid = pid;
+ maps->next = *pid_maps;
+ *pid_maps = maps;
+ } else {
+ for (i = 0; i < maps->nr_lib_maps; i++)
+ free(maps->lib_maps[i].lib_name);
+ free(maps->lib_maps);
+ maps->lib_maps = NULL;
+ maps->nr_lib_maps = 0;
+ free(maps->proc_name);
+ }
+
+ maps->proc_name = strdup(mapname);
+ if (!maps->proc_name)
+ goto out;
+
+ while (fgets(buf, sizeof(buf), f)) {
+ mapname[0] = '\0';
+ res = sscanf(buf, "%llx-%llx %*s %*x %*s %*d %"STRINGIFY(PATH_MAX)"s",
+ &begin, &end, mapname);
+ if (res == 3 && mapname[0] != '\0') {
+ map = realloc(maps->lib_maps,
+ (maps->nr_lib_maps + 1) * sizeof(*map));
+ if (!map)
+ goto out_fail;
+ map[maps->nr_lib_maps].end = end;
+ map[maps->nr_lib_maps].start = begin;
+ map[maps->nr_lib_maps].lib_name = strdup(mapname);
+ if (!map[maps->nr_lib_maps].lib_name)
+ goto out_fail;
+ maps->lib_maps = map;
+ maps->nr_lib_maps++;
+ }
+ }
+out:
+ fclose(f);
+ return 0;
+
+out_fail:
+ fclose(f);
+ if (maps) {
+ for (i = 0; i < maps->nr_lib_maps; i++)
+ free(maps->lib_maps[i].lib_name);
+ if (*pid_maps != maps) {
+ m = *pid_maps;
+ while (m) {
+ if (m->next == maps) {
+ m->next = maps->next;
+ break;
+ }
+ m = m->next;
+ }
+ } else
+ *pid_maps = maps->next;
+ free(maps->lib_maps);
+ maps->lib_maps = NULL;
+ maps->nr_lib_maps = 0;
+ free(maps->proc_name);
+ maps->proc_name = NULL;
+ free(maps);
+ }
+ return ret;
+}
+
+static void procmap_free(struct pid_addr_maps *maps)
+{
+ int i;
+
+ if (!maps)
+ return;
+ if (maps->lib_maps) {
+ for (i = 0; i < maps->nr_lib_maps; i++)
+ free(maps->lib_maps[i].lib_name);
+ free(maps->lib_maps);
+ }
+ free(maps->proc_name);
+ free(maps);
+}
+
+void trace_debug_free_filemap(struct pid_addr_maps *maps)
+{
+ struct pid_addr_maps *del;
+
+ while (maps) {
+ del = maps;
+ maps = maps->next;
+ procmap_free(del);
+ }
+}
@@ -1080,109 +1080,6 @@ static char *make_pid_filter(struct buffer_instance *instance,
return filter;
}
-#define _STRINGIFY(x) #x
-#define STRINGIFY(x) _STRINGIFY(x)
-
-static int get_pid_addr_maps(struct buffer_instance *instance, int pid)
-{
- struct pid_addr_maps *maps = instance->pid_maps;
- struct tracecmd_proc_addr_map *map;
- unsigned long long begin, end;
- struct pid_addr_maps *m;
- char mapname[PATH_MAX+1];
- char fname[PATH_MAX+1];
- char buf[PATH_MAX+100];
- FILE *f;
- int ret;
- int res;
- int i;
-
- sprintf(fname, "/proc/%d/exe", pid);
- ret = readlink(fname, mapname, PATH_MAX);
- if (ret >= PATH_MAX || ret < 0)
- return -ENOENT;
- mapname[ret] = 0;
-
- sprintf(fname, "/proc/%d/maps", pid);
- f = fopen(fname, "r");
- if (!f)
- return -ENOENT;
-
- while (maps) {
- if (pid == maps->pid)
- break;
- maps = maps->next;
- }
-
- ret = -ENOMEM;
- if (!maps) {
- maps = calloc(1, sizeof(*maps));
- if (!maps)
- goto out_fail;
- maps->pid = pid;
- maps->next = instance->pid_maps;
- instance->pid_maps = maps;
- } else {
- for (i = 0; i < maps->nr_lib_maps; i++)
- free(maps->lib_maps[i].lib_name);
- free(maps->lib_maps);
- maps->lib_maps = NULL;
- maps->nr_lib_maps = 0;
- free(maps->proc_name);
- }
-
- maps->proc_name = strdup(mapname);
- if (!maps->proc_name)
- goto out;
-
- while (fgets(buf, sizeof(buf), f)) {
- mapname[0] = '\0';
- res = sscanf(buf, "%llx-%llx %*s %*x %*s %*d %"STRINGIFY(PATH_MAX)"s",
- &begin, &end, mapname);
- if (res == 3 && mapname[0] != '\0') {
- map = realloc(maps->lib_maps,
- (maps->nr_lib_maps + 1) * sizeof(*map));
- if (!map)
- goto out_fail;
- map[maps->nr_lib_maps].end = end;
- map[maps->nr_lib_maps].start = begin;
- map[maps->nr_lib_maps].lib_name = strdup(mapname);
- if (!map[maps->nr_lib_maps].lib_name)
- goto out_fail;
- maps->lib_maps = map;
- maps->nr_lib_maps++;
- }
- }
-out:
- fclose(f);
- return 0;
-
-out_fail:
- fclose(f);
- if (maps) {
- for (i = 0; i < maps->nr_lib_maps; i++)
- free(maps->lib_maps[i].lib_name);
- if (instance->pid_maps != maps) {
- m = instance->pid_maps;
- while (m) {
- if (m->next == maps) {
- m->next = maps->next;
- break;
- }
- m = m->next;
- }
- } else
- instance->pid_maps = maps->next;
- free(maps->lib_maps);
- maps->lib_maps = NULL;
- maps->nr_lib_maps = 0;
- free(maps->proc_name);
- maps->proc_name = NULL;
- free(maps);
- }
- return ret;
-}
-
static void get_filter_pid_maps(void)
{
struct buffer_instance *instance;
@@ -1194,7 +1091,7 @@ static void get_filter_pid_maps(void)
for (p = instance->filter_pids; p; p = p->next) {
if (p->exclude)
continue;
- get_pid_addr_maps(instance, p->pid);
+ trace_debug_get_filemap(&instance->pid_maps, p->pid);
}
}
}
@@ -1524,7 +1421,7 @@ static void ptrace_wait(enum trace_type type)
case PTRACE_EVENT_EXIT:
instance = get_intance_fpid(pid);
if (instance && instance->get_procmap)
- get_pid_addr_maps(instance, pid);
+ trace_debug_get_filemap(&instance->pid_maps, pid);
ptrace(PTRACE_GETEVENTMSG, pid, NULL, &cstatus);
ptrace(PTRACE_DETACH, pid, NULL, NULL);
break;
Make functions for collecting file to memory map of a PID non static, so they can be reused in the trace-cmd application context. Created new file trace-obj-debug.c with these functions. Signed-off-by: Tzvetomir Stoyanov (VMware) <tz.stoyanov@gmail.com> --- tracecmd/Makefile | 1 + tracecmd/include/trace-local.h | 19 +++-- tracecmd/trace-obj-debug.c | 138 +++++++++++++++++++++++++++++++++ tracecmd/trace-record.c | 107 +------------------------ 4 files changed, 152 insertions(+), 113 deletions(-) create mode 100644 tracecmd/trace-obj-debug.c