1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2  * vim: set ts=8 sts=2 et sw=2 tw=80:
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 /*
8  * Functionality provided for the JSM component loader in Gecko, that requires
9  * its own unique manner of global environment and currently requires assistance
10  * from SpiderMonkey to do so.
11  *
12  * Embedders who aren't Gecko can ignore this header.
13  */
14 
15 #ifndef js_friend_JSMEnvironment_h
16 #define js_friend_JSMEnvironment_h
17 
18 #include "jstypes.h"  // JS_PUBLIC_API
19 
20 #include "js/GCVector.h"  // JS::StackGCVector
21 #include "js/TypeDecls.h"
22 
23 // A 'JSMEnvironment' refers to an environment chain constructed for JSM loading
24 // in a shared global. Internally it is a NonSyntacticVariablesObject with a
25 // corresponding extensible LexicalEnvironmentObject that is accessible by
26 // JS_ExtensibleLexicalEnvironment. The |this| value of that lexical environment
27 // is the NSVO itself.
28 //
29 // Normal global environment (ES6):     JSM "global" environment:
30 //
31 //                                      * - extensible lexical environment
32 //                                      |   (code runs in this environment;
33 //                                      |    `let/const` bindings go here)
34 //                                      |
35 //                                      * - JSMEnvironment (=== `this`)
36 //                                      |   (`var` bindings go here)
37 //                                      |
38 // * - extensible lexical environment   * - extensible lexical environment
39 // |   (code runs in this environment;  |   (empty)
40 // |    `let/const` bindings go here)   |
41 // |                                    |
42 // * - actual global (=== `this`)       * - shared JSM global
43 //     (var bindings go here; and           (Object, Math, etc. live here)
44 //      Object, Math, etc. live here)
45 
46 namespace JS {
47 
48 /**
49  * Allocate a new environment in the current compartment that is compatible with
50  * JSM shared loading.
51  */
52 extern JS_PUBLIC_API JSObject* NewJSMEnvironment(JSContext* cx);
53 
54 /**
55  * Execute the given script (copied into the current compartment if necessary)
56  * in the given JSMEnvironment.  The script must have been compiled for
57  * hasNonSyntacticScope.  The |jsmEnv| must have been previously allocated by
58  * |NewJSMEnvironment|.
59  *
60  * NOTE: The associated extensible lexical environment is reused.
61  */
62 extern JS_PUBLIC_API bool ExecuteInJSMEnvironment(JSContext* cx,
63                                                   Handle<JSScript*> script,
64                                                   Handle<JSObject*> jsmEnv);
65 
66 // Additionally, target objects may be specified as required by the Gecko
67 // subscript loader. These are wrapped in non-syntactic WithEnvironments and
68 // temporarily placed on the environment chain.
69 //
70 // See also: JS::CloneAndExecuteScript(...)
71 extern JS_PUBLIC_API bool ExecuteInJSMEnvironment(
72     JSContext* cx, Handle<JSScript*> script, Handle<JSObject*> jsmEnv,
73     Handle<StackGCVector<JSObject*>> targetObj);
74 
75 // Used by native methods to determine the JSMEnvironment of caller if possible
76 // by looking at stack frames. Returns nullptr if top frame isn't a scripted
77 // caller in a JSM.
78 //
79 // NOTE: This may find NonSyntacticVariablesObject generated by other embedding
80 // such as a Gecko FrameScript. Caller can check the compartment if needed.
81 extern JS_PUBLIC_API JSObject* GetJSMEnvironmentOfScriptedCaller(JSContext* cx);
82 
83 /**
84  * Determine if obj is a JSMEnvironment
85  *
86  * NOTE: This may return true for an NonSyntacticVariablesObject generated by
87  * other embedding such as a Gecko FrameScript. Caller can check compartment.
88  */
89 extern JS_PUBLIC_API bool IsJSMEnvironment(JSObject* obj);
90 
91 }  // namespace JS
92 
93 #endif  // js_friend_JSMEnvironment_h
94