Change soft-fail to use the config, rather than env
[rbx.git] / shotgun / lib / class.c
blobf2078a26c377cddc43d097e6a35b575a1d706223
1 #include "shotgun/lib/shotgun.h"
2 #include "shotgun/lib/module.h"
3 #include "shotgun/lib/class.h"
5 OBJECT class_superclass(STATE, OBJECT cls) {
6 OBJECT sup;
8 sup = class_get_superclass(cls);
10 while(!ISA(sup, BASIC_CLASS(class))) {
11 sup = class_get_superclass(sup);
14 return sup;
17 OBJECT class_new(STATE, const char *name, int fields, OBJECT sup, OBJECT ns) {
18 OBJECT cls;
20 cls = class_create(state);
21 class_set_instance_fields(cls, I2N(fields));
22 class_set_superclass(cls, sup);
23 module_setup_fields(state, cls);
24 object_create_metaclass(state, cls, object_metaclass(state, sup));
25 module_setup_name(state, cls, name, ns);
26 return cls;
29 OBJECT class_new_instance(STATE, OBJECT self) {
30 int count;
32 count = N2I(class_get_instance_fields(self));
33 return NEW_OBJECT(self, count);
36 OBJECT class_constitute(STATE, OBJECT sup, OBJECT under) {
37 OBJECT val, sup_itr;
39 if(NIL_P(sup)) {
40 sup = state->global->object;
41 } else if(sup == Qfalse) {
42 /* Support class detached from the normal class heirarchy. */
43 sup = Qnil;
44 } else if(!ISA(sup, state->global->class)) {
45 /* Validate sup is a valid superclass-like object. */
47 sup_itr = sup;
48 while(!NIL_P(sup_itr)) {
49 if(NUM_FIELDS(sup_itr) <= CLASS_f_SUPERCLASS ||
50 !ISA(class_get_method_table(sup_itr), state->global->hash)) {
51 /* Ok, this wont work as a superclass. */
52 return Qnil;
53 } else {
54 sup_itr = class_get_superclass(sup_itr);
58 /* Ok, we validated the hierarchy as being superclass-like, so it's
59 ok to use. */
62 val = class_create(state);
64 /* Push superclass instance information down. */
65 if(NIL_P(sup) || NUM_FIELDS(sup) <= CLASS_f_INSTANCE_FIELDS) {
66 /* When this object is detatched from the normal class hierarchy, we give
67 it the normal fields and flags info by default. */
68 class_set_instance_fields(val, class_get_instance_fields(state->global->object));
69 class_set_has_ivars(val, class_get_has_ivars(state->global->object));
70 class_set_needs_cleanup(val, class_get_needs_cleanup(state->global->object));
71 class_set_object_type(val, class_get_object_type(state->global->object));
72 } else {
73 class_set_instance_fields(val, class_get_instance_fields(sup));
74 class_set_has_ivars(val, class_get_has_ivars(sup));
75 class_set_needs_cleanup(val, class_get_needs_cleanup(sup));
76 class_set_object_type(val, class_get_object_type(sup));
79 // printf("Setting superclass of %p to: %p\n", val, sup);
80 class_set_superclass(val, sup);
81 module_setup_fields(state, val);
82 object_create_metaclass(state, val, object_metaclass(state, sup));
83 module_set_encloser(val, under);
84 module_setup_fields(state, object_metaclass(state, val));
85 module_set_encloser(object_metaclass(state, val), under);
86 return val;