Tue, 25 May 2010 15:54:51 -0700
6943119: Rebrand source copyright notices
Reviewed-by: darcy
1 /*
2 * Copyright (c) 2002, 2008, 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 */
27 package com.sun.tools.javah;
29 import java.util.*;
30 import javax.lang.model.element.Name;
31 import javax.lang.model.element.TypeElement;
32 import javax.lang.model.type.ArrayType;
33 import javax.lang.model.type.DeclaredType;
34 import javax.lang.model.type.NoType;
35 import javax.lang.model.type.PrimitiveType;
36 import javax.lang.model.type.TypeKind;
37 import javax.lang.model.type.TypeMirror;
38 import javax.lang.model.type.TypeVariable;
39 import javax.lang.model.type.TypeVisitor;
40 import javax.lang.model.util.Elements;
41 import javax.lang.model.util.SimpleTypeVisitor6;
43 /**
44 * Returns internal type signature.
45 *
46 * <p><b>This is NOT part of any API supported by Sun Microsystems.
47 * If you write code that depends on this, you do so at your own
48 * risk. This code and its internal interfaces are subject to change
49 * or deletion without notice.</b></p>
50 *
51 * @author Sucheta Dambalkar
52 */
54 public class TypeSignature{
56 Elements elems;
58 /* Signature Characters */
60 private static final String SIG_VOID = "V";
61 private static final String SIG_BOOLEAN = "Z";
62 private static final String SIG_BYTE = "B";
63 private static final String SIG_CHAR = "C";
64 private static final String SIG_SHORT = "S";
65 private static final String SIG_INT = "I";
66 private static final String SIG_LONG = "J";
67 private static final String SIG_FLOAT = "F";
68 private static final String SIG_DOUBLE = "D";
69 private static final String SIG_ARRAY = "[";
70 private static final String SIG_CLASS = "L";
74 public TypeSignature(Elements elems){
75 this.elems = elems;
76 }
78 /*
79 * Returns the type signature of a field according to JVM specs
80 */
81 public String getTypeSignature(String javasignature){
82 return getParamJVMSignature(javasignature);
83 }
85 /*
86 * Returns the type signature of a method according to JVM specs
87 */
88 public String getTypeSignature(String javasignature, TypeMirror returnType){
89 String signature = null; //Java type signature.
90 String typeSignature = null; //Internal type signature.
91 List<String> params = new ArrayList<String>(); //List of parameters.
92 String paramsig = null; //Java parameter signature.
93 String paramJVMSig = null; //Internal parameter signature.
94 String returnSig = null; //Java return type signature.
95 String returnJVMType = null; //Internal return type signature.
96 int dimensions = 0; //Array dimension.
98 int startIndex = -1;
99 int endIndex = -1;
100 StringTokenizer st = null;
101 int i = 0;
103 // Gets the actual java signature without parentheses.
104 if (javasignature != null) {
105 startIndex = javasignature.indexOf("(");
106 endIndex = javasignature.indexOf(")");
107 }
109 if (((startIndex != -1) && (endIndex != -1))
110 &&(startIndex+1 < javasignature.length())
111 &&(endIndex < javasignature.length())) {
112 signature = javasignature.substring(startIndex+1, endIndex);
113 }
115 // Separates parameters.
116 if (signature != null) {
117 if (signature.indexOf(",") != -1) {
118 st = new StringTokenizer(signature, ",");
119 if (st != null) {
120 while (st.hasMoreTokens()) {
121 params.add(st.nextToken());
122 }
123 }
124 } else {
125 params.add(signature);
126 }
127 }
129 /* JVM type signature. */
130 typeSignature = "(";
132 // Gets indivisual internal parameter signature.
133 while (params.isEmpty() != true) {
134 paramsig = params.remove(i).trim();
135 paramJVMSig = getParamJVMSignature(paramsig);
136 if (paramJVMSig != null) {
137 typeSignature += paramJVMSig;
138 }
139 }
141 typeSignature += ")";
143 // Get internal return type signature.
145 returnJVMType = "";
146 if (returnType != null) {
147 dimensions = dimensions(returnType);
148 }
150 //Gets array dimension of return type.
151 while (dimensions-- > 0) {
152 returnJVMType += "[";
153 }
154 if (returnType != null) {
155 returnSig = qualifiedTypeName(returnType);
156 returnJVMType += getComponentType(returnSig);
157 } else {
158 System.out.println("Invalid return type.");
159 }
161 typeSignature += returnJVMType;
163 return typeSignature;
164 }
166 /*
167 * Returns internal signature of a parameter.
168 */
169 private String getParamJVMSignature(String paramsig) {
170 String paramJVMSig = "";
171 String componentType ="";
173 if(paramsig != null){
175 if(paramsig.indexOf("[]") != -1) {
176 // Gets array dimension.
177 int endindex = paramsig.indexOf("[]");
178 componentType = paramsig.substring(0, endindex);
179 String dimensionString = paramsig.substring(endindex);
180 if(dimensionString != null){
181 while(dimensionString.indexOf("[]") != -1){
182 paramJVMSig += "[";
183 int beginindex = dimensionString.indexOf("]") + 1;
184 if(beginindex < dimensionString.length()){
185 dimensionString = dimensionString.substring(beginindex);
186 }else
187 dimensionString = "";
188 }
189 }
190 } else componentType = paramsig;
192 paramJVMSig += getComponentType(componentType);
193 }
194 return paramJVMSig;
195 }
197 /*
198 * Returns internal signature of a component.
199 */
200 private String getComponentType(String componentType){
202 String JVMSig = "";
204 if(componentType != null){
205 if(componentType.equals("void")) JVMSig += SIG_VOID ;
206 else if(componentType.equals("boolean")) JVMSig += SIG_BOOLEAN ;
207 else if(componentType.equals("byte")) JVMSig += SIG_BYTE ;
208 else if(componentType.equals("char")) JVMSig += SIG_CHAR ;
209 else if(componentType.equals("short")) JVMSig += SIG_SHORT ;
210 else if(componentType.equals("int")) JVMSig += SIG_INT ;
211 else if(componentType.equals("long")) JVMSig += SIG_LONG ;
212 else if(componentType.equals("float")) JVMSig += SIG_FLOAT ;
213 else if(componentType.equals("double")) JVMSig += SIG_DOUBLE ;
214 else {
215 if(!componentType.equals("")){
216 TypeElement classNameDoc = elems.getTypeElement(componentType);
218 if(classNameDoc == null){
219 System.out.println("Invalid class type for " + componentType);
220 new Exception().printStackTrace();
221 }else {
222 String classname = classNameDoc.getQualifiedName().toString();
223 String newclassname = classname.replace('.', '/');
224 JVMSig += "L";
225 JVMSig += newclassname;
226 JVMSig += ";";
227 }
228 }
229 }
230 }
231 return JVMSig;
232 }
234 int dimensions(TypeMirror t) {
235 if (t.getKind() != TypeKind.ARRAY)
236 return 0;
237 return 1 + dimensions(((ArrayType) t).getComponentType());
238 }
241 String qualifiedTypeName(TypeMirror type) {
242 TypeVisitor<Name, Void> v = new SimpleTypeVisitor6<Name, Void>() {
243 @Override
244 public Name visitArray(ArrayType t, Void p) {
245 return t.getComponentType().accept(this, p);
246 }
248 @Override
249 public Name visitDeclared(DeclaredType t, Void p) {
250 return ((TypeElement) t.asElement()).getQualifiedName();
251 }
253 @Override
254 public Name visitPrimitive(PrimitiveType t, Void p) {
255 return elems.getName(t.toString());
256 }
258 @Override
259 public Name visitNoType(NoType t, Void p) {
260 if (t.getKind() == TypeKind.VOID)
261 return elems.getName("void");
262 return defaultAction(t, p);
263 }
265 @Override
266 public Name visitTypeVariable(TypeVariable t, Void p) {
267 return t.getUpperBound().accept(this, p);
268 }
269 };
270 return v.visit(type).toString();
271 }
272 }