mirror of
https://github.com/mruby/mruby
synced 2026-06-08 16:11:16 +00:00
Allow Class#allocate to be prohibited
Calling `Class#allocate` with `UnboundMethod#bind_call` usually succeeds without problems. If this behavior does not make us happy, we can now prohibit it with `MRB_SET_INSTANCE_TT(klass, MRB_TT_UNDEF)`. At the same time, it applies to the `Binding`, `Complex`, `Data`, `Float`, `Integer`, `Method`, `Rational` and `UnboundMethod` classes.
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
#include <mruby.h>
|
||||
#include <mruby/array.h>
|
||||
#include <mruby/class.h>
|
||||
#include <mruby/hash.h>
|
||||
#include <mruby/proc.h>
|
||||
#include <mruby/variable.h>
|
||||
@@ -413,6 +414,7 @@ void
|
||||
mrb_mruby_binding_gem_init(mrb_state *mrb)
|
||||
{
|
||||
struct RClass *binding = mrb_define_class(mrb, "Binding", mrb->object_class);
|
||||
MRB_SET_INSTANCE_TT(binding, MRB_TT_UNDEF);
|
||||
mrb_undef_class_method(mrb, binding, "new");
|
||||
mrb_undef_class_method(mrb, binding, "allocate");
|
||||
|
||||
|
||||
@@ -392,7 +392,7 @@ void mrb_mruby_complex_gem_init(mrb_state *mrb)
|
||||
struct RClass *comp;
|
||||
|
||||
comp = mrb_define_class_id(mrb, MRB_SYM(Complex), mrb_class_get_id(mrb, MRB_SYM(Numeric)));
|
||||
MRB_SET_INSTANCE_TT(comp, MRB_TT_COMPLEX);
|
||||
MRB_SET_INSTANCE_TT(comp, MRB_TT_UNDEF);
|
||||
|
||||
mrb_undef_class_method(mrb, comp, "new");
|
||||
mrb_define_class_method(mrb, comp, "rectangular", complex_s_rect, MRB_ARGS_REQ(1)|MRB_ARGS_OPT(1));
|
||||
|
||||
@@ -433,7 +433,7 @@ mrb_mruby_data_gem_init(mrb_state* mrb)
|
||||
{
|
||||
struct RClass *d;
|
||||
d = mrb_define_class(mrb, "Data", mrb->object_class);
|
||||
MRB_SET_INSTANCE_TT(d, MRB_TT_STRUCT);
|
||||
MRB_SET_INSTANCE_TT(d, MRB_TT_UNDEF);
|
||||
|
||||
mrb_undef_class_method(mrb, d, "new");
|
||||
mrb_define_class_method(mrb, d, "define", mrb_data_s_def, MRB_ARGS_ANY());
|
||||
|
||||
@@ -517,6 +517,7 @@ mrb_mruby_method_gem_init(mrb_state* mrb)
|
||||
struct RClass *unbound_method = mrb_define_class_id(mrb, MRB_SYM(UnboundMethod), mrb->object_class);
|
||||
struct RClass *method = mrb_define_class_id(mrb, MRB_SYM(Method), mrb->object_class);
|
||||
|
||||
MRB_SET_INSTANCE_TT(unbound_method, MRB_TT_UNDEF);
|
||||
mrb_undef_class_method(mrb, unbound_method, "new");
|
||||
mrb_define_method(mrb, unbound_method, "bind", unbound_method_bind, MRB_ARGS_REQ(1));
|
||||
mrb_define_method(mrb, unbound_method, "super_method", method_super_method, MRB_ARGS_NONE());
|
||||
@@ -531,6 +532,7 @@ mrb_mruby_method_gem_init(mrb_state* mrb)
|
||||
mrb_define_method(mrb, unbound_method, "owner", method_owner, MRB_ARGS_NONE());
|
||||
mrb_define_method(mrb, unbound_method, "name", method_name, MRB_ARGS_NONE());
|
||||
|
||||
MRB_SET_INSTANCE_TT(method, MRB_TT_UNDEF);
|
||||
mrb_undef_class_method(mrb, method, "new");
|
||||
mrb_define_method(mrb, method, "==", method_eql, MRB_ARGS_REQ(1));
|
||||
mrb_define_method(mrb, method, "eql?", method_eql, MRB_ARGS_REQ(1));
|
||||
|
||||
@@ -769,7 +769,7 @@ void mrb_mruby_rational_gem_init(mrb_state *mrb)
|
||||
struct RClass *rat;
|
||||
|
||||
rat = mrb_define_class_id(mrb, MRB_SYM(Rational), mrb_class_get_id(mrb, MRB_SYM(Numeric)));
|
||||
MRB_SET_INSTANCE_TT(rat, MRB_TT_RATIONAL);
|
||||
MRB_SET_INSTANCE_TT(rat, MRB_TT_UNDEF);
|
||||
mrb_undef_class_method(mrb, rat, "new");
|
||||
mrb_define_class_method(mrb, rat, "_new", rational_s_new, MRB_ARGS_REQ(2));
|
||||
mrb_define_method(mrb, rat, "numerator", rational_numerator, MRB_ARGS_NONE());
|
||||
|
||||
@@ -1945,6 +1945,9 @@ mrb_instance_alloc(mrb_state *mrb, mrb_value cv)
|
||||
ttype = MRB_TT_OBJECT;
|
||||
}
|
||||
if (ttype <= MRB_TT_CPTR) {
|
||||
if (ttype == MRB_TT_UNDEF) {
|
||||
mrb_raisef(mrb, E_TYPE_ERROR, "allocator undefined for %v", cv);
|
||||
}
|
||||
mrb_raisef(mrb, E_TYPE_ERROR, "can't create instance of %v", cv);
|
||||
}
|
||||
o = (struct RObject*)mrb_obj_alloc(mrb, ttype, c);
|
||||
|
||||
@@ -515,6 +515,7 @@ mrb_obj_alloc(mrb_state *mrb, enum mrb_vtype ttype, struct RClass *cls)
|
||||
}
|
||||
tt = MRB_INSTANCE_TT(cls);
|
||||
if (tt != MRB_TT_FALSE &&
|
||||
tt != MRB_TT_UNDEF &&
|
||||
ttype != MRB_TT_SCLASS &&
|
||||
ttype != MRB_TT_ICLASS &&
|
||||
ttype != MRB_TT_ENV &&
|
||||
|
||||
+2
-2
@@ -2219,7 +2219,7 @@ mrb_init_numeric(mrb_state *mrb)
|
||||
|
||||
/* Integer Class */
|
||||
mrb->integer_class = integer = mrb_define_class(mrb, "Integer", numeric); /* 15.2.8 */
|
||||
MRB_SET_INSTANCE_TT(integer, MRB_TT_INTEGER);
|
||||
MRB_SET_INSTANCE_TT(integer, MRB_TT_UNDEF);
|
||||
mrb_undef_class_method(mrb, integer, "new");
|
||||
mrb_define_method(mrb, integer, "**", int_pow, MRB_ARGS_REQ(1));
|
||||
mrb_define_method(mrb, integer, "<=>", num_cmp, MRB_ARGS_REQ(1)); /* 15.2.8.3.1 */
|
||||
@@ -2264,7 +2264,7 @@ mrb_init_numeric(mrb_state *mrb)
|
||||
#ifndef MRB_NO_FLOAT
|
||||
/* Float Class */
|
||||
mrb->float_class = fl = mrb_define_class(mrb, "Float", numeric); /* 15.2.9 */
|
||||
MRB_SET_INSTANCE_TT(fl, MRB_TT_FLOAT);
|
||||
MRB_SET_INSTANCE_TT(fl, MRB_TT_UNDEF);
|
||||
mrb_undef_class_method(mrb, fl, "new");
|
||||
mrb_define_method(mrb, fl, "**", flo_pow, MRB_ARGS_REQ(1));
|
||||
mrb_define_method(mrb, fl, "/", flo_div, MRB_ARGS_REQ(1)); /* 15.2.9.3.6 */
|
||||
|
||||
Reference in New Issue
Block a user