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

Side by Side Diff: src/hydrogen.cc

Issue 5550003: Add optimized compiler support for generic global loads.... (Closed) Base URL: http://v8.googlecode.com/svn/branches/bleeding_edge/
Patch Set: ported to x64 and arm Created 9 years, 9 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 2011 the V8 project authors. All rights reserved. 1 // Copyright 2011 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 2087 matching lines...) Expand 10 before | Expand all | Expand 10 after
2098 Visit(expr); 2098 Visit(expr);
2099 } 2099 }
2100 2100
2101 2101
2102 void HGraphBuilder::VisitForValue(Expression* expr) { 2102 void HGraphBuilder::VisitForValue(Expression* expr) {
2103 ValueContext for_value(this); 2103 ValueContext for_value(this);
2104 Visit(expr); 2104 Visit(expr);
2105 } 2105 }
2106 2106
2107 2107
2108 void HGraphBuilder::VisitForTypeofValue(Expression* expr) {
2109 ValueContext for_value(this);
2110 for_value.MarkAsTypeof();
2111 Visit(expr);
2112 }
2113
2114
2108 void HGraphBuilder::VisitForControl(Expression* expr, 2115 void HGraphBuilder::VisitForControl(Expression* expr,
2109 HBasicBlock* true_block, 2116 HBasicBlock* true_block,
2110 HBasicBlock* false_block) { 2117 HBasicBlock* false_block) {
2111 TestContext for_test(this, true_block, false_block); 2118 TestContext for_test(this, true_block, false_block);
2112 Visit(expr); 2119 Visit(expr);
2113 } 2120 }
2114 2121
2115 2122
2116 void HGraphBuilder::VisitArgument(Expression* expr) { 2123 void HGraphBuilder::VisitArgument(Expression* expr) {
2117 VISIT_FOR_VALUE(expr); 2124 VISIT_FOR_VALUE(expr);
(...skipping 672 matching lines...) Expand 10 before | Expand all | Expand 10 after
2790 CHECK_BAILOUT; 2797 CHECK_BAILOUT;
2791 2798
2792 if (!ast_context()->IsTest()) { 2799 if (!ast_context()->IsTest()) {
2793 HBasicBlock* join = CreateJoin(other, current_block(), expr->id()); 2800 HBasicBlock* join = CreateJoin(other, current_block(), expr->id());
2794 set_current_block(join); 2801 set_current_block(join);
2795 if (!ast_context()->IsEffect()) ast_context()->ReturnValue(Pop()); 2802 if (!ast_context()->IsEffect()) ast_context()->ReturnValue(Pop());
2796 } 2803 }
2797 } 2804 }
2798 2805
2799 2806
2800 void HGraphBuilder::LookupGlobalPropertyCell(Variable* var, 2807 bool HGraphBuilder::LookupGlobalPropertyCell(Variable* var,
2801 LookupResult* lookup, 2808 LookupResult* lookup,
2802 bool is_store) { 2809 bool is_store) {
2803 if (var->is_this()) { 2810 if (var->is_this()) {
2804 BAILOUT("global this reference"); 2811 Bailout("global this reference");
2812 return true;
2805 } 2813 }
2806 if (!info()->has_global_object()) { 2814 if (!info()->has_global_object()) {
2807 BAILOUT("no global object to optimize VariableProxy"); 2815 Bailout("no global object to optimize VariableProxy");
2816 return true;
2808 } 2817 }
2809 Handle<GlobalObject> global(info()->global_object()); 2818 Handle<GlobalObject> global(info()->global_object());
2810 global->Lookup(*var->name(), lookup); 2819 global->Lookup(*var->name(), lookup);
2811 if (!lookup->IsProperty()) { 2820 if (!lookup->IsProperty()) return true;
2812 BAILOUT("global variable cell not yet introduced"); 2821 if (is_store && lookup->IsReadOnly()) {
2822 Bailout("store to read-only global variable");
2823 return true;
2813 } 2824 }
2814 if (lookup->type() != NORMAL) { 2825 if (lookup->type() != NORMAL) return true;
2815 BAILOUT("global variable has accessors"); 2826 if (!lookup->IsProperty()) return true;
2816 } 2827 if (lookup->holder() != *global) return true;
2817 if (is_store && lookup->IsReadOnly()) { 2828 return false;
2818 BAILOUT("read-only global variable");
2819 }
2820 if (lookup->holder() != *global) {
2821 BAILOUT("global property on prototype of global object");
2822 }
2823 } 2829 }
2824 2830
2825 2831
2826 HValue* HGraphBuilder::BuildContextChainWalk(Variable* var) { 2832 HValue* HGraphBuilder::BuildContextChainWalk(Variable* var) {
2827 ASSERT(var->IsContextSlot()); 2833 ASSERT(var->IsContextSlot());
2828 HInstruction* context = new HContext; 2834 HInstruction* context = new HContext;
2829 AddInstruction(context); 2835 AddInstruction(context);
2830 int length = info()->scope()->ContextChainLength(var->scope()); 2836 int length = info()->scope()->ContextChainLength(var->scope());
2831 while (length-- > 0) { 2837 while (length-- > 0) {
2832 context = new HOuterContext(context); 2838 context = new HOuterContext(context);
(...skipping 15 matching lines...) Expand all
2848 } else if (variable->IsContextSlot()) { 2854 } else if (variable->IsContextSlot()) {
2849 if (variable->mode() == Variable::CONST) { 2855 if (variable->mode() == Variable::CONST) {
2850 BAILOUT("reference to const context slot"); 2856 BAILOUT("reference to const context slot");
2851 } 2857 }
2852 HValue* context = BuildContextChainWalk(variable); 2858 HValue* context = BuildContextChainWalk(variable);
2853 int index = variable->AsSlot()->index(); 2859 int index = variable->AsSlot()->index();
2854 HLoadContextSlot* instr = new HLoadContextSlot(context, index); 2860 HLoadContextSlot* instr = new HLoadContextSlot(context, index);
2855 ast_context()->ReturnInstruction(instr, expr->id()); 2861 ast_context()->ReturnInstruction(instr, expr->id());
2856 } else if (variable->is_global()) { 2862 } else if (variable->is_global()) {
2857 LookupResult lookup; 2863 LookupResult lookup;
2858 LookupGlobalPropertyCell(variable, &lookup, false); 2864 bool is_generic = LookupGlobalPropertyCell(variable, &lookup, false);
2859 CHECK_BAILOUT; 2865 CHECK_BAILOUT;
2860
2861 Handle<GlobalObject> global(info()->global_object()); 2866 Handle<GlobalObject> global(info()->global_object());
2862 // TODO(3039103): Handle global property load through an IC call when access 2867 HInstruction* instr = NULL;
2863 // checks are enabled. 2868 if (is_generic || global->IsAccessCheckNeeded()) {
2864 if (global->IsAccessCheckNeeded()) { 2869 HContext* context = new HContext;
2865 BAILOUT("global object requires access check"); 2870 AddInstruction(context);
2871 HGlobalObject* global_object = new HGlobalObject(context);
2872 AddInstruction(global_object);
2873 instr = new HLoadGlobalGeneric(context,
2874 global_object,
2875 variable->name(),
2876 ast_context()->IsTypeof());
2877 } else {
2878 Handle<JSGlobalPropertyCell> cell(global->GetPropertyCell(&lookup));
2879 bool check_hole = !lookup.IsDontDelete() || lookup.IsReadOnly();
2880 instr = new HLoadGlobal(cell, check_hole);
2866 } 2881 }
2867 Handle<JSGlobalPropertyCell> cell(global->GetPropertyCell(&lookup));
2868 bool check_hole = !lookup.IsDontDelete() || lookup.IsReadOnly();
2869 HLoadGlobal* instr = new HLoadGlobal(cell, check_hole);
2870 ast_context()->ReturnInstruction(instr, expr->id()); 2882 ast_context()->ReturnInstruction(instr, expr->id());
2871 } else { 2883 } else {
2872 BAILOUT("reference to a variable which requires dynamic lookup"); 2884 BAILOUT("reference to a variable which requires dynamic lookup");
2873 } 2885 }
2874 } 2886 }
2875 2887
2876 2888
2877 void HGraphBuilder::VisitLiteral(Literal* expr) { 2889 void HGraphBuilder::VisitLiteral(Literal* expr) {
2878 HConstant* instr = new HConstant(expr->handle(), Representation::Tagged()); 2890 HConstant* instr = new HConstant(expr->handle(), Representation::Tagged());
2879 ast_context()->ReturnInstruction(instr, expr->id()); 2891 ast_context()->ReturnInstruction(instr, expr->id());
(...skipping 337 matching lines...) Expand 10 before | Expand all | Expand 10 after
3217 3229
3218 3230
3219 // Because not every expression has a position and there is not common 3231 // Because not every expression has a position and there is not common
3220 // superclass of Assignment and CountOperation, we cannot just pass the 3232 // superclass of Assignment and CountOperation, we cannot just pass the
3221 // owning expression instead of position and ast_id separately. 3233 // owning expression instead of position and ast_id separately.
3222 void HGraphBuilder::HandleGlobalVariableAssignment(Variable* var, 3234 void HGraphBuilder::HandleGlobalVariableAssignment(Variable* var,
3223 HValue* value, 3235 HValue* value,
3224 int position, 3236 int position,
3225 int ast_id) { 3237 int ast_id) {
3226 LookupResult lookup; 3238 LookupResult lookup;
3227 LookupGlobalPropertyCell(var, &lookup, true); 3239 bool is_generic = LookupGlobalPropertyCell(var, &lookup, true);
3228 CHECK_BAILOUT; 3240 CHECK_BAILOUT;
3229 3241
3230 bool check_hole = !lookup.IsDontDelete() || lookup.IsReadOnly(); 3242 bool check_hole = !lookup.IsDontDelete() || lookup.IsReadOnly();
3231 Handle<GlobalObject> global(info()->global_object()); 3243 Handle<GlobalObject> global(info()->global_object());
3232 Handle<JSGlobalPropertyCell> cell(global->GetPropertyCell(&lookup)); 3244 if (!is_generic && !global->IsAccessCheckNeeded()) {
3233 HInstruction* instr = new HStoreGlobal(value, cell, check_hole); 3245 Handle<JSGlobalPropertyCell> cell(global->GetPropertyCell(&lookup));
3234 instr->set_position(position); 3246 HStoreGlobal* instr = new HStoreGlobal(value, cell, check_hole);
3235 AddInstruction(instr); 3247 instr->set_position(position);
3236 if (instr->HasSideEffects()) AddSimulate(ast_id); 3248 AddInstruction(instr);
3249 if (instr->HasSideEffects()) AddSimulate(ast_id);
3250 } else {
3251 BAILOUT("unsupported store to global");
3252 }
3237 } 3253 }
3238 3254
3239 3255
3240 void HGraphBuilder::HandleCompoundAssignment(Assignment* expr) { 3256 void HGraphBuilder::HandleCompoundAssignment(Assignment* expr) {
3241 Expression* target = expr->target(); 3257 Expression* target = expr->target();
3242 VariableProxy* proxy = target->AsVariableProxy(); 3258 VariableProxy* proxy = target->AsVariableProxy();
3243 Variable* var = proxy->AsVariable(); 3259 Variable* var = proxy->AsVariable();
3244 Property* prop = target->AsProperty(); 3260 Property* prop = target->AsProperty();
3245 ASSERT(var == NULL || prop == NULL); 3261 ASSERT(var == NULL || prop == NULL);
3246 3262
(...skipping 1280 matching lines...) Expand 10 before | Expand all | Expand 10 after
4527 break; 4543 break;
4528 case Token::SUB: 4544 case Token::SUB:
4529 instr = new HMul(graph_->GetConstantMinus1(), value); 4545 instr = new HMul(graph_->GetConstantMinus1(), value);
4530 break; 4546 break;
4531 default: 4547 default:
4532 UNREACHABLE(); 4548 UNREACHABLE();
4533 break; 4549 break;
4534 } 4550 }
4535 ast_context()->ReturnInstruction(instr, expr->id()); 4551 ast_context()->ReturnInstruction(instr, expr->id());
4536 } else if (op == Token::TYPEOF) { 4552 } else if (op == Token::TYPEOF) {
4537 VISIT_FOR_VALUE(expr->expression()); 4553 VisitForTypeofValue(expr->expression());
4554 if (HasStackOverflow()) return;
4538 HValue* value = Pop(); 4555 HValue* value = Pop();
4539 ast_context()->ReturnInstruction(new HTypeof(value), expr->id()); 4556 ast_context()->ReturnInstruction(new HTypeof(value), expr->id());
4540 } else { 4557 } else {
4541 BAILOUT("Value: unsupported unary operation"); 4558 BAILOUT("Value: unsupported unary operation");
4542 } 4559 }
4543 } 4560 }
4544 4561
4545 4562
4546 void HGraphBuilder::VisitIncrementOperation(IncrementOperation* expr) { 4563 void HGraphBuilder::VisitIncrementOperation(IncrementOperation* expr) {
4547 // IncrementOperation is never visited by the visitor. It only 4564 // IncrementOperation is never visited by the visitor. It only
(...skipping 364 matching lines...) Expand 10 before | Expand all | Expand 10 after
4912 ast_context()->ReturnInstruction(instr, expr->id()); 4929 ast_context()->ReturnInstruction(instr, expr->id());
4913 return; 4930 return;
4914 } 4931 }
4915 4932
4916 // Check for the pattern: typeof <expression> == <string literal>. 4933 // Check for the pattern: typeof <expression> == <string literal>.
4917 UnaryOperation* left_unary = expr->left()->AsUnaryOperation(); 4934 UnaryOperation* left_unary = expr->left()->AsUnaryOperation();
4918 Literal* right_literal = expr->right()->AsLiteral(); 4935 Literal* right_literal = expr->right()->AsLiteral();
4919 if ((expr->op() == Token::EQ || expr->op() == Token::EQ_STRICT) && 4936 if ((expr->op() == Token::EQ || expr->op() == Token::EQ_STRICT) &&
4920 left_unary != NULL && left_unary->op() == Token::TYPEOF && 4937 left_unary != NULL && left_unary->op() == Token::TYPEOF &&
4921 right_literal != NULL && right_literal->handle()->IsString()) { 4938 right_literal != NULL && right_literal->handle()->IsString()) {
4922 VISIT_FOR_VALUE(left_unary->expression()); 4939 VisitForTypeofValue(left_unary->expression());
4940 if (HasStackOverflow()) return;
4923 HValue* left = Pop(); 4941 HValue* left = Pop();
4924 HInstruction* instr = new HTypeofIs(left, 4942 HInstruction* instr = new HTypeofIs(left,
4925 Handle<String>::cast(right_literal->handle())); 4943 Handle<String>::cast(right_literal->handle()));
4926 instr->set_position(expr->position()); 4944 instr->set_position(expr->position());
4927 ast_context()->ReturnInstruction(instr, expr->id()); 4945 ast_context()->ReturnInstruction(instr, expr->id());
4928 return; 4946 return;
4929 } 4947 }
4930 4948
4931 VISIT_FOR_VALUE(expr->left()); 4949 VISIT_FOR_VALUE(expr->left());
4932 VISIT_FOR_VALUE(expr->right()); 4950 VISIT_FOR_VALUE(expr->right());
(...skipping 971 matching lines...) Expand 10 before | Expand all | Expand 10 after
5904 } 5922 }
5905 } 5923 }
5906 5924
5907 #ifdef DEBUG 5925 #ifdef DEBUG
5908 if (graph_ != NULL) graph_->Verify(); 5926 if (graph_ != NULL) graph_->Verify();
5909 if (allocator_ != NULL) allocator_->Verify(); 5927 if (allocator_ != NULL) allocator_->Verify();
5910 #endif 5928 #endif
5911 } 5929 }
5912 5930
5913 } } // namespace v8::internal 5931 } } // 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