OLD | NEW |
---|---|
1 // Copyright (c) 1994-2006 Sun Microsystems Inc. | 1 // Copyright (c) 1994-2006 Sun Microsystems Inc. |
2 // All Rights Reserved. | 2 // All Rights Reserved. |
3 // | 3 // |
4 // Redistribution and use in source and binary forms, with or without | 4 // Redistribution and use in source and binary forms, with or without |
5 // modification, are permitted provided that the following conditions | 5 // modification, are permitted provided that the following conditions |
6 // are met: | 6 // are met: |
7 // | 7 // |
8 // - Redistributions of source code must retain the above copyright notice, | 8 // - Redistributions of source code must retain the above copyright notice, |
9 // this list of conditions and the following disclaimer. | 9 // this list of conditions and the following disclaimer. |
10 // | 10 // |
(...skipping 130 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
141 // ----------------------------------------------------------------------------- | 141 // ----------------------------------------------------------------------------- |
142 // Implementation of RelocInfo | 142 // Implementation of RelocInfo |
143 | 143 |
144 const int RelocInfo::kApplyMask = 1 << RelocInfo::INTERNAL_REFERENCE | | 144 const int RelocInfo::kApplyMask = 1 << RelocInfo::INTERNAL_REFERENCE | |
145 1 << RelocInfo::INTERNAL_REFERENCE_ENCODED; | 145 1 << RelocInfo::INTERNAL_REFERENCE_ENCODED; |
146 | 146 |
147 | 147 |
148 bool RelocInfo::IsCodedSpecially() { | 148 bool RelocInfo::IsCodedSpecially() { |
149 // The deserializer needs to know whether a pointer is specially | 149 // The deserializer needs to know whether a pointer is specially |
150 // coded. Being specially coded on PPC means that it is a lis/ori | 150 // coded. Being specially coded on PPC means that it is a lis/ori |
151 // instruction sequence, and these are always the case inside code | 151 // instruction sequence or is a constant pool entry, and these are |
152 // objects. | 152 // always the case inside code objects. |
153 return true; | 153 return true; |
154 } | 154 } |
155 | 155 |
156 | 156 |
157 bool RelocInfo::IsInConstantPool() { | 157 bool RelocInfo::IsInConstantPool() { |
158 if (FLAG_enable_embedded_constant_pool) { | |
159 Address constant_pool = host_->constant_pool(); | |
160 return (constant_pool && Assembler::IsConstantPoolLoadStart(pc_)); | |
161 } | |
158 return false; | 162 return false; |
159 } | 163 } |
160 | 164 |
161 | 165 |
162 // ----------------------------------------------------------------------------- | 166 // ----------------------------------------------------------------------------- |
163 // Implementation of Operand and MemOperand | 167 // Implementation of Operand and MemOperand |
164 // See assembler-ppc-inl.h for inlined constructors | 168 // See assembler-ppc-inl.h for inlined constructors |
165 | 169 |
166 Operand::Operand(Handle<Object> handle) { | 170 Operand::Operand(Handle<Object> handle) { |
167 AllowDeferredHandleDereference using_raw_address; | 171 AllowDeferredHandleDereference using_raw_address; |
(...skipping 26 matching lines...) Expand all Loading... | |
194 } | 198 } |
195 | 199 |
196 | 200 |
197 // ----------------------------------------------------------------------------- | 201 // ----------------------------------------------------------------------------- |
198 // Specific instructions, constants, and masks. | 202 // Specific instructions, constants, and masks. |
199 | 203 |
200 | 204 |
201 Assembler::Assembler(Isolate* isolate, void* buffer, int buffer_size) | 205 Assembler::Assembler(Isolate* isolate, void* buffer, int buffer_size) |
202 : AssemblerBase(isolate, buffer, buffer_size), | 206 : AssemblerBase(isolate, buffer, buffer_size), |
203 recorded_ast_id_(TypeFeedbackId::None()), | 207 recorded_ast_id_(TypeFeedbackId::None()), |
208 constant_pool_builder_(15, 15), // 15-bit unsigned reach | |
rmcilroy
2015/05/20 14:32:12
same comments as Arm
MTBrandyberry
2015/05/20 22:28:23
Done.
| |
204 positions_recorder_(this) { | 209 positions_recorder_(this) { |
205 reloc_info_writer.Reposition(buffer_ + buffer_size_, pc_); | 210 reloc_info_writer.Reposition(buffer_ + buffer_size_, pc_); |
206 | 211 |
207 no_trampoline_pool_before_ = 0; | 212 no_trampoline_pool_before_ = 0; |
208 trampoline_pool_blocked_nesting_ = 0; | 213 trampoline_pool_blocked_nesting_ = 0; |
214 constant_pool_entry_sharing_blocked_nesting_ = 0; | |
209 // We leave space (kMaxBlockTrampolineSectionSize) | 215 // We leave space (kMaxBlockTrampolineSectionSize) |
210 // for BlockTrampolinePoolScope buffer. | 216 // for BlockTrampolinePoolScope buffer. |
211 next_buffer_check_ = | 217 next_buffer_check_ = |
212 FLAG_force_long_branches ? kMaxInt : kMaxCondBranchReach - | 218 FLAG_force_long_branches ? kMaxInt : kMaxCondBranchReach - |
213 kMaxBlockTrampolineSectionSize; | 219 kMaxBlockTrampolineSectionSize; |
214 internal_trampoline_exception_ = false; | 220 internal_trampoline_exception_ = false; |
215 last_bound_pos_ = 0; | 221 last_bound_pos_ = 0; |
216 trampoline_emitted_ = FLAG_force_long_branches; | 222 trampoline_emitted_ = FLAG_force_long_branches; |
217 unbound_labels_count_ = 0; | 223 unbound_labels_count_ = 0; |
218 ClearRecordedAstId(); | 224 ClearRecordedAstId(); |
219 relocations_.reserve(128); | 225 relocations_.reserve(128); |
220 } | 226 } |
221 | 227 |
222 | 228 |
223 void Assembler::GetCode(CodeDesc* desc) { | 229 void Assembler::GetCode(CodeDesc* desc) { |
230 // Emit constant pool if necessary. | |
231 int offset = EmitConstantPool(); | |
232 | |
224 EmitRelocations(); | 233 EmitRelocations(); |
225 | 234 |
226 // Set up code descriptor. | 235 // Set up code descriptor. |
227 desc->buffer = buffer_; | 236 desc->buffer = buffer_; |
228 desc->buffer_size = buffer_size_; | 237 desc->buffer_size = buffer_size_; |
229 desc->instr_size = pc_offset(); | 238 desc->instr_size = pc_offset(); |
230 desc->reloc_size = (buffer_ + buffer_size_) - reloc_info_writer.pos(); | 239 desc->reloc_size = (buffer_ + buffer_size_) - reloc_info_writer.pos(); |
240 desc->constant_pool_size = (offset ? desc->instr_size - offset : 0); | |
231 desc->origin = this; | 241 desc->origin = this; |
232 } | 242 } |
233 | 243 |
234 | 244 |
235 void Assembler::Align(int m) { | 245 void Assembler::Align(int m) { |
236 #if V8_TARGET_ARCH_PPC64 | 246 #if V8_TARGET_ARCH_PPC64 |
237 DCHECK(m >= 4 && base::bits::IsPowerOfTwo64(m)); | 247 DCHECK(m >= 4 && base::bits::IsPowerOfTwo64(m)); |
238 #else | 248 #else |
239 DCHECK(m >= 4 && base::bits::IsPowerOfTwo32(m)); | 249 DCHECK(m >= 4 && base::bits::IsPowerOfTwo32(m)); |
240 #endif | 250 #endif |
(...skipping 223 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
464 int32_t offset = target_pos + SIGN_EXT_IMM16(operands & kImm16Mask); | 474 int32_t offset = target_pos + SIGN_EXT_IMM16(operands & kImm16Mask); |
465 CodePatcher patcher(reinterpret_cast<byte*>(buffer_ + pos), 2, | 475 CodePatcher patcher(reinterpret_cast<byte*>(buffer_ + pos), 2, |
466 CodePatcher::DONT_FLUSH); | 476 CodePatcher::DONT_FLUSH); |
467 patcher.masm()->bitwise_add32(dst, base, offset); | 477 patcher.masm()->bitwise_add32(dst, base, offset); |
468 break; | 478 break; |
469 } | 479 } |
470 case kUnboundMovLabelAddrOpcode: { | 480 case kUnboundMovLabelAddrOpcode: { |
471 // Load the address of the label in a register. | 481 // Load the address of the label in a register. |
472 Register dst = Register::from_code(instr_at(pos + kInstrSize)); | 482 Register dst = Register::from_code(instr_at(pos + kInstrSize)); |
473 CodePatcher patcher(reinterpret_cast<byte*>(buffer_ + pos), | 483 CodePatcher patcher(reinterpret_cast<byte*>(buffer_ + pos), |
474 kMovInstructions, CodePatcher::DONT_FLUSH); | 484 kMovInstructionsNoConstantPool, |
485 CodePatcher::DONT_FLUSH); | |
475 // Keep internal references relative until EmitRelocations. | 486 // Keep internal references relative until EmitRelocations. |
476 patcher.masm()->bitwise_mov(dst, target_pos); | 487 patcher.masm()->bitwise_mov(dst, target_pos); |
477 break; | 488 break; |
478 } | 489 } |
479 case kUnboundJumpTableEntryOpcode: { | 490 case kUnboundJumpTableEntryOpcode: { |
480 CodePatcher patcher(reinterpret_cast<byte*>(buffer_ + pos), | 491 CodePatcher patcher(reinterpret_cast<byte*>(buffer_ + pos), |
481 kPointerSize / kInstrSize, CodePatcher::DONT_FLUSH); | 492 kPointerSize / kInstrSize, CodePatcher::DONT_FLUSH); |
482 // Keep internal references relative until EmitRelocations. | 493 // Keep internal references relative until EmitRelocations. |
483 patcher.masm()->emit_ptr(target_pos); | 494 patcher.masm()->dp(target_pos); |
484 break; | 495 break; |
485 } | 496 } |
486 default: | 497 default: |
487 DCHECK(false); | 498 DCHECK(false); |
488 break; | 499 break; |
489 } | 500 } |
490 } | 501 } |
491 | 502 |
492 | 503 |
493 int Assembler::max_reach_from(int pos) { | 504 int Assembler::max_reach_from(int pos) { |
(...skipping 991 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1485 | 1496 |
1486 | 1497 |
1487 // Function descriptor for AIX. | 1498 // Function descriptor for AIX. |
1488 // Code address skips the function descriptor "header". | 1499 // Code address skips the function descriptor "header". |
1489 // TOC and static chain are ignored and set to 0. | 1500 // TOC and static chain are ignored and set to 0. |
1490 void Assembler::function_descriptor() { | 1501 void Assembler::function_descriptor() { |
1491 #if ABI_USES_FUNCTION_DESCRIPTORS | 1502 #if ABI_USES_FUNCTION_DESCRIPTORS |
1492 Label instructions; | 1503 Label instructions; |
1493 DCHECK(pc_offset() == 0); | 1504 DCHECK(pc_offset() == 0); |
1494 emit_label_addr(&instructions); | 1505 emit_label_addr(&instructions); |
1495 emit_ptr(0); | 1506 dp(0); |
1496 emit_ptr(0); | 1507 dp(0); |
1497 bind(&instructions); | 1508 bind(&instructions); |
1498 #endif | 1509 #endif |
1499 } | 1510 } |
1500 | 1511 |
1501 | 1512 |
1513 int Assembler::instructions_required_for_mov(Register dst, | |
1514 const Operand& src) const { | |
1515 bool canOptimize = | |
1516 !(src.must_output_reloc_info(this) || is_trampoline_pool_blocked()); | |
1517 if (use_constant_pool_for_mov(dst, src, canOptimize)) { | |
1518 if (ConstantPoolOverflow()) return kMovInstructionsConstantPool + 1; | |
1519 return kMovInstructionsConstantPool; | |
1520 } | |
1521 DCHECK(!canOptimize); | |
1522 return kMovInstructionsNoConstantPool; | |
1523 } | |
1524 | |
1525 | |
1526 bool Assembler::use_constant_pool_for_mov(Register dst, const Operand& src, | |
1527 bool canOptimize) const { | |
1528 if (!FLAG_enable_embedded_constant_pool || !is_constant_pool_available()) { | |
1529 // If there is no constant pool available, we must use a mov | |
1530 // immediate sequence. | |
1531 return false; | |
1532 } | |
1533 | |
1534 intptr_t value = src.immediate(); | |
1535 #if V8_TARGET_ARCH_PPC64 | |
1536 bool allowOverflow = !((canOptimize && is_int32(value)) || dst.is(r0)); | |
1537 #else | |
1538 bool allowOverflow = !(canOptimize || dst.is(r0)); | |
1539 #endif | |
1540 if (canOptimize && is_int16(value)) { | |
1541 // Prefer a single-instruction load-immediate. | |
1542 return false; | |
1543 } | |
1544 if (!allowOverflow && ConstantPoolOverflow()) { | |
1545 // Prefer non-relocatable two-instruction bitwise-mov32 over | |
1546 // overflow sequence. | |
1547 return false; | |
1548 } | |
1549 | |
1550 return true; | |
1551 } | |
1552 | |
1553 | |
1502 void Assembler::EnsureSpaceFor(int space_needed) { | 1554 void Assembler::EnsureSpaceFor(int space_needed) { |
1503 if (buffer_space() <= (kGap + space_needed)) { | 1555 if (buffer_space() <= (kGap + space_needed)) { |
1504 GrowBuffer(space_needed); | 1556 GrowBuffer(space_needed); |
1505 } | 1557 } |
1506 } | 1558 } |
1507 | 1559 |
1508 | 1560 |
1509 bool Operand::must_output_reloc_info(const Assembler* assembler) const { | 1561 bool Operand::must_output_reloc_info(const Assembler* assembler) const { |
1510 if (rmode_ == RelocInfo::EXTERNAL_REFERENCE) { | 1562 if (rmode_ == RelocInfo::EXTERNAL_REFERENCE) { |
1511 if (assembler != NULL && assembler->predictable_code_size()) return true; | 1563 if (assembler != NULL && assembler->predictable_code_size()) return true; |
(...skipping 12 matching lines...) Expand all Loading... | |
1524 // Todo - break this dependency so we can optimize mov() in general | 1576 // Todo - break this dependency so we can optimize mov() in general |
1525 // and only use the generic version when we require a fixed sequence | 1577 // and only use the generic version when we require a fixed sequence |
1526 void Assembler::mov(Register dst, const Operand& src) { | 1578 void Assembler::mov(Register dst, const Operand& src) { |
1527 intptr_t value = src.immediate(); | 1579 intptr_t value = src.immediate(); |
1528 bool relocatable = src.must_output_reloc_info(this); | 1580 bool relocatable = src.must_output_reloc_info(this); |
1529 bool canOptimize; | 1581 bool canOptimize; |
1530 | 1582 |
1531 canOptimize = | 1583 canOptimize = |
1532 !(relocatable || (is_trampoline_pool_blocked() && !is_int16(value))); | 1584 !(relocatable || (is_trampoline_pool_blocked() && !is_int16(value))); |
1533 | 1585 |
1586 if (use_constant_pool_for_mov(dst, src, canOptimize)) { | |
1587 DCHECK(is_constant_pool_available()); | |
1588 if (relocatable) { | |
1589 RecordRelocInfo(src.rmode_); | |
1590 } | |
1591 ConstantPoolEntry::Access access = ConstantPoolAddEntry(src.rmode_, value); | |
1592 #if V8_TARGET_ARCH_PPC64 | |
1593 if (access == ConstantPoolEntry::OVERFLOWED) { | |
1594 addis(dst, kConstantPoolRegister, Operand::Zero()); | |
1595 ld(dst, MemOperand(dst, 0)); | |
1596 } else { | |
1597 ld(dst, MemOperand(kConstantPoolRegister, 0)); | |
1598 } | |
1599 #else | |
1600 if (access == ConstantPoolEntry::OVERFLOWED) { | |
1601 addis(dst, kConstantPoolRegister, Operand::Zero()); | |
1602 lwz(dst, MemOperand(dst, 0)); | |
1603 } else { | |
1604 lwz(dst, MemOperand(kConstantPoolRegister, 0)); | |
1605 } | |
1606 #endif | |
1607 return; | |
1608 } | |
1609 | |
1534 if (canOptimize) { | 1610 if (canOptimize) { |
1535 if (is_int16(value)) { | 1611 if (is_int16(value)) { |
1536 li(dst, Operand(value)); | 1612 li(dst, Operand(value)); |
1537 } else { | 1613 } else { |
1538 uint16_t u16; | 1614 uint16_t u16; |
1539 #if V8_TARGET_ARCH_PPC64 | 1615 #if V8_TARGET_ARCH_PPC64 |
1540 if (is_int32(value)) { | 1616 if (is_int32(value)) { |
1541 #endif | 1617 #endif |
1542 lis(dst, Operand(value >> 16)); | 1618 lis(dst, Operand(value >> 16)); |
1543 #if V8_TARGET_ARCH_PPC64 | 1619 #if V8_TARGET_ARCH_PPC64 |
(...skipping 145 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1689 DCHECK(is_int26(link)); | 1765 DCHECK(is_int26(link)); |
1690 | 1766 |
1691 // When the label is bound, these instructions will be patched | 1767 // When the label is bound, these instructions will be patched |
1692 // with a multi-instruction mov sequence that will load the | 1768 // with a multi-instruction mov sequence that will load the |
1693 // destination register with the address of the label. | 1769 // destination register with the address of the label. |
1694 // | 1770 // |
1695 // target_at extracts the link and target_at_put patches the instructions. | 1771 // target_at extracts the link and target_at_put patches the instructions. |
1696 BlockTrampolinePoolScope block_trampoline_pool(this); | 1772 BlockTrampolinePoolScope block_trampoline_pool(this); |
1697 emit(kUnboundMovLabelAddrOpcode | (link & kImm26Mask)); | 1773 emit(kUnboundMovLabelAddrOpcode | (link & kImm26Mask)); |
1698 emit(dst.code()); | 1774 emit(dst.code()); |
1699 DCHECK(kMovInstructions >= 2); | 1775 DCHECK(kMovInstructionsNoConstantPool >= 2); |
1700 for (int i = 0; i < kMovInstructions - 2; i++) nop(); | 1776 for (int i = 0; i < kMovInstructionsNoConstantPool - 2; i++) nop(); |
1701 } | 1777 } |
1702 } | 1778 } |
1703 | 1779 |
1704 | 1780 |
1705 void Assembler::emit_label_addr(Label* label) { | 1781 void Assembler::emit_label_addr(Label* label) { |
1706 CheckBuffer(); | 1782 CheckBuffer(); |
1707 RecordRelocInfo(RelocInfo::INTERNAL_REFERENCE); | 1783 RecordRelocInfo(RelocInfo::INTERNAL_REFERENCE); |
1708 int position = link(label); | 1784 int position = link(label); |
1709 if (label->is_bound()) { | 1785 if (label->is_bound()) { |
1710 // Keep internal references relative until EmitRelocations. | 1786 // Keep internal references relative until EmitRelocations. |
1711 emit_ptr(position); | 1787 dp(position); |
1712 } else { | 1788 } else { |
1713 // Encode internal reference to unbound label. We use a dummy opcode | 1789 // Encode internal reference to unbound label. We use a dummy opcode |
1714 // such that it won't collide with any opcode that might appear in the | 1790 // such that it won't collide with any opcode that might appear in the |
1715 // label's chain. | 1791 // label's chain. |
1716 int link = position - pc_offset(); | 1792 int link = position - pc_offset(); |
1717 DCHECK_EQ(0, link & 3); | 1793 DCHECK_EQ(0, link & 3); |
1718 link >>= 2; | 1794 link >>= 2; |
1719 DCHECK(is_int26(link)); | 1795 DCHECK(is_int26(link)); |
1720 | 1796 |
1721 // When the label is bound, the instruction(s) will be patched | 1797 // When the label is bound, the instruction(s) will be patched |
(...skipping 110 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1832 | 1908 |
1833 | 1909 |
1834 void Assembler::isync() { emit(EXT1 | ISYNC); } | 1910 void Assembler::isync() { emit(EXT1 | ISYNC); } |
1835 | 1911 |
1836 | 1912 |
1837 // Floating point support | 1913 // Floating point support |
1838 | 1914 |
1839 void Assembler::lfd(const DoubleRegister frt, const MemOperand& src) { | 1915 void Assembler::lfd(const DoubleRegister frt, const MemOperand& src) { |
1840 int offset = src.offset(); | 1916 int offset = src.offset(); |
1841 Register ra = src.ra(); | 1917 Register ra = src.ra(); |
1918 DCHECK(!ra.is(r0)); | |
1842 DCHECK(is_int16(offset)); | 1919 DCHECK(is_int16(offset)); |
1843 int imm16 = offset & kImm16Mask; | 1920 int imm16 = offset & kImm16Mask; |
1844 // could be x_form instruction with some casting magic | 1921 // could be x_form instruction with some casting magic |
1845 emit(LFD | frt.code() * B21 | ra.code() * B16 | imm16); | 1922 emit(LFD | frt.code() * B21 | ra.code() * B16 | imm16); |
1846 } | 1923 } |
1847 | 1924 |
1848 | 1925 |
1849 void Assembler::lfdu(const DoubleRegister frt, const MemOperand& src) { | 1926 void Assembler::lfdu(const DoubleRegister frt, const MemOperand& src) { |
1850 int offset = src.offset(); | 1927 int offset = src.offset(); |
1851 Register ra = src.ra(); | 1928 Register ra = src.ra(); |
1929 DCHECK(!ra.is(r0)); | |
1852 DCHECK(is_int16(offset)); | 1930 DCHECK(is_int16(offset)); |
1853 int imm16 = offset & kImm16Mask; | 1931 int imm16 = offset & kImm16Mask; |
1854 // could be x_form instruction with some casting magic | 1932 // could be x_form instruction with some casting magic |
1855 emit(LFDU | frt.code() * B21 | ra.code() * B16 | imm16); | 1933 emit(LFDU | frt.code() * B21 | ra.code() * B16 | imm16); |
1856 } | 1934 } |
1857 | 1935 |
1858 | 1936 |
1859 void Assembler::lfdx(const DoubleRegister frt, const MemOperand& src) { | 1937 void Assembler::lfdx(const DoubleRegister frt, const MemOperand& src) { |
1860 Register ra = src.ra(); | 1938 Register ra = src.ra(); |
1861 Register rb = src.rb(); | 1939 Register rb = src.rb(); |
(...skipping 379 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2241 } | 2319 } |
2242 | 2320 |
2243 | 2321 |
2244 void Assembler::dd(uint32_t data) { | 2322 void Assembler::dd(uint32_t data) { |
2245 CheckBuffer(); | 2323 CheckBuffer(); |
2246 *reinterpret_cast<uint32_t*>(pc_) = data; | 2324 *reinterpret_cast<uint32_t*>(pc_) = data; |
2247 pc_ += sizeof(uint32_t); | 2325 pc_ += sizeof(uint32_t); |
2248 } | 2326 } |
2249 | 2327 |
2250 | 2328 |
2251 void Assembler::emit_ptr(intptr_t data) { | 2329 void Assembler::dq(uint64_t value) { |
2252 CheckBuffer(); | 2330 CheckBuffer(); |
2253 *reinterpret_cast<intptr_t*>(pc_) = data; | 2331 *reinterpret_cast<uint64_t*>(pc_) = value; |
2254 pc_ += sizeof(intptr_t); | 2332 pc_ += sizeof(uint64_t); |
2255 } | 2333 } |
2256 | 2334 |
2257 | 2335 |
2258 void Assembler::emit_double(double value) { | 2336 void Assembler::dp(uintptr_t data) { |
2259 CheckBuffer(); | 2337 CheckBuffer(); |
2260 *reinterpret_cast<double*>(pc_) = value; | 2338 *reinterpret_cast<uintptr_t*>(pc_) = data; |
2261 pc_ += sizeof(double); | 2339 pc_ += sizeof(uintptr_t); |
2262 } | 2340 } |
2263 | 2341 |
2264 | 2342 |
2265 void Assembler::RecordRelocInfo(RelocInfo::Mode rmode, intptr_t data) { | 2343 void Assembler::RecordRelocInfo(RelocInfo::Mode rmode, intptr_t data) { |
2344 if (RelocInfo::IsNone(rmode) || | |
2345 // Don't record external references unless the heap will be serialized. | |
2346 (rmode == RelocInfo::EXTERNAL_REFERENCE && !serializer_enabled() && | |
2347 !emit_debug_code())) { | |
2348 return; | |
2349 } | |
2350 if (rmode == RelocInfo::CODE_TARGET_WITH_ID) { | |
2351 data = RecordedAstId().ToInt(); | |
2352 ClearRecordedAstId(); | |
2353 } | |
2266 DeferredRelocInfo rinfo(pc_offset(), rmode, data); | 2354 DeferredRelocInfo rinfo(pc_offset(), rmode, data); |
2267 RecordRelocInfo(rinfo); | 2355 relocations_.push_back(rinfo); |
2268 } | 2356 } |
2269 | 2357 |
2270 | 2358 |
2271 void Assembler::RecordRelocInfo(const DeferredRelocInfo& rinfo) { | |
2272 if (rinfo.rmode() >= RelocInfo::JS_RETURN && | |
2273 rinfo.rmode() <= RelocInfo::DEBUG_BREAK_SLOT) { | |
2274 // Adjust code for new modes. | |
2275 DCHECK(RelocInfo::IsDebugBreakSlot(rinfo.rmode()) || | |
2276 RelocInfo::IsJSReturn(rinfo.rmode()) || | |
2277 RelocInfo::IsComment(rinfo.rmode()) || | |
2278 RelocInfo::IsPosition(rinfo.rmode())); | |
2279 } | |
2280 if (!RelocInfo::IsNone(rinfo.rmode())) { | |
2281 // Don't record external references unless the heap will be serialized. | |
2282 if (rinfo.rmode() == RelocInfo::EXTERNAL_REFERENCE) { | |
2283 if (!serializer_enabled() && !emit_debug_code()) { | |
2284 return; | |
2285 } | |
2286 } | |
2287 if (rinfo.rmode() == RelocInfo::CODE_TARGET_WITH_ID) { | |
2288 DeferredRelocInfo reloc_info_with_ast_id(rinfo.position(), rinfo.rmode(), | |
2289 RecordedAstId().ToInt()); | |
2290 ClearRecordedAstId(); | |
2291 relocations_.push_back(reloc_info_with_ast_id); | |
2292 } else { | |
2293 relocations_.push_back(rinfo); | |
2294 } | |
2295 } | |
2296 } | |
2297 | |
2298 | |
2299 void Assembler::EmitRelocations() { | 2359 void Assembler::EmitRelocations() { |
2300 EnsureSpaceFor(relocations_.size() * kMaxRelocSize); | 2360 EnsureSpaceFor(relocations_.size() * kMaxRelocSize); |
2301 | 2361 |
2302 for (std::vector<DeferredRelocInfo>::iterator it = relocations_.begin(); | 2362 for (std::vector<DeferredRelocInfo>::iterator it = relocations_.begin(); |
2303 it != relocations_.end(); it++) { | 2363 it != relocations_.end(); it++) { |
2304 RelocInfo::Mode rmode = it->rmode(); | 2364 RelocInfo::Mode rmode = it->rmode(); |
2305 Address pc = buffer_ + it->position(); | 2365 Address pc = buffer_ + it->position(); |
2306 Code* code = NULL; | 2366 Code* code = NULL; |
2307 RelocInfo rinfo(pc, rmode, it->data(), code); | 2367 RelocInfo rinfo(pc, rmode, it->data(), code); |
2308 | 2368 |
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2369 next_buffer_check_ = kMaxInt; | 2429 next_buffer_check_ = kMaxInt; |
2370 } | 2430 } |
2371 } else { | 2431 } else { |
2372 // Number of branches to unbound label at this point is zero, so we can | 2432 // Number of branches to unbound label at this point is zero, so we can |
2373 // move next buffer check to maximum. | 2433 // move next buffer check to maximum. |
2374 next_buffer_check_ = | 2434 next_buffer_check_ = |
2375 pc_offset() + kMaxCondBranchReach - kMaxBlockTrampolineSectionSize; | 2435 pc_offset() + kMaxCondBranchReach - kMaxBlockTrampolineSectionSize; |
2376 } | 2436 } |
2377 return; | 2437 return; |
2378 } | 2438 } |
2379 | |
2380 | |
2381 Handle<ConstantPoolArray> Assembler::NewConstantPool(Isolate* isolate) { | |
2382 DCHECK(!FLAG_enable_ool_constant_pool); | |
2383 return isolate->factory()->empty_constant_pool_array(); | |
2384 } | |
2385 | |
2386 | |
2387 void Assembler::PopulateConstantPool(ConstantPoolArray* constant_pool) { | |
2388 DCHECK(!FLAG_enable_ool_constant_pool); | |
2389 } | |
2390 } | 2439 } |
2391 } // namespace v8::internal | 2440 } // namespace v8::internal |
2392 | 2441 |
2393 #endif // V8_TARGET_ARCH_PPC | 2442 #endif // V8_TARGET_ARCH_PPC |
OLD | NEW |