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

Side by Side Diff: snapshot/win/pe_image_reader.cc

Issue 1311003003: Implement ModuleSnapshotWin::UUID (Closed) Base URL: https://chromium.googlesource.com/crashpad/crashpad@master
Patch Set: fixes Created 5 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
« no previous file with comments | « snapshot/win/pe_image_reader.h ('k') | snapshot/win/pe_image_reader_test.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2015 The Crashpad Authors. All rights reserved. 1 // Copyright 2015 The Crashpad Authors. All rights reserved.
2 // 2 //
3 // Licensed under the Apache License, Version 2.0 (the "License"); 3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License. 4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at 5 // You may obtain a copy of the License at
6 // 6 //
7 // http://www.apache.org/licenses/LICENSE-2.0 7 // http://www.apache.org/licenses/LICENSE-2.0
8 // 8 //
9 // Unless required by applicable law or agreed to in writing, software 9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS, 10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and 12 // See the License for the specific language governing permissions and
13 // limitations under the License. 13 // limitations under the License.
14 14
15 #include "snapshot/win/pe_image_reader.h" 15 #include "snapshot/win/pe_image_reader.h"
16 16
17 #include <string.h> 17 #include <string.h>
18 18
19 #include "base/logging.h" 19 #include "base/logging.h"
20 #include "base/memory/scoped_ptr.h"
20 #include "base/strings/stringprintf.h" 21 #include "base/strings/stringprintf.h"
21 #include "client/crashpad_info.h" 22 #include "client/crashpad_info.h"
22 #include "snapshot/win/process_reader_win.h" 23 #include "snapshot/win/process_reader_win.h"
24 #include "util/misc/pdb_structures.h"
23 25
24 namespace crashpad { 26 namespace crashpad {
25 27
26 namespace { 28 namespace {
27 29
28 std::string RangeToString(const CheckedWinAddressRange& range) { 30 std::string RangeToString(const CheckedWinAddressRange& range) {
29 return base::StringPrintf("[0x%llx + 0x%llx (%s)]", 31 return base::StringPrintf("[0x%llx + 0x%llx (%s)]",
30 range.Base(), 32 range.Base(),
31 range.Size(), 33 range.Size(),
32 range.Is64Bit() ? "64" : "32"); 34 range.Is64Bit() ? "64" : "32");
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after
103 105
104 if (crashpad_info->signature != CrashpadInfo::kSignature || 106 if (crashpad_info->signature != CrashpadInfo::kSignature ||
105 crashpad_info->version < 1) { 107 crashpad_info->version < 1) {
106 LOG(WARNING) << "unexpected crashpad info data " << module_name_; 108 LOG(WARNING) << "unexpected crashpad info data " << module_name_;
107 return false; 109 return false;
108 } 110 }
109 111
110 return true; 112 return true;
111 } 113 }
112 114
113 bool PEImageReader::GetSectionByName(const std::string& name, 115 bool PEImageReader::DebugDirectoryInformation(UUID* uuid,
114 IMAGE_SECTION_HEADER* section) const { 116 DWORD* age,
115 if (name.size() > sizeof(section->Name)) { 117 std::string* pdbname) {
116 LOG(WARNING) << "supplied section name too long " << name; 118 WinVMAddress nt_headers_address;
119 IMAGE_NT_HEADERS nt_headers;
120 if (!ReadNtHeaders(&nt_headers_address, &nt_headers))
117 return false; 121 return false;
122
123 const IMAGE_DATA_DIRECTORY& data_directory =
124 nt_headers.OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_DEBUG];
125 if (data_directory.VirtualAddress == 0 || data_directory.Size == 0)
126 return false;
127 IMAGE_DEBUG_DIRECTORY debug_directory;
128 if (data_directory.Size % sizeof(debug_directory) != 0)
129 return false;
130 for (size_t offset = 0; offset < data_directory.Size;
131 offset += sizeof(debug_directory)) {
132 if (!CheckedReadMemory(Address() + data_directory.VirtualAddress + offset,
133 sizeof(debug_directory),
134 &debug_directory)) {
135 LOG(WARNING) << "could not read data directory";
136 return false;
137 }
138
139 if (debug_directory.Type != IMAGE_DEBUG_TYPE_CODEVIEW)
140 continue;
141
142 if (debug_directory.SizeOfData < sizeof(CodeViewRecordPDB70)) {
143 LOG(WARNING) << "CodeView debug entry of unexpected size";
144 continue;
145 }
146 scoped_ptr<char[]> data(new char[debug_directory.SizeOfData]);
147 if (!CheckedReadMemory(Address() + debug_directory.AddressOfRawData,
148 debug_directory.SizeOfData,
149 data.get())) {
150 LOG(WARNING) << "could not read debug directory";
151 return false;
152 }
153
154 if (*reinterpret_cast<DWORD*>(data.get()) !=
155 CodeViewRecordPDB70::kSignature) {
156 // TODO(scottmg): Consider supporting other record types, see
157 // https://code.google.com/p/crashpad/issues/detail?id=47.
158 LOG(WARNING) << "encountered non-7.0 CodeView debug record";
159 continue;
160 }
161
162 CodeViewRecordPDB70* codeview =
163 reinterpret_cast<CodeViewRecordPDB70*>(data.get());
164 *uuid = codeview->uuid;
165 *age = codeview->age;
166 // This is a NUL-terminated string encoded in the codepage of the system
167 // where the binary was linked. We have no idea what that was, so we just
168 // assume ASCII.
169 *pdbname = std::string(reinterpret_cast<char*>(&codeview->pdb_name[0]));
170 return true;
118 } 171 }
119 172
173 return false;
174 }
175
176 // TODO(scottmg): This needs to be made cross-bitness supporting.
177 bool PEImageReader::ReadNtHeaders(WinVMAddress* nt_headers_address,
178 IMAGE_NT_HEADERS* nt_headers) const {
120 IMAGE_DOS_HEADER dos_header; 179 IMAGE_DOS_HEADER dos_header;
121 if (!CheckedReadMemory(Address(), sizeof(IMAGE_DOS_HEADER), &dos_header)) { 180 if (!CheckedReadMemory(Address(), sizeof(IMAGE_DOS_HEADER), &dos_header)) {
122 LOG(WARNING) << "could not read dos header of " << module_name_; 181 LOG(WARNING) << "could not read dos header of " << module_name_;
123 return false; 182 return false;
124 } 183 }
125 184
126 if (dos_header.e_magic != IMAGE_DOS_SIGNATURE) { 185 if (dos_header.e_magic != IMAGE_DOS_SIGNATURE) {
127 LOG(WARNING) << "invalid e_magic in dos header of " << module_name_; 186 LOG(WARNING) << "invalid e_magic in dos header of " << module_name_;
128 return false; 187 return false;
129 } 188 }
130 189
131 // TODO(scottmg): This is reading a same-bitness sized structure. 190 *nt_headers_address = Address() + dos_header.e_lfanew;
132 IMAGE_NT_HEADERS nt_headers;
133 WinVMAddress nt_headers_address = Address() + dos_header.e_lfanew;
134 if (!CheckedReadMemory( 191 if (!CheckedReadMemory(
135 nt_headers_address, sizeof(IMAGE_NT_HEADERS), &nt_headers)) { 192 *nt_headers_address, sizeof(IMAGE_NT_HEADERS), nt_headers)) {
136 LOG(WARNING) << "could not read nt headers of " << module_name_; 193 LOG(WARNING) << "could not read nt headers of " << module_name_;
137 return false; 194 return false;
138 } 195 }
139 196
140 if (nt_headers.Signature != IMAGE_NT_SIGNATURE) { 197 if (nt_headers->Signature != IMAGE_NT_SIGNATURE) {
141 LOG(WARNING) << "invalid signature in nt headers of " << module_name_; 198 LOG(WARNING) << "invalid signature in nt headers of " << module_name_;
142 return false; 199 return false;
143 } 200 }
144 201
202 return true;
203 }
204
205 bool PEImageReader::GetSectionByName(const std::string& name,
206 IMAGE_SECTION_HEADER* section) const {
207 if (name.size() > sizeof(section->Name)) {
208 LOG(WARNING) << "supplied section name too long " << name;
209 return false;
210 }
211
212 WinVMAddress nt_headers_address;
213 IMAGE_NT_HEADERS nt_headers;
214 if (!ReadNtHeaders(&nt_headers_address, &nt_headers))
215 return false;
216
145 WinVMAddress first_section_address = 217 WinVMAddress first_section_address =
146 nt_headers_address + offsetof(IMAGE_NT_HEADERS, OptionalHeader) + 218 nt_headers_address + offsetof(IMAGE_NT_HEADERS, OptionalHeader) +
147 nt_headers.FileHeader.SizeOfOptionalHeader; 219 nt_headers.FileHeader.SizeOfOptionalHeader;
148 for (DWORD i = 0; i < nt_headers.FileHeader.NumberOfSections; ++i) { 220 for (DWORD i = 0; i < nt_headers.FileHeader.NumberOfSections; ++i) {
149 WinVMAddress section_address = 221 WinVMAddress section_address =
150 first_section_address + sizeof(IMAGE_SECTION_HEADER) * i; 222 first_section_address + sizeof(IMAGE_SECTION_HEADER) * i;
151 if (!CheckedReadMemory( 223 if (!CheckedReadMemory(
152 section_address, sizeof(IMAGE_SECTION_HEADER), section)) { 224 section_address, sizeof(IMAGE_SECTION_HEADER), section)) {
153 LOG(WARNING) << "could not read section " << i << " of " << module_name_; 225 LOG(WARNING) << "could not read section " << i << " of " << module_name_;
154 return false; 226 return false;
(...skipping 18 matching lines...) Expand all
173 } 245 }
174 if (!module_range_.ContainsRange(read_range)) { 246 if (!module_range_.ContainsRange(read_range)) {
175 LOG(WARNING) << "attempt to read outside of module " << module_name_ 247 LOG(WARNING) << "attempt to read outside of module " << module_name_
176 << " at range: " << RangeToString(read_range); 248 << " at range: " << RangeToString(read_range);
177 return false; 249 return false;
178 } 250 }
179 return process_reader_->ReadMemory(address, size, into); 251 return process_reader_->ReadMemory(address, size, into);
180 } 252 }
181 253
182 } // namespace crashpad 254 } // namespace crashpad
OLDNEW
« no previous file with comments | « snapshot/win/pe_image_reader.h ('k') | snapshot/win/pe_image_reader_test.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698