1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/dom/base/nsJSEnvironment.h Wed Dec 31 06:09:35 2014 +0100 1.3 @@ -0,0 +1,254 @@ 1.4 +/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ 1.5 +/* This Source Code Form is subject to the terms of the Mozilla Public 1.6 + * License, v. 2.0. If a copy of the MPL was not distributed with this 1.7 + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 1.8 +#ifndef nsJSEnvironment_h 1.9 +#define nsJSEnvironment_h 1.10 + 1.11 +#include "nsIScriptContext.h" 1.12 +#include "nsIScriptGlobalObject.h" 1.13 +#include "nsCOMPtr.h" 1.14 +#include "nsIObserver.h" 1.15 +#include "prtime.h" 1.16 +#include "nsCycleCollectionParticipant.h" 1.17 +#include "nsIXPConnect.h" 1.18 +#include "nsIArray.h" 1.19 +#include "mozilla/Attributes.h" 1.20 +#include "nsThreadUtils.h" 1.21 + 1.22 +class nsICycleCollectorListener; 1.23 +class nsIXPConnectJSObjectHolder; 1.24 +class nsScriptNameSpaceManager; 1.25 +class nsCycleCollectionNoteRootCallback; 1.26 + 1.27 +namespace JS { 1.28 +class AutoValueVector; 1.29 +} 1.30 + 1.31 +namespace mozilla { 1.32 +template <class> class Maybe; 1.33 +struct CycleCollectorResults; 1.34 +} 1.35 + 1.36 +// The amount of time we wait between a request to GC (due to leaving 1.37 +// a page) and doing the actual GC. 1.38 +#define NS_GC_DELAY 4000 // ms 1.39 + 1.40 +class nsJSContext : public nsIScriptContext 1.41 +{ 1.42 +public: 1.43 + nsJSContext(bool aGCOnDestruction, nsIScriptGlobalObject* aGlobalObject); 1.44 + virtual ~nsJSContext(); 1.45 + 1.46 + NS_DECL_CYCLE_COLLECTING_ISUPPORTS 1.47 + NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS_AMBIGUOUS(nsJSContext, 1.48 + nsIScriptContext) 1.49 + 1.50 + virtual nsIScriptGlobalObject *GetGlobalObject() MOZ_OVERRIDE; 1.51 + inline nsIScriptGlobalObject *GetGlobalObjectRef() { return mGlobalObjectRef; } 1.52 + 1.53 + virtual JSContext* GetNativeContext() MOZ_OVERRIDE; 1.54 + virtual nsresult InitContext() MOZ_OVERRIDE; 1.55 + virtual bool IsContextInitialized() MOZ_OVERRIDE; 1.56 + 1.57 + virtual nsresult SetProperty(JS::Handle<JSObject*> aTarget, const char* aPropName, nsISupports* aVal) MOZ_OVERRIDE; 1.58 + 1.59 + virtual bool GetProcessingScriptTag() MOZ_OVERRIDE; 1.60 + virtual void SetProcessingScriptTag(bool aResult) MOZ_OVERRIDE; 1.61 + 1.62 + virtual nsresult InitClasses(JS::Handle<JSObject*> aGlobalObj) MOZ_OVERRIDE; 1.63 + 1.64 + virtual void WillInitializeContext() MOZ_OVERRIDE; 1.65 + virtual void DidInitializeContext() MOZ_OVERRIDE; 1.66 + 1.67 + virtual void SetWindowProxy(JS::Handle<JSObject*> aWindowProxy) MOZ_OVERRIDE; 1.68 + virtual JSObject* GetWindowProxy() MOZ_OVERRIDE; 1.69 + virtual JSObject* GetWindowProxyPreserveColor() MOZ_OVERRIDE; 1.70 + 1.71 + static void LoadStart(); 1.72 + static void LoadEnd(); 1.73 + 1.74 + enum IsCompartment { 1.75 + CompartmentGC, 1.76 + NonCompartmentGC 1.77 + }; 1.78 + 1.79 + enum IsShrinking { 1.80 + ShrinkingGC, 1.81 + NonShrinkingGC 1.82 + }; 1.83 + 1.84 + enum IsIncremental { 1.85 + IncrementalGC, 1.86 + NonIncrementalGC 1.87 + }; 1.88 + 1.89 + // Setup all the statics etc - safe to call multiple times after Startup(). 1.90 + void EnsureStatics(); 1.91 + 1.92 + static void GarbageCollectNow(JS::gcreason::Reason reason, 1.93 + IsIncremental aIncremental = NonIncrementalGC, 1.94 + IsCompartment aCompartment = NonCompartmentGC, 1.95 + IsShrinking aShrinking = NonShrinkingGC, 1.96 + int64_t aSliceMillis = 0); 1.97 + static void ShrinkGCBuffersNow(); 1.98 + 1.99 + // If aExtraForgetSkippableCalls is -1, forgetSkippable won't be 1.100 + // called even if the previous collection was GC. 1.101 + static void CycleCollectNow(nsICycleCollectorListener *aListener = nullptr, 1.102 + int32_t aExtraForgetSkippableCalls = 0); 1.103 + 1.104 + // Run a cycle collector slice, using a heuristic to decide how long to run it. 1.105 + static void RunCycleCollectorSlice(); 1.106 + 1.107 + static void BeginCycleCollectionCallback(); 1.108 + static void EndCycleCollectionCallback(mozilla::CycleCollectorResults &aResults); 1.109 + 1.110 + static void RunNextCollectorTimer(); 1.111 + 1.112 + static void PokeGC(JS::gcreason::Reason aReason, int aDelay = 0); 1.113 + static void KillGCTimer(); 1.114 + 1.115 + static void PokeShrinkGCBuffers(); 1.116 + static void KillShrinkGCBuffersTimer(); 1.117 + 1.118 + static void MaybePokeCC(); 1.119 + static void KillCCTimer(); 1.120 + static void KillICCTimer(); 1.121 + static void KillFullGCTimer(); 1.122 + static void KillInterSliceGCTimer(); 1.123 + 1.124 + // Calling LikelyShortLivingObjectCreated() makes a GC more likely. 1.125 + static void LikelyShortLivingObjectCreated(); 1.126 + 1.127 + virtual void GC(JS::gcreason::Reason aReason) MOZ_OVERRIDE; 1.128 + 1.129 + static uint32_t CleanupsSinceLastGC(); 1.130 + 1.131 + nsIScriptGlobalObject* GetCachedGlobalObject() 1.132 + { 1.133 + // Verify that we have a global so that this 1.134 + // does always return a null when GetGlobalObject() is null. 1.135 + JSObject* global = GetWindowProxy(); 1.136 + return global ? mGlobalObjectRef.get() : nullptr; 1.137 + } 1.138 +protected: 1.139 + nsresult InitializeExternalClasses(); 1.140 + 1.141 + // Helper to convert xpcom datatypes to jsvals. 1.142 + nsresult ConvertSupportsTojsvals(nsISupports *aArgs, 1.143 + JS::Handle<JSObject*> aScope, 1.144 + JS::AutoValueVector &aArgsOut); 1.145 + 1.146 + nsresult AddSupportsPrimitiveTojsvals(nsISupports *aArg, JS::Value *aArgv); 1.147 + 1.148 + // Report the pending exception on our mContext, if any. This 1.149 + // function will set aside the frame chain on mContext before 1.150 + // reporting. 1.151 + void ReportPendingException(); 1.152 + 1.153 +private: 1.154 + void DestroyJSContext(); 1.155 + 1.156 + nsrefcnt GetCCRefcnt(); 1.157 + 1.158 + JSContext *mContext; 1.159 + JS::Heap<JSObject*> mWindowProxy; 1.160 + 1.161 + bool mIsInitialized; 1.162 + bool mGCOnDestruction; 1.163 + bool mProcessingScriptTag; 1.164 + 1.165 + PRTime mModalStateTime; 1.166 + uint32_t mModalStateDepth; 1.167 + 1.168 + // mGlobalObjectRef ensures that the outer window stays alive as long as the 1.169 + // context does. It is eventually collected by the cycle collector. 1.170 + nsCOMPtr<nsIScriptGlobalObject> mGlobalObjectRef; 1.171 + 1.172 + static void JSOptionChangedCallback(const char *pref, void *data); 1.173 + 1.174 + static bool DOMOperationCallback(JSContext *cx); 1.175 +}; 1.176 + 1.177 +class nsIJSRuntimeService; 1.178 +class nsIPrincipal; 1.179 +class nsPIDOMWindow; 1.180 + 1.181 +namespace mozilla { 1.182 +namespace dom { 1.183 + 1.184 +void StartupJSEnvironment(); 1.185 +void ShutdownJSEnvironment(); 1.186 + 1.187 +// Get the NameSpaceManager, creating if necessary 1.188 +nsScriptNameSpaceManager* GetNameSpaceManager(); 1.189 + 1.190 +// Runnable that's used to do async error reporting 1.191 +class AsyncErrorReporter : public nsRunnable 1.192 +{ 1.193 +public: 1.194 + // aWindow may be null if this error report is not associated with a window 1.195 + AsyncErrorReporter(JSRuntime* aRuntime, 1.196 + JSErrorReport* aErrorReport, 1.197 + const char* aFallbackMessage, 1.198 + bool aIsChromeError, // To determine category 1.199 + nsPIDOMWindow* aWindow); 1.200 + 1.201 + NS_IMETHOD Run() 1.202 + { 1.203 + ReportError(); 1.204 + return NS_OK; 1.205 + } 1.206 + 1.207 +protected: 1.208 + // Do the actual error reporting 1.209 + void ReportError(); 1.210 + 1.211 + nsString mErrorMsg; 1.212 + nsString mFileName; 1.213 + nsString mSourceLine; 1.214 + nsCString mCategory; 1.215 + uint32_t mLineNumber; 1.216 + uint32_t mColumn; 1.217 + uint32_t mFlags; 1.218 + uint64_t mInnerWindowID; 1.219 +}; 1.220 + 1.221 +} // namespace dom 1.222 +} // namespace mozilla 1.223 + 1.224 +// An interface for fast and native conversion to/from nsIArray. If an object 1.225 +// supports this interface, JS can reach directly in for the argv, and avoid 1.226 +// nsISupports conversion. If this interface is not supported, the object will 1.227 +// be queried for nsIArray, and everything converted via xpcom objects. 1.228 +#define NS_IJSARGARRAY_IID \ 1.229 +{ 0xb6acdac8, 0xf5c6, 0x432c, \ 1.230 + { 0xa8, 0x6e, 0x33, 0xee, 0xb1, 0xb0, 0xcd, 0xdc } } 1.231 + 1.232 +class nsIJSArgArray : public nsIArray 1.233 +{ 1.234 +public: 1.235 + NS_DECLARE_STATIC_IID_ACCESSOR(NS_IJSARGARRAY_IID) 1.236 + // Bug 312003 describes why this must be "void **", but after calling argv 1.237 + // may be cast to JS::Value* and the args found at: 1.238 + // ((JS::Value*)argv)[0], ..., ((JS::Value*)argv)[argc - 1] 1.239 + virtual nsresult GetArgs(uint32_t *argc, void **argv) = 0; 1.240 +}; 1.241 + 1.242 +NS_DEFINE_STATIC_IID_ACCESSOR(nsIJSArgArray, NS_IJSARGARRAY_IID) 1.243 + 1.244 +/* prototypes */ 1.245 +void NS_ScriptErrorReporter(JSContext *cx, const char *message, JSErrorReport *report); 1.246 + 1.247 +JSObject* NS_DOMReadStructuredClone(JSContext* cx, 1.248 + JSStructuredCloneReader* reader, uint32_t tag, 1.249 + uint32_t data, void* closure); 1.250 + 1.251 +bool NS_DOMWriteStructuredClone(JSContext* cx, 1.252 + JSStructuredCloneWriter* writer, 1.253 + JS::Handle<JSObject*> obj, void *closure); 1.254 + 1.255 +void NS_DOMStructuredCloneError(JSContext* cx, uint32_t errorid); 1.256 + 1.257 +#endif /* nsJSEnvironment_h */