gatorface gatorface - 1 month ago 8
C Question

Integer Execution in C?

I am trying to understand why

ret();
works in the following C program:

#include<stdio.h>
#include<string.h>

unsigned char code[] = \
"\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69"
"\x6e\x89\xe3\x50\x53\x89\xe1\xb0\x0b\xcd\x80";

main()
{
printf("Shellcode Length: %d\n", strlen(code));
int (*ret)() = (int(*)())code;
ret();
}


Of course you must compile the above with no stack protections, allowing the stack to be executable.

What I'm wondering though is why calling
ret();
, which appears to be an integer assigned to the value
(int(*)())code;
works...

I am guessing it has something to do with function pointers really being integers, but I have not been able to mentally unpack the implications of
int (*ret)() = (int(*)())code;


Thank you for your help

Answer Source

What I'm wondering though is why calling ret(), which appears to be an integer assigned to the value (int(*)())code works

ret is not an integer, it is a pointer to a function returning an integer. The "inline" syntax, i.e. int (*ret)() is harder to "decipher" than an equivalent typedef, i.e.

typedef int (*func_returning_int)();
...
func_returning_int ret = (func_returning_int)code;

Note: It goes without saying that this is undefined behavior regardless of the way you go about casting pointers.