Mercurial > hg > graal-compiler
comparison src/cpu/x86/vm/x86_64.ad @ 1571:2d127394260e
6916623: Align object to 16 bytes to use Compressed Oops with java heap up to 64Gb
Summary: Added new product ObjectAlignmentInBytes flag to control object alignment.
Reviewed-by: twisti, ysr, iveresov
author | kvn |
---|---|
date | Thu, 27 May 2010 18:01:56 -0700 |
parents | 110501f54a99 |
children | 3657cb01ffc5 |
comparison
equal
deleted
inserted
replaced
1570:de91a2f25c7e | 1571:2d127394260e |
---|---|
1849 //============================================================================= | 1849 //============================================================================= |
1850 #ifndef PRODUCT | 1850 #ifndef PRODUCT |
1851 void MachUEPNode::format(PhaseRegAlloc* ra_, outputStream* st) const | 1851 void MachUEPNode::format(PhaseRegAlloc* ra_, outputStream* st) const |
1852 { | 1852 { |
1853 if (UseCompressedOops) { | 1853 if (UseCompressedOops) { |
1854 st->print_cr("movl rscratch1, [j_rarg0 + oopDesc::klass_offset_in_bytes() #%d]\t", oopDesc::klass_offset_in_bytes()); | 1854 st->print_cr("movl rscratch1, [j_rarg0 + oopDesc::klass_offset_in_bytes()]\t# compressed klass"); |
1855 if (Universe::narrow_oop_shift() != 0) { | 1855 if (Universe::narrow_oop_shift() != 0) { |
1856 st->print_cr("leaq rscratch1, [r12_heapbase, r, Address::times_8, 0]"); | 1856 st->print_cr("\tdecode_heap_oop_not_null rscratch1, rscratch1"); |
1857 } | 1857 } |
1858 st->print_cr("cmpq rax, rscratch1\t # Inline cache check"); | 1858 st->print_cr("\tcmpq rax, rscratch1\t # Inline cache check"); |
1859 } else { | 1859 } else { |
1860 st->print_cr("cmpq rax, [j_rarg0 + oopDesc::klass_offset_in_bytes() #%d]\t" | 1860 st->print_cr("\tcmpq rax, [j_rarg0 + oopDesc::klass_offset_in_bytes()]\t" |
1861 "# Inline cache check", oopDesc::klass_offset_in_bytes()); | 1861 "# Inline cache check"); |
1862 } | 1862 } |
1863 st->print_cr("\tjne SharedRuntime::_ic_miss_stub"); | 1863 st->print_cr("\tjne SharedRuntime::_ic_miss_stub"); |
1864 st->print_cr("\tnop"); | 1864 st->print_cr("\tnop\t# nops to align entry point"); |
1865 if (!OptoBreakpoint) { | |
1866 st->print_cr("\tnop"); | |
1867 } | |
1868 } | 1865 } |
1869 #endif | 1866 #endif |
1870 | 1867 |
1871 void MachUEPNode::emit(CodeBuffer& cbuf, PhaseRegAlloc* ra_) const | 1868 void MachUEPNode::emit(CodeBuffer& cbuf, PhaseRegAlloc* ra_) const |
1872 { | 1869 { |
1873 MacroAssembler masm(&cbuf); | 1870 MacroAssembler masm(&cbuf); |
1874 #ifdef ASSERT | |
1875 uint code_size = cbuf.code_size(); | 1871 uint code_size = cbuf.code_size(); |
1876 #endif | |
1877 if (UseCompressedOops) { | 1872 if (UseCompressedOops) { |
1878 masm.load_klass(rscratch1, j_rarg0); | 1873 masm.load_klass(rscratch1, j_rarg0); |
1879 masm.cmpptr(rax, rscratch1); | 1874 masm.cmpptr(rax, rscratch1); |
1880 } else { | 1875 } else { |
1881 masm.cmpptr(rax, Address(j_rarg0, oopDesc::klass_offset_in_bytes())); | 1876 masm.cmpptr(rax, Address(j_rarg0, oopDesc::klass_offset_in_bytes())); |
1882 } | 1877 } |
1883 | 1878 |
1884 masm.jump_cc(Assembler::notEqual, RuntimeAddress(SharedRuntime::get_ic_miss_stub())); | 1879 masm.jump_cc(Assembler::notEqual, RuntimeAddress(SharedRuntime::get_ic_miss_stub())); |
1885 | 1880 |
1886 /* WARNING these NOPs are critical so that verified entry point is properly | 1881 /* WARNING these NOPs are critical so that verified entry point is properly |
1887 aligned for patching by NativeJump::patch_verified_entry() */ | 1882 4 bytes aligned for patching by NativeJump::patch_verified_entry() */ |
1888 int nops_cnt = 1; | 1883 int nops_cnt = 4 - ((cbuf.code_size() - code_size) & 0x3); |
1889 if (!OptoBreakpoint) { | 1884 if (OptoBreakpoint) { |
1890 // Leave space for int3 | 1885 // Leave space for int3 |
1891 nops_cnt += 1; | 1886 nops_cnt -= 1; |
1892 } | 1887 } |
1893 if (UseCompressedOops) { | 1888 nops_cnt &= 0x3; // Do not add nops if code is aligned. |
1894 // ??? divisible by 4 is aligned? | 1889 if (nops_cnt > 0) |
1895 nops_cnt += 1; | 1890 masm.nop(nops_cnt); |
1896 } | |
1897 masm.nop(nops_cnt); | |
1898 | |
1899 assert(cbuf.code_size() - code_size == size(ra_), | |
1900 "checking code size of inline cache node"); | |
1901 } | 1891 } |
1902 | 1892 |
1903 uint MachUEPNode::size(PhaseRegAlloc* ra_) const | 1893 uint MachUEPNode::size(PhaseRegAlloc* ra_) const |
1904 { | 1894 { |
1905 if (UseCompressedOops) { | 1895 return MachNode::size(ra_); // too many variables; just compute it |
1906 if (Universe::narrow_oop_shift() == 0) { | 1896 // the hard way |
1907 return OptoBreakpoint ? 15 : 16; | |
1908 } else { | |
1909 return OptoBreakpoint ? 19 : 20; | |
1910 } | |
1911 } else { | |
1912 return OptoBreakpoint ? 11 : 12; | |
1913 } | |
1914 } | 1897 } |
1915 | 1898 |
1916 | 1899 |
1917 //============================================================================= | 1900 //============================================================================= |
1918 uint size_exception_handler() | 1901 uint size_exception_handler() |
5125 | 5108 |
5126 // Indirect Narrow Oop Plus Offset Operand | 5109 // Indirect Narrow Oop Plus Offset Operand |
5127 // Note: x86 architecture doesn't support "scale * index + offset" without a base | 5110 // Note: x86 architecture doesn't support "scale * index + offset" without a base |
5128 // we can't free r12 even with Universe::narrow_oop_base() == NULL. | 5111 // we can't free r12 even with Universe::narrow_oop_base() == NULL. |
5129 operand indCompressedOopOffset(rRegN reg, immL32 off) %{ | 5112 operand indCompressedOopOffset(rRegN reg, immL32 off) %{ |
5130 predicate(UseCompressedOops && (Universe::narrow_oop_shift() != 0)); | 5113 predicate(UseCompressedOops && (Universe::narrow_oop_shift() == Address::times_8)); |
5131 constraint(ALLOC_IN_RC(ptr_reg)); | 5114 constraint(ALLOC_IN_RC(ptr_reg)); |
5132 match(AddP (DecodeN reg) off); | 5115 match(AddP (DecodeN reg) off); |
5133 | 5116 |
5134 op_cost(10); | 5117 op_cost(10); |
5135 format %{"[R12 + $reg << 3 + $off] (compressed oop addressing)" %} | 5118 format %{"[R12 + $reg << 3 + $off] (compressed oop addressing)" %} |
7740 __ decode_heap_oop(d); | 7723 __ decode_heap_oop(d); |
7741 %} | 7724 %} |
7742 ins_pipe(ialu_reg_long); | 7725 ins_pipe(ialu_reg_long); |
7743 %} | 7726 %} |
7744 | 7727 |
7745 instruct decodeHeapOop_not_null(rRegP dst, rRegN src) %{ | 7728 instruct decodeHeapOop_not_null(rRegP dst, rRegN src, rFlagsReg cr) %{ |
7746 predicate(n->bottom_type()->is_oopptr()->ptr() == TypePtr::NotNull || | 7729 predicate(n->bottom_type()->is_oopptr()->ptr() == TypePtr::NotNull || |
7747 n->bottom_type()->is_oopptr()->ptr() == TypePtr::Constant); | 7730 n->bottom_type()->is_oopptr()->ptr() == TypePtr::Constant); |
7748 match(Set dst (DecodeN src)); | 7731 match(Set dst (DecodeN src)); |
7732 effect(KILL cr); | |
7749 format %{ "decode_heap_oop_not_null $dst,$src" %} | 7733 format %{ "decode_heap_oop_not_null $dst,$src" %} |
7750 ins_encode %{ | 7734 ins_encode %{ |
7751 Register s = $src$$Register; | 7735 Register s = $src$$Register; |
7752 Register d = $dst$$Register; | 7736 Register d = $dst$$Register; |
7753 if (s != d) { | 7737 if (s != d) { |