Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(460)

Side by Side Diff: experimental/visual_studio_plugin/src/dwarf_reader/dwarf_parser.cc

Issue 10928195: First round of dead file removal (Closed) Base URL: https://github.com/samclegg/nativeclient-sdk.git@master
Patch Set: Created 8 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 // Copyright (c) 2011 The Native Client Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include <stdlib.h>
6
7 #include "common/dwarf/bytereader.h"
8
9 #include "dwarf_reader/dwarf_frame_info_reader.h"
10 #include "dwarf_reader/dwarf_info_parser.h"
11 #include "dwarf_reader/dwarf_line_parser.h"
12 #include "dwarf_reader/dwarf_parser.h"
13 #include "dwarf_reader/dwarf_reader.h"
14 #include "dwarf_reader/elf_section_reader.h"
15 #include "dwarf_reader/parse_state.h"
16
17 #include "elf_reader/elf_object.h"
18
19 namespace {
20 const uint64 kMaxValue = static_cast<uint64>(-1);
21 }
22
23 namespace dwarf_reader {
24
25 DwarfParser::DwarfParser()
26 : elf_section_reader_(NULL),
27 file_path_(NULL),
28 is_initialized_(false) { }
29
30 DwarfParser::~DwarfParser() {
31 delete elf_section_reader_;
32 }
33
34 bool DwarfParser::Init(elf_reader::ElfObject *elf_object) {
35 if (NULL == elf_object) return false;
36
37 file_path_ = elf_object->GetPath();
38 elf_section_reader_ = new ElfSectionReader();
39
40 if (NULL == file_path_ || NULL == elf_section_reader_) return false;
41
42 elf_object->Parse(elf_section_reader_);
43 is_initialized_ = true;
44
45 return is_initialized_;
46 }
47
48 void DwarfParser::PopulateReader(IDwarfReader *dwarf_reader) const {
49 if (is_initialized_) {
50 PopulateCompilationUnits(dwarf_reader);
51 PopulateCallFrameInfo(dwarf_reader);
52 PopulateLocationLists(dwarf_reader);
53 PopulateRangeLists(dwarf_reader);
54 }
55 }
56
57 void DwarfParser::PopulateCallFrameInfo(IDwarfReader *dwarf_reader) const {
58 SectionInfo debug_frame_section =
59 elf_section_reader_->GetSectionInfo(".eh_frame");
60 SectionInfo text_section = elf_section_reader_->GetSectionInfo(".text");
61
62 elf_section_reader_->GetByteReader()->SetTextBase(
63 reinterpret_cast<uint64>(text_section.first));
64 elf_section_reader_->GetByteReader()->SetCFIDataBase(
65 elf_section_reader_->GetSectionLoadAddress(".eh_frame"),
66 debug_frame_section.first);
67
68 // Read the call frame information
69 dwarf2reader::CallFrameInfo::Reporter reporter(file_path_);
70 DwarfFrameInfoReader handler(dwarf_reader);
71 dwarf2reader::CallFrameInfo cfi_reader(
72 debug_frame_section.first,
73 debug_frame_section.second,
74 elf_section_reader_->GetByteReader(),
75 &handler,
76 &reporter,
77 true);
78 cfi_reader.Start();
79 }
80
81 void DwarfParser::PopulateCompilationUnits(IDwarfReader *dwarf_reader) const {
82 ParseState parse_state;
83
84 SectionInfo debug_info_section =
85 elf_section_reader_->GetSectionInfo(".debug_info");
86 SectionInfo debug_line_section =
87 elf_section_reader_->GetSectionInfo(".debug_line");
88
89 DwarfInfoParser info_handler(&parse_state, dwarf_reader);
90 DwarfLineParser line_handler(&parse_state, dwarf_reader);
91
92 uint64 debug_info_length = debug_info_section.second;
93 uint64 debug_line_length = debug_line_section.second;
94 const char *debug_line_ptr = debug_line_section.first;
95 for (uint64 offset = 0; offset < debug_info_length;) {
96 dwarf2reader::CompilationUnit compilation_unit_reader(
97 elf_section_reader_->sections(),
98 offset,
99 elf_section_reader_->GetByteReader(),
100 &info_handler);
101
102 // Process the entire compilation unit; get the offset of the next.
103 offset += compilation_unit_reader.Start();
104
105 // Process the matching line information; get the offset of the next.
106 dwarf2reader::LineInfo lineInfo(debug_line_ptr,
107 debug_line_length,
108 elf_section_reader_->GetByteReader(),
109 &line_handler);
110
111 debug_line_ptr += lineInfo.Start();
112
113 // Pop the end of the compilation unit manually
114 dwarf_reader->EndCompilationUnit(parse_state.GetTopStackContext(),
115 parse_state.GetTopStackAddress());
116 parse_state.PopStackFrame();
117 }
118 }
119
120 void DwarfParser::PopulateLocationLists(IDwarfReader *dwarf_reader) const {
121 SectionInfo debug_loc_section =
122 elf_section_reader_->GetSectionInfo(".debug_loc");
123
124 // Read the location list
125 const char* debug_loc_ptr = debug_loc_section.first;
126 const char* current = debug_loc_ptr;
127 uint64 debug_loc_length = debug_loc_section.second;
128 const char* debug_loc_end = debug_loc_ptr + debug_loc_length;
129 dwarf2reader::ByteReader* byte_reader =
130 elf_section_reader_->GetByteReader();
131 bool is_first = true;
132 while (current < debug_loc_end) {
133 // Layout of the debug_loc block is:
134 //
135 // LowPc - address
136 // HighPc - address
137 // DataLength - ushort (optional)
138 // Data - byte[] (optional)
139 uint64 offset = current - debug_loc_ptr;
140 uint64 low_pc = byte_reader->ReadAddress(current);
141 current += byte_reader->AddressSize();
142 uint64 high_pc = byte_reader->ReadAddress(current);
143 current += byte_reader->AddressSize();
144
145 size_t data_size = 0;
146 const void* data = 0;
147
148 if (0 == low_pc && 0 == high_pc) {
149 // if low_pc and high_pc are both zero, that signals end of list.
150 is_first = true;
151 continue;
152 } else if (kMaxValue == low_pc) {
153 // the location is an absolute address; its value is in high_pc.
154 data_size = 4;
155 data = &high_pc;
156 } else {
157 data_size = byte_reader->ReadTwoBytes(current);
158 current += 2;
159 data = reinterpret_cast<const void *>(current);
160 current += data_size;
161 }
162 dwarf_reader->AddLocListEntry(offset,
163 is_first,
164 low_pc,
165 high_pc,
166 data,
167 data_size);
168 is_first = false;
169 }
170 }
171
172 void DwarfParser::PopulateRangeLists(IDwarfReader *dwarf_reader) const {
173 SectionInfo debug_ranges_section =
174 elf_section_reader_->GetSectionInfo(".debug_ranges");
175
176 const char *debug_ranges_start = debug_ranges_section.first;
177 const char *current = debug_ranges_section.first;
178 const char *debug_ranges_end =
179 debug_ranges_start + debug_ranges_section.second;
180
181 dwarf2reader::ByteReader *byte_reader =
182 elf_section_reader_->GetByteReader();
183
184 uint64 offset = 0;
185 // When there is no explicit base_address set, we want to populate the range
186 // list entry with max value. By convention, this means that the
187 // compilation unit's base will serve as the base for these entries.
188 uint64 base_address = kMaxValue;
189
190 while (current < debug_ranges_end) {
191 uint64 low_pc = byte_reader->ReadAddress(current);
192 current += byte_reader->AddressSize();
193 uint64 high_pc = byte_reader->ReadAddress(current);
194 current += byte_reader->AddressSize();
195
196 if (0 == low_pc && 0 == high_pc) {
197 // We are now looking at the start of the next list.
198 offset = current - debug_ranges_start;
199 base_address = kMaxValue;
200 } else if (kMaxValue == low_pc) {
201 // This entry is an base address; its value is in high_pc.
202 base_address = high_pc;
203 } else {
204 dwarf_reader->AddRangeListEntry(offset, base_address, low_pc, high_pc);
205 }
206 }
207 }
208
209 } // namespace dwarf_parser
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698