Commit 7617452e authored by swift_gan's avatar swift_gan Committed by swift_gan

tweak code

parent 1e554746
......@@ -14,6 +14,17 @@ U32 InstructionA64<InstStruct>::size() {
return sizeof(InstA64);
}
//Unknow
A64_UNKNOW::A64_UNKNOW(A64_STRUCT_UNKNOW *inst) : InstructionA64(inst) {
}
A64_UNKNOW::A64_UNKNOW(STRUCT_A64(UNKNOW) &inst) {
inst_backup = inst;
this->set(&inst_backup);
}
//PC Rel Inst
template<typename Inst>
......@@ -109,13 +120,21 @@ A64_B_BL::A64_B_BL(STRUCT_A64(B_BL) *inst) : A64_INST_PC_REL(inst) {
}
A64_B_BL::A64_B_BL(A64_B_BL::OP op, Off offset) : op(op), offset(offset) {
assembler();
}
A64_B_BL::A64_B_BL(A64_B_BL::OP op, Label &l) : op(op) {
bindLabel(l);
}
Off A64_B_BL::getImmPCOffset() {
return signExtend64(26 + 2, COMBINE(get()->imm26, 0b00, 2));
}
void A64_B_BL::onOffsetApply(Off offset) {
this->offset = offset;
get()->imm26 = TruncateToUint26(offset);
}
void A64_B_BL::decode(STRUCT_A64(B_BL) *inst) {
op = OP(inst->op);
offset = getImmPCOffset();
......@@ -139,9 +158,7 @@ A64_CBZ_CBNZ::A64_CBZ_CBNZ(STRUCT_A64(CBZ_CBNZ) *inst) : A64_INST_PC_REL(inst) {
A64_CBZ_CBNZ::A64_CBZ_CBNZ(A64_CBZ_CBNZ::OP op, Off offset, RegisterA64 *rt) : op(op),
offset(offset),
rt(rt) {
assembler();
}
rt(rt) {}
Off A64_CBZ_CBNZ::getImmPCOffset() {
return signExtend64(19 + 2, COMBINE(get()->imm19, 0b00, 2));
......@@ -174,9 +191,7 @@ A64_B_COND::A64_B_COND(STRUCT_A64(B_COND) *inst) : A64_INST_PC_REL(inst) {
decode(inst);
}
A64_B_COND::A64_B_COND(Condition condition, Off offset) : condition(condition), offset(offset) {
assembler();
}
A64_B_COND::A64_B_COND(Condition condition, Off offset) : condition(condition), offset(offset) {}
Off A64_B_COND::getImmPCOffset() {
return signExtend64(19 + 2, COMBINE(get()->imm19, 0b00, 2));
......@@ -205,9 +220,7 @@ A64_TBZ_TBNZ::A64_TBZ_TBNZ(STRUCT_A64(TBZ_TBNZ) &inst) : A64_INST_PC_REL(&inst)
A64_TBZ_TBNZ::A64_TBZ_TBNZ(A64_TBZ_TBNZ::OP op, RegisterA64 *rt, U32 bit, Off offset) : op(op),
rt(rt),
bit(bit),
offset(offset) {
assembler();
}
offset(offset) {}
Off A64_TBZ_TBNZ::getImmPCOffset() {
return signExtend64(14 + 2, COMBINE(get()->imm14, 0b00, 2));
......@@ -245,9 +258,7 @@ A64_LDR_LIT::A64_LDR_LIT(STRUCT_A64(LDR_LIT) *inst) : A64_INST_PC_REL(inst) {
A64_LDR_LIT::A64_LDR_LIT(A64_LDR_LIT::OP op, RegisterA64 *rt, Off offset) : op(op), rt(rt),
offset(offset) {
assembler();
}
offset(offset) {}
Off A64_LDR_LIT::getImmPCOffset() {
return signExtend64(19 + 2, COMBINE(get()->imm19, 0b00, 2));
......@@ -279,14 +290,10 @@ A64_STR_IMM::A64_STR_IMM(STRUCT_A64(STR_IMM) *inst) : InstructionA64(inst) {
decode(inst);
}
A64_STR_IMM::A64_STR_IMM(RegisterA64 &rt, const MemOperand &operand) : rt(&rt), operand(operand) {
assembler();
}
A64_STR_IMM::A64_STR_IMM(RegisterA64 &rt, const MemOperand &operand) : rt(&rt), operand(operand) {}
A64_STR_IMM::A64_STR_IMM(Condition condition, RegisterA64 &rt, const MemOperand &operand)
: condition(condition), rt(&rt), operand(operand) {
assembler();
}
: condition(condition), rt(&rt), operand(operand) {}
AddrMode A64_STR_IMM::decodeAddrMode() {
if (get()->P == 1 && get()->W == 0) {
......@@ -325,9 +332,7 @@ A64_BR_BLR_RET::A64_BR_BLR_RET(STRUCT_A64(BR_BLR_RET) &inst) : InstructionA64(&i
decode(&inst);
}
A64_BR_BLR_RET::A64_BR_BLR_RET(A64_BR_BLR_RET::OP op, XRegister &rn) : op(op), rn(&rn) {
assembler();
}
A64_BR_BLR_RET::A64_BR_BLR_RET(A64_BR_BLR_RET::OP op, XRegister &rn) : op(op), rn(&rn) {}
void A64_BR_BLR_RET::decode(A64_STRUCT_BR_BLR_RET *inst) {
rn = XReg(static_cast<U8>(inst->op));
......
......@@ -152,6 +152,20 @@ namespace SandHook {
};
class INST_A64(UNKNOW) : public InstructionA64<STRUCT_A64(UNKNOW)> {
public:
A64_UNKNOW(STRUCT_A64(UNKNOW) *inst);
A64_UNKNOW(STRUCT_A64(UNKNOW) &inst);
inline bool unknow() override {
return true;
}
private:
STRUCT_A64(UNKNOW) inst_backup;
};
template <typename Inst>
class A64_INST_PC_REL : public InstructionA64<Inst> {
public:
......@@ -287,6 +301,8 @@ namespace SandHook {
A64_B_BL(OP op, Off offset);
A64_B_BL(OP op, Label &l);
DEFINE_IS(B_BL)
inline Off getOffset() {
......@@ -303,6 +319,8 @@ namespace SandHook {
Off getImmPCOffset() override;
void onOffsetApply(Off offset) override;
void decode(STRUCT_A64(B_BL) *decode) override;
void assembler() override;
......
......@@ -12,6 +12,7 @@
#define STRUCT_A64(X) A64_STRUCT_##X
#define OPCODE_A64(X) A64_OPCODE_##X
#define DEFINE_OPCODE(X, V) const U32 OPCODE_A64(X) = V;
#define DEFINE_STRUCT_A64(X) struct STRUCT_A64(X) : public Base
enum InstructionFields {
......@@ -86,6 +87,11 @@ enum Extend {
SXTX = 7
};
//unknow inst
DEFINE_STRUCT_A64(UNKNOW) {
InstA64 raw;
};
#define IMM_LO_W 2
#define IMM_HI_W 19
DEFINE_OPCODE(ADR_ADRP, 0b10000)
......@@ -98,7 +104,7 @@ struct STRUCT_A64(ADR_ADRP) {
};
DEFINE_OPCODE(MOV_WIDE, 0b100101)
struct STRUCT_A64(MOV_WIDE) {
DEFINE_STRUCT_A64(MOV_WIDE) {
InstA64 rd:5;
InstA64 imm16:16;
InstA64 hw:2;
......@@ -108,14 +114,14 @@ struct STRUCT_A64(MOV_WIDE) {
};
DEFINE_OPCODE(B_BL, 0b00101)
struct STRUCT_A64(B_BL) {
DEFINE_STRUCT_A64(B_BL) {
InstA64 imm26:26;
InstA64 opcode:5;
InstA64 op:1;
};
DEFINE_OPCODE(CBZ_CBNZ, 0b011010)
struct STRUCT_A64(CBZ_CBNZ) {
DEFINE_STRUCT_A64(CBZ_CBNZ) {
InstA64 rt:5;
InstA64 imm19:19;
InstA64 op:1;
......@@ -124,7 +130,7 @@ struct STRUCT_A64(CBZ_CBNZ) {
};
DEFINE_OPCODE(B_COND, 0b01010100)
struct STRUCT_A64(B_COND) {
DEFINE_STRUCT_A64(B_COND) {
InstA64 cond:4;
InstA64 unkown_0:1;
InstA64 imm19:19;
......@@ -132,7 +138,7 @@ struct STRUCT_A64(B_COND) {
};
DEFINE_OPCODE(TBZ_TBNZ, 0b011011)
struct STRUCT_A64(TBZ_TBNZ) {
DEFINE_STRUCT_A64(TBZ_TBNZ) {
InstA64 rt:5;
InstA64 imm14:14;
InstA64 b40:5;
......@@ -142,7 +148,7 @@ struct STRUCT_A64(TBZ_TBNZ) {
};
DEFINE_OPCODE(LDR_LIT, 0b011000)
struct STRUCT_A64(LDR_LIT) {
DEFINE_STRUCT_A64(LDR_LIT) {
InstA64 rt:5;
InstA64 imm19:19;
InstA64 opcode:6;
......@@ -150,7 +156,7 @@ struct STRUCT_A64(LDR_LIT) {
};
DEFINE_OPCODE(STR_IMM, 0b011)
struct STRUCT_A64(STR_IMM) {
DEFINE_STRUCT_A64(STR_IMM) {
InstA64 imm12:12;
InstA64 rt:4;
InstA64 rn:4;
......@@ -166,7 +172,7 @@ struct STRUCT_A64(STR_IMM) {
DEFINE_OPCODE(BR_BLR_RET_1, 0b110101100)
DEFINE_OPCODE(BR_BLR_RET_2, 0b11111000000)
DEFINE_OPCODE(BR_BLR_RET_3, 0b00000)
struct STRUCT_A64(BR_BLR_RET) {
DEFINE_STRUCT_A64(BR_BLR_RET) {
InstA64 opcode3:5;
InstA64 rn:5;
InstA64 opcode2:11;
......
......@@ -7,31 +7,48 @@
#include "unit.h"
#define DATA(BITS) STRUCT_DATA_##BITS
#define DEFINE_DATA(BITS) \
struct DATA(BITS) : public Base { \
U##BITS raw_; \
public: \
DATA(BITS)(U##BITS r) { \
raw_ = r; \
} \
};
namespace SandHook {
namespace Asm {
template <typename DType>
class Data : public Unit<DType> {
public:
Data(DType raw) : Unit<DType>(raw) {}
Data(DType raw) : Unit<DType>() {
this->set(raw);
}
inline UnitType unitType() override {
return UnitType::Data;
return UnitType::UnitData;
};
};
class Data16 : public Data<U16> {
DEFINE_DATA(16)
class Data16 : public Data<DATA(16)> {
public:
Data16(U16 raw) : Data(raw) {}
Data16(U16 raw) : Data(DATA(16)(raw)) {}
};
class Data32 : public Data<U32> {
DEFINE_DATA(32)
class Data32 : public Data<DATA(32)> {
public:
Data32(U32 raw) : Data(raw) {}
Data32(U32 raw) : Data(DATA(32)(raw)) {}
};
class Data64 : public Data<U64> {
DEFINE_DATA(64)
class Data64 : public Data<DATA(64)> {
public:
Data64(U64 raw) : Data(raw) {}
Data64(U64 raw) : Data(DATA(64)(raw)) {}
};
}
......
......@@ -6,6 +6,7 @@
#define SANDHOOK_INSTRUCTION_H
#include "unit.h"
#include "label.h"
//aarch64
typedef U32 InstA64;
......@@ -36,23 +37,22 @@ namespace SandHook {
namespace Asm {
template <typename Inst>
class Instruction : public Unit<Inst> {
class Instruction : public Unit<Inst>, public LabelBinder {
public:
Instruction() {}
Instruction(Inst *inst) : Unit<Inst>(inst) {}
UnitType unitType() override {
return UnitType::Inst;
return UnitType::UnitInst;
};
virtual InstType instType() {
return unkownInst;
return unknowInst;
}
virtual Arch arch() {
return unkownArch;
return unknowArch;
}
virtual U32 instCode() {
......@@ -63,19 +63,35 @@ namespace SandHook {
return false;
}
virtual bool unknow() {
return false;
}
inline bool isValid() const {
return valid;
}
virtual void onOffsetApply(Off offset) {}
void onLabelApply(void *pc) override {
onOffsetApply((Addr)pc - (Addr)this->getPC());
}
inline void bindLabel(Label &l) {
label = &l;
l.addBinder(this);
}
virtual void decode(Inst* inst) {}
virtual void assembler() {}
protected:
bool valid = true;
Label* label = nullptr;
};
class Void : public Unit<None> {
class Void : public Unit<Base> {
public:
Void(U32 size) : size_(size) {}
......
......@@ -11,12 +11,12 @@
namespace SandHook {
namespace Asm {
virtual class LabelBinder {
class LabelBinder {
public:
virtual void bindLabel(void* pc) = 0;
virtual void onLabelApply(void* pc) = 0;
};
class Label : public Unit<None> {
class Label : public Unit<Base> {
public:
Label() {}
......@@ -24,7 +24,7 @@ namespace SandHook {
Label(void *pc) : pc(pc) {}
inline UnitType unitType() override {
return UnitType::Label;
return UnitType::UnitLabel;
}
inline U32 size() override {
......@@ -47,17 +47,16 @@ namespace SandHook {
binders.push_back(binder);
}
inline void bindLabel(void* pc) {
setPC(pc);
inline void bindLabel() {
std::list<LabelBinder*>::iterator binder;
for(binder = binders.begin();binder != binders.end(); ++binder) {
(*binder)->bindLabel(pc);
(*binder)->onLabelApply(pc);
}
}
private:
void* pc;
std::list<LabelBinder*> binders = std::list();
std::list<LabelBinder*> binders = std::list<LabelBinder*>();
};
}
......
......@@ -16,7 +16,7 @@ namespace SandHook {
public:
Unit() {
if (unitType() != Void) {
if (unitType() != UnitVoid) {
raw = reinterpret_cast<Raw *>(malloc(size()));
memset(raw, 0, size());
auto_alloc = true;
......@@ -42,12 +42,30 @@ namespace SandHook {
*this->raw = raw;
}
inline void set(Raw* raw) {
if (auto_alloc) {
free(this->raw);
auto_alloc = false;
}
this->raw = raw;
}
inline void copy(void* dest) {
memcpy(dest, getPC(), size());
}
inline void move(Raw* dest) {
memcpy(dest, raw, size());
if (auto_alloc) {
free(raw);
auto_alloc = false;
}
raw = dest;
}
virtual UnitType unitType() {
return UnitType::Unkown;
return UnitType::UnitUnknow;
};
virtual U32 size() {
......
......@@ -2,3 +2,34 @@
// Created by swift on 2019/5/10.
//
#include <assembler.h>
using namespace SandHook::Assembler;
using namespace SandHook::Asm;
void CodeContainer::append(Unit<Base> *unit) {
units.push_back(unit);
switch (unit->unitType()) {
case UnitLabel:
labels.push_back((Label*)unit);
break;
default:
curPc += unit->size();
}
if (unit->unitType() == UnitData) {
unit->move((Base*)codeBuffer->getBuffer(unit));
} else if (unit->unitType() != UnitLabel) {
unit->set((Base*)codeBuffer->getBuffer(unit));
}
}
void CodeContainer::commit() {
std::list<Label*>::iterator label;
for(label = labels.begin();label != labels.end(); ++label) {
(*label)->bindLabel();
}
}
void *CodeBuffer::getBuffer(Unit<Base> *unit) {
return nullptr;
}
......@@ -5,8 +5,14 @@
#ifndef SANDHOOK_NH_ASSEMBLER_H
#define SANDHOOK_NH_ASSEMBLER_H
#include "label.h"
#include "instruction.h"
#include "data.h"
namespace SandHook {
using namespace Asm;
namespace Assembler {
class Assembler {
......@@ -14,7 +20,21 @@ namespace SandHook {
};
class CodeBuffer {
public:
void* getBuffer(Unit<Base>* unit);
};
class CodeContainer {
public:
void append(Unit<Base>* unit);
void commit();
private:
void* startPc = nullptr;
Addr curPc = 0;
Addr maxSize = 0;
std::list<Unit<Base>*> units = std::list<Unit<Base>*>();
std::list<Label*> labels = std::list<Label*>();
CodeBuffer* codeBuffer = nullptr;
};
......
......@@ -33,15 +33,15 @@ const Addr PAGE_SIZE = 2 << PAGE_OFFSET;
enum Arch {
arm32,
arm64,
unkownArch
unknowArch
};
enum UnitType {
Inst,
Data,
Label,
Void,
Unkown
UnitInst,
UnitData,
UnitLabel,
UnitVoid,
UnitUnknow
};
enum InstType {
......@@ -49,7 +49,7 @@ enum InstType {
thumb16,
thumb32,
A64,
unkownInst
unknowInst
};
template <int SizeInBits>
......@@ -71,7 +71,7 @@ struct Unsigned<64> {
};
class None {};
struct Base {};
template <typename T>
T AlignDown(T pointer,
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment