Перейти к содержанию
  • запись
    101
  • комментариев
    110
  • просмотров
    6 597

Наработки по сканеру указателей основанному на отладке

Авторизация  
partoftheworlD

184 просмотра

Разработка этого плагина началась с того, что Dark Souls 3 начал выеживаться, а именно не работал сканер указателей, в целом этот "плагин" бесполезная, но точная(в теории) вещь для большинства игр.
Может быть кто-то более опытный в Lua захочет его доделать. Осталось сделать 3 пункта:

  1. Нормальный парсинг инструкций

 

Парсинг...ну что тут сказать, в Lua паттерны это какой-то regex после авиакатастрофы попавший в аварию на машине скорой.

Картинки по запросу мем разводит руки

 

 

Спойлер

offsets          = {}
search_array     = {}
address          = 0x0042578F

addr_range_start = 0x1
addr_range_end   = 0x2

src              = address
onBreakpoint_idx = 1

-- Глубина поиска смещений
struct_depth     = 3

low_regs         = {"eax", "ebx", "ecx", "edx", "edi", "esi", "rax", "rbx", "rcx", "rdx", "rdi", "rsi"," r8"," r9", "r10", "r11", "r12", "r13", "r14", "r15"}
global_regs      = {EAX, EBX, ECX, EDX, EDI, ESI, RAX, RBX, RCX, RDX, RDI, RSI, R8, R9, R10, R11, R12, R13, R14, R15}


function parse_output(debug_output)
    local result = {}
    -- Парсим инструкцию, чтобы разбить на блоки dst, src offset
    result[1] = string.match(debug_output, "[re][abcds0-90-9]+[x]") --base
    --for j in string.gmatch(debug_output, "r[0-9]+") do result[1] = j end
    result[2] = string.match(debug_output, "[+-][0-9A-F]+") --offset
    if not result[2] then
        result[2] = '+0'
        print(result[2])
    else
        print(result[2])
    end
    print(defineGRegs(result[1]))
    src     = search_addr("0x192c7c0") -- адрес для поиска указателя
end

function debugger_onBreakpoint()
    -- Обновляем контекст на всякий случай
    debug_getContext(0)
    for r = 1, #global_regs do
        -- Проверяем, есть ли указанный адрес в регистрах или регионе памяти
        if (global_regs[r] == src and global_regs[r] <= addr_range_start or global_regs[r] >= addr_range_end) then
            offsets[#offsets+1] = global_regs[r]
        end
    end
    -- Парсим текущую инструкцию, чтобы получить смещение и новый адрес для установки бряка
    if targetIs64Bit() then
        parse_output(disassemble(RIP))
    else
        parse_output(disassemble(EIP))
    end

    debug_removeBreakpoint(address)

    local type = 0
    if targetIs64Bit() then
        type = 8
    else
        type = 4
    end

    src = search_array[onBreakpoint_idx+1]
    debug_setBreakpoint(src, type, bptAccess)
    return 1
end

function search_addr(addr)
    local m_MemScan   = createMemScan()
    local m_FoundList = createFoundList(m_MemScan)
    local idx         = 0

    if targetIs64Bit then
        m_MemScan.firstScan(soExactValue, vtQword, rtRounded, addr, 0, 0, 0xffffffffffffffff, "+W-C", fsmAligned, "8", true, false, false, false)
    else
        m_MemScan.firstScan(soExactValue, vtDword, rtRounded, addr, 0, 0, 0xffffffffffffffff, "+W-C", fsmAligned, "4", true, false, false, false)
    end

    m_MemScan.waitTillDone()
    m_FoundList.initialize()

    for i = m_FoundList.Count / 2 + 1, m_FoundList.Count do
        search_array[idx+1] = m_FoundList.Address[i]
    end

    m_MemScan.destroy()
    m_FoundList.destroy()
end

function clean_bplist()
    for _,v in ipairs(debug_getBreakpointList()) do debug_removeBreakpoint(v) end
end

function defineGRegs(reg)
    for i = 1, #low_regs do
        if low_regs[i] == reg then
        return global_regs[i]
        end
    end
end

function main()
    debugProcess()
    -- Очищаем старые брейкпоинты перед началом
    clean_bplist()
    debug_setBreakpoint(src, 1, bptExecute)
end

main()

 

 

  • Понравилось 1
  • Плюс 1
Авторизация  


3 Комментария


Рекомендуемые комментарии

Проблема с ассоциативным списком решена с помощь костылей. (defineGRegs)

 

Код в принципе рабочий, но я бы переписал, а именно тот участок кода, который устанавливает бряк на найденный регистр, это не совсем правильно.
Правильнее будет искать указатель на этот адрес, через поиск и уже после ставить бряк на найденный указатель, чтобы получить следующее смещение, если код не переписать он может зациклится на одной инструкции, если нет выхода на структуру выше.

Поделиться этим комментарием


Ссылка на комментарий

Для публикации сообщений создайте учётную запись или авторизуйтесь

Вы должны быть пользователем, чтобы оставить комментарий

Создать учетную запись

Зарегистрируйте новую учётную запись в нашем сообществе. Это очень просто!

Регистрация нового пользователя

Войти

Уже есть аккаунт? Войти в систему.

Войти
×

Важная информация

Находясь на нашем сайте, Вы автоматически соглашаетесь соблюдать наши Условия использования.