I have this piece of code to test a shellcode but I don't understand it so can anyone explain it to me?
Forget about the assembly shellcode, what I want to understand is the C code,
char shellcode[] = "...";
int main(int argc, char **argv)
{
int (*func)();
func = (int (*)()) shellcode;
(int)(*func)();
}
I mean everything, what are the empty ()
, please explain it as if you are explaining it to a beginner.
int (*func)();
This is a declaration of a function pointer. A function pointer is essentially a variable that holds the address of a function. In this case, the type of function that func
points to is a one that takes no arguments and returns an int
. You can assign the address of a function to this variable like so:
func = foo;
Where foo
is a function with the prototype int foo();
.
Once a function has been assigned to this variable, you can call the function that func
points to like so:
(*func)();
There is an alternate syntax (which is equivalent), which I think is more clear:
func();
So if foo
was assigned to func
, then both examples above would actually call the function foo
.
You can also cast values to function pointers. In the code example
(int (*)())
is a cast to a function pointer that takes no arguments and returns an int
. This is so the compiler won't complain about assigning what is essentially a char*
to the function pointer func
.
In the code you gave above, there is one last thing. After func
is called, the result is (for some reason) cast to an int
. As far as I can tell, this cast is totally unnecessary. So the last line
(int)(*func)();
could be replaced with
(*func)();
int (*func)();
is the definition of a pointer to a function with return type int
, func = (int (*)()) shellcode;
assigns a function pointer an address to the shellcode[]
(assembler bytecode, the instructions your CPU executes), (int)(*func)();
calls the function by its address (assembler instructions) with no arguments passed, because ()
is specified. For example the assembler instruction \x90
has name NOP
(N o Op eration) and does nothing, other assembler instructions do different things depending on the system you're executing them on.