Index: experimental/visual_studio_plugin/third_party/breakpad/common/module_unittest.cc |
diff --git a/experimental/visual_studio_plugin/third_party/breakpad/common/module_unittest.cc b/experimental/visual_studio_plugin/third_party/breakpad/common/module_unittest.cc |
deleted file mode 100644 |
index 079034113119de30e01e037a3753c55e690a1543..0000000000000000000000000000000000000000 |
--- a/experimental/visual_studio_plugin/third_party/breakpad/common/module_unittest.cc |
+++ /dev/null |
@@ -1,396 +0,0 @@ |
-// Copyright (c) 2010 Google Inc. |
-// All rights reserved. |
-// |
-// Redistribution and use in source and binary forms, with or without |
-// modification, are permitted provided that the following conditions are |
-// met: |
-// |
-// * Redistributions of source code must retain the above copyright |
-// notice, this list of conditions and the following disclaimer. |
-// * Redistributions in binary form must reproduce the above |
-// copyright notice, this list of conditions and the following disclaimer |
-// in the documentation and/or other materials provided with the |
-// distribution. |
-// * Neither the name of Google Inc. nor the names of its |
-// contributors may be used to endorse or promote products derived from |
-// this software without specific prior written permission. |
-// |
-// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS |
-// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT |
-// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR |
-// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT |
-// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, |
-// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT |
-// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |
-// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
-// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
-// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
-// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
- |
-// Original author: Jim Blandy <jimb@mozilla.com> <jimb@red-bean.com> |
- |
-// module_unittest.cc: Unit tests for google_breakpad::Module. |
- |
-#include <cerrno> |
-#include <cstdio> |
-#include <cstdlib> |
-#include <cstring> |
- |
-#include <algorithm> |
-#include <string> |
- |
-#include "breakpad_googletest_includes.h" |
-#include "common/module.h" |
- |
-using google_breakpad::Module; |
-using std::string; |
-using std::vector; |
-using testing::ContainerEq; |
- |
-// Return a FILE * referring to a temporary file that will be deleted |
-// automatically when the stream is closed or the program exits. |
-FILE *checked_tmpfile() { |
- FILE *f = tmpfile(); |
- if (!f) { |
- fprintf(stderr, "error creating temporary file: %s\n", strerror(errno)); |
- exit(1); |
- } |
- return f; |
-} |
- |
-// Read from STREAM until end of file, and return the contents as a |
-// string. |
-string checked_read(FILE *stream) { |
- string contents; |
- int c; |
- while ((c = getc(stream)) != EOF) |
- contents.push_back(c); |
- if (ferror(stream)) { |
- fprintf(stderr, "error reading temporary file contents: %s\n", |
- strerror(errno)); |
- exit(1); |
- } |
- return contents; |
-} |
- |
-// Apply 'fflush' to STREAM, and check for errors. |
-void checked_fflush(FILE *stream) { |
- if (fflush(stream) == EOF) { |
- fprintf(stderr, "error flushing temporary file stream: %s\n", |
- strerror(errno)); |
- exit(1); |
- } |
-} |
- |
-// Apply 'fclose' to STREAM, and check for errors. |
-void checked_fclose(FILE *stream) { |
- if (fclose(stream) == EOF) { |
- fprintf(stderr, "error closing temporary file stream: %s\n", |
- strerror(errno)); |
- exit(1); |
- } |
-} |
- |
-#define MODULE_NAME "name with spaces" |
-#define MODULE_OS "os-name" |
-#define MODULE_ARCH "architecture" |
-#define MODULE_ID "id-string" |
- |
-TEST(Write, Header) { |
- FILE *f = checked_tmpfile(); |
- Module m(MODULE_NAME, MODULE_OS, MODULE_ARCH, MODULE_ID); |
- m.Write(f); |
- checked_fflush(f); |
- rewind(f); |
- string contents = checked_read(f); |
- checked_fclose(f); |
- EXPECT_STREQ("MODULE os-name architecture id-string name with spaces\n", |
- contents.c_str()); |
-} |
- |
-TEST(Write, OneLineFunc) { |
- FILE *f = checked_tmpfile(); |
- Module m(MODULE_NAME, MODULE_OS, MODULE_ARCH, MODULE_ID); |
- |
- Module::File *file = m.FindFile("file_name.cc"); |
- Module::Function *function = new(Module::Function); |
- function->name = "function_name"; |
- function->address = 0xe165bf8023b9d9abLL; |
- function->size = 0x1e4bb0eb1cbf5b09LL; |
- function->parameter_size = 0x772beee89114358aLL; |
- Module::Line line = { 0xe165bf8023b9d9abLL, 0x1e4bb0eb1cbf5b09LL, |
- file, 67519080 }; |
- function->lines.push_back(line); |
- m.AddFunction(function); |
- |
- m.Write(f); |
- checked_fflush(f); |
- rewind(f); |
- string contents = checked_read(f); |
- checked_fclose(f); |
- EXPECT_STREQ("MODULE os-name architecture id-string name with spaces\n" |
- "FILE 0 file_name.cc\n" |
- "FUNC e165bf8023b9d9ab 1e4bb0eb1cbf5b09 772beee89114358a" |
- " function_name\n" |
- "e165bf8023b9d9ab 1e4bb0eb1cbf5b09 67519080 0\n", |
- contents.c_str()); |
-} |
- |
-TEST(Write, RelativeLoadAddress) { |
- FILE *f = checked_tmpfile(); |
- Module m(MODULE_NAME, MODULE_OS, MODULE_ARCH, MODULE_ID); |
- |
- m.SetLoadAddress(0x2ab698b0b6407073LL); |
- |
- // Some source files. We will expect to see them in lexicographic order. |
- Module::File *file1 = m.FindFile("filename-b.cc"); |
- Module::File *file2 = m.FindFile("filename-a.cc"); |
- |
- // A function. |
- Module::Function *function = new(Module::Function); |
- function->name = "A_FLIBBERTIJIBBET::a_will_o_the_wisp(a clown)"; |
- function->address = 0xbec774ea5dd935f3LL; |
- function->size = 0x2922088f98d3f6fcLL; |
- function->parameter_size = 0xe5e9aa008bd5f0d0LL; |
- |
- // Some source lines. The module should not sort these. |
- Module::Line line1 = { 0xbec774ea5dd935f3LL, 0x1c2be6d6c5af2611LL, |
- file1, 41676901 }; |
- Module::Line line2 = { 0xdaf35bc123885c04LL, 0xcf621b8d324d0ebLL, |
- file2, 67519080 }; |
- function->lines.push_back(line2); |
- function->lines.push_back(line1); |
- |
- m.AddFunction(function); |
- |
- // Some stack information. |
- Module::StackFrameEntry *entry = new Module::StackFrameEntry(); |
- entry->address = 0x30f9e5c83323973dULL; |
- entry->size = 0x49fc9ca7c7c13dc2ULL; |
- entry->initial_rules[".cfa"] = "he was a handsome man"; |
- entry->initial_rules["and"] = "what i want to know is"; |
- entry->rule_changes[0x30f9e5c83323973eULL]["how"] = |
- "do you like your blueeyed boy"; |
- entry->rule_changes[0x30f9e5c83323973eULL]["Mister"] = "Death"; |
- m.AddStackFrameEntry(entry); |
- |
- m.Write(f); |
- checked_fflush(f); |
- rewind(f); |
- string contents = checked_read(f); |
- checked_fclose(f); |
- EXPECT_STREQ("MODULE os-name architecture id-string name with spaces\n" |
- "FILE 0 filename-a.cc\n" |
- "FILE 1 filename-b.cc\n" |
- "FUNC 9410dc39a798c580 2922088f98d3f6fc e5e9aa008bd5f0d0" |
- " A_FLIBBERTIJIBBET::a_will_o_the_wisp(a clown)\n" |
- "b03cc3106d47eb91 cf621b8d324d0eb 67519080 0\n" |
- "9410dc39a798c580 1c2be6d6c5af2611 41676901 1\n" |
- "STACK CFI INIT 6434d177ce326ca 49fc9ca7c7c13dc2" |
- " .cfa: he was a handsome man" |
- " and: what i want to know is\n" |
- "STACK CFI 6434d177ce326cb" |
- " Mister: Death" |
- " how: do you like your blueeyed boy\n", |
- contents.c_str()); |
-} |
- |
-TEST(Write, OmitUnusedFiles) { |
- Module m(MODULE_NAME, MODULE_OS, MODULE_ARCH, MODULE_ID); |
- |
- // Create some source files. |
- Module::File *file1 = m.FindFile("filename1"); |
- m.FindFile("filename2"); // not used by any line |
- Module::File *file3 = m.FindFile("filename3"); |
- |
- // Create a function. |
- Module::Function *function = new(Module::Function); |
- function->name = "function_name"; |
- function->address = 0x9b926d464f0b9384LL; |
- function->size = 0x4f524a4ba795e6a6LL; |
- function->parameter_size = 0xbbe8133a6641c9b7LL; |
- |
- // Source files that refer to some files, but not others. |
- Module::Line line1 = { 0x595fa44ebacc1086LL, 0x1e1e0191b066c5b3LL, |
- file1, 137850127 }; |
- Module::Line line2 = { 0x401ce8c8a12d25e3LL, 0x895751c41b8d2ce2LL, |
- file3, 28113549 }; |
- function->lines.push_back(line1); |
- function->lines.push_back(line2); |
- m.AddFunction(function); |
- |
- m.AssignSourceIds(); |
- |
- vector<Module::File *> vec; |
- m.GetFiles(&vec); |
- EXPECT_EQ((size_t) 3, vec.size()); |
- EXPECT_STREQ("filename1", vec[0]->name.c_str()); |
- EXPECT_NE(-1, vec[0]->source_id); |
- // Expect filename2 not to be used. |
- EXPECT_STREQ("filename2", vec[1]->name.c_str()); |
- EXPECT_EQ(-1, vec[1]->source_id); |
- EXPECT_STREQ("filename3", vec[2]->name.c_str()); |
- EXPECT_NE(-1, vec[2]->source_id); |
- |
- FILE *f = checked_tmpfile(); |
- m.Write(f); |
- checked_fflush(f); |
- rewind(f); |
- string contents = checked_read(f); |
- checked_fclose(f); |
- EXPECT_STREQ("MODULE os-name architecture id-string name with spaces\n" |
- "FILE 0 filename1\n" |
- "FILE 1 filename3\n" |
- "FUNC 9b926d464f0b9384 4f524a4ba795e6a6 bbe8133a6641c9b7" |
- " function_name\n" |
- "595fa44ebacc1086 1e1e0191b066c5b3 137850127 0\n" |
- "401ce8c8a12d25e3 895751c41b8d2ce2 28113549 1\n", |
- contents.c_str()); |
-} |
- |
-TEST(Construct, AddFunctions) { |
- FILE *f = checked_tmpfile(); |
- Module m(MODULE_NAME, MODULE_OS, MODULE_ARCH, MODULE_ID); |
- |
- // Two functions. |
- Module::Function *function1 = new(Module::Function); |
- function1->name = "_without_form"; |
- function1->address = 0xd35024aa7ca7da5cLL; |
- function1->size = 0x200b26e605f99071LL; |
- function1->parameter_size = 0xf14ac4fed48c4a99LL; |
- |
- Module::Function *function2 = new(Module::Function); |
- function2->name = "_and_void"; |
- function2->address = 0x2987743d0b35b13fLL; |
- function2->size = 0xb369db048deb3010LL; |
- function2->parameter_size = 0x938e556cb5a79988LL; |
- |
- // Put them in a vector. |
- vector<Module::Function *> vec; |
- vec.push_back(function1); |
- vec.push_back(function2); |
- |
- m.AddFunctions(vec.begin(), vec.end()); |
- |
- m.Write(f); |
- checked_fflush(f); |
- rewind(f); |
- string contents = checked_read(f); |
- checked_fclose(f); |
- EXPECT_STREQ("MODULE os-name architecture id-string name with spaces\n" |
- "FUNC d35024aa7ca7da5c 200b26e605f99071 f14ac4fed48c4a99" |
- " _without_form\n" |
- "FUNC 2987743d0b35b13f b369db048deb3010 938e556cb5a79988" |
- " _and_void\n", |
- contents.c_str()); |
- |
- // Check that m.GetFunctions returns the functions we expect. |
- vec.clear(); |
- m.GetFunctions(&vec, vec.end()); |
- EXPECT_TRUE(vec.end() != find(vec.begin(), vec.end(), function1)); |
- EXPECT_TRUE(vec.end() != find(vec.begin(), vec.end(), function2)); |
- EXPECT_EQ((size_t) 2, vec.size()); |
-} |
- |
-TEST(Construct, AddFrames) { |
- FILE *f = checked_tmpfile(); |
- Module m(MODULE_NAME, MODULE_OS, MODULE_ARCH, MODULE_ID); |
- |
- // First STACK CFI entry, with no initial rules or deltas. |
- Module::StackFrameEntry *entry1 = new Module::StackFrameEntry(); |
- entry1->address = 0xddb5f41285aa7757ULL; |
- entry1->size = 0x1486493370dc5073ULL; |
- m.AddStackFrameEntry(entry1); |
- |
- // Second STACK CFI entry, with initial rules but no deltas. |
- Module::StackFrameEntry *entry2 = new Module::StackFrameEntry(); |
- entry2->address = 0x8064f3af5e067e38ULL; |
- entry2->size = 0x0de2a5ee55509407ULL; |
- entry2->initial_rules[".cfa"] = "I think that I shall never see"; |
- entry2->initial_rules["stromboli"] = "a poem lovely as a tree"; |
- entry2->initial_rules["cannoli"] = "a tree whose hungry mouth is prest"; |
- m.AddStackFrameEntry(entry2); |
- |
- // Third STACK CFI entry, with initial rules and deltas. |
- Module::StackFrameEntry *entry3 = new Module::StackFrameEntry(); |
- entry3->address = 0x5e8d0db0a7075c6cULL; |
- entry3->size = 0x1c7edb12a7aea229ULL; |
- entry3->initial_rules[".cfa"] = "Whose woods are these"; |
- entry3->rule_changes[0x47ceb0f63c269d7fULL]["calzone"] = |
- "the village though"; |
- entry3->rule_changes[0x47ceb0f63c269d7fULL]["cannoli"] = |
- "he will not see me stopping here"; |
- entry3->rule_changes[0x36682fad3763ffffULL]["stromboli"] = |
- "his house is in"; |
- entry3->rule_changes[0x36682fad3763ffffULL][".cfa"] = |
- "I think I know"; |
- m.AddStackFrameEntry(entry3); |
- |
- // Check that Write writes STACK CFI records properly. |
- m.Write(f); |
- checked_fflush(f); |
- rewind(f); |
- string contents = checked_read(f); |
- checked_fclose(f); |
- EXPECT_STREQ("MODULE os-name architecture id-string name with spaces\n" |
- "STACK CFI INIT ddb5f41285aa7757 1486493370dc5073 \n" |
- "STACK CFI INIT 8064f3af5e067e38 de2a5ee55509407" |
- " .cfa: I think that I shall never see" |
- " cannoli: a tree whose hungry mouth is prest" |
- " stromboli: a poem lovely as a tree\n" |
- "STACK CFI INIT 5e8d0db0a7075c6c 1c7edb12a7aea229" |
- " .cfa: Whose woods are these\n" |
- "STACK CFI 36682fad3763ffff" |
- " .cfa: I think I know" |
- " stromboli: his house is in\n" |
- "STACK CFI 47ceb0f63c269d7f" |
- " calzone: the village though" |
- " cannoli: he will not see me stopping here\n", |
- contents.c_str()); |
- |
- // Check that GetStackFrameEntries works. |
- vector<Module::StackFrameEntry *> entries; |
- m.GetStackFrameEntries(&entries); |
- ASSERT_EQ(3U, entries.size()); |
- // Check first entry. |
- EXPECT_EQ(0xddb5f41285aa7757ULL, entries[0]->address); |
- EXPECT_EQ(0x1486493370dc5073ULL, entries[0]->size); |
- ASSERT_EQ(0U, entries[0]->initial_rules.size()); |
- ASSERT_EQ(0U, entries[0]->rule_changes.size()); |
- // Check second entry. |
- EXPECT_EQ(0x8064f3af5e067e38ULL, entries[1]->address); |
- EXPECT_EQ(0x0de2a5ee55509407ULL, entries[1]->size); |
- ASSERT_EQ(3U, entries[1]->initial_rules.size()); |
- Module::RuleMap entry2_initial; |
- entry2_initial[".cfa"] = "I think that I shall never see"; |
- entry2_initial["stromboli"] = "a poem lovely as a tree"; |
- entry2_initial["cannoli"] = "a tree whose hungry mouth is prest"; |
- EXPECT_THAT(entries[1]->initial_rules, ContainerEq(entry2_initial)); |
- ASSERT_EQ(0U, entries[1]->rule_changes.size()); |
- // Check third entry. |
- EXPECT_EQ(0x5e8d0db0a7075c6cULL, entries[2]->address); |
- EXPECT_EQ(0x1c7edb12a7aea229ULL, entries[2]->size); |
- Module::RuleMap entry3_initial; |
- entry3_initial[".cfa"] = "Whose woods are these"; |
- EXPECT_THAT(entries[2]->initial_rules, ContainerEq(entry3_initial)); |
- Module::RuleChangeMap entry3_changes; |
- entry3_changes[0x36682fad3763ffffULL][".cfa"] = "I think I know"; |
- entry3_changes[0x36682fad3763ffffULL]["stromboli"] = "his house is in"; |
- entry3_changes[0x47ceb0f63c269d7fULL]["calzone"] = "the village though"; |
- entry3_changes[0x47ceb0f63c269d7fULL]["cannoli"] = |
- "he will not see me stopping here"; |
- EXPECT_THAT(entries[2]->rule_changes, ContainerEq(entry3_changes)); |
-} |
- |
-TEST(Construct, UniqueFiles) { |
- Module m(MODULE_NAME, MODULE_OS, MODULE_ARCH, MODULE_ID); |
- Module::File *file1 = m.FindFile("foo"); |
- Module::File *file2 = m.FindFile(string("bar")); |
- Module::File *file3 = m.FindFile(string("foo")); |
- Module::File *file4 = m.FindFile("bar"); |
- EXPECT_NE(file1, file2); |
- EXPECT_EQ(file1, file3); |
- EXPECT_EQ(file2, file4); |
- EXPECT_EQ(file1, m.FindExistingFile("foo")); |
- EXPECT_TRUE(m.FindExistingFile("baz") == NULL); |
-} |