| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268 |
- //-------------------------------------------------------------------------------------------------------
- // Copyright (C) Microsoft. All rights reserved.
- // Licensed under the MIT license. See LICENSE.txt file in the project root for full license information.
- //-------------------------------------------------------------------------------------------------------
- #pragma once
- namespace Js
- {
- class ScriptFunctionBase : public JavascriptFunction
- {
- protected:
- ScriptFunctionBase(DynamicType * type);
- ScriptFunctionBase(DynamicType * type, FunctionInfo * functionInfo);
- DEFINE_VTABLE_CTOR(ScriptFunctionBase, JavascriptFunction);
- public:
- virtual Var GetHomeObj() const = 0;
- virtual void SetHomeObj(Var homeObj) = 0;
- virtual void SetComputedNameVar(Var computedNameVar) = 0;
- virtual Var GetComputedNameVar() const = 0;
- virtual bool IsAnonymousFunction() const = 0;
- };
- template <> bool VarIsImpl<ScriptFunctionBase>(RecyclableObject* obj);
- template <class BaseClass>
- class FunctionWithComputedName : public BaseClass
- {
- private:
- Field(Var) computedNameVar;
- protected:
- DEFINE_VTABLE_CTOR(FunctionWithComputedName<BaseClass>, BaseClass);
- DEFINE_MARSHAL_OBJECT_TO_SCRIPT_CONTEXT(FunctionWithComputedName<BaseClass>);
- public:
- FunctionWithComputedName(FunctionProxy * proxy, ScriptFunctionType* deferredPrototypeType)
- : BaseClass(proxy, deferredPrototypeType), computedNameVar(nullptr)
- {
- Assert(proxy->GetFunctionInfo()->HasComputedName());
- }
- virtual Var GetComputedNameVar() const override { return this->computedNameVar; }
- virtual void SetComputedNameVar(Var computedNameVar) override;
- virtual VTableValue DummyVirtualFunctionToHinderLinkerICF() const;
- };
- template <class BaseClass>
- class FunctionWithHomeObj : public BaseClass
- {
- private:
- Field(Var) homeObj;
- protected:
- DEFINE_VTABLE_CTOR(FunctionWithHomeObj<BaseClass>, BaseClass);
- DEFINE_MARSHAL_OBJECT_TO_SCRIPT_CONTEXT(FunctionWithHomeObj<BaseClass>);
- public:
- FunctionWithHomeObj(FunctionProxy* proxy, ScriptFunctionType* deferredPrototypeType)
- : BaseClass(proxy, deferredPrototypeType), homeObj(nullptr)
- {
- Assert(proxy->GetFunctionInfo()->HasHomeObj());
- }
- virtual Var GetHomeObj() const override { return homeObj; }
- virtual void SetHomeObj(Var homeObj) override { this->homeObj = homeObj; }
- static uint32 GetOffsetOfHomeObj() { return offsetof(FunctionWithHomeObj<BaseClass>, homeObj); }
- virtual VTableValue DummyVirtualFunctionToHinderLinkerICF() const;
- };
- class ScriptFunction : public ScriptFunctionBase
- {
- private:
- Field(FrameDisplay*) environment; // Optional environment, for closures
- Field(ActivationObjectEx *) cachedScopeObj;
- Field(bool) hasInlineCaches;
- static JavascriptString* GetComputedName(Var computedNameVar, ScriptContext * scriptContext);
- static bool GetSymbolName(Var computedNameVar, const char16** symbolName, charcount_t *length);
- protected:
- DEFINE_VTABLE_CTOR(ScriptFunction, ScriptFunctionBase);
- DEFINE_MARSHAL_OBJECT_TO_SCRIPT_CONTEXT(ScriptFunction);
- public:
- ScriptFunction(FunctionProxy * proxy, ScriptFunctionType* deferredPrototypeType);
- inline static BOOL Test(JavascriptFunction *func) { return func->IsScriptFunction(); }
- static ScriptFunction * OP_NewScFunc(FrameDisplay *environment, FunctionInfoPtrPtr infoRef);
- static ScriptFunction * OP_NewScFuncHomeObj(FrameDisplay *environment, FunctionInfoPtrPtr infoRef, Var homeObj);
- static ScriptFunction * OP_NewClassConstructor(FrameDisplay *environment, FunctionInfoPtrPtr infoRef, Var homeObject, RecyclableObject * constructorParent);
- static void CopyEntryPointInfoToThreadContextIfNecessary(ProxyEntryPointInfo* oldEntryPointInfo, ProxyEntryPointInfo* newEntryPointInfo);
- ProxyEntryPointInfo* GetEntryPointInfo() const;
- FunctionEntryPointInfo* GetFunctionEntryPointInfo() const
- {
- Assert(this->GetFunctionProxy()->IsDeferred() == FALSE);
- ProxyEntryPointInfo* result = this->GetEntryPointInfo();
- Assert(result->IsFunctionEntryPointInfo());
- return (FunctionEntryPointInfo*)result;
- }
- FunctionProxy * GetFunctionProxy() const;
- ScriptFunctionType * GetScriptFunctionType() const;
- FrameDisplay* GetEnvironment() const { return environment; }
- void SetEnvironment(FrameDisplay * environment);
- ActivationObjectEx *GetCachedScope() const { return cachedScopeObj; }
- void SetCachedScope(ActivationObjectEx *obj) { cachedScopeObj = obj; }
- void InvalidateCachedScopeChain();
- static uint32 GetOffsetOfEnvironment() { return offsetof(ScriptFunction, environment); }
- static uint32 GetOffsetOfCachedScopeObj() { return offsetof(ScriptFunction, cachedScopeObj); };
- static uint32 GetOffsetOfHasInlineCaches() { return offsetof(ScriptFunction, hasInlineCaches); };
- void ChangeEntryPoint(ProxyEntryPointInfo* entryPointInfo, JavascriptMethod entryPoint);
- JavascriptMethod UpdateThunkEntryPoint(FunctionEntryPointInfo* entryPointInfo, JavascriptMethod entryPoint);
- bool IsNewEntryPointAvailable();
- JavascriptMethod UpdateUndeferredBody(FunctionBody* newFunctionInfo);
- virtual ScriptFunctionType * DuplicateType() override;
- virtual void PrepareForConversionToNonPathType() override;
- virtual void ReplaceTypeWithPredecessorType(DynamicType * previousType) override;
- virtual Var GetSourceString() const;
- virtual JavascriptString * EnsureSourceString();
- bool GetHasInlineCaches() { return hasInlineCaches; }
- void SetHasInlineCaches(bool has) { hasInlineCaches = has; }
- bool HasSuperReference();
- virtual Var GetHomeObj() const override { return nullptr; }
- virtual void SetHomeObj(Var homeObj) override { AssertMsg(false, "Should have created FunctionWithHomeObj variant"); }
- virtual Var GetComputedNameVar() const override { return nullptr; }
- virtual void SetComputedNameVar(Var computedNameVar) override { AssertMsg(false, "Should have created the FunctionWithComputedName variant"); }
- virtual JavascriptString* GetDisplayNameImpl() const override;
- virtual bool IsAnonymousFunction() const override;
- virtual bool IsAsmJsFunction() const { return false; }
- virtual bool IsWasmFunction() const { return false; }
- virtual JavascriptFunction* GetRealFunctionObject() { return this; }
- bool HasFunctionBody();
- #if ENABLE_TTD
- public:
- virtual void MarkVisitKindSpecificPtrs(TTD::SnapshotExtractor* extractor) override;
- virtual void ProcessCorePaths() override;
- virtual TTD::NSSnapObjects::SnapObjectType GetSnapTag_TTD() const override;
- virtual void ExtractSnapObjectDataInto(TTD::NSSnapObjects::SnapObject* objData, TTD::SlabAllocator& alloc) override;
- virtual void ExtractSnapObjectDataIntoSnapScriptFunctionInfo(/*TTD::NSSnapObjects::SnapScriptFunctionInfo* */ void* ssfi, TTD::SlabAllocator& alloc);
- #endif
- public:
- virtual VTableValue DummyVirtualFunctionToHinderLinkerICF()
- {
- return VTableValue::VtableScriptFunction;
- }
- };
- template <> inline bool VarIsImpl<ScriptFunction>(RecyclableObject* obj)
- {
- return VarIs<JavascriptFunction>(obj) && UnsafeVarTo<JavascriptFunction>(obj)->IsScriptFunction();
- }
- typedef FunctionWithComputedName<ScriptFunction> ScriptFunctionWithComputedName;
- typedef FunctionWithHomeObj<ScriptFunction> ScriptFunctionWithHomeObj;
- class AsmJsScriptFunction : public ScriptFunction
- {
- public:
- AsmJsScriptFunction(FunctionProxy * proxy, ScriptFunctionType* deferredPrototypeType);
- static AsmJsScriptFunction * OP_NewAsmJsFunc(FrameDisplay *environment, FunctionInfoPtrPtr infoRef);
- virtual bool IsAsmJsFunction() const override { return true; }
- void SetModuleEnvironment(Field(Var)* mem) { m_moduleEnvironment = mem; }
- Field(Var)* GetModuleEnvironment() const { return m_moduleEnvironment; }
- static uint32 GetOffsetOfModuleMemory() { return offsetof(AsmJsScriptFunction, m_moduleEnvironment); }
- class JavascriptArrayBuffer* GetAsmJsArrayBuffer() const;
- protected:
- DEFINE_VTABLE_CTOR(AsmJsScriptFunction, ScriptFunction);
- DEFINE_MARSHAL_OBJECT_TO_SCRIPT_CONTEXT(AsmJsScriptFunction);
- private:
- Field(Field(Var)*) m_moduleEnvironment;
- };
- template <> inline bool VarIsImpl<AsmJsScriptFunction>(RecyclableObject* obj)
- {
- return VarIs<ScriptFunction>(obj) && UnsafeVarTo<ScriptFunction>(obj)->IsAsmJsFunction();
- }
- typedef FunctionWithComputedName<AsmJsScriptFunction> AsmJsScriptFunctionWithComputedName;
- #ifdef ENABLE_WASM
- class WasmScriptFunction : public AsmJsScriptFunction
- {
- public:
- WasmScriptFunction(FunctionProxy * proxy, ScriptFunctionType* deferredPrototypeType);
- void SetSignature(Wasm::WasmSignature * sig) { m_signature = sig; }
- Wasm::WasmSignature * GetSignature() const { return m_signature; }
- static uint32 GetOffsetOfSignature() { return offsetof(WasmScriptFunction, m_signature); }
- WebAssemblyMemory* GetWebAssemblyMemory() const;
- virtual bool IsWasmFunction() const override { return true; }
- protected:
- DEFINE_VTABLE_CTOR(WasmScriptFunction, AsmJsScriptFunction);
- DEFINE_MARSHAL_OBJECT_TO_SCRIPT_CONTEXT(WasmScriptFunction);
- private:
- Field(Wasm::WasmSignature *) m_signature;
- };
- template <> inline bool VarIsImpl<WasmScriptFunction>(RecyclableObject* obj)
- {
- return VarIs<ScriptFunction>(obj) && UnsafeVarTo<ScriptFunction>(obj)->IsWasmFunction();
- }
- #else
- class WasmScriptFunction : public AsmJsScriptFunction
- {
- };
- template <> inline bool VarIsImpl<WasmScriptFunction>(RecyclableObject* obj) { return false; }
- #endif
- class ScriptFunctionWithInlineCache : public ScriptFunction
- {
- private:
- Field(void**) m_inlineCaches;
- #if DBG
- #define InlineCacheTypeNone 0x00
- #define InlineCacheTypeInlineCache 0x01
- #define InlineCacheTypeIsInst 0x02
- Field(byte *) m_inlineCacheTypes;
- #endif
- Field(uint) inlineCacheCount;
- Field(uint) rootObjectLoadInlineCacheStart;
- Field(uint) rootObjectLoadMethodInlineCacheStart;
- Field(uint) rootObjectStoreInlineCacheStart;
- Field(uint) isInstInlineCacheCount;
- protected:
- ScriptFunctionWithInlineCache(DynamicType * type);
- DEFINE_VTABLE_CTOR(ScriptFunctionWithInlineCache, ScriptFunction);
- DEFINE_MARSHAL_OBJECT_TO_SCRIPT_CONTEXT(ScriptFunctionWithInlineCache);
- public:
- ScriptFunctionWithInlineCache(FunctionProxy * proxy, ScriptFunctionType* deferredPrototypeType);
- void CreateInlineCache();
- void AllocateInlineCache();
- void ClearInlineCacheOnFunctionObject();
- InlineCache * GetInlineCache(uint index);
- uint GetInlineCacheCount() { return inlineCacheCount; }
- Field(void**) GetInlineCaches() const { return m_inlineCaches; }
- static uint32 GetOffsetOfInlineCaches() { return offsetof(ScriptFunctionWithInlineCache, m_inlineCaches); };
- template<bool isShutdown>
- void FreeOwnInlineCaches();
- virtual void Finalize(bool isShutdown) override;
- };
- template <> inline bool VarIsImpl<ScriptFunctionWithInlineCache>(RecyclableObject* obj)
- {
- return VarIs<ScriptFunction>(obj) && UnsafeVarTo<ScriptFunction>(obj)->GetHasInlineCaches();
- }
- typedef FunctionWithComputedName<ScriptFunctionWithInlineCache> ScriptFunctionWithInlineCacheAndComputedName;
- } // namespace Js
|