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

Side by Side Diff: src/full-codegen/mips/full-codegen-mips.cc

Issue 2615033002: [fullcodegen] Remove dead hole check logic (Closed)
Patch Set: x87 Created 3 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
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #if V8_TARGET_ARCH_MIPS 5 #if V8_TARGET_ARCH_MIPS
6 6
7 // Note on Mips implementation: 7 // Note on Mips implementation:
8 // 8 //
9 // The result_register() for mips is the 'v0' register, which is defined 9 // The result_register() for mips is the 'v0' register, which is defined
10 // by the ABI to contain function return values. However, the first 10 // by the ABI to contain function return values. However, the first
(...skipping 736 matching lines...) Expand 10 before | Expand all | Expand 10 after
747 __ Check(ne, kDeclarationInCatchContext, 747 __ Check(ne, kDeclarationInCatchContext,
748 a1, Operand(t0)); 748 a1, Operand(t0));
749 } 749 }
750 } 750 }
751 751
752 752
753 void FullCodeGenerator::VisitVariableDeclaration( 753 void FullCodeGenerator::VisitVariableDeclaration(
754 VariableDeclaration* declaration) { 754 VariableDeclaration* declaration) {
755 VariableProxy* proxy = declaration->proxy(); 755 VariableProxy* proxy = declaration->proxy();
756 Variable* variable = proxy->var(); 756 Variable* variable = proxy->var();
757 DCHECK(!variable->binding_needs_init());
757 switch (variable->location()) { 758 switch (variable->location()) {
758 case VariableLocation::UNALLOCATED: { 759 case VariableLocation::UNALLOCATED: {
759 DCHECK(!variable->binding_needs_init());
760 globals_->Add(variable->name(), zone()); 760 globals_->Add(variable->name(), zone());
761 FeedbackVectorSlot slot = proxy->VariableFeedbackSlot(); 761 FeedbackVectorSlot slot = proxy->VariableFeedbackSlot();
762 DCHECK(!slot.IsInvalid()); 762 DCHECK(!slot.IsInvalid());
763 globals_->Add(handle(Smi::FromInt(slot.ToInt()), isolate()), zone()); 763 globals_->Add(handle(Smi::FromInt(slot.ToInt()), isolate()), zone());
764 globals_->Add(isolate()->factory()->undefined_value(), zone()); 764 globals_->Add(isolate()->factory()->undefined_value(), zone());
765 break; 765 break;
766 } 766 }
767 case VariableLocation::PARAMETER: 767 case VariableLocation::PARAMETER:
768 case VariableLocation::LOCAL: 768 case VariableLocation::LOCAL:
769 if (variable->binding_needs_init()) {
770 Comment cmnt(masm_, "[ VariableDeclaration");
771 __ LoadRoot(t0, Heap::kTheHoleValueRootIndex);
772 __ sw(t0, StackOperand(variable));
773 }
774 break;
775
776 case VariableLocation::CONTEXT: 769 case VariableLocation::CONTEXT:
777 if (variable->binding_needs_init()) {
778 Comment cmnt(masm_, "[ VariableDeclaration");
779 EmitDebugCheckDeclarationContext(variable);
780 __ LoadRoot(at, Heap::kTheHoleValueRootIndex);
781 __ sw(at, ContextMemOperand(cp, variable->index()));
782 // No write barrier since the_hole_value is in old space.
783 PrepareForBailoutForId(proxy->id(), BailoutState::NO_REGISTERS);
784 }
785 break; 770 break;
786 771
787 case VariableLocation::LOOKUP: 772 case VariableLocation::LOOKUP:
788 case VariableLocation::MODULE: 773 case VariableLocation::MODULE:
789 UNREACHABLE(); 774 UNREACHABLE();
790 } 775 }
791 } 776 }
792 777
793 778
794 void FullCodeGenerator::VisitFunctionDeclaration( 779 void FullCodeGenerator::VisitFunctionDeclaration(
(...skipping 344 matching lines...) Expand 10 before | Expand all | Expand 10 after
1139 MemOperand(sp, offset * kPointerSize)); 1124 MemOperand(sp, offset * kPointerSize));
1140 CallStoreIC(slot, isolate()->factory()->home_object_symbol()); 1125 CallStoreIC(slot, isolate()->factory()->home_object_symbol());
1141 } 1126 }
1142 1127
1143 void FullCodeGenerator::EmitVariableLoad(VariableProxy* proxy, 1128 void FullCodeGenerator::EmitVariableLoad(VariableProxy* proxy,
1144 TypeofMode typeof_mode) { 1129 TypeofMode typeof_mode) {
1145 // Record position before possible IC call. 1130 // Record position before possible IC call.
1146 SetExpressionPosition(proxy); 1131 SetExpressionPosition(proxy);
1147 PrepareForBailoutForId(proxy->BeforeId(), BailoutState::NO_REGISTERS); 1132 PrepareForBailoutForId(proxy->BeforeId(), BailoutState::NO_REGISTERS);
1148 Variable* var = proxy->var(); 1133 Variable* var = proxy->var();
1134 DCHECK(!var->binding_needs_init());
1149 1135
1150 // Two cases: global variables and all other types of variables. 1136 // Two cases: global variables and all other types of variables.
1151 switch (var->location()) { 1137 switch (var->location()) {
1152 case VariableLocation::UNALLOCATED: { 1138 case VariableLocation::UNALLOCATED: {
1153 Comment cmnt(masm_, "[ Global variable"); 1139 Comment cmnt(masm_, "[ Global variable");
1154 EmitGlobalVariableLoad(proxy, typeof_mode); 1140 EmitGlobalVariableLoad(proxy, typeof_mode);
1155 context()->Plug(v0); 1141 context()->Plug(v0);
1156 break; 1142 break;
1157 } 1143 }
1158 1144
1159 case VariableLocation::PARAMETER: 1145 case VariableLocation::PARAMETER:
1160 case VariableLocation::LOCAL: 1146 case VariableLocation::LOCAL:
1161 case VariableLocation::CONTEXT: { 1147 case VariableLocation::CONTEXT: {
1162 DCHECK_EQ(NOT_INSIDE_TYPEOF, typeof_mode); 1148 DCHECK_EQ(NOT_INSIDE_TYPEOF, typeof_mode);
1163 Comment cmnt(masm_, var->IsContextSlot() ? "[ Context variable" 1149 Comment cmnt(masm_, var->IsContextSlot() ? "[ Context variable"
1164 : "[ Stack variable"); 1150 : "[ Stack variable");
1165 if (proxy->hole_check_mode() == HoleCheckMode::kRequired) {
1166 // Throw a reference error when using an uninitialized let/const
1167 // binding in harmony mode.
1168 Label done;
1169 GetVar(v0, var);
1170 __ LoadRoot(at, Heap::kTheHoleValueRootIndex);
1171 __ subu(at, v0, at); // Sub as compare: at == 0 on eq.
1172 __ Branch(&done, ne, at, Operand(zero_reg));
1173 __ li(a0, Operand(var->name()));
1174 __ push(a0);
1175 __ CallRuntime(Runtime::kThrowReferenceError);
1176 __ bind(&done);
1177 context()->Plug(v0);
1178 break;
1179 }
1180 context()->Plug(var); 1151 context()->Plug(var);
1181 break; 1152 break;
1182 } 1153 }
1183 1154
1184 case VariableLocation::LOOKUP: 1155 case VariableLocation::LOOKUP:
1185 case VariableLocation::MODULE: 1156 case VariableLocation::MODULE:
1186 UNREACHABLE(); 1157 UNREACHABLE();
1187 } 1158 }
1188 } 1159 }
1189 1160
(...skipping 298 matching lines...) Expand 10 before | Expand all | Expand 10 after
1488 } else { 1459 } else {
1489 VisitForAccumulatorValue(expr->value()); 1460 VisitForAccumulatorValue(expr->value());
1490 } 1461 }
1491 1462
1492 SetExpressionPosition(expr); 1463 SetExpressionPosition(expr);
1493 1464
1494 // Store the value. 1465 // Store the value.
1495 switch (assign_type) { 1466 switch (assign_type) {
1496 case VARIABLE: { 1467 case VARIABLE: {
1497 VariableProxy* proxy = expr->target()->AsVariableProxy(); 1468 VariableProxy* proxy = expr->target()->AsVariableProxy();
1498 EmitVariableAssignment(proxy->var(), expr->op(), expr->AssignmentSlot(), 1469 EmitVariableAssignment(proxy->var(), expr->op(), expr->AssignmentSlot());
1499 proxy->hole_check_mode());
1500 PrepareForBailoutForId(expr->AssignmentId(), BailoutState::TOS_REGISTER); 1470 PrepareForBailoutForId(expr->AssignmentId(), BailoutState::TOS_REGISTER);
1501 context()->Plug(v0); 1471 context()->Plug(v0);
1502 break; 1472 break;
1503 } 1473 }
1504 case NAMED_PROPERTY: 1474 case NAMED_PROPERTY:
1505 EmitNamedPropertyAssignment(expr); 1475 EmitNamedPropertyAssignment(expr);
1506 break; 1476 break;
1507 case KEYED_PROPERTY: 1477 case KEYED_PROPERTY:
1508 EmitKeyedPropertyAssignment(expr); 1478 EmitKeyedPropertyAssignment(expr);
1509 break; 1479 break;
(...skipping 171 matching lines...) Expand 10 before | Expand all | Expand 10 after
1681 FeedbackVectorSlot slot) { 1651 FeedbackVectorSlot slot) {
1682 DCHECK(expr->IsValidReferenceExpressionOrThis()); 1652 DCHECK(expr->IsValidReferenceExpressionOrThis());
1683 1653
1684 Property* prop = expr->AsProperty(); 1654 Property* prop = expr->AsProperty();
1685 LhsKind assign_type = Property::GetAssignType(prop); 1655 LhsKind assign_type = Property::GetAssignType(prop);
1686 1656
1687 switch (assign_type) { 1657 switch (assign_type) {
1688 case VARIABLE: { 1658 case VARIABLE: {
1689 VariableProxy* proxy = expr->AsVariableProxy(); 1659 VariableProxy* proxy = expr->AsVariableProxy();
1690 EffectContext context(this); 1660 EffectContext context(this);
1691 EmitVariableAssignment(proxy->var(), Token::ASSIGN, slot, 1661 EmitVariableAssignment(proxy->var(), Token::ASSIGN, slot);
1692 proxy->hole_check_mode());
1693 break; 1662 break;
1694 } 1663 }
1695 case NAMED_PROPERTY: { 1664 case NAMED_PROPERTY: {
1696 PushOperand(result_register()); // Preserve value. 1665 PushOperand(result_register()); // Preserve value.
1697 VisitForAccumulatorValue(prop->obj()); 1666 VisitForAccumulatorValue(prop->obj());
1698 __ mov(StoreDescriptor::ReceiverRegister(), result_register()); 1667 __ mov(StoreDescriptor::ReceiverRegister(), result_register());
1699 PopOperand(StoreDescriptor::ValueRegister()); // Restore value. 1668 PopOperand(StoreDescriptor::ValueRegister()); // Restore value.
1700 CallStoreIC(slot, prop->key()->AsLiteral()->value()); 1669 CallStoreIC(slot, prop->key()->AsLiteral()->value());
1701 break; 1670 break;
1702 } 1671 }
(...skipping 22 matching lines...) Expand all
1725 if (var->IsContextSlot()) { 1694 if (var->IsContextSlot()) {
1726 // RecordWrite may destroy all its register arguments. 1695 // RecordWrite may destroy all its register arguments.
1727 __ Move(a3, result_register()); 1696 __ Move(a3, result_register());
1728 int offset = Context::SlotOffset(var->index()); 1697 int offset = Context::SlotOffset(var->index());
1729 __ RecordWriteContextSlot( 1698 __ RecordWriteContextSlot(
1730 a1, offset, a3, a2, kRAHasBeenSaved, kDontSaveFPRegs); 1699 a1, offset, a3, a2, kRAHasBeenSaved, kDontSaveFPRegs);
1731 } 1700 }
1732 } 1701 }
1733 1702
1734 void FullCodeGenerator::EmitVariableAssignment(Variable* var, Token::Value op, 1703 void FullCodeGenerator::EmitVariableAssignment(Variable* var, Token::Value op,
1735 FeedbackVectorSlot slot, 1704 FeedbackVectorSlot slot) {
1736 HoleCheckMode hole_check_mode) { 1705 DCHECK(!var->binding_needs_init());
1737 if (var->IsUnallocated()) { 1706 if (var->IsUnallocated()) {
1738 // Global var, const, or let. 1707 // Global var, const, or let.
1739 __ mov(StoreDescriptor::ValueRegister(), result_register()); 1708 __ mov(StoreDescriptor::ValueRegister(), result_register());
1740 __ LoadGlobalObject(StoreDescriptor::ReceiverRegister()); 1709 __ LoadGlobalObject(StoreDescriptor::ReceiverRegister());
1741 CallStoreIC(slot, var->name()); 1710 CallStoreIC(slot, var->name());
1742 1711
1743 } else if (IsLexicalVariableMode(var->mode()) && op != Token::INIT) { 1712 } else if (var->mode() == CONST && op != Token::INIT) {
1744 DCHECK(!var->IsLookupSlot()); 1713 if (var->throw_on_const_assignment(language_mode())) {
1745 DCHECK(var->IsStackAllocated() || var->IsContextSlot());
1746 MemOperand location = VarOperand(var, a1);
1747 // Perform an initialization check for lexically declared variables.
1748 if (hole_check_mode == HoleCheckMode::kRequired) {
1749 Label assign;
1750 __ lw(a3, location);
1751 __ LoadRoot(t0, Heap::kTheHoleValueRootIndex);
1752 __ Branch(&assign, ne, a3, Operand(t0));
1753 __ li(a3, Operand(var->name()));
1754 __ push(a3);
1755 __ CallRuntime(Runtime::kThrowReferenceError);
1756 __ bind(&assign);
1757 }
1758 if (var->mode() != CONST) {
1759 EmitStoreToStackLocalOrContextSlot(var, location);
1760 } else if (var->throw_on_const_assignment(language_mode())) {
1761 __ CallRuntime(Runtime::kThrowConstAssignError); 1714 __ CallRuntime(Runtime::kThrowConstAssignError);
1762 } 1715 }
1763 } else if (var->is_this() && var->mode() == CONST && op == Token::INIT) {
1764 // Initializing assignment to const {this} needs a write barrier.
1765 DCHECK(var->IsStackAllocated() || var->IsContextSlot());
1766 Label uninitialized_this;
1767 MemOperand location = VarOperand(var, a1);
1768 __ lw(a3, location);
1769 __ LoadRoot(at, Heap::kTheHoleValueRootIndex);
1770 __ Branch(&uninitialized_this, eq, a3, Operand(at));
1771 __ li(a0, Operand(var->name()));
1772 __ Push(a0);
1773 __ CallRuntime(Runtime::kThrowReferenceError);
1774 __ bind(&uninitialized_this);
1775 EmitStoreToStackLocalOrContextSlot(var, location);
1776
1777 } else { 1716 } else {
1778 DCHECK(var->mode() != CONST || op == Token::INIT); 1717 DCHECK(!var->is_this());
1779 DCHECK((var->IsStackAllocated() || var->IsContextSlot())); 1718 DCHECK((var->IsStackAllocated() || var->IsContextSlot()));
1780 DCHECK(!var->IsLookupSlot()); 1719 DCHECK(!var->IsLookupSlot());
1781 // Assignment to var or initializing assignment to let/const in harmony
1782 // mode.
1783 MemOperand location = VarOperand(var, a1); 1720 MemOperand location = VarOperand(var, a1);
1784 if (FLAG_debug_code && var->mode() == LET && op == Token::INIT) {
1785 // Check for an uninitialized let binding.
1786 __ lw(a2, location);
1787 __ LoadRoot(t0, Heap::kTheHoleValueRootIndex);
1788 __ Check(eq, kLetBindingReInitialization, a2, Operand(t0));
1789 }
1790 EmitStoreToStackLocalOrContextSlot(var, location); 1721 EmitStoreToStackLocalOrContextSlot(var, location);
1791 } 1722 }
1792 } 1723 }
1793 1724
1794 1725
1795 void FullCodeGenerator::EmitNamedPropertyAssignment(Assignment* expr) { 1726 void FullCodeGenerator::EmitNamedPropertyAssignment(Assignment* expr) {
1796 // Assignment to a property, using a named store IC. 1727 // Assignment to a property, using a named store IC.
1797 Property* prop = expr->target()->AsProperty(); 1728 Property* prop = expr->target()->AsProperty();
1798 DCHECK(prop != NULL); 1729 DCHECK(prop != NULL);
1799 DCHECK(prop->key()->IsLiteral()); 1730 DCHECK(prop->key()->IsLiteral());
(...skipping 721 matching lines...) Expand 10 before | Expand all | Expand 10 after
2521 CallIC(code, expr->CountBinOpFeedbackId()); 2452 CallIC(code, expr->CountBinOpFeedbackId());
2522 patch_site.EmitPatchInfo(); 2453 patch_site.EmitPatchInfo();
2523 __ bind(&done); 2454 __ bind(&done);
2524 2455
2525 // Store the value returned in v0. 2456 // Store the value returned in v0.
2526 switch (assign_type) { 2457 switch (assign_type) {
2527 case VARIABLE: { 2458 case VARIABLE: {
2528 VariableProxy* proxy = expr->expression()->AsVariableProxy(); 2459 VariableProxy* proxy = expr->expression()->AsVariableProxy();
2529 if (expr->is_postfix()) { 2460 if (expr->is_postfix()) {
2530 { EffectContext context(this); 2461 { EffectContext context(this);
2531 EmitVariableAssignment(proxy->var(), Token::ASSIGN, expr->CountSlot(), 2462 EmitVariableAssignment(proxy->var(), Token::ASSIGN,
2532 proxy->hole_check_mode()); 2463 expr->CountSlot());
2533 PrepareForBailoutForId(expr->AssignmentId(), 2464 PrepareForBailoutForId(expr->AssignmentId(),
2534 BailoutState::TOS_REGISTER); 2465 BailoutState::TOS_REGISTER);
2535 context.Plug(v0); 2466 context.Plug(v0);
2536 } 2467 }
2537 // For all contexts except EffectConstant we have the result on 2468 // For all contexts except EffectConstant we have the result on
2538 // top of the stack. 2469 // top of the stack.
2539 if (!context()->IsEffect()) { 2470 if (!context()->IsEffect()) {
2540 context()->PlugTOS(); 2471 context()->PlugTOS();
2541 } 2472 }
2542 } else { 2473 } else {
2543 EmitVariableAssignment(proxy->var(), Token::ASSIGN, expr->CountSlot(), 2474 EmitVariableAssignment(proxy->var(), Token::ASSIGN, expr->CountSlot());
2544 proxy->hole_check_mode());
2545 PrepareForBailoutForId(expr->AssignmentId(), 2475 PrepareForBailoutForId(expr->AssignmentId(),
2546 BailoutState::TOS_REGISTER); 2476 BailoutState::TOS_REGISTER);
2547 context()->Plug(v0); 2477 context()->Plug(v0);
2548 } 2478 }
2549 break; 2479 break;
2550 } 2480 }
2551 case NAMED_PROPERTY: { 2481 case NAMED_PROPERTY: {
2552 __ mov(StoreDescriptor::ValueRegister(), result_register()); 2482 __ mov(StoreDescriptor::ValueRegister(), result_register());
2553 PopOperand(StoreDescriptor::ReceiverRegister()); 2483 PopOperand(StoreDescriptor::ReceiverRegister());
2554 CallStoreIC(expr->CountSlot(), prop->key()->AsLiteral()->value()); 2484 CallStoreIC(expr->CountSlot(), prop->key()->AsLiteral()->value());
(...skipping 328 matching lines...) Expand 10 before | Expand all | Expand 10 after
2883 reinterpret_cast<uint32_t>( 2813 reinterpret_cast<uint32_t>(
2884 isolate->builtins()->OnStackReplacement()->entry())); 2814 isolate->builtins()->OnStackReplacement()->entry()));
2885 return ON_STACK_REPLACEMENT; 2815 return ON_STACK_REPLACEMENT;
2886 } 2816 }
2887 2817
2888 2818
2889 } // namespace internal 2819 } // namespace internal
2890 } // namespace v8 2820 } // namespace v8
2891 2821
2892 #endif // V8_TARGET_ARCH_MIPS 2822 #endif // V8_TARGET_ARCH_MIPS
OLDNEW
« no previous file with comments | « src/full-codegen/ia32/full-codegen-ia32.cc ('k') | src/full-codegen/mips64/full-codegen-mips64.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698