Chromium Code Reviews| Index: courgette/assembly_program.h |
| diff --git a/courgette/assembly_program.h b/courgette/assembly_program.h |
| index 50ab30a6f6cac90685c496cbb96a8244bf30aae1..38477cc1a301a44a8c31fbf1505b3f8add918b51 100644 |
| --- a/courgette/assembly_program.h |
| +++ b/courgette/assembly_program.h |
| @@ -23,6 +23,7 @@ |
| namespace courgette { |
| +class AssemblyProgram; |
| class EncodedProgram; |
| // Opcodes of simple assembly language |
| @@ -57,7 +58,104 @@ class Instruction { |
| DISALLOW_COPY_AND_ASSIGN(Instruction); |
| }; |
| -typedef NoThrowBuffer<Instruction*> InstructionVector; |
| +class InstructionReceptor { |
| + public: |
| + InstructionReceptor(); |
|
grt (UTC plus 2)
2016/11/04 09:38:53
remove this so that the compiler-generated ctor is
huangs
2016/11/04 18:20:40
Won't compile if I remove line. Changing to
Instr
|
| + virtual ~InstructionReceptor(); |
|
grt (UTC plus 2)
2016/11/04 09:38:53
= default; here and remove the definition from the
huangs
2016/11/04 18:20:39
Done.
|
| + |
| + // Generates an entire base relocation table. |
| + virtual CheckBool EmitPeRelocs() WARN_UNUSED_RESULT = 0; |
| + |
| + // Generates an ELF style relocation table for X86. |
| + virtual CheckBool EmitElfRelocation() WARN_UNUSED_RESULT = 0; |
| + |
| + // Generates an ELF style relocation table for ARM. |
| + virtual CheckBool EmitElfARMRelocation() WARN_UNUSED_RESULT = 0; |
| + |
| + // Following instruction will be assembled at address 'rva'. |
| + virtual CheckBool EmitOrigin(RVA rva) WARN_UNUSED_RESULT = 0; |
| + |
| + // Generates a single byte of data or machine instruction. |
| + virtual CheckBool EmitSingleByte(uint8_t byte) WARN_UNUSED_RESULT = 0; |
| + |
| + // Generates multiple bytes of data or machine instructions. |
| + virtual CheckBool EmitMultipleBytes(const uint8_t* value, |
|
grt (UTC plus 2)
2016/11/04 09:38:53
nit: value -> bytes here and elsewhere
huangs
2016/11/04 18:20:39
Done.
|
| + size_t len) WARN_UNUSED_RESULT = 0; |
| + |
| + // Generates 4-byte relative reference to address of 'label'. |
|
grt (UTC plus 2)
2016/11/04 09:38:53
nit: "Generates a..." (here and elsewhere)
huangs
2016/11/04 18:20:40
Done.
|
| + virtual CheckBool EmitRel32(Label* label) WARN_UNUSED_RESULT = 0; |
| + |
| + // Generates 4-byte relative reference to address of 'label' for ARM. |
| + virtual CheckBool EmitRel32ARM(uint16_t op, |
| + Label* label, |
| + const uint8_t* arm_op, |
| + uint16_t op_size) WARN_UNUSED_RESULT = 0; |
| + |
| + // Generates 4-byte absolute reference to address of 'label'. |
| + virtual CheckBool EmitAbs32(Label* label) WARN_UNUSED_RESULT = 0; |
| + |
| + // Generates 8-byte absolute reference to address of 'label'. |
| + virtual CheckBool EmitAbs64(Label* label) WARN_UNUSED_RESULT = 0; |
| + |
| + private: |
| + DISALLOW_COPY_AND_ASSIGN(InstructionReceptor); |
| +}; |
| + |
| +class InstructionCountReceptor : public InstructionReceptor { |
| + public: |
| + InstructionCountReceptor(); |
|
grt (UTC plus 2)
2016/11/04 09:38:53
remove
huangs
2016/11/04 18:20:39
Won't compile if I remove line. Changing to
Inst
|
| + ~InstructionCountReceptor() override; |
|
grt (UTC plus 2)
2016/11/04 09:38:53
remove
huangs
2016/11/04 18:20:39
Done.
|
| + |
| + // InstructionReceptor interfaces. |
|
grt (UTC plus 2)
2016/11/04 09:38:53
nit: just " // InstructionReceptor:"
huangs
2016/11/04 18:20:39
Done.
|
| + CheckBool EmitPeRelocs() override WARN_UNUSED_RESULT; |
| + CheckBool EmitElfRelocation() override WARN_UNUSED_RESULT; |
| + CheckBool EmitElfARMRelocation() override WARN_UNUSED_RESULT; |
| + CheckBool EmitOrigin(RVA rva) override WARN_UNUSED_RESULT; |
| + CheckBool EmitSingleByte(uint8_t byte) override WARN_UNUSED_RESULT; |
| + CheckBool EmitMultipleBytes(const uint8_t* value, |
| + size_t len) override WARN_UNUSED_RESULT; |
| + CheckBool EmitRel32(Label* label) override WARN_UNUSED_RESULT; |
| + CheckBool EmitRel32ARM(uint16_t op, |
| + Label* label, |
| + const uint8_t* arm_op, |
| + uint16_t op_size) override WARN_UNUSED_RESULT; |
| + CheckBool EmitAbs32(Label* label) override WARN_UNUSED_RESULT; |
| + CheckBool EmitAbs64(Label* label) override WARN_UNUSED_RESULT; |
| + |
| + size_t size() const { return size_; } |
| + |
| + private: |
| + size_t size_; |
|
grt (UTC plus 2)
2016/11/04 09:38:53
= 0;
huangs
2016/11/04 18:20:39
Done.
|
| + |
| + DISALLOW_COPY_AND_ASSIGN(InstructionCountReceptor); |
| +}; |
| + |
| +class InstructionStoreReceptor : public InstructionReceptor { |
| + public: |
| + InstructionStoreReceptor(size_t init_size, AssemblyProgram* program); |
| + ~InstructionStoreReceptor() override; |
| + |
| + // InstructionReceptor interfaces. |
|
grt (UTC plus 2)
2016/11/04 09:38:53
// InstructionReceptor:
huangs
2016/11/04 18:20:39
Done.
|
| + CheckBool EmitPeRelocs() override WARN_UNUSED_RESULT; |
| + CheckBool EmitElfRelocation() override WARN_UNUSED_RESULT; |
| + CheckBool EmitElfARMRelocation() override WARN_UNUSED_RESULT; |
| + CheckBool EmitOrigin(RVA rva) override WARN_UNUSED_RESULT; |
| + CheckBool EmitSingleByte(uint8_t byte) override WARN_UNUSED_RESULT; |
| + CheckBool EmitMultipleBytes(const uint8_t* value, |
| + size_t len) override WARN_UNUSED_RESULT; |
| + CheckBool EmitRel32(Label* label) override WARN_UNUSED_RESULT; |
| + CheckBool EmitRel32ARM(uint16_t op, |
| + Label* label, |
| + const uint8_t* arm_op, |
| + uint16_t op_size) override WARN_UNUSED_RESULT; |
| + CheckBool EmitAbs32(Label* label) override WARN_UNUSED_RESULT; |
| + CheckBool EmitAbs64(Label* label) override WARN_UNUSED_RESULT; |
| + |
| + private: |
| + AssemblyProgram* program_; |
| + |
| + DISALLOW_COPY_AND_ASSIGN(InstructionStoreReceptor); |
| +}; |
| // An AssemblyProgram is the result of disassembling an executable file. |
| // |
| @@ -77,7 +175,7 @@ typedef NoThrowBuffer<Instruction*> InstructionVector; |
| // AssemblyProgram. The modification process should call UnassignIndexes, do |
| // its own assignment, and then call AssignRemainingIndexes to ensure all |
| // indexes are assigned. |
| -// |
| + |
| class AssemblyProgram { |
| public: |
| using LabelHandler = base::Callback<void(Label*)>; |
| @@ -90,43 +188,6 @@ class AssemblyProgram { |
| void set_image_base(uint64_t image_base) { image_base_ = image_base; } |
| - // Instructions will be assembled in the order they are emitted. |
| - |
| - // Generates an entire base relocation table. |
| - CheckBool EmitPeRelocsInstruction() WARN_UNUSED_RESULT; |
| - |
| - // Generates an ELF style relocation table for X86. |
| - CheckBool EmitElfRelocationInstruction() WARN_UNUSED_RESULT; |
| - |
| - // Generates an ELF style relocation table for ARM. |
| - CheckBool EmitElfARMRelocationInstruction() WARN_UNUSED_RESULT; |
| - |
| - // Following instruction will be assembled at address 'rva'. |
| - CheckBool EmitOriginInstruction(RVA rva) WARN_UNUSED_RESULT; |
| - |
| - // Generates a single byte of data or machine instruction. |
| - CheckBool EmitByteInstruction(uint8_t byte) WARN_UNUSED_RESULT; |
| - |
| - // Generates multiple bytes of data or machine instructions. |
| - CheckBool EmitBytesInstruction(const uint8_t* value, |
| - size_t len) WARN_UNUSED_RESULT; |
| - |
| - // Generates 4-byte relative reference to address of 'label'. |
| - CheckBool EmitRel32(Label* label) WARN_UNUSED_RESULT; |
| - |
| - // Generates 4-byte relative reference to address of 'label' for |
| - // ARM. |
| - CheckBool EmitRel32ARM(uint16_t op, |
| - Label* label, |
| - const uint8_t* arm_op, |
| - uint16_t op_size) WARN_UNUSED_RESULT; |
| - |
| - // Generates 4-byte absolute reference to address of 'label'. |
| - CheckBool EmitAbs32(Label* label) WARN_UNUSED_RESULT; |
| - |
| - // Generates 8-byte absolute reference to address of 'label'. |
| - CheckBool EmitAbs64(Label* label) WARN_UNUSED_RESULT; |
| - |
| // Traverses RVAs in |abs32_visitor| and |rel32_visitor| to precompute Labels. |
| void PrecomputeLabels(RvaVisitor* abs32_visitor, RvaVisitor* rel32_visitor); |
| @@ -152,10 +213,61 @@ class AssemblyProgram { |
| // opcodes for an instruction that have label. |
| void HandleInstructionLabels(const LabelHandlerMap& handler_map) const; |
| + // Returns via |ret| the InstructionCountReceptor instance owned by |this|. |
| + // Should only be called once. Returns true on success. |
|
grt (UTC plus 2)
2016/11/04 09:38:53
should or must?
huangs
2016/11/04 18:20:39
Must. Updated.
|
| + CheckBool CreateInstructionCountReceptor(InstructionCountReceptor** ret); |
| + |
| + // Returns via |ret| the InstructionStoreReceptor instance owned by |this|. |
| + // Should only be called once, and only after CreateInstructionCountReceptor() |
| + // has been called. Returns true on success. |
| + CheckBool CreateInstructionStoreReceptor(InstructionStoreReceptor** ret); |
| + |
| private: |
| + using InstructionVector = NoThrowBuffer<Instruction*>; |
| + |
| using ScopedInstruction = |
| std::unique_ptr<Instruction, UncheckedDeleter<Instruction>>; |
| + friend InstructionStoreReceptor; |
| + |
| + // Instructions will be assembled in the order they are emitted. |
| + |
| + // TODO(huangs): Implement these in InstructionStoreReceptor. |
| + |
| + // Generates an entire base relocation table. |
| + CheckBool EmitPeRelocs() WARN_UNUSED_RESULT; |
| + |
| + // Generates an ELF style relocation table for X86. |
| + CheckBool EmitElfRelocation() WARN_UNUSED_RESULT; |
| + |
| + // Generates an ELF style relocation table for ARM. |
| + CheckBool EmitElfARMRelocation() WARN_UNUSED_RESULT; |
| + |
| + // Following instruction will be assembled at address 'rva'. |
| + CheckBool EmitOrigin(RVA rva) WARN_UNUSED_RESULT; |
| + |
| + // Generates a single byte of data or machine instruction. |
| + CheckBool EmitSingleByte(uint8_t byte) WARN_UNUSED_RESULT; |
| + |
| + // Generates multiple bytes of data or machine instructions. |
| + CheckBool EmitMultipleBytes(const uint8_t* value, |
| + size_t len) WARN_UNUSED_RESULT; |
| + |
| + // Generates 4-byte relative reference to address of 'label'. |
| + CheckBool EmitRel32(Label* label) WARN_UNUSED_RESULT; |
| + |
| + // Generates 4-byte relative reference to address of 'label' for ARM. |
| + CheckBool EmitRel32ARM(uint16_t op, |
| + Label* label, |
| + const uint8_t* arm_op, |
| + uint16_t op_size) WARN_UNUSED_RESULT; |
| + |
| + // Generates 4-byte absolute reference to address of 'label'. |
| + CheckBool EmitAbs32(Label* label) WARN_UNUSED_RESULT; |
| + |
| + // Generates 8-byte absolute reference to address of 'label'. |
| + CheckBool EmitAbs64(Label* label) WARN_UNUSED_RESULT; |
| + |
| ExecutableType kind_; |
| CheckBool Emit(ScopedInstruction instruction) WARN_UNUSED_RESULT; |
| @@ -184,6 +296,9 @@ class AssemblyProgram { |
| LabelManager abs32_label_manager_; |
| LabelManager rel32_label_manager_; |
| + std::unique_ptr<InstructionCountReceptor> count_receptor_; |
| + std::unique_ptr<InstructionStoreReceptor> store_receptor_; |
| + |
| DISALLOW_COPY_AND_ASSIGN(AssemblyProgram); |
| }; |