Chromium Code Reviews| OLD | NEW |
|---|---|
| (Empty) | |
| 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 // Declaration of the filler instrumentation transform. This instruments a given | |
| 16 // list of functions by injecting benign fillers at various places. | |
|
chrisha
2015/06/04 22:31:55
Maybe specify that the benign fillers are nops?
huangs
2015/06/05 15:13:24
Done.
| |
| 17 | |
| 18 #ifndef SYZYGY_INSTRUMENT_TRANSFORMS_FILLER_TRANSFORM_H_ | |
| 19 #define SYZYGY_INSTRUMENT_TRANSFORMS_FILLER_TRANSFORM_H_ | |
| 20 | |
| 21 #include <map> | |
| 22 #include <string> | |
| 23 #include <vector> | |
| 24 | |
| 25 #include "base/macros.h" | |
| 26 #include "base/files/file_path.h" | |
| 27 #include "base/memory/scoped_ptr.h" | |
| 28 #include "syzygy/block_graph/basic_block.h" | |
| 29 #include "syzygy/block_graph/block_graph.h" | |
| 30 #include "syzygy/block_graph/transforms/iterative_transform.h" | |
| 31 #include "syzygy/block_graph/transforms/named_transform.h" | |
| 32 | |
| 33 using block_graph::TransformPolicyInterface; | |
| 34 | |
| 35 namespace instrument { | |
| 36 namespace transforms { | |
| 37 | |
| 38 // A class to inject NOP into Instructions. | |
| 39 class NopInjector { | |
| 40 public: | |
| 41 typedef block_graph::BasicBlock BasicBlock; | |
| 42 | |
| 43 // NOP sizes that are represented by a single instruction. Multi-instruction | |
| 44 // NOPs are avoided to maintain consistent NOP code offsets after injection. | |
| 45 enum NopSizes { | |
| 46 NOP1 = 1, | |
| 47 NOP2, | |
| 48 NOP3, | |
| 49 NOP4, | |
| 50 NOP5, | |
| 51 NOP6, | |
| 52 NOP7, | |
| 53 NOP8, | |
| 54 NOP9, | |
| 55 NOP10, | |
| 56 NOP11 | |
|
chrisha
2015/06/04 22:31:55
Do you really need this enum? Can't we just have a
huangs
2015/06/05 15:13:23
I wanted to automatically enforce correctness, and
| |
| 57 }; | |
| 58 | |
| 59 // Specifications (code offsets and sizes) for NOP injection. The keys | |
| 60 // specify desired 0-based code offsets *after* injection. The values specify | |
|
chrisha
2015/06/04 22:31:55
A code offset generally refers to the actual bytes
huangs
2015/06/05 15:13:24
Done; renamed throughout.
| |
| 61 // NOP sizes. For example, {1: NOP3, 3: NOP2, 4: NOP5} specifies a | |
| 62 // transformation that takes instruction sequence "ABCDE" to "AXBYZCDE", where | |
| 63 // "X" is NOP3, "Y" is NOP2, and "Z" is NOP5. | |
| 64 typedef const std::map<size_t, NopSizes> NopSpec; | |
| 65 | |
| 66 explicit NopInjector(const NopSpec& nop_spec) : nop_spec_(nop_spec) { } | |
| 67 ~NopInjector() { } | |
| 68 | |
| 69 // Injects NOP into @p instruction. The (post-injection) offsets and NOP sizes | |
| 70 // are given by nop_spec_. NOP is not injected past the last instruction. | |
| 71 // Returns the number of NOPs injected. | |
|
chrisha
2015/06/04 22:31:54
Is the return value useful?
Maybe just a true fal
huangs
2015/06/05 15:13:24
I used it for testing, but its not used in actual
| |
| 72 size_t Inject(BasicBlock::Instructions* instructions) const; | |
| 73 | |
| 74 private: | |
| 75 NopSpec nop_spec_; | |
| 76 | |
| 77 DISALLOW_COPY_AND_ASSIGN(NopInjector); | |
| 78 }; | |
| 79 | |
| 80 // Applies filler transform to a subgraph. | |
|
chrisha
2015/06/04 22:31:55
That describes the TransformBasicBlockSubGraph fun
huangs
2015/06/05 15:13:24
Done.
| |
| 81 class FillerBasicBlockTransform | |
| 82 : public block_graph::transforms::NamedBasicBlockSubGraphTransformImpl< | |
| 83 FillerBasicBlockTransform> { | |
| 84 public: | |
| 85 typedef block_graph::BasicBlock BasicBlock; | |
| 86 typedef block_graph::BasicCodeBlock BasicCodeBlock; | |
| 87 typedef block_graph::BlockGraph BlockGraph; | |
| 88 typedef BlockGraph::Block Block; | |
|
chrisha
2015/06/04 22:31:55
This typedef to the end of the list (block_graph s
huangs
2015/06/05 15:13:24
Done.
| |
| 89 typedef block_graph::BasicBlockSubGraph BasicBlockSubGraph; | |
|
chrisha
2015/06/04 22:31:54
And put this one in alphabetical order too, please
huangs
2015/06/05 15:13:24
Done.
| |
| 90 typedef block_graph::TransformPolicyInterface TransformPolicyInterface; | |
| 91 | |
| 92 FillerBasicBlockTransform() { } | |
| 93 virtual ~FillerBasicBlockTransform() { } | |
| 94 | |
| 95 // For NamedBlockGraphTransformImpl. | |
| 96 static const char kTransformName[]; | |
| 97 | |
|
chrisha
2015/06/04 22:31:55
Please endow this transform with a debug_friendly
huangs
2015/06/05 15:13:24
Done. Had to rewrite InjectNop() so consecutive in
| |
| 98 protected: | |
| 99 // @name BasicBlockSubGraphTransformInterface implementation. | |
| 100 // @{ | |
| 101 // Applies the filler transform. Specifically, visits every basic code graph | |
|
chrisha
2015/06/04 22:31:55
basic code block?
huangs
2015/06/05 15:13:24
Done.
| |
| 102 // in @p basic_block_subgraph and injects NOP at various places. | |
| 103 bool TransformBasicBlockSubGraph( | |
|
chrisha
2015/06/04 22:31:54
Why is this function protected?
huangs
2015/06/05 15:13:25
Moved to public:.
| |
| 104 const TransformPolicyInterface* policy, | |
| 105 BlockGraph* block_graph, | |
| 106 BasicBlockSubGraph* basic_block_subgraph) override; | |
| 107 // @} | |
| 108 | |
| 109 private: | |
| 110 DISALLOW_COPY_AND_ASSIGN(FillerBasicBlockTransform); | |
| 111 }; | |
| 112 | |
| 113 // Takes a list of target function names, and applies filler transform only to | |
|
chrisha
2015/06/04 22:31:55
Decorated function names? Undecorated? Please be v
huangs
2015/06/05 15:13:24
Done.
| |
| 114 // the specified functions. Also contains counters. | |
|
chrisha
2015/06/04 22:31:55
Counters of what? For what purpose?
If they're im
huangs
2015/06/05 15:13:24
Counters to display messages (displays message if
| |
| 115 class FillerTransform | |
| 116 : public block_graph::transforms::IterativeTransformImpl<FillerTransform> { | |
| 117 public: | |
| 118 typedef block_graph::BasicBlockSubGraph BasicBlockSubGraph; | |
| 119 typedef block_graph::BlockGraph BlockGraph; | |
| 120 typedef BlockGraph::Block Block; | |
| 121 | |
| 122 explicit FillerTransform(const std::vector<std::string>& target_list); | |
|
chrisha
2015/06/04 22:31:55
We want this transform to be randomized, but repea
huangs
2015/06/05 15:13:24
Can we do this in a separate CL? This complicates
| |
| 123 virtual ~FillerTransform() { } | |
| 124 | |
| 125 // Accessors | |
| 126 // @{ | |
| 127 size_t num_target_updated() const { return num_target_updated_; } | |
| 128 // @} | |
| 129 | |
| 130 // For NamedBlockGraphTransformImpl. | |
| 131 static const char kTransformName[]; | |
| 132 | |
| 133 protected: | |
| 134 // Returns whether @p block is a target. | |
| 135 bool ShouldProcessBlock(Block* block) const; | |
| 136 | |
| 137 // Verifies that all targets were found, and displays error messages if not. | |
| 138 void CheckAllTargetFound() const; | |
|
chrisha
2015/06/04 22:31:55
AllTargets*
Errors are unrecoverable, typically.
huangs
2015/06/05 15:13:24
Done.
| |
| 139 | |
| 140 // @name IterativeTransformImpl implementation. | |
| 141 // @{ | |
| 142 bool PreBlockGraphIteration(const TransformPolicyInterface* policy, | |
| 143 BlockGraph* block_graph, | |
| 144 Block* header_block); | |
| 145 bool OnBlock(const TransformPolicyInterface* policy, | |
| 146 BlockGraph* block_graph, | |
| 147 Block* block); | |
| 148 bool PostBlockGraphIteration(const TransformPolicyInterface* policy, | |
| 149 BlockGraph* block_graph, | |
| 150 Block* header_block); | |
| 151 // @} | |
| 152 | |
| 153 private: | |
| 154 friend NamedBlockGraphTransformImpl<FillerTransform>; | |
| 155 friend IterativeTransformImpl<FillerTransform>; | |
| 156 | |
| 157 scoped_ptr<FillerBasicBlockTransform> basic_block_transform_; | |
| 158 | |
| 159 // Names of targets, maps to whether the target was seen. | |
| 160 std::map<std::string, bool> target_names_; | |
| 161 | |
| 162 // Counters. | |
|
chrisha
2015/06/04 22:31:54
I imagine these are used by CheckAllTargetsFound?
huangs
2015/06/05 15:13:24
Done.
| |
| 163 // @{ | |
| 164 size_t num_block_; | |
| 165 size_t num_code_block_; | |
|
chrisha
2015/06/04 22:31:55
num_blocks_?
chrisha
2015/06/04 22:31:55
num_code_basic_blocks_?
huangs
2015/06/05 15:13:24
Done.
huangs
2015/06/05 15:13:24
Done.
| |
| 166 size_t num_target_updated_; | |
|
chrisha
2015/06/04 22:31:54
num_targets_updated_?
huangs
2015/06/05 15:13:24
Done.
| |
| 167 // @} | |
| 168 | |
| 169 DISALLOW_COPY_AND_ASSIGN(FillerTransform); | |
| 170 }; | |
| 171 | |
| 172 } // namespace transforms | |
| 173 } // namespace instrument | |
| 174 | |
| 175 #endif // SYZYGY_INSTRUMENT_TRANSFORMS_FILLER_TRANSFORM_H_ | |
| OLD | NEW |