+Tue Apr 5 20:13:44 2005 Søren Sandmann <sandmann@redhat.com>
+
+ * process.c (process_ensure_map): Add commented out debug spew.
+
+ * process.c (process_lookup_symbol): Remove all should_offset()
+ function and all references to it.
+
+ * binfile.c (bin_file_lookup_symbol): Document that address must
+ be in file coordinates.
+
+ * binfile.c (read_symbols): Remove misguided code that tried to
+ guess the load address of the file. Instead, do all computations
+ in "file coordinates". Also fix a memory leak. Add commented out
+ debug spew.
+
+ * binfile.c (separate_debug_file_exists): Fix signedness
+
Tue Apr 5 14:34:43 2005 Søren Sandmann <sandmann@redhat.com>
* sysprof-module.c (x_access_process_vm): Make it compile with
{
unsigned long file_crc = 0;
int fd;
- char buffer[8*1024];
+ guchar buffer[8*1024];
int count;
fd = open (name, O_RDONLY);
int i;
bfd *bfd;
GArray *symbols;
- asection *sec;
- ulong load_address;
bf->symbols = NULL;
bf->n_symbols = 0;
{
bfd_close (bfd);
bfd = open_bfd (separate_debug_file);
+#if 0
+ g_print ("bfd for %s is %s\n", bf->filename, separate_debug_file);
+#endif
if (!bfd)
return;
}
if (!bfd_symbols)
return;
- load_address = 0xffffffff;
- for (sec = bfd->sections; sec != NULL; sec = sec->next)
- {
- if (sec->flags & SEC_LOAD)
- {
- if ((gulong)sec->vma < load_address)
- load_address = sec->vma & ~4095;
- }
- }
-
text_section = bfd_get_section_by_name (bfd, ".text");
if (!text_section)
return;
(bfd_symbols[i]->section == text_section))
{
char *name;
-
- symbol.address = bfd_asymbol_value (bfd_symbols[i]) - load_address;
+
+ /* Store the address in file coordinates:
+ * - all addresses are already offset by section->vma
+ * - the section is positioned at section->filepos
+ */
+ symbol.address = bfd_asymbol_value (bfd_symbols[i]) - text_section->vma + text_section->filepos;
name = demangle (bfd, bfd_asymbol_name (bfd_symbols[i]));
+
#if 0
symbol.name = g_strdup_printf ("%s (%s)", name, bf->filename);
#endif
symbol.name = g_strdup (name);
- free (name);
+#if 0
+ g_print ("symbol: %s (%s) %p\n", name, bf->filename, symbol.address);
+#endif
+ free (name);
+
g_array_append_vals (symbols, &symbol, 1);
}
}
if (n_symbols)
free (bfd_symbols);
+
+#if 0
+ if (!n_symbols)
+ g_print ("no symbols found for %s\n", bf->filename);
+ else
+ g_print ("symbols found for %s\n", bf->filename);
+#endif
/* Sort the symbols by address */
qsort (symbols->data, symbols->len, sizeof(Symbol), compare_address);
g_free (bf);
}
+/**
+ * bin_file_lookup_symbol:
+ * @bf: A BinFile
+ * @address: The address to lookup
+ *
+ * Look up a symbol. @address should be in file coordinates
+ *
+ **/
const Symbol *
bin_file_lookup_symbol (BinFile *bf,
gulong address)
*/
if (strcmp (result->name, "call_gmon_start") == 0)
return &(bf->undefined);
-#if 0
else if (strncmp (result->name, "__do_global_ctors_aux", strlen ("__do_global_ctors_aux")) == 0)
{
+#if 0
g_print ("ctors: %p, pos: %p\n", address, result->address);
- }
#endif
+ }
return result;
}
gulong start;
gulong end;
gulong offset;
+#if 0
gboolean do_offset;
+#endif
BinFile * bin_file;
};
}
}
-static gboolean
-should_offset (const char *filename, int pid)
-{
- return FALSE;
-
- gboolean result = TRUE;
-
- struct stat stat1, stat2;
- char *progname = g_strdup_printf ("/proc/%d/exe", pid);
-
- if (stat (filename, &stat1) == 0)
- {
- if (stat (progname, &stat2) == 0)
- result = !(stat1.st_ino == stat2.st_ino &&
- stat1.st_dev == stat2.st_dev);
- }
-
- g_free (progname);
-
- return result;
-}
-
static GList *
read_maps (int pid)
{
result = g_list_prepend (result, map);
}
+#if 0
+ else
+ {
+ g_print ("scanf\n");
+ }
+#endif
}
g_free (name);
process_ensure_map (Process *process, int pid, gulong addr)
{
/* Round down to closest page */
+
addr = (addr - addr % PAGE_SIZE);
if (process_has_page (process, addr))
if (g_list_find (process->bad_pages, (gpointer)addr))
return;
-
+
/* a map containing addr was not found */
if (process->maps)
process_free_maps (process);
process->maps = read_maps (pid);
if (!process_has_page (process, addr))
+ {
+#if 0
+ g_print ("Bad page: %p\n", addr);
+#endif
process->bad_pages = g_list_prepend (process->bad_pages, (gpointer)addr);
+ }
}
static gboolean
{
g_free (cmdline);
return NULL;
- }
+ }
return cmdline;
}
undefined.name = g_strdup_printf ("??? %s", process->cmdline);
undefined.address = 0xBABE0001;
+#if 0
+ g_print ("no map for %p (%s)\n", address, process->cmdline);
+#endif
+
return &undefined;
}
+
+#if 0
+ g_print ("has map: %s\n", process->cmdline);
+#endif
/* if (map->do_offset) */
/* address -= map->start; */
+ /* convert address to file coordinates */
address -= map->start;
address += map->offset;
if (!map->bin_file)
map->bin_file = bin_file_new (map->filename);
-#if 0
- /* FIXME - this seems to work with prelinked binaries, but is
- * it correct? IE., will normal binaries always have a preferred_addres of 0?
- */
- address = address - map->start + map->offset + bin_file_get_load_address (map->bin_file);
- address -= map->start;
- address += map->offset;
- address += bin_file_get_load_address (map->bin_file);
-#endif
-
/* g_print ("%s: start: %p, load: %p\n", */
/* map->filename, map->start, bin_file_get_load_address (map->bin_file)); */
-
- if (should_offset (map->filename, process->pid))
- address -= map->start;
- result = bin_file_lookup_symbol (map->bin_file, address);
+ result = bin_file_lookup_symbol (map->bin_file, address);
/* g_print ("(%x) %x %x name; %s\n", address, map->start, map->offset, result->name); */
if (rd == -1 && errno == EWOULDBLOCK)
return;
-
+
#if 0
+ int i;
g_print ("pid: %d\n", trace.pid);
for (i=0; i < trace.n_addresses; ++i)
g_print ("rd: %08x\n", trace.addresses[i]);