1. RE: ASM Help
> -----Original Message-----
> From: stabmaster_ at HOTMAIL.COM [mailto:stabmaster_ at HOTMAIL.COM]
>
> First of all, I see an evil typo in here. You're storing the
> adress to CALL
> in EDX, but you're CALLin EAX..
> And you shouldn't use CALL FAR, but CALL NEAR.
>
> This is how to call a procedure (void) with one parameter:
>
> PUSH the_parameter
> MOV EAX, proc_address
> CALL NEAR EAX
Thanks. Unfortunately, I haven't been able to get that to work, so I've
taken a different route. I wrote a little DLL (63K compressed) in VC that
will call the funcs by pointer, taking up to 10 arguments.
Rob, I'd like to add this to the wishlist: call functions by pointer. It
seems it shouldn't be hard to do, since you probably already do something
like this for c_func.
Matt Lewis
2. RE: ASM Help
call_back() returns a value wich is a pointer to an Eu
function.
Call it from ASM or use call().
example:
atom ptr
ptr = call_back(routine_id("crap"))
call(crap)
Mike The Spike
--- Matthew Lewis <matthewwalkerlewis at YAHOO.COM>
wrote:
>
> > -----Original Message-----
> > From: stabmaster_ at HOTMAIL.COM
> [mailto:stabmaster_ at HOTMAIL.COM]
> >
> > First of all, I see an evil typo in here. You're
> storing the
> > adress to CALL
> > in EDX, but you're CALLin EAX..
> > And you shouldn't use CALL FAR, but CALL NEAR.
> >
> > This is how to call a procedure (void) with one
> parameter:
> >
> > PUSH the_parameter
> > MOV EAX, proc_address
> > CALL NEAR EAX
>
> Thanks. Unfortunately, I haven't been able to get
> that to work, so I've
> taken a different route. I wrote a little DLL (63K
> compressed) in VC that
> will call the funcs by pointer, taking up to 10
> arguments.
>
> Rob, I'd like to add this to the wishlist: call
> functions by pointer. It
> seems it shouldn't be hard to do, since you probably
> already do something
> like this for c_func.
>
> Matt Lewis
>
3. RE: ASM Help
Just a quick qusetion: You did remember to push the parameters in opposite
order, right?
e.g:
PUSH param3
PUSH param2
PUSH param1
MOV EBX, my_callback
CALL NEAR EBX
wich is the same as the following MASM code
INVOKE my_callback, param1,param2, param3
4. RE: ASM Help
> -----Original Message-----
> From: Robert Craig [mailto:rds at RapidEuphoria.com]
> Can't you use VC to disassemble, or generate an
> assembly listing of your .dll? Then you could
> poke the bytes of code into your Euphoria program,
> and eliminate the need for the .dll. Alternatively,
> you could get the address of the start of the dll routine,
> using '&' in C, and write the first 100 bytes or so to a file.
D'oh! Thanks.
I used the VC debugger and aped the machine code that VC was generating, and
now I can call functions by pointers (including Eu routines with a call_back
address!). Here's the asm code (mostly generated by asm.e, but I hand
modified the 'call' instruction in order to call using a dword pointer as
address):
constant
fptr_asm = {
#60, -- 0: pusha
#BB,#00,#00,#00,#00, -- 1: mov ebx, paramcount (2)
#B9,#00,#00,#00,#00, -- 6: mov ecx, params (7)
-- B: start: (this pushes the params onto the
stack)
#8B,#01, -- B: mov eax, [ecx]
#50, -- D: push eax
#83,#C1,#04, -- E: add ecx, 4
#4B, -- 11: dec ebx
#75,#F7, -- 12: jnz start
#FF,#15,#00,#00,#00,#00,-- 14: call dword ptr [comfunc] (22)
#89,#15,#00,#00,#00,#00,-- 1A: mov [retpointer], edx (28) (puts the
return into a buffer)
#61, -- 20: popa
#C3}, -- 21: ret
fptr_paramcount = 2,
fptr_params = 7,
fptr_funcptr = 22,
fptr_retptr = 28
Of course, call() doesn't return a value, so I had to allocate some memory
for a return value. Here's the code to call a function:
constant
fptr_asm_addr = allocate( length( fptr_asm ) )
poke( fptr_asm_addr, fptr_asm )
function call_fptr( atom fptr, sequence params )
atom ptraddr, paramptr, ret
ptraddr = allocate(4)
poke4( ptraddr, fptr )
poke4( fptr_asm_addr + fptr_funcptr, ptraddr )
params = reverse(params)
paramptr = allocate( length( params )*4)
poke4( paramptr, params )
poke4( fptr_asm_addr + fptr_params, paramptr )
poke4( fptr_asm_addr + fptr_paramcount, length(params) )
poke4( fptr_asm_addr + fptr_retptr, retval )
call( fptr_asm_addr )
ret = peek4u( retval )
free( ptraddr )
free( paramptr )
return ret
end function