1 : // Copyright 2015 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 : #ifndef SYZYGY_REFINERY_ANALYZERS_ANALYZER_H_
16 : #define SYZYGY_REFINERY_ANALYZERS_ANALYZER_H_
17 :
18 : #include "syzygy/minidump/minidump.h"
19 : #include "syzygy/refinery/process_state/process_state.h"
20 : #include "syzygy/refinery/symbols/dia_symbol_provider.h"
21 : #include "syzygy/refinery/symbols/symbol_provider.h"
22 :
23 m : namespace refinery {
24 :
25 : // The interface implemented by analyzers. Each analyzer is responsible for
26 : // analyzing some part of the minidump and/or the process state. Analyzers will
27 : // for example extract memory/thread/module information from minidumps to
28 : // fill in the appropriate layers in the process state.
29 : // Other analyzers may work solely on the process state, by e.g. coalescing
30 : // overlapping, consistent data in a layer, propagating type information,
31 : // discovering references and the like.
32 m : class Analyzer {
33 m : public:
34 m : enum AnalysisResult {
35 : // Analyzer will not do any more work if re-invoked.
36 m : ANALYSIS_COMPLETE,
37 : // Analyzer may do more work if re-invoked.
38 m : ANALYSIS_ITERATE,
39 : // Analyzer encountered an error.
40 m : ANALYSIS_ERROR,
41 m : };
42 m : class ProcessAnalysis;
43 :
44 m : virtual ~Analyzer() = 0 {};
45 : // @returns the analyzer's name.
46 m : virtual const char* name() const = 0;
47 :
48 : // Analyze @p minidump and update the ProcessState provided through
49 : // @p process_analysis. Analysis may involve examining the ProcessState,
50 : // and may be an iterative process.
51 : // @param minidump the minidump under analysis.
52 : // @param process_analysis provides the ProcessState to update, along with
53 : // factories providing symbols etc, necessary to perform the analysis.
54 : // @returns an analysis result. An analyzer may not be invoked again after
55 : // it's returned ANALYSIS_COMPLETE. If an analyzer returns ANALYSIS_ERROR
56 : // the resultant ProcessState may be inconsistent.
57 : // @note Analysis completes only once all analyzers have returned
58 : // ANALYSIS_COMPLETED.
59 m : virtual AnalysisResult Analyze(const minidump::Minidump& minidump,
60 m : const ProcessAnalysis& process_analysis) = 0;
61 m : };
62 :
63 : // A process analysis brokers the state that analyzers may need during
64 : // analysis. It vends the process state, symbol providers and so on.
65 m : class Analyzer::ProcessAnalysis {
66 m : public:
67 : // The process state to update in this analysis.
68 m : virtual ProcessState* process_state() const = 0;
69 :
70 : // A DIA symbol provider to use during this analysis.
71 m : virtual scoped_refptr<DiaSymbolProvider> dia_symbol_provider() const = 0;
72 :
73 : // A symbol provider to use during this analysis.
74 m : virtual scoped_refptr<SymbolProvider> symbol_provider() const = 0;
75 m : };
76 :
77 : // @name Utility macros to allow declaring analyzer input and output layer
78 : // dependencies.
79 : // @{
80 : #define ANALYZER_INPUT_LAYERS(...) \
81 m : static const ProcessState::LayerEnum* InputLayers() { \
82 m : static const ProcessState::LayerEnum kInputLayers[] = { \
83 m : __VA_ARGS__, ProcessState::UnknownLayer}; \
84 m : return kInputLayers; \
85 m : }
86 :
87 : #define ANALYZER_NO_INPUT_LAYERS() \
88 m : static const ProcessState::LayerEnum* InputLayers() { \
89 m : static const ProcessState::LayerEnum kSentinel = \
90 m : ProcessState::UnknownLayer; \
91 m : return &kSentinel; \
92 m : }
93 :
94 : #define ANALYZER_OUTPUT_LAYERS(...) \
95 m : static const ProcessState::LayerEnum* OutputLayers() { \
96 m : static const ProcessState::LayerEnum kOutputLayers[] = { \
97 m : __VA_ARGS__, ProcessState::UnknownLayer}; \
98 m : return kOutputLayers; \
99 m : }
100 :
101 : #define ANALYZER_NO_OUTPUT_LAYERS() \
102 m : static const ProcessState::LayerEnum* OutputLayers() { \
103 m : static const ProcessState::LayerEnum kSentinel = \
104 m : ProcessState::UnknownLayer; \
105 m : return &kSentinel; \
106 m : }
107 :
108 : // @}
109 :
110 m : } // namespace refinery
111 :
112 : #endif // SYZYGY_REFINERY_ANALYZERS_ANALYZER_H_
|