[ruby-dev:47917] Re: [ruby-changes:32633] nobu:r44712 (trunk): thread_pthread.c: get current main thread stack size
From:
KOSAKI Motohiro <kosaki.motohiro@...>
Date:
2014-01-28 01:06:33 UTC
List:
ruby-dev #47917
Ruby-devに河岸をうつしました。
On Mon, Jan 27, 2014 at 7:53 AM, nobu <ko1@atdot.net> wrote:
> nobu 2014-01-27 21:53:48 +0900 (Mon, 27 Jan 2014)
>
> New Revision: 44712
>
> http://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=rev&revision=44712
>
> Log:
> thread_pthread.c: get current main thread stack size
>
> * thread_pthread.c: get current main thread stack size, which may
> be expanded than allocated size at initialization, by rlimit().
> [ruby-core:60113] [Bug #9454]
>
> Modified files:
> trunk/ChangeLog
> trunk/test/ruby/test_exception.rb
> trunk/thread_pthread.c
> Index: ChangeLog
> ===================================================================
> --- ChangeLog (revision 44711)
> +++ ChangeLog (revision 44712)
> @@ -1,3 +1,15 @@ https://github.com/ruby/ruby/blob/trunk/ChangeLog#L1
> +Mon Jan 27 21:53:45 2014 Nobuyoshi Nakada <nobu@ruby-lang.org>
> +
> + * thread_pthread.c: get current main thread stack size, which may
> + be expanded than allocated size at initialization, by rlimit().
> + [ruby-core:60113] [Bug #9454]
> +
> +Mon Jan 27 21:52:55 2014 Nobuyoshi Nakada <nobu@ruby-lang.org>
> +
> + * thread_pthread.c: get current main thread stack size, which may
> + be expanded than allocated size at initialization, by rlimit().
> + [ruby-core:60113] [Bug #9454]
> +
> Sat Jan 25 22:17:02 2014 Kazuhiro NISHIYAMA <zn@mbf.nifty.com>
>
> * README.ja.md, README.md: update the controller address of
> Index: thread_pthread.c
> ===================================================================
> --- thread_pthread.c (revision 44711)
> +++ thread_pthread.c (revision 44712)
> @@ -1562,6 +1562,14 @@ ruby_stack_overflowed_p(const rb_thread_ https://github.com/ruby/ruby/blob/trunk/thread_pthread.c#L1562
>
> if (th) {
> size = th->machine_stack_maxsize;
> +#if defined(HAVE_GETRLIMIT) && MAINSTACKADDR_AVAILABLE
> + if (pthread_equal(th->thread_id, native_main_thread.id)) {
> + struct rlimit rlim;
> + if (getrlimit(RLIMIT_STACK, &rlim) == 0 && rlim.rlim_cur > size) {
> + size = rlim.rlim_cur;
> + }
> + }
> +#endif
これが間違ってることは分かるが、どうしたいのかが分からない。
チケットに一切情報がないのはいつものこととはいえ・・・・・
まず、単純にifdefにRLIMIT_STACKの有無が抜けているというのもあるが、
メインスレッドならRLIM_STACKで取れるというのがLinux固有なので、
それはHAVE_GETRLIMITとかの機能有無じゃなく、ifdef linux でないと
おかしいように思える。
Linuxだとrlim_curがulongでinfinityが-1だからつまりULONG_MAX扱いになって
常にオーバーフロー扱いにならない。
というか RLIM_INFINITY の値はOS依存だから大小比較するまえに
if (rlim.rlim_cur == RLIM_INFINITY) とかないとおかしくないですか?
次に、get_stack()で使っているpthread_getattr_np()はもうちょっと賢いことをやっていて、
/proc/self/mapsみてVMAのサイズを超えないように調整してる。これを避けたのは
たぶん、シグナルコンテキストというのを意識したのだと思うし、それは正しいと
思うのだけど、ちょっとラフすぎる印象。
どうせ current threadとれないときは、get_stack呼んじゃってるんだから、これだったら
メインスレッドのケースも get_stack呼んでしまったほうが誤判定減るように思えます。
チケットに書いてない、OSのバグ情報などありましたら教えて下さい。