• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2005 Apple Computer, Inc.  All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  *
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  * 3.  Neither the name of Apple Computer, Inc. ("Apple") nor the names of
14  *     its contributors may be used to endorse or promote products derived
15  *     from this software without specific prior written permission.
16  *
17  * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
18  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
19  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
20  * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
21  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
22  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
23  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
24  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27  */
28 
29 #include "config.h"
30 #include "JSValueWrapper.h"
31 #include "JSRun.h"
32 #include <JavaScriptCore/PropertyNameArray.h>
33 #include <pthread.h>
34 
JSValueWrapper(JSValuePtr inValue)35 JSValueWrapper::JSValueWrapper(JSValuePtr inValue)
36     : fValue(inValue)
37 {
38 }
39 
~JSValueWrapper()40 JSValueWrapper::~JSValueWrapper()
41 {
42 }
43 
GetValue()44 JSValuePtr JSValueWrapper::GetValue()
45 {
46     return fValue.get();
47 }
48 
GetJSObectCallBacks(JSObjectCallBacks & callBacks)49 void JSValueWrapper::GetJSObectCallBacks(JSObjectCallBacks& callBacks)
50 {
51     callBacks.dispose = (JSObjectDisposeProcPtr)JSValueWrapper::JSObjectDispose;
52     callBacks.equal = (JSObjectEqualProcPtr)0;
53     callBacks.copyPropertyNames = (JSObjectCopyPropertyNamesProcPtr)JSValueWrapper::JSObjectCopyPropertyNames;
54     callBacks.copyCFValue = (JSObjectCopyCFValueProcPtr)JSValueWrapper::JSObjectCopyCFValue;
55     callBacks.copyProperty = (JSObjectCopyPropertyProcPtr)JSValueWrapper::JSObjectCopyProperty;
56     callBacks.setProperty = (JSObjectSetPropertyProcPtr)JSValueWrapper::JSObjectSetProperty;
57     callBacks.callFunction = (JSObjectCallFunctionProcPtr)JSValueWrapper::JSObjectCallFunction;
58 }
59 
JSObjectDispose(void * data)60 void JSValueWrapper::JSObjectDispose(void *data)
61 {
62     JSValueWrapper* ptr = (JSValueWrapper*)data;
63     delete ptr;
64 }
65 
66 
JSObjectCopyPropertyNames(void * data)67 CFArrayRef JSValueWrapper::JSObjectCopyPropertyNames(void *data)
68 {
69     JSLock lock(true);
70 
71     CFMutableArrayRef result = 0;
72     JSValueWrapper* ptr = (JSValueWrapper*)data;
73     if (ptr)
74     {
75         ExecState* exec = getThreadGlobalExecState();
76         JSObject* object = ptr->GetValue().toObject(exec);
77         PropertyNameArray propNames(exec);
78         object->getPropertyNames(exec, propNames);
79         PropertyNameArray::const_iterator iterator = propNames.begin();
80 
81         while (iterator != propNames.end()) {
82             Identifier name = *iterator;
83             CFStringRef nameStr = IdentifierToCFString(name);
84 
85             if (!result)
86             {
87                 result = CFArrayCreateMutable(0, 0, &kCFTypeArrayCallBacks);
88             }
89             if (result && nameStr)
90             {
91                 CFArrayAppendValue(result, nameStr);
92             }
93             ReleaseCFType(nameStr);
94             iterator++;
95         }
96 
97     }
98     return result;
99 }
100 
101 
JSObjectCopyProperty(void * data,CFStringRef propertyName)102 JSObjectRef JSValueWrapper::JSObjectCopyProperty(void *data, CFStringRef propertyName)
103 {
104     JSLock lock(true);
105 
106     JSObjectRef result = 0;
107     JSValueWrapper* ptr = (JSValueWrapper*)data;
108     if (ptr)
109     {
110         ExecState* exec = getThreadGlobalExecState();
111         JSValuePtr propValue = ptr->GetValue().toObject(exec)->get(exec, CFStringToIdentifier(propertyName, exec));
112         JSValueWrapper* wrapperValue = new JSValueWrapper(propValue);
113 
114         JSObjectCallBacks callBacks;
115         GetJSObectCallBacks(callBacks);
116         result = JSObjectCreateInternal(wrapperValue, &callBacks, JSValueWrapper::JSObjectMark, kJSUserObjectDataTypeJSValueWrapper);
117 
118         if (!result)
119         {
120             delete wrapperValue;
121         }
122     }
123     return result;
124 }
125 
JSObjectSetProperty(void * data,CFStringRef propertyName,JSObjectRef jsValue)126 void JSValueWrapper::JSObjectSetProperty(void *data, CFStringRef propertyName, JSObjectRef jsValue)
127 {
128     JSLock lock(true);
129 
130     JSValueWrapper* ptr = (JSValueWrapper*)data;
131     if (ptr)
132     {
133         ExecState* exec = getThreadGlobalExecState();
134         JSValuePtr value = JSObjectKJSValue((JSUserObject*)jsValue);
135         JSObject *objValue = ptr->GetValue().toObject(exec);
136         PutPropertySlot slot;
137         objValue->put(exec, CFStringToIdentifier(propertyName, exec), value, slot);
138     }
139 }
140 
JSObjectCallFunction(void * data,JSObjectRef thisObj,CFArrayRef args)141 JSObjectRef JSValueWrapper::JSObjectCallFunction(void *data, JSObjectRef thisObj, CFArrayRef args)
142 {
143     JSLock lock(true);
144 
145     JSObjectRef result = 0;
146     JSValueWrapper* ptr = (JSValueWrapper*)data;
147     if (ptr)
148     {
149         ExecState* exec = getThreadGlobalExecState();
150 
151         JSValuePtr value = JSObjectKJSValue((JSUserObject*)thisObj);
152         JSObject* ksjThisObj = value.toObject(exec);
153         JSObject* objValue = ptr->GetValue().toObject(exec);
154 
155         ArgList listArgs;
156         CFIndex argCount = args ? CFArrayGetCount(args) : 0;
157         for (CFIndex i = 0; i < argCount; i++)
158         {
159             JSObjectRef jsArg = (JSObjectRef)CFArrayGetValueAtIndex(args, i);
160             JSValuePtr kgsArg = JSObjectKJSValue((JSUserObject*)jsArg);
161             listArgs.append(kgsArg);
162         }
163 
164         CallData callData;
165         CallType callType = objValue->getCallData(callData);
166         if (callType == CallTypeNone)
167             return 0;
168         JSValuePtr  resultValue = call(exec, objValue, callType, callData, ksjThisObj, listArgs);
169         JSValueWrapper* wrapperValue = new JSValueWrapper(resultValue);
170         JSObjectCallBacks callBacks;
171         GetJSObectCallBacks(callBacks);
172         result = JSObjectCreate(wrapperValue, &callBacks);
173         if (!result)
174         {
175             delete wrapperValue;
176         }
177     }
178     return result;
179 }
180 
JSObjectCopyCFValue(void * data)181 CFTypeRef JSValueWrapper::JSObjectCopyCFValue(void *data)
182 {
183     JSLock lock(true);
184 
185     CFTypeRef result = 0;
186     JSValueWrapper* ptr = (JSValueWrapper*)data;
187     if (ptr)
188     {
189         result = KJSValueToCFType(ptr->GetValue(), getThreadGlobalExecState());
190     }
191     return result;
192 }
193 
JSObjectMark(void * data)194 void JSValueWrapper::JSObjectMark(void *data)
195 {
196     JSValueWrapper* ptr = (JSValueWrapper*)data;
197     if (ptr)
198     {
199         ptr->fValue.get().mark();
200     }
201 }
202