Type.java revision 3331:09cd25821441
1/*
2 * Copyright (c) 1999, 2015, 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
26package com.sun.tools.javac.code;
27
28import java.lang.annotation.Annotation;
29import java.util.ArrayDeque;
30import java.util.Collections;
31import java.util.EnumMap;
32import java.util.Map;
33import java.util.function.Function;
34
35import javax.lang.model.type.*;
36
37import com.sun.tools.javac.code.Symbol.*;
38import com.sun.tools.javac.code.TypeMetadata.Entry;
39import com.sun.tools.javac.comp.Infer.IncorporationAction;
40import com.sun.tools.javac.util.*;
41import com.sun.tools.javac.util.DefinedBy.Api;
42
43import static com.sun.tools.javac.code.BoundKind.*;
44import static com.sun.tools.javac.code.Flags.*;
45import static com.sun.tools.javac.code.Kinds.Kind.*;
46import static com.sun.tools.javac.code.TypeTag.*;
47
48/** This class represents Java types. The class itself defines the behavior of
49 *  the following types:
50 *  <pre>
51 *  base types (tags: BYTE, CHAR, SHORT, INT, LONG, FLOAT, DOUBLE, BOOLEAN),
52 *  type `void' (tag: VOID),
53 *  the bottom type (tag: BOT),
54 *  the missing type (tag: NONE).
55 *  </pre>
56 *  <p>The behavior of the following types is defined in subclasses, which are
57 *  all static inner classes of this class:
58 *  <pre>
59 *  class types (tag: CLASS, class: ClassType),
60 *  array types (tag: ARRAY, class: ArrayType),
61 *  method types (tag: METHOD, class: MethodType),
62 *  package types (tag: PACKAGE, class: PackageType),
63 *  type variables (tag: TYPEVAR, class: TypeVar),
64 *  type arguments (tag: WILDCARD, class: WildcardType),
65 *  generic method types (tag: FORALL, class: ForAll),
66 *  the error type (tag: ERROR, class: ErrorType).
67 *  </pre>
68 *
69 *  <p><b>This is NOT part of any supported API.
70 *  If you write code that depends on this, you do so at your own risk.
71 *  This code and its internal interfaces are subject to change or
72 *  deletion without notice.</b>
73 *
74 *  @see TypeTag
75 */
76public abstract class Type extends AnnoConstruct implements TypeMirror {
77
78    /**
79     * Type metadata,  Should be {@code null} for the default value.
80     *
81     * Note: it is an invariant that for any {@code TypeMetadata}
82     * class, a given {@code Type} may have at most one metadata array
83     * entry of that class.
84     */
85    protected final TypeMetadata metadata;
86
87    public TypeMetadata getMetadata() {
88        return metadata;
89    }
90
91    public Entry getMetadataOfKind(final Entry.Kind kind) {
92        return metadata != null ? metadata.get(kind) : null;
93    }
94
95    /** Constant type: no type at all. */
96    public static final JCNoType noType = new JCNoType() {
97        @Override @DefinedBy(Api.LANGUAGE_MODEL)
98        public String toString() {
99            return "none";
100        }
101    };
102
103    /** Constant type: special type to be used during recovery of deferred expressions. */
104    public static final JCNoType recoveryType = new JCNoType(){
105        @Override @DefinedBy(Api.LANGUAGE_MODEL)
106        public String toString() {
107            return "recovery";
108        }
109    };
110
111    /** Constant type: special type to be used for marking stuck trees. */
112    public static final JCNoType stuckType = new JCNoType() {
113        @Override @DefinedBy(Api.LANGUAGE_MODEL)
114        public String toString() {
115            return "stuck";
116        }
117    };
118
119    /** If this switch is turned on, the names of type variables
120     *  and anonymous classes are printed with hashcodes appended.
121     */
122    public static boolean moreInfo = false;
123
124    /** The defining class / interface / package / type variable.
125     */
126    public TypeSymbol tsym;
127
128    /**
129     * Checks if the current type tag is equal to the given tag.
130     * @return true if tag is equal to the current type tag.
131     */
132    public boolean hasTag(TypeTag tag) {
133        return tag == getTag();
134    }
135
136    /**
137     * Returns the current type tag.
138     * @return the value of the current type tag.
139     */
140    public abstract TypeTag getTag();
141
142    public boolean isNumeric() {
143        return false;
144    }
145
146    public boolean isIntegral() {
147        return false;
148    }
149
150    public boolean isPrimitive() {
151        return false;
152    }
153
154    public boolean isPrimitiveOrVoid() {
155        return false;
156    }
157
158    public boolean isReference() {
159        return false;
160    }
161
162    public boolean isNullOrReference() {
163        return false;
164    }
165
166    public boolean isPartial() {
167        return false;
168    }
169
170    /**
171     * The constant value of this type, null if this type does not
172     * have a constant value attribute. Only primitive types and
173     * strings (ClassType) can have a constant value attribute.
174     * @return the constant value attribute of this type
175     */
176    public Object constValue() {
177        return null;
178    }
179
180    /** Is this a constant type whose value is false?
181     */
182    public boolean isFalse() {
183        return false;
184    }
185
186    /** Is this a constant type whose value is true?
187     */
188    public boolean isTrue() {
189        return false;
190    }
191
192    /**
193     * Get the representation of this type used for modelling purposes.
194     * By default, this is itself. For ErrorType, a different value
195     * may be provided.
196     */
197    public Type getModelType() {
198        return this;
199    }
200
201    public static List<Type> getModelTypes(List<Type> ts) {
202        ListBuffer<Type> lb = new ListBuffer<>();
203        for (Type t: ts)
204            lb.append(t.getModelType());
205        return lb.toList();
206    }
207
208    /**For ErrorType, returns the original type, otherwise returns the type itself.
209     */
210    public Type getOriginalType() {
211        return this;
212    }
213
214    public <R,S> R accept(Type.Visitor<R,S> v, S s) { return v.visitType(this, s); }
215
216    /** Define a type given its tag, type symbol, and type annotations
217     */
218
219    public Type(TypeSymbol tsym, TypeMetadata metadata) {
220        Assert.checkNonNull(metadata);
221        this.tsym = tsym;
222        this.metadata = metadata;
223    }
224
225    /** An abstract class for mappings from types to types
226     */
227    public static abstract class TypeMapping<S> extends Types.MapVisitor<S> implements Function<Type, Type> {
228
229        @Override
230        public Type apply(Type type) {
231            return visit(type);
232        }
233
234        List<Type> visit(List<Type> ts, S s) {
235            return ts.map(t -> visit(t, s));
236        }
237
238        @Override
239        public Type visitClassType(ClassType t, S s) {
240            Type outer = t.getEnclosingType();
241            Type outer1 = visit(outer, s);
242            List<Type> typarams = t.getTypeArguments();
243            List<Type> typarams1 = visit(typarams, s);
244            if (outer1 == outer && typarams1 == typarams) return t;
245            else return new ClassType(outer1, typarams1, t.tsym, t.metadata) {
246                @Override
247                protected boolean needsStripping() {
248                    return true;
249                }
250            };
251        }
252
253        @Override
254        public Type visitWildcardType(WildcardType wt, S s) {
255            Type t = wt.type;
256            if (t != null)
257                t = visit(t, s);
258            if (t == wt.type)
259                return wt;
260            else
261                return new WildcardType(t, wt.kind, wt.tsym, wt.bound, wt.metadata) {
262                    @Override
263                    protected boolean needsStripping() {
264                        return true;
265                    }
266                };
267        }
268
269        @Override
270        public Type visitArrayType(ArrayType t, S s) {
271            Type elemtype = t.elemtype;
272            Type elemtype1 = visit(elemtype, s);
273            if (elemtype1 == elemtype) return t;
274            else return new ArrayType(elemtype1, t.tsym, t.metadata) {
275                @Override
276                protected boolean needsStripping() {
277                    return true;
278                }
279            };
280        }
281
282        @Override
283        public Type visitMethodType(MethodType t, S s) {
284            List<Type> argtypes = t.argtypes;
285            Type restype = t.restype;
286            List<Type> thrown = t.thrown;
287            List<Type> argtypes1 = visit(argtypes, s);
288            Type restype1 = visit(restype, s);
289            List<Type> thrown1 = visit(thrown, s);
290            if (argtypes1 == argtypes &&
291                restype1 == restype &&
292                thrown1 == thrown) return t;
293            else return new MethodType(argtypes1, restype1, thrown1, t.tsym) {
294                @Override
295                protected boolean needsStripping() {
296                    return true;
297                }
298            };
299        }
300
301        @Override
302        public Type visitCapturedType(CapturedType t, S s) {
303            return visitTypeVar(t, s);
304        }
305
306        @Override
307        public Type visitForAll(ForAll t, S s) {
308            return visit(t.qtype, s);
309        }
310    }
311
312    /** map a type function over all immediate descendants of this type
313     */
314    public <Z> Type map(TypeMapping<Z> mapping, Z arg) {
315        return mapping.visit(this, arg);
316    }
317
318    /** map a type function over all immediate descendants of this type (no arg version)
319     */
320    public <Z> Type map(TypeMapping<Z> mapping) {
321        return mapping.visit(this, null);
322    }
323
324    /** Define a constant type, of the same kind as this type
325     *  and with given constant value
326     */
327    public Type constType(Object constValue) {
328        throw new AssertionError();
329    }
330
331    /**
332     * If this is a constant type, return its underlying type.
333     * Otherwise, return the type itself.
334     */
335    public Type baseType() {
336        return this;
337    }
338
339    /**
340     * Returns the original version of this type, before metadata were added. This routine is meant
341     * for internal use only (i.e. {@link Type#equalsIgnoreMetadata(Type)}, {@link Type#stripMetadata});
342     * it should not be used outside this class.
343     */
344    protected Type typeNoMetadata() {
345        return metadata == TypeMetadata.EMPTY ? this : baseType();
346    }
347
348    /**
349     * Create a new copy of this type but with the specified TypeMetadata.
350     */
351    public abstract Type cloneWithMetadata(TypeMetadata metadata);
352
353    /**
354     * Does this type require annotation stripping for API clients?
355     */
356    protected boolean needsStripping() {
357        return false;
358    }
359
360    /**
361     * Strip all metadata associated with this type - this could return a new clone of the type.
362     * This routine is only used to present the correct annotated types back to the users when types
363     * are accessed through compiler APIs; it should not be used anywhere in the compiler internals
364     * as doing so might result in performance penalties.
365     */
366    public Type stripMetadataIfNeeded() {
367        return needsStripping() ?
368                accept(stripMetadata, null) :
369                this;
370    }
371
372    public Type stripMetadata() {
373        return accept(stripMetadata, null);
374    }
375    //where
376        private final static TypeMapping<Void> stripMetadata = new TypeMapping<Void>() {
377            @Override
378            public Type visitClassType(ClassType t, Void aVoid) {
379                return super.visitClassType((ClassType)t.typeNoMetadata(), aVoid);
380            }
381
382            @Override
383            public Type visitArrayType(ArrayType t, Void aVoid) {
384                return super.visitArrayType((ArrayType)t.typeNoMetadata(), aVoid);
385            }
386
387            @Override
388            public Type visitTypeVar(TypeVar t, Void aVoid) {
389                return super.visitTypeVar((TypeVar)t.typeNoMetadata(), aVoid);
390            }
391
392            @Override
393            public Type visitWildcardType(WildcardType wt, Void aVoid) {
394                return super.visitWildcardType((WildcardType)wt.typeNoMetadata(), aVoid);
395            }
396        };
397
398    public Type annotatedType(final List<Attribute.TypeCompound> annos) {
399        final Entry annoMetadata = new TypeMetadata.Annotations(annos);
400        return cloneWithMetadata(metadata.combine(annoMetadata));
401    }
402
403    public boolean isAnnotated() {
404        final TypeMetadata.Annotations metadata =
405            (TypeMetadata.Annotations)getMetadataOfKind(Entry.Kind.ANNOTATIONS);
406
407        return null != metadata && !metadata.getAnnotations().isEmpty();
408    }
409
410    @Override @DefinedBy(Api.LANGUAGE_MODEL)
411    public List<Attribute.TypeCompound> getAnnotationMirrors() {
412        final TypeMetadata.Annotations metadata =
413            (TypeMetadata.Annotations)getMetadataOfKind(Entry.Kind.ANNOTATIONS);
414
415        return metadata == null ? List.nil() : metadata.getAnnotations();
416    }
417
418
419    @Override @DefinedBy(Api.LANGUAGE_MODEL)
420    public <A extends Annotation> A getAnnotation(Class<A> annotationType) {
421        return null;
422    }
423
424
425    @Override @DefinedBy(Api.LANGUAGE_MODEL)
426    public <A extends Annotation> A[] getAnnotationsByType(Class<A> annotationType) {
427        @SuppressWarnings("unchecked")
428        A[] tmp = (A[]) java.lang.reflect.Array.newInstance(annotationType, 0);
429        return tmp;
430    }
431
432    /** Return the base types of a list of types.
433     */
434    public static List<Type> baseTypes(List<Type> ts) {
435        if (ts.nonEmpty()) {
436            Type t = ts.head.baseType();
437            List<Type> baseTypes = baseTypes(ts.tail);
438            if (t != ts.head || baseTypes != ts.tail)
439                return baseTypes.prepend(t);
440        }
441        return ts;
442    }
443
444    protected void appendAnnotationsString(StringBuilder sb,
445                                         boolean prefix) {
446        if (isAnnotated()) {
447            if (prefix) {
448                sb.append(" ");
449            }
450            sb.append(getAnnotationMirrors());
451            sb.append(" ");
452        }
453    }
454
455    protected void appendAnnotationsString(StringBuilder sb) {
456        appendAnnotationsString(sb, false);
457    }
458
459    /** The Java source which this type represents.
460     */
461    @DefinedBy(Api.LANGUAGE_MODEL)
462    public String toString() {
463        StringBuilder sb = new StringBuilder();
464        appendAnnotationsString(sb);
465        if (tsym == null || tsym.name == null) {
466            sb.append("<none>");
467        } else {
468            sb.append(tsym.name);
469        }
470        if (moreInfo && hasTag(TYPEVAR)) {
471            sb.append(hashCode());
472        }
473        return sb.toString();
474    }
475
476    /**
477     * The Java source which this type list represents.  A List is
478     * represented as a comma-spearated listing of the elements in
479     * that list.
480     */
481    public static String toString(List<Type> ts) {
482        if (ts.isEmpty()) {
483            return "";
484        } else {
485            StringBuilder buf = new StringBuilder();
486            buf.append(ts.head.toString());
487            for (List<Type> l = ts.tail; l.nonEmpty(); l = l.tail)
488                buf.append(",").append(l.head.toString());
489            return buf.toString();
490        }
491    }
492
493    /**
494     * The constant value of this type, converted to String
495     */
496    public String stringValue() {
497        Object cv = Assert.checkNonNull(constValue());
498        return cv.toString();
499    }
500
501    /**
502     * Override this method with care. For most Type instances this should behave as ==.
503     */
504    @Override @DefinedBy(Api.LANGUAGE_MODEL)
505    public boolean equals(Object t) {
506        return this == t;
507    }
508
509    public boolean equalsIgnoreMetadata(Type t) {
510        return typeNoMetadata().equals(t.typeNoMetadata());
511    }
512
513    @Override @DefinedBy(Api.LANGUAGE_MODEL)
514    public int hashCode() {
515        return super.hashCode();
516    }
517
518    public String argtypes(boolean varargs) {
519        List<Type> args = getParameterTypes();
520        if (!varargs) return args.toString();
521        StringBuilder buf = new StringBuilder();
522        while (args.tail.nonEmpty()) {
523            buf.append(args.head);
524            args = args.tail;
525            buf.append(',');
526        }
527        if (args.head.hasTag(ARRAY)) {
528            buf.append(((ArrayType)args.head).elemtype);
529            if (args.head.getAnnotationMirrors().nonEmpty()) {
530                buf.append(args.head.getAnnotationMirrors());
531            }
532            buf.append("...");
533        } else {
534            buf.append(args.head);
535        }
536        return buf.toString();
537    }
538
539    /** Access methods.
540     */
541    public List<Type>        getTypeArguments()  { return List.nil(); }
542    public Type              getEnclosingType()  { return null; }
543    public List<Type>        getParameterTypes() { return List.nil(); }
544    public Type              getReturnType()     { return null; }
545    public Type              getReceiverType()   { return null; }
546    public List<Type>        getThrownTypes()    { return List.nil(); }
547    public Type              getUpperBound()     { return null; }
548    public Type              getLowerBound()     { return null; }
549
550    /** Navigation methods, these will work for classes, type variables,
551     *  foralls, but will return null for arrays and methods.
552     */
553
554   /** Return all parameters of this type and all its outer types in order
555    *  outer (first) to inner (last).
556    */
557    public List<Type> allparams() { return List.nil(); }
558
559    /** Does this type contain "error" elements?
560     */
561    public boolean isErroneous() {
562        return false;
563    }
564
565    public static boolean isErroneous(List<Type> ts) {
566        for (List<Type> l = ts; l.nonEmpty(); l = l.tail)
567            if (l.head.isErroneous()) return true;
568        return false;
569    }
570
571    /** Is this type parameterized?
572     *  A class type is parameterized if it has some parameters.
573     *  An array type is parameterized if its element type is parameterized.
574     *  All other types are not parameterized.
575     */
576    public boolean isParameterized() {
577        return false;
578    }
579
580    /** Is this type a raw type?
581     *  A class type is a raw type if it misses some of its parameters.
582     *  An array type is a raw type if its element type is raw.
583     *  All other types are not raw.
584     *  Type validation will ensure that the only raw types
585     *  in a program are types that miss all their type variables.
586     */
587    public boolean isRaw() {
588        return false;
589    }
590
591    /**
592     * A compound type is a special class type whose supertypes are used to store a list
593     * of component types. There are two kinds of compound types: (i) intersection types
594     * {@see IntersectionClassType} and (ii) union types {@see UnionClassType}.
595     */
596    public boolean isCompound() {
597        return false;
598    }
599
600    public boolean isIntersection() {
601        return false;
602    }
603
604    public boolean isUnion() {
605        return false;
606    }
607
608    public boolean isInterface() {
609        return (tsym.flags() & INTERFACE) != 0;
610    }
611
612    public boolean isFinal() {
613        return (tsym.flags() & FINAL) != 0;
614    }
615
616    /**
617     * Does this type contain occurrences of type t?
618     */
619    public boolean contains(Type t) {
620        return t.equalsIgnoreMetadata(this);
621    }
622
623    public static boolean contains(List<Type> ts, Type t) {
624        for (List<Type> l = ts;
625             l.tail != null /*inlined: l.nonEmpty()*/;
626             l = l.tail)
627            if (l.head.contains(t)) return true;
628        return false;
629    }
630
631    /** Does this type contain an occurrence of some type in 'ts'?
632     */
633    public boolean containsAny(List<Type> ts) {
634        for (Type t : ts)
635            if (this.contains(t)) return true;
636        return false;
637    }
638
639    public static boolean containsAny(List<Type> ts1, List<Type> ts2) {
640        for (Type t : ts1)
641            if (t.containsAny(ts2)) return true;
642        return false;
643    }
644
645    public static List<Type> filter(List<Type> ts, Filter<Type> tf) {
646        ListBuffer<Type> buf = new ListBuffer<>();
647        for (Type t : ts) {
648            if (tf.accepts(t)) {
649                buf.append(t);
650            }
651        }
652        return buf.toList();
653    }
654
655    public boolean isSuperBound() { return false; }
656    public boolean isExtendsBound() { return false; }
657    public boolean isUnbound() { return false; }
658    public Type withTypeVar(Type t) { return this; }
659
660    /** The underlying method type of this type.
661     */
662    public MethodType asMethodType() { throw new AssertionError(); }
663
664    /** Complete loading all classes in this type.
665     */
666    public void complete() {}
667
668    public TypeSymbol asElement() {
669        return tsym;
670    }
671
672    @Override @DefinedBy(Api.LANGUAGE_MODEL)
673    public TypeKind getKind() {
674        return TypeKind.OTHER;
675    }
676
677    @Override @DefinedBy(Api.LANGUAGE_MODEL)
678    public <R, P> R accept(TypeVisitor<R, P> v, P p) {
679        throw new AssertionError();
680    }
681
682    public static class JCPrimitiveType extends Type
683            implements javax.lang.model.type.PrimitiveType {
684
685        TypeTag tag;
686
687        public JCPrimitiveType(TypeTag tag, TypeSymbol tsym) {
688            this(tag, tsym, TypeMetadata.EMPTY);
689        }
690
691        private JCPrimitiveType(TypeTag tag, TypeSymbol tsym, TypeMetadata metadata) {
692            super(tsym, metadata);
693            this.tag = tag;
694            Assert.check(tag.isPrimitive);
695        }
696
697        @Override
698        public JCPrimitiveType cloneWithMetadata(TypeMetadata md) {
699            return new JCPrimitiveType(tag, tsym, md) {
700                @Override
701                public Type baseType() { return JCPrimitiveType.this.baseType(); }
702            };
703        }
704
705        @Override
706        public boolean isNumeric() {
707            return tag != BOOLEAN;
708        }
709
710        @Override
711        public boolean isIntegral() {
712            switch (tag) {
713                case CHAR:
714                case BYTE:
715                case SHORT:
716                case INT:
717                case LONG:
718                    return true;
719                default:
720                    return false;
721            }
722        }
723
724        @Override
725        public boolean isPrimitive() {
726            return true;
727        }
728
729        @Override
730        public TypeTag getTag() {
731            return tag;
732        }
733
734        @Override
735        public boolean isPrimitiveOrVoid() {
736            return true;
737        }
738
739        /** Define a constant type, of the same kind as this type
740         *  and with given constant value
741         */
742        @Override
743        public Type constType(Object constValue) {
744            final Object value = constValue;
745            return new JCPrimitiveType(tag, tsym, metadata) {
746                    @Override
747                    public Object constValue() {
748                        return value;
749                    }
750                    @Override
751                    public Type baseType() {
752                        return tsym.type;
753                    }
754                };
755        }
756
757        /**
758         * The constant value of this type, converted to String
759         */
760        @Override
761        public String stringValue() {
762            Object cv = Assert.checkNonNull(constValue());
763            if (tag == BOOLEAN) {
764                return ((Integer) cv).intValue() == 0 ? "false" : "true";
765            }
766            else if (tag == CHAR) {
767                return String.valueOf((char) ((Integer) cv).intValue());
768            }
769            else {
770                return cv.toString();
771            }
772        }
773
774        /** Is this a constant type whose value is false?
775         */
776        @Override
777        public boolean isFalse() {
778            return
779                tag == BOOLEAN &&
780                constValue() != null &&
781                ((Integer)constValue()).intValue() == 0;
782        }
783
784        /** Is this a constant type whose value is true?
785         */
786        @Override
787        public boolean isTrue() {
788            return
789                tag == BOOLEAN &&
790                constValue() != null &&
791                ((Integer)constValue()).intValue() != 0;
792        }
793
794        @Override @DefinedBy(Api.LANGUAGE_MODEL)
795        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
796            return v.visitPrimitive(this, p);
797        }
798
799        @Override @DefinedBy(Api.LANGUAGE_MODEL)
800        public TypeKind getKind() {
801            switch (tag) {
802                case BYTE:      return TypeKind.BYTE;
803                case CHAR:      return TypeKind.CHAR;
804                case SHORT:     return TypeKind.SHORT;
805                case INT:       return TypeKind.INT;
806                case LONG:      return TypeKind.LONG;
807                case FLOAT:     return TypeKind.FLOAT;
808                case DOUBLE:    return TypeKind.DOUBLE;
809                case BOOLEAN:   return TypeKind.BOOLEAN;
810            }
811            throw new AssertionError();
812        }
813
814    }
815
816    public static class WildcardType extends Type
817            implements javax.lang.model.type.WildcardType {
818
819        public Type type;
820        public BoundKind kind;
821        public TypeVar bound;
822
823        @Override
824        public <R,S> R accept(Type.Visitor<R,S> v, S s) {
825            return v.visitWildcardType(this, s);
826        }
827
828        public WildcardType(Type type, BoundKind kind, TypeSymbol tsym) {
829            this(type, kind, tsym, null, TypeMetadata.EMPTY);
830        }
831
832        public WildcardType(Type type, BoundKind kind, TypeSymbol tsym,
833                            TypeMetadata metadata) {
834            this(type, kind, tsym, null, metadata);
835        }
836
837        public WildcardType(Type type, BoundKind kind, TypeSymbol tsym,
838                            TypeVar bound) {
839            this(type, kind, tsym, bound, TypeMetadata.EMPTY);
840        }
841
842        public WildcardType(Type type, BoundKind kind, TypeSymbol tsym,
843                            TypeVar bound, TypeMetadata metadata) {
844            super(tsym, metadata);
845            this.type = Assert.checkNonNull(type);
846            this.kind = kind;
847            this.bound = bound;
848        }
849
850        @Override
851        public WildcardType cloneWithMetadata(TypeMetadata md) {
852            return new WildcardType(type, kind, tsym, bound, md) {
853                @Override
854                public Type baseType() { return WildcardType.this.baseType(); }
855            };
856        }
857
858        @Override
859        public TypeTag getTag() {
860            return WILDCARD;
861        }
862
863        @Override
864        public boolean contains(Type t) {
865            return kind != UNBOUND && type.contains(t);
866        }
867
868        public boolean isSuperBound() {
869            return kind == SUPER ||
870                kind == UNBOUND;
871        }
872        public boolean isExtendsBound() {
873            return kind == EXTENDS ||
874                kind == UNBOUND;
875        }
876        public boolean isUnbound() {
877            return kind == UNBOUND;
878        }
879
880        @Override
881        public boolean isReference() {
882            return true;
883        }
884
885        @Override
886        public boolean isNullOrReference() {
887            return true;
888        }
889
890        @Override
891        public Type withTypeVar(Type t) {
892            //-System.err.println(this+".withTypeVar("+t+");");//DEBUG
893            if (bound == t)
894                return this;
895            bound = (TypeVar)t;
896            return this;
897        }
898
899        boolean isPrintingBound = false;
900        @DefinedBy(Api.LANGUAGE_MODEL)
901        public String toString() {
902            StringBuilder s = new StringBuilder();
903            appendAnnotationsString(s);
904            s.append(kind.toString());
905            if (kind != UNBOUND)
906                s.append(type);
907            if (moreInfo && bound != null && !isPrintingBound)
908                try {
909                    isPrintingBound = true;
910                    s.append("{:").append(bound.bound).append(":}");
911                } finally {
912                    isPrintingBound = false;
913                }
914            return s.toString();
915        }
916
917        @DefinedBy(Api.LANGUAGE_MODEL)
918        public Type getExtendsBound() {
919            if (kind == EXTENDS)
920                return type;
921            else
922                return null;
923        }
924
925        @DefinedBy(Api.LANGUAGE_MODEL)
926        public Type getSuperBound() {
927            if (kind == SUPER)
928                return type;
929            else
930                return null;
931        }
932
933        @DefinedBy(Api.LANGUAGE_MODEL)
934        public TypeKind getKind() {
935            return TypeKind.WILDCARD;
936        }
937
938        @DefinedBy(Api.LANGUAGE_MODEL)
939        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
940            return v.visitWildcard(this, p);
941        }
942    }
943
944    public static class ClassType extends Type implements DeclaredType {
945
946        /** The enclosing type of this type. If this is the type of an inner
947         *  class, outer_field refers to the type of its enclosing
948         *  instance class, in all other cases it refers to noType.
949         */
950        private Type outer_field;
951
952        /** The type parameters of this type (to be set once class is loaded).
953         */
954        public List<Type> typarams_field;
955
956        /** A cache variable for the type parameters of this type,
957         *  appended to all parameters of its enclosing class.
958         *  @see #allparams
959         */
960        public List<Type> allparams_field;
961
962        /** The supertype of this class (to be set once class is loaded).
963         */
964        public Type supertype_field;
965
966        /** The interfaces of this class (to be set once class is loaded).
967         */
968        public List<Type> interfaces_field;
969
970        /** All the interfaces of this class, including missing ones.
971         */
972        public List<Type> all_interfaces_field;
973
974        public ClassType(Type outer, List<Type> typarams, TypeSymbol tsym) {
975            this(outer, typarams, tsym, TypeMetadata.EMPTY);
976        }
977
978        public ClassType(Type outer, List<Type> typarams, TypeSymbol tsym,
979                         TypeMetadata metadata) {
980            super(tsym, metadata);
981            this.outer_field = outer;
982            this.typarams_field = typarams;
983            this.allparams_field = null;
984            this.supertype_field = null;
985            this.interfaces_field = null;
986        }
987
988        @Override
989        public ClassType cloneWithMetadata(TypeMetadata md) {
990            return new ClassType(outer_field, typarams_field, tsym, md) {
991                @Override
992                public Type baseType() { return ClassType.this.baseType(); }
993            };
994        }
995
996        @Override
997        public TypeTag getTag() {
998            return CLASS;
999        }
1000
1001        @Override
1002        public <R,S> R accept(Type.Visitor<R,S> v, S s) {
1003            return v.visitClassType(this, s);
1004        }
1005
1006        public Type constType(Object constValue) {
1007            final Object value = constValue;
1008            return new ClassType(getEnclosingType(), typarams_field, tsym, metadata) {
1009                    @Override
1010                    public Object constValue() {
1011                        return value;
1012                    }
1013                    @Override
1014                    public Type baseType() {
1015                        return tsym.type;
1016                    }
1017                };
1018        }
1019
1020        /** The Java source which this type represents.
1021         */
1022        @DefinedBy(Api.LANGUAGE_MODEL)
1023        public String toString() {
1024            StringBuilder buf = new StringBuilder();
1025            if (getEnclosingType().hasTag(CLASS) && tsym.owner.kind == TYP) {
1026                buf.append(getEnclosingType().toString());
1027                buf.append(".");
1028                appendAnnotationsString(buf);
1029                buf.append(className(tsym, false));
1030            } else {
1031                appendAnnotationsString(buf);
1032                buf.append(className(tsym, true));
1033            }
1034
1035            if (getTypeArguments().nonEmpty()) {
1036                buf.append('<');
1037                buf.append(getTypeArguments().toString());
1038                buf.append(">");
1039            }
1040            return buf.toString();
1041        }
1042//where
1043            private String className(Symbol sym, boolean longform) {
1044                if (sym.name.isEmpty() && (sym.flags() & COMPOUND) != 0) {
1045                    StringBuilder s = new StringBuilder(supertype_field.toString());
1046                    for (List<Type> is=interfaces_field; is.nonEmpty(); is = is.tail) {
1047                        s.append("&");
1048                        s.append(is.head.toString());
1049                    }
1050                    return s.toString();
1051                } else if (sym.name.isEmpty()) {
1052                    String s;
1053                    ClassType norm = (ClassType) tsym.type;
1054                    if (norm == null) {
1055                        s = Log.getLocalizedString("anonymous.class", (Object)null);
1056                    } else if (norm.interfaces_field != null && norm.interfaces_field.nonEmpty()) {
1057                        s = Log.getLocalizedString("anonymous.class",
1058                                                   norm.interfaces_field.head);
1059                    } else {
1060                        s = Log.getLocalizedString("anonymous.class",
1061                                                   norm.supertype_field);
1062                    }
1063                    if (moreInfo)
1064                        s += String.valueOf(sym.hashCode());
1065                    return s;
1066                } else if (longform) {
1067                    return sym.getQualifiedName().toString();
1068                } else {
1069                    return sym.name.toString();
1070                }
1071            }
1072
1073        @DefinedBy(Api.LANGUAGE_MODEL)
1074        public List<Type> getTypeArguments() {
1075            if (typarams_field == null) {
1076                complete();
1077                if (typarams_field == null)
1078                    typarams_field = List.nil();
1079            }
1080            return typarams_field;
1081        }
1082
1083        public boolean hasErasedSupertypes() {
1084            return isRaw();
1085        }
1086
1087        @DefinedBy(Api.LANGUAGE_MODEL)
1088        public Type getEnclosingType() {
1089            return outer_field;
1090        }
1091
1092        public void setEnclosingType(Type outer) {
1093            outer_field = outer;
1094        }
1095
1096        public List<Type> allparams() {
1097            if (allparams_field == null) {
1098                allparams_field = getTypeArguments().prependList(getEnclosingType().allparams());
1099            }
1100            return allparams_field;
1101        }
1102
1103        public boolean isErroneous() {
1104            return
1105                getEnclosingType().isErroneous() ||
1106                isErroneous(getTypeArguments()) ||
1107                this != tsym.type && tsym.type.isErroneous();
1108        }
1109
1110        public boolean isParameterized() {
1111            return allparams().tail != null;
1112            // optimization, was: allparams().nonEmpty();
1113        }
1114
1115        @Override
1116        public boolean isReference() {
1117            return true;
1118        }
1119
1120        @Override
1121        public boolean isNullOrReference() {
1122            return true;
1123        }
1124
1125        /** A cache for the rank. */
1126        int rank_field = -1;
1127
1128        /** A class type is raw if it misses some
1129         *  of its type parameter sections.
1130         *  After validation, this is equivalent to:
1131         *  {@code allparams.isEmpty() && tsym.type.allparams.nonEmpty(); }
1132         */
1133        public boolean isRaw() {
1134            return
1135                this != tsym.type && // necessary, but not sufficient condition
1136                tsym.type.allparams().nonEmpty() &&
1137                allparams().isEmpty();
1138        }
1139
1140        public boolean contains(Type elem) {
1141            return
1142                elem.equalsIgnoreMetadata(this)
1143                || (isParameterized()
1144                    && (getEnclosingType().contains(elem) || contains(getTypeArguments(), elem)))
1145                || (isCompound()
1146                    && (supertype_field.contains(elem) || contains(interfaces_field, elem)));
1147        }
1148
1149        public void complete() {
1150            tsym.complete();
1151        }
1152
1153        @DefinedBy(Api.LANGUAGE_MODEL)
1154        public TypeKind getKind() {
1155            return TypeKind.DECLARED;
1156        }
1157
1158        @DefinedBy(Api.LANGUAGE_MODEL)
1159        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
1160            return v.visitDeclared(this, p);
1161        }
1162    }
1163
1164    public static class ErasedClassType extends ClassType {
1165        public ErasedClassType(Type outer, TypeSymbol tsym,
1166                               TypeMetadata metadata) {
1167            super(outer, List.<Type>nil(), tsym, metadata);
1168        }
1169
1170        @Override
1171        public boolean hasErasedSupertypes() {
1172            return true;
1173        }
1174    }
1175
1176    // a clone of a ClassType that knows about the alternatives of a union type.
1177    public static class UnionClassType extends ClassType implements UnionType {
1178        final List<? extends Type> alternatives_field;
1179
1180        public UnionClassType(ClassType ct, List<? extends Type> alternatives) {
1181            // Presently no way to refer to this type directly, so we
1182            // cannot put annotations directly on it.
1183            super(ct.outer_field, ct.typarams_field, ct.tsym);
1184            allparams_field = ct.allparams_field;
1185            supertype_field = ct.supertype_field;
1186            interfaces_field = ct.interfaces_field;
1187            all_interfaces_field = ct.interfaces_field;
1188            alternatives_field = alternatives;
1189        }
1190
1191        @Override
1192        public UnionClassType cloneWithMetadata(TypeMetadata md) {
1193            throw new AssertionError("Cannot add metadata to a union type");
1194        }
1195
1196        public Type getLub() {
1197            return tsym.type;
1198        }
1199
1200        @DefinedBy(Api.LANGUAGE_MODEL)
1201        public java.util.List<? extends TypeMirror> getAlternatives() {
1202            return Collections.unmodifiableList(alternatives_field);
1203        }
1204
1205        @Override
1206        public boolean isUnion() {
1207            return true;
1208        }
1209
1210        @Override
1211        public boolean isCompound() {
1212            return getLub().isCompound();
1213        }
1214
1215        @Override @DefinedBy(Api.LANGUAGE_MODEL)
1216        public TypeKind getKind() {
1217            return TypeKind.UNION;
1218        }
1219
1220        @Override @DefinedBy(Api.LANGUAGE_MODEL)
1221        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
1222            return v.visitUnion(this, p);
1223        }
1224
1225        public Iterable<? extends Type> getAlternativeTypes() {
1226            return alternatives_field;
1227        }
1228    }
1229
1230    // a clone of a ClassType that knows about the bounds of an intersection type.
1231    public static class IntersectionClassType extends ClassType implements IntersectionType {
1232
1233        public boolean allInterfaces;
1234
1235        public IntersectionClassType(List<Type> bounds, ClassSymbol csym, boolean allInterfaces) {
1236            // Presently no way to refer to this type directly, so we
1237            // cannot put annotations directly on it.
1238            super(Type.noType, List.<Type>nil(), csym);
1239            this.allInterfaces = allInterfaces;
1240            Assert.check((csym.flags() & COMPOUND) != 0);
1241            supertype_field = bounds.head;
1242            interfaces_field = bounds.tail;
1243            Assert.check(!supertype_field.tsym.isCompleted() ||
1244                    !supertype_field.isInterface(), supertype_field);
1245        }
1246
1247        @Override
1248        public IntersectionClassType cloneWithMetadata(TypeMetadata md) {
1249            throw new AssertionError("Cannot add metadata to an intersection type");
1250        }
1251
1252        @DefinedBy(Api.LANGUAGE_MODEL)
1253        public java.util.List<? extends TypeMirror> getBounds() {
1254            return Collections.unmodifiableList(getExplicitComponents());
1255        }
1256
1257        @Override
1258        public boolean isCompound() {
1259            return true;
1260        }
1261
1262        public List<Type> getComponents() {
1263            return interfaces_field.prepend(supertype_field);
1264        }
1265
1266        @Override
1267        public boolean isIntersection() {
1268            return true;
1269        }
1270
1271        public List<Type> getExplicitComponents() {
1272            return allInterfaces ?
1273                    interfaces_field :
1274                    getComponents();
1275        }
1276
1277        @Override @DefinedBy(Api.LANGUAGE_MODEL)
1278        public TypeKind getKind() {
1279            return TypeKind.INTERSECTION;
1280        }
1281
1282        @Override @DefinedBy(Api.LANGUAGE_MODEL)
1283        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
1284            return v.visitIntersection(this, p);
1285        }
1286    }
1287
1288    public static class ArrayType extends Type
1289            implements javax.lang.model.type.ArrayType {
1290
1291        public Type elemtype;
1292
1293        public ArrayType(Type elemtype, TypeSymbol arrayClass) {
1294            this(elemtype, arrayClass, TypeMetadata.EMPTY);
1295        }
1296
1297        public ArrayType(Type elemtype, TypeSymbol arrayClass,
1298                         TypeMetadata metadata) {
1299            super(arrayClass, metadata);
1300            this.elemtype = elemtype;
1301        }
1302
1303        public ArrayType(ArrayType that) {
1304            //note: type metadata is deliberately shared here, as we want side-effects from annotation
1305            //processing to flow from original array to the cloned array.
1306            this(that.elemtype, that.tsym, that.getMetadata());
1307        }
1308
1309        @Override
1310        public ArrayType cloneWithMetadata(TypeMetadata md) {
1311            return new ArrayType(elemtype, tsym, md) {
1312                @Override
1313                public Type baseType() { return ArrayType.this.baseType(); }
1314            };
1315        }
1316
1317        @Override
1318        public TypeTag getTag() {
1319            return ARRAY;
1320        }
1321
1322        public <R,S> R accept(Type.Visitor<R,S> v, S s) {
1323            return v.visitArrayType(this, s);
1324        }
1325
1326        @DefinedBy(Api.LANGUAGE_MODEL)
1327        public String toString() {
1328            StringBuilder sb = new StringBuilder();
1329
1330            // First append root component type
1331            Type t = elemtype;
1332            while (t.getKind() == TypeKind.ARRAY)
1333                t = ((ArrayType) t).getComponentType();
1334            sb.append(t);
1335
1336            // then append @Anno[] @Anno[] ... @Anno[]
1337            t = this;
1338            do {
1339                t.appendAnnotationsString(sb, true);
1340                sb.append("[]");
1341                t = ((ArrayType) t).getComponentType();
1342            } while (t.getKind() == TypeKind.ARRAY);
1343
1344            return sb.toString();
1345        }
1346
1347        @Override @DefinedBy(Api.LANGUAGE_MODEL)
1348        public boolean equals(Object obj) {
1349            if (obj instanceof ArrayType) {
1350                ArrayType that = (ArrayType)obj;
1351                return this == that ||
1352                        elemtype.equals(that.elemtype);
1353            }
1354
1355            return false;
1356        }
1357
1358        @DefinedBy(Api.LANGUAGE_MODEL)
1359        public int hashCode() {
1360            return (ARRAY.ordinal() << 5) + elemtype.hashCode();
1361        }
1362
1363        public boolean isVarargs() {
1364            return false;
1365        }
1366
1367        public List<Type> allparams() { return elemtype.allparams(); }
1368
1369        public boolean isErroneous() {
1370            return elemtype.isErroneous();
1371        }
1372
1373        public boolean isParameterized() {
1374            return elemtype.isParameterized();
1375        }
1376
1377        @Override
1378        public boolean isReference() {
1379            return true;
1380        }
1381
1382        @Override
1383        public boolean isNullOrReference() {
1384            return true;
1385        }
1386
1387        public boolean isRaw() {
1388            return elemtype.isRaw();
1389        }
1390
1391        public ArrayType makeVarargs() {
1392            return new ArrayType(elemtype, tsym, metadata) {
1393                @Override
1394                public boolean isVarargs() {
1395                    return true;
1396                }
1397            };
1398        }
1399
1400        public boolean contains(Type elem) {
1401            return elem.equalsIgnoreMetadata(this) || elemtype.contains(elem);
1402        }
1403
1404        public void complete() {
1405            elemtype.complete();
1406        }
1407
1408        @DefinedBy(Api.LANGUAGE_MODEL)
1409        public Type getComponentType() {
1410            return elemtype;
1411        }
1412
1413        @DefinedBy(Api.LANGUAGE_MODEL)
1414        public TypeKind getKind() {
1415            return TypeKind.ARRAY;
1416        }
1417
1418        @DefinedBy(Api.LANGUAGE_MODEL)
1419        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
1420            return v.visitArray(this, p);
1421        }
1422    }
1423
1424    public static class MethodType extends Type implements ExecutableType {
1425
1426        public List<Type> argtypes;
1427        public Type restype;
1428        public List<Type> thrown;
1429
1430        /** The type annotations on the method receiver.
1431         */
1432        public Type recvtype;
1433
1434        public MethodType(List<Type> argtypes,
1435                          Type restype,
1436                          List<Type> thrown,
1437                          TypeSymbol methodClass) {
1438            // Presently no way to refer to a method type directly, so
1439            // we cannot put type annotations on it.
1440            super(methodClass, TypeMetadata.EMPTY);
1441            this.argtypes = argtypes;
1442            this.restype = restype;
1443            this.thrown = thrown;
1444        }
1445
1446        @Override
1447        public MethodType cloneWithMetadata(TypeMetadata md) {
1448            throw new AssertionError("Cannot add metadata to a method type");
1449        }
1450
1451        @Override
1452        public TypeTag getTag() {
1453            return METHOD;
1454        }
1455
1456        public <R,S> R accept(Type.Visitor<R,S> v, S s) {
1457            return v.visitMethodType(this, s);
1458        }
1459
1460        /** The Java source which this type represents.
1461         *
1462         *  XXX 06/09/99 iris This isn't correct Java syntax, but it probably
1463         *  should be.
1464         */
1465        @DefinedBy(Api.LANGUAGE_MODEL)
1466        public String toString() {
1467            StringBuilder sb = new StringBuilder();
1468            appendAnnotationsString(sb);
1469            sb.append('(');
1470            sb.append(argtypes);
1471            sb.append(')');
1472            sb.append(restype);
1473            return sb.toString();
1474        }
1475
1476        @DefinedBy(Api.LANGUAGE_MODEL)
1477        public List<Type>        getParameterTypes() { return argtypes; }
1478        @DefinedBy(Api.LANGUAGE_MODEL)
1479        public Type              getReturnType()     { return restype; }
1480        @DefinedBy(Api.LANGUAGE_MODEL)
1481        public Type              getReceiverType()   { return recvtype; }
1482        @DefinedBy(Api.LANGUAGE_MODEL)
1483        public List<Type>        getThrownTypes()    { return thrown; }
1484
1485        public boolean isErroneous() {
1486            return
1487                isErroneous(argtypes) ||
1488                restype != null && restype.isErroneous();
1489        }
1490
1491        public boolean contains(Type elem) {
1492            return elem.equalsIgnoreMetadata(this) || contains(argtypes, elem) || restype.contains(elem) || contains(thrown, elem);
1493        }
1494
1495        public MethodType asMethodType() { return this; }
1496
1497        public void complete() {
1498            for (List<Type> l = argtypes; l.nonEmpty(); l = l.tail)
1499                l.head.complete();
1500            restype.complete();
1501            recvtype.complete();
1502            for (List<Type> l = thrown; l.nonEmpty(); l = l.tail)
1503                l.head.complete();
1504        }
1505
1506        @DefinedBy(Api.LANGUAGE_MODEL)
1507        public List<TypeVar> getTypeVariables() {
1508            return List.nil();
1509        }
1510
1511        public TypeSymbol asElement() {
1512            return null;
1513        }
1514
1515        @DefinedBy(Api.LANGUAGE_MODEL)
1516        public TypeKind getKind() {
1517            return TypeKind.EXECUTABLE;
1518        }
1519
1520        @DefinedBy(Api.LANGUAGE_MODEL)
1521        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
1522            return v.visitExecutable(this, p);
1523        }
1524    }
1525
1526    public static class PackageType extends Type implements NoType {
1527
1528        PackageType(PackageSymbol tsym) {
1529            // Package types cannot be annotated
1530            super(tsym, TypeMetadata.EMPTY);
1531        }
1532
1533        @Override
1534        public PackageType cloneWithMetadata(TypeMetadata md) {
1535            throw new AssertionError("Cannot add metadata to a package type");
1536        }
1537
1538        @Override
1539        public TypeTag getTag() {
1540            return PACKAGE;
1541        }
1542
1543        @Override
1544        public <R,S> R accept(Type.Visitor<R,S> v, S s) {
1545            return v.visitPackageType(this, s);
1546        }
1547
1548        @DefinedBy(Api.LANGUAGE_MODEL)
1549        public String toString() {
1550            return tsym.getQualifiedName().toString();
1551        }
1552
1553        @DefinedBy(Api.LANGUAGE_MODEL)
1554        public TypeKind getKind() {
1555            return TypeKind.PACKAGE;
1556        }
1557
1558        @DefinedBy(Api.LANGUAGE_MODEL)
1559        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
1560            return v.visitNoType(this, p);
1561        }
1562    }
1563
1564    public static class ModuleType extends Type implements NoType {
1565
1566        ModuleType(ModuleSymbol tsym) {
1567            // Module types cannot be annotated
1568            super(tsym, TypeMetadata.EMPTY);
1569        }
1570
1571        @Override
1572        public ModuleType cloneWithMetadata(TypeMetadata md) {
1573            throw new AssertionError("Cannot add metadata to a module type");
1574        }
1575
1576        @Override
1577        public ModuleType annotatedType(List<Attribute.TypeCompound> annos) {
1578            throw new AssertionError("Cannot annotate a module type");
1579        }
1580
1581        @Override
1582        public TypeTag getTag() {
1583            return TypeTag.MODULE;
1584        }
1585
1586        @Override
1587        public <R,S> R accept(Type.Visitor<R,S> v, S s) {
1588            return v.visitModuleType(this, s);
1589        }
1590
1591        @Override
1592        public String toString() {
1593            return tsym.getQualifiedName().toString();
1594        }
1595
1596        @Override
1597        public TypeKind getKind() {
1598            return TypeKind.MODULE;
1599        }
1600
1601        @Override
1602        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
1603            return v.visitNoType(this, p);
1604        }
1605    }
1606
1607    public static class TypeVar extends Type implements TypeVariable {
1608
1609        /** The upper bound of this type variable; set from outside.
1610         *  Must be nonempty once it is set.
1611         *  For a bound, `bound' is the bound type itself.
1612         *  Multiple bounds are expressed as a single class type which has the
1613         *  individual bounds as superclass, respectively interfaces.
1614         *  The class type then has as `tsym' a compiler generated class `c',
1615         *  which has a flag COMPOUND and whose owner is the type variable
1616         *  itself. Furthermore, the erasure_field of the class
1617         *  points to the first class or interface bound.
1618         */
1619        public Type bound = null;
1620
1621        /** The lower bound of this type variable.
1622         *  TypeVars don't normally have a lower bound, so it is normally set
1623         *  to syms.botType.
1624         *  Subtypes, such as CapturedType, may provide a different value.
1625         */
1626        public Type lower;
1627
1628        public TypeVar(Name name, Symbol owner, Type lower) {
1629            super(null, TypeMetadata.EMPTY);
1630            tsym = new TypeVariableSymbol(0, name, this, owner);
1631            this.bound = null;
1632            this.lower = lower;
1633        }
1634
1635        public TypeVar(TypeSymbol tsym, Type bound, Type lower) {
1636            this(tsym, bound, lower, TypeMetadata.EMPTY);
1637        }
1638
1639        public TypeVar(TypeSymbol tsym, Type bound, Type lower,
1640                       TypeMetadata metadata) {
1641            super(tsym, metadata);
1642            this.bound = bound;
1643            this.lower = lower;
1644        }
1645
1646        @Override
1647        public TypeVar cloneWithMetadata(TypeMetadata md) {
1648            return new TypeVar(tsym, bound, lower, md) {
1649                @Override
1650                public Type baseType() { return TypeVar.this.baseType(); }
1651            };
1652        }
1653
1654        @Override
1655        public TypeTag getTag() {
1656            return TYPEVAR;
1657        }
1658
1659        @Override
1660        public <R,S> R accept(Type.Visitor<R,S> v, S s) {
1661            return v.visitTypeVar(this, s);
1662        }
1663
1664        @Override @DefinedBy(Api.LANGUAGE_MODEL)
1665        public Type getUpperBound() {
1666            if ((bound == null || bound.hasTag(NONE)) && this != tsym.type) {
1667                bound = tsym.type.getUpperBound();
1668            }
1669            return bound;
1670        }
1671
1672        int rank_field = -1;
1673
1674        @Override @DefinedBy(Api.LANGUAGE_MODEL)
1675        public Type getLowerBound() {
1676            return lower;
1677        }
1678
1679        @DefinedBy(Api.LANGUAGE_MODEL)
1680        public TypeKind getKind() {
1681            return TypeKind.TYPEVAR;
1682        }
1683
1684        public boolean isCaptured() {
1685            return false;
1686        }
1687
1688        @Override
1689        public boolean isReference() {
1690            return true;
1691        }
1692
1693        @Override
1694        public boolean isNullOrReference() {
1695            return true;
1696        }
1697
1698        @Override @DefinedBy(Api.LANGUAGE_MODEL)
1699        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
1700            return v.visitTypeVariable(this, p);
1701        }
1702    }
1703
1704    /** A captured type variable comes from wildcards which can have
1705     *  both upper and lower bound.  CapturedType extends TypeVar with
1706     *  a lower bound.
1707     */
1708    public static class CapturedType extends TypeVar {
1709
1710        public WildcardType wildcard;
1711
1712        public CapturedType(Name name,
1713                            Symbol owner,
1714                            Type upper,
1715                            Type lower,
1716                            WildcardType wildcard) {
1717            super(name, owner, lower);
1718            this.lower = Assert.checkNonNull(lower);
1719            this.bound = upper;
1720            this.wildcard = wildcard;
1721        }
1722
1723        public CapturedType(TypeSymbol tsym,
1724                            Type bound,
1725                            Type upper,
1726                            Type lower,
1727                            WildcardType wildcard,
1728                            TypeMetadata metadata) {
1729            super(tsym, bound, lower, metadata);
1730            this.wildcard = wildcard;
1731        }
1732
1733        @Override
1734        public CapturedType cloneWithMetadata(TypeMetadata md) {
1735            return new CapturedType(tsym, bound, bound, lower, wildcard, md) {
1736                @Override
1737                public Type baseType() { return CapturedType.this.baseType(); }
1738            };
1739        }
1740
1741        @Override
1742        public <R,S> R accept(Type.Visitor<R,S> v, S s) {
1743            return v.visitCapturedType(this, s);
1744        }
1745
1746        @Override
1747        public boolean isCaptured() {
1748            return true;
1749        }
1750
1751        @Override @DefinedBy(Api.LANGUAGE_MODEL)
1752        public String toString() {
1753            StringBuilder sb = new StringBuilder();
1754            appendAnnotationsString(sb);
1755            sb.append("capture#");
1756            sb.append((hashCode() & 0xFFFFFFFFL) % Printer.PRIME);
1757            sb.append(" of ");
1758            sb.append(wildcard);
1759            return sb.toString();
1760        }
1761    }
1762
1763    public static abstract class DelegatedType extends Type {
1764        public Type qtype;
1765        public TypeTag tag;
1766
1767        public DelegatedType(TypeTag tag, Type qtype) {
1768            this(tag, qtype, TypeMetadata.EMPTY);
1769        }
1770
1771        public DelegatedType(TypeTag tag, Type qtype,
1772                             TypeMetadata metadata) {
1773            super(qtype.tsym, metadata);
1774            this.tag = tag;
1775            this.qtype = qtype;
1776        }
1777
1778        public TypeTag getTag() { return tag; }
1779        @DefinedBy(Api.LANGUAGE_MODEL)
1780        public String toString() { return qtype.toString(); }
1781        public List<Type> getTypeArguments() { return qtype.getTypeArguments(); }
1782        public Type getEnclosingType() { return qtype.getEnclosingType(); }
1783        public List<Type> getParameterTypes() { return qtype.getParameterTypes(); }
1784        public Type getReturnType() { return qtype.getReturnType(); }
1785        public Type getReceiverType() { return qtype.getReceiverType(); }
1786        public List<Type> getThrownTypes() { return qtype.getThrownTypes(); }
1787        public List<Type> allparams() { return qtype.allparams(); }
1788        public Type getUpperBound() { return qtype.getUpperBound(); }
1789        public boolean isErroneous() { return qtype.isErroneous(); }
1790    }
1791
1792    /**
1793     * The type of a generic method type. It consists of a method type and
1794     * a list of method type-parameters that are used within the method
1795     * type.
1796     */
1797    public static class ForAll extends DelegatedType implements ExecutableType {
1798        public List<Type> tvars;
1799
1800        public ForAll(List<Type> tvars, Type qtype) {
1801            super(FORALL, (MethodType)qtype);
1802            this.tvars = tvars;
1803        }
1804
1805        @Override
1806        public ForAll cloneWithMetadata(TypeMetadata md) {
1807            throw new AssertionError("Cannot add metadata to a forall type");
1808        }
1809
1810        @Override
1811        public <R,S> R accept(Type.Visitor<R,S> v, S s) {
1812            return v.visitForAll(this, s);
1813        }
1814
1815        @DefinedBy(Api.LANGUAGE_MODEL)
1816        public String toString() {
1817            StringBuilder sb = new StringBuilder();
1818            appendAnnotationsString(sb);
1819            sb.append('<');
1820            sb.append(tvars);
1821            sb.append('>');
1822            sb.append(qtype);
1823            return sb.toString();
1824        }
1825
1826        public List<Type> getTypeArguments()   { return tvars; }
1827
1828        public boolean isErroneous()  {
1829            return qtype.isErroneous();
1830        }
1831
1832        public boolean contains(Type elem) {
1833            return qtype.contains(elem);
1834        }
1835
1836        public MethodType asMethodType() {
1837            return (MethodType)qtype;
1838        }
1839
1840        public void complete() {
1841            for (List<Type> l = tvars; l.nonEmpty(); l = l.tail) {
1842                ((TypeVar)l.head).bound.complete();
1843            }
1844            qtype.complete();
1845        }
1846
1847        @DefinedBy(Api.LANGUAGE_MODEL)
1848        public List<TypeVar> getTypeVariables() {
1849            return List.convert(TypeVar.class, getTypeArguments());
1850        }
1851
1852        @DefinedBy(Api.LANGUAGE_MODEL)
1853        public TypeKind getKind() {
1854            return TypeKind.EXECUTABLE;
1855        }
1856
1857        @DefinedBy(Api.LANGUAGE_MODEL)
1858        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
1859            return v.visitExecutable(this, p);
1860        }
1861    }
1862
1863    /** A class for inference variables, for use during method/diamond type
1864     *  inference. An inference variable has upper/lower bounds and a set
1865     *  of equality constraints. Such bounds are set during subtyping, type-containment,
1866     *  type-equality checks, when the types being tested contain inference variables.
1867     *  A change listener can be attached to an inference variable, to receive notifications
1868     *  whenever the bounds of an inference variable change.
1869     */
1870    public static class UndetVar extends DelegatedType {
1871
1872        /** Inference variable change listener. The listener method is called
1873         *  whenever a change to the inference variable's bounds occurs
1874         */
1875        public interface UndetVarListener {
1876            /** called when some inference variable bounds (of given kinds ibs) change */
1877            void varBoundChanged(UndetVar uv, InferenceBound ib, Type bound, boolean update);
1878            /** called when the inferred type is set on some inference variable */
1879            default void varInstantiated(UndetVar uv) { Assert.error(); }
1880        }
1881
1882        /**
1883         * Inference variable bound kinds
1884         */
1885        public enum InferenceBound {
1886            /** lower bounds */
1887            LOWER {
1888                public InferenceBound complement() { return UPPER; }
1889            },
1890            /** equality constraints */
1891            EQ {
1892                public InferenceBound complement() { return EQ; }
1893            },
1894            /** upper bounds */
1895            UPPER {
1896                public InferenceBound complement() { return LOWER; }
1897            };
1898
1899            public abstract InferenceBound complement();
1900
1901            public boolean lessThan(InferenceBound that) {
1902                if (that == this) {
1903                    return false;
1904                } else {
1905                    switch (that) {
1906                        case UPPER: return true;
1907                        case LOWER: return false;
1908                        case EQ: return (this != UPPER);
1909                        default:
1910                            Assert.error("Cannot get here!");
1911                            return false;
1912                    }
1913                }
1914            }
1915        }
1916
1917        /** list of incorporation actions (used by the incorporation engine). */
1918        public ArrayDeque<IncorporationAction> incorporationActions = new ArrayDeque<>();
1919
1920        /** inference variable bounds */
1921        protected Map<InferenceBound, List<Type>> bounds;
1922
1923        /** inference variable's inferred type (set from Infer.java) */
1924        private Type inst = null;
1925
1926        /** number of declared (upper) bounds */
1927        public int declaredCount;
1928
1929        /** inference variable's change listener */
1930        public UndetVarListener listener = null;
1931
1932        @Override
1933        public <R,S> R accept(Type.Visitor<R,S> v, S s) {
1934            return v.visitUndetVar(this, s);
1935        }
1936
1937        public UndetVar(TypeVar origin, UndetVarListener listener, Types types) {
1938            // This is a synthesized internal type, so we cannot annotate it.
1939            super(UNDETVAR, origin);
1940            this.listener = listener;
1941            bounds = new EnumMap<>(InferenceBound.class);
1942            List<Type> declaredBounds = types.getBounds(origin);
1943            declaredCount = declaredBounds.length();
1944            bounds.put(InferenceBound.UPPER, List.nil());
1945            bounds.put(InferenceBound.LOWER, List.nil());
1946            bounds.put(InferenceBound.EQ, List.nil());
1947            for (Type t : declaredBounds.reverse()) {
1948                //add bound works in reverse order
1949                addBound(InferenceBound.UPPER, t, types, true);
1950            }
1951        }
1952
1953        @DefinedBy(Api.LANGUAGE_MODEL)
1954        public String toString() {
1955            StringBuilder sb = new StringBuilder();
1956            appendAnnotationsString(sb);
1957            if (inst == null) {
1958                sb.append(qtype);
1959                sb.append('?');
1960            } else {
1961                sb.append(inst);
1962            }
1963            return sb.toString();
1964        }
1965
1966        public String debugString() {
1967            String result = "inference var = " + qtype + "\n";
1968            if (inst != null) {
1969                result += "inst = " + inst + '\n';
1970            }
1971            for (InferenceBound bound: InferenceBound.values()) {
1972                List<Type> aboundList = bounds.get(bound);
1973                if (aboundList.size() > 0) {
1974                    result += bound + " = " + aboundList + '\n';
1975                }
1976            }
1977            return result;
1978        }
1979
1980        /**
1981         * Returns a new copy of this undet var.
1982         */
1983        public UndetVar dup(Types types) {
1984            UndetVar uv2 = new UndetVar((TypeVar)qtype, listener, types);
1985            dupTo(uv2, types);
1986            return uv2;
1987        }
1988
1989        /**
1990         * Dumps the contents of this undet var on another undet var.
1991         */
1992        public void dupTo(UndetVar uv2, Types types) {
1993            uv2.listener = null;
1994            uv2.bounds.clear();
1995            for (InferenceBound ib : InferenceBound.values()) {
1996                uv2.bounds.put(ib, List.nil());
1997                for (Type t : getBounds(ib)) {
1998                    uv2.addBound(ib, t, types, true);
1999                }
2000            }
2001            uv2.inst = inst;
2002            uv2.listener = listener;
2003            uv2.incorporationActions = new ArrayDeque<>();
2004            for (IncorporationAction action : incorporationActions) {
2005                uv2.incorporationActions.add(action.dup(uv2));
2006            }
2007        }
2008
2009        @Override
2010        public UndetVar cloneWithMetadata(TypeMetadata md) {
2011            throw new AssertionError("Cannot add metadata to an UndetVar type");
2012        }
2013
2014        @Override
2015        public boolean isPartial() {
2016            return true;
2017        }
2018
2019        @Override
2020        public Type baseType() {
2021            return (inst == null) ? this : inst.baseType();
2022        }
2023
2024        public Type getInst() {
2025            return inst;
2026        }
2027
2028        public void setInst(Type inst) {
2029            this.inst = inst;
2030            if (listener != null) {
2031                listener.varInstantiated(this);
2032            }
2033        }
2034
2035        /** get all bounds of a given kind */
2036        public List<Type> getBounds(InferenceBound... ibs) {
2037            ListBuffer<Type> buf = new ListBuffer<>();
2038            for (InferenceBound ib : ibs) {
2039                buf.appendList(bounds.get(ib));
2040            }
2041            return buf.toList();
2042        }
2043
2044        /** get the list of declared (upper) bounds */
2045        public List<Type> getDeclaredBounds() {
2046            ListBuffer<Type> buf = new ListBuffer<>();
2047            int count = 0;
2048            for (Type b : getBounds(InferenceBound.UPPER)) {
2049                if (count++ == declaredCount) break;
2050                buf.append(b);
2051            }
2052            return buf.toList();
2053        }
2054
2055        /** internal method used to override an undetvar bounds */
2056        public void setBounds(InferenceBound ib, List<Type> newBounds) {
2057            bounds.put(ib, newBounds);
2058        }
2059
2060        /** add a bound of a given kind - this might trigger listener notification */
2061        public final void addBound(InferenceBound ib, Type bound, Types types) {
2062            addBound(ib, bound, types, false);
2063        }
2064
2065        protected void addBound(InferenceBound ib, Type bound, Types types, boolean update) {
2066            Type bound2 = bound.map(toTypeVarMap).baseType();
2067            List<Type> prevBounds = bounds.get(ib);
2068            if (bound == qtype) return;
2069            for (Type b : prevBounds) {
2070                //check for redundancy - use strict version of isSameType on tvars
2071                //(as the standard version will lead to false positives w.r.t. clones ivars)
2072                if (types.isSameType(b, bound2, true)) return;
2073            }
2074            bounds.put(ib, prevBounds.prepend(bound2));
2075            notifyBoundChange(ib, bound2, false);
2076        }
2077        //where
2078            TypeMapping<Void> toTypeVarMap = new TypeMapping<Void>() {
2079                @Override
2080                public Type visitUndetVar(UndetVar uv, Void _unused) {
2081                    return uv.inst != null ? uv.inst : uv.qtype;
2082                }
2083            };
2084
2085        /** replace types in all bounds - this might trigger listener notification */
2086        public void substBounds(List<Type> from, List<Type> to, Types types) {
2087            final ListBuffer<Pair<InferenceBound, Type>>  boundsChanged = new ListBuffer<>();
2088            UndetVarListener prevListener = listener;
2089            try {
2090                //setup new listener for keeping track of changed bounds
2091                listener = new UndetVarListener() {
2092                    public void varBoundChanged(UndetVar uv, InferenceBound ib, Type t, boolean _ignored) {
2093                        Assert.check(uv == UndetVar.this);
2094                        boundsChanged.add(new Pair<>(ib, t));
2095                    }
2096                };
2097                for (Map.Entry<InferenceBound, List<Type>> _entry : bounds.entrySet()) {
2098                    InferenceBound ib = _entry.getKey();
2099                    List<Type> prevBounds = _entry.getValue();
2100                    ListBuffer<Type> newBounds = new ListBuffer<>();
2101                    ListBuffer<Type> deps = new ListBuffer<>();
2102                    //step 1 - re-add bounds that are not dependent on ivars
2103                    for (Type t : prevBounds) {
2104                        if (!t.containsAny(from)) {
2105                            newBounds.append(t);
2106                        } else {
2107                            deps.append(t);
2108                        }
2109                    }
2110                    //step 2 - replace bounds
2111                    bounds.put(ib, newBounds.toList());
2112                    //step 3 - for each dependency, add new replaced bound
2113                    for (Type dep : deps) {
2114                        addBound(ib, types.subst(dep, from, to), types, true);
2115                    }
2116                }
2117            } finally {
2118                listener = prevListener;
2119                for (Pair<InferenceBound, Type> boundUpdate : boundsChanged) {
2120                    notifyBoundChange(boundUpdate.fst, boundUpdate.snd, true);
2121                }
2122            }
2123        }
2124
2125        private void notifyBoundChange(InferenceBound ib, Type bound, boolean update) {
2126            if (listener != null) {
2127                listener.varBoundChanged(this, ib, bound, update);
2128            }
2129        }
2130
2131        public boolean isCaptured() {
2132            return false;
2133        }
2134    }
2135
2136    /**
2137     * This class is used to represent synthetic captured inference variables
2138     * that can be generated during nested generic method calls. The only difference
2139     * between these inference variables and ordinary ones is that captured inference
2140     * variables cannot get new bounds through incorporation.
2141     */
2142    public static class CapturedUndetVar extends UndetVar {
2143
2144        public CapturedUndetVar(CapturedType origin, UndetVarListener listener, Types types) {
2145            super(origin, listener, types);
2146            if (!origin.lower.hasTag(BOT)) {
2147                addBound(InferenceBound.LOWER, origin.lower, types, true);
2148            }
2149        }
2150
2151        @Override
2152        public void addBound(InferenceBound ib, Type bound, Types types, boolean update) {
2153            if (update) {
2154                //only change bounds if request comes from substBounds
2155                super.addBound(ib, bound, types, update);
2156            }
2157            else if (bound.hasTag(UNDETVAR) && !((UndetVar) bound).isCaptured()) {
2158                ((UndetVar) bound).addBound(ib.complement(), this, types, false);
2159            }
2160        }
2161
2162        @Override
2163        public boolean isCaptured() {
2164            return true;
2165        }
2166
2167        public UndetVar dup(Types types) {
2168            UndetVar uv2 = new CapturedUndetVar((CapturedType)qtype, listener, types);
2169            dupTo(uv2, types);
2170            return uv2;
2171        }
2172    }
2173
2174    /** Represents NONE.
2175     */
2176    public static class JCNoType extends Type implements NoType {
2177        public JCNoType() {
2178            // Need to use List.nil(), because JCNoType constructor
2179            // gets called in static initializers in Type, where
2180            // noAnnotations is also defined.
2181            super(null, TypeMetadata.EMPTY);
2182        }
2183
2184        @Override
2185        public JCNoType cloneWithMetadata(TypeMetadata md) {
2186            throw new AssertionError("Cannot add metadata to a JCNoType");
2187        }
2188
2189        @Override
2190        public TypeTag getTag() {
2191            return NONE;
2192        }
2193
2194        @Override @DefinedBy(Api.LANGUAGE_MODEL)
2195        public TypeKind getKind() {
2196            return TypeKind.NONE;
2197        }
2198
2199        @Override @DefinedBy(Api.LANGUAGE_MODEL)
2200        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
2201            return v.visitNoType(this, p);
2202        }
2203
2204        @Override
2205        public boolean isCompound() { return false; }
2206    }
2207
2208    /** Represents VOID.
2209     */
2210    public static class JCVoidType extends Type implements NoType {
2211
2212        public JCVoidType() {
2213            // Void cannot be annotated
2214            super(null, TypeMetadata.EMPTY);
2215        }
2216
2217        @Override
2218        public JCVoidType cloneWithMetadata(TypeMetadata md) {
2219            throw new AssertionError("Cannot add metadata to a void type");
2220        }
2221
2222        @Override
2223        public TypeTag getTag() {
2224            return VOID;
2225        }
2226
2227        @Override @DefinedBy(Api.LANGUAGE_MODEL)
2228        public TypeKind getKind() {
2229            return TypeKind.VOID;
2230        }
2231
2232        @Override
2233        public boolean isCompound() { return false; }
2234
2235        @Override @DefinedBy(Api.LANGUAGE_MODEL)
2236        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
2237            return v.visitNoType(this, p);
2238        }
2239
2240        @Override
2241        public boolean isPrimitiveOrVoid() {
2242            return true;
2243        }
2244    }
2245
2246    static class BottomType extends Type implements NullType {
2247        public BottomType() {
2248            // Bottom is a synthesized internal type, so it cannot be annotated
2249            super(null, TypeMetadata.EMPTY);
2250        }
2251
2252        @Override
2253        public BottomType cloneWithMetadata(TypeMetadata md) {
2254            throw new AssertionError("Cannot add metadata to a bottom type");
2255        }
2256
2257        @Override
2258        public TypeTag getTag() {
2259            return BOT;
2260        }
2261
2262        @Override @DefinedBy(Api.LANGUAGE_MODEL)
2263        public TypeKind getKind() {
2264            return TypeKind.NULL;
2265        }
2266
2267        @Override
2268        public boolean isCompound() { return false; }
2269
2270        @Override @DefinedBy(Api.LANGUAGE_MODEL)
2271        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
2272            return v.visitNull(this, p);
2273        }
2274
2275        @Override
2276        public Type constType(Object value) {
2277            return this;
2278        }
2279
2280        @Override
2281        public String stringValue() {
2282            return "null";
2283        }
2284
2285        @Override
2286        public boolean isNullOrReference() {
2287            return true;
2288        }
2289
2290    }
2291
2292    public static class ErrorType extends ClassType
2293            implements javax.lang.model.type.ErrorType {
2294
2295        private Type originalType = null;
2296
2297        public ErrorType(ClassSymbol c, Type originalType) {
2298            this(originalType, c);
2299            c.type = this;
2300            c.kind = ERR;
2301            c.members_field = new Scope.ErrorScope(c);
2302        }
2303
2304        public ErrorType(Type originalType, TypeSymbol tsym) {
2305            super(noType, List.<Type>nil(), null);
2306            this.tsym = tsym;
2307            this.originalType = (originalType == null ? noType : originalType);
2308        }
2309
2310        private ErrorType(Type originalType, TypeSymbol tsym,
2311                          TypeMetadata metadata) {
2312            super(noType, List.<Type>nil(), null, metadata);
2313            this.tsym = tsym;
2314            this.originalType = (originalType == null ? noType : originalType);
2315        }
2316
2317        @Override
2318        public ErrorType cloneWithMetadata(TypeMetadata md) {
2319            return new ErrorType(originalType, tsym, md) {
2320                @Override
2321                public Type baseType() { return ErrorType.this.baseType(); }
2322            };
2323        }
2324
2325        @Override
2326        public TypeTag getTag() {
2327            return ERROR;
2328        }
2329
2330        @Override
2331        public boolean isPartial() {
2332            return true;
2333        }
2334
2335        @Override
2336        public boolean isReference() {
2337            return true;
2338        }
2339
2340        @Override
2341        public boolean isNullOrReference() {
2342            return true;
2343        }
2344
2345        public ErrorType(Name name, TypeSymbol container, Type originalType) {
2346            this(new ClassSymbol(PUBLIC|STATIC|ACYCLIC, name, null, container), originalType);
2347        }
2348
2349        @Override
2350        public <R,S> R accept(Type.Visitor<R,S> v, S s) {
2351            return v.visitErrorType(this, s);
2352        }
2353
2354        public Type constType(Object constValue) { return this; }
2355        @DefinedBy(Api.LANGUAGE_MODEL)
2356        public Type getEnclosingType()           { return this; }
2357        public Type getReturnType()              { return this; }
2358        public Type asSub(Symbol sym)            { return this; }
2359
2360        public boolean isGenType(Type t)         { return true; }
2361        public boolean isErroneous()             { return true; }
2362        public boolean isCompound()              { return false; }
2363        public boolean isInterface()             { return false; }
2364
2365        public List<Type> allparams()            { return List.nil(); }
2366        @DefinedBy(Api.LANGUAGE_MODEL)
2367        public List<Type> getTypeArguments()     { return List.nil(); }
2368
2369        @DefinedBy(Api.LANGUAGE_MODEL)
2370        public TypeKind getKind() {
2371            return TypeKind.ERROR;
2372        }
2373
2374        public Type getOriginalType() {
2375            return originalType;
2376        }
2377
2378        @DefinedBy(Api.LANGUAGE_MODEL)
2379        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
2380            return v.visitError(this, p);
2381        }
2382    }
2383
2384    public static class UnknownType extends Type {
2385
2386        public UnknownType() {
2387            // Unknown is a synthesized internal type, so it cannot be
2388            // annotated.
2389            super(null, TypeMetadata.EMPTY);
2390        }
2391
2392        @Override
2393        public UnknownType cloneWithMetadata(TypeMetadata md) {
2394            throw new AssertionError("Cannot add metadata to an unknown type");
2395        }
2396
2397        @Override
2398        public TypeTag getTag() {
2399            return UNKNOWN;
2400        }
2401
2402        @Override @DefinedBy(Api.LANGUAGE_MODEL)
2403        public <R, P> R accept(TypeVisitor<R, P> v, P p) {
2404            return v.visitUnknown(this, p);
2405        }
2406
2407        @Override
2408        public boolean isPartial() {
2409            return true;
2410        }
2411    }
2412
2413    /**
2414     * A visitor for types.  A visitor is used to implement operations
2415     * (or relations) on types.  Most common operations on types are
2416     * binary relations and this interface is designed for binary
2417     * relations, that is, operations of the form
2418     * Type&nbsp;&times;&nbsp;S&nbsp;&rarr;&nbsp;R.
2419     * <!-- In plain text: Type x S -> R -->
2420     *
2421     * @param <R> the return type of the operation implemented by this
2422     * visitor; use Void if no return type is needed.
2423     * @param <S> the type of the second argument (the first being the
2424     * type itself) of the operation implemented by this visitor; use
2425     * Void if a second argument is not needed.
2426     */
2427    public interface Visitor<R,S> {
2428        R visitClassType(ClassType t, S s);
2429        R visitWildcardType(WildcardType t, S s);
2430        R visitArrayType(ArrayType t, S s);
2431        R visitMethodType(MethodType t, S s);
2432        R visitPackageType(PackageType t, S s);
2433        R visitModuleType(ModuleType t, S s);
2434        R visitTypeVar(TypeVar t, S s);
2435        R visitCapturedType(CapturedType t, S s);
2436        R visitForAll(ForAll t, S s);
2437        R visitUndetVar(UndetVar t, S s);
2438        R visitErrorType(ErrorType t, S s);
2439        R visitType(Type t, S s);
2440    }
2441}
2442