Add binary location information
authorAntoine Busque <abusque@efficios.com>
Mon, 18 Apr 2016 22:31:53 +0000 (18:31 -0400)
committerJérémie Galarneau <jeremie.galarneau@efficios.com>
Thu, 21 Apr 2016 18:12:49 +0000 (14:12 -0400)
Signed-off-by: Antoine Busque <abusque@efficios.com>
Signed-off-by: Jérémie Galarneau <jeremie.galarneau@efficios.com>
include/babeltrace/debuginfo.h
include/babeltrace/so-info.h
include/babeltrace/trace-debuginfo.h
lib/debuginfo.c
lib/so-info.c

index 5e9d79cacc8e744d10659301750ca069f4d72a09..d85c36c48e7e0fc1ec807d9d2da94f43dfacb2f4 100644 (file)
@@ -48,6 +48,11 @@ struct debug_info_source {
        char *bin_path;
        /* short_bin_path points inside bin_path, no need to free. */
        const char *short_bin_path;
+       /*
+        * Location within the binary. Either absolute (@0x1234) or
+        * relative (+0x4321).
+        */
+       char *bin_loc;
 };
 
 BT_HIDDEN
index 7badeb2fa43940e4b4cd5e37670866831db06f2d..17d0f59cfd278e6ed61e3bf87a860190e04fe2d2 100644 (file)
@@ -192,6 +192,25 @@ int so_info_lookup_function_name(struct so_info *so, uint64_t addr,
 BT_HIDDEN
 int so_info_lookup_source_location(struct so_info *so, uint64_t addr,
                struct source_location **src_loc);
+/**
+ * Get a string representing the location within the binary of a given
+ * address.
+ *
+ * In the  case of a PIC binary, the location is relative (+0x1234).
+ * For a non-PIC binary, the location is absolute (@0x1234)
+ *
+ * On success, the out parameter `bin_loc` is set. The ownership is
+ * passed to the caller. On failure, `bin_loc` remains unchanged.
+ *
+ * @param so           so_info instance for the executable containing
+ *                     the address
+ * @param addr         Virtual memory address for which to find the
+ *                     binary location
+ * @param bin_loc      Out parameter, the binary location
+ * @returns            0 on success, -1 on failure
+ */
+BT_HIDDEN
+int so_info_get_bin_loc(struct so_info *so, uint64_t addr, char **bin_loc);
 
 /**
  * Destroy the given source_location instance
index cf4069a228496245575bbabb6936d0ffdac5c41e..2733e99a3fc11e52739adce02b8d23b63a8878b2 100644 (file)
@@ -76,10 +76,11 @@ void ctf_text_integer_write_debug_info(struct bt_stream_pos *ppos,
                                        fprintf(pos->fp, ", ");
                                }
 
-                               fprintf(pos->fp, "bin = \"%s\"",
+                               fprintf(pos->fp, "bin = \"%s%s\"",
                                                opt_debug_info_full_path ?
                                                debug_info_src->bin_path :
-                                               debug_info_src->short_bin_path);
+                                               debug_info_src->short_bin_path,
+                                               debug_info_src->bin_loc);
                        }
 
                        fprintf(pos->fp, " }");
index fae645d64d798d93434c377a48b40c0383d3a6d1..ab92898505e763f77653802adc44fdbfa0ba20a8 100644 (file)
@@ -87,6 +87,7 @@ void debug_info_source_destroy(struct debug_info_source *debug_info_src)
        free(debug_info_src->func);
        free(debug_info_src->src_path);
        free(debug_info_src->bin_path);
+       free(debug_info_src->bin_loc);
        g_free(debug_info_src);
 }
 
@@ -143,6 +144,11 @@ struct debug_info_source *debug_info_source_create_from_so(struct so_info *so,
 
                debug_info_src->short_bin_path = get_filename_from_path(
                                debug_info_src->bin_path);
+
+               ret = so_info_get_bin_loc(so, ip, &(debug_info_src->bin_loc));
+               if (ret) {
+                       goto error;
+               }
        }
 
 end:
index 3a603b8f1561f0b2c52cb8e2b5765a559b9501b3..88106f39daccb8d3285e3698a9d82ccc69a8faf1 100644 (file)
@@ -849,12 +849,11 @@ error:
 }
 
 BT_HIDDEN
-int so_info_lookup_function_name(struct so_info *so, uint64_t ip,
+int so_info_lookup_function_name(struct so_info *so, uint64_t addr,
                char **func_name)
 {
        int ret = 0;
        char *_func_name = NULL;
-       uint64_t relative_addr;
 
        if (!so || !func_name) {
                goto error;
@@ -869,46 +868,57 @@ int so_info_lookup_function_name(struct so_info *so, uint64_t ip,
                }
        }
 
-       if (!so_info_has_address(so, ip)) {
+       if (!so_info_has_address(so, addr)) {
                goto error;
        }
 
-       relative_addr = ip - so->low_addr;
        /*
         * Addresses in ELF and DWARF are relative to base address for
         * PIC, so make the address argument relative too if needed.
         */
+       if (so->is_pic) {
+               addr -= so->low_addr;
+       }
+
        if (so->is_elf_only) {
-               ret = so_info_lookup_elf_function_name(so,
-                               so->is_pic ? relative_addr : ip,
-                               &_func_name);
+               ret = so_info_lookup_elf_function_name(so, addr, &_func_name);
        } else {
-               ret = so_info_lookup_dwarf_function_name(so,
-                               so->is_pic ? relative_addr : ip,
-                               &_func_name);
+               ret = so_info_lookup_dwarf_function_name(so, addr, &_func_name);
        }
 
-       if (ret) {
+       if (ret || !_func_name) {
                goto error;
        }
 
-       if (!_func_name) {
-               /*
-                * Can't map to a function; fallback to a generic output of the
-                * form binary+/@address.
-                *
-                * FIXME check position independence flag.
-                */
-               const char *binary_name = get_filename_from_path(so->elf_path);
+       *func_name = _func_name;
+       return 0;
 
-               ret = asprintf(&_func_name, "%s+%#0" PRIx64, binary_name,
-                               relative_addr);
-               if (!_func_name) {
-                       goto error;
-               }
+error:
+       return -1;
+}
+
+BT_HIDDEN
+int so_info_get_bin_loc(struct so_info *so, uint64_t addr, char **bin_loc)
+{
+       int ret = 0;
+       char *_bin_loc = NULL;
+
+       if (!so || !bin_loc) {
+               goto error;
        }
 
-       *func_name = _func_name;
+       if (so->is_pic) {
+               addr -= so->low_addr;
+               ret = asprintf(&_bin_loc, "+%#0" PRIx64, addr);
+       } else {
+               ret = asprintf(&_bin_loc, "@%#0" PRIx64, addr);
+       }
+
+       if (ret == -1 || !_bin_loc) {
+               goto error;
+       }
+
+       *bin_loc = _bin_loc;
        return 0;
 
 error:
This page took 0.028025 seconds and 4 git commands to generate.