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

Unified Diff: src/ast.cc

Issue 6529032: Merge 6168:6800 from bleeding_edge to experimental/gc branch. (Closed) Base URL: http://v8.googlecode.com/svn/branches/experimental/gc/
Patch Set: Created 9 years, 10 months 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/ast.h ('k') | src/bignum.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/ast.cc
===================================================================
--- src/ast.cc (revision 6800)
+++ src/ast.cc (working copy)
@@ -32,7 +32,6 @@
#include "parser.h"
#include "scopes.h"
#include "string-stream.h"
-#include "stub-cache.h"
namespace v8 {
namespace internal {
@@ -166,12 +165,6 @@
}
-bool FunctionLiteral::AllowOptimize() {
- // We can't deal with heap-allocated locals.
- return scope()->num_heap_slots() == 0;
-}
-
-
ObjectLiteral::Property::Property(Literal* key, Expression* value) {
emit_store_ = true;
key_ = key;
@@ -215,20 +208,35 @@
bool IsEqualString(void* first, void* second) {
+ ASSERT((*reinterpret_cast<String**>(first))->IsString());
+ ASSERT((*reinterpret_cast<String**>(second))->IsString());
Handle<String> h1(reinterpret_cast<String**>(first));
Handle<String> h2(reinterpret_cast<String**>(second));
return (*h1)->Equals(*h2);
}
-bool IsEqualSmi(void* first, void* second) {
- Handle<Smi> h1(reinterpret_cast<Smi**>(first));
- Handle<Smi> h2(reinterpret_cast<Smi**>(second));
- return (*h1)->value() == (*h2)->value();
+
+bool IsEqualNumber(void* first, void* second) {
+ ASSERT((*reinterpret_cast<Object**>(first))->IsNumber());
+ ASSERT((*reinterpret_cast<Object**>(second))->IsNumber());
+
+ Handle<Object> h1(reinterpret_cast<Object**>(first));
+ Handle<Object> h2(reinterpret_cast<Object**>(second));
+ if (h1->IsSmi()) {
+ return h2->IsSmi() && *h1 == *h2;
+ }
+ if (h2->IsSmi()) return false;
+ Handle<HeapNumber> n1 = Handle<HeapNumber>::cast(h1);
+ Handle<HeapNumber> n2 = Handle<HeapNumber>::cast(h2);
+ ASSERT(isfinite(n1->value()));
+ ASSERT(isfinite(n2->value()));
+ return n1->value() == n2->value();
}
+
void ObjectLiteral::CalculateEmitStore() {
HashMap properties(&IsEqualString);
- HashMap elements(&IsEqualSmi);
+ HashMap elements(&IsEqualNumber);
for (int i = this->properties()->length() - 1; i >= 0; i--) {
ObjectLiteral::Property* property = this->properties()->at(i);
Literal* literal = property->key();
@@ -241,16 +249,19 @@
uint32_t hash;
HashMap* table;
void* key;
- uint32_t index;
if (handle->IsSymbol()) {
Handle<String> name(String::cast(*handle));
- ASSERT(!name->AsArrayIndex(&index));
- key = name.location();
- hash = name->Hash();
- table = &properties;
- } else if (handle->ToArrayIndex(&index)) {
+ if (name->AsArrayIndex(&hash)) {
+ Handle<Object> key_handle = Factory::NewNumberFromUint(hash);
+ key = key_handle.location();
+ table = &elements;
+ } else {
+ key = name.location();
+ hash = name->Hash();
+ table = &properties;
+ }
+ } else if (handle->ToArrayIndex(&hash)) {
key = handle.location();
- hash = index;
table = &elements;
} else {
ASSERT(handle->IsNumber());
@@ -266,12 +277,12 @@
// If the key of a computed property is in the table, do not emit
// a store for the property later.
if (property->kind() == ObjectLiteral::Property::COMPUTED) {
- if (table->Lookup(literal, hash, false) != NULL) {
+ if (table->Lookup(key, hash, false) != NULL) {
property->set_emit_store(false);
}
}
// Add key to the table.
- table->Lookup(literal, hash, true);
+ table->Lookup(key, hash, true);
}
}
@@ -517,6 +528,8 @@
if (key()->IsPropertyName()) {
if (oracle->LoadIsBuiltin(this, Builtins::LoadIC_ArrayLength)) {
is_array_length_ = true;
+ } else if (oracle->LoadIsBuiltin(this, Builtins::LoadIC_StringLength)) {
+ is_string_length_ = true;
} else if (oracle->LoadIsBuiltin(this,
Builtins::LoadIC_FunctionPrototype)) {
is_function_prototype_ = true;
@@ -562,25 +575,25 @@
}
-static bool CallWithoutIC(Handle<JSFunction> target, int arity) {
+static bool CanCallWithoutIC(Handle<JSFunction> target, int arity) {
SharedFunctionInfo* info = target->shared();
- if (target->NeedsArgumentsAdaption()) {
- // If the number of formal parameters of the target function
- // does not match the number of arguments we're passing, we
- // don't want to deal with it.
- return info->formal_parameter_count() == arity;
- } else {
- // If the target doesn't need arguments adaption, we can call
- // it directly, but we avoid to do so if it has a custom call
- // generator, because that is likely to generate better code.
- return !info->HasBuiltinFunctionId() ||
- !CallStubCompiler::HasCustomCallGenerator(info->builtin_function_id());
- }
+ // If the number of formal parameters of the target function does
+ // not match the number of arguments we're passing, we don't want to
+ // deal with it. Otherwise, we can call it directly.
+ return !target->NeedsArgumentsAdaption() ||
+ info->formal_parameter_count() == arity;
}
bool Call::ComputeTarget(Handle<Map> type, Handle<String> name) {
- holder_ = Handle<JSObject>::null();
+ if (check_type_ == RECEIVER_MAP_CHECK) {
+ // For primitive checks the holder is set up to point to the
+ // corresponding prototype object, i.e. one step of the algorithm
+ // below has been already performed.
+ // For non-primitive checks we clear it to allow computing targets
+ // for polymorphic calls.
+ holder_ = Handle<JSObject>::null();
+ }
while (true) {
LookupResult lookup;
type->LookupInDescriptors(NULL, *name, &lookup);
@@ -591,7 +604,7 @@
type = Handle<Map>(holder()->map());
} else if (lookup.IsProperty() && lookup.type() == CONSTANT_FUNCTION) {
target_ = Handle<JSFunction>(lookup.GetConstantFunctionFromMap(*type));
- return CallWithoutIC(target_, arguments()->length());
+ return CanCallWithoutIC(target_, arguments()->length());
} else {
return false;
}
@@ -605,14 +618,16 @@
cell_ = Handle<JSGlobalPropertyCell>::null();
LookupResult lookup;
global->Lookup(*name, &lookup);
- if (lookup.IsProperty() && lookup.type() == NORMAL) {
+ if (lookup.IsProperty() &&
+ lookup.type() == NORMAL &&
+ lookup.holder() == *global) {
cell_ = Handle<JSGlobalPropertyCell>(global->GetPropertyCell(&lookup));
if (cell_->value()->IsJSFunction()) {
Handle<JSFunction> candidate(JSFunction::cast(cell_->value()));
// If the function is in new space we assume it's more likely to
// change and thus prefer the general IC code.
- if (!Heap::InNewSpace(*candidate)
- && CallWithoutIC(candidate, arguments()->length())) {
+ if (!Heap::InNewSpace(*candidate) &&
+ CanCallWithoutIC(candidate, arguments()->length())) {
target_ = candidate;
return true;
}
@@ -641,27 +656,29 @@
}
}
#endif
- if (receiver_types_ != NULL && receiver_types_->length() > 0) {
- Handle<Map> type = receiver_types_->at(0);
- is_monomorphic_ = oracle->CallIsMonomorphic(this);
- if (is_monomorphic_) is_monomorphic_ = ComputeTarget(type, name);
+ is_monomorphic_ = oracle->CallIsMonomorphic(this);
+ check_type_ = oracle->GetCallCheckType(this);
+ if (is_monomorphic_) {
+ Handle<Map> map;
+ if (receiver_types_ != NULL && receiver_types_->length() > 0) {
+ ASSERT(check_type_ == RECEIVER_MAP_CHECK);
+ map = receiver_types_->at(0);
+ } else {
+ ASSERT(check_type_ != RECEIVER_MAP_CHECK);
+ holder_ = Handle<JSObject>(
+ oracle->GetPrototypeForPrimitiveCheck(check_type_));
+ map = Handle<Map>(holder_->map());
+ }
+ is_monomorphic_ = ComputeTarget(map, name);
}
}
-void BinaryOperation::RecordTypeFeedback(TypeFeedbackOracle* oracle) {
- TypeInfo left = oracle->BinaryType(this, TypeFeedbackOracle::LEFT);
- TypeInfo right = oracle->BinaryType(this, TypeFeedbackOracle::RIGHT);
- is_smi_only_ = left.IsSmi() && right.IsSmi();
-}
-
-
void CompareOperation::RecordTypeFeedback(TypeFeedbackOracle* oracle) {
- TypeInfo left = oracle->CompareType(this, TypeFeedbackOracle::LEFT);
- TypeInfo right = oracle->CompareType(this, TypeFeedbackOracle::RIGHT);
- if (left.IsSmi() && right.IsSmi()) {
+ TypeInfo info = oracle->CompareType(this);
+ if (info.IsSmi()) {
compare_type_ = SMI_ONLY;
- } else if (left.IsNonPrimitive() && right.IsNonPrimitive()) {
+ } else if (info.IsNonPrimitive()) {
compare_type_ = OBJECT_ONLY;
} else {
ASSERT(compare_type_ == NONE);
« no previous file with comments | « src/ast.h ('k') | src/bignum.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698