1 : // Copyright 2012 Google Inc. All Rights Reserved.
2 : //
3 : // Licensed under the Apache License, Version 2.0 (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
6 : //
7 : // http://www.apache.org/licenses/LICENSE-2.0
8 : //
9 : // Unless required by applicable law or agreed to in writing, software
10 : // distributed under the License is distributed on an "AS IS" BASIS,
11 : // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 : // See the License for the specific language governing permissions and
13 : // limitations under the License.
14 :
15 : #include "syzygy/playback/playback.h"
16 :
17 : #include <string>
18 :
19 : #include "gmock/gmock.h"
20 : #include "gtest/gtest.h"
21 : #include "syzygy/common/syzygy_version.h"
22 : #include "syzygy/core/unittest_util.h"
23 : #include "syzygy/pdb/omap.h"
24 : #include "syzygy/pe/pe_file.h"
25 : #include "syzygy/pe/unittest_util.h"
26 : #include "syzygy/trace/parse/unittest_util.h"
27 :
28 : namespace playback {
29 :
30 : namespace {
31 :
32 : using testing::_;
33 : using testing::GetSrcRelativePath;
34 : using testing::GetExeRelativePath;
35 : using testing::GetExeTestDataRelativePath;
36 : using testing::MockParseEventHandler;
37 : using testing::Return;
38 :
39 : class PlaybackTest : public testing::PELibUnitTest {
40 : public:
41 E : PlaybackTest() : image_layout_(&block_graph_) {
42 E : }
43 :
44 E : void SetUp() {
45 : module_path_ =
46 E : GetExeTestDataRelativePath(testing::kTestDllName);
47 :
48 : instrumented_path_ =
49 E : GetExeTestDataRelativePath(testing::kCallTraceInstrumentedTestDllName);
50 :
51 : const base::FilePath kTraceFiles[] = {
52 E : GetExeTestDataRelativePath(testing::kCallTraceTraceFiles[0]),
53 E : GetExeTestDataRelativePath(testing::kCallTraceTraceFiles[1]),
54 E : GetExeTestDataRelativePath(testing::kCallTraceTraceFiles[2]),
55 E : GetExeTestDataRelativePath(testing::kCallTraceTraceFiles[3]),
56 : };
57 : trace_files_ = Playback::TraceFileList(kTraceFiles,
58 E : kTraceFiles + arraysize(kTraceFiles));
59 E : }
60 :
61 E : bool Init() {
62 : playback_.reset(
63 E : new Playback(module_path_, instrumented_path_, trace_files_));
64 :
65 E : parse_event_handler_.reset(new MockParseEventHandler);
66 E : parser_.reset(new Playback::Parser);
67 E : return parser_->Init(parse_event_handler_.get());
68 E : }
69 :
70 : protected:
71 : scoped_ptr<Playback> playback_;
72 :
73 : base::FilePath module_path_;
74 : base::FilePath instrumented_path_;
75 : Playback::TraceFileList trace_files_;
76 :
77 : pe::PEFile input_dll_;
78 : block_graph::BlockGraph block_graph_;
79 : pe::ImageLayout image_layout_;
80 :
81 : scoped_ptr<MockParseEventHandler> parse_event_handler_;
82 : scoped_ptr<Playback::Parser> parser_;
83 : };
84 :
85 : } // namespace
86 :
87 E : TEST_F(PlaybackTest, MismatchedDLLTest) {
88 E : module_path_ = GetExeTestDataRelativePath(L"randomized_test_dll.dll");
89 :
90 E : EXPECT_TRUE(Init());
91 E : EXPECT_FALSE(playback_->Init(&input_dll_, &image_layout_, parser_.get()));
92 E : }
93 :
94 E : TEST_F(PlaybackTest, BadTraceFile) {
95 : const base::FilePath kTraceFile = GetSrcRelativePath(
96 E : L"syzygy/playback/test_data/bad-trace.bin");
97 E : trace_files_ = Playback::TraceFileList(&kTraceFile, &kTraceFile + 1);
98 :
99 E : EXPECT_TRUE(Init());
100 E : EXPECT_FALSE(playback_->Init(&input_dll_, &image_layout_, parser_.get()));
101 E : }
102 :
103 E : TEST_F(PlaybackTest, SuccessfulInit) {
104 E : EXPECT_TRUE(Init());
105 E : EXPECT_TRUE(playback_->Init(&input_dll_, &image_layout_, parser_.get()));
106 E : }
107 :
108 E : TEST_F(PlaybackTest, ConsumeCallTraceEvents) {
109 E : EXPECT_TRUE(Init());
110 E : EXPECT_TRUE(playback_->Init(&input_dll_, &image_layout_, parser_.get()));
111 :
112 : #ifdef OFFICIAL_BUILD
113 : static const size_t kProcessAttachCount = 4;
114 : static const size_t kBatchFunctionEntryCount = 4;
115 : #else
116 : static const size_t kProcessAttachCount = 12;
117 : static const size_t kBatchFunctionEntryCount = 12;
118 : #endif
119 :
120 E : EXPECT_CALL(*parse_event_handler_, OnProcessStarted(_, _, _)).Times(4);
121 E : EXPECT_CALL(*parse_event_handler_, OnProcessEnded(_, _)).Times(4);
122 E : EXPECT_CALL(*parse_event_handler_, OnFunctionEntry(_, _, _, _)).Times(0);
123 E : EXPECT_CALL(*parse_event_handler_, OnFunctionExit(_, _, _, _)).Times(0);
124 : EXPECT_CALL(*parse_event_handler_, OnBatchFunctionEntry(_, _, _, _)).
125 E : Times(kBatchFunctionEntryCount);
126 : EXPECT_CALL(*parse_event_handler_, OnProcessAttach(_, _, _, _)).
127 E : Times(kProcessAttachCount);
128 E : EXPECT_CALL(*parse_event_handler_, OnThreadAttach(_, _, _, _)).Times(0);
129 E : EXPECT_CALL(*parse_event_handler_, OnThreadDetach(_, _, _, _)).Times(0);
130 : EXPECT_CALL(*parse_event_handler_,
131 E : OnInvocationBatch(_, _, _, _, _)).Times(0);
132 :
133 E : EXPECT_TRUE(parser_->Consume());
134 E : }
135 :
136 : } // namespace playback
|