65bc5f9
https://bugzilla.redhat.com/bugzilla/show_bug.cgi?id=109921
65bc5f9
65bc5f9
65bc5f9
2007-01-09  Jan Kratochvil  <jan.kratochvil@redhat.com>
65bc5f9
65bc5f9
	* buildsym.c (start_subfile_index): Renamed `start_subfile' now
65bc5f9
	supporting the FILE_INDEX parameter.
65bc5f9
	(start_subfile): Backward compatible stub for `start_subfile_index'.
65bc5f9
	(end_symtab): Resolve new SYMBOL.FILE.SYMTAB from SYMBOL.FILE.INDEX.
65bc5f9
	Substitute possibly missing DIRNAME from the CU's main file DIRNAME.
65bc5f9
	Clear `subfiles' variable as its data have been deallocated.
65bc5f9
	* buildsym.h (struct subfile): New field `file_index'.
65bc5f9
	(start_subfile_index): New prototype.
65bc5f9
	* dwarf2read.c (add_file_name): Ensure subfile has been founded.
65bc5f9
	(dwarf_decode_lines): Specify the new FILE_INDEX parameter.
65bc5f9
	(dwarf2_start_subfile): New FILE_INDEX parameter.
65bc5f9
	(new_symbol): Extract `DW_AT_decl_file' DWARF 2 information entry.
65bc5f9
	* symtab.c (lookup_symbol): Override by the new SYMBOL.FILE.SYMTAB.
65bc5f9
	(search_symbols): Likewise.
65bc5f9
	* symtab.h (struct symbol): New fields FILE.INDEX and FILE.SYMTAB.
65bc5f9
	(SYMBOL_FILE_INDEX, SYMBOL_FILE_SYMTAB): New macros.
65bc5f9
65bc5f9
65bc5f9
--- ./gdb/buildsym.c	2005-12-17 22:33:59.000000000 +0000
65bc5f9
+++ ./gdb/buildsym.c	2007-01-09 08:30:38.000000000 +0000
65bc5f9
@@ -535,7 +535,7 @@ make_blockvector (struct objfile *objfil
65bc5f9
    the directory in which it resides (or NULL if not known).  */
65bc5f9
 
65bc5f9
 void
65bc5f9
-start_subfile (char *name, char *dirname)
65bc5f9
+start_subfile_index (char *name, char *dirname, unsigned file_index)
65bc5f9
 {
65bc5f9
   struct subfile *subfile;
65bc5f9
 
65bc5f9
@@ -547,6 +547,17 @@ start_subfile (char *name, char *dirname
65bc5f9
       if (FILENAME_CMP (subfile->name, name) == 0)
65bc5f9
 	{
65bc5f9
 	  current_subfile = subfile;
65bc5f9
+
65bc5f9
+	  if (subfile->file_index != 0 && file_index != 0
65bc5f9
+	      && subfile->file_index != file_index)
65bc5f9
+	    complaint (&symfile_complaints, _("Filenames indexing conflict: "
65bc5f9
+	               "name \"%s\" dir \"%s\" index %u vs. "
65bc5f9
+		       "name \"%s\" dir \"%s\" index %u"),
65bc5f9
+		       subfile->name, subfile->dirname, subfile->file_index,
65bc5f9
+		       name, dirname, file_index);
65bc5f9
+	  if (subfile->file_index == 0)
65bc5f9
+	    subfile->file_index = file_index;
65bc5f9
+
65bc5f9
 	  return;
65bc5f9
 	}
65bc5f9
     }
65bc5f9
@@ -562,6 +573,7 @@ start_subfile (char *name, char *dirname
65bc5f9
   current_subfile = subfile;
65bc5f9
 
65bc5f9
   /* Save its name and compilation directory name */
65bc5f9
+  subfile->file_index = file_index;
65bc5f9
   subfile->name = (name == NULL) ? NULL : savestring (name, strlen (name));
65bc5f9
   subfile->dirname =
65bc5f9
     (dirname == NULL) ? NULL : savestring (dirname, strlen (dirname));
65bc5f9
@@ -617,6 +629,13 @@ start_subfile (char *name, char *dirname
65bc5f9
     }
65bc5f9
 }
65bc5f9
 
65bc5f9
+/* Backward compatibility.  */
65bc5f9
+void
65bc5f9
+start_subfile (char *name, char *dirname)
65bc5f9
+{
65bc5f9
+  start_subfile_index (name, dirname, 0);
65bc5f9
+}
65bc5f9
+
65bc5f9
 /* For stabs readers, the first N_SO symbol is assumed to be the
65bc5f9
    source file name, and the subfile struct is initialized using that
65bc5f9
    assumption.  If another N_SO symbol is later seen, immediately
65bc5f9
@@ -816,9 +835,12 @@ end_symtab (CORE_ADDR end_addr, struct o
65bc5f9
 {
65bc5f9
   struct symtab *symtab = NULL;
65bc5f9
   struct blockvector *blockvector;
65bc5f9
-  struct subfile *subfile;
65bc5f9
+  struct subfile *subfile, *subfile_main;
65bc5f9
   struct context_stack *cstk;
65bc5f9
   struct subfile *nextsub;
65bc5f9
+  int subfiles_count;
65bc5f9
+  struct symtab **file_index_to_symtab;
65bc5f9
+  size_t file_index_to_symtab_size;
65bc5f9
 
65bc5f9
   /* Finish the lexical context of the last function in the file; pop
65bc5f9
      the context stack.  */
65bc5f9
@@ -916,6 +938,18 @@ end_symtab (CORE_ADDR end_addr, struct o
65bc5f9
 #endif
65bc5f9
   PROCESS_LINENUMBER_HOOK ();	/* Needed for xcoff. */
65bc5f9
 
65bc5f9
+  /* Get the last subfile s SUBFILE_MAIN which is the main file of CU.
65bc5f9
+     Count SUBFILES_COUNT.
65bc5f9
+     Start with 1 as we do not iterate past the last item.  */
65bc5f9
+  subfiles_count = 1;
65bc5f9
+  for (subfile_main = subfiles; subfile_main && subfile_main->next;
65bc5f9
+       subfile_main = subfile_main->next)
65bc5f9
+    subfiles_count++;
65bc5f9
+
65bc5f9
+  file_index_to_symtab_size = sizeof (*file_index_to_symtab) * subfiles_count;
65bc5f9
+  file_index_to_symtab = xmalloc (file_index_to_symtab_size);
65bc5f9
+  memset ((char *) file_index_to_symtab, 0, file_index_to_symtab_size);
65bc5f9
+
65bc5f9
   /* Now create the symtab objects proper, one for each subfile.  */
65bc5f9
   /* (The main file is the last one on the chain.)  */
65bc5f9
 
65bc5f9
@@ -976,6 +1010,16 @@ end_symtab (CORE_ADDR end_addr, struct o
65bc5f9
 			       strlen (subfile->dirname) + 1);
65bc5f9
 	      strcpy (symtab->dirname, subfile->dirname);
65bc5f9
 	    }
65bc5f9
+	  /* Non-primary subfiles may miss COMP_DIR resulting in NULL
65bc5f9
+	     DIRNAME and so default it from the CU file - SUBFILE_MAIN.  */
65bc5f9
+	  else if (subfile_main->dirname)
65bc5f9
+	    {
65bc5f9
+	      /* Reallocate the dirname on the symbol obstack */
65bc5f9
+	      symtab->dirname = (char *)
65bc5f9
+		obstack_alloc (&objfile->objfile_obstack,
65bc5f9
+			       strlen (subfile_main->dirname) + 1);
65bc5f9
+	      strcpy (symtab->dirname, subfile_main->dirname);
65bc5f9
+	    }
65bc5f9
 	  else
65bc5f9
 	    {
65bc5f9
 	      symtab->dirname = NULL;
65bc5f9
@@ -1004,6 +1048,13 @@ end_symtab (CORE_ADDR end_addr, struct o
65bc5f9
 	     but the main file.  */
65bc5f9
 
65bc5f9
 	  symtab->primary = 0;
65bc5f9
+
65bc5f9
+	  /* It may be zero for files unlisted in File Table.  */
65bc5f9
+	  if (subfile->file_index)
65bc5f9
+	    {
65bc5f9
+	      gdb_assert (subfile->file_index <= subfiles_count);
65bc5f9
+	      file_index_to_symtab[subfile->file_index - 1] = symtab;
65bc5f9
+	    }
65bc5f9
 	}
65bc5f9
       if (subfile->name != NULL)
65bc5f9
 	{
65bc5f9
@@ -1032,9 +1083,40 @@ end_symtab (CORE_ADDR end_addr, struct o
65bc5f9
       symtab->primary = 1;
65bc5f9
     }
65bc5f9
 
65bc5f9
+  /* Resolve `struct symbol.file.index' into `struct symbol.file.symtab'.  */
65bc5f9
+  if (blockvector)
65bc5f9
+    {
65bc5f9
+      int block_i;
65bc5f9
+
65bc5f9
+      for (block_i = 0; block_i < BLOCKVECTOR_NBLOCKS (blockvector); block_i++)
65bc5f9
+	{
65bc5f9
+	  struct symbol *sym;
65bc5f9
+	  struct dict_iterator iter;
65bc5f9
+
65bc5f9
+	  for (sym = dict_iterator_first (BLOCK_DICT
65bc5f9
+		       (BLOCKVECTOR_BLOCK (blockvector, block_i)), &iter);
65bc5f9
+	       sym != NULL;
65bc5f9
+	       sym = dict_iterator_next (&iter))
65bc5f9
+	    {
65bc5f9
+	      /* Beware the ordering as `sym->file' is a union.  */
65bc5f9
+	      if (SYMBOL_FILE_INDEX (sym)
65bc5f9
+		  && file_index_to_symtab[SYMBOL_FILE_INDEX (sym) - 1])
65bc5f9
+	        SYMBOL_FILE_SYMTAB (sym) = file_index_to_symtab
65bc5f9
+					     [SYMBOL_FILE_INDEX (sym) - 1];
65bc5f9
+	      else
65bc5f9
+	        {
65bc5f9
+		  /* Default to the primary symbol table, never use NULL.  */
65bc5f9
+		  SYMBOL_FILE_SYMTAB (sym) = symtab;
65bc5f9
+		}
65bc5f9
+	    }
65bc5f9
+	}
65bc5f9
+    }
65bc5f9
+
65bc5f9
+  xfree (file_index_to_symtab);
65bc5f9
   last_source_file = NULL;
