Home | History | Annotate | Download | only in src
      1 // Copyright 2012 the V8 project authors. All rights reserved.
      2 // Redistribution and use in source and binary forms, with or without
      3 // modification, are permitted provided that the following conditions are
      4 // met:
      5 //
      6 //     * Redistributions of source code must retain the above copyright
      7 //       notice, this list of conditions and the following disclaimer.
      8 //     * Redistributions in binary form must reproduce the above
      9 //       copyright notice, this list of conditions and the following
     10 //       disclaimer in the documentation and/or other materials provided
     11 //       with the distribution.
     12 //     * Neither the name of Google Inc. nor the names of its
     13 //       contributors may be used to endorse or promote products derived
     14 //       from this software without specific prior written permission.
     15 //
     16 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
     17 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
     18 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
     19 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
     20 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
     21 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
     22 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     23 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     24 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     25 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     27 
     28 #ifndef V8_CONTEXTS_H_
     29 #define V8_CONTEXTS_H_
     30 
     31 #include "heap.h"
     32 #include "objects.h"
     33 
     34 namespace v8 {
     35 namespace internal {
     36 
     37 
     38 enum ContextLookupFlags {
     39   FOLLOW_CONTEXT_CHAIN = 1,
     40   FOLLOW_PROTOTYPE_CHAIN = 2,
     41 
     42   DONT_FOLLOW_CHAINS = 0,
     43   FOLLOW_CHAINS = FOLLOW_CONTEXT_CHAIN | FOLLOW_PROTOTYPE_CHAIN
     44 };
     45 
     46 
     47 // ES5 10.2 defines lexical environments with mutable and immutable bindings.
     48 // Immutable bindings have two states, initialized and uninitialized, and
     49 // their state is changed by the InitializeImmutableBinding method. The
     50 // BindingFlags enum represents information if a binding has definitely been
     51 // initialized. A mutable binding does not need to be checked and thus has
     52 // the BindingFlag MUTABLE_IS_INITIALIZED.
     53 //
     54 // There are two possibilities for immutable bindings
     55 //  * 'const' declared variables. They are initialized when evaluating the
     56 //    corresponding declaration statement. They need to be checked for being
     57 //    initialized and thus get the flag IMMUTABLE_CHECK_INITIALIZED.
     58 //  * The function name of a named function literal. The binding is immediately
     59 //    initialized when entering the function and thus does not need to be
     60 //    checked. it gets the BindingFlag IMMUTABLE_IS_INITIALIZED.
     61 // Accessing an uninitialized binding produces the undefined value.
     62 //
     63 // The harmony proposal for block scoped bindings also introduces the
     64 // uninitialized state for mutable bindings.
     65 //  * A 'let' declared variable. They are initialized when evaluating the
     66 //    corresponding declaration statement. They need to be checked for being
     67 //    initialized and thus get the flag MUTABLE_CHECK_INITIALIZED.
     68 //  * A 'var' declared variable. It is initialized immediately upon creation
     69 //    and thus doesn't need to be checked. It gets the flag
     70 //    MUTABLE_IS_INITIALIZED.
     71 //  * Catch bound variables, function parameters and variables introduced by
     72 //    function declarations are initialized immediately and do not need to be
     73 //    checked. Thus they get the flag MUTABLE_IS_INITIALIZED.
     74 // Immutable bindings in harmony mode get the _HARMONY flag variants. Accessing
     75 // an uninitialized binding produces a reference error.
     76 //
     77 // In V8 uninitialized bindings are set to the hole value upon creation and set
     78 // to a different value upon initialization.
     79 enum BindingFlags {
     80   MUTABLE_IS_INITIALIZED,
     81   MUTABLE_CHECK_INITIALIZED,
     82   IMMUTABLE_IS_INITIALIZED,
     83   IMMUTABLE_CHECK_INITIALIZED,
     84   IMMUTABLE_IS_INITIALIZED_HARMONY,
     85   IMMUTABLE_CHECK_INITIALIZED_HARMONY,
     86   MISSING_BINDING
     87 };
     88 
     89 
     90 // Heap-allocated activation contexts.
     91 //
     92 // Contexts are implemented as FixedArray objects; the Context
     93 // class is a convenience interface casted on a FixedArray object.
     94 //
     95 // Note: Context must have no virtual functions and Context objects
     96 // must always be allocated via Heap::AllocateContext() or
     97 // Factory::NewContext.
     98 
     99 #define NATIVE_CONTEXT_FIELDS(V) \
    100   V(GLOBAL_PROXY_INDEX, JSObject, global_proxy_object) \
    101   V(SECURITY_TOKEN_INDEX, Object, security_token) \
    102   V(BOOLEAN_FUNCTION_INDEX, JSFunction, boolean_function) \
    103   V(NUMBER_FUNCTION_INDEX, JSFunction, number_function) \
    104   V(STRING_FUNCTION_INDEX, JSFunction, string_function) \
    105   V(STRING_FUNCTION_PROTOTYPE_MAP_INDEX, Map, string_function_prototype_map) \
    106   V(SYMBOL_FUNCTION_INDEX, JSFunction, symbol_function) \
    107   V(OBJECT_FUNCTION_INDEX, JSFunction, object_function) \
    108   V(INTERNAL_ARRAY_FUNCTION_INDEX, JSFunction, internal_array_function) \
    109   V(ARRAY_FUNCTION_INDEX, JSFunction, array_function) \
    110   V(JS_ARRAY_MAPS_INDEX, Object, js_array_maps) \
    111   V(DATE_FUNCTION_INDEX, JSFunction, date_function) \
    112   V(JSON_OBJECT_INDEX, JSObject, json_object) \
    113   V(REGEXP_FUNCTION_INDEX, JSFunction, regexp_function) \
    114   V(INITIAL_OBJECT_PROTOTYPE_INDEX, JSObject, initial_object_prototype) \
    115   V(INITIAL_ARRAY_PROTOTYPE_INDEX, JSObject, initial_array_prototype) \
    116   V(CREATE_DATE_FUN_INDEX, JSFunction,  create_date_fun) \
    117   V(TO_NUMBER_FUN_INDEX, JSFunction, to_number_fun) \
    118   V(TO_STRING_FUN_INDEX, JSFunction, to_string_fun) \
    119   V(TO_DETAIL_STRING_FUN_INDEX, JSFunction, to_detail_string_fun) \
    120   V(TO_OBJECT_FUN_INDEX, JSFunction, to_object_fun) \
    121   V(TO_INTEGER_FUN_INDEX, JSFunction, to_integer_fun) \
    122   V(TO_UINT32_FUN_INDEX, JSFunction, to_uint32_fun) \
    123   V(TO_INT32_FUN_INDEX, JSFunction, to_int32_fun) \
    124   V(GLOBAL_EVAL_FUN_INDEX, JSFunction, global_eval_fun) \
    125   V(INSTANTIATE_FUN_INDEX, JSFunction, instantiate_fun) \
    126   V(CONFIGURE_INSTANCE_FUN_INDEX, JSFunction, configure_instance_fun) \
    127   V(ARRAY_BUFFER_FUN_INDEX, JSFunction, array_buffer_fun) \
    128   V(UINT8_ARRAY_FUN_INDEX, JSFunction, uint8_array_fun) \
    129   V(INT8_ARRAY_FUN_INDEX, JSFunction, int8_array_fun) \
    130   V(UINT16_ARRAY_FUN_INDEX, JSFunction, uint16_array_fun) \
    131   V(INT16_ARRAY_FUN_INDEX, JSFunction, int16_array_fun) \
    132   V(UINT32_ARRAY_FUN_INDEX, JSFunction, uint32_array_fun) \
    133   V(INT32_ARRAY_FUN_INDEX, JSFunction, int32_array_fun) \
    134   V(FLOAT_ARRAY_FUN_INDEX, JSFunction, float_array_fun) \
    135   V(DOUBLE_ARRAY_FUN_INDEX, JSFunction, double_array_fun) \
    136   V(UINT8C_ARRAY_FUN_INDEX, JSFunction, uint8c_array_fun) \
    137   V(DATA_VIEW_FUN_INDEX, JSFunction, data_view_fun) \
    138   V(FUNCTION_MAP_INDEX, Map, function_map) \
    139   V(STRICT_MODE_FUNCTION_MAP_INDEX, Map, strict_mode_function_map) \
    140   V(FUNCTION_WITHOUT_PROTOTYPE_MAP_INDEX, Map, function_without_prototype_map) \
    141   V(STRICT_MODE_FUNCTION_WITHOUT_PROTOTYPE_MAP_INDEX, Map, \
    142     strict_mode_function_without_prototype_map) \
    143   V(REGEXP_RESULT_MAP_INDEX, Map, regexp_result_map)\
    144   V(ARGUMENTS_BOILERPLATE_INDEX, JSObject, arguments_boilerplate) \
    145   V(ALIASED_ARGUMENTS_BOILERPLATE_INDEX, JSObject, \
    146     aliased_arguments_boilerplate) \
    147   V(STRICT_MODE_ARGUMENTS_BOILERPLATE_INDEX, JSObject, \
    148     strict_mode_arguments_boilerplate) \
    149   V(MESSAGE_LISTENERS_INDEX, JSObject, message_listeners) \
    150   V(MAKE_MESSAGE_FUN_INDEX, JSFunction, make_message_fun) \
    151   V(GET_STACK_TRACE_LINE_INDEX, JSFunction, get_stack_trace_line_fun) \
    152   V(CONFIGURE_GLOBAL_INDEX, JSFunction, configure_global_fun) \
    153   V(FUNCTION_CACHE_INDEX, JSObject, function_cache) \
    154   V(JSFUNCTION_RESULT_CACHES_INDEX, FixedArray, jsfunction_result_caches) \
    155   V(NORMALIZED_MAP_CACHE_INDEX, NormalizedMapCache, normalized_map_cache) \
    156   V(RUNTIME_CONTEXT_INDEX, Context, runtime_context) \
    157   V(CALL_AS_FUNCTION_DELEGATE_INDEX, JSFunction, call_as_function_delegate) \
    158   V(CALL_AS_CONSTRUCTOR_DELEGATE_INDEX, JSFunction, \
    159     call_as_constructor_delegate) \
    160   V(SCRIPT_FUNCTION_INDEX, JSFunction, script_function) \
    161   V(OPAQUE_REFERENCE_FUNCTION_INDEX, JSFunction, opaque_reference_function) \
    162   V(CONTEXT_EXTENSION_FUNCTION_INDEX, JSFunction, context_extension_function) \
    163   V(OUT_OF_MEMORY_INDEX, Object, out_of_memory) \
    164   V(MAP_CACHE_INDEX, Object, map_cache) \
    165   V(EMBEDDER_DATA_INDEX, FixedArray, embedder_data) \
    166   V(ALLOW_CODE_GEN_FROM_STRINGS_INDEX, Object, allow_code_gen_from_strings) \
    167   V(ERROR_MESSAGE_FOR_CODE_GEN_FROM_STRINGS_INDEX, Object, \
    168     error_message_for_code_gen_from_strings) \
    169   V(RUN_MICROTASKS_INDEX, JSFunction, run_microtasks) \
    170   V(TO_COMPLETE_PROPERTY_DESCRIPTOR_INDEX, JSFunction, \
    171     to_complete_property_descriptor) \
    172   V(DERIVED_HAS_TRAP_INDEX, JSFunction, derived_has_trap) \
    173   V(DERIVED_GET_TRAP_INDEX, JSFunction, derived_get_trap) \
    174   V(DERIVED_SET_TRAP_INDEX, JSFunction, derived_set_trap) \
    175   V(PROXY_ENUMERATE_INDEX, JSFunction, proxy_enumerate) \
    176   V(OBSERVERS_NOTIFY_CHANGE_INDEX, JSFunction, observers_notify_change) \
    177   V(OBSERVERS_ENQUEUE_SPLICE_INDEX, JSFunction, observers_enqueue_splice) \
    178   V(OBSERVERS_BEGIN_SPLICE_INDEX, JSFunction, \
    179     observers_begin_perform_splice) \
    180   V(OBSERVERS_END_SPLICE_INDEX, JSFunction, \
    181     observers_end_perform_splice) \
    182   V(GENERATOR_FUNCTION_MAP_INDEX, Map, generator_function_map) \
    183   V(STRICT_MODE_GENERATOR_FUNCTION_MAP_INDEX, Map, \
    184     strict_mode_generator_function_map) \
    185   V(GENERATOR_OBJECT_PROTOTYPE_MAP_INDEX, Map, \
    186     generator_object_prototype_map) \
    187   V(GENERATOR_RESULT_MAP_INDEX, Map, generator_result_map)
    188 
    189 // JSFunctions are pairs (context, function code), sometimes also called
    190 // closures. A Context object is used to represent function contexts and
    191 // dynamically pushed 'with' contexts (or 'scopes' in ECMA-262 speak).
    192 //
    193 // At runtime, the contexts build a stack in parallel to the execution
    194 // stack, with the top-most context being the current context. All contexts
    195 // have the following slots:
    196 //
    197 // [ closure   ]  This is the current function. It is the same for all
    198 //                contexts inside a function. It provides access to the
    199 //                incoming context (i.e., the outer context, which may
    200 //                or may not become the current function's context), and
    201 //                it provides access to the functions code and thus it's
    202 //                scope information, which in turn contains the names of
    203 //                statically allocated context slots. The names are needed
    204 //                for dynamic lookups in the presence of 'with' or 'eval'.
    205 //
    206 // [ previous  ]  A pointer to the previous context. It is NULL for
    207 //                function contexts, and non-NULL for 'with' contexts.
    208 //                Used to implement the 'with' statement.
    209 //
    210 // [ extension ]  A pointer to an extension JSObject, or NULL. Used to
    211 //                implement 'with' statements and dynamic declarations
    212 //                (through 'eval'). The object in a 'with' statement is
    213 //                stored in the extension slot of a 'with' context.
    214 //                Dynamically declared variables/functions are also added
    215 //                to lazily allocated extension object. Context::Lookup
    216 //                searches the extension object for properties.
    217 //                For global and block contexts, contains the respective
    218 //                ScopeInfo.
    219 //                For module contexts, points back to the respective JSModule.
    220 //
    221 // [ global_object ]  A pointer to the global object. Provided for quick
    222 //                access to the global object from inside the code (since
    223 //                we always have a context pointer).
    224 //
    225 // In addition, function contexts may have statically allocated context slots
    226 // to store local variables/functions that are accessed from inner functions
    227 // (via static context addresses) or through 'eval' (dynamic context lookups).
    228 // Finally, the native context contains additional slots for fast access to
    229 // native properties.
    230 
    231 class Context: public FixedArray {
    232  public:
    233   // Conversions.
    234   static Context* cast(Object* context) {
    235     ASSERT(context->IsContext());
    236     return reinterpret_cast<Context*>(context);
    237   }
    238 
    239   // The default context slot layout; indices are FixedArray slot indices.
    240   enum {
    241     // These slots are in all contexts.
    242     CLOSURE_INDEX,
    243     PREVIOUS_INDEX,
    244     // The extension slot is used for either the global object (in global
    245     // contexts), eval extension object (function contexts), subject of with
    246     // (with contexts), or the variable name (catch contexts), the serialized
    247     // scope info (block contexts), or the module instance (module contexts).
    248     EXTENSION_INDEX,
    249     GLOBAL_OBJECT_INDEX,
    250     MIN_CONTEXT_SLOTS,
    251 
    252     // This slot holds the thrown value in catch contexts.
    253     THROWN_OBJECT_INDEX = MIN_CONTEXT_SLOTS,
    254 
    255     // These slots are only in native contexts.
    256     GLOBAL_PROXY_INDEX = MIN_CONTEXT_SLOTS,
    257     SECURITY_TOKEN_INDEX,
    258     ARGUMENTS_BOILERPLATE_INDEX,
    259     ALIASED_ARGUMENTS_BOILERPLATE_INDEX,
    260     STRICT_MODE_ARGUMENTS_BOILERPLATE_INDEX,
    261     REGEXP_RESULT_MAP_INDEX,
    262     FUNCTION_MAP_INDEX,
    263     STRICT_MODE_FUNCTION_MAP_INDEX,
    264     FUNCTION_WITHOUT_PROTOTYPE_MAP_INDEX,
    265     STRICT_MODE_FUNCTION_WITHOUT_PROTOTYPE_MAP_INDEX,
    266     INITIAL_OBJECT_PROTOTYPE_INDEX,
    267     INITIAL_ARRAY_PROTOTYPE_INDEX,
    268     BOOLEAN_FUNCTION_INDEX,
    269     NUMBER_FUNCTION_INDEX,
    270     STRING_FUNCTION_INDEX,
    271     STRING_FUNCTION_PROTOTYPE_MAP_INDEX,
    272     SYMBOL_FUNCTION_INDEX,
    273     OBJECT_FUNCTION_INDEX,
    274     INTERNAL_ARRAY_FUNCTION_INDEX,
    275     ARRAY_FUNCTION_INDEX,
    276     JS_ARRAY_MAPS_INDEX,
    277     DATE_FUNCTION_INDEX,
    278     JSON_OBJECT_INDEX,
    279     REGEXP_FUNCTION_INDEX,
    280     CREATE_DATE_FUN_INDEX,
    281     TO_NUMBER_FUN_INDEX,
    282     TO_STRING_FUN_INDEX,
    283     TO_DETAIL_STRING_FUN_INDEX,
    284     TO_OBJECT_FUN_INDEX,
    285     TO_INTEGER_FUN_INDEX,
    286     TO_UINT32_FUN_INDEX,
    287     TO_INT32_FUN_INDEX,
    288     TO_BOOLEAN_FUN_INDEX,
    289     GLOBAL_EVAL_FUN_INDEX,
    290     INSTANTIATE_FUN_INDEX,
    291     CONFIGURE_INSTANCE_FUN_INDEX,
    292     ARRAY_BUFFER_FUN_INDEX,
    293     UINT8_ARRAY_FUN_INDEX,
    294     INT8_ARRAY_FUN_INDEX,
    295     UINT16_ARRAY_FUN_INDEX,
    296     INT16_ARRAY_FUN_INDEX,
    297     UINT32_ARRAY_FUN_INDEX,
    298     INT32_ARRAY_FUN_INDEX,
    299     FLOAT_ARRAY_FUN_INDEX,
    300     DOUBLE_ARRAY_FUN_INDEX,
    301     UINT8C_ARRAY_FUN_INDEX,
    302     DATA_VIEW_FUN_INDEX,
    303     MESSAGE_LISTENERS_INDEX,
    304     MAKE_MESSAGE_FUN_INDEX,
    305     GET_STACK_TRACE_LINE_INDEX,
    306     CONFIGURE_GLOBAL_INDEX,
    307     FUNCTION_CACHE_INDEX,
    308     JSFUNCTION_RESULT_CACHES_INDEX,
    309     NORMALIZED_MAP_CACHE_INDEX,
    310     RUNTIME_CONTEXT_INDEX,
    311     CALL_AS_FUNCTION_DELEGATE_INDEX,
    312     CALL_AS_CONSTRUCTOR_DELEGATE_INDEX,
    313     SCRIPT_FUNCTION_INDEX,
    314     OPAQUE_REFERENCE_FUNCTION_INDEX,
    315     CONTEXT_EXTENSION_FUNCTION_INDEX,
    316     OUT_OF_MEMORY_INDEX,
    317     EMBEDDER_DATA_INDEX,
    318     ALLOW_CODE_GEN_FROM_STRINGS_INDEX,
    319     ERROR_MESSAGE_FOR_CODE_GEN_FROM_STRINGS_INDEX,
    320     RUN_MICROTASKS_INDEX,
    321     TO_COMPLETE_PROPERTY_DESCRIPTOR_INDEX,
    322     DERIVED_HAS_TRAP_INDEX,
    323     DERIVED_GET_TRAP_INDEX,
    324     DERIVED_SET_TRAP_INDEX,
    325     PROXY_ENUMERATE_INDEX,
    326     OBSERVERS_NOTIFY_CHANGE_INDEX,
    327     OBSERVERS_ENQUEUE_SPLICE_INDEX,
    328     OBSERVERS_BEGIN_SPLICE_INDEX,
    329     OBSERVERS_END_SPLICE_INDEX,
    330     GENERATOR_FUNCTION_MAP_INDEX,
    331     STRICT_MODE_GENERATOR_FUNCTION_MAP_INDEX,
    332     GENERATOR_OBJECT_PROTOTYPE_MAP_INDEX,
    333     GENERATOR_RESULT_MAP_INDEX,
    334 
    335     // Properties from here are treated as weak references by the full GC.
    336     // Scavenge treats them as strong references.
    337     OPTIMIZED_FUNCTIONS_LIST,  // Weak.
    338     OPTIMIZED_CODE_LIST,       // Weak.
    339     DEOPTIMIZED_CODE_LIST,     // Weak.
    340     MAP_CACHE_INDEX,           // Weak.
    341     NEXT_CONTEXT_LINK,         // Weak.
    342 
    343     // Total number of slots.
    344     NATIVE_CONTEXT_SLOTS,
    345 
    346     FIRST_WEAK_SLOT = OPTIMIZED_FUNCTIONS_LIST
    347   };
    348 
    349   // Direct slot access.
    350   JSFunction* closure() { return JSFunction::cast(get(CLOSURE_INDEX)); }
    351   void set_closure(JSFunction* closure) { set(CLOSURE_INDEX, closure); }
    352 
    353   Context* previous() {
    354     Object* result = unchecked_previous();
    355     ASSERT(IsBootstrappingOrValidParentContext(result, this));
    356     return reinterpret_cast<Context*>(result);
    357   }
    358   void set_previous(Context* context) { set(PREVIOUS_INDEX, context); }
    359 
    360   bool has_extension() { return extension() != NULL; }
    361   Object* extension() { return get(EXTENSION_INDEX); }
    362   void set_extension(Object* object) { set(EXTENSION_INDEX, object); }
    363 
    364   JSModule* module() { return JSModule::cast(get(EXTENSION_INDEX)); }
    365   void set_module(JSModule* module) { set(EXTENSION_INDEX, module); }
    366 
    367   // Get the context where var declarations will be hoisted to, which
    368   // may be the context itself.
    369   Context* declaration_context();
    370 
    371   GlobalObject* global_object() {
    372     Object* result = get(GLOBAL_OBJECT_INDEX);
    373     ASSERT(IsBootstrappingOrGlobalObject(this->GetIsolate(), result));
    374     return reinterpret_cast<GlobalObject*>(result);
    375   }
    376   void set_global_object(GlobalObject* object) {
    377     set(GLOBAL_OBJECT_INDEX, object);
    378   }
    379 
    380   // Returns a JSGlobalProxy object or null.
    381   JSObject* global_proxy();
    382   void set_global_proxy(JSObject* global);
    383 
    384   // The builtins object.
    385   JSBuiltinsObject* builtins();
    386 
    387   // Get the innermost global context by traversing the context chain.
    388   Context* global_context();
    389 
    390   // Compute the native context by traversing the context chain.
    391   Context* native_context();
    392 
    393   // Predicates for context types.  IsNativeContext is also defined on Object
    394   // because we frequently have to know if arbitrary objects are natives
    395   // contexts.
    396   bool IsNativeContext() {
    397     Map* map = this->map();
    398     return map == map->GetHeap()->native_context_map();
    399   }
    400   bool IsFunctionContext() {
    401     Map* map = this->map();
    402     return map == map->GetHeap()->function_context_map();
    403   }
    404   bool IsCatchContext() {
    405     Map* map = this->map();
    406     return map == map->GetHeap()->catch_context_map();
    407   }
    408   bool IsWithContext() {
    409     Map* map = this->map();
    410     return map == map->GetHeap()->with_context_map();
    411   }
    412   bool IsBlockContext() {
    413     Map* map = this->map();
    414     return map == map->GetHeap()->block_context_map();
    415   }
    416   bool IsModuleContext() {
    417     Map* map = this->map();
    418     return map == map->GetHeap()->module_context_map();
    419   }
    420   bool IsGlobalContext() {
    421     Map* map = this->map();
    422     return map == map->GetHeap()->global_context_map();
    423   }
    424 
    425   // Tells whether the native context is marked with out of memory.
    426   inline bool has_out_of_memory();
    427 
    428   // Mark the native context with out of memory.
    429   inline void mark_out_of_memory();
    430 
    431   // A native context holds a list of all functions with optimized code.
    432   void AddOptimizedFunction(JSFunction* function);
    433   void RemoveOptimizedFunction(JSFunction* function);
    434   void SetOptimizedFunctionsListHead(Object* head);
    435   Object* OptimizedFunctionsListHead();
    436 
    437   // The native context also stores a list of all optimized code and a
    438   // list of all deoptimized code, which are needed by the deoptimizer.
    439   void AddOptimizedCode(Code* code);
    440   void SetOptimizedCodeListHead(Object* head);
    441   Object* OptimizedCodeListHead();
    442   void SetDeoptimizedCodeListHead(Object* head);
    443   Object* DeoptimizedCodeListHead();
    444 
    445   Handle<Object> ErrorMessageForCodeGenerationFromStrings();
    446 
    447 #define NATIVE_CONTEXT_FIELD_ACCESSORS(index, type, name) \
    448   void  set_##name(type* value) {                         \
    449     ASSERT(IsNativeContext());                            \
    450     set(index, value);                                    \
    451   }                                                       \
    452   bool is_##name(type* value) {                           \
    453     ASSERT(IsNativeContext());                            \
    454     return type::cast(get(index)) == value;               \
    455   }                                                       \
    456   type* name() {                                          \
    457     ASSERT(IsNativeContext());                            \
    458     return type::cast(get(index));                        \
    459   }
    460   NATIVE_CONTEXT_FIELDS(NATIVE_CONTEXT_FIELD_ACCESSORS)
    461 #undef NATIVE_CONTEXT_FIELD_ACCESSORS
    462 
    463   // Lookup the slot called name, starting with the current context.
    464   // There are three possibilities:
    465   //
    466   // 1) result->IsContext():
    467   //    The binding was found in a context.  *index is always the
    468   //    non-negative slot index.  *attributes is NONE for var and let
    469   //    declarations, READ_ONLY for const declarations (never ABSENT).
    470   //
    471   // 2) result->IsJSObject():
    472   //    The binding was found as a named property in a context extension
    473   //    object (i.e., was introduced via eval), as a property on the subject
    474   //    of with, or as a property of the global object.  *index is -1 and
    475   //    *attributes is not ABSENT.
    476   //
    477   // 3) result.is_null():
    478   //    There was no binding found, *index is always -1 and *attributes is
    479   //    always ABSENT.
    480   Handle<Object> Lookup(Handle<String> name,
    481                         ContextLookupFlags flags,
    482                         int* index,
    483                         PropertyAttributes* attributes,
    484                         BindingFlags* binding_flags);
    485 
    486   // Code generation support.
    487   static int SlotOffset(int index) {
    488     return kHeaderSize + index * kPointerSize - kHeapObjectTag;
    489   }
    490 
    491   static int FunctionMapIndex(LanguageMode language_mode, bool is_generator) {
    492     return is_generator
    493       ? (language_mode == CLASSIC_MODE
    494          ? GENERATOR_FUNCTION_MAP_INDEX
    495          : STRICT_MODE_GENERATOR_FUNCTION_MAP_INDEX)
    496       : (language_mode == CLASSIC_MODE
    497          ? FUNCTION_MAP_INDEX
    498          : STRICT_MODE_FUNCTION_MAP_INDEX);
    499   }
    500 
    501   static const int kSize = kHeaderSize + NATIVE_CONTEXT_SLOTS * kPointerSize;
    502 
    503   // GC support.
    504   typedef FixedBodyDescriptor<
    505       kHeaderSize, kSize, kSize> ScavengeBodyDescriptor;
    506 
    507   typedef FixedBodyDescriptor<
    508       kHeaderSize,
    509       kHeaderSize + FIRST_WEAK_SLOT * kPointerSize,
    510       kSize> MarkCompactBodyDescriptor;
    511 
    512  private:
    513   // Unchecked access to the slots.
    514   Object* unchecked_previous() { return get(PREVIOUS_INDEX); }
    515 
    516 #ifdef DEBUG
    517   // Bootstrapping-aware type checks.
    518   static bool IsBootstrappingOrValidParentContext(Object* object, Context* kid);
    519   static bool IsBootstrappingOrGlobalObject(Isolate* isolate, Object* object);
    520 #endif
    521 
    522   STATIC_CHECK(kHeaderSize == Internals::kContextHeaderSize);
    523   STATIC_CHECK(EMBEDDER_DATA_INDEX == Internals::kContextEmbedderDataIndex);
    524 };
    525 
    526 } }  // namespace v8::internal
    527 
    528 #endif  // V8_CONTEXTS_H_
    529