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

Side by Side Diff: src/hydrogen.cc

Issue 16482004: Revert "Enable map dependency to in-flight compilation info." (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Created 7 years, 6 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 unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « src/hydrogen.h ('k') | src/hydrogen-instructions.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 3789 matching lines...) Expand 10 before | Expand all | Expand 10 after
3800 3800
3801 3801
3802 #define CHECK_ALIVE(call) \ 3802 #define CHECK_ALIVE(call) \
3803 do { \ 3803 do { \
3804 call; \ 3804 call; \
3805 if (HasStackOverflow() || current_block() == NULL) return; \ 3805 if (HasStackOverflow() || current_block() == NULL) return; \
3806 } while (false) 3806 } while (false)
3807 3807
3808 3808
3809 void HOptimizedGraphBuilder::Bailout(const char* reason) { 3809 void HOptimizedGraphBuilder::Bailout(const char* reason) {
3810 current_info()->set_bailout_reason(reason); 3810 info()->set_bailout_reason(reason);
3811 SetStackOverflow(); 3811 SetStackOverflow();
3812 } 3812 }
3813 3813
3814 3814
3815 void HOptimizedGraphBuilder::VisitForEffect(Expression* expr) { 3815 void HOptimizedGraphBuilder::VisitForEffect(Expression* expr) {
3816 EffectContext for_effect(this); 3816 EffectContext for_effect(this);
3817 Visit(expr); 3817 Visit(expr);
3818 } 3818 }
3819 3819
3820 3820
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
3857 3857
3858 void HOptimizedGraphBuilder::VisitExpressions( 3858 void HOptimizedGraphBuilder::VisitExpressions(
3859 ZoneList<Expression*>* exprs) { 3859 ZoneList<Expression*>* exprs) {
3860 for (int i = 0; i < exprs->length(); ++i) { 3860 for (int i = 0; i < exprs->length(); ++i) {
3861 CHECK_ALIVE(VisitForValue(exprs->at(i))); 3861 CHECK_ALIVE(VisitForValue(exprs->at(i)));
3862 } 3862 }
3863 } 3863 }
3864 3864
3865 3865
3866 bool HOptimizedGraphBuilder::BuildGraph() { 3866 bool HOptimizedGraphBuilder::BuildGraph() {
3867 if (current_info()->function()->is_generator()) { 3867 if (info()->function()->is_generator()) {
3868 Bailout("function is a generator"); 3868 Bailout("function is a generator");
3869 return false; 3869 return false;
3870 } 3870 }
3871 Scope* scope = current_info()->scope(); 3871 Scope* scope = info()->scope();
3872 if (scope->HasIllegalRedeclaration()) { 3872 if (scope->HasIllegalRedeclaration()) {
3873 Bailout("function with illegal redeclaration"); 3873 Bailout("function with illegal redeclaration");
3874 return false; 3874 return false;
3875 } 3875 }
3876 if (scope->calls_eval()) { 3876 if (scope->calls_eval()) {
3877 Bailout("function calls eval"); 3877 Bailout("function calls eval");
3878 return false; 3878 return false;
3879 } 3879 }
3880 SetUpScope(scope); 3880 SetUpScope(scope);
3881 3881
(...skipping 23 matching lines...) Expand all
3905 if (scope->is_function_scope() && scope->function() != NULL) { 3905 if (scope->is_function_scope() && scope->function() != NULL) {
3906 VisitVariableDeclaration(scope->function()); 3906 VisitVariableDeclaration(scope->function());
3907 } 3907 }
3908 VisitDeclarations(scope->declarations()); 3908 VisitDeclarations(scope->declarations());
3909 AddSimulate(BailoutId::Declarations()); 3909 AddSimulate(BailoutId::Declarations());
3910 3910
3911 HValue* context = environment()->LookupContext(); 3911 HValue* context = environment()->LookupContext();
3912 AddInstruction( 3912 AddInstruction(
3913 new(zone()) HStackCheck(context, HStackCheck::kFunctionEntry)); 3913 new(zone()) HStackCheck(context, HStackCheck::kFunctionEntry));
3914 3914
3915 VisitStatements(current_info()->function()->body()); 3915 VisitStatements(info()->function()->body());
3916 if (HasStackOverflow()) return false; 3916 if (HasStackOverflow()) return false;
3917 3917
3918 if (current_block() != NULL) { 3918 if (current_block() != NULL) {
3919 AddReturn(graph()->GetConstantUndefined()); 3919 AddReturn(graph()->GetConstantUndefined());
3920 set_current_block(NULL); 3920 set_current_block(NULL);
3921 } 3921 }
3922 3922
3923 // If the checksum of the number of type info changes is the same as the 3923 // If the checksum of the number of type info changes is the same as the
3924 // last time this function was compiled, then this recompile is likely not 3924 // last time this function was compiled, then this recompile is likely not
3925 // due to missing/inadequate type feedback, but rather too aggressive 3925 // due to missing/inadequate type feedback, but rather too aggressive
3926 // optimization. Disable optimistic LICM in that case. 3926 // optimization. Disable optimistic LICM in that case.
3927 Handle<Code> unoptimized_code(current_info()->shared_info()->code()); 3927 Handle<Code> unoptimized_code(info()->shared_info()->code());
3928 ASSERT(unoptimized_code->kind() == Code::FUNCTION); 3928 ASSERT(unoptimized_code->kind() == Code::FUNCTION);
3929 Handle<TypeFeedbackInfo> type_info( 3929 Handle<TypeFeedbackInfo> type_info(
3930 TypeFeedbackInfo::cast(unoptimized_code->type_feedback_info())); 3930 TypeFeedbackInfo::cast(unoptimized_code->type_feedback_info()));
3931 int checksum = type_info->own_type_change_checksum(); 3931 int checksum = type_info->own_type_change_checksum();
3932 int composite_checksum = graph()->update_type_change_checksum(checksum); 3932 int composite_checksum = graph()->update_type_change_checksum(checksum);
3933 graph()->set_use_optimistic_licm( 3933 graph()->set_use_optimistic_licm(
3934 !type_info->matches_inlined_type_change_checksum(composite_checksum)); 3934 !type_info->matches_inlined_type_change_checksum(composite_checksum));
3935 type_info->set_inlined_type_change_checksum(composite_checksum); 3935 type_info->set_inlined_type_change_checksum(composite_checksum);
3936 3936
3937 return true; 3937 return true;
(...skipping 1168 matching lines...) Expand 10 before | Expand all | Expand 10 after
5106 } else { 5106 } else {
5107 if (fall_through_block != NULL) fall_through_block->Goto(break_block); 5107 if (fall_through_block != NULL) fall_through_block->Goto(break_block);
5108 if (last_block != NULL) last_block->Goto(break_block); 5108 if (last_block != NULL) last_block->Goto(break_block);
5109 break_block->SetJoinId(stmt->ExitId()); 5109 break_block->SetJoinId(stmt->ExitId());
5110 set_current_block(break_block); 5110 set_current_block(break_block);
5111 } 5111 }
5112 } 5112 }
5113 5113
5114 5114
5115 bool HOptimizedGraphBuilder::HasOsrEntryAt(IterationStatement* statement) { 5115 bool HOptimizedGraphBuilder::HasOsrEntryAt(IterationStatement* statement) {
5116 return statement->OsrEntryId() == current_info()->osr_ast_id(); 5116 return statement->OsrEntryId() == info()->osr_ast_id();
5117 } 5117 }
5118 5118
5119 5119
5120 bool HOptimizedGraphBuilder::PreProcessOsrEntry(IterationStatement* statement) { 5120 bool HOptimizedGraphBuilder::PreProcessOsrEntry(IterationStatement* statement) {
5121 if (!HasOsrEntryAt(statement)) return false; 5121 if (!HasOsrEntryAt(statement)) return false;
5122 5122
5123 HBasicBlock* non_osr_entry = graph()->CreateBasicBlock(); 5123 HBasicBlock* non_osr_entry = graph()->CreateBasicBlock();
5124 HBasicBlock* osr_entry = graph()->CreateBasicBlock(); 5124 HBasicBlock* osr_entry = graph()->CreateBasicBlock();
5125 HValue* true_value = graph()->GetConstantTrue(); 5125 HValue* true_value = graph()->GetConstantTrue();
5126 HBranch* test = new(zone()) HBranch(true_value, non_osr_entry, osr_entry); 5126 HBranch* test = new(zone()) HBranch(true_value, non_osr_entry, osr_entry);
(...skipping 366 matching lines...) Expand 10 before | Expand all | Expand 10 after
5493 5493
5494 return Handle<SharedFunctionInfo>(); 5494 return Handle<SharedFunctionInfo>();
5495 } 5495 }
5496 5496
5497 5497
5498 void HOptimizedGraphBuilder::VisitFunctionLiteral(FunctionLiteral* expr) { 5498 void HOptimizedGraphBuilder::VisitFunctionLiteral(FunctionLiteral* expr) {
5499 ASSERT(!HasStackOverflow()); 5499 ASSERT(!HasStackOverflow());
5500 ASSERT(current_block() != NULL); 5500 ASSERT(current_block() != NULL);
5501 ASSERT(current_block()->HasPredecessor()); 5501 ASSERT(current_block()->HasPredecessor());
5502 Handle<SharedFunctionInfo> shared_info = 5502 Handle<SharedFunctionInfo> shared_info =
5503 SearchSharedFunctionInfo(current_info()->shared_info()->code(), expr); 5503 SearchSharedFunctionInfo(info()->shared_info()->code(), expr);
5504 if (shared_info.is_null()) { 5504 if (shared_info.is_null()) {
5505 shared_info = Compiler::BuildFunctionInfo(expr, current_info()->script()); 5505 shared_info = Compiler::BuildFunctionInfo(expr, info()->script());
5506 } 5506 }
5507 // We also have a stack overflow if the recursive compilation did. 5507 // We also have a stack overflow if the recursive compilation did.
5508 if (HasStackOverflow()) return; 5508 if (HasStackOverflow()) return;
5509 HValue* context = environment()->LookupContext(); 5509 HValue* context = environment()->LookupContext();
5510 HFunctionLiteral* instr = 5510 HFunctionLiteral* instr =
5511 new(zone()) HFunctionLiteral(context, shared_info, expr->pretenure()); 5511 new(zone()) HFunctionLiteral(context, shared_info, expr->pretenure());
5512 return ast_context()->ReturnInstruction(instr, expr->id()); 5512 return ast_context()->ReturnInstruction(instr, expr->id());
5513 } 5513 }
5514 5514
5515 5515
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
5556 if (join != NULL && !ast_context()->IsEffect()) { 5556 if (join != NULL && !ast_context()->IsEffect()) {
5557 return ast_context()->ReturnValue(Pop()); 5557 return ast_context()->ReturnValue(Pop());
5558 } 5558 }
5559 } 5559 }
5560 } 5560 }
5561 5561
5562 5562
5563 HOptimizedGraphBuilder::GlobalPropertyAccess 5563 HOptimizedGraphBuilder::GlobalPropertyAccess
5564 HOptimizedGraphBuilder::LookupGlobalProperty( 5564 HOptimizedGraphBuilder::LookupGlobalProperty(
5565 Variable* var, LookupResult* lookup, bool is_store) { 5565 Variable* var, LookupResult* lookup, bool is_store) {
5566 if (var->is_this() || !current_info()->has_global_object()) { 5566 if (var->is_this() || !info()->has_global_object()) {
5567 return kUseGeneric; 5567 return kUseGeneric;
5568 } 5568 }
5569 Handle<GlobalObject> global(current_info()->global_object()); 5569 Handle<GlobalObject> global(info()->global_object());
5570 global->Lookup(*var->name(), lookup); 5570 global->Lookup(*var->name(), lookup);
5571 if (!lookup->IsNormal() || 5571 if (!lookup->IsNormal() ||
5572 (is_store && lookup->IsReadOnly()) || 5572 (is_store && lookup->IsReadOnly()) ||
5573 lookup->holder() != *global) { 5573 lookup->holder() != *global) {
5574 return kUseGeneric; 5574 return kUseGeneric;
5575 } 5575 }
5576 5576
5577 return kUseCell; 5577 return kUseCell;
5578 } 5578 }
5579 5579
5580 5580
5581 HValue* HOptimizedGraphBuilder::BuildContextChainWalk(Variable* var) { 5581 HValue* HOptimizedGraphBuilder::BuildContextChainWalk(Variable* var) {
5582 ASSERT(var->IsContextSlot()); 5582 ASSERT(var->IsContextSlot());
5583 HValue* context = environment()->LookupContext(); 5583 HValue* context = environment()->LookupContext();
5584 int length = current_info()->scope()->ContextChainLength(var->scope()); 5584 int length = info()->scope()->ContextChainLength(var->scope());
5585 while (length-- > 0) { 5585 while (length-- > 0) {
5586 HInstruction* context_instruction = new(zone()) HOuterContext(context); 5586 HInstruction* context_instruction = new(zone()) HOuterContext(context);
5587 AddInstruction(context_instruction); 5587 AddInstruction(context_instruction);
5588 context = context_instruction; 5588 context = context_instruction;
5589 } 5589 }
5590 return context; 5590 return context;
5591 } 5591 }
5592 5592
5593 5593
5594 void HOptimizedGraphBuilder::VisitVariableProxy(VariableProxy* expr) { 5594 void HOptimizedGraphBuilder::VisitVariableProxy(VariableProxy* expr) {
(...skipping 15 matching lines...) Expand all
5610 HConstant* instr = 5610 HConstant* instr =
5611 new(zone()) HConstant(constant_value, Representation::Tagged()); 5611 new(zone()) HConstant(constant_value, Representation::Tagged());
5612 return ast_context()->ReturnInstruction(instr, expr->id()); 5612 return ast_context()->ReturnInstruction(instr, expr->id());
5613 } 5613 }
5614 5614
5615 LookupResult lookup(isolate()); 5615 LookupResult lookup(isolate());
5616 GlobalPropertyAccess type = 5616 GlobalPropertyAccess type =
5617 LookupGlobalProperty(variable, &lookup, false); 5617 LookupGlobalProperty(variable, &lookup, false);
5618 5618
5619 if (type == kUseCell && 5619 if (type == kUseCell &&
5620 current_info()->global_object()->IsAccessCheckNeeded()) { 5620 info()->global_object()->IsAccessCheckNeeded()) {
5621 type = kUseGeneric; 5621 type = kUseGeneric;
5622 } 5622 }
5623 5623
5624 if (type == kUseCell) { 5624 if (type == kUseCell) {
5625 Handle<GlobalObject> global(current_info()->global_object()); 5625 Handle<GlobalObject> global(info()->global_object());
5626 Handle<JSGlobalPropertyCell> cell(global->GetPropertyCell(&lookup)); 5626 Handle<JSGlobalPropertyCell> cell(global->GetPropertyCell(&lookup));
5627 HLoadGlobalCell* instr = 5627 HLoadGlobalCell* instr =
5628 new(zone()) HLoadGlobalCell(cell, lookup.GetPropertyDetails()); 5628 new(zone()) HLoadGlobalCell(cell, lookup.GetPropertyDetails());
5629 return ast_context()->ReturnInstruction(instr, expr->id()); 5629 return ast_context()->ReturnInstruction(instr, expr->id());
5630 } else { 5630 } else {
5631 HValue* context = environment()->LookupContext(); 5631 HValue* context = environment()->LookupContext();
5632 HGlobalObject* global_object = new(zone()) HGlobalObject(context); 5632 HGlobalObject* global_object = new(zone()) HGlobalObject(context);
5633 AddInstruction(global_object); 5633 AddInstruction(global_object);
5634 HLoadGlobalGeneric* instr = 5634 HLoadGlobalGeneric* instr =
5635 new(zone()) HLoadGlobalGeneric(context, 5635 new(zone()) HLoadGlobalGeneric(context,
(...skipping 570 matching lines...) Expand 10 before | Expand all | Expand 10 after
6206 // Otherwise, find the top prototype. 6206 // Otherwise, find the top prototype.
6207 while (proto->GetPrototype(isolate())->IsJSObject()) { 6207 while (proto->GetPrototype(isolate())->IsJSObject()) {
6208 proto = proto->GetPrototype(isolate()); 6208 proto = proto->GetPrototype(isolate());
6209 } 6209 }
6210 ASSERT(proto->GetPrototype(isolate())->IsNull()); 6210 ASSERT(proto->GetPrototype(isolate())->IsNull());
6211 } 6211 }
6212 ASSERT(proto->IsJSObject()); 6212 ASSERT(proto->IsJSObject());
6213 AddInstruction(new(zone()) HCheckPrototypeMaps( 6213 AddInstruction(new(zone()) HCheckPrototypeMaps(
6214 Handle<JSObject>(JSObject::cast(map->prototype())), 6214 Handle<JSObject>(JSObject::cast(map->prototype())),
6215 Handle<JSObject>(JSObject::cast(proto)), 6215 Handle<JSObject>(JSObject::cast(proto)),
6216 zone(), 6216 zone()));
6217 top_info()));
6218 } 6217 }
6219 6218
6220 HObjectAccess field_access = HObjectAccess::ForField(map, lookup, name); 6219 HObjectAccess field_access = HObjectAccess::ForField(map, lookup, name);
6221 Representation representation = ComputeLoadStoreRepresentation(map, lookup); 6220 Representation representation = ComputeLoadStoreRepresentation(map, lookup);
6222 bool transition_to_field = lookup->IsTransitionToField(*map); 6221 bool transition_to_field = lookup->IsTransitionToField(*map);
6223 6222
6224 HStoreNamedField *instr; 6223 HStoreNamedField *instr;
6225 if (FLAG_track_double_fields && representation.IsDouble()) { 6224 if (FLAG_track_double_fields && representation.IsDouble()) {
6226 if (transition_to_field) { 6225 if (transition_to_field) {
6227 // The store requires a mutable HeapNumber to be allocated. 6226 // The store requires a mutable HeapNumber to be allocated.
(...skipping 15 matching lines...) Expand all
6243 HObjectAccess::ForHeapNumberValue(), value, Representation::Double()); 6242 HObjectAccess::ForHeapNumberValue(), value, Representation::Double());
6244 } 6243 }
6245 } else { 6244 } else {
6246 // This is a non-double store. 6245 // This is a non-double store.
6247 instr = new(zone()) HStoreNamedField( 6246 instr = new(zone()) HStoreNamedField(
6248 object, field_access, value, representation); 6247 object, field_access, value, representation);
6249 } 6248 }
6250 6249
6251 if (transition_to_field) { 6250 if (transition_to_field) {
6252 Handle<Map> transition(lookup->GetTransitionMapFromMap(*map)); 6251 Handle<Map> transition(lookup->GetTransitionMapFromMap(*map));
6253 instr->SetTransition(transition, top_info()); 6252 instr->set_transition(transition);
6254 // TODO(fschneider): Record the new map type of the object in the IR to 6253 // TODO(fschneider): Record the new map type of the object in the IR to
6255 // enable elimination of redundant checks after the transition store. 6254 // enable elimination of redundant checks after the transition store.
6256 instr->SetGVNFlag(kChangesMaps); 6255 instr->SetGVNFlag(kChangesMaps);
6257 } 6256 }
6258 return instr; 6257 return instr;
6259 } 6258 }
6260 6259
6261 6260
6262 HInstruction* HOptimizedGraphBuilder::BuildStoreNamedGeneric( 6261 HInstruction* HOptimizedGraphBuilder::BuildStoreNamedGeneric(
6263 HValue* object, 6262 HValue* object,
(...skipping 282 matching lines...) Expand 10 before | Expand all | Expand 10 after
6546 // superclass of Assignment and CountOperation, we cannot just pass the 6545 // superclass of Assignment and CountOperation, we cannot just pass the
6547 // owning expression instead of position and ast_id separately. 6546 // owning expression instead of position and ast_id separately.
6548 void HOptimizedGraphBuilder::HandleGlobalVariableAssignment( 6547 void HOptimizedGraphBuilder::HandleGlobalVariableAssignment(
6549 Variable* var, 6548 Variable* var,
6550 HValue* value, 6549 HValue* value,
6551 int position, 6550 int position,
6552 BailoutId ast_id) { 6551 BailoutId ast_id) {
6553 LookupResult lookup(isolate()); 6552 LookupResult lookup(isolate());
6554 GlobalPropertyAccess type = LookupGlobalProperty(var, &lookup, true); 6553 GlobalPropertyAccess type = LookupGlobalProperty(var, &lookup, true);
6555 if (type == kUseCell) { 6554 if (type == kUseCell) {
6556 Handle<GlobalObject> global(current_info()->global_object()); 6555 Handle<GlobalObject> global(info()->global_object());
6557 Handle<JSGlobalPropertyCell> cell(global->GetPropertyCell(&lookup)); 6556 Handle<JSGlobalPropertyCell> cell(global->GetPropertyCell(&lookup));
6558 HInstruction* instr = 6557 HInstruction* instr =
6559 new(zone()) HStoreGlobalCell(value, cell, lookup.GetPropertyDetails()); 6558 new(zone()) HStoreGlobalCell(value, cell, lookup.GetPropertyDetails());
6560 instr->set_position(position); 6559 instr->set_position(position);
6561 AddInstruction(instr); 6560 AddInstruction(instr);
6562 if (instr->HasObservableSideEffects()) { 6561 if (instr->HasObservableSideEffects()) {
6563 AddSimulate(ast_id, REMOVABLE_SIMULATE); 6562 AddSimulate(ast_id, REMOVABLE_SIMULATE);
6564 } 6563 }
6565 } else { 6564 } else {
6566 HValue* context = environment()->LookupContext(); 6565 HValue* context = environment()->LookupContext();
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
6611 if (var->mode() == CONST) { 6610 if (var->mode() == CONST) {
6612 return Bailout("unsupported const compound assignment"); 6611 return Bailout("unsupported const compound assignment");
6613 } 6612 }
6614 BindIfLive(var, Top()); 6613 BindIfLive(var, Top());
6615 break; 6614 break;
6616 6615
6617 case Variable::CONTEXT: { 6616 case Variable::CONTEXT: {
6618 // Bail out if we try to mutate a parameter value in a function 6617 // Bail out if we try to mutate a parameter value in a function
6619 // using the arguments object. We do not (yet) correctly handle the 6618 // using the arguments object. We do not (yet) correctly handle the
6620 // arguments property of the function. 6619 // arguments property of the function.
6621 if (current_info()->scope()->arguments() != NULL) { 6620 if (info()->scope()->arguments() != NULL) {
6622 // Parameters will be allocated to context slots. We have no 6621 // Parameters will be allocated to context slots. We have no
6623 // direct way to detect that the variable is a parameter so we do 6622 // direct way to detect that the variable is a parameter so we do
6624 // a linear search of the parameter variables. 6623 // a linear search of the parameter variables.
6625 int count = current_info()->scope()->num_parameters(); 6624 int count = info()->scope()->num_parameters();
6626 for (int i = 0; i < count; ++i) { 6625 for (int i = 0; i < count; ++i) {
6627 if (var == current_info()->scope()->parameter(i)) { 6626 if (var == info()->scope()->parameter(i)) {
6628 Bailout( 6627 Bailout(
6629 "assignment to parameter, function uses arguments object"); 6628 "assignment to parameter, function uses arguments object");
6630 } 6629 }
6631 } 6630 }
6632 } 6631 }
6633 6632
6634 HStoreContextSlot::Mode mode; 6633 HStoreContextSlot::Mode mode;
6635 6634
6636 switch (var->mode()) { 6635 switch (var->mode()) {
6637 case LET: 6636 case LET:
(...skipping 199 matching lines...) Expand 10 before | Expand all | Expand 10 after
6837 CHECK_ALIVE(VisitForValue(expr->value(), ARGUMENTS_ALLOWED)); 6836 CHECK_ALIVE(VisitForValue(expr->value(), ARGUMENTS_ALLOWED));
6838 HValue* value = Pop(); 6837 HValue* value = Pop();
6839 BindIfLive(var, value); 6838 BindIfLive(var, value);
6840 return ast_context()->ReturnValue(value); 6839 return ast_context()->ReturnValue(value);
6841 } 6840 }
6842 6841
6843 case Variable::CONTEXT: { 6842 case Variable::CONTEXT: {
6844 // Bail out if we try to mutate a parameter value in a function using 6843 // Bail out if we try to mutate a parameter value in a function using
6845 // the arguments object. We do not (yet) correctly handle the 6844 // the arguments object. We do not (yet) correctly handle the
6846 // arguments property of the function. 6845 // arguments property of the function.
6847 if (current_info()->scope()->arguments() != NULL) { 6846 if (info()->scope()->arguments() != NULL) {
6848 // Parameters will rewrite to context slots. We have no direct way 6847 // Parameters will rewrite to context slots. We have no direct way
6849 // to detect that the variable is a parameter. 6848 // to detect that the variable is a parameter.
6850 int count = current_info()->scope()->num_parameters(); 6849 int count = info()->scope()->num_parameters();
6851 for (int i = 0; i < count; ++i) { 6850 for (int i = 0; i < count; ++i) {
6852 if (var == current_info()->scope()->parameter(i)) { 6851 if (var == info()->scope()->parameter(i)) {
6853 return Bailout("assignment to parameter in arguments object"); 6852 return Bailout("assignment to parameter in arguments object");
6854 } 6853 }
6855 } 6854 }
6856 } 6855 }
6857 6856
6858 CHECK_ALIVE(VisitForValue(expr->value())); 6857 CHECK_ALIVE(VisitForValue(expr->value()));
6859 HStoreContextSlot::Mode mode; 6858 HStoreContextSlot::Mode mode;
6860 if (expr->op() == Token::ASSIGN) { 6859 if (expr->op() == Token::ASSIGN) {
6861 switch (var->mode()) { 6860 switch (var->mode()) {
6862 case LET: 6861 case LET:
(...skipping 141 matching lines...) Expand 10 before | Expand all | Expand 10 after
7004 return new(zone()) HConstant(function, Representation::Tagged()); 7003 return new(zone()) HConstant(function, Representation::Tagged());
7005 } 7004 }
7006 7005
7007 // Handle a load from a known field somewhere in the prototype chain. 7006 // Handle a load from a known field somewhere in the prototype chain.
7008 LookupInPrototypes(map, name, &lookup); 7007 LookupInPrototypes(map, name, &lookup);
7009 if (lookup.IsField()) { 7008 if (lookup.IsField()) {
7010 Handle<JSObject> prototype(JSObject::cast(map->prototype())); 7009 Handle<JSObject> prototype(JSObject::cast(map->prototype()));
7011 Handle<JSObject> holder(lookup.holder()); 7010 Handle<JSObject> holder(lookup.holder());
7012 Handle<Map> holder_map(holder->map()); 7011 Handle<Map> holder_map(holder->map());
7013 AddCheckMap(object, map); 7012 AddCheckMap(object, map);
7014 AddInstruction(new(zone()) HCheckPrototypeMaps( 7013 AddInstruction(
7015 prototype, holder, zone(), top_info())); 7014 new(zone()) HCheckPrototypeMaps(prototype, holder, zone()));
7016 HValue* holder_value = AddInstruction(new(zone()) 7015 HValue* holder_value = AddInstruction(new(zone())
7017 HConstant(holder, Representation::Tagged())); 7016 HConstant(holder, Representation::Tagged()));
7018 return BuildLoadNamedField(holder_value, 7017 return BuildLoadNamedField(holder_value,
7019 HObjectAccess::ForField(holder_map, &lookup, name), 7018 HObjectAccess::ForField(holder_map, &lookup, name),
7020 ComputeLoadStoreRepresentation(map, &lookup)); 7019 ComputeLoadStoreRepresentation(map, &lookup));
7021 } 7020 }
7022 7021
7023 // Handle a load of a constant function somewhere in the prototype chain. 7022 // Handle a load of a constant function somewhere in the prototype chain.
7024 if (lookup.IsConstantFunction()) { 7023 if (lookup.IsConstantFunction()) {
7025 Handle<JSObject> prototype(JSObject::cast(map->prototype())); 7024 Handle<JSObject> prototype(JSObject::cast(map->prototype()));
7026 Handle<JSObject> holder(lookup.holder()); 7025 Handle<JSObject> holder(lookup.holder());
7027 Handle<Map> holder_map(holder->map()); 7026 Handle<Map> holder_map(holder->map());
7028 AddCheckMap(object, map); 7027 AddCheckMap(object, map);
7029 AddInstruction(new(zone()) HCheckPrototypeMaps( 7028 AddInstruction(new(zone()) HCheckPrototypeMaps(prototype, holder, zone()));
7030 prototype, holder, zone(), top_info()));
7031 Handle<JSFunction> function(lookup.GetConstantFunctionFromMap(*holder_map)); 7029 Handle<JSFunction> function(lookup.GetConstantFunctionFromMap(*holder_map));
7032 return new(zone()) HConstant(function, Representation::Tagged()); 7030 return new(zone()) HConstant(function, Representation::Tagged());
7033 } 7031 }
7034 7032
7035 // No luck, do a generic load. 7033 // No luck, do a generic load.
7036 return BuildLoadNamedGeneric(object, name, expr); 7034 return BuildLoadNamedGeneric(object, name, expr);
7037 } 7035 }
7038 7036
7039 7037
7040 HInstruction* HOptimizedGraphBuilder::BuildLoadKeyedGeneric(HValue* object, 7038 HInstruction* HOptimizedGraphBuilder::BuildLoadKeyedGeneric(HValue* object,
(...skipping 16 matching lines...) Expand all
7057 if (dependency) { 7055 if (dependency) {
7058 mapcheck->ClearGVNFlag(kDependsOnElementsKind); 7056 mapcheck->ClearGVNFlag(kDependsOnElementsKind);
7059 } 7057 }
7060 7058
7061 // Loads from a "stock" fast holey double arrays can elide the hole check. 7059 // Loads from a "stock" fast holey double arrays can elide the hole check.
7062 LoadKeyedHoleMode load_mode = NEVER_RETURN_HOLE; 7060 LoadKeyedHoleMode load_mode = NEVER_RETURN_HOLE;
7063 if (*map == isolate()->get_initial_js_array_map(FAST_HOLEY_DOUBLE_ELEMENTS) && 7061 if (*map == isolate()->get_initial_js_array_map(FAST_HOLEY_DOUBLE_ELEMENTS) &&
7064 isolate()->IsFastArrayConstructorPrototypeChainIntact()) { 7062 isolate()->IsFastArrayConstructorPrototypeChainIntact()) {
7065 Handle<JSObject> prototype(JSObject::cast(map->prototype()), isolate()); 7063 Handle<JSObject> prototype(JSObject::cast(map->prototype()), isolate());
7066 Handle<JSObject> object_prototype = isolate()->initial_object_prototype(); 7064 Handle<JSObject> object_prototype = isolate()->initial_object_prototype();
7067 AddInstruction(new(zone()) HCheckPrototypeMaps( 7065 AddInstruction(
7068 prototype, object_prototype, zone(), top_info())); 7066 new(zone()) HCheckPrototypeMaps(prototype, object_prototype, zone()));
7069 load_mode = ALLOW_RETURN_HOLE; 7067 load_mode = ALLOW_RETURN_HOLE;
7070 graph()->MarkDependsOnEmptyArrayProtoElements(); 7068 graph()->MarkDependsOnEmptyArrayProtoElements();
7071 } 7069 }
7072 7070
7073 return BuildUncheckedMonomorphicElementAccess( 7071 return BuildUncheckedMonomorphicElementAccess(
7074 object, key, val, 7072 object, key, val,
7075 mapcheck, map->instance_type() == JS_ARRAY_TYPE, 7073 mapcheck, map->instance_type() == JS_ARRAY_TYPE,
7076 map->elements_kind(), is_store, load_mode, store_mode); 7074 map->elements_kind(), is_store, load_mode, store_mode);
7077 } 7075 }
7078 7076
(...skipping 494 matching lines...) Expand 10 before | Expand all | Expand 10 after
7573 } 7571 }
7574 instr->set_position(expr->position()); 7572 instr->set_position(expr->position());
7575 return ast_context()->ReturnInstruction(instr, expr->id()); 7573 return ast_context()->ReturnInstruction(instr, expr->id());
7576 } 7574 }
7577 7575
7578 7576
7579 void HOptimizedGraphBuilder::AddCheckPrototypeMaps(Handle<JSObject> holder, 7577 void HOptimizedGraphBuilder::AddCheckPrototypeMaps(Handle<JSObject> holder,
7580 Handle<Map> receiver_map) { 7578 Handle<Map> receiver_map) {
7581 if (!holder.is_null()) { 7579 if (!holder.is_null()) {
7582 Handle<JSObject> prototype(JSObject::cast(receiver_map->prototype())); 7580 Handle<JSObject> prototype(JSObject::cast(receiver_map->prototype()));
7583 AddInstruction(new(zone()) HCheckPrototypeMaps( 7581 AddInstruction(
7584 prototype, holder, zone(), top_info())); 7582 new(zone()) HCheckPrototypeMaps(prototype, holder, zone()));
7585 } 7583 }
7586 } 7584 }
7587 7585
7588 7586
7589 void HOptimizedGraphBuilder::AddCheckConstantFunction( 7587 void HOptimizedGraphBuilder::AddCheckConstantFunction(
7590 Handle<JSObject> holder, 7588 Handle<JSObject> holder,
7591 HValue* receiver, 7589 HValue* receiver,
7592 Handle<Map> receiver_map) { 7590 Handle<Map> receiver_map) {
7593 // Constant functions have the nice property that the map will change if they 7591 // Constant functions have the nice property that the map will change if they
7594 // are overwritten. Therefore it is enough to check the map of the holder and 7592 // are overwritten. Therefore it is enough to check the map of the holder and
(...skipping 124 matching lines...) Expand 10 before | Expand all | Expand 10 after
7719 if (expr->check_type() == NUMBER_CHECK) { 7717 if (expr->check_type() == NUMBER_CHECK) {
7720 if_true->Goto(number_block); 7718 if_true->Goto(number_block);
7721 if_true = number_block; 7719 if_true = number_block;
7722 number_block->SetJoinId(expr->id()); 7720 number_block->SetJoinId(expr->id());
7723 } 7721 }
7724 set_current_block(if_true); 7722 set_current_block(if_true);
7725 7723
7726 expr->ComputeTarget(map, name); 7724 expr->ComputeTarget(map, name);
7727 AddCheckPrototypeMaps(expr->holder(), map); 7725 AddCheckPrototypeMaps(expr->holder(), map);
7728 if (FLAG_trace_inlining && FLAG_polymorphic_inlining) { 7726 if (FLAG_trace_inlining && FLAG_polymorphic_inlining) {
7729 Handle<JSFunction> caller = current_info()->closure(); 7727 Handle<JSFunction> caller = info()->closure();
7730 SmartArrayPointer<char> caller_name = 7728 SmartArrayPointer<char> caller_name =
7731 caller->shared()->DebugName()->ToCString(); 7729 caller->shared()->DebugName()->ToCString();
7732 PrintF("Trying to inline the polymorphic call to %s from %s\n", 7730 PrintF("Trying to inline the polymorphic call to %s from %s\n",
7733 *name->ToCString(), 7731 *name->ToCString(),
7734 *caller_name); 7732 *caller_name);
7735 } 7733 }
7736 if (FLAG_polymorphic_inlining && TryInlineCall(expr)) { 7734 if (FLAG_polymorphic_inlining && TryInlineCall(expr)) {
7737 // Trying to inline will signal that we should bailout from the 7735 // Trying to inline will signal that we should bailout from the
7738 // entire compilation by setting stack overflow on the visitor. 7736 // entire compilation by setting stack overflow on the visitor.
7739 if (HasStackOverflow()) return; 7737 if (HasStackOverflow()) return;
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after
7803 7801
7804 7802
7805 static const int kNotInlinable = 1000000000; 7803 static const int kNotInlinable = 1000000000;
7806 7804
7807 7805
7808 int HOptimizedGraphBuilder::InliningAstSize(Handle<JSFunction> target) { 7806 int HOptimizedGraphBuilder::InliningAstSize(Handle<JSFunction> target) {
7809 if (!FLAG_use_inlining) return kNotInlinable; 7807 if (!FLAG_use_inlining) return kNotInlinable;
7810 7808
7811 // Precondition: call is monomorphic and we have found a target with the 7809 // Precondition: call is monomorphic and we have found a target with the
7812 // appropriate arity. 7810 // appropriate arity.
7813 Handle<JSFunction> caller = current_info()->closure(); 7811 Handle<JSFunction> caller = info()->closure();
7814 Handle<SharedFunctionInfo> target_shared(target->shared()); 7812 Handle<SharedFunctionInfo> target_shared(target->shared());
7815 7813
7816 // Do a quick check on source code length to avoid parsing large 7814 // Do a quick check on source code length to avoid parsing large
7817 // inlining candidates. 7815 // inlining candidates.
7818 if (target_shared->SourceSize() > 7816 if (target_shared->SourceSize() >
7819 Min(FLAG_max_inlined_source_size, kUnlimitedMaxInlinedSourceSize)) { 7817 Min(FLAG_max_inlined_source_size, kUnlimitedMaxInlinedSourceSize)) {
7820 TraceInline(target, caller, "target text too big"); 7818 TraceInline(target, caller, "target text too big");
7821 return kNotInlinable; 7819 return kNotInlinable;
7822 } 7820 }
7823 7821
(...skipping 15 matching lines...) Expand all
7839 bool HOptimizedGraphBuilder::TryInline(CallKind call_kind, 7837 bool HOptimizedGraphBuilder::TryInline(CallKind call_kind,
7840 Handle<JSFunction> target, 7838 Handle<JSFunction> target,
7841 int arguments_count, 7839 int arguments_count,
7842 HValue* implicit_return_value, 7840 HValue* implicit_return_value,
7843 BailoutId ast_id, 7841 BailoutId ast_id,
7844 BailoutId return_id, 7842 BailoutId return_id,
7845 InliningKind inlining_kind) { 7843 InliningKind inlining_kind) {
7846 int nodes_added = InliningAstSize(target); 7844 int nodes_added = InliningAstSize(target);
7847 if (nodes_added == kNotInlinable) return false; 7845 if (nodes_added == kNotInlinable) return false;
7848 7846
7849 Handle<JSFunction> caller = current_info()->closure(); 7847 Handle<JSFunction> caller = info()->closure();
7850 7848
7851 if (nodes_added > Min(FLAG_max_inlined_nodes, kUnlimitedMaxInlinedNodes)) { 7849 if (nodes_added > Min(FLAG_max_inlined_nodes, kUnlimitedMaxInlinedNodes)) {
7852 TraceInline(target, caller, "target AST is too large [early]"); 7850 TraceInline(target, caller, "target AST is too large [early]");
7853 return false; 7851 return false;
7854 } 7852 }
7855 7853
7856 #if !defined(V8_TARGET_ARCH_IA32) 7854 #if !defined(V8_TARGET_ARCH_IA32)
7857 // Target must be able to use caller's context. 7855 // Target must be able to use caller's context.
7858 CompilationInfo* outer_info = current_info(); 7856 CompilationInfo* outer_info = info();
7859 if (target->context() != outer_info->closure()->context() || 7857 if (target->context() != outer_info->closure()->context() ||
7860 outer_info->scope()->contains_with() || 7858 outer_info->scope()->contains_with() ||
7861 outer_info->scope()->num_heap_slots() > 0) { 7859 outer_info->scope()->num_heap_slots() > 0) {
7862 TraceInline(target, caller, "target requires context change"); 7860 TraceInline(target, caller, "target requires context change");
7863 return false; 7861 return false;
7864 } 7862 }
7865 #endif 7863 #endif
7866 7864
7867 7865
7868 // Don't inline deeper than kMaxInliningLevels calls. 7866 // Don't inline deeper than kMaxInliningLevels calls.
(...skipping 414 matching lines...) Expand 10 before | Expand all | Expand 10 after
8283 case kStringCharAt: 8281 case kStringCharAt:
8284 if (argument_count == 2 && check_type == STRING_CHECK) { 8282 if (argument_count == 2 && check_type == STRING_CHECK) {
8285 HValue* index = Pop(); 8283 HValue* index = Pop();
8286 HValue* string = Pop(); 8284 HValue* string = Pop();
8287 HValue* context = environment()->LookupContext(); 8285 HValue* context = environment()->LookupContext();
8288 ASSERT(!expr->holder().is_null()); 8286 ASSERT(!expr->holder().is_null());
8289 AddInstruction(new(zone()) HCheckPrototypeMaps( 8287 AddInstruction(new(zone()) HCheckPrototypeMaps(
8290 Call::GetPrototypeForPrimitiveCheck(STRING_CHECK, 8288 Call::GetPrototypeForPrimitiveCheck(STRING_CHECK,
8291 expr->holder()->GetIsolate()), 8289 expr->holder()->GetIsolate()),
8292 expr->holder(), 8290 expr->holder(),
8293 zone(), 8291 zone()));
8294 top_info()));
8295 HInstruction* char_code = 8292 HInstruction* char_code =
8296 BuildStringCharCodeAt(context, string, index); 8293 BuildStringCharCodeAt(context, string, index);
8297 if (id == kStringCharCodeAt) { 8294 if (id == kStringCharCodeAt) {
8298 ast_context()->ReturnInstruction(char_code, expr->id()); 8295 ast_context()->ReturnInstruction(char_code, expr->id());
8299 return true; 8296 return true;
8300 } 8297 }
8301 AddInstruction(char_code); 8298 AddInstruction(char_code);
8302 HInstruction* result = 8299 HInstruction* result =
8303 HStringCharFromCode::New(zone(), context, char_code); 8300 HStringCharFromCode::New(zone(), context, char_code);
8304 ast_context()->ReturnInstruction(result, expr->id()); 8301 ast_context()->ReturnInstruction(result, expr->id());
(...skipping 130 matching lines...) Expand 10 before | Expand all | Expand 10 after
8435 if (!expr->IsMonomorphic() || expr->check_type() != RECEIVER_MAP_CHECK) { 8432 if (!expr->IsMonomorphic() || expr->check_type() != RECEIVER_MAP_CHECK) {
8436 return false; 8433 return false;
8437 } 8434 }
8438 Handle<Map> function_map = expr->GetReceiverTypes()->first(); 8435 Handle<Map> function_map = expr->GetReceiverTypes()->first();
8439 if (function_map->instance_type() != JS_FUNCTION_TYPE || 8436 if (function_map->instance_type() != JS_FUNCTION_TYPE ||
8440 !expr->target()->shared()->HasBuiltinFunctionId() || 8437 !expr->target()->shared()->HasBuiltinFunctionId() ||
8441 expr->target()->shared()->builtin_function_id() != kFunctionApply) { 8438 expr->target()->shared()->builtin_function_id() != kFunctionApply) {
8442 return false; 8439 return false;
8443 } 8440 }
8444 8441
8445 if (current_info()->scope()->arguments() == NULL) return false; 8442 if (info()->scope()->arguments() == NULL) return false;
8446 8443
8447 ZoneList<Expression*>* args = expr->arguments(); 8444 ZoneList<Expression*>* args = expr->arguments();
8448 if (args->length() != 2) return false; 8445 if (args->length() != 2) return false;
8449 8446
8450 VariableProxy* arg_two = args->at(1)->AsVariableProxy(); 8447 VariableProxy* arg_two = args->at(1)->AsVariableProxy();
8451 if (arg_two == NULL || !arg_two->var()->IsStackAllocated()) return false; 8448 if (arg_two == NULL || !arg_two->var()->IsStackAllocated()) return false;
8452 HValue* arg_two_value = LookupAndMakeLive(arg_two->var()); 8449 HValue* arg_two_value = LookupAndMakeLive(arg_two->var());
8453 if (!arg_two_value->CheckFlag(HValue::kIsArguments)) return false; 8450 if (!arg_two_value->CheckFlag(HValue::kIsArguments)) return false;
8454 8451
8455 // Found pattern f.apply(receiver, arguments). 8452 // Found pattern f.apply(receiver, arguments).
(...skipping 220 matching lines...) Expand 10 before | Expand all | Expand 10 after
8676 8673
8677 if (global_call) { 8674 if (global_call) {
8678 Variable* var = proxy->var(); 8675 Variable* var = proxy->var();
8679 bool known_global_function = false; 8676 bool known_global_function = false;
8680 // If there is a global property cell for the name at compile time and 8677 // If there is a global property cell for the name at compile time and
8681 // access check is not enabled we assume that the function will not change 8678 // access check is not enabled we assume that the function will not change
8682 // and generate optimized code for calling the function. 8679 // and generate optimized code for calling the function.
8683 LookupResult lookup(isolate()); 8680 LookupResult lookup(isolate());
8684 GlobalPropertyAccess type = LookupGlobalProperty(var, &lookup, false); 8681 GlobalPropertyAccess type = LookupGlobalProperty(var, &lookup, false);
8685 if (type == kUseCell && 8682 if (type == kUseCell &&
8686 !current_info()->global_object()->IsAccessCheckNeeded()) { 8683 !info()->global_object()->IsAccessCheckNeeded()) {
8687 Handle<GlobalObject> global(current_info()->global_object()); 8684 Handle<GlobalObject> global(info()->global_object());
8688 known_global_function = expr->ComputeGlobalTarget(global, &lookup); 8685 known_global_function = expr->ComputeGlobalTarget(global, &lookup);
8689 } 8686 }
8690 if (known_global_function) { 8687 if (known_global_function) {
8691 // Push the global object instead of the global receiver because 8688 // Push the global object instead of the global receiver because
8692 // code generated by the full code generator expects it. 8689 // code generated by the full code generator expects it.
8693 HValue* context = environment()->LookupContext(); 8690 HValue* context = environment()->LookupContext();
8694 HGlobalObject* global_object = new(zone()) HGlobalObject(context); 8691 HGlobalObject* global_object = new(zone()) HGlobalObject(context);
8695 PushAndAdd(global_object); 8692 PushAndAdd(global_object);
8696 CHECK_ALIVE(VisitExpressions(expr->arguments())); 8693 CHECK_ALIVE(VisitExpressions(expr->arguments()));
8697 8694
(...skipping 14 matching lines...) Expand all
8712 if (TryInlineBuiltinFunctionCall(expr, false)) { // Nothing to drop. 8709 if (TryInlineBuiltinFunctionCall(expr, false)) { // Nothing to drop.
8713 if (FLAG_trace_inlining) { 8710 if (FLAG_trace_inlining) {
8714 PrintF("Inlining builtin "); 8711 PrintF("Inlining builtin ");
8715 expr->target()->ShortPrint(); 8712 expr->target()->ShortPrint();
8716 PrintF("\n"); 8713 PrintF("\n");
8717 } 8714 }
8718 return; 8715 return;
8719 } 8716 }
8720 if (TryInlineCall(expr)) return; 8717 if (TryInlineCall(expr)) return;
8721 8718
8722 if (expr->target().is_identical_to(current_info()->closure())) { 8719 if (expr->target().is_identical_to(info()->closure())) {
8723 graph()->MarkRecursive(); 8720 graph()->MarkRecursive();
8724 } 8721 }
8725 8722
8726 call = PreProcessCall(new(zone()) HCallKnownGlobal(expr->target(), 8723 call = PreProcessCall(new(zone()) HCallKnownGlobal(expr->target(),
8727 argument_count)); 8724 argument_count));
8728 } else { 8725 } else {
8729 HValue* context = environment()->LookupContext(); 8726 HValue* context = environment()->LookupContext();
8730 HGlobalObject* receiver = new(zone()) HGlobalObject(context); 8727 HGlobalObject* receiver = new(zone()) HGlobalObject(context);
8731 AddInstruction(receiver); 8728 AddInstruction(receiver);
8732 PushAndAdd(new(zone()) HPushArgument(receiver)); 8729 PushAndAdd(new(zone()) HPushArgument(receiver));
(...skipping 478 matching lines...) Expand 10 before | Expand all | Expand 10 after
9211 9208
9212 case Variable::PARAMETER: 9209 case Variable::PARAMETER:
9213 case Variable::LOCAL: 9210 case Variable::LOCAL:
9214 BindIfLive(var, after); 9211 BindIfLive(var, after);
9215 break; 9212 break;
9216 9213
9217 case Variable::CONTEXT: { 9214 case Variable::CONTEXT: {
9218 // Bail out if we try to mutate a parameter value in a function 9215 // Bail out if we try to mutate a parameter value in a function
9219 // using the arguments object. We do not (yet) correctly handle the 9216 // using the arguments object. We do not (yet) correctly handle the
9220 // arguments property of the function. 9217 // arguments property of the function.
9221 if (current_info()->scope()->arguments() != NULL) { 9218 if (info()->scope()->arguments() != NULL) {
9222 // Parameters will rewrite to context slots. We have no direct 9219 // Parameters will rewrite to context slots. We have no direct
9223 // way to detect that the variable is a parameter so we use a 9220 // way to detect that the variable is a parameter so we use a
9224 // linear search of the parameter list. 9221 // linear search of the parameter list.
9225 int count = current_info()->scope()->num_parameters(); 9222 int count = info()->scope()->num_parameters();
9226 for (int i = 0; i < count; ++i) { 9223 for (int i = 0; i < count; ++i) {
9227 if (var == current_info()->scope()->parameter(i)) { 9224 if (var == info()->scope()->parameter(i)) {
9228 return Bailout("assignment to parameter in arguments object"); 9225 return Bailout("assignment to parameter in arguments object");
9229 } 9226 }
9230 } 9227 }
9231 } 9228 }
9232 9229
9233 HValue* context = BuildContextChainWalk(var); 9230 HValue* context = BuildContextChainWalk(var);
9234 HStoreContextSlot::Mode mode = IsLexicalVariableMode(var->mode()) 9231 HStoreContextSlot::Mode mode = IsLexicalVariableMode(var->mode())
9235 ? HStoreContextSlot::kCheckDeoptimize : HStoreContextSlot::kNoCheck; 9232 ? HStoreContextSlot::kCheckDeoptimize : HStoreContextSlot::kNoCheck;
9236 HStoreContextSlot* instr = 9233 HStoreContextSlot* instr =
9237 new(zone()) HStoreContextSlot(context, var->index(), mode, after); 9234 new(zone()) HStoreContextSlot(context, var->index(), mode, after);
(...skipping 578 matching lines...) Expand 10 before | Expand all | Expand 10 after
9816 } 9813 }
9817 9814
9818 if (op == Token::INSTANCEOF) { 9815 if (op == Token::INSTANCEOF) {
9819 // Check to see if the rhs of the instanceof is a global function not 9816 // Check to see if the rhs of the instanceof is a global function not
9820 // residing in new space. If it is we assume that the function will stay the 9817 // residing in new space. If it is we assume that the function will stay the
9821 // same. 9818 // same.
9822 Handle<JSFunction> target = Handle<JSFunction>::null(); 9819 Handle<JSFunction> target = Handle<JSFunction>::null();
9823 VariableProxy* proxy = expr->right()->AsVariableProxy(); 9820 VariableProxy* proxy = expr->right()->AsVariableProxy();
9824 bool global_function = (proxy != NULL) && proxy->var()->IsUnallocated(); 9821 bool global_function = (proxy != NULL) && proxy->var()->IsUnallocated();
9825 if (global_function && 9822 if (global_function &&
9826 current_info()->has_global_object() && 9823 info()->has_global_object() &&
9827 !current_info()->global_object()->IsAccessCheckNeeded()) { 9824 !info()->global_object()->IsAccessCheckNeeded()) {
9828 Handle<String> name = proxy->name(); 9825 Handle<String> name = proxy->name();
9829 Handle<GlobalObject> global(current_info()->global_object()); 9826 Handle<GlobalObject> global(info()->global_object());
9830 LookupResult lookup(isolate()); 9827 LookupResult lookup(isolate());
9831 global->Lookup(*name, &lookup); 9828 global->Lookup(*name, &lookup);
9832 if (lookup.IsNormal() && lookup.GetValue()->IsJSFunction()) { 9829 if (lookup.IsNormal() && lookup.GetValue()->IsJSFunction()) {
9833 Handle<JSFunction> candidate(JSFunction::cast(lookup.GetValue())); 9830 Handle<JSFunction> candidate(JSFunction::cast(lookup.GetValue()));
9834 // If the function is in new space we assume it's more likely to 9831 // If the function is in new space we assume it's more likely to
9835 // change and thus prefer the general IC code. 9832 // change and thus prefer the general IC code.
9836 if (!isolate()->heap()->InNewSpace(*candidate)) { 9833 if (!isolate()->heap()->InNewSpace(*candidate)) {
9837 target = candidate; 9834 target = candidate;
9838 } 9835 }
9839 } 9836 }
(...skipping 422 matching lines...) Expand 10 before | Expand all | Expand 10 after
10262 10259
10263 10260
10264 void HOptimizedGraphBuilder::VisitDeclarations( 10261 void HOptimizedGraphBuilder::VisitDeclarations(
10265 ZoneList<Declaration*>* declarations) { 10262 ZoneList<Declaration*>* declarations) {
10266 ASSERT(globals_.is_empty()); 10263 ASSERT(globals_.is_empty());
10267 AstVisitor::VisitDeclarations(declarations); 10264 AstVisitor::VisitDeclarations(declarations);
10268 if (!globals_.is_empty()) { 10265 if (!globals_.is_empty()) {
10269 Handle<FixedArray> array = 10266 Handle<FixedArray> array =
10270 isolate()->factory()->NewFixedArray(globals_.length(), TENURED); 10267 isolate()->factory()->NewFixedArray(globals_.length(), TENURED);
10271 for (int i = 0; i < globals_.length(); ++i) array->set(i, *globals_.at(i)); 10268 for (int i = 0; i < globals_.length(); ++i) array->set(i, *globals_.at(i));
10272 int flags = DeclareGlobalsEvalFlag::encode(current_info()->is_eval()) | 10269 int flags = DeclareGlobalsEvalFlag::encode(info()->is_eval()) |
10273 DeclareGlobalsNativeFlag::encode(current_info()->is_native()) | 10270 DeclareGlobalsNativeFlag::encode(info()->is_native()) |
10274 DeclareGlobalsLanguageMode::encode(current_info()->language_mode()); 10271 DeclareGlobalsLanguageMode::encode(info()->language_mode());
10275 HInstruction* result = new(zone()) HDeclareGlobals( 10272 HInstruction* result = new(zone()) HDeclareGlobals(
10276 environment()->LookupContext(), array, flags); 10273 environment()->LookupContext(), array, flags);
10277 AddInstruction(result); 10274 AddInstruction(result);
10278 globals_.Clear(); 10275 globals_.Clear();
10279 } 10276 }
10280 } 10277 }
10281 10278
10282 10279
10283 void HOptimizedGraphBuilder::VisitVariableDeclaration( 10280 void HOptimizedGraphBuilder::VisitVariableDeclaration(
10284 VariableDeclaration* declaration) { 10281 VariableDeclaration* declaration) {
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
10318 } 10315 }
10319 10316
10320 10317
10321 void HOptimizedGraphBuilder::VisitFunctionDeclaration( 10318 void HOptimizedGraphBuilder::VisitFunctionDeclaration(
10322 FunctionDeclaration* declaration) { 10319 FunctionDeclaration* declaration) {
10323 VariableProxy* proxy = declaration->proxy(); 10320 VariableProxy* proxy = declaration->proxy();
10324 Variable* variable = proxy->var(); 10321 Variable* variable = proxy->var();
10325 switch (variable->location()) { 10322 switch (variable->location()) {
10326 case Variable::UNALLOCATED: { 10323 case Variable::UNALLOCATED: {
10327 globals_.Add(variable->name(), zone()); 10324 globals_.Add(variable->name(), zone());
10328 Handle<SharedFunctionInfo> function = Compiler::BuildFunctionInfo( 10325 Handle<SharedFunctionInfo> function =
10329 declaration->fun(), current_info()->script()); 10326 Compiler::BuildFunctionInfo(declaration->fun(), info()->script());
10330 // Check for stack-overflow exception. 10327 // Check for stack-overflow exception.
10331 if (function.is_null()) return SetStackOverflow(); 10328 if (function.is_null()) return SetStackOverflow();
10332 globals_.Add(function, zone()); 10329 globals_.Add(function, zone());
10333 return; 10330 return;
10334 } 10331 }
10335 case Variable::PARAMETER: 10332 case Variable::PARAMETER:
10336 case Variable::LOCAL: { 10333 case Variable::LOCAL: {
10337 CHECK_ALIVE(VisitForValue(declaration->fun())); 10334 CHECK_ALIVE(VisitForValue(declaration->fun()));
10338 HValue* value = Pop(); 10335 HValue* value = Pop();
10339 BindIfLive(variable, value); 10336 BindIfLive(variable, value);
(...skipping 1260 matching lines...) Expand 10 before | Expand all | Expand 10 after
11600 } 11597 }
11601 } 11598 }
11602 11599
11603 #ifdef DEBUG 11600 #ifdef DEBUG
11604 if (graph_ != NULL) graph_->Verify(false); // No full verify. 11601 if (graph_ != NULL) graph_->Verify(false); // No full verify.
11605 if (allocator_ != NULL) allocator_->Verify(); 11602 if (allocator_ != NULL) allocator_->Verify();
11606 #endif 11603 #endif
11607 } 11604 }
11608 11605
11609 } } // namespace v8::internal 11606 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/hydrogen.h ('k') | src/hydrogen-instructions.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698