clang API Documentation
00001 //===--- TypePrinter.cpp - Pretty-Print Clang Types -----------------------===// 00002 // 00003 // The LLVM Compiler Infrastructure 00004 // 00005 // This file is distributed under the University of Illinois Open Source 00006 // License. See LICENSE.TXT for details. 00007 // 00008 //===----------------------------------------------------------------------===// 00009 // 00010 // This contains code to print types from Clang's type system. 00011 // 00012 //===----------------------------------------------------------------------===// 00013 00014 #include "clang/AST/PrettyPrinter.h" 00015 #include "clang/AST/ASTContext.h" 00016 #include "clang/AST/Decl.h" 00017 #include "clang/AST/DeclObjC.h" 00018 #include "clang/AST/DeclTemplate.h" 00019 #include "clang/AST/Expr.h" 00020 #include "clang/AST/Type.h" 00021 #include "clang/Basic/LangOptions.h" 00022 #include "clang/Basic/SourceManager.h" 00023 #include "llvm/ADT/SmallString.h" 00024 #include "llvm/ADT/StringExtras.h" 00025 #include "llvm/Support/SaveAndRestore.h" 00026 #include "llvm/Support/raw_ostream.h" 00027 using namespace clang; 00028 00029 namespace { 00030 /// \brief RAII object that enables printing of the ARC __strong lifetime 00031 /// qualifier. 00032 class IncludeStrongLifetimeRAII { 00033 PrintingPolicy &Policy; 00034 bool Old; 00035 00036 public: 00037 explicit IncludeStrongLifetimeRAII(PrintingPolicy &Policy) 00038 : Policy(Policy), Old(Policy.SuppressStrongLifetime) { 00039 if (!Policy.SuppressLifetimeQualifiers) 00040 Policy.SuppressStrongLifetime = false; 00041 } 00042 00043 ~IncludeStrongLifetimeRAII() { 00044 Policy.SuppressStrongLifetime = Old; 00045 } 00046 }; 00047 00048 class ParamPolicyRAII { 00049 PrintingPolicy &Policy; 00050 bool Old; 00051 00052 public: 00053 explicit ParamPolicyRAII(PrintingPolicy &Policy) 00054 : Policy(Policy), Old(Policy.SuppressSpecifiers) { 00055 Policy.SuppressSpecifiers = false; 00056 } 00057 00058 ~ParamPolicyRAII() { 00059 Policy.SuppressSpecifiers = Old; 00060 } 00061 }; 00062 00063 class ElaboratedTypePolicyRAII { 00064 PrintingPolicy &Policy; 00065 bool SuppressTagKeyword; 00066 bool SuppressScope; 00067 00068 public: 00069 explicit ElaboratedTypePolicyRAII(PrintingPolicy &Policy) : Policy(Policy) { 00070 SuppressTagKeyword = Policy.SuppressTagKeyword; 00071 SuppressScope = Policy.SuppressScope; 00072 Policy.SuppressTagKeyword = true; 00073 Policy.SuppressScope = true; 00074 } 00075 00076 ~ElaboratedTypePolicyRAII() { 00077 Policy.SuppressTagKeyword = SuppressTagKeyword; 00078 Policy.SuppressScope = SuppressScope; 00079 } 00080 }; 00081 00082 class TypePrinter { 00083 PrintingPolicy Policy; 00084 bool HasEmptyPlaceHolder; 00085 bool InsideCCAttribute; 00086 00087 public: 00088 explicit TypePrinter(const PrintingPolicy &Policy) 00089 : Policy(Policy), HasEmptyPlaceHolder(false), InsideCCAttribute(false) { } 00090 00091 void print(const Type *ty, Qualifiers qs, raw_ostream &OS, 00092 StringRef PlaceHolder); 00093 void print(QualType T, raw_ostream &OS, StringRef PlaceHolder); 00094 00095 static bool canPrefixQualifiers(const Type *T, bool &NeedARCStrongQualifier); 00096 void spaceBeforePlaceHolder(raw_ostream &OS); 00097 void printTypeSpec(const NamedDecl *D, raw_ostream &OS); 00098 00099 void printBefore(const Type *ty, Qualifiers qs, raw_ostream &OS); 00100 void printBefore(QualType T, raw_ostream &OS); 00101 void printAfter(const Type *ty, Qualifiers qs, raw_ostream &OS); 00102 void printAfter(QualType T, raw_ostream &OS); 00103 void AppendScope(DeclContext *DC, raw_ostream &OS); 00104 void printTag(TagDecl *T, raw_ostream &OS); 00105 #define ABSTRACT_TYPE(CLASS, PARENT) 00106 #define TYPE(CLASS, PARENT) \ 00107 void print##CLASS##Before(const CLASS##Type *T, raw_ostream &OS); \ 00108 void print##CLASS##After(const CLASS##Type *T, raw_ostream &OS); 00109 #include "clang/AST/TypeNodes.def" 00110 }; 00111 } 00112 00113 static void AppendTypeQualList(raw_ostream &OS, unsigned TypeQuals) { 00114 bool appendSpace = false; 00115 if (TypeQuals & Qualifiers::Const) { 00116 OS << "const"; 00117 appendSpace = true; 00118 } 00119 if (TypeQuals & Qualifiers::Volatile) { 00120 if (appendSpace) OS << ' '; 00121 OS << "volatile"; 00122 appendSpace = true; 00123 } 00124 if (TypeQuals & Qualifiers::Restrict) { 00125 if (appendSpace) OS << ' '; 00126 OS << "restrict"; 00127 } 00128 } 00129 00130 void TypePrinter::spaceBeforePlaceHolder(raw_ostream &OS) { 00131 if (!HasEmptyPlaceHolder) 00132 OS << ' '; 00133 } 00134 00135 void TypePrinter::print(QualType t, raw_ostream &OS, StringRef PlaceHolder) { 00136 SplitQualType split = t.split(); 00137 print(split.Ty, split.Quals, OS, PlaceHolder); 00138 } 00139 00140 void TypePrinter::print(const Type *T, Qualifiers Quals, raw_ostream &OS, 00141 StringRef PlaceHolder) { 00142 if (!T) { 00143 OS << "NULL TYPE"; 00144 return; 00145 } 00146 00147 SaveAndRestore<bool> PHVal(HasEmptyPlaceHolder, PlaceHolder.empty()); 00148 00149 printBefore(T, Quals, OS); 00150 OS << PlaceHolder; 00151 printAfter(T, Quals, OS); 00152 } 00153 00154 bool TypePrinter::canPrefixQualifiers(const Type *T, 00155 bool &NeedARCStrongQualifier) { 00156 // CanPrefixQualifiers - We prefer to print type qualifiers before the type, 00157 // so that we get "const int" instead of "int const", but we can't do this if 00158 // the type is complex. For example if the type is "int*", we *must* print 00159 // "int * const", printing "const int *" is different. Only do this when the 00160 // type expands to a simple string. 00161 bool CanPrefixQualifiers = false; 00162 NeedARCStrongQualifier = false; 00163 Type::TypeClass TC = T->getTypeClass(); 00164 if (const AutoType *AT = dyn_cast<AutoType>(T)) 00165 TC = AT->desugar()->getTypeClass(); 00166 if (const SubstTemplateTypeParmType *Subst 00167 = dyn_cast<SubstTemplateTypeParmType>(T)) 00168 TC = Subst->getReplacementType()->getTypeClass(); 00169 00170 switch (TC) { 00171 case Type::Auto: 00172 case Type::Builtin: 00173 case Type::Complex: 00174 case Type::UnresolvedUsing: 00175 case Type::Typedef: 00176 case Type::TypeOfExpr: 00177 case Type::TypeOf: 00178 case Type::Decltype: 00179 case Type::UnaryTransform: 00180 case Type::Record: 00181 case Type::Enum: 00182 case Type::Elaborated: 00183 case Type::TemplateTypeParm: 00184 case Type::SubstTemplateTypeParmPack: 00185 case Type::TemplateSpecialization: 00186 case Type::InjectedClassName: 00187 case Type::DependentName: 00188 case Type::DependentTemplateSpecialization: 00189 case Type::ObjCObject: 00190 case Type::ObjCInterface: 00191 case Type::Atomic: 00192 CanPrefixQualifiers = true; 00193 break; 00194 00195 case Type::ObjCObjectPointer: 00196 CanPrefixQualifiers = T->isObjCIdType() || T->isObjCClassType() || 00197 T->isObjCQualifiedIdType() || T->isObjCQualifiedClassType(); 00198 break; 00199 00200 case Type::ConstantArray: 00201 case Type::IncompleteArray: 00202 case Type::VariableArray: 00203 case Type::DependentSizedArray: 00204 NeedARCStrongQualifier = true; 00205 // Fall through 00206 00207 case Type::Adjusted: 00208 case Type::Decayed: 00209 case Type::Pointer: 00210 case Type::BlockPointer: 00211 case Type::LValueReference: 00212 case Type::RValueReference: 00213 case Type::MemberPointer: 00214 case Type::DependentSizedExtVector: 00215 case Type::Vector: 00216 case Type::ExtVector: 00217 case Type::FunctionProto: 00218 case Type::FunctionNoProto: 00219 case Type::Paren: 00220 case Type::Attributed: 00221 case Type::PackExpansion: 00222 case Type::SubstTemplateTypeParm: 00223 CanPrefixQualifiers = false; 00224 break; 00225 } 00226 00227 return CanPrefixQualifiers; 00228 } 00229 00230 void TypePrinter::printBefore(QualType T, raw_ostream &OS) { 00231 SplitQualType Split = T.split(); 00232 00233 // If we have cv1 T, where T is substituted for cv2 U, only print cv1 - cv2 00234 // at this level. 00235 Qualifiers Quals = Split.Quals; 00236 if (const SubstTemplateTypeParmType *Subst = 00237 dyn_cast<SubstTemplateTypeParmType>(Split.Ty)) 00238 Quals -= QualType(Subst, 0).getQualifiers(); 00239 00240 printBefore(Split.Ty, Quals, OS); 00241 } 00242 00243 /// \brief Prints the part of the type string before an identifier, e.g. for 00244 /// "int foo[10]" it prints "int ". 00245 void TypePrinter::printBefore(const Type *T,Qualifiers Quals, raw_ostream &OS) { 00246 if (Policy.SuppressSpecifiers && T->isSpecifierType()) 00247 return; 00248 00249 SaveAndRestore<bool> PrevPHIsEmpty(HasEmptyPlaceHolder); 00250 00251 // Print qualifiers as appropriate. 00252 00253 bool CanPrefixQualifiers = false; 00254 bool NeedARCStrongQualifier = false; 00255 CanPrefixQualifiers = canPrefixQualifiers(T, NeedARCStrongQualifier); 00256 00257 if (CanPrefixQualifiers && !Quals.empty()) { 00258 if (NeedARCStrongQualifier) { 00259 IncludeStrongLifetimeRAII Strong(Policy); 00260 Quals.print(OS, Policy, /*appendSpaceIfNonEmpty=*/true); 00261 } else { 00262 Quals.print(OS, Policy, /*appendSpaceIfNonEmpty=*/true); 00263 } 00264 } 00265 00266 bool hasAfterQuals = false; 00267 if (!CanPrefixQualifiers && !Quals.empty()) { 00268 hasAfterQuals = !Quals.isEmptyWhenPrinted(Policy); 00269 if (hasAfterQuals) 00270 HasEmptyPlaceHolder = false; 00271 } 00272 00273 switch (T->getTypeClass()) { 00274 #define ABSTRACT_TYPE(CLASS, PARENT) 00275 #define TYPE(CLASS, PARENT) case Type::CLASS: \ 00276 print##CLASS##Before(cast<CLASS##Type>(T), OS); \ 00277 break; 00278 #include "clang/AST/TypeNodes.def" 00279 } 00280 00281 if (hasAfterQuals) { 00282 if (NeedARCStrongQualifier) { 00283 IncludeStrongLifetimeRAII Strong(Policy); 00284 Quals.print(OS, Policy, /*appendSpaceIfNonEmpty=*/!PrevPHIsEmpty.get()); 00285 } else { 00286 Quals.print(OS, Policy, /*appendSpaceIfNonEmpty=*/!PrevPHIsEmpty.get()); 00287 } 00288 } 00289 } 00290 00291 void TypePrinter::printAfter(QualType t, raw_ostream &OS) { 00292 SplitQualType split = t.split(); 00293 printAfter(split.Ty, split.Quals, OS); 00294 } 00295 00296 /// \brief Prints the part of the type string after an identifier, e.g. for 00297 /// "int foo[10]" it prints "[10]". 00298 void TypePrinter::printAfter(const Type *T, Qualifiers Quals, raw_ostream &OS) { 00299 switch (T->getTypeClass()) { 00300 #define ABSTRACT_TYPE(CLASS, PARENT) 00301 #define TYPE(CLASS, PARENT) case Type::CLASS: \ 00302 print##CLASS##After(cast<CLASS##Type>(T), OS); \ 00303 break; 00304 #include "clang/AST/TypeNodes.def" 00305 } 00306 } 00307 00308 void TypePrinter::printBuiltinBefore(const BuiltinType *T, raw_ostream &OS) { 00309 OS << T->getName(Policy); 00310 spaceBeforePlaceHolder(OS); 00311 } 00312 void TypePrinter::printBuiltinAfter(const BuiltinType *T, raw_ostream &OS) { } 00313 00314 void TypePrinter::printComplexBefore(const ComplexType *T, raw_ostream &OS) { 00315 OS << "_Complex "; 00316 printBefore(T->getElementType(), OS); 00317 } 00318 void TypePrinter::printComplexAfter(const ComplexType *T, raw_ostream &OS) { 00319 printAfter(T->getElementType(), OS); 00320 } 00321 00322 void TypePrinter::printPointerBefore(const PointerType *T, raw_ostream &OS) { 00323 IncludeStrongLifetimeRAII Strong(Policy); 00324 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00325 printBefore(T->getPointeeType(), OS); 00326 // Handle things like 'int (*A)[4];' correctly. 00327 // FIXME: this should include vectors, but vectors use attributes I guess. 00328 if (isa<ArrayType>(T->getPointeeType())) 00329 OS << '('; 00330 OS << '*'; 00331 } 00332 void TypePrinter::printPointerAfter(const PointerType *T, raw_ostream &OS) { 00333 IncludeStrongLifetimeRAII Strong(Policy); 00334 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00335 // Handle things like 'int (*A)[4];' correctly. 00336 // FIXME: this should include vectors, but vectors use attributes I guess. 00337 if (isa<ArrayType>(T->getPointeeType())) 00338 OS << ')'; 00339 printAfter(T->getPointeeType(), OS); 00340 } 00341 00342 void TypePrinter::printBlockPointerBefore(const BlockPointerType *T, 00343 raw_ostream &OS) { 00344 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00345 printBefore(T->getPointeeType(), OS); 00346 OS << '^'; 00347 } 00348 void TypePrinter::printBlockPointerAfter(const BlockPointerType *T, 00349 raw_ostream &OS) { 00350 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00351 printAfter(T->getPointeeType(), OS); 00352 } 00353 00354 void TypePrinter::printLValueReferenceBefore(const LValueReferenceType *T, 00355 raw_ostream &OS) { 00356 IncludeStrongLifetimeRAII Strong(Policy); 00357 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00358 printBefore(T->getPointeeTypeAsWritten(), OS); 00359 // Handle things like 'int (&A)[4];' correctly. 00360 // FIXME: this should include vectors, but vectors use attributes I guess. 00361 if (isa<ArrayType>(T->getPointeeTypeAsWritten())) 00362 OS << '('; 00363 OS << '&'; 00364 } 00365 void TypePrinter::printLValueReferenceAfter(const LValueReferenceType *T, 00366 raw_ostream &OS) { 00367 IncludeStrongLifetimeRAII Strong(Policy); 00368 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00369 // Handle things like 'int (&A)[4];' correctly. 00370 // FIXME: this should include vectors, but vectors use attributes I guess. 00371 if (isa<ArrayType>(T->getPointeeTypeAsWritten())) 00372 OS << ')'; 00373 printAfter(T->getPointeeTypeAsWritten(), OS); 00374 } 00375 00376 void TypePrinter::printRValueReferenceBefore(const RValueReferenceType *T, 00377 raw_ostream &OS) { 00378 IncludeStrongLifetimeRAII Strong(Policy); 00379 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00380 printBefore(T->getPointeeTypeAsWritten(), OS); 00381 // Handle things like 'int (&&A)[4];' correctly. 00382 // FIXME: this should include vectors, but vectors use attributes I guess. 00383 if (isa<ArrayType>(T->getPointeeTypeAsWritten())) 00384 OS << '('; 00385 OS << "&&"; 00386 } 00387 void TypePrinter::printRValueReferenceAfter(const RValueReferenceType *T, 00388 raw_ostream &OS) { 00389 IncludeStrongLifetimeRAII Strong(Policy); 00390 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00391 // Handle things like 'int (&&A)[4];' correctly. 00392 // FIXME: this should include vectors, but vectors use attributes I guess. 00393 if (isa<ArrayType>(T->getPointeeTypeAsWritten())) 00394 OS << ')'; 00395 printAfter(T->getPointeeTypeAsWritten(), OS); 00396 } 00397 00398 void TypePrinter::printMemberPointerBefore(const MemberPointerType *T, 00399 raw_ostream &OS) { 00400 IncludeStrongLifetimeRAII Strong(Policy); 00401 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00402 printBefore(T->getPointeeType(), OS); 00403 // Handle things like 'int (Cls::*A)[4];' correctly. 00404 // FIXME: this should include vectors, but vectors use attributes I guess. 00405 if (isa<ArrayType>(T->getPointeeType())) 00406 OS << '('; 00407 00408 PrintingPolicy InnerPolicy(Policy); 00409 InnerPolicy.SuppressTag = false; 00410 TypePrinter(InnerPolicy).print(QualType(T->getClass(), 0), OS, StringRef()); 00411 00412 OS << "::*"; 00413 } 00414 void TypePrinter::printMemberPointerAfter(const MemberPointerType *T, 00415 raw_ostream &OS) { 00416 IncludeStrongLifetimeRAII Strong(Policy); 00417 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00418 // Handle things like 'int (Cls::*A)[4];' correctly. 00419 // FIXME: this should include vectors, but vectors use attributes I guess. 00420 if (isa<ArrayType>(T->getPointeeType())) 00421 OS << ')'; 00422 printAfter(T->getPointeeType(), OS); 00423 } 00424 00425 void TypePrinter::printConstantArrayBefore(const ConstantArrayType *T, 00426 raw_ostream &OS) { 00427 IncludeStrongLifetimeRAII Strong(Policy); 00428 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00429 printBefore(T->getElementType(), OS); 00430 } 00431 void TypePrinter::printConstantArrayAfter(const ConstantArrayType *T, 00432 raw_ostream &OS) { 00433 OS << '['; 00434 if (T->getIndexTypeQualifiers().hasQualifiers()) { 00435 AppendTypeQualList(OS, T->getIndexTypeCVRQualifiers()); 00436 OS << ' '; 00437 } 00438 00439 if (T->getSizeModifier() == ArrayType::Static) 00440 OS << "static "; 00441 00442 OS << T->getSize().getZExtValue() << ']'; 00443 printAfter(T->getElementType(), OS); 00444 } 00445 00446 void TypePrinter::printIncompleteArrayBefore(const IncompleteArrayType *T, 00447 raw_ostream &OS) { 00448 IncludeStrongLifetimeRAII Strong(Policy); 00449 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00450 printBefore(T->getElementType(), OS); 00451 } 00452 void TypePrinter::printIncompleteArrayAfter(const IncompleteArrayType *T, 00453 raw_ostream &OS) { 00454 OS << "[]"; 00455 printAfter(T->getElementType(), OS); 00456 } 00457 00458 void TypePrinter::printVariableArrayBefore(const VariableArrayType *T, 00459 raw_ostream &OS) { 00460 IncludeStrongLifetimeRAII Strong(Policy); 00461 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00462 printBefore(T->getElementType(), OS); 00463 } 00464 void TypePrinter::printVariableArrayAfter(const VariableArrayType *T, 00465 raw_ostream &OS) { 00466 OS << '['; 00467 if (T->getIndexTypeQualifiers().hasQualifiers()) { 00468 AppendTypeQualList(OS, T->getIndexTypeCVRQualifiers()); 00469 OS << ' '; 00470 } 00471 00472 if (T->getSizeModifier() == VariableArrayType::Static) 00473 OS << "static "; 00474 else if (T->getSizeModifier() == VariableArrayType::Star) 00475 OS << '*'; 00476 00477 if (T->getSizeExpr()) 00478 T->getSizeExpr()->printPretty(OS, nullptr, Policy); 00479 OS << ']'; 00480 00481 printAfter(T->getElementType(), OS); 00482 } 00483 00484 void TypePrinter::printAdjustedBefore(const AdjustedType *T, raw_ostream &OS) { 00485 // Print the adjusted representation, otherwise the adjustment will be 00486 // invisible. 00487 printBefore(T->getAdjustedType(), OS); 00488 } 00489 void TypePrinter::printAdjustedAfter(const AdjustedType *T, raw_ostream &OS) { 00490 printAfter(T->getAdjustedType(), OS); 00491 } 00492 00493 void TypePrinter::printDecayedBefore(const DecayedType *T, raw_ostream &OS) { 00494 // Print as though it's a pointer. 00495 printAdjustedBefore(T, OS); 00496 } 00497 void TypePrinter::printDecayedAfter(const DecayedType *T, raw_ostream &OS) { 00498 printAdjustedAfter(T, OS); 00499 } 00500 00501 void TypePrinter::printDependentSizedArrayBefore( 00502 const DependentSizedArrayType *T, 00503 raw_ostream &OS) { 00504 IncludeStrongLifetimeRAII Strong(Policy); 00505 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00506 printBefore(T->getElementType(), OS); 00507 } 00508 void TypePrinter::printDependentSizedArrayAfter( 00509 const DependentSizedArrayType *T, 00510 raw_ostream &OS) { 00511 OS << '['; 00512 if (T->getSizeExpr()) 00513 T->getSizeExpr()->printPretty(OS, nullptr, Policy); 00514 OS << ']'; 00515 printAfter(T->getElementType(), OS); 00516 } 00517 00518 void TypePrinter::printDependentSizedExtVectorBefore( 00519 const DependentSizedExtVectorType *T, 00520 raw_ostream &OS) { 00521 printBefore(T->getElementType(), OS); 00522 } 00523 void TypePrinter::printDependentSizedExtVectorAfter( 00524 const DependentSizedExtVectorType *T, 00525 raw_ostream &OS) { 00526 OS << " __attribute__((ext_vector_type("; 00527 if (T->getSizeExpr()) 00528 T->getSizeExpr()->printPretty(OS, nullptr, Policy); 00529 OS << ")))"; 00530 printAfter(T->getElementType(), OS); 00531 } 00532 00533 void TypePrinter::printVectorBefore(const VectorType *T, raw_ostream &OS) { 00534 switch (T->getVectorKind()) { 00535 case VectorType::AltiVecPixel: 00536 OS << "__vector __pixel "; 00537 break; 00538 case VectorType::AltiVecBool: 00539 OS << "__vector __bool "; 00540 printBefore(T->getElementType(), OS); 00541 break; 00542 case VectorType::AltiVecVector: 00543 OS << "__vector "; 00544 printBefore(T->getElementType(), OS); 00545 break; 00546 case VectorType::NeonVector: 00547 OS << "__attribute__((neon_vector_type(" 00548 << T->getNumElements() << "))) "; 00549 printBefore(T->getElementType(), OS); 00550 break; 00551 case VectorType::NeonPolyVector: 00552 OS << "__attribute__((neon_polyvector_type(" << 00553 T->getNumElements() << "))) "; 00554 printBefore(T->getElementType(), OS); 00555 break; 00556 case VectorType::GenericVector: { 00557 // FIXME: We prefer to print the size directly here, but have no way 00558 // to get the size of the type. 00559 OS << "__attribute__((__vector_size__(" 00560 << T->getNumElements() 00561 << " * sizeof("; 00562 print(T->getElementType(), OS, StringRef()); 00563 OS << ")))) "; 00564 printBefore(T->getElementType(), OS); 00565 break; 00566 } 00567 } 00568 } 00569 void TypePrinter::printVectorAfter(const VectorType *T, raw_ostream &OS) { 00570 printAfter(T->getElementType(), OS); 00571 } 00572 00573 void TypePrinter::printExtVectorBefore(const ExtVectorType *T, 00574 raw_ostream &OS) { 00575 printBefore(T->getElementType(), OS); 00576 } 00577 void TypePrinter::printExtVectorAfter(const ExtVectorType *T, raw_ostream &OS) { 00578 printAfter(T->getElementType(), OS); 00579 OS << " __attribute__((ext_vector_type("; 00580 OS << T->getNumElements(); 00581 OS << ")))"; 00582 } 00583 00584 void 00585 FunctionProtoType::printExceptionSpecification(raw_ostream &OS, 00586 const PrintingPolicy &Policy) 00587 const { 00588 00589 if (hasDynamicExceptionSpec()) { 00590 OS << " throw("; 00591 if (getExceptionSpecType() == EST_MSAny) 00592 OS << "..."; 00593 else 00594 for (unsigned I = 0, N = getNumExceptions(); I != N; ++I) { 00595 if (I) 00596 OS << ", "; 00597 00598 OS << getExceptionType(I).stream(Policy); 00599 } 00600 OS << ')'; 00601 } else if (isNoexceptExceptionSpec(getExceptionSpecType())) { 00602 OS << " noexcept"; 00603 if (getExceptionSpecType() == EST_ComputedNoexcept) { 00604 OS << '('; 00605 if (getNoexceptExpr()) 00606 getNoexceptExpr()->printPretty(OS, nullptr, Policy); 00607 OS << ')'; 00608 } 00609 } 00610 } 00611 00612 void TypePrinter::printFunctionProtoBefore(const FunctionProtoType *T, 00613 raw_ostream &OS) { 00614 if (T->hasTrailingReturn()) { 00615 OS << "auto "; 00616 if (!HasEmptyPlaceHolder) 00617 OS << '('; 00618 } else { 00619 // If needed for precedence reasons, wrap the inner part in grouping parens. 00620 SaveAndRestore<bool> PrevPHIsEmpty(HasEmptyPlaceHolder, false); 00621 printBefore(T->getReturnType(), OS); 00622 if (!PrevPHIsEmpty.get()) 00623 OS << '('; 00624 } 00625 } 00626 00627 void TypePrinter::printFunctionProtoAfter(const FunctionProtoType *T, 00628 raw_ostream &OS) { 00629 // If needed for precedence reasons, wrap the inner part in grouping parens. 00630 if (!HasEmptyPlaceHolder) 00631 OS << ')'; 00632 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00633 00634 OS << '('; 00635 { 00636 ParamPolicyRAII ParamPolicy(Policy); 00637 for (unsigned i = 0, e = T->getNumParams(); i != e; ++i) { 00638 if (i) OS << ", "; 00639 print(T->getParamType(i), OS, StringRef()); 00640 } 00641 } 00642 00643 if (T->isVariadic()) { 00644 if (T->getNumParams()) 00645 OS << ", "; 00646 OS << "..."; 00647 } else if (T->getNumParams() == 0 && !Policy.LangOpts.CPlusPlus) { 00648 // Do not emit int() if we have a proto, emit 'int(void)'. 00649 OS << "void"; 00650 } 00651 00652 OS << ')'; 00653 00654 FunctionType::ExtInfo Info = T->getExtInfo(); 00655 00656 if (!InsideCCAttribute) { 00657 switch (Info.getCC()) { 00658 case CC_C: 00659 // The C calling convention is the default on the vast majority of platforms 00660 // we support. If the user wrote it explicitly, it will usually be printed 00661 // while traversing the AttributedType. If the type has been desugared, let 00662 // the canonical spelling be the implicit calling convention. 00663 // FIXME: It would be better to be explicit in certain contexts, such as a 00664 // cdecl function typedef used to declare a member function with the 00665 // Microsoft C++ ABI. 00666 break; 00667 case CC_X86StdCall: 00668 OS << " __attribute__((stdcall))"; 00669 break; 00670 case CC_X86FastCall: 00671 OS << " __attribute__((fastcall))"; 00672 break; 00673 case CC_X86ThisCall: 00674 OS << " __attribute__((thiscall))"; 00675 break; 00676 case CC_X86VectorCall: 00677 OS << " __attribute__((vectorcall))"; 00678 break; 00679 case CC_X86Pascal: 00680 OS << " __attribute__((pascal))"; 00681 break; 00682 case CC_AAPCS: 00683 OS << " __attribute__((pcs(\"aapcs\")))"; 00684 break; 00685 case CC_AAPCS_VFP: 00686 OS << " __attribute__((pcs(\"aapcs-vfp\")))"; 00687 break; 00688 case CC_PnaclCall: 00689 OS << " __attribute__((pnaclcall))"; 00690 break; 00691 case CC_IntelOclBicc: 00692 OS << " __attribute__((intel_ocl_bicc))"; 00693 break; 00694 case CC_X86_64Win64: 00695 OS << " __attribute__((ms_abi))"; 00696 break; 00697 case CC_X86_64SysV: 00698 OS << " __attribute__((sysv_abi))"; 00699 break; 00700 } 00701 } 00702 00703 if (Info.getNoReturn()) 00704 OS << " __attribute__((noreturn))"; 00705 if (Info.getRegParm()) 00706 OS << " __attribute__((regparm (" 00707 << Info.getRegParm() << ")))"; 00708 00709 if (unsigned quals = T->getTypeQuals()) { 00710 OS << ' '; 00711 AppendTypeQualList(OS, quals); 00712 } 00713 00714 switch (T->getRefQualifier()) { 00715 case RQ_None: 00716 break; 00717 00718 case RQ_LValue: 00719 OS << " &"; 00720 break; 00721 00722 case RQ_RValue: 00723 OS << " &&"; 00724 break; 00725 } 00726 T->printExceptionSpecification(OS, Policy); 00727 00728 if (T->hasTrailingReturn()) { 00729 OS << " -> "; 00730 print(T->getReturnType(), OS, StringRef()); 00731 } else 00732 printAfter(T->getReturnType(), OS); 00733 } 00734 00735 void TypePrinter::printFunctionNoProtoBefore(const FunctionNoProtoType *T, 00736 raw_ostream &OS) { 00737 // If needed for precedence reasons, wrap the inner part in grouping parens. 00738 SaveAndRestore<bool> PrevPHIsEmpty(HasEmptyPlaceHolder, false); 00739 printBefore(T->getReturnType(), OS); 00740 if (!PrevPHIsEmpty.get()) 00741 OS << '('; 00742 } 00743 void TypePrinter::printFunctionNoProtoAfter(const FunctionNoProtoType *T, 00744 raw_ostream &OS) { 00745 // If needed for precedence reasons, wrap the inner part in grouping parens. 00746 if (!HasEmptyPlaceHolder) 00747 OS << ')'; 00748 SaveAndRestore<bool> NonEmptyPH(HasEmptyPlaceHolder, false); 00749 00750 OS << "()"; 00751 if (T->getNoReturnAttr()) 00752 OS << " __attribute__((noreturn))"; 00753 printAfter(T->getReturnType(), OS); 00754 } 00755 00756 void TypePrinter::printTypeSpec(const NamedDecl *D, raw_ostream &OS) { 00757 IdentifierInfo *II = D->getIdentifier(); 00758 OS << II->getName(); 00759 spaceBeforePlaceHolder(OS); 00760 } 00761 00762 void TypePrinter::printUnresolvedUsingBefore(const UnresolvedUsingType *T, 00763 raw_ostream &OS) { 00764 printTypeSpec(T->getDecl(), OS); 00765 } 00766 void TypePrinter::printUnresolvedUsingAfter(const UnresolvedUsingType *T, 00767 raw_ostream &OS) { } 00768 00769 void TypePrinter::printTypedefBefore(const TypedefType *T, raw_ostream &OS) { 00770 printTypeSpec(T->getDecl(), OS); 00771 } 00772 void TypePrinter::printTypedefAfter(const TypedefType *T, raw_ostream &OS) { } 00773 00774 void TypePrinter::printTypeOfExprBefore(const TypeOfExprType *T, 00775 raw_ostream &OS) { 00776 OS << "typeof "; 00777 if (T->getUnderlyingExpr()) 00778 T->getUnderlyingExpr()->printPretty(OS, nullptr, Policy); 00779 spaceBeforePlaceHolder(OS); 00780 } 00781 void TypePrinter::printTypeOfExprAfter(const TypeOfExprType *T, 00782 raw_ostream &OS) { } 00783 00784 void TypePrinter::printTypeOfBefore(const TypeOfType *T, raw_ostream &OS) { 00785 OS << "typeof("; 00786 print(T->getUnderlyingType(), OS, StringRef()); 00787 OS << ')'; 00788 spaceBeforePlaceHolder(OS); 00789 } 00790 void TypePrinter::printTypeOfAfter(const TypeOfType *T, raw_ostream &OS) { } 00791 00792 void TypePrinter::printDecltypeBefore(const DecltypeType *T, raw_ostream &OS) { 00793 OS << "decltype("; 00794 if (T->getUnderlyingExpr()) 00795 T->getUnderlyingExpr()->printPretty(OS, nullptr, Policy); 00796 OS << ')'; 00797 spaceBeforePlaceHolder(OS); 00798 } 00799 void TypePrinter::printDecltypeAfter(const DecltypeType *T, raw_ostream &OS) { } 00800 00801 void TypePrinter::printUnaryTransformBefore(const UnaryTransformType *T, 00802 raw_ostream &OS) { 00803 IncludeStrongLifetimeRAII Strong(Policy); 00804 00805 switch (T->getUTTKind()) { 00806 case UnaryTransformType::EnumUnderlyingType: 00807 OS << "__underlying_type("; 00808 print(T->getBaseType(), OS, StringRef()); 00809 OS << ')'; 00810 spaceBeforePlaceHolder(OS); 00811 return; 00812 } 00813 00814 printBefore(T->getBaseType(), OS); 00815 } 00816 void TypePrinter::printUnaryTransformAfter(const UnaryTransformType *T, 00817 raw_ostream &OS) { 00818 IncludeStrongLifetimeRAII Strong(Policy); 00819 00820 switch (T->getUTTKind()) { 00821 case UnaryTransformType::EnumUnderlyingType: 00822 return; 00823 } 00824 00825 printAfter(T->getBaseType(), OS); 00826 } 00827 00828 void TypePrinter::printAutoBefore(const AutoType *T, raw_ostream &OS) { 00829 // If the type has been deduced, do not print 'auto'. 00830 if (!T->getDeducedType().isNull()) { 00831 printBefore(T->getDeducedType(), OS); 00832 } else { 00833 OS << (T->isDecltypeAuto() ? "decltype(auto)" : "auto"); 00834 spaceBeforePlaceHolder(OS); 00835 } 00836 } 00837 void TypePrinter::printAutoAfter(const AutoType *T, raw_ostream &OS) { 00838 // If the type has been deduced, do not print 'auto'. 00839 if (!T->getDeducedType().isNull()) 00840 printAfter(T->getDeducedType(), OS); 00841 } 00842 00843 void TypePrinter::printAtomicBefore(const AtomicType *T, raw_ostream &OS) { 00844 IncludeStrongLifetimeRAII Strong(Policy); 00845 00846 OS << "_Atomic("; 00847 print(T->getValueType(), OS, StringRef()); 00848 OS << ')'; 00849 spaceBeforePlaceHolder(OS); 00850 } 00851 void TypePrinter::printAtomicAfter(const AtomicType *T, raw_ostream &OS) { } 00852 00853 /// Appends the given scope to the end of a string. 00854 void TypePrinter::AppendScope(DeclContext *DC, raw_ostream &OS) { 00855 if (DC->isTranslationUnit()) return; 00856 if (DC->isFunctionOrMethod()) return; 00857 AppendScope(DC->getParent(), OS); 00858 00859 if (NamespaceDecl *NS = dyn_cast<NamespaceDecl>(DC)) { 00860 if (Policy.SuppressUnwrittenScope && 00861 (NS->isAnonymousNamespace() || NS->isInline())) 00862 return; 00863 if (NS->getIdentifier()) 00864 OS << NS->getName() << "::"; 00865 else 00866 OS << "(anonymous namespace)::"; 00867 } else if (ClassTemplateSpecializationDecl *Spec 00868 = dyn_cast<ClassTemplateSpecializationDecl>(DC)) { 00869 IncludeStrongLifetimeRAII Strong(Policy); 00870 OS << Spec->getIdentifier()->getName(); 00871 const TemplateArgumentList &TemplateArgs = Spec->getTemplateArgs(); 00872 TemplateSpecializationType::PrintTemplateArgumentList(OS, 00873 TemplateArgs.data(), 00874 TemplateArgs.size(), 00875 Policy); 00876 OS << "::"; 00877 } else if (TagDecl *Tag = dyn_cast<TagDecl>(DC)) { 00878 if (TypedefNameDecl *Typedef = Tag->getTypedefNameForAnonDecl()) 00879 OS << Typedef->getIdentifier()->getName() << "::"; 00880 else if (Tag->getIdentifier()) 00881 OS << Tag->getIdentifier()->getName() << "::"; 00882 else 00883 return; 00884 } 00885 } 00886 00887 void TypePrinter::printTag(TagDecl *D, raw_ostream &OS) { 00888 if (Policy.SuppressTag) 00889 return; 00890 00891 bool HasKindDecoration = false; 00892 00893 // bool SuppressTagKeyword 00894 // = Policy.LangOpts.CPlusPlus || Policy.SuppressTagKeyword; 00895 00896 // We don't print tags unless this is an elaborated type. 00897 // In C, we just assume every RecordType is an elaborated type. 00898 if (!(Policy.LangOpts.CPlusPlus || Policy.SuppressTagKeyword || 00899 D->getTypedefNameForAnonDecl())) { 00900 HasKindDecoration = true; 00901 OS << D->getKindName(); 00902 OS << ' '; 00903 } 00904 00905 // Compute the full nested-name-specifier for this type. 00906 // In C, this will always be empty except when the type 00907 // being printed is anonymous within other Record. 00908 if (!Policy.SuppressScope) 00909 AppendScope(D->getDeclContext(), OS); 00910 00911 if (const IdentifierInfo *II = D->getIdentifier()) 00912 OS << II->getName(); 00913 else if (TypedefNameDecl *Typedef = D->getTypedefNameForAnonDecl()) { 00914 assert(Typedef->getIdentifier() && "Typedef without identifier?"); 00915 OS << Typedef->getIdentifier()->getName(); 00916 } else { 00917 // Make an unambiguous representation for anonymous types, e.g. 00918 // (anonymous enum at /usr/include/string.h:120:9) 00919 00920 if (isa<CXXRecordDecl>(D) && cast<CXXRecordDecl>(D)->isLambda()) { 00921 OS << "(lambda"; 00922 HasKindDecoration = true; 00923 } else { 00924 OS << "(anonymous"; 00925 } 00926 00927 if (Policy.AnonymousTagLocations) { 00928 // Suppress the redundant tag keyword if we just printed one. 00929 // We don't have to worry about ElaboratedTypes here because you can't 00930 // refer to an anonymous type with one. 00931 if (!HasKindDecoration) 00932 OS << " " << D->getKindName(); 00933 00934 PresumedLoc PLoc = D->getASTContext().getSourceManager().getPresumedLoc( 00935 D->getLocation()); 00936 if (PLoc.isValid()) { 00937 OS << " at " << PLoc.getFilename() 00938 << ':' << PLoc.getLine() 00939 << ':' << PLoc.getColumn(); 00940 } 00941 } 00942 00943 OS << ')'; 00944 } 00945 00946 // If this is a class template specialization, print the template 00947 // arguments. 00948 if (ClassTemplateSpecializationDecl *Spec 00949 = dyn_cast<ClassTemplateSpecializationDecl>(D)) { 00950 const TemplateArgument *Args; 00951 unsigned NumArgs; 00952 if (TypeSourceInfo *TAW = Spec->getTypeAsWritten()) { 00953 const TemplateSpecializationType *TST = 00954 cast<TemplateSpecializationType>(TAW->getType()); 00955 Args = TST->getArgs(); 00956 NumArgs = TST->getNumArgs(); 00957 } else { 00958 const TemplateArgumentList &TemplateArgs = Spec->getTemplateArgs(); 00959 Args = TemplateArgs.data(); 00960 NumArgs = TemplateArgs.size(); 00961 } 00962 IncludeStrongLifetimeRAII Strong(Policy); 00963 TemplateSpecializationType::PrintTemplateArgumentList(OS, 00964 Args, NumArgs, 00965 Policy); 00966 } 00967 00968 spaceBeforePlaceHolder(OS); 00969 } 00970 00971 void TypePrinter::printRecordBefore(const RecordType *T, raw_ostream &OS) { 00972 printTag(T->getDecl(), OS); 00973 } 00974 void TypePrinter::printRecordAfter(const RecordType *T, raw_ostream &OS) { } 00975 00976 void TypePrinter::printEnumBefore(const EnumType *T, raw_ostream &OS) { 00977 printTag(T->getDecl(), OS); 00978 } 00979 void TypePrinter::printEnumAfter(const EnumType *T, raw_ostream &OS) { } 00980 00981 void TypePrinter::printTemplateTypeParmBefore(const TemplateTypeParmType *T, 00982 raw_ostream &OS) { 00983 if (IdentifierInfo *Id = T->getIdentifier()) 00984 OS << Id->getName(); 00985 else 00986 OS << "type-parameter-" << T->getDepth() << '-' << T->getIndex(); 00987 spaceBeforePlaceHolder(OS); 00988 } 00989 void TypePrinter::printTemplateTypeParmAfter(const TemplateTypeParmType *T, 00990 raw_ostream &OS) { } 00991 00992 void TypePrinter::printSubstTemplateTypeParmBefore( 00993 const SubstTemplateTypeParmType *T, 00994 raw_ostream &OS) { 00995 IncludeStrongLifetimeRAII Strong(Policy); 00996 printBefore(T->getReplacementType(), OS); 00997 } 00998 void TypePrinter::printSubstTemplateTypeParmAfter( 00999 const SubstTemplateTypeParmType *T, 01000 raw_ostream &OS) { 01001 IncludeStrongLifetimeRAII Strong(Policy); 01002 printAfter(T->getReplacementType(), OS); 01003 } 01004 01005 void TypePrinter::printSubstTemplateTypeParmPackBefore( 01006 const SubstTemplateTypeParmPackType *T, 01007 raw_ostream &OS) { 01008 IncludeStrongLifetimeRAII Strong(Policy); 01009 printTemplateTypeParmBefore(T->getReplacedParameter(), OS); 01010 } 01011 void TypePrinter::printSubstTemplateTypeParmPackAfter( 01012 const SubstTemplateTypeParmPackType *T, 01013 raw_ostream &OS) { 01014 IncludeStrongLifetimeRAII Strong(Policy); 01015 printTemplateTypeParmAfter(T->getReplacedParameter(), OS); 01016 } 01017 01018 void TypePrinter::printTemplateSpecializationBefore( 01019 const TemplateSpecializationType *T, 01020 raw_ostream &OS) { 01021 IncludeStrongLifetimeRAII Strong(Policy); 01022 T->getTemplateName().print(OS, Policy); 01023 01024 TemplateSpecializationType::PrintTemplateArgumentList(OS, 01025 T->getArgs(), 01026 T->getNumArgs(), 01027 Policy); 01028 spaceBeforePlaceHolder(OS); 01029 } 01030 void TypePrinter::printTemplateSpecializationAfter( 01031 const TemplateSpecializationType *T, 01032 raw_ostream &OS) { } 01033 01034 void TypePrinter::printInjectedClassNameBefore(const InjectedClassNameType *T, 01035 raw_ostream &OS) { 01036 printTemplateSpecializationBefore(T->getInjectedTST(), OS); 01037 } 01038 void TypePrinter::printInjectedClassNameAfter(const InjectedClassNameType *T, 01039 raw_ostream &OS) { } 01040 01041 void TypePrinter::printElaboratedBefore(const ElaboratedType *T, 01042 raw_ostream &OS) { 01043 if (Policy.SuppressTag && isa<TagType>(T->getNamedType())) 01044 return; 01045 OS << TypeWithKeyword::getKeywordName(T->getKeyword()); 01046 if (T->getKeyword() != ETK_None) 01047 OS << " "; 01048 NestedNameSpecifier* Qualifier = T->getQualifier(); 01049 if (Qualifier) 01050 Qualifier->print(OS, Policy); 01051 01052 ElaboratedTypePolicyRAII PolicyRAII(Policy); 01053 printBefore(T->getNamedType(), OS); 01054 } 01055 void TypePrinter::printElaboratedAfter(const ElaboratedType *T, 01056 raw_ostream &OS) { 01057 ElaboratedTypePolicyRAII PolicyRAII(Policy); 01058 printAfter(T->getNamedType(), OS); 01059 } 01060 01061 void TypePrinter::printParenBefore(const ParenType *T, raw_ostream &OS) { 01062 if (!HasEmptyPlaceHolder && !isa<FunctionType>(T->getInnerType())) { 01063 printBefore(T->getInnerType(), OS); 01064 OS << '('; 01065 } else 01066 printBefore(T->getInnerType(), OS); 01067 } 01068 void TypePrinter::printParenAfter(const ParenType *T, raw_ostream &OS) { 01069 if (!HasEmptyPlaceHolder && !isa<FunctionType>(T->getInnerType())) { 01070 OS << ')'; 01071 printAfter(T->getInnerType(), OS); 01072 } else 01073 printAfter(T->getInnerType(), OS); 01074 } 01075 01076 void TypePrinter::printDependentNameBefore(const DependentNameType *T, 01077 raw_ostream &OS) { 01078 OS << TypeWithKeyword::getKeywordName(T->getKeyword()); 01079 if (T->getKeyword() != ETK_None) 01080 OS << " "; 01081 01082 T->getQualifier()->print(OS, Policy); 01083 01084 OS << T->getIdentifier()->getName(); 01085 spaceBeforePlaceHolder(OS); 01086 } 01087 void TypePrinter::printDependentNameAfter(const DependentNameType *T, 01088 raw_ostream &OS) { } 01089 01090 void TypePrinter::printDependentTemplateSpecializationBefore( 01091 const DependentTemplateSpecializationType *T, raw_ostream &OS) { 01092 IncludeStrongLifetimeRAII Strong(Policy); 01093 01094 OS << TypeWithKeyword::getKeywordName(T->getKeyword()); 01095 if (T->getKeyword() != ETK_None) 01096 OS << " "; 01097 01098 if (T->getQualifier()) 01099 T->getQualifier()->print(OS, Policy); 01100 OS << T->getIdentifier()->getName(); 01101 TemplateSpecializationType::PrintTemplateArgumentList(OS, 01102 T->getArgs(), 01103 T->getNumArgs(), 01104 Policy); 01105 spaceBeforePlaceHolder(OS); 01106 } 01107 void TypePrinter::printDependentTemplateSpecializationAfter( 01108 const DependentTemplateSpecializationType *T, raw_ostream &OS) { } 01109 01110 void TypePrinter::printPackExpansionBefore(const PackExpansionType *T, 01111 raw_ostream &OS) { 01112 printBefore(T->getPattern(), OS); 01113 } 01114 void TypePrinter::printPackExpansionAfter(const PackExpansionType *T, 01115 raw_ostream &OS) { 01116 printAfter(T->getPattern(), OS); 01117 OS << "..."; 01118 } 01119 01120 void TypePrinter::printAttributedBefore(const AttributedType *T, 01121 raw_ostream &OS) { 01122 // Prefer the macro forms of the GC and ownership qualifiers. 01123 if (T->getAttrKind() == AttributedType::attr_objc_gc || 01124 T->getAttrKind() == AttributedType::attr_objc_ownership) 01125 return printBefore(T->getEquivalentType(), OS); 01126 01127 printBefore(T->getModifiedType(), OS); 01128 01129 if (T->isMSTypeSpec()) { 01130 switch (T->getAttrKind()) { 01131 default: return; 01132 case AttributedType::attr_ptr32: OS << " __ptr32"; break; 01133 case AttributedType::attr_ptr64: OS << " __ptr64"; break; 01134 case AttributedType::attr_sptr: OS << " __sptr"; break; 01135 case AttributedType::attr_uptr: OS << " __uptr"; break; 01136 } 01137 spaceBeforePlaceHolder(OS); 01138 } 01139 } 01140 01141 void TypePrinter::printAttributedAfter(const AttributedType *T, 01142 raw_ostream &OS) { 01143 // Prefer the macro forms of the GC and ownership qualifiers. 01144 if (T->getAttrKind() == AttributedType::attr_objc_gc || 01145 T->getAttrKind() == AttributedType::attr_objc_ownership) 01146 return printAfter(T->getEquivalentType(), OS); 01147 01148 // TODO: not all attributes are GCC-style attributes. 01149 if (T->isMSTypeSpec()) 01150 return; 01151 01152 // If this is a calling convention attribute, don't print the implicit CC from 01153 // the modified type. 01154 SaveAndRestore<bool> MaybeSuppressCC(InsideCCAttribute, T->isCallingConv()); 01155 01156 printAfter(T->getModifiedType(), OS); 01157 01158 OS << " __attribute__(("; 01159 switch (T->getAttrKind()) { 01160 default: llvm_unreachable("This attribute should have been handled already"); 01161 case AttributedType::attr_address_space: 01162 OS << "address_space("; 01163 OS << T->getEquivalentType().getAddressSpace(); 01164 OS << ')'; 01165 break; 01166 01167 case AttributedType::attr_vector_size: { 01168 OS << "__vector_size__("; 01169 if (const VectorType *vector =T->getEquivalentType()->getAs<VectorType>()) { 01170 OS << vector->getNumElements(); 01171 OS << " * sizeof("; 01172 print(vector->getElementType(), OS, StringRef()); 01173 OS << ')'; 01174 } 01175 OS << ')'; 01176 break; 01177 } 01178 01179 case AttributedType::attr_neon_vector_type: 01180 case AttributedType::attr_neon_polyvector_type: { 01181 if (T->getAttrKind() == AttributedType::attr_neon_vector_type) 01182 OS << "neon_vector_type("; 01183 else 01184 OS << "neon_polyvector_type("; 01185 const VectorType *vector = T->getEquivalentType()->getAs<VectorType>(); 01186 OS << vector->getNumElements(); 01187 OS << ')'; 01188 break; 01189 } 01190 01191 case AttributedType::attr_regparm: { 01192 // FIXME: When Sema learns to form this AttributedType, avoid printing the 01193 // attribute again in printFunctionProtoAfter. 01194 OS << "regparm("; 01195 QualType t = T->getEquivalentType(); 01196 while (!t->isFunctionType()) 01197 t = t->getPointeeType(); 01198 OS << t->getAs<FunctionType>()->getRegParmType(); 01199 OS << ')'; 01200 break; 01201 } 01202 01203 case AttributedType::attr_objc_gc: { 01204 OS << "objc_gc("; 01205 01206 QualType tmp = T->getEquivalentType(); 01207 while (tmp.getObjCGCAttr() == Qualifiers::GCNone) { 01208 QualType next = tmp->getPointeeType(); 01209 if (next == tmp) break; 01210 tmp = next; 01211 } 01212 01213 if (tmp.isObjCGCWeak()) 01214 OS << "weak"; 01215 else 01216 OS << "strong"; 01217 OS << ')'; 01218 break; 01219 } 01220 01221 case AttributedType::attr_objc_ownership: 01222 OS << "objc_ownership("; 01223 switch (T->getEquivalentType().getObjCLifetime()) { 01224 case Qualifiers::OCL_None: llvm_unreachable("no ownership!"); 01225 case Qualifiers::OCL_ExplicitNone: OS << "none"; break; 01226 case Qualifiers::OCL_Strong: OS << "strong"; break; 01227 case Qualifiers::OCL_Weak: OS << "weak"; break; 01228 case Qualifiers::OCL_Autoreleasing: OS << "autoreleasing"; break; 01229 } 01230 OS << ')'; 01231 break; 01232 01233 // FIXME: When Sema learns to form this AttributedType, avoid printing the 01234 // attribute again in printFunctionProtoAfter. 01235 case AttributedType::attr_noreturn: OS << "noreturn"; break; 01236 01237 case AttributedType::attr_cdecl: OS << "cdecl"; break; 01238 case AttributedType::attr_fastcall: OS << "fastcall"; break; 01239 case AttributedType::attr_stdcall: OS << "stdcall"; break; 01240 case AttributedType::attr_thiscall: OS << "thiscall"; break; 01241 case AttributedType::attr_vectorcall: OS << "vectorcall"; break; 01242 case AttributedType::attr_pascal: OS << "pascal"; break; 01243 case AttributedType::attr_ms_abi: OS << "ms_abi"; break; 01244 case AttributedType::attr_sysv_abi: OS << "sysv_abi"; break; 01245 case AttributedType::attr_pcs: 01246 case AttributedType::attr_pcs_vfp: { 01247 OS << "pcs("; 01248 QualType t = T->getEquivalentType(); 01249 while (!t->isFunctionType()) 01250 t = t->getPointeeType(); 01251 OS << (t->getAs<FunctionType>()->getCallConv() == CC_AAPCS ? 01252 "\"aapcs\"" : "\"aapcs-vfp\""); 01253 OS << ')'; 01254 break; 01255 } 01256 case AttributedType::attr_pnaclcall: OS << "pnaclcall"; break; 01257 case AttributedType::attr_inteloclbicc: OS << "inteloclbicc"; break; 01258 } 01259 OS << "))"; 01260 } 01261 01262 void TypePrinter::printObjCInterfaceBefore(const ObjCInterfaceType *T, 01263 raw_ostream &OS) { 01264 OS << T->getDecl()->getName(); 01265 spaceBeforePlaceHolder(OS); 01266 } 01267 void TypePrinter::printObjCInterfaceAfter(const ObjCInterfaceType *T, 01268 raw_ostream &OS) { } 01269 01270 void TypePrinter::printObjCObjectBefore(const ObjCObjectType *T, 01271 raw_ostream &OS) { 01272 if (T->qual_empty()) 01273 return printBefore(T->getBaseType(), OS); 01274 01275 print(T->getBaseType(), OS, StringRef()); 01276 OS << '<'; 01277 bool isFirst = true; 01278 for (const auto *I : T->quals()) { 01279 if (isFirst) 01280 isFirst = false; 01281 else 01282 OS << ','; 01283 OS << I->getName(); 01284 } 01285 OS << '>'; 01286 spaceBeforePlaceHolder(OS); 01287 } 01288 void TypePrinter::printObjCObjectAfter(const ObjCObjectType *T, 01289 raw_ostream &OS) { 01290 if (T->qual_empty()) 01291 return printAfter(T->getBaseType(), OS); 01292 } 01293 01294 void TypePrinter::printObjCObjectPointerBefore(const ObjCObjectPointerType *T, 01295 raw_ostream &OS) { 01296 T->getPointeeType().getLocalQualifiers().print(OS, Policy, 01297 /*appendSpaceIfNonEmpty=*/true); 01298 01299 assert(!T->isObjCSelType()); 01300 01301 if (T->isObjCIdType() || T->isObjCQualifiedIdType()) 01302 OS << "id"; 01303 else if (T->isObjCClassType() || T->isObjCQualifiedClassType()) 01304 OS << "Class"; 01305 else 01306 OS << T->getInterfaceDecl()->getName(); 01307 01308 if (!T->qual_empty()) { 01309 OS << '<'; 01310 for (ObjCObjectPointerType::qual_iterator I = T->qual_begin(), 01311 E = T->qual_end(); 01312 I != E; ++I) { 01313 OS << (*I)->getName(); 01314 if (I+1 != E) 01315 OS << ','; 01316 } 01317 OS << '>'; 01318 } 01319 01320 if (!T->isObjCIdType() && !T->isObjCQualifiedIdType() && 01321 !T->isObjCClassType() && !T->isObjCQualifiedClassType()) { 01322 OS << " *"; // Don't forget the implicit pointer. 01323 } else { 01324 spaceBeforePlaceHolder(OS); 01325 } 01326 } 01327 void TypePrinter::printObjCObjectPointerAfter(const ObjCObjectPointerType *T, 01328 raw_ostream &OS) { } 01329 01330 void TemplateSpecializationType:: 01331 PrintTemplateArgumentList(raw_ostream &OS, 01332 const TemplateArgumentListInfo &Args, 01333 const PrintingPolicy &Policy) { 01334 return PrintTemplateArgumentList(OS, 01335 Args.getArgumentArray(), 01336 Args.size(), 01337 Policy); 01338 } 01339 01340 void 01341 TemplateSpecializationType::PrintTemplateArgumentList( 01342 raw_ostream &OS, 01343 const TemplateArgument *Args, 01344 unsigned NumArgs, 01345 const PrintingPolicy &Policy, 01346 bool SkipBrackets) { 01347 if (!SkipBrackets) 01348 OS << '<'; 01349 01350 bool needSpace = false; 01351 for (unsigned Arg = 0; Arg < NumArgs; ++Arg) { 01352 // Print the argument into a string. 01353 SmallString<128> Buf; 01354 llvm::raw_svector_ostream ArgOS(Buf); 01355 if (Args[Arg].getKind() == TemplateArgument::Pack) { 01356 if (Args[Arg].pack_size() && Arg > 0) 01357 OS << ", "; 01358 PrintTemplateArgumentList(ArgOS, 01359 Args[Arg].pack_begin(), 01360 Args[Arg].pack_size(), 01361 Policy, true); 01362 } else { 01363 if (Arg > 0) 01364 OS << ", "; 01365 Args[Arg].print(Policy, ArgOS); 01366 } 01367 StringRef ArgString = ArgOS.str(); 01368 01369 // If this is the first argument and its string representation 01370 // begins with the global scope specifier ('::foo'), add a space 01371 // to avoid printing the diagraph '<:'. 01372 if (!Arg && !ArgString.empty() && ArgString[0] == ':') 01373 OS << ' '; 01374 01375 OS << ArgString; 01376 01377 needSpace = (!ArgString.empty() && ArgString.back() == '>'); 01378 } 01379 01380 // If the last character of our string is '>', add another space to 01381 // keep the two '>''s separate tokens. We don't *have* to do this in 01382 // C++0x, but it's still good hygiene. 01383 if (needSpace) 01384 OS << ' '; 01385 01386 if (!SkipBrackets) 01387 OS << '>'; 01388 } 01389 01390 // Sadly, repeat all that with TemplateArgLoc. 01391 void TemplateSpecializationType:: 01392 PrintTemplateArgumentList(raw_ostream &OS, 01393 const TemplateArgumentLoc *Args, unsigned NumArgs, 01394 const PrintingPolicy &Policy) { 01395 OS << '<'; 01396 01397 bool needSpace = false; 01398 for (unsigned Arg = 0; Arg < NumArgs; ++Arg) { 01399 if (Arg > 0) 01400 OS << ", "; 01401 01402 // Print the argument into a string. 01403 SmallString<128> Buf; 01404 llvm::raw_svector_ostream ArgOS(Buf); 01405 if (Args[Arg].getArgument().getKind() == TemplateArgument::Pack) { 01406 PrintTemplateArgumentList(ArgOS, 01407 Args[Arg].getArgument().pack_begin(), 01408 Args[Arg].getArgument().pack_size(), 01409 Policy, true); 01410 } else { 01411 Args[Arg].getArgument().print(Policy, ArgOS); 01412 } 01413 StringRef ArgString = ArgOS.str(); 01414 01415 // If this is the first argument and its string representation 01416 // begins with the global scope specifier ('::foo'), add a space 01417 // to avoid printing the diagraph '<:'. 01418 if (!Arg && !ArgString.empty() && ArgString[0] == ':') 01419 OS << ' '; 01420 01421 OS << ArgString; 01422 01423 needSpace = (!ArgString.empty() && ArgString.back() == '>'); 01424 } 01425 01426 // If the last character of our string is '>', add another space to 01427 // keep the two '>''s separate tokens. We don't *have* to do this in 01428 // C++0x, but it's still good hygiene. 01429 if (needSpace) 01430 OS << ' '; 01431 01432 OS << '>'; 01433 } 01434 01435 std::string Qualifiers::getAsString() const { 01436 LangOptions LO; 01437 return getAsString(PrintingPolicy(LO)); 01438 } 01439 01440 // Appends qualifiers to the given string, separated by spaces. Will 01441 // prefix a space if the string is non-empty. Will not append a final 01442 // space. 01443 std::string Qualifiers::getAsString(const PrintingPolicy &Policy) const { 01444 SmallString<64> Buf; 01445 llvm::raw_svector_ostream StrOS(Buf); 01446 print(StrOS, Policy); 01447 return StrOS.str(); 01448 } 01449 01450 bool Qualifiers::isEmptyWhenPrinted(const PrintingPolicy &Policy) const { 01451 if (getCVRQualifiers()) 01452 return false; 01453 01454 if (getAddressSpace()) 01455 return false; 01456 01457 if (getObjCGCAttr()) 01458 return false; 01459 01460 if (Qualifiers::ObjCLifetime lifetime = getObjCLifetime()) 01461 if (!(lifetime == Qualifiers::OCL_Strong && Policy.SuppressStrongLifetime)) 01462 return false; 01463 01464 return true; 01465 } 01466 01467 // Appends qualifiers to the given string, separated by spaces. Will 01468 // prefix a space if the string is non-empty. Will not append a final 01469 // space. 01470 void Qualifiers::print(raw_ostream &OS, const PrintingPolicy& Policy, 01471 bool appendSpaceIfNonEmpty) const { 01472 bool addSpace = false; 01473 01474 unsigned quals = getCVRQualifiers(); 01475 if (quals) { 01476 AppendTypeQualList(OS, quals); 01477 addSpace = true; 01478 } 01479 if (unsigned addrspace = getAddressSpace()) { 01480 if (addSpace) 01481 OS << ' '; 01482 addSpace = true; 01483 switch (addrspace) { 01484 case LangAS::opencl_global: 01485 OS << "__global"; 01486 break; 01487 case LangAS::opencl_local: 01488 OS << "__local"; 01489 break; 01490 case LangAS::opencl_constant: 01491 OS << "__constant"; 01492 break; 01493 default: 01494 OS << "__attribute__((address_space("; 01495 OS << addrspace; 01496 OS << ")))"; 01497 } 01498 } 01499 if (Qualifiers::GC gc = getObjCGCAttr()) { 01500 if (addSpace) 01501 OS << ' '; 01502 addSpace = true; 01503 if (gc == Qualifiers::Weak) 01504 OS << "__weak"; 01505 else 01506 OS << "__strong"; 01507 } 01508 if (Qualifiers::ObjCLifetime lifetime = getObjCLifetime()) { 01509 if (!(lifetime == Qualifiers::OCL_Strong && Policy.SuppressStrongLifetime)){ 01510 if (addSpace) 01511 OS << ' '; 01512 addSpace = true; 01513 } 01514 01515 switch (lifetime) { 01516 case Qualifiers::OCL_None: llvm_unreachable("none but true"); 01517 case Qualifiers::OCL_ExplicitNone: OS << "__unsafe_unretained"; break; 01518 case Qualifiers::OCL_Strong: 01519 if (!Policy.SuppressStrongLifetime) 01520 OS << "__strong"; 01521 break; 01522 01523 case Qualifiers::OCL_Weak: OS << "__weak"; break; 01524 case Qualifiers::OCL_Autoreleasing: OS << "__autoreleasing"; break; 01525 } 01526 } 01527 01528 if (appendSpaceIfNonEmpty && addSpace) 01529 OS << ' '; 01530 } 01531 01532 std::string QualType::getAsString(const PrintingPolicy &Policy) const { 01533 std::string S; 01534 getAsStringInternal(S, Policy); 01535 return S; 01536 } 01537 01538 std::string QualType::getAsString(const Type *ty, Qualifiers qs) { 01539 std::string buffer; 01540 LangOptions options; 01541 getAsStringInternal(ty, qs, buffer, PrintingPolicy(options)); 01542 return buffer; 01543 } 01544 01545 void QualType::print(const Type *ty, Qualifiers qs, 01546 raw_ostream &OS, const PrintingPolicy &policy, 01547 const Twine &PlaceHolder) { 01548 SmallString<128> PHBuf; 01549 StringRef PH = PlaceHolder.toStringRef(PHBuf); 01550 01551 TypePrinter(policy).print(ty, qs, OS, PH); 01552 } 01553 01554 void QualType::getAsStringInternal(const Type *ty, Qualifiers qs, 01555 std::string &buffer, 01556 const PrintingPolicy &policy) { 01557 SmallString<256> Buf; 01558 llvm::raw_svector_ostream StrOS(Buf); 01559 TypePrinter(policy).print(ty, qs, StrOS, buffer); 01560 std::string str = StrOS.str(); 01561 buffer.swap(str); 01562 }