jdk/src/share/classes/java/lang/invoke/LambdaMetafactory.java
author henryjen
Tue, 22 Oct 2013 15:12:22 -0700
changeset 21339 20e8b81964d5
parent 18716 9723e722b955
child 21360 2c2f062cf52f
permissions -rw-r--r--
8025909: Lambda Library Spec Updates 8024179: Document limitations and performance characteristics of stream sources and operations 8024138: (Spec clarification) Lambda Metafacory spec should state DMH constraint on implMethod Reviewed-by: mduigou Contributed-by: brian.goetz@oracle.com, paul.sandoz@oracle.com
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
14323
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
     1
/*
16036
a30224365db2 8009102: Several docs warnings in Project Lambda APIs
darcy
parents: 16001
diff changeset
     2
 * Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
14323
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
     3
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
     4
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
     5
 * This code is free software; you can redistribute it and/or modify it
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
     6
 * under the terms of the GNU General Public License version 2 only, as
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
     7
 * published by the Free Software Foundation.  Oracle designates this
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
     8
 * particular file as subject to the "Classpath" exception as provided
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
     9
 * by Oracle in the LICENSE file that accompanied this code.
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    10
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    11
 * This code is distributed in the hope that it will be useful, but WITHOUT
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    12
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    13
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    14
 * version 2 for more details (a copy is included in the LICENSE file that
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    15
 * accompanied this code).
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    16
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    17
 * You should have received a copy of the GNU General Public License version
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    18
 * 2 along with this work; if not, write to the Free Software Foundation,
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    19
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    20
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    21
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    22
 * or visit www.oracle.com if you need additional information or have any
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    23
 * questions.
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    24
 */
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    25
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    26
package java.lang.invoke;
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    27
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
    28
import java.io.Serializable;
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
    29
import java.util.Arrays;
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
    30
