OLD | NEW |
1 // Copyright 2014 The Crashpad Authors. All rights reserved. | 1 // Copyright 2014 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 "minidump/minidump_file_writer.h" | 15 #include "minidump/minidump_file_writer.h" |
16 | 16 |
17 #include <dbghelp.h> | 17 #include <dbghelp.h> |
18 | 18 |
19 #include <string> | 19 #include <string> |
20 | 20 |
21 #include "base/basictypes.h" | 21 #include "base/basictypes.h" |
22 #include "gtest/gtest.h" | 22 #include "gtest/gtest.h" |
23 #include "minidump/minidump_stream_writer.h" | 23 #include "minidump/minidump_stream_writer.h" |
| 24 #include "minidump/minidump_test_util.h" |
24 #include "minidump/minidump_writable.h" | 25 #include "minidump/minidump_writable.h" |
25 #include "util/file/file_writer.h" | 26 #include "util/file/file_writer.h" |
26 #include "util/file/string_file_writer.h" | 27 #include "util/file/string_file_writer.h" |
27 | 28 |
28 namespace { | 29 namespace { |
29 | 30 |
30 using namespace crashpad; | 31 using namespace crashpad; |
| 32 using namespace crashpad::test; |
31 | 33 |
32 TEST(MinidumpFileWriter, Empty) { | 34 TEST(MinidumpFileWriter, Empty) { |
33 MinidumpFileWriter minidump_file; | 35 MinidumpFileWriter minidump_file; |
34 StringFileWriter file_writer; | 36 StringFileWriter file_writer; |
35 ASSERT_TRUE(minidump_file.WriteEverything(&file_writer)); | 37 ASSERT_TRUE(minidump_file.WriteEverything(&file_writer)); |
36 ASSERT_EQ(sizeof(MINIDUMP_HEADER), file_writer.string().size()); | 38 ASSERT_EQ(sizeof(MINIDUMP_HEADER), file_writer.string().size()); |
37 | 39 |
38 const MINIDUMP_HEADER* header = | 40 const MINIDUMP_HEADER* header = |
39 reinterpret_cast<const MINIDUMP_HEADER*>(&file_writer.string()[0]); | 41 reinterpret_cast<const MINIDUMP_HEADER*>(&file_writer.string()[0]); |
40 | 42 |
41 EXPECT_EQ(static_cast<uint32_t>(MINIDUMP_SIGNATURE), header->Signature); | 43 VerifyMinidumpHeader(header, 0, 0); |
42 EXPECT_EQ(static_cast<uint32_t>(MINIDUMP_VERSION), header->Version); | 44 if (Test::HasFatalFailure()) { |
43 EXPECT_EQ(0u, header->NumberOfStreams); | 45 return; |
44 EXPECT_EQ(0u, header->StreamDirectoryRva); | 46 } |
45 EXPECT_EQ(0u, header->CheckSum); | |
46 EXPECT_EQ(0u, header->TimeDateStamp); | |
47 EXPECT_EQ(MiniDumpNormal, header->Flags); | |
48 } | 47 } |
49 | 48 |
50 class TestStream final : public internal::MinidumpStreamWriter { | 49 class TestStream final : public internal::MinidumpStreamWriter { |
51 public: | 50 public: |
52 TestStream(MinidumpStreamType stream_type, | 51 TestStream(MinidumpStreamType stream_type, |
53 size_t stream_size, | 52 size_t stream_size, |
54 uint8_t stream_value) | 53 uint8_t stream_value) |
55 : stream_data_(stream_size, stream_value), stream_type_(stream_type) {} | 54 : stream_data_(stream_size, stream_value), stream_type_(stream_type) {} |
56 | 55 |
57 ~TestStream() {} | 56 ~TestStream() {} |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
96 | 95 |
97 const size_t kDirectoryOffset = sizeof(MINIDUMP_HEADER); | 96 const size_t kDirectoryOffset = sizeof(MINIDUMP_HEADER); |
98 const size_t kStreamOffset = kDirectoryOffset + sizeof(MINIDUMP_DIRECTORY); | 97 const size_t kStreamOffset = kDirectoryOffset + sizeof(MINIDUMP_DIRECTORY); |
99 const size_t kFileSize = kStreamOffset + kStreamSize; | 98 const size_t kFileSize = kStreamOffset + kStreamSize; |
100 | 99 |
101 ASSERT_EQ(kFileSize, file_writer.string().size()); | 100 ASSERT_EQ(kFileSize, file_writer.string().size()); |
102 | 101 |
103 const MINIDUMP_HEADER* header = | 102 const MINIDUMP_HEADER* header = |
104 reinterpret_cast<const MINIDUMP_HEADER*>(&file_writer.string()[0]); | 103 reinterpret_cast<const MINIDUMP_HEADER*>(&file_writer.string()[0]); |
105 | 104 |
106 EXPECT_EQ(static_cast<uint32_t>(MINIDUMP_SIGNATURE), header->Signature); | 105 VerifyMinidumpHeader(header, 1, kTimestamp); |
107 EXPECT_EQ(static_cast<uint32_t>(MINIDUMP_VERSION), header->Version); | 106 if (Test::HasFatalFailure()) { |
108 EXPECT_EQ(1u, header->NumberOfStreams); | 107 return; |
109 EXPECT_EQ(kDirectoryOffset, header->StreamDirectoryRva); | 108 } |
110 EXPECT_EQ(0u, header->CheckSum); | |
111 EXPECT_EQ(kTimestamp, header->TimeDateStamp); | |
112 EXPECT_EQ(MiniDumpNormal, header->Flags); | |
113 | 109 |
114 const MINIDUMP_DIRECTORY* directory = | 110 const MINIDUMP_DIRECTORY* directory = |
115 reinterpret_cast<const MINIDUMP_DIRECTORY*>( | 111 reinterpret_cast<const MINIDUMP_DIRECTORY*>( |
116 &file_writer.string()[kDirectoryOffset]); | 112 &file_writer.string()[kDirectoryOffset]); |
117 | 113 |
118 EXPECT_EQ(kStreamType, directory->StreamType); | 114 EXPECT_EQ(kStreamType, directory->StreamType); |
119 EXPECT_EQ(kStreamSize, directory->Location.DataSize); | 115 EXPECT_EQ(kStreamSize, directory->Location.DataSize); |
120 EXPECT_EQ(kStreamOffset, directory->Location.Rva); | 116 EXPECT_EQ(kStreamOffset, directory->Location.Rva); |
121 | 117 |
122 const uint8_t* stream_data = | 118 const uint8_t* stream_data = |
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
162 const size_t kStream2Offset = kStream1Offset + kStream1Size + kStream2Padding; | 158 const size_t kStream2Offset = kStream1Offset + kStream1Size + kStream2Padding; |
163 const size_t kStream3Padding = 1; | 159 const size_t kStream3Padding = 1; |
164 const size_t kStream3Offset = kStream2Offset + kStream2Size + kStream3Padding; | 160 const size_t kStream3Offset = kStream2Offset + kStream2Size + kStream3Padding; |
165 const size_t kFileSize = kStream3Offset + kStream3Size; | 161 const size_t kFileSize = kStream3Offset + kStream3Size; |
166 | 162 |
167 ASSERT_EQ(kFileSize, file_writer.string().size()); | 163 ASSERT_EQ(kFileSize, file_writer.string().size()); |
168 | 164 |
169 const MINIDUMP_HEADER* header = | 165 const MINIDUMP_HEADER* header = |
170 reinterpret_cast<const MINIDUMP_HEADER*>(&file_writer.string()[0]); | 166 reinterpret_cast<const MINIDUMP_HEADER*>(&file_writer.string()[0]); |
171 | 167 |
172 EXPECT_EQ(static_cast<uint32_t>(MINIDUMP_SIGNATURE), header->Signature); | 168 VerifyMinidumpHeader(header, 3, kTimestamp); |
173 EXPECT_EQ(static_cast<uint32_t>(MINIDUMP_VERSION), header->Version); | 169 if (Test::HasFatalFailure()) { |
174 EXPECT_EQ(3u, header->NumberOfStreams); | 170 return; |
175 EXPECT_EQ(kDirectoryOffset, header->StreamDirectoryRva); | 171 } |
176 EXPECT_EQ(0u, header->CheckSum); | |
177 EXPECT_EQ(kTimestamp, header->TimeDateStamp); | |
178 EXPECT_EQ(MiniDumpNormal, header->Flags); | |
179 | 172 |
180 const MINIDUMP_DIRECTORY* directory = | 173 const MINIDUMP_DIRECTORY* directory = |
181 reinterpret_cast<const MINIDUMP_DIRECTORY*>( | 174 reinterpret_cast<const MINIDUMP_DIRECTORY*>( |
182 &file_writer.string()[kDirectoryOffset]); | 175 &file_writer.string()[kDirectoryOffset]); |
183 | 176 |
184 EXPECT_EQ(kStream1Type, directory[0].StreamType); | 177 EXPECT_EQ(kStream1Type, directory[0].StreamType); |
185 EXPECT_EQ(kStream1Size, directory[0].Location.DataSize); | 178 EXPECT_EQ(kStream1Size, directory[0].Location.DataSize); |
186 EXPECT_EQ(kStream1Offset, directory[0].Location.Rva); | 179 EXPECT_EQ(kStream1Offset, directory[0].Location.Rva); |
187 EXPECT_EQ(kStream2Type, directory[1].StreamType); | 180 EXPECT_EQ(kStream2Type, directory[1].StreamType); |
188 EXPECT_EQ(kStream2Size, directory[1].Location.DataSize); | 181 EXPECT_EQ(kStream2Size, directory[1].Location.DataSize); |
(...skipping 21 matching lines...) Expand all Loading... |
210 ASSERT_GE(sizeof(kZeroes), kStream3Padding); | 203 ASSERT_GE(sizeof(kZeroes), kStream3Padding); |
211 EXPECT_EQ(0, memcmp(stream2_data + kStream2Size, kZeroes, kStream3Padding)); | 204 EXPECT_EQ(0, memcmp(stream2_data + kStream2Size, kZeroes, kStream3Padding)); |
212 | 205 |
213 const uint8_t* stream3_data = | 206 const uint8_t* stream3_data = |
214 reinterpret_cast<const uint8_t*>(&file_writer.string()[kStream3Offset]); | 207 reinterpret_cast<const uint8_t*>(&file_writer.string()[kStream3Offset]); |
215 | 208 |
216 std::string expected_stream3(kStream3Size, kStream3Value); | 209 std::string expected_stream3(kStream3Size, kStream3Value); |
217 EXPECT_EQ(0, memcmp(stream3_data, expected_stream3.c_str(), kStream3Size)); | 210 EXPECT_EQ(0, memcmp(stream3_data, expected_stream3.c_str(), kStream3Size)); |
218 } | 211 } |
219 | 212 |
| 213 TEST(MinidumpFileWriter, ZeroLengthStream) { |
| 214 MinidumpFileWriter minidump_file; |
| 215 |
| 216 const size_t kStreamSize = 0; |
| 217 const MinidumpStreamType kStreamType = static_cast<MinidumpStreamType>(0x4d); |
| 218 TestStream stream(kStreamType, kStreamSize, 0); |
| 219 minidump_file.AddStream(&stream); |
| 220 |
| 221 StringFileWriter file_writer; |
| 222 ASSERT_TRUE(minidump_file.WriteEverything(&file_writer)); |
| 223 |
| 224 const size_t kDirectoryOffset = sizeof(MINIDUMP_HEADER); |
| 225 const size_t kStreamOffset = kDirectoryOffset + sizeof(MINIDUMP_DIRECTORY); |
| 226 const size_t kFileSize = kStreamOffset + kStreamSize; |
| 227 |
| 228 ASSERT_EQ(kFileSize, file_writer.string().size()); |
| 229 |
| 230 const MINIDUMP_HEADER* header = |
| 231 reinterpret_cast<const MINIDUMP_HEADER*>(&file_writer.string()[0]); |
| 232 |
| 233 VerifyMinidumpHeader(header, 1, 0); |
| 234 if (Test::HasFatalFailure()) { |
| 235 return; |
| 236 } |
| 237 |
| 238 const MINIDUMP_DIRECTORY* directory = |
| 239 reinterpret_cast<const MINIDUMP_DIRECTORY*>( |
| 240 &file_writer.string()[kDirectoryOffset]); |
| 241 |
| 242 EXPECT_EQ(kStreamType, directory->StreamType); |
| 243 EXPECT_EQ(kStreamSize, directory->Location.DataSize); |
| 244 EXPECT_EQ(kStreamOffset, directory->Location.Rva); |
| 245 } |
| 246 |
220 TEST(MinidumpFileWriterDeathTest, SameStreamType) { | 247 TEST(MinidumpFileWriterDeathTest, SameStreamType) { |
221 MinidumpFileWriter minidump_file; | 248 MinidumpFileWriter minidump_file; |
222 | 249 |
223 const size_t kStream1Size = 5; | 250 const size_t kStream1Size = 5; |
224 const MinidumpStreamType kStream1Type = static_cast<MinidumpStreamType>(0x4d); | 251 const MinidumpStreamType kStream1Type = static_cast<MinidumpStreamType>(0x4d); |
225 const uint8_t kStream1Value = 0x5a; | 252 const uint8_t kStream1Value = 0x5a; |
226 TestStream stream1(kStream1Type, kStream1Size, kStream1Value); | 253 TestStream stream1(kStream1Type, kStream1Size, kStream1Value); |
227 minidump_file.AddStream(&stream1); | 254 minidump_file.AddStream(&stream1); |
228 | 255 |
229 // It is an error to add a second stream of the same type. | 256 // It is an error to add a second stream of the same type. |
230 const size_t kStream2Size = 3; | 257 const size_t kStream2Size = 3; |
231 const MinidumpStreamType kStream2Type = static_cast<MinidumpStreamType>(0x4d); | 258 const MinidumpStreamType kStream2Type = static_cast<MinidumpStreamType>(0x4d); |
232 const uint8_t kStream2Value = 0xa5; | 259 const uint8_t kStream2Value = 0xa5; |
233 TestStream stream2(kStream2Type, kStream2Size, kStream2Value); | 260 TestStream stream2(kStream2Type, kStream2Size, kStream2Value); |
234 ASSERT_DEATH(minidump_file.AddStream(&stream2), "already present"); | 261 ASSERT_DEATH(minidump_file.AddStream(&stream2), "already present"); |
235 } | 262 } |
236 | 263 |
237 } // namespace | 264 } // namespace |
OLD | NEW |