I am creating a Kernel and I need some help with the call instruction. I am using Flat Assembler to build the Kernel.
call fs:bx
Is that possible ?
Because flat assembler gives me an "invalid size of operand" Error.
I know I can do
call 1000h:0h
But that is not what I want. Does someone have the answer to this question?
I'm assuming you want call fs:bx
to set cs=fs
and ip=bx
, as a far call.
Indirect far calls require the seg:offset to be in memory, not registers. See the insn ref entry for call
to confirm that the only available indirect far call
is the call m16:16
form.
So in 16-bit code, you could
push fs
push bx
... ; push args
far call [bp-whatever] ; assuming you know the difference between bp and sp at this point
add sp, 4 + arg_size ; clean up args and the far-pointer
Or reserve space on the stack ahead of time so you can do something like
my_function:
push bp
mov bp, sp
sub sp, 16 ; or whatever size you need for locals. 16 and 8 are just for example.
...
mov [bp - 8], fs
mov [bp - 6], bx ; separately store both parts of fs:bx into [bp-8]
far call [bp - 8]
...
leave
ret
You can't mov cs, fs
or anything like that (even using a scratch GP register). Changing cs
would be a jump, so you have to do the whole thing as one far call
.
Of course, you probably only put the segment value in fs
in the first place to set up for this instruction, so don't do that in the first place.