hi there, i've got a question about how to get the kernel's address, here it comes:



KernelAdress [color=#FF0000]dd[/color] ?

StartOfYourProgram:
[color=#0000FF]mov[/color] ecx,[esp] [color=#008000]; Return adress of call from[/color]
[color=#008000]; CreateProcess[/color]
GetKrnlBaseLoop: [color=#008000]; Get Kernel32 module base adress[/color]
[color=#0000FF]xor[/color] edx,edx [color=#008000];[/color]
[color=#0000FF]dec[/color] ecx [color=#008000]; Scan backward[/color]
[color=#0000FF]mov[/color] dx,[ecx+03ch] [color=#008000]; Take beginning of PE header[/color]
[color=#0000FF]test[/color] dx,0f800h [color=#008000]; Is it a PE header ?[/color]
[color=#0000FF]jnz[/color] GetKrnlBaseLoop [color=#008000]; No, forget about it[/color]
[color=#0000FF]cmp[/color] ecx,[ecx+edx+34h] [color=#008000]; Compare current adress with the[/color]
[color=#008000]; address that PE should be loaded at[/color]
[color=#0000FF]jnz[/color] GetKrnlBaseLoop [color=#008000]; Different ? Search again[/color]
[color=#0000FF]mov[/color] [KernelAdress+ebp],ecx [color=#008000]; ecx hold KernelBase... Store it[/color]


Now the question is, what's the meaning of this line:

test dx,0f800h ; Is it a PE header ?

What's 0f800h? I can't get the idea, why not 5045h("PE")?
Posted on 2003-04-16 06:46:00 by pazuluo
pazuluo,

Here is a quick way to get the base of kernel:




.386
.model flat,stdcall
option casemap:none

include \masm32\include\windows.inc
include \masm32\include\kernel32.inc
include \masm32\include\masm32.inc
includelib \masm32\lib\kernel32.lib
includelib \masm32\lib\masm32.lib

.data?
buffer db 12 dup(?)
.code
start:
mov ecx, [esp + 9 * 4]
@@: dec ecx
movzx edx, WORD PTR [ ecx + 03CH ]
cmp ecx, [ ecx + edx + 034H ]
jnz @B
invoke dw2hex,ecx,addr buffer
invoke StdOut,addr buffer
invoke ExitProcess,0
end start



This trick is used by Mob:

http://www.asmcommunity.net/board/showthread.php?s=&postid=14865.msg14865

Regards,

Vortex
Posted on 2003-04-16 08:11:15 by Vortex
nice trick but,

what can i do then with the kernel address ?
Posted on 2003-04-16 16:03:19 by Bit7
If you have the Kernel address you can get the LoadLibrary and GetProcAddress functions then call api's without libraries. Very useful for injecting code.
Posted on 2003-04-16 16:15:53 by donkey
Votex,

Isn't this even quicker, at least to write?

386

.model flat,stdcall
option casemap:none

include \masm32\include\windows.inc
include \masm32\include\kernel32.inc
include \masm32\include\masm32.inc
includelib \masm32\lib\kernel32.lib
includelib \masm32\lib\masm32.lib

.data?
buffer db 12 dup(?)
.code
start:
invoke GetModuleHandle,SADD('Kernel32.dll')
invoke dw2hex,eax,addr buffer
invoke StdOut,addr buffer
invoke ExitProcess,0
end start

The difference to pazuluo's code is that the KernelAdress label of placeholder is located in the .code section, not the .data? section. It also indicate that ebp is a startpoint of a foreign code in another process or am I wrong? However I prefer this code
    mov ecx,[esp] ;return address

and ecx,0fffffff0h ;align
@@:
cmp word ptr [ecx],"ZM" ;find IMAGE_DOS_SIGNATURE
je @F
sub ecx,4
jmp @B
@@:
mov [KernelAdress+ebp],ecx ;Store Kernel Base address


Regard
Posted on 2003-04-16 16:23:45 by minor28
pazuluo,
I use the fastest method (without loops and additional garbage)
You can use it where you want rather then at "StartOfYourProgram":


assume fs:nothing

mov eax, fs:[30h]
mov edx, 0B8h
mov ecx, [eax+30h]
test eax, eax
jns KI_1
mov ebx, [eax+34h]
test ecx, ecx
jnz KI_2
KI_1:
mov eax, [eax+0Ch]
sub edx, 0B0h
mov eax, [eax+1Ch]
mov ebx, [eax]
KI_2:
mov eax, [ebx+edx] ; and finally we get the Kernel address in eax

Regards,
Lingo
Posted on 2003-04-16 20:00:36 by lingo12
Thanks all! :)

I know the code I posted is very very slooooooow... So I won't use it to get the kernel's address, but I still don't know the meaning of 0f800h:stupid: , could anybody give me some tips of it? :)


To lingo12:
Your method is very good, but I guess it can only run on the Win NT/2k/XP platform, right? :)
Posted on 2003-04-16 20:47:59 by pazuluo
No
Posted on 2003-04-16 20:49:37 by lingo12

No


Thanks! :)

I've posted the files here, could anybody trace it and tell me the meaning of 0f800h? Thanks a lot!

Yesterday I used OllyDbg 1.09 to trace the program, but too many loop in it...:confused: :confused:
Posted on 2003-04-16 21:15:32 by pazuluo
I think 0f800h is where the default code segment is loaded, could be wrong though
Posted on 2003-04-16 21:35:43 by donkey
thx donkey, bu what do you mean for "injecting code" ? To owerwrite some part of the apie's or replace some of them? .Seems that moving inside the kernel is a most used thing... Could someone show me a little example (if exist) of how to use this base address.
Posted on 2003-04-17 02:05:27 by Bit7
I'm pretty sure that talking too much about injecting code would violate some of the rules of the board, enough to say that it is extensively used in v*r*i.
Posted on 2003-04-17 02:08:05 by donkey
Lingo,

Are you enough brave to tell us the source of your algo?
I think,it doesn't belong to you.:grin:
Posted on 2003-04-17 02:29:33 by Vortex
Just a question lingo,

What does your edx do?
Posted on 2003-04-17 03:21:29 by roticv
If you have the Kernel address you can get the LoadLibrary and GetProcAddress functions then call api's without libraries. Very useful for injecting code.


donkey

What is the meaning of "injecting code". I haven't been able to figure it out.

Regards
Posted on 2003-04-17 03:28:40 by minor28
minor28,

http://www.asmcommunity.net/board/showthread.php?s=&postid=97414.msg97414

About your algo,yes I think it's possible.
Posted on 2003-04-17 03:32:47 by Vortex
Thank you all guys, i just want to know the meaning of 0f800h :)

Regards.
Posted on 2003-04-17 03:38:48 by pazuluo
Vortex

I read the thread from your link. As I understod it you put your own code in another author's exe in the PE last section, change the entrypoint to your code and then go back to the original exe. Is that legal?

Regards
Posted on 2003-04-17 04:21:15 by minor28

pazuluo,
I use the fastest method (without loops and additional garbage)
You can use it where you want rather then at "StartOfYourProgram":


assume fs:nothing

mov eax, fs:[30h]
mov edx, 0B8h
mov ecx, [eax+30h]
test eax, eax
jns KI_1
mov ebx, [eax+34h]
test ecx, ecx
jnz KI_2
KI_1:
mov eax, [eax+0Ch]
sub edx, 0B0h
mov eax, [eax+1Ch]
mov ebx, [eax]
KI_2:
mov eax, [ebx+edx] ; and finally we get the Kernel address in eax

Regards,
Lingo
Hi lingo. Do you have also code to emulate GetProcAddress?
Posted on 2003-04-17 04:45:47 by Bugs' Bounty Hunter
; ebp holds a delta offset


szGetProcAddress db "GetProcAddress",0
GPASIZE = $ - szGetProcAddress
ApiCounter dd 0

GetGetProcAddressAddress proc
and dword ptr [ebp + ApiCounter],0
mov edi,dword ptr [eax+3Ch] ; kernel PE hdr
add edi,eax ; add image base
assume edi:ptr IMAGE_NT_HEADERS
mov edi,[edi].OptionalHeader.DataDirectory.VirtualAddress
add edi,eax
assume edi:ptr IMAGE_EXPORT_DIRECTORY
mov ecx,[edi].NumberOfNames
mov esi,[edi].AddressOfNames


add esi,eax
xchg eax,ebx
MatchLp:

lodsd
add eax,ebx

push ecx
push edi
push esi

push GPASIZE
pop ecx
lea edi,[ebp+szGetProcAddress]
mov esi,eax
repz cmpsb

pop esi
pop edi

jecxz GPA_found

inc dword ptr [ebp + ApiCounter]

pop ecx
dec ecx
jnz MatchLp

xor eax, eax ; error
ret

GPA_found:

mov esi,[edi].AddressOfNameOrdinals
pop ecx


mov ecx,dword ptr [ebp + ApiCounter]
shl ecx,1
add esi,ecx
add esi,ebx
xor eax,eax
lodsw
shl eax,2

add eax,[edi].AddressOfFunctions
mov esi,eax
add esi,ebx
lodsd
add eax,ebx

assume edi :nothing

ret
GetGetProcAddressAddress endp
Posted on 2003-04-17 05:14:20 by Axial