Function pointer declaration syntax confusion [duplicate]

*爱你&永不变心* 提交于 2019-12-23 12:09:40

问题


I have read and googled about the right-left rule to decode function pointers.

For ex:

int (*(*fun_one)(char *,double))[9][20];

is: fun_one is pointer to function expecting (char *,double) and returning pointer to array (size 9) of array (size 20) of int.

So what is

const char code[] = "\x31\xc0";

int main(){
     ((void(*)( ))code)();
}

"code is ?? returning a pointer to function returning void...???? what about after that the outside ()"

I am utterly confused with this one.


回答1:


const char code[] = "\x31\xc0";

int main(){
     ((void(*)( ))code)();
}

Here's how it works. The code variable will decay to the address of the first element (\x31).

That address will then be cast to the address of a function taking indeterminate arguments, and returning nothing.

That covers the entire ((void(*)( ))code) bit and, up to there, you've basically constructed a function pointer pointing to your string.

The () then simply calls the function that you're pointing to.

If that's an Intel CPU you're targeting, 31 c0 disassembles to xor eax, eax but I'm not expecting much joy when it runs off the end of the buffer, it's likely to crash spectacularly. The \x00 marking the end of the string is the first bit of an add instruction but, as to what comes after that, there's no guarantee.

Adding a ret instruction to the end of the string may make it safer but you may have to examine the generated assembler code for the call itself to figure out which ret should be used.




回答2:


That's not a function pointer declaration, it's a function pointer cast and a call.

Glossing over the cast for a moment, we have ((sometype)code)() — that is, cast code to some type (obviously a function pointer) and then call it.

So what's the type inside the cast? It's void (*)(). In other words, a pointer to a function that returns void and takes nothing in particular (it actually can take arguments, thanks to C legacy, but in this case it doesn't). Nothing in, nothing out.

After the * is where the name would go if this was a declaration, but since it's a cast, the type stands alone and there's no name at all.




回答3:


You are confused because it's not a function pointer declaration, but a cast followed by a function call.

(void (*)()) code 

This casts code to a pointer to a function taking an unspecified number of arguments returning nothing.

((void (*)()) code) 

This is the whole expression above enclosed in parentheses; the result is a function pointer.

(void (*)() code)();

This calls the function to which the function pointer "created" by the cast points.

This is effectively trying to call some machine code constructed in code - here you are omitting the rest, but 31 c0 is the usual xor eax,eax.



来源:https://stackoverflow.com/questions/33624012/function-pointer-declaration-syntax-confusion

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!