/src/mozilla-central/js/xpconnect/loader/mozJSComponentLoader.h
Line | Count | Source (jump to first uncovered line) |
1 | | /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ |
2 | | /* vim: set ts=8 sts=4 et sw=4 tw=99: */ |
3 | | /* This Source Code Form is subject to the terms of the Mozilla Public |
4 | | * License, v. 2.0. If a copy of the MPL was not distributed with this |
5 | | * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ |
6 | | |
7 | | #ifndef mozJSComponentLoader_h |
8 | | #define mozJSComponentLoader_h |
9 | | |
10 | | #include "mozilla/dom/ScriptSettings.h" |
11 | | #include "mozilla/MemoryReporting.h" |
12 | | #include "mozilla/ModuleLoader.h" |
13 | | #include "nsAutoPtr.h" |
14 | | #include "nsISupports.h" |
15 | | #include "nsIObserver.h" |
16 | | #include "nsIURI.h" |
17 | | #include "xpcIJSModuleLoader.h" |
18 | | #include "nsClassHashtable.h" |
19 | | #include "nsDataHashtable.h" |
20 | | #include "jsapi.h" |
21 | | |
22 | | #include "xpcIJSGetFactory.h" |
23 | | #include "xpcpublic.h" |
24 | | |
25 | | class nsIFile; |
26 | | class ComponentLoaderInfo; |
27 | | |
28 | | namespace mozilla { |
29 | | class ScriptPreloader; |
30 | | } // namespace mozilla |
31 | | |
32 | | |
33 | | /* 6bd13476-1dd2-11b2-bbef-f0ccb5fa64b6 (thanks, mozbot) */ |
34 | | |
35 | | #define MOZJSCOMPONENTLOADER_CID \ |
36 | | {0x6bd13476, 0x1dd2, 0x11b2, \ |
37 | | { 0xbb, 0xef, 0xf0, 0xcc, 0xb5, 0xfa, 0x64, 0xb6 }} |
38 | | #define MOZJSCOMPONENTLOADER_CONTRACTID "@mozilla.org/moz/jsloader;1" |
39 | | |
40 | | #if defined(NIGHTLY_BUILD) || defined(MOZ_DEV_EDITION) || defined(DEBUG) |
41 | | #define STARTUP_RECORDER_ENABLED |
42 | | #endif |
43 | | |
44 | | class mozJSComponentLoader final : public mozilla::ModuleLoader, |
45 | | public xpcIJSModuleLoader, |
46 | | public nsIObserver |
47 | | { |
48 | | public: |
49 | | NS_DECL_ISUPPORTS |
50 | | NS_DECL_XPCIJSMODULELOADER |
51 | | NS_DECL_NSIOBSERVER |
52 | | |
53 | | mozJSComponentLoader(); |
54 | | |
55 | | // ModuleLoader |
56 | | const mozilla::Module* LoadModule(mozilla::FileLocation& aFile) override; |
57 | | |
58 | | void FindTargetObject(JSContext* aCx, |
59 | | JS::MutableHandleObject aTargetObject); |
60 | | |
61 | | static already_AddRefed<mozJSComponentLoader> GetOrCreate(); |
62 | | |
63 | 8 | static mozJSComponentLoader* Get() { return sSelf; } |
64 | | |
65 | | nsresult ImportInto(const nsACString& aResourceURI, JS::HandleValue aTargetObj, |
66 | | JSContext* aCx, uint8_t aArgc, JS::MutableHandleValue aRetval); |
67 | | |
68 | | nsresult Import(JSContext* aCx, const nsACString& aResourceURI, |
69 | | JS::MutableHandleObject aModuleGlobal, |
70 | | JS::MutableHandleObject aModuleExports, |
71 | | bool aIgnoreExports = false); |
72 | | |
73 | | nsresult Unload(const nsACString& aResourceURI); |
74 | | nsresult IsModuleLoaded(const nsACString& aResourceURI, bool* aRetval); |
75 | 8 | bool IsLoaderGlobal(JSObject* aObj) { |
76 | 8 | return mLoaderGlobal == aObj; |
77 | 8 | } |
78 | | |
79 | | size_t SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf); |
80 | | |
81 | | /** |
82 | | * Temporary diagnostic function for startup crashes in bug 1403348: |
83 | | * |
84 | | * Annotate the crash report with the contents of the async shutdown |
85 | | * module/component scripts. |
86 | | */ |
87 | | nsresult AnnotateCrashReport(); |
88 | | |
89 | | protected: |
90 | | virtual ~mozJSComponentLoader(); |
91 | | |
92 | | friend class XPCJSRuntime; |
93 | | |
94 | | JSObject* CompilationScope(JSContext* aCx) |
95 | 0 | { |
96 | 0 | if (mLoaderGlobal) { |
97 | 0 | return mLoaderGlobal; |
98 | 0 | } |
99 | 0 | return GetSharedGlobal(aCx); |
100 | 0 | } |
101 | | |
102 | | private: |
103 | | static mozJSComponentLoader* sSelf; |
104 | | |
105 | | nsresult ReallyInit(); |
106 | | void UnloadModules(); |
107 | | |
108 | | void CreateLoaderGlobal(JSContext* aCx, |
109 | | const nsACString& aLocation, |
110 | | JS::MutableHandleObject aGlobal); |
111 | | |
112 | | bool ReuseGlobal(nsIURI* aComponent); |
113 | | |
114 | | JSObject* GetSharedGlobal(JSContext* aCx); |
115 | | |
116 | | JSObject* PrepareObjectForLocation(JSContext* aCx, |
117 | | nsIFile* aComponentFile, |
118 | | nsIURI* aComponent, |
119 | | bool* aReuseGlobal, |
120 | | bool* aRealFile); |
121 | | |
122 | | nsresult ObjectForLocation(ComponentLoaderInfo& aInfo, |
123 | | nsIFile* aComponentFile, |
124 | | JS::MutableHandleObject aObject, |
125 | | JS::MutableHandleScript aTableScript, |
126 | | char** location, |
127 | | bool aCatchException, |
128 | | JS::MutableHandleValue aException); |
129 | | |
130 | | nsresult ImportInto(const nsACString& aLocation, |
131 | | JS::HandleObject targetObj, |
132 | | JSContext* callercx, |
133 | | JS::MutableHandleObject vp); |
134 | | |
135 | | nsCOMPtr<nsIComponentManager> mCompMgr; |
136 | | |
137 | | class ModuleEntry : public mozilla::Module |
138 | | { |
139 | | public: |
140 | | explicit ModuleEntry(JS::RootingContext* aRootingCx) |
141 | | : mozilla::Module(), obj(aRootingCx), exports(aRootingCx), |
142 | | thisObjectKey(aRootingCx) |
143 | 5 | { |
144 | 5 | mVersion = mozilla::Module::kVersion; |
145 | 5 | mCIDs = nullptr; |
146 | 5 | mContractIDs = nullptr; |
147 | 5 | mCategoryEntries = nullptr; |
148 | 5 | getFactoryProc = GetFactory; |
149 | 5 | loadProc = nullptr; |
150 | 5 | unloadProc = nullptr; |
151 | 5 | |
152 | 5 | location = nullptr; |
153 | 5 | } |
154 | | |
155 | 0 | ~ModuleEntry() { |
156 | 0 | Clear(); |
157 | 0 | } |
158 | | |
159 | 0 | void Clear() { |
160 | 0 | getfactoryobj = nullptr; |
161 | 0 |
|
162 | 0 | if (obj) { |
163 | 0 | mozilla::AutoJSContext cx; |
164 | 0 | JSAutoRealm ar(cx, obj); |
165 | 0 |
|
166 | 0 | if (JS_HasExtensibleLexicalEnvironment(obj)) { |
167 | 0 | JS_SetAllNonReservedSlotsToUndefined(cx, JS_ExtensibleLexicalEnvironment(obj)); |
168 | 0 | } |
169 | 0 | JS_SetAllNonReservedSlotsToUndefined(cx, obj); |
170 | 0 | obj = nullptr; |
171 | 0 | thisObjectKey = nullptr; |
172 | 0 | } |
173 | 0 |
|
174 | 0 | if (location) { |
175 | 0 | free(location); |
176 | 0 | } |
177 | 0 |
|
178 | 0 | obj = nullptr; |
179 | 0 | thisObjectKey = nullptr; |
180 | 0 | location = nullptr; |
181 | 0 | #ifdef STARTUP_RECORDER_ENABLED |
182 | 0 | importStack.Truncate(); |
183 | 0 | #endif |
184 | 0 | } |
185 | | |
186 | | size_t SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const; |
187 | | |
188 | | static already_AddRefed<nsIFactory> GetFactory(const mozilla::Module& module, |
189 | | const mozilla::Module::CIDEntry& entry); |
190 | | |
191 | | nsCOMPtr<xpcIJSGetFactory> getfactoryobj; |
192 | | JS::PersistentRootedObject obj; |
193 | | JS::PersistentRootedObject exports; |
194 | | JS::PersistentRootedScript thisObjectKey; |
195 | | char* location; |
196 | | nsCString resolvedURL; |
197 | | #ifdef STARTUP_RECORDER_ENABLED |
198 | | nsCString importStack; |
199 | | #endif |
200 | | }; |
201 | | |
202 | | nsresult ExtractExports(JSContext* aCx, ComponentLoaderInfo& aInfo, |
203 | | ModuleEntry* aMod, |
204 | | JS::MutableHandleObject aExports); |
205 | | |
206 | | static size_t DataEntrySizeOfExcludingThis(const nsACString& aKey, ModuleEntry* const& aData, |
207 | | mozilla::MallocSizeOf aMallocSizeOf, void* arg); |
208 | | static size_t ClassEntrySizeOfExcludingThis(const nsACString& aKey, |
209 | | const nsAutoPtr<ModuleEntry>& aData, |
210 | | mozilla::MallocSizeOf aMallocSizeOf, void* arg); |
211 | | |
212 | | // Modules are intentionally leaked, but still cleared. |
213 | | nsDataHashtable<nsCStringHashKey, ModuleEntry*> mModules; |
214 | | |
215 | | nsClassHashtable<nsCStringHashKey, ModuleEntry> mImports; |
216 | | nsDataHashtable<nsCStringHashKey, ModuleEntry*> mInProgressImports; |
217 | | |
218 | | // A map of on-disk file locations which are loaded as modules to the |
219 | | // pre-resolved URIs they were loaded from. Used to prevent the same file |
220 | | // from being loaded separately, from multiple URLs. |
221 | | nsClassHashtable<nsCStringHashKey, nsCString> mLocations; |
222 | | |
223 | | bool mInitialized; |
224 | | bool mShareLoaderGlobal; |
225 | | JS::PersistentRooted<JSObject*> mLoaderGlobal; |
226 | | }; |
227 | | |
228 | | #endif |