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 : // Call trace event parsing classes.
16 :
17 : #ifndef SYZYGY_TRACE_PARSE_PARSE_ENGINE_H_
18 : #define SYZYGY_TRACE_PARSE_PARSE_ENGINE_H_
19 :
20 : #include <map>
21 : #include <set>
22 : #include <string>
23 :
24 : #include "syzygy/pe/pe_file.h"
25 : #include "syzygy/trace/parse/parser.h"
26 :
27 m : namespace trace {
28 m : namespace parser {
29 :
30 : // This base class defines and implements the common event dispatching and
31 : // module tracking for all supported parse engines. It also declares the
32 : // abstract interface a parse engine exposes to its clients.
33 m : class ParseEngine {
34 m : public:
35 m : virtual ~ParseEngine();
36 :
37 : // Returns a short human readable name by which this parse engine can be
38 : // recognized.
39 m : const char* name() const;
40 :
41 : // Returns true if an error occurred while parsing the trace files.
42 m : bool error_occurred() const;
43 :
44 : // Set or reset the error flag.
45 m : void set_error_occurred(bool value);
46 :
47 : // Registers an event handler with this trace-file parse engine.
48 m : void set_event_handler(ParseEventHandler* event_handler);
49 :
50 : // Returns true if the file given by @p trace_file_path is parseable by this
51 : // parse engine.
52 m : virtual bool IsRecognizedTraceFile(const base::FilePath& trace_file_path) = 0;
53 :
54 : // Opens the trace log given by @p trace_file_path and prepares it for
55 : // consumption. It is an error to call this method given a file that
56 : // will not be recognized by the parse engine.
57 : //
58 : // @return true on success.
59 m : virtual bool OpenTraceFile(const base::FilePath& trace_file_path) = 0;
60 :
61 : // Consume all events across all currently open trace files and for each
62 : // event call the dispatcher to notify the event handler.
63 : //
64 : // @return true on success.
65 m : virtual bool ConsumeAllEvents() = 0;
66 :
67 : // Close all currently open trace files.
68 : //
69 : // @return true on success.
70 m : virtual bool CloseAllTraceFiles() = 0;
71 :
72 : // Given an address and a process id, returns the module in memory at that
73 : // address.
74 : //
75 : // @param process_id The id of the process to look up.
76 : // @param addr An address in the memory space of the process.
77 : //
78 : // @return NULL if no such module exists; otherwise, a pointer to the module.
79 m : const ModuleInformation* GetModuleInformation(uint32 process_id,
80 m : AbsoluteAddress64 addr) const;
81 :
82 m : protected:
83 : // Used to store module information about each observed process.
84 m : typedef std::map<uint32, ModuleSpace> ProcessMap;
85 :
86 : // Initialize the base ParseEngine.
87 : //
88 : // @param name The name of this parse engine. This will be logged.
89 : // @param fail_on_module_conflict A flag denoting whether to abort on
90 : // conflicting module information. In ETW traces, for example, we
91 : // sometimes get conflicting module information if background
92 : // processes are actively coming and going. In RPC traces, we should
93 : // never get conflicting module information.
94 m : ParseEngine(const char* const name, bool fail_on_module_conflict);
95 :
96 : // Registers a module in the address space of the process denoted by
97 : // @p process_id.
98 : //
99 : // @param process_id The process in which the module has been loaded.
100 : // @param module_info The meta-data describing the loaded module.
101 : //
102 : // @return true on success.
103 m : bool AddModuleInformation(DWORD process_id,
104 m : const ModuleInformation& module_info);
105 :
106 : // Unregisters a module from the address space of the process denoted by
107 : // @p process_id.
108 : //
109 : // @param process_id The process in which the module has been unloaded.
110 : // @param module_info The meta-data describing the loaded module.
111 : //
112 : // @return true on success.
113 m : bool RemoveModuleInformation(DWORD process_id,
114 m : const ModuleInformation& module_info);
115 :
116 : // Unregisters a process (and all of the modules it contains) from the
117 : // process map.
118 : //
119 : // @param process_id The process which has been unloaded.
120 : // @return true on success.
121 m : bool RemoveProcessInformation(DWORD process_id);
122 :
123 : // The main entry point by which trace events are dispatched to the
124 : // event handler.
125 : //
126 : // @param event The event to dispatch.
127 : //
128 : // @return true if the event was recognized and handled in some way; false
129 : // if the event must be handled elsewhere. If an error occurs during
130 : // the handling of the event, the error_occurred_ flag will be set to
131 : // true.
132 m : bool DispatchEvent(EVENT_TRACE* event);
133 :
134 : // Parses and dispatches function entry and exit events. Called from
135 : // DispatchEvent().
136 : //
137 : // @param event The event to dispatch.
138 : // @param type TRACE_ENTER_EVENT or TRACE_EXIT_EVENT
139 : //
140 : // @return true if the event was successfully dispatched, false otherwise.
141 : // If an error occurred, the error_occurred_ flag will be set to
142 : // true.
143 m : bool DispatchEntryExitEvent(EVENT_TRACE* event, TraceEventType type);
144 :
145 : // Parses and dispatches batch function entry events. Called from
146 : // DispatchEvent().
147 : //
148 : // @param event The event to dispatch.
149 : //
150 : // @return true if the event was successfully dispatched, false otherwise.
151 : // If an error occurred, the error_occurred_ flag will be set to
152 : // true.
153 m : bool DispatchBatchEnterEvent(EVENT_TRACE* event);
154 :
155 : // Parses and dispatches a process ended event. Called from DispatchEvent().
156 : //
157 : // @param event The event to dispatch.
158 : //
159 : // @return true if the event was successfully dispatched, false otherwise.
160 : // If an error occurred the error_occurred_ flag will be set to true.
161 m : bool DispatchProcessEndedEvent(EVENT_TRACE* event);
162 :
163 : // Parses and dispatches invocation batch function events. Called from
164 : // DispatchEvent().
165 : //
166 : // @param event The event to dispatch.
167 : //
168 : // @return true if the event was successfully dispatched, false otherwise.
169 : // If an error occurred, the error_occurred_ flag will be set to
170 : // true.
171 m : bool DispatchBatchInvocationEvent(EVENT_TRACE* event);
172 :
173 : // Parses and dispatches dynamic library events (i.e., process and thread
174 : // attach/detach events). Called from DispatchEvent().
175 : //
176 : // @param event The event to dispatch.
177 : // @param type One of TRACE_PROCESS_ATTACH_EVENT, TRACE_PROCESS_DETACH_EVENT,
178 : // TRACE_THREAD_ATTACH_EVENT, or TRACE_THREAD_DETACH_EVENT.
179 : //
180 : // @return true if the event was successfully dispatched, false otherwise.
181 : // If an error occurred, the error_occurred_ flag will be set to
182 : // true.
183 m : bool DispatchModuleEvent(EVENT_TRACE* event, TraceEventType type);
184 :
185 : // Parses and dispatches thread name events. Called from DispatchEvent().
186 : //
187 : // @param event The event to dispatch.
188 : //
189 : // @return true if the event was successfully dispatched, false otherwise.
190 : // If an error occurred, the error_occurred_ flag will be set to
191 : // true.
192 m : bool DispatchThreadNameEvent(EVENT_TRACE* event);
193 :
194 : // Parses and dispatches indexed frequency events.
195 : //
196 : // @param event the event to dispatch.
197 : //
198 : // @return true if the event was successfully dispatched, false otherwise.
199 : // Does not explicitly set error occurred.
200 m : bool DispatchIndexedFrequencyEvent(EVENT_TRACE* event);
201 :
202 : // Parses and dispatches dynamic module events.
203 : //
204 : // @param event the event to dispatch.
205 : //
206 : // @return true if the event was successfully dispatched, false otherwise.
207 : // Does not explicitly set error occurred.
208 m : bool DispatchDynamicSymbolEvent(EVENT_TRACE* event);
209 :
210 : // Parses and dispatches sampling profiler data.
211 : //
212 : // @param event the event to dispatch.
213 : //
214 : // @return true if the event was successfully dispatched, false otherwise.
215 : // Does not explicitly set error occurred.
216 m : bool DispatchSampleDataEvent(EVENT_TRACE* event);
217 :
218 : // The name by which this parse engine is known.
219 m : std::string name_;
220 :
221 : // The event handler to be notified on trace events.
222 m : ParseEventHandler* event_handler_;
223 :
224 : // For each process, we store its point of view of the world.
225 m : ProcessMap processes_;
226 :
227 : // Flag indicating whether or not an error has occurred in parsing the trace
228 : // event stream.
229 m : bool error_occurred_;
230 :
231 : // A flag denoting whether to abort on conflicting module information. In
232 : // ETW traces, we sometimes get conflicting module information if background
233 : // processes are actively coming a going. In RPC traces, we should never get
234 : // conflicting module information.
235 m : bool fail_on_module_conflict_;
236 :
237 m : private:
238 m : DISALLOW_COPY_AND_ASSIGN(ParseEngine);
239 m : };
240 :
241 m : } // namespace parser
242 m : } // namespace trace
243 :
244 : #endif // SYZYGY_TRACE_PARSE_PARSE_ENGINE_H_
|