X-Git-Url: https://git.saurik.com/apple/javascriptcore.git/blobdiff_plain/9dae56ea45a0f5f8136a5c93d6f3a7f99399ca73..14957cd040308e3eeec43d26bae5d76da13fcd85:/API/JSObjectRef.cpp diff --git a/API/JSObjectRef.cpp b/API/JSObjectRef.cpp index e81e512..2df010a 100644 --- a/API/JSObjectRef.cpp +++ b/API/JSObjectRef.cpp @@ -26,8 +26,10 @@ #include "config.h" #include "JSObjectRef.h" +#include "JSObjectRefPrivate.h" #include "APICast.h" +#include "CodeBlock.h" #include "DateConstructor.h" #include "ErrorConstructor.h" #include "FunctionConstructor.h" @@ -47,7 +49,6 @@ #include "ObjectPrototype.h" #include "PropertyNameArray.h" #include "RegExpConstructor.h" -#include using namespace JSC; @@ -58,7 +59,7 @@ JSClassRef JSClassCreate(const JSClassDefinition* definition) ? OpaqueJSClass::createNoAutomaticPrototype(definition) : OpaqueJSClass::create(definition); - return jsClass.release().releaseRef(); + return jsClass.release().leakRef(); } JSClassRef JSClassRetain(JSClassRef jsClass) @@ -75,15 +76,14 @@ void JSClassRelease(JSClassRef jsClass) JSObjectRef JSObjectMake(JSContextRef ctx, JSClassRef jsClass, void* data) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); if (!jsClass) - return toRef(new (exec) JSObject(exec->lexicalGlobalObject()->emptyObjectStructure())); // slightly more efficient + return toRef(constructEmptyObject(exec)); - JSCallbackObject* object = new (exec) JSCallbackObject(exec, exec->lexicalGlobalObject()->callbackObjectStructure(), jsClass, data); + JSCallbackObject* object = new (exec) JSCallbackObject(exec, exec->lexicalGlobalObject(), exec->lexicalGlobalObject()->callbackObjectStructure(), jsClass, data); if (JSObject* prototype = jsClass->prototype(exec)) - object->setPrototype(prototype); + object->setPrototype(exec->globalData(), prototype); return toRef(object); } @@ -91,46 +91,43 @@ JSObjectRef JSObjectMake(JSContextRef ctx, JSClassRef jsClass, void* data) JSObjectRef JSObjectMakeFunctionWithCallback(JSContextRef ctx, JSStringRef name, JSObjectCallAsFunctionCallback callAsFunction) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); Identifier nameID = name ? name->identifier(&exec->globalData()) : Identifier(exec, "anonymous"); - return toRef(new (exec) JSCallbackFunction(exec, callAsFunction, nameID)); + return toRef(new (exec) JSCallbackFunction(exec, exec->lexicalGlobalObject(), callAsFunction, nameID)); } JSObjectRef JSObjectMakeConstructor(JSContextRef ctx, JSClassRef jsClass, JSObjectCallAsConstructorCallback callAsConstructor) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); - JSValuePtr jsPrototype = jsClass - ? jsClass->prototype(exec) - : exec->lexicalGlobalObject()->objectPrototype(); - - JSCallbackConstructor* constructor = new (exec) JSCallbackConstructor(exec->lexicalGlobalObject()->callbackConstructorStructure(), jsClass, callAsConstructor); - constructor->putDirect(exec->propertyNames().prototype, jsPrototype, DontEnum | DontDelete | ReadOnly); + JSValue jsPrototype = jsClass ? jsClass->prototype(exec) : 0; + if (!jsPrototype) + jsPrototype = exec->lexicalGlobalObject()->objectPrototype(); + + JSCallbackConstructor* constructor = new (exec) JSCallbackConstructor(exec->lexicalGlobalObject(), exec->lexicalGlobalObject()->callbackConstructorStructure(), jsClass, callAsConstructor); + constructor->putDirect(exec->globalData(), exec->propertyNames().prototype, jsPrototype, DontEnum | DontDelete | ReadOnly); return toRef(constructor); } JSObjectRef JSObjectMakeFunction(JSContextRef ctx, JSStringRef name, unsigned parameterCount, const JSStringRef parameterNames[], JSStringRef body, JSStringRef sourceURL, int startingLineNumber, JSValueRef* exception) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); Identifier nameID = name ? name->identifier(&exec->globalData()) : Identifier(exec, "anonymous"); - ArgList args; + MarkedArgumentBuffer args; for (unsigned i = 0; i < parameterCount; i++) args.append(jsString(exec, parameterNames[i]->ustring())); args.append(jsString(exec, body->ustring())); - JSObject* result = constructFunction(exec, args, nameID, sourceURL->ustring(), startingLineNumber); + JSObject* result = constructFunction(exec, exec->lexicalGlobalObject(), args, nameID, sourceURL->ustring(), startingLineNumber); if (exec->hadException()) { if (exception) - *exception = toRef(exec->exception()); + *exception = toRef(exec, exec->exception()); exec->clearException(); result = 0; } @@ -140,14 +137,13 @@ JSObjectRef JSObjectMakeFunction(JSContextRef ctx, JSStringRef name, unsigned pa JSObjectRef JSObjectMakeArray(JSContextRef ctx, size_t argumentCount, const JSValueRef arguments[], JSValueRef* exception) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); JSObject* result; if (argumentCount) { - ArgList argList; + MarkedArgumentBuffer argList; for (size_t i = 0; i < argumentCount; ++i) - argList.append(toJS(arguments[i])); + argList.append(toJS(exec, arguments[i])); result = constructArray(exec, argList); } else @@ -155,7 +151,7 @@ JSObjectRef JSObjectMakeArray(JSContextRef ctx, size_t argumentCount, const JSVa if (exec->hadException()) { if (exception) - *exception = toRef(exec->exception()); + *exception = toRef(exec, exec->exception()); exec->clearException(); result = 0; } @@ -166,17 +162,16 @@ JSObjectRef JSObjectMakeArray(JSContextRef ctx, size_t argumentCount, const JSVa JSObjectRef JSObjectMakeDate(JSContextRef ctx, size_t argumentCount, const JSValueRef arguments[], JSValueRef* exception) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); - ArgList argList; + MarkedArgumentBuffer argList; for (size_t i = 0; i < argumentCount; ++i) - argList.append(toJS(arguments[i])); + argList.append(toJS(exec, arguments[i])); - JSObject* result = constructDate(exec, argList); + JSObject* result = constructDate(exec, exec->lexicalGlobalObject(), argList); if (exec->hadException()) { if (exception) - *exception = toRef(exec->exception()); + *exception = toRef(exec, exec->exception()); exec->clearException(); result = 0; } @@ -187,17 +182,15 @@ JSObjectRef JSObjectMakeDate(JSContextRef ctx, size_t argumentCount, const JSVal JSObjectRef JSObjectMakeError(JSContextRef ctx, size_t argumentCount, const JSValueRef arguments[], JSValueRef* exception) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); - ArgList argList; - for (size_t i = 0; i < argumentCount; ++i) - argList.append(toJS(arguments[i])); + JSValue message = argumentCount ? toJS(exec, arguments[0]) : jsUndefined(); + Structure* errorStructure = exec->lexicalGlobalObject()->errorStructure(); + JSObject* result = ErrorInstance::create(exec, errorStructure, message); - JSObject* result = constructError(exec, argList); if (exec->hadException()) { if (exception) - *exception = toRef(exec->exception()); + *exception = toRef(exec, exec->exception()); exec->clearException(); result = 0; } @@ -208,17 +201,16 @@ JSObjectRef JSObjectMakeError(JSContextRef ctx, size_t argumentCount, const JSVa JSObjectRef JSObjectMakeRegExp(JSContextRef ctx, size_t argumentCount, const JSValueRef arguments[], JSValueRef* exception) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); - ArgList argList; + MarkedArgumentBuffer argList; for (size_t i = 0; i < argumentCount; ++i) - argList.append(toJS(arguments[i])); + argList.append(toJS(exec, arguments[i])); - JSObject* result = constructRegExp(exec, argList); + JSObject* result = constructRegExp(exec, exec->lexicalGlobalObject(), argList); if (exec->hadException()) { if (exception) - *exception = toRef(exec->exception()); + *exception = toRef(exec, exec->exception()); exec->clearException(); result = 0; } @@ -226,25 +218,30 @@ JSObjectRef JSObjectMakeRegExp(JSContextRef ctx, size_t argumentCount, const JSV return toRef(result); } -JSValueRef JSObjectGetPrototype(JSContextRef, JSObjectRef object) +JSValueRef JSObjectGetPrototype(JSContextRef ctx, JSObjectRef object) { + ExecState* exec = toJS(ctx); + APIEntryShim entryShim(exec); + JSObject* jsObject = toJS(object); - return toRef(jsObject->prototype()); + return toRef(exec, jsObject->prototype()); } -void JSObjectSetPrototype(JSContextRef, JSObjectRef object, JSValueRef value) +void JSObjectSetPrototype(JSContextRef ctx, JSObjectRef object, JSValueRef value) { + ExecState* exec = toJS(ctx); + APIEntryShim entryShim(exec); + JSObject* jsObject = toJS(object); - JSValuePtr jsValue = toJS(value); + JSValue jsValue = toJS(exec, value); - jsObject->setPrototype(jsValue.isObject() ? jsValue : jsNull()); + jsObject->setPrototypeWithCycleCheck(exec->globalData(), jsValue.isObject() ? jsValue : jsNull()); } bool JSObjectHasProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); JSObject* jsObject = toJS(object); @@ -254,29 +251,27 @@ bool JSObjectHasProperty(JSContextRef ctx, JSObjectRef object, JSStringRef prope JSValueRef JSObjectGetProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName, JSValueRef* exception) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); JSObject* jsObject = toJS(object); - JSValuePtr jsValue = jsObject->get(exec, propertyName->identifier(&exec->globalData())); + JSValue jsValue = jsObject->get(exec, propertyName->identifier(&exec->globalData())); if (exec->hadException()) { if (exception) - *exception = toRef(exec->exception()); + *exception = toRef(exec, exec->exception()); exec->clearException(); } - return toRef(jsValue); + return toRef(exec, jsValue); } void JSObjectSetProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName, JSValueRef value, JSPropertyAttributes attributes, JSValueRef* exception) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); JSObject* jsObject = toJS(object); Identifier name(propertyName->identifier(&exec->globalData())); - JSValuePtr jsValue = toJS(value); + JSValue jsValue = toJS(exec, value); if (attributes && !jsObject->hasProperty(exec, name)) jsObject->putWithAttributes(exec, name, jsValue, attributes); @@ -287,7 +282,7 @@ void JSObjectSetProperty(JSContextRef ctx, JSObjectRef object, JSStringRef prope if (exec->hadException()) { if (exception) - *exception = toRef(exec->exception()); + *exception = toRef(exec, exec->exception()); exec->clearException(); } } @@ -295,34 +290,32 @@ void JSObjectSetProperty(JSContextRef ctx, JSObjectRef object, JSStringRef prope JSValueRef JSObjectGetPropertyAtIndex(JSContextRef ctx, JSObjectRef object, unsigned propertyIndex, JSValueRef* exception) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); JSObject* jsObject = toJS(object); - JSValuePtr jsValue = jsObject->get(exec, propertyIndex); + JSValue jsValue = jsObject->get(exec, propertyIndex); if (exec->hadException()) { if (exception) - *exception = toRef(exec->exception()); + *exception = toRef(exec, exec->exception()); exec->clearException(); } - return toRef(jsValue); + return toRef(exec, jsValue); } void JSObjectSetPropertyAtIndex(JSContextRef ctx, JSObjectRef object, unsigned propertyIndex, JSValueRef value, JSValueRef* exception) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); JSObject* jsObject = toJS(object); - JSValuePtr jsValue = toJS(value); + JSValue jsValue = toJS(exec, value); jsObject->put(exec, propertyIndex, jsValue); if (exec->hadException()) { if (exception) - *exception = toRef(exec->exception()); + *exception = toRef(exec, exec->exception()); exec->clearException(); } } @@ -330,15 +323,14 @@ void JSObjectSetPropertyAtIndex(JSContextRef ctx, JSObjectRef object, unsigned p bool JSObjectDeleteProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName, JSValueRef* exception) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); JSObject* jsObject = toJS(object); bool result = jsObject->deleteProperty(exec, propertyName->identifier(&exec->globalData())); if (exec->hadException()) { if (exception) - *exception = toRef(exec->exception()); + *exception = toRef(exec, exec->exception()); exec->clearException(); } return result; @@ -348,10 +340,10 @@ void* JSObjectGetPrivate(JSObjectRef object) { JSObject* jsObject = toJS(object); - if (jsObject->inherits(&JSCallbackObject::info)) + if (jsObject->inherits(&JSCallbackObject::s_info)) return static_cast*>(jsObject)->getPrivate(); - else if (jsObject->inherits(&JSCallbackObject::info)) - return static_cast*>(jsObject)->getPrivate(); + if (jsObject->inherits(&JSCallbackObject::s_info)) + return static_cast*>(jsObject)->getPrivate(); return 0; } @@ -360,17 +352,67 @@ bool JSObjectSetPrivate(JSObjectRef object, void* data) { JSObject* jsObject = toJS(object); - if (jsObject->inherits(&JSCallbackObject::info)) { + if (jsObject->inherits(&JSCallbackObject::s_info)) { static_cast*>(jsObject)->setPrivate(data); return true; - } else if (jsObject->inherits(&JSCallbackObject::info)) { - static_cast*>(jsObject)->setPrivate(data); + } + if (jsObject->inherits(&JSCallbackObject::s_info)) { + static_cast*>(jsObject)->setPrivate(data); return true; } return false; } +JSValueRef JSObjectGetPrivateProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName) +{ + ExecState* exec = toJS(ctx); + APIEntryShim entryShim(exec); + JSObject* jsObject = toJS(object); + JSValue result; + Identifier name(propertyName->identifier(&exec->globalData())); + if (jsObject->inherits(&JSCallbackObject::s_info)) + result = static_cast*>(jsObject)->getPrivateProperty(name); + else if (jsObject->inherits(&JSCallbackObject::s_info)) + result = static_cast*>(jsObject)->getPrivateProperty(name); + return toRef(exec, result); +} + +bool JSObjectSetPrivateProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName, JSValueRef value) +{ + ExecState* exec = toJS(ctx); + APIEntryShim entryShim(exec); + JSObject* jsObject = toJS(object); + JSValue jsValue = value ? toJS(exec, value) : JSValue(); + Identifier name(propertyName->identifier(&exec->globalData())); + if (jsObject->inherits(&JSCallbackObject::s_info)) { + static_cast*>(jsObject)->setPrivateProperty(exec->globalData(), name, jsValue); + return true; + } + if (jsObject->inherits(&JSCallbackObject::s_info)) { + static_cast*>(jsObject)->setPrivateProperty(exec->globalData(), name, jsValue); + return true; + } + return false; +} + +bool JSObjectDeletePrivateProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName) +{ + ExecState* exec = toJS(ctx); + APIEntryShim entryShim(exec); + JSObject* jsObject = toJS(object); + Identifier name(propertyName->identifier(&exec->globalData())); + if (jsObject->inherits(&JSCallbackObject::s_info)) { + static_cast*>(jsObject)->deletePrivateProperty(name); + return true; + } + if (jsObject->inherits(&JSCallbackObject::s_info)) { + static_cast*>(jsObject)->deletePrivateProperty(name); + return true; + } + return false; +} + bool JSObjectIsFunction(JSContextRef, JSObjectRef object) { CallData callData; @@ -380,8 +422,7 @@ bool JSObjectIsFunction(JSContextRef, JSObjectRef object) JSValueRef JSObjectCallAsFunction(JSContextRef ctx, JSObjectRef object, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef* exception) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); JSObject* jsObject = toJS(object); JSObject* jsThisObject = toJS(thisObject); @@ -389,19 +430,19 @@ JSValueRef JSObjectCallAsFunction(JSContextRef ctx, JSObjectRef object, JSObject if (!jsThisObject) jsThisObject = exec->globalThisValue(); - ArgList argList; + MarkedArgumentBuffer argList; for (size_t i = 0; i < argumentCount; i++) - argList.append(toJS(arguments[i])); + argList.append(toJS(exec, arguments[i])); CallData callData; CallType callType = jsObject->getCallData(callData); if (callType == CallTypeNone) return 0; - JSValueRef result = toRef(call(exec, jsObject, callType, callData, jsThisObject, argList)); + JSValueRef result = toRef(exec, call(exec, jsObject, callType, callData, jsThisObject, argList)); if (exec->hadException()) { if (exception) - *exception = toRef(exec->exception()); + *exception = toRef(exec, exec->exception()); exec->clearException(); result = 0; } @@ -418,8 +459,7 @@ bool JSObjectIsConstructor(JSContextRef, JSObjectRef object) JSObjectRef JSObjectCallAsConstructor(JSContextRef ctx, JSObjectRef object, size_t argumentCount, const JSValueRef arguments[], JSValueRef* exception) { ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); JSObject* jsObject = toJS(object); @@ -428,13 +468,13 @@ JSObjectRef JSObjectCallAsConstructor(JSContextRef ctx, JSObjectRef object, size if (constructType == ConstructTypeNone) return 0; - ArgList argList; + MarkedArgumentBuffer argList; for (size_t i = 0; i < argumentCount; i++) - argList.append(toJS(arguments[i])); + argList.append(toJS(exec, arguments[i])); JSObjectRef result = toRef(construct(exec, jsObject, constructType, constructData, argList)); if (exec->hadException()) { if (exception) - *exception = toRef(exec->exception()); + *exception = toRef(exec, exec->exception()); exec->clearException(); result = 0; } @@ -442,6 +482,8 @@ JSObjectRef JSObjectCallAsConstructor(JSContextRef ctx, JSObjectRef object, size } struct OpaqueJSPropertyNameArray { + WTF_MAKE_FAST_ALLOCATED; +public: OpaqueJSPropertyNameArray(JSGlobalData* globalData) : refCount(0) , globalData(globalData) @@ -457,8 +499,7 @@ JSPropertyNameArrayRef JSObjectCopyPropertyNames(JSContextRef ctx, JSObjectRef o { JSObject* jsObject = toJS(object); ExecState* exec = toJS(ctx); - exec->globalData().heap.registerThread(); - JSLock lock(exec); + APIEntryShim entryShim(exec); JSGlobalData* globalData = &exec->globalData(); @@ -469,7 +510,7 @@ JSPropertyNameArrayRef JSObjectCopyPropertyNames(JSContextRef ctx, JSObjectRef o size_t size = array.size(); propertyNames->array.reserveInitialCapacity(size); for (size_t i = 0; i < size; ++i) - propertyNames->array.append(JSRetainPtr(Adopt, OpaqueJSString::create(array[i].ustring()).releaseRef())); + propertyNames->array.append(JSRetainPtr(Adopt, OpaqueJSString::create(array[i].ustring()).leakRef())); return JSPropertyNameArrayRetain(propertyNames); } @@ -483,7 +524,7 @@ JSPropertyNameArrayRef JSPropertyNameArrayRetain(JSPropertyNameArrayRef array) void JSPropertyNameArrayRelease(JSPropertyNameArrayRef array) { if (--array->refCount == 0) { - JSLock lock(array->globalData->isSharedInstance); + APIEntryShim entryShim(array->globalData, false); delete array; } } @@ -501,9 +542,6 @@ JSStringRef JSPropertyNameArrayGetNameAtIndex(JSPropertyNameArrayRef array, size void JSPropertyNameAccumulatorAddName(JSPropertyNameAccumulatorRef array, JSStringRef propertyName) { PropertyNameArray* propertyNames = toJS(array); - - propertyNames->globalData()->heap.registerThread(); - JSLock lock(propertyNames->globalData()->isSharedInstance); - + APIEntryShim entryShim(propertyNames->globalData()); propertyNames->add(propertyName->identifier(propertyNames->globalData())); }