From: Jay Freeman (saurik) Date: Fri, 14 Sep 2012 13:09:51 +0000 (-0700) Subject: Use Type as the prototype-bridge for metaclasses. X-Git-Tag: v0.9.460~22 X-Git-Url: https://git.saurik.com/cycript.git/commitdiff_plain/bc3080fdd24b9858d9c9dcbd3d8dd78ae010962a Use Type as the prototype-bridge for metaclasses. --- diff --git a/Execute.cpp b/Execute.cpp index 4012186..0bb732c 100644 --- a/Execute.cpp +++ b/Execute.cpp @@ -1469,7 +1469,12 @@ extern "C" void CYSetupContext(JSGlobalContextRef context) { CYSetProperty(context, cycript, CYJSString("Functor"), Functor); CYSetProperty(context, cycript, CYJSString("Pointer"), JSObjectMakeConstructor(context, Pointer_, &Pointer_new)); - CYSetProperty(context, cycript, CYJSString("Type"), JSObjectMakeConstructor(context, Type_privateData::Class_, &Type_new)); + + JSObjectRef Type(JSObjectMakeConstructor(context, Type_privateData::Class_, &Type_new)); + CYSetProperty(context, cycript, CYJSString("Type"), Type); + + JSObjectRef Type_prototype(CYCastJSObject(context, CYGetProperty(context, Type, prototype_s))); + CYSetProperty(context, cy, CYJSString("Type_prototype"), Type_prototype); JSObjectRef all(JSObjectMake(context, All_, NULL)); CYSetProperty(context, cycript, CYJSString("all"), all); diff --git a/ObjectiveC/Library.mm b/ObjectiveC/Library.mm index d526163..44eb057 100644 --- a/ObjectiveC/Library.mm +++ b/ObjectiveC/Library.mm @@ -245,6 +245,7 @@ static JSClassRef ArrayInstance_; static JSClassRef FunctionInstance_; static JSClassRef ObjectInstance_; static JSClassRef StringInstance_; +static JSClassRef TypeInstance_; static JSClassRef Internal_; static JSClassRef Message_; @@ -290,9 +291,11 @@ Type_privateData *Selector_privateData::GetType() const { static JSValueRef Instance_callAsFunction_toString(JSContextRef context, JSObjectRef object, JSObjectRef _this, size_t count, const JSValueRef arguments[], JSValueRef *exception); -JSValueRef CYGetClassPrototype(JSContextRef context, id self) { +JSValueRef CYGetClassPrototype(JSContextRef context, Class self, bool meta) { if (self == nil) return CYGetCachedObject(context, CYJSString("Instance_prototype")); + else if (meta && !class_isMetaClass(self)) + return CYGetCachedObject(context, CYJSString("TypeInstance_prototype")); JSObjectRef global(CYGetGlobalObject(context)); JSObjectRef cy(CYCastJSObject(context, CYGetProperty(context, global, cy_s))); @@ -317,7 +320,7 @@ JSValueRef CYGetClassPrototype(JSContextRef context, id self) { else if (self == NSString_) prototype = CYGetCachedObject(context, CYJSString("StringInstance_prototype")); else - prototype = CYGetClassPrototype(context, class_getSuperclass(self)); + prototype = CYGetClassPrototype(context, class_getSuperclass(self), meta); JSObjectRef object(JSObjectMake(context, _class, NULL)); JSObjectSetPrototype(context, object, prototype); @@ -326,6 +329,10 @@ JSValueRef CYGetClassPrototype(JSContextRef context, id self) { return object; } +_finline JSValueRef CYGetClassPrototype(JSContextRef context, Class self) { + return CYGetClassPrototype(context, self, class_isMetaClass(self)); +} + JSObjectRef Messages::Make(JSContextRef context, Class _class) { JSObjectRef value(JSObjectMake(context, Messages_, new Messages(_class))); if (Class super = class_getSuperclass(_class)) @@ -2545,6 +2552,9 @@ void CYObjectiveC_Initialize() { /*XXX*/ JSContextRef context(NULL); CYPoolTry { definition.className = "StringInstance"; StringInstance_ = JSClassCreate(&definition); + definition.className = "TypeInstance"; + TypeInstance_ = JSClassCreate(&definition); + definition.className = "FunctionInstance"; FunctionInstance_ = JSClassCreate(&definition); @@ -2686,6 +2696,12 @@ void CYObjectiveC_SetupContext(JSContextRef context) { CYPoolTry { JSObjectRef String_prototype(CYGetCachedObject(context, CYJSString("String_prototype"))); JSObjectSetPrototype(context, StringInstance_prototype, String_prototype); + JSObjectRef TypeInstance(JSObjectMakeConstructor(context, TypeInstance_, NULL)); + JSObjectRef TypeInstance_prototype(CYCastJSObject(context, CYGetProperty(context, TypeInstance, prototype_s))); + CYSetProperty(context, cy, CYJSString("TypeInstance_prototype"), TypeInstance_prototype); + JSObjectRef Type_prototype(CYGetCachedObject(context, CYJSString("Type_prototype"))); + JSObjectSetPrototype(context, TypeInstance_prototype, Type_prototype); + CYSetProperty(context, cycript, CYJSString("Instance"), Instance); CYSetProperty(context, cycript, CYJSString("Selector"), Selector); CYSetProperty(context, cycript, CYJSString("Super"), Super);