00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 #include "comma/ast/AstResource.h"
00010 #include "comma/ast/Decl.h"
00011 #include "comma/ast/Type.h"
00012 
00013 #include "llvm/ADT/Twine.h"
00014 
00015 #include <algorithm>
00016 #include <iostream>
00017 
00018 using namespace comma;
00019 using llvm::cast;
00020 using llvm::dyn_cast;
00021 using llvm::isa;
00022 
00023 
00024 
00025 
00026 bool Type::memberOf(Classification ID) const
00027 {
00028     switch (ID) {
00029     default:
00030         assert(false && "Bad classification ID!");
00031         return false;
00032     case CLASS_Scalar:
00033         return isScalarType();
00034     case CLASS_Discrete:
00035         return isDiscreteType();
00036     case CLASS_Enum:
00037         return isEnumType();
00038     case CLASS_Integer:
00039         return isIntegerType() || isUniversalIntegerType();
00040     case CLASS_Composite:
00041         return isCompositeType();
00042     case CLASS_Array:
00043         return isArrayType();
00044     case CLASS_String:
00045         return isStringType();
00046     case CLASS_Access:
00047         return isAccessType() || isUniversalAccessType();
00048     case CLASS_Record:
00049         return isRecordType();
00050     }
00051 }
00052 
00053 bool Type::isScalarType() const
00054 {
00055     
00056     return isDiscreteType();
00057 }
00058 
00059 bool Type::isDiscreteType() const
00060 {
00061     return isIntegerType() || isEnumType();
00062 }
00063 
00064 bool Type::isIntegerType() const
00065 {
00066     return isa<IntegerType>(this);
00067 }
00068 
00069 bool Type::isEnumType() const
00070 {
00071     return isa<EnumerationType>(this);
00072 }
00073 
00074 bool Type::isCompositeType() const
00075 {
00076     return this->denotesCompositeType();
00077 }
00078 
00079 bool Type::isArrayType() const
00080 {
00081     return isa<ArrayType>(this);
00082 }
00083 
00084 bool Type::isRecordType() const
00085 {
00086     return isa<RecordType>(this);
00087 }
00088 
00089 bool Type::isStringType() const
00090 {
00091     const ArrayType *arrTy = const_cast<Type*>(this)->getAsArrayType();
00092     if (arrTy && arrTy->isVector()) {
00093         EnumerationType *enumTy = arrTy->getComponentType()->getAsEnumType();
00094         return enumTy && enumTy->isCharacterType();
00095     }
00096     return false;
00097 }
00098 
00099 bool Type::isAccessType() const
00100 {
00101     return isa<AccessType>(this);
00102 }
00103 
00104 bool Type::isFatAccessType() const
00105 {
00106     if (const AccessType *access = dyn_cast<AccessType>(this))
00107         return access->getTargetType()->isIndefiniteType();
00108     return false;
00109 }
00110 
00111 bool Type::isThinAccessType() const
00112 {
00113     if (const AccessType *access = dyn_cast<AccessType>(this))
00114         return !access->getTargetType()->isIndefiniteType();
00115     return false;
00116 }
00117 
00118 bool Type::isUniversalType() const
00119 {
00120     return isa<UniversalType>(this);
00121 }
00122 
00123 bool Type::isUniversalIntegerType() const
00124 {
00125     if (const UniversalType *univTy = dyn_cast<UniversalType>(this))
00126         return univTy->isUniversalIntegerType();
00127     return false;
00128 }
00129 
00130 bool Type::isUniversalAccessType() const
00131 {
00132     if (const UniversalType *univTy = dyn_cast<UniversalType>(this))
00133         return univTy->isUniversalAccessType();
00134     return false;
00135 }
00136 
00137 bool Type::isUniversalFixedType() const
00138 {
00139     if (const UniversalType *univTy = dyn_cast<UniversalType>(this))
00140         return univTy->isUniversalFixedType();
00141     return false;
00142 }
00143 
00144 bool Type::isUniversalRealType() const
00145 {
00146     if (const UniversalType *univTy = dyn_cast<UniversalType>(this))
00147         return univTy->isUniversalRealType();
00148     return false;
00149 }
00150 
00151 bool Type::isUniversalTypeOf(const Type *type) const
00152 {
00153     if (type->isUniversalIntegerType())
00154         return type->memberOf(CLASS_Integer);
00155     if (type->isUniversalAccessType())
00156         return type->memberOf(CLASS_Access);
00157     if (type->isUniversalFixedType() || type->isUniversalRealType())
00158         assert(false && "Cannot handle this kind of universal type yet!");
00159 
00160     return false;
00161 }
00162 
00163 ArrayType *Type::getAsArrayType()
00164 {
00165     return dyn_cast<ArrayType>(this);
00166 }
00167 
00168 IntegerType *Type::getAsIntegerType()
00169 {
00170     return dyn_cast<IntegerType>(this);
00171 }
00172 
00173 EnumerationType *Type::getAsEnumType()
00174 {
00175     return dyn_cast<EnumerationType>(this);
00176 }
00177 
00178 bool Type::involvesPercent() const
00179 {
00180     if (const DomainType *domTy = dyn_cast<DomainType>(this)) {
00181         if (domTy->denotesPercent())
00182             return true;
00183 
00184         if (const DomainInstanceDecl *instance = domTy->getInstanceDecl()) {
00185             unsigned arity = instance->getArity();
00186             for (unsigned i = 0; i < arity; ++i) {
00187                 const DomainType *param = instance->getActualParamType(i);
00188                 if (param->involvesPercent())
00189                     return true;
00190             }
00191         }
00192         return false;
00193     }
00194 
00195     if (const ArrayType *arrTy = dyn_cast<ArrayType>(this))
00196         return arrTy->getComponentType()->involvesPercent();
00197 
00198     if (const SubroutineType *subTy = dyn_cast<SubroutineType>(this)) {
00199         SubroutineType::arg_type_iterator I = subTy->begin();
00200         SubroutineType::arg_type_iterator E = subTy->end();
00201         for ( ; I != E; ++I) {
00202             const Type *argTy = *I;
00203             if (argTy->involvesPercent())
00204                 return true;
00205         }
00206 
00207         if (const FunctionType *fnTy = dyn_cast<FunctionType>(subTy))
00208             return fnTy->getReturnType()->involvesPercent();
00209     }
00210 
00211     if (const RecordType *recordTy = dyn_cast<RecordType>(this)) {
00212         unsigned components = recordTy->numComponents();
00213         for (unsigned i = 0; i < components; ++i) {
00214             if (recordTy->getComponentType(i)->involvesPercent())
00215                 return true;
00216         }
00217         return false;
00218     }
00219 
00220     return false;
00221 }
00222 
00223 bool Type::isIndefiniteType() const
00224 {
00225     if (const ArrayType *arrTy = dyn_cast<ArrayType>(this))
00226         return arrTy->isUnconstrained() || !arrTy->isStaticallyConstrained();
00227     return false;
00228 }
00229 
00230 
00231 
00232 
00233 SubroutineType::SubroutineType(AstKind kind, Type **argTypes, unsigned numArgs)
00234     : Type(kind),
00235       argumentTypes(0),
00236       numArguments(numArgs)
00237 {
00238     assert(this->denotesSubroutineType());
00239     if (numArgs > 0) {
00240         argumentTypes = new Type*[numArgs];
00241         std::copy(argTypes, argTypes + numArgs, argumentTypes);
00242     }
00243 }
00244 
00245 
00246 
00247 
00248 UniversalType *UniversalType::universal_integer = 0;
00249 UniversalType *UniversalType::universal_access  = 0;
00250 UniversalType *UniversalType::universal_fixed   = 0;
00251 UniversalType *UniversalType::universal_real    = 0;
00252 
00253 
00254 
00255 
00256 IdentifierInfo *IncompleteType::getIdInfo() const
00257 {
00258     if (IncompleteTypeDecl *decl = definingDecl.dyn_cast<IncompleteTypeDecl*>())
00259         return decl->getIdInfo();
00260     return definingDecl.get<IdentifierInfo*>();
00261 }
00262 
00263 IncompleteTypeDecl *IncompleteType::getDefiningDecl()
00264 {
00265     IncompleteType *rootType = getRootType();
00266     return rootType->definingDecl.get<IncompleteTypeDecl*>();
00267 }
00268 
00269 bool IncompleteType::hasCompletion() const
00270 {
00271     return getDefiningDecl()->hasCompletion();
00272 }
00273 
00274 PrimaryType *IncompleteType::getCompleteType()
00275 {
00276     assert(hasCompletion() && "Type does not have a completion!");
00277     return getDefiningDecl()->getCompletion()->getType();
00278 }
00279 
00280 
00281 
00282 
00283 DomainType::DomainType(DomainTypeDecl *DTDecl)
00284     : PrimaryType(AST_DomainType, 0, false),
00285       definingDecl(DTDecl)
00286 { }
00287 
00288 DomainType::DomainType(DomainType *rootType, IdentifierInfo *name)
00289     : PrimaryType(AST_DomainType, rootType, true),
00290       definingDecl(name)
00291 { }
00292 
00293 IdentifierInfo *DomainType::getIdInfo() const
00294 {
00295     if (DomainTypeDecl *decl = definingDecl.dyn_cast<DomainTypeDecl*>())
00296         return decl->getIdInfo();
00297     return definingDecl.get<IdentifierInfo*>();
00298 }
00299 
00300 PrimaryType *DomainType::getRepresentationType()
00301 {
00302     if (DomainInstanceDecl *decl = getInstanceDecl())
00303         return decl->getRepresentationType();
00304     return 0;
00305 }
00306 
00307 
00308 
00309 
00310 
00311 const DomainTypeDecl *DomainType::getDomainTypeDecl() const
00312 {
00313     const DomainType *root = isSubtype() ? getRootType() : this;
00314     return root->definingDecl.get<DomainTypeDecl*>();
00315 }
00316 
00317 DomainTypeDecl *DomainType::getDomainTypeDecl()
00318 {
00319     DomainType *root = isSubtype() ? getRootType() : this;
00320     return root->definingDecl.get<DomainTypeDecl*>();
00321 }
00322 
00323 const PercentDecl *DomainType::getPercentDecl() const
00324 {
00325     return dyn_cast<PercentDecl>(getDomainTypeDecl());
00326 }
00327 
00328 PercentDecl *DomainType::getPercentDecl()
00329 {
00330     return dyn_cast<PercentDecl>(getDomainTypeDecl());
00331 }
00332 
00333 const DomainInstanceDecl *DomainType::getInstanceDecl() const
00334 {
00335     return dyn_cast<DomainInstanceDecl>(getDomainTypeDecl());
00336 }
00337 
00338 DomainInstanceDecl *DomainType::getInstanceDecl()
00339 {
00340     return dyn_cast<DomainInstanceDecl>(getDomainTypeDecl());
00341 }
00342 
00343 const AbstractDomainDecl *DomainType::getAbstractDecl() const
00344 {
00345     return dyn_cast<AbstractDomainDecl>(getDomainTypeDecl());
00346 }
00347 
00348 AbstractDomainDecl *DomainType::getAbstractDecl()
00349 {
00350     return dyn_cast<AbstractDomainDecl>(getDomainTypeDecl());
00351 }
00352 
00353 
00354 
00355 
00356 DiscreteType::ContainmentResult
00357 DiscreteType::contains(const DiscreteType *target) const
00358 {
00359     
00360     if (this == target)
00361         return Is_Contained;
00362 
00363     
00364     if (this->getKind() != target->getKind())
00365         return Not_Contained;
00366 
00367     
00368     llvm::APInt min;
00369     llvm::APInt max;
00370 
00371     if (const Range *constraint = getConstraint()) {
00372         
00373         
00374         if (!constraint->isStatic())
00375             return Maybe_Contained;
00376 
00377         
00378         if (constraint->isNull())
00379             return Not_Contained;
00380 
00381         min = constraint->getStaticLowerBound();
00382         max = constraint->getStaticUpperBound();
00383     }
00384     else {
00385         
00386         getLowerLimit(min);
00387         getUpperLimit(max);
00388     }
00389 
00390 
00391     
00392     llvm::APInt lower;
00393     llvm::APInt upper;
00394 
00395     if (const Range *constraint = target->getConstraint()) {
00396         if (constraint->isStatic()) {
00397             
00398             
00399             if (constraint->isNull())
00400                 return Is_Contained;
00401 
00402             lower = constraint->getStaticLowerBound();
00403             upper = constraint->getStaticUpperBound();
00404         }
00405         else {
00406             
00407             target->getLowerLimit(lower);
00408             target->getUpperLimit(upper);
00409         }
00410     }
00411     else {
00412         
00413         target->getLowerLimit(lower);
00414         target->getUpperLimit(upper);
00415     }
00416 
00417     
00418     unsigned width = std::max(getSize(), target->getSize());
00419     min.sextOrTrunc(width);
00420     max.sextOrTrunc(width);
00421     lower.sextOrTrunc(width);
00422     upper.sextOrTrunc(width);
00423     if (min.sle(lower) && upper.sle(max))
00424         return Is_Contained;
00425     else
00426         return Not_Contained;
00427 }
00428 
00429 DiscreteType::ContainmentResult
00430 DiscreteType::contains(const llvm::APInt &value) const
00431 {
00432     ContainmentResult result = Not_Contained;
00433 
00434     if (const Range *constraint = getConstraint()) {
00435         if (constraint->isStatic())
00436             result = constraint->contains(value) ? Is_Contained : Not_Contained;
00437         else
00438             result = Maybe_Contained;
00439     }
00440     else {
00441         llvm::APInt lower;
00442         llvm::APInt upper;
00443         llvm::APInt candidate(value);
00444 
00445         getLowerLimit(lower);
00446         getUpperLimit(upper);
00447 
00448         
00449         
00450         unsigned width = std::max(getSize(), uint64_t(value.getBitWidth()));
00451         if (isSigned()) {
00452             lower.sextOrTrunc(width);
00453             upper.sextOrTrunc(width);
00454             candidate.sextOrTrunc(width);
00455             result = lower.sle(candidate) && candidate.sle(upper)
00456                 ? Is_Contained : Not_Contained;
00457         }
00458         else {
00459             lower.zextOrTrunc(width);
00460             upper.zextOrTrunc(width);
00461             candidate.zextOrTrunc(width);
00462             result = lower.ule(candidate) && candidate.ule(upper)
00463                 ? Is_Contained : Not_Contained;
00464         }
00465     }
00466 
00467     return result;
00468 }
00469 
00470 unsigned DiscreteType::getPreferredSize(uint64_t bits)
00471 {
00472     unsigned size;
00473 
00474     if (bits <= 1)
00475         size = 1;
00476     else if (bits <= 8)
00477         size = 8;
00478     else if (bits <= 16)
00479         size = 16;
00480     else if (bits <= 32)
00481         size = 32;
00482     else if (bits <= 64)
00483         size = 64;
00484     else {
00485         assert(false && "Range too wide to represent!");
00486         size = 64;
00487     }
00488     return size;
00489 }
00490 
00491 bool DiscreteType::isSigned() const
00492 {
00493     
00494     return isa<IntegerType>(this);
00495 }
00496 
00497 uint64_t DiscreteType::length() const
00498 {
00499     if (const Range *range = getConstraint())
00500         return range->length();
00501 
00502     
00503     
00504     int64_t lower;
00505     int64_t upper;
00506 
00507     
00508     if (this->isSigned()) {
00509         llvm::APInt limit;
00510         getLowerLimit(limit);
00511         lower = limit.getSExtValue();
00512         getUpperLimit(limit);
00513         upper = limit.getSExtValue();
00514     }
00515     else {
00516         llvm::APInt limit;
00517         getLowerLimit(limit);
00518         lower = limit.getZExtValue();
00519         getUpperLimit(limit);
00520         upper = limit.getZExtValue();
00521     }
00522 
00523     if (upper < lower)
00524         return 0;
00525 
00526     if (lower < 0) {
00527         uint64_t lowElems = -lower;
00528         if (upper >= 0)
00529             return uint64_t(upper) + lowElems + 1;
00530         else {
00531             uint64_t upElems = -upper;
00532             return lowElems - upElems + 1;
00533         }
00534     }
00535 
00536     return uint64_t(upper - lower) + 1;
00537 }
00538 
00539 
00540 
00541 
00542 
00543 
00544 
00545 
00546 namespace {
00547 
00548 class UnconstrainedEnumType;
00549 class ConstrainedEnumType;
00550 
00551 class RootEnumType : public EnumerationType {
00552 
00553 public:
00554     RootEnumType(AstResource &resource, EnumerationDecl *decl);
00555 
00557     IdentifierInfo *getIdInfo() const { return definingDecl->getIdInfo(); }
00558 
00560 
00561     EnumerationDecl *getDefiningDecl() { return definingDecl; }
00562     const EnumerationDecl *getDefiningDecl() const { return definingDecl; }
00564 
00566     uint64_t getNumLiterals() const { return definingDecl->getNumLiterals(); }
00567 
00571     uint64_t getSize() const;
00572 
00574 
00575     const EnumerationType *getBaseSubtype() const;
00576     EnumerationType *getBaseSubtype();
00578 
00580     void getLowerLimit(llvm::APInt &res) const {
00581         res = llvm::APInt(getSize(), uint64_t(0), true);
00582     }
00583 
00585     void getUpperLimit(llvm::APInt &res) const {
00586         uint64_t max = definingDecl->getNumLiterals() - 1;
00587         res = llvm::APInt(getSize(), max, true);
00588     }
00589 
00590     
00591     static bool classof(const RootEnumType *node) { return true; }
00592     static bool classof(const EnumerationType *node) {
00593         return node->getEnumKind() == RootEnumType_KIND;
00594     }
00595 
00596 private:
00597     UnconstrainedEnumType *baseType; 
00598     EnumerationDecl *definingDecl;   
00599 };
00600 
00601 class UnconstrainedEnumType : public EnumerationType {
00602 
00603 public:
00604     UnconstrainedEnumType(EnumerationType *base,
00605                           EnumerationDecl *decl = 0)
00606         : EnumerationType(UnconstrainedEnumType_KIND, base),
00607           definingDecl(decl) {
00608         assert(decl == 0 || decl->isSubtypeDeclaration());
00609     }
00610 
00612     bool isAnonymous() const { return definingDecl == 0; }
00613 
00618     IdentifierInfo *getIdInfo() const {
00619         if (isAnonymous())
00620             return getRootType()->getIdInfo();
00621         else
00622             return definingDecl->getIdInfo();
00623     }
00624 
00626 
00627 
00628     const EnumerationDecl *getDefiningDecl() const { return definingDecl; }
00629     EnumerationDecl *getDefiningDecl() { return definingDecl; }
00631 
00632     
00633     static bool classof(const UnconstrainedEnumType *node) { return true; }
00634     static bool classof(const EnumerationType *node) {
00635         return node->getEnumKind() == UnconstrainedEnumType_KIND;
00636     }
00637 
00638 private:
00639     EnumerationDecl *definingDecl;
00640 };
00641 
00642 class ConstrainedEnumType : public EnumerationType {
00643 
00644 public:
00645     ConstrainedEnumType(EnumerationType *base,
00646                         Expr *lowerBound, Expr *upperBound,
00647                         EnumerationDecl *decl = 0)
00648         : EnumerationType(ConstrainedEnumType_KIND, base),
00649           constraint(new Range(lowerBound, upperBound, base)),
00650           definingDecl(decl) { }
00651 
00653     bool isAnonymous() const { return definingDecl == 0; }
00654 
00659     IdentifierInfo *getIdInfo() const {
00660         if (isAnonymous())
00661             return getRootType()->getIdInfo();
00662         else
00663             return definingDecl->getIdInfo();
00664     }
00665 
00667 
00668     Range *getConstraint() { return constraint; }
00669     const Range *getConstraint() const { return constraint; }
00671 
00674     bool isStaticallyConstrained() const { return constraint->isStatic(); }
00675 
00677 
00678 
00679     const EnumerationDecl *getDefiningDecl() const { return definingDecl; }
00680     EnumerationDecl *getDefiningDecl() { return definingDecl; }
00682 
00683     
00684     static bool classof(const ConstrainedEnumType *node) { return true; }
00685     static bool classof(const EnumerationType *node) {
00686         return node->getEnumKind() == ConstrainedEnumType_KIND;
00687     }
00688 
00689 private:
00690     Range *constraint;             
00691     EnumerationDecl *definingDecl; 
00692 };
00693 
00694 } 
00695 
00696 RootEnumType::RootEnumType(AstResource &resource, EnumerationDecl *decl)
00697     : EnumerationType(RootEnumType_KIND, 0),
00698       definingDecl(decl)
00699 {
00700     
00701     baseType = cast<UnconstrainedEnumType>(resource.createEnumSubtype(this));
00702 }
00703 
00704 uint64_t RootEnumType::getSize() const
00705 {
00706     uint64_t numBits = llvm::Log2_64_Ceil(definingDecl->getNumLiterals());
00707     return DiscreteType::getPreferredSize(numBits);
00708 }
00709 
00710 const EnumerationType *RootEnumType::getBaseSubtype() const
00711 {
00712     return baseType;
00713 }
00714 
00715 EnumerationType *RootEnumType::getBaseSubtype()
00716 {
00717     return baseType;
00718 }
00719 
00720 EnumerationDecl *EnumerationType::getDefiningDecl()
00721 {
00722     RootEnumType *root = cast<RootEnumType>(getRootType());
00723     return root->getDefiningDecl();
00724 }
00725 
00726 bool EnumerationType::isCharacterType() const
00727 {
00728     return getDefiningDecl()->isCharacterType();
00729 };
00730 
00731 uint64_t EnumerationType::getNumLiterals() const
00732 {
00733     return cast<RootEnumType>(getRootType())->getNumLiterals();
00734 }
00735 
00736 Range *EnumerationType::getConstraint()
00737 {
00738     if (ConstrainedEnumType *Ty = dyn_cast<ConstrainedEnumType>(this))
00739         return Ty->getConstraint();
00740     return 0;
00741 }
00742 
00743 const Range *EnumerationType::getConstraint() const
00744 {
00745     if (const ConstrainedEnumType *Ty = dyn_cast<ConstrainedEnumType>(this))
00746         return Ty->getConstraint();
00747     return 0;
00748 }
00749 
00750 void EnumerationType::getLowerLimit(llvm::APInt &res) const
00751 {
00752     cast<RootEnumType>(getRootType())->getLowerLimit(res);
00753 }
00754 
00755 void EnumerationType::getUpperLimit(llvm::APInt &res) const
00756 {
00757     cast<RootEnumType>(this->getRootType())->getUpperLimit(res);
00758 }
00759 
00760 uint64_t EnumerationType::getSize() const
00761 {
00762     return cast<RootEnumType>(this->getRootType())->getSize();
00763 }
00764 
00765 const EnumerationType *EnumerationType::getBaseSubtype() const
00766 {
00767     return const_cast<EnumerationType*>(this)->getBaseSubtype();
00768 }
00769 
00770 EnumerationType *EnumerationType::getBaseSubtype()
00771 {
00772     RootEnumType *root = cast<RootEnumType>(this->getRootType());
00773     return root->getBaseSubtype();
00774 }
00775 
00776 
00777 PosAD *EnumerationType::getPosAttribute()
00778 {
00779     assert(false && "Enumeration attributes not yet implemented!");
00780     return 0;
00781 }
00782 
00783 ValAD *EnumerationType::getValAttribute()
00784 {
00785     assert(false && "Enumeration attributes not yet implemented!");
00786     return 0;
00787 }
00788 
00789 EnumerationType *EnumerationType::create(AstResource &resource,
00790                                          EnumerationDecl *decl)
00791 {
00792     return new RootEnumType(resource, decl);
00793 }
00794 
00795 EnumerationType *EnumerationType::createSubtype(EnumerationType *type,
00796                                                 EnumerationDecl *decl)
00797 {
00798     return new UnconstrainedEnumType(type, decl);
00799 }
00800 
00801 EnumerationType *
00802 EnumerationType::createConstrainedSubtype(EnumerationType *type,
00803                                           Expr *lowerBound, Expr *upperBound,
00804                                           EnumerationDecl *decl)
00805 {
00806     return new ConstrainedEnumType(type, lowerBound, upperBound, decl);
00807 }
00808 
00809 
00810 
00811 
00812 
00813 
00814 
00815 
00816 namespace {
00817 
00818 class ConstrainedIntegerType;
00819 class UnconstrainedIntegerType;
00820 
00821 class RootIntegerType : public IntegerType {
00822 
00823 public:
00824     RootIntegerType(AstResource &resource, IntegerDecl *decl,
00825                     const llvm::APInt &low, const llvm::APInt &high);
00826 
00828     IdentifierInfo *getIdInfo() const { return definingDecl->getIdInfo(); }
00829 
00831 
00832     IntegerDecl *getDefiningDecl() { return definingDecl; }
00833     const IntegerDecl *getDefiningDecl() const { return definingDecl; }
00835 
00839     uint64_t getSize() const { return lowerBound.getBitWidth(); }
00840 
00842     UnconstrainedIntegerType *getBaseSubtype() { return baseType; }
00843 
00845     void getLowerLimit(llvm::APInt &res) const { res = lowerBound; }
00846 
00848     void getUpperLimit(llvm::APInt &res) const { res = upperBound; }
00849 
00850     
00851     static bool classof(const RootIntegerType *node) { return true; }
00852     static bool classof(const IntegerType *node) {
00853         return node->getIntegerKind() == RootIntegerType_KIND;
00854     }
00855 
00856 private:
00857     llvm::APInt lowerBound;             
00858     llvm::APInt upperBound;             
00859     UnconstrainedIntegerType *baseType; 
00860     IntegerDecl *definingDecl;          
00861 
00863     void initBounds(const llvm::APInt &low, const llvm::APInt &high);
00864 };
00865 
00866 class ConstrainedIntegerType : public IntegerType {
00867 
00868 public:
00869     ConstrainedIntegerType(IntegerType *base, Expr *lower, Expr *upper,
00870                            IntegerDecl *decl = 0)
00871         : IntegerType(ConstrainedIntegerType_KIND, base),
00872           constraint(new Range(lower, upper, base)),
00873           definingDecl(decl) { }
00874 
00876     bool isAnonymous() const { return definingDecl == 0; }
00877 
00882     IdentifierInfo *getIdInfo() const {
00883         if (isAnonymous())
00884             return getRootType()->getIdInfo();
00885         else
00886             return definingDecl->getIdInfo();
00887     }
00888 
00890 
00891     Range *getConstraint() { return constraint; }
00892     const Range *getConstraint() const { return constraint; }
00894 
00897     bool isStaticallyConstrained() const { return constraint->isStatic(); }
00898 
00900 
00901 
00902     const IntegerDecl *getDefiningDecl() const { return definingDecl;  }
00903     IntegerDecl *getDefiningDecl() { return definingDecl; }
00905 
00906     
00907     static bool classof(const ConstrainedIntegerType *node) { return true; }
00908     static bool classof(const IntegerType *node) {
00909         return node->getIntegerKind() == ConstrainedIntegerType_KIND;
00910     }
00911 
00912 private:
00913     Range *constraint;          
00914     IntegerDecl *definingDecl;  
00915 };
00916 
00917 class UnconstrainedIntegerType : public IntegerType {
00918 
00919 public:
00920     UnconstrainedIntegerType(IntegerType *base,
00921                              IntegerDecl *decl = 0)
00922         : IntegerType(UnconstrainedIntegerType_KIND, base),
00923           definingDecl(decl) {
00924         assert(decl == 0 || decl->isSubtypeDeclaration());
00925     }
00926 
00928     bool isAnonymous() const { return definingDecl == 0; }
00929 
00931 
00932 
00933     const IntegerDecl *getDefiningDecl() const { return definingDecl; }
00934     IntegerDecl *getDefiningDecl() { return definingDecl; }
00936 
00941     IdentifierInfo *getIdInfo() const {
00942         if (isAnonymous())
00943             return getRootType()->getIdInfo();
00944         else
00945             return definingDecl->getIdInfo();
00946     }
00947 
00948     
00949     static bool classof(const UnconstrainedIntegerType *node) { return true; }
00950     static bool classof(const IntegerType *node) {
00951         return node->getIntegerKind() == UnconstrainedIntegerType_KIND;
00952     }
00953 
00954 private:
00955     IntegerDecl *definingDecl;  
00956 };
00957 
00958 } 
00959 
00960 RootIntegerType::RootIntegerType(AstResource &resource,
00961                                  IntegerDecl *decl,
00962                                  const llvm::APInt &low,
00963                                  const llvm::APInt &high)
00964     : IntegerType(RootIntegerType_KIND, 0),
00965       definingDecl(decl)
00966 {
00967     initBounds(low, high);
00968 
00969     
00970     baseType = cast<UnconstrainedIntegerType>
00971         (resource.createIntegerSubtype(this));
00972 }
00973 
00974 void RootIntegerType::initBounds(const llvm::APInt &low,
00975                                  const llvm::APInt &high)
00976 {
00977     
00978     
00979     
00980     unsigned minimalWidth = std::max(low.getMinSignedBits(),
00981                                      high.getMinSignedBits());
00982 
00983     unsigned preferredWidth = DiscreteType::getPreferredSize(minimalWidth);
00984     lowerBound = llvm::APInt::getSignedMinValue(preferredWidth);
00985     upperBound = llvm::APInt::getSignedMaxValue(preferredWidth);
00986 }
00987 
00988 IntegerType *IntegerType::create(AstResource &resource, IntegerDecl *decl,
00989                                  const llvm::APInt &lower,
00990                                  const llvm::APInt &upper)
00991 {
00992     return new RootIntegerType(resource, decl, lower, upper);
00993 }
00994 
00995 IntegerType *IntegerType::createSubtype(IntegerType *type,
00996                                         IntegerDecl *decl)
00997 {
00998     return new UnconstrainedIntegerType(type, decl);
00999 }
01000 
01001 IntegerType *IntegerType::createConstrainedSubtype(IntegerType *type,
01002                                                    Expr *lowerBound,
01003                                                    Expr *upperBound,
01004                                                    IntegerDecl *decl)
01005 {
01006     return new ConstrainedIntegerType(type, lowerBound, upperBound, decl);
01007 }
01008 
01009 IntegerType *IntegerType::getBaseSubtype()
01010 {
01011     RootIntegerType *root = cast<RootIntegerType>(this->getRootType());
01012     return root->getBaseSubtype();
01013 }
01014 
01015 Range *IntegerType::getConstraint()
01016 {
01017     ConstrainedIntegerType *Ty;
01018     Ty = dyn_cast<ConstrainedIntegerType>(this);
01019     return Ty ? Ty->getConstraint() : 0;
01020 }
01021 
01022 const Range *IntegerType::getConstraint() const {
01023     const ConstrainedIntegerType *Ty;
01024     Ty = dyn_cast<ConstrainedIntegerType>(this);
01025     return Ty ? Ty->getConstraint() : 0;
01026 }
01027 
01028 void IntegerType::getLowerLimit(llvm::APInt &res) const
01029 {
01030     const RootIntegerType *root = cast<RootIntegerType>(getRootType());
01031     root->getLowerLimit(res);
01032 }
01033 
01034 void IntegerType::getUpperLimit(llvm::APInt &res) const
01035 {
01036     const RootIntegerType *root = cast<RootIntegerType>(getRootType());
01037     root->getUpperLimit(res);
01038 }
01039 
01040 bool IntegerType::baseContains(const llvm::APInt &value) const
01041 {
01042     uint64_t activeBits = value.getMinSignedBits();
01043     uint64_t width = getSize();
01044 
01045     if (activeBits > width)
01046         return false;
01047 
01048     llvm::APInt lower;
01049     llvm::APInt upper;
01050     getLowerLimit(lower);
01051     getUpperLimit(upper);
01052 
01053     
01054     
01055     if (lower.sgt(upper))
01056         return false;
01057 
01058     
01059     
01060     llvm::APInt candidate(value);
01061     if (activeBits < width)
01062         candidate.sext(width);
01063 
01064     return lower.sle(candidate) && candidate.sle(upper);
01065 }
01066 
01067 uint64_t IntegerType::getSize() const
01068 {
01069     const RootIntegerType *root = cast<RootIntegerType>(getRootType());
01070     return root->getSize();
01071 }
01072 
01073 PosAD *IntegerType::getPosAttribute()
01074 {
01075     return getDefiningDecl()->getPosAttribute();
01076 }
01077 
01078 ValAD *IntegerType::getValAttribute()
01079 {
01080     return getDefiningDecl()->getValAttribute();
01081 }
01082 
01083 
01084 
01085 
01086 ArrayType::ArrayType(ArrayDecl *decl, unsigned rank, DiscreteType **indices,
01087                      Type *component, bool isConstrained)
01088     : CompositeType(AST_ArrayType, 0, false),
01089       indices(indices, indices + rank),
01090       componentType(component),
01091       definingDecl(decl)
01092 {
01093     assert(rank != 0 && "Missing index types!");
01094     assert(this->isRootType());
01095     if (isConstrained)
01096         setConstraintBit();
01097 }
01098 
01099 ArrayType::ArrayType(IdentifierInfo *name, ArrayType *rootType,
01100                      DiscreteType **indices)
01101     : CompositeType(AST_ArrayType, rootType, true),
01102       indices(indices, indices + rootType->getRank()),
01103       componentType(rootType->getComponentType()),
01104       definingDecl(name)
01105 {
01106     setConstraintBit();
01107     assert(this->isSubtype());
01108 }
01109 
01110 ArrayType::ArrayType(IdentifierInfo *name, ArrayType *rootType)
01111     : CompositeType(AST_ArrayType, rootType, true),
01112       indices(rootType->begin(), rootType->end()),
01113       componentType(rootType->getComponentType()),
01114       definingDecl(name)
01115 {
01116     assert(this->isSubtype());
01117     if (getRootType()->isConstrained())
01118         setConstraintBit();
01119 }
01120 
01121 IdentifierInfo *ArrayType::getIdInfo() const
01122 {
01123     if (IdentifierInfo *idInfo = definingDecl.dyn_cast<IdentifierInfo*>())
01124         return idInfo;
01125     const ArrayType *root = getRootType();
01126     return root->definingDecl.get<ArrayDecl*>()->getIdInfo();
01127 }
01128 
01129 uint64_t ArrayType::length() const
01130 {
01131     assert(isConstrained() &&
01132            "Cannot determine length of unconstrained arrays!");
01133 
01134     const DiscreteType *indexTy = getIndexType(0);
01135     const Range *constraint = indexTy->getConstraint();
01136 
01137     assert(constraint->isStatic() &&
01138            "Cannot determine length using non-static index constraint!");
01139 
01140     if (constraint->isNull())
01141         return 0;
01142 
01147     llvm::APInt lower(constraint->getStaticLowerBound());
01148     llvm::APInt upper(constraint->getStaticUpperBound());
01149     llvm::APInt length(upper - lower);
01150     return length.getZExtValue() + 1;
01151 }
01152 
01153 bool ArrayType::isStaticallyConstrained() const
01154 {
01155     if (!isConstrained())
01156         return false;
01157     for (const_iterator I = begin(); I != end(); ++I) {
01158         DiscreteType *Ty = *I;
01159         if (!Ty->isStaticallyConstrained())
01160             return false;
01161     }
01162     return true;
01163 }
01164 
01165 
01166 
01167 
01168 RecordType::RecordType(RecordDecl *decl)
01169     : CompositeType(AST_RecordType, 0, false),
01170       definingDecl(decl) { }
01171 
01172 RecordType::RecordType(RecordType *rootType, IdentifierInfo *name)
01173   : CompositeType(AST_RecordType, rootType, true),
01174     definingDecl(name) { }
01175 
01176 RecordDecl *RecordType::getDefiningDecl()
01177 {
01178     return getRootType()->definingDecl.get<RecordDecl*>();
01179 }
01180 
01181 IdentifierInfo *RecordType::getIdInfo() const
01182 {
01183     if (IdentifierInfo *idInfo = definingDecl.dyn_cast<IdentifierInfo*>())
01184         return idInfo;
01185     return getDefiningDecl()->getIdInfo();
01186 }
01187 
01188 unsigned RecordType::numComponents() const
01189 {
01190     return getDefiningDecl()->numComponents();
01191 }
01192 
01193 Type *RecordType::getComponentType(unsigned i)
01194 {
01195     return getDefiningDecl()->getComponent(i)->getType();
01196 }
01197 
01198 
01199 
01200 
01201 AccessType::AccessType(AccessDecl *decl, Type *targetType)
01202     : PrimaryType(AST_AccessType, 0, false),
01203       targetType(targetType),
01204       definingDecl(decl) { }
01205 
01206 AccessType::AccessType(AccessType *rootType, IdentifierInfo *name)
01207     : PrimaryType(AST_AccessType, rootType, true),
01208       targetType(rootType->getTargetType()),
01209       definingDecl(name) { }
01210 
01211 AccessDecl *AccessType::getDefiningDecl()
01212 {
01213     return getRootType()->definingDecl.get<AccessDecl*>();
01214 }
01215 
01216 IdentifierInfo *AccessType::getIdInfo() const
01217 {
01218     if (IdentifierInfo *idInfo = definingDecl.dyn_cast<IdentifierInfo*>())
01219         return idInfo;
01220     return getDefiningDecl()->getIdInfo();
01221 }
01222 
01223 
01224 
01225