Ignore:
Timestamp:
Jul 28, 2014, 1:43:57 PM (11 years ago)
Author:
[email protected]
Message:

REGRESSION: JSObjectSetPrototype() does not work on result of JSGetGlobalObject()
https://bugs.webkit.org/show_bug.cgi?id=135322

Reviewed by Oliver Hunt.

The prototype chain of the JSProxy object should match that of the JSGlobalObject.

This is a separate but related issue with JSObjectSetPrototype which doesn't correctly
account for JSProxies. I also audited the rest of the C API to check that we correctly
handle JSProxies in all other situations where we expect a JSCallbackObject of some sort
and found some SPI calls (JSObject*PrivateProperty) that didn't behave correctly when
passed a JSProxy.

I also added some new tests for these cases.

  • API/JSObjectRef.cpp:

(JSObjectSetPrototype):
(JSObjectGetPrivateProperty):
(JSObjectSetPrivateProperty):
(JSObjectDeletePrivateProperty):

  • API/JSWeakObjectMapRefPrivate.cpp:
  • API/tests/CustomGlobalObjectClassTest.c:

(globalObjectSetPrototypeTest):
(globalObjectPrivatePropertyTest):

  • API/tests/CustomGlobalObjectClassTest.h:
  • API/tests/testapi.c:

(main):

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/JavaScriptCore/API/JSObjectRef.cpp

    r167313 r171691  
    303303    JSValue jsValue = toJS(exec, value);
    304304
     305    if (JSProxy* proxy = jsDynamicCast<JSProxy*>(jsObject)) {
     306        if (JSGlobalObject* globalObject = jsDynamicCast<JSGlobalObject*>(proxy->target())) {
     307            globalObject->resetPrototype(exec->vm(), jsValue.isObject() ? jsValue : jsNull());
     308            return;
     309        }
     310        // Someday we might use proxies for something other than JSGlobalObjects, but today is not that day.
     311        RELEASE_ASSERT_NOT_REACHED();
     312    }
    305313    jsObject->setPrototypeWithCycleCheck(exec, jsValue.isObject() ? jsValue : jsNull());
    306314}
     
    502510    JSValue result;
    503511    Identifier name(propertyName->identifier(&exec->vm()));
     512
     513    // Get wrapped object if proxied
     514    if (jsObject->inherits(JSProxy::info()))
     515        jsObject = jsCast<JSProxy*>(jsObject)->target();
     516
    504517    if (jsObject->inherits(JSCallbackObject<JSGlobalObject>::info()))
    505518        result = jsCast<JSCallbackObject<JSGlobalObject>*>(jsObject)->getPrivateProperty(name);
     
    520533    JSValue jsValue = value ? toJS(exec, value) : JSValue();
    521534    Identifier name(propertyName->identifier(&exec->vm()));
     535
     536    // Get wrapped object if proxied
     537    if (jsObject->inherits(JSProxy::info()))
     538        jsObject = jsCast<JSProxy*>(jsObject)->target();
     539
    522540    if (jsObject->inherits(JSCallbackObject<JSGlobalObject>::info())) {
    523541        jsCast<JSCallbackObject<JSGlobalObject>*>(jsObject)->setPrivateProperty(exec->vm(), name, jsValue);
     
    543561    JSObject* jsObject = toJS(object);
    544562    Identifier name(propertyName->identifier(&exec->vm()));
     563
     564    // Get wrapped object if proxied
     565    if (jsObject->inherits(JSProxy::info()))
     566        jsObject = jsCast<JSProxy*>(jsObject)->target();
     567
    545568    if (jsObject->inherits(JSCallbackObject<JSGlobalObject>::info())) {
    546569        jsCast<JSCallbackObject<JSGlobalObject>*>(jsObject)->deletePrivateProperty(name);
Note: See TracChangeset for help on using the changeset viewer.