with same name but non-LFS function on MinGW. [ruby-core:24757]
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@27300 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
defined EWOULDBLOCK. based on a patch from Charlie Savage,
see [ruby-core:29255]
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@27222 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
* missing.h (struct timezone): define if not defined.
* win32/win32.h (struct timezone): defined in the newer w32api.
[ruby-core:27515]
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@26311 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
* defs/dtrace.d: new file. defined a dtrace provider "ruby".
* include/ruby/ruby.h (LIKELY): moved from vm.c.
(UNLIKELY): ditto.
(OBJSETUP): probe "object-create".
(RUBY_EVENT_RESCUE): new event.
* vm_exec.c (DEBUG_ENTER_INSN): embeded a probe insn-entry into it.
(DEBUG_END_INSN): insn-return.
* vm.c (LIKELY): moved into ruby.h.
(UNLIKELY): ditto.
(Init_BareVM): embeded a probe "raise" into it.
* variable.c (rb_class2name_without_alloc): new utility function.
* tool/rbinstall.rb (install?(:ext, :arch, :'ext-arch')): installs
dtrace.d if necessary.
* thread_pthread.c (add_signal_thread_list): probe "raise".
(rb_thread_create_timer_thread): ditto.
* thread.c (rb_thread_schedule_rec): probes "thread-enter" and
"thread-leave",
(thread_start_func_2): ditto.
(thread_cleanup_func): probe "thread-term"
* lib/mkmf.rb: supports dtrace postprocessor on making an extension.
* iseq.c (rb_vm_insn_name): new utility function.
(rb_vm_insn_len): ditto.
* insns.def (hook): probes "method-etnry", "method-return", "line",
and "rescue".
* compile.c (iseq_compile_each): adds a trace op for "rescue" probe.
* gc.c (garbage_collect): probes "gc-begin" and "gc-end".
(obj_free): probe "object-free"
(garbage_collect_with_gvl): probe "raise"
(negative_size_allocation_error): ditto.
(rb_memerror): ditto.
* eval.c (rb_rescue2): probe "rescue"
(rb_longjmp): probe "raise"
* ext/probe/probe.c: new extension for application defined probes.
* ext/probe/extconf.rb: ditto.
* configure.in (--with-tracing-model): new option to choose a tracing
mechanism.
(DTRACE): new substitution. name of dtrace(1).
(RUBY_TRACING_MODEL): new substitution.
(DTRACE_OBJ): ditto.
(MINIDTRACE_OBJ): ditto.
(GOLFDTRACE_OBJ): ditto.
(LIBRUBY_DTRACE_OBJ): ditto.
(RUBY_DTRACE_POSTPROCESS): new macro. checks whether the dtrace on
the system needs postprocessing.
(RUBY_DTRACE_BSD_BROKEN): new macro. checks whether the dtrace
supports USDT.
* Makefile.in:
(DTRACE): new variable. name of dtrace(1).
(TRACING_MODEL): new variable. name of the chosen tracing mechanism.
(DTRACE_OBJ): same as the one in configure.in.
(MINIDTRACE_OBJ): ditto.
(GOLFDTRACE_OBJ): ditto.
(LIBRUBY_DTRACE_OBJ): ditto.
(CPPOUTFILE): new substitution. necessary for generating dtrace.d
(trace_none.h): new target for TRACING_MODEL=none
(RUBY_H_INCLUDES): appended a header for tracing.
(distclean-local): also removes preprocessed version of dtrace.d
($(LIBRUBY_A)): needs $(LIBRUBY_DTRACE_OBJ) if dtrace needs
postprocessing.
($(PROGRAM)): ditto.
(golf): ditto.
(miniruby): ditto.
($(arch_hdrdir)/ruby/dtrace.d): new target. preprocessed verson
of defs/dtrace.d. generated if necessary.
($(arch_hdrdir)/ruby/trace_dtrace.h): new target.
definition of probes.
($(LIBRUBY_DTRACE_OBJ)): new target. generated if dtrace needs
postprocessing.
($(DTRACE_OBJ)): ditto.
($(MINIDTRACE_OBJ)): ditto.
($(GOLFDTRACE_OBJ)): ditto.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@26235 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
* template/known_errors.inc.tmpl: generate defined_error() and
undefined_error() instead of set_syserr.
* error.c (Init_syserr): define defined_error() and undefined_error()
to follow the above change.
(rb_strerrno): defined.
* thread_pthread.c: show error message and errno macro name with
rb_bug.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@25893 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
to_ary. Just call. [ruby-core:23738]
* eval.c (rb_check_funcall): new function with method existence
check. returns Qundef when the method does not exist.
* enumerator.c (enumerator_rewind): just call method, using
rb_check_funcall(). [ruby-core:23738]
* error.c (exc_equal): ditto.
* object.c (convert_type): ditto.
* error.c (rb_name_err_mesg_new): export function.
* eval.c (make_exception): ditto.
* io.c (pop_last_hash): return early when the last argument is nil.
* io.c (rb_io_puts): treat T_STRING specially for small
optimization.
* vm_eval.c (raise_method_missing): skip method call if possible
using rb_method_basic_definition_p().
* vm_eval.c (method_missing): ditto.
* test/ruby/test_rubyoptions.rb (TestRubyOptions#test_debug): test
suites changed to ignore exceptions caused by just-call policy.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@25556 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
rb_read_check. This makes other threads runnable in getstr and
wgetstr.
(getch_func): extracted from curses_getch.
(curses_getch): use rb_thread_blocking_region with getch_func.
(getstr_func): extracted from curses_getstr.
(curses_getstr): use rb_thread_blocking_region with getstr_func.
(wgetch_func): extracted from window_getch.
(window_getch): use rb_thread_blocking_region with wgetch_func.
(wgetstr_func): extracted from window_getstr.
(window_getstr): use rb_thread_blocking_region with wgetstr_func.
* include/ruby/io.h (rb_read_check): deprecated because it access
internal of stdio.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@25286 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
split compiler specification and runtime library specification.
* win32/Makefile.sub (LD_SHARED*, config.status): no need to embbed
manifest if not exist.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@25173 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Returns 1 when the encoding is Unicode series
other than UTF-7 else 0.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@25142 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
instead of rb_str_new2.
ENV['PATH'].encoding should be Filesystem Encoding
because its content is related to filesystem.
see [ruby-dev:39393]
* hash.c (env_fetch): ditto.
* string.c (rb_filesystem_str_new): defined.
* string.c (rb_filesystem_str_new_cstr): ditto.
* include/ruby/intern.h (rb_filesystem_str_new): added.
* include/ruby/intern.h (rb_filesystem_str_new_cstr): ditto.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@25139 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
* eval.c (ruby_cleanup): destruct current VM before exit.
* gc.c (rb_objspace_free): free object space.
* vm.c (ruby_vm_destruct): destruct and free VM struct.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@25000 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
* test/ruby/test_thread.rb (test_recursive_outer): Test for above
* hash.c (rb_hash_hash): Return a sensible hash for in case of recursion [ruby-core:24648]
* range.c (rb_range_hash): ditto
* struct.c (rb_struct_hash): ditto
* array.c (rb_array_hash): ditto
* test/ruby/test_array.rb (test_hash2): test for above
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@24943 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
(LONG2NUM, ULONG2NUM, NUM2CHR): get rid of backward references of
macros. the code couldn't compile by VC.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@24917 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
And add a member variable "data", a multi-purpose storage
area for rb_data_type.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@24835 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
new functions to define a nested class/module with non-ascii
name.
* struct.c (make_struct): use name with encoding.
* struct.c (inspect_struct): ditto. [ruby-core:24849]
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@24513 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
deal with non-ascii class path. [ruby-core:24790]
* marshal.c (r_unique, path2class, path2module, obj_alloc_by_path),
(r_object0): ditto.
* variable.c (rb_path_to_class): new encoding-aware function to
get a class from its name.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@24488 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
names. [ruby-core:24600]
* variable.c (rb_set_class_path_string): set class path with a
string value.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@24321 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
sendmsg like UNIX. these functions are experimental and not tested
well. bug reports are welcome.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@24218 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
method management. This change affect some VM control stack structure.
* vm.c, vm_insnhelper.c, vm_method.c, vm_eval.c: ditto. and make some
refactoring.
* insns.def, class.c, eval.c, proc.c, vm_dump.c : ditto.
* vm_core.h, compile.c (iseq_specialized_instruction): remove
VM_CALL_SEND_BIT. use another optimization tech for Kernel#send.
* node.h: remove unused node types.
* ext/objspace/objspace.c (count_nodes): ditto.
* gc.c: add mark/free functions for method entry.
* include/ruby/intern.h: remove decl of
rb_define_notimplement_method_id(). nobody can use it
because noex is not opend.
* iseq.c (iseq_mark): fix to check ic_method is available.
* iseq.c (rb_iseq_disasm): fix to use rb_method_get_iseq().
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@24128 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
* include/ruby/io.h (FMODE_STRIP_BOM): new constant.
* io.c (io_encname_bom_p): judge whether the encoding name
is *-bom or not.
(parse_mode_enc): drop "-bom".
(rb_io_modestr_fmode): set FMODE_STRIP_BOM if needed.
(rb_io_extract_modeenc): ditto.
(io_strip_bom): strip bom if exists.
(io_set_encoding_by_bom): set encoding if there is bom.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@24001 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
paths with tilde twice.
* load.c (rb_f_load): load the given path directly if not found in
load_path.
* load.c (search_required): search file in specified safe level.
* load.c (rb_require_safe): path to load is already searched in
search_required().
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@23828 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This structure incldues more explicit type information for
T_DATA objects. If RData(obj)->dfree is immediate value `1' on
T_DATA object obj, obj is needed to be accessed with RTYPEDDATA(obj)
instead of RDATA(obj). A RTypedData structure points the structure
rb_typed_data_t. rb_typed_data_t includes information such as the
type name of this data, mark and free function what RData includes,
and memsize function show how data consuming the memory size.
Note that you do not need any change existing T_DATA objects.
If you use RDataType instead of RData on T_DATA object,
you can specify explicit type information.
* gc.c (rb_data_typed_object_alloc, rb_objspace_data_type_memsize,
rb_objspace_data_type_name): added.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@23710 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
"rb_thread_t *", the prefix to be rb_threadptr_ instead of
rb_thread_.
* thread.c (rb_thread_add_event_hook(), rb_thread_remove_event_hook):
change the parameter type from rb_thread_t * to VALUE.
* eval.c, eval_error.c, eval_intern.h, signal.c, vm_core.h, vm_eval.c:
ditto.
* include/ruby/intern.h: remove decl of rb_thread_signal_raise() and
rb_thread_signal_exit().
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@23651 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
e.g. copy.
* hash.c (rb_hash_aset): use st_insert2() to reduce redundant
st_lookup calls.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@23594 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
to be valid.
* string.c (enc_strlen): coderange specified version of
rb_enc_strlen(). use rb_enc_fast_mbclen() if coderange is 7bit
or valid.
* string.c (str_gsub): use rb_enc_fast_mbclen().
* string.c (rb_str_reverse, rb_str_split_m, rb_str_each_char,
scan_once): ditto.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@23495 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
* include/ruby/encoding.h (rb_enc_nth): long is used for index.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@23358 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
if rb_f_notimplement is given.
(rb_define_protected_method): ditto.
(rb_define_private_method): ditto.
(rb_define_method): use rb_define_method_id.
* include/ruby/intern.h (rb_f_notimplement): declared.
(rb_define_notimplement_method_id): declared.
* proc.c (method_inspect): show not-implemented.
* vm_method.c (notimplement_body): new variable.
(rb_notimplement_body_p): new function.
(rb_method_boundp): return false if not implemented.
(rb_f_notimplement): new function.
(rb_define_notimplement_method_id): new function.
* process.c (rb_f_fork): use rb_f_notimplement if not implemented.
* file.c (rb_file_s_lchmod): use rb_f_notimplement if not implemented.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@23192 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
using rb_fdset_t.
* io.c (select_internal): use rb_thread_fd_select instead of
rb_thread_select. based on the patch from Kengo Matsuyama.
[ruby-dev:38221]
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@23109 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
* include/ruby/ruby.h (NUM2INT, rb_special_const_p): returns true
and false instead of Qtrue and Qfalse for platforms where VALUE
is bigger than int.
* gc.c (gc_stress_set), ext/openssl/ossl_asn1.c (decode_bool): got
rid of variables named `bool'.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@22922 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
is not defined already.
* include/ruby/encoding.h (ENC_FROM_ENCINDEX): removed because
depending on a static variable.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@22773 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
* win32/Makefile.sub (config.h): defines WIN95 only if unicows.lib
is available.
* win32/setup.mak (-unicows-): checks if unicows.lib is available.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@22763 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
#singleton_methods and so on return Symbols. [ruby-talk:328775]
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@22566 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
a loop to fix iteration miss when hash is modified during iteration.
[ruby-dev:37910]
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@22132 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
(rb_thread_blocking_region_end): marked as deprecated.
* include/ruby/backward/rubysig.h (TRAP_BEG): fix for C++. a
patch from Aman Gupta at [ruby-core:21934]
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@22130 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
universal binary. replaced --enable-fat-binary option which
didn't work actually.
* configure.in (RUBY_FUNC_ATTRIBUTE): added conditional test.
* configure.in (ac_cv_type_getgroups): decalared because getgroups()
fills rest of the buffer with garbages on Rosetta.
* configure.in (alloca): defines only for powerpc, but always
create empty object to suppress ld warning.
* configure.in (LIBRUBY_DLDFLAGS): set compatibility version with
TEENY.
* configure.in (CFLAGS, LDFLAGS): separates ARCH_FLAG.
* configure.in (arch): renamed to "universal" from "fat".
* Makefile.in (ARCH_FLAG): added.
* include/ruby/defines.h (WORDS_BIGENDIAN): uses
AC_APPLE_UNIVERSAL_BUILD.
* missing/alloca.c (alloca): defines only if C_ALLOCA is defined.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@22106 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
instead of uintptr_t, since many %lx and so on are still used.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@21605 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
if not, cause compile error in using PRI?VALUE.
* win32/Makefile.sub (config.h): add SIZEOF_INTPTR_T and
SIZEOF_UINTPTR_T for SIZEOF_VALUE.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@21590 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
name if no default type is given.
* configure.in (RUBY_DEFINT): checks size.
* include/ruby/ruby.h (VALUE): use uintptr_t if available.
* include/ruby/ruby.h (PRI_PTRDIFF_PREFIX, PRI_SIZE_PREFIX):
assumes usable if PRIdPTR is defined.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@21587 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
rb_fd_init, rb_fd_term, rb_fd_zero, rb_fd_set, rb_fd_clr, rb_fd_isset,
rb_fd_select, rb_fd_ptr, rb_fd_max, HAVE_RB_FD_INIT): new type,
functions, and macros for Windows.
* win32/win32.c (extract_fd, rb_w32_select): use rb_fdset_t to expand
fd_array if needed. [ruby-core:19946]
* win32/win32.c (copy_fd): new funcion for rb_w32_select().
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@21487 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
is_internal_cmd.
* win32/win32.c (argv_size, join_argv): escapes redirection, pipe
and carret punctuations with carrets.
* win32/win32.c (rb_w32_aspawn): ditto, and redirections and pipe
have no meanings.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@21473 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
values. [ruby-dev:37656]
* object.c (rb_to_float): new function to type check floats.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@21179 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
to specify no-transcoding. and other corner case fixed.
[ruby-dev:37496]
* hash.c (rb_hash_lookup2): new function to look-up hash with
default value.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@20870 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
touching.
* load.c (rb_feature_provided): new function to return the loading
path in addition to rb_provided().
* load.c (search_required): sets path if loading.
* variable.c (autoload_provided): load paths are expanded to check
if loading.
* variable.c (autoload_node): keeps autoload mark while loading.
[ruby-core:20235]
* variable.c (rb_const_get_0): loops while autoload mark is set.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@20531 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
loaded, to get rid of loading same library again. [ruby-core:19798]
* thread.c (rb_barrier_wait): can not wait destroyed barrier.
* thread.c (rb_barrier_destroy): destroys barrier so that no longer
waited.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@20223 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
* ext/curses/curses.c (curses_getch): 1.9 getch should return one
character string for single byte string. wchar_t support may
follow in the future.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@20145 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
[ruby-dev:36854]
* string.c (rb_external_str_new_cstr): new function to create
string from external NUL terminated C string.
* string.c (rb_locale_str_new_cstr): ditto.
* ext/readline/readline.c: now use rb_locale_str_new_cstr().
* test/sdbm/test_sdbm.rb (TestSDBM#test_delete_with_block):
deleted key to the block may be a copy of specified key.
* test/dbm/test_dbm.rb (TestDBM#test_delete_with_block): ditto.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@19885 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
* common.mk: remove vm.h from any rules.
vm.h is not needed on this version.
* vm_core.h: ditto.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@19882 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
string in internal encoding to external to export.
* string.c (rb_str_export): new function to do conversion to
external encoding.
* ext/sdbm/init.c: encoding conversion support.
* ext/dbm/dbm.c: ditto.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@19855 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
external encoding to internal encoding. if something went
wrong, it returns a string with the external encoding.
* string.c (rb_external_str_new_with_enc): same as above besides
you can specify the source encoding.
* ruby.c (ruby_set_argv): use rb_external_str_new()
* ruby.c (set_arg0, ruby_script): ditto.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@19834 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
remove deprecated functions which do not work. [ruby-dev:36697]
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@19805 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Michael Selig <michael.selig at fs.com.au> in [ruby-core:18985].
* io.c (rb_io_ext_int_to_encs): ditto.
* ruby.c (proc_options): support default internal encoding in -E
option.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@19709 b2dd03c8-39d4-4d8f-98ff-823fe69b080e