/*
文件名:HackerClass.nut
路径:Dps_A/BaseClass/HackerClass/HackerClass.nut
创建日期:2024-09-22	11:33
文件用途:黑客类
*/
class _Hacker {
    HookTable = null;

    HookJumpMemoryTable = null;

    __strtol__function__address__ = null;

    NextReturnAddress = null;
    CpuContext = null;

    

    constructor() {
        HookTable = {};
        HookJumpMemoryTable = {};
    }


    function UnLoadHook(AddressStr) {
        Sq_DeHookFunc(HookTable[AddressStr]);
    }

    function LoadHook(AddressStr, ArgumentArr, EnterFunc, LeaveFunc) {
        //如果已经HOOK过 需要先卸载原来的HOOK
        if (HookTable.rawin(AddressStr)) {
            UnLoadHook(AddressStr);
            print("地址: " + AddressStr + " 已经装载了Hook,本次操作将会卸载之前的Hook在执行。")
        }

        local Controler = Sq_HookFunc(S_Ptr(AddressStr), ArgumentArr, EnterFunc, LeaveFunc);
        HookTable.rawset(AddressStr, Controler);
    }


    function HexStringToInt(Str) {
        if (!__strtol__function__address__) __strtol__function__address__ = Module.getExportByName(null, "strtol");
        local Ret = Sq_CallFunc(__strtol__function__address__, "int", ["pointer", "pointer", "int"], Memory.allocUtf8String(Str).C_Object, Memory.alloc(0), 16);
        return Ret;
    }

    function AsmGenerateMcd(...) {
        local CodeArr = [];
        local CurCode = "";
        try {
            foreach(Str in vargv) {
                CurCode = Str;
                local Code = Sq_Asmjit_Compile(Str);
                CodeArr.extend(Code);
            }
        } catch (exception) {
            error("汇编代码有误,错误行: " + CurCode);
        }
        return CodeArr;
    }

    function InsertCode(Address, Code) {
        //置入代码的大小
        local CodeSize = Code.len();
        //申请一块内存
        local MemBuffer = Memory.alloc(CodeSize);
        //记录
        HookJumpMemoryTable.rawset(Address, MemBuffer);
        //写入置入的代码
        MemBuffer.writeByteArray(Code);

        //计算偏移
        local Offset = Sq_PointerOperationPointer(MemBuffer.C_Object, Sq_PointerOperation(S_Ptr(Address), 5, "+"), "-");
        local Str = "" + Offset;
        Str = Str.slice(Str.find("0x") + 4, -1);
        local JumpCodeArr = [0xE9];
        for (local i = 0; i< 4; i++) {
            local Index = -2 * (i + 1);
            local StrBuffer = "0x" + (Str.slice(Index).slice(0, 2));
            JumpCodeArr.push(HexStringToInt(StrBuffer));
        }
        Sq_WriteByteArr(S_Ptr(Address), JumpCodeArr);
    }
}

function _Haker_SetNextReturnAddress(Address) {
    local Buffer = "" + Address;
    Haker.NextReturnAddress = Buffer.slice(Buffer.find("0x") + 2, -1);

}
function _Haker_SetCpuContext(tab) {
    Haker.CpuContext = tab;

}
//初始化Hacker
Haker <- _Hacker();