1 /* |
1 /* |
2 * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved. |
2 * Copyright (c) 2014, 2017, Oracle and/or its affiliates. All rights reserved. |
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
4 * |
4 * |
5 * This code is free software; you can redistribute it and/or modify it |
5 * This code is free software; you can redistribute it and/or modify it |
6 * under the terms of the GNU General Public License version 2 only, as |
6 * under the terms of the GNU General Public License version 2 only, as |
7 * published by the Free Software Foundation. |
7 * published by the Free Software Foundation. |
50 */ |
50 */ |
51 static class LazyInitialization { |
51 static class LazyInitialization { |
52 static final ResolvedJavaType lambdaFormType; |
52 static final ResolvedJavaType lambdaFormType; |
53 static final ResolvedJavaField methodHandleFormField; |
53 static final ResolvedJavaField methodHandleFormField; |
54 static final ResolvedJavaField lambdaFormVmentryField; |
54 static final ResolvedJavaField lambdaFormVmentryField; |
55 static final HotSpotResolvedJavaField memberNameVmtargetField; |
55 static final ResolvedJavaField methodField; |
|
56 static final HotSpotResolvedJavaField vmtargetField; |
56 |
57 |
57 /** |
58 /** |
58 * Search for an instance field with the given name in a class. |
59 * Search for an instance field with the given name in a class. |
59 * |
60 * |
60 * @param declaringType the type declaring the field |
61 * @param declaringType the type declaring the field |
86 ResolvedJavaType methodHandleType = resolveType(MethodHandle.class); |
87 ResolvedJavaType methodHandleType = resolveType(MethodHandle.class); |
87 ResolvedJavaType memberNameType = resolveType("java.lang.invoke.MemberName"); |
88 ResolvedJavaType memberNameType = resolveType("java.lang.invoke.MemberName"); |
88 lambdaFormType = resolveType("java.lang.invoke.LambdaForm"); |
89 lambdaFormType = resolveType("java.lang.invoke.LambdaForm"); |
89 methodHandleFormField = findFieldInClass(methodHandleType, "form", lambdaFormType); |
90 methodHandleFormField = findFieldInClass(methodHandleType, "form", lambdaFormType); |
90 lambdaFormVmentryField = findFieldInClass(lambdaFormType, "vmentry", memberNameType); |
91 lambdaFormVmentryField = findFieldInClass(lambdaFormType, "vmentry", memberNameType); |
91 memberNameVmtargetField = (HotSpotResolvedJavaField) findFieldInClass(memberNameType, "vmtarget", resolveType(long.class)); |
92 ResolvedJavaType methodType = resolveType("java.lang.invoke.ResolvedMethodName"); |
|
93 methodField = findFieldInClass(memberNameType, "method", methodType); |
|
94 vmtargetField = (HotSpotResolvedJavaField) findFieldInClass(methodType, "vmtarget", resolveType(HotSpotJVMCIRuntime.getHostWordKind().toJavaClass())); |
|
95 |
92 } catch (Throwable ex) { |
96 } catch (Throwable ex) { |
93 throw new JVMCIError(ex); |
97 throw new JVMCIError(ex); |
94 } |
98 } |
95 } |
99 } |
96 } |
100 } |
137 Object lf = ((HotSpotObjectConstant) lambdaForm).asObject(LazyInitialization.lambdaFormType); |
141 Object lf = ((HotSpotObjectConstant) lambdaForm).asObject(LazyInitialization.lambdaFormType); |
138 compilerToVM().compileToBytecode(Objects.requireNonNull(lf)); |
142 compilerToVM().compileToBytecode(Objects.requireNonNull(lf)); |
139 memberName = constantReflection.readFieldValue(LazyInitialization.lambdaFormVmentryField, lambdaForm); |
143 memberName = constantReflection.readFieldValue(LazyInitialization.lambdaFormVmentryField, lambdaForm); |
140 assert memberName.isNonNull(); |
144 assert memberName.isNonNull(); |
141 } |
145 } |
142 return getTargetMethod(memberName); |
146 JavaConstant method = constantReflection.readFieldValue(LazyInitialization.methodField, memberName); |
|
147 return getTargetMethod(method); |
143 } |
148 } |
144 |
149 |
145 @Override |
150 @Override |
146 public ResolvedJavaMethod resolveLinkToTarget(JavaConstant memberName) { |
151 public ResolvedJavaMethod resolveLinkToTarget(JavaConstant memberName) { |
147 return getTargetMethod(memberName); |
152 if (memberName.isNull()) { |
|
153 return null; |
|
154 } |
|
155 JavaConstant method = constantReflection.readFieldValue(LazyInitialization.methodField, memberName); |
|
156 return getTargetMethod(method); |
148 } |
157 } |
149 |
158 |
150 /** |
159 /** |
151 * Returns the {@link ResolvedJavaMethod} for the vmtarget of a java.lang.invoke.MemberName. |
160 * Returns the {@link ResolvedJavaMethod} for the method of a java.lang.invoke.MemberName. |
152 */ |
161 */ |
153 private static ResolvedJavaMethod getTargetMethod(JavaConstant memberName) { |
162 private static ResolvedJavaMethod getTargetMethod(JavaConstant method) { |
154 if (memberName.isNull()) { |
163 if (method == null) { |
155 return null; |
164 // If readFieldValue returns NULL the type was wrong |
|
165 throw new IllegalArgumentException("unexpected type for memberName"); |
156 } |
166 } |
157 |
167 |
158 Object object = ((HotSpotObjectConstantImpl) memberName).object(); |
168 Object object = ((HotSpotObjectConstantImpl) method).object(); |
159 /* Read the ResolvedJavaMethod from the injected field MemberName.vmtarget */ |
169 /* Read the ResolvedJavaMethod from the injected field MemberName.method.vmtarget */ |
160 return compilerToVM().getResolvedJavaMethod(object, LazyInitialization.memberNameVmtargetField.offset()); |
170 return compilerToVM().getResolvedJavaMethod(object, LazyInitialization.vmtargetField.offset()); |
161 } |
171 } |
162 } |
172 } |