13ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch// Copyright 2012 the V8 project authors. All rights reserved. 2a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// Redistribution and use in source and binary forms, with or without 3a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// modification, are permitted provided that the following conditions are 4a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// met: 5a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// 6a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// * Redistributions of source code must retain the above copyright 7a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// notice, this list of conditions and the following disclaimer. 8a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// * Redistributions in binary form must reproduce the above 9a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// copyright notice, this list of conditions and the following 10a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// disclaimer in the documentation and/or other materials provided 11a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// with the distribution. 12a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// * Neither the name of Google Inc. nor the names of its 13a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// contributors may be used to endorse or promote products derived 14a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// from this software without specific prior written permission. 15a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// 16a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 28a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#include "v8.h" 29a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 30a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#include "accessors.h" 31a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#include "api.h" 32257744e915dfc84d6d07a6b2accf8402d9ffc708Ben Murdoch#include "bootstrapper.h" 33a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#include "execution.h" 34a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#include "global-handles.h" 35a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#include "ic-inl.h" 36a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#include "natives.h" 37a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#include "platform.h" 38a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#include "runtime.h" 39a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#include "serialize.h" 40a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#include "stub-cache.h" 41a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#include "v8threads.h" 42a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 43a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Blocknamespace v8 { 44a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Blocknamespace internal { 45a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 46a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 47a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// ----------------------------------------------------------------------------- 48a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// Coding of external references. 49a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 50a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// The encoding of an external reference. The type is in the high word. 51a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block// The id is in the low word. 52a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Blockstatic uint32_t EncodeExternal(TypeCode type, uint16_t id) { 53a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block return static_cast<uint32_t>(type) << 16 | id; 54a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 55a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 56a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 57a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Blockstatic int* GetInternalPointer(StatsCounter* counter) { 58a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // All counters refer to dummy_counter, if deserializing happens without 59a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // setting up counters. 60a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block static int dummy_counter = 0; 61a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block return counter->Enabled() ? counter->GetInternalPointer() : &dummy_counter; 62a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 63a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 64a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 6569a99ed0b2b2ef69d393c371b03db3a98aaf880eBen MurdochExternalReferenceTable* ExternalReferenceTable::instance(Isolate* isolate) { 6669a99ed0b2b2ef69d393c371b03db3a98aaf880eBen Murdoch ExternalReferenceTable* external_reference_table = 6769a99ed0b2b2ef69d393c371b03db3a98aaf880eBen Murdoch isolate->external_reference_table(); 6869a99ed0b2b2ef69d393c371b03db3a98aaf880eBen Murdoch if (external_reference_table == NULL) { 6969a99ed0b2b2ef69d393c371b03db3a98aaf880eBen Murdoch external_reference_table = new ExternalReferenceTable(isolate); 7069a99ed0b2b2ef69d393c371b03db3a98aaf880eBen Murdoch isolate->set_external_reference_table(external_reference_table); 7144f0eee88ff00398ff7f715fab053374d808c90dSteve Block } 7269a99ed0b2b2ef69d393c371b03db3a98aaf880eBen Murdoch return external_reference_table; 7369a99ed0b2b2ef69d393c371b03db3a98aaf880eBen Murdoch} 74a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 75a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 76a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Blockvoid ExternalReferenceTable::AddFromId(TypeCode type, 77a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block uint16_t id, 7844f0eee88ff00398ff7f715fab053374d808c90dSteve Block const char* name, 7944f0eee88ff00398ff7f715fab053374d808c90dSteve Block Isolate* isolate) { 80a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block Address address; 81a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block switch (type) { 82a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block case C_BUILTIN: { 8344f0eee88ff00398ff7f715fab053374d808c90dSteve Block ExternalReference ref(static_cast<Builtins::CFunctionId>(id), isolate); 84a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block address = ref.address(); 85a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block break; 86a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 87a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block case BUILTIN: { 8844f0eee88ff00398ff7f715fab053374d808c90dSteve Block ExternalReference ref(static_cast<Builtins::Name>(id), isolate); 89a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block address = ref.address(); 90a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block break; 91a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 92a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block case RUNTIME_FUNCTION: { 9344f0eee88ff00398ff7f715fab053374d808c90dSteve Block ExternalReference ref(static_cast<Runtime::FunctionId>(id), isolate); 94a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block address = ref.address(); 95a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block break; 96a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 97a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block case IC_UTILITY: { 9844f0eee88ff00398ff7f715fab053374d808c90dSteve Block ExternalReference ref(IC_Utility(static_cast<IC::UtilityId>(id)), 9944f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate); 100a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block address = ref.address(); 101a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block break; 102a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 103a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block default: 104a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNREACHABLE(); 105a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block return; 106a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 107a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block Add(address, type, id, name); 108a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 109a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 110a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 111a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Blockvoid ExternalReferenceTable::Add(Address address, 112a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block TypeCode type, 113a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block uint16_t id, 114a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block const char* name) { 115d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ASSERT_NE(NULL, address); 116a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block ExternalReferenceEntry entry; 117a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block entry.address = address; 118a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block entry.code = EncodeExternal(type, id); 119a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block entry.name = name; 120d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ASSERT_NE(0, entry.code); 121a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block refs_.Add(entry); 122a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block if (id > max_id_[type]) max_id_[type] = id; 123a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 124a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 125a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 12644f0eee88ff00398ff7f715fab053374d808c90dSteve Blockvoid ExternalReferenceTable::PopulateTable(Isolate* isolate) { 127a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block for (int type_code = 0; type_code < kTypeCodeCount; type_code++) { 128a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block max_id_[type_code] = 0; 129a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 130a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 131a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // The following populates all of the different type of external references 132a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // into the ExternalReferenceTable. 133a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // 134a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // NOTE: This function was originally 100k of code. It has since been 135a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // rewritten to be mostly table driven, as the callback macro style tends to 136a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // very easily cause code bloat. Please be careful in the future when adding 137a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // new references. 138a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 139a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block struct RefTableEntry { 140a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block TypeCode type; 141a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block uint16_t id; 142a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block const char* name; 143a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block }; 144a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 145a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block static const RefTableEntry ref_table[] = { 146a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // Builtins 147e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke#define DEF_ENTRY_C(name, ignored) \ 148a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block { C_BUILTIN, \ 149a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block Builtins::c_##name, \ 150a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Builtins::" #name }, 151a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 152a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block BUILTIN_LIST_C(DEF_ENTRY_C) 153a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#undef DEF_ENTRY_C 154a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 155e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke#define DEF_ENTRY_C(name, ignored) \ 156a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block { BUILTIN, \ 15744f0eee88ff00398ff7f715fab053374d808c90dSteve Block Builtins::k##name, \ 158a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Builtins::" #name }, 1591e0659c275bb392c045087af4f6b0d7565cb3d77Steve Block#define DEF_ENTRY_A(name, kind, state, extra) DEF_ENTRY_C(name, ignored) 160a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 161a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block BUILTIN_LIST_C(DEF_ENTRY_C) 162a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block BUILTIN_LIST_A(DEF_ENTRY_A) 163a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block BUILTIN_LIST_DEBUG_A(DEF_ENTRY_A) 164a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#undef DEF_ENTRY_C 165a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#undef DEF_ENTRY_A 166a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 167a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // Runtime functions 168a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#define RUNTIME_ENTRY(name, nargs, ressize) \ 169a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block { RUNTIME_FUNCTION, \ 170a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block Runtime::k##name, \ 171a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Runtime::" #name }, 172a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 173a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block RUNTIME_FUNCTION_LIST(RUNTIME_ENTRY) 174a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#undef RUNTIME_ENTRY 175a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 176a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // IC utilities 177a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#define IC_ENTRY(name) \ 178a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block { IC_UTILITY, \ 179a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block IC::k##name, \ 180a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "IC::" #name }, 181a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 182a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block IC_UTIL_LIST(IC_ENTRY) 183a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#undef IC_ENTRY 184a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block }; // end of ref_table[]. 185a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 186a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block for (size_t i = 0; i < ARRAY_SIZE(ref_table); ++i) { 18744f0eee88ff00398ff7f715fab053374d808c90dSteve Block AddFromId(ref_table[i].type, 18844f0eee88ff00398ff7f715fab053374d808c90dSteve Block ref_table[i].id, 18944f0eee88ff00398ff7f715fab053374d808c90dSteve Block ref_table[i].name, 19044f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate); 191a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 192a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 193a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#ifdef ENABLE_DEBUGGER_SUPPORT 194a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // Debug addresses 19544f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(Debug_Address(Debug::k_after_break_target_address).address(isolate), 196a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block DEBUG_ADDRESS, 197a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block Debug::k_after_break_target_address << kDebugIdShift, 198a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Debug::after_break_target_address()"); 19944f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(Debug_Address(Debug::k_debug_break_slot_address).address(isolate), 2007f4d5bd8c03935e2c0cd412e561b8fc5a6a880aeBen Murdoch DEBUG_ADDRESS, 2017f4d5bd8c03935e2c0cd412e561b8fc5a6a880aeBen Murdoch Debug::k_debug_break_slot_address << kDebugIdShift, 2027f4d5bd8c03935e2c0cd412e561b8fc5a6a880aeBen Murdoch "Debug::debug_break_slot_address()"); 20344f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(Debug_Address(Debug::k_debug_break_return_address).address(isolate), 204a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block DEBUG_ADDRESS, 205a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block Debug::k_debug_break_return_address << kDebugIdShift, 206a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Debug::debug_break_return_address()"); 20744f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(Debug_Address(Debug::k_restarter_frame_function_pointer).address(isolate), 208bb769b257e753aafcbd96767abb2abc645eaa20cBen Murdoch DEBUG_ADDRESS, 209bb769b257e753aafcbd96767abb2abc645eaa20cBen Murdoch Debug::k_restarter_frame_function_pointer << kDebugIdShift, 210bb769b257e753aafcbd96767abb2abc645eaa20cBen Murdoch "Debug::restarter_frame_function_pointer_address()"); 211a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#endif 212a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 213a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // Stat counters 214a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block struct StatsRefTableEntry { 21544f0eee88ff00398ff7f715fab053374d808c90dSteve Block StatsCounter* (Counters::*counter)(); 216a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block uint16_t id; 217a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block const char* name; 218a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block }; 219a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 22044f0eee88ff00398ff7f715fab053374d808c90dSteve Block const StatsRefTableEntry stats_ref_table[] = { 221a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#define COUNTER_ENTRY(name, caption) \ 22244f0eee88ff00398ff7f715fab053374d808c90dSteve Block { &Counters::name, \ 223a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block Counters::k_##name, \ 224a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Counters::" #name }, 225a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 226a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block STATS_COUNTER_LIST_1(COUNTER_ENTRY) 227a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block STATS_COUNTER_LIST_2(COUNTER_ENTRY) 228a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#undef COUNTER_ENTRY 229a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block }; // end of stats_ref_table[]. 230a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 23144f0eee88ff00398ff7f715fab053374d808c90dSteve Block Counters* counters = isolate->counters(); 232a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block for (size_t i = 0; i < ARRAY_SIZE(stats_ref_table); ++i) { 23344f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(reinterpret_cast<Address>(GetInternalPointer( 23444f0eee88ff00398ff7f715fab053374d808c90dSteve Block (counters->*(stats_ref_table[i].counter))())), 235a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block STATS_COUNTER, 236a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block stats_ref_table[i].id, 237a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block stats_ref_table[i].name); 238a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 239a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 240a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // Top addresses 2413ce2e2076e8e3e60cf1810eec160ea2d8557e9e7Steve Block 2423ce2e2076e8e3e60cf1810eec160ea2d8557e9e7Steve Block const char* AddressNames[] = { 243589d6979ff2ef66fca2d8fa51404c369ca5e9250Ben Murdoch#define BUILD_NAME_LITERAL(CamelName, hacker_name) \ 244589d6979ff2ef66fca2d8fa51404c369ca5e9250Ben Murdoch "Isolate::" #hacker_name "_address", 245589d6979ff2ef66fca2d8fa51404c369ca5e9250Ben Murdoch FOR_EACH_ISOLATE_ADDRESS_NAME(BUILD_NAME_LITERAL) 2463ce2e2076e8e3e60cf1810eec160ea2d8557e9e7Steve Block NULL 2473ce2e2076e8e3e60cf1810eec160ea2d8557e9e7Steve Block#undef C 2483ce2e2076e8e3e60cf1810eec160ea2d8557e9e7Steve Block }; 2493ce2e2076e8e3e60cf1810eec160ea2d8557e9e7Steve Block 250589d6979ff2ef66fca2d8fa51404c369ca5e9250Ben Murdoch for (uint16_t i = 0; i < Isolate::kIsolateAddressCount; ++i) { 25144f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(isolate->get_address_from_id((Isolate::AddressId)i), 25244f0eee88ff00398ff7f715fab053374d808c90dSteve Block TOP_ADDRESS, i, AddressNames[i]); 253a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 254a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 255a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // Accessors 256a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#define ACCESSOR_DESCRIPTOR_DECLARATION(name) \ 257a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block Add((Address)&Accessors::name, \ 258a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block ACCESSOR, \ 259a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block Accessors::k##name, \ 260a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Accessors::" #name); 261a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 262a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block ACCESSOR_DESCRIPTOR_LIST(ACCESSOR_DESCRIPTOR_DECLARATION) 263a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#undef ACCESSOR_DESCRIPTOR_DECLARATION 264a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 26544f0eee88ff00398ff7f715fab053374d808c90dSteve Block StubCache* stub_cache = isolate->stub_cache(); 26644f0eee88ff00398ff7f715fab053374d808c90dSteve Block 267a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // Stub cache tables 26844f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(stub_cache->key_reference(StubCache::kPrimary).address(), 269a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block STUB_CACHE_TABLE, 270a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1, 271a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "StubCache::primary_->key"); 27244f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(stub_cache->value_reference(StubCache::kPrimary).address(), 273a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block STUB_CACHE_TABLE, 274a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 2, 275a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "StubCache::primary_->value"); 2763ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Add(stub_cache->map_reference(StubCache::kPrimary).address(), 2775d4cdbf7a67d3662fa0bee4efdb7edd8daec9b0bBen Murdoch STUB_CACHE_TABLE, 27885b71799222b55eb5dd74ea26efe0c64ab655c8cBen Murdoch 3, 2793ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch "StubCache::primary_->map"); 2803ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Add(stub_cache->key_reference(StubCache::kSecondary).address(), 2813ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch STUB_CACHE_TABLE, 2823ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 4, 283a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "StubCache::secondary_->key"); 28444f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(stub_cache->value_reference(StubCache::kSecondary).address(), 285a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block STUB_CACHE_TABLE, 2863ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 5, 287a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "StubCache::secondary_->value"); 2883ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Add(stub_cache->map_reference(StubCache::kSecondary).address(), 2893ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch STUB_CACHE_TABLE, 2903ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 6, 2913ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch "StubCache::secondary_->map"); 292a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 293a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // Runtime entries 29444f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::perform_gc_function(isolate).address(), 295a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block RUNTIME_ENTRY, 296a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1, 297a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Runtime::PerformGC"); 29844f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::fill_heap_number_with_random_function( 29944f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate).address(), 300a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block RUNTIME_ENTRY, 301a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 2, 3026ded16be15dd865a9b21ea304d5273c8be299c87Steve Block "V8::FillHeapNumberWithRandom"); 30344f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::random_uint32_function(isolate).address(), 3046ded16be15dd865a9b21ea304d5273c8be299c87Steve Block RUNTIME_ENTRY, 3056ded16be15dd865a9b21ea304d5273c8be299c87Steve Block 3, 3066ded16be15dd865a9b21ea304d5273c8be299c87Steve Block "V8::Random"); 30744f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::delete_handle_scope_extensions(isolate).address(), 3085913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck RUNTIME_ENTRY, 3091e0659c275bb392c045087af4f6b0d7565cb3d77Steve Block 4, 3105913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck "HandleScope::DeleteExtensions"); 3113ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Add(ExternalReference:: 3123ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch incremental_marking_record_write_function(isolate).address(), 3133ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch RUNTIME_ENTRY, 3143ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 5, 3153ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch "IncrementalMarking::RecordWrite"); 3163ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Add(ExternalReference::store_buffer_overflow_function(isolate).address(), 3173ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch RUNTIME_ENTRY, 3183ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 6, 3193ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch "StoreBuffer::StoreBufferOverflow"); 3203ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Add(ExternalReference:: 3213ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch incremental_evacuation_record_write_function(isolate).address(), 3223ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch RUNTIME_ENTRY, 3233ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 7, 3243ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch "IncrementalMarking::RecordWrite"); 3253ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 3263ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 3275913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck 328a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // Miscellaneous 3293ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Add(ExternalReference::roots_array_start(isolate).address(), 330a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 331a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 3, 3323ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch "Heap::roots_array_start()"); 33344f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::address_of_stack_limit(isolate).address(), 334a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 335a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 4, 336a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "StackGuard::address_of_jslimit()"); 33744f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::address_of_real_stack_limit(isolate).address(), 338a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 339a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 5, 340d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block "StackGuard::address_of_real_jslimit()"); 3413bec4d28b1f388dbc06a9c4276e1a03e86c52b04Ben Murdoch#ifndef V8_INTERPRETED_REGEXP 34244f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::address_of_regexp_stack_limit(isolate).address(), 343d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block UNCLASSIFIED, 344d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block 6, 345a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "RegExpStack::limit_address()"); 34644f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::address_of_regexp_stack_memory_address( 34744f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate).address(), 348a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 349d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block 7, 3509dcf7e2f83591d471e88bf7d230651900b8e424bKristian Monsen "RegExpStack::memory_address()"); 35144f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::address_of_regexp_stack_memory_size(isolate).address(), 3529dcf7e2f83591d471e88bf7d230651900b8e424bKristian Monsen UNCLASSIFIED, 3539dcf7e2f83591d471e88bf7d230651900b8e424bKristian Monsen 8, 3549dcf7e2f83591d471e88bf7d230651900b8e424bKristian Monsen "RegExpStack::memory_size()"); 35544f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::address_of_static_offsets_vector(isolate).address(), 3569dcf7e2f83591d471e88bf7d230651900b8e424bKristian Monsen UNCLASSIFIED, 3579dcf7e2f83591d471e88bf7d230651900b8e424bKristian Monsen 9, 3589dcf7e2f83591d471e88bf7d230651900b8e424bKristian Monsen "OffsetsVector::static_offsets_vector"); 3593bec4d28b1f388dbc06a9c4276e1a03e86c52b04Ben Murdoch#endif // V8_INTERPRETED_REGEXP 36044f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::new_space_start(isolate).address(), 3619dcf7e2f83591d471e88bf7d230651900b8e424bKristian Monsen UNCLASSIFIED, 3629dcf7e2f83591d471e88bf7d230651900b8e424bKristian Monsen 10, 363a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Heap::NewSpaceStart()"); 36444f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::new_space_mask(isolate).address(), 365a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 3669dcf7e2f83591d471e88bf7d230651900b8e424bKristian Monsen 11, 367402d937239b0e2fd11bf2f4fe972ad78aa9fd481Andrei Popescu "Heap::NewSpaceMask()"); 36844f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::heap_always_allocate_scope_depth(isolate).address(), 369402d937239b0e2fd11bf2f4fe972ad78aa9fd481Andrei Popescu UNCLASSIFIED, 3709dcf7e2f83591d471e88bf7d230651900b8e424bKristian Monsen 12, 371a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Heap::always_allocate_scope_depth()"); 37244f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::new_space_allocation_limit_address(isolate).address(), 373a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 3743ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 14, 375a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Heap::NewSpaceAllocationLimitAddress()"); 37644f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::new_space_allocation_top_address(isolate).address(), 377a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 3783ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 15, 379a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Heap::NewSpaceAllocationTopAddress()"); 380a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#ifdef ENABLE_DEBUGGER_SUPPORT 38144f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::debug_break(isolate).address(), 382a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 3833ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 16, 384a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Debug::Break()"); 38544f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::debug_step_in_fp_address(isolate).address(), 386a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 3873ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 17, 388a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "Debug::step_in_fp_addr()"); 389a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block#endif 39044f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::double_fp_operation(Token::ADD, isolate).address(), 391a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 3923ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 18, 393a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "add_two_doubles"); 39444f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::double_fp_operation(Token::SUB, isolate).address(), 395a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 3963ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 19, 397a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "sub_two_doubles"); 39844f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::double_fp_operation(Token::MUL, isolate).address(), 399a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 4003ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 20, 401a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "mul_two_doubles"); 40244f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::double_fp_operation(Token::DIV, isolate).address(), 403a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 4043ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 21, 405a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "div_two_doubles"); 40644f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::double_fp_operation(Token::MOD, isolate).address(), 407a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 4083ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 22, 409a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "mod_two_doubles"); 41044f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::compare_doubles(isolate).address(), 411a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 4123ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 23, 413a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "compare_doubles"); 4146ded16be15dd865a9b21ea304d5273c8be299c87Steve Block#ifndef V8_INTERPRETED_REGEXP 41544f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::re_case_insensitive_compare_uc16(isolate).address(), 4166ded16be15dd865a9b21ea304d5273c8be299c87Steve Block UNCLASSIFIED, 4173ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 24, 418a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "NativeRegExpMacroAssembler::CaseInsensitiveCompareUC16()"); 41944f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::re_check_stack_guard_state(isolate).address(), 420a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 4213ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 25, 422a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "RegExpMacroAssembler*::CheckStackGuardState()"); 42344f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::re_grow_stack(isolate).address(), 424a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNCLASSIFIED, 4253ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 26, 426a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block "NativeRegExpMacroAssembler::GrowStack()"); 427e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke Add(ExternalReference::re_word_character_map().address(), 428e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke UNCLASSIFIED, 4293ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 27, 430e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke "NativeRegExpMacroAssembler::word_character_map"); 4316ded16be15dd865a9b21ea304d5273c8be299c87Steve Block#endif // V8_INTERPRETED_REGEXP 432e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke // Keyed lookup cache. 43344f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::keyed_lookup_cache_keys(isolate).address(), 434e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke UNCLASSIFIED, 4353ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 28, 436e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke "KeyedLookupCache::keys()"); 43744f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::keyed_lookup_cache_field_offsets(isolate).address(), 438e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke UNCLASSIFIED, 4393ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 29, 440e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke "KeyedLookupCache::field_offsets()"); 44144f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::transcendental_cache_array_address(isolate).address(), 442402d937239b0e2fd11bf2f4fe972ad78aa9fd481Andrei Popescu UNCLASSIFIED, 4433ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 30, 444402d937239b0e2fd11bf2f4fe972ad78aa9fd481Andrei Popescu "TranscendentalCache::caches()"); 4455913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck Add(ExternalReference::handle_scope_next_address().address(), 4465913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck UNCLASSIFIED, 4473ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 31, 4485913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck "HandleScope::next"); 4495913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck Add(ExternalReference::handle_scope_limit_address().address(), 4505913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck UNCLASSIFIED, 4513ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 32, 4525913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck "HandleScope::limit"); 4535913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck Add(ExternalReference::handle_scope_level_address().address(), 4545913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck UNCLASSIFIED, 4553ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 33, 4565913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck "HandleScope::level"); 45744f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::new_deoptimizer_function(isolate).address(), 458b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch UNCLASSIFIED, 4593ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 34, 460b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch "Deoptimizer::New()"); 46144f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::compute_output_frames_function(isolate).address(), 462b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch UNCLASSIFIED, 4633ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 35, 464b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch "Deoptimizer::ComputeOutputFrames()"); 465b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch Add(ExternalReference::address_of_min_int().address(), 466b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch UNCLASSIFIED, 4673ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 36, 468b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch "LDoubleConstant::min_int"); 469b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch Add(ExternalReference::address_of_one_half().address(), 470b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch UNCLASSIFIED, 4713ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 37, 472b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch "LDoubleConstant::one_half"); 47344f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::isolate_address().address(), 474b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch UNCLASSIFIED, 4753ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 38, 47644f0eee88ff00398ff7f715fab053374d808c90dSteve Block "isolate"); 47744f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::address_of_minus_zero().address(), 47844f0eee88ff00398ff7f715fab053374d808c90dSteve Block UNCLASSIFIED, 4793ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 39, 480b8e0da25ee8efac3bb05cd6b2730aafbd96119f4Ben Murdoch "LDoubleConstant::minus_zero"); 481b8e0da25ee8efac3bb05cd6b2730aafbd96119f4Ben Murdoch Add(ExternalReference::address_of_negative_infinity().address(), 482b8e0da25ee8efac3bb05cd6b2730aafbd96119f4Ben Murdoch UNCLASSIFIED, 4833ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 40, 484b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch "LDoubleConstant::negative_infinity"); 48544f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::power_double_double_function(isolate).address(), 486b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch UNCLASSIFIED, 4873ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 41, 488b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch "power_double_double_function"); 48944f0eee88ff00398ff7f715fab053374d808c90dSteve Block Add(ExternalReference::power_double_int_function(isolate).address(), 490b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch UNCLASSIFIED, 4913ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 42, 492b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch "power_double_int_function"); 4933ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Add(ExternalReference::store_buffer_top(isolate).address(), 494592a9fc1d8ea420377a2e7efd0600e20b058be2bBen Murdoch UNCLASSIFIED, 4953ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 43, 4963ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch "store_buffer_top"); 4973ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Add(ExternalReference::address_of_canonical_non_hole_nan().address(), 4983ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch UNCLASSIFIED, 4993ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 44, 5003ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch "canonical_nan"); 5013ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Add(ExternalReference::address_of_the_hole_nan().address(), 5023ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch UNCLASSIFIED, 5033ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 45, 5043ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch "the_hole_nan"); 5053ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Add(ExternalReference::get_date_field_function(isolate).address(), 5063ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch UNCLASSIFIED, 5073ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 46, 5083ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch "JSDate::GetField"); 5093ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Add(ExternalReference::date_cache_stamp(isolate).address(), 5103ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch UNCLASSIFIED, 5113ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 47, 5123ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch "date_cache_stamp"); 513a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 514a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 515a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 516a7e24c173cf37484693b9abb38e494fa7bd7baebSteve BlockExternalReferenceEncoder::ExternalReferenceEncoder() 51744f0eee88ff00398ff7f715fab053374d808c90dSteve Block : encodings_(Match), 51844f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate_(Isolate::Current()) { 519a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block ExternalReferenceTable* external_references = 52044f0eee88ff00398ff7f715fab053374d808c90dSteve Block ExternalReferenceTable::instance(isolate_); 521a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block for (int i = 0; i < external_references->size(); ++i) { 522a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block Put(external_references->address(i), i); 523a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 524a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 525a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 526a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 527a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Blockuint32_t ExternalReferenceEncoder::Encode(Address key) const { 528a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block int index = IndexOf(key); 529bb769b257e753aafcbd96767abb2abc645eaa20cBen Murdoch ASSERT(key == NULL || index >= 0); 53044f0eee88ff00398ff7f715fab053374d808c90dSteve Block return index >=0 ? 53144f0eee88ff00398ff7f715fab053374d808c90dSteve Block ExternalReferenceTable::instance(isolate_)->code(index) : 0; 532a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 533a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 534a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 535a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Blockconst char* ExternalReferenceEncoder::NameOfAddress(Address key) const { 536a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block int index = IndexOf(key); 53744f0eee88ff00398ff7f715fab053374d808c90dSteve Block return index >= 0 ? 53844f0eee88ff00398ff7f715fab053374d808c90dSteve Block ExternalReferenceTable::instance(isolate_)->name(index) : NULL; 539a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 540a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 541a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 542a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Blockint ExternalReferenceEncoder::IndexOf(Address key) const { 543a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block if (key == NULL) return -1; 544a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block HashMap::Entry* entry = 54544f0eee88ff00398ff7f715fab053374d808c90dSteve Block const_cast<HashMap&>(encodings_).Lookup(key, Hash(key), false); 546a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block return entry == NULL 547a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block ? -1 548a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block : static_cast<int>(reinterpret_cast<intptr_t>(entry->value)); 549a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 550a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 551a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 552a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Blockvoid ExternalReferenceEncoder::Put(Address key, int index) { 553a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block HashMap::Entry* entry = encodings_.Lookup(key, Hash(key), true); 5546ded16be15dd865a9b21ea304d5273c8be299c87Steve Block entry->value = reinterpret_cast<void*>(index); 555a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 556a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 557a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 558a7e24c173cf37484693b9abb38e494fa7bd7baebSteve BlockExternalReferenceDecoder::ExternalReferenceDecoder() 55944f0eee88ff00398ff7f715fab053374d808c90dSteve Block : encodings_(NewArray<Address*>(kTypeCodeCount)), 56044f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate_(Isolate::Current()) { 561a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block ExternalReferenceTable* external_references = 56244f0eee88ff00398ff7f715fab053374d808c90dSteve Block ExternalReferenceTable::instance(isolate_); 563a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block for (int type = kFirstTypeCode; type < kTypeCodeCount; ++type) { 564a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block int max = external_references->max_id(type) + 1; 565a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block encodings_[type] = NewArray<Address>(max + 1); 566a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 567a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block for (int i = 0; i < external_references->size(); ++i) { 568a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block Put(external_references->code(i), external_references->address(i)); 569a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 570a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 571a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 572a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 573a7e24c173cf37484693b9abb38e494fa7bd7baebSteve BlockExternalReferenceDecoder::~ExternalReferenceDecoder() { 574a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block for (int type = kFirstTypeCode; type < kTypeCodeCount; ++type) { 575a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block DeleteArray(encodings_[type]); 576a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 577a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block DeleteArray(encodings_); 578a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 579a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 580a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 581d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockbool Serializer::serialization_enabled_ = false; 582d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockbool Serializer::too_late_to_enable_now_ = false; 583a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 584a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 58544f0eee88ff00398ff7f715fab053374d808c90dSteve BlockDeserializer::Deserializer(SnapshotByteSource* source) 58644f0eee88ff00398ff7f715fab053374d808c90dSteve Block : isolate_(NULL), 58744f0eee88ff00398ff7f715fab053374d808c90dSteve Block source_(source), 58844f0eee88ff00398ff7f715fab053374d808c90dSteve Block external_reference_decoder_(NULL) { 589a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 590a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 591a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 592d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block// This routine both allocates a new object, and also keeps 593d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block// track of where objects have been allocated so that we can 594d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block// fix back references when deserializing. 595d0582a6c46733687d045e4188a1bcd0123c758a1Steve BlockAddress Deserializer::Allocate(int space_index, Space* space, int size) { 596d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Address address; 597d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (!SpaceIsLarge(space_index)) { 598d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ASSERT(!SpaceIsPaged(space_index) || 599d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block size <= Page::kPageSize - Page::kObjectStartOffset); 6005913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck MaybeObject* maybe_new_allocation; 601d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (space_index == NEW_SPACE) { 6025913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck maybe_new_allocation = 6035913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck reinterpret_cast<NewSpace*>(space)->AllocateRaw(size); 604d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } else { 6055913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck maybe_new_allocation = 6065913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck reinterpret_cast<PagedSpace*>(space)->AllocateRaw(size); 607d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 6083ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch ASSERT(!maybe_new_allocation->IsFailure()); 6095913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck Object* new_allocation = maybe_new_allocation->ToObjectUnchecked(); 610d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block HeapObject* new_object = HeapObject::cast(new_allocation); 611d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block address = new_object->address(); 612d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block high_water_[space_index] = address + size; 613d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } else { 614d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ASSERT(SpaceIsLarge(space_index)); 615d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block LargeObjectSpace* lo_space = reinterpret_cast<LargeObjectSpace*>(space); 616d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Object* new_allocation; 6173ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (space_index == kLargeData || space_index == kLargeFixedArray) { 6185913587db4c6bab03d97bfe44b06289fd6d7270dJohn Reck new_allocation = 6193ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch lo_space->AllocateRaw(size, NOT_EXECUTABLE)->ToObjectUnchecked(); 620d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } else { 621d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ASSERT_EQ(kLargeCode, space_index); 6223ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch new_allocation = 6233ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch lo_space->AllocateRaw(size, EXECUTABLE)->ToObjectUnchecked(); 624a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 625d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block HeapObject* new_object = HeapObject::cast(new_allocation); 626d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // Record all large objects in the same space. 627d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block address = new_object->address(); 6283100271588b61cbc1dc472a3f2f105d2eed8497fAndrei Popescu pages_[LO_SPACE].Add(address); 629a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 630d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block last_object_address_ = address; 631d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return address; 632d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block} 633a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 634a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 635d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block// This returns the address of an object that has been described in the 636d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block// snapshot as being offset bytes back in a particular space. 637d0582a6c46733687d045e4188a1bcd0123c758a1Steve BlockHeapObject* Deserializer::GetAddressFromEnd(int space) { 638d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int offset = source_->GetInt(); 639d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ASSERT(!SpaceIsLarge(space)); 640d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block offset <<= kObjectAlignmentBits; 641d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return HeapObject::FromAddress(high_water_[space] - offset); 642d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block} 643a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 644a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 645d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block// This returns the address of an object that has been described in the 646d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block// snapshot as being offset bytes into a particular space. 647d0582a6c46733687d045e4188a1bcd0123c758a1Steve BlockHeapObject* Deserializer::GetAddressFromStart(int space) { 648d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int offset = source_->GetInt(); 649d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (SpaceIsLarge(space)) { 650d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // Large spaces have one object per 'page'. 651d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return HeapObject::FromAddress(pages_[LO_SPACE][offset]); 652a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 653d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block offset <<= kObjectAlignmentBits; 654d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (space == NEW_SPACE) { 655d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // New space has only one space - numbered 0. 656d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return HeapObject::FromAddress(pages_[space][0] + offset); 657a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 658d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ASSERT(SpaceIsPaged(space)); 659e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke int page_of_pointee = offset >> kPageSizeBits; 660d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Address object_address = pages_[space][page_of_pointee] + 661d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block (offset & Page::kPageAlignmentMask); 662d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return HeapObject::FromAddress(object_address); 663a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 664a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 665a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 666d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockvoid Deserializer::Deserialize() { 66744f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate_ = Isolate::Current(); 6683ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch ASSERT(isolate_ != NULL); 669d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // Don't GC while deserializing - just expand the heap. 670d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block AlwaysAllocateScope always_allocate; 671d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // Don't use the free lists while deserializing. 672d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block LinearAllocationScope allocate_linearly; 673d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // No active threads. 67444f0eee88ff00398ff7f715fab053374d808c90dSteve Block ASSERT_EQ(NULL, isolate_->thread_manager()->FirstThreadStateInUse()); 675d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // No active handles. 67644f0eee88ff00398ff7f715fab053374d808c90dSteve Block ASSERT(isolate_->handle_scope_implementer()->blocks()->is_empty()); 677d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // Make sure the entire partial snapshot cache is traversed, filling it with 678d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // valid object pointers. 67944f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate_->set_serialize_partial_snapshot_cache_length( 68044f0eee88ff00398ff7f715fab053374d808c90dSteve Block Isolate::kPartialSnapshotCacheCapacity); 681d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ASSERT_EQ(NULL, external_reference_decoder_); 682d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block external_reference_decoder_ = new ExternalReferenceDecoder(); 68344f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate_->heap()->IterateStrongRoots(this, VISIT_ONLY_STRONG); 68444f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate_->heap()->IterateWeakRoots(this, VISIT_ALL); 685f87a203d89e1bbb6708282e0b64dbd13d59b723dBen Murdoch 68644f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate_->heap()->set_global_contexts_list( 68744f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate_->heap()->undefined_value()); 6883ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 6893ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // Update data pointers to the external strings containing natives sources. 6903ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch for (int i = 0; i < Natives::GetBuiltinsCount(); i++) { 6913ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Object* source = isolate_->heap()->natives_source_cache()->get(i); 6923ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (!source->IsUndefined()) { 6933ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch ExternalAsciiString::cast(source)->update_data_cache(); 6943ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 6953ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 696e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke} 697e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke 698e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke 699e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarkevoid Deserializer::DeserializePartial(Object** root) { 70044f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate_ = Isolate::Current(); 701e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke // Don't GC while deserializing - just expand the heap. 702e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke AlwaysAllocateScope always_allocate; 703e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke // Don't use the free lists while deserializing. 704e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke LinearAllocationScope allocate_linearly; 705e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke if (external_reference_decoder_ == NULL) { 706e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke external_reference_decoder_ = new ExternalReferenceDecoder(); 707e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke } 708e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke VisitPointer(root); 709e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke} 710e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke 711e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke 712d91b9f7d46489a9ee00f9cb415630299c76a502bLeon ClarkeDeserializer::~Deserializer() { 713d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke ASSERT(source_->AtEOF()); 71444f0eee88ff00398ff7f715fab053374d808c90dSteve Block if (external_reference_decoder_) { 715e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke delete external_reference_decoder_; 716e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke external_reference_decoder_ = NULL; 717e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke } 718a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 719a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 720a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 721d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block// This is called on the roots. It is the driver of the deserialization 722d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block// process. It is also called on the body of each function. 723d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockvoid Deserializer::VisitPointers(Object** start, Object** end) { 724d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // The space must be new space. Any other space would cause ReadChunk to try 725d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // to update the remembered using NULL as the address. 726d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ReadChunk(start, end, NEW_SPACE, NULL); 727d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block} 728d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block 729d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block 730d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block// This routine writes the new object into the pointer provided and then 731d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block// returns true if the new object was in young space and false otherwise. 732d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block// The reason for this strange interface is that otherwise the object is 7333ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch// written very late, which means the FreeSpace map is not set up by the 7343ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch// time we need to use it to mark the space at the end of a page free. 735d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockvoid Deserializer::ReadObject(int space_number, 736d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Space* space, 737d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Object** write_back) { 738d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int size = source_->GetInt() << kObjectAlignmentBits; 739d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Address address = Allocate(space_number, space, size); 740d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block *write_back = HeapObject::FromAddress(address); 741d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Object** current = reinterpret_cast<Object**>(address); 742d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Object** limit = current + (size >> kPointerSizeLog2); 743e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke if (FLAG_log_snapshot_positions) { 74444f0eee88ff00398ff7f715fab053374d808c90dSteve Block LOG(isolate_, SnapshotPositionEvent(address, source_->position())); 745e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke } 746d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ReadChunk(current, limit, space_number, address); 74744f0eee88ff00398ff7f715fab053374d808c90dSteve Block#ifdef DEBUG 74844f0eee88ff00398ff7f715fab053374d808c90dSteve Block bool is_codespace = (space == HEAP->code_space()) || 74944f0eee88ff00398ff7f715fab053374d808c90dSteve Block ((space == HEAP->lo_space()) && (space_number == kLargeCode)); 75044f0eee88ff00398ff7f715fab053374d808c90dSteve Block ASSERT(HeapObject::FromAddress(address)->IsCode() == is_codespace); 75144f0eee88ff00398ff7f715fab053374d808c90dSteve Block#endif 752d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block} 753d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block 754d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block 755f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke// This macro is always used with a constant argument so it should all fold 756f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke// away to almost nothing in the generated code. It might be nicer to do this 757f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke// with the ternary operator but there are type issues with that. 758f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke#define ASSIGN_DEST_SPACE(space_number) \ 759f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke Space* dest_space; \ 760f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke if (space_number == NEW_SPACE) { \ 76144f0eee88ff00398ff7f715fab053374d808c90dSteve Block dest_space = isolate->heap()->new_space(); \ 762f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else if (space_number == OLD_POINTER_SPACE) { \ 76344f0eee88ff00398ff7f715fab053374d808c90dSteve Block dest_space = isolate->heap()->old_pointer_space(); \ 764f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else if (space_number == OLD_DATA_SPACE) { \ 76544f0eee88ff00398ff7f715fab053374d808c90dSteve Block dest_space = isolate->heap()->old_data_space(); \ 766f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else if (space_number == CODE_SPACE) { \ 76744f0eee88ff00398ff7f715fab053374d808c90dSteve Block dest_space = isolate->heap()->code_space(); \ 768f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else if (space_number == MAP_SPACE) { \ 76944f0eee88ff00398ff7f715fab053374d808c90dSteve Block dest_space = isolate->heap()->map_space(); \ 770f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else if (space_number == CELL_SPACE) { \ 77144f0eee88ff00398ff7f715fab053374d808c90dSteve Block dest_space = isolate->heap()->cell_space(); \ 772f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else { \ 773f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ASSERT(space_number >= LO_SPACE); \ 77444f0eee88ff00398ff7f715fab053374d808c90dSteve Block dest_space = isolate->heap()->lo_space(); \ 775f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } 776f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 777f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 778f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarkestatic const int kUnknownOffsetFromStart = -1; 779d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block 780d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block 781d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockvoid Deserializer::ReadChunk(Object** current, 782d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Object** limit, 783f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke int source_space, 7843ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Address current_object_address) { 78544f0eee88ff00398ff7f715fab053374d808c90dSteve Block Isolate* const isolate = isolate_; 7863ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch bool write_barrier_needed = (current_object_address != NULL && 7873ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch source_space != NEW_SPACE && 7883ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch source_space != CELL_SPACE && 7893ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch source_space != CODE_SPACE && 7903ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch source_space != OLD_DATA_SPACE); 791d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block while (current < limit) { 792d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int data = source_->Get(); 793d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block switch (data) { 794f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke#define CASE_STATEMENT(where, how, within, space_number) \ 795f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke case where + how + within + space_number: \ 796f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ASSERT((where & ~kPointedToMask) == 0); \ 797f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ASSERT((how & ~kHowToCodeMask) == 0); \ 798f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ASSERT((within & ~kWhereToPointMask) == 0); \ 799f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ASSERT((space_number & ~kSpaceMask) == 0); 800f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 801f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke#define CASE_BODY(where, how, within, space_number_if_any, offset_from_start) \ 802f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke { \ 803f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke bool emit_write_barrier = false; \ 804f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke bool current_was_incremented = false; \ 805f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke int space_number = space_number_if_any == kAnyOldSpace ? \ 806f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke (data & kSpaceMask) : space_number_if_any; \ 807f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke if (where == kNewObject && how == kPlain && within == kStartOfObject) {\ 808f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ASSIGN_DEST_SPACE(space_number) \ 809f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ReadObject(space_number, dest_space, current); \ 8103ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch emit_write_barrier = (space_number == NEW_SPACE); \ 811f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else { \ 812f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke Object* new_object = NULL; /* May not be a real Object pointer. */ \ 813f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke if (where == kNewObject) { \ 814f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ASSIGN_DEST_SPACE(space_number) \ 815f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ReadObject(space_number, dest_space, &new_object); \ 816f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else if (where == kRootArray) { \ 817f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke int root_id = source_->GetInt(); \ 8183ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch new_object = isolate->heap()->roots_array_start()[root_id]; \ 8193ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch emit_write_barrier = isolate->heap()->InNewSpace(new_object); \ 820f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else if (where == kPartialSnapshotCache) { \ 821f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke int cache_index = source_->GetInt(); \ 82244f0eee88ff00398ff7f715fab053374d808c90dSteve Block new_object = isolate->serialize_partial_snapshot_cache() \ 82344f0eee88ff00398ff7f715fab053374d808c90dSteve Block [cache_index]; \ 8243ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch emit_write_barrier = isolate->heap()->InNewSpace(new_object); \ 825f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else if (where == kExternalReference) { \ 826f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke int reference_id = source_->GetInt(); \ 82744f0eee88ff00398ff7f715fab053374d808c90dSteve Block Address address = external_reference_decoder_-> \ 82844f0eee88ff00398ff7f715fab053374d808c90dSteve Block Decode(reference_id); \ 829f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke new_object = reinterpret_cast<Object*>(address); \ 830f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else if (where == kBackref) { \ 8313ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch emit_write_barrier = (space_number == NEW_SPACE); \ 832f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke new_object = GetAddressFromEnd(data & kSpaceMask); \ 833f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else { \ 834f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ASSERT(where == kFromStart); \ 835f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke if (offset_from_start == kUnknownOffsetFromStart) { \ 8363ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch emit_write_barrier = (space_number == NEW_SPACE); \ 837f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke new_object = GetAddressFromStart(data & kSpaceMask); \ 838f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else { \ 839f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke Address object_address = pages_[space_number][0] + \ 840f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke (offset_from_start << kObjectAlignmentBits); \ 841f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke new_object = HeapObject::FromAddress(object_address); \ 842f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } \ 843f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } \ 844f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke if (within == kFirstInstruction) { \ 845f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke Code* new_code_object = reinterpret_cast<Code*>(new_object); \ 846f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke new_object = reinterpret_cast<Object*>( \ 847f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke new_code_object->instruction_start()); \ 848f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } \ 849f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke if (how == kFromCode) { \ 850f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke Address location_of_branch_data = \ 851f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke reinterpret_cast<Address>(current); \ 8523ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Assembler::deserialization_set_special_target_at( \ 8533ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch location_of_branch_data, \ 8543ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch reinterpret_cast<Address>(new_object)); \ 8553ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch location_of_branch_data += Assembler::kSpecialTargetSize; \ 8563ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch current = reinterpret_cast<Object**>(location_of_branch_data); \ 8573ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch current_was_incremented = true; \ 858f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else { \ 859f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke *current = new_object; \ 860f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } \ 861f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } \ 8623ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (emit_write_barrier && write_barrier_needed) { \ 8633ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Address current_address = reinterpret_cast<Address>(current); \ 8643ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch isolate->heap()->RecordWrite( \ 8653ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch current_object_address, \ 8663ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch static_cast<int>(current_address - current_object_address)); \ 867f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } \ 868f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke if (!current_was_incremented) { \ 8693ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch current++; \ 870f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } \ 871f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke break; \ 872f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } \ 873f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 874f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke// This generates a case and a body for each space. The large object spaces are 875f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke// very rare in snapshots so they are grouped in one body. 876f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke#define ONE_PER_SPACE(where, how, within) \ 877f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, NEW_SPACE) \ 878f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(where, how, within, NEW_SPACE, kUnknownOffsetFromStart) \ 879f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, OLD_DATA_SPACE) \ 880f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(where, how, within, OLD_DATA_SPACE, kUnknownOffsetFromStart) \ 881f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, OLD_POINTER_SPACE) \ 882f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(where, how, within, OLD_POINTER_SPACE, kUnknownOffsetFromStart) \ 883f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, CODE_SPACE) \ 884f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(where, how, within, CODE_SPACE, kUnknownOffsetFromStart) \ 885f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, CELL_SPACE) \ 886f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(where, how, within, CELL_SPACE, kUnknownOffsetFromStart) \ 887f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, MAP_SPACE) \ 888f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(where, how, within, MAP_SPACE, kUnknownOffsetFromStart) \ 889f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, kLargeData) \ 890f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, kLargeCode) \ 891f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, kLargeFixedArray) \ 892f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(where, how, within, kAnyOldSpace, kUnknownOffsetFromStart) 893f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 894f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke// This generates a case and a body for the new space (which has to do extra 895f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke// write barrier handling) and handles the other spaces with 8 fall-through 896f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke// cases and one body. 897f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke#define ALL_SPACES(where, how, within) \ 898f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, NEW_SPACE) \ 899f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(where, how, within, NEW_SPACE, kUnknownOffsetFromStart) \ 900f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, OLD_DATA_SPACE) \ 901f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, OLD_POINTER_SPACE) \ 902f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, CODE_SPACE) \ 903f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, CELL_SPACE) \ 904f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, MAP_SPACE) \ 905f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, kLargeData) \ 906f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, kLargeCode) \ 907f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(where, how, within, kLargeFixedArray) \ 908f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(where, how, within, kAnyOldSpace, kUnknownOffsetFromStart) 909f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 910791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block#define ONE_PER_CODE_SPACE(where, how, within) \ 911791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block CASE_STATEMENT(where, how, within, CODE_SPACE) \ 912791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block CASE_BODY(where, how, within, CODE_SPACE, kUnknownOffsetFromStart) \ 913791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block CASE_STATEMENT(where, how, within, kLargeCode) \ 91444f0eee88ff00398ff7f715fab053374d808c90dSteve Block CASE_BODY(where, how, within, kLargeCode, kUnknownOffsetFromStart) 915791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block 9163ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch#define FOUR_CASES(byte_code) \ 9173ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch case byte_code: \ 9183ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch case byte_code + 1: \ 9193ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch case byte_code + 2: \ 9203ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch case byte_code + 3: 9213ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 9223ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch#define SIXTEEN_CASES(byte_code) \ 9233ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch FOUR_CASES(byte_code) \ 9243ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch FOUR_CASES(byte_code + 4) \ 9253ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch FOUR_CASES(byte_code + 8) \ 9263ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch FOUR_CASES(byte_code + 12) 927f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 928f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // We generate 15 cases and bodies that process special tags that combine 929f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // the raw data tag and the length into one byte. 930d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block#define RAW_CASE(index, size) \ 931f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke case kRawData + index: { \ 932d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block byte* raw_data_out = reinterpret_cast<byte*>(current); \ 933d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block source_->CopyRaw(raw_data_out, size); \ 934d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block current = reinterpret_cast<Object**>(raw_data_out + size); \ 935d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block break; \ 936d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 937d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block COMMON_RAW_LENGTHS(RAW_CASE) 938d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block#undef RAW_CASE 939f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 940f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // Deserialize a chunk of raw data that doesn't have one of the popular 941f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // lengths. 942f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke case kRawData: { 943d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int size = source_->GetInt(); 944d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block byte* raw_data_out = reinterpret_cast<byte*>(current); 945d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block source_->CopyRaw(raw_data_out, size); 946d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block current = reinterpret_cast<Object**>(raw_data_out + size); 947d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block break; 948d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 949f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 9503ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch SIXTEEN_CASES(kRootArrayLowConstants) 9513ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch SIXTEEN_CASES(kRootArrayHighConstants) { 9523ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch int root_id = RootArrayConstantFromByteCode(data); 9533ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Object* object = isolate->heap()->roots_array_start()[root_id]; 9543ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch ASSERT(!isolate->heap()->InNewSpace(object)); 9553ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch *current++ = object; 9563ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch break; 9573ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 9583ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 9593ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch case kRepeat: { 9603ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch int repeats = source_->GetInt(); 9613ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Object* object = current[-1]; 9623ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch ASSERT(!isolate->heap()->InNewSpace(object)); 9633ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch for (int i = 0; i < repeats; i++) current[i] = object; 9643ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch current += repeats; 9653ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch break; 9663ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 9673ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 9683ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch STATIC_ASSERT(kRootArrayNumberOfConstantEncodings == 9693ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Heap::kOldSpaceRoots); 9703ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch STATIC_ASSERT(kMaxRepeats == 12); 9713ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch FOUR_CASES(kConstantRepeat) 9723ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch FOUR_CASES(kConstantRepeat + 4) 9733ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch FOUR_CASES(kConstantRepeat + 8) { 9743ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch int repeats = RepeatsForCode(data); 9753ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Object* object = current[-1]; 9763ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch ASSERT(!isolate->heap()->InNewSpace(object)); 9773ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch for (int i = 0; i < repeats; i++) current[i] = object; 9783ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch current += repeats; 9793ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch break; 9803ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 9813ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 982f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // Deserialize a new object and write a pointer to it to the current 983f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // object. 984f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ONE_PER_SPACE(kNewObject, kPlain, kStartOfObject) 985791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block // Support for direct instruction pointers in functions 986791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block ONE_PER_CODE_SPACE(kNewObject, kPlain, kFirstInstruction) 987f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // Deserialize a new code object and write a pointer to its first 988f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // instruction to the current code object. 989f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ONE_PER_SPACE(kNewObject, kFromCode, kFirstInstruction) 990f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // Find a recently deserialized object using its offset from the current 991f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // allocation point and write a pointer to it to the current object. 992f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ALL_SPACES(kBackref, kPlain, kStartOfObject) 9933ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch#if V8_TARGET_ARCH_MIPS 9943ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // Deserialize a new object from pointer found in code and write 9953ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // a pointer to it to the current object. Required only for MIPS, and 9963ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // omitted on the other architectures because it is fully unrolled and 9973ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // would cause bloat. 9983ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch ONE_PER_SPACE(kNewObject, kFromCode, kStartOfObject) 9993ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // Find a recently deserialized code object using its offset from the 10003ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // current allocation point and write a pointer to it to the current 10013ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // object. Required only for MIPS. 10023ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch ALL_SPACES(kBackref, kFromCode, kStartOfObject) 10033ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // Find an already deserialized code object using its offset from 10043ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // the start and write a pointer to it to the current object. 10053ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // Required only for MIPS. 10063ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch ALL_SPACES(kFromStart, kFromCode, kStartOfObject) 10073ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch#endif 1008f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // Find a recently deserialized code object using its offset from the 1009f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // current allocation point and write a pointer to its first instruction 1010791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block // to the current code object or the instruction pointer in a function 1011791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block // object. 1012f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ALL_SPACES(kBackref, kFromCode, kFirstInstruction) 1013791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block ALL_SPACES(kBackref, kPlain, kFirstInstruction) 1014f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // Find an already deserialized object using its offset from the start 1015f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // and write a pointer to it to the current object. 1016f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ALL_SPACES(kFromStart, kPlain, kStartOfObject) 1017791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block ALL_SPACES(kFromStart, kPlain, kFirstInstruction) 1018f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // Find an already deserialized code object using its offset from the 1019f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // start and write a pointer to its first instruction to the current code 1020f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // object. 1021f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke ALL_SPACES(kFromStart, kFromCode, kFirstInstruction) 1022f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // Find an object in the roots array and write a pointer to it to the 1023f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // current object. 1024f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(kRootArray, kPlain, kStartOfObject, 0) 1025f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(kRootArray, kPlain, kStartOfObject, 0, kUnknownOffsetFromStart) 1026f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // Find an object in the partial snapshots cache and write a pointer to it 1027f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // to the current object. 1028f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(kPartialSnapshotCache, kPlain, kStartOfObject, 0) 1029f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(kPartialSnapshotCache, 1030f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke kPlain, 1031f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke kStartOfObject, 1032f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 0, 1033f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke kUnknownOffsetFromStart) 1034791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block // Find an code entry in the partial snapshots cache and 1035791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block // write a pointer to it to the current object. 1036791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block CASE_STATEMENT(kPartialSnapshotCache, kPlain, kFirstInstruction, 0) 1037791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block CASE_BODY(kPartialSnapshotCache, 1038791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block kPlain, 1039791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block kFirstInstruction, 1040791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block 0, 1041791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block kUnknownOffsetFromStart) 1042f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // Find an external reference and write a pointer to it to the current 1043f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // object. 1044f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(kExternalReference, kPlain, kStartOfObject, 0) 1045f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(kExternalReference, 1046f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke kPlain, 1047f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke kStartOfObject, 1048f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 0, 1049f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke kUnknownOffsetFromStart) 1050f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // Find an external reference and write a pointer to it in the current 1051f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // code object. 1052f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_STATEMENT(kExternalReference, kFromCode, kStartOfObject, 0) 1053f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke CASE_BODY(kExternalReference, 1054f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke kFromCode, 1055f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke kStartOfObject, 1056f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 0, 1057f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke kUnknownOffsetFromStart) 1058f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 1059f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke#undef CASE_STATEMENT 1060f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke#undef CASE_BODY 1061f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke#undef ONE_PER_SPACE 1062f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke#undef ALL_SPACES 1063f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke#undef ASSIGN_DEST_SPACE 1064f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 1065f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke case kNewPage: { 1066d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int space = source_->Get(); 1067d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block pages_[space].Add(last_object_address_); 10686ded16be15dd865a9b21ea304d5273c8be299c87Steve Block if (space == CODE_SPACE) { 10696ded16be15dd865a9b21ea304d5273c8be299c87Steve Block CPU::FlushICache(last_object_address_, Page::kPageSize); 10706ded16be15dd865a9b21ea304d5273c8be299c87Steve Block } 1071d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block break; 1072d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1073f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 10743ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch case kSkip: { 10753ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch current++; 10763ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch break; 10773ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 10783ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 1079f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke case kNativesStringResource: { 1080d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int index = source_->Get(); 10813fb3ca8c7ca439d408449a395897395c0faae8d1Ben Murdoch Vector<const char> source_vector = Natives::GetRawScriptSource(index); 1082d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block NativesExternalStringResource* resource = 10833fb3ca8c7ca439d408449a395897395c0faae8d1Ben Murdoch new NativesExternalStringResource(isolate->bootstrapper(), 10843fb3ca8c7ca439d408449a395897395c0faae8d1Ben Murdoch source_vector.start(), 10853fb3ca8c7ca439d408449a395897395c0faae8d1Ben Murdoch source_vector.length()); 1086d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block *current++ = reinterpret_cast<Object*>(resource); 1087d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block break; 1088d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1089f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 1090f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke case kSynchronize: { 1091d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // If we get here then that indicates that you have a mismatch between 1092d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // the number of GC roots when serializing and deserializing. 1093d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke UNREACHABLE(); 1094d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke } 1095f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke 1096d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block default: 1097d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block UNREACHABLE(); 1098d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1099a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1100d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ASSERT_EQ(current, limit); 1101a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1102a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1103a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1104d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockvoid SnapshotByteSink::PutInt(uintptr_t integer, const char* description) { 1105d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block const int max_shift = ((kPointerSize * kBitsPerByte) / 7) * 7; 1106d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block for (int shift = max_shift; shift > 0; shift -= 7) { 1107d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (integer >= static_cast<uintptr_t>(1u) << shift) { 1108402d937239b0e2fd11bf2f4fe972ad78aa9fd481Andrei Popescu Put((static_cast<int>((integer >> shift)) & 0x7f) | 0x80, "IntPart"); 1109d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1110a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1111402d937239b0e2fd11bf2f4fe972ad78aa9fd481Andrei Popescu PutSection(static_cast<int>(integer & 0x7f), "IntLastPart"); 1112a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1113a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1114a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1115d0582a6c46733687d045e4188a1bcd0123c758a1Steve BlockSerializer::Serializer(SnapshotByteSink* sink) 1116d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block : sink_(sink), 1117d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block current_root_index_(0), 11183100271588b61cbc1dc472a3f2f105d2eed8497fAndrei Popescu external_reference_encoder_(new ExternalReferenceEncoder), 11193ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch large_object_total_(0), 11203ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch root_index_wave_front_(0) { 11213ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch isolate_ = Isolate::Current(); 112244f0eee88ff00398ff7f715fab053374d808c90dSteve Block // The serializer is meant to be used only to generate initial heap images 112344f0eee88ff00398ff7f715fab053374d808c90dSteve Block // from a context in which there is only one isolate. 11243ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch ASSERT(isolate_->IsDefaultIsolate()); 1125d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block for (int i = 0; i <= LAST_SPACE; i++) { 1126d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block fullness_[i] = 0; 1127d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1128a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1129a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1130a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 11313100271588b61cbc1dc472a3f2f105d2eed8497fAndrei PopescuSerializer::~Serializer() { 11323100271588b61cbc1dc472a3f2f105d2eed8497fAndrei Popescu delete external_reference_encoder_; 11333100271588b61cbc1dc472a3f2f105d2eed8497fAndrei Popescu} 11343100271588b61cbc1dc472a3f2f105d2eed8497fAndrei Popescu 11353100271588b61cbc1dc472a3f2f105d2eed8497fAndrei Popescu 1136d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarkevoid StartupSerializer::SerializeStrongReferences() { 113744f0eee88ff00398ff7f715fab053374d808c90dSteve Block Isolate* isolate = Isolate::Current(); 1138a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // No active threads. 113944f0eee88ff00398ff7f715fab053374d808c90dSteve Block CHECK_EQ(NULL, Isolate::Current()->thread_manager()->FirstThreadStateInUse()); 1140a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block // No active or weak handles. 114144f0eee88ff00398ff7f715fab053374d808c90dSteve Block CHECK(isolate->handle_scope_implementer()->blocks()->is_empty()); 114244f0eee88ff00398ff7f715fab053374d808c90dSteve Block CHECK_EQ(0, isolate->global_handles()->NumberOfWeakHandles()); 1143d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // We don't support serializing installed extensions. 11443ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch CHECK(!isolate->has_installed_extensions()); 11453ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 114644f0eee88ff00398ff7f715fab053374d808c90dSteve Block HEAP->IterateStrongRoots(this, VISIT_ONLY_STRONG); 1147a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1148a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1149a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1150d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarkevoid PartialSerializer::Serialize(Object** object) { 1151e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke this->VisitPointer(object); 115244f0eee88ff00398ff7f715fab053374d808c90dSteve Block Isolate* isolate = Isolate::Current(); 1153d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1154d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // After we have done the partial serialization the partial snapshot cache 1155d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // will contain some references needed to decode the partial snapshot. We 1156d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // fill it up with undefineds so it has a predictable length so the 1157d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // deserialization code doesn't need to know the length. 115844f0eee88ff00398ff7f715fab053374d808c90dSteve Block for (int index = isolate->serialize_partial_snapshot_cache_length(); 115944f0eee88ff00398ff7f715fab053374d808c90dSteve Block index < Isolate::kPartialSnapshotCacheCapacity; 1160d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke index++) { 116144f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate->serialize_partial_snapshot_cache()[index] = 116244f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate->heap()->undefined_value(); 116344f0eee88ff00398ff7f715fab053374d808c90dSteve Block startup_serializer_->VisitPointer( 116444f0eee88ff00398ff7f715fab053374d808c90dSteve Block &isolate->serialize_partial_snapshot_cache()[index]); 1165d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke } 116644f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate->set_serialize_partial_snapshot_cache_length( 116744f0eee88ff00398ff7f715fab053374d808c90dSteve Block Isolate::kPartialSnapshotCacheCapacity); 1168e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke} 1169e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke 1170e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke 1171a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Blockvoid Serializer::VisitPointers(Object** start, Object** end) { 11723ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Isolate* isolate = Isolate::Current(); 11733ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 1174d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block for (Object** current = start; current < end; current++) { 11753ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (start == isolate->heap()->roots_array_start()) { 11763ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch root_index_wave_front_ = 11773ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Max(root_index_wave_front_, static_cast<intptr_t>(current - start)); 11783ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 11793ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (reinterpret_cast<Address>(current) == 11803ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch isolate->heap()->store_buffer()->TopAddress()) { 11813ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch sink_->Put(kSkip, "Skip"); 11823ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } else if ((*current)->IsSmi()) { 1183f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke sink_->Put(kRawData, "RawData"); 1184d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block sink_->PutInt(kPointerSize, "length"); 1185d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block for (int i = 0; i < kPointerSize; i++) { 1186d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block sink_->Put(reinterpret_cast<byte*>(current)[i], "Byte"); 1187d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1188d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } else { 1189f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke SerializeObject(*current, kPlain, kStartOfObject); 1190a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1191a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1192a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1193a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1194a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1195d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// This ensures that the partial snapshot cache keeps things alive during GC and 1196d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// tracks their movement. When it is called during serialization of the startup 1197d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// snapshot the partial snapshot is empty, so nothing happens. When the partial 1198d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// (context) snapshot is created, this array is populated with the pointers that 1199d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// the partial snapshot will need. As that happens we emit serialized objects to 1200d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// the startup snapshot that correspond to the elements of this cache array. On 1201d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// deserialization we therefore need to visit the cache array. This fills it up 1202d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// with pointers to deserialized objects. 12036ded16be15dd865a9b21ea304d5273c8be299c87Steve Blockvoid SerializerDeserializer::Iterate(ObjectVisitor* visitor) { 120444f0eee88ff00398ff7f715fab053374d808c90dSteve Block Isolate* isolate = Isolate::Current(); 1205d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke visitor->VisitPointers( 120644f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate->serialize_partial_snapshot_cache(), 120744f0eee88ff00398ff7f715fab053374d808c90dSteve Block &isolate->serialize_partial_snapshot_cache()[ 120844f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate->serialize_partial_snapshot_cache_length()]); 1209d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke} 1210d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1211d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1212d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// When deserializing we need to set the size of the snapshot cache. This means 1213d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// the root iteration code (above) will iterate over array elements, writing the 1214d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// references to deserialized objects in them. 1215d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarkevoid SerializerDeserializer::SetSnapshotCacheSize(int size) { 121644f0eee88ff00398ff7f715fab053374d808c90dSteve Block Isolate::Current()->set_serialize_partial_snapshot_cache_length(size); 1217d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke} 1218d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1219d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1220d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarkeint PartialSerializer::PartialSnapshotCacheIndex(HeapObject* heap_object) { 122144f0eee88ff00398ff7f715fab053374d808c90dSteve Block Isolate* isolate = Isolate::Current(); 122244f0eee88ff00398ff7f715fab053374d808c90dSteve Block 122344f0eee88ff00398ff7f715fab053374d808c90dSteve Block for (int i = 0; 122444f0eee88ff00398ff7f715fab053374d808c90dSteve Block i < isolate->serialize_partial_snapshot_cache_length(); 122544f0eee88ff00398ff7f715fab053374d808c90dSteve Block i++) { 122644f0eee88ff00398ff7f715fab053374d808c90dSteve Block Object* entry = isolate->serialize_partial_snapshot_cache()[i]; 1227d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke if (entry == heap_object) return i; 1228d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke } 12293100271588b61cbc1dc472a3f2f105d2eed8497fAndrei Popescu 1230d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // We didn't find the object in the cache. So we add it to the cache and 1231d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // then visit the pointer so that it becomes part of the startup snapshot 1232d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // and we can refer to it from the partial snapshot. 123344f0eee88ff00398ff7f715fab053374d808c90dSteve Block int length = isolate->serialize_partial_snapshot_cache_length(); 123444f0eee88ff00398ff7f715fab053374d808c90dSteve Block CHECK(length < Isolate::kPartialSnapshotCacheCapacity); 123544f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate->serialize_partial_snapshot_cache()[length] = heap_object; 123644f0eee88ff00398ff7f715fab053374d808c90dSteve Block startup_serializer_->VisitPointer( 123744f0eee88ff00398ff7f715fab053374d808c90dSteve Block &isolate->serialize_partial_snapshot_cache()[length]); 1238d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // We don't recurse from the startup snapshot generator into the partial 1239d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // snapshot generator. 124044f0eee88ff00398ff7f715fab053374d808c90dSteve Block ASSERT(length == isolate->serialize_partial_snapshot_cache_length()); 124144f0eee88ff00398ff7f715fab053374d808c90dSteve Block isolate->set_serialize_partial_snapshot_cache_length(length + 1); 124244f0eee88ff00398ff7f715fab053374d808c90dSteve Block return length; 1243d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke} 1244d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1245d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 12463ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdochint Serializer::RootIndex(HeapObject* heap_object, HowToCode from) { 12473ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Heap* heap = HEAP; 12483ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (heap->InNewSpace(heap_object)) return kInvalidRootIndex; 12493ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch for (int i = 0; i < root_index_wave_front_; i++) { 12503ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Object* root = heap->roots_array_start()[i]; 12513ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (!root->IsSmi() && root == heap_object) { 12523ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch#if V8_TARGET_ARCH_MIPS 12533ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (from == kFromCode) { 12543ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // In order to avoid code bloat in the deserializer we don't have 12553ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // support for the encoding that specifies a particular root should 12563ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // be written into the lui/ori instructions on MIPS. Therefore we 12573ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // should not generate such serialization data for MIPS. 12583ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch return kInvalidRootIndex; 12593ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 12603ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch#endif 12613ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch return i; 12623ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 1263e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke } 1264e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke return kInvalidRootIndex; 1265e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke} 1266e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke 1267e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke 1268d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// Encode the location of an already deserialized object in order to write its 1269d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// location into a later object. We can encode the location as an offset from 1270d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// the start of the deserialized objects or as an offset backwards from the 1271d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke// current allocation pointer. 1272d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarkevoid Serializer::SerializeReferenceToPreviousObject( 1273d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke int space, 1274d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke int address, 1275f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke HowToCode how_to_code, 1276f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke WhereToPoint where_to_point) { 1277d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke int offset = CurrentAllocationAddress(space) - address; 1278d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke bool from_start = true; 1279d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke if (SpaceIsPaged(space)) { 1280d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // For paged space it is simple to encode back from current allocation if 1281d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // the object is on the same page as the current allocation pointer. 1282d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke if ((CurrentAllocationAddress(space) >> kPageSizeBits) == 1283d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke (address >> kPageSizeBits)) { 1284d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke from_start = false; 1285d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke address = offset; 1286a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1287d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke } else if (space == NEW_SPACE) { 1288d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // For new space it is always simple to encode back from current allocation. 1289d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke if (offset < address) { 1290d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke from_start = false; 1291d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke address = offset; 1292888f6729be6a6f6fbe246cb5a9f122e2dbe455b7Leon Clarke } 1293d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke } 1294d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // If we are actually dealing with real offsets (and not a numbering of 1295d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // all objects) then we should shift out the bits that are always 0. 1296d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke if (!SpaceIsLarge(space)) address >>= kObjectAlignmentBits; 1297f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke if (from_start) { 12983ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch sink_->Put(kFromStart + how_to_code + where_to_point + space, "RefSer"); 12993ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch sink_->PutInt(address, "address"); 1300f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else { 1301f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke sink_->Put(kBackref + how_to_code + where_to_point + space, "BackRefSer"); 1302f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke sink_->PutInt(address, "address"); 1303d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke } 1304d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke} 1305d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1306d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1307d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarkevoid StartupSerializer::SerializeObject( 1308d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke Object* o, 1309f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke HowToCode how_to_code, 1310f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke WhereToPoint where_to_point) { 1311d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke CHECK(o->IsHeapObject()); 1312d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke HeapObject* heap_object = HeapObject::cast(o); 1313d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 13143ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch int root_index; 13153ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if ((root_index = RootIndex(heap_object, how_to_code)) != kInvalidRootIndex) { 13163ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch PutRoot(root_index, heap_object, how_to_code, where_to_point); 13173ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch return; 13183ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 13193ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 1320d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke if (address_mapper_.IsMapped(heap_object)) { 1321d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke int space = SpaceOfAlreadySerializedObject(heap_object); 1322d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke int address = address_mapper_.MappedTo(heap_object); 1323d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke SerializeReferenceToPreviousObject(space, 1324d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke address, 1325f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke how_to_code, 1326f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke where_to_point); 1327d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke } else { 1328d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // Object has not yet been serialized. Serialize it here. 1329d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke ObjectSerializer object_serializer(this, 1330d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke heap_object, 1331d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke sink_, 1332f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke how_to_code, 1333f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke where_to_point); 1334d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke object_serializer.Serialize(); 1335d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke } 1336d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke} 1337d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1338d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1339d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarkevoid StartupSerializer::SerializeWeakReferences() { 134044f0eee88ff00398ff7f715fab053374d808c90dSteve Block for (int i = Isolate::Current()->serialize_partial_snapshot_cache_length(); 134144f0eee88ff00398ff7f715fab053374d808c90dSteve Block i < Isolate::kPartialSnapshotCacheCapacity; 1342d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke i++) { 1343f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke sink_->Put(kRootArray + kPlain + kStartOfObject, "RootSerialization"); 1344d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke sink_->PutInt(Heap::kUndefinedValueRootIndex, "root_index"); 1345d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke } 134644f0eee88ff00398ff7f715fab053374d808c90dSteve Block HEAP->IterateWeakRoots(this, VISIT_ALL); 1347d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke} 1348d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1349d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 13503ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdochvoid Serializer::PutRoot(int root_index, 13513ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch HeapObject* object, 13523ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch SerializerDeserializer::HowToCode how_to_code, 13533ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch SerializerDeserializer::WhereToPoint where_to_point) { 13543ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (how_to_code == kPlain && 13553ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch where_to_point == kStartOfObject && 13563ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch root_index < kRootArrayNumberOfConstantEncodings && 13573ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch !HEAP->InNewSpace(object)) { 13583ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (root_index < kRootArrayNumberOfLowConstantEncodings) { 13593ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch sink_->Put(kRootArrayLowConstants + root_index, "RootLoConstant"); 13603ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } else { 13613ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch sink_->Put(kRootArrayHighConstants + root_index - 13623ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch kRootArrayNumberOfLowConstantEncodings, 13633ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch "RootHiConstant"); 13643ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 13653ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } else { 13663ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch sink_->Put(kRootArray + how_to_code + where_to_point, "RootSerialization"); 13673ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch sink_->PutInt(root_index, "root_index"); 13683ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 13693ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch} 13703ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 13713ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 1372d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarkevoid PartialSerializer::SerializeObject( 1373d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke Object* o, 1374f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke HowToCode how_to_code, 1375f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke WhereToPoint where_to_point) { 1376d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke CHECK(o->IsHeapObject()); 1377d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke HeapObject* heap_object = HeapObject::cast(o); 1378d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 13793ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (heap_object->IsMap()) { 13803ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // The code-caches link to context-specific code objects, which 13813ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // the startup and context serializes cannot currently handle. 13823ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch ASSERT(Map::cast(heap_object)->code_cache() == 13833ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch heap_object->GetHeap()->raw_unchecked_empty_fixed_array()); 13843ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 13853ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 1386d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke int root_index; 13873ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if ((root_index = RootIndex(heap_object, how_to_code)) != kInvalidRootIndex) { 13883ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch PutRoot(root_index, heap_object, how_to_code, where_to_point); 1389d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke return; 1390d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke } 1391d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1392d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke if (ShouldBeInThePartialSnapshotCache(heap_object)) { 1393d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke int cache_index = PartialSnapshotCacheIndex(heap_object); 1394f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke sink_->Put(kPartialSnapshotCache + how_to_code + where_to_point, 1395f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke "PartialSnapshotCache"); 1396d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke sink_->PutInt(cache_index, "partial_snapshot_cache_index"); 1397d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke return; 1398d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke } 1399d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1400d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // Pointers from the partial snapshot to the objects in the startup snapshot 1401d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // should go through the root array or through the partial snapshot cache. 1402d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // If this is not the case you may have to add something to the root array. 1403d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke ASSERT(!startup_serializer_->address_mapper()->IsMapped(heap_object)); 1404d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // All the symbols that the partial snapshot needs should be either in the 1405d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke // root table or in the partial snapshot cache. 1406d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke ASSERT(!heap_object->IsSymbol()); 1407d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke 1408d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke if (address_mapper_.IsMapped(heap_object)) { 1409d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke int space = SpaceOfAlreadySerializedObject(heap_object); 1410d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke int address = address_mapper_.MappedTo(heap_object); 1411d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke SerializeReferenceToPreviousObject(space, 1412d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke address, 1413f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke how_to_code, 1414f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke where_to_point); 1415d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } else { 1416d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // Object has not yet been serialized. Serialize it here. 1417d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ObjectSerializer serializer(this, 1418d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block heap_object, 1419d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block sink_, 1420f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke how_to_code, 1421f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke where_to_point); 1422d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block serializer.Serialize(); 1423a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1424a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1425a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1426a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1427d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockvoid Serializer::ObjectSerializer::Serialize() { 1428d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int space = Serializer::SpaceOfObject(object_); 1429d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int size = object_->Size(); 1430a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1431f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke sink_->Put(kNewObject + reference_representation_ + space, 1432f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke "ObjectSerialization"); 1433d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block sink_->PutInt(size >> kObjectAlignmentBits, "Size in words"); 1434a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 143544f0eee88ff00398ff7f715fab053374d808c90dSteve Block LOG(i::Isolate::Current(), 143644f0eee88ff00398ff7f715fab053374d808c90dSteve Block SnapshotPositionEvent(object_->address(), sink_->Position())); 1437e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke 1438d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // Mark this object as already serialized. 1439d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block bool start_new_page; 1440d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke int offset = serializer_->Allocate(space, size, &start_new_page); 1441d91b9f7d46489a9ee00f9cb415630299c76a502bLeon Clarke serializer_->address_mapper()->AddMapping(object_, offset); 1442d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (start_new_page) { 1443f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke sink_->Put(kNewPage, "NewPage"); 1444d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block sink_->PutSection(space, "NewPageSpace"); 1445a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1446a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1447d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // Serialize the map (first word of the object). 1448f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke serializer_->SerializeObject(object_->map(), kPlain, kStartOfObject); 1449a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1450d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // Serialize the rest of the object. 1451d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block CHECK_EQ(0, bytes_processed_so_far_); 1452d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block bytes_processed_so_far_ = kPointerSize; 1453d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block object_->IterateBody(object_->map()->instance_type(), size, this); 1454d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block OutputRawData(object_->address() + size); 1455a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1456a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1457a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1458d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockvoid Serializer::ObjectSerializer::VisitPointers(Object** start, 1459d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Object** end) { 1460d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Object** current = start; 1461d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block while (current < end) { 1462d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block while (current < end && (*current)->IsSmi()) current++; 1463d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (current < end) OutputRawData(reinterpret_cast<Address>(current)); 1464a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1465d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block while (current < end && !(*current)->IsSmi()) { 14663ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch HeapObject* current_contents = HeapObject::cast(*current); 14673ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch int root_index = serializer_->RootIndex(current_contents, kPlain); 14683ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // Repeats are not subject to the write barrier so there are only some 14693ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // objects that can be used in a repeat encoding. These are the early 14703ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch // ones in the root array that are never in new space. 14713ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (current != start && 14723ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch root_index != kInvalidRootIndex && 14733ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch root_index < kRootArrayNumberOfConstantEncodings && 14743ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch current_contents == current[-1]) { 14753ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch ASSERT(!HEAP->InNewSpace(current_contents)); 14763ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch int repeat_count = 1; 14773ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch while (current < end - 1 && current[repeat_count] == current_contents) { 14783ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch repeat_count++; 14793ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 14803ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch current += repeat_count; 14813ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch bytes_processed_so_far_ += repeat_count * kPointerSize; 14823ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (repeat_count > kMaxRepeats) { 14833ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch sink_->Put(kRepeat, "SerializeRepeats"); 14843ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch sink_->PutInt(repeat_count, "SerializeRepeats"); 14853ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } else { 14863ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch sink_->Put(CodeForRepeats(repeat_count), "SerializeRepeats"); 14873ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 14883ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } else { 14893ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch serializer_->SerializeObject(current_contents, kPlain, kStartOfObject); 14903ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch bytes_processed_so_far_ += kPointerSize; 14913ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch current++; 14923ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 1493a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1494a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1495a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1496a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1497a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 14983ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdochvoid Serializer::ObjectSerializer::VisitEmbeddedPointer(RelocInfo* rinfo) { 14993ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Object** current = rinfo->target_object_address(); 15003ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 15013ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch OutputRawData(rinfo->target_address_address()); 15023ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch HowToCode representation = rinfo->IsCodedSpecially() ? kFromCode : kPlain; 15033ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch serializer_->SerializeObject(*current, representation, kStartOfObject); 15043ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch bytes_processed_so_far_ += rinfo->target_address_size(); 15053ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch} 15063ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 15073ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 1508d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockvoid Serializer::ObjectSerializer::VisitExternalReferences(Address* start, 1509d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Address* end) { 1510d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Address references_start = reinterpret_cast<Address>(start); 1511d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block OutputRawData(references_start); 1512a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1513d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block for (Address* current = start; current < end; current++) { 1514f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke sink_->Put(kExternalReference + kPlain + kStartOfObject, "ExternalRef"); 1515d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int reference_id = serializer_->EncodeExternalReference(*current); 1516d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block sink_->PutInt(reference_id, "reference id"); 1517a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1518d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block bytes_processed_so_far_ += static_cast<int>((end - start) * kPointerSize); 1519a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1520a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1521a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 15223ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdochvoid Serializer::ObjectSerializer::VisitExternalReference(RelocInfo* rinfo) { 15233ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Address references_start = rinfo->target_address_address(); 15243ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch OutputRawData(references_start); 15253ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 15263ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch Address* current = rinfo->target_reference_address(); 15273ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch int representation = rinfo->IsCodedSpecially() ? 15283ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch kFromCode + kStartOfObject : kPlain + kStartOfObject; 15293ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch sink_->Put(kExternalReference + representation, "ExternalRef"); 15303ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch int reference_id = serializer_->EncodeExternalReference(*current); 15313ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch sink_->PutInt(reference_id, "reference id"); 15323ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch bytes_processed_so_far_ += rinfo->target_address_size(); 15333ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch} 15343ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 15353ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 1536d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockvoid Serializer::ObjectSerializer::VisitRuntimeEntry(RelocInfo* rinfo) { 1537d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Address target_start = rinfo->target_address_address(); 1538d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block OutputRawData(target_start); 1539d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Address target = rinfo->target_address(); 1540d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block uint32_t encoding = serializer_->EncodeExternalReference(target); 1541d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block CHECK(target == NULL ? encoding == 0 : encoding != 0); 1542f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke int representation; 1543f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke // Can't use a ternary operator because of gcc. 1544f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke if (rinfo->IsCodedSpecially()) { 1545f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke representation = kStartOfObject + kFromCode; 1546f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } else { 1547f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke representation = kStartOfObject + kPlain; 1548f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke } 1549f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke sink_->Put(kExternalReference + representation, "ExternalReference"); 1550d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block sink_->PutInt(encoding, "reference id"); 1551f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke bytes_processed_so_far_ += rinfo->target_address_size(); 1552a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1553a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1554a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1555d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockvoid Serializer::ObjectSerializer::VisitCodeTarget(RelocInfo* rinfo) { 1556d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block CHECK(RelocInfo::IsCodeTarget(rinfo->rmode())); 1557d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Address target_start = rinfo->target_address_address(); 1558d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block OutputRawData(target_start); 1559d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Code* target = Code::GetCodeFromTargetAddress(rinfo->target_address()); 1560f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke serializer_->SerializeObject(target, kFromCode, kFirstInstruction); 1561f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke bytes_processed_so_far_ += rinfo->target_address_size(); 1562d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block} 1563d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block 1564d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block 1565791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Blockvoid Serializer::ObjectSerializer::VisitCodeEntry(Address entry_address) { 1566791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block Code* target = Code::cast(Code::GetObjectFromEntryAddress(entry_address)); 1567791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block OutputRawData(entry_address); 1568791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block serializer_->SerializeObject(target, kPlain, kFirstInstruction); 1569791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block bytes_processed_so_far_ += kPointerSize; 1570791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block} 1571791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block 1572791712a13f1814dd3ab5d1a5ab8ff5dbc476f6d6Steve Block 1573b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdochvoid Serializer::ObjectSerializer::VisitGlobalPropertyCell(RelocInfo* rinfo) { 1574b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch // We shouldn't have any global property cell references in code 1575b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch // objects in the snapshot. 1576b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch UNREACHABLE(); 1577b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch} 1578b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch 1579b0fe1620dcb4135ac3ab2d66ff93072373911299Ben Murdoch 1580d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockvoid Serializer::ObjectSerializer::VisitExternalAsciiString( 1581d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block v8::String::ExternalAsciiStringResource** resource_pointer) { 1582d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Address references_start = reinterpret_cast<Address>(resource_pointer); 1583d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block OutputRawData(references_start); 1584d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block for (int i = 0; i < Natives::GetBuiltinsCount(); i++) { 158544f0eee88ff00398ff7f715fab053374d808c90dSteve Block Object* source = HEAP->natives_source_cache()->get(i); 1586d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (!source->IsUndefined()) { 1587d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ExternalAsciiString* string = ExternalAsciiString::cast(source); 1588d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block typedef v8::String::ExternalAsciiStringResource Resource; 15893ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch const Resource* resource = string->resource(); 1590d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (resource == *resource_pointer) { 1591f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke sink_->Put(kNativesStringResource, "NativesStringResource"); 1592d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block sink_->PutSection(i, "NativesStringResourceEnd"); 1593d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block bytes_processed_so_far_ += sizeof(resource); 1594d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return; 1595d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1596a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1597a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1598d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // One of the strings in the natives cache should match the resource. We 1599d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // can't serialize any other kinds of external strings. 1600d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block UNREACHABLE(); 1601a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1602a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1603a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1604d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockvoid Serializer::ObjectSerializer::OutputRawData(Address up_to) { 1605d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Address object_start = object_->address(); 1606d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int up_to_offset = static_cast<int>(up_to - object_start); 1607d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int skipped = up_to_offset - bytes_processed_so_far_; 1608d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // This assert will fail if the reloc info gives us the target_address_address 1609d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // locations in a non-ascending order. Luckily that doesn't happen. 1610d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block ASSERT(skipped >= 0); 1611d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (skipped != 0) { 1612d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block Address base = object_start + bytes_processed_so_far_; 1613d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block#define RAW_CASE(index, length) \ 1614d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (skipped == length) { \ 1615f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke sink_->PutSection(kRawData + index, "RawDataFixed"); \ 1616d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } else /* NOLINT */ 1617d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block COMMON_RAW_LENGTHS(RAW_CASE) 1618d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block#undef RAW_CASE 1619d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block { /* NOLINT */ 1620f7060e27768c550ace7ec48ad8c093466db52dfaLeon Clarke sink_->Put(kRawData, "RawData"); 1621d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block sink_->PutInt(skipped, "length"); 1622a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1623d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block for (int i = 0; i < skipped; i++) { 1624d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block unsigned int data = base[i]; 1625d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block sink_->PutSection(data, "Byte"); 1626d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1627d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block bytes_processed_so_far_ += skipped; 1628a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1629a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1630a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1631a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1632d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockint Serializer::SpaceOfObject(HeapObject* object) { 1633d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block for (int i = FIRST_SPACE; i <= LAST_SPACE; i++) { 1634d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block AllocationSpace s = static_cast<AllocationSpace>(i); 163544f0eee88ff00398ff7f715fab053374d808c90dSteve Block if (HEAP->InSpace(object, s)) { 1636d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (i == LO_SPACE) { 1637d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (object->IsCode()) { 1638d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return kLargeCode; 1639d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } else if (object->IsFixedArray()) { 1640d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return kLargeFixedArray; 1641d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } else { 1642d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return kLargeData; 1643d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1644d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1645d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return i; 1646d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1647a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1648d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block UNREACHABLE(); 1649d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return 0; 1650a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1651a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1652a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1653d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockint Serializer::SpaceOfAlreadySerializedObject(HeapObject* object) { 1654d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block for (int i = FIRST_SPACE; i <= LAST_SPACE; i++) { 1655d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block AllocationSpace s = static_cast<AllocationSpace>(i); 165644f0eee88ff00398ff7f715fab053374d808c90dSteve Block if (HEAP->InSpace(object, s)) { 1657d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return i; 1658d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1659a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block } 1660a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block UNREACHABLE(); 1661d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return 0; 1662d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block} 1663d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block 1664d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block 1665d0582a6c46733687d045e4188a1bcd0123c758a1Steve Blockint Serializer::Allocate(int space, int size, bool* new_page) { 1666d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block CHECK(space >= 0 && space < kNumberOfSpaces); 1667d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (SpaceIsLarge(space)) { 1668d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // In large object space we merely number the objects instead of trying to 1669d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // determine some sort of address. 1670d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block *new_page = true; 1671e46be819fca9468a0cd4e74859ce0f778eb8ca60Leon Clarke large_object_total_ += size; 1672d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return fullness_[LO_SPACE]++; 1673d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1674d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block *new_page = false; 1675d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (fullness_[space] == 0) { 1676d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block *new_page = true; 1677d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1678d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block if (SpaceIsPaged(space)) { 1679d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // Paged spaces are a little special. We encode their addresses as if the 1680d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // pages were all contiguous and each page were filled up in the range 1681d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // 0 - Page::kObjectAreaSize. In practice the pages may not be contiguous 1682d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // and allocation does not start at offset 0 in the page, but this scheme 1683d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // means the deserializer can get the page number quickly by shifting the 1684d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block // serialized address. 1685d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block CHECK(IsPowerOf2(Page::kPageSize)); 1686d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int used_in_this_page = (fullness_[space] & (Page::kPageSize - 1)); 16873ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch CHECK(size <= SpaceAreaSize(space)); 16883ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (used_in_this_page + size > SpaceAreaSize(space)) { 1689d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block *new_page = true; 1690d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block fullness_[space] = RoundUp(fullness_[space], Page::kPageSize); 1691d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1692d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block } 1693d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block int allocation_address = fullness_[space]; 1694d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block fullness_[space] = allocation_address + size; 1695d0582a6c46733687d045e4188a1bcd0123c758a1Steve Block return allocation_address; 1696a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} 1697a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 1698a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block 16993ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdochint Serializer::SpaceAreaSize(int space) { 17003ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch if (space == CODE_SPACE) { 17013ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch return isolate_->memory_allocator()->CodePageAreaSize(); 17023ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } else { 17033ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch return Page::kPageSize - Page::kObjectStartOffset; 17043ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch } 17053ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch} 17063ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 17073ef787dbeca8a5fb1086949cda830dccee07bfbdBen Murdoch 1708a7e24c173cf37484693b9abb38e494fa7bd7baebSteve Block} } // namespace v8::internal 1709