mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
* variable.c (rb_copy_generic_ivar): remove old generic instance
variable table if it existes. * class.c (rb_make_metaclass): metaclass of a metaclass is a metaclass itself. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@2784 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
parent
20254d4e13
commit
6f484e4930
22 changed files with 276 additions and 238 deletions
41
ChangeLog
41
ChangeLog
|
@ -14,10 +14,20 @@ Mon Sep 2 21:21:46 2002 Minero Aoki <aamine@loveruby.net>
|
|||
|
||||
* intern.h (ruby_parser_stack_on_heap): added.
|
||||
|
||||
Mon Sep 2 18:45:07 2002 Yukihiro Matsumoto <matz@ruby-lang.org>
|
||||
|
||||
* variable.c (rb_copy_generic_ivar): remove old generic instance
|
||||
variable table if it existes.
|
||||
|
||||
Sun Sep 1 15:54:33 2002 WATANABE Hirofumi <eban@ruby-lang.org>
|
||||
|
||||
* config.guess: fixed for Linux/PPC.
|
||||
|
||||
Sat Aug 31 09:38:12 2002 Yukihiro Matsumoto <matz@ruby-lang.org>
|
||||
|
||||
* class.c (rb_make_metaclass): metaclass of a metaclass is a
|
||||
metaclass itself.
|
||||
|
||||
Fri Aug 30 22:45:16 2002 Akinori MUSHA <knu@iDaemons.org>
|
||||
|
||||
* lib/set.rb: Added.
|
||||
|
@ -45,6 +55,37 @@ Fri Aug 30 19:40:28 2002 Nobuyoshi Nakada <nobu.nokada@softhome.net>
|
|||
|
||||
* ext/tcltklib/tcltklib.c (ip_toUTF8, ip_fromUTF8): ditto.
|
||||
|
||||
Fri Aug 30 01:32:17 2002 Yukihiro Matsumoto <matz@ruby-lang.org>
|
||||
|
||||
* class.c (rb_singleton_class): superclass of a metaclass
|
||||
should be a metaclass of superclass.
|
||||
|
||||
* range.c (range_eq): two instances must belong to a same class to
|
||||
be equal.
|
||||
|
||||
* range.c (range_eql): ditto.
|
||||
|
||||
* io.c (rb_io_taint_check): frozen check added.
|
||||
|
||||
* file.c (rb_stat_become): frozen check added.
|
||||
|
||||
* object.c (rb_obj_become): ditto.
|
||||
|
||||
* re.c (rb_reg_become): ditto.
|
||||
|
||||
* struct.c (rb_struct_become): ditto.
|
||||
|
||||
* time.c (time_become): ditto.
|
||||
|
||||
* array.c (rb_ary_become): should call rb_ary_modify().
|
||||
|
||||
* hash.c (rb_hash_become): should call rb_hash_modify().
|
||||
|
||||
* compar.c (cmp_equal): should not use NUM2LONG(), since <=> may
|
||||
return bignum.
|
||||
|
||||
* compar.c (cmp_gt, cmp_ge, cmp_lt, cmp_le, cmp_between): ditto.
|
||||
|
||||
Thu Aug 29 23:34:42 2002 KONISHI Hiromasa <konishih@fd6.so-net.ne.jp>
|
||||
|
||||
* bcc32/MakeFile.sub (sitearch): add.
|
||||
|
|
38
array.c
38
array.c
|
@ -795,22 +795,6 @@ rb_ary_empty_p(ary)
|
|||
return Qfalse;
|
||||
}
|
||||
|
||||
static VALUE
|
||||
rb_ary_become(copy, orig)
|
||||
VALUE copy, orig;
|
||||
{
|
||||
orig = to_ary(orig);
|
||||
ary_make_shared(orig);
|
||||
if (RARRAY(copy)->ptr && !FL_TEST(copy, ELTS_SHARED))
|
||||
free(RARRAY(copy)->ptr);
|
||||
RARRAY(copy)->ptr = RARRAY(orig)->ptr;
|
||||
RARRAY(copy)->len = RARRAY(orig)->len;
|
||||
RARRAY(copy)->aux.shared = RARRAY(orig)->aux.shared;
|
||||
FL_SET(copy, ELTS_SHARED);
|
||||
|
||||
return copy;
|
||||
}
|
||||
|
||||
VALUE
|
||||
rb_ary_dup(ary)
|
||||
VALUE ary;
|
||||
|
@ -1316,13 +1300,21 @@ rb_ary_delete_if(ary)
|
|||
}
|
||||
|
||||
static VALUE
|
||||
rb_ary_replace(ary, ary2)
|
||||
VALUE ary, ary2;
|
||||
rb_ary_replace(copy, orig)
|
||||
VALUE copy, orig;
|
||||
{
|
||||
if (ary == ary2) return ary;
|
||||
ary2 = to_ary(ary2);
|
||||
rb_ary_update(ary, 0, RARRAY(ary)->len, ary2);
|
||||
return ary;
|
||||
rb_ary_modify(copy);
|
||||
orig = to_ary(orig);
|
||||
if (copy == orig) return copy;
|
||||
ary_make_shared(orig);
|
||||
if (RARRAY(copy)->ptr && !FL_TEST(copy, ELTS_SHARED))
|
||||
free(RARRAY(copy)->ptr);
|
||||
RARRAY(copy)->ptr = RARRAY(orig)->ptr;
|
||||
RARRAY(copy)->len = RARRAY(orig)->len;
|
||||
RARRAY(copy)->aux.shared = RARRAY(orig)->aux.shared;
|
||||
FL_SET(copy, ELTS_SHARED);
|
||||
|
||||
return copy;
|
||||
}
|
||||
|
||||
VALUE
|
||||
|
@ -1857,7 +1849,7 @@ Init_Array()
|
|||
rb_define_method(rb_cArray, "rindex", rb_ary_rindex, 1);
|
||||
rb_define_method(rb_cArray, "indexes", rb_ary_indexes, -1);
|
||||
rb_define_method(rb_cArray, "indices", rb_ary_indexes, -1);
|
||||
rb_define_method(rb_cArray, "become", rb_ary_become, 1);
|
||||
rb_define_method(rb_cArray, "become", rb_ary_replace, 1);
|
||||
rb_define_method(rb_cArray, "join", rb_ary_join_m, -1);
|
||||
rb_define_method(rb_cArray, "reverse", rb_ary_reverse_m, 0);
|
||||
rb_define_method(rb_cArray, "reverse!", rb_ary_reverse_bang, 0);
|
||||
|
|
54
class.c
54
class.c
|
@ -94,25 +94,24 @@ rb_mod_dup(mod)
|
|||
}
|
||||
|
||||
VALUE
|
||||
rb_singleton_class_new(super)
|
||||
VALUE super;
|
||||
rb_singleton_class_clone(obj)
|
||||
VALUE obj;
|
||||
{
|
||||
VALUE klass = rb_class_boot(super);
|
||||
VALUE klass = RBASIC(obj)->klass;
|
||||
|
||||
FL_SET(klass, FL_SINGLETON);
|
||||
return klass;
|
||||
}
|
||||
|
||||
VALUE
|
||||
rb_singleton_class_clone(klass)
|
||||
VALUE klass;
|
||||
{
|
||||
if (!FL_TEST(klass, FL_SINGLETON))
|
||||
return klass;
|
||||
else {
|
||||
/* copy singleton(unnamed) class */
|
||||
NEWOBJ(clone, struct RClass);
|
||||
CLONESETUP(clone, klass);
|
||||
OBJSETUP(clone, 0, RBASIC(klass)->flags);
|
||||
|
||||
if (BUILTIN_TYPE(obj) == T_CLASS) {
|
||||
RBASIC(clone)->klass = (VALUE)clone;
|
||||
}
|
||||
else {
|
||||
RBASIC(clone)->klass = rb_singleton_class_clone(klass);
|
||||
}
|
||||
|
||||
clone->super = RCLASS(klass)->super;
|
||||
clone->iv_tbl = 0;
|
||||
|
@ -122,6 +121,7 @@ rb_singleton_class_clone(klass)
|
|||
}
|
||||
clone->m_tbl = st_init_numtable();
|
||||
st_foreach(RCLASS(klass)->m_tbl, clone_method, clone->m_tbl);
|
||||
rb_singleton_class_attached(RBASIC(clone)->klass, (VALUE)clone);
|
||||
FL_SET(clone, FL_SINGLETON);
|
||||
return (VALUE)clone;
|
||||
}
|
||||
|
@ -140,12 +140,17 @@ rb_singleton_class_attached(klass, obj)
|
|||
}
|
||||
|
||||
VALUE
|
||||
rb_make_metaclass(obj, klass)
|
||||
VALUE obj, klass;
|
||||
rb_make_metaclass(obj, super)
|
||||
VALUE obj, super;
|
||||
{
|
||||
klass = rb_singleton_class_new(klass);
|
||||
VALUE klass = rb_class_boot(super);
|
||||
FL_SET(klass, FL_SINGLETON);
|
||||
RBASIC(obj)->klass = klass;
|
||||
rb_singleton_class_attached(klass, obj);
|
||||
if (BUILTIN_TYPE(obj) == T_CLASS) {
|
||||
RBASIC(klass)->klass = klass;
|
||||
}
|
||||
|
||||
return klass;
|
||||
}
|
||||
|
||||
|
@ -667,28 +672,12 @@ rb_undef_method(klass, name)
|
|||
rb_add_method(klass, rb_intern(name), 0, NOEX_UNDEF);
|
||||
}
|
||||
|
||||
#if 0
|
||||
|
||||
#define SPECIAL_SINGLETON(x,c) do {
|
||||
if (obj == (x)) {\
|
||||
if (!FL_TEST(c, FL_SINGLETON)) {\
|
||||
c = rb_singleton_class_new(c);\
|
||||
rb_singleton_class_attached(c,obj);\
|
||||
}\
|
||||
return c;\
|
||||
}\
|
||||
} while (0)
|
||||
|
||||
#else
|
||||
|
||||
#define SPECIAL_SINGLETON(x,c) do {\
|
||||
if (obj == (x)) {\
|
||||
return c;\
|
||||
}\
|
||||
} while (0)
|
||||
|
||||
#endif
|
||||
|
||||
VALUE
|
||||
rb_singleton_class(obj)
|
||||
VALUE obj;
|
||||
|
@ -707,13 +696,12 @@ rb_singleton_class(obj)
|
|||
|
||||
DEFER_INTS;
|
||||
if (FL_TEST(RBASIC(obj)->klass, FL_SINGLETON) &&
|
||||
((BUILTIN_TYPE(obj) != T_CLASS && BUILTIN_TYPE(obj) != T_MODULE) ||
|
||||
(BUILTIN_TYPE(obj) == T_CLASS || /* metaclass (or metaclass of metaclass) */
|
||||
rb_iv_get(RBASIC(obj)->klass, "__attached__") == obj)) {
|
||||
klass = RBASIC(obj)->klass;
|
||||
}
|
||||
else {
|
||||
klass = rb_make_metaclass(obj, RBASIC(obj)->klass);
|
||||
RBASIC(klass)->klass = CLASS_OF(RCLASS(klass)->super);
|
||||
}
|
||||
if (OBJ_TAINTED(obj)) {
|
||||
OBJ_TAINT(klass);
|
||||
|
|
40
compar.c
40
compar.c
|
@ -23,7 +23,10 @@ cmp_equal(x, y)
|
|||
VALUE c = rb_funcall(x, cmp, 1, y);
|
||||
|
||||
if (NIL_P(c)) return Qfalse;
|
||||
if (NUM2LONG(c) == 0) return Qtrue;
|
||||
if (c == INT2FIX(0)) return Qtrue;
|
||||
if (TYPE(c) == T_BIGNUM) {
|
||||
if (rb_big_norm(c) == INT2FIX(0)) return Qtrue;
|
||||
}
|
||||
return Qfalse;
|
||||
}
|
||||
|
||||
|
@ -34,7 +37,11 @@ cmp_gt(x, y)
|
|||
VALUE c = rb_funcall(x, cmp, 1, y);
|
||||
|
||||
if (NIL_P(c)) return Qfalse;
|
||||
if (NUM2LONG(c) > 0) return Qtrue;
|
||||
if (FIXNUM_P(c) && FIX2INT(c) > 0) return Qtrue;
|
||||
if (TYPE(c) == T_BIGNUM) {
|
||||
if (rb_big_norm(x) == INT2FIX(0)) return Qfalse;
|
||||
if (RBIGNUM(c)->sign) return Qtrue;
|
||||
}
|
||||
return Qfalse;
|
||||
}
|
||||
|
||||
|
@ -45,7 +52,11 @@ cmp_ge(x, y)
|
|||
VALUE c = rb_funcall(x, cmp, 1, y);
|
||||
|
||||
if (NIL_P(c)) return Qfalse;
|
||||
if (NUM2LONG(c) >= 0) return Qtrue;
|
||||
if (FIXNUM_P(c) && FIX2INT(c) >= 0) return Qtrue;
|
||||
if (TYPE(c) == T_BIGNUM) {
|
||||
if (rb_big_norm(x) == INT2FIX(0)) return Qtrue;
|
||||
if (RBIGNUM(c)->sign) return Qtrue;
|
||||
}
|
||||
return Qfalse;
|
||||
}
|
||||
|
||||
|
@ -55,8 +66,11 @@ cmp_lt(x, y)
|
|||
{
|
||||
VALUE c = rb_funcall(x, cmp, 1, y);
|
||||
|
||||
if (NIL_P(c)) return Qfalse;
|
||||
if (NUM2LONG(c) < 0) return Qtrue;
|
||||
if (FIXNUM_P(c) && FIX2INT(c) < 0) return Qtrue;
|
||||
if (TYPE(c) == T_BIGNUM) {
|
||||
if (rb_big_norm(x) == INT2FIX(0)) return Qfalse;
|
||||
if (!RBIGNUM(c)->sign) return Qtrue;
|
||||
}
|
||||
return Qfalse;
|
||||
}
|
||||
|
||||
|
@ -67,7 +81,11 @@ cmp_le(x, y)
|
|||
VALUE c = rb_funcall(x, cmp, 1, y);
|
||||
|
||||
if (NIL_P(c)) return Qfalse;
|
||||
if (NUM2LONG(c) <= 0) return Qtrue;
|
||||
if (FIXNUM_P(c) && FIX2INT(c) <= 0) return Qtrue;
|
||||
if (TYPE(c) == T_BIGNUM) {
|
||||
if (rb_big_norm(x) == INT2FIX(0)) return Qtrue;
|
||||
if (!RBIGNUM(c)->sign) return Qtrue;
|
||||
}
|
||||
return Qfalse;
|
||||
}
|
||||
|
||||
|
@ -75,14 +93,8 @@ static VALUE
|
|||
cmp_between(x, min, max)
|
||||
VALUE x, min, max;
|
||||
{
|
||||
VALUE c = rb_funcall(x, cmp, 1, min);
|
||||
|
||||
if (NIL_P(c)) return Qfalse;
|
||||
if (NUM2LONG(c) < 0) return Qfalse;
|
||||
|
||||
c = rb_funcall(x, cmp, 1, max);
|
||||
if (NIL_P(c)) return Qfalse;
|
||||
if (NUM2LONG(c) > 0) return Qfalse;
|
||||
if (cmp_lt(x, min)) return Qfalse;
|
||||
if (cmp_gt(x, max)) return Qfalse;
|
||||
return Qtrue;
|
||||
}
|
||||
|
||||
|
|
7
error.c
7
error.c
|
@ -813,6 +813,13 @@ rb_error_frozen(what)
|
|||
rb_raise(rb_eTypeError, "can't modify frozen %s", what);
|
||||
}
|
||||
|
||||
void
|
||||
rb_check_frozen(obj)
|
||||
VALUE obj;
|
||||
{
|
||||
if (OBJ_FROZEN(obj)) rb_error_frozen(rb_class2name(CLASS_OF(obj)));
|
||||
}
|
||||
|
||||
static void
|
||||
init_syserr()
|
||||
{
|
||||
|
|
|
@ -41,16 +41,17 @@ static ID id_metadata;
|
|||
*/
|
||||
|
||||
static algo_t *
|
||||
get_digest_base_metadata(class)
|
||||
VALUE class;
|
||||
get_digest_base_metadata(klass)
|
||||
VALUE klass;
|
||||
{
|
||||
VALUE obj;
|
||||
algo_t *algo;
|
||||
|
||||
if (rb_cvar_defined(class, id_metadata) == Qfalse)
|
||||
if (rb_cvar_defined(klass, id_metadata) == Qfalse) {
|
||||
rb_notimplement();
|
||||
}
|
||||
|
||||
obj = rb_cvar_get(class, id_metadata);
|
||||
obj = rb_cvar_get(klass, id_metadata);
|
||||
|
||||
Data_Get_Struct(obj, algo_t, algo);
|
||||
|
||||
|
@ -58,54 +59,42 @@ get_digest_base_metadata(class)
|
|||
}
|
||||
|
||||
static VALUE
|
||||
rb_digest_base_s_new(argc, argv, class)
|
||||
int argc;
|
||||
VALUE* argv;
|
||||
VALUE class;
|
||||
rb_digest_base_alloc(klass)
|
||||
VALUE klass;
|
||||
{
|
||||
algo_t *algo;
|
||||
VALUE obj;
|
||||
void *pctx;
|
||||
|
||||
if (class == cDigest_Base)
|
||||
if (klass == cDigest_Base) {
|
||||
rb_raise(rb_eNotImpError, "Digest::Base is an abstract class");
|
||||
}
|
||||
|
||||
algo = get_digest_base_metadata(class);
|
||||
algo = get_digest_base_metadata(klass);
|
||||
|
||||
pctx = xmalloc(algo->ctx_size);
|
||||
algo->init_func(pctx);
|
||||
|
||||
obj = Data_Wrap_Struct(class, 0, free, pctx);
|
||||
|
||||
rb_obj_call_init(obj, argc, argv);
|
||||
obj = Data_Wrap_Struct(klass, 0, free, pctx);
|
||||
|
||||
return obj;
|
||||
}
|
||||
|
||||
static VALUE
|
||||
rb_digest_base_s_digest(class, str)
|
||||
VALUE class;
|
||||
rb_digest_base_s_digest(klass, str)
|
||||
VALUE klass;
|
||||
VALUE str;
|
||||
{
|
||||
algo_t *algo;
|
||||
void *pctx;
|
||||
size_t len;
|
||||
unsigned char *digest;
|
||||
VALUE obj;
|
||||
VALUE obj = rb_digest_base_alloc(klass);
|
||||
|
||||
if (class == cDigest_Base)
|
||||
rb_raise(rb_eNotImpError, "Digest::Base is an abstract class");
|
||||
algo = get_digest_base_metadata(klass);
|
||||
Data_Get_Struct(obj, void, pctx);
|
||||
|
||||
#ifdef StringValue
|
||||
StringValue(str);
|
||||
#else
|
||||
Check_Type(str, T_STRING);
|
||||
#endif
|
||||
|
||||
algo = get_digest_base_metadata(class);
|
||||
|
||||
pctx = xmalloc(algo->ctx_size);
|
||||
algo->init_func(pctx);
|
||||
algo->update_func(pctx, RSTRING(str)->ptr, RSTRING(str)->len);
|
||||
|
||||
len = algo->digest_len;
|
||||
|
@ -122,26 +111,18 @@ rb_digest_base_s_digest(class, str)
|
|||
}
|
||||
|
||||
static VALUE
|
||||
rb_digest_base_s_hexdigest(class, str)
|
||||
VALUE class;
|
||||
rb_digest_base_s_hexdigest(klass, str)
|
||||
VALUE klass;
|
||||
VALUE str;
|
||||
{
|
||||
algo_t *algo;
|
||||
void *pctx;
|
||||
size_t len;
|
||||
unsigned char *hexdigest;
|
||||
VALUE obj;
|
||||
VALUE obj = rb_digest_base_alloc(klass);
|
||||
|
||||
if (class == cDigest_Base)
|
||||
rb_raise(rb_eNotImpError, "Digest::Base is an abstract class");
|
||||
|
||||
#ifdef StringValue
|
||||
StringValue(str);
|
||||
#else
|
||||
Check_Type(str, T_STRING);
|
||||
#endif
|
||||
|
||||
algo = get_digest_base_metadata(class);
|
||||
algo = get_digest_base_metadata(klass);
|
||||
|
||||
pctx = xmalloc(algo->ctx_size);
|
||||
algo->init_func(pctx);
|
||||
|
@ -161,21 +142,25 @@ rb_digest_base_s_hexdigest(class, str)
|
|||
}
|
||||
|
||||
static VALUE
|
||||
rb_digest_base_clone(self)
|
||||
VALUE self;
|
||||
rb_digest_base_become(copy, obj)
|
||||
VALUE copy, obj;
|
||||
{
|
||||
algo_t *algo;
|
||||
void *pctx1, *pctx2;
|
||||
VALUE class;
|
||||
VALUE klass;
|
||||
|
||||
class = CLASS_OF(self);
|
||||
algo = get_digest_base_metadata(class);
|
||||
Data_Get_Struct(self, void, pctx1);
|
||||
|
||||
pctx2 = xmalloc(algo->ctx_size);
|
||||
printf("Digest::Base::bacome\n");
|
||||
if (copy = obj) return copy;
|
||||
rb_check_frozen(copy);
|
||||
algo = get_digest_base_metadata(CLASS_OF(klass));
|
||||
if (algo != get_digest_base_metadata(CLASS_OF(obj))) {
|
||||
rb_raise(rb_eTypeError, "wrong argument class");
|
||||
}
|
||||
Data_Get_Struct(copy, void, pctx1);
|
||||
Data_Get_Struct(copy, void, pctx2);
|
||||
memcpy(pctx2, pctx1, algo->ctx_size);
|
||||
|
||||
return Data_Wrap_Struct(class, 0, free, pctx2);
|
||||
return copy;
|
||||
}
|
||||
|
||||
static VALUE
|
||||
|
@ -185,12 +170,7 @@ rb_digest_base_update(self, str)
|
|||
algo_t *algo;
|
||||
void *pctx;
|
||||
|
||||
#ifdef StringValue
|
||||
StringValue(str);
|
||||
#else
|
||||
Check_Type(str, T_STRING);
|
||||
#endif
|
||||
|
||||
algo = get_digest_base_metadata(CLASS_OF(self));
|
||||
Data_Get_Struct(self, void, pctx);
|
||||
|
||||
|
@ -281,13 +261,13 @@ rb_digest_base_equal(self, other)
|
|||
VALUE self, other;
|
||||
{
|
||||
algo_t *algo;
|
||||
VALUE class;
|
||||
VALUE klass;
|
||||
VALUE str1, str2;
|
||||
|
||||
class = CLASS_OF(self);
|
||||
algo = get_digest_base_metadata(class);
|
||||
klass = CLASS_OF(self);
|
||||
algo = get_digest_base_metadata(klass);
|
||||
|
||||
if (CLASS_OF(other) == class) {
|
||||
if (CLASS_OF(other) == klass) {
|
||||
void *pctx1, *pctx2;
|
||||
|
||||
Data_Get_Struct(self, void, pctx1);
|
||||
|
@ -296,11 +276,7 @@ rb_digest_base_equal(self, other)
|
|||
return algo->equal_func(pctx1, pctx2) ? Qtrue : Qfalse;
|
||||
}
|
||||
|
||||
#ifdef StringValue
|
||||
StringValue(other);
|
||||
#else
|
||||
Check_Type(other, T_STRING);
|
||||
#endif
|
||||
str2 = other;
|
||||
|
||||
if (RSTRING(str2)->len == algo->digest_len)
|
||||
|
@ -326,12 +302,13 @@ Init_digest()
|
|||
|
||||
cDigest_Base = rb_define_class_under(mDigest, "Base", rb_cObject);
|
||||
|
||||
rb_define_singleton_method(cDigest_Base, "new", rb_digest_base_s_new, -1);
|
||||
printf("Init_digest\n");
|
||||
rb_define_singleton_method(cDigest_Base, "allocate", rb_digest_base_alloc, 0);
|
||||
rb_define_singleton_method(cDigest_Base, "digest", rb_digest_base_s_digest, 1);
|
||||
rb_define_singleton_method(cDigest_Base, "hexdigest", rb_digest_base_s_hexdigest, 1);
|
||||
|
||||
rb_define_method(cDigest_Base, "initialize", rb_digest_base_init, -1);
|
||||
rb_define_method(cDigest_Base, "clone", rb_digest_base_clone, 0);
|
||||
rb_define_method(cDigest_Base, "become", rb_digest_base_become, 1);
|
||||
rb_define_method(cDigest_Base, "update", rb_digest_base_update, 1);
|
||||
rb_define_method(cDigest_Base, "<<", rb_digest_base_update, 1);
|
||||
rb_define_method(cDigest_Base, "digest", rb_digest_base_digest, 0);
|
||||
|
|
|
@ -18,7 +18,6 @@ void
|
|||
Init_md5()
|
||||
{
|
||||
VALUE mDigest, cDigest_Base, cDigest_MD5;
|
||||
ID id_metadata;
|
||||
|
||||
rb_require("digest.so");
|
||||
|
||||
|
@ -27,8 +26,6 @@ Init_md5()
|
|||
|
||||
cDigest_MD5 = rb_define_class_under(mDigest, "MD5", cDigest_Base);
|
||||
|
||||
id_metadata = rb_intern("metadata");
|
||||
|
||||
rb_cvar_set(cDigest_MD5, id_metadata,
|
||||
Data_Wrap_Struct(rb_cObject, 0, 0, &md5), Qtrue);
|
||||
rb_cvar_declare(cDigest_MD5, rb_intern("metadata"),
|
||||
Data_Wrap_Struct(rb_cObject, 0, 0, &md5));
|
||||
}
|
||||
|
|
|
@ -822,7 +822,7 @@ if $extlist.size > 0
|
|||
if File.exist?(f)
|
||||
$extinit += format("\
|
||||
\tInit_%s();\n\
|
||||
\trb_provide(\"%s\");\n\
|
||||
\trb_provide(\"%s.so\");\n\
|
||||
", i, t)
|
||||
$extobjs += "ext/"
|
||||
$extobjs += f
|
||||
|
|
|
@ -148,7 +148,7 @@ static VALUE strio_closed _((VALUE));
|
|||
static VALUE strio_closed_read _((VALUE));
|
||||
static VALUE strio_closed_write _((VALUE));
|
||||
static VALUE strio_eof _((VALUE));
|
||||
static VALUE strio_clone _((VALUE));
|
||||
static VALUE strio_become _((VALUE, VALUE));
|
||||
static VALUE strio_get_lineno _((VALUE));
|
||||
static VALUE strio_set_lineno _((VALUE, VALUE));
|
||||
static VALUE strio_get_pos _((VALUE));
|
||||
|
@ -405,14 +405,17 @@ strio_eof(self)
|
|||
}
|
||||
|
||||
static VALUE
|
||||
strio_clone(self)
|
||||
VALUE self;
|
||||
strio_become(copy, orig)
|
||||
VALUE copy, orig;
|
||||
{
|
||||
struct StringIO *ptr = StringIO(self);
|
||||
VALUE clone = rb_call_super(0, 0);
|
||||
DATA_PTR(clone) = ptr;
|
||||
struct StringIO *ptr = StringIO(orig);
|
||||
|
||||
if (DATA_PTR(copy)) {
|
||||
strio_free(DATA_PTR(ptr));
|
||||
}
|
||||
DATA_PTR(copy) = ptr;
|
||||
++ptr->count;
|
||||
return self;
|
||||
return copy;
|
||||
}
|
||||
|
||||
static VALUE
|
||||
|
@ -883,8 +886,7 @@ Init_stringio()
|
|||
rb_define_singleton_method(StringIO, "open", strio_s_open, -1);
|
||||
rb_define_method(StringIO, "initialize", strio_initialize, -1);
|
||||
rb_enable_super(StringIO, "initialize");
|
||||
rb_define_method(StringIO, "clone", strio_clone, 0);
|
||||
rb_enable_super(StringIO, "clone");
|
||||
rb_define_method(StringIO, "become", strio_become, 1);
|
||||
rb_define_method(StringIO, "reopen", strio_reopen, -1);
|
||||
|
||||
rb_define_method(StringIO, "string", strio_get_string, 0);
|
||||
|
|
18
file.c
18
file.c
|
@ -2024,26 +2024,28 @@ rb_stat_init(obj, fname)
|
|||
}
|
||||
|
||||
static VALUE
|
||||
rb_stat_become(obj, orig)
|
||||
VALUE obj, orig;
|
||||
rb_stat_become(copy, orig)
|
||||
VALUE copy, orig;
|
||||
{
|
||||
struct stat *nst;
|
||||
|
||||
if (copy == orig) return orig;
|
||||
rb_check_frozen(copy);
|
||||
/* need better argument type check */
|
||||
if (!rb_obj_is_instance_of(orig, rb_obj_class(obj))) {
|
||||
if (!rb_obj_is_instance_of(orig, rb_obj_class(copy))) {
|
||||
rb_raise(rb_eTypeError, "wrong argument class");
|
||||
}
|
||||
if (DATA_PTR(obj)) {
|
||||
free(DATA_PTR(obj));
|
||||
DATA_PTR(obj) = 0;
|
||||
if (DATA_PTR(copy)) {
|
||||
free(DATA_PTR(copy));
|
||||
DATA_PTR(copy) = 0;
|
||||
}
|
||||
if (DATA_PTR(orig)) {
|
||||
nst = ALLOC(struct stat);
|
||||
*nst = *(struct stat*)DATA_PTR(orig);
|
||||
DATA_PTR(obj) = nst;
|
||||
DATA_PTR(copy) = nst;
|
||||
}
|
||||
|
||||
return obj;
|
||||
return copy;
|
||||
}
|
||||
|
||||
static VALUE
|
||||
|
|
28
hash.c
28
hash.c
|
@ -254,30 +254,6 @@ to_hash(hash)
|
|||
return rb_convert_type(hash, T_HASH, "Hash", "to_hash");
|
||||
}
|
||||
|
||||
static VALUE
|
||||
rb_hash_become(copy, orig)
|
||||
VALUE copy, orig;
|
||||
{
|
||||
orig = to_hash(orig);
|
||||
if (RHASH(copy)->tbl) st_free_table(RHASH(copy)->tbl);
|
||||
RHASH(copy)->tbl = (st_table*)st_copy(RHASH(orig)->tbl);
|
||||
RHASH(copy)->ifnone = RHASH(orig)->ifnone;
|
||||
if (FL_TEST(orig, HASH_PROC_DEFAULT)) {
|
||||
FL_SET(copy, HASH_PROC_DEFAULT);
|
||||
}
|
||||
else {
|
||||
FL_UNSET(copy, HASH_PROC_DEFAULT);
|
||||
}
|
||||
if (FL_TEST(orig, HASH_DELETED)) {
|
||||
FL_SET(copy, HASH_DELETED);
|
||||
}
|
||||
else {
|
||||
FL_UNSET(copy, HASH_DELETED);
|
||||
}
|
||||
|
||||
return copy;
|
||||
}
|
||||
|
||||
static int
|
||||
rb_hash_rehash_i(key, value, tbl)
|
||||
VALUE key, value;
|
||||
|
@ -596,7 +572,7 @@ replace_i(key, val, hash)
|
|||
}
|
||||
|
||||
static VALUE
|
||||
rb_hash_replace(hash, hash2)
|
||||
rb_hash_become(hash, hash2)
|
||||
VALUE hash, hash2;
|
||||
{
|
||||
hash2 = to_hash(hash2);
|
||||
|
@ -1654,7 +1630,7 @@ Init_Hash()
|
|||
rb_define_method(rb_cHash,"clear", rb_hash_clear, 0);
|
||||
rb_define_method(rb_cHash,"invert", rb_hash_invert, 0);
|
||||
rb_define_method(rb_cHash,"update", rb_hash_update, 1);
|
||||
rb_define_method(rb_cHash,"replace", rb_hash_replace, 1);
|
||||
rb_define_method(rb_cHash,"replace", rb_hash_become, 1);
|
||||
|
||||
rb_define_method(rb_cHash,"include?", rb_hash_has_key, 1);
|
||||
rb_define_method(rb_cHash,"member?", rb_hash_has_key, 1);
|
||||
|
|
1
intern.h
1
intern.h
|
@ -95,7 +95,6 @@ VALUE rb_class_boot _((VALUE));
|
|||
VALUE rb_class_new _((VALUE));
|
||||
VALUE rb_mod_clone _((VALUE));
|
||||
VALUE rb_mod_dup _((VALUE));
|
||||
VALUE rb_singleton_class_new _((VALUE));
|
||||
VALUE rb_singleton_class_clone _((VALUE));
|
||||
void rb_singleton_class_attached _((VALUE,VALUE));
|
||||
VALUE rb_make_metaclass _((VALUE, VALUE));
|
||||
|
|
2
io.c
2
io.c
|
@ -177,6 +177,7 @@ rb_io_taint_check(io)
|
|||
{
|
||||
if (!OBJ_TAINTED(io) && rb_safe_level() >= 4)
|
||||
rb_raise(rb_eSecurityError, "Insecure: operation on untainted IO");
|
||||
rb_check_frozen(io);
|
||||
return io;
|
||||
}
|
||||
|
||||
|
@ -2270,6 +2271,7 @@ rb_io_become(clone, io)
|
|||
char *mode;
|
||||
|
||||
io = rb_io_get_io(io);
|
||||
if (clone == io) return clone;
|
||||
GetOpenFile(io, orig);
|
||||
MakeOpenFile(clone, fptr);
|
||||
|
||||
|
|
52
object.c
52
object.c
|
@ -90,23 +90,43 @@ rb_obj_class(obj)
|
|||
return rb_class_real(CLASS_OF(obj));
|
||||
}
|
||||
|
||||
static void
|
||||
copy_object(dest, obj)
|
||||
VALUE dest, obj;
|
||||
{
|
||||
RBASIC(dest)->flags &= ~(T_MASK|FL_EXIVAR|FL_TAINT);
|
||||
RBASIC(dest)->flags |= RBASIC(obj)->flags & (T_MASK|FL_EXIVAR|FL_TAINT);
|
||||
if (FL_TEST(obj, FL_EXIVAR)) {
|
||||
rb_copy_generic_ivar(dest, obj);
|
||||
}
|
||||
switch (TYPE(obj)) {
|
||||
case T_OBJECT:
|
||||
case T_CLASS:
|
||||
case T_MODULE:
|
||||
if (ROBJECT(dest)->iv_tbl) {
|
||||
st_free_table(ROBJECT(dest)->iv_tbl);
|
||||
ROBJECT(dest)->iv_tbl = 0;
|
||||
}
|
||||
if (ROBJECT(obj)->iv_tbl) {
|
||||
ROBJECT(dest)->iv_tbl = st_copy(ROBJECT(obj)->iv_tbl);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
VALUE
|
||||
rb_obj_clone(obj)
|
||||
VALUE obj;
|
||||
{
|
||||
VALUE clone;
|
||||
int frozen;
|
||||
|
||||
if (rb_special_const_p(obj)) {
|
||||
rb_raise(rb_eTypeError, "can't clone %s", rb_class2name(CLASS_OF(obj)));
|
||||
}
|
||||
clone = rb_obj_alloc(rb_class_real(RBASIC(obj)->klass));
|
||||
CLONESETUP(clone, obj);
|
||||
frozen = OBJ_FROZEN(obj);
|
||||
FL_UNSET(clone, FL_FREEZE); /* temporarily remove frozen flag */
|
||||
clone = rb_obj_alloc(rb_obj_class(obj));
|
||||
RBASIC(clone)->klass = rb_singleton_class_clone(obj);
|
||||
copy_object(clone, obj);
|
||||
rb_funcall(clone, become, 1, obj);
|
||||
if (frozen) OBJ_FREEZE(clone); /* restore frozen status */
|
||||
OBJ_INFECT(clone, obj);
|
||||
RBASIC(clone)->flags = RBASIC(obj)->flags;
|
||||
|
||||
return clone;
|
||||
}
|
||||
|
@ -120,10 +140,9 @@ rb_obj_dup(obj)
|
|||
if (rb_special_const_p(obj)) {
|
||||
rb_raise(rb_eTypeError, "can't dup %s", rb_class2name(CLASS_OF(obj)));
|
||||
}
|
||||
dup = rb_obj_alloc(rb_class_real(RBASIC(obj)->klass));
|
||||
DUPSETUP(dup, obj);
|
||||
dup = rb_obj_alloc(rb_obj_class(obj));
|
||||
copy_object(dup, obj);
|
||||
rb_funcall(dup, become, 1, obj);
|
||||
OBJ_INFECT(dup, obj);
|
||||
|
||||
return dup;
|
||||
}
|
||||
|
@ -132,18 +151,11 @@ VALUE
|
|||
rb_obj_become(obj, orig)
|
||||
VALUE obj, orig;
|
||||
{
|
||||
long type;
|
||||
|
||||
if ((type = TYPE(obj)) != TYPE(orig) ||
|
||||
rb_obj_class(obj) != rb_obj_class(orig)) {
|
||||
if (obj == orig) return obj;
|
||||
rb_check_frozen(obj);
|
||||
if (TYPE(obj) != TYPE(orig) || rb_obj_class(obj) != rb_obj_class(orig)) {
|
||||
rb_raise(rb_eTypeError, "become should take same class object");
|
||||
}
|
||||
if (type == T_OBJECT) {
|
||||
if (ROBJECT(obj)->iv_tbl) st_free_table(ROBJECT(obj)->iv_tbl);
|
||||
if (ROBJECT(orig)->iv_tbl) {
|
||||
ROBJECT(obj)->iv_tbl = st_copy(ROBJECT(orig)->iv_tbl);
|
||||
}
|
||||
}
|
||||
return obj;
|
||||
}
|
||||
|
||||
|
|
6
range.c
6
range.c
|
@ -95,7 +95,8 @@ range_eq(range, obj)
|
|||
VALUE range, obj;
|
||||
{
|
||||
if (range == obj) return Qtrue;
|
||||
if (!rb_obj_is_kind_of(obj, rb_obj_class(range))) return Qfalse;
|
||||
if (!rb_obj_is_instance_of(obj, rb_obj_class(range)))
|
||||
return Qfalse;
|
||||
|
||||
if (!rb_equal(rb_ivar_get(range, id_beg), rb_ivar_get(obj, id_beg)))
|
||||
return Qfalse;
|
||||
|
@ -153,7 +154,8 @@ range_eql(range, obj)
|
|||
VALUE range, obj;
|
||||
{
|
||||
if (range == obj) return Qtrue;
|
||||
if (!rb_obj_is_kind_of(obj, rb_obj_class(obj))) return Qfalse;
|
||||
if (!rb_obj_is_instance_of(obj, rb_obj_class(range)))
|
||||
return Qfalse;
|
||||
|
||||
if (!rb_eql(rb_ivar_get(range, id_beg), rb_ivar_get(obj, id_beg)))
|
||||
return Qfalse;
|
||||
|
|
37
re.c
37
re.c
|
@ -526,6 +526,23 @@ match_alloc(klass)
|
|||
return (VALUE)match;
|
||||
}
|
||||
|
||||
static VALUE
|
||||
match_clone(match)
|
||||
VALUE match;
|
||||
{
|
||||
NEWOBJ(clone, struct RMatch);
|
||||
CLONESETUP(clone, match);
|
||||
|
||||
clone->str = RMATCH(match)->str;
|
||||
clone->regs = 0;
|
||||
|
||||
clone->regs = ALLOC(struct re_registers);
|
||||
clone->regs->allocated = 0;
|
||||
re_copy_registers(clone->regs, RMATCH(match)->regs);
|
||||
|
||||
return (VALUE)clone;
|
||||
}
|
||||
|
||||
static VALUE
|
||||
match_become(obj, orig)
|
||||
VALUE obj, orig;
|
||||
|
@ -1158,9 +1175,7 @@ rb_reg_initialize_m(argc, argv, self)
|
|||
}
|
||||
}
|
||||
|
||||
if (OBJ_FROZEN(self)) {
|
||||
rb_error_frozen("Regexp");
|
||||
}
|
||||
rb_check_frozen(self);
|
||||
src = argv[0];
|
||||
if (TYPE(src) == T_REGEXP) {
|
||||
rb_reg_check(src);
|
||||
|
@ -1311,20 +1326,22 @@ rb_reg_options(re)
|
|||
}
|
||||
|
||||
static VALUE
|
||||
rb_reg_become(clone, re)
|
||||
rb_reg_become(copy, re)
|
||||
VALUE re;
|
||||
{
|
||||
if (copy == re) return copy;
|
||||
rb_check_frozen(copy);
|
||||
/* need better argument type check */
|
||||
if (!rb_obj_is_instance_of(re, rb_obj_class(clone))) {
|
||||
if (!rb_obj_is_instance_of(re, rb_obj_class(copy))) {
|
||||
rb_raise(rb_eTypeError, "wrong argument type");
|
||||
}
|
||||
RREGEXP(clone)->ptr = 0;
|
||||
RREGEXP(clone)->len = 0;
|
||||
RREGEXP(clone)->str = 0;
|
||||
RREGEXP(copy)->ptr = 0;
|
||||
RREGEXP(copy)->len = 0;
|
||||
RREGEXP(copy)->str = 0;
|
||||
rb_reg_check(re);
|
||||
rb_reg_initialize(clone, RREGEXP(re)->str, RREGEXP(re)->len,
|
||||
rb_reg_initialize(copy, RREGEXP(re)->str, RREGEXP(re)->len,
|
||||
rb_reg_options(re));
|
||||
return clone;
|
||||
return copy;
|
||||
}
|
||||
|
||||
VALUE
|
||||
|
|
2
ruby.h
2
ruby.h
|
@ -278,7 +278,7 @@ VALUE rb_newobj _((void));
|
|||
if (rb_safe_level() >= 3) FL_SET(obj, FL_TAINT);\
|
||||
} while (0)
|
||||
#define CLONESETUP(clone,obj) do {\
|
||||
OBJSETUP(clone,rb_singleton_class_clone(RBASIC(obj)->klass),RBASIC(obj)->flags);\
|
||||
OBJSETUP(clone,rb_singleton_class_clone((VALUE)obj),RBASIC(obj)->flags);\
|
||||
rb_singleton_class_attached(RBASIC(clone)->klass, (VALUE)clone);\
|
||||
if (FL_TEST(obj, FL_EXIVAR)) rb_copy_generic_ivar((VALUE)clone,(VALUE)obj);\
|
||||
} while (0)
|
||||
|
|
4
string.c
4
string.c
|
@ -213,7 +213,7 @@ rb_str_to_str(str)
|
|||
}
|
||||
|
||||
static void
|
||||
rb_str_become(str, str2)
|
||||
rb_str_shared_replace(str, str2)
|
||||
VALUE str, str2;
|
||||
{
|
||||
if (str == str2) return;
|
||||
|
@ -1071,7 +1071,7 @@ rb_str_succ_bang(str)
|
|||
VALUE str;
|
||||
{
|
||||
rb_str_modify(str);
|
||||
rb_str_become(str, rb_str_succ(str));
|
||||
rb_str_shared_replace(str, rb_str_succ(str));
|
||||
|
||||
return str;
|
||||
}
|
||||
|
|
16
struct.c
16
struct.c
|
@ -421,17 +421,19 @@ rb_struct_to_a(s)
|
|||
}
|
||||
|
||||
static VALUE
|
||||
rb_struct_become(clone, s)
|
||||
VALUE clone, s;
|
||||
rb_struct_become(copy, s)
|
||||
VALUE copy, s;
|
||||
{
|
||||
if (!rb_obj_is_instance_of(s, rb_obj_class(clone))) {
|
||||
if (copy == s) return copy;
|
||||
rb_check_frozen(copy);
|
||||
if (!rb_obj_is_instance_of(s, rb_obj_class(copy))) {
|
||||
rb_raise(rb_eTypeError, "wrong argument class");
|
||||
}
|
||||
RSTRUCT(clone)->ptr = ALLOC_N(VALUE, RSTRUCT(s)->len);
|
||||
RSTRUCT(clone)->len = RSTRUCT(s)->len;
|
||||
MEMCPY(RSTRUCT(clone)->ptr, RSTRUCT(s)->ptr, VALUE, RSTRUCT(clone)->len);
|
||||
RSTRUCT(copy)->ptr = ALLOC_N(VALUE, RSTRUCT(s)->len);
|
||||
RSTRUCT(copy)->len = RSTRUCT(s)->len;
|
||||
MEMCPY(RSTRUCT(copy)->ptr, RSTRUCT(s)->ptr, VALUE, RSTRUCT(copy)->len);
|
||||
|
||||
return clone;
|
||||
return copy;
|
||||
}
|
||||
|
||||
static VALUE
|
||||
|
|
20
time.c
20
time.c
|
@ -793,12 +793,23 @@ time_hash(time)
|
|||
return LONG2FIX(hash);
|
||||
}
|
||||
|
||||
static void
|
||||
time_modify(time)
|
||||
VALUE time;
|
||||
{
|
||||
rb_check_frozen(time);
|
||||
if (!OBJ_TAINTED(time) && rb_safe_level() >= 4)
|
||||
rb_raise(rb_eSecurityError, "Insecure: can't modify Time");
|
||||
}
|
||||
|
||||
static VALUE
|
||||
time_become(copy, time)
|
||||
VALUE copy, time;
|
||||
{
|
||||
struct time_object *tobj, *tcopy;
|
||||
|
||||
if (copy == time) return copy;
|
||||
time_modify(copy);
|
||||
if (TYPE(time) != T_DATA || RDATA(time)->dfree != time_free) {
|
||||
rb_raise(rb_eTypeError, "wrong argument type");
|
||||
}
|
||||
|
@ -818,15 +829,6 @@ time_dup(time)
|
|||
return dup;
|
||||
}
|
||||
|
||||
static void
|
||||
time_modify(time)
|
||||
VALUE time;
|
||||
{
|
||||
if (OBJ_FROZEN(time)) rb_error_frozen("Time");
|
||||
if (!OBJ_TAINTED(time) && rb_safe_level() >= 4)
|
||||
rb_raise(rb_eSecurityError, "Insecure: can't modify Time");
|
||||
}
|
||||
|
||||
static VALUE
|
||||
time_localtime(time)
|
||||
VALUE time;
|
||||
|
|
|
@ -924,9 +924,17 @@ rb_copy_generic_ivar(clone, obj)
|
|||
|
||||
if (!generic_iv_tbl) return;
|
||||
if (st_lookup(generic_iv_tbl, obj, &tbl)) {
|
||||
st_table *old;
|
||||
|
||||
if (st_lookup(generic_iv_tbl, clone, &old)) {
|
||||
st_free_table(old);
|
||||
st_insert(generic_iv_tbl, clone, st_copy(tbl));
|
||||
}
|
||||
else {
|
||||
st_add_direct(generic_iv_tbl, clone, st_copy(tbl));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
VALUE
|
||||
rb_ivar_get(obj, id)
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
#define RUBY_VERSION "1.7.3"
|
||||
#define RUBY_RELEASE_DATE "2002-09-02"
|
||||
#define RUBY_RELEASE_DATE "2002-09-03"
|
||||
#define RUBY_VERSION_CODE 173
|
||||
#define RUBY_RELEASE_CODE 20020902
|
||||
#define RUBY_RELEASE_CODE 20020903
|
||||
|
|
Loading…
Reference in a new issue