Показаны сообщения с ярлыком KPRCB. Показать все сообщения
Показаны сообщения с ярлыком KPRCB. Показать все сообщения

воскресенье, 25 декабря 2011 г.

scheduler structures on windows 64bit

а вот например как всем давно известно (c) под 64битными версиями windows все структуры планировщика теперь расположены в KPRCB. Соотв-но определение subj мистическим образом сводится все к той же задаче определения версии KPRCB
Нужны же нам смещения следующих полей:
  • список WaitListHead
  • ReadySummary
  • массив LIST_ENTRY DispatcherReadyListHead
  • список DeferredReadyListHead
Попробуем найти чего-нть из этого списка с помощью стат. анализа кода. Все примеры кода нагло позаимствованы из ядра windows 8, KPRCB он нее можно посмотреть тут

DeferredReadyListHead

Обращение к этому полю встречается примерно в 24 функциях, среди которых есть и немало экспортируемых. На мой вкус проще всего посмотреть начало KeAlertThread:
  mov     rbx, gs:20h
  xor     esi, esi
  lea     r13d, [rax-1]
  lock bts qword ptr [rdi+40h], 0
  jb      loc_140034F29
  mov     r8b, r14b
  mov     rdx, rdi
  mov     rcx, rbx
  call    KiAlertThread
  mov     qword ptr [rdi+40h], 0
  cmp     qword ptr [rbx+2C88h], 0 ;
KPRCB.DeferredReadyListHead
  mov     r15b, al
  jnz     short loc_140034E7B


Если поле DeferredReadyListHead содержит не NULL, то ниже по коду вызывается KiProcessThreadWaitList, из которой можно узнать еще и смещение KTHREAD.WaitListEntry:
     mov     r15, [rcx+2C88h] ; KPRCB.DeferredReadyListHead
     and     qword ptr [rcx+2C88h], 0 ; KPRCB.DeferredReadyListHead = NULL
     mov     r12d, r8d
     mov     r13, rcx
     lea     rsi, [r15-0D8h] ; offsetof(KTHREAD.WaitListEntry)

ReadySummary

Проще всего ищется в начале функции NtYieldExecution:
  sub     rsp, 20h
  mov     eax, gs:5218h   ; KPRCB.ReadySummary
  test    eax, eax
  jnz     short loc_14004A9EE

Поскольку в данном случае чтение идет не из KPRCB, то нужно вычесть размер KPCR

вторник, 13 декабря 2011 г.

определение версии KPRCB 2

я тут писал уже как-то про сие невинное занятие, но внезапно выяснилось что метод не работает например под windows 8 - под ней KeIsExecutingDpc выглядит так:
  mov     eax, large fs:2354h
  and     eax, 10001h
  retn

это дает нам смещение на DpcRoutineActive равным 0x2234, что неверно

Но есть и еще один способ - например можно узнать смещение поля WorkerRoutine. В экспортируемой ф-ции KiIpiServiceRoutine есть примерно такой кусочек кода:
  mov     eax, [edx+2170h]
  mov     edx, [esp+24h+arg_0]
  mov     [esi+2128h], edx
  call    eax

0x2170 - это и есть наше искомое смещение. К недостаткам метода относится его применимость только для 32 бит, потому что под 64битными системами ф-ция KiIpiServiceRoutine не экспортируется
Также работает он только начиная с xp - под w2k ф-ция KiIpiServiceRoutine пуста

пятница, 5 августа 2011 г.

определение версии KPRCB

а вот нас тут спросили давеча - нету ли другого способа узнать какая именно версия KPRCB используется кроме как по версии windows ?

Такой способ есть.Например есть такая экспортируемая кернелом ф-ция - KeIsExecutingDpc. Она возвращает значение KPRC.PrcbData.DpcRoutineActive. Выглядит на разных windows примерно так (я приведу только самую первую и нужную инструкцию)

w2k/xp/w2k3
  movzx   eax, byte ptr ds:0FFDFFA7Ah


Учитывая что по адресу FFDFF000 хранится KPCR для процессора 0, а сама структура KPCR имеет размер 0x120 байт, получаем что смещение поля DpcRoutineActive равно 0x95A.

vista/w7
  mov     eax, large fs:1A54h

Тут тоже все просто - в fs расположен KPRC, cмещение поля DpcRoutineActive равно 0x1934.

Соотв-но можно составить табличку смещений поля DpcRoutineActive для всех поддерживаемых версий KPRCB и простым дизасмом ф-ции KeIsExecutingDpc определить, какая версия KPRCB используется

четверг, 4 августа 2011 г.