1 //===---------------- SemaCodeComplete.cpp - Code Completion ----*- C++ -*-===// 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 defines the code-completion semantic actions. 11 // 12 //===----------------------------------------------------------------------===// 13 #include "clang/Sema/SemaInternal.h" 14 #include "clang/Sema/Lookup.h" 15 #include "clang/Sema/Overload.h" 16 #include "clang/Sema/CodeCompleteConsumer.h" 17 #include "clang/Sema/ExternalSemaSource.h" 18 #include "clang/Sema/Scope.h" 19 #include "clang/Sema/ScopeInfo.h" 20 #include "clang/AST/DeclObjC.h" 21 #include "clang/AST/ExprCXX.h" 22 #include "clang/AST/ExprObjC.h" 23 #include "clang/Lex/MacroInfo.h" 24 #include "clang/Lex/Preprocessor.h" 25 #include "llvm/ADT/DenseSet.h" 26 #include "llvm/ADT/SmallPtrSet.h" 27 #include "llvm/ADT/StringExtras.h" 28 #include "llvm/ADT/StringSwitch.h" 29 #include "llvm/ADT/Twine.h" 30 #include <list> 31 #include <map> 32 #include <vector> 33 34 using namespace clang; 35 using namespace sema; 36 37 namespace { 38 /// \brief A container of code-completion results. 39 class ResultBuilder { 40 public: 41 /// \brief The type of a name-lookup filter, which can be provided to the 42 /// name-lookup routines to specify which declarations should be included in 43 /// the result set (when it returns true) and which declarations should be 44 /// filtered out (returns false). 45 typedef bool (ResultBuilder::*LookupFilter)(NamedDecl *) const; 46 47 typedef CodeCompletionResult Result; 48 49 private: 50 /// \brief The actual results we have found. 51 std::vector<Result> Results; 52 53 /// \brief A record of all of the declarations we have found and placed 54 /// into the result set, used to ensure that no declaration ever gets into 55 /// the result set twice. 56 llvm::SmallPtrSet<Decl*, 16> AllDeclsFound; 57 58 typedef std::pair<NamedDecl *, unsigned> DeclIndexPair; 59 60 /// \brief An entry in the shadow map, which is optimized to store 61 /// a single (declaration, index) mapping (the common case) but 62 /// can also store a list of (declaration, index) mappings. 63 class ShadowMapEntry { 64 typedef SmallVector<DeclIndexPair, 4> DeclIndexPairVector; 65 66 /// \brief Contains either the solitary NamedDecl * or a vector 67 /// of (declaration, index) pairs. 68 llvm::PointerUnion<NamedDecl *, DeclIndexPairVector*> DeclOrVector; 69 70 /// \brief When the entry contains a single declaration, this is 71 /// the index associated with that entry. 72 unsigned SingleDeclIndex; 73 74 public: 75 ShadowMapEntry() : DeclOrVector(), SingleDeclIndex(0) { } 76 77 void Add(NamedDecl *ND, unsigned Index) { 78 if (DeclOrVector.isNull()) { 79 // 0 - > 1 elements: just set the single element information. 80 DeclOrVector = ND; 81 SingleDeclIndex = Index; 82 return; 83 } 84 85 if (NamedDecl *PrevND = DeclOrVector.dyn_cast<NamedDecl *>()) { 86 // 1 -> 2 elements: create the vector of results and push in the 87 // existing declaration. 88 DeclIndexPairVector *Vec = new DeclIndexPairVector; 89 Vec->push_back(DeclIndexPair(PrevND, SingleDeclIndex)); 90 DeclOrVector = Vec; 91 } 92 93 // Add the new element to the end of the vector. 94 DeclOrVector.get<DeclIndexPairVector*>()->push_back( 95 DeclIndexPair(ND, Index)); 96 } 97 98 void Destroy() { 99 if (DeclIndexPairVector *Vec 100 = DeclOrVector.dyn_cast<DeclIndexPairVector *>()) { 101 delete Vec; 102 DeclOrVector = ((NamedDecl *)0); 103 } 104 } 105 106 // Iteration. 107 class iterator; 108 iterator begin() const; 109 iterator end() const; 110 }; 111 112 /// \brief A mapping from declaration names to the declarations that have 113 /// this name within a particular scope and their index within the list of 114 /// results. 115 typedef llvm::DenseMap<DeclarationName, ShadowMapEntry> ShadowMap; 116 117 /// \brief The semantic analysis object for which results are being 118 /// produced. 119 Sema &SemaRef; 120 121 /// \brief The allocator used to allocate new code-completion strings. 122 CodeCompletionAllocator &Allocator; 123 124 /// \brief If non-NULL, a filter function used to remove any code-completion 125 /// results that are not desirable. 126 LookupFilter Filter; 127 128 /// \brief Whether we should allow declarations as 129 /// nested-name-specifiers that would otherwise be filtered out. 130 bool AllowNestedNameSpecifiers; 131 132 /// \brief If set, the type that we would prefer our resulting value 133 /// declarations to have. 134 /// 135 /// Closely matching the preferred type gives a boost to a result's 136 /// priority. 137 CanQualType PreferredType; 138 139 /// \brief A list of shadow maps, which is used to model name hiding at 140 /// different levels of, e.g., the inheritance hierarchy. 141 std::list<ShadowMap> ShadowMaps; 142 143 /// \brief If we're potentially referring to a C++ member function, the set 144 /// of qualifiers applied to the object type. 145 Qualifiers ObjectTypeQualifiers; 146 147 /// \brief Whether the \p ObjectTypeQualifiers field is active. 148 bool HasObjectTypeQualifiers; 149 150 /// \brief The selector that we prefer. 151 Selector PreferredSelector; 152 153 /// \brief The completion context in which we are gathering results. 154 CodeCompletionContext CompletionContext; 155 156 /// \brief If we are in an instance method definition, the @implementation 157 /// object. 158 ObjCImplementationDecl *ObjCImplementation; 159 160 void AdjustResultPriorityForDecl(Result &R); 161 162 void MaybeAddConstructorResults(Result R); 163 164 public: 165 explicit ResultBuilder(Sema &SemaRef, CodeCompletionAllocator &Allocator, 166 const CodeCompletionContext &CompletionContext, 167 LookupFilter Filter = 0) 168 : SemaRef(SemaRef), Allocator(Allocator), Filter(Filter), 169 AllowNestedNameSpecifiers(false), HasObjectTypeQualifiers(false), 170 CompletionContext(CompletionContext), 171 ObjCImplementation(0) 172 { 173 // If this is an Objective-C instance method definition, dig out the 174 // corresponding implementation. 175 switch (CompletionContext.getKind()) { 176 case CodeCompletionContext::CCC_Expression: 177 case CodeCompletionContext::CCC_ObjCMessageReceiver: 178 case CodeCompletionContext::CCC_ParenthesizedExpression: 179 case CodeCompletionContext::CCC_Statement: 180 case CodeCompletionContext::CCC_Recovery: 181 if (ObjCMethodDecl *Method = SemaRef.getCurMethodDecl()) 182 if (Method->isInstanceMethod()) 183 if (ObjCInterfaceDecl *Interface = Method->getClassInterface()) 184 ObjCImplementation = Interface->getImplementation(); 185 break; 186 187 default: 188 break; 189 } 190 } 191 192 /// \brief Whether we should include code patterns in the completion 193 /// results. 194 bool includeCodePatterns() const { 195 return SemaRef.CodeCompleter && 196 SemaRef.CodeCompleter->includeCodePatterns(); 197 } 198 199 /// \brief Set the filter used for code-completion results. 200 void setFilter(LookupFilter Filter) { 201 this->Filter = Filter; 202 } 203 204 Result *data() { return Results.empty()? 0 : &Results.front(); } 205 unsigned size() const { return Results.size(); } 206 bool empty() const { return Results.empty(); } 207 208 /// \brief Specify the preferred type. 209 void setPreferredType(QualType T) { 210 PreferredType = SemaRef.Context.getCanonicalType(T); 211 } 212 213 /// \brief Set the cv-qualifiers on the object type, for us in filtering 214 /// calls to member functions. 215 /// 216 /// When there are qualifiers in this set, they will be used to filter 217 /// out member functions that aren't available (because there will be a 218 /// cv-qualifier mismatch) or prefer functions with an exact qualifier 219 /// match. 220 void setObjectTypeQualifiers(Qualifiers Quals) { 221 ObjectTypeQualifiers = Quals; 222 HasObjectTypeQualifiers = true; 223 } 224 225 /// \brief Set the preferred selector. 226 /// 227 /// When an Objective-C method declaration result is added, and that 228 /// method's selector matches this preferred selector, we give that method 229 /// a slight priority boost. 230 void setPreferredSelector(Selector Sel) { 231 PreferredSelector = Sel; 232 } 233 234 /// \brief Retrieve the code-completion context for which results are 235 /// being collected. 236 const CodeCompletionContext &getCompletionContext() const { 237 return CompletionContext; 238 } 239 240 /// \brief Specify whether nested-name-specifiers are allowed. 241 void allowNestedNameSpecifiers(bool Allow = true) { 242 AllowNestedNameSpecifiers = Allow; 243 } 244 245 /// \brief Return the semantic analysis object for which we are collecting 246 /// code completion results. 247 Sema &getSema() const { return SemaRef; } 248 249 /// \brief Retrieve the allocator used to allocate code completion strings. 250 CodeCompletionAllocator &getAllocator() const { return Allocator; } 251 252 /// \brief Determine whether the given declaration is at all interesting 253 /// as a code-completion result. 254 /// 255 /// \param ND the declaration that we are inspecting. 256 /// 257 /// \param AsNestedNameSpecifier will be set true if this declaration is 258 /// only interesting when it is a nested-name-specifier. 259 bool isInterestingDecl(NamedDecl *ND, bool &AsNestedNameSpecifier) const; 260 261 /// \brief Check whether the result is hidden by the Hiding declaration. 262 /// 263 /// \returns true if the result is hidden and cannot be found, false if 264 /// the hidden result could still be found. When false, \p R may be 265 /// modified to describe how the result can be found (e.g., via extra 266 /// qualification). 267 bool CheckHiddenResult(Result &R, DeclContext *CurContext, 268 NamedDecl *Hiding); 269 270 /// \brief Add a new result to this result set (if it isn't already in one 271 /// of the shadow maps), or replace an existing result (for, e.g., a 272 /// redeclaration). 273 /// 274 /// \param CurContext the result to add (if it is unique). 275 /// 276 /// \param R the context in which this result will be named. 277 void MaybeAddResult(Result R, DeclContext *CurContext = 0); 278 279 /// \brief Add a new result to this result set, where we already know 280 /// the hiding declation (if any). 281 /// 282 /// \param R the result to add (if it is unique). 283 /// 284 /// \param CurContext the context in which this result will be named. 285 /// 286 /// \param Hiding the declaration that hides the result. 287 /// 288 /// \param InBaseClass whether the result was found in a base 289 /// class of the searched context. 290 void AddResult(Result R, DeclContext *CurContext, NamedDecl *Hiding, 291 bool InBaseClass); 292 293 /// \brief Add a new non-declaration result to this result set. 294 void AddResult(Result R); 295 296 /// \brief Enter into a new scope. 297 void EnterNewScope(); 298 299 /// \brief Exit from the current scope. 300 void ExitScope(); 301 302 /// \brief Ignore this declaration, if it is seen again. 303 void Ignore(Decl *D) { AllDeclsFound.insert(D->getCanonicalDecl()); } 304 305 /// \name Name lookup predicates 306 /// 307 /// These predicates can be passed to the name lookup functions to filter the 308 /// results of name lookup. All of the predicates have the same type, so that 309 /// 310 //@{ 311 bool IsOrdinaryName(NamedDecl *ND) const; 312 bool IsOrdinaryNonTypeName(NamedDecl *ND) const; 313 bool IsIntegralConstantValue(NamedDecl *ND) const; 314 bool IsOrdinaryNonValueName(NamedDecl *ND) const; 315 bool IsNestedNameSpecifier(NamedDecl *ND) const; 316 bool IsEnum(NamedDecl *ND) const; 317 bool IsClassOrStruct(NamedDecl *ND) const; 318 bool IsUnion(NamedDecl *ND) const; 319 bool IsNamespace(NamedDecl *ND) const; 320 bool IsNamespaceOrAlias(NamedDecl *ND) const; 321 bool IsType(NamedDecl *ND) const; 322 bool IsMember(NamedDecl *ND) const; 323 bool IsObjCIvar(NamedDecl *ND) const; 324 bool IsObjCMessageReceiver(NamedDecl *ND) const; 325 bool IsObjCCollection(NamedDecl *ND) const; 326 bool IsImpossibleToSatisfy(NamedDecl *ND) const; 327 //@} 328 }; 329 } 330 331 class ResultBuilder::ShadowMapEntry::iterator { 332 llvm::PointerUnion<NamedDecl*, const DeclIndexPair*> DeclOrIterator; 333 unsigned SingleDeclIndex; 334 335 public: 336 typedef DeclIndexPair value_type; 337 typedef value_type reference; 338 typedef std::ptrdiff_t difference_type; 339 typedef std::input_iterator_tag iterator_category; 340 341 class pointer { 342 DeclIndexPair Value; 343 344 public: 345 pointer(const DeclIndexPair &Value) : Value(Value) { } 346 347 const DeclIndexPair *operator->() const { 348 return &Value; 349 } 350 }; 351 352 iterator() : DeclOrIterator((NamedDecl *)0), SingleDeclIndex(0) { } 353 354 iterator(NamedDecl *SingleDecl, unsigned Index) 355 : DeclOrIterator(SingleDecl), SingleDeclIndex(Index) { } 356 357 iterator(const DeclIndexPair *Iterator) 358 : DeclOrIterator(Iterator), SingleDeclIndex(0) { } 359 360 iterator &operator++() { 361 if (DeclOrIterator.is<NamedDecl *>()) { 362 DeclOrIterator = (NamedDecl *)0; 363 SingleDeclIndex = 0; 364 return *this; 365 } 366 367 const DeclIndexPair *I = DeclOrIterator.get<const DeclIndexPair*>(); 368 ++I; 369 DeclOrIterator = I; 370 return *this; 371 } 372 373 /*iterator operator++(int) { 374 iterator tmp(*this); 375 ++(*this); 376 return tmp; 377 }*/ 378 379 reference operator*() const { 380 if (NamedDecl *ND = DeclOrIterator.dyn_cast<NamedDecl *>()) 381 return reference(ND, SingleDeclIndex); 382 383 return *DeclOrIterator.get<const DeclIndexPair*>(); 384 } 385 386 pointer operator->() const { 387 return pointer(**this); 388 } 389 390 friend bool operator==(const iterator &X, const iterator &Y) { 391 return X.DeclOrIterator.getOpaqueValue() 392 == Y.DeclOrIterator.getOpaqueValue() && 393 X.SingleDeclIndex == Y.SingleDeclIndex; 394 } 395 396 friend bool operator!=(const iterator &X, const iterator &Y) { 397 return !(X == Y); 398 } 399 }; 400 401 ResultBuilder::ShadowMapEntry::iterator 402 ResultBuilder::ShadowMapEntry::begin() const { 403 if (DeclOrVector.isNull()) 404 return iterator(); 405 406 if (NamedDecl *ND = DeclOrVector.dyn_cast<NamedDecl *>()) 407 return iterator(ND, SingleDeclIndex); 408 409 return iterator(DeclOrVector.get<DeclIndexPairVector *>()->begin()); 410 } 411 412 ResultBuilder::ShadowMapEntry::iterator 413 ResultBuilder::ShadowMapEntry::end() const { 414 if (DeclOrVector.is<NamedDecl *>() || DeclOrVector.isNull()) 415 return iterator(); 416 417 return iterator(DeclOrVector.get<DeclIndexPairVector *>()->end()); 418 } 419 420 /// \brief Compute the qualification required to get from the current context 421 /// (\p CurContext) to the target context (\p TargetContext). 422 /// 423 /// \param Context the AST context in which the qualification will be used. 424 /// 425 /// \param CurContext the context where an entity is being named, which is 426 /// typically based on the current scope. 427 /// 428 /// \param TargetContext the context in which the named entity actually 429 /// resides. 430 /// 431 /// \returns a nested name specifier that refers into the target context, or 432 /// NULL if no qualification is needed. 433 static NestedNameSpecifier * 434 getRequiredQualification(ASTContext &Context, 435 DeclContext *CurContext, 436 DeclContext *TargetContext) { 437 SmallVector<DeclContext *, 4> TargetParents; 438 439 for (DeclContext *CommonAncestor = TargetContext; 440 CommonAncestor && !CommonAncestor->Encloses(CurContext); 441 CommonAncestor = CommonAncestor->getLookupParent()) { 442 if (CommonAncestor->isTransparentContext() || 443 CommonAncestor->isFunctionOrMethod()) 444 continue; 445 446 TargetParents.push_back(CommonAncestor); 447 } 448 449 NestedNameSpecifier *Result = 0; 450 while (!TargetParents.empty()) { 451 DeclContext *Parent = TargetParents.back(); 452 TargetParents.pop_back(); 453 454 if (NamespaceDecl *Namespace = dyn_cast<NamespaceDecl>(Parent)) { 455 if (!Namespace->getIdentifier()) 456 continue; 457 458 Result = NestedNameSpecifier::Create(Context, Result, Namespace); 459 } 460 else if (TagDecl *TD = dyn_cast<TagDecl>(Parent)) 461 Result = NestedNameSpecifier::Create(Context, Result, 462 false, 463 Context.getTypeDeclType(TD).getTypePtr()); 464 } 465 return Result; 466 } 467 468 bool ResultBuilder::isInterestingDecl(NamedDecl *ND, 469 bool &AsNestedNameSpecifier) const { 470 AsNestedNameSpecifier = false; 471 472 ND = ND->getUnderlyingDecl(); 473 unsigned IDNS = ND->getIdentifierNamespace(); 474 475 // Skip unnamed entities. 476 if (!ND->getDeclName()) 477 return false; 478 479 // Friend declarations and declarations introduced due to friends are never 480 // added as results. 481 if (IDNS & (Decl::IDNS_OrdinaryFriend | Decl::IDNS_TagFriend)) 482 return false; 483 484 // Class template (partial) specializations are never added as results. 485 if (isa<ClassTemplateSpecializationDecl>(ND) || 486 isa<ClassTemplatePartialSpecializationDecl>(ND)) 487 return false; 488 489 // Using declarations themselves are never added as results. 490 if (isa<UsingDecl>(ND)) 491 return false; 492 493 // Some declarations have reserved names that we don't want to ever show. 494 if (const IdentifierInfo *Id = ND->getIdentifier()) { 495 // __va_list_tag is a freak of nature. Find it and skip it. 496 if (Id->isStr("__va_list_tag") || Id->isStr("__builtin_va_list")) 497 return false; 498 499 // Filter out names reserved for the implementation (C99 7.1.3, 500 // C++ [lib.global.names]) if they come from a system header. 501 // 502 // FIXME: Add predicate for this. 503 if (Id->getLength() >= 2) { 504 const char *Name = Id->getNameStart(); 505 if (Name[0] == '_' && 506 (Name[1] == '_' || (Name[1] >= 'A' && Name[1] <= 'Z')) && 507 (ND->getLocation().isInvalid() || 508 SemaRef.SourceMgr.isInSystemHeader( 509 SemaRef.SourceMgr.getSpellingLoc(ND->getLocation())))) 510 return false; 511 } 512 } 513 514 // Skip out-of-line declarations and definitions. 515 // NOTE: Unless it's an Objective-C property, method, or ivar, where 516 // the contexts can be messy. 517 if (!ND->getDeclContext()->Equals(ND->getLexicalDeclContext()) && 518 !(isa<ObjCPropertyDecl>(ND) || isa<ObjCIvarDecl>(ND) || 519 isa<ObjCMethodDecl>(ND))) 520 return false; 521 522 if (Filter == &ResultBuilder::IsNestedNameSpecifier || 523 ((isa<NamespaceDecl>(ND) || isa<NamespaceAliasDecl>(ND)) && 524 Filter != &ResultBuilder::IsNamespace && 525 Filter != &ResultBuilder::IsNamespaceOrAlias && 526 Filter != 0)) 527 AsNestedNameSpecifier = true; 528 529 // Filter out any unwanted results. 530 if (Filter && !(this->*Filter)(ND)) { 531 // Check whether it is interesting as a nested-name-specifier. 532 if (AllowNestedNameSpecifiers && SemaRef.getLangOptions().CPlusPlus && 533 IsNestedNameSpecifier(ND) && 534 (Filter != &ResultBuilder::IsMember || 535 (isa<CXXRecordDecl>(ND) && 536 cast<CXXRecordDecl>(ND)->isInjectedClassName()))) { 537 AsNestedNameSpecifier = true; 538 return true; 539 } 540 541 return false; 542 } 543 // ... then it must be interesting! 544 return true; 545 } 546 547 bool ResultBuilder::CheckHiddenResult(Result &R, DeclContext *CurContext, 548 NamedDecl *Hiding) { 549 // In C, there is no way to refer to a hidden name. 550 // FIXME: This isn't true; we can find a tag name hidden by an ordinary 551 // name if we introduce the tag type. 552 if (!SemaRef.getLangOptions().CPlusPlus) 553 return true; 554 555 DeclContext *HiddenCtx = R.Declaration->getDeclContext()->getRedeclContext(); 556 557 // There is no way to qualify a name declared in a function or method. 558 if (HiddenCtx->isFunctionOrMethod()) 559 return true; 560 561 if (HiddenCtx == Hiding->getDeclContext()->getRedeclContext()) 562 return true; 563 564 // We can refer to the result with the appropriate qualification. Do it. 565 R.Hidden = true; 566 R.QualifierIsInformative = false; 567 568 if (!R.Qualifier) 569 R.Qualifier = getRequiredQualification(SemaRef.Context, 570 CurContext, 571 R.Declaration->getDeclContext()); 572 return false; 573 } 574 575 /// \brief A simplified classification of types used to determine whether two 576 /// types are "similar enough" when adjusting priorities. 577 SimplifiedTypeClass clang::getSimplifiedTypeClass(CanQualType T) { 578 switch (T->getTypeClass()) { 579 case Type::Builtin: 580 switch (cast<BuiltinType>(T)->getKind()) { 581 case BuiltinType::Void: 582 return STC_Void; 583 584 case BuiltinType::NullPtr: 585 return STC_Pointer; 586 587 case BuiltinType::Overload: 588 case BuiltinType::Dependent: 589 return STC_Other; 590 591 case BuiltinType::ObjCId: 592 case BuiltinType::ObjCClass: 593 case BuiltinType::ObjCSel: 594 return STC_ObjectiveC; 595 596 default: 597 return STC_Arithmetic; 598 } 599 return STC_Other; 600 601 case Type::Complex: 602 return STC_Arithmetic; 603 604 case Type::Pointer: 605 return STC_Pointer; 606 607 case Type::BlockPointer: 608 return STC_Block; 609 610 case Type::LValueReference: 611 case Type::RValueReference: 612 return getSimplifiedTypeClass(T->getAs<ReferenceType>()->getPointeeType()); 613 614 case Type::ConstantArray: 615 case Type::IncompleteArray: 616 case Type::VariableArray: 617 case Type::DependentSizedArray: 618 return STC_Array; 619 620 case Type::DependentSizedExtVector: 621 case Type::Vector: 622 case Type::ExtVector: 623 return STC_Arithmetic; 624 625 case Type::FunctionProto: 626 case Type::FunctionNoProto: 627 return STC_Function; 628 629 case Type::Record: 630 return STC_Record; 631 632 case Type::Enum: 633 return STC_Arithmetic; 634 635 case Type::ObjCObject: 636 case Type::ObjCInterface: 637 case Type::ObjCObjectPointer: 638 return STC_ObjectiveC; 639 640 default: 641 return STC_Other; 642 } 643 } 644 645 /// \brief Get the type that a given expression will have if this declaration 646 /// is used as an expression in its "typical" code-completion form. 647 QualType clang::getDeclUsageType(ASTContext &C, NamedDecl *ND) { 648 ND = cast<NamedDecl>(ND->getUnderlyingDecl()); 649 650 if (TypeDecl *Type = dyn_cast<TypeDecl>(ND)) 651 return C.getTypeDeclType(Type); 652 if (ObjCInterfaceDecl *Iface = dyn_cast<ObjCInterfaceDecl>(ND)) 653 return C.getObjCInterfaceType(Iface); 654 655 QualType T; 656 if (FunctionDecl *Function = dyn_cast<FunctionDecl>(ND)) 657 T = Function->getCallResultType(); 658 else if (ObjCMethodDecl *Method = dyn_cast<ObjCMethodDecl>(ND)) 659 T = Method->getSendResultType(); 660 else if (FunctionTemplateDecl *FunTmpl = dyn_cast<FunctionTemplateDecl>(ND)) 661 T = FunTmpl->getTemplatedDecl()->getCallResultType(); 662 else if (EnumConstantDecl *Enumerator = dyn_cast<EnumConstantDecl>(ND)) 663 T = C.getTypeDeclType(cast<EnumDecl>(Enumerator->getDeclContext())); 664 else if (ObjCPropertyDecl *Property = dyn_cast<ObjCPropertyDecl>(ND)) 665 T = Property->getType(); 666 else if (ValueDecl *Value = dyn_cast<ValueDecl>(ND)) 667 T = Value->getType(); 668 else 669 return QualType(); 670 671 // Dig through references, function pointers, and block pointers to 672 // get down to the likely type of an expression when the entity is 673 // used. 674 do { 675 if (const ReferenceType *Ref = T->getAs<ReferenceType>()) { 676 T = Ref->getPointeeType(); 677 continue; 678 } 679 680 if (const PointerType *Pointer = T->getAs<PointerType>()) { 681 if (Pointer->getPointeeType()->isFunctionType()) { 682 T = Pointer->getPointeeType(); 683 continue; 684 } 685 686 break; 687 } 688 689 if (const BlockPointerType *Block = T->getAs<BlockPointerType>()) { 690 T = Block->getPointeeType(); 691 continue; 692 } 693 694 if (const FunctionType *Function = T->getAs<FunctionType>()) { 695 T = Function->getResultType(); 696 continue; 697 } 698 699 break; 700 } while (true); 701 702 return T; 703 } 704 705 void ResultBuilder::AdjustResultPriorityForDecl(Result &R) { 706 // If this is an Objective-C method declaration whose selector matches our 707 // preferred selector, give it a priority boost. 708 if (!PreferredSelector.isNull()) 709 if (ObjCMethodDecl *Method = dyn_cast<ObjCMethodDecl>(R.Declaration)) 710 if (PreferredSelector == Method->getSelector()) 711 R.Priority += CCD_SelectorMatch; 712 713 // If we have a preferred type, adjust the priority for results with exactly- 714 // matching or nearly-matching types. 715 if (!PreferredType.isNull()) { 716 QualType T = getDeclUsageType(SemaRef.Context, R.Declaration); 717 if (!T.isNull()) { 718 CanQualType TC = SemaRef.Context.getCanonicalType(T); 719 // Check for exactly-matching types (modulo qualifiers). 720 if (SemaRef.Context.hasSameUnqualifiedType(PreferredType, TC)) 721 R.Priority /= CCF_ExactTypeMatch; 722 // Check for nearly-matching types, based on classification of each. 723 else if ((getSimplifiedTypeClass(PreferredType) 724 == getSimplifiedTypeClass(TC)) && 725 !(PreferredType->isEnumeralType() && TC->isEnumeralType())) 726 R.Priority /= CCF_SimilarTypeMatch; 727 } 728 } 729 } 730 731 void ResultBuilder::MaybeAddConstructorResults(Result R) { 732 if (!SemaRef.getLangOptions().CPlusPlus || !R.Declaration || 733 !CompletionContext.wantConstructorResults()) 734 return; 735 736 ASTContext &Context = SemaRef.Context; 737 NamedDecl *D = R.Declaration; 738 CXXRecordDecl *Record = 0; 739 if (ClassTemplateDecl *ClassTemplate = dyn_cast<ClassTemplateDecl>(D)) 740 Record = ClassTemplate->getTemplatedDecl(); 741 else if ((Record = dyn_cast<CXXRecordDecl>(D))) { 742 // Skip specializations and partial specializations. 743 if (isa<ClassTemplateSpecializationDecl>(Record)) 744 return; 745 } else { 746 // There are no constructors here. 747 return; 748 } 749 750 Record = Record->getDefinition(); 751 if (!Record) 752 return; 753 754 755 QualType RecordTy = Context.getTypeDeclType(Record); 756 DeclarationName ConstructorName 757 = Context.DeclarationNames.getCXXConstructorName( 758 Context.getCanonicalType(RecordTy)); 759 for (DeclContext::lookup_result Ctors = Record->lookup(ConstructorName); 760 Ctors.first != Ctors.second; ++Ctors.first) { 761 R.Declaration = *Ctors.first; 762 R.CursorKind = getCursorKindForDecl(R.Declaration); 763 Results.push_back(R); 764 } 765 } 766 767 void ResultBuilder::MaybeAddResult(Result R, DeclContext *CurContext) { 768 assert(!ShadowMaps.empty() && "Must enter into a results scope"); 769 770 if (R.Kind != Result::RK_Declaration) { 771 // For non-declaration results, just add the result. 772 Results.push_back(R); 773 return; 774 } 775 776 // Look through using declarations. 777 if (UsingShadowDecl *Using = dyn_cast<UsingShadowDecl>(R.Declaration)) { 778 MaybeAddResult(Result(Using->getTargetDecl(), R.Qualifier), CurContext); 779 return; 780 } 781 782 Decl *CanonDecl = R.Declaration->getCanonicalDecl(); 783 unsigned IDNS = CanonDecl->getIdentifierNamespace(); 784 785 bool AsNestedNameSpecifier = false; 786 if (!isInterestingDecl(R.Declaration, AsNestedNameSpecifier)) 787 return; 788 789 // C++ constructors are never found by name lookup. 790 if (isa<CXXConstructorDecl>(R.Declaration)) 791 return; 792 793 ShadowMap &SMap = ShadowMaps.back(); 794 ShadowMapEntry::iterator I, IEnd; 795 ShadowMap::iterator NamePos = SMap.find(R.Declaration->getDeclName()); 796 if (NamePos != SMap.end()) { 797 I = NamePos->second.begin(); 798 IEnd = NamePos->second.end(); 799 } 800 801 for (; I != IEnd; ++I) { 802 NamedDecl *ND = I->first; 803 unsigned Index = I->second; 804 if (ND->getCanonicalDecl() == CanonDecl) { 805 // This is a redeclaration. Always pick the newer declaration. 806 Results[Index].Declaration = R.Declaration; 807 808 // We're done. 809 return; 810 } 811 } 812 813 // This is a new declaration in this scope. However, check whether this 814 // declaration name is hidden by a similarly-named declaration in an outer 815 // scope. 816 std::list<ShadowMap>::iterator SM, SMEnd = ShadowMaps.end(); 817 --SMEnd; 818 for (SM = ShadowMaps.begin(); SM != SMEnd; ++SM) { 819 ShadowMapEntry::iterator I, IEnd; 820 ShadowMap::iterator NamePos = SM->find(R.Declaration->getDeclName()); 821 if (NamePos != SM->end()) { 822 I = NamePos->second.begin(); 823 IEnd = NamePos->second.end(); 824 } 825 for (; I != IEnd; ++I) { 826 // A tag declaration does not hide a non-tag declaration. 827 if (I->first->hasTagIdentifierNamespace() && 828 (IDNS & (Decl::IDNS_Member | Decl::IDNS_Ordinary | 829 Decl::IDNS_ObjCProtocol))) 830 continue; 831 832 // Protocols are in distinct namespaces from everything else. 833 if (((I->first->getIdentifierNamespace() & Decl::IDNS_ObjCProtocol) 834 || (IDNS & Decl::IDNS_ObjCProtocol)) && 835 I->first->getIdentifierNamespace() != IDNS) 836 continue; 837 838 // The newly-added result is hidden by an entry in the shadow map. 839 if (CheckHiddenResult(R, CurContext, I->first)) 840 return; 841 842 break; 843 } 844 } 845 846 // Make sure that any given declaration only shows up in the result set once. 847 if (!AllDeclsFound.insert(CanonDecl)) 848 return; 849 850 // If the filter is for nested-name-specifiers, then this result starts a 851 // nested-name-specifier. 852 if (AsNestedNameSpecifier) { 853 R.StartsNestedNameSpecifier = true; 854 R.Priority = CCP_NestedNameSpecifier; 855 } else 856 AdjustResultPriorityForDecl(R); 857 858 // If this result is supposed to have an informative qualifier, add one. 859 if (R.QualifierIsInformative && !R.Qualifier && 860 !R.StartsNestedNameSpecifier) { 861 DeclContext *Ctx = R.Declaration->getDeclContext(); 862 if (NamespaceDecl *Namespace = dyn_cast<NamespaceDecl>(Ctx)) 863 R.Qualifier = NestedNameSpecifier::Create(SemaRef.Context, 0, Namespace); 864 else if (TagDecl *Tag = dyn_cast<TagDecl>(Ctx)) 865 R.Qualifier = NestedNameSpecifier::Create(SemaRef.Context, 0, false, 866 SemaRef.Context.getTypeDeclType(Tag).getTypePtr()); 867 else 868 R.QualifierIsInformative = false; 869 } 870 871 // Insert this result into the set of results and into the current shadow 872 // map. 873 SMap[R.Declaration->getDeclName()].Add(R.Declaration, Results.size()); 874 Results.push_back(R); 875 876 if (!AsNestedNameSpecifier) 877 MaybeAddConstructorResults(R); 878 } 879 880 void ResultBuilder::AddResult(Result R, DeclContext *CurContext, 881 NamedDecl *Hiding, bool InBaseClass = false) { 882 if (R.Kind != Result::RK_Declaration) { 883 // For non-declaration results, just add the result. 884 Results.push_back(R); 885 return; 886 } 887 888 // Look through using declarations. 889 if (UsingShadowDecl *Using = dyn_cast<UsingShadowDecl>(R.Declaration)) { 890 AddResult(Result(Using->getTargetDecl(), R.Qualifier), CurContext, Hiding); 891 return; 892 } 893 894 bool AsNestedNameSpecifier = false; 895 if (!isInterestingDecl(R.Declaration, AsNestedNameSpecifier)) 896 return; 897 898 // C++ constructors are never found by name lookup. 899 if (isa<CXXConstructorDecl>(R.Declaration)) 900 return; 901 902 if (Hiding && CheckHiddenResult(R, CurContext, Hiding)) 903 return; 904 905 // Make sure that any given declaration only shows up in the result set once. 906 if (!AllDeclsFound.insert(R.Declaration->getCanonicalDecl())) 907 return; 908 909 // If the filter is for nested-name-specifiers, then this result starts a 910 // nested-name-specifier. 911 if (AsNestedNameSpecifier) { 912 R.StartsNestedNameSpecifier = true; 913 R.Priority = CCP_NestedNameSpecifier; 914 } 915 else if (Filter == &ResultBuilder::IsMember && !R.Qualifier && InBaseClass && 916 isa<CXXRecordDecl>(R.Declaration->getDeclContext() 917 ->getRedeclContext())) 918 R.QualifierIsInformative = true; 919 920 // If this result is supposed to have an informative qualifier, add one. 921 if (R.QualifierIsInformative && !R.Qualifier && 922 !R.StartsNestedNameSpecifier) { 923 DeclContext *Ctx = R.Declaration->getDeclContext(); 924 if (NamespaceDecl *Namespace = dyn_cast<NamespaceDecl>(Ctx)) 925 R.Qualifier = NestedNameSpecifier::Create(SemaRef.Context, 0, Namespace); 926 else if (TagDecl *Tag = dyn_cast<TagDecl>(Ctx)) 927 R.Qualifier = NestedNameSpecifier::Create(SemaRef.Context, 0, false, 928 SemaRef.Context.getTypeDeclType(Tag).getTypePtr()); 929 else 930 R.QualifierIsInformative = false; 931 } 932 933 // Adjust the priority if this result comes from a base class. 934 if (InBaseClass) 935 R.Priority += CCD_InBaseClass; 936 937 AdjustResultPriorityForDecl(R); 938 939 if (HasObjectTypeQualifiers) 940 if (CXXMethodDecl *Method = dyn_cast<CXXMethodDecl>(R.Declaration)) 941 if (Method->isInstance()) { 942 Qualifiers MethodQuals 943 = Qualifiers::fromCVRMask(Method->getTypeQualifiers()); 944 if (ObjectTypeQualifiers == MethodQuals) 945 R.Priority += CCD_ObjectQualifierMatch; 946 else if (ObjectTypeQualifiers - MethodQuals) { 947 // The method cannot be invoked, because doing so would drop 948 // qualifiers. 949 return; 950 } 951 } 952 953 // Insert this result into the set of results. 954 Results.push_back(R); 955 956 if (!AsNestedNameSpecifier) 957 MaybeAddConstructorResults(R); 958 } 959 960 void ResultBuilder::AddResult(Result R) { 961 assert(R.Kind != Result::RK_Declaration && 962 "Declaration results need more context"); 963 Results.push_back(R); 964 } 965 966 /// \brief Enter into a new scope. 967 void ResultBuilder::EnterNewScope() { 968 ShadowMaps.push_back(ShadowMap()); 969 } 970 971 /// \brief Exit from the current scope. 972 void ResultBuilder::ExitScope() { 973 for (ShadowMap::iterator E = ShadowMaps.back().begin(), 974 EEnd = ShadowMaps.back().end(); 975 E != EEnd; 976 ++E) 977 E->second.Destroy(); 978 979 ShadowMaps.pop_back(); 980 } 981 982 /// \brief Determines whether this given declaration will be found by 983 /// ordinary name lookup. 984 bool ResultBuilder::IsOrdinaryName(NamedDecl *ND) const { 985 ND = cast<NamedDecl>(ND->getUnderlyingDecl()); 986 987 unsigned IDNS = Decl::IDNS_Ordinary; 988 if (SemaRef.getLangOptions().CPlusPlus) 989 IDNS |= Decl::IDNS_Tag | Decl::IDNS_Namespace | Decl::IDNS_Member; 990 else if (SemaRef.getLangOptions().ObjC1) { 991 if (isa<ObjCIvarDecl>(ND)) 992 return true; 993 } 994 995 return ND->getIdentifierNamespace() & IDNS; 996 } 997 998 /// \brief Determines whether this given declaration will be found by 999 /// ordinary name lookup but is not a type name. 1000 bool ResultBuilder::IsOrdinaryNonTypeName(NamedDecl *ND) const { 1001 ND = cast<NamedDecl>(ND->getUnderlyingDecl()); 1002 if (isa<TypeDecl>(ND) || isa<ObjCInterfaceDecl>(ND)) 1003 return false; 1004 1005 unsigned IDNS = Decl::IDNS_Ordinary; 1006 if (SemaRef.getLangOptions().CPlusPlus) 1007 IDNS |= Decl::IDNS_Tag | Decl::IDNS_Namespace | Decl::IDNS_Member; 1008 else if (SemaRef.getLangOptions().ObjC1) { 1009 if (isa<ObjCIvarDecl>(ND)) 1010 return true; 1011 } 1012 1013 return ND->getIdentifierNamespace() & IDNS; 1014 } 1015 1016 bool ResultBuilder::IsIntegralConstantValue(NamedDecl *ND) const { 1017 if (!IsOrdinaryNonTypeName(ND)) 1018 return 0; 1019 1020 if (ValueDecl *VD = dyn_cast<ValueDecl>(ND->getUnderlyingDecl())) 1021 if (VD->getType()->isIntegralOrEnumerationType()) 1022 return true; 1023 1024 return false; 1025 } 1026 1027 /// \brief Determines whether this given declaration will be found by 1028 /// ordinary name lookup. 1029 bool ResultBuilder::IsOrdinaryNonValueName(NamedDecl *ND) const { 1030 ND = cast<NamedDecl>(ND->getUnderlyingDecl()); 1031 1032 unsigned IDNS = Decl::IDNS_Ordinary; 1033 if (SemaRef.getLangOptions().CPlusPlus) 1034 IDNS |= Decl::IDNS_Tag | Decl::IDNS_Namespace; 1035 1036 return (ND->getIdentifierNamespace() & IDNS) && 1037 !isa<ValueDecl>(ND) && !isa<FunctionTemplateDecl>(ND) && 1038 !isa<ObjCPropertyDecl>(ND); 1039 } 1040 1041 /// \brief Determines whether the given declaration is suitable as the 1042 /// start of a C++ nested-name-specifier, e.g., a class or namespace. 1043 bool ResultBuilder::IsNestedNameSpecifier(NamedDecl *ND) const { 1044 // Allow us to find class templates, too. 1045 if (ClassTemplateDecl *ClassTemplate = dyn_cast<ClassTemplateDecl>(ND)) 1046 ND = ClassTemplate->getTemplatedDecl(); 1047 1048 return SemaRef.isAcceptableNestedNameSpecifier(ND); 1049 } 1050 1051 /// \brief Determines whether the given declaration is an enumeration. 1052 bool ResultBuilder::IsEnum(NamedDecl *ND) const { 1053 return isa<EnumDecl>(ND); 1054 } 1055 1056 /// \brief Determines whether the given declaration is a class or struct. 1057 bool ResultBuilder::IsClassOrStruct(NamedDecl *ND) const { 1058 // Allow us to find class templates, too. 1059 if (ClassTemplateDecl *ClassTemplate = dyn_cast<ClassTemplateDecl>(ND)) 1060 ND = ClassTemplate->getTemplatedDecl(); 1061 1062 if (RecordDecl *RD = dyn_cast<RecordDecl>(ND)) 1063 return RD->getTagKind() == TTK_Class || 1064 RD->getTagKind() == TTK_Struct; 1065 1066 return false; 1067 } 1068 1069 /// \brief Determines whether the given declaration is a union. 1070 bool ResultBuilder::IsUnion(NamedDecl *ND) const { 1071 // Allow us to find class templates, too. 1072 if (ClassTemplateDecl *ClassTemplate = dyn_cast<ClassTemplateDecl>(ND)) 1073 ND = ClassTemplate->getTemplatedDecl(); 1074 1075 if (RecordDecl *RD = dyn_cast<RecordDecl>(ND)) 1076 return RD->getTagKind() == TTK_Union; 1077 1078 return false; 1079 } 1080 1081 /// \brief Determines whether the given declaration is a namespace. 1082 bool ResultBuilder::IsNamespace(NamedDecl *ND) const { 1083 return isa<NamespaceDecl>(ND); 1084 } 1085 1086 /// \brief Determines whether the given declaration is a namespace or 1087 /// namespace alias. 1088 bool ResultBuilder::IsNamespaceOrAlias(NamedDecl *ND) const { 1089 return isa<NamespaceDecl>(ND) || isa<NamespaceAliasDecl>(ND); 1090 } 1091 1092 /// \brief Determines whether the given declaration is a type. 1093 bool ResultBuilder::IsType(NamedDecl *ND) const { 1094 if (UsingShadowDecl *Using = dyn_cast<UsingShadowDecl>(ND)) 1095 ND = Using->getTargetDecl(); 1096 1097 return isa<TypeDecl>(ND) || isa<ObjCInterfaceDecl>(ND); 1098 } 1099 1100 /// \brief Determines which members of a class should be visible via 1101 /// "." or "->". Only value declarations, nested name specifiers, and 1102 /// using declarations thereof should show up. 1103 bool ResultBuilder::IsMember(NamedDecl *ND) const { 1104 if (UsingShadowDecl *Using = dyn_cast<UsingShadowDecl>(ND)) 1105 ND = Using->getTargetDecl(); 1106 1107 return isa<ValueDecl>(ND) || isa<FunctionTemplateDecl>(ND) || 1108 isa<ObjCPropertyDecl>(ND); 1109 } 1110 1111 static bool isObjCReceiverType(ASTContext &C, QualType T) { 1112 T = C.getCanonicalType(T); 1113 switch (T->getTypeClass()) { 1114 case Type::ObjCObject: 1115 case Type::ObjCInterface: 1116 case Type::ObjCObjectPointer: 1117 return true; 1118 1119 case Type::Builtin: 1120 switch (cast<BuiltinType>(T)->getKind()) { 1121 case BuiltinType::ObjCId: 1122 case BuiltinType::ObjCClass: 1123 case BuiltinType::ObjCSel: 1124 return true; 1125 1126 default: 1127 break; 1128 } 1129 return false; 1130 1131 default: 1132 break; 1133 } 1134 1135 if (!C.getLangOptions().CPlusPlus) 1136 return false; 1137 1138 // FIXME: We could perform more analysis here to determine whether a 1139 // particular class type has any conversions to Objective-C types. For now, 1140 // just accept all class types. 1141 return T->isDependentType() || T->isRecordType(); 1142 } 1143 1144 bool ResultBuilder::IsObjCMessageReceiver(NamedDecl *ND) const { 1145 QualType T = getDeclUsageType(SemaRef.Context, ND); 1146 if (T.isNull()) 1147 return false; 1148 1149 T = SemaRef.Context.getBaseElementType(T); 1150 return isObjCReceiverType(SemaRef.Context, T); 1151 } 1152 1153 bool ResultBuilder::IsObjCCollection(NamedDecl *ND) const { 1154 if ((SemaRef.getLangOptions().CPlusPlus && !IsOrdinaryName(ND)) || 1155 (!SemaRef.getLangOptions().CPlusPlus && !IsOrdinaryNonTypeName(ND))) 1156 return false; 1157 1158 QualType T = getDeclUsageType(SemaRef.Context, ND); 1159 if (T.isNull()) 1160 return false; 1161 1162 T = SemaRef.Context.getBaseElementType(T); 1163 return T->isObjCObjectType() || T->isObjCObjectPointerType() || 1164 T->isObjCIdType() || 1165 (SemaRef.getLangOptions().CPlusPlus && T->isRecordType()); 1166 } 1167 1168 bool ResultBuilder::IsImpossibleToSatisfy(NamedDecl *ND) const { 1169 return false; 1170 } 1171 1172 /// \rief Determines whether the given declaration is an Objective-C 1173 /// instance variable. 1174 bool ResultBuilder::IsObjCIvar(NamedDecl *ND) const { 1175 return isa<ObjCIvarDecl>(ND); 1176 } 1177 1178 namespace { 1179 /// \brief Visible declaration consumer that adds a code-completion result 1180 /// for each visible declaration. 1181 class CodeCompletionDeclConsumer : public VisibleDeclConsumer { 1182 ResultBuilder &Results; 1183 DeclContext *CurContext; 1184 1185 public: 1186 CodeCompletionDeclConsumer(ResultBuilder &Results, DeclContext *CurContext) 1187 : Results(Results), CurContext(CurContext) { } 1188 1189 virtual void FoundDecl(NamedDecl *ND, NamedDecl *Hiding, DeclContext *Ctx, 1190 bool InBaseClass) { 1191 bool Accessible = true; 1192 if (Ctx) 1193 Accessible = Results.getSema().IsSimplyAccessible(ND, Ctx); 1194 1195 ResultBuilder::Result Result(ND, 0, false, Accessible); 1196 Results.AddResult(Result, CurContext, Hiding, InBaseClass); 1197 } 1198 }; 1199 } 1200 1201 /// \brief Add type specifiers for the current language as keyword results. 1202 static void AddTypeSpecifierResults(const LangOptions &LangOpts, 1203 ResultBuilder &Results) { 1204 typedef CodeCompletionResult Result; 1205 Results.AddResult(Result("short", CCP_Type)); 1206 Results.AddResult(Result("long", CCP_Type)); 1207 Results.AddResult(Result("signed", CCP_Type)); 1208 Results.AddResult(Result("unsigned", CCP_Type)); 1209 Results.AddResult(Result("void", CCP_Type)); 1210 Results.AddResult(Result("char", CCP_Type)); 1211 Results.AddResult(Result("int", CCP_Type)); 1212 Results.AddResult(Result("float", CCP_Type)); 1213 Results.AddResult(Result("double", CCP_Type)); 1214 Results.AddResult(Result("enum", CCP_Type)); 1215 Results.AddResult(Result("struct", CCP_Type)); 1216 Results.AddResult(Result("union", CCP_Type)); 1217 Results.AddResult(Result("const", CCP_Type)); 1218 Results.AddResult(Result("volatile", CCP_Type)); 1219 1220 if (LangOpts.C99) { 1221 // C99-specific 1222 Results.AddResult(Result("_Complex", CCP_Type)); 1223 Results.AddResult(Result("_Imaginary", CCP_Type)); 1224 Results.AddResult(Result("_Bool", CCP_Type)); 1225 Results.AddResult(Result("restrict", CCP_Type)); 1226 } 1227 1228 CodeCompletionBuilder Builder(Results.getAllocator()); 1229 if (LangOpts.CPlusPlus) { 1230 // C++-specific 1231 Results.AddResult(Result("bool", CCP_Type + 1232 (LangOpts.ObjC1? CCD_bool_in_ObjC : 0))); 1233 Results.AddResult(Result("class", CCP_Type)); 1234 Results.AddResult(Result("wchar_t", CCP_Type)); 1235 1236 // typename qualified-id 1237 Builder.AddTypedTextChunk("typename"); 1238 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1239 Builder.AddPlaceholderChunk("qualifier"); 1240 Builder.AddTextChunk("::"); 1241 Builder.AddPlaceholderChunk("name"); 1242 Results.AddResult(Result(Builder.TakeString())); 1243 1244 if (LangOpts.CPlusPlus0x) { 1245 Results.AddResult(Result("auto", CCP_Type)); 1246 Results.AddResult(Result("char16_t", CCP_Type)); 1247 Results.AddResult(Result("char32_t", CCP_Type)); 1248 1249 Builder.AddTypedTextChunk("decltype"); 1250 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1251 Builder.AddPlaceholderChunk("expression"); 1252 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1253 Results.AddResult(Result(Builder.TakeString())); 1254 } 1255 } 1256 1257 // GNU extensions 1258 if (LangOpts.GNUMode) { 1259 // FIXME: Enable when we actually support decimal floating point. 1260 // Results.AddResult(Result("_Decimal32")); 1261 // Results.AddResult(Result("_Decimal64")); 1262 // Results.AddResult(Result("_Decimal128")); 1263 1264 Builder.AddTypedTextChunk("typeof"); 1265 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1266 Builder.AddPlaceholderChunk("expression"); 1267 Results.AddResult(Result(Builder.TakeString())); 1268 1269 Builder.AddTypedTextChunk("typeof"); 1270 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1271 Builder.AddPlaceholderChunk("type"); 1272 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1273 Results.AddResult(Result(Builder.TakeString())); 1274 } 1275 } 1276 1277 static void AddStorageSpecifiers(Sema::ParserCompletionContext CCC, 1278 const LangOptions &LangOpts, 1279 ResultBuilder &Results) { 1280 typedef CodeCompletionResult Result; 1281 // Note: we don't suggest either "auto" or "register", because both 1282 // are pointless as storage specifiers. Elsewhere, we suggest "auto" 1283 // in C++0x as a type specifier. 1284 Results.AddResult(Result("extern")); 1285 Results.AddResult(Result("static")); 1286 } 1287 1288 static void AddFunctionSpecifiers(Sema::ParserCompletionContext CCC, 1289 const LangOptions &LangOpts, 1290 ResultBuilder &Results) { 1291 typedef CodeCompletionResult Result; 1292 switch (CCC) { 1293 case Sema::PCC_Class: 1294 case Sema::PCC_MemberTemplate: 1295 if (LangOpts.CPlusPlus) { 1296 Results.AddResult(Result("explicit")); 1297 Results.AddResult(Result("friend")); 1298 Results.AddResult(Result("mutable")); 1299 Results.AddResult(Result("virtual")); 1300 } 1301 // Fall through 1302 1303 case Sema::PCC_ObjCInterface: 1304 case Sema::PCC_ObjCImplementation: 1305 case Sema::PCC_Namespace: 1306 case Sema::PCC_Template: 1307 if (LangOpts.CPlusPlus || LangOpts.C99) 1308 Results.AddResult(Result("inline")); 1309 break; 1310 1311 case Sema::PCC_ObjCInstanceVariableList: 1312 case Sema::PCC_Expression: 1313 case Sema::PCC_Statement: 1314 case Sema::PCC_ForInit: 1315 case Sema::PCC_Condition: 1316 case Sema::PCC_RecoveryInFunction: 1317 case Sema::PCC_Type: 1318 case Sema::PCC_ParenthesizedExpression: 1319 case Sema::PCC_LocalDeclarationSpecifiers: 1320 break; 1321 } 1322 } 1323 1324 static void AddObjCExpressionResults(ResultBuilder &Results, bool NeedAt); 1325 static void AddObjCStatementResults(ResultBuilder &Results, bool NeedAt); 1326 static void AddObjCVisibilityResults(const LangOptions &LangOpts, 1327 ResultBuilder &Results, 1328 bool NeedAt); 1329 static void AddObjCImplementationResults(const LangOptions &LangOpts, 1330 ResultBuilder &Results, 1331 bool NeedAt); 1332 static void AddObjCInterfaceResults(const LangOptions &LangOpts, 1333 ResultBuilder &Results, 1334 bool NeedAt); 1335 static void AddObjCTopLevelResults(ResultBuilder &Results, bool NeedAt); 1336 1337 static void AddTypedefResult(ResultBuilder &Results) { 1338 CodeCompletionBuilder Builder(Results.getAllocator()); 1339 Builder.AddTypedTextChunk("typedef"); 1340 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1341 Builder.AddPlaceholderChunk("type"); 1342 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1343 Builder.AddPlaceholderChunk("name"); 1344 Results.AddResult(CodeCompletionResult(Builder.TakeString())); 1345 } 1346 1347 static bool WantTypesInContext(Sema::ParserCompletionContext CCC, 1348 const LangOptions &LangOpts) { 1349 switch (CCC) { 1350 case Sema::PCC_Namespace: 1351 case Sema::PCC_Class: 1352 case Sema::PCC_ObjCInstanceVariableList: 1353 case Sema::PCC_Template: 1354 case Sema::PCC_MemberTemplate: 1355 case Sema::PCC_Statement: 1356 case Sema::PCC_RecoveryInFunction: 1357 case Sema::PCC_Type: 1358 case Sema::PCC_ParenthesizedExpression: 1359 case Sema::PCC_LocalDeclarationSpecifiers: 1360 return true; 1361 1362 case Sema::PCC_Expression: 1363 case Sema::PCC_Condition: 1364 return LangOpts.CPlusPlus; 1365 1366 case Sema::PCC_ObjCInterface: 1367 case Sema::PCC_ObjCImplementation: 1368 return false; 1369 1370 case Sema::PCC_ForInit: 1371 return LangOpts.CPlusPlus || LangOpts.ObjC1 || LangOpts.C99; 1372 } 1373 1374 return false; 1375 } 1376 1377 /// \brief Retrieve a printing policy suitable for code completion. 1378 static PrintingPolicy getCompletionPrintingPolicy(Sema &S) { 1379 PrintingPolicy Policy = S.getPrintingPolicy(); 1380 Policy.AnonymousTagLocations = false; 1381 Policy.SuppressStrongLifetime = true; 1382 Policy.SuppressUnwrittenScope = true; 1383 return Policy; 1384 } 1385 1386 /// \brief Retrieve the string representation of the given type as a string 1387 /// that has the appropriate lifetime for code completion. 1388 /// 1389 /// This routine provides a fast path where we provide constant strings for 1390 /// common type names. 1391 static const char *GetCompletionTypeString(QualType T, 1392 ASTContext &Context, 1393 const PrintingPolicy &Policy, 1394 CodeCompletionAllocator &Allocator) { 1395 if (!T.getLocalQualifiers()) { 1396 // Built-in type names are constant strings. 1397 if (const BuiltinType *BT = dyn_cast<BuiltinType>(T)) 1398 return BT->getName(Policy); 1399 1400 // Anonymous tag types are constant strings. 1401 if (const TagType *TagT = dyn_cast<TagType>(T)) 1402 if (TagDecl *Tag = TagT->getDecl()) 1403 if (!Tag->getIdentifier() && !Tag->getTypedefNameForAnonDecl()) { 1404 switch (Tag->getTagKind()) { 1405 case TTK_Struct: return "struct <anonymous>"; 1406 case TTK_Class: return "class <anonymous>"; 1407 case TTK_Union: return "union <anonymous>"; 1408 case TTK_Enum: return "enum <anonymous>"; 1409 } 1410 } 1411 } 1412 1413 // Slow path: format the type as a string. 1414 std::string Result; 1415 T.getAsStringInternal(Result, Policy); 1416 return Allocator.CopyString(Result); 1417 } 1418 1419 /// \brief Add language constructs that show up for "ordinary" names. 1420 static void AddOrdinaryNameResults(Sema::ParserCompletionContext CCC, 1421 Scope *S, 1422 Sema &SemaRef, 1423 ResultBuilder &Results) { 1424 CodeCompletionAllocator &Allocator = Results.getAllocator(); 1425 CodeCompletionBuilder Builder(Allocator); 1426 PrintingPolicy Policy = getCompletionPrintingPolicy(SemaRef); 1427 1428 typedef CodeCompletionResult Result; 1429 switch (CCC) { 1430 case Sema::PCC_Namespace: 1431 if (SemaRef.getLangOptions().CPlusPlus) { 1432 if (Results.includeCodePatterns()) { 1433 // namespace <identifier> { declarations } 1434 Builder.AddTypedTextChunk("namespace"); 1435 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1436 Builder.AddPlaceholderChunk("identifier"); 1437 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 1438 Builder.AddPlaceholderChunk("declarations"); 1439 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 1440 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 1441 Results.AddResult(Result(Builder.TakeString())); 1442 } 1443 1444 // namespace identifier = identifier ; 1445 Builder.AddTypedTextChunk("namespace"); 1446 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1447 Builder.AddPlaceholderChunk("name"); 1448 Builder.AddChunk(CodeCompletionString::CK_Equal); 1449 Builder.AddPlaceholderChunk("namespace"); 1450 Results.AddResult(Result(Builder.TakeString())); 1451 1452 // Using directives 1453 Builder.AddTypedTextChunk("using"); 1454 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1455 Builder.AddTextChunk("namespace"); 1456 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1457 Builder.AddPlaceholderChunk("identifier"); 1458 Results.AddResult(Result(Builder.TakeString())); 1459 1460 // asm(string-literal) 1461 Builder.AddTypedTextChunk("asm"); 1462 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1463 Builder.AddPlaceholderChunk("string-literal"); 1464 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1465 Results.AddResult(Result(Builder.TakeString())); 1466 1467 if (Results.includeCodePatterns()) { 1468 // Explicit template instantiation 1469 Builder.AddTypedTextChunk("template"); 1470 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1471 Builder.AddPlaceholderChunk("declaration"); 1472 Results.AddResult(Result(Builder.TakeString())); 1473 } 1474 } 1475 1476 if (SemaRef.getLangOptions().ObjC1) 1477 AddObjCTopLevelResults(Results, true); 1478 1479 AddTypedefResult(Results); 1480 // Fall through 1481 1482 case Sema::PCC_Class: 1483 if (SemaRef.getLangOptions().CPlusPlus) { 1484 // Using declaration 1485 Builder.AddTypedTextChunk("using"); 1486 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1487 Builder.AddPlaceholderChunk("qualifier"); 1488 Builder.AddTextChunk("::"); 1489 Builder.AddPlaceholderChunk("name"); 1490 Results.AddResult(Result(Builder.TakeString())); 1491 1492 // using typename qualifier::name (only in a dependent context) 1493 if (SemaRef.CurContext->isDependentContext()) { 1494 Builder.AddTypedTextChunk("using"); 1495 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1496 Builder.AddTextChunk("typename"); 1497 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1498 Builder.AddPlaceholderChunk("qualifier"); 1499 Builder.AddTextChunk("::"); 1500 Builder.AddPlaceholderChunk("name"); 1501 Results.AddResult(Result(Builder.TakeString())); 1502 } 1503 1504 if (CCC == Sema::PCC_Class) { 1505 AddTypedefResult(Results); 1506 1507 // public: 1508 Builder.AddTypedTextChunk("public"); 1509 Builder.AddChunk(CodeCompletionString::CK_Colon); 1510 Results.AddResult(Result(Builder.TakeString())); 1511 1512 // protected: 1513 Builder.AddTypedTextChunk("protected"); 1514 Builder.AddChunk(CodeCompletionString::CK_Colon); 1515 Results.AddResult(Result(Builder.TakeString())); 1516 1517 // private: 1518 Builder.AddTypedTextChunk("private"); 1519 Builder.AddChunk(CodeCompletionString::CK_Colon); 1520 Results.AddResult(Result(Builder.TakeString())); 1521 } 1522 } 1523 // Fall through 1524 1525 case Sema::PCC_Template: 1526 case Sema::PCC_MemberTemplate: 1527 if (SemaRef.getLangOptions().CPlusPlus && Results.includeCodePatterns()) { 1528 // template < parameters > 1529 Builder.AddTypedTextChunk("template"); 1530 Builder.AddChunk(CodeCompletionString::CK_LeftAngle); 1531 Builder.AddPlaceholderChunk("parameters"); 1532 Builder.AddChunk(CodeCompletionString::CK_RightAngle); 1533 Results.AddResult(Result(Builder.TakeString())); 1534 } 1535 1536 AddStorageSpecifiers(CCC, SemaRef.getLangOptions(), Results); 1537 AddFunctionSpecifiers(CCC, SemaRef.getLangOptions(), Results); 1538 break; 1539 1540 case Sema::PCC_ObjCInterface: 1541 AddObjCInterfaceResults(SemaRef.getLangOptions(), Results, true); 1542 AddStorageSpecifiers(CCC, SemaRef.getLangOptions(), Results); 1543 AddFunctionSpecifiers(CCC, SemaRef.getLangOptions(), Results); 1544 break; 1545 1546 case Sema::PCC_ObjCImplementation: 1547 AddObjCImplementationResults(SemaRef.getLangOptions(), Results, true); 1548 AddStorageSpecifiers(CCC, SemaRef.getLangOptions(), Results); 1549 AddFunctionSpecifiers(CCC, SemaRef.getLangOptions(), Results); 1550 break; 1551 1552 case Sema::PCC_ObjCInstanceVariableList: 1553 AddObjCVisibilityResults(SemaRef.getLangOptions(), Results, true); 1554 break; 1555 1556 case Sema::PCC_RecoveryInFunction: 1557 case Sema::PCC_Statement: { 1558 AddTypedefResult(Results); 1559 1560 if (SemaRef.getLangOptions().CPlusPlus && Results.includeCodePatterns() && 1561 SemaRef.getLangOptions().CXXExceptions) { 1562 Builder.AddTypedTextChunk("try"); 1563 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 1564 Builder.AddPlaceholderChunk("statements"); 1565 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 1566 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 1567 Builder.AddTextChunk("catch"); 1568 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1569 Builder.AddPlaceholderChunk("declaration"); 1570 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1571 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 1572 Builder.AddPlaceholderChunk("statements"); 1573 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 1574 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 1575 Results.AddResult(Result(Builder.TakeString())); 1576 } 1577 if (SemaRef.getLangOptions().ObjC1) 1578 AddObjCStatementResults(Results, true); 1579 1580 if (Results.includeCodePatterns()) { 1581 // if (condition) { statements } 1582 Builder.AddTypedTextChunk("if"); 1583 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1584 if (SemaRef.getLangOptions().CPlusPlus) 1585 Builder.AddPlaceholderChunk("condition"); 1586 else 1587 Builder.AddPlaceholderChunk("expression"); 1588 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1589 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 1590 Builder.AddPlaceholderChunk("statements"); 1591 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 1592 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 1593 Results.AddResult(Result(Builder.TakeString())); 1594 1595 // switch (condition) { } 1596 Builder.AddTypedTextChunk("switch"); 1597 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1598 if (SemaRef.getLangOptions().CPlusPlus) 1599 Builder.AddPlaceholderChunk("condition"); 1600 else 1601 Builder.AddPlaceholderChunk("expression"); 1602 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1603 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 1604 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 1605 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 1606 Results.AddResult(Result(Builder.TakeString())); 1607 } 1608 1609 // Switch-specific statements. 1610 if (!SemaRef.getCurFunction()->SwitchStack.empty()) { 1611 // case expression: 1612 Builder.AddTypedTextChunk("case"); 1613 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1614 Builder.AddPlaceholderChunk("expression"); 1615 Builder.AddChunk(CodeCompletionString::CK_Colon); 1616 Results.AddResult(Result(Builder.TakeString())); 1617 1618 // default: 1619 Builder.AddTypedTextChunk("default"); 1620 Builder.AddChunk(CodeCompletionString::CK_Colon); 1621 Results.AddResult(Result(Builder.TakeString())); 1622 } 1623 1624 if (Results.includeCodePatterns()) { 1625 /// while (condition) { statements } 1626 Builder.AddTypedTextChunk("while"); 1627 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1628 if (SemaRef.getLangOptions().CPlusPlus) 1629 Builder.AddPlaceholderChunk("condition"); 1630 else 1631 Builder.AddPlaceholderChunk("expression"); 1632 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1633 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 1634 Builder.AddPlaceholderChunk("statements"); 1635 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 1636 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 1637 Results.AddResult(Result(Builder.TakeString())); 1638 1639 // do { statements } while ( expression ); 1640 Builder.AddTypedTextChunk("do"); 1641 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 1642 Builder.AddPlaceholderChunk("statements"); 1643 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 1644 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 1645 Builder.AddTextChunk("while"); 1646 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1647 Builder.AddPlaceholderChunk("expression"); 1648 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1649 Results.AddResult(Result(Builder.TakeString())); 1650 1651 // for ( for-init-statement ; condition ; expression ) { statements } 1652 Builder.AddTypedTextChunk("for"); 1653 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1654 if (SemaRef.getLangOptions().CPlusPlus || SemaRef.getLangOptions().C99) 1655 Builder.AddPlaceholderChunk("init-statement"); 1656 else 1657 Builder.AddPlaceholderChunk("init-expression"); 1658 Builder.AddChunk(CodeCompletionString::CK_SemiColon); 1659 Builder.AddPlaceholderChunk("condition"); 1660 Builder.AddChunk(CodeCompletionString::CK_SemiColon); 1661 Builder.AddPlaceholderChunk("inc-expression"); 1662 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1663 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 1664 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 1665 Builder.AddPlaceholderChunk("statements"); 1666 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 1667 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 1668 Results.AddResult(Result(Builder.TakeString())); 1669 } 1670 1671 if (S->getContinueParent()) { 1672 // continue ; 1673 Builder.AddTypedTextChunk("continue"); 1674 Results.AddResult(Result(Builder.TakeString())); 1675 } 1676 1677 if (S->getBreakParent()) { 1678 // break ; 1679 Builder.AddTypedTextChunk("break"); 1680 Results.AddResult(Result(Builder.TakeString())); 1681 } 1682 1683 // "return expression ;" or "return ;", depending on whether we 1684 // know the function is void or not. 1685 bool isVoid = false; 1686 if (FunctionDecl *Function = dyn_cast<FunctionDecl>(SemaRef.CurContext)) 1687 isVoid = Function->getResultType()->isVoidType(); 1688 else if (ObjCMethodDecl *Method 1689 = dyn_cast<ObjCMethodDecl>(SemaRef.CurContext)) 1690 isVoid = Method->getResultType()->isVoidType(); 1691 else if (SemaRef.getCurBlock() && 1692 !SemaRef.getCurBlock()->ReturnType.isNull()) 1693 isVoid = SemaRef.getCurBlock()->ReturnType->isVoidType(); 1694 Builder.AddTypedTextChunk("return"); 1695 if (!isVoid) { 1696 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1697 Builder.AddPlaceholderChunk("expression"); 1698 } 1699 Results.AddResult(Result(Builder.TakeString())); 1700 1701 // goto identifier ; 1702 Builder.AddTypedTextChunk("goto"); 1703 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1704 Builder.AddPlaceholderChunk("label"); 1705 Results.AddResult(Result(Builder.TakeString())); 1706 1707 // Using directives 1708 Builder.AddTypedTextChunk("using"); 1709 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1710 Builder.AddTextChunk("namespace"); 1711 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1712 Builder.AddPlaceholderChunk("identifier"); 1713 Results.AddResult(Result(Builder.TakeString())); 1714 } 1715 1716 // Fall through (for statement expressions). 1717 case Sema::PCC_ForInit: 1718 case Sema::PCC_Condition: 1719 AddStorageSpecifiers(CCC, SemaRef.getLangOptions(), Results); 1720 // Fall through: conditions and statements can have expressions. 1721 1722 case Sema::PCC_ParenthesizedExpression: 1723 if (SemaRef.getLangOptions().ObjCAutoRefCount && 1724 CCC == Sema::PCC_ParenthesizedExpression) { 1725 // (__bridge <type>)<expression> 1726 Builder.AddTypedTextChunk("__bridge"); 1727 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1728 Builder.AddPlaceholderChunk("type"); 1729 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1730 Builder.AddPlaceholderChunk("expression"); 1731 Results.AddResult(Result(Builder.TakeString())); 1732 1733 // (__bridge_transfer <Objective-C type>)<expression> 1734 Builder.AddTypedTextChunk("__bridge_transfer"); 1735 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1736 Builder.AddPlaceholderChunk("Objective-C type"); 1737 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1738 Builder.AddPlaceholderChunk("expression"); 1739 Results.AddResult(Result(Builder.TakeString())); 1740 1741 // (__bridge_retained <CF type>)<expression> 1742 Builder.AddTypedTextChunk("__bridge_retained"); 1743 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1744 Builder.AddPlaceholderChunk("CF type"); 1745 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1746 Builder.AddPlaceholderChunk("expression"); 1747 Results.AddResult(Result(Builder.TakeString())); 1748 } 1749 // Fall through 1750 1751 case Sema::PCC_Expression: { 1752 if (SemaRef.getLangOptions().CPlusPlus) { 1753 // 'this', if we're in a non-static member function. 1754 QualType ThisTy = SemaRef.getCurrentThisType(false); 1755 if (!ThisTy.isNull()) { 1756 Builder.AddResultTypeChunk(GetCompletionTypeString(ThisTy, 1757 SemaRef.Context, 1758 Policy, 1759 Allocator)); 1760 Builder.AddTypedTextChunk("this"); 1761 Results.AddResult(Result(Builder.TakeString())); 1762 } 1763 1764 // true 1765 Builder.AddResultTypeChunk("bool"); 1766 Builder.AddTypedTextChunk("true"); 1767 Results.AddResult(Result(Builder.TakeString())); 1768 1769 // false 1770 Builder.AddResultTypeChunk("bool"); 1771 Builder.AddTypedTextChunk("false"); 1772 Results.AddResult(Result(Builder.TakeString())); 1773 1774 if (SemaRef.getLangOptions().RTTI) { 1775 // dynamic_cast < type-id > ( expression ) 1776 Builder.AddTypedTextChunk("dynamic_cast"); 1777 Builder.AddChunk(CodeCompletionString::CK_LeftAngle); 1778 Builder.AddPlaceholderChunk("type"); 1779 Builder.AddChunk(CodeCompletionString::CK_RightAngle); 1780 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1781 Builder.AddPlaceholderChunk("expression"); 1782 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1783 Results.AddResult(Result(Builder.TakeString())); 1784 } 1785 1786 // static_cast < type-id > ( expression ) 1787 Builder.AddTypedTextChunk("static_cast"); 1788 Builder.AddChunk(CodeCompletionString::CK_LeftAngle); 1789 Builder.AddPlaceholderChunk("type"); 1790 Builder.AddChunk(CodeCompletionString::CK_RightAngle); 1791 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1792 Builder.AddPlaceholderChunk("expression"); 1793 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1794 Results.AddResult(Result(Builder.TakeString())); 1795 1796 // reinterpret_cast < type-id > ( expression ) 1797 Builder.AddTypedTextChunk("reinterpret_cast"); 1798 Builder.AddChunk(CodeCompletionString::CK_LeftAngle); 1799 Builder.AddPlaceholderChunk("type"); 1800 Builder.AddChunk(CodeCompletionString::CK_RightAngle); 1801 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1802 Builder.AddPlaceholderChunk("expression"); 1803 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1804 Results.AddResult(Result(Builder.TakeString())); 1805 1806 // const_cast < type-id > ( expression ) 1807 Builder.AddTypedTextChunk("const_cast"); 1808 Builder.AddChunk(CodeCompletionString::CK_LeftAngle); 1809 Builder.AddPlaceholderChunk("type"); 1810 Builder.AddChunk(CodeCompletionString::CK_RightAngle); 1811 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1812 Builder.AddPlaceholderChunk("expression"); 1813 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1814 Results.AddResult(Result(Builder.TakeString())); 1815 1816 if (SemaRef.getLangOptions().RTTI) { 1817 // typeid ( expression-or-type ) 1818 Builder.AddResultTypeChunk("std::type_info"); 1819 Builder.AddTypedTextChunk("typeid"); 1820 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1821 Builder.AddPlaceholderChunk("expression-or-type"); 1822 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1823 Results.AddResult(Result(Builder.TakeString())); 1824 } 1825 1826 // new T ( ... ) 1827 Builder.AddTypedTextChunk("new"); 1828 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1829 Builder.AddPlaceholderChunk("type"); 1830 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1831 Builder.AddPlaceholderChunk("expressions"); 1832 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1833 Results.AddResult(Result(Builder.TakeString())); 1834 1835 // new T [ ] ( ... ) 1836 Builder.AddTypedTextChunk("new"); 1837 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1838 Builder.AddPlaceholderChunk("type"); 1839 Builder.AddChunk(CodeCompletionString::CK_LeftBracket); 1840 Builder.AddPlaceholderChunk("size"); 1841 Builder.AddChunk(CodeCompletionString::CK_RightBracket); 1842 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1843 Builder.AddPlaceholderChunk("expressions"); 1844 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1845 Results.AddResult(Result(Builder.TakeString())); 1846 1847 // delete expression 1848 Builder.AddResultTypeChunk("void"); 1849 Builder.AddTypedTextChunk("delete"); 1850 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1851 Builder.AddPlaceholderChunk("expression"); 1852 Results.AddResult(Result(Builder.TakeString())); 1853 1854 // delete [] expression 1855 Builder.AddResultTypeChunk("void"); 1856 Builder.AddTypedTextChunk("delete"); 1857 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1858 Builder.AddChunk(CodeCompletionString::CK_LeftBracket); 1859 Builder.AddChunk(CodeCompletionString::CK_RightBracket); 1860 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1861 Builder.AddPlaceholderChunk("expression"); 1862 Results.AddResult(Result(Builder.TakeString())); 1863 1864 if (SemaRef.getLangOptions().CXXExceptions) { 1865 // throw expression 1866 Builder.AddResultTypeChunk("void"); 1867 Builder.AddTypedTextChunk("throw"); 1868 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 1869 Builder.AddPlaceholderChunk("expression"); 1870 Results.AddResult(Result(Builder.TakeString())); 1871 } 1872 1873 // FIXME: Rethrow? 1874 1875 if (SemaRef.getLangOptions().CPlusPlus0x) { 1876 // nullptr 1877 Builder.AddResultTypeChunk("std::nullptr_t"); 1878 Builder.AddTypedTextChunk("nullptr"); 1879 Results.AddResult(Result(Builder.TakeString())); 1880 1881 // alignof 1882 Builder.AddResultTypeChunk("size_t"); 1883 Builder.AddTypedTextChunk("alignof"); 1884 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1885 Builder.AddPlaceholderChunk("type"); 1886 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1887 Results.AddResult(Result(Builder.TakeString())); 1888 1889 // noexcept 1890 Builder.AddResultTypeChunk("bool"); 1891 Builder.AddTypedTextChunk("noexcept"); 1892 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1893 Builder.AddPlaceholderChunk("expression"); 1894 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1895 Results.AddResult(Result(Builder.TakeString())); 1896 1897 // sizeof... expression 1898 Builder.AddResultTypeChunk("size_t"); 1899 Builder.AddTypedTextChunk("sizeof..."); 1900 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1901 Builder.AddPlaceholderChunk("parameter-pack"); 1902 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1903 Results.AddResult(Result(Builder.TakeString())); 1904 } 1905 } 1906 1907 if (SemaRef.getLangOptions().ObjC1) { 1908 // Add "super", if we're in an Objective-C class with a superclass. 1909 if (ObjCMethodDecl *Method = SemaRef.getCurMethodDecl()) { 1910 // The interface can be NULL. 1911 if (ObjCInterfaceDecl *ID = Method->getClassInterface()) 1912 if (ID->getSuperClass()) { 1913 std::string SuperType; 1914 SuperType = ID->getSuperClass()->getNameAsString(); 1915 if (Method->isInstanceMethod()) 1916 SuperType += " *"; 1917 1918 Builder.AddResultTypeChunk(Allocator.CopyString(SuperType)); 1919 Builder.AddTypedTextChunk("super"); 1920 Results.AddResult(Result(Builder.TakeString())); 1921 } 1922 } 1923 1924 AddObjCExpressionResults(Results, true); 1925 } 1926 1927 // sizeof expression 1928 Builder.AddResultTypeChunk("size_t"); 1929 Builder.AddTypedTextChunk("sizeof"); 1930 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 1931 Builder.AddPlaceholderChunk("expression-or-type"); 1932 Builder.AddChunk(CodeCompletionString::CK_RightParen); 1933 Results.AddResult(Result(Builder.TakeString())); 1934 break; 1935 } 1936 1937 case Sema::PCC_Type: 1938 case Sema::PCC_LocalDeclarationSpecifiers: 1939 break; 1940 } 1941 1942 if (WantTypesInContext(CCC, SemaRef.getLangOptions())) 1943 AddTypeSpecifierResults(SemaRef.getLangOptions(), Results); 1944 1945 if (SemaRef.getLangOptions().CPlusPlus && CCC != Sema::PCC_Type) 1946 Results.AddResult(Result("operator")); 1947 } 1948 1949 /// \brief If the given declaration has an associated type, add it as a result 1950 /// type chunk. 1951 static void AddResultTypeChunk(ASTContext &Context, 1952 const PrintingPolicy &Policy, 1953 NamedDecl *ND, 1954 CodeCompletionBuilder &Result) { 1955 if (!ND) 1956 return; 1957 1958 // Skip constructors and conversion functions, which have their return types 1959 // built into their names. 1960 if (isa<CXXConstructorDecl>(ND) || isa<CXXConversionDecl>(ND)) 1961 return; 1962 1963 // Determine the type of the declaration (if it has a type). 1964 QualType T; 1965 if (FunctionDecl *Function = dyn_cast<FunctionDecl>(ND)) 1966 T = Function->getResultType(); 1967 else if (ObjCMethodDecl *Method = dyn_cast<ObjCMethodDecl>(ND)) 1968 T = Method->getResultType(); 1969 else if (FunctionTemplateDecl *FunTmpl = dyn_cast<FunctionTemplateDecl>(ND)) 1970 T = FunTmpl->getTemplatedDecl()->getResultType(); 1971 else if (EnumConstantDecl *Enumerator = dyn_cast<EnumConstantDecl>(ND)) 1972 T = Context.getTypeDeclType(cast<TypeDecl>(Enumerator->getDeclContext())); 1973 else if (isa<UnresolvedUsingValueDecl>(ND)) { 1974 /* Do nothing: ignore unresolved using declarations*/ 1975 } else if (ValueDecl *Value = dyn_cast<ValueDecl>(ND)) { 1976 T = Value->getType(); 1977 } else if (ObjCPropertyDecl *Property = dyn_cast<ObjCPropertyDecl>(ND)) 1978 T = Property->getType(); 1979 1980 if (T.isNull() || Context.hasSameType(T, Context.DependentTy)) 1981 return; 1982 1983 Result.AddResultTypeChunk(GetCompletionTypeString(T, Context, Policy, 1984 Result.getAllocator())); 1985 } 1986 1987 static void MaybeAddSentinel(ASTContext &Context, NamedDecl *FunctionOrMethod, 1988 CodeCompletionBuilder &Result) { 1989 if (SentinelAttr *Sentinel = FunctionOrMethod->getAttr<SentinelAttr>()) 1990 if (Sentinel->getSentinel() == 0) { 1991 if (Context.getLangOptions().ObjC1 && 1992 Context.Idents.get("nil").hasMacroDefinition()) 1993 Result.AddTextChunk(", nil"); 1994 else if (Context.Idents.get("NULL").hasMacroDefinition()) 1995 Result.AddTextChunk(", NULL"); 1996 else 1997 Result.AddTextChunk(", (void*)0"); 1998 } 1999 } 2000 2001 static std::string formatObjCParamQualifiers(unsigned ObjCQuals) { 2002 std::string Result; 2003 if (ObjCQuals & Decl::OBJC_TQ_In) 2004 Result += "in "; 2005 else if (ObjCQuals & Decl::OBJC_TQ_Inout) 2006 Result += "inout "; 2007 else if (ObjCQuals & Decl::OBJC_TQ_Out) 2008 Result += "out "; 2009 if (ObjCQuals & Decl::OBJC_TQ_Bycopy) 2010 Result += "bycopy "; 2011 else if (ObjCQuals & Decl::OBJC_TQ_Byref) 2012 Result += "byref "; 2013 if (ObjCQuals & Decl::OBJC_TQ_Oneway) 2014 Result += "oneway "; 2015 return Result; 2016 } 2017 2018 static std::string FormatFunctionParameter(ASTContext &Context, 2019 const PrintingPolicy &Policy, 2020 ParmVarDecl *Param, 2021 bool SuppressName = false, 2022 bool SuppressBlock = false) { 2023 bool ObjCMethodParam = isa<ObjCMethodDecl>(Param->getDeclContext()); 2024 if (Param->getType()->isDependentType() || 2025 !Param->getType()->isBlockPointerType()) { 2026 // The argument for a dependent or non-block parameter is a placeholder 2027 // containing that parameter's type. 2028 std::string Result; 2029 2030 if (Param->getIdentifier() && !ObjCMethodParam && !SuppressName) 2031 Result = Param->getIdentifier()->getName(); 2032 2033 Param->getType().getAsStringInternal(Result, Policy); 2034 2035 if (ObjCMethodParam) { 2036 Result = "(" + formatObjCParamQualifiers(Param->getObjCDeclQualifier()) 2037 + Result + ")"; 2038 if (Param->getIdentifier() && !SuppressName) 2039 Result += Param->getIdentifier()->getName(); 2040 } 2041 return Result; 2042 } 2043 2044 // The argument for a block pointer parameter is a block literal with 2045 // the appropriate type. 2046 FunctionTypeLoc *Block = 0; 2047 FunctionProtoTypeLoc *BlockProto = 0; 2048 TypeLoc TL; 2049 if (TypeSourceInfo *TSInfo = Param->getTypeSourceInfo()) { 2050 TL = TSInfo->getTypeLoc().getUnqualifiedLoc(); 2051 while (true) { 2052 // Look through typedefs. 2053 if (!SuppressBlock) { 2054 if (TypedefTypeLoc *TypedefTL = dyn_cast<TypedefTypeLoc>(&TL)) { 2055 if (TypeSourceInfo *InnerTSInfo 2056 = TypedefTL->getTypedefNameDecl()->getTypeSourceInfo()) { 2057 TL = InnerTSInfo->getTypeLoc().getUnqualifiedLoc(); 2058 continue; 2059 } 2060 } 2061 2062 // Look through qualified types 2063 if (QualifiedTypeLoc *QualifiedTL = dyn_cast<QualifiedTypeLoc>(&TL)) { 2064 TL = QualifiedTL->getUnqualifiedLoc(); 2065 continue; 2066 } 2067 } 2068 2069 // Try to get the function prototype behind the block pointer type, 2070 // then we're done. 2071 if (BlockPointerTypeLoc *BlockPtr 2072 = dyn_cast<BlockPointerTypeLoc>(&TL)) { 2073 TL = BlockPtr->getPointeeLoc().IgnoreParens(); 2074 Block = dyn_cast<FunctionTypeLoc>(&TL); 2075 BlockProto = dyn_cast<FunctionProtoTypeLoc>(&TL); 2076 } 2077 break; 2078 } 2079 } 2080 2081 if (!Block) { 2082 // We were unable to find a FunctionProtoTypeLoc with parameter names 2083 // for the block; just use the parameter type as a placeholder. 2084 std::string Result; 2085 if (!ObjCMethodParam && Param->getIdentifier()) 2086 Result = Param->getIdentifier()->getName(); 2087 2088 Param->getType().getUnqualifiedType().getAsStringInternal(Result, Policy); 2089 2090 if (ObjCMethodParam) { 2091 Result = "(" + formatObjCParamQualifiers(Param->getObjCDeclQualifier()) 2092 + Result + ")"; 2093 if (Param->getIdentifier()) 2094 Result += Param->getIdentifier()->getName(); 2095 } 2096 2097 return Result; 2098 } 2099 2100 // We have the function prototype behind the block pointer type, as it was 2101 // written in the source. 2102 std::string Result; 2103 QualType ResultType = Block->getTypePtr()->getResultType(); 2104 if (!ResultType->isVoidType() || SuppressBlock) 2105 ResultType.getAsStringInternal(Result, Policy); 2106 2107 // Format the parameter list. 2108 std::string Params; 2109 if (!BlockProto || Block->getNumArgs() == 0) { 2110 if (BlockProto && BlockProto->getTypePtr()->isVariadic()) 2111 Params = "(...)"; 2112 else 2113 Params = "(void)"; 2114 } else { 2115 Params += "("; 2116 for (unsigned I = 0, N = Block->getNumArgs(); I != N; ++I) { 2117 if (I) 2118 Params += ", "; 2119 Params += FormatFunctionParameter(Context, Policy, Block->getArg(I), 2120 /*SuppressName=*/false, 2121 /*SuppressBlock=*/true); 2122 2123 if (I == N - 1 && BlockProto->getTypePtr()->isVariadic()) 2124 Params += ", ..."; 2125 } 2126 Params += ")"; 2127 } 2128 2129 if (SuppressBlock) { 2130 // Format as a parameter. 2131 Result = Result + " (^"; 2132 if (Param->getIdentifier()) 2133 Result += Param->getIdentifier()->getName(); 2134 Result += ")"; 2135 Result += Params; 2136 } else { 2137 // Format as a block literal argument. 2138 Result = '^' + Result; 2139 Result += Params; 2140 2141 if (Param->getIdentifier()) 2142 Result += Param->getIdentifier()->getName(); 2143 } 2144 2145 return Result; 2146 } 2147 2148 /// \brief Add function parameter chunks to the given code completion string. 2149 static void AddFunctionParameterChunks(ASTContext &Context, 2150 const PrintingPolicy &Policy, 2151 FunctionDecl *Function, 2152 CodeCompletionBuilder &Result, 2153 unsigned Start = 0, 2154 bool InOptional = false) { 2155 typedef CodeCompletionString::Chunk Chunk; 2156 bool FirstParameter = true; 2157 2158 for (unsigned P = Start, N = Function->getNumParams(); P != N; ++P) { 2159 ParmVarDecl *Param = Function->getParamDecl(P); 2160 2161 if (Param->hasDefaultArg() && !InOptional) { 2162 // When we see an optional default argument, put that argument and 2163 // the remaining default arguments into a new, optional string. 2164 CodeCompletionBuilder Opt(Result.getAllocator()); 2165 if (!FirstParameter) 2166 Opt.AddChunk(Chunk(CodeCompletionString::CK_Comma)); 2167 AddFunctionParameterChunks(Context, Policy, Function, Opt, P, true); 2168 Result.AddOptionalChunk(Opt.TakeString()); 2169 break; 2170 } 2171 2172 if (FirstParameter) 2173 FirstParameter = false; 2174 else 2175 Result.AddChunk(Chunk(CodeCompletionString::CK_Comma)); 2176 2177 InOptional = false; 2178 2179 // Format the placeholder string. 2180 std::string PlaceholderStr = FormatFunctionParameter(Context, Policy, 2181 Param); 2182 2183 if (Function->isVariadic() && P == N - 1) 2184 PlaceholderStr += ", ..."; 2185 2186 // Add the placeholder string. 2187 Result.AddPlaceholderChunk( 2188 Result.getAllocator().CopyString(PlaceholderStr)); 2189 } 2190 2191 if (const FunctionProtoType *Proto 2192 = Function->getType()->getAs<FunctionProtoType>()) 2193 if (Proto->isVariadic()) { 2194 if (Proto->getNumArgs() == 0) 2195 Result.AddPlaceholderChunk("..."); 2196 2197 MaybeAddSentinel(Context, Function, Result); 2198 } 2199 } 2200 2201 /// \brief Add template parameter chunks to the given code completion string. 2202 static void AddTemplateParameterChunks(ASTContext &Context, 2203 const PrintingPolicy &Policy, 2204 TemplateDecl *Template, 2205 CodeCompletionBuilder &Result, 2206 unsigned MaxParameters = 0, 2207 unsigned Start = 0, 2208 bool InDefaultArg = false) { 2209 typedef CodeCompletionString::Chunk Chunk; 2210 bool FirstParameter = true; 2211 2212 TemplateParameterList *Params = Template->getTemplateParameters(); 2213 TemplateParameterList::iterator PEnd = Params->end(); 2214 if (MaxParameters) 2215 PEnd = Params->begin() + MaxParameters; 2216 for (TemplateParameterList::iterator P = Params->begin() + Start; 2217 P != PEnd; ++P) { 2218 bool HasDefaultArg = false; 2219 std::string PlaceholderStr; 2220 if (TemplateTypeParmDecl *TTP = dyn_cast<TemplateTypeParmDecl>(*P)) { 2221 if (TTP->wasDeclaredWithTypename()) 2222 PlaceholderStr = "typename"; 2223 else 2224 PlaceholderStr = "class"; 2225 2226 if (TTP->getIdentifier()) { 2227 PlaceholderStr += ' '; 2228 PlaceholderStr += TTP->getIdentifier()->getName(); 2229 } 2230 2231 HasDefaultArg = TTP->hasDefaultArgument(); 2232 } else if (NonTypeTemplateParmDecl *NTTP 2233 = dyn_cast<NonTypeTemplateParmDecl>(*P)) { 2234 if (NTTP->getIdentifier()) 2235 PlaceholderStr = NTTP->getIdentifier()->getName(); 2236 NTTP->getType().getAsStringInternal(PlaceholderStr, Policy); 2237 HasDefaultArg = NTTP->hasDefaultArgument(); 2238 } else { 2239 assert(isa<TemplateTemplateParmDecl>(*P)); 2240 TemplateTemplateParmDecl *TTP = cast<TemplateTemplateParmDecl>(*P); 2241 2242 // Since putting the template argument list into the placeholder would 2243 // be very, very long, we just use an abbreviation. 2244 PlaceholderStr = "template<...> class"; 2245 if (TTP->getIdentifier()) { 2246 PlaceholderStr += ' '; 2247 PlaceholderStr += TTP->getIdentifier()->getName(); 2248 } 2249 2250 HasDefaultArg = TTP->hasDefaultArgument(); 2251 } 2252 2253 if (HasDefaultArg && !InDefaultArg) { 2254 // When we see an optional default argument, put that argument and 2255 // the remaining default arguments into a new, optional string. 2256 CodeCompletionBuilder Opt(Result.getAllocator()); 2257 if (!FirstParameter) 2258 Opt.AddChunk(Chunk(CodeCompletionString::CK_Comma)); 2259 AddTemplateParameterChunks(Context, Policy, Template, Opt, MaxParameters, 2260 P - Params->begin(), true); 2261 Result.AddOptionalChunk(Opt.TakeString()); 2262 break; 2263 } 2264 2265 InDefaultArg = false; 2266 2267 if (FirstParameter) 2268 FirstParameter = false; 2269 else 2270 Result.AddChunk(Chunk(CodeCompletionString::CK_Comma)); 2271 2272 // Add the placeholder string. 2273 Result.AddPlaceholderChunk( 2274 Result.getAllocator().CopyString(PlaceholderStr)); 2275 } 2276 } 2277 2278 /// \brief Add a qualifier to the given code-completion string, if the 2279 /// provided nested-name-specifier is non-NULL. 2280 static void 2281 AddQualifierToCompletionString(CodeCompletionBuilder &Result, 2282 NestedNameSpecifier *Qualifier, 2283 bool QualifierIsInformative, 2284 ASTContext &Context, 2285 const PrintingPolicy &Policy) { 2286 if (!Qualifier) 2287 return; 2288 2289 std::string PrintedNNS; 2290 { 2291 llvm::raw_string_ostream OS(PrintedNNS); 2292 Qualifier->print(OS, Policy); 2293 } 2294 if (QualifierIsInformative) 2295 Result.AddInformativeChunk(Result.getAllocator().CopyString(PrintedNNS)); 2296 else 2297 Result.AddTextChunk(Result.getAllocator().CopyString(PrintedNNS)); 2298 } 2299 2300 static void 2301 AddFunctionTypeQualsToCompletionString(CodeCompletionBuilder &Result, 2302 FunctionDecl *Function) { 2303 const FunctionProtoType *Proto 2304 = Function->getType()->getAs<FunctionProtoType>(); 2305 if (!Proto || !Proto->getTypeQuals()) 2306 return; 2307 2308 // FIXME: Add ref-qualifier! 2309 2310 // Handle single qualifiers without copying 2311 if (Proto->getTypeQuals() == Qualifiers::Const) { 2312 Result.AddInformativeChunk(" const"); 2313 return; 2314 } 2315 2316 if (Proto->getTypeQuals() == Qualifiers::Volatile) { 2317 Result.AddInformativeChunk(" volatile"); 2318 return; 2319 } 2320 2321 if (Proto->getTypeQuals() == Qualifiers::Restrict) { 2322 Result.AddInformativeChunk(" restrict"); 2323 return; 2324 } 2325 2326 // Handle multiple qualifiers. 2327 std::string QualsStr; 2328 if (Proto->getTypeQuals() & Qualifiers::Const) 2329 QualsStr += " const"; 2330 if (Proto->getTypeQuals() & Qualifiers::Volatile) 2331 QualsStr += " volatile"; 2332 if (Proto->getTypeQuals() & Qualifiers::Restrict) 2333 QualsStr += " restrict"; 2334 Result.AddInformativeChunk(Result.getAllocator().CopyString(QualsStr)); 2335 } 2336 2337 /// \brief Add the name of the given declaration 2338 static void AddTypedNameChunk(ASTContext &Context, const PrintingPolicy &Policy, 2339 NamedDecl *ND, CodeCompletionBuilder &Result) { 2340 typedef CodeCompletionString::Chunk Chunk; 2341 2342 DeclarationName Name = ND->getDeclName(); 2343 if (!Name) 2344 return; 2345 2346 switch (Name.getNameKind()) { 2347 case DeclarationName::CXXOperatorName: { 2348 const char *OperatorName = 0; 2349 switch (Name.getCXXOverloadedOperator()) { 2350 case OO_None: 2351 case OO_Conditional: 2352 case NUM_OVERLOADED_OPERATORS: 2353 OperatorName = "operator"; 2354 break; 2355 2356 #define OVERLOADED_OPERATOR(Name,Spelling,Token,Unary,Binary,MemberOnly) \ 2357 case OO_##Name: OperatorName = "operator" Spelling; break; 2358 #define OVERLOADED_OPERATOR_MULTI(Name,Spelling,Unary,Binary,MemberOnly) 2359 #include "clang/Basic/OperatorKinds.def" 2360 2361 case OO_New: OperatorName = "operator new"; break; 2362 case OO_Delete: OperatorName = "operator delete"; break; 2363 case OO_Array_New: OperatorName = "operator new[]"; break; 2364 case OO_Array_Delete: OperatorName = "operator delete[]"; break; 2365 case OO_Call: OperatorName = "operator()"; break; 2366 case OO_Subscript: OperatorName = "operator[]"; break; 2367 } 2368 Result.AddTypedTextChunk(OperatorName); 2369 break; 2370 } 2371 2372 case DeclarationName::Identifier: 2373 case DeclarationName::CXXConversionFunctionName: 2374 case DeclarationName::CXXDestructorName: 2375 case DeclarationName::CXXLiteralOperatorName: 2376 Result.AddTypedTextChunk( 2377 Result.getAllocator().CopyString(ND->getNameAsString())); 2378 break; 2379 2380 case DeclarationName::CXXUsingDirective: 2381 case DeclarationName::ObjCZeroArgSelector: 2382 case DeclarationName::ObjCOneArgSelector: 2383 case DeclarationName::ObjCMultiArgSelector: 2384 break; 2385 2386 case DeclarationName::CXXConstructorName: { 2387 CXXRecordDecl *Record = 0; 2388 QualType Ty = Name.getCXXNameType(); 2389 if (const RecordType *RecordTy = Ty->getAs<RecordType>()) 2390 Record = cast<CXXRecordDecl>(RecordTy->getDecl()); 2391 else if (const InjectedClassNameType *InjectedTy 2392 = Ty->getAs<InjectedClassNameType>()) 2393 Record = InjectedTy->getDecl(); 2394 else { 2395 Result.AddTypedTextChunk( 2396 Result.getAllocator().CopyString(ND->getNameAsString())); 2397 break; 2398 } 2399 2400 Result.AddTypedTextChunk( 2401 Result.getAllocator().CopyString(Record->getNameAsString())); 2402 if (ClassTemplateDecl *Template = Record->getDescribedClassTemplate()) { 2403 Result.AddChunk(Chunk(CodeCompletionString::CK_LeftAngle)); 2404 AddTemplateParameterChunks(Context, Policy, Template, Result); 2405 Result.AddChunk(Chunk(CodeCompletionString::CK_RightAngle)); 2406 } 2407 break; 2408 } 2409 } 2410 } 2411 2412 /// \brief If possible, create a new code completion string for the given 2413 /// result. 2414 /// 2415 /// \returns Either a new, heap-allocated code completion string describing 2416 /// how to use this result, or NULL to indicate that the string or name of the 2417 /// result is all that is needed. 2418 CodeCompletionString * 2419 CodeCompletionResult::CreateCodeCompletionString(Sema &S, 2420 CodeCompletionAllocator &Allocator) { 2421 typedef CodeCompletionString::Chunk Chunk; 2422 CodeCompletionBuilder Result(Allocator, Priority, Availability); 2423 2424 PrintingPolicy Policy = getCompletionPrintingPolicy(S); 2425 if (Kind == RK_Pattern) { 2426 Pattern->Priority = Priority; 2427 Pattern->Availability = Availability; 2428 return Pattern; 2429 } 2430 2431 if (Kind == RK_Keyword) { 2432 Result.AddTypedTextChunk(Keyword); 2433 return Result.TakeString(); 2434 } 2435 2436 if (Kind == RK_Macro) { 2437 MacroInfo *MI = S.PP.getMacroInfo(Macro); 2438 assert(MI && "Not a macro?"); 2439 2440 Result.AddTypedTextChunk( 2441 Result.getAllocator().CopyString(Macro->getName())); 2442 2443 if (!MI->isFunctionLike()) 2444 return Result.TakeString(); 2445 2446 // Format a function-like macro with placeholders for the arguments. 2447 Result.AddChunk(Chunk(CodeCompletionString::CK_LeftParen)); 2448 bool CombineVariadicArgument = false; 2449 MacroInfo::arg_iterator A = MI->arg_begin(), AEnd = MI->arg_end(); 2450 if (MI->isVariadic() && AEnd - A > 1) { 2451 AEnd -= 2; 2452 CombineVariadicArgument = true; 2453 } 2454 for (MacroInfo::arg_iterator A = MI->arg_begin(); A != AEnd; ++A) { 2455 if (A != MI->arg_begin()) 2456 Result.AddChunk(Chunk(CodeCompletionString::CK_Comma)); 2457 2458 if (!MI->isVariadic() || A + 1 != AEnd) { 2459 // Non-variadic argument. 2460 Result.AddPlaceholderChunk( 2461 Result.getAllocator().CopyString((*A)->getName())); 2462 continue; 2463 } 2464 2465 // Variadic argument; cope with the difference between GNU and C99 2466 // variadic macros, providing a single placeholder for the rest of the 2467 // arguments. 2468 if ((*A)->isStr("__VA_ARGS__")) 2469 Result.AddPlaceholderChunk("..."); 2470 else { 2471 std::string Arg = (*A)->getName(); 2472 Arg += "..."; 2473 Result.AddPlaceholderChunk(Result.getAllocator().CopyString(Arg)); 2474 } 2475 } 2476 2477 if (CombineVariadicArgument) { 2478 // Handle the next-to-last argument, combining it with the variadic 2479 // argument. 2480 std::string LastArg = (*A)->getName(); 2481 ++A; 2482 if ((*A)->isStr("__VA_ARGS__")) 2483 LastArg += ", ..."; 2484 else 2485 LastArg += ", " + (*A)->getName().str() + "..."; 2486 Result.AddPlaceholderChunk(Result.getAllocator().CopyString(LastArg)); 2487 } 2488 Result.AddChunk(Chunk(CodeCompletionString::CK_RightParen)); 2489 return Result.TakeString(); 2490 } 2491 2492 assert(Kind == RK_Declaration && "Missed a result kind?"); 2493 NamedDecl *ND = Declaration; 2494 2495 if (StartsNestedNameSpecifier) { 2496 Result.AddTypedTextChunk( 2497 Result.getAllocator().CopyString(ND->getNameAsString())); 2498 Result.AddTextChunk("::"); 2499 return Result.TakeString(); 2500 } 2501 2502 for (Decl::attr_iterator i = ND->attr_begin(); i != ND->attr_end(); ++i) { 2503 if (AnnotateAttr *Attr = dyn_cast_or_null<AnnotateAttr>(*i)) { 2504 Result.AddAnnotation(Result.getAllocator().CopyString(Attr->getAnnotation())); 2505 } 2506 } 2507 2508 AddResultTypeChunk(S.Context, Policy, ND, Result); 2509 2510 if (FunctionDecl *Function = dyn_cast<FunctionDecl>(ND)) { 2511 AddQualifierToCompletionString(Result, Qualifier, QualifierIsInformative, 2512 S.Context, Policy); 2513 AddTypedNameChunk(S.Context, Policy, ND, Result); 2514 Result.AddChunk(Chunk(CodeCompletionString::CK_LeftParen)); 2515 AddFunctionParameterChunks(S.Context, Policy, Function, Result); 2516 Result.AddChunk(Chunk(CodeCompletionString::CK_RightParen)); 2517 AddFunctionTypeQualsToCompletionString(Result, Function); 2518 return Result.TakeString(); 2519 } 2520 2521 if (FunctionTemplateDecl *FunTmpl = dyn_cast<FunctionTemplateDecl>(ND)) { 2522 AddQualifierToCompletionString(Result, Qualifier, QualifierIsInformative, 2523 S.Context, Policy); 2524 FunctionDecl *Function = FunTmpl->getTemplatedDecl(); 2525 AddTypedNameChunk(S.Context, Policy, Function, Result); 2526 2527 // Figure out which template parameters are deduced (or have default 2528 // arguments). 2529 SmallVector<bool, 16> Deduced; 2530 S.MarkDeducedTemplateParameters(FunTmpl, Deduced); 2531 unsigned LastDeducibleArgument; 2532 for (LastDeducibleArgument = Deduced.size(); LastDeducibleArgument > 0; 2533 --LastDeducibleArgument) { 2534 if (!Deduced[LastDeducibleArgument - 1]) { 2535 // C++0x: Figure out if the template argument has a default. If so, 2536 // the user doesn't need to type this argument. 2537 // FIXME: We need to abstract template parameters better! 2538 bool HasDefaultArg = false; 2539 NamedDecl *Param = FunTmpl->getTemplateParameters()->getParam( 2540 LastDeducibleArgument - 1); 2541 if (TemplateTypeParmDecl *TTP = dyn_cast<TemplateTypeParmDecl>(Param)) 2542 HasDefaultArg = TTP->hasDefaultArgument(); 2543 else if (NonTypeTemplateParmDecl *NTTP 2544 = dyn_cast<NonTypeTemplateParmDecl>(Param)) 2545 HasDefaultArg = NTTP->hasDefaultArgument(); 2546 else { 2547 assert(isa<TemplateTemplateParmDecl>(Param)); 2548 HasDefaultArg 2549 = cast<TemplateTemplateParmDecl>(Param)->hasDefaultArgument(); 2550 } 2551 2552 if (!HasDefaultArg) 2553 break; 2554 } 2555 } 2556 2557 if (LastDeducibleArgument) { 2558 // Some of the function template arguments cannot be deduced from a 2559 // function call, so we introduce an explicit template argument list 2560 // containing all of the arguments up to the first deducible argument. 2561 Result.AddChunk(Chunk(CodeCompletionString::CK_LeftAngle)); 2562 AddTemplateParameterChunks(S.Context, Policy, FunTmpl, Result, 2563 LastDeducibleArgument); 2564 Result.AddChunk(Chunk(CodeCompletionString::CK_RightAngle)); 2565 } 2566 2567 // Add the function parameters 2568 Result.AddChunk(Chunk(CodeCompletionString::CK_LeftParen)); 2569 AddFunctionParameterChunks(S.Context, Policy, Function, Result); 2570 Result.AddChunk(Chunk(CodeCompletionString::CK_RightParen)); 2571 AddFunctionTypeQualsToCompletionString(Result, Function); 2572 return Result.TakeString(); 2573 } 2574 2575 if (TemplateDecl *Template = dyn_cast<TemplateDecl>(ND)) { 2576 AddQualifierToCompletionString(Result, Qualifier, QualifierIsInformative, 2577 S.Context, Policy); 2578 Result.AddTypedTextChunk( 2579 Result.getAllocator().CopyString(Template->getNameAsString())); 2580 Result.AddChunk(Chunk(CodeCompletionString::CK_LeftAngle)); 2581 AddTemplateParameterChunks(S.Context, Policy, Template, Result); 2582 Result.AddChunk(Chunk(CodeCompletionString::CK_RightAngle)); 2583 return Result.TakeString(); 2584 } 2585 2586 if (ObjCMethodDecl *Method = dyn_cast<ObjCMethodDecl>(ND)) { 2587 Selector Sel = Method->getSelector(); 2588 if (Sel.isUnarySelector()) { 2589 Result.AddTypedTextChunk(Result.getAllocator().CopyString( 2590 Sel.getNameForSlot(0))); 2591 return Result.TakeString(); 2592 } 2593 2594 std::string SelName = Sel.getNameForSlot(0).str(); 2595 SelName += ':'; 2596 if (StartParameter == 0) 2597 Result.AddTypedTextChunk(Result.getAllocator().CopyString(SelName)); 2598 else { 2599 Result.AddInformativeChunk(Result.getAllocator().CopyString(SelName)); 2600 2601 // If there is only one parameter, and we're past it, add an empty 2602 // typed-text chunk since there is nothing to type. 2603 if (Method->param_size() == 1) 2604 Result.AddTypedTextChunk(""); 2605 } 2606 unsigned Idx = 0; 2607 for (ObjCMethodDecl::param_iterator P = Method->param_begin(), 2608 PEnd = Method->param_end(); 2609 P != PEnd; (void)++P, ++Idx) { 2610 if (Idx > 0) { 2611 std::string Keyword; 2612 if (Idx > StartParameter) 2613 Result.AddChunk(CodeCompletionString::CK_HorizontalSpace); 2614 if (IdentifierInfo *II = Sel.getIdentifierInfoForSlot(Idx)) 2615 Keyword += II->getName(); 2616 Keyword += ":"; 2617 if (Idx < StartParameter || AllParametersAreInformative) 2618 Result.AddInformativeChunk(Result.getAllocator().CopyString(Keyword)); 2619 else 2620 Result.AddTypedTextChunk(Result.getAllocator().CopyString(Keyword)); 2621 } 2622 2623 // If we're before the starting parameter, skip the placeholder. 2624 if (Idx < StartParameter) 2625 continue; 2626 2627 std::string Arg; 2628 2629 if ((*P)->getType()->isBlockPointerType() && !DeclaringEntity) 2630 Arg = FormatFunctionParameter(S.Context, Policy, *P, true); 2631 else { 2632 (*P)->getType().getAsStringInternal(Arg, Policy); 2633 Arg = "(" + formatObjCParamQualifiers((*P)->getObjCDeclQualifier()) 2634 + Arg + ")"; 2635 if (IdentifierInfo *II = (*P)->getIdentifier()) 2636 if (DeclaringEntity || AllParametersAreInformative) 2637 Arg += II->getName(); 2638 } 2639 2640 if (Method->isVariadic() && (P + 1) == PEnd) 2641 Arg += ", ..."; 2642 2643 if (DeclaringEntity) 2644 Result.AddTextChunk(Result.getAllocator().CopyString(Arg)); 2645 else if (AllParametersAreInformative) 2646 Result.AddInformativeChunk(Result.getAllocator().CopyString(Arg)); 2647 else 2648 Result.AddPlaceholderChunk(Result.getAllocator().CopyString(Arg)); 2649 } 2650 2651 if (Method->isVariadic()) { 2652 if (Method->param_size() == 0) { 2653 if (DeclaringEntity) 2654 Result.AddTextChunk(", ..."); 2655 else if (AllParametersAreInformative) 2656 Result.AddInformativeChunk(", ..."); 2657 else 2658 Result.AddPlaceholderChunk(", ..."); 2659 } 2660 2661 MaybeAddSentinel(S.Context, Method, Result); 2662 } 2663 2664 return Result.TakeString(); 2665 } 2666 2667 if (Qualifier) 2668 AddQualifierToCompletionString(Result, Qualifier, QualifierIsInformative, 2669 S.Context, Policy); 2670 2671 Result.AddTypedTextChunk( 2672 Result.getAllocator().CopyString(ND->getNameAsString())); 2673 return Result.TakeString(); 2674 } 2675 2676 CodeCompletionString * 2677 CodeCompleteConsumer::OverloadCandidate::CreateSignatureString( 2678 unsigned CurrentArg, 2679 Sema &S, 2680 CodeCompletionAllocator &Allocator) const { 2681 typedef CodeCompletionString::Chunk Chunk; 2682 PrintingPolicy Policy = getCompletionPrintingPolicy(S); 2683 2684 // FIXME: Set priority, availability appropriately. 2685 CodeCompletionBuilder Result(Allocator, 1, CXAvailability_Available); 2686 FunctionDecl *FDecl = getFunction(); 2687 AddResultTypeChunk(S.Context, Policy, FDecl, Result); 2688 const FunctionProtoType *Proto 2689 = dyn_cast<FunctionProtoType>(getFunctionType()); 2690 if (!FDecl && !Proto) { 2691 // Function without a prototype. Just give the return type and a 2692 // highlighted ellipsis. 2693 const FunctionType *FT = getFunctionType(); 2694 Result.AddTextChunk(GetCompletionTypeString(FT->getResultType(), 2695 S.Context, Policy, 2696 Result.getAllocator())); 2697 Result.AddChunk(Chunk(CodeCompletionString::CK_LeftParen)); 2698 Result.AddChunk(Chunk(CodeCompletionString::CK_CurrentParameter, "...")); 2699 Result.AddChunk(Chunk(CodeCompletionString::CK_RightParen)); 2700 return Result.TakeString(); 2701 } 2702 2703 if (FDecl) 2704 Result.AddTextChunk( 2705 Result.getAllocator().CopyString(FDecl->getNameAsString())); 2706 else 2707 Result.AddTextChunk( 2708 Result.getAllocator().CopyString( 2709 Proto->getResultType().getAsString(Policy))); 2710 2711 Result.AddChunk(Chunk(CodeCompletionString::CK_LeftParen)); 2712 unsigned NumParams = FDecl? FDecl->getNumParams() : Proto->getNumArgs(); 2713 for (unsigned I = 0; I != NumParams; ++I) { 2714 if (I) 2715 Result.AddChunk(Chunk(CodeCompletionString::CK_Comma)); 2716 2717 std::string ArgString; 2718 QualType ArgType; 2719 2720 if (FDecl) { 2721 ArgString = FDecl->getParamDecl(I)->getNameAsString(); 2722 ArgType = FDecl->getParamDecl(I)->getOriginalType(); 2723 } else { 2724 ArgType = Proto->getArgType(I); 2725 } 2726 2727 ArgType.getAsStringInternal(ArgString, Policy); 2728 2729 if (I == CurrentArg) 2730 Result.AddChunk(Chunk(CodeCompletionString::CK_CurrentParameter, 2731 Result.getAllocator().CopyString(ArgString))); 2732 else 2733 Result.AddTextChunk(Result.getAllocator().CopyString(ArgString)); 2734 } 2735 2736 if (Proto && Proto->isVariadic()) { 2737 Result.AddChunk(Chunk(CodeCompletionString::CK_Comma)); 2738 if (CurrentArg < NumParams) 2739 Result.AddTextChunk("..."); 2740 else 2741 Result.AddChunk(Chunk(CodeCompletionString::CK_CurrentParameter, "...")); 2742 } 2743 Result.AddChunk(Chunk(CodeCompletionString::CK_RightParen)); 2744 2745 return Result.TakeString(); 2746 } 2747 2748 unsigned clang::getMacroUsagePriority(StringRef MacroName, 2749 const LangOptions &LangOpts, 2750 bool PreferredTypeIsPointer) { 2751 unsigned Priority = CCP_Macro; 2752 2753 // Treat the "nil", "Nil" and "NULL" macros as null pointer constants. 2754 if (MacroName.equals("nil") || MacroName.equals("NULL") || 2755 MacroName.equals("Nil")) { 2756 Priority = CCP_Constant; 2757 if (PreferredTypeIsPointer) 2758 Priority = Priority / CCF_SimilarTypeMatch; 2759 } 2760 // Treat "YES", "NO", "true", and "false" as constants. 2761 else if (MacroName.equals("YES") || MacroName.equals("NO") || 2762 MacroName.equals("true") || MacroName.equals("false")) 2763 Priority = CCP_Constant; 2764 // Treat "bool" as a type. 2765 else if (MacroName.equals("bool")) 2766 Priority = CCP_Type + (LangOpts.ObjC1? CCD_bool_in_ObjC : 0); 2767 2768 2769 return Priority; 2770 } 2771 2772 CXCursorKind clang::getCursorKindForDecl(Decl *D) { 2773 if (!D) 2774 return CXCursor_UnexposedDecl; 2775 2776 switch (D->getKind()) { 2777 case Decl::Enum: return CXCursor_EnumDecl; 2778 case Decl::EnumConstant: return CXCursor_EnumConstantDecl; 2779 case Decl::Field: return CXCursor_FieldDecl; 2780 case Decl::Function: 2781 return CXCursor_FunctionDecl; 2782 case Decl::ObjCCategory: return CXCursor_ObjCCategoryDecl; 2783 case Decl::ObjCCategoryImpl: return CXCursor_ObjCCategoryImplDecl; 2784 // FIXME 2785 return CXCursor_UnexposedDecl; 2786 case Decl::ObjCImplementation: return CXCursor_ObjCImplementationDecl; 2787 2788 case Decl::ObjCInterface: 2789 if (cast<ObjCInterfaceDecl>(D)->isThisDeclarationADefinition()) 2790 return CXCursor_ObjCInterfaceDecl; 2791 2792 // Forward declarations are not directly exposed. 2793 return CXCursor_UnexposedDecl; 2794 2795 case Decl::ObjCIvar: return CXCursor_ObjCIvarDecl; 2796 case Decl::ObjCMethod: 2797 return cast<ObjCMethodDecl>(D)->isInstanceMethod() 2798 ? CXCursor_ObjCInstanceMethodDecl : CXCursor_ObjCClassMethodDecl; 2799 case Decl::CXXMethod: return CXCursor_CXXMethod; 2800 case Decl::CXXConstructor: return CXCursor_Constructor; 2801 case Decl::CXXDestructor: return CXCursor_Destructor; 2802 case Decl::CXXConversion: return CXCursor_ConversionFunction; 2803 case Decl::ObjCProperty: return CXCursor_ObjCPropertyDecl; 2804 case Decl::ObjCProtocol: 2805 if (cast<ObjCProtocolDecl>(D)->isThisDeclarationADefinition()) 2806 return CXCursor_ObjCProtocolDecl; 2807 2808 return CXCursor_UnexposedDecl; 2809 2810 case Decl::ParmVar: return CXCursor_ParmDecl; 2811 case Decl::Typedef: return CXCursor_TypedefDecl; 2812 case Decl::TypeAlias: return CXCursor_TypeAliasDecl; 2813 case Decl::Var: return CXCursor_VarDecl; 2814 case Decl::Namespace: return CXCursor_Namespace; 2815 case Decl::NamespaceAlias: return CXCursor_NamespaceAlias; 2816 case Decl::TemplateTypeParm: return CXCursor_TemplateTypeParameter; 2817 case Decl::NonTypeTemplateParm:return CXCursor_NonTypeTemplateParameter; 2818 case Decl::TemplateTemplateParm:return CXCursor_TemplateTemplateParameter; 2819 case Decl::FunctionTemplate: return CXCursor_FunctionTemplate; 2820 case Decl::ClassTemplate: return CXCursor_ClassTemplate; 2821 case Decl::AccessSpec: return CXCursor_CXXAccessSpecifier; 2822 case Decl::ClassTemplatePartialSpecialization: 2823 return CXCursor_ClassTemplatePartialSpecialization; 2824 case Decl::UsingDirective: return CXCursor_UsingDirective; 2825 2826 case Decl::Using: 2827 case Decl::UnresolvedUsingValue: 2828 case Decl::UnresolvedUsingTypename: 2829 return CXCursor_UsingDeclaration; 2830 2831 case Decl::ObjCPropertyImpl: 2832 switch (cast<ObjCPropertyImplDecl>(D)->getPropertyImplementation()) { 2833 case ObjCPropertyImplDecl::Dynamic: 2834 return CXCursor_ObjCDynamicDecl; 2835 2836 case ObjCPropertyImplDecl::Synthesize: 2837 return CXCursor_ObjCSynthesizeDecl; 2838 } 2839 break; 2840 2841 default: 2842 if (TagDecl *TD = dyn_cast<TagDecl>(D)) { 2843 switch (TD->getTagKind()) { 2844 case TTK_Struct: return CXCursor_StructDecl; 2845 case TTK_Class: return CXCursor_ClassDecl; 2846 case TTK_Union: return CXCursor_UnionDecl; 2847 case TTK_Enum: return CXCursor_EnumDecl; 2848 } 2849 } 2850 } 2851 2852 return CXCursor_UnexposedDecl; 2853 } 2854 2855 static void AddMacroResults(Preprocessor &PP, ResultBuilder &Results, 2856 bool TargetTypeIsPointer = false) { 2857 typedef CodeCompletionResult Result; 2858 2859 Results.EnterNewScope(); 2860 2861 for (Preprocessor::macro_iterator M = PP.macro_begin(), 2862 MEnd = PP.macro_end(); 2863 M != MEnd; ++M) { 2864 Results.AddResult(Result(M->first, 2865 getMacroUsagePriority(M->first->getName(), 2866 PP.getLangOptions(), 2867 TargetTypeIsPointer))); 2868 } 2869 2870 Results.ExitScope(); 2871 2872 } 2873 2874 static void AddPrettyFunctionResults(const LangOptions &LangOpts, 2875 ResultBuilder &Results) { 2876 typedef CodeCompletionResult Result; 2877 2878 Results.EnterNewScope(); 2879 2880 Results.AddResult(Result("__PRETTY_FUNCTION__", CCP_Constant)); 2881 Results.AddResult(Result("__FUNCTION__", CCP_Constant)); 2882 if (LangOpts.C99 || LangOpts.CPlusPlus0x) 2883 Results.AddResult(Result("__func__", CCP_Constant)); 2884 Results.ExitScope(); 2885 } 2886 2887 static void HandleCodeCompleteResults(Sema *S, 2888 CodeCompleteConsumer *CodeCompleter, 2889 CodeCompletionContext Context, 2890 CodeCompletionResult *Results, 2891 unsigned NumResults) { 2892 if (CodeCompleter) 2893 CodeCompleter->ProcessCodeCompleteResults(*S, Context, Results, NumResults); 2894 } 2895 2896 static enum CodeCompletionContext::Kind mapCodeCompletionContext(Sema &S, 2897 Sema::ParserCompletionContext PCC) { 2898 switch (PCC) { 2899 case Sema::PCC_Namespace: 2900 return CodeCompletionContext::CCC_TopLevel; 2901 2902 case Sema::PCC_Class: 2903 return CodeCompletionContext::CCC_ClassStructUnion; 2904 2905 case Sema::PCC_ObjCInterface: 2906 return CodeCompletionContext::CCC_ObjCInterface; 2907 2908 case Sema::PCC_ObjCImplementation: 2909 return CodeCompletionContext::CCC_ObjCImplementation; 2910 2911 case Sema::PCC_ObjCInstanceVariableList: 2912 return CodeCompletionContext::CCC_ObjCIvarList; 2913 2914 case Sema::PCC_Template: 2915 case Sema::PCC_MemberTemplate: 2916 if (S.CurContext->isFileContext()) 2917 return CodeCompletionContext::CCC_TopLevel; 2918 else if (S.CurContext->isRecord()) 2919 return CodeCompletionContext::CCC_ClassStructUnion; 2920 else 2921 return CodeCompletionContext::CCC_Other; 2922 2923 case Sema::PCC_RecoveryInFunction: 2924 return CodeCompletionContext::CCC_Recovery; 2925 2926 case Sema::PCC_ForInit: 2927 if (S.getLangOptions().CPlusPlus || S.getLangOptions().C99 || 2928 S.getLangOptions().ObjC1) 2929 return CodeCompletionContext::CCC_ParenthesizedExpression; 2930 else 2931 return CodeCompletionContext::CCC_Expression; 2932 2933 case Sema::PCC_Expression: 2934 case Sema::PCC_Condition: 2935 return CodeCompletionContext::CCC_Expression; 2936 2937 case Sema::PCC_Statement: 2938 return CodeCompletionContext::CCC_Statement; 2939 2940 case Sema::PCC_Type: 2941 return CodeCompletionContext::CCC_Type; 2942 2943 case Sema::PCC_ParenthesizedExpression: 2944 return CodeCompletionContext::CCC_ParenthesizedExpression; 2945 2946 case Sema::PCC_LocalDeclarationSpecifiers: 2947 return CodeCompletionContext::CCC_Type; 2948 } 2949 2950 return CodeCompletionContext::CCC_Other; 2951 } 2952 2953 /// \brief If we're in a C++ virtual member function, add completion results 2954 /// that invoke the functions we override, since it's common to invoke the 2955 /// overridden function as well as adding new functionality. 2956 /// 2957 /// \param S The semantic analysis object for which we are generating results. 2958 /// 2959 /// \param InContext This context in which the nested-name-specifier preceding 2960 /// the code-completion point 2961 static void MaybeAddOverrideCalls(Sema &S, DeclContext *InContext, 2962 ResultBuilder &Results) { 2963 // Look through blocks. 2964 DeclContext *CurContext = S.CurContext; 2965 while (isa<BlockDecl>(CurContext)) 2966 CurContext = CurContext->getParent(); 2967 2968 2969 CXXMethodDecl *Method = dyn_cast<CXXMethodDecl>(CurContext); 2970 if (!Method || !Method->isVirtual()) 2971 return; 2972 2973 // We need to have names for all of the parameters, if we're going to 2974 // generate a forwarding call. 2975 for (CXXMethodDecl::param_iterator P = Method->param_begin(), 2976 PEnd = Method->param_end(); 2977 P != PEnd; 2978 ++P) { 2979 if (!(*P)->getDeclName()) 2980 return; 2981 } 2982 2983 PrintingPolicy Policy = getCompletionPrintingPolicy(S); 2984 for (CXXMethodDecl::method_iterator M = Method->begin_overridden_methods(), 2985 MEnd = Method->end_overridden_methods(); 2986 M != MEnd; ++M) { 2987 CodeCompletionBuilder Builder(Results.getAllocator()); 2988 CXXMethodDecl *Overridden = const_cast<CXXMethodDecl *>(*M); 2989 if (Overridden->getCanonicalDecl() == Method->getCanonicalDecl()) 2990 continue; 2991 2992 // If we need a nested-name-specifier, add one now. 2993 if (!InContext) { 2994 NestedNameSpecifier *NNS 2995 = getRequiredQualification(S.Context, CurContext, 2996 Overridden->getDeclContext()); 2997 if (NNS) { 2998 std::string Str; 2999 llvm::raw_string_ostream OS(Str); 3000 NNS->print(OS, Policy); 3001 Builder.AddTextChunk(Results.getAllocator().CopyString(OS.str())); 3002 } 3003 } else if (!InContext->Equals(Overridden->getDeclContext())) 3004 continue; 3005 3006 Builder.AddTypedTextChunk(Results.getAllocator().CopyString( 3007 Overridden->getNameAsString())); 3008 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 3009 bool FirstParam = true; 3010 for (CXXMethodDecl::param_iterator P = Method->param_begin(), 3011 PEnd = Method->param_end(); 3012 P != PEnd; ++P) { 3013 if (FirstParam) 3014 FirstParam = false; 3015 else 3016 Builder.AddChunk(CodeCompletionString::CK_Comma); 3017 3018 Builder.AddPlaceholderChunk(Results.getAllocator().CopyString( 3019 (*P)->getIdentifier()->getName())); 3020 } 3021 Builder.AddChunk(CodeCompletionString::CK_RightParen); 3022 Results.AddResult(CodeCompletionResult(Builder.TakeString(), 3023 CCP_SuperCompletion, 3024 CXCursor_CXXMethod)); 3025 Results.Ignore(Overridden); 3026 } 3027 } 3028 3029 void Sema::CodeCompleteOrdinaryName(Scope *S, 3030 ParserCompletionContext CompletionContext) { 3031 typedef CodeCompletionResult Result; 3032 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 3033 mapCodeCompletionContext(*this, CompletionContext)); 3034 Results.EnterNewScope(); 3035 3036 // Determine how to filter results, e.g., so that the names of 3037 // values (functions, enumerators, function templates, etc.) are 3038 // only allowed where we can have an expression. 3039 switch (CompletionContext) { 3040 case PCC_Namespace: 3041 case PCC_Class: 3042 case PCC_ObjCInterface: 3043 case PCC_ObjCImplementation: 3044 case PCC_ObjCInstanceVariableList: 3045 case PCC_Template: 3046 case PCC_MemberTemplate: 3047 case PCC_Type: 3048 case PCC_LocalDeclarationSpecifiers: 3049 Results.setFilter(&ResultBuilder::IsOrdinaryNonValueName); 3050 break; 3051 3052 case PCC_Statement: 3053 case PCC_ParenthesizedExpression: 3054 case PCC_Expression: 3055 case PCC_ForInit: 3056 case PCC_Condition: 3057 if (WantTypesInContext(CompletionContext, getLangOptions())) 3058 Results.setFilter(&ResultBuilder::IsOrdinaryName); 3059 else 3060 Results.setFilter(&ResultBuilder::IsOrdinaryNonTypeName); 3061 3062 if (getLangOptions().CPlusPlus) 3063 MaybeAddOverrideCalls(*this, /*InContext=*/0, Results); 3064 break; 3065 3066 case PCC_RecoveryInFunction: 3067 // Unfiltered 3068 break; 3069 } 3070 3071 // If we are in a C++ non-static member function, check the qualifiers on 3072 // the member function to filter/prioritize the results list. 3073 if (CXXMethodDecl *CurMethod = dyn_cast<CXXMethodDecl>(CurContext)) 3074 if (CurMethod->isInstance()) 3075 Results.setObjectTypeQualifiers( 3076 Qualifiers::fromCVRMask(CurMethod->getTypeQualifiers())); 3077 3078 CodeCompletionDeclConsumer Consumer(Results, CurContext); 3079 LookupVisibleDecls(S, LookupOrdinaryName, Consumer, 3080 CodeCompleter->includeGlobals()); 3081 3082 AddOrdinaryNameResults(CompletionContext, S, *this, Results); 3083 Results.ExitScope(); 3084 3085 switch (CompletionContext) { 3086 case PCC_ParenthesizedExpression: 3087 case PCC_Expression: 3088 case PCC_Statement: 3089 case PCC_RecoveryInFunction: 3090 if (S->getFnParent()) 3091 AddPrettyFunctionResults(PP.getLangOptions(), Results); 3092 break; 3093 3094 case PCC_Namespace: 3095 case PCC_Class: 3096 case PCC_ObjCInterface: 3097 case PCC_ObjCImplementation: 3098 case PCC_ObjCInstanceVariableList: 3099 case PCC_Template: 3100 case PCC_MemberTemplate: 3101 case PCC_ForInit: 3102 case PCC_Condition: 3103 case PCC_Type: 3104 case PCC_LocalDeclarationSpecifiers: 3105 break; 3106 } 3107 3108 if (CodeCompleter->includeMacros()) 3109 AddMacroResults(PP, Results); 3110 3111 HandleCodeCompleteResults(this, CodeCompleter, Results.getCompletionContext(), 3112 Results.data(),Results.size()); 3113 } 3114 3115 static void AddClassMessageCompletions(Sema &SemaRef, Scope *S, 3116 ParsedType Receiver, 3117 IdentifierInfo **SelIdents, 3118 unsigned NumSelIdents, 3119 bool AtArgumentExpression, 3120 bool IsSuper, 3121 ResultBuilder &Results); 3122 3123 void Sema::CodeCompleteDeclSpec(Scope *S, DeclSpec &DS, 3124 bool AllowNonIdentifiers, 3125 bool AllowNestedNameSpecifiers) { 3126 typedef CodeCompletionResult Result; 3127 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 3128 AllowNestedNameSpecifiers 3129 ? CodeCompletionContext::CCC_PotentiallyQualifiedName 3130 : CodeCompletionContext::CCC_Name); 3131 Results.EnterNewScope(); 3132 3133 // Type qualifiers can come after names. 3134 Results.AddResult(Result("const")); 3135 Results.AddResult(Result("volatile")); 3136 if (getLangOptions().C99) 3137 Results.AddResult(Result("restrict")); 3138 3139 if (getLangOptions().CPlusPlus) { 3140 if (AllowNonIdentifiers) { 3141 Results.AddResult(Result("operator")); 3142 } 3143 3144 // Add nested-name-specifiers. 3145 if (AllowNestedNameSpecifiers) { 3146 Results.allowNestedNameSpecifiers(); 3147 Results.setFilter(&ResultBuilder::IsImpossibleToSatisfy); 3148 CodeCompletionDeclConsumer Consumer(Results, CurContext); 3149 LookupVisibleDecls(S, LookupNestedNameSpecifierName, Consumer, 3150 CodeCompleter->includeGlobals()); 3151 Results.setFilter(0); 3152 } 3153 } 3154 Results.ExitScope(); 3155 3156 // If we're in a context where we might have an expression (rather than a 3157 // declaration), and what we've seen so far is an Objective-C type that could 3158 // be a receiver of a class message, this may be a class message send with 3159 // the initial opening bracket '[' missing. Add appropriate completions. 3160 if (AllowNonIdentifiers && !AllowNestedNameSpecifiers && 3161 DS.getTypeSpecType() == DeclSpec::TST_typename && 3162 DS.getStorageClassSpecAsWritten() == DeclSpec::SCS_unspecified && 3163 !DS.isThreadSpecified() && !DS.isExternInLinkageSpec() && 3164 DS.getTypeSpecComplex() == DeclSpec::TSC_unspecified && 3165 DS.getTypeSpecSign() == DeclSpec::TSS_unspecified && 3166 DS.getTypeQualifiers() == 0 && 3167 S && 3168 (S->getFlags() & Scope::DeclScope) != 0 && 3169 (S->getFlags() & (Scope::ClassScope | Scope::TemplateParamScope | 3170 Scope::FunctionPrototypeScope | 3171 Scope::AtCatchScope)) == 0) { 3172 ParsedType T = DS.getRepAsType(); 3173 if (!T.get().isNull() && T.get()->isObjCObjectOrInterfaceType()) 3174 AddClassMessageCompletions(*this, S, T, 0, 0, false, false, Results); 3175 } 3176 3177 // Note that we intentionally suppress macro results here, since we do not 3178 // encourage using macros to produce the names of entities. 3179 3180 HandleCodeCompleteResults(this, CodeCompleter, 3181 Results.getCompletionContext(), 3182 Results.data(), Results.size()); 3183 } 3184 3185 struct Sema::CodeCompleteExpressionData { 3186 CodeCompleteExpressionData(QualType PreferredType = QualType()) 3187 : PreferredType(PreferredType), IntegralConstantExpression(false), 3188 ObjCCollection(false) { } 3189 3190 QualType PreferredType; 3191 bool IntegralConstantExpression; 3192 bool ObjCCollection; 3193 SmallVector<Decl *, 4> IgnoreDecls; 3194 }; 3195 3196 /// \brief Perform code-completion in an expression context when we know what 3197 /// type we're looking for. 3198 /// 3199 /// \param IntegralConstantExpression Only permit integral constant 3200 /// expressions. 3201 void Sema::CodeCompleteExpression(Scope *S, 3202 const CodeCompleteExpressionData &Data) { 3203 typedef CodeCompletionResult Result; 3204 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 3205 CodeCompletionContext::CCC_Expression); 3206 if (Data.ObjCCollection) 3207 Results.setFilter(&ResultBuilder::IsObjCCollection); 3208 else if (Data.IntegralConstantExpression) 3209 Results.setFilter(&ResultBuilder::IsIntegralConstantValue); 3210 else if (WantTypesInContext(PCC_Expression, getLangOptions())) 3211 Results.setFilter(&ResultBuilder::IsOrdinaryName); 3212 else 3213 Results.setFilter(&ResultBuilder::IsOrdinaryNonTypeName); 3214 3215 if (!Data.PreferredType.isNull()) 3216 Results.setPreferredType(Data.PreferredType.getNonReferenceType()); 3217 3218 // Ignore any declarations that we were told that we don't care about. 3219 for (unsigned I = 0, N = Data.IgnoreDecls.size(); I != N; ++I) 3220 Results.Ignore(Data.IgnoreDecls[I]); 3221 3222 CodeCompletionDeclConsumer Consumer(Results, CurContext); 3223 LookupVisibleDecls(S, LookupOrdinaryName, Consumer, 3224 CodeCompleter->includeGlobals()); 3225 3226 Results.EnterNewScope(); 3227 AddOrdinaryNameResults(PCC_Expression, S, *this, Results); 3228 Results.ExitScope(); 3229 3230 bool PreferredTypeIsPointer = false; 3231 if (!Data.PreferredType.isNull()) 3232 PreferredTypeIsPointer = Data.PreferredType->isAnyPointerType() 3233 || Data.PreferredType->isMemberPointerType() 3234 || Data.PreferredType->isBlockPointerType(); 3235 3236 if (S->getFnParent() && 3237 !Data.ObjCCollection && 3238 !Data.IntegralConstantExpression) 3239 AddPrettyFunctionResults(PP.getLangOptions(), Results); 3240 3241 if (CodeCompleter->includeMacros()) 3242 AddMacroResults(PP, Results, PreferredTypeIsPointer); 3243 HandleCodeCompleteResults(this, CodeCompleter, 3244 CodeCompletionContext(CodeCompletionContext::CCC_Expression, 3245 Data.PreferredType), 3246 Results.data(),Results.size()); 3247 } 3248 3249 void Sema::CodeCompletePostfixExpression(Scope *S, ExprResult E) { 3250 if (E.isInvalid()) 3251 CodeCompleteOrdinaryName(S, PCC_RecoveryInFunction); 3252 else if (getLangOptions().ObjC1) 3253 CodeCompleteObjCInstanceMessage(S, E.take(), 0, 0, false); 3254 } 3255 3256 /// \brief The set of properties that have already been added, referenced by 3257 /// property name. 3258 typedef llvm::SmallPtrSet<IdentifierInfo*, 16> AddedPropertiesSet; 3259 3260 static void AddObjCProperties(ObjCContainerDecl *Container, 3261 bool AllowCategories, 3262 bool AllowNullaryMethods, 3263 DeclContext *CurContext, 3264 AddedPropertiesSet &AddedProperties, 3265 ResultBuilder &Results) { 3266 typedef CodeCompletionResult Result; 3267 3268 // Add properties in this container. 3269 for (ObjCContainerDecl::prop_iterator P = Container->prop_begin(), 3270 PEnd = Container->prop_end(); 3271 P != PEnd; 3272 ++P) { 3273 if (AddedProperties.insert(P->getIdentifier())) 3274 Results.MaybeAddResult(Result(*P, 0), CurContext); 3275 } 3276 3277 // Add nullary methods 3278 if (AllowNullaryMethods) { 3279 ASTContext &Context = Container->getASTContext(); 3280 PrintingPolicy Policy = getCompletionPrintingPolicy(Results.getSema()); 3281 for (ObjCContainerDecl::method_iterator M = Container->meth_begin(), 3282 MEnd = Container->meth_end(); 3283 M != MEnd; ++M) { 3284 if (M->getSelector().isUnarySelector()) 3285 if (IdentifierInfo *Name = M->getSelector().getIdentifierInfoForSlot(0)) 3286 if (AddedProperties.insert(Name)) { 3287 CodeCompletionBuilder Builder(Results.getAllocator()); 3288 AddResultTypeChunk(Context, Policy, *M, Builder); 3289 Builder.AddTypedTextChunk( 3290 Results.getAllocator().CopyString(Name->getName())); 3291 3292 CXAvailabilityKind Availability = CXAvailability_Available; 3293 switch (M->getAvailability()) { 3294 case AR_Available: 3295 case AR_NotYetIntroduced: 3296 Availability = CXAvailability_Available; 3297 break; 3298 3299 case AR_Deprecated: 3300 Availability = CXAvailability_Deprecated; 3301 break; 3302 3303 case AR_Unavailable: 3304 Availability = CXAvailability_NotAvailable; 3305 break; 3306 } 3307 3308 Results.MaybeAddResult(Result(Builder.TakeString(), 3309 CCP_MemberDeclaration + CCD_MethodAsProperty, 3310 M->isInstanceMethod() 3311 ? CXCursor_ObjCInstanceMethodDecl 3312 : CXCursor_ObjCClassMethodDecl, 3313 Availability), 3314 CurContext); 3315 } 3316 } 3317 } 3318 3319 3320 // Add properties in referenced protocols. 3321 if (ObjCProtocolDecl *Protocol = dyn_cast<ObjCProtocolDecl>(Container)) { 3322 for (ObjCProtocolDecl::protocol_iterator P = Protocol->protocol_begin(), 3323 PEnd = Protocol->protocol_end(); 3324 P != PEnd; ++P) 3325 AddObjCProperties(*P, AllowCategories, AllowNullaryMethods, CurContext, 3326 AddedProperties, Results); 3327 } else if (ObjCInterfaceDecl *IFace = dyn_cast<ObjCInterfaceDecl>(Container)){ 3328 if (AllowCategories) { 3329 // Look through categories. 3330 for (ObjCCategoryDecl *Category = IFace->getCategoryList(); 3331 Category; Category = Category->getNextClassCategory()) 3332 AddObjCProperties(Category, AllowCategories, AllowNullaryMethods, 3333 CurContext, AddedProperties, Results); 3334 } 3335 3336 // Look through protocols. 3337 for (ObjCInterfaceDecl::all_protocol_iterator 3338 I = IFace->all_referenced_protocol_begin(), 3339 E = IFace->all_referenced_protocol_end(); I != E; ++I) 3340 AddObjCProperties(*I, AllowCategories, AllowNullaryMethods, CurContext, 3341 AddedProperties, Results); 3342 3343 // Look in the superclass. 3344 if (IFace->getSuperClass()) 3345 AddObjCProperties(IFace->getSuperClass(), AllowCategories, 3346 AllowNullaryMethods, CurContext, 3347 AddedProperties, Results); 3348 } else if (const ObjCCategoryDecl *Category 3349 = dyn_cast<ObjCCategoryDecl>(Container)) { 3350 // Look through protocols. 3351 for (ObjCCategoryDecl::protocol_iterator P = Category->protocol_begin(), 3352 PEnd = Category->protocol_end(); 3353 P != PEnd; ++P) 3354 AddObjCProperties(*P, AllowCategories, AllowNullaryMethods, CurContext, 3355 AddedProperties, Results); 3356 } 3357 } 3358 3359 void Sema::CodeCompleteMemberReferenceExpr(Scope *S, Expr *BaseE, 3360 SourceLocation OpLoc, 3361 bool IsArrow) { 3362 if (!BaseE || !CodeCompleter) 3363 return; 3364 3365 typedef CodeCompletionResult Result; 3366 3367 Expr *Base = static_cast<Expr *>(BaseE); 3368 QualType BaseType = Base->getType(); 3369 3370 if (IsArrow) { 3371 if (const PointerType *Ptr = BaseType->getAs<PointerType>()) 3372 BaseType = Ptr->getPointeeType(); 3373 else if (BaseType->isObjCObjectPointerType()) 3374 /*Do nothing*/ ; 3375 else 3376 return; 3377 } 3378 3379 enum CodeCompletionContext::Kind contextKind; 3380 3381 if (IsArrow) { 3382 contextKind = CodeCompletionContext::CCC_ArrowMemberAccess; 3383 } 3384 else { 3385 if (BaseType->isObjCObjectPointerType() || 3386 BaseType->isObjCObjectOrInterfaceType()) { 3387 contextKind = CodeCompletionContext::CCC_ObjCPropertyAccess; 3388 } 3389 else { 3390 contextKind = CodeCompletionContext::CCC_DotMemberAccess; 3391 } 3392 } 3393 3394 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 3395 CodeCompletionContext(contextKind, 3396 BaseType), 3397 &ResultBuilder::IsMember); 3398 Results.EnterNewScope(); 3399 if (const RecordType *Record = BaseType->getAs<RecordType>()) { 3400 // Indicate that we are performing a member access, and the cv-qualifiers 3401 // for the base object type. 3402 Results.setObjectTypeQualifiers(BaseType.getQualifiers()); 3403 3404 // Access to a C/C++ class, struct, or union. 3405 Results.allowNestedNameSpecifiers(); 3406 CodeCompletionDeclConsumer Consumer(Results, CurContext); 3407 LookupVisibleDecls(Record->getDecl(), LookupMemberName, Consumer, 3408 CodeCompleter->includeGlobals()); 3409 3410 if (getLangOptions().CPlusPlus) { 3411 if (!Results.empty()) { 3412 // The "template" keyword can follow "->" or "." in the grammar. 3413 // However, we only want to suggest the template keyword if something 3414 // is dependent. 3415 bool IsDependent = BaseType->isDependentType(); 3416 if (!IsDependent) { 3417 for (Scope *DepScope = S; DepScope; DepScope = DepScope->getParent()) 3418 if (DeclContext *Ctx = (DeclContext *)DepScope->getEntity()) { 3419 IsDependent = Ctx->isDependentContext(); 3420 break; 3421 } 3422 } 3423 3424 if (IsDependent) 3425 Results.AddResult(Result("template")); 3426 } 3427 } 3428 } else if (!IsArrow && BaseType->getAsObjCInterfacePointerType()) { 3429 // Objective-C property reference. 3430 AddedPropertiesSet AddedProperties; 3431 3432 // Add property results based on our interface. 3433 const ObjCObjectPointerType *ObjCPtr 3434 = BaseType->getAsObjCInterfacePointerType(); 3435 assert(ObjCPtr && "Non-NULL pointer guaranteed above!"); 3436 AddObjCProperties(ObjCPtr->getInterfaceDecl(), true, 3437 /*AllowNullaryMethods=*/true, CurContext, 3438 AddedProperties, Results); 3439 3440 // Add properties from the protocols in a qualified interface. 3441 for (ObjCObjectPointerType::qual_iterator I = ObjCPtr->qual_begin(), 3442 E = ObjCPtr->qual_end(); 3443 I != E; ++I) 3444 AddObjCProperties(*I, true, /*AllowNullaryMethods=*/true, CurContext, 3445 AddedProperties, Results); 3446 } else if ((IsArrow && BaseType->isObjCObjectPointerType()) || 3447 (!IsArrow && BaseType->isObjCObjectType())) { 3448 // Objective-C instance variable access. 3449 ObjCInterfaceDecl *Class = 0; 3450 if (const ObjCObjectPointerType *ObjCPtr 3451 = BaseType->getAs<ObjCObjectPointerType>()) 3452 Class = ObjCPtr->getInterfaceDecl(); 3453 else 3454 Class = BaseType->getAs<ObjCObjectType>()->getInterface(); 3455 3456 // Add all ivars from this class and its superclasses. 3457 if (Class) { 3458 CodeCompletionDeclConsumer Consumer(Results, CurContext); 3459 Results.setFilter(&ResultBuilder::IsObjCIvar); 3460 LookupVisibleDecls(Class, LookupMemberName, Consumer, 3461 CodeCompleter->includeGlobals()); 3462 } 3463 } 3464 3465 // FIXME: How do we cope with isa? 3466 3467 Results.ExitScope(); 3468 3469 // Hand off the results found for code completion. 3470 HandleCodeCompleteResults(this, CodeCompleter, 3471 Results.getCompletionContext(), 3472 Results.data(),Results.size()); 3473 } 3474 3475 void Sema::CodeCompleteTag(Scope *S, unsigned TagSpec) { 3476 if (!CodeCompleter) 3477 return; 3478 3479 typedef CodeCompletionResult Result; 3480 ResultBuilder::LookupFilter Filter = 0; 3481 enum CodeCompletionContext::Kind ContextKind 3482 = CodeCompletionContext::CCC_Other; 3483 switch ((DeclSpec::TST)TagSpec) { 3484 case DeclSpec::TST_enum: 3485 Filter = &ResultBuilder::IsEnum; 3486 ContextKind = CodeCompletionContext::CCC_EnumTag; 3487 break; 3488 3489 case DeclSpec::TST_union: 3490 Filter = &ResultBuilder::IsUnion; 3491 ContextKind = CodeCompletionContext::CCC_UnionTag; 3492 break; 3493 3494 case DeclSpec::TST_struct: 3495 case DeclSpec::TST_class: 3496 Filter = &ResultBuilder::IsClassOrStruct; 3497 ContextKind = CodeCompletionContext::CCC_ClassOrStructTag; 3498 break; 3499 3500 default: 3501 llvm_unreachable("Unknown type specifier kind in CodeCompleteTag"); 3502 } 3503 3504 ResultBuilder Results(*this, CodeCompleter->getAllocator(), ContextKind); 3505 CodeCompletionDeclConsumer Consumer(Results, CurContext); 3506 3507 // First pass: look for tags. 3508 Results.setFilter(Filter); 3509 LookupVisibleDecls(S, LookupTagName, Consumer, 3510 CodeCompleter->includeGlobals()); 3511 3512 if (CodeCompleter->includeGlobals()) { 3513 // Second pass: look for nested name specifiers. 3514 Results.setFilter(&ResultBuilder::IsNestedNameSpecifier); 3515 LookupVisibleDecls(S, LookupNestedNameSpecifierName, Consumer); 3516 } 3517 3518 HandleCodeCompleteResults(this, CodeCompleter, Results.getCompletionContext(), 3519 Results.data(),Results.size()); 3520 } 3521 3522 void Sema::CodeCompleteTypeQualifiers(DeclSpec &DS) { 3523 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 3524 CodeCompletionContext::CCC_TypeQualifiers); 3525 Results.EnterNewScope(); 3526 if (!(DS.getTypeQualifiers() & DeclSpec::TQ_const)) 3527 Results.AddResult("const"); 3528 if (!(DS.getTypeQualifiers() & DeclSpec::TQ_volatile)) 3529 Results.AddResult("volatile"); 3530 if (getLangOptions().C99 && 3531 !(DS.getTypeQualifiers() & DeclSpec::TQ_restrict)) 3532 Results.AddResult("restrict"); 3533 Results.ExitScope(); 3534 HandleCodeCompleteResults(this, CodeCompleter, 3535 Results.getCompletionContext(), 3536 Results.data(), Results.size()); 3537 } 3538 3539 void Sema::CodeCompleteCase(Scope *S) { 3540 if (getCurFunction()->SwitchStack.empty() || !CodeCompleter) 3541 return; 3542 3543 SwitchStmt *Switch = getCurFunction()->SwitchStack.back(); 3544 QualType type = Switch->getCond()->IgnoreImplicit()->getType(); 3545 if (!type->isEnumeralType()) { 3546 CodeCompleteExpressionData Data(type); 3547 Data.IntegralConstantExpression = true; 3548 CodeCompleteExpression(S, Data); 3549 return; 3550 } 3551 3552 // Code-complete the cases of a switch statement over an enumeration type 3553 // by providing the list of 3554 EnumDecl *Enum = type->castAs<EnumType>()->getDecl(); 3555 3556 // Determine which enumerators we have already seen in the switch statement. 3557 // FIXME: Ideally, we would also be able to look *past* the code-completion 3558 // token, in case we are code-completing in the middle of the switch and not 3559 // at the end. However, we aren't able to do so at the moment. 3560 llvm::SmallPtrSet<EnumConstantDecl *, 8> EnumeratorsSeen; 3561 NestedNameSpecifier *Qualifier = 0; 3562 for (SwitchCase *SC = Switch->getSwitchCaseList(); SC; 3563 SC = SC->getNextSwitchCase()) { 3564 CaseStmt *Case = dyn_cast<CaseStmt>(SC); 3565 if (!Case) 3566 continue; 3567 3568 Expr *CaseVal = Case->getLHS()->IgnoreParenCasts(); 3569 if (DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(CaseVal)) 3570 if (EnumConstantDecl *Enumerator 3571 = dyn_cast<EnumConstantDecl>(DRE->getDecl())) { 3572 // We look into the AST of the case statement to determine which 3573 // enumerator was named. Alternatively, we could compute the value of 3574 // the integral constant expression, then compare it against the 3575 // values of each enumerator. However, value-based approach would not 3576 // work as well with C++ templates where enumerators declared within a 3577 // template are type- and value-dependent. 3578 EnumeratorsSeen.insert(Enumerator); 3579 3580 // If this is a qualified-id, keep track of the nested-name-specifier 3581 // so that we can reproduce it as part of code completion, e.g., 3582 // 3583 // switch (TagD.getKind()) { 3584 // case TagDecl::TK_enum: 3585 // break; 3586 // case XXX 3587 // 3588 // At the XXX, our completions are TagDecl::TK_union, 3589 // TagDecl::TK_struct, and TagDecl::TK_class, rather than TK_union, 3590 // TK_struct, and TK_class. 3591 Qualifier = DRE->getQualifier(); 3592 } 3593 } 3594 3595 if (getLangOptions().CPlusPlus && !Qualifier && EnumeratorsSeen.empty()) { 3596 // If there are no prior enumerators in C++, check whether we have to 3597 // qualify the names of the enumerators that we suggest, because they 3598 // may not be visible in this scope. 3599 Qualifier = getRequiredQualification(Context, CurContext, 3600 Enum->getDeclContext()); 3601 3602 // FIXME: Scoped enums need to start with "EnumDecl" as the context! 3603 } 3604 3605 // Add any enumerators that have not yet been mentioned. 3606 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 3607 CodeCompletionContext::CCC_Expression); 3608 Results.EnterNewScope(); 3609 for (EnumDecl::enumerator_iterator E = Enum->enumerator_begin(), 3610 EEnd = Enum->enumerator_end(); 3611 E != EEnd; ++E) { 3612 if (EnumeratorsSeen.count(*E)) 3613 continue; 3614 3615 CodeCompletionResult R(*E, Qualifier); 3616 R.Priority = CCP_EnumInCase; 3617 Results.AddResult(R, CurContext, 0, false); 3618 } 3619 Results.ExitScope(); 3620 3621 //We need to make sure we're setting the right context, 3622 //so only say we include macros if the code completer says we do 3623 enum CodeCompletionContext::Kind kind = CodeCompletionContext::CCC_Other; 3624 if (CodeCompleter->includeMacros()) { 3625 AddMacroResults(PP, Results); 3626 kind = CodeCompletionContext::CCC_OtherWithMacros; 3627 } 3628 3629 3630 HandleCodeCompleteResults(this, CodeCompleter, 3631 kind, 3632 Results.data(),Results.size()); 3633 } 3634 3635 namespace { 3636 struct IsBetterOverloadCandidate { 3637 Sema &S; 3638 SourceLocation Loc; 3639 3640 public: 3641 explicit IsBetterOverloadCandidate(Sema &S, SourceLocation Loc) 3642 : S(S), Loc(Loc) { } 3643 3644 bool 3645 operator()(const OverloadCandidate &X, const OverloadCandidate &Y) const { 3646 return isBetterOverloadCandidate(S, X, Y, Loc); 3647 } 3648 }; 3649 } 3650 3651 static bool anyNullArguments(Expr **Args, unsigned NumArgs) { 3652 if (NumArgs && !Args) 3653 return true; 3654 3655 for (unsigned I = 0; I != NumArgs; ++I) 3656 if (!Args[I]) 3657 return true; 3658 3659 return false; 3660 } 3661 3662 void Sema::CodeCompleteCall(Scope *S, Expr *FnIn, 3663 Expr **ArgsIn, unsigned NumArgs) { 3664 if (!CodeCompleter) 3665 return; 3666 3667 // When we're code-completing for a call, we fall back to ordinary 3668 // name code-completion whenever we can't produce specific 3669 // results. We may want to revisit this strategy in the future, 3670 // e.g., by merging the two kinds of results. 3671 3672 Expr *Fn = (Expr *)FnIn; 3673 Expr **Args = (Expr **)ArgsIn; 3674 3675 // Ignore type-dependent call expressions entirely. 3676 if (!Fn || Fn->isTypeDependent() || anyNullArguments(Args, NumArgs) || 3677 Expr::hasAnyTypeDependentArguments(Args, NumArgs)) { 3678 CodeCompleteOrdinaryName(S, PCC_Expression); 3679 return; 3680 } 3681 3682 // Build an overload candidate set based on the functions we find. 3683 SourceLocation Loc = Fn->getExprLoc(); 3684 OverloadCandidateSet CandidateSet(Loc); 3685 3686 // FIXME: What if we're calling something that isn't a function declaration? 3687 // FIXME: What if we're calling a pseudo-destructor? 3688 // FIXME: What if we're calling a member function? 3689 3690 typedef CodeCompleteConsumer::OverloadCandidate ResultCandidate; 3691 SmallVector<ResultCandidate, 8> Results; 3692 3693 Expr *NakedFn = Fn->IgnoreParenCasts(); 3694 if (UnresolvedLookupExpr *ULE = dyn_cast<UnresolvedLookupExpr>(NakedFn)) 3695 AddOverloadedCallCandidates(ULE, Args, NumArgs, CandidateSet, 3696 /*PartialOverloading=*/ true); 3697 else if (DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(NakedFn)) { 3698 FunctionDecl *FDecl = dyn_cast<FunctionDecl>(DRE->getDecl()); 3699 if (FDecl) { 3700 if (!getLangOptions().CPlusPlus || 3701 !FDecl->getType()->getAs<FunctionProtoType>()) 3702 Results.push_back(ResultCandidate(FDecl)); 3703 else 3704 // FIXME: access? 3705 AddOverloadCandidate(FDecl, DeclAccessPair::make(FDecl, AS_none), 3706 Args, NumArgs, CandidateSet, 3707 false, /*PartialOverloading*/true); 3708 } 3709 } 3710 3711 QualType ParamType; 3712 3713 if (!CandidateSet.empty()) { 3714 // Sort the overload candidate set by placing the best overloads first. 3715 std::stable_sort(CandidateSet.begin(), CandidateSet.end(), 3716 IsBetterOverloadCandidate(*this, Loc)); 3717 3718 // Add the remaining viable overload candidates as code-completion reslults. 3719 for (OverloadCandidateSet::iterator Cand = CandidateSet.begin(), 3720 CandEnd = CandidateSet.end(); 3721 Cand != CandEnd; ++Cand) { 3722 if (Cand->Viable) 3723 Results.push_back(ResultCandidate(Cand->Function)); 3724 } 3725 3726 // From the viable candidates, try to determine the type of this parameter. 3727 for (unsigned I = 0, N = Results.size(); I != N; ++I) { 3728 if (const FunctionType *FType = Results[I].getFunctionType()) 3729 if (const FunctionProtoType *Proto = dyn_cast<FunctionProtoType>(FType)) 3730 if (NumArgs < Proto->getNumArgs()) { 3731 if (ParamType.isNull()) 3732 ParamType = Proto->getArgType(NumArgs); 3733 else if (!Context.hasSameUnqualifiedType( 3734 ParamType.getNonReferenceType(), 3735 Proto->getArgType(NumArgs).getNonReferenceType())) { 3736 ParamType = QualType(); 3737 break; 3738 } 3739 } 3740 } 3741 } else { 3742 // Try to determine the parameter type from the type of the expression 3743 // being called. 3744 QualType FunctionType = Fn->getType(); 3745 if (const PointerType *Ptr = FunctionType->getAs<PointerType>()) 3746 FunctionType = Ptr->getPointeeType(); 3747 else if (const BlockPointerType *BlockPtr 3748 = FunctionType->getAs<BlockPointerType>()) 3749 FunctionType = BlockPtr->getPointeeType(); 3750 else if (const MemberPointerType *MemPtr 3751 = FunctionType->getAs<MemberPointerType>()) 3752 FunctionType = MemPtr->getPointeeType(); 3753 3754 if (const FunctionProtoType *Proto 3755 = FunctionType->getAs<FunctionProtoType>()) { 3756 if (NumArgs < Proto->getNumArgs()) 3757 ParamType = Proto->getArgType(NumArgs); 3758 } 3759 } 3760 3761 if (ParamType.isNull()) 3762 CodeCompleteOrdinaryName(S, PCC_Expression); 3763 else 3764 CodeCompleteExpression(S, ParamType); 3765 3766 if (!Results.empty()) 3767 CodeCompleter->ProcessOverloadCandidates(*this, NumArgs, Results.data(), 3768 Results.size()); 3769 } 3770 3771 void Sema::CodeCompleteInitializer(Scope *S, Decl *D) { 3772 ValueDecl *VD = dyn_cast_or_null<ValueDecl>(D); 3773 if (!VD) { 3774 CodeCompleteOrdinaryName(S, PCC_Expression); 3775 return; 3776 } 3777 3778 CodeCompleteExpression(S, VD->getType()); 3779 } 3780 3781 void Sema::CodeCompleteReturn(Scope *S) { 3782 QualType ResultType; 3783 if (isa<BlockDecl>(CurContext)) { 3784 if (BlockScopeInfo *BSI = getCurBlock()) 3785 ResultType = BSI->ReturnType; 3786 } else if (FunctionDecl *Function = dyn_cast<FunctionDecl>(CurContext)) 3787 ResultType = Function->getResultType(); 3788 else if (ObjCMethodDecl *Method = dyn_cast<ObjCMethodDecl>(CurContext)) 3789 ResultType = Method->getResultType(); 3790 3791 if (ResultType.isNull()) 3792 CodeCompleteOrdinaryName(S, PCC_Expression); 3793 else 3794 CodeCompleteExpression(S, ResultType); 3795 } 3796 3797 void Sema::CodeCompleteAfterIf(Scope *S) { 3798 typedef CodeCompletionResult Result; 3799 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 3800 mapCodeCompletionContext(*this, PCC_Statement)); 3801 Results.setFilter(&ResultBuilder::IsOrdinaryName); 3802 Results.EnterNewScope(); 3803 3804 CodeCompletionDeclConsumer Consumer(Results, CurContext); 3805 LookupVisibleDecls(S, LookupOrdinaryName, Consumer, 3806 CodeCompleter->includeGlobals()); 3807 3808 AddOrdinaryNameResults(PCC_Statement, S, *this, Results); 3809 3810 // "else" block 3811 CodeCompletionBuilder Builder(Results.getAllocator()); 3812 Builder.AddTypedTextChunk("else"); 3813 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 3814 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 3815 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 3816 Builder.AddPlaceholderChunk("statements"); 3817 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 3818 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 3819 Results.AddResult(Builder.TakeString()); 3820 3821 // "else if" block 3822 Builder.AddTypedTextChunk("else"); 3823 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 3824 Builder.AddTextChunk("if"); 3825 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 3826 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 3827 if (getLangOptions().CPlusPlus) 3828 Builder.AddPlaceholderChunk("condition"); 3829 else 3830 Builder.AddPlaceholderChunk("expression"); 3831 Builder.AddChunk(CodeCompletionString::CK_RightParen); 3832 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 3833 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 3834 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 3835 Builder.AddPlaceholderChunk("statements"); 3836 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 3837 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 3838 Results.AddResult(Builder.TakeString()); 3839 3840 Results.ExitScope(); 3841 3842 if (S->getFnParent()) 3843 AddPrettyFunctionResults(PP.getLangOptions(), Results); 3844 3845 if (CodeCompleter->includeMacros()) 3846 AddMacroResults(PP, Results); 3847 3848 HandleCodeCompleteResults(this, CodeCompleter, Results.getCompletionContext(), 3849 Results.data(),Results.size()); 3850 } 3851 3852 void Sema::CodeCompleteAssignmentRHS(Scope *S, Expr *LHS) { 3853 if (LHS) 3854 CodeCompleteExpression(S, static_cast<Expr *>(LHS)->getType()); 3855 else 3856 CodeCompleteOrdinaryName(S, PCC_Expression); 3857 } 3858 3859 void Sema::CodeCompleteQualifiedId(Scope *S, CXXScopeSpec &SS, 3860 bool EnteringContext) { 3861 if (!SS.getScopeRep() || !CodeCompleter) 3862 return; 3863 3864 DeclContext *Ctx = computeDeclContext(SS, EnteringContext); 3865 if (!Ctx) 3866 return; 3867 3868 // Try to instantiate any non-dependent declaration contexts before 3869 // we look in them. 3870 if (!isDependentScopeSpecifier(SS) && RequireCompleteDeclContext(SS, Ctx)) 3871 return; 3872 3873 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 3874 CodeCompletionContext::CCC_Name); 3875 Results.EnterNewScope(); 3876 3877 // The "template" keyword can follow "::" in the grammar, but only 3878 // put it into the grammar if the nested-name-specifier is dependent. 3879 NestedNameSpecifier *NNS = (NestedNameSpecifier *)SS.getScopeRep(); 3880 if (!Results.empty() && NNS->isDependent()) 3881 Results.AddResult("template"); 3882 3883 // Add calls to overridden virtual functions, if there are any. 3884 // 3885 // FIXME: This isn't wonderful, because we don't know whether we're actually 3886 // in a context that permits expressions. This is a general issue with 3887 // qualified-id completions. 3888 if (!EnteringContext) 3889 MaybeAddOverrideCalls(*this, Ctx, Results); 3890 Results.ExitScope(); 3891 3892 CodeCompletionDeclConsumer Consumer(Results, CurContext); 3893 LookupVisibleDecls(Ctx, LookupOrdinaryName, Consumer); 3894 3895 HandleCodeCompleteResults(this, CodeCompleter, 3896 Results.getCompletionContext(), 3897 Results.data(),Results.size()); 3898 } 3899 3900 void Sema::CodeCompleteUsing(Scope *S) { 3901 if (!CodeCompleter) 3902 return; 3903 3904 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 3905 CodeCompletionContext::CCC_PotentiallyQualifiedName, 3906 &ResultBuilder::IsNestedNameSpecifier); 3907 Results.EnterNewScope(); 3908 3909 // If we aren't in class scope, we could see the "namespace" keyword. 3910 if (!S->isClassScope()) 3911 Results.AddResult(CodeCompletionResult("namespace")); 3912 3913 // After "using", we can see anything that would start a 3914 // nested-name-specifier. 3915 CodeCompletionDeclConsumer Consumer(Results, CurContext); 3916 LookupVisibleDecls(S, LookupOrdinaryName, Consumer, 3917 CodeCompleter->includeGlobals()); 3918 Results.ExitScope(); 3919 3920 HandleCodeCompleteResults(this, CodeCompleter, 3921 CodeCompletionContext::CCC_PotentiallyQualifiedName, 3922 Results.data(),Results.size()); 3923 } 3924 3925 void Sema::CodeCompleteUsingDirective(Scope *S) { 3926 if (!CodeCompleter) 3927 return; 3928 3929 // After "using namespace", we expect to see a namespace name or namespace 3930 // alias. 3931 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 3932 CodeCompletionContext::CCC_Namespace, 3933 &ResultBuilder::IsNamespaceOrAlias); 3934 Results.EnterNewScope(); 3935 CodeCompletionDeclConsumer Consumer(Results, CurContext); 3936 LookupVisibleDecls(S, LookupOrdinaryName, Consumer, 3937 CodeCompleter->includeGlobals()); 3938 Results.ExitScope(); 3939 HandleCodeCompleteResults(this, CodeCompleter, 3940 CodeCompletionContext::CCC_Namespace, 3941 Results.data(),Results.size()); 3942 } 3943 3944 void Sema::CodeCompleteNamespaceDecl(Scope *S) { 3945 if (!CodeCompleter) 3946 return; 3947 3948 DeclContext *Ctx = (DeclContext *)S->getEntity(); 3949 if (!S->getParent()) 3950 Ctx = Context.getTranslationUnitDecl(); 3951 3952 bool SuppressedGlobalResults 3953 = Ctx && !CodeCompleter->includeGlobals() && isa<TranslationUnitDecl>(Ctx); 3954 3955 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 3956 SuppressedGlobalResults 3957 ? CodeCompletionContext::CCC_Namespace 3958 : CodeCompletionContext::CCC_Other, 3959 &ResultBuilder::IsNamespace); 3960 3961 if (Ctx && Ctx->isFileContext() && !SuppressedGlobalResults) { 3962 // We only want to see those namespaces that have already been defined 3963 // within this scope, because its likely that the user is creating an 3964 // extended namespace declaration. Keep track of the most recent 3965 // definition of each namespace. 3966 std::map<NamespaceDecl *, NamespaceDecl *> OrigToLatest; 3967 for (DeclContext::specific_decl_iterator<NamespaceDecl> 3968 NS(Ctx->decls_begin()), NSEnd(Ctx->decls_end()); 3969 NS != NSEnd; ++NS) 3970 OrigToLatest[NS->getOriginalNamespace()] = *NS; 3971 3972 // Add the most recent definition (or extended definition) of each 3973 // namespace to the list of results. 3974 Results.EnterNewScope(); 3975 for (std::map<NamespaceDecl *, NamespaceDecl *>::iterator 3976 NS = OrigToLatest.begin(), NSEnd = OrigToLatest.end(); 3977 NS != NSEnd; ++NS) 3978 Results.AddResult(CodeCompletionResult(NS->second, 0), 3979 CurContext, 0, false); 3980 Results.ExitScope(); 3981 } 3982 3983 HandleCodeCompleteResults(this, CodeCompleter, 3984 Results.getCompletionContext(), 3985 Results.data(),Results.size()); 3986 } 3987 3988 void Sema::CodeCompleteNamespaceAliasDecl(Scope *S) { 3989 if (!CodeCompleter) 3990 return; 3991 3992 // After "namespace", we expect to see a namespace or alias. 3993 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 3994 CodeCompletionContext::CCC_Namespace, 3995 &ResultBuilder::IsNamespaceOrAlias); 3996 CodeCompletionDeclConsumer Consumer(Results, CurContext); 3997 LookupVisibleDecls(S, LookupOrdinaryName, Consumer, 3998 CodeCompleter->includeGlobals()); 3999 HandleCodeCompleteResults(this, CodeCompleter, 4000 Results.getCompletionContext(), 4001 Results.data(),Results.size()); 4002 } 4003 4004 void Sema::CodeCompleteOperatorName(Scope *S) { 4005 if (!CodeCompleter) 4006 return; 4007 4008 typedef CodeCompletionResult Result; 4009 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 4010 CodeCompletionContext::CCC_Type, 4011 &ResultBuilder::IsType); 4012 Results.EnterNewScope(); 4013 4014 // Add the names of overloadable operators. 4015 #define OVERLOADED_OPERATOR(Name,Spelling,Token,Unary,Binary,MemberOnly) \ 4016 if (std::strcmp(Spelling, "?")) \ 4017 Results.AddResult(Result(Spelling)); 4018 #include "clang/Basic/OperatorKinds.def" 4019 4020 // Add any type names visible from the current scope 4021 Results.allowNestedNameSpecifiers(); 4022 CodeCompletionDeclConsumer Consumer(Results, CurContext); 4023 LookupVisibleDecls(S, LookupOrdinaryName, Consumer, 4024 CodeCompleter->includeGlobals()); 4025 4026 // Add any type specifiers 4027 AddTypeSpecifierResults(getLangOptions(), Results); 4028 Results.ExitScope(); 4029 4030 HandleCodeCompleteResults(this, CodeCompleter, 4031 CodeCompletionContext::CCC_Type, 4032 Results.data(),Results.size()); 4033 } 4034 4035 void Sema::CodeCompleteConstructorInitializer(Decl *ConstructorD, 4036 CXXCtorInitializer** Initializers, 4037 unsigned NumInitializers) { 4038 PrintingPolicy Policy = getCompletionPrintingPolicy(*this); 4039 CXXConstructorDecl *Constructor 4040 = static_cast<CXXConstructorDecl *>(ConstructorD); 4041 if (!Constructor) 4042 return; 4043 4044 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 4045 CodeCompletionContext::CCC_PotentiallyQualifiedName); 4046 Results.EnterNewScope(); 4047 4048 // Fill in any already-initialized fields or base classes. 4049 llvm::SmallPtrSet<FieldDecl *, 4> InitializedFields; 4050 llvm::SmallPtrSet<CanQualType, 4> InitializedBases; 4051 for (unsigned I = 0; I != NumInitializers; ++I) { 4052 if (Initializers[I]->isBaseInitializer()) 4053 InitializedBases.insert( 4054 Context.getCanonicalType(QualType(Initializers[I]->getBaseClass(), 0))); 4055 else 4056 InitializedFields.insert(cast<FieldDecl>( 4057 Initializers[I]->getAnyMember())); 4058 } 4059 4060 // Add completions for base classes. 4061 CodeCompletionBuilder Builder(Results.getAllocator()); 4062 bool SawLastInitializer = (NumInitializers == 0); 4063 CXXRecordDecl *ClassDecl = Constructor->getParent(); 4064 for (CXXRecordDecl::base_class_iterator Base = ClassDecl->bases_begin(), 4065 BaseEnd = ClassDecl->bases_end(); 4066 Base != BaseEnd; ++Base) { 4067 if (!InitializedBases.insert(Context.getCanonicalType(Base->getType()))) { 4068 SawLastInitializer 4069 = NumInitializers > 0 && 4070 Initializers[NumInitializers - 1]->isBaseInitializer() && 4071 Context.hasSameUnqualifiedType(Base->getType(), 4072 QualType(Initializers[NumInitializers - 1]->getBaseClass(), 0)); 4073 continue; 4074 } 4075 4076 Builder.AddTypedTextChunk( 4077 Results.getAllocator().CopyString( 4078 Base->getType().getAsString(Policy))); 4079 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 4080 Builder.AddPlaceholderChunk("args"); 4081 Builder.AddChunk(CodeCompletionString::CK_RightParen); 4082 Results.AddResult(CodeCompletionResult(Builder.TakeString(), 4083 SawLastInitializer? CCP_NextInitializer 4084 : CCP_MemberDeclaration)); 4085 SawLastInitializer = false; 4086 } 4087 4088 // Add completions for virtual base classes. 4089 for (CXXRecordDecl::base_class_iterator Base = ClassDecl->vbases_begin(), 4090 BaseEnd = ClassDecl->vbases_end(); 4091 Base != BaseEnd; ++Base) { 4092 if (!InitializedBases.insert(Context.getCanonicalType(Base->getType()))) { 4093 SawLastInitializer 4094 = NumInitializers > 0 && 4095 Initializers[NumInitializers - 1]->isBaseInitializer() && 4096 Context.hasSameUnqualifiedType(Base->getType(), 4097 QualType(Initializers[NumInitializers - 1]->getBaseClass(), 0)); 4098 continue; 4099 } 4100 4101 Builder.AddTypedTextChunk( 4102 Builder.getAllocator().CopyString( 4103 Base->getType().getAsString(Policy))); 4104 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 4105 Builder.AddPlaceholderChunk("args"); 4106 Builder.AddChunk(CodeCompletionString::CK_RightParen); 4107 Results.AddResult(CodeCompletionResult(Builder.TakeString(), 4108 SawLastInitializer? CCP_NextInitializer 4109 : CCP_MemberDeclaration)); 4110 SawLastInitializer = false; 4111 } 4112 4113 // Add completions for members. 4114 for (CXXRecordDecl::field_iterator Field = ClassDecl->field_begin(), 4115 FieldEnd = ClassDecl->field_end(); 4116 Field != FieldEnd; ++Field) { 4117 if (!InitializedFields.insert(cast<FieldDecl>(Field->getCanonicalDecl()))) { 4118 SawLastInitializer 4119 = NumInitializers > 0 && 4120 Initializers[NumInitializers - 1]->isAnyMemberInitializer() && 4121 Initializers[NumInitializers - 1]->getAnyMember() == *Field; 4122 continue; 4123 } 4124 4125 if (!Field->getDeclName()) 4126 continue; 4127 4128 Builder.AddTypedTextChunk(Builder.getAllocator().CopyString( 4129 Field->getIdentifier()->getName())); 4130 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 4131 Builder.AddPlaceholderChunk("args"); 4132 Builder.AddChunk(CodeCompletionString::CK_RightParen); 4133 Results.AddResult(CodeCompletionResult(Builder.TakeString(), 4134 SawLastInitializer? CCP_NextInitializer 4135 : CCP_MemberDeclaration, 4136 CXCursor_MemberRef)); 4137 SawLastInitializer = false; 4138 } 4139 Results.ExitScope(); 4140 4141 HandleCodeCompleteResults(this, CodeCompleter, Results.getCompletionContext(), 4142 Results.data(), Results.size()); 4143 } 4144 4145 // Macro that expands to @Keyword or Keyword, depending on whether NeedAt is 4146 // true or false. 4147 #define OBJC_AT_KEYWORD_NAME(NeedAt,Keyword) NeedAt? "@" #Keyword : #Keyword 4148 static void AddObjCImplementationResults(const LangOptions &LangOpts, 4149 ResultBuilder &Results, 4150 bool NeedAt) { 4151 typedef CodeCompletionResult Result; 4152 // Since we have an implementation, we can end it. 4153 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt,end))); 4154 4155 CodeCompletionBuilder Builder(Results.getAllocator()); 4156 if (LangOpts.ObjC2) { 4157 // @dynamic 4158 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,dynamic)); 4159 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 4160 Builder.AddPlaceholderChunk("property"); 4161 Results.AddResult(Result(Builder.TakeString())); 4162 4163 // @synthesize 4164 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,synthesize)); 4165 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 4166 Builder.AddPlaceholderChunk("property"); 4167 Results.AddResult(Result(Builder.TakeString())); 4168 } 4169 } 4170 4171 static void AddObjCInterfaceResults(const LangOptions &LangOpts, 4172 ResultBuilder &Results, 4173 bool NeedAt) { 4174 typedef CodeCompletionResult Result; 4175 4176 // Since we have an interface or protocol, we can end it. 4177 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt,end))); 4178 4179 if (LangOpts.ObjC2) { 4180 // @property 4181 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt,property))); 4182 4183 // @required 4184 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt,required))); 4185 4186 // @optional 4187 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt,optional))); 4188 } 4189 } 4190 4191 static void AddObjCTopLevelResults(ResultBuilder &Results, bool NeedAt) { 4192 typedef CodeCompletionResult Result; 4193 CodeCompletionBuilder Builder(Results.getAllocator()); 4194 4195 // @class name ; 4196 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,class)); 4197 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 4198 Builder.AddPlaceholderChunk("name"); 4199 Results.AddResult(Result(Builder.TakeString())); 4200 4201 if (Results.includeCodePatterns()) { 4202 // @interface name 4203 // FIXME: Could introduce the whole pattern, including superclasses and 4204 // such. 4205 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,interface)); 4206 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 4207 Builder.AddPlaceholderChunk("class"); 4208 Results.AddResult(Result(Builder.TakeString())); 4209 4210 // @protocol name 4211 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,protocol)); 4212 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 4213 Builder.AddPlaceholderChunk("protocol"); 4214 Results.AddResult(Result(Builder.TakeString())); 4215 4216 // @implementation name 4217 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,implementation)); 4218 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 4219 Builder.AddPlaceholderChunk("class"); 4220 Results.AddResult(Result(Builder.TakeString())); 4221 } 4222 4223 // @compatibility_alias name 4224 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,compatibility_alias)); 4225 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 4226 Builder.AddPlaceholderChunk("alias"); 4227 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 4228 Builder.AddPlaceholderChunk("class"); 4229 Results.AddResult(Result(Builder.TakeString())); 4230 } 4231 4232 void Sema::CodeCompleteObjCAtDirective(Scope *S) { 4233 typedef CodeCompletionResult Result; 4234 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 4235 CodeCompletionContext::CCC_Other); 4236 Results.EnterNewScope(); 4237 if (isa<ObjCImplDecl>(CurContext)) 4238 AddObjCImplementationResults(getLangOptions(), Results, false); 4239 else if (CurContext->isObjCContainer()) 4240 AddObjCInterfaceResults(getLangOptions(), Results, false); 4241 else 4242 AddObjCTopLevelResults(Results, false); 4243 Results.ExitScope(); 4244 HandleCodeCompleteResults(this, CodeCompleter, 4245 CodeCompletionContext::CCC_Other, 4246 Results.data(),Results.size()); 4247 } 4248 4249 static void AddObjCExpressionResults(ResultBuilder &Results, bool NeedAt) { 4250 typedef CodeCompletionResult Result; 4251 CodeCompletionBuilder Builder(Results.getAllocator()); 4252 4253 // @encode ( type-name ) 4254 const char *EncodeType = "char[]"; 4255 if (Results.getSema().getLangOptions().CPlusPlus || 4256 Results.getSema().getLangOptions().ConstStrings) 4257 EncodeType = " const char[]"; 4258 Builder.AddResultTypeChunk(EncodeType); 4259 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,encode)); 4260 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 4261 Builder.AddPlaceholderChunk("type-name"); 4262 Builder.AddChunk(CodeCompletionString::CK_RightParen); 4263 Results.AddResult(Result(Builder.TakeString())); 4264 4265 // @protocol ( protocol-name ) 4266 Builder.AddResultTypeChunk("Protocol *"); 4267 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,protocol)); 4268 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 4269 Builder.AddPlaceholderChunk("protocol-name"); 4270 Builder.AddChunk(CodeCompletionString::CK_RightParen); 4271 Results.AddResult(Result(Builder.TakeString())); 4272 4273 // @selector ( selector ) 4274 Builder.AddResultTypeChunk("SEL"); 4275 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,selector)); 4276 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 4277 Builder.AddPlaceholderChunk("selector"); 4278 Builder.AddChunk(CodeCompletionString::CK_RightParen); 4279 Results.AddResult(Result(Builder.TakeString())); 4280 } 4281 4282 static void AddObjCStatementResults(ResultBuilder &Results, bool NeedAt) { 4283 typedef CodeCompletionResult Result; 4284 CodeCompletionBuilder Builder(Results.getAllocator()); 4285 4286 if (Results.includeCodePatterns()) { 4287 // @try { statements } @catch ( declaration ) { statements } @finally 4288 // { statements } 4289 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,try)); 4290 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 4291 Builder.AddPlaceholderChunk("statements"); 4292 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 4293 Builder.AddTextChunk("@catch"); 4294 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 4295 Builder.AddPlaceholderChunk("parameter"); 4296 Builder.AddChunk(CodeCompletionString::CK_RightParen); 4297 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 4298 Builder.AddPlaceholderChunk("statements"); 4299 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 4300 Builder.AddTextChunk("@finally"); 4301 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 4302 Builder.AddPlaceholderChunk("statements"); 4303 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 4304 Results.AddResult(Result(Builder.TakeString())); 4305 } 4306 4307 // @throw 4308 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,throw)); 4309 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 4310 Builder.AddPlaceholderChunk("expression"); 4311 Results.AddResult(Result(Builder.TakeString())); 4312 4313 if (Results.includeCodePatterns()) { 4314 // @synchronized ( expression ) { statements } 4315 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt,synchronized)); 4316 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 4317 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 4318 Builder.AddPlaceholderChunk("expression"); 4319 Builder.AddChunk(CodeCompletionString::CK_RightParen); 4320 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 4321 Builder.AddPlaceholderChunk("statements"); 4322 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 4323 Results.AddResult(Result(Builder.TakeString())); 4324 } 4325 } 4326 4327 static void AddObjCVisibilityResults(const LangOptions &LangOpts, 4328 ResultBuilder &Results, 4329 bool NeedAt) { 4330 typedef CodeCompletionResult Result; 4331 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt,private))); 4332 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt,protected))); 4333 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt,public))); 4334 if (LangOpts.ObjC2) 4335 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt,package))); 4336 } 4337 4338 void Sema::CodeCompleteObjCAtVisibility(Scope *S) { 4339 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 4340 CodeCompletionContext::CCC_Other); 4341 Results.EnterNewScope(); 4342 AddObjCVisibilityResults(getLangOptions(), Results, false); 4343 Results.ExitScope(); 4344 HandleCodeCompleteResults(this, CodeCompleter, 4345 CodeCompletionContext::CCC_Other, 4346 Results.data(),Results.size()); 4347 } 4348 4349 void Sema::CodeCompleteObjCAtStatement(Scope *S) { 4350 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 4351 CodeCompletionContext::CCC_Other); 4352 Results.EnterNewScope(); 4353 AddObjCStatementResults(Results, false); 4354 AddObjCExpressionResults(Results, false); 4355 Results.ExitScope(); 4356 HandleCodeCompleteResults(this, CodeCompleter, 4357 CodeCompletionContext::CCC_Other, 4358 Results.data(),Results.size()); 4359 } 4360 4361 void Sema::CodeCompleteObjCAtExpression(Scope *S) { 4362 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 4363 CodeCompletionContext::CCC_Other); 4364 Results.EnterNewScope(); 4365 AddObjCExpressionResults(Results, false); 4366 Results.ExitScope(); 4367 HandleCodeCompleteResults(this, CodeCompleter, 4368 CodeCompletionContext::CCC_Other, 4369 Results.data(),Results.size()); 4370 } 4371 4372 /// \brief Determine whether the addition of the given flag to an Objective-C 4373 /// property's attributes will cause a conflict. 4374 static bool ObjCPropertyFlagConflicts(unsigned Attributes, unsigned NewFlag) { 4375 // Check if we've already added this flag. 4376 if (Attributes & NewFlag) 4377 return true; 4378 4379 Attributes |= NewFlag; 4380 4381 // Check for collisions with "readonly". 4382 if ((Attributes & ObjCDeclSpec::DQ_PR_readonly) && 4383 (Attributes & (ObjCDeclSpec::DQ_PR_readwrite | 4384 ObjCDeclSpec::DQ_PR_assign | 4385 ObjCDeclSpec::DQ_PR_unsafe_unretained | 4386 ObjCDeclSpec::DQ_PR_copy | 4387 ObjCDeclSpec::DQ_PR_retain | 4388 ObjCDeclSpec::DQ_PR_strong))) 4389 return true; 4390 4391 // Check for more than one of { assign, copy, retain, strong }. 4392 unsigned AssignCopyRetMask = Attributes & (ObjCDeclSpec::DQ_PR_assign | 4393 ObjCDeclSpec::DQ_PR_unsafe_unretained | 4394 ObjCDeclSpec::DQ_PR_copy | 4395 ObjCDeclSpec::DQ_PR_retain| 4396 ObjCDeclSpec::DQ_PR_strong); 4397 if (AssignCopyRetMask && 4398 AssignCopyRetMask != ObjCDeclSpec::DQ_PR_assign && 4399 AssignCopyRetMask != ObjCDeclSpec::DQ_PR_unsafe_unretained && 4400 AssignCopyRetMask != ObjCDeclSpec::DQ_PR_copy && 4401 AssignCopyRetMask != ObjCDeclSpec::DQ_PR_retain && 4402 AssignCopyRetMask != ObjCDeclSpec::DQ_PR_strong) 4403 return true; 4404 4405 return false; 4406 } 4407 4408 void Sema::CodeCompleteObjCPropertyFlags(Scope *S, ObjCDeclSpec &ODS) { 4409 if (!CodeCompleter) 4410 return; 4411 4412 unsigned Attributes = ODS.getPropertyAttributes(); 4413 4414 typedef CodeCompletionResult Result; 4415 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 4416 CodeCompletionContext::CCC_Other); 4417 Results.EnterNewScope(); 4418 if (!ObjCPropertyFlagConflicts(Attributes, ObjCDeclSpec::DQ_PR_readonly)) 4419 Results.AddResult(CodeCompletionResult("readonly")); 4420 if (!ObjCPropertyFlagConflicts(Attributes, ObjCDeclSpec::DQ_PR_assign)) 4421 Results.AddResult(CodeCompletionResult("assign")); 4422 if (!ObjCPropertyFlagConflicts(Attributes, 4423 ObjCDeclSpec::DQ_PR_unsafe_unretained)) 4424 Results.AddResult(CodeCompletionResult("unsafe_unretained")); 4425 if (!ObjCPropertyFlagConflicts(Attributes, ObjCDeclSpec::DQ_PR_readwrite)) 4426 Results.AddResult(CodeCompletionResult("readwrite")); 4427 if (!ObjCPropertyFlagConflicts(Attributes, ObjCDeclSpec::DQ_PR_retain)) 4428 Results.AddResult(CodeCompletionResult("retain")); 4429 if (!ObjCPropertyFlagConflicts(Attributes, ObjCDeclSpec::DQ_PR_strong)) 4430 Results.AddResult(CodeCompletionResult("strong")); 4431 if (!ObjCPropertyFlagConflicts(Attributes, ObjCDeclSpec::DQ_PR_copy)) 4432 Results.AddResult(CodeCompletionResult("copy")); 4433 if (!ObjCPropertyFlagConflicts(Attributes, ObjCDeclSpec::DQ_PR_nonatomic)) 4434 Results.AddResult(CodeCompletionResult("nonatomic")); 4435 if (!ObjCPropertyFlagConflicts(Attributes, ObjCDeclSpec::DQ_PR_atomic)) 4436 Results.AddResult(CodeCompletionResult("atomic")); 4437 if (!ObjCPropertyFlagConflicts(Attributes, ObjCDeclSpec::DQ_PR_setter)) { 4438 CodeCompletionBuilder Setter(Results.getAllocator()); 4439 Setter.AddTypedTextChunk("setter"); 4440 Setter.AddTextChunk(" = "); 4441 Setter.AddPlaceholderChunk("method"); 4442 Results.AddResult(CodeCompletionResult(Setter.TakeString())); 4443 } 4444 if (!ObjCPropertyFlagConflicts(Attributes, ObjCDeclSpec::DQ_PR_getter)) { 4445 CodeCompletionBuilder Getter(Results.getAllocator()); 4446 Getter.AddTypedTextChunk("getter"); 4447 Getter.AddTextChunk(" = "); 4448 Getter.AddPlaceholderChunk("method"); 4449 Results.AddResult(CodeCompletionResult(Getter.TakeString())); 4450 } 4451 Results.ExitScope(); 4452 HandleCodeCompleteResults(this, CodeCompleter, 4453 CodeCompletionContext::CCC_Other, 4454 Results.data(),Results.size()); 4455 } 4456 4457 /// \brief Descripts the kind of Objective-C method that we want to find 4458 /// via code completion. 4459 enum ObjCMethodKind { 4460 MK_Any, //< Any kind of method, provided it means other specified criteria. 4461 MK_ZeroArgSelector, //< Zero-argument (unary) selector. 4462 MK_OneArgSelector //< One-argument selector. 4463 }; 4464 4465 static bool isAcceptableObjCSelector(Selector Sel, 4466 ObjCMethodKind WantKind, 4467 IdentifierInfo **SelIdents, 4468 unsigned NumSelIdents, 4469 bool AllowSameLength = true) { 4470 if (NumSelIdents > Sel.getNumArgs()) 4471 return false; 4472 4473 switch (WantKind) { 4474 case MK_Any: break; 4475 case MK_ZeroArgSelector: return Sel.isUnarySelector(); 4476 case MK_OneArgSelector: return Sel.getNumArgs() == 1; 4477 } 4478 4479 if (!AllowSameLength && NumSelIdents && NumSelIdents == Sel.getNumArgs()) 4480 return false; 4481 4482 for (unsigned I = 0; I != NumSelIdents; ++I) 4483 if (SelIdents[I] != Sel.getIdentifierInfoForSlot(I)) 4484 return false; 4485 4486 return true; 4487 } 4488 4489 static bool isAcceptableObjCMethod(ObjCMethodDecl *Method, 4490 ObjCMethodKind WantKind, 4491 IdentifierInfo **SelIdents, 4492 unsigned NumSelIdents, 4493 bool AllowSameLength = true) { 4494 return isAcceptableObjCSelector(Method->getSelector(), WantKind, SelIdents, 4495 NumSelIdents, AllowSameLength); 4496 } 4497 4498 namespace { 4499 /// \brief A set of selectors, which is used to avoid introducing multiple 4500 /// completions with the same selector into the result set. 4501 typedef llvm::SmallPtrSet<Selector, 16> VisitedSelectorSet; 4502 } 4503 4504 /// \brief Add all of the Objective-C methods in the given Objective-C 4505 /// container to the set of results. 4506 /// 4507 /// The container will be a class, protocol, category, or implementation of 4508 /// any of the above. This mether will recurse to include methods from 4509 /// the superclasses of classes along with their categories, protocols, and 4510 /// implementations. 4511 /// 4512 /// \param Container the container in which we'll look to find methods. 4513 /// 4514 /// \param WantInstance whether to add instance methods (only); if false, this 4515 /// routine will add factory methods (only). 4516 /// 4517 /// \param CurContext the context in which we're performing the lookup that 4518 /// finds methods. 4519 /// 4520 /// \param AllowSameLength Whether we allow a method to be added to the list 4521 /// when it has the same number of parameters as we have selector identifiers. 4522 /// 4523 /// \param Results the structure into which we'll add results. 4524 static void AddObjCMethods(ObjCContainerDecl *Container, 4525 bool WantInstanceMethods, 4526 ObjCMethodKind WantKind, 4527 IdentifierInfo **SelIdents, 4528 unsigned NumSelIdents, 4529 DeclContext *CurContext, 4530 VisitedSelectorSet &Selectors, 4531 bool AllowSameLength, 4532 ResultBuilder &Results, 4533 bool InOriginalClass = true) { 4534 typedef CodeCompletionResult Result; 4535 for (ObjCContainerDecl::method_iterator M = Container->meth_begin(), 4536 MEnd = Container->meth_end(); 4537 M != MEnd; ++M) { 4538 if ((*M)->isInstanceMethod() == WantInstanceMethods) { 4539 // Check whether the selector identifiers we've been given are a 4540 // subset of the identifiers for this particular method. 4541 if (!isAcceptableObjCMethod(*M, WantKind, SelIdents, NumSelIdents, 4542 AllowSameLength)) 4543 continue; 4544 4545 if (!Selectors.insert((*M)->getSelector())) 4546 continue; 4547 4548 Result R = Result(*M, 0); 4549 R.StartParameter = NumSelIdents; 4550 R.AllParametersAreInformative = (WantKind != MK_Any); 4551 if (!InOriginalClass) 4552 R.Priority += CCD_InBaseClass; 4553 Results.MaybeAddResult(R, CurContext); 4554 } 4555 } 4556 4557 // Visit the protocols of protocols. 4558 if (ObjCProtocolDecl *Protocol = dyn_cast<ObjCProtocolDecl>(Container)) { 4559 if (Protocol->hasDefinition()) { 4560 const ObjCList<ObjCProtocolDecl> &Protocols 4561 = Protocol->getReferencedProtocols(); 4562 for (ObjCList<ObjCProtocolDecl>::iterator I = Protocols.begin(), 4563 E = Protocols.end(); 4564 I != E; ++I) 4565 AddObjCMethods(*I, WantInstanceMethods, WantKind, SelIdents, 4566 NumSelIdents, CurContext, Selectors, AllowSameLength, 4567 Results, false); 4568 } 4569 } 4570 4571 ObjCInterfaceDecl *IFace = dyn_cast<ObjCInterfaceDecl>(Container); 4572 if (!IFace || !IFace->hasDefinition()) 4573 return; 4574 4575 // Add methods in protocols. 4576 const ObjCList<ObjCProtocolDecl> &Protocols= IFace->getReferencedProtocols(); 4577 for (ObjCList<ObjCProtocolDecl>::iterator I = Protocols.begin(), 4578 E = Protocols.end(); 4579 I != E; ++I) 4580 AddObjCMethods(*I, WantInstanceMethods, WantKind, SelIdents, NumSelIdents, 4581 CurContext, Selectors, AllowSameLength, Results, false); 4582 4583 // Add methods in categories. 4584 for (ObjCCategoryDecl *CatDecl = IFace->getCategoryList(); CatDecl; 4585 CatDecl = CatDecl->getNextClassCategory()) { 4586 AddObjCMethods(CatDecl, WantInstanceMethods, WantKind, SelIdents, 4587 NumSelIdents, CurContext, Selectors, AllowSameLength, 4588 Results, InOriginalClass); 4589 4590 // Add a categories protocol methods. 4591 const ObjCList<ObjCProtocolDecl> &Protocols 4592 = CatDecl->getReferencedProtocols(); 4593 for (ObjCList<ObjCProtocolDecl>::iterator I = Protocols.begin(), 4594 E = Protocols.end(); 4595 I != E; ++I) 4596 AddObjCMethods(*I, WantInstanceMethods, WantKind, SelIdents, 4597 NumSelIdents, CurContext, Selectors, AllowSameLength, 4598 Results, false); 4599 4600 // Add methods in category implementations. 4601 if (ObjCCategoryImplDecl *Impl = CatDecl->getImplementation()) 4602 AddObjCMethods(Impl, WantInstanceMethods, WantKind, SelIdents, 4603 NumSelIdents, CurContext, Selectors, AllowSameLength, 4604 Results, InOriginalClass); 4605 } 4606 4607 // Add methods in superclass. 4608 if (IFace->getSuperClass()) 4609 AddObjCMethods(IFace->getSuperClass(), WantInstanceMethods, WantKind, 4610 SelIdents, NumSelIdents, CurContext, Selectors, 4611 AllowSameLength, Results, false); 4612 4613 // Add methods in our implementation, if any. 4614 if (ObjCImplementationDecl *Impl = IFace->getImplementation()) 4615 AddObjCMethods(Impl, WantInstanceMethods, WantKind, SelIdents, 4616 NumSelIdents, CurContext, Selectors, AllowSameLength, 4617 Results, InOriginalClass); 4618 } 4619 4620 4621 void Sema::CodeCompleteObjCPropertyGetter(Scope *S) { 4622 typedef CodeCompletionResult Result; 4623 4624 // Try to find the interface where getters might live. 4625 ObjCInterfaceDecl *Class = dyn_cast_or_null<ObjCInterfaceDecl>(CurContext); 4626 if (!Class) { 4627 if (ObjCCategoryDecl *Category 4628 = dyn_cast_or_null<ObjCCategoryDecl>(CurContext)) 4629 Class = Category->getClassInterface(); 4630 4631 if (!Class) 4632 return; 4633 } 4634 4635 // Find all of the potential getters. 4636 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 4637 CodeCompletionContext::CCC_Other); 4638 Results.EnterNewScope(); 4639 4640 VisitedSelectorSet Selectors; 4641 AddObjCMethods(Class, true, MK_ZeroArgSelector, 0, 0, CurContext, Selectors, 4642 /*AllowSameLength=*/true, Results); 4643 Results.ExitScope(); 4644 HandleCodeCompleteResults(this, CodeCompleter, 4645 CodeCompletionContext::CCC_Other, 4646 Results.data(),Results.size()); 4647 } 4648 4649 void Sema::CodeCompleteObjCPropertySetter(Scope *S) { 4650 typedef CodeCompletionResult Result; 4651 4652 // Try to find the interface where setters might live. 4653 ObjCInterfaceDecl *Class 4654 = dyn_cast_or_null<ObjCInterfaceDecl>(CurContext); 4655 if (!Class) { 4656 if (ObjCCategoryDecl *Category 4657 = dyn_cast_or_null<ObjCCategoryDecl>(CurContext)) 4658 Class = Category->getClassInterface(); 4659 4660 if (!Class) 4661 return; 4662 } 4663 4664 // Find all of the potential getters. 4665 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 4666 CodeCompletionContext::CCC_Other); 4667 Results.EnterNewScope(); 4668 4669 VisitedSelectorSet Selectors; 4670 AddObjCMethods(Class, true, MK_OneArgSelector, 0, 0, CurContext, 4671 Selectors, /*AllowSameLength=*/true, Results); 4672 4673 Results.ExitScope(); 4674 HandleCodeCompleteResults(this, CodeCompleter, 4675 CodeCompletionContext::CCC_Other, 4676 Results.data(),Results.size()); 4677 } 4678 4679 void Sema::CodeCompleteObjCPassingType(Scope *S, ObjCDeclSpec &DS, 4680 bool IsParameter) { 4681 typedef CodeCompletionResult Result; 4682 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 4683 CodeCompletionContext::CCC_Type); 4684 Results.EnterNewScope(); 4685 4686 // Add context-sensitive, Objective-C parameter-passing keywords. 4687 bool AddedInOut = false; 4688 if ((DS.getObjCDeclQualifier() & 4689 (ObjCDeclSpec::DQ_In | ObjCDeclSpec::DQ_Inout)) == 0) { 4690 Results.AddResult("in"); 4691 Results.AddResult("inout"); 4692 AddedInOut = true; 4693 } 4694 if ((DS.getObjCDeclQualifier() & 4695 (ObjCDeclSpec::DQ_Out | ObjCDeclSpec::DQ_Inout)) == 0) { 4696 Results.AddResult("out"); 4697 if (!AddedInOut) 4698 Results.AddResult("inout"); 4699 } 4700 if ((DS.getObjCDeclQualifier() & 4701 (ObjCDeclSpec::DQ_Bycopy | ObjCDeclSpec::DQ_Byref | 4702 ObjCDeclSpec::DQ_Oneway)) == 0) { 4703 Results.AddResult("bycopy"); 4704 Results.AddResult("byref"); 4705 Results.AddResult("oneway"); 4706 } 4707 4708 // If we're completing the return type of an Objective-C method and the 4709 // identifier IBAction refers to a macro, provide a completion item for 4710 // an action, e.g., 4711 // IBAction)<#selector#>:(id)sender 4712 if (DS.getObjCDeclQualifier() == 0 && !IsParameter && 4713 Context.Idents.get("IBAction").hasMacroDefinition()) { 4714 typedef CodeCompletionString::Chunk Chunk; 4715 CodeCompletionBuilder Builder(Results.getAllocator(), CCP_CodePattern, 4716 CXAvailability_Available); 4717 Builder.AddTypedTextChunk("IBAction"); 4718 Builder.AddChunk(Chunk(CodeCompletionString::CK_RightParen)); 4719 Builder.AddPlaceholderChunk("selector"); 4720 Builder.AddChunk(Chunk(CodeCompletionString::CK_Colon)); 4721 Builder.AddChunk(Chunk(CodeCompletionString::CK_LeftParen)); 4722 Builder.AddTextChunk("id"); 4723 Builder.AddChunk(Chunk(CodeCompletionString::CK_RightParen)); 4724 Builder.AddTextChunk("sender"); 4725 Results.AddResult(CodeCompletionResult(Builder.TakeString())); 4726 } 4727 4728 // Add various builtin type names and specifiers. 4729 AddOrdinaryNameResults(PCC_Type, S, *this, Results); 4730 Results.ExitScope(); 4731 4732 // Add the various type names 4733 Results.setFilter(&ResultBuilder::IsOrdinaryNonValueName); 4734 CodeCompletionDeclConsumer Consumer(Results, CurContext); 4735 LookupVisibleDecls(S, LookupOrdinaryName, Consumer, 4736 CodeCompleter->includeGlobals()); 4737 4738 if (CodeCompleter->includeMacros()) 4739 AddMacroResults(PP, Results); 4740 4741 HandleCodeCompleteResults(this, CodeCompleter, 4742 CodeCompletionContext::CCC_Type, 4743 Results.data(), Results.size()); 4744 } 4745 4746 /// \brief When we have an expression with type "id", we may assume 4747 /// that it has some more-specific class type based on knowledge of 4748 /// common uses of Objective-C. This routine returns that class type, 4749 /// or NULL if no better result could be determined. 4750 static ObjCInterfaceDecl *GetAssumedMessageSendExprType(Expr *E) { 4751 ObjCMessageExpr *Msg = dyn_cast_or_null<ObjCMessageExpr>(E); 4752 if (!Msg) 4753 return 0; 4754 4755 Selector Sel = Msg->getSelector(); 4756 if (Sel.isNull()) 4757 return 0; 4758 4759 IdentifierInfo *Id = Sel.getIdentifierInfoForSlot(0); 4760 if (!Id) 4761 return 0; 4762 4763 ObjCMethodDecl *Method = Msg->getMethodDecl(); 4764 if (!Method) 4765 return 0; 4766 4767 // Determine the class that we're sending the message to. 4768 ObjCInterfaceDecl *IFace = 0; 4769 switch (Msg->getReceiverKind()) { 4770 case ObjCMessageExpr::Class: 4771 if (const ObjCObjectType *ObjType 4772 = Msg->getClassReceiver()->getAs<ObjCObjectType>()) 4773 IFace = ObjType->getInterface(); 4774 break; 4775 4776 case ObjCMessageExpr::Instance: { 4777 QualType T = Msg->getInstanceReceiver()->getType(); 4778 if (const ObjCObjectPointerType *Ptr = T->getAs<ObjCObjectPointerType>()) 4779 IFace = Ptr->getInterfaceDecl(); 4780 break; 4781 } 4782 4783 case ObjCMessageExpr::SuperInstance: 4784 case ObjCMessageExpr::SuperClass: 4785 break; 4786 } 4787 4788 if (!IFace) 4789 return 0; 4790 4791 ObjCInterfaceDecl *Super = IFace->getSuperClass(); 4792 if (Method->isInstanceMethod()) 4793 return llvm::StringSwitch<ObjCInterfaceDecl *>(Id->getName()) 4794 .Case("retain", IFace) 4795 .Case("strong", IFace) 4796 .Case("autorelease", IFace) 4797 .Case("copy", IFace) 4798 .Case("copyWithZone", IFace) 4799 .Case("mutableCopy", IFace) 4800 .Case("mutableCopyWithZone", IFace) 4801 .Case("awakeFromCoder", IFace) 4802 .Case("replacementObjectFromCoder", IFace) 4803 .Case("class", IFace) 4804 .Case("classForCoder", IFace) 4805 .Case("superclass", Super) 4806 .Default(0); 4807 4808 return llvm::StringSwitch<ObjCInterfaceDecl *>(Id->getName()) 4809 .Case("new", IFace) 4810 .Case("alloc", IFace) 4811 .Case("allocWithZone", IFace) 4812 .Case("class", IFace) 4813 .Case("superclass", Super) 4814 .Default(0); 4815 } 4816 4817 // Add a special completion for a message send to "super", which fills in the 4818 // most likely case of forwarding all of our arguments to the superclass 4819 // function. 4820 /// 4821 /// \param S The semantic analysis object. 4822 /// 4823 /// \param S NeedSuperKeyword Whether we need to prefix this completion with 4824 /// the "super" keyword. Otherwise, we just need to provide the arguments. 4825 /// 4826 /// \param SelIdents The identifiers in the selector that have already been 4827 /// provided as arguments for a send to "super". 4828 /// 4829 /// \param NumSelIdents The number of identifiers in \p SelIdents. 4830 /// 4831 /// \param Results The set of results to augment. 4832 /// 4833 /// \returns the Objective-C method declaration that would be invoked by 4834 /// this "super" completion. If NULL, no completion was added. 4835 static ObjCMethodDecl *AddSuperSendCompletion(Sema &S, bool NeedSuperKeyword, 4836 IdentifierInfo **SelIdents, 4837 unsigned NumSelIdents, 4838 ResultBuilder &Results) { 4839 ObjCMethodDecl *CurMethod = S.getCurMethodDecl(); 4840 if (!CurMethod) 4841 return 0; 4842 4843 ObjCInterfaceDecl *Class = CurMethod->getClassInterface(); 4844 if (!Class) 4845 return 0; 4846 4847 // Try to find a superclass method with the same selector. 4848 ObjCMethodDecl *SuperMethod = 0; 4849 while ((Class = Class->getSuperClass()) && !SuperMethod) { 4850 // Check in the class 4851 SuperMethod = Class->getMethod(CurMethod->getSelector(), 4852 CurMethod->isInstanceMethod()); 4853 4854 // Check in categories or class extensions. 4855 if (!SuperMethod) { 4856 for (ObjCCategoryDecl *Category = Class->getCategoryList(); Category; 4857 Category = Category->getNextClassCategory()) 4858 if ((SuperMethod = Category->getMethod(CurMethod->getSelector(), 4859 CurMethod->isInstanceMethod()))) 4860 break; 4861 } 4862 } 4863 4864 if (!SuperMethod) 4865 return 0; 4866 4867 // Check whether the superclass method has the same signature. 4868 if (CurMethod->param_size() != SuperMethod->param_size() || 4869 CurMethod->isVariadic() != SuperMethod->isVariadic()) 4870 return 0; 4871 4872 for (ObjCMethodDecl::param_iterator CurP = CurMethod->param_begin(), 4873 CurPEnd = CurMethod->param_end(), 4874 SuperP = SuperMethod->param_begin(); 4875 CurP != CurPEnd; ++CurP, ++SuperP) { 4876 // Make sure the parameter types are compatible. 4877 if (!S.Context.hasSameUnqualifiedType((*CurP)->getType(), 4878 (*SuperP)->getType())) 4879 return 0; 4880 4881 // Make sure we have a parameter name to forward! 4882 if (!(*CurP)->getIdentifier()) 4883 return 0; 4884 } 4885 4886 // We have a superclass method. Now, form the send-to-super completion. 4887 CodeCompletionBuilder Builder(Results.getAllocator()); 4888 4889 // Give this completion a return type. 4890 AddResultTypeChunk(S.Context, getCompletionPrintingPolicy(S), SuperMethod, 4891 Builder); 4892 4893 // If we need the "super" keyword, add it (plus some spacing). 4894 if (NeedSuperKeyword) { 4895 Builder.AddTypedTextChunk("super"); 4896 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 4897 } 4898 4899 Selector Sel = CurMethod->getSelector(); 4900 if (Sel.isUnarySelector()) { 4901 if (NeedSuperKeyword) 4902 Builder.AddTextChunk(Builder.getAllocator().CopyString( 4903 Sel.getNameForSlot(0))); 4904 else 4905 Builder.AddTypedTextChunk(Builder.getAllocator().CopyString( 4906 Sel.getNameForSlot(0))); 4907 } else { 4908 ObjCMethodDecl::param_iterator CurP = CurMethod->param_begin(); 4909 for (unsigned I = 0, N = Sel.getNumArgs(); I != N; ++I, ++CurP) { 4910 if (I > NumSelIdents) 4911 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 4912 4913 if (I < NumSelIdents) 4914 Builder.AddInformativeChunk( 4915 Builder.getAllocator().CopyString( 4916 Sel.getNameForSlot(I) + ":")); 4917 else if (NeedSuperKeyword || I > NumSelIdents) { 4918 Builder.AddTextChunk( 4919 Builder.getAllocator().CopyString( 4920 Sel.getNameForSlot(I) + ":")); 4921 Builder.AddPlaceholderChunk(Builder.getAllocator().CopyString( 4922 (*CurP)->getIdentifier()->getName())); 4923 } else { 4924 Builder.AddTypedTextChunk( 4925 Builder.getAllocator().CopyString( 4926 Sel.getNameForSlot(I) + ":")); 4927 Builder.AddPlaceholderChunk(Builder.getAllocator().CopyString( 4928 (*CurP)->getIdentifier()->getName())); 4929 } 4930 } 4931 } 4932 4933 Results.AddResult(CodeCompletionResult(Builder.TakeString(), CCP_SuperCompletion, 4934 SuperMethod->isInstanceMethod() 4935 ? CXCursor_ObjCInstanceMethodDecl 4936 : CXCursor_ObjCClassMethodDecl)); 4937 return SuperMethod; 4938 } 4939 4940 void Sema::CodeCompleteObjCMessageReceiver(Scope *S) { 4941 typedef CodeCompletionResult Result; 4942 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 4943 CodeCompletionContext::CCC_ObjCMessageReceiver, 4944 &ResultBuilder::IsObjCMessageReceiver); 4945 4946 CodeCompletionDeclConsumer Consumer(Results, CurContext); 4947 Results.EnterNewScope(); 4948 LookupVisibleDecls(S, LookupOrdinaryName, Consumer, 4949 CodeCompleter->includeGlobals()); 4950 4951 // If we are in an Objective-C method inside a class that has a superclass, 4952 // add "super" as an option. 4953 if (ObjCMethodDecl *Method = getCurMethodDecl()) 4954 if (ObjCInterfaceDecl *Iface = Method->getClassInterface()) 4955 if (Iface->getSuperClass()) { 4956 Results.AddResult(Result("super")); 4957 4958 AddSuperSendCompletion(*this, /*NeedSuperKeyword=*/true, 0, 0, Results); 4959 } 4960 4961 Results.ExitScope(); 4962 4963 if (CodeCompleter->includeMacros()) 4964 AddMacroResults(PP, Results); 4965 HandleCodeCompleteResults(this, CodeCompleter, Results.getCompletionContext(), 4966 Results.data(), Results.size()); 4967 4968 } 4969 4970 void Sema::CodeCompleteObjCSuperMessage(Scope *S, SourceLocation SuperLoc, 4971 IdentifierInfo **SelIdents, 4972 unsigned NumSelIdents, 4973 bool AtArgumentExpression) { 4974 ObjCInterfaceDecl *CDecl = 0; 4975 if (ObjCMethodDecl *CurMethod = getCurMethodDecl()) { 4976 // Figure out which interface we're in. 4977 CDecl = CurMethod->getClassInterface(); 4978 if (!CDecl) 4979 return; 4980 4981 // Find the superclass of this class. 4982 CDecl = CDecl->getSuperClass(); 4983 if (!CDecl) 4984 return; 4985 4986 if (CurMethod->isInstanceMethod()) { 4987 // We are inside an instance method, which means that the message 4988 // send [super ...] is actually calling an instance method on the 4989 // current object. 4990 return CodeCompleteObjCInstanceMessage(S, 0, 4991 SelIdents, NumSelIdents, 4992 AtArgumentExpression, 4993 CDecl); 4994 } 4995 4996 // Fall through to send to the superclass in CDecl. 4997 } else { 4998 // "super" may be the name of a type or variable. Figure out which 4999 // it is. 5000 IdentifierInfo *Super = &Context.Idents.get("super"); 5001 NamedDecl *ND = LookupSingleName(S, Super, SuperLoc, 5002 LookupOrdinaryName); 5003 if ((CDecl = dyn_cast_or_null<ObjCInterfaceDecl>(ND))) { 5004 // "super" names an interface. Use it. 5005 } else if (TypeDecl *TD = dyn_cast_or_null<TypeDecl>(ND)) { 5006 if (const ObjCObjectType *Iface 5007 = Context.getTypeDeclType(TD)->getAs<ObjCObjectType>()) 5008 CDecl = Iface->getInterface(); 5009 } else if (ND && isa<UnresolvedUsingTypenameDecl>(ND)) { 5010 // "super" names an unresolved type; we can't be more specific. 5011 } else { 5012 // Assume that "super" names some kind of value and parse that way. 5013 CXXScopeSpec SS; 5014 UnqualifiedId id; 5015 id.setIdentifier(Super, SuperLoc); 5016 ExprResult SuperExpr = ActOnIdExpression(S, SS, id, false, false); 5017 return CodeCompleteObjCInstanceMessage(S, (Expr *)SuperExpr.get(), 5018 SelIdents, NumSelIdents, 5019 AtArgumentExpression); 5020 } 5021 5022 // Fall through 5023 } 5024 5025 ParsedType Receiver; 5026 if (CDecl) 5027 Receiver = ParsedType::make(Context.getObjCInterfaceType(CDecl)); 5028 return CodeCompleteObjCClassMessage(S, Receiver, SelIdents, 5029 NumSelIdents, AtArgumentExpression, 5030 /*IsSuper=*/true); 5031 } 5032 5033 /// \brief Given a set of code-completion results for the argument of a message 5034 /// send, determine the preferred type (if any) for that argument expression. 5035 static QualType getPreferredArgumentTypeForMessageSend(ResultBuilder &Results, 5036 unsigned NumSelIdents) { 5037 typedef CodeCompletionResult Result; 5038 ASTContext &Context = Results.getSema().Context; 5039 5040 QualType PreferredType; 5041 unsigned BestPriority = CCP_Unlikely * 2; 5042 Result *ResultsData = Results.data(); 5043 for (unsigned I = 0, N = Results.size(); I != N; ++I) { 5044 Result &R = ResultsData[I]; 5045 if (R.Kind == Result::RK_Declaration && 5046 isa<ObjCMethodDecl>(R.Declaration)) { 5047 if (R.Priority <= BestPriority) { 5048 ObjCMethodDecl *Method = cast<ObjCMethodDecl>(R.Declaration); 5049 if (NumSelIdents <= Method->param_size()) { 5050 QualType MyPreferredType = Method->param_begin()[NumSelIdents - 1] 5051 ->getType(); 5052 if (R.Priority < BestPriority || PreferredType.isNull()) { 5053 BestPriority = R.Priority; 5054 PreferredType = MyPreferredType; 5055 } else if (!Context.hasSameUnqualifiedType(PreferredType, 5056 MyPreferredType)) { 5057 PreferredType = QualType(); 5058 } 5059 } 5060 } 5061 } 5062 } 5063 5064 return PreferredType; 5065 } 5066 5067 static void AddClassMessageCompletions(Sema &SemaRef, Scope *S, 5068 ParsedType Receiver, 5069 IdentifierInfo **SelIdents, 5070 unsigned NumSelIdents, 5071 bool AtArgumentExpression, 5072 bool IsSuper, 5073 ResultBuilder &Results) { 5074 typedef CodeCompletionResult Result; 5075 ObjCInterfaceDecl *CDecl = 0; 5076 5077 // If the given name refers to an interface type, retrieve the 5078 // corresponding declaration. 5079 if (Receiver) { 5080 QualType T = SemaRef.GetTypeFromParser(Receiver, 0); 5081 if (!T.isNull()) 5082 if (const ObjCObjectType *Interface = T->getAs<ObjCObjectType>()) 5083 CDecl = Interface->getInterface(); 5084 } 5085 5086 // Add all of the factory methods in this Objective-C class, its protocols, 5087 // superclasses, categories, implementation, etc. 5088 Results.EnterNewScope(); 5089 5090 // If this is a send-to-super, try to add the special "super" send 5091 // completion. 5092 if (IsSuper) { 5093 if (ObjCMethodDecl *SuperMethod 5094 = AddSuperSendCompletion(SemaRef, false, SelIdents, NumSelIdents, 5095 Results)) 5096 Results.Ignore(SuperMethod); 5097 } 5098 5099 // If we're inside an Objective-C method definition, prefer its selector to 5100 // others. 5101 if (ObjCMethodDecl *CurMethod = SemaRef.getCurMethodDecl()) 5102 Results.setPreferredSelector(CurMethod->getSelector()); 5103 5104 VisitedSelectorSet Selectors; 5105 if (CDecl) 5106 AddObjCMethods(CDecl, false, MK_Any, SelIdents, NumSelIdents, 5107 SemaRef.CurContext, Selectors, AtArgumentExpression, 5108 Results); 5109 else { 5110 // We're messaging "id" as a type; provide all class/factory methods. 5111 5112 // If we have an external source, load the entire class method 5113 // pool from the AST file. 5114 if (SemaRef.ExternalSource) { 5115 for (uint32_t I = 0, 5116 N = SemaRef.ExternalSource->GetNumExternalSelectors(); 5117 I != N; ++I) { 5118 Selector Sel = SemaRef.ExternalSource->GetExternalSelector(I); 5119 if (Sel.isNull() || SemaRef.MethodPool.count(Sel)) 5120 continue; 5121 5122 SemaRef.ReadMethodPool(Sel); 5123 } 5124 } 5125 5126 for (Sema::GlobalMethodPool::iterator M = SemaRef.MethodPool.begin(), 5127 MEnd = SemaRef.MethodPool.end(); 5128 M != MEnd; ++M) { 5129 for (ObjCMethodList *MethList = &M->second.second; 5130 MethList && MethList->Method; 5131 MethList = MethList->Next) { 5132 if (!isAcceptableObjCMethod(MethList->Method, MK_Any, SelIdents, 5133 NumSelIdents)) 5134 continue; 5135 5136 Result R(MethList->Method, 0); 5137 R.StartParameter = NumSelIdents; 5138 R.AllParametersAreInformative = false; 5139 Results.MaybeAddResult(R, SemaRef.CurContext); 5140 } 5141 } 5142 } 5143 5144 Results.ExitScope(); 5145 } 5146 5147 void Sema::CodeCompleteObjCClassMessage(Scope *S, ParsedType Receiver, 5148 IdentifierInfo **SelIdents, 5149 unsigned NumSelIdents, 5150 bool AtArgumentExpression, 5151 bool IsSuper) { 5152 5153 QualType T = this->GetTypeFromParser(Receiver); 5154 5155 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 5156 CodeCompletionContext(CodeCompletionContext::CCC_ObjCClassMessage, 5157 T, SelIdents, NumSelIdents)); 5158 5159 AddClassMessageCompletions(*this, S, Receiver, SelIdents, NumSelIdents, 5160 AtArgumentExpression, IsSuper, Results); 5161 5162 // If we're actually at the argument expression (rather than prior to the 5163 // selector), we're actually performing code completion for an expression. 5164 // Determine whether we have a single, best method. If so, we can 5165 // code-complete the expression using the corresponding parameter type as 5166 // our preferred type, improving completion results. 5167 if (AtArgumentExpression) { 5168 QualType PreferredType = getPreferredArgumentTypeForMessageSend(Results, 5169 NumSelIdents); 5170 if (PreferredType.isNull()) 5171 CodeCompleteOrdinaryName(S, PCC_Expression); 5172 else 5173 CodeCompleteExpression(S, PreferredType); 5174 return; 5175 } 5176 5177 HandleCodeCompleteResults(this, CodeCompleter, 5178 Results.getCompletionContext(), 5179 Results.data(), Results.size()); 5180 } 5181 5182 void Sema::CodeCompleteObjCInstanceMessage(Scope *S, Expr *Receiver, 5183 IdentifierInfo **SelIdents, 5184 unsigned NumSelIdents, 5185 bool AtArgumentExpression, 5186 ObjCInterfaceDecl *Super) { 5187 typedef CodeCompletionResult Result; 5188 5189 Expr *RecExpr = static_cast<Expr *>(Receiver); 5190 5191 // If necessary, apply function/array conversion to the receiver. 5192 // C99 6.7.5.3p[7,8]. 5193 if (RecExpr) { 5194 ExprResult Conv = DefaultFunctionArrayLvalueConversion(RecExpr); 5195 if (Conv.isInvalid()) // conversion failed. bail. 5196 return; 5197 RecExpr = Conv.take(); 5198 } 5199 QualType ReceiverType = RecExpr? RecExpr->getType() 5200 : Super? Context.getObjCObjectPointerType( 5201 Context.getObjCInterfaceType(Super)) 5202 : Context.getObjCIdType(); 5203 5204 // If we're messaging an expression with type "id" or "Class", check 5205 // whether we know something special about the receiver that allows 5206 // us to assume a more-specific receiver type. 5207 if (ReceiverType->isObjCIdType() || ReceiverType->isObjCClassType()) 5208 if (ObjCInterfaceDecl *IFace = GetAssumedMessageSendExprType(RecExpr)) { 5209 if (ReceiverType->isObjCClassType()) 5210 return CodeCompleteObjCClassMessage(S, 5211 ParsedType::make(Context.getObjCInterfaceType(IFace)), 5212 SelIdents, NumSelIdents, 5213 AtArgumentExpression, Super); 5214 5215 ReceiverType = Context.getObjCObjectPointerType( 5216 Context.getObjCInterfaceType(IFace)); 5217 } 5218 5219 // Build the set of methods we can see. 5220 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 5221 CodeCompletionContext(CodeCompletionContext::CCC_ObjCInstanceMessage, 5222 ReceiverType, SelIdents, NumSelIdents)); 5223 5224 Results.EnterNewScope(); 5225 5226 // If this is a send-to-super, try to add the special "super" send 5227 // completion. 5228 if (Super) { 5229 if (ObjCMethodDecl *SuperMethod 5230 = AddSuperSendCompletion(*this, false, SelIdents, NumSelIdents, 5231 Results)) 5232 Results.Ignore(SuperMethod); 5233 } 5234 5235 // If we're inside an Objective-C method definition, prefer its selector to 5236 // others. 5237 if (ObjCMethodDecl *CurMethod = getCurMethodDecl()) 5238 Results.setPreferredSelector(CurMethod->getSelector()); 5239 5240 // Keep track of the selectors we've already added. 5241 VisitedSelectorSet Selectors; 5242 5243 // Handle messages to Class. This really isn't a message to an instance 5244 // method, so we treat it the same way we would treat a message send to a 5245 // class method. 5246 if (ReceiverType->isObjCClassType() || 5247 ReceiverType->isObjCQualifiedClassType()) { 5248 if (ObjCMethodDecl *CurMethod = getCurMethodDecl()) { 5249 if (ObjCInterfaceDecl *ClassDecl = CurMethod->getClassInterface()) 5250 AddObjCMethods(ClassDecl, false, MK_Any, SelIdents, NumSelIdents, 5251 CurContext, Selectors, AtArgumentExpression, Results); 5252 } 5253 } 5254 // Handle messages to a qualified ID ("id<foo>"). 5255 else if (const ObjCObjectPointerType *QualID 5256 = ReceiverType->getAsObjCQualifiedIdType()) { 5257 // Search protocols for instance methods. 5258 for (ObjCObjectPointerType::qual_iterator I = QualID->qual_begin(), 5259 E = QualID->qual_end(); 5260 I != E; ++I) 5261 AddObjCMethods(*I, true, MK_Any, SelIdents, NumSelIdents, CurContext, 5262 Selectors, AtArgumentExpression, Results); 5263 } 5264 // Handle messages to a pointer to interface type. 5265 else if (const ObjCObjectPointerType *IFacePtr 5266 = ReceiverType->getAsObjCInterfacePointerType()) { 5267 // Search the class, its superclasses, etc., for instance methods. 5268 AddObjCMethods(IFacePtr->getInterfaceDecl(), true, MK_Any, SelIdents, 5269 NumSelIdents, CurContext, Selectors, AtArgumentExpression, 5270 Results); 5271 5272 // Search protocols for instance methods. 5273 for (ObjCObjectPointerType::qual_iterator I = IFacePtr->qual_begin(), 5274 E = IFacePtr->qual_end(); 5275 I != E; ++I) 5276 AddObjCMethods(*I, true, MK_Any, SelIdents, NumSelIdents, CurContext, 5277 Selectors, AtArgumentExpression, Results); 5278 } 5279 // Handle messages to "id". 5280 else if (ReceiverType->isObjCIdType()) { 5281 // We're messaging "id", so provide all instance methods we know 5282 // about as code-completion results. 5283 5284 // If we have an external source, load the entire class method 5285 // pool from the AST file. 5286 if (ExternalSource) { 5287 for (uint32_t I = 0, N = ExternalSource->GetNumExternalSelectors(); 5288 I != N; ++I) { 5289 Selector Sel = ExternalSource->GetExternalSelector(I); 5290 if (Sel.isNull() || MethodPool.count(Sel)) 5291 continue; 5292 5293 ReadMethodPool(Sel); 5294 } 5295 } 5296 5297 for (GlobalMethodPool::iterator M = MethodPool.begin(), 5298 MEnd = MethodPool.end(); 5299 M != MEnd; ++M) { 5300 for (ObjCMethodList *MethList = &M->second.first; 5301 MethList && MethList->Method; 5302 MethList = MethList->Next) { 5303 if (!isAcceptableObjCMethod(MethList->Method, MK_Any, SelIdents, 5304 NumSelIdents)) 5305 continue; 5306 5307 if (!Selectors.insert(MethList->Method->getSelector())) 5308 continue; 5309 5310 Result R(MethList->Method, 0); 5311 R.StartParameter = NumSelIdents; 5312 R.AllParametersAreInformative = false; 5313 Results.MaybeAddResult(R, CurContext); 5314 } 5315 } 5316 } 5317 Results.ExitScope(); 5318 5319 5320 // If we're actually at the argument expression (rather than prior to the 5321 // selector), we're actually performing code completion for an expression. 5322 // Determine whether we have a single, best method. If so, we can 5323 // code-complete the expression using the corresponding parameter type as 5324 // our preferred type, improving completion results. 5325 if (AtArgumentExpression) { 5326 QualType PreferredType = getPreferredArgumentTypeForMessageSend(Results, 5327 NumSelIdents); 5328 if (PreferredType.isNull()) 5329 CodeCompleteOrdinaryName(S, PCC_Expression); 5330 else 5331 CodeCompleteExpression(S, PreferredType); 5332 return; 5333 } 5334 5335 HandleCodeCompleteResults(this, CodeCompleter, 5336 Results.getCompletionContext(), 5337 Results.data(),Results.size()); 5338 } 5339 5340 void Sema::CodeCompleteObjCForCollection(Scope *S, 5341 DeclGroupPtrTy IterationVar) { 5342 CodeCompleteExpressionData Data; 5343 Data.ObjCCollection = true; 5344 5345 if (IterationVar.getAsOpaquePtr()) { 5346 DeclGroupRef DG = IterationVar.getAsVal<DeclGroupRef>(); 5347 for (DeclGroupRef::iterator I = DG.begin(), End = DG.end(); I != End; ++I) { 5348 if (*I) 5349 Data.IgnoreDecls.push_back(*I); 5350 } 5351 } 5352 5353 CodeCompleteExpression(S, Data); 5354 } 5355 5356 void Sema::CodeCompleteObjCSelector(Scope *S, IdentifierInfo **SelIdents, 5357 unsigned NumSelIdents) { 5358 // If we have an external source, load the entire class method 5359 // pool from the AST file. 5360 if (ExternalSource) { 5361 for (uint32_t I = 0, N = ExternalSource->GetNumExternalSelectors(); 5362 I != N; ++I) { 5363 Selector Sel = ExternalSource->GetExternalSelector(I); 5364 if (Sel.isNull() || MethodPool.count(Sel)) 5365 continue; 5366 5367 ReadMethodPool(Sel); 5368 } 5369 } 5370 5371 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 5372 CodeCompletionContext::CCC_SelectorName); 5373 Results.EnterNewScope(); 5374 for (GlobalMethodPool::iterator M = MethodPool.begin(), 5375 MEnd = MethodPool.end(); 5376 M != MEnd; ++M) { 5377 5378 Selector Sel = M->first; 5379 if (!isAcceptableObjCSelector(Sel, MK_Any, SelIdents, NumSelIdents)) 5380 continue; 5381 5382 CodeCompletionBuilder Builder(Results.getAllocator()); 5383 if (Sel.isUnarySelector()) { 5384 Builder.AddTypedTextChunk(Builder.getAllocator().CopyString( 5385 Sel.getNameForSlot(0))); 5386 Results.AddResult(Builder.TakeString()); 5387 continue; 5388 } 5389 5390 std::string Accumulator; 5391 for (unsigned I = 0, N = Sel.getNumArgs(); I != N; ++I) { 5392 if (I == NumSelIdents) { 5393 if (!Accumulator.empty()) { 5394 Builder.AddInformativeChunk(Builder.getAllocator().CopyString( 5395 Accumulator)); 5396 Accumulator.clear(); 5397 } 5398 } 5399 5400 Accumulator += Sel.getNameForSlot(I); 5401 Accumulator += ':'; 5402 } 5403 Builder.AddTypedTextChunk(Builder.getAllocator().CopyString( Accumulator)); 5404 Results.AddResult(Builder.TakeString()); 5405 } 5406 Results.ExitScope(); 5407 5408 HandleCodeCompleteResults(this, CodeCompleter, 5409 CodeCompletionContext::CCC_SelectorName, 5410 Results.data(), Results.size()); 5411 } 5412 5413 /// \brief Add all of the protocol declarations that we find in the given 5414 /// (translation unit) context. 5415 static void AddProtocolResults(DeclContext *Ctx, DeclContext *CurContext, 5416 bool OnlyForwardDeclarations, 5417 ResultBuilder &Results) { 5418 typedef CodeCompletionResult Result; 5419 5420 for (DeclContext::decl_iterator D = Ctx->decls_begin(), 5421 DEnd = Ctx->decls_end(); 5422 D != DEnd; ++D) { 5423 // Record any protocols we find. 5424 if (ObjCProtocolDecl *Proto = dyn_cast<ObjCProtocolDecl>(*D)) 5425 if (!OnlyForwardDeclarations || !Proto->hasDefinition()) 5426 Results.AddResult(Result(Proto, 0), CurContext, 0, false); 5427 } 5428 } 5429 5430 void Sema::CodeCompleteObjCProtocolReferences(IdentifierLocPair *Protocols, 5431 unsigned NumProtocols) { 5432 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 5433 CodeCompletionContext::CCC_ObjCProtocolName); 5434 5435 if (CodeCompleter && CodeCompleter->includeGlobals()) { 5436 Results.EnterNewScope(); 5437 5438 // Tell the result set to ignore all of the protocols we have 5439 // already seen. 5440 // FIXME: This doesn't work when caching code-completion results. 5441 for (unsigned I = 0; I != NumProtocols; ++I) 5442 if (ObjCProtocolDecl *Protocol = LookupProtocol(Protocols[I].first, 5443 Protocols[I].second)) 5444 Results.Ignore(Protocol); 5445 5446 // Add all protocols. 5447 AddProtocolResults(Context.getTranslationUnitDecl(), CurContext, false, 5448 Results); 5449 5450 Results.ExitScope(); 5451 } 5452 5453 HandleCodeCompleteResults(this, CodeCompleter, 5454 CodeCompletionContext::CCC_ObjCProtocolName, 5455 Results.data(),Results.size()); 5456 } 5457 5458 void Sema::CodeCompleteObjCProtocolDecl(Scope *) { 5459 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 5460 CodeCompletionContext::CCC_ObjCProtocolName); 5461 5462 if (CodeCompleter && CodeCompleter->includeGlobals()) { 5463 Results.EnterNewScope(); 5464 5465 // Add all protocols. 5466 AddProtocolResults(Context.getTranslationUnitDecl(), CurContext, true, 5467 Results); 5468 5469 Results.ExitScope(); 5470 } 5471 5472 HandleCodeCompleteResults(this, CodeCompleter, 5473 CodeCompletionContext::CCC_ObjCProtocolName, 5474 Results.data(),Results.size()); 5475 } 5476 5477 /// \brief Add all of the Objective-C interface declarations that we find in 5478 /// the given (translation unit) context. 5479 static void AddInterfaceResults(DeclContext *Ctx, DeclContext *CurContext, 5480 bool OnlyForwardDeclarations, 5481 bool OnlyUnimplemented, 5482 ResultBuilder &Results) { 5483 typedef CodeCompletionResult Result; 5484 5485 for (DeclContext::decl_iterator D = Ctx->decls_begin(), 5486 DEnd = Ctx->decls_end(); 5487 D != DEnd; ++D) { 5488 // Record any interfaces we find. 5489 if (ObjCInterfaceDecl *Class = dyn_cast<ObjCInterfaceDecl>(*D)) 5490 if ((!OnlyForwardDeclarations || !Class->hasDefinition()) && 5491 (!OnlyUnimplemented || !Class->getImplementation())) 5492 Results.AddResult(Result(Class, 0), CurContext, 0, false); 5493 } 5494 } 5495 5496 void Sema::CodeCompleteObjCInterfaceDecl(Scope *S) { 5497 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 5498 CodeCompletionContext::CCC_Other); 5499 Results.EnterNewScope(); 5500 5501 if (CodeCompleter->includeGlobals()) { 5502 // Add all classes. 5503 AddInterfaceResults(Context.getTranslationUnitDecl(), CurContext, false, 5504 false, Results); 5505 } 5506 5507 Results.ExitScope(); 5508 5509 HandleCodeCompleteResults(this, CodeCompleter, 5510 CodeCompletionContext::CCC_ObjCInterfaceName, 5511 Results.data(),Results.size()); 5512 } 5513 5514 void Sema::CodeCompleteObjCSuperclass(Scope *S, IdentifierInfo *ClassName, 5515 SourceLocation ClassNameLoc) { 5516 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 5517 CodeCompletionContext::CCC_ObjCInterfaceName); 5518 Results.EnterNewScope(); 5519 5520 // Make sure that we ignore the class we're currently defining. 5521 NamedDecl *CurClass 5522 = LookupSingleName(TUScope, ClassName, ClassNameLoc, LookupOrdinaryName); 5523 if (CurClass && isa<ObjCInterfaceDecl>(CurClass)) 5524 Results.Ignore(CurClass); 5525 5526 if (CodeCompleter->includeGlobals()) { 5527 // Add all classes. 5528 AddInterfaceResults(Context.getTranslationUnitDecl(), CurContext, false, 5529 false, Results); 5530 } 5531 5532 Results.ExitScope(); 5533 5534 HandleCodeCompleteResults(this, CodeCompleter, 5535 CodeCompletionContext::CCC_ObjCInterfaceName, 5536 Results.data(),Results.size()); 5537 } 5538 5539 void Sema::CodeCompleteObjCImplementationDecl(Scope *S) { 5540 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 5541 CodeCompletionContext::CCC_Other); 5542 Results.EnterNewScope(); 5543 5544 if (CodeCompleter->includeGlobals()) { 5545 // Add all unimplemented classes. 5546 AddInterfaceResults(Context.getTranslationUnitDecl(), CurContext, false, 5547 true, Results); 5548 } 5549 5550 Results.ExitScope(); 5551 5552 HandleCodeCompleteResults(this, CodeCompleter, 5553 CodeCompletionContext::CCC_ObjCInterfaceName, 5554 Results.data(),Results.size()); 5555 } 5556 5557 void Sema::CodeCompleteObjCInterfaceCategory(Scope *S, 5558 IdentifierInfo *ClassName, 5559 SourceLocation ClassNameLoc) { 5560 typedef CodeCompletionResult Result; 5561 5562 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 5563 CodeCompletionContext::CCC_ObjCCategoryName); 5564 5565 // Ignore any categories we find that have already been implemented by this 5566 // interface. 5567 llvm::SmallPtrSet<IdentifierInfo *, 16> CategoryNames; 5568 NamedDecl *CurClass 5569 = LookupSingleName(TUScope, ClassName, ClassNameLoc, LookupOrdinaryName); 5570 if (ObjCInterfaceDecl *Class = dyn_cast_or_null<ObjCInterfaceDecl>(CurClass)) 5571 for (ObjCCategoryDecl *Category = Class->getCategoryList(); Category; 5572 Category = Category->getNextClassCategory()) 5573 CategoryNames.insert(Category->getIdentifier()); 5574 5575 // Add all of the categories we know about. 5576 Results.EnterNewScope(); 5577 TranslationUnitDecl *TU = Context.getTranslationUnitDecl(); 5578 for (DeclContext::decl_iterator D = TU->decls_begin(), 5579 DEnd = TU->decls_end(); 5580 D != DEnd; ++D) 5581 if (ObjCCategoryDecl *Category = dyn_cast<ObjCCategoryDecl>(*D)) 5582 if (CategoryNames.insert(Category->getIdentifier())) 5583 Results.AddResult(Result(Category, 0), CurContext, 0, false); 5584 Results.ExitScope(); 5585 5586 HandleCodeCompleteResults(this, CodeCompleter, 5587 CodeCompletionContext::CCC_ObjCCategoryName, 5588 Results.data(),Results.size()); 5589 } 5590 5591 void Sema::CodeCompleteObjCImplementationCategory(Scope *S, 5592 IdentifierInfo *ClassName, 5593 SourceLocation ClassNameLoc) { 5594 typedef CodeCompletionResult Result; 5595 5596 // Find the corresponding interface. If we couldn't find the interface, the 5597 // program itself is ill-formed. However, we'll try to be helpful still by 5598 // providing the list of all of the categories we know about. 5599 NamedDecl *CurClass 5600 = LookupSingleName(TUScope, ClassName, ClassNameLoc, LookupOrdinaryName); 5601 ObjCInterfaceDecl *Class = dyn_cast_or_null<ObjCInterfaceDecl>(CurClass); 5602 if (!Class) 5603 return CodeCompleteObjCInterfaceCategory(S, ClassName, ClassNameLoc); 5604 5605 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 5606 CodeCompletionContext::CCC_ObjCCategoryName); 5607 5608 // Add all of the categories that have have corresponding interface 5609 // declarations in this class and any of its superclasses, except for 5610 // already-implemented categories in the class itself. 5611 llvm::SmallPtrSet<IdentifierInfo *, 16> CategoryNames; 5612 Results.EnterNewScope(); 5613 bool IgnoreImplemented = true; 5614 while (Class) { 5615 for (ObjCCategoryDecl *Category = Class->getCategoryList(); Category; 5616 Category = Category->getNextClassCategory()) 5617 if ((!IgnoreImplemented || !Category->getImplementation()) && 5618 CategoryNames.insert(Category->getIdentifier())) 5619 Results.AddResult(Result(Category, 0), CurContext, 0, false); 5620 5621 Class = Class->getSuperClass(); 5622 IgnoreImplemented = false; 5623 } 5624 Results.ExitScope(); 5625 5626 HandleCodeCompleteResults(this, CodeCompleter, 5627 CodeCompletionContext::CCC_ObjCCategoryName, 5628 Results.data(),Results.size()); 5629 } 5630 5631 void Sema::CodeCompleteObjCPropertyDefinition(Scope *S) { 5632 typedef CodeCompletionResult Result; 5633 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 5634 CodeCompletionContext::CCC_Other); 5635 5636 // Figure out where this @synthesize lives. 5637 ObjCContainerDecl *Container 5638 = dyn_cast_or_null<ObjCContainerDecl>(CurContext); 5639 if (!Container || 5640 (!isa<ObjCImplementationDecl>(Container) && 5641 !isa<ObjCCategoryImplDecl>(Container))) 5642 return; 5643 5644 // Ignore any properties that have already been implemented. 5645 for (DeclContext::decl_iterator D = Container->decls_begin(), 5646 DEnd = Container->decls_end(); 5647 D != DEnd; ++D) 5648 if (ObjCPropertyImplDecl *PropertyImpl = dyn_cast<ObjCPropertyImplDecl>(*D)) 5649 Results.Ignore(PropertyImpl->getPropertyDecl()); 5650 5651 // Add any properties that we find. 5652 AddedPropertiesSet AddedProperties; 5653 Results.EnterNewScope(); 5654 if (ObjCImplementationDecl *ClassImpl 5655 = dyn_cast<ObjCImplementationDecl>(Container)) 5656 AddObjCProperties(ClassImpl->getClassInterface(), false, 5657 /*AllowNullaryMethods=*/false, CurContext, 5658 AddedProperties, Results); 5659 else 5660 AddObjCProperties(cast<ObjCCategoryImplDecl>(Container)->getCategoryDecl(), 5661 false, /*AllowNullaryMethods=*/false, CurContext, 5662 AddedProperties, Results); 5663 Results.ExitScope(); 5664 5665 HandleCodeCompleteResults(this, CodeCompleter, 5666 CodeCompletionContext::CCC_Other, 5667 Results.data(),Results.size()); 5668 } 5669 5670 void Sema::CodeCompleteObjCPropertySynthesizeIvar(Scope *S, 5671 IdentifierInfo *PropertyName) { 5672 typedef CodeCompletionResult Result; 5673 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 5674 CodeCompletionContext::CCC_Other); 5675 5676 // Figure out where this @synthesize lives. 5677 ObjCContainerDecl *Container 5678 = dyn_cast_or_null<ObjCContainerDecl>(CurContext); 5679 if (!Container || 5680 (!isa<ObjCImplementationDecl>(Container) && 5681 !isa<ObjCCategoryImplDecl>(Container))) 5682 return; 5683 5684 // Figure out which interface we're looking into. 5685 ObjCInterfaceDecl *Class = 0; 5686 if (ObjCImplementationDecl *ClassImpl 5687 = dyn_cast<ObjCImplementationDecl>(Container)) 5688 Class = ClassImpl->getClassInterface(); 5689 else 5690 Class = cast<ObjCCategoryImplDecl>(Container)->getCategoryDecl() 5691 ->getClassInterface(); 5692 5693 // Determine the type of the property we're synthesizing. 5694 QualType PropertyType = Context.getObjCIdType(); 5695 if (Class) { 5696 if (ObjCPropertyDecl *Property 5697 = Class->FindPropertyDeclaration(PropertyName)) { 5698 PropertyType 5699 = Property->getType().getNonReferenceType().getUnqualifiedType(); 5700 5701 // Give preference to ivars 5702 Results.setPreferredType(PropertyType); 5703 } 5704 } 5705 5706 // Add all of the instance variables in this class and its superclasses. 5707 Results.EnterNewScope(); 5708 bool SawSimilarlyNamedIvar = false; 5709 std::string NameWithPrefix; 5710 NameWithPrefix += '_'; 5711 NameWithPrefix += PropertyName->getName(); 5712 std::string NameWithSuffix = PropertyName->getName().str(); 5713 NameWithSuffix += '_'; 5714 for(; Class; Class = Class->getSuperClass()) { 5715 for (ObjCIvarDecl *Ivar = Class->all_declared_ivar_begin(); Ivar; 5716 Ivar = Ivar->getNextIvar()) { 5717 Results.AddResult(Result(Ivar, 0), CurContext, 0, false); 5718 5719 // Determine whether we've seen an ivar with a name similar to the 5720 // property. 5721 if ((PropertyName == Ivar->getIdentifier() || 5722 NameWithPrefix == Ivar->getName() || 5723 NameWithSuffix == Ivar->getName())) { 5724 SawSimilarlyNamedIvar = true; 5725 5726 // Reduce the priority of this result by one, to give it a slight 5727 // advantage over other results whose names don't match so closely. 5728 if (Results.size() && 5729 Results.data()[Results.size() - 1].Kind 5730 == CodeCompletionResult::RK_Declaration && 5731 Results.data()[Results.size() - 1].Declaration == Ivar) 5732 Results.data()[Results.size() - 1].Priority--; 5733 } 5734 } 5735 } 5736 5737 if (!SawSimilarlyNamedIvar) { 5738 // Create ivar result _propName, that the user can use to synthesize 5739 // an ivar of the appropriate type. 5740 unsigned Priority = CCP_MemberDeclaration + 1; 5741 typedef CodeCompletionResult Result; 5742 CodeCompletionAllocator &Allocator = Results.getAllocator(); 5743 CodeCompletionBuilder Builder(Allocator, Priority,CXAvailability_Available); 5744 5745 PrintingPolicy Policy = getCompletionPrintingPolicy(*this); 5746 Builder.AddResultTypeChunk(GetCompletionTypeString(PropertyType, Context, 5747 Policy, Allocator)); 5748 Builder.AddTypedTextChunk(Allocator.CopyString(NameWithPrefix)); 5749 Results.AddResult(Result(Builder.TakeString(), Priority, 5750 CXCursor_ObjCIvarDecl)); 5751 } 5752 5753 Results.ExitScope(); 5754 5755 HandleCodeCompleteResults(this, CodeCompleter, 5756 CodeCompletionContext::CCC_Other, 5757 Results.data(),Results.size()); 5758 } 5759 5760 // Mapping from selectors to the methods that implement that selector, along 5761 // with the "in original class" flag. 5762 typedef llvm::DenseMap<Selector, std::pair<ObjCMethodDecl *, bool> > 5763 KnownMethodsMap; 5764 5765 /// \brief Find all of the methods that reside in the given container 5766 /// (and its superclasses, protocols, etc.) that meet the given 5767 /// criteria. Insert those methods into the map of known methods, 5768 /// indexed by selector so they can be easily found. 5769 static void FindImplementableMethods(ASTContext &Context, 5770 ObjCContainerDecl *Container, 5771 bool WantInstanceMethods, 5772 QualType ReturnType, 5773 KnownMethodsMap &KnownMethods, 5774 bool InOriginalClass = true) { 5775 if (ObjCInterfaceDecl *IFace = dyn_cast<ObjCInterfaceDecl>(Container)) { 5776 // Recurse into protocols. 5777 if (!IFace->hasDefinition()) 5778 return; 5779 5780 const ObjCList<ObjCProtocolDecl> &Protocols 5781 = IFace->getReferencedProtocols(); 5782 for (ObjCList<ObjCProtocolDecl>::iterator I = Protocols.begin(), 5783 E = Protocols.end(); 5784 I != E; ++I) 5785 FindImplementableMethods(Context, *I, WantInstanceMethods, ReturnType, 5786 KnownMethods, InOriginalClass); 5787 5788 // Add methods from any class extensions and categories. 5789 for (const ObjCCategoryDecl *Cat = IFace->getCategoryList(); Cat; 5790 Cat = Cat->getNextClassCategory()) 5791 FindImplementableMethods(Context, const_cast<ObjCCategoryDecl*>(Cat), 5792 WantInstanceMethods, ReturnType, 5793 KnownMethods, false); 5794 5795 // Visit the superclass. 5796 if (IFace->getSuperClass()) 5797 FindImplementableMethods(Context, IFace->getSuperClass(), 5798 WantInstanceMethods, ReturnType, 5799 KnownMethods, false); 5800 } 5801 5802 if (ObjCCategoryDecl *Category = dyn_cast<ObjCCategoryDecl>(Container)) { 5803 // Recurse into protocols. 5804 const ObjCList<ObjCProtocolDecl> &Protocols 5805 = Category->getReferencedProtocols(); 5806 for (ObjCList<ObjCProtocolDecl>::iterator I = Protocols.begin(), 5807 E = Protocols.end(); 5808 I != E; ++I) 5809 FindImplementableMethods(Context, *I, WantInstanceMethods, ReturnType, 5810 KnownMethods, InOriginalClass); 5811 5812 // If this category is the original class, jump to the interface. 5813 if (InOriginalClass && Category->getClassInterface()) 5814 FindImplementableMethods(Context, Category->getClassInterface(), 5815 WantInstanceMethods, ReturnType, KnownMethods, 5816 false); 5817 } 5818 5819 if (ObjCProtocolDecl *Protocol = dyn_cast<ObjCProtocolDecl>(Container)) { 5820 if (Protocol->hasDefinition()) { 5821 // Recurse into protocols. 5822 const ObjCList<ObjCProtocolDecl> &Protocols 5823 = Protocol->getReferencedProtocols(); 5824 for (ObjCList<ObjCProtocolDecl>::iterator I = Protocols.begin(), 5825 E = Protocols.end(); 5826 I != E; ++I) 5827 FindImplementableMethods(Context, *I, WantInstanceMethods, ReturnType, 5828 KnownMethods, false); 5829 } 5830 } 5831 5832 // Add methods in this container. This operation occurs last because 5833 // we want the methods from this container to override any methods 5834 // we've previously seen with the same selector. 5835 for (ObjCContainerDecl::method_iterator M = Container->meth_begin(), 5836 MEnd = Container->meth_end(); 5837 M != MEnd; ++M) { 5838 if ((*M)->isInstanceMethod() == WantInstanceMethods) { 5839 if (!ReturnType.isNull() && 5840 !Context.hasSameUnqualifiedType(ReturnType, (*M)->getResultType())) 5841 continue; 5842 5843 KnownMethods[(*M)->getSelector()] = std::make_pair(*M, InOriginalClass); 5844 } 5845 } 5846 } 5847 5848 /// \brief Add the parenthesized return or parameter type chunk to a code 5849 /// completion string. 5850 static void AddObjCPassingTypeChunk(QualType Type, 5851 ASTContext &Context, 5852 const PrintingPolicy &Policy, 5853 CodeCompletionBuilder &Builder) { 5854 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 5855 Builder.AddTextChunk(GetCompletionTypeString(Type, Context, Policy, 5856 Builder.getAllocator())); 5857 Builder.AddChunk(CodeCompletionString::CK_RightParen); 5858 } 5859 5860 /// \brief Determine whether the given class is or inherits from a class by 5861 /// the given name. 5862 static bool InheritsFromClassNamed(ObjCInterfaceDecl *Class, 5863 StringRef Name) { 5864 if (!Class) 5865 return false; 5866 5867 if (Class->getIdentifier() && Class->getIdentifier()->getName() == Name) 5868 return true; 5869 5870 return InheritsFromClassNamed(Class->getSuperClass(), Name); 5871 } 5872 5873 /// \brief Add code completions for Objective-C Key-Value Coding (KVC) and 5874 /// Key-Value Observing (KVO). 5875 static void AddObjCKeyValueCompletions(ObjCPropertyDecl *Property, 5876 bool IsInstanceMethod, 5877 QualType ReturnType, 5878 ASTContext &Context, 5879 VisitedSelectorSet &KnownSelectors, 5880 ResultBuilder &Results) { 5881 IdentifierInfo *PropName = Property->getIdentifier(); 5882 if (!PropName || PropName->getLength() == 0) 5883 return; 5884 5885 PrintingPolicy Policy = getCompletionPrintingPolicy(Results.getSema()); 5886 5887 // Builder that will create each code completion. 5888 typedef CodeCompletionResult Result; 5889 CodeCompletionAllocator &Allocator = Results.getAllocator(); 5890 CodeCompletionBuilder Builder(Allocator); 5891 5892 // The selector table. 5893 SelectorTable &Selectors = Context.Selectors; 5894 5895 // The property name, copied into the code completion allocation region 5896 // on demand. 5897 struct KeyHolder { 5898 CodeCompletionAllocator &Allocator; 5899 StringRef Key; 5900 const char *CopiedKey; 5901 5902 KeyHolder(CodeCompletionAllocator &Allocator, StringRef Key) 5903 : Allocator(Allocator), Key(Key), CopiedKey(0) { } 5904 5905 operator const char *() { 5906 if (CopiedKey) 5907 return CopiedKey; 5908 5909 return CopiedKey = Allocator.CopyString(Key); 5910 } 5911 } Key(Allocator, PropName->getName()); 5912 5913 // The uppercased name of the property name. 5914 std::string UpperKey = PropName->getName(); 5915 if (!UpperKey.empty()) 5916 UpperKey[0] = toupper(UpperKey[0]); 5917 5918 bool ReturnTypeMatchesProperty = ReturnType.isNull() || 5919 Context.hasSameUnqualifiedType(ReturnType.getNonReferenceType(), 5920 Property->getType()); 5921 bool ReturnTypeMatchesVoid 5922 = ReturnType.isNull() || ReturnType->isVoidType(); 5923 5924 // Add the normal accessor -(type)key. 5925 if (IsInstanceMethod && 5926 KnownSelectors.insert(Selectors.getNullarySelector(PropName)) && 5927 ReturnTypeMatchesProperty && !Property->getGetterMethodDecl()) { 5928 if (ReturnType.isNull()) 5929 AddObjCPassingTypeChunk(Property->getType(), Context, Policy, Builder); 5930 5931 Builder.AddTypedTextChunk(Key); 5932 Results.AddResult(Result(Builder.TakeString(), CCP_CodePattern, 5933 CXCursor_ObjCInstanceMethodDecl)); 5934 } 5935 5936 // If we have an integral or boolean property (or the user has provided 5937 // an integral or boolean return type), add the accessor -(type)isKey. 5938 if (IsInstanceMethod && 5939 ((!ReturnType.isNull() && 5940 (ReturnType->isIntegerType() || ReturnType->isBooleanType())) || 5941 (ReturnType.isNull() && 5942 (Property->getType()->isIntegerType() || 5943 Property->getType()->isBooleanType())))) { 5944 std::string SelectorName = (Twine("is") + UpperKey).str(); 5945 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 5946 if (KnownSelectors.insert(Selectors.getNullarySelector(SelectorId))) { 5947 if (ReturnType.isNull()) { 5948 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 5949 Builder.AddTextChunk("BOOL"); 5950 Builder.AddChunk(CodeCompletionString::CK_RightParen); 5951 } 5952 5953 Builder.AddTypedTextChunk( 5954 Allocator.CopyString(SelectorId->getName())); 5955 Results.AddResult(Result(Builder.TakeString(), CCP_CodePattern, 5956 CXCursor_ObjCInstanceMethodDecl)); 5957 } 5958 } 5959 5960 // Add the normal mutator. 5961 if (IsInstanceMethod && ReturnTypeMatchesVoid && 5962 !Property->getSetterMethodDecl()) { 5963 std::string SelectorName = (Twine("set") + UpperKey).str(); 5964 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 5965 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId))) { 5966 if (ReturnType.isNull()) { 5967 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 5968 Builder.AddTextChunk("void"); 5969 Builder.AddChunk(CodeCompletionString::CK_RightParen); 5970 } 5971 5972 Builder.AddTypedTextChunk( 5973 Allocator.CopyString(SelectorId->getName())); 5974 Builder.AddTypedTextChunk(":"); 5975 AddObjCPassingTypeChunk(Property->getType(), Context, Policy, Builder); 5976 Builder.AddTextChunk(Key); 5977 Results.AddResult(Result(Builder.TakeString(), CCP_CodePattern, 5978 CXCursor_ObjCInstanceMethodDecl)); 5979 } 5980 } 5981 5982 // Indexed and unordered accessors 5983 unsigned IndexedGetterPriority = CCP_CodePattern; 5984 unsigned IndexedSetterPriority = CCP_CodePattern; 5985 unsigned UnorderedGetterPriority = CCP_CodePattern; 5986 unsigned UnorderedSetterPriority = CCP_CodePattern; 5987 if (const ObjCObjectPointerType *ObjCPointer 5988 = Property->getType()->getAs<ObjCObjectPointerType>()) { 5989 if (ObjCInterfaceDecl *IFace = ObjCPointer->getInterfaceDecl()) { 5990 // If this interface type is not provably derived from a known 5991 // collection, penalize the corresponding completions. 5992 if (!InheritsFromClassNamed(IFace, "NSMutableArray")) { 5993 IndexedSetterPriority += CCD_ProbablyNotObjCCollection; 5994 if (!InheritsFromClassNamed(IFace, "NSArray")) 5995 IndexedGetterPriority += CCD_ProbablyNotObjCCollection; 5996 } 5997 5998 if (!InheritsFromClassNamed(IFace, "NSMutableSet")) { 5999 UnorderedSetterPriority += CCD_ProbablyNotObjCCollection; 6000 if (!InheritsFromClassNamed(IFace, "NSSet")) 6001 UnorderedGetterPriority += CCD_ProbablyNotObjCCollection; 6002 } 6003 } 6004 } else { 6005 IndexedGetterPriority += CCD_ProbablyNotObjCCollection; 6006 IndexedSetterPriority += CCD_ProbablyNotObjCCollection; 6007 UnorderedGetterPriority += CCD_ProbablyNotObjCCollection; 6008 UnorderedSetterPriority += CCD_ProbablyNotObjCCollection; 6009 } 6010 6011 // Add -(NSUInteger)countOf<key> 6012 if (IsInstanceMethod && 6013 (ReturnType.isNull() || ReturnType->isIntegerType())) { 6014 std::string SelectorName = (Twine("countOf") + UpperKey).str(); 6015 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6016 if (KnownSelectors.insert(Selectors.getNullarySelector(SelectorId))) { 6017 if (ReturnType.isNull()) { 6018 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6019 Builder.AddTextChunk("NSUInteger"); 6020 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6021 } 6022 6023 Builder.AddTypedTextChunk( 6024 Allocator.CopyString(SelectorId->getName())); 6025 Results.AddResult(Result(Builder.TakeString(), 6026 std::min(IndexedGetterPriority, 6027 UnorderedGetterPriority), 6028 CXCursor_ObjCInstanceMethodDecl)); 6029 } 6030 } 6031 6032 // Indexed getters 6033 // Add -(id)objectInKeyAtIndex:(NSUInteger)index 6034 if (IsInstanceMethod && 6035 (ReturnType.isNull() || ReturnType->isObjCObjectPointerType())) { 6036 std::string SelectorName 6037 = (Twine("objectIn") + UpperKey + "AtIndex").str(); 6038 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6039 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId))) { 6040 if (ReturnType.isNull()) { 6041 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6042 Builder.AddTextChunk("id"); 6043 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6044 } 6045 6046 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6047 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6048 Builder.AddTextChunk("NSUInteger"); 6049 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6050 Builder.AddTextChunk("index"); 6051 Results.AddResult(Result(Builder.TakeString(), IndexedGetterPriority, 6052 CXCursor_ObjCInstanceMethodDecl)); 6053 } 6054 } 6055 6056 // Add -(NSArray *)keyAtIndexes:(NSIndexSet *)indexes 6057 if (IsInstanceMethod && 6058 (ReturnType.isNull() || 6059 (ReturnType->isObjCObjectPointerType() && 6060 ReturnType->getAs<ObjCObjectPointerType>()->getInterfaceDecl() && 6061 ReturnType->getAs<ObjCObjectPointerType>()->getInterfaceDecl() 6062 ->getName() == "NSArray"))) { 6063 std::string SelectorName 6064 = (Twine(Property->getName()) + "AtIndexes").str(); 6065 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6066 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId))) { 6067 if (ReturnType.isNull()) { 6068 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6069 Builder.AddTextChunk("NSArray *"); 6070 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6071 } 6072 6073 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6074 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6075 Builder.AddTextChunk("NSIndexSet *"); 6076 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6077 Builder.AddTextChunk("indexes"); 6078 Results.AddResult(Result(Builder.TakeString(), IndexedGetterPriority, 6079 CXCursor_ObjCInstanceMethodDecl)); 6080 } 6081 } 6082 6083 // Add -(void)getKey:(type **)buffer range:(NSRange)inRange 6084 if (IsInstanceMethod && ReturnTypeMatchesVoid) { 6085 std::string SelectorName = (Twine("get") + UpperKey).str(); 6086 IdentifierInfo *SelectorIds[2] = { 6087 &Context.Idents.get(SelectorName), 6088 &Context.Idents.get("range") 6089 }; 6090 6091 if (KnownSelectors.insert(Selectors.getSelector(2, SelectorIds))) { 6092 if (ReturnType.isNull()) { 6093 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6094 Builder.AddTextChunk("void"); 6095 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6096 } 6097 6098 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6099 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6100 Builder.AddPlaceholderChunk("object-type"); 6101 Builder.AddTextChunk(" **"); 6102 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6103 Builder.AddTextChunk("buffer"); 6104 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6105 Builder.AddTypedTextChunk("range:"); 6106 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6107 Builder.AddTextChunk("NSRange"); 6108 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6109 Builder.AddTextChunk("inRange"); 6110 Results.AddResult(Result(Builder.TakeString(), IndexedGetterPriority, 6111 CXCursor_ObjCInstanceMethodDecl)); 6112 } 6113 } 6114 6115 // Mutable indexed accessors 6116 6117 // - (void)insertObject:(type *)object inKeyAtIndex:(NSUInteger)index 6118 if (IsInstanceMethod && ReturnTypeMatchesVoid) { 6119 std::string SelectorName = (Twine("in") + UpperKey + "AtIndex").str(); 6120 IdentifierInfo *SelectorIds[2] = { 6121 &Context.Idents.get("insertObject"), 6122 &Context.Idents.get(SelectorName) 6123 }; 6124 6125 if (KnownSelectors.insert(Selectors.getSelector(2, SelectorIds))) { 6126 if (ReturnType.isNull()) { 6127 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6128 Builder.AddTextChunk("void"); 6129 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6130 } 6131 6132 Builder.AddTypedTextChunk("insertObject:"); 6133 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6134 Builder.AddPlaceholderChunk("object-type"); 6135 Builder.AddTextChunk(" *"); 6136 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6137 Builder.AddTextChunk("object"); 6138 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6139 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6140 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6141 Builder.AddPlaceholderChunk("NSUInteger"); 6142 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6143 Builder.AddTextChunk("index"); 6144 Results.AddResult(Result(Builder.TakeString(), IndexedSetterPriority, 6145 CXCursor_ObjCInstanceMethodDecl)); 6146 } 6147 } 6148 6149 // - (void)insertKey:(NSArray *)array atIndexes:(NSIndexSet *)indexes 6150 if (IsInstanceMethod && ReturnTypeMatchesVoid) { 6151 std::string SelectorName = (Twine("insert") + UpperKey).str(); 6152 IdentifierInfo *SelectorIds[2] = { 6153 &Context.Idents.get(SelectorName), 6154 &Context.Idents.get("atIndexes") 6155 }; 6156 6157 if (KnownSelectors.insert(Selectors.getSelector(2, SelectorIds))) { 6158 if (ReturnType.isNull()) { 6159 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6160 Builder.AddTextChunk("void"); 6161 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6162 } 6163 6164 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6165 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6166 Builder.AddTextChunk("NSArray *"); 6167 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6168 Builder.AddTextChunk("array"); 6169 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6170 Builder.AddTypedTextChunk("atIndexes:"); 6171 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6172 Builder.AddPlaceholderChunk("NSIndexSet *"); 6173 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6174 Builder.AddTextChunk("indexes"); 6175 Results.AddResult(Result(Builder.TakeString(), IndexedSetterPriority, 6176 CXCursor_ObjCInstanceMethodDecl)); 6177 } 6178 } 6179 6180 // -(void)removeObjectFromKeyAtIndex:(NSUInteger)index 6181 if (IsInstanceMethod && ReturnTypeMatchesVoid) { 6182 std::string SelectorName 6183 = (Twine("removeObjectFrom") + UpperKey + "AtIndex").str(); 6184 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6185 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId))) { 6186 if (ReturnType.isNull()) { 6187 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6188 Builder.AddTextChunk("void"); 6189 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6190 } 6191 6192 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6193 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6194 Builder.AddTextChunk("NSUInteger"); 6195 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6196 Builder.AddTextChunk("index"); 6197 Results.AddResult(Result(Builder.TakeString(), IndexedSetterPriority, 6198 CXCursor_ObjCInstanceMethodDecl)); 6199 } 6200 } 6201 6202 // -(void)removeKeyAtIndexes:(NSIndexSet *)indexes 6203 if (IsInstanceMethod && ReturnTypeMatchesVoid) { 6204 std::string SelectorName 6205 = (Twine("remove") + UpperKey + "AtIndexes").str(); 6206 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6207 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId))) { 6208 if (ReturnType.isNull()) { 6209 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6210 Builder.AddTextChunk("void"); 6211 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6212 } 6213 6214 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6215 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6216 Builder.AddTextChunk("NSIndexSet *"); 6217 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6218 Builder.AddTextChunk("indexes"); 6219 Results.AddResult(Result(Builder.TakeString(), IndexedSetterPriority, 6220 CXCursor_ObjCInstanceMethodDecl)); 6221 } 6222 } 6223 6224 // - (void)replaceObjectInKeyAtIndex:(NSUInteger)index withObject:(id)object 6225 if (IsInstanceMethod && ReturnTypeMatchesVoid) { 6226 std::string SelectorName 6227 = (Twine("replaceObjectIn") + UpperKey + "AtIndex").str(); 6228 IdentifierInfo *SelectorIds[2] = { 6229 &Context.Idents.get(SelectorName), 6230 &Context.Idents.get("withObject") 6231 }; 6232 6233 if (KnownSelectors.insert(Selectors.getSelector(2, SelectorIds))) { 6234 if (ReturnType.isNull()) { 6235 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6236 Builder.AddTextChunk("void"); 6237 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6238 } 6239 6240 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6241 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6242 Builder.AddPlaceholderChunk("NSUInteger"); 6243 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6244 Builder.AddTextChunk("index"); 6245 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6246 Builder.AddTypedTextChunk("withObject:"); 6247 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6248 Builder.AddTextChunk("id"); 6249 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6250 Builder.AddTextChunk("object"); 6251 Results.AddResult(Result(Builder.TakeString(), IndexedSetterPriority, 6252 CXCursor_ObjCInstanceMethodDecl)); 6253 } 6254 } 6255 6256 // - (void)replaceKeyAtIndexes:(NSIndexSet *)indexes withKey:(NSArray *)array 6257 if (IsInstanceMethod && ReturnTypeMatchesVoid) { 6258 std::string SelectorName1 6259 = (Twine("replace") + UpperKey + "AtIndexes").str(); 6260 std::string SelectorName2 = (Twine("with") + UpperKey).str(); 6261 IdentifierInfo *SelectorIds[2] = { 6262 &Context.Idents.get(SelectorName1), 6263 &Context.Idents.get(SelectorName2) 6264 }; 6265 6266 if (KnownSelectors.insert(Selectors.getSelector(2, SelectorIds))) { 6267 if (ReturnType.isNull()) { 6268 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6269 Builder.AddTextChunk("void"); 6270 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6271 } 6272 6273 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName1 + ":")); 6274 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6275 Builder.AddPlaceholderChunk("NSIndexSet *"); 6276 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6277 Builder.AddTextChunk("indexes"); 6278 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6279 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName2 + ":")); 6280 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6281 Builder.AddTextChunk("NSArray *"); 6282 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6283 Builder.AddTextChunk("array"); 6284 Results.AddResult(Result(Builder.TakeString(), IndexedSetterPriority, 6285 CXCursor_ObjCInstanceMethodDecl)); 6286 } 6287 } 6288 6289 // Unordered getters 6290 // - (NSEnumerator *)enumeratorOfKey 6291 if (IsInstanceMethod && 6292 (ReturnType.isNull() || 6293 (ReturnType->isObjCObjectPointerType() && 6294 ReturnType->getAs<ObjCObjectPointerType>()->getInterfaceDecl() && 6295 ReturnType->getAs<ObjCObjectPointerType>()->getInterfaceDecl() 6296 ->getName() == "NSEnumerator"))) { 6297 std::string SelectorName = (Twine("enumeratorOf") + UpperKey).str(); 6298 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6299 if (KnownSelectors.insert(Selectors.getNullarySelector(SelectorId))) { 6300 if (ReturnType.isNull()) { 6301 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6302 Builder.AddTextChunk("NSEnumerator *"); 6303 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6304 } 6305 6306 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName)); 6307 Results.AddResult(Result(Builder.TakeString(), UnorderedGetterPriority, 6308 CXCursor_ObjCInstanceMethodDecl)); 6309 } 6310 } 6311 6312 // - (type *)memberOfKey:(type *)object 6313 if (IsInstanceMethod && 6314 (ReturnType.isNull() || ReturnType->isObjCObjectPointerType())) { 6315 std::string SelectorName = (Twine("memberOf") + UpperKey).str(); 6316 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6317 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId))) { 6318 if (ReturnType.isNull()) { 6319 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6320 Builder.AddPlaceholderChunk("object-type"); 6321 Builder.AddTextChunk(" *"); 6322 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6323 } 6324 6325 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6326 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6327 if (ReturnType.isNull()) { 6328 Builder.AddPlaceholderChunk("object-type"); 6329 Builder.AddTextChunk(" *"); 6330 } else { 6331 Builder.AddTextChunk(GetCompletionTypeString(ReturnType, Context, 6332 Policy, 6333 Builder.getAllocator())); 6334 } 6335 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6336 Builder.AddTextChunk("object"); 6337 Results.AddResult(Result(Builder.TakeString(), UnorderedGetterPriority, 6338 CXCursor_ObjCInstanceMethodDecl)); 6339 } 6340 } 6341 6342 // Mutable unordered accessors 6343 // - (void)addKeyObject:(type *)object 6344 if (IsInstanceMethod && ReturnTypeMatchesVoid) { 6345 std::string SelectorName 6346 = (Twine("add") + UpperKey + Twine("Object")).str(); 6347 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6348 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId))) { 6349 if (ReturnType.isNull()) { 6350 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6351 Builder.AddTextChunk("void"); 6352 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6353 } 6354 6355 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6356 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6357 Builder.AddPlaceholderChunk("object-type"); 6358 Builder.AddTextChunk(" *"); 6359 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6360 Builder.AddTextChunk("object"); 6361 Results.AddResult(Result(Builder.TakeString(), UnorderedSetterPriority, 6362 CXCursor_ObjCInstanceMethodDecl)); 6363 } 6364 } 6365 6366 // - (void)addKey:(NSSet *)objects 6367 if (IsInstanceMethod && ReturnTypeMatchesVoid) { 6368 std::string SelectorName = (Twine("add") + UpperKey).str(); 6369 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6370 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId))) { 6371 if (ReturnType.isNull()) { 6372 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6373 Builder.AddTextChunk("void"); 6374 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6375 } 6376 6377 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6378 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6379 Builder.AddTextChunk("NSSet *"); 6380 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6381 Builder.AddTextChunk("objects"); 6382 Results.AddResult(Result(Builder.TakeString(), UnorderedSetterPriority, 6383 CXCursor_ObjCInstanceMethodDecl)); 6384 } 6385 } 6386 6387 // - (void)removeKeyObject:(type *)object 6388 if (IsInstanceMethod && ReturnTypeMatchesVoid) { 6389 std::string SelectorName 6390 = (Twine("remove") + UpperKey + Twine("Object")).str(); 6391 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6392 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId))) { 6393 if (ReturnType.isNull()) { 6394 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6395 Builder.AddTextChunk("void"); 6396 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6397 } 6398 6399 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6400 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6401 Builder.AddPlaceholderChunk("object-type"); 6402 Builder.AddTextChunk(" *"); 6403 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6404 Builder.AddTextChunk("object"); 6405 Results.AddResult(Result(Builder.TakeString(), UnorderedSetterPriority, 6406 CXCursor_ObjCInstanceMethodDecl)); 6407 } 6408 } 6409 6410 // - (void)removeKey:(NSSet *)objects 6411 if (IsInstanceMethod && ReturnTypeMatchesVoid) { 6412 std::string SelectorName = (Twine("remove") + UpperKey).str(); 6413 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6414 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId))) { 6415 if (ReturnType.isNull()) { 6416 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6417 Builder.AddTextChunk("void"); 6418 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6419 } 6420 6421 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6422 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6423 Builder.AddTextChunk("NSSet *"); 6424 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6425 Builder.AddTextChunk("objects"); 6426 Results.AddResult(Result(Builder.TakeString(), UnorderedSetterPriority, 6427 CXCursor_ObjCInstanceMethodDecl)); 6428 } 6429 } 6430 6431 // - (void)intersectKey:(NSSet *)objects 6432 if (IsInstanceMethod && ReturnTypeMatchesVoid) { 6433 std::string SelectorName = (Twine("intersect") + UpperKey).str(); 6434 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6435 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId))) { 6436 if (ReturnType.isNull()) { 6437 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6438 Builder.AddTextChunk("void"); 6439 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6440 } 6441 6442 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":")); 6443 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6444 Builder.AddTextChunk("NSSet *"); 6445 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6446 Builder.AddTextChunk("objects"); 6447 Results.AddResult(Result(Builder.TakeString(), UnorderedSetterPriority, 6448 CXCursor_ObjCInstanceMethodDecl)); 6449 } 6450 } 6451 6452 // Key-Value Observing 6453 // + (NSSet *)keyPathsForValuesAffectingKey 6454 if (!IsInstanceMethod && 6455 (ReturnType.isNull() || 6456 (ReturnType->isObjCObjectPointerType() && 6457 ReturnType->getAs<ObjCObjectPointerType>()->getInterfaceDecl() && 6458 ReturnType->getAs<ObjCObjectPointerType>()->getInterfaceDecl() 6459 ->getName() == "NSSet"))) { 6460 std::string SelectorName 6461 = (Twine("keyPathsForValuesAffecting") + UpperKey).str(); 6462 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6463 if (KnownSelectors.insert(Selectors.getNullarySelector(SelectorId))) { 6464 if (ReturnType.isNull()) { 6465 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6466 Builder.AddTextChunk("NSSet *"); 6467 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6468 } 6469 6470 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName)); 6471 Results.AddResult(Result(Builder.TakeString(), CCP_CodePattern, 6472 CXCursor_ObjCClassMethodDecl)); 6473 } 6474 } 6475 6476 // + (BOOL)automaticallyNotifiesObserversForKey 6477 if (!IsInstanceMethod && 6478 (ReturnType.isNull() || 6479 ReturnType->isIntegerType() || 6480 ReturnType->isBooleanType())) { 6481 std::string SelectorName 6482 = (Twine("automaticallyNotifiesObserversOf") + UpperKey).str(); 6483 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName); 6484 if (KnownSelectors.insert(Selectors.getNullarySelector(SelectorId))) { 6485 if (ReturnType.isNull()) { 6486 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6487 Builder.AddTextChunk("BOOL"); 6488 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6489 } 6490 6491 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName)); 6492 Results.AddResult(Result(Builder.TakeString(), CCP_CodePattern, 6493 CXCursor_ObjCClassMethodDecl)); 6494 } 6495 } 6496 } 6497 6498 void Sema::CodeCompleteObjCMethodDecl(Scope *S, 6499 bool IsInstanceMethod, 6500 ParsedType ReturnTy) { 6501 // Determine the return type of the method we're declaring, if 6502 // provided. 6503 QualType ReturnType = GetTypeFromParser(ReturnTy); 6504 Decl *IDecl = 0; 6505 if (CurContext->isObjCContainer()) { 6506 ObjCContainerDecl *OCD = dyn_cast<ObjCContainerDecl>(CurContext); 6507 IDecl = cast<Decl>(OCD); 6508 } 6509 // Determine where we should start searching for methods. 6510 ObjCContainerDecl *SearchDecl = 0; 6511 bool IsInImplementation = false; 6512 if (Decl *D = IDecl) { 6513 if (ObjCImplementationDecl *Impl = dyn_cast<ObjCImplementationDecl>(D)) { 6514 SearchDecl = Impl->getClassInterface(); 6515 IsInImplementation = true; 6516 } else if (ObjCCategoryImplDecl *CatImpl 6517 = dyn_cast<ObjCCategoryImplDecl>(D)) { 6518 SearchDecl = CatImpl->getCategoryDecl(); 6519 IsInImplementation = true; 6520 } else 6521 SearchDecl = dyn_cast<ObjCContainerDecl>(D); 6522 } 6523 6524 if (!SearchDecl && S) { 6525 if (DeclContext *DC = static_cast<DeclContext *>(S->getEntity())) 6526 SearchDecl = dyn_cast<ObjCContainerDecl>(DC); 6527 } 6528 6529 if (!SearchDecl) { 6530 HandleCodeCompleteResults(this, CodeCompleter, 6531 CodeCompletionContext::CCC_Other, 6532 0, 0); 6533 return; 6534 } 6535 6536 // Find all of the methods that we could declare/implement here. 6537 KnownMethodsMap KnownMethods; 6538 FindImplementableMethods(Context, SearchDecl, IsInstanceMethod, 6539 ReturnType, KnownMethods); 6540 6541 // Add declarations or definitions for each of the known methods. 6542 typedef CodeCompletionResult Result; 6543 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 6544 CodeCompletionContext::CCC_Other); 6545 Results.EnterNewScope(); 6546 PrintingPolicy Policy = getCompletionPrintingPolicy(*this); 6547 for (KnownMethodsMap::iterator M = KnownMethods.begin(), 6548 MEnd = KnownMethods.end(); 6549 M != MEnd; ++M) { 6550 ObjCMethodDecl *Method = M->second.first; 6551 CodeCompletionBuilder Builder(Results.getAllocator()); 6552 6553 // If the result type was not already provided, add it to the 6554 // pattern as (type). 6555 if (ReturnType.isNull()) 6556 AddObjCPassingTypeChunk(Method->getResultType(), Context, Policy, 6557 Builder); 6558 6559 Selector Sel = Method->getSelector(); 6560 6561 // Add the first part of the selector to the pattern. 6562 Builder.AddTypedTextChunk(Builder.getAllocator().CopyString( 6563 Sel.getNameForSlot(0))); 6564 6565 // Add parameters to the pattern. 6566 unsigned I = 0; 6567 for (ObjCMethodDecl::param_iterator P = Method->param_begin(), 6568 PEnd = Method->param_end(); 6569 P != PEnd; (void)++P, ++I) { 6570 // Add the part of the selector name. 6571 if (I == 0) 6572 Builder.AddTypedTextChunk(":"); 6573 else if (I < Sel.getNumArgs()) { 6574 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6575 Builder.AddTypedTextChunk( 6576 Builder.getAllocator().CopyString(Sel.getNameForSlot(I) + ":")); 6577 } else 6578 break; 6579 6580 // Add the parameter type. 6581 AddObjCPassingTypeChunk((*P)->getOriginalType(), Context, Policy, 6582 Builder); 6583 6584 if (IdentifierInfo *Id = (*P)->getIdentifier()) 6585 Builder.AddTextChunk(Builder.getAllocator().CopyString( Id->getName())); 6586 } 6587 6588 if (Method->isVariadic()) { 6589 if (Method->param_size() > 0) 6590 Builder.AddChunk(CodeCompletionString::CK_Comma); 6591 Builder.AddTextChunk("..."); 6592 } 6593 6594 if (IsInImplementation && Results.includeCodePatterns()) { 6595 // We will be defining the method here, so add a compound statement. 6596 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6597 Builder.AddChunk(CodeCompletionString::CK_LeftBrace); 6598 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 6599 if (!Method->getResultType()->isVoidType()) { 6600 // If the result type is not void, add a return clause. 6601 Builder.AddTextChunk("return"); 6602 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6603 Builder.AddPlaceholderChunk("expression"); 6604 Builder.AddChunk(CodeCompletionString::CK_SemiColon); 6605 } else 6606 Builder.AddPlaceholderChunk("statements"); 6607 6608 Builder.AddChunk(CodeCompletionString::CK_VerticalSpace); 6609 Builder.AddChunk(CodeCompletionString::CK_RightBrace); 6610 } 6611 6612 unsigned Priority = CCP_CodePattern; 6613 if (!M->second.second) 6614 Priority += CCD_InBaseClass; 6615 6616 Results.AddResult(Result(Builder.TakeString(), Priority, 6617 Method->isInstanceMethod() 6618 ? CXCursor_ObjCInstanceMethodDecl 6619 : CXCursor_ObjCClassMethodDecl)); 6620 } 6621 6622 // Add Key-Value-Coding and Key-Value-Observing accessor methods for all of 6623 // the properties in this class and its categories. 6624 if (Context.getLangOptions().ObjC2) { 6625 SmallVector<ObjCContainerDecl *, 4> Containers; 6626 Containers.push_back(SearchDecl); 6627 6628 VisitedSelectorSet KnownSelectors; 6629 for (KnownMethodsMap::iterator M = KnownMethods.begin(), 6630 MEnd = KnownMethods.end(); 6631 M != MEnd; ++M) 6632 KnownSelectors.insert(M->first); 6633 6634 6635 ObjCInterfaceDecl *IFace = dyn_cast<ObjCInterfaceDecl>(SearchDecl); 6636 if (!IFace) 6637 if (ObjCCategoryDecl *Category = dyn_cast<ObjCCategoryDecl>(SearchDecl)) 6638 IFace = Category->getClassInterface(); 6639 6640 if (IFace) { 6641 for (ObjCCategoryDecl *Category = IFace->getCategoryList(); Category; 6642 Category = Category->getNextClassCategory()) 6643 Containers.push_back(Category); 6644 } 6645 6646 for (unsigned I = 0, N = Containers.size(); I != N; ++I) { 6647 for (ObjCContainerDecl::prop_iterator P = Containers[I]->prop_begin(), 6648 PEnd = Containers[I]->prop_end(); 6649 P != PEnd; ++P) { 6650 AddObjCKeyValueCompletions(*P, IsInstanceMethod, ReturnType, Context, 6651 KnownSelectors, Results); 6652 } 6653 } 6654 } 6655 6656 Results.ExitScope(); 6657 6658 HandleCodeCompleteResults(this, CodeCompleter, 6659 CodeCompletionContext::CCC_Other, 6660 Results.data(),Results.size()); 6661 } 6662 6663 void Sema::CodeCompleteObjCMethodDeclSelector(Scope *S, 6664 bool IsInstanceMethod, 6665 bool AtParameterName, 6666 ParsedType ReturnTy, 6667 IdentifierInfo **SelIdents, 6668 unsigned NumSelIdents) { 6669 // If we have an external source, load the entire class method 6670 // pool from the AST file. 6671 if (ExternalSource) { 6672 for (uint32_t I = 0, N = ExternalSource->GetNumExternalSelectors(); 6673 I != N; ++I) { 6674 Selector Sel = ExternalSource->GetExternalSelector(I); 6675 if (Sel.isNull() || MethodPool.count(Sel)) 6676 continue; 6677 6678 ReadMethodPool(Sel); 6679 } 6680 } 6681 6682 // Build the set of methods we can see. 6683 typedef CodeCompletionResult Result; 6684 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 6685 CodeCompletionContext::CCC_Other); 6686 6687 if (ReturnTy) 6688 Results.setPreferredType(GetTypeFromParser(ReturnTy).getNonReferenceType()); 6689 6690 Results.EnterNewScope(); 6691 for (GlobalMethodPool::iterator M = MethodPool.begin(), 6692 MEnd = MethodPool.end(); 6693 M != MEnd; ++M) { 6694 for (ObjCMethodList *MethList = IsInstanceMethod ? &M->second.first : 6695 &M->second.second; 6696 MethList && MethList->Method; 6697 MethList = MethList->Next) { 6698 if (!isAcceptableObjCMethod(MethList->Method, MK_Any, SelIdents, 6699 NumSelIdents)) 6700 continue; 6701 6702 if (AtParameterName) { 6703 // Suggest parameter names we've seen before. 6704 if (NumSelIdents && NumSelIdents <= MethList->Method->param_size()) { 6705 ParmVarDecl *Param = MethList->Method->param_begin()[NumSelIdents-1]; 6706 if (Param->getIdentifier()) { 6707 CodeCompletionBuilder Builder(Results.getAllocator()); 6708 Builder.AddTypedTextChunk(Builder.getAllocator().CopyString( 6709 Param->getIdentifier()->getName())); 6710 Results.AddResult(Builder.TakeString()); 6711 } 6712 } 6713 6714 continue; 6715 } 6716 6717 Result R(MethList->Method, 0); 6718 R.StartParameter = NumSelIdents; 6719 R.AllParametersAreInformative = false; 6720 R.DeclaringEntity = true; 6721 Results.MaybeAddResult(R, CurContext); 6722 } 6723 } 6724 6725 Results.ExitScope(); 6726 HandleCodeCompleteResults(this, CodeCompleter, 6727 CodeCompletionContext::CCC_Other, 6728 Results.data(),Results.size()); 6729 } 6730 6731 void Sema::CodeCompletePreprocessorDirective(bool InConditional) { 6732 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 6733 CodeCompletionContext::CCC_PreprocessorDirective); 6734 Results.EnterNewScope(); 6735 6736 // #if <condition> 6737 CodeCompletionBuilder Builder(Results.getAllocator()); 6738 Builder.AddTypedTextChunk("if"); 6739 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6740 Builder.AddPlaceholderChunk("condition"); 6741 Results.AddResult(Builder.TakeString()); 6742 6743 // #ifdef <macro> 6744 Builder.AddTypedTextChunk("ifdef"); 6745 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6746 Builder.AddPlaceholderChunk("macro"); 6747 Results.AddResult(Builder.TakeString()); 6748 6749 // #ifndef <macro> 6750 Builder.AddTypedTextChunk("ifndef"); 6751 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6752 Builder.AddPlaceholderChunk("macro"); 6753 Results.AddResult(Builder.TakeString()); 6754 6755 if (InConditional) { 6756 // #elif <condition> 6757 Builder.AddTypedTextChunk("elif"); 6758 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6759 Builder.AddPlaceholderChunk("condition"); 6760 Results.AddResult(Builder.TakeString()); 6761 6762 // #else 6763 Builder.AddTypedTextChunk("else"); 6764 Results.AddResult(Builder.TakeString()); 6765 6766 // #endif 6767 Builder.AddTypedTextChunk("endif"); 6768 Results.AddResult(Builder.TakeString()); 6769 } 6770 6771 // #include "header" 6772 Builder.AddTypedTextChunk("include"); 6773 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6774 Builder.AddTextChunk("\""); 6775 Builder.AddPlaceholderChunk("header"); 6776 Builder.AddTextChunk("\""); 6777 Results.AddResult(Builder.TakeString()); 6778 6779 // #include <header> 6780 Builder.AddTypedTextChunk("include"); 6781 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6782 Builder.AddTextChunk("<"); 6783 Builder.AddPlaceholderChunk("header"); 6784 Builder.AddTextChunk(">"); 6785 Results.AddResult(Builder.TakeString()); 6786 6787 // #define <macro> 6788 Builder.AddTypedTextChunk("define"); 6789 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6790 Builder.AddPlaceholderChunk("macro"); 6791 Results.AddResult(Builder.TakeString()); 6792 6793 // #define <macro>(<args>) 6794 Builder.AddTypedTextChunk("define"); 6795 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6796 Builder.AddPlaceholderChunk("macro"); 6797 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6798 Builder.AddPlaceholderChunk("args"); 6799 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6800 Results.AddResult(Builder.TakeString()); 6801 6802 // #undef <macro> 6803 Builder.AddTypedTextChunk("undef"); 6804 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6805 Builder.AddPlaceholderChunk("macro"); 6806 Results.AddResult(Builder.TakeString()); 6807 6808 // #line <number> 6809 Builder.AddTypedTextChunk("line"); 6810 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6811 Builder.AddPlaceholderChunk("number"); 6812 Results.AddResult(Builder.TakeString()); 6813 6814 // #line <number> "filename" 6815 Builder.AddTypedTextChunk("line"); 6816 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6817 Builder.AddPlaceholderChunk("number"); 6818 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6819 Builder.AddTextChunk("\""); 6820 Builder.AddPlaceholderChunk("filename"); 6821 Builder.AddTextChunk("\""); 6822 Results.AddResult(Builder.TakeString()); 6823 6824 // #error <message> 6825 Builder.AddTypedTextChunk("error"); 6826 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6827 Builder.AddPlaceholderChunk("message"); 6828 Results.AddResult(Builder.TakeString()); 6829 6830 // #pragma <arguments> 6831 Builder.AddTypedTextChunk("pragma"); 6832 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6833 Builder.AddPlaceholderChunk("arguments"); 6834 Results.AddResult(Builder.TakeString()); 6835 6836 if (getLangOptions().ObjC1) { 6837 // #import "header" 6838 Builder.AddTypedTextChunk("import"); 6839 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6840 Builder.AddTextChunk("\""); 6841 Builder.AddPlaceholderChunk("header"); 6842 Builder.AddTextChunk("\""); 6843 Results.AddResult(Builder.TakeString()); 6844 6845 // #import <header> 6846 Builder.AddTypedTextChunk("import"); 6847 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6848 Builder.AddTextChunk("<"); 6849 Builder.AddPlaceholderChunk("header"); 6850 Builder.AddTextChunk(">"); 6851 Results.AddResult(Builder.TakeString()); 6852 } 6853 6854 // #include_next "header" 6855 Builder.AddTypedTextChunk("include_next"); 6856 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6857 Builder.AddTextChunk("\""); 6858 Builder.AddPlaceholderChunk("header"); 6859 Builder.AddTextChunk("\""); 6860 Results.AddResult(Builder.TakeString()); 6861 6862 // #include_next <header> 6863 Builder.AddTypedTextChunk("include_next"); 6864 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6865 Builder.AddTextChunk("<"); 6866 Builder.AddPlaceholderChunk("header"); 6867 Builder.AddTextChunk(">"); 6868 Results.AddResult(Builder.TakeString()); 6869 6870 // #warning <message> 6871 Builder.AddTypedTextChunk("warning"); 6872 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6873 Builder.AddPlaceholderChunk("message"); 6874 Results.AddResult(Builder.TakeString()); 6875 6876 // Note: #ident and #sccs are such crazy anachronisms that we don't provide 6877 // completions for them. And __include_macros is a Clang-internal extension 6878 // that we don't want to encourage anyone to use. 6879 6880 // FIXME: we don't support #assert or #unassert, so don't suggest them. 6881 Results.ExitScope(); 6882 6883 HandleCodeCompleteResults(this, CodeCompleter, 6884 CodeCompletionContext::CCC_PreprocessorDirective, 6885 Results.data(), Results.size()); 6886 } 6887 6888 void Sema::CodeCompleteInPreprocessorConditionalExclusion(Scope *S) { 6889 CodeCompleteOrdinaryName(S, 6890 S->getFnParent()? Sema::PCC_RecoveryInFunction 6891 : Sema::PCC_Namespace); 6892 } 6893 6894 void Sema::CodeCompletePreprocessorMacroName(bool IsDefinition) { 6895 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 6896 IsDefinition? CodeCompletionContext::CCC_MacroName 6897 : CodeCompletionContext::CCC_MacroNameUse); 6898 if (!IsDefinition && (!CodeCompleter || CodeCompleter->includeMacros())) { 6899 // Add just the names of macros, not their arguments. 6900 CodeCompletionBuilder Builder(Results.getAllocator()); 6901 Results.EnterNewScope(); 6902 for (Preprocessor::macro_iterator M = PP.macro_begin(), 6903 MEnd = PP.macro_end(); 6904 M != MEnd; ++M) { 6905 Builder.AddTypedTextChunk(Builder.getAllocator().CopyString( 6906 M->first->getName())); 6907 Results.AddResult(Builder.TakeString()); 6908 } 6909 Results.ExitScope(); 6910 } else if (IsDefinition) { 6911 // FIXME: Can we detect when the user just wrote an include guard above? 6912 } 6913 6914 HandleCodeCompleteResults(this, CodeCompleter, Results.getCompletionContext(), 6915 Results.data(), Results.size()); 6916 } 6917 6918 void Sema::CodeCompletePreprocessorExpression() { 6919 ResultBuilder Results(*this, CodeCompleter->getAllocator(), 6920 CodeCompletionContext::CCC_PreprocessorExpression); 6921 6922 if (!CodeCompleter || CodeCompleter->includeMacros()) 6923 AddMacroResults(PP, Results); 6924 6925 // defined (<macro>) 6926 Results.EnterNewScope(); 6927 CodeCompletionBuilder Builder(Results.getAllocator()); 6928 Builder.AddTypedTextChunk("defined"); 6929 Builder.AddChunk(CodeCompletionString::CK_HorizontalSpace); 6930 Builder.AddChunk(CodeCompletionString::CK_LeftParen); 6931 Builder.AddPlaceholderChunk("macro"); 6932 Builder.AddChunk(CodeCompletionString::CK_RightParen); 6933 Results.AddResult(Builder.TakeString()); 6934 Results.ExitScope(); 6935 6936 HandleCodeCompleteResults(this, CodeCompleter, 6937 CodeCompletionContext::CCC_PreprocessorExpression, 6938 Results.data(), Results.size()); 6939 } 6940 6941 void Sema::CodeCompletePreprocessorMacroArgument(Scope *S, 6942 IdentifierInfo *Macro, 6943 MacroInfo *MacroInfo, 6944 unsigned Argument) { 6945 // FIXME: In the future, we could provide "overload" results, much like we 6946 // do for function calls. 6947 6948 // Now just ignore this. There will be another code-completion callback 6949 // for the expanded tokens. 6950 } 6951 6952 void Sema::CodeCompleteNaturalLanguage() { 6953 HandleCodeCompleteResults(this, CodeCompleter, 6954 CodeCompletionContext::CCC_NaturalLanguage, 6955 0, 0); 6956 } 6957 6958 void Sema::GatherGlobalCodeCompletions(CodeCompletionAllocator &Allocator, 6959 SmallVectorImpl<CodeCompletionResult> &Results) { 6960 ResultBuilder Builder(*this, Allocator, CodeCompletionContext::CCC_Recovery); 6961 if (!CodeCompleter || CodeCompleter->includeGlobals()) { 6962 CodeCompletionDeclConsumer Consumer(Builder, 6963 Context.getTranslationUnitDecl()); 6964 LookupVisibleDecls(Context.getTranslationUnitDecl(), LookupAnyName, 6965 Consumer); 6966 } 6967 6968 if (!CodeCompleter || CodeCompleter->includeMacros()) 6969 AddMacroResults(PP, Builder); 6970 6971 Results.clear(); 6972 Results.insert(Results.end(), 6973 Builder.data(), Builder.data() + Builder.size()); 6974 } 6975