public List<VMThreadLocalInfo> sortThreadLocals(Feature.CompilationAccess config) { return sortThreadLocals(config, null); }
@Override public void beforeCompilation(BeforeCompilationAccess config) { if (SubstrateOptions.MultiThreaded.getValue()) { VMThreadMTFeature threadFeature = ImageSingletons.lookup(VMThreadMTFeature.class); vmThreadSize = threadFeature.getVMThreadSize(); } }
@Override public void beforeAnalysis(BeforeAnalysisAccess access) { if (SubstrateOptions.MultiThreaded.getValue()) { /* * The per-thread JNI environment is located at offset 0 of each thread's {@link * VMThread} structure. For that reason, it has the same address as the VMThread and can * be used to restore the designated VMThread register when transitioning from native to * Java. */ VMThreadMTFeature mt = ImageSingletons.lookup(VMThreadMTFeature.class); mt.setThreadLocalAtOffsetZero(JNIThreadLocalEnvironment.jniFunctions); } } }
private boolean handleSet(GraphBuilderContext b, Receiver receiver, ValueNode valueNode) { VMThreadLocalInfo info = threadLocalCollector.findInfo(b, receiver.get()); VMThreadLocalSTHolderNode holder = b.add(new VMThreadLocalSTHolderNode(info)); b.add(new StoreVMThreadLocalNode(info, holder, valueNode, BarrierType.PRECISE)); return true; }
@Override public void beforeCompilation(BeforeCompilationAccess config) { List<VMThreadLocalInfo> sortedThreadLocalInfos = threadLocalCollector.sortThreadLocals(config, threadLocalAtOffsetZero); SubstrateReferenceMap referenceMap = new SubstrateReferenceMap(); int nextOffset = 0; for (VMThreadLocalInfo info : sortedThreadLocalInfos) { assert nextOffset % Math.min(8, info.sizeInBytes) == 0 : "alignment mismatch: " + info.sizeInBytes + ", " + nextOffset; if (info.isObject) { referenceMap.markReferenceAtOffset(nextOffset, true); } info.offset = nextOffset; nextOffset += info.sizeInBytes; } VMError.guarantee(threadLocalAtOffsetZero == null || threadLocalCollector.getInfo(threadLocalAtOffsetZero).offset == 0); ReferenceMapEncoder encoder = new ReferenceMapEncoder(); encoder.add(referenceMap); objectReferenceWalker.vmThreadReferenceMapEncoding = encoder.encodeAll(null); objectReferenceWalker.vmThreadReferenceMapIndex = encoder.lookupEncoding(referenceMap); objectReferenceWalker.vmThreadSize = nextOffset; /* Remember the final sorted list. */ VMThreadLocalInfos.setInfos(sortedThreadLocalInfos); } }
Registration r = new Registration(invocationPlugins, threadLocalClass); Class<?> valueClass = VMThreadLocalInfo.getValueClass(threadLocalClass); registerAccessors(r, valueClass, false); registerAccessors(r, valueClass, true);
Class<?> valueClass = VMThreadLocalInfo.getValueClass(threadLocalClass); registerAccessors(r, valueClass, false); registerAccessors(r, valueClass, true);
private boolean handleCompareAndSet(GraphBuilderContext b, ResolvedJavaMethod targetMethod, Receiver receiver, ValueNode threadNode, ValueNode expect, ValueNode update) { VMThreadLocalInfo threadLocalInfo = threadLocalCollector.findInfo(b, receiver.get()); b.addPush(targetMethod.getSignature().getReturnKind(), new CompareAndSetVMThreadLocalNode(threadLocalInfo, threadNode, expect, update)); return true; }
@Override public void beforeCompilation(BeforeCompilationAccess config) { List<VMThreadLocalInfo> sortedThreadLocalInfos = threadLocalCollector.sortThreadLocals(config); ObjectLayout layout = ConfigurationValues.getObjectLayout(); int nextObject = 0; int nextPrimitive = 0; for (VMThreadLocalInfo info : sortedThreadLocalInfos) { if (info.isObject) { info.offset = layout.getArrayElementOffset(JavaKind.Object, nextObject); nextObject += 1; } else { assert nextPrimitive % Math.min(8, info.sizeInBytes) == 0 : "alignment mismatch: " + info.sizeInBytes + ", " + nextPrimitive; info.offset = layout.getArrayElementOffset(JavaKind.Byte, nextPrimitive); nextPrimitive += info.sizeInBytes; } } VMThreadLocalSTSupport support = ImageSingletons.lookup(VMThreadLocalSTSupport.class); support.objectThreadLocals = new Object[nextObject]; support.primitiveThreadLocals = new byte[nextPrimitive]; /* Remember the final sorted list. */ VMThreadLocalInfos.setInfos(sortedThreadLocalInfos); } }
private boolean handleGetAddress(GraphBuilderContext b, ResolvedJavaMethod targetMethod, Receiver receiver, ValueNode threadNode) { VMThreadLocalInfo threadLocalInfo = threadLocalCollector.findInfo(b, receiver.get()); b.addPush(targetMethod.getSignature().getReturnKind(), new AddressOfVMThreadLocalNode(threadLocalInfo, threadNode)); return true; }
private boolean handleSet(GraphBuilderContext b, Receiver receiver, ValueNode threadNode, ValueNode valueNode, boolean isVolatile) { VMThreadLocalInfo threadLocalInfo = threadLocalCollector.findInfo(b, receiver.get()); if (isVolatile) { b.add(new MembarNode(MemoryBarriers.JMM_PRE_VOLATILE_WRITE)); } b.add(new StoreVMThreadLocalNode(threadLocalInfo, threadNode, valueNode, BarrierType.NONE)); if (isVolatile) { b.add(new MembarNode(MemoryBarriers.JMM_POST_VOLATILE_WRITE)); } return true; }
private boolean handleGetAddress(GraphBuilderContext b, ResolvedJavaMethod targetMethod, Receiver receiver) { VMThreadLocalInfo threadLocalInfo = threadLocalCollector.findInfo(b, receiver.get()); VMThreadLocalSTHolderNode holder = b.add(new VMThreadLocalSTHolderNode(threadLocalInfo)); b.addPush(targetMethod.getSignature().getReturnKind(), new AddressOfVMThreadLocalNode(threadLocalInfo, holder)); return true; }
private boolean handleCompareAndSet(GraphBuilderContext b, ResolvedJavaMethod targetMethod, Receiver receiver, ValueNode expect, ValueNode update) { VMThreadLocalInfo threadLocalInfo = threadLocalCollector.findInfo(b, receiver.get()); VMThreadLocalSTHolderNode holder = b.add(new VMThreadLocalSTHolderNode(threadLocalInfo)); b.addPush(targetMethod.getSignature().getReturnKind(), new CompareAndSetVMThreadLocalNode(threadLocalInfo, holder, expect, update)); return true; }
private boolean handleGet(GraphBuilderContext b, ResolvedJavaMethod targetMethod, Receiver receiver) { VMThreadLocalInfo info = threadLocalCollector.findInfo(b, receiver.get()); VMThreadLocalSTHolderNode holder = b.add(new VMThreadLocalSTHolderNode(info)); b.addPush(targetMethod.getSignature().getReturnKind(), new LoadVMThreadLocalNode(b.getMetaAccess(), info, holder, BarrierType.PRECISE)); return true; }
private boolean handleGet(GraphBuilderContext b, ResolvedJavaMethod targetMethod, Receiver receiver, ValueNode threadNode, boolean isVolatile) { VMThreadLocalInfo threadLocalInfo = threadLocalCollector.findInfo(b, receiver.get()); if (isVolatile) { b.add(new MembarNode(MemoryBarriers.JMM_PRE_VOLATILE_READ)); } b.addPush(targetMethod.getSignature().getReturnKind(), new LoadVMThreadLocalNode(b.getMetaAccess(), threadLocalInfo, threadNode, BarrierType.NONE)); if (isVolatile) { b.add(new MembarNode(MemoryBarriers.JMM_POST_VOLATILE_READ)); } return true; }