ruby-trunk-changes r45615 - r45635

今日は文字列まわりで内部的にいろいろ変更があって、codepage の検出の最適化や、一時的に部分文字列の共有化の条件の緩和(そのかわり RSTRING_PTR() が '\0' で終わらない場合があるようになる)がありました。今はやっぱりこれまで通り文字列の末尾を共有する時だけ共有文字列を使えるようになっています。

nobu: r45615 2014-04-18 08:50:20 +0900

r45598 で POSIX.1-2001 の拡張である getcwd(3) の引数に NULL を渡してライブラリ関数内でメモリ確保してもらう機能を使うようにしましたが、Solaris で動かなかったそうで configure でチェックして使えない時は NO_GETCWD_MALLOC マクロを定義するようにしています。 [ruby-core:62072] [Bug #9752]

svn: r45616 2014-04-18 08:50:24 +0900

version.h の日付更新。

naruse: r45617 2014-04-18 15:42:51 +0900

文字列の文字数計算の UTF-8 用特別処理(高速化のための)を str_strlen() から enc_strlen() に移動しています。 関数呼び出しのより深い位置にあるエンコーディング毎の処理を書いているところに移動しているようです。

naruse: r45618 2014-04-18 15:43:08 +0900

文字列の文字数をカウントする str_strlen() で一度 rb_enc_strlen_cr() で coderange がわかったら struct RBasic::flags にセットして次回からはそれを利用して直接 enc_strlen() を呼んで高速化するようにしています。

naruse: r45619 2014-04-18 15:43:11 +0900

str_strlen() の第2引数に NULL を渡したら第1引数の文字列のエンコーディングを利用するようにして、明示的に str_strlen(str, STR_ENC_GET(str)); のように渡していたところを NULL 渡しに変更しています。

naruse: r45620 2014-04-18 15:43:29 +0900

同じく文字列長カウントに関する関数 search_nonascii()、count_utf8_lead_bytes_with_word()、enc_strlen()、str_utf8_nth() などでなぜか文字列のポインタを VALUE * で扱っていたところがあったのを uintptr_t * を使うように変更しています。 ワード幅で処理して高速化しているのでしょうけど。

nobu: r45621 2014-04-18 16:55:04 +0900

文字列を連結する str_buf_cat() で rb_str_modify() を呼んでいたところを coderange を保持するように str_modify_keep_cr() の呼び出しに変更しています。 けど文字列追加したら coderange の再検索必要になるような気がしますけど…

nobu: r45622 2014-04-18 17:00:04 +0900

rb_str_modify_expand() で ENC_CODERANGE_CLEAR() で flags に記憶している coderange をクリアしているのを ENC_CODERANGE_BROKEN の時だけにしています。こっちは文字列の内容は(まだ)変更していないのでいいのでしょうけど、今までここでクリアしてたから追記時にクリアしてない箇所があったりしそう…。

nobu: r45623 2014-04-18 17:17:44 +0900

やっぱり 45621 の str_buf_cat() での rb_str_modify() -> str_modify_keep_cr() の変更は revert しています。 str_buf_cat() では coderange を再検索していないので coderange のクリアが必要でした。

nobu: r45624 2014-04-18 17:27:09 +0900

r45622 も revert しています。やっぱり後で coderange を変更してないところがあったっぽいですね。

nobu: r45625 2014-04-18 20:46:02 +0900

拡張ライブラリ zlib の zstream_shift_buffer() でバッファに使っている文字列オブジェクトから rb_str_subseq() と rb_obj_reveal() を使って無理矢理内部的オブジェクトのコピーを作っていたのを rb_str_new() で単にバッファからコピーを作るように修正しています。

nobu: r45626 2014-04-18 20:46:04 +0900

拡張ライブラリ openssl で文字列オブジェクトから NUL-terminated な C の文字列を取り出すべく StringValueCStr() を呼び出すようにしています。そういえば RSTRING_PTR() って NUL-terminated という保証はないんでしたっけ(実際にはされてたと思いますが)。

nobu: r45627 2014-04-18 21:42:04 +0900

README.EXT の Appendix B に関数マクロ RSTRING_LEN() と RSTRING_PTR() についての言及を追加して、RSTRING_PTR() は NUL-terminated とは限らないということを書いています。また StringValueCStr() で取得できる char * な文字列は NUL-terminated が保証されることも追記しています。

nobu: r45628 2014-04-18 21:48:26 +0900

部分文字列を作る時に共有文字列オブジェクトを生成する場合、文字列の途中までの部分文字列はこれまで NUL-terminated にするために共有できなかったのですが、それも可能にしています。このため RSTRING_PTR() が NUL-terminated とは限らないケースが実際に発生するようになっています、これはかなり影響デカい。と思ったら後でやっぱり当面はやめるようにしているみたいです。

nobu: r45629 2014-04-18 23:27:22 +0900

r45628 で文字列の途中までの部分文字列を共有文字列で実現できるようになったのを受けて parse.y の lex_get_str() でスクリプト全体の文字列から1行ずつコピーするのではなくて rb_str_subseq() で部分文字列として切り出すようにしています。

nobu: r45630 2014-04-19 00:09:49 +0900

time.c の month_arg()、time_strftime() などで RSTRING_PTR() が NUL-terminated であることを前提とした部分があったので RSTRING_LEN() を考慮した処理に修正しています。

svn: r45631 2014-04-19 00:09:53 +0900

version.h の日付更新。

nobu: r45632 2014-04-19 00:11:35 +0900

NEWS、README.EXT などで NULL-terminated -> NUL-terminated と typo 修正しています。

nobu: r45633 2014-04-19 00:17:21 +0900

SHARABLE_SUBSTRING_P() という文字列の部分文字列が共有文字列で共有できるかを判定するマクロを追加して、デフォルトではこれまで通り文字列の末尾部分のみ共有できるように戻しています。いずれは途中までの部分文字列も共有化したいとのこと。

akr: r45634 2014-04-19 00:46:32 +0900

rb_big2ulong()、rb_num2ulong() や rb_big2long()、rb_num2long() がそれぞれ VALUE や SIGNED_VALUE 型を返すように宣言されていたのを long/unsigned long を返すように宣言を変更しています。 なんか当初は理由があったんだったような気もしますけど、xxx2long() が long を返してなかったというのはトラップですよね。

nobu: r45635 2014-04-19 00:51:06 +0900

r45634 の ChangeLog エントリの行末の空白を除去しています。