src/java.base/share/classes/java/lang/invoke/LambdaForm.java
Index Unified diffs Context diffs Sdiffs Patch New Old Previous File Next File jdk Cdiff src/java.base/share/classes/java/lang/invoke/LambdaForm.java

src/java.base/share/classes/java/lang/invoke/LambdaForm.java

Print this page
rev 11254 : 8063137: Never-taken branches should be pruned when GWT LambdaForms are shared
Reviewed-by: ?
rev 11255 : [mq]: gwt.profile.1
rev 11258 : 8069591: Customize LambdaForms which are invoked using MH.invoke/invokeExact
Reviewed-by: ?

*** 118,127 **** --- 118,128 ---- */ class LambdaForm { final int arity; final int result; final boolean forceInline; + final MethodHandle customized; @Stable final Name[] names; final String debugName; MemberName vmentry; // low-level behavior, or null if not yet prepared private boolean isCompiled;
*** 242,285 **** } } LambdaForm(String debugName, int arity, Name[] names, int result) { ! this(debugName, arity, names, result, /*forceInline=*/true); } LambdaForm(String debugName, ! int arity, Name[] names, int result, boolean forceInline) { assert(namesOK(arity, names)); this.arity = arity; this.result = fixResult(result, names); this.names = names.clone(); this.debugName = fixDebugName(debugName); this.forceInline = forceInline; int maxOutArity = normalize(); if (maxOutArity > MethodType.MAX_MH_INVOKER_ARITY) { // Cannot use LF interpreter on very high arity expressions. assert(maxOutArity <= MethodType.MAX_JVM_ARITY); compileToBytecode(); } } LambdaForm(String debugName, int arity, Name[] names) { ! this(debugName, arity, names, LAST_RESULT, /*forceInline=*/true); } LambdaForm(String debugName, int arity, Name[] names, boolean forceInline) { ! this(debugName, arity, names, LAST_RESULT, forceInline); } LambdaForm(String debugName, Name[] formals, Name[] temps, Name result) { this(debugName, ! formals.length, buildNames(formals, temps, result), LAST_RESULT, /*forceInline=*/true); } LambdaForm(String debugName, Name[] formals, Name[] temps, Name result, boolean forceInline) { this(debugName, ! formals.length, buildNames(formals, temps, result), LAST_RESULT, forceInline); } private static Name[] buildNames(Name[] formals, Name[] temps, Name result) { int arity = formals.length; int length = arity + temps.length + (result == null ? 0 : 1); --- 243,287 ---- } } LambdaForm(String debugName, int arity, Name[] names, int result) { ! this(debugName, arity, names, result, /*forceInline=*/true, /*customized=*/null); } LambdaForm(String debugName, ! int arity, Name[] names, int result, boolean forceInline, MethodHandle customized) { assert(namesOK(arity, names)); this.arity = arity; this.result = fixResult(result, names); this.names = names.clone(); this.debugName = fixDebugName(debugName); this.forceInline = forceInline; + this.customized = customized; int maxOutArity = normalize(); if (maxOutArity > MethodType.MAX_MH_INVOKER_ARITY) { // Cannot use LF interpreter on very high arity expressions. assert(maxOutArity <= MethodType.MAX_JVM_ARITY); compileToBytecode(); } } LambdaForm(String debugName, int arity, Name[] names) { ! this(debugName, arity, names, LAST_RESULT, /*forceInline=*/true, /*customized=*/null); } LambdaForm(String debugName, int arity, Name[] names, boolean forceInline) { ! this(debugName, arity, names, LAST_RESULT, forceInline, /*customized=*/null); } LambdaForm(String debugName, Name[] formals, Name[] temps, Name result) { this(debugName, ! formals.length, buildNames(formals, temps, result), LAST_RESULT, /*forceInline=*/true, /*customized=*/null); } LambdaForm(String debugName, Name[] formals, Name[] temps, Name result, boolean forceInline) { this(debugName, ! formals.length, buildNames(formals, temps, result), LAST_RESULT, forceInline, /*customized=*/null); } private static Name[] buildNames(Name[] formals, Name[] temps, Name result) { int arity = formals.length; int length = arity + temps.length + (result == null ? 0 : 1);
*** 298,307 **** --- 300,310 ---- this.arity = signatureArity(sig); this.result = (signatureReturn(sig) == V_TYPE ? -1 : arity); this.names = buildEmptyNames(arity, sig); this.debugName = "LF.zero"; this.forceInline = true; + this.customized = null; assert(nameRefsAreLegal()); assert(isEmpty()); assert(sig.equals(basicTypeSignature())) : sig + " != " + basicTypeSignature(); }
*** 369,378 **** --- 372,402 ---- assert(!n.isParam()) : n + " is param at " + i; } return true; } + LambdaForm customize(MethodHandle mh) { + LambdaForm customForm = new LambdaForm(debugName, arity, names, result, forceInline, mh); + if (COMPILE_THRESHOLD > 0 && isCompiled) { + // If shared LambdaForm has been compiled, compile customized version as well. + customForm.compileToBytecode(); + } + return customForm; + } + + LambdaForm uncustomize() { + if (customized == null) { + return this; + } + LambdaForm uncustomizedForm = new LambdaForm(debugName, arity, names, result, forceInline, null); + if (COMPILE_THRESHOLD > 0 && isCompiled) { + // If customized LambdaForm has been compiled, compile uncustomized version as well. + uncustomizedForm.compileToBytecode(); + } + return uncustomizedForm; + } + /** Renumber and/or replace params so that they are interned and canonically numbered. * @return maximum argument list length among the names (since we have to pass over them anyway) */ private int normalize() { Name[] oldNames = null;
*** 411,422 **** } if (needIntern) { for (int i = arity; i < names.length; i++) { names[i].internArguments(); } - assert(nameRefsAreLegal()); } return maxOutArity; } /** * Check that all embedded Name references are localizable to this lambda, --- 435,446 ---- } if (needIntern) { for (int i = arity; i < names.length; i++) { names[i].internArguments(); } } + assert(nameRefsAreLegal()); return maxOutArity; } /** * Check that all embedded Name references are localizable to this lambda,
src/java.base/share/classes/java/lang/invoke/LambdaForm.java
Index Unified diffs Context diffs Sdiffs Patch New Old Previous File Next File