diff options
-rw-r--r-- | ChangeLog | 17 | ||||
-rw-r--r-- | array.c | 3 | ||||
-rw-r--r-- | error.c | 31 | ||||
-rw-r--r-- | eval.c | 68 | ||||
-rw-r--r-- | ext/gtk/extconf.rb | 2 | ||||
-rw-r--r-- | lib/debug.rb | 7 | ||||
-rw-r--r-- | lib/delegate.rb | 2 | ||||
-rw-r--r-- | lib/tk.rb | 21 | ||||
-rw-r--r-- | object.c | 3 | ||||
-rw-r--r-- | parse.y | 3 | ||||
-rw-r--r-- | sample/from.rb | 13 | ||||
-rw-r--r-- | string.c | 7 | ||||
-rw-r--r-- | struct.c | 1 | ||||
-rw-r--r-- | time.c | 7 |
14 files changed, 137 insertions, 48 deletions
@@ -1,3 +1,20 @@ +Thu Apr 30 01:08:35 1998 Yukihiro Matsumoto <matz@netlab.co.jp> + + * lib/tk.rb: call 'unknown', if proc not defined. + + * eval.c (handle_rescue): default rescue handles `Exceptional' not + only the instance of the `Exception's. + + * eval.c (errinfo_setter): $! can be any `Throwable' object. + + * time.c (time_gm_or_local): call time_gmtime or time_localtime. + + * eval.c (f_raise): raises TypeError if the class which is not a + subclass of String is specified (checked in exc_new()). + + * error.c (exc_new): need to check whether invalid class (not a + subclass of String) is specified. + Tue Apr 28 15:27:58 1998 Yukihiro Matsumoto <matz@netlab.co.jp> * experimental release 1.1b9_16. @@ -640,7 +640,7 @@ ary_join(ary, sep) default: tmp = obj_as_string(tmp); } - if (!NIL_P(sep)) str_cat(result, RSTRING(sep)->ptr, RSTRING(sep)->len); + if (!NIL_P(sep)) str_concat(result, sep); str_cat(result, RSTRING(tmp)->ptr, RSTRING(tmp)->len); if (str_tainted(tmp)) str_taint(result); } @@ -658,7 +658,6 @@ ary_join_method(argc, argv, ary) rb_scan_args(argc, argv, "01", &sep); if (NIL_P(sep)) sep = OFS; - if (!NIL_P(sep)) Check_Type(sep, T_STRING); return ary_join(ary, sep); } @@ -212,6 +212,7 @@ rb_check_type(x, t) #include "errno.h" extern VALUE cString; +VALUE eThrowable, eExceptional; VALUE eGlobalExit, eException; VALUE eSystemExit, eInterrupt, eFatal; VALUE eRuntimeError; @@ -258,8 +259,11 @@ VALUE exc_new3(etype, str) VALUE etype, str; { - Check_Type(str, T_STRING); - return exc_new(etype, RSTRING(str)->ptr, RSTRING(str)->len); + char *s; + int len; + + s = str2cstr(str, &len); + return exc_new(etype, s, len); } static VALUE @@ -281,6 +285,23 @@ exc_s_new(argc, argv, etype) } static VALUE +exc_new_method(self, str) + VALUE self, str; +{ + VALUE etype; + char *s; + int len; + + if (self == str) return self; + etype = CLASS_OF(self); + while (FL_TEST(etype, FL_SINGLETON)) { + etype = RCLASS(etype)->super; + } + s = str2cstr(str, &len); + return exc_new(etype, s, len); +} + +static VALUE exc_inspect(exc) VALUE exc; { @@ -351,15 +372,21 @@ static void init_syserr(); void Init_Exception() { + eThrowable = rb_define_module("Throwable"); eGlobalExit = rb_define_class("GlobalExit", cString); + rb_include_module(eGlobalExit, eThrowable); rb_define_singleton_method(eGlobalExit, "new", exc_s_new, -1); + rb_define_method(eGlobalExit, "new", exc_new_method, 1); rb_define_method(eGlobalExit, "inspect", exc_inspect, 0); eSystemExit = rb_define_class("SystemExit", eGlobalExit); eFatal = rb_define_class("fatal", eGlobalExit); eInterrupt = rb_define_class("Interrupt", eGlobalExit); + eExceptional = rb_define_module("Exceptional"); + rb_include_module(eExceptional, eThrowable); eException = rb_define_class("Exception", eGlobalExit); + rb_include_module(eException, eExceptional); eSyntaxError = rb_define_class("SyntaxError", eException); eTypeError = rb_define_class("TypeError", eException); eArgError = rb_define_class("ArgumentError", eException); @@ -362,7 +362,8 @@ extern int nerrs; extern VALUE mKernel; extern VALUE cModule; extern VALUE eFatal; -extern VALUE eGlobalExit; +extern VALUE eThrowable; +extern VALUE eExceptional; extern VALUE eInterrupt; extern VALUE eSystemExit; extern VALUE eException; @@ -722,6 +723,7 @@ static void error_print() { VALUE eclass; + VALUE einfo; if (NIL_P(errinfo)) return; @@ -735,36 +737,37 @@ error_print() } eclass = CLASS_OF(errinfo); - if (eclass == eRuntimeError && RSTRING(errinfo)->len == 0) { + einfo = obj_as_string(errinfo); + if (eclass == eRuntimeError && RSTRING(einfo)->len == 0) { fprintf(stderr, ": unhandled exception\n"); } else { VALUE epath; epath = rb_class_path(eclass); - if (RSTRING(errinfo)->len == 0) { + if (RSTRING(einfo)->len == 0) { fprintf(stderr, ": "); fwrite(RSTRING(epath)->ptr, 1, RSTRING(epath)->len, stderr); putc('\n', stderr); } else { - unsigned char *tail = 0; - int len = RSTRING(errinfo)->len; + UCHAR *tail = 0; + int len = RSTRING(einfo)->len; if (RSTRING(epath)->ptr[0] == '#') epath = 0; - if (tail = strchr(RSTRING(errinfo)->ptr, '\n')) { - len = tail - RSTRING(errinfo)->ptr; + if (tail = strchr(RSTRING(einfo)->ptr, '\n')) { + len = tail - RSTRING(einfo)->ptr; tail++; /* skip newline */ } fprintf(stderr, ": "); - fwrite(RSTRING(errinfo)->ptr, 1, len, stderr); + fwrite(RSTRING(einfo)->ptr, 1, len, stderr); if (epath) { fprintf(stderr, " ("); fwrite(RSTRING(epath)->ptr, 1, RSTRING(epath)->len, stderr); fprintf(stderr, ")\n"); } if (tail) { - fwrite(tail, 1, RSTRING(errinfo)->len-len-1, stderr); + fwrite(tail, 1, RSTRING(einfo)->len-len-1, stderr); putc('\n', stderr); } } @@ -982,9 +985,10 @@ static void compile_error(at) char *at; { - VALUE mesg; + char *mesg; + int len; - mesg = errinfo; + mesg = str2cstr(errinfo, &len); nerrs = 0; errinfo = exc_new2(eSyntaxError, "compile error"); if (at) { @@ -992,7 +996,7 @@ compile_error(at) str_cat(errinfo, at, strlen(at)); } str_cat(errinfo, "\n", 1); - str_cat(errinfo, RSTRING(mesg)->ptr, RSTRING(mesg)->len); + str_cat(errinfo, mesg, len); rb_raise(errinfo); } @@ -1378,7 +1382,7 @@ is_defined(self, node, buf) case NODE_LVAR: return "local-variable"; case NODE_DVAR: - return "local-variable(ephemeral)"; + return "local-variable(in-block)"; case NODE_GVAR: if (rb_gvar_defined(node->nd_entry)) { @@ -2704,13 +2708,15 @@ rb_longjmp(tag, mesg, at) } if (!NIL_P(mesg)) { - if (obj_is_kind_of(mesg, eGlobalExit)) { + if (obj_is_kind_of(mesg, eThrowable)) { errinfo = mesg; } else { errinfo = exc_new3(eRuntimeError, mesg); } - str_freeze(errinfo); + if (TYPE(errinfo) == T_STRING) { + str_freeze(errinfo); + } } trap_restore_mask(); @@ -2759,7 +2765,7 @@ f_raise(argc, argv) case 2: case 3: etype = arg1; - if (obj_is_kind_of(etype, eGlobalExit)) { + if (obj_is_kind_of(etype, eThrowable)) { etype = CLASS_OF(etype); } else { @@ -2770,9 +2776,12 @@ f_raise(argc, argv) } if (!NIL_P(mesg)) { - Check_Type(mesg, T_STRING); - if (n == 2 || !obj_is_kind_of(mesg, eException)) { - mesg = exc_new3(etype, mesg); + if (n >= 2 || !obj_is_kind_of(mesg, eThrowable)) { + mesg = rb_funcall(etype, rb_intern("new"), 1, mesg); + } + if (!obj_is_kind_of(mesg, eThrowable)) { + TypeError("should be Throwable, %s given", + rb_class2name(CLASS_OF(mesg))); } } @@ -3042,7 +3051,7 @@ handle_rescue(self, node) TMP_PROTECT; if (!node->nd_args) { - return obj_is_kind_of(errinfo, eException); + return obj_is_kind_of(errinfo, eExceptional); } PUSH_ITER(ITER_NOT); @@ -3071,7 +3080,7 @@ rb_rescue(b_proc, data1, r_proc, data2) retry_entry: result = (*b_proc)(data1); } - else if (state == TAG_RAISE && obj_is_kind_of(errinfo, eException)) { + else if (state == TAG_RAISE && obj_is_kind_of(errinfo, eExceptional)) { if (r_proc) { PUSH_TAG(PROT_NONE); if ((state = EXEC_TAG()) == 0) { @@ -3838,7 +3847,7 @@ eval(self, src, scope, file, line) if (sourceline > 1) { err = RARRAY(errat)->ptr[0]; str_cat(err, ": ", 2); - str_cat(err, RSTRING(errinfo)->ptr, RSTRING(errinfo)->len); + str_concat(err, errinfo); } else { err = str_dup(errinfo); @@ -4488,6 +4497,19 @@ errat_setter(val, id, var) *var = check_errat(val); } +static void +errinfo_setter(val, id, var) + VALUE val; + ID id; + VALUE *var; +{ + if (!obj_is_kind_of(val, eThrowable)) { + TypeError("$! should be Throwable, %s given", + rb_class2name(CLASS_OF(val))); + } + *var = val; +} + VALUE f_global_variables(); VALUE f_instance_variables(); @@ -4595,7 +4617,7 @@ Init_eval() rb_global_variable((VALUE*)&the_dyna_vars); rb_define_hooked_variable("$@", &errat, 0, errat_setter); - rb_define_hooked_variable("$!", &errinfo, 0, rb_str_setter); + rb_define_hooked_variable("$!", &errinfo, 0, errinfo_setter); rb_define_global_function("eval", f_eval, -1); rb_define_global_function("iterator?", f_iterator_p, 0); diff --git a/ext/gtk/extconf.rb b/ext/gtk/extconf.rb index a30f050e66..5839fac1ce 100644 --- a/ext/gtk/extconf.rb +++ b/ext/gtk/extconf.rb @@ -2,7 +2,7 @@ require "mkmf" # may need to be changed $LDFLAGS="-L/usr/X11R6/lib -L/usr/local/lib" -$CFLAGS=`gtk-config --cflags` +$CFLAGS=`gtk-config --cflags`.chomp! have_library("X11", "XOpenDisplay") have_library("Xext", "XShmQueryVersion") diff --git a/lib/debug.rb b/lib/debug.rb index 432c7b4d19..2e3a29aa9e 100644 --- a/lib/debug.rb +++ b/lib/debug.rb @@ -11,6 +11,8 @@ class DEBUGGER__ @scripts = {} end + DEBUG_LAST_CMD = [] + def interrupt @stop_next = 1 end @@ -40,6 +42,11 @@ class DEBUGGER__ STDOUT.flush while input = STDIN.gets input.chop! + if input == "" + input = DEBUG_LAST_CMD[0] + else + DEBUG_LAST_CMD[0] = input + end case input when /^b(reak)?\s+(([^:\n]+:)?.+)/ pos = $2 diff --git a/lib/delegate.rb b/lib/delegate.rb index c73a3bd8a0..bc6f876212 100644 --- a/lib/delegate.rb +++ b/lib/delegate.rb @@ -7,7 +7,7 @@ # # Usage: # foo = Object.new -# foo = SimpleDelegator.new(foo) +# foo2 = SimpleDelegator.new(foo) # foo.hash == foo2.hash # => true class Delegator @@ -113,7 +113,6 @@ module TkComm end end def list(val) - p val tk_split_list(val).to_a end def window(val) @@ -274,7 +273,7 @@ module TkCore end def _get_eval_string(str) - return str if str == None + return nil if str == None if str.kind_of?(Hash) str = hash_kv(str).join(" ") elsif str == nil @@ -294,10 +293,20 @@ module TkCore def tk_call(*args) print args.join(" "), "\n" if $DEBUG args.filter {|x|_get_eval_string(x)} - args.delete!(None) - args.flatten! args.compact! - res = INTERP._invoke(*args) + args.flatten! + begin + res = INTERP._invoke(*args) + rescue NameError + err = $! + begin + args.unshift "unknown" + res = INTERP._invoke(*args) + rescue + raise unless /^invalid command/ =~ $! + raise err + end + end if INTERP._return_value() != 0 fail RuntimeError, res, error_at end @@ -819,8 +828,6 @@ class TkObject<TkKernel if (args.length == 1) configure id.id2name, args[0] else - p caller - p id.id2name $@ = error_at super end @@ -526,7 +526,8 @@ mod_cmp(mod, arg) return INT2FIX(1); } -VALUE module_s_new() +VALUE +module_s_new() { VALUE mod = module_new(); @@ -2366,8 +2366,7 @@ retry: case '<': c = nextc(); if (c == '<' && - lex_state != EXPR_END - && lex_state != EXPR_CLASS && + lex_state != EXPR_END && lex_state != EXPR_CLASS && (lex_state != EXPR_ARG || space_seen)) { int c2 = nextc(); if (!isspace(c2) && (strchr("\"'`", c2) || is_identchar(c2))) { diff --git a/sample/from.rb b/sample/from.rb index 0a83f081f1..98fc54799d 100644 --- a/sample/from.rb +++ b/sample/from.rb @@ -30,16 +30,19 @@ if ARGV[0] == '-w' end if ARGV.length == 0 - user = ENV['USER'] + file = ENV['MAIL'] + user = ENV['USER'] || ENV['USERNAME'] || ENV['LOGNAME'] else file = user = ARGV[0] ARGV.clear end -[ENV['SPOOLDIR'], '/usr/spool', '/var/spool', '/usr', '/var'].each do |m| - if File.exist? f = "#{m}/mail/#{user}" - file = f - break +if file == nil or !File.exist? file + [ENV['SPOOLDIR'], '/usr/spool', '/var/spool', '/usr', '/var'].each do |m| + if File.exist? f = "#{m}/mail/#{user}" + file = f + break + end end end @@ -171,7 +171,10 @@ VALUE str_dup(str) VALUE str; { - VALUE s = str_new(RSTRING(str)->ptr, RSTRING(str)->len); + VALUE s; + + str = to_str(str); + s = str_new(RSTRING(str)->ptr, RSTRING(str)->len); if (str_tainted(str)) s = str_taint(s); if (RSTRING(str)->orig && FL_TEST(str, STR_NO_ORIG)) RSTRING(s)->orig = RSTRING(str)->orig; @@ -442,7 +445,7 @@ str_cat(str, ptr, len) return str; } -static VALUE +VALUE str_concat(str1, str2) VALUE str1, str2; { @@ -310,7 +310,6 @@ struct_inspect(s) str_cat(str, p, strlen(p)); str_cat(str, "=", 1); str2 = rb_inspect(RSTRUCT(s)->ptr[i]); - str2 = obj_as_string(str2); str_cat(str, RSTRING(str2)->ptr, RSTRING(str2)->len); } str_cat(str, ">", 1); @@ -232,6 +232,8 @@ time_arg(argc, argv, args) ArgError("argument out of range"); } +static VALUE time_gmtime _((VALUE)); +static VALUE time_localtime _((VALUE)); static VALUE time_gm_or_local(argc, argv, gm_or_local, klass) int argc; @@ -245,6 +247,7 @@ time_gm_or_local(argc, argv, gm_or_local, klass) time_t guess, t; int diff; struct tm *(*fn)(); + VALUE time; fn = (gm_or_local) ? gmtime : localtime; time_arg(argc, argv, args); @@ -272,7 +275,9 @@ time_gm_or_local(argc, argv, gm_or_local, klass) guess += (args[4] - tm->tm_min) * 60; guess += args[5] - tm->tm_sec; - return time_new_internal(klass, guess, 0); + time = time_new_internal(klass, guess, 0); + if (gm_or_local) return time_gmtime(time); + return time_localtime(time); error: ArgError("gmtime/localtime error"); |