+ FunctionRareData* rareData(ExecState* exec, unsigned inlineCapacity)
+ {
+ if (UNLIKELY(!m_rareData))
+ return allocateAndInitializeRareData(exec, inlineCapacity);
+ if (UNLIKELY(!m_rareData->isInitialized()))
+ return initializeRareData(exec, inlineCapacity);
+ return m_rareData.get();
+ }
+
+ FunctionRareData* rareData()
+ {
+ FunctionRareData* rareData = m_rareData.get();
+
+ // The JS thread may be concurrently creating the rare data
+ // If we see it, we want to ensure it has been properly created
+ WTF::loadLoadFence();
+
+ return rareData;
+ }
+
+ bool isHostOrBuiltinFunction() const;
+ bool isBuiltinFunction() const;
+ JS_EXPORT_PRIVATE bool isHostFunctionNonInline() const;
+ bool isClassConstructorFunction() const;
+
+protected:
+ JS_EXPORT_PRIVATE JSFunction(VM&, JSGlobalObject*, Structure*);
+ JSFunction(VM&, FunctionExecutable*, JSScope*);
+
+ void finishCreation(VM&, NativeExecutable*, int length, const String& name);
+ using Base::finishCreation;
+
+ FunctionRareData* allocateAndInitializeRareData(ExecState*, size_t inlineCapacity);
+ FunctionRareData* initializeRareData(ExecState*, size_t inlineCapacity);
+
+ static bool getOwnPropertySlot(JSObject*, ExecState*, PropertyName, PropertySlot&);
+ static void getOwnNonIndexPropertyNames(JSObject*, ExecState*, PropertyNameArray&, EnumerationMode = EnumerationMode());
+ static bool defineOwnProperty(JSObject*, ExecState*, PropertyName, const PropertyDescriptor&, bool shouldThrow);
+
+ static void put(JSCell*, ExecState*, PropertyName, JSValue, PutPropertySlot&);
+
+ static bool deleteProperty(JSCell*, ExecState*, PropertyName);
+
+ static void visitChildren(JSCell*, SlotVisitor&);
+
+private:
+ static JSFunction* createImpl(VM& vm, FunctionExecutable* executable, JSScope* scope)
+ {
+ JSFunction* function = new (NotNull, allocateCell<JSFunction>(vm.heap)) JSFunction(vm, executable, scope);
+ ASSERT(function->structure()->globalObject());
+ function->finishCreation(vm);
+ return function;
+ }
+
+ friend class LLIntOffsetsExtractor;
+
+ static EncodedJSValue argumentsGetter(ExecState*, JSObject*, EncodedJSValue, PropertyName);
+ static EncodedJSValue callerGetter(ExecState*, JSObject*, EncodedJSValue, PropertyName);
+ static EncodedJSValue lengthGetter(ExecState*, JSObject*, EncodedJSValue, PropertyName);
+ static EncodedJSValue nameGetter(ExecState*, JSObject*, EncodedJSValue, PropertyName);
+
+ WriteBarrier<ExecutableBase> m_executable;
+ WriteBarrier<FunctionRareData> m_rareData;
+};
+