Reputation: 85
I am trying to write an inline assebly function which exchanges two values.( and i'm using extended ASM format)
This code works:
#include <stdio.h>
void Exchange(int *x, int *y)
{
printf("In Exchange function: Before exchange x is: %d\n",*x);
printf("In Exchange function: Before exchange y is: %d\n",*y);
asm("xchg %%eax,%%edx\n\t" \
:"+a"(*x),"+d"(*y));
printf("In Exchange function: After exchange x is: %d\n",*x);
printf("In Exchange function: After exchange y is: %d\n",*y);
}
int main()
{
int x=20;
int y=30;
printf("In main: Before exchange x is: %d\n",x);
printf("In main: Before exchange y is: %d\n",y);
Exchange(&x,&y);
printf("In main: After exchange x is: %d\n",x);
printf("In main: After exchange y is: %d\n",y);
return 0;
}
but when i try to wirte it in full assembly like below i get segmentation fault (core dumped) error.
void Exchange(int *x, int *y)
{
asm("subl $8,%%esp\n\t" \
"movl %%eax,4(%%esp)\n\t" \
"movl %%edx,(%%esp)\n\t" \
"call printf\n\t" \
"addl $8,%%esp\n\t" \
"xchg %%eax,%%edx\n\t" \
"subl $8,%%esp\n\t" \
"movl %%eax,4(%%esp)\n\t" \
"movl %%edx,(%%esp)\n\t" \
"call printf\n\t" \
"addl $8,%%esp\n\t" \
:"+a"(*x),"+d"(*y));
}
int main()
{
int x=20;
int y=30;
printf("In main: Before exchange x is: %d\n",x);
printf("In main: Before exchange y is: %d\n",y);
Exchange(&x,&y);
printf("In main: After exchange x is: %d\n",x);
printf("In main: After exchange y is: %d\n",y);
return 0;
}
Aren't we allowed to use printf function in the assembly section?
Upvotes: 0
Views: 1034
Reputation: 126418
Your asm code calls printf with two integer arguments -- no format string. So it tries to dereference the first integer as a pointer to a format string and crashes.
Also, calling printf will clobber the values in %eax and %edx, as they are not preserved across calls in the standard x86 calling conventions.
Upvotes: 3