Is there is a way to find out the number of parameters a function expects that is exported from a dll?
Posted on 2003-12-08 04:52:23 by Odyssey
If you disassembe the proc you can look at the ret instruction to see how many bytes it takes to restore the stack. Generally paramters are DWORD in size so dividing by four gives the number of parameters. Some DLL's have the procs listed in the "decorated" form _procname@4 where @4 is the number of bytes pushed onto the stack, same formula to tell how many paramters are passed (/4). Could be another simpler way but that's what I use.
Posted on 2003-12-08 04:57:15 by donkey

Thanks for the tip. So what I need to do is to get the address of the function and look for the ret opcode? :)
Posted on 2003-12-08 05:19:04 by Odyssey
Yeah, it'll be something like RET 10, that will be 16 bytes or 4 DWORD parameters. Another dirty way that I do it is this....

PrintDec esp
Call DllFunction
PrintDec esp

The difference will give you the number of bytes.
Posted on 2003-12-08 05:29:50 by donkey
hi silky. it should be the "retn n" instruction if im not wrong. it is used to balance the stack as far as i remember from long back. use pe explorer it shows you exactly what you want to know. an example diasm:

;;for a function _func@4:
push ebp
mov ebp, esp
pop ebp
retn 04 ;; <---- check this value - this func has one param

donkey's trick is good if you know the function does no harm. dont try it on file system formatting functions for instance
Posted on 2003-12-08 05:37:01 by evil__donkey
Use IDA pro. The disassembly will tell you how many parameters to be passed.
Posted on 2003-12-08 05:38:39 by roticv
Actually PEBrowse Pro does it also now that I think about it, and it's free:
Posted on 2003-12-08 05:41:26 by donkey
where do i get ida pro. i tried finding but didn't get it
Posted on 2003-12-08 05:42:04 by evil__donkey

It's a commerical product. Well worth its price in my opinion.There is also a free version by datarescue (Do not know whether they are still hosting it or not).
Posted on 2003-12-08 05:45:45 by roticv
Yeah, IDA pro is a very nice looking app, I just could never justify $520 Can. to buy it. I slog though the hard way with PEBrowse pro, hopefully I'll be replacing it soon with Rigda ;)
Posted on 2003-12-08 06:02:21 by donkey
donkey pebrowse pro dont show the api functions i am calling? btw it is good app. ridga is something i want to work on too.
Posted on 2003-12-08 06:06:39 by evil__donkey
Can't use a disassembler or PE viewer. I am going to write a program that generates function prototypes for functions in a dll. So thats why I need the info.
Posted on 2003-12-08 06:20:21 by Odyssey
Sure it shows exported functions:
Posted on 2003-12-08 06:21:22 by donkey

Can't use a disassembler or PE viewer. I am going to write a program that generates function prototypes for functions in a dll. So thats why I need the info.

You might want to use the call without parameters method then correct the stack afterwards, that will give you a way to find the number of parameters

mov edi,esp
CALL function
sub edi,esp
neg edi
add esp, edi
shr edi,2

edi has the number of parameters

or something like that, might have got the order flubbed.
Posted on 2003-12-08 06:27:09 by donkey
donkey not the exported functions the functions that are being called in my dll functions for example

;; pe explorer output
;; begin myproc
push ebp
mov ebp, esp
call GetVersion ; this func gets displayed as some number
pop ebp
retn 0h
;; end myproc
Posted on 2003-12-08 06:45:13 by evil__donkey
That's because you do not need to pass any parameters or that the calling convention is C and not stdcall.
Posted on 2003-12-08 06:47:33 by roticv
PE Explorer:

push ebp
mov ebp,esp
push edx
push [ebp+08h]
call jmp_kernel32.dll!GetFileAttributesA
mov edx,eax
cmp edx,FFFFFFFFh
jnz L10001353
call jmp_kernel32.dll!GetLastError
cmp eax,00000002h
jnz L10001353
mov eax,00000000h
jmp L10001367
test edx,00000010h
jz L10001362
mov eax,00000000h
jmp L10001367
mov eax,00000001h
pop edx
retn 0004h

PE Browse output:

Disassembly of Function GetFileExists (0x1000132F)
; *** GetFileExists (5) ***
0x1000132F: 55 push ebp
0x10001330: 8BEC mov ebp,esp
0x10001332: 52 push edx
0x10001333: FF7508 push dword ptr [ebp+0x8] ; ARG:0x8
0x10001336: E847030000 call 0x10001682
0x1000133B: 8BD0 mov edx,eax
0x1000133D: 83FAFF cmp edx,0xff
0x10001340: 7511 jnz 0x10001353 ; (*+0x13)
0x10001342: E841030000 call 0x10001688
0x10001347: 83F802 cmp eax,0x2
0x1000134A: 7507 jnz 0x10001353 ; (*+0x9)
0x1000134C: B800000000 mov eax,0x0
0x10001351: EB14 jmp 0x10001367 ; (*+0x16)
0x10001353: F7C210000000 test edx,0x10 ; <==0x1000134A(*-0x9), 0x10001340(*-0x13)
0x10001359: 7407 jz 0x10001362 ; (*+0x9)
0x1000135B: B800000000 mov eax,0x0
0x10001360: EB05 jmp 0x10001367 ; (*+0x7)
0x10001362: B801000000 mov eax,0x1 ; <==0x10001359(*-0x9)
0x10001367: 5A pop edx ; <==0x10001360(*-0x7), 0x10001351(*-0x16)
0x10001368: C9 leave
0x10001369: C20400 ret 0x4
Posted on 2003-12-08 06:56:20 by evil__donkey
Hi all,

Well Ody, if you are building such a tool then please send it over to me too when you finish making it. BTW, please remember a few points. There are aliases in dlls, so you'll have to scan for them to for example, in some earlier post i had demonstrated that you can use aliases for dll functions, which may be exported as undecorated, decorated, or both. So check for name collisions. For example, a dll i'm working on right now has these two functions as aliases:


both these functions are exported. Go here if you want more info:

Posted on 2003-12-08 07:04:16 by Art Sands