// Get outer context and create a new context based on it.
frame_->PushFunction();
Result context = frame_->CallRuntime(Runtime::kNewContext, 1);
+
// Update context local.
frame_->SaveContextRegister();
- if (kDebug) {
- JumpTarget verified_true(this);
- // Verify eax and esi are the same in debug mode
+ // Verify that the runtime call result and esi agree.
+ if (FLAG_debug_code) {
__ cmp(context.reg(), Operand(esi));
- context.Unuse();
- verified_true.Branch(equal);
- frame_->SpillAll();
- __ int3();
- verified_true.Bind();
+ __ Assert(equal, "Runtime::NewContext should end up in esi");
}
}
// Update context local.
frame_->SaveContextRegister();
- if (kDebug) {
- JumpTarget verified_true(this);
- // Verify that the result of the runtime call and the esi register are
- // the same in debug mode.
+ // Verify that the runtime call result and esi agree.
+ if (FLAG_debug_code) {
__ cmp(context.reg(), Operand(esi));
- context.Unuse();
- verified_true.Branch(equal);
- frame_->SpillAll();
- __ int3();
- verified_true.Bind();
+ __ Assert(equal, "Runtime::NewContext should end up in esi");
}
}
}
-// We only re-use a cached function for some script source code if the
-// script originates from the same places. This is to avoid issues
-// when reporting errors, etc.
-static bool HasOrigin(Handle<JSFunction> boilerplate,
- Handle<Object> name,
- int line_offset,
- int column_offset) {
- Handle<Script> script =
- Handle<Script>(Script::cast(boilerplate->shared()->script()));
- // If the script name isn't set, the boilerplate script should have
- // an undefined name to have the same origin.
- if (name.is_null()) {
- return script->name()->IsUndefined();
- }
- // Do the fast bailout checks first.
- if (line_offset != script->line_offset()->value()) return false;
- if (column_offset != script->column_offset()->value()) return false;
- // Check that both names are strings. If not, no match.
- if (!name->IsString() || !script->name()->IsString()) return false;
- // Compare the two name strings for equality.
- return String::cast(*name)->Equals(String::cast(script->name()));
-}
-
-
static Handle<JSFunction> Lookup(Handle<String> source,
+ Handle<Context> context,
CompilationCache::Entry entry) {
// Make sure not to leak the table into the surrounding handle
// scope. Otherwise, we risk keeping old tables around even after
Object* result;
{ HandleScope scope;
Handle<CompilationCacheTable> table = GetTable(entry);
- result = table->Lookup(*source);
+ result = table->LookupEval(*source, *context);
}
if (result->IsJSFunction()) {
return Handle<JSFunction>(JSFunction::cast(result));
}
-static Handle<JSFunction> Lookup(Handle<String> source,
- Handle<Context> context,
- CompilationCache::Entry entry) {
+static Handle<FixedArray> Lookup(Handle<String> source,
+ JSRegExp::Flags flags) {
// Make sure not to leak the table into the surrounding handle
// scope. Otherwise, we risk keeping old tables around even after
// having cleared the cache.
Object* result;
{ HandleScope scope;
- Handle<CompilationCacheTable> table = GetTable(entry);
- result = table->LookupEval(*source, *context);
+ Handle<CompilationCacheTable> table = GetTable(CompilationCache::REGEXP);
+ result = table->LookupRegExp(*source, flags);
}
- if (result->IsJSFunction()) {
- return Handle<JSFunction>(JSFunction::cast(result));
+ if (result->IsFixedArray()) {
+ return Handle<FixedArray>(FixedArray::cast(result));
} else {
- return Handle<JSFunction>::null();
+ return Handle<FixedArray>::null();
}
}
Handle<Object> name,
int line_offset,
int column_offset) {
- Handle<JSFunction> result = Lookup(source, SCRIPT);
- if (result.is_null()) {
- Counters::compilation_cache_misses.Increment();
- } else if (HasOrigin(result, name, line_offset, column_offset)) {
- Counters::compilation_cache_hits.Increment();
- } else {
- result = Handle<JSFunction>::null();
- Counters::compilation_cache_misses.Increment();
- }
- return result;
+ // TODO(245): Start caching scripts again but make it local to a
+ // global context to avoid sharing code between independent
+ // environments.
+ return Handle<JSFunction>::null();
}
}
-void CompilationCache::PutFunction(Handle<String> source,
- Entry entry,
- Handle<JSFunction> boilerplate) {
- HandleScope scope;
- ASSERT(boilerplate->IsBoilerplate());
- Handle<CompilationCacheTable> table = GetTable(entry);
- CALL_HEAP_FUNCTION_VOID(table->Put(*source, *boilerplate));
+Handle<FixedArray> CompilationCache::LookupRegExp(Handle<String> source,
+ JSRegExp::Flags flags) {
+ Handle<FixedArray> result = Lookup(source, flags);
+ if (result.is_null()) {
+ Counters::compilation_cache_misses.Increment();
+ } else {
+ Counters::compilation_cache_hits.Increment();
+ }
+ return result;
}
-void CompilationCache::PutEvalFunction(Handle<String> source,
- Handle<Context> context,
- Entry entry,
- Handle<JSFunction> boilerplate) {
+void CompilationCache::PutScript(Handle<String> source,
+ Entry entry,
+ Handle<JSFunction> boilerplate) {
+ // TODO(245): Start caching scripts again but make it local to a
+ // global context to avoid sharing code between independent
+ // environments.
+}
+
+
+void CompilationCache::PutEval(Handle<String> source,
+ Handle<Context> context,
+ Entry entry,
+ Handle<JSFunction> boilerplate) {
HandleScope scope;
ASSERT(boilerplate->IsBoilerplate());
Handle<CompilationCacheTable> table = GetTable(entry);
}
-Handle<FixedArray> CompilationCache::LookupRegExp(Handle<String> source,
- JSRegExp::Flags flags) {
- Handle<CompilationCacheTable> table = GetTable(REGEXP);
- Object* result = table->LookupRegExp(*source, flags);
- if (result->IsFixedArray()) {
- Counters::regexp_cache_hits.Increment();
- return Handle<FixedArray>(FixedArray::cast(result));
- } else {
- Counters::regexp_cache_misses.Increment();
- return Handle<FixedArray>();
- }
-}
-
void CompilationCache::PutRegExp(Handle<String> source,
JSRegExp::Flags flags,
static Handle<FixedArray> LookupRegExp(Handle<String> source,
JSRegExp::Flags flags);
+ // Associate the (source, kind) pair to the boilerplate. This may
+ // overwrite an existing mapping.
+ static void PutScript(Handle<String> source,
+ Entry entry,
+ Handle<JSFunction> boilerplate);
+
+ // Associate the (source, context->closure()->shared(), kind) triple
+ // with the boilerplate. This may overwrite an existing mapping.
+ static void PutEval(Handle<String> source,
+ Handle<Context> context,
+ Entry entry,
+ Handle<JSFunction> boilerplate);
+
// Associate the (source, flags) pair to the given regexp data.
// This may overwrite an existing mapping.
static void PutRegExp(Handle<String> source,
JSRegExp::Flags flags,
Handle<FixedArray> data);
- // Associate the (source, kind) pair to the boilerplate. This may
- // overwrite an existing mapping.
- static void PutFunction(Handle<String> source,
- Entry entry,
- Handle<JSFunction> boilerplate);
-
- // Associate the (source, context->closure()->shared(), kind)
- // triple with the boilerplate. This may overwrite an existing
- // mapping.
- static void PutEvalFunction(Handle<String> source,
- Handle<Context> context,
- Entry entry,
- Handle<JSFunction> boilerplate);
-
// Clear the cache - also used to initialize the cache at startup.
static void Clear();