请教mik版主:考虑IA32的ABI,像printf这样的带有可变数目参数的函数
请教mik版主:考虑IA32的ABI,像printf这样的带有可变数目参数的函数,怎么知道该从stack上取几个参数?libc库已经编译好了, 我写个hello程序,调用printf -- 它怎么知道我传了几个参数给它呢? 难道gcc编译 library的时候,是对可变参数函数单独处理的?
谢谢! 传了几个参数,完全在于调用者的指示;
如果调用者没有任何指示,可变参数函数是不知道调用者使用了几个参数的。
最常用的是在第一个参数上指示。
比如printf("%s:%d"....
根据第一个参数,知道printf还有两个参数。
再比如我们熟悉的open系统调用,可以带两个或者三个参数,这是在第二个参数上指示的。 原帖由 albcamus 于 2008-9-1 16:17 发表 http://linux.chinaunix.net/bbs/images/common/back.gif
请教mik版主:考虑IA32的ABI,像printf这样的带有可变数目参数的函数,怎么知道该从stack上取几个参数?
libc库已经编译好了, 我写个hello程序,调用printf -- 它怎么知道我传了几个参数给它呢? 难道gcc ...
这和ABI有什么关系呢?
它是从fmt字符串解析需要几个参数,然后从栈上取相应的个数出来,你也可以传多余的参数进去,只不过不会用罢了。
例如
printf("%d\n",1,2,3);
printf("%d,%d,%d\n",1); 原帖由 zx_wing 于 2008-9-1 16:31 发表 http://linux.chinaunix.net/bbs/images/common/back.gif
这和ABI有什么关系呢?
它是从fmt字符串解析需要几个参数,然后从栈上取相应的个数出来,你也可以传多余的参数进去,只不过不会用罢了。
例如
printf("%d\n",1,2,3);
printf("%d,%d,%d\n",1);
有关系啊, abi只规定从stack传递,但是没规定怎么指示传了几个。因此, printf的汇编代码, 必须想办法知道自己获得了几个参数。
难道是通过分析fmt得来的? 原帖由 albcamus 于 2008-9-1 16:38 发表 http://linux.chinaunix.net/bbs/images/common/back.gif
有关系啊, abi只规定从stack传递,但是没规定怎么指示传了几个。因此, printf的汇编代码, 必须想办法知道自己获得了几个参数。
难道是通过分析fmt得来的?
没有任何的指示作用的话,可变参数函数是无从得知参数的个数的。
无论是很隐藏的指示,还是很显然的指示,你总是要指示的。
以下是显型指示
func(n,....)
n为参数个数 机器级不像脚本级,一般来说不会直接说明参数个数。
也就是对于函数func(.....)
机器在函数调用的时候不会传一个参数个数进去(我不敢说机器级表示一定不会,原理上这样的机器是存在的,只是我没有见过)。
而脚本则不同:
比如shell
因为参数字符串里已经潜在的指示了参数的个数 原帖由 albcamus 于 2008-9-1 16:38 发表 http://linux.chinaunix.net/bbs/images/common/back.gif
有关系啊, abi只规定从stack传递,但是没规定怎么指示传了几个。因此, printf的汇编代码, 必须想办法知道自己获得了几个参数。
难道是通过分析fmt得来的?
"它是从fmt字符串解析需要几个参数,然后从栈上取相应的个数出来,你也可以传多余的参数进去,只不过不会用罢了。"
前面回复已经说了啊,是从fmt分析得到的,也举了两个参数个数不对的例子。
和ABI有关系的我记得就只有x86_64的系统调用,编译后会用eax传参数个数。printf是没有关系的 原帖由 cjaizss 于 2008-9-1 16:43 发表 http://linux.chinaunix.net/bbs/images/common/back.gif
没有任何的指示作用的话,可变参数函数是无从得知参数的个数的。
无论是很隐藏的指示,还是很显然的指示,你总是要指示的。
以下是显型指示
func(n,....)
n为参数个数
如果calling 和called function都是我自己写的, 那么编译器很直接就知道我传递了几个参数给called function, 从而生成汇编代码时很容易;
我现在就是糊涂, gcc编译库函数时, 怎么为它指定参数个数。。。 原帖由 albcamus 于 2008-9-1 16:48 发表 http://linux.chinaunix.net/bbs/images/common/back.gif
如果calling 和called function都是我自己写的, 那么编译器很直接就知道我传递了几个参数给called function, 从而生成汇编代码时很容易;
我现在就是糊涂, gcc编译库函数时, 怎么为它指定参数个数 ...
呵呵,只能靠调用者的指示。
除非有人造出了一台机器(或者其实编译器也行),在传递参数的时候对参数个数压栈(不知道有没有这样的编译器,不敢乱说,因为原理上可以存在,在看到申明的时候就知道是可变参数,那么遇到可变参数,就多压了个数),函数用这个个数来指定其参数的个数,当然其实这也是调用者的指示 http://bbs.chinaunix.net/viewthread.php?tid=1010016&extra=page%3D1%26amp%3Bfilter%3Ddigest&page=1
看这个帖子,去年的,第二页
页:
[1]
2