src/share/classes/com/sun/tools/classfile/Type.java

Tue, 19 Feb 2013 17:19:01 -0800

author
ksrini
date
Tue, 19 Feb 2013 17:19:01 -0800
changeset 1592
9345394ac8fe
parent 953
c55928005af4
child 2525
2eb010b6cb22
permissions
-rw-r--r--

8006948: Update javac for MethodParameters format change
Reviewed-by: ksrini, forax
Contributed-by: eric.mccorkle@oracle.com

jjg@46 1 /*
jjg@953 2 * Copyright (c) 2008, 2011, Oracle and/or its affiliates. All rights reserved.
jjg@46 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
jjg@46 4 *
jjg@46 5 * This code is free software; you can redistribute it and/or modify it
jjg@46 6 * under the terms of the GNU General Public License version 2 only, as
ohair@554 7 * published by the Free Software Foundation. Oracle designates this
jjg@46 8 * particular file as subject to the "Classpath" exception as provided
ohair@554 9 * by Oracle in the LICENSE file that accompanied this code.
jjg@46 10 *
jjg@46 11 * This code is distributed in the hope that it will be useful, but WITHOUT
jjg@46 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
jjg@46 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
jjg@46 14 * version 2 for more details (a copy is included in the LICENSE file that
jjg@46 15 * accompanied this code).
jjg@46 16 *
jjg@46 17 * You should have received a copy of the GNU General Public License version
jjg@46 18 * 2 along with this work; if not, write to the Free Software Foundation,
jjg@46 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
jjg@46 20 *
ohair@554 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
ohair@554 22 * or visit www.oracle.com if you need additional information or have any
ohair@554 23 * questions.
jjg@46 24 */
jjg@46 25
jjg@46 26 package com.sun.tools.classfile;
jjg@46 27
jjg@280 28 import java.util.Arrays;
jjg@280 29 import java.util.HashSet;
jjg@46 30 import java.util.List;
jjg@280 31 import java.util.Set;
jjg@46 32
jjg@46 33 /*
jjg@427 34 * Family of classes used to represent the parsed form of a {@link Descriptor}
jjg@427 35 * or {@link Signature}.
jjg@427 36 *
jjg@581 37 * <p><b>This is NOT part of any supported API.
jjg@581 38 * If you write code that depends on this, you do so at your own risk.
jjg@46 39 * This code and its internal interfaces are subject to change or
jjg@46 40 * deletion without notice.</b>
jjg@46 41 */
jjg@280 42 public abstract class Type {
jjg@46 43 protected Type() { }
jjg@953 44
jjg@953 45 public boolean isObject() {
jjg@953 46 return false;
jjg@953 47 }
jjg@953 48
jjg@280 49 public abstract <R,D> R accept(Visitor<R,D> visitor, D data);
jjg@46 50
jjg@46 51 protected static void append(StringBuilder sb, String prefix, List<? extends Type> types, String suffix) {
jjg@46 52 sb.append(prefix);
jjg@46 53 String sep = "";
jjg@46 54 for (Type t: types) {
jjg@46 55 sb.append(sep);
jjg@46 56 sb.append(t);
jjg@46 57 sep = ", ";
jjg@46 58 }
jjg@46 59 sb.append(suffix);
jjg@46 60 }
jjg@46 61
jjg@46 62 protected static void appendIfNotEmpty(StringBuilder sb, String prefix, List<? extends Type> types, String suffix) {
jjg@46 63 if (types != null && types.size() > 0)
jjg@46 64 append(sb, prefix, types, suffix);
jjg@46 65 }
jjg@46 66
jjg@280 67 public interface Visitor<R,P> {
jjg@280 68 R visitSimpleType(SimpleType type, P p);
jjg@280 69 R visitArrayType(ArrayType type, P p);
jjg@280 70 R visitMethodType(MethodType type, P p);
jjg@280 71 R visitClassSigType(ClassSigType type, P p);
jjg@280 72 R visitClassType(ClassType type, P p);
jjg@427 73 R visitTypeParamType(TypeParamType type, P p);
jjg@280 74 R visitWildcardType(WildcardType type, P p);
jjg@280 75 }
jjg@280 76
jjg@427 77 /**
jjg@427 78 * Represents a type signature with a simple name. The name may be that of a
jjg@427 79 * primitive type, such "{@code int}, {@code float}, etc
jjg@427 80 * or that of a type argument, such as {@code T}, {@code K}, {@code V}, etc.
jjg@427 81 *
jjg@427 82 * See:
jjg@427 83 * JVMS 4.3.2
jjg@427 84 * BaseType:
jjg@427 85 * {@code B}, {@code C}, {@code D}, {@code F}, {@code I},
jjg@427 86 * {@code J}, {@code S}, {@code Z};
jjg@427 87 * VoidDescriptor:
jjg@427 88 * {@code V};
jjg@427 89 * JVMS 4.3.4
jjg@427 90 * TypeVariableSignature:
jjg@427 91 * {@code T} Identifier {@code ;}
jjg@427 92 */
jjg@46 93 public static class SimpleType extends Type {
jjg@46 94 public SimpleType(String name) {
jjg@46 95 this.name = name;
jjg@46 96 }
jjg@46 97
jjg@280 98 public <R, D> R accept(Visitor<R, D> visitor, D data) {
jjg@280 99 return visitor.visitSimpleType(this, data);
jjg@280 100 }
jjg@280 101
jjg@280 102 public boolean isPrimitiveType() {
jjg@280 103 return primitiveTypes.contains(name);
jjg@280 104 }
jjg@280 105 // where
jjg@280 106 private static final Set<String> primitiveTypes = new HashSet<String>(Arrays.asList(
jjg@280 107 "boolean", "byte", "char", "double", "float", "int", "long", "short", "void"));
jjg@280 108
jjg@46 109 @Override
jjg@46 110 public String toString() {
jjg@46 111 return name;
jjg@46 112 }
jjg@46 113
jjg@46 114 public final String name;
jjg@46 115 }
jjg@46 116
jjg@427 117 /**
jjg@427 118 * Represents an array type signature.
jjg@427 119 *
jjg@427 120 * See:
jjg@427 121 * JVMS 4.3.4
jjg@427 122 * ArrayTypeSignature:
jjg@427 123 * {@code [} TypeSignature {@code ]}
jjg@427 124 */
jjg@46 125 public static class ArrayType extends Type {
jjg@46 126 public ArrayType(Type elemType) {
jjg@46 127 this.elemType = elemType;
jjg@46 128 }
jjg@46 129
jjg@280 130 public <R, D> R accept(Visitor<R, D> visitor, D data) {
jjg@280 131 return visitor.visitArrayType(this, data);
jjg@280 132 }
jjg@280 133
jjg@46 134 @Override
jjg@46 135 public String toString() {
jjg@46 136 return elemType + "[]";
jjg@46 137 }
jjg@46 138
jjg@46 139 public final Type elemType;
jjg@46 140 }
jjg@46 141
jjg@427 142 /**
jjg@427 143 * Represents a method type signature.
jjg@427 144 *
jjg@427 145 * See;
jjg@427 146 * JVMS 4.3.4
jjg@427 147 * MethodTypeSignature:
jjg@427 148 * FormalTypeParameters_opt {@code (} TypeSignature* {@code)} ReturnType
jjg@427 149 * ThrowsSignature*
jjg@427 150 */
jjg@46 151 public static class MethodType extends Type {
jjg@427 152 public MethodType(List<? extends Type> paramTypes, Type resultType) {
jjg@427 153 this(null, paramTypes, resultType, null);
jjg@46 154 }
jjg@46 155
jjg@427 156 public MethodType(List<? extends TypeParamType> typeParamTypes,
jjg@427 157 List<? extends Type> paramTypes,
jjg@46 158 Type returnType,
jjg@46 159 List<? extends Type> throwsTypes) {
jjg@427 160 this.typeParamTypes = typeParamTypes;
jjg@427 161 this.paramTypes = paramTypes;
jjg@46 162 this.returnType = returnType;
jjg@46 163 this.throwsTypes = throwsTypes;
jjg@46 164 }
jjg@46 165
jjg@280 166 public <R, D> R accept(Visitor<R, D> visitor, D data) {
jjg@280 167 return visitor.visitMethodType(this, data);
jjg@280 168 }
jjg@280 169
jjg@46 170 @Override
jjg@46 171 public String toString() {
jjg@46 172 StringBuilder sb = new StringBuilder();
jjg@427 173 appendIfNotEmpty(sb, "<", typeParamTypes, "> ");
jjg@46 174 sb.append(returnType);
jjg@427 175 append(sb, " (", paramTypes, ")");
jjg@46 176 appendIfNotEmpty(sb, " throws ", throwsTypes, "");
jjg@46 177 return sb.toString();
jjg@46 178 }
jjg@46 179
jjg@427 180 public final List<? extends TypeParamType> typeParamTypes;
jjg@427 181 public final List<? extends Type> paramTypes;
jjg@46 182 public final Type returnType;
jjg@46 183 public final List<? extends Type> throwsTypes;
jjg@46 184 }
jjg@46 185
jjg@427 186 /**
jjg@427 187 * Represents a class signature. These describe the signature of
jjg@427 188 * a class that has type arguments.
jjg@427 189 *
jjg@427 190 * See:
jjg@427 191 * JVMS 4.3.4
jjg@427 192 * ClassSignature:
jjg@427 193 * FormalTypeParameters_opt SuperclassSignature SuperinterfaceSignature*
jjg@427 194 */
jjg@46 195 public static class ClassSigType extends Type {
jjg@427 196 public ClassSigType(List<TypeParamType> typeParamTypes, Type superclassType,
jjg@427 197 List<Type> superinterfaceTypes) {
jjg@427 198 this.typeParamTypes = typeParamTypes;
jjg@46 199 this.superclassType = superclassType;
jjg@46 200 this.superinterfaceTypes = superinterfaceTypes;
jjg@46 201 }
jjg@46 202
jjg@280 203 public <R, D> R accept(Visitor<R, D> visitor, D data) {
jjg@280 204 return visitor.visitClassSigType(this, data);
jjg@280 205 }
jjg@280 206
jjg@46 207 @Override
jjg@46 208 public String toString() {
jjg@46 209 StringBuilder sb = new StringBuilder();
jjg@427 210 appendIfNotEmpty(sb, "<", typeParamTypes, ">");
jjg@65 211 if (superclassType != null) {
jjg@46 212 sb.append(" extends ");
jjg@46 213 sb.append(superclassType);
jjg@46 214 }
jjg@46 215 appendIfNotEmpty(sb, " implements ", superinterfaceTypes, "");
jjg@46 216 return sb.toString();
jjg@46 217 }
jjg@46 218
jjg@427 219 public final List<TypeParamType> typeParamTypes;
jjg@46 220 public final Type superclassType;
jjg@46 221 public final List<Type> superinterfaceTypes;
jjg@46 222 }
jjg@46 223
jjg@427 224 /**
jjg@427 225 * Represents a class type signature. This is used to represent a
jjg@427 226 * reference to a class, such as in a field, parameter, return type, etc.
jjg@427 227 *
jjg@427 228 * See:
jjg@427 229 * JVMS 4.3.4
jjg@427 230 * ClassTypeSignature:
jjg@427 231 * {@code L} PackageSpecifier_opt SimpleClassTypeSignature
jjg@427 232 * ClassTypeSignatureSuffix* {@code ;}
jjg@427 233 * PackageSpecifier:
jjg@427 234 * Identifier {@code /} PackageSpecifier*
jjg@427 235 * SimpleClassTypeSignature:
jjg@427 236 * Identifier TypeArguments_opt }
jjg@427 237 * ClassTypeSignatureSuffix:
jjg@427 238 * {@code .} SimpleClassTypeSignature
jjg@427 239 */
jjg@46 240 public static class ClassType extends Type {
jjg@427 241 public ClassType(ClassType outerType, String name, List<Type> typeArgs) {
jjg@427 242 this.outerType = outerType;
jjg@46 243 this.name = name;
jjg@46 244 this.typeArgs = typeArgs;
jjg@46 245 }
jjg@46 246
jjg@280 247 public <R, D> R accept(Visitor<R, D> visitor, D data) {
jjg@280 248 return visitor.visitClassType(this, data);
jjg@280 249 }
jjg@280 250
jjg@427 251 public String getBinaryName() {
jjg@427 252 if (outerType == null)
jjg@427 253 return name;
jjg@427 254 else
jjg@427 255 return (outerType.getBinaryName() + "$" + name);
jjg@427 256 }
jjg@427 257
jjg@46 258 @Override
jjg@46 259 public String toString() {
jjg@46 260 StringBuilder sb = new StringBuilder();
jjg@427 261 if (outerType != null) {
jjg@427 262 sb.append(outerType);
jjg@427 263 sb.append(".");
jjg@427 264 }
jjg@46 265 sb.append(name);
jjg@46 266 appendIfNotEmpty(sb, "<", typeArgs, ">");
jjg@46 267 return sb.toString();
jjg@46 268 }
jjg@46 269
jjg@953 270 @Override
jjg@953 271 public boolean isObject() {
jjg@953 272 return (outerType == null)
jjg@953 273 && name.equals("java/lang/Object")
jjg@953 274 && (typeArgs == null || typeArgs.isEmpty());
jjg@953 275 }
jjg@953 276
jjg@427 277 public final ClassType outerType;
jjg@46 278 public final String name;
jjg@46 279 public final List<Type> typeArgs;
jjg@46 280 }
jjg@46 281
jjg@427 282 /**
jjg@427 283 * Represents a FormalTypeParameter. These are used to declare the type
jjg@427 284 * parameters for generic classes and methods.
jjg@427 285 *
jjg@427 286 * See:
jjg@427 287 * JVMS 4.3.4
jjg@427 288 * FormalTypeParameters:
jjg@427 289 * {@code <} FormalTypeParameter+ {@code >}
jjg@427 290 * FormalTypeParameter:
jjg@427 291 * Identifier ClassBound InterfaceBound*
jjg@427 292 * ClassBound:
jjg@427 293 * {@code :} FieldTypeSignature_opt
jjg@427 294 * InterfaceBound:
jjg@427 295 * {@code :} FieldTypeSignature
jjg@427 296 */
jjg@427 297 public static class TypeParamType extends Type {
jjg@427 298 public TypeParamType(String name, Type classBound, List<Type> interfaceBounds) {
jjg@46 299 this.name = name;
jjg@46 300 this.classBound = classBound;
jjg@46 301 this.interfaceBounds = interfaceBounds;
jjg@46 302 }
jjg@46 303
jjg@280 304 public <R, D> R accept(Visitor<R, D> visitor, D data) {
jjg@427 305 return visitor.visitTypeParamType(this, data);
jjg@280 306 }
jjg@280 307
jjg@46 308 @Override
jjg@46 309 public String toString() {
jjg@46 310 StringBuilder sb = new StringBuilder();
jjg@46 311 sb.append(name);
jjg@46 312 String sep = " extends ";
jjg@65 313 if (classBound != null) {
jjg@46 314 sb.append(sep);
jjg@46 315 sb.append(classBound);
jjg@46 316 sep = " & ";
jjg@46 317 }
jjg@46 318 if (interfaceBounds != null) {
jjg@46 319 for (Type bound: interfaceBounds) {
jjg@46 320 sb.append(sep);
jjg@46 321 sb.append(bound);
jjg@46 322 sep = " & ";
jjg@46 323 }
jjg@46 324 }
jjg@46 325 return sb.toString();
jjg@46 326 }
jjg@46 327
jjg@46 328 public final String name;
jjg@46 329 public final Type classBound;
jjg@46 330 public final List<Type> interfaceBounds;
jjg@46 331 }
jjg@46 332
jjg@427 333 /**
jjg@427 334 * Represents a wildcard type argument. A type argument that is not a
jjg@427 335 * wildcard type argument will be represented by a ClassType, ArrayType, etc.
jjg@427 336 *
jjg@427 337 * See:
jjg@427 338 * JVMS 4.3.4
jjg@427 339 * TypeArgument:
jjg@427 340 * WildcardIndicator_opt FieldTypeSignature
jjg@427 341 * {@code *}
jjg@427 342 * WildcardIndicator:
jjg@427 343 * {@code +}
jjg@427 344 * {@code -}
jjg@427 345 */
jjg@46 346 public static class WildcardType extends Type {
jjg@427 347 public enum Kind { UNBOUNDED, EXTENDS, SUPER };
jjg@46 348 public WildcardType() {
jjg@427 349 this(Kind.UNBOUNDED, null);
jjg@46 350 }
jjg@427 351 public WildcardType(Kind kind, Type boundType) {
jjg@46 352 this.kind = kind;
jjg@46 353 this.boundType = boundType;
jjg@46 354 }
jjg@46 355
jjg@280 356 public <R, D> R accept(Visitor<R, D> visitor, D data) {
jjg@280 357 return visitor.visitWildcardType(this, data);
jjg@280 358 }
jjg@280 359
jjg@46 360 @Override
jjg@46 361 public String toString() {
jjg@427 362 switch (kind) {
jjg@427 363 case UNBOUNDED:
jjg@427 364 return "?";
jjg@427 365 case EXTENDS:
jjg@427 366 return "? extends " + boundType;
jjg@427 367 case SUPER:
jjg@427 368 return "? super " + boundType;
jjg@427 369 default:
jjg@427 370 throw new AssertionError();
jjg@427 371 }
jjg@46 372 }
jjg@46 373
jjg@427 374 public final Kind kind;
jjg@46 375 public final Type boundType;
jjg@46 376 }
jjg@46 377 }

mercurial