Assembly CALL instruction on extern labels

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
User avatar
iman
Member
Member
Posts: 84
Joined: Wed Feb 06, 2019 10:41 am
Libera.chat IRC: ImAn

Assembly CALL instruction on extern labels

Post by iman »

Hi.

I had a discussion some days ago (viewtopic.php?f=1&t=37142) regarding an issue to bring up the AP cpu with trampoline code. If you scroll down, you would see that in the end, I solved the problem, but something new draw my attention for a while. It's about how NASM perform a CALL instruction on an extern label.
So, basically, I had some C and assembly routines specified for my BSP cpu. In my trampoline code to wake up the AP cpu, I would like to have one of those routines (printing on screen) at hand. I labeled it as extern in the beginning of the code.
If I call it as

Code: Select all

call printk
it gives me a triple fault, but if instead I do

Code: Select all

mov eax, printk
call eax
or

Code: Select all

mov DWORD[mem32], printk
call DWORD[mem32]
it is completely fine and flawless.
Of course the machine code for the first call would be as E8 rel32 and for the second or third call would be something like FF r/m32.
The trampoline code itself is based at physical address 0x8000 (I put it here and jump into it when I switch the AP cpu to protected mode), but I always assumed that something like call printk, will perform the right jump into the specified address, while apparently is not the case.
The question:
Even if it is fine to perform the call instruction with the use of FF machine code, why a call instruction directly on label (E8 machine code) would be ended up in kernel crash? It puzzles me.

Best.
Iman.
Iman Abdollahzadeh
Github
Codeberg
Gigasoft
Member
Member
Posts: 856
Joined: Sat Nov 21, 2009 5:11 pm

Re: Assembly CALL instruction on extern labels

Post by Gigasoft »

If you have copied the code to another location, the operands of direct near jumps and calls will of course be relative to the new location and therefore not point to the intended target address.
User avatar
iman
Member
Member
Posts: 84
Joined: Wed Feb 06, 2019 10:41 am
Libera.chat IRC: ImAn

Re: Assembly CALL instruction on extern labels

Post by iman »

Gigasoft wrote:If you have copied the code to another location, the operands of direct near jumps and calls will of course be relative to the new location and therefore not point to the intended target address.
I did not put ORG 0x8000 in the beginning of the assembly code but instead copied it directly. Does it still make near jumps and calls relative to the new position?
Iman Abdollahzadeh
Github
Codeberg
Octocontrabass
Member
Member
Posts: 5572
Joined: Mon Mar 25, 2013 7:01 pm

Re: Assembly CALL instruction on extern labels

Post by Octocontrabass »

Yes. Direct near jumps and calls are always dependent on the position. These instructions only store the difference between the current location and the destination, so if you move the code containing the jump or call instruction to a different address, the destination address also changes.

If you tell the linker that the code will be located at 0x8000 when it runs, the linker will calculate the correct difference so the code can run when you move it to 0x8000.

ORG does not work unless you're using NASM to link your code to a flat binary.
Post Reply