| OLD | NEW |
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "courgette/assembly_program.h" | 5 #include "courgette/assembly_program.h" |
| 6 | 6 |
| 7 #include "base/callback.h" | 7 #include "base/callback.h" |
| 8 #include "base/logging.h" | 8 #include "base/logging.h" |
| 9 #include "courgette/courgette.h" | 9 #include "courgette/courgette.h" |
| 10 #include "courgette/disassembler.h" |
| 10 #include "courgette/encoded_program.h" | 11 #include "courgette/encoded_program.h" |
| 11 | 12 |
| 12 namespace courgette { | 13 namespace courgette { |
| 13 | 14 |
| 14 namespace { | 15 namespace { |
| 15 | 16 |
| 16 // Sets the current address for the emitting instructions. | 17 // Sets the current address for the emitting instructions. |
| 17 class OriginInstruction : public Instruction { | 18 class OriginInstruction : public Instruction { |
| 18 public: | 19 public: |
| 19 explicit OriginInstruction(RVA rva) : Instruction(ORIGIN, 0), rva_(rva) {} | 20 explicit OriginInstruction(RVA rva) : Instruction(ORIGIN, 0), rva_(rva) {} |
| (...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 97 uint16_t op_size_; | 98 uint16_t op_size_; |
| 98 }; | 99 }; |
| 99 | 100 |
| 100 /******** InstructionCountReceptor ********/ | 101 /******** InstructionCountReceptor ********/ |
| 101 | 102 |
| 102 // An InstructionReceptor that counts space occupied by emitted instructions. | 103 // An InstructionReceptor that counts space occupied by emitted instructions. |
| 103 class InstructionCountReceptor : public InstructionReceptor { | 104 class InstructionCountReceptor : public InstructionReceptor { |
| 104 public: | 105 public: |
| 105 InstructionCountReceptor() = default; | 106 InstructionCountReceptor() = default; |
| 106 | 107 |
| 107 size_t size() const { return size_; } | 108 size_t abs_count() const { return abs_count_; } |
| 109 size_t rel_count() const { return rel_count_; } |
| 108 | 110 |
| 109 // InstructionReceptor: | 111 // InstructionReceptor: |
| 110 // TODO(huangs): 2016/11: Populate these with size_ += ... | |
| 111 CheckBool EmitPeRelocs() override { return true; } | 112 CheckBool EmitPeRelocs() override { return true; } |
| 112 CheckBool EmitElfRelocation() override { return true; } | 113 CheckBool EmitElfRelocation() override { return true; } |
| 113 CheckBool EmitElfARMRelocation() override { return true; } | 114 CheckBool EmitElfARMRelocation() override { return true; } |
| 114 CheckBool EmitOrigin(RVA rva) override { return true; } | 115 CheckBool EmitOrigin(RVA rva) override { return true; } |
| 115 CheckBool EmitSingleByte(uint8_t byte) override { return true; } | 116 CheckBool EmitSingleByte(uint8_t byte) override { return true; } |
| 116 CheckBool EmitMultipleBytes(const uint8_t* bytes, size_t len) override { | 117 CheckBool EmitMultipleBytes(const uint8_t* bytes, size_t len) override { |
| 117 return true; | 118 return true; |
| 118 } | 119 } |
| 119 CheckBool EmitRel32(Label* label) override { return true; } | 120 CheckBool EmitRel32(Label* label) override { |
| 121 ++rel_count_; |
| 122 return true; |
| 123 } |
| 120 CheckBool EmitRel32ARM(uint16_t op, | 124 CheckBool EmitRel32ARM(uint16_t op, |
| 121 Label* label, | 125 Label* label, |
| 122 const uint8_t* arm_op, | 126 const uint8_t* arm_op, |
| 123 uint16_t op_size) override { | 127 uint16_t op_size) override { |
| 128 ++rel_count_; |
| 124 return true; | 129 return true; |
| 125 } | 130 } |
| 126 CheckBool EmitAbs32(Label* label) override { return true; } | 131 CheckBool EmitAbs32(Label* label) override { |
| 127 CheckBool EmitAbs64(Label* label) override { return true; } | 132 ++abs_count_; |
| 133 return true; |
| 134 } |
| 135 CheckBool EmitAbs64(Label* label) override { |
| 136 ++abs_count_; |
| 137 return true; |
| 138 } |
| 128 | 139 |
| 129 private: | 140 private: |
| 130 size_t size_ = 0; | 141 size_t abs_count_ = 0; |
| 142 size_t rel_count_ = 0; |
| 131 | 143 |
| 132 DISALLOW_COPY_AND_ASSIGN(InstructionCountReceptor); | 144 DISALLOW_COPY_AND_ASSIGN(InstructionCountReceptor); |
| 133 }; | 145 }; |
| 134 | 146 |
| 135 /******** InstructionStoreReceptor ********/ | 147 /******** InstructionStoreReceptor ********/ |
| 136 | 148 |
| 137 // An InstructionReceptor that stores emitted instructions. | 149 // An InstructionReceptor that stores emitted instructions. |
| 138 class InstructionStoreReceptor : public InstructionReceptor { | 150 class InstructionStoreReceptor : public InstructionReceptor { |
| 139 public: | 151 public: |
| 140 explicit InstructionStoreReceptor(AssemblyProgram* program) | 152 InstructionStoreReceptor(AssemblyProgram* program, bool annotate_labels) |
| 141 : program_(program) { | 153 : program_(program), annotate_labels_(annotate_labels) { |
| 142 CHECK(program_); | 154 CHECK(program_); |
| 143 } | 155 } |
| 144 | 156 |
| 145 // TODO(huangs): 2016/11: Add Reserve(). | 157 // TODO(huangs): 2017/04: Add Reserve(). |
| 146 | 158 |
| 147 // InstructionReceptor: | 159 // InstructionReceptor: |
| 148 // TODO(huangs): 2016/11: Replace stub with implementation. | 160 // TODO(huangs): 2017/04: Move implementations here. |
| 149 CheckBool EmitPeRelocs() override { return program_->EmitPeRelocs(); } | 161 CheckBool EmitPeRelocs() override { return program_->EmitPeRelocs(); } |
| 150 CheckBool EmitElfRelocation() override { | 162 CheckBool EmitElfRelocation() override { |
| 151 return program_->EmitElfRelocation(); | 163 return program_->EmitElfRelocation(); |
| 152 } | 164 } |
| 153 CheckBool EmitElfARMRelocation() override { | 165 CheckBool EmitElfARMRelocation() override { |
| 154 return program_->EmitElfARMRelocation(); | 166 return program_->EmitElfARMRelocation(); |
| 155 } | 167 } |
| 156 CheckBool EmitOrigin(RVA rva) override { return program_->EmitOrigin(rva); } | 168 CheckBool EmitOrigin(RVA rva) override { return program_->EmitOrigin(rva); } |
| 157 CheckBool EmitSingleByte(uint8_t byte) override { | 169 CheckBool EmitSingleByte(uint8_t byte) override { |
| 158 return program_->EmitSingleByte(byte); | 170 return program_->EmitSingleByte(byte); |
| 159 } | 171 } |
| 160 CheckBool EmitMultipleBytes(const uint8_t* bytes, size_t len) override { | 172 CheckBool EmitMultipleBytes(const uint8_t* bytes, size_t len) override { |
| 161 return program_->EmitMultipleBytes(bytes, len); | 173 return program_->EmitMultipleBytes(bytes, len); |
| 162 } | 174 } |
| 163 CheckBool EmitRel32(Label* label) override { | 175 CheckBool EmitRel32(Label* label) override { |
| 176 if (annotate_labels_) |
| 177 program_->mutable_rel32_label_annotations()->push_back(label); |
| 164 return program_->EmitRel32(label); | 178 return program_->EmitRel32(label); |
| 165 } | 179 } |
| 166 CheckBool EmitRel32ARM(uint16_t op, | 180 CheckBool EmitRel32ARM(uint16_t op, |
| 167 Label* label, | 181 Label* label, |
| 168 const uint8_t* arm_op, | 182 const uint8_t* arm_op, |
| 169 uint16_t op_size) override { | 183 uint16_t op_size) override { |
| 184 if (annotate_labels_) |
| 185 program_->mutable_rel32_label_annotations()->push_back(label); |
| 170 return program_->EmitRel32ARM(op, label, arm_op, op_size); | 186 return program_->EmitRel32ARM(op, label, arm_op, op_size); |
| 171 } | 187 } |
| 172 CheckBool EmitAbs32(Label* label) override { | 188 CheckBool EmitAbs32(Label* label) override { |
| 189 if (annotate_labels_) |
| 190 program_->mutable_abs32_label_annotations()->push_back(label); |
| 173 return program_->EmitAbs32(label); | 191 return program_->EmitAbs32(label); |
| 174 } | 192 } |
| 175 CheckBool EmitAbs64(Label* label) override { | 193 CheckBool EmitAbs64(Label* label) override { |
| 194 if (annotate_labels_) |
| 195 program_->mutable_abs32_label_annotations()->push_back(label); |
| 176 return program_->EmitAbs64(label); | 196 return program_->EmitAbs64(label); |
| 177 } | 197 } |
| 178 | 198 |
| 179 private: | 199 private: |
| 180 AssemblyProgram* program_; | 200 AssemblyProgram* program_; |
| 201 const bool annotate_labels_; |
| 181 | 202 |
| 182 DISALLOW_COPY_AND_ASSIGN(InstructionStoreReceptor); | 203 DISALLOW_COPY_AND_ASSIGN(InstructionStoreReceptor); |
| 183 }; | 204 }; |
| 184 | 205 |
| 185 } // namespace | 206 } // namespace |
| 186 | 207 |
| 187 /******** AssemblyProgram ********/ | 208 /******** AssemblyProgram ********/ |
| 188 | 209 |
| 189 AssemblyProgram::AssemblyProgram(ExecutableType kind, uint64_t image_base) | 210 AssemblyProgram::AssemblyProgram(ExecutableType kind, uint64_t image_base) |
| 190 : kind_(kind), image_base_(image_base) {} | 211 : kind_(kind), image_base_(image_base) {} |
| (...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 287 } | 308 } |
| 288 | 309 |
| 289 Label* AssemblyProgram::FindAbs32Label(RVA rva) { | 310 Label* AssemblyProgram::FindAbs32Label(RVA rva) { |
| 290 return abs32_label_manager_.Find(rva); | 311 return abs32_label_manager_.Find(rva); |
| 291 } | 312 } |
| 292 | 313 |
| 293 Label* AssemblyProgram::FindRel32Label(RVA rva) { | 314 Label* AssemblyProgram::FindRel32Label(RVA rva) { |
| 294 return rel32_label_manager_.Find(rva); | 315 return rel32_label_manager_.Find(rva); |
| 295 } | 316 } |
| 296 | 317 |
| 297 void AssemblyProgram::HandleInstructionLabels( | 318 CheckBool AssemblyProgram::GenerateInstructions(const InstructionGenerator& gen, |
| 298 const AssemblyProgram::LabelHandlerMap& handler_map) const { | 319 bool annotate_labels) { |
| 299 for (const Instruction* instruction : instructions_) { | 320 // Pass 1: Count storage space required and reserve in advance. |
| 300 LabelHandlerMap::const_iterator it = handler_map.find(instruction->op()); | |
| 301 if (it != handler_map.end()) { | |
| 302 it->second.Run( | |
| 303 static_cast<const InstructionWithLabel*>(instruction)->label()); | |
| 304 } | |
| 305 } | |
| 306 } | |
| 307 | |
| 308 CheckBool AssemblyProgram::GenerateInstructions( | |
| 309 const InstructionGenerator& gen) { | |
| 310 // Pass 1: Count the space needed to store instructions. | |
| 311 InstructionCountReceptor count_receptor; | 321 InstructionCountReceptor count_receptor; |
| 312 if (!gen.Run(&count_receptor)) | 322 if (!gen.Run(&count_receptor)) |
| 313 return false; | 323 return false; |
| 314 | 324 |
| 315 // Pass 2: Emit all instructions to preallocated buffer (uses Phase 1 count). | 325 if (annotate_labels) { |
| 316 InstructionStoreReceptor store_receptor(this); | 326 DCHECK(abs32_label_annotations_.empty()); |
| 317 // TODO(huangs): 2017/03: Pass |count_receptor->size()| to |store_receptor_| | 327 abs32_label_annotations_.reserve(count_receptor.abs_count()); |
| 318 // to reserve space for raw data. | 328 DCHECK(rel32_label_annotations_.empty()); |
| 329 rel32_label_annotations_.reserve(count_receptor.rel_count()); |
| 330 } |
| 331 |
| 332 // Pass 2: Emit all instructions to reserved buffer (uses Phase 1 count). |
| 333 // Populates |abs32_label_annotations_| and |re32_label_annotations_| if |
| 334 // |annotate_labels| is true. |
| 335 InstructionStoreReceptor store_receptor(this, annotate_labels); |
| 319 return gen.Run(&store_receptor); | 336 return gen.Run(&store_receptor); |
| 320 } | 337 } |
| 321 | 338 |
| 322 CheckBool AssemblyProgram::Emit(ScopedInstruction instruction) { | 339 CheckBool AssemblyProgram::Emit(ScopedInstruction instruction) { |
| 323 if (!instruction || !instructions_.push_back(instruction.get())) | 340 if (!instruction || !instructions_.push_back(instruction.get())) |
| 324 return false; | 341 return false; |
| 325 // Ownership successfully passed to instructions_. | 342 // Ownership successfully passed to instructions_. |
| 326 ignore_result(instruction.release()); | 343 ignore_result(instruction.release()); |
| 327 return true; | 344 return true; |
| 328 } | 345 } |
| (...skipping 116 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 445 Status Encode(const AssemblyProgram& program, | 462 Status Encode(const AssemblyProgram& program, |
| 446 std::unique_ptr<EncodedProgram>* output) { | 463 std::unique_ptr<EncodedProgram>* output) { |
| 447 // Explicitly release any memory associated with the output before encoding. | 464 // Explicitly release any memory associated with the output before encoding. |
| 448 output->reset(); | 465 output->reset(); |
| 449 | 466 |
| 450 *output = program.Encode(); | 467 *output = program.Encode(); |
| 451 return (*output) ? C_OK : C_GENERAL_ERROR; | 468 return (*output) ? C_OK : C_GENERAL_ERROR; |
| 452 } | 469 } |
| 453 | 470 |
| 454 } // namespace courgette | 471 } // namespace courgette |
| OLD | NEW |