OLD | NEW |
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 #include <limits.h> // For LONG_MIN, LONG_MAX. | 5 #include <limits.h> // For LONG_MIN, LONG_MAX. |
6 | 6 |
7 #include "src/v8.h" | 7 #include "src/v8.h" |
8 | 8 |
9 #if V8_TARGET_ARCH_MIPS64 | 9 #if V8_TARGET_ARCH_MIPS64 |
10 | 10 |
(...skipping 1633 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1644 DCHECK(nan || target); | 1644 DCHECK(nan || target); |
1645 // Check for unordered (NaN) cases. | 1645 // Check for unordered (NaN) cases. |
1646 if (nan) { | 1646 if (nan) { |
1647 bool long_branch = nan->is_bound() ? is_near(nan) : is_trampoline_emitted(); | 1647 bool long_branch = nan->is_bound() ? is_near(nan) : is_trampoline_emitted(); |
1648 if (kArchVariant != kMips64r6) { | 1648 if (kArchVariant != kMips64r6) { |
1649 if (long_branch) { | 1649 if (long_branch) { |
1650 Label skip; | 1650 Label skip; |
1651 c(UN, D, cmp1, cmp2); | 1651 c(UN, D, cmp1, cmp2); |
1652 bc1f(&skip); | 1652 bc1f(&skip); |
1653 nop(); | 1653 nop(); |
1654 Jr(nan, bd); | 1654 J(nan, bd); |
1655 bind(&skip); | 1655 bind(&skip); |
1656 } else { | 1656 } else { |
1657 c(UN, D, cmp1, cmp2); | 1657 c(UN, D, cmp1, cmp2); |
1658 bc1t(nan); | 1658 bc1t(nan); |
1659 if (bd == PROTECT) { | 1659 if (bd == PROTECT) { |
1660 nop(); | 1660 nop(); |
1661 } | 1661 } |
1662 } | 1662 } |
1663 } else { | 1663 } else { |
1664 // Use kDoubleCompareReg for comparison result. It has to be unavailable | 1664 // Use kDoubleCompareReg for comparison result. It has to be unavailable |
1665 // to lithium | 1665 // to lithium |
1666 // register allocator. | 1666 // register allocator. |
1667 DCHECK(!cmp1.is(kDoubleCompareReg) && !cmp2.is(kDoubleCompareReg)); | 1667 DCHECK(!cmp1.is(kDoubleCompareReg) && !cmp2.is(kDoubleCompareReg)); |
1668 if (long_branch) { | 1668 if (long_branch) { |
1669 Label skip; | 1669 Label skip; |
1670 cmp(UN, L, kDoubleCompareReg, cmp1, cmp2); | 1670 cmp(UN, L, kDoubleCompareReg, cmp1, cmp2); |
1671 bc1eqz(&skip, kDoubleCompareReg); | 1671 bc1eqz(&skip, kDoubleCompareReg); |
1672 nop(); | 1672 nop(); |
1673 Jr(nan, bd); | 1673 J(nan, bd); |
1674 bind(&skip); | 1674 bind(&skip); |
1675 } else { | 1675 } else { |
1676 cmp(UN, L, kDoubleCompareReg, cmp1, cmp2); | 1676 cmp(UN, L, kDoubleCompareReg, cmp1, cmp2); |
1677 bc1nez(nan, kDoubleCompareReg); | 1677 bc1nez(nan, kDoubleCompareReg); |
1678 if (bd == PROTECT) { | 1678 if (bd == PROTECT) { |
1679 nop(); | 1679 nop(); |
1680 } | 1680 } |
1681 } | 1681 } |
1682 } | 1682 } |
1683 } | 1683 } |
1684 | 1684 |
1685 if (target) { | 1685 if (target) { |
1686 bool long_branch = | 1686 bool long_branch = |
1687 target->is_bound() ? is_near(target) : is_trampoline_emitted(); | 1687 target->is_bound() ? is_near(target) : is_trampoline_emitted(); |
1688 if (long_branch) { | 1688 if (long_branch) { |
1689 Label skip; | 1689 Label skip; |
1690 Condition neg_cond = NegateFpuCondition(cond); | 1690 Condition neg_cond = NegateFpuCondition(cond); |
1691 BranchShortF(sizeField, &skip, neg_cond, cmp1, cmp2, bd); | 1691 BranchShortF(sizeField, &skip, neg_cond, cmp1, cmp2, bd); |
1692 Jr(target, bd); | 1692 J(target, bd); |
1693 bind(&skip); | 1693 bind(&skip); |
1694 } else { | 1694 } else { |
1695 BranchShortF(sizeField, target, cond, cmp1, cmp2, bd); | 1695 BranchShortF(sizeField, target, cond, cmp1, cmp2, bd); |
1696 } | 1696 } |
1697 } | 1697 } |
1698 } | 1698 } |
1699 | 1699 |
1700 | 1700 |
1701 void MacroAssembler::BranchShortF(SecondaryField sizeField, Label* target, | 1701 void MacroAssembler::BranchShortF(SecondaryField sizeField, Label* target, |
1702 Condition cc, FPURegister cmp1, | 1702 Condition cc, FPURegister cmp1, |
(...skipping 415 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2118 BranchDelaySlot bdslot) { | 2118 BranchDelaySlot bdslot) { |
2119 BranchShort(offset, cond, rs, rt, bdslot); | 2119 BranchShort(offset, cond, rs, rt, bdslot); |
2120 } | 2120 } |
2121 | 2121 |
2122 | 2122 |
2123 void MacroAssembler::Branch(Label* L, BranchDelaySlot bdslot) { | 2123 void MacroAssembler::Branch(Label* L, BranchDelaySlot bdslot) { |
2124 if (L->is_bound()) { | 2124 if (L->is_bound()) { |
2125 if (is_near(L)) { | 2125 if (is_near(L)) { |
2126 BranchShort(L, bdslot); | 2126 BranchShort(L, bdslot); |
2127 } else { | 2127 } else { |
2128 Jr(L, bdslot); | 2128 J(L, bdslot); |
2129 } | 2129 } |
2130 } else { | 2130 } else { |
2131 if (is_trampoline_emitted()) { | 2131 if (is_trampoline_emitted()) { |
2132 Jr(L, bdslot); | 2132 J(L, bdslot); |
2133 } else { | 2133 } else { |
2134 BranchShort(L, bdslot); | 2134 BranchShort(L, bdslot); |
2135 } | 2135 } |
2136 } | 2136 } |
2137 } | 2137 } |
2138 | 2138 |
2139 | 2139 |
2140 void MacroAssembler::Branch(Label* L, Condition cond, Register rs, | 2140 void MacroAssembler::Branch(Label* L, Condition cond, Register rs, |
2141 const Operand& rt, | 2141 const Operand& rt, |
2142 BranchDelaySlot bdslot) { | 2142 BranchDelaySlot bdslot) { |
2143 if (L->is_bound()) { | 2143 if (L->is_bound()) { |
2144 if (is_near(L)) { | 2144 if (is_near(L)) { |
2145 BranchShort(L, cond, rs, rt, bdslot); | 2145 BranchShort(L, cond, rs, rt, bdslot); |
2146 } else { | 2146 } else { |
2147 if (cond != cc_always) { | 2147 if (cond != cc_always) { |
2148 Label skip; | 2148 Label skip; |
2149 Condition neg_cond = NegateCondition(cond); | 2149 Condition neg_cond = NegateCondition(cond); |
2150 BranchShort(&skip, neg_cond, rs, rt); | 2150 BranchShort(&skip, neg_cond, rs, rt); |
2151 Jr(L, bdslot); | 2151 J(L, bdslot); |
2152 bind(&skip); | 2152 bind(&skip); |
2153 } else { | 2153 } else { |
2154 Jr(L, bdslot); | 2154 J(L, bdslot); |
2155 } | 2155 } |
2156 } | 2156 } |
2157 } else { | 2157 } else { |
2158 if (is_trampoline_emitted()) { | 2158 if (is_trampoline_emitted()) { |
2159 if (cond != cc_always) { | 2159 if (cond != cc_always) { |
2160 Label skip; | 2160 Label skip; |
2161 Condition neg_cond = NegateCondition(cond); | 2161 Condition neg_cond = NegateCondition(cond); |
2162 BranchShort(&skip, neg_cond, rs, rt); | 2162 BranchShort(&skip, neg_cond, rs, rt); |
2163 Jr(L, bdslot); | 2163 J(L, bdslot); |
2164 bind(&skip); | 2164 bind(&skip); |
2165 } else { | 2165 } else { |
2166 Jr(L, bdslot); | 2166 J(L, bdslot); |
2167 } | 2167 } |
2168 } else { | 2168 } else { |
2169 BranchShort(L, cond, rs, rt, bdslot); | 2169 BranchShort(L, cond, rs, rt, bdslot); |
2170 } | 2170 } |
2171 } | 2171 } |
2172 } | 2172 } |
2173 | 2173 |
2174 | 2174 |
2175 void MacroAssembler::Branch(Label* L, | 2175 void MacroAssembler::Branch(Label* L, |
2176 Condition cond, | 2176 Condition cond, |
(...skipping 545 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2722 BranchDelaySlot bdslot) { | 2722 BranchDelaySlot bdslot) { |
2723 BranchAndLinkShort(offset, cond, rs, rt, bdslot); | 2723 BranchAndLinkShort(offset, cond, rs, rt, bdslot); |
2724 } | 2724 } |
2725 | 2725 |
2726 | 2726 |
2727 void MacroAssembler::BranchAndLink(Label* L, BranchDelaySlot bdslot) { | 2727 void MacroAssembler::BranchAndLink(Label* L, BranchDelaySlot bdslot) { |
2728 if (L->is_bound()) { | 2728 if (L->is_bound()) { |
2729 if (is_near(L)) { | 2729 if (is_near(L)) { |
2730 BranchAndLinkShort(L, bdslot); | 2730 BranchAndLinkShort(L, bdslot); |
2731 } else { | 2731 } else { |
2732 Jalr(L, bdslot); | 2732 Jal(L, bdslot); |
2733 } | 2733 } |
2734 } else { | 2734 } else { |
2735 if (is_trampoline_emitted()) { | 2735 if (is_trampoline_emitted()) { |
2736 Jalr(L, bdslot); | 2736 Jal(L, bdslot); |
2737 } else { | 2737 } else { |
2738 BranchAndLinkShort(L, bdslot); | 2738 BranchAndLinkShort(L, bdslot); |
2739 } | 2739 } |
2740 } | 2740 } |
2741 } | 2741 } |
2742 | 2742 |
2743 | 2743 |
2744 void MacroAssembler::BranchAndLink(Label* L, Condition cond, Register rs, | 2744 void MacroAssembler::BranchAndLink(Label* L, Condition cond, Register rs, |
2745 const Operand& rt, | 2745 const Operand& rt, |
2746 BranchDelaySlot bdslot) { | 2746 BranchDelaySlot bdslot) { |
2747 if (L->is_bound()) { | 2747 if (L->is_bound()) { |
2748 if (is_near(L)) { | 2748 if (is_near(L)) { |
2749 BranchAndLinkShort(L, cond, rs, rt, bdslot); | 2749 BranchAndLinkShort(L, cond, rs, rt, bdslot); |
2750 } else { | 2750 } else { |
2751 Label skip; | 2751 Label skip; |
2752 Condition neg_cond = NegateCondition(cond); | 2752 Condition neg_cond = NegateCondition(cond); |
2753 BranchShort(&skip, neg_cond, rs, rt); | 2753 BranchShort(&skip, neg_cond, rs, rt); |
2754 Jalr(L, bdslot); | 2754 J(L, bdslot); |
2755 bind(&skip); | 2755 bind(&skip); |
2756 } | 2756 } |
2757 } else { | 2757 } else { |
2758 if (is_trampoline_emitted()) { | 2758 if (is_trampoline_emitted()) { |
2759 Label skip; | 2759 Label skip; |
2760 Condition neg_cond = NegateCondition(cond); | 2760 Condition neg_cond = NegateCondition(cond); |
2761 BranchShort(&skip, neg_cond, rs, rt); | 2761 BranchShort(&skip, neg_cond, rs, rt); |
2762 Jalr(L, bdslot); | 2762 Jal(L, bdslot); |
2763 bind(&skip); | 2763 bind(&skip); |
2764 } else { | 2764 } else { |
2765 BranchAndLinkShort(L, cond, rs, rt, bdslot); | 2765 BranchAndLinkShort(L, cond, rs, rt, bdslot); |
2766 } | 2766 } |
2767 } | 2767 } |
2768 } | 2768 } |
2769 | 2769 |
2770 | 2770 |
2771 // We need to use a bgezal or bltzal, but they can't be used directly with the | 2771 // We need to use a bgezal or bltzal, but they can't be used directly with the |
2772 // slt instructions. We could use sub or add instead but we would miss overflow | 2772 // slt instructions. We could use sub or add instead but we would miss overflow |
(...skipping 407 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3180 | 3180 |
3181 | 3181 |
3182 void MacroAssembler::Ret(Condition cond, | 3182 void MacroAssembler::Ret(Condition cond, |
3183 Register rs, | 3183 Register rs, |
3184 const Operand& rt, | 3184 const Operand& rt, |
3185 BranchDelaySlot bd) { | 3185 BranchDelaySlot bd) { |
3186 Jump(ra, cond, rs, rt, bd); | 3186 Jump(ra, cond, rs, rt, bd); |
3187 } | 3187 } |
3188 | 3188 |
3189 | 3189 |
| 3190 void MacroAssembler::J(Label* L, BranchDelaySlot bdslot) { |
| 3191 BlockTrampolinePoolScope block_trampoline_pool(this); |
| 3192 |
| 3193 uint64_t imm28; |
| 3194 imm28 = jump_address(L); |
| 3195 { |
| 3196 BlockGrowBufferScope block_buf_growth(this); |
| 3197 // Buffer growth (and relocation) must be blocked for internal references |
| 3198 // until associated instructions are emitted and available to be patched. |
| 3199 RecordRelocInfo(RelocInfo::INTERNAL_REFERENCE_ENCODED); |
| 3200 j(imm28); |
| 3201 } |
| 3202 // Emit a nop in the branch delay slot if required. |
| 3203 if (bdslot == PROTECT) nop(); |
| 3204 } |
| 3205 |
| 3206 |
| 3207 void MacroAssembler::Jal(Label* L, BranchDelaySlot bdslot) { |
| 3208 BlockTrampolinePoolScope block_trampoline_pool(this); |
| 3209 |
| 3210 uint64_t imm28; |
| 3211 imm28 = jump_address(L); |
| 3212 { |
| 3213 BlockGrowBufferScope block_buf_growth(this); |
| 3214 // Buffer growth (and relocation) must be blocked for internal references |
| 3215 // until associated instructions are emitted and available to be patched. |
| 3216 RecordRelocInfo(RelocInfo::INTERNAL_REFERENCE_ENCODED); |
| 3217 jal(imm28); |
| 3218 } |
| 3219 // Emit a nop in the branch delay slot if required. |
| 3220 if (bdslot == PROTECT) nop(); |
| 3221 } |
| 3222 |
| 3223 |
3190 void MacroAssembler::Jr(Label* L, BranchDelaySlot bdslot) { | 3224 void MacroAssembler::Jr(Label* L, BranchDelaySlot bdslot) { |
3191 BlockTrampolinePoolScope block_trampoline_pool(this); | 3225 BlockTrampolinePoolScope block_trampoline_pool(this); |
3192 | 3226 |
3193 uint64_t imm64; | 3227 uint64_t imm64; |
3194 imm64 = jump_address(L); | 3228 imm64 = jump_address(L); |
3195 { BlockGrowBufferScope block_buf_growth(this); | 3229 { BlockGrowBufferScope block_buf_growth(this); |
3196 // Buffer growth (and relocation) must be blocked for internal references | 3230 // Buffer growth (and relocation) must be blocked for internal references |
3197 // until associated instructions are emitted and available to be patched. | 3231 // until associated instructions are emitted and available to be patched. |
3198 RecordRelocInfo(RelocInfo::INTERNAL_REFERENCE_ENCODED); | 3232 RecordRelocInfo(RelocInfo::INTERNAL_REFERENCE_ENCODED); |
3199 li(at, Operand(imm64), ADDRESS_LOAD); | 3233 li(at, Operand(imm64), ADDRESS_LOAD); |
(...skipping 2994 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6194 } | 6228 } |
6195 if (mag.shift > 0) sra(result, result, mag.shift); | 6229 if (mag.shift > 0) sra(result, result, mag.shift); |
6196 srl(at, dividend, 31); | 6230 srl(at, dividend, 31); |
6197 Addu(result, result, Operand(at)); | 6231 Addu(result, result, Operand(at)); |
6198 } | 6232 } |
6199 | 6233 |
6200 | 6234 |
6201 } } // namespace v8::internal | 6235 } } // namespace v8::internal |
6202 | 6236 |
6203 #endif // V8_TARGET_ARCH_MIPS64 | 6237 #endif // V8_TARGET_ARCH_MIPS64 |
OLD | NEW |