1 /* 2 * Copyright (c) 2009, 2016, 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. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 */ 23 package jdk.vm.ci.meta; 24 25 import java.util.IllegalFormatException; 26 import java.util.UnknownFormatConversionException; 27 28 /** 29 * Represents a reference to a Java method, either resolved or unresolved. Methods, like fields and 30 * types, are resolved through {@link ConstantPool constant pools}. 31 */ 32 public interface JavaMethod { 33 34 /** 35 * Returns the name of this method. 36 */ 37 String getName(); 38 39 /** 40 * Returns the {@link JavaType} object representing the class or interface that declares this 41 * method. 42 */ 43 JavaType getDeclaringClass(); 44 45 /** 46 * Returns the signature of this method. 47 */ 48 Signature getSignature(); 49 50 /** 51 * Gets a string for this method formatted according to a given format specification. A format 52 * specification is composed of characters that are to be copied verbatim to the result and 53 * specifiers that denote an attribute of this method that is to be copied to the result. A 54 * specifier is a single character preceded by a '%' character. The accepted specifiers and the 55 * method attributes they denote are described below: 56 * 57 * <pre> 58 * Specifier | Description | Example(s) 59 * ----------+------------------------------------------------------------------------------------------ 60 * 'R' | Qualified return type | "int" "java.lang.String" 61 * 'r' | Unqualified return type | "int" "String" 62 * 'H' | Qualified holder | "java.util.Map.Entry" 63 * 'h' | Unqualified holder | "Entry" 64 * 'n' | Method name | "add" 65 * 'P' | Qualified parameter types, separated by ', ' | "int, java.lang.String" 66 * 'p' | Unqualified parameter types, separated by ', ' | "int, String" 67 * 'f' | Indicator if method is unresolved, static or virtual | "unresolved" "static" "virtual" 68 * '%' | A '%' character | "%" 69 * </pre> 70 * 71 * @param format a format specification 72 * @return the result of formatting this method according to {@code format} 73 * @throws IllegalFormatException if an illegal specifier is encountered in {@code format} 74 */ 75 default String format(String format) throws IllegalFormatException { 76 StringBuilder sb = new StringBuilder(); 77 int index = 0; 78 Signature sig = null; 79 while (index < format.length()) { 80 char ch = format.charAt(index++); 81 if (ch == '%') { 82 if (index >= format.length()) { 83 throw new UnknownFormatConversionException("An unquoted '%' character cannot terminate a method format specification"); 84 } 85 char specifier = format.charAt(index++); 86 switch (specifier) { 87 case 'R': 88 case 'r': { 89 if (sig == null) { 90 sig = getSignature(); 91 } 92 sb.append(sig.getReturnType(null).toJavaName(specifier == 'R')); 93 break; 94 } 95 case 'H': 96 case 'h': { 97 sb.append(getDeclaringClass().toJavaName(specifier == 'H')); 98 break; 99 } 100 case 'n': { 101 sb.append(getName()); 102 break; 103 } 104 case 'P': 105 case 'p': { 106 if (sig == null) { 107 sig = getSignature(); 108 } 109 for (int i = 0; i < sig.getParameterCount(false); i++) { 110 if (i != 0) { 111 sb.append(", "); 112 } 113 sb.append(sig.getParameterType(i, null).toJavaName(specifier == 'P')); 114 } 115 break; 116 } 117 case 'f': { 118 sb.append(!(this instanceof ResolvedJavaMethod) ? "unresolved" : ((ResolvedJavaMethod) this).isStatic() ? "static" : "virtual"); 119 break; 120 } 121 case '%': { 122 sb.append('%'); 123 break; 124 } 125 default: { 126 throw new UnknownFormatConversionException(String.valueOf(specifier)); 127 } 128 } 129 } else { 130 sb.append(ch); 131 } 132 } 133 return sb.toString(); 134 } 135 }