mbed I/F binding for mruby

Dependents:   mruby_mbed_web mirb_mbed

mbed-mruby

How to use

Class

Committer:
mzta
Date:
Mon Apr 13 05:20:15 2015 +0000
Revision:
1:8ccd1d494a4b
Parent:
0:158c61bb030f
- code refactoring.; - add SPI, SPISlave, I2C class to mruby-mbed (Incomplete).

Who changed what in which revision?

UserRevisionLine numberNew contents of line
mzta 0:158c61bb030f 1 /*
mzta 0:158c61bb030f 2 ** kernel.c - Kernel module
mzta 0:158c61bb030f 3 **
mzta 0:158c61bb030f 4 ** See Copyright Notice in mruby.h
mzta 0:158c61bb030f 5 */
mzta 0:158c61bb030f 6
mzta 0:158c61bb030f 7 #include "mruby.h"
mzta 0:158c61bb030f 8 #include "mruby/array.h"
mzta 0:158c61bb030f 9 #include "mruby/class.h"
mzta 0:158c61bb030f 10 #include "mruby/proc.h"
mzta 0:158c61bb030f 11 #include "mruby/string.h"
mzta 0:158c61bb030f 12 #include "mruby/variable.h"
mzta 0:158c61bb030f 13 #include "mruby/error.h"
mzta 0:158c61bb030f 14
mzta 0:158c61bb030f 15 typedef enum {
mzta 0:158c61bb030f 16 NOEX_PUBLIC = 0x00,
mzta 0:158c61bb030f 17 NOEX_NOSUPER = 0x01,
mzta 0:158c61bb030f 18 NOEX_PRIVATE = 0x02,
mzta 0:158c61bb030f 19 NOEX_PROTECTED = 0x04,
mzta 0:158c61bb030f 20 NOEX_MASK = 0x06,
mzta 0:158c61bb030f 21 NOEX_BASIC = 0x08,
mzta 0:158c61bb030f 22 NOEX_UNDEF = NOEX_NOSUPER,
mzta 0:158c61bb030f 23 NOEX_MODFUNC = 0x12,
mzta 0:158c61bb030f 24 NOEX_SUPER = 0x20,
mzta 0:158c61bb030f 25 NOEX_VCALL = 0x40,
mzta 0:158c61bb030f 26 NOEX_RESPONDS = 0x80
mzta 0:158c61bb030f 27 } mrb_method_flag_t;
mzta 0:158c61bb030f 28
mzta 0:158c61bb030f 29 static mrb_bool
mzta 0:158c61bb030f 30 mrb_obj_basic_to_s_p(mrb_state *mrb, mrb_value obj)
mzta 0:158c61bb030f 31 {
mzta 0:158c61bb030f 32 struct RProc *me = mrb_method_search(mrb, mrb_class(mrb, obj), mrb_intern_lit(mrb, "to_s"));
mzta 0:158c61bb030f 33 if (MRB_PROC_CFUNC_P(me) && (me->body.func == mrb_any_to_s))
mzta 0:158c61bb030f 34 return TRUE;
mzta 0:158c61bb030f 35 return FALSE;
mzta 0:158c61bb030f 36 }
mzta 0:158c61bb030f 37
mzta 0:158c61bb030f 38 /* 15.3.1.3.17 */
mzta 0:158c61bb030f 39 /*
mzta 0:158c61bb030f 40 * call-seq:
mzta 0:158c61bb030f 41 * obj.inspect -> string
mzta 0:158c61bb030f 42 *
mzta 0:158c61bb030f 43 * Returns a string containing a human-readable representation of
mzta 0:158c61bb030f 44 * <i>obj</i>. If not overridden and no instance variables, uses the
mzta 0:158c61bb030f 45 * <code>to_s</code> method to generate the string.
mzta 0:158c61bb030f 46 * <i>obj</i>. If not overridden, uses the <code>to_s</code> method to
mzta 0:158c61bb030f 47 * generate the string.
mzta 0:158c61bb030f 48 *
mzta 0:158c61bb030f 49 * [ 1, 2, 3..4, 'five' ].inspect #=> "[1, 2, 3..4, \"five\"]"
mzta 0:158c61bb030f 50 * Time.new.inspect #=> "2008-03-08 19:43:39 +0900"
mzta 0:158c61bb030f 51 */
mzta 0:158c61bb030f 52 MRB_API mrb_value
mzta 0:158c61bb030f 53 mrb_obj_inspect(mrb_state *mrb, mrb_value obj)
mzta 0:158c61bb030f 54 {
mzta 0:158c61bb030f 55 if ((mrb_type(obj) == MRB_TT_OBJECT) && mrb_obj_basic_to_s_p(mrb, obj)) {
mzta 0:158c61bb030f 56 return mrb_obj_iv_inspect(mrb, mrb_obj_ptr(obj));
mzta 0:158c61bb030f 57 }
mzta 0:158c61bb030f 58 return mrb_any_to_s(mrb, obj);
mzta 0:158c61bb030f 59 }
mzta 0:158c61bb030f 60
mzta 0:158c61bb030f 61 /* 15.3.1.3.1 */
mzta 0:158c61bb030f 62 /* 15.3.1.3.10 */
mzta 0:158c61bb030f 63 /* 15.3.1.3.11 */
mzta 0:158c61bb030f 64 /*
mzta 0:158c61bb030f 65 * call-seq:
mzta 0:158c61bb030f 66 * obj == other -> true or false
mzta 0:158c61bb030f 67 * obj.equal?(other) -> true or false
mzta 0:158c61bb030f 68 * obj.eql?(other) -> true or false
mzta 0:158c61bb030f 69 *
mzta 0:158c61bb030f 70 * Equality---At the <code>Object</code> level, <code>==</code> returns
mzta 0:158c61bb030f 71 * <code>true</code> only if <i>obj</i> and <i>other</i> are the
mzta 0:158c61bb030f 72 * same object. Typically, this method is overridden in descendant
mzta 0:158c61bb030f 73 * classes to provide class-specific meaning.
mzta 0:158c61bb030f 74 *
mzta 0:158c61bb030f 75 * Unlike <code>==</code>, the <code>equal?</code> method should never be
mzta 0:158c61bb030f 76 * overridden by subclasses: it is used to determine object identity
mzta 0:158c61bb030f 77 * (that is, <code>a.equal?(b)</code> iff <code>a</code> is the same
mzta 0:158c61bb030f 78 * object as <code>b</code>).
mzta 0:158c61bb030f 79 *
mzta 0:158c61bb030f 80 * The <code>eql?</code> method returns <code>true</code> if
mzta 0:158c61bb030f 81 * <i>obj</i> and <i>anObject</i> have the same value. Used by
mzta 0:158c61bb030f 82 * <code>Hash</code> to test members for equality. For objects of
mzta 0:158c61bb030f 83 * class <code>Object</code>, <code>eql?</code> is synonymous with
mzta 0:158c61bb030f 84 * <code>==</code>. Subclasses normally continue this tradition, but
mzta 0:158c61bb030f 85 * there are exceptions. <code>Numeric</code> types, for example,
mzta 0:158c61bb030f 86 * perform type conversion across <code>==</code>, but not across
mzta 0:158c61bb030f 87 * <code>eql?</code>, so:
mzta 0:158c61bb030f 88 *
mzta 0:158c61bb030f 89 * 1 == 1.0 #=> true
mzta 0:158c61bb030f 90 * 1.eql? 1.0 #=> false
mzta 0:158c61bb030f 91 */
mzta 0:158c61bb030f 92 static mrb_value
mzta 0:158c61bb030f 93 mrb_obj_equal_m(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 94 {
mzta 0:158c61bb030f 95 mrb_value arg;
mzta 0:158c61bb030f 96
mzta 0:158c61bb030f 97 mrb_get_args(mrb, "o", &arg);
mzta 0:158c61bb030f 98 return mrb_bool_value(mrb_obj_equal(mrb, self, arg));
mzta 0:158c61bb030f 99 }
mzta 0:158c61bb030f 100
mzta 0:158c61bb030f 101 static mrb_value
mzta 0:158c61bb030f 102 mrb_obj_not_equal_m(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 103 {
mzta 0:158c61bb030f 104 mrb_value arg;
mzta 0:158c61bb030f 105
mzta 0:158c61bb030f 106 mrb_get_args(mrb, "o", &arg);
mzta 0:158c61bb030f 107 return mrb_bool_value(!mrb_equal(mrb, self, arg));
mzta 0:158c61bb030f 108 }
mzta 0:158c61bb030f 109
mzta 0:158c61bb030f 110 /* 15.3.1.3.2 */
mzta 0:158c61bb030f 111 /*
mzta 0:158c61bb030f 112 * call-seq:
mzta 0:158c61bb030f 113 * obj === other -> true or false
mzta 0:158c61bb030f 114 *
mzta 0:158c61bb030f 115 * Case Equality---For class <code>Object</code>, effectively the same
mzta 0:158c61bb030f 116 * as calling <code>#==</code>, but typically overridden by descendants
mzta 0:158c61bb030f 117 * to provide meaningful semantics in <code>case</code> statements.
mzta 0:158c61bb030f 118 */
mzta 0:158c61bb030f 119 static mrb_value
mzta 0:158c61bb030f 120 mrb_equal_m(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 121 {
mzta 0:158c61bb030f 122 mrb_value arg;
mzta 0:158c61bb030f 123
mzta 0:158c61bb030f 124 mrb_get_args(mrb, "o", &arg);
mzta 0:158c61bb030f 125 return mrb_bool_value(mrb_equal(mrb, self, arg));
mzta 0:158c61bb030f 126 }
mzta 0:158c61bb030f 127
mzta 0:158c61bb030f 128 /* 15.3.1.3.3 */
mzta 0:158c61bb030f 129 /* 15.3.1.3.33 */
mzta 0:158c61bb030f 130 /*
mzta 0:158c61bb030f 131 * Document-method: __id__
mzta 0:158c61bb030f 132 * Document-method: object_id
mzta 0:158c61bb030f 133 *
mzta 0:158c61bb030f 134 * call-seq:
mzta 0:158c61bb030f 135 * obj.__id__ -> fixnum
mzta 0:158c61bb030f 136 * obj.object_id -> fixnum
mzta 0:158c61bb030f 137 *
mzta 0:158c61bb030f 138 * Returns an integer identifier for <i>obj</i>. The same number will
mzta 0:158c61bb030f 139 * be returned on all calls to <code>id</code> for a given object, and
mzta 0:158c61bb030f 140 * no two active objects will share an id.
mzta 0:158c61bb030f 141 * <code>Object#object_id</code> is a different concept from the
mzta 0:158c61bb030f 142 * <code>:name</code> notation, which returns the symbol id of
mzta 0:158c61bb030f 143 * <code>name</code>. Replaces the deprecated <code>Object#id</code>.
mzta 0:158c61bb030f 144 */
mzta 0:158c61bb030f 145 static mrb_value
mzta 0:158c61bb030f 146 mrb_obj_id_m(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 147 {
mzta 0:158c61bb030f 148 return mrb_fixnum_value(mrb_obj_id(self));
mzta 0:158c61bb030f 149 }
mzta 0:158c61bb030f 150
mzta 0:158c61bb030f 151 /* 15.3.1.2.2 */
mzta 0:158c61bb030f 152 /* 15.3.1.2.5 */
mzta 0:158c61bb030f 153 /* 15.3.1.3.6 */
mzta 0:158c61bb030f 154 /* 15.3.1.3.25 */
mzta 0:158c61bb030f 155 /*
mzta 0:158c61bb030f 156 * call-seq:
mzta 0:158c61bb030f 157 * block_given? -> true or false
mzta 0:158c61bb030f 158 * iterator? -> true or false
mzta 0:158c61bb030f 159 *
mzta 0:158c61bb030f 160 * Returns <code>true</code> if <code>yield</code> would execute a
mzta 0:158c61bb030f 161 * block in the current context. The <code>iterator?</code> form
mzta 0:158c61bb030f 162 * is mildly deprecated.
mzta 0:158c61bb030f 163 *
mzta 0:158c61bb030f 164 * def try
mzta 0:158c61bb030f 165 * if block_given?
mzta 0:158c61bb030f 166 * yield
mzta 0:158c61bb030f 167 * else
mzta 0:158c61bb030f 168 * "no block"
mzta 0:158c61bb030f 169 * end
mzta 0:158c61bb030f 170 * end
mzta 0:158c61bb030f 171 * try #=> "no block"
mzta 0:158c61bb030f 172 * try { "hello" } #=> "hello"
mzta 0:158c61bb030f 173 * try do "hello" end #=> "hello"
mzta 0:158c61bb030f 174 */
mzta 0:158c61bb030f 175 static mrb_value
mzta 0:158c61bb030f 176 mrb_f_block_given_p_m(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 177 {
mzta 0:158c61bb030f 178 mrb_callinfo *ci = mrb->c->ci;
mzta 0:158c61bb030f 179 mrb_value *bp;
mzta 0:158c61bb030f 180 mrb_bool given_p;
mzta 0:158c61bb030f 181
mzta 0:158c61bb030f 182 bp = ci->stackent + 1;
mzta 0:158c61bb030f 183 ci--;
mzta 0:158c61bb030f 184 if (ci <= mrb->c->cibase) {
mzta 0:158c61bb030f 185 given_p = FALSE;
mzta 0:158c61bb030f 186 }
mzta 0:158c61bb030f 187 else {
mzta 0:158c61bb030f 188 /* block_given? called within block; check upper scope */
mzta 0:158c61bb030f 189 if (ci->proc->env && ci->proc->env->stack) {
mzta 0:158c61bb030f 190 given_p = !(ci->proc->env->stack == mrb->c->stbase ||
mzta 0:158c61bb030f 191 mrb_nil_p(ci->proc->env->stack[1]));
mzta 0:158c61bb030f 192 }
mzta 0:158c61bb030f 193 else {
mzta 0:158c61bb030f 194 if (ci->argc > 0) {
mzta 0:158c61bb030f 195 bp += ci->argc;
mzta 0:158c61bb030f 196 }
mzta 0:158c61bb030f 197 given_p = !mrb_nil_p(*bp);
mzta 0:158c61bb030f 198 }
mzta 0:158c61bb030f 199 }
mzta 0:158c61bb030f 200
mzta 0:158c61bb030f 201 return mrb_bool_value(given_p);
mzta 0:158c61bb030f 202 }
mzta 0:158c61bb030f 203
mzta 0:158c61bb030f 204 /* 15.3.1.3.7 */
mzta 0:158c61bb030f 205 /*
mzta 0:158c61bb030f 206 * call-seq:
mzta 0:158c61bb030f 207 * obj.class -> class
mzta 0:158c61bb030f 208 *
mzta 0:158c61bb030f 209 * Returns the class of <i>obj</i>. This method must always be
mzta 0:158c61bb030f 210 * called with an explicit receiver, as <code>class</code> is also a
mzta 0:158c61bb030f 211 * reserved word in Ruby.
mzta 0:158c61bb030f 212 *
mzta 0:158c61bb030f 213 * 1.class #=> Fixnum
mzta 0:158c61bb030f 214 * self.class #=> Object
mzta 0:158c61bb030f 215 */
mzta 0:158c61bb030f 216 static mrb_value
mzta 0:158c61bb030f 217 mrb_obj_class_m(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 218 {
mzta 0:158c61bb030f 219 return mrb_obj_value(mrb_obj_class(mrb, self));
mzta 0:158c61bb030f 220 }
mzta 0:158c61bb030f 221
mzta 0:158c61bb030f 222 static struct RClass*
mzta 0:158c61bb030f 223 mrb_singleton_class_clone(mrb_state *mrb, mrb_value obj)
mzta 0:158c61bb030f 224 {
mzta 0:158c61bb030f 225 struct RClass *klass = mrb_basic_ptr(obj)->c;
mzta 0:158c61bb030f 226
mzta 0:158c61bb030f 227 if (klass->tt != MRB_TT_SCLASS)
mzta 0:158c61bb030f 228 return klass;
mzta 0:158c61bb030f 229 else {
mzta 0:158c61bb030f 230 /* copy singleton(unnamed) class */
mzta 0:158c61bb030f 231 struct RClass *clone = (struct RClass*)mrb_obj_alloc(mrb, klass->tt, mrb->class_class);
mzta 0:158c61bb030f 232
mzta 0:158c61bb030f 233 if ((mrb_type(obj) == MRB_TT_CLASS) ||
mzta 0:158c61bb030f 234 (mrb_type(obj) == MRB_TT_SCLASS)) { /* BUILTIN_TYPE(obj) == T_CLASS */
mzta 0:158c61bb030f 235 clone->c = clone;
mzta 0:158c61bb030f 236 }
mzta 0:158c61bb030f 237 else {
mzta 0:158c61bb030f 238 clone->c = mrb_singleton_class_clone(mrb, mrb_obj_value(klass));
mzta 0:158c61bb030f 239 }
mzta 0:158c61bb030f 240
mzta 0:158c61bb030f 241 clone->super = klass->super;
mzta 0:158c61bb030f 242 if (klass->iv) {
mzta 0:158c61bb030f 243 mrb_iv_copy(mrb, mrb_obj_value(clone), mrb_obj_value(klass));
mzta 0:158c61bb030f 244 mrb_obj_iv_set(mrb, (struct RObject*)clone, mrb_intern_lit(mrb, "__attached__"), obj);
mzta 0:158c61bb030f 245 }
mzta 0:158c61bb030f 246 if (klass->mt) {
mzta 0:158c61bb030f 247 clone->mt = kh_copy(mt, mrb, klass->mt);
mzta 0:158c61bb030f 248 }
mzta 0:158c61bb030f 249 else {
mzta 0:158c61bb030f 250 clone->mt = kh_init(mt, mrb);
mzta 0:158c61bb030f 251 }
mzta 0:158c61bb030f 252 clone->tt = MRB_TT_SCLASS;
mzta 0:158c61bb030f 253 return clone;
mzta 0:158c61bb030f 254 }
mzta 0:158c61bb030f 255 }
mzta 0:158c61bb030f 256
mzta 0:158c61bb030f 257 static void
mzta 0:158c61bb030f 258 copy_class(mrb_state *mrb, mrb_value dst, mrb_value src)
mzta 0:158c61bb030f 259 {
mzta 0:158c61bb030f 260 struct RClass *dc = mrb_class_ptr(dst);
mzta 0:158c61bb030f 261 struct RClass *sc = mrb_class_ptr(src);
mzta 0:158c61bb030f 262 dc->mt = kh_copy(mt, mrb, sc->mt);
mzta 0:158c61bb030f 263 dc->super = sc->super;
mzta 0:158c61bb030f 264 }
mzta 0:158c61bb030f 265
mzta 0:158c61bb030f 266 static void
mzta 0:158c61bb030f 267 init_copy(mrb_state *mrb, mrb_value dest, mrb_value obj)
mzta 0:158c61bb030f 268 {
mzta 0:158c61bb030f 269 switch (mrb_type(obj)) {
mzta 0:158c61bb030f 270 case MRB_TT_CLASS:
mzta 0:158c61bb030f 271 case MRB_TT_MODULE:
mzta 0:158c61bb030f 272 copy_class(mrb, dest, obj);
mzta 0:158c61bb030f 273 /* fall through */
mzta 0:158c61bb030f 274 case MRB_TT_OBJECT:
mzta 0:158c61bb030f 275 case MRB_TT_SCLASS:
mzta 0:158c61bb030f 276 case MRB_TT_HASH:
mzta 0:158c61bb030f 277 case MRB_TT_DATA:
mzta 0:158c61bb030f 278 case MRB_TT_EXCEPTION:
mzta 0:158c61bb030f 279 mrb_iv_copy(mrb, dest, obj);
mzta 0:158c61bb030f 280 break;
mzta 0:158c61bb030f 281
mzta 0:158c61bb030f 282 default:
mzta 0:158c61bb030f 283 break;
mzta 0:158c61bb030f 284 }
mzta 0:158c61bb030f 285 mrb_funcall(mrb, dest, "initialize_copy", 1, obj);
mzta 0:158c61bb030f 286 }
mzta 0:158c61bb030f 287
mzta 0:158c61bb030f 288 /* 15.3.1.3.8 */
mzta 0:158c61bb030f 289 /*
mzta 0:158c61bb030f 290 * call-seq:
mzta 0:158c61bb030f 291 * obj.clone -> an_object
mzta 0:158c61bb030f 292 *
mzta 0:158c61bb030f 293 * Produces a shallow copy of <i>obj</i>---the instance variables of
mzta 0:158c61bb030f 294 * <i>obj</i> are copied, but not the objects they reference. Copies
mzta 0:158c61bb030f 295 * the frozen state of <i>obj</i>. See also the discussion
mzta 0:158c61bb030f 296 * under <code>Object#dup</code>.
mzta 0:158c61bb030f 297 *
mzta 0:158c61bb030f 298 * class Klass
mzta 0:158c61bb030f 299 * attr_accessor :str
mzta 0:158c61bb030f 300 * end
mzta 0:158c61bb030f 301 * s1 = Klass.new #=> #<Klass:0x401b3a38>
mzta 0:158c61bb030f 302 * s1.str = "Hello" #=> "Hello"
mzta 0:158c61bb030f 303 * s2 = s1.clone #=> #<Klass:0x401b3998 @str="Hello">
mzta 0:158c61bb030f 304 * s2.str[1,4] = "i" #=> "i"
mzta 0:158c61bb030f 305 * s1.inspect #=> "#<Klass:0x401b3a38 @str=\"Hi\">"
mzta 0:158c61bb030f 306 * s2.inspect #=> "#<Klass:0x401b3998 @str=\"Hi\">"
mzta 0:158c61bb030f 307 *
mzta 0:158c61bb030f 308 * This method may have class-specific behavior. If so, that
mzta 0:158c61bb030f 309 * behavior will be documented under the #+initialize_copy+ method of
mzta 0:158c61bb030f 310 * the class.
mzta 0:158c61bb030f 311 *
mzta 0:158c61bb030f 312 * Some Class(True False Nil Symbol Fixnum Float) Object cannot clone.
mzta 0:158c61bb030f 313 */
mzta 0:158c61bb030f 314 MRB_API mrb_value
mzta 0:158c61bb030f 315 mrb_obj_clone(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 316 {
mzta 0:158c61bb030f 317 struct RObject *p;
mzta 0:158c61bb030f 318 mrb_value clone;
mzta 0:158c61bb030f 319
mzta 0:158c61bb030f 320 if (mrb_immediate_p(self)) {
mzta 0:158c61bb030f 321 mrb_raisef(mrb, E_TYPE_ERROR, "can't clone %S", self);
mzta 0:158c61bb030f 322 }
mzta 0:158c61bb030f 323 p = (struct RObject*)mrb_obj_alloc(mrb, mrb_type(self), mrb_obj_class(mrb, self));
mzta 0:158c61bb030f 324 p->c = mrb_singleton_class_clone(mrb, self);
mzta 0:158c61bb030f 325 clone = mrb_obj_value(p);
mzta 0:158c61bb030f 326 init_copy(mrb, clone, self);
mzta 0:158c61bb030f 327
mzta 0:158c61bb030f 328 return clone;
mzta 0:158c61bb030f 329 }
mzta 0:158c61bb030f 330
mzta 0:158c61bb030f 331 /* 15.3.1.3.9 */
mzta 0:158c61bb030f 332 /*
mzta 0:158c61bb030f 333 * call-seq:
mzta 0:158c61bb030f 334 * obj.dup -> an_object
mzta 0:158c61bb030f 335 *
mzta 0:158c61bb030f 336 * Produces a shallow copy of <i>obj</i>---the instance variables of
mzta 0:158c61bb030f 337 * <i>obj</i> are copied, but not the objects they reference.
mzta 0:158c61bb030f 338 * <code>dup</code> copies the frozen state of <i>obj</i>. See also
mzta 0:158c61bb030f 339 * the discussion under <code>Object#clone</code>. In general,
mzta 0:158c61bb030f 340 * <code>clone</code> and <code>dup</code> may have different semantics
mzta 0:158c61bb030f 341 * in descendant classes. While <code>clone</code> is used to duplicate
mzta 0:158c61bb030f 342 * an object, including its internal state, <code>dup</code> typically
mzta 0:158c61bb030f 343 * uses the class of the descendant object to create the new instance.
mzta 0:158c61bb030f 344 *
mzta 0:158c61bb030f 345 * This method may have class-specific behavior. If so, that
mzta 0:158c61bb030f 346 * behavior will be documented under the #+initialize_copy+ method of
mzta 0:158c61bb030f 347 * the class.
mzta 0:158c61bb030f 348 */
mzta 0:158c61bb030f 349
mzta 0:158c61bb030f 350 MRB_API mrb_value
mzta 0:158c61bb030f 351 mrb_obj_dup(mrb_state *mrb, mrb_value obj)
mzta 0:158c61bb030f 352 {
mzta 0:158c61bb030f 353 struct RBasic *p;
mzta 0:158c61bb030f 354 mrb_value dup;
mzta 0:158c61bb030f 355
mzta 0:158c61bb030f 356 if (mrb_immediate_p(obj)) {
mzta 0:158c61bb030f 357 mrb_raisef(mrb, E_TYPE_ERROR, "can't dup %S", obj);
mzta 0:158c61bb030f 358 }
mzta 0:158c61bb030f 359 p = mrb_obj_alloc(mrb, mrb_type(obj), mrb_obj_class(mrb, obj));
mzta 0:158c61bb030f 360 dup = mrb_obj_value(p);
mzta 0:158c61bb030f 361 init_copy(mrb, dup, obj);
mzta 0:158c61bb030f 362
mzta 0:158c61bb030f 363 return dup;
mzta 0:158c61bb030f 364 }
mzta 0:158c61bb030f 365
mzta 0:158c61bb030f 366 static mrb_value
mzta 0:158c61bb030f 367 mrb_obj_extend(mrb_state *mrb, mrb_int argc, mrb_value *argv, mrb_value obj)
mzta 0:158c61bb030f 368 {
mzta 0:158c61bb030f 369 mrb_int i;
mzta 0:158c61bb030f 370
mzta 0:158c61bb030f 371 if (argc == 0) {
mzta 0:158c61bb030f 372 mrb_raise(mrb, E_ARGUMENT_ERROR, "wrong number of arguments (at least 1)");
mzta 0:158c61bb030f 373 }
mzta 0:158c61bb030f 374 for (i = 0; i < argc; i++) {
mzta 0:158c61bb030f 375 mrb_check_type(mrb, argv[i], MRB_TT_MODULE);
mzta 0:158c61bb030f 376 }
mzta 0:158c61bb030f 377 while (argc--) {
mzta 0:158c61bb030f 378 mrb_funcall(mrb, argv[argc], "extend_object", 1, obj);
mzta 0:158c61bb030f 379 mrb_funcall(mrb, argv[argc], "extended", 1, obj);
mzta 0:158c61bb030f 380 }
mzta 0:158c61bb030f 381 return obj;
mzta 0:158c61bb030f 382 }
mzta 0:158c61bb030f 383
mzta 0:158c61bb030f 384 /* 15.3.1.3.13 */
mzta 0:158c61bb030f 385 /*
mzta 0:158c61bb030f 386 * call-seq:
mzta 0:158c61bb030f 387 * obj.extend(module, ...) -> obj
mzta 0:158c61bb030f 388 *
mzta 0:158c61bb030f 389 * Adds to _obj_ the instance methods from each module given as a
mzta 0:158c61bb030f 390 * parameter.
mzta 0:158c61bb030f 391 *
mzta 0:158c61bb030f 392 * module Mod
mzta 0:158c61bb030f 393 * def hello
mzta 0:158c61bb030f 394 * "Hello from Mod.\n"
mzta 0:158c61bb030f 395 * end
mzta 0:158c61bb030f 396 * end
mzta 0:158c61bb030f 397 *
mzta 0:158c61bb030f 398 * class Klass
mzta 0:158c61bb030f 399 * def hello
mzta 0:158c61bb030f 400 * "Hello from Klass.\n"
mzta 0:158c61bb030f 401 * end
mzta 0:158c61bb030f 402 * end
mzta 0:158c61bb030f 403 *
mzta 0:158c61bb030f 404 * k = Klass.new
mzta 0:158c61bb030f 405 * k.hello #=> "Hello from Klass.\n"
mzta 0:158c61bb030f 406 * k.extend(Mod) #=> #<Klass:0x401b3bc8>
mzta 0:158c61bb030f 407 * k.hello #=> "Hello from Mod.\n"
mzta 0:158c61bb030f 408 */
mzta 0:158c61bb030f 409 static mrb_value
mzta 0:158c61bb030f 410 mrb_obj_extend_m(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 411 {
mzta 0:158c61bb030f 412 mrb_value *argv;
mzta 0:158c61bb030f 413 mrb_int argc;
mzta 0:158c61bb030f 414
mzta 0:158c61bb030f 415 mrb_get_args(mrb, "*", &argv, &argc);
mzta 0:158c61bb030f 416 return mrb_obj_extend(mrb, argc, argv, self);
mzta 0:158c61bb030f 417 }
mzta 0:158c61bb030f 418
mzta 0:158c61bb030f 419 /* 15.3.1.3.15 */
mzta 0:158c61bb030f 420 /*
mzta 0:158c61bb030f 421 * call-seq:
mzta 0:158c61bb030f 422 * obj.hash -> fixnum
mzta 0:158c61bb030f 423 *
mzta 0:158c61bb030f 424 * Generates a <code>Fixnum</code> hash value for this object. This
mzta 0:158c61bb030f 425 * function must have the property that <code>a.eql?(b)</code> implies
mzta 0:158c61bb030f 426 * <code>a.hash == b.hash</code>. The hash value is used by class
mzta 0:158c61bb030f 427 * <code>Hash</code>. Any hash value that exceeds the capacity of a
mzta 0:158c61bb030f 428 * <code>Fixnum</code> will be truncated before being used.
mzta 0:158c61bb030f 429 */
mzta 0:158c61bb030f 430 MRB_API mrb_value
mzta 0:158c61bb030f 431 mrb_obj_hash(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 432 {
mzta 0:158c61bb030f 433 return mrb_fixnum_value(mrb_obj_id(self));
mzta 0:158c61bb030f 434 }
mzta 0:158c61bb030f 435
mzta 0:158c61bb030f 436 /* 15.3.1.3.16 */
mzta 0:158c61bb030f 437 static mrb_value
mzta 0:158c61bb030f 438 mrb_obj_init_copy(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 439 {
mzta 0:158c61bb030f 440 mrb_value orig;
mzta 0:158c61bb030f 441
mzta 0:158c61bb030f 442 mrb_get_args(mrb, "o", &orig);
mzta 0:158c61bb030f 443 if (mrb_obj_equal(mrb, self, orig)) return self;
mzta 0:158c61bb030f 444 if ((mrb_type(self) != mrb_type(orig)) || (mrb_obj_class(mrb, self) != mrb_obj_class(mrb, orig))) {
mzta 0:158c61bb030f 445 mrb_raise(mrb, E_TYPE_ERROR, "initialize_copy should take same class object");
mzta 0:158c61bb030f 446 }
mzta 0:158c61bb030f 447 return self;
mzta 0:158c61bb030f 448 }
mzta 0:158c61bb030f 449
mzta 0:158c61bb030f 450
mzta 0:158c61bb030f 451 /* implementation of instance_eval */
mzta 0:158c61bb030f 452 mrb_value mrb_obj_instance_eval(mrb_state*, mrb_value);
mzta 0:158c61bb030f 453
mzta 0:158c61bb030f 454 MRB_API mrb_bool
mzta 0:158c61bb030f 455 mrb_obj_is_instance_of(mrb_state *mrb, mrb_value obj, struct RClass* c)
mzta 0:158c61bb030f 456 {
mzta 0:158c61bb030f 457 if (mrb_obj_class(mrb, obj) == c) return TRUE;
mzta 0:158c61bb030f 458 return FALSE;
mzta 0:158c61bb030f 459 }
mzta 0:158c61bb030f 460
mzta 0:158c61bb030f 461 /* 15.3.1.3.19 */
mzta 0:158c61bb030f 462 /*
mzta 0:158c61bb030f 463 * call-seq:
mzta 0:158c61bb030f 464 * obj.instance_of?(class) -> true or false
mzta 0:158c61bb030f 465 *
mzta 0:158c61bb030f 466 * Returns <code>true</code> if <i>obj</i> is an instance of the given
mzta 0:158c61bb030f 467 * class. See also <code>Object#kind_of?</code>.
mzta 0:158c61bb030f 468 */
mzta 0:158c61bb030f 469 static mrb_value
mzta 0:158c61bb030f 470 obj_is_instance_of(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 471 {
mzta 0:158c61bb030f 472 mrb_value arg;
mzta 0:158c61bb030f 473
mzta 0:158c61bb030f 474 mrb_get_args(mrb, "C", &arg);
mzta 0:158c61bb030f 475
mzta 0:158c61bb030f 476 return mrb_bool_value(mrb_obj_is_instance_of(mrb, self, mrb_class_ptr(arg)));
mzta 0:158c61bb030f 477 }
mzta 0:158c61bb030f 478
mzta 0:158c61bb030f 479 /* 15.3.1.3.20 */
mzta 0:158c61bb030f 480 /*
mzta 0:158c61bb030f 481 * call-seq:
mzta 0:158c61bb030f 482 * obj.instance_variable_defined?(symbol) -> true or false
mzta 0:158c61bb030f 483 *
mzta 0:158c61bb030f 484 * Returns <code>true</code> if the given instance variable is
mzta 0:158c61bb030f 485 * defined in <i>obj</i>.
mzta 0:158c61bb030f 486 *
mzta 0:158c61bb030f 487 * class Fred
mzta 0:158c61bb030f 488 * def initialize(p1, p2)
mzta 0:158c61bb030f 489 * @a, @b = p1, p2
mzta 0:158c61bb030f 490 * end
mzta 0:158c61bb030f 491 * end
mzta 0:158c61bb030f 492 * fred = Fred.new('cat', 99)
mzta 0:158c61bb030f 493 * fred.instance_variable_defined?(:@a) #=> true
mzta 0:158c61bb030f 494 * fred.instance_variable_defined?("@b") #=> true
mzta 0:158c61bb030f 495 * fred.instance_variable_defined?("@c") #=> false
mzta 0:158c61bb030f 496 */
mzta 0:158c61bb030f 497 static mrb_value
mzta 0:158c61bb030f 498 mrb_obj_ivar_defined(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 499 {
mzta 0:158c61bb030f 500 mrb_sym sym;
mzta 0:158c61bb030f 501
mzta 0:158c61bb030f 502 mrb_get_args(mrb, "n", &sym);
mzta 0:158c61bb030f 503 mrb_iv_check(mrb, sym);
mzta 0:158c61bb030f 504 return mrb_bool_value(mrb_iv_defined(mrb, self, sym));
mzta 0:158c61bb030f 505 }
mzta 0:158c61bb030f 506
mzta 0:158c61bb030f 507 /* 15.3.1.3.21 */
mzta 0:158c61bb030f 508 /*
mzta 0:158c61bb030f 509 * call-seq:
mzta 0:158c61bb030f 510 * obj.instance_variable_get(symbol) -> obj
mzta 0:158c61bb030f 511 *
mzta 0:158c61bb030f 512 * Returns the value of the given instance variable, or nil if the
mzta 0:158c61bb030f 513 * instance variable is not set. The <code>@</code> part of the
mzta 0:158c61bb030f 514 * variable name should be included for regular instance
mzta 0:158c61bb030f 515 * variables. Throws a <code>NameError</code> exception if the
mzta 0:158c61bb030f 516 * supplied symbol is not valid as an instance variable name.
mzta 0:158c61bb030f 517 *
mzta 0:158c61bb030f 518 * class Fred
mzta 0:158c61bb030f 519 * def initialize(p1, p2)
mzta 0:158c61bb030f 520 * @a, @b = p1, p2
mzta 0:158c61bb030f 521 * end
mzta 0:158c61bb030f 522 * end
mzta 0:158c61bb030f 523 * fred = Fred.new('cat', 99)
mzta 0:158c61bb030f 524 * fred.instance_variable_get(:@a) #=> "cat"
mzta 0:158c61bb030f 525 * fred.instance_variable_get("@b") #=> 99
mzta 0:158c61bb030f 526 */
mzta 0:158c61bb030f 527 static mrb_value
mzta 0:158c61bb030f 528 mrb_obj_ivar_get(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 529 {
mzta 0:158c61bb030f 530 mrb_sym iv_name;
mzta 0:158c61bb030f 531
mzta 0:158c61bb030f 532 mrb_get_args(mrb, "n", &iv_name);
mzta 0:158c61bb030f 533 mrb_iv_check(mrb, iv_name);
mzta 0:158c61bb030f 534 return mrb_iv_get(mrb, self, iv_name);
mzta 0:158c61bb030f 535 }
mzta 0:158c61bb030f 536
mzta 0:158c61bb030f 537 /* 15.3.1.3.22 */
mzta 0:158c61bb030f 538 /*
mzta 0:158c61bb030f 539 * call-seq:
mzta 0:158c61bb030f 540 * obj.instance_variable_set(symbol, obj) -> obj
mzta 0:158c61bb030f 541 *
mzta 0:158c61bb030f 542 * Sets the instance variable names by <i>symbol</i> to
mzta 0:158c61bb030f 543 * <i>object</i>, thereby frustrating the efforts of the class's
mzta 0:158c61bb030f 544 * author to attempt to provide proper encapsulation. The variable
mzta 0:158c61bb030f 545 * did not have to exist prior to this call.
mzta 0:158c61bb030f 546 *
mzta 0:158c61bb030f 547 * class Fred
mzta 0:158c61bb030f 548 * def initialize(p1, p2)
mzta 0:158c61bb030f 549 * @a, @b = p1, p2
mzta 0:158c61bb030f 550 * end
mzta 0:158c61bb030f 551 * end
mzta 0:158c61bb030f 552 * fred = Fred.new('cat', 99)
mzta 0:158c61bb030f 553 * fred.instance_variable_set(:@a, 'dog') #=> "dog"
mzta 0:158c61bb030f 554 * fred.instance_variable_set(:@c, 'cat') #=> "cat"
mzta 0:158c61bb030f 555 * fred.inspect #=> "#<Fred:0x401b3da8 @a=\"dog\", @b=99, @c=\"cat\">"
mzta 0:158c61bb030f 556 */
mzta 0:158c61bb030f 557 static mrb_value
mzta 0:158c61bb030f 558 mrb_obj_ivar_set(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 559 {
mzta 0:158c61bb030f 560 mrb_sym iv_name;
mzta 0:158c61bb030f 561 mrb_value val;
mzta 0:158c61bb030f 562
mzta 0:158c61bb030f 563 mrb_get_args(mrb, "no", &iv_name, &val);
mzta 0:158c61bb030f 564 mrb_iv_check(mrb, iv_name);
mzta 0:158c61bb030f 565 mrb_iv_set(mrb, self, iv_name, val);
mzta 0:158c61bb030f 566 return val;
mzta 0:158c61bb030f 567 }
mzta 0:158c61bb030f 568
mzta 0:158c61bb030f 569 /* 15.3.1.3.24 */
mzta 0:158c61bb030f 570 /* 15.3.1.3.26 */
mzta 0:158c61bb030f 571 /*
mzta 0:158c61bb030f 572 * call-seq:
mzta 0:158c61bb030f 573 * obj.is_a?(class) -> true or false
mzta 0:158c61bb030f 574 * obj.kind_of?(class) -> true or false
mzta 0:158c61bb030f 575 *
mzta 0:158c61bb030f 576 * Returns <code>true</code> if <i>class</i> is the class of
mzta 0:158c61bb030f 577 * <i>obj</i>, or if <i>class</i> is one of the superclasses of
mzta 0:158c61bb030f 578 * <i>obj</i> or modules included in <i>obj</i>.
mzta 0:158c61bb030f 579 *
mzta 0:158c61bb030f 580 * module M; end
mzta 0:158c61bb030f 581 * class A
mzta 0:158c61bb030f 582 * include M
mzta 0:158c61bb030f 583 * end
mzta 0:158c61bb030f 584 * class B < A; end
mzta 0:158c61bb030f 585 * class C < B; end
mzta 0:158c61bb030f 586 * b = B.new
mzta 0:158c61bb030f 587 * b.instance_of? A #=> false
mzta 0:158c61bb030f 588 * b.instance_of? B #=> true
mzta 0:158c61bb030f 589 * b.instance_of? C #=> false
mzta 0:158c61bb030f 590 * b.instance_of? M #=> false
mzta 0:158c61bb030f 591 * b.kind_of? A #=> true
mzta 0:158c61bb030f 592 * b.kind_of? B #=> true
mzta 0:158c61bb030f 593 * b.kind_of? C #=> false
mzta 0:158c61bb030f 594 * b.kind_of? M #=> true
mzta 0:158c61bb030f 595 */
mzta 0:158c61bb030f 596 static mrb_value
mzta 0:158c61bb030f 597 mrb_obj_is_kind_of_m(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 598 {
mzta 0:158c61bb030f 599 mrb_value arg;
mzta 0:158c61bb030f 600
mzta 0:158c61bb030f 601 mrb_get_args(mrb, "C", &arg);
mzta 0:158c61bb030f 602
mzta 0:158c61bb030f 603 return mrb_bool_value(mrb_obj_is_kind_of(mrb, self, mrb_class_ptr(arg)));
mzta 0:158c61bb030f 604 }
mzta 0:158c61bb030f 605
mzta 0:158c61bb030f 606 KHASH_DECLARE(st, mrb_sym, char, FALSE)
mzta 0:158c61bb030f 607 KHASH_DEFINE(st, mrb_sym, char, FALSE, kh_int_hash_func, kh_int_hash_equal)
mzta 0:158c61bb030f 608
mzta 0:158c61bb030f 609 static void
mzta 0:158c61bb030f 610 method_entry_loop(mrb_state *mrb, struct RClass* klass, khash_t(st)* set)
mzta 0:158c61bb030f 611 {
mzta 0:158c61bb030f 612 khint_t i;
mzta 0:158c61bb030f 613
mzta 0:158c61bb030f 614 khash_t(mt) *h = klass->mt;
mzta 0:158c61bb030f 615 if (!h) return;
mzta 0:158c61bb030f 616 for (i=0;i<kh_end(h);i++) {
mzta 0:158c61bb030f 617 if (kh_exist(h, i) && kh_value(h, i)) {
mzta 0:158c61bb030f 618 kh_put(st, mrb, set, kh_key(h, i));
mzta 0:158c61bb030f 619 }
mzta 0:158c61bb030f 620 }
mzta 0:158c61bb030f 621 }
mzta 0:158c61bb030f 622
mzta 0:158c61bb030f 623 mrb_value
mzta 0:158c61bb030f 624 mrb_class_instance_method_list(mrb_state *mrb, mrb_bool recur, struct RClass* klass, int obj)
mzta 0:158c61bb030f 625 {
mzta 0:158c61bb030f 626 khint_t i;
mzta 0:158c61bb030f 627 mrb_value ary;
mzta 0:158c61bb030f 628 struct RClass* oldklass;
mzta 0:158c61bb030f 629 khash_t(st)* set = kh_init(st, mrb);
mzta 0:158c61bb030f 630
mzta 0:158c61bb030f 631 oldklass = 0;
mzta 0:158c61bb030f 632 while (klass && (klass != oldklass)) {
mzta 0:158c61bb030f 633 method_entry_loop(mrb, klass, set);
mzta 0:158c61bb030f 634 if ((klass->tt == MRB_TT_ICLASS) ||
mzta 0:158c61bb030f 635 (klass->tt == MRB_TT_SCLASS)) {
mzta 0:158c61bb030f 636 }
mzta 0:158c61bb030f 637 else {
mzta 0:158c61bb030f 638 if (!recur) break;
mzta 0:158c61bb030f 639 }
mzta 0:158c61bb030f 640 oldklass = klass;
mzta 0:158c61bb030f 641 klass = klass->super;
mzta 0:158c61bb030f 642 }
mzta 0:158c61bb030f 643
mzta 0:158c61bb030f 644 ary = mrb_ary_new(mrb);
mzta 0:158c61bb030f 645 for (i=0;i<kh_end(set);i++) {
mzta 0:158c61bb030f 646 if (kh_exist(set, i)) {
mzta 0:158c61bb030f 647 mrb_ary_push(mrb, ary, mrb_symbol_value(kh_key(set, i)));
mzta 0:158c61bb030f 648 }
mzta 0:158c61bb030f 649 }
mzta 0:158c61bb030f 650 kh_destroy(st, mrb, set);
mzta 0:158c61bb030f 651
mzta 0:158c61bb030f 652 return ary;
mzta 0:158c61bb030f 653 }
mzta 0:158c61bb030f 654
mzta 0:158c61bb030f 655 static mrb_value
mzta 0:158c61bb030f 656 mrb_obj_singleton_methods(mrb_state *mrb, mrb_bool recur, mrb_value obj)
mzta 0:158c61bb030f 657 {
mzta 0:158c61bb030f 658 khint_t i;
mzta 0:158c61bb030f 659 mrb_value ary;
mzta 0:158c61bb030f 660 struct RClass* klass;
mzta 0:158c61bb030f 661 khash_t(st)* set = kh_init(st, mrb);
mzta 0:158c61bb030f 662
mzta 0:158c61bb030f 663 klass = mrb_class(mrb, obj);
mzta 0:158c61bb030f 664
mzta 0:158c61bb030f 665 if (klass && (klass->tt == MRB_TT_SCLASS)) {
mzta 0:158c61bb030f 666 method_entry_loop(mrb, klass, set);
mzta 0:158c61bb030f 667 klass = klass->super;
mzta 0:158c61bb030f 668 }
mzta 0:158c61bb030f 669 if (recur) {
mzta 0:158c61bb030f 670 while (klass && ((klass->tt == MRB_TT_SCLASS) || (klass->tt == MRB_TT_ICLASS))) {
mzta 0:158c61bb030f 671 method_entry_loop(mrb, klass, set);
mzta 0:158c61bb030f 672 klass = klass->super;
mzta 0:158c61bb030f 673 }
mzta 0:158c61bb030f 674 }
mzta 0:158c61bb030f 675
mzta 0:158c61bb030f 676 ary = mrb_ary_new(mrb);
mzta 0:158c61bb030f 677 for (i=0;i<kh_end(set);i++) {
mzta 0:158c61bb030f 678 if (kh_exist(set, i)) {
mzta 0:158c61bb030f 679 mrb_ary_push(mrb, ary, mrb_symbol_value(kh_key(set, i)));
mzta 0:158c61bb030f 680 }
mzta 0:158c61bb030f 681 }
mzta 0:158c61bb030f 682 kh_destroy(st, mrb, set);
mzta 0:158c61bb030f 683
mzta 0:158c61bb030f 684 return ary;
mzta 0:158c61bb030f 685 }
mzta 0:158c61bb030f 686
mzta 0:158c61bb030f 687 static mrb_value
mzta 0:158c61bb030f 688 mrb_obj_methods(mrb_state *mrb, mrb_bool recur, mrb_value obj, mrb_method_flag_t flag)
mzta 0:158c61bb030f 689 {
mzta 0:158c61bb030f 690 if (recur)
mzta 0:158c61bb030f 691 return mrb_class_instance_method_list(mrb, recur, mrb_class(mrb, obj), 0);
mzta 0:158c61bb030f 692 return mrb_obj_singleton_methods(mrb, recur, obj);
mzta 0:158c61bb030f 693 }
mzta 0:158c61bb030f 694 /* 15.3.1.3.31 */
mzta 0:158c61bb030f 695 /*
mzta 0:158c61bb030f 696 * call-seq:
mzta 0:158c61bb030f 697 * obj.methods -> array
mzta 0:158c61bb030f 698 *
mzta 0:158c61bb030f 699 * Returns a list of the names of methods publicly accessible in
mzta 0:158c61bb030f 700 * <i>obj</i>. This will include all the methods accessible in
mzta 0:158c61bb030f 701 * <i>obj</i>'s ancestors.
mzta 0:158c61bb030f 702 *
mzta 0:158c61bb030f 703 * class Klass
mzta 0:158c61bb030f 704 * def kMethod()
mzta 0:158c61bb030f 705 * end
mzta 0:158c61bb030f 706 * end
mzta 0:158c61bb030f 707 * k = Klass.new
mzta 0:158c61bb030f 708 * k.methods[0..9] #=> [:kMethod, :respond_to?, :nil?, :is_a?,
mzta 0:158c61bb030f 709 * # :class, :instance_variable_set,
mzta 0:158c61bb030f 710 * # :methods, :extend, :__send__, :instance_eval]
mzta 0:158c61bb030f 711 * k.methods.length #=> 42
mzta 0:158c61bb030f 712 */
mzta 0:158c61bb030f 713 static mrb_value
mzta 0:158c61bb030f 714 mrb_obj_methods_m(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 715 {
mzta 0:158c61bb030f 716 mrb_bool recur = TRUE;
mzta 0:158c61bb030f 717 mrb_get_args(mrb, "|b", &recur);
mzta 0:158c61bb030f 718 return mrb_obj_methods(mrb, recur, self, (mrb_method_flag_t)0); /* everything but private */
mzta 0:158c61bb030f 719 }
mzta 0:158c61bb030f 720
mzta 0:158c61bb030f 721 /* 15.3.1.3.32 */
mzta 0:158c61bb030f 722 /*
mzta 0:158c61bb030f 723 * call_seq:
mzta 0:158c61bb030f 724 * nil.nil? -> true
mzta 0:158c61bb030f 725 * <anything_else>.nil? -> false
mzta 0:158c61bb030f 726 *
mzta 0:158c61bb030f 727 * Only the object <i>nil</i> responds <code>true</code> to <code>nil?</code>.
mzta 0:158c61bb030f 728 */
mzta 0:158c61bb030f 729 static mrb_value
mzta 0:158c61bb030f 730 mrb_false(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 731 {
mzta 0:158c61bb030f 732 return mrb_false_value();
mzta 0:158c61bb030f 733 }
mzta 0:158c61bb030f 734
mzta 0:158c61bb030f 735 /* 15.3.1.3.36 */
mzta 0:158c61bb030f 736 /*
mzta 0:158c61bb030f 737 * call-seq:
mzta 0:158c61bb030f 738 * obj.private_methods(all=true) -> array
mzta 0:158c61bb030f 739 *
mzta 0:158c61bb030f 740 * Returns the list of private methods accessible to <i>obj</i>. If
mzta 0:158c61bb030f 741 * the <i>all</i> parameter is set to <code>false</code>, only those methods
mzta 0:158c61bb030f 742 * in the receiver will be listed.
mzta 0:158c61bb030f 743 */
mzta 0:158c61bb030f 744 static mrb_value
mzta 0:158c61bb030f 745 mrb_obj_private_methods(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 746 {
mzta 0:158c61bb030f 747 mrb_bool recur = TRUE;
mzta 0:158c61bb030f 748 mrb_get_args(mrb, "|b", &recur);
mzta 0:158c61bb030f 749 return mrb_obj_methods(mrb, recur, self, NOEX_PRIVATE); /* private attribute not define */
mzta 0:158c61bb030f 750 }
mzta 0:158c61bb030f 751
mzta 0:158c61bb030f 752 /* 15.3.1.3.37 */
mzta 0:158c61bb030f 753 /*
mzta 0:158c61bb030f 754 * call-seq:
mzta 0:158c61bb030f 755 * obj.protected_methods(all=true) -> array
mzta 0:158c61bb030f 756 *
mzta 0:158c61bb030f 757 * Returns the list of protected methods accessible to <i>obj</i>. If
mzta 0:158c61bb030f 758 * the <i>all</i> parameter is set to <code>false</code>, only those methods
mzta 0:158c61bb030f 759 * in the receiver will be listed.
mzta 0:158c61bb030f 760 */
mzta 0:158c61bb030f 761 static mrb_value
mzta 0:158c61bb030f 762 mrb_obj_protected_methods(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 763 {
mzta 0:158c61bb030f 764 mrb_bool recur = TRUE;
mzta 0:158c61bb030f 765 mrb_get_args(mrb, "|b", &recur);
mzta 0:158c61bb030f 766 return mrb_obj_methods(mrb, recur, self, NOEX_PROTECTED); /* protected attribute not define */
mzta 0:158c61bb030f 767 }
mzta 0:158c61bb030f 768
mzta 0:158c61bb030f 769 /* 15.3.1.3.38 */
mzta 0:158c61bb030f 770 /*
mzta 0:158c61bb030f 771 * call-seq:
mzta 0:158c61bb030f 772 * obj.public_methods(all=true) -> array
mzta 0:158c61bb030f 773 *
mzta 0:158c61bb030f 774 * Returns the list of public methods accessible to <i>obj</i>. If
mzta 0:158c61bb030f 775 * the <i>all</i> parameter is set to <code>false</code>, only those methods
mzta 0:158c61bb030f 776 * in the receiver will be listed.
mzta 0:158c61bb030f 777 */
mzta 0:158c61bb030f 778 static mrb_value
mzta 0:158c61bb030f 779 mrb_obj_public_methods(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 780 {
mzta 0:158c61bb030f 781 mrb_bool recur = TRUE;
mzta 0:158c61bb030f 782 mrb_get_args(mrb, "|b", &recur);
mzta 0:158c61bb030f 783 return mrb_obj_methods(mrb, recur, self, NOEX_PUBLIC); /* public attribute not define */
mzta 0:158c61bb030f 784 }
mzta 0:158c61bb030f 785
mzta 0:158c61bb030f 786 /* 15.3.1.2.12 */
mzta 0:158c61bb030f 787 /* 15.3.1.3.40 */
mzta 0:158c61bb030f 788 /*
mzta 0:158c61bb030f 789 * call-seq:
mzta 0:158c61bb030f 790 * raise
mzta 0:158c61bb030f 791 * raise(string)
mzta 0:158c61bb030f 792 * raise(exception [, string])
mzta 0:158c61bb030f 793 *
mzta 0:158c61bb030f 794 * With no arguments, raises a <code>RuntimeError</code>
mzta 0:158c61bb030f 795 * With a single +String+ argument, raises a
mzta 0:158c61bb030f 796 * +RuntimeError+ with the string as a message. Otherwise,
mzta 0:158c61bb030f 797 * the first parameter should be the name of an +Exception+
mzta 0:158c61bb030f 798 * class (or an object that returns an +Exception+ object when sent
mzta 0:158c61bb030f 799 * an +exception+ message). The optional second parameter sets the
mzta 0:158c61bb030f 800 * message associated with the exception, and the third parameter is an
mzta 0:158c61bb030f 801 * array of callback information. Exceptions are caught by the
mzta 0:158c61bb030f 802 * +rescue+ clause of <code>begin...end</code> blocks.
mzta 0:158c61bb030f 803 *
mzta 0:158c61bb030f 804 * raise "Failed to create socket"
mzta 0:158c61bb030f 805 * raise ArgumentError, "No parameters", caller
mzta 0:158c61bb030f 806 */
mzta 0:158c61bb030f 807 MRB_API mrb_value
mzta 0:158c61bb030f 808 mrb_f_raise(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 809 {
mzta 0:158c61bb030f 810 mrb_value a[2], exc;
mzta 0:158c61bb030f 811 int argc;
mzta 0:158c61bb030f 812
mzta 0:158c61bb030f 813
mzta 0:158c61bb030f 814 argc = mrb_get_args(mrb, "|oo", &a[0], &a[1]);
mzta 0:158c61bb030f 815 switch (argc) {
mzta 0:158c61bb030f 816 case 0:
mzta 0:158c61bb030f 817 mrb_raise(mrb, E_RUNTIME_ERROR, "");
mzta 0:158c61bb030f 818 break;
mzta 0:158c61bb030f 819 case 1:
mzta 0:158c61bb030f 820 a[1] = mrb_check_string_type(mrb, a[0]);
mzta 0:158c61bb030f 821 if (!mrb_nil_p(a[1])) {
mzta 0:158c61bb030f 822 argc = 2;
mzta 0:158c61bb030f 823 a[0] = mrb_obj_value(E_RUNTIME_ERROR);
mzta 0:158c61bb030f 824 }
mzta 0:158c61bb030f 825 /* fall through */
mzta 0:158c61bb030f 826 default:
mzta 0:158c61bb030f 827 exc = mrb_make_exception(mrb, argc, a);
mzta 0:158c61bb030f 828 mrb_obj_iv_set(mrb, mrb_obj_ptr(exc), mrb_intern_lit(mrb, "lastpc"), mrb_cptr_value(mrb, mrb->c->ci->pc));
mzta 0:158c61bb030f 829 mrb_exc_raise(mrb, exc);
mzta 0:158c61bb030f 830 break;
mzta 0:158c61bb030f 831 }
mzta 0:158c61bb030f 832 return mrb_nil_value(); /* not reached */
mzta 0:158c61bb030f 833 }
mzta 0:158c61bb030f 834
mzta 0:158c61bb030f 835 /* 15.3.1.3.41 */
mzta 0:158c61bb030f 836 /*
mzta 0:158c61bb030f 837 * call-seq:
mzta 0:158c61bb030f 838 * obj.remove_instance_variable(symbol) -> obj
mzta 0:158c61bb030f 839 *
mzta 0:158c61bb030f 840 * Removes the named instance variable from <i>obj</i>, returning that
mzta 0:158c61bb030f 841 * variable's value.
mzta 0:158c61bb030f 842 *
mzta 0:158c61bb030f 843 * class Dummy
mzta 0:158c61bb030f 844 * attr_reader :var
mzta 0:158c61bb030f 845 * def initialize
mzta 0:158c61bb030f 846 * @var = 99
mzta 0:158c61bb030f 847 * end
mzta 0:158c61bb030f 848 * def remove
mzta 0:158c61bb030f 849 * remove_instance_variable(:@var)
mzta 0:158c61bb030f 850 * end
mzta 0:158c61bb030f 851 * end
mzta 0:158c61bb030f 852 * d = Dummy.new
mzta 0:158c61bb030f 853 * d.var #=> 99
mzta 0:158c61bb030f 854 * d.remove #=> 99
mzta 0:158c61bb030f 855 * d.var #=> nil
mzta 0:158c61bb030f 856 */
mzta 0:158c61bb030f 857 static mrb_value
mzta 0:158c61bb030f 858 mrb_obj_remove_instance_variable(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 859 {
mzta 0:158c61bb030f 860 mrb_sym sym;
mzta 0:158c61bb030f 861 mrb_value val;
mzta 0:158c61bb030f 862
mzta 0:158c61bb030f 863 mrb_get_args(mrb, "n", &sym);
mzta 0:158c61bb030f 864 mrb_iv_check(mrb, sym);
mzta 0:158c61bb030f 865 val = mrb_iv_remove(mrb, self, sym);
mzta 0:158c61bb030f 866 if (mrb_undef_p(val)) {
mzta 0:158c61bb030f 867 mrb_name_error(mrb, sym, "instance variable %S not defined", mrb_sym2str(mrb, sym));
mzta 0:158c61bb030f 868 }
mzta 0:158c61bb030f 869 return val;
mzta 0:158c61bb030f 870 }
mzta 0:158c61bb030f 871
mzta 0:158c61bb030f 872 static inline mrb_bool
mzta 0:158c61bb030f 873 basic_obj_respond_to(mrb_state *mrb, mrb_value obj, mrb_sym id, int pub)
mzta 0:158c61bb030f 874 {
mzta 0:158c61bb030f 875 return mrb_respond_to(mrb, obj, id);
mzta 0:158c61bb030f 876 }
mzta 0:158c61bb030f 877 /* 15.3.1.3.43 */
mzta 0:158c61bb030f 878 /*
mzta 0:158c61bb030f 879 * call-seq:
mzta 0:158c61bb030f 880 * obj.respond_to?(symbol, include_private=false) -> true or false
mzta 0:158c61bb030f 881 *
mzta 0:158c61bb030f 882 * Returns +true+ if _obj_ responds to the given
mzta 0:158c61bb030f 883 * method. Private methods are included in the search only if the
mzta 0:158c61bb030f 884 * optional second parameter evaluates to +true+.
mzta 0:158c61bb030f 885 *
mzta 0:158c61bb030f 886 * If the method is not implemented,
mzta 0:158c61bb030f 887 * as Process.fork on Windows, File.lchmod on GNU/Linux, etc.,
mzta 0:158c61bb030f 888 * false is returned.
mzta 0:158c61bb030f 889 *
mzta 0:158c61bb030f 890 * If the method is not defined, <code>respond_to_missing?</code>
mzta 0:158c61bb030f 891 * method is called and the result is returned.
mzta 0:158c61bb030f 892 */
mzta 0:158c61bb030f 893 static mrb_value
mzta 0:158c61bb030f 894 obj_respond_to(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 895 {
mzta 0:158c61bb030f 896 mrb_value mid;
mzta 0:158c61bb030f 897 mrb_sym id, rtm_id;
mzta 0:158c61bb030f 898 mrb_bool priv = FALSE, respond_to_p = TRUE;
mzta 0:158c61bb030f 899
mzta 0:158c61bb030f 900 mrb_get_args(mrb, "o|b", &mid, &priv);
mzta 0:158c61bb030f 901
mzta 0:158c61bb030f 902 if (mrb_symbol_p(mid)) {
mzta 0:158c61bb030f 903 id = mrb_symbol(mid);
mzta 0:158c61bb030f 904 }
mzta 0:158c61bb030f 905 else {
mzta 0:158c61bb030f 906 mrb_value tmp;
mzta 0:158c61bb030f 907 if (!mrb_string_p(mid)) {
mzta 0:158c61bb030f 908 tmp = mrb_check_string_type(mrb, mid);
mzta 0:158c61bb030f 909 if (mrb_nil_p(tmp)) {
mzta 0:158c61bb030f 910 tmp = mrb_inspect(mrb, mid);
mzta 0:158c61bb030f 911 mrb_raisef(mrb, E_TYPE_ERROR, "%S is not a symbol", tmp);
mzta 0:158c61bb030f 912 }
mzta 0:158c61bb030f 913 }
mzta 0:158c61bb030f 914 tmp = mrb_check_intern_str(mrb, mid);
mzta 0:158c61bb030f 915 if (mrb_nil_p(tmp)) {
mzta 0:158c61bb030f 916 respond_to_p = FALSE;
mzta 0:158c61bb030f 917 }
mzta 0:158c61bb030f 918 else {
mzta 0:158c61bb030f 919 id = mrb_symbol(tmp);
mzta 0:158c61bb030f 920 }
mzta 0:158c61bb030f 921 }
mzta 0:158c61bb030f 922
mzta 0:158c61bb030f 923 if (respond_to_p) {
mzta 0:158c61bb030f 924 respond_to_p = basic_obj_respond_to(mrb, self, id, !priv);
mzta 0:158c61bb030f 925 }
mzta 0:158c61bb030f 926
mzta 0:158c61bb030f 927 if (!respond_to_p) {
mzta 0:158c61bb030f 928 rtm_id = mrb_intern_lit(mrb, "respond_to_missing?");
mzta 0:158c61bb030f 929 if (basic_obj_respond_to(mrb, self, rtm_id, !priv)) {
mzta 0:158c61bb030f 930 mrb_value args[2];
mzta 0:158c61bb030f 931 args[0] = mid;
mzta 0:158c61bb030f 932 args[1] = mrb_bool_value(priv);
mzta 0:158c61bb030f 933 return mrb_funcall_argv(mrb, self, rtm_id, 2, args);
mzta 0:158c61bb030f 934 }
mzta 0:158c61bb030f 935 }
mzta 0:158c61bb030f 936 return mrb_bool_value(respond_to_p);
mzta 0:158c61bb030f 937 }
mzta 0:158c61bb030f 938
mzta 0:158c61bb030f 939 /* 15.3.1.3.45 */
mzta 0:158c61bb030f 940 /*
mzta 0:158c61bb030f 941 * call-seq:
mzta 0:158c61bb030f 942 * obj.singleton_methods(all=true) -> array
mzta 0:158c61bb030f 943 *
mzta 0:158c61bb030f 944 * Returns an array of the names of singleton methods for <i>obj</i>.
mzta 0:158c61bb030f 945 * If the optional <i>all</i> parameter is true, the list will include
mzta 0:158c61bb030f 946 * methods in modules included in <i>obj</i>.
mzta 0:158c61bb030f 947 * Only public and protected singleton methods are returned.
mzta 0:158c61bb030f 948 *
mzta 0:158c61bb030f 949 * module Other
mzta 0:158c61bb030f 950 * def three() end
mzta 0:158c61bb030f 951 * end
mzta 0:158c61bb030f 952 *
mzta 0:158c61bb030f 953 * class Single
mzta 0:158c61bb030f 954 * def Single.four() end
mzta 0:158c61bb030f 955 * end
mzta 0:158c61bb030f 956 *
mzta 0:158c61bb030f 957 * a = Single.new
mzta 0:158c61bb030f 958 *
mzta 0:158c61bb030f 959 * def a.one()
mzta 0:158c61bb030f 960 * end
mzta 0:158c61bb030f 961 *
mzta 0:158c61bb030f 962 * class << a
mzta 0:158c61bb030f 963 * include Other
mzta 0:158c61bb030f 964 * def two()
mzta 0:158c61bb030f 965 * end
mzta 0:158c61bb030f 966 * end
mzta 0:158c61bb030f 967 *
mzta 0:158c61bb030f 968 * Single.singleton_methods #=> [:four]
mzta 0:158c61bb030f 969 * a.singleton_methods(false) #=> [:two, :one]
mzta 0:158c61bb030f 970 * a.singleton_methods #=> [:two, :one, :three]
mzta 0:158c61bb030f 971 */
mzta 0:158c61bb030f 972 static mrb_value
mzta 0:158c61bb030f 973 mrb_obj_singleton_methods_m(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 974 {
mzta 0:158c61bb030f 975 mrb_bool recur = TRUE;
mzta 0:158c61bb030f 976 mrb_get_args(mrb, "|b", &recur);
mzta 0:158c61bb030f 977 return mrb_obj_singleton_methods(mrb, recur, self);
mzta 0:158c61bb030f 978 }
mzta 0:158c61bb030f 979
mzta 0:158c61bb030f 980 static mrb_value
mzta 0:158c61bb030f 981 mod_define_singleton_method(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 982 {
mzta 0:158c61bb030f 983 struct RProc *p;
mzta 0:158c61bb030f 984 mrb_sym mid;
mzta 0:158c61bb030f 985 mrb_value blk = mrb_nil_value();
mzta 0:158c61bb030f 986
mzta 0:158c61bb030f 987 mrb_get_args(mrb, "n&", &mid, &blk);
mzta 0:158c61bb030f 988 if (mrb_nil_p(blk)) {
mzta 0:158c61bb030f 989 mrb_raise(mrb, E_ARGUMENT_ERROR, "no block given");
mzta 0:158c61bb030f 990 }
mzta 0:158c61bb030f 991 p = (struct RProc*)mrb_obj_alloc(mrb, MRB_TT_PROC, mrb->proc_class);
mzta 0:158c61bb030f 992 mrb_proc_copy(p, mrb_proc_ptr(blk));
mzta 0:158c61bb030f 993 p->flags |= MRB_PROC_STRICT;
mzta 0:158c61bb030f 994 mrb_define_method_raw(mrb, mrb_class_ptr(mrb_singleton_class(mrb, self)), mid, p);
mzta 0:158c61bb030f 995 return mrb_symbol_value(mid);
mzta 0:158c61bb030f 996 }
mzta 0:158c61bb030f 997
mzta 0:158c61bb030f 998 static mrb_value
mzta 0:158c61bb030f 999 mrb_obj_ceqq(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 1000 {
mzta 0:158c61bb030f 1001 mrb_value v;
mzta 0:158c61bb030f 1002 mrb_int i, len;
mzta 0:158c61bb030f 1003 mrb_sym eqq = mrb_intern_lit(mrb, "===");
mzta 0:158c61bb030f 1004 mrb_value ary = mrb_ary_splat(mrb, self);
mzta 0:158c61bb030f 1005
mzta 0:158c61bb030f 1006 mrb_get_args(mrb, "o", &v);
mzta 0:158c61bb030f 1007 len = RARRAY_LEN(ary);
mzta 0:158c61bb030f 1008 for (i=0; i<len; i++) {
mzta 0:158c61bb030f 1009 mrb_value c = mrb_funcall_argv(mrb, mrb_ary_entry(ary, i), eqq, 1, &v);
mzta 0:158c61bb030f 1010 if (mrb_test(c)) return mrb_true_value();
mzta 0:158c61bb030f 1011 }
mzta 0:158c61bb030f 1012 return mrb_false_value();
mzta 0:158c61bb030f 1013 }
mzta 0:158c61bb030f 1014
mzta 0:158c61bb030f 1015 static mrb_value
mzta 0:158c61bb030f 1016 mrb_local_variables(mrb_state *mrb, mrb_value self)
mzta 0:158c61bb030f 1017 {
mzta 0:158c61bb030f 1018 mrb_value ret;
mzta 0:158c61bb030f 1019 struct RProc *proc;
mzta 0:158c61bb030f 1020 struct mrb_irep *irep;
mzta 0:158c61bb030f 1021 size_t i;
mzta 0:158c61bb030f 1022
mzta 0:158c61bb030f 1023 proc = mrb->c->ci[-1].proc;
mzta 0:158c61bb030f 1024
mzta 0:158c61bb030f 1025 if (MRB_PROC_CFUNC_P(proc)) {
mzta 0:158c61bb030f 1026 return mrb_ary_new(mrb);
mzta 0:158c61bb030f 1027 }
mzta 0:158c61bb030f 1028
mzta 0:158c61bb030f 1029 irep = proc->body.irep;
mzta 0:158c61bb030f 1030 if (!irep->lv) {
mzta 0:158c61bb030f 1031 return mrb_ary_new(mrb);
mzta 0:158c61bb030f 1032 }
mzta 0:158c61bb030f 1033 ret = mrb_ary_new_capa(mrb, irep->nlocals - 1);
mzta 0:158c61bb030f 1034 for (i = 0; i + 1 < irep->nlocals; ++i) {
mzta 0:158c61bb030f 1035 if (irep->lv[i].name) {
mzta 0:158c61bb030f 1036 mrb_ary_push(mrb, ret, mrb_symbol_value(irep->lv[i].name));
mzta 0:158c61bb030f 1037 }
mzta 0:158c61bb030f 1038 }
mzta 0:158c61bb030f 1039 if (proc->env) {
mzta 0:158c61bb030f 1040 struct REnv *e = proc->env;
mzta 0:158c61bb030f 1041
mzta 0:158c61bb030f 1042 while (e) {
mzta 0:158c61bb030f 1043 if (!MRB_PROC_CFUNC_P(mrb->c->cibase[e->cioff].proc)) {
mzta 0:158c61bb030f 1044 irep = mrb->c->cibase[e->cioff].proc->body.irep;
mzta 0:158c61bb030f 1045 if (irep->lv) {
mzta 0:158c61bb030f 1046 for (i = 0; i + 1 < irep->nlocals; ++i) {
mzta 0:158c61bb030f 1047 if (irep->lv[i].name) {
mzta 0:158c61bb030f 1048 mrb_ary_push(mrb, ret, mrb_symbol_value(irep->lv[i].name));
mzta 0:158c61bb030f 1049 }
mzta 0:158c61bb030f 1050 }
mzta 0:158c61bb030f 1051 }
mzta 0:158c61bb030f 1052 }
mzta 0:158c61bb030f 1053 e = (struct REnv*)e->c;
mzta 0:158c61bb030f 1054 }
mzta 0:158c61bb030f 1055 }
mzta 0:158c61bb030f 1056
mzta 0:158c61bb030f 1057 return ret;
mzta 0:158c61bb030f 1058 }
mzta 0:158c61bb030f 1059
mzta 0:158c61bb030f 1060 void
mzta 0:158c61bb030f 1061 mrb_init_kernel(mrb_state *mrb)
mzta 0:158c61bb030f 1062 {
mzta 0:158c61bb030f 1063 struct RClass *krn;
mzta 0:158c61bb030f 1064
mzta 0:158c61bb030f 1065 krn = mrb->kernel_module = mrb_define_module(mrb, "Kernel"); /* 15.3.1 */
mzta 0:158c61bb030f 1066 mrb_define_class_method(mrb, krn, "block_given?", mrb_f_block_given_p_m, MRB_ARGS_NONE()); /* 15.3.1.2.2 */
mzta 0:158c61bb030f 1067 mrb_define_class_method(mrb, krn, "global_variables", mrb_f_global_variables, MRB_ARGS_NONE()); /* 15.3.1.2.4 */
mzta 0:158c61bb030f 1068 mrb_define_class_method(mrb, krn, "iterator?", mrb_f_block_given_p_m, MRB_ARGS_NONE()); /* 15.3.1.2.5 */
mzta 0:158c61bb030f 1069 mrb_define_class_method(mrb, krn, "local_variables", mrb_local_variables, MRB_ARGS_NONE()); /* 15.3.1.2.7 */
mzta 0:158c61bb030f 1070 ; /* 15.3.1.2.11 */
mzta 0:158c61bb030f 1071 mrb_define_class_method(mrb, krn, "raise", mrb_f_raise, MRB_ARGS_OPT(2)); /* 15.3.1.2.12 */
mzta 0:158c61bb030f 1072
mzta 0:158c61bb030f 1073 mrb_define_method(mrb, krn, "singleton_class", mrb_singleton_class, MRB_ARGS_NONE());
mzta 0:158c61bb030f 1074
mzta 0:158c61bb030f 1075 mrb_define_method(mrb, krn, "==", mrb_obj_equal_m, MRB_ARGS_REQ(1)); /* 15.3.1.3.1 */
mzta 0:158c61bb030f 1076 mrb_define_method(mrb, krn, "!=", mrb_obj_not_equal_m, MRB_ARGS_REQ(1));
mzta 0:158c61bb030f 1077 mrb_define_method(mrb, krn, "===", mrb_equal_m, MRB_ARGS_REQ(1)); /* 15.3.1.3.2 */
mzta 0:158c61bb030f 1078 mrb_define_method(mrb, krn, "__id__", mrb_obj_id_m, MRB_ARGS_NONE()); /* 15.3.1.3.3 */
mzta 0:158c61bb030f 1079 mrb_define_method(mrb, krn, "__send__", mrb_f_send, MRB_ARGS_ANY()); /* 15.3.1.3.4 */
mzta 0:158c61bb030f 1080 mrb_define_method(mrb, krn, "block_given?", mrb_f_block_given_p_m, MRB_ARGS_NONE()); /* 15.3.1.3.6 */
mzta 0:158c61bb030f 1081 mrb_define_method(mrb, krn, "class", mrb_obj_class_m, MRB_ARGS_NONE()); /* 15.3.1.3.7 */
mzta 0:158c61bb030f 1082 mrb_define_method(mrb, krn, "clone", mrb_obj_clone, MRB_ARGS_NONE()); /* 15.3.1.3.8 */
mzta 0:158c61bb030f 1083 mrb_define_method(mrb, krn, "dup", mrb_obj_dup, MRB_ARGS_NONE()); /* 15.3.1.3.9 */
mzta 0:158c61bb030f 1084 mrb_define_method(mrb, krn, "eql?", mrb_obj_equal_m, MRB_ARGS_REQ(1)); /* 15.3.1.3.10 */
mzta 0:158c61bb030f 1085 mrb_define_method(mrb, krn, "equal?", mrb_obj_equal_m, MRB_ARGS_REQ(1)); /* 15.3.1.3.11 */
mzta 0:158c61bb030f 1086 mrb_define_method(mrb, krn, "extend", mrb_obj_extend_m, MRB_ARGS_ANY()); /* 15.3.1.3.13 */
mzta 0:158c61bb030f 1087 mrb_define_method(mrb, krn, "global_variables", mrb_f_global_variables, MRB_ARGS_NONE()); /* 15.3.1.3.14 */
mzta 0:158c61bb030f 1088 mrb_define_method(mrb, krn, "hash", mrb_obj_hash, MRB_ARGS_NONE()); /* 15.3.1.3.15 */
mzta 0:158c61bb030f 1089 mrb_define_method(mrb, krn, "initialize_copy", mrb_obj_init_copy, MRB_ARGS_REQ(1)); /* 15.3.1.3.16 */
mzta 0:158c61bb030f 1090 mrb_define_method(mrb, krn, "inspect", mrb_obj_inspect, MRB_ARGS_NONE()); /* 15.3.1.3.17 */
mzta 0:158c61bb030f 1091 mrb_define_method(mrb, krn, "instance_eval", mrb_obj_instance_eval, MRB_ARGS_ANY()); /* 15.3.1.3.18 */
mzta 0:158c61bb030f 1092 mrb_define_method(mrb, krn, "instance_of?", obj_is_instance_of, MRB_ARGS_REQ(1)); /* 15.3.1.3.19 */
mzta 0:158c61bb030f 1093 mrb_define_method(mrb, krn, "instance_variable_defined?", mrb_obj_ivar_defined, MRB_ARGS_REQ(1)); /* 15.3.1.3.20 */
mzta 0:158c61bb030f 1094 mrb_define_method(mrb, krn, "instance_variable_get", mrb_obj_ivar_get, MRB_ARGS_REQ(1)); /* 15.3.1.3.21 */
mzta 0:158c61bb030f 1095 mrb_define_method(mrb, krn, "instance_variable_set", mrb_obj_ivar_set, MRB_ARGS_REQ(2)); /* 15.3.1.3.22 */
mzta 0:158c61bb030f 1096 mrb_define_method(mrb, krn, "instance_variables", mrb_obj_instance_variables, MRB_ARGS_NONE()); /* 15.3.1.3.23 */
mzta 0:158c61bb030f 1097 mrb_define_method(mrb, krn, "is_a?", mrb_obj_is_kind_of_m, MRB_ARGS_REQ(1)); /* 15.3.1.3.24 */
mzta 0:158c61bb030f 1098 mrb_define_method(mrb, krn, "iterator?", mrb_f_block_given_p_m, MRB_ARGS_NONE()); /* 15.3.1.3.25 */
mzta 0:158c61bb030f 1099 mrb_define_method(mrb, krn, "kind_of?", mrb_obj_is_kind_of_m, MRB_ARGS_REQ(1)); /* 15.3.1.3.26 */
mzta 0:158c61bb030f 1100 mrb_define_method(mrb, krn, "local_variables", mrb_local_variables, MRB_ARGS_NONE()); /* 15.3.1.3.28 */
mzta 0:158c61bb030f 1101 mrb_define_method(mrb, krn, "methods", mrb_obj_methods_m, MRB_ARGS_OPT(1)); /* 15.3.1.3.31 */
mzta 0:158c61bb030f 1102 mrb_define_method(mrb, krn, "nil?", mrb_false, MRB_ARGS_NONE()); /* 15.3.1.3.32 */
mzta 0:158c61bb030f 1103 mrb_define_method(mrb, krn, "object_id", mrb_obj_id_m, MRB_ARGS_NONE()); /* 15.3.1.3.33 */
mzta 0:158c61bb030f 1104 mrb_define_method(mrb, krn, "private_methods", mrb_obj_private_methods, MRB_ARGS_OPT(1)); /* 15.3.1.3.36 */
mzta 0:158c61bb030f 1105 mrb_define_method(mrb, krn, "protected_methods", mrb_obj_protected_methods, MRB_ARGS_OPT(1)); /* 15.3.1.3.37 */
mzta 0:158c61bb030f 1106 mrb_define_method(mrb, krn, "public_methods", mrb_obj_public_methods, MRB_ARGS_OPT(1)); /* 15.3.1.3.38 */
mzta 0:158c61bb030f 1107 mrb_define_method(mrb, krn, "raise", mrb_f_raise, MRB_ARGS_ANY()); /* 15.3.1.3.40 */
mzta 0:158c61bb030f 1108 mrb_define_method(mrb, krn, "remove_instance_variable", mrb_obj_remove_instance_variable,MRB_ARGS_REQ(1)); /* 15.3.1.3.41 */
mzta 0:158c61bb030f 1109 mrb_define_method(mrb, krn, "respond_to?", obj_respond_to, MRB_ARGS_ANY()); /* 15.3.1.3.43 */
mzta 0:158c61bb030f 1110 mrb_define_method(mrb, krn, "send", mrb_f_send, MRB_ARGS_ANY()); /* 15.3.1.3.44 */
mzta 0:158c61bb030f 1111 mrb_define_method(mrb, krn, "singleton_methods", mrb_obj_singleton_methods_m, MRB_ARGS_OPT(1)); /* 15.3.1.3.45 */
mzta 0:158c61bb030f 1112 mrb_define_method(mrb, krn, "define_singleton_method", mod_define_singleton_method, MRB_ARGS_ANY());
mzta 0:158c61bb030f 1113 mrb_define_method(mrb, krn, "to_s", mrb_any_to_s, MRB_ARGS_NONE()); /* 15.3.1.3.46 */
mzta 0:158c61bb030f 1114 mrb_define_method(mrb, krn, "__case_eqq", mrb_obj_ceqq, MRB_ARGS_REQ(1)); /* internal */
mzta 0:158c61bb030f 1115
mzta 0:158c61bb030f 1116 mrb_include_module(mrb, mrb->object_class, mrb->kernel_module);
mzta 0:158c61bb030f 1117 mrb_alias_method(mrb, mrb->module_class, mrb_intern_lit(mrb, "dup"), mrb_intern_lit(mrb, "clone"));
mzta 0:158c61bb030f 1118 }
mzta 0:158c61bb030f 1119