65bc5f9
   current_subfile = NULL;
65bc5f9
   pending_macros = NULL;
65bc5f9
+  subfiles = NULL;
65bc5f9
 
65bc5f9
   return symtab;
65bc5f9
 }
65bc5f9
--- ./gdb/buildsym.h	2005-12-17 22:33:59.000000000 +0000
65bc5f9
+++ ./gdb/buildsym.h	2007-01-09 08:17:17.000000000 +0000
65bc5f9
@@ -63,6 +63,7 @@ EXTERN CORE_ADDR last_source_start_addr;
65bc5f9
 struct subfile
65bc5f9
   {
65bc5f9
     struct subfile *next;
65bc5f9
+    unsigned file_index;
65bc5f9
     char *name;
65bc5f9
     char *dirname;
65bc5f9
     struct linetable *line_vector;
65bc5f9
@@ -240,6 +241,9 @@ extern void finish_block (struct symbol 
65bc5f9
 
65bc5f9
 extern void really_free_pendings (void *dummy);
65bc5f9
 
65bc5f9
+extern void start_subfile_index (char *name, char *dirname,
65bc5f9
+				 unsigned file_index);
65bc5f9
+
65bc5f9
 extern void start_subfile (char *name, char *dirname);
65bc5f9
 
65bc5f9
 extern void patch_subfile_names (struct subfile *subfile, char *name);
65bc5f9
--- ./gdb/dwarf2read.c	2007-01-08 22:28:24.000000000 +0000
65bc5f9
+++ ./gdb/dwarf2read.c	2007-01-09 08:58:41.000000000 +0000
65bc5f9
@@ -847,7 +847,7 @@ static struct line_header *(dwarf_decode
65bc5f9
 static void dwarf_decode_lines (struct line_header *, char *, bfd *,
65bc5f9
 				struct dwarf2_cu *, struct partial_symtab *);
65bc5f9
 
65bc5f9
-static void dwarf2_start_subfile (char *, char *, char *);
65bc5f9
+static void dwarf2_start_subfile (char *, char *, char *, unsigned);
65bc5f9
 
65bc5f9
 static struct symbol *new_symbol (struct die_info *, struct type *,
65bc5f9
 				  struct dwarf2_cu *);
65bc5f9
@@ -6321,6 +6321,7 @@ add_file_name (struct line_header *lh,
65bc5f9
                unsigned int length)
65bc5f9
 {
65bc5f9
   struct file_entry *fe;
65bc5f9
+  char *dir = NULL;
65bc5f9
 
65bc5f9
   /* Grow the array if necessary.  */
65bc5f9
   if (lh->file_names_size == 0)
65bc5f9
@@ -6343,6 +6344,10 @@ add_file_name (struct line_header *lh,
65bc5f9
   fe->mod_time = mod_time;
65bc5f9
   fe->length = length;
65bc5f9
   fe->included_p = 0;
65bc5f9
+
65bc5f9
+  if (dir_index)
65bc5f9
+    dir = lh->include_dirs[dir_index - 1];
65bc5f9
+  dwarf2_start_subfile (name, dir, NULL, lh->num_file_names);
65bc5f9
 }
65bc5f9
  
65bc5f9
 
65bc5f9
@@ -6560,7 +6565,7 @@ dwarf_decode_lines (struct line_header *
65bc5f9
           if (fe->dir_index)
65bc5f9
             dir = lh->include_dirs[fe->dir_index - 1];
65bc5f9
 
65bc5f9
-	  dwarf2_start_subfile (fe->name, dir, comp_dir);
65bc5f9
+	  dwarf2_start_subfile (fe->name, dir, comp_dir, file);
65bc5f9
 	}
65bc5f9
 
65bc5f9
       /* Decode the table.  */
65bc5f9
@@ -6661,7 +6666,7 @@ dwarf_decode_lines (struct line_header *
65bc5f9
                   dir = lh->include_dirs[fe->dir_index - 1];
65bc5f9
 
65bc5f9
                 if (!decode_for_pst_p)
65bc5f9
-                  dwarf2_start_subfile (fe->name, dir, comp_dir);
65bc5f9
+                  dwarf2_start_subfile (fe->name, dir, comp_dir, file);
65bc5f9
               }
65bc5f9
 	      break;
65bc5f9
 	    case DW_LNS_set_column:
65bc5f9
@@ -6764,7 +6769,8 @@ dwarf_decode_lines (struct line_header *
65bc5f9
    subfile's name.  */
65bc5f9
 
65bc5f9
 static void
65bc5f9
-dwarf2_start_subfile (char *filename, char *dirname, char *comp_dir)
65bc5f9
+dwarf2_start_subfile (char *filename, char *dirname, char *comp_dir,
65bc5f9
+		      unsigned file_index)
65bc5f9
 {
65bc5f9
   char *fullname;
65bc5f9
 
65bc5f9
@@ -6783,7 +6789,7 @@ dwarf2_start_subfile (char *filename, ch
65bc5f9
   else
65bc5f9
     fullname = filename;
65bc5f9
 
65bc5f9
-  start_subfile (fullname, comp_dir);
65bc5f9
+  start_subfile_index (fullname, comp_dir, file_index);
65bc5f9
 
65bc5f9
   if (fullname != filename)
65bc5f9
     xfree (fullname);
65bc5f9
@@ -6892,6 +6898,13 @@ new_symbol (struct die_info *die, struct
65bc5f9
 	{
65bc5f9
 	  SYMBOL_LINE (sym) = DW_UNSND (attr);
65bc5f9
 	}
65bc5f9
+      attr = dwarf2_attr (die, DW_AT_decl_file, cu);
65bc5f9
+      if (attr)
65bc5f9
+	{
65bc5f9
+	  /* Do not yet search `objfile->symtabs' here as they still do not
65bc5f9
+	     have filled in their FILE.INDEX fields.  */
65bc5f9
+	  SYMBOL_FILE_INDEX (sym) = DW_UNSND (attr);
65bc5f9
+	}
65bc5f9
       switch (die->tag)
65bc5f9
 	{
65bc5f9
 	case DW_TAG_label:
65bc5f9
--- ./gdb/symtab.c	2007-01-08 22:28:25.000000000 +0000
65bc5f9
+++ ./gdb/symtab.c	2007-01-09 08:19:05.000000000 +0000
65bc5f9
@@ -1129,6 +1129,10 @@ lookup_symbol (const char *name, const s
65bc5f9
   if (needtofreename)
65bc5f9
     xfree (demangled_name);
65bc5f9
 
65bc5f9
+  /* Override the returned symtab with optional symbol's specific one.  */
65bc5f9
+  if (returnval != NULL && symtab != NULL)
65bc5f9
+    *symtab = SYMBOL_FILE_SYMTAB (returnval);
65bc5f9
+
65bc5f9
   return returnval;	 
65bc5f9
 }
65bc5f9
 
65bc5f9
@@ -3235,7 +3239,7 @@ search_symbols (char *regexp, domain_enu
65bc5f9
 	  ALL_BLOCK_SYMBOLS (b, iter, sym)
65bc5f9
 	    {
65bc5f9
 	      QUIT;
65bc5f9
-	      if (file_matches (s->filename, files, nfiles)
65bc5f9
+	      if (file_matches (SYMBOL_FILE_SYMTAB (sym)->filename, files, nfiles)
65bc5f9
 		  && ((regexp == NULL
65bc5f9
 		       || re_exec (SYMBOL_NATURAL_NAME (sym)) != 0)
65bc5f9
 		      && ((kind == VARIABLES_DOMAIN && SYMBOL_CLASS (sym) != LOC_TYPEDEF
65bc5f9
@@ -3248,7 +3252,7 @@ search_symbols (char *regexp, domain_enu
65bc5f9
 		  /* match */
65bc5f9
 		  psr = (struct symbol_search *) xmalloc (sizeof (struct symbol_search));
65bc5f9
 		  psr->block = i;
65bc5f9
-		  psr->symtab = s;
65bc5f9
+		  psr->symtab = SYMBOL_FILE_SYMTAB (sym);
65bc5f9
 		  psr->symbol = sym;
65bc5f9
 		  psr->msymbol = NULL;
65bc5f9
 		  psr->next = NULL;
65bc5f9
--- ./gdb/symtab.h	2007-01-08 22:28:25.000000000 +0000
65bc5f9
+++ ./gdb/symtab.h	2007-01-09 08:44:02.000000000 +0000
65bc5f9
@@ -623,6 +623,18 @@ struct symbol
65bc5f9
 
65bc5f9
   ENUM_BITFIELD(address_class) aclass : 6;
65bc5f9
 
65bc5f9
+  /* File name it comes from.  Use with `line' below.
65bc5f9
+     FILE.INDEX is zero if the symbol's specific file is not known and in such
65bc5f9
+     case we later default to the main file of the compilation unit.
65bc5f9
+     FILE.SYMTAB gets resolved during end_symtab() and it is never NULL.  */
65bc5f9
+
65bc5f9
+  union
65bc5f9
+  {
65bc5f9
+    unsigned index;
65bc5f9
+    struct symtab *symtab;
65bc5f9
+  }
65bc5f9
+  file;
65bc5f9
+
65bc5f9
   /* Line number of definition.  FIXME:  Should we really make the assumption
65bc5f9
      that nobody will try to debug files longer than 64K lines?  What about
65bc5f9
      machine generated programs? */
65bc5f9
@@ -663,6 +675,8 @@ struct symbol
65bc5f9
 #define SYMBOL_DOMAIN(symbol)	(symbol)->domain
65bc5f9
 #define SYMBOL_CLASS(symbol)		(symbol)->aclass
65bc5f9
 #define SYMBOL_TYPE(symbol)		(symbol)->type
65bc5f9
+#define SYMBOL_FILE_INDEX(symbol)	(symbol)->file.index
65bc5f9
+#define SYMBOL_FILE_SYMTAB(symbol)	(symbol)->file.symtab
65bc5f9
 #define SYMBOL_LINE(symbol)		(symbol)->line
65bc5f9
 #define SYMBOL_BASEREG(symbol)		(symbol)->aux_value.basereg
65bc5f9
 #define SYMBOL_OBJFILE(symbol)          (symbol)->aux_value.objfile