47 import org.graalvm.compiler.core.common.CompilationIdentifier; |
47 import org.graalvm.compiler.core.common.CompilationIdentifier; |
48 import org.graalvm.compiler.core.common.LIRKind; |
48 import org.graalvm.compiler.core.common.LIRKind; |
49 import org.graalvm.compiler.core.common.alloc.RegisterAllocationConfig; |
49 import org.graalvm.compiler.core.common.alloc.RegisterAllocationConfig; |
50 import org.graalvm.compiler.core.common.spi.ForeignCallLinkage; |
50 import org.graalvm.compiler.core.common.spi.ForeignCallLinkage; |
51 import org.graalvm.compiler.core.gen.LIRGenerationProvider; |
51 import org.graalvm.compiler.core.gen.LIRGenerationProvider; |
|
52 import org.graalvm.compiler.debug.DebugContext; |
52 import org.graalvm.compiler.hotspot.GraalHotSpotVMConfig; |
53 import org.graalvm.compiler.hotspot.GraalHotSpotVMConfig; |
53 import org.graalvm.compiler.hotspot.HotSpotDataBuilder; |
54 import org.graalvm.compiler.hotspot.HotSpotDataBuilder; |
54 import org.graalvm.compiler.hotspot.HotSpotGraalRuntimeProvider; |
55 import org.graalvm.compiler.hotspot.HotSpotGraalRuntimeProvider; |
55 import org.graalvm.compiler.hotspot.HotSpotHostBackend; |
56 import org.graalvm.compiler.hotspot.HotSpotHostBackend; |
56 import org.graalvm.compiler.hotspot.HotSpotLIRGenerationResult; |
57 import org.graalvm.compiler.hotspot.HotSpotLIRGenerationResult; |
70 import org.graalvm.compiler.lir.framemap.FrameMapBuilder; |
71 import org.graalvm.compiler.lir.framemap.FrameMapBuilder; |
71 import org.graalvm.compiler.lir.gen.LIRGenerationResult; |
72 import org.graalvm.compiler.lir.gen.LIRGenerationResult; |
72 import org.graalvm.compiler.lir.gen.LIRGeneratorTool; |
73 import org.graalvm.compiler.lir.gen.LIRGeneratorTool; |
73 import org.graalvm.compiler.nodes.StructuredGraph; |
74 import org.graalvm.compiler.nodes.StructuredGraph; |
74 import org.graalvm.compiler.nodes.spi.NodeLIRBuilderTool; |
75 import org.graalvm.compiler.nodes.spi.NodeLIRBuilderTool; |
|
76 import org.graalvm.compiler.serviceprovider.GraalUnsafeAccess; |
75 |
77 |
76 import jdk.vm.ci.aarch64.AArch64Kind; |
78 import jdk.vm.ci.aarch64.AArch64Kind; |
77 import jdk.vm.ci.code.CallingConvention; |
79 import jdk.vm.ci.code.CallingConvention; |
|
80 import jdk.vm.ci.code.CompilationRequest; |
|
81 import jdk.vm.ci.code.InstalledCode; |
78 import jdk.vm.ci.code.Register; |
82 import jdk.vm.ci.code.Register; |
79 import jdk.vm.ci.code.RegisterConfig; |
83 import jdk.vm.ci.code.RegisterConfig; |
80 import jdk.vm.ci.code.StackSlot; |
84 import jdk.vm.ci.code.StackSlot; |
|
85 import jdk.vm.ci.code.site.Mark; |
81 import jdk.vm.ci.hotspot.HotSpotCallingConventionType; |
86 import jdk.vm.ci.hotspot.HotSpotCallingConventionType; |
82 import jdk.vm.ci.hotspot.HotSpotSentinelConstant; |
87 import jdk.vm.ci.hotspot.HotSpotSentinelConstant; |
83 import jdk.vm.ci.hotspot.aarch64.AArch64HotSpotRegisterConfig; |
88 import jdk.vm.ci.hotspot.aarch64.AArch64HotSpotRegisterConfig; |
84 import jdk.vm.ci.meta.JavaKind; |
89 import jdk.vm.ci.meta.JavaKind; |
85 import jdk.vm.ci.meta.JavaType; |
90 import jdk.vm.ci.meta.JavaType; |
86 import jdk.vm.ci.meta.ResolvedJavaMethod; |
91 import jdk.vm.ci.meta.ResolvedJavaMethod; |
87 |
92 |
|
93 import sun.misc.Unsafe; |
|
94 |
88 /** |
95 /** |
89 * HotSpot AArch64 specific backend. |
96 * HotSpot AArch64 specific backend. |
90 */ |
97 */ |
91 public class AArch64HotSpotBackend extends HotSpotHostBackend implements LIRGenerationProvider { |
98 public class AArch64HotSpotBackend extends HotSpotHostBackend implements LIRGenerationProvider { |
92 |
99 |
122 try (ScratchRegister sc = masm.getScratchRegister()) { |
129 try (ScratchRegister sc = masm.getScratchRegister()) { |
123 Register scratch = sc.getRegister(); |
130 Register scratch = sc.getRegister(); |
124 AArch64Address address = masm.makeAddress(sp, -bangOffset, scratch, 8, /* allowOverwrite */false); |
131 AArch64Address address = masm.makeAddress(sp, -bangOffset, scratch, 8, /* allowOverwrite */false); |
125 masm.str(64, zr, address); |
132 masm.str(64, zr, address); |
126 } |
133 } |
|
134 } |
|
135 |
|
136 @Override |
|
137 public InstalledCode createInstalledCode(DebugContext debug, |
|
138 ResolvedJavaMethod method, |
|
139 CompilationRequest compilationRequest, |
|
140 CompilationResult compilationResult, |
|
141 InstalledCode predefinedInstalledCode, |
|
142 boolean isDefault, |
|
143 Object[] context) { |
|
144 boolean isStub = (method == null); |
|
145 boolean isAOT = compilationResult.isImmutablePIC(); |
|
146 if (!isStub && !isAOT) { |
|
147 // Non-stub compilation results are installed into HotSpot as nmethods. As AArch64 has |
|
148 // a constraint that the instruction at nmethod verified entry point should be a nop or |
|
149 // jump, AArch64HotSpotBackend always generate a nop placeholder before the code body |
|
150 // for non-AOT compilations. See AArch64HotSpotBackend.emitInvalidatePlaceholder(). This |
|
151 // assert checks if the nop placeholder is generated at all required places, including |
|
152 // in manually assembled code in CodeGenTest cases. |
|
153 assert hasInvalidatePlaceholder(compilationResult); |
|
154 } |
|
155 return super.createInstalledCode(debug, method, compilationRequest, compilationResult, predefinedInstalledCode, isDefault, context); |
|
156 } |
|
157 |
|
158 private boolean hasInvalidatePlaceholder(CompilationResult compilationResult) { |
|
159 byte[] targetCode = compilationResult.getTargetCode(); |
|
160 int verifiedEntryOffset = 0; |
|
161 for (Mark mark : compilationResult.getMarks()) { |
|
162 Object markId = mark.id; |
|
163 if (markId instanceof Integer && (int) markId == config.MARKID_VERIFIED_ENTRY) { |
|
164 // The nmethod verified entry is located at some pc offset. |
|
165 verifiedEntryOffset = mark.pcOffset; |
|
166 break; |
|
167 } |
|
168 } |
|
169 Unsafe unsafe = GraalUnsafeAccess.getUnsafe(); |
|
170 int instruction = unsafe.getIntVolatile(targetCode, unsafe.arrayBaseOffset(byte[].class) + verifiedEntryOffset); |
|
171 AArch64MacroAssembler masm = new AArch64MacroAssembler(getTarget()); |
|
172 masm.nop(); |
|
173 return instruction == masm.getInt(0); |
127 } |
174 } |
128 |
175 |
129 private class HotSpotFrameContext implements FrameContext { |
176 private class HotSpotFrameContext implements FrameContext { |
130 final boolean isStub; |
177 final boolean isStub; |
131 |
178 |