flat assembler
Message board for the users of flat assembler.

Index > Windows > Win32 calls. Register usage?

Goto page Previous  1, 2, 3, 4 ... 9, 10, 11  Next
Author
Thread Post new topic Reply to topic
Azu



Joined: 16 Dec 2008
Posts: 1159
Azu 07 Jun 2009, 08:31
f0dder wrote:
Azu wrote:
revolution wrote:
To what end? It is only one function anyway. No need to invent a whole new calling convention for it.
They felt the need to make "a whole new calling convention" for this "one little function", so they may as well do it right..
No, they went with standard cdecl.
..which only exists for this one function.
Post 07 Jun 2009, 08:31
View user's profile Send private message Send e-mail AIM Address Yahoo Messenger MSN Messenger ICQ Number Reply with quote
f0dder



Joined: 19 Feb 2004
Posts: 3175
Location: Denmark
f0dder 07 Jun 2009, 08:35
Azu wrote:
f0dder wrote:
Azu wrote:
revolution wrote:
To what end? It is only one function anyway. No need to invent a whole new calling convention for it.
They felt the need to make "a whole new calling convention" for this "one little function", so they may as well do it right..
No, they went with standard cdecl.
..which only exists for this one function.
Get your head out of the bushes and look around Smile

_________________
Image - carpe noctem
Post 07 Jun 2009, 08:35
View user's profile Send private message Visit poster's website Reply with quote
Azu



Joined: 16 Dec 2008
Posts: 1159
Azu 07 Jun 2009, 08:38
f0dder wrote:
Azu wrote:
f0dder wrote:
Azu wrote:
revolution wrote:
To what end? It is only one function anyway. No need to invent a whole new calling convention for it.
They felt the need to make "a whole new calling convention" for this "one little function", so they may as well do it right..
No, they went with standard cdecl.
..which only exists for this one function.
Get your head out of the bushes and look around Smile
I did. Couldn't find any other functions in Windows that don't clean up after themselves. Since you obviously know more then me, why don't you just save both of us time by naming them (if there really are any others)? Confused
Post 07 Jun 2009, 08:38
View user's profile Send private message Send e-mail AIM Address Yahoo Messenger MSN Messenger ICQ Number Reply with quote
LocoDelAssembly
Your code has a bug


Joined: 06 May 2005
Posts: 4624
Location: Argentina
LocoDelAssembly 07 Jun 2009, 14:35
Quote:

BTW why does this forum keep forgetting to notify me when a reply is posted? I have to keep re-checking the box over and over.. =/
Go to your profile and enable "Always notify me of replies:"

Quote:
I did. Couldn't find any other functions in Windows that don't clean up after themselves. Since you obviously know more then me, why don't you just save both of us time by naming them (if there really are any others)?
All the functions in CRTDLL.DLL and MSVCRT.DLL for example. Microsoft haven't invented nothing, they used an already existing calling convention called cdecl because that one already handled varargs correctly. They even borrowed wsprintf from sprintf of C language (also available in the aforementioned DLLs), which turns out to be where cdecl comes from.


Last edited by LocoDelAssembly on 07 Jun 2009, 14:43; edited 1 time in total
Post 07 Jun 2009, 14:35
View user's profile Send private message Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20448
Location: In your JS exploiting you and your system
revolution 07 Jun 2009, 14:39
Azu wrote:
Couldn't find any other functions in Windows that don't clean up after themselves. Since you obviously know more then me, why don't you just save both of us time by naming them (if there really are any others)? Confused
There is more to this world than just Windows. You didn't really believe that MS invented CDECL just for one function? Did you? Question Confused
Post 07 Jun 2009, 14:39
View user's profile Send private message Visit poster's website Reply with quote
Azu



Joined: 16 Dec 2008
Posts: 1159
Azu 07 Jun 2009, 15:23
LocoDelAssembly wrote:
Quote:

BTW why does this forum keep forgetting to notify me when a reply is posted? I have to keep re-checking the box over and over.. =/
Go to your profile and enable "Always notify me of replies:"
Thanks, I don't want notified of all replies though. Just for the threads I asked for notification on.. without it randomly unsubscribing them for no reason after a few days or so.

LocoDelAssembly wrote:
Quote:
I did. Couldn't find any other functions in Windows that don't clean up after themselves. Since you obviously know more then me, why don't you just save both of us time by naming them (if there really are any others)?
All the functions in CRTDLL.DLL and MSVCRT.DLL for example. Microsoft haven't invented nothing, they used an already existing calling convention called cdecl because that one already handled varargs correctly. They even borrowed wsprintf from sprintf of C language (also available in the aforementioned DLLs), which turns out to be where cdecl comes from.
Aren't those DLLs from the C++ redistributable package thing? Wouldn't this topic be in Main or Heap if it was about C++ not Windows? Confused

revolution wrote:
Azu wrote:
Couldn't find any other functions in Windows that don't clean up after themselves. Since you obviously know more then me, why don't you just save both of us time by naming them (if there really are any others)? Confused
There is more to this world than just Windows.
We are talking about Windows, though.. not DOS, or UNIX, not OSX..


revolution wrote:
You didn't really believe that MS invented CDECL just for one function? Did you? Question Confused
Yes.

And if not.. then all the more reason for it to be done right. Very Happy
Post 07 Jun 2009, 15:23
View user's profile Send private message Send e-mail AIM Address Yahoo Messenger MSN Messenger ICQ Number Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20448
Location: In your JS exploiting you and your system
revolution 07 Jun 2009, 15:36
Azu wrote:
Yes [I did think MS invented CDECL just for wsprintf].
In that case you need to read more and make less assumptions about things. Google is your friend. Razz
Azu wrote:
And if not.. then all the more reason for it to be done right. Very Happy
Only you are saying it is not "done right". Others have tried to explain to you why it can't be stdcall, but you keep coming back with the same thing saying that is it "wrong". It is not wrong, it was done because it was necessary. Anyhow, it is not worth so much argument, one function only, with an alternate stdcall version. It is a special case but you don't have to use it if you don't want to. Ignore it, forget about it, don't think about it, don't use it, pretend it doesn't exist, there, problem solved. Cool
Post 07 Jun 2009, 15:36
View user's profile Send private message Visit poster's website Reply with quote
Azu



Joined: 16 Dec 2008
Posts: 1159
Azu 07 Jun 2009, 15:43
revolution wrote:
Azu wrote:
Yes [I think this is the only Windows function that acts this way].
In that case you need to read more and make less assumptions about things. Google is your friend. Razz
I used Google, but couldn't find any other Windows functions like this. According to Wikipedia, C/C++ aren't part of Windows, they actually are operating system independent, so they aren't on topic since this thread is in Windows category.



revolution wrote:
Azu wrote:
And if not.. then all the more reason for it to be done right. Very Happy
Only you are saying it is not "done right". Others have tried to explain to you why it can't be stdcall, but you keep coming back with the same thing saying that is it "wrong". It is not wrong, it was done because it was necessary. Anyhow, it is not worth so much argument, one function only, with an alternate stdcall version. It is a special case but
The only one I see defending it is you, and your only explanation "it must be this way so it can be HLL" makes no sense since wvsprintf and wsprintf are (according to you) both HLL, and wvsprintf doesn't work this way, and wsprintf (which calls wvsprintf) is (according to you) HLL! So I am confused.. Confused


revolution wrote:
you don't have to use it if you don't want to. Ignore it, forget about it, don't think about it, don't use it, pretend it doesn't exist, there, problem solved. Cool
I hate this line of reasoning. When something doesn't make sense, I want to understand what's up with it, especially when lots of the programs I use use it.. >_>
Post 07 Jun 2009, 15:43
View user's profile Send private message Send e-mail AIM Address Yahoo Messenger MSN Messenger ICQ Number Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20448
Location: In your JS exploiting you and your system
revolution 07 Jun 2009, 15:55
But you said you thought cdecl was invented by MS for this one function. It would seem reasonable to search google for cdecl history, not for more Windows functions. That way your assumption could have be quickly confirmed or refuted (in this case refuted).

One function is vararg, the other is not. vararg is not supported by stdcall, so the function can't be stdcall, it falls outside the stdcall standard. You can't implement vararg in stdcall, not possible with HLL code, can't be done. Tricky asm code could do it, but then that is not HLL anymore, so MS won't do it, not sensible to do, not portable to other systems.

As for the non-vararg version: no problem, falls within stdcall standard, easy in HLL. Nothing tricky required. But now YOU have to allocate memory and things to pass the arguments to the function, makes it not so convenient for you.
Post 07 Jun 2009, 15:55
View user's profile Send private message Visit poster's website Reply with quote
LocoDelAssembly
Your code has a bug


Joined: 06 May 2005
Posts: 4624
Location: Argentina
LocoDelAssembly 07 Jun 2009, 16:04
Quote:

Aren't those DLLs from the C++ redistributable package thing?

At least for MSVCRT.DLL I'm sure it comes on a Win95 OSR2 without installing anything else. Yet, even if you were right you are not proving Microsoft invented cdecl at all. They merely copied sprintf to the Windows API and prefixed it with "w" (so you can call it even if you are using C language with no collision problems). cdecl had already solved the problem of handling varargs so they didn't invented a new calling convention to handle this (which would have defeated the purpose a bit because the idea was to copy the sprintf function from C language).
Post 07 Jun 2009, 16:04
View user's profile Send private message Reply with quote
Azu



Joined: 16 Dec 2008
Posts: 1159
Azu 07 Jun 2009, 16:27
revolution wrote:
But you said you thought cdecl was invented by MS for this one function. It would seem reasonable to search google for cdecl history, not for more Windows functions. That way your assumption could have be quickly confirmed or refuted (in this case refuted).
I never said that. I only said that this is the only Windows function that uses it.. thus, this function is the reason they implemented that calling standard. Does not mean they invented it...

revolution wrote:
One function is vararg, the other is not. vararg is not supported by stdcall, so the function can't be stdcall, it falls outside the stdcall standard. You can't implement vararg in stdcall, not possible with HLL code, can't be done. Tricky asm code could do it, but then that is not HLL anymore, so MS won't do it, not sensible to do, not portable to other systems.
But you said that both of those functions are HLL. So obviously it can be done in HLL code. It's nothing complicated anyways, if anything the code would be a LOT simpler with the whole thing just being a standalone vararg function, much more simple then the function it calls (wvsprintf) I think. It would be like this;
;Data
PointerToString db "world",0
PointerToInput "Hello %s! %i is the answer Smile",0
PointerToOutput rb 255

;Callee
push PointerToString
push 42
push PointerToInput
push PointerToOutput
call wsprintf

;Called
wsprintf:
pop ecx
pusha
pop edi
pop esi
LoadLoop
lodsb
test al,al
jz NullChar
cmp al,"%"
je FormatChar
stosb
jmp LoadLoop

FormatChar:
lodsb
cmp al,"i"
jne StringChar
pop eax
;put integer to ascii code here.. to lazy to write it, and doesn't matter for example anyways..
jmp LoadLoop

StringChar:
mov edx,esi
pop esi

StringCharLoop
lodsb
test al,al
jz StringCharLoopNull
stosb
jmp StringCharLoop
StringCharLoopNull
mov esi,edx
jmp LoadLoop
NullChar:
popa
jmp ecx


Surely that way is more easy for a HLL to generate then the stuff it's currently doing? And then the stack is cleaned up after itself, and it is still vararg, and using the normal standard, and not having to piggy back off of the other function..


revolution wrote:
As for the non-vararg version: no problem, falls within stdcall standard, easy in HLL. Nothing tricky required. But now YOU have to allocate memory and things to pass the arguments to the function, makes it not so convenient for you.
But.. it doesn't allocate any memory or anything. It just does this
mov edi, edi
push ebp
mov ebp, esp
lea eax, [ebp+arglist]
push eax ; arglist
push [ebp+arg_4] ; LPCWSTR
push [ebp+arg_0] ; LPWSTR
call wvsprintfW
pop ebp
retn


