1 /*
2  * Copyright (c) 2018, Oracle and/or its affiliates. All rights reserved.
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
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
7  * published by the Free Software Foundation.  Oracle designates this
8  * particular file as subject to the "Classpath" exception as provided
9  * by Oracle in the LICENSE file that accompanied this code.
10  *
11  * This code is distributed in the hope that it will be useful, but WITHOUT
12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
14  * version 2 for more details (a copy is included in the LICENSE file that
15  * accompanied this code).
16  *
17  * You should have received a copy of the GNU General Public License version
18  * 2 along with this work; if not, write to the Free Software Foundation,
19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20  *
21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22  * or visit www.oracle.com if you need additional information or have any
23  * questions.
24  */
25 package java.lang.invoke;
26 
27 import java.util.List;
28 
29 /**
30  * An entity that has a field or method type descriptor
31  *
32  * @jvms 4.3.2 Field Descriptors
33  * @jvms 4.3.3 Method Descriptors
34  *
35  * @since 12
36  */
37 public interface TypeDescriptor {
38     /**
39      * Return the type descriptor string for this instance, which must be either
40      * a field type descriptor (JVMS 4.3.2) or method type descriptor (JVMS 4.3.3).
41      *
42      * @return the type descriptor
43      * @jvms 4.3.2 Field Descriptors
44      * @jvms 4.3.3 Method Descriptors
45      */
descriptorString()46     String descriptorString();
47 
48 
49     /**
50      * An entity that has a field type descriptor
51      *
52      * @param <F> the class implementing {@linkplain TypeDescriptor.OfField}
53      * @jvms 4.3.2 Field Descriptors
54      * @since 12
55      */
56     interface OfField<F extends TypeDescriptor.OfField<F>> extends TypeDescriptor {
57         /**
58          * Does this field descriptor describe an array type?
59          * @return whether this field descriptor describes an array type
60          */
isArray()61         boolean isArray();
62 
63         /**
64          * Does this field descriptor describe a primitive type (including void.)
65          *
66          * @return whether this field descriptor describes a primitive type
67          */
isPrimitive()68         boolean isPrimitive();
69 
70         /**
71          * If this field descriptor describes an array type, return
72          * a descriptor for its component type, otherwise return {@code null}.
73          * @return the component type, or {@code null} if this field descriptor does
74          * not describe an array type
75          */
componentType()76         F componentType();
77 
78         /**
79          * Return a descriptor for the array type whose component type is described by this
80          * descriptor
81          * @return the descriptor for the array type
82          */
arrayType()83         F arrayType();
84     }
85 
86 
87     /**
88      * An entity that has a method type descriptor
89      *
90      * @param <F> the type representing field type descriptors
91      * @param <M> the class implementing {@linkplain TypeDescriptor.OfMethod}
92      * @jvms 4.3.2 Field Descriptors
93      * @jvms 4.3.3 Method Descriptors
94      * @since 12
95      */
96     interface OfMethod<F extends TypeDescriptor.OfField<F>, M extends TypeDescriptor.OfMethod<F, M>>
97             extends TypeDescriptor {
98 
99         /**
100          * Return the number of parameters in the method type
101          * @return the number of parameters
102          */
parameterCount()103         int parameterCount();
104 
105         /**
106          * Return a field descriptor describing the requested parameter of the method type
107          * described by this descriptor
108          * @param i the index of the parameter
109          * @return a field descriptor for the requested parameter type
110          * @throws IndexOutOfBoundsException if the index is outside the half-open
111          * range {[0, parameterCount)}
112          */
parameterType(int i)113         F parameterType(int i);
114 
115         /**
116          * Return a field descriptor describing the return type of the method type described
117          * by this descriptor
118          * @return a field descriptor for the return type
119          */
returnType()120         F returnType();
121 
122         /**
123          * Return an array of field descriptors for the parameter types of the method type
124          * described by this descriptor
125          * @return field descriptors for the parameter types
126          */
parameterArray()127         F[] parameterArray();
128 
129         /**
130          * Return an immutable list of field descriptors for the parameter types of the method type
131          * described by this descriptor
132          * @return field descriptors for the parameter types
133          */
parameterList()134         List<F> parameterList();
135 
136         /**
137          * Return a method descriptor that is identical to this one, except that the return
138          * type has been changed to the specified type
139          *
140          * @param newReturn a field descriptor for the new return type
141          * @throws NullPointerException if any argument is {@code null}
142          * @return the new method descriptor
143          */
changeReturnType(F newReturn)144         M changeReturnType(F newReturn);
145 
146         /**
147          * Return a method descriptor that is identical to this one,
148          * except that a single parameter type has been changed to the specified type.
149          *
150          * @param index the index of the parameter to change
151          * @param paramType a field descriptor describing the new parameter type
152          * @return the new method descriptor
153          * @throws NullPointerException if any argument is {@code null}
154          * @throws IndexOutOfBoundsException if the index is outside the half-open
155          * range {[0, parameterCount)}
156          */
changeParameterType(int index, F paramType)157         M changeParameterType(int index, F paramType);
158 
159         /**
160          * Return a method descriptor that is identical to this one,
161          * except that a range of parameter types have been removed.
162          *
163          * @param start the index of the first parameter to remove
164          * @param end the index after the last parameter to remove
165          * @return the new method descriptor
166          *
167          * @throws IndexOutOfBoundsException if {@code start} is outside the half-open
168          * range {@code [0, parameterCount)}, or {@code end} is outside the closed range
169          * {@code [0, parameterCount]}, or if {@code start > end}
170          */
dropParameterTypes(int start, int end)171         M dropParameterTypes(int start, int end);
172 
173         /**
174          * Return a method descriptor that is identical to this one,
175          * except that a range of additional parameter types have been inserted.
176          *
177          * @param pos the index at which to insert the first inserted parameter
178          * @param paramTypes field descriptors describing the new parameter types
179          *                   to insert
180          * @return the new method descriptor
181          * @throws NullPointerException if any argument is {@code null}
182          * @throws IndexOutOfBoundsException if {@code pos} is outside the closed
183          * range {[0, parameterCount]}
184          */
185         @SuppressWarnings("unchecked")
insertParameterTypes(int pos, F... paramTypes)186         M insertParameterTypes(int pos, F... paramTypes);
187     }
188 }
189