Inline Assembly & C Question - Concerning Variables

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
SteveB

Inline Assembly & C Question - Concerning Variables

Post by SteveB »

Hi.

I know this isn't the best place to put this but I thought I'd put it here since this is related to OS development for me.

What I want to do, for example, is move the information from eax into a variable defined in C. How would I do this properly? Basically what I want to do is move data from a register into a C variable.

I've tried several ways which were messy since I don't grasp the GCC inline syntax very well. The times I tried and got the C file to compile, it failed when I linked them into the bin.

Thank you,

- Steve
paulbarker

Re:Inline Assembly & C Question - Concerning Variables

Post by paulbarker »

Take a look at the GCC manual (the best place is online at http://gcc.gnu.org/ ). You need to learn about how the constraints operate, but heres a trick. Do a 'nop' with your variable loaded from eax as an output:

Code: Select all

asm volatile ("nop": "=a" (dest)::)
This is a very quick idea, the code above is probably wrong in terms of the letter after the "=" and the number of colons between the nop and the =, but the general idea should be right. Please check this against the manual before trying it.
proxy

Re:Inline Assembly & C Question - Concerning Variables

Post by proxy »

what i do for these situations is define a set of ASM fucntions with C interfaces that fit the form:

uint32_t get_eax(void); for each register

they look like this: (a few examples)

Code: Select all

get_eip:
   mov (%esp), %eax
   ret

get_eax:
   ret

get_ebx:
   mov %ebx, %eax
   ret
setting is easier as an inline ASM macro:

Code: Select all

#define set_eax(val) do { __asm__ __volatile__ ("mov %0, %%eax" :: "r" (val)); } while(0)
proxy
User avatar
Pype.Clicker
Member
Member
Posts: 5964
Joined: Wed Oct 18, 2006 2:31 am
Location: In a galaxy, far, far away
Contact:

Re:Inline Assembly & C Question - Concerning Variables

Post by Pype.Clicker »

the real question is "what is in eax and why should it be somewhere else ?"

If the data is indeed in eax (or in eax:edx) as the result of a function call, then everything is fine: that's where C expect data to be returned!

e.g.

Code: Select all

global foo
foo: 
    mov eax, 0x12345678
    ret

Code: Select all

unsigned foo(void);
bar() {
   unsigned baz=foo();
   // f is now 0x12345678
}
If you need to access a C variable from ASM code, just make sure you know its linking name (that may be baz, _baz, __baz_Q26kernel depending on your compiler/language/environment. yet 'baz' is typical for linux and _baz for windows). Then

Code: Select all

extern baz
foo:
    mov [baz],eax
    ret
should do it too...

If you're instead trying to support something like "CPUID" from C, i suggest you look at the "Sample Inline Functions" page on the FAQ. It should show you how to access not only EAX, but all the other potential output registers from inlined assembly.
Post Reply