View | Details | Raw Unified | Return to bug 26828
Collapse All | Expand All

(-)a/gdb/dwarf2/read.c (-16 / +14 lines)
Lines 23219-23224 follow_die_offset (sect_offset sect_off, int offset_in_dwz, Link Here
23219
23219
23220
  target_cu = cu;
23220
  target_cu = cu;
23221
23221
23222
  dwarf_read_debug_printf_v ("source CU offset: %s, target offset: %s, "
23223
			     "source CU contains target offset: %d",
23224
			     sect_offset_str (cu->per_cu->sect_off),
23225
			     sect_offset_str (sect_off),
23226
			     cu->header.offset_in_cu_p (sect_off));
23227
23222
  if (cu->per_cu->is_debug_types)
23228
  if (cu->per_cu->is_debug_types)
23223
    {
23229
    {
23224
      /* .debug_types CUs cannot reference anything outside their CU.
23230
      /* .debug_types CUs cannot reference anything outside their CU.
Lines 23235-23240 follow_die_offset (sect_offset sect_off, int offset_in_dwz, Link Here
23235
      per_cu = dwarf2_find_containing_comp_unit (sect_off, offset_in_dwz,
23241
      per_cu = dwarf2_find_containing_comp_unit (sect_off, offset_in_dwz,
23236
						 per_objfile);
23242
						 per_objfile);
23237
23243
23244
      dwarf_read_debug_printf_v ("target CU offset: %s, target CU DIEs loaded: %d",
23245
				 sect_offset_str (per_cu->sect_off),
23246
				 per_objfile->get_cu (per_cu) != nullptr);
23247
23238
      /* If necessary, add it to the queue and load its DIEs.  */
23248
      /* If necessary, add it to the queue and load its DIEs.  */
23239
      if (maybe_queue_comp_unit (cu, per_cu, per_objfile, cu->language))
23249
      if (maybe_queue_comp_unit (cu, per_cu, per_objfile, cu->language))
23240
	load_full_comp_unit (per_cu, per_objfile, per_objfile->get_cu (per_cu),
23250
	load_full_comp_unit (per_cu, per_objfile, per_objfile->get_cu (per_cu),
Lines 24615-24620 dwarf2_per_objfile::set_cu (dwarf2_per_cu_data *per_cu, dwarf2_cu *cu) Link Here
24615
void
24625
void
24616
dwarf2_per_objfile::age_comp_units ()
24626
dwarf2_per_objfile::age_comp_units ()
24617
{
24627
{
24628
  dwarf_read_debug_printf_v ("running");
24629
24618
  /* Start by clearing all marks.  */
24630
  /* Start by clearing all marks.  */
24619
  for (auto pair : m_dwarf2_cus)
24631
  for (auto pair : m_dwarf2_cus)
24620
    pair.second->mark = false;
24632
    pair.second->mark = false;
Lines 24637-24642 dwarf2_per_objfile::age_comp_units () Link Here
24637
24649
24638
      if (!cu->mark)
24650
      if (!cu->mark)
24639
	{
24651
	{
24652
	  dwarf_read_debug_printf_v ("deleting old CU %s",
24653
				     sect_offset_str (cu->per_cu->sect_off));
24640
	  delete cu;
24654
	  delete cu;
24641
	  it = m_dwarf2_cus.erase (it);
24655
	  it = m_dwarf2_cus.erase (it);
24642
	}
24656
	}
24643
- 
24644
     /* If necessary, add it to the queue and load its DIEs.  */
24657
     /* If necessary, add it to the queue and load its DIEs.  */
24645
     if (maybe_queue_comp_unit (cu, per_cu, per_objfile, cu->language))
24658
     if (maybe_queue_comp_unit (cu, per_cu, per_objfile, cu->language))
24646
     target_cu = per_objfile->get_cu (per_cu);  <--- HERE
24659
     target_cu = per_objfile->get_cu (per_cu);  <--- HERE
24647
 dwarf2_fetch_die_type_sect_off gets called for a DIE in CU A
24648
 A DIE in CU A requires some DIE in CU B
24649
 follow_die_offset calls maybe_queue_comp_unit.  maybe_queue_comp_unit
24650
 sees CU B is not queued and its DIEs are not loaded, so it enqueues it
24660
 sees CU B is not queued and its DIEs are not loaded, so it enqueues it
24651
 and returns 1 to its caller - meaning "the DIEs are not loaded, you
24661
 and returns 1 to its caller - meaning "the DIEs are not loaded, you
24652
 should load them" - prompting follow_die_offset to load the DIEs by
24662
 should load them" - prompting follow_die_offset to load the DIEs by
24653
 calling load_full_comp_unit
24663
 calling load_full_comp_unit
24654
 Note that CU B is enqueued by maybe_queue_comp_unit even if it has
24655
 already been expanded.  It's a bit useless, but that's how it works
24664
 already been expanded.  It's a bit useless, but that's how it works
24656
 right now.
24665
 right now.
24657
 Since we entered the dwarf2/read code through
24658
 dwarf2_fetch_die_type_sect_off, nothing processes the queue, so we
24666
 dwarf2_fetch_die_type_sect_off, nothing processes the queue, so we
24659
 exit the dwarf2/read code with CU B still lingering in the queue.
24667
 exit the dwarf2/read code with CU B still lingering in the queue.
24660
 dwarf2_fetch_die_type_sect_off gets called for a DIE in CU A, again
24661
 A DIE in CU A requires some DIE in CU B, again
24662
 This time, maybe_queue_comp_unit sees that CU B is in the queue.
24663
 Because of the supposed invariant that if a CU is in the queue, its
24668
 Because of the supposed invariant that if a CU is in the queue, its
24664
 DIEs are loaded in the memory, it returns 0 to its caller, meaning
24669
 DIEs are loaded in the memory, it returns 0 to its caller, meaning
24665
 "you don't need to load the DIEs!".
24670
 "you don't need to load the DIEs!".
24666
 That happens to be true, so everything is fine for now.
24667
 However, some things call dwarf2_per_objfile::age_comp_units in the
24668
 mean time, enough so that CU B's age becomes past the
24671
 mean time, enough so that CU B's age becomes past the
24669
 dwarf_max_cache_age threshold.  age_comp_units proceeds to free CU B's
24672
 dwarf_max_cache_age threshold.  age_comp_units proceeds to free CU B's
24670
 DIEs.  Remember that CU B is still lingering in the queue (oops).
24673
 DIEs.  Remember that CU B is still lingering in the queue (oops).
24671
 dwarf2_fetch_die_type_sect_off gets called for a DIE in CU A, again
24672
 A DIE in CU A requires some DIE in CU B
24673
 maybe_queue_comp_unit sees that CU B is in the queue, so returns to
24674
 its caller "you don't need to load the DIEs!".  However, we know at
24674
 its caller "you don't need to load the DIEs!".  However, we know at
24675
 this point this is false.
24675
 this point this is false.
24676
 follow_die_offset doesn't load the DIEs, tries to obtain the DIEs for
24677
 CU B:
24676
 CU B:
24678
   target_cu = per_objfile->get_cu (per_cu);
24677
   target_cu = per_objfile->get_cu (per_cu);
24679
 But since they are not loaded, target_cu is nullptr, and we get the
24678
 But since they are not loaded, target_cu is nullptr, and we get the
24680
 crash mentioned above.
24679
 crash mentioned above.
24681
   /home/simark/src/binutils-gdb/gdb/dwarf2/read.c:9100: internal-error:
24680
   /home/simark/src/binutils-gdb/gdb/dwarf2/read.c:9100: internal-error:
24682
       int maybe_queue_comp_unit(dwarf2_cu*, dwarf2_per_cu_data*, dwarf2_per_objfile*, language):
24681
       int maybe_queue_comp_unit(dwarf2_cu*, dwarf2_per_cu_data*, dwarf2_per_objfile*, language):
24683
       Assertion `per_objfile->get_cu (per_cu) != nullptr' failed.
24682
       Assertion `per_objfile->get_cu (per_cu) != nullptr' failed.
24684
--
24685
gdb/dwarf2/read.c | 7 ++++++-
24683
gdb/dwarf2/read.c | 7 ++++++-
24686
1 file changed, 6 insertions(+), 1 deletion(-)
24684
1 file changed, 6 insertions(+), 1 deletion(-)
(-)a/gdb/dwarf2/read.c (-3 / +6 lines)
Lines 9094-9100 maybe_queue_comp_unit (struct dwarf2_cu *dependent_cu, Link Here
9094
9094
9095
  /* If it's already on the queue, we have nothing to do.  */
9095
  /* If it's already on the queue, we have nothing to do.  */
9096
  if (per_cu->queued)
9096
  if (per_cu->queued)
9097
    return 0;
9097
    {
9098
      /* Verify the invariant that if a CU is queue for expansion, its DIEs are
9099
	 loaded.  */
9100
      gdb_assert (per_objfile->get_cu (per_cu) != nullptr);
9101
      return 0;
9102
    }
9098
9103
9099
  /* If the compilation unit is already loaded, just mark it as
9104
  /* If the compilation unit is already loaded, just mark it as
9100
     used.  */
9105
     used.  */
9101
- 
9102
CUs-to-expand queue
9106
CUs-to-expand queue
9103
--
9104
gdb/dwarf2/read.c | 72 ++++++++++++++++++++++++++++-------------------
9107
gdb/dwarf2/read.c | 72 ++++++++++++++++++++++++++++-------------------
9105
gdb/dwarf2/read.h |  2 +-
9108
gdb/dwarf2/read.h |  2 +-
9106
2 files changed, 44 insertions(+), 30 deletions(-)
9109
2 files changed, 44 insertions(+), 30 deletions(-)
(-)a/gdb/dwarf2/read.c (-29 / +43 lines)
Lines 1667-1681 class dwarf2_queue_guard Link Here
1667
  explicit dwarf2_queue_guard (dwarf2_per_objfile *per_objfile)
1667
  explicit dwarf2_queue_guard (dwarf2_per_objfile *per_objfile)
1668
    : m_per_objfile (per_objfile)
1668
    : m_per_objfile (per_objfile)
1669
  {
1669
  {
1670
    gdb_assert (!m_per_objfile->per_bfd->queue.has_value ());
1671
1672
    m_per_objfile->per_bfd->queue.emplace ();
1670
  }
1673
  }
1671
1674
1672
  /* Free any entries remaining on the queue.  There should only be
1675
  /* Free any entries remaining on the queue.  There should only be
1673
     entries left if we hit an error while processing the dwarf.  */
1676
     entries left if we hit an error while processing the dwarf.  */
1674
  ~dwarf2_queue_guard ()
1677
  ~dwarf2_queue_guard ()
1675
  {
1678
  {
1676
    /* Ensure that no memory is allocated by the queue.  */
1679
    gdb_assert (m_per_objfile->per_bfd->queue.has_value ());
1677
    std::queue<dwarf2_queue_item> empty;
1680
1678
    std::swap (m_per_objfile->per_bfd->queue, empty);
1681
    m_per_objfile->per_bfd->queue.reset ();
1679
  }
1682
  }
1680
1683
1681
  DISABLE_COPY_AND_ASSIGN (dwarf2_queue_guard);
1684
  DISABLE_COPY_AND_ASSIGN (dwarf2_queue_guard);
Lines 2432-2461 dw2_do_instantiate_symtab (dwarf2_per_cu_data *per_cu, Link Here
2432
  if (per_cu->type_unit_group_p ())
2435
  if (per_cu->type_unit_group_p ())
2433
    return;
2436
    return;
2434
2437
2435
  /* The destructor of dwarf2_queue_guard frees any entries left on
2438
  {
2436
     the queue.  After this point we're guaranteed to leave this function
2439
    /* The destructor of dwarf2_queue_guard frees any entries left on
2437
     with the dwarf queue empty.  */
2440
       the queue.  After this point we're guaranteed to leave this function
2438
  dwarf2_queue_guard q_guard (per_objfile);
2441
       with the dwarf queue empty.  */
2439
2442
    dwarf2_queue_guard q_guard (per_objfile);
2440
  if (!per_objfile->symtab_set_p (per_cu))
2441
    {
2442
      queue_comp_unit (per_cu, per_objfile, language_minimal);
2443
      dwarf2_cu *cu = load_cu (per_cu, per_objfile, skip_partial);
2444
2443
2445
      /* If we just loaded a CU from a DWO, and we're working with an index
2444
    if (!per_objfile->symtab_set_p (per_cu))
2446
	 that may badly handle TUs, load all the TUs in that DWO as well.
2445
      {
2447
	 http://sourceware.org/bugzilla/show_bug.cgi?id=15021  */
2446
	queue_comp_unit (per_cu, per_objfile, language_minimal);
2448
      if (!per_cu->is_debug_types
2447
	dwarf2_cu *cu = load_cu (per_cu, per_objfile, skip_partial);
2449
	  && cu != NULL
2448
2450
	  && cu->dwo_unit != NULL
2449
	/* If we just loaded a CU from a DWO, and we're working with an index
2451
	  && per_objfile->per_bfd->index_table != NULL
2450
	   that may badly handle TUs, load all the TUs in that DWO as well.
2452
	  && per_objfile->per_bfd->index_table->version <= 7
2451
	   http://sourceware.org/bugzilla/show_bug.cgi?id=15021  */
2453
	  /* DWP files aren't supported yet.  */
2452
	if (!per_cu->is_debug_types
2454
	  && get_dwp_file (per_objfile) == NULL)
2453
	    && cu != NULL
2455
	queue_and_load_all_dwo_tus (cu);
2454
	    && cu->dwo_unit != NULL
2456
    }
2455
	    && per_objfile->per_bfd->index_table != NULL
2456
	    && per_objfile->per_bfd->index_table->version <= 7
2457
	    /* DWP files aren't supported yet.  */
2458
	    && get_dwp_file (per_objfile) == NULL)
2459
	  queue_and_load_all_dwo_tus (cu);
2460
      }
2457
2461
2458
  process_queue (per_objfile);
2462
    process_queue (per_objfile);
2463
  }
2459
2464
2460
  /* Age the cache, releasing compilation units that have not
2465
  /* Age the cache, releasing compilation units that have not
2461
     been used recently.  */
2466
     been used recently.  */
Lines 9057-9063 queue_comp_unit (dwarf2_per_cu_data *per_cu, Link Here
9057
		 enum language pretend_language)
9062
		 enum language pretend_language)
9058
{
9063
{
9059
  per_cu->queued = 1;
9064
  per_cu->queued = 1;
9060
  per_cu->per_bfd->queue.emplace (per_cu, per_objfile, pretend_language);
9065
9066
  gdb_assert (per_objfile->per_bfd->queue.has_value ());
9067
  per_cu->per_bfd->queue->emplace (per_cu, per_objfile, pretend_language);
9061
}
9068
}
9062
9069
9063
/* If PER_CU is not yet queued, add it to the queue.
9070
/* If PER_CU is not yet queued, add it to the queue.
Lines 9126-9134 process_queue (dwarf2_per_objfile *per_objfile) Link Here
9126
9133
9127
  /* The queue starts out with one item, but following a DIE reference
9134
  /* The queue starts out with one item, but following a DIE reference
9128
     may load a new CU, adding it to the end of the queue.  */
9135
     may load a new CU, adding it to the end of the queue.  */
9129
  while (!per_objfile->per_bfd->queue.empty ())
9136
  while (!per_objfile->per_bfd->queue->empty ())
9130
    {
9137
    {
9131
      dwarf2_queue_item &item = per_objfile->per_bfd->queue.front ();
9138
      dwarf2_queue_item &item = per_objfile->per_bfd->queue->front ();
9132
      dwarf2_per_cu_data *per_cu = item.per_cu;
9139
      dwarf2_per_cu_data *per_cu = item.per_cu;
9133
9140
9134
      if (!per_objfile->symtab_set_p (per_cu))
9141
      if (!per_objfile->symtab_set_p (per_cu))
Lines 9174-9180 process_queue (dwarf2_per_objfile *per_objfile) Link Here
9174
	}
9181
	}
9175
9182
9176
      per_cu->queued = 0;
9183
      per_cu->queued = 0;
9177
      per_objfile->per_bfd->queue.pop ();
9184
      per_objfile->per_bfd->queue->pop ();
9178
    }
9185
    }
9179
9186
9180
  dwarf_read_debug_printf ("Done expanding symtabs of %s.",
9187
  dwarf_read_debug_printf ("Done expanding symtabs of %s.",
Lines 24632-24637 dwarf2_per_objfile::age_comp_units () Link Here
24632
{
24639
{
24633
  dwarf_read_debug_printf_v ("running");
24640
  dwarf_read_debug_printf_v ("running");
24634
24641
24642
  /* This is not expected to be called in the middle of CU expansion.  There is
24643
     an invariant that if a CU is in the CUs-to-expand queue, its DIEs are
24644
     loaded in memory.  Calling age_comp_units while the queue is in use could
24645
     make us free the DIEs for a CU that is in the queue and therefore break
24646
     that invariant.  */
24647
  gdb_assert (!this->per_bfd->queue.has_value ());
24648
24635
  /* Start by clearing all marks.  */
24649
  /* Start by clearing all marks.  */
24636
  for (auto pair : m_dwarf2_cus)
24650
  for (auto pair : m_dwarf2_cus)
24637
    pair.second->mark = false;
24651
    pair.second->mark = false;
(-)a/gdb/dwarf2/read.h (-3 / +1 lines)
Lines 250-256 struct dwarf2_per_bfd Link Here
250
    abstract_to_concrete;
250
    abstract_to_concrete;
251
251
252
  /* CUs that are queued to be read.  */
252
  /* CUs that are queued to be read.  */
253
  std::queue<dwarf2_queue_item> queue;
253
  gdb::optional<std::queue<dwarf2_queue_item>> queue;
254
254
255
  /* We keep a separate reference to the partial symtabs, in case we
255
  /* We keep a separate reference to the partial symtabs, in case we
256
     are sharing them between objfiles.  This is only set after
256
     are sharing them between objfiles.  This is only set after
257
- 
258
already expanded
257
already expanded
259
--
260
gdb/dwarf2/read.c | 16 ++++++++--------
258
gdb/dwarf2/read.c | 16 ++++++++--------
261
1 file changed, 8 insertions(+), 8 deletions(-)
259
1 file changed, 8 insertions(+), 8 deletions(-)
(-)a/gdb/dwarf2/read.c (-9 / +8 lines)
Lines 9108-9126 maybe_queue_comp_unit (struct dwarf2_cu *dependent_cu, Link Here
9108
      return 0;
9108
      return 0;
9109
    }
9109
    }
9110
9110
9111
  if (!per_objfile->symtab_set_p (per_cu))
9112
    {
9113
      /* Add it to the queue.  */
9114
      queue_comp_unit (per_cu, per_objfile,  pretend_language);
9115
    }
9116
9111
  /* If the compilation unit is already loaded, just mark it as
9117
  /* If the compilation unit is already loaded, just mark it as
9112
     used.  */
9118
     used.  */
9113
  dwarf2_cu *cu = per_objfile->get_cu (per_cu);
9119
  dwarf2_cu *cu = per_objfile->get_cu (per_cu);
9114
  if (cu != nullptr)
9120
  if (cu != nullptr)
9115
    {
9121
    cu->last_used = 0;
9116
      cu->last_used = 0;
9117
      return 0;
9118
    }
9119
9122
9120
  /* Add it to the queue.  */
9123
  return cu == nullptr;
9121
  queue_comp_unit (per_cu, per_objfile,  pretend_language);
9122
9123
  return 1;
9124
}
9124
}
9125
9125
9126
/* Process the queue.  */
9126
/* Process the queue.  */
9127
- 

Return to bug 26828