summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author(no author) <(no author)@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>1998-02-10 08:44:05 +0000
committer(no author) <(no author)@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>1998-02-10 08:44:05 +0000
commit36f3603cae6536e571220721e916b8d284cf0675 (patch)
treeeb9605811483000f6980263aa163b4f627ab1c3f
parentfd1d8cdc09ed86e4a0812120a17ff0d7b04adcaf (diff)
This commit was manufactured by cvs2svn to create tag 'v1_1b7'.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/tags/v1_1b7@70 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
-rw-r--r--.cvsignore1
-rw-r--r--ChangeLog152
-rw-r--r--MANIFEST5
-rw-r--r--README.EXT.jp1079
-rw-r--r--array.c49
-rw-r--r--bignum.c18
-rw-r--r--class.c44
-rw-r--r--compar.c2
-rw-r--r--dir.c2
-rw-r--r--dln.c10
-rw-r--r--enum.c22
-rw-r--r--error.c4
-rw-r--r--eval.c507
-rw-r--r--ext/Setup1
-rw-r--r--ext/dbm/dbm.c21
-rw-r--r--ext/extmk.rb.in2
-rw-r--r--ext/fcntl/fcntl.c2
-rw-r--r--ext/gtk/MANIFEST18
-rw-r--r--ext/gtk/extconf.rb6
-rw-r--r--ext/gtk/gtk.c5904
-rw-r--r--ext/gtk/test.rb96
-rw-r--r--ext/gtk/test.xpm92
-rw-r--r--ext/gtk/test0.rb13
-rw-r--r--ext/gtk/test1.rb41
-rw-r--r--ext/gtk/test2.rb89
-rw-r--r--ext/gtk/test3.rb16
-rw-r--r--ext/gtk/test4.rb77
-rw-r--r--ext/gtk/test5.rb63
-rw-r--r--ext/gtk/test6.rb49
-rw-r--r--ext/gtk/test7.rb49
-rw-r--r--ext/gtk/test8.rb49
-rw-r--r--ext/gtk/test9.rb98
-rw-r--r--ext/gtk/testa.rb78
-rw-r--r--ext/gtk/testb.rb78
-rw-r--r--ext/gtk/testc.rb64
-rw-r--r--ext/marshal/MANIFEST5
-rw-r--r--ext/marshal/depend2
-rw-r--r--ext/marshal/extconf.rb1
-rw-r--r--ext/marshal/marshal.c850
-rw-r--r--ext/marshal/marshal.doc48
-rw-r--r--ext/socket/socket.c2
-rw-r--r--ext/tcltklib/extconf.rb105
-rw-r--r--file.c134
-rw-r--r--gc.c34
-rw-r--r--hash.c39
-rw-r--r--inits.c2
-rw-r--r--instruby.rb1
-rw-r--r--intern.h3
-rw-r--r--io.c129
-rw-r--r--io.h3
-rw-r--r--keywords2
-rw-r--r--lex.c44
-rw-r--r--lib/Env.rb28
-rw-r--r--lib/complex.rb4
-rw-r--r--lib/date.rb72
-rw-r--r--lib/delegate.rb21
-rw-r--r--lib/e2mmap1_0.rb71
-rw-r--r--lib/final.rb41
-rw-r--r--lib/finalize.rb150
-rw-r--r--lib/ftplib.rb2
-rw-r--r--lib/getopts.rb2
-rw-r--r--lib/mathn.rb4
-rw-r--r--lib/matrix.rb2
-rw-r--r--lib/mutex_m.rb4
-rw-r--r--lib/parsearg.rb2
-rw-r--r--lib/parsedate.rb79
-rw-r--r--lib/rational.rb4
-rw-r--r--lib/sync.rb9
-rw-r--r--lib/tempfile.rb88
-rw-r--r--lib/thread.rb30
-rw-r--r--lib/tk.rb25
-rw-r--r--lib/tkcore.rb528
-rw-r--r--lib/tkmenubar.rb137
-rw-r--r--lib/tkthcore.rb550
-rw-r--r--lib/tracer.rb107
-rw-r--r--lib/weakref.rb2
-rw-r--r--marshal.c2
-rw-r--r--math.c2
-rw-r--r--missing/dir.h21
-rw-r--r--node.h11
-rw-r--r--numeric.c57
-rw-r--r--object.c37
-rw-r--r--pack.c2
-rw-r--r--parse.y82
-rw-r--r--process.c9
-rw-r--r--random.c2
-rw-r--r--range.c2
-rw-r--r--re.c10
-rw-r--r--re.h2
-rw-r--r--regex.c3389
-rw-r--r--ruby.12
-rw-r--r--ruby.c3
-rw-r--r--ruby.h21
-rw-r--r--rubytest.rb1
-rw-r--r--sample/fib.scm4
-rw-r--r--sample/from.rb22
-rw-r--r--sample/io.rb44
-rw-r--r--sample/rbc.rb46
-rw-r--r--sample/ruby-mode.el20
-rw-r--r--sample/test.rb2
-rw-r--r--sample/tkfrom.rb40
-rw-r--r--sprintf.c8
-rw-r--r--st.c435
-rw-r--r--st.h52
-rw-r--r--string.c142
-rw-r--r--time.c25
-rw-r--r--util.c2
-rw-r--r--util.h2
-rw-r--r--variable.c137
-rw-r--r--version.c4
-rw-r--r--version.h4
-rw-r--r--win32/sdbm.c4
112 files changed, 6887 insertions, 9928 deletions
diff --git a/.cvsignore b/.cvsignore
index c1bdd084b3..2474526e2a 100644
--- a/.cvsignore
+++ b/.cvsignore
@@ -1,3 +1,4 @@
+Makefile
parse.c
newver.rb
ruby
diff --git a/ChangeLog b/ChangeLog
index 029e20077c..23faf77d93 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,153 @@
+Tue Feb 10 17:29:08 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * string.c (str_aset): string insertion by `str[n] = str2'.
+
+ * string.c (str_oct): does recognize `0x'.
+
+ * sprintf.c (f_sprintf): use baes 10 for conversion from string to
+ integer.
+
+Mon Feb 9 14:51:56 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * numeric.c (do_coerce): proper error message.
+
+ * string.c (str_sum): bug - masked by wrong value. (sigh..)
+
+Sat Feb 7 15:11:14 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * string.c (str_empty): new method
+
+Fri Feb 6 01:42:15 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * time.c (time_asctime): use asctime(3), not strftime(3).
+
+Thu Feb 5 18:58:46 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * io.c (io_fptr_close): do not free path on close().
+
+ * array.c (ary_filter): new method.
+
+ * enum.c (enum_each_with_index): new method.
+
+Thu Feb 5 14:10:35 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * parse.y (primary): singleton class def can be appeared inside
+ method bodies.
+
+ * hash.c (hash_replace): replace content.
+
+ * string.c (str_replace_method): replace content.
+
+ * array.c (ary_replace_method): replace elements.
+
+ * string.c (str_succ_bang): String#succ!
+
+Thu Feb 5 18:20:30 1998 WATANABE Hirofumi <watanabe@ase.ptg.sony.co.jp>
+
+ * string.c (str_upcase_bang): multi byte character support.
+
+Wed Feb 4 13:55:26 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * array.c (ary_reverse): SEGV on empty array reverse.
+
+Tue Feb 3 12:24:07 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * re.c (match_to_a): non matching element should be nil.
+
+ * ruby.c (ruby_load_script): load script after all initialization.
+
+ * bignum.c (str2inum): need to interpret prefix `0' of `0x'.
+
+Tue Feb 3 10:00:18 1998 WATANABE Hirofumi <watanabe@ase.ptg.sony.co.jp>
+
+ * numeric.c (fix_rshift): use `sizeof(INT)*8' instead of 32.
+
+Mon Feb 2 14:09:24 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * ruby.c (set_arg0): grab environment region too.
+
+Thu Jan 29 18:36:25 1998 WATANABE Hirofumi <watanabe@ase.ptg.sony.co.jp>
+
+ * process.c (rb_proc_exec): check `sh' to be exist.
+
+Thu Jan 29 18:18:19 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * io.c (io_stdio_set): assignment to $stdin or $stdout does
+ reopen() as well as $stderr.
+
+Thu Jan 29 14:18:40 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * class.c (mod_ancestors): should not include singleton classes.
+
+ * object.c (obj_type): should not return internal class.
+
+ * io.c (io_reopen): unwillingly closes stdio streams.
+
+Thu Jan 29 11:50:35 1998 Toshihiko SHIMOKAWA <toshi@csce.kyushu-u.ac.jp>
+
+ * ext/socket/socket.c (udp_addrsetup): forgot to use htons().
+
+Tue Jan 27 23:15:24 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * keywords: __FILE__, __LINE__ are available again.
+
+Fri Jan 23 14:19:28 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * version 1.1b6 released.
+
+ * object.c (mod_to_s): need to duplicate classpath.
+
+ * error.c (exc_inspect): need to duplicate classpath.
+
+Thu Jan 22 00:37:47 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * ruby.h (STR2CSTR): new macro to retrieve char*.
+
+ * class.c (rb_define_method): `initialize' should always be
+ private, even if it defined by C extensions.
+
+ * eval.c (rb_eval): `initialize' should always be private.
+
+Thu Jan 22 16:21:08 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * eval.c (rb_eval): some singleton class def cause SEGV.
+
+ * eval.c (TMP_ALLOC): replace ALLOCA_N, where thread context
+ switch may happen.
+
+Wed Jan 21 01:43:42 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * eval.c (PUSH_FRAME): do not use ALLOCA_N(). crash on some
+ platforms that use missing/alloca.c.
+
+ * regex.c (re_compile_pattern): too many pops for non register
+ subexpr.
+
+ * parse.y (yylex): open parentheses after identifiers are argument
+ list, even if whitespaces have seen.
+
+Tue Jan 20 15:19:59 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * parse.y (terms): quoted word list by %w(a b c).
+
+ * ext/tcltklib/extconf.rb: more accurate check for tcl/tk libs.
+
+ * file.c (rb_stat): most of the FileTest methods (and function
+ `test') accept File objects as the argument.
+
+Tue Jan 19 18:19:24 1998 WATANABE Hirofumi <watanabe@ase.ptg.sony.co.jp>
+
+ * ext/extmk.rb.in (install): there should be no newline after install:
+
+ * re.c (MIN): renamed from min(). there's a local variable named
+ min in the file, so that some cpp will raise an error.
+
+Mon Jan 19 16:30:05 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+
+ * version 1.1b5 released.
+
+ * process.c (rb_syswait): no exception raised.
+
Fri Jan 16 00:43:43 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
* ruby.h (CLONESETUP): copies its singleton classes too.
@@ -27,6 +177,8 @@ Tue Jan 13 10:00:18 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
Fri Jan 9 13:19:55 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
+ * version 1.1b4 released.
+
* eval.c (f_missing): class name omitted from the error message.
* error.c (exc_inspect): description changed.
diff --git a/MANIFEST b/MANIFEST
index 2bdaf290b3..095588c57a 100644
--- a/MANIFEST
+++ b/MANIFEST
@@ -5,6 +5,7 @@ Makefile.in
README
README.jp
README.EXT
+README.EXT.jp
ToDo
array.c
bignum.c
@@ -81,6 +82,7 @@ ext/extmk.rb.in
ext/extmk.rb.nt
ext/aix_ld.rb
lib/English.rb
+lib/Env.rb
lib/base64.rb
lib/cgi-lib.rb
lib/complex.rb
@@ -90,6 +92,7 @@ lib/delegate.rb
lib/e2mmap.rb
lib/eregex.rb
lib/find.rb
+lib/final.rb
lib/finalize.rb
lib/ftplib.rb
lib/ftools.rb
@@ -110,6 +113,7 @@ lib/pstore.rb
lib/rational.rb
lib/shellwords.rb
lib/sync.rb
+lib/tempfile.rb
lib/thread.rb
lib/thwait.rb
lib/tk.rb
@@ -117,6 +121,7 @@ lib/tkcanvas.rb
lib/tkclass.rb
lib/tkdialog.rb
lib/tkentry.rb
+lib/tkmenubar.rb
lib/tkscrollbox.rb
lib/tktext.rb
lib/tracer.rb
diff --git a/README.EXT.jp b/README.EXT.jp
new file mode 100644
index 0000000000..980aff0394
--- /dev/null
+++ b/README.EXT.jp
@@ -0,0 +1,1079 @@
+.\" README.EXT - -*- Text -*- created at: Mon Aug 7 16:45:54 JST 1995
+
+rubyの拡張モジュールの作り方を説明します.
+
+1.基礎知識
+
+Cの変数には型があり,データには型がありません.ですから,た
+とえばポインタをintの変数に代入すると,その値は整数として取
+り扱われます.逆にrubyの変数には型がなく,データに型がありま
+す.この違いのため,Cとrubyは相互に変換しなければ,お互いの
+データをアクセスできません.
+
+rubyのデータはVALUEというCの型で表現されます.VALUE型のデー
+タはそのデータタイプを自分で知っています.このデータタイプと
+いうのはデータ(オブジェクト)の実際の構造を意味していて,ruby
+のクラスとはまた違ったものです.
+
+VALUEからCにとって意味のあるデータを取り出すためには
+
+ (1) VALUEのデータタイプを知る
+ (2) VALUEをCのデータに変換する
+
+の両方が必要です.(1)を忘れると間違ったデータの変換が行われ
+て,最悪プログラムがcore dumpします.
+
+1.1 データタイプ
+
+rubyにはユーザが使う可能性のある以下のタイプがあります.
+
+ T_NIL nil
+ T_OBJECT 通常のオブジェクト
+ T_CLASS クラス
+ T_MODULE モジュール
+ T_FLOAT 浮動小数点数
+ T_STRING 文字列
+ T_REGEXP 正規表現
+ T_ARRAY 配列
+ T_FIXNUM Fixnum(31bit長整数)
+ T_HASH 連想配列
+ T_STRUCT (rubyの)構造体
+ T_BIGNUM 多倍長整数
+ T_TRUE 真
+ T_FALSE 偽
+ T_DATA データ
+
+その他に内部で利用されている以下のタイプがあります.
+
+ T_ICLASS
+ T_MATCH
+ T_VARMAP
+ T_SCOPE
+ T_NODE
+
+いくつかのタイプはCの構造体で実装されています.
+
+1.2 VALUEのデータタイプをチェックする
+
+ruby.hではTYPE()というマクロが定義されていて,VALUEのデータ
+タイプを知ることが出来ます.TYPE()マクロは上で紹介したT_XXXX
+の形式の定数を返します.VALUEのデータタイプに応じて処理する
+場合には,TYPE()の値で分岐することになります.
+
+ switch (TYPE(obj)) {
+ case T_FIXNUM:
+ /* FIXNUMの処理 */
+ break;
+ case T_STRING:
+ /* 文字列の処理 */
+ break;
+ case T_ARRAY:
+ /* 配列の処理 */
+ break;
+ default:
+ /* 例外を発生させる */
+ Fail("not valid value");
+ break;
+ }
+
+それとデータタイプをチェックして,正しくなければ例外を発生す
+る関数が用意されています.
+
+ void Check_Type(VALUE value, int type)
+
+この関数はvalueがtypeで無ければ,例外を発生させます.引数と
+して与えられたVALUEのデータタイプが正しいかどうかチェックす
+るためには,この関数を使います.
+
+FIXNUMとNILに関してはより高速な判別マクロが用意されています.
+
+ FIXNUM_P(obj)
+ NIL_P(obj)
+
+1.3 VALUEをCのデータに変換する
+
+データタイプがT_NIL, T_FALSE, T_TRUEである時,データはそれぞ
+れnil, FALSE, TRUEです.このデータタイプのオブジェクトはひと
+つずつしか存在しません.
+
+データタイプがT_FIXNUMの時,これは31bitのサイズを持つ整数で
+す.FIXNUMをCの整数に変換するためにはマクロ「FIX2INT()」を使
+います.それから,FIXNUMに限らずrubyのデータを整数に変換する
+「NUM2INT()」というマクロがあります.このマクロはデータタイ
+プのチェック無しで使えます(整数に変換できない場合には例外が
+発生する).
+
+それ以外のデータタイプは対応するCの構造体があります.対応す
+る構造体のあるVALUEはそのままキャスト(型変換)すれば構造体の
+ポインタに変換できます.
+
+構造体は「struct RXxxxx」という名前でruby.hで定義されていま
+す.例えば文字列は「struct RString」です.実際に使う可能性が
+あるのは文字列と配列くらいだと思います.
+
+ruby.hでは構造体へキャストするマクロも「RXXXXX()」(全部大文
+字にしたもの)という名前で提供されています(例: RSTRING()).
+
+例えば,文字列strの長さを得るためには「RSTRING(str)->len」と
+し,文字列strをchar*として得るためには「RSTRING(str)->ptr」
+とします.配列の場合には,それぞれ「RARRAT(str)->len」,
+「RARRAT(str)->ptr」となります.
+
+rubyの構造体を直接アクセスする時に気をつけなければならないこ
+とは,配列や文字列の構造体の中身は参照するだけで,直接変更し
+ないことです.直接変更した場合,オブジェクトの内容の整合性が
+とれなくなって,思わぬバグの原因になります.
+
+1.4 CのデータをVALUEに変換する
+
+VALUEの実際の構造は
+
+ * FIXNUMの場合
+
+ 1bit右シフトして,LSBを立てる.
+
+ * その他のポインタの場合
+
+ そのままVALUEにキャストする.
+
+となっています.よって,LSBをチェックすればVALUEがFIXNUMかど
+うかわかるわけです(ポインタのLSBが立っていないことを仮定して
+いる).
+
+ですから,FIXNUM以外のrubyのオブジェクトの構造体は単にVALUE
+にキャストするだけでVALUEに変換出来ます.ただし,任意の構造
+体がVALUEにキャスト出来るわけではありません.キャストするの
+はrubyの知っている構造体(ruby.hで定義されているstruct RXxxx
+のもの)だけにしておいてください.
+
+FIXNUMに関しては変換マクロを経由する必要があります.Cの整数
+からVALUEに変換するマクロは以下のものがあります.必要に応じ
+て使い分けてください.
+
+ INT2FIX() もとの整数が31bit以内に収まる時
+ INT2NUM() 任意の整数からVALUEへ
+
+INT2NUM()は整数がFIXNUMの範囲に収まらない場合,Bignumに変換
+してくれます(が,少し遅い).
+
+1.5 rubyのデータを操作する
+
+先程も述べた通り,rubyの構造体をアクセスする時に内容の更新を
+行うことは勧められません.で,rubyのデータを操作する時には
+rubyが用意している関数を用いてください.
+
+ここではもっとも使われるであろう文字列と配列の生成/操作を行
+い関数をあげます(全部ではないです).
+
+ 文字列に対する関数
+
+ str_new(char *ptr, int len)
+
+ 新しいrubyの文字列を生成する.
+
+ str_new2(char *ptr)
+
+ Cの文字列からrubyの文字列を生成する.この関数の機能は
+ str_new(ptr, strlen(ptr))と同等である.
+
+ str_cat(VALUE str, char *ptr, int len)
+
+ rubyの文字列strにlenバイトの文字列ptrを追加する.
+
+ 配列に対する関数
+
+ ary_new()
+
+ 要素が0の配列を生成する.
+
+ ary_new2(int len)
+
+ 要素が0の配列を生成する.len要素分の領域をあらかじめ割り
+ 当てておく.
+
+ ary_new3(int n, ...)
+
+ 引数で指定したn要素を含む配列を生成する.
+
+ ary_new4(int n, VALUE *elts)
+
+ 配列で与えたn要素の配列を生成する.
+
+ ary_push(VALUE ary)
+ ary_pop(VALUE ary, VALUE val)
+ ary_shift(VALUE ary)
+ ary_unshift(VALUE ary, VALUE val)
+ ary_entry(VALUE ary, int idx)
+
+ Arrayの同名のメソッドと同じ働きをする関数.第1引数は必ず
+ 配列でなければならない.
+
+2.rubyの機能を使う
+
+原理的にrubyで書けることはCでも書けます.rubyそのものがCで記
+述されているんですから,当然といえば当然なんですけど.ここで
+はrubyの拡張に使うことが多いだろうと予測される機能を中心に紹
+介します.
+
+2.1 rubyに機能を追加する
+
+rubyで提供されている関数を使えばrubyインタプリタに新しい機能
+を追加することができます.rubyでは以下の機能を追加する関数が
+提供されています.
+
+ * クラス,モジュール
+ * メソッド,特異メソッドなど
+ * 定数
+
+では順に紹介します.
+
+2.1.1 クラス/モジュール定義
+
+クラスやモジュールを定義するためには,以下の関数を使います.
+
+ VALUE rb_define_class(char *name, VALUE super)
+ VALUE rb_define_module(char *name)
+
+これらの関数は新しく定義されたクラスやモジュールを返します.
+メソッドや定数の定義にこれらの値が必要なので,ほとんどの場合
+は戻り値を変数に格納しておく必要があるでしょう.
+
+2.1.2 メソッド/特異メソッド定義
+
+メソッドや特異メソッドを定義するには以下の関数を使います.
+
+ void rb_define_method(VALUE class, char *name,
+ VALUE (*func)(), int argc)
+
+ void rb_define_singleton_method(VALUE object, char *name,
+ VALUE (*func)(), int argc)
+
+
+念のため説明すると「特異メソッド」とは,その特定のオブジェク
+トに対してだけ有効なメソッドです.rubyではよくSmalltalkにお
+けるクラスメソッドとして,クラスに対する特異メソッドが使われ
+ます.
+
+これらの関数の argcという引数はCの関数へ渡される引数の数(と
+形式)を決めます.argcが正の時は関数に引き渡す引数の数を意味
+します.16個以上の引数は使えません(が,要りませんよね,そん
+なに).
+
+argcが負の時は引数の数ではなく,形式を指定したことになります.
+argcが-1の時は引数を配列に入れて渡されます.argcが-2の時は引
+数はrubyの配列として渡されます.
+
+メソッドを定義する関数はもう二つあります.ひとつはprivateメ
+ソッドを定義する関数で,引数はrb_define_method()と同じです.
+
+ void rb_define_private_method(VALUE class, char *name,
+ VALUE (*func)(), int argc)
+
+privateメソッドとは関数形式でしか呼び出すことの出来ないメソッ
+ドです.
+
+もうひとつはモジュール関数を定義するものです.モジュール関数
+とはモジュールの特異メソッドであり,同時にprivateメソッドで
+もあるものです.例をあげるとMathモジュールのsqrt()などがあげ
+られます.このメソッドは
+
+ Math.sqrt(4)
+
+という形式でも
+
+ include Math
+ sqrt(4)
+
+という形式でも使えます.モジュール関数を定義する関数は以下の
+通りです.
+
+ void rb_define_module_function(VALUE module, char *name,
+ VALUE (*func)(), int argc)
+
+関数的メソッド(Kernelモジュールのprivaet method)を定義するた
+めの関数は以下の通りです.
+
+ void rb_define_global_function(char *name, VALUE (*func)(), int argc)
+
+
+2.1.3 定数定義
+
+拡張モジュールが必要な定数はあらかじめ定義しておいた方が良い
+でしょう.定数を定義する関数は二つあります.
+
+ void rb_define_const(VALUE class, char *name, VALUE val)
+ void rb_define_global_const(char *name, VALUE val)
+
+前者は特定のクラス/モジュールに属する定数を定義するもの,後
+者はグローバルな定数を定義するものです.
+
+2.2 rubyの機能をCから呼び出す
+
+既に『1.5 rubyのデータを操作する』で一部紹介したような関数を
+使えば,rubyの機能を実現している関数を直接呼び出すことが出来
+ます.
+
+# このような関数の一覧表はいまのところありません.ソースを見
+# るしかないですね.
+
+それ以外にもrubyの機能を呼び出す方法はいくつかあります.
+
+2.2.1 rubyのプログラムをevalする
+
+Cからrubyの機能を呼び出すもっとも簡単な方法として,文字列で
+与えられたrubyのプログラムを評価する関数があります.
+
+ VALUE rb_eval_string(char *str)
+
+この評価は現在の環境で行われます.つまり,現在のローカル変数
+などを受け継ぎます.
+
+2.2.2 IDまたはシンボル
+
+Cから文字列を経由せずにrubyのメソッドを呼び出すこともできま
+す.その前に,rubyインタプリタ内でメソッドや変数名を指定する
+時に使われているIDについて説明しておきましょう.
+
+IDとは変数名,メソッド名を表す整数です.rubyの中では
+
+ :識別子
+
+でアクセスできます.Cからこの整数を得るためには関数
+
+ rb_intern(char *name)
+
+を使います.また一文字の演算子はその文字コードがそのままシン
+ボルになっています.
+
+2.2.3 Cからrubyのメソッドを呼び出す
+
+Cから文字列を経由せずにrubyのメソッドを呼び出すためには以下
+の関数を使います.
+
+ VALUE rb_funcall(VALUE recv, ID mid, int argc, ...)
+
+この関数はオブジェクトrecvのmidで指定されるメソッドを呼び出
+します.
+
+2.2.4 変数/定数を参照/更新する
+
+Cから関数を使って参照・更新できるのは,クラス定数,インスタ
+ンス変数です.大域変数は一部のものはCの大域変数としてアクセ
+スできます.ローカル変数を参照する方法は公開していません.
+
+オブジェクトのインスタンス変数を参照・更新する関数は以下の通
+りです.
+
+ VALUE rb_ivar_get(VALUE obj, ID id)
+ VALUE rb_ivar_set(VALUE obj, ID id, VALUE val)
+
+idはrb_intern()で得られるものを使ってください.
+
+クラス定数を参照するには以下の関数を使ってください.
+
+ VALUE rb_const_get(VALUE obj, ID id)
+
+クラス定数を新しく定義するためには『2.1.3 定数定義』で紹介さ
+れている関数を使ってください.
+
+3.rubyとCとの情報共有
+
+C言語とrubyの間で情報を共有する方法について解説します.
+
+3.1 Cから参照できるrubyの定数
+
+以下のrubyの定数はCのレベルから参照できる.
+
+ TRUE
+ FALSE
+
+真偽値.FALSEはC言語でも偽とみなされる(つまり0).
+
+ Qnil
+
+C言語から見た「nil」.
+
+3.2 Cとrubyで共有される大域変数
+
+Cとrubyで大域変数を使って情報を共有できます.共有できる大域
+変数にはいくつかの種類があります.そのなかでもっとも良く使わ
+れると思われるのはrb_define_variable()です.
+
+ void rb_define_variable(char *name, VALUE *var)
+
+この関数はrubyとCとで共有する大域変数を定義します.変数名が
+`$'で始まらない時には自動的に追加されます.この変数の値を変
+更すると自動的にrubyの対応する変数の値も変わります.
+
+またruby側からは更新できない変数もあります.このread onlyの
+変数は以下の関数で定義します.
+
+ void rb_define_readonly_variable(char *name, VALUE *var)
+
+これら変数の他にhookをつけた大域変数を定義できます.hook付き
+の大域変数は以下の関数を用いて定義します.hook付き大域変数の
+値の参照や設定はhookで行う必要があります.
+
+ void rb_define_hooked_variable(char *name, VALUE *var,
+ VALUE (*getter)(), VALUE (*setter)())
+
+この関数はCの関数によってhookのつけられた大域変数を定義しま
+す.変数が参照された時には関数getterが,変数に値がセットされ
+た時には関数setterが呼ばれる.hookを指定しない場合はgetterや
+setterに0を指定します.
+
+# getterもsetterも0ならばrb_define_variable()と同じになる.
+
+それから,Cの関数によって実現されるrubyの大域変数を定義する
+関数があります.
+
+ void rb_define_virtual_variable(char *name,
+ VALUE (*getter)(), VALUE (*setter)())
+
+この関数によって定義されたrubyの大域変数が参照された時には
+getterが,変数に値がセットされた時にはsetterが呼ばれます.
+
+getterとsetterの仕様は以下の通りです.
+
+ (*getter)(ID id, void *data, struct global_entry* entry);
+ (*setter)(VALUE val, ID id, void *data, struct global_entry* entry);
+
+3.3 Cのデータをrubyオブジェクトにする
+
+Cの世界で定義されたデータ(構造体)をrubyのオブジェクトとして
+取り扱いたい場合がありえます.このような場合には,Dataという
+rubyオブジェクトにCの構造体(へのポインタ)をくるむことでruby
+オブジェクトとして取り扱えるようになります.
+
+Dataオブジェクトを生成して構造体をrubyオブジェクトにカプセル
+化するためには,以下のマクロを使います.
+
+ Data_Wrap_Struct(class,mark,free,ptr)
+
+このマクロの戻り値は生成されたDataオブジェクトです.
+
+classはこのDataオブジェクトのクラスです.ptrはカプセル化する
+Cの構造体へのポインタです.markはこの構造体がrubyのオブジェ
+クトへの参照がある時に使う関数です.そのような参照を含まない
+時には0を指定します.
+
+# そのような参照は勧められません.
+
+freeはこの構造体がもう不要になった時に呼ばれる関数です.この
+関数がガーベージコレクタから呼ばれます.
+
+Cの構造体の割当とDataオブジェクトの生成を同時に行うマクロと
+して以下のものが提供されています.
+
+ Data_Make_Struct(class, type, mark, free, sval)
+
+このマクロの戻り値は生成されたDataオブジェクトです.
+
+class, mark, freeはData_Wrap_Structと同じ働きをします.type
+は割り当てるC構造体の型です.割り当てられた構造体は変数sval
+に代入されます.この変数の型は (type*) である必要があります.
+
+Dataオブジェクトからポインタを取り出すのは以下のマクロを用い
+ます.
+
+ Data_Get_Struct(obj, type, sval)
+
+Cの構造体へのポインタは変数svalに代入されます.
+
+これらのDataの使い方はちょっと分かりにくいので,後で説明する
+例題を参照してください.
+
+4.例題 - dbmパッケージを作る
+
+ここまでの説明でとりあえず拡張モジュールは作れるはずです.
+rubyのextディレクトリにすでに含まれているdbmモジュールを例に
+して段階的に説明します.
+
+(1) ディレクトリを作る
+
+ % mkdir ext/dbm
+
+rubyを展開したディレクトリの下,extディレクトリの中に拡張モ
+ジュール用のディレクトリを作ります.名前は適当に選んで構いま
+せん.
+
+(2) MANIFESTファイルを作る
+
+ % cd ext/dbm
+ % touch MANIFEST
+
+拡張モジュールのディレクトリの下にはMANIFESTというファイルが
+必要なので,とりあえず空のファイルを作っておきます.後でこの
+ファイルには必要なファイル一覧が入ることになります.
+
+MANIFESTというファイルは,makeの時にディレクトリが拡張モジュー
+ルを含んでいるかどうか判定するために使われれています.
+
+(3) 設計する
+
+まあ,当然なんですけど,どういう機能を実現するかどうかまず設
+計する必要があります.どんなクラスをつくるか,そのクラスには
+どんなメソッドがあるか,クラスが提供する定数などについて設計
+します.dbmクラスについてはext/dbm.docを参照してください.
+
+(4) Cコードを書く
+
+拡張モジュール本体となるC言語のソースを書きます.C言語のソー
+スがひとつの時には「モジュール名.c」を選ぶと良いでしょう.C
+言語のソースが複数の場合には逆に「モジュール名.c」というファ
+イル名は避ける必要があります.オブジェクトファイルとモジュー
+ル生成時に中間的に生成される「モジュール名.o」というファイル
+とが衝突するからです.
+
+rubyは拡張モジュールをロードする時に「Init_モジュール名」と
+いう関数を自動的に実行します.dbmモジュールの場合「Init_dbm」
+です.この関数の中でクラス,モジュール,メソッド,定数などの
+定義を行います.dbm.cから一部引用します.
+
+--
+Init_dbm()
+{
+ /* DBMクラスを定義する */
+ cDBM = rb_define_class("DBM", cObject);
+ /* DBMはEnumerateモジュールをインクルードする */
+ rb_include_module(cDBM, mEnumerable);
+
+ /* DBMクラスのクラスメソッドopen(): 引数はCの配列で受ける */
+ rb_define_singleton_method(cDBM, "open", fdbm_s_open, -1);
+
+ /* DBMクラスのメソッドclose(): 引数はなし */
+ rb_define_method(cDBM, "close", fdbm_close, 0);
+ /* DBMクラスのメソッド[]: 引数は1個 */
+ rb_define_method(cDBM, "[]", fdbm_fetch, 1);
+ :
+
+ /* DBMデータを格納するインスタンス変数名のためのID */
+ id_dbm = rb_intern("dbm");
+}
+--
+
+DBMモジュールはdbmのデータと対応するオブジェクトになるはずで
+すから,Cの世界のdbmをrubyの世界に取り込む必要があります.
+
+
+dbm.cではData_Make_Structを以下のように使っています.
+
+--
+struct dbmdata {
+ int di_size;
+ DBM *di_dbm;
+};
+
+
+obj = Data_Make_Struct(class,struct dbmdata,0,free_dbm,dbmp);
+--
+
+ここではdbmstruct構造体へのポインタをDataにカプセル化してい
+ます.DBM*を直接カプセル化しないのはclose()した時の処理を考
+えてのことです.
+
+Dataオブジェクトからdbmstruct構造体のポインタを取り出すため
+に以下のマクロを使っています.
+
+--
+#define GetDBM(obj, dbmp) {\
+ Data_Get_Struct(obj, struct dbmdata, dbmp);\
+ if (dbmp->di_dbm == 0) closed_dbm();\
+}
+--
+
+ちょっと複雑なマクロですが,要するにdbmdata構造体のポインタ
+の取り出しと,closeされているかどうかのチェックをまとめてい
+るだけです.
+
+DBMクラスにはたくさんメソッドがありますが,分類すると3種類の
+引数の受け方があります.ひとつは引数の数が固定のもので,例と
+してはdeleteメソッドがあります.deleteメソッドを実装している
+fdbm_delete()はこのようになっています.
+
+--
+static VALUE
+fdbm_delete(obj, keystr)
+ VALUE obj, keystr;
+{
+ :
+}
+--
+
+引数の数が固定のタイプは第1引数がself,第2引数以降がメソッド
+の引数となります.
+
+引数の数が不定のものはCの配列で受けるものとrubyの配列で受け
+るものとがあります.dbmモジュールの中で,Cの配列で受けるもの
+はDBMのクラスメソッドであるopen()です.これを実装している関
+数fdbm_s_open()はこうなっています.
+
+--
+static VALUE
+fdbm_s_open(argc, argv, class)
+ int argc;
+ VALUE *argv;
+ VALUE class;
+{
+ :
+ if (rb_scan_args(argc, argv, "11", &file, &vmode) == 1) {
+ mode = 0666; /* default value */
+ }
+ :
+}
+--
+
+このタイプの関数は第1引数が与えられた引数の数,第2引数が与え
+られた引数の入っている配列になります.selfは第3引数として与
+えられます.
+
+この配列で与えられた引数を解析するための関数がopen()でも使わ
+れているrb_scan_args()です.第3引数に指定したフォーマットに
+従い,第4変数以降に指定した変数に値を代入してくれます.この
+フォーマットは,第1文字目が省略できない引数の数,第2文字目が
+省略できる引数の数,第3文字目が対応する相手が無いあまりの引
+数があるかどうかを示す"*"です.2文字目と3文字目は省略できま
+す.dbm.cの例では,フォーマットは"11"ですから,引数は最低1つ
+で,2つまで許されるという意味になります.省略されている時の
+変数の値はnil(C言語のレベルではQnil)になります.
+
+rubyの配列で引数を受け取るものはindexesがあります.実装はこ
+うです.
+
+--
+static VALUE
+fdbm_indexes(obj, args)
+ VALUE obj;
+ struct RArray *args;
+{
+ :
+}
+--
+
+第1引数はself,第2引数はrubyの配列です.ここではキャストを減
+らすため struct RArray* で受けていますが,VALUEでも同じこと
+です.
+
+** 注意事項
+
+rubyと共有はしないがrubyのオブジェクトを格納する可能性のある
+Cの大域変数は以下の関数を使ってrubyインタプリタに変数の存在
+を教えてあげてください.でないとGCでトラブルを起こします.
+
+ void rb_global_variable(VALUE *var)
+
+(5) extconf.rbを用意する
+
+もしディレクトリに「extconf.rb」というファイルが存在すれば,
+make時に実行されます.なければ適当にMakefileが生成されます.
+
+extconf.rbはモジュールのコンパイルに必要な条件のチェックなど
+を行うことが目的です.extconf.rbの中では以下のruby関数を使う
+ことが出来ます.
+
+ have_library(lib, func): ライブラリの存在チェック
+ have_func(func): 関数の存在チェック
+ have_header(header): ヘッダファイルの存在チェック
+ create_makefile(target): Makefileの生成
+
+以下の変数を使うことができます.
+
+ $CFLAGS: コンパイル時に追加的に指定するフラグ(-Iなど)
+ $LDFLAGS: リンク時に追加的に指定するフラグ(-Lなど)
+
+モジュールをコンパイルする条件が揃わなず,そのモジュールはコ
+ンパイルしない時にはcreate_makefileを呼ばなければMakefileは
+生成されず,コンパイルも行われません.
+
+(6) dependを用意する
+
+もし,ディレクトリにdependというファイルが存在すれば,
+Makefileが依存関係をチェックしてくれます.
+
+ % gcc -MM *.c > depend
+
+などで作ることが出来ます.あって損は無いでしょう.
+
+(7) MANIFESTファイルにファイル名を入れる
+
+ % ls > MANIFEST
+ % vi MANIFEST
+
+*.o, *~など不必要なファイル以外はMANIFESTに追加しておきます.
+make時にはMANIFESTの内容は参照しませんので,空のままでも問題
+は起きませんが,パッケージングの時に参照することがあるのと,
+必要なファイルを区別できるので,用意しておいた方が良いでしょ
+う.
+
+(8) makeする
+
+rubyのディレクトリでmakeを実行するとMakefileを生成からmake,
+必要によってはそのモジュールのrubyへのリンクまで自動的に実行
+してくれます.extconf.rbを書き換えるなどしてMakefileの再生成
+が必要な時はまたrubyディレクトリでmakeしてください.
+
+動的リンクライブラリはmake installでrubyライブラリのディレク
+トリの下にコピーされます.もしモジュールと協調して使うrubyで
+記述されたプログラムがあり,rubyライブラリに置きたい場合には,
+拡張モジュール用のディレクトリの下に lib というディレクトリ
+を作り,そこに 拡張子 .rb のファイルを置いておけば同時にイン
+ストールされます.
+
+(9) デバッグ
+
+まあ,デバッグしないと動かないでしょうね.ext/Setupにディレ
+クトリ名を書くと静的にリンクするのでデバッガが使えるようにな
+ります.その分コンパイルが遅くなりますけど.
+
+(10) できあがり
+
+後はこっそり使うなり,広く公開するなり,売るなり,ご自由にお
+使いください.rubyの作者は拡張モジュールに関して一切の権利を
+主張しません.
+
+Appendix A. rubyのソースコードの分類
+
+rubyのソースはいくつかに分類することが出来ます.このうちクラ
+スライブラリの部分は基本的に拡張モジュールと同じ作り方になっ
+ています.これらのソースは今までの説明でほとんど理解できると
+思います.
+
+ruby言語のコア
+
+ class.c
+ error.c
+ eval.c
+ gc.c
+ object.c
+ parse.y
+ variable.c
+
+ユーティリティ関数
+
+ dln.c
+ fnmatch.c
+ glob.c
+ regex.c
+ st.c
+ util.c
+
+rubyコマンドの実装
+
+ dmyext.c
+ inits.c
+ main.c
+ ruby.c
+ version.c
+
+クラスライブラリ
+
+ array.c
+ bignum.c
+ compar.c
+ dir.c
+ enum.c
+ file.c
+ hash.c
+ io.c
+ math.c
+ numeric.c
+ pack.c
+ process.c
+ random.c
+ range.c
+ re.c
+ signal.c
+ sprintf.c
+ string.c
+ struct.c
+ time.c
+
+Appendix B. 拡張用関数リファレンス
+
+C言語からrubyの機能を利用するAPIは以下の通りである.
+
+** 型
+
+ VALUE
+
+rubyオブジェクトを表現する型.必要に応じてキャストして用いる.
+組み込み型を表現するCの型はruby.hに記述してあるRで始まる構造
+体である.VALUE型をこれらにキャストするためにRで始まる構造体
+名を全て大文字にした名前のマクロが用意されている.
+
+** 変数・定数
+
+ Qnil
+
+定数: nilオブジェクト
+
+ TRUE
+
+定数: TRUEオブジェクト(真のデフォルト値)
+
+ FALSE
+
+定数: FALSEオブジェクト
+
+** Cデータのカプセル化
+
+ Wrap_Data_Ptr(VALUE class, void (*mark)(), void (*free)(), void *sval)
+
+Cの任意のポインタをカプセル化したrubyオブジェクトを返す.こ
+のポインタがrubyからアクセスされなくなった時,freeで指定した
+関数が呼ばれる.また,このポインタの指すデータが他のrubyオブ
+ジェクトを指している場合,markに指定する関数でマークする必要
+がある.
+
+ Make_Data_Struct(class, type, mark, free, sval)
+
+type型のメモリをmallocし,変数svalに代入した後,それをカプセ
+ル化したデータを返すマクロ.
+
+ Data_Get_Struct(data, type, sval)
+
+dataからtype型のポインタを取り出し変数svalに代入するマクロ.
+
+** クラス/モジュール定義
+
+ VALUE rb_define_class(char *name, VALUE super)
+
+superのサブクラスとして新しいrubyクラスを定義する.
+
+ VALUE rb_define_class_under(VALUE module, char *name, VALUE super)
+
+superのサブクラスとして新しいrubyクラスを定義し,moduleの定
+数として定義する.
+
+ VALUE rb_define_module(char *name)
+
+新しいrubyモジュールを定義する.
+
+ VALUE rb_define_module_under(VALUE module, char *name, VALUE super)
+
+新しいrubyモジュールを定義し,moduleの定数として定義する.
+
+ void rb_include_module(VALUE class, VALUE module)
+
+モジュールをインクルードする.classがすでにmoduleをインクルー
+ドしている時には何もしない(多重インクルードの禁止).
+
+ void rb_extend_object(VALUE object, VALUE module)
+
+オブジェクトをモジュール(で定義されているメソッド)で拡張する.
+
+** 大域変数定義
+
+ void rb_define_variable(char *name, VALUE *var)
+
+rubyとCとで共有するグローバル変数を定義する.変数名が`$'で始
+まらない時には自動的に追加される.nameとしてrubyの識別子とし
+て許されない文字(例えば` ')を含む場合にはrubyプログラムから
+は見えなくなる.
+
+ void rb_define_readonly_variable(char *name, VALUE *var)
+
+rubyとCとで共有するread onlyのグローバル変数を定義する.read
+onlyであること以外はrb_define_variable()と同じ.
+
+ void rb_define_virtual_variable(char *name,
+ VALUE (*getter)(), VALUE (*setter)())
+
+関数によって実現されるruby変数を定義する.変数が参照された時
+にはgetterが,変数に値がセットされた時にはsetterが呼ばれる.
+
+ void rb_define_hooked_variable(char *name, VALUE *var,
+ VALUE (*getter)(), VALUE (*setter)())
+
+関数によってhookのつけられたグローバル変数を定義する.変数が
+参照された時にはgetterが,関数に値がセットされた時にはsetter
+が呼ばれる.getterやsetterに0を指定した時にはhookを指定しな
+いのと同じ事になる.
+
+ void rb_global_variable(VALUE *var)
+
+GCのため,rubyプログラムからはアクセスされないが, rubyオブジェ
+クトを含む大域変数をマークする.
+
+** クラス定数
+
+ void rb_define_const(VALUE class, char *name, VALUE val)
+
+クラス定数を定義する.
+
+ void rb_define_global_const(char *name, VALUE val)
+
+大域定数を定義する.
+
+ rb_define_const(cKernal, name, val)
+
+と同じ意味.
+
+** メソッド定義
+
+ rb_define_method(VALUE class, char *name, VALUE (*func)(), int argc)
+
+メソッドを定義する.argcはselfを除く引数の数.argcが-1の時,
+関数には引数の数(selfを含まない)を第1引数, 引数の配列を第2引
+数とする形式で与えられる(第3引数はself).argcが-2の時, 第1引
+数がself, 第2引数がargs(argsは引数を含むrubyの配列)という形
+式で与えられる.
+
+ rb_define_private_method(VALUE class, char *name, VALUE (*func)(), int argc)
+
+privateメソッドを定義する.引数はrb_define_method()と同じ.
+
+ rb_define_singleton_method(VALUE class, char *name, VALUE (*func)(), int argc)
+
+特異メソッドを定義する.引数はrb_define_method()と同じ.
+
+ rb_scan_args(int atgc, VALUE *argv, char *fmt, ...)
+
+argc,argv形式で与えられた引数を分解する.fmtは必須引数の数,
+付加引数の数, 残りの引数があるかを指定する文字列で, "数字数
+字*"という形式である. 2 番目の数字と"*"はそれぞれ省略可能で
+ある.必須引数が一つもない場合は0を指定する.第3引数以降は変
+数へのポインタで, 該当する要素がその変数に格納される.付加引
+数に対応する引数が与えられていない場合は変数にQnilが代入され
+る.
+
+** rubyメソッド呼び出し
+
+ VALUE rb_funcall(VALUE recv, ID mid, int narg, ...)
+
+メソッド呼び出し.文字列からmidを得るためにはrb_intern()を使う.
+
+ VALUE rb_funcall2(VALUE recv, ID mid, int argc, VALUE *argv)
+
+メソッド呼び出し.引数をargc,argv形式で渡す.
+
+ VALUE rb_eval_string(char *str)
+
+文字列をrubyとスクリプトしてコンパイル・実行する.
+
+ ID rb_intern(char *name)
+
+文字列に対応するIDを返す.
+
+ char *rb_id2name(ID id)
+
+IDに対応する文字列を返す(デバッグ用).
+
+ char *rb_class2name(VALUE class)
+
+classの名前を返す(デバッグ用).classが名前を持たない時には,
+祖先を遡って名前を持つクラスの名前を返す.
+
+** インスタンス変数
+
+ VALUE rb_iv_get(VALUE obj, char *name)
+
+objのインスタンス変数の値を得る.`@'で始まらないインスタンス
+変数は rubyプログラムからアクセスできない「隠れた」インスタ
+ンス変数になる.
+
+ VALUE rb_iv_set(VALUE obj, char *name, VALUE val)
+
+objのインスタンス変数をvalにセットする.
+
+** 制御構造
+
+ VALUE rb_iterate(VALUE (*func1)(), void *arg1, VALUE (*func2)(), void *arg2)
+
+func2をブロックとして設定し, func1をイテレータとして呼ぶ.
+func1には arg1が引数として渡され, func2には第1引数にイテレー
+タから与えられた値, 第2引数にarg2が渡される.
+
+ VALUE rb_yield(VALUE val)
+
+valを値としてイテレータブロックを呼び出す.
+
+ VALUE rb_rescue(VALUE (*func1)(), void *arg1, VALUE (*func2)(), void *arg2)
+
+関数func1をarg1を引数に呼び出す.func1の実行中に例外が発生し
+た時には func2をarg2を引数として呼ぶ.戻り値は例外が発生しな
+かった時はfunc1の戻り値, 例外が発生した時にはfunc2の戻り値で
+ある.
+
+ VALUE rb_ensure(VALUE (*func1)(), void *arg1, void (*func2)(), void *arg2)
+
+関数func1をarg1を引数として実行し, 実行終了後(たとえ例外が発
+生しても) func2をarg2を引数として実行する.戻り値はfunc1の戻
+り値である(例外が発生した時は戻らない).
+
+** 例外・エラー
+
+ void Warning(char *fmt, ...)
+
+verbose時に標準エラー出力に警告情報を表示する.引数はprintf()と同じ.
+
+ void Fail(char *fmt, ...)
+
+RuntimeError例外を発生させる.引数はprintf()と同じ.
+
+ void Raise(VALUE exception, char *fmt, ...)
+
+exceptionで指定した例外を発生させる.引数はprintf()と同じ.
+
+ void Fatal(char *fmt, ...)
+
+致命的例外を発生させる.通常の例外処理は行なわれず, インター
+プリタが終了する(ただしensureで指定されたコードは終了前に実
+行される).
+
+ void Bug(char *fmt, ...)
+
+インタープリタなどプログラムのバグでしか発生するはずのない状
+況の時呼ぶ.インタープリタはコアダンプし直ちに終了する.例外
+処理は一切行なわれない.
+
+** rubyの初期化・実行
+
+rubyをアプリケーションに埋め込む場合には以下のインタフェース
+を使う.通常の拡張モジュールには必要ない.
+
+ void ruby_init(int argc, char **argv, char **envp)
+
+rubyインタプリタの初期化を行なう.
+
+ void ruby_run()
+
+rubyインタプリタを実行する.
+
+ void ruby_script(char *name)
+
+rubyのスクリプト名($0)を設定する.
+
+
+Appendix B. extconf.rbで使える関数たち
+
+extconf.rbの中では利用可能なコンパイル条件チェックの関数は以
+下の通りである.
+
+ have_library(lib, func)
+
+関数funcを定義しているライブラリlibの存在をチェックする.ラ
+イブラリが存在する時,TRUEを返す.
+
+ have_func(func)
+
+関数funcの存在をチェックする.funcが標準ではリンクされないラ
+イブラリ内のものである時には先にhave_libraryでそのライブラリ
+をチェックしておく事.関数が存在する時TRUEを返す.
+
+ have_header(header)
+
+ヘッダファイルの存在をチェックする.ヘッダファイルが存在する
+時TRUEを返す.
+
+ create_makefile(target)
+
+拡張モジュール用のMakefileを生成する.この関数を呼ばなければ
+そのモジュールはコンパイルされない.targetはモジュール名を表
+す.
+
+/*
+ * Local variables:
+ * fill-column: 60
+ * end:
+ */
diff --git a/array.c b/array.c
index 388fb05bd7..e39f1f167c 100644
--- a/array.c
+++ b/array.c
@@ -6,7 +6,7 @@
$Date$
created at: Fri Aug 6 09:46:12 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -403,24 +403,19 @@ ary_index(ary, val)
}
static VALUE
-ary_indexes(ary, args)
- VALUE ary, args;
+ary_indexes(argc, argv, ary)
+ int argc;
+ VALUE *argv;
+ VALUE ary;
{
- VALUE *p, *pend;
VALUE new_ary;
- int i = 0;
+ int i;
- if (!args || NIL_P(args)) {
- return ary_new2(0);
+ new_ary = ary_new2(argc);
+ for (i=0; i<argc; i++) {
+ ary_store(new_ary, i, ary_entry(ary, NUM2INT(argv[i])));
}
- new_ary = ary_new2(RARRAY(args)->len);
-
- p = RARRAY(args)->ptr; pend = p + RARRAY(args)->len;
- while (p < pend) {
- ary_store(new_ary, i++, ary_entry(ary, NUM2INT(*p)));
- p++;
- }
return new_ary;
}
@@ -683,6 +678,8 @@ ary_reverse(ary)
VALUE *p1, *p2;
VALUE tmp;
+ if (RARRAY(ary)->len == 0) return ary;
+
p1 = RARRAY(ary)->ptr;
p2 = p1 + RARRAY(ary)->len - 1; /* points last item */
@@ -734,6 +731,8 @@ VALUE
ary_sort_bang(ary)
VALUE ary;
{
+ if (RARRAY(ary)->len == 0) return ary;
+
ary_modify(ary);
qsort(RARRAY(ary)->ptr, RARRAY(ary)->len, sizeof(VALUE), iterator_p()?sort_1:sort_2);
return ary;
@@ -743,6 +742,7 @@ VALUE
ary_sort(ary)
VALUE ary;
{
+ if (RARRAY(ary)->len == 0) return ary;
return ary_sort_bang(ary_clone(ary));
}
@@ -816,20 +816,27 @@ ary_delete_if(ary)
return ary;
}
-#if 0
static VALUE
-ary_replace(ary)
+ary_filter(ary)
VALUE ary;
{
int i;
+ ary_modify(ary);
for (i = 0; i < RARRAY(ary)->len; i++) {
RARRAY(ary)->ptr[i] = rb_yield(RARRAY(ary)->ptr[i]);
}
+ return ary;
+}
+static VALUE
+ary_replace_method(ary, ary2)
+ VALUE ary, ary2;
+{
+ Check_Type(ary2, T_ARRAY);
+ ary_replace(ary, 0, RARRAY(ary2)->len, ary2);
return ary;
}
-#endif
static VALUE
ary_clear(ary)
@@ -1183,7 +1190,8 @@ Init_Array()
rb_define_alias(cArray, "size", "length");
rb_define_method(cArray, "empty?", ary_empty_p, 0);
rb_define_method(cArray, "index", ary_index, 1);
- rb_define_method(cArray, "indexes", ary_indexes, -2);
+ rb_define_method(cArray, "indexes", ary_indexes, -1);
+ rb_define_method(cArray, "indices", ary_indexes, -1);
rb_define_method(cArray, "clone", ary_clone, 0);
rb_define_method(cArray, "dup", ary_dup, 0);
rb_define_method(cArray, "join", ary_join_method, -1);
@@ -1194,9 +1202,8 @@ Init_Array()
rb_define_method(cArray, "delete", ary_delete, 1);
rb_define_method(cArray, "delete_at", ary_delete_at, 1);
rb_define_method(cArray, "delete_if", ary_delete_if, 0);
-#if 0
- rb_define_method(cArray, "replace", ary_replace, 0);
-#endif
+ rb_define_method(cArray, "filter", ary_filter, 0);
+ rb_define_method(cArray, "replace", ary_replace_method, 1);
rb_define_method(cArray, "clear", ary_clear, 0);
rb_define_method(cArray, "fill", ary_fill, -1);
rb_define_method(cArray, "include?", ary_includes, 1);
diff --git a/bignum.c b/bignum.c
index 17d9c839c5..8a6e54a9da 100644
--- a/bignum.c
+++ b/bignum.c
@@ -24,13 +24,13 @@ VALUE cBignum;
#define BIGLO(x) ((x) & (BIGRAD-1))
static VALUE
-bignew_1(class, len, sign)
- VALUE class;
+bignew_1(klass, len, sign)
+ VALUE klass;
UINT len;
char sign;
{
NEWOBJ(big, struct RBignum);
- OBJSETUP(big, cBignum, T_BIGNUM);
+ OBJSETUP(big, klass, T_BIGNUM);
big->sign = sign;
big->len = len;
BDIGITS(big) = ALLOC_N(USHORT, len);
@@ -195,12 +195,16 @@ str2inum(str, base)
base = 10;
}
}
- len = strlen(str);
if (base == 8) {
- len = 3*len*sizeof(char);
+ while (str[0] == '0') str++;
+ len = 3*strlen(str)*sizeof(char);
}
else { /* base == 10 or 16 */
- len = 4*len*sizeof(char);
+ if (base == 16 && str[0] == '0' && (str[1] == 'x'||str[1] == 'X')) {
+ str += 2;
+ }
+ while (str[0] == '0') str++;
+ len = 4*strlen(str)*sizeof(char);
}
if (len <= (sizeof(VALUE)*CHAR_BIT)) {
@@ -1177,7 +1181,7 @@ big_abs(x)
x = big_clone(x);
RBIGNUM(x)->sign = 1;
}
- return (VALUE)x;
+ return x;
}
/* !!!warnig!!!!
diff --git a/class.c b/class.c
index 13c9298c1c..b5bfecfbd5 100644
--- a/class.c
+++ b/class.c
@@ -95,11 +95,11 @@ rb_define_class_id(id, super)
klass = class_new(super);
rb_name_class(klass, id);
/* make metaclass */
- RBASIC(klass)->class = singleton_class_new(RBASIC(super)->class);
- singleton_class_attached(RBASIC(klass)->class, klass);
+ RBASIC(klass)->klass = singleton_class_new(RBASIC(super)->klass);
+ singleton_class_attached(RBASIC(klass)->klass, klass);
rb_funcall(super, rb_intern("inherited"), 1, klass);
- return (VALUE)klass;
+ return klass;
}
VALUE
@@ -201,10 +201,10 @@ include_class_new(module, super)
klass->iv_tbl = RCLASS(module)->iv_tbl;
klass->super = super;
if (TYPE(module) == T_ICLASS) {
- RBASIC(klass)->class = RBASIC(module)->class;
+ RBASIC(klass)->klass = RBASIC(module)->klass;
}
else {
- RBASIC(klass)->class = module;
+ RBASIC(klass)->klass = module;
}
return (VALUE)klass;
@@ -253,7 +253,7 @@ mod_included_modules(mod)
for (p = RCLASS(mod)->super; p; p = RCLASS(p)->super) {
if (BUILTIN_TYPE(p) == T_ICLASS) {
- ary_push(ary, RBASIC(p)->class);
+ ary_push(ary, RBASIC(p)->klass);
}
}
return ary;
@@ -267,8 +267,10 @@ mod_ancestors(mod)
VALUE p;
for (p = mod; p; p = RCLASS(p)->super) {
+ if (FL_TEST(p, FL_SINGLETON))
+ continue;
if (BUILTIN_TYPE(p) == T_ICLASS) {
- ary_push(ary, RBASIC(p)->class);
+ ary_push(ary, RBASIC(p)->klass);
}
else {
ary_push(ary, p);
@@ -419,25 +421,29 @@ rb_define_method(klass, name, func, argc)
VALUE (*func)();
int argc;
{
- rb_add_method(klass, rb_intern(name), NEW_CFUNC(func, argc), NOEX_PUBLIC);
+ ID id = rb_intern(name);
+
+ rb_add_method(klass, id, NEW_CFUNC(func, argc),
+ (name[0] == 'i' && id == rb_intern("initialize"))?
+ NOEX_PRIVATE:NOEX_PUBLIC);
}
void
-rb_undef_method(klass, name)
+rb_define_private_method(klass, name, func, argc)
VALUE klass;
char *name;
+ VALUE (*func)();
+ int argc;
{
- rb_add_method(klass, rb_intern(name), 0, NOEX_PUBLIC);
+ rb_add_method(klass, rb_intern(name), NEW_CFUNC(func, argc), NOEX_PRIVATE);
}
void
-rb_define_private_method(klass, name, func, argc)
+rb_undef_method(klass, name)
VALUE klass;
char *name;
- VALUE (*func)();
- int argc;
{
- rb_add_method(klass, rb_intern(name), NEW_CFUNC(func, argc), NOEX_PRIVATE);
+ rb_add_method(klass, rb_intern(name), 0, NOEX_PUBLIC);
}
VALUE
@@ -447,12 +453,12 @@ rb_singleton_class(obj)
if (rb_special_const_p(obj)) {
TypeError("cannot define singleton");
}
- if (FL_TEST(RBASIC(obj)->class, FL_SINGLETON)) {
- return (VALUE)RBASIC(obj)->class;
+ if (FL_TEST(RBASIC(obj)->klass, FL_SINGLETON)) {
+ return RBASIC(obj)->klass;
}
- RBASIC(obj)->class = singleton_class_new(RBASIC(obj)->class);
- singleton_class_attached(RBASIC(obj)->class, obj);
- return RBASIC(obj)->class;
+ RBASIC(obj)->klass = singleton_class_new(RBASIC(obj)->klass);
+ singleton_class_attached(RBASIC(obj)->klass, obj);
+ return RBASIC(obj)->klass;
}
void
diff --git a/compar.c b/compar.c
index e852fb1e49..ce85198873 100644
--- a/compar.c
+++ b/compar.c
@@ -6,7 +6,7 @@
$Date$
created at: Thu Aug 26 14:39:48 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
diff --git a/dir.c b/dir.c
index 29ce261272..e89f247a02 100644
--- a/dir.c
+++ b/dir.c
@@ -6,7 +6,7 @@
$Date$
created at: Wed Jan 5 09:51:01 JST 1994
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
diff --git a/dln.c b/dln.c
index f4ab012021..4a8dcdc8ec 100644
--- a/dln.c
+++ b/dln.c
@@ -6,20 +6,20 @@
$Date$
created at: Tue Jan 18 17:05:06 JST 1994
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
-#ifdef _AIX
-#pragma alloca
-#endif
-
#include "config.h"
#include "defines.h"
#include "dln.h"
char *dln_argv0;
+#ifdef _AIX
+#pragma alloca
+#endif
+
#if defined(HAVE_ALLOCA_H) && !defined(__GNUC__)
#include <alloca.h>
#endif
diff --git a/enum.c b/enum.c
index d8e2fcdc8b..3b804fae48 100644
--- a/enum.c
+++ b/enum.c
@@ -6,7 +6,7 @@
$Date$
created at: Fri Oct 1 15:15:19 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -356,6 +356,25 @@ enum_length(obj)
return INT2FIX(length);
}
+each_with_index_i(val, indexp)
+ VALUE val;
+ int *indexp;
+{
+ rb_yield(assoc_new(val, INT2FIX(*indexp)));
+ (*indexp)++;
+ return Qnil;
+}
+
+VALUE
+enum_each_with_index(obj)
+ VALUE obj;
+{
+ int index = 0;
+
+ rb_iterate(rb_each, obj, each_with_index_i, (VALUE)&index);
+ return Qnil;
+}
+
void
Init_Enumerable()
{
@@ -376,6 +395,7 @@ Init_Enumerable()
rb_define_method(mEnumerable,"include?", enum_member, 1);
rb_define_method(mEnumerable,"length", enum_length, 0);
rb_define_method(mEnumerable,"size", enum_length, 0);
+ rb_define_method(mEnumerable,"each_with_index", enum_each_with_index, 0);
id_eqq = rb_intern("===");
id_each = rb_intern("each");
diff --git a/error.c b/error.c
index 7163f62609..4c8aea5964 100644
--- a/error.c
+++ b/error.c
@@ -6,7 +6,7 @@
$Date$
created at: Mon Aug 9 16:11:34 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -254,7 +254,7 @@ exc_inspect(exc)
klass = CLASS_OF(exc);
if (RSTRING(exc)->len == 0) {
- return rb_class_path(klass);
+ return str_dup(rb_class_path(klass));
}
str = str_new2("#<");
diff --git a/eval.c b/eval.c
index 42617c2b27..182471cd6d 100644
--- a/eval.c
+++ b/eval.c
@@ -6,7 +6,7 @@
$Date$
created at: Thu Jun 10 14:22:17 JST 1993
- Copyright (C) 1993-1997 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -43,6 +43,7 @@ static VALUE f_binding _((VALUE));
static void f_END _((void));
#define SCOPE_PRIVATE FL_USER4
+#define SCOPE_MODFUNC FL_USER5
#define CACHE_SIZE 0x200
#define CACHE_MASK 0x1ff
@@ -51,7 +52,7 @@ static void f_END _((void));
struct cache_entry { /* method hash table. */
ID mid; /* method's id */
ID mid0; /* method's original id */
- VALUE class; /* receiver's class */
+ VALUE klass; /* receiver's class */
VALUE origin; /* where method defined */
NODE *method;
int noex;
@@ -87,80 +88,80 @@ rb_clear_cache_by_id(id)
}
void
-rb_add_method(class, mid, node, noex)
- VALUE class;
+rb_add_method(klass, mid, node, noex)
+ VALUE klass;
ID mid;
NODE *node;
int noex;
{
NODE *body;
- if (NIL_P(class)) class = cObject;
+ if (NIL_P(klass)) klass = cObject;
body = NEW_METHOD(node, noex);
- st_insert(RCLASS(class)->m_tbl, mid, body);
+ st_insert(RCLASS(klass)->m_tbl, mid, body);
}
void
-rb_remove_method(class, mid)
- VALUE class;
+rb_remove_method(klass, mid)
+ VALUE klass;
ID mid;
{
NODE *body;
- if (!st_delete(RCLASS(class)->m_tbl, &mid, &body)) {
+ if (!st_delete(RCLASS(klass)->m_tbl, &mid, &body)) {
NameError("method `%s' not defined in %s",
- rb_id2name(mid), rb_class2name(class));
+ rb_id2name(mid), rb_class2name(klass));
}
rb_clear_cache_by_id(mid);
}
static NODE*
-search_method(class, id, origin)
- VALUE class, *origin;
+search_method(klass, id, origin)
+ VALUE klass, *origin;
ID id;
{
NODE *body;
- while (!st_lookup(RCLASS(class)->m_tbl, id, &body)) {
- class = (VALUE)RCLASS(class)->super;
- if (!class) return 0;
+ while (!st_lookup(RCLASS(klass)->m_tbl, id, &body)) {
+ klass = RCLASS(klass)->super;
+ if (!klass) return 0;
}
- if (origin) *origin = class;
+ if (origin) *origin = klass;
return body;
}
static NODE*
-rb_get_method_body(classp, idp, noexp)
- VALUE *classp;
+rb_get_method_body(klassp, idp, noexp)
+ VALUE *klassp;
ID *idp;
int *noexp;
{
ID id = *idp;
- VALUE class = *classp;
+ VALUE klass = *klassp;
VALUE origin;
NODE *body;
struct cache_entry *ent;
- if ((body = search_method(class, id, &origin)) == 0) {
+ if ((body = search_method(klass, id, &origin)) == 0) {
return 0;
}
if (!body->nd_body) return 0;
/* store in cache */
- ent = cache + EXPR1(class, id);
- ent->class = class;
+ ent = cache + EXPR1(klass, id);
+ ent->klass = klass;
ent->noex = body->nd_noex;
body = body->nd_body;
if (nd_type(body) == NODE_FBODY) {
ent->mid = id;
- *classp = body->nd_orig;
+ *klassp = body->nd_orig;
ent->origin = body->nd_orig;
*idp = ent->mid0 = body->nd_mid;
body = ent->method = body->nd_head;
}
else {
- *classp = (VALUE)origin;
+ *klassp = origin;
ent->origin = origin;
ent->mid = ent->mid0 = id;
ent->method = body;
@@ -171,23 +172,23 @@ rb_get_method_body(classp, idp, noexp)
}
void
-rb_alias(class, name, def)
- VALUE class;
+rb_alias(klass, name, def)
+ VALUE klass;
ID name, def;
{
VALUE origin;
NODE *orig, *body;
if (name == def) return;
- orig = search_method(class, def, &origin);
+ orig = search_method(klass, def, &origin);
if (!orig || !orig->nd_body) {
- if (TYPE(class) == T_MODULE) {
+ if (TYPE(klass) == T_MODULE) {
orig = search_method(cObject, def, &origin);
}
}
if (!orig || !orig->nd_body) {
NameError("undefined method `%s' for `%s'",
- rb_id2name(def), rb_class2name((VALUE)class));
+ rb_id2name(def), rb_class2name(klass));
}
body = orig->nd_body;
if (nd_type(body) == NODE_FBODY) { /* was alias */
@@ -196,47 +197,47 @@ rb_alias(class, name, def)
origin = body->nd_orig;
}
- st_insert(RCLASS(class)->m_tbl, name,
+ st_insert(RCLASS(klass)->m_tbl, name,
NEW_METHOD(NEW_FBODY(body, def, origin), orig->nd_noex));
}
static void
-rb_export_method(class, name, noex)
- VALUE class;
+rb_export_method(klass, name, noex)
+ VALUE klass;
ID name;
int noex;
{
NODE *body;
- struct RClass *origin;
+ VALUE origin;
- body = search_method(class, name, &origin);
- if (!body && TYPE(class) == T_MODULE) {
+ body = search_method(klass, name, &origin);
+ if (!body && TYPE(klass) == T_MODULE) {
body = search_method(cObject, name, &origin);
}
if (!body) {
NameError("undefined method `%s' for `%s'",
- rb_id2name(name), rb_class2name(class));
+ rb_id2name(name), rb_class2name(klass));
}
if (body->nd_noex != noex) {
- if (class == (VALUE)origin) {
+ if (klass == origin) {
body->nd_noex = noex;
}
else {
rb_clear_cache_by_id(name);
- rb_add_method(class, name, NEW_ZSUPER(), noex);
+ rb_add_method(klass, name, NEW_ZSUPER(), noex);
}
}
}
static VALUE
-method_boundp(class, id, ex)
- VALUE class;
+method_boundp(klass, id, ex)
+ VALUE klass;
ID id;
int ex;
{
int noex;
- if (rb_get_method_body(&class, &id, &noex)) {
+ if (rb_get_method_body(&klass, &id, &noex)) {
if (ex && noex == NOEX_PRIVATE)
return FALSE;
return TRUE;
@@ -245,12 +246,12 @@ method_boundp(class, id, ex)
}
int
-rb_method_boundp(class, id, ex)
- VALUE class;
+rb_method_boundp(klass, id, ex)
+ VALUE klass;
ID id;
int ex;
{
- if (method_boundp(class, id, ex))
+ if (method_boundp(klass, id, ex))
return TRUE;
return FALSE;
}
@@ -282,15 +283,15 @@ static struct FRAME *top_frame;
static struct SCOPE *top_scope;
#define PUSH_FRAME() { \
- struct FRAME *_frame = ALLOCA_N(struct FRAME,1);\
- _frame->prev = the_frame; \
- _frame->file = sourcefile; \
- _frame->line = sourceline; \
- _frame->iter = the_iter->iter; \
- _frame->cbase = the_frame->cbase; \
- the_frame = _frame; \
+ struct FRAME _frame; \
+ _frame.prev = the_frame; \
+ _frame.file = sourcefile; \
+ _frame.line = sourceline; \
+ _frame.iter = the_iter->iter; \
+ _frame.cbase = the_frame->cbase; \
+ the_frame = &_frame; \
-#define POP_FRAME() the_frame = _frame->prev; }
+#define POP_FRAME() the_frame = _frame.prev; }
struct BLOCK {
NODE *var;
@@ -298,7 +299,7 @@ struct BLOCK {
VALUE self;
struct FRAME frame;
struct SCOPE *scope;
- VALUE class;
+ VALUE klass;
struct tag *tag;
int iter;
struct RVarmap *d_vars;
@@ -309,29 +310,29 @@ struct BLOCK {
} *the_block;
#define PUSH_BLOCK(v,b) { \
- struct BLOCK *_block = ALLOCA_N(struct BLOCK,1);\
- _block->tag = prot_tag; \
- _block->var = v; \
- _block->body = b; \
- _block->self = self; \
- _block->frame = *the_frame; \
- _block->class = the_class; \
- _block->frame.file = sourcefile; \
- _block->frame.line = sourceline; \
- _block->scope = the_scope; \
- _block->d_vars = the_dyna_vars; \
- _block->prev = the_block; \
- _block->iter = the_iter->iter; \
- the_block = _block;
+ struct BLOCK _block; \
+ _block.tag = prot_tag; \
+ _block.var = v; \
+ _block.body = b; \
+ _block.self = self; \
+ _block.frame = *the_frame; \
+ _block.klass = the_class; \
+ _block.frame.file = sourcefile; \
+ _block.frame.line = sourceline; \
+ _block.scope = the_scope; \
+ _block.d_vars = the_dyna_vars; \
+ _block.prev = the_block; \
+ _block.iter = the_iter->iter; \
+ the_block = &_block;
#define PUSH_BLOCK2(b) { \
- struct BLOCK *_block = ALLOCA_N(struct BLOCK,1);\
- *_block = *b; \
- _block->prev = the_block; \
- the_block = _block;
+ struct BLOCK _block; \
+ _block = *b; \
+ _block.prev = the_block; \
+ the_block = &_block;
#define POP_BLOCK() \
- the_block = the_block->prev; \
+ the_block = _block.prev; \
}
struct RVarmap *the_dyna_vars;
@@ -416,38 +417,26 @@ static struct iter {
the_iter = _iter.prev; \
}
-#ifdef C_ALLOCA
-/* need to protect retval in struct tag from GC. */
-#define tag_retval_dcl VALUE *dd_retval
-#define tag_retval_init VALUE _tag_retval = Qnil;\
- _tag->dd_retval = &_tag_retval;
-#define tag_retval dd_retval[0]
-#else
-#define tag_retval_dcl VALUE retval
-#define tag_retval_init _tag->retval = Qnil
-#define tag_retval retval
-#endif
-
static struct tag {
jmp_buf buf;
struct FRAME *frame;
struct iter *iter;
ID tag;
- tag_retval_dcl;
+ VALUE retval;
ID dst;
struct tag *prev;
} *prot_tag;
#define PUSH_TAG(ptag) { \
- struct tag *_tag = ALLOCA_N(struct tag,1);\
- tag_retval_init; \
- _tag->frame = the_frame; \
- _tag->iter = the_iter; \
- _tag->prev = prot_tag; \
- _tag->tag_retval = Qnil; \
- _tag->tag = ptag; \
- _tag->dst = 0; \
- prot_tag = _tag;
+ struct tag _tag; \
+ _tag.retval = Qnil; \
+ _tag.frame = the_frame; \
+ _tag.iter = the_iter; \
+ _tag.prev = prot_tag; \
+ _tag.retval = Qnil; \
+ _tag.tag = ptag; \
+ _tag.dst = 0; \
+ prot_tag = &_tag;
#define PROT_NONE 0
#define PROT_FUNC -1
@@ -462,7 +451,7 @@ static struct tag {
}
#define POP_TAG() \
- prot_tag = _tag->prev; \
+ prot_tag = _tag.prev; \
}
#define TAG_RETURN 0x1
@@ -717,6 +706,7 @@ ruby_init()
top_scope = the_scope;
/* default visibility is private at toplevel */
FL_SET(top_scope, SCOPE_PRIVATE);
+ FL_UNSET(top_scope, SCOPE_MODFUNC);
PUSH_TAG(PROT_NONE)
if ((state = EXEC_TAG()) == 0) {
@@ -746,11 +736,10 @@ ruby_options(argc, argv)
NODE *save;
ruby_process_options(argc, argv);
+ ext_init = 1; /* Init_ext() called in ruby_process_options */
save = eval_tree;
eval_tree = 0;
- Init_ext();
- ext_init = 1;
- rb_require_modules();
+ ruby_require_modules();
eval_tree = save;
}
POP_TAG();
@@ -1024,10 +1013,10 @@ ev_const_defined(cref, id)
NODE *cbase = cref;
while (cbase && cbase->nd_clss != cObject) {
- struct RClass *class = RCLASS(cbase->nd_clss);
+ struct RClass *klass = RCLASS(cbase->nd_clss);
- if (class->iv_tbl &&
- st_lookup(class->iv_tbl, id, 0)) {
+ if (klass->iv_tbl &&
+ st_lookup(klass->iv_tbl, id, 0)) {
return TRUE;
}
cbase = cbase->nd_next;
@@ -1044,10 +1033,10 @@ ev_const_get(cref, id)
VALUE result;
while (cbase && cbase->nd_clss != cObject) {
- struct RClass *class = RCLASS(cbase->nd_clss);
+ struct RClass *klass = RCLASS(cbase->nd_clss);
- if (class->iv_tbl &&
- st_lookup(class->iv_tbl, id, &result)) {
+ if (klass->iv_tbl &&
+ st_lookup(klass->iv_tbl, id, &result)) {
return result;
}
cbase = cbase->nd_next;
@@ -1103,16 +1092,27 @@ mod_undef_method(mod, name)
}
static VALUE
-mod_alias_method(mod, new, old)
- VALUE mod, new, old;
+mod_alias_method(mod, newname, oldname)
+ VALUE mod, newname, oldname;
{
- ID id = rb_to_id(new);
+ ID id = rb_to_id(newname);
- rb_alias(mod, id, rb_to_id(old));
+ rb_alias(mod, id, rb_to_id(oldname));
rb_clear_cache_by_id(id);
return mod;
}
+#if defined(C_ALLOCA) && defined(THREAD)
+# define TMP_PROTECT NODE *__protect_tmp=0
+# define TMP_ALLOC(type,n) \
+ (__protect_tmp = node_newnode(NODE_ALLOCA, \
+ str_new(0,sizeof(type)*(n)),0,__protect_tmp), \
+ (void*)RSTRING(__protect_tmp->nd_head)->ptr)
+#else
+# define TMP_PROTECT typedef int foobazzz
+# define TMP_ALLOC(type,n) ALLOCA_N(type,n)
+#endif
+
#define SETUP_ARGS(anode) {\
NODE *n = anode;\
if (!n) {\
@@ -1126,7 +1126,7 @@ mod_alias_method(mod, new, old)
int line = sourceline;\
int i;\
n = anode;\
- argv = ALLOCA_N(VALUE,argc);\
+ argv = TMP_ALLOC(VALUE,argc);\
for (i=0;i<argc;i++) {\
argv[i] = rb_eval(self,n->nd_head);\
n=n->nd_next;\
@@ -1371,7 +1371,7 @@ call_trace_func(event, file, line, self, id)
prev = the_frame;
PUSH_FRAME();
- *the_frame = *_frame->prev;
+ *the_frame = *_frame.prev;
the_frame->prev = prev;
the_frame->line = sourceline = line;
@@ -1606,7 +1606,7 @@ rb_eval(self, node)
else if (the_block->tag->dst == state) {
state &= TAG_MASK;
if (state == TAG_RETURN) {
- result = prot_tag->tag_retval;
+ result = prot_tag->retval;
}
}
POP_TAG();
@@ -1767,6 +1767,7 @@ rb_eval(self, node)
{
VALUE recv;
int argc; VALUE *argv; /* used in SETUP_ARGS */
+ TMP_PROTECT;
PUSH_ITER(ITER_NOT);
recv = rb_eval(self, node->nd_recv);
@@ -1779,6 +1780,7 @@ rb_eval(self, node)
case NODE_FCALL:
{
int argc; VALUE *argv; /* used in SETUP_ARGS */
+ TMP_PROTECT;
PUSH_ITER(ITER_NOT);
SETUP_ARGS(node->nd_args);
@@ -1795,6 +1797,7 @@ rb_eval(self, node)
case NODE_ZSUPER:
{
int argc; VALUE *argv; /* used in SETUP_ARGS */
+ TMP_PROTECT;
if (nd_type(node) == NODE_ZSUPER) {
argc = the_frame->argc;
@@ -1819,7 +1822,7 @@ rb_eval(self, node)
PUSH_SCOPE();
PUSH_TAG(PROT_NONE);
- if (node->nd_rval) the_frame->cbase = (VALUE)node->nd_rval;
+ if (node->nd_rval) the_frame->cbase = node->nd_rval;
if (node->nd_tbl) {
VALUE *vars = ALLOCA_N(VALUE, node->nd_tbl[0]+1);
*vars++ = (VALUE)node;
@@ -1846,6 +1849,7 @@ rb_eval(self, node)
int argc; VALUE *argv; /* used in SETUP_ARGS */
VALUE recv, val;
NODE *rval;
+ TMP_PROTECT;
recv = rb_eval(self, node->nd_recv);
rval = node->nd_args->nd_head;
@@ -1950,18 +1954,18 @@ rb_eval(self, node)
case NODE_COLON2:
{
- VALUE cls;
+ VALUE klass;
- cls = rb_eval(self, node->nd_head);
- switch (TYPE(cls)) {
+ klass = rb_eval(self, node->nd_head);
+ switch (TYPE(klass)) {
case T_CLASS:
case T_MODULE:
break;
default:
- Check_Type(cls, T_CLASS);
+ Check_Type(klass, T_CLASS);
break;
}
- result = rb_const_get_at(cls, node->nd_mid);
+ result = rb_const_get_at(klass, node->nd_mid);
}
break;
@@ -2106,19 +2110,25 @@ rb_eval(self, node)
body = search_method(the_class, node->nd_mid, &origin);
if (body) {
- if (origin == (VALUE)the_class) {
+ if (origin == the_class) {
Warning("discarding old %s", rb_id2name(node->nd_mid));
}
rb_clear_cache_by_id(node->nd_mid);
}
- if (FL_TEST(the_scope,SCOPE_PRIVATE)) {
+ if (FL_TEST(the_scope,SCOPE_PRIVATE) || node->nd_mid == init) {
noex = NOEX_PRIVATE;
}
else {
noex = NOEX_PUBLIC;
}
rb_add_method(the_class, node->nd_mid, node->nd_defn, noex);
+ if (FL_TEST(the_scope,SCOPE_MODFUNC)) {
+ rb_add_method(rb_singleton_class(the_class),
+ node->nd_mid, node->nd_defn, NOEX_PUBLIC);
+ rb_funcall(the_class, rb_intern("singleton_method_added"),
+ 1, INT2FIX(node->nd_mid));
+ }
if (FL_TEST(the_class, FL_SINGLETON)) {
VALUE recv = rb_iv_get(the_class, "__attached__");
rb_funcall(recv, rb_intern("singleton_method_added"),
@@ -2135,7 +2145,7 @@ rb_eval(self, node)
case NODE_DEFS:
if (node->nd_defn) {
VALUE recv = rb_eval(self, node->nd_recv);
- VALUE class;
+ VALUE klass;
NODE *body;
if (FIXNUM_P(recv)) {
@@ -2151,12 +2161,12 @@ rb_eval(self, node)
rb_id2name(node->nd_mid));
}
- class = rb_singleton_class(recv);
- if (st_lookup(RCLASS(class)->m_tbl, node->nd_mid, &body)) {
+ klass = rb_singleton_class(recv);
+ if (st_lookup(RCLASS(klass)->m_tbl, node->nd_mid, &body)) {
Warning("redefine %s", rb_id2name(node->nd_mid));
}
rb_clear_cache_by_id(node->nd_mid);
- rb_add_method(class, node->nd_mid, node->nd_defn, NOEX_PUBLIC);
+ rb_add_method(klass, node->nd_mid, node->nd_defn, NOEX_PUBLIC);
rb_funcall(recv, rb_intern("singleton_method_added"),
1, INT2FIX(node->nd_mid));
result = Qnil;
@@ -2171,7 +2181,7 @@ rb_eval(self, node)
body = search_method(the_class, node->nd_mid, &origin);
if (!body || !body->nd_body) {
NameError("undefined method `%s' for class `%s'",
- rb_id2name(node->nd_mid), rb_class2name((VALUE)the_class));
+ rb_id2name(node->nd_mid), rb_class2name(the_class));
}
rb_clear_cache_by_id(node->nd_mid);
rb_add_method(the_class, node->nd_mid, 0, NOEX_PUBLIC);
@@ -2193,7 +2203,7 @@ rb_eval(self, node)
case NODE_CLASS:
{
- VALUE super, class, tmp;
+ VALUE super, klass, tmp;
if (node->nd_super) {
super = superclass(self, node->nd_super);
@@ -2203,15 +2213,15 @@ rb_eval(self, node)
}
if (rb_const_defined_at(the_class, node->nd_cname) &&
- ((VALUE)the_class != cObject ||
+ (the_class != cObject ||
!rb_autoload_defined(node->nd_cname))) {
- class = rb_const_get_at(the_class, node->nd_cname);
- if (TYPE(class) != T_CLASS) {
+ klass = rb_const_get_at(the_class, node->nd_cname);
+ if (TYPE(klass) != T_CLASS) {
TypeError("%s is not a class", rb_id2name(node->nd_cname));
}
if (super) {
- tmp = RCLASS(class)->super;
+ tmp = RCLASS(klass)->super;
if (FL_TEST(tmp, FL_SINGLETON)) {
tmp = RCLASS(tmp)->super;
}
@@ -2230,12 +2240,12 @@ rb_eval(self, node)
}
else {
if (!super) super = cObject;
- class = rb_define_class_id(node->nd_cname, super);
- rb_const_set(the_class, node->nd_cname, class);
- rb_set_class_path(class,the_class,rb_id2name(node->nd_cname));
+ klass = rb_define_class_id(node->nd_cname, super);
+ rb_const_set(the_class, node->nd_cname, klass);
+ rb_set_class_path(klass,the_class,rb_id2name(node->nd_cname));
}
- return module_setup(class, node->nd_body);
+ return module_setup(klass, node->nd_body);
}
break;
@@ -2244,7 +2254,7 @@ rb_eval(self, node)
VALUE module;
if (rb_const_defined_at(the_class, node->nd_cname) &&
- ((VALUE)the_class != cObject ||
+ (the_class != cObject ||
!rb_autoload_defined(node->nd_cname))) {
module = rb_const_get_at(the_class, node->nd_cname);
@@ -2267,24 +2277,24 @@ rb_eval(self, node)
case NODE_SCLASS:
{
- VALUE class;
+ VALUE klass;
- class = rb_eval(self, node->nd_recv);
- if (FIXNUM_P(class)) {
+ klass = rb_eval(self, node->nd_recv);
+ if (FIXNUM_P(klass)) {
TypeError("No virtual class for Fixnums");
}
- if (NIL_P(class)) {
+ if (NIL_P(klass)) {
TypeError("No virtual class for nil");
}
- if (rb_special_const_p(class)) {
+ if (rb_special_const_p(klass)) {
TypeError("No virtual class for special constants");
}
- if (FL_TEST(CLASS_OF(class), FL_SINGLETON)) {
+ if (FL_TEST(CLASS_OF(klass), FL_SINGLETON)) {
rb_clear_cache();
- class = rb_singleton_class(class);
}
-
- result = module_setup(class, node->nd_body);
+ klass = rb_singleton_class(klass);
+
+ result = module_setup(klass, node->nd_body);
}
break;
@@ -2326,6 +2336,7 @@ module_setup(module, node)
VALUE result; /* OK */
char *file = sourcefile;
int line = sourceline;
+ TMP_PROTECT;
/* fill c-ref */
node->nd_clss = module;
@@ -2337,7 +2348,7 @@ module_setup(module, node)
if (node->nd_rval) the_frame->cbase = node->nd_rval;
if (node->nd_tbl) {
- VALUE *vars = ALLOCA_N(VALUE, node->nd_tbl[0]+1);
+ VALUE *vars = TMP_ALLOC(VALUE, node->nd_tbl[0]+1);
*vars++ = (VALUE)node;
the_scope->local_vars = vars;
memclear(the_scope->local_vars, node->nd_tbl[0]);
@@ -2354,7 +2365,7 @@ module_setup(module, node)
call_trace_func("class", file, line,
the_class, the_frame->last_func);
}
- result = rb_eval((VALUE)the_class, node->nd_body);
+ result = rb_eval(the_class, node->nd_body);
}
POP_TAG();
POP_SCOPE();
@@ -2568,7 +2579,7 @@ f_raise(argc, argv)
}
PUSH_FRAME(); /* fake frame */
- *the_frame = *_frame->prev->prev;
+ *the_frame = *_frame.prev->prev;
rb_longjmp(TAG_RAISE, mesg, arg3);
POP_FRAME();
}
@@ -2614,7 +2625,7 @@ rb_yield_0(val, self)
the_scope = block->scope;
the_block = block->prev;
the_dyna_vars = block->d_vars;
- the_class = block->class;
+ the_class = block->klass;
if (!self) self = block->self;
node = block->body;
if (block->var) {
@@ -2795,7 +2806,7 @@ rb_iterate(it_proc, data1, bl_proc, data2)
if (the_block->tag->dst == state) {
state &= TAG_MASK;
if (state == TAG_RETURN) {
- retval = prot_tag->tag_retval;
+ retval = prot_tag->retval;
}
}
POP_TAG();
@@ -2828,6 +2839,7 @@ handle_rescue(self, node)
NODE *node;
{
int argc; VALUE *argv; /* used in SETUP_ARGS */
+ TMP_PROTECT;
if (!node->nd_args) {
return obj_is_kind_of(errinfo, eException);
@@ -2968,7 +2980,7 @@ f_missing(argc, argv, obj)
sourcefile = file;
sourceline = line;
PUSH_FRAME(); /* fake frame */
- *the_frame = *_frame->prev->prev;
+ *the_frame = *_frame.prev->prev;
NameError(format,
rb_id2name(id),
@@ -3022,8 +3034,8 @@ stack_length()
}
static VALUE
-rb_call(class, recv, mid, argc, argv, scope)
- VALUE class, recv;
+rb_call(klass, recv, mid, argc, argv, scope)
+ VALUE klass, recv;
ID mid;
int argc; /* OK */
VALUE *argv; /* OK */
@@ -3037,17 +3049,18 @@ rb_call(class, recv, mid, argc, argv, scope)
int itr;
enum node_type type;
static int tick;
+ TMP_PROTECT;
again:
/* is it in the method cache? */
- ent = cache + EXPR1(class, mid);
- if (ent->mid == mid && ent->class == class) {
- class = ent->origin;
+ ent = cache + EXPR1(klass, mid);
+ if (ent->mid == mid && ent->klass == klass) {
+ klass = ent->origin;
id = ent->mid0;
noex = ent->noex;
body = ent->method;
}
- else if ((body = rb_get_method_body(&class, &id, &noex)) == 0) {
+ else if ((body = rb_get_method_body(&klass, &id, &noex)) == 0) {
return rb_undefined(recv, mid, argc, argv, scope==2?CSTAT_VCALL:0);
}
@@ -3070,19 +3083,19 @@ rb_call(class, recv, mid, argc, argv, scope)
/* for re-scoped/renamed method */
mid = id;
if (scope == 0) scope = 1;
- if (RCLASS(class)->super == 0) {
+ if (RCLASS(klass)->super == 0) {
/* origin is the Module, so need to scan superclass hierarchy. */
- struct RClass *cl = RCLASS(class);
+ struct RClass *cl = RCLASS(klass);
- class = RBASIC(recv)->class;
- while (class) {
- if (RCLASS(class)->m_tbl == cl->m_tbl)
+ klass = RBASIC(recv)->klass;
+ while (klass) {
+ if (RCLASS(klass)->m_tbl == cl->m_tbl)
break;
- class = RCLASS(class)->super;
+ klass = RCLASS(klass)->super;
}
}
else {
- class = RCLASS(class)->super;
+ klass = RCLASS(klass)->super;
}
goto again;
}
@@ -3093,7 +3106,7 @@ rb_call(class, recv, mid, argc, argv, scope)
PUSH_ITER(itr);
PUSH_FRAME();
the_frame->last_func = id;
- the_frame->last_class = class;
+ the_frame->last_class = klass;
the_frame->argc = argc;
the_frame->argv = argv;
@@ -3200,7 +3213,7 @@ rb_call(class, recv, mid, argc, argv, scope)
default:
if (len < 0) {
Bug("bad argc(%d) specified for `%s(%s)'",
- len, rb_class2name((VALUE)class), rb_id2name(mid));
+ len, rb_class2name(klass), rb_id2name(mid));
}
else {
ArgError("too many arguments(%d)", len);
@@ -3225,7 +3238,7 @@ rb_call(class, recv, mid, argc, argv, scope)
if (body->nd_rval) the_frame->cbase = body->nd_rval;
if (body->nd_tbl) {
- local_vars = ALLOCA_N(VALUE, body->nd_tbl[0]+1);
+ local_vars = TMP_ALLOC(VALUE, body->nd_tbl[0]+1);
*local_vars++ = (VALUE)body;
memclear(local_vars, body->nd_tbl[0]);
the_scope->local_tbl = body->nd_tbl;
@@ -3301,7 +3314,7 @@ rb_call(class, recv, mid, argc, argv, scope)
result = rb_eval(recv, body);
}
else if (state == TAG_RETURN) {
- result = prot_tag->tag_retval;
+ result = prot_tag->retval;
state = 0;
}
POP_VARS();
@@ -3572,7 +3585,7 @@ eval(self, src, scope)
rb_in_eval++;
if (TYPE(the_class) == T_ICLASS) {
- the_class = RBASIC(the_class)->class;
+ the_class = RBASIC(the_class)->klass;
}
PUSH_TAG(PROT_NONE);
if ((state = EXEC_TAG()) == 0) {
@@ -3644,8 +3657,8 @@ eval_under(under, self, src)
PUSH_CLASS();
the_class = under;
PUSH_FRAME();
- the_frame->last_func = _frame->last_func;
- the_frame->last_class = _frame->last_class;
+ the_frame->last_func = _frame.last_func;
+ the_frame->last_class = _frame.last_class;
the_frame->argc = 1;
the_frame->argv = &src;
the_frame->cbase = (VALUE)node_newnode(NODE_CREF,under,0,cbase);
@@ -3722,6 +3735,7 @@ f_load(obj, fname)
int state;
char *file;
volatile ID last_func;
+ TMP_PROTECT;
Check_SafeStr(fname);
if (RSTRING(fname)->ptr[0] == '~') {
@@ -3737,7 +3751,7 @@ f_load(obj, fname)
if (top_scope->local_tbl) {
int len = top_scope->local_tbl[0]+1;
ID *tbl = ALLOC_N(ID, len);
- VALUE *vars = ALLOCA_N(VALUE, len);
+ VALUE *vars = TMP_ALLOC(VALUE, len);
*vars++ = 0;
MEMCPY(tbl, top_scope->local_tbl, ID, len);
MEMCPY(vars, top_scope->local_vars, ID, len-1);
@@ -3746,6 +3760,7 @@ f_load(obj, fname)
}
/* default visibility is private at loading toplevel */
FL_SET(the_scope, SCOPE_PRIVATE);
+ FL_UNSET(top_scope, SCOPE_MODFUNC);
state = EXEC_TAG();
last_func = the_frame->last_func;
@@ -3938,6 +3953,7 @@ mod_public(argc, argv, module)
{
if (argc == 0) {
FL_UNSET(the_scope, SCOPE_PRIVATE);
+ FL_UNSET(top_scope, SCOPE_MODFUNC);
}
else {
set_method_visibility(module, argc, argv, NOEX_PUBLIC);
@@ -3953,6 +3969,7 @@ mod_private(argc, argv, module)
{
if (argc == 0) {
FL_SET(the_scope, SCOPE_PRIVATE);
+ FL_UNSET(top_scope, SCOPE_MODFUNC);
}
else {
set_method_visibility(module, argc, argv, NOEX_PRIVATE);
@@ -4006,7 +4023,12 @@ mod_modfunc(argc, argv, module)
ID id;
NODE *body;
- rb_clear_cache();
+ if (argc == 0) {
+ FL_SET(the_scope, SCOPE_PRIVATE);
+ FL_SET(the_scope, SCOPE_MODFUNC);
+ return module;
+ }
+
set_method_visibility(module, argc, argv, NOEX_PRIVATE);
for (i=0; i<argc; i++) {
id = rb_to_id(argv[i]);
@@ -4015,6 +4037,7 @@ mod_modfunc(argc, argv, module)
NameError("undefined method `%s' for module `%s'",
rb_id2name(id), rb_class2name(module));
}
+ rb_clear_cache_by_id(id);
rb_add_method(rb_singleton_class(module), id, body->nd_body, NOEX_PUBLIC);
}
return module;
@@ -4053,17 +4076,17 @@ mod_include(argc, argv, module)
}
VALUE
-class_new_instance(argc, argv, class)
+class_new_instance(argc, argv, klass)
int argc;
VALUE *argv;
- VALUE class;
+ VALUE klass;
{
VALUE obj;
- if (FL_TEST(class, FL_SINGLETON)) {
+ if (FL_TEST(klass, FL_SINGLETON)) {
TypeError("can't create instance of virtual class");
}
- obj = obj_alloc(class);
+ obj = obj_alloc(klass);
PUSH_ITER(iterator_p()?ITER_PRE:ITER_NOT);
rb_funcall2(obj, init, argc, argv);
POP_ITER();
@@ -4347,8 +4370,8 @@ f_binding(self)
#define PROC_TMASK (FL_USER1|FL_USER2)
static VALUE
-proc_s_new(class)
- VALUE class;
+proc_s_new(klass)
+ VALUE klass;
{
volatile VALUE proc;
struct BLOCK *data;
@@ -4357,7 +4380,7 @@ proc_s_new(class)
ArgError("tryed to create Procedure-Object out of iterator");
}
- proc = Data_Make_Struct(class, struct BLOCK, blk_mark, blk_free, data);
+ proc = Data_Make_Struct(klass, struct BLOCK, blk_mark, blk_free, data);
*data = *the_block;
#ifdef THREAD
@@ -4392,6 +4415,22 @@ f_lambda()
return proc_s_new(cProc);
}
+static int
+blk_orphan(data)
+ struct BLOCK *data;
+{
+ if (data->scope && data->scope != top_scope &&
+ (data->scope->flag & SCOPE_NOSTACK)) {
+ return 1;
+ }
+#ifdef THREAD
+ if (data->orig_thread != thread_current()) {
+ return 1;
+ }
+#endif
+ return 0;
+}
+
static VALUE
proc_call(proc, args)
VALUE proc, args; /* OK */
@@ -4414,32 +4453,22 @@ proc_call(proc, args)
}
Data_Get_Struct(proc, struct BLOCK, data);
+ orphan = blk_orphan(data);
+
+ /* PUSH BLOCK from data */
+ PUSH_BLOCK2(data);
+ PUSH_ITER(ITER_CUR);
+ the_frame->iter = ITER_CUR;
- if (data->scope && (data->scope->flag & SCOPE_NOSTACK)) {
- orphan = 1;
- }
- else {
-#ifdef THREAD
- if (data->orig_thread != thread_current()) {
- orphan = 1;
- }
- else
-#endif
- orphan = 0;
- }
if (orphan) {/* orphan procedure */
if (iterator_p()) {
- data->frame.iter = ITER_CUR;
+ the_block->frame.iter = ITER_CUR;
}
else {
- data->frame.iter = ITER_NOT;
+ the_block->frame.iter = ITER_NOT;
}
}
- /* PUSH BLOCK from data */
- PUSH_BLOCK2(data);
- PUSH_ITER(ITER_CUR);
- the_frame->iter = ITER_CUR;
if (FL_TEST(proc, PROC_TAINT)) {
switch (RBASIC(proc)->flags & PROC_TMASK) {
case PROC_T3:
@@ -4487,6 +4516,76 @@ proc_call(proc, args)
return result;
}
+static VALUE
+proc_iterate(proc)
+ VALUE proc;
+{
+ VALUE lambda = f_lambda();
+ struct BLOCK *data;
+ volatile VALUE result = Qnil;
+ int state;
+ volatile int orphan;
+ volatile int safe = safe_level;
+
+ Data_Get_Struct(lambda, struct BLOCK, data);
+ data->frame.iter = ITER_PRE;
+ data->iter = ITER_PRE;
+
+ Data_Get_Struct(proc, struct BLOCK, data);
+ orphan = blk_orphan(data);
+
+ /* PUSH BLOCK from data */
+ PUSH_BLOCK2(data);
+ PUSH_ITER(ITER_PRE);
+ the_frame->iter = ITER_PRE;
+ if (FL_TEST(proc, PROC_TAINT)) {
+ switch (RBASIC(proc)->flags & PROC_TMASK) {
+ case PROC_T3:
+ safe_level = 3;
+ break;
+ case PROC_T4:
+ safe_level = 4;
+ break;
+ case PROC_T5:
+ safe_level = 5;
+ break;
+ }
+ }
+
+ PUSH_TAG(PROT_NONE);
+ state = EXEC_TAG();
+ if (state == 0) {
+ result = proc_call(lambda, Qnil);
+ }
+ POP_TAG();
+
+ POP_ITER();
+ if (the_block->tag->dst == state) {
+ state &= TAG_MASK;
+ orphan = 2;
+ }
+ POP_BLOCK();
+ safe_level = safe;
+
+ if (state) {
+ if (orphan == 2) {/* escape from orphan procedure */
+ switch (state) {
+ case TAG_BREAK:
+ Raise(eLocalJumpError, "break from proc-closure");
+ break;
+ case TAG_RETRY:
+ Raise(eLocalJumpError, "retry from proc-closure");
+ break;
+ case TAG_RETURN:
+ Raise(eLocalJumpError, "return from proc-closure");
+ break;
+ }
+ }
+ JUMP_TAG(state);
+ }
+ return result;
+}
+
void
Init_Proc()
{
@@ -4496,6 +4595,7 @@ Init_Proc()
rb_define_singleton_method(cProc, "new", proc_s_new, 0);
rb_define_method(cProc, "call", proc_call, -2);
+ rb_define_method(cProc, "iterate", proc_iterate, 0);
rb_define_global_function("proc", f_lambda, 0);
rb_define_global_function("lambda", f_lambda, 0);
rb_define_global_function("binding", f_binding, 0);
@@ -4562,7 +4662,7 @@ struct thread {
struct BLOCK *block;
struct iter *iter;
struct tag *tag;
- VALUE class;
+ VALUE klass;
VALUE trace;
@@ -4707,7 +4807,7 @@ thread_save_context(th)
th->frame = the_frame;
th->scope = the_scope;
- th->class = the_class;
+ th->klass = the_class;
th->dyna_vars = the_dyna_vars;
th->block = the_block;
th->iter = the_iter;
@@ -4764,12 +4864,11 @@ thread_restore_context(th, exit)
the_frame = th->frame;
the_scope = th->scope;
- the_class = th->class;
+ the_class = th->klass;
the_dyna_vars = th->dyna_vars;
the_block = th->block;
the_iter = th->iter;
prot_tag = th->tag;
- the_class = th->class;
errat = th->errat;
errinfo = th->errinfo;
last_status = th->last_status;
@@ -5376,7 +5475,7 @@ thread_alloc()
th->frame = 0;
th->scope = 0;
- th->class = 0;
+ th->klass = 0;
th->dyna_vars = 0;
th->block = 0;
th->iter = 0;
@@ -5721,7 +5820,7 @@ f_catch(dmy, tag)
val = rb_yield(tag);
}
else if (state == TAG_THROW && prot_tag->tag == prot_tag->dst) {
- val = prot_tag->tag_retval;
+ val = prot_tag->retval;
state = 0;
}
POP_TAG();
@@ -5745,7 +5844,7 @@ f_throw(argc, argv)
while (tt) {
if (tt->tag == t) {
tt->dst = t;
- tt->tag_retval = value;
+ tt->retval = value;
break;
}
#ifdef THREAD
@@ -5773,7 +5872,7 @@ return_value(val)
while (tt) {
if (tt->tag == PROT_FUNC) {
- tt->tag_retval = val;
+ tt->retval = val;
break;
}
#ifdef THREAD
diff --git a/ext/Setup b/ext/Setup
index c92ac53e00..9e3a2474c3 100644
--- a/ext/Setup
+++ b/ext/Setup
@@ -10,3 +10,4 @@
#socket
#tkutil
#tcltklib
+#gtk
diff --git a/ext/dbm/dbm.c b/ext/dbm/dbm.c
index b416802241..2941877dd6 100644
--- a/ext/dbm/dbm.c
+++ b/ext/dbm/dbm.c
@@ -122,19 +122,19 @@ fdbm_fetch(obj, keystr)
}
static VALUE
-fdbm_indexes(obj, ag)
- VALUE obj, ag;
+fdbm_indexes(argc, argv, obj)
+ int argc;
+ VALUE *argv;
+ VALUE obj;
{
- VALUE *p, *pend;
VALUE new;
- int i = 0;
- struct RArray *args = RARRAY(rb_Array(ag));
+ int i;
- new = ary_new2(args->len);
- p = args->ptr; pend = p + args->len;
- while (p < pend) {
- ary_push(new, fdbm_fetch(obj, *p++));
+ new = ary_new2(argc);
+ for (i=0; i<argc; i++) {
+ ary_push(new, fdbm_fetch(obj, argv[i]));
}
+
return new;
}
@@ -489,7 +489,8 @@ Init_dbm()
rb_define_method(cDBM, "close", fdbm_close, 0);
rb_define_method(cDBM, "[]", fdbm_fetch, 1);
rb_define_method(cDBM, "[]=", fdbm_store, 2);
- rb_define_method(cDBM, "indexes", fdbm_indexes, -2);
+ rb_define_method(cDBM, "indexes", fdbm_indexes, -1);
+ rb_define_method(cDBM, "indices", fdbm_indexes, -1);
rb_define_method(cDBM, "length", fdbm_length, 0);
rb_define_alias(cDBM, "size", "length");
rb_define_method(cDBM, "empty?", fdbm_empty_p, 0);
diff --git a/ext/extmk.rb.in b/ext/extmk.rb.in
index e1d318d19c..066e744944 100644
--- a/ext/extmk.rb.in
+++ b/ext/extmk.rb.in
@@ -276,7 +276,7 @@ realclean: clean
install:
"
if !$static
- mfile.printf "
+ mfile.printf "\
@test -d $(libdir) || mkdir $(libdir)
$(INSTALL) $(TARGET) $(libdir)/$(TARGET)
"
diff --git a/ext/fcntl/fcntl.c b/ext/fcntl/fcntl.c
index 17aacb13c3..186f9ac893 100644
--- a/ext/fcntl/fcntl.c
+++ b/ext/fcntl/fcntl.c
@@ -5,7 +5,7 @@
$Author$
created at: Mon Apr 7 18:53:05 JST 1997
- Copyright (C) 1997 Yukihiro Matsumoto
+ Copyright (C) 1997-1998 Yukihiro Matsumoto
************************************************/
diff --git a/ext/gtk/MANIFEST b/ext/gtk/MANIFEST
deleted file mode 100644
index 3e1962e1f3..0000000000
--- a/ext/gtk/MANIFEST
+++ /dev/null
@@ -1,18 +0,0 @@
-MANIFEST
-extconf.rb
-gtk.c
-test.rb
-test.xpm
-test0.rb
-test1.rb
-test2.rb
-test3.rb
-test4.rb
-test5.rb
-test6.rb
-test7.rb
-test8.rb
-test9.rb
-testa.rb
-testb.rb
-testc.rb
diff --git a/ext/gtk/extconf.rb b/ext/gtk/extconf.rb
deleted file mode 100644
index 621e0739a5..0000000000
--- a/ext/gtk/extconf.rb
+++ /dev/null
@@ -1,6 +0,0 @@
-require "mkmf"
-if have_library("glib", "g_print") and
- have_library("gdk", "gdk_init") and
- have_library("gtk", "gtk_init")
- create_makefile("gtk")
-end
diff --git a/ext/gtk/gtk.c b/ext/gtk/gtk.c
deleted file mode 100644
index 9114312195..0000000000
--- a/ext/gtk/gtk.c
+++ /dev/null
@@ -1,5904 +0,0 @@
-/************************************************
-
- gtk.c -
-
- $Author$
- $Date$
- created at: Wed Jan 7 23:55:11 JST 1998
-
-************************************************/
-
-#include "ruby.h"
-#include "sig.h"
-#include <gtk/gtk.h>
-#include <signal.h>
-
-extern VALUE rb_argv, rb_argv0;
-extern VALUE cData;
-
-static VALUE mGtk;
-
-static VALUE gObject;
-static VALUE gWidget;
-static VALUE gContainer;
-static VALUE gBin;
-static VALUE gAlignment;
-static VALUE gMisc;
-static VALUE gArrow;
-static VALUE gFrame;
-static VALUE gAspectFrame;
-static VALUE gData;
-static VALUE gAdjustment;
-static VALUE gBox;
-static VALUE gButton;
-static VALUE gTButton;
-static VALUE gCButton;
-static VALUE gRButton;
-static VALUE gBBox;
-static VALUE gCList;
-static VALUE gWindow;
-static VALUE gDialog;
-static VALUE gFileSel;
-static VALUE gVBox;
-static VALUE gColorSel;
-static VALUE gColorSelDialog;
-static VALUE gImage;
-static VALUE gDrawArea;
-static VALUE gEntry;
-static VALUE gEventBox;
-static VALUE gFixed;
-static VALUE gGamma;
-static VALUE gHBBox;
-static VALUE gVBBox;
-static VALUE gHBox;
-static VALUE gPaned;
-static VALUE gHPaned;
-static VALUE gVPaned;
-static VALUE gRuler;
-static VALUE gHRuler;
-static VALUE gVRuler;
-static VALUE gRange;
-static VALUE gScale;
-static VALUE gHScale;
-static VALUE gVScale;
-static VALUE gScrollbar;
-static VALUE gHScrollbar;
-static VALUE gVScrollbar;
-static VALUE gSeparator;
-static VALUE gHSeparator;
-static VALUE gVSeparator;
-static VALUE gInputDialog;
-static VALUE gLabel;
-static VALUE gList;
-static VALUE gItem;
-static VALUE gListItem;
-static VALUE gMenuShell;
-static VALUE gMenu;
-static VALUE gMenuBar;
-static VALUE gMenuItem;
-static VALUE gCMenuItem;
-static VALUE gRMenuItem;
-static VALUE gNotebook;
-static VALUE gOptionMenu;
-static VALUE gPixmap;
-static VALUE gPreview;
-static VALUE gProgressBar;
-static VALUE gScrolledWin;
-static VALUE gTable;
-static VALUE gText;
-static VALUE gToolbar;
-static VALUE gTooltips;
-static VALUE gTree;
-static VALUE gTreeItem;
-static VALUE gViewPort;
-
-static VALUE gAcceleratorTable;
-static VALUE gStyle;
-static VALUE gPreviewInfo;
-static VALUE gAllocation;
-static VALUE gRequisiton;
-
-static VALUE mGdk;
-
-static VALUE gdkFont;
-static VALUE gdkColor;
-static VALUE gdkColormap;
-static VALUE gdkPixmap;
-static VALUE gdkBitmap;
-static VALUE gdkWindow;
-static VALUE gdkImage;
-static VALUE gdkVisual;
-static VALUE gdkGC;
-static VALUE gdkRectangle;
-static VALUE gdkGCValues;
-static VALUE gdkRectangle;
-static VALUE gdkSegment;
-static VALUE gdkWindowAttr;
-static VALUE gdkCursor;
-static VALUE gdkAtom;
-static VALUE gdkColorContext;
-static VALUE gdkEvent;
-
-ID id_gtkdata, id_relatives, id_call;
-
-static void gobj_free();
-
-static char*
-get_cstring(str)
- VALUE str;
-{
- if (NIL_P(str)) return NULL;
- Check_Type(str, T_STRING);
- return RSTRING(str)->ptr;
-}
-
-static GtkObject*
-get_gobject(obj)
- VALUE obj;
-{
- struct RData *data;
- GtkObject *gtkp;
-
- if (NIL_P(obj)) return NULL;
-
- Check_Type(obj, T_OBJECT);
- data = RDATA(rb_ivar_get(obj, id_gtkdata));
- if (NIL_P(data) || data->dfree != gobj_free) {
- TypeError("not a Gtk object");
- }
- Data_Get_Struct(data, GtkObject, gtkp);
- if (!GTK_IS_OBJECT(gtkp)) {
- TypeError("not a GtkObject");
- }
-
- return gtkp;
-}
-
-static GtkWidget*
-get_widget(obj)
- VALUE obj;
-{
- GtkObject *data = get_gobject(obj);
-
- return GTK_WIDGET(data);
-}
-
-static VALUE
-get_value_from_gobject(obj)
- GtkObject *obj;
-{
- return (VALUE)gtk_object_get_user_data(obj);
-}
-
-static void
-clear_gobject(obj)
- VALUE obj;
-{
- rb_ivar_set(obj, id_relatives, Qnil);
-}
-
-static void
-add_relative(obj, relative)
- VALUE obj, relative;
-{
- VALUE ary = rb_ivar_get(obj, id_relatives);
-
- if (TYPE(ary) != T_ARRAY) {
- ary = ary_new();
- rb_ivar_set(obj, id_relatives, ary);
- }
- ary_push(ary, relative);
-}
-
-static VALUE gtk_object_list;
-
-static void
-gobj_free(obj)
- GtkObject *obj;
-{
- VALUE self = get_value_from_gobject(obj);
-
- if (GTK_OBJECT_NEED_DESTROY(obj)) {
- gtk_object_destroy(obj);
- }
- rb_ivar_set(self, id_relatives, Qnil);
-}
-
-static void
-delete_gobject(obj)
- GtkObject *obj;
-{
- ary_delete(gtk_object_list, get_value_from_gobject(obj));
-}
-
-static VALUE
-make_gobject(klass, gtkobj)
- VALUE klass;
- GtkObject *gtkobj;
-{
- VALUE obj = obj_alloc(klass);
- VALUE data;
-
- data = Data_Wrap_Struct(cData, 0, gobj_free, gtkobj);
- gtk_object_set_user_data(gtkobj, (gpointer)obj);
-
- rb_ivar_set(obj, id_gtkdata, data);
- gtk_signal_connect(gtkobj, "destroy", (GtkSignalFunc)delete_gobject, 0);
- ary_push(gtk_object_list, obj);
- return obj;
-}
-
-static VALUE
-make_widget(klass, widget)
- VALUE klass;
- GtkWidget *widget;
-{
- return make_gobject(klass, GTK_OBJECT(widget));
-}
-
-static void
-free_gstyle(style)
- GtkStyle *style;
-{
- gtk_style_unref(style);
-}
-
-static VALUE
-make_gstyle(style)
- GtkStyle *style;
-{
- gtk_style_ref(style);
- return Data_Wrap_Struct(gStyle, 0, free_gstyle, style);
-}
-
-static GtkStyle*
-get_gstyle(style)
- VALUE style;
-{
- GtkStyle *gstyle;
-
- if (NIL_P(style)) return NULL;
- if (!obj_is_instance_of(style, gStyle)) {
- TypeError("not a GtkStyle");
- }
- Data_Get_Struct(style, GtkStyle, gstyle);
-
- return gstyle;
-}
-
-static void
-free_gaccel(tbl)
- GtkAcceleratorTable *tbl;
-{
- gtk_accelerator_table_unref(tbl);
-}
-
-static VALUE
-make_gtkacceltbl(tbl)
- GtkAcceleratorTable *tbl;
-{
- gtk_accelerator_table_ref(tbl);
- return Data_Wrap_Struct(gAcceleratorTable, 0, free_gaccel, tbl);
-}
-
-static GtkAcceleratorTable*
-get_gtkacceltbl(value)
- VALUE value;
-{
- GtkAcceleratorTable *tbl;
-
- if (NIL_P(value)) return NULL;
-
- if (!obj_is_instance_of(value, gAcceleratorTable)) {
- TypeError("not an AcceleratorTable");
- }
- Data_Get_Struct(value, GtkAcceleratorTable, tbl);
-
- return tbl;
-}
-
-static VALUE
-make_gtkprevinfo(info)
- GtkPreviewInfo *info;
-{
- return Data_Wrap_Struct(gAcceleratorTable, 0, 0, info);
-}
-
-static GtkPreviewInfo*
-get_gtkprevinfo(value)
- VALUE value;
-{
- GtkPreviewInfo *info;
-
- if (NIL_P(value)) return NULL;
-
- if (!obj_is_instance_of(value, gPreviewInfo)) {
- TypeError("not a PreviewInfo");
- }
- Data_Get_Struct(value, GtkPreviewInfo, info);
-
- return info;
-}
-
-static void
-exec_callback(widget, data, nparams, params)
- GtkWidget *widget;
- VALUE data;
- int nparams;
- GtkType *params;
-{
- VALUE self = get_value_from_gobject(GTK_OBJECT(widget));
- VALUE proc = RARRAY(data)->ptr[0];
- VALUE event = RARRAY(data)->ptr[1];
- ID id = NUM2INT(event);
-
- if (NIL_P(proc) && rb_respond_to(self, id)) {
- rb_funcall(self, id, 3, self,
- INT2FIX(nparams), INT2NUM((INT)params));
- }
- else {
- rb_funcall(proc, id_call, 1, self);
- }
-}
-
-static void
-free_ttips(tips)
- GtkTooltips *tips;
-{
- gtk_tooltips_unref(tips);
-}
-
-static VALUE
-make_ttips(klass, tips)
- VALUE klass;
- GtkTooltips *tips;
-{
- gtk_tooltips_ref(tips);
- return Data_Wrap_Struct(klass, 0, free_ttips, tips);
-}
-
-static GtkTooltips*
-get_ttips(tips)
- VALUE tips;
-{
- GtkTooltips *gtips;
-
- if (NIL_P(tips)) return NULL;
-
- if (!obj_is_instance_of(tips, gTooltips)) {
- TypeError("not a GtkTooltips");
- }
- Data_Get_Struct(tips, GtkTooltips, gtips);
-
- return gtips;
-}
-
-static void
-free_gdkfont(font)
- GdkFont *font;
-{
- gdk_font_unref(font);
-}
-
-static VALUE
-make_gdkfont(font)
- GdkFont *font;
-{
- gdk_font_ref(font);
- return Data_Wrap_Struct(gdkFont, 0, free_gdkfont, font);
-}
-
-static GdkFont*
-get_gdkfont(font)
- VALUE font;
-{
- GdkFont *gfont;
-
- if (NIL_P(font)) return NULL;
-
- if (!obj_is_instance_of(font, gdkFont)) {
- TypeError("not a GdkFont");
- }
- Data_Get_Struct(font, GdkFont, gfont);
-
- return gfont;
-}
-
-static VALUE
-gdkfnt_equal(fn1, fn2)
- VALUE fn1, fn2;
-{
- if (gdk_font_equal(get_gdkfont(fn1), get_gdkfont(fn2)))
- return TRUE;
- return FALSE;
-}
-
-static void
-free_tobj(obj)
- gpointer obj;
-{
- free(obj);
-}
-
-static VALUE
-make_tobj(obj, klass, size)
- gpointer obj;
- VALUE klass;
- int size;
-{
- gpointer copy;
- VALUE data;
-
- copy = xmalloc(size);
- memcpy(copy, obj, size);
- data = Data_Wrap_Struct(klass, 0, free_tobj, copy);
-
- return data;
-}
-
-static gpointer
-get_tobj(obj, klass)
- VALUE obj, klass;
-{
- void *ptr;
-
- if (NIL_P(obj)) return NULL;
-
- if (!obj_is_instance_of(obj, klass)) {
- TypeError("not a %s", rb_class2name(klass));
- }
- Data_Get_Struct(obj, void, ptr);
-
- return ptr;
-}
-
-#define make_gdkcolor(c) make_tobj(c, gdkColor, sizeof(GdkColor))
-#define get_gdkcolor(c) ((GdkColor*)get_tobj(c, gdkColor))
-
-#define make_gdkrect(c) make_tobj(c, gdkRectangle, sizeof(GdkRectangle))
-#define get_gdkrect(c) ((GdkRectangle*)get_tobj(c, gdkRectangle))
-
-#define make_gdksegment(c) make_tobj(c, gdkSegment, sizeof(GdkSegment))
-#define get_gdksegment(c) ((GdkSegment*)get_tobj(c, gdkSegment))
-
-#define make_gdkwinattr(c) make_tobj(c, gdkWindowAttr, sizeof(GdkWindowAttr))
-#define get_gdkwinattr(c) ((GdkWindowAttr*)get_tobj(c, gdkWindowAttr))
-
-#define make_gdkwinattr(c) make_tobj(c, gdkWindowAttr, sizeof(GdkWindowAttr))
-#define get_gdkwinattr(c) ((GdkWindowAttr*)get_tobj(c, gdkWindowAttr))
-
-#define make_gallocation(c) make_tobj(c, gAllocation, sizeof(GtkAllocation))
-#define get_gallocation(c) ((GtkAllocation*)get_tobj(c, gAllocation))
-
-#define make_grequisiton(c) make_tobj(c, gRequisiton, sizeof(GtkRequisition))
-#define get_grequisiton(c) ((GtkRequisition*)get_tobj(c, gRequisiton))
-
-#define make_gdkrectangle(r) make_tobj(r, gdkRectangle, sizeof(GdkRectangle))
-#define get_gdkrectangle(r) ((GdkRectangle*)get_tobj(r, gdkRectangle))
-
-static void
-free_gdkcmap(cmap)
- GdkColormap *cmap;
-{
- gdk_colormap_unref(cmap);
-}
-
-static VALUE
-make_gdkcmap(cmap)
- GdkColormap *cmap;
-{
- gdk_colormap_ref(cmap);
- return Data_Wrap_Struct(gdkColormap, 0, free_gdkcmap, cmap);
-}
-
-static GdkColormap*
-get_gdkcmap(cmap)
- VALUE cmap;
-{
- GdkColormap *gcmap;
-
- if (NIL_P(cmap)) return NULL;
-
- if (!obj_is_kind_of(cmap, gdkColormap)) {
- TypeError("not a GdkColormap");
- }
- Data_Get_Struct(cmap, GdkColormap, gcmap);
-
- return gcmap;
-}
-
-static VALUE
-make_gdkvisual(visual)
- GdkVisual *visual;
-{
- return Data_Wrap_Struct(gdkVisual, 0, 0, visual);
-}
-
-static GdkVisual*
-get_gdkvisual(visual)
- VALUE visual;
-{
- GdkVisual *gvisual;
-
- if (NIL_P(visual)) return NULL;
-
- if (!obj_is_kind_of(visual, gdkVisual)) {
- TypeError("not a GdkVisual");
- }
- Data_Get_Struct(visual, GdkVisual, gvisual);
-
- return gvisual;
-}
-
-static void
-free_gdkwindow(window)
- GdkWindow *window;
-{
- gdk_window_unref(window);
-}
-
-static VALUE
-make_gdkwindow(window)
- GdkWindow *window;
-{
- gdk_window_ref(window);
- return Data_Wrap_Struct(gdkWindow, 0, free_gdkwindow, window);
-}
-
-static GdkWindow*
-get_gdkwindow(window)
- VALUE window;
-{
- GdkWindow *gwindow;
-
- if (NIL_P(window)) return NULL;
-
- if (!obj_is_kind_of(window, gdkWindow)) {
- TypeError("not a GdkWindow");
- }
- Data_Get_Struct(window, GdkWindow, gwindow);
-
- return gwindow;
-}
-
-static void
-free_gdkpixmap(pixmap)
- GdkPixmap *pixmap;
-{
- gdk_pixmap_unref(pixmap);
-}
-
-static VALUE
-make_gdkpixmap(klass, pixmap)
- VALUE klass;
- GdkPixmap *pixmap;
-{
- gdk_pixmap_ref(pixmap);
- return Data_Wrap_Struct(klass, 0, free_gdkpixmap, pixmap);
-}
-
-static GdkPixmap*
-get_gdkpixmap(pixmap)
- VALUE pixmap;
-{
- GdkPixmap *gpixmap;
-
- if (NIL_P(pixmap)) return NULL;
-
- if (!obj_is_kind_of(pixmap, gdkPixmap)) {
- TypeError("not a GdkPixmap");
- }
- Data_Get_Struct(pixmap, GdkPixmap, gpixmap);
-
- return gpixmap;
-}
-
-static VALUE
-gdkpmap_s_new(self, win, w, h, depth)
- VALUE self, win, w, h, depth;
-{
- GdkPixmap *new;
- GdkWindow *window = get_gdkwindow(win);
-
- new = gdk_pixmap_new(window, NUM2INT(w), NUM2INT(h), NUM2INT(depth));
- return make_gdkpixmap(self, new);
-}
-
-static VALUE
-gdkpmap_create_from_data(self, win, data, w, h, depth, fg, bg)
- VALUE self, win, data, w, h, depth, fg, bg;
-{
- GdkPixmap *new;
- GdkWindow *window = get_gdkwindow(win);
-
- Check_Type(data, T_STRING);
- new = gdk_pixmap_create_from_data(window,
- RSTRING(data)->ptr,
- NUM2INT(w), NUM2INT(h),
- NUM2INT(depth),
- get_gdkcolor(fg),
- get_gdkcolor(bg));
- return make_gdkpixmap(self, new);
-}
-
-static VALUE
-gdkpmap_create_from_xpm(self, win, tcolor, fname)
- VALUE self, win, tcolor, fname;
-{
- GdkPixmap *new;
- GdkBitmap *mask;
- GdkWindow *window = get_gdkwindow(win);
-
- Check_Type(fname, T_STRING);
- new = gdk_pixmap_create_from_xpm(window, &mask,
- get_gdkcolor(tcolor),
- RSTRING(fname)->ptr);
- if (!new) {
- ArgError("Pixmap not created from %s", RSTRING(fname)->ptr);
- }
- return assoc_new(make_gdkpixmap(self, new),
- make_gdkpixmap(gdkBitmap, mask));
-}
-
-static VALUE
-gdkpmap_create_from_xpm_d(self, win, tcolor, data)
- VALUE self, win, tcolor, data;
-{
- GdkPixmap *new;
- GdkBitmap *mask;
- GdkWindow *window = get_gdkwindow(win);
- int i;
- gchar **buf;
-
- Check_Type(data, T_ARRAY);
- buf = ALLOCA_N(char*, RARRAY(data)->len);
- for (i=0; i<RARRAY(data)->len; i++) {
- Check_Type(RARRAY(data)->ptr[i], T_STRING);
- buf[i] = RSTRING(RARRAY(data)->ptr[i])->ptr;
- }
-
- new = gdk_pixmap_create_from_xpm_d(window, &mask,
- get_gdkcolor(tcolor),
- buf);
-
- return assoc_new(make_gdkpixmap(self, new),
- make_gdkpixmap(gdkBitmap, mask));
-}
-
-static VALUE
-gdkbmap_s_new(self, win, w, h)
- VALUE self, win, w, h;
-{
- GdkPixmap *new;
- GdkWindow *window = get_gdkwindow(win);
-
- new = gdk_pixmap_new(window, NUM2INT(w), NUM2INT(h), 1);
- return make_gdkpixmap(self, new);
-}
-
-static VALUE
-gdkbmap_create_from_data(self, win, data, w, h)
- VALUE self, win, data, w, h;
-{
- GdkBitmap *new;
- GdkWindow *window = get_gdkwindow(win);
-
- Check_Type(data, T_STRING);
- new = gdk_bitmap_create_from_data(window,
- RSTRING(data)->ptr,
- NUM2INT(w), NUM2INT(h));
- return make_gdkpixmap(self, (GdkPixmap*)new);
-}
-
-static void
-free_gdkimage(image)
- GdkImage *image;
-{
- gdk_image_destroy(image);
-}
-
-static VALUE
-make_gdkimage(image)
- GdkImage *image;
-{
- return Data_Wrap_Struct(gdkImage, 0, free_gdkimage, image);
-}
-
-static GdkImage*
-get_gdkimage(image)
- VALUE image;
-{
- GdkImage *gimage;
-
- if (NIL_P(image)) return NULL;
-
- if (!obj_is_instance_of(image, gdkImage)) {
- TypeError("not a GdkImage");
- }
- Data_Get_Struct(image, GdkImage, gimage);
-
- return gimage;
-}
-
-static void
-free_gdkevent(event)
- GdkEvent *event;
-{
- gdk_event_free(event);
-}
-
-static VALUE
-make_gdkevent(event)
- GdkEvent *event;
-{
- event = gdk_event_copy(event);
- return Data_Wrap_Struct(gdkEvent, 0, free_gdkevent, event);
-}
-
-static GdkEvent*
-get_gdkevent(event)
- VALUE event;
-{
- GdkEvent *gevent;
-
- if (NIL_P(event)) return NULL;
-
- if (!obj_is_instance_of(event, gdkEvent)) {
- TypeError("not a GdkEvent");
- }
- Data_Get_Struct(event, GdkEvent, gevent);
-
- return gevent;
-}
-
-static VALUE
-glist2ary(list)
- GList *list;
-{
- VALUE ary = ary_new();
-
- while (list) {
- ary_push(ary, get_value_from_gobject(GTK_OBJECT(list->data)));
- list = list->next;
- }
-
- return ary;
-}
-
-static GList*
-ary2glist(ary)
- VALUE ary;
-{
- int i;
- GList *glist = NULL;
-
- Check_Type(ary, T_ARRAY);
- for (i=0; i<RARRAY(ary)->len; i++) {
- glist = g_list_prepend(glist,get_widget(RARRAY(ary)->ptr[i]));
- }
-
- return g_list_reverse(glist);
-}
-
-static GSList*
-ary2gslist(ary)
- VALUE ary;
-{
- int i;
- GSList *glist = NULL;
-
- if (NIL_P(ary)) return NULL;
- Check_Type(ary, T_ARRAY);
- for (i=0; i<RARRAY(ary)->len; i++) {
- glist = g_slist_append(glist,get_widget(RARRAY(ary)->ptr[i]));
- }
-
- return glist;
-}
-
-static VALUE
-gslist2ary(list)
- GSList *list;
-{
- VALUE ary = ary_new();
-
- while (list) {
- ary_push(ary, get_value_from_gobject(GTK_OBJECT(list->data)));
- list = list->next;
- }
-
- return ary;
-}
-
-static VALUE
-gobj_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- Fail("can't instantiate class %s", rb_class2name(self));
-}
-
-static VALUE
-gobj_smethod_added(self, id)
- VALUE self, id;
-{
- GtkObject *obj = get_gobject(self);
- char *name = rb_id2name(NUM2INT(id));
-
-
- if (gtk_signal_lookup(name, GTK_OBJECT_TYPE(obj))) {
- VALUE handler = assoc_new(Qnil, id);
-
- add_relative(self, handler);
- gtk_signal_connect_interp(obj, name,
- exec_callback, (gpointer)handler,
- NULL, 0);
- }
- return Qnil;
-}
-
-static VALUE
-gobj_destroy(self)
- VALUE self;
-{
- printf("a\n");
- gtk_object_destroy(get_gobject(self));
- printf("b\n");
- clear_gobject(self);
- return Qnil;
-}
-
-static VALUE
-gobj_set_flags(self, flags)
- VALUE self, flags;
-{
- GtkObject *object = get_gobject(self);
- GTK_OBJECT_SET_FLAGS(object, NUM2INT(flags));
- return self;
-}
-
-static VALUE
-gobj_unset_flags(self, flags)
- VALUE self, flags;
-{
- GtkObject *object = get_gobject(self);
- GTK_OBJECT_UNSET_FLAGS(object, NUM2INT(flags));
- return self;
-}
-
-static VALUE
-gobj_sig_connect(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE sig, handler;
- GtkWidget *widget = get_widget(self);
- ID id = 0;
- int n;
-
- rb_scan_args(argc, argv, "11", &sig, &handler);
- Check_Type(sig, T_STRING);
- if (NIL_P(handler) && iterator_p()) {
- handler = f_lambda();
- id = rb_intern(RSTRING(sig)->ptr);
- }
- handler = assoc_new(handler, INT2NUM(id));
- add_relative(self, handler);
- n = gtk_signal_connect_interp(GTK_OBJECT(widget), RSTRING(sig)->ptr,
- exec_callback, (gpointer)handler,
- NULL, 0);
-
- return INT2FIX(n);
-}
-
-static VALUE
-gobj_sig_connect_after(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE sig, handler;
- GtkWidget *widget = get_widget(self);
- ID id = 0;
- int n;
-
- rb_scan_args(argc, argv, "11", &sig, &handler);
- Check_Type(sig, T_STRING);
- if (NIL_P(handler) && iterator_p()) {
- handler = f_lambda();
- id = rb_intern(RSTRING(sig)->ptr);
- }
- add_relative(self, handler);
- n = gtk_signal_connect_interp(GTK_OBJECT(widget), RSTRING(sig)->ptr,
- exec_callback, (gpointer)handler,
- NULL, 1);
-
- return INT2FIX(n);
-}
-
-static VALUE
-cont_bwidth(self, width)
- VALUE self, width;
-{
- GtkWidget *widget = get_widget(self);
- gtk_container_border_width(GTK_CONTAINER(widget), NUM2INT(width));
- return self;
-}
-
-static VALUE
-cont_add(self, other)
- VALUE self, other;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_container_add(GTK_CONTAINER(widget), get_widget(other));
- return self;
-}
-
-static VALUE
-cont_disable_resize(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_container_disable_resize(GTK_CONTAINER(widget));
- return self;
-}
-
-static VALUE
-cont_enable_resize(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_container_enable_resize(GTK_CONTAINER(widget));
- return self;
-}
-
-static VALUE
-cont_block_resize(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_container_block_resize(GTK_CONTAINER(widget));
- return self;
-}
-
-static VALUE
-cont_unblock_resize(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_container_unblock_resize(GTK_CONTAINER(widget));
- return self;
-}
-
-static VALUE
-cont_need_resize(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_container_need_resize(GTK_CONTAINER(widget));
- return self;
-}
-
-static VALUE
-cont_foreach(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE callback;
- GtkWidget *widget = get_widget(self);
-
- rb_scan_args(argc, argv, "01", &callback);
- if (NIL_P(callback)) {
- callback = f_lambda();
- }
- gtk_container_foreach(GTK_CONTAINER(widget),
- exec_callback, (gpointer)callback);
- return self;
-}
-
-static void
-yield_callback(widget)
- GtkWidget *widget;
-{
- rb_yield(get_value_from_gobject(GTK_OBJECT(widget)));
-}
-
-static VALUE
-cont_each(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_container_foreach(GTK_CONTAINER(widget),
- yield_callback, 0);
- return self;
-}
-
-static VALUE
-cont_focus(self, direction)
- VALUE self, direction;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_container_focus(GTK_CONTAINER(widget),
- (GtkDirectionType)NUM2INT(direction));
- return self;
-}
-
-static void
-cont_children_callback(widget, data)
- GtkWidget *widget;
- gpointer data;
-{
- VALUE ary = (VALUE)data;
-
- ary_push(ary, get_value_from_gobject(GTK_OBJECT(widget)));
-}
-
-static VALUE
-cont_children(self, direction)
- VALUE self, direction;
-{
- GtkWidget *widget = get_widget(self);
- VALUE ary = ary_new();
-
- gtk_container_foreach(GTK_CONTAINER(widget),
- cont_children_callback,
- (gpointer)ary);
- return ary;
-}
-
-static VALUE
-align_s_new(self, xalign, yalign, xscale, yscale)
- VALUE self, xalign, yalign, xscale, yscale;
-{
- return make_widget(self, gtk_alignment_new(NUM2DBL(xalign),
- NUM2DBL(yalign),
- NUM2DBL(xscale),
- NUM2DBL(yscale)));
-}
-
-static VALUE
-align_set(self, xalign, yalign, xscale, yscale)
- VALUE self, xalign, yalign, xscale, yscale;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_alignment_set(GTK_ALIGNMENT(widget),
- NUM2DBL(xalign), NUM2DBL(yalign),
- NUM2DBL(xscale), NUM2DBL(yscale));
- return self;
-}
-
-static VALUE
-misc_set_align(self, xalign, yalign)
- VALUE self, xalign, yalign;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_misc_set_alignment(GTK_MISC(widget),
- NUM2DBL(xalign), NUM2DBL(yalign));
- return self;
-}
-
-static VALUE
-misc_set_padding(self, xpad, ypad)
- VALUE self, xpad, ypad;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_misc_set_padding(GTK_MISC(widget),
- NUM2DBL(xpad), NUM2DBL(ypad));
- return self;
-}
-
-static VALUE
-arrow_s_new(self, arrow_t, shadow_t)
- VALUE self, arrow_t, shadow_t;
-{
- return make_widget(self, gtk_arrow_new((GtkArrowType)NUM2INT(arrow_t),
- (GtkShadowType)NUM2INT(shadow_t)));
-}
-
-static VALUE
-arrow_set(self, arrow_t, shadow_t)
- VALUE self, arrow_t, shadow_t;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_arrow_set(GTK_ARROW(widget),
- (GtkArrowType)NUM2INT(arrow_t),
- (GtkShadowType)NUM2INT(shadow_t));
- return self;
-}
-
-static VALUE
-frame_s_new(self, label)
- VALUE self, label;
-{
- return make_widget(self, gtk_frame_new(get_cstring(label)));
-}
-
-static VALUE
-frame_set_label(self, label)
- VALUE self, label;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_frame_set_label(GTK_FRAME(widget), get_cstring(label));
- return self;
-}
-
-static VALUE
-frame_set_label_align(self, xalign, yalign)
- VALUE self, xalign, yalign;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_frame_set_label_align(GTK_FRAME(widget),
- NUM2DBL(xalign),
- NUM2DBL(yalign));
-
- return self;
-}
-
-static VALUE
-frame_set_shadow_type(self, type)
- VALUE self, type;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_frame_set_shadow_type(GTK_FRAME(widget),
- (GtkShadowType)NUM2INT(type));
- return self;
-}
-
-static VALUE
-aframe_s_new(self, label, xalign, yalign, ratio, obey_child)
- VALUE self, label, xalign, yalign, ratio, obey_child;
-{
- return make_widget(self, gtk_aspect_frame_new(get_cstring(label),
- NUM2DBL(xalign),
- NUM2DBL(yalign),
- NUM2DBL(ratio),
- RTEST(obey_child)));
-}
-
-static VALUE
-aframe_set(self, xalign, yalign, ratio, obey_child)
- VALUE self, xalign, yalign, ratio, obey_child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_aspect_frame_set(GTK_ASPECT_FRAME(widget),
- NUM2DBL(xalign), NUM2DBL(yalign),
- NUM2DBL(ratio), RTEST(obey_child));
- return self;
-}
-
-static VALUE
-adj_s_new(self, value, lower, upper, step_inc, page_inc, page_size)
- VALUE self, value, lower, upper, step_inc, page_inc, page_size;
-{
- return make_widget(self, gtk_adjustment_new(NUM2DBL(value),
- NUM2DBL(lower),
- NUM2DBL(upper),
- NUM2DBL(step_inc),
- NUM2DBL(page_inc),
- NUM2DBL(page_size)));
-}
-
-static VALUE
-widget_destroy(self)
- VALUE self;
-{
- gtk_widget_destroy(get_widget(self));
- clear_gobject(self);
-
- return Qnil;
-}
-
-static VALUE
-widget_show(self)
- VALUE self;
-{
- gtk_widget_show(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_show_all(self)
- VALUE self;
-{
- gtk_widget_show_all(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_hide(self)
- VALUE self;
-{
- gtk_widget_hide(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_hide_all(self)
- VALUE self;
-{
- gtk_widget_hide_all(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_map(self)
- VALUE self;
-{
- gtk_widget_map(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_unmap(self)
- VALUE self;
-{
- gtk_widget_unmap(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_realize(self)
- VALUE self;
-{
- gtk_widget_realize(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_unrealize(self)
- VALUE self;
-{
- gtk_widget_unrealize(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_queue_draw(self)
- VALUE self;
-{
- gtk_widget_queue_draw(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_queue_resize(self)
- VALUE self;
-{
- gtk_widget_queue_resize(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_draw(self, rect)
- VALUE self, rect;
-{
- gtk_widget_draw(get_widget(self), get_gdkrectangle(rect));
- return self;
-}
-
-static VALUE
-widget_draw_focus(self)
- VALUE self;
-{
- gtk_widget_draw_focus(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_draw_default(self)
- VALUE self;
-{
- gtk_widget_draw_default(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_draw_children(self)
- VALUE self;
-{
- gtk_widget_draw_children(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_size_request(self, req)
- VALUE self, req;
-{
- gtk_widget_size_request(get_widget(self), get_grequisiton(req));
- return self;
-}
-
-static VALUE
-widget_size_allocate(self, alloc)
- VALUE self, alloc;
-{
- gtk_widget_size_allocate(get_widget(self), get_gallocation(alloc));
- return self;
-}
-
-static VALUE
-widget_inst_accel(self, accel, sig, key, mod)
- VALUE self, accel, sig, key, mod;
-{
- gtk_widget_install_accelerator(get_widget(self),
- get_gtkacceltbl(accel),
- get_cstring(sig),
- NUM2INT(key),
- (guint8)NUM2INT(mod));
- return self;
-}
-
-static VALUE
-widget_rm_accel(self, accel, sig)
- VALUE self, accel, sig;
-{
- gtk_widget_remove_accelerator(get_widget(self),
- get_gtkacceltbl(accel),
- get_cstring(sig));
- return self;
-}
-
-static VALUE
-widget_event(self, event)
- VALUE self, event;
-{
- int n = gtk_widget_event(get_widget(self), get_gdkevent(event));
- return NUM2INT(n);
-}
-
-static VALUE
-widget_activate(self)
- VALUE self;
-{
- gtk_widget_activate(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_grab_focus(self)
- VALUE self;
-{
- gtk_widget_grab_focus(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_grab_default(self)
- VALUE self;
-{
- gtk_widget_grab_default(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_restore_state(self)
- VALUE self;
-{
- gtk_widget_restore_state(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_visible(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- if (GTK_WIDGET_VISIBLE(widget))
- return TRUE;
- return FALSE;
-}
-
-static VALUE
-widget_reparent(self, parent)
- VALUE self, parent;
-{
- gtk_widget_reparent(get_widget(self), get_widget(parent));
- return self;
-}
-
-static VALUE
-widget_popup(self, x, y)
- VALUE self, x, y;
-{
- gtk_widget_popup(get_widget(self), NUM2INT(x), NUM2INT(y));
- return self;
-}
-
-static VALUE
-widget_intersect(self, area, intersect)
- VALUE self, area, intersect;
-{
- int n = gtk_widget_intersect(get_widget(self),
- get_gdkrectangle(area),
- get_gdkrectangle(intersect));
- return NUM2INT(n);
-}
-
-static VALUE
-widget_basic(self)
- VALUE self;
-{
- int n = gtk_widget_basic(get_widget(self));
- return NUM2INT(n);
-}
-
-static VALUE
-widget_set_state(self, state)
- VALUE self, state;
-{
- gtk_widget_set_state(get_widget(self), (GtkStateType)NUM2INT(state));
- return self;
-}
-
-static VALUE
-widget_set_style(self, style)
- VALUE self, style;
-{
- gtk_widget_set_style(get_widget(self),
- get_gstyle(style));
- return self;
-}
-
-static VALUE
-widget_set_parent(self, parent)
- VALUE self, parent;
-{
- gtk_widget_set_parent(get_widget(self), get_widget(parent));
- return self;
-}
-
-static VALUE
-widget_set_name(self, name)
- VALUE self, name;
-{
- gtk_widget_set_name(get_widget(self), get_cstring(name));
- return self;
-}
-
-static VALUE
-widget_get_name(self)
- VALUE self;
-{
- char *name = gtk_widget_get_name(get_widget(self));
-
- return str_new2(name);
-}
-
-static VALUE
-widget_set_sensitive(self, sensitive)
- VALUE self, sensitive;
-{
- gtk_widget_set_sensitive(get_widget(self), RTEST(sensitive));
- return self;
-}
-
-static VALUE
-widget_set_uposition(self, x, y)
- VALUE self, x, y;
-{
- gtk_widget_set_uposition(get_widget(self), NUM2INT(x), NUM2INT(y));
- return self;
-}
-
-static VALUE
-widget_set_usize(self, w, h)
- VALUE self, w, h;
-{
- gtk_widget_set_usize(get_widget(self), NUM2INT(w), NUM2INT(h));
- return self;
-}
-
-static VALUE
-widget_set_events(self, events)
- VALUE self, events;
-{
- gtk_widget_set_events(get_widget(self), NUM2INT(events));
- return self;
-}
-
-static VALUE
-widget_set_eevents(self, mode)
- VALUE self, mode;
-{
- gtk_widget_set_extension_events(get_widget(self),
- (GdkExtensionMode)NUM2INT(mode));
- return self;
-}
-
-static VALUE
-widget_unparent(self)
- VALUE self;
-{
- gtk_widget_unparent(get_widget(self));
- return self;
-}
-
-static VALUE
-widget_window(self)
- VALUE self;
-{
- return make_gdkwindow(get_widget(self)->window);
-}
-
-static VALUE
-widget_get_toplevel(self)
- VALUE self;
-{
- return get_value_from_gobject(gtk_widget_get_toplevel(get_widget(self)));
-}
-
-static VALUE
-widget_get_ancestor(self, type)
- VALUE self, type;
-{
- GtkWidget *widget = get_widget(self);
-#if 0
- if (obj_is_kind_of(type, cClass)) {
- }
-#endif
- widget = gtk_widget_get_ancestor(widget, NUM2INT(type));
-
- return get_value_from_gobject(widget);
-}
-
-static VALUE
-widget_get_colormap(self)
- VALUE self;
-{
- GdkColormap *cmap = gtk_widget_get_colormap(get_widget(self));
-
- return make_gdkcmap(cmap);
-}
-
-static VALUE
-widget_get_visual(self)
- VALUE self;
-{
- GdkVisual *v = gtk_widget_get_visual(get_widget(self));
-
- return make_gdkvisual(v);
-}
-
-static VALUE
-widget_get_style(self)
- VALUE self;
-{
- GtkStyle *s = gtk_widget_get_style(get_widget(self));
-
- return make_gstyle(s);
-}
-
-static VALUE
-widget_get_pointer(self)
- VALUE self;
-{
- int x, y;
-
- gtk_widget_get_pointer(get_widget(self), &x, &y);
- return assoc_new(INT2FIX(x), INT2FIX(y));
-}
-
-static VALUE
-widget_is_ancestor(self, ancestor)
- VALUE self, ancestor;
-{
- if (gtk_widget_is_ancestor(get_widget(self), get_widget(ancestor))) {
- return TRUE;
- }
- return FALSE;
-}
-
-static VALUE
-widget_is_child(self, child)
- VALUE self, child;
-{
- if (gtk_widget_is_child(get_widget(self), get_widget(child))) {
- return TRUE;
- }
- return FALSE;
-}
-
-static VALUE
-widget_get_events(self)
- VALUE self;
-{
- int n = gtk_widget_get_events(get_widget(self));
- return NUM2INT(n);
-}
-
-static VALUE
-widget_get_eevents(self)
- VALUE self;
-{
- GdkExtensionMode m;
- m = gtk_widget_get_extension_events(get_widget(self));
- return NUM2INT((int)m);
-}
-
-static VALUE
-widget_push_cmap(self, cmap)
- VALUE self, cmap;
-{
- gtk_widget_push_colormap(get_gdkcmap(cmap));
- return Qnil;
-}
-
-static VALUE
-widget_push_visual(self, visual)
- VALUE self, visual;
-{
- gtk_widget_push_visual(get_gdkvisual(visual));
- return make_gdkcmap(visual);
-}
-
-static VALUE
-widget_push_style(self, style)
- VALUE self, style;
-{
- gtk_widget_push_style(get_gstyle(style));
- return Qnil;
-}
-
-static VALUE
-widget_pop_cmap(self, cmap)
- VALUE self, cmap;
-{
- gtk_widget_pop_colormap();
- return Qnil;
-}
-
-static VALUE
-widget_pop_visual(self, visual)
- VALUE self, visual;
-{
- gtk_widget_pop_visual();
- return Qnil;
-}
-
-static VALUE
-widget_pop_style(self, style)
- VALUE self, style;
-{
- gtk_widget_pop_style();
- return Qnil;
-}
-
-static VALUE
-widget_set_default_cmap(self, cmap)
- VALUE self, cmap;
-{
- gtk_widget_set_default_colormap(get_gdkcmap(cmap));
- return Qnil;
-}
-
-static VALUE
-widget_set_default_visual(self, visual)
- VALUE self, visual;
-{
- gtk_widget_set_default_visual(get_gdkvisual(visual));
- return make_gdkcmap(visual);
-}
-
-static VALUE
-widget_set_default_style(self, style)
- VALUE self, style;
-{
- gtk_widget_set_default_style(get_gstyle(style));
- return Qnil;
-}
-
-static VALUE
-widget_get_default_cmap(self)
- VALUE self;
-{
- GdkColormap *cmap = gtk_widget_get_default_colormap();
-
- return make_gdkcmap(cmap);
-}
-
-static VALUE
-widget_get_default_visual(self)
- VALUE self;
-{
- GdkVisual *v = gtk_widget_get_default_visual();
-
- return make_gdkvisual(v);
-}
-
-static VALUE
-widget_get_default_style(self)
- VALUE self;
-{
- GtkStyle *s = gtk_widget_get_default_style();
-
- return make_gstyle(s);
-}
-
-static VALUE
-widget_propagate_default_style(self)
- VALUE self;
-{
- gtk_widget_propagate_default_style();
- return Qnil;
-}
-
-static VALUE
-bbox_get_child_size_default(self)
- VALUE self;
-{
- int min_width, max_width;
-
- gtk_button_box_get_child_size_default(&min_width, &max_width);
-
- return assoc_new(INT2FIX(min_width), INT2FIX(max_width));
-}
-
-static VALUE
-bbox_get_child_ipadding_default(self)
- VALUE self;
-{
- int ipad_x, ipad_y;
-
- gtk_button_box_get_child_ipadding_default(&ipad_x, &ipad_y);
- return assoc_new(INT2FIX(ipad_x), INT2FIX(ipad_y));
-}
-
-static VALUE
-bbox_set_child_size_default(self, min_width, max_width)
- VALUE self, min_width, max_width;
-{
- gtk_button_box_set_child_size_default(NUM2INT(min_width),
- NUM2INT(max_width));
- return Qnil;
-}
-
-static VALUE
-bbox_set_child_ipadding_default(self, ipad_x, ipad_y)
- VALUE self, ipad_x, ipad_y;
-{
- gtk_button_box_set_child_ipadding_default(NUM2INT(ipad_x),
- NUM2INT(ipad_y));
- return Qnil;
-}
-
-static VALUE
-bbox_get_spacing(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- int n = gtk_button_box_get_spacing(GTK_BUTTON_BOX(widget));
-
- return INT2FIX(n);
-}
-
-static VALUE
-bbox_get_layout(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- int n = gtk_button_box_get_layout(GTK_BUTTON_BOX(widget));
-
- return INT2FIX(n);
-}
-
-static VALUE
-bbox_get_child_size(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- int min_width, max_width;
-
- gtk_button_box_get_child_size(GTK_BUTTON_BOX(widget),
- &min_width, &max_width);
- return assoc_new(INT2FIX(min_width), INT2FIX(max_width));
-}
-
-static VALUE
-bbox_get_child_ipadding(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- int ipad_x, ipad_y;
-
- gtk_button_box_get_child_ipadding(GTK_BUTTON_BOX(widget),
- &ipad_x, &ipad_y);
- return assoc_new(INT2FIX(ipad_x), INT2FIX(ipad_y));
-}
-
-static VALUE
-bbox_set_spacing(self, spacing)
- VALUE self, spacing;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_button_box_set_spacing(GTK_BUTTON_BOX(widget),
- NUM2INT(spacing));
- return self;
-}
-
-static VALUE
-bbox_set_layout(self, layout)
- VALUE self, layout;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_button_box_set_layout(GTK_BUTTON_BOX(widget),
- NUM2INT(layout));
- return self;
-}
-
-static VALUE
-bbox_set_child_size(self, min_width, max_width)
- VALUE self, min_width, max_width;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_button_box_set_child_size(GTK_BUTTON_BOX(widget),
- NUM2INT(min_width),
- NUM2INT(max_width));
- return self;
-}
-
-static VALUE
-bbox_set_child_ipadding(self, ipad_x, ipad_y)
- VALUE self, ipad_x, ipad_y;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_button_box_set_child_ipadding(GTK_BUTTON_BOX(widget),
- NUM2INT(ipad_x),
- NUM2INT(ipad_y));
- return self;
-}
-
-static VALUE
-clist_s_new(self, titles)
- VALUE self, titles;
-{
- char **buf;
- int i, len;
-
- Check_Type(titles, T_ARRAY);
- len = RARRAY(titles)->len;
- buf = ALLOCA_N(char*, len);
- for (i=0; i<len; i++) {
- Check_Type(RARRAY(titles)->ptr[i], T_STRING);
- buf[i] = RSTRING(RARRAY(titles)->ptr[i])->ptr;
- }
- return make_widget(self, gtk_clist_new(len, buf));
-}
-
-static VALUE
-clist_set_border(self, border)
- VALUE self, border;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_border(GTK_CLIST(widget), (GtkShadowType)NUM2INT(border));
- return self;
-}
-
-static VALUE
-clist_set_sel_mode(self, mode)
- VALUE self, mode;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_selection_mode(GTK_CLIST(widget),
- (GtkSelectionMode)NUM2INT(mode));
- return self;
-}
-
-static VALUE
-clist_set_policy(self, vpolicy, hpolicy)
- VALUE self, vpolicy, hpolicy;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_policy(GTK_CLIST(widget),
- (GtkPolicyType)NUM2INT(vpolicy),
- (GtkPolicyType)NUM2INT(hpolicy));
- return self;
-}
-
-static VALUE
-clist_freeze(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_freeze(GTK_CLIST(widget));
- return self;
-}
-
-static VALUE
-clist_thaw(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_thaw(GTK_CLIST(widget));
- return self;
-}
-
-static VALUE
-clist_set_col_title(self, col, title)
- VALUE self, col, title;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_column_title(GTK_CLIST(widget),
- NUM2INT(col),
- get_cstring(title));
- return self;
-}
-
-static VALUE
-clist_set_col_wigdet(self, col, win)
- VALUE self, col, win;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_column_widget(GTK_CLIST(widget),
- NUM2INT(col),
- get_widget(win));
- return self;
-}
-
-static VALUE
-clist_set_col_just(self, col, just)
- VALUE self, col, just;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_column_justification(GTK_CLIST(widget),
- NUM2INT(col),
- (GtkJustification)NUM2INT(just));
- return self;
-}
-
-static VALUE
-clist_set_col_width(self, col, width)
- VALUE self, col, width;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_column_width(GTK_CLIST(widget),
- NUM2INT(col), NUM2INT(width));
- return self;
-}
-
-static VALUE
-clist_set_row_height(self, height)
- VALUE self, height;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_row_height(GTK_CLIST(widget), NUM2INT(height));
- return self;
-}
-
-static VALUE
-clist_moveto(self, row, col, row_align, col_align)
- VALUE self, row, col, row_align, col_align;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_moveto(GTK_CLIST(widget),
- NUM2INT(row), NUM2INT(col),
- NUM2INT(row_align), NUM2INT(col_align));
- return self;
-}
-
-static VALUE
-clist_set_text(self, row, col, text)
- VALUE self, row, col, text;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_text(GTK_CLIST(widget),
- NUM2INT(row), NUM2INT(col),
- get_cstring(text));
- return self;
-}
-
-static VALUE
-clist_set_pixmap(self, row, col, pixmap, mask)
- VALUE self, row, col, pixmap, mask;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_pixmap(GTK_CLIST(widget),
- NUM2INT(row), NUM2INT(col),
- get_gdkpixmap(pixmap),
- (GdkBitmap*)get_gdkpixmap(mask));
- return self;
-}
-
-static VALUE
-clist_set_pixtext(self, row, col, text, spacing, pixmap, mask)
- VALUE self, row, col, text, spacing, pixmap, mask;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_pixtext(GTK_CLIST(widget),
- NUM2INT(row), NUM2INT(col),
- get_cstring(text),
- NUM2INT(spacing),
- get_gdkpixmap(pixmap),
- (GdkBitmap*)get_gdkpixmap(mask));
- return self;
-}
-
-static VALUE
-clist_set_foreground(self, row, color)
- VALUE self, row, color;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_foreground(GTK_CLIST(widget),
- NUM2INT(row), get_gdkcolor(color));
- return self;
-}
-
-static VALUE
-clist_set_background(self, row, color)
- VALUE self, row, color;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_background(GTK_CLIST(widget),
- NUM2INT(row), get_gdkcolor(color));
- return self;
-}
-
-static VALUE
-clist_set_shift(self, row, col, verticle, horizontal)
- VALUE self, row, col, verticle, horizontal;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_set_shift(GTK_CLIST(widget),
- NUM2INT(row), NUM2INT(col),
- NUM2INT(verticle), NUM2INT(horizontal));
- return self;
-}
-
-static VALUE
-clist_append(self, text)
- VALUE self, text;
-{
- GtkWidget *widget = get_widget(self);
- char **buf;
- int i, len;
-
- Check_Type(text, T_ARRAY);
- len = GTK_CLIST(widget)->columns;
- if (len > RARRAY(text)->len) {
- ArgError("text too short");
- }
- buf = ALLOCA_N(char*, len);
- for (i=0; i<len; i++) {
- Check_Type(RARRAY(text)->ptr[i], T_STRING);
- buf[i] = RSTRING(RARRAY(text)->ptr[i])->ptr;
- }
- i = gtk_clist_append(GTK_CLIST(widget), buf);
- return INT2FIX(i);
-}
-
-static VALUE
-clist_insert(self, row, text)
- VALUE self, row, text;
-{
- GtkWidget *widget = get_widget(self);
- char **buf;
- int i, len;
-
- Check_Type(text, T_ARRAY);
- len = GTK_CLIST(widget)->columns;
- if (len > RARRAY(text)->len) {
- ArgError("text too short");
- }
- buf = ALLOCA_N(char*, len);
- for (i=0; i<len; i++) {
- Check_Type(RARRAY(text)->ptr[i], T_STRING);
- buf[i] = RSTRING(RARRAY(text)->ptr[i])->ptr;
- }
- gtk_clist_insert(GTK_CLIST(widget), NUM2INT(row), buf);
- return self;
-}
-
-static VALUE
-clist_remove(self, row)
- VALUE self, row;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_remove(GTK_CLIST(widget), NUM2INT(row));
- return self;
-}
-
-static VALUE
-clist_set_row_data(self, row, data)
- VALUE self, row, data;
-{
- GtkWidget *widget = get_widget(self);
-
- add_relative(self, data);
- gtk_clist_set_row_data(GTK_CLIST(widget), NUM2INT(row), (gpointer)data);
- return self;
-}
-
-static VALUE
-clist_get_row_data(self, row)
- VALUE self, row;
-{
- GtkWidget *widget = get_widget(self);
-
- return (VALUE)gtk_clist_get_row_data(GTK_CLIST(widget), NUM2INT(row));
-}
-
-static VALUE
-clist_select_row(self, row, col)
- VALUE self, row, col;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_select_row(GTK_CLIST(widget), NUM2INT(row), NUM2INT(col));
- return self;
-}
-
-static VALUE
-clist_unselect_row(self, row, col)
- VALUE self, row, col;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_unselect_row(GTK_CLIST(widget), NUM2INT(row), NUM2INT(col));
- return self;
-}
-
-static VALUE
-clist_clear(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_clist_clear(GTK_CLIST(widget));
- return self;
-}
-
-static VALUE
-gwin_s_new(self, type)
- VALUE self, type;
-{
- return make_widget(self, gtk_window_new(NUM2INT(type)));
-}
-
-static VALUE
-gwin_set_policy(self, shrink, grow, auto_shrink)
- VALUE self, shrink, grow, auto_shrink;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_window_set_policy(GTK_WINDOW(widget),
- RTEST(shrink), RTEST(grow), RTEST(auto_shrink));
- return self;
-}
-
-static VALUE
-gwin_set_title(self, title)
- VALUE self, title;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_window_set_title(GTK_WINDOW(widget), get_cstring(title));
- return self;
-}
-
-static VALUE
-gwin_position(self, pos)
- VALUE self, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_window_position(GTK_WINDOW(widget),
- (GtkWindowPosition)NUM2INT(pos));
-
- return self;
-}
-
-static VALUE
-gwin_set_wmclass(self, wmclass1, wmclass2)
- VALUE self, wmclass1, wmclass2;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_window_set_wmclass(GTK_WINDOW(widget),
- get_cstring(wmclass1),
- get_cstring(wmclass2));
- return self;
-}
-
-static VALUE
-gwin_set_focus(self, win)
- VALUE self, win;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_window_set_focus(GTK_WINDOW(widget), get_widget(win));
- return self;
-}
-
-static VALUE
-gwin_set_default(self, win)
- VALUE self, win;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_window_set_default(GTK_WINDOW(widget), get_widget(win));
- return self;
-}
-
-static VALUE
-gwin_add_accel(self, accel)
- VALUE self, accel;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_window_add_accelerator_table(GTK_WINDOW(widget),
- get_gtkacceltbl(accel));
- return self;
-}
-
-static VALUE
-gwin_rm_accel(self, accel)
- VALUE self, accel;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_window_remove_accelerator_table(GTK_WINDOW(widget),
- get_gtkacceltbl(accel));
- return self;
-}
-
-static VALUE
-dialog_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_dialog_new());
-}
-
-static VALUE
-fsel_s_new(self, title)
- VALUE self, title;
-{
- return make_widget(self, gtk_file_selection_new(get_cstring(title)));
-}
-
-static VALUE
-fsel_set_fname(self, fname)
- VALUE self, fname;
-{
- GtkWidget *widget = get_widget(self);
-
- Check_Type(fname, T_STRING);
- gtk_file_selection_set_filename(GTK_FILE_SELECTION(widget),
- RSTRING(fname)->ptr);
-
- return self;
-}
-
-static VALUE
-fsel_get_fname(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- gchar *fname;
-
- fname = gtk_file_selection_get_filename(GTK_FILE_SELECTION(widget));
-
- return str_new2(fname);
-}
-
-static VALUE
-fsel_ok_button(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- VALUE b = rb_iv_get(self, "ok_button");
-
- if (NIL_P(b)) {
- GtkWidget *w = GTK_FILE_SELECTION(widget)->ok_button;
- b = make_widget(gButton, w);
- rb_iv_set(self, "ok_button", b);
- }
-
- return b;
-}
-
-static VALUE
-fsel_cancel_button(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- VALUE b = rb_iv_get(self, "cancel_button");
-
- if (NIL_P(b)) {
- GtkWidget *w = GTK_FILE_SELECTION(widget)->cancel_button;
- b = make_widget(gButton, w);
- rb_iv_set(self, "cancel_button", b);
- }
-
- return b;
-}
-
-static VALUE
-fsel_help_button(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- VALUE b = rb_iv_get(self, "help_button");
-
- if (NIL_P(b)) {
- GtkWidget *w = GTK_FILE_SELECTION(widget)->help_button;
- b = make_widget(gButton, w);
- rb_iv_set(self, "help_button", b);
- }
-
- return b;
-}
-
-static VALUE
-label_s_new(self, label)
- VALUE self, label;
-{
- return make_widget(self, gtk_label_new(get_cstring(label)));
-}
-
-static VALUE
-list_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_list_new());
-}
-
-static VALUE
-list_set_sel_mode(self, mode)
- VALUE self, mode;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_list_set_selection_mode(GTK_LIST(widget),
- (GtkSelectionMode)NUM2INT(mode));
- return self;
-}
-
-static VALUE
-list_sel_mode(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- return INT2FIX(GTK_LIST(widget)->selection_mode);
-}
-
-static VALUE
-list_selection(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- return glist2ary(GTK_LIST(widget)->selection);
-}
-
-static VALUE
-list_insert_items(self, items, pos)
- VALUE self, items, pos;
-{
- GtkWidget *widget = get_widget(self);
- GList *glist;
-
- glist = ary2glist(items);
-
- gtk_list_insert_items(GTK_LIST(widget), glist, NUM2INT(pos));
- g_list_free(glist);
-
- return self;
-}
-
-static VALUE
-list_append_items(self, items)
- VALUE self, items;
-{
- GtkWidget *widget = get_widget(self);
- GList *glist;
-
- glist = ary2glist(items);
-
- gtk_list_append_items(GTK_LIST(widget), glist);
- g_list_free(glist);
-
- return self;
-}
-
-static VALUE
-list_prepend_items(self, items)
- VALUE self, items;
-{
- GtkWidget *widget = get_widget(self);
- GList *glist;
-
- glist = ary2glist(items);
- gtk_list_prepend_items(GTK_LIST(widget), glist);
- g_list_free(glist);
-
- return self;
-}
-
-static VALUE
-list_remove_items(self, items)
- VALUE self, items;
-{
- GtkWidget *widget = get_widget(self);
- GList *glist;
-
- glist = ary2glist(items);
- gtk_list_remove_items(GTK_LIST(widget), glist);
- g_list_free(glist);
-
- return self;
-}
-
-static VALUE
-list_clear_items(self, start, end)
- VALUE self, start, end;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_list_clear_items(GTK_LIST(widget), NUM2INT(start), NUM2INT(end));
- return self;
-}
-
-static VALUE
-list_select_item(self, pos)
- VALUE self, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_list_select_item(GTK_LIST(widget), NUM2INT(pos));
- return self;
-}
-
-static VALUE
-list_unselect_item(self, pos)
- VALUE self, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_list_unselect_item(GTK_LIST(widget), NUM2INT(pos));
- return self;
-}
-
-static VALUE
-list_select_child(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_list_select_child(GTK_LIST(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-list_unselect_child(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_list_unselect_child(GTK_LIST(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-list_child_position(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
- gint pos;
-
- pos = gtk_list_child_position(GTK_LIST(widget), get_widget(child));
- return INT2FIX(pos);
-}
-
-static VALUE
-item_select(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_item_select(GTK_ITEM(widget));
- return self;
-}
-
-static VALUE
-item_deselect(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_item_deselect(GTK_ITEM(widget));
- return self;
-}
-
-static VALUE
-item_toggle(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_item_toggle(GTK_ITEM(widget));
- return self;
-}
-
-static VALUE
-litem_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE label;
- GtkWidget *widget;
-
- if (rb_scan_args(argc, argv, "01", &label) == 1) {
- widget = gtk_list_item_new_with_label(get_cstring(label));
- }
- else {
- widget = gtk_list_item_new();
- }
-
- return make_widget(self, widget);
-}
-
-static VALUE
-mshell_append(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_shell_append(GTK_MENU_SHELL(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-mshell_prepend(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_shell_prepend(GTK_MENU_SHELL(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-mshell_insert(self, child, pos)
- VALUE self, child, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_shell_insert(GTK_MENU_SHELL(widget), get_widget(child),
- NUM2INT(pos));
- return self;
-}
-
-static VALUE
-mshell_deactivate(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_shell_deactivate(GTK_MENU_SHELL(widget));
- return self;
-}
-
-static VALUE
-menu_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_menu_new());
-}
-
-static VALUE
-menu_append(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_append(GTK_MENU(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-menu_prepend(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_prepend(GTK_MENU(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-menu_insert(self, child, pos)
- VALUE self, child, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_insert(GTK_MENU(widget), get_widget(child), NUM2INT(pos));
- return self;
-}
-
-static void
-menu_pos_func(menu, x, y, data)
- GtkMenu *menu;
- gint x, y;
- gpointer data;
-{
- VALUE m = get_value_from_gobject(GTK_OBJECT(menu));
-
- rb_funcall((VALUE)data, 3, m, INT2FIX(x), INT2FIX(y));
-}
-
-static VALUE
-menu_popup(self, pshell, pitem, func, button, activate_time)
- VALUE self, pshell, pitem, func, button, activate_time;
-{
- GtkWidget *widget = get_widget(self);
- GtkMenuPositionFunc pfunc = NULL;
- gpointer data = NULL;
-
- if (!NIL_P(func)) {
- pfunc = menu_pos_func;
- data = (gpointer)func;
- add_relative(self, func);
- }
- gtk_menu_popup(GTK_MENU(widget),
- get_widget(pshell), get_widget(pitem),
- pfunc,
- data,
- NUM2INT(button),
- NUM2INT(activate_time));
- return self;
-}
-
-static VALUE
-menu_popdown(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_popdown(GTK_MENU(widget));
- return self;
-}
-
-static VALUE
-menu_get_active(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- GtkWidget *mitem = gtk_menu_get_active(GTK_MENU(widget));
-
- return make_widget(gMenuItem, mitem);
-}
-
-static VALUE
-menu_set_active(self, active)
- VALUE self, active;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_set_active(GTK_MENU(widget), NUM2INT(active));
- return self;
-}
-
-static VALUE
-menu_set_acceltbl(self, table)
- VALUE self, table;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_set_accelerator_table(GTK_MENU(widget),
- get_gtkacceltbl(table));
- return self;
-}
-
-static VALUE
-mbar_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_menu_bar_new());
-}
-
-static VALUE
-mbar_append(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_bar_append(GTK_MENU_BAR(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-mbar_prepend(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_bar_prepend(GTK_MENU_BAR(widget), get_widget(child));
- return self;
-}
-static VALUE
-mbar_insert(self, child, pos)
- VALUE self, child, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_bar_insert(GTK_MENU_BAR(widget),
- get_widget(child), NUM2INT(pos));
- return self;
-}
-
-static VALUE
-mitem_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
-{
- VALUE label;
- GtkWidget *widget;
-
- if (rb_scan_args(argc, argv, "01", &label) == 1) {
- widget = gtk_menu_item_new_with_label(get_cstring(label));
- }
- else {
- widget = gtk_menu_item_new();
- }
-
- return make_widget(self, widget);
-}
-
-static VALUE
-mitem_set_submenu(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_item_set_submenu(GTK_MENU_ITEM(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-mitem_set_placement(self, place)
- VALUE self, place;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_item_set_placement(GTK_MENU_ITEM(widget),
- (GtkSubmenuPlacement)NUM2INT(place));
- return self;
-}
-
-static VALUE
-mitem_accelerator_size(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_item_accelerator_size(GTK_MENU_ITEM(widget));
- return self;
-}
-
-static VALUE
-mitem_accelerator_text(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- char buf[1024]; /* enough? */
-
- gtk_menu_item_accelerator_text(GTK_MENU_ITEM(widget), buf);
- return str_new2(buf);
-}
-
-static VALUE
-mitem_configure(self, show_toggle, show_submenu)
- VALUE self, show_toggle, show_submenu;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_item_configure(GTK_MENU_ITEM(widget),
- NUM2INT(show_toggle),
- NUM2INT(show_submenu));
- return self;
-}
-
-static VALUE
-mitem_select(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_item_select(GTK_MENU_ITEM(widget));
- return self;
-}
-
-static VALUE
-mitem_deselect(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_item_deselect(GTK_MENU_ITEM(widget));
- return self;
-}
-
-static VALUE
-mitem_activate(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_item_activate(GTK_MENU_ITEM(widget));
- return self;
-}
-
-static VALUE
-mitem_right_justify(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_menu_item_right_justify(GTK_MENU_ITEM(widget));
- return self;
-}
-
-static VALUE
-cmitem_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
-{
- VALUE label;
- GtkWidget *widget;
-
- if (rb_scan_args(argc, argv, "01", &label) == 1) {
- widget = gtk_check_menu_item_new_with_label(get_cstring(label));
- }
- else {
- widget = gtk_check_menu_item_new();
- }
-
- return make_widget(self, widget);
-}
-
-static VALUE
-cmitem_set_state(self, state)
- VALUE self, state;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_check_menu_item_set_state(GTK_CHECK_MENU_ITEM(widget),
- NUM2INT(state));
- return self;
-}
-
-static VALUE
-cmitem_set_show_toggle(self, always)
- VALUE self, always;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_check_menu_item_set_show_toggle(GTK_CHECK_MENU_ITEM(widget),
- (gboolean)RTEST(always));
- return self;
-}
-
-static VALUE
-cmitem_toggled(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_check_menu_item_toggled(GTK_CHECK_MENU_ITEM(widget));
- return self;
-}
-
-static VALUE
-rmitem_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
-{
- VALUE arg1, arg2;
- GtkWidget *widget;
- GSList *list = NULL;
- char *label = NULL;
-
- if (rb_scan_args(argc, argv, "02", &arg1, &arg2) == 1 &&
- TYPE(arg1) == T_STRING) {
- label = RSTRING(arg1)->ptr;
- }
- else {
- if (!NIL_P(arg2)) {
- Check_Type(arg2, T_STRING);
- label = RSTRING(arg2)->ptr;
- }
- if (obj_is_kind_of(arg1, gRMenuItem)) {
- GtkWidget *b = get_widget(arg1);
- list = GTK_RADIO_MENU_ITEM(b)->group;
- }
- else {
- list = ary2gslist(arg1);
- }
- }
- if (label) {
- widget = gtk_radio_menu_item_new_with_label(list, label);
- }
- else {
- widget = gtk_radio_menu_item_new(list);
- }
- return make_widget(self, widget);
-}
-
-static VALUE
-rmitem_group(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- return gslist2ary(gtk_radio_menu_item_group(GTK_RADIO_MENU_ITEM(widget)));
-}
-
-static VALUE
-note_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_notebook_new());
-}
-
-static VALUE
-note_append_page(self, child, label)
- VALUE self, child, label;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_notebook_append_page(GTK_NOTEBOOK(widget),
- get_widget(child),
- get_widget(label));
- return self;
-}
-
-static VALUE
-note_prepend_page(self, child, label)
- VALUE self, child, label;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_notebook_prepend_page(GTK_NOTEBOOK(widget),
- get_widget(child),
- get_widget(label));
- return self;
-}
-
-static VALUE
-note_insert_page(self, child, label, pos)
- VALUE self, child, label, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_notebook_insert_page(GTK_NOTEBOOK(widget),
- get_widget(child),
- get_widget(label),
- NUM2INT(pos));
- return self;
-}
-
-static VALUE
-note_remove_page(self, pos)
- VALUE self, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_notebook_remove_page(GTK_NOTEBOOK(widget), NUM2INT(pos));
- return self;
-}
-
-static VALUE
-note_set_page(self, pos)
- VALUE self, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_notebook_set_page(GTK_NOTEBOOK(widget), NUM2INT(pos));
- return self;
-}
-
-static VALUE
-note_cur_page(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- return INT2FIX(GTK_NOTEBOOK(widget)->cur_page);
-}
-
-static VALUE
-note_next_page(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_notebook_next_page(GTK_NOTEBOOK(widget));
- return self;
-}
-
-static VALUE
-note_prev_page(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_notebook_prev_page(GTK_NOTEBOOK(widget));
- return self;
-}
-
-static VALUE
-note_set_tab_pos(self, pos)
- VALUE self, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_notebook_set_tab_pos(GTK_NOTEBOOK(widget), NUM2INT(pos));
- return self;
-}
-
-static VALUE
-note_tab_pos(self, pos)
- VALUE self, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- return INT2FIX(GTK_NOTEBOOK(widget)->tab_pos);
-}
-
-static VALUE
-note_set_show_tabs(self, show_tabs)
- VALUE self, show_tabs;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_notebook_set_tab_pos(GTK_NOTEBOOK(widget), RTEST(show_tabs));
- return self;
-}
-
-static VALUE
-note_show_tabs(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- return GTK_NOTEBOOK(widget)->show_tabs?TRUE:FALSE;
-}
-
-static VALUE
-note_set_show_border(self, show_border)
- VALUE self, show_border;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_notebook_set_tab_pos(GTK_NOTEBOOK(widget), RTEST(show_border));
- return self;
-}
-
-static VALUE
-note_show_border(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- return GTK_NOTEBOOK(widget)->show_border?TRUE:FALSE;
-}
-
-static VALUE
-omenu_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_option_menu_new());
-}
-
-static VALUE
-omenu_set_menu(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- rb_iv_set(self, "option_menu", child);
- gtk_option_menu_set_menu(GTK_OPTION_MENU(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-omenu_get_menu(self)
- VALUE self;
-{
- return rb_iv_get(self, "option_menu");
-}
-
-static VALUE
-omenu_remove_menu(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_option_menu_remove_menu(GTK_OPTION_MENU(widget));
- return self;
-}
-
-static VALUE
-omenu_set_history(self, index)
- VALUE self, index;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_option_menu_set_history(GTK_OPTION_MENU(widget), NUM2INT(index));
- return self;
-}
-
-static VALUE
-image_s_new(self, val, mask)
- VALUE self, val, mask;
-{
- return make_widget(self, gtk_image_new(get_gdkimage(val),
- (GdkBitmap*)get_gdkpixmap(mask)));
-}
-
-static VALUE
-image_set(self, val, mask)
- VALUE self, val, mask;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_image_set(GTK_IMAGE(widget), get_gdkimage(val), get_gdkpixmap(mask));
- return self;
-}
-
-static VALUE
-image_get(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- GdkImage *val;
- GdkBitmap *mask;
-
- gtk_image_get(GTK_IMAGE(widget), &val, &mask);
-
- return assoc_new(make_gdkimage(self, val),
- make_gdkpixmap(self, mask));
-}
-
-static VALUE
-preview_s_new(self, type)
- VALUE self, type;
-{
- return make_widget(self, gtk_preview_new((GtkPreviewType)NUM2INT(type)));
-}
-
-
-static VALUE
-preview_size(self, w, h)
- VALUE self, w, h;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_preview_size(GTK_PREVIEW(widget), NUM2INT(w), NUM2INT(h));
- return self;
-}
-
-#if 0
- rb_define_method(gPixmap, "put", preview_size, 8);
- rb_define_method(gPixmap, "put_row", preview_size, 5);
- rb_define_method(gPixmap, "draw_row", preview_size, 4);
-#endif
-
-static VALUE
-preview_set_expand(self, expand)
- VALUE self, expand;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_preview_set_expand(GTK_PREVIEW(widget), NUM2INT(expand));
- return self;
-}
-
-static VALUE
-preview_set_gamma(self, gamma)
- VALUE self, gamma;
-{
- gtk_preview_set_gamma(NUM2DBL(gamma));
- return Qnil;
-}
-
-static VALUE
-preview_set_color_cube(self, nred, ngreen, nblue, ngray)
- VALUE self, nred, ngreen, nblue, ngray;
-{
- gtk_preview_set_color_cube(NUM2INT(nred),
- NUM2INT(ngreen),
- NUM2INT(nblue),
- NUM2INT(ngray));
- return Qnil;
-}
-
-static VALUE
-preview_set_install_cmap(self, cmap)
- VALUE self, cmap;
-{
- gtk_preview_set_install_cmap(NUM2INT(cmap));
- return Qnil;
-}
-
-static VALUE
-preview_set_reserved(self, nreserved)
- VALUE self, nreserved;
-{
- gtk_preview_set_reserved(NUM2INT(nreserved));
- return Qnil;
-}
-
-static VALUE
-preview_get_visual(self)
- VALUE self;
-{
- GdkVisual *v = gtk_preview_get_visual();
- return make_gdkvisual(v);
-}
-
-static VALUE
-preview_get_cmap(self)
- VALUE self;
-{
- GdkColormap *c = gtk_preview_get_cmap();
- return make_gdkcmap(c);
-}
-
-static VALUE
-preview_get_info(self)
- VALUE self;
-{
- GtkPreviewInfo *i = gtk_preview_get_info();
- return make_gtkprevinfo(i);
-}
-
-static VALUE
-pbar_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_progress_bar_new());
-}
-
-static VALUE
-pbar_update(self, percentage)
- VALUE self, percentage;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_progress_bar_update(GTK_PROGRESS_BAR(widget),
- NUM2DBL(percentage));
- return self;
-}
-
-static VALUE
-scwin_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE arg1, arg2;
- GtkAdjustment *h_adj = NULL;
- GtkAdjustment *v_adj = NULL;
-
- rb_scan_args(argc, argv, "02", &arg1, &arg2);
- if (!NIL_P(arg1)) h_adj = (GtkAdjustment*)get_gobject(arg1);
- if (!NIL_P(arg2)) v_adj = (GtkAdjustment*)get_gobject(arg2);
-
- return make_widget(self, gtk_scrolled_window_new(h_adj, v_adj));
-}
-
-static VALUE
-scwin_set_policy(self, hpolicy, vpolicy)
- VALUE self, hpolicy, vpolicy;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(widget),
- (GtkPolicyType)NUM2INT(hpolicy),
- (GtkPolicyType)NUM2INT(vpolicy));
- return self;
-}
-
-
-static VALUE
-tbl_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
-{
- VALUE row, col, homogeneous;
-
- rb_scan_args(argc, argv, "21", &row, &col, &homogeneous);
- return make_widget(self, gtk_table_new(NUM2INT(row),
- NUM2INT(col),
- RTEST(homogeneous)));
-}
-
-static VALUE
-tbl_attach(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- VALUE child, left, right, top, bottom;
- VALUE arg0, arg1, arg2, arg3;
- int xopt, yopt, xspc, yspc;
-
- xopt = yopt = GTK_EXPAND | GTK_FILL;
- xspc = yspc = 0;
- rb_scan_args(argc, argv, "54",
- &child, &left, &right, &top, &bottom,
- &arg0, &arg1, &arg2, &arg3);
- if (!NIL_P(arg0)) xopt = NUM2INT(arg0);
- if (!NIL_P(arg1)) yopt = NUM2INT(arg1);
- if (!NIL_P(arg2)) xspc = NUM2INT(arg2);
- if (!NIL_P(arg3)) yspc = NUM2INT(arg3);
-
- gtk_table_attach(GTK_TABLE(widget),
- get_widget(child),
- NUM2INT(left),NUM2INT(right),
- NUM2INT(top),NUM2INT(bottom),
- xopt, yopt, xspc, yspc);
-
- return self;
-}
-
-static VALUE
-tbl_set_row_spacing(self, row, spc)
- VALUE self, row, spc;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_table_set_row_spacing(GTK_TABLE(widget), NUM2INT(row), NUM2INT(spc));
- return self;
-}
-
-static VALUE
-tbl_set_col_spacing(self, col, spc)
- VALUE self, col, spc;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_table_set_col_spacing(GTK_TABLE(widget), NUM2INT(col), NUM2INT(spc));
- return self;
-}
-
-static VALUE
-tbl_set_row_spacings(self, spc)
- VALUE self, spc;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_table_set_row_spacings(GTK_TABLE(widget), NUM2INT(spc));
- return self;
-}
-
-static VALUE
-tbl_set_col_spacings(self, spc)
- VALUE self, spc;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_table_set_col_spacings(GTK_TABLE(widget), NUM2INT(spc));
- return self;
-}
-
-static VALUE
-txt_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE arg1, arg2;
- GtkAdjustment *h_adj = NULL;
- GtkAdjustment *v_adj = NULL;
-
- rb_scan_args(argc, argv, "02", &arg1, &arg2);
- if (!NIL_P(arg1)) h_adj = (GtkAdjustment*)get_gobject(arg1);
- if (!NIL_P(arg2)) v_adj = (GtkAdjustment*)get_gobject(arg2);
-
- return make_widget(self, gtk_text_new(h_adj, v_adj));
-}
-
-static VALUE
-txt_set_editable(self, editable)
- VALUE self, editable;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_text_set_editable(GTK_TEXT(widget), RTEST(editable));
- return self;
-}
-
-static VALUE
-txt_set_adjustment(self, h_adj, v_adj)
- VALUE self, h_adj, v_adj;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_text_set_adjustments(GTK_TEXT(widget),
- (GtkAdjustment*)get_gobject(h_adj),
- (GtkAdjustment*)get_gobject(v_adj));
-
- return self;
-}
-
-static VALUE
-txt_set_point(self, index)
- VALUE self, index;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_text_set_point(GTK_TEXT(widget), NUM2INT(index));
- return self;
-}
-
-static VALUE
-txt_get_point(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- int index = gtk_text_get_point(GTK_TEXT(widget));
-
- return INT2FIX(index);
-}
-
-static VALUE
-txt_get_length(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- int len = gtk_text_get_length(GTK_TEXT(widget));
-
- return INT2FIX(len);
-}
-
-static VALUE
-txt_freeze(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_text_freeze(GTK_TEXT(widget));
- return self;
-}
-
-static VALUE
-txt_thaw(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_text_thaw(GTK_TEXT(widget));
- return self;
-}
-
-static VALUE
-txt_insert(self, font, fore, back, str)
- VALUE self, font, fore, back, str;
-{
- GtkWidget *widget = get_widget(self);
-
- Check_Type(str, T_STRING);
- gtk_text_insert(GTK_TEXT(widget),
- get_gdkfont(font),
- get_gdkcolor(fore),
- get_gdkcolor(back),
- RSTRING(str)->ptr,
- RSTRING(str)->len);
-
- return self;
-}
-
-static VALUE
-txt_backward_delete(self, nchars)
- VALUE self, nchars;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_text_backward_delete(GTK_TEXT(widget), NUM2INT(nchars));
- return self;
-}
-
-static VALUE
-txt_forward_delete(self, nchars)
- VALUE self, nchars;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_text_forward_delete(GTK_TEXT(widget), NUM2INT(nchars));
- return self;
-}
-
-static VALUE
-tbar_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE arg1, arg2;
- GtkOrientation orientation = GTK_ORIENTATION_HORIZONTAL;
- GtkToolbarStyle style = GTK_TOOLBAR_BOTH;
-
- rb_scan_args(argc, argv, "02", &arg1, &arg2);
- if (!NIL_P(arg1)) orientation = (GtkOrientation)NUM2INT(arg1);
- if (!NIL_P(arg2)) style = (GtkToolbarStyle)NUM2INT(arg2);
-
- return make_widget(self, gtk_toolbar_new(orientation, style));
-}
-
-static VALUE
-tbar_append_item(self, text, ttext, icon, func)
- VALUE self, text, ttext, icon, func;
-{
- GtkWidget *widget = get_widget(self);
- GtkObject *pixmap = get_gobject(icon);
-
- if (NIL_P(func)) {
- func = f_lambda();
- }
- gtk_toolbar_append_item(GTK_TOOLBAR(widget),
- get_cstring(text),
- get_cstring(ttext),
- GTK_PIXMAP(pixmap),
- exec_callback,
- (gpointer)ary_new3(1, func));
- return self;
-}
-
-static VALUE
-tbar_prepend_item(self, text, ttext, icon, func)
- VALUE self, text, ttext, icon, func;
-{
- GtkWidget *widget = get_widget(self);
- GtkObject *pixmap = get_gobject(icon);
-
- if (NIL_P(func)) {
- func = f_lambda();
- }
- gtk_toolbar_prepend_item(GTK_TOOLBAR(widget),
- get_cstring(text),
- get_cstring(ttext),
- GTK_PIXMAP(pixmap),
- exec_callback,
- (gpointer)ary_new3(1, func));
- return self;
-}
-
-static VALUE
-tbar_insert_item(self, text, ttext, icon, func, pos)
- VALUE self, text, ttext, icon, func, pos;
-{
- GtkWidget *widget = get_widget(self);
- GtkObject *pixmap = get_gobject(icon);
-
- if (NIL_P(func)) {
- func = f_lambda();
- }
- gtk_toolbar_insert_item(GTK_TOOLBAR(widget),
- get_cstring(text),
- get_cstring(ttext),
- GTK_PIXMAP(pixmap),
- exec_callback,
- (gpointer)ary_new3(1, func),
- NUM2INT(pos));
- return self;
-}
-
-static VALUE
-tbar_append_space(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_toolbar_append_space(GTK_TOOLBAR(widget));
- return self;
-}
-
-static VALUE
-tbar_prepend_space(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_toolbar_prepend_space(GTK_TOOLBAR(widget));
- return self;
-}
-
-static VALUE
-tbar_insert_space(self, pos)
- VALUE self, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_toolbar_insert_space(GTK_TOOLBAR(widget), NUM2INT(pos));
- return self;
-}
-
-static VALUE
-tbar_set_orientation(self, orientation)
- VALUE self, orientation;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_toolbar_set_orientation(GTK_TOOLBAR(widget),
- (GtkOrientation)NUM2INT(orientation));
- return self;
-}
-
-static VALUE
-tbar_set_style(self, style)
- VALUE self, style;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_toolbar_set_style(GTK_TOOLBAR(widget),
- (GtkToolbarStyle)NUM2INT(style));
- return self;
-}
-
-static VALUE
-tbar_set_space_size(self, size)
- VALUE self, size;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_toolbar_set_space_size(GTK_TOOLBAR(widget), NUM2INT(size));
- return self;
-}
-
-static VALUE
-tbar_set_tooltips(self, enable)
- VALUE self, enable;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_toolbar_set_tooltips(GTK_TOOLBAR(widget), RTEST(enable));
- return self;
-}
-
-static VALUE
-ttips_s_new(self)
- VALUE self;
-{
- return make_ttips(self, gtk_tooltips_new());
-}
-
-static VALUE
-ttips_set_tips(self, win, text)
- VALUE self, win, text;
-{
- Check_Type(text, T_STRING);
- gtk_tooltips_set_tips(get_ttips(self),
- get_widget(win),
- RSTRING(text)->ptr);
-
- return self;
-}
-
-static VALUE
-ttips_set_delay(self, delay)
- VALUE self, delay;
-{
- gtk_tooltips_set_delay(get_ttips(self), NUM2INT(delay));
-
- return self;
-}
-
-static VALUE
-ttips_enable(self)
- VALUE self;
-{
- gtk_tooltips_enable(get_ttips(self));
- return self;
-}
-
-static VALUE
-ttips_disable(self)
- VALUE self;
-{
- gtk_tooltips_enable(get_ttips(self));
- return self;
-}
-
-static VALUE
-tree_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_tree_new());
-}
-
-static VALUE
-tree_append(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_tree_append(GTK_TREE(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-tree_prepend(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_tree_prepend(GTK_TREE(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-tree_insert(self, child, pos)
- VALUE self, child, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_tree_insert(GTK_TREE(widget), get_widget(child), NUM2INT(pos));
- return self;
-}
-
-static VALUE
-titem_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
-{
- VALUE label;
- GtkWidget *widget;
-
- if (rb_scan_args(argc, argv, "01", &label) == 1) {
- Check_Type(label, T_STRING);
- widget = gtk_tree_item_new_with_label(RSTRING(label)->ptr);
- }
- else {
- widget = gtk_tree_item_new();
- }
-
- return make_widget(self, widget);
-}
-
-static VALUE
-titem_set_subtree(self, subtree)
- VALUE self, subtree;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_tree_item_set_subtree(GTK_TREE_ITEM(widget), get_widget(subtree));
- return self;
-}
-
-static VALUE
-titem_select(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_tree_item_select(GTK_TREE_ITEM(widget));
- return self;
-}
-
-static VALUE
-titem_deselect(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_tree_item_deselect(GTK_TREE_ITEM(widget));
- return self;
-}
-
-static VALUE
-titem_expand(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_tree_item_expand(GTK_TREE_ITEM(widget));
- return self;
-}
-
-static VALUE
-titem_collapse(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_tree_item_collapse(GTK_TREE_ITEM(widget));
- return self;
-}
-
-static VALUE
-vport_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE arg1, arg2;
- GtkAdjustment *h_adj = NULL;
- GtkAdjustment *v_adj = NULL;
-
- rb_scan_args(argc, argv, "02", &arg1, &arg2);
- if (!NIL_P(arg1)) h_adj = (GtkAdjustment*)get_gobject(arg1);
- if (!NIL_P(arg2)) v_adj = (GtkAdjustment*)get_gobject(arg2);
-
- return make_widget(self, gtk_viewport_new(h_adj, v_adj));
-}
-
-static VALUE
-vport_get_hadj(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- GtkAdjustment *adj = gtk_viewport_get_hadjustment(GTK_VIEWPORT(widget));
-
- return make_gobject(gAdjustment, GTK_OBJECT(adj));
-}
-
-static VALUE
-vport_get_vadj(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- GtkAdjustment *adj = gtk_viewport_get_vadjustment(GTK_VIEWPORT(widget));
-
- return make_gobject(gAdjustment, GTK_OBJECT(adj));
-}
-
-static VALUE
-vport_set_vadj(self, adj)
- VALUE self, adj;
-{
- GtkWidget *widget = get_widget(self);
- GtkObject *adjustment = get_gobject(adj);
-
- gtk_viewport_set_vadjustment(GTK_VIEWPORT(widget),
- GTK_ADJUSTMENT(adj));
-
- return self;
-}
-
-static VALUE
-vport_set_hadj(self, adj)
- VALUE self, adj;
-{
- GtkWidget *widget = get_widget(self);
- GtkObject *adjustment = get_gobject(adj);
-
- gtk_viewport_set_hadjustment(GTK_VIEWPORT(widget),
- GTK_ADJUSTMENT(adj));
-
- return self;
-}
-
-static VALUE
-vport_set_shadow(self, type)
- VALUE self, type;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_viewport_set_shadow_type(GTK_VIEWPORT(widget),
- (GtkShadowType)NUM2INT(type));
-
- return self;
-}
-
-static VALUE
-button_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
-{
- VALUE label;
- GtkWidget *widget;
-
- if (rb_scan_args(argc, argv, "01", &label) == 1) {
- Check_Type(label, T_STRING);
- widget = gtk_button_new_with_label(RSTRING(label)->ptr);
- }
- else {
- widget = gtk_button_new();
- }
-
- return make_widget(self, widget);
-}
-
-static VALUE
-button_pressed(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_button_pressed(GTK_BUTTON(widget));
- return self;
-}
-
-static VALUE
-button_released(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_button_released(GTK_BUTTON(widget));
- return self;
-}
-
-static VALUE
-button_clicked(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_button_clicked(GTK_BUTTON(widget));
- return self;
-}
-
-static VALUE
-button_enter(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_button_enter(GTK_BUTTON(widget));
- return self;
-}
-
-static VALUE
-button_leave(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_button_leave(GTK_BUTTON(widget));
- return self;
-}
-
-static VALUE
-tbtn_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
-{
- VALUE label;
- GtkWidget *widget;
-
- if (rb_scan_args(argc, argv, "01", &label) == 1) {
- Check_Type(label, T_STRING);
- widget = gtk_toggle_button_new_with_label(RSTRING(label)->ptr);
- }
- else {
- widget = gtk_toggle_button_new();
- }
-
- return make_widget(self, widget);
-}
-
-static VALUE
-tbtn_set_mode(self, mode)
- VALUE self, mode;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_toggle_button_set_mode(GTK_TOGGLE_BUTTON(widget), NUM2INT(mode));
- return self;
-}
-
-static VALUE
-tbtn_set_state(self, state)
- VALUE self, state;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(widget), NUM2INT(state));
- return self;
-}
-
-static VALUE
-tbtn_toggled(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_toggle_button_toggled(GTK_TOGGLE_BUTTON(widget));
- return self;
-}
-
-static VALUE
-cbtn_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
-{
- VALUE label;
- GtkWidget *widget;
-
- if (rb_scan_args(argc, argv, "01", &label) == 1) {
- Check_Type(label, T_STRING);
- widget = gtk_check_button_new_with_label(RSTRING(label)->ptr);
- }
- else {
- widget = gtk_check_button_new();
- }
-
- return make_widget(self, widget);
-}
-
-static VALUE
-rbtn_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
-{
- VALUE arg1, arg2;
- GtkWidget *widget;
- GSList *list = NULL;
- char *label = NULL;
-
- if (rb_scan_args(argc, argv, "02", &arg1, &arg2) == 1 &&
- TYPE(arg1) == T_STRING) {
- label = RSTRING(arg1)->ptr;
- }
- else {
- if (!NIL_P(arg2)) {
- Check_Type(arg2, T_STRING);
- label = RSTRING(arg2)->ptr;
- }
- if (obj_is_kind_of(arg1, gRButton)) {
- GtkWidget *b = get_widget(arg1);
- list = GTK_RADIO_BUTTON(b)->group;
- }
- else {
- list = ary2gslist(arg1);
- }
- }
- if (label) {
- widget = gtk_radio_button_new_with_label(list, label);
- }
- else {
- widget = gtk_radio_button_new(list);
- }
- return make_widget(self, widget);
-}
-
-static VALUE
-rbtn_group(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- return gslist2ary(gtk_radio_button_group(GTK_RADIO_BUTTON(widget)));
-}
-
-static void
-box_pack_start_or_end(argc, argv, self, start)
- int argc;
- VALUE *argv;
- VALUE self;
- int start;
-{
- VALUE arg0, arg1, arg2, arg3;
- gint expand, fill, padding;
- GtkWidget *widget, *child;
-
- expand = fill = TRUE; padding = 0;
- switch (rb_scan_args(argc, argv, "13", &arg0, &arg1, &arg2, &arg3)) {
- case 4:
- padding = NUM2INT(arg3);
- case 3:
- fill = RTEST(arg2);
- case 2:
- expand = RTEST(arg1);
- default:
- child = get_widget(arg0);
- break;
- }
- widget = get_widget(self);
-
- if (start)
- gtk_box_pack_start(GTK_BOX(widget), child, expand, fill, padding);
- else
- gtk_box_pack_end(GTK_BOX(widget), child, expand, fill, padding);
-}
-
-static VALUE
-box_pack_start(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- box_pack_start_or_end(argc, argv, self, 1);
- return self;
-}
-
-static VALUE
-box_pack_end(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- box_pack_start_or_end(argc, argv, self, 0);
- return self;
-}
-
-static VALUE
-vbox_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE homogeneous, spacing;
- GtkWidget *widget;
-
- rb_scan_args(argc, argv, "02", &homogeneous, &spacing);
- widget = gtk_vbox_new(RTEST(homogeneous), NUM2INT(spacing));
-
- return make_widget(self, widget);
-}
-
-static VALUE
-colorsel_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_color_selection_new());
-}
-
-static VALUE
-colorsel_set_update_policy(self, policy)
- VALUE self, policy;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_color_selection_set_update_policy(GTK_COLOR_SELECTION(widget),
- (GtkUpdateType)NUM2INT(policy));
- return self;
-}
-
-static VALUE
-colorsel_set_opacity(self, opacity)
- VALUE self, opacity;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_color_selection_set_opacity(GTK_COLOR_SELECTION(widget),
- RTEST(opacity));
- return self;
-}
-
-static VALUE
-colorsel_set_color(self, color)
- VALUE self, color;
-{
- GtkWidget *widget = get_widget(self);
- double buf[3];
-
- Check_Type(color, T_ARRAY);
- if (RARRAY(color)->len < 3) {
- ArgError("color array too small");
- }
- buf[0] = NUM2DBL(RARRAY(color)->ptr[0]);
- buf[1] = NUM2DBL(RARRAY(color)->ptr[1]);
- buf[2] = NUM2DBL(RARRAY(color)->ptr[2]);
-
- gtk_color_selection_set_color(GTK_COLOR_SELECTION(widget), buf);
- return self;
-}
-
-static VALUE
-colorsel_get_color(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- double buf[3];
- VALUE ary;
-
- gtk_color_selection_get_color(GTK_COLOR_SELECTION(widget), buf);
- ary = ary_new2(3);
- ary_push(ary, NUM2DBL(buf[0]));
- ary_push(ary, NUM2DBL(buf[1]));
- ary_push(ary, NUM2DBL(buf[2]));
- return ary;
-}
-
-static VALUE
-cdialog_s_new(self, title)
- VALUE self;
-{
- char *t;
-
- Check_Type(title, T_STRING);
- t = RSTRING(title)->ptr;
- return make_widget(self, gtk_color_selection_dialog_new(t));
-}
-
-static VALUE
-pixmap_s_new(self, val, mask)
- VALUE self, val, mask;
-{
- return make_widget(self, gtk_pixmap_new(get_gdkpixmap(val),
- get_gdkpixmap(mask)));
-}
-
-static VALUE
-pixmap_set(self, val, mask)
- VALUE self, val, mask;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_pixmap_set(GTK_PIXMAP(widget),
- get_gdkpixmap(val), get_gdkpixmap(mask));
- return self;
-}
-
-static VALUE
-pixmap_get(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- GdkPixmap *val;
- GdkBitmap *mask;
-
- gtk_pixmap_get(GTK_PIXMAP(widget), &val, &mask);
-
- return assoc_new(make_gdkpixmap(self, val),
- make_gdkpixmap(self, mask));
-}
-
-static VALUE
-darea_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_drawing_area_new());
-}
-
-static VALUE
-darea_size(self, w, h)
- VALUE self, w, h;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_drawing_area_size(GTK_DRAWING_AREA(widget), NUM2INT(w), NUM2INT(h));
- return self;
-}
-
-static VALUE
-entry_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_entry_new());
-}
-
-static VALUE
-entry_set_text(self, text)
- VALUE self, text;
-{
- GtkWidget *widget = get_widget(self);
-
- Check_Type(text, T_STRING);
- gtk_entry_set_text(GTK_ENTRY(widget), RSTRING(text)->ptr);
-
- return self;
-}
-
-static VALUE
-eventbox_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_event_box_new());
-}
-
-static VALUE
-fixed_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_fixed_new());
-}
-
-static VALUE
-fixed_put(self, win, x, y)
- VALUE self, win, x, y;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_fixed_put(GTK_FIXED(widget), get_widget(win), NUM2INT(x), NUM2INT(y));
- return self;
-}
-
-static VALUE
-fixed_move(self, win, x, y)
- VALUE self, win, x, y;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_fixed_move(GTK_FIXED(widget), get_widget(win), NUM2INT(x), NUM2INT(y));
- return self;
-}
-
-static VALUE
-gamma_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_gamma_curve_new());
-}
-
-static VALUE
-gamma_gamma(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- return float_new(GTK_GAMMA_CURVE(widget)->gamma);
-}
-
-static VALUE
-hbbox_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_hbutton_box_new());
-}
-
-static VALUE
-hbbox_get_spacing_default(self)
- VALUE self;
-{
- int n = gtk_hbutton_box_get_spacing_default();
-
- return INT2FIX(n);
-}
-
-static VALUE
-hbbox_get_layout_default(self)
- VALUE self;
-{
- int n = gtk_hbutton_box_get_layout_default();
-
- return INT2FIX(n);
-}
-
-static VALUE
-hbbox_set_spacing_default(self, spacing)
- VALUE self, spacing;
-{
- gtk_hbutton_box_set_spacing_default(NUM2INT(spacing));
- return Qnil;
-}
-
-static VALUE
-hbbox_set_layout_default(self, layout)
- VALUE self, layout;
-{
- gtk_hbutton_box_set_layout_default(NUM2INT(layout));
- return Qnil;
-}
-
-static VALUE
-vbbox_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_vbutton_box_new());
-}
-
-static VALUE
-vbbox_get_spacing_default(self)
- VALUE self;
-{
- int n = gtk_vbutton_box_get_spacing_default();
-
- return INT2FIX(n);
-}
-
-static VALUE
-vbbox_get_layout_default(self)
- VALUE self;
-{
- int n = gtk_vbutton_box_get_layout_default();
-
- return INT2FIX(n);
-}
-
-static VALUE
-vbbox_set_spacing_default(self, spacing)
- VALUE self, spacing;
-{
- gtk_vbutton_box_set_spacing_default(NUM2INT(spacing));
- return Qnil;
-}
-
-static VALUE
-vbbox_set_layout_default(self, layout)
- VALUE self, layout;
-{
- gtk_vbutton_box_set_layout_default(NUM2INT(layout));
- return Qnil;
-}
-
-static VALUE
-hbox_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE homogeneous, spacing;
- GtkWidget *widget;
-
- rb_scan_args(argc, argv, "02", &homogeneous, &spacing);
- widget = gtk_hbox_new(RTEST(homogeneous), NUM2INT(spacing));
-
- return make_widget(self, widget);
-}
-
-static VALUE
-paned_add1(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_paned_add1(GTK_PANED(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-paned_add2(self, child)
- VALUE self, child;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_paned_add2(GTK_PANED(widget), get_widget(child));
- return self;
-}
-
-static VALUE
-paned_handle_size(self, size)
- VALUE self, size;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_paned_handle_size(GTK_PANED(widget), NUM2INT(size));
- return self;
-}
-
-static VALUE
-paned_gutter_size(self, size)
- VALUE self, size;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_paned_gutter_size(GTK_PANED(widget), NUM2INT(size));
- return self;
-}
-
-static VALUE
-hpaned_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_hpaned_new());
-}
-
-static VALUE
-vpaned_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_vpaned_new());
-}
-
-static VALUE
-ruler_set_metric(self, metric)
- VALUE self, metric;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_ruler_set_metric(GTK_RULER(widget),
- (GtkMetricType)NUM2INT(metric));
-
- return self;
-}
-
-static VALUE
-ruler_set_range(self, lower, upper, position, max_size)
- VALUE self, lower, upper, position, max_size;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_ruler_set_range(GTK_RULER(widget),
- NUM2DBL(lower), NUM2DBL(upper),
- NUM2DBL(position), NUM2DBL(max_size));
-
- return self;
-}
-
-static VALUE
-ruler_draw_ticks(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_ruler_draw_ticks(GTK_RULER(widget));
- return self;
-}
-
-static VALUE
-ruler_draw_pos(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_ruler_draw_pos(GTK_RULER(widget));
- return self;
-}
-
-static VALUE
-hruler_s_new(self)
-{
- return make_widget(self, gtk_hruler_new());
-}
-
-static VALUE
-vruler_s_new(self)
-{
- return make_widget(self, gtk_vruler_new());
-}
-
-static VALUE
-range_get_adj(self)
-{
- GtkWidget *widget = get_widget(self);
- GtkAdjustment *adj = gtk_range_get_adjustment(GTK_RANGE(widget));
-
- return make_gobject(gAdjustment, GTK_OBJECT(adj));
-}
-
-static VALUE
-range_set_update_policy(self, policy)
- VALUE self, policy;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_set_update_policy(GTK_RANGE(widget),
- (GtkUpdateType)NUM2INT(policy));
- return self;
-}
-
-static VALUE
-range_set_adj(self, adj)
- VALUE self, adj;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_set_adjustment(GTK_RANGE(widget),
- (GtkAdjustment*)get_gobject(adj));
-
- return self;
-}
-
-static VALUE
-range_draw_bg(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_draw_background(GTK_RANGE(widget));
- return self;
-}
-
-static VALUE
-range_draw_trough(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_draw_trough(GTK_RANGE(widget));
- return self;
-}
-
-static VALUE
-range_draw_slider(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_draw_slider(GTK_RANGE(widget));
- return self;
-}
-
-static VALUE
-range_draw_step_forw(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_draw_step_forw(GTK_RANGE(widget));
- return self;
-}
-
-static VALUE
-range_draw_step_back(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_draw_step_back(GTK_RANGE(widget));
- return self;
-}
-
-static VALUE
-range_slider_update(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_slider_update(GTK_RANGE(widget));
- return self;
-}
-
-static VALUE
-range_trough_click(self, x, y)
- VALUE self, x, y;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_trough_click(GTK_RANGE(widget), NUM2INT(x), NUM2INT(y));
- return self;
-}
-
-static VALUE
-range_default_hslider_update(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_default_hslider_update(GTK_RANGE(widget));
- return self;
-}
-
-static VALUE
-range_default_vslider_update(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_default_vslider_update(GTK_RANGE(widget));
- return self;
-}
-
-static VALUE
-range_default_htrough_click(self, x, y)
- VALUE self, x, y;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_default_htrough_click(GTK_RANGE(widget),
- NUM2INT(x), NUM2INT(y));
- return self;
-}
-
-static VALUE
-range_default_vtrough_click(self, x, y)
- VALUE self, x, y;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_default_vtrough_click(GTK_RANGE(widget),
- NUM2INT(x), NUM2INT(y));
- return self;
-}
-
-static VALUE
-range_default_hmotion(self, xdelta, ydelta)
- VALUE self, xdelta, ydelta;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_default_hmotion(GTK_RANGE(widget),
- NUM2INT(xdelta), NUM2INT(ydelta));
- return self;
-}
-
-static VALUE
-range_default_vmotion(self, xdelta, ydelta)
- VALUE self, xdelta, ydelta;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_default_vmotion(GTK_RANGE(widget),
- NUM2INT(xdelta), NUM2INT(ydelta));
- return self;
-}
-
-static VALUE
-range_calc_value(self, pos)
- VALUE self, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_range_calc_value(GTK_RANGE(widget), NUM2INT(pos));
- return self;
-}
-
-static VALUE
-scale_set_digits(self, digits)
- VALUE self, digits;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_scale_set_digits(GTK_SCALE(widget), NUM2INT(digits));
- return self;
-}
-
-static VALUE
-scale_set_draw_value(self, draw_value)
- VALUE self, draw_value;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_scale_set_draw_value(GTK_SCALE(widget), NUM2INT(draw_value));
- return self;
-}
-
-static VALUE
-scale_set_value_pos(self, pos)
- VALUE self, pos;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_scale_set_value_pos(GTK_SCALE(widget),
- (GtkPositionType)NUM2INT(pos));
- return self;
-}
-
-static VALUE
-scale_value_width(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
- int i = gtk_scale_value_width(GTK_SCALE(widget));
-
- return INT2FIX(i);
-}
-
-static VALUE
-scale_draw_value(self)
- VALUE self;
-{
- GtkWidget *widget = get_widget(self);
-
- gtk_scale_draw_value(GTK_SCALE(widget));
- return self;
-}
-
-static VALUE
-hscale_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE arg1;
- GtkAdjustment *adj = NULL;
-
- rb_scan_args(argc, argv, "01", &arg1);
- if (!NIL_P(arg1)) adj = (GtkAdjustment*)get_gobject(arg1);
-
- return make_widget(self, gtk_hscale_new(adj));
-}
-
-static VALUE
-vscale_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE arg1;
- GtkAdjustment *adj = NULL;
-
- rb_scan_args(argc, argv, "01", &arg1);
- if (!NIL_P(arg1)) adj = (GtkAdjustment*)get_gobject(arg1);
-
- return make_widget(self, gtk_vscale_new(adj));
-}
-
-static VALUE
-hscrollbar_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE arg1;
- GtkAdjustment *adj = NULL;
-
- rb_scan_args(argc, argv, "01", &arg1);
- if (!NIL_P(arg1)) adj = (GtkAdjustment*)get_gobject(arg1);
-
- return make_widget(self, gtk_hscrollbar_new(adj));
-}
-
-static VALUE
-vscrollbar_s_new(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE arg1;
- GtkAdjustment *adj = NULL;
-
- rb_scan_args(argc, argv, "01", &arg1);
- if (!NIL_P(arg1)) adj = (GtkAdjustment*)get_gobject(arg1);
-
- return make_widget(self, gtk_vscrollbar_new(adj));
-}
-
-static VALUE
-hsep_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_hseparator_new());
-}
-
-static VALUE
-vsep_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_vseparator_new());
-}
-
-static VALUE
-idiag_s_new(self)
- VALUE self;
-{
- return make_widget(self, gtk_input_dialog_new());
-}
-
-static VALUE
-gtk_m_main(self)
- VALUE self;
-{
- gtk_main();
- return Qnil;
-}
-
-static gint
-idle()
-{
- CHECK_INTS;
- return TRUE;
-}
-
-static void
-exec_interval(proc)
- VALUE proc;
-{
- rb_funcall(proc, id_call, 0);
-}
-
-static VALUE
-timeout_add(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE interval, func;
- int id;
-
- rb_scan_args(argc, argv, "11", &interval, &func);
- if (NIL_P(func)) {
- func = f_lambda();
- }
- id = gtk_timeout_add_interp(NUM2INT(interval), exec_interval,
- (gpointer)func, 0);
- return INT2FIX(id);
-}
-
-static VALUE
-timeout_remove(self, id)
- VALUE self, id;
-{
- gtk_timeout_remove(NUM2INT(id));
- return Qnil;
-}
-
-static VALUE
-idle_add(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE func;
- int id;
-
- rb_scan_args(argc, argv, "01", &func);
- if (NIL_P(func)) {
- func = f_lambda();
- }
- id = gtk_idle_add_interp(exec_interval, (gpointer)func, 0);
- return INT2FIX(id);
-}
-
-static VALUE
-idle_remove(self, id)
- VALUE self, id;
-{
- gtk_idle_remove(NUM2INT(id));
- return Qnil;
-}
-
-static VALUE warn_handler;
-static VALUE mesg_handler;
-static VALUE print_handler;
-
-static void
-gtkwarn(mesg)
- char *mesg;
-{
- rb_funcall(warn_handler, id_call, 1, str_new2(mesg));
-}
-
-static void
-gtkmesg(mesg)
- char *mesg;
-{
- rb_funcall(mesg_handler, id_call, 1, str_new2(mesg));
-}
-
-static void
-gtkprint(mesg)
- char *mesg;
-{
- rb_funcall(print_handler, id_call, 1, str_new2(mesg));
-}
-
-static VALUE
-set_warning_handler(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE handler;
-
- rb_scan_args(argc, argv, "01", &handler);
- if (NIL_P(handler)) {
- handler = f_lambda();
- }
- g_set_warning_handler(gtkwarn);
-}
-
-static VALUE
-set_message_handler(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE handler;
-
- rb_scan_args(argc, argv, "01", &handler);
- if (NIL_P(handler)) {
- handler = f_lambda();
- }
- g_set_message_handler(gtkmesg);
-}
-
-static VALUE
-set_print_handler(argc, argv, self)
- int argc;
- VALUE *argv;
- VALUE self;
-{
- VALUE handler;
-
- rb_scan_args(argc, argv, "01", &handler);
- if (NIL_P(handler)) {
- handler = f_lambda();
- }
- g_set_print_handler(gtkprint);
-}
-
-static void
-gtkerr(mesg)
- char *mesg;
-{
- Fail("%s", mesg);
-}
-
-void
-Init_gtk()
-{
- int argc, i;
- char **argv;
-
- gtk_object_list = ary_new();
- rb_global_variable(&gtk_object_list);
-
- mGtk = rb_define_module("Gtk");
-
- gObject = rb_define_class_under(mGtk, "GtkObject", cObject);
- gWidget = rb_define_class_under(mGtk, "Widget", gObject);
- gContainer = rb_define_class_under(mGtk, "Container", gWidget);
- gBin = rb_define_class_under(mGtk, "Bin", gContainer);
- gAlignment = rb_define_class_under(mGtk, "Alignment", gBin);
- gMisc = rb_define_class_under(mGtk, "Misc", gWidget);
- gArrow = rb_define_class_under(mGtk, "Arrow", gMisc);
- gFrame = rb_define_class_under(mGtk, "Frame", gBin);
- gAspectFrame = rb_define_class_under(mGtk, "AspectFrame", gFrame);
- gData = rb_define_class_under(mGtk, "Data", gObject);
- gAdjustment = rb_define_class_under(mGtk, "Adjustment", gData);
- gBox = rb_define_class_under(mGtk, "Box", gContainer);
- gButton = rb_define_class_under(mGtk, "Button", gContainer);
- gTButton = rb_define_class_under(mGtk, "ToggleButton", gButton);
- gCButton = rb_define_class_under(mGtk, "CheckButton", gTButton);
- gRButton = rb_define_class_under(mGtk, "RadioButton", gCButton);
- gBBox = rb_define_class_under(mGtk, "ButtonBox", gBox);
- gCList = rb_define_class_under(mGtk, "CList", gContainer);
- gWindow = rb_define_class_under(mGtk, "Window", gBin);
- gDialog = rb_define_class_under(mGtk, "Dialog", gWindow);
- gFileSel = rb_define_class_under(mGtk, "FileSelection", gWindow);
- gVBox = rb_define_class_under(mGtk, "VBox", gBox);
- gColorSel = rb_define_class_under(mGtk, "ColorSelection", gVBox);
- gColorSelDialog = rb_define_class_under(mGtk, "ColorSelectionDialog", gWindow);
- gImage = rb_define_class_under(mGtk, "Image", gMisc);
- gDrawArea = rb_define_class_under(mGtk, "DrawingArea", gWidget);
- gEntry = rb_define_class_under(mGtk, "Entry", gWidget);
- gEventBox = rb_define_class_under(mGtk, "EventBox", gBin);
- gFixed = rb_define_class_under(mGtk, "Fixed", gContainer);
- gGamma = rb_define_class_under(mGtk, "GammaCurve", gVBox);
- gHBBox = rb_define_class_under(mGtk, "HButtonBox", gBBox);
- gVBBox = rb_define_class_under(mGtk, "VButtonBox", gBBox);
- gHBox = rb_define_class_under(mGtk, "HBox", gBox);
- gPaned = rb_define_class_under(mGtk, "Paned", gContainer);
- gHPaned = rb_define_class_under(mGtk, "HPaned", gPaned);
- gVPaned = rb_define_class_under(mGtk, "VPaned", gPaned);
- gRuler = rb_define_class_under(mGtk, "Ruler", gWidget);
- gHRuler = rb_define_class_under(mGtk, "HRuler", gRuler);
- gVRuler = rb_define_class_under(mGtk, "VRuler", gRuler);
- gRange = rb_define_class_under(mGtk, "Range", gWidget);
- gScale = rb_define_class_under(mGtk, "Scale", gRange);
- gHScale = rb_define_class_under(mGtk, "HScale", gScale);
- gVScale = rb_define_class_under(mGtk, "VScale", gScale);
- gScrollbar = rb_define_class_under(mGtk, "Scrollbar", gRange);
- gHScrollbar = rb_define_class_under(mGtk, "HScrollbar", gScrollbar);
- gVScrollbar = rb_define_class_under(mGtk, "VScrollbar", gScrollbar);
- gSeparator = rb_define_class_under(mGtk, "Separator", gWidget);
- gHSeparator = rb_define_class_under(mGtk, "HSeparator", gSeparator);
- gVSeparator = rb_define_class_under(mGtk, "VSeparator", gSeparator);
- gInputDialog = rb_define_class_under(mGtk, "InputDialog", gDialog);
- gLabel = rb_define_class_under(mGtk, "Label", gMisc);
- gList = rb_define_class_under(mGtk, "List", gContainer);
- gItem = rb_define_class_under(mGtk, "Item", gBin);
- gListItem = rb_define_class_under(mGtk, "ListItem", gItem);
- gMenuShell = rb_define_class_under(mGtk, "MenuShell", gContainer);
- gMenu = rb_define_class_under(mGtk, "Menu", gMenuShell);
- gMenuBar = rb_define_class_under(mGtk, "MenuBar", gMenuShell);
- gMenuItem = rb_define_class_under(mGtk, "MenuItem", gItem);
- gCMenuItem = rb_define_class_under(mGtk, "CheckMenuItem", gMenuItem);
- gRMenuItem = rb_define_class_under(mGtk, "RadioMenuItem", gCMenuItem);
- gNotebook = rb_define_class_under(mGtk, "Notebook", gContainer);
- gOptionMenu = rb_define_class_under(mGtk, "OptionMenu", gButton);
- gPixmap = rb_define_class_under(mGtk, "Pixmap", gMisc);
- gPreview = rb_define_class_under(mGtk, "Preview", gWidget);
- gProgressBar = rb_define_class_under(mGtk, "ProgressBar", gWidget);
- gScrolledWin = rb_define_class_under(mGtk, "ScrolledWindow", gContainer);
- gTable = rb_define_class_under(mGtk, "Table", gContainer);
- gText = rb_define_class_under(mGtk, "Text", gWidget);
- gToolbar = rb_define_class_under(mGtk, "Toolbar", gContainer);
- gTooltips = rb_define_class_under(mGtk, "Tooltips", cObject);
- gTree = rb_define_class_under(mGtk, "Tree", gContainer);
- gTreeItem = rb_define_class_under(mGtk, "TreeItem", gItem);
- gViewPort = rb_define_class_under(mGtk, "ViewPort", gBin);
-
- gAcceleratorTable = rb_define_class_under(mGtk, "AcceleratorTable", cObject);
- gStyle = rb_define_class_under(mGtk, "Style", cObject);
- gPreviewInfo = rb_define_class_under(mGtk, "PreviewInfo", cObject);
- gRequisiton = rb_define_class_under(mGtk, "Requisiton", cObject);
- gAllocation = rb_define_class_under(mGtk, "Allocation", cObject);
-
- mGdk = rb_define_module("Gdk");
-
- gdkFont = rb_define_class_under(mGdk, "Font", cObject);
- gdkColor = rb_define_class_under(mGdk, "Color", cObject);
- gdkPixmap = rb_define_class_under(mGdk, "Pixmap", cObject);
- gdkBitmap = rb_define_class_under(mGdk, "Bitmap", gdkPixmap);
- gdkWindow = rb_define_class_under(mGdk, "Window", cObject);
- gdkImage = rb_define_class_under(mGdk, "Image", cObject);
- gdkVisual = rb_define_class_under(mGdk, "Visual", cObject);
- gdkGC = rb_define_class_under(mGdk, "GC", cObject);
- gdkGCValues = rb_define_class_under(mGdk, "GCValues", cObject);
- gdkRectangle = rb_define_class_under(mGdk, "Rectangle", cObject);
- gdkSegment = rb_define_class_under(mGdk, "Segment", cObject);
- gdkWindowAttr = rb_define_class_under(mGdk, "WindowAttr", cObject);
- gdkCursor = rb_define_class_under(mGdk, "Cursor", cObject);
- gdkAtom = rb_define_class_under(mGdk, "Atom", cObject);
- gdkColorContext = rb_define_class_under(mGdk, "ColotContext", cObject);
- gdkEvent = rb_define_class_under(mGdk, "gdkEvent", cObject);
-
- /* GtkObject */
- rb_define_singleton_method(gObject, "new", gobj_s_new, -1);
- rb_define_method(gObject, "set_flags", gobj_set_flags, 1);
- rb_define_method(gObject, "unset_flags", gobj_unset_flags, 1);
- rb_define_method(gObject, "destroy", gobj_destroy, 0);
- rb_define_method(gObject, "signal_connect", gobj_sig_connect, -1);
- rb_define_method(gObject, "signal_connect_after", gobj_sig_connect_after, -1);
- rb_define_method(gObject, "singleton_method_added", gobj_smethod_added, 1);
-
- /* Widget */
- rb_define_method(gWidget, "destroy", widget_destroy, 0);
- rb_define_method(gWidget, "show", widget_show, 0);
- rb_define_method(gWidget, "show_all", widget_show_all, 0);
- rb_define_method(gWidget, "hide", widget_hide, 0);
- rb_define_method(gWidget, "hide_all", widget_hide_all, 0);
- rb_define_method(gWidget, "map", widget_map, 0);
- rb_define_method(gWidget, "unmap", widget_unmap, 0);
- rb_define_method(gWidget, "realize", widget_realize, 0);
- rb_define_method(gWidget, "unrealize", widget_unrealize, 0);
- rb_define_method(gWidget, "queue_draw", widget_queue_draw, 0);
- rb_define_method(gWidget, "queue_resize", widget_queue_resize, 0);
- rb_define_method(gWidget, "draw", widget_draw, 1);
- rb_define_method(gWidget, "draw_focus", widget_draw_focus, 0);
- rb_define_method(gWidget, "draw_default", widget_draw_default, 0);
- rb_define_method(gWidget, "draw_children", widget_draw_children, 0);
- rb_define_method(gWidget, "size_request", widget_size_request, 1);
- rb_define_method(gWidget, "size_alocate", widget_size_allocate, 1);
- rb_define_method(gWidget, "install_accelerator", widget_inst_accel, 4);
- rb_define_method(gWidget, "remove_accelerator", widget_rm_accel, 4);
- rb_define_method(gWidget, "event", widget_event, 1);
- rb_define_method(gWidget, "activate", widget_activate, 0);
- rb_define_method(gWidget, "grab_focus", widget_grab_focus, 0);
- rb_define_method(gWidget, "grab_default", widget_grab_default, 0);
- rb_define_method(gWidget, "restore_state", widget_restore_state, 0);
- rb_define_method(gWidget, "visible?", widget_visible, 0);
- rb_define_method(gWidget, "reparent", widget_reparent, 1);
- rb_define_method(gWidget, "popup", widget_popup, 2);
- rb_define_method(gWidget, "intersect", widget_intersect, 2);
- rb_define_method(gWidget, "basic", widget_basic, 0);
- rb_define_method(gWidget, "get_name", widget_set_name, 0);
- rb_define_method(gWidget, "set_name", widget_set_name, 1);
- rb_define_method(gWidget, "set_parent", widget_set_parent, 1);
- rb_define_method(gWidget, "set_sensitive", widget_set_sensitive, 1);
- rb_define_method(gWidget, "set_usize", widget_set_usize, 2);
- rb_define_method(gWidget, "set_uposition", widget_set_uposition, 2);
- rb_define_method(gWidget, "set_style", widget_set_style, 1);
- rb_define_method(gWidget, "set_events", widget_set_events, 1);
- rb_define_method(gWidget, "set_extension_events", widget_set_eevents, 1);
- rb_define_method(gWidget, "unparent", widget_unparent, 0);
- rb_define_method(gWidget, "get_toplevel", widget_get_toplevel, 0);
- rb_define_method(gWidget, "get_ancestor", widget_get_ancestor, 1);
- rb_define_method(gWidget, "get_colormap", widget_get_colormap, 0);
- rb_define_method(gWidget, "get_visual", widget_get_visual, 0);
- rb_define_method(gWidget, "get_style", widget_get_style, 0);
- rb_define_method(gWidget, "style", widget_get_style, 0);
- rb_define_method(gWidget, "get_events", widget_get_events, 0);
- rb_define_method(gWidget, "get_extension_events", widget_get_eevents, 0);
- rb_define_method(gWidget, "get_pointer", widget_get_eevents, 0);
- rb_define_method(gWidget, "ancestor?", widget_is_ancestor, 1);
- rb_define_method(gWidget, "child?", widget_is_child, 1);
- rb_define_method(gWidget, "window", widget_window, 0);
-
- rb_define_singleton_method(gWidget, "push_colomap", widget_push_cmap, 1);
- rb_define_singleton_method(gWidget, "push_visual", widget_push_visual, 1);
- rb_define_singleton_method(gWidget, "push_style", widget_push_style, 1);
- rb_define_singleton_method(gWidget, "pop_colomap", widget_pop_cmap, 0);
- rb_define_singleton_method(gWidget, "pop_visual", widget_pop_visual, 0);
- rb_define_singleton_method(gWidget, "pop_style", widget_pop_style, 0);
-
- rb_define_singleton_method(gWidget, "set_default_colomap",
- widget_set_default_cmap, 1);
- rb_define_singleton_method(gWidget, "set_default_visual",
- widget_set_default_visual, 1);
- rb_define_singleton_method(gWidget, "set_default_style",
- widget_set_default_style, 1);
- rb_define_singleton_method(gWidget, "get_default_colomap",
- widget_get_default_cmap, 0);
- rb_define_singleton_method(gWidget, "get_default_visual",
- widget_get_default_visual, 0);
- rb_define_singleton_method(gWidget, "get_default_style",
- widget_get_default_style, 0);
- rb_define_singleton_method(gWidget, "set_default_colomap",
- widget_set_default_cmap, 1);
- rb_define_singleton_method(gWidget, "set_default_visual",
- widget_set_default_visual, 1);
- rb_define_singleton_method(gWidget, "set_default_style",
- widget_set_default_style, 1);
- rb_define_singleton_method(gWidget, "set_default_colomap",
- widget_set_default_cmap, 1);
- rb_define_singleton_method(gWidget, "set_default_visual",
- widget_set_default_visual, 1);
- rb_define_singleton_method(gWidget, "propagage_default_style",
- widget_propagate_default_style, 0);
-
- /* Container */
- rb_define_method(gContainer, "border_width", cont_bwidth, 1);
- rb_define_method(gContainer, "add", cont_add, 1);
- rb_define_method(gContainer, "disable_resize", cont_disable_resize, 0);
- rb_define_method(gContainer, "enable_resize", cont_enable_resize, 0);
- rb_define_method(gContainer, "block_resize", cont_block_resize, 0);
- rb_define_method(gContainer, "unblock_resize", cont_unblock_resize, 0);
- rb_define_method(gContainer, "need_resize", cont_need_resize, 0);
- rb_define_method(gContainer, "foreach", cont_foreach, -1);
- rb_define_method(gContainer, "each", cont_each, 0);
- rb_define_method(gContainer, "focus", cont_focus, 1);
- rb_define_method(gContainer, "children", cont_children, 0);
-
- /* Bin */
- /* -- */
-
- /* Alignment */
- rb_define_singleton_method(gAlignment, "new", align_s_new, 4);
- rb_define_method(gAlignment, "set", align_set, 4);
-
- /* Misc */
- rb_define_method(gMisc, "set_alignment", misc_set_align, 2);
- rb_define_method(gMisc, "set_padding", misc_set_padding, 2);
-
- /* Arrow */
- rb_define_singleton_method(gArrow, "new", arrow_s_new, 2);
- rb_define_method(gArrow, "set", arrow_s_new, 2);
-
- /* Frame */
- rb_define_singleton_method(gFrame, "new", frame_s_new, 1);
- rb_define_method(gFrame, "set_label", frame_set_label, 1);
- rb_define_method(gFrame, "set_label_align", frame_set_label_align, 2);
- rb_define_method(gFrame, "set_shadow_type", frame_set_shadow_type, 1);
-
- /* AspectFrame */
- rb_define_singleton_method(gAspectFrame, "new", aframe_s_new, 5);
- rb_define_method(gAspectFrame, "set", aframe_set, 4);
-
- /* Data */
- /* -- */
-
- /* Adjustment */
- rb_define_singleton_method(gAdjustment, "new", adj_s_new, 6);
-
- /* Box */
- rb_define_method(gBox, "pack_start", box_pack_start, -1);
- rb_define_method(gBox, "pack_end", box_pack_end, -1);
-
- /* Button */
- rb_define_singleton_method(gButton, "new", button_s_new, -1);
- rb_define_method(gButton, "pressed", button_pressed, 0);
- rb_define_method(gButton, "released", button_released, 0);
- rb_define_method(gButton, "clicked", button_clicked, 0);
- rb_define_method(gButton, "enter", button_enter, 0);
- rb_define_method(gButton, "leave", button_leave, 0);
-
- /* ToggleButton */
- rb_define_singleton_method(gTButton, "new", tbtn_s_new, -1);
- rb_define_method(gTButton, "set_mode", tbtn_set_mode, 1);
- rb_define_method(gTButton, "set_state", tbtn_set_state, 1);
- rb_define_method(gTButton, "toggled", tbtn_toggled, 0);
-
- /* CheckButton */
- rb_define_singleton_method(gCButton, "new", cbtn_s_new, -1);
-
- /* RadioButton */
- rb_define_singleton_method(gCButton, "new", rbtn_s_new, -1);
- rb_define_method(gCButton, "group", rbtn_group, 0);
-
- /* ButtonBox */
- rb_define_singleton_method(gBBox, "get_child_size_default",
- bbox_get_child_size_default, 0);
- rb_define_singleton_method(gBBox, "get_child_ipadding_default",
- bbox_get_child_ipadding_default, 0);
- rb_define_singleton_method(gBBox, "set_child_size_default",
- bbox_set_child_size_default, 2);
- rb_define_singleton_method(gBBox, "set_child_ipadding_default",
- bbox_set_child_ipadding_default, 2);
- rb_define_method(gBBox, "get_spacing", bbox_get_spacing, 0);
- rb_define_method(gBBox, "get_layout", bbox_get_layout, 0);
- rb_define_method(gBBox, "get_child_size", bbox_get_child_size, 0);
- rb_define_method(gBBox, "get_child_ipadding", bbox_get_child_ipadding, 0);
- rb_define_method(gBBox, "set_spacing", bbox_set_spacing, 1);
- rb_define_method(gBBox, "set_layout", bbox_set_layout, 1);
- rb_define_method(gBBox, "set_child_size", bbox_set_child_size, 2);
- rb_define_method(gBBox, "set_child_ipadding", bbox_set_child_ipadding, 2);
-
- /* CList */
- rb_define_singleton_method(gCList, "new", clist_s_new, 1);
- rb_define_method(gCList, "set_border", clist_set_border, 1);
- rb_define_method(gCList, "set_selection_mode", clist_set_sel_mode, 1);
- rb_define_method(gCList, "set_policy", clist_set_policy, 2);
- rb_define_method(gCList, "freeze", clist_freeze, 0);
- rb_define_method(gCList, "thaw", clist_thaw, 0);
- rb_define_method(gCList, "set_column_title", clist_set_col_title, 2);
- rb_define_method(gCList, "set_column_widget", clist_set_col_wigdet, 2);
- rb_define_method(gCList, "set_column_justification", clist_set_col_just, 2);
- rb_define_method(gCList, "set_column_width", clist_set_col_width, 2);
- rb_define_method(gCList, "set_row_height", clist_set_row_height, 1);
- rb_define_method(gCList, "moveto", clist_moveto, 4);
- rb_define_method(gCList, "set_text", clist_set_text, 3);
- rb_define_method(gCList, "set_pixmap", clist_set_text, 4);
- rb_define_method(gCList, "set_pixtext", clist_set_pixtext, 6);
- rb_define_method(gCList, "set_foreground", clist_set_foreground, 2);
- rb_define_method(gCList, "set_background", clist_set_background, 2);
- rb_define_method(gCList, "set_shift", clist_set_shift, 4);
- rb_define_method(gCList, "append", clist_append, 1);
- rb_define_method(gCList, "insert", clist_insert, 2);
- rb_define_method(gCList, "remove", clist_remove, 1);
- rb_define_method(gCList, "set_row_data", clist_set_row_data, 2);
- rb_define_method(gCList, "get_row_data", clist_set_row_data, 1);
- rb_define_method(gCList, "select_row", clist_select_row, 2);
- rb_define_method(gCList, "unselect_row", clist_unselect_row, 2);
- rb_define_method(gCList, "clear", clist_clear, 0);
-
- /* Window */
- rb_define_singleton_method(gWindow, "new", gwin_s_new, 1);
- rb_define_method(gWindow, "set_title", gwin_set_title, 1);
- rb_define_method(gWindow, "set_policy", gwin_set_policy, 3);
- rb_define_method(gWindow, "set_wmclass", gwin_set_wmclass, 1);
- rb_define_method(gWindow, "set_focus", gwin_set_focus, 1);
- rb_define_method(gWindow, "set_default", gwin_set_focus, 1);
- rb_define_method(gWindow, "add_accelerator_table", gwin_add_accel, 1);
- rb_define_method(gWindow, "remove_accelerator_table", gwin_rm_accel, 1);
- rb_define_method(gWindow, "position", gwin_position, 1);
-
- /* Dialog */
- rb_define_singleton_method(gDialog, "new", dialog_s_new, 0);
-
- /* FileSelection */
- rb_define_singleton_method(gFileSel, "new", fsel_s_new, 1);
- rb_define_method(gFileSel, "set_filename", fsel_set_fname, 1);
- rb_define_method(gFileSel, "get_filename", fsel_get_fname, 0);
- rb_define_method(gFileSel, "ok_button", fsel_ok_button, 0);
- rb_define_method(gFileSel, "cancel_button", fsel_cancel_button, 0);
- rb_define_method(gFileSel, "help_button", fsel_help_button, 0);
-
- /* VBox */
- rb_define_singleton_method(gVBox, "new", vbox_s_new, -1);
-
- /* ColorSelection */
- rb_define_singleton_method(gColorSel, "new", colorsel_s_new, 0);
- rb_define_method(gColorSel, "set_update_policy", colorsel_set_update_policy, 1);
- rb_define_method(gColorSel, "set_opacity", colorsel_set_opacity, 1);
- rb_define_method(gColorSel, "set_color", colorsel_set_color, 1);
- rb_define_method(gColorSel, "get_color", colorsel_get_color, 0);
-
- /* ColorSelectionDialog */
- rb_define_singleton_method(gColorSelDialog, "new", cdialog_s_new, 1);
-
- /* Image */
- rb_define_singleton_method(gImage, "new", image_s_new, 2);
- rb_define_method(gImage, "set", image_set, 2);
- rb_define_method(gImage, "get", image_get, 0);
-
- /* DrawingArea */
- rb_define_singleton_method(gDrawArea, "new", darea_s_new, 0);
- rb_define_method(gDrawArea, "size", darea_size, 2);
-
- /* Entry */
- rb_define_singleton_method(gEntry, "new", entry_s_new, 0);
- rb_define_method(gEntry, "set_text", entry_set_text, 1);
-
- /* EventBox */
- rb_define_singleton_method(gEventBox, "new", eventbox_s_new, 0);
-
- /* Fixed */
- rb_define_singleton_method(gFixed, "new", fixed_s_new, 0);
- rb_define_method(gFixed, "put", fixed_put, 3);
- rb_define_method(gFixed, "move", fixed_move, 3);
-
- /* GammaCurve */
- rb_define_singleton_method(gGamma, "new", gamma_s_new, 0);
- rb_define_method(gGamma, "gamma", gamma_gamma, 0);
-
- /* HButtonBox */
- rb_define_singleton_method(gHBBox, "new", hbbox_s_new, 0);
- rb_define_singleton_method(gHBBox, "get_spacing_default",
- hbbox_get_spacing_default, 0);
- rb_define_singleton_method(gHBBox, "get_layout_default",
- hbbox_get_spacing_default, 0);
- rb_define_singleton_method(gHBBox, "set_spacing_default",
- hbbox_set_spacing_default, 1);
- rb_define_singleton_method(gHBBox, "set_layout_default",
- hbbox_set_layout_default, 1);
-
- /* VButtonBox */
- rb_define_singleton_method(gVBBox, "new", vbbox_s_new, 0);
- rb_define_singleton_method(gVBBox, "get_spacing_default",
- vbbox_get_spacing_default, 0);
- rb_define_singleton_method(gVBBox, "get_layout_default",
- vbbox_get_spacing_default, 0);
- rb_define_singleton_method(gVBBox, "set_spacing_default",
- vbbox_set_spacing_default, 1);
- rb_define_singleton_method(gVBBox, "set_layout_default",
- vbbox_set_layout_default, 1);
-
- /* HBox */
- rb_define_singleton_method(gHBox, "new", hbox_s_new, -1);
-
- /* Paned */
- rb_define_method(gPaned, "add1", paned_add1, 1);
- rb_define_method(gPaned, "add2", paned_add1, 1);
- rb_define_method(gPaned, "handle_size", paned_handle_size, 1);
- rb_define_method(gPaned, "gutter_size", paned_gutter_size, 1);
-
- /* HPaned */
- rb_define_singleton_method(gHPaned, "new", hpaned_s_new, 0);
-
- /* VPaned */
- rb_define_singleton_method(gVPaned, "new", vpaned_s_new, 0);
-
- /* Ruler */
- rb_define_method(gRuler, "set_metric", ruler_set_metric, 1);
- rb_define_method(gRuler, "set_range", ruler_set_range, 4);
- rb_define_method(gRuler, "draw_ticks", ruler_draw_ticks, 0);
- rb_define_method(gRuler, "draw_pos", ruler_draw_pos, 0);
-
- /* HRuler */
- rb_define_singleton_method(gHRuler, "new", hruler_s_new, 0);
-
- /* VRuler */
- rb_define_singleton_method(gVRuler, "new", vruler_s_new, 0);
-
- /* Range */
- rb_define_method(gRange, "get_adjustment", range_get_adj, 0);
- rb_define_method(gRange, "set_update_policy", range_set_update_policy, 1);
- rb_define_method(gRange, "set_adjustment", range_set_adj, 1);
- rb_define_method(gRange, "draw_background", range_draw_bg, 0);
- rb_define_method(gRange, "draw_trough", range_draw_trough, 0);
- rb_define_method(gRange, "draw_slider", range_draw_slider, 0);
- rb_define_method(gRange, "draw_step_forw", range_draw_step_forw, 0);
- rb_define_method(gRange, "draw_step_back", range_draw_step_back, 0);
- rb_define_method(gRange, "slider_update", range_slider_update, 0);
- rb_define_method(gRange, "trough_click", range_trough_click, 2);
- rb_define_method(gRange, "draw_background", range_draw_bg, 2);
- rb_define_method(gRange, "default_hslider_update", range_default_hslider_update, 0);
- rb_define_method(gRange, "default_vslider_update", range_default_vslider_update, 0);
- rb_define_method(gRange, "default_htrough_click", range_default_htrough_click, 2);
- rb_define_method(gRange, "default_vtrough_click", range_default_vtrough_click, 2);
- rb_define_method(gRange, "default_hmotion", range_default_hmotion, 2);
- rb_define_method(gRange, "default_vmotion", range_default_vmotion, 2);
- rb_define_method(gRange, "calc_value", range_calc_value, 1);
-
- /* Scale */
- rb_define_method(gScale, "set_digits", scale_set_digits, 1);
- rb_define_method(gScale, "set_draw_value", scale_set_draw_value, 1);
- rb_define_method(gScale, "set_value_pos", scale_set_value_pos, 1);
- rb_define_method(gScale, "value_width", scale_value_width, 0);
- rb_define_method(gScale, "draw_value", scale_draw_value, 0);
-
- /* HScale */
- rb_define_singleton_method(gHScale, "new", hscale_s_new, -1);
-
- /* VScale */
- rb_define_singleton_method(gVScale, "new", vscale_s_new, -1);
-
- /* Scrollbar */
- /* -- */
-
- /* HScrollbar */
- rb_define_singleton_method(gHScrollbar, "new", hscrollbar_s_new, -1);
-
- /* VScrollbar */
- rb_define_singleton_method(gVScrollbar, "new", vscrollbar_s_new, -1);
-
- /* Separator */
- /* -- */
-
- /* HSeparator */
- rb_define_singleton_method(gHSeparator, "new", hsep_s_new, 0);
-
- /* VSeparator */
- rb_define_singleton_method(gVSeparator, "new", vsep_s_new, 0);
-
- /* InputDialog */
- rb_define_singleton_method(gInputDialog, "new", idiag_s_new, 0);
-
- /* Label */
- rb_define_singleton_method(gLabel, "new", label_s_new, 1);
-
- /* List */
- rb_define_singleton_method(gList, "new", list_s_new, 0);
- rb_define_method(gList, "set_selection_mode", list_set_sel_mode, 1);
- rb_define_method(gList, "selection_mode", list_sel_mode, 1);
- rb_define_method(gList, "selection", list_selection, 0);
- rb_define_method(gList, "insert_items", list_insert_items, 2);
- rb_define_method(gList, "append_items", list_append_items, 1);
- rb_define_method(gList, "prepend_items", list_prepend_items, 1);
- rb_define_method(gList, "remove_items", list_remove_items, 1);
- rb_define_method(gList, "clear_items", list_clear_items, 2);
- rb_define_method(gList, "select_item", list_select_item, 1);
- rb_define_method(gList, "unselect_item", list_unselect_item, 1);
- rb_define_method(gList, "select_child", list_select_child, 1);
- rb_define_method(gList, "unselect_child", list_unselect_child, 1);
- rb_define_method(gList, "child_position", list_child_position, 1);
-
- /* Item */
- rb_define_method(gItem, "select", item_select, 0);
- rb_define_method(gItem, "deselect", item_deselect, 0);
- rb_define_method(gItem, "toggle", item_toggle, 0);
-
- /* ListItem */
- rb_define_singleton_method(gListItem, "new", litem_s_new, -1);
-
- /* MenuShell */
- rb_define_method(gMenuShell, "append", mshell_append, 1);
- rb_define_method(gMenuShell, "prepend", mshell_prepend, 1);
- rb_define_method(gMenuShell, "insert", mshell_insert, 2);
- rb_define_method(gMenuShell, "deactivate", mshell_deactivate, 0);
-
- /* Menu */
- rb_define_singleton_method(gMenu, "new", menu_s_new, 0);
- rb_define_method(gMenu, "append", menu_append, 1);
- rb_define_method(gMenu, "prepend", menu_prepend, 1);
- rb_define_method(gMenu, "insert", menu_insert, 2);
- rb_define_method(gMenu, "popup", menu_popup, 6);
- rb_define_method(gMenu, "popdown", menu_popup, 0);
- rb_define_method(gMenu, "get_active", menu_get_active, 0);
- rb_define_method(gMenu, "set_active", menu_set_active, 1);
- rb_define_method(gMenu, "set_accelerator_table", menu_set_acceltbl, 1);
-
- /* MenuBar */
- rb_define_singleton_method(gMenuBar, "new", mbar_s_new, 0);
- rb_define_method(gMenuBar, "append", mbar_append, 1);
- rb_define_method(gMenuBar, "prepend", mbar_prepend, 1);
- rb_define_method(gMenuBar, "insert", mbar_insert, 2);
-
- /* MenuItem */
- rb_define_singleton_method(gMenuItem, "new", mitem_s_new, -1);
- rb_define_method(gMenuItem, "set_submenu", mitem_set_submenu, 1);
- rb_define_method(gMenuItem, "set_placement", mitem_set_placement, 1);
- rb_define_method(gMenuItem, "accelerator_size", mitem_accelerator_size, 0);
- rb_define_method(gMenuItem, "accelerator_text", mitem_accelerator_text, 0);
- rb_define_method(gMenuItem, "configure", mitem_configure, 2);
- rb_define_method(gMenuItem, "select", mitem_select, 0);
- rb_define_method(gMenuItem, "deselect", mitem_deselect, 0);
- rb_define_method(gMenuItem, "activate", mitem_activate, 0);
- rb_define_method(gMenuItem, "right_justify", mitem_right_justify, 0);
-
- /* CheckMenuItem */
- rb_define_singleton_method(gCMenuItem, "new", cmitem_s_new, -1);
- rb_define_method(gCMenuItem, "set_state", cmitem_set_state, 1);
- rb_define_method(gCMenuItem, "set_show_toggle", cmitem_set_show_toggle, 1);
- rb_define_method(gCMenuItem, "toggled", cmitem_toggled, 0);
-
- /* RadioMenuItem */
- rb_define_singleton_method(gRMenuItem, "new", rmitem_s_new, -1);
- rb_define_method(gRMenuItem, "group", rmitem_group, 0);
-
- /* NoteBook */
- rb_define_singleton_method(gNotebook, "new", note_s_new, 0);
- rb_define_method(gNotebook, "append_page", note_append_page, 2);
- rb_define_method(gNotebook, "prepend_page", note_prepend_page, 2);
- rb_define_method(gNotebook, "insert_page", note_insert_page, 3);
- rb_define_method(gNotebook, "remove_page", note_remove_page, 1);
- rb_define_method(gNotebook, "set_page", note_set_page, 1);
- rb_define_method(gNotebook, "cur_page", note_cur_page, 0);
- rb_define_method(gNotebook, "page", note_cur_page, 0);
- rb_define_method(gNotebook, "next_page", note_next_page, 0);
- rb_define_method(gNotebook, "prev_page", note_prev_page, 0);
- rb_define_method(gNotebook, "set_tab_pos", note_set_tab_pos, 1);
- rb_define_method(gNotebook, "tab_pos", note_tab_pos, 0);
- rb_define_method(gNotebook, "set_show_tabs", note_set_show_tabs, 1);
- rb_define_method(gNotebook, "show_tabs", note_show_tabs, 0);
- rb_define_method(gNotebook, "set_show_border", note_set_show_border, 1);
- rb_define_method(gNotebook, "show_border", note_show_border, 0);
-
- /* OptionMenu */
- rb_define_singleton_method(gOptionMenu, "new", omenu_s_new, 0);
- rb_define_method(gOptionMenu, "get_menu", omenu_get_menu, 0);
- rb_define_method(gOptionMenu, "set_menu", omenu_set_menu, 1);
- rb_define_method(gOptionMenu, "remove_menu", omenu_set_menu, 0);
- rb_define_method(gOptionMenu, "set_history", omenu_set_history, 1);
-
- /* Pixmap */
- rb_define_singleton_method(gPixmap, "new", pixmap_s_new, 2);
- rb_define_method(gPixmap, "set", pixmap_set, 2);
- rb_define_method(gPixmap, "get", pixmap_get, 0);
-
- /* Preview */
- rb_define_singleton_method(gPreview, "new", preview_s_new, 1);
- rb_define_method(gPreview, "size", preview_size, 2);
- rb_define_method(gPreview, "put", preview_size, 8);
- rb_define_method(gPreview, "put_row", preview_size, 5);
- rb_define_method(gPreview, "draw_row", preview_size, 4);
- rb_define_method(gPreview, "set_expand", preview_set_expand, 1);
- rb_define_singleton_method(gPreview, "set_gamma", preview_set_gamma, 1);
- rb_define_singleton_method(gPreview, "set_color_cube",
- preview_set_color_cube, 4);
- rb_define_singleton_method(gPreview, "set_install_cmap",
- preview_set_install_cmap, 1);
- rb_define_singleton_method(gPreview, "set_reserved",
- preview_set_reserved, 1);
- rb_define_singleton_method(gPreview, "get_visual", preview_get_visual, 0);
- rb_define_singleton_method(gPreview, "get_cmap", preview_get_cmap, 0);
- rb_define_singleton_method(gPreview, "get_info", preview_get_info, 0);
-
- /* ProgressBar */
- rb_define_singleton_method(gProgressBar, "new", pbar_s_new, 0);
- rb_define_method(gProgressBar, "update", pbar_update, 1);
-
- /* ScrolledWindow */
- rb_define_singleton_method(gScrolledWin, "new", scwin_s_new, -1);
- rb_define_method(gScrolledWin, "set_policy", scwin_set_policy, 2);
-
- /* Table */
- rb_define_singleton_method(gTable, "new", tbl_s_new, -1);
- rb_define_method(gTable, "attach", tbl_attach, -1);
- rb_define_method(gTable, "set_row_spacing", tbl_set_row_spacing, 2);
- rb_define_method(gTable, "set_col_spacing", tbl_set_col_spacing, 2);
- rb_define_method(gTable, "set_row_spacings", tbl_set_row_spacings, 1);
- rb_define_method(gTable, "set_col_spacings", tbl_set_col_spacings, 1);
-
- /* Text */
- rb_define_singleton_method(gText, "new", txt_s_new, -1);
- rb_define_method(gText, "set_editable", txt_set_editable, 1);
- rb_define_method(gText, "set_adjustment", txt_set_adjustment, 2);
- rb_define_method(gText, "set_point", txt_set_point, 1);
- rb_define_method(gText, "get_point", txt_get_point, 0);
- rb_define_method(gText, "get_length", txt_get_length, 0);
- rb_define_method(gText, "freeze", txt_freeze, 0);
- rb_define_method(gText, "thaw", txt_thaw, 0);
- rb_define_method(gText, "insert", txt_insert, 4);
- rb_define_method(gText, "backward_delete", txt_backward_delete, 1);
- rb_define_method(gText, "forward_delete", txt_forward_delete, 1);
-
- /* Toolbar */
- rb_define_singleton_method(gToolbar, "new", tbar_s_new, -1);
- rb_define_method(gToolbar, "append_item", tbar_append_item, 4);
- rb_define_method(gToolbar, "prepend_item", tbar_prepend_item, 4);
- rb_define_method(gToolbar, "insert_item", tbar_append_item, 5);
- rb_define_method(gToolbar, "append_space", tbar_append_space, 0);
- rb_define_method(gToolbar, "prepend_space", tbar_prepend_space, 0);
- rb_define_method(gToolbar, "insert_space", tbar_append_space, 1);
- rb_define_method(gToolbar, "set_orientation", tbar_set_orientation, 1);
- rb_define_method(gToolbar, "set_style", tbar_set_style, 1);
- rb_define_method(gToolbar, "set_space_size", tbar_set_space_size, 1);
- rb_define_method(gToolbar, "set_tooltips", tbar_set_tooltips, 1);
-
- /* Tooltips */
- rb_define_singleton_method(gTooltips, "new", ttips_s_new, 0);
- rb_define_method(gTooltips, "set_tips", ttips_set_tips, 2);
- rb_define_method(gTooltips, "set_delay", ttips_set_delay, 1);
- rb_define_method(gTooltips, "enable", ttips_enable, 0);
- rb_define_method(gTooltips, "disable", ttips_disable, 0);
-
- /* Tree */
- rb_define_singleton_method(gTree, "new", tree_s_new, 0);
- rb_define_method(gTree, "append", tree_append, 1);
- rb_define_method(gTree, "prepend", tree_prepend, 1);
- rb_define_method(gTree, "insert", tree_insert, 2);
-
- /* TreeItem */
- rb_define_singleton_method(gTreeItem, "new", titem_s_new, -1);
- rb_define_method(gTreeItem, "set_subtree", titem_set_subtree, 1);
- rb_define_method(gTreeItem, "select", titem_select, 0);
- rb_define_method(gTreeItem, "deselect", titem_deselect, 0);
- rb_define_method(gTreeItem, "expand", titem_expand, 0);
- rb_define_method(gTreeItem, "collapse", titem_collapse, 0);
-
- /* ViewPort */
- rb_define_singleton_method(gViewPort, "new", vport_s_new, -1);
- rb_define_method(gViewPort, "get_hadjustment", vport_get_hadj, 0);
- rb_define_method(gViewPort, "get_vadjustment", vport_get_vadj, 0);
- rb_define_method(gViewPort, "set_hadjustment", vport_set_hadj, 1);
- rb_define_method(gViewPort, "set_vadjustment", vport_set_vadj, 1);
- rb_define_method(gViewPort, "set_shadow_type", vport_set_shadow, 1);
-
- /* AcceleratorTable */
- /* Style */
-
- /* Gtk module */
- rb_define_module_function(mGtk, "main", gtk_m_main, 0);
- rb_define_module_function(mGtk, "timeout_add", timeout_add, -1);
- rb_define_module_function(mGtk, "timeout_remove", timeout_remove, 1);
- rb_define_module_function(mGtk, "idle_add", idle_add, -1);
- rb_define_module_function(mGtk, "idle_remove", idle_remove, 1);
-
- rb_define_module_function(mGtk, "set_warning_handler",
- set_warning_handler, -1);
- rb_define_module_function(mGtk, "set_message_handler",
- set_message_handler, -1);
- rb_define_module_function(mGtk, "set_print_handler",
- set_print_handler, -1);
-
- /* Gdk module */
- /* GdkFont */
- rb_define_method(gdkFont, "==", gdkfnt_equal, 1);
-
- /* GdkBitmap */
- rb_define_singleton_method(gdkBitmap, "new", gdkbmap_s_new, 3);
- rb_define_singleton_method(gdkBitmap, "create_from_data",
- gdkbmap_create_from_data, 4);
-
- /* GdkPixmap */
- rb_define_singleton_method(gdkPixmap, "new", gdkpmap_s_new, 4);
- rb_define_singleton_method(gdkPixmap, "create_from_xpm",
- gdkpmap_create_from_xpm, 3);
- rb_define_singleton_method(gdkPixmap, "create_from_xpm_d",
- gdkpmap_create_from_xpm, 3);
-
- /* GdkWindow */
-
- /* GdkImage */
-
- rb_define_const(mGtk, "VISIBLE", INT2FIX(GTK_VISIBLE));
- rb_define_const(mGtk, "MAPPED", INT2FIX(GTK_MAPPED));
- rb_define_const(mGtk, "UNMAPPED", INT2FIX(GTK_UNMAPPED));
- rb_define_const(mGtk, "REALIZED", INT2FIX(GTK_REALIZED));
- rb_define_const(mGtk, "SENSITIVE", INT2FIX(GTK_SENSITIVE));
- rb_define_const(mGtk, "PARENT_SENSITIVE", INT2FIX(GTK_PARENT_SENSITIVE));
- rb_define_const(mGtk, "NO_WINDOW", INT2FIX(GTK_NO_WINDOW));
- rb_define_const(mGtk, "HAS_FOCUS", INT2FIX(GTK_HAS_FOCUS));
- rb_define_const(mGtk, "CAN_FOCUS", INT2FIX(GTK_CAN_FOCUS));
- rb_define_const(mGtk, "HAS_DEFAULT", INT2FIX(GTK_HAS_DEFAULT));
- rb_define_const(mGtk, "CAN_DEFAULT", INT2FIX(GTK_CAN_DEFAULT));
- rb_define_const(mGtk, "PROPAGATE_STATE", INT2FIX(GTK_PROPAGATE_STATE));
- rb_define_const(mGtk, "ANCHORED", INT2FIX(GTK_ANCHORED));
- rb_define_const(mGtk, "BASIC", INT2FIX(GTK_BASIC));
- rb_define_const(mGtk, "USER_STYLE", INT2FIX(GTK_USER_STYLE));
- rb_define_const(mGtk, "GRAB_ALL", INT2FIX(GTK_GRAB_ALL));
- rb_define_const(mGtk, "REDRAW_PENDING", INT2FIX(GTK_REDRAW_PENDING));
- rb_define_const(mGtk, "RESIZE_PENDING", INT2FIX(GTK_RESIZE_PENDING));
- rb_define_const(mGtk, "RESIZE_NEEDED", INT2FIX(GTK_RESIZE_NEEDED));
- rb_define_const(mGtk, "HAS_SHAPE_MASK", INT2FIX(GTK_HAS_SHAPE_MASK));
-
- /* GtkWindowType */
- rb_define_const(mGtk, "WINDOW_TOPLEVEL", INT2FIX(GTK_WINDOW_TOPLEVEL));
- rb_define_const(mGtk, "WINDOW_DIALOG", INT2FIX(GTK_WINDOW_DIALOG));
- rb_define_const(mGtk, "WIN_POS_NONE", INT2FIX(GTK_WIN_POS_NONE));
- rb_define_const(mGtk, "WIN_POS_CENTER", INT2FIX(GTK_WIN_POS_CENTER));
- rb_define_const(mGtk, "WIN_POS_MOUSE", INT2FIX(GTK_WIN_POS_MOUSE));
-
- /* GtkDirectionType */
- rb_define_const(mGtk, "DIR_TAB_FORWARD", INT2FIX(GTK_DIR_TAB_FORWARD));
- rb_define_const(mGtk, "DIR_TAB_BACKWARD", INT2FIX(GTK_DIR_TAB_BACKWARD));
- rb_define_const(mGtk, "DIR_UP", INT2FIX(GTK_DIR_UP));
- rb_define_const(mGtk, "DIR_DOWN", INT2FIX(GTK_DIR_DOWN));
- rb_define_const(mGtk, "DIR_LEFT", INT2FIX(GTK_DIR_LEFT));
- rb_define_const(mGtk, "DIR_RIGHT", INT2FIX(GTK_DIR_RIGHT));
-
- /* GtkPolicyType */
- rb_define_const(mGtk, "POLICY_ALWAYS", INT2FIX(GTK_POLICY_ALWAYS));
- rb_define_const(mGtk, "POLICY_AUTOMATIC", INT2FIX(GTK_POLICY_AUTOMATIC));
-
- /* GtkSelectionMode */
- rb_define_const(mGtk, "SELECTION_SINGLE", INT2FIX(GTK_SELECTION_SINGLE));
- rb_define_const(mGtk, "SELECTION_BROWSE", INT2FIX(GTK_SELECTION_BROWSE));
- rb_define_const(mGtk, "SELECTION_MULTIPLE", INT2FIX(GTK_SELECTION_MULTIPLE));
- rb_define_const(mGtk, "SELECTION_EXTENDED", INT2FIX(GTK_SELECTION_EXTENDED));
- /* GtkPositionType */
- rb_define_const(mGtk, "POS_LEFT", INT2FIX(GTK_POS_LEFT));
- rb_define_const(mGtk, "POS_RIGHT", INT2FIX(GTK_POS_RIGHT));
- rb_define_const(mGtk, "POS_TOP", INT2FIX(GTK_POS_TOP));
- rb_define_const(mGtk, "POS_BOTTOM", INT2FIX(GTK_POS_BOTTOM));
-
- /* GtkShadowType */
- rb_define_const(mGtk, "SHADOW_NONE", INT2FIX(GTK_SHADOW_NONE));
- rb_define_const(mGtk, "SHADOW_IN", INT2FIX(GTK_SHADOW_IN));
- rb_define_const(mGtk, "SHADOW_OUT", INT2FIX(GTK_SHADOW_OUT));
- rb_define_const(mGtk, "SHADOW_ETCHED_IN", INT2FIX(GTK_SHADOW_ETCHED_IN));
- rb_define_const(mGtk, "SHADOW_ETCHED_OUT", INT2FIX(GTK_SHADOW_ETCHED_OUT));
- /* GtkStateType */
- rb_define_const(mGtk, "STATE_NORMAL", INT2FIX(GTK_STATE_NORMAL));
- rb_define_const(mGtk, "STATE_ACTIVE", INT2FIX(GTK_STATE_ACTIVE));
- rb_define_const(mGtk, "STATE_PRELIGHT", INT2FIX(GTK_STATE_PRELIGHT));
- rb_define_const(mGtk, "STATE_SELECTED", INT2FIX(GTK_STATE_SELECTED));
- rb_define_const(mGtk, "STATE_INSENSITIVE", INT2FIX(GTK_STATE_INSENSITIVE));
- /* GtkAttachOptions */
- rb_define_const(mGtk, "EXPAND", INT2FIX(GTK_EXPAND));
- rb_define_const(mGtk, "SHRINK", INT2FIX(GTK_SHRINK));
- rb_define_const(mGtk, "FILL", INT2FIX(GTK_FILL));
- /* GtkSubmenuDirection */
- rb_define_const(mGtk, "DIRECTION_LEFT", INT2FIX(GTK_DIRECTION_LEFT));
- rb_define_const(mGtk, "DIRECTION_RIGHT", INT2FIX(GTK_DIRECTION_RIGHT));
- /* GtkSubmenuPlacement */
- rb_define_const(mGtk, "TOP_BOTTOM", INT2FIX(GTK_TOP_BOTTOM));
- rb_define_const(mGtk, "LEFT_RIGHT", INT2FIX(GTK_LEFT_RIGHT));
- /* GtkMetricType */
- rb_define_const(mGtk, "PIXELS", INT2FIX(GTK_PIXELS));
- rb_define_const(mGtk, "INCHES", INT2FIX(GTK_INCHES));
- rb_define_const(mGtk, "CENTIMETERS", INT2FIX(GTK_CENTIMETERS));
-
- /* GtkArrowType */
- rb_define_const(mGtk, "ARROW_UP", INT2FIX(GTK_ARROW_UP));
- rb_define_const(mGtk, "ARROW_DOWN", INT2FIX(GTK_ARROW_DOWN));
- rb_define_const(mGtk, "ARROW_LEFT", INT2FIX(GTK_ARROW_LEFT));
- rb_define_const(mGtk, "ARROW_RIGHT", INT2FIX(GTK_ARROW_RIGHT));
-
- /* GtkPreviewType */
- rb_define_const(mGtk, "PREVIEW_COLOR", INT2FIX(GTK_PREVIEW_COLOR));
- rb_define_const(mGtk, "PREVIEW_GRAYSCALE", INT2FIX(GTK_PREVIEW_GRAYSCALE));
-
- rb_define_const(mGtk, "BUTTONBOX_DEFAULT", INT2FIX(GTK_BUTTONBOX_DEFAULT));
- rb_define_const(mGtk, "BUTTONBOX_SPREAD", INT2FIX(GTK_BUTTONBOX_SPREAD));
- rb_define_const(mGtk, "BUTTONBOX_EDGE", INT2FIX(GTK_BUTTONBOX_EDGE));
- rb_define_const(mGtk, "BUTTONBOX_START", INT2FIX(GTK_BUTTONBOX_START));
- rb_define_const(mGtk, "BUTTONBOX_END", INT2FIX(GTK_BUTTONBOX_END));
-
- /* GtkToolbarStyle */
- rb_define_const(mGtk, "TOOLBAR_ICONS", INT2FIX(GTK_TOOLBAR_ICONS));
- rb_define_const(mGtk, "TOOLBAR_TEXT", INT2FIX(GTK_TOOLBAR_TEXT));
- rb_define_const(mGtk, "TOOLBAR_BOTH", INT2FIX(GTK_TOOLBAR_BOTH));
-
- /* GtkOrientation */
- rb_define_const(mGtk, "ORIENTATION_HORIZONTAL", INT2FIX(GTK_ORIENTATION_HORIZONTAL));
- rb_define_const(mGtk, "ORIENTATION_VERTICAL", INT2FIX(GTK_ORIENTATION_VERTICAL));
-
- /* GdkExtensionMode */
- rb_define_const(mGdk, "EXTENSION_EVENTS_NONE", INT2FIX(GDK_EXTENSION_EVENTS_NONE));
- rb_define_const(mGdk, "EXTENSION_EVENTS_ALL", INT2FIX(GDK_EXTENSION_EVENTS_ALL));
- rb_define_const(mGdk, "EXTENSION_EVENTS_CURSOR", INT2FIX(GDK_EXTENSION_EVENTS_CURSOR));
-
- argc = RARRAY(rb_argv)->len;
- argv = ALLOCA_N(char*,argc+1);
- argv[0] = RSTRING(rb_argv0)->ptr;
- for (i=0;i<argc;i++) {
- if (TYPE(RARRAY(rb_argv)->ptr[i]) == T_STRING) {
- argv[i+1] = RSTRING(RARRAY(rb_argv)->ptr[i])->ptr;
- }
- else {
- argv[i+1] = "";
- }
- }
- argc++;
- {
- /* Gdk modifies sighandlers, sigh */
- RETSIGTYPE (*sigfunc[7])();
-
- sigfunc[0] = signal(SIGHUP, SIG_IGN);
- sigfunc[1] = signal(SIGINT, SIG_IGN);
- sigfunc[2] = signal(SIGQUIT, SIG_IGN);
- sigfunc[3] = signal(SIGBUS, SIG_IGN);
- sigfunc[4] = signal(SIGSEGV, SIG_IGN);
- sigfunc[5] = signal(SIGPIPE, SIG_IGN);
- sigfunc[6] = signal(SIGTERM, SIG_IGN);
-
- gdk_init(&argc, &argv);
-
- signal(SIGHUP, sigfunc[0]);
- signal(SIGINT, sigfunc[1]);
- signal(SIGQUIT, sigfunc[2]);
- signal(SIGBUS, sigfunc[3]);
- signal(SIGSEGV, sigfunc[4]);
- signal(SIGPIPE, sigfunc[5]);
- signal(SIGTERM, sigfunc[6]);
- }
-
- for (i=1;i<argc;i++) {
- RARRAY(rb_argv)->ptr[i] = str_taint(str_new2(argv[i]));
- }
- RARRAY(rb_argv)->len = argc-1;
-
- id_gtkdata = rb_intern("gtkdata");
- id_relatives = rb_intern("relatives");
- id_call = rb_intern("call");
- gtk_idle_add((GtkFunction)idle, 0);
-
- g_set_error_handler(gtkerr);
- g_set_warning_handler(gtkerr);
- rb_global_variable(&warn_handler);
- rb_global_variable(&mesg_handler);
- rb_global_variable(&print_handler);
-}
diff --git a/ext/gtk/test.rb b/ext/gtk/test.rb
deleted file mode 100644
index 52ce5db7e0..0000000000
--- a/ext/gtk/test.rb
+++ /dev/null
@@ -1,96 +0,0 @@
-require 'gtk'
-
-def create_menu(depth)
- return nil if depth < 1
-
- menu = Gtk::Menu::new()
- group = nil
- submenu = nil
-
- for i in 0..4
- buf = sprintf("item %2d - %d", depth, i+1)
-# menuitem = Gtk::MenuItem::new(buf)
- menuitem = Gtk::RadioMenuItem.new(group, buf)
- group = menuitem.group
- if depth % 2
- menuitem.set_show_toggle TRUE
- end
- menu.append menuitem
- menuitem.show
- if depth > 0
- unless submenu
- submenu = create_menu(depth - 1)
- end
- menuitem.set_submenu submenu
- end
- end
- return menu
-end
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.signal_connect("destroy") do
- exit
-end
-window.signal_connect("delete_event") do
- exit
-end
-window.set_title("menus")
-window.border_width(0)
-
-box1 = Gtk::VBox::new(FALSE, 0)
-window.add box1
-box1.show
-
-menubar = Gtk::MenuBar::new()
-box1.pack_start menubar, FALSE, TRUE, 0
-menubar.show
-
-menu = create_menu(2)
-menuitem = Gtk::MenuItem::new("test\nline2")
-menuitem.set_submenu menu
-menubar.append menuitem
-menuitem.show
-
-menuitem = Gtk::MenuItem::new("foo")
-menuitem.set_submenu menu
-menubar.append menuitem
-menuitem.show
-
-menuitem = Gtk::MenuItem::new("bar")
-menuitem.set_submenu menu
-menubar.append menuitem
-menuitem.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width 10
-box1.pack_start box2, TRUE, TRUE, 0
-box2.show
-
-optionmenu = Gtk::OptionMenu::new()
-optionmenu.set_menu create_menu(1)
-optionmenu.set_history 4
-box2.pack_start optionmenu, TRUE, TRUE, 0
-optionmenu.show
-
-separator = Gtk::HSeparator::new()
-box1.pack_start(separator, FALSE, TRUE, 0)
-separator.show
-
-box2 = Gtk::HBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, FALSE, TRUE, 0)
-box2.show
-
-button = Gtk::Button::new("close")
-button.signal_connect("clicked") do
- window.destroy
- exit
-end
-box2.pack_start(button, TRUE, TRUE, 0)
-button.set_flags(Gtk::CAN_DEFAULT);
-button.grab_default
-button.show
-
-window.show
-
-Gtk::main()
diff --git a/ext/gtk/test.xpm b/ext/gtk/test.xpm
deleted file mode 100644
index 9b0d2efdb2..0000000000
--- a/ext/gtk/test.xpm
+++ /dev/null
@@ -1,92 +0,0 @@
-/* XPM */
-static char *openfile[] = {
-/* width height num_colors chars_per_pixel */
-" 20 19 66 2",
-/* colors */
-".. c None",
-".# c #000000",
-".a c #dfdfdf",
-".b c #7f7f7f",
-".c c #006f6f",
-".d c #00efef",
-".e c #009f9f",
-".f c #004040",
-".g c #00bfbf",
-".h c #ff0000",
-".i c #ffffff",
-".j c #7f0000",
-".k c #007070",
-".l c #00ffff",
-".m c #00a0a0",
-".n c #004f4f",
-".o c #00cfcf",
-".p c #8f8f8f",
-".q c #6f6f6f",
-".r c #a0a0a0",
-".s c #7f7f00",
-".t c #007f7f",
-".u c #5f5f5f",
-".v c #707070",
-".w c #00f0f0",
-".x c #009090",
-".y c #ffff00",
-".z c #0000ff",
-".A c #00afaf",
-".B c #00d0d0",
-".C c #00dfdf",
-".D c #005f5f",
-".E c #00b0b0",
-".F c #001010",
-".G c #00c0c0",
-".H c #000f0f",
-".I c #00007f",
-".J c #005050",
-".K c #002f2f",
-".L c #dfcfcf",
-".M c #dfd0d0",
-".N c #006060",
-".O c #00e0e0",
-".P c #00ff00",
-".Q c #002020",
-".R c #dfc0c0",
-".S c #008080",
-".T c #001f1f",
-".U c #003f3f",
-".V c #007f00",
-".W c #00000f",
-".X c #000010",
-".Y c #00001f",
-".Z c #000020",
-".0 c #00002f",
-".1 c #000030",
-".2 c #00003f",
-".3 c #000040",
-".4 c #00004f",
-".5 c #000050",
-".6 c #00005f",
-".7 c #000060",
-".8 c #00006f",
-".9 c #000070",
-"#. c #7f7f80",
-"## c #9f9f9f",
-/* pixels */
-"........................................",
-"........................................",
-"........................................",
-".......................#.#.#............",
-".....................#.......#...#......",
-"...............................#.#......",
-".......#.#.#.................#.#.#......",
-".....#.y.i.y.#.#.#.#.#.#.#..............",
-".....#.i.y.i.y.i.y.i.y.i.#..............",
-".....#.y.i.y.i.y.i.y.i.y.#..............",
-".....#.i.y.i.y.#.#.#.#.#.#.#.#.#.#.#....",
-".....#.y.i.y.#.s.s.s.s.s.s.s.s.s.#......",
-".....#.i.y.#.s.s.s.s.s.s.s.s.s.#........",
-".....#.y.#.s.s.s.s.s.s.s.s.s.#..........",
-".....#.#.s.s.s.s.s.s.s.s.s.#............",
-".....#.#.#.#.#.#.#.#.#.#.#..............",
-"........................................",
-"........................................",
-"........................................"
-};
diff --git a/ext/gtk/test0.rb b/ext/gtk/test0.rb
deleted file mode 100644
index 4ff802d6ca..0000000000
--- a/ext/gtk/test0.rb
+++ /dev/null
@@ -1,13 +0,0 @@
-require 'gtk'
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.border_width(10)
-button = Gtk::Button::new("Hello World")
-button.signal_connect("clicked") do
- print "hello world\n"
- exit
-end
-window.add(button)
-button.show
-window.show
-Gtk::main()
diff --git a/ext/gtk/test1.rb b/ext/gtk/test1.rb
deleted file mode 100644
index 7d24199580..0000000000
--- a/ext/gtk/test1.rb
+++ /dev/null
@@ -1,41 +0,0 @@
-require 'gtk'
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.set_title("entry")
-window.border_width(0)
-
-box1 = Gtk::VBox::new(FALSE, 0)
-window.add(box1)
-box1.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, TRUE, TRUE, 0)
-box2.show
-
-entry = Gtk::Entry::new()
-entry.set_text("hello world")
-box2.pack_start(entry, TRUE, TRUE, 0)
-entry.show
-
-separator = Gtk::HSeparator::new()
-box1.pack_start(separator, FALSE, TRUE, 0)
-separator.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, FALSE, TRUE, 0)
-box2.show
-
-button = Gtk::Button::new("close")
-button.signal_connect("clicked") do
- window.destroy
- exit
-end
-box2.pack_start(button, TRUE, TRUE, 0)
-button.set_flags(Gtk::CAN_DEFAULT);
-button.grab_default
-button.show
-window.show
-
-Gtk::main()
diff --git a/ext/gtk/test2.rb b/ext/gtk/test2.rb
deleted file mode 100644
index 170de96185..0000000000
--- a/ext/gtk/test2.rb
+++ /dev/null
@@ -1,89 +0,0 @@
-require 'gtk'
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.set_title("list")
-window.border_width(0)
-
-box1 = Gtk::VBox::new(FALSE, 0)
-window.add(box1)
-box1.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, TRUE, TRUE, 0)
-box2.show
-
-scrolled_win = Gtk::ScrolledWindow::new()
-scrolled_win.set_policy(Gtk::POLICY_AUTOMATIC,Gtk::POLICY_AUTOMATIC)
-box2.pack_start(scrolled_win, TRUE, TRUE, 0)
-scrolled_win.show
-
-list = Gtk::List::new()
-list.set_selection_mode(Gtk::SELECTION_MULTIPLE)
-list.set_selection_mode(Gtk::SELECTION_BROWSE)
-scrolled_win.add(list)
-list.show
-
-for i in [
- "hello",
- "world",
- "blah",
- "foo",
- "bar",
- "argh",
- "spencer",
- "is a",
- "wussy",
- "programmer",
- ]
- list_item = Gtk::ListItem::new(i)
- list.add(list_item)
- list_item.show
-end
-
-button = Gtk::Button::new("add")
-button.set_flags(Gtk::CAN_FOCUS);
-i = 1
-button.signal_connect("clicked") do
- list_item = Gtk::ListItem::new(format("added item %d", i))
- list.add(list_item)
- list_item.show
- i += 1
-end
-box2.pack_start(button, FALSE, TRUE, 0)
-button.show
-
-button = Gtk::Button::new("remove")
-button.set_flags(Gtk::CAN_FOCUS);
-button.signal_connect("clicked") do
- tmp_list = list.selection
- list.remove_items(tmp_list)
- for i in tmp_list
- i.destroy
- end
-end
-box2.pack_start(button, FALSE, TRUE, 0)
-button.show
-
-separator = Gtk::HSeparator::new()
-box1.pack_start(separator, FALSE, TRUE, 0)
-separator.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, FALSE, TRUE, 0)
-box2.show
-
-button = Gtk::Button::new("close")
-button.signal_connect("clicked") do
- window.destroy
- exit
-end
-box2.pack_start(button, TRUE, TRUE, 0)
-button.set_flags(Gtk::CAN_DEFAULT);
-button.grab_default
-button.show
-
-window.show
-
-Gtk::main()
diff --git a/ext/gtk/test3.rb b/ext/gtk/test3.rb
deleted file mode 100644
index d73f72f9fa..0000000000
--- a/ext/gtk/test3.rb
+++ /dev/null
@@ -1,16 +0,0 @@
-require 'gtk'
-
-window = Gtk::FileSelection::new("file selection dialog")
-window.position(Gtk::WIN_POS_MOUSE)
-window.border_width(0)
-
-window.ok_button.signal_connect("clicked") do
- print window.get_filename, "\n"
-end
-window.cancel_button.signal_connect("clicked") do
- window.destroy
- exit
-end
-window.show
-
-Gtk::main()
diff --git a/ext/gtk/test4.rb b/ext/gtk/test4.rb
deleted file mode 100644
index da0000c420..0000000000
--- a/ext/gtk/test4.rb
+++ /dev/null
@@ -1,77 +0,0 @@
-require 'gtk'
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.set_title("notebook")
-window.border_width(0)
-
-box1 = Gtk::VBox::new(FALSE, 0)
-window.add(box1)
-box1.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, TRUE, TRUE, 0)
-box2.show
-
-notebook = Gtk::Notebook::new()
-notebook.set_tab_pos(Gtk::POS_TOP)
-box2.pack_start(notebook, TRUE, TRUE, 0)
-notebook.show
-
-for i in 1..5
- frame = Gtk::Frame::new(format("Page %d", i))
- frame.border_width(10)
- frame.set_usize(200, 150)
- frame.show
-
- label = Gtk::Label::new(format("Box %d", i))
- frame.add label
- label.show
-
- label = Gtk::Label::new(format("Tab %d", i))
- notebook.append_page frame, label
-end
-
-separator = Gtk::HSeparator::new()
-box1.pack_start(separator, FALSE, TRUE, 0)
-separator.show
-
-box2 = Gtk::HBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, FALSE, TRUE, 0)
-box2.show
-
-button = Gtk::Button::new("close")
-button.signal_connect("clicked") do
- window.destroy
- exit
-end
-box2.pack_start(button, TRUE, TRUE, 0)
-button.set_flags(Gtk::CAN_DEFAULT);
-button.grab_default
-button.show
-
-button = Gtk::Button::new("next")
-button.signal_connect("clicked") do
- notebook.next_page
-end
-box2.pack_start(button, TRUE, TRUE, 0)
-button.show
-
-button = Gtk::Button::new("prev")
-button.signal_connect("clicked") do
- notebook.prev_page
-end
-box2.pack_start(button, TRUE, TRUE, 0)
-button.show
-
-button = Gtk::Button::new("rotate")
-button.signal_connect("clicked") do
- notebook.set_tab_pos((notebook.tab_pos+1)%4)
-end
-box2.pack_start(button, TRUE, TRUE, 0)
-button.show
-
-window.show
-
-Gtk::main()
diff --git a/ext/gtk/test5.rb b/ext/gtk/test5.rb
deleted file mode 100644
index 714232079b..0000000000
--- a/ext/gtk/test5.rb
+++ /dev/null
@@ -1,63 +0,0 @@
-require 'gtk'
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.set_title("buttons")
-window.border_width(0)
-
-box1 = Gtk::VBox::new(FALSE, 0)
-window.add(box1)
-box1.show
-
-table = Gtk::Table::new(3, 3, FALSE)
-table.set_row_spacings(5)
-table.set_col_spacings(5)
-table.border_width(10)
-box1.pack_start(table, TRUE, TRUE, 0)
-table.show
-
-button = []
-0.upto(8) do |i|
- button.push Gtk::Button::new("button"+(i+1))
-end
-0.upto(8) do |i|
- button[i].signal_connect("clicked") do |w|
- if button[i+1].visible?
- button[i+1].hide
- else
- button[i+1].show
- end
- end
- button[i].show
-end
-table.attach(button[0], 0, 1, 0, 1, nil, nil, 0, 0)
-table.attach(button[1], 1, 2, 1, 2, nil, nil, 0, 0)
-table.attach(button[2], 2, 3, 2, 3, nil, nil, 0, 0)
-table.attach(button[3], 0, 1, 2, 3, nil, nil, 0, 0)
-table.attach(button[4], 2, 3, 0, 1, nil, nil, 0, 0)
-table.attach(button[5], 1, 2, 2, 3, nil, nil, 0, 0)
-table.attach(button[6], 1, 2, 0, 1, nil, nil, 0, 0)
-table.attach(button[7], 2, 3, 1, 2, nil, nil, 0, 0)
-table.attach(button[8], 0, 1, 1, 2, nil, nil, 0, 0)
-
-separator = Gtk::HSeparator::new()
-box1.pack_start(separator, FALSE, TRUE, 0)
-separator.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, FALSE, TRUE, 0)
-box2.show
-
-close = Gtk::Button::new("close")
-close.signal_connect("clicked") do
- window.destroy
- exit
-end
-box2.pack_start(close, TRUE, TRUE, 0)
-close.set_flags(Gtk::CAN_DEFAULT);
-close.grab_default
-close.show
-
-window.show
-
-Gtk::main()
diff --git a/ext/gtk/test6.rb b/ext/gtk/test6.rb
deleted file mode 100644
index a589530ab0..0000000000
--- a/ext/gtk/test6.rb
+++ /dev/null
@@ -1,49 +0,0 @@
-require 'gtk'
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.set_title("toggle buttons")
-window.border_width(0)
-
-box1 = Gtk::VBox::new(FALSE, 0)
-window.add(box1)
-box1.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, TRUE, TRUE, 0)
-box2.show
-
-button = Gtk::ToggleButton::new("button1")
-box2.pack_start(button, TRUE, TRUE, 0)
-button.show
-
-button = Gtk::ToggleButton::new("button2")
-box2.pack_start(button, TRUE, TRUE, 0)
-button.show
-
-button = Gtk::ToggleButton::new("button3")
-box2.pack_start(button, TRUE, TRUE, 0)
-button.show
-
-separator = Gtk::HSeparator::new()
-box1.pack_start(separator, FALSE, TRUE, 0)
-separator.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, FALSE, TRUE, 0)
-box2.show
-
-close = Gtk::Button::new("close")
-close.signal_connect("clicked") do
- window.destroy
- exit
-end
-box2.pack_start(close, TRUE, TRUE, 0)
-close.set_flags(Gtk::CAN_DEFAULT);
-close.grab_default
-close.show
-
-window.show
-
-Gtk::main()
diff --git a/ext/gtk/test7.rb b/ext/gtk/test7.rb
deleted file mode 100644
index 4d78648a3c..0000000000
--- a/ext/gtk/test7.rb
+++ /dev/null
@@ -1,49 +0,0 @@
-require 'gtk'
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.set_title("check buttons")
-window.border_width(0)
-
-box1 = Gtk::VBox::new(FALSE, 0)
-window.add(box1)
-box1.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, TRUE, TRUE, 0)
-box2.show
-
-button = Gtk::CheckButton::new("button1")
-box2.pack_start(button, TRUE, TRUE, 0)
-button.show
-
-button = Gtk::CheckButton::new("button2")
-box2.pack_start(button, TRUE, TRUE, 0)
-button.show
-
-button = Gtk::CheckButton::new("button3")
-box2.pack_start(button, TRUE, TRUE, 0)
-button.show
-
-separator = Gtk::HSeparator::new()
-box1.pack_start(separator, FALSE, TRUE, 0)
-separator.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, FALSE, TRUE, 0)
-box2.show
-
-close = Gtk::Button::new("close")
-close.signal_connect("clicked") do
- window.destroy
- exit
-end
-box2.pack_start(close, TRUE, TRUE, 0)
-close.set_flags(Gtk::CAN_DEFAULT);
-close.grab_default
-close.show
-
-window.show
-
-Gtk::main()
diff --git a/ext/gtk/test8.rb b/ext/gtk/test8.rb
deleted file mode 100644
index 4ac4b0b8ad..0000000000
--- a/ext/gtk/test8.rb
+++ /dev/null
@@ -1,49 +0,0 @@
-require 'gtk'
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.set_title("radio buttons")
-window.border_width(0)
-
-box1 = Gtk::VBox::new(FALSE, 0)
-window.add(box1)
-box1.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width 10
-box1.pack_start(box2, TRUE, TRUE, 0)
-box2.show
-
-button = Gtk::RadioButton::new("button1")
-box2.pack_start(button, TRUE, TRUE, 0)
-button.show
-
-button = Gtk::RadioButton::new(button, "button2")
-box2.pack_start(button, TRUE, TRUE, 0)
-button.show
-
-button = Gtk::RadioButton::new(button, "button3")
-box2.pack_start(button, TRUE, TRUE, 0)
-button.show
-
-separator = Gtk::HSeparator::new()
-box1.pack_start(separator, FALSE, TRUE, 0)
-separator.show
-
-box2 = Gtk::VBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, FALSE, TRUE, 0)
-box2.show
-
-close = Gtk::Button::new("close")
-close.signal_connect("clicked") do
- window.destroy
- exit
-end
-box2.pack_start(close, TRUE, TRUE, 0)
-close.set_flags(Gtk::CAN_DEFAULT);
-close.grab_default
-close.show
-
-window.show
-
-Gtk::main()
diff --git a/ext/gtk/test9.rb b/ext/gtk/test9.rb
deleted file mode 100644
index 7bb3bf305e..0000000000
--- a/ext/gtk/test9.rb
+++ /dev/null
@@ -1,98 +0,0 @@
-require 'gtk'
-
-def create_bbox_window(horizontal, title, pos, spacing, cw, ch, layout)
- window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
- window.set_title(title)
- window.signal_connect("destroy") do
- window.destroy
- end
- window.signal_connect("delete_event") do
- window.hide
- window.destroy
- end
- if horizontal
- window.set_usize(550, 60)
- window.set_uposition(150, pos)
- else
- window.set_usize(150, 400)
- window.set_uposition(pos, 200)
- end
- box1 = Gtk::VBox::new(FALSE, 0)
- window.add box1
- box1.show
- if horizontal
- bbox = Gtk::HButtonBox::new()
- else
- bbox = Gtk::VButtonBox::new()
- end
- bbox.set_layout layout
- bbox.set_spacing spacing
- bbox.set_child_size cw, ch
- bbox.show
- box1.border_width 25
- box1.pack_start(bbox, TRUE, TRUE, 0)
- button = Gtk::Button::new("OK")
- bbox.add button
- button.signal_connect("clicked") do
- window.hide
- window.destroy
- end
- button.show
-
- button = Gtk::Button::new("Cancel")
- bbox.add button
- button.signal_connect("clicked") do
- window.hide
- window.destroy
- end
- button.show
-
- button = Gtk::Button::new("Help")
- bbox.add button
- button.show
-
- window.show
-end
-
-def test_hbbox
- create_bbox_window(TRUE, "Spread", 50, 40, 85, 25, Gtk::BUTTONBOX_SPREAD);
- create_bbox_window(TRUE, "Edge", 250, 40, 85, 28, Gtk::BUTTONBOX_EDGE);
- create_bbox_window(TRUE, "Start", 450, 40, 85, 25, Gtk::BUTTONBOX_START);
- create_bbox_window(TRUE, "End", 650, 15, 30, 25, Gtk::BUTTONBOX_END);
-end
-
-def test_vbbox
- create_bbox_window(FALSE, "Spread", 50, 40, 85, 25, Gtk::BUTTONBOX_SPREAD);
- create_bbox_window(FALSE, "Edge", 250, 40, 85, 28, Gtk::BUTTONBOX_EDGE);
- create_bbox_window(FALSE, "Start", 450, 40, 85, 25, Gtk::BUTTONBOX_START);
- create_bbox_window(FALSE, "End", 650, 15, 30, 25, Gtk::BUTTONBOX_END);
-end
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.signal_connect("delete_event") do
- window.destroy
- exit
-end
-window.set_title("button box")
-window.border_width(20)
-
-bbox = Gtk::HButtonBox::new()
-window.add(bbox)
-bbox.show
-
-button = Gtk::Button::new("Horizontal")
-def button.clicked(*args)
- test_hbbox
-end
-bbox.add button
-button.show
-
-button = Gtk::Button::new("Vertical")
-def button.clicked(*args)
- test_vbbox
-end
-bbox.add button
-button.show
-window.show
-
-Gtk::main()
diff --git a/ext/gtk/testa.rb b/ext/gtk/testa.rb
deleted file mode 100644
index 00a6603dfd..0000000000
--- a/ext/gtk/testa.rb
+++ /dev/null
@@ -1,78 +0,0 @@
-require 'gtk'
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.set_title("toolbar test")
-window.set_policy(TRUE, TRUE, TRUE)
-window.signal_connect("destroy") do
- exit
-end
-window.signal_connect("delete_event") do
- exit
-end
-window.border_width(0)
-window.realize
-
-toolbar = Gtk::Toolbar::new(Gtk::ORIENTATION_HORIZONTAL, Gtk::TOOLBAR_BOTH)
-toolbar.append_item "Horizontal", "Horizontal toolbar layout",
- Gtk::Pixmap::new(*Gdk::Pixmap::create_from_xpm(window.window,
- nil,
- #window.style.bg[Gtk::STATE_NORMAL],
- "test.xpm")), nil do
- toolbar.set_orientation Gtk::ORIENTATION_HORIZONTAL
-end
-toolbar.append_item "Vertival", "Vertical toolbar layout",
- Gtk::Pixmap::new(*Gdk::Pixmap::create_from_xpm(window.window,
- nil, #window.style.bg[Gtk::STATE_NORMAL],
- "test.xpm")), nil do
- toolbar.set_orientation Gtk::ORIENTATION_VERTICAL
-end
-toolbar.append_space
-toolbar.append_item "Icons", "Only show toolbar icons",
- Gtk::Pixmap::new(*Gdk::Pixmap::create_from_xpm(window.window,
- nil, #window.style.bg[Gtk::STATE_NORMAL],
- "test.xpm")), nil do
- toolbar.set_style Gtk::TOOLBAR_ICONS
-end
-toolbar.append_item "Text", "Only show toolbar text",
- Gtk::Pixmap::new(*Gdk::Pixmap::create_from_xpm(window.window,
- nil,#window.style.bg[Gtk::STATE_NORMAL],
- "test.xpm")), nil do
- toolbar.set_style Gtk::TOOLBAR_TEXT
-end
-toolbar.append_item "Both", "Show toolbar icons and text",
- Gtk::Pixmap::new(*Gdk::Pixmap::create_from_xpm(window.window,
- nil, #window.style.bg[Gtk::STATE_NORMAL],
- "test.xpm")), nil do
- toolbar.set_style Gtk::TOOLBAR_BOTH
-end
-toolbar.append_space
-toolbar.append_item "Small", "User small spaces",
- Gtk::Pixmap::new(*Gdk::Pixmap::create_from_xpm(window.window,
- nil,#window.style.bg[Gtk::STATE_NORMAL],
- "test.xpm")), nil do
- toolbar.set_space_size 5
-end
-toolbar.append_item "Big", "User big spaces",
- Gtk::Pixmap::new(*Gdk::Pixmap::create_from_xpm(window.window,
- nil,#window.style.bg[Gtk::STATE_NORMAL],
- "test.xpm")), nil do
- toolbar.set_space_size 10
-end
-toolbar.append_space
-toolbar.append_item "Enable", "Enable tooltips",
- Gtk::Pixmap::new(*Gdk::Pixmap::create_from_xpm(window.window,
- nil,#window.style.bg[Gtk::STATE_NORMAL],
- "test.xpm")), nil do
- toolbar.set_tooltips TRUE
-end
-toolbar.append_item "Disable", "Disable tooltips",
- Gtk::Pixmap::new(*Gdk::Pixmap::create_from_xpm(window.window,
- nil,#window.style.bg[Gtk::STATE_NORMAL],
- "test.xpm")), nil do
- toolbar.set_tooltips FALSE
-end
-window.add toolbar
-toolbar.show
-window.show
-
-Gtk::main()
diff --git a/ext/gtk/testb.rb b/ext/gtk/testb.rb
deleted file mode 100644
index 4e707bcf87..0000000000
--- a/ext/gtk/testb.rb
+++ /dev/null
@@ -1,78 +0,0 @@
-require 'gtk'
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.signal_connect("destroy") do
- exit
-end
-window.signal_connect("delete_event") do
- exit
-end
-window.set_title("buttons")
-window.border_width(0)
-
-box1 = Gtk::VBox::new(FALSE, 0)
-window.add box1
-box1.show
-
-box2 = Gtk::HBox::new(FALSE, 5)
-box2.border_width 10
-box1.pack_start box2, TRUE, TRUE, 0
-box2.show
-
-label = Gtk::Label::new("Hello World")
-frame = Gtk::Frame::new("Frame 1")
-box2.pack_start frame, TRUE, TRUE, 0
-frame.show
-
-box3 = Gtk::VBox::new(FALSE, 5)
-box3.border_width 5
-frame.add box3
-box3.show
-
-button = Gtk::Button::new("switch")
-button.signal_connect("clicked") do
- label.reparent box3
-end
-box3.pack_start button, FALSE, TRUE, 0
-button.show
-box3.pack_start label, FALSE, TRUE, 0
-label.show
-
-frame = Gtk::Frame::new("Frame 2")
-box2.pack_start frame, TRUE, TRUE, 0
-frame.show
-
-box4 = Gtk::VBox::new(FALSE, 5)
-box4.border_width 5
-frame.add box4
-box4.show
-
-button = Gtk::Button::new("switch")
-button.signal_connect("clicked") do
- label.reparent box4
-end
-box4.pack_start button, FALSE, TRUE, 0
-button.show
-
-separator = Gtk::HSeparator::new()
-box1.pack_start(separator, FALSE, TRUE, 0)
-separator.show
-
-box2 = Gtk::HBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, FALSE, TRUE, 0)
-box2.show
-
-button = Gtk::Button::new("close")
-button.signal_connect("clicked") do
- window.destroy
- exit
-end
-box2.pack_start(button, TRUE, TRUE, 0)
-button.set_flags(Gtk::CAN_DEFAULT);
-button.grab_default
-button.show
-
-window.show
-
-Gtk::main()
diff --git a/ext/gtk/testc.rb b/ext/gtk/testc.rb
deleted file mode 100644
index 98c6466beb..0000000000
--- a/ext/gtk/testc.rb
+++ /dev/null
@@ -1,64 +0,0 @@
-require 'gtk'
-
-window = Gtk::Window::new(Gtk::WINDOW_TOPLEVEL)
-window.signal_connect("destroy") do
- exit
-end
-window.signal_connect("delete_event") do
- exit
-end
-window.set_title("pixmap")
-window.border_width(0)
-window.realize
-
-box1 = Gtk::VBox::new(FALSE, 0)
-window.add box1
-box1.show
-
-box2 = Gtk::HBox::new(FALSE, 10)
-box2.border_width 10
-box1.pack_start box2, TRUE, TRUE, 0
-box2.show
-
-button = Gtk::Button::new()
-box2.pack_start button, FALSE, FALSE, 0
-button.show
-
-style = button.style
-pixmap, mask = Gdk::Pixmap::create_from_xpm(window.window,
- nil,
- #style.bg[Gtk::STATE_NORMAL],
- "test.xpm")
-pixmapwid = Gtk::Pixmap::new(pixmap, mask)
-label = Gtk::Label::new("Pixmap\ntest")
-box3 = Gtk::HBox::new(FALSE, 0)
-box3.border_width 2
-box3.add pixmapwid
-box3.add label
-button.add box3
-pixmapwid.show
-label.show
-box3.show
-
-separator = Gtk::HSeparator::new()
-box1.pack_start(separator, FALSE, TRUE, 0)
-separator.show
-
-box2 = Gtk::HBox::new(FALSE, 10)
-box2.border_width(10)
-box1.pack_start(box2, FALSE, TRUE, 0)
-box2.show
-
-button = Gtk::Button::new("close")
-button.signal_connect("clicked") do
- window.destroy
- exit
-end
-box2.pack_start(button, TRUE, TRUE, 0)
-button.set_flags(Gtk::CAN_DEFAULT);
-button.grab_default
-button.show
-
-window.show
-
-Gtk::main()
diff --git a/ext/marshal/MANIFEST b/ext/marshal/MANIFEST
deleted file mode 100644
index 54870ec71f..0000000000
--- a/ext/marshal/MANIFEST
+++ /dev/null
@@ -1,5 +0,0 @@
-MANIFEST
-depend
-extconf.rb
-marshal.c
-marshal.doc
diff --git a/ext/marshal/depend b/ext/marshal/depend
deleted file mode 100644
index c955eb2d59..0000000000
--- a/ext/marshal/depend
+++ /dev/null
@@ -1,2 +0,0 @@
-marshal.o: marshal.c ../../ruby.h ../../config.h ../../defines.h ../../io.h \
- ../../st.h
diff --git a/ext/marshal/extconf.rb b/ext/marshal/extconf.rb
deleted file mode 100644
index ab30bd117b..0000000000
--- a/ext/marshal/extconf.rb
+++ /dev/null
@@ -1 +0,0 @@
-create_makefile("marshal")
diff --git a/ext/marshal/marshal.c b/ext/marshal/marshal.c
deleted file mode 100644
index 99e87d0b5f..0000000000
--- a/ext/marshal/marshal.c
+++ /dev/null
@@ -1,850 +0,0 @@
-/************************************************
-
- marshal.c -
-
- $Author$
- $Revision$
- $Date$
- created at: Thu Apr 27 16:30:01 JST 1995
-
-************************************************/
-
-#include "ruby.h"
-#include "io.h"
-#include "st.h"
-
-#define MARSHAL_MAJOR 4
-#define MARSHAL_MINOR 0
-
-#define TYPE_NIL '0'
-#define TYPE_TRUE 'T'
-#define TYPE_FALSE 'F'
-#define TYPE_FIXNUM 'i'
-
-#define TYPE_UCLASS 'C'
-#define TYPE_OBJECT 'o'
-#define TYPE_USERDEF 'u'
-#define TYPE_FLOAT 'f'
-#define TYPE_BIGNUM 'l'
-#define TYPE_STRING '"'
-#define TYPE_REGEXP '/'
-#define TYPE_ARRAY '['
-#define TYPE_HASH '{'
-#define TYPE_STRUCT 'S'
-#define TYPE_MODULE 'M'
-
-#define TYPE_SYMBOL ':'
-#define TYPE_SYMLINK ';'
-
-#define TYPE_LINK '@'
-
-extern VALUE cString;
-extern VALUE cRegexp;
-extern VALUE cArray;
-extern VALUE cHash;
-
-VALUE rb_path2class();
-
-static ID s_dump, s_load;
-
-struct dump_arg {
- VALUE obj;
- FILE *fp;
- VALUE str;
- st_table *symbol;
- st_table *data;
-};
-
-struct dump_call_arg {
- VALUE obj;
- struct dump_arg *arg;
- int limit;
-};
-
-static void w_long _((long, struct dump_arg*));
-
-static void
-w_byte(c, arg)
- char c;
- struct dump_arg *arg;
-{
- if (arg->fp) putc(c, arg->fp);
- else str_cat(arg->str, (UCHAR*)&c, 1);
-}
-
-static void
-w_bytes(s, n, arg)
- char *s;
- int n;
- struct dump_arg *arg;
-{
- w_long(n, arg);
- if (arg->fp) {
- fwrite(s, 1, n, arg->fp);
- }
- else {
- str_cat(arg->str, s, n);
- }
-}
-
-static void
-w_short(x, arg)
- int x;
- struct dump_arg *arg;
-{
- int i;
-
- for (i=0; i<sizeof(USHORT); i++) {
- w_byte((x >> (i*8)) & 0xff, arg);
- }
-}
-
-static void
-w_long(x, arg)
- long x;
- struct dump_arg *arg;
-{
- char buf[sizeof(long)+1];
- int i, len = 0;
-
- if (x == 0) {
- w_byte(0, arg);
- return;
- }
- for (i=1;i<sizeof(long)+1;i++) {
- buf[i] = x & 0xff;
- x = RSHIFT(x,8);
- if (x == 0) {
- buf[0] = i;
- break;
- }
- if (x == -1) {
- buf[0] = -i;
- break;
- }
- }
- len = i;
- for (i=0;i<=len;i++) {
- w_byte(buf[i], arg);
- }
-}
-
-static void
-w_float(d, arg)
- double d;
- struct dump_arg *arg;
-{
- char buf[100];
-
- sprintf(buf, "%.12g", d);
- w_bytes(buf, strlen(buf), arg);
-}
-
-static void
-w_symbol(id, arg)
- ID id;
- struct dump_arg *arg;
-{
- char *sym = rb_id2name(id);
- int num;
-
- if (st_lookup(arg->symbol, id, &num)) {
- w_byte(TYPE_SYMLINK, arg);
- w_long(num, arg);
- }
- else {
- w_byte(TYPE_SYMBOL, arg);
- w_bytes(sym, strlen(sym), arg);
- st_insert(arg->symbol, id, arg->symbol->num_entries);
- }
-}
-
-static void
-w_unique(s, arg)
- char *s;
- struct dump_arg *arg;
-{
- w_symbol(rb_intern(s), arg);
-}
-
-static void w_object _((VALUE,struct dump_arg*,int));
-extern VALUE cIO, cBignum, cStruct;
-
-static int
-hash_each(key, value, arg)
- VALUE key, value;
- struct dump_call_arg *arg;
-{
- w_object(key, arg->arg, arg->limit);
- w_object(value, arg->arg, arg->limit);
- return ST_CONTINUE;
-}
-
-static int
-obj_each(id, value, arg)
- ID id;
- VALUE value;
- struct dump_call_arg *arg;
-{
- w_symbol(id, arg->arg);
- w_object(value, arg->arg, arg->limit);
- return ST_CONTINUE;
-}
-
-static void
-w_uclass(obj, class, arg)
- VALUE obj, class;
- struct dump_arg *arg;
-{
- if (CLASS_OF(obj) != class) {
- w_byte(TYPE_UCLASS, arg);
- w_unique(rb_class2name(CLASS_OF(obj)), arg);
- }
-}
-
-static void
-w_object(obj, arg, limit)
- VALUE obj;
- struct dump_arg *arg;
- int limit;
-{
- int n;
- struct dump_call_arg c_arg;
-
- if (limit == 0) {
- Fail("exceed depth limit");
- }
- limit--;
- c_arg.limit = limit;
- c_arg.arg = arg;
-
- if (obj == Qnil) {
- w_byte(TYPE_NIL, arg);
- }
- else if (obj == TRUE) {
- w_byte(TYPE_TRUE, arg);
- }
- else if (obj == FALSE) {
- w_byte(TYPE_FALSE, arg);
- }
- else if (FIXNUM_P(obj)) {
-#if SIZEOF_LONG <= 4
- w_byte(TYPE_FIXNUM, arg);
- w_long(FIX2INT(obj), arg);
-#else
- if (RSHIFT(obj, 32) == 0 || RSHIFT(obj, 32) == -1) {
- w_byte(TYPE_FIXNUM, arg);
- w_long(FIX2INT(obj), arg);
- }
- else {
- obj = int2big(FIX2INT(obj));
- goto write_bignum;
- }
-#endif
- }
- else {
- int num;
-
- if (st_lookup(arg->data, obj, &num)) {
- w_byte(TYPE_LINK, arg);
- w_long(num, arg);
- return;
- }
- st_insert(arg->data, obj, arg->data->num_entries);
- if (rb_respond_to(obj, s_dump)) {
- VALUE v;
-
- w_byte(TYPE_USERDEF, arg);
- w_unique(rb_class2name(CLASS_OF(obj)), arg);
- v = rb_funcall(obj, s_dump, 1, limit);
- if (TYPE(v) != T_STRING) {
- TypeError("_dump_to must return String");
- }
- w_bytes(RSTRING(v)->ptr, RSTRING(v)->len, arg);
- return;
- }
-
- switch (BUILTIN_TYPE(obj)) {
- case T_MODULE:
- case T_CLASS:
- w_byte(TYPE_MODULE, arg);
- {
- VALUE path = rb_class_path(obj);
- w_bytes(RSTRING(path)->ptr, RSTRING(path)->len, arg);
- }
- return;
-
- case T_FLOAT:
- w_byte(TYPE_FLOAT, arg);
- w_float(RFLOAT(obj)->value, arg);
- return;
-
- case T_BIGNUM:
- write_bignum:
- w_byte(TYPE_BIGNUM, arg);
- {
- char sign = RBIGNUM(obj)->sign?'+':'-';
- int len = RBIGNUM(obj)->len;
- USHORT *d = RBIGNUM(obj)->digits;
-
- w_byte(sign, arg);
- w_long(len, arg);
- while (len--) {
- w_short(*d, arg);
- d++;
- }
- }
- return;
-
- case T_STRING:
- w_uclass(obj, cString, arg);
- w_byte(TYPE_STRING, arg);
- w_bytes(RSTRING(obj)->ptr, RSTRING(obj)->len, arg);
- return;
-
- case T_REGEXP:
- w_uclass(obj, cRegexp, arg);
- w_byte(TYPE_REGEXP, arg);
- w_bytes(RREGEXP(obj)->str, RREGEXP(obj)->len, arg);
- w_byte(FL_TEST(obj, FL_USER1), arg);
- return;
-
- case T_ARRAY:
- w_uclass(obj, cArray, arg);
- w_byte(TYPE_ARRAY, arg);
- {
- int len = RARRAY(obj)->len;
- VALUE *ptr = RARRAY(obj)->ptr;
-
- w_long(len, arg);
- while (len--) {
- w_object(*ptr, arg, limit);
- ptr++;
- }
- }
- break;
-
- case T_HASH:
- w_uclass(obj, cHash, arg);
- w_byte(TYPE_HASH, arg);
- w_long(RHASH(obj)->tbl->num_entries, arg);
- st_foreach(RHASH(obj)->tbl, hash_each, &c_arg);
- break;
-
- case T_STRUCT:
- w_byte(TYPE_STRUCT, arg);
- {
- int len = RSTRUCT(obj)->len;
- char *path = rb_class2name(CLASS_OF(obj));
- VALUE mem;
- int i;
-
- w_unique(path, arg);
- w_long(len, arg);
- mem = rb_ivar_get(CLASS_OF(obj), rb_intern("__member__"));
- if (mem == Qnil) {
- Fatal("non-initialized struct");
- }
- for (i=0; i<len; i++) {
- w_symbol(FIX2INT(RARRAY(mem)->ptr[i]), arg);
- w_object(RSTRUCT(obj)->ptr[i], arg, limit);
- }
- }
- break;
-
- case T_OBJECT:
- w_byte(TYPE_OBJECT, arg);
- {
- VALUE class = CLASS_OF(obj);
- char *path;
-
- if (FL_TEST(class, FL_SINGLETON)) {
- TypeError("singleton can't be dumped");
- }
- path = rb_class2name(class);
- w_unique(path, arg);
- if (ROBJECT(obj)->iv_tbl) {
- w_long(ROBJECT(obj)->iv_tbl->num_entries, arg);
- st_foreach(ROBJECT(obj)->iv_tbl, obj_each, &c_arg);
- }
- else {
- w_long(0, arg);
- }
- }
- break;
-
- default:
- TypeError("can't dump %s", rb_class2name(CLASS_OF(obj)));
- break;
- }
- }
-}
-
-static VALUE
-dump(arg)
- struct dump_call_arg *arg;
-{
- w_object(arg->obj, arg->arg, arg->limit);
-}
-
-static VALUE
-dump_ensure(arg)
- struct dump_arg *arg;
-{
- st_free_table(arg->symbol);
- st_free_table(arg->data);
-}
-
-static VALUE
-marshal_dump(argc, argv)
- int argc;
- VALUE argv;
-{
- VALUE obj, port, a1, a2;
- int limit = -1;
- extern VALUE cIO;
- struct dump_arg arg;
- struct dump_call_arg c_arg;
-
- port = 0;
- rb_scan_args(argc, argv, "12", &obj, &a1, &a2);
- if (argc == 3) {
- limit = NUM2INT(a2);
- port = a1;
- }
- else if (argc == 2) {
- if (FIXNUM_P(a1)) limit = FIX2INT(a1);
- else port = a1;
- }
- if (port) {
- if (obj_is_kind_of(port, cIO)) {
- OpenFile *fptr;
-
- io_binmode(port);
- GetOpenFile(port, fptr);
- io_writable(fptr);
- arg.fp = (fptr->f2) ? fptr->f2 : fptr->f;
- }
- else {
- TypeError("instance of IO needed");
- }
- }
- else {
- arg.fp = 0;
- port = str_new(0, 0);
- arg.str = port;
- }
-
- arg.symbol = st_init_numtable();
- arg.data = st_init_numtable();
- c_arg.obj = obj;
- c_arg.arg = &arg;
- c_arg.limit = limit;
-
- w_byte(MARSHAL_MAJOR, &arg);
- w_byte(MARSHAL_MINOR, &arg);
-
- rb_ensure(dump, &c_arg, dump_ensure, &arg);
-
- return port;
-}
-
-struct load_arg {
- FILE *fp;
- UCHAR *ptr, *end;
- st_table *symbol;
- st_table *data;
-};
-
-static int
-r_byte(arg)
- struct load_arg *arg;
-{
- if (arg->fp) return getc(arg->fp);
- if (arg->ptr < arg->end) return *arg->ptr++;
- return EOF;
-}
-
-static USHORT
-r_short(arg)
- struct load_arg *arg;
-{
- USHORT x;
- int i;
-
- x = 0;
- for (i=0; i<sizeof(USHORT); i++) {
- x |= r_byte(arg)<<(i*8);
- }
-
- return x;
-}
-
-static void
-long_toobig(size)
- int size;
-{
- TypeError("long too big for this architecture (size %d, given %d)",
- sizeof(long), size);
-}
-
-static long
-r_long(arg)
- struct load_arg *arg;
-{
- int c = r_byte(arg), i;
- register long x;
-
- if (c == 0) return 0;
- if (c > 0) {
- if (c > sizeof(long)) long_toobig((int)c);
- x = 0;
- for (i=0;i<c;i++) {
- x |= (long)r_byte(arg) << (8*i);
- }
- }
- else if (c < 0) {
- c = -c;
- if (c > sizeof(long)) long_toobig((int)c);
- x = -1;
- for (i=0;i<c;i++) {
- x &= ~(0xff << (8*i));
- x |= (long)r_byte(arg) << (8*i);
- }
- }
- return x;
-}
-
-#define r_bytes(s, arg) \
- (s = (char*)r_long(arg), r_bytes0(&s,ALLOCA_N(char,(long)s),(long)s,arg))
-
-static int
-r_bytes0(sp, s, len, arg)
- char **sp, *s;
- int len;
- struct load_arg *arg;
-{
- if (arg->fp) {
- len = fread(s, 1, len, arg->fp);
- }
- else {
- if (arg->ptr + len > arg->end) {
- len = arg->end - arg->ptr;
- }
- memcpy(s, arg->ptr, len);
- arg->ptr += len;
- }
-
- (s)[len] = '\0';
- *sp = s;
-
- return len;
-}
-
-static ID
-r_symbol(arg)
- struct load_arg *arg;
-{
- char *buf;
- ID id;
- char type;
-
- if (r_byte(arg) == TYPE_SYMLINK) {
- int num = r_long(arg);
-
- if (st_lookup(arg->symbol, num, &id)) {
- return id;
- }
- TypeError("bad symbol");
- }
- r_bytes(buf, arg);
- id = rb_intern(buf);
- st_insert(arg->symbol, arg->symbol->num_entries, id);
-
- return id;
-}
-
-static char*
-r_unique(arg)
- struct load_arg *arg;
-{
- return rb_id2name(r_symbol(arg));
-}
-
-static VALUE
-r_string(arg)
- struct load_arg *arg;
-{
- char *buf;
- int len = r_bytes(buf, arg);
-
- return str_taint(str_new(buf, len));
-}
-
-static VALUE
-r_regist(v, arg)
- VALUE v;
- struct load_arg *arg;
-{
- st_insert(arg->data, arg->data->num_entries, v);
- return v;
-}
-
-static VALUE
-r_object(arg)
- struct load_arg *arg;
-{
- VALUE v;
- int type = r_byte(arg);
-
- switch (type) {
- case EOF:
- eof_error();
- return Qnil;
-
- case TYPE_LINK:
- if (st_lookup(arg->data, r_long(arg), &v)) {
- return v;
- }
- ArgError("dump format error (unlinked)");
- break;
-
- case TYPE_UCLASS:
- {
- VALUE c = rb_path2class(r_unique(arg));
- v = r_object(arg);
- if (rb_special_const_p(v)) {
- ArgError("dump format error (user class)");
- }
- RBASIC(v)->class = c;
- return v;
- }
-
- case TYPE_NIL:
- return Qnil;
-
- case TYPE_TRUE:
- return TRUE;
-
- case TYPE_FALSE:
- return FALSE;
-
- case TYPE_FIXNUM:
- {
- int i = r_long(arg);
- return INT2FIX(i);
- }
-
- case TYPE_FLOAT:
- {
-#ifndef atof
- double atof();
-#endif
- char *buf;
-
- r_bytes(buf, arg);
- v = float_new(atof(buf));
- return r_regist(v, arg);
- }
-
- case TYPE_BIGNUM:
- {
- int len;
- USHORT *digits;
-
- NEWOBJ(big, struct RBignum);
- OBJSETUP(big, cBignum, T_BIGNUM);
- big->sign = (r_byte(arg) == '+');
- big->len = len = r_long(arg);
- big->digits = digits = ALLOC_N(USHORT, len);
- while (len--) {
- *digits++ = r_short(arg);
- }
- big = RBIGNUM(big_norm((VALUE)big));
- if (TYPE(big) == T_BIGNUM) {
- r_regist(big, arg);
- }
- return (VALUE)big;
- }
-
- case TYPE_STRING:
- return r_regist(r_string(arg), arg);
-
- case TYPE_REGEXP:
- {
- char *buf;
- int len = r_bytes(buf, arg);
- int ci = r_byte(arg);
- return r_regist(reg_new(buf, len, ci), arg);
- }
-
- case TYPE_ARRAY:
- {
- volatile int len = r_long(arg);
- v = ary_new2(len);
- r_regist(v, arg);
- while (len--) {
- ary_push(v, r_object(arg));
- }
- return v;
- }
-
- case TYPE_HASH:
- {
- int len = r_long(arg);
-
- v = hash_new();
- r_regist(v, arg);
- while (len--) {
- VALUE key = r_object(arg);
- VALUE value = r_object(arg);
- hash_aset(v, key, value);
- }
- return v;
- }
-
- case TYPE_STRUCT:
- {
- VALUE class, mem, values;
- int i, len;
- int num = arg->data->num_entries;
-
- class = rb_path2class(r_unique(arg));
- mem = rb_ivar_get(class, rb_intern("__member__"));
- if (mem == Qnil) {
- Fatal("non-initialized struct");
- }
- len = r_long(arg);
-
- values = ary_new2(len);
- for (i=0; i<len; i++) {
- ary_push(values, Qnil);
- }
- v = struct_alloc(class, values);
- r_regist(v, arg);
- for (i=0; i<len; i++) {
- ID slot = r_symbol(arg);
- if (RARRAY(mem)->ptr[i] != INT2FIX(slot))
- TypeError("struct not compatible");
- struct_aset(v, INT2FIX(i), r_object(arg));
- }
- return v;
- }
- break;
-
- case TYPE_USERDEF:
- {
- VALUE class;
- int len;
-
- class = rb_path2class(r_unique(arg));
- if (rb_respond_to(class, s_load)) {
- v = rb_funcall(class, s_load, 1, r_string(arg));
- return r_regist(v, arg);
- }
- TypeError("class %s needs to have method `_load_from'",
- rb_class2name(class));
- }
- break;
-
- case TYPE_OBJECT:
- {
- VALUE class;
- int len;
-
- class = rb_path2class(r_unique(arg));
- len = r_long(arg);
- v = obj_alloc(class);
- r_regist(v, arg);
- if (len > 0) {
- while (len--) {
- ID id = r_symbol(arg);
- VALUE val = r_object(arg);
- rb_ivar_set(v, id, val);
- }
- }
- return v;
- }
- break;
-
- case TYPE_MODULE:
- {
- char *buf;
- r_bytes(buf, arg);
- return rb_path2class(buf);
- }
-
- default:
- ArgError("dump format error(0x%x)", type);
- break;
- }
-}
-
-static VALUE
-load(arg)
- struct load_arg *arg;
-{
- return r_object(arg);
-}
-
-static VALUE
-load_ensure(arg)
- struct load_arg *arg;
-{
- st_free_table(arg->symbol);
- st_free_table(arg->data);
-}
-
-static VALUE
-marshal_load(self, port)
- VALUE self, port;
-{
- FILE *fp;
- int major;
- VALUE v;
- OpenFile *fptr;
- struct load_arg arg;
-
- if (TYPE(port) == T_STRING) {
- arg.fp = 0;
- arg.ptr = RSTRING(port)->ptr;
- arg.end = arg.ptr + RSTRING(port)->len;
- }
- else {
- if (obj_is_kind_of(port, cIO)) {
- io_binmode(port);
- GetOpenFile(port, fptr);
- io_readable(fptr);
- arg.fp = fptr->f;
- }
- else {
- TypeError("instance of IO needed");
- }
- }
-
- major = r_byte(&arg);
- if (major == MARSHAL_MAJOR) {
- if (r_byte(&arg) != MARSHAL_MINOR) {
- Warning("Old marshal file format (can be read)");
- }
- arg.symbol = st_init_numtable();
- arg.data = st_init_numtable();
- v = rb_ensure(load, &arg, load_ensure, &arg);
- }
- else {
- TypeError("Old marshal file format (can't read)");
- }
-
- return v;
-}
-
-Init_marshal()
-{
- VALUE mMarshal = rb_define_module("Marshal");
-
- s_dump = rb_intern("_dump_to");
- s_load = rb_intern("_load_from");
- rb_define_module_function(mMarshal, "dump", marshal_dump, -1);
- rb_define_module_function(mMarshal, "load", marshal_load, 1);
- rb_define_module_function(mMarshal, "restore", marshal_load, 1);
-}
diff --git a/ext/marshal/marshal.doc b/ext/marshal/marshal.doc
deleted file mode 100644
index 7529e7942f..0000000000
--- a/ext/marshal/marshal.doc
+++ /dev/null
@@ -1,48 +0,0 @@
-.\" marshal.doc - -*- Indented-Text -*- created at: Tue May 16 12:18:08 JST 1995
-
-** Marshal(モジュール)
-
-rubyオブジェクトをファイルに書き出したり,読みも度したりする機能を提供
-するモジュール.大部分のクラスのインスタンスを書き出す事ができるが,ファ
-イルへの不可能なクラスも存在し(例:IO),そのようなクラスを書き出そうと
-すると例外を発生させる.
-
-Methods:
-Single Methods:
-
- dump(obj, port[, limit])
-
- objを再帰的にファイルに書き出す.ファイルに書き出せないクラスのイ
- ンスタンスをファイルに書き出そうとすると例外を発生させる.ファイル
- に書き出せないクラスは以下の通り.
-
- Class, Module, Data
-
- また,これらのクラスを間接的に指すクラス(例えばIOのサブクラス)など
- も書き出せない.portはIO(またはそのサブクラス)のインスタンスを指定
- する.
-
- 出力するオブジェクトがメソッド`_dump_to'を定義している場合には,ファ
- イル出力はそのメソッドを使って行われる.メソッド`_dump_to'は引数と
- して出力先のファイルオブジェクトを受け取る.インスタンスがメソッド
- `_dump_to'を持つクラスは必ず同じフォーマットを読み戻す特異メソッド
- `_load_from'を定義する必要がある.
-
- limitを指定した場合,limit段以上深くリンクしたオブジェクトをダンプ
- できない(デフォルトは100レベル)。負のlimitを指定すると深さチェック
- を行わない。
-
- dumps(obj)
-
- dump()がファイルに書き出すのと同じ内容を含む文字列を返す.
-
- load(port)
-
- portからオブジェクトを読み込んで来て,元のオブジェクトと同じ状態を
- もつオブジェクトを生成する.portは文字列かIO(またはそのサブクラス)
- のインスタンスである.
-
--------------------------------------------------------
-Local variables:
-fill-column: 70
-end:
diff --git a/ext/socket/socket.c b/ext/socket/socket.c
index f5d191b056..a4e4c40e52 100644
--- a/ext/socket/socket.c
+++ b/ext/socket/socket.c
@@ -821,7 +821,7 @@ udp_addrsetup(host, port, addr)
setipaddr(RSTRING(host)->ptr, addr);
}
if (FIXNUM_P(port)) {
- addr->sin_port = FIX2INT(port);
+ addr->sin_port = htons(FIX2INT(port));
}
else {
struct servent *servent;
diff --git a/ext/tcltklib/extconf.rb b/ext/tcltklib/extconf.rb
index 26e7fe7b09..bb7327db0b 100644
--- a/ext/tcltklib/extconf.rb
+++ b/ext/tcltklib/extconf.rb
@@ -1,9 +1,14 @@
# extconf.rb for tcltklib
+require 'mkmf'
+
have_library("socket", "socket")
have_library("nsl", "gethostbyname")
+have_library("dl", "dlopen")
+have_library("m", "log")
-def search_file(var, include, *path)
+$includes = []
+def search_header(include, *path)
pwd = Dir.getwd
begin
for i in path.reverse!
@@ -12,8 +17,10 @@ def search_file(var, include, *path)
Dir.chdir path
files = Dir[include]
if files.size > 0
- var << path
- return files.pop
+ unless $includes.include? path
+ $includes << path
+ end
+ return
end
end
end
@@ -22,58 +29,56 @@ def search_file(var, include, *path)
end
end
-$includes = []
-search_file($includes,
- "tcl.h",
- "/usr/include/tcl*",
- "/usr/include",
- "/usr/local/include/tcl*",
- "/usr/local/include")
-search_file($includes,
- "tk.h",
- "/usr/include/tk*",
- "/usr/include",
- "/usr/local/include/tk*",
- "/usr/local/include")
-search_file($includes,
- "X11/Xlib.h",
- "/usr/include",
- "/usr/X11*/include",
- "/usr/include",
- "/usr/X11*/include")
+search_header("tcl.h",
+ "/usr/include/tcl*",
+ "/usr/include",
+ "/usr/local/include/tcl*",
+ "/usr/local/include")
+search_header("tk.h",
+ "/usr/include/tk*",
+ "/usr/include",
+ "/usr/local/include/tk*",
+ "/usr/local/include")
+search_header("X11/Xlib.h",
+ "/usr/include",
+ "/usr/X11*/include",
+ "/usr/include",
+ "/usr/X11*/include")
$CFLAGS = "-Wall " + $includes.collect{|path| "-I" + path}.join(" ")
$libraries = []
-tcllibfile = search_file($libraries,
- "libtcl{,7*,8*}.{a,so}",
- "/usr/lib",
- "/usr/local/lib")
-if tcllibfile
- tcllibfile.sub!(/^lib/, '')
- tcllibfile.sub!(/\.(a|so)$/, '')
-end
-tklibfile = search_file($libraries,
- "libtk{,4*,8*}.{a,so}",
- "/usr/lib",
- "/usr/local/lib")
-if tklibfile
- tklibfile.sub!(/^lib/, '')
- tklibfile.sub!(/\.(a|so)$/, '')
+def search_lib(file, func, *path)
+ for i in path.reverse!
+ dir = Dir[i]
+ for path in dir
+ $LDFLAGS = $libraries.collect{|p| "-L" + p}.join(" ") + " -L" + path
+ files = Dir[path+"/"+file]
+ if files.size > 0
+ for lib in files
+ lib = File::basename(lib)
+ lib.sub!(/^lib/, '')
+ lib.sub!(/\.(a|so)$/, '')
+ if have_library(lib, func)
+ unless $libraries.include? path
+ $libraries << path
+ end
+ return TRUE
+ end
+ end
+ end
+ end
+ end
+ return FALSE;
end
-search_file($libraries,
- "libX11.{a,so}",
- "/usr/lib",
- "/usr/X11*/lib")
-$LDFLAGS = $libraries.collect{|path| "-L" + path}.join(" ")
-
-have_library("dl", "dlopen")
-if have_header("tcl.h") &&
- have_header("tk.h") &&
- have_library("X11", "XOpenDisplay") &&
- have_library("m", "log") &&
- have_library(tcllibfile, "Tcl_FindExecutable") &&
- have_library(tklibfile, "Tk_Init")
+if have_header("tcl.h") && have_header("tk.h") &&
+ search_lib("libX11.{a,so}", "XOpenDisplay",
+ "/usr/lib", "/usr/X11*/lib") &&
+ search_lib("libtcl{,7*,8*}.{a,so}", "Tcl_FindExecutable",
+ "/usr/lib", "/usr/local/lib") &&
+ search_lib("libtk{,4*,8*}.{a,so}", "Tk_Init",
+ "/usr/lib", "/usr/local/lib")
+ $LDFLAGS = $libraries.collect{|path| "-L" + path}.join(" ")
create_makefile("tcltklib")
end
diff --git a/file.c b/file.c
index b60ec65d55..b189a239cb 100644
--- a/file.c
+++ b/file.c
@@ -6,7 +6,7 @@
$Date$
created at: Mon Nov 15 12:24:34 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -46,6 +46,7 @@ struct timeval {
char *strrchr();
#endif
+#include <sys/types.h>
#include <sys/stat.h>
#ifndef NT
@@ -77,10 +78,10 @@ file_open(fname, mode)
}
static VALUE
-file_s_open(argc, argv, class)
+file_s_open(argc, argv, klass)
int argc;
VALUE *argv;
- VALUE class;
+ VALUE klass;
{
VALUE fname, vmode, file;
char *mode;
@@ -96,7 +97,7 @@ file_s_open(argc, argv, class)
}
file = file_open(RSTRING(fname)->ptr, mode);
- RBASIC(file)->class = class;
+ RBASIC(file)->klass = klass;
if (iterator_p()) {
rb_ensure(rb_yield, file, io_close, file);
}
@@ -136,8 +137,7 @@ file_reopen(argc, argv, file)
if (!fptr->f) {
fptr->f = rb_fopen(RSTRING(fname)->ptr, mode);
if (fptr->f2) {
- if (fileno(fptr->f2) < 3) /* need to keep stdio */
- fclose(fptr->f2);
+ fclose(fptr->f2);
fptr->f2 = NULL;
}
return file;
@@ -186,7 +186,7 @@ file_tell(obj)
long pos;
GetOpenFile(obj, fptr);
-
+ io_check_closed(fptr);
pos = ftell(fptr->f);
if (ferror(fptr->f) != 0) rb_sys_fail(0);
@@ -201,7 +201,7 @@ file_seek(obj, offset, ptrname)
long pos;
GetOpenFile(obj, fptr);
-
+ io_check_closed(fptr);
pos = fseek(fptr->f, NUM2INT(offset), NUM2INT(ptrname));
if (pos != 0) rb_sys_fail(0);
clearerr(fptr->f);
@@ -217,6 +217,7 @@ file_set_pos(obj, offset)
long pos;
GetOpenFile(obj, fptr);
+ io_check_closed(fptr);
pos = fseek(fptr->f, NUM2INT(offset), 0);
if (pos != 0) rb_sys_fail(0);
clearerr(fptr->f);
@@ -231,6 +232,7 @@ file_rewind(obj)
OpenFile *fptr;
GetOpenFile(obj, fptr);
+ io_check_closed(fptr);
if (fseek(fptr->f, 0L, 0) != 0) rb_sys_fail(0);
clearerr(fptr->f);
@@ -244,6 +246,7 @@ file_eof(obj)
OpenFile *fptr;
GetOpenFile(obj, fptr);
+ io_check_closed(fptr);
if (feof(fptr->f) == 0) return FALSE;
return TRUE;
}
@@ -255,17 +258,10 @@ file_path(obj)
OpenFile *fptr;
GetOpenFile(obj, fptr);
+ if (fptr->path == NULL) return Qnil;
return str_new2(fptr->path);
}
-static VALUE
-file_isatty(obj)
- VALUE obj;
-{
- return FALSE;
-}
-
-#include <sys/types.h>
#ifndef NT
#include <sys/file.h>
#else
@@ -305,6 +301,28 @@ stat_new(st)
time_new(st->st_ctime, 0));
}
+static int
+rb_stat(file, st)
+ VALUE file;
+ struct stat *st;
+{
+ OpenFile *fptr;
+
+ switch (TYPE(file)) {
+ case T_STRING:
+ Check_SafeStr(file);
+ return stat(RSTRING(file)->ptr, st);
+ break;
+ case T_FILE:
+ GetOpenFile(file, fptr);
+ return fstat(fileno(fptr->f), st);
+ break;
+ default:
+ Check_Type(file, T_STRING);
+ }
+ return -1; /* not reached */
+}
+
static VALUE
file_s_stat(obj, fname)
VALUE obj, fname;
@@ -345,7 +363,7 @@ file_s_lstat(obj, fname)
}
return stat_new(&st);
#else
- rb_notimplement();
+ rb_notimplement();
#endif
}
@@ -358,12 +376,13 @@ file_lstat(obj)
struct stat st;
GetOpenFile(obj, fptr);
+ io_check_closed(fptr);
if (lstat(fptr->path, &st) == -1) {
rb_sys_fail(fptr->path);
}
return stat_new(&st);
#else
- rb_notimplement();
+ rb_notimplement();
#endif
}
@@ -446,8 +465,7 @@ test_d(obj, fname)
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0) return FALSE;
+ if (rb_stat(fname, &st) < 0) return FALSE;
if (S_ISDIR(st.st_mode)) return TRUE;
return FALSE;
}
@@ -463,8 +481,7 @@ test_p(obj, fname)
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0) return FALSE;
+ if (rb_stat(fname, &st) < 0) return FALSE;
if (S_ISFIFO(st.st_mode)) return TRUE;
#endif
@@ -521,8 +538,7 @@ test_S(obj, fname)
#ifdef S_ISSOCK
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0) return FALSE;
+ if (rb_stat(fname, &st) < 0) return FALSE;
if (S_ISSOCK(st.st_mode)) return TRUE;
#endif
@@ -544,8 +560,7 @@ test_b(obj, fname)
#ifdef S_ISBLK
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0) return FALSE;
+ if (rb_stat(fname, &st) < 0) return FALSE;
if (S_ISBLK(st.st_mode)) return TRUE;
#endif
@@ -562,8 +577,7 @@ test_c(obj, fname)
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0) return FALSE;
+ if (rb_stat(fname, &st) < 0) return FALSE;
if (S_ISBLK(st.st_mode)) return TRUE;
return FALSE;
@@ -575,8 +589,7 @@ test_e(obj, fname)
{
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0) return FALSE;
+ if (rb_stat(fname, &st) < 0) return FALSE;
return TRUE;
}
@@ -644,8 +657,7 @@ test_f(obj, fname)
{
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0) return FALSE;
+ if (rb_stat(fname, &st) < 0) return FALSE;
if (S_ISREG(st.st_mode)) return TRUE;
return FALSE;
}
@@ -656,8 +668,7 @@ test_z(obj, fname)
{
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0) return FALSE;
+ if (rb_stat(fname, &st) < 0) return FALSE;
if (st.st_size == 0) return TRUE;
return FALSE;
}
@@ -668,8 +679,7 @@ test_s(obj, fname)
{
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0) return FALSE;
+ if (rb_stat(fname, &st) < 0) return FALSE;
if (st.st_size == 0) return FALSE;
return int2inum(st.st_size);
}
@@ -680,8 +690,7 @@ test_owned(obj, fname)
{
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0) return FALSE;
+ if (rb_stat(fname, &st) < 0) return FALSE;
if (st.st_uid == geteuid()) return TRUE;
return FALSE;
}
@@ -692,8 +701,7 @@ test_rowned(obj, fname)
{
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0) return FALSE;
+ if (rb_stat(fname, &st) < 0) return FALSE;
if (st.st_uid == getuid()) return TRUE;
return FALSE;
}
@@ -705,8 +713,7 @@ test_grpowned(obj, fname)
#ifndef NT
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0) return FALSE;
+ if (rb_stat(fname, &st) < 0) return FALSE;
if (st.st_gid == getegid()) return TRUE;
#endif
return FALSE;
@@ -768,8 +775,7 @@ file_s_size(obj, fname)
{
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0)
+ if (rb_stat(fname, &st) < 0)
rb_sys_fail(RSTRING(fname)->ptr);
return int2inum(st.st_size);
}
@@ -781,8 +787,7 @@ file_s_ftype(obj, fname)
struct stat st;
char *t;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0)
+ if (rb_stat(fname, &st) < 0)
rb_sys_fail(RSTRING(fname)->ptr);
if (S_ISREG(st.st_mode)) {
@@ -825,8 +830,7 @@ file_s_atime(obj, fname)
{
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0)
+ if (rb_stat(fname, &st) < 0)
rb_sys_fail(RSTRING(fname)->ptr);
return time_new(st.st_atime, 0);
}
@@ -851,8 +855,7 @@ file_s_mtime(obj, fname)
{
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0)
+ if (rb_stat(fname, &st) < 0)
rb_sys_fail(RSTRING(fname)->ptr);
return time_new(st.st_mtime, 0);
}
@@ -877,8 +880,7 @@ file_s_ctime(obj, fname)
{
struct stat st;
- Check_SafeStr(fname);
- if (stat(RSTRING(fname)->ptr, &st) < 0)
+ if (rb_stat(fname, &st) < 0)
rb_sys_fail(RSTRING(fname)->ptr);
return time_new(st.st_ctime, 0);
}
@@ -934,6 +936,7 @@ file_chmod(obj, vmode)
GetOpenFile(obj, fptr);
#if defined(DJGPP) || defined(__CYGWIN32__) || defined(NT)
+ io_check_closed(fptr);
if (chmod(fptr->path, mode) == -1)
rb_sys_fail(fptr->path);
#else
@@ -993,6 +996,7 @@ file_chown(obj, owner, group)
rb_secure(2);
GetOpenFile(obj, fptr);
#if defined(DJGPP) || defined(__CYGWIN32__) || defined(NT)
+ io_check_closed(fptr);
if (chown(fptr->path, NUM2INT(owner), NUM2INT(group)) == -1)
rb_sys_fail(fptr->path);
#else
@@ -1104,7 +1108,7 @@ file_s_symlink(obj, from, to)
rb_sys_fail(RSTRING(from)->ptr);
return TRUE;
#else
- rb_notimplement();
+ rb_notimplement();
#endif
}
@@ -1311,7 +1315,7 @@ file_s_basename(argc, argv)
f = rmext(RSTRING(fname)->ptr, RSTRING(ext)->ptr);
if (f) return str_new(RSTRING(fname)->ptr, f);
}
- return (VALUE)fname;
+ return fname;
}
p++; /* skip last `/' */
if (!NIL_P(ext)) {
@@ -1446,7 +1450,16 @@ test_check(n, argc, argv)
n+=1;
if (n < argc) ArgError("Wrong # of arguments(%d for %d)", argc, n);
for (i=1; i<n; i++) {
- Check_SafeStr(argv[i]);
+ switch (TYPE(argv[i])) {
+ case T_STRING:
+ Check_SafeStr(argv[i]);
+ break;
+ case T_FILE:
+ break;
+ default:
+ Check_Type(argv[i], T_STRING);
+ break;
+ }
}
}
@@ -1543,7 +1556,7 @@ f_test(argc, argv)
struct stat st;
CHECK(1);
- if (stat(RSTRING(argv[1])->ptr, &st) == -1) {
+ if (rb_stat(argv[1], &st) == -1) {
rb_sys_fail(RSTRING(argv[1])->ptr);
}
@@ -1561,8 +1574,8 @@ f_test(argc, argv)
struct stat st1, st2;
CHECK(2);
- if (stat(RSTRING(argv[1])->ptr, &st1) < 0) return FALSE;
- if (stat(RSTRING(argv[2])->ptr, &st2) < 0) return FALSE;
+ if (rb_stat(argv[1], &st1) < 0) return FALSE;
+ if (rb_stat(argv[2], &st2) < 0) return FALSE;
switch (cmd) {
case '-':
@@ -1675,12 +1688,11 @@ Init_File()
rb_define_method(cFile, "tell", file_tell, 0);
rb_define_method(cFile, "seek", file_seek, 2);
+ rb_define_method(cFile, "rewind", file_rewind, 0);
+
rb_define_method(cFile, "pos", file_tell, 0);
rb_define_method(cFile, "pos=", file_set_pos, 1);
- rb_define_method(cFile, "rewind", file_rewind, 0);
- rb_define_method(cFile, "isatty", file_isatty, 0);
- rb_define_method(cFile, "tty?", file_isatty, 0);
rb_define_method(cFile, "eof", file_eof, 0);
rb_define_method(cFile, "eof?", file_eof, 0);
diff --git a/gc.c b/gc.c
index 27065af1cb..9eab3b6c18 100644
--- a/gc.c
+++ b/gc.c
@@ -6,7 +6,7 @@
$Date$
created at: Tue Oct 5 09:44:46 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -26,10 +26,6 @@
#endif
#endif
-#ifdef _AIX
-#pragma alloca
-#endif
-
#ifdef C_ALLOCA
void *alloca();
#endif
@@ -177,7 +173,7 @@ typedef struct RVALUE {
} free;
struct RBasic basic;
struct RObject object;
- struct RClass class;
+ struct RClass klass;
struct RFloat flonum;
struct RString string;
struct RArray array;
@@ -253,14 +249,14 @@ rb_newobj()
}
VALUE
-data_object_alloc(class, datap, dmark, dfree)
- VALUE class;
+data_object_alloc(klass, datap, dmark, dfree)
+ VALUE klass;
void *datap;
void (*dfree)();
void (*dmark)();
{
NEWOBJ(data, struct RData);
- OBJSETUP(data, class, T_DATA);
+ OBJSETUP(data, klass, T_DATA);
data->data = datap;
data->dfree = dfree;
data->dmark = dmark;
@@ -389,6 +385,7 @@ gc_mark(ptr)
case NODE_IF: /* 1,2,3 */
case NODE_FOR:
case NODE_ITER:
+ case NODE_CREF:
gc_mark(obj->as.node.u2.node);
/* fall through */
case NODE_BLOCK: /* 1,3 */
@@ -400,6 +397,9 @@ gc_mark(ptr)
case NODE_DREGX_ONCE:
case NODE_FBODY:
case NODE_CALL:
+#ifdef C_ALLOCA
+ case NODE_ALLOCA:
+#endif
gc_mark(obj->as.node.u1.node);
/* fall through */
case NODE_SUPER: /* 3 */
@@ -466,19 +466,19 @@ gc_mark(ptr)
return; /* no need to mark class. */
}
- gc_mark(obj->as.basic.class);
+ gc_mark(obj->as.basic.klass);
switch (obj->as.basic.flags & T_MASK) {
case T_ICLASS:
- gc_mark(obj->as.class.super);
- mark_tbl(obj->as.class.iv_tbl);
- mark_tbl(obj->as.class.m_tbl);
+ gc_mark(obj->as.klass.super);
+ mark_tbl(obj->as.klass.iv_tbl);
+ mark_tbl(obj->as.klass.m_tbl);
break;
case T_CLASS:
case T_MODULE:
- gc_mark(obj->as.class.super);
- mark_tbl(obj->as.class.m_tbl);
- mark_tbl(obj->as.class.iv_tbl);
+ gc_mark(obj->as.klass.super);
+ mark_tbl(obj->as.klass.m_tbl);
+ mark_tbl(obj->as.klass.iv_tbl);
break;
case T_ARRAY:
@@ -644,7 +644,7 @@ obj_free(obj)
case T_MODULE:
case T_CLASS:
rb_clear_cache();
- st_free_table(RANY(obj)->as.class.m_tbl);
+ st_free_table(RANY(obj)->as.klass.m_tbl);
if (RANY(obj)->as.object.iv_tbl) {
st_free_table(RANY(obj)->as.object.iv_tbl);
}
diff --git a/hash.c b/hash.c
index 49be7de6aa..b36cfa2317 100644
--- a/hash.c
+++ b/hash.c
@@ -6,7 +6,7 @@
$Date$
created at: Mon Nov 22 18:51:18 JST 1993
- Copyright (C) 1993-1997 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -14,6 +14,7 @@
#include "st.h"
#include "sig.h"
+#include <sys/types.h>
#include <sys/stat.h>
#ifndef HAVE_STRING_H
@@ -179,7 +180,7 @@ hash_foreach(hash, func, farg)
arg.hash = hash;
arg.func = func;
arg.arg = farg;
- return rb_ensure(hash_foreach_call, (VALUE)&arg, hash_foreach_ensure, (VALUE)hash);
+ return rb_ensure(hash_foreach_call, (VALUE)&arg, hash_foreach_ensure, hash);
}
static VALUE
@@ -307,7 +308,7 @@ hash_rehash(hash)
RHASH(hash)->tbl = tbl;
if (RHASH(hash)->iter_lev > 0) RHASH(hash)->status |= HASH_REHASHED;
- return (VALUE)hash;
+ return hash;
}
VALUE
@@ -405,7 +406,7 @@ hash_delete_if(hash)
hash_modify(hash);
hash_foreach(hash, delete_if_i, 0);
- return (VALUE)hash;
+ return hash;
}
static int
@@ -422,7 +423,7 @@ hash_clear(hash)
hash_modify(hash);
st_foreach(RHASH(hash)->tbl, clear_i);
- return (VALUE)hash;
+ return hash;
}
VALUE
@@ -441,6 +442,25 @@ hash_aset(hash, key, val)
return val;
}
+static int
+replace_i(key, val, hash)
+ VALUE key, val, hash;
+{
+ hash_aset(hash, key, val);
+ return ST_CONTINUE;
+}
+
+static VALUE
+hash_replace(hash, hash2)
+ VALUE hash, hash2;
+{
+ Check_Type(hash2, T_HASH);
+ hash_clear(hash);
+ st_foreach(RHASH(hash2)->tbl, replace_i, hash);
+
+ return hash;
+}
+
static VALUE
hash_length(hash)
VALUE hash;
@@ -471,7 +491,7 @@ hash_each_value(hash)
VALUE hash;
{
hash_foreach(hash, each_value_i);
- return (VALUE)hash;
+ return hash;
}
static int
@@ -488,7 +508,7 @@ hash_each_key(hash)
VALUE hash;
{
hash_foreach(hash, each_key_i);
- return (VALUE)hash;
+ return hash;
}
static int
@@ -505,7 +525,7 @@ hash_each_pair(hash)
VALUE hash;
{
hash_foreach(hash, each_pair_i);
- return (VALUE)hash;
+ return hash;
}
static int
@@ -1095,6 +1115,7 @@ Init_Hash()
rb_define_method(cHash,"[]", hash_aref, 1);
rb_define_method(cHash,"[]=", hash_aset, 2);
rb_define_method(cHash,"indexes", hash_indexes, -1);
+ rb_define_method(cHash,"indices", hash_indexes, -1);
rb_define_method(cHash,"length", hash_length, 0);
rb_define_alias(cHash, "size", "length");
rb_define_method(cHash,"empty?", hash_empty_p, 0);
@@ -1113,6 +1134,7 @@ Init_Hash()
rb_define_method(cHash,"clear", hash_clear, 0);
rb_define_method(cHash,"invert", hash_invert, 0);
rb_define_method(cHash,"update", hash_update, 1);
+ rb_define_method(cHash,"replace", hash_replace, 1);
rb_define_method(cHash,"include?", hash_has_key, 1);
rb_define_method(cHash,"has_key?", hash_has_key, 1);
@@ -1135,6 +1157,7 @@ Init_Hash()
rb_define_singleton_method(envtbl,"rehash", env_none, 0);
rb_define_singleton_method(envtbl,"to_a", env_to_a, 0);
rb_define_singleton_method(envtbl,"indexes", env_indexes, -1);
+ rb_define_singleton_method(envtbl,"indices", env_indexes, -1);
rb_define_singleton_method(envtbl,"length", env_size, 0);
rb_define_singleton_method(envtbl,"empty?", env_empty_p, 0);
rb_define_singleton_method(envtbl,"keys", env_keys, 0);
diff --git a/inits.c b/inits.c
index 123b32c989..55db006bfe 100644
--- a/inits.c
+++ b/inits.c
@@ -6,7 +6,7 @@
$Date$
created at: Tue Dec 28 16:01:58 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
diff --git a/instruby.rb b/instruby.rb
index 8fd77055f2..3d3f2a4173 100644
--- a/instruby.rb
+++ b/instruby.rb
@@ -33,5 +33,6 @@ IO.foreach 'MANIFEST' do |$_|
File.install "config.h", archdir, 0644, TRUE
end
File.install "rbconfig.rb", archdir, 0644, TRUE
+File.makedirs mandir, TRUE
File.install "ruby.1", mandir, 0644, TRUE
# vi:set sw=2:
diff --git a/intern.h b/intern.h
index 192da014d5..d8531bdda4 100644
--- a/intern.h
+++ b/intern.h
@@ -216,12 +216,13 @@ VALUE reg_match _((VALUE, VALUE));
VALUE reg_match2 _((VALUE));
void rb_set_kcode _((char *));
/* ruby.c */
-void rb_require_modules _((void));
void rb_load_file _((char *));
void ruby_script _((char *));
void ruby_prog_init _((void));
void ruby_set_argv _((int, char **));
void ruby_process_options _((int, char **));
+void ruby_require_modules _((void));
+void ruby_load_script _((void));
/* signal.c */
VALUE f_kill _((int, VALUE *));
void gc_mark_trap_list _((void));
diff --git a/io.c b/io.c
index f84e15e447..6e4c7e7d76 100644
--- a/io.c
+++ b/io.c
@@ -6,7 +6,7 @@
$Date$
created at: Fri Oct 15 18:08:59 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -108,27 +108,31 @@ eof_error()
}
void
-io_writable(fptr)
+io_check_closed(fptr)
OpenFile *fptr;
{
- if (!(fptr->mode & FMODE_WRITABLE)) {
- Raise(eIOError, "not opened for writing");
- }
+ if (fptr->f == NULL)
+ Raise(eIOError, "closed stream");
}
void
io_readable(fptr)
OpenFile *fptr;
{
+ io_check_closed(fptr);
if (!(fptr->mode & FMODE_READABLE)) {
Raise(eIOError, "not opened for reading");
}
}
-static void
-closed()
+void
+io_writable(fptr)
+ OpenFile *fptr;
{
- Raise(eIOError, "closed stream");
+ io_check_closed(fptr);
+ if (!(fptr->mode & FMODE_WRITABLE)) {
+ Raise(eIOError, "not opened for writing");
+ }
}
/* writing functions */
@@ -153,7 +157,6 @@ io_write(io, str)
io_writable(fptr);
f = GetWriteFile(fptr);
- if (f == NULL) closed();
#ifdef __human68k__
{
@@ -197,7 +200,6 @@ io_flush(io)
GetOpenFile(io, fptr);
io_writable(fptr);
f = GetWriteFile(fptr);
- if (f == NULL) closed();
if (fflush(f) == EOF) rb_sys_fail(0);
@@ -213,7 +215,6 @@ io_eof(io)
GetOpenFile(io, fptr);
io_readable(fptr);
- if (fptr->f == NULL) closed();
if (READ_DATA_PENDING(fptr->f)) return FALSE;
if (feof(fptr->f)) return TRUE;
@@ -289,7 +290,6 @@ read_all(port)
GetOpenFile(port, fptr);
io_readable(fptr);
- if (fptr->f == NULL) closed();
if (fstat(fileno(fptr->f), &st) == 0 && S_ISREG(st.st_mode)) {
if (st.st_size == 0) return Qnil;
@@ -335,7 +335,6 @@ io_read(argc, argv, io)
len = NUM2INT(length);
GetOpenFile(io, fptr);
io_readable(fptr);
- if (fptr->f == NULL) closed();
str = str_new(0, len);
@@ -379,7 +378,6 @@ io_gets_method(argc, argv, io)
GetOpenFile(io, fptr);
io_readable(fptr);
f = fptr->f;
- if (f == NULL) closed();
if (!NIL_P(rs)) {
rslen = RSTRING(rs)->len;
@@ -546,7 +544,6 @@ io_each_byte(io)
GetOpenFile(io, fptr);
io_readable(fptr);
f = fptr->f;
- if (f == NULL) closed();
for (;;) {
READ_CHECK(f);
@@ -571,7 +568,6 @@ io_getc(io)
GetOpenFile(io, fptr);
io_readable(fptr);
f = fptr->f;
- if (f == NULL) closed();
READ_CHECK(f);
TRAP_BEG;
@@ -606,7 +602,6 @@ io_ungetc(io, c)
Check_Type(c, T_FIXNUM);
GetOpenFile(io, fptr);
io_readable(fptr);
- if (fptr->f == NULL) closed();
if (ungetc(FIX2INT(c), fptr->f) == EOF)
rb_sys_fail(fptr->path);
@@ -620,7 +615,7 @@ io_isatty(io)
OpenFile *fptr;
GetOpenFile(io, fptr);
- if (fptr->f == NULL) closed();
+ io_check_closed(fptr);
if (isatty(fileno(fptr->f)) == 0)
return FALSE;
return TRUE;
@@ -636,23 +631,20 @@ fptr_finalize(fptr)
if (fptr->f2 != NULL) {
fclose(fptr->f2);
}
- if (fptr->path) {
- free(fptr->path);
- fptr->path = NULL;
- }
if (fptr->pid) {
rb_syswait(fptr->pid);
fptr->pid = 0;
}
}
-void
-io_fptr_finalize(fptr)
+static void
+io_fptr_close(fptr)
OpenFile *fptr;
{
+ if (fptr->f == NULL) return;
+
if (fptr->finalize) {
(*fptr->finalize)(fptr);
- fptr->finalize = 0;
}
else {
fptr_finalize(fptr);
@@ -660,6 +652,17 @@ io_fptr_finalize(fptr)
fptr->f = fptr->f2 = NULL;
}
+void
+io_fptr_finalize(fptr)
+ OpenFile *fptr;
+{
+ io_fptr_close(fptr);
+ if (fptr->path) {
+ free(fptr->path);
+ fptr->path = NULL;
+ }
+}
+
VALUE
io_close(io)
VALUE io;
@@ -667,7 +670,7 @@ io_close(io)
OpenFile *fptr;
GetOpenFile(io, fptr);
- io_fptr_finalize(fptr);
+ io_fptr_close(fptr);
return Qnil;
}
@@ -697,7 +700,6 @@ io_syswrite(io, str)
GetOpenFile(io, fptr);
io_writable(fptr);
f = GetWriteFile(fptr);
- if (f == NULL) closed();
#ifdef THREAD
thread_fd_writable(fileno(f));
@@ -720,7 +722,6 @@ io_sysread(io, len)
ilen = NUM2INT(len);
GetOpenFile(io, fptr);
io_readable(fptr);
- if (fptr->f == NULL) closed();
str = str_new(0, ilen);
@@ -1001,7 +1002,8 @@ pipe_open(pname, mode)
break;
default: /* parent */
- {
+ if (pid < 0) rb_sys_fail(pname);
+ else {
NEWOBJ(port, struct RFile);
OBJSETUP(port, cIO, T_FILE);
MakeOpenFile(port, fptr);
@@ -1143,18 +1145,21 @@ io_reopen(io, nfile)
mode = io_mode_string(fptr);
fd = fileno(fptr->f);
- if (fileno(fptr->f) < 3) /* need to keep stdio */
+ if (fileno(fptr->f) < 3) {
+ /* need to keep stdio */
+ dup2(fileno(orig->f), fd);
+ }
+ else {
fclose(fptr->f);
- dup2(fileno(orig->f), fd);
- fptr->f = rb_fdopen(fd, mode);
+ fptr->f = rb_fdopen(fd, mode);
+ }
if (fptr->f2) {
fd = fileno(fptr->f2);
- if (fileno(fptr->f2) < 3)
- fclose(fptr->f2);
+ fclose(fptr->f2);
if (orig->f2) {
dup2(fileno(orig->f2), fd);
- fptr->f = rb_fdopen(fd, "w");
+ fptr->f2 = rb_fdopen(fd, "w");
}
else {
fptr->f2 = 0;
@@ -1165,7 +1170,7 @@ io_reopen(io, nfile)
io_binmode(io);
}
- RBASIC(io)->class = RBASIC(nfile)->class;
+ RBASIC(io)->klass = RBASIC(nfile)->klass;
return io;
}
@@ -1390,38 +1395,27 @@ io_defset(val, id)
}
static void
-io_errset(val, id)
+io_stdio_set(val, id, var)
VALUE val;
ID id;
+ VALUE *var;
{
- OpenFile *fptr;
+ OpenFile *fptr, *fptr2;
int fd;
if (TYPE(val) != T_FILE) {
- TypeError("$stderr must be IO Object");
+ TypeError("%s must be IO object", rb_id2name(id));
}
+ GetOpenFile(*var, fptr);
+ fd = fileno(fptr->f);
GetOpenFile(val, fptr);
- io_writable(fptr);
- rb_stderr = val;
-
- fd = fileno(fptr->f2?fptr->f2:fptr->f);
- if (fd != 2) {
- FILE *f;
-
- fflush(stderr);
- dup2(fd, 2);
- f = rb_fdopen(2, io_mode_string(fptr));
- if (fptr->f2) {
- if (fileno(fptr->f2) < 3) /* need to keep stdio */
- fclose(fptr->f2);
- fptr->f2 = f;
- }
- else {
- if (fileno(fptr->f) < 3)
- fclose(fptr->f);
- fptr->f = f;
- }
+ if (fd == 0) {
+ io_readable(fptr);
}
+ else {
+ io_writable(fptr);
+ }
+ io_reopen(*var, val);
}
static VALUE
@@ -1716,14 +1710,13 @@ f_select(argc, argv, obj)
FD_ZERO(&pset);
if (!NIL_P(read)) {
-
Check_Type(read, T_ARRAY);
rp = &rset;
FD_ZERO(rp);
for (i=0; i<RARRAY(read)->len; i++) {
Check_Type(RARRAY(read)->ptr[i], T_FILE);
GetOpenFile(RARRAY(read)->ptr[i], fptr);
- if (fptr->f == NULL) closed();
+ io_check_closed(fptr);
FD_SET(fileno(fptr->f), rp);
if (READ_DATA_PENDING(fptr->f)) { /* check for buffered data */
pending++;
@@ -1746,7 +1739,7 @@ f_select(argc, argv, obj)
for (i=0; i<RARRAY(write)->len; i++) {
Check_Type(RARRAY(write)->ptr[i], T_FILE);
GetOpenFile(RARRAY(write)->ptr[i], fptr);
- if (fptr->f == NULL) closed();
+ io_check_closed(fptr);
FD_SET(fileno(fptr->f), wp);
if (max > fileno(fptr->f)) max = fileno(fptr->f);
if (fptr->f2) {
@@ -1765,7 +1758,7 @@ f_select(argc, argv, obj)
for (i=0; i<RARRAY(except)->len; i++) {
Check_Type(RARRAY(except)->ptr[i], T_FILE);
GetOpenFile(RARRAY(except)->ptr[i], fptr);
- if (fptr->f == NULL) closed();
+ io_check_closed(fptr);
FD_SET(fileno(fptr->f), ep);
if (max < fileno(fptr->f)) max = fileno(fptr->f);
if (fptr->f2) {
@@ -1861,13 +1854,13 @@ io_ctl(io, req, arg, io_p)
rb_secure(2);
GetOpenFile(io, fptr);
- if (NIL_P(arg) || (VALUE)arg == FALSE) {
+ if (NIL_P(arg) || arg == FALSE) {
narg = 0;
}
else if (FIXNUM_P(arg)) {
narg = FIX2INT(arg);
}
- else if ((VALUE)arg == TRUE) {
+ else if (arg == TRUE) {
narg = 1;
}
else {
@@ -2379,11 +2372,11 @@ Init_IO()
rb_define_method(cIO, "fcntl", io_fcntl, -1);
rb_stdin = prep_stdio(stdin, FMODE_READABLE);
- rb_define_readonly_variable("$stdin", &rb_stdin);
+ rb_define_hooked_variable("$stdin", &rb_stdin, 0, io_stdio_set);
rb_stdout = prep_stdio(stdout, FMODE_WRITABLE);
- rb_define_readonly_variable("$stdout", &rb_stdout);
+ rb_define_hooked_variable("$stdout", &rb_stdout, 0, io_stdio_set);
rb_stderr = prep_stdio(stderr, FMODE_WRITABLE);
- rb_define_hooked_variable("$stderr", &rb_stderr, 0, io_errset);
+ rb_define_hooked_variable("$stderr", &rb_stderr, 0, io_stdio_set);
rb_defout = rb_stdout;
rb_define_hooked_variable("$>", &rb_defout, 0, io_defset);
diff --git a/io.h b/io.h
index c671fca8ed..ddb49961dc 100644
--- a/io.h
+++ b/io.h
@@ -7,7 +7,7 @@
$Date$
created at: Fri Nov 12 16:47:09 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -54,5 +54,6 @@ void io_writable _((OpenFile *));
void io_readable _((OpenFile *));
void io_fptr_finalize _((OpenFile *));
void io_unbuffered _((OpenFile *));
+void io_check_closed _((OpenFile *));
#endif
diff --git a/keywords b/keywords
index 9e3870d1a6..1772de42b0 100644
--- a/keywords
+++ b/keywords
@@ -1,5 +1,7 @@
struct kwtable {char *name; int id[2]; enum lex_state state;};
%%
+__LINE__, k__LINE__, k__LINE__, EXPR_END
+__FILE__, k__FILE__, k__FILE__, EXPR_END
BEGIN, klBEGIN, klBEGIN, EXPR_END
END, klEND, klEND, EXPR_END
alias, kALIAS, kALIAS, EXPR_FNAME
diff --git a/lex.c b/lex.c
index 390471c424..1abc048638 100644
--- a/lex.c
+++ b/lex.c
@@ -2,12 +2,12 @@
/* Command-line: gperf -p -j1 -i 1 -g -o -t -N rb_reserved_word -k1,3,$ keywords */
struct kwtable {char *name; int id[2]; enum lex_state state;};
-#define TOTAL_KEYWORDS 38
+#define TOTAL_KEYWORDS 40
#define MIN_WORD_LENGTH 2
#define MAX_WORD_LENGTH 8
#define MIN_HASH_VALUE 6
-#define MAX_HASH_VALUE 52
-/* maximum key range = 47, duplicates = 0 */
+#define MAX_HASH_VALUE 55
+/* maximum key range = 50, duplicates = 0 */
#ifdef __GNUC__
inline
@@ -19,19 +19,19 @@ hash (str, len)
{
static unsigned char asso_values[] =
{
- 53, 53, 53, 53, 53, 53, 53, 53, 53, 53,
- 53, 53, 53, 53, 53, 53, 53, 53, 53, 53,
- 53, 53, 53, 53, 53, 53, 53, 53, 53, 53,
- 53, 53, 53, 53, 53, 53, 53, 53, 53, 53,
- 53, 53, 53, 53, 53, 53, 53, 53, 53, 53,
- 53, 53, 53, 53, 53, 53, 53, 53, 53, 53,
- 53, 53, 53, 11, 53, 53, 34, 53, 1, 35,
- 53, 1, 53, 53, 53, 53, 53, 53, 1, 53,
- 53, 53, 53, 53, 53, 53, 53, 53, 53, 53,
- 53, 53, 53, 53, 53, 53, 53, 29, 1, 2,
- 1, 1, 4, 24, 53, 17, 53, 20, 9, 2,
- 9, 26, 14, 53, 5, 1, 1, 16, 53, 21,
- 24, 9, 53, 53, 53, 53, 53, 53,
+ 56, 56, 56, 56, 56, 56, 56, 56, 56, 56,
+ 56, 56, 56, 56, 56, 56, 56, 56, 56, 56,
+ 56, 56, 56, 56, 56, 56, 56, 56, 56, 56,
+ 56, 56, 56, 56, 56, 56, 56, 56, 56, 56,
+ 56, 56, 56, 56, 56, 56, 56, 56, 56, 56,
+ 56, 56, 56, 56, 56, 56, 56, 56, 56, 56,
+ 56, 56, 56, 11, 56, 56, 36, 56, 1, 37,
+ 31, 1, 56, 56, 56, 56, 29, 56, 1, 56,
+ 56, 56, 56, 56, 56, 56, 56, 56, 56, 56,
+ 56, 56, 56, 56, 56, 1, 56, 32, 1, 2,
+ 1, 1, 4, 23, 56, 17, 56, 20, 9, 2,
+ 9, 26, 14, 56, 5, 1, 1, 16, 56, 21,
+ 20, 9, 56, 56, 56, 56, 56, 56,
};
register int hval = len;
@@ -87,17 +87,19 @@ rb_reserved_word (str, len)
{"until", kUNTIL, kUNTIL_MOD, EXPR_BEG},
{"unless", kUNLESS, kUNLESS_MOD, EXPR_BEG},
{"or", kOR, kOR, EXPR_BEG},
- {"and", kAND, kAND, EXPR_BEG},
+ {"next", kNEXT, kNEXT, EXPR_END},
{"when", kWHEN, kWHEN, EXPR_BEG},
{"redo", kREDO, kREDO, EXPR_END},
- {"class", kCLASS, kCLASS, EXPR_CLASS},
- {"next", kNEXT, kNEXT, EXPR_END},
+ {"and", kAND, kAND, EXPR_BEG},
{"begin", kBEGIN, kBEGIN, EXPR_BEG},
+ {"__LINE__", k__LINE__, k__LINE__, EXPR_END},
+ {"class", kCLASS, kCLASS, EXPR_CLASS},
+ {"__FILE__", k__FILE__, k__FILE__, EXPR_END},
{"END", klEND, klEND, EXPR_END},
{"BEGIN", klBEGIN, klBEGIN, EXPR_END},
- {"",}, {"",},
{"while", kWHILE, kWHILE_MOD, EXPR_BEG},
- {"",}, {"",}, {"",}, {"",}, {"",}, {"",}, {"",},
+ {"",}, {"",}, {"",}, {"",}, {"",}, {"",}, {"",}, {"",}, {"",},
+ {"",},
{"alias", kALIAS, kALIAS, EXPR_FNAME},
};
diff --git a/lib/Env.rb b/lib/Env.rb
new file mode 100644
index 0000000000..e52501f801
--- /dev/null
+++ b/lib/Env.rb
@@ -0,0 +1,28 @@
+# Env.rb -- imports environment variables as global variables
+#
+# Usage:
+#
+# p $USER
+# $USER = "matz"
+# p ENV["USER"]
+
+for k,v in ENV
+ next unless /^[a-zA-Z][_a-zA-Z0-9]*/ =~ k
+ eval <<EOS
+ $#{k} = %q!#{v}!
+ trace_var "$#{k}", proc{|v|
+ ENV[%q!#{k}!] = v;
+ $#{k} = %q!#{v}!
+ if v == nil
+ untrace_var "$#{k}"
+ end
+ }
+EOS
+end
+
+p $TERM
+$TERM = nil
+p $TERM
+p ENV["TERM"]
+$TERM = "foo"
+p ENV["TERM"]
diff --git a/lib/complex.rb b/lib/complex.rb
index aa5d219d2f..69437b01bb 100644
--- a/lib/complex.rb
+++ b/lib/complex.rb
@@ -1,8 +1,8 @@
#
# complex.rb -
# $Release Version: 0.5 $
-# $Revision: 1.1 $
-# $Date: 1996/11/11 04:25:19 $
+# $Revision: 1.1.1.1 $
+# $Date: 1998/01/16 04:05:49 $
# by Keiju ISHITSUKA(SHL Japan Inc.)
#
# --
diff --git a/lib/date.rb b/lib/date.rb
index 998c2e8152..2d5090b62b 100644
--- a/lib/date.rb
+++ b/lib/date.rb
@@ -1,8 +1,8 @@
#
# Date.rb -
# $Release Version: $
-# $Revision: 1.2 $
-# $Date: 1997/02/14 11:05:29 $
+# $Revision: 1.1.1.1.4.2 $
+# $Date: 1998/02/02 04:49:13 $
# by Yasuo OHBA(SHL Japan Inc. Technology Dept.)
#
# --
@@ -17,15 +17,34 @@
class Date
include Comparable
+ Weektag = [
+ "Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"
+ ]
+
+ Monthtag = [
+ "January","February","March","April", "May", "June","July",
+ "August", "September", "October", "November", "December"
+ ]
+
+ Monthtab = {
+ "jan"=>1, "feb"=>2, "mar"=>3, "apr"=>4, "may"=>5, "jun"=>6,
+ "jul"=>7, "aug"=>8, "sep"=>9, "oct"=>10, "nov"=>11, "dec"=>12
+ }
+
def initialize(y = 1, m = 1, d = 1)
- if y.kind_of?(String) && y.size == 8
- @year = y[0,4].to_i
- @month = y[4,2].to_i
- @day = y[6,2].to_i
+ if y.kind_of?(String)
+ case y
+ when /(\d\d\d\d)-?(?:(\d\d)-?(\d\d)?)?/
+ @year = $1.to_i
+ @month = if $2 then $2.to_i else 1 end
+ @day = if $3 then $3.to_i else 1 end
+ else
+ require 'parsedate'
+ @year, @month, @day = ParseDate.parsedate(y)
+ end
else
if m.kind_of?(String)
- ml = {"jan"=>1, "feb"=>2, "mar"=>3, "apr"=>4, "may"=>5, "jun"=>6, "jul"=>7, "aug"=>8, "sep"=>9, "oct"=>10, "nov"=>11, "dec"=>12}
- m = ml[m.downcase]
+ m = Monthtab[m.downcase]
if m.nil?
raise ArgumentError, "Wrong argument. (month)"
end
@@ -53,25 +72,35 @@ class Date
def period
return Date.period!(@year, @month, @day)
end
-
+
+ def jd
+ return period + 1721423
+ end
+
+ def mjd
+ return jd - 2400000.5
+ end
+
+ def to_s
+ format("%.3s, %.3s %2d %4d", name_of_week, name_of_month, @day, @year)
+ end
+
+ def inspect
+ to_s
+ end
+
def day_of_week
- dl = Date.daylist(@year)
- d = Date.jan1!(@year)
- for m in 1..(@month - 1)
- d += dl[m]
- end
- d += @day - 1
- if @year == 1752 && @month == 9 && @day >= 14
- d -= (14 - 3)
- end
- return (d % 7)
+ return (period + 5) % 7
end
- Weektag = ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"]
def name_of_week
return Weektag[self.day_of_week]
end
+ def name_of_month
+ return Monthtag[@month-1]
+ end
+
def +(o)
if o.kind_of?(Numeric)
d = Integer(self.period + o)
@@ -125,6 +154,9 @@ class Date
end
def _check_date
+ if @year == nil or @month == nil or @day == nil
+ raise ArgumentError, "argument contains nil"
+ end
m = Date.daylist(@year)
if @month < 1 || @month > 12
raise ArgumentError, "argument(month) out of range."
diff --git a/lib/delegate.rb b/lib/delegate.rb
index e5943cead8..571bf87510 100644
--- a/lib/delegate.rb
+++ b/lib/delegate.rb
@@ -7,16 +7,16 @@
#
# Usage:
# foo = Object.new
-# foo = SimpleDelegater.new(foo)
+# foo = SimpleDelegator.new(foo)
# foo.type # => Object
-class Delegater
+class Delegator
def initialize(obj)
preserved = ["id", "equal?", "__getobj__"]
for t in self.type.ancestors
preserved |= t.instance_methods
- break if t == Delegater
+ break if t == Delegator
end
for method in obj.methods
next if preserved.include? method
@@ -30,7 +30,7 @@ class Delegater
end
-class SimpleDelegater<Delegater
+class SimpleDelegator<Delegator
def initialize(obj)
super
@@ -41,4 +41,17 @@ class SimpleDelegater<Delegater
@obj
end
+ def __setobj__(obj)
+ @obj = obj
+ end
+end
+
+# backword compatibility ^_^;;;
+Delegater = Delegator
+SimpleDelegater = SimpleDelegator
+
+if __FILE__ == $0
+ foo = Object.new
+ foo = SimpleDelegator.new(foo)
+ p foo.type # => Object
end
diff --git a/lib/e2mmap1_0.rb b/lib/e2mmap1_0.rb
deleted file mode 100644
index d245dec975..0000000000
--- a/lib/e2mmap1_0.rb
+++ /dev/null
@@ -1,71 +0,0 @@
-#
-# e2mmap.rb -
-# $Release Version: 1.0$
-# $Revision$
-# $Date$
-# by Keiju ISHITSUKA
-#
-# --
-#
-#
-
-module Exception2MessageMapper
- RCS_ID='-$Header$-'
- E2MM = Exception2MessageMapper
-
- def E2MM.extend_to(b)
- c = eval("self", b)
- c.extend(self)
- c.bind(b)
- end
-
- def bind(b)
- eval "
- @binding = binding
- E2MM_ErrorMSG = Hash.new
-
- # fail(err, *rest)
- # err: 例外
- # rest: メッセージに渡すパラメータ
- #
- def fail!(*rest)
- super
- end
-
- def fail(err, *rest)
- $! = err.new(sprintf(E2MM_ErrorMSG[err], *rest))
- super()
- end
-
- public :fail
- # def_exception(c, m)
- # c: exception
- # m: message_form
- # 例外cのメッセージをmとする.
- #
- def def_e2message(c, m)
- E2MM_ErrorMSG[c] = m
- end
-
- # def_exception(c, m)
- # c: exception_name
- # m: message_form
- # s: 例外スーパークラス(デフォルト: Exception)
- # 例外名``c''をもつ例外を定義し, そのメッセージをmとする.
- #
- def def_exception(c, m)
-
- c = c.id2name if c.kind_of?(Fixnum)
- eval \"class \#{c} < Exception
- end
- E2MM_ErrorMSG[\#{c}] = '\#{m}'
- \", @binding
- end
-", b
-
- end
-
- E2MM.extend_to(binding)
- def_exception("ErrNotClassOrModule", "Not Class or Module")
-end
-
diff --git a/lib/final.rb b/lib/final.rb
new file mode 100644
index 0000000000..fc17dce289
--- /dev/null
+++ b/lib/final.rb
@@ -0,0 +1,41 @@
+#
+# $Id$
+# Copyright (C) 1998 Yukihiro Matsumoto. All rights reserved.
+
+# The ObjectSpace extention:
+#
+# ObjectSpace.define_finalizer(obj, proc=lambda())
+#
+# Defines the finalizer for the specified object.
+#
+# ObjectSpace.undefine_finalizer(obj)
+#
+# Removes the finalizers for the object. If multiple finalizers are
+# defined for the object, all finalizers will be removed.
+#
+
+module ObjectSpace
+ Finalizers = {}
+ def define_finalizer(obj, proc=lambda())
+ ObjectSpace.call_finalizer(obj)
+ if assoc = Finalizers[obj.id]
+ assoc.push(proc)
+ else
+ Finalizers[obj.id] = [proc]
+ end
+ end
+ def undefine_finalizer(obj)
+ Finalizers.delete(obj.id)
+ end
+ module_function :define_finalizer, :undefine_finalizer
+
+ Generic_Finalizer = proc {|id|
+ if Finalizers.key? id
+ for proc in Finalizers[id]
+ proc.call(id)
+ end
+ Finalizers.delete(id)
+ end
+ }
+ add_finalizer Generic_Finalizer
+end
diff --git a/lib/finalize.rb b/lib/finalize.rb
index 9b2ffefcf5..1482e7ae20 100644
--- a/lib/finalize.rb
+++ b/lib/finalize.rb
@@ -13,10 +13,10 @@
# add_dependency(obj, dependant, method = :finalize, *opt)
# 依存関係 R_method(obj, dependant) の追加
#
-# delete(obj_or_id, dependant, method = :finalize)
-# delete_dependency(obj_or_id, dependant, method = :finalize)
+# delete(obj, dependant, method = :finalize)
+# delete_dependency(obj, dependant, method = :finalize)
# 依存関係 R_method(obj, dependant) の削除
-# delete_all_dependency(obj_or_id, dependant)
+# delete_all_dependency(obj, dependant)
# 依存関係 R_*(obj, dependant) の削除
# delete_by_dependant(dependant, method = :finalize)
# 依存関係 R_method(*, dependant) の削除
@@ -25,11 +25,11 @@
# delete_all
# 全ての依存関係の削除.
#
-# finalize(obj_or_id, dependant, method = :finalize)
-# finalize_dependency(obj_or_id, dependant, method = :finalize)
+# finalize(obj, dependant, method = :finalize)
+# finalize_dependency(obj, dependant, method = :finalize)
# 依存関連 R_method(obj, dependtant) で結ばれるdependantを
# finalizeする.
-# finalize_all_dependency(obj_or_id, dependant)
+# finalize_all_dependency(obj, dependant)
# 依存関連 R_*(obj, dependtant) で結ばれるdependantをfinalizeする.
# finalize_by_dependant(dependant, method = :finalize)
# 依存関連 R_method(*, dependtant) で結ばれるdependantをfinalizeする.
@@ -45,49 +45,45 @@
module Finalizer
RCS_ID='-$Header: /home/keiju/var/src/var.lib/ruby/RCS/finalize.rb,v 1.3 1998/01/09 08:09:49 keiju Exp keiju $-'
-
- # @dependency: {id => [[dependant, method, *opt], ...], ...}
-
+
+ # Dependency: {id => [[dependant, method, opt], ...], ...}
+ Dependency = {}
+
# 依存関係 R_method(obj, dependant) の追加
def add_dependency(obj, dependant, method = :finalize, *opt)
ObjectSpace.call_finalizer(obj)
- method = method.intern unless method.kind_of?(Integer)
- assoc = [dependant, method].concat(opt)
- if dep = @dependency[obj.id]
+ assoc = [dependant, method, opt]
+ if dep = Dependency[obj.id]
dep.push assoc
else
- @dependency[obj.id] = [assoc]
+ Dependency[obj.id] = [assoc]
end
end
alias add add_dependency
-
+
# 依存関係 R_method(obj, dependant) の削除
- def delete_dependency(id, dependant, method = :finalize)
- id = id.id unless id.kind_of?(Integer)
- method = method.intern unless method.kind_of?(Integer)
- for assoc in @dependency[id]
- assoc.delete_if do
- |d, m, *o|
+ def delete_dependency(obj, dependant, method = :finalize)
+ id = obj.id
+ for assoc in Dependency[id]
+ assoc.delete_if do |d,m,*o|
d == dependant && m == method
end
- @dependency.delete(id) if assoc.empty?
+ Dependency.delete(id) if assoc.empty?
end
end
alias delete delete_dependency
-
+
# 依存関係 R_*(obj, dependant) の削除
- def delete_all_dependency(id, dependant)
- id = id.id unless id.kind_of?(Integer)
- method = method.intern unless method.kind_of?(Integer)
- for assoc in @dependency[id]
- assoc.delete_if do
- |d, m, *o|
+ def delete_all_dependency(obj, dependant)
+ id = obj.id
+ for assoc in Dependency[id]
+ assoc.delete_if do |d,m,*o|
d == dependant
end
- @dependency.delete(id) if assoc.empty?
+ Dependency.delete(id) if assoc.empty?
end
end
-
+
# 依存関係 R_method(*, dependant) の削除
def delete_by_dependant(dependant, method = :finalize)
method = method.intern unless method.kind_of?(Integer)
@@ -95,100 +91,103 @@ module Finalizer
delete(id, dependant, method)
end
end
-
+
# 依存関係 R_*(*, dependant) の削除
def delete_all_by_dependant(dependant)
- for id in @dependency.keys
+ for id in Dependency.keys
delete_all_dependency(id, dependant)
end
end
-
- # 依存関連 R_method(obj, dependtant) で結ばれるdependantをfinalizeす
+
+ # 依存関連 R_method(id, dependtant) で結ばれるdependantをfinalizeす
# る.
def finalize_dependency(id, dependant, method = :finalize)
- id = id.id unless id.kind_of?(Integer)
- method = method.intern unless method.kind_of?(Integer)
- for assocs in @dependency[id]
- assocs.delete_if do
- |d, m, *o|
- d.send(m, *o) if ret = d == dependant && m == method
- ret
+ for assocs in Dependency[id]
+ assocs.delete_if do |d, m, *o|
+ if d == dependant && m == method
+ d.send(m, *o)
+ true
+ else
+ false
+ end
end
- @dependency.delete(id) if assoc.empty?
+ Dependency.delete(id) if assoc.empty?
end
end
alias finalize finalize_dependency
-
- # 依存関連 R_*(obj, dependtant) で結ばれるdependantをfinalizeする.
+
+ # 依存関連 R_*(id, dependtant) で結ばれるdependantをfinalizeする.
def finalize_all_dependency(id, dependant)
- id = id.id unless id.kind_of?(Integer)
- method = method.intern unless method.kind_of?(Integer)
- for assoc in @dependency[id]
- assoc.delete_if do
- |d, m, *o|
- d.send(m, *o) if ret = d == dependant
+ for assoc in Dependency[id]
+ assoc.delete_if do |d, m, *o|
+ if d == dependant
+ d.send(m, *o)
+ true
+ else
+ false
+ end
end
- @dependency.delete(id) if assoc.empty?
+ Dependency.delete(id) if assoc.empty?
end
end
-
+
# 依存関連 R_method(*, dependtant) で結ばれるdependantをfinalizeする.
def finalize_by_dependant(dependant, method = :finalize)
- method = method.intern unless method.kind_of?(Integer)
- for id in @dependency.keys
+ for id in Dependency.keys
finalize(id, dependant, method)
end
end
-
+
# 依存関連 R_*(*, dependtant) で結ばれるdependantをfinalizeする.
def fainalize_all_by_dependant(dependant)
- for id in @dependency.keys
+ for id in Dependency.keys
finalize_all_dependency(id, dependant)
end
end
-
+
# Finalizerに登録されている全てのdependantをfinalizeする
def finalize_all
- for id, assocs in @dependency
+ for id, assocs in Dependency
for dependant, method, *opt in assocs
dependant.send(method, id, *opt)
end
assocs.clear
end
end
-
+
# finalize_* を安全に呼び出すためのイテレータ
def safe
- old_status = Thread.critical
- Thread.critical = TRUE
- ObjectSpace.remove_finalizer(@proc)
- yield
- ObjectSpace.add_finalizer(@proc)
- Thread.critical = old_status
+ old_status, Thread.critical = Thread.critical, true
+ ObjectSpace.remove_finalizer(Proc)
+ begin
+ yield
+ ensure
+ ObjectSpace.add_finalizer(Proc)
+ Thread.critical = old_status
+ end
end
-
+
# ObjectSpace#add_finalizerへの登録関数
def final_of(id)
- if assocs = @dependency.delete(id)
+ if assocs = Dependency.delete(id)
for dependant, method, *opt in assocs
dependant.send(method, id, *opt)
end
end
end
-
- @dependency = Hash.new
- @proc = proc{|id| final_of(id)}
- ObjectSpace.add_finalizer(@proc)
+
+ Proc = proc{|id| final_of(id)}
+ ObjectSpace.add_finalizer(Proc)
module_function :add
module_function :add_dependency
-
+
module_function :delete
module_function :delete_dependency
module_function :delete_all_dependency
module_function :delete_by_dependant
module_function :delete_all_by_dependant
-
+
module_function :finalize
module_function :finalize_dependency
module_function :finalize_all_dependency
@@ -197,9 +196,8 @@ module Finalizer
module_function :finalize_all
module_function :safe
-
+
module_function :final_of
private_class_method :final_of
-
-end
+end
diff --git a/lib/ftplib.rb b/lib/ftplib.rb
index 34ee2f8d62..a8edac8123 100644
--- a/lib/ftplib.rb
+++ b/lib/ftplib.rb
@@ -17,7 +17,7 @@ class FTPProtoError < FTPError; end
class FTP
- RCS_ID = '$Id: ftplib.rb,v 1.5 1997/09/16 08:03:31 shugo Exp $'
+ RCS_ID = %q$Id: ftplib.rb,v 1.5 1997/09/16 08:03:31 shugo Exp $
FTP_PORT = 21
CRLF = "\r\n"
diff --git a/lib/getopts.rb b/lib/getopts.rb
index 6929f7e4fd..1862f56080 100644
--- a/lib/getopts.rb
+++ b/lib/getopts.rb
@@ -11,7 +11,7 @@
#
#
-$RCS_ID="$Header$"
+$RCS_ID=%q$Header$
def isSingle(lopt)
if lopt.index(":")
diff --git a/lib/mathn.rb b/lib/mathn.rb
index fdf27f6771..b5cc9b818b 100644
--- a/lib/mathn.rb
+++ b/lib/mathn.rb
@@ -1,8 +1,8 @@
#
# mathn.rb -
# $Release Version: 0.5 $
-# $Revision: 1.1 $
-# $Date: 1997/07/03 04:43:47 $
+# $Revision: 1.1.1.1 $
+# $Date: 1998/01/16 04:05:49 $
# by Keiju ISHITSUKA(SHL Japan Inc.)
#
# --
diff --git a/lib/matrix.rb b/lib/matrix.rb
index 394c66f098..175981379f 100644
--- a/lib/matrix.rb
+++ b/lib/matrix.rb
@@ -36,7 +36,7 @@ module ExceptionForMatrix
end
class Matrix
- RCS_ID='-$Header: ruby-mode,v 1.2 91/04/20 17:24:57 keiju Locked $-'
+ RCS_ID='-$Header: matrix.rb,v 1.2 91/04/20 17:24:57 keiju Locked $-'
include ExceptionForMatrix
diff --git a/lib/mutex_m.rb b/lib/mutex_m.rb
index 823888e72f..693da41675 100644
--- a/lib/mutex_m.rb
+++ b/lib/mutex_m.rb
@@ -1,8 +1,8 @@
#
# mutex_m.rb -
# $Release Version: 2.0$
-# $Revision: 1.2 $
-# $Date: 1997/07/25 02:43:21 $
+# $Revision: 1.1.1.1 $
+# $Date: 1998/01/16 04:05:49 $
# Original from mutex.rb
# by Keiju ISHITSUKA(SHL Japan Inc.)
#
diff --git a/lib/parsearg.rb b/lib/parsearg.rb
index a0ef90f018..6811dd3b97 100644
--- a/lib/parsearg.rb
+++ b/lib/parsearg.rb
@@ -11,7 +11,7 @@
#
#
-$RCS_ID="$Header$"
+$RCS_ID=%q$Header$
load("getopts.rb")
diff --git a/lib/parsedate.rb b/lib/parsedate.rb
index 1c1dda76bc..69b7ae98a9 100644
--- a/lib/parsedate.rb
+++ b/lib/parsedate.rb
@@ -4,39 +4,66 @@ module ParseDate
'may' => 5, 'jun' => 6, 'jul' => 7, 'aug' => 8,
'sep' => 9, 'oct' =>10, 'nov' =>11, 'dec' =>12 }
MONTHPAT = MONTHS.keys.join('|')
- DAYPAT = 'mon|tue|wed|thu|fri|sat|sun'
+ DAYS = {
+ 'sun' => 0, 'mon' => 1, 'tue' => 2, 'wed' => 3,
+ 'thu' => 4, 'fri' => 5, 'sat' => 6 }
+ DAYPAT = DAYS.keys.join('|')
def parsedate(date)
- if date.sub!(/(#{DAYPAT})/i, ' ')
- dayofweek = $1
+ # ISO 8601?
+ if date =~ /(\d\d\d\d)-?(?:(\d\d)-?(\d\d)?)? *(?:(\d\d):(\d\d)(?::(\d\d))?)?/
+ return $1.to_i,
+ if $2 then $2.to_i else 1 end,
+ if $3 then $3.to_i else 1 end,
+ nil,
+ if $4 then $4.to_i end,
+ if $5 then $5.to_i end,
+ if $6 then $6.to_i end,
+ nil
end
- if date.sub!(/\s+(\d+:\d+(:\d+)?)/, ' ')
- time = $1
+ date = date.dup
+ if date.sub!(/(#{DAYPAT})[a-z]*,?/i, ' ')
+ wday = DAYS[$1.downcase]
end
- if date =~ /19(\d\d)/
- year = Integer($1)
+ if date.sub!(/(\d+):(\d+)(?::(\d+))?\s*(am|pm)?\s*(?:\s+([a-z]{1,4}(?:\s+[a-z]{1,4})|[-+]\d{4}))?/i, ' ')
+ hour = $1.to_i
+ min = $2.to_i
+ if $3
+ sec = $3.to_i
+ end
+ if $4 == 'pm'
+ hour += 12
+ end
+ if $5
+ zone = $5
+ end
end
- if date.sub!(/\s*(\d+)\s+(#{MONTHPAT})\S*\s+/i, ' ')
- dayofmonth = $1.to_i
- monthname = $2
- elsif date.sub!(/\s*(#{MONTHPAT})\S*\s+(\d+)\s+/i, ' ')
- monthname = $1
- dayofmonth = $2.to_i
- elsif date.sub!(/\s*(#{MONTHPAT})\S*\s+(\d+)\D+/i, ' ')
- monthname = $1
- dayofmonth = $2.to_i
- elsif date.sub!(/\s*(\d\d?)\/(\d\d?)/, ' ')
- month = $1
- dayofmonth = $2.to_i
+ if date.sub!(/(\d+)\S*\s+(#{MONTHPAT})\S*(?:\s+(\d+))?/i, ' ')
+ mday = $1.to_i
+ mon = MONTHS[$2.downcase]
+ if $3
+ year = $3.to_i
+ end
+ elsif date.sub!(/(#{MONTHPAT})\S*\s+(\d+)\S*\s*,?(?:\s+(\d+))?/i, ' ')
+ mon = MONTHS[$1.downcase]
+ mday = $2.to_i
+ if $3
+ year = $3.to_i
+ end
+ elsif date.sub!(/(\d+)\/(\d+)(?:\/(\d+))/, ' ')
+ mon = $1.to_i
+ mday = $2.to_i
+ if $3
+ year = $3.to_i
+ end
end
- if monthname
- month = MONTHS[monthname.downcase]
- end
- if ! year && date =~ /\d\d/
- year = Integer($&)
- end
- return year, month, dayofmonth
+ return year, mon, mday, wday, hour, min, sec, zone
end
module_function :parsedate
end
+
+if __FILE__ == $0
+ p Time.now.asctime
+ p ParseDate.parsedate(Time.now.asctime)
+end
diff --git a/lib/rational.rb b/lib/rational.rb
index d4112c2956..a8c8322abc 100644
--- a/lib/rational.rb
+++ b/lib/rational.rb
@@ -1,8 +1,8 @@
#
# rational.rb -
# $Release Version: 0.5 $
-# $Revision: 1.1 $
-# $Date: 1996/11/11 04:25:14 $
+# $Revision: 1.1.1.1 $
+# $Date: 1998/01/16 04:05:49 $
# by Keiju ISHITSUKA(SHL Japan Inc.)
#
# --
diff --git a/lib/sync.rb b/lib/sync.rb
index b5a3fc32b3..1cf70a66ab 100644
--- a/lib/sync.rb
+++ b/lib/sync.rb
@@ -4,6 +4,7 @@
# $Revision$
# $Date$
# by Keiju ISHITSUKA
+# modified by matz
#
# --
# Sync_m, Synchronizer_m
@@ -43,7 +44,7 @@ unless defined? Thread
fail "Thread not available for this ruby interpreter"
end
-require "finalize"
+require "final"
module Sync_m
RCS_ID='-$Header$-'
@@ -321,7 +322,11 @@ module Sync_m
def For_primitive_object.extend_object(obj)
super
obj.sync_extended
- Finalizer.add(obj, For_primitive_object, :sync_finalize)
+ # Changed to use `final.rb'.
+ # Finalizer.add(obj, For_primitive_object, :sync_finalize)
+ ObjectSpace.define_finalizer(obj) do |id|
+ For_primitive_object.sync_finalize(id)
+ end
end
def initialize
diff --git a/lib/tempfile.rb b/lib/tempfile.rb
new file mode 100644
index 0000000000..9d986e7691
--- /dev/null
+++ b/lib/tempfile.rb
@@ -0,0 +1,88 @@
+#
+# $Id$
+#
+# The class for temporary files.
+# o creates a temporary file, which name is "basename.pid.n" with mode "w+".
+# o Tempfile objects can be used like IO object.
+# o with tmpfile.close(true) created temporary files are removed.
+# o created files are also removed on script termination.
+# o with Tempfile#open, you can reopen the temporary file.
+# o file mode of the temporary files are 0600.
+
+require 'delegate'
+require 'final'
+
+class Tempfile < SimpleDelegator
+ Max_try = 10
+
+ def Tempfile.callback(path)
+ lambda{
+ print "removing ", path, "..."
+ if File.exist?(path)
+ File.unlink(path)
+ end
+ if File.exist?(path + '.lock')
+ File.unlink(path + '.lock')
+ end
+ print "done\n"
+ }
+ end
+
+ def initialize(basename, tmpdir = '/tmp')
+ umask = File.umask(0177)
+ begin
+ n = 0
+ while true
+ begin
+ @tmpname = sprintf('%s/%s.%d.%d', tmpdir, basename, $$, n)
+ unless File.exist?(@tmpname)
+ File.symlink(tmpdir, @tmpname + '.lock')
+ break
+ end
+ rescue
+ raise "cannot generate tmpfile `%s'" % @tmpname if n >= Max_try
+ #sleep(1)
+ end
+ n += 1
+ end
+
+ @clean_files = Tempfile.callback(@tmpname)
+ ObjectSpace.define_finalizer(self, @clean_files)
+
+ @tmpfile = File.open(@tmpname, 'w+')
+ super(@tmpfile)
+ File.unlink(@tmpname + '.lock')
+ ensure
+ File.umask(umask)
+ end
+ end
+
+ def Tempfile.open(*args)
+ Tempfile.new(*args)
+ end
+
+ def open
+ @tmpfile.close if @tmpfile
+ @tmpfile = File.open(@tmpname, 'r+')
+ __setobj__(@tmpfile)
+ end
+
+ def close(real=false)
+ @tmpfile.close if @tmpfile
+ @tmpfile = nil
+ if real
+ @clean_files.call
+ ObjectSpace.undefine_finalizer(self)
+ end
+ end
+end
+
+if __FILE__ == $0
+ f = Tempfile.new("foo")
+ f.print("foo\n")
+ f.close
+ f = nil
+ f.open
+ p f.gets # => "foo\n"
+ f.close(true)
+end
diff --git a/lib/thread.rb b/lib/thread.rb
index 4f294cc9a3..8f7f6cdd6a 100644
--- a/lib/thread.rb
+++ b/lib/thread.rb
@@ -13,6 +13,10 @@ unless defined? ThreadError
end
end
+if $DEBUG
+ Thread.abort_on_exception = true
+end
+
class Mutex
def initialize
@waiting = []
@@ -107,4 +111,30 @@ class Queue
def length
@que.length
end
+ alias size length
+end
+
+class SizedQueue<Queue
+ def initialize(max)
+ @max = max
+ @queue_wait = []
+ super()
+ end
+
+ def push(obj)
+ while @que.length >= @max
+ @queue_wait.push Thread.current
+ Thread.stop
+ end
+ super
+ end
+
+ def pop(*args)
+ if @que.length < @max
+ t = @queue_wait.shift
+ t.run if t
+ end
+ pop = super
+ pop
+ end
end
diff --git a/lib/tk.rb b/lib/tk.rb
index 2cbbec02a8..5a3bf2052b 100644
--- a/lib/tk.rb
+++ b/lib/tk.rb
@@ -26,6 +26,9 @@ module TkComm
private :error_at
def tk_tcl2ruby(val)
+ if val.include? ?
+ return val.split.collect{|v| tk_tcl2ruby(v)}
+ end
case val
when /^-?\d+$/
val.to_i
@@ -241,6 +244,15 @@ module TkComm
uninstall_cmd myid
})
end
+
+ def update(idle=nil)
+ if idle
+ tk_call 'update', 'idletasks'
+ else
+ tk_call 'update'
+ end
+ end
+
end
module TkCore
@@ -963,6 +975,7 @@ class TkRoot<TkWindow
return ROOT[0] if ROOT[0]
new = super
ROOT[0] = new
+ Tk_WINDOWS["."] = new
end
def create_self
@path = '.'
@@ -1220,12 +1233,12 @@ module TkComposite
@delegates = {}
@delegates['DEFAULT'] = @frame
end
- if option.kind_of?(String)
- @delegates[option] = wins
- else
- for i in option
- @delegates[i] = wins
+ if @delegates[option].kind_of?(Array)
+ for i in wins
+ @delegates[option].push(i)
end
+ else
+ @delegates[option] = wins
end
end
@@ -1252,3 +1265,5 @@ autoload :TkBitmapImage, 'tkcanvas'
autoload :TkPhotoImage, 'tkcanvas'
autoload :TkEntry, 'tkentry'
autoload :TkText, 'tktext'
+autoload :TkDialog, 'tkdialog'
+autoload :TkMenubar, 'tkmenubar'
diff --git a/lib/tkcore.rb b/lib/tkcore.rb
deleted file mode 100644
index c151b0af9e..0000000000
--- a/lib/tkcore.rb
+++ /dev/null
@@ -1,528 +0,0 @@
-#
-# tkcore.rb - Tk interface modue without thread
-# $Date$
-# by Yukihiro Matsumoto <matz@caelum.co.jp>
-
-require "tkutil"
-if defined? Thread
- require "thread"
-end
-
-module Tk
- include TkUtil
- extend Tk
-
- wish_path = nil
- ENV['PATH'].split(":").each {|path|
- for wish in ['wish4.2', 'wish4.1', 'wish4.0', 'wish']
- if File.exist? path+'/'+wish
- wish_path = path+'/'+wish
- break
- end
- break if wish_path
- end
- }
- fail 'can\'t find wish' if not wish_path #'
-
- def Tk.tk_exit
- if not PORT.closed?
- PORT.print "exit\n"
- PORT.close
- end
- end
-
-# PORT = open(format("|%s -n %s", wish_path, File.basename($0)), "w+");
- PORT = open(format("|%s", wish_path), "w+");
- trap "EXIT", proc{Tk.tk_exit}
- trap "PIPE", ""
-
- def tk_write(*args)
- printf PORT, *args;
- PORT.print "\n"
- PORT.flush
- end
- tk_write '\
-wm withdraw .
-proc rb_out args {
- puts [format %%s $args]
- flush stdout
-}
-proc rb_ans arg {
- if [catch $arg var] {puts "!$var"} {puts "=$var@@"}
- flush stdout
-}
-proc tkerror args { exit }
-proc keepalive {} { rb_out alive; after 120000 keepalive}
-after 120000 keepalive'
-
- READABLE = []
- READ_CMD = {}
-
- def file_readable(port, cmd)
- if cmd == nil
- READABLE.delete port
- else
- READABLE.push port
- end
- READ_CMD[port] = cmd
- end
-
- WRITABLE = []
- WRITE_CMD = {}
- def file_writable(port, cmd)
- if cmd == nil
- WRITABLE.delete port
- else
- WRITABLE.push port
- end
- WRITE_CMD[port] = cmd
- end
- module_function :file_readable, :file_writable
-
- file_readable PORT, proc {
- line = PORT.gets
- exit if not line
- Tk.dispatch(line.chop!)
- }
-
- def error_at
- frames = caller(1)
- frames.delete_if do |c|
- c =~ %r!/tk(|core|thcore|canvas|text|entry|scrollbox)\.rb:\d+!
- end
- frames
- end
-
- def tk_tcl2ruby(val)
- case val
- when /^-?\d+$/
- val.to_i
- when /^\./
- $tk_window_list[val]
- when /^rb_out (c\d+)/
- $tk_cmdtbl[$1]
- when / /
- val.split.collect{|elt|
- tk_tcl2ruby(elt)
- }
- when /^-?\d+\.\d*$/
- val.to_f
- else
- val
- end
- end
-
- def tk_split_list(str)
- idx = str.index('{')
- return tk_tcl2ruby(str) if not idx
-
- list = tk_tcl2ruby(str[0,idx])
- str = str[idx+1..-1]
- i = -1
- brace = 1
- str.each_byte {|c|
- i += 1
- brace += 1 if c == ?{
- brace -= 1 if c == ?}
- break if brace == 0
- }
- if str[0, i] == ' '
- list.push ' '
- else
- list.push tk_split_list(str[0, i])
- end
- list += tk_split_list(str[i+1..-1])
- list
- end
- private :tk_tcl2ruby, :tk_split_list
-
- def bool(val)
- case bool
- when "1", 1, 'yes', 'true'
- TRUE
- else
- FALSE
- end
- end
- def number(val)
- case val
- when /^-?\d+$/
- val.to_i
- when /^-?\d+\.\d*$/
- val.to_f
- else
- val
- end
- end
- def string(val)
- if val == "{}"
- ''
- elsif val[0] == ?{
- val[1..-2]
- else
- val
- end
- end
- def list(val)
- tk_split_list(val)
- end
- def window(val)
- $tk_window_list[val]
- end
- def procedure(val)
- if val =~ /^rb_out (c\d+)/
- $tk_cmdtbl[$1]
- else
- nil
- end
- end
- private :bool, :number, :string, :list, :window, :procedure
-
- # mark for non-given arguments
- None = Object.new
- def None.to_s
- 'None'
- end
-
- $tk_event_queue = []
- def tk_call(str, *args)
- args = args.collect{|s|
- next if s == None
- if s.kind_of?(Hash)
- s = hash_kv(s).join(" ")
- else
- if not s
- s = "0"
- elsif s == TRUE
- s = "1"
- elsif s.kind_of?(TkObject)
- s = s.path
- elsif s.kind_of?(TkVariable)
- s = s.id
- else
- s = s.to_s
- s.gsub!(/["\\\$\[\]]/, '\\\\\0') #"
- s.gsub!(/\{/, '\\\\173')
- s.gsub!(/\}/, '\\\\175')
- end
- "\"#{s}\""
- end
- }
- str += " "
- str += args.join(" ")
- print str, "\n" if $DEBUG
- tk_write 'rb_ans {%s}', str
- while PORT.gets
- print $_ if $DEBUG
- $_.chop!
- if /^=(.*)@@$/
- val = $1
- break
- elsif /^=/
- val = $' + "\n"
- while TRUE
- PORT.readline
- if ~/@@$/
- val += $'
- return val
- else
- val += $_
- end
- end
- elsif /^!/
- $@ = error_at
- msg = $'
- if msg =~ /unknown option "-(.*)"/
- $! = NameError.new(format("undefined method `%s' for %s(%s)",
- $1, self, self.type)) #`'
- else
- $! = RuntimeError.new(format("%s - %s", self.type, msg))
- end
- fail
- end
- $tk_event_queue.push $_
- end
-
- while ev = $tk_event_queue.shift
- Tk.dispatch ev
- end
- fail 'wish closed' if PORT.closed?
-# tk_split_list(val)
- val
- end
-
- def hash_kv(keys)
- conf = []
- if keys
- for k, v in keys
- conf.push("-#{k}")
- v = install_cmd(v) if v.kind_of? Proc
- conf.push(v)
- end
- end
- conf
- end
- private :tk_call, :error_at, :hash_kv
-
- $tk_cmdid = 0
- def install_cmd(cmd)
- return '' if cmd == '' # uninstall cmd
- id = format("c%.4d", $tk_cmdid)
- $tk_cmdid += 1
- $tk_cmdtbl[id] = cmd
- @cmdtbl = [] if not @cmdtbl
- @cmdtbl.push id
- return format('rb_out %s', id)
- end
- def uninstall_cmd(id)
- $tk_cmdtbl[id] = nil
- end
- private :install_cmd, :uninstall_cmd
-
- $tk_window_list = {}
- class Event
- def initialize(seq,b,f,h,k,s,t,w,x,y,aa,ee,kk,nn,ww,tt,xx,yy)
- @serial = seq
- @num = b
- @focus = (f == 1)
- @height = h
- @keycode = k
- @state = s
- @time = t
- @width = w
- @x = x
- @y = y
- @char = aa
- @send_event = (ee == 1)
- @keysym = kk
- @keysym_num = nn
- @type = tt
- @widget = ww
- @x_root = xx
- @y_root = yy
- end
- attr :serial
- attr :num
- attr :focus
- attr :height
- attr :keycode
- attr :state
- attr :time
- attr :width
- attr :x
- attr :y
- attr :char
- attr :send_event
- attr :keysym
- attr :keysym_num
- attr :type
- attr :widget
- attr :x_root
- attr :y_root
- end
-
- def install_bind(cmd, args=nil)
- if args
- id = install_cmd(proc{|arg|
- TkUtil.eval_cmd cmd, *arg
- })
- id + " " + args
- else
- id = install_cmd(proc{|arg|
- TkUtil.eval_cmd cmd, Event.new(*arg)
- })
- id + " %# %b %f %h %k %s %t %w %x %y %A %E %K %N %W %T %X %Y"
- end
- end
-
- def _bind(path, context, cmd, args=nil)
- begin
- id = install_bind(cmd, args)
- tk_call 'bind', path, "<#{context}>", id
- rescue
- $tk_cmdtbl[id] = nil
- fail
- end
- end
- private :install_bind, :_bind
-
- def bind_all(context, cmd=Proc.new, args=nil)
- _bind 'all', context, cmd, args
- end
-
- def pack(*args)
- TkPack.configure *args
- end
-
- $tk_cmdtbl = {}
-
- def after(ms, cmd=Proc.new)
- myid = format("c%.4d", $tk_cmdid)
- tk_call 'after', ms,
- install_cmd(proc{
- TkUtil.eval_cmd cmd
- uninstall_cmd myid
- })
- end
-
- def update(idle=nil)
- if idle
- tk_call 'update', 'idletasks'
- else
- tk_call 'update'
- end
- end
-
- def dispatch(line)
- if line =~ /^c\d+/
- cmd = $&
- fail "no command `#{cmd}'" if not $tk_cmdtbl[cmd]
- args = tk_split_list($')
- TkUtil.eval_cmd $tk_cmdtbl[cmd], *args
- elsif line =~ /^alive$/
- # keep alive, do nothing
- else
- fail "malformed line <#{line}>"
- end
- end
-
- def mainloop
- begin
- tk_write 'after idle {wm deiconify .}'
- while TRUE
- rf, wf = select(READABLE, WRITABLE)
- for f in rf
- READ_CMD[f].call(f) if READ_CMD[f]
- if f.closed?
- READABLE.delete f
- READ_CMD[f] = nil
- end
- end
- for f in wf
- WRITE_CMD[f].call(f) if WRITE_CMD[f]
- if f.closed?
- WRITABLE.delete f
- WRITE_CMD[f] = nil
- end
- end
- end
- ensure
- Tk.tk_exit
- end
- end
-
- def root
- $tk_root
- end
-
- def bell
- tk_call 'bell'
- end
- module_function :after, :update, :dispatch, :mainloop, :root, :bell
-
- module Scrollable
- def xscrollcommand(cmd=Proc.new)
- configure_cmd 'xscrollcommand', cmd
- end
- def yscrollcommand(cmd=Proc.new)
- configure_cmd 'yscrollcommand', cmd
- end
- end
-
- module Wm
- def aspect(*args)
- w = window(tk_call('wm', 'grid', path, *args))
- w.split.collect{|s|s.to_i} if args.length == 0
- end
- def client(name=None)
- tk_call 'wm', 'client', path, name
- end
- def colormapwindows(*args)
- list(tk_call('wm', 'colormapwindows', path, *args))
- end
- def wm_command(value=None)
- string(tk_call('wm', 'command', path, value))
- end
- def deiconify
- tk_call 'wm', 'deiconify', path
- end
- def focusmodel(*args)
- tk_call 'wm', 'focusmodel', path, *args
- end
- def frame
- tk_call 'wm', 'frame', path
- end
- def geometry(*args)
- list(tk_call('wm', 'geometry', path, *args))
- end
- def grid(*args)
- w = tk_call('wm', 'grid', path, *args)
- list(w) if args.size == 0
- end
- def group(*args)
- tk_call 'wm', 'path', path, *args
- end
- def iconbitmap(*args)
- tk_call 'wm', 'bitmap', path, *args
- end
- def iconify
- tk_call 'wm', 'iconify'
- end
- def iconmask(*args)
- tk_call 'wm', 'iconmask', path, *args
- end
- def iconname(*args)
- tk_call 'wm', 'iconname', path, *args
- end
- def iconposition(*args)
- w = tk_call('wm', 'iconposition', path, *args)
- list(w) if args.size == 0
- end
- def iconwindow(*args)
- tk_call 'wm', 'iconwindow', path, *args
- end
- def maxsize(*args)
- w = tk_call('wm', 'maxsize', path, *args)
- list(w) if not args.size == 0
- end
- def minsize(*args)
- w = tk_call('wm', 'minsize', path, *args)
- list(w) if args.size == 0
- end
- def overrideredirect(bool=None)
- if bool == None
- bool(tk_call('wm', 'overrideredirect', path))
- else
- tk_call 'wm', 'overrideredirect', path, bool
- end
- end
- def positionfrom(*args)
- tk_call 'wm', 'positionfrom', path, *args
- end
- def protocol(name, func=None)
- func = install_cmd(func) if not func == None
- tk_call 'wm', 'command', path, name, func
- end
- def resizable(*args)
- w = tk_call('wm', 'resizable', path, *args)
- if args.length == 0
- list(w).collect{|e| bool(e)}
- end
- end
- def sizefrom(*args)
- list(tk_call('wm', 'sizefrom', path, *args))
- end
- def state
- tk_call 'wm', 'state', path
- end
- def title(*args)
- tk_call 'wm', 'title', path, *args
- end
- def transient(*args)
- tk_call 'wm', 'transient', path, *args
- end
- def withdraw
- tk_call 'wm', 'withdraw', path
- end
- end
-end
diff --git a/lib/tkmenubar.rb b/lib/tkmenubar.rb
new file mode 100644
index 0000000000..441f3f5c03
--- /dev/null
+++ b/lib/tkmenubar.rb
@@ -0,0 +1,137 @@
+#
+# tkmenubar.rb
+#
+# Copyright (C) 1998 maeda shugo. All rights reserved.
+# This file can be distributed under the terms of the Ruby.
+
+# Usage:
+#
+# menu_spec = [
+# [['File', 0],
+# ['Open', proc{puts('Open clicked')}, 0],
+# '---',
+# ['Quit', proc{exit}, 0]],
+# [['Edit', 0],
+# ['Cut', proc{puts('Cut clicked')}, 2],
+# ['Copy', proc{puts('Copy clicked')}, 0],
+# ['Paste', proc{puts('Paste clicked')}, 0]]
+# ]
+# menubar = TkMenubar.new(nil, menu_spec,
+# 'tearoff'=>false,
+# 'foreground'=>'grey40',
+# 'activeforeground'=>'red',
+# 'font'=>'-adobe-helvetica-bold-r-*--12-*-iso8859-1')
+# menubar.pack('side'=>'top', 'fill'=>'x')
+#
+#
+# OR
+#
+#
+# menubar = TkMenubar.new
+# menubar.add_menu([['File', 0],
+# ['Open', proc{puts('Open clicked')}, 0],
+# '---',
+# ['Quit', proc{exit}, 0]])
+# menubar.add_menu([['Edit', 0],
+# ['Cut', proc{puts('Cut clicked')}, 2],
+# ['Copy', proc{puts('Copy clicked')}, 0],
+# ['Paste', proc{puts('Paste clicked')}, 0]])
+# menubar.configure('tearoff', false)
+# menubar.configure('foreground', 'grey40')
+# menubar.configure('activeforeground', 'red')
+# menubar.configure('font', '-adobe-helvetica-bold-r-*--12-*-iso8859-1')
+# menubar.pack('side'=>'top', 'fill'=>'x')
+
+# The format of the menu_spec is:
+# [
+# [
+# [button text, underline, accelerator],
+# [menu label, command, underline, accelerator],
+# '---', # separator
+# ...
+# ],
+# ...
+# ]
+
+# underline and accelerator are optional parameters.
+# Hashes are OK instead of Arrays.
+
+# To use add_menu, configuration must be done by calling configure after
+# adding all menus by add_menu, not by the constructor arguments.
+
+require "tk"
+
+class TkMenubar<TkFrame
+
+ include TkComposite
+
+ def initialize(parent = nil, spec = nil, options = nil)
+ super(parent, options)
+
+ @menus = []
+
+ if spec
+ for menu_info in spec
+ add_menu(menu_info)
+ end
+ end
+
+ if options
+ for key, value in options
+ configure(key, value)
+ end
+ end
+ end
+
+ def add_menu(menu_info)
+ btn_info = menu_info.shift
+ mbtn = TkMenubutton.new(@frame)
+
+ if btn_info.kind_of?(Hash)
+ for key, value in btn_info
+ mbtn.configure(key, value)
+ end
+ elsif btn_info.kind_of?(Array)
+ mbtn.configure('text', btn_info[0]) if btn_info[0]
+ mbtn.configure('underline', btn_info[1]) if btn_info[1]
+ mbtn.configure('accelerator', btn_info[2]) if btn_info[2]
+ else
+ mbtn.configure('text', btn_info)
+ end
+
+ menu = TkMenu.new(mbtn)
+
+ for item_info in menu_info
+ if item_info.kind_of?(Hash)
+ menu.add('command', item_info)
+ elsif item_info.kind_of?(Array)
+ options = {}
+ options['label'] = item_info[0] if item_info[0]
+ options['command'] = item_info[1] if item_info[1]
+ options['underline'] = item_info[2] if item_info[2]
+ options['accelerator'] = item_info[3] if item_info[3]
+ menu.add('command', options)
+ elsif /^-+$/ =~ item_info
+ menu.add('sep')
+ else
+ menu.add('command', 'label' => item_info)
+ end
+ end
+
+ mbtn.menu(menu)
+ @menus.push([mbtn, menu])
+ delegate('tearoff', menu)
+ delegate('foreground', mbtn, menu)
+ delegate('background', mbtn, menu)
+ delegate('disabledforeground', mbtn, menu)
+ delegate('activeforeground', mbtn, menu)
+ delegate('activebackground', mbtn, menu)
+ delegate('font', mbtn, menu)
+ delegate('kanjifont', mbtn, menu)
+ mbtn.pack('side' => 'left')
+ end
+
+ def [](index)
+ return @menus[index]
+ end
+end
diff --git a/lib/tkthcore.rb b/lib/tkthcore.rb
deleted file mode 100644
index a6648502bd..0000000000
--- a/lib/tkthcore.rb
+++ /dev/null
@@ -1,550 +0,0 @@
-#
-# tkthcore.rb - Tk interface modue using thread
-# $Date$
-# by Yukihiro Matsumoto <matz@caelum.co.jp>
-
-require "tkutil"
-require "thread"
-
-module Tk
- include TkUtil
- extend Tk
-
- def Tk.tk_exit
- if not PORT.closed?
- tk_write "exit"
- PORT.close
- end
- end
-
- trap "EXIT", proc{Tk.tk_exit}
- trap "PIPE", ''
-
- wish_path = nil
- ENV['PATH'].split(":").each {|path|
- for wish in ['wish4.2', 'wish4.1', 'wish4.0', 'wish']
- if File.exist? path+'/'+wish
- wish_path = path+'/'+wish
- break
- end
- break if wish_path
- end
- }
- fail 'can\'t find wish' if not wish_path #'
-
- # mark for non-given arguments
- None = Object.new
- def None.to_s
- 'None'
- end
-
- Qin = Queue.new
- Qout = Queue.new
- Qwish = Queue.new
- Qcmd = Queue.new
- PORT = open(format("|%s -n %s", wish_path, File.basename($0)), "w+");
-
- $tk_not_init = TRUE
-
- def Tk.init
- $tk_not_init = FALSE
- Thread.start do
- loop do
- while line = PORT.gets
- line.chop!
- if line =~ /^[=!]/
- Qwish.push line
- else
- Qcmd.push line
- end
- end
- exit
- end
- end
-
- Thread.start do
- ary = [PORT]
- loop do
- str = Qin.pop
- print "Qin: ", str, "\n" if $DEBUG
- tk_write 'if [catch {%s} var] {puts "!$var"} {puts "=$var@@"};flush stdout', str
- line = tk_recv
- Qout.push(line)
- end
- end
- end
-
- $tk_event_queue = []
- def tk_recv()
- val = nil
- $_ = Qwish.pop
- loop do
- if /^=(.*)@@$/
- val = $1
- break
- elsif /^=/
- val = $' + "\n"
- while TRUE
- PORT.readline
- if ~/@@$/
- val += $'
- return val
- else
- val += $_
- end
- end
- elsif /^!/
- $@ = error_at
- msg = $'
- if msg =~ /unknown option "-(.*)"/
- fail NameError, format("undefined method `%s' for %s(%s)", $1, self, self.type) #`'
- else
- fail format("%s - %s", self.type, msg)
- end
- end
- end
-
- fail 'wish closed' if PORT.closed?
-# tk_split_list(val)
- val
- end
-
- def tk_call(str, *args)
- Tk.init if $tk_not_init
- args = args.collect{|s|
- next if s == None
- if s.kind_of?(Hash)
- s = hash_kv(s).join(" ")
- else
- if not s
- s = "0"
- elsif s == TRUE
- s = "1"
- elsif s.kind_of?(TkObject)
- s = s.path
- elsif s.kind_of?(TkVariable)
- s = s.id
- else
- s = s.to_s
- s.gsub!(/["\\\$\[\]]/, '\\\\\0') #"
- s.gsub!(/\{/, '\\\\173')
- s.gsub!(/\}/, '\\\\175')
- end
- "\"#{s}\""
- end
- }
- str += " "
- str += args.join(" ")
- Qin.push str
- return Qout.pop
- end
-
- def tk_write(*args)
- PORT.printf *args; PORT.print "\n"
- PORT.flush
- end
- module_function :tk_write, :tk_recv
- tk_write '\
-wm withdraw .
-proc rb_out args {
- puts [format %%s $args]
- flush stdout
-}
-proc tkerror args { exit }
-proc keepalive {} { rb_out alive; after 120000 keepalive}
-after 120000 keepalive'
-
- READ_TH = {}
- def file_readable(port, cmd)
- if cmd == nil
- if READ_TH[port].has_key?
- READ_TH[port].exit
- READ_TH[port] = nil
- end
- else
- READ_TH[port] = Thread.start{
- loop do
- TkUtil.eval_cmd cmd
- end
- }
- end
- end
-
- WRITE_TH = {}
- def file_writable(port, cmd)
- if cmd == nil
- if WRITE_TH[port].has_key?
- WRITE_TH[port].exit
- end
- else
- WRITE_TH[port] = Thread.start{
- loop do
- TkUtil.eval_cmd cmd
- end
- }
- end
- end
- module_function :file_readable, :file_writable
-
- def tk_tcl2ruby(val)
- case val
- when /^-?\d+$/
- val.to_i
- when /^\./
- $tk_window_list[val]
- when /^rb_out (c\d+)/
- $tk_cmdtbl[$1]
- when / /
- val.split.collect{|elt|
- tk_tcl2ruby(elt)
- }
- when /^-?\d+\.\d*$/
- val.to_f
- else
- val
- end
- end
-
- def tk_split_list(str)
- idx = str.index('{')
- return tk_tcl2ruby(str) if not idx
-
- list = tk_tcl2ruby(str[0,idx])
- str = str[idx+1..-1]
- i = -1
- brace = 1
- str.each_byte {|c|
- i += 1
- brace += 1 if c == ?{
- brace -= 1 if c == ?}
- break if brace == 0
- }
- if str[0, i] == ' '
- list.push ' '
- else
- list.push tk_split_list(str[0, i])
- end
- list += tk_split_list(str[i+1..-1])
- list
- end
- private :tk_tcl2ruby, :tk_split_list
-
- def dispatch(line)
- if line =~ /^c\d+/
- cmd = $&
- fail "no command `#{cmd}'" if not $tk_cmdtbl[cmd]
- args = tk_split_list($')
- TkUtil.eval_cmd $tk_cmdtbl[cmd], *args
- elsif line =~ /^alive$/
- # keep alive, do nothing
- else
- fail "malformed line <#{line}>"
- end
- end
- module_function :dispatch
-
- def error_at
- frames = caller(1)
- frames.delete_if do |c|
- c =~ %r!/tk(|core|thcore|canvas|text|entry|scrollbox)\.rb:\d+!
- end
- frames
- end
-
- def bool(val)
- case bool
- when "1", 1, 'yes', 'true'
- TRUE
- else
- FALSE
- end
- end
- def number(val)
- case val
- when /^-?\d+$/
- val.to_i
- when /^-?\d+\.\d*$/
- val.to_f
- else
- val
- end
- end
- def string(val)
- if val == "{}"
- ''
- elsif val[0] == ?{
- val[1..-2]
- else
- val
- end
- end
- def list(val)
- tk_split_list(val)
- end
- def window(val)
- $tk_window_list[val]
- end
- def procedure(val)
- if val =~ /^rb_out (c\d+)/
- $tk_cmdtbl[$1]
- else
- nil
- end
- end
- private :bool, :number, :string, :list, :window, :procedure
-
- def hash_kv(keys)
- conf = []
- if keys
- for k, v in keys
- conf.push("-#{k}")
- v = install_cmd(v) if v.kind_of? Proc
- conf.push(v)
- end
- end
- conf
- end
- private :tk_call, :error_at, :hash_kv
-
- $tk_cmdid = 0
- def install_cmd(cmd)
- return '' if cmd == '' # uninstall cmd
- id = format("c%.4d", $tk_cmdid)
- $tk_cmdid += 1
- $tk_cmdtbl[id] = cmd
- @cmdtbl = [] if not @cmdtbl
- @cmdtbl.push id
- return format('rb_out %s', id)
- end
- def uninstall_cmd(id)
- $tk_cmdtbl[id] = nil
- end
- private :install_cmd, :uninstall_cmd
-
- $tk_window_list = {}
- class Event
- def initialize(seq,b,f,h,k,s,t,w,x,y,aa,ee,kk,nn,ww,tt,xx,yy)
- @serial = seq
- @num = b
- @focus = (f == 1)
- @height = h
- @keycode = k
- @state = s
- @time = t
- @width = w
- @x = x
- @y = y
- @char = aa
- @send_event = (ee == 1)
- @keysym = kk
- @keysym_num = nn
- @type = tt
- @widget = ww
- @x_root = xx
- @y_root = yy
- end
- attr :serial
- attr :num
- attr :focus
- attr :height
- attr :keycode
- attr :state
- attr :time
- attr :width
- attr :x
- attr :y
- attr :char
- attr :send_event
- attr :keysym
- attr :keysym_num
- attr :type
- attr :widget
- attr :x_root
- attr :y_root
- end
-
- def install_bind(cmd, args=nil)
- if args
- id = install_cmd(proc{|arg|
- TkUtil.eval_cmd cmd, *arg
- })
- id + " " + args
- else
- id = install_cmd(proc{|arg|
- TkUtil.eval_cmd cmd, Event.new(*arg)
- })
- id + " %# %b %f %h %k %s %t %w %x %y %A %E %K %N %W %T %X %Y"
- end
- end
-
- def _bind(path, context, cmd, args=nil)
- begin
- id = install_bind(cmd, args)
- tk_call 'bind', path, "<#{context}>", id
- rescue
- $tk_cmdtbl[id] = nil
- fail
- end
- end
- private :install_bind, :_bind
-
- def bind_all(context, cmd=Proc.new, args=nil)
- _bind 'all', context, cmd, args
- end
-
- def pack(*args)
- TkPack.configure *args
- end
-
- $tk_cmdtbl = {}
-
- Qafter = Queue.new
- def after(ms, cmd=Proc.new)
- unless $tk_after_thread
- $tk_after_thread = Thread.start{
- loop do
- cmd = Qafter.pop
- TkUtil.eval_cmd cmd
- end
- }
- end
- Thread.start do
- sleep Float(ms)/1000
- Qafter.push cmd
- end
- end
-
- def update(idle=nil)
- if idle
- tk_call 'update', 'idletasks'
- else
- tk_call 'update'
- end
- end
-
- def root
- $tk_root
- end
-
- def bell
- tk_call 'bell'
- end
-
- def mainloop
- begin
- tk_call 'after', 'idle', 'wm deiconify .'
- loop do
- dispatch Qcmd.pop
- end
- ensure
- Tk.tk_exit
- end
- end
- module_function :after, :update, :dispatch, :mainloop, :root, :bell
-
- module Scrollable
- def xscrollcommand(cmd=Proc.new)
- configure_cmd 'xscrollcommand', cmd
- end
- def yscrollcommand(cmd=Proc.new)
- configure_cmd 'yscrollcommand', cmd
- end
- end
-
- module Wm
- def aspect(*args)
- w = window(tk_call('wm', 'grid', path, *args))
- w.split.collect{|s|s.to_i} if args.length == 0
- end
- def client(name=None)
- tk_call 'wm', 'client', path, name
- end
- def colormapwindows(*args)
- list(tk_call('wm', 'colormapwindows', path, *args))
- end
- def wm_command(value=None)
- string(tk_call('wm', 'command', path, value))
- end
- def deiconify
- tk_call 'wm', 'deiconify', path
- end
- def focusmodel(*args)
- tk_call 'wm', 'focusmodel', path, *args
- end
- def frame
- tk_call 'wm', 'frame', path
- end
- def geometry(*args)
- list(tk_call('wm', 'geometry', path, *args))
- end
- def grid(*args)
- w = tk_call('wm', 'grid', path, *args)
- list(w) if args.size == 0
- end
- def group(*args)
- tk_call 'wm', 'path', path, *args
- end
- def iconbitmap(*args)
- tk_call 'wm', 'bitmap', path, *args
- end
- def iconify
- tk_call 'wm', 'iconify'
- end
- def iconmask(*args)
- tk_call 'wm', 'iconmask', path, *args
- end
- def iconname(*args)
- tk_call 'wm', 'iconname', path, *args
- end
- def iconposition(*args)
- w = tk_call('wm', 'iconposition', path, *args)
- list(w) if args.size == 0
- end
- def iconwindow(*args)
- tk_call 'wm', 'iconwindow', path, *args
- end
- def maxsize(*args)
- w = tk_call('wm', 'maxsize', path, *args)
- list(w) if not args.size == 0
- end
- def minsize(*args)
- w = tk_call('wm', 'minsize', path, *args)
- list(w) if args.size == 0
- end
- def overrideredirect(bool=None)
- if bool == None
- bool(tk_call('wm', 'overrideredirect', path))
- else
- tk_call 'wm', 'overrideredirect', path, bool
- end
- end
- def positionfrom(*args)
- tk_call 'wm', 'positionfrom', path, *args
- end
- def protocol(name, func=None)
- func = install_cmd(func) if not func == None
- tk_call 'wm', 'command', path, name, func
- end
- def resizable(*args)
- w = tk_call('wm', 'resizable', path, *args)
- if args.length == 0
- list(w).collect{|e| bool(e)}
- end
- end
- def sizefrom(*args)
- list(tk_call('wm', 'sizefrom', path, *args))
- end
- def state
- tk_call 'wm', 'state', path
- end
- def title(*args)
- tk_call 'wm', 'title', path, *args
- end
- def transient(*args)
- tk_call 'wm', 'transient', path, *args
- end
- def withdraw
- tk_call 'wm', 'withdraw', path
- end
- end
-end
diff --git a/lib/tracer.rb b/lib/tracer.rb
index d37339fd62..ef03fe09c9 100644
--- a/lib/tracer.rb
+++ b/lib/tracer.rb
@@ -1,7 +1,23 @@
+#!/usr/local/bin/ruby
+#
+# tracer.rb -
+# $Release Version: 0.2$
+# $Revision: 1.6 $
+# $Date: 1998/02/02 08:12:02 $
+# by Keiju ISHITSUKA(Nippon Rational Inc.)
+#
+# --
+#
+#
+#
+
+#
+# tracer main class
+#
class Tracer
- MY_FILE_NAME_PATTERN = /^tracer\.(rb)?/
- Threads = Hash.new
- Sources = Hash.new
+ RCS_ID='-$Id: tracer.rb,v 1.6 1998/02/02 08:12:02 keiju Exp keiju $-'
+
+ MY_FILE_NAME = caller(0)[0].scan(/^(.*):[0-9]+$/)[0]
EVENT_SYMBOL = {
"line" => "-",
@@ -10,11 +26,31 @@ class Tracer
"class" => "C",
"end" => "E"}
+ def initialize
+ @threads = Hash.new
+ if defined? Thread.main
+ @threads[Thread.main.id] = 0
+ else
+ @threads[Thread.current.id] = 0
+ end
+
+ @sources = Hash.new
+ end
+
def on
- set_trace_func proc{|event, file, line, id, binding|
- trace_func event, file, line, id, binding
- }
- print "Trace on\n"
+ if iterator?
+ on
+ begin
+ yield
+ ensure
+ off
+ end
+ else
+ set_trace_func proc{|event, file, line, id, binding|
+ trace_func event, file, line, id, binding
+ }
+ print "Trace on\n"
+ end
end
def off
@@ -22,27 +58,38 @@ class Tracer
print "Trace off\n"
end
- def get_thread_no
- unless no = Threads[Thread.current.id]
- Threads[Thread.current.id] = no = Threads.size
+ def get_line(file, line)
+ unless list = @sources[file]
+# print file if $DEBUG
+ begin
+ f = open(file)
+ begin
+ @sources[file] = list = f.readlines
+ ensure
+ f.close
+ end
+ rescue
+ @sources[file] = list = []
+ end
+ end
+ if l = list[line - 1]
+ l
+ else
+ "-\n"
end
- no
end
- def get_line(file, line)
- unless list = Sources[file]
- f =open(file)
- begin
- Sources[file] = list = f.readlines
- ensure
- f.close
- end
+ def get_thread_no
+ if no = @threads[Thread.current.id]
+ no
+ else
+ @threads[Thread.current.id] = @threads.size
end
- list[line - 1]
end
def trace_func(event, file, line, id, binding)
- return if File.basename(file) =~ MY_FILE_NAME_PATTERN
+ return if file == MY_FILE_NAME
+ #printf "Th: %s\n", Thread.current.inspect
Thread.critical = TRUE
printf("#%d:%s:%d:%s: %s",
@@ -65,11 +112,15 @@ class Tracer
end
-if File.basename($0) =~ Tracer::MY_FILE_NAME_PATTERN
- $0 = ARGV.shift
-
- Tracer.on
- load $0
-else
- Tracer.on
+if caller(0).size == 1
+ if $0 == Tracer::MY_FILE_NAME
+ # direct call
+
+ $0 = ARGV[0]
+ ARGV.shift
+ Tracer.on
+ require $0
+ else
+ Tracer.on
+ end
end
diff --git a/lib/weakref.rb b/lib/weakref.rb
index 93b2c65ecd..18d3bbc9a3 100644
--- a/lib/weakref.rb
+++ b/lib/weakref.rb
@@ -10,7 +10,7 @@
require "delegate"
-class WeakRef<Delegater
+class WeakRef<Delegator
Exception :RefError
diff --git a/marshal.c b/marshal.c
index ac95e438ae..7d4d987829 100644
--- a/marshal.c
+++ b/marshal.c
@@ -621,7 +621,7 @@ r_object(arg)
if (rb_special_const_p(v)) {
ArgError("dump format error (user class)");
}
- RBASIC(v)->class = c;
+ RBASIC(v)->klass = c;
return v;
}
diff --git a/math.c b/math.c
index 0e427035f4..775bddaf16 100644
--- a/math.c
+++ b/math.c
@@ -6,7 +6,7 @@
$Date$
created at: Tue Jan 25 14:12:56 JST 1994
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
diff --git a/missing/dir.h b/missing/dir.h
index 34be77b9c0..6cf5318fa9 100644
--- a/missing/dir.h
+++ b/missing/dir.h
@@ -1,11 +1,14 @@
-/* $RCSfile: dir.h,v $$Revision: 4.0.1.1 $$Date: 91/06/07 11:22:10 $
+/* $RCSfile: dir.h,v $$Revision: 1.1.1.2 $$Date: 1998/01/16 04:14:54 $
*
* (C) Copyright 1987, 1990 Diomidis Spinellis.
*
* You may distribute under the terms of either the GNU General Public
* License or the Artistic License, as specified in the README file.
*
- * $Log: dir.h,v $
+ * $Log: dir.h,v $
+ * Revision 1.1.1.2 1998/01/16 04:14:54 matz
+ * *** empty log message ***
+ *
* Revision 4.0.1.1 91/06/07 11:22:10 lwall
* patch4: new copyright notice
*
@@ -61,14 +64,17 @@ void rewinddir(DIR *dirp);
void closedir(DIR *dirp);
#endif /* __DIR_INCLUDED */
-/* $RCSfile: dir.h,v $$Revision: 4.0.1.1 $$Date: 91/06/07 11:22:10 $
+/* $RCSfile: dir.h,v $$Revision: 1.1.1.2 $$Date: 1998/01/16 04:14:54 $
*
* (C) Copyright 1987, 1990 Diomidis Spinellis.
*
* You may distribute under the terms of either the GNU General Public
* License or the Artistic License, as specified in the README file.
*
- * $Log: dir.h,v $
+ * $Log: dir.h,v $
+ * Revision 1.1.1.2 1998/01/16 04:14:54 matz
+ * *** empty log message ***
+ *
* Revision 4.0.1.1 91/06/07 11:22:10 lwall
* patch4: new copyright notice
*
@@ -122,14 +128,17 @@ void rewinddir(DIR *dirp);
void closedir(DIR *dirp);
#endif /* __DIR_INCLUDED */
-/* $RCSfile: dir.h,v $$Revision: 4.0.1.1 $$Date: 91/06/07 11:22:10 $
+/* $RCSfile: dir.h,v $$Revision: 1.1.1.2 $$Date: 1998/01/16 04:14:54 $
*
* (C) Copyright 1987, 1990 Diomidis Spinellis.
*
* You may distribute under the terms of either the GNU General Public
* License or the Artistic License, as specified in the README file.
*
- * $Log: dir.h,v $
+ * $Log: dir.h,v $
+ * Revision 1.1.1.2 1998/01/16 04:14:54 matz
+ * *** empty log message ***
+ *
* Revision 4.0.1.1 91/06/07 11:22:10 lwall
* patch4: new copyright notice
*
diff --git a/node.h b/node.h
index cdb354c007..b5a837a091 100644
--- a/node.h
+++ b/node.h
@@ -6,7 +6,7 @@
$Date$
created at: Fri May 28 15:14:02 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -101,6 +101,9 @@ enum node_type {
NODE_TAG,
NODE_NEWLINE,
NODE_POSTEXE,
+#ifdef C_ALLOCA
+ NODE_ALLOCA,
+#endif
};
typedef struct RNode {
@@ -116,15 +119,15 @@ typedef struct RNode {
union {
struct RNode *node;
ID id;
- int argc;
+ INT argc;
VALUE value;
} u2;
union {
struct RNode *node;
ID id;
- int state;
+ INT state;
struct global_entry *entry;
- int cnt;
+ INT cnt;
VALUE value;
} u3;
} NODE;
diff --git a/numeric.c b/numeric.c
index b0d5f7f522..61e695a605 100644
--- a/numeric.c
+++ b/numeric.c
@@ -6,7 +6,7 @@
$Date$
created at: Fri Aug 13 18:33:09 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -40,20 +40,48 @@ num_coerce(x, y)
return assoc_new(rb_Float(x),rb_Float(y));
}
-VALUE
-num_coerce_bin(x, y)
- VALUE x, y;
+coerce_body(x)
+ VALUE *x;
+{
+ return rb_funcall(x[1], coerce, 1, x[0]);
+}
+
+coerce_rescue(x)
+ VALUE *x;
+{
+ TypeError("%s can't convert into %s",
+ rb_class2name(CLASS_OF(x[1])),
+ rb_class2name(CLASS_OF(x[0])));
+}
+
+static void
+do_coerce(x, y)
+ VALUE *x, *y;
{
VALUE ary;
+#if 0
+ VALUE a[2];
- ary = rb_funcall(y, coerce, 1, x);
+ a[0] = *x; a[1] = *y;
+ ary = rb_rescue(coerce_body, a, coerce_rescue, a);
+#else
+ ary = rb_funcall(*y, coerce, 1, *x);
+#endif
if (TYPE(ary) != T_ARRAY || RARRAY(ary)->len != 2) {
TypeError("coerce must return [x, y]");
}
- x = RARRAY(ary)->ptr[0];
- y = RARRAY(ary)->ptr[1];
+ *x = RARRAY(ary)->ptr[0];
+ *y = RARRAY(ary)->ptr[1];
+}
+VALUE
+num_coerce_bin(x, y)
+ VALUE x, y;
+{
+ VALUE ary;
+
+ do_coerce(&x, &y);
return rb_funcall(x, rb_frame_last_func(), 1, y);
}
@@ -68,17 +96,12 @@ static VALUE
num_uminus(num)
VALUE num;
{
- VALUE ary, x, y;
-
- ary = rb_funcall(num, coerce, 1, INT2FIX(0));
- if (TYPE(ary) != T_ARRAY || RARRAY(ary)->len != 2) {
- TypeError("coerce must return [x, y]");
- }
+ VALUE zero;
- x = RARRAY(ary)->ptr[0];
- y = RARRAY(ary)->ptr[1];
+ zero = INT2FIX(0);
+ do_coerce(&num, &zero);
- return rb_funcall(x, '-', 1, y);
+ return rb_funcall(zero, '-', 1, num);
}
static VALUE
@@ -824,7 +847,7 @@ fix_rshift(x, y)
long i, val;
i = NUM2INT(y);
- if (y < 32) {
+ if (i < sizeof(INT) * 8) {
val = RSHIFT(FIX2INT(x), i);
return INT2FIX(val);
}
diff --git a/object.c b/object.c
index 2e614b3a41..90d774a1f0 100644
--- a/object.c
+++ b/object.c
@@ -6,7 +6,7 @@
$Date$
created at: Thu Jul 15 12:01:24 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -81,7 +81,7 @@ obj_type(obj)
{
VALUE cl = CLASS_OF(obj);
- if (FL_TEST(cl, FL_SINGLETON)) {
+ while (FL_TEST(cl, FL_SINGLETON) || TYPE(cl) == T_ICLASS) {
cl = RCLASS(cl)->super;
}
return cl;
@@ -96,12 +96,12 @@ obj_clone(obj)
if (TYPE(obj) != T_OBJECT) {
TypeError("can't clone %s", rb_class2name(CLASS_OF(obj)));
}
- clone = obj_alloc(RBASIC(obj)->class);
+ clone = obj_alloc(RBASIC(obj)->klass);
CLONESETUP(clone,obj);
if (ROBJECT(obj)->iv_tbl) {
ROBJECT(clone)->iv_tbl = st_copy(ROBJECT(obj)->iv_tbl);
- RBASIC(clone)->class = singleton_class_clone(RBASIC(obj)->class);
- RBASIC(clone)->flags = RBASIC(obj)->flags;
+ RBASIC(clone)->klass = singleton_class_clone(RBASIC(obj)->klass);
+ RBASIC(clone)->flags = RBASIC(obj)->flags;
}
return clone;
@@ -386,7 +386,7 @@ static VALUE
mod_to_s(class)
VALUE class;
{
- return rb_class_path(class);
+ return str_dup(rb_class_path(class));
}
static VALUE
@@ -488,8 +488,8 @@ class_s_new(argc, argv)
}
klass = class_new(super);
/* make metaclass */
- RBASIC(klass)->class = singleton_class_new(RBASIC(super)->class);
- singleton_class_attached(RBASIC(klass)->class, klass);
+ RBASIC(klass)->klass = singleton_class_new(RBASIC(super)->klass);
+ singleton_class_attached(RBASIC(klass)->klass, klass);
return klass;
}
@@ -680,7 +680,7 @@ fail_to_flo(val)
double big2dbl();
-static VALUE
+VALUE
f_float(obj, arg)
VALUE obj, arg;
{
@@ -721,6 +721,15 @@ f_string(obj, arg)
return rb_funcall(arg, rb_intern("to_s"), 0);
}
+char*
+str2cstr(str)
+ VALUE str;
+{
+ if (NIL_P(str)) return NULL;
+ Check_Type(str, T_STRING);
+ return RSTRING(str)->ptr;
+}
+
VALUE
rb_String(val)
VALUE val;
@@ -765,7 +774,7 @@ boot_defclass(name, super)
rb_name_class(obj, id);
st_add_direct(rb_class_tbl, id, obj);
- return (VALUE)obj;
+ return obj;
}
VALUE
@@ -777,7 +786,7 @@ rb_class_of(obj)
if (obj == FALSE) return cFalseClass;
if (obj == TRUE) return cTrueClass;
- return RBASIC(obj)->class;
+ return RBASIC(obj)->klass;
}
VALUE TopSelf;
@@ -791,11 +800,11 @@ Init_Object()
cModule = boot_defclass("Module", cObject);
cClass = boot_defclass("Class", cModule);
- metaclass = RBASIC(cObject)->class = singleton_class_new(cClass);
+ metaclass = RBASIC(cObject)->klass = singleton_class_new(cClass);
singleton_class_attached(metaclass, cObject);
- metaclass = RBASIC(cModule)->class = singleton_class_new(metaclass);
+ metaclass = RBASIC(cModule)->klass = singleton_class_new(metaclass);
singleton_class_attached(metaclass, cModule);
- metaclass = RBASIC(cClass)->class = singleton_class_new(metaclass);
+ metaclass = RBASIC(cClass)->klass = singleton_class_new(metaclass);
singleton_class_attached(metaclass, cClass);
mKernel = rb_define_module("Kernel");
diff --git a/pack.c b/pack.c
index 20d12d4003..52a0dd5027 100644
--- a/pack.c
+++ b/pack.c
@@ -6,7 +6,7 @@
$Date$
created at: Thu Feb 10 15:17:05 JST 1994
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
diff --git a/parse.y b/parse.y
index 4bf13cf398..8a3c2ef9a7 100644
--- a/parse.y
+++ b/parse.y
@@ -6,7 +6,7 @@
$Date$
created at: Fri May 28 18:02:42 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -158,6 +158,8 @@ static void top_local_setup();
kDEFINED
klBEGIN
klEND
+ k__LINE__
+ k__FILE__
%token <id> IDENTIFIER FID GVAR IVAR CONSTANT
%token <val> INTEGER FLOAT STRING XSTRING REGEXP
@@ -175,8 +177,8 @@ static void top_local_setup();
%type <id> variable symbol operation assoc_kw
%type <id> cname fname op rest_arg
%type <num> f_arg
-%token oUPLUS /* unary+ */
-%token MINUS /* unary- */
+%token UPLUS /* unary+ */
+%token UMINUS /* unary- */
%token POW /* ** */
%token CMP /* <=> */
%token EQ /* == */
@@ -208,6 +210,7 @@ static void top_local_setup();
%right kNOT
%nonassoc kDEFINED
%right '=' OP_ASGN
+%right '?' ':'
%nonassoc DOT2 DOT3
%left OROP
%left ANDOP
@@ -458,10 +461,6 @@ lhs : variable
{
$$ = attrset($1, $3, 0);
}
- | primary '.' CONSTANT
- {
- $$ = attrset($1, $3, 0);
- }
| backref
{
backref_error($1);
@@ -696,6 +695,12 @@ arg : variable '=' arg
in_defined = 0;
$$ = NEW_DEFINED($4);
}
+ | arg '?' arg ':' arg
+ {
+ value_expr($1);
+ $$ = NEW_IF(cond($1), $3, $5);
+ fixpos($$, $1);
+ }
| primary
{
$$ = $1;
@@ -977,9 +982,6 @@ primary : literal
}
| kCLASS LSHFT expr term
{
- if (cur_mid || in_single)
- yyerror("class definition in method body");
-
class_nest++;
cref_push();
local_push();
@@ -1236,6 +1238,8 @@ variable : IDENTIFIER
| kSELF {$$ = kSELF;}
| kTRUE {$$ = kTRUE;}
| kFALSE {$$ = kFALSE;}
+ | k__FILE__ {$$ = k__FILE__;}
+ | k__LINE__ {$$ = k__LINE__;}
var_ref : variable
{
@@ -1257,7 +1261,7 @@ superclass : term
{
$$ = $3;
}
- | error term {yyerrok;}
+ | error term {yyerrok; $$ = 0}
f_arglist : '(' f_args ')'
{
@@ -1988,6 +1992,15 @@ parse_qstring(term)
return STRING;
}
+static int
+parse_quotedword(term)
+ int term;
+{
+ if (parse_qstring(term) == 0) return 0;
+ yylval.node = NEW_CALL(NEW_STR(yylval.val), rb_intern("split"), 0);
+ return DSTRING;
+}
+
char *strdup();
static int
@@ -2041,6 +2054,7 @@ here_document(term)
free(eos);
return 0;
}
+ sourceline++;
if (strncmp(eos, RSTRING(line)->ptr, len) == 0 &&
(RSTRING(line)->ptr[len] == '\n' ||
RSTRING(line)->ptr[len] == '\r')) {
@@ -2049,7 +2063,6 @@ here_document(term)
lex_pbeg = lex_p = RSTRING(line)->ptr;
lex_pend = lex_p + RSTRING(line)->len;
- sourceline++;
switch (parse_string(term, '\n')) {
case STRING:
case XSTRING:
@@ -2298,7 +2311,20 @@ retry:
return parse_qstring(c);
case '?':
- if ((c = nextc()) == '\\') {
+ if (lex_state == EXPR_END) {
+ Warning("a?b:c is undocumented feature ^^;;;");
+ lex_state = EXPR_BEG;
+ return '?';
+ }
+ c = nextc();
+ if (lex_state == EXPR_ARG && space_seen && isspace(c)){
+ pushback(c);
+ arg_ambiguous();
+ lex_state = EXPR_BEG;
+ Warning("a?b:c is undocumented feature ^^;;;");
+ return '?';
+ }
+ if (c == '\\') {
c = read_escape();
}
c &= 0xff;
@@ -2379,6 +2405,7 @@ retry:
return OP_ASGN;
}
if (c == '>') {
+ Warning("-> is undocumented feature ^^;;;");
lex_state = EXPR_BEG;
return KW_ASSOC;
}
@@ -2544,8 +2571,10 @@ retry:
return COLON2;
}
pushback(c);
- if (isspace(c))
+ if (lex_state == EXPR_END || isspace(c)) {
+ lex_state = EXPR_BEG;
return ':';
+ }
lex_state = EXPR_FNAME;
return SYMBEG;
@@ -2579,9 +2608,6 @@ retry:
return c;
case ',':
- lex_state = EXPR_BEG;
- return c;
-
case ';':
lex_state = EXPR_BEG;
return c;
@@ -2600,11 +2626,6 @@ retry:
c = LPAREN;
lex_state = EXPR_BEG;
}
- else if (lex_state == EXPR_ARG && space_seen) {
- arg_ambiguous();
- c = LPAREN;
- lex_state = EXPR_BEG;
- }
else {
lex_state = EXPR_BEG;
}
@@ -2686,6 +2707,9 @@ retry:
case 'q':
return parse_qstring(term);
+ case 'w':
+ return parse_quotedword(term);
+
case 'x':
return parse_string('`', term);
@@ -2693,7 +2717,7 @@ retry:
return parse_regx(term);
default:
- yyerror("unknown type of string `%c'", c);
+ yyerror("unknown type of %string");
return 0;
}
}
@@ -3219,6 +3243,12 @@ gettable(id)
else if (id == kFALSE) {
return NEW_FALSE();
}
+ else if (id == k__FILE__) {
+ return NEW_STR(str_new2(sourcefile));
+ }
+ else if (id == k__LINE__) {
+ return NEW_LIT(INT2FIX(sourceline));
+ }
else if (is_local_id(id)) {
if (local_id(id)) return NEW_LVAR(id);
if (dyna_var_defined(id)) return NEW_DVAR(id);
@@ -3257,6 +3287,12 @@ assignable(id, val)
else if (id == kFALSE) {
yyerror("Can't assign to false");
}
+ else if (id == k__FILE__) {
+ yyerror("Can't assign to __FILE__");
+ }
+ else if (id == k__LINE__) {
+ yyerror("Can't assign to __LINE__");
+ }
else if (is_local_id(id)) {
if (local_id(id) || !dyna_in_block()) {
lhs = NEW_LASGN(id, val);
diff --git a/process.c b/process.c
index 9d50fea8bf..314d3ea24a 100644
--- a/process.c
+++ b/process.c
@@ -6,7 +6,7 @@
$Date$
created at: Tue Aug 10 14:30:50 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -361,7 +361,7 @@ rb_proc_exec(str)
if (state != -1)
exit(state);
#else
-#if defined(__human68k__)
+#if defined(__human68k__) || defined(__CYGWIN32__)
char *shell = dln_find_exe("sh", 0);
int state = -1;
before_exec();
@@ -579,6 +579,7 @@ rb_syswait(pid)
{
RETSIGTYPE (*hfunc)(), (*qfunc)(), (*ifunc)();
int status;
+ int i;
#ifdef SIGHUP
hfunc = signal(SIGHUP, SIG_IGN);
@@ -588,7 +589,9 @@ rb_syswait(pid)
#endif
ifunc = signal(SIGINT, SIG_IGN);
- if (rb_waitpid(pid, 0, &status) < 0) rb_sys_fail("wait");
+ do {
+ i = rb_waitpid(pid, 0, &status);
+ } while (i == -1 && errno == EINTR);
#ifdef SIGHUP
signal(SIGHUP, hfunc);
diff --git a/random.c b/random.c
index d0a5756b69..8674dd0bad 100644
--- a/random.c
+++ b/random.c
@@ -6,7 +6,7 @@
$Date$
created at: Fri Dec 24 16:39:21 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
diff --git a/range.c b/range.c
index 9596e07f93..121acfe5a6 100644
--- a/range.c
+++ b/range.c
@@ -6,7 +6,7 @@
$Date$
created at: Thu Aug 19 17:46:47 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
diff --git a/re.c b/re.c
index cb0ade9aaf..245bcbea48 100644
--- a/re.c
+++ b/re.c
@@ -6,7 +6,7 @@
$Date$
created at: Mon Aug 9 18:24:49 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -69,7 +69,7 @@ static char casetable[] = {
>>> "You lose. You will need a translation table for your character set." <<<
#endif
-#define min(a,b) (((a)>(b))?(b):(a))
+#define MIN(a,b) (((a)>(b))?(b):(a))
int
str_cicmp(str1, str2)
@@ -78,7 +78,7 @@ str_cicmp(str1, str2)
int len, i;
char *p1, *p2;
- len = min(RSTRING(str1)->len, RSTRING(str2)->len);
+ len = MIN(RSTRING(str1)->len, RSTRING(str2)->len);
p1 = RSTRING(str1)->ptr; p2 = RSTRING(str2)->ptr;
for (i = 0; i < len; i++, p1++, p2++) {
@@ -570,7 +570,7 @@ match_to_a(match)
int i;
for (i=0; i<regs->num_regs; i++) {
- if (regs->beg[0] == -1) ary_push(ary, Qnil);
+ if (regs->beg[i] == -1) ary_push(ary, Qnil);
else ary_push(ary, str_new(ptr+regs->beg[i],
regs->end[i]-regs->beg[i]));
}
@@ -929,7 +929,7 @@ reg_regsub(str, src, regs)
if (!val) val = str_new(p, e-p);
else str_cat(val, p, e-p);
}
- if (!val) return (VALUE)str;
+ if (!val) return str;
return val;
}
diff --git a/re.h b/re.h
index 8769d6ef39..dd93168ab1 100644
--- a/re.h
+++ b/re.h
@@ -7,7 +7,7 @@
$Date$
created at: Thu Sep 30 14:18:32 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
diff --git a/regex.c b/regex.c
new file mode 100644
index 0000000000..152eebbf6d
--- /dev/null
+++ b/regex.c
@@ -0,0 +1,3389 @@
+/* Extended regular expression matching and search library.
+ Copyright (C) 1985, 1989-90 Free Software Foundation, Inc.
+
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 1, or (at your option)
+ any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
+/* Multi-byte extension added May, 1993 by t^2 (Takahiro Tanimoto)
+ Last change: May 21, 1993 by t^2 */
+
+
+/* To test, compile with -Dtest. This Dtestable feature turns this into
+ a self-contained program which reads a pattern, describes how it
+ compiles, then reads a string and searches for it.
+
+ On the other hand, if you compile with both -Dtest and -Dcanned you
+ can run some tests we've already thought of. */
+
+/* We write fatal error messages on standard error. */
+#include <stdio.h>
+
+/* isalpha(3) etc. are used for the character classes. */
+#include <ctype.h>
+#include <sys/types.h>
+
+#include "config.h"
+#include "defines.h"
+
+#ifdef __STDC__
+#define P(s) s
+#define MALLOC_ARG_T size_t
+#else
+#define P(s) ()
+#define MALLOC_ARG_T unsigned
+#define volatile
+#define const
+#endif
+
+/* #define NO_ALLOCA /* try it out for now */
+#ifndef NO_ALLOCA
+/* Make alloca work the best possible way. */
+#ifdef __GNUC__
+#ifndef atarist
+#ifndef alloca
+#define alloca __builtin_alloca
+#endif
+#endif /* atarist */
+#else
+#if defined(HAVE_ALLOCA_H) && !defined(__GNUC__)
+#include <alloca.h>
+#else
+char *alloca();
+#endif
+#endif /* __GNUC__ */
+
+#ifdef _AIX
+#pragma alloca
+#endif
+
+#ifdef HAVE_STRING_H
+# include <string.h>
+#else
+# include <strings.h>
+#endif
+
+#define RE_ALLOCATE alloca
+#define FREE_VARIABLES() alloca(0)
+
+#define FREE_AND_RETURN_VOID(stackb) return
+#define FREE_AND_RETURN(stackb,val) return(val)
+#define DOUBLE_STACK(stackx,stackb,len,type) \
+ (stackx = (type*) alloca(2 * len * sizeof(type)), \
+ /* Only copy what is in use. */ \
+ (type*) memcpy(stackx, stackb, len * sizeof (type)))
+#else /* NO_ALLOCA defined */
+
+#define RE_ALLOCATE malloc
+
+#define FREE_VAR(var) if (var) free(var); var = NULL
+#define FREE_VARIABLES() \
+ do { \
+ FREE_VAR(regstart); \
+ FREE_VAR(regend); \
+ FREE_VAR(best_regstart); \
+ FREE_VAR(best_regend); \
+ FREE_VAR(reg_info); \
+ } while (0)
+
+#define FREE_AND_RETURN_VOID(stackb) free(stackb);return
+#define FREE_AND_RETURN(stackb,val) free(stackb);return(val)
+#define DOUBLE_STACK(stackx,stackb,len,type) \
+ (type*)xrealloc(stackb, 2 * len * sizeof(type))
+#endif /* NO_ALLOCA */
+
+#define RE_TALLOC(n,t) ((t*)RE_ALLOCATE((n)*sizeof(t)))
+#define TMALLOC(n,t) ((t*)xmalloc((n)*sizeof(t)))
+#define TREALLOC(s,n,t) (s=((t*)xrealloc(s,(n)*sizeof(t))))
+
+#define EXPAND_FAIL_STACK(stackx,stackb,len) \
+ do {\
+ /* Roughly double the size of the stack. */ \
+ stackx = DOUBLE_STACK(stackx,stackb,len,unsigned char*); \
+ /* Rearrange the pointers. */ \
+ stackp = stackx + (stackp - stackb); \
+ stackb = stackx; \
+ stacke = stackb + 2 * len; \
+ } while (0); \
+
+/* Get the interface, including the syntax bits. */
+#include "regex.h"
+
+/* Subroutines for re_compile_pattern. */
+static void store_jump P((char *, int, char *));
+static void insert_jump P((int, char *, char *, char *));
+static void store_jump_n P((char *, int, char *, unsigned));
+static void insert_jump_n P((int, char *, char *, char *, unsigned));
+static void insert_op P((int, char *, char *));
+static void insert_op_2 P((int, char *, char *, int, int));
+static int memcmp_translate P((unsigned char *, unsigned char *,
+ int, unsigned char *));
+
+/* Define the syntax stuff, so we can do the \<, \>, etc. */
+
+/* This must be nonzero for the wordchar and notwordchar pattern
+ commands in re_match_2. */
+#ifndef Sword
+#define Sword 1
+#endif
+
+#define SYNTAX(c) re_syntax_table[c]
+
+static char re_syntax_table[256];
+static void init_syntax_once P((void));
+
+#undef P
+
+#include "util.h"
+
+static void
+init_syntax_once()
+{
+ register int c;
+ static int done = 0;
+
+ if (done)
+ return;
+
+ memset(re_syntax_table, 0, sizeof re_syntax_table);
+
+ for (c = 'a'; c <= 'z'; c++)
+ re_syntax_table[c] = Sword;
+
+ for (c = 'A'; c <= 'Z'; c++)
+ re_syntax_table[c] = Sword;
+
+ for (c = '0'; c <= '9'; c++)
+ re_syntax_table[c] = Sword;
+
+ re_syntax_table['_'] = Sword;
+
+ /* Add specific syntax for ISO Latin-1. */
+ for (c = 0300; c <= 0377; c++)
+ re_syntax_table[c] = Sword;
+ re_syntax_table[0327] = 0;
+ re_syntax_table[0367] = 0;
+
+ done = 1;
+}
+
+/* Sequents are missing isgraph. */
+#ifndef isgraph
+#define isgraph(c) (isprint((c)) && !isspace((c)))
+#endif
+
+/* These are the command codes that appear in compiled regular
+ expressions, one per byte. Some command codes are followed by
+ argument bytes. A command code can specify any interpretation
+ whatsoever for its arguments. Zero-bytes may appear in the compiled
+ regular expression.
+
+ The value of `exactn' is needed in search.c (search_buffer) in emacs.
+ So regex.h defines a symbol `RE_EXACTN_VALUE' to be 1; the value of
+ `exactn' we use here must also be 1. */
+
+enum regexpcode
+ {
+ unused=0,
+ exactn=1, /* Followed by one byte giving n, then by n literal bytes. */
+ begline, /* Fail unless at beginning of line. */
+ endline, /* Fail unless at end of line. */
+ begbuf, /* Succeeds if at beginning of buffer (if emacs) or at beginning
+ of string to be matched (if not). */
+ endbuf, /* Analogously, for end of buffer/string. */
+ jump, /* Followed by two bytes giving relative address to jump to. */
+ on_failure_jump, /* Followed by two bytes giving relative address of
+ place to resume at in case of failure. */
+ finalize_jump, /* Throw away latest failure point and then jump to
+ address. */
+ maybe_finalize_jump, /* Like jump but finalize if safe to do so.
+ This is used to jump back to the beginning
+ of a repeat. If the command that follows
+ this jump is clearly incompatible with the
+ one at the beginning of the repeat, such that
+ we can be sure that there is no use backtracking
+ out of repetitions already completed,
+ then we finalize. */
+ dummy_failure_jump, /* Jump, and push a dummy failure point. This
+ failure point will be thrown away if an attempt
+ is made to use it for a failure. A + construct
+ makes this before the first repeat. Also
+ use it as an intermediary kind of jump when
+ compiling an or construct. */
+ succeed_n, /* Used like on_failure_jump except has to succeed n times;
+ then gets turned into an on_failure_jump. The relative
+ address following it is useless until then. The
+ address is followed by two bytes containing n. */
+ jump_n, /* Similar to jump, but jump n times only; also the relative
+ address following is in turn followed by yet two more bytes
+ containing n. */
+ try_next, /* Jump to next pattern for the first time,
+ leaving this pattern on the failure stack. */
+ finalize_push, /* Finalize stack and push the beginning of the pattern
+ on the stack to retry (used for non-greedy match) */
+ finalize_push_n, /* Similar to finalize_push, buf finalize n time only */
+ set_number_at, /* Set the following relative location to the
+ subsequent number. */
+ anychar, /* Matches any (more or less) one character. */
+ charset, /* Matches any one char belonging to specified set.
+ First following byte is number of bitmap bytes.
+ Then come bytes for a bitmap saying which chars are in.
+ Bits in each byte are ordered low-bit-first.
+ A character is in the set if its bit is 1.
+ A character too large to have a bit in the map
+ is automatically not in the set. */
+ charset_not, /* Same parameters as charset, but match any character
+ that is not one of those specified. */
+ start_memory, /* Start remembering the text that is matched, for
+ storing in a memory register. Followed by one
+ byte containing the register number. Register numbers
+ must be in the range 0 through RE_NREGS. */
+ stop_memory, /* Stop remembering the text that is matched
+ and store it in a memory register. Followed by
+ one byte containing the register number. Register
+ numbers must be in the range 0 through RE_NREGS. */
+ start_nowidth, /* Save string point to the stack. */
+ stop_nowidth, /* Restore string place at the point start_nowidth. */
+ pop_and_fail, /* Fail after popping nowidth entry from stack. */
+ duplicate, /* Match a duplicate of something remembered.
+ Followed by one byte containing the index of the memory
+ register. */
+ wordchar, /* Matches any word-constituent character. */
+ notwordchar, /* Matches any char that is not a word-constituent. */
+ wordbeg, /* Succeeds if at word beginning. */
+ wordend, /* Succeeds if at word end. */
+ wordbound, /* Succeeds if at a word boundary. */
+ notwordbound,/* Succeeds if not at a word boundary. */
+ };
+
+
+/* Number of failure points to allocate space for initially,
+ when matching. If this number is exceeded, more space is allocated,
+ so it is not a hard limit. */
+
+#ifndef NFAILURES
+#define NFAILURES 80
+#endif
+
+#if defined(CHAR_UNSIGNED) || defined(__CHAR_UNSIGNED__)
+#define SIGN_EXTEND_CHAR(c) ((c)>(char)127?(c)-256:(c)) /* for IBM RT */
+#endif
+#ifndef SIGN_EXTEND_CHAR
+#define SIGN_EXTEND_CHAR(x) (x)
+#endif
+
+
+/* Store NUMBER in two contiguous bytes starting at DESTINATION. */
+#define STORE_NUMBER(destination, number) \
+ { (destination)[0] = (number) & 0377; \
+ (destination)[1] = (number) >> 8; }
+
+/* Same as STORE_NUMBER, except increment the destination pointer to
+ the byte after where the number is stored. Watch out that values for
+ DESTINATION such as p + 1 won't work, whereas p will. */
+#define STORE_NUMBER_AND_INCR(destination, number) \
+ { STORE_NUMBER(destination, number); \
+ (destination) += 2; }
+
+
+/* Put into DESTINATION a number stored in two contingous bytes starting
+ at SOURCE. */
+#define EXTRACT_NUMBER(destination, source) \
+ { (destination) = *(source) & 0377; \
+ (destination) += SIGN_EXTEND_CHAR (*(char *)((source) + 1)) << 8; }
+
+/* Same as EXTRACT_NUMBER, except increment the pointer for source to
+ point to second byte of SOURCE. Note that SOURCE has to be a value
+ such as p, not, e.g., p + 1. */
+#define EXTRACT_NUMBER_AND_INCR(destination, source) \
+ { EXTRACT_NUMBER(destination, source); \
+ (source) += 2; }
+
+
+/* Specify the precise syntax of regexps for compilation. This provides
+ for compatibility for various utilities which historically have
+ different, incompatible syntaxes.
+
+ The argument SYNTAX is a bit-mask comprised of the various bits
+ defined in regex.h. */
+
+long
+re_set_syntax(syntax)
+ long syntax;
+{
+ long ret;
+
+ ret = re_syntax_options;
+ re_syntax_options = syntax;
+ return ret;
+}
+
+/* Set by re_set_syntax to the current regexp syntax to recognize. */
+long re_syntax_options = DEFAULT_MBCTYPE;
+
+
+/* Macros for re_compile_pattern, which is found below these definitions. */
+
+/* Fetch the next character in the uncompiled pattern---translating it
+ if necessary. Also cast from a signed character in the constant
+ string passed to us by the user to an unsigned char that we can use
+ as an array index (in, e.g., `translate'). */
+#define PATFETCH(c) \
+ do {if (p == pend) goto end_of_pattern; \
+ c = (unsigned char) *p++; \
+ if (translate) c = (unsigned char)translate[c]; \
+ } while (0)
+
+/* Fetch the next character in the uncompiled pattern, with no
+ translation. */
+#define PATFETCH_RAW(c) \
+ do {if (p == pend) goto end_of_pattern; \
+ c = (unsigned char) *p++; \
+ } while (0)
+
+/* Go backwards one character in the pattern. */
+#define PATUNFETCH p--
+
+
+/* If the buffer isn't allocated when it comes in, use this. */
+#define INIT_BUF_SIZE 28
+
+/* Make sure we have at least N more bytes of space in buffer. */
+#define GET_BUFFER_SPACE(n) \
+ { \
+ while (b - bufp->buffer + (n) >= bufp->allocated) \
+ EXTEND_BUFFER; \
+ }
+
+/* Make sure we have one more byte of buffer space and then add CH to it. */
+#define BUFPUSH(ch) \
+ { \
+ GET_BUFFER_SPACE(1); \
+ *b++ = (char)(ch); \
+ }
+
+/* Extend the buffer by twice its current size via reallociation and
+ reset the pointers that pointed into the old allocation to point to
+ the correct places in the new allocation. If extending the buffer
+ results in it being larger than 1 << 16, then flag memory exhausted. */
+#define EXTEND_BUFFER \
+ { char *old_buffer = bufp->buffer; \
+ if (bufp->allocated == (1L<<16)) goto too_big; \
+ bufp->allocated *= 2; \
+ if (bufp->allocated > (1L<<16)) bufp->allocated = (1L<<16); \
+ bufp->buffer = (char *) xrealloc (bufp->buffer, bufp->allocated); \
+ if (bufp->buffer == 0) \
+ goto memory_exhausted; \
+ b = (b - old_buffer) + bufp->buffer; \
+ if (fixup_jump) \
+ fixup_jump = (fixup_jump - old_buffer) + bufp->buffer; \
+ if (laststart) \
+ laststart = (laststart - old_buffer) + bufp->buffer; \
+ begalt = (begalt - old_buffer) + bufp->buffer; \
+ if (pending_exact) \
+ pending_exact = (pending_exact - old_buffer) + bufp->buffer; \
+ }
+
+
+/* Set the bit for character C in a character set list. */
+#define SET_LIST_BIT(c) \
+ (b[(unsigned char)(c) / BYTEWIDTH] \
+ |= 1 << ((unsigned char)(c) % BYTEWIDTH))
+
+/* Get the next unsigned number in the uncompiled pattern. */
+#define GET_UNSIGNED_NUMBER(num) \
+ { if (p != pend) \
+ { \
+ PATFETCH(c); \
+ while (isdigit(c)) \
+ { \
+ if (num < 0) \
+ num = 0; \
+ num = num * 10 + c - '0'; \
+ if (p == pend) \
+ break; \
+ PATFETCH(c); \
+ } \
+ } \
+ }
+
+
+#define STORE_MBC(p, c) \
+ ((p)[0] = (unsigned char)(c >> 8), (p)[1] = (unsigned char)(c))
+#define STORE_MBC_AND_INCR(p, c) \
+ (*(p)++ = (unsigned char)(c >> 8), *(p)++ = (unsigned char)(c))
+
+#define EXTRACT_MBC(p) \
+ ((unsigned short)((unsigned char)(p)[0] << 8 | (unsigned char)(p)[1]))
+#define EXTRACT_MBC_AND_INCR(p) \
+ ((unsigned short)((p) += 2, (unsigned char)(p)[-2] << 8 | (unsigned char)(p)[-1]))
+
+#define EXTRACT_UNSIGNED(p) \
+ ((unsigned char)(p)[0] | (unsigned char)(p)[1] << 8)
+#define EXTRACT_UNSIGNED_AND_INCR(p) \
+ ((p) += 2, (unsigned char)(p)[-2] | (unsigned char)(p)[-1] << 8)
+
+/* Handle (mb)?charset(_not)?.
+
+ Structure of mbcharset(_not)? in compiled pattern.
+
+ struct {
+ unsinged char id; mbcharset(_not)?
+ unsigned char sbc_size;
+ unsigned char sbc_map[sbc_size]; same as charset(_not)? up to here.
+ unsigned short mbc_size; number of intervals.
+ struct {
+ unsigned short beg; beginning of interval.
+ unsigned short end; end of interval.
+ } intervals[mbc_size];
+ }; */
+
+static void
+set_list_bits(c1, c2, b)
+ unsigned short c1, c2;
+ unsigned char *b;
+{
+ unsigned char sbc_size = b[-1];
+ unsigned short mbc_size = EXTRACT_UNSIGNED(&b[sbc_size]);
+ unsigned short beg, end, upb;
+
+ if (c1 > c2)
+ return;
+ if ((int)c1 < 1 << BYTEWIDTH) {
+ upb = c2;
+ if (1 << BYTEWIDTH <= (int)upb)
+ upb = (1 << BYTEWIDTH) - 1; /* The last single-byte char */
+ if (sbc_size <= (unsigned short)(upb / BYTEWIDTH)) {
+ /* Allocate maximum size so it never happens again. */
+ /* NOTE: memcpy() would not work here. */
+ memmove(&b[(1 << BYTEWIDTH) / BYTEWIDTH], &b[sbc_size], 2 + mbc_size*4);
+ memset(&b[sbc_size], 0, (1 << BYTEWIDTH) / BYTEWIDTH - sbc_size);
+ b[-1] = sbc_size = (1 << BYTEWIDTH) / BYTEWIDTH;
+ }
+ for (; c1 <= upb; c1++)
+ if (!ismbchar(c1))
+ SET_LIST_BIT(c1);
+ if ((int)c2 < 1 << BYTEWIDTH)
+ return;
+ c1 = 0x8000; /* The first wide char */
+ }
+ b = &b[sbc_size + 2];
+
+ for (beg = 0, upb = mbc_size; beg < upb; ) {
+ unsigned short mid = (unsigned short)(beg + upb) >> 1;
+
+ if ((int)c1 - 1 > (int)EXTRACT_MBC(&b[mid*4 + 2]))
+ beg = mid + 1;
+ else
+ upb = mid;
+ }
+
+ for (end = beg, upb = mbc_size; end < upb; ) {
+ unsigned short mid = (unsigned short)(end + upb) >> 1;
+
+ if ((int)c2 >= (int)EXTRACT_MBC(&b[mid*4]) - 1)
+ end = mid + 1;
+ else
+ upb = mid;
+ }
+
+ if (beg != end) {
+ if (c1 > EXTRACT_MBC(&b[beg*4]))
+ c1 = EXTRACT_MBC(&b[beg*4]);
+ if (c2 < EXTRACT_MBC(&b[(end - 1)*4]))
+ c2 = EXTRACT_MBC(&b[(end - 1)*4]);
+ }
+ if (end < mbc_size && end != beg + 1)
+ /* NOTE: memcpy() would not work here. */
+ memmove(&b[(beg + 1)*4], &b[end*4], (mbc_size - end)*4);
+ STORE_MBC(&b[beg*4 + 0], c1);
+ STORE_MBC(&b[beg*4 + 2], c2);
+ mbc_size += beg - end + 1;
+ STORE_NUMBER(&b[-2], mbc_size);
+}
+
+static int
+is_in_list(c, b)
+ unsigned short c;
+ const unsigned char *b;
+{
+ unsigned short size;
+ unsigned short i, j;
+ int result = 0;
+
+ size = *b++;
+ if ((int)c < 1<<BYTEWIDTH) {
+ if ((int)c / BYTEWIDTH < (int)size && b[c / BYTEWIDTH] & 1 << c % BYTEWIDTH) {
+ return 1;
+ }
+ }
+ b += size + 2;
+ size = EXTRACT_UNSIGNED(&b[-2]);
+ if (size == 0) return 0;
+
+ if (b[(size-1)*4] == 0xff) {
+ i = c;
+ if ((int)c >= 1<<BYTEWIDTH) {
+ i = i>>BYTEWIDTH;
+ }
+ while (size>0 && b[size*4-2] == 0xff) {
+ size--;
+ if (b[size*4+1] <= i && i <= b[size*4+3]) {
+ result = 2;
+ break;
+ }
+ }
+ }
+ for (i = 0, j = size; i < j; ) {
+ unsigned short k = (unsigned short)(i + j) >> 1;
+
+ if (c > EXTRACT_MBC(&b[k*4+2]))
+ i = k + 1;
+ else
+ j = k;
+ }
+ if (i < size && EXTRACT_MBC(&b[i*4]) <= c
+ && ((unsigned char)c != '\n' && (unsigned char)c != '\0'))
+ return 1;
+ return result;
+}
+
+static void
+print_partial_compiled_pattern(start, end)
+ unsigned char *start;
+ unsigned char *end;
+{
+ int mcnt, mcnt2;
+ unsigned char *p = start;
+ unsigned char *pend = end;
+
+ if (start == NULL)
+ {
+ printf ("(null)\n");
+ return;
+ }
+
+ /* Loop over pattern commands. */
+ while (p < pend)
+ {
+ switch ((enum regexpcode) *p++)
+ {
+ case unused:
+ printf ("/unused");
+ break;
+
+ case exactn:
+ mcnt = *p++;
+ printf ("/exactn/%d", mcnt);
+ do
+ {
+ putchar('/');
+ printf("%c", *p++);
+ }
+ while (--mcnt);
+ break;
+
+ case start_memory:
+ mcnt = *p++;
+ printf ("/start_memory/%d", mcnt);
+ break;
+
+ case stop_memory:
+ mcnt = *p++;
+ printf ("/stop_memory/%d", mcnt);
+ break;
+
+ case start_nowidth:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ printf ("/start_nowidth//%d", mcnt);
+ break;
+
+ case stop_nowidth:
+ printf ("/stop_nowidth//");
+ p += 2;
+ break;
+
+ case pop_and_fail:
+ printf ("/pop_and_fail");
+ break;
+
+ case duplicate:
+ printf ("/duplicate/%d", *p++);
+ break;
+
+ case anychar:
+ printf ("/anychar");
+ break;
+
+ case charset:
+ case charset_not:
+ {
+ register int c;
+
+ printf ("/charset%s",
+ (enum regexpcode) *(p - 1) == charset_not ? "_not" : "");
+
+ mcnt = *p;
+ printf("/%d", mcnt);
+ for (c = 0; c < mcnt; c++)
+ {
+ unsigned bit;
+ unsigned char map_byte = p[1 + c];
+
+ putchar ('/');
+
+ for (bit = 0; bit < BYTEWIDTH; bit++)
+ if (map_byte & (1 << bit))
+ printf("%c", c * BYTEWIDTH + bit);
+ }
+ p += mcnt + 1;
+ mcnt = EXTRACT_UNSIGNED(p);
+ p += 2;
+ while (mcnt--) {
+ int beg = *p++;
+ int end = *p++;
+ printf("/%c%c-%c%c", beg>>BYTEWIDTH, beg&0xff, end>>BYTEWIDTH, end&0xff);
+ }
+ break;
+ }
+
+ case begline:
+ printf ("/begline");
+ break;
+
+ case endline:
+ printf ("/endline");
+ break;
+
+ case on_failure_jump:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ printf ("/on_failure_jump//%d", mcnt);
+ break;
+
+ case dummy_failure_jump:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ printf ("/dummy_failure_jump//%d", mcnt);
+ break;
+
+ case finalize_jump:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ printf ("/finalize_jump//%d", mcnt);
+ break;
+
+ case maybe_finalize_jump:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ printf ("/maybe_finalize_jump//%d", mcnt);
+ break;
+
+ case jump:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ printf ("/jump//%d", mcnt);
+ break;
+
+ case succeed_n:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ EXTRACT_NUMBER_AND_INCR (mcnt2, p);
+ printf ("/succeed_n//%d//%d", mcnt, mcnt2);
+ break;
+
+ case jump_n:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ EXTRACT_NUMBER_AND_INCR (mcnt2, p);
+ printf ("/jump_n//%d//%d", mcnt, mcnt2);
+ break;
+
+ case set_number_at:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ EXTRACT_NUMBER_AND_INCR (mcnt2, p);
+ printf ("/set_number_at//%d//%d", mcnt, mcnt2);
+ break;
+
+ case try_next:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ printf ("/try_next//%d", mcnt);
+ break;
+
+ case finalize_push:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ printf ("/finalize_push//%d", mcnt);
+ break;
+
+ case finalize_push_n:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ EXTRACT_NUMBER_AND_INCR (mcnt2, p);
+ printf ("/finalize_push_n//%d//%d", mcnt, mcnt2);
+ break;
+
+ case wordbound:
+ printf ("/wordbound");
+ break;
+
+ case notwordbound:
+ printf ("/notwordbound");
+ break;
+
+ case wordbeg:
+ printf ("/wordbeg");
+ break;
+
+ case wordend:
+ printf ("/wordend");
+
+ case wordchar:
+ printf ("/wordchar");
+ break;
+
+ case notwordchar:
+ printf ("/notwordchar");
+ break;
+
+ case begbuf:
+ printf ("/begbuf");
+ break;
+
+ case endbuf:
+ printf ("/endbuf");
+ break;
+
+ default:
+ printf ("?%d", *(p-1));
+ }
+ }
+ printf ("/\n");
+}
+
+
+static void
+print_compiled_pattern(bufp)
+ struct re_pattern_buffer *bufp;
+{
+ unsigned char *buffer = bufp->buffer;
+
+ print_partial_compiled_pattern (buffer, buffer + bufp->used);
+}
+
+static char*
+calculate_must_string(start, end)
+ unsigned char *start;
+ unsigned char *end;
+{
+ int mcnt, mcnt2;
+ int max = 0;
+ unsigned char *p = start;
+ unsigned char *pend = end;
+ unsigned char *must = 0;
+
+ if (start == NULL) return 0;
+
+ /* Loop over pattern commands. */
+ while (p < pend)
+ {
+ switch ((enum regexpcode) *p++)
+ {
+ case unused:
+ break;
+
+ case exactn:
+ mcnt = *p;
+ if (mcnt > max) {
+ must = p;
+ }
+ p += mcnt+1;
+ break;
+
+ case start_memory:
+ case stop_memory:
+ case duplicate:
+ p++;
+ break;
+
+ case start_nowidth:
+ case stop_nowidth:
+ case pop_and_fail:
+ case anychar:
+ case begline:
+ case endline:
+ case wordbound:
+ case notwordbound:
+ case wordbeg:
+ case wordend:
+ case wordchar:
+ case notwordchar:
+ case begbuf:
+ case endbuf:
+ break;
+
+ case charset:
+ case charset_not:
+ mcnt = *p++;
+ p += mcnt;
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ while (mcnt--) {
+ EXTRACT_NUMBER_AND_INCR (mcnt2, p);
+ EXTRACT_NUMBER_AND_INCR (mcnt2, p);
+ }
+ break;
+
+ case on_failure_jump:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ if (mcnt > 0) p += mcnt;
+ if ((enum regexpcode)p[-3] == jump) {
+ p -= 3;
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ if (mcnt > 0) p += mcnt;
+ }
+ break;
+
+ case dummy_failure_jump:
+ case succeed_n:
+ case try_next:
+ case jump:
+ EXTRACT_NUMBER_AND_INCR (mcnt, p);
+ if (mcnt > 0) p += mcnt;
+ break;
+
+ case finalize_jump:
+ case maybe_finalize_jump:
+ case finalize_push:
+ p += 2;
+ break;
+
+ case jump_n:
+ case set_number_at:
+ case finalize_push_n:
+ p += 4;
+ break;
+
+ default:
+ break;
+ }
+ }
+ return must;
+}
+
+
+/* re_compile_pattern takes a regular-expression string
+ and converts it into a buffer full of byte commands for matching.
+
+ PATTERN is the address of the pattern string
+ SIZE is the length of it.
+ BUFP is a struct re_pattern_buffer * which points to the info
+ on where to store the byte commands.
+ This structure contains a char * which points to the
+ actual space, which should have been obtained with malloc.
+ re_compile_pattern may use realloc to grow the buffer space.
+
+ The number of bytes of commands can be found out by looking in
+ the `struct re_pattern_buffer' that bufp pointed to, after
+ re_compile_pattern returns. */
+
+char *
+re_compile_pattern(pattern, size, bufp)
+ char *pattern;
+ size_t size;
+ struct re_pattern_buffer *bufp;
+{
+ register char *b = bufp->buffer;
+ register char *p = pattern;
+ char *pend = pattern + size;
+ register unsigned c, c1;
+ char *p0;
+ int numlen;
+
+ /* Address of the count-byte of the most recently inserted `exactn'
+ command. This makes it possible to tell whether a new exact-match
+ character can be added to that command or requires a new `exactn'
+ command. */
+
+ char *pending_exact = 0;
+
+ /* Address of the place where a forward-jump should go to the end of
+ the containing expression. Each alternative of an `or', except the
+ last, ends with a forward-jump of this sort. */
+
+ char *fixup_jump = 0;
+
+ /* Address of start of the most recently finished expression.
+ This tells postfix * where to find the start of its operand. */
+
+ char *laststart = 0;
+
+ /* In processing a repeat, 1 means zero matches is allowed. */
+
+ char zero_times_ok;
+
+ /* In processing a repeat, 1 means many matches is allowed. */
+
+ char many_times_ok;
+
+ /* In processing a repeat, 1 means non-greedy matches. */
+
+ char greedy;
+
+ /* Address of beginning of regexp, or inside of last \(. */
+
+ char *begalt = b;
+
+ /* In processing an interval, at least this many matches must be made. */
+ int lower_bound;
+
+ /* In processing an interval, at most this many matches can be made. */
+ int upper_bound;
+
+ /* Stack of information saved by \( and restored by \).
+ Five stack elements are pushed by each \(:
+ First, the value of b.
+ Second, the value of fixup_jump.
+ Third, the value of begalt.
+ Fourth, the value of regnum.
+ Fifth, the type of the paren. */
+
+ int *stackb = RE_TALLOC(40, int);
+ int *stackp = stackb;
+ int *stacke = stackb + 40;
+ int *stackt;
+
+ /* Counts \('s as they are encountered. Remembered for the matching \),
+ where it becomes the register number to put in the stop_memory
+ command. */
+
+ int regnum = 1;
+ int range = 0;
+
+ /* How to translate the characters in the pattern. */
+ char *translate = bufp->translate;
+
+ bufp->fastmap_accurate = 0;
+
+ /* Initialize the syntax table. */
+ init_syntax_once();
+
+ if (bufp->allocated == 0)
+ {
+ bufp->allocated = INIT_BUF_SIZE;
+ if (bufp->buffer)
+ /* EXTEND_BUFFER loses when bufp->allocated is 0. */
+ bufp->buffer = (char *) xrealloc (bufp->buffer, INIT_BUF_SIZE);
+ else
+ /* Caller did not allocate a buffer. Do it for them. */
+ bufp->buffer = (char *) xmalloc(INIT_BUF_SIZE);
+ if (!bufp->buffer) goto memory_exhausted;
+ begalt = b = bufp->buffer;
+ }
+
+ while (p != pend)
+ {
+ PATFETCH(c);
+
+ switch (c)
+ {
+ case '$':
+ {
+ char *p1 = p;
+ /* When testing what follows the $,
+ look past the \-constructs that don't consume anything. */
+ if (! (re_syntax_options & RE_CONTEXT_INDEP_OPS))
+ while (p1 != pend)
+ {
+ if (*p1 == '\\' && p1 + 1 != pend
+ && (p1[1] == 'b' || p1[1] == 'B'))
+ p1 += 2;
+ else
+ break;
+ }
+ if (re_syntax_options & RE_TIGHT_VBAR)
+ {
+ if (! (re_syntax_options & RE_CONTEXT_INDEP_OPS) && p1 != pend)
+ goto normal_char;
+ /* Make operand of last vbar end before this `$'. */
+ if (fixup_jump)
+ store_jump(fixup_jump, jump, b);
+ fixup_jump = 0;
+ BUFPUSH(endline);
+ break;
+ }
+ /* $ means succeed if at end of line, but only in special contexts.
+ If validly in the middle of a pattern, it is a normal character. */
+
+ if (p1 == pend || *p1 == '\n'
+ || (re_syntax_options & RE_CONTEXT_INDEP_OPS)
+ || (re_syntax_options & RE_NO_BK_PARENS
+ ? *p1 == ')'
+ : *p1 == '\\' && p1[1] == ')')
+ || (re_syntax_options & RE_NO_BK_VBAR
+ ? *p1 == '|'
+ : *p1 == '\\' && p1[1] == '|'))
+ {
+ BUFPUSH(endline);
+ break;
+ }
+ goto normal_char;
+ }
+ case '^':
+ /* ^ means succeed if at beg of line, but only if no preceding
+ pattern. */
+
+ if ((re_syntax_options & RE_CONTEXTUAL_INVALID_OPS) && laststart)
+ goto invalid_pattern;
+ if (laststart && p - 2 >= pattern && p[-2] != '\n'
+ && !(re_syntax_options & RE_CONTEXT_INDEP_OPS))
+ goto normal_char;
+ if (re_syntax_options & RE_TIGHT_VBAR)
+ {
+ if (p != pattern + 1
+ && ! (re_syntax_options & RE_CONTEXT_INDEP_OPS))
+ goto normal_char;
+ BUFPUSH(begline);
+ begalt = b;
+ }
+ else
+ {
+ BUFPUSH(begline);
+ }
+ break;
+
+ case '+':
+ case '?':
+ if (re_syntax_options & RE_LIMITED_OPS)
+ goto normal_char;
+ case '*':
+ /* If there is no previous pattern, char not special. */
+ if (!laststart) {
+ if (re_syntax_options & RE_CONTEXTUAL_INVALID_OPS)
+ goto invalid_pattern;
+ else if (! (re_syntax_options & RE_CONTEXT_INDEP_OPS))
+ goto normal_char;
+ }
+ /* If there is a sequence of repetition chars,
+ collapse it down to just one. */
+ zero_times_ok = c != '+';
+ many_times_ok = c != '?';
+ greedy = 1;
+ if (p != pend) {
+ PATFETCH(c);
+ switch (c) {
+ case '?':
+ greedy = 0;
+ break;
+ case '*':
+ case '+':
+ goto nested_meta;
+ default:
+ PATUNFETCH;
+ break;
+ }
+ }
+
+ repeat:
+ /* Star, etc. applied to an empty pattern is equivalent
+ to an empty pattern. */
+ if (!laststart)
+ break;
+
+ /* Now we know whether or not zero matches is allowed
+ and also whether or not two or more matches is allowed. */
+ if (many_times_ok) {
+ /* If more than one repetition is allowed, put in at the
+ end a backward relative jump from b to before the next
+ jump we're going to put in below (which jumps from
+ laststart to after this jump). */
+ GET_BUFFER_SPACE(3);
+ store_jump(b,greedy?maybe_finalize_jump:finalize_push,laststart-3);
+ b += 3; /* Because store_jump put stuff here. */
+ }
+
+ /* On failure, jump from laststart to next pattern, which will be the
+ end of the buffer after this jump is inserted. */
+ GET_BUFFER_SPACE(3);
+ insert_jump(on_failure_jump, laststart, b + 3, b);
+ b += 3;
+
+ if (zero_times_ok) {
+ if (greedy == 0) {
+ GET_BUFFER_SPACE(3);
+ insert_jump(try_next, laststart, b + 3, b);
+ b += 3;
+ }
+ }
+ else {
+ /* At least one repetition is required, so insert a
+ `dummy_failure_jump' before the initial
+ `on_failure_jump' instruction of the loop. This
+ effects a skip over that instruction the first time
+ we hit that loop. */
+ GET_BUFFER_SPACE(3);
+ insert_jump(dummy_failure_jump, laststart, laststart + 6, b);
+ b += 3;
+ }
+ break;
+
+ case '.':
+ laststart = b;
+ BUFPUSH(anychar);
+ break;
+
+ case '[':
+ if (p == pend)
+ goto invalid_pattern;
+ while (b - bufp->buffer
+ > bufp->allocated - 9 - (1 << BYTEWIDTH) / BYTEWIDTH)
+ EXTEND_BUFFER;
+
+ laststart = b;
+ if (*p == '^')
+ {
+ BUFPUSH(charset_not);
+ p++;
+ }
+ else
+ BUFPUSH(charset);
+ p0 = p;
+
+ BUFPUSH((1 << BYTEWIDTH) / BYTEWIDTH);
+ /* Clear the whole map */
+ memset(b, 0, (1 << BYTEWIDTH) / BYTEWIDTH + 2);
+
+ if ((re_syntax_options & RE_HAT_NOT_NEWLINE) && b[-2] == charset_not)
+ SET_LIST_BIT('\n');
+
+
+ /* Read in characters and ranges, setting map bits. */
+ for (;;)
+ {
+ int size;
+ unsigned last = (unsigned)-1;
+
+ if ((size = EXTRACT_UNSIGNED(&b[(1 << BYTEWIDTH) / BYTEWIDTH]))) {
+ /* Ensure the space is enough to hold another interval
+ of multi-byte chars in charset(_not)?. */
+ size = (1 << BYTEWIDTH) / BYTEWIDTH + 2 + size*4 + 4;
+ while (b + size + 1 > bufp->buffer + bufp->allocated)
+ EXTEND_BUFFER;
+ }
+ range_retry:
+ PATFETCH(c);
+
+ if (c == ']') {
+ if (p == p0 + 1) {
+ /* If this is an empty bracket expression. */
+ if ((re_syntax_options & RE_NO_EMPTY_BRACKETS)
+ && p == pend)
+ goto invalid_pattern;
+ }
+ else
+ /* Stop if this isn't merely a ] inside a bracket
+ expression, but rather the end of a bracket
+ expression. */
+ break;
+ }
+ if (ismbchar(c)) {
+ PATFETCH(c1);
+ c = c << BYTEWIDTH | c1;
+ }
+
+ /* \ escapes characters when inside [...]. */
+ if (c == '\\') {
+ PATFETCH(c);
+ switch (c) {
+ case 'w':
+ for (c = 0; c < (1 << BYTEWIDTH); c++)
+ if (SYNTAX(c) == Sword)
+ SET_LIST_BIT(c);
+ last = -1;
+ continue;
+
+ case 'W':
+ for (c = 0; c < (1 << BYTEWIDTH); c++)
+ if (SYNTAX(c) != Sword)
+ SET_LIST_BIT(c);
+ if (re_syntax_options & RE_MBCTYPE_MASK) {
+ set_list_bits(0x8000, 0xffff, (unsigned char*)b);
+ }
+ last = -1;
+ continue;
+
+ case 's':
+ for (c = 0; c < 256; c++)
+ if (isspace(c))
+ SET_LIST_BIT(c);
+ last = -1;
+ continue;
+
+ case 'S':
+ for (c = 0; c < 256; c++)
+ if (!isspace(c))
+ SET_LIST_BIT(c);
+ if (re_syntax_options & RE_MBCTYPE_MASK) {
+ set_list_bits(0x8000, 0xffff, (unsigned char*)b);
+ }
+ last = -1;
+ continue;
+
+ case 'd':
+ for (c = '0'; c <= '9'; c++)
+ SET_LIST_BIT(c);
+ last = -1;
+ continue;
+
+ case 'D':
+ for (c = 0; c < 256; c++)
+ if (!isdigit(c))
+ SET_LIST_BIT(c);
+ if (re_syntax_options & RE_MBCTYPE_MASK) {
+ set_list_bits(0x8000, 0xffff, (unsigned char*)b);
+ }
+ last = -1;
+ continue;
+
+ case 'x':
+ c = scan_hex(p, 2, &numlen);
+ if ((re_syntax_options & RE_MBCTYPE_MASK) && c > 0x7f)
+ c = 0xff00 | c;
+ p += numlen;
+ break;
+
+ case '0': case '1': case '2': case '3': case '4':
+ case '5': case '6': case '7': case '8': case '9':
+ PATUNFETCH;
+ c = scan_oct(p, 3, &numlen);
+ if ((re_syntax_options & RE_MBCTYPE_MASK) && ismbchar(c))
+ c = 0xff00 | c;
+ p += numlen;
+ break;
+
+ default:
+ if (ismbchar(c)) {
+ PATFETCH(c1);
+ c = c << 8 | c1;
+ }
+ break;
+ }
+ }
+
+ /* Get a range. */
+ if (range) {
+ if (last > c)
+ goto invalid_pattern;
+
+ if ((re_syntax_options & RE_NO_HYPHEN_RANGE_END)
+ && c == '-' && *p != ']')
+ goto invalid_pattern;
+
+ range = 0;
+ if (last < 1 << BYTEWIDTH && c < 1 << BYTEWIDTH) {
+ for (;last<=c;last++)
+ SET_LIST_BIT(last);
+ }
+ else {
+ set_list_bits(last, c, (unsigned char*)b);
+ }
+ }
+ else if (p[0] == '-' && p[1] != ']') {
+ last = c;
+ PATFETCH(c1);
+ range = 1;
+ goto range_retry;
+ }
+ else if (c < 1 << BYTEWIDTH)
+ SET_LIST_BIT(c);
+ else
+ set_list_bits(c, c, (unsigned char*)b);
+ }
+
+ /* Discard any character set/class bitmap bytes that are all
+ 0 at the end of the map. Decrement the map-length byte too. */
+ while ((int) b[-1] > 0 && b[b[-1] - 1] == 0)
+ b[-1]--;
+ if (b[-1] != (1 << BYTEWIDTH) / BYTEWIDTH)
+ memmove(&b[b[-1]], &b[(1 << BYTEWIDTH) / BYTEWIDTH],
+ 2 + EXTRACT_UNSIGNED (&b[(1 << BYTEWIDTH) / BYTEWIDTH])*4);
+ b += b[-1] + 2 + EXTRACT_UNSIGNED (&b[b[-1]])*4;
+ break;
+
+ case '(':
+ PATFETCH(c);
+ if (c == '?') {
+ PATFETCH(c);
+ switch (c) {
+ case '#':
+ case 'i':
+ case 'm':
+ case 's':
+ case 'x':
+ for (;;) {
+ PATFETCH(c);
+ if (c == ')') break;
+ }
+ c = '#';
+ break;
+
+ case ':':
+ case '=':
+ case '!':
+ break;
+
+ default:
+ FREE_AND_RETURN(stackb, "undefined (?...) sequence");
+ }
+ }
+ else {
+ PATUNFETCH;
+ c = '(';
+ }
+ if (c == '#') break;
+ if (stackp+6 >= stacke) {
+ int *stackx;
+ unsigned int len = stacke - stackb;
+
+ stackx = DOUBLE_STACK(stackx,stackb,len,int);
+ /* Rearrange the pointers. */
+ stackp = stackx + (stackp - stackb);
+ stackb = stackx;
+ stacke = stackb + 2 * len;
+ }
+
+ /* Laststart should point to the start_memory that we are about
+ to push (unless the pattern has RE_NREGS or more ('s). */
+ /* obsolete: now RE_NREGS is just a default register size. */
+ *stackp++ = b - bufp->buffer;
+ *stackp++ = fixup_jump ? fixup_jump - bufp->buffer + 1 : 0;
+ *stackp++ = begalt - bufp->buffer;
+ switch (c) {
+ case '(':
+ BUFPUSH(start_memory);
+ BUFPUSH(regnum);
+ *stackp++ = regnum++;
+ /* too many ()'s to fit in a byte. (max 254) */
+ if (regnum >= RE_REG_MAX) goto too_big;
+ break;
+
+ case '=':
+ case '!':
+ BUFPUSH(start_nowidth);
+ *stackp++ = b - bufp->buffer;
+ BUFPUSH(0); /* temporary value */
+ BUFPUSH(0);
+ if (c == '=') break;
+
+ BUFPUSH(on_failure_jump);
+ *stackp++ = b - bufp->buffer;
+ BUFPUSH(0); /* temporary value */
+ BUFPUSH(0);
+ break;
+
+ case ':':
+ default:
+ break;
+ }
+ *stackp++ = c;
+ fixup_jump = 0;
+ laststart = 0;
+ begalt = b;
+ break;
+
+ case ')':
+ if (stackp == stackb) goto unmatched_close;
+ switch (c = *--stackp) {
+ case '(':
+ if (fixup_jump)
+ store_jump(fixup_jump, jump, b);
+ BUFPUSH(stop_memory);
+ BUFPUSH(stackp[-1]);
+ stackp--;
+ break;
+
+ case '!':
+ BUFPUSH(pop_and_fail);
+ /* back patch */
+ STORE_NUMBER(bufp->buffer+stackp[-1], b - bufp->buffer - stackp[-1] - 2);
+ stackp--;
+ /* fall through */
+ case '=':
+ BUFPUSH(stop_nowidth);
+ /* tell stack-pos place to start_nowidth */
+ STORE_NUMBER(bufp->buffer+stackp[-1], b - bufp->buffer - stackp[-1] - 2);
+ BUFPUSH(0); /* space to hold stack pos */
+ BUFPUSH(0);
+ stackp--;
+ break;
+
+ case ':':
+ default:
+ break;
+ }
+ begalt = *--stackp + bufp->buffer;
+ stackp--;
+ fixup_jump = *stackp ? *stackp + bufp->buffer - 1 : 0;
+ laststart = *--stackp + bufp->buffer;
+ if (c == '!' || c == '=') laststart = b;
+ break;
+
+ case '|':
+ /* Insert before the previous alternative a jump which
+ jumps to this alternative if the former fails. */
+ GET_BUFFER_SPACE(6);
+ insert_jump(on_failure_jump, begalt, b + 6, b);
+ pending_exact = 0;
+ b += 3;
+ /* The alternative before the previous alternative has a
+ jump after it which gets executed if it gets matched.
+ Adjust that jump so it will jump to the previous
+ alternative's analogous jump (put in below, which in
+ turn will jump to the next (if any) alternative's such
+ jump, etc.). The last such jump jumps to the correct
+ final destination. */
+ if (fixup_jump)
+ store_jump(fixup_jump, jump, b);
+
+ /* Leave space for a jump after previous alternative---to be
+ filled in later. */
+ fixup_jump = b;
+ b += 3;
+
+ laststart = 0;
+ begalt = b;
+ break;
+
+ case '{':
+ /* If there is no previous pattern, this isn't an interval. */
+ if (!laststart)
+ {
+ if (re_syntax_options & RE_CONTEXTUAL_INVALID_OPS)
+ goto invalid_pattern;
+ else
+ goto normal_backsl;
+ }
+ /* It also isn't an interval if not preceded by an re
+ matching a single character or subexpression, or if
+ the current type of intervals can't handle back
+ references and the previous thing is a back reference. */
+ if (! (*laststart == anychar
+ || *laststart == charset
+ || *laststart == charset_not
+ || *laststart == wordchar
+ || *laststart == notwordchar
+ || *laststart == start_memory
+ || (*laststart == exactn
+ && (laststart[1] == 1
+ || laststart[1] == 2 && ismbchar(laststart[2])))
+ || (! (re_syntax_options & RE_NO_BK_REFS)
+ && *laststart == duplicate)))
+ {
+ /* Posix extended syntax is handled in previous
+ statement; this is for Posix basic syntax. */
+ if (re_syntax_options & RE_INTERVALS)
+ goto invalid_pattern;
+
+ goto normal_backsl;
+ }
+ lower_bound = -1; /* So can see if are set. */
+ upper_bound = -1;
+ GET_UNSIGNED_NUMBER(lower_bound);
+ if (c == ',') {
+ GET_UNSIGNED_NUMBER(upper_bound);
+ if (upper_bound < 0)
+ upper_bound = RE_DUP_MAX;
+ }
+ if (upper_bound < 0)
+ upper_bound = lower_bound;
+ if (c != '}' || lower_bound < 0 || upper_bound > RE_DUP_MAX
+ || lower_bound > upper_bound
+ || (p != pend && *p == '{')) {
+ goto invalid_pattern;
+ }
+ greedy = 1;
+ if (p != pend) {
+ PATFETCH(c);
+ if (c == '?') greedy = 0;
+ else PATUNFETCH;
+ }
+
+ /* If upper_bound is zero, don't want to succeed at all;
+ jump from laststart to b + 3, which will be the end of
+ the buffer after this jump is inserted. */
+
+ if (upper_bound == 0) {
+ GET_BUFFER_SPACE(3);
+ insert_jump(jump, laststart, b + 3, b);
+ b += 3;
+ break;
+ }
+
+ if (lower_bound == 0) {
+ zero_times_ok = 1;
+ if (upper_bound == RE_DUP_MAX) {
+ many_times_ok = 1;
+ goto repeat;
+ }
+ if (upper_bound == 1) {
+ many_times_ok = 0;
+ goto repeat;
+ }
+ }
+ if (lower_bound == 1 && upper_bound == RE_DUP_MAX) {
+ many_times_ok = 1;
+ zero_times_ok = 0;
+ goto repeat;
+ }
+
+ /* Star, etc. applied to an empty pattern is equivalent
+ to an empty pattern. */
+ if (!laststart)
+ break;
+
+ { /* If the upper bound is > 1, we need to insert
+ more at the end of the loop. */
+ unsigned slots_needed = upper_bound == 1 ? 5 : 10;
+
+ GET_BUFFER_SPACE(5);
+ /* Initialize lower bound of the `succeed_n', even
+ though it will be set during matching by its
+ attendant `set_number_at' (inserted next),
+ because `re_compile_fastmap' needs to know.
+ Jump to the `jump_n' we might insert below. */
+ insert_jump_n(succeed_n, laststart, b + slots_needed,
+ b, lower_bound);
+ b += 5; /* Just increment for the succeed_n here. */
+
+ /* Code to initialize the lower bound. Insert
+ before the `succeed_n'. The `5' is the last two
+ bytes of this `set_number_at', plus 3 bytes of
+ the following `succeed_n'. */
+ GET_BUFFER_SPACE(5);
+ insert_op_2(set_number_at, laststart, b, 5, lower_bound);
+ b += 5;
+
+ if (upper_bound > 1)
+ { /* More than one repetition is allowed, so
+ append a backward jump to the `succeed_n'
+ that starts this interval.
+
+ When we've reached this during matching,
+ we'll have matched the interval once, so
+ jump back only `upper_bound - 1' times. */
+ GET_BUFFER_SPACE(5);
+ store_jump_n(b, greedy?jump_n:finalize_push_n, laststart + 5, upper_bound - 1);
+ b += 5;
+
+ /* The location we want to set is the second
+ parameter of the `jump_n'; that is `b-2' as
+ an absolute address. `laststart' will be
+ the `set_number_at' we're about to insert;
+ `laststart+3' the number to set, the source
+ for the relative address. But we are
+ inserting into the middle of the pattern --
+ so everything is getting moved up by 5.
+ Conclusion: (b - 2) - (laststart + 3) + 5,
+ i.e., b - laststart.
+
+ We insert this at the beginning of the loop
+ so that if we fail during matching, we'll
+ reinitialize the bounds. */
+ GET_BUFFER_SPACE(5);
+ insert_op_2(set_number_at, laststart, b, b - laststart, upper_bound - 1);
+ b += 5;
+
+ GET_BUFFER_SPACE(5);
+ BUFPUSH(set_number_at);
+ STORE_NUMBER_AND_INCR(b, -5);
+ STORE_NUMBER_AND_INCR(b, upper_bound - 1);
+ }
+ pending_exact = 0;
+ }
+ break;
+
+ case '\\':
+ if (p == pend) goto invalid_pattern;
+ /* Do not translate the character after the \, so that we can
+ distinguish, e.g., \B from \b, even if we normally would
+ translate, e.g., B to b. */
+ PATFETCH_RAW(c);
+ switch (c)
+ {
+ case 's':
+ case 'S':
+ case 'd':
+ case 'D':
+ while (b - bufp->buffer
+ > bufp->allocated - 9 - (1 << BYTEWIDTH) / BYTEWIDTH)
+ EXTEND_BUFFER;
+
+ laststart = b;
+ if (c == 's' || c == 'd') {
+ BUFPUSH(charset);
+ }
+ else {
+ BUFPUSH(charset_not);
+ }
+
+ BUFPUSH((1 << BYTEWIDTH) / BYTEWIDTH);
+ memset(b, 0, (1 << BYTEWIDTH) / BYTEWIDTH + 2);
+ if (c == 's' || c == 'S') {
+ SET_LIST_BIT(' ');
+ SET_LIST_BIT('\t');
+ SET_LIST_BIT('\n');
+ SET_LIST_BIT('\r');
+ SET_LIST_BIT('\f');
+ }
+ else {
+ char cc;
+
+ for (cc = '0'; cc <= '9'; cc++) {
+ SET_LIST_BIT(cc);
+ }
+ }
+
+ while ((int) b[-1] > 0 && b[b[-1] - 1] == 0)
+ b[-1]--;
+ if (b[-1] != (1 << BYTEWIDTH) / BYTEWIDTH)
+ memmove(&b[b[-1]], &b[(1 << BYTEWIDTH) / BYTEWIDTH],
+ 2 + EXTRACT_UNSIGNED(&b[(1 << BYTEWIDTH) / BYTEWIDTH])*4);
+ b += b[-1] + 2 + EXTRACT_UNSIGNED(&b[b[-1]])*4;
+ break;
+
+ case 'w':
+ laststart = b;
+ BUFPUSH(wordchar);
+ break;
+
+ case 'W':
+ laststart = b;
+ BUFPUSH(notwordchar);
+ break;
+
+ case '<':
+ BUFPUSH(wordbeg);
+ break;
+
+ case '>':
+ BUFPUSH(wordend);
+ break;
+
+ case 'b':
+ BUFPUSH(wordbound);
+ break;
+
+ case 'B':
+ BUFPUSH(notwordbound);
+ break;
+
+ case 'A':
+ BUFPUSH(begbuf);
+ break;
+
+ case 'Z':
+ BUFPUSH(endbuf);
+ break;
+
+ /* hex */
+ case 'x':
+ c1 = 0;
+ c = scan_hex(p, 2, &numlen);
+ p += numlen;
+ if ((re_syntax_options & RE_MBCTYPE_MASK) && c > 0x7f)
+ c1 = 0xff;
+ goto numeric_char;
+
+ /* octal */
+ case '0':
+ c1 = 0;
+ c = scan_oct(p, 3, &numlen);
+ p += numlen;
+ if ((re_syntax_options & RE_MBCTYPE_MASK) && c > 0x7f)
+ c1 = 0xff;
+ goto numeric_char;
+
+ /* back-ref or octal */
+ case '1': case '2': case '3':
+ case '4': case '5': case '6':
+ case '7': case '8': case '9':
+ {
+ char *p_save;
+
+ PATUNFETCH;
+ p_save = p;
+
+ c1 = 0;
+ GET_UNSIGNED_NUMBER(c1);
+ if (p < pend) PATUNFETCH;
+
+ if (c1 >= regnum) {
+ /* need to get octal */
+ p = p_save;
+ c = scan_oct(p_save, 3, &numlen);
+ p = p_save + numlen;
+ c1 = 0;
+ if ((re_syntax_options & RE_MBCTYPE_MASK) && c > 0x7f)
+ c1 = 0xff;
+ goto numeric_char;
+ }
+ }
+
+ /* Can't back reference to a subexpression if inside of it. */
+ for (stackt = stackp - 2; stackt > stackb; stackt -= 5)
+ if (*stackt == c1)
+ goto normal_char;
+ laststart = b;
+ BUFPUSH(duplicate);
+ BUFPUSH(c1);
+ break;
+
+ default:
+ normal_backsl:
+ goto normal_char;
+ }
+ break;
+
+ default:
+ normal_char: /* Expects the character in `c'. */
+ c1 = 0;
+ if (ismbchar(c)) {
+ c1 = c;
+ PATFETCH(c);
+ }
+ else if (c > 0x7f) {
+ c1 = 0xff;
+ }
+ numeric_char:
+ if (!pending_exact || pending_exact + *pending_exact + 1 != b
+ || *pending_exact >= (c1 ? 0176 : 0177)
+ || *p == '+' || *p == '?'
+ || *p == '*' || *p == '^'
+ || *p == '{')
+ {
+ laststart = b;
+ BUFPUSH(exactn);
+ pending_exact = b;
+ BUFPUSH(0);
+ }
+ if (c1) {
+ BUFPUSH(c1);
+ (*pending_exact)++;
+ }
+ BUFPUSH(c);
+ (*pending_exact)++;
+ }
+ }
+
+ if (fixup_jump)
+ store_jump(fixup_jump, jump, b);
+
+ if (stackp != stackb) goto unmatched_open;
+
+ bufp->used = b - bufp->buffer;
+ bufp->re_nsub = regnum;
+ bufp->must = calculate_must_string(bufp->buffer, b);
+ FREE_AND_RETURN(stackb, 0);
+
+ invalid_char:
+ FREE_AND_RETURN(stackb, "invalid character in regular expression");
+
+ invalid_pattern:
+ FREE_AND_RETURN(stackb, "invalid regular expression");
+
+ unmatched_open:
+ FREE_AND_RETURN(stackb, "unmatched (");
+
+ unmatched_close:
+ FREE_AND_RETURN(stackb, "unmatched )");
+
+ end_of_pattern:
+ FREE_AND_RETURN(stackb, "premature end of regular expression");
+
+ too_big:
+ FREE_AND_RETURN(stackb, "regular expression too big");
+
+ memory_exhausted:
+ FREE_AND_RETURN(stackb, "memory exhausted");
+
+ nested_meta:
+ FREE_AND_RETURN(stackb, "nested *?+ in regexp");
+}
+
+
+/* Store a jump of the form <OPCODE> <relative address>.
+ Store in the location FROM a jump operation to jump to relative
+ address FROM - TO. OPCODE is the opcode to store. */
+
+static void
+store_jump(from, opcode, to)
+ char *from, *to;
+ int opcode;
+{
+ from[0] = (char)opcode;
+ STORE_NUMBER(from + 1, to - (from + 3));
+}
+
+
+/* Open up space before char FROM, and insert there a jump to TO.
+ CURRENT_END gives the end of the storage not in use, so we know
+ how much data to copy up. OP is the opcode of the jump to insert.
+
+ If you call this function, you must zero out pending_exact. */
+
+static void
+insert_jump(op, from, to, current_end)
+ int op;
+ char *from, *to, *current_end;
+{
+ register char *pfrom = current_end; /* Copy from here... */
+ register char *pto = current_end + 3; /* ...to here. */
+
+ while (pfrom != from)
+ *--pto = *--pfrom;
+ store_jump(from, op, to);
+}
+
+
+/* Store a jump of the form <opcode> <relative address> <n> .
+
+ Store in the location FROM a jump operation to jump to relative
+ address FROM - TO. OPCODE is the opcode to store, N is a number the
+ jump uses, say, to decide how many times to jump.
+
+ If you call this function, you must zero out pending_exact. */
+
+static void
+store_jump_n(from, opcode, to, n)
+ char *from, *to;
+ int opcode;
+ unsigned n;
+{
+ from[0] = (char)opcode;
+ STORE_NUMBER(from + 1, to - (from + 3));
+ STORE_NUMBER(from + 3, n);
+}
+
+
+/* Similar to insert_jump, but handles a jump which needs an extra
+ number to handle minimum and maximum cases. Open up space at
+ location FROM, and insert there a jump to TO. CURRENT_END gives the
+ end of the storage in use, so we know how much data to copy up. OP is
+ the opcode of the jump to insert.
+
+ If you call this function, you must zero out pending_exact. */
+
+static void
+insert_jump_n(op, from, to, current_end, n)
+ int op;
+ char *from, *to, *current_end;
+ unsigned n;
+{
+ register char *pfrom = current_end; /* Copy from here... */
+ register char *pto = current_end + 5; /* ...to here. */
+
+ while (pfrom != from)
+ *--pto = *--pfrom;
+ store_jump_n(from, op, to, n);
+}
+
+
+/* Open up space at location THERE, and insert operation OP.
+ CURRENT_END gives the end of the storage in use, so
+ we know how much data to copy up.
+
+ If you call this function, you must zero out pending_exact. */
+
+static void
+insert_op(op, there, current_end)
+ int op;
+ char *there, *current_end;
+{
+ register char *pfrom = current_end; /* Copy from here... */
+ register char *pto = current_end + 1; /* ...to here. */
+
+ while (pfrom != there)
+ *--pto = *--pfrom;
+
+ there[0] = (char)op;
+}
+
+
+/* Open up space at location THERE, and insert operation OP followed by
+ NUM_1 and NUM_2. CURRENT_END gives the end of the storage in use, so
+ we know how much data to copy up.
+
+ If you call this function, you must zero out pending_exact. */
+
+static void
+insert_op_2(op, there, current_end, num_1, num_2)
+ int op;
+ char *there, *current_end;
+ int num_1, num_2;
+{
+ register char *pfrom = current_end; /* Copy from here... */
+ register char *pto = current_end + 5; /* ...to here. */
+
+ while (pfrom != there)
+ *--pto = *--pfrom;
+
+ there[0] = (char)op;
+ STORE_NUMBER(there + 1, num_1);
+ STORE_NUMBER(there + 3, num_2);
+}
+
+
+#define trans_eq(c1, c2, translate) (translate?(translate[c1]==translate[c2]):((c1)==(c2)))
+static int
+must_match(little, lend, big, bend, translate)
+ unsigned char *little, *lend;
+ unsigned char *big, *bend;
+ unsigned char *translate;
+{
+ int c;
+
+ while (little < lend && big < bend) {
+ c = *little++;
+ if (c == 0xff) {
+ if (!trans_eq(*big++, *little++, translate)) break;
+ continue;
+ }
+ if (!trans_eq(*big++, c, translate)) break;
+ }
+ if (little == lend) return 1;
+ return 0;
+}
+
+static int
+must_instr(little, llen, big, blen, translate)
+ unsigned char *little;
+ int llen;
+ unsigned char *big;
+ int blen;
+ char *translate;
+{
+ unsigned char *bend = big + blen;
+ register int c;
+ int fescape = 0;
+
+ if (blen < llen)
+ return 0;
+
+ c = *little;
+ if (c == 0xff) {
+ c = *++little;
+ fescape = 1;
+ }
+ else if (translate && !ismbchar(c)) {
+ c = translate[c];
+ }
+
+ while (big < bend) {
+ /* look for first character */
+ if (fescape) {
+ while (big < bend) {
+ if (*big == c) break;
+ big++;
+ }
+ }
+ else if (translate && !ismbchar(c)) {
+ while (big < bend) {
+ if (ismbchar(*big)) big++;
+ else if (translate[*big] == c) break;
+ big++;
+ }
+ }
+ else {
+ while (big < bend) {
+ if (*big == c) break;
+ if (ismbchar(*big)) big++;
+ big++;
+ }
+ }
+
+ if (must_match(little, little+llen, big, bend, translate))
+ return 1;
+
+ if (ismbchar(*big)) big++;
+ big++;
+ }
+ return 0;
+}
+
+
+/* Given a pattern, compute a fastmap from it. The fastmap records
+ which of the (1 << BYTEWIDTH) possible characters can start a string
+ that matches the pattern. This fastmap is used by re_search to skip
+ quickly over totally implausible text.
+
+ The caller must supply the address of a (1 << BYTEWIDTH)-byte data
+ area as bufp->fastmap.
+ The other components of bufp describe the pattern to be used. */
+void
+re_compile_fastmap(bufp)
+ struct re_pattern_buffer *bufp;
+{
+ unsigned char *pattern = (unsigned char *) bufp->buffer;
+ int size = bufp->used;
+ register char *fastmap = bufp->fastmap;
+ register unsigned char *p = pattern;
+ register unsigned char *pend = pattern + size;
+ register int j, k;
+ unsigned char *translate = (unsigned char *)bufp->translate;
+ unsigned is_a_succeed_n;
+
+ unsigned char **stackb = RE_TALLOC(NFAILURES, unsigned char*);
+ unsigned char **stackp = stackb;
+ unsigned char **stacke = stackb + NFAILURES;
+
+ memset(fastmap, 0, (1 << BYTEWIDTH));
+ bufp->fastmap_accurate = 1;
+ bufp->can_be_null = 0;
+
+ while (p)
+ {
+ is_a_succeed_n = 0;
+ if (p == pend)
+ {
+ bufp->can_be_null = 1;
+ break;
+ }
+#ifdef SWITCH_ENUM_BUG
+ switch ((int) ((enum regexpcode)*p++))
+#else
+ switch ((enum regexpcode)*p++)
+#endif
+ {
+ case exactn:
+ if (p[1] == 0xff) {
+ if (translate)
+ fastmap[translate[p[2]]] = 2;
+ else
+ fastmap[p[2]] = 2;
+ }
+ else if (translate)
+ fastmap[translate[p[1]]] = 1;
+ else
+ fastmap[p[1]] = 1;
+ break;
+
+ case begline:
+ case begbuf:
+ case endbuf:
+ case wordbound:
+ case notwordbound:
+ case wordbeg:
+ case wordend:
+ case pop_and_fail:
+ continue;
+
+ case endline:
+ if (translate)
+ fastmap[translate['\n']] = 1;
+ else
+ fastmap['\n'] = 1;
+
+ if (bufp->can_be_null == 0)
+ bufp->can_be_null = 2;
+ break;
+
+ case jump_n:
+ case finalize_jump:
+ case maybe_finalize_jump:
+ case jump:
+ case dummy_failure_jump:
+ EXTRACT_NUMBER_AND_INCR(j, p);
+ p += j;
+ if (j > 0)
+ continue;
+ /* Jump backward reached implies we just went through
+ the body of a loop and matched nothing.
+ Opcode jumped to should be an on_failure_jump.
+ Just treat it like an ordinary jump.
+ For a * loop, it has pushed its failure point already;
+ If so, discard that as redundant. */
+
+ if ((enum regexpcode) *p != on_failure_jump
+ && (enum regexpcode) *p != try_next
+ && (enum regexpcode) *p != finalize_push
+ && (enum regexpcode) *p != finalize_push_n)
+ continue;
+ p++;
+ EXTRACT_NUMBER_AND_INCR(j, p);
+ p += j;
+ if (stackp != stackb && *stackp == p)
+ stackp--; /* pop */
+ continue;
+
+ case start_nowidth:
+ case stop_nowidth:
+ case finalize_push:
+ p += 2;
+ continue;
+
+ case finalize_push_n:
+ p += 4;
+ continue;
+
+ case try_next:
+ case on_failure_jump:
+ handle_on_failure_jump:
+ EXTRACT_NUMBER_AND_INCR(j, p);
+ if (p + j < pend) {
+ if (stackp == stacke) {
+ unsigned char **stackx;
+ unsigned int len = stacke - stackb;
+
+ EXPAND_FAIL_STACK(stackx, stackb, len);
+ }
+ *++stackp = p + j; /* push */
+ }
+ else {
+ bufp->can_be_null = 1;
+ }
+ if (is_a_succeed_n)
+ EXTRACT_NUMBER_AND_INCR(k, p); /* Skip the n. */
+ continue;
+
+ case succeed_n:
+ is_a_succeed_n = 1;
+ /* Get to the number of times to succeed. */
+ EXTRACT_NUMBER(k, p + 2);
+ /* Increment p past the n for when k != 0. */
+ if (k == 0) {
+ p += 4;
+ }
+ else {
+ goto handle_on_failure_jump;
+ }
+ continue;
+
+ case set_number_at:
+ p += 4;
+ continue;
+
+ case start_memory:
+ case stop_memory:
+ p++;
+ continue;
+
+ case duplicate:
+ bufp->can_be_null = 1;
+ fastmap['\n'] = 1;
+ case anychar:
+ for (j = 0; j < (1 << BYTEWIDTH); j++)
+ if (j != '\n')
+ fastmap[j] = 1;
+ if (bufp->can_be_null)
+ {
+ FREE_AND_RETURN_VOID(stackb);
+ }
+ /* Don't return; check the alternative paths
+ so we can set can_be_null if appropriate. */
+ break;
+
+ case wordchar:
+ for (j = 0; j < (1 << BYTEWIDTH); j++)
+ if (SYNTAX(j) == Sword)
+ fastmap[j] = 1;
+ break;
+
+ case notwordchar:
+ for (j = 0; j < 0x80; j++)
+ if (SYNTAX(j) != Sword)
+ fastmap[j] = 1;
+ for (j = 0x80; j < (1 << BYTEWIDTH); j++)
+ fastmap[j] = 1;
+ break;
+
+ case charset:
+ /* NOTE: Charset for single-byte chars never contain
+ multi-byte char. See set_list_bits(). */
+ for (j = *p++ * BYTEWIDTH - 1; j >= 0; j--)
+ if (p[j / BYTEWIDTH] & (1 << (j % BYTEWIDTH)))
+ {
+ if (translate)
+ fastmap[translate[j]] = 1;
+ else
+ fastmap[j] = 1;
+ }
+ {
+ unsigned short size;
+ unsigned c, end;
+
+ p += p[-1] + 2;
+ size = EXTRACT_UNSIGNED(&p[-2]);
+ for (j = 0; j < (int)size; j++) {
+ if ((unsigned char)p[j*4] == 0xff) {
+ for (c = (unsigned char)p[j*4+1],
+ end = (unsigned char)p[j*4+3];
+ c <= end; c++) {
+ fastmap[c] = 2;
+ }
+ }
+ else {
+ /* set bits for 1st bytes of multi-byte chars. */
+ for (c = (unsigned char)p[j*4],
+ end = (unsigned char)p[j*4 + 2];
+ c <= end; c++) {
+ /* NOTE: Charset for multi-byte chars might contain
+ single-byte chars. We must reject them. */
+ if (ismbchar(c))
+ fastmap[c] = 1;
+ }
+ }
+ }
+ }
+ break;
+
+ case charset_not:
+ /* S: set of all single-byte chars.
+ M: set of all first bytes that can start multi-byte chars.
+ s: any set of single-byte chars.
+ m: any set of first bytes that can start multi-byte chars.
+
+ We assume S+M = U.
+ ___ _ _
+ s+m = (S*s+M*m). */
+ /* Chars beyond end of map must be allowed */
+ /* NOTE: Charset_not for single-byte chars might contain
+ multi-byte chars. See set_list_bits(). */
+ for (j = *p * BYTEWIDTH; j < (1 << BYTEWIDTH); j++)
+ if (!ismbchar(j))
+ fastmap[j] = 1;
+
+ for (j = *p++ * BYTEWIDTH - 1; j >= 0; j--)
+ if (!(p[j / BYTEWIDTH] & (1 << (j % BYTEWIDTH))))
+ {
+ if (!ismbchar(j))
+ fastmap[j] = 1;
+ }
+ {
+ unsigned short size;
+ unsigned char c, beg;
+
+ p += p[-1] + 2;
+ size = EXTRACT_UNSIGNED(&p[-2]);
+ if (size == 0) {
+ for (j = 0x80; j < (1 << BYTEWIDTH); j++)
+ if (ismbchar(j))
+ fastmap[j] = 1;
+ }
+ for (j = 0,c = 0x80;j < (int)size; j++) {
+ if ((unsigned char)p[j*4] == 0xff) {
+ for (beg = (unsigned char)p[j*4+1]; c < beg; c++)
+ fastmap[c] = 2;
+ c = (unsigned char)p[j*4+3] + 1;
+ }
+ else {
+ for (beg = (unsigned char)p[j*4 + 0]; c < beg; c++)
+ if (ismbchar(c))
+ fastmap[c] = 1;
+ c = (unsigned char)p[j*4 + 2] + 1;
+ }
+ }
+ }
+ break;
+
+ case unused: /* pacify gcc -Wall */
+ break;
+ }
+
+ /* Get here means we have successfully found the possible starting
+ characters of one path of the pattern. We need not follow this
+ path any farther. Instead, look at the next alternative
+ remembered in the stack. */
+ if (stackp != stackb)
+ p = *stackp--; /* pop */
+ else
+ break;
+ }
+ FREE_AND_RETURN_VOID(stackb);
+}
+
+
+/* Using the compiled pattern in BUFP->buffer, first tries to match
+ STRING, starting first at index STARTPOS, then at STARTPOS + 1, and
+ so on. RANGE is the number of places to try before giving up. If
+ RANGE is negative, it searches backwards, i.e., the starting
+ positions tried are STARTPOS, STARTPOS - 1, etc. STRING is of SIZE.
+ In REGS, return the indices of STRING that matched the entire
+ BUFP->buffer and its contained subexpressions.
+
+ The value returned is the position in the strings at which the match
+ was found, or -1 if no match was found, or -2 if error (such as
+ failure stack overflow). */
+
+int
+re_search(bufp, string, size, startpos, range, regs)
+ struct re_pattern_buffer *bufp;
+ char *string;
+ int size, startpos, range;
+ struct re_registers *regs;
+{
+ register char *fastmap = bufp->fastmap;
+ register unsigned char *translate = (unsigned char *) bufp->translate;
+ int val, anchor = 0;
+
+ /* Check for out-of-range starting position. */
+ if (startpos < 0 || startpos > size)
+ return -1;
+
+ /* If the search isn't to be a backwards one, don't waste time in a
+ search for a pattern that must be anchored. */
+ if (bufp->used>0) {
+ switch ((enum regexpcode)bufp->buffer[0]) {
+ case begbuf:
+ if (range > 0) {
+ if (startpos > 0)
+ return -1;
+ else
+ return re_match(bufp, string, size, 0, regs);
+ }
+ break;
+
+ case begline:
+ if (startpos == 0) {
+ val = re_match(bufp, string, size, 0, regs);
+ if (val >= 0) return 0;
+ }
+ anchor = 1;
+ break;
+
+ default:
+ break;
+ }
+ }
+#if 1
+ if (range > 0
+ && bufp->must
+ && !must_instr(bufp->must+1, bufp->must[0],
+ string+startpos, size-startpos,
+ translate)) {
+ return -1;
+ }
+#endif
+ /* Update the fastmap now if not correct already. */
+ if (fastmap && !bufp->fastmap_accurate) {
+ re_compile_fastmap(bufp);
+ }
+
+ for (;;)
+ {
+ /* If a fastmap is supplied, skip quickly over characters that
+ cannot possibly be the start of a match. Note, however, that
+ if the pattern can possibly match the null string, we must
+ test it at each starting point so that we take the first null
+ string we get. */
+
+ if (fastmap && startpos < size
+ && bufp->can_be_null != 1 && !(anchor && startpos == 0))
+ {
+ if (range > 0) /* Searching forwards. */
+ {
+ register unsigned char *p, c;
+ int irange = range;
+
+ p = (unsigned char *)string+startpos;
+
+ while (range > 0) {
+ c = *p++;
+ if (ismbchar(c)) {
+ if (fastmap[c])
+ break;
+ c = *p++;
+ range--;
+ if (fastmap[c] == 2)
+ break;
+ }
+ else
+ if (fastmap[translate ? translate[c] : c])
+ break;
+ range--;
+ }
+ startpos += irange - range;
+ }
+ else /* Searching backwards. */
+ {
+ register unsigned char c;
+
+ c = string[startpos];
+ c &= 0xff;
+ if (translate ? !fastmap[translate[c]] : !fastmap[c])
+ goto advance;
+ }
+ }
+
+ if (anchor && startpos > 0 && startpos < size
+ && string[startpos-1] != '\n') goto advance;
+
+ if (fastmap && startpos == size && range >= 0
+ && (bufp->can_be_null == 0 ||
+ (bufp->can_be_null == 2 && size > 0
+ && string[startpos-1] == '\n')))
+ return -1;
+
+ val = re_match(bufp, string, size, startpos, regs);
+ if (val >= 0)
+ return startpos;
+ if (val == -2)
+ return -2;
+
+#ifndef NO_ALLOCA
+#ifdef cALLOCA
+ alloca(0);
+#endif /* cALLOCA */
+#endif /* NO_ALLOCA */
+
+ advance:
+ if (!range)
+ break;
+ else if (range > 0) {
+ const char *d = string + startpos;
+
+ if (ismbchar(*d)) {
+ range--, startpos++;
+ if (!range)
+ break;
+ }
+ range--, startpos++;
+ }
+ else {
+ range++, startpos--;
+ {
+ const char *s, *d, *p;
+
+ s = string; d = string + startpos;
+ for (p = d; p-- > s && ismbchar(*p); )
+ /* --p >= s would not work on 80[12]?86.
+ (when the offset of s equals 0 other than huge model.) */
+ ;
+ if (!((d - p) & 1)) {
+ if (!range)
+ break;
+ range++, startpos--;
+ }
+ }
+ }
+ }
+ return -1;
+}
+
+
+
+
+/* The following are used for re_match, defined below: */
+
+/* Roughly the maximum number of failure points on the stack. Would be
+ exactly that if always pushed MAX_NUM_FAILURE_ITEMS each time we failed. */
+
+int re_max_failures = 2000;
+
+/* Routine used by re_match. */
+/* static int memcmp_translate(); *//* already declared */
+
+
+/* Structure and accessing macros used in re_match: */
+
+struct register_info
+{
+ unsigned is_active : 1;
+ unsigned matched_something : 1;
+};
+
+#define IS_ACTIVE(R) ((R).is_active)
+#define MATCHED_SOMETHING(R) ((R).matched_something)
+
+
+/* Macros used by re_match: */
+
+/* I.e., regstart, regend, and reg_info. */
+
+#define NUM_REG_ITEMS 3
+
+/* We push at most this many things on the stack whenever we
+ fail. The `+ 2' refers to PATTERN_PLACE and STRING_PLACE, which are
+ arguments to the PUSH_FAILURE_POINT macro. */
+
+#define MAX_NUM_FAILURE_ITEMS (num_regs * NUM_REG_ITEMS + 2)
+
+
+/* We push this many things on the stack whenever we fail. */
+
+#define NUM_FAILURE_ITEMS (last_used_reg * NUM_REG_ITEMS + 2)
+
+
+/* This pushes most of the information about the current state we will want
+ if we ever fail back to it. */
+
+#define PUSH_FAILURE_POINT(pattern_place, string_place) \
+ { \
+ long last_used_reg, this_reg; \
+ \
+ /* Find out how many registers are active or have been matched. \
+ (Aside from register zero, which is only set at the end.) */ \
+ for (last_used_reg = num_regs - 1; last_used_reg > 0; last_used_reg--)\
+ if (regstart[last_used_reg] != (unsigned char *)(-1L)) \
+ break; \
+ \
+ if (stacke - stackp <= NUM_FAILURE_ITEMS) \
+ { \
+ unsigned char **stackx; \
+ unsigned int len = stacke - stackb; \
+ if (len > re_max_failures * MAX_NUM_FAILURE_ITEMS) \
+ { \
+ FREE_VARIABLES(); \
+ FREE_AND_RETURN(stackb,(-2)); \
+ } \
+ \
+ /* Roughly double the size of the stack. */ \
+ EXPAND_FAIL_STACK(stackx, stackb, len); \
+ } \
+ \
+ /* Now push the info for each of those registers. */ \
+ for (this_reg = 1; this_reg <= last_used_reg; this_reg++) \
+ { \
+ *stackp++ = regstart[this_reg]; \
+ *stackp++ = regend[this_reg]; \
+ *stackp++ = (unsigned char *)&reg_info[this_reg]; \
+ } \
+ \
+ /* Push how many registers we saved. */ \
+ *stackp++ = (unsigned char *)last_used_reg; \
+ \
+ *stackp++ = pattern_place; \
+ *stackp++ = string_place; \
+ *stackp++ = (unsigned char *)0; /* non-greedy flag */ \
+ }
+
+
+/* This pops what PUSH_FAILURE_POINT pushes. */
+
+#define POP_FAILURE_POINT() \
+ { \
+ int temp; \
+ stackp -= 3; /* Remove failure points (and flag). */ \
+ temp = (int) *--stackp; /* How many regs pushed. */ \
+ temp *= NUM_REG_ITEMS; /* How much to take off the stack. */ \
+ stackp -= temp; /* Remove the register info. */ \
+ }
+
+#define PREFETCH if (d == dend) goto fail
+
+/* Call this when have matched something; it sets `matched' flags for the
+ registers corresponding to the subexpressions of which we currently
+ are inside. */
+#define SET_REGS_MATCHED \
+ { unsigned this_reg; \
+ for (this_reg = 0; this_reg < num_regs; this_reg++) \
+ { \
+ if (IS_ACTIVE(reg_info[this_reg])) \
+ MATCHED_SOMETHING(reg_info[this_reg]) = 1; \
+ else \
+ MATCHED_SOMETHING(reg_info[this_reg]) = 0; \
+ } \
+ }
+
+#define AT_STRINGS_BEG(d) (d == string)
+#define AT_STRINGS_END(d) (d == dend)
+
+#define AT_WORD_BOUNDARY(d) \
+ (AT_STRINGS_BEG(d) || AT_STRINGS_END(d) || IS_A_LETTER(d - 1) != IS_A_LETTER(d))
+
+/* We have two special cases to check for:
+ 1) if we're past the end of string1, we have to look at the first
+ character in string2;
+ 2) if we're before the beginning of string2, we have to look at the
+ last character in string1; we assume there is a string1, so use
+ this in conjunction with AT_STRINGS_BEG. */
+#define IS_A_LETTER(d) (SYNTAX(*(d)) == Sword)
+
+static void
+init_regs(regs, num_regs)
+ struct re_registers *regs;
+ unsigned num_regs;
+{
+ int i;
+
+ regs->num_regs = num_regs;
+ if (num_regs < RE_NREGS)
+ num_regs = RE_NREGS;
+
+ if (regs->allocated == 0) {
+ regs->beg = TMALLOC(num_regs, int);
+ regs->end = TMALLOC(num_regs, int);
+ regs->allocated = num_regs;
+ }
+ else if (regs->allocated < num_regs) {
+ TREALLOC(regs->beg, num_regs, int);
+ TREALLOC(regs->end, num_regs, int);
+ }
+ for (i=0; i<num_regs; i++) {
+ regs->beg[i] = regs->end[i] = -1;
+ }
+}
+
+/* Match the pattern described by BUFP against STRING, which is of
+ SIZE. Start the match at index POS in STRING. In REGS, return the
+ indices of STRING that matched the entire BUFP->buffer and its
+ contained subexpressions.
+
+ If bufp->fastmap is nonzero, then it had better be up to date.
+
+ The reason that the data to match are specified as two components
+ which are to be regarded as concatenated is so this function can be
+ used directly on the contents of an Emacs buffer.
+
+ -1 is returned if there is no match. -2 is returned if there is an
+ error (such as match stack overflow). Otherwise the value is the
+ length of the substring which was matched. */
+
+int
+re_match(bufp, string_arg, size, pos, regs)
+ struct re_pattern_buffer *bufp;
+ char *string_arg;
+ int size, pos;
+ struct re_registers *regs;
+{
+ register unsigned char *p = (unsigned char *) bufp->buffer;
+
+ /* Pointer to beyond end of buffer. */
+ register unsigned char *pend = p + bufp->used;
+
+ unsigned num_regs = bufp->re_nsub;
+
+ unsigned char *string = (unsigned char *) string_arg;
+
+ register unsigned char *d, *dend;
+ register int mcnt; /* Multipurpose. */
+ unsigned char *translate = (unsigned char *) bufp->translate;
+ unsigned is_a_jump_n = 0;
+
+ /* Failure point stack. Each place that can handle a failure further
+ down the line pushes a failure point on this stack. It consists of
+ restart, regend, and reg_info for all registers corresponding to the
+ subexpressions we're currently inside, plus the number of such
+ registers, and, finally, two char *'s. The first char * is where to
+ resume scanning the pattern; the second one is where to resume
+ scanning the strings. If the latter is zero, the failure point is a
+ ``dummy''; if a failure happens and the failure point is a dummy, it
+ gets discarded and the next next one is tried. */
+
+ unsigned char **stackb;
+ unsigned char **stackp;
+ unsigned char **stacke;
+
+
+ /* Information on the contents of registers. These are pointers into
+ the input strings; they record just what was matched (on this
+ attempt) by a subexpression part of the pattern, that is, the
+ regnum-th regstart pointer points to where in the pattern we began
+ matching and the regnum-th regend points to right after where we
+ stopped matching the regnum-th subexpression. (The zeroth register
+ keeps track of what the whole pattern matches.) */
+
+ unsigned char **regstart = RE_TALLOC(num_regs, unsigned char*);
+ unsigned char **regend = RE_TALLOC(num_regs, unsigned char*);
+
+ /* The is_active field of reg_info helps us keep track of which (possibly
+ nested) subexpressions we are currently in. The matched_something
+ field of reg_info[reg_num] helps us tell whether or not we have
+ matched any of the pattern so far this time through the reg_num-th
+ subexpression. These two fields get reset each time through any
+ loop their register is in. */
+
+ struct register_info *reg_info = RE_TALLOC(num_regs, struct register_info);
+
+ /* The following record the register info as found in the above
+ variables when we find a match better than any we've seen before.
+ This happens as we backtrack through the failure points, which in
+ turn happens only if we have not yet matched the entire string. */
+
+ unsigned best_regs_set = 0;
+ unsigned char **best_regstart = RE_TALLOC(num_regs, unsigned char*);
+ unsigned char **best_regend = RE_TALLOC(num_regs, unsigned char*);
+
+ if (regs) {
+ init_regs(regs, num_regs);
+ }
+
+ /* Initialize the stack. */
+ stackb = RE_TALLOC(MAX_NUM_FAILURE_ITEMS * NFAILURES, unsigned char*);
+ stackp = stackb;
+ stacke = &stackb[MAX_NUM_FAILURE_ITEMS * NFAILURES];
+
+#ifdef DEBUG_REGEX
+ fprintf (stderr, "Entering re_match(%s%s)\n", string1_arg, string2_arg);
+#endif
+
+ /* Initialize subexpression text positions to -1 to mark ones that no
+ \( or ( and \) or ) has been seen for. Also set all registers to
+ inactive and mark them as not having matched anything or ever
+ failed. */
+ for (mcnt = 0; mcnt < num_regs; mcnt++) {
+ regstart[mcnt] = regend[mcnt] = (unsigned char *) (-1L);
+ IS_ACTIVE(reg_info[mcnt]) = 0;
+ MATCHED_SOMETHING(reg_info[mcnt]) = 0;
+ }
+
+ /* Set up pointers to ends of strings.
+ Don't allow the second string to be empty unless both are empty. */
+
+
+ /* `p' scans through the pattern as `d' scans through the data. `dend'
+ is the end of the input string that `d' points within. `d' is
+ advanced into the following input string whenever necessary, but
+ this happens before fetching; therefore, at the beginning of the
+ loop, `d' can be pointing at the end of a string, but it cannot
+ equal string2. */
+
+ d = string + pos, dend = string + size;
+
+
+ /* This loops over pattern commands. It exits by returning from the
+ function if match is complete, or it drops through if match fails
+ at this starting point in the input data. */
+
+ for (;;)
+ {
+#ifdef DEBUG_REGEX
+ fprintf(stderr,
+ "regex loop(%d): matching 0x%02d\n",
+ p - (unsigned char *) bufp->buffer,
+ *p);
+#endif
+ is_a_jump_n = 0;
+ /* End of pattern means we might have succeeded. */
+ if (p == pend)
+ {
+ /* If not end of string, try backtracking. Otherwise done. */
+ if (d != dend)
+ {
+ if (stackp != stackb)
+ {
+ /* More failure points to try. */
+
+ /* If exceeds best match so far, save it. */
+ if (! best_regs_set || (d > best_regend[0]))
+ {
+ best_regs_set = 1;
+ best_regend[0] = d; /* Never use regstart[0]. */
+
+ for (mcnt = 1; mcnt < num_regs; mcnt++)
+ {
+ best_regstart[mcnt] = regstart[mcnt];
+ best_regend[mcnt] = regend[mcnt];
+ }
+ }
+ goto fail;
+ }
+ /* If no failure points, don't restore garbage. */
+ else if (best_regs_set)
+ {
+ restore_best_regs:
+ /* Restore best match. */
+ d = best_regend[0];
+
+ for (mcnt = 0; mcnt < num_regs; mcnt++)
+ {
+ regstart[mcnt] = best_regstart[mcnt];
+ regend[mcnt] = best_regend[mcnt];
+ }
+ }
+ }
+
+ /* If caller wants register contents data back, convert it
+ to indices. */
+ if (regs)
+ {
+ regs->beg[0] = pos;
+ regs->end[0] = d - string;
+ for (mcnt = 1; mcnt < num_regs; mcnt++)
+ {
+ if (regend[mcnt] == (unsigned char *)(-1L))
+ {
+ regs->beg[mcnt] = -1;
+ regs->end[mcnt] = -1;
+ continue;
+ }
+ regs->beg[mcnt] = regstart[mcnt] - string;
+ regs->end[mcnt] = regend[mcnt] - string;
+ }
+ }
+ FREE_VARIABLES();
+ FREE_AND_RETURN(stackb, (d - pos - string));
+ }
+
+ /* Otherwise match next pattern command. */
+#ifdef SWITCH_ENUM_BUG
+ switch ((int)((enum regexpcode)*p++))
+#else
+ switch ((enum regexpcode)*p++)
+#endif
+ {
+
+ /* \( [or `(', as appropriate] is represented by start_memory,
+ \) by stop_memory. Both of those commands are followed by
+ a register number in the next byte. The text matched
+ within the \( and \) is recorded under that number. */
+ case start_memory:
+ regstart[*p] = d;
+ IS_ACTIVE(reg_info[*p]) = 1;
+ MATCHED_SOMETHING(reg_info[*p]) = 0;
+ p++;
+ continue;
+
+ case stop_memory:
+ regend[*p] = d;
+ IS_ACTIVE(reg_info[*p]) = 0;
+
+ /* If just failed to match something this time around with a sub-
+ expression that's in a loop, try to force exit from the loop. */
+ if ((! MATCHED_SOMETHING(reg_info[*p])
+ || (enum regexpcode) p[-3] == start_memory)
+ && (p + 1) != pend)
+ {
+ register unsigned char *p2 = p + 1;
+ mcnt = 0;
+ switch (*p2++)
+ {
+ case jump_n:
+ is_a_jump_n = 1;
+ case finalize_jump:
+ case maybe_finalize_jump:
+ case jump:
+ case dummy_failure_jump:
+ EXTRACT_NUMBER_AND_INCR(mcnt, p2);
+ if (is_a_jump_n)
+ p2 += 2;
+ break;
+ }
+ p2 += mcnt;
+
+ /* If the next operation is a jump backwards in the pattern
+ to an on_failure_jump, exit from the loop by forcing a
+ failure after pushing on the stack the on_failure_jump's
+ jump in the pattern, and d. */
+ if (mcnt < 0 && (enum regexpcode) *p2++ == on_failure_jump)
+ {
+ EXTRACT_NUMBER_AND_INCR(mcnt, p2);
+ PUSH_FAILURE_POINT(p2 + mcnt, d);
+ goto fail;
+ }
+ }
+ p++;
+ continue;
+
+ /* \<digit> has been turned into a `duplicate' command which is
+ followed by the numeric value of <digit> as the register number. */
+ case duplicate:
+ {
+ int regno = *p++; /* Get which register to match against */
+ register unsigned char *d2, *dend2;
+
+ /* Where in input to try to start matching. */
+ d2 = regstart[regno];
+
+ /* Where to stop matching; if both the place to start and
+ the place to stop matching are in the same string, then
+ set to the place to stop, otherwise, for now have to use
+ the end of the first string. */
+
+ dend2 = regend[regno];
+ for (;;)
+ {
+ /* At end of register contents => success */
+ if (d2 == dend2) break;
+
+ /* If necessary, advance to next segment in data. */
+ PREFETCH;
+
+ /* How many characters left in this segment to match. */
+ mcnt = dend - d;
+
+ /* Want how many consecutive characters we can match in
+ one shot, so, if necessary, adjust the count. */
+ if (mcnt > dend2 - d2)
+ mcnt = dend2 - d2;
+
+ /* Compare that many; failure if mismatch, else move
+ past them. */
+ if (translate
+ ? memcmp_translate(d, d2, mcnt, translate)
+ : memcmp((char *)d, (char *)d2, mcnt))
+ goto fail;
+ d += mcnt, d2 += mcnt;
+ }
+ }
+ break;
+
+ case start_nowidth:
+ PUSH_FAILURE_POINT(0, d);
+ EXTRACT_NUMBER_AND_INCR(mcnt, p);
+ STORE_NUMBER(p+mcnt, stackp - stackb);
+ continue;
+
+ case stop_nowidth:
+ EXTRACT_NUMBER_AND_INCR(mcnt, p);
+ stackp = stackb + mcnt;
+ d = stackp[-2];
+ POP_FAILURE_POINT();
+ continue;
+
+ case pop_and_fail:
+ EXTRACT_NUMBER(mcnt, p+1);
+ stackp = stackb + mcnt;
+ POP_FAILURE_POINT();
+ goto fail;
+
+ case anychar:
+ PREFETCH;
+ /* Match anything but a newline, maybe even a null. */
+ if (ismbchar(*d)) {
+ if (d + 1 == dend || d[1] == '\n' || d[1] == '\0')
+ goto fail;
+ SET_REGS_MATCHED;
+ d += 2;
+ break;
+ }
+ if ((translate ? translate[*d] : *d) == '\n'
+ || ((re_syntax_options & RE_DOT_NOT_NULL)
+ && (translate ? translate[*d] : *d) == '\000'))
+ goto fail;
+ SET_REGS_MATCHED;
+ d++;
+ break;
+
+ case charset:
+ case charset_not:
+ {
+ int not; /* Nonzero for charset_not. */
+ int half; /* 2 if need to match latter half of mbc */
+ int c;
+
+ PREFETCH;
+ c = (unsigned char)*d;
+ if (ismbchar(c)) {
+ if (d + 1 != dend) {
+ c <<= 8;
+ c |= (unsigned char)d[1];
+ }
+ }
+ else if (translate)
+ c = (unsigned char)translate[c];
+
+ half = not = is_in_list(c, p);
+ if (*(p - 1) == (unsigned char)charset_not) {
+ not = !not;
+ }
+
+ p += 1 + *p + 2 + EXTRACT_UNSIGNED(&p[1 + *p])*4;
+
+ if (!not) goto fail;
+ SET_REGS_MATCHED;
+
+ d++;
+ if (half != 2 && d != dend && c >= 1 << BYTEWIDTH)
+ d++;
+ break;
+ }
+
+ case begline:
+ if (size == 0
+ || d == string
+ || (d && d[-1] == '\n'))
+ break;
+ else
+ goto fail;
+
+ case endline:
+ if (d == dend || *d == '\n')
+ break;
+ goto fail;
+
+ /* Match at the very beginning of the string. */
+ case begbuf:
+ if (AT_STRINGS_BEG(d))
+ break;
+ goto fail;
+
+ /* Match at the very end of the data. */
+ case endbuf:
+ if (AT_STRINGS_END(d))
+ break;
+ goto fail;
+
+ /* `or' constructs are handled by starting each alternative with
+ an on_failure_jump that points to the start of the next
+ alternative. Each alternative except the last ends with a
+ jump to the joining point. (Actually, each jump except for
+ the last one really jumps to the following jump, because
+ tensioning the jumps is a hassle.) */
+
+ /* The start of a stupid repeat has an on_failure_jump that points
+ past the end of the repeat text. This makes a failure point so
+ that on failure to match a repetition, matching restarts past
+ as many repetitions have been found with no way to fail and
+ look for another one. */
+
+ /* A smart repeat is similar but loops back to the on_failure_jump
+ so that each repetition makes another failure point. */
+
+ case on_failure_jump:
+ on_failure:
+ EXTRACT_NUMBER_AND_INCR(mcnt, p);
+ PUSH_FAILURE_POINT(p + mcnt, d);
+ continue;
+
+ /* The end of a smart repeat has a maybe_finalize_jump back.
+ Change it either to a finalize_jump or an ordinary jump. */
+ case maybe_finalize_jump:
+ EXTRACT_NUMBER_AND_INCR(mcnt, p);
+ {
+ register unsigned char *p2 = p;
+ /* Compare what follows with the beginning of the repeat.
+ If we can establish that there is nothing that they would
+ both match, we can change to finalize_jump. */
+ while (p2 + 1 != pend
+ && (*p2 == (unsigned char)stop_memory
+ || *p2 == (unsigned char)start_memory))
+ p2 += 2; /* Skip over reg number. */
+ if (p2 == pend)
+ p[-3] = (unsigned char)finalize_jump;
+ else if (*p2 == (unsigned char)exactn
+ || *p2 == (unsigned char)endline)
+ {
+ register int c = *p2 == (unsigned char)endline ? '\n' : p2[2];
+ register unsigned char *p1 = p + mcnt;
+ /* p1[0] ... p1[2] are an on_failure_jump.
+ Examine what follows that. */
+ if (p1[3] == (unsigned char)exactn && p1[5] != c)
+ p[-3] = (unsigned char)finalize_jump;
+ else if (p1[3] == (unsigned char)charset
+ || p1[3] == (unsigned char)charset_not) {
+ int not;
+ if (ismbchar(c))
+ c = c << 8 | p2[3];
+ /* `is_in_list()' is TRUE if c would match */
+ /* That means it is not safe to finalize. */
+ not = is_in_list(c, p1 + 4);
+ if (p1[3] == (unsigned char)charset_not)
+ not = !not;
+ if (!not)
+ p[-3] = (unsigned char)finalize_jump;
+ }
+ }
+ }
+ p -= 2; /* Point at relative address again. */
+ if (p[-1] != (unsigned char)finalize_jump)
+ {
+ p[-1] = (unsigned char)jump;
+ goto nofinalize;
+ }
+ /* Note fall through. */
+
+ /* The end of a stupid repeat has a finalize_jump back to the
+ start, where another failure point will be made which will
+ point to after all the repetitions found so far. */
+
+ /* Take off failure points put on by matching on_failure_jump
+ because didn't fail. Also remove the register information
+ put on by the on_failure_jump. */
+ case finalize_jump:
+ POP_FAILURE_POINT();
+ /* Note fall through. */
+
+ /* Jump without taking off any failure points. */
+ case jump:
+ nofinalize:
+ EXTRACT_NUMBER_AND_INCR(mcnt, p);
+ p += mcnt;
+ continue;
+
+ case dummy_failure_jump:
+ /* Normally, the on_failure_jump pushes a failure point, which
+ then gets popped at finalize_jump. We will end up at
+ finalize_jump, also, and with a pattern of, say, `a+', we
+ are skipping over the on_failure_jump, so we have to push
+ something meaningless for finalize_jump to pop. */
+ PUSH_FAILURE_POINT(0, 0);
+ goto nofinalize;
+
+ /* Have to succeed matching what follows at least n times. Then
+ just handle like an on_failure_jump. */
+ case succeed_n:
+ EXTRACT_NUMBER(mcnt, p + 2);
+ /* Originally, this is how many times we HAVE to succeed. */
+ if (mcnt > 0)
+ {
+ mcnt--;
+ p += 2;
+ STORE_NUMBER_AND_INCR(p, mcnt);
+ PUSH_FAILURE_POINT(0, 0);
+ }
+ else if (mcnt == 0)
+ {
+ p[2] = unused;
+ p[3] = unused;
+ goto on_failure;
+ }
+ continue;
+
+ case jump_n:
+ EXTRACT_NUMBER(mcnt, p + 2);
+ /* Originally, this is how many times we CAN jump. */
+ if (mcnt)
+ {
+ mcnt--;
+ STORE_NUMBER(p + 2, mcnt);
+ goto nofinalize; /* Do the jump without taking off
+ any failure points. */
+ }
+ /* If don't have to jump any more, skip over the rest of command. */
+ else
+ p += 4;
+ continue;
+
+ case set_number_at:
+ {
+ register unsigned char *p1;
+
+ EXTRACT_NUMBER_AND_INCR(mcnt, p);
+ p1 = p + mcnt;
+ EXTRACT_NUMBER_AND_INCR(mcnt, p);
+ STORE_NUMBER(p1, mcnt);
+ continue;
+ }
+
+ case try_next:
+ EXTRACT_NUMBER_AND_INCR(mcnt, p);
+ if (p + mcnt < pend) {
+ PUSH_FAILURE_POINT(p, d);
+ stackp[-1] = (unsigned char*)1;
+ }
+ p += mcnt;
+ continue;
+
+ case finalize_push:
+ POP_FAILURE_POINT();
+ EXTRACT_NUMBER_AND_INCR(mcnt, p);
+ PUSH_FAILURE_POINT(p + mcnt, d);
+ stackp[-1] = (unsigned char*)1;
+ continue;
+
+ case finalize_push_n:
+ EXTRACT_NUMBER(mcnt, p + 2);
+ /* Originally, this is how many times we CAN jump. */
+ if (mcnt) {
+ mcnt--;
+ STORE_NUMBER(p + 2, mcnt);
+ POP_FAILURE_POINT();
+ EXTRACT_NUMBER_AND_INCR(mcnt, p);
+ PUSH_FAILURE_POINT(p + mcnt, d);
+ stackp[-1] = (unsigned char*)1;
+ p += 7; /* skip n and set_number_at after destination */
+ }
+ /* If don't have to push any more, skip over the rest of command. */
+ else
+ p += 4;
+ continue;
+
+ /* Ignore these. Used to ignore the n of succeed_n's which
+ currently have n == 0. */
+ case unused:
+ continue;
+
+ case wordbound:
+ if (AT_WORD_BOUNDARY(d))
+ break;
+ goto fail;
+
+ case notwordbound:
+ if (AT_WORD_BOUNDARY(d))
+ goto fail;
+ break;
+
+ case wordbeg:
+ if (IS_A_LETTER(d) && (AT_STRINGS_BEG(d) || !IS_A_LETTER(d - 1)))
+ break;
+ goto fail;
+
+ case wordend:
+ if (!AT_STRINGS_BEG(d) && IS_A_LETTER(d - 1)
+ && (!IS_A_LETTER(d) || AT_STRINGS_END(d)))
+ break;
+ goto fail;
+
+ case wordchar:
+ PREFETCH;
+ if (!IS_A_LETTER(d))
+ goto fail;
+ d++;
+ SET_REGS_MATCHED;
+ break;
+
+ case notwordchar:
+ PREFETCH;
+ if (IS_A_LETTER(d))
+ goto fail;
+ if (ismbchar(*d) && d + 1 != dend)
+ d++;
+ d++;
+ SET_REGS_MATCHED;
+ break;
+
+ case exactn:
+ /* Match the next few pattern characters exactly.
+ mcnt is how many characters to match. */
+ mcnt = *p++;
+ /* This is written out as an if-else so we don't waste time
+ testing `translate' inside the loop. */
+ if (translate)
+ {
+ do
+ {
+ unsigned char c;
+
+ PREFETCH;
+ c = *d++;
+ if (*p == 0xff) {
+ p++;
+ if (!--mcnt
+ || d == dend
+ || (unsigned char)*d++ != (unsigned char)*p++)
+ goto fail;
+ continue;
+ }
+ if (ismbchar(c)) {
+ if (c != (unsigned char)*p++
+ || !--mcnt /* redundant check if pattern was
+ compiled properly. */
+ || d == dend
+ || (unsigned char)*d++ != (unsigned char)*p++)
+ goto fail;
+ continue;
+ }
+ /* compiled code translation needed for ruby */
+ if ((unsigned char)translate[c]
+ != (unsigned char)translate[*p++])
+ goto fail;
+ }
+ while (--mcnt);
+ }
+ else
+ {
+ do
+ {
+ PREFETCH;
+ if (*p == 0xff) {p++; mcnt--;}
+ if (*d++ != *p++) goto fail;
+ }
+ while (--mcnt);
+ }
+ SET_REGS_MATCHED;
+ break;
+ }
+ if (stackp != stackb && (int)stackp[-1] == 1)
+ POP_FAILURE_POINT();
+ continue; /* Successfully executed one pattern command; keep going. */
+
+ /* Jump here if any matching operation fails. */
+ fail:
+ if (stackp != stackb)
+ /* A restart point is known. Restart there and pop it. */
+ {
+ short last_used_reg, this_reg;
+
+ /* If this failure point is from a dummy_failure_point, just
+ skip it. */
+ if (stackp[-3] == 0) {
+ POP_FAILURE_POINT();
+ goto fail;
+ }
+ stackp--; /* discard flag */
+ d = *--stackp;
+ p = *--stackp;
+ /* Restore register info. */
+ last_used_reg = (long) *--stackp;
+
+ /* Make the ones that weren't saved -1 or 0 again. */
+ for (this_reg = num_regs - 1; this_reg > last_used_reg; this_reg--)
+ {
+ regend[this_reg] = (unsigned char *)(-1L);
+ regstart[this_reg] = (unsigned char *)(-1L);
+ IS_ACTIVE(reg_info[this_reg]) = 0;
+ MATCHED_SOMETHING(reg_info[this_reg]) = 0;
+ }
+
+ /* And restore the rest from the stack. */
+ for ( ; this_reg > 0; this_reg--)
+ {
+ reg_info[this_reg] = *(struct register_info *) *--stackp;
+ regend[this_reg] = *--stackp;
+ regstart[this_reg] = *--stackp;
+ }
+ }
+ else
+ break; /* Matching at this starting point really fails. */
+ }
+
+ if (best_regs_set)
+ goto restore_best_regs;
+
+ FREE_AND_RETURN(stackb,(-1)); /* Failure to match. */
+}
+
+
+static int
+memcmp_translate(s1, s2, len, translate)
+ unsigned char *s1, *s2;
+ register int len;
+ unsigned char *translate;
+{
+ register unsigned char *p1 = s1, *p2 = s2, c;
+ while (len)
+ {
+ c = *p1++;
+ if (ismbchar(c)) {
+ if (c != *p2++ || !--len || *p1++ != *p2++)
+ return 1;
+ }
+ else
+ if (translate[c] != translate[*p2++])
+ return 1;
+ len--;
+ }
+ return 0;
+}
+
+void
+re_copy_registers(regs1, regs2)
+ struct re_registers *regs1, *regs2;
+{
+ int i;
+
+ if (regs1 == regs2) return;
+ if (regs1->allocated == 0) {
+ regs1->beg = TMALLOC(regs2->num_regs, int);
+ regs1->end = TMALLOC(regs2->num_regs, int);
+ regs1->allocated = regs2->num_regs;
+ }
+ else if (regs1->allocated < regs2->num_regs) {
+ TREALLOC(regs1->beg, regs2->num_regs, int);
+ TREALLOC(regs1->end, regs2->num_regs, int);
+ regs1->allocated = regs2->num_regs;
+ }
+ for (i=0; i<regs2->num_regs; i++) {
+ regs1->beg[i] = regs2->beg[i];
+ regs1->end[i] = regs2->end[i];
+ }
+ regs1->num_regs = regs2->num_regs;
+}
+
+void
+re_free_registers(regs)
+ struct re_registers *regs;
+{
+ if (regs->allocated == 0) return;
+ if (regs->beg) free(regs->beg);
+ if (regs->end) free(regs->end);
+}
diff --git a/ruby.1 b/ruby.1
index fe1e76007a..8a349eada6 100644
--- a/ruby.1
+++ b/ruby.1
@@ -272,7 +272,7 @@ example:
.ne 3
\& #! /usr/local/bin/ruby -s
\& # prints "true" if invoked with `-xyz' switch.
-\& print "true\n" if $xyz
+\& print "true\en" if $xyz
.fi
.TP
.B -S
diff --git a/ruby.c b/ruby.c
index 6e748f249d..43250e7c16 100644
--- a/ruby.c
+++ b/ruby.c
@@ -124,7 +124,7 @@ add_modules(mod)
}
void
-rb_require_modules()
+ruby_require_modules()
{
struct req_list *list = req_list;
struct req_list *tmp;
@@ -361,6 +361,7 @@ proc_options(argcp, argvp)
show_copyright();
}
+ Init_ext(); /* should be called here for some reason :-( */
if (script_given == FALSE) {
if (argc == 0) { /* no more args */
if (verbose == 3) exit(0);
diff --git a/ruby.h b/ruby.h
index ac53f620a9..d40456b01a 100644
--- a/ruby.h
+++ b/ruby.h
@@ -6,7 +6,7 @@
$Date$
created at: Thu Jun 10 14:26:32 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
*************************************************/
@@ -165,20 +165,23 @@ int num2int _((VALUE));
double num2dbl _((VALUE));
#define NUM2DBL(x) num2dbl((VALUE)(x))
+char *str2cstr _((VALUE));
+#define STR2CSTR(x) str2cstr((VALUE)(x))
+
VALUE rb_newobj _((void));
#define NEWOBJ(obj,type) type *obj = (type*)rb_newobj()
#define OBJSETUP(obj,c,t) {\
- RBASIC(obj)->class = (c);\
+ RBASIC(obj)->klass = (c);\
RBASIC(obj)->flags = (t);\
}
#define CLONESETUP(clone,obj) {\
- OBJSETUP(clone,singleton_class_clone(RBASIC(obj)->class),RBASIC(obj)->flags);\
- singleton_class_attached(RBASIC(clone)->class, (VALUE)clone);\
+ OBJSETUP(clone,singleton_class_clone(RBASIC(obj)->klass),RBASIC(obj)->flags);\
+ singleton_class_attached(RBASIC(clone)->klass, (VALUE)clone);\
}
struct RBasic {
UINT flags;
- VALUE class;
+ VALUE klass;
};
struct RObject {
@@ -240,14 +243,14 @@ struct RData {
#define DATA_PTR(dta) (RDATA(dta)->data)
VALUE data_object_alloc _((VALUE,void*,void (*)(),void (*)()));
-#define Data_Make_Struct(class,type,mark,free,sval) (\
+#define Data_Make_Struct(klass,type,mark,free,sval) (\
sval = ALLOC(type),\
memset(sval, 0, sizeof(type)),\
- data_object_alloc(class,sval,mark,free)\
+ data_object_alloc(klass,sval,mark,free)\
)
-#define Data_Wrap_Struct(class,mark,free,sval) (\
- data_object_alloc(class,sval,mark,free)\
+#define Data_Wrap_Struct(klass,mark,free,sval) (\
+ data_object_alloc(klass,sval,mark,free)\
)
#define Data_Get_Struct(obj,type,sval) {\
diff --git a/rubytest.rb b/rubytest.rb
index f0e4bf8c8e..4830c9a261 100644
--- a/rubytest.rb
+++ b/rubytest.rb
@@ -1,3 +1,4 @@
+#! ./miniruby
require 'rbconfig'
include Config
diff --git a/sample/fib.scm b/sample/fib.scm
index 8eba75bb9e..5c2b86e656 100644
--- a/sample/fib.scm
+++ b/sample/fib.scm
@@ -3,4 +3,6 @@
n
(+ (fib (- n 2)) (fib (- n 1)))))
-(fib 20)
+(display (fib 20))
+(newline)
+
diff --git a/sample/from.rb b/sample/from.rb
index d39bb70084..39aa4b7553 100644
--- a/sample/from.rb
+++ b/sample/from.rb
@@ -9,8 +9,6 @@ include Kconv
class String
- public :kconv
-
def kconv(code = Kconv::EUC)
Kconv.kconv(self, code, Kconv::AUTO)
end
@@ -35,10 +33,11 @@ if ARGV.length == 0
user = ENV['USER']
else
user = ARGV[0]
+ ARGV.clear
end
[ENV['SPOOLDIR'], '/usr/spool', '/var/spool', '/usr', '/var'].each do |m|
- break if File.exist? ARGV[0] = "#{m}/mail/#{user}"
+ break if File.exist? file = "#{m}/mail/#{user}"
end
$outcount = 0;
@@ -67,14 +66,19 @@ def fromout(date, from, subj)
$outcount += 1
end
-for file in ARGV
- next if !File.exist?(file)
+if File.exist?(file)
+ atime = File.atime(file)
+ mtime = File.mtime(file)
f = open(file, "r")
- while !f.eof?
- mail = Mail.new(f)
- fromout mail.header['Date'], mail.header['From'], mail.header['Subject']
+ begin
+ until f.eof?
+ mail = Mail.new(f)
+ fromout mail.header['Date'],mail.header['From'],mail.header['Subject']
+ end
+ ensure
+ f.close
+ File.utime(atime, mtime, file)
end
- f.close
end
if $outcount == 0
diff --git a/sample/io.rb b/sample/io.rb
deleted file mode 100644
index 0b38d2112d..0000000000
--- a/sample/io.rb
+++ /dev/null
@@ -1,44 +0,0 @@
-# IO test
-# usage: ruby io.rb file..
-
-home = ENV["HOME"]
-home.sub("m", "&&")
-print(home, "\n")
-print(home.reverse, "\n")
-
-if File.s("io.rb")
- print(File.s("io.rb"), ": io.rb\n")
-end
-
-$/="f\n"
-for i in "abc\n\ndef\nghi\n"
- print("tt: ", i)
-end
-
-printf("%s:(%d)%s\n", $0, ARGV.length, ARGV[0])
-passwd = open(ARGV[0], "r")
-#printf("%s", passwd.find{i|i =~ /\*/})
-
-n = 1
-for i in passwd #.grep(/^\*/)
- printf("%6d: %s", n, i)
- n = n + 1;
-end
-
-fp = open("|-", "r")
-
-if fp == nil
- for i in 1..5
- print(i, "\n")
- end
-else
- for line in fp
- print(line)
- end
-end
-
-def printUsage()
- if $USAGE
- apply($USAGE);
- end
-end
diff --git a/sample/rbc.rb b/sample/rbc.rb
index 88a5b2d069..7ab0edba12 100644
--- a/sample/rbc.rb
+++ b/sample/rbc.rb
@@ -11,29 +11,29 @@
#
# rbc.rb [options] file_name opts
# options:
-# -d デバッグモード(利用しない方が良いでしょう)
-# -m bcモード(分数, 行列の計算ができます)
-# -r load-module ruby -r と同じ
-# --inspect 結果出力にinspectを用いる(bcモード以外はデ
-# フォルト).
-# --noinspect 結果出力にinspectを用いない.
-# --noreadline readlineライブラリを利用しない(デフォルト
-# ではreadlineライブラリを利用しようとする).
+# -d debug mode(not encouraged)
+# -m bc mode(calculate rational, matrix)
+# -r load-module same as `ruby -r'
+# --inspect use inspect for output.
+# (default except in bc mode)
+# --noinspect do not use inspect for output.
+# --noreadline do not use readline library.
+# (rbc tries to use readline as default).
#
-# 追加 private method:
-# exit, quit 終了する.
-# inspect(sw = nil) インスペクトモードのトグル
-# trace_load(sw = nil) load/require時にrbcのfile読み込み機能を用
-# いるモードのスイッチ(デフォルトはトレース
-# モード)
+# additional private methods:
+# exit, quit quit
+# inspect(sw = nil) toggle inspect mode
+# trace_load(sw = nil) toggle trace mode for load/require.
+# (default is trace mode on)
#
require "e2mmap.rb"
$stdout.sync = TRUE
module BC_APPLICATION__
- RCS_ID='-$Header: /home/keiju/var/src/var.lib/ruby/ruby/RCS/rbc.rb,v 1.2 1997/11/27 13:46:06 keiju Exp keiju $-'
-
+
+ RCS_ID=%q$Id: rbc.rb,v 1.2 1997/11/27 13:46:06 keiju Exp keiju $
+
extend Exception2MessageMapper
def_exception :UnrecognizedSwitch, "Unrecognized switch: %s"
@@ -120,9 +120,9 @@ module BC_APPLICATION__
if line != "\n"
begin
if CONFIG[:INSPECT]
- print (cont._=eval(line, bind)).inspect, "\n"
+ print((cont._=eval(line, bind)).inspect, "\n")
else
- print (cont._=eval(line, bind)), "\n"
+ print((cont._=eval(line, bind)), "\n")
end
rescue
# $! = 'exception raised' unless $!
@@ -186,7 +186,7 @@ module BC_APPLICATION__
PARCENT_LTYPE = {
"q" => "\'",
- "Q" => "\"",
+ "Q" => "\"", #"
"x" => "\`",
"r" => "\/"
}
@@ -332,7 +332,7 @@ module BC_APPLICATION__
@lex_state = EXPR_BEG
end
end
- @OP.def_rule('$') do
+ @OP.def_rule('$') do #'
|op, rests|
identify_gvar(rests)
end
@@ -444,7 +444,7 @@ module BC_APPLICATION__
print token, "\n" if $DEBUG
if state = CLAUSE_STATE_TRANS[token]
if @lex_state != EXPR_BEG and token =~ /^(if|unless|while|until)/
- # 修飾子
+ # $B=$>~;R(B
else
if ENINDENT_CLAUSE.include?(token)
@indent += 1
@@ -472,7 +472,7 @@ module BC_APPLICATION__
if lt = PARCENT_LTYPE[ch]
ch = chrs.shift
else
- lt = "\""
+ lt = "\"" #"
end
if ch !~ /\W/
chrs.unshift ch
@@ -618,7 +618,7 @@ module BC_APPLICATION__
def_exception :ErrNodeAlreadyExists, "node already exists"
class Node
- # postprocがなければ抽象ノード, nilじゃなければ具象ノード
+ # postproc$B$,$J$1$l$PCj>]%N!<%I(B, nil$B$8$c$J$1$l$P6q>]%N!<%I(B
def initialize(preproc = nil, postproc = nil)
@Tree = {}
@preproc = preproc
diff --git a/sample/ruby-mode.el b/sample/ruby-mode.el
index 0f56477ea0..d31b2d196e 100644
--- a/sample/ruby-mode.el
+++ b/sample/ruby-mode.el
@@ -2,11 +2,16 @@
;;; ruby-mode.el -
;;;
;;; $Author$
-;;; Time-stamp: <97/03/21 01:16:05 matz>
+;;; $Date$
;;; created at: Fri Feb 4 14:49:13 JST 1994
;;;
-(defconst ruby-mode-version "1.0.7")
+(defconst ruby-mode-revision "$Revision$")
+
+(defconst ruby-mode-version
+ (progn
+ (string-match "[0-9.]+" ruby-mode-revision)
+ (substring ruby-mode-revision (match-beginning 0) (match-end 0))))
(defconst ruby-block-beg-re
"class\\|module\\|def\\|if\\|unless\\|case\\|while\\|until\\|for\\|begin\\|do"
@@ -79,7 +84,7 @@
(modify-syntax-entry ?\` "\"" ruby-mode-syntax-table)
(modify-syntax-entry ?# "<" ruby-mode-syntax-table)
(modify-syntax-entry ?\n ">" ruby-mode-syntax-table)
- (modify-syntax-entry ?\\ "'" ruby-mode-syntax-table)
+ (modify-syntax-entry ?\\ "\\" ruby-mode-syntax-table)
(modify-syntax-entry ?$ "/" ruby-mode-syntax-table)
(modify-syntax-entry ?? "_" ruby-mode-syntax-table)
(modify-syntax-entry ?_ "_" ruby-mode-syntax-table)
@@ -632,10 +637,10 @@ An end of a defun is found by moving forward from the beginning of one."
'("\\(^\\|[^_]\\)\\b\\([A-Z]+[a-zA-Z0-9_]*\\)"
2 font-lock-type-face)
;; functions
- '("^\\s *def[ \t]+.*$"
- 0 font-lock-function-name-face))
+ '("^\\s *def[ \t]+[^ \t(]*"
+ 0 font-lock-function-name-face t))
"*Additional expressions to highlight in ruby mode.")
- (if (and (>= (string-to-int emacs-version) 20)
+ (if (and (>= (string-to-int emacs-version) 19)
(not (featurep 'xemacs)))
(add-hook
'ruby-mode-hook
@@ -645,5 +650,4 @@ An end of a defun is found by moving forward from the beginning of one."
'((ruby-font-lock-keywords) nil nil ((?\_ . "w"))))))
(add-hook 'ruby-mode-hook
(lambda ()
- (setq font-lock-keywords ruby-font-lock-keywords)
- (font-lock-mode 1))))))
+ (setq font-lock-keywords ruby-font-lock-keywords))))))
diff --git a/sample/test.rb b/sample/test.rb
index 0a9d41c2ed..52e936af71 100644
--- a/sample/test.rb
+++ b/sample/test.rb
@@ -120,7 +120,7 @@ $bad = false
tmp = open("while_tmp", "r")
while tmp.gets()
if gsub!('vt100', 'VT100')
- gsub!('VT100', 'Vt100')
+ p gsub!('VT100', 'Vt100')
redo;
end
$bad = 1 if /vt100/;
diff --git a/sample/tkfrom.rb b/sample/tkfrom.rb
index b0ef8995ca..ba0e547799 100644
--- a/sample/tkfrom.rb
+++ b/sample/tkfrom.rb
@@ -94,25 +94,31 @@ root.bind "space", proc{exit}
$outcount = 0;
for file in ARGV
- next if !File.exist?(file)
+ next if File.exist?(file)
+ atime = File.atime(file)
+ mtime = File.mtime(file)
f = open(file, "r")
- while !f.eof
- mail = Mail.new(f)
- date = mail.header['Date']
- next if !date
- from = mail.header['From']
- subj = mail.header['Subject']
- y = m = d = 0
- y, m, d = parsedate(date) if date
- from = "sombody@somewhere" if ! from
- subj = "(nil)" if ! subj
- from = decode_b(from)
- subj = decode_b(subj)
- list.insert 'end', format('%-02d/%02d/%02d [%-28.28s] %s',y,m,d,from,subj)
- $outcount += 1
+ begin
+ until f.eof
+ mail = Mail.new(f)
+ date = mail.header['Date']
+ next unless date
+ from = mail.header['From']
+ subj = mail.header['Subject']
+ y = m = d = 0
+ y, m, d = parsedate(date) if date
+ from = "sombody@somewhere" unless from
+ subj = "(nil)" unless subj
+ from = decode_b(from)
+ subj = decode_b(subj)
+ list.insert 'end', format('%-02d/%02d/%02d [%-28.28s] %s',y,m,d,from,subj)
+ $outcount += 1
+ end
+ ensure
+ f.close
+ File.utime(atime, mtime, file)
+ list.see 'end'
end
- f.close
- list.see 'end'
end
limit = 10000
diff --git a/sprintf.c b/sprintf.c
index 7862a469e8..57ce682b5e 100644
--- a/sprintf.c
+++ b/sprintf.c
@@ -6,7 +6,7 @@
$Date$
created at: Fri Oct 15 10:39:26 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -327,7 +327,7 @@ f_sprintf(argc, argv)
bignum = 1;
break;
case T_STRING:
- val = str2inum(RSTRING(val)->ptr, 0);
+ val = str2inum(RSTRING(val)->ptr, 10);
goto bin_retry;
case T_BIGNUM:
bignum = 1;
@@ -339,10 +339,10 @@ f_sprintf(argc, argv)
if (*p == 'x') base = 16;
else if (*p == 'o') base = 8;
- else if (*p == 'u') base = 10;
+ else if (*p == 'u' || *p == 'd') base = 10;
else if (*p == 'b' || *p == 'B') base = 2;
if (!bignum) {
- if (*p == 'b' || *p == 'B') {
+ if (base == 2) {
val = int2big(v);
}
else {
diff --git a/st.c b/st.c
new file mode 100644
index 0000000000..6b25bc854b
--- /dev/null
+++ b/st.c
@@ -0,0 +1,435 @@
+/* This is a general purpose hash table package written by Peter Moore @ UCB. */
+
+static char sccsid[] = "@(#) st.c 5.1 89/12/14 Crucible";
+
+#include "config.h"
+#include <stdio.h>
+#include "st.h"
+
+#define ST_DEFAULT_MAX_DENSITY 5
+#define ST_DEFAULT_INIT_TABLE_SIZE 11
+
+ /*
+ * DEFAULT_MAX_DENSITY is the default for the largest we allow the
+ * average number of items per bin before increasing the number of
+ * bins
+ *
+ * DEFAULT_INIT_TABLE_SIZE is the default for the number of bins
+ * allocated initially
+ *
+ */
+static int numcmp();
+static int numhash();
+static struct st_hash_type type_numhash = {
+ numcmp,
+ numhash,
+};
+
+extern int strcmp();
+static int strhash();
+static struct st_hash_type type_strhash = {
+ strcmp,
+ strhash,
+};
+
+void *xmalloc();
+void *xcalloc();
+void *xrealloc();
+static void rehash();
+
+#define max(a,b) ((a) > (b) ? (a) : (b))
+#define nil(type) ((type*)0)
+#define alloc(type) (type*)xmalloc((unsigned)sizeof(type))
+#define Calloc(n,s) (char*)xcalloc((n),(s))
+
+#define EQUAL(table, x, y) ((*table->type->compare)(x, y) == 0)
+
+#define do_hash(key, table) (*(table)->type->hash)((key), (table)->num_bins)
+
+st_table*
+st_init_table_with_size(type, size)
+ struct st_hash_type *type;
+ int size;
+{
+ st_table *tbl;
+
+ if (size == 0) size = ST_DEFAULT_INIT_TABLE_SIZE;
+ else size /= ST_DEFAULT_MAX_DENSITY*0.87;
+
+ if (size < ST_DEFAULT_INIT_TABLE_SIZE)
+ size = ST_DEFAULT_INIT_TABLE_SIZE;
+
+ tbl = alloc(st_table);
+ tbl->type = type;
+ tbl->num_entries = 0;
+ tbl->num_bins = size;
+ tbl->bins = (st_table_entry **)Calloc(size, sizeof(st_table_entry*));
+ return tbl;
+}
+
+st_table*
+st_init_table(type)
+ struct st_hash_type *type;
+{
+ return st_init_table_with_size(type, 0);
+}
+
+st_table*
+st_init_numtable()
+{
+ return st_init_table(&type_numhash);
+}
+
+st_table*
+st_init_strtable()
+{
+ return st_init_table(&type_strhash);
+}
+
+void
+st_free_table(table)
+ st_table *table;
+{
+ register st_table_entry *ptr, *next;
+ int i;
+
+ for(i = 0; i < table->num_bins ; i++) {
+ ptr = table->bins[i];
+ while (ptr != nil(st_table_entry)) {
+ next = ptr->next;
+ free((char*)ptr);
+ ptr = next;
+ }
+ }
+ free((char*)table->bins);
+ free((char*)table);
+}
+
+#define PTR_NOT_EQUAL(table, ptr, key) \
+(ptr != nil(st_table_entry) && !EQUAL(table, key, (ptr)->key))
+
+#define FIND_ENTRY(table, ptr, hash_val) \
+ptr = (table)->bins[hash_val];\
+if (PTR_NOT_EQUAL(table, ptr, key)) {\
+ while (PTR_NOT_EQUAL(table, ptr->next, key)) {\
+ ptr = ptr->next;\
+ }\
+ ptr = ptr->next;\
+}
+
+int
+st_lookup(table, key, value)
+ st_table *table;
+ register char *key;
+ char **value;
+{
+ int hash_val;
+ register st_table_entry *ptr;
+
+ hash_val = do_hash(key, table);
+
+ FIND_ENTRY(table, ptr, hash_val);
+
+ if (ptr == nil(st_table_entry)) {
+ return 0;
+ } else {
+ if (value != nil(char*)) *value = ptr->record;
+ return 1;
+ }
+}
+
+#define ADD_DIRECT(table, key, value, hash_val, tbl)\
+{\
+ if (table->num_entries/table->num_bins > ST_DEFAULT_MAX_DENSITY) {\
+ rehash(table);\
+ hash_val = do_hash(key, table);\
+ }\
+ \
+ tbl = alloc(st_table_entry);\
+ \
+ tbl->key = key;\
+ tbl->record = value;\
+ tbl->next = table->bins[hash_val];\
+ table->bins[hash_val] = tbl;\
+ table->num_entries++;\
+}
+
+int
+st_insert(table, key, value)
+ register st_table *table;
+ register char *key;
+ char *value;
+{
+ int hash_val;
+ st_table_entry *tbl;
+ register st_table_entry *ptr;
+
+ hash_val = do_hash(key, table);
+
+ FIND_ENTRY(table, ptr, hash_val);
+
+ if (ptr == nil(st_table_entry)) {
+ ADD_DIRECT(table,key,value,hash_val,tbl);
+ return 0;
+ } else {
+ ptr->record = value;
+ return 1;
+ }
+}
+
+void
+st_add_direct(table, key, value)
+ st_table *table;
+ char *key;
+ char *value;
+{
+ int hash_val;
+ st_table_entry *tbl;
+
+ hash_val = do_hash(key, table);
+ ADD_DIRECT(table, key, value, hash_val, tbl);
+}
+
+int
+st_find_or_add(table, key, slot)
+ st_table *table;
+ char *key;
+ char ***slot;
+{
+ int hash_val;
+ st_table_entry *tbl, *ptr;
+
+ hash_val = do_hash(key, table);
+
+ FIND_ENTRY(table, ptr, hash_val);
+
+ if (ptr == nil(st_table_entry)) {
+ ADD_DIRECT(table, key, (char*)0, hash_val, tbl)
+ if (slot != nil(char**)) *slot = &tbl->record;
+ return 0;
+ } else {
+ if (slot != nil(char**)) *slot = &ptr->record;
+ return 1;
+ }
+}
+
+static void
+rehash(table)
+ register st_table *table;
+{
+ register st_table_entry *ptr, *next, **old_bins = table->bins;
+ int i, old_num_bins = table->num_bins, hash_val;
+
+ table->num_bins = 1.79*old_num_bins;
+
+ if (table->num_bins%2 == 0) {
+ table->num_bins += 1;
+ }
+
+ table->num_entries = 0;
+ table->bins = (st_table_entry **)
+ Calloc((unsigned)table->num_bins, sizeof(st_table_entry*));
+
+ for(i = 0; i < old_num_bins ; i++) {
+ ptr = old_bins[i];
+ while (ptr != nil(st_table_entry)) {
+ next = ptr->next;
+ hash_val = do_hash(ptr->key, table);
+ ptr->next = table->bins[hash_val];
+ table->bins[hash_val] = ptr;
+ table->num_entries++;
+ ptr = next;
+ }
+ }
+ free((char*)old_bins);
+}
+
+st_table*
+st_copy(old_table)
+ st_table *old_table;
+{
+ st_table *new_table;
+ st_table_entry *ptr, *tbl;
+ int i, num_bins = old_table->num_bins;
+
+ new_table = alloc(st_table);
+ if (new_table == nil(st_table)) {
+ return nil(st_table);
+ }
+
+ *new_table = *old_table;
+ new_table->bins = (st_table_entry**)
+ Calloc((unsigned)num_bins, sizeof(st_table_entry*));
+
+ if (new_table->bins == nil(st_table_entry*)) {
+ free((char*)new_table);
+ return nil(st_table);
+ }
+
+ for(i = 0; i < num_bins ; i++) {
+ new_table->bins[i] = nil(st_table_entry);
+ ptr = old_table->bins[i];
+ while (ptr != nil(st_table_entry)) {
+ tbl = alloc(st_table_entry);
+ if (tbl == nil(st_table_entry)) {
+ free((char*)new_table->bins);
+ free((char*)new_table);
+ return nil(st_table);
+ }
+ *tbl = *ptr;
+ tbl->next = new_table->bins[i];
+ new_table->bins[i] = tbl;
+ ptr = ptr->next;
+ }
+ }
+ return new_table;
+}
+
+int
+st_delete(table, key, value)
+ register st_table *table;
+ register char **key;
+ char **value;
+{
+ int hash_val;
+ st_table_entry *tmp;
+ register st_table_entry *ptr;
+
+ hash_val = do_hash(*key, table);
+
+ ptr = table->bins[hash_val];
+
+ if (ptr == nil(st_table_entry)) {
+ if (value != nil(char*)) *value = nil(char);
+ return 0;
+ }
+
+ if (EQUAL(table, *key, ptr->key)) {
+ table->bins[hash_val] = ptr->next;
+ table->num_entries--;
+ if (value != nil(char*)) *value = ptr->record;
+ *key = ptr->key;
+ free((char*)ptr);
+ return 1;
+ }
+
+ for(; ptr->next != nil(st_table_entry); ptr = ptr->next) {
+ if (EQUAL(table, ptr->next->key, *key)) {
+ tmp = ptr->next;
+ ptr->next = ptr->next->next;
+ table->num_entries--;
+ if (value != nil(char*)) *value = tmp->record;
+ *key = tmp->key;
+ free((char*)tmp);
+ return 1;
+ }
+ }
+
+ return 0;
+}
+
+int
+st_delete_safe(table, key, value, never)
+ register st_table *table;
+ register char **key;
+ char **value;
+ char *never;
+{
+ int hash_val;
+ register st_table_entry *ptr;
+
+ hash_val = do_hash(*key, table);
+
+ ptr = table->bins[hash_val];
+
+ if (ptr == nil(st_table_entry)) {
+ if (value != nil(char*)) *value = nil(char);
+ return 0;
+ }
+
+ if (EQUAL(table, *key, ptr->key)) {
+ table->num_entries--;
+ *key = ptr->key;
+ if (value != nil(char*)) *value = ptr->record;
+ ptr->key = ptr->record = never;
+ return 1;
+ }
+
+ for(; ptr->next != nil(st_table_entry); ptr = ptr->next) {
+ if (EQUAL(table, ptr->next->key, *key)) {
+ table->num_entries--;
+ *key = ptr->key;
+ if (value != nil(char*)) *value = ptr->record;
+ ptr->key = ptr->record = never;
+ return 1;
+ }
+ }
+
+ return 0;
+}
+
+void
+st_foreach(table, func, arg)
+ st_table *table;
+ enum st_retval (*func)();
+ char *arg;
+{
+ st_table_entry *ptr, *last, *tmp;
+ enum st_retval retval;
+ int i;
+
+ for(i = 0; i < table->num_bins; i++) {
+ last = nil(st_table_entry);
+ for(ptr = table->bins[i]; ptr != nil(st_table_entry);) {
+ retval = (*func)(ptr->key, ptr->record, arg);
+ switch (retval) {
+ case ST_CONTINUE:
+ last = ptr;
+ ptr = ptr->next;
+ break;
+ case ST_STOP:
+ return;
+ case ST_DELETE:
+ tmp = ptr;
+ if (last == nil(st_table_entry)) {
+ table->bins[i] = ptr->next;
+ } else {
+ last->next = ptr->next;
+ }
+ ptr = ptr->next;
+ free((char*)tmp);
+ table->num_entries--;
+ }
+ }
+ }
+}
+
+static int
+strhash(string, modulus)
+ register char *string;
+ int modulus;
+{
+ register int val = 0;
+ register int c;
+
+ while ((c = *string++) != '\0') {
+ val = val*997 + c;
+ }
+
+ return ((val < 0) ? -val : val)%modulus;
+}
+
+static int
+numcmp(x, y)
+ int x, y;
+{
+ return x != y;
+}
+
+static int
+numhash(n, modulus)
+ int n;
+ int modulus;
+{
+ return n % modulus;
+}
diff --git a/st.h b/st.h
new file mode 100644
index 0000000000..c27b110ce1
--- /dev/null
+++ b/st.h
@@ -0,0 +1,52 @@
+/* This is a general purpose hash table package written by Peter Moore @ UCB. */
+
+/* @(#) st.h 5.1 89/12/14 */
+
+#ifndef ST_INCLUDED
+
+#define ST_INCLUDED
+
+typedef struct st_table_entry st_table_entry;
+
+struct st_table_entry {
+ char *key;
+ char *record;
+ st_table_entry *next;
+};
+
+typedef struct st_table st_table;
+
+struct st_hash_type {
+ int (*compare)();
+ int (*hash)();
+};
+
+struct st_table {
+ struct st_hash_type *type;
+ int num_bins;
+ int num_entries;
+ st_table_entry **bins;
+};
+
+#define st_is_member(table,key) st_lookup(table,key,(char **) 0)
+
+enum st_retval {ST_CONTINUE, ST_STOP, ST_DELETE};
+
+st_table *st_init_table();
+st_table *st_init_table_with_size();
+st_table *st_init_numtable();
+st_table *st_init_strtable();
+int st_delete(), st_delete_safe(), st_insert();
+int st_lookup(), st_find_or_add();
+void st_foreach(), st_add_direct(), st_free_table();
+st_table *st_copy();
+
+#define ST_NUMCMP ((int (*)()) 0)
+#define ST_NUMHASH ((int (*)()) -2)
+
+#define st_numcmp ST_NUMCMP
+#define st_numhash ST_NUMHASH
+
+int st_strhash();
+
+#endif /* ST_INCLUDED */
diff --git a/string.c b/string.c
index 3c3d24f3cf..972da1bcdb 100644
--- a/string.c
+++ b/string.c
@@ -6,7 +6,7 @@
$Date$
created at: Mon Aug 9 17:12:58 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -100,6 +100,21 @@ str_new4(orig)
return (VALUE)str;
}
+static void
+str_assign(str, str2)
+ VALUE str, str2;
+{
+ if (NIL_P(str2) || str == str2) return;
+ if (!RSTRING(str)->orig && RSTRING(str)->ptr)
+ free(RSTRING(str)->ptr);
+ RSTRING(str)->ptr = RSTRING(str2)->ptr;
+ RSTRING(str)->len = RSTRING(str2)->len;
+ RSTRING(str)->orig = RSTRING(str2)->orig;
+ RSTRING(str2)->ptr = 0; /* abandon str2 */
+ RSTRING(str2)->len = 0;
+ if (str_tainted(str2)) str_taint(str);
+}
+
static ID pr_str;
VALUE
@@ -171,6 +186,15 @@ str_length(str)
return INT2FIX(RSTRING(str)->len);
}
+static VALUE
+str_empty(str)
+ VALUE str;
+{
+ if (RSTRING(str)->len == 0)
+ return TRUE;
+ return FALSE;
+}
+
VALUE
str_plus(str1, str2)
VALUE str1, str2;
@@ -185,7 +209,7 @@ str_plus(str1, str2)
if (str_tainted(str1) || str_tainted(str2))
return str_taint(str3);
- return (VALUE)str3;
+ return str3;
}
VALUE
@@ -208,7 +232,7 @@ str_times(str, times)
RSTRING(str2)->ptr[RSTRING(str2)->len] = '\0';
if (str_tainted(str)) {
- return str_taint((VALUE)str2);
+ return str_taint(str2);
}
return str2;
@@ -371,7 +395,7 @@ str_resize(str, len)
RSTRING(str)->len = len;
RSTRING(str)->ptr[len] = '\0'; /* sentinel */
}
- return (VALUE)str;
+ return str;
}
VALUE
@@ -696,6 +720,16 @@ str_succ(orig)
return str;
}
+static VALUE
+str_succ_bang(str)
+ VALUE str;
+{
+ str_modify(str);
+ str_assign(str, str_succ(str));
+
+ return str;
+}
+
VALUE
str_upto(beg, end)
VALUE beg, end;
@@ -735,7 +769,7 @@ str_aref(str, indx)
if (idx < 0 || RSTRING(str)->len <= idx) {
return Qnil;
}
- return (VALUE)INT2FIX(RSTRING(str)->ptr[idx] & 0xff);
+ return INT2FIX(RSTRING(str)->ptr[idx] & 0xff);
case T_REGEXP:
if (str_match(str, indx))
@@ -900,13 +934,10 @@ str_sub_f(str, pat, val, once)
str_modify(str);
result = str_sub_s(str, pat, val, once);
-
if (NIL_P(result)) return Qnil;
- str_resize(str, RSTRING(result)->len);
- memcpy(RSTRING(str)->ptr, RSTRING(result)->ptr, RSTRING(result)->len);
- if (str_tainted(result)) str_taint(str);
+ str_assign(str, result);
- return (VALUE)str;
+ return str;
}
static VALUE
@@ -981,12 +1012,10 @@ str_sub_iter_f(str, pat, once)
str_modify(str);
result = str_sub_iter_s(str, pat, once);
-
if (NIL_P(result)) return Qnil;
- str_resize(str, RSTRING(result)->len);
- memcpy(RSTRING(str)->ptr, RSTRING(result)->ptr, RSTRING(result)->len);
+ str_assign(str, result);
- return (VALUE)str;
+ return str;
}
static VALUE
@@ -1005,7 +1034,12 @@ str_aset(str, indx, val)
if (idx < 0 || RSTRING(str)->len <= idx) {
IndexError("index %d out of range [0..%d]", idx, RSTRING(str)->len-1);
}
- RSTRING(str)->ptr[idx] = FIX2INT(val) & 0xff;
+ if (TYPE(val) == T_STRING) {
+ str_replace(str, idx, 1, val);
+ }
+ else {
+ RSTRING(str)->ptr[idx] = NUM2INT(val) & 0xff;
+ }
return val;
case T_REGEXP:
@@ -1131,6 +1165,20 @@ str_gsub(argc, argv, str)
}
static VALUE
+str_replace_method(str, str2)
+ VALUE str, str2;
+{
+ Check_Type(str2, T_STRING);
+
+ str_modify(str);
+ str_resize(str, RSTRING(str2)->len);
+ memcpy(RSTRING(str)->ptr, RSTRING(str2)->ptr, RSTRING(str2)->len);
+ if (str_tainted(str2)) str_taint(str);
+
+ return str;
+}
+
+static VALUE
uscore_get()
{
VALUE line;
@@ -1227,7 +1275,7 @@ str_reverse_bang(str)
}
MEMCPY(RSTRING(str)->ptr, p, char, RSTRING(str)->len);
- return (VALUE)str;
+ return str;
}
static VALUE
@@ -1397,13 +1445,16 @@ str_upcase_bang(str)
str_modify(str);
s = RSTRING(str)->ptr; send = s + RSTRING(str)->len;
while (s < send) {
- if (islower(*s)) {
+ if (ismbchar(*s)) {
+ s++;
+ }
+ else if (islower(*s)) {
*s = toupper(*s);
}
s++;
}
- return (VALUE)str;
+ return str;
}
static VALUE
@@ -1422,13 +1473,16 @@ str_downcase_bang(str)
str_modify(str);
s = RSTRING(str)->ptr; send = s + RSTRING(str)->len;
while (s < send) {
- if (isupper(*s)) {
+ if (ismbchar(*s)) {
+ s++;
+ }
+ else if (isupper(*s)) {
*s = tolower(*s);
}
s++;
}
- return (VALUE)str;
+ return str;
}
static VALUE
@@ -1449,11 +1503,14 @@ str_capitalize_bang(str)
if (islower(*s))
*s = toupper(*s);
while (++s < send) {
- if (isupper(*s)) {
+ if (ismbchar(*s)) {
+ s++;
+ }
+ else if (isupper(*s)) {
*s = tolower(*s);
}
}
- return (VALUE)str;
+ return str;
}
static VALUE
@@ -1472,7 +1529,10 @@ str_swapcase_bang(str)
str_modify(str);
s = RSTRING(str)->ptr; send = s + RSTRING(str)->len;
while (s < send) {
- if (isupper(*s)) {
+ if (ismbchar(*s)) {
+ s++;
+ }
+ else if (isupper(*s)) {
*s = tolower(*s);
}
else if (islower(*s)) {
@@ -1481,7 +1541,7 @@ str_swapcase_bang(str)
s++;
}
- return (VALUE)str;
+ return str;
}
static VALUE
@@ -1611,7 +1671,7 @@ tr_trans(str, src, repl, sflag)
*t = '\0';
if (sflag) RSTRING(str)->len = (t - RSTRING(str)->ptr);
- return (VALUE)str;
+ return str;
}
static VALUE
@@ -1675,7 +1735,7 @@ str_delete_bang(str1, str2)
*t = '\0';
RSTRING(str1)->len = t - RSTRING(str1)->ptr;
- return (VALUE)str1;
+ return str1;
}
static VALUE
@@ -1718,7 +1778,7 @@ tr_squeeze(str1, str2)
*t = '\0';
RSTRING(str1)->len = t - RSTRING(str1)->ptr;
- return (VALUE)str1;
+ return str1;
}
static VALUE
@@ -2100,7 +2160,7 @@ str_strip_bang(str)
RSTRING(str)->ptr[RSTRING(str)->len] = '\0';
}
- return (VALUE)str;
+ return str;
}
static VALUE
@@ -2188,7 +2248,13 @@ static VALUE
str_oct(str)
VALUE str;
{
- return str2inum(RSTRING(str)->ptr, 8);
+ int base = 8;
+
+ if (RSTRING(str)->len > 2 && RSTRING(str)->ptr[0] == '0' &&
+ (RSTRING(str)->ptr[1] == 'x' || RSTRING(str)->ptr[1] == 'X')) {
+ base = 16;
+ }
+ return str2inum(RSTRING(str)->ptr, base);
}
static VALUE
@@ -2229,7 +2295,7 @@ str_sum(argc, argv, str)
else bits = NUM2INT(vbits);
p = RSTRING(str)->ptr; pend = p + RSTRING(str)->len;
- if (bits > 32) {
+ if (bits > sizeof(UINT)*CHAR_BIT) {
VALUE res = INT2FIX(0);
VALUE mod;
@@ -2238,20 +2304,23 @@ str_sum(argc, argv, str)
while (p < pend) {
res = rb_funcall(res, '+', 1, INT2FIX((UINT)*p));
- res = rb_funcall(res, '%', 1, mod);
p++;
}
+ res = rb_funcall(res, '&', 1, mod);
return res;
}
else {
UINT res = 0;
UINT mod = (1<<bits)-1;
+ if (mod == 0) {
+ mod = -1;
+ }
while (p < pend) {
res += (UINT)*p;
- res %= mod;
p++;
}
+ res &= mod;
return int2inum(res);
}
}
@@ -2265,7 +2334,7 @@ str_ljust(str, w)
VALUE res;
UCHAR *p, *pend;
- if (RSTRING(str)->len >= width) return (VALUE)str;
+ if (RSTRING(str)->len >= width) return str;
res = str_new(0, width);
memcpy(RSTRING(res)->ptr, RSTRING(str)->ptr, RSTRING(str)->len);
p = RSTRING(res)->ptr + RSTRING(str)->len; pend = RSTRING(res)->ptr + width;
@@ -2284,7 +2353,7 @@ str_rjust(str, w)
VALUE res;
UCHAR *p, *pend;
- if (RSTRING(str)->len >= width) return (VALUE)str;
+ if (RSTRING(str)->len >= width) return str;
res = str_new(0, width);
p = RSTRING(res)->ptr; pend = p + width - RSTRING(str)->len;
while (p < pend) {
@@ -2304,7 +2373,7 @@ str_center(str, w)
UCHAR *p, *pend;
int n;
- if (RSTRING(str)->len >= width) return (VALUE)str;
+ if (RSTRING(str)->len >= width) return str;
res = str_new(0, width);
n = (width - RSTRING(str)->len)/2;
p = RSTRING(res)->ptr; pend = p + n;
@@ -2345,12 +2414,15 @@ Init_String()
rb_define_method(cString, "[]=", str_aset_method, -1);
rb_define_method(cString, "length", str_length, 0);
rb_define_alias(cString, "size", "length");
+ rb_define_method(cString, "empty?", str_empty, 0);
rb_define_method(cString, "=~", str_match, 1);
rb_define_method(cString, "~", str_match2, 0);
rb_define_method(cString, "succ", str_succ, 0);
+ rb_define_method(cString, "succ!", str_succ_bang, 0);
rb_define_method(cString, "upto", str_upto, 1);
rb_define_method(cString, "index", str_index_method, -1);
rb_define_method(cString, "rindex", str_rindex, -1);
+ rb_define_method(cString, "replace", str_replace_method, 1);
rb_define_method(cString, "freeze", str_freeze, 0);
rb_define_method(cString, "frozen?", str_frozen_p, 0);
diff --git a/time.c b/time.c
index 1749c32319..4bbe4fbd4f 100644
--- a/time.c
+++ b/time.c
@@ -6,7 +6,7 @@
$Date$
created at: Tue Dec 28 14:31:59 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -201,7 +201,7 @@ time_arg(argc, argv, args)
}
/* value validation */
- if ( args[0] < 70|| args[1] > 137
+ if ( args[0] < 70|| args[0] > 137
|| args[1] < 0 || args[1] > 11
|| args[2] < 1 || args[2] > 31
|| args[3] < 0 || args[3] > 23
@@ -414,6 +414,23 @@ time_asctime(time)
VALUE time;
{
struct time_object *tobj;
+ char *s;
+
+ GetTimeval(time, tobj);
+ if (tobj->tm_got == 0) {
+ time_localtime(time);
+ }
+ s = asctime(&(tobj->tm));
+ if (s[24] == '\n') s[24] = '\0';
+
+ return str_new2(s);
+}
+
+static VALUE
+time_to_s(time)
+ VALUE time;
+{
+ struct time_object *tobj;
char buf[64];
int len;
@@ -774,8 +791,8 @@ Init_Time()
rb_define_method(cTime, "gmtime", time_gmtime, 0);
rb_define_method(cTime, "ctime", time_asctime, 0);
rb_define_method(cTime, "asctime", time_asctime, 0);
- rb_define_method(cTime, "to_s", time_asctime, 0);
- rb_define_method(cTime, "inspect", time_asctime, 0);
+ rb_define_method(cTime, "to_s", time_to_s, 0);
+ rb_define_method(cTime, "inspect", time_to_s, 0);
rb_define_method(cTime, "to_a", time_to_a, 0);
rb_define_method(cTime, "+", time_plus, 1);
diff --git a/util.c b/util.c
index 21e0a55639..527ce87d03 100644
--- a/util.c
+++ b/util.c
@@ -6,7 +6,7 @@
$Date$
created at: Fri Mar 10 17:22:34 JST 1995
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
diff --git a/util.h b/util.h
index 570d894ccb..78f8169fdb 100644
--- a/util.h
+++ b/util.h
@@ -6,7 +6,7 @@
$Date$
created at: Thu Mar 9 11:55:53 JST 1995
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
#ifndef UTIL_H
diff --git a/variable.c b/variable.c
index 0115b87d68..fa3a79516f 100644
--- a/variable.c
+++ b/variable.c
@@ -97,14 +97,14 @@ fc_i(key, value, res)
}
static VALUE
-find_class_path(cls)
- VALUE cls;
+find_class_path(klass)
+ VALUE klass;
{
struct fc_result arg;
arg.name = 0;
arg.path = 0;
- arg.klass = cls;
+ arg.klass = klass;
arg.track = cObject;
arg.prev = 0;
if (RCLASS(cObject)->iv_tbl) {
@@ -114,30 +114,24 @@ find_class_path(cls)
st_foreach(class_tbl, fc_i, &arg);
}
if (arg.name) {
- rb_iv_set(cls, "__classpath__", arg.path);
+ rb_iv_set(klass, "__classpath__", arg.path);
return arg.path;
}
return Qnil;
}
static VALUE
-classname(cls)
- VALUE cls;
+classname(klass)
+ VALUE klass;
{
VALUE path;
- while (TYPE(cls) == T_ICLASS || FL_TEST(cls, FL_SINGLETON)) {
- cls = (VALUE)RCLASS(cls)->super;
- }
- path = rb_iv_get(cls, "__classpath__");
- if (NIL_P(path)) {
- path = rb_iv_get(cls, "__classid__");
- if (!NIL_P(path)) {
- path = str_new2(rb_id2name(FIX2INT(path)));
- }
+ while (TYPE(klass) == T_ICLASS || FL_TEST(klass, FL_SINGLETON)) {
+ klass = (VALUE)RCLASS(klass)->super;
}
+ path = rb_iv_get(klass, "__classpath__");
if (NIL_P(path)) {
- path = find_class_path(cls);
+ path = find_class_path(klass);
if (NIL_P(path)) {
return 0;
}
@@ -153,30 +147,30 @@ mod_name(mod)
{
VALUE path = classname(mod);
- if (path) return path;
+ if (path) return str_dup(path);
return str_new(0,0);
}
VALUE
-rb_class_path(cls)
- VALUE cls;
+rb_class_path(klass)
+ VALUE klass;
{
- VALUE path = classname(cls);
+ VALUE path = classname(klass);
if (path) return path;
else {
char buf[256];
char *s = "Class";
- if (TYPE(cls) == T_MODULE) s = "Module";
- sprintf(buf, "#<%s 0x%x>", s, cls);
+ if (TYPE(klass) == T_MODULE) s = "Module";
+ sprintf(buf, "#<%s 0x%x>", s, klass);
return str_new2(buf);
}
}
void
-rb_set_class_path(cls, under, name)
- VALUE cls, under;
+rb_set_class_path(klass, under, name)
+ VALUE klass, under;
char *name;
{
VALUE str;
@@ -189,7 +183,7 @@ rb_set_class_path(cls, under, name)
str_cat(str, "::", 2);
str_cat(str, name, strlen(name));
}
- rb_iv_set(cls, "__classpath__", str);
+ rb_iv_set(klass, "__classpath__", str);
}
VALUE
@@ -203,18 +197,13 @@ rb_path2class(path)
}
void
-rb_name_class(cls, id)
- VALUE cls;
+rb_name_class(klass, id)
+ VALUE klass;
ID id;
{
extern VALUE cString;
- if (cString) {
- rb_iv_set(cls, "__classpath__", str_new2(rb_id2name(id)));
- }
- else {
- rb_iv_set(cls, "__classid__", INT2FIX(id));
- }
+ rb_iv_set(klass, "__classpath__", str_new2(rb_id2name(id)));
}
static st_table *autoload_tbl = 0;
@@ -235,17 +224,17 @@ rb_autoload_id(id, filename)
}
void
-rb_autoload(cls, filename)
- char *cls, *filename;
+rb_autoload(klass, filename)
+ char *klass, *filename;
{
- rb_autoload_id(rb_intern(cls), filename);
+ rb_autoload_id(rb_intern(klass), filename);
}
VALUE
-f_autoload(obj, cls, file)
- VALUE obj, cls, file;
+f_autoload(obj, klass, file)
+ VALUE obj, klass, file;
{
- ID id = rb_to_id(cls);
+ ID id = rb_to_id(klass);
Check_Type(file, T_STRING);
rb_autoload_id(id, RSTRING(file)->ptr);
@@ -253,10 +242,10 @@ f_autoload(obj, cls, file)
}
char *
-rb_class2name(cls)
- VALUE cls;
+rb_class2name(klass)
+ VALUE klass;
{
- return RSTRING(rb_class_path(cls))->ptr;
+ return RSTRING(rb_class_path(klass))->ptr;
}
struct trace_var {
@@ -817,41 +806,41 @@ obj_remove_instance_variable(obj, name)
}
VALUE
-rb_const_get_at(cls, id)
- VALUE cls;
+rb_const_get_at(klass, id)
+ VALUE klass;
ID id;
{
VALUE value;
- if (RCLASS(cls)->iv_tbl && st_lookup(RCLASS(cls)->iv_tbl, id, &value)) {
+ if (RCLASS(klass)->iv_tbl && st_lookup(RCLASS(klass)->iv_tbl, id, &value)) {
return value;
}
- if (cls == cObject) {
- return rb_const_get(cls, id);
+ if (klass == cObject) {
+ return rb_const_get(klass, id);
}
NameError("Uninitialized constant %s::%s",
- RSTRING(rb_class_path(cls))->ptr,
+ RSTRING(rb_class_path(klass))->ptr,
rb_id2name(id));
/* not reached */
}
VALUE
-rb_const_get(cls, id)
- VALUE cls;
+rb_const_get(klass, id)
+ VALUE klass;
ID id;
{
VALUE value;
VALUE tmp;
- tmp = cls;
+ tmp = klass;
while (tmp) {
if (RCLASS(tmp)->iv_tbl && st_lookup(RCLASS(tmp)->iv_tbl,id,&value)) {
return value;
}
tmp = RCLASS(tmp)->super;
}
- if (BUILTIN_TYPE(cls) == T_MODULE) {
+ if (BUILTIN_TYPE(klass) == T_MODULE) {
return rb_const_get(cObject, id);
}
@@ -867,13 +856,13 @@ rb_const_get(cls, id)
module = str_new2(modname);
free(modname);
f_require(0, module);
- return rb_const_get(cls, id);
+ return rb_const_get(klass, id);
}
/* Uninitialized constant */
- if (cls && cls != cObject)
+ if (klass && klass != cObject)
NameError("Uninitialized constant %s::%s",
- RSTRING(rb_class_path(cls))->ptr,
+ RSTRING(rb_class_path(klass))->ptr,
rb_id2name(id));
else {
NameError("Uninitialized constant %s",rb_id2name(id));
@@ -947,15 +936,15 @@ mod_const_of(mod, ary)
}
int
-rb_const_defined_at(cls, id)
- VALUE cls;
+rb_const_defined_at(klass, id)
+ VALUE klass;
ID id;
{
- if (RCLASS(cls)->iv_tbl && st_lookup(RCLASS(cls)->iv_tbl, id, 0)) {
+ if (RCLASS(klass)->iv_tbl && st_lookup(RCLASS(klass)->iv_tbl, id, 0)) {
return TRUE;
}
- if (cls == cObject) {
- return rb_const_defined(cls, id);
+ if (klass == cObject) {
+ return rb_const_defined(klass, id);
}
return FALSE;
}
@@ -970,15 +959,15 @@ rb_autoload_defined(id)
}
int
-rb_const_defined(cls, id)
- VALUE cls;
+rb_const_defined(klass, id)
+ VALUE klass;
ID id;
{
- while (cls) {
- if (RCLASS(cls)->iv_tbl && st_lookup(RCLASS(cls)->iv_tbl, id, 0)) {
+ while (klass) {
+ if (RCLASS(klass)->iv_tbl && st_lookup(RCLASS(klass)->iv_tbl, id, 0)) {
return TRUE;
}
- cls = RCLASS(cls)->super;
+ klass = RCLASS(klass)->super;
}
if (st_lookup(class_tbl, id, 0))
return TRUE;
@@ -986,24 +975,24 @@ rb_const_defined(cls, id)
}
void
-rb_const_set(cls, id, val)
- VALUE cls;
+rb_const_set(klass, id, val)
+ VALUE klass;
ID id;
VALUE val;
{
- if (!RCLASS(cls)->iv_tbl) {
- RCLASS(cls)->iv_tbl = new_idhash();
+ if (!RCLASS(klass)->iv_tbl) {
+ RCLASS(klass)->iv_tbl = new_idhash();
}
- else if (st_lookup(RCLASS(cls)->iv_tbl, id, 0)) {
+ else if (st_lookup(RCLASS(klass)->iv_tbl, id, 0)) {
NameError("already initialized constant %s", rb_id2name(id));
}
- st_insert(RCLASS(cls)->iv_tbl, id, val);
+ st_insert(RCLASS(klass)->iv_tbl, id, val);
}
void
-rb_define_const(cls, name, val)
- VALUE cls;
+rb_define_const(klass, name, val)
+ VALUE klass;
char *name;
VALUE val;
{
@@ -1011,7 +1000,7 @@ rb_define_const(cls, name, val)
if (!rb_is_const_id(id)) {
NameError("wrong constant name %s", name);
}
- rb_const_set(cls, id, val);
+ rb_const_set(klass, id, val);
}
void
diff --git a/version.c b/version.c
index 71f531c963..7f1832a4af 100644
--- a/version.c
+++ b/version.c
@@ -7,7 +7,7 @@
$Date$
created at: Thu Sep 30 20:08:01 JST 1993
- Copyright (C) 1993-1996 Yukihiro Matsumoto
+ Copyright (C) 1993-1998 Yukihiro Matsumoto
************************************************/
@@ -31,6 +31,6 @@ show_version()
void
show_copyright()
{
- fprintf(stderr, "ruby - Copyright (C) 1993-1997 Yukihiro Matsumoto\n");
+ fprintf(stderr, "ruby - Copyright (C) 1993-1998 Yukihiro Matsumoto\n");
exit(0);
}
diff --git a/version.h b/version.h
index b737876434..0c921244af 100644
--- a/version.h
+++ b/version.h
@@ -1,2 +1,2 @@
-#define RUBY_VERSION "1.1b5"
-#define VERSION_DATE "98/01/16"
+#define RUBY_VERSION "1.1b6"
+#define VERSION_DATE "98/01/23"
diff --git a/win32/sdbm.c b/win32/sdbm.c
index 0e4673bbb5..39fbb72d40 100644
--- a/win32/sdbm.c
+++ b/win32/sdbm.c
@@ -8,7 +8,7 @@
*/
#ifndef lint
-/*char sdbm_rcsid[] = "$Id: sdbm.c,v 1.16 90/12/13 13:01:31 oz Exp $";*/
+/*char sdbm_rcsid[] = "$Id: sdbm.c,v 1.1.1.1 1998/01/16 04:14:57 matz Exp $";*/
#endif
#include "sdbm.h"
@@ -634,7 +634,7 @@ register DBM *db;
*/
#ifndef lint
-/*char pair_rcsid[] = "$Id: pair.c,v 1.10 90/12/13 13:00:35 oz Exp $";*/
+/*char pair_rcsid[] = "$Id: sdbm.c,v 1.1.1.1 1998/01/16 04:14:57 matz Exp $";*/
#endif
#ifndef BSD42