JavaScriptCore/API/JSObjectRef.cpp
changeset 0 4f2f89ce4247
equal deleted inserted replaced
-1:000000000000 0:4f2f89ce4247
       
     1 /*
       
     2  * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved.
       
     3  * Copyright (C) 2008 Kelvin W Sherlock (ksherlock@gmail.com)
       
     4  *
       
     5  * Redistribution and use in source and binary forms, with or without
       
     6  * modification, are permitted provided that the following conditions
       
     7  * are met:
       
     8  * 1. Redistributions of source code must retain the above copyright
       
     9  *    notice, this list of conditions and the following disclaimer.
       
    10  * 2. Redistributions in binary form must reproduce the above copyright
       
    11  *    notice, this list of conditions and the following disclaimer in the
       
    12  *    documentation and/or other materials provided with the distribution.
       
    13  *
       
    14  * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
       
    15  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
       
    16  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
       
    17  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE COMPUTER, INC. OR
       
    18  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
       
    19  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
       
    20  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
       
    21  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
       
    22  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
       
    23  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
       
    24  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 
       
    25  */
       
    26 
       
    27 #include "config.h"
       
    28 #include "JSObjectRef.h"
       
    29 #include "JSObjectRefPrivate.h"
       
    30 
       
    31 #include "APICast.h"
       
    32 #include "CodeBlock.h"
       
    33 #include "DateConstructor.h"
       
    34 #include "ErrorConstructor.h"
       
    35 #include "FunctionConstructor.h"
       
    36 #include "Identifier.h"
       
    37 #include "InitializeThreading.h"
       
    38 #include "JSArray.h"
       
    39 #include "JSCallbackConstructor.h"
       
    40 #include "JSCallbackFunction.h"
       
    41 #include "JSCallbackObject.h"
       
    42 #include "JSClassRef.h"
       
    43 #include "JSFunction.h"
       
    44 #include "JSGlobalObject.h"
       
    45 #include "JSObject.h"
       
    46 #include "JSRetainPtr.h"
       
    47 #include "JSString.h"
       
    48 #include "JSValueRef.h"
       
    49 #include "ObjectPrototype.h"
       
    50 #include "PropertyNameArray.h"
       
    51 #include "RegExpConstructor.h"
       
    52 
       
    53 using namespace JSC;
       
    54 
       
    55 JSClassRef JSClassCreate(const JSClassDefinition* definition)
       
    56 {
       
    57     initializeThreading();
       
    58     RefPtr<OpaqueJSClass> jsClass = (definition->attributes & kJSClassAttributeNoAutomaticPrototype)
       
    59         ? OpaqueJSClass::createNoAutomaticPrototype(definition)
       
    60         : OpaqueJSClass::create(definition);
       
    61     
       
    62     return jsClass.release().releaseRef();
       
    63 }
       
    64 
       
    65 JSClassRef JSClassRetain(JSClassRef jsClass)
       
    66 {
       
    67     jsClass->ref();
       
    68     return jsClass;
       
    69 }
       
    70 
       
    71 void JSClassRelease(JSClassRef jsClass)
       
    72 {
       
    73     jsClass->deref();
       
    74 }
       
    75 
       
    76 JSObjectRef JSObjectMake(JSContextRef ctx, JSClassRef jsClass, void* data)
       
    77 {
       
    78     ExecState* exec = toJS(ctx);
       
    79     APIEntryShim entryShim(exec);
       
    80 
       
    81     if (!jsClass)
       
    82         return toRef(new (exec) JSObject(exec->lexicalGlobalObject()->emptyObjectStructure())); // slightly more efficient
       
    83 
       
    84     JSCallbackObject<JSObjectWithGlobalObject>* object = new (exec) JSCallbackObject<JSObjectWithGlobalObject>(exec, exec->lexicalGlobalObject(), exec->lexicalGlobalObject()->callbackObjectStructure(), jsClass, data);
       
    85     if (JSObject* prototype = jsClass->prototype(exec))
       
    86         object->setPrototype(prototype);
       
    87 
       
    88     return toRef(object);
       
    89 }
       
    90 
       
    91 JSObjectRef JSObjectMakeFunctionWithCallback(JSContextRef ctx, JSStringRef name, JSObjectCallAsFunctionCallback callAsFunction)
       
    92 {
       
    93     ExecState* exec = toJS(ctx);
       
    94     APIEntryShim entryShim(exec);
       
    95 
       
    96     Identifier nameID = name ? name->identifier(&exec->globalData()) : Identifier(exec, "anonymous");
       
    97     
       
    98     return toRef(new (exec) JSCallbackFunction(exec, exec->lexicalGlobalObject(), callAsFunction, nameID));
       
    99 }
       
   100 
       
   101 JSObjectRef JSObjectMakeConstructor(JSContextRef ctx, JSClassRef jsClass, JSObjectCallAsConstructorCallback callAsConstructor)
       
   102 {
       
   103     ExecState* exec = toJS(ctx);
       
   104     APIEntryShim entryShim(exec);
       
   105 
       
   106     JSValue jsPrototype = jsClass ? jsClass->prototype(exec) : 0;
       
   107     if (!jsPrototype)
       
   108         jsPrototype = exec->lexicalGlobalObject()->objectPrototype();
       
   109 
       
   110     JSCallbackConstructor* constructor = new (exec) JSCallbackConstructor(exec->lexicalGlobalObject(), exec->lexicalGlobalObject()->callbackConstructorStructure(), jsClass, callAsConstructor);
       
   111     constructor->putDirect(exec->propertyNames().prototype, jsPrototype, DontEnum | DontDelete | ReadOnly);
       
   112     return toRef(constructor);
       
   113 }
       
   114 
       
   115 JSObjectRef JSObjectMakeFunction(JSContextRef ctx, JSStringRef name, unsigned parameterCount, const JSStringRef parameterNames[], JSStringRef body, JSStringRef sourceURL, int startingLineNumber, JSValueRef* exception)
       
   116 {
       
   117     ExecState* exec = toJS(ctx);
       
   118     APIEntryShim entryShim(exec);
       
   119 
       
   120     Identifier nameID = name ? name->identifier(&exec->globalData()) : Identifier(exec, "anonymous");
       
   121     
       
   122     MarkedArgumentBuffer args;
       
   123     for (unsigned i = 0; i < parameterCount; i++)
       
   124         args.append(jsString(exec, parameterNames[i]->ustring()));
       
   125     args.append(jsString(exec, body->ustring()));
       
   126 
       
   127     JSObject* result = constructFunction(exec, args, nameID, sourceURL->ustring(), startingLineNumber);
       
   128     if (exec->hadException()) {
       
   129         if (exception)
       
   130             *exception = toRef(exec, exec->exception());
       
   131         exec->clearException();
       
   132         result = 0;
       
   133     }
       
   134     return toRef(result);
       
   135 }
       
   136 
       
   137 JSObjectRef JSObjectMakeArray(JSContextRef ctx, size_t argumentCount, const JSValueRef arguments[],  JSValueRef* exception)
       
   138 {
       
   139     ExecState* exec = toJS(ctx);
       
   140     APIEntryShim entryShim(exec);
       
   141 
       
   142     JSObject* result;
       
   143     if (argumentCount) {
       
   144         MarkedArgumentBuffer argList;
       
   145         for (size_t i = 0; i < argumentCount; ++i)
       
   146             argList.append(toJS(exec, arguments[i]));
       
   147 
       
   148         result = constructArray(exec, argList);
       
   149     } else
       
   150         result = constructEmptyArray(exec);
       
   151 
       
   152     if (exec->hadException()) {
       
   153         if (exception)
       
   154             *exception = toRef(exec, exec->exception());
       
   155         exec->clearException();
       
   156         result = 0;
       
   157     }
       
   158 
       
   159     return toRef(result);
       
   160 }
       
   161 
       
   162 JSObjectRef JSObjectMakeDate(JSContextRef ctx, size_t argumentCount, const JSValueRef arguments[],  JSValueRef* exception)
       
   163 {
       
   164     ExecState* exec = toJS(ctx);
       
   165     APIEntryShim entryShim(exec);
       
   166 
       
   167     MarkedArgumentBuffer argList;
       
   168     for (size_t i = 0; i < argumentCount; ++i)
       
   169         argList.append(toJS(exec, arguments[i]));
       
   170 
       
   171     JSObject* result = constructDate(exec, argList);
       
   172     if (exec->hadException()) {
       
   173         if (exception)
       
   174             *exception = toRef(exec, exec->exception());
       
   175         exec->clearException();
       
   176         result = 0;
       
   177     }
       
   178 
       
   179     return toRef(result);
       
   180 }
       
   181 
       
   182 JSObjectRef JSObjectMakeError(JSContextRef ctx, size_t argumentCount, const JSValueRef arguments[],  JSValueRef* exception)
       
   183 {
       
   184     ExecState* exec = toJS(ctx);
       
   185     APIEntryShim entryShim(exec);
       
   186 
       
   187     JSValue message = argumentCount ? toJS(exec, arguments[0]) : jsUndefined();
       
   188     Structure* errorStructure = exec->lexicalGlobalObject()->errorStructure();
       
   189     JSObject* result = ErrorInstance::create(exec, errorStructure, message);
       
   190 
       
   191     if (exec->hadException()) {
       
   192         if (exception)
       
   193             *exception = toRef(exec, exec->exception());
       
   194         exec->clearException();
       
   195         result = 0;
       
   196     }
       
   197 
       
   198     return toRef(result);
       
   199 }
       
   200 
       
   201 JSObjectRef JSObjectMakeRegExp(JSContextRef ctx, size_t argumentCount, const JSValueRef arguments[],  JSValueRef* exception)
       
   202 {
       
   203     ExecState* exec = toJS(ctx);
       
   204     APIEntryShim entryShim(exec);
       
   205 
       
   206     MarkedArgumentBuffer argList;
       
   207     for (size_t i = 0; i < argumentCount; ++i)
       
   208         argList.append(toJS(exec, arguments[i]));
       
   209 
       
   210     JSObject* result = constructRegExp(exec, argList);
       
   211     if (exec->hadException()) {
       
   212         if (exception)
       
   213             *exception = toRef(exec, exec->exception());
       
   214         exec->clearException();
       
   215         result = 0;
       
   216     }
       
   217     
       
   218     return toRef(result);
       
   219 }
       
   220 
       
   221 JSValueRef JSObjectGetPrototype(JSContextRef ctx, JSObjectRef object)
       
   222 {
       
   223     ExecState* exec = toJS(ctx);
       
   224     APIEntryShim entryShim(exec);
       
   225 
       
   226     JSObject* jsObject = toJS(object);
       
   227     return toRef(exec, jsObject->prototype());
       
   228 }
       
   229 
       
   230 void JSObjectSetPrototype(JSContextRef ctx, JSObjectRef object, JSValueRef value)
       
   231 {
       
   232     ExecState* exec = toJS(ctx);
       
   233     APIEntryShim entryShim(exec);
       
   234 
       
   235     JSObject* jsObject = toJS(object);
       
   236     JSValue jsValue = toJS(exec, value);
       
   237 
       
   238     jsObject->setPrototypeWithCycleCheck(jsValue.isObject() ? jsValue : jsNull());
       
   239 }
       
   240 
       
   241 bool JSObjectHasProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName)
       
   242 {
       
   243     ExecState* exec = toJS(ctx);
       
   244     APIEntryShim entryShim(exec);
       
   245 
       
   246     JSObject* jsObject = toJS(object);
       
   247     
       
   248     return jsObject->hasProperty(exec, propertyName->identifier(&exec->globalData()));
       
   249 }
       
   250 
       
   251 JSValueRef JSObjectGetProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName, JSValueRef* exception)
       
   252 {
       
   253     ExecState* exec = toJS(ctx);
       
   254     APIEntryShim entryShim(exec);
       
   255 
       
   256     JSObject* jsObject = toJS(object);
       
   257 
       
   258     JSValue jsValue = jsObject->get(exec, propertyName->identifier(&exec->globalData()));
       
   259     if (exec->hadException()) {
       
   260         if (exception)
       
   261             *exception = toRef(exec, exec->exception());
       
   262         exec->clearException();
       
   263     }
       
   264     return toRef(exec, jsValue);
       
   265 }
       
   266 
       
   267 void JSObjectSetProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName, JSValueRef value, JSPropertyAttributes attributes, JSValueRef* exception)
       
   268 {
       
   269     ExecState* exec = toJS(ctx);
       
   270     APIEntryShim entryShim(exec);
       
   271 
       
   272     JSObject* jsObject = toJS(object);
       
   273     Identifier name(propertyName->identifier(&exec->globalData()));
       
   274     JSValue jsValue = toJS(exec, value);
       
   275 
       
   276     if (attributes && !jsObject->hasProperty(exec, name))
       
   277         jsObject->putWithAttributes(exec, name, jsValue, attributes);
       
   278     else {
       
   279         PutPropertySlot slot;
       
   280         jsObject->put(exec, name, jsValue, slot);
       
   281     }
       
   282 
       
   283     if (exec->hadException()) {
       
   284         if (exception)
       
   285             *exception = toRef(exec, exec->exception());
       
   286         exec->clearException();
       
   287     }
       
   288 }
       
   289 
       
   290 JSValueRef JSObjectGetPropertyAtIndex(JSContextRef ctx, JSObjectRef object, unsigned propertyIndex, JSValueRef* exception)
       
   291 {
       
   292     ExecState* exec = toJS(ctx);
       
   293     APIEntryShim entryShim(exec);
       
   294 
       
   295     JSObject* jsObject = toJS(object);
       
   296 
       
   297     JSValue jsValue = jsObject->get(exec, propertyIndex);
       
   298     if (exec->hadException()) {
       
   299         if (exception)
       
   300             *exception = toRef(exec, exec->exception());
       
   301         exec->clearException();
       
   302     }
       
   303     return toRef(exec, jsValue);
       
   304 }
       
   305 
       
   306 
       
   307 void JSObjectSetPropertyAtIndex(JSContextRef ctx, JSObjectRef object, unsigned propertyIndex, JSValueRef value, JSValueRef* exception)
       
   308 {
       
   309     ExecState* exec = toJS(ctx);
       
   310     APIEntryShim entryShim(exec);
       
   311 
       
   312     JSObject* jsObject = toJS(object);
       
   313     JSValue jsValue = toJS(exec, value);
       
   314     
       
   315     jsObject->put(exec, propertyIndex, jsValue);
       
   316     if (exec->hadException()) {
       
   317         if (exception)
       
   318             *exception = toRef(exec, exec->exception());
       
   319         exec->clearException();
       
   320     }
       
   321 }
       
   322 
       
   323 bool JSObjectDeleteProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName, JSValueRef* exception)
       
   324 {
       
   325     ExecState* exec = toJS(ctx);
       
   326     APIEntryShim entryShim(exec);
       
   327 
       
   328     JSObject* jsObject = toJS(object);
       
   329 
       
   330     bool result = jsObject->deleteProperty(exec, propertyName->identifier(&exec->globalData()));
       
   331     if (exec->hadException()) {
       
   332         if (exception)
       
   333             *exception = toRef(exec, exec->exception());
       
   334         exec->clearException();
       
   335     }
       
   336     return result;
       
   337 }
       
   338 
       
   339 void* JSObjectGetPrivate(JSObjectRef object)
       
   340 {
       
   341     JSObject* jsObject = toJS(object);
       
   342     
       
   343     if (jsObject->inherits(&JSCallbackObject<JSGlobalObject>::info))
       
   344         return static_cast<JSCallbackObject<JSGlobalObject>*>(jsObject)->getPrivate();
       
   345     else if (jsObject->inherits(&JSCallbackObject<JSObjectWithGlobalObject>::info))
       
   346         return static_cast<JSCallbackObject<JSObjectWithGlobalObject>*>(jsObject)->getPrivate();
       
   347     
       
   348     return 0;
       
   349 }
       
   350 
       
   351 bool JSObjectSetPrivate(JSObjectRef object, void* data)
       
   352 {
       
   353     JSObject* jsObject = toJS(object);
       
   354     
       
   355     if (jsObject->inherits(&JSCallbackObject<JSGlobalObject>::info)) {
       
   356         static_cast<JSCallbackObject<JSGlobalObject>*>(jsObject)->setPrivate(data);
       
   357         return true;
       
   358     } else if (jsObject->inherits(&JSCallbackObject<JSObjectWithGlobalObject>::info)) {
       
   359         static_cast<JSCallbackObject<JSObjectWithGlobalObject>*>(jsObject)->setPrivate(data);
       
   360         return true;
       
   361     }
       
   362         
       
   363     return false;
       
   364 }
       
   365 
       
   366 JSValueRef JSObjectGetPrivateProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName)
       
   367 {
       
   368     ExecState* exec = toJS(ctx);
       
   369     APIEntryShim entryShim(exec);
       
   370     JSObject* jsObject = toJS(object);
       
   371     JSValue result;
       
   372     Identifier name(propertyName->identifier(&exec->globalData()));
       
   373     if (jsObject->inherits(&JSCallbackObject<JSGlobalObject>::info))
       
   374         result = static_cast<JSCallbackObject<JSGlobalObject>*>(jsObject)->getPrivateProperty(name);
       
   375     else if (jsObject->inherits(&JSCallbackObject<JSObjectWithGlobalObject>::info))
       
   376         result = static_cast<JSCallbackObject<JSObjectWithGlobalObject>*>(jsObject)->getPrivateProperty(name);
       
   377     return toRef(exec, result);
       
   378 }
       
   379 
       
   380 bool JSObjectSetPrivateProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName, JSValueRef value)
       
   381 {
       
   382     ExecState* exec = toJS(ctx);
       
   383     APIEntryShim entryShim(exec);
       
   384     JSObject* jsObject = toJS(object);
       
   385     JSValue jsValue = toJS(exec, value);
       
   386     Identifier name(propertyName->identifier(&exec->globalData()));
       
   387     if (jsObject->inherits(&JSCallbackObject<JSGlobalObject>::info)) {
       
   388         static_cast<JSCallbackObject<JSGlobalObject>*>(jsObject)->setPrivateProperty(name, jsValue);
       
   389         return true;
       
   390     }
       
   391     if (jsObject->inherits(&JSCallbackObject<JSObjectWithGlobalObject>::info)) {
       
   392         static_cast<JSCallbackObject<JSObjectWithGlobalObject>*>(jsObject)->setPrivateProperty(name, jsValue);
       
   393         return true;
       
   394     }
       
   395     return false;
       
   396 }
       
   397 
       
   398 bool JSObjectDeletePrivateProperty(JSContextRef ctx, JSObjectRef object, JSStringRef propertyName)
       
   399 {
       
   400     ExecState* exec = toJS(ctx);
       
   401     APIEntryShim entryShim(exec);
       
   402     JSObject* jsObject = toJS(object);
       
   403     Identifier name(propertyName->identifier(&exec->globalData()));
       
   404     if (jsObject->inherits(&JSCallbackObject<JSGlobalObject>::info)) {
       
   405         static_cast<JSCallbackObject<JSGlobalObject>*>(jsObject)->deletePrivateProperty(name);
       
   406         return true;
       
   407     }
       
   408     if (jsObject->inherits(&JSCallbackObject<JSObjectWithGlobalObject>::info)) {
       
   409         static_cast<JSCallbackObject<JSObjectWithGlobalObject>*>(jsObject)->deletePrivateProperty(name);
       
   410         return true;
       
   411     }
       
   412     return false;
       
   413 }
       
   414 
       
   415 bool JSObjectIsFunction(JSContextRef, JSObjectRef object)
       
   416 {
       
   417     CallData callData;
       
   418     return toJS(object)->getCallData(callData) != CallTypeNone;
       
   419 }
       
   420 
       
   421 JSValueRef JSObjectCallAsFunction(JSContextRef ctx, JSObjectRef object, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef* exception)
       
   422 {
       
   423     ExecState* exec = toJS(ctx);
       
   424     APIEntryShim entryShim(exec);
       
   425 
       
   426     JSObject* jsObject = toJS(object);
       
   427     JSObject* jsThisObject = toJS(thisObject);
       
   428 
       
   429     if (!jsThisObject)
       
   430         jsThisObject = exec->globalThisValue();
       
   431 
       
   432     MarkedArgumentBuffer argList;
       
   433     for (size_t i = 0; i < argumentCount; i++)
       
   434         argList.append(toJS(exec, arguments[i]));
       
   435 
       
   436     CallData callData;
       
   437     CallType callType = jsObject->getCallData(callData);
       
   438     if (callType == CallTypeNone)
       
   439         return 0;
       
   440 
       
   441     JSValueRef result = toRef(exec, call(exec, jsObject, callType, callData, jsThisObject, argList));
       
   442     if (exec->hadException()) {
       
   443         if (exception)
       
   444             *exception = toRef(exec, exec->exception());
       
   445         exec->clearException();
       
   446         result = 0;
       
   447     }
       
   448     return result;
       
   449 }
       
   450 
       
   451 bool JSObjectIsConstructor(JSContextRef, JSObjectRef object)
       
   452 {
       
   453     JSObject* jsObject = toJS(object);
       
   454     ConstructData constructData;
       
   455     return jsObject->getConstructData(constructData) != ConstructTypeNone;
       
   456 }
       
   457 
       
   458 JSObjectRef JSObjectCallAsConstructor(JSContextRef ctx, JSObjectRef object, size_t argumentCount, const JSValueRef arguments[], JSValueRef* exception)
       
   459 {
       
   460     ExecState* exec = toJS(ctx);
       
   461     APIEntryShim entryShim(exec);
       
   462 
       
   463     JSObject* jsObject = toJS(object);
       
   464 
       
   465     ConstructData constructData;
       
   466     ConstructType constructType = jsObject->getConstructData(constructData);
       
   467     if (constructType == ConstructTypeNone)
       
   468         return 0;
       
   469 
       
   470     MarkedArgumentBuffer argList;
       
   471     for (size_t i = 0; i < argumentCount; i++)
       
   472         argList.append(toJS(exec, arguments[i]));
       
   473     JSObjectRef result = toRef(construct(exec, jsObject, constructType, constructData, argList));
       
   474     if (exec->hadException()) {
       
   475         if (exception)
       
   476             *exception = toRef(exec, exec->exception());
       
   477         exec->clearException();
       
   478         result = 0;
       
   479     }
       
   480     return result;
       
   481 }
       
   482 
       
   483 struct OpaqueJSPropertyNameArray : FastAllocBase {
       
   484     OpaqueJSPropertyNameArray(JSGlobalData* globalData)
       
   485         : refCount(0)
       
   486         , globalData(globalData)
       
   487     {
       
   488     }
       
   489     
       
   490     unsigned refCount;
       
   491     JSGlobalData* globalData;
       
   492     Vector<JSRetainPtr<JSStringRef> > array;
       
   493 };
       
   494 
       
   495 JSPropertyNameArrayRef JSObjectCopyPropertyNames(JSContextRef ctx, JSObjectRef object)
       
   496 {
       
   497     JSObject* jsObject = toJS(object);
       
   498     ExecState* exec = toJS(ctx);
       
   499     APIEntryShim entryShim(exec);
       
   500 
       
   501     JSGlobalData* globalData = &exec->globalData();
       
   502 
       
   503     JSPropertyNameArrayRef propertyNames = new OpaqueJSPropertyNameArray(globalData);
       
   504     PropertyNameArray array(globalData);
       
   505     jsObject->getPropertyNames(exec, array);
       
   506 
       
   507     size_t size = array.size();
       
   508     propertyNames->array.reserveInitialCapacity(size);
       
   509     for (size_t i = 0; i < size; ++i)
       
   510         propertyNames->array.append(JSRetainPtr<JSStringRef>(Adopt, OpaqueJSString::create(array[i].ustring()).releaseRef()));
       
   511     
       
   512     return JSPropertyNameArrayRetain(propertyNames);
       
   513 }
       
   514 
       
   515 JSPropertyNameArrayRef JSPropertyNameArrayRetain(JSPropertyNameArrayRef array)
       
   516 {
       
   517     ++array->refCount;
       
   518     return array;
       
   519 }
       
   520 
       
   521 void JSPropertyNameArrayRelease(JSPropertyNameArrayRef array)
       
   522 {
       
   523     if (--array->refCount == 0) {
       
   524         APIEntryShim entryShim(array->globalData, false);
       
   525         delete array;
       
   526     }
       
   527 }
       
   528 
       
   529 size_t JSPropertyNameArrayGetCount(JSPropertyNameArrayRef array)
       
   530 {
       
   531     return array->array.size();
       
   532 }
       
   533 
       
   534 JSStringRef JSPropertyNameArrayGetNameAtIndex(JSPropertyNameArrayRef array, size_t index)
       
   535 {
       
   536     return array->array[static_cast<unsigned>(index)].get();
       
   537 }
       
   538 
       
   539 void JSPropertyNameAccumulatorAddName(JSPropertyNameAccumulatorRef array, JSStringRef propertyName)
       
   540 {
       
   541     PropertyNameArray* propertyNames = toJS(array);
       
   542     APIEntryShim entryShim(propertyNames->globalData());
       
   543     propertyNames->add(propertyName->identifier(propertyNames->globalData()));
       
   544 }