Source Code Cross Referenced for Type.java in  » Parser » Rats-Parser-Generators » xtc » type » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » Parser » Rats Parser Generators » xtc.type 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


0001:        /*
0002:         * xtc - The eXTensible Compiler
0003:         * Copyright (C) 2005-2007 Robert Grimm
0004:         *
0005:         * This program is free software; you can redistribute it and/or
0006:         * modify it under the terms of the GNU General Public License
0007:         * version 2 as published by the Free Software Foundation.
0008:         *
0009:         * This program is distributed in the hope that it will be useful,
0010:         * but WITHOUT ANY WARRANTY; without even the implied warranty of
0011:         * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
0012:         * GNU General Public License for more details.
0013:         *
0014:         * You should have received a copy of the GNU General Public License
0015:         * along with this program; if not, write to the Free Software
0016:         * Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
0017:         * USA.
0018:         */
0019:        package xtc.type;
0020:
0021:        import java.math.BigInteger;
0022:
0023:        import java.util.ArrayList;
0024:        import java.util.Collections;
0025:        import java.util.List;
0026:        import java.util.Set;
0027:
0028:        import xtc.Constants;
0029:
0030:        import xtc.tree.Attribute;
0031:        import xtc.tree.Location;
0032:        import xtc.tree.Locatable;
0033:        import xtc.tree.Node;
0034:        import xtc.tree.Visitor;
0035:
0036:        import xtc.util.Runtime;
0037:
0038:        /**
0039:         * The superclass of all types.
0040:         *
0041:         * <p />The class hierarchy for types distinguishes basic from wrapped
0042:         * types, with wrapped types providing additional information for
0043:         * basic types.  For each basic type, this class provides
0044:         * <code>is<i>Name</i>()</code> and <code>to<i>Name</i>()</code>
0045:         * methods to replace instanceof tests and casts, respectively.  For
0046:         * each wrapped type, this class additionally provides a
0047:         * <code>has<i>Name</i>()</code> method, which identifies instances of
0048:         * the wrapped type even if they are wrapped inside another (wrapped)
0049:         * type.  In other words, invocations of <code>has<i>Name</i>()</code>
0050:         * are forwarded across wrapped types while invocations of
0051:         * <code>is<i>Name</i>()</code> only apply to the outermost type
0052:         * object.  For wrapped types, invocations of
0053:         * <code>to<i>Name</i>()</code> are also forwarded across (other)
0054:         * wrapped types.
0055:         *
0056:         * <p />As an example, consider an int type wrapped in an annotated
0057:         * type and an alias type:
0058:         * <pre>
0059:         * Type i = NumberT.INT;
0060:         * Type j = new AnnotatedT(i);
0061:         * Type k = new AliasT("alias", j);
0062:         * </pre>
0063:         * Then the following method invocations have the following results:
0064:         * <pre>
0065:         * k.isAlias()        &rArr; <i>true</i>
0066:         * k.hasAlias()       &rArr; <i>true</i>
0067:         * k.toAlias()        &rArr; <i>k</i>
0068:         *
0069:         * k.isAnnotated()    &rArr; <i>false</i>
0070:         * k.hasAnnotated()   &rArr; <i>true</i>
0071:         * k.toAnnotated()    &rArr; <i>j</i>
0072:         *
0073:         * k.isInteger()      &rArr; <i>false</i>
0074:         * k.toInteger()      &rArr; <i>error</i>
0075:         * </pre>
0076:         * The {@link #resolve()} method can be used to strip any wrapped
0077:         * types:
0078:         * <pre>
0079:         * Type r = k.resolve();
0080:         *
0081:         * r.isAlias()        &rArr; <i>false</i>
0082:         * r.isAnnotated()    &rArr; <i>false</i>
0083:         * r.isInteger()      &rArr; <i>true</i>
0084:         * r.toInteger()      &rArr; <i>i</i>
0085:         * </pre>
0086:         *
0087:         * <p />The {@link Tag} enumeration also identifies particular types.
0088:         * A type's tag can be accessed through {@link #tag()}, which is
0089:         * forwarded across wrapped types, and through {@link #wtag()}, which
0090:         * is <em>not</em> forwarded across wrapped types.  As a result,
0091:         * <code>tag()</code> identifies basic types independent of whether
0092:         * they are wrapped or not, while <code>wtag()</code> always
0093:         * identifies the outermost type:
0094:         * <pre>
0095:         * k.tag()            &rArr; <i>Tag.INTEGER</i>
0096:         * k.wtag()           &rArr; <i>Tag.ALIAS</i>
0097:         *
0098:         * i.tag()            &rArr; <i>Tag.INTEGER</i>
0099:         * i.tag()            &rArr; <i>Tag.INTEGER</i>
0100:         * </pre>
0101:         *
0102:         * <p />Each type can have one or more of the following
0103:         * annotations:<ul>
0104:         *
0105:         * <li>Its source location represented as a {@link Location}.</li>
0106:         *
0107:         * <li>Its source language represented as a {@link Language} tag.</li>
0108:         *
0109:         * <li>Its scope represented as a {@link String}.</li>
0110:         *
0111:         * <li>Its constant value represented as a {@link Constant}.</li>
0112:         *
0113:         * <li>Its memory shape represented as a {@link Reference}.  Only
0114:         * lvalues can have a shape.</li>
0115:         *
0116:         * <li>Its attributes represented as a list of {@link Attribute}
0117:         * values.</li>
0118:         *
0119:         * </ul>
0120:         * For each kind of annotation, this class defines tester, getter, and
0121:         * setter methods.  The tester and getter methods come in two
0122:         * versions, one that is forwarded across wrapped types and one that
0123:         * uses a boolean parameter to control forwarding.
0124:         *
0125:         * @author Robert Grimm
0126:         * @version $Revision: 1.110 $
0127:         */
0128:        public abstract class Type extends Node {
0129:
0130:            /**
0131:             * A type's tag.  Only leaves of the type hierarchy have their own
0132:             * tags.  A type's tag is accessed through {@link #tag()} and {@link
0133:             * #wtag()}.
0134:             */
0135:            public static enum Tag {
0136:                /** A boolean. */
0137:                BOOLEAN,
0138:                /** An array. */
0139:                ARRAY,
0140:                /** A class. */
0141:                CLASS,
0142:                /** An interface. */
0143:                INTERFACE,
0144:                /** A function. */
0145:                FUNCTION,
0146:                /** A method. */
0147:                METHOD,
0148:                /** A parameter. */
0149:                PARAMETER,
0150:                /** A wildcard. */
0151:                WILDCARD,
0152:                /** A pointer. */
0153:                POINTER,
0154:                /** A struct. */
0155:                STRUCT,
0156:                /** A tuple. */
0157:                TUPLE,
0158:                /** A union. */
0159:                UNION,
0160:                /** A variant. */
0161:                VARIANT,
0162:                /** An error. */
0163:                ERROR,
0164:                /** An internal type. */
0165:                INTERNAL,
0166:                /** A label. */
0167:                LABEL,
0168:                /** A float. */
0169:                FLOAT,
0170:                /** An integer. */
0171:                INTEGER,
0172:                /** A package. */
0173:                PACKAGE,
0174:                /** A unit type. */
0175:                UNIT,
0176:                /** A void type. */
0177:                VOID,
0178:                /** An alias. */
0179:                ALIAS,
0180:                /** An annotated type. */
0181:                ANNOTATED,
0182:                /** An enumerator. */
0183:                ENUMERATOR,
0184:                /** An enum. */
0185:                ENUM,
0186:                /** An instantiated type. */
0187:                INSTANTIATED,
0188:                /** A parameterized type. */
0189:                PARAMETERIZED,
0190:                /** A variable. */
0191:                VARIABLE
0192:            }
0193:
0194:            // =========================================================================
0195:
0196:            /** The flag for whether this type is sealed. */
0197:            boolean sealed;
0198:
0199:            // This type's location is implicit in the Node.
0200:
0201:            /** This type's language. */
0202:            Language language;
0203:
0204:            /** This type's scope. */
0205:            String scope;
0206:
0207:            /** This type's constant value. */
0208:            Constant constant;
0209:
0210:            /** This type's shape. */
0211:            Reference shape;
0212:
0213:            /** This type's attributes. */
0214:            List<Attribute> attributes;
0215:
0216:            // =========================================================================
0217:
0218:            /**
0219:             * Create a new type.  The newly created type does not have any
0220:             * annotations and is not sealed.
0221:             */
0222:            public Type() { /* Nothing to do. */
0223:            }
0224:
0225:            /**
0226:             * Create a new type.  The newly created type is not sealed.  Its
0227:             * annotations are a copy of the specified template's annotations.
0228:             *
0229:             * @param template The type whose annotations to copy.
0230:             */
0231:            public Type(Type template) {
0232:                if (null == template)
0233:                    return;
0234:
0235:                setLocation(template);
0236:                this .language = template.language;
0237:                this .scope = template.scope;
0238:                this .constant = template.constant;
0239:                this .shape = template.shape;
0240:                if (null != template.attributes) {
0241:                    this .attributes = new ArrayList<Attribute>(
0242:                            template.attributes);
0243:                }
0244:            }
0245:
0246:            // =========================================================================
0247:
0248:            /**
0249:             * Create a deep copy of this type.  The resulting type is not
0250:             * sealed.
0251:             *
0252:             * @return A deep copy of this type.
0253:             */
0254:            public abstract Type copy();
0255:
0256:            // =========================================================================
0257:
0258:            /**
0259:             * Determine whether this type is sealed.
0260:             *
0261:             * @return <code>true</code> if this type is sealed.
0262:             */
0263:            public boolean isSealed() {
0264:                return sealed;
0265:            }
0266:
0267:            /**
0268:             * Seal this type.  Subclasses that reference other types must
0269:             * override this method and, if the instance is not sealed, first
0270:             * invoke the superclass' version and then seal all referenced
0271:             * types.  For example, if a subclass references a single type
0272:             * <code>type</code>, the corresponding overridden method reads:
0273:             * <pre>
0274:             * public Type seal() {
0275:             *   if (! isSealed()) {
0276:             *     super.seal();
0277:             *     type.seal();
0278:             *   }
0279:             *   return this;
0280:             * }
0281:             * </pre>
0282:             * First testing whether a type is sealed and then invoking the
0283:             * superclass' <code>seal()</code> method avoids infinite recursions
0284:             * for mutually recursive types.
0285:             *
0286:             * @see #seal(List)
0287:             *
0288:             * @return This type.
0289:             */
0290:            public Type seal() {
0291:                sealed = true;
0292:                return this ;
0293:            }
0294:
0295:            /**
0296:             * Ensure that this type is not sealed.  This method must be called
0297:             * by any subclass before modifying its internal state.
0298:             *
0299:             * @throws IllegalStateException Signals that this type is sealed.
0300:             */
0301:            protected void checkNotSealed() {
0302:                if (sealed) {
0303:                    throw new IllegalStateException("Type " + this 
0304:                            + " is sealed");
0305:                }
0306:            }
0307:
0308:            // =========================================================================
0309:
0310:            /**
0311:             * Annotate this type.  If this type is not an annotated type or a
0312:             * sealed annotated type, this method wraps this type in a new
0313:             * {@link AnnotatedT}.
0314:             *
0315:             * @return The annotated type.
0316:             */
0317:            public Type annotate() {
0318:                return isAnnotated() && (!isSealed()) ? this  : new AnnotatedT(
0319:                        this );
0320:            }
0321:
0322:            /**
0323:             * Deannotate this type.  This method strips away any {@link
0324:             * AnnotatedT} from this type.
0325:             *
0326:             * @return The deannotated type.
0327:             */
0328:            public Type deannotate() {
0329:                Type t = this ;
0330:                while (t.isAnnotated())
0331:                    t = t.toAnnotated().getType();
0332:                return t;
0333:            }
0334:
0335:            // =========================================================================
0336:
0337:            public Object setProperty(String name, Object value) {
0338:                checkNotSealed();
0339:                return super .setProperty(name, value);
0340:            }
0341:
0342:            public Object removeProperty(String name) {
0343:                checkNotSealed();
0344:                return super .removeProperty(name);
0345:            }
0346:
0347:            public Set<String> properties() {
0348:                if (sealed) {
0349:                    return Collections.unmodifiableSet(super .properties());
0350:                } else {
0351:                    return properties();
0352:                }
0353:            }
0354:
0355:            // =========================================================================
0356:
0357:            /**
0358:             * Determine whether this type or any wrapped type has a location.
0359:             * Calling this method on type <code>t</code> is equivalent to:
0360:             * <pre>
0361:             * t.hasLocation(true)
0362:             * </pre>
0363:             *
0364:             * @see #hasLocation(boolean)
0365:             *
0366:             * @return <code>true</code> if this type or any wrapped type has a
0367:             *   location.
0368:             */
0369:            public boolean hasLocation() {
0370:                return hasLocation(true);
0371:            }
0372:
0373:            /**
0374:             * Determine whether this type or any wrapped type has a location.
0375:             *
0376:             * @param forward The flag for whether to forward this method across
0377:             *   wrapped types.
0378:             * @return <code>true</code> if this type or any wrapped type has a
0379:             *   location.
0380:             */
0381:            public boolean hasLocation(boolean forward) {
0382:                return super .hasLocation();
0383:            }
0384:
0385:            /**
0386:             * Get this type's or any wrapped type's location.  Calling this
0387:             * method on type <code>t</code> is equivalent to:
0388:             * <pre>
0389:             * t.getLocation(true)
0390:             * </pre>
0391:             *
0392:             * @see #getLocation(boolean)
0393:             *
0394:             * @return The location or <code>null</code> if this type or any
0395:             *   wrapped type does not have a location.
0396:             */
0397:            public Location getLocation() {
0398:                return getLocation(true);
0399:            }
0400:
0401:            /**
0402:             * Get this type's or any wrapped type's location.
0403:             *
0404:             * @param forward The flag for whether to forward this method across
0405:             *   wrapped types.
0406:             * @return The location or <code>null</code> if this type or any
0407:             *   wrapped type does not have a location.
0408:             */
0409:            public Location getLocation(boolean forward) {
0410:                return super .getLocation();
0411:            }
0412:
0413:            /**
0414:             * Set this type's location.
0415:             *
0416:             * @param location The location.
0417:             * @return This type.
0418:             * @throws IllegalStateException Signals that this type is sealed.
0419:             */
0420:            public Type locate(Location location) {
0421:                setLocation(location);
0422:                return this ;
0423:            }
0424:
0425:            /**
0426:             * Set this type's location.
0427:             *
0428:             * @param locatable The locatable.
0429:             * @return This type.
0430:             * @throws IllegalStateException Signals that this type is sealed.
0431:             */
0432:            public Type locate(Locatable locatable) {
0433:                setLocation(locatable);
0434:                return this ;
0435:            }
0436:
0437:            public void setLocation(Location location) {
0438:                checkNotSealed();
0439:                super .setLocation(location);
0440:            }
0441:
0442:            public void setLocation(Locatable locatable) {
0443:                checkNotSealed();
0444:                super .setLocation(locatable);
0445:            }
0446:
0447:            // =========================================================================
0448:
0449:            /**
0450:             * Determine whether this type or any wrapped type has a language.
0451:             * Calling this method on type <code>t</code> is equivalent to:
0452:             * <pre>
0453:             * t.hasLanguage(true)
0454:             * </pre>
0455:             *
0456:             * @see #hasLanguage(boolean)
0457:             *
0458:             * @return <code>true</code> if this type or any wrapped type has a
0459:             *   language.
0460:             */
0461:            public boolean hasLanguage() {
0462:                return hasLanguage(true);
0463:            }
0464:
0465:            /**
0466:             * Determine whether this type or any wrapped type has a language.
0467:             *
0468:             * @param forward The flag for whether to forward this method across
0469:             *   wrapped types.
0470:             * @return <code>true</code> if this type or any wrapped type has a
0471:             *   language.
0472:             */
0473:            public boolean hasLanguage(boolean forward) {
0474:                return null != language;
0475:            }
0476:
0477:            /**
0478:             * Get this type's or any wrapped type's language.  Calling this
0479:             * method on type <code>t</code> is equivalent to:
0480:             * <pre>
0481:             * t.getLanguage(true)
0482:             * </pre>
0483:             *
0484:             * @see #getLanguage(boolean)
0485:             *
0486:             * @return The language or <code>null</code> if this type or any
0487:             *   wrapped type does not have a language.
0488:             */
0489:            public Language getLanguage() {
0490:                return getLanguage(true);
0491:            }
0492:
0493:            /**
0494:             * Get this type's or any wrapped type's language.
0495:             *
0496:             * @param forward The flag for whether to forward this method across
0497:             *   wrapped types.
0498:             * @return The language or <code>null</code> if this type or any
0499:             *   wrapped type does not have a language.
0500:             */
0501:            public Language getLanguage(boolean forward) {
0502:                return language;
0503:            }
0504:
0505:            /**
0506:             * Set this type's language.
0507:             *
0508:             * @param language The language.
0509:             * @return This type.
0510:             * @throws IllegalStateException Signals that this type is sealed.
0511:             */
0512:            public Type language(Language language) {
0513:                checkNotSealed();
0514:                this .language = language;
0515:                return this ;
0516:            }
0517:
0518:            // =========================================================================
0519:
0520:            /**
0521:             * Determine whether this type or any wrapped type has a scope.
0522:             * Calling this method on type <code>t</code> is equivalent to:
0523:             * <pre>
0524:             * t.hasScope(true)
0525:             * </pre>
0526:             *
0527:             * @see #hasScope(boolean)
0528:             *
0529:             * @return <code>true</code> if this type or any wrapped type has a
0530:             *   scope.
0531:             */
0532:            public boolean hasScope() {
0533:                return hasScope(true);
0534:            }
0535:
0536:            /**
0537:             * Determine whether this type or any wrapped type has a scope.
0538:             *
0539:             * @param forward The flag for whether to forward this method across
0540:             *   wrapped types.
0541:             * @return <code>true</code> if this type or any wrapped type has a
0542:             *   scope.
0543:             */
0544:            public boolean hasScope(boolean forward) {
0545:                return null != scope;
0546:            }
0547:
0548:            /**
0549:             * Get this type's or any wrapped type's scope.  Calling this method
0550:             * on type <code>t</code> is equivalent to:
0551:             * <pre>
0552:             * t.getScope(true)
0553:             * </pre>
0554:             *
0555:             * @see #getScope(boolean)
0556:             *
0557:             * @return The scope or <code>null</code> if this type or any
0558:             *   wrapped type does not have a scope.
0559:             */
0560:            public String getScope() {
0561:                return getScope(true);
0562:            }
0563:
0564:            /**
0565:             * Get this type's or any wrapped type's scope.
0566:             *
0567:             * @param forward The flag for whether to forward this method across
0568:             *   wrapped types.
0569:             * @return The scope or <code>null</code> if this type or any
0570:             *   wrapped type does not have a scope.
0571:             */
0572:            public String getScope(boolean forward) {
0573:                return scope;
0574:            }
0575:
0576:            /**
0577:             * Set this type's scope.
0578:             *
0579:             * @param scope The scope.
0580:             * @return This type.
0581:             * @throws IllegalStateException Signals that this type is sealed.
0582:             */
0583:            public Type scope(String scope) {
0584:                checkNotSealed();
0585:                this .scope = scope;
0586:                return this ;
0587:            }
0588:
0589:            // =========================================================================
0590:
0591:            /**
0592:             * Determine whether this type or any wrapped type has a constant.
0593:             * Calling this method on type <code>t</code> is equivalent to:
0594:             * <pre>
0595:             * t.hasConstant(true)
0596:             * </pre>
0597:             *
0598:             * @see #hasConstant(boolean)
0599:             *
0600:             * @return <code>true</code> if this type has a constant.
0601:             */
0602:            public boolean hasConstant() {
0603:                return hasConstant(true);
0604:            }
0605:
0606:            /**
0607:             * Determine whether this type or any wrapped type has a constant.
0608:             *
0609:             * @param forward The flag for whether to forward this method across
0610:             *   wrapped types.
0611:             * @return <code>true</code> if this type or any wrapped type has a
0612:             *   constant.
0613:             */
0614:            public boolean hasConstant(boolean forward) {
0615:                return null != constant;
0616:            }
0617:
0618:            /**
0619:             * Get this type's or any wrapped type's constant.  Calling this
0620:             * method on type <code>t</code> is equivalent to:
0621:             * <pre>
0622:             * t.getConstant(true)
0623:             * </pre>
0624:             *
0625:             * @see #getConstant(boolean)
0626:             *
0627:             * @return The constant or <code>null</code> if this type or any
0628:             *   wrapped type does not have a constant.
0629:             */
0630:            public Constant getConstant() {
0631:                return getConstant(true);
0632:            }
0633:
0634:            /**
0635:             * Get this type's or any wrapped type's constant.
0636:             *
0637:             * @param forward The flag for whether to forward this method across
0638:             *   wrapped types.
0639:             * @return The constant or <code>null</code> if this type or any
0640:             *   wrapped type does not have a constant.
0641:             */
0642:            public Constant getConstant(boolean forward) {
0643:                return constant;
0644:            }
0645:
0646:            /**
0647:             * Set this type's constant.
0648:             *
0649:             * @see #constant(Object)
0650:             *
0651:             * @param value The value.
0652:             * @return This type.
0653:             * @throws IllegalStateException Signals that this type is sealed.
0654:             */
0655:            public Type constant(boolean value) {
0656:                return constant(value ? BigInteger.ONE : BigInteger.ZERO);
0657:            }
0658:
0659:            /**
0660:             * Set this type's constant.
0661:             *
0662:             * @param value The value.
0663:             * @return This type.
0664:             * @throws IllegalArgumentException Signals an invalid value.
0665:             * @throws IllegalStateException Signals that this type is sealed.
0666:             */
0667:            public Type constant(Object value) {
0668:                checkNotSealed();
0669:                this .constant = new Constant(value);
0670:                return this ;
0671:            }
0672:
0673:            // =========================================================================
0674:
0675:            /**
0676:             * Determine whether this type or any wrapped type has a shape.
0677:             * Calling this method on type <code>t</code> is equivalent to:
0678:             * <pre>
0679:             * t.hasShape(true)
0680:             * </pre>
0681:             *
0682:             * @see #hasShape(boolean)
0683:             *
0684:             * @return <code>true</code> if this type or any wrapped type has a
0685:             *   shape.
0686:             */
0687:            public boolean hasShape() {
0688:                return hasShape(true);
0689:            }
0690:
0691:            /**
0692:             * Determine whether this type or any wrapped type has a shape.
0693:             *
0694:             * @param forward The flag for whether to forward this method across
0695:             *   wrapped types.
0696:             * @return <code>true</code> if this type or any wrapped type has a
0697:             *   shape.
0698:             */
0699:            public boolean hasShape(boolean forward) {
0700:                return null != shape;
0701:            }
0702:
0703:            /**
0704:             * Get this type's or any wrapped type's shape.  Calling this method
0705:             * on type <code>t</code> is equivalent to:
0706:             * <pre>
0707:             * t.getShape(true)
0708:             * </pre>
0709:             *
0710:             * @see #getShape(boolean)
0711:             *
0712:             * @return The shape or <code>null</code> if this type or any
0713:             *   wrapped type does not have a shape.
0714:             */
0715:            public Reference getShape() {
0716:                return getShape(true);
0717:            }
0718:
0719:            /**
0720:             * Get this type's or any wrapped type's shape.
0721:             *
0722:             * @param forward The flag for whether to forward this method across
0723:             *   wrapped types.
0724:             * @return The shape or <code>null</code> if this type or any
0725:             *   wrapped type does not have a shape.
0726:             */
0727:            public Reference getShape(boolean forward) {
0728:                return shape;
0729:            }
0730:
0731:            /**
0732:             * Set this type's shape to a variable reference with the specified
0733:             * name.
0734:             *
0735:             * @see StaticReference
0736:             * @see DynamicReference
0737:             * @see #shape(Reference)
0738:             *
0739:             * @param isStatic The flag for whether the variable is static.
0740:             * @param name The variable name.
0741:             * @return This type.
0742:             * @throws IllegalStateException Signals that this type is sealed.
0743:             */
0744:            public Type shape(boolean isStatic, String name) {
0745:                if (isStatic) {
0746:                    return shape(new StaticReference(name, resolve()));
0747:                } else {
0748:                    return shape(new DynamicReference(name, resolve()));
0749:                }
0750:            }
0751:
0752:            /**
0753:             * Set this type's shape.
0754:             *
0755:             * @param shape The shape represented as a reference.
0756:             * @return This type.
0757:             * @throws IllegalStateException Signals that this type is sealed.
0758:             */
0759:            public Type shape(Reference shape) {
0760:                checkNotSealed();
0761:                this .shape = shape;
0762:                return this ;
0763:            }
0764:
0765:            // =========================================================================
0766:
0767:            /**
0768:             * Determine whether this type has any attributes.  Note that this
0769:             * method does <em>not</em> check any wrapped types.
0770:             *
0771:             * @return <code>true</code> if this type has any attributes.
0772:             */
0773:            public boolean hasAttributes() {
0774:                return ((null != attributes) && (!attributes.isEmpty()));
0775:            }
0776:
0777:            /**
0778:             * Get this type's attributes.
0779:             *
0780:             * @return This type's attributes.
0781:             */
0782:            public List<Attribute> attributes() {
0783:                if (null == attributes) {
0784:                    return Collections.emptyList();
0785:                } else if (sealed) {
0786:                    return Collections.unmodifiableList(attributes);
0787:                } else {
0788:                    return attributes;
0789:                }
0790:            }
0791:
0792:            // =========================================================================
0793:
0794:            /**
0795:             * Determine whether this type or any wrapped type has the specified
0796:             * attribute.  Calling this method on type <code>t</code> is
0797:             * equivalent to:
0798:             * <pre>
0799:             * t.hasAttribute(att, true)
0800:             * </pre>
0801:             *
0802:             * @see #hasAttribute(Attribute,boolean)
0803:             *
0804:             * @param att The attribute.
0805:             * @return <code>true</code> if this type or any wrapped type has
0806:             *   the attribute.
0807:             */
0808:            public boolean hasAttribute(Attribute att) {
0809:                return hasAttribute(att, true);
0810:            }
0811:
0812:            /**
0813:             * Determine whether this type or any wrapped type has the specified
0814:             * attribute.
0815:             *
0816:             * @param att The attribute.
0817:             * @param forward The flag for whether to forward this method across
0818:             *   wrapped types.
0819:             * @return <code>true</code> if this type or any wrapped type has
0820:             *   the attribute.
0821:             */
0822:            public boolean hasAttribute(Attribute att, boolean forward) {
0823:                return ((null != attributes) && attributes.contains(att));
0824:            }
0825:
0826:            /**
0827:             * Determine whether this type has an attribute with the specified
0828:             * name.  Calling this method on type <code>t</code> is equivalent
0829:             * to:
0830:             * <pre>
0831:             * null != t.getAttribute(name, true)
0832:             * </pre>
0833:             *
0834:             * @see #getAttribute(String,boolean)
0835:             *
0836:             * @param name The name.
0837:             * @return <code>true</code> if this type or any wrapped type has
0838:             *   an attribute with the specified name.
0839:             */
0840:            public boolean hasAttribute(String name) {
0841:                return null != getAttribute(name);
0842:            }
0843:
0844:            /**
0845:             * Determine whether this type has an attribute with the specified
0846:             * name.  Calling this method on type <code>t</code> is equivalent
0847:             * to:
0848:             * <pre>
0849:             * null != t.getAttribute(name, forward)
0850:             * </pre>
0851:             *
0852:             * @link #getAttribute(String,boolean)
0853:             *
0854:             * @param name The name.
0855:             * @param forward The flag for whether to forward this method across
0856:             *   wrapped types.
0857:             * @return <code>true</code> if this type or any wrapped type has
0858:             *   an attribute with the specified name.
0859:             */
0860:            public boolean hasAttribute(String name, boolean forward) {
0861:                return null != getAttribute(name, forward);
0862:            }
0863:
0864:            /**
0865:             * Get the attribute with the specified name.  Calling this method
0866:             * on type <code>t</code> is equivalent to:
0867:             * <pre>
0868:             * t.getAttribute(name, true)
0869:             * </pre>
0870:             *
0871:             * @see #getAttribute(String,boolean)
0872:             *
0873:             * @param name The name.
0874:             * @return An attribute with that name or <code>null</code> if this
0875:             *   type or any wrapped type does not have such an attribute.
0876:             */
0877:            public Attribute getAttribute(String name) {
0878:                return getAttribute(name, true);
0879:            }
0880:
0881:            /**
0882:             * Get the attribute with the specified name.
0883:             *
0884:             * @param name The name.
0885:             * @param forward The flag for whether to forward this method across
0886:             *   wrapped types.
0887:             * @return An attribute with the name or <code>null</code> if this
0888:             *   or any wrapped type does not have such an attribute.
0889:             */
0890:            public Attribute getAttribute(String name, boolean forward) {
0891:                return Attribute.get(name, attributes);
0892:            }
0893:
0894:            // =========================================================================
0895:
0896:            /**
0897:             * Add the specified attribute.  This method adds the specified
0898:             * attribute to this type's list of attributes &mdash; without
0899:             * checking whether the type already has that attribute.  For almost
0900:             * all applications of attributes, it is preferable to use {@link
0901:             * #attribute(Attribute)}, {@link #attribute(List)}, or {@link
0902:             * #attribute(Type)}.
0903:             *
0904:             * @param att The new attribute.
0905:             * @throws IllegalStateException Signals that this type is sealed.
0906:             */
0907:            public void addAttribute(Attribute att) {
0908:                checkNotSealed();
0909:                if (null == attributes)
0910:                    attributes = new ArrayList<Attribute>();
0911:                attributes.add(att);
0912:            }
0913:
0914:            /**
0915:             * Remove the specified attribute.  Note that this method does
0916:             * <em>not</em> remove the attribute from any wrapped types.
0917:             *
0918:             * @param att The attribute.
0919:             * @return <code>true</code> if this type had the specified
0920:             *   attribute.
0921:             * @throws IllegalStateException Signals that this type is sealed.
0922:             */
0923:            public boolean removeAttribute(Attribute att) {
0924:                checkNotSealed();
0925:                return null != attributes ? attributes.remove(att) : false;
0926:            }
0927:
0928:            // =========================================================================
0929:
0930:            /**
0931:             * Annotate this type with the specified attribute.  If this type or
0932:             * any wrapped type does not have the specified attribute, this
0933:             * method adds the attribute to this type's list of attributes.
0934:             *
0935:             * @param att The attribute.
0936:             * @return This type.
0937:             * @throws IllegalStateException Signals that this type is sealed.
0938:             */
0939:            public Type attribute(Attribute att) {
0940:                if (!hasAttribute(att)) {
0941:                    addAttribute(att);
0942:                }
0943:                return this ;
0944:            }
0945:
0946:            /**
0947:             * Annotate this type with the specified attributes.
0948:             *
0949:             * @see #attribute(Attribute)
0950:             *
0951:             * @param attributes The attributes.
0952:             * @return This type.
0953:             * @throws IllegalStateException Signals that this type is sealed.
0954:             */
0955:            public Type attribute(List<Attribute> attributes) {
0956:                for (Attribute att : attributes) {
0957:                    if (!hasAttribute(att))
0958:                        addAttribute(att);
0959:                }
0960:                return this ;
0961:            }
0962:
0963:            /**
0964:             * Annotate this type with the specified type's attributes.
0965:             *
0966:             * @param template The type whose annotations to copy.
0967:             * @return This type.
0968:             * @throws IllegalStateException Signals that this type is sealed.
0969:             */
0970:            public Type attribute(Type template) {
0971:                do {
0972:                    // If the template has any attributes, copy them.
0973:                    if (template.hasAttributes()) {
0974:                        for (Attribute att : template.attributes()) {
0975:                            if (!hasAttribute(att))
0976:                                addAttribute(att);
0977:                        }
0978:                    }
0979:
0980:                    // If the template is a wrapped type, continue with the wrapped type.
0981:                    template = template.isWrapped() ? template.toWrapped()
0982:                            .getType() : null;
0983:                } while (null != template);
0984:
0985:                // Done.
0986:                return this ;
0987:            }
0988:
0989:            // =========================================================================
0990:
0991:            /**
0992:             * Mark the specified node as having this type.  This method sets
0993:             * the node's {@link Constants#TYPE type property} to this type.
0994:             *
0995:             * @param node The node.
0996:             * @throws IllegalArgumentException Signals that the node already
0997:             *   has a type property.
0998:             */
0999:            public void mark(Node node) {
1000:                if (node.hasProperty(Constants.TYPE)) {
1001:                    throw new IllegalArgumentException("Node " + node
1002:                            + " already has type");
1003:                } else {
1004:                    node.setProperty(Constants.TYPE, this );
1005:                }
1006:            }
1007:
1008:            // =========================================================================
1009:
1010:            /**
1011:             * Determine whether this type has the specified tag.  Invocations
1012:             * to this method are forwarded across wrapped types.  Calling this
1013:             * method on type <code>t</code> is equivalent to:
1014:             * <pre>
1015:             * tag == t.tag()
1016:             * </pre>
1017:             *
1018:             * @see #tag()
1019:             *
1020:             * @param tag The tag.
1021:             * @return <code>true</code> if this type has the specified tag.
1022:             */
1023:            public boolean hasTag(Tag tag) {
1024:                return tag == tag();
1025:            }
1026:
1027:            /**
1028:             * Get this type's tag.  Invocations to this method are forwarded
1029:             * across wrapped types.
1030:             *
1031:             * @see #wtag()
1032:             *
1033:             * @return This type's tag.
1034:             */
1035:            public abstract Tag tag();
1036:
1037:            /**
1038:             * Determine whether this wrapped type has the specified tag.
1039:             * Invocations to this method are <em>not</em> forwarded across
1040:             * wrapped types.  Calling this method on type <code>t</code> is
1041:             * equivalent to:
1042:             * <pre>
1043:             * tag == wtag()
1044:             * </pre>
1045:             *
1046:             * @see #wtag()
1047:             *
1048:             * @param tag The tag.
1049:             * @return <code>true</code> if this wrapped type has the specified
1050:             *   tag.
1051:             */
1052:            public boolean hasWTag(Tag tag) {
1053:                return tag == wtag();
1054:            }
1055:
1056:            /**
1057:             * Get this wrapped type's tag.  Invocations to this method are
1058:             * <em>not</em> forwarded across wrapped types.
1059:             *
1060:             * @see #tag()
1061:             *
1062:             * @return This wrapped type's tag.
1063:             */
1064:            public Tag wtag() {
1065:                return tag();
1066:            }
1067:
1068:            // =========================================================================
1069:
1070:            /**
1071:             * Determine whether this type is an error.
1072:             *
1073:             * @link #hasError()
1074:             *
1075:             * @return <code>true</code> if this type is internal.
1076:             */
1077:            public boolean isError() {
1078:                return false;
1079:            }
1080:
1081:            /**
1082:             * Determine whether this type has an error.  This method identifies
1083:             * the {@link ErrorT error type} even if it is wrapped.  Calling this
1084:             * method on type <code>t</code> is equivalent to:
1085:             * <pre>
1086:             * Type.Tag.Error == tag()
1087:             * </pre>
1088:             *
1089:             * @see #tag()
1090:             *
1091:             * @return <code>true</code> if this type has an error.
1092:             */
1093:            public boolean hasError() {
1094:                return Tag.ERROR == tag();
1095:            }
1096:
1097:            // =========================================================================
1098:
1099:            /**
1100:             * Determine whether this type is a type parameter.
1101:             *
1102:             * @return <code>true</code> if this type is a parameter.
1103:             */
1104:            public boolean isParameter() {
1105:                return false;
1106:            }
1107:
1108:            /**
1109:             * Get this type as a type parameter.
1110:             *
1111:             * @return This type as a parameter.
1112:             * @throws ClassCastException Signals that this type is not a
1113:             *   parameter.
1114:             */
1115:            public Parameter toParameter() {
1116:                throw new ClassCastException("Not a parameter " + this );
1117:            }
1118:
1119:            /**
1120:             * Determine whether this type is a wildcard.
1121:             *
1122:             * @return <code>true</code> if this type is a wildcard.
1123:             */
1124:            public boolean isWildcard() {
1125:                return false;
1126:            }
1127:
1128:            /**
1129:             * Get this type as a wildcard.
1130:             *
1131:             * @return This type as a wildcard.
1132:             * @throws ClassCastException Signals that this type is not a
1133:             *   wildcard.
1134:             */
1135:            public Wildcard toWildcard() {
1136:                throw new ClassCastException("Not a wildcard " + this );
1137:            }
1138:
1139:            /**
1140:             * Determine whether this type is void.
1141:             *
1142:             * @return <code>true</code> if this type is void.
1143:             */
1144:            public boolean isVoid() {
1145:                return false;
1146:            }
1147:
1148:            /**
1149:             * Get this type as a void type.
1150:             *
1151:             * @return This type as a void type.
1152:             * @throws ClassCastException Signals that this type is not a void
1153:             *   type.
1154:             */
1155:            public VoidT toVoid() {
1156:                throw new ClassCastException("Not a void " + this );
1157:            }
1158:
1159:            /**
1160:             * Determine whether this type is the unit type.
1161:             *
1162:             * @return <code>true</code> if this type is the unit type.
1163:             */
1164:            public boolean isUnit() {
1165:                return false;
1166:            }
1167:
1168:            /**
1169:             * Get this type as a unit type.
1170:             *
1171:             * @return This type as a unit type.
1172:             * @throws ClassCastException Signals that this type is not a unit
1173:             *   type.
1174:             */
1175:            public UnitT toUnit() {
1176:                throw new ClassCastException("Not a unit " + this );
1177:            }
1178:
1179:            /**
1180:             * Determine whether this type is a boolean.
1181:             *
1182:             * @return <code>true</code> if this type is a boolean.
1183:             */
1184:            public boolean isBoolean() {
1185:                return false;
1186:            }
1187:
1188:            /**
1189:             * Get this type as a boolean.
1190:             *
1191:             * @return This type as a boolean.
1192:             * @throws ClassCastException Signals that this type is a not a
1193:             *   boolean.
1194:             */
1195:            public BooleanT toBoolean() {
1196:                throw new ClassCastException("Not a boolean " + this );
1197:            }
1198:
1199:            /**
1200:             * Determine whether this type is a number.
1201:             *
1202:             * @return <code>true</code> if this type is a number.
1203:             */
1204:            public boolean isNumber() {
1205:                return false;
1206:            }
1207:
1208:            /**
1209:             * Get this type as a number.
1210:             *
1211:             * @return This type as a number.
1212:             * @throws ClassCastException Signals that this type is not a
1213:             *   number.
1214:             */
1215:            public NumberT toNumber() {
1216:                throw new ClassCastException("Not a number " + this );
1217:            }
1218:
1219:            /**
1220:             * Determine whether this type is an integer.
1221:             *
1222:             * @return <code>true</code> if this type is an integer.
1223:             */
1224:            public boolean isInteger() {
1225:                return false;
1226:            }
1227:
1228:            /**
1229:             * Get this type as an integer.
1230:             *
1231:             * @return This type as an integer.
1232:             * @throws ClassCastException Signals that this type is not an
1233:             *   integer.
1234:             */
1235:            public IntegerT toInteger() {
1236:                throw new ClassCastException("Not an integer " + this );
1237:            }
1238:
1239:            /**
1240:             * Determine whether this type is a float.
1241:             *
1242:             * @return <code>true</code> if this type is a float.
1243:             */
1244:            public boolean isFloat() {
1245:                return false;
1246:            }
1247:
1248:            /**
1249:             * Get this type as a float.
1250:             *
1251:             * @return This type as a float.
1252:             * @throws ClassCastException Signals that this type is not a
1253:             *   float.
1254:             */
1255:            public FloatT toFloat() {
1256:                throw new ClassCastException("Not a float " + this );
1257:            }
1258:
1259:            /**
1260:             * Determine whether this type is internal.
1261:             *
1262:             * @return <code>true</code> if this type is internal.
1263:             */
1264:            public boolean isInternal() {
1265:                return false;
1266:            }
1267:
1268:            /**
1269:             * Get this type as an internal type.
1270:             *
1271:             * @return This type as an internal type.
1272:             * @throws ClassCastException Signals that this type is not an
1273:             *   internal type.
1274:             */
1275:            public InternalT toInternal() {
1276:                throw new ClassCastException("Not an internal type " + this );
1277:            }
1278:
1279:            /**
1280:             * Determine whether this type is a label.
1281:             *
1282:             * @return <code>true</code> if this type is a label.
1283:             */
1284:            public boolean isLabel() {
1285:                return false;
1286:            }
1287:
1288:            /**
1289:             * Get this type as a label.
1290:             *
1291:             * @return This type as a label.
1292:             * @throws ClassCastException Signals that this type is not a
1293:             *   label.
1294:             */
1295:            public LabelT toLabel() {
1296:                throw new ClassCastException("Not a label " + this );
1297:            }
1298:
1299:            /**
1300:             * Determine whether this type is a package.
1301:             *
1302:             * @return <code>true</code> if this type is a package.
1303:             */
1304:            public boolean isPackage() {
1305:                return false;
1306:            }
1307:
1308:            /**
1309:             * Get this type as a package.
1310:             *
1311:             * @return This type as a package.
1312:             * @throws ClassCastException Signals that this type is not a
1313:             *   package.
1314:             */
1315:            public PackageT toPackage() {
1316:                throw new ClassCastException("Not a package " + this );
1317:            }
1318:
1319:            /**
1320:             * Determine whether this type is derived.
1321:             *
1322:             * @return <code>true</code> if this type is derived.
1323:             */
1324:            public boolean isDerived() {
1325:                return false;
1326:            }
1327:
1328:            /**
1329:             * Determine whether this type is a pointer.
1330:             *
1331:             * @return <code>true</code> if this type is a pointer.
1332:             */
1333:            public boolean isPointer() {
1334:                return false;
1335:            }
1336:
1337:            /**
1338:             * Get this type as a pointer.
1339:             *
1340:             * @return This type as a pointer.
1341:             * @throws ClassCastException Signals that this type is not a
1342:             *   pointer.
1343:             */
1344:            public PointerT toPointer() {
1345:                throw new ClassCastException("Not a pointer " + this );
1346:            }
1347:
1348:            /**
1349:             * Determine whether this type is an array.
1350:             *
1351:             * @return <code>true</code> if this type is an array.
1352:             */
1353:            public boolean isArray() {
1354:                return false;
1355:            }
1356:
1357:            /**
1358:             * Get this type as an array.
1359:             *
1360:             * @return This type as an array.
1361:             * @throws ClassCastException Signals that this type is not an
1362:             *   array.
1363:             */
1364:            public ArrayT toArray() {
1365:                throw new ClassCastException("Not an array " + this );
1366:            }
1367:
1368:            /**
1369:             * Determine whether this type contains a struct or union.
1370:             *
1371:             * @return <code>true</code> if this type contains a struct or
1372:             *   union.
1373:             */
1374:            public boolean hasStructOrUnion() {
1375:                switch (tag()) {
1376:                case STRUCT:
1377:                case UNION:
1378:                    return true;
1379:                default:
1380:                    return false;
1381:                }
1382:            }
1383:
1384:            /**
1385:             * Determine whether this type is a struct.
1386:             *
1387:             * @return <code>true</code> if this type is a struct.
1388:             */
1389:            public boolean isStruct() {
1390:                return false;
1391:            }
1392:
1393:            /**
1394:             * Get this type as a struct.
1395:             *
1396:             * @return This type as a struct.
1397:             * @throws ClassCastException Signas that this type is not a
1398:             *    struct.
1399:             */
1400:            public StructT toStruct() {
1401:                throw new ClassCastException("Not a struct " + this );
1402:            }
1403:
1404:            /**
1405:             * Determine whether this type is a union.
1406:             *
1407:             * @return <code>true</code> if this type is a union.
1408:             */
1409:            public boolean isUnion() {
1410:                return false;
1411:            }
1412:
1413:            /**
1414:             * Get this type as a union.
1415:             *
1416:             * @return This type as a union.
1417:             * @throws ClassCastException Signals that this type is not a
1418:             *   union.
1419:             */
1420:            public UnionT toUnion() {
1421:                throw new ClassCastException("Not a union " + this );
1422:            }
1423:
1424:            /**
1425:             * Determine whether this type is a function.
1426:             *
1427:             * @return <code>true</code> if this type is a function.
1428:             */
1429:            public boolean isFunction() {
1430:                return false;
1431:            }
1432:
1433:            /**
1434:             * Get this type as a function.
1435:             *
1436:             * @return This type has a function.
1437:             * @throws ClassCastException Signals that this type is not a
1438:             *   function.
1439:             */
1440:            public FunctionT toFunction() {
1441:                throw new ClassCastException("Not a function " + this );
1442:            }
1443:
1444:            /**
1445:             * Determine whether this type is a method.
1446:             *
1447:             * @return <code>true</code> if this type is a method.
1448:             */
1449:            public boolean isMethod() {
1450:                return false;
1451:            }
1452:
1453:            /**
1454:             * Get this type as a method.
1455:             *
1456:             * @return This type as a method.
1457:             * @throws ClassCastException Signals that this type is not a
1458:             *   method.
1459:             */
1460:            public MethodT toMethod() {
1461:                throw new ClassCastException("Not a method " + this );
1462:            }
1463:
1464:            /**
1465:             * Determine whether this type is a class.
1466:             *
1467:             * @return <code>true</code> if this type is a class.
1468:             */
1469:            public boolean isClass() {
1470:                return false;
1471:            }
1472:
1473:            /**
1474:             * Get this type as a class.
1475:             *
1476:             * @return This type as a class.
1477:             * @throws ClassCastException Signals that this type is not a class.
1478:             */
1479:            public ClassT toClass() {
1480:                throw new ClassCastException("Not a class " + this );
1481:            }
1482:
1483:            /**
1484:             * Determine whether this type is an interface.
1485:             *
1486:             * @return <code>true</code> if this type is an interface.
1487:             */
1488:            public boolean isInterface() {
1489:                return false;
1490:            }
1491:
1492:            /**
1493:             * Get this type as an interface.
1494:             *
1495:             * @return This type as an interface.
1496:             * @throws ClassCastException Signals that this type is not an
1497:             *   interface.
1498:             */
1499:            public InterfaceT toInterface() {
1500:                throw new ClassCastException("Not an interface " + this );
1501:            }
1502:
1503:            /**
1504:             * Determine whether this type is an tuple.
1505:             *
1506:             * @return <code>true</code> if this type is an tuple.
1507:             */
1508:            public boolean isTuple() {
1509:                return false;
1510:            }
1511:
1512:            /**
1513:             * Get this type as an tuple.
1514:             *
1515:             * @return This type as an tuple.
1516:             * @throws ClassCastException Signals that this type is not an tuple.
1517:             */
1518:            public TupleT toTuple() {
1519:                throw new ClassCastException("Not an tuple " + this );
1520:            }
1521:
1522:            /**
1523:             * Determine whether this type is an variant.
1524:             *
1525:             * @return <code>true</code> if this type is an variant.
1526:             */
1527:            public boolean isVariant() {
1528:                return false;
1529:            }
1530:
1531:            /**
1532:             * Get this type as an variant.
1533:             *
1534:             * @return This type as an variant.
1535:             * @throws ClassCastException Signals that this type is not an variant.
1536:             */
1537:            public VariantT toVariant() {
1538:                throw new ClassCastException("Not an variant " + this );
1539:            }
1540:
1541:            // =========================================================================
1542:
1543:            /**
1544:             * Determine whether this type is wrapped.
1545:             *
1546:             * @return <code>true</code> if this type is wrapped.
1547:             */
1548:            public boolean isWrapped() {
1549:                return false;
1550:            }
1551:
1552:            /**
1553:             * Get this type as a wrapped type.
1554:             *
1555:             * @return This type as a wrapped type.
1556:             * @throws ClassCastException Signals that this type is not wrapped.
1557:             */
1558:            public WrappedT toWrapped() {
1559:                throw new ClassCastException("Not a wrapped type " + this );
1560:            }
1561:
1562:            // =========================================================================
1563:
1564:            /**
1565:             * Determine whether this type is annotated.
1566:             *
1567:             * @return <code>true</code> if this type is annotated.
1568:             */
1569:            public boolean isAnnotated() {
1570:                return false;
1571:            }
1572:
1573:            /**
1574:             * Determine whether this type has an annotated type.
1575:             *
1576:             * @return <code>true</code> if this type has an annotated type.
1577:             */
1578:            public boolean hasAnnotated() {
1579:                return false;
1580:            }
1581:
1582:            /**
1583:             * Get this type as an annotated type.
1584:             *
1585:             * @return This type as an annotated type.
1586:             * @throws ClassCastException Signas that this type is not an
1587:             *   annotated type.
1588:             */
1589:            public AnnotatedT toAnnotated() {
1590:                throw new ClassCastException("Not an annotated type " + this );
1591:            }
1592:
1593:            /**
1594:             * Determine whether this type is an alias.
1595:             *
1596:             * @return <code>true</code> if this type is an alias.
1597:             */
1598:            public boolean isAlias() {
1599:                return false;
1600:            }
1601:
1602:            /**
1603:             * Determine whether this type contains an alias.
1604:             *
1605:             * @return <code>true</code> if this type contains an alias.
1606:             */
1607:            public boolean hasAlias() {
1608:                return false;
1609:            }
1610:
1611:            /**
1612:             * Get this type as an alias.
1613:             *
1614:             * @return This type as an alias.
1615:             * @throws ClassCastException Signals that this type is not an
1616:             *   alias.
1617:             */
1618:            public AliasT toAlias() {
1619:                throw new ClassCastException("Not an alias " + this );
1620:            }
1621:
1622:            /**
1623:             * Determine whether this type is an enum.
1624:             *
1625:             * @return <code>true</code> if this type is an enum.
1626:             */
1627:            public boolean isEnum() {
1628:                return false;
1629:            }
1630:
1631:            /**
1632:             * Determine whether this type contains an enum.
1633:             *
1634:             * @return <code>true</code> if this type contains an enum.
1635:             */
1636:            public boolean hasEnum() {
1637:                return false;
1638:            }
1639:
1640:            /**
1641:             * Get this type as an enum.
1642:             *
1643:             * @return This type as an enum.
1644:             * @throws ClassCastException Signals that this type is not an enum.
1645:             */
1646:            public EnumT toEnum() {
1647:                throw new ClassCastException("Not an enum " + this );
1648:            }
1649:
1650:            /**
1651:             * Determine whether this type is an enumerator.
1652:             *
1653:             * @return <code>true</code> if this type is an enumerator.
1654:             */
1655:            public boolean isEnumerator() {
1656:                return false;
1657:            }
1658:
1659:            /**
1660:             * Determine whether this type contains an enumerator.
1661:             *
1662:             * @return <code>true</code> if this type contains an enumerator.
1663:             */
1664:            public boolean hasEnumerator() {
1665:                return false;
1666:            }
1667:
1668:            /**
1669:             * Get this type as an enumerator.
1670:             *
1671:             * @return This type as an enumerator.
1672:             * @throws ClassCastException Signals that this type is not an
1673:             *   enumerator.
1674:             */
1675:            public EnumeratorT toEnumerator() {
1676:                throw new ClassCastException("Not an enumerator " + this );
1677:            }
1678:
1679:            /**
1680:             * Determine whether this type is instantiated.
1681:             *
1682:             * @return <code>true</code> if this type is instantiated.
1683:             */
1684:            public boolean isInstantiated() {
1685:                return false;
1686:            }
1687:
1688:            /**
1689:             * Determine whether this type has an instantiated type.
1690:             *
1691:             * @return <code>true</code> if this type has an instantiated type.
1692:             */
1693:            public boolean hasInstantiated() {
1694:                return false;
1695:            }
1696:
1697:            /**
1698:             * Get this type as an instantiated type.
1699:             *
1700:             * @return This type as an instantiated type.
1701:             * @throws ClassCastException Signas that this type is not an
1702:             *   instantiated type.
1703:             */
1704:            public InstantiatedT toInstantiated() {
1705:                throw new ClassCastException("Not an instantiated type " + this );
1706:            }
1707:
1708:            /**
1709:             * Determine whether this type is parameterized.
1710:             *
1711:             * @return <code>true</code> if this type is parameterized.
1712:             */
1713:            public boolean isParameterized() {
1714:                return false;
1715:            }
1716:
1717:            /**
1718:             * Determine whether this type has a parameterized type.
1719:             *
1720:             * @return <code>true</code> if this type has a parameterized type.
1721:             */
1722:            public boolean hasParameterized() {
1723:                return false;
1724:            }
1725:
1726:            /**
1727:             * Get this type as a parameterized type.
1728:             *
1729:             * @return This type as a parameterized type.
1730:             * @throws ClassCastException Signas that this type is not a
1731:             *   parameterized type.
1732:             */
1733:            public ParameterizedT toParameterized() {
1734:                throw new ClassCastException("Not a parameterized type " + this );
1735:            }
1736:
1737:            /**
1738:             * Determine whether this type is a variable.
1739:             *
1740:             * @return <code>true</code> if this type is a variable.
1741:             */
1742:            public boolean isVariable() {
1743:                return false;
1744:            }
1745:
1746:            /**
1747:             * Determine whether this type contains a variable.
1748:             *
1749:             * @return <code>true</code> if this type contains a variable.
1750:             */
1751:            public boolean hasVariable() {
1752:                return false;
1753:            }
1754:
1755:            /**
1756:             * Get this type as a variable.
1757:             *
1758:             * @return This type as a variable.
1759:             * @throws ClassCastException Signals that this type does not
1760:             *   contain a variable.
1761:             */
1762:            public VariableT toVariable() {
1763:                throw new ClassCastException("Not a variable " + this );
1764:            }
1765:
1766:            // =========================================================================
1767:
1768:            /**
1769:             * Determine whether this type is tagged.
1770:             *
1771:             * @return <code>true</code> if this type is tagged.
1772:             */
1773:            public boolean hasTagged() {
1774:                return false;
1775:            }
1776:
1777:            /**
1778:             * Get this type as a tagged type.
1779:             *
1780:             * @see #hasTagged()
1781:             *
1782:             * @return This type as a tagged type.
1783:             * @throws ClassCastException Signals that this type is not
1784:             *   tagged.
1785:             */
1786:            public Tagged toTagged() {
1787:                throw new ClassCastException("Not a tagged type " + this );
1788:            }
1789:
1790:            // =========================================================================
1791:
1792:            /**
1793:             * Determine whether this type is concrete.  This method returns
1794:             * <code>true</code> if this type is not parameterized or is both
1795:             * parameterized and instantiated.
1796:             *
1797:             * @return <code>true</code> if this type is concrete.
1798:             */
1799:            public boolean isConcrete() {
1800:                return (!hasParameterized()) || hasInstantiated();
1801:            }
1802:
1803:            // =========================================================================
1804:
1805:            /**
1806:             * Resolve this type.  This method removes any symbolic information,
1807:             * i.e., wrapped types, and returns the underlying, "raw" type.
1808:             *
1809:             * @return The resolved type.
1810:             */
1811:            public Type resolve() {
1812:                return this ;
1813:            }
1814:
1815:            // =========================================================================
1816:
1817:            /**
1818:             * Trace this type to the runtime's console.  This method prints
1819:             * this type to the runtime's console using a new instance of {@link
1820:             * TypePrinter}; it is useful for debugging.
1821:             *
1822:             * @param runtime The runtime.
1823:             */
1824:            public void trace(Runtime runtime) {
1825:                // Save the registered visitor.
1826:                Visitor visitor = runtime.console().visitor();
1827:                TypePrinter printer = new TypePrinter(runtime.console());
1828:                try {
1829:                    printer.dispatch(this );
1830:                    runtime.console().pln();
1831:                } finally {
1832:                    // Restore the previously registered visitor.
1833:                    runtime.console().register(visitor);
1834:                }
1835:                runtime.console().flush();
1836:            }
1837:
1838:            // =========================================================================
1839:
1840:            /**
1841:             * Cast the specified object to a type.
1842:             *
1843:             * @param type The type as an object.
1844:             * @return The type as a type.
1845:             * @throws ClassCastException Signals that the specified object is
1846:             *   not a type.
1847:             */
1848:            public static Type cast(Object type) {
1849:                return (Type) type;
1850:            }
1851:
1852:            /**
1853:             * Resolve the specified object as type.
1854:             *
1855:             * @param type The type.
1856:             * @return The resolved type.
1857:             * @throws ClassCastException Signals that the specified object is
1858:             *   not a type.
1859:             */
1860:            public static Type resolve(Object type) {
1861:                return ((Type) type).resolve();
1862:            }
1863:
1864:            // =========================================================================
1865:
1866:            /**
1867:             * Copy the specified list of types.  A null list is ignored.
1868:             *
1869:             * @param types The list of types.
1870:             * @return A new list of the types' copies.
1871:             */
1872:            @SuppressWarnings("unchecked")
1873:            public static <T extends Type> List<T> copy(List<T> types) {
1874:                if (null == types)
1875:                    return null;
1876:
1877:                List<T> copy = new ArrayList<T>(types.size());
1878:                for (T t : types) {
1879:                    // This cast can never fail in the presence of covariant return
1880:                    // types for copy().
1881:                    copy.add((T) t.copy());
1882:                }
1883:                return copy;
1884:            }
1885:
1886:            /**
1887:             * Seal the specified list of types.  A null list is ignored.
1888:             *
1889:             * @param types The list of types.
1890:             * @return An unmodifiable list of sealed types.
1891:             */
1892:            public static <T extends Type> List<T> seal(List<T> types) {
1893:                if (null == types)
1894:                    return null;
1895:
1896:                for (T t : types)
1897:                    t.seal();
1898:                return Collections.unmodifiableList(types);
1899:            }
1900:
1901:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.