Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(168)

Unified Diff: src/deoptimizer.cc

Issue 11275145: Decouple allocation and creation of deopt tables (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Review feedback Created 8 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « src/deoptimizer.h ('k') | no next file » | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/deoptimizer.cc
diff --git a/src/deoptimizer.cc b/src/deoptimizer.cc
index e7576562ba09c894f78809c0c4fdf09bf4a34ca0..037561f1b9dd393ee0699fbc7f548db9b87c72d5 100644
--- a/src/deoptimizer.cc
+++ b/src/deoptimizer.cc
@@ -41,8 +41,11 @@ namespace v8 {
namespace internal {
DeoptimizerData::DeoptimizerData() {
- eager_deoptimization_entry_code_ = NULL;
- lazy_deoptimization_entry_code_ = NULL;
+ eager_deoptimization_entry_code_entries_ = -1;
+ lazy_deoptimization_entry_code_entries_ = -1;
+ size_t deopt_table_size = Deoptimizer::GetMaxDeoptTableSize();
+ eager_deoptimization_entry_code_ = new VirtualMemory(deopt_table_size);
+ lazy_deoptimization_entry_code_ = new VirtualMemory(deopt_table_size);
current_ = NULL;
deoptimizing_code_list_ = NULL;
#ifdef ENABLE_DEBUGGER_SUPPORT
@@ -52,16 +55,11 @@ DeoptimizerData::DeoptimizerData() {
DeoptimizerData::~DeoptimizerData() {
- if (eager_deoptimization_entry_code_ != NULL) {
- Isolate::Current()->memory_allocator()->Free(
- eager_deoptimization_entry_code_);
- eager_deoptimization_entry_code_ = NULL;
- }
- if (lazy_deoptimization_entry_code_ != NULL) {
- Isolate::Current()->memory_allocator()->Free(
- lazy_deoptimization_entry_code_);
- lazy_deoptimization_entry_code_ = NULL;
- }
+ delete eager_deoptimization_entry_code_;
+ eager_deoptimization_entry_code_ = NULL;
+ delete lazy_deoptimization_entry_code_;
+ lazy_deoptimization_entry_code_ = NULL;
+
DeoptimizingCodeListNode* current = deoptimizing_code_list_;
while (current != NULL) {
DeoptimizingCodeListNode* prev = current;
@@ -103,6 +101,19 @@ Deoptimizer* Deoptimizer::New(JSFunction* function,
}
+// No larger than 2K on all platforms
+static const int kDeoptTableMaxEpilogueCodeSize = 2 * KB;
+
+
+size_t Deoptimizer::GetMaxDeoptTableSize() {
+ size_t entries_size =
+ Deoptimizer::kMaxNumberOfEntries * Deoptimizer::table_entry_size_;
+ int page_count = ((kDeoptTableMaxEpilogueCodeSize + entries_size - 1) /
+ OS::CommitPageSize()) + 1;
+ return OS::CommitPageSize() * page_count;
+}
+
+
Deoptimizer* Deoptimizer::Grab(Isolate* isolate) {
ASSERT(isolate == Isolate::Current());
Deoptimizer* result = isolate->deoptimizer_data()->current_;
@@ -461,44 +472,45 @@ void Deoptimizer::DeleteFrameDescriptions() {
}
-Address Deoptimizer::GetDeoptimizationEntry(int id, BailoutType type) {
+Address Deoptimizer::GetDeoptimizationEntry(int id,
+ BailoutType type,
+ GetEntryMode mode) {
ASSERT(id >= 0);
- if (id >= kNumberOfEntries) return NULL;
- MemoryChunk* base = NULL;
+ if (id >= kMaxNumberOfEntries) return NULL;
+ VirtualMemory* base = NULL;
+ if (mode == ENSURE_ENTRY_CODE) {
+ EnsureCodeForDeoptimizationEntry(type, id);
+ } else {
+ ASSERT(mode == CALCULATE_ENTRY_ADDRESS);
+ }
DeoptimizerData* data = Isolate::Current()->deoptimizer_data();
if (type == EAGER) {
- if (data->eager_deoptimization_entry_code_ == NULL) {
- data->eager_deoptimization_entry_code_ = CreateCode(type);
- }
base = data->eager_deoptimization_entry_code_;
} else {
- if (data->lazy_deoptimization_entry_code_ == NULL) {
- data->lazy_deoptimization_entry_code_ = CreateCode(type);
- }
base = data->lazy_deoptimization_entry_code_;
}
return
- static_cast<Address>(base->area_start()) + (id * table_entry_size_);
+ static_cast<Address>(base->address()) + (id * table_entry_size_);
}
int Deoptimizer::GetDeoptimizationId(Address addr, BailoutType type) {
- MemoryChunk* base = NULL;
+ VirtualMemory* base = NULL;
DeoptimizerData* data = Isolate::Current()->deoptimizer_data();
if (type == EAGER) {
base = data->eager_deoptimization_entry_code_;
} else {
base = data->lazy_deoptimization_entry_code_;
}
+ Address base_casted = reinterpret_cast<Address>(base->address());
if (base == NULL ||
- addr < base->area_start() ||
- addr >= base->area_start() +
- (kNumberOfEntries * table_entry_size_)) {
+ addr < base->address() ||
+ addr >= base_casted + (kMaxNumberOfEntries * table_entry_size_)) {
return kNotDeoptimizationEntry;
}
ASSERT_EQ(0,
- static_cast<int>(addr - base->area_start()) % table_entry_size_);
- return static_cast<int>(addr - base->area_start()) / table_entry_size_;
+ static_cast<int>(addr - base_casted) % table_entry_size_);
+ return static_cast<int>(addr - base_casted) / table_entry_size_;
}
@@ -1384,31 +1396,44 @@ void Deoptimizer::AddDoubleValue(intptr_t slot_address, double value) {
}
-MemoryChunk* Deoptimizer::CreateCode(BailoutType type) {
+void Deoptimizer::EnsureCodeForDeoptimizationEntry(BailoutType type,
+ int max_entry_id) {
// We cannot run this if the serializer is enabled because this will
// cause us to emit relocation information for the external
// references. This is fine because the deoptimizer's code section
// isn't meant to be serialized at all.
ASSERT(!Serializer::enabled());
+ ASSERT(type == EAGER || type == LAZY);
+ DeoptimizerData* data = Isolate::Current()->deoptimizer_data();
+ int entry_count = (type == EAGER)
+ ? data->eager_deoptimization_entry_code_entries_
+ : data->lazy_deoptimization_entry_code_entries_;
+ if (max_entry_id < entry_count) return;
+ entry_count = Min(Max(entry_count * 2, Deoptimizer::kMinNumberOfEntries),
+ Deoptimizer::kMaxNumberOfEntries);
+
MacroAssembler masm(Isolate::Current(), NULL, 16 * KB);
masm.set_emit_debug_code(false);
- GenerateDeoptimizationEntries(&masm, kNumberOfEntries, type);
+ GenerateDeoptimizationEntries(&masm, entry_count, type);
CodeDesc desc;
masm.GetCode(&desc);
ASSERT(desc.reloc_size == 0);
- MemoryChunk* chunk =
- Isolate::Current()->memory_allocator()->AllocateChunk(desc.instr_size,
- EXECUTABLE,
- NULL);
- ASSERT(chunk->area_size() >= desc.instr_size);
- if (chunk == NULL) {
- V8::FatalProcessOutOfMemory("Not enough memory for deoptimization table");
+ VirtualMemory* memory = type == EAGER
+ ? data->eager_deoptimization_entry_code_
+ : data->lazy_deoptimization_entry_code_;
+ size_t table_size = Deoptimizer::GetMaxDeoptTableSize();
+ ASSERT(static_cast<int>(table_size) >= desc.instr_size);
+ memory->Commit(memory->address(), table_size, true);
+ memcpy(memory->address(), desc.buffer, desc.instr_size);
+ CPU::FlushICache(memory->address(), desc.instr_size);
+
+ if (type == EAGER) {
+ data->eager_deoptimization_entry_code_entries_ = entry_count;
+ } else {
+ data->lazy_deoptimization_entry_code_entries_ = entry_count;
}
- memcpy(chunk->area_start(), desc.buffer, desc.instr_size);
- CPU::FlushICache(chunk->area_start(), desc.instr_size);
- return chunk;
}
« no previous file with comments | « src/deoptimizer.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698