1. ver 4.0 c_func problem on WIN98
- Posted by bernie Apr 20, 2009
- 1208 views
Calling a machine code function using c_func with SVN 1705 on WIN98 works properly.
Calling a machine code function using c_func with ANY SVN after SVN 1705 RETURNS ZERO using the exact same code.
name = {115's',116't',114'r',116't',111'o',107'k',95'_'} p = {22315904,21900200} -- calling parameters r = 22315904 -- returned value d = { 36'$', -- routine id 20820768, -- machine address {33554436,33554436}, -- C_ULONG, C_ULONG 33554436, -- returns C_ULONG -13 -- special meaning to my code } -- Note: other confusing code removed here. -- THIS is where call took place C:\WMOTOR\INCLUDE\motor.e:2449 if d[4] then C:\WMOTOR\INCLUDE\motor.e:2450 r = c_func(d[1],p) C:\WMOTOR\INCLUDE\motor.e:2454 return r
program aborted name = {115's',116't',114'r',116't',111'o',107'k',95'_'} p = {23511640,24122848} -- calling parameters r = 0 -- NOTE RETURNED VALUE IS ZERO ! d = { 36'$', -- routine id 6587648, -- machine address {33554436,33554436}, -- C_ULONG, C_ULONG 33554436, -- returns C_ULONG -13 -- special meaning to my code } -- Note: other confusing code removed here. -- THIS is where call took place C:\wmotor\include\motor.e:2449 if d[4] then C:\wmotor\include\motor.e:2450 r = c_func(d[1],p) C:\wmotor\include\motor.e:2454 return r
2. Re: ver 4.0 c_func problem on WIN98
- Posted by jeremy (admin) Apr 22, 2009
- 1195 views
Bernie,
Is this still a problem in recent copies of Euphoria? We are up to 1971 now.
Jeremy
3. Re: ver 4.0 c_func problem on WIN98
- Posted by bernie Apr 22, 2009
- 1204 views
Bernie,
Is this still a problem in recent copies of Euphoria? We are up to 1971 now.
Jeremy
Yes
I have tried every new update that has been added to the trunk.
I have been trying to find the problem with no luck.
Also If you click open euiw.exe on WIN98 the window just flashes open and immediately closes ( which doesn't happen on XP ) so there is no way a user can read the help options. euid.exe stays open.
4. Re: ver 4.0 c_func problem on WIN98
- Posted by DerekParnell (admin) Apr 22, 2009
- 1205 views
If you click open euiw.exe on WIN98 the window just flashes open and immediately closes ( which doesn't happen on XP )
On XP, do you see the message "(press any key and window will close ...)" at the end of the help text?
On WIN98, does the wait_key() function work for you?
5. Re: ver 4.0 c_func problem on WIN98
- Posted by jemima Apr 22, 2009
- 1197 views
d = { 36'$', -- routine id 20820768, -- machine address } r = c_func(d[1],p)
looks to me that should be either call_func(d[1]) or c_func(d[2])...
6. Re: ver 4.0 c_func problem on WIN98
- Posted by bernie Apr 22, 2009
- 1215 views
If you click open euiw.exe on WIN98 the window just flashes open and immediately closes ( which doesn't happen on XP )
On XP, do you see the message "(press any key and window will close ...)" at the end of the help text?
On WIN98, does the wait_key() function work for you?
Yes XP works correctly derek. It displays the options and press key etc.
I am just clicking on euiw.exe file not a program so
the wait_key would not have anything to do with it.
ON WIN98 window just flashs open and closes immediately
On SVN 1705 the window displays
Euphoria Interpreter 4.0.0 development for 32-bit Windows. SVN Revision 1705 Using Managed Memory Copyright (c) Rapid Deployment Software 2008 See http://www.RapidEuphoria.com/License.txt
file name to execute?
7. Re: ver 4.0 c_func problem on WIN98
- Posted by mattlewis (admin) Apr 22, 2009
- 1217 views
I am just clicking on euiw.exe file not a program so the wait_key would not have anything to do with it.
How do you suppose the interpreter knows when you've pressed a key, and it can continue? Technically, it uses get(0), not wait_key() (see Cleanup() in error.e for details).
Matt
8. Re: ver 4.0 c_func problem on WIN98
- Posted by DerekParnell (admin) Apr 22, 2009
- 1178 views
If you click open euiw.exe on WIN98 the window just flashes open and immediately closes ( which doesn't happen on XP )
On XP, do you see the message "(press any key and window will close ...)" at the end of the help text?
On WIN98, does the wait_key() function work for you?
Yes XP works correctly derek. It displays the options and press key etc.
I am just clicking on euiw.exe file not a program so
the wait_key would not have anything to do with it.
Please humor me ... does the wait_key() function work for you in WIN98?
I ask this because the way the help text is supposed to work is that if the program running contains "euiw" in its name, the message "(press any key and window will close ...)" is displayed and wait_key() is called. The window is then closed after you press any key. As this is working for XP, it should also be working for WIN98.
Here is a simple test program for you to see if wait_key() is working in WIN98...
-- waiting.ex -- include std/console.e puts(1, "Waiting ...\n") wait_key()
This should display a new console window with "Waiting ..." in it and just sit there until you press one of the keyboard keys.
Can you try this test program on your WIN98system and let me know what happens?
If this works as expected, can you also try this following test program ...
-- waiting2.ex -- include std/console.e any_key("Still Waiting ...\n")
9. Re: ver 4.0 c_func problem on WIN98
- Posted by jimcbrown (admin) Apr 22, 2009
- 1200 views
Bernie,
Is this still a problem in recent copies of Euphoria? We are up to 1971 now.
Jeremy
I did not test 1971, but I did test eui - 1787 with managed mem - on w98. Here is the output:
1
And here is the source code:
include std/dll.e include std/machine.e sequence mcode mcode = { #55, #89, #E5, #B8, #01, #00, #00, #00, #C9, #C3 } object x, addr addr = allocate(20) poke(addr, mcode) x = define_c_func("", {'+', addr}, {}, C_INT) ? c_func(x, {})
For those who are curious, here is how I got the machine code (from the assembly dump):
(gdb) x/9ib 0x08048334 0x8048334 <g>: push ebp 0x8048335 <g+1>: mov ebp,esp 0x8048337 <g+3>: mov eax,0x1 0x804833c <g+8>: leave 0x804833d <g+9>: ret 0x804833e <main>: lea ecx,[esp+4] 0x8048342 <main+4>: and esp,0xfffffff0 0x8048345 <main+7>: push DWORD PTR [ecx-4] 0x8048348 <main+10>: push ebp (gdb) x/10xb 0x08048334 0x8048334 <g>: 0x55 0x89 0xe5 0xb8 0x01 0x00 0x00 0x00 0x804833c <g+8>: 0xc9 0xc3
And here is the original C source code:
int g() { return 1; } int main() { return g(); }
10. Re: ver 4.0 c_func problem on WIN98
- Posted by DerekParnell (admin) Apr 22, 2009
- 1180 views
How do you suppose the interpreter knows when you've pressed a key, and it can continue? Technically, it uses get(0), not wait_key() (see Cleanup() in error.e for details).
Matt, the relevant code can be found in main.e ...
if src_file = -2 then -- No source supplied on command line show_usage() if find("WIN32_GUI", OpDefines) then any_key("(press any key and window will close ...)", STDERR) end if Cleanup(1) end if
11. Re: ver 4.0 c_func problem on WIN98
- Posted by bernie Apr 22, 2009
- 1168 views
-- waiting.ex -- include std/console.e puts(1, "Waiting ...\n") wait_key()
This should display a new console window with "Waiting ..." in it and just sit there until you press one of the keyboard keys.
Can you try this test program on your WIN98system and let me know what happens?
If this works as expected, can you also try this following test program ...
Yes the first test works
12. Re: ver 4.0 c_func problem on WIN98
- Posted by DerekParnell (admin) Apr 22, 2009
- 1209 views
-- waiting.ex -- include std/console.e puts(1, "Waiting ...\n") wait_key()
This should display a new console window with "Waiting ..." in it and just sit there until you press one of the keyboard keys.
Can you try this test program on your WIN98system and let me know what happens?
If this works as expected, can you also try this following test program ...
Yes the first test works
And the second test ???
Also, what happens when instead of clicking on the euiw.exe file name, you start a DOS console and type in "euiw"?
13. Re: ver 4.0 c_func problem on WIN98
- Posted by bernie Apr 22, 2009
- 1156 views
-- waiting.ex -- include std/console.e puts(1, "Waiting ...\n") wait_key()
This should display a new console window with "Waiting ..." in it and just sit there until you press one of the keyboard keys.
Can you try this test program on your WIN98system and let me know what happens?
If this works as expected, can you also try this following test program ...
Yes the first test works
And the second test ???
Also, what happens when instead of clicking on the euiw.exe file name, you start a DOS console and type in "euiw"?
FIRST test with .EX file Opens full screen hitting key shrinks to window but have to close by [x] in top right corner
FIRST test with .EXW file Opens window hitting key closes window
SECOND test with .EX file Opens full screen hitting key shrinks to window but have to close by [x] in top right corner
SECOND test with .EXW file Opens window hitting key closes window
14. Re: ver 4.0 c_func problem on WIN98
- Posted by jimcbrown (admin) Apr 22, 2009
- 1148 views
I just tested 1971 and I have identical results.
Bernie,
Is this still a problem in recent copies of Euphoria? We are up to 1971 now.
Jeremy
I did not test 1971, but I did test eui - 1787 with managed mem - on w98. Here is the output:
1
And here is the source code:
include std/dll.e include std/machine.e sequence mcode mcode = { #55, #89, #E5, #B8, #01, #00, #00, #00, #C9, #C3 } object x, addr addr = allocate(20) poke(addr, mcode) x = define_c_func("", {'+', addr}, {}, C_INT) ? c_func(x, {})
For those who are curious, here is how I got the machine code (from the assembly dump):
(gdb) x/9ib 0x08048334 0x8048334 <g>: push ebp 0x8048335 <g+1>: mov ebp,esp 0x8048337 <g+3>: mov eax,0x1 0x804833c <g+8>: leave 0x804833d <g+9>: ret 0x804833e <main>: lea ecx,[esp+4] 0x8048342 <main+4>: and esp,0xfffffff0 0x8048345 <main+7>: push DWORD PTR [ecx-4] 0x8048348 <main+10>: push ebp (gdb) x/10xb 0x08048334 0x8048334 <g>: 0x55 0x89 0xe5 0xb8 0x01 0x00 0x00 0x00 0x804833c <g+8>: 0xc9 0xc3
And here is the original C source code:
int g() { return 1; } int main() { return g(); }
15. Re: ver 4.0 c_func problem on WIN98
- Posted by jimcbrown (admin) Apr 22, 2009
- 1196 views
I just tested 1971 with a slightly different machine code:
Here is the output with eui:
9
And here is the source code:
include std/dll.e include std/machine.e sequence mcode2 mcode2 = { #55, #89, #E5, #8B, #45, #08, #C9, #C3 } object x, addr addr = allocate(20) poke(addr, mcode2) x = define_c_func("", {'+', addr}, {C_INT}, C_INT) ? c_func(x, {9})
euiw doesn't work, the window flashes and then immediately disappears, despite the fact that it is being run from a DOS Command Prompt (thus from another console window).
16. Re: ver 4.0 c_func problem on WIN98
- Posted by DerekParnell (admin) Apr 22, 2009
- 1174 views
euiw doesn't work, the window flashes and then immediately disappears, despite the fact that it is being run from a DOS Command Prompt (thus from another console window).
This is to be expected. That is how euiw is designed to work. If you need to see the console output of a program run with euiw, you must manually pause the console before the application closes.
For example ...
? c_func(x, {9}) ifdef WIN32_GUI then -- thus running under euiw.exe wait_key() end ifdef
17. Re: ver 4.0 c_func problem on WIN98
- Posted by DerekParnell (admin) Apr 22, 2009
- 1183 views
And the second test ???
Also, what happens when instead of clicking on the euiw.exe file name, you start a DOS console and type in "euiw"?
FIRST test with .EX file Opens full screen hitting key shrinks to window but have to close by [x] in top right corner
FIRST test with .EXW file Opens window hitting key closes window
SECOND test with .EX file Opens full screen hitting key shrinks to window but have to close by [x] in top right corner
SECOND test with .EXW file Opens window hitting key closes window
I see. Well it appears that you have ".EX" associated with euid.exe and ".EXW" associated with euiw.exe. This is normal and not the issue.
It also appears that clicking on the ".EXW" file, which invokes euiw.exe, has no problems with running wait_key(). This is good.
Now, can you please open a DOS console and type in "euiw" instead of clicking on "euiw.exe" file name. Remember that the wait_key() is only used after the help text if Euphoria sees "euiw" somewhere in the name of the file that is running Euphoria. If you have renamed "euiw.exe" to something else it defintely won't work as expected, but I'm pretty sure you haven't done that. What I'm trying to test now is to see if Windows 98 treats invoking the program from the command line any differently than invoking it by clicking on the file name.
It should be the same, but it won't hurt to test it out.
So all you have to do for this next test, is ...
- start a new DOS console.
- Type in "euiw" and press the Enter key.
If this does not wait (just flashes a new console) then I'm out of ideas for now, except to say why the heck are you still using WIN98???
18. Re: ver 4.0 c_func problem on WIN98
- Posted by bernie Apr 22, 2009
- 1181 views
I just tested 1971 with a slightly different machine code:
Here is the output with eui:
9
And here is the source code:
include std/dll.e include std/machine.e sequence mcode2 mcode2 = { #55, #89, #E5, #8B, #45, #08, #C9, #C3 } object x, addr addr = allocate(20) poke(addr, mcode2) x = define_c_func("", {'+', addr}, {C_INT}, C_INT) ? c_func(x, {9})
euiw doesn't work, the window flashes and then immediately disappears, despite the fact that it is being run from a DOS Command Prompt (thus from another console window).
Thanks Jim:
I tried your code and it works ok on my system.
My code is much more involved than that; its assembler nested into euphoria functions that is dynamically translated into machine code. Thats why I can't just post a simple example to show the problem.
19. Re: ver 4.0 c_func problem on WIN98
- Posted by jimcbrown (admin) Apr 22, 2009
- 1205 views
Now, can you please open a DOS console and type in "euiw" instead of clicking on "euiw.exe" file name. Remember that the wait_key() is only used after the help text if Euphoria sees "euiw" somewhere in the name of the file that is running Euphoria. If you have renamed "euiw.exe" to something else it defintely won't work as expected, but I'm pretty sure you haven't done that. What I'm trying to test now is to see if Windows 98 treats invoking the program from the command line any differently than invoking it by clicking on the file name.
It should be the same, but it won't hurt to test it out.
So all you have to do for this next test, is ...
- start a new DOS console.
- Type in "euiw" and press the Enter key.
If this does not wait (just flashes a new console) then I'm out of ideas for now, except to say why the heck are you still using WIN98???
I can confirm that on w98 using 1971 with managed mem, running the above steps causes euiw to quickly dump the help screen on a new console window and then quickly disappear. If my box was faster I suspect I'd have only seen a flash.
euiw does not wait.
20. Re: ver 4.0 c_func problem on WIN98
- Posted by DerekParnell (admin) Apr 22, 2009
- 1213 views
I can confirm that on w98 using 1971 with managed mem, running the above steps causes euiw to quickly dump the help screen on a new console window and then quickly disappear. If my box was faster I suspect I'd have only seen a flash.
euiw does not wait.
By any chance is "euiw.exe" in upper case in WIN98? On my system, XP, it is in lowercase but EUID.EXE is in upper case. I was just wondering if on WIN98 the file name is EUIW.EXE and not euiw.exe? I can quickly fix this in Euphoria if this is the issue.
21. Re: ver 4.0 c_func problem on WIN98
- Posted by bernie Apr 22, 2009
- 1195 views
And the second test ???
Also, what happens when instead of clicking on the euiw.exe file name, you start a DOS console and type in "euiw"?
FIRST test with .EX file Opens full screen hitting key shrinks to window but have to close by [x] in top right corner
FIRST test with .EXW file Opens window hitting key closes window
SECOND test with .EX file Opens full screen hitting key shrinks to window but have to close by [x] in top right corner
SECOND test with .EXW file Opens window hitting key closes window
I see. Well it appears that you have ".EX" associated with euid.exe and ".EXW" associated with euiw.exe. This is normal and not the issue.
It also appears that clicking on the ".EXW" file, which invokes euiw.exe, has no problems with running wait_key(). This is good.
Now, can you please open a DOS console and type in "euiw" instead of clicking on "euiw.exe" file name. Remember that the wait_key() is only used after the help text if Euphoria sees "euiw" somewhere in the name of the file that is running Euphoria. If you have renamed "euiw.exe" to something else it defintely won't work as expected, but I'm pretty sure you haven't done that. What I'm trying to test now is to see if Windows 98 treats invoking the program from the command line any differently than invoking it by clicking on the file name.
It should be the same, but it won't hurt to test it out.
So all you have to do for this next test, is ...
- start a new DOS console.
- Type in "euiw" and press the Enter key.
If this does not wait (just flashes a new console) then I'm out of ideas for now, except to say why the heck are you still using WIN98???
When I type in euiw in a DOS window a second window pops open and immediately closes in a flash leaving just the DOS window open.
First I have to support my wife's WIN98 dos games and someone has to make sure ver 4.0 works on WIN98.
22. Re: ver 4.0 c_func problem on WIN98
- Posted by jimcbrown (admin) Apr 22, 2009
- 1192 views
I can confirm that on w98 using 1971 with managed mem, running the above steps causes euiw to quickly dump the help screen on a new console window and then quickly disappear. If my box was faster I suspect I'd have only seen a flash.
euiw does not wait.
By any chance is "euiw.exe" in upper case in WIN98? On my system, XP, it is in lowercase but EUID.EXE is in upper case. I was just wondering if on WIN98 the file name is EUIW.EXE and not euiw.exe? I can quickly fix this in Euphoria if this is the issue.
command_line() reports EUIW.EXE (despite the fact that "dir" and explorer show it in lower case).
23. Re: ver 4.0 c_func problem on WIN98
- Posted by jimcbrown (admin) Apr 22, 2009
- 1199 views
euiw doesn't work, the window flashes and then immediately disappears, despite the fact that it is being run from a DOS Command Prompt (thus from another console window).
This is to be expected. That is how euiw is designed to work. If you need to see the console output of a program run with euiw, you must manually pause the console before the application closes.
For example ...
? c_func(x, {9}) ifdef WIN32_GUI then -- thus running under euiw.exe wait_key() end ifdef
This does not work, it acts as if WIN32_GUI is not defined for euiw.
Futhermore, when running either euiw or eui from explorer, I get the flash. eui does not wait for a keypress either, if it has its own console window.
24. Re: ver 4.0 c_func problem on WIN98
- Posted by jimcbrown (admin) Apr 22, 2009
- 1228 views
Thanks Jim:
I tried your code and it works ok on my system.
My code is much more involved than that; its assembler nested into euphoria functions that is dynamically translated into machine code. Thats why I can't just post a simple example to show the problem.
Without an example that demonstrates the problem, it will be very difficult to track down this bug. (Even a very complex example is better than no example.)
25. Re: ver 4.0 c_func problem on WIN98
- Posted by DerekParnell (admin) Apr 22, 2009
- 1221 views
This does not work, it acts as if WIN32_GUI is not defined for euiw.
Ok! I see the problem and have just uploaded the fix. The problem was that when setting WIN32_GUI define, it only checked for lowercase "euiw". Obviously this is not correct because Windows uses case-insensitive file names.
Futhermore, when running either euiw or eui from explorer, I get the flash.
I assume you mean that when clicking on the eui.exe file name, it just flashes and does not keep a console opened. This is the expected behaviour as it assumes that the operating system has opened a console/shell for it to use. By clicking, Windows does open a console/shell and when the application closes, then Windows closes the console down.
eui does not wait for a keypress either, if it has its own console window.
If you saying that if you manually open a console, then type in "eui", that the 'press a key' message does not appear, then this is the expected behaviour. This is because eui assumes that the console is already open and will stay open after the application ends. In other words, it assumes that it will be run from a command line prompt.
26. Re: ver 4.0 c_func problem on WIN98
- Posted by jimcbrown (admin) Apr 22, 2009
- 1225 views
This does not work, it acts as if WIN32_GUI is not defined for euiw.
Ok! I see the problem and have just uploaded the fix. The problem was that when setting WIN32_GUI define, it only checked for lowercase "euiw". Obviously this is not correct because Windows uses case-insensitive file names.
Great, thanks for the prompt response!
Futhermore, when running either euiw or eui from explorer, I get the flash.
I assume you mean that when clicking on the eui.exe file name, it just flashes and does not keep a console opened. This is the expected behaviour as it assumes that the operating system has opened a console/shell for it to use. By clicking, Windows does open a console/shell and when the application closes, then Windows closes the console down.
eui does not wait for a keypress either, if it has its own console window.
If you saying that if you manually open a console, then type in "eui", that the 'press a key' message does not appear, then this is the expected behaviour. This is because eui assumes that the console is already open and will stay open after the application ends. In other words, it assumes that it will be run from a command line prompt.
Understood. So the only bug left now is to find out why bernie's code always returns 0 while my machine code appears to work without issue.
27. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by bernie Apr 22, 2009
- 1200 views
This is a program that works on SVN 1705 on WIN98
BUT FAILS on later SVN's for example SVN 1971 on WIN98.
The program parses tokens out of string s.
If the first token returns ZERO then all you will see on the screen is "That's All Folks!"
If the program WORKS it will print a token and pause until you press a key for next token.
It will do this until it sees no more tokens and then print "That's All Folks!"
include std\machine.e include std\dll.e include std\sequence.e constant mcode = allocate(253) poke(mcode, { -- strlen_: @ ;---------- @ #FC, -- cld ; clear the direction flag #8B,#7C,#24,#04, -- mov edi, [esp+4] ; offset of str parameter #31,#C0, -- xor eax, eax ; set al to contain zero #83,#C9,#FF, -- or ecx, -1 ; set counter to #FFFFFFFF #F2,#AE, -- repne scasb ; scan for zero termination #F7,#D1, -- not ecx ; invert ecx to get the count #49, -- dec ecx ; subtract 1 from the ecx ( null termination ) #89,#C8, -- mov eax, ecx ; Return ecx ( the length ) #C2,#04,#00, -- ret 4 ; ret 4 adjust the stack -- strspn_: @ ;---------- @ #FC, -- cld #31,#C0, -- xor eax, eax #8B,#4C,#24,#04, -- mov ecx, [esp+4] #EB,#13, -- jmp ssp004 -- ssp001: #41, -- inc ecx #8B,#7C,#24,#08, -- mov edi, [esp+8] -- ssp002: #8A,#37, -- mov dh, [edi] #08,#F6, -- or dh, dh #74,#0E, -- jz ssp005 #38,#F2, -- cmp dl, dh #74,#03, -- je ssp003 #47, -- inc edi #EB,#F3, -- jmp ssp002 -- ssp003: #40, -- inc eax -- ssp004: #8A,#11, -- mov dl, [ecx] #08,#D2, -- or dl, dl #75,#E7, -- jnz ssp001 -- ssp005: #C2,#08,#00, -- ret 8 ; ret 8 -- strpbrk_: @ ;--------- #FC, -- cld ; #8B,#44,#24,#04, -- mov eax, [esp+4] ; #EB,#12, -- jmp sb004 ; -- sb001: ; #8B,#4C,#24,#08, -- mov ecx, [esp+8] ; -- sb002: ; #8A,#31, -- mov dh, [ecx] ; #08,#F6, -- or dh, dh ; #74,#07, -- jz sb003 ; #38,#F2, -- cmp dl, dh ; #74,#0C, -- je sb005 ; #41, -- inc ecx ; #EB,#F3, -- jmp sb002 ; -- sb003: ; #40, -- inc eax ; -- sb004: ; #8A,#10, -- mov dl, [eax] ; #08,#D2, -- or dl, dl ; #75,#E8, -- jnz sb001 ; #31,#C0, -- xor eax, eax ; -- sb005: ; #C2,#08,#00, -- ret 8 ; ret 8 -- strtok_: @ ;----------- #8B,#74,#24,#04, -- mov esi, [esp+4] ; get buffer #85,#F6, -- test esi esi ; first call ? #74,#06, -- jz nexttok ; no #89,#35,#A1,#AD,#D1,#83,-- mov [@ptr], esi ; save buffer -- nexttok: ; #8B,#7C,#24,#08, -- mov edi, [esp+8] ; yes get delimit #8B,#35,#A1,#AD,#D1,#83,-- mov esi, [@ptr] ; get current ptr #83,#FE,#00, -- cmp esi, 0 ; #74,#77, -- je endtok ; bail out #57, -- push edi ; delimit #56, -- push esi ; buffer #E8,#93,#FF,#FF,#FF, -- call near strspn_ ; find start of token #01,#05,#A1,#AD,#D1,#83,-- add [@ptr], eax ; goto first token #8B,#7C,#24,#08, -- mov edi, [esp+8] ; get delimit #8B,#35,#A1,#AD,#D1,#83,-- mov esi, [@ptr] ; get current ptr #83,#FE,#00, -- cmp esi, 0 ; #74,#5B, -- je endtok ; bail out #83,#3E,#00, -- cmp [esi], 0 ; pointing to zero ? #74,#56, -- je endtok ; bail out #57, -- push edi ; delimit #56, -- push esi ; buffer #E8,#97,#FF,#FF,#FF, -- call near strpbrk_ ; find the end of the token #8B,#35,#A1,#AD,#D1,#83,-- mov esi, [@ptr] ; get current ptr #39,#F0, -- cmp eax, esi ; #74,#45, -- je endtok ; #83,#F8,#00, -- cmp eax, 0 ; #74,#1A, -- je exact ; #A3,#A1,#AD,#D1,#83, -- mov [@ptr], eax ; #89,#C7, -- mov edi, eax ; #B8,#00,#00,#00,#00, -- mov eax, 0 ; #88,#07, -- mov [edi], al ; #89,#F0, -- mov eax, esi ; #83,#05,#A1,#AD,#D1,#83,#01,-- add [@ptr], 1 ; #C2,#08,#00, -- ret 8 ; -- exact: ; #8B,#35,#A1,#AD,#D1,#83,-- mov esi, [@ptr] ; get current ptr #56, -- push esi ; #E8,#29,#FF,#FF,#FF, -- call near strlen_ ; #83,#F8,#00, -- cmp eax, 0 ; #75,#02, -- jne lasttok ; #EB,#13, -- jmp endtok ; -- lasttok: ; #B9,#00,#00,#00,#00, -- mov ecx, 0 ; #A1,#A1,#AD,#D1,#83, -- mov eax, [@ptr] ; get current ptr #89,#0D,#A1,#AD,#D1,#83,-- mov [@ptr], ecx ; block next call #C2,#08,#00, -- ret 8 ; -- endtok: ; #B8,#00,#00,#00,#00, -- mov eax, 0 ; #C2,#08,#00, -- ret 8 ; #00,#00,#00,#00}) -- ptr: dd 0 ; (249) poke4(mcode + 103, mcode + 249) -- @ptr poke4(mcode + 113, mcode + 249) -- @ptr poke4(mcode + 131, mcode + 249) -- @ptr poke4(mcode + 141, mcode + 249) -- @ptr poke4(mcode + 164, mcode + 249) -- @ptr poke4(mcode + 178, mcode + 249) -- @ptr poke4(mcode + 195, mcode + 249) -- @ptr poke4(mcode + 205, mcode + 249) -- @ptr poke4(mcode + 228, mcode + 249) -- @ptr poke4(mcode + 234, mcode + 249) -- @ptr integer rid = define_c_func("", mcode+93, {C_ULONG,C_ULONG}, C_ULONG) sequence s = "Thisqxzzw::q is: qaq z \"test\" of xxbernie'sx zzcode " -- parse string atom tok, b = allocate_string(s), d = allocate_string("qxz w:\"") tok = c_func(rid,{b,d}) -- strtok get token while tok do puts(1,peek_string(tok)&"\n") -- display the token if getc(0) then end if -- pause tok = c_func(rid,{0,d}) -- strtok get another token end while -- IF THIS IS THE ONLY THING THAT PRINTS THE ABOVE TOK RETURNED ZERO !!! puts(1,"That's All Folks!\n") if getc(0) then end if -- pause
28. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 22, 2009
- 1184 views
This is a program that works on SVN 1705 on WIN98
BUT FAILS on later SVN's for example SVN 1971 on WIN98.
The program parses tokens out of string s.
If the first token returns ZERO then all you will see on the screen is "That's All Folks!"
If the program WORKS it will print a token and pause until you press a key for next token.
It will do this until it sees no more tokens and then print "That's All Folks!"
I am able to confirm the following:
The code works fine on Linux, with or without a '+'. (Looking at the source, it seems Linux just uses CDECL no matter what.)
The code works fine on w98 when using mingw eui.exe and STDCALL.
The code causes a machine level exception on w98 when using mingw eui.exe and CDECL.
The code does not crash, but the first token returns 0 on w98 when using watcom eui.exe, with or without a '+'. (Looking at the source, it seems Watcom also uses CDECL no matter what.)
I believe the issue is not in the machine code itself, nor in call_c()'s preamble to calling the machine code, but how we handle the return value from the function in be_callc.c's call_c() function.
29. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by bernie Apr 22, 2009
- 1196 views
This is a program that works on SVN 1705 on WIN98
BUT FAILS on later SVN's for example SVN 1971 on WIN98.
The program parses tokens out of string s.
If the first token returns ZERO then all you will see on the screen is "That's All Folks!"
If the program WORKS it will print a token and pause until you press a key for next token.
It will do this until it sees no more tokens and then print "That's All Folks!"
I am able to confirm the following:
The code works fine on Linux, with or without a '+'. (Looking at the source, it seems Linux just uses CDECL no matter what.)
The code works fine on w98 when using mingw eui.exe and STDCALL.
The code causes a machine level exception on w98 when using mingw eui.exe and CDECL.
The code does not crash, but the first token returns 0 on w98 when using watcom eui.exe, with or without a '+'. (Looking at the source, it seems Watcom also uses CDECL no matter what.)
I believe the issue is not in the machine code itself, nor in call_c()'s preamble to calling the machine code, but how we handle the return value from the function in be_callc.c's call_c() function.
Jim I built all my binaries on XP using OpenWatcom Ver 1.8.
The program should run on any Euphoria binary no matter what compiler the binary was built with.
As far as the calling convention if I am calling my own internal code in my program I am controlling what I do to the stack so that should not matter.
30. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 22, 2009
- 1263 views
Jim I built all my binaries on XP using OpenWatcom Ver 1.8.
Can you confirm that the code works correctly on XP? Even if called with '+' ?
The program should run on any Euphoria binary no matter what compiler the binary was built with.
Agreed. This is a bug of eui.exe/euiw.exe
As far as the calling convention if I am calling my own internal code in my program I am controlling what I do to the stack so that should not matter.
This is wrong.
You call
tok = c_func(rid, {b,d})
So we need to know the correct calling convention to pass the arguments (b and d) onto the stack to the machine code, and then we need to know the convention again to obtain the correct return value.
Thus, for the call to rid to be successful, the calling convention is important. You can't just assume that c_func() will magically know the right thing to do.
However,
1. The default calling convetion on Windows is STDCALL (and '+' means CDECL). 2. Your machine code appears to be using STDCALL, if i understand the assembly languge correctly.
Therefore, this example should have worked on w98.
31. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 22, 2009
- 1180 views
I added some debug code to call_c() (nothing but printf()s) and suddenly the code is working correctly.
This sounds like an optimization bug.
32. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 22, 2009
- 1219 views
I added some debug code to call_c() (nothing but printf()s) and suddenly the code is working correctly.
This sounds like an optimization bug.
If you are unable to use patch, the entire file (source/be_callc.c) is available at http://euphoria.pastey.net/112882
But, as you can see from the diff, the only changes required to make it work are 3 printf() statements.
--- ../feu3/source/be_callc.c 2009-04-08 14:04:05.000000000 -0400 +++ /tmp/fl/eu40/source/be_callc9.c 2009-04-22 23:26:38.000000000 -0400 @@ -118,6 +118,7 @@ if (IS_ATOM(arg_list)) { RTFatal("c_proc/c_func: argument list must be a sequence"); } + printf("ha! %d\n", proc_index); arg_list_ptr = SEQ_PTR(arg_list); next_arg_ptr = arg_list_ptr->base + arg_list_ptr->length; @@ -277,11 +278,13 @@ #if defined(EWINDOWS) && !defined(EWATCOM) if (cdecl_call) { iresult = (*((int ( __cdecl *)())int_proc_address))(); + printf("iresult cdecl %d %d %d %x\n", iresult, proc_ind ex, func, return_type); pop(); } else #endif iresult = (*((int (__stdcall *)())int_proc_address))(); + printf("iresult stdcall %d %d %d %x\n", iresult, proc_i ndex, func, return_type); #ifdef EUNIX pop(); #endif
33. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by bernie Apr 22, 2009
- 1214 views
- Last edited Apr 23, 2009
This is wrong.
You call
tok = c_func(rid, {b,d})
So we need to know the correct calling convention to pass the arguments (b and d) onto the stack to the machine code, and then we need to know the convention again to obtain the correct return value.
Thus, for the call to rid to be successful, the calling convention is important. You can't just assume that c_func() will magically know the right thing to do.
However,
1. The default calling convetion on Windows is STDCALL (and '+' means CDECL). 2. Your machine code appears to be using STDCALL, if i understand the assembly languge correctly.
Therefore, this example should have worked on w98.
What I meant is I know when I am calling windows code or my code so I have control over cleaning stack when its neccesary.
The only difference between CDECL and STDCALL is:
- CDECL
- CDECL calling convention the following holds:
- Arguments are passed on the stack in Right-to-Left order, and return values are passed in eax.
- The calling function cleans the stack. This allows CDECL functions to have variable-length argument lists (aka variadic functions). For this reason the number of arguments is not appended to the name of the function by the compiler, and the assembler and the linker are therefore unable to determine if an incorrect number of arguments is used.
- STDCALL
- STDCALL passes arguments right-to-left, and returns the value in eax. (The Microsoft documentation erroneously claims that arguments are passed left-to-right, but this is not the case.)
- The called function cleans the stack, unlike CDECL. This means that STDCALL doesn't allow variable-length argument lists.
These are quotes from this web page: http://en.wikibooks.org/wiki/X86_Disassembly/Calling_Convention_Examples
34. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 22, 2009
- 1177 views
- Last edited Apr 23, 2009
What I meant is I know when I am calling windows code or my code so I have control over cleaning stack when its neccesary.
Ok, I understand now. You are correct, Bernie.
Can you look at my previous post and confirm if the patch (of printf()s ) makes the machine code call work correctly on w98?
35. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by bernie Apr 22, 2009
- 1198 views
- Last edited Apr 23, 2009
I copied the file that you posted and then replaced the file in SVN1973 with your file I ran it compiled it with Watcom .
I then took the binaries That were just compiled and placed them in the bin and then tried to used them to see if I could build the binaries again and Watcom goes into a loop printing
ha! 35 iresult stdcall ... over and over again.
I often build binaries this way to check their integrity. I don't think that your patch is a safe one.
I'll try them after one build just to see if we are on the right path.
36. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 22, 2009
- 1191 views
- Last edited Apr 23, 2009
I copied the file that you posted and then replaced the file in SVN1973 with your file I ran it compiled it with Watcom .
I then took the binaries That were just compiled and placed them in the bin and then tried to used them to see if I could build the binaries again and Watcom goes into a loop printing
ha! 35 iresult stdcall ... over and over again.
I often build binaries this way to check their integrity. I don't think that your patch is a safe one.
I'll try them after one build just to see if we are on the right path.
That is the debug code ... but even with the extra junk I was able to run your example and saw that it corrected the problem. (This patch isn't a real fix of course, because of the extra junk.)
37. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by bernie Apr 22, 2009
- 1210 views
- Last edited Apr 23, 2009
Jim:
As far as I can tell that should fix everything. Let me know when you get the new files ready.
Thanks very much.
I am going to call it a night.
38. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jeremy (admin) Apr 23, 2009
- 1182 views
I added some debug code to call_c() (nothing but printf()s) and suddenly the code is working correctly.
This sounds like an optimization bug.
I've had similar problems, I get a machine crash here or there, add a ? 0 and everything works. I try to reduce the program to a small test case and fail every time. It seems that if that happens, I just continue programming and the problem goes away itself. I've never had a good test case, maybe this is one Matt can track down?
Jeremy
39. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 23, 2009
- 1164 views
I added some debug code to call_c() (nothing but printf()s) and suddenly the code is working correctly.
This sounds like an optimization bug.
I've had similar problems, I get a machine crash here or there, add a ? 0 and everything works. I try to reduce the program to a small test case and fail every time. It seems that if that happens, I just continue programming and the problem goes away itself. I've never had a good test case, maybe this is one Matt can track down?
Jeremy
Well, this is in be_callc.c (100% C code, aside from a few asm macros), so it is either a) a bug in Watcom or b) expected behavior because we are telling Watcom to be overly aggressive in its optimizations.
40. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by mattlewis (admin) Apr 23, 2009
- 1168 views
I added some debug code to call_c() (nothing but printf()s) and suddenly the code is working correctly.
This sounds like an optimization bug.
I've had similar problems, I get a machine crash here or there, add a ? 0 and everything works. I try to reduce the program to a small test case and fail every time. It seems that if that happens, I just continue programming and the problem goes away itself. I've never had a good test case, maybe this is one Matt can track down?
This is gonna be a fun bug. The code works correctly for me on XP when I build a debug version of eui.exe, but it displays the reported behavior when built in release mode.
Matt
41. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 23, 2009
- 1178 views
This is gonna be a fun bug. The code works correctly for me on XP when I build a debug version of eui.exe, but it displays the reported behavior when built in release mode.
Matt
I was able to get an acceptable patch by changing the printfs into snprintfs.
The nature of the bug makes me think that Watcom is optimizing the value of iresult or return_type away.
42. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by mattlewis (admin) Apr 23, 2009
- 1180 views
This is gonna be a fun bug. The code works correctly for me on XP when I build a debug version of eui.exe, but it displays the reported behavior when built in release mode.
Matt
I was able to get an acceptable patch by changing the printfs into snprintfs.
The nature of the bug makes me think that Watcom is optimizing the value of iresult or return_type away.
It's not optimizing it away, but during the call, the value is changed. I put printfs around the call, and found that return_value was changing. This definitely seems like a Watcom bug. When I added printfs that took a reference to return_value, the problem went away.
Also, moving the declaration for the function pointer to be the last declared variable corrected the problem. I'm not sure what the proper fix might bedoes this cause other problems? We should probably take a look at the generated assembly to see what it's doing.
Sounds like something that should be submitted to OpenWatcom as a bug report.
Matt
43. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by bernie Apr 23, 2009
- 1179 views
In my opinion the problem acts like a memory problem.
The reason I think that is the problem goes away as Jim says when you add something or change something the problem goes away.
I suspect that it then moves code to different offset in memory.
This problem popup around time that Jeremy was change the binary names. At that time Jeremy started creating binaries that were crashing or building garbled up.
Jermey then fixed the problem at that time and there was a decision make binaries with the default using manage memory.
Are we sure that the code that is being built now is always laying on 4 byte boundaries as it was designed to work in 3.11 or has some bug been introduced during major changes in memory management.
44. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 23, 2009
- 1190 views
I don't believe that managed memory has changed at all since i last touched it, over a thousand revisions ago.
The change to make managed memory default was a change in the makefile only, but no code changes.
In my opinion the problem acts like a memory problem.
The reason I think that is the problem goes away as Jim says when you add something or change something the problem goes away.
I suspect that it then moves code to different offset in memory.
This problem popup around time that Jeremy was change the binary names. At that time Jeremy started creating binaries that were crashing or building garbled up.
Jermey then fixed the problem at that time and there was a decision make binaries with the default using manage memory.
Are we sure that the code that is being built now is always laying on 4 byte boundaries as it was designed to work in 3.11 or has some bug been introduced during major changes in memory management.
45. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by bernie Apr 23, 2009
- 1186 views
I just built the binaries SVN1973 using be_callc.c file
from EU ver 3.11 source and those binaries work ok.
46. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by mattlewis (admin) Apr 24, 2009
- 1171 views
We should probably take a look at the generated assembly to see what it's doing.
I added a couple of printf statements:
printf("1: return_type %8x %8x\n", return_type, int_proc_address ); iresult = (*((int (__stdcall *)())int_proc_address))(); printf("2: return_type %8x %8x\n", return_type, int_proc_address );
When calling Bernie's procedure, here's what we get:
1: return_type 2000004 ad7545 2: return_type b01ea8 ad7545
So it's clear that return_type is changing. Looking at the assembly for the printf and the call:
printf("1: return_type %8x %8x\n", return_type, int_proc_address ); 0378 8B 45 E8 mov eax,dword ptr -0x18[ebp] 037B 50 push eax 037C 56 push esi 037D 68 AB 01 00 00 push offset L$58 0382 E8 00 00 00 00 call printf_ iresult = (*((int (__stdcall *)())int_proc_address))(); 0387 83 C4 0C add esp,0x0000000c 038A 8B 5D E8 mov ebx,dword ptr -0x18[ebp] 038D FF 55 E8 call dword ptr -0x18[ebp] printf("2: return_type %8x %8x\n", return_type, int_proc_address ); 0390 53 push ebx 0391 56 push esi 0392 68 C4 01 00 00 push offset L$59 0397 89 C2 mov edx,eax 0399 89 C1 mov ecx,eax 039B E8 00 00 00 00 call printf_It looks like return_type is being stored in esi. I notice that Bernie's code modifies esi. I'm not sure whose responsibility it is to restore esi, but the problem appears to be that Watcom thinks that it's Bernie's job to restore any registers. That also helps explain why, when I took the address of return_type, it started working again
Matt
47. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by bernie Apr 24, 2009
- 1161 views
We should probably take a look at the generated assembly to see what it's doing.
I added a couple of printf statements:
printf("1: return_type %8x %8x\n", return_type, int_proc_address ); iresult = (*((int (__stdcall *)())int_proc_address))(); printf("2: return_type %8x %8x\n", return_type, int_proc_address );
When calling Bernie's procedure, here's what we get:
1: return_type 2000004 ad7545 2: return_type b01ea8 ad7545
So it's clear that return_type is changing. Looking at the assembly for the printf and the call:
printf("1: return_type %8x %8x\n", return_type, int_proc_address ); 0378 8B 45 E8 mov eax,dword ptr -0x18[ebp] 037B 50 push eax 037C 56 push esi 037D 68 AB 01 00 00 push offset L$58 0382 E8 00 00 00 00 call printf_ iresult = (*((int (__stdcall *)())int_proc_address))(); 0387 83 C4 0C add esp,0x0000000c 038A 8B 5D E8 mov ebx,dword ptr -0x18[ebp] 038D FF 55 E8 call dword ptr -0x18[ebp] printf("2: return_type %8x %8x\n", return_type, int_proc_address ); 0390 53 push ebx 0391 56 push esi 0392 68 C4 01 00 00 push offset L$59 0397 89 C2 mov edx,eax 0399 89 C1 mov ecx,eax 039B E8 00 00 00 00 call printf_It looks like return_type is being stored in esi. I notice that Bernie's code modifies esi. I'm not sure whose responsibility it is to restore esi, but the problem appears to be that Watcom thinks that it's Bernie's job to restore any registers. That also helps explain why, when I took the address of return_type, it started working again
Matt
Matt:
My code does not have any thing to do with changing the return type.
If you will note that the return type is set up in the define_c_func by a C_ULONG which is NOT controlled by my program code but internally by Euphoria.
No matter what is done to the ESI register internally in my code; it should not effect the external Euphoria code.
The return VALUE will on each pass; return a different pointer. The only thing that I am storing in my is the program is at ptr: dd 0 location in my code which keeps the pointer for the next pass.
48. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by mattlewis (admin) Apr 24, 2009
- 1166 views
It looks like return_type is being stored in esi. I notice that Bernie's code modifies esi. I'm not sure whose responsibility it is to restore esi, but the problem appears to be that Watcom thinks that it's Bernie's job to restore any registers. That also helps explain why, when I took the address of return_type, it started working againbecause Watcom stopped putting return_type in a register that gets clobbered.
My code does not have any thing to do with changing the return type.
If you will note that the return type is set up in the define_c_func by a C_ULONG which is NOT controlled by my program code but internally by Euphoria.
No matter what is done to the ESI register internally in my code; it should not effect the external Euphoria code.
The return VALUE will on each pass; return a different pointer. The only thing that I am storing in my is the program is at ptr: dd 0 location in my code which keeps the pointer for the next pass.
Bernie,
Please re-read what I wrote. Your code changes esi. Watcom is storing the variable return_type in esi. Therefore, as far as the call_c code is concerned, your code is changing return_type.
See, for example (from your code):
#8B,#35,#A1,#AD,#D1,#83,-- mov esi, [@ptr] ; get current ptr
Matt
49. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 24, 2009
- 1171 views
My code does not have any thing to do with changing the return type.
Not the return type, but (the C variable that is internal to Euphoria) return_type.
If you will note that the return type is set up in the define_c_func by a C_ULONG which is NOT controlled by my program code but internally by Euphoria.
This information (the C_ULONG) is stored in return_type, however, so if return_type gets changed then the information is lost. Watcom makes the return_type variable the same as the ESI register.
No matter what is done to the ESI register internally in my code; it should not effect the external Euphoria code.
What Matt is saying is that your machine code is clobbering a register.
If you saved all registers before your machine code starts and then restored all registers before your machine code returns, that would fix the bug.
Now the question is, is the bug Watcom's fault or not? In other words, should the compiler be saving and restoring registers for us or is your machine code suppose to do that? This is beyond the internals of Euphoria, but entering the realm of the internals of Watcom C, the realm of the Watcom developer team.
50. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by mattlewis (admin) Apr 24, 2009
- 1178 views
Now the question is, is the bug Watcom's fault or not? In other words, should the compiler be saving and restoring registers for us or is your machine code suppose to do that? This is beyond the internals of Euphoria, but entering the realm of the internals of Watcom C, the realm of the Watcom developer team.
After thinking about this, I believe that it must be the called function's responsibility. If it were the calling function's responsibility, then it would have to know which registers were modified. But this clearly cannot work (just imagine how it would work with dynamic linking, or indeed any function pointer whose contents cannot be known at compile time), so it would always have to save all registers. Indeed, looking at the top and bottom of the emitted assembly code for call_c, we can see that it saves the registers that it uses:
0000 call_c_: 0000 51 push ecx 0001 56 push esi 0002 57 push edi 0003 55 push ebp ... 047B 5D pop ebp 047C 5F pop edi 047D 5E pop esi 047E 59 pop ecx 047F C3 retI think that this bug in Bernie's code was previously hidden only because the compiler wasn't counting on the esi register being changed at that point in the code.
Matt
51. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by DerekParnell (admin) Apr 24, 2009
- 1198 views
After thinking about this, I believe that it must be the called function's responsibility.
I believe you are correct too. If one writes a machine code function, that function should save all general registers that it uses, except eax of course, and restore them just prior to returning. The machine code function cannot know which registers are being used by the caller, so it should be cautious. The returned data is assumed to be returned in eax.
52. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by Critic Apr 24, 2009
- 1180 views
@DerekParnell, @MattLewis It depends on the particular register. EAX, ECX, EDX can be used without saving (maybe others too I don't remember). It is nothing specific to Watcom. Use Google to find out more. Googling is faster than thinking
@Bernie Why not simply rewrite the assembler parts? Poking bytes that represent machine code is not the most maintainable thing in the world, you know.
53. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by bernie Apr 24, 2009
- 1165 views
- Last edited Apr 25, 2009
I have done the following :
I built SVN1975 binaries on XP for WIN98 and ran them using my assembler code.
protecting the ESI register PASSED.
not protecting the ESI FAILED.
I then built SVN1975 binaries on XP for WIN98 WITH DEBUG TURNED ON and ran them using my assembler code.
protecting the ESI register PASSED.
not protecting the ESI PASSED.
Something is different between debug be turned on and off.
54. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 24, 2009
- 1235 views
- Last edited Apr 25, 2009
Something is different between debug be turned on and off.
Correct. This is expected behavior, sadly.
Therefore, you will just have to always protect ESI. According to Watcom FAQ, that is what you are suppose to do.
55. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by DerekParnell (admin) Apr 24, 2009
- 1181 views
- Last edited Apr 25, 2009
Something is different between debug be turned on and off.
Yes there is, but protecting ESI is the way to go.
Here is a comment from the Watcom manual ...
All used 80x86 registers must be saved on entry and restored on exit except those used to pass arguments and return values, and AX, which is considered a stratch register. Note that segment registers only have to saved and restored if you are compiling your application with the "r" option.
The argument passing registers are EAX, EBX, ECX, EDX, so it means that ESI really must be protected.
56. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by bernie Apr 24, 2009
- 1167 views
- Last edited Apr 25, 2009
Something is different between debug be turned on and off.
Yes there is, but protecting ESI is the way to go.
Here is a comment from the Watcom manual ...
All used 80x86 registers must be saved on entry and restored on exit except those used to pass arguments and return values, and AX, which is considered a stratch register. Note that segment registers only have to saved and restored if you are compiling your application with the "r" option.
The argument passing registers are EAX, EBX, ECX, EDX, so it means that ESI really must be protected.
Then Why did my code work since euphoria version 2.2 all the way up to ver 4.0 SVN 1705 ????
57. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 24, 2009
- 1144 views
- Last edited Apr 25, 2009
Then Why did my code work since euphoria version 2.2 all the way up to ver 4.0 SVN 1705 ????
bernie, do you even know how to program machine code?!
58. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 24, 2009
- 1157 views
- Last edited Apr 25, 2009
Sorry, this was a bit harsh.
Then Why did my code work since euphoria version 2.2 all the way up to ver 4.0 SVN 1705 ????
bernie, do you even know how to program machine code?!
The reason it worked before, I am guessing, is that older versions of watcom, before OpenWatcom 1.7c, were not as good at optimizing, and so did not use the ESI register. Thus, there was never a conflict.
Since debug mode turns off optimizations, ESI is also not used, and thus no conflcit.
So its only newever versions of euphoria with more aggressive openwatcom optimizations that trigger the problem.
59. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by DerekParnell (admin) Apr 24, 2009
- 1160 views
- Last edited Apr 25, 2009
Then Why did my code work since euphoria version 2.2 all the way up to ver 4.0 SVN 1705 ????
You were lucky
Up until now, the Watcom compiler was not using ESI for anything important, but now (at least sometimes) Watcom has decided to use the ESI register for something, and assumes you are protecting it in your routine. Why is Watcom using the ESI? ... Don't know and don't care really. It is, and that's just the end of the matter as there is nothing efficiently we can do about it.
60. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by bernie Apr 24, 2009
- 1156 views
- Last edited Apr 25, 2009
Then Why did my code work since euphoria version 2.2 all the way up to ver 4.0 SVN 1705 ????
You were lucky
Up until now, the Watcom compiler was not using ESI for anything important, but now (at least sometimes) Watcom has decided to use the ESI register for something, and assumes you are protecting it in your routine. Why is Watcom using the ESI? ... Don't know and don't care really. It is, and that's just the end of the matter as there is nothing efficiently we can do about it.
Well I guess I will have to come up with a way to protect the registers automatically because I won't be able to be sure that the end user of my code always protects the registers.
Good luck on all the other compilers you are going to support. They will probably come up with a different way of optimizing and cause you more head aches.
61. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by jimcbrown (admin) Apr 24, 2009
- 1153 views
- Last edited Apr 25, 2009
Well I guess I will have to come up with a way to protect the registers automatically because I won't be able to be sure that the end user of my code always protects the registers.
Good luck on all the other compilers you are going to support. They will probably come up with a different way of optimizing and cause you more head aches.
bernie, do you even know how to program machine code?!
62. Re: ver 4.0 c_func problem on WIN98 Here Is proof of the problem !
- Posted by DerekParnell (admin) Apr 24, 2009
- 1171 views
- Last edited Apr 25, 2009
Well I guess I will have to come up with a way to protect the registers automatically because I won't be able to be sure that the end user of my code always protects the registers.
What are you talking about?
Does your application allow arbitary user-written machine code to be executed? This is a potentially dangerous thing to do as it promotes virus writing etc...
In any case it is a simple thing to do. You just write a wrapper around your user's (dangerous) code that effectively does this ...
- Save all registers (except EAX - EDX)
- Call the code written by your users.
- Restore all saved registers
Good luck on all the other compilers you are going to support. They will probably come up with a different way of optimizing and cause you more head aches.
This register convention is very common, if not universal. All compilers do it this way.
The golden rule for functions being called by code generated by any compiler is ... save all registers that the function uses and restore them on exit (apart from the EAX,EBX,ECX,EDX which can contain the return value).
63. Machine exceptions
- Posted by LarryMiller May 02, 2009
- 1087 views
I have been experiencing some unexplained machine exceptions when using c_func on XP. The thread of the message below primarily concerns Win98 but I get the impression that the problem is not confined to Win98.
I added some debug code to call_c() (nothing but printf()s) and suddenly the code is working correctly.
This sounds like an optimization bug.
I've had similar problems, I get a machine crash here or there, add a ? 0 and everything works. I try to reduce the program to a small test case and fail every time. It seems that if that happens, I just continue programming and the problem goes away itself. I've never had a good test case, maybe this is one Matt can track down?
Jeremy
Has anyone had these unexplained problems with systems other than Win98?
64. Re: Machine exceptions
- Posted by jimcbrown (admin) May 02, 2009
- 1109 views
- Last edited May 03, 2009
I have been experiencing some unexplained machine exceptions when using c_func on XP. The thread of the message below primarily concerns Win98 but I get the impression that the problem is not confined to Win98.
The bug described in the thread turned out to be the result of a bug in bernie's machine code. There was no problem with c_func() on 98 or any other OS.
Note that bernie was using c_func() to call custom machine code, instead of the more usual usage to call a C function in a dll.
I've had similar problems, I get a machine crash here or there, add a ? 0 and everything works. I try to reduce the program to a small test case and fail every time. It seems that if that happens, I just continue programming and the problem goes away itself. I've never had a good test case, maybe this is one Matt can track down?
Jeremy
Has anyone had these unexplained problems with systems other than Win98?
I do not think Jeremy is talking about 98 when he describes the above issue, as he does not have a 98 system to test out on.
65. Re: Machine exceptions
- Posted by jimcbrown (admin) May 03, 2009
- 1114 views
I have been experiencing some unexplained machine exceptions when using c_func on XP. The thread of the message below primarily concerns Win98 but I get the impression that the problem is not confined to Win98.
The bug described in the thread turned out to be the result of a bug in bernie's machine code. There was no problem with c_func() on 98 or any other OS.
Note that bernie was using c_func() to call custom machine code, instead of the more usual usage to call a C function in a dll.
I did not mean to discourage you from reporting your bug, I was simply stating that it was unlikely to be related to bernies.
Most of the time, getting a machine-level exception is a bug in Euphoria. If in doubt, report it as a bug.