14323
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    31
/**
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    32
 * <p>Bootstrap methods for converting lambda expressions and method references to functional interface objects.</p>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    33
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    34
 * <p>For every lambda expressions or method reference in the source code, there is a target type which is a
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    35
 * functional interface. Evaluating a lambda expression produces an object of its target type. The mechanism for
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    36
 * evaluating lambda expressions is to invoke an invokedynamic call site, which takes arguments describing the sole
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    37
 * method of the functional interface and the implementation method, and returns an object (the lambda object) that
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    38
 * implements the target type. Methods of the lambda object invoke the implementation method. For method
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    39
 * references, the implementation method is simply the referenced method; for lambda expressions, the
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    40
 * implementation method is produced by the compiler based on the body of the lambda expression. The methods in
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    41
 * this file are the bootstrap methods for those invokedynamic call sites, called lambda factories, and the
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    42
 * bootstrap methods responsible for linking the lambda factories are called lambda meta-factories.
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    43
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    44
 * <p>The bootstrap methods in this class take the information about the functional interface, the implementation
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    45
 * method, and the static types of the captured lambda arguments, and link a call site which, when invoked,
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    46
 * produces the lambda object.
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    47
 *
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
    48
 * <p>When parameterized types are used, the instantiated type of the functional interface method may be different
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
    49
 * from that in the functional interface. For example, consider
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
    50
 * {@code interface I<T> { int m(T x); }} if this functional interface type is used in a lambda
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
    51
 * {@code I<Byte>; v = ...}, we need both the actual functional interface method which has the signature
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
    52
 * {@code (Object)int} and the erased instantiated type of the functional interface method (or simply
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
    53
 * <I>instantiated method type</I>), which has signature
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
    54
 * {@code (Byte)int}.
14323
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    55
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    56
 * <p>The argument list of the implementation method and the argument list of the functional interface method(s)
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    57
 * may differ in several ways.  The implementation methods may have additional arguments to accommodate arguments
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    58
 * captured by the lambda expression; there may also be differences resulting from permitted adaptations of
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    59
 * arguments, such as casting, boxing, unboxing, and primitive widening. They may also differ because of var-args,
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    60
 * but this is expected to be handled by the compiler.
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    61
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    62
 * <p>Invokedynamic call sites have two argument lists: a static argument list and a dynamic argument list.  The
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    63
 * static argument list lives in the constant pool; the dynamic argument list lives on the operand stack at
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    64
 * invocation time.  The bootstrap method has access to the entire static argument list (which in this case,
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    65
 * contains method handles describing the implementation method and the canonical functional interface method),
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    66
 * as well as a method signature describing the number and static types (but not the values) of the dynamic
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    67
 * arguments, and the static return type of the invokedynamic site.
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    68
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    69
 * <p>The implementation method is described with a method handle. In theory, any method handle could be used.
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    70
 * Currently supported are method handles representing invocation of virtual, interface, constructor and static
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    71
 * methods.
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    72
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    73
 * <p>Assume:
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    74
 * <ul>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    75
 *      <li>the functional interface method has N arguments, of types (U1, U2, ... Un) and return type Ru</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    76
 *      <li>then the instantiated method type also has N arguments, of types (T1, T2, ... Tn) and return type Rt</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    77
 *      <li>the implementation method has M arguments, of types (A1..Am) and return type Ra,</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    78
 *      <li>the dynamic argument list has K arguments of types (D1..Dk), and the invokedynamic return site has
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    79
 *          type Rd</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    80
 *      <li>the functional interface type is F</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    81
 * </ul>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    82
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    83
 * <p>The following signature invariants must hold:
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    84
 * <ul>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    85
 *     <li>Rd is a subtype of F</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    86
 *     <li>For i=1..N, Ti is a subtype of Ui</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    87
 *     <li>Either Rt and Ru are primitive and are the same type, or both are reference types and
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    88
 *         Rt is a subtype of Ru</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    89
 *     <li>If the implementation method is a static method:
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    90
 *     <ul>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    91
 *         <li>K + N = M</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    92
 *         <li>For i=1..K, Di = Ai</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    93
 *         <li>For i=1..N, Ti is adaptable to Aj, where j=i+k</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    94
 *     </ul></li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    95
 *     <li>If the implementation method is an instance method:
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    96
 *     <ul>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    97
 *         <li>K + N = M + 1</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    98
 *         <li>D1 must be a subtype of the enclosing class for the implementation method</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
    99
 *         <li>For i=2..K, Di = Aj, where j=i-1</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   100
 *         <li>For i=1..N, Ti is adaptable to Aj, where j=i+k-1</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   101
 *     </ul></li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   102
 *     <li>The return type Rt is void, or the return type Ra is not void and is adaptable to Rt</li>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   103
 * </ul>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   104
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   105
 * <p>Note that the potentially parameterized implementation return type provides the value for the SAM. Whereas
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   106
 * the completely known instantiated return type is adapted to the implementation arguments. Because the
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   107
 * instantiated type of the implementation method is not available, the adaptability of return types cannot be
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   108
 * checked as precisely at link-time as the arguments can be checked. Thus a loose version of link-time checking is
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   109
 * done on return type, while a strict version is applied to arguments.
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   110
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   111
 * <p>A type Q is considered adaptable to S as follows:
18569
0e46c17766b7 8019357: Fix doclint warnings in java.lang.invoke
darcy
parents: 18284
diff changeset
   112
 * <table summary="adaptable types">
14323
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   113
 *     <tr><th>Q</th><th>S</th><th>Link-time checks</th><th>Capture-time checks</th></tr>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   114
 *     <tr>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   115
 *         <td>Primitive</td><td>Primitive</td>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   116
 *         <td>Q can be converted to S via a primitive widening conversion</td>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   117
 *         <td>None</td>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   118
 *     </tr>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   119
 *     <tr>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   120
 *         <td>Primitive</td><td>Reference</td>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   121
 *         <td>S is a supertype of the Wrapper(Q)</td>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   122
 *         <td>Cast from Wrapper(Q) to S</td>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   123
 *     </tr>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   124
 *     <tr>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   125
 *         <td>Reference</td><td>Primitive</td>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   126
 *         <td>strict: Q is a primitive wrapper and Primitive(Q) can be widened to S
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   127
 *         <br>loose: If Q is a primitive wrapper, check that Primitive(Q) can be widened to S</td>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   128
 *         <td>If Q is not a primitive wrapper, cast Q to the base Wrapper(S); for example Number for numeric types</td>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   129
 *     </tr>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   130
 *     <tr>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   131
 *         <td>Reference</td><td>Reference</td>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   132
 *         <td>strict: S is a supertype of Q
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   133
 *         <br>loose: none</td>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   134
 *         <td>Cast from Q to S</td>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   135
 *     </tr>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   136
 * </table>
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   137
 *
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   138
 * The default bootstrap ({@link #metafactory}) represents the common cases and uses an optimized protocol.
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   139
 * Alternate bootstraps (e.g., {@link #altMetafactory}) exist to support uncommon cases such as serialization
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   140
 * or additional marker superinterfaces.
14323
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   141
 *
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   142
 */
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   143
public class LambdaMetafactory {
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   144
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   145
    /** Flag for alternate metafactories indicating the lambda object is
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   146
     * must to be serializable */
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   147
    public static final int FLAG_SERIALIZABLE = 1 << 0;
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   148
14323
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   149
    /**
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   150
     * Flag for alternate metafactories indicating the lambda object implements
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   151
     * other marker interfaces
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   152
     * besides Serializable
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   153
     */
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   154
    public static final int FLAG_MARKERS = 1 << 1;
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   155
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   156
    /**
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   157
     * Flag for alternate metafactories indicating the lambda object requires
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   158
     * additional bridge methods
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   159
     */
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   160
    public static final int FLAG_BRIDGES = 1 << 2;
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   161
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   162
    private static final Class<?>[] EMPTY_CLASS_ARRAY = new Class<?>[0];
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   163
    private static final MethodType[] EMPTY_MT_ARRAY = new MethodType[0];
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   164
18569
0e46c17766b7 8019357: Fix doclint warnings in java.lang.invoke
darcy
parents: 18284
diff changeset
   165
    /**
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   166
     * Standard meta-factory for conversion of lambda expressions or method
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   167
     * references to functional interfaces.
14323
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   168
     *
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   169
     * @param caller Stacked automatically by VM; represents a lookup context
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   170
     *                   with the accessibility privileges of the caller.
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   171
     * @param invokedName Stacked automatically by VM; the name of the invoked
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   172
     *                    method as it appears at the call site.
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   173
     *                    Used as the name of the functional interface method
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   174
     *                    to which the lambda or method reference is being
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   175
     *                    converted.
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   176
     * @param invokedType Stacked automatically by VM; the signature of the
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   177
     *                    invoked method, which includes the expected static
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   178
     *                    type of the returned lambda object, and the static
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   179
     *                    types of the captured arguments for the lambda.
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   180
     *                    In the event that the implementation method is an
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   181
     *                    instance method, the first argument in the invocation
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   182
     *                    signature will correspond to the receiver.
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   183
     * @param samMethodType MethodType of the method in the functional interface
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   184
     *                      to which the lambda or method reference is being
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   185
     *                      converted, represented as a MethodType.
21339
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   186
     * @param implMethod A direct method handle describing the implementation
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   187
     *                   method which should be called (with suitable adaptation
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   188
     *                   of argument types, return types, and adjustment for
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   189
     *                   captured arguments) when methods of the resulting
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   190
     *                   functional interface instance are invoked.
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   191
     * @param instantiatedMethodType The signature of the primary functional
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   192
     *                               interface method after type variables
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   193
     *                               are substituted with their instantiation
21339
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   194
     *                               from the capture site.
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   195
     * @return a CallSite, which, when invoked, will return an instance of the
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   196
     * functional interface
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   197
     * @throws ReflectiveOperationException if the caller is not able to
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   198
     * reconstruct one of the method handles
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   199
     * @throws LambdaConversionException If any of the meta-factory protocol
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   200
     * invariants are violated
14323
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   201
     */
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   202
    public static CallSite metafactory(MethodHandles.Lookup caller,
14323
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   203
                                       String invokedName,
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   204
                                       MethodType invokedType,
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   205
                                       MethodType samMethodType,
14323
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   206
                                       MethodHandle implMethod,
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   207
                                       MethodType instantiatedMethodType)
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   208
                   throws ReflectiveOperationException, LambdaConversionException {
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   209
        AbstractValidatingLambdaMetafactory mf;
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   210
        mf = new InnerClassLambdaMetafactory(caller, invokedType,
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   211
                                             invokedName, samMethodType,
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   212
                                             implMethod, instantiatedMethodType,
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   213
                                             false, EMPTY_CLASS_ARRAY, EMPTY_MT_ARRAY);
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   214
        mf.validateMetafactoryArgs();
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   215
        return mf.buildCallSite();
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   216
    }
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   217
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   218
    /**
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   219
     * Alternate meta-factory for conversion of lambda expressions or method
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   220
     * references to functional interfaces, which supports serialization and
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   221
     * other uncommon options.
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   222
     *
21339
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   223
     * <p>The declared argument list for this method is:
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   224
     *
21339
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   225
     * <pre>{@code
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   226
     *  CallSite altMetafactory(MethodHandles.Lookup caller,
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   227
     *                          String invokedName,
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   228
     *                          MethodType invokedType,
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   229
     *                          Object... args)
21339
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   230
     * }</pre>
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   231
     *
21339
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   232
     * <p>but it behaves as if the argument list is as follows, where names that
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   233
     * appear in the argument list for
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   234
     * {@link #metafactory(MethodHandles.Lookup, String, MethodType, MethodType, MethodHandle, MethodType)}
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   235
     * have the same specification as in that method:
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   236
     *
21339
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   237
     * <pre>{@code
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   238
     *  CallSite altMetafactory(MethodHandles.Lookup caller,
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   239
     *                          String invokedName,
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   240
     *                          MethodType invokedType,
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   241
     *                          MethodType samMethodType
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   242
     *                          MethodHandle implMethod,
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   243
     *                          MethodType instantiatedMethodType,
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   244
     *                          int flags,
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   245
     *                          int markerInterfaceCount, // IF flags has MARKERS set
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   246
     *                          Class... markerInterfaces // IF flags has MARKERS set
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   247
     *                          int bridgeCount,          // IF flags has BRIDGES set
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   248
     *                          MethodType... bridges     // IF flags has BRIDGES set
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   249
     *                          )
21339
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   250
     * }</pre>
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   251
     *
21339
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   252
     * <p>If the flags contains {@code FLAG_SERIALIZABLE}, or one of the marker
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   253
     * interfaces extends {@link Serializable}, the metafactory will link the
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   254
     * call site to one that produces a serializable lambda.  In addition to
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   255
     * the lambda instance implementing {@code Serializable}, it will have a
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   256
     * {@code writeReplace} method that returns an appropriate {@link
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   257
     * SerializedLambda}, and an appropriate {@code $deserializeLambda$}
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   258
     * method.
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   259
     *
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   260
     * @param caller Stacked automatically by VM; represents a lookup context
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   261
     *               with the accessibility privileges of the caller.
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   262
     * @param invokedName Stacked automatically by VM; the name of the invoked
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   263
     *                    method as it appears at the call site.
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   264
     *                    Used as the name of the functional interface method
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   265
     *                    to which the lambda or method reference is being
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   266
     *                    converted.
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   267
     * @param invokedType Stacked automatically by VM; the signature of the
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   268
     *                    invoked method, which includes the expected static
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   269
     *                    type of the returned lambda object, and the static
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   270
     *                    types of the captured arguments for the lambda.
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   271
     *                    In the event that the implementation method is an
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   272
     *                    instance method, the first argument in the invocation
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   273
     *                    signature will correspond to the receiver.
21339
20e8b81964d5 8025909: Lambda Library Spec Updates
henryjen
parents: 18716
diff changeset
   274
     * @param  args       flags and optional arguments, as described above.
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   275
     * @return a CallSite, which, when invoked, will return an instance of the
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   276
     * functional interface
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   277
     * @throws ReflectiveOperationException if the caller is not able to
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   278
     * reconstruct one of the method handles
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   279
     * @throws LambdaConversionException If any of the meta-factory protocol
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   280
     * invariants are violated
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   281
     */
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   282
    public static CallSite altMetafactory(MethodHandles.Lookup caller,
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   283
                                          String invokedName,
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   284
                                          MethodType invokedType,
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   285
                                          Object... args)
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   286
            throws ReflectiveOperationException, LambdaConversionException {
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   287
        MethodType samMethodType = (MethodType)args[0];
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   288
        MethodHandle implMethod = (MethodHandle)args[1];
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   289
        MethodType instantiatedMethodType = (MethodType)args[2];
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   290
        int flags = (Integer) args[3];
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   291
        Class<?>[] markerInterfaces;
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   292
        MethodType[] bridges;
16001
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   293
        int argIndex = 4;
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   294
        if ((flags & FLAG_MARKERS) != 0) {
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   295
            int markerCount = (Integer) args[argIndex++];
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   296
            markerInterfaces = new Class<?>[markerCount];
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   297
            System.arraycopy(args, argIndex, markerInterfaces, 0, markerCount);
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   298
            argIndex += markerCount;
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   299
        }
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   300
        else
fd4c8d3becf8 8004970: Implement serialization in the lambda metafactory
rfield
parents: 14323
diff changeset
   301
            markerInterfaces = EMPTY_CLASS_ARRAY;
18716
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   302
        if ((flags & FLAG_BRIDGES) != 0) {
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   303
            int bridgeCount = (Integer) args[argIndex++];
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   304
            bridges = new MethodType[bridgeCount];
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   305
            System.arraycopy(args, argIndex, bridges, 0, bridgeCount);
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   306
            argIndex += bridgeCount;
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   307
        }
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   308
        else
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   309
            bridges = EMPTY_MT_ARRAY;
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   310
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   311
        boolean foundSerializableSupertype = Serializable.class.isAssignableFrom(invokedType.returnType());
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   312
        for (Class<?> c : markerInterfaces)
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   313
            foundSerializableSupertype |= Serializable.class.isAssignableFrom(c);
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   314
        boolean isSerializable = ((flags & LambdaMetafactory.FLAG_SERIALIZABLE) != 0)
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   315
                                 || foundSerializableSupertype;
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   316
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   317
        if (isSerializable && !foundSerializableSupertype) {
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   318
            markerInterfaces = Arrays.copyOf(markerInterfaces, markerInterfaces.length + 1);
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   319
            markerInterfaces[markerInterfaces.length-1] = Serializable.class;
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   320
        }
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   321
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   322
        AbstractValidatingLambdaMetafactory mf
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   323
                = new InnerClassLambdaMetafactory(caller, invokedType,
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   324
                                                  invokedName, samMethodType,
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   325
                                                  implMethod,
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   326
                                                  instantiatedMethodType,
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   327
                                                  isSerializable,
9723e722b955 8016281: The SAM method should be passed to the metafactory as a MethodType not a MethodHandle
mcimadamore
parents: 18569
diff changeset
   328
                                                  markerInterfaces, bridges);
14323
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   329
        mf.validateMetafactoryArgs();
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   330
        return mf.buildCallSite();
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   331
    }
5acca3d1f124 8000806: Implement runtime lambda metafactory
rfield
parents:
diff changeset
   332
}