Commit 2f1f203b authored by erik.corry@gmail.com's avatar erik.corry@gmail.com

Fix pc to code cache so it can cope with a pointer to the start of the code

object.  Rename it to be the inner pointer to code cache.
Review URL: http://codereview.chromium.org/7969013

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@9336 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
parent fdffe672
...@@ -106,7 +106,7 @@ inline StackHandler* StackFrame::top_handler() const { ...@@ -106,7 +106,7 @@ inline StackHandler* StackFrame::top_handler() const {
inline Code* StackFrame::GetContainingCode(Isolate* isolate, Address pc) { inline Code* StackFrame::GetContainingCode(Isolate* isolate, Address pc) {
return isolate->pc_to_code_cache()->GetCacheEntry(pc)->code; return isolate->inner_pointer_to_code_cache()->GetCacheEntry(pc)->code;
} }
......
...@@ -366,16 +366,17 @@ void SafeStackTraceFrameIterator::Advance() { ...@@ -366,16 +366,17 @@ void SafeStackTraceFrameIterator::Advance() {
Code* StackFrame::GetSafepointData(Isolate* isolate, Code* StackFrame::GetSafepointData(Isolate* isolate,
Address pc, Address inner_pointer,
SafepointEntry* safepoint_entry, SafepointEntry* safepoint_entry,
unsigned* stack_slots) { unsigned* stack_slots) {
PcToCodeCache::PcToCodeCacheEntry* entry = InnerPointerToCodeCache::InnerPointerToCodeCacheEntry* entry =
isolate->pc_to_code_cache()->GetCacheEntry(pc); isolate->inner_pointer_to_code_cache()->GetCacheEntry(inner_pointer);
if (!entry->safepoint_entry.is_valid()) { if (!entry->safepoint_entry.is_valid()) {
entry->safepoint_entry = entry->code->GetSafepointEntry(pc); entry->safepoint_entry = entry->code->GetSafepointEntry(inner_pointer);
ASSERT(entry->safepoint_entry.is_valid()); ASSERT(entry->safepoint_entry.is_valid());
} else { } else {
ASSERT(entry->safepoint_entry.Equals(entry->code->GetSafepointEntry(pc))); ASSERT(entry->safepoint_entry.Equals(
entry->code->GetSafepointEntry(inner_pointer)));
} }
// Fill in the results and return the code. // Fill in the results and return the code.
...@@ -819,7 +820,8 @@ DeoptimizationInputData* OptimizedFrame::GetDeoptimizationData( ...@@ -819,7 +820,8 @@ DeoptimizationInputData* OptimizedFrame::GetDeoptimizationData(
// back to a slow search in this case to find the original optimized // back to a slow search in this case to find the original optimized
// code object. // code object.
if (!code->contains(pc())) { if (!code->contains(pc())) {
code = isolate()->pc_to_code_cache()->GcSafeFindCodeForPc(pc()); code = isolate()->inner_pointer_to_code_cache()->
GcSafeFindCodeForInnerPointer(pc());
} }
ASSERT(code != NULL); ASSERT(code != NULL);
ASSERT(code->kind() == Code::OPTIMIZED_FUNCTION); ASSERT(code->kind() == Code::OPTIMIZED_FUNCTION);
...@@ -1155,9 +1157,10 @@ JavaScriptFrame* StackFrameLocator::FindJavaScriptFrame(int n) { ...@@ -1155,9 +1157,10 @@ JavaScriptFrame* StackFrameLocator::FindJavaScriptFrame(int n) {
// ------------------------------------------------------------------------- // -------------------------------------------------------------------------
Code* PcToCodeCache::GcSafeCastToCode(HeapObject* object, Address pc) { Code* InnerPointerToCodeCache::GcSafeCastToCode(HeapObject* object,
Address inner_pointer) {
Code* code = reinterpret_cast<Code*>(object); Code* code = reinterpret_cast<Code*>(object);
ASSERT(code != NULL && code->contains(pc)); ASSERT(code != NULL && code->contains(inner_pointer));
return code; return code;
} }
...@@ -1170,17 +1173,20 @@ static int GcSafeSizeOfCodeSpaceObject(HeapObject* object) { ...@@ -1170,17 +1173,20 @@ static int GcSafeSizeOfCodeSpaceObject(HeapObject* object) {
} }
Code* PcToCodeCache::GcSafeFindCodeForPc(Address pc) { Code* InnerPointerToCodeCache::GcSafeFindCodeForInnerPointer(
Address inner_pointer) {
Heap* heap = isolate_->heap(); Heap* heap = isolate_->heap();
// Check if the pc points into a large object chunk. // Check if the inner pointer points into a large object chunk.
LargePage* large_page = heap->lo_space()->FindPageContainingPc(pc); LargePage* large_page = heap->lo_space()->FindPageContainingPc(inner_pointer);
if (large_page != NULL) return GcSafeCastToCode(large_page->GetObject(), pc); if (large_page != NULL) {
return GcSafeCastToCode(large_page->GetObject(), inner_pointer);
}
// Iterate through the page until we reach the end or find an object starting // Iterate through the page until we reach the end or find an object starting
// after the pc. // after the inner pointer.
Page* page = Page::FromAddress(pc); Page* page = Page::FromAddress(inner_pointer);
Address addr = page->skip_list()->StartFor(pc); Address addr = page->skip_list()->StartFor(inner_pointer);
Address top = heap->code_space()->top(); Address top = heap->code_space()->top();
Address limit = heap->code_space()->limit(); Address limit = heap->code_space()->limit();
...@@ -1194,30 +1200,31 @@ Code* PcToCodeCache::GcSafeFindCodeForPc(Address pc) { ...@@ -1194,30 +1200,31 @@ Code* PcToCodeCache::GcSafeFindCodeForPc(Address pc) {
HeapObject* obj = HeapObject::FromAddress(addr); HeapObject* obj = HeapObject::FromAddress(addr);
int obj_size = GcSafeSizeOfCodeSpaceObject(obj); int obj_size = GcSafeSizeOfCodeSpaceObject(obj);
Address next_addr = addr + obj_size; Address next_addr = addr + obj_size;
if (next_addr >= pc) return GcSafeCastToCode(obj, pc); if (next_addr > inner_pointer) return GcSafeCastToCode(obj, inner_pointer);
addr = next_addr; addr = next_addr;
} }
} }
PcToCodeCache::PcToCodeCacheEntry* PcToCodeCache::GetCacheEntry(Address pc) { InnerPointerToCodeCache::InnerPointerToCodeCacheEntry*
InnerPointerToCodeCache::GetCacheEntry(Address inner_pointer) {
isolate_->counters()->pc_to_code()->Increment(); isolate_->counters()->pc_to_code()->Increment();
ASSERT(IsPowerOf2(kPcToCodeCacheSize)); ASSERT(IsPowerOf2(kInnerPointerToCodeCacheSize));
uint32_t hash = ComputeIntegerHash( uint32_t hash = ComputeIntegerHash(
static_cast<uint32_t>(reinterpret_cast<uintptr_t>(pc))); static_cast<uint32_t>(reinterpret_cast<uintptr_t>(inner_pointer)));
uint32_t index = hash & (kPcToCodeCacheSize - 1); uint32_t index = hash & (kInnerPointerToCodeCacheSize - 1);
PcToCodeCacheEntry* entry = cache(index); InnerPointerToCodeCacheEntry* entry = cache(index);
if (entry->pc == pc) { if (entry->inner_pointer == inner_pointer) {
isolate_->counters()->pc_to_code_cached()->Increment(); isolate_->counters()->pc_to_code_cached()->Increment();
ASSERT(entry->code == GcSafeFindCodeForPc(pc)); ASSERT(entry->code == GcSafeFindCodeForInnerPointer(inner_pointer));
} else { } else {
// Because this code may be interrupted by a profiling signal that // Because this code may be interrupted by a profiling signal that
// also queries the cache, we cannot update pc before the code has // also queries the cache, we cannot update inner_pointer before the code
// been set. Otherwise, we risk trying to use a cache entry before // has been set. Otherwise, we risk trying to use a cache entry before
// the code has been computed. // the code has been computed.
entry->code = GcSafeFindCodeForPc(pc); entry->code = GcSafeFindCodeForInnerPointer(inner_pointer);
entry->safepoint_entry.Reset(); entry->safepoint_entry.Reset();
entry->pc = pc; entry->inner_pointer = inner_pointer;
} }
return entry; return entry;
} }
......
...@@ -49,36 +49,36 @@ class StackFrameIterator; ...@@ -49,36 +49,36 @@ class StackFrameIterator;
class ThreadLocalTop; class ThreadLocalTop;
class Isolate; class Isolate;
class PcToCodeCache { class InnerPointerToCodeCache {
public: public:
struct PcToCodeCacheEntry { struct InnerPointerToCodeCacheEntry {
Address pc; Address inner_pointer;
Code* code; Code* code;
SafepointEntry safepoint_entry; SafepointEntry safepoint_entry;
}; };
explicit PcToCodeCache(Isolate* isolate) : isolate_(isolate) { explicit InnerPointerToCodeCache(Isolate* isolate) : isolate_(isolate) {
Flush(); Flush();
} }
Code* GcSafeFindCodeForPc(Address pc); Code* GcSafeFindCodeForInnerPointer(Address inner_pointer);
Code* GcSafeCastToCode(HeapObject* object, Address pc); Code* GcSafeCastToCode(HeapObject* object, Address inner_pointer);
void Flush() { void Flush() {
memset(&cache_[0], 0, sizeof(cache_)); memset(&cache_[0], 0, sizeof(cache_));
} }
PcToCodeCacheEntry* GetCacheEntry(Address pc); InnerPointerToCodeCacheEntry* GetCacheEntry(Address inner_pointer);
private: private:
PcToCodeCacheEntry* cache(int index) { return &cache_[index]; } InnerPointerToCodeCacheEntry* cache(int index) { return &cache_[index]; }
Isolate* isolate_; Isolate* isolate_;
static const int kPcToCodeCacheSize = 1024; static const int kInnerPointerToCodeCacheSize = 1024;
PcToCodeCacheEntry cache_[kPcToCodeCacheSize]; InnerPointerToCodeCacheEntry cache_[kInnerPointerToCodeCacheSize];
DISALLOW_COPY_AND_ASSIGN(PcToCodeCache); DISALLOW_COPY_AND_ASSIGN(InnerPointerToCodeCache);
}; };
......
...@@ -844,7 +844,8 @@ void Heap::MarkCompactPrologue() { ...@@ -844,7 +844,8 @@ void Heap::MarkCompactPrologue() {
Object* Heap::FindCodeObject(Address a) { Object* Heap::FindCodeObject(Address a) {
return isolate()->pc_to_code_cache()->GcSafeFindCodeForPc(a); return isolate()->inner_pointer_to_code_cache()->
GcSafeFindCodeForInnerPointer(a);
} }
......
...@@ -87,8 +87,8 @@ void IncrementalMarking::RecordWriteForEvacuationFromCode(HeapObject* obj, ...@@ -87,8 +87,8 @@ void IncrementalMarking::RecordWriteForEvacuationFromCode(HeapObject* obj,
void IncrementalMarking::RecordCodeTargetPatch(Address pc, HeapObject* value) { void IncrementalMarking::RecordCodeTargetPatch(Address pc, HeapObject* value) {
if (IsMarking()) { if (IsMarking()) {
Code* host = Code* host = heap_->isolate()->inner_pointer_to_code_cache()->
heap_->isolate()->pc_to_code_cache()->GcSafeFindCodeForPc(pc); GcSafeFindCodeForInnerPointer(pc);
RelocInfo rinfo(pc, RelocInfo::CODE_TARGET, 0, host); RelocInfo rinfo(pc, RelocInfo::CODE_TARGET, 0, host);
RecordWriteIntoCode(host, &rinfo, value); RecordWriteIntoCode(host, &rinfo, value);
} }
......
...@@ -1403,7 +1403,7 @@ Isolate::Isolate() ...@@ -1403,7 +1403,7 @@ Isolate::Isolate()
in_use_list_(0), in_use_list_(0),
free_list_(0), free_list_(0),
preallocated_storage_preallocated_(false), preallocated_storage_preallocated_(false),
pc_to_code_cache_(NULL), inner_pointer_to_code_cache_(NULL),
write_input_buffer_(NULL), write_input_buffer_(NULL),
global_handles_(NULL), global_handles_(NULL),
context_switcher_(NULL), context_switcher_(NULL),
...@@ -1576,8 +1576,8 @@ Isolate::~Isolate() { ...@@ -1576,8 +1576,8 @@ Isolate::~Isolate() {
compilation_cache_ = NULL; compilation_cache_ = NULL;
delete bootstrapper_; delete bootstrapper_;
bootstrapper_ = NULL; bootstrapper_ = NULL;
delete pc_to_code_cache_; delete inner_pointer_to_code_cache_;
pc_to_code_cache_ = NULL; inner_pointer_to_code_cache_ = NULL;
delete write_input_buffer_; delete write_input_buffer_;
write_input_buffer_ = NULL; write_input_buffer_ = NULL;
...@@ -1701,7 +1701,7 @@ bool Isolate::Init(Deserializer* des) { ...@@ -1701,7 +1701,7 @@ bool Isolate::Init(Deserializer* des) {
context_slot_cache_ = new ContextSlotCache(); context_slot_cache_ = new ContextSlotCache();
descriptor_lookup_cache_ = new DescriptorLookupCache(); descriptor_lookup_cache_ = new DescriptorLookupCache();
unicode_cache_ = new UnicodeCache(); unicode_cache_ = new UnicodeCache();
pc_to_code_cache_ = new PcToCodeCache(this); inner_pointer_to_code_cache_ = new InnerPointerToCodeCache(this);
write_input_buffer_ = new StringInputBuffer(); write_input_buffer_ = new StringInputBuffer();
global_handles_ = new GlobalHandles(this); global_handles_ = new GlobalHandles(this);
bootstrapper_ = new Bootstrapper(); bootstrapper_ = new Bootstrapper();
......
...@@ -66,7 +66,7 @@ class HandleScopeImplementer; ...@@ -66,7 +66,7 @@ class HandleScopeImplementer;
class HeapProfiler; class HeapProfiler;
class InlineRuntimeFunctionsTable; class InlineRuntimeFunctionsTable;
class NoAllocationStringAllocator; class NoAllocationStringAllocator;
class PcToCodeCache; class InnerPointerToCodeCache;
class PreallocatedMemoryThread; class PreallocatedMemoryThread;
class RegExpStack; class RegExpStack;
class SaveContext; class SaveContext;
...@@ -841,7 +841,9 @@ class Isolate { ...@@ -841,7 +841,9 @@ class Isolate {
return unicode_cache_; return unicode_cache_;
} }
PcToCodeCache* pc_to_code_cache() { return pc_to_code_cache_; } InnerPointerToCodeCache* inner_pointer_to_code_cache() {
return inner_pointer_to_code_cache_;
}
StringInputBuffer* write_input_buffer() { return write_input_buffer_; } StringInputBuffer* write_input_buffer() { return write_input_buffer_; }
...@@ -1136,7 +1138,7 @@ class Isolate { ...@@ -1136,7 +1138,7 @@ class Isolate {
PreallocatedStorage in_use_list_; PreallocatedStorage in_use_list_;
PreallocatedStorage free_list_; PreallocatedStorage free_list_;
bool preallocated_storage_preallocated_; bool preallocated_storage_preallocated_;
PcToCodeCache* pc_to_code_cache_; InnerPointerToCodeCache* inner_pointer_to_code_cache_;
StringInputBuffer* write_input_buffer_; StringInputBuffer* write_input_buffer_;
GlobalHandles* global_handles_; GlobalHandles* global_handles_;
ContextSwitcher* context_switcher_; ContextSwitcher* context_switcher_;
......
...@@ -281,7 +281,7 @@ void MarkCompactCollector::CollectGarbage() { ...@@ -281,7 +281,7 @@ void MarkCompactCollector::CollectGarbage() {
if (!collect_maps_) ReattachInitialMaps(); if (!collect_maps_) ReattachInitialMaps();
heap_->isolate()->pc_to_code_cache()->Flush(); heap_->isolate()->inner_pointer_to_code_cache()->Flush();
Finish(); Finish();
......
...@@ -3864,9 +3864,8 @@ byte* Code::entry() { ...@@ -3864,9 +3864,8 @@ byte* Code::entry() {
} }
bool Code::contains(byte* pc) { bool Code::contains(byte* inner_pointer) {
return (instruction_start() <= pc) && return (address() <= inner_pointer) && (inner_pointer <= address() + Size());
(pc <= instruction_start() + instruction_size());
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment