Bug #7307
closedgcc -ansi vs. alloca (undefined reference to `alloca')
Description
Ruby 2.0.0からは CFLAGS に -ansi が(サポートがあれば)付くように
なりましたが、これにより、 gcc の builtin alloca に依存しており
libc に alloca(3) を持たない環境、具体的にはOpenBSD(およびおそら
くNetBSDの mips, powerpc, powerpc64, sparc, sparc64 等)で次のよう
なリンクエラーが発生します。
linking miniruby
addr2line.o(.text+0x9e7): In function follow_debuglink': /home/knu/src/ruby-trunk-vanilla/addr2line.c:424: warning: strcpy() is almost always misused, please use strlcpy() regerror.o(.text+0x499): In function
onig_vsnprintf_with_pattern':
/home/knu/src/ruby-trunk-vanilla/regerror.c:334: warning: strcat() is almost always misused, please use strlcat()
regerror.o(.text+0x55e):/home/knu/src/ruby-trunk-vanilla/regerror.c:197: warning: sprintf() is often misused, please use snprintf()
dmyencoding.o(.text+0x120e): In function set_encoding_const': /home/knu/src/ruby-trunk-vanilla/encoding.c:1535: undefined reference to
alloca'
bignum.o(.text+0xbfea): In function rb_str_to_inum': /home/knu/src/ruby-trunk-vanilla/bignum.c:791: undefined reference to
alloca'
object.o(.text+0x11c2): In function rb_str_to_dbl': /home/knu/src/ruby-trunk-vanilla/object.c:2565: undefined reference to
alloca'
parse.o(.text+0x1e24): In function parser_yyerror': /home/knu/src/ruby-trunk-vanilla/build.unknown.openbsd-amd64/parse.y:5221: undefined reference to
alloca'
parse.o(.text+0xb2c8): In function parser_tokadd_string': /home/knu/src/ruby-trunk-vanilla/build.unknown.openbsd-amd64/parse.y:6072: undefined reference to
alloca'
parse.o(.text+0xb2fb):/home/knu/src/ruby-trunk-vanilla/build.unknown.openbsd-amd64/parse.y:6085: more undefined references to `alloca' follow
collect2: ld returned 1 exit status
*** Error code 1
Stop in /home/knu/src/ruby-trunk-vanilla/build.unknown.openbsd-amd64 (line 180 of Makefile).
なぜ(configure は成功するのに)こけるかの説明は以下の通りです。
- autoconf の AC_FUNC_ALLOCA は次のようなコードによるテストに展開
されるので、 gcc を使う限りは alloca は __builtin_alloca に置き換
わるので configure は成功する
#ifdef GNUC
define alloca __builtin_alloca¶
#else
ifdef _MSC_VER¶
include <malloc.h>¶
define alloca _alloca¶
else¶
ifdef HAVE_ALLOCA_H¶
include <alloca.h>¶
else¶
ifdef _AIX¶
#pragma alloca
else¶
ifndef alloca /* predefined by HP cc +Olibcalls */¶
void *alloca (size_t);
endif¶
endif¶
endif¶
endif¶
#endif
-
gcc は -ansi を付けると alloca を提供しなくなる
(__builtin_alloca は常にある) -
ruby のソースツリーでは(マクロを通じて)広く alloca が使われて
いるが、上記1のような alloca のケア(置換)を行っているのは gc.c
や #include "eval_intern.h" しているもののみ -
しかし、基本的にすべてのファイルが -ansi 付きでビルドされるので、
addr2line.o, regerror.o, encoding.o 等々に alloca への参照が埋まっ
てしまい、 libc に alloca がない環境ではリンクエラーとなる
解決策は、 ruby/ruby.h の alloca 関連部を gc.c などにあるような
gcc 対応を含む完全なものにすることです。
下のパッチを適用し、以下の環境で make test が通りました。
- OpenBSD/amd64 5.2-RELEASE (GCC 4.2.1) - libc has no alloca
- FreeBSD/amd64 9.1-PRERELEASE (GCC 4.2.1)
- FreeBSD/amd64 9.1-PRERELEASE (clang 3.1)
- Mac OS X 10.8.2 (Apple clang 4.1)
問題なければコミットします。
Files