And anyways what I meant was, vararg is fine, the problem is that it doesn't clean up after itself so programs must have ons of add esp,XXX all over it for no reason. Sad Very bad standard!


Last edited by Azu on 07 Jun 2009, 16:42; edited 2 times in total
Post 07 Jun 2009, 16:27
View user's profile Send private message Send e-mail AIM Address Yahoo Messenger MSN Messenger ICQ Number Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20448
Location: In your JS exploiting you and your system
revolution 07 Jun 2009, 16:34
Your code won't work. edi is the return address and you overwrite your code with stosb. The 'ret' jumps to somewhere not where you expect.

I think you clearly don't understand HOW an HLL works. Like I said, and it is not a mistake, HLL using a stdcall interface cannot implement a vararg function. Once you understand that you will see WHY wsprintf cannot be stdcall.
Post 07 Jun 2009, 16:34
View user's profile Send private message Visit poster's website Reply with quote
Azu



Joined: 16 Dec 2008
Posts: 1159
Azu 07 Jun 2009, 16:38
revolution wrote:
You code won't work. edi is the return address and you overwrite your code with stosb. The 'ret' jumps to somewhere not where you expect.
Oh well. It was just an example. Fixing that, as well as preserving registers, is trivial regardless of which standard you use and has nothing to do with the example.. it was just meant to demonstrate having vararg and cleaning up stack by itself..

revolution wrote:
I think you clearly don't understand HOW an HLL works. Like I said, and it is not a mistake, HLL using a stdcall interface cannot implement a vararg function. Once you understand that you will see WHY wsprintf cannot be stdcall.
stdcall means that you push your arguments onto the stack and then call the function where as cdecl means you push your arguments onto the stack and then call the function and then after it returns you have to fix the stack yourself. I still don't understand why the latter standard is needed, since the function obviously knows how many args are passed to it or it wouldn't be able to use them, and my example demonstrates this. It isn't even needed to pass first arg telling it how many args to expect! ^^




Edit: I went back and fixed the stupid example so it should work right now Razz
And with that I make my leave. Can hardly keep my eyes open lol. I'll be back tomorrow okay
Post 07 Jun 2009, 16:38
View user's profile Send private message Send e-mail AIM Address Yahoo Messenger MSN Messenger ICQ Number Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20448
Location: In your JS exploiting you and your system
revolution 07 Jun 2009, 16:44
Please read up about HOW and HLL will implement the vararg solution you suggest. There is no calling standard that supports vararg with auto-stack cleanup, so therefore, no HLL can implement it. IF there is an HLL that has access to the stack register then it may be possible to do, but I don't know of any HLL that allows such thing without recourse to embedded assembly.

BTW: a better asm solution is already presented in this thread early on.

But you can't do these things in an HLL. Okay, really, no bluff, HLLs just can't do it.


Last edited by revolution on 07 Jun 2009, 16:50; edited 1 time in total
Post 07 Jun 2009, 16:44
View user's profile Send private message Visit poster's website Reply with quote
Azu



Joined: 16 Dec 2008
Posts: 1159
Azu 07 Jun 2009, 16:47
P.S. I never directly accessed the stack register (esp) or even the frame register (ebp) anywhere in my example. Yet the way it is doing it now, with the HLL, directly accesses them both, see
"mov edi, edi
push ebp
mov ebp, esp
lea eax, [ebp+arglist]
push eax ; arglist
push [ebp+arg_4] ; LPCWSTR
push [ebp+arg_0] ; LPWSTR
call wvsprintfW
pop ebp
retn"


