📄 stub-cache.h.svn-base
字号:
// Copyright 2006-2008 the V8 project authors. All rights reserved.// Redistribution and use in source and binary forms, with or without// modification, are permitted provided that the following conditions are// met://// * Redistributions of source code must retain the above copyright// notice, this list of conditions and the following disclaimer.// * Redistributions in binary form must reproduce the above// copyright notice, this list of conditions and the following// disclaimer in the documentation and/or other materials provided// with the distribution.// * Neither the name of Google Inc. nor the names of its// contributors may be used to endorse or promote products derived// from this software without specific prior written permission.//// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.#ifndef V8_STUB_CACHE_H_#define V8_STUB_CACHE_H_#include "macro-assembler.h"namespace v8 { namespace internal {// The stub cache is used for megamorphic calls and property accesses.// It maps (map, name, type)->Code*// The design of the table uses the inline cache stubs used for// mono-morphic calls. The beauty of this, we do not have to// invalidate the cache whenever a prototype map is changed. The stub// validates the map chain as in the mono-morphic case.class SCTableReference;class StubCache : public AllStatic { public: struct Entry { String* key; Code* value; }; static void Initialize(bool create_heap_objects); // Computes the right stub matching. Inserts the result in the // cache before returning. This might compile a stub if needed. static Object* ComputeLoadField(String* name, JSObject* receiver, JSObject* holder, int field_index); static Object* ComputeLoadCallback(String* name, JSObject* receiver, JSObject* holder, AccessorInfo* callback); static Object* ComputeLoadConstant(String* name, JSObject* receiver, JSObject* holder, Object* value); static Object* ComputeLoadInterceptor(String* name, JSObject* receiver, JSObject* holder); static Object* ComputeLoadNormal(String* name, JSObject* receiver); // --- static Object* ComputeKeyedLoadField(String* name, JSObject* receiver, JSObject* holder, int field_index); static Object* ComputeKeyedLoadCallback(String* name, JSObject* receiver, JSObject* holder, AccessorInfo* callback); static Object* ComputeKeyedLoadConstant(String* name, JSObject* receiver, JSObject* holder, Object* value); static Object* ComputeKeyedLoadInterceptor(String* name, JSObject* receiver, JSObject* holder); static Object* ComputeKeyedLoadArrayLength(String* name, JSArray* receiver); static Object* ComputeKeyedLoadShortStringLength(String* name, String* receiver); static Object* ComputeKeyedLoadMediumStringLength(String* name, String* receiver); static Object* ComputeKeyedLoadLongStringLength(String* name, String* receiver); static Object* ComputeKeyedLoadFunctionPrototype(String* name, JSFunction* receiver); // --- static Object* ComputeStoreField(String* name, JSObject* receiver, int field_index, Map* transition = NULL); static Object* ComputeStoreCallback(String* name, JSObject* receiver, AccessorInfo* callback); static Object* ComputeStoreInterceptor(String* name, JSObject* receiver); // --- static Object* ComputeKeyedStoreField(String* name, JSObject* receiver, int field_index, Map* transition = NULL); // --- static Object* ComputeCallField(int argc, String* name, Object* object, JSObject* holder, int index); static Object* ComputeCallConstant(int argc, String* name, Object* object, JSObject* holder, JSFunction* function); static Object* ComputeCallNormal(int argc, String* name, JSObject* receiver); static Object* ComputeCallInterceptor(int argc, String* name, Object* object, JSObject* holder); // --- static Object* ComputeCallInitialize(int argc); static Object* ComputeCallPreMonomorphic(int argc); static Object* ComputeCallNormal(int argc); static Object* ComputeCallMegamorphic(int argc); static Object* ComputeCallMiss(int argc); // Finds the Code object stored in the Heap::non_monomorphic_cache(). static Code* FindCallInitialize(int argc); static Object* ComputeCallDebugBreak(int argc); static Object* ComputeCallDebugPrepareStepIn(int argc); static Object* ComputeLazyCompile(int argc); // Update cache for entry hash(name, map). static Code* Set(String* name, Map* map, Code* code); // Clear the lookup table (@ mark compact collection). static void Clear(); // Functions for generating stubs at startup. static void GenerateMiss(MacroAssembler* masm); // Generate code for probing the stub cache table. static void GenerateProbe(MacroAssembler* masm, Code::Flags flags, Register receiver, Register name, Register scratch); enum Table { kPrimary, kSecondary }; private: friend class SCTableReference; static const int kPrimaryTableSize = 2048; static const int kSecondaryTableSize = 512; static Entry primary_[]; static Entry secondary_[]; // Computes the hashed offsets for primary and secondary caches. static int PrimaryOffset(String* name, Code::Flags flags, Map* map) { // Compute the hash of the name (use entire length field). uint32_t name_hash = name->length_field(); ASSERT(name_hash & String::kHashComputedMask); // Base the offset on a simple combination of name, flags, and map. uint32_t key = (reinterpret_cast<uint32_t>(map) + name_hash) ^ flags; return key & ((kPrimaryTableSize - 1) << kHeapObjectTagSize); } static int SecondaryOffset(String* name, Code::Flags flags, int seed) { // Use the seed from the primary cache in the secondary cache. uint32_t key = seed - reinterpret_cast<uint32_t>(name) + flags; return key & ((kSecondaryTableSize - 1) << kHeapObjectTagSize); } // Compute the entry for a given offset in exactly the same way as // we done in generated code. This makes it a lot easier to avoid // making mistakes in the hashed offset computations. static Entry* entry(Entry* table, int offset) { return reinterpret_cast<Entry*>( reinterpret_cast<Address>(table) + (offset << 1)); }};class SCTableReference { public: static SCTableReference keyReference(StubCache::Table table) { return SCTableReference( reinterpret_cast<Address>(&first_entry(table)->key)); } static SCTableReference valueReference(StubCache::Table table) { return SCTableReference( reinterpret_cast<Address>(&first_entry(table)->value)); }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -