DeclSpec.cpp revision 1ab0d90af489b5441d0bf25338d420ddae3ece74
1//===--- SemaDeclSpec.cpp - Declaration Specifier Semantic Analysis -------===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9// 10// This file implements semantic analysis for declaration specifiers. 11// 12//===----------------------------------------------------------------------===// 13 14#include "clang/Parse/ParseDiagnostic.h" // FIXME: remove this back-dependency! 15#include "clang/Sema/DeclSpec.h" 16#include "clang/Sema/LocInfoType.h" 17#include "clang/Sema/ParsedTemplate.h" 18#include "clang/AST/ASTContext.h" 19#include "clang/AST/Expr.h" 20#include "clang/AST/NestedNameSpecifier.h" 21#include "clang/AST/TypeLoc.h" 22#include "clang/Lex/Preprocessor.h" 23#include "clang/Basic/LangOptions.h" 24#include "llvm/ADT/STLExtras.h" 25#include "llvm/Support/ErrorHandling.h" 26#include <cstring> 27using namespace clang; 28 29 30static DiagnosticBuilder Diag(Diagnostic &D, SourceLocation Loc, 31 unsigned DiagID) { 32 return D.Report(Loc, DiagID); 33} 34 35 36void UnqualifiedId::setTemplateId(TemplateIdAnnotation *TemplateId) { 37 assert(TemplateId && "NULL template-id annotation?"); 38 Kind = IK_TemplateId; 39 this->TemplateId = TemplateId; 40 StartLocation = TemplateId->TemplateNameLoc; 41 EndLocation = TemplateId->RAngleLoc; 42} 43 44void UnqualifiedId::setConstructorTemplateId(TemplateIdAnnotation *TemplateId) { 45 assert(TemplateId && "NULL template-id annotation?"); 46 Kind = IK_ConstructorTemplateId; 47 this->TemplateId = TemplateId; 48 StartLocation = TemplateId->TemplateNameLoc; 49 EndLocation = TemplateId->RAngleLoc; 50} 51 52void CXXScopeSpec::Extend(ASTContext &Context, SourceLocation TemplateKWLoc, 53 TypeLoc TL, SourceLocation ColonColonLoc) { 54 Builder.Extend(Context, TemplateKWLoc, TL, ColonColonLoc); 55 if (Range.getBegin().isInvalid()) 56 Range.setBegin(TL.getBeginLoc()); 57 Range.setEnd(ColonColonLoc); 58 59 assert(Range == Builder.getSourceRange() && 60 "NestedNameSpecifierLoc range computation incorrect"); 61} 62 63void CXXScopeSpec::Extend(ASTContext &Context, IdentifierInfo *Identifier, 64 SourceLocation IdentifierLoc, 65 SourceLocation ColonColonLoc) { 66 Builder.Extend(Context, Identifier, IdentifierLoc, ColonColonLoc); 67 68 if (Range.getBegin().isInvalid()) 69 Range.setBegin(IdentifierLoc); 70 Range.setEnd(ColonColonLoc); 71 72 assert(Range == Builder.getSourceRange() && 73 "NestedNameSpecifierLoc range computation incorrect"); 74} 75 76void CXXScopeSpec::Extend(ASTContext &Context, NamespaceDecl *Namespace, 77 SourceLocation NamespaceLoc, 78 SourceLocation ColonColonLoc) { 79 Builder.Extend(Context, Namespace, NamespaceLoc, ColonColonLoc); 80 81 if (Range.getBegin().isInvalid()) 82 Range.setBegin(NamespaceLoc); 83 Range.setEnd(ColonColonLoc); 84 85 assert(Range == Builder.getSourceRange() && 86 "NestedNameSpecifierLoc range computation incorrect"); 87} 88 89void CXXScopeSpec::Extend(ASTContext &Context, NamespaceAliasDecl *Alias, 90 SourceLocation AliasLoc, 91 SourceLocation ColonColonLoc) { 92 Builder.Extend(Context, Alias, AliasLoc, ColonColonLoc); 93 94 if (Range.getBegin().isInvalid()) 95 Range.setBegin(AliasLoc); 96 Range.setEnd(ColonColonLoc); 97 98 assert(Range == Builder.getSourceRange() && 99 "NestedNameSpecifierLoc range computation incorrect"); 100} 101 102void CXXScopeSpec::MakeGlobal(ASTContext &Context, 103 SourceLocation ColonColonLoc) { 104 Builder.MakeGlobal(Context, ColonColonLoc); 105 106 Range = SourceRange(ColonColonLoc); 107 108 assert(Range == Builder.getSourceRange() && 109 "NestedNameSpecifierLoc range computation incorrect"); 110} 111 112void CXXScopeSpec::MakeTrivial(ASTContext &Context, 113 NestedNameSpecifier *Qualifier, SourceRange R) { 114 Builder.MakeTrivial(Context, Qualifier, R); 115 Range = R; 116} 117 118void CXXScopeSpec::Adopt(NestedNameSpecifierLoc Other) { 119 if (!Other) { 120 Range = SourceRange(); 121 Builder.Clear(); 122 return; 123 } 124 125 Range = Other.getSourceRange(); 126 Builder.Adopt(Other); 127} 128 129NestedNameSpecifierLoc 130CXXScopeSpec::getWithLocInContext(ASTContext &Context) const { 131 if (!Builder.getRepresentation()) 132 return NestedNameSpecifierLoc(); 133 134 return Builder.getWithLocInContext(Context); 135} 136 137/// DeclaratorChunk::getFunction - Return a DeclaratorChunk for a function. 138/// "TheDeclarator" is the declarator that this will be added to. 139DeclaratorChunk DeclaratorChunk::getFunction(bool hasProto, bool isVariadic, 140 SourceLocation EllipsisLoc, 141 ParamInfo *ArgInfo, 142 unsigned NumArgs, 143 unsigned TypeQuals, 144 bool RefQualifierIsLvalueRef, 145 SourceLocation RefQualifierLoc, 146 ExceptionSpecificationType 147 ESpecType, 148 SourceLocation ESpecLoc, 149 ParsedType *Exceptions, 150 SourceRange *ExceptionRanges, 151 unsigned NumExceptions, 152 Expr *NoexceptExpr, 153 SourceLocation LocalRangeBegin, 154 SourceLocation LocalRangeEnd, 155 Declarator &TheDeclarator, 156 ParsedType TrailingReturnType) { 157 DeclaratorChunk I; 158 I.Kind = Function; 159 I.Loc = LocalRangeBegin; 160 I.EndLoc = LocalRangeEnd; 161 I.Fun.AttrList = 0; 162 I.Fun.hasPrototype = hasProto; 163 I.Fun.isVariadic = isVariadic; 164 I.Fun.EllipsisLoc = EllipsisLoc.getRawEncoding(); 165 I.Fun.DeleteArgInfo = false; 166 I.Fun.TypeQuals = TypeQuals; 167 I.Fun.NumArgs = NumArgs; 168 I.Fun.ArgInfo = 0; 169 I.Fun.RefQualifierIsLValueRef = RefQualifierIsLvalueRef; 170 I.Fun.RefQualifierLoc = RefQualifierLoc.getRawEncoding(); 171 I.Fun.ExceptionSpecType = ESpecType; 172 I.Fun.ExceptionSpecLoc = ESpecLoc.getRawEncoding(); 173 I.Fun.NumExceptions = 0; 174 I.Fun.Exceptions = 0; 175 I.Fun.NoexceptExpr = 0; 176 I.Fun.TrailingReturnType = TrailingReturnType.getAsOpaquePtr(); 177 178 // new[] an argument array if needed. 179 if (NumArgs) { 180 // If the 'InlineParams' in Declarator is unused and big enough, put our 181 // parameter list there (in an effort to avoid new/delete traffic). If it 182 // is already used (consider a function returning a function pointer) or too 183 // small (function taking too many arguments), go to the heap. 184 if (!TheDeclarator.InlineParamsUsed && 185 NumArgs <= llvm::array_lengthof(TheDeclarator.InlineParams)) { 186 I.Fun.ArgInfo = TheDeclarator.InlineParams; 187 I.Fun.DeleteArgInfo = false; 188 TheDeclarator.InlineParamsUsed = true; 189 } else { 190 I.Fun.ArgInfo = new DeclaratorChunk::ParamInfo[NumArgs]; 191 I.Fun.DeleteArgInfo = true; 192 } 193 memcpy(I.Fun.ArgInfo, ArgInfo, sizeof(ArgInfo[0])*NumArgs); 194 } 195 196 // Check what exception specification information we should actually store. 197 switch (ESpecType) { 198 default: break; // By default, save nothing. 199 case EST_Dynamic: 200 // new[] an exception array if needed 201 if (NumExceptions) { 202 I.Fun.NumExceptions = NumExceptions; 203 I.Fun.Exceptions = new DeclaratorChunk::TypeAndRange[NumExceptions]; 204 for (unsigned i = 0; i != NumExceptions; ++i) { 205 I.Fun.Exceptions[i].Ty = Exceptions[i]; 206 I.Fun.Exceptions[i].Range = ExceptionRanges[i]; 207 } 208 } 209 break; 210 211 case EST_ComputedNoexcept: 212 I.Fun.NoexceptExpr = NoexceptExpr; 213 break; 214 } 215 return I; 216} 217 218bool Declarator::isDeclarationOfFunction() const { 219 for (unsigned i = 0, i_end = DeclTypeInfo.size(); i < i_end; ++i) { 220 switch (DeclTypeInfo[i].Kind) { 221 case DeclaratorChunk::Function: 222 return true; 223 case DeclaratorChunk::Paren: 224 continue; 225 case DeclaratorChunk::Pointer: 226 case DeclaratorChunk::Reference: 227 case DeclaratorChunk::Array: 228 case DeclaratorChunk::BlockPointer: 229 case DeclaratorChunk::MemberPointer: 230 return false; 231 } 232 llvm_unreachable("Invalid type chunk"); 233 return false; 234 } 235 236 switch (DS.getTypeSpecType()) { 237 case TST_auto: 238 case TST_bool: 239 case TST_char: 240 case TST_char16: 241 case TST_char32: 242 case TST_class: 243 case TST_decimal128: 244 case TST_decimal32: 245 case TST_decimal64: 246 case TST_double: 247 case TST_enum: 248 case TST_error: 249 case TST_float: 250 case TST_int: 251 case TST_struct: 252 case TST_union: 253 case TST_unknown_anytype: 254 case TST_unspecified: 255 case TST_void: 256 case TST_wchar: 257 return false; 258 259 case TST_decltype: 260 case TST_typeofExpr: 261 if (Expr *E = DS.getRepAsExpr()) 262 return E->getType()->isFunctionType(); 263 return false; 264 265 case TST_underlyingType: 266 case TST_typename: 267 case TST_typeofType: { 268 QualType QT = DS.getRepAsType().get(); 269 if (QT.isNull()) 270 return false; 271 272 if (const LocInfoType *LIT = dyn_cast<LocInfoType>(QT)) 273 QT = LIT->getType(); 274 275 if (QT.isNull()) 276 return false; 277 278 return QT->isFunctionType(); 279 } 280 } 281 282 return false; 283} 284 285/// getParsedSpecifiers - Return a bitmask of which flavors of specifiers this 286/// declaration specifier includes. 287/// 288unsigned DeclSpec::getParsedSpecifiers() const { 289 unsigned Res = 0; 290 if (StorageClassSpec != SCS_unspecified || 291 SCS_thread_specified) 292 Res |= PQ_StorageClassSpecifier; 293 294 if (TypeQualifiers != TQ_unspecified) 295 Res |= PQ_TypeQualifier; 296 297 if (hasTypeSpecifier()) 298 Res |= PQ_TypeSpecifier; 299 300 if (FS_inline_specified || FS_virtual_specified || FS_explicit_specified) 301 Res |= PQ_FunctionSpecifier; 302 return Res; 303} 304 305template <class T> static bool BadSpecifier(T TNew, T TPrev, 306 const char *&PrevSpec, 307 unsigned &DiagID) { 308 PrevSpec = DeclSpec::getSpecifierName(TPrev); 309 DiagID = (TNew == TPrev ? diag::ext_duplicate_declspec 310 : diag::err_invalid_decl_spec_combination); 311 return true; 312} 313 314const char *DeclSpec::getSpecifierName(DeclSpec::SCS S) { 315 switch (S) { 316 case DeclSpec::SCS_unspecified: return "unspecified"; 317 case DeclSpec::SCS_typedef: return "typedef"; 318 case DeclSpec::SCS_extern: return "extern"; 319 case DeclSpec::SCS_static: return "static"; 320 case DeclSpec::SCS_auto: return "auto"; 321 case DeclSpec::SCS_register: return "register"; 322 case DeclSpec::SCS_private_extern: return "__private_extern__"; 323 case DeclSpec::SCS_mutable: return "mutable"; 324 } 325 llvm_unreachable("Unknown typespec!"); 326} 327 328const char *DeclSpec::getSpecifierName(TSW W) { 329 switch (W) { 330 case TSW_unspecified: return "unspecified"; 331 case TSW_short: return "short"; 332 case TSW_long: return "long"; 333 case TSW_longlong: return "long long"; 334 } 335 llvm_unreachable("Unknown typespec!"); 336} 337 338const char *DeclSpec::getSpecifierName(TSC C) { 339 switch (C) { 340 case TSC_unspecified: return "unspecified"; 341 case TSC_imaginary: return "imaginary"; 342 case TSC_complex: return "complex"; 343 } 344 llvm_unreachable("Unknown typespec!"); 345} 346 347 348const char *DeclSpec::getSpecifierName(TSS S) { 349 switch (S) { 350 case TSS_unspecified: return "unspecified"; 351 case TSS_signed: return "signed"; 352 case TSS_unsigned: return "unsigned"; 353 } 354 llvm_unreachable("Unknown typespec!"); 355} 356 357const char *DeclSpec::getSpecifierName(DeclSpec::TST T) { 358 switch (T) { 359 case DeclSpec::TST_unspecified: return "unspecified"; 360 case DeclSpec::TST_void: return "void"; 361 case DeclSpec::TST_char: return "char"; 362 case DeclSpec::TST_wchar: return "wchar_t"; 363 case DeclSpec::TST_char16: return "char16_t"; 364 case DeclSpec::TST_char32: return "char32_t"; 365 case DeclSpec::TST_int: return "int"; 366 case DeclSpec::TST_float: return "float"; 367 case DeclSpec::TST_double: return "double"; 368 case DeclSpec::TST_bool: return "_Bool"; 369 case DeclSpec::TST_decimal32: return "_Decimal32"; 370 case DeclSpec::TST_decimal64: return "_Decimal64"; 371 case DeclSpec::TST_decimal128: return "_Decimal128"; 372 case DeclSpec::TST_enum: return "enum"; 373 case DeclSpec::TST_class: return "class"; 374 case DeclSpec::TST_union: return "union"; 375 case DeclSpec::TST_struct: return "struct"; 376 case DeclSpec::TST_typename: return "type-name"; 377 case DeclSpec::TST_typeofType: 378 case DeclSpec::TST_typeofExpr: return "typeof"; 379 case DeclSpec::TST_auto: return "auto"; 380 case DeclSpec::TST_decltype: return "(decltype)"; 381 case DeclSpec::TST_underlyingType: return "__underlying_type"; 382 case DeclSpec::TST_unknown_anytype: return "__unknown_anytype"; 383 case DeclSpec::TST_error: return "(error)"; 384 } 385 llvm_unreachable("Unknown typespec!"); 386} 387 388const char *DeclSpec::getSpecifierName(TQ T) { 389 switch (T) { 390 case DeclSpec::TQ_unspecified: return "unspecified"; 391 case DeclSpec::TQ_const: return "const"; 392 case DeclSpec::TQ_restrict: return "restrict"; 393 case DeclSpec::TQ_volatile: return "volatile"; 394 } 395 llvm_unreachable("Unknown typespec!"); 396} 397 398bool DeclSpec::SetStorageClassSpec(SCS S, SourceLocation Loc, 399 const char *&PrevSpec, 400 unsigned &DiagID, 401 const LangOptions &Lang) { 402 // OpenCL prohibits extern, auto, register, and static 403 // It seems sensible to prohibit private_extern too 404 if (Lang.OpenCL) { 405 switch (S) { 406 case SCS_extern: 407 case SCS_private_extern: 408 case SCS_auto: 409 case SCS_register: 410 case SCS_static: 411 DiagID = diag::err_not_opencl_storage_class_specifier; 412 PrevSpec = getSpecifierName(S); 413 return true; 414 default: 415 break; 416 } 417 } 418 419 if (StorageClassSpec != SCS_unspecified) { 420 // Changing storage class is allowed only if the previous one 421 // was the 'extern' that is part of a linkage specification and 422 // the new storage class is 'typedef'. 423 if (!(SCS_extern_in_linkage_spec && 424 StorageClassSpec == SCS_extern && 425 S == SCS_typedef)) 426 return BadSpecifier(S, (SCS)StorageClassSpec, PrevSpec, DiagID); 427 } 428 StorageClassSpec = S; 429 StorageClassSpecLoc = Loc; 430 assert((unsigned)S == StorageClassSpec && "SCS constants overflow bitfield"); 431 return false; 432} 433 434bool DeclSpec::SetStorageClassSpecThread(SourceLocation Loc, 435 const char *&PrevSpec, 436 unsigned &DiagID) { 437 if (SCS_thread_specified) { 438 PrevSpec = "__thread"; 439 DiagID = diag::ext_duplicate_declspec; 440 return true; 441 } 442 SCS_thread_specified = true; 443 SCS_threadLoc = Loc; 444 return false; 445} 446 447/// These methods set the specified attribute of the DeclSpec, but return true 448/// and ignore the request if invalid (e.g. "extern" then "auto" is 449/// specified). 450bool DeclSpec::SetTypeSpecWidth(TSW W, SourceLocation Loc, 451 const char *&PrevSpec, 452 unsigned &DiagID) { 453 // Overwrite TSWLoc only if TypeSpecWidth was unspecified, so that 454 // for 'long long' we will keep the source location of the first 'long'. 455 if (TypeSpecWidth == TSW_unspecified) 456 TSWLoc = Loc; 457 // Allow turning long -> long long. 458 else if (W != TSW_longlong || TypeSpecWidth != TSW_long) 459 return BadSpecifier(W, (TSW)TypeSpecWidth, PrevSpec, DiagID); 460 TypeSpecWidth = W; 461 if (TypeAltiVecVector && !TypeAltiVecBool && 462 ((TypeSpecWidth == TSW_long) || (TypeSpecWidth == TSW_longlong))) { 463 PrevSpec = DeclSpec::getSpecifierName((TST) TypeSpecType); 464 DiagID = diag::warn_vector_long_decl_spec_combination; 465 return true; 466 } 467 return false; 468} 469 470bool DeclSpec::SetTypeSpecComplex(TSC C, SourceLocation Loc, 471 const char *&PrevSpec, 472 unsigned &DiagID) { 473 if (TypeSpecComplex != TSC_unspecified) 474 return BadSpecifier(C, (TSC)TypeSpecComplex, PrevSpec, DiagID); 475 TypeSpecComplex = C; 476 TSCLoc = Loc; 477 return false; 478} 479 480bool DeclSpec::SetTypeSpecSign(TSS S, SourceLocation Loc, 481 const char *&PrevSpec, 482 unsigned &DiagID) { 483 if (TypeSpecSign != TSS_unspecified) 484 return BadSpecifier(S, (TSS)TypeSpecSign, PrevSpec, DiagID); 485 TypeSpecSign = S; 486 TSSLoc = Loc; 487 return false; 488} 489 490bool DeclSpec::SetTypeSpecType(TST T, SourceLocation Loc, 491 const char *&PrevSpec, 492 unsigned &DiagID, 493 ParsedType Rep) { 494 return SetTypeSpecType(T, Loc, Loc, PrevSpec, DiagID, Rep); 495} 496 497bool DeclSpec::SetTypeSpecType(TST T, SourceLocation TagKwLoc, 498 SourceLocation TagNameLoc, 499 const char *&PrevSpec, 500 unsigned &DiagID, 501 ParsedType Rep) { 502 assert(isTypeRep(T) && "T does not store a type"); 503 assert(Rep && "no type provided!"); 504 if (TypeSpecType != TST_unspecified) { 505 PrevSpec = DeclSpec::getSpecifierName((TST) TypeSpecType); 506 DiagID = diag::err_invalid_decl_spec_combination; 507 return true; 508 } 509 TypeSpecType = T; 510 TypeRep = Rep; 511 TSTLoc = TagKwLoc; 512 TSTNameLoc = TagNameLoc; 513 TypeSpecOwned = false; 514 return false; 515} 516 517bool DeclSpec::SetTypeSpecType(TST T, SourceLocation Loc, 518 const char *&PrevSpec, 519 unsigned &DiagID, 520 Expr *Rep) { 521 assert(isExprRep(T) && "T does not store an expr"); 522 assert(Rep && "no expression provided!"); 523 if (TypeSpecType != TST_unspecified) { 524 PrevSpec = DeclSpec::getSpecifierName((TST) TypeSpecType); 525 DiagID = diag::err_invalid_decl_spec_combination; 526 return true; 527 } 528 TypeSpecType = T; 529 ExprRep = Rep; 530 TSTLoc = Loc; 531 TSTNameLoc = Loc; 532 TypeSpecOwned = false; 533 return false; 534} 535 536bool DeclSpec::SetTypeSpecType(TST T, SourceLocation Loc, 537 const char *&PrevSpec, 538 unsigned &DiagID, 539 Decl *Rep, bool Owned) { 540 return SetTypeSpecType(T, Loc, Loc, PrevSpec, DiagID, Rep, Owned); 541} 542 543bool DeclSpec::SetTypeSpecType(TST T, SourceLocation TagKwLoc, 544 SourceLocation TagNameLoc, 545 const char *&PrevSpec, 546 unsigned &DiagID, 547 Decl *Rep, bool Owned) { 548 assert(isDeclRep(T) && "T does not store a decl"); 549 // Unlike the other cases, we don't assert that we actually get a decl. 550 551 if (TypeSpecType != TST_unspecified) { 552 PrevSpec = DeclSpec::getSpecifierName((TST) TypeSpecType); 553 DiagID = diag::err_invalid_decl_spec_combination; 554 return true; 555 } 556 TypeSpecType = T; 557 DeclRep = Rep; 558 TSTLoc = TagKwLoc; 559 TSTNameLoc = TagNameLoc; 560 TypeSpecOwned = Owned; 561 return false; 562} 563 564bool DeclSpec::SetTypeSpecType(TST T, SourceLocation Loc, 565 const char *&PrevSpec, 566 unsigned &DiagID) { 567 assert(!isDeclRep(T) && !isTypeRep(T) && !isExprRep(T) && 568 "rep required for these type-spec kinds!"); 569 if (TypeSpecType != TST_unspecified) { 570 PrevSpec = DeclSpec::getSpecifierName((TST) TypeSpecType); 571 DiagID = diag::err_invalid_decl_spec_combination; 572 return true; 573 } 574 TSTLoc = Loc; 575 TSTNameLoc = Loc; 576 if (TypeAltiVecVector && (T == TST_bool) && !TypeAltiVecBool) { 577 TypeAltiVecBool = true; 578 return false; 579 } 580 TypeSpecType = T; 581 TypeSpecOwned = false; 582 if (TypeAltiVecVector && !TypeAltiVecBool && (TypeSpecType == TST_double)) { 583 PrevSpec = DeclSpec::getSpecifierName((TST) TypeSpecType); 584 DiagID = diag::err_invalid_vector_decl_spec; 585 return true; 586 } 587 return false; 588} 589 590bool DeclSpec::SetTypeAltiVecVector(bool isAltiVecVector, SourceLocation Loc, 591 const char *&PrevSpec, unsigned &DiagID) { 592 if (TypeSpecType != TST_unspecified) { 593 PrevSpec = DeclSpec::getSpecifierName((TST) TypeSpecType); 594 DiagID = diag::err_invalid_vector_decl_spec_combination; 595 return true; 596 } 597 TypeAltiVecVector = isAltiVecVector; 598 AltiVecLoc = Loc; 599 return false; 600} 601 602bool DeclSpec::SetTypeAltiVecPixel(bool isAltiVecPixel, SourceLocation Loc, 603 const char *&PrevSpec, unsigned &DiagID) { 604 if (!TypeAltiVecVector || TypeAltiVecPixel || 605 (TypeSpecType != TST_unspecified)) { 606 PrevSpec = DeclSpec::getSpecifierName((TST) TypeSpecType); 607 DiagID = diag::err_invalid_pixel_decl_spec_combination; 608 return true; 609 } 610 TypeAltiVecPixel = isAltiVecPixel; 611 TSTLoc = Loc; 612 TSTNameLoc = Loc; 613 return false; 614} 615 616bool DeclSpec::SetTypeSpecError() { 617 TypeSpecType = TST_error; 618 TypeSpecOwned = false; 619 TSTLoc = SourceLocation(); 620 TSTNameLoc = SourceLocation(); 621 return false; 622} 623 624bool DeclSpec::SetTypeQual(TQ T, SourceLocation Loc, const char *&PrevSpec, 625 unsigned &DiagID, const LangOptions &Lang) { 626 // Duplicates turn into warnings pre-C99. 627 if ((TypeQualifiers & T) && !Lang.C99) 628 return BadSpecifier(T, T, PrevSpec, DiagID); 629 TypeQualifiers |= T; 630 631 switch (T) { 632 default: assert(0 && "Unknown type qualifier!"); 633 case TQ_const: TQ_constLoc = Loc; break; 634 case TQ_restrict: TQ_restrictLoc = Loc; break; 635 case TQ_volatile: TQ_volatileLoc = Loc; break; 636 } 637 return false; 638} 639 640bool DeclSpec::SetFunctionSpecInline(SourceLocation Loc, const char *&PrevSpec, 641 unsigned &DiagID) { 642 // 'inline inline' is ok. 643 FS_inline_specified = true; 644 FS_inlineLoc = Loc; 645 return false; 646} 647 648bool DeclSpec::SetFunctionSpecVirtual(SourceLocation Loc, const char *&PrevSpec, 649 unsigned &DiagID) { 650 // 'virtual virtual' is ok. 651 FS_virtual_specified = true; 652 FS_virtualLoc = Loc; 653 return false; 654} 655 656bool DeclSpec::SetFunctionSpecExplicit(SourceLocation Loc, const char *&PrevSpec, 657 unsigned &DiagID) { 658 // 'explicit explicit' is ok. 659 FS_explicit_specified = true; 660 FS_explicitLoc = Loc; 661 return false; 662} 663 664bool DeclSpec::SetFriendSpec(SourceLocation Loc, const char *&PrevSpec, 665 unsigned &DiagID) { 666 if (Friend_specified) { 667 PrevSpec = "friend"; 668 DiagID = diag::ext_duplicate_declspec; 669 return true; 670 } 671 672 Friend_specified = true; 673 FriendLoc = Loc; 674 return false; 675} 676 677bool DeclSpec::SetConstexprSpec(SourceLocation Loc, const char *&PrevSpec, 678 unsigned &DiagID) { 679 // 'constexpr constexpr' is ok. 680 Constexpr_specified = true; 681 ConstexprLoc = Loc; 682 return false; 683} 684 685void DeclSpec::setProtocolQualifiers(Decl * const *Protos, 686 unsigned NP, 687 SourceLocation *ProtoLocs, 688 SourceLocation LAngleLoc) { 689 if (NP == 0) return; 690 ProtocolQualifiers = new Decl*[NP]; 691 ProtocolLocs = new SourceLocation[NP]; 692 memcpy((void*)ProtocolQualifiers, Protos, sizeof(Decl*)*NP); 693 memcpy(ProtocolLocs, ProtoLocs, sizeof(SourceLocation)*NP); 694 NumProtocolQualifiers = NP; 695 ProtocolLAngleLoc = LAngleLoc; 696} 697 698void DeclSpec::SaveWrittenBuiltinSpecs() { 699 writtenBS.Sign = getTypeSpecSign(); 700 writtenBS.Width = getTypeSpecWidth(); 701 writtenBS.Type = getTypeSpecType(); 702 // Search the list of attributes for the presence of a mode attribute. 703 writtenBS.ModeAttr = false; 704 AttributeList* attrs = getAttributes().getList(); 705 while (attrs) { 706 if (attrs->getKind() == AttributeList::AT_mode) { 707 writtenBS.ModeAttr = true; 708 break; 709 } 710 attrs = attrs->getNext(); 711 } 712} 713 714void DeclSpec::SaveStorageSpecifierAsWritten() { 715 if (SCS_extern_in_linkage_spec && StorageClassSpec == SCS_extern) 716 // If 'extern' is part of a linkage specification, 717 // then it is not a storage class "as written". 718 StorageClassSpecAsWritten = SCS_unspecified; 719 else 720 StorageClassSpecAsWritten = StorageClassSpec; 721} 722 723/// Finish - This does final analysis of the declspec, rejecting things like 724/// "_Imaginary" (lacking an FP type). This returns a diagnostic to issue or 725/// diag::NUM_DIAGNOSTICS if there is no error. After calling this method, 726/// DeclSpec is guaranteed self-consistent, even if an error occurred. 727void DeclSpec::Finish(Diagnostic &D, Preprocessor &PP) { 728 // Before possibly changing their values, save specs as written. 729 SaveWrittenBuiltinSpecs(); 730 SaveStorageSpecifierAsWritten(); 731 732 // Check the type specifier components first. 733 734 // Validate and finalize AltiVec vector declspec. 735 if (TypeAltiVecVector) { 736 if (TypeAltiVecBool) { 737 // Sign specifiers are not allowed with vector bool. (PIM 2.1) 738 if (TypeSpecSign != TSS_unspecified) { 739 Diag(D, TSSLoc, diag::err_invalid_vector_bool_decl_spec) 740 << getSpecifierName((TSS)TypeSpecSign); 741 } 742 743 // Only char/int are valid with vector bool. (PIM 2.1) 744 if (((TypeSpecType != TST_unspecified) && (TypeSpecType != TST_char) && 745 (TypeSpecType != TST_int)) || TypeAltiVecPixel) { 746 Diag(D, TSTLoc, diag::err_invalid_vector_bool_decl_spec) 747 << (TypeAltiVecPixel ? "__pixel" : 748 getSpecifierName((TST)TypeSpecType)); 749 } 750 751 // Only 'short' is valid with vector bool. (PIM 2.1) 752 if ((TypeSpecWidth != TSW_unspecified) && (TypeSpecWidth != TSW_short)) 753 Diag(D, TSWLoc, diag::err_invalid_vector_bool_decl_spec) 754 << getSpecifierName((TSW)TypeSpecWidth); 755 756 // Elements of vector bool are interpreted as unsigned. (PIM 2.1) 757 if ((TypeSpecType == TST_char) || (TypeSpecType == TST_int) || 758 (TypeSpecWidth != TSW_unspecified)) 759 TypeSpecSign = TSS_unsigned; 760 } 761 762 if (TypeAltiVecPixel) { 763 //TODO: perform validation 764 TypeSpecType = TST_int; 765 TypeSpecSign = TSS_unsigned; 766 TypeSpecWidth = TSW_short; 767 TypeSpecOwned = false; 768 } 769 } 770 771 // signed/unsigned are only valid with int/char/wchar_t. 772 if (TypeSpecSign != TSS_unspecified) { 773 if (TypeSpecType == TST_unspecified) 774 TypeSpecType = TST_int; // unsigned -> unsigned int, signed -> signed int. 775 else if (TypeSpecType != TST_int && 776 TypeSpecType != TST_char && TypeSpecType != TST_wchar) { 777 Diag(D, TSSLoc, diag::err_invalid_sign_spec) 778 << getSpecifierName((TST)TypeSpecType); 779 // signed double -> double. 780 TypeSpecSign = TSS_unspecified; 781 } 782 } 783 784 // Validate the width of the type. 785 switch (TypeSpecWidth) { 786 case TSW_unspecified: break; 787 case TSW_short: // short int 788 case TSW_longlong: // long long int 789 if (TypeSpecType == TST_unspecified) 790 TypeSpecType = TST_int; // short -> short int, long long -> long long int. 791 else if (TypeSpecType != TST_int) { 792 Diag(D, TSWLoc, 793 TypeSpecWidth == TSW_short ? diag::err_invalid_short_spec 794 : diag::err_invalid_longlong_spec) 795 << getSpecifierName((TST)TypeSpecType); 796 TypeSpecType = TST_int; 797 TypeSpecOwned = false; 798 } 799 break; 800 case TSW_long: // long double, long int 801 if (TypeSpecType == TST_unspecified) 802 TypeSpecType = TST_int; // long -> long int. 803 else if (TypeSpecType != TST_int && TypeSpecType != TST_double) { 804 Diag(D, TSWLoc, diag::err_invalid_long_spec) 805 << getSpecifierName((TST)TypeSpecType); 806 TypeSpecType = TST_int; 807 TypeSpecOwned = false; 808 } 809 break; 810 } 811 812 // TODO: if the implementation does not implement _Complex or _Imaginary, 813 // disallow their use. Need information about the backend. 814 if (TypeSpecComplex != TSC_unspecified) { 815 if (TypeSpecType == TST_unspecified) { 816 Diag(D, TSCLoc, diag::ext_plain_complex) 817 << FixItHint::CreateInsertion( 818 PP.getLocForEndOfToken(getTypeSpecComplexLoc()), 819 " double"); 820 TypeSpecType = TST_double; // _Complex -> _Complex double. 821 } else if (TypeSpecType == TST_int || TypeSpecType == TST_char) { 822 // Note that this intentionally doesn't include _Complex _Bool. 823 Diag(D, TSTLoc, diag::ext_integer_complex); 824 } else if (TypeSpecType != TST_float && TypeSpecType != TST_double) { 825 Diag(D, TSCLoc, diag::err_invalid_complex_spec) 826 << getSpecifierName((TST)TypeSpecType); 827 TypeSpecComplex = TSC_unspecified; 828 } 829 } 830 831 // C++ [class.friend]p6: 832 // No storage-class-specifier shall appear in the decl-specifier-seq 833 // of a friend declaration. 834 if (isFriendSpecified() && getStorageClassSpec()) { 835 DeclSpec::SCS SC = getStorageClassSpec(); 836 const char *SpecName = getSpecifierName(SC); 837 838 SourceLocation SCLoc = getStorageClassSpecLoc(); 839 SourceLocation SCEndLoc = SCLoc.getFileLocWithOffset(strlen(SpecName)); 840 841 Diag(D, SCLoc, diag::err_friend_storage_spec) 842 << SpecName 843 << FixItHint::CreateRemoval(SourceRange(SCLoc, SCEndLoc)); 844 845 ClearStorageClassSpecs(); 846 } 847 848 assert(!TypeSpecOwned || isDeclRep((TST) TypeSpecType)); 849 850 // Okay, now we can infer the real type. 851 852 // TODO: return "auto function" and other bad things based on the real type. 853 854 // 'data definition has no type or storage class'? 855} 856 857bool DeclSpec::isMissingDeclaratorOk() { 858 TST tst = getTypeSpecType(); 859 return isDeclRep(tst) && getRepAsDecl() != 0 && 860 StorageClassSpec != DeclSpec::SCS_typedef; 861} 862 863void UnqualifiedId::clear() { 864 Kind = IK_Identifier; 865 Identifier = 0; 866 StartLocation = SourceLocation(); 867 EndLocation = SourceLocation(); 868} 869 870void UnqualifiedId::setOperatorFunctionId(SourceLocation OperatorLoc, 871 OverloadedOperatorKind Op, 872 SourceLocation SymbolLocations[3]) { 873 Kind = IK_OperatorFunctionId; 874 StartLocation = OperatorLoc; 875 EndLocation = OperatorLoc; 876 OperatorFunctionId.Operator = Op; 877 for (unsigned I = 0; I != 3; ++I) { 878 OperatorFunctionId.SymbolLocations[I] = SymbolLocations[I].getRawEncoding(); 879 880 if (SymbolLocations[I].isValid()) 881 EndLocation = SymbolLocations[I]; 882 } 883} 884 885bool VirtSpecifiers::SetSpecifier(Specifier VS, SourceLocation Loc, 886 const char *&PrevSpec) { 887 LastLocation = Loc; 888 889 if (Specifiers & VS) { 890 PrevSpec = getSpecifierName(VS); 891 return true; 892 } 893 894 Specifiers |= VS; 895 896 switch (VS) { 897 default: assert(0 && "Unknown specifier!"); 898 case VS_Override: VS_overrideLoc = Loc; break; 899 case VS_Final: VS_finalLoc = Loc; break; 900 } 901 902 return false; 903} 904 905const char *VirtSpecifiers::getSpecifierName(Specifier VS) { 906 switch (VS) { 907 default: assert(0 && "Unknown specifier"); 908 case VS_Override: return "override"; 909 case VS_Final: return "final"; 910 } 911} 912