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

Side by Side Diff: src/ia32/fast-codegen-ia32.cc

Issue 550043: Fix issue 541 and some refactoring of the top-level compiler. (Closed) Base URL: http://v8.googlecode.com/svn/branches/bleeding_edge/
Patch Set: '' Created 10 years, 11 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/fast-codegen.cc ('k') | src/x64/fast-codegen-x64.cc » ('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 2009 the V8 project authors. All rights reserved. 1 // Copyright 2009 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 109 matching lines...) Expand 10 before | Expand all | Expand 10 after
120 // stack frame was an arguments adapter frame. 120 // stack frame was an arguments adapter frame.
121 ArgumentsAccessStub stub(ArgumentsAccessStub::NEW_OBJECT); 121 ArgumentsAccessStub stub(ArgumentsAccessStub::NEW_OBJECT);
122 __ CallStub(&stub); 122 __ CallStub(&stub);
123 __ mov(ecx, eax); // Duplicate result. 123 __ mov(ecx, eax); // Duplicate result.
124 Move(arguments->slot(), eax, ebx, edx); 124 Move(arguments->slot(), eax, ebx, edx);
125 Slot* dot_arguments_slot = 125 Slot* dot_arguments_slot =
126 fun->scope()->arguments_shadow()->AsVariable()->slot(); 126 fun->scope()->arguments_shadow()->AsVariable()->slot();
127 Move(dot_arguments_slot, ecx, ebx, edx); 127 Move(dot_arguments_slot, ecx, ebx, edx);
128 } 128 }
129 129
130
131 { Comment cmnt(masm_, "[ Declarations"); 130 { Comment cmnt(masm_, "[ Declarations");
132 VisitDeclarations(fun->scope()->declarations()); 131 VisitDeclarations(fun->scope()->declarations());
133 } 132 }
134 133
135 { Comment cmnt(masm_, "[ Stack check"); 134 { Comment cmnt(masm_, "[ Stack check");
136 Label ok; 135 Label ok;
137 ExternalReference stack_limit = 136 ExternalReference stack_limit =
138 ExternalReference::address_of_stack_limit(); 137 ExternalReference::address_of_stack_limit();
139 __ cmp(esp, Operand::StaticVariable(stack_limit)); 138 __ cmp(esp, Operand::StaticVariable(stack_limit));
140 __ j(above_equal, &ok, taken); 139 __ j(above_equal, &ok, taken);
(...skipping 657 matching lines...) Expand 10 before | Expand all | Expand 10 after
798 TestAndBranch(eax, &discard, false_label_); 797 TestAndBranch(eax, &discard, false_label_);
799 __ bind(&discard); 798 __ bind(&discard);
800 __ Drop(1); 799 __ Drop(1);
801 __ jmp(true_label_); 800 __ jmp(true_label_);
802 break; 801 break;
803 } 802 }
804 } 803 }
805 } 804 }
806 805
807 806
808 void FastCodeGenerator::EmitNamedPropertyLoad(Property* prop, 807 void FastCodeGenerator::EmitNamedPropertyLoad(Property* prop) {
809 Expression::Context context) {
810 SetSourcePosition(prop->position()); 808 SetSourcePosition(prop->position());
811 Literal* key = prop->key()->AsLiteral(); 809 Literal* key = prop->key()->AsLiteral();
812 __ mov(ecx, Immediate(key->handle())); 810 __ mov(ecx, Immediate(key->handle()));
813 Handle<Code> ic(Builtins::builtin(Builtins::LoadIC_Initialize)); 811 Handle<Code> ic(Builtins::builtin(Builtins::LoadIC_Initialize));
814 __ call(ic, RelocInfo::CODE_TARGET); 812 __ call(ic, RelocInfo::CODE_TARGET);
815 Apply(context, eax); 813 __ nop();
816 } 814 }
817 815
818 816
819 void FastCodeGenerator::EmitKeyedPropertyLoad(Property* prop, 817 void FastCodeGenerator::EmitKeyedPropertyLoad(Property* prop) {
820 Expression::Context context) {
821 SetSourcePosition(prop->position()); 818 SetSourcePosition(prop->position());
822 Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize)); 819 Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize));
823 __ call(ic, RelocInfo::CODE_TARGET); 820 __ call(ic, RelocInfo::CODE_TARGET);
824 Apply(context, eax); 821 __ nop();
825 } 822 }
826 823
827 824
828 void FastCodeGenerator::EmitCompoundAssignmentOp(Token::Value op, 825 void FastCodeGenerator::EmitCompoundAssignmentOp(Token::Value op,
829 Expression::Context context) { 826 Expression::Context context) {
830 GenericBinaryOpStub stub(op, 827 GenericBinaryOpStub stub(op,
831 NO_OVERWRITE, 828 NO_OVERWRITE,
832 NO_GENERIC_BINARY_FLAGS); 829 NO_GENERIC_BINARY_FLAGS);
833 __ CallStub(&stub); 830 __ CallStub(&stub);
834 Apply(context, eax); 831 Apply(context, eax);
835 } 832 }
836 833
837 834
838 void FastCodeGenerator::EmitVariableAssignment(Variable* var, 835 void FastCodeGenerator::EmitVariableAssignment(Variable* var,
839 Expression::Context context) { 836 Expression::Context context) {
840 ASSERT(var != NULL); 837 ASSERT(var != NULL);
841 ASSERT(var->is_global() || var->slot() != NULL); 838 ASSERT(var->is_global() || var->slot() != NULL);
842 if (var->is_global()) { 839 if (var->is_global()) {
843 // Assignment to a global variable. Use inline caching for the 840 // Assignment to a global variable. Use inline caching for the
844 // assignment. Right-hand-side value is passed in eax, variable name in 841 // assignment. Right-hand-side value is passed in eax, variable name in
845 // ecx, and the global object on the stack. 842 // ecx, and the global object on the stack.
846 __ pop(eax); 843 __ pop(eax);
847 __ mov(ecx, var->name()); 844 __ mov(ecx, var->name());
848 __ push(CodeGenerator::GlobalObject()); 845 __ push(CodeGenerator::GlobalObject());
849 Handle<Code> ic(Builtins::builtin(Builtins::StoreIC_Initialize)); 846 Handle<Code> ic(Builtins::builtin(Builtins::StoreIC_Initialize));
850 __ call(ic, RelocInfo::CODE_TARGET); 847 __ call(ic, RelocInfo::CODE_TARGET);
848 __ nop();
851 // Overwrite the receiver on the stack with the result if needed. 849 // Overwrite the receiver on the stack with the result if needed.
852 DropAndApply(1, context, eax); 850 DropAndApply(1, context, eax);
853 851
854 } else if (var->slot() != NULL) { 852 } else if (var->slot() != NULL) {
855 Slot* slot = var->slot(); 853 Slot* slot = var->slot();
856 switch (slot->type()) { 854 switch (slot->type()) {
857 case Slot::LOCAL: 855 case Slot::LOCAL:
858 case Slot::PARAMETER: { 856 case Slot::PARAMETER: {
859 Operand target = Operand(ebp, SlotOffset(slot)); 857 Operand target = Operand(ebp, SlotOffset(slot));
860 switch (context) { 858 switch (context) {
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after
937 ASSERT(prop->key()->AsLiteral() != NULL); 935 ASSERT(prop->key()->AsLiteral() != NULL);
938 936
939 // If the assignment starts a block of assignments to the same object, 937 // If the assignment starts a block of assignments to the same object,
940 // change to slow case to avoid the quadratic behavior of repeatedly 938 // change to slow case to avoid the quadratic behavior of repeatedly
941 // adding fast properties. 939 // adding fast properties.
942 if (expr->starts_initialization_block()) { 940 if (expr->starts_initialization_block()) {
943 __ push(Operand(esp, kPointerSize)); // Receiver is under value. 941 __ push(Operand(esp, kPointerSize)); // Receiver is under value.
944 __ CallRuntime(Runtime::kToSlowProperties, 1); 942 __ CallRuntime(Runtime::kToSlowProperties, 1);
945 } 943 }
946 944
945 // Record source code position before IC call.
946 SetSourcePosition(expr->position());
947
947 __ pop(eax); 948 __ pop(eax);
948 __ mov(ecx, prop->key()->AsLiteral()->handle()); 949 __ mov(ecx, prop->key()->AsLiteral()->handle());
949 Handle<Code> ic(Builtins::builtin(Builtins::StoreIC_Initialize)); 950 Handle<Code> ic(Builtins::builtin(Builtins::StoreIC_Initialize));
950 __ call(ic, RelocInfo::CODE_TARGET); 951 __ call(ic, RelocInfo::CODE_TARGET);
951 952
952 // If the assignment ends an initialization block, revert to fast case. 953 // If the assignment ends an initialization block, revert to fast case.
953 if (expr->ends_initialization_block()) { 954 if (expr->ends_initialization_block()) {
954 __ push(eax); // Result of assignment, saved even if not needed. 955 __ push(eax); // Result of assignment, saved even if not needed.
955 __ push(Operand(esp, kPointerSize)); // Receiver is under value. 956 __ push(Operand(esp, kPointerSize)); // Receiver is under value.
956 __ CallRuntime(Runtime::kToFastProperties, 1); 957 __ CallRuntime(Runtime::kToFastProperties, 1);
957 __ pop(eax); 958 __ pop(eax);
958 } 959 }
959 960
960 DropAndApply(1, expr->context(), eax); 961 DropAndApply(1, expr->context(), eax);
961 } 962 }
962 963
963 964
964 void FastCodeGenerator::EmitKeyedPropertyAssignment(Assignment* expr) { 965 void FastCodeGenerator::EmitKeyedPropertyAssignment(Assignment* expr) {
965 // Assignment to a property, using a keyed store IC. 966 // Assignment to a property, using a keyed store IC.
966 967
967 // If the assignment starts a block of assignments to the same object, 968 // If the assignment starts a block of assignments to the same object,
968 // change to slow case to avoid the quadratic behavior of repeatedly 969 // change to slow case to avoid the quadratic behavior of repeatedly
969 // adding fast properties. 970 // adding fast properties.
970 if (expr->starts_initialization_block()) { 971 if (expr->starts_initialization_block()) {
971 // Reciever is under the key and value. 972 // Reciever is under the key and value.
972 __ push(Operand(esp, 2 * kPointerSize)); 973 __ push(Operand(esp, 2 * kPointerSize));
973 __ CallRuntime(Runtime::kToSlowProperties, 1); 974 __ CallRuntime(Runtime::kToSlowProperties, 1);
974 } 975 }
975 976
977 // Record source code position before IC call.
978 SetSourcePosition(expr->position());
979
976 __ pop(eax); 980 __ pop(eax);
977 Handle<Code> ic(Builtins::builtin(Builtins::KeyedStoreIC_Initialize)); 981 Handle<Code> ic(Builtins::builtin(Builtins::KeyedStoreIC_Initialize));
978 __ call(ic, RelocInfo::CODE_TARGET); 982 __ call(ic, RelocInfo::CODE_TARGET);
979 // This nop signals to the IC that there is no inlined code at the call 983 // This nop signals to the IC that there is no inlined code at the call
980 // site for it to patch. 984 // site for it to patch.
981 __ nop(); 985 __ nop();
982 986
983 // If the assignment ends an initialization block, revert to fast case. 987 // If the assignment ends an initialization block, revert to fast case.
984 if (expr->ends_initialization_block()) { 988 if (expr->ends_initialization_block()) {
985 __ push(eax); // Result of assignment, saved even if not needed. 989 __ push(eax); // Result of assignment, saved even if not needed.
986 // Reciever is under the key and value. 990 // Reciever is under the key and value.
987 __ push(Operand(esp, 2 * kPointerSize)); 991 __ push(Operand(esp, 2 * kPointerSize));
988 __ CallRuntime(Runtime::kToFastProperties, 1); 992 __ CallRuntime(Runtime::kToFastProperties, 1);
989 __ pop(eax); 993 __ pop(eax);
990 } 994 }
991 995
992 // Receiver and key are still on stack. 996 // Receiver and key are still on stack.
993 DropAndApply(2, expr->context(), eax); 997 DropAndApply(2, expr->context(), eax);
994 } 998 }
995 999
996 1000
997 void FastCodeGenerator::VisitProperty(Property* expr) { 1001 void FastCodeGenerator::VisitProperty(Property* expr) {
998 Comment cmnt(masm_, "[ Property"); 1002 Comment cmnt(masm_, "[ Property");
999 Expression* key = expr->key(); 1003 Expression* key = expr->key();
1000 1004
1001 // Record the source position for the property load.
1002 SetSourcePosition(expr->position());
1003
1004 // Evaluate the receiver. 1005 // Evaluate the receiver.
1005 Visit(expr->obj()); 1006 Visit(expr->obj());
1006 1007
1007 if (key->IsPropertyName()) { 1008 if (key->IsPropertyName()) {
1008 // Do a named property load. The IC expects the property name in ecx 1009 EmitNamedPropertyLoad(expr);
1009 // and the receiver on the stack. 1010 // Drop receiver left on the stack by IC.
1010 __ mov(ecx, Immediate(key->AsLiteral()->handle()));
1011 Handle<Code> ic(Builtins::builtin(Builtins::LoadIC_Initialize));
1012 __ call(ic, RelocInfo::CODE_TARGET);
1013 // By emitting a nop we make sure that we do not have a test eax
1014 // instruction after the call it is treated specially by the LoadIC code.
1015 __ nop();
1016 DropAndApply(1, expr->context(), eax); 1011 DropAndApply(1, expr->context(), eax);
1017 } else { 1012 } else {
1018 // Do a keyed property load.
1019 Visit(expr->key()); 1013 Visit(expr->key());
1020 Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize)); 1014 EmitKeyedPropertyLoad(expr);
1021 __ call(ic, RelocInfo::CODE_TARGET); 1015 // Drop key and receiver left on the stack by IC.
1022 // By emitting a nop we make sure that we do not have a "test eax,..."
1023 // instruction after the call it is treated specially by the LoadIC code.
1024 __ nop();
1025 // Drop key left on the stack by IC.
1026 DropAndApply(2, expr->context(), eax); 1016 DropAndApply(2, expr->context(), eax);
1027 } 1017 }
1028 } 1018 }
1029 1019
1030 1020
1031 void FastCodeGenerator::EmitCallWithIC(Call* expr, 1021 void FastCodeGenerator::EmitCallWithIC(Call* expr,
1032 Handle<Object> name, 1022 Handle<Object> name,
1033 RelocInfo::Mode mode) { 1023 RelocInfo::Mode mode) {
1034 // Code common for calls using the IC. 1024 // Code common for calls using the IC.
1035 ZoneList<Expression*>* args = expr->arguments(); 1025 ZoneList<Expression*>* args = expr->arguments();
(...skipping 309 matching lines...) Expand 10 before | Expand all | Expand 10 after
1345 Expression::kValue); 1335 Expression::kValue);
1346 } else { 1336 } else {
1347 // Reserve space for result of postfix operation. 1337 // Reserve space for result of postfix operation.
1348 if (expr->is_postfix() && expr->context() != Expression::kEffect) { 1338 if (expr->is_postfix() && expr->context() != Expression::kEffect) {
1349 ASSERT(expr->context() != Expression::kUninitialized); 1339 ASSERT(expr->context() != Expression::kUninitialized);
1350 __ push(Immediate(Smi::FromInt(0))); 1340 __ push(Immediate(Smi::FromInt(0)));
1351 } 1341 }
1352 Visit(prop->obj()); 1342 Visit(prop->obj());
1353 ASSERT_EQ(Expression::kValue, prop->obj()->context()); 1343 ASSERT_EQ(Expression::kValue, prop->obj()->context());
1354 if (assign_type == NAMED_PROPERTY) { 1344 if (assign_type == NAMED_PROPERTY) {
1355 EmitNamedPropertyLoad(prop, Expression::kValue); 1345 EmitNamedPropertyLoad(prop);
1356 } else { 1346 } else {
1357 Visit(prop->key()); 1347 Visit(prop->key());
1358 ASSERT_EQ(Expression::kValue, prop->key()->context()); 1348 ASSERT_EQ(Expression::kValue, prop->key()->context());
1359 EmitKeyedPropertyLoad(prop, Expression::kValue); 1349 EmitKeyedPropertyLoad(prop);
1360 } 1350 }
1351 __ push(eax);
1361 } 1352 }
1362 1353
1363 // Convert to number. 1354 // Convert to number.
1364 __ InvokeBuiltin(Builtins::TO_NUMBER, CALL_FUNCTION); 1355 __ InvokeBuiltin(Builtins::TO_NUMBER, CALL_FUNCTION);
1365 1356
1366 // Save result for postfix expressions. 1357 // Save result for postfix expressions.
1367 if (expr->is_postfix()) { 1358 if (expr->is_postfix()) {
1368 switch (expr->context()) { 1359 switch (expr->context()) {
1369 case Expression::kUninitialized: 1360 case Expression::kUninitialized:
1370 UNREACHABLE(); 1361 UNREACHABLE();
(...skipping 330 matching lines...) Expand 10 before | Expand all | Expand 10 after
1701 __ add(Operand(edx), Immediate(masm_->CodeObject())); 1692 __ add(Operand(edx), Immediate(masm_->CodeObject()));
1702 __ mov(Operand(esp, 0), edx); 1693 __ mov(Operand(esp, 0), edx);
1703 // And return. 1694 // And return.
1704 __ ret(0); 1695 __ ret(0);
1705 } 1696 }
1706 1697
1707 1698
1708 #undef __ 1699 #undef __
1709 1700
1710 } } // namespace v8::internal 1701 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/fast-codegen.cc ('k') | src/x64/fast-codegen-x64.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698