Last edited by Azu on 07 Jun 2009, 16:49; edited 1 time in total
Post 07 Jun 2009, 16:47
View user's profile Send private message Send e-mail AIM Address Yahoo Messenger MSN Messenger ICQ Number Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20448
Location: In your JS exploiting you and your system
revolution 07 Jun 2009, 16:49
'pop ecx' is direct stack manipulation. In HLL, how will you make it do a 'pop ecx'?
Post 07 Jun 2009, 16:49
View user's profile Send private message Visit poster's website Reply with quote
Azu



Joined: 16 Dec 2008
Posts: 1159
Azu 07 Jun 2009, 16:52
Dunno but they do. Try this

mov edi,esp
push 1
call Sleep
sub edi,esp
jnz Sleepy
int3
Sleepy:
push -1
call Sleep

It will crash every time. If the normal Windows functions didn't pop the args off, it would just sleep forever.

Okay I'm REALLY going to bed now, good night
Post 07 Jun 2009, 16:52
View user's profile Send private message Send e-mail AIM Address Yahoo Messenger MSN Messenger ICQ Number Reply with quote
LocoDelAssembly
Your code has a bug


Joined: 06 May 2005
Posts: 4624
Location: Argentina
LocoDelAssembly 07 Jun 2009, 16:53
Oh, you think that the number of varargs can be calculated from the fmt?

What would you think it could happen here then?
Code:
wsprintf(buff, person.showAge ? "Person %u works at %s, and is %u years old" : "Person %u works at %s. Age can't be disclosed",\
         person.id, person.department, person.age);    
Code:
.
.
.

fmtTab   dd fmtNoAge, fmtAge

fmtAge   db "Person %u works at %s, and is %u years old", 0
fmtNoAge db "Person %u works at %s. Age can't be disclosed", 0

.
.
.

      cmp     [person.printAge], 0
      setne   cl
      movzx   ecx, cl
      mov     ecx, [fmtTab+ecx*4]

      ccall   wsprintf, buff, ecx, [person.id], [person.department], [person.age]

.
.
.    
Post 07 Jun 2009, 16:53
View user's profile Send private message Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20448
Location: In your JS exploiting you and your system
revolution 07 Jun 2009, 17:03
Azu wrote:
Dunno but they do. Try this

mov edi,esp
push 1
call Sleep
sub edi,esp
jnz Sleepy
int3
Sleepy:
push -1
call Sleep

It will crash every time. If the normal Windows functions didn't pop the args off, it would just sleep forever.
Well, that is just normal stdcall. It will always pop the 1 parameter from the stack. But consider what happens if you push 2 parameters and then call Sleep? The stdcall function will only ever pop off the expected amount of parameters as required from the function definition. So when we try to move this into wsprintf then we are REQUIRED for declare, at the start of the function, how many parameters to pop off the stack, that is what stdcall does for us. So with vararg functions we have NO WAY to declare a vararg parameter. Therefore we HAVE TO choose another calling standard for vararg functions.

All of your code above is fine for assembly programmers, but HLL imposes restrictions that make some things impossible to do.
Post 07 Jun 2009, 17:03
View user's profile Send private message Visit poster's website Reply with quote
Borsuc



Joined: 29 Dec 2005
Posts: 2465
Location: Bucharest, Romania
Borsuc 07 Jun 2009, 23:51
f0dder wrote:
No, they went with standard cdecl.
See that was what I was talking about, it's a bad standard from day 1 Razz

Actually, it could have small speed improvements in some cases. But it's still bad design in my opinion.

(just for the record, I don't blame MS, I blame cdecl).
On second thought, vararg functions (that is, the functions themselves, not the code that calls them) should be made in asm anyway RazzRazzRazz

_________________
Previously known as The_Grey_Beast
Post 07 Jun 2009, 23:51
View user's profile Send private message Reply with quote
Display posts from previous:
Post new topic Reply to topic

Jump to:  
Goto page Previous  1, 2, 3, 4 ... 9, 10, 11  Next

< Last Thread | Next Thread >
Forum Rules:
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum
You cannot attach files in this forum
You can download files in this forum


Copyright © 1999-2025, Tomasz Grysztar. Also on GitHub, YouTube.

Website powered by rwasa.