(
&self,
section_index: SectionIndex,
offset: u64,
)
| 575 | } |
| 576 | |
| 577 | pub fn locate<'tcx>( |
| 578 | &self, |
| 579 | section_index: SectionIndex, |
| 580 | offset: u64, |
| 581 | ) -> Result<Option<Location>, Error> { |
| 582 | // FIXME: should this be optimized? |
| 583 | |
| 584 | let mut iter = self.dwarf.units(); |
| 585 | while let Some(header) = iter.next()? { |
| 586 | let mut unit = self.dwarf.unit(header)?; |
| 587 | |
| 588 | let mut prev: Option<(_, LineRow)> = None; |
| 589 | if let Some(ilnp) = unit.line_program.take() { |
| 590 | let mut rows = ilnp.rows(); |
| 591 | while let Some((_, row)) = rows.next_row()? { |
| 592 | let row = *row; |
| 593 | let encoded_address = row.address(); |
| 594 | let (encoded_section, encoded_offset) = |
| 595 | self.section_layout.decode(encoded_address)?; |
| 596 | |
| 597 | // Skip over sections that we don't care about. |
| 598 | if encoded_section != section_index { |
| 599 | continue; |
| 600 | } |
| 601 | |
| 602 | if let Some((prev_addr, prev_row)) = prev |
| 603 | && prev_row.line().is_some() |
| 604 | && (prev_addr..encoded_offset).contains(&(offset as i64)) |
| 605 | { |
| 606 | let file = self.file_name(&unit, rows.header(), prev_row.file_index())?; |
| 607 | let line = prev_row.line().map_or(0, NonZero::get); |
| 608 | let column = match prev_row.column() { |
| 609 | gimli::ColumnType::LeftEdge => 0, |
| 610 | gimli::ColumnType::Column(v) => v.get(), |
| 611 | }; |
| 612 | return Ok(Some(Location { file, line, column })); |
| 613 | } |
| 614 | |
| 615 | if row.end_sequence() { |
| 616 | prev = None; |
| 617 | } else { |
| 618 | prev = Some((encoded_offset, row)); |
| 619 | } |
| 620 | } |
| 621 | } |
| 622 | } |
| 623 | |
| 624 | Ok(None) |
| 625 | } |
| 626 | } |
no test coverage detected