clang 24.0.0git
SemaCodeComplete.cpp
Go to the documentation of this file.
1//===---------------- SemaCodeComplete.cpp - Code Completion ----*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file defines the code-completion semantic actions.
10//
11//===----------------------------------------------------------------------===//
13#include "clang/AST/Decl.h"
14#include "clang/AST/DeclBase.h"
15#include "clang/AST/DeclCXX.h"
16#include "clang/AST/DeclObjC.h"
19#include "clang/AST/Expr.h"
20#include "clang/AST/ExprCXX.h"
22#include "clang/AST/ExprObjC.h"
26#include "clang/AST/Type.h"
34#include "clang/Lex/MacroInfo.h"
37#include "clang/Sema/DeclSpec.h"
40#include "clang/Sema/Lookup.h"
41#include "clang/Sema/Overload.h"
44#include "clang/Sema/Scope.h"
46#include "clang/Sema/Sema.h"
48#include "clang/Sema/SemaObjC.h"
49#include "llvm/ADT/ArrayRef.h"
50#include "llvm/ADT/DenseSet.h"
51#include "llvm/ADT/SmallBitVector.h"
52#include "llvm/ADT/SmallPtrSet.h"
53#include "llvm/ADT/SmallString.h"
54#include "llvm/ADT/StringSet.h"
55#include "llvm/ADT/StringSwitch.h"
56#include "llvm/ADT/Twine.h"
57#include "llvm/ADT/iterator_range.h"
58#include "llvm/Support/Casting.h"
59#include "llvm/Support/FileSystem.h"
60#include "llvm/Support/Path.h"
61#include "llvm/Support/VirtualFileSystem.h"
62#include "llvm/Support/raw_ostream.h"
63
64#include <list>
65#include <map>
66#include <optional>
67#include <string>
68#include <vector>
69
70using namespace clang;
71using namespace sema;
72
73namespace {
74/// A container of code-completion results.
75class ResultBuilder {
76public:
77 /// The type of a name-lookup filter, which can be provided to the
78 /// name-lookup routines to specify which declarations should be included in
79 /// the result set (when it returns true) and which declarations should be
80 /// filtered out (returns false).
81 typedef bool (ResultBuilder::*LookupFilter)(const NamedDecl *) const;
82
83 typedef CodeCompletionResult Result;
84
85private:
86 /// The actual results we have found.
87 std::vector<Result> Results;
88
89 /// A record of all of the declarations we have found and placed
90 /// into the result set, used to ensure that no declaration ever gets into
91 /// the result set twice.
92 llvm::SmallPtrSet<const Decl *, 16> AllDeclsFound;
93
94 typedef std::pair<const NamedDecl *, unsigned> DeclIndexPair;
95
96 /// An entry in the shadow map, which is optimized to store
97 /// a single (declaration, index) mapping (the common case) but
98 /// can also store a list of (declaration, index) mappings.
99 class ShadowMapEntry {
100 typedef SmallVector<DeclIndexPair, 4> DeclIndexPairVector;
101
102 /// Contains either the solitary NamedDecl * or a vector
103 /// of (declaration, index) pairs.
104 llvm::PointerUnion<const NamedDecl *, DeclIndexPairVector *> DeclOrVector;
105
106 /// When the entry contains a single declaration, this is
107 /// the index associated with that entry.
108 unsigned SingleDeclIndex = 0;
109
110 public:
111 ShadowMapEntry() = default;
112 ShadowMapEntry(const ShadowMapEntry &) = delete;
113 ShadowMapEntry(ShadowMapEntry &&Move) { *this = std::move(Move); }
114 ShadowMapEntry &operator=(const ShadowMapEntry &) = delete;
115 ShadowMapEntry &operator=(ShadowMapEntry &&Move) {
116 SingleDeclIndex = Move.SingleDeclIndex;
117 DeclOrVector = Move.DeclOrVector;
118 Move.DeclOrVector = nullptr;
119 return *this;
120 }
121
122 void Add(const NamedDecl *ND, unsigned Index) {
123 if (DeclOrVector.isNull()) {
124 // 0 - > 1 elements: just set the single element information.
125 DeclOrVector = ND;
126 SingleDeclIndex = Index;
127 return;
128 }
129
130 if (const NamedDecl *PrevND = dyn_cast<const NamedDecl *>(DeclOrVector)) {
131 // 1 -> 2 elements: create the vector of results and push in the
132 // existing declaration.
133 DeclIndexPairVector *Vec = new DeclIndexPairVector;
134 Vec->push_back(DeclIndexPair(PrevND, SingleDeclIndex));
135 DeclOrVector = Vec;
136 }
137
138 // Add the new element to the end of the vector.
139 cast<DeclIndexPairVector *>(DeclOrVector)
140 ->push_back(DeclIndexPair(ND, Index));
141 }
142
143 ~ShadowMapEntry() {
144 if (DeclIndexPairVector *Vec =
145 dyn_cast_if_present<DeclIndexPairVector *>(DeclOrVector)) {
146 delete Vec;
147 DeclOrVector = ((NamedDecl *)nullptr);
148 }
149 }
150
151 // Iteration.
152 class iterator;
153 iterator begin() const;
154 iterator end() const;
155 };
156
157 /// A mapping from declaration names to the declarations that have
158 /// this name within a particular scope and their index within the list of
159 /// results.
160 typedef llvm::DenseMap<DeclarationName, ShadowMapEntry> ShadowMap;
161
162 /// The semantic analysis object for which results are being
163 /// produced.
164 Sema &SemaRef;
165
166 /// The allocator used to allocate new code-completion strings.
167 CodeCompletionAllocator &Allocator;
168
169 CodeCompletionTUInfo &CCTUInfo;
170
171 /// If non-NULL, a filter function used to remove any code-completion
172 /// results that are not desirable.
173 LookupFilter Filter;
174
175 /// Whether we should allow declarations as
176 /// nested-name-specifiers that would otherwise be filtered out.
177 bool AllowNestedNameSpecifiers;
178
179 /// If set, the type that we would prefer our resulting value
180 /// declarations to have.
181 ///
182 /// Closely matching the preferred type gives a boost to a result's
183 /// priority.
184 CanQualType PreferredType;
185
186 /// A list of shadow maps, which is used to model name hiding at
187 /// different levels of, e.g., the inheritance hierarchy.
188 std::list<ShadowMap> ShadowMaps;
189
190 /// Overloaded C++ member functions found by SemaLookup.
191 /// Used to determine when one overload is dominated by another.
192 llvm::DenseMap<std::pair<DeclContext *, /*Name*/uintptr_t>, ShadowMapEntry>
193 OverloadMap;
194
195 /// If we're potentially referring to a C++ member function, the set
196 /// of qualifiers applied to the object type.
197 Qualifiers ObjectTypeQualifiers;
198 /// The kind of the object expression, for rvalue/lvalue overloads.
199 ExprValueKind ObjectKind;
200
201 /// Whether the \p ObjectTypeQualifiers field is active.
202 bool HasObjectTypeQualifiers;
203
204 // Whether the member function is using an explicit object parameter
205 bool IsExplicitObjectMemberFunction;
206
207 /// The selector that we prefer.
208 Selector PreferredSelector;
209
210 /// The completion context in which we are gathering results.
211 CodeCompletionContext CompletionContext;
212
213 /// If we are in an instance method definition, the \@implementation
214 /// object.
215 ObjCImplementationDecl *ObjCImplementation;
216
217 void AdjustResultPriorityForDecl(Result &R);
218
219 void MaybeAddConstructorResults(Result R);
220
221public:
222 explicit ResultBuilder(Sema &SemaRef, CodeCompletionAllocator &Allocator,
223 CodeCompletionTUInfo &CCTUInfo,
224 const CodeCompletionContext &CompletionContext,
225 LookupFilter Filter = nullptr)
226 : SemaRef(SemaRef), Allocator(Allocator), CCTUInfo(CCTUInfo),
227 Filter(Filter), AllowNestedNameSpecifiers(false),
228 HasObjectTypeQualifiers(false), IsExplicitObjectMemberFunction(false),
229 CompletionContext(CompletionContext), ObjCImplementation(nullptr) {
230 // If this is an Objective-C instance method definition, dig out the
231 // corresponding implementation.
232 switch (CompletionContext.getKind()) {
233 case CodeCompletionContext::CCC_Expression:
234 case CodeCompletionContext::CCC_ObjCMessageReceiver:
235 case CodeCompletionContext::CCC_ParenthesizedExpression:
236 case CodeCompletionContext::CCC_Statement:
237 case CodeCompletionContext::CCC_TopLevelOrExpression:
238 case CodeCompletionContext::CCC_Recovery:
239 if (ObjCMethodDecl *Method = SemaRef.getCurMethodDecl())
240 if (Method->isInstanceMethod())
241 if (ObjCInterfaceDecl *Interface = Method->getClassInterface())
242 ObjCImplementation = Interface->getImplementation();
243 break;
244
245 default:
246 break;
247 }
248 }
249
250 /// Determine the priority for a reference to the given declaration.
251 unsigned getBasePriority(const NamedDecl *D);
252
253 /// Whether we should include code patterns in the completion
254 /// results.
255 bool includeCodePatterns() const {
256 return SemaRef.CodeCompletion().CodeCompleter &&
257 SemaRef.CodeCompletion().CodeCompleter->includeCodePatterns();
258 }
259
260 /// Set the filter used for code-completion results.
261 void setFilter(LookupFilter Filter) { this->Filter = Filter; }
262
263 Result *data() { return Results.empty() ? nullptr : &Results.front(); }
264 unsigned size() const { return Results.size(); }
265 bool empty() const { return Results.empty(); }
266
267 /// Specify the preferred type.
268 void setPreferredType(QualType T) {
269 PreferredType = SemaRef.Context.getCanonicalType(T);
270 }
271
272 /// Set the cv-qualifiers on the object type, for us in filtering
273 /// calls to member functions.
274 ///
275 /// When there are qualifiers in this set, they will be used to filter
276 /// out member functions that aren't available (because there will be a
277 /// cv-qualifier mismatch) or prefer functions with an exact qualifier
278 /// match.
279 void setObjectTypeQualifiers(Qualifiers Quals, ExprValueKind Kind) {
280 ObjectTypeQualifiers = Quals;
281 ObjectKind = Kind;
282 HasObjectTypeQualifiers = true;
283 }
284
285 void setExplicitObjectMemberFn(bool IsExplicitObjectFn) {
286 IsExplicitObjectMemberFunction = IsExplicitObjectFn;
287 }
288
289 /// Set the preferred selector.
290 ///
291 /// When an Objective-C method declaration result is added, and that
292 /// method's selector matches this preferred selector, we give that method
293 /// a slight priority boost.
294 void setPreferredSelector(Selector Sel) { PreferredSelector = Sel; }
295
296 /// Retrieve the code-completion context for which results are
297 /// being collected.
298 const CodeCompletionContext &getCompletionContext() const {
299 return CompletionContext;
300 }
301
302 /// Specify whether nested-name-specifiers are allowed.
303 void allowNestedNameSpecifiers(bool Allow = true) {
304 AllowNestedNameSpecifiers = Allow;
305 }
306
307 /// Return the semantic analysis object for which we are collecting
308 /// code completion results.
309 Sema &getSema() const { return SemaRef; }
310
311 /// Retrieve the allocator used to allocate code completion strings.
312 CodeCompletionAllocator &getAllocator() const { return Allocator; }
313
314 CodeCompletionTUInfo &getCodeCompletionTUInfo() const { return CCTUInfo; }
315
316 /// Determine whether the given declaration is at all interesting
317 /// as a code-completion result.
318 ///
319 /// \param ND the declaration that we are inspecting.
320 ///
321 /// \param AsNestedNameSpecifier will be set true if this declaration is
322 /// only interesting when it is a nested-name-specifier.
323 bool isInterestingDecl(const NamedDecl *ND,
324 bool &AsNestedNameSpecifier) const;
325
326 /// Decide whether or not a use of function Decl can be a call.
327 ///
328 /// \param ND the function declaration.
329 ///
330 /// \param BaseExprType the object type in a member access expression,
331 /// if any.
332 bool canFunctionBeCalled(const NamedDecl *ND, QualType BaseExprType) const;
333
334 /// Decide whether or not a use of member function Decl can be a call.
335 ///
336 /// \param Method the function declaration.
337 ///
338 /// \param BaseExprType the object type in a member access expression,
339 /// if any.
340 bool canCxxMethodBeCalled(const CXXMethodDecl *Method,
341 QualType BaseExprType) const;
342
343 /// Check whether the result is hidden by the Hiding declaration.
344 ///
345 /// \returns true if the result is hidden and cannot be found, false if
346 /// the hidden result could still be found. When false, \p R may be
347 /// modified to describe how the result can be found (e.g., via extra
348 /// qualification).
349 bool CheckHiddenResult(Result &R, DeclContext *CurContext,
350 const NamedDecl *Hiding);
351
352 /// Add a new result to this result set (if it isn't already in one
353 /// of the shadow maps), or replace an existing result (for, e.g., a
354 /// redeclaration).
355 ///
356 /// \param R the result to add (if it is unique).
357 ///
358 /// \param CurContext the context in which this result will be named.
359 void MaybeAddResult(Result R, DeclContext *CurContext = nullptr);
360
361 /// Add a new result to this result set, where we already know
362 /// the hiding declaration (if any).
363 ///
364 /// \param R the result to add (if it is unique).
365 ///
366 /// \param CurContext the context in which this result will be named.
367 ///
368 /// \param Hiding the declaration that hides the result.
369 ///
370 /// \param InBaseClass whether the result was found in a base
371 /// class of the searched context.
372 ///
373 /// \param BaseExprType the type of expression that precedes the "." or "->"
374 /// in a member access expression.
375 void AddResult(Result R, DeclContext *CurContext, NamedDecl *Hiding,
376 bool InBaseClass, QualType BaseExprType,
377 bool IsInDeclarationContext, bool IsAddressOfOperand);
378
379 /// Add a new non-declaration result to this result set.
380 void AddResult(Result R);
381
382 /// Enter into a new scope.
383 void EnterNewScope();
384
385 /// Exit from the current scope.
386 void ExitScope();
387
388 /// Ignore this declaration, if it is seen again.
389 void Ignore(const Decl *D) { AllDeclsFound.insert(D->getCanonicalDecl()); }
390
391 /// Add a visited context.
392 void addVisitedContext(DeclContext *Ctx) {
393 CompletionContext.addVisitedContext(Ctx);
394 }
395
396 /// \name Name lookup predicates
397 ///
398 /// These predicates can be passed to the name lookup functions to filter the
399 /// results of name lookup. All of the predicates have the same type, so that
400 ///
401 //@{
402 bool IsOrdinaryName(const NamedDecl *ND) const;
403 bool IsOrdinaryNonTypeName(const NamedDecl *ND) const;
404 bool IsIntegralConstantValue(const NamedDecl *ND) const;
405 bool IsOrdinaryNonValueName(const NamedDecl *ND) const;
406 bool IsNestedNameSpecifier(const NamedDecl *ND) const;
407 bool IsEnum(const NamedDecl *ND) const;
408 bool IsClassOrStruct(const NamedDecl *ND) const;
409 bool IsUnion(const NamedDecl *ND) const;
410 bool IsNamespace(const NamedDecl *ND) const;
411 bool IsNamespaceOrAlias(const NamedDecl *ND) const;
412 bool IsType(const NamedDecl *ND) const;
413 bool IsMember(const NamedDecl *ND) const;
414 bool IsOffsetofField(const NamedDecl *ND) const;
415 bool IsObjCIvar(const NamedDecl *ND) const;
416 bool IsObjCMessageReceiver(const NamedDecl *ND) const;
417 bool IsObjCMessageReceiverOrLambdaCapture(const NamedDecl *ND) const;
418 bool IsObjCCollection(const NamedDecl *ND) const;
419 bool IsImpossibleToSatisfy(const NamedDecl *ND) const;
420 //@}
421};
422
423// Traverse declarations of the function (in a deterministic order,
424// for consistency) to find one which has parameter names.
425// For simplicity, consider a redecl to have parameter names
426// if at least one parameter has a name.
427const FunctionDecl *BetterSignature(const FunctionDecl *Function,
428 unsigned Start) {
429 auto ParaCount = Function->getNumParams();
430 // Note that `redecls()` traverses in a circular order from the current decl,
431 // so for consistency we have to first get the first declaration.
432 for (auto *Redecl : Function->getFirstDecl()->redecls()) {
433 // The callers will expect to be able to use the same index from the initial
434 // function on the redeclaration. While we do not expect this to happen,
435 // this is a failsafe.
436 if (Redecl->getNumParams() < ParaCount)
437 continue;
438 for (unsigned P = Start, N = Redecl->getNumParams(); P != N; ++P)
439 if (Redecl->getParamDecl(P)->getIdentifier())
440 return Redecl;
441 }
442 return Function;
443}
444} // namespace
445
447 if (!Enabled)
448 return;
449 if (isa<BlockDecl>(S.CurContext)) {
450 if (sema::BlockScopeInfo *BSI = S.getCurBlock()) {
451 ComputeType = nullptr;
452 Type = BSI->ReturnType;
453 ExpectedLoc = Tok;
454 }
455 } else if (const auto *Function = dyn_cast<FunctionDecl>(S.CurContext)) {
456 ComputeType = nullptr;
457 Type = Function->getReturnType();
458 ExpectedLoc = Tok;
459 } else if (const auto *Method = dyn_cast<ObjCMethodDecl>(S.CurContext)) {
460 ComputeType = nullptr;
461 Type = Method->getReturnType();
462 ExpectedLoc = Tok;
463 }
464}
465
467 if (!Enabled)
468 return;
469 auto *VD = llvm::dyn_cast_or_null<ValueDecl>(D);
470 ComputeType = nullptr;
471 Type = VD ? VD->getType() : QualType();
472 ExpectedLoc = Tok;
473}
474
475static const FieldDecl *lookupDirectField(RecordDecl *RD, const Designator &D);
477 ASTContext &Context, QualType BaseType, const Designation &Desig,
478 HeuristicResolver &Resolver,
479 llvm::function_ref<const FieldDecl *(RecordDecl *, const Designator &)>
480 LookupField);
481
483 QualType BaseType,
484 const Designation &D) {
485 if (!Enabled)
486 return;
487 ComputeType = nullptr;
488 HeuristicResolver Resolver(*Ctx);
489 Type = getDesignatedType(*Ctx, BaseType, D, Resolver, lookupDirectField);
490 ExpectedLoc = Tok;
491}
492
494 SourceLocation Tok, llvm::function_ref<QualType()> ComputeType) {
495 if (!Enabled)
496 return;
497 this->ComputeType = ComputeType;
498 Type = QualType();
499 ExpectedLoc = Tok;
500}
501
503 SourceLocation LParLoc) {
504 if (!Enabled)
505 return;
506 // expected type for parenthesized expression does not change.
507 if (ExpectedLoc == LParLoc)
508 ExpectedLoc = Tok;
509}
510
512 tok::TokenKind Op) {
513 if (!LHS)
514 return QualType();
515
516 QualType LHSType = LHS->getType();
517 if (LHSType->isPointerType()) {
518 if (Op == tok::plus || Op == tok::plusequal || Op == tok::minusequal)
520 // Pointer difference is more common than subtracting an int from a pointer.
521 if (Op == tok::minus)
522 return LHSType;
523 }
524
525 switch (Op) {
526 // No way to infer the type of RHS from LHS.
527 case tok::comma:
528 return QualType();
529 // Prefer the type of the left operand for all of these.
530 // Arithmetic operations.
531 case tok::plus:
532 case tok::plusequal:
533 case tok::minus:
534 case tok::minusequal:
535 case tok::percent:
536 case tok::percentequal:
537 case tok::slash:
538 case tok::slashequal:
539 case tok::star:
540 case tok::starequal:
541 // Assignment.
542 case tok::equal:
543 // Comparison operators.
544 case tok::equalequal:
545 case tok::exclaimequal:
546 case tok::less:
547 case tok::lessequal:
548 case tok::greater:
549 case tok::greaterequal:
550 case tok::spaceship:
551 return LHS->getType();
552 // Binary shifts are often overloaded, so don't try to guess those.
553 case tok::greatergreater:
554 case tok::greatergreaterequal:
555 case tok::lessless:
556 case tok::lesslessequal:
557 if (LHSType->isIntegralOrEnumerationType())
558 return S.getASTContext().IntTy;
559 return QualType();
560 // Logical operators, assume we want bool.
561 case tok::ampamp:
562 case tok::pipepipe:
563 return S.getASTContext().BoolTy;
564 // Operators often used for bit manipulation are typically used with the type
565 // of the left argument.
566 case tok::pipe:
567 case tok::pipeequal:
568 case tok::caret:
569 case tok::caretequal:
570 case tok::amp:
571 case tok::ampequal:
572 if (LHSType->isIntegralOrEnumerationType())
573 return LHSType;
574 return QualType();
575 // RHS should be a pointer to a member of the 'LHS' type, but we can't give
576 // any particular type here.
577 case tok::periodstar:
578 case tok::arrowstar:
579 return QualType();
580 default:
581 // FIXME(ibiryukov): handle the missing op, re-add the assertion.
582 // assert(false && "unhandled binary op");
583 return QualType();
584 }
585}
586
587/// Get preferred type for an argument of an unary expression. \p ContextType is
588/// preferred type of the whole unary expression.
590 tok::TokenKind Op) {
591 switch (Op) {
592 case tok::exclaim:
593 return S.getASTContext().BoolTy;
594 case tok::amp:
595 if (!ContextType.isNull() && ContextType->isPointerType())
596 return ContextType->getPointeeType();
597 return QualType();
598 case tok::star:
599 if (ContextType.isNull())
600 return QualType();
601 return S.getASTContext().getPointerType(ContextType.getNonReferenceType());
602 case tok::plus:
603 case tok::minus:
604 case tok::tilde:
605 case tok::minusminus:
606 case tok::plusplus:
607 if (ContextType.isNull())
608 return S.getASTContext().IntTy;
609 // leave as is, these operators typically return the same type.
610 return ContextType;
611 case tok::kw___real:
612 case tok::kw___imag:
613 return QualType();
614 default:
615 assert(false && "unhandled unary op");
616 return QualType();
617 }
618}
619
621 tok::TokenKind Op) {
622 if (!Enabled)
623 return;
624 ComputeType = nullptr;
625 Type = getPreferredTypeOfBinaryRHS(S, LHS, Op);
626 ExpectedLoc = Tok;
627}
628
630 Expr *Base) {
631 if (!Enabled || !Base)
632 return;
633 // Do we have expected type for Base?
634 if (ExpectedLoc != Base->getBeginLoc())
635 return;
636 // Keep the expected type, only update the location.
637 ExpectedLoc = Tok;
638}
639
641 tok::TokenKind OpKind,
642 SourceLocation OpLoc) {
643 if (!Enabled)
644 return;
645 ComputeType = nullptr;
646 Type = getPreferredTypeOfUnaryArg(S, this->get(OpLoc), OpKind);
647 ExpectedLoc = Tok;
648}
649
651 Expr *LHS) {
652 if (!Enabled)
653 return;
654 ComputeType = nullptr;
655 Type = S.getASTContext().IntTy;
656 ExpectedLoc = Tok;
657}
658
661 if (!Enabled)
662 return;
663 ComputeType = nullptr;
664 Type = !CastType.isNull() ? CastType.getCanonicalType() : QualType();
665 ExpectedLoc = Tok;
666}
667
669 if (!Enabled)
670 return;
671 ComputeType = nullptr;
672 Type = S.getASTContext().BoolTy;
673 ExpectedLoc = Tok;
674}
675
677 llvm::PointerUnion<const NamedDecl *, const DeclIndexPair *> DeclOrIterator;
678 unsigned SingleDeclIndex;
679
680public:
681 typedef DeclIndexPair value_type;
683 typedef std::ptrdiff_t difference_type;
684 typedef std::input_iterator_tag iterator_category;
685
686 class pointer {
687 DeclIndexPair Value;
688
689 public:
690 pointer(const DeclIndexPair &Value) : Value(Value) {}
691
692 const DeclIndexPair *operator->() const { return &Value; }
693 };
694
695 iterator() : DeclOrIterator((NamedDecl *)nullptr), SingleDeclIndex(0) {}
696
697 iterator(const NamedDecl *SingleDecl, unsigned Index)
698 : DeclOrIterator(SingleDecl), SingleDeclIndex(Index) {}
699
700 iterator(const DeclIndexPair *Iterator)
701 : DeclOrIterator(Iterator), SingleDeclIndex(0) {}
702
704 if (isa<const NamedDecl *>(DeclOrIterator)) {
705 DeclOrIterator = (NamedDecl *)nullptr;
706 SingleDeclIndex = 0;
707 return *this;
708 }
709
710 const DeclIndexPair *I = cast<const DeclIndexPair *>(DeclOrIterator);
711 ++I;
712 DeclOrIterator = I;
713 return *this;
714 }
715
716 /*iterator operator++(int) {
717 iterator tmp(*this);
718 ++(*this);
719 return tmp;
720 }*/
721
723 if (const NamedDecl *ND = dyn_cast<const NamedDecl *>(DeclOrIterator))
724 return reference(ND, SingleDeclIndex);
725
726 return *cast<const DeclIndexPair *>(DeclOrIterator);
727 }
728
729 pointer operator->() const { return pointer(**this); }
730
731 friend bool operator==(const iterator &X, const iterator &Y) {
732 return X.DeclOrIterator.getOpaqueValue() ==
733 Y.DeclOrIterator.getOpaqueValue() &&
734 X.SingleDeclIndex == Y.SingleDeclIndex;
735 }
736
737 friend bool operator!=(const iterator &X, const iterator &Y) {
738 return !(X == Y);
739 }
740};
741
743ResultBuilder::ShadowMapEntry::begin() const {
744 if (DeclOrVector.isNull())
745 return iterator();
746
747 if (const NamedDecl *ND = dyn_cast<const NamedDecl *>(DeclOrVector))
748 return iterator(ND, SingleDeclIndex);
749
750 return iterator(cast<DeclIndexPairVector *>(DeclOrVector)->begin());
751}
752
754ResultBuilder::ShadowMapEntry::end() const {
755 if (isa<const NamedDecl *>(DeclOrVector) || DeclOrVector.isNull())
756 return iterator();
757
758 return iterator(cast<DeclIndexPairVector *>(DeclOrVector)->end());
759}
760
761/// Compute the qualification required to get from the current context
762/// (\p CurContext) to the target context (\p TargetContext).
763///
764/// \param Context the AST context in which the qualification will be used.
765///
766/// \param CurContext the context where an entity is being named, which is
767/// typically based on the current scope.
768///
769/// \param TargetContext the context in which the named entity actually
770/// resides.
771///
772/// \returns a nested name specifier that refers into the target context, or
773/// NULL if no qualification is needed.
776 const DeclContext *TargetContext) {
778
779 for (const DeclContext *CommonAncestor = TargetContext;
780 CommonAncestor && !CommonAncestor->Encloses(CurContext);
781 CommonAncestor = CommonAncestor->getLookupParent()) {
782 if (CommonAncestor->isTransparentContext() ||
783 CommonAncestor->isFunctionOrMethod())
784 continue;
785
786 TargetParents.push_back(CommonAncestor);
787 }
788
789 NestedNameSpecifier Result = std::nullopt;
790 while (!TargetParents.empty()) {
791 const DeclContext *Parent = TargetParents.pop_back_val();
792
793 if (const auto *Namespace = dyn_cast<NamespaceDecl>(Parent)) {
794 if (!Namespace->getIdentifier())
795 continue;
796
797 Result = NestedNameSpecifier(Context, Namespace, Result);
798 } else if (const auto *TD = dyn_cast<TagDecl>(Parent)) {
799 QualType TT = Context.getTagType(ElaboratedTypeKeyword::None, Result, TD,
800 /*OwnsTag=*/false);
802 }
803 }
804 return Result;
805}
806
807// Some declarations have reserved names that we don't want to ever show.
808// Filter out names reserved for the implementation if they come from a
809// system header.
810static bool shouldIgnoreDueToReservedName(const NamedDecl *ND, Sema &SemaRef) {
811 // Debuggers want access to all identifiers, including reserved ones.
812 if (SemaRef.getLangOpts().DebuggerSupport)
813 return false;
814
815 ReservedIdentifierStatus Status = ND->isReserved(SemaRef.getLangOpts());
816 // Ignore reserved names for compiler provided decls.
817 if (isReservedInAllContexts(Status) && ND->getLocation().isInvalid())
818 return true;
819
820 // For system headers ignore only double-underscore names.
821 // This allows for system headers providing private symbols with a single
822 // underscore.
825 SemaRef.SourceMgr.getSpellingLoc(ND->getLocation())))
826 return true;
827
828 return false;
829}
830
831bool ResultBuilder::isInterestingDecl(const NamedDecl *ND,
832 bool &AsNestedNameSpecifier) const {
833 AsNestedNameSpecifier = false;
834
835 auto *Named = ND;
836 ND = ND->getUnderlyingDecl();
837
838 // Skip unnamed entities.
839 if (!ND->getDeclName())
840 return false;
841
842 // Friend declarations and declarations introduced due to friends are never
843 // added as results.
845 return false;
846
847 // Class template (partial) specializations are never added as results.
850 return false;
851
852 // Using declarations themselves are never added as results.
853 if (isa<UsingDecl>(ND))
854 return false;
855
856 if (shouldIgnoreDueToReservedName(ND, SemaRef))
857 return false;
858
859 if (Filter == &ResultBuilder::IsNestedNameSpecifier ||
860 (isa<NamespaceDecl>(ND) && Filter != &ResultBuilder::IsNamespace &&
861 Filter != &ResultBuilder::IsNamespaceOrAlias && Filter != nullptr))
862 AsNestedNameSpecifier = true;
863
864 // Filter out any unwanted results.
865 if (Filter && !(this->*Filter)(Named)) {
866 // Check whether it is interesting as a nested-name-specifier.
867 if (AllowNestedNameSpecifiers && SemaRef.getLangOpts().CPlusPlus &&
868 IsNestedNameSpecifier(ND) &&
869 (Filter != &ResultBuilder::IsMember ||
870 (isa<CXXRecordDecl>(ND) &&
871 cast<CXXRecordDecl>(ND)->isInjectedClassName()))) {
872 AsNestedNameSpecifier = true;
873 return true;
874 }
875
876 return false;
877 }
878 // ... then it must be interesting!
879 return true;
880}
881
882bool ResultBuilder::CheckHiddenResult(Result &R, DeclContext *CurContext,
883 const NamedDecl *Hiding) {
884 // In C, there is no way to refer to a hidden name.
885 // FIXME: This isn't true; we can find a tag name hidden by an ordinary
886 // name if we introduce the tag type.
887 if (!SemaRef.getLangOpts().CPlusPlus)
888 return true;
889
890 const DeclContext *HiddenCtx =
891 R.Declaration->getDeclContext()->getRedeclContext();
892
893 // There is no way to qualify a name declared in a function or method.
894 if (HiddenCtx->isFunctionOrMethod())
895 return true;
896
897 if (HiddenCtx == Hiding->getDeclContext()->getRedeclContext())
898 return true;
899
900 // We can refer to the result with the appropriate qualification. Do it.
901 R.Hidden = true;
902 R.QualifierIsInformative = false;
903
904 if (!R.Qualifier)
905 R.Qualifier = getRequiredQualification(SemaRef.Context, CurContext,
906 R.Declaration->getDeclContext());
907 return false;
908}
909
910/// A simplified classification of types used to determine whether two
911/// types are "similar enough" when adjusting priorities.
913 switch (T->getTypeClass()) {
914 case Type::Builtin:
915 switch (cast<BuiltinType>(T)->getKind()) {
916 case BuiltinType::Void:
917 return STC_Void;
918
919 case BuiltinType::NullPtr:
920 return STC_Pointer;
921
922 case BuiltinType::Overload:
923 case BuiltinType::Dependent:
924 return STC_Other;
925
926 case BuiltinType::ObjCId:
927 case BuiltinType::ObjCClass:
928 case BuiltinType::ObjCSel:
929 return STC_ObjectiveC;
930
931 default:
932 return STC_Arithmetic;
933 }
934
935 case Type::Complex:
936 return STC_Arithmetic;
937
938 case Type::Pointer:
939 return STC_Pointer;
940
941 case Type::BlockPointer:
942 return STC_Block;
943
944 case Type::LValueReference:
945 case Type::RValueReference:
947
948 case Type::ConstantArray:
949 case Type::IncompleteArray:
950 case Type::VariableArray:
951 case Type::DependentSizedArray:
952 return STC_Array;
953
954 case Type::DependentSizedExtVector:
955 case Type::Vector:
956 case Type::ExtVector:
957 return STC_Arithmetic;
958
959 case Type::FunctionProto:
960 case Type::FunctionNoProto:
961 return STC_Function;
962
963 case Type::Record:
964 return STC_Record;
965
966 case Type::Enum:
967 return STC_Arithmetic;
968
969 case Type::ObjCObject:
970 case Type::ObjCInterface:
971 case Type::ObjCObjectPointer:
972 return STC_ObjectiveC;
973
974 default:
975 return STC_Other;
976 }
977}
978
979/// Get the type that a given expression will have if this declaration
980/// is used as an expression in its "typical" code-completion form.
982 const NamedDecl *ND) {
983 ND = ND->getUnderlyingDecl();
984
985 if (const auto *Type = dyn_cast<TypeDecl>(ND))
986 return C.getTypeDeclType(ElaboratedTypeKeyword::None, Qualifier, Type);
987 if (const auto *Iface = dyn_cast<ObjCInterfaceDecl>(ND))
988 return C.getObjCInterfaceType(Iface);
989
990 QualType T;
991 if (const FunctionDecl *Function = ND->getAsFunction())
992 T = Function->getCallResultType();
993 else if (const auto *Method = dyn_cast<ObjCMethodDecl>(ND))
994 T = Method->getSendResultType();
995 else if (const auto *Enumerator = dyn_cast<EnumConstantDecl>(ND))
996 T = C.getTagType(ElaboratedTypeKeyword::None, Qualifier,
997 cast<EnumDecl>(Enumerator->getDeclContext()),
998 /*OwnsTag=*/false);
999 else if (const auto *Property = dyn_cast<ObjCPropertyDecl>(ND))
1000 T = Property->getType();
1001 else if (const auto *Value = dyn_cast<ValueDecl>(ND))
1002 T = Value->getType();
1003
1004 if (T.isNull())
1005 return QualType();
1006
1007 // Dig through references, function pointers, and block pointers to
1008 // get down to the likely type of an expression when the entity is
1009 // used.
1010 do {
1011 if (const auto *Ref = T->getAs<ReferenceType>()) {
1012 T = Ref->getPointeeType();
1013 continue;
1014 }
1015
1016 if (const auto *Pointer = T->getAs<PointerType>()) {
1017 if (Pointer->getPointeeType()->isFunctionType()) {
1018 T = Pointer->getPointeeType();
1019 continue;
1020 }
1021
1022 break;
1023 }
1024
1025 if (const auto *Block = T->getAs<BlockPointerType>()) {
1026 T = Block->getPointeeType();
1027 continue;
1028 }
1029
1030 if (const auto *Function = T->getAs<FunctionType>()) {
1031 T = Function->getReturnType();
1032 continue;
1033 }
1034
1035 break;
1036 } while (true);
1037
1038 return T;
1039}
1040
1041unsigned ResultBuilder::getBasePriority(const NamedDecl *ND) {
1042 if (!ND)
1043 return CCP_Unlikely;
1044
1045 // Context-based decisions.
1046 const DeclContext *LexicalDC = ND->getLexicalDeclContext();
1047 if (LexicalDC->isFunctionOrMethod()) {
1048 // _cmd is relatively rare
1049 if (const auto *ImplicitParam = dyn_cast<ImplicitParamDecl>(ND))
1050 if (ImplicitParam->getIdentifier() &&
1051 ImplicitParam->getIdentifier()->isStr("_cmd"))
1052 return CCP_ObjC_cmd;
1053
1054 return CCP_LocalDeclaration;
1055 }
1056
1057 const DeclContext *DC = ND->getDeclContext()->getRedeclContext();
1058 if (DC->isRecord() || isa<ObjCContainerDecl>(DC)) {
1059 // Explicit destructor calls are very rare.
1060 if (isa<CXXDestructorDecl>(ND))
1061 return CCP_Unlikely;
1062 // Explicit operator and conversion function calls are also very rare.
1063 auto DeclNameKind = ND->getDeclName().getNameKind();
1064 if (DeclNameKind == DeclarationName::CXXOperatorName ||
1067 return CCP_Unlikely;
1068 return CCP_MemberDeclaration;
1069 }
1070
1071 // Content-based decisions.
1072 if (isa<EnumConstantDecl>(ND))
1073 return CCP_Constant;
1074
1075 // Use CCP_Type for type declarations unless we're in a statement, Objective-C
1076 // message receiver, or parenthesized expression context. There, it's as
1077 // likely that the user will want to write a type as other declarations.
1078 if ((isa<TypeDecl>(ND) || isa<ObjCInterfaceDecl>(ND)) &&
1079 !(CompletionContext.getKind() == CodeCompletionContext::CCC_Statement ||
1080 CompletionContext.getKind() ==
1082 CompletionContext.getKind() ==
1084 return CCP_Type;
1085
1086 return CCP_Declaration;
1087}
1088
1089void ResultBuilder::AdjustResultPriorityForDecl(Result &R) {
1090 // If this is an Objective-C method declaration whose selector matches our
1091 // preferred selector, give it a priority boost.
1092 if (!PreferredSelector.isNull())
1093 if (const auto *Method = dyn_cast<ObjCMethodDecl>(R.Declaration))
1094 if (PreferredSelector == Method->getSelector())
1095 R.Priority += CCD_SelectorMatch;
1096
1097 // If we have a preferred type, adjust the priority for results with exactly-
1098 // matching or nearly-matching types.
1099 if (!PreferredType.isNull()) {
1100 QualType T = getDeclUsageType(SemaRef.Context, R.Qualifier, R.Declaration);
1101 if (!T.isNull()) {
1102 CanQualType TC = SemaRef.Context.getCanonicalType(T);
1103 // Check for exactly-matching types (modulo qualifiers).
1104 if (SemaRef.Context.hasSameUnqualifiedType(PreferredType, TC))
1105 R.Priority /= CCF_ExactTypeMatch;
1106 // Check for nearly-matching types, based on classification of each.
1107 else if ((getSimplifiedTypeClass(PreferredType) ==
1109 !(PreferredType->isEnumeralType() && TC->isEnumeralType()))
1110 R.Priority /= CCF_SimilarTypeMatch;
1111 }
1112 }
1113}
1114
1116 const CXXRecordDecl *Record) {
1117 CanQualType RecordTy = Context.getCanonicalTagType(Record);
1118 DeclarationName ConstructorName =
1119 Context.DeclarationNames.getCXXConstructorName(RecordTy);
1120 return Record->lookup(ConstructorName);
1121}
1122
1123void ResultBuilder::MaybeAddConstructorResults(Result R) {
1124 if (!SemaRef.getLangOpts().CPlusPlus || !R.Declaration ||
1125 !CompletionContext.wantConstructorResults())
1126 return;
1127
1128 const NamedDecl *D = R.Declaration;
1129 const CXXRecordDecl *Record = nullptr;
1130 if (const ClassTemplateDecl *ClassTemplate = dyn_cast<ClassTemplateDecl>(D))
1131 Record = ClassTemplate->getTemplatedDecl();
1132 else if ((Record = dyn_cast<CXXRecordDecl>(D))) {
1133 // Skip specializations and partial specializations.
1135 return;
1136 } else {
1137 // There are no constructors here.
1138 return;
1139 }
1140
1142 if (!Record)
1143 return;
1144
1145 for (NamedDecl *Ctor : getConstructors(SemaRef.Context, Record)) {
1146 R.Declaration = Ctor;
1147 R.CursorKind = getCursorKindForDecl(R.Declaration);
1148 Results.push_back(R);
1149 }
1150}
1151
1152static bool isConstructor(const Decl *ND) {
1153 if (const auto *Tmpl = dyn_cast<FunctionTemplateDecl>(ND))
1154 ND = Tmpl->getTemplatedDecl();
1155 return isa<CXXConstructorDecl>(ND);
1156}
1157
1158void ResultBuilder::MaybeAddResult(Result R, DeclContext *CurContext) {
1159 assert(!ShadowMaps.empty() && "Must enter into a results scope");
1160
1161 if (R.Kind != Result::RK_Declaration) {
1162 // For non-declaration results, just add the result.
1163 Results.push_back(R);
1164 return;
1165 }
1166
1167 // Look through using declarations.
1168 if (const UsingShadowDecl *Using = dyn_cast<UsingShadowDecl>(R.Declaration)) {
1169 CodeCompletionResult Result(Using->getTargetDecl(),
1170 getBasePriority(Using->getTargetDecl()),
1171 R.Qualifier, false,
1172 (R.Availability == CXAvailability_Available ||
1173 R.Availability == CXAvailability_Deprecated),
1174 std::move(R.FixIts));
1175 Result.ShadowDecl = Using;
1176 MaybeAddResult(Result, CurContext);
1177 return;
1178 }
1179
1180 const Decl *CanonDecl = R.Declaration->getCanonicalDecl();
1181 unsigned IDNS = CanonDecl->getIdentifierNamespace();
1182
1183 bool AsNestedNameSpecifier = false;
1184 if (!isInterestingDecl(R.Declaration, AsNestedNameSpecifier))
1185 return;
1186
1187 // C++ constructors are never found by name lookup.
1188 if (isConstructor(R.Declaration))
1189 return;
1190
1191 ShadowMap &SMap = ShadowMaps.back();
1192 ShadowMapEntry::iterator I, IEnd;
1193 ShadowMap::iterator NamePos = SMap.find(R.Declaration->getDeclName());
1194 if (NamePos != SMap.end()) {
1195 I = NamePos->second.begin();
1196 IEnd = NamePos->second.end();
1197 }
1198
1199 for (; I != IEnd; ++I) {
1200 const NamedDecl *ND = I->first;
1201 unsigned Index = I->second;
1202 if (ND->getCanonicalDecl() == CanonDecl) {
1203 // This is a redeclaration. Always pick the newer declaration.
1204 Results[Index].Declaration = R.Declaration;
1205
1206 // We're done.
1207 return;
1208 }
1209 }
1210
1211 // This is a new declaration in this scope. However, check whether this
1212 // declaration name is hidden by a similarly-named declaration in an outer
1213 // scope.
1214 std::list<ShadowMap>::iterator SM, SMEnd = ShadowMaps.end();
1215 --SMEnd;
1216 for (SM = ShadowMaps.begin(); SM != SMEnd; ++SM) {
1217 ShadowMapEntry::iterator I, IEnd;
1218 ShadowMap::iterator NamePos = SM->find(R.Declaration->getDeclName());
1219 if (NamePos != SM->end()) {
1220 I = NamePos->second.begin();
1221 IEnd = NamePos->second.end();
1222 }
1223 for (; I != IEnd; ++I) {
1224 // A tag declaration does not hide a non-tag declaration.
1225 if (I->first->hasTagIdentifierNamespace() &&
1228 continue;
1229
1230 // Protocols are in distinct namespaces from everything else.
1231 if (((I->first->getIdentifierNamespace() & Decl::IDNS_ObjCProtocol) ||
1232 (IDNS & Decl::IDNS_ObjCProtocol)) &&
1233 I->first->getIdentifierNamespace() != IDNS)
1234 continue;
1235
1236 // The newly-added result is hidden by an entry in the shadow map.
1237 if (CheckHiddenResult(R, CurContext, I->first))
1238 return;
1239
1240 break;
1241 }
1242 }
1243
1244 // Make sure that any given declaration only shows up in the result set once.
1245 if (!AllDeclsFound.insert(CanonDecl).second)
1246 return;
1247
1248 // If the filter is for nested-name-specifiers, then this result starts a
1249 // nested-name-specifier.
1250 if (AsNestedNameSpecifier) {
1251 R.StartsNestedNameSpecifier = true;
1252 R.Priority = CCP_NestedNameSpecifier;
1253 } else
1254 AdjustResultPriorityForDecl(R);
1255
1256 // If this result is supposed to have an informative qualifier, add one.
1257 if (R.QualifierIsInformative && !R.Qualifier &&
1258 !R.StartsNestedNameSpecifier) {
1259 const DeclContext *Ctx = R.Declaration->getDeclContext();
1260 if (const NamespaceDecl *Namespace = dyn_cast<NamespaceDecl>(Ctx))
1261 R.Qualifier =
1262 NestedNameSpecifier(SemaRef.Context, Namespace, std::nullopt);
1263 else if (const TagDecl *Tag = dyn_cast<TagDecl>(Ctx))
1264 R.Qualifier = NestedNameSpecifier(
1265 SemaRef.Context
1267 /*Qualifier=*/std::nullopt, Tag, /*OwnsTag=*/false)
1268 .getTypePtr());
1269 else
1270 R.QualifierIsInformative = false;
1271 }
1272
1273 // Insert this result into the set of results and into the current shadow
1274 // map.
1275 SMap[R.Declaration->getDeclName()].Add(R.Declaration, Results.size());
1276 Results.push_back(R);
1277
1278 if (!AsNestedNameSpecifier)
1279 MaybeAddConstructorResults(R);
1280}
1281
1282static void setInBaseClass(ResultBuilder::Result &R) {
1283 R.Priority += CCD_InBaseClass;
1284 R.InBaseClass = true;
1285}
1286
1288// Will Candidate ever be called on the object, when overloaded with Incumbent?
1289// Returns Dominates if Candidate is always called, Dominated if Incumbent is
1290// always called, BothViable if either may be called depending on arguments.
1291// Precondition: must actually be overloads!
1293 const CXXMethodDecl &Incumbent,
1294 const Qualifiers &ObjectQuals,
1295 ExprValueKind ObjectKind,
1296 const ASTContext &Ctx) {
1297 // Base/derived shadowing is handled elsewhere.
1298 if (Candidate.getDeclContext() != Incumbent.getDeclContext())
1300 if (Candidate.isVariadic() != Incumbent.isVariadic() ||
1301 Candidate.getNumParams() != Incumbent.getNumParams() ||
1302 Candidate.getMinRequiredArguments() !=
1303 Incumbent.getMinRequiredArguments())
1305 for (unsigned I = 0, E = Candidate.getNumParams(); I != E; ++I)
1306 if (Candidate.parameters()[I]->getType().getCanonicalType() !=
1307 Incumbent.parameters()[I]->getType().getCanonicalType())
1309 if (!Candidate.specific_attrs<EnableIfAttr>().empty() ||
1310 !Incumbent.specific_attrs<EnableIfAttr>().empty())
1312 // At this point, we know calls can't pick one or the other based on
1313 // arguments, so one of the two must win. (Or both fail, handled elsewhere).
1314 RefQualifierKind CandidateRef = Candidate.getRefQualifier();
1315 RefQualifierKind IncumbentRef = Incumbent.getRefQualifier();
1316 if (CandidateRef != IncumbentRef) {
1317 // If the object kind is LValue/RValue, there's one acceptable ref-qualifier
1318 // and it can't be mixed with ref-unqualified overloads (in valid code).
1319
1320 // For xvalue objects, we prefer the rvalue overload even if we have to
1321 // add qualifiers (which is rare, because const&& is rare).
1322 if (ObjectKind == clang::VK_XValue)
1323 return CandidateRef == RQ_RValue ? OverloadCompare::Dominates
1325 }
1326 // Now the ref qualifiers are the same (or we're in some invalid state).
1327 // So make some decision based on the qualifiers.
1328 Qualifiers CandidateQual = Candidate.getMethodQualifiers();
1329 Qualifiers IncumbentQual = Incumbent.getMethodQualifiers();
1330 bool CandidateSuperset = CandidateQual.compatiblyIncludes(IncumbentQual, Ctx);
1331 bool IncumbentSuperset = IncumbentQual.compatiblyIncludes(CandidateQual, Ctx);
1332 if (CandidateSuperset == IncumbentSuperset)
1334 return IncumbentSuperset ? OverloadCompare::Dominates
1336}
1337
1338bool ResultBuilder::canCxxMethodBeCalled(const CXXMethodDecl *Method,
1339 QualType BaseExprType) const {
1340 // Find the class scope that we're currently in.
1341 // We could e.g. be inside a lambda, so walk up the DeclContext until we
1342 // find a CXXMethodDecl.
1343 DeclContext *CurContext = SemaRef.CurContext;
1344 const auto *CurrentClassScope = [&]() -> const CXXRecordDecl * {
1345 for (DeclContext *Ctx = CurContext; Ctx; Ctx = Ctx->getParent()) {
1346 const auto *CtxMethod = llvm::dyn_cast<CXXMethodDecl>(Ctx);
1347 if (CtxMethod && !CtxMethod->getParent()->isLambda()) {
1348 return CtxMethod->getParent();
1349 }
1350 }
1351 return nullptr;
1352 }();
1353
1354 // If we're not inside the scope of the method's class, it can't be a call.
1355 bool FunctionCanBeCall =
1356 CurrentClassScope &&
1357 (CurrentClassScope == Method->getParent() ||
1358 CurrentClassScope->isDerivedFrom(Method->getParent()));
1359
1360 // We skip the following calculation for exceptions if it's already true.
1361 if (FunctionCanBeCall)
1362 return true;
1363
1364 // Exception: foo->FooBase::bar() or foo->Foo::bar() *is* a call.
1365 if (const CXXRecordDecl *MaybeDerived =
1366 BaseExprType.isNull() ? nullptr
1367 : BaseExprType->getAsCXXRecordDecl()) {
1368 auto *MaybeBase = Method->getParent();
1369 FunctionCanBeCall =
1370 MaybeDerived == MaybeBase || MaybeDerived->isDerivedFrom(MaybeBase);
1371 }
1372
1373 return FunctionCanBeCall;
1374}
1375
1376bool ResultBuilder::canFunctionBeCalled(const NamedDecl *ND,
1377 QualType BaseExprType) const {
1378 // We apply heuristics only to CCC_Symbol:
1379 // * CCC_{Arrow,Dot}MemberAccess reflect member access expressions:
1380 // f.method() and f->method(). These are always calls.
1381 // * A qualified name to a member function may *not* be a call. We have to
1382 // subdivide the cases: For example, f.Base::method(), which is regarded as
1383 // CCC_Symbol, should be a call.
1384 // * Non-member functions and static member functions are always considered
1385 // calls.
1386 if (CompletionContext.getKind() == clang::CodeCompletionContext::CCC_Symbol) {
1387 if (const auto *FuncTmpl = dyn_cast<FunctionTemplateDecl>(ND)) {
1388 ND = FuncTmpl->getTemplatedDecl();
1389 }
1390 const auto *Method = dyn_cast<CXXMethodDecl>(ND);
1391 if (Method && !Method->isStatic()) {
1392 return canCxxMethodBeCalled(Method, BaseExprType);
1393 }
1394 }
1395 return true;
1396}
1397
1398void ResultBuilder::AddResult(Result R, DeclContext *CurContext,
1399 NamedDecl *Hiding, bool InBaseClass = false,
1400 QualType BaseExprType = QualType(),
1401 bool IsInDeclarationContext = false,
1402 bool IsAddressOfOperand = false) {
1403 if (R.Kind != Result::RK_Declaration) {
1404 // For non-declaration results, just add the result.
1405 Results.push_back(R);
1406 return;
1407 }
1408
1409 // Look through using declarations.
1410 if (const auto *Using = dyn_cast<UsingShadowDecl>(R.Declaration)) {
1411 CodeCompletionResult Result(Using->getTargetDecl(),
1412 getBasePriority(Using->getTargetDecl()),
1413 R.Qualifier, false,
1414 (R.Availability == CXAvailability_Available ||
1415 R.Availability == CXAvailability_Deprecated),
1416 std::move(R.FixIts));
1417 Result.ShadowDecl = Using;
1418 AddResult(Result, CurContext, Hiding, /*InBaseClass=*/false,
1419 /*BaseExprType=*/BaseExprType);
1420 return;
1421 }
1422
1423 bool AsNestedNameSpecifier = false;
1424 if (!isInterestingDecl(R.Declaration, AsNestedNameSpecifier))
1425 return;
1426
1427 // C++ constructors are never found by name lookup.
1428 if (isConstructor(R.Declaration))
1429 return;
1430
1431 if (Hiding && CheckHiddenResult(R, CurContext, Hiding))
1432 return;
1433
1434 // Make sure that any given declaration only shows up in the result set once.
1435 if (!AllDeclsFound.insert(R.Declaration->getCanonicalDecl()).second)
1436 return;
1437
1438 // If the filter is for nested-name-specifiers, then this result starts a
1439 // nested-name-specifier.
1440 if (AsNestedNameSpecifier) {
1441 R.StartsNestedNameSpecifier = true;
1442 R.Priority = CCP_NestedNameSpecifier;
1443 } else if (Filter == &ResultBuilder::IsMember && !R.Qualifier &&
1444 InBaseClass &&
1446 R.Declaration->getDeclContext()->getRedeclContext()))
1447 R.QualifierIsInformative = true;
1448
1449 // If this result is supposed to have an informative qualifier, add one.
1450 if (R.QualifierIsInformative && !R.Qualifier &&
1451 !R.StartsNestedNameSpecifier) {
1452 const DeclContext *Ctx = R.Declaration->getDeclContext();
1453 if (const auto *Namespace = dyn_cast<NamespaceDecl>(Ctx))
1454 R.Qualifier =
1455 NestedNameSpecifier(SemaRef.Context, Namespace, std::nullopt);
1456 else if (const auto *Tag = dyn_cast<TagDecl>(Ctx))
1457 R.Qualifier = NestedNameSpecifier(
1458 SemaRef.Context
1460 /*Qualifier=*/std::nullopt, Tag, /*OwnsTag=*/false)
1461 .getTypePtr());
1462 else
1463 R.QualifierIsInformative = false;
1464 }
1465
1466 // Adjust the priority if this result comes from a base class.
1467 if (InBaseClass)
1468 setInBaseClass(R);
1469
1470 AdjustResultPriorityForDecl(R);
1471
1472 // Account for explicit object parameter
1473 const auto GetQualifiers = [&](const CXXMethodDecl *MethodDecl) {
1474 if (MethodDecl->isExplicitObjectMemberFunction())
1475 return MethodDecl->getFunctionObjectParameterType().getQualifiers();
1476 else
1477 return MethodDecl->getMethodQualifiers();
1478 };
1479
1480 if (IsExplicitObjectMemberFunction &&
1482 (isa<CXXMethodDecl>(R.Declaration) || isa<FieldDecl>(R.Declaration))) {
1483 // If result is a member in the context of an explicit-object member
1484 // function, drop it because it must be accessed through the object
1485 // parameter
1486 return;
1487 }
1488
1489 if (HasObjectTypeQualifiers)
1490 if (const auto *Method = dyn_cast<CXXMethodDecl>(R.Declaration))
1491 if (Method->isInstance()) {
1492 Qualifiers MethodQuals = GetQualifiers(Method);
1493 if (ObjectTypeQualifiers == MethodQuals)
1494 R.Priority += CCD_ObjectQualifierMatch;
1495 else if (ObjectTypeQualifiers - MethodQuals) {
1496 // The method cannot be invoked, because doing so would drop
1497 // qualifiers.
1498 return;
1499 }
1500 // Detect cases where a ref-qualified method cannot be invoked.
1501 switch (Method->getRefQualifier()) {
1502 case RQ_LValue:
1503 if (ObjectKind != VK_LValue && !MethodQuals.hasConst())
1504 return;
1505 break;
1506 case RQ_RValue:
1507 if (ObjectKind == VK_LValue)
1508 return;
1509 break;
1510 case RQ_None:
1511 break;
1512 }
1513
1514 /// Check whether this dominates another overloaded method, which should
1515 /// be suppressed (or vice versa).
1516 /// Motivating case is const_iterator begin() const vs iterator begin().
1517 auto &OverloadSet = OverloadMap[std::make_pair(
1518 CurContext, Method->getDeclName().getAsOpaqueInteger())];
1519 for (const DeclIndexPair Entry : OverloadSet) {
1520 Result &Incumbent = Results[Entry.second];
1521 switch (compareOverloads(*Method,
1522 *cast<CXXMethodDecl>(Incumbent.Declaration),
1523 ObjectTypeQualifiers, ObjectKind,
1524 CurContext->getParentASTContext())) {
1526 // Replace the dominated overload with this one.
1527 // FIXME: if the overload dominates multiple incumbents then we
1528 // should remove all. But two overloads is by far the common case.
1529 Incumbent = std::move(R);
1530 return;
1532 // This overload can't be called, drop it.
1533 return;
1535 break;
1536 }
1537 }
1538 OverloadSet.Add(Method, Results.size());
1539 }
1540 R.DeclaringEntity = IsInDeclarationContext;
1541 R.FunctionCanBeCall =
1542 canFunctionBeCalled(R.getDeclaration(), BaseExprType) &&
1543 // If the user wrote `&` before the function name, assume the
1544 // user is more likely to take the address of the function rather
1545 // than call it and take the address of the result.
1546 !IsAddressOfOperand;
1547
1548 // Insert this result into the set of results.
1549 Results.push_back(R);
1550
1551 if (!AsNestedNameSpecifier)
1552 MaybeAddConstructorResults(R);
1553}
1554
1555void ResultBuilder::AddResult(Result R) {
1556 assert(R.Kind != Result::RK_Declaration &&
1557 "Declaration results need more context");
1558 Results.push_back(R);
1559}
1560
1561/// Enter into a new scope.
1562void ResultBuilder::EnterNewScope() { ShadowMaps.emplace_back(); }
1563
1564/// Exit from the current scope.
1565void ResultBuilder::ExitScope() {
1566 ShadowMaps.pop_back();
1567}
1568
1569/// Determines whether this given declaration will be found by
1570/// ordinary name lookup.
1571bool ResultBuilder::IsOrdinaryName(const NamedDecl *ND) const {
1572 ND = ND->getUnderlyingDecl();
1573
1574 // If name lookup finds a local extern declaration, then we are in a
1575 // context where it behaves like an ordinary name.
1577 if (SemaRef.getLangOpts().CPlusPlus)
1579 else if (SemaRef.getLangOpts().ObjC) {
1580 if (isa<ObjCIvarDecl>(ND))
1581 return true;
1582 }
1583
1584 return ND->getIdentifierNamespace() & IDNS;
1585}
1586
1587/// Determines whether this given declaration will be found by
1588/// ordinary name lookup but is not a type name.
1589bool ResultBuilder::IsOrdinaryNonTypeName(const NamedDecl *ND) const {
1590 ND = ND->getUnderlyingDecl();
1591 if (isa<TypeDecl>(ND))
1592 return false;
1593 // Objective-C interfaces names are not filtered by this method because they
1594 // can be used in a class property expression. We can still filter out
1595 // @class declarations though.
1596 if (const auto *ID = dyn_cast<ObjCInterfaceDecl>(ND)) {
1597 if (!ID->getDefinition())
1598 return false;
1599 }
1600
1602 if (SemaRef.getLangOpts().CPlusPlus)
1604 else if (SemaRef.getLangOpts().ObjC) {
1605 if (isa<ObjCIvarDecl>(ND))
1606 return true;
1607 }
1608
1609 return ND->getIdentifierNamespace() & IDNS;
1610}
1611
1612bool ResultBuilder::IsIntegralConstantValue(const NamedDecl *ND) const {
1613 if (!IsOrdinaryNonTypeName(ND))
1614 return false;
1615
1616 if (const auto *VD = dyn_cast<ValueDecl>(ND->getUnderlyingDecl()))
1617 if (VD->getType()->isIntegralOrEnumerationType())
1618 return true;
1619
1620 return false;
1621}
1622
1623/// Determines whether this given declaration will be found by
1624/// ordinary name lookup.
1625bool ResultBuilder::IsOrdinaryNonValueName(const NamedDecl *ND) const {
1626 ND = ND->getUnderlyingDecl();
1627
1629 if (SemaRef.getLangOpts().CPlusPlus)
1631
1632 return (ND->getIdentifierNamespace() & IDNS) && !isa<ValueDecl>(ND) &&
1634}
1635
1636/// Determines whether the given declaration is suitable as the
1637/// start of a C++ nested-name-specifier, e.g., a class or namespace.
1638bool ResultBuilder::IsNestedNameSpecifier(const NamedDecl *ND) const {
1639 // Allow us to find class templates, too.
1640 if (const auto *ClassTemplate = dyn_cast<ClassTemplateDecl>(ND))
1641 ND = ClassTemplate->getTemplatedDecl();
1642
1643 return SemaRef.isAcceptableNestedNameSpecifier(ND);
1644}
1645
1646/// Determines whether the given declaration is an enumeration.
1647bool ResultBuilder::IsEnum(const NamedDecl *ND) const {
1648 return isa<EnumDecl>(ND);
1649}
1650
1651/// Determines whether the given declaration is a class or struct.
1652bool ResultBuilder::IsClassOrStruct(const NamedDecl *ND) const {
1653 // Allow us to find class templates, too.
1654 if (const auto *ClassTemplate = dyn_cast<ClassTemplateDecl>(ND))
1655 ND = ClassTemplate->getTemplatedDecl();
1656
1657 // For purposes of this check, interfaces match too.
1658 if (const auto *RD = dyn_cast<RecordDecl>(ND))
1659 return RD->getTagKind() == TagTypeKind::Class ||
1660 RD->getTagKind() == TagTypeKind::Struct ||
1661 RD->getTagKind() == TagTypeKind::Interface;
1662
1663 return false;
1664}
1665
1666/// Determines whether the given declaration is a union.
1667bool ResultBuilder::IsUnion(const NamedDecl *ND) const {
1668 // Allow us to find class templates, too.
1669 if (const auto *ClassTemplate = dyn_cast<ClassTemplateDecl>(ND))
1670 ND = ClassTemplate->getTemplatedDecl();
1671
1672 if (const auto *RD = dyn_cast<RecordDecl>(ND))
1673 return RD->getTagKind() == TagTypeKind::Union;
1674
1675 return false;
1676}
1677
1678/// Determines whether the given declaration is a namespace.
1679bool ResultBuilder::IsNamespace(const NamedDecl *ND) const {
1680 return isa<NamespaceDecl>(ND);
1681}
1682
1683/// Determines whether the given declaration is a namespace or
1684/// namespace alias.
1685bool ResultBuilder::IsNamespaceOrAlias(const NamedDecl *ND) const {
1687}
1688
1689/// Determines whether the given declaration is a type.
1690bool ResultBuilder::IsType(const NamedDecl *ND) const {
1691 ND = ND->getUnderlyingDecl();
1692 return isa<TypeDecl>(ND) || isa<ObjCInterfaceDecl>(ND);
1693}
1694
1695/// Determines which members of a class should be visible via
1696/// "." or "->". Only value declarations, nested name specifiers, and
1697/// using declarations thereof should show up.
1698bool ResultBuilder::IsMember(const NamedDecl *ND) const {
1699 ND = ND->getUnderlyingDecl();
1700 return isa<ValueDecl>(ND) || isa<FunctionTemplateDecl>(ND) ||
1702}
1703
1704/// Determines whether the given declaration is a member that
1705/// __builtin_offsetof can name: a (direct or indirect) non-bit-field.
1706bool ResultBuilder::IsOffsetofField(const NamedDecl *ND) const {
1707 ND = ND->getUnderlyingDecl();
1708 if (const auto *FD = dyn_cast<FieldDecl>(ND))
1709 return !FD->isBitField();
1710 if (const auto *IFD = dyn_cast<IndirectFieldDecl>(ND))
1711 return !IFD->getAnonField()->isBitField();
1712 return false;
1713}
1714
1716 T = C.getCanonicalType(T);
1717 switch (T->getTypeClass()) {
1718 case Type::ObjCObject:
1719 case Type::ObjCInterface:
1720 case Type::ObjCObjectPointer:
1721 return true;
1722
1723 case Type::Builtin:
1724 switch (cast<BuiltinType>(T)->getKind()) {
1725 case BuiltinType::ObjCId:
1726 case BuiltinType::ObjCClass:
1727 case BuiltinType::ObjCSel:
1728 return true;
1729
1730 default:
1731 break;
1732 }
1733 return false;
1734
1735 default:
1736 break;
1737 }
1738
1739 if (!C.getLangOpts().CPlusPlus)
1740 return false;
1741
1742 // FIXME: We could perform more analysis here to determine whether a
1743 // particular class type has any conversions to Objective-C types. For now,
1744 // just accept all class types.
1745 return T->isDependentType() || T->isRecordType();
1746}
1747
1748bool ResultBuilder::IsObjCMessageReceiver(const NamedDecl *ND) const {
1749 QualType T =
1750 getDeclUsageType(SemaRef.Context, /*Qualifier=*/std::nullopt, ND);
1751 if (T.isNull())
1752 return false;
1753
1754 T = SemaRef.Context.getBaseElementType(T);
1755 return isObjCReceiverType(SemaRef.Context, T);
1756}
1757
1758bool ResultBuilder::IsObjCMessageReceiverOrLambdaCapture(
1759 const NamedDecl *ND) const {
1760 if (IsObjCMessageReceiver(ND))
1761 return true;
1762
1763 const auto *Var = dyn_cast<VarDecl>(ND);
1764 if (!Var)
1765 return false;
1766
1767 return Var->hasLocalStorage() && !Var->hasAttr<BlocksAttr>();
1768}
1769
1770bool ResultBuilder::IsObjCCollection(const NamedDecl *ND) const {
1771 if ((SemaRef.getLangOpts().CPlusPlus && !IsOrdinaryName(ND)) ||
1772 (!SemaRef.getLangOpts().CPlusPlus && !IsOrdinaryNonTypeName(ND)))
1773 return false;
1774
1775 QualType T =
1776 getDeclUsageType(SemaRef.Context, /*Qualifier=*/std::nullopt, ND);
1777 if (T.isNull())
1778 return false;
1779
1780 T = SemaRef.Context.getBaseElementType(T);
1781 return T->isObjCObjectType() || T->isObjCObjectPointerType() ||
1782 T->isObjCIdType() ||
1783 (SemaRef.getLangOpts().CPlusPlus && T->isRecordType());
1784}
1785
1786bool ResultBuilder::IsImpossibleToSatisfy(const NamedDecl *ND) const {
1787 return false;
1788}
1789
1790/// Determines whether the given declaration is an Objective-C
1791/// instance variable.
1792bool ResultBuilder::IsObjCIvar(const NamedDecl *ND) const {
1793 return isa<ObjCIvarDecl>(ND);
1794}
1795
1796namespace {
1797
1798/// Visible declaration consumer that adds a code-completion result
1799/// for each visible declaration.
1800class CodeCompletionDeclConsumer : public VisibleDeclConsumer {
1801 ResultBuilder &Results;
1802 DeclContext *InitialLookupCtx;
1803 // NamingClass and BaseType are used for access-checking. See
1804 // Sema::IsSimplyAccessible for details.
1805 CXXRecordDecl *NamingClass;
1806 QualType BaseType;
1807 std::vector<FixItHint> FixIts;
1808 bool IsInDeclarationContext;
1809 // Completion is invoked after an identifier preceded by '&'.
1810 bool IsAddressOfOperand;
1811
1812public:
1813 CodeCompletionDeclConsumer(
1814 ResultBuilder &Results, DeclContext *InitialLookupCtx,
1815 QualType BaseType = QualType(),
1816 std::vector<FixItHint> FixIts = std::vector<FixItHint>())
1817 : Results(Results), InitialLookupCtx(InitialLookupCtx),
1818 FixIts(std::move(FixIts)), IsInDeclarationContext(false),
1819 IsAddressOfOperand(false) {
1820 NamingClass = llvm::dyn_cast<CXXRecordDecl>(InitialLookupCtx);
1821 // If BaseType was not provided explicitly, emulate implicit 'this->'.
1822 if (BaseType.isNull()) {
1823 auto ThisType = Results.getSema().getCurrentThisType();
1824 if (!ThisType.isNull()) {
1825 assert(ThisType->isPointerType());
1826 BaseType = ThisType->getPointeeType();
1827 if (!NamingClass)
1828 NamingClass = BaseType->getAsCXXRecordDecl();
1829 }
1830 }
1831 this->BaseType = BaseType;
1832 }
1833
1834 void setIsInDeclarationContext(bool IsInDeclarationContext) {
1835 this->IsInDeclarationContext = IsInDeclarationContext;
1836 }
1837
1838 void setIsAddressOfOperand(bool IsAddressOfOperand) {
1839 this->IsAddressOfOperand = IsAddressOfOperand;
1840 }
1841
1842 void FoundDecl(NamedDecl *ND, NamedDecl *Hiding, DeclContext *Ctx,
1843 bool InBaseClass) override {
1844 ResultBuilder::Result Result(ND, Results.getBasePriority(ND),
1845 /*Qualifier=*/std::nullopt,
1846 /*QualifierIsInformative=*/false,
1847 IsAccessible(ND, Ctx), FixIts);
1848 Results.AddResult(Result, InitialLookupCtx, Hiding, InBaseClass, BaseType,
1849 IsInDeclarationContext, IsAddressOfOperand);
1850 }
1851
1852 void EnteredContext(DeclContext *Ctx) override {
1853 Results.addVisitedContext(Ctx);
1854 }
1855
1856private:
1857 bool IsAccessible(NamedDecl *ND, DeclContext *Ctx) {
1858 // Naming class to use for access check. In most cases it was provided
1859 // explicitly (e.g. member access (lhs.foo) or qualified lookup (X::)),
1860 // for unqualified lookup we fallback to the \p Ctx in which we found the
1861 // member.
1862 auto *NamingClass = this->NamingClass;
1863 QualType BaseType = this->BaseType;
1864 if (auto *Cls = llvm::dyn_cast_or_null<CXXRecordDecl>(Ctx)) {
1865 if (!NamingClass)
1866 NamingClass = Cls;
1867 // When we emulate implicit 'this->' in an unqualified lookup, we might
1868 // end up with an invalid naming class. In that case, we avoid emulating
1869 // 'this->' qualifier to satisfy preconditions of the access checking.
1870 if (NamingClass->getCanonicalDecl() != Cls->getCanonicalDecl() &&
1871 !NamingClass->isDerivedFrom(Cls)) {
1872 NamingClass = Cls;
1873 BaseType = QualType();
1874 }
1875 } else {
1876 // The decl was found outside the C++ class, so only ObjC access checks
1877 // apply. Those do not rely on NamingClass and BaseType, so we clear them
1878 // out.
1879 NamingClass = nullptr;
1880 BaseType = QualType();
1881 }
1882 return Results.getSema().IsSimplyAccessible(ND, NamingClass, BaseType);
1883 }
1884};
1885} // namespace
1886
1887/// Add type specifiers for the current language as keyword results.
1888static void AddTypeSpecifierResults(const LangOptions &LangOpts,
1889 ResultBuilder &Results) {
1891 Results.AddResult(Result("short", CCP_Type));
1892 Results.AddResult(Result("long", CCP_Type));
1893 Results.AddResult(Result("signed", CCP_Type));
1894 Results.AddResult(Result("unsigned", CCP_Type));
1895 Results.AddResult(Result("void", CCP_Type));
1896 Results.AddResult(Result("char", CCP_Type));
1897 Results.AddResult(Result("int", CCP_Type));
1898 Results.AddResult(Result("float", CCP_Type));
1899 Results.AddResult(Result("double", CCP_Type));
1900 Results.AddResult(Result("enum", CCP_Type));
1901 Results.AddResult(Result("struct", CCP_Type));
1902 Results.AddResult(Result("union", CCP_Type));
1903 Results.AddResult(Result("const", CCP_Type));
1904 Results.AddResult(Result("volatile", CCP_Type));
1905
1906 if (LangOpts.C99) {
1907 // C99-specific
1908 Results.AddResult(Result("_Complex", CCP_Type));
1909 if (!LangOpts.C2y)
1910 Results.AddResult(Result("_Imaginary", CCP_Type));
1911 Results.AddResult(Result("_Bool", CCP_Type));
1912 Results.AddResult(Result("restrict", CCP_Type));
1913 }
1914
1915 CodeCompletionBuilder Builder(Results.getAllocator(),
1916 Results.getCodeCompletionTUInfo());
1917 if (LangOpts.CPlusPlus) {
1918 // C++-specific
1919 Results.AddResult(
1920 Result("bool", CCP_Type + (LangOpts.ObjC ? CCD_bool_in_ObjC : 0)));
1921 Results.AddResult(Result("class", CCP_Type));
1922 Results.AddResult(Result("wchar_t", CCP_Type));
1923
1924 // typename name
1925 Builder.AddTypedTextChunk("typename");
1927 Builder.AddPlaceholderChunk("name");
1928 Results.AddResult(Result(Builder.TakeString()));
1929
1930 if (LangOpts.CPlusPlus11) {
1931 Results.AddResult(Result("auto", CCP_Type));
1932 Results.AddResult(Result("char16_t", CCP_Type));
1933 Results.AddResult(Result("char32_t", CCP_Type));
1934
1935 Builder.AddTypedTextChunk("decltype");
1936 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
1937 Builder.AddPlaceholderChunk("expression");
1938 Builder.AddChunk(CodeCompletionString::CK_RightParen);
1939 Results.AddResult(Result(Builder.TakeString()));
1940 }
1941
1942 if (LangOpts.Char8 || LangOpts.CPlusPlus20)
1943 Results.AddResult(Result("char8_t", CCP_Type));
1944 } else
1945 Results.AddResult(Result("__auto_type", CCP_Type));
1946
1947 // GNU keywords
1948 if (LangOpts.GNUKeywords) {
1949 // FIXME: Enable when we actually support decimal floating point.
1950 // Results.AddResult(Result("_Decimal32"));
1951 // Results.AddResult(Result("_Decimal64"));
1952 // Results.AddResult(Result("_Decimal128"));
1953
1954 Builder.AddTypedTextChunk("typeof");
1956 Builder.AddPlaceholderChunk("expression");
1957 Results.AddResult(Result(Builder.TakeString()));
1958
1959 Builder.AddTypedTextChunk("typeof");
1960 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
1961 Builder.AddPlaceholderChunk("type");
1962 Builder.AddChunk(CodeCompletionString::CK_RightParen);
1963 Results.AddResult(Result(Builder.TakeString()));
1964 }
1965
1966 // Nullability
1967 Results.AddResult(Result("_Nonnull", CCP_Type));
1968 Results.AddResult(Result("_Null_unspecified", CCP_Type));
1969 Results.AddResult(Result("_Nullable", CCP_Type));
1970}
1971
1972static void
1974 const LangOptions &LangOpts, ResultBuilder &Results) {
1976 // Note: we don't suggest either "auto" or "register", because both
1977 // are pointless as storage specifiers. Elsewhere, we suggest "auto"
1978 // in C++0x as a type specifier.
1979 Results.AddResult(Result("extern"));
1980 Results.AddResult(Result("static"));
1981
1982 if (LangOpts.CPlusPlus11) {
1983 CodeCompletionAllocator &Allocator = Results.getAllocator();
1984 CodeCompletionBuilder Builder(Allocator, Results.getCodeCompletionTUInfo());
1985
1986 // alignas
1987 Builder.AddTypedTextChunk("alignas");
1988 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
1989 Builder.AddPlaceholderChunk("expression");
1990 Builder.AddChunk(CodeCompletionString::CK_RightParen);
1991 Results.AddResult(Result(Builder.TakeString()));
1992
1993 Results.AddResult(Result("constexpr"));
1994 Results.AddResult(Result("thread_local"));
1995 }
1996
1997 if (LangOpts.CPlusPlus20)
1998 Results.AddResult(Result("constinit"));
1999}
2000
2001static void
2003 const LangOptions &LangOpts, ResultBuilder &Results) {
2005 switch (CCC) {
2008 if (LangOpts.CPlusPlus) {
2009 Results.AddResult(Result("explicit"));
2010 Results.AddResult(Result("friend"));
2011 Results.AddResult(Result("mutable"));
2012 Results.AddResult(Result("virtual"));
2013 }
2014 [[fallthrough]];
2015
2020 if (LangOpts.CPlusPlus || LangOpts.C99)
2021 Results.AddResult(Result("inline"));
2022
2023 if (LangOpts.CPlusPlus20)
2024 Results.AddResult(Result("consteval"));
2025 break;
2026
2037 break;
2038 }
2039}
2040
2041static void AddObjCExpressionResults(ResultBuilder &Results, bool NeedAt);
2042static void AddObjCStatementResults(ResultBuilder &Results, bool NeedAt);
2043static void AddObjCVisibilityResults(const LangOptions &LangOpts,
2044 ResultBuilder &Results, bool NeedAt);
2045static void AddObjCImplementationResults(const LangOptions &LangOpts,
2046 ResultBuilder &Results, bool NeedAt);
2047static void AddObjCInterfaceResults(const LangOptions &LangOpts,
2048 ResultBuilder &Results, bool NeedAt);
2049static void AddObjCTopLevelResults(ResultBuilder &Results, bool NeedAt);
2050
2051static void AddTypedefResult(ResultBuilder &Results) {
2052 CodeCompletionBuilder Builder(Results.getAllocator(),
2053 Results.getCodeCompletionTUInfo());
2054 Builder.AddTypedTextChunk("typedef");
2056 Builder.AddPlaceholderChunk("type");
2058 Builder.AddPlaceholderChunk("name");
2059 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2060 Results.AddResult(CodeCompletionResult(Builder.TakeString()));
2061}
2062
2063// using name = type
2065 ResultBuilder &Results) {
2066 Builder.AddTypedTextChunk("using");
2068 Builder.AddPlaceholderChunk("name");
2069 Builder.AddChunk(CodeCompletionString::CK_Equal);
2070 Builder.AddPlaceholderChunk("type");
2071 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2072 Results.AddResult(CodeCompletionResult(Builder.TakeString()));
2073}
2074
2076 const LangOptions &LangOpts) {
2077 switch (CCC) {
2089 return true;
2090
2093 return LangOpts.CPlusPlus;
2094
2097 return false;
2098
2100 return LangOpts.CPlusPlus || LangOpts.ObjC || LangOpts.C99;
2101 }
2102
2103 llvm_unreachable("Invalid ParserCompletionContext!");
2104}
2105
2107 const Preprocessor &PP) {
2108 PrintingPolicy Policy = Sema::getPrintingPolicy(Context, PP);
2109 Policy.AnonymousTagNameStyle =
2110 llvm::to_underlying(PrintingPolicy::AnonymousTagMode::Plain);
2111 Policy.SuppressStrongLifetime = true;
2112 Policy.SuppressUnwrittenScope = true;
2113 Policy.CleanUglifiedParameters = true;
2114 return Policy;
2115}
2116
2117/// Retrieve a printing policy suitable for code completion.
2121
2122/// Retrieve the string representation of the given type as a string
2123/// that has the appropriate lifetime for code completion.
2124///
2125/// This routine provides a fast path where we provide constant strings for
2126/// common type names.
2127static const char *GetCompletionTypeString(QualType T, ASTContext &Context,
2128 const PrintingPolicy &Policy,
2129 CodeCompletionAllocator &Allocator) {
2130 if (!T.getLocalQualifiers()) {
2131 // Built-in type names are constant strings.
2132 if (const BuiltinType *BT = dyn_cast<BuiltinType>(T))
2133 return BT->getNameAsCString(Policy);
2134
2135 // Anonymous tag types are constant strings.
2136 if (const TagType *TagT = dyn_cast<TagType>(T))
2137 if (TagDecl *Tag = TagT->getDecl())
2138 if (!Tag->hasNameForLinkage()) {
2139 switch (Tag->getTagKind()) {
2141 return "struct <anonymous>";
2143 return "__interface <anonymous>";
2144 case TagTypeKind::Class:
2145 return "class <anonymous>";
2146 case TagTypeKind::Union:
2147 return "union <anonymous>";
2148 case TagTypeKind::Enum:
2149 return "enum <anonymous>";
2150 }
2151 }
2152 }
2153
2154 // Slow path: format the type as a string.
2155 std::string Result;
2156 T.getAsStringInternal(Result, Policy);
2157 return Allocator.CopyString(Result);
2158}
2159
2160/// Add a completion for "this", if we're in a member function.
2161static void addThisCompletion(Sema &S, ResultBuilder &Results) {
2162 QualType ThisTy = S.getCurrentThisType();
2163 if (ThisTy.isNull())
2164 return;
2165
2166 CodeCompletionAllocator &Allocator = Results.getAllocator();
2167 CodeCompletionBuilder Builder(Allocator, Results.getCodeCompletionTUInfo());
2169 Builder.AddResultTypeChunk(
2170 GetCompletionTypeString(ThisTy, S.Context, Policy, Allocator));
2171 Builder.AddTypedTextChunk("this");
2172 Results.AddResult(CodeCompletionResult(Builder.TakeString()));
2173}
2174
2176 ResultBuilder &Results,
2177 const LangOptions &LangOpts) {
2178 if (!LangOpts.CPlusPlus11)
2179 return;
2180
2181 Builder.AddTypedTextChunk("static_assert");
2182 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2183 Builder.AddPlaceholderChunk("expression");
2184 Builder.AddChunk(CodeCompletionString::CK_Comma);
2185 Builder.AddPlaceholderChunk("message");
2186 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2187 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2188 Results.AddResult(CodeCompletionResult(Builder.TakeString()));
2189}
2190
2191static void AddOverrideResults(ResultBuilder &Results,
2192 const CodeCompletionContext &CCContext,
2193 CodeCompletionBuilder &Builder) {
2194 Sema &S = Results.getSema();
2195 const auto *CR = llvm::dyn_cast<CXXRecordDecl>(S.CurContext);
2196 // If not inside a class/struct/union return empty.
2197 if (!CR)
2198 return;
2199 // First store overrides within current class.
2200 // These are stored by name to make querying fast in the later step.
2201 llvm::StringMap<std::vector<FunctionDecl *>> Overrides;
2202 for (auto *Method : CR->methods()) {
2203 if (!Method->isVirtual() || !Method->getIdentifier())
2204 continue;
2205 Overrides[Method->getName()].push_back(Method);
2206 }
2207
2208 for (const auto &Base : CR->bases()) {
2209 const auto *BR = Base.getType().getTypePtr()->getAsCXXRecordDecl();
2210 if (!BR)
2211 continue;
2212 for (auto *Method : BR->methods()) {
2213 if (!Method->isVirtual() || !Method->getIdentifier())
2214 continue;
2215 const auto it = Overrides.find(Method->getName());
2216 bool IsOverriden = false;
2217 if (it != Overrides.end()) {
2218 for (auto *MD : it->second) {
2219 // If the method in current body is not an overload of this virtual
2220 // function, then it overrides this one.
2221 if (!S.IsOverload(MD, Method, false)) {
2222 IsOverriden = true;
2223 break;
2224 }
2225 }
2226 }
2227 if (!IsOverriden) {
2228 // Generates a new CodeCompletionResult by taking this function and
2229 // converting it into an override declaration with only one chunk in the
2230 // final CodeCompletionString as a TypedTextChunk.
2231 CodeCompletionResult CCR(Method, 0);
2232 PrintingPolicy Policy =
2235 S.getPreprocessor(), S.getASTContext(), Builder,
2236 /*IncludeBriefComments=*/false, CCContext, Policy);
2237 Results.AddResult(CodeCompletionResult(CCS, Method, CCP_CodePattern));
2238 }
2239 }
2240 }
2241}
2242
2243/// Add language constructs that show up for "ordinary" names.
2244static void
2246 Scope *S, Sema &SemaRef, ResultBuilder &Results) {
2247 CodeCompletionAllocator &Allocator = Results.getAllocator();
2248 CodeCompletionBuilder Builder(Allocator, Results.getCodeCompletionTUInfo());
2249
2251 switch (CCC) {
2253 if (SemaRef.getLangOpts().CPlusPlus) {
2254 if (Results.includeCodePatterns()) {
2255 // namespace <identifier> { declarations }
2256 Builder.AddTypedTextChunk("namespace");
2258 Builder.AddPlaceholderChunk("identifier");
2260 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
2262 Builder.AddPlaceholderChunk("declarations");
2264 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
2265 Results.AddResult(Result(Builder.TakeString()));
2266 }
2267
2268 // namespace identifier = identifier ;
2269 Builder.AddTypedTextChunk("namespace");
2271 Builder.AddPlaceholderChunk("name");
2272 Builder.AddChunk(CodeCompletionString::CK_Equal);
2273 Builder.AddPlaceholderChunk("namespace");
2274 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2275 Results.AddResult(Result(Builder.TakeString()));
2276
2277 // Using directives
2278 Builder.AddTypedTextChunk("using namespace");
2280 Builder.AddPlaceholderChunk("identifier");
2281 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2282 Results.AddResult(Result(Builder.TakeString()));
2283
2284 // asm(string-literal)
2285 Builder.AddTypedTextChunk("asm");
2286 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2287 Builder.AddPlaceholderChunk("string-literal");
2288 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2289 Results.AddResult(Result(Builder.TakeString()));
2290
2291 if (Results.includeCodePatterns()) {
2292 // Explicit template instantiation
2293 Builder.AddTypedTextChunk("template");
2295 Builder.AddPlaceholderChunk("declaration");
2296 Results.AddResult(Result(Builder.TakeString()));
2297 } else {
2298 Results.AddResult(Result("template", CodeCompletionResult::RK_Keyword));
2299 }
2300
2301 if (SemaRef.getLangOpts().CPlusPlus20 &&
2302 SemaRef.getLangOpts().CPlusPlusModules) {
2303 clang::Module *CurrentModule = SemaRef.getCurrentModule();
2304 if (SemaRef.CurContext->isTranslationUnit()) {
2305 /// Global module fragment can only be declared in the beginning of
2306 /// the file. CurrentModule should be null in this case.
2307 if (!CurrentModule) {
2308 // module;
2309 Builder.AddTypedTextChunk("module");
2310 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2312 Results.AddResult(Result(Builder.TakeString()));
2313 }
2314
2315 /// Named module should be declared in the beginning of the file,
2316 /// or after the global module fragment.
2317 if (!CurrentModule ||
2318 CurrentModule->Kind == Module::ExplicitGlobalModuleFragment ||
2319 CurrentModule->Kind == Module::ImplicitGlobalModuleFragment) {
2320 // export module;
2321 // module name;
2322 Builder.AddTypedTextChunk("module");
2324 Builder.AddPlaceholderChunk("name");
2325 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2327 Results.AddResult(Result(Builder.TakeString()));
2328 }
2329
2330 /// Import can occur in non module file or after the named module
2331 /// declaration.
2332 if (!CurrentModule ||
2333 CurrentModule->Kind == Module::ModuleInterfaceUnit ||
2334 CurrentModule->Kind == Module::ModulePartitionInterface) {
2335 // import name;
2336 Builder.AddTypedTextChunk("import");
2338 Builder.AddPlaceholderChunk("name");
2339 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2341 Results.AddResult(Result(Builder.TakeString()));
2342 }
2343
2344 if (CurrentModule &&
2345 (CurrentModule->Kind == Module::ModuleInterfaceUnit ||
2346 CurrentModule->Kind == Module::ModulePartitionInterface)) {
2347 // module: private;
2348 Builder.AddTypedTextChunk("module");
2349 Builder.AddChunk(CodeCompletionString::CK_Colon);
2351 Builder.AddTypedTextChunk("private");
2352 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2354 Results.AddResult(Result(Builder.TakeString()));
2355 }
2356 }
2357
2358 // export
2359 if (!CurrentModule ||
2361 Results.AddResult(Result("export", CodeCompletionResult::RK_Keyword));
2362 }
2363 }
2364
2365 if (SemaRef.getLangOpts().ObjC)
2366 AddObjCTopLevelResults(Results, true);
2367
2368 AddTypedefResult(Results);
2369 [[fallthrough]];
2370
2372 if (SemaRef.getLangOpts().CPlusPlus) {
2373 // Using declaration
2374 Builder.AddTypedTextChunk("using");
2376 Builder.AddPlaceholderChunk("qualifier");
2377 Builder.AddTextChunk("::");
2378 Builder.AddPlaceholderChunk("name");
2379 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2380 Results.AddResult(Result(Builder.TakeString()));
2381
2382 if (SemaRef.getLangOpts().CPlusPlus11)
2383 AddUsingAliasResult(Builder, Results);
2384
2385 // using typename qualifier::name (only in a dependent context)
2386 if (SemaRef.CurContext->isDependentContext()) {
2387 Builder.AddTypedTextChunk("using typename");
2389 Builder.AddPlaceholderChunk("qualifier");
2390 Builder.AddTextChunk("::");
2391 Builder.AddPlaceholderChunk("name");
2392 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2393 Results.AddResult(Result(Builder.TakeString()));
2394 }
2395
2396 AddStaticAssertResult(Builder, Results, SemaRef.getLangOpts());
2397
2398 if (CCC == SemaCodeCompletion::PCC_Class) {
2399 AddTypedefResult(Results);
2400
2401 bool IsNotInheritanceScope = !S->isClassInheritanceScope();
2402 // public:
2403 Builder.AddTypedTextChunk("public");
2404 if (IsNotInheritanceScope && Results.includeCodePatterns())
2405 Builder.AddChunk(CodeCompletionString::CK_Colon);
2406 Results.AddResult(Result(Builder.TakeString()));
2407
2408 // protected:
2409 Builder.AddTypedTextChunk("protected");
2410 if (IsNotInheritanceScope && Results.includeCodePatterns())
2411 Builder.AddChunk(CodeCompletionString::CK_Colon);
2412 Results.AddResult(Result(Builder.TakeString()));
2413
2414 // private:
2415 Builder.AddTypedTextChunk("private");
2416 if (IsNotInheritanceScope && Results.includeCodePatterns())
2417 Builder.AddChunk(CodeCompletionString::CK_Colon);
2418 Results.AddResult(Result(Builder.TakeString()));
2419
2420 // FIXME: This adds override results only if we are at the first word of
2421 // the declaration/definition. Also call this from other sides to have
2422 // more use-cases.
2424 Builder);
2425 }
2426 }
2427 [[fallthrough]];
2428
2430 if (SemaRef.getLangOpts().CPlusPlus20 &&
2432 Results.AddResult(Result("concept", CCP_Keyword));
2433 [[fallthrough]];
2434
2436 if (SemaRef.getLangOpts().CPlusPlus && Results.includeCodePatterns()) {
2437 // template < parameters >
2438 Builder.AddTypedTextChunk("template");
2439 Builder.AddChunk(CodeCompletionString::CK_LeftAngle);
2440 Builder.AddPlaceholderChunk("parameters");
2441 Builder.AddChunk(CodeCompletionString::CK_RightAngle);
2442 Results.AddResult(Result(Builder.TakeString()));
2443 } else {
2444 Results.AddResult(Result("template", CodeCompletionResult::RK_Keyword));
2445 }
2446
2447 if (SemaRef.getLangOpts().CPlusPlus20 &&
2450 Results.AddResult(Result("requires", CCP_Keyword));
2451
2452 AddStorageSpecifiers(CCC, SemaRef.getLangOpts(), Results);
2453 AddFunctionSpecifiers(CCC, SemaRef.getLangOpts(), Results);
2454 break;
2455
2457 AddObjCInterfaceResults(SemaRef.getLangOpts(), Results, true);
2458 AddStorageSpecifiers(CCC, SemaRef.getLangOpts(), Results);
2459 AddFunctionSpecifiers(CCC, SemaRef.getLangOpts(), Results);
2460 break;
2461
2463 AddObjCImplementationResults(SemaRef.getLangOpts(), Results, true);
2464 AddStorageSpecifiers(CCC, SemaRef.getLangOpts(), Results);
2465 AddFunctionSpecifiers(CCC, SemaRef.getLangOpts(), Results);
2466 break;
2467
2469 AddObjCVisibilityResults(SemaRef.getLangOpts(), Results, true);
2470 break;
2471
2475 if (SemaRef.getLangOpts().CPlusPlus11)
2476 AddUsingAliasResult(Builder, Results);
2477
2478 AddTypedefResult(Results);
2479
2480 if (SemaRef.getLangOpts().CPlusPlus && Results.includeCodePatterns() &&
2481 SemaRef.getLangOpts().CXXExceptions) {
2482 Builder.AddTypedTextChunk("try");
2484 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
2486 Builder.AddPlaceholderChunk("statements");
2488 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
2490 Builder.AddTextChunk("catch");
2492 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2493 Builder.AddPlaceholderChunk("declaration");
2494 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2496 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
2498 Builder.AddPlaceholderChunk("statements");
2500 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
2501 Results.AddResult(Result(Builder.TakeString()));
2502 }
2503 if (SemaRef.getLangOpts().ObjC)
2504 AddObjCStatementResults(Results, true);
2505
2506 if (Results.includeCodePatterns()) {
2507 // if (condition) { statements }
2508 Builder.AddTypedTextChunk("if");
2510 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2511 if (SemaRef.getLangOpts().CPlusPlus)
2512 Builder.AddPlaceholderChunk("condition");
2513 else
2514 Builder.AddPlaceholderChunk("expression");
2515 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2517 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
2519 Builder.AddPlaceholderChunk("statements");
2521 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
2522 Results.AddResult(Result(Builder.TakeString()));
2523
2524 // switch (condition) { }
2525 Builder.AddTypedTextChunk("switch");
2527 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2528 if (SemaRef.getLangOpts().CPlusPlus)
2529 Builder.AddPlaceholderChunk("condition");
2530 else
2531 Builder.AddPlaceholderChunk("expression");
2532 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2534 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
2536 Builder.AddPlaceholderChunk("cases");
2538 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
2539 Results.AddResult(Result(Builder.TakeString()));
2540 }
2541
2542 // Switch-specific statements.
2543 if (SemaRef.getCurFunction() &&
2544 !SemaRef.getCurFunction()->SwitchStack.empty()) {
2545 // case expression:
2546 Builder.AddTypedTextChunk("case");
2548 Builder.AddPlaceholderChunk("expression");
2549 Builder.AddChunk(CodeCompletionString::CK_Colon);
2550 Results.AddResult(Result(Builder.TakeString()));
2551
2552 // default:
2553 Builder.AddTypedTextChunk("default");
2554 Builder.AddChunk(CodeCompletionString::CK_Colon);
2555 Results.AddResult(Result(Builder.TakeString()));
2556 }
2557
2558 if (Results.includeCodePatterns()) {
2559 /// while (condition) { statements }
2560 Builder.AddTypedTextChunk("while");
2562 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2563 if (SemaRef.getLangOpts().CPlusPlus)
2564 Builder.AddPlaceholderChunk("condition");
2565 else
2566 Builder.AddPlaceholderChunk("expression");
2567 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2569 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
2571 Builder.AddPlaceholderChunk("statements");
2573 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
2574 Results.AddResult(Result(Builder.TakeString()));
2575
2576 // do { statements } while ( expression );
2577 Builder.AddTypedTextChunk("do");
2579 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
2581 Builder.AddPlaceholderChunk("statements");
2583 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
2584 Builder.AddTextChunk("while");
2586 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2587 Builder.AddPlaceholderChunk("expression");
2588 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2589 Results.AddResult(Result(Builder.TakeString()));
2590
2591 // for ( for-init-statement ; condition ; expression ) { statements }
2592 Builder.AddTypedTextChunk("for");
2594 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2595 if (SemaRef.getLangOpts().CPlusPlus || SemaRef.getLangOpts().C99)
2596 Builder.AddPlaceholderChunk("init-statement");
2597 else
2598 Builder.AddPlaceholderChunk("init-expression");
2599 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2601 Builder.AddPlaceholderChunk("condition");
2602 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2604 Builder.AddPlaceholderChunk("inc-expression");
2605 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2607 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
2609 Builder.AddPlaceholderChunk("statements");
2611 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
2612 Results.AddResult(Result(Builder.TakeString()));
2613
2614 if (SemaRef.getLangOpts().CPlusPlus11 || SemaRef.getLangOpts().ObjC) {
2615 // for ( range_declaration (:|in) range_expression ) { statements }
2616 Builder.AddTypedTextChunk("for");
2618 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2619 Builder.AddPlaceholderChunk("range-declaration");
2621 if (SemaRef.getLangOpts().ObjC)
2622 Builder.AddTextChunk("in");
2623 else
2624 Builder.AddChunk(CodeCompletionString::CK_Colon);
2626 Builder.AddPlaceholderChunk("range-expression");
2627 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2629 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
2631 Builder.AddPlaceholderChunk("statements");
2633 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
2634 Results.AddResult(Result(Builder.TakeString()));
2635 }
2636 }
2637
2638 if (S->getContinueParent()) {
2639 // continue ;
2640 Builder.AddTypedTextChunk("continue");
2641 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2642 Results.AddResult(Result(Builder.TakeString()));
2643 }
2644
2645 if (S->getBreakParent()) {
2646 // break ;
2647 Builder.AddTypedTextChunk("break");
2648 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2649 Results.AddResult(Result(Builder.TakeString()));
2650 }
2651
2652 // "return expression ;" or "return ;", depending on the return type.
2653 QualType ReturnType;
2654 if (const auto *Function = dyn_cast<FunctionDecl>(SemaRef.CurContext)) {
2655 if (!Function->getType().isNull())
2656 ReturnType = Function->getReturnType();
2657 } else if (const auto *Method =
2658 dyn_cast<ObjCMethodDecl>(SemaRef.CurContext))
2659 ReturnType = Method->getReturnType();
2660 else if (SemaRef.getCurBlock() &&
2661 !SemaRef.getCurBlock()->ReturnType.isNull())
2662 ReturnType = SemaRef.getCurBlock()->ReturnType;;
2663 if (ReturnType.isNull() || ReturnType->isVoidType()) {
2664 Builder.AddTypedTextChunk("return");
2665 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2666 Results.AddResult(Result(Builder.TakeString()));
2667 } else {
2668 assert(!ReturnType.isNull());
2669 // "return expression ;"
2670 Builder.AddTypedTextChunk("return");
2672 Builder.AddPlaceholderChunk("expression");
2673 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2674 Results.AddResult(Result(Builder.TakeString()));
2675 // "co_return expression ;" for coroutines(C++20).
2676 if (SemaRef.getLangOpts().CPlusPlus20) {
2677 Builder.AddTypedTextChunk("co_return");
2679 Builder.AddPlaceholderChunk("expression");
2680 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2681 Results.AddResult(Result(Builder.TakeString()));
2682 }
2683 // When boolean, also add 'return true;' and 'return false;'.
2684 if (ReturnType->isBooleanType()) {
2685 Builder.AddTypedTextChunk("return true");
2686 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2687 Results.AddResult(Result(Builder.TakeString()));
2688
2689 Builder.AddTypedTextChunk("return false");
2690 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2691 Results.AddResult(Result(Builder.TakeString()));
2692 }
2693 // For pointers, suggest 'return nullptr' in C++.
2694 if (SemaRef.getLangOpts().CPlusPlus11 &&
2695 (ReturnType->isPointerType() || ReturnType->isMemberPointerType())) {
2696 Builder.AddTypedTextChunk("return nullptr");
2697 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2698 Results.AddResult(Result(Builder.TakeString()));
2699 }
2700 }
2701
2702 // goto identifier ;
2703 Builder.AddTypedTextChunk("goto");
2705 Builder.AddPlaceholderChunk("label");
2706 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2707 Results.AddResult(Result(Builder.TakeString()));
2708
2709 // Using directives
2710 Builder.AddTypedTextChunk("using namespace");
2712 Builder.AddPlaceholderChunk("identifier");
2713 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2714 Results.AddResult(Result(Builder.TakeString()));
2715
2716 AddStaticAssertResult(Builder, Results, SemaRef.getLangOpts());
2717 }
2718 [[fallthrough]];
2719
2720 // Fall through (for statement expressions).
2723 AddStorageSpecifiers(CCC, SemaRef.getLangOpts(), Results);
2724 // Fall through: conditions and statements can have expressions.
2725 [[fallthrough]];
2726
2728 if (SemaRef.getLangOpts().ObjCAutoRefCount &&
2730 // (__bridge <type>)<expression>
2731 Builder.AddTypedTextChunk("__bridge");
2733 Builder.AddPlaceholderChunk("type");
2734 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2735 Builder.AddPlaceholderChunk("expression");
2736 Results.AddResult(Result(Builder.TakeString()));
2737
2738 // (__bridge_transfer <Objective-C type>)<expression>
2739 Builder.AddTypedTextChunk("__bridge_transfer");
2741 Builder.AddPlaceholderChunk("Objective-C type");
2742 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2743 Builder.AddPlaceholderChunk("expression");
2744 Results.AddResult(Result(Builder.TakeString()));
2745
2746 // (__bridge_retained <CF type>)<expression>
2747 Builder.AddTypedTextChunk("__bridge_retained");
2749 Builder.AddPlaceholderChunk("CF type");
2750 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2751 Builder.AddPlaceholderChunk("expression");
2752 Results.AddResult(Result(Builder.TakeString()));
2753 }
2754 // Fall through
2755 [[fallthrough]];
2756
2758 if (SemaRef.getLangOpts().CPlusPlus) {
2759 // 'this', if we're in a non-static member function.
2760 addThisCompletion(SemaRef, Results);
2761
2762 // true
2763 Builder.AddResultTypeChunk("bool");
2764 Builder.AddTypedTextChunk("true");
2765 Results.AddResult(Result(Builder.TakeString()));
2766
2767 // false
2768 Builder.AddResultTypeChunk("bool");
2769 Builder.AddTypedTextChunk("false");
2770 Results.AddResult(Result(Builder.TakeString()));
2771
2772 if (SemaRef.getLangOpts().RTTI) {
2773 // dynamic_cast < type-id > ( expression )
2774 Builder.AddTypedTextChunk("dynamic_cast");
2775 Builder.AddChunk(CodeCompletionString::CK_LeftAngle);
2776 Builder.AddPlaceholderChunk("type");
2777 Builder.AddChunk(CodeCompletionString::CK_RightAngle);
2778 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2779 Builder.AddPlaceholderChunk("expression");
2780 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2781 Results.AddResult(Result(Builder.TakeString()));
2782 }
2783
2784 // static_cast < type-id > ( expression )
2785 Builder.AddTypedTextChunk("static_cast");
2786 Builder.AddChunk(CodeCompletionString::CK_LeftAngle);
2787 Builder.AddPlaceholderChunk("type");
2788 Builder.AddChunk(CodeCompletionString::CK_RightAngle);
2789 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2790 Builder.AddPlaceholderChunk("expression");
2791 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2792 Results.AddResult(Result(Builder.TakeString()));
2793
2794 // reinterpret_cast < type-id > ( expression )
2795 Builder.AddTypedTextChunk("reinterpret_cast");
2796 Builder.AddChunk(CodeCompletionString::CK_LeftAngle);
2797 Builder.AddPlaceholderChunk("type");
2798 Builder.AddChunk(CodeCompletionString::CK_RightAngle);
2799 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2800 Builder.AddPlaceholderChunk("expression");
2801 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2802 Results.AddResult(Result(Builder.TakeString()));
2803
2804 // const_cast < type-id > ( expression )
2805 Builder.AddTypedTextChunk("const_cast");
2806 Builder.AddChunk(CodeCompletionString::CK_LeftAngle);
2807 Builder.AddPlaceholderChunk("type");
2808 Builder.AddChunk(CodeCompletionString::CK_RightAngle);
2809 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2810 Builder.AddPlaceholderChunk("expression");
2811 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2812 Results.AddResult(Result(Builder.TakeString()));
2813
2814 if (SemaRef.getLangOpts().RTTI) {
2815 // typeid ( expression-or-type )
2816 Builder.AddResultTypeChunk("std::type_info");
2817 Builder.AddTypedTextChunk("typeid");
2818 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2819 Builder.AddPlaceholderChunk("expression-or-type");
2820 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2821 Results.AddResult(Result(Builder.TakeString()));
2822 }
2823
2824 // new T ( ... )
2825 Builder.AddTypedTextChunk("new");
2827 Builder.AddPlaceholderChunk("type");
2828 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2829 Builder.AddPlaceholderChunk("expressions");
2830 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2831 Results.AddResult(Result(Builder.TakeString()));
2832
2833 // new T [ ] ( ... )
2834 Builder.AddTypedTextChunk("new");
2836 Builder.AddPlaceholderChunk("type");
2837 Builder.AddChunk(CodeCompletionString::CK_LeftBracket);
2838 Builder.AddPlaceholderChunk("size");
2839 Builder.AddChunk(CodeCompletionString::CK_RightBracket);
2840 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2841 Builder.AddPlaceholderChunk("expressions");
2842 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2843 Results.AddResult(Result(Builder.TakeString()));
2844
2845 // delete expression
2846 Builder.AddResultTypeChunk("void");
2847 Builder.AddTypedTextChunk("delete");
2849 Builder.AddPlaceholderChunk("expression");
2850 Results.AddResult(Result(Builder.TakeString()));
2851
2852 // delete [] expression
2853 Builder.AddResultTypeChunk("void");
2854 Builder.AddTypedTextChunk("delete");
2856 Builder.AddChunk(CodeCompletionString::CK_LeftBracket);
2857 Builder.AddChunk(CodeCompletionString::CK_RightBracket);
2859 Builder.AddPlaceholderChunk("expression");
2860 Results.AddResult(Result(Builder.TakeString()));
2861
2862 if (SemaRef.getLangOpts().CXXExceptions) {
2863 // throw expression
2864 Builder.AddResultTypeChunk("void");
2865 Builder.AddTypedTextChunk("throw");
2867 Builder.AddPlaceholderChunk("expression");
2868 Results.AddResult(Result(Builder.TakeString()));
2869 }
2870
2871 // FIXME: Rethrow?
2872
2873 if (SemaRef.getLangOpts().CPlusPlus11) {
2874 // nullptr
2875 Builder.AddResultTypeChunk("std::nullptr_t");
2876 Builder.AddTypedTextChunk("nullptr");
2877 Results.AddResult(Result(Builder.TakeString()));
2878
2879 // alignof
2880 Builder.AddResultTypeChunk("size_t");
2881 Builder.AddTypedTextChunk("alignof");
2882 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2883 Builder.AddPlaceholderChunk("type");
2884 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2885 Results.AddResult(Result(Builder.TakeString()));
2886
2887 // noexcept
2888 Builder.AddResultTypeChunk("bool");
2889 Builder.AddTypedTextChunk("noexcept");
2890 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2891 Builder.AddPlaceholderChunk("expression");
2892 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2893 Results.AddResult(Result(Builder.TakeString()));
2894
2895 // sizeof... expression
2896 Builder.AddResultTypeChunk("size_t");
2897 Builder.AddTypedTextChunk("sizeof...");
2898 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2899 Builder.AddPlaceholderChunk("parameter-pack");
2900 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2901 Results.AddResult(Result(Builder.TakeString()));
2902 }
2903
2904 if (SemaRef.getLangOpts().CPlusPlus20) {
2905 // co_await expression
2906 Builder.AddTypedTextChunk("co_await");
2908 Builder.AddPlaceholderChunk("expression");
2909 Results.AddResult(Result(Builder.TakeString()));
2910
2911 // co_yield expression
2912 Builder.AddTypedTextChunk("co_yield");
2914 Builder.AddPlaceholderChunk("expression");
2915 Results.AddResult(Result(Builder.TakeString()));
2916
2917 // requires (parameters) { requirements }
2918 Builder.AddResultTypeChunk("bool");
2919 Builder.AddTypedTextChunk("requires");
2921 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2922 Builder.AddPlaceholderChunk("parameters");
2923 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2925 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
2927 Builder.AddPlaceholderChunk("requirements");
2929 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
2930 Results.AddResult(Result(Builder.TakeString()));
2931
2932 if (SemaRef.CurContext->isRequiresExprBody()) {
2933 // requires expression ;
2934 Builder.AddTypedTextChunk("requires");
2936 Builder.AddPlaceholderChunk("expression");
2937 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
2938 Results.AddResult(Result(Builder.TakeString()));
2939 }
2940 }
2941 }
2942
2943 if (SemaRef.getLangOpts().ObjC) {
2944 // Add "super", if we're in an Objective-C class with a superclass.
2945 if (ObjCMethodDecl *Method = SemaRef.getCurMethodDecl()) {
2946 // The interface can be NULL.
2947 if (ObjCInterfaceDecl *ID = Method->getClassInterface())
2948 if (ID->getSuperClass()) {
2949 std::string SuperType;
2950 SuperType = ID->getSuperClass()->getNameAsString();
2951 if (Method->isInstanceMethod())
2952 SuperType += " *";
2953
2954 Builder.AddResultTypeChunk(Allocator.CopyString(SuperType));
2955 Builder.AddTypedTextChunk("super");
2956 Results.AddResult(Result(Builder.TakeString()));
2957 }
2958 }
2959
2960 AddObjCExpressionResults(Results, true);
2961 }
2962
2963 if (SemaRef.getLangOpts().C11) {
2964 // _Alignof
2965 Builder.AddResultTypeChunk("size_t");
2966 if (SemaRef.PP.isMacroDefined("alignof"))
2967 Builder.AddTypedTextChunk("alignof");
2968 else
2969 Builder.AddTypedTextChunk("_Alignof");
2970 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2971 Builder.AddPlaceholderChunk("type");
2972 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2973 Results.AddResult(Result(Builder.TakeString()));
2974 }
2975
2976 if (SemaRef.getLangOpts().C23) {
2977 // nullptr
2978 Builder.AddResultTypeChunk("nullptr_t");
2979 Builder.AddTypedTextChunk("nullptr");
2980 Results.AddResult(Result(Builder.TakeString()));
2981 }
2982
2983 // sizeof expression
2984 Builder.AddResultTypeChunk("size_t");
2985 Builder.AddTypedTextChunk("sizeof");
2986 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
2987 Builder.AddPlaceholderChunk("expression-or-type");
2988 Builder.AddChunk(CodeCompletionString::CK_RightParen);
2989 Results.AddResult(Result(Builder.TakeString()));
2990 break;
2991 }
2992
2995 break;
2996 }
2997
2998 if (WantTypesInContext(CCC, SemaRef.getLangOpts()))
2999 AddTypeSpecifierResults(SemaRef.getLangOpts(), Results);
3000
3001 if (SemaRef.getLangOpts().CPlusPlus && CCC != SemaCodeCompletion::PCC_Type)
3002 Results.AddResult(Result("operator"));
3003}
3004
3005/// If the given declaration has an associated type, add it as a result
3006/// type chunk.
3007static void AddResultTypeChunk(ASTContext &Context,
3008 const PrintingPolicy &Policy,
3009 const NamedDecl *ND, QualType BaseType,
3011 if (!ND)
3012 return;
3013
3014 // Skip constructors and conversion functions, which have their return types
3015 // built into their names.
3017 return;
3018
3019 // Determine the type of the declaration (if it has a type).
3020 QualType T;
3021 if (const FunctionDecl *Function = ND->getAsFunction())
3022 T = Function->getReturnType();
3023 else if (const auto *Method = dyn_cast<ObjCMethodDecl>(ND)) {
3024 if (!BaseType.isNull())
3025 T = Method->getSendResultType(BaseType);
3026 else
3027 T = Method->getReturnType();
3028 } else if (const auto *Enumerator = dyn_cast<EnumConstantDecl>(ND)) {
3029 T = Context.getCanonicalTagType(
3030 cast<EnumDecl>(Enumerator->getDeclContext()));
3031 } else if (isa<UnresolvedUsingValueDecl>(ND)) {
3032 /* Do nothing: ignore unresolved using declarations*/
3033 } else if (const auto *Ivar = dyn_cast<ObjCIvarDecl>(ND)) {
3034 if (!BaseType.isNull())
3035 T = Ivar->getUsageType(BaseType);
3036 else
3037 T = Ivar->getType();
3038 } else if (const auto *Value = dyn_cast<ValueDecl>(ND)) {
3039 T = Value->getType();
3040 } else if (const auto *Property = dyn_cast<ObjCPropertyDecl>(ND)) {
3041 if (!BaseType.isNull())
3042 T = Property->getUsageType(BaseType);
3043 else
3044 T = Property->getType();
3045 }
3046
3047 if (T.isNull() || Context.hasSameType(T, Context.DependentTy))
3048 return;
3049
3050 Result.AddResultTypeChunk(
3051 GetCompletionTypeString(T, Context, Policy, Result.getAllocator()));
3052}
3053
3055 const NamedDecl *FunctionOrMethod,
3057 if (SentinelAttr *Sentinel = FunctionOrMethod->getAttr<SentinelAttr>())
3058 if (Sentinel->getSentinel() == 0) {
3059 if (PP.getLangOpts().ObjC && PP.isMacroDefined("nil"))
3060 Result.AddTextChunk(", nil");
3061 else if (PP.isMacroDefined("NULL"))
3062 Result.AddTextChunk(", NULL");
3063 else
3064 Result.AddTextChunk(", (void*)0");
3065 }
3066}
3067
3068static std::string formatObjCParamQualifiers(unsigned ObjCQuals,
3069 QualType &Type) {
3070 std::string Result;
3071 if (ObjCQuals & Decl::OBJC_TQ_In)
3072 Result += "in ";
3073 else if (ObjCQuals & Decl::OBJC_TQ_Inout)
3074 Result += "inout ";
3075 else if (ObjCQuals & Decl::OBJC_TQ_Out)
3076 Result += "out ";
3077 if (ObjCQuals & Decl::OBJC_TQ_Bycopy)
3078 Result += "bycopy ";
3079 else if (ObjCQuals & Decl::OBJC_TQ_Byref)
3080 Result += "byref ";
3081 if (ObjCQuals & Decl::OBJC_TQ_Oneway)
3082 Result += "oneway ";
3083 if (ObjCQuals & Decl::OBJC_TQ_CSNullability) {
3084 if (auto nullability = AttributedType::stripOuterNullability(Type)) {
3085 switch (*nullability) {
3087 Result += "nonnull ";
3088 break;
3089
3091 Result += "nullable ";
3092 break;
3093
3095 Result += "null_unspecified ";
3096 break;
3097
3099 llvm_unreachable("Not supported as a context-sensitive keyword!");
3100 break;
3101 }
3102 }
3103 }
3104 return Result;
3105}
3106
3107/// Tries to find the most appropriate type location for an Objective-C
3108/// block placeholder.
3109///
3110/// This function ignores things like typedefs and qualifiers in order to
3111/// present the most relevant and accurate block placeholders in code completion
3112/// results.
3115 FunctionProtoTypeLoc &BlockProto,
3116 bool SuppressBlock = false) {
3117 if (!TSInfo)
3118 return;
3119 TypeLoc TL = TSInfo->getTypeLoc().getUnqualifiedLoc();
3120 while (true) {
3121 // Look through typedefs.
3122 if (!SuppressBlock) {
3123 if (TypedefTypeLoc TypedefTL = TL.getAsAdjusted<TypedefTypeLoc>()) {
3124 if (TypeSourceInfo *InnerTSInfo =
3125 TypedefTL.getDecl()->getTypeSourceInfo()) {
3126 TL = InnerTSInfo->getTypeLoc().getUnqualifiedLoc();
3127 continue;
3128 }
3129 }
3130
3131 // Look through qualified types
3132 if (QualifiedTypeLoc QualifiedTL = TL.getAs<QualifiedTypeLoc>()) {
3133 TL = QualifiedTL.getUnqualifiedLoc();
3134 continue;
3135 }
3136
3137 if (AttributedTypeLoc AttrTL = TL.getAs<AttributedTypeLoc>()) {
3138 TL = AttrTL.getModifiedLoc();
3139 continue;
3140 }
3141 }
3142
3143 // Try to get the function prototype behind the block pointer type,
3144 // then we're done.
3145 if (BlockPointerTypeLoc BlockPtr = TL.getAs<BlockPointerTypeLoc>()) {
3146 TL = BlockPtr.getPointeeLoc().IgnoreParens();
3147 Block = TL.getAs<FunctionTypeLoc>();
3148 BlockProto = TL.getAs<FunctionProtoTypeLoc>();
3149 }
3150 break;
3151 }
3152}
3153
3154static std::string formatBlockPlaceholder(
3155 const PrintingPolicy &Policy, const NamedDecl *BlockDecl,
3157 bool SuppressBlockName = false, bool SuppressBlock = false,
3158 std::optional<ArrayRef<QualType>> ObjCSubsts = std::nullopt);
3159
3160static std::string FormatFunctionParameter(
3161 const PrintingPolicy &Policy, const DeclaratorDecl *Param,
3162 bool SuppressName = false, bool SuppressBlock = false,
3163 std::optional<ArrayRef<QualType>> ObjCSubsts = std::nullopt) {
3164 // Params are unavailable in FunctionTypeLoc if the FunctionType is invalid.
3165 // It would be better to pass in the param Type, which is usually available.
3166 // But this case is rare, so just pretend we fell back to int as elsewhere.
3167 if (!Param)
3168 return "int";
3170 if (const auto *PVD = dyn_cast<ParmVarDecl>(Param))
3171 ObjCQual = PVD->getObjCDeclQualifier();
3172 bool ObjCMethodParam = isa<ObjCMethodDecl>(Param->getDeclContext());
3173 if (Param->getType()->isDependentType() ||
3174 !Param->getType()->isBlockPointerType()) {
3175 // The argument for a dependent or non-block parameter is a placeholder
3176 // containing that parameter's type.
3177 std::string Result;
3178
3179 if (Param->getIdentifier() && !ObjCMethodParam && !SuppressName)
3180 Result = std::string(Param->getIdentifier()->deuglifiedName());
3181
3182 QualType Type = Param->getType();
3183 if (ObjCSubsts)
3184 Type = Type.substObjCTypeArgs(Param->getASTContext(), *ObjCSubsts,
3186 if (ObjCMethodParam) {
3187 Result = "(" + formatObjCParamQualifiers(ObjCQual, Type);
3188 Result += Type.getAsString(Policy) + ")";
3189 if (Param->getIdentifier() && !SuppressName)
3190 Result += Param->getIdentifier()->deuglifiedName();
3191 } else {
3192 Type.getAsStringInternal(Result, Policy);
3193 }
3194 return Result;
3195 }
3196
3197 // The argument for a block pointer parameter is a block literal with
3198 // the appropriate type.
3200 FunctionProtoTypeLoc BlockProto;
3201 findTypeLocationForBlockDecl(Param->getTypeSourceInfo(), Block, BlockProto,
3202 SuppressBlock);
3203 // Try to retrieve the block type information from the property if this is a
3204 // parameter in a setter.
3205 if (!Block && ObjCMethodParam &&
3206 cast<ObjCMethodDecl>(Param->getDeclContext())->isPropertyAccessor()) {
3207 if (const auto *PD = cast<ObjCMethodDecl>(Param->getDeclContext())
3208 ->findPropertyDecl(/*CheckOverrides=*/false))
3209 findTypeLocationForBlockDecl(PD->getTypeSourceInfo(), Block, BlockProto,
3210 SuppressBlock);
3211 }
3212
3213 if (!Block) {
3214 // We were unable to find a FunctionProtoTypeLoc with parameter names
3215 // for the block; just use the parameter type as a placeholder.
3216 std::string Result;
3217 if (!ObjCMethodParam && Param->getIdentifier())
3218 Result = std::string(Param->getIdentifier()->deuglifiedName());
3219
3220 QualType Type = Param->getType().getUnqualifiedType();
3221
3222 if (ObjCMethodParam) {
3223 Result = Type.getAsString(Policy);
3224 std::string Quals = formatObjCParamQualifiers(ObjCQual, Type);
3225 if (!Quals.empty())
3226 Result = "(" + Quals + " " + Result + ")";
3227 if (Result.back() != ')')
3228 Result += " ";
3229 if (Param->getIdentifier())
3230 Result += Param->getIdentifier()->deuglifiedName();
3231 } else {
3232 Type.getAsStringInternal(Result, Policy);
3233 }
3234
3235 return Result;
3236 }
3237
3238 // We have the function prototype behind the block pointer type, as it was
3239 // written in the source.
3240 return formatBlockPlaceholder(Policy, Param, Block, BlockProto,
3241 /*SuppressBlockName=*/false, SuppressBlock,
3242 ObjCSubsts);
3243}
3244
3245/// Returns a placeholder string that corresponds to an Objective-C block
3246/// declaration.
3247///
3248/// \param BlockDecl A declaration with an Objective-C block type.
3249///
3250/// \param Block The most relevant type location for that block type.
3251///
3252/// \param SuppressBlockName Determines whether or not the name of the block
3253/// declaration is included in the resulting string.
3254static std::string
3257 bool SuppressBlockName, bool SuppressBlock,
3258 std::optional<ArrayRef<QualType>> ObjCSubsts) {
3259 std::string Result;
3260 QualType ResultType = Block.getTypePtr()->getReturnType();
3261 if (ObjCSubsts)
3262 ResultType =
3263 ResultType.substObjCTypeArgs(BlockDecl->getASTContext(), *ObjCSubsts,
3265 if (!ResultType->isVoidType() || SuppressBlock)
3266 ResultType.getAsStringInternal(Result, Policy);
3267
3268 // Format the parameter list.
3269 std::string Params;
3270 if (!BlockProto || Block.getNumParams() == 0) {
3271 if (BlockProto && BlockProto.getTypePtr()->isVariadic())
3272 Params = "(...)";
3273 else
3274 Params = "(void)";
3275 } else {
3276 Params += "(";
3277 for (unsigned I = 0, N = Block.getNumParams(); I != N; ++I) {
3278 if (I)
3279 Params += ", ";
3280 Params += FormatFunctionParameter(Policy, Block.getParam(I),
3281 /*SuppressName=*/false,
3282 /*SuppressBlock=*/true, ObjCSubsts);
3283
3284 if (I == N - 1 && BlockProto.getTypePtr()->isVariadic())
3285 Params += ", ...";
3286 }
3287 Params += ")";
3288 }
3289
3290 if (SuppressBlock) {
3291 // Format as a parameter.
3292 Result = Result + " (^";
3293 if (!SuppressBlockName && BlockDecl->getIdentifier())
3294 Result += BlockDecl->getIdentifier()->getName();
3295 Result += ")";
3296 Result += Params;
3297 } else {
3298 // Format as a block literal argument.
3299 Result = '^' + Result;
3300 Result += Params;
3301
3302 if (!SuppressBlockName && BlockDecl->getIdentifier())
3303 Result += BlockDecl->getIdentifier()->getName();
3304 }
3305
3306 return Result;
3307}
3308
3309static std::string GetDefaultValueString(const ParmVarDecl *Param,
3310 const SourceManager &SM,
3311 const LangOptions &LangOpts) {
3312 const SourceRange SrcRange = Param->getDefaultArgRange();
3313 CharSourceRange CharSrcRange = CharSourceRange::getTokenRange(SrcRange);
3314 bool Invalid = CharSrcRange.isInvalid();
3315 if (Invalid)
3316 return "";
3317 StringRef srcText =
3318 Lexer::getSourceText(CharSrcRange, SM, LangOpts, &Invalid);
3319 if (Invalid)
3320 return "";
3321
3322 if (srcText.empty() || srcText == "=") {
3323 // Lexer can't determine the value.
3324 // This happens if the code is incorrect (for example class is forward
3325 // declared).
3326 return "";
3327 }
3328 std::string DefValue(srcText.str());
3329 // FIXME: remove this check if the Lexer::getSourceText value is fixed and
3330 // this value always has (or always does not have) '=' in front of it
3331 if (DefValue.at(0) != '=') {
3332 // If we don't have '=' in front of value.
3333 // Lexer returns built-in types values without '=' and user-defined types
3334 // values with it.
3335 return " = " + DefValue;
3336 }
3337 return " " + DefValue;
3338}
3339
3340/// Add function parameter chunks to the given code completion string.
3342 Preprocessor &PP, const PrintingPolicy &Policy,
3343 const FunctionDecl *Function, CodeCompletionBuilder &Result,
3344 unsigned Start = 0, bool InOptional = false, bool FunctionCanBeCall = true,
3345 bool IsInDeclarationContext = false) {
3346 bool FirstParameter = true;
3347 bool AsInformativeChunk = !(FunctionCanBeCall || IsInDeclarationContext);
3348
3349 const FunctionDecl *BetterSignatureDecl = BetterSignature(Function, Start);
3350
3351 for (unsigned P = Start, N = Function->getNumParams(); P != N; ++P) {
3352 const ParmVarDecl *Param = BetterSignatureDecl->getParamDecl(P);
3353
3354 if (Param->hasDefaultArg() && !InOptional && !IsInDeclarationContext &&
3355 !AsInformativeChunk) {
3356 // When we see an optional default argument, put that argument and
3357 // the remaining default arguments into a new, optional string.
3358 CodeCompletionBuilder Opt(Result.getAllocator(),
3359 Result.getCodeCompletionTUInfo());
3360 if (!FirstParameter)
3362 AddFunctionParameterChunks(PP, Policy, Function, Opt, P, true);
3363 Result.AddOptionalChunk(Opt.TakeString());
3364 break;
3365 }
3366
3367 // C++23 introduces an explicit object parameter, a.k.a. "deducing this"
3368 // Skip it for autocomplete and treat the next parameter as the first
3369 // parameter
3370 if (FirstParameter && Param->isExplicitObjectParameter()) {
3371 continue;
3372 }
3373
3374 if (FirstParameter)
3375 FirstParameter = false;
3376 else {
3377 if (AsInformativeChunk)
3378 Result.AddInformativeChunk(", ");
3379 else
3381 }
3382
3383 InOptional = false;
3384
3385 // Format the placeholder string.
3386 std::string PlaceholderStr = FormatFunctionParameter(Policy, Param);
3387 std::string DefaultValue;
3388 if (Param->hasDefaultArg()) {
3389 if (IsInDeclarationContext)
3390 DefaultValue = GetDefaultValueString(Param, PP.getSourceManager(),
3391 PP.getLangOpts());
3392 else
3393 PlaceholderStr += GetDefaultValueString(Param, PP.getSourceManager(),
3394 PP.getLangOpts());
3395 }
3396
3397 if (Function->isVariadic() && P == N - 1)
3398 PlaceholderStr += ", ...";
3399
3400 // Add the placeholder string.
3401 if (AsInformativeChunk)
3402 Result.AddInformativeChunk(
3403 Result.getAllocator().CopyString(PlaceholderStr));
3404 else if (IsInDeclarationContext) { // No placeholders in declaration context
3405 Result.AddTextChunk(Result.getAllocator().CopyString(PlaceholderStr));
3406 if (DefaultValue.length() != 0)
3407 Result.AddInformativeChunk(
3408 Result.getAllocator().CopyString(DefaultValue));
3409 } else
3410 Result.AddPlaceholderChunk(
3411 Result.getAllocator().CopyString(PlaceholderStr));
3412 }
3413
3414 if (const auto *Proto = Function->getType()->getAs<FunctionProtoType>())
3415 if (Proto->isVariadic()) {
3416 if (Proto->getNumParams() == 0)
3417 Result.AddPlaceholderChunk("...");
3418
3419 MaybeAddSentinel(PP, Function, Result);
3420 }
3421}
3422
3423/// Add template parameter chunks to the given code completion string.
3425 ASTContext &Context, const PrintingPolicy &Policy,
3427 unsigned MaxParameters = 0, unsigned Start = 0, bool InDefaultArg = false,
3428 bool AsInformativeChunk = false) {
3429 bool FirstParameter = true;
3430
3431 // Prefer to take the template parameter names from the first declaration of
3432 // the template.
3433 Template = cast<TemplateDecl>(Template->getCanonicalDecl());
3434
3435 TemplateParameterList *Params = Template->getTemplateParameters();
3436 TemplateParameterList::iterator PEnd = Params->end();
3437 if (MaxParameters)
3438 PEnd = Params->begin() + MaxParameters;
3439 for (TemplateParameterList::iterator P = Params->begin() + Start; P != PEnd;
3440 ++P) {
3441 bool HasDefaultArg = false;
3442 std::string PlaceholderStr;
3443 if (TemplateTypeParmDecl *TTP = dyn_cast<TemplateTypeParmDecl>(*P)) {
3444 if (TTP->wasDeclaredWithTypename())
3445 PlaceholderStr = "typename";
3446 else if (const auto *TC = TTP->getTypeConstraint()) {
3447 llvm::raw_string_ostream OS(PlaceholderStr);
3448 TC->print(OS, Policy);
3449 } else
3450 PlaceholderStr = "class";
3451
3452 if (TTP->getIdentifier()) {
3453 PlaceholderStr += ' ';
3454 PlaceholderStr += TTP->getIdentifier()->deuglifiedName();
3455 }
3456
3457 HasDefaultArg = TTP->hasDefaultArgument();
3458 } else if (NonTypeTemplateParmDecl *NTTP =
3459 dyn_cast<NonTypeTemplateParmDecl>(*P)) {
3460 if (NTTP->getIdentifier())
3461 PlaceholderStr = std::string(NTTP->getIdentifier()->deuglifiedName());
3462 NTTP->getType().getAsStringInternal(PlaceholderStr, Policy);
3463 HasDefaultArg = NTTP->hasDefaultArgument();
3464 } else {
3467
3468 // Since putting the template argument list into the placeholder would
3469 // be very, very long, we just use an abbreviation.
3470 PlaceholderStr = "template<...> class";
3471 if (TTP->getIdentifier()) {
3472 PlaceholderStr += ' ';
3473 PlaceholderStr += TTP->getIdentifier()->deuglifiedName();
3474 }
3475
3476 HasDefaultArg = TTP->hasDefaultArgument();
3477 }
3478
3479 if (HasDefaultArg && !InDefaultArg && !AsInformativeChunk) {
3480 // When we see an optional default argument, put that argument and
3481 // the remaining default arguments into a new, optional string.
3482 CodeCompletionBuilder Opt(Result.getAllocator(),
3483 Result.getCodeCompletionTUInfo());
3484 if (!FirstParameter)
3486 AddTemplateParameterChunks(Context, Policy, Template, Opt, MaxParameters,
3487 P - Params->begin(), true);
3488 Result.AddOptionalChunk(Opt.TakeString());
3489 break;
3490 }
3491
3492 InDefaultArg = false;
3493
3494 if (FirstParameter)
3495 FirstParameter = false;
3496 else {
3497 if (AsInformativeChunk)
3498 Result.AddInformativeChunk(", ");
3499 else
3501 }
3502
3503 if (AsInformativeChunk)
3504 Result.AddInformativeChunk(
3505 Result.getAllocator().CopyString(PlaceholderStr));
3506 else // Add the placeholder string.
3507 Result.AddPlaceholderChunk(
3508 Result.getAllocator().CopyString(PlaceholderStr));
3509 }
3510}
3511
3512/// Add a qualifier to the given code-completion string, if the
3513/// provided nested-name-specifier is non-NULL.
3515 NestedNameSpecifier Qualifier,
3516 bool QualifierIsInformative,
3517 ASTContext &Context,
3518 const PrintingPolicy &Policy) {
3519 if (!Qualifier)
3520 return;
3521
3522 std::string PrintedNNS;
3523 {
3524 llvm::raw_string_ostream OS(PrintedNNS);
3525 Qualifier.print(OS, Policy);
3526 }
3527 if (QualifierIsInformative)
3528 Result.AddInformativeChunk(Result.getAllocator().CopyString(PrintedNNS));
3529 else
3530 Result.AddTextChunk(Result.getAllocator().CopyString(PrintedNNS));
3531}
3532
3534 const Qualifiers Quals,
3535 bool AsInformativeChunk = true) {
3536 // FIXME: Add ref-qualifier!
3537
3538 // Handle single qualifiers without copying
3539 if (Quals.hasOnlyConst()) {
3540 if (AsInformativeChunk)
3541 Result.AddInformativeChunk(" const");
3542 else
3543 Result.AddTextChunk(" const");
3544 return;
3545 }
3546
3547 if (Quals.hasOnlyVolatile()) {
3548 if (AsInformativeChunk)
3549 Result.AddInformativeChunk(" volatile");
3550 else
3551 Result.AddTextChunk(" volatile");
3552 return;
3553 }
3554
3555 if (Quals.hasOnlyRestrict()) {
3556 if (AsInformativeChunk)
3557 Result.AddInformativeChunk(" restrict");
3558 else
3559 Result.AddTextChunk(" restrict");
3560 return;
3561 }
3562
3563 // Handle multiple qualifiers.
3564 std::string QualsStr;
3565 if (Quals.hasConst())
3566 QualsStr += " const";
3567 if (Quals.hasVolatile())
3568 QualsStr += " volatile";
3569 if (Quals.hasRestrict())
3570 QualsStr += " restrict";
3571
3572 if (AsInformativeChunk)
3573 Result.AddInformativeChunk(Result.getAllocator().CopyString(QualsStr));
3574 else
3575 Result.AddTextChunk(Result.getAllocator().CopyString(QualsStr));
3576}
3577
3578static void
3580 const FunctionDecl *Function,
3581 bool AsInformativeChunks = true) {
3582 if (auto *CxxMethodDecl = llvm::dyn_cast_if_present<CXXMethodDecl>(Function);
3583 CxxMethodDecl && CxxMethodDecl->hasCXXExplicitFunctionObjectParameter()) {
3584 // if explicit object method, infer quals from the object parameter
3585 const auto Quals = CxxMethodDecl->getFunctionObjectParameterType();
3586 if (!Quals.hasQualifiers())
3587 return;
3588
3589 AddFunctionTypeQuals(Result, Quals.getQualifiers(), AsInformativeChunks);
3590 } else {
3591 const auto *Proto = Function->getType()->getAs<FunctionProtoType>();
3592 if (!Proto || !Proto->getMethodQuals())
3593 return;
3594
3595 AddFunctionTypeQuals(Result, Proto->getMethodQuals(), AsInformativeChunks);
3596 }
3597}
3598
3599static void
3600AddFunctionExceptSpecToCompletionString(std::string &NameAndSignature,
3601 const FunctionDecl *Function) {
3602 const auto *Proto = Function->getType()->getAs<FunctionProtoType>();
3603 if (!Proto)
3604 return;
3605
3606 auto ExceptInfo = Proto->getExceptionSpecInfo();
3607 switch (ExceptInfo.Type) {
3608 case EST_BasicNoexcept:
3609 case EST_NoexceptTrue:
3610 NameAndSignature += " noexcept";
3611 break;
3612
3613 default:
3614 break;
3615 }
3616}
3617
3618/// Add the name of the given declaration
3619static void AddTypedNameChunk(ASTContext &Context, const PrintingPolicy &Policy,
3620 const NamedDecl *ND,
3622 DeclarationName Name = ND->getDeclName();
3623 if (!Name)
3624 return;
3625
3626 switch (Name.getNameKind()) {
3628 const char *OperatorName = nullptr;
3629 switch (Name.getCXXOverloadedOperator()) {
3630 case OO_None:
3631 case OO_Conditional:
3633 OperatorName = "operator";
3634 break;
3635
3636#define OVERLOADED_OPERATOR(Name, Spelling, Token, Unary, Binary, MemberOnly) \
3637 case OO_##Name: \
3638 OperatorName = "operator" Spelling; \
3639 break;
3640#define OVERLOADED_OPERATOR_MULTI(Name, Spelling, Unary, Binary, MemberOnly)
3641#include "clang/Basic/OperatorKinds.def"
3642
3643 case OO_New:
3644 OperatorName = "operator new";
3645 break;
3646 case OO_Delete:
3647 OperatorName = "operator delete";
3648 break;
3649 case OO_Array_New:
3650 OperatorName = "operator new[]";
3651 break;
3652 case OO_Array_Delete:
3653 OperatorName = "operator delete[]";
3654 break;
3655 case OO_Call:
3656 OperatorName = "operator()";
3657 break;
3658 case OO_Subscript:
3659 OperatorName = "operator[]";
3660 break;
3661 }
3662 Result.AddTypedTextChunk(OperatorName);
3663 break;
3664 }
3665
3670 Result.AddTypedTextChunk(
3671 Result.getAllocator().CopyString(ND->getNameAsString()));
3672 break;
3673
3679 break;
3680
3682 CXXRecordDecl *Record = nullptr;
3683 QualType Ty = Name.getCXXNameType();
3684 if (auto *RD = Ty->getAsCXXRecordDecl()) {
3685 Record = RD;
3686 } else {
3687 Result.AddTypedTextChunk(
3688 Result.getAllocator().CopyString(ND->getNameAsString()));
3689 break;
3690 }
3691
3692 Result.AddTypedTextChunk(
3693 Result.getAllocator().CopyString(Record->getNameAsString()));
3694 if (ClassTemplateDecl *Template = Record->getDescribedClassTemplate()) {
3696 AddTemplateParameterChunks(Context, Policy, Template, Result);
3698 }
3699 break;
3700 }
3701 }
3702}
3703
3705 Sema &S, const CodeCompletionContext &CCContext,
3706 CodeCompletionAllocator &Allocator, CodeCompletionTUInfo &CCTUInfo,
3707 bool IncludeBriefComments) {
3708 return CreateCodeCompletionString(S.Context, S.PP, CCContext, Allocator,
3709 CCTUInfo, IncludeBriefComments);
3710}
3711
3713 Preprocessor &PP, CodeCompletionAllocator &Allocator,
3714 CodeCompletionTUInfo &CCTUInfo) {
3715 assert(Kind == RK_Macro);
3716 CodeCompletionBuilder Result(Allocator, CCTUInfo, Priority, Availability);
3717 const MacroInfo *MI = PP.getMacroInfo(Macro);
3718 Result.AddTypedTextChunk(Result.getAllocator().CopyString(Macro->getName()));
3719
3720 if (!MI || !MI->isFunctionLike())
3721 return Result.TakeString();
3722
3723 // Format a function-like macro with placeholders for the arguments.
3725 MacroInfo::param_iterator A = MI->param_begin(), AEnd = MI->param_end();
3726
3727 // C99 variadic macros add __VA_ARGS__ at the end. Skip it.
3728 if (MI->isC99Varargs()) {
3729 --AEnd;
3730
3731 if (A == AEnd) {
3732 Result.AddPlaceholderChunk("...");
3733 }
3734 }
3735
3736 for (MacroInfo::param_iterator A = MI->param_begin(); A != AEnd; ++A) {
3737 if (A != MI->param_begin())
3739
3740 if (MI->isVariadic() && (A + 1) == AEnd) {
3741 SmallString<32> Arg = (*A)->getName();
3742 if (MI->isC99Varargs())
3743 Arg += ", ...";
3744 else
3745 Arg += "...";
3746 Result.AddPlaceholderChunk(Result.getAllocator().CopyString(Arg));
3747 break;
3748 }
3749
3750 // Non-variadic macros are simple.
3751 Result.AddPlaceholderChunk(
3752 Result.getAllocator().CopyString((*A)->getName()));
3753 }
3755 return Result.TakeString();
3756}
3757
3758/// If possible, create a new code completion string for the given
3759/// result.
3760///
3761/// \returns Either a new, heap-allocated code completion string describing
3762/// how to use this result, or NULL to indicate that the string or name of the
3763/// result is all that is needed.
3765 ASTContext &Ctx, Preprocessor &PP, const CodeCompletionContext &CCContext,
3766 CodeCompletionAllocator &Allocator, CodeCompletionTUInfo &CCTUInfo,
3767 bool IncludeBriefComments) {
3768 if (Kind == RK_Macro)
3769 return CreateCodeCompletionStringForMacro(PP, Allocator, CCTUInfo);
3770
3771 CodeCompletionBuilder Result(Allocator, CCTUInfo, Priority, Availability);
3772
3774 if (Kind == RK_Pattern) {
3775 Pattern->Priority = Priority;
3776 Pattern->Availability = Availability;
3777
3778 if (Declaration) {
3779 Result.addParentContext(Declaration->getDeclContext());
3780 Pattern->ParentName = Result.getParentName();
3781 if (const RawComment *RC =
3783 Result.addBriefComment(RC->getBriefText(Ctx));
3784 Pattern->BriefComment = Result.getBriefComment();
3785 }
3786 }
3787
3788 return Pattern;
3789 }
3790
3791 if (Kind == RK_Keyword) {
3792 Result.AddTypedTextChunk(Keyword);
3793 return Result.TakeString();
3794 }
3795 assert(Kind == RK_Declaration && "Missed a result kind?");
3797 PP, Ctx, Result, IncludeBriefComments, CCContext, Policy);
3798}
3799
3801 std::string &BeforeName,
3802 std::string &NameAndSignature) {
3803 bool SeenTypedChunk = false;
3804 for (auto &Chunk : CCS) {
3805 if (Chunk.Kind == CodeCompletionString::CK_Optional) {
3806 assert(SeenTypedChunk && "optional parameter before name");
3807 // Note that we put all chunks inside into NameAndSignature.
3808 printOverrideString(*Chunk.Optional, NameAndSignature, NameAndSignature);
3809 continue;
3810 }
3811 SeenTypedChunk |= Chunk.Kind == CodeCompletionString::CK_TypedText;
3812 if (SeenTypedChunk)
3813 NameAndSignature += Chunk.Text;
3814 else
3815 BeforeName += Chunk.Text;
3816 }
3817}
3818
3822 bool IncludeBriefComments, const CodeCompletionContext &CCContext,
3823 PrintingPolicy &Policy) {
3824 auto *CCS = createCodeCompletionStringForDecl(PP, Ctx, Result,
3825 /*IncludeBriefComments=*/false,
3826 CCContext, Policy);
3827 std::string BeforeName;
3828 std::string NameAndSignature;
3829 // For overrides all chunks go into the result, none are informative.
3830 printOverrideString(*CCS, BeforeName, NameAndSignature);
3831
3832 // If the virtual function is declared with "noexcept", add it in the result
3833 // code completion string.
3834 const auto *VirtualFunc = dyn_cast<FunctionDecl>(Declaration);
3835 assert(VirtualFunc && "overridden decl must be a function");
3836 AddFunctionExceptSpecToCompletionString(NameAndSignature, VirtualFunc);
3837
3838 NameAndSignature += " override";
3839
3840 Result.AddTextChunk(Result.getAllocator().CopyString(BeforeName));
3842 Result.AddTypedTextChunk(Result.getAllocator().CopyString(NameAndSignature));
3843 return Result.TakeString();
3844}
3845
3846// FIXME: Right now this works well with lambdas. Add support for other functor
3847// types like std::function.
3849 const auto *VD = dyn_cast<VarDecl>(ND);
3850 if (!VD)
3851 return nullptr;
3852 const auto *RecordDecl = VD->getType()->getAsCXXRecordDecl();
3853 if (!RecordDecl || !RecordDecl->isLambda())
3854 return nullptr;
3855 return RecordDecl->getLambdaCallOperator();
3856}
3857
3860 bool IncludeBriefComments, const CodeCompletionContext &CCContext,
3861 PrintingPolicy &Policy) {
3862 const NamedDecl *ND = Declaration;
3863 Result.addParentContext(ND->getDeclContext());
3864
3865 if (IncludeBriefComments) {
3866 // Add documentation comment, if it exists.
3867 if (const RawComment *RC = getCompletionComment(Ctx, Declaration)) {
3868 Result.addBriefComment(RC->getBriefText(Ctx));
3869 }
3870 }
3871
3873 Result.AddTypedTextChunk(
3874 Result.getAllocator().CopyString(ND->getNameAsString()));
3875 Result.AddTextChunk("::");
3876 return Result.TakeString();
3877 }
3878
3879 for (const auto *I : ND->specific_attrs<AnnotateAttr>())
3880 Result.AddAnnotation(Result.getAllocator().CopyString(I->getAnnotation()));
3881
3882 auto AddFunctionTypeAndResult = [&](const FunctionDecl *Function) {
3883 AddResultTypeChunk(Ctx, Policy, Function, CCContext.getBaseType(), Result);
3885 Ctx, Policy);
3886 AddTypedNameChunk(Ctx, Policy, ND, Result);
3887 bool InsertParameters = FunctionCanBeCall || DeclaringEntity;
3888 if (InsertParameters)
3890 else
3891 Result.AddInformativeChunk("(");
3892 AddFunctionParameterChunks(PP, Policy, Function, Result, /*Start=*/0,
3893 /*InOptional=*/false,
3894 /*FunctionCanBeCall=*/FunctionCanBeCall,
3895 /*IsInDeclarationContext=*/DeclaringEntity);
3896 if (InsertParameters)
3898 else
3899 Result.AddInformativeChunk(")");
3901 Result, Function, /*AsInformativeChunks=*/!DeclaringEntity);
3902 };
3903
3904 if (const auto *Function = dyn_cast<FunctionDecl>(ND)) {
3905 AddFunctionTypeAndResult(Function);
3906 return Result.TakeString();
3907 }
3908
3909 if (const auto *CallOperator =
3910 dyn_cast_or_null<FunctionDecl>(extractFunctorCallOperator(ND))) {
3911 AddFunctionTypeAndResult(CallOperator);
3912 return Result.TakeString();
3913 }
3914
3915 AddResultTypeChunk(Ctx, Policy, ND, CCContext.getBaseType(), Result);
3916
3917 if (const FunctionTemplateDecl *FunTmpl =
3918 dyn_cast<FunctionTemplateDecl>(ND)) {
3920 Ctx, Policy);
3921 FunctionDecl *Function = FunTmpl->getTemplatedDecl();
3922 AddTypedNameChunk(Ctx, Policy, Function, Result);
3923
3924 // Figure out which template parameters are deduced (or have default
3925 // arguments).
3926 // Note that we're creating a non-empty bit vector so that we can go
3927 // through the loop below to omit default template parameters for non-call
3928 // cases.
3929 llvm::SmallBitVector Deduced(FunTmpl->getTemplateParameters()->size());
3930 // Avoid running it if this is not a call: We should emit *all* template
3931 // parameters.
3934 unsigned LastDeducibleArgument;
3935 for (LastDeducibleArgument = Deduced.size(); LastDeducibleArgument > 0;
3936 --LastDeducibleArgument) {
3937 if (!Deduced[LastDeducibleArgument - 1]) {
3938 // C++0x: Figure out if the template argument has a default. If so,
3939 // the user doesn't need to type this argument.
3940 // FIXME: We need to abstract template parameters better!
3941 bool HasDefaultArg = false;
3942 NamedDecl *Param = FunTmpl->getTemplateParameters()->getParam(
3943 LastDeducibleArgument - 1);
3944 if (TemplateTypeParmDecl *TTP = dyn_cast<TemplateTypeParmDecl>(Param))
3945 HasDefaultArg = TTP->hasDefaultArgument();
3946 else if (NonTypeTemplateParmDecl *NTTP =
3947 dyn_cast<NonTypeTemplateParmDecl>(Param))
3948 HasDefaultArg = NTTP->hasDefaultArgument();
3949 else {
3950 assert(isa<TemplateTemplateParmDecl>(Param));
3951 HasDefaultArg =
3952 cast<TemplateTemplateParmDecl>(Param)->hasDefaultArgument();
3953 }
3954
3955 if (!HasDefaultArg)
3956 break;
3957 }
3958 }
3959
3960 if (LastDeducibleArgument || !FunctionCanBeCall) {
3961 // Some of the function template arguments cannot be deduced from a
3962 // function call, so we introduce an explicit template argument list
3963 // containing all of the arguments up to the first deducible argument.
3964 //
3965 // Or, if this isn't a call, emit all the template arguments
3966 // to disambiguate the (potential) overloads.
3967 //
3968 // FIXME: Detect cases where the function parameters can be deduced from
3969 // the surrounding context, as per [temp.deduct.funcaddr].
3970 // e.g.,
3971 // template <class T> void foo(T);
3972 // void (*f)(int) = foo;
3973 if (!DeclaringEntity)
3975 else
3976 Result.AddInformativeChunk("<");
3978 Ctx, Policy, FunTmpl, Result, LastDeducibleArgument, /*Start=*/0,
3979 /*InDefaultArg=*/false, /*AsInformativeChunk=*/DeclaringEntity);
3980 // Only adds template arguments as informative chunks in declaration
3981 // context.
3982 if (!DeclaringEntity)
3984 else
3985 Result.AddInformativeChunk(">");
3986 }
3987
3988 // Add the function parameters
3989 bool InsertParameters = FunctionCanBeCall || DeclaringEntity;
3990 if (InsertParameters)
3992 else
3993 Result.AddInformativeChunk("(");
3994 AddFunctionParameterChunks(PP, Policy, Function, Result, /*Start=*/0,
3995 /*InOptional=*/false,
3996 /*FunctionCanBeCall=*/FunctionCanBeCall,
3997 /*IsInDeclarationContext=*/DeclaringEntity);
3998 if (InsertParameters)
4000 else
4001 Result.AddInformativeChunk(")");
4003 return Result.TakeString();
4004 }
4005
4006 if (const auto *Template = dyn_cast<TemplateDecl>(ND)) {
4008 Ctx, Policy);
4009 Result.AddTypedTextChunk(
4010 Result.getAllocator().CopyString(Template->getNameAsString()));
4014 return Result.TakeString();
4015 }
4016
4017 if (const auto *Method = dyn_cast<ObjCMethodDecl>(ND)) {
4018 Selector Sel = Method->getSelector();
4019 if (Sel.isUnarySelector()) {
4020 Result.AddTypedTextChunk(
4021 Result.getAllocator().CopyString(Sel.getNameForSlot(0)));
4022 return Result.TakeString();
4023 }
4024
4025 std::string SelName = Sel.getNameForSlot(0).str();
4026 SelName += ':';
4027 if (StartParameter == 0)
4028 Result.AddTypedTextChunk(Result.getAllocator().CopyString(SelName));
4029 else {
4030 Result.AddInformativeChunk(Result.getAllocator().CopyString(SelName));
4031
4032 // If there is only one parameter, and we're past it, add an empty
4033 // typed-text chunk since there is nothing to type.
4034 if (Method->param_size() == 1)
4035 Result.AddTypedTextChunk("");
4036 }
4037 unsigned Idx = 0;
4038 // The extra Idx < Sel.getNumArgs() check is needed due to legacy C-style
4039 // method parameters.
4040 for (ObjCMethodDecl::param_const_iterator P = Method->param_begin(),
4041 PEnd = Method->param_end();
4042 P != PEnd && Idx < Sel.getNumArgs(); (void)++P, ++Idx) {
4043 if (Idx > 0) {
4044 std::string Keyword;
4045 if (Idx > StartParameter)
4047 if (const IdentifierInfo *II = Sel.getIdentifierInfoForSlot(Idx))
4048 Keyword += II->getName();
4049 Keyword += ":";
4051 Result.AddInformativeChunk(Result.getAllocator().CopyString(Keyword));
4052 else
4053 Result.AddTypedTextChunk(Result.getAllocator().CopyString(Keyword));
4054 }
4055
4056 // If we're before the starting parameter, skip the placeholder.
4057 if (Idx < StartParameter)
4058 continue;
4059
4060 std::string Arg;
4061 QualType ParamType = (*P)->getType();
4062 std::optional<ArrayRef<QualType>> ObjCSubsts;
4063 if (!CCContext.getBaseType().isNull())
4064 ObjCSubsts = CCContext.getBaseType()->getObjCSubstitutions(Method);
4065
4066 if (ParamType->isBlockPointerType() && !DeclaringEntity)
4067 Arg = FormatFunctionParameter(Policy, *P, true,
4068 /*SuppressBlock=*/false, ObjCSubsts);
4069 else {
4070 if (ObjCSubsts)
4071 ParamType = ParamType.substObjCTypeArgs(
4072 Ctx, *ObjCSubsts, ObjCSubstitutionContext::Parameter);
4073 Arg = "(" + formatObjCParamQualifiers((*P)->getObjCDeclQualifier(),
4074 ParamType);
4075 Arg += ParamType.getAsString(Policy) + ")";
4076 if (const IdentifierInfo *II = (*P)->getIdentifier())
4078 Arg += II->getName();
4079 }
4080
4081 if (Method->isVariadic() && (P + 1) == PEnd)
4082 Arg += ", ...";
4083
4084 if (DeclaringEntity)
4085 Result.AddTextChunk(Result.getAllocator().CopyString(Arg));
4087 Result.AddInformativeChunk(Result.getAllocator().CopyString(Arg));
4088 else
4089 Result.AddPlaceholderChunk(Result.getAllocator().CopyString(Arg));
4090 }
4091
4092 if (Method->isVariadic()) {
4093 if (Method->param_size() == 0) {
4094 if (DeclaringEntity)
4095 Result.AddTextChunk(", ...");
4097 Result.AddInformativeChunk(", ...");
4098 else
4099 Result.AddPlaceholderChunk(", ...");
4100 }
4101
4103 }
4104
4105 return Result.TakeString();
4106 }
4107
4108 if (Qualifier)
4110 Ctx, Policy);
4111
4112 Result.AddTypedTextChunk(
4113 Result.getAllocator().CopyString(ND->getNameAsString()));
4114 return Result.TakeString();
4115}
4116
4118 const NamedDecl *ND) {
4119 if (!ND)
4120 return nullptr;
4121 if (auto *RC = Ctx.getRawCommentForAnyRedecl(ND))
4122 return RC;
4123
4124 // Try to find comment from a property for ObjC methods.
4125 const auto *M = dyn_cast<ObjCMethodDecl>(ND);
4126 if (!M)
4127 return nullptr;
4128 const ObjCPropertyDecl *PDecl = M->findPropertyDecl();
4129 if (!PDecl)
4130 return nullptr;
4131
4132 return Ctx.getRawCommentForAnyRedecl(PDecl);
4133}
4134
4136 const NamedDecl *ND) {
4137 const auto *M = dyn_cast_or_null<ObjCMethodDecl>(ND);
4138 if (!M || !M->isPropertyAccessor())
4139 return nullptr;
4140
4141 // Provide code completion comment for self.GetterName where
4142 // GetterName is the getter method for a property with name
4143 // different from the property name (declared via a property
4144 // getter attribute.
4145 const ObjCPropertyDecl *PDecl = M->findPropertyDecl();
4146 if (!PDecl)
4147 return nullptr;
4148 if (PDecl->getGetterName() == M->getSelector() &&
4149 PDecl->getIdentifier() != M->getIdentifier()) {
4150 if (auto *RC = Ctx.getRawCommentForAnyRedecl(M))
4151 return RC;
4152 if (auto *RC = Ctx.getRawCommentForAnyRedecl(PDecl))
4153 return RC;
4154 }
4155 return nullptr;
4156}
4157
4159 const ASTContext &Ctx,
4160 const CodeCompleteConsumer::OverloadCandidate &Result, unsigned ArgIndex) {
4161 auto FDecl = Result.getFunction();
4162 if (!FDecl)
4163 return nullptr;
4164 if (ArgIndex < FDecl->getNumParams())
4165 return Ctx.getRawCommentForAnyRedecl(FDecl->getParamDecl(ArgIndex));
4166 return nullptr;
4167}
4168
4170 const PrintingPolicy &Policy,
4172 unsigned CurrentArg) {
4173 unsigned ChunkIndex = 0;
4174 auto AddChunk = [&](llvm::StringRef Placeholder) {
4175 if (ChunkIndex > 0)
4177 const char *Copy = Result.getAllocator().CopyString(Placeholder);
4178 if (ChunkIndex == CurrentArg)
4179 Result.AddCurrentParameterChunk(Copy);
4180 else
4181 Result.AddPlaceholderChunk(Copy);
4182 ++ChunkIndex;
4183 };
4184 // Aggregate initialization has all bases followed by all fields.
4185 // (Bases are not legal in C++11 but in that case we never get here).
4186 if (auto *CRD = llvm::dyn_cast<CXXRecordDecl>(RD)) {
4187 for (const auto &Base : CRD->bases())
4188 AddChunk(Base.getType().getAsString(Policy));
4189 }
4190 for (const auto &Field : RD->fields())
4191 AddChunk(FormatFunctionParameter(Policy, Field));
4192}
4193
4194/// Add function overload parameter chunks to the given code completion
4195/// string.
4197 ASTContext &Context, const PrintingPolicy &Policy,
4198 const FunctionDecl *Function, const FunctionProtoType *Prototype,
4200 unsigned CurrentArg, unsigned Start = 0, bool InOptional = false) {
4201 if (!Function && !Prototype) {
4203 return;
4204 }
4205
4206 bool FirstParameter = true;
4207 unsigned NumParams =
4208 Function ? Function->getNumParams() : Prototype->getNumParams();
4209 const FunctionDecl *BetterSignatureDecl =
4210 Function ? BetterSignature(Function, Start) : nullptr;
4211
4212 for (unsigned P = Start; P != NumParams; ++P) {
4213 if (Function && Function->getParamDecl(P)->hasDefaultArg() && !InOptional) {
4214 // When we see an optional default argument, put that argument and
4215 // the remaining default arguments into a new, optional string.
4216 CodeCompletionBuilder Opt(Result.getAllocator(),
4217 Result.getCodeCompletionTUInfo());
4218 if (!FirstParameter)
4220 // Optional sections are nested.
4221 AddOverloadParameterChunks(Context, Policy, Function, Prototype,
4222 PrototypeLoc, Opt, CurrentArg, P,
4223 /*InOptional=*/true);
4224 Result.AddOptionalChunk(Opt.TakeString());
4225 return;
4226 }
4227
4228 // C++23 introduces an explicit object parameter, a.k.a. "deducing this"
4229 // Skip it for autocomplete and treat the next parameter as the first
4230 // parameter
4231 if (Function && FirstParameter &&
4232 Function->getParamDecl(P)->isExplicitObjectParameter()) {
4233 continue;
4234 }
4235
4236 if (FirstParameter)
4237 FirstParameter = false;
4238 else
4240
4241 InOptional = false;
4242
4243 // Format the placeholder string.
4244 std::string Placeholder;
4245 assert(P < Prototype->getNumParams());
4246 if (Function || PrototypeLoc) {
4247 const ParmVarDecl *Param = Function ? BetterSignatureDecl->getParamDecl(P)
4248 : PrototypeLoc.getParam(P);
4249 Placeholder = FormatFunctionParameter(Policy, Param);
4250 if (Param->hasDefaultArg())
4251 Placeholder += GetDefaultValueString(Param, Context.getSourceManager(),
4252 Context.getLangOpts());
4253 } else {
4254 Placeholder = Prototype->getParamType(P).getAsString(Policy);
4255 }
4256
4257 if (P == CurrentArg)
4258 Result.AddCurrentParameterChunk(
4259 Result.getAllocator().CopyString(Placeholder));
4260 else
4261 Result.AddPlaceholderChunk(Result.getAllocator().CopyString(Placeholder));
4262 }
4263
4264 if (Prototype && Prototype->isVariadic()) {
4265 CodeCompletionBuilder Opt(Result.getAllocator(),
4266 Result.getCodeCompletionTUInfo());
4267 if (!FirstParameter)
4269
4270 if (CurrentArg < NumParams)
4271 Opt.AddPlaceholderChunk("...");
4272 else
4273 Opt.AddCurrentParameterChunk("...");
4274
4275 Result.AddOptionalChunk(Opt.TakeString());
4276 }
4277}
4278
4279static std::string
4281 const PrintingPolicy &Policy) {
4282 if (const auto *Type = dyn_cast<TemplateTypeParmDecl>(Param)) {
4283 Optional = Type->hasDefaultArgument();
4284 } else if (const auto *NonType = dyn_cast<NonTypeTemplateParmDecl>(Param)) {
4285 Optional = NonType->hasDefaultArgument();
4286 } else if (const auto *Template = dyn_cast<TemplateTemplateParmDecl>(Param)) {
4287 Optional = Template->hasDefaultArgument();
4288 }
4289 std::string Result;
4290 llvm::raw_string_ostream OS(Result);
4291 Param->print(OS, Policy);
4292 return Result;
4293}
4294
4295static std::string templateResultType(const TemplateDecl *TD,
4296 const PrintingPolicy &Policy) {
4297 if (const auto *CTD = dyn_cast<ClassTemplateDecl>(TD))
4298 return CTD->getTemplatedDecl()->getKindName().str();
4299 if (const auto *VTD = dyn_cast<VarTemplateDecl>(TD))
4300 return VTD->getTemplatedDecl()->getType().getAsString(Policy);
4301 if (const auto *FTD = dyn_cast<FunctionTemplateDecl>(TD))
4302 return FTD->getTemplatedDecl()->getReturnType().getAsString(Policy);
4304 return "type";
4306 return "class";
4307 if (isa<ConceptDecl>(TD))
4308 return "concept";
4309 return "";
4310}
4311
4313 const TemplateDecl *TD, CodeCompletionBuilder &Builder, unsigned CurrentArg,
4314 const PrintingPolicy &Policy) {
4316 CodeCompletionBuilder OptionalBuilder(Builder.getAllocator(),
4317 Builder.getCodeCompletionTUInfo());
4318 std::string ResultType = templateResultType(TD, Policy);
4319 if (!ResultType.empty())
4320 Builder.AddResultTypeChunk(Builder.getAllocator().CopyString(ResultType));
4321 Builder.AddTextChunk(
4322 Builder.getAllocator().CopyString(TD->getNameAsString()));
4323 Builder.AddChunk(CodeCompletionString::CK_LeftAngle);
4324 // Initially we're writing into the main string. Once we see an optional arg
4325 // (with default), we're writing into the nested optional chunk.
4326 CodeCompletionBuilder *Current = &Builder;
4327 for (unsigned I = 0; I < Params.size(); ++I) {
4328 bool Optional = false;
4329 std::string Placeholder =
4330 formatTemplateParameterPlaceholder(Params[I], Optional, Policy);
4331 if (Optional)
4332 Current = &OptionalBuilder;
4333 if (I > 0)
4335 Current->AddChunk(I == CurrentArg
4338 Current->getAllocator().CopyString(Placeholder));
4339 }
4340 // Add the optional chunk to the main string if we ever used it.
4341 if (Current == &OptionalBuilder)
4342 Builder.AddOptionalChunk(OptionalBuilder.TakeString());
4343 Builder.AddChunk(CodeCompletionString::CK_RightAngle);
4344 // For function templates, ResultType was the function's return type.
4345 // Give some clue this is a function. (Don't show the possibly-bulky params).
4347 Builder.AddInformativeChunk("()");
4348 return Builder.TakeString();
4349}
4350
4353 unsigned CurrentArg, Sema &S, CodeCompletionAllocator &Allocator,
4354 CodeCompletionTUInfo &CCTUInfo, bool IncludeBriefComments,
4355 bool Braced) const {
4357 // Show signatures of constructors as they are declared:
4358 // vector(int n) rather than vector<string>(int n)
4359 // This is less noisy without being less clear, and avoids tricky cases.
4361
4362 // FIXME: Set priority, availability appropriately.
4363 CodeCompletionBuilder Result(Allocator, CCTUInfo, 1,
4365
4366 if (getKind() == CK_Template)
4367 return createTemplateSignatureString(getTemplate(), Result, CurrentArg,
4368 Policy);
4369
4370 FunctionDecl *FDecl = getFunction();
4371 const FunctionProtoType *Proto =
4372 dyn_cast_or_null<FunctionProtoType>(getFunctionType());
4373
4374 // First, the name/type of the callee.
4375 if (getKind() == CK_Aggregate) {
4376 Result.AddTextChunk(
4377 Result.getAllocator().CopyString(getAggregate()->getName()));
4378 } else if (FDecl) {
4379 if (IncludeBriefComments) {
4380 if (auto RC = getParameterComment(S.getASTContext(), *this, CurrentArg))
4381 Result.addBriefComment(RC->getBriefText(S.getASTContext()));
4382 }
4383 AddResultTypeChunk(S.Context, Policy, FDecl, QualType(), Result);
4384
4385 std::string Name;
4386 llvm::raw_string_ostream OS(Name);
4387 FDecl->getDeclName().print(OS, Policy);
4388 Result.AddTextChunk(Result.getAllocator().CopyString(Name));
4389 } else {
4390 // Function without a declaration. Just give the return type.
4391 Result.AddResultTypeChunk(Result.getAllocator().CopyString(
4392 getFunctionType()->getReturnType().getAsString(Policy)));
4393 }
4394
4395 // Next, the brackets and parameters.
4398 if (getKind() == CK_Aggregate)
4399 AddOverloadAggregateChunks(getAggregate(), Policy, Result, CurrentArg);
4400 else
4401 AddOverloadParameterChunks(S.getASTContext(), Policy, FDecl, Proto,
4402 getFunctionProtoTypeLoc(), Result, CurrentArg);
4405
4406 return Result.TakeString();
4407}
4408
4409unsigned clang::getMacroUsagePriority(StringRef MacroName,
4410 const LangOptions &LangOpts,
4411 bool PreferredTypeIsPointer) {
4412 unsigned Priority = CCP_Macro;
4413
4414 // Treat the "nil", "Nil" and "NULL" macros as null pointer constants.
4415 if (MacroName == "nil" || MacroName == "NULL" || MacroName == "Nil") {
4416 Priority = CCP_Constant;
4417 if (PreferredTypeIsPointer)
4418 Priority = Priority / CCF_SimilarTypeMatch;
4419 }
4420 // Treat "YES", "NO", "true", and "false" as constants.
4421 else if (MacroName == "YES" || MacroName == "NO" || MacroName == "true" ||
4422 MacroName == "false")
4423 Priority = CCP_Constant;
4424 // Treat "bool" as a type.
4425 else if (MacroName == "bool")
4426 Priority = CCP_Type + (LangOpts.ObjC ? CCD_bool_in_ObjC : 0);
4427
4428 return Priority;
4429}
4430
4431CXCursorKind clang::getCursorKindForDecl(const Decl *D) {
4432 if (!D)
4434
4435 switch (D->getKind()) {
4436 case Decl::Enum:
4437 return CXCursor_EnumDecl;
4438 case Decl::EnumConstant:
4440 case Decl::Field:
4441 return CXCursor_FieldDecl;
4442 case Decl::Function:
4443 return CXCursor_FunctionDecl;
4444 case Decl::ObjCCategory:
4446 case Decl::ObjCCategoryImpl:
4448 case Decl::ObjCImplementation:
4450
4451 case Decl::ObjCInterface:
4453 case Decl::ObjCIvar:
4454 return CXCursor_ObjCIvarDecl;
4455 case Decl::ObjCMethod:
4456 return cast<ObjCMethodDecl>(D)->isInstanceMethod()
4459 case Decl::CXXMethod:
4460 return CXCursor_CXXMethod;
4461 case Decl::CXXConstructor:
4462 return CXCursor_Constructor;
4463 case Decl::CXXDestructor:
4464 return CXCursor_Destructor;
4465 case Decl::CXXConversion:
4467 case Decl::ObjCProperty:
4469 case Decl::ObjCProtocol:
4471 case Decl::ParmVar:
4472 return CXCursor_ParmDecl;
4473 case Decl::Typedef:
4474 return CXCursor_TypedefDecl;
4475 case Decl::TypeAlias:
4477 case Decl::TypeAliasTemplate:
4479 case Decl::Var:
4480 return CXCursor_VarDecl;
4481 case Decl::Namespace:
4482 return CXCursor_Namespace;
4483 case Decl::NamespaceAlias:
4485 case Decl::TemplateTypeParm:
4487 case Decl::NonTypeTemplateParm:
4489 case Decl::TemplateTemplateParm:
4491 case Decl::FunctionTemplate:
4493 case Decl::ClassTemplate:
4495 case Decl::AccessSpec:
4497 case Decl::ClassTemplatePartialSpecialization:
4499 case Decl::UsingDirective:
4501 case Decl::StaticAssert:
4502 return CXCursor_StaticAssert;
4503 case Decl::Friend:
4504 case Decl::FriendTemplate:
4505 return CXCursor_FriendDecl;
4506 case Decl::TranslationUnit:
4508
4509 case Decl::Using:
4510 case Decl::UnresolvedUsingValue:
4511 case Decl::UnresolvedUsingTypename:
4513
4514 case Decl::UsingEnum:
4515 return CXCursor_EnumDecl;
4516
4517 case Decl::ObjCPropertyImpl:
4518 switch (cast<ObjCPropertyImplDecl>(D)->getPropertyImplementation()) {
4521
4524 }
4525 llvm_unreachable("Unexpected Kind!");
4526
4527 case Decl::Import:
4529
4530 case Decl::ObjCTypeParam:
4532
4533 case Decl::Concept:
4534 return CXCursor_ConceptDecl;
4535
4536 case Decl::LinkageSpec:
4537 return CXCursor_LinkageSpec;
4538
4539 default:
4540 if (const auto *TD = dyn_cast<TagDecl>(D)) {
4541 switch (TD->getTagKind()) {
4542 case TagTypeKind::Interface: // fall through
4544 return CXCursor_StructDecl;
4545 case TagTypeKind::Class:
4546 return CXCursor_ClassDecl;
4547 case TagTypeKind::Union:
4548 return CXCursor_UnionDecl;
4549 case TagTypeKind::Enum:
4550 return CXCursor_EnumDecl;
4551 }
4552 }
4553 }
4554
4556}
4557
4558static void AddMacroResults(Preprocessor &PP, ResultBuilder &Results,
4559 bool LoadExternal, bool IncludeUndefined,
4560 bool TargetTypeIsPointer = false) {
4562
4563 Results.EnterNewScope();
4564
4565 for (const auto &M : PP.macros(LoadExternal)) {
4566 auto MD = PP.getMacroDefinition(M.first);
4567 if (IncludeUndefined || MD) {
4568 MacroInfo *MI = MD.getMacroInfo();
4569 if (MI && MI->isUsedForHeaderGuard())
4570 continue;
4571
4572 Results.AddResult(
4573 Result(M.first, MI,
4574 getMacroUsagePriority(M.first->getName(), PP.getLangOpts(),
4575 TargetTypeIsPointer)));
4576 }
4577 }
4578
4579 Results.ExitScope();
4580}
4581
4582static void AddPrettyFunctionResults(const LangOptions &LangOpts,
4583 ResultBuilder &Results) {
4585
4586 Results.EnterNewScope();
4587
4588 Results.AddResult(Result("__PRETTY_FUNCTION__", CCP_Constant));
4589 Results.AddResult(Result("__FUNCTION__", CCP_Constant));
4590 if (LangOpts.C99 || LangOpts.CPlusPlus11)
4591 Results.AddResult(Result("__func__", CCP_Constant));
4592 Results.ExitScope();
4593}
4594
4596 CodeCompleteConsumer *CodeCompleter,
4597 const CodeCompletionContext &Context,
4598 CodeCompletionResult *Results,
4599 unsigned NumResults) {
4600 if (CodeCompleter)
4601 CodeCompleter->ProcessCodeCompleteResults(*S, Context, Results, NumResults);
4602}
4603
4604static CodeCompletionContext
4607 switch (PCC) {
4610
4613
4616
4619
4622
4625 if (S.CurContext->isFileContext())
4627 if (S.CurContext->isRecord())
4630
4633
4635 if (S.getLangOpts().CPlusPlus || S.getLangOpts().C99 ||
4636 S.getLangOpts().ObjC)
4638 else
4640
4645 S.getASTContext().BoolTy);
4646
4649
4652
4655
4660 }
4661
4662 llvm_unreachable("Invalid ParserCompletionContext!");
4663}
4664
4665/// If we're in a C++ virtual member function, add completion results
4666/// that invoke the functions we override, since it's common to invoke the
4667/// overridden function as well as adding new functionality.
4668///
4669/// \param S The semantic analysis object for which we are generating results.
4670///
4671/// \param InContext This context in which the nested-name-specifier preceding
4672/// the code-completion point
4673static void MaybeAddOverrideCalls(Sema &S, DeclContext *InContext,
4674 ResultBuilder &Results) {
4675 // Look through blocks.
4676 DeclContext *CurContext = S.CurContext;
4677 while (isa<BlockDecl>(CurContext))
4678 CurContext = CurContext->getParent();
4679
4680 CXXMethodDecl *Method = dyn_cast<CXXMethodDecl>(CurContext);
4681 if (!Method || !Method->isVirtual())
4682 return;
4683
4684 // We need to have names for all of the parameters, if we're going to
4685 // generate a forwarding call.
4686 for (auto *P : Method->parameters())
4687 if (!P->getDeclName())
4688 return;
4689
4691 for (const CXXMethodDecl *Overridden : Method->overridden_methods()) {
4692 CodeCompletionBuilder Builder(Results.getAllocator(),
4693 Results.getCodeCompletionTUInfo());
4694 if (Overridden->getCanonicalDecl() == Method->getCanonicalDecl())
4695 continue;
4696
4697 // If we need a nested-name-specifier, add one now.
4698 if (!InContext) {
4700 S.Context, CurContext, Overridden->getDeclContext());
4701 if (NNS) {
4702 std::string Str;
4703 llvm::raw_string_ostream OS(Str);
4704 NNS.print(OS, Policy);
4705 Builder.AddTextChunk(Results.getAllocator().CopyString(Str));
4706 }
4707 } else if (!InContext->Equals(Overridden->getDeclContext()))
4708 continue;
4709
4710 Builder.AddTypedTextChunk(
4711 Results.getAllocator().CopyString(Overridden->getNameAsString()));
4712 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
4713 bool FirstParam = true;
4714 for (auto *P : Method->parameters()) {
4715 if (FirstParam)
4716 FirstParam = false;
4717 else
4718 Builder.AddChunk(CodeCompletionString::CK_Comma);
4719
4720 Builder.AddPlaceholderChunk(
4721 Results.getAllocator().CopyString(P->getIdentifier()->getName()));
4722 }
4723 Builder.AddChunk(CodeCompletionString::CK_RightParen);
4724 Results.AddResult(CodeCompletionResult(
4725 Builder.TakeString(), CCP_SuperCompletion, CXCursor_CXXMethod,
4726 CXAvailability_Available, Overridden));
4727 Results.Ignore(Overridden);
4728 }
4729}
4730
4732 ModuleIdPath Path) {
4734 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
4735 CodeCompleter->getCodeCompletionTUInfo(),
4737 Results.EnterNewScope();
4738
4739 CodeCompletionAllocator &Allocator = Results.getAllocator();
4740 CodeCompletionBuilder Builder(Allocator, Results.getCodeCompletionTUInfo());
4742 if (Path.empty()) {
4743 // Enumerate all top-level modules.
4745 SemaRef.PP.getHeaderSearchInfo().collectAllModules(Modules);
4746 // Determine the primary module interface name of the current file's
4747 // declared module, if any. Prefer Sema's view, but fall back to the
4748 // preprocessor's module declaration state: module declarations are
4749 // processed as preprocessor directives, so the preprocessor may know the
4750 // declared module before Sema has acted on it (e.g. when completing an
4751 // import right after the module declaration).
4752 StringRef CurrentPrimary;
4753 if (Module *CurrentModule = SemaRef.getCurrentModule())
4754 CurrentPrimary = CurrentModule->getPrimaryModuleInterfaceName();
4755 else if (SemaRef.PP.isInNamedModule())
4756 CurrentPrimary = SemaRef.PP.getNamedModuleName().split(':').first;
4757 llvm::StringSet<> AddedModules;
4758 for (unsigned I = 0, N = Modules.size(); I != N; ++I) {
4759 // Skip module partitions that don't belong to the current file's declared
4760 // module.
4761 if (Modules[I]->isModulePartition()) {
4762 if (CurrentPrimary.empty() ||
4763 Modules[I]->getPrimaryModuleInterfaceName() != CurrentPrimary)
4764 continue;
4765 }
4766 Builder.AddTypedTextChunk(
4767 Builder.getAllocator().CopyString(Modules[I]->Name));
4768 Results.AddResult(Result(
4769 Builder.TakeString(), CCP_Declaration, CXCursor_ModuleImportDecl,
4770 Modules[I]->isAvailable() ? CXAvailability_Available
4772 AddedModules.insert(Modules[I]->Name);
4773 }
4774
4775 // Also suggest C++20 named modules from -fmodule-file=<name>=<path> that
4776 // haven't been loaded into the module map yet.
4777 for (const auto &Entry : SemaRef.PP.getHeaderSearchInfo()
4778 .getHeaderSearchOpts()
4779 .PrebuiltModuleFiles) {
4780 if (AddedModules.count(Entry.first))
4781 continue;
4782 StringRef Name = Entry.first;
4783 // Apply the same partition filtering as above.
4784 if (auto [Primary, Partition] = Name.split(':'); !Partition.empty()) {
4785 if (CurrentPrimary.empty() || Primary != CurrentPrimary)
4786 continue;
4787 }
4788 Builder.AddTypedTextChunk(Builder.getAllocator().CopyString(Name));
4789 Results.AddResult(Result(Builder.TakeString(), CCP_Declaration,
4792 }
4793 } else if (getLangOpts().Modules) {
4794 // Load the named module.
4795 Module *Mod = SemaRef.PP.getModuleLoader().loadModule(
4796 ImportLoc, Path, Module::AllVisible,
4797 /*IsInclusionDirective=*/false);
4798 // Enumerate submodules.
4799 if (Mod) {
4800 for (Module *Submodule : Mod->submodules()) {
4801 Builder.AddTypedTextChunk(
4802 Builder.getAllocator().CopyString(Submodule->Name));
4803 Results.AddResult(Result(
4804 Builder.TakeString(), CCP_Declaration, CXCursor_ModuleImportDecl,
4805 Submodule->isAvailable() ? CXAvailability_Available
4807 }
4808 }
4809 }
4810 Results.ExitScope();
4812 Results.getCompletionContext(), Results.data(),
4813 Results.size());
4814}
4815
4817 Scope *S, SemaCodeCompletion::ParserCompletionContext CompletionContext) {
4818 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
4819 CodeCompleter->getCodeCompletionTUInfo(),
4820 mapCodeCompletionContext(SemaRef, CompletionContext));
4821 Results.EnterNewScope();
4822
4823 // Determine how to filter results, e.g., so that the names of
4824 // values (functions, enumerators, function templates, etc.) are
4825 // only allowed where we can have an expression.
4826 switch (CompletionContext) {
4827 case PCC_Namespace:
4828 case PCC_Class:
4829 case PCC_ObjCInterface:
4832 case PCC_Template:
4833 case PCC_MemberTemplate:
4834 case PCC_Type:
4836 Results.setFilter(&ResultBuilder::IsOrdinaryNonValueName);
4837 break;
4838
4839 case PCC_Statement:
4842 case PCC_Expression:
4843 case PCC_ForInit:
4844 case PCC_Condition:
4845 if (WantTypesInContext(CompletionContext, getLangOpts()))
4846 Results.setFilter(&ResultBuilder::IsOrdinaryName);
4847 else
4848 Results.setFilter(&ResultBuilder::IsOrdinaryNonTypeName);
4849
4850 if (getLangOpts().CPlusPlus)
4851 MaybeAddOverrideCalls(SemaRef, /*InContext=*/nullptr, Results);
4852 break;
4853
4855 // Unfiltered
4856 break;
4857 }
4858
4859 auto ThisType = SemaRef.getCurrentThisType();
4860 if (ThisType.isNull()) {
4861 // check if function scope is an explicit object function
4862 if (auto *MethodDecl = llvm::dyn_cast_if_present<CXXMethodDecl>(
4863 SemaRef.getCurFunctionDecl()))
4864 Results.setExplicitObjectMemberFn(
4865 MethodDecl->isExplicitObjectMemberFunction());
4866 } else {
4867 // If we are in a C++ non-static member function, check the qualifiers on
4868 // the member function to filter/prioritize the results list.
4869 Results.setObjectTypeQualifiers(ThisType->getPointeeType().getQualifiers(),
4870 VK_LValue);
4871 }
4872
4873 CodeCompletionDeclConsumer Consumer(Results, SemaRef.CurContext);
4874 SemaRef.LookupVisibleDecls(S, SemaRef.LookupOrdinaryName, Consumer,
4875 CodeCompleter->includeGlobals(),
4876 CodeCompleter->loadExternal());
4877
4878 AddOrdinaryNameResults(CompletionContext, S, SemaRef, Results);
4879 Results.ExitScope();
4880
4881 switch (CompletionContext) {
4883 case PCC_Expression:
4884 case PCC_Statement:
4887 if (S->getFnParent())
4889 break;
4890
4891 case PCC_Namespace:
4892 case PCC_Class:
4893 case PCC_ObjCInterface:
4896 case PCC_Template:
4897 case PCC_MemberTemplate:
4898 case PCC_ForInit:
4899 case PCC_Condition:
4900 case PCC_Type:
4902 break;
4903 }
4904
4905 if (CodeCompleter->includeMacros())
4906 AddMacroResults(SemaRef.PP, Results, CodeCompleter->loadExternal(), false);
4907
4909 Results.getCompletionContext(), Results.data(),
4910 Results.size());
4911}
4912
4913static void
4914AddClassMessageCompletions(Sema &SemaRef, Scope *S, ParsedType Receiver,
4916 bool AtArgumentExpression, bool IsSuper,
4917 ResultBuilder &Results);
4918
4920 bool AllowNonIdentifiers,
4921 bool AllowNestedNameSpecifiers) {
4923 ResultBuilder Results(
4924 SemaRef, CodeCompleter->getAllocator(),
4925 CodeCompleter->getCodeCompletionTUInfo(),
4926 AllowNestedNameSpecifiers
4927 // FIXME: Try to separate codepath leading here to deduce whether we
4928 // need an existing symbol or a new one.
4931 Results.EnterNewScope();
4932
4933 // Type qualifiers can come after names.
4934 Results.AddResult(Result("const"));
4935 Results.AddResult(Result("volatile"));
4936 if (getLangOpts().C99)
4937 Results.AddResult(Result("restrict"));
4938
4939 if (getLangOpts().CPlusPlus) {
4940 if (getLangOpts().CPlusPlus11 &&
4943 Results.AddResult("final");
4944
4945 if (AllowNonIdentifiers) {
4946 Results.AddResult(Result("operator"));
4947 }
4948
4949 // Add nested-name-specifiers.
4950 if (AllowNestedNameSpecifiers) {
4951 Results.allowNestedNameSpecifiers();
4952 Results.setFilter(&ResultBuilder::IsImpossibleToSatisfy);
4953 CodeCompletionDeclConsumer Consumer(Results, SemaRef.CurContext);
4954 SemaRef.LookupVisibleDecls(S, Sema::LookupNestedNameSpecifierName,
4955 Consumer, CodeCompleter->includeGlobals(),
4956 CodeCompleter->loadExternal());
4957 Results.setFilter(nullptr);
4958 }
4959 }
4960 Results.ExitScope();
4961
4962 // If we're in a context where we might have an expression (rather than a
4963 // declaration), and what we've seen so far is an Objective-C type that could
4964 // be a receiver of a class message, this may be a class message send with
4965 // the initial opening bracket '[' missing. Add appropriate completions.
4966 if (AllowNonIdentifiers && !AllowNestedNameSpecifiers &&
4971 !DS.isTypeAltiVecVector() && S &&
4972 (S->getFlags() & Scope::DeclScope) != 0 &&
4975 0) {
4976 ParsedType T = DS.getRepAsType();
4977 if (!T.get().isNull() && T.get()->isObjCObjectOrInterfaceType())
4978 AddClassMessageCompletions(SemaRef, S, T, {}, false, false, Results);
4979 }
4980
4981 // Note that we intentionally suppress macro results here, since we do not
4982 // encourage using macros to produce the names of entities.
4983
4985 Results.getCompletionContext(), Results.data(),
4986 Results.size());
4987}
4988
4989static const char *underscoreAttrScope(llvm::StringRef Scope) {
4990 if (Scope == "clang")
4991 return "_Clang";
4992 if (Scope == "gnu")
4993 return "__gnu__";
4994 return nullptr;
4995}
4996
4997static const char *noUnderscoreAttrScope(llvm::StringRef Scope) {
4998 if (Scope == "_Clang")
4999 return "clang";
5000 if (Scope == "__gnu__")
5001 return "gnu";
5002 return nullptr;
5003}
5004
5007 const IdentifierInfo *InScope) {
5008 if (Completion == AttributeCompletion::None)
5009 return;
5010 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
5011 CodeCompleter->getCodeCompletionTUInfo(),
5013
5014 // We're going to iterate over the normalized spellings of the attribute.
5015 // These don't include "underscore guarding": the normalized spelling is
5016 // clang::foo but you can also write _Clang::__foo__.
5017 //
5018 // (Clang supports a mix like clang::__foo__ but we won't suggest it: either
5019 // you care about clashing with macros or you don't).
5020 //
5021 // So if we're already in a scope, we determine its canonical spellings
5022 // (for comparison with normalized attr spelling) and remember whether it was
5023 // underscore-guarded (so we know how to spell contained attributes).
5024 llvm::StringRef InScopeName;
5025 bool InScopeUnderscore = false;
5026 if (InScope) {
5027 InScopeName = InScope->getName();
5028 if (const char *NoUnderscore = noUnderscoreAttrScope(InScopeName)) {
5029 InScopeName = NoUnderscore;
5030 InScopeUnderscore = true;
5031 }
5032 }
5033 bool SyntaxSupportsGuards = Syntax == AttributeCommonInfo::AS_GNU ||
5036
5037 llvm::DenseSet<llvm::StringRef> FoundScopes;
5038 auto AddCompletions = [&](const ParsedAttrInfo &A) {
5039 if (A.IsTargetSpecific &&
5040 !A.existsInTarget(getASTContext().getTargetInfo()))
5041 return;
5042 if (!A.acceptsLangOpts(getLangOpts()))
5043 return;
5044 for (const auto &S : A.Spellings) {
5045 if (S.Syntax != Syntax)
5046 continue;
5047 llvm::StringRef Name = S.NormalizedFullName;
5048 llvm::StringRef Scope;
5049 if ((Syntax == AttributeCommonInfo::AS_CXX11 ||
5050 Syntax == AttributeCommonInfo::AS_C23)) {
5051 std::tie(Scope, Name) = Name.split("::");
5052 if (Name.empty()) // oops, unscoped
5053 std::swap(Name, Scope);
5054 }
5055
5056 // Do we just want a list of scopes rather than attributes?
5057 if (Completion == AttributeCompletion::Scope) {
5058 // Make sure to emit each scope only once.
5059 if (!Scope.empty() && FoundScopes.insert(Scope).second) {
5060 Results.AddResult(
5061 CodeCompletionResult(Results.getAllocator().CopyString(Scope)));
5062 // Include alternate form (__gnu__ instead of gnu).
5063 if (const char *Scope2 = underscoreAttrScope(Scope))
5064 Results.AddResult(CodeCompletionResult(Scope2));
5065 }
5066 continue;
5067 }
5068
5069 // If a scope was specified, it must match but we don't need to print it.
5070 if (!InScopeName.empty()) {
5071 if (Scope != InScopeName)
5072 continue;
5073 Scope = "";
5074 }
5075
5076 auto Add = [&](llvm::StringRef Scope, llvm::StringRef Name,
5077 bool Underscores) {
5078 CodeCompletionBuilder Builder(Results.getAllocator(),
5079 Results.getCodeCompletionTUInfo());
5081 if (!Scope.empty()) {
5082 Text.append(Scope);
5083 Text.append("::");
5084 }
5085 if (Underscores)
5086 Text.append("__");
5087 Text.append(Name);
5088 if (Underscores)
5089 Text.append("__");
5090 Builder.AddTypedTextChunk(Results.getAllocator().CopyString(Text));
5091
5092 if (!A.ArgNames.empty()) {
5093 Builder.AddChunk(CodeCompletionString::CK_LeftParen, "(");
5094 bool First = true;
5095 for (const char *Arg : A.ArgNames) {
5096 if (!First)
5097 Builder.AddChunk(CodeCompletionString::CK_Comma, ", ");
5098 First = false;
5099 Builder.AddPlaceholderChunk(Arg);
5100 }
5101 Builder.AddChunk(CodeCompletionString::CK_RightParen, ")");
5102 }
5103
5104 Results.AddResult(Builder.TakeString());
5105 };
5106
5107 // Generate the non-underscore-guarded result.
5108 // Note this is (a suffix of) the NormalizedFullName, no need to copy.
5109 // If an underscore-guarded scope was specified, only the
5110 // underscore-guarded attribute name is relevant.
5111 if (!InScopeUnderscore)
5112 Add(Scope, Name, /*Underscores=*/false);
5113
5114 // Generate the underscore-guarded version, for syntaxes that support it.
5115 // We skip this if the scope was already spelled and not guarded, or
5116 // we must spell it and can't guard it.
5117 if (!(InScope && !InScopeUnderscore) && SyntaxSupportsGuards) {
5118 if (Scope.empty()) {
5119 Add(Scope, Name, /*Underscores=*/true);
5120 } else {
5121 const char *GuardedScope = underscoreAttrScope(Scope);
5122 if (!GuardedScope)
5123 continue;
5124 Add(GuardedScope, Name, /*Underscores=*/true);
5125 }
5126 }
5127
5128 // It may be nice to include the Kind so we can look up the docs later.
5129 }
5130 };
5131
5132 for (const auto *A : ParsedAttrInfo::getAllBuiltin())
5133 AddCompletions(*A);
5134 for (const auto &Entry : ParsedAttrInfoRegistry::entries())
5135 AddCompletions(*Entry.instantiate());
5136
5138 Results.getCompletionContext(), Results.data(),
5139 Results.size());
5140}
5141
5154
5155namespace {
5156/// Information that allows to avoid completing redundant enumerators.
5157struct CoveredEnumerators {
5159 NestedNameSpecifier SuggestedQualifier = std::nullopt;
5160};
5161} // namespace
5162
5163static void AddEnumerators(ResultBuilder &Results, ASTContext &Context,
5164 EnumDecl *Enum, DeclContext *CurContext,
5165 const CoveredEnumerators &Enumerators) {
5166 NestedNameSpecifier Qualifier = Enumerators.SuggestedQualifier;
5167 if (Context.getLangOpts().CPlusPlus && !Qualifier && Enumerators.Seen.empty()) {
5168 // If there are no prior enumerators in C++, check whether we have to
5169 // qualify the names of the enumerators that we suggest, because they
5170 // may not be visible in this scope.
5171 Qualifier = getRequiredQualification(Context, CurContext, Enum);
5172 }
5173
5174 Results.EnterNewScope();
5175 for (auto *E : Enum->enumerators()) {
5176 if (Enumerators.Seen.count(E))
5177 continue;
5178
5179 CodeCompletionResult R(E, CCP_EnumInCase, Qualifier);
5180 Results.AddResult(R, CurContext, nullptr, false);
5181 }
5182 Results.ExitScope();
5183}
5184
5185/// Try to find a corresponding FunctionProtoType for function-like types (e.g.
5186/// function pointers, std::function, etc).
5188 assert(!T.isNull());
5189 // Try to extract first template argument from std::function<> and similar.
5190 // Note we only handle the sugared types, they closely match what users wrote.
5191 // We explicitly choose to not handle ClassTemplateSpecializationDecl.
5192 if (auto *Specialization = T->getAs<TemplateSpecializationType>()) {
5193 if (Specialization->template_arguments().size() != 1)
5194 return nullptr;
5195 const TemplateArgument &Argument = Specialization->template_arguments()[0];
5196 if (Argument.getKind() != TemplateArgument::Type)
5197 return nullptr;
5198 return Argument.getAsType()->getAs<FunctionProtoType>();
5199 }
5200 // Handle other cases.
5201 if (T->isPointerType())
5202 T = T->getPointeeType();
5203 return T->getAs<FunctionProtoType>();
5204}
5205
5206/// Adds a pattern completion for a lambda expression with the specified
5207/// parameter types and placeholders for parameter names.
5208static void AddLambdaCompletion(ResultBuilder &Results,
5209 llvm::ArrayRef<QualType> Parameters,
5210 const LangOptions &LangOpts) {
5211 if (!Results.includeCodePatterns())
5212 return;
5213 CodeCompletionBuilder Completion(Results.getAllocator(),
5214 Results.getCodeCompletionTUInfo());
5215 // [](<parameters>) {}
5217 Completion.AddPlaceholderChunk("=");
5219 if (!Parameters.empty()) {
5221 bool First = true;
5222 for (auto Parameter : Parameters) {
5223 if (!First)
5225 else
5226 First = false;
5227
5228 constexpr llvm::StringLiteral NamePlaceholder = "!#!NAME_GOES_HERE!#!";
5229 std::string Type = std::string(NamePlaceholder);
5230 Parameter.getAsStringInternal(Type, PrintingPolicy(LangOpts));
5231 llvm::StringRef Prefix, Suffix;
5232 std::tie(Prefix, Suffix) = llvm::StringRef(Type).split(NamePlaceholder);
5233 Prefix = Prefix.rtrim();
5234 Suffix = Suffix.ltrim();
5235
5236 Completion.AddTextChunk(Completion.getAllocator().CopyString(Prefix));
5238 Completion.AddPlaceholderChunk("parameter");
5239 Completion.AddTextChunk(Completion.getAllocator().CopyString(Suffix));
5240 };
5242 }
5246 Completion.AddPlaceholderChunk("body");
5249
5250 Results.AddResult(Completion.TakeString());
5251}
5252
5253/// Perform code-completion in an expression context when we know what
5254/// type we're looking for.
5256 Scope *S, const CodeCompleteExpressionData &Data, bool IsAddressOfOperand) {
5257 ResultBuilder Results(
5258 SemaRef, CodeCompleter->getAllocator(),
5259 CodeCompleter->getCodeCompletionTUInfo(),
5261 Data.IsParenthesized
5264 Data.PreferredType));
5265 auto PCC =
5267 if (Data.ObjCCollection)
5268 Results.setFilter(&ResultBuilder::IsObjCCollection);
5269 else if (Data.IntegralConstantExpression)
5270 Results.setFilter(&ResultBuilder::IsIntegralConstantValue);
5271 else if (WantTypesInContext(PCC, getLangOpts()))
5272 Results.setFilter(&ResultBuilder::IsOrdinaryName);
5273 else
5274 Results.setFilter(&ResultBuilder::IsOrdinaryNonTypeName);
5275
5276 if (!Data.PreferredType.isNull())
5277 Results.setPreferredType(Data.PreferredType.getNonReferenceType());
5278
5279 // Ignore any declarations that we were told that we don't care about.
5280 for (unsigned I = 0, N = Data.IgnoreDecls.size(); I != N; ++I)
5281 Results.Ignore(Data.IgnoreDecls[I]);
5282
5283 CodeCompletionDeclConsumer Consumer(Results, SemaRef.CurContext);
5284 Consumer.setIsAddressOfOperand(IsAddressOfOperand);
5285 SemaRef.LookupVisibleDecls(S, Sema::LookupOrdinaryName, Consumer,
5286 CodeCompleter->includeGlobals(),
5287 CodeCompleter->loadExternal());
5288
5289 Results.EnterNewScope();
5290 AddOrdinaryNameResults(PCC, S, SemaRef, Results);
5291 Results.ExitScope();
5292
5293 bool PreferredTypeIsPointer = false;
5294 if (!Data.PreferredType.isNull()) {
5295 PreferredTypeIsPointer = Data.PreferredType->isAnyPointerType() ||
5296 Data.PreferredType->isMemberPointerType() ||
5297 Data.PreferredType->isBlockPointerType();
5298 if (auto *Enum = Data.PreferredType->getAsEnumDecl()) {
5299 // FIXME: collect covered enumerators in cases like:
5300 // if (x == my_enum::one) { ... } else if (x == ^) {}
5301 AddEnumerators(Results, getASTContext(), Enum, SemaRef.CurContext,
5302 CoveredEnumerators());
5303 }
5304 }
5305
5306 if (S->getFnParent() && !Data.ObjCCollection &&
5307 !Data.IntegralConstantExpression)
5309
5310 if (CodeCompleter->includeMacros())
5311 AddMacroResults(SemaRef.PP, Results, CodeCompleter->loadExternal(), false,
5312 PreferredTypeIsPointer);
5313
5314 // Complete a lambda expression when preferred type is a function.
5315 if (!Data.PreferredType.isNull() && getLangOpts().CPlusPlus11) {
5316 if (const FunctionProtoType *F =
5317 TryDeconstructFunctionLike(Data.PreferredType))
5318 AddLambdaCompletion(Results, F->getParamTypes(), getLangOpts());
5319 }
5320
5322 Results.getCompletionContext(), Results.data(),
5323 Results.size());
5324}
5325
5327 QualType PreferredType,
5328 bool IsParenthesized,
5329 bool IsAddressOfOperand) {
5331 S, CodeCompleteExpressionData(PreferredType, IsParenthesized),
5332 IsAddressOfOperand);
5333}
5334
5336 QualType PreferredType) {
5337 if (E.isInvalid())
5338 CodeCompleteExpression(S, PreferredType);
5339 else if (getLangOpts().ObjC)
5340 CodeCompleteObjCInstanceMessage(S, E.get(), {}, false);
5341}
5342
5343/// The set of properties that have already been added, referenced by
5344/// property name.
5346
5347/// Retrieve the container definition, if any?
5349 if (ObjCInterfaceDecl *Interface = dyn_cast<ObjCInterfaceDecl>(Container)) {
5350 if (Interface->hasDefinition())
5351 return Interface->getDefinition();
5352
5353 return Interface;
5354 }
5355
5356 if (ObjCProtocolDecl *Protocol = dyn_cast<ObjCProtocolDecl>(Container)) {
5357 if (Protocol->hasDefinition())
5358 return Protocol->getDefinition();
5359
5360 return Protocol;
5361 }
5362 return Container;
5363}
5364
5365/// Adds a block invocation code completion result for the given block
5366/// declaration \p BD.
5367static void AddObjCBlockCall(ASTContext &Context, const PrintingPolicy &Policy,
5368 CodeCompletionBuilder &Builder,
5369 const NamedDecl *BD,
5370 const FunctionTypeLoc &BlockLoc,
5371 const FunctionProtoTypeLoc &BlockProtoLoc) {
5372 Builder.AddResultTypeChunk(
5373 GetCompletionTypeString(BlockLoc.getReturnLoc().getType(), Context,
5374 Policy, Builder.getAllocator()));
5375
5376 AddTypedNameChunk(Context, Policy, BD, Builder);
5377 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
5378
5379 if (BlockProtoLoc && BlockProtoLoc.getTypePtr()->isVariadic()) {
5380 Builder.AddPlaceholderChunk("...");
5381 } else {
5382 for (unsigned I = 0, N = BlockLoc.getNumParams(); I != N; ++I) {
5383 if (I)
5384 Builder.AddChunk(CodeCompletionString::CK_Comma);
5385
5386 // Format the placeholder string.
5387 std::string PlaceholderStr =
5388 FormatFunctionParameter(Policy, BlockLoc.getParam(I));
5389
5390 if (I == N - 1 && BlockProtoLoc &&
5391 BlockProtoLoc.getTypePtr()->isVariadic())
5392 PlaceholderStr += ", ...";
5393
5394 // Add the placeholder string.
5395 Builder.AddPlaceholderChunk(
5396 Builder.getAllocator().CopyString(PlaceholderStr));
5397 }
5398 }
5399
5400 Builder.AddChunk(CodeCompletionString::CK_RightParen);
5401}
5402
5403static void
5405 ObjCContainerDecl *Container, bool AllowCategories,
5406 bool AllowNullaryMethods, DeclContext *CurContext,
5407 AddedPropertiesSet &AddedProperties, ResultBuilder &Results,
5408 bool IsBaseExprStatement = false,
5409 bool IsClassProperty = false, bool InOriginalClass = true) {
5411
5412 // Retrieve the definition.
5413 Container = getContainerDef(Container);
5414
5415 // Add properties in this container.
5416 const auto AddProperty = [&](const ObjCPropertyDecl *P) {
5417 if (!AddedProperties.insert(P->getIdentifier()).second)
5418 return;
5419
5420 // FIXME: Provide block invocation completion for non-statement
5421 // expressions.
5422 if (!P->getType().getTypePtr()->isBlockPointerType() ||
5423 !IsBaseExprStatement) {
5424 Result R =
5425 Result(P, Results.getBasePriority(P), /*Qualifier=*/std::nullopt);
5426 if (!InOriginalClass)
5427 setInBaseClass(R);
5428 Results.MaybeAddResult(R, CurContext);
5429 return;
5430 }
5431
5432 // Block setter and invocation completion is provided only when we are able
5433 // to find the FunctionProtoTypeLoc with parameter names for the block.
5434 FunctionTypeLoc BlockLoc;
5435 FunctionProtoTypeLoc BlockProtoLoc;
5436 findTypeLocationForBlockDecl(P->getTypeSourceInfo(), BlockLoc,
5437 BlockProtoLoc);
5438 if (!BlockLoc) {
5439 Result R =
5440 Result(P, Results.getBasePriority(P), /*Qualifier=*/std::nullopt);
5441 if (!InOriginalClass)
5442 setInBaseClass(R);
5443 Results.MaybeAddResult(R, CurContext);
5444 return;
5445 }
5446
5447 // The default completion result for block properties should be the block
5448 // invocation completion when the base expression is a statement.
5449 CodeCompletionBuilder Builder(Results.getAllocator(),
5450 Results.getCodeCompletionTUInfo());
5451 AddObjCBlockCall(Container->getASTContext(),
5452 getCompletionPrintingPolicy(Results.getSema()), Builder, P,
5453 BlockLoc, BlockProtoLoc);
5454 Result R = Result(Builder.TakeString(), P, Results.getBasePriority(P));
5455 if (!InOriginalClass)
5456 setInBaseClass(R);
5457 Results.MaybeAddResult(R, CurContext);
5458
5459 // Provide additional block setter completion iff the base expression is a
5460 // statement and the block property is mutable.
5461 if (!P->isReadOnly()) {
5462 CodeCompletionBuilder Builder(Results.getAllocator(),
5463 Results.getCodeCompletionTUInfo());
5464 AddResultTypeChunk(Container->getASTContext(),
5465 getCompletionPrintingPolicy(Results.getSema()), P,
5466 CCContext.getBaseType(), Builder);
5467 Builder.AddTypedTextChunk(
5468 Results.getAllocator().CopyString(P->getName()));
5469 Builder.AddChunk(CodeCompletionString::CK_Equal);
5470
5471 std::string PlaceholderStr = formatBlockPlaceholder(
5472 getCompletionPrintingPolicy(Results.getSema()), P, BlockLoc,
5473 BlockProtoLoc, /*SuppressBlockName=*/true);
5474 // Add the placeholder string.
5475 Builder.AddPlaceholderChunk(
5476 Builder.getAllocator().CopyString(PlaceholderStr));
5477
5478 // When completing blocks properties that return void the default
5479 // property completion result should show up before the setter,
5480 // otherwise the setter completion should show up before the default
5481 // property completion, as we normally want to use the result of the
5482 // call.
5483 Result R =
5484 Result(Builder.TakeString(), P,
5485 Results.getBasePriority(P) +
5486 (BlockLoc.getTypePtr()->getReturnType()->isVoidType()
5489 if (!InOriginalClass)
5490 setInBaseClass(R);
5491 Results.MaybeAddResult(R, CurContext);
5492 }
5493 };
5494
5495 if (IsClassProperty) {
5496 for (const auto *P : Container->class_properties())
5497 AddProperty(P);
5498 } else {
5499 for (const auto *P : Container->instance_properties())
5500 AddProperty(P);
5501 }
5502
5503 // Add nullary methods or implicit class properties
5504 if (AllowNullaryMethods) {
5505 ASTContext &Context = Container->getASTContext();
5506 PrintingPolicy Policy = getCompletionPrintingPolicy(Results.getSema());
5507 // Adds a method result
5508 const auto AddMethod = [&](const ObjCMethodDecl *M) {
5509 const IdentifierInfo *Name = M->getSelector().getIdentifierInfoForSlot(0);
5510 if (!Name)
5511 return;
5512 if (!AddedProperties.insert(Name).second)
5513 return;
5514 CodeCompletionBuilder Builder(Results.getAllocator(),
5515 Results.getCodeCompletionTUInfo());
5516 AddResultTypeChunk(Context, Policy, M, CCContext.getBaseType(), Builder);
5517 Builder.AddTypedTextChunk(
5518 Results.getAllocator().CopyString(Name->getName()));
5519 Result R = Result(Builder.TakeString(), M,
5521 if (!InOriginalClass)
5522 setInBaseClass(R);
5523 Results.MaybeAddResult(R, CurContext);
5524 };
5525
5526 if (IsClassProperty) {
5527 for (const auto *M : Container->methods()) {
5528 // Gather the class method that can be used as implicit property
5529 // getters. Methods with arguments or methods that return void aren't
5530 // added to the results as they can't be used as a getter.
5531 if (!M->getSelector().isUnarySelector() ||
5532 M->getReturnType()->isVoidType() || M->isInstanceMethod())
5533 continue;
5534 AddMethod(M);
5535 }
5536 } else {
5537 for (auto *M : Container->methods()) {
5538 if (M->getSelector().isUnarySelector())
5539 AddMethod(M);
5540 }
5541 }
5542 }
5543
5544 // Add properties in referenced protocols.
5545 if (ObjCProtocolDecl *Protocol = dyn_cast<ObjCProtocolDecl>(Container)) {
5546 for (auto *P : Protocol->protocols())
5547 AddObjCProperties(CCContext, P, AllowCategories, AllowNullaryMethods,
5548 CurContext, AddedProperties, Results,
5549 IsBaseExprStatement, IsClassProperty,
5550 /*InOriginalClass*/ false);
5551 } else if (ObjCInterfaceDecl *IFace =
5552 dyn_cast<ObjCInterfaceDecl>(Container)) {
5553 if (AllowCategories) {
5554 // Look through categories.
5555 for (auto *Cat : IFace->known_categories())
5556 AddObjCProperties(CCContext, Cat, AllowCategories, AllowNullaryMethods,
5557 CurContext, AddedProperties, Results,
5558 IsBaseExprStatement, IsClassProperty,
5559 InOriginalClass);
5560 }
5561
5562 // Look through protocols.
5563 for (auto *I : IFace->all_referenced_protocols())
5564 AddObjCProperties(CCContext, I, AllowCategories, AllowNullaryMethods,
5565 CurContext, AddedProperties, Results,
5566 IsBaseExprStatement, IsClassProperty,
5567 /*InOriginalClass*/ false);
5568
5569 // Look in the superclass.
5570 if (IFace->getSuperClass())
5571 AddObjCProperties(CCContext, IFace->getSuperClass(), AllowCategories,
5572 AllowNullaryMethods, CurContext, AddedProperties,
5573 Results, IsBaseExprStatement, IsClassProperty,
5574 /*InOriginalClass*/ false);
5575 } else if (const auto *Category =
5576 dyn_cast<ObjCCategoryDecl>(Container)) {
5577 // Look through protocols.
5578 for (auto *P : Category->protocols())
5579 AddObjCProperties(CCContext, P, AllowCategories, AllowNullaryMethods,
5580 CurContext, AddedProperties, Results,
5581 IsBaseExprStatement, IsClassProperty,
5582 /*InOriginalClass*/ false);
5583 }
5584}
5585
5586static void
5587AddRecordMembersCompletionResults(Sema &SemaRef, ResultBuilder &Results,
5588 Scope *S, QualType BaseType,
5589 ExprValueKind BaseKind, RecordDecl *RD,
5590 std::optional<FixItHint> AccessOpFixIt) {
5591 // Indicate that we are performing a member access, and the cv-qualifiers
5592 // for the base object type.
5593 Results.setObjectTypeQualifiers(BaseType.getQualifiers(), BaseKind);
5594
5595 // Access to a C/C++ class, struct, or union.
5596 Results.allowNestedNameSpecifiers();
5597 std::vector<FixItHint> FixIts;
5598 if (AccessOpFixIt)
5599 FixIts.emplace_back(*AccessOpFixIt);
5600 CodeCompletionDeclConsumer Consumer(Results, RD, BaseType, std::move(FixIts));
5601 SemaRef.LookupVisibleDecls(
5602 RD, Sema::LookupMemberName, Consumer,
5604 /*IncludeDependentBases=*/true,
5606
5607 if (SemaRef.getLangOpts().CPlusPlus) {
5608 if (!Results.empty()) {
5609 // The "template" keyword can follow "->" or "." in the grammar.
5610 // However, we only want to suggest the template keyword if something
5611 // is dependent.
5612 bool IsDependent = BaseType->isDependentType();
5613 if (!IsDependent) {
5614 for (Scope *DepScope = S; DepScope; DepScope = DepScope->getParent())
5615 if (DeclContext *Ctx = DepScope->getEntity()) {
5616 IsDependent = Ctx->isDependentContext();
5617 break;
5618 }
5619 }
5620
5621 if (IsDependent)
5622 Results.AddResult(CodeCompletionResult("template"));
5623 }
5624 }
5625}
5626
5627// Returns the RecordDecl inside the BaseType, falling back to primary template
5628// in case of specializations. Since we might not have a decl for the
5629// instantiation/specialization yet, e.g. dependent code.
5631 HeuristicResolver &Resolver) {
5632 BaseType = Resolver.simplifyType(BaseType, nullptr, /*UnwrapPointer=*/false);
5633 return dyn_cast_if_present<RecordDecl>(
5634 Resolver.resolveTypeToTagDecl(BaseType));
5635}
5636
5637namespace {
5638// Collects completion-relevant information about a concept-constrainted type T.
5639// In particular, examines the constraint expressions to find members of T.
5640//
5641// The design is very simple: we walk down each constraint looking for
5642// expressions of the form T.foo().
5643// If we're extra lucky, the return type is specified.
5644// We don't do any clever handling of && or || in constraint expressions, we
5645// take members from both branches.
5646//
5647// For example, given:
5648// template <class T> concept X = requires (T t, string& s) { t.print(s); };
5649// template <X U> void foo(U u) { u.^ }
5650// We want to suggest the inferred member function 'print(string)'.
5651// We see that u has type U, so X<U> holds.
5652// X<U> requires t.print(s) to be valid, where t has type U (substituted for T).
5653// By looking at the CallExpr we find the signature of print().
5654//
5655// While we tend to know in advance which kind of members (access via . -> ::)
5656// we want, it's simpler just to gather them all and post-filter.
5657//
5658// FIXME: some of this machinery could be used for non-concept type-parms too,
5659// enabling completion for type parameters based on other uses of that param.
5660//
5661// FIXME: there are other cases where a type can be constrained by a concept,
5662// e.g. inside `if constexpr(ConceptSpecializationExpr) { ... }`
5663class ConceptInfo {
5664public:
5665 // Describes a likely member of a type, inferred by concept constraints.
5666 // Offered as a code completion for T. T-> and T:: contexts.
5667 struct Member {
5668 // Always non-null: we only handle members with ordinary identifier names.
5669 const IdentifierInfo *Name = nullptr;
5670 // Set for functions we've seen called.
5671 // We don't have the declared parameter types, only the actual types of
5672 // arguments we've seen. These are still valuable, as it's hard to render
5673 // a useful function completion with neither parameter types nor names!
5674 std::optional<SmallVector<QualType, 1>> ArgTypes;
5675 // Whether this is accessed as T.member, T->member, or T::member.
5676 enum AccessOperator {
5677 Colons,
5678 Arrow,
5679 Dot,
5680 } Operator = Dot;
5681 // What's known about the type of a variable or return type of a function.
5682 const TypeConstraint *ResultType = nullptr;
5683 // FIXME: also track:
5684 // - kind of entity (function/variable/type), to expose structured results
5685 // - template args kinds/types, as a proxy for template params
5686
5687 // For now we simply return these results as "pattern" strings.
5688 CodeCompletionString *render(Sema &S, CodeCompletionAllocator &Alloc,
5689 CodeCompletionTUInfo &Info) const {
5690 CodeCompletionBuilder B(Alloc, Info);
5691 // Result type
5692 if (ResultType) {
5693 std::string AsString;
5694 {
5695 llvm::raw_string_ostream OS(AsString);
5696 QualType ExactType = deduceType(*ResultType);
5697 if (!ExactType.isNull())
5698 ExactType.print(OS, getCompletionPrintingPolicy(S));
5699 else
5700 ResultType->print(OS, getCompletionPrintingPolicy(S));
5701 }
5702 B.AddResultTypeChunk(Alloc.CopyString(AsString));
5703 }
5704 // Member name
5705 B.AddTypedTextChunk(Alloc.CopyString(Name->getName()));
5706 // Function argument list
5707 if (ArgTypes) {
5709 bool First = true;
5710 for (QualType Arg : *ArgTypes) {
5711 if (First)
5712 First = false;
5713 else {
5716 }
5717 B.AddPlaceholderChunk(Alloc.CopyString(
5718 Arg.getAsString(getCompletionPrintingPolicy(S))));
5719 }
5721 }
5722 return B.TakeString();
5723 }
5724 };
5725
5726 // BaseType is the type parameter T to infer members from.
5727 // T must be accessible within S, as we use it to find the template entity
5728 // that T is attached to in order to gather the relevant constraints.
5729 ConceptInfo(const TemplateTypeParmType &BaseType, Scope *S) {
5730 auto *TemplatedEntity = getTemplatedEntity(BaseType.getDecl(), S);
5731 for (const AssociatedConstraint &AC :
5732 constraintsForTemplatedEntity(TemplatedEntity))
5733 believe(AC.ConstraintExpr, &BaseType);
5734 }
5735
5736 std::vector<Member> members() {
5737 std::vector<Member> Results;
5738 for (const auto &E : this->Results)
5739 Results.push_back(E.second);
5740 llvm::sort(Results, [](const Member &L, const Member &R) {
5741 return L.Name->getName() < R.Name->getName();
5742 });
5743 return Results;
5744 }
5745
5746private:
5747 // Infer members of T, given that the expression E (dependent on T) is true.
5748 void believe(const Expr *E, const TemplateTypeParmType *T) {
5749 if (!E || !T)
5750 return;
5751 if (auto *CSE = dyn_cast<ConceptSpecializationExpr>(E)) {
5752 // If the concept is
5753 // template <class A, class B> concept CD = f<A, B>();
5754 // And the concept specialization is
5755 // CD<int, T>
5756 // Then we're substituting T for B, so we want to make f<A, B>() true
5757 // by adding members to B - i.e. believe(f<A, B>(), B);
5758 //
5759 // For simplicity:
5760 // - we don't attempt to substitute int for A
5761 // - when T is used in other ways (like CD<T*>) we ignore it
5762 ConceptDecl *CD = CSE->getConceptDecl();
5763 TemplateParameterList *Params = CD->getTemplateParameters();
5764 unsigned Index = 0;
5765 for (const auto &Arg : CSE->getTemplateArguments()) {
5766 if (Index >= Params->size())
5767 break; // Won't happen in valid code.
5768 if (isApprox(Arg, T)) {
5769 auto *TTPD = dyn_cast<TemplateTypeParmDecl>(Params->getParam(Index));
5770 if (!TTPD)
5771 continue;
5772 // T was used as an argument, and bound to the parameter TT.
5773 auto *TT = cast<TemplateTypeParmType>(TTPD->getTypeForDecl());
5774 // So now we know the constraint as a function of TT is true.
5775 believe(CD->getConstraintExpr(), TT);
5776 // (concepts themselves have no associated constraints to require)
5777 }
5778
5779 ++Index;
5780 }
5781 } else if (auto *BO = dyn_cast<BinaryOperator>(E)) {
5782 // For A && B, we can infer members from both branches.
5783 // For A || B, the union is still more useful than the intersection.
5784 if (BO->getOpcode() == BO_LAnd || BO->getOpcode() == BO_LOr) {
5785 believe(BO->getLHS(), T);
5786 believe(BO->getRHS(), T);
5787 }
5788 } else if (auto *RE = dyn_cast<RequiresExpr>(E)) {
5789 // A requires(){...} lets us infer members from each requirement.
5790 for (const concepts::Requirement *Req : RE->getRequirements()) {
5791 if (!Req->isDependent())
5792 continue; // Can't tell us anything about T.
5793 // Now Req cannot a substitution-error: those aren't dependent.
5794
5795 if (auto *TR = dyn_cast<concepts::TypeRequirement>(Req)) {
5796 // Do a full traversal so we get `foo` from `typename T::foo::bar`.
5797 QualType AssertedType = TR->getType()->getType();
5798 ValidVisitor(this, T).TraverseType(AssertedType);
5799 } else if (auto *ER = dyn_cast<concepts::ExprRequirement>(Req)) {
5800 ValidVisitor Visitor(this, T);
5801 // If we have a type constraint on the value of the expression,
5802 // AND the whole outer expression describes a member, then we'll
5803 // be able to use the constraint to provide the return type.
5804 if (ER->getReturnTypeRequirement().isTypeConstraint()) {
5805 Visitor.OuterType =
5806 ER->getReturnTypeRequirement().getTypeConstraint();
5807 Visitor.OuterExpr = ER->getExpr();
5808 }
5809 Visitor.TraverseStmt(ER->getExpr());
5810 } else if (auto *NR = dyn_cast<concepts::NestedRequirement>(Req)) {
5811 believe(NR->getConstraintExpr(), T);
5812 }
5813 }
5814 }
5815 }
5816
5817 // This visitor infers members of T based on traversing expressions/types
5818 // that involve T. It is invoked with code known to be valid for T.
5819 class ValidVisitor : public DynamicRecursiveASTVisitor {
5820 ConceptInfo *Outer;
5821 const TemplateTypeParmType *T;
5822
5823 CallExpr *Caller = nullptr;
5824 Expr *Callee = nullptr;
5825
5826 public:
5827 // If set, OuterExpr is constrained by OuterType.
5828 Expr *OuterExpr = nullptr;
5829 const TypeConstraint *OuterType = nullptr;
5830
5831 ValidVisitor(ConceptInfo *Outer, const TemplateTypeParmType *T)
5832 : Outer(Outer), T(T) {
5833 assert(T);
5834 }
5835
5836 // In T.foo or T->foo, `foo` is a member function/variable.
5837 bool
5838 VisitCXXDependentScopeMemberExpr(CXXDependentScopeMemberExpr *E) override {
5839 const Type *Base = E->getBaseType().getTypePtr();
5840 bool IsArrow = E->isArrow();
5841 if (Base->isPointerType() && IsArrow) {
5842 IsArrow = false;
5843 Base = Base->getPointeeType().getTypePtr();
5844 }
5845 if (isApprox(Base, T))
5846 addValue(E, E->getMember(), IsArrow ? Member::Arrow : Member::Dot);
5847 return true;
5848 }
5849
5850 // In T::foo, `foo` is a static member function/variable.
5851 bool VisitDependentScopeDeclRefExpr(DependentScopeDeclRefExpr *E) override {
5852 NestedNameSpecifier Qualifier = E->getQualifier();
5853 if (Qualifier.getKind() == NestedNameSpecifier::Kind::Type &&
5854 isApprox(Qualifier.getAsType(), T))
5855 addValue(E, E->getDeclName(), Member::Colons);
5856 return true;
5857 }
5858
5859 // In T::typename foo, `foo` is a type.
5860 bool VisitDependentNameType(DependentNameType *DNT) override {
5861 NestedNameSpecifier Q = DNT->getQualifier();
5862 if (Q.getKind() == NestedNameSpecifier::Kind::Type &&
5863 isApprox(Q.getAsType(), T))
5864 addType(DNT->getIdentifier());
5865 return true;
5866 }
5867
5868 // In T::foo::bar, `foo` must be a type.
5869 // VisitNNS() doesn't exist, and TraverseNNS isn't always called :-(
5870 bool TraverseNestedNameSpecifierLoc(NestedNameSpecifierLoc NNSL) override {
5871 if (NNSL) {
5872 NestedNameSpecifier NNS = NNSL.getNestedNameSpecifier();
5873 if (NNS.getKind() == NestedNameSpecifier::Kind::Type) {
5874 const Type *NNST = NNS.getAsType();
5875 if (NestedNameSpecifier Q = NNST->getPrefix();
5876 Q.getKind() == NestedNameSpecifier::Kind::Type &&
5877 isApprox(Q.getAsType(), T))
5878 if (const auto *DNT = dyn_cast_or_null<DependentNameType>(NNST))
5879 addType(DNT->getIdentifier());
5880 }
5881 }
5882 // FIXME: also handle T::foo<X>::bar
5884 }
5885
5886 // FIXME also handle T::foo<X>
5887
5888 // Track the innermost caller/callee relationship so we can tell if a
5889 // nested expr is being called as a function.
5890 bool VisitCallExpr(CallExpr *CE) override {
5891 Caller = CE;
5892 Callee = CE->getCallee();
5893 return true;
5894 }
5895
5896 private:
5897 void addResult(Member &&M) {
5898 auto R = Outer->Results.try_emplace(M.Name);
5899 Member &O = R.first->second;
5900 // Overwrite existing if the new member has more info.
5901 // The preference of . vs :: vs -> is fairly arbitrary.
5902 if (/*Inserted*/ R.second ||
5903 std::make_tuple(M.ArgTypes.has_value(), M.ResultType != nullptr,
5904 M.Operator) > std::make_tuple(O.ArgTypes.has_value(),
5905 O.ResultType != nullptr,
5906 O.Operator))
5907 O = std::move(M);
5908 }
5909
5910 void addType(const IdentifierInfo *Name) {
5911 if (!Name)
5912 return;
5913 Member M;
5914 M.Name = Name;
5915 M.Operator = Member::Colons;
5916 addResult(std::move(M));
5917 }
5918
5919 void addValue(Expr *E, DeclarationName Name,
5920 Member::AccessOperator Operator) {
5921 if (!Name.isIdentifier())
5922 return;
5923 Member Result;
5924 Result.Name = Name.getAsIdentifierInfo();
5925 Result.Operator = Operator;
5926 // If this is the callee of an immediately-enclosing CallExpr, then
5927 // treat it as a method, otherwise it's a variable.
5928 if (Caller != nullptr && Callee == E) {
5929 Result.ArgTypes.emplace();
5930 for (const auto *Arg : Caller->arguments())
5931 Result.ArgTypes->push_back(Arg->getType());
5932 if (Caller == OuterExpr) {
5933 Result.ResultType = OuterType;
5934 }
5935 } else {
5936 if (E == OuterExpr)
5937 Result.ResultType = OuterType;
5938 }
5939 addResult(std::move(Result));
5940 }
5941 };
5942
5943 static bool isApprox(const TemplateArgument &Arg, const Type *T) {
5944 return Arg.getKind() == TemplateArgument::Type &&
5945 isApprox(Arg.getAsType().getTypePtr(), T);
5946 }
5947
5948 static bool isApprox(const Type *T1, const Type *T2) {
5949 return T1 && T2 &&
5952 }
5953
5954 // Returns the DeclContext immediately enclosed by the template parameter
5955 // scope. For primary templates, this is the templated (e.g.) CXXRecordDecl.
5956 // For specializations, this is e.g. ClassTemplatePartialSpecializationDecl.
5957 static DeclContext *getTemplatedEntity(const TemplateTypeParmDecl *D,
5958 Scope *S) {
5959 if (D == nullptr)
5960 return nullptr;
5961 Scope *Inner = nullptr;
5962 while (S) {
5963 if (S->isTemplateParamScope() && S->isDeclScope(D))
5964 return Inner ? Inner->getEntity() : nullptr;
5965 Inner = S;
5966 S = S->getParent();
5967 }
5968 return nullptr;
5969 }
5970
5971 // Gets all the type constraint expressions that might apply to the type
5972 // variables associated with DC (as returned by getTemplatedEntity()).
5973 static SmallVector<AssociatedConstraint, 1>
5974 constraintsForTemplatedEntity(DeclContext *DC) {
5975 SmallVector<AssociatedConstraint, 1> Result;
5976 if (DC == nullptr)
5977 return Result;
5978 // Primary templates can have constraints.
5979 if (const auto *TD = cast<Decl>(DC)->getDescribedTemplate())
5980 TD->getAssociatedConstraints(Result);
5981 // Partial specializations may have constraints.
5982 if (const auto *CTPSD =
5983 dyn_cast<ClassTemplatePartialSpecializationDecl>(DC))
5984 CTPSD->getAssociatedConstraints(Result);
5985 if (const auto *VTPSD = dyn_cast<VarTemplatePartialSpecializationDecl>(DC))
5986 VTPSD->getAssociatedConstraints(Result);
5987 return Result;
5988 }
5989
5990 // Attempt to find the unique type satisfying a constraint.
5991 // This lets us show e.g. `int` instead of `std::same_as<int>`.
5992 static QualType deduceType(const TypeConstraint &T) {
5993 // Assume a same_as<T> return type constraint is std::same_as or equivalent.
5994 // In this case the return type is T.
5995 DeclarationName DN =
5996 T.getConceptReference()->getConceptNameInfo().getName();
5997 if (DN.isIdentifier() && DN.getAsIdentifierInfo()->isStr("same_as"))
5998 if (const auto *Args = T.getTemplateArgsAsWritten())
5999 if (Args->getNumTemplateArgs() == 1) {
6000 const auto &Arg = Args->arguments().front().getArgument();
6001 if (Arg.getKind() == TemplateArgument::Type)
6002 return Arg.getAsType();
6003 }
6004 return {};
6005 }
6006
6007 llvm::DenseMap<const IdentifierInfo *, Member> Results;
6008};
6009
6010// Returns a type for E that yields acceptable member completions.
6011// In particular, when E->getType() is DependentTy, try to guess a likely type.
6012// We accept some lossiness (like dropping parameters).
6013// We only try to handle common expressions on the LHS of MemberExpr.
6014QualType getApproximateType(const Expr *E, HeuristicResolver &Resolver) {
6015 QualType Result = Resolver.resolveExprToType(E);
6016 if (Result.isNull())
6017 return Result;
6018 Result = Resolver.simplifyType(Result.getNonReferenceType(), E, false);
6019 if (Result.isNull())
6020 return Result;
6021 return Result.getNonReferenceType();
6022}
6023
6024// If \p Base is ParenListExpr, assume a chain of comma operators and pick the
6025// last expr. We expect other ParenListExprs to be resolved to e.g. constructor
6026// calls before here. (So the ParenListExpr should be nonempty, but check just
6027// in case)
6028Expr *unwrapParenList(Expr *Base) {
6029 if (auto *PLE = llvm::dyn_cast_or_null<ParenListExpr>(Base)) {
6030 if (PLE->getNumExprs() == 0)
6031 return nullptr;
6032 Base = PLE->getExpr(PLE->getNumExprs() - 1);
6033 }
6034 return Base;
6035}
6036
6037} // namespace
6038
6040 Scope *S, Expr *Base, Expr *OtherOpBase, SourceLocation OpLoc, bool IsArrow,
6041 bool IsBaseExprStatement, QualType PreferredType) {
6042 Base = unwrapParenList(Base);
6043 OtherOpBase = unwrapParenList(OtherOpBase);
6044 if (!Base || !CodeCompleter)
6045 return;
6046
6047 ExprResult ConvertedBase =
6048 SemaRef.PerformMemberExprBaseConversion(Base, IsArrow);
6049 if (ConvertedBase.isInvalid())
6050 return;
6051 QualType ConvertedBaseType =
6052 getApproximateType(ConvertedBase.get(), Resolver);
6053
6054 enum CodeCompletionContext::Kind contextKind;
6055
6056 if (IsArrow) {
6057 if (QualType PointeeType = Resolver.getPointeeType(ConvertedBaseType);
6058 !PointeeType.isNull()) {
6059 ConvertedBaseType = PointeeType;
6060 }
6061 }
6062
6063 if (IsArrow) {
6065 } else {
6066 if (ConvertedBaseType->isObjCObjectPointerType() ||
6067 ConvertedBaseType->isObjCObjectOrInterfaceType()) {
6069 } else {
6071 }
6072 }
6073
6074 CodeCompletionContext CCContext(contextKind, ConvertedBaseType);
6075 CCContext.setPreferredType(PreferredType);
6076 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
6077 CodeCompleter->getCodeCompletionTUInfo(), CCContext,
6078 &ResultBuilder::IsMember);
6079
6080 auto DoCompletion = [&](Expr *Base, bool IsArrow,
6081 std::optional<FixItHint> AccessOpFixIt) -> bool {
6082 if (!Base)
6083 return false;
6084
6085 ExprResult ConvertedBase =
6086 SemaRef.PerformMemberExprBaseConversion(Base, IsArrow);
6087 if (ConvertedBase.isInvalid())
6088 return false;
6089 Base = ConvertedBase.get();
6090
6091 QualType BaseType = getApproximateType(Base, Resolver);
6092 if (BaseType.isNull())
6093 return false;
6094 ExprValueKind BaseKind = Base->getValueKind();
6095
6096 if (IsArrow) {
6097 if (QualType PointeeType = Resolver.getPointeeType(BaseType);
6098 !PointeeType.isNull()) {
6099 BaseType = PointeeType;
6100 BaseKind = VK_LValue;
6101 } else if (BaseType->isObjCObjectPointerType() ||
6102 BaseType->isTemplateTypeParmType()) {
6103 // Both cases (dot/arrow) handled below.
6104 } else {
6105 return false;
6106 }
6107 }
6108
6109 if (RecordDecl *RD = getAsRecordDecl(BaseType, Resolver)) {
6110 AddRecordMembersCompletionResults(SemaRef, Results, S, BaseType, BaseKind,
6111 RD, std::move(AccessOpFixIt));
6112 } else if (const auto *TTPT =
6113 dyn_cast<TemplateTypeParmType>(BaseType.getTypePtr())) {
6114 auto Operator =
6115 IsArrow ? ConceptInfo::Member::Arrow : ConceptInfo::Member::Dot;
6116 for (const auto &R : ConceptInfo(*TTPT, S).members()) {
6117 if (R.Operator != Operator)
6118 continue;
6120 R.render(SemaRef, CodeCompleter->getAllocator(),
6121 CodeCompleter->getCodeCompletionTUInfo()));
6122 if (AccessOpFixIt)
6123 Result.FixIts.push_back(*AccessOpFixIt);
6124 Results.AddResult(std::move(Result));
6125 }
6126 } else if (!IsArrow && BaseType->isObjCObjectPointerType()) {
6127 // Objective-C property reference. Bail if we're performing fix-it code
6128 // completion since Objective-C properties are normally backed by ivars,
6129 // most Objective-C fix-its here would have little value.
6130 if (AccessOpFixIt) {
6131 return false;
6132 }
6133 AddedPropertiesSet AddedProperties;
6134
6135 if (const ObjCObjectPointerType *ObjCPtr =
6136 BaseType->getAsObjCInterfacePointerType()) {
6137 // Add property results based on our interface.
6138 assert(ObjCPtr && "Non-NULL pointer guaranteed above!");
6139 AddObjCProperties(CCContext, ObjCPtr->getInterfaceDecl(), true,
6140 /*AllowNullaryMethods=*/true, SemaRef.CurContext,
6141 AddedProperties, Results, IsBaseExprStatement);
6142 }
6143
6144 // Add properties from the protocols in a qualified interface.
6145 for (auto *I : BaseType->castAs<ObjCObjectPointerType>()->quals())
6146 AddObjCProperties(CCContext, I, true, /*AllowNullaryMethods=*/true,
6147 SemaRef.CurContext, AddedProperties, Results,
6148 IsBaseExprStatement, /*IsClassProperty*/ false,
6149 /*InOriginalClass*/ false);
6150 } else if ((IsArrow && BaseType->isObjCObjectPointerType()) ||
6151 (!IsArrow && BaseType->isObjCObjectType())) {
6152 // Objective-C instance variable access. Bail if we're performing fix-it
6153 // code completion since Objective-C properties are normally backed by
6154 // ivars, most Objective-C fix-its here would have little value.
6155 if (AccessOpFixIt) {
6156 return false;
6157 }
6158 ObjCInterfaceDecl *Class = nullptr;
6159 if (const ObjCObjectPointerType *ObjCPtr =
6160 BaseType->getAs<ObjCObjectPointerType>())
6161 Class = ObjCPtr->getInterfaceDecl();
6162 else
6163 Class = BaseType->castAs<ObjCObjectType>()->getInterface();
6164
6165 // Add all ivars from this class and its superclasses.
6166 if (Class) {
6167 CodeCompletionDeclConsumer Consumer(Results, Class, BaseType);
6168 Results.setFilter(&ResultBuilder::IsObjCIvar);
6169 SemaRef.LookupVisibleDecls(Class, Sema::LookupMemberName, Consumer,
6170 CodeCompleter->includeGlobals(),
6171 /*IncludeDependentBases=*/false,
6172 CodeCompleter->loadExternal());
6173 }
6174 }
6175
6176 // FIXME: How do we cope with isa?
6177 return true;
6178 };
6179
6180 Results.EnterNewScope();
6181
6182 bool CompletionSucceded = DoCompletion(Base, IsArrow, std::nullopt);
6183 if (CodeCompleter->includeFixIts()) {
6184 const CharSourceRange OpRange =
6185 CharSourceRange::getTokenRange(OpLoc, OpLoc);
6186 CompletionSucceded |= DoCompletion(
6187 OtherOpBase, !IsArrow,
6188 FixItHint::CreateReplacement(OpRange, IsArrow ? "." : "->"));
6189 }
6190
6191 Results.ExitScope();
6192
6193 if (!CompletionSucceded)
6194 return;
6195
6196 // Hand off the results found for code completion.
6198 Results.getCompletionContext(), Results.data(),
6199 Results.size());
6200}
6201
6203 Scope *S, const IdentifierInfo &ClassName, SourceLocation ClassNameLoc,
6204 bool IsBaseExprStatement) {
6205 const IdentifierInfo *ClassNamePtr = &ClassName;
6206 ObjCInterfaceDecl *IFace =
6207 SemaRef.ObjC().getObjCInterfaceDecl(ClassNamePtr, ClassNameLoc);
6208 if (!IFace)
6209 return;
6210 CodeCompletionContext CCContext(
6212 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
6213 CodeCompleter->getCodeCompletionTUInfo(), CCContext,
6214 &ResultBuilder::IsMember);
6215 Results.EnterNewScope();
6216 AddedPropertiesSet AddedProperties;
6217 AddObjCProperties(CCContext, IFace, true,
6218 /*AllowNullaryMethods=*/true, SemaRef.CurContext,
6219 AddedProperties, Results, IsBaseExprStatement,
6220 /*IsClassProperty=*/true);
6221 Results.ExitScope();
6223 Results.getCompletionContext(), Results.data(),
6224 Results.size());
6225}
6226
6227void SemaCodeCompletion::CodeCompleteTag(Scope *S, unsigned TagSpec) {
6228 if (!CodeCompleter)
6229 return;
6230
6231 ResultBuilder::LookupFilter Filter = nullptr;
6232 enum CodeCompletionContext::Kind ContextKind =
6234 switch ((DeclSpec::TST)TagSpec) {
6235 case DeclSpec::TST_enum:
6236 Filter = &ResultBuilder::IsEnum;
6238 break;
6239
6241 Filter = &ResultBuilder::IsUnion;
6243 break;
6244
6248 Filter = &ResultBuilder::IsClassOrStruct;
6250 break;
6251
6252 default:
6253 llvm_unreachable("Unknown type specifier kind in CodeCompleteTag");
6254 }
6255
6256 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
6257 CodeCompleter->getCodeCompletionTUInfo(), ContextKind);
6258 CodeCompletionDeclConsumer Consumer(Results, SemaRef.CurContext);
6259
6260 // First pass: look for tags.
6261 Results.setFilter(Filter);
6262 SemaRef.LookupVisibleDecls(S, Sema::LookupTagName, Consumer,
6263 CodeCompleter->includeGlobals(),
6264 CodeCompleter->loadExternal());
6265
6266 if (CodeCompleter->includeGlobals()) {
6267 // Second pass: look for nested name specifiers.
6268 Results.setFilter(&ResultBuilder::IsNestedNameSpecifier);
6269 SemaRef.LookupVisibleDecls(S, Sema::LookupNestedNameSpecifierName, Consumer,
6270 CodeCompleter->includeGlobals(),
6271 CodeCompleter->loadExternal());
6272 }
6273
6275 Results.getCompletionContext(), Results.data(),
6276 Results.size());
6277}
6278
6279static void AddTypeQualifierResults(DeclSpec &DS, ResultBuilder &Results,
6280 const LangOptions &LangOpts) {
6282 Results.AddResult("const");
6284 Results.AddResult("volatile");
6285 if (LangOpts.C99 && !(DS.getTypeQualifiers() & DeclSpec::TQ_restrict))
6286 Results.AddResult("restrict");
6287 if (LangOpts.C11 && !(DS.getTypeQualifiers() & DeclSpec::TQ_atomic))
6288 Results.AddResult("_Atomic");
6289 if (LangOpts.MSVCCompat && !(DS.getTypeQualifiers() & DeclSpec::TQ_unaligned))
6290 Results.AddResult("__unaligned");
6291}
6292
6294 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
6295 CodeCompleter->getCodeCompletionTUInfo(),
6297 Results.EnterNewScope();
6298 AddTypeQualifierResults(DS, Results, getLangOpts());
6299 Results.ExitScope();
6301 Results.getCompletionContext(), Results.data(),
6302 Results.size());
6303}
6304
6306 DeclSpec &DS, Declarator &D, const VirtSpecifiers *VS) {
6307 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
6308 CodeCompleter->getCodeCompletionTUInfo(),
6310 Results.EnterNewScope();
6311 AddTypeQualifierResults(DS, Results, getLangOpts());
6312 if (getLangOpts().CPlusPlus11) {
6313 Results.AddResult("noexcept");
6315 !D.isStaticMember()) {
6316 if (!VS || !VS->isFinalSpecified())
6317 Results.AddResult("final");
6318 if (!VS || !VS->isOverrideSpecified())
6319 Results.AddResult("override");
6320 }
6321 }
6322 Results.ExitScope();
6324 Results.getCompletionContext(), Results.data(),
6325 Results.size());
6326}
6327
6331
6333 if (SemaRef.getCurFunction()->SwitchStack.empty() || !CodeCompleter)
6334 return;
6335
6337 SemaRef.getCurFunction()->SwitchStack.back().getPointer();
6338 // Condition expression might be invalid, do not continue in this case.
6339 if (!Switch->getCond())
6340 return;
6341 QualType type = Switch->getCond()->IgnoreImplicit()->getType();
6342 EnumDecl *Enum = type->getAsEnumDecl();
6343 if (!Enum) {
6345 Data.IntegralConstantExpression = true;
6347 return;
6348 }
6349
6350 // Determine which enumerators we have already seen in the switch statement.
6351 // FIXME: Ideally, we would also be able to look *past* the code-completion
6352 // token, in case we are code-completing in the middle of the switch and not
6353 // at the end. However, we aren't able to do so at the moment.
6354 CoveredEnumerators Enumerators;
6355 for (SwitchCase *SC = Switch->getSwitchCaseList(); SC;
6356 SC = SC->getNextSwitchCase()) {
6357 CaseStmt *Case = dyn_cast<CaseStmt>(SC);
6358 if (!Case)
6359 continue;
6360
6361 Expr *CaseVal = Case->getLHS()->IgnoreParenCasts();
6362 if (auto *DRE = dyn_cast<DeclRefExpr>(CaseVal))
6363 if (auto *Enumerator =
6364 dyn_cast<EnumConstantDecl>(DRE->getDecl())) {
6365 // We look into the AST of the case statement to determine which
6366 // enumerator was named. Alternatively, we could compute the value of
6367 // the integral constant expression, then compare it against the
6368 // values of each enumerator. However, value-based approach would not
6369 // work as well with C++ templates where enumerators declared within a
6370 // template are type- and value-dependent.
6371 Enumerators.Seen.insert(Enumerator);
6372
6373 // If this is a qualified-id, keep track of the nested-name-specifier
6374 // so that we can reproduce it as part of code completion, e.g.,
6375 //
6376 // switch (TagD.getKind()) {
6377 // case TagDecl::TK_enum:
6378 // break;
6379 // case XXX
6380 //
6381 // At the XXX, our completions are TagDecl::TK_union,
6382 // TagDecl::TK_struct, and TagDecl::TK_class, rather than TK_union,
6383 // TK_struct, and TK_class.
6384 Enumerators.SuggestedQualifier = DRE->getQualifier();
6385 }
6386 }
6387
6388 // Add any enumerators that have not yet been mentioned.
6389 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
6390 CodeCompleter->getCodeCompletionTUInfo(),
6392 AddEnumerators(Results, getASTContext(), Enum, SemaRef.CurContext,
6393 Enumerators);
6394
6395 if (CodeCompleter->includeMacros()) {
6396 AddMacroResults(SemaRef.PP, Results, CodeCompleter->loadExternal(), false);
6397 }
6399 Results.getCompletionContext(), Results.data(),
6400 Results.size());
6401}
6402
6404 if (Args.size() && !Args.data())
6405 return true;
6406
6407 for (unsigned I = 0; I != Args.size(); ++I)
6408 if (!Args[I])
6409 return true;
6410
6411 return false;
6412}
6413
6415
6417 Sema &SemaRef, SmallVectorImpl<ResultCandidate> &Results,
6418 OverloadCandidateSet &CandidateSet, SourceLocation Loc, size_t ArgSize) {
6419 // Sort the overload candidate set by placing the best overloads first.
6420 llvm::stable_sort(CandidateSet, [&](const OverloadCandidate &X,
6421 const OverloadCandidate &Y) {
6422 return isBetterOverloadCandidate(SemaRef, X, Y, Loc, CandidateSet.getKind(),
6423 /*PartialOverloading=*/true);
6424 });
6425
6426 // Add the remaining viable overload candidates as code-completion results.
6427 for (OverloadCandidate &Candidate : CandidateSet) {
6428 if (Candidate.Function) {
6429 if (Candidate.Function->isDeleted())
6430 continue;
6431 if (shouldEnforceArgLimit(/*PartialOverloading=*/true,
6432 Candidate.Function) &&
6433 Candidate.Function->getNumParams() <= ArgSize &&
6434 // Having zero args is annoying, normally we don't surface a function
6435 // with 2 params, if you already have 2 params, because you are
6436 // inserting the 3rd now. But with zero, it helps the user to figure
6437 // out there are no overloads that take any arguments. Hence we are
6438 // keeping the overload.
6439 ArgSize > 0)
6440 continue;
6441 }
6442 if (Candidate.Viable)
6443 Results.push_back(ResultCandidate(Candidate.Function));
6444 }
6445}
6446
6447/// Get the type of the Nth parameter from a given set of overload
6448/// candidates.
6450 ArrayRef<ResultCandidate> Candidates, unsigned N) {
6451
6452 // Given the overloads 'Candidates' for a function call matching all arguments
6453 // up to N, return the type of the Nth parameter if it is the same for all
6454 // overload candidates.
6455 QualType ParamType;
6456 for (auto &Candidate : Candidates) {
6457 QualType CandidateParamType = Candidate.getParamType(N);
6458 if (CandidateParamType.isNull())
6459 continue;
6460 if (ParamType.isNull()) {
6461 ParamType = CandidateParamType;
6462 continue;
6463 }
6464 if (!SemaRef.Context.hasSameUnqualifiedType(
6465 ParamType.getNonReferenceType(),
6466 CandidateParamType.getNonReferenceType()))
6467 // Two conflicting types, give up.
6468 return QualType();
6469 }
6470
6471 return ParamType;
6472}
6473
6474static QualType
6476 unsigned CurrentArg, SourceLocation OpenParLoc,
6477 bool Braced) {
6478 if (Candidates.empty())
6479 return QualType();
6482 SemaRef, CurrentArg, Candidates.data(), Candidates.size(), OpenParLoc,
6483 Braced);
6484 return getParamType(SemaRef, Candidates, CurrentArg);
6485}
6486
6487QualType
6489 SourceLocation OpenParLoc) {
6490 Fn = unwrapParenList(Fn);
6491 if (!CodeCompleter || !Fn)
6492 return QualType();
6493
6494 // FIXME: Provide support for variadic template functions.
6495 // Ignore type-dependent call expressions entirely.
6496 if (Fn->isTypeDependent() || anyNullArguments(Args))
6497 return QualType();
6498 // In presence of dependent args we surface all possible signatures using the
6499 // non-dependent args in the prefix. Afterwards we do a post filtering to make
6500 // sure provided candidates satisfy parameter count restrictions.
6501 auto ArgsWithoutDependentTypes =
6502 Args.take_while([](Expr *Arg) { return !Arg->isTypeDependent(); });
6503
6505
6506 Expr *NakedFn = Fn->IgnoreParenCasts();
6507 // Build an overload candidate set based on the functions we find.
6508 SourceLocation Loc = Fn->getExprLoc();
6509 OverloadCandidateSet CandidateSet(Loc,
6511
6512 if (auto ULE = dyn_cast<UnresolvedLookupExpr>(NakedFn)) {
6513 SemaRef.AddOverloadedCallCandidates(ULE, ArgsWithoutDependentTypes,
6514 CandidateSet,
6515 /*PartialOverloading=*/true);
6516 } else if (auto UME = dyn_cast<UnresolvedMemberExpr>(NakedFn)) {
6517 TemplateArgumentListInfo TemplateArgsBuffer, *TemplateArgs = nullptr;
6518 if (UME->hasExplicitTemplateArgs()) {
6519 UME->copyTemplateArgumentsInto(TemplateArgsBuffer);
6520 TemplateArgs = &TemplateArgsBuffer;
6521 }
6522
6523 // Add the base as first argument (use a nullptr if the base is implicit).
6524 SmallVector<Expr *, 12> ArgExprs(
6525 1, UME->isImplicitAccess() ? nullptr : UME->getBase());
6526 ArgExprs.append(ArgsWithoutDependentTypes.begin(),
6527 ArgsWithoutDependentTypes.end());
6528 UnresolvedSet<8> Decls;
6529 Decls.append(UME->decls_begin(), UME->decls_end());
6530 const bool FirstArgumentIsBase = !UME->isImplicitAccess() && UME->getBase();
6531 SemaRef.AddFunctionCandidates(Decls, ArgExprs, CandidateSet, TemplateArgs,
6532 /*SuppressUserConversions=*/false,
6533 /*PartialOverloading=*/true,
6534 FirstArgumentIsBase);
6535 } else {
6536 FunctionDecl *FD = nullptr;
6537 if (auto *MCE = dyn_cast<MemberExpr>(NakedFn))
6538 FD = dyn_cast<FunctionDecl>(MCE->getMemberDecl());
6539 else if (auto *DRE = dyn_cast<DeclRefExpr>(NakedFn))
6540 FD = dyn_cast<FunctionDecl>(DRE->getDecl());
6541 if (FD) { // We check whether it's a resolved function declaration.
6542 if (!getLangOpts().CPlusPlus ||
6543 !FD->getType()->getAs<FunctionProtoType>())
6544 Results.push_back(ResultCandidate(FD));
6545 else
6546 SemaRef.AddOverloadCandidate(FD,
6548 ArgsWithoutDependentTypes, CandidateSet,
6549 /*SuppressUserConversions=*/false,
6550 /*PartialOverloading=*/true);
6551
6552 } else if (auto DC = NakedFn->getType()->getAsCXXRecordDecl()) {
6553 // If expression's type is CXXRecordDecl, it may overload the function
6554 // call operator, so we check if it does and add them as candidates.
6555 // A complete type is needed to lookup for member function call operators.
6556 if (SemaRef.isCompleteType(Loc, NakedFn->getType())) {
6557 DeclarationName OpName =
6558 getASTContext().DeclarationNames.getCXXOperatorName(OO_Call);
6560 SemaRef.LookupQualifiedName(R, DC);
6561 R.suppressDiagnostics();
6562 SmallVector<Expr *, 12> ArgExprs(1, NakedFn);
6563 ArgExprs.append(ArgsWithoutDependentTypes.begin(),
6564 ArgsWithoutDependentTypes.end());
6565 SemaRef.AddFunctionCandidates(R.asUnresolvedSet(), ArgExprs,
6566 CandidateSet,
6567 /*ExplicitArgs=*/nullptr,
6568 /*SuppressUserConversions=*/false,
6569 /*PartialOverloading=*/true);
6570 }
6571 } else {
6572 // Lastly we check whether expression's type is function pointer or
6573 // function.
6574
6575 FunctionProtoTypeLoc P = Resolver.getFunctionProtoTypeLoc(NakedFn);
6576 QualType T = NakedFn->getType();
6577 if (!T->getPointeeType().isNull())
6578 T = T->getPointeeType();
6579
6580 if (auto FP = T->getAs<FunctionProtoType>()) {
6581 if (!SemaRef.TooManyArguments(FP->getNumParams(),
6582 ArgsWithoutDependentTypes.size(),
6583 /*PartialOverloading=*/true) ||
6584 FP->isVariadic()) {
6585 if (P) {
6586 Results.push_back(ResultCandidate(P));
6587 } else {
6588 Results.push_back(ResultCandidate(FP));
6589 }
6590 }
6591 } else if (auto FT = T->getAs<FunctionType>())
6592 // No prototype and declaration, it may be a K & R style function.
6593 Results.push_back(ResultCandidate(FT));
6594 }
6595 }
6596 mergeCandidatesWithResults(SemaRef, Results, CandidateSet, Loc, Args.size());
6597 QualType ParamType = ProduceSignatureHelp(SemaRef, Results, Args.size(),
6598 OpenParLoc, /*Braced=*/false);
6599 return !CandidateSet.empty() ? ParamType : QualType();
6600}
6601
6602// Determine which param to continue aggregate initialization from after
6603// a designated initializer.
6604//
6605// Given struct S { int a,b,c,d,e; }:
6606// after `S{.b=1,` we want to suggest c to continue
6607// after `S{.b=1, 2,` we continue with d (this is legal C and ext in C++)
6608// after `S{.b=1, .a=2,` we continue with b (this is legal C and ext in C++)
6609//
6610// Possible outcomes:
6611// - we saw a designator for a field, and continue from the returned index.
6612// Only aggregate initialization is allowed.
6613// - we saw a designator, but it was complex or we couldn't find the field.
6614// Only aggregate initialization is possible, but we can't assist with it.
6615// Returns an out-of-range index.
6616// - we saw no designators, just positional arguments.
6617// Returns std::nullopt.
6618static std::optional<unsigned>
6620 ArrayRef<Expr *> Args) {
6621 static constexpr unsigned Invalid = std::numeric_limits<unsigned>::max();
6622 assert(Aggregate.getKind() == ResultCandidate::CK_Aggregate);
6623
6624 // Look for designated initializers.
6625 // They're in their syntactic form, not yet resolved to fields.
6626 const IdentifierInfo *DesignatedFieldName = nullptr;
6627 unsigned ArgsAfterDesignator = 0;
6628 for (const Expr *Arg : Args) {
6629 if (const auto *DIE = dyn_cast<DesignatedInitExpr>(Arg)) {
6630 if (DIE->size() == 1 && DIE->getDesignator(0)->isFieldDesignator()) {
6631 DesignatedFieldName = DIE->getDesignator(0)->getFieldName();
6632 ArgsAfterDesignator = 0;
6633 } else {
6634 return Invalid; // Complicated designator.
6635 }
6636 } else if (isa<DesignatedInitUpdateExpr>(Arg)) {
6637 return Invalid; // Unsupported.
6638 } else {
6639 ++ArgsAfterDesignator;
6640 }
6641 }
6642 if (!DesignatedFieldName)
6643 return std::nullopt;
6644
6645 // Find the index within the class's fields.
6646 // (Probing getParamDecl() directly would be quadratic in number of fields).
6647 unsigned DesignatedIndex = 0;
6648 const FieldDecl *DesignatedField = nullptr;
6649 for (const auto *Field : Aggregate.getAggregate()->fields()) {
6650 if (Field->getIdentifier() == DesignatedFieldName) {
6651 DesignatedField = Field;
6652 break;
6653 }
6654 ++DesignatedIndex;
6655 }
6656 if (!DesignatedField)
6657 return Invalid; // Designator referred to a missing field, give up.
6658
6659 // Find the index within the aggregate (which may have leading bases).
6660 unsigned AggregateSize = Aggregate.getNumParams();
6661 while (DesignatedIndex < AggregateSize &&
6662 Aggregate.getParamDecl(DesignatedIndex) != DesignatedField)
6663 ++DesignatedIndex;
6664
6665 // Continue from the index after the last named field.
6666 return DesignatedIndex + ArgsAfterDesignator + 1;
6667}
6668
6671 SourceLocation OpenParLoc, bool Braced) {
6672 if (!CodeCompleter)
6673 return QualType();
6675
6676 // A complete type is needed to lookup for constructors.
6677 RecordDecl *RD =
6678 SemaRef.isCompleteType(Loc, Type) ? Type->getAsRecordDecl() : nullptr;
6679 if (!RD)
6680 return Type;
6681 CXXRecordDecl *CRD = dyn_cast<CXXRecordDecl>(RD);
6682
6683 // Consider aggregate initialization.
6684 // We don't check that types so far are correct.
6685 // We also don't handle C99/C++17 brace-elision, we assume init-list elements
6686 // are 1:1 with fields.
6687 // FIXME: it would be nice to support "unwrapping" aggregates that contain
6688 // a single subaggregate, like std::array<T, N> -> T __elements[N].
6689 if (Braced && !RD->isUnion() &&
6690 (!getLangOpts().CPlusPlus || (CRD && CRD->isAggregate()))) {
6691 ResultCandidate AggregateSig(RD);
6692 unsigned AggregateSize = AggregateSig.getNumParams();
6693
6694 if (auto NextIndex =
6695 getNextAggregateIndexAfterDesignatedInit(AggregateSig, Args)) {
6696 // A designator was used, only aggregate init is possible.
6697 if (*NextIndex >= AggregateSize)
6698 return Type;
6699 Results.push_back(AggregateSig);
6700 return ProduceSignatureHelp(SemaRef, Results, *NextIndex, OpenParLoc,
6701 Braced);
6702 }
6703
6704 // Describe aggregate initialization, but also constructors below.
6705 if (Args.size() < AggregateSize)
6706 Results.push_back(AggregateSig);
6707 }
6708
6709 // FIXME: Provide support for member initializers.
6710 // FIXME: Provide support for variadic template constructors.
6711
6712 if (CRD) {
6713 OverloadCandidateSet CandidateSet(Loc,
6715 for (NamedDecl *C : SemaRef.LookupConstructors(CRD)) {
6716 if (auto *FD = dyn_cast<FunctionDecl>(C)) {
6717 // FIXME: we can't yet provide correct signature help for initializer
6718 // list constructors, so skip them entirely.
6719 if (Braced && getLangOpts().CPlusPlus &&
6720 SemaRef.isInitListConstructor(FD))
6721 continue;
6722 SemaRef.AddOverloadCandidate(
6723 FD, DeclAccessPair::make(FD, C->getAccess()), Args, CandidateSet,
6724 /*SuppressUserConversions=*/false,
6725 /*PartialOverloading=*/true,
6726 /*AllowExplicit*/ true);
6727 } else if (auto *FTD = dyn_cast<FunctionTemplateDecl>(C)) {
6728 if (Braced && getLangOpts().CPlusPlus &&
6729 SemaRef.isInitListConstructor(FTD->getTemplatedDecl()))
6730 continue;
6731
6732 SemaRef.AddTemplateOverloadCandidate(
6733 FTD, DeclAccessPair::make(FTD, C->getAccess()),
6734 /*ExplicitTemplateArgs=*/nullptr, Args, CandidateSet,
6735 /*SuppressUserConversions=*/false,
6736 /*PartialOverloading=*/true);
6737 }
6738 }
6739 mergeCandidatesWithResults(SemaRef, Results, CandidateSet, Loc,
6740 Args.size());
6741 }
6742
6743 return ProduceSignatureHelp(SemaRef, Results, Args.size(), OpenParLoc,
6744 Braced);
6745}
6746
6748 Decl *ConstructorDecl, CXXScopeSpec SS, ParsedType TemplateTypeTy,
6749 ArrayRef<Expr *> ArgExprs, IdentifierInfo *II, SourceLocation OpenParLoc,
6750 bool Braced) {
6751 if (!CodeCompleter)
6752 return QualType();
6753
6755 dyn_cast<CXXConstructorDecl>(ConstructorDecl);
6756 if (!Constructor)
6757 return QualType();
6758 // FIXME: Add support for Base class constructors as well.
6759 if (ValueDecl *MemberDecl = SemaRef.tryLookupCtorInitMemberDecl(
6760 Constructor->getParent(), SS, TemplateTypeTy, II))
6761 return ProduceConstructorSignatureHelp(MemberDecl->getType(),
6762 MemberDecl->getLocation(), ArgExprs,
6763 OpenParLoc, Braced);
6764 return QualType();
6765}
6766
6768 unsigned Index,
6769 const TemplateParameterList &Params) {
6770 const NamedDecl *Param;
6771 if (Index < Params.size())
6772 Param = Params.getParam(Index);
6773 else if (Params.hasParameterPack())
6774 Param = Params.asArray().back();
6775 else
6776 return false; // too many args
6777
6778 switch (Arg.getKind()) {
6780 return llvm::isa<TemplateTypeParmDecl>(Param); // constraints not checked
6782 return llvm::isa<NonTypeTemplateParmDecl>(Param); // type not checked
6784 return llvm::isa<TemplateTemplateParmDecl>(Param); // signature not checked
6785 }
6786 llvm_unreachable("Unhandled switch case");
6787}
6788
6790 TemplateTy ParsedTemplate, ArrayRef<ParsedTemplateArgument> Args,
6791 SourceLocation LAngleLoc) {
6792 if (!CodeCompleter || !ParsedTemplate)
6793 return QualType();
6794
6796 auto Consider = [&](const TemplateDecl *TD) {
6797 // Only add if the existing args are compatible with the template.
6798 bool Matches = true;
6799 for (unsigned I = 0; I < Args.size(); ++I) {
6800 if (!argMatchesTemplateParams(Args[I], I, *TD->getTemplateParameters())) {
6801 Matches = false;
6802 break;
6803 }
6804 }
6805 if (Matches)
6806 Results.emplace_back(TD);
6807 };
6808
6809 TemplateName Template = ParsedTemplate.get();
6810 if (const auto *TD = Template.getAsTemplateDecl()) {
6811 Consider(TD);
6812 } else if (const auto *OTS = Template.getAsOverloadedTemplate()) {
6813 for (const NamedDecl *ND : *OTS)
6814 if (const auto *TD = llvm::dyn_cast<TemplateDecl>(ND))
6815 Consider(TD);
6816 }
6817 return ProduceSignatureHelp(SemaRef, Results, Args.size(), LAngleLoc,
6818 /*Braced=*/false);
6819}
6820
6821// Direct member lookup, used by designated initializers: only fields declared
6822// in `RD` itself (including indirect fields from anonymous members) are valid.
6823static const FieldDecl *lookupDirectField(RecordDecl *RD, const Designator &D) {
6824 for (const auto *Member : RD->lookup(D.getFieldDecl())) {
6825 if (const auto *FD = llvm::dyn_cast<FieldDecl>(Member))
6826 return FD;
6827 if (const auto *IFD = llvm::dyn_cast<IndirectFieldDecl>(Member))
6828 return IFD->getAnonField();
6829 }
6830 return nullptr;
6831}
6832
6834 ASTContext &Context, QualType BaseType, const Designation &Desig,
6835 HeuristicResolver &Resolver,
6836 llvm::function_ref<const FieldDecl *(RecordDecl *, const Designator &)>
6837 LookupField) {
6838 for (unsigned I = 0; I < Desig.getNumDesignators(); ++I) {
6839 if (BaseType.isNull())
6840 break;
6841
6842 const auto &D = Desig.getDesignator(I);
6843 if (D.isArrayDesignator() || D.isArrayRangeDesignator()) {
6844 if (BaseType->isDependentType()) {
6845 BaseType = Context.DependentTy;
6846 continue;
6847 }
6848 const ArrayType *AT = Context.getAsArrayType(BaseType);
6849 if (!AT)
6850 return QualType();
6851 BaseType = AT->getElementType();
6852 continue;
6853 }
6854
6855 assert(D.isFieldDesignator());
6856 if (BaseType->isDependentType()) {
6857 BaseType = Context.DependentTy;
6858 continue;
6859 }
6860
6861 RecordDecl *RD = getAsRecordDecl(BaseType, Resolver);
6862 if (!RD || !RD->isCompleteDefinition())
6863 return QualType();
6864
6865 const FieldDecl *MemberDecl = LookupField(RD, D);
6866 if (!MemberDecl)
6867 return QualType();
6868
6869 BaseType = MemberDecl->getType().getNonReferenceType();
6870 }
6871 return BaseType;
6872}
6873
6875 QualType BaseType, llvm::ArrayRef<Expr *> InitExprs, const Designation &D) {
6876 BaseType = getDesignatedType(SemaRef.Context, BaseType, D, Resolver,
6878 if (BaseType.isNull())
6879 return;
6880 const auto *RD = getAsRecordDecl(BaseType, Resolver);
6881 if (!RD || RD->fields().empty())
6882 return;
6883
6885 BaseType);
6886 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
6887 CodeCompleter->getCodeCompletionTUInfo(), CCC);
6888
6889 Results.EnterNewScope();
6890 for (const Decl *D : RD->decls()) {
6891 const FieldDecl *FD;
6892 if (auto *IFD = dyn_cast<IndirectFieldDecl>(D))
6893 FD = IFD->getAnonField();
6894 else if (auto *DFD = dyn_cast<FieldDecl>(D))
6895 FD = DFD;
6896 else
6897 continue;
6898
6899 // FIXME: Make use of previous designators to mark any fields before those
6900 // inaccessible, and also compute the next initializer priority.
6901 ResultBuilder::Result Result(FD, Results.getBasePriority(FD));
6902 Results.AddResult(Result, SemaRef.CurContext, /*Hiding=*/nullptr);
6903 }
6904 Results.ExitScope();
6906 Results.getCompletionContext(), Results.data(),
6907 Results.size());
6908}
6909
6911 const Designation &D) {
6912 // offsetof allows inherited fields and follows normal qualified name lookup,
6913 // not the direct-member iteration used by designated initializers.
6914 auto LookupQualified = [&](RecordDecl *RD,
6915 const Designator &Des) -> const FieldDecl * {
6916 LookupResult R(SemaRef, Des.getFieldDecl(), Des.getFieldLoc(),
6918 SemaRef.LookupQualifiedName(R, RD);
6919 // Peel via getUnderlyingDecl so a field exposed by `using Base::f;`
6920 // resolves through its UsingShadowDecl.
6921 for (NamedDecl *ND : R) {
6922 ND = ND->getUnderlyingDecl();
6923 if (auto *FD = dyn_cast<FieldDecl>(ND))
6924 return FD;
6925 if (auto *IFD = dyn_cast<IndirectFieldDecl>(ND))
6926 return IFD->getAnonField();
6927 }
6928 return nullptr;
6929 };
6930 BaseType = getDesignatedType(SemaRef.Context, BaseType, D, Resolver,
6931 LookupQualified);
6932 if (BaseType.isNull())
6933 return;
6934
6935 RecordDecl *RD = getAsRecordDecl(BaseType, Resolver);
6936 if (!RD)
6937 return;
6938
6940 BaseType);
6941 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
6942 CodeCompleter->getCodeCompletionTUInfo(), CCC,
6943 &ResultBuilder::IsOffsetofField);
6944
6945 Results.EnterNewScope();
6946 CodeCompletionDeclConsumer Consumer(Results, RD, BaseType);
6947 // LookupVisibleDecls traverses base classes (required for inherited fields)
6948 // and dependent bases (best-effort for templates). Globals are skipped:
6949 // offsetof designators name only members of the surrounding type.
6950 SemaRef.LookupVisibleDecls(RD, Sema::LookupMemberName, Consumer,
6951 /*IncludeGlobalScope=*/false,
6952 /*IncludeDependentBases=*/true,
6953 CodeCompleter->loadExternal());
6954 Results.ExitScope();
6955
6957 Results.getCompletionContext(), Results.data(),
6958 Results.size());
6959}
6960
6962 ValueDecl *VD = dyn_cast_or_null<ValueDecl>(D);
6963 if (!VD) {
6965 return;
6966 }
6967
6969 Data.PreferredType = VD->getType();
6970 // Ignore VD to avoid completing the variable itself, e.g. in 'int foo = ^'.
6971 Data.IgnoreDecls.push_back(VD);
6972
6974}
6975
6977 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
6978 CodeCompleter->getCodeCompletionTUInfo(),
6980 CodeCompletionBuilder Builder(Results.getAllocator(),
6981 Results.getCodeCompletionTUInfo());
6982 if (getLangOpts().CPlusPlus17) {
6983 if (!AfterExclaim) {
6984 if (Results.includeCodePatterns()) {
6985 Builder.AddTypedTextChunk("constexpr");
6987 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
6988 Builder.AddPlaceholderChunk("condition");
6989 Builder.AddChunk(CodeCompletionString::CK_RightParen);
6991 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
6993 Builder.AddPlaceholderChunk("statements");
6995 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
6996 Results.AddResult({Builder.TakeString()});
6997 } else {
6998 Results.AddResult({"constexpr"});
6999 }
7000 }
7001 }
7002 if (getLangOpts().CPlusPlus23) {
7003 if (Results.includeCodePatterns()) {
7004 Builder.AddTypedTextChunk("consteval");
7006 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
7008 Builder.AddPlaceholderChunk("statements");
7010 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
7011 Results.AddResult({Builder.TakeString()});
7012 } else {
7013 Results.AddResult({"consteval"});
7014 }
7015 }
7016
7018 Results.getCompletionContext(), Results.data(),
7019 Results.size());
7020}
7021
7023 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7024 CodeCompleter->getCodeCompletionTUInfo(),
7026 Results.setFilter(&ResultBuilder::IsOrdinaryName);
7027 Results.EnterNewScope();
7028
7029 CodeCompletionDeclConsumer Consumer(Results, SemaRef.CurContext);
7030 SemaRef.LookupVisibleDecls(S, Sema::LookupOrdinaryName, Consumer,
7031 CodeCompleter->includeGlobals(),
7032 CodeCompleter->loadExternal());
7033
7035
7036 // "else" block
7037 CodeCompletionBuilder Builder(Results.getAllocator(),
7038 Results.getCodeCompletionTUInfo());
7039
7040 auto AddElseBodyPattern = [&] {
7041 if (IsBracedThen) {
7043 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
7045 Builder.AddPlaceholderChunk("statements");
7047 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
7048 } else {
7051 Builder.AddPlaceholderChunk("statement");
7052 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
7053 }
7054 };
7055 Builder.AddTypedTextChunk("else");
7056 if (Results.includeCodePatterns())
7057 AddElseBodyPattern();
7058 Results.AddResult(Builder.TakeString());
7059
7060 // "else if" block
7061 Builder.AddTypedTextChunk("else if");
7063 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
7064 if (getLangOpts().CPlusPlus)
7065 Builder.AddPlaceholderChunk("condition");
7066 else
7067 Builder.AddPlaceholderChunk("expression");
7068 Builder.AddChunk(CodeCompletionString::CK_RightParen);
7069 if (Results.includeCodePatterns()) {
7070 AddElseBodyPattern();
7071 }
7072 Results.AddResult(Builder.TakeString());
7073
7074 Results.ExitScope();
7075
7076 if (S->getFnParent())
7078
7079 if (CodeCompleter->includeMacros())
7080 AddMacroResults(SemaRef.PP, Results, CodeCompleter->loadExternal(), false);
7081
7083 Results.getCompletionContext(), Results.data(),
7084 Results.size());
7085}
7086
7088 Scope *S, CXXScopeSpec &SS, bool EnteringContext, bool IsUsingDeclaration,
7089 bool IsAddressOfOperand, bool IsInDeclarationContext, QualType BaseType,
7090 QualType PreferredType) {
7091 if (SS.isEmpty() || !CodeCompleter)
7092 return;
7093
7095 CC.setIsUsingDeclaration(IsUsingDeclaration);
7096 CC.setCXXScopeSpecifier(SS);
7097
7098 // We want to keep the scope specifier even if it's invalid (e.g. the scope
7099 // "a::b::" is not corresponding to any context/namespace in the AST), since
7100 // it can be useful for global code completion which have information about
7101 // contexts/symbols that are not in the AST.
7102 if (SS.isInvalid()) {
7103 // As SS is invalid, we try to collect accessible contexts from the current
7104 // scope with a dummy lookup so that the completion consumer can try to
7105 // guess what the specified scope is.
7106 ResultBuilder DummyResults(SemaRef, CodeCompleter->getAllocator(),
7107 CodeCompleter->getCodeCompletionTUInfo(), CC);
7108 if (!PreferredType.isNull())
7109 DummyResults.setPreferredType(PreferredType);
7110 if (S->getEntity()) {
7111 CodeCompletionDeclConsumer Consumer(DummyResults, S->getEntity(),
7112 BaseType);
7113 SemaRef.LookupVisibleDecls(S, Sema::LookupOrdinaryName, Consumer,
7114 /*IncludeGlobalScope=*/false,
7115 /*LoadExternal=*/false);
7116 }
7118 DummyResults.getCompletionContext(), nullptr, 0);
7119 return;
7120 }
7121 // Always pretend to enter a context to ensure that a dependent type
7122 // resolves to a dependent record.
7123 DeclContext *Ctx = SemaRef.computeDeclContext(SS, /*EnteringContext=*/true);
7124
7125 std::optional<Sema::ContextRAII> SimulateContext;
7126 // When completing a definition, simulate that we are in class scope to access
7127 // private methods.
7128 if (IsInDeclarationContext && Ctx != nullptr)
7129 SimulateContext.emplace(SemaRef, Ctx);
7130
7131 // Try to instantiate any non-dependent declaration contexts before
7132 // we look in them. Bail out if we fail.
7134 if (NNS && !NNS.isDependent()) {
7135 if (Ctx == nullptr || SemaRef.RequireCompleteDeclContext(SS, Ctx))
7136 return;
7137 }
7138
7139 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7140 CodeCompleter->getCodeCompletionTUInfo(), CC);
7141 if (!PreferredType.isNull())
7142 Results.setPreferredType(PreferredType);
7143 Results.EnterNewScope();
7144
7145 // The "template" keyword can follow "::" in the grammar, but only
7146 // put it into the grammar if the nested-name-specifier is dependent.
7147 // FIXME: results is always empty, this appears to be dead.
7148 if (!Results.empty() && NNS.isDependent())
7149 Results.AddResult("template");
7150
7151 // If the scope is a concept-constrained type parameter, infer nested
7152 // members based on the constraints.
7154 if (const auto *TTPT = dyn_cast<TemplateTypeParmType>(NNS.getAsType())) {
7155 for (const auto &R : ConceptInfo(*TTPT, S).members()) {
7156 if (R.Operator != ConceptInfo::Member::Colons)
7157 continue;
7158 Results.AddResult(CodeCompletionResult(
7159 R.render(SemaRef, CodeCompleter->getAllocator(),
7160 CodeCompleter->getCodeCompletionTUInfo())));
7161 }
7162 }
7163 }
7164
7165 // Add calls to overridden virtual functions, if there are any.
7166 //
7167 // FIXME: This isn't wonderful, because we don't know whether we're actually
7168 // in a context that permits expressions. This is a general issue with
7169 // qualified-id completions.
7170 if (Ctx && !EnteringContext)
7171 MaybeAddOverrideCalls(SemaRef, Ctx, Results);
7172 Results.ExitScope();
7173
7174 if (Ctx &&
7175 (CodeCompleter->includeNamespaceLevelDecls() || !Ctx->isFileContext())) {
7176 CodeCompletionDeclConsumer Consumer(Results, Ctx, BaseType);
7177 Consumer.setIsInDeclarationContext(IsInDeclarationContext);
7178 Consumer.setIsAddressOfOperand(IsAddressOfOperand);
7179 SemaRef.LookupVisibleDecls(Ctx, Sema::LookupOrdinaryName, Consumer,
7180 /*IncludeGlobalScope=*/true,
7181 /*IncludeDependentBases=*/true,
7182 CodeCompleter->loadExternal());
7183 }
7184 SimulateContext.reset();
7186 Results.getCompletionContext(), Results.data(),
7187 Results.size());
7188}
7189
7191 if (!CodeCompleter)
7192 return;
7193
7194 // This can be both a using alias or using declaration, in the former we
7195 // expect a new name and a symbol in the latter case.
7197 Context.setIsUsingDeclaration(true);
7198
7199 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7200 CodeCompleter->getCodeCompletionTUInfo(), Context,
7201 &ResultBuilder::IsNestedNameSpecifier);
7202 Results.EnterNewScope();
7203
7204 // If we aren't in class scope, we could see the "namespace" keyword.
7205 if (!S->isClassScope())
7206 Results.AddResult(CodeCompletionResult("namespace"));
7207
7208 // After "using", we can see anything that would start a
7209 // nested-name-specifier.
7210 CodeCompletionDeclConsumer Consumer(Results, SemaRef.CurContext);
7211 SemaRef.LookupVisibleDecls(S, Sema::LookupOrdinaryName, Consumer,
7212 CodeCompleter->includeGlobals(),
7213 CodeCompleter->loadExternal());
7214 Results.ExitScope();
7215
7217 Results.getCompletionContext(), Results.data(),
7218 Results.size());
7219}
7220
7222 if (!CodeCompleter)
7223 return;
7224
7225 // After "using namespace", we expect to see a namespace name or namespace
7226 // alias.
7227 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7228 CodeCompleter->getCodeCompletionTUInfo(),
7230 &ResultBuilder::IsNamespaceOrAlias);
7231 Results.EnterNewScope();
7232 CodeCompletionDeclConsumer Consumer(Results, SemaRef.CurContext);
7233 SemaRef.LookupVisibleDecls(S, Sema::LookupOrdinaryName, Consumer,
7234 CodeCompleter->includeGlobals(),
7235 CodeCompleter->loadExternal());
7236 Results.ExitScope();
7238 Results.getCompletionContext(), Results.data(),
7239 Results.size());
7240}
7241
7243 if (!CodeCompleter)
7244 return;
7245
7246 DeclContext *Ctx = S->getEntity();
7247 if (!S->getParent())
7248 Ctx = getASTContext().getTranslationUnitDecl();
7249
7250 bool SuppressedGlobalResults =
7251 Ctx && !CodeCompleter->includeGlobals() && isa<TranslationUnitDecl>(Ctx);
7252
7253 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7254 CodeCompleter->getCodeCompletionTUInfo(),
7255 SuppressedGlobalResults
7258 &ResultBuilder::IsNamespace);
7259
7260 if (Ctx && Ctx->isFileContext() && !SuppressedGlobalResults) {
7261 // We only want to see those namespaces that have already been defined
7262 // within this scope, because its likely that the user is creating an
7263 // extended namespace declaration. Keep track of the most recent
7264 // definition of each namespace.
7265 std::map<NamespaceDecl *, NamespaceDecl *> OrigToLatest;
7267 NS(Ctx->decls_begin()),
7268 NSEnd(Ctx->decls_end());
7269 NS != NSEnd; ++NS)
7270 OrigToLatest[NS->getFirstDecl()] = *NS;
7271
7272 // Add the most recent definition (or extended definition) of each
7273 // namespace to the list of results.
7274 Results.EnterNewScope();
7275 for (std::map<NamespaceDecl *, NamespaceDecl *>::iterator
7276 NS = OrigToLatest.begin(),
7277 NSEnd = OrigToLatest.end();
7278 NS != NSEnd; ++NS)
7279 Results.AddResult(
7280 CodeCompletionResult(NS->second, Results.getBasePriority(NS->second),
7281 /*Qualifier=*/std::nullopt),
7282 SemaRef.CurContext, nullptr, false);
7283 Results.ExitScope();
7284 }
7285
7287 Results.getCompletionContext(), Results.data(),
7288 Results.size());
7289}
7290
7292 if (!CodeCompleter)
7293 return;
7294
7295 // After "namespace", we expect to see a namespace or alias.
7296 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7297 CodeCompleter->getCodeCompletionTUInfo(),
7299 &ResultBuilder::IsNamespaceOrAlias);
7300 CodeCompletionDeclConsumer Consumer(Results, SemaRef.CurContext);
7301 SemaRef.LookupVisibleDecls(S, Sema::LookupOrdinaryName, Consumer,
7302 CodeCompleter->includeGlobals(),
7303 CodeCompleter->loadExternal());
7305 Results.getCompletionContext(), Results.data(),
7306 Results.size());
7307}
7308
7310 if (!CodeCompleter)
7311 return;
7312
7314 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7315 CodeCompleter->getCodeCompletionTUInfo(),
7317 &ResultBuilder::IsType);
7318 Results.EnterNewScope();
7319
7320 // Add the names of overloadable operators. Note that OO_Conditional is not
7321 // actually overloadable.
7322#define OVERLOADED_OPERATOR(Name, Spelling, Token, Unary, Binary, MemberOnly) \
7323 if (OO_##Name != OO_Conditional) \
7324 Results.AddResult(Result(Spelling));
7325#include "clang/Basic/OperatorKinds.def"
7326
7327 // Add any type names visible from the current scope
7328 Results.allowNestedNameSpecifiers();
7329 CodeCompletionDeclConsumer Consumer(Results, SemaRef.CurContext);
7330 SemaRef.LookupVisibleDecls(S, Sema::LookupOrdinaryName, Consumer,
7331 CodeCompleter->includeGlobals(),
7332 CodeCompleter->loadExternal());
7333
7334 // Add any type specifiers
7336 Results.ExitScope();
7337
7339 Results.getCompletionContext(), Results.data(),
7340 Results.size());
7341}
7342
7344 Decl *ConstructorD, ArrayRef<CXXCtorInitializer *> Initializers) {
7345 if (!ConstructorD)
7346 return;
7347
7348 SemaRef.AdjustDeclIfTemplate(ConstructorD);
7349
7350 auto *Constructor = dyn_cast<CXXConstructorDecl>(ConstructorD);
7351 if (!Constructor)
7352 return;
7353
7354 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7355 CodeCompleter->getCodeCompletionTUInfo(),
7357 Results.EnterNewScope();
7358
7359 // Fill in any already-initialized fields or base classes.
7360 llvm::SmallPtrSet<FieldDecl *, 4> InitializedFields;
7361 llvm::SmallPtrSet<CanQualType, 4> InitializedBases;
7362 for (unsigned I = 0, E = Initializers.size(); I != E; ++I) {
7363 if (Initializers[I]->isBaseInitializer())
7364 InitializedBases.insert(getASTContext().getCanonicalType(
7365 QualType(Initializers[I]->getBaseClass(), 0)));
7366 else
7367 InitializedFields.insert(
7368 cast<FieldDecl>(Initializers[I]->getAnyMember()));
7369 }
7370
7371 // Add completions for base classes.
7373 bool SawLastInitializer = Initializers.empty();
7374 CXXRecordDecl *ClassDecl = Constructor->getParent();
7375
7376 auto GenerateCCS = [&](const NamedDecl *ND, const char *Name) {
7377 CodeCompletionBuilder Builder(Results.getAllocator(),
7378 Results.getCodeCompletionTUInfo());
7379 Builder.AddTypedTextChunk(Name);
7380 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
7381 if (const auto *Function = dyn_cast<FunctionDecl>(ND))
7382 AddFunctionParameterChunks(SemaRef.PP, Policy, Function, Builder);
7383 else if (const auto *FunTemplDecl = dyn_cast<FunctionTemplateDecl>(ND))
7385 FunTemplDecl->getTemplatedDecl(), Builder);
7386 Builder.AddChunk(CodeCompletionString::CK_RightParen);
7387 return Builder.TakeString();
7388 };
7389 auto AddDefaultCtorInit = [&](const char *Name, const char *Type,
7390 const NamedDecl *ND) {
7391 CodeCompletionBuilder Builder(Results.getAllocator(),
7392 Results.getCodeCompletionTUInfo());
7393 Builder.AddTypedTextChunk(Name);
7394 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
7395 Builder.AddPlaceholderChunk(Type);
7396 Builder.AddChunk(CodeCompletionString::CK_RightParen);
7397 if (ND) {
7398 auto CCR = CodeCompletionResult(
7399 Builder.TakeString(), ND,
7400 SawLastInitializer ? CCP_NextInitializer : CCP_MemberDeclaration);
7401 if (isa<FieldDecl>(ND))
7402 CCR.CursorKind = CXCursor_MemberRef;
7403 return Results.AddResult(CCR);
7404 }
7405 return Results.AddResult(CodeCompletionResult(
7406 Builder.TakeString(),
7407 SawLastInitializer ? CCP_NextInitializer : CCP_MemberDeclaration));
7408 };
7409 auto AddCtorsWithName = [&](const CXXRecordDecl *RD, unsigned int Priority,
7410 const char *Name, const FieldDecl *FD) {
7411 if (!RD)
7412 return AddDefaultCtorInit(Name,
7413 FD ? Results.getAllocator().CopyString(
7414 FD->getType().getAsString(Policy))
7415 : Name,
7416 FD);
7417 auto Ctors = getConstructors(getASTContext(), RD);
7418 if (Ctors.begin() == Ctors.end())
7419 return AddDefaultCtorInit(Name, Name, RD);
7420 for (const NamedDecl *Ctor : Ctors) {
7421 auto CCR = CodeCompletionResult(GenerateCCS(Ctor, Name), RD, Priority);
7422 CCR.CursorKind = getCursorKindForDecl(Ctor);
7423 Results.AddResult(CCR);
7424 }
7425 };
7426 auto AddBase = [&](const CXXBaseSpecifier &Base) {
7427 const char *BaseName =
7428 Results.getAllocator().CopyString(Base.getType().getAsString(Policy));
7429 const auto *RD = Base.getType()->getAsCXXRecordDecl();
7430 AddCtorsWithName(
7431 RD, SawLastInitializer ? CCP_NextInitializer : CCP_MemberDeclaration,
7432 BaseName, nullptr);
7433 };
7434 auto AddField = [&](const FieldDecl *FD) {
7435 const char *FieldName =
7436 Results.getAllocator().CopyString(FD->getIdentifier()->getName());
7437 const CXXRecordDecl *RD = FD->getType()->getAsCXXRecordDecl();
7438 AddCtorsWithName(
7439 RD, SawLastInitializer ? CCP_NextInitializer : CCP_MemberDeclaration,
7440 FieldName, FD);
7441 };
7442
7443 for (const auto &Base : ClassDecl->bases()) {
7444 if (!InitializedBases
7445 .insert(getASTContext().getCanonicalType(Base.getType()))
7446 .second) {
7447 SawLastInitializer =
7448 !Initializers.empty() && Initializers.back()->isBaseInitializer() &&
7449 getASTContext().hasSameUnqualifiedType(
7450 Base.getType(), QualType(Initializers.back()->getBaseClass(), 0));
7451 continue;
7452 }
7453
7454 AddBase(Base);
7455 SawLastInitializer = false;
7456 }
7457
7458 // Add completions for virtual base classes.
7459 for (const auto &Base : ClassDecl->vbases()) {
7460 if (!InitializedBases
7461 .insert(getASTContext().getCanonicalType(Base.getType()))
7462 .second) {
7463 SawLastInitializer =
7464 !Initializers.empty() && Initializers.back()->isBaseInitializer() &&
7465 getASTContext().hasSameUnqualifiedType(
7466 Base.getType(), QualType(Initializers.back()->getBaseClass(), 0));
7467 continue;
7468 }
7469
7470 AddBase(Base);
7471 SawLastInitializer = false;
7472 }
7473
7474 // Add completions for members.
7475 for (auto *Field : ClassDecl->fields()) {
7476 if (!InitializedFields.insert(cast<FieldDecl>(Field->getCanonicalDecl()))
7477 .second) {
7478 SawLastInitializer = !Initializers.empty() &&
7479 Initializers.back()->isAnyMemberInitializer() &&
7480 Initializers.back()->getAnyMember() == Field;
7481 continue;
7482 }
7483
7484 if (!Field->getDeclName())
7485 continue;
7486
7487 AddField(Field);
7488 SawLastInitializer = false;
7489 }
7490 Results.ExitScope();
7491
7493 Results.getCompletionContext(), Results.data(),
7494 Results.size());
7495}
7496
7497/// Determine whether this scope denotes a namespace.
7498static bool isNamespaceScope(Scope *S) {
7499 DeclContext *DC = S->getEntity();
7500 if (!DC)
7501 return false;
7502
7503 return DC->isFileContext();
7504}
7505
7507 LambdaIntroducer &Intro,
7508 bool AfterAmpersand) {
7509 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7510 CodeCompleter->getCodeCompletionTUInfo(),
7512 Results.EnterNewScope();
7513
7514 // Note what has already been captured.
7516 bool IncludedThis = false;
7517 for (const auto &C : Intro.Captures) {
7518 if (C.Kind == LCK_This) {
7519 IncludedThis = true;
7520 continue;
7521 }
7522
7523 Known.insert(C.Id);
7524 }
7525
7526 // Look for other capturable variables.
7527 for (; S && !isNamespaceScope(S); S = S->getParent()) {
7528 for (const auto *D : S->decls()) {
7529 const auto *Var = dyn_cast<VarDecl>(D);
7530 if (!Var || !Var->hasLocalStorage() || Var->hasAttr<BlocksAttr>())
7531 continue;
7532
7533 if (Known.insert(Var->getIdentifier()).second)
7534 Results.AddResult(CodeCompletionResult(Var, CCP_LocalDeclaration),
7535 SemaRef.CurContext, nullptr, false);
7536 }
7537 }
7538
7539 // Add 'this', if it would be valid.
7540 if (!IncludedThis && !AfterAmpersand && Intro.Default != LCD_ByCopy)
7541 addThisCompletion(SemaRef, Results);
7542
7543 Results.ExitScope();
7544
7546 Results.getCompletionContext(), Results.data(),
7547 Results.size());
7548}
7549
7551 if (!getLangOpts().CPlusPlus11)
7552 return;
7553 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7554 CodeCompleter->getCodeCompletionTUInfo(),
7556 auto ShouldAddDefault = [&D, this]() {
7557 if (!D.isFunctionDeclarator())
7558 return false;
7559 auto &Id = D.getName();
7560 if (Id.getKind() == UnqualifiedIdKind::IK_DestructorName)
7561 return true;
7562 // FIXME(liuhui): Ideally, we should check the constructor parameter list to
7563 // verify that it is the default, copy or move constructor?
7564 if (Id.getKind() == UnqualifiedIdKind::IK_ConstructorName &&
7566 return true;
7567 if (Id.getKind() == UnqualifiedIdKind::IK_OperatorFunctionId) {
7568 auto Op = Id.OperatorFunctionId.Operator;
7569 // FIXME(liuhui): Ideally, we should check the function parameter list to
7570 // verify that it is the copy or move assignment?
7571 if (Op == OverloadedOperatorKind::OO_Equal)
7572 return true;
7573 if (getLangOpts().CPlusPlus20 &&
7574 (Op == OverloadedOperatorKind::OO_EqualEqual ||
7575 Op == OverloadedOperatorKind::OO_ExclaimEqual ||
7576 Op == OverloadedOperatorKind::OO_Less ||
7577 Op == OverloadedOperatorKind::OO_LessEqual ||
7578 Op == OverloadedOperatorKind::OO_Greater ||
7579 Op == OverloadedOperatorKind::OO_GreaterEqual ||
7580 Op == OverloadedOperatorKind::OO_Spaceship))
7581 return true;
7582 }
7583 return false;
7584 };
7585
7586 Results.EnterNewScope();
7587 if (ShouldAddDefault())
7588 Results.AddResult("default");
7589 // FIXME(liuhui): Ideally, we should only provide `delete` completion for the
7590 // first function declaration.
7591 Results.AddResult("delete");
7592 Results.ExitScope();
7594 Results.getCompletionContext(), Results.data(),
7595 Results.size());
7596}
7597
7598/// Macro that optionally prepends an "@" to the string literal passed in via
7599/// Keyword, depending on whether NeedAt is true or false.
7600#define OBJC_AT_KEYWORD_NAME(NeedAt, Keyword) ((NeedAt) ? "@" Keyword : Keyword)
7601
7602static void AddObjCImplementationResults(const LangOptions &LangOpts,
7603 ResultBuilder &Results, bool NeedAt) {
7605 // Since we have an implementation, we can end it.
7606 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt, "end")));
7607
7608 CodeCompletionBuilder Builder(Results.getAllocator(),
7609 Results.getCodeCompletionTUInfo());
7610 if (LangOpts.ObjC) {
7611 // @dynamic
7612 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "dynamic"));
7614 Builder.AddPlaceholderChunk("property");
7615 Results.AddResult(Result(Builder.TakeString()));
7616
7617 // @synthesize
7618 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "synthesize"));
7620 Builder.AddPlaceholderChunk("property");
7621 Results.AddResult(Result(Builder.TakeString()));
7622 }
7623}
7624
7625static void AddObjCInterfaceResults(const LangOptions &LangOpts,
7626 ResultBuilder &Results, bool NeedAt) {
7628
7629 // Since we have an interface or protocol, we can end it.
7630 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt, "end")));
7631
7632 if (LangOpts.ObjC) {
7633 // @property
7634 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt, "property")));
7635
7636 // @required
7637 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt, "required")));
7638
7639 // @optional
7640 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt, "optional")));
7641 }
7642}
7643
7644static void AddObjCTopLevelResults(ResultBuilder &Results, bool NeedAt) {
7646 CodeCompletionBuilder Builder(Results.getAllocator(),
7647 Results.getCodeCompletionTUInfo());
7648
7649 // @class name ;
7650 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "class"));
7652 Builder.AddPlaceholderChunk("name");
7653 Results.AddResult(Result(Builder.TakeString()));
7654
7655 if (Results.includeCodePatterns()) {
7656 // @interface name
7657 // FIXME: Could introduce the whole pattern, including superclasses and
7658 // such.
7659 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "interface"));
7661 Builder.AddPlaceholderChunk("class");
7662 Results.AddResult(Result(Builder.TakeString()));
7663
7664 // @protocol name
7665 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "protocol"));
7667 Builder.AddPlaceholderChunk("protocol");
7668 Results.AddResult(Result(Builder.TakeString()));
7669
7670 // @implementation name
7671 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "implementation"));
7673 Builder.AddPlaceholderChunk("class");
7674 Results.AddResult(Result(Builder.TakeString()));
7675 }
7676
7677 // @compatibility_alias name
7678 Builder.AddTypedTextChunk(
7679 OBJC_AT_KEYWORD_NAME(NeedAt, "compatibility_alias"));
7681 Builder.AddPlaceholderChunk("alias");
7683 Builder.AddPlaceholderChunk("class");
7684 Results.AddResult(Result(Builder.TakeString()));
7685
7686 if (Results.getSema().getLangOpts().Modules) {
7687 // @import name
7688 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "import"));
7690 Builder.AddPlaceholderChunk("module");
7691 Results.AddResult(Result(Builder.TakeString()));
7692 }
7693}
7694
7696 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7697 CodeCompleter->getCodeCompletionTUInfo(),
7699 Results.EnterNewScope();
7700 if (isa<ObjCImplDecl>(SemaRef.CurContext))
7701 AddObjCImplementationResults(getLangOpts(), Results, false);
7702 else if (SemaRef.CurContext->isObjCContainer())
7703 AddObjCInterfaceResults(getLangOpts(), Results, false);
7704 else
7705 AddObjCTopLevelResults(Results, false);
7706 Results.ExitScope();
7708 Results.getCompletionContext(), Results.data(),
7709 Results.size());
7710}
7711
7712static void AddObjCExpressionResults(ResultBuilder &Results, bool NeedAt) {
7714 CodeCompletionBuilder Builder(Results.getAllocator(),
7715 Results.getCodeCompletionTUInfo());
7716
7717 // @encode ( type-name )
7718 const char *EncodeType = "char[]";
7719 if (Results.getSema().getLangOpts().CPlusPlus ||
7720 Results.getSema().getLangOpts().ConstStrings)
7721 EncodeType = "const char[]";
7722 Builder.AddResultTypeChunk(EncodeType);
7723 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "encode"));
7724 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
7725 Builder.AddPlaceholderChunk("type-name");
7726 Builder.AddChunk(CodeCompletionString::CK_RightParen);
7727 Results.AddResult(Result(Builder.TakeString()));
7728
7729 // @protocol ( protocol-name )
7730 Builder.AddResultTypeChunk("Protocol *");
7731 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "protocol"));
7732 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
7733 Builder.AddPlaceholderChunk("protocol-name");
7734 Builder.AddChunk(CodeCompletionString::CK_RightParen);
7735 Results.AddResult(Result(Builder.TakeString()));
7736
7737 // @selector ( selector )
7738 Builder.AddResultTypeChunk("SEL");
7739 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "selector"));
7740 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
7741 Builder.AddPlaceholderChunk("selector");
7742 Builder.AddChunk(CodeCompletionString::CK_RightParen);
7743 Results.AddResult(Result(Builder.TakeString()));
7744
7745 // @"string"
7746 Builder.AddResultTypeChunk("NSString *");
7747 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "\""));
7748 Builder.AddPlaceholderChunk("string");
7749 Builder.AddTextChunk("\"");
7750 Results.AddResult(Result(Builder.TakeString()));
7751
7752 // @[objects, ...]
7753 Builder.AddResultTypeChunk("NSArray *");
7754 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "["));
7755 Builder.AddPlaceholderChunk("objects, ...");
7756 Builder.AddChunk(CodeCompletionString::CK_RightBracket);
7757 Results.AddResult(Result(Builder.TakeString()));
7758
7759 // @{key : object, ...}
7760 Builder.AddResultTypeChunk("NSDictionary *");
7761 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "{"));
7762 Builder.AddPlaceholderChunk("key");
7763 Builder.AddChunk(CodeCompletionString::CK_Colon);
7765 Builder.AddPlaceholderChunk("object, ...");
7766 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
7767 Results.AddResult(Result(Builder.TakeString()));
7768
7769 // @(expression)
7770 Builder.AddResultTypeChunk("id");
7771 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "("));
7772 Builder.AddPlaceholderChunk("expression");
7773 Builder.AddChunk(CodeCompletionString::CK_RightParen);
7774 Results.AddResult(Result(Builder.TakeString()));
7775}
7776
7777static void AddObjCStatementResults(ResultBuilder &Results, bool NeedAt) {
7779 CodeCompletionBuilder Builder(Results.getAllocator(),
7780 Results.getCodeCompletionTUInfo());
7781
7782 if (Results.includeCodePatterns()) {
7783 // @try { statements } @catch ( declaration ) { statements } @finally
7784 // { statements }
7785 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "try"));
7786 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
7787 Builder.AddPlaceholderChunk("statements");
7788 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
7789 Builder.AddTextChunk("@catch");
7790 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
7791 Builder.AddPlaceholderChunk("parameter");
7792 Builder.AddChunk(CodeCompletionString::CK_RightParen);
7793 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
7794 Builder.AddPlaceholderChunk("statements");
7795 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
7796 Builder.AddTextChunk("@finally");
7797 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
7798 Builder.AddPlaceholderChunk("statements");
7799 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
7800 Results.AddResult(Result(Builder.TakeString()));
7801 }
7802
7803 // @throw
7804 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "throw"));
7806 Builder.AddPlaceholderChunk("expression");
7807 Results.AddResult(Result(Builder.TakeString()));
7808
7809 if (Results.includeCodePatterns()) {
7810 // @synchronized ( expression ) { statements }
7811 Builder.AddTypedTextChunk(OBJC_AT_KEYWORD_NAME(NeedAt, "synchronized"));
7813 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
7814 Builder.AddPlaceholderChunk("expression");
7815 Builder.AddChunk(CodeCompletionString::CK_RightParen);
7816 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
7817 Builder.AddPlaceholderChunk("statements");
7818 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
7819 Results.AddResult(Result(Builder.TakeString()));
7820 }
7821}
7822
7823static void AddObjCVisibilityResults(const LangOptions &LangOpts,
7824 ResultBuilder &Results, bool NeedAt) {
7826 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt, "private")));
7827 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt, "protected")));
7828 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt, "public")));
7829 if (LangOpts.ObjC)
7830 Results.AddResult(Result(OBJC_AT_KEYWORD_NAME(NeedAt, "package")));
7831}
7832
7834 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7835 CodeCompleter->getCodeCompletionTUInfo(),
7837 Results.EnterNewScope();
7838 AddObjCVisibilityResults(getLangOpts(), Results, false);
7839 Results.ExitScope();
7841 Results.getCompletionContext(), Results.data(),
7842 Results.size());
7843}
7844
7846 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7847 CodeCompleter->getCodeCompletionTUInfo(),
7849 Results.EnterNewScope();
7850 AddObjCStatementResults(Results, false);
7851 AddObjCExpressionResults(Results, false);
7852 Results.ExitScope();
7854 Results.getCompletionContext(), Results.data(),
7855 Results.size());
7856}
7857
7859 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7860 CodeCompleter->getCodeCompletionTUInfo(),
7862 Results.EnterNewScope();
7863 AddObjCExpressionResults(Results, false);
7864 Results.ExitScope();
7866 Results.getCompletionContext(), Results.data(),
7867 Results.size());
7868}
7869
7870/// Determine whether the addition of the given flag to an Objective-C
7871/// property's attributes will cause a conflict.
7872static bool ObjCPropertyFlagConflicts(unsigned Attributes, unsigned NewFlag) {
7873 // Check if we've already added this flag.
7874 if (Attributes & NewFlag)
7875 return true;
7876
7877 Attributes |= NewFlag;
7878
7879 // Check for collisions with "readonly".
7880 if ((Attributes & ObjCPropertyAttribute::kind_readonly) &&
7882 return true;
7883
7884 // Check for more than one of { assign, copy, retain, strong, weak }.
7885 unsigned AssignCopyRetMask =
7886 Attributes &
7891 if (AssignCopyRetMask &&
7892 AssignCopyRetMask != ObjCPropertyAttribute::kind_assign &&
7893 AssignCopyRetMask != ObjCPropertyAttribute::kind_unsafe_unretained &&
7894 AssignCopyRetMask != ObjCPropertyAttribute::kind_copy &&
7895 AssignCopyRetMask != ObjCPropertyAttribute::kind_retain &&
7896 AssignCopyRetMask != ObjCPropertyAttribute::kind_strong &&
7897 AssignCopyRetMask != ObjCPropertyAttribute::kind_weak)
7898 return true;
7899
7900 return false;
7901}
7902
7904 ObjCDeclSpec &ODS) {
7905 if (!CodeCompleter)
7906 return;
7907
7908 unsigned Attributes = ODS.getPropertyAttributes();
7909
7910 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
7911 CodeCompleter->getCodeCompletionTUInfo(),
7913 Results.EnterNewScope();
7914 if (!ObjCPropertyFlagConflicts(Attributes,
7916 Results.AddResult(CodeCompletionResult("readonly"));
7917 if (!ObjCPropertyFlagConflicts(Attributes,
7919 Results.AddResult(CodeCompletionResult("assign"));
7920 if (!ObjCPropertyFlagConflicts(Attributes,
7922 Results.AddResult(CodeCompletionResult("unsafe_unretained"));
7923 if (!ObjCPropertyFlagConflicts(Attributes,
7925 Results.AddResult(CodeCompletionResult("readwrite"));
7926 if (!ObjCPropertyFlagConflicts(Attributes,
7928 Results.AddResult(CodeCompletionResult("retain"));
7929 if (!ObjCPropertyFlagConflicts(Attributes,
7931 Results.AddResult(CodeCompletionResult("strong"));
7933 Results.AddResult(CodeCompletionResult("copy"));
7934 if (!ObjCPropertyFlagConflicts(Attributes,
7936 Results.AddResult(CodeCompletionResult("nonatomic"));
7937 if (!ObjCPropertyFlagConflicts(Attributes,
7939 Results.AddResult(CodeCompletionResult("atomic"));
7940
7941 // Only suggest "weak" if we're compiling for ARC-with-weak-references or GC.
7942 if (getLangOpts().ObjCWeak || getLangOpts().getGC() != LangOptions::NonGC)
7943 if (!ObjCPropertyFlagConflicts(Attributes,
7945 Results.AddResult(CodeCompletionResult("weak"));
7946
7947 if (!ObjCPropertyFlagConflicts(Attributes,
7949 CodeCompletionBuilder Setter(Results.getAllocator(),
7950 Results.getCodeCompletionTUInfo());
7951 Setter.AddTypedTextChunk("setter");
7952 Setter.AddTextChunk("=");
7953 Setter.AddPlaceholderChunk("method");
7954 Results.AddResult(CodeCompletionResult(Setter.TakeString()));
7955 }
7956 if (!ObjCPropertyFlagConflicts(Attributes,
7958 CodeCompletionBuilder Getter(Results.getAllocator(),
7959 Results.getCodeCompletionTUInfo());
7960 Getter.AddTypedTextChunk("getter");
7961 Getter.AddTextChunk("=");
7962 Getter.AddPlaceholderChunk("method");
7963 Results.AddResult(CodeCompletionResult(Getter.TakeString()));
7964 }
7965 if (!ObjCPropertyFlagConflicts(Attributes,
7967 Results.AddResult(CodeCompletionResult("nonnull"));
7968 Results.AddResult(CodeCompletionResult("nullable"));
7969 Results.AddResult(CodeCompletionResult("null_unspecified"));
7970 Results.AddResult(CodeCompletionResult("null_resettable"));
7971 }
7972 Results.ExitScope();
7974 Results.getCompletionContext(), Results.data(),
7975 Results.size());
7976}
7977
7978/// Describes the kind of Objective-C method that we want to find
7979/// via code completion.
7981 MK_Any, ///< Any kind of method, provided it means other specified criteria.
7982 MK_ZeroArgSelector, ///< Zero-argument (unary) selector.
7983 MK_OneArgSelector ///< One-argument selector.
7984};
7985
7988 bool AllowSameLength = true) {
7989 unsigned NumSelIdents = SelIdents.size();
7990 if (NumSelIdents > Sel.getNumArgs())
7991 return false;
7992
7993 switch (WantKind) {
7994 case MK_Any:
7995 break;
7996 case MK_ZeroArgSelector:
7997 return Sel.isUnarySelector();
7998 case MK_OneArgSelector:
7999 return Sel.getNumArgs() == 1;
8000 }
8001
8002 if (!AllowSameLength && NumSelIdents && NumSelIdents == Sel.getNumArgs())
8003 return false;
8004
8005 for (unsigned I = 0; I != NumSelIdents; ++I)
8006 if (SelIdents[I] != Sel.getIdentifierInfoForSlot(I))
8007 return false;
8008
8009 return true;
8010}
8011
8013 ObjCMethodKind WantKind,
8015 bool AllowSameLength = true) {
8016 return isAcceptableObjCSelector(Method->getSelector(), WantKind, SelIdents,
8017 AllowSameLength);
8018}
8019
8020/// A set of selectors, which is used to avoid introducing multiple
8021/// completions with the same selector into the result set.
8023
8024/// Add all of the Objective-C methods in the given Objective-C
8025/// container to the set of results.
8026///
8027/// The container will be a class, protocol, category, or implementation of
8028/// any of the above. This mether will recurse to include methods from
8029/// the superclasses of classes along with their categories, protocols, and
8030/// implementations.
8031///
8032/// \param Container the container in which we'll look to find methods.
8033///
8034/// \param WantInstanceMethods Whether to add instance methods (only); if
8035/// false, this routine will add factory methods (only).
8036///
8037/// \param CurContext the context in which we're performing the lookup that
8038/// finds methods.
8039///
8040/// \param AllowSameLength Whether we allow a method to be added to the list
8041/// when it has the same number of parameters as we have selector identifiers.
8042///
8043/// \param Results the structure into which we'll add results.
8044static void AddObjCMethods(ObjCContainerDecl *Container,
8045 bool WantInstanceMethods, ObjCMethodKind WantKind,
8047 DeclContext *CurContext,
8048 VisitedSelectorSet &Selectors, bool AllowSameLength,
8049 ResultBuilder &Results, bool InOriginalClass = true,
8050 bool IsRootClass = false) {
8052 Container = getContainerDef(Container);
8053 ObjCInterfaceDecl *IFace = dyn_cast<ObjCInterfaceDecl>(Container);
8054 IsRootClass = IsRootClass || (IFace && !IFace->getSuperClass());
8055 for (ObjCMethodDecl *M : Container->methods()) {
8056 // The instance methods on the root class can be messaged via the
8057 // metaclass.
8058 if (M->isInstanceMethod() == WantInstanceMethods ||
8059 (IsRootClass && !WantInstanceMethods)) {
8060 // Check whether the selector identifiers we've been given are a
8061 // subset of the identifiers for this particular method.
8062 if (!isAcceptableObjCMethod(M, WantKind, SelIdents, AllowSameLength))
8063 continue;
8064
8065 if (!Selectors.insert(M->getSelector()).second)
8066 continue;
8067
8068 Result R =
8069 Result(M, Results.getBasePriority(M), /*Qualifier=*/std::nullopt);
8070 R.StartParameter = SelIdents.size();
8071 R.AllParametersAreInformative = (WantKind != MK_Any);
8072 if (!InOriginalClass)
8073 setInBaseClass(R);
8074 Results.MaybeAddResult(R, CurContext);
8075 }
8076 }
8077
8078 // Visit the protocols of protocols.
8079 if (const auto *Protocol = dyn_cast<ObjCProtocolDecl>(Container)) {
8080 if (Protocol->hasDefinition()) {
8081 const ObjCList<ObjCProtocolDecl> &Protocols =
8082 Protocol->getReferencedProtocols();
8083 for (ObjCList<ObjCProtocolDecl>::iterator I = Protocols.begin(),
8084 E = Protocols.end();
8085 I != E; ++I)
8086 AddObjCMethods(*I, WantInstanceMethods, WantKind, SelIdents, CurContext,
8087 Selectors, AllowSameLength, Results, false, IsRootClass);
8088 }
8089 }
8090
8091 if (!IFace || !IFace->hasDefinition())
8092 return;
8093
8094 // Add methods in protocols.
8095 for (ObjCProtocolDecl *I : IFace->protocols())
8096 AddObjCMethods(I, WantInstanceMethods, WantKind, SelIdents, CurContext,
8097 Selectors, AllowSameLength, Results, false, IsRootClass);
8098
8099 // Add methods in categories.
8100 for (ObjCCategoryDecl *CatDecl : IFace->known_categories()) {
8101 AddObjCMethods(CatDecl, WantInstanceMethods, WantKind, SelIdents,
8102 CurContext, Selectors, AllowSameLength, Results,
8103 InOriginalClass, IsRootClass);
8104
8105 // Add a categories protocol methods.
8106 const ObjCList<ObjCProtocolDecl> &Protocols =
8107 CatDecl->getReferencedProtocols();
8108 for (ObjCList<ObjCProtocolDecl>::iterator I = Protocols.begin(),
8109 E = Protocols.end();
8110 I != E; ++I)
8111 AddObjCMethods(*I, WantInstanceMethods, WantKind, SelIdents, CurContext,
8112 Selectors, AllowSameLength, Results, false, IsRootClass);
8113
8114 // Add methods in category implementations.
8115 if (ObjCCategoryImplDecl *Impl = CatDecl->getImplementation())
8116 AddObjCMethods(Impl, WantInstanceMethods, WantKind, SelIdents, CurContext,
8117 Selectors, AllowSameLength, Results, InOriginalClass,
8118 IsRootClass);
8119 }
8120
8121 // Add methods in superclass.
8122 // Avoid passing in IsRootClass since root classes won't have super classes.
8123 if (IFace->getSuperClass())
8124 AddObjCMethods(IFace->getSuperClass(), WantInstanceMethods, WantKind,
8125 SelIdents, CurContext, Selectors, AllowSameLength, Results,
8126 /*IsRootClass=*/false);
8127
8128 // Add methods in our implementation, if any.
8129 if (ObjCImplementationDecl *Impl = IFace->getImplementation())
8130 AddObjCMethods(Impl, WantInstanceMethods, WantKind, SelIdents, CurContext,
8131 Selectors, AllowSameLength, Results, InOriginalClass,
8132 IsRootClass);
8133}
8134
8136 // Try to find the interface where getters might live.
8138 dyn_cast_or_null<ObjCInterfaceDecl>(SemaRef.CurContext);
8139 if (!Class) {
8140 if (ObjCCategoryDecl *Category =
8141 dyn_cast_or_null<ObjCCategoryDecl>(SemaRef.CurContext))
8142 Class = Category->getClassInterface();
8143
8144 if (!Class)
8145 return;
8146 }
8147
8148 // Find all of the potential getters.
8149 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
8150 CodeCompleter->getCodeCompletionTUInfo(),
8152 Results.EnterNewScope();
8153
8154 VisitedSelectorSet Selectors;
8155 AddObjCMethods(Class, true, MK_ZeroArgSelector, {}, SemaRef.CurContext,
8156 Selectors,
8157 /*AllowSameLength=*/true, Results);
8158 Results.ExitScope();
8160 Results.getCompletionContext(), Results.data(),
8161 Results.size());
8162}
8163
8165 // Try to find the interface where setters might live.
8167 dyn_cast_or_null<ObjCInterfaceDecl>(SemaRef.CurContext);
8168 if (!Class) {
8169 if (ObjCCategoryDecl *Category =
8170 dyn_cast_or_null<ObjCCategoryDecl>(SemaRef.CurContext))
8171 Class = Category->getClassInterface();
8172
8173 if (!Class)
8174 return;
8175 }
8176
8177 // Find all of the potential getters.
8178 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
8179 CodeCompleter->getCodeCompletionTUInfo(),
8181 Results.EnterNewScope();
8182
8183 VisitedSelectorSet Selectors;
8184 AddObjCMethods(Class, true, MK_OneArgSelector, {}, SemaRef.CurContext,
8185 Selectors,
8186 /*AllowSameLength=*/true, Results);
8187
8188 Results.ExitScope();
8190 Results.getCompletionContext(), Results.data(),
8191 Results.size());
8192}
8193
8195 bool IsParameter) {
8196 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
8197 CodeCompleter->getCodeCompletionTUInfo(),
8199 Results.EnterNewScope();
8200
8201 // Add context-sensitive, Objective-C parameter-passing keywords.
8202 bool AddedInOut = false;
8203 if ((DS.getObjCDeclQualifier() &
8205 Results.AddResult("in");
8206 Results.AddResult("inout");
8207 AddedInOut = true;
8208 }
8209 if ((DS.getObjCDeclQualifier() &
8211 Results.AddResult("out");
8212 if (!AddedInOut)
8213 Results.AddResult("inout");
8214 }
8215 if ((DS.getObjCDeclQualifier() &
8217 ObjCDeclSpec::DQ_Oneway)) == 0) {
8218 Results.AddResult("bycopy");
8219 Results.AddResult("byref");
8220 Results.AddResult("oneway");
8221 }
8223 Results.AddResult("nonnull");
8224 Results.AddResult("nullable");
8225 Results.AddResult("null_unspecified");
8226 }
8227
8228 // If we're completing the return type of an Objective-C method and the
8229 // identifier IBAction refers to a macro, provide a completion item for
8230 // an action, e.g.,
8231 // IBAction)<#selector#>:(id)sender
8232 if (DS.getObjCDeclQualifier() == 0 && !IsParameter &&
8233 SemaRef.PP.isMacroDefined("IBAction")) {
8234 CodeCompletionBuilder Builder(Results.getAllocator(),
8235 Results.getCodeCompletionTUInfo(),
8237 Builder.AddTypedTextChunk("IBAction");
8238 Builder.AddChunk(CodeCompletionString::CK_RightParen);
8239 Builder.AddPlaceholderChunk("selector");
8240 Builder.AddChunk(CodeCompletionString::CK_Colon);
8241 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
8242 Builder.AddTextChunk("id");
8243 Builder.AddChunk(CodeCompletionString::CK_RightParen);
8244 Builder.AddTextChunk("sender");
8245 Results.AddResult(CodeCompletionResult(Builder.TakeString()));
8246 }
8247
8248 // If we're completing the return type, provide 'instancetype'.
8249 if (!IsParameter) {
8250 Results.AddResult(CodeCompletionResult("instancetype"));
8251 }
8252
8253 // Add various builtin type names and specifiers.
8255 Results.ExitScope();
8256
8257 // Add the various type names
8258 Results.setFilter(&ResultBuilder::IsOrdinaryNonValueName);
8259 CodeCompletionDeclConsumer Consumer(Results, SemaRef.CurContext);
8260 SemaRef.LookupVisibleDecls(S, Sema::LookupOrdinaryName, Consumer,
8261 CodeCompleter->includeGlobals(),
8262 CodeCompleter->loadExternal());
8263
8264 if (CodeCompleter->includeMacros())
8265 AddMacroResults(SemaRef.PP, Results, CodeCompleter->loadExternal(), false);
8266
8268 Results.getCompletionContext(), Results.data(),
8269 Results.size());
8270}
8271
8272/// When we have an expression with type "id", we may assume
8273/// that it has some more-specific class type based on knowledge of
8274/// common uses of Objective-C. This routine returns that class type,
8275/// or NULL if no better result could be determined.
8277 auto *Msg = dyn_cast_or_null<ObjCMessageExpr>(E);
8278 if (!Msg)
8279 return nullptr;
8280
8281 Selector Sel = Msg->getSelector();
8282 if (Sel.isNull())
8283 return nullptr;
8284
8285 const IdentifierInfo *Id = Sel.getIdentifierInfoForSlot(0);
8286 if (!Id)
8287 return nullptr;
8288
8289 ObjCMethodDecl *Method = Msg->getMethodDecl();
8290 if (!Method)
8291 return nullptr;
8292
8293 // Determine the class that we're sending the message to.
8294 ObjCInterfaceDecl *IFace = nullptr;
8295 switch (Msg->getReceiverKind()) {
8297 if (const ObjCObjectType *ObjType =
8298 Msg->getClassReceiver()->getAs<ObjCObjectType>())
8299 IFace = ObjType->getInterface();
8300 break;
8301
8303 QualType T = Msg->getInstanceReceiver()->getType();
8304 if (const ObjCObjectPointerType *Ptr = T->getAs<ObjCObjectPointerType>())
8305 IFace = Ptr->getInterfaceDecl();
8306 break;
8307 }
8308
8311 break;
8312 }
8313
8314 if (!IFace)
8315 return nullptr;
8316
8317 ObjCInterfaceDecl *Super = IFace->getSuperClass();
8318 if (Method->isInstanceMethod())
8319 return llvm::StringSwitch<ObjCInterfaceDecl *>(Id->getName())
8320 .Case("retain", IFace)
8321 .Case("strong", IFace)
8322 .Case("autorelease", IFace)
8323 .Case("copy", IFace)
8324 .Case("copyWithZone", IFace)
8325 .Case("mutableCopy", IFace)
8326 .Case("mutableCopyWithZone", IFace)
8327 .Case("awakeFromCoder", IFace)
8328 .Case("replacementObjectFromCoder", IFace)
8329 .Case("class", IFace)
8330 .Case("classForCoder", IFace)
8331 .Case("superclass", Super)
8332 .Default(nullptr);
8333
8334 return llvm::StringSwitch<ObjCInterfaceDecl *>(Id->getName())
8335 .Case("new", IFace)
8336 .Case("alloc", IFace)
8337 .Case("allocWithZone", IFace)
8338 .Case("class", IFace)
8339 .Case("superclass", Super)
8340 .Default(nullptr);
8341}
8342
8343// Add a special completion for a message send to "super", which fills in the
8344// most likely case of forwarding all of our arguments to the superclass
8345// function.
8346///
8347/// \param S The semantic analysis object.
8348///
8349/// \param NeedSuperKeyword Whether we need to prefix this completion with
8350/// the "super" keyword. Otherwise, we just need to provide the arguments.
8351///
8352/// \param SelIdents The identifiers in the selector that have already been
8353/// provided as arguments for a send to "super".
8354///
8355/// \param Results The set of results to augment.
8356///
8357/// \returns the Objective-C method declaration that would be invoked by
8358/// this "super" completion. If NULL, no completion was added.
8359static ObjCMethodDecl *
8360AddSuperSendCompletion(Sema &S, bool NeedSuperKeyword,
8362 ResultBuilder &Results) {
8363 ObjCMethodDecl *CurMethod = S.getCurMethodDecl();
8364 if (!CurMethod)
8365 return nullptr;
8366
8367 ObjCInterfaceDecl *Class = CurMethod->getClassInterface();
8368 if (!Class)
8369 return nullptr;
8370
8371 // Try to find a superclass method with the same selector.
8372 ObjCMethodDecl *SuperMethod = nullptr;
8373 while ((Class = Class->getSuperClass()) && !SuperMethod) {
8374 // Check in the class
8375 SuperMethod = Class->getMethod(CurMethod->getSelector(),
8376 CurMethod->isInstanceMethod());
8377
8378 // Check in categories or class extensions.
8379 if (!SuperMethod) {
8380 for (const auto *Cat : Class->known_categories()) {
8381 if ((SuperMethod = Cat->getMethod(CurMethod->getSelector(),
8382 CurMethod->isInstanceMethod())))
8383 break;
8384 }
8385 }
8386 }
8387
8388 if (!SuperMethod)
8389 return nullptr;
8390
8391 // Check whether the superclass method has the same signature.
8392 if (CurMethod->param_size() != SuperMethod->param_size() ||
8393 CurMethod->isVariadic() != SuperMethod->isVariadic())
8394 return nullptr;
8395
8396 for (ObjCMethodDecl::param_iterator CurP = CurMethod->param_begin(),
8397 CurPEnd = CurMethod->param_end(),
8398 SuperP = SuperMethod->param_begin();
8399 CurP != CurPEnd; ++CurP, ++SuperP) {
8400 // Make sure the parameter types are compatible.
8401 if (!S.Context.hasSameUnqualifiedType((*CurP)->getType(),
8402 (*SuperP)->getType()))
8403 return nullptr;
8404
8405 // Make sure we have a parameter name to forward!
8406 if (!(*CurP)->getIdentifier())
8407 return nullptr;
8408 }
8409
8410 // We have a superclass method. Now, form the send-to-super completion.
8411 CodeCompletionBuilder Builder(Results.getAllocator(),
8412 Results.getCodeCompletionTUInfo());
8413
8414 // Give this completion a return type.
8416 Results.getCompletionContext().getBaseType(), Builder);
8417
8418 // If we need the "super" keyword, add it (plus some spacing).
8419 if (NeedSuperKeyword) {
8420 Builder.AddTypedTextChunk("super");
8422 }
8423
8424 Selector Sel = CurMethod->getSelector();
8425 if (Sel.isUnarySelector()) {
8426 if (NeedSuperKeyword)
8427 Builder.AddTextChunk(
8428 Builder.getAllocator().CopyString(Sel.getNameForSlot(0)));
8429 else
8430 Builder.AddTypedTextChunk(
8431 Builder.getAllocator().CopyString(Sel.getNameForSlot(0)));
8432 } else {
8433 ObjCMethodDecl::param_iterator CurP = CurMethod->param_begin();
8434 for (unsigned I = 0, N = Sel.getNumArgs(); I != N; ++I, ++CurP) {
8435 if (I > SelIdents.size())
8437
8438 if (I < SelIdents.size())
8439 Builder.AddInformativeChunk(
8440 Builder.getAllocator().CopyString(Sel.getNameForSlot(I) + ":"));
8441 else if (NeedSuperKeyword || I > SelIdents.size()) {
8442 Builder.AddTextChunk(
8443 Builder.getAllocator().CopyString(Sel.getNameForSlot(I) + ":"));
8444 Builder.AddPlaceholderChunk(Builder.getAllocator().CopyString(
8445 (*CurP)->getIdentifier()->getName()));
8446 } else {
8447 Builder.AddTypedTextChunk(
8448 Builder.getAllocator().CopyString(Sel.getNameForSlot(I) + ":"));
8449 Builder.AddPlaceholderChunk(Builder.getAllocator().CopyString(
8450 (*CurP)->getIdentifier()->getName()));
8451 }
8452 }
8453 }
8454
8455 Results.AddResult(CodeCompletionResult(Builder.TakeString(), SuperMethod,
8457 return SuperMethod;
8458}
8459
8462 ResultBuilder Results(
8463 SemaRef, CodeCompleter->getAllocator(),
8464 CodeCompleter->getCodeCompletionTUInfo(),
8467 ? &ResultBuilder::IsObjCMessageReceiverOrLambdaCapture
8468 : &ResultBuilder::IsObjCMessageReceiver);
8469
8470 CodeCompletionDeclConsumer Consumer(Results, SemaRef.CurContext);
8471 Results.EnterNewScope();
8472 SemaRef.LookupVisibleDecls(S, Sema::LookupOrdinaryName, Consumer,
8473 CodeCompleter->includeGlobals(),
8474 CodeCompleter->loadExternal());
8475
8476 // If we are in an Objective-C method inside a class that has a superclass,
8477 // add "super" as an option.
8478 if (ObjCMethodDecl *Method = SemaRef.getCurMethodDecl())
8479 if (ObjCInterfaceDecl *Iface = Method->getClassInterface())
8480 if (Iface->getSuperClass()) {
8481 Results.AddResult(Result("super"));
8482
8483 AddSuperSendCompletion(SemaRef, /*NeedSuperKeyword=*/true, {}, Results);
8484 }
8485
8487 addThisCompletion(SemaRef, Results);
8488
8489 Results.ExitScope();
8490
8491 if (CodeCompleter->includeMacros())
8492 AddMacroResults(SemaRef.PP, Results, CodeCompleter->loadExternal(), false);
8494 Results.getCompletionContext(), Results.data(),
8495 Results.size());
8496}
8497
8499 Scope *S, SourceLocation SuperLoc,
8500 ArrayRef<const IdentifierInfo *> SelIdents, bool AtArgumentExpression) {
8501 ObjCInterfaceDecl *CDecl = nullptr;
8502 if (ObjCMethodDecl *CurMethod = SemaRef.getCurMethodDecl()) {
8503 // Figure out which interface we're in.
8504 CDecl = CurMethod->getClassInterface();
8505 if (!CDecl)
8506 return;
8507
8508 // Find the superclass of this class.
8509 CDecl = CDecl->getSuperClass();
8510 if (!CDecl)
8511 return;
8512
8513 if (CurMethod->isInstanceMethod()) {
8514 // We are inside an instance method, which means that the message
8515 // send [super ...] is actually calling an instance method on the
8516 // current object.
8517 return CodeCompleteObjCInstanceMessage(S, nullptr, SelIdents,
8518 AtArgumentExpression, CDecl);
8519 }
8520
8521 // Fall through to send to the superclass in CDecl.
8522 } else {
8523 // "super" may be the name of a type or variable. Figure out which
8524 // it is.
8525 const IdentifierInfo *Super = SemaRef.getSuperIdentifier();
8526 NamedDecl *ND =
8527 SemaRef.LookupSingleName(S, Super, SuperLoc, Sema::LookupOrdinaryName);
8528 if ((CDecl = dyn_cast_or_null<ObjCInterfaceDecl>(ND))) {
8529 // "super" names an interface. Use it.
8530 } else if (TypeDecl *TD = dyn_cast_or_null<TypeDecl>(ND)) {
8531 if (const ObjCObjectType *Iface =
8532 getASTContext().getTypeDeclType(TD)->getAs<ObjCObjectType>())
8533 CDecl = Iface->getInterface();
8534 } else if (ND && isa<UnresolvedUsingTypenameDecl>(ND)) {
8535 // "super" names an unresolved type; we can't be more specific.
8536 } else {
8537 // Assume that "super" names some kind of value and parse that way.
8538 CXXScopeSpec SS;
8539 SourceLocation TemplateKWLoc;
8540 UnqualifiedId id;
8541 id.setIdentifier(Super, SuperLoc);
8542 ExprResult SuperExpr =
8543 SemaRef.ActOnIdExpression(S, SS, TemplateKWLoc, id,
8544 /*HasTrailingLParen=*/false,
8545 /*IsAddressOfOperand=*/false);
8546 return CodeCompleteObjCInstanceMessage(S, (Expr *)SuperExpr.get(),
8547 SelIdents, AtArgumentExpression);
8548 }
8549
8550 // Fall through
8551 }
8552
8553 ParsedType Receiver;
8554 if (CDecl)
8555 Receiver = ParsedType::make(getASTContext().getObjCInterfaceType(CDecl));
8556 return CodeCompleteObjCClassMessage(S, Receiver, SelIdents,
8557 AtArgumentExpression,
8558 /*IsSuper=*/true);
8559}
8560
8561/// Given a set of code-completion results for the argument of a message
8562/// send, determine the preferred type (if any) for that argument expression.
8564 unsigned NumSelIdents) {
8566 ASTContext &Context = Results.getSema().Context;
8567
8568 QualType PreferredType;
8569 unsigned BestPriority = CCP_Unlikely * 2;
8570 Result *ResultsData = Results.data();
8571 for (unsigned I = 0, N = Results.size(); I != N; ++I) {
8572 Result &R = ResultsData[I];
8573 if (R.Kind == Result::RK_Declaration &&
8574 isa<ObjCMethodDecl>(R.Declaration)) {
8575 if (R.Priority <= BestPriority) {
8576 const ObjCMethodDecl *Method = cast<ObjCMethodDecl>(R.Declaration);
8577 if (NumSelIdents <= Method->param_size()) {
8578 QualType MyPreferredType =
8579 Method->parameters()[NumSelIdents - 1]->getType();
8580 if (R.Priority < BestPriority || PreferredType.isNull()) {
8581 BestPriority = R.Priority;
8582 PreferredType = MyPreferredType;
8583 } else if (!Context.hasSameUnqualifiedType(PreferredType,
8584 MyPreferredType)) {
8585 PreferredType = QualType();
8586 }
8587 }
8588 }
8589 }
8590 }
8591
8592 return PreferredType;
8593}
8594
8595static void
8598 bool AtArgumentExpression, bool IsSuper,
8599 ResultBuilder &Results) {
8601 ObjCInterfaceDecl *CDecl = nullptr;
8602
8603 // If the given name refers to an interface type, retrieve the
8604 // corresponding declaration.
8605 if (Receiver) {
8606 QualType T = SemaRef.GetTypeFromParser(Receiver, nullptr);
8607 if (!T.isNull())
8608 if (const ObjCObjectType *Interface = T->getAs<ObjCObjectType>())
8609 CDecl = Interface->getInterface();
8610 }
8611
8612 // Add all of the factory methods in this Objective-C class, its protocols,
8613 // superclasses, categories, implementation, etc.
8614 Results.EnterNewScope();
8615
8616 // If this is a send-to-super, try to add the special "super" send
8617 // completion.
8618 if (IsSuper) {
8619 if (ObjCMethodDecl *SuperMethod =
8620 AddSuperSendCompletion(SemaRef, false, SelIdents, Results))
8621 Results.Ignore(SuperMethod);
8622 }
8623
8624 // If we're inside an Objective-C method definition, prefer its selector to
8625 // others.
8626 if (ObjCMethodDecl *CurMethod = SemaRef.getCurMethodDecl())
8627 Results.setPreferredSelector(CurMethod->getSelector());
8628
8629 VisitedSelectorSet Selectors;
8630 if (CDecl)
8631 AddObjCMethods(CDecl, false, MK_Any, SelIdents, SemaRef.CurContext,
8632 Selectors, AtArgumentExpression, Results);
8633 else {
8634 // We're messaging "id" as a type; provide all class/factory methods.
8635
8636 // If we have an external source, load the entire class method
8637 // pool from the AST file.
8638 if (SemaRef.getExternalSource()) {
8639 for (uint32_t I = 0,
8641 I != N; ++I) {
8643 if (Sel.isNull() || SemaRef.ObjC().MethodPool.count(Sel))
8644 continue;
8645
8646 SemaRef.ObjC().ReadMethodPool(Sel);
8647 }
8648 }
8649
8650 for (SemaObjC::GlobalMethodPool::iterator
8651 M = SemaRef.ObjC().MethodPool.begin(),
8652 MEnd = SemaRef.ObjC().MethodPool.end();
8653 M != MEnd; ++M) {
8654 for (ObjCMethodList *MethList = &M->second.second;
8655 MethList && MethList->getMethod(); MethList = MethList->getNext()) {
8656 if (!isAcceptableObjCMethod(MethList->getMethod(), MK_Any, SelIdents))
8657 continue;
8658
8659 Result R(MethList->getMethod(),
8660 Results.getBasePriority(MethList->getMethod()),
8661 /*Qualifier=*/std::nullopt);
8662 R.StartParameter = SelIdents.size();
8663 R.AllParametersAreInformative = false;
8664 Results.MaybeAddResult(R, SemaRef.CurContext);
8665 }
8666 }
8667 }
8668
8669 Results.ExitScope();
8670}
8671
8673 Scope *S, ParsedType Receiver, ArrayRef<const IdentifierInfo *> SelIdents,
8674 bool AtArgumentExpression, bool IsSuper) {
8675
8676 QualType T = SemaRef.GetTypeFromParser(Receiver);
8677
8678 ResultBuilder Results(
8679 SemaRef, CodeCompleter->getAllocator(),
8680 CodeCompleter->getCodeCompletionTUInfo(),
8682 SelIdents));
8683
8684 AddClassMessageCompletions(SemaRef, S, Receiver, SelIdents,
8685 AtArgumentExpression, IsSuper, Results);
8686
8687 // If we're actually at the argument expression (rather than prior to the
8688 // selector), we're actually performing code completion for an expression.
8689 // Determine whether we have a single, best method. If so, we can
8690 // code-complete the expression using the corresponding parameter type as
8691 // our preferred type, improving completion results.
8692 if (AtArgumentExpression) {
8693 QualType PreferredType =
8694 getPreferredArgumentTypeForMessageSend(Results, SelIdents.size());
8695 if (PreferredType.isNull())
8697 else
8698 CodeCompleteExpression(S, PreferredType);
8699 return;
8700 }
8701
8703 Results.getCompletionContext(), Results.data(),
8704 Results.size());
8705}
8706
8708 Scope *S, Expr *RecExpr, ArrayRef<const IdentifierInfo *> SelIdents,
8709 bool AtArgumentExpression, ObjCInterfaceDecl *Super) {
8711 ASTContext &Context = getASTContext();
8712
8713 // If necessary, apply function/array conversion to the receiver.
8714 // C99 6.7.5.3p[7,8].
8715 if (RecExpr) {
8716 // If the receiver expression has no type (e.g., a parenthesized C-style
8717 // cast that hasn't been resolved), bail out to avoid dereferencing a null
8718 // type.
8719 if (RecExpr->getType().isNull())
8720 return;
8721 ExprResult Conv = SemaRef.DefaultFunctionArrayLvalueConversion(RecExpr);
8722 if (Conv.isInvalid()) // conversion failed. bail.
8723 return;
8724 RecExpr = Conv.get();
8725 }
8726 QualType ReceiverType = RecExpr
8727 ? RecExpr->getType()
8728 : Super ? Context.getObjCObjectPointerType(
8729 Context.getObjCInterfaceType(Super))
8730 : Context.getObjCIdType();
8731
8732 // If we're messaging an expression with type "id" or "Class", check
8733 // whether we know something special about the receiver that allows
8734 // us to assume a more-specific receiver type.
8735 if (ReceiverType->isObjCIdType() || ReceiverType->isObjCClassType()) {
8736 if (ObjCInterfaceDecl *IFace = GetAssumedMessageSendExprType(RecExpr)) {
8737 if (ReceiverType->isObjCClassType())
8739 S, ParsedType::make(Context.getObjCInterfaceType(IFace)), SelIdents,
8740 AtArgumentExpression, Super);
8741
8742 ReceiverType =
8743 Context.getObjCObjectPointerType(Context.getObjCInterfaceType(IFace));
8744 }
8745 } else if (RecExpr && getLangOpts().CPlusPlus) {
8746 ExprResult Conv = SemaRef.PerformContextuallyConvertToObjCPointer(RecExpr);
8747 if (Conv.isUsable()) {
8748 RecExpr = Conv.get();
8749 ReceiverType = RecExpr->getType();
8750 }
8751 }
8752
8753 // Build the set of methods we can see.
8754 ResultBuilder Results(
8755 SemaRef, CodeCompleter->getAllocator(),
8756 CodeCompleter->getCodeCompletionTUInfo(),
8758 ReceiverType, SelIdents));
8759
8760 Results.EnterNewScope();
8761
8762 // If this is a send-to-super, try to add the special "super" send
8763 // completion.
8764 if (Super) {
8765 if (ObjCMethodDecl *SuperMethod =
8766 AddSuperSendCompletion(SemaRef, false, SelIdents, Results))
8767 Results.Ignore(SuperMethod);
8768 }
8769
8770 // If we're inside an Objective-C method definition, prefer its selector to
8771 // others.
8772 if (ObjCMethodDecl *CurMethod = SemaRef.getCurMethodDecl())
8773 Results.setPreferredSelector(CurMethod->getSelector());
8774
8775 // Keep track of the selectors we've already added.
8776 VisitedSelectorSet Selectors;
8777
8778 // Handle messages to Class. This really isn't a message to an instance
8779 // method, so we treat it the same way we would treat a message send to a
8780 // class method.
8781 if (ReceiverType->isObjCClassType() ||
8782 ReceiverType->isObjCQualifiedClassType()) {
8783 if (ObjCMethodDecl *CurMethod = SemaRef.getCurMethodDecl()) {
8784 if (ObjCInterfaceDecl *ClassDecl = CurMethod->getClassInterface())
8785 AddObjCMethods(ClassDecl, false, MK_Any, SelIdents, SemaRef.CurContext,
8786 Selectors, AtArgumentExpression, Results);
8787 }
8788 }
8789 // Handle messages to a qualified ID ("id<foo>").
8790 else if (const ObjCObjectPointerType *QualID =
8791 ReceiverType->getAsObjCQualifiedIdType()) {
8792 // Search protocols for instance methods.
8793 for (auto *I : QualID->quals())
8794 AddObjCMethods(I, true, MK_Any, SelIdents, SemaRef.CurContext, Selectors,
8795 AtArgumentExpression, Results);
8796 }
8797 // Handle messages to a pointer to interface type.
8798 else if (const ObjCObjectPointerType *IFacePtr =
8799 ReceiverType->getAsObjCInterfacePointerType()) {
8800 // Search the class, its superclasses, etc., for instance methods.
8801 AddObjCMethods(IFacePtr->getInterfaceDecl(), true, MK_Any, SelIdents,
8802 SemaRef.CurContext, Selectors, AtArgumentExpression,
8803 Results);
8804
8805 // Search protocols for instance methods.
8806 for (auto *I : IFacePtr->quals())
8807 AddObjCMethods(I, true, MK_Any, SelIdents, SemaRef.CurContext, Selectors,
8808 AtArgumentExpression, Results);
8809 }
8810 // Handle messages to "id".
8811 else if (ReceiverType->isObjCIdType()) {
8812 // We're messaging "id", so provide all instance methods we know
8813 // about as code-completion results.
8814
8815 // If we have an external source, load the entire class method
8816 // pool from the AST file.
8817 if (SemaRef.ExternalSource) {
8818 for (uint32_t I = 0,
8819 N = SemaRef.ExternalSource->GetNumExternalSelectors();
8820 I != N; ++I) {
8821 Selector Sel = SemaRef.ExternalSource->GetExternalSelector(I);
8822 if (Sel.isNull() || SemaRef.ObjC().MethodPool.count(Sel))
8823 continue;
8824
8825 SemaRef.ObjC().ReadMethodPool(Sel);
8826 }
8827 }
8828
8829 for (SemaObjC::GlobalMethodPool::iterator
8830 M = SemaRef.ObjC().MethodPool.begin(),
8831 MEnd = SemaRef.ObjC().MethodPool.end();
8832 M != MEnd; ++M) {
8833 for (ObjCMethodList *MethList = &M->second.first;
8834 MethList && MethList->getMethod(); MethList = MethList->getNext()) {
8835 if (!isAcceptableObjCMethod(MethList->getMethod(), MK_Any, SelIdents))
8836 continue;
8837
8838 if (!Selectors.insert(MethList->getMethod()->getSelector()).second)
8839 continue;
8840
8841 Result R(MethList->getMethod(),
8842 Results.getBasePriority(MethList->getMethod()),
8843 /*Qualifier=*/std::nullopt);
8844 R.StartParameter = SelIdents.size();
8845 R.AllParametersAreInformative = false;
8846 Results.MaybeAddResult(R, SemaRef.CurContext);
8847 }
8848 }
8849 }
8850 Results.ExitScope();
8851
8852 // If we're actually at the argument expression (rather than prior to the
8853 // selector), we're actually performing code completion for an expression.
8854 // Determine whether we have a single, best method. If so, we can
8855 // code-complete the expression using the corresponding parameter type as
8856 // our preferred type, improving completion results.
8857 if (AtArgumentExpression) {
8858 QualType PreferredType =
8859 getPreferredArgumentTypeForMessageSend(Results, SelIdents.size());
8860 if (PreferredType.isNull())
8862 else
8863 CodeCompleteExpression(S, PreferredType);
8864 return;
8865 }
8866
8868 Results.getCompletionContext(), Results.data(),
8869 Results.size());
8870}
8871
8873 Scope *S, DeclGroupPtrTy IterationVar) {
8875 Data.ObjCCollection = true;
8876
8877 if (IterationVar.getAsOpaquePtr()) {
8878 DeclGroupRef DG = IterationVar.get();
8879 for (DeclGroupRef::iterator I = DG.begin(), End = DG.end(); I != End; ++I) {
8880 if (*I)
8881 Data.IgnoreDecls.push_back(*I);
8882 }
8883 }
8884
8886}
8887
8890 // If we have an external source, load the entire class method
8891 // pool from the AST file.
8892 if (SemaRef.ExternalSource) {
8893 for (uint32_t I = 0, N = SemaRef.ExternalSource->GetNumExternalSelectors();
8894 I != N; ++I) {
8895 Selector Sel = SemaRef.ExternalSource->GetExternalSelector(I);
8896 if (Sel.isNull() || SemaRef.ObjC().MethodPool.count(Sel))
8897 continue;
8898
8899 SemaRef.ObjC().ReadMethodPool(Sel);
8900 }
8901 }
8902
8903 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
8904 CodeCompleter->getCodeCompletionTUInfo(),
8906 Results.EnterNewScope();
8907 for (SemaObjC::GlobalMethodPool::iterator
8908 M = SemaRef.ObjC().MethodPool.begin(),
8909 MEnd = SemaRef.ObjC().MethodPool.end();
8910 M != MEnd; ++M) {
8911
8912 Selector Sel = M->first;
8913 if (!isAcceptableObjCSelector(Sel, MK_Any, SelIdents))
8914 continue;
8915
8916 CodeCompletionBuilder Builder(Results.getAllocator(),
8917 Results.getCodeCompletionTUInfo());
8918 if (Sel.isUnarySelector()) {
8919 Builder.AddTypedTextChunk(
8920 Builder.getAllocator().CopyString(Sel.getNameForSlot(0)));
8921 Results.AddResult(Builder.TakeString());
8922 continue;
8923 }
8924
8925 std::string Accumulator;
8926 for (unsigned I = 0, N = Sel.getNumArgs(); I != N; ++I) {
8927 if (I == SelIdents.size()) {
8928 if (!Accumulator.empty()) {
8929 Builder.AddInformativeChunk(
8930 Builder.getAllocator().CopyString(Accumulator));
8931 Accumulator.clear();
8932 }
8933 }
8934
8935 Accumulator += Sel.getNameForSlot(I);
8936 Accumulator += ':';
8937 }
8938 Builder.AddTypedTextChunk(Builder.getAllocator().CopyString(Accumulator));
8939 Results.AddResult(Builder.TakeString());
8940 }
8941 Results.ExitScope();
8942
8944 Results.getCompletionContext(), Results.data(),
8945 Results.size());
8946}
8947
8948/// Add all of the protocol declarations that we find in the given
8949/// (translation unit) context.
8950static void AddProtocolResults(DeclContext *Ctx, DeclContext *CurContext,
8951 bool OnlyForwardDeclarations,
8952 ResultBuilder &Results) {
8954
8955 for (const auto *D : Ctx->decls()) {
8956 // Record any protocols we find.
8957 if (const auto *Proto = dyn_cast<ObjCProtocolDecl>(D))
8958 if (!OnlyForwardDeclarations || !Proto->hasDefinition())
8959 Results.AddResult(Result(Proto, Results.getBasePriority(Proto),
8960 /*Qualifier=*/std::nullopt),
8961 CurContext, nullptr, false);
8962 }
8963}
8964
8966 ArrayRef<IdentifierLoc> Protocols) {
8967 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
8968 CodeCompleter->getCodeCompletionTUInfo(),
8970
8971 if (CodeCompleter->includeGlobals()) {
8972 Results.EnterNewScope();
8973
8974 // Tell the result set to ignore all of the protocols we have
8975 // already seen.
8976 // FIXME: This doesn't work when caching code-completion results.
8977 for (const IdentifierLoc &Pair : Protocols)
8978 if (ObjCProtocolDecl *Protocol = SemaRef.ObjC().LookupProtocol(
8979 Pair.getIdentifierInfo(), Pair.getLoc()))
8980 Results.Ignore(Protocol);
8981
8982 // Add all protocols.
8983 AddProtocolResults(getASTContext().getTranslationUnitDecl(),
8984 SemaRef.CurContext, false, Results);
8985
8986 Results.ExitScope();
8987 }
8988
8990 Results.getCompletionContext(), Results.data(),
8991 Results.size());
8992}
8993
8995 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
8996 CodeCompleter->getCodeCompletionTUInfo(),
8998
8999 if (CodeCompleter->includeGlobals()) {
9000 Results.EnterNewScope();
9001
9002 // Add all protocols.
9003 AddProtocolResults(getASTContext().getTranslationUnitDecl(),
9004 SemaRef.CurContext, true, Results);
9005
9006 Results.ExitScope();
9007 }
9008
9010 Results.getCompletionContext(), Results.data(),
9011 Results.size());
9012}
9013
9014/// Add all of the Objective-C interface declarations that we find in
9015/// the given (translation unit) context.
9016static void AddInterfaceResults(DeclContext *Ctx, DeclContext *CurContext,
9017 bool OnlyForwardDeclarations,
9018 bool OnlyUnimplemented,
9019 ResultBuilder &Results) {
9021
9022 for (const auto *D : Ctx->decls()) {
9023 // Record any interfaces we find.
9024 if (const auto *Class = dyn_cast<ObjCInterfaceDecl>(D))
9025 if ((!OnlyForwardDeclarations || !Class->hasDefinition()) &&
9026 (!OnlyUnimplemented || !Class->getImplementation()))
9027 Results.AddResult(Result(Class, Results.getBasePriority(Class),
9028 /*Qualifier=*/std::nullopt),
9029 CurContext, nullptr, false);
9030 }
9031}
9032
9034 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
9035 CodeCompleter->getCodeCompletionTUInfo(),
9037 Results.EnterNewScope();
9038
9039 if (CodeCompleter->includeGlobals()) {
9040 // Add all classes.
9041 AddInterfaceResults(getASTContext().getTranslationUnitDecl(),
9042 SemaRef.CurContext, false, false, Results);
9043 }
9044
9045 Results.ExitScope();
9046
9048 Results.getCompletionContext(), Results.data(),
9049 Results.size());
9050}
9051
9053 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
9054 CodeCompleter->getCodeCompletionTUInfo(),
9056 Results.EnterNewScope();
9057
9058 if (CodeCompleter->includeGlobals()) {
9059 // Add all classes.
9060 AddInterfaceResults(getASTContext().getTranslationUnitDecl(),
9061 SemaRef.CurContext, false, false, Results);
9062 }
9063
9064 Results.ExitScope();
9065
9067 Results.getCompletionContext(), Results.data(),
9068 Results.size());
9069}
9070
9072 Scope *S, IdentifierInfo *ClassName, SourceLocation ClassNameLoc) {
9073 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
9074 CodeCompleter->getCodeCompletionTUInfo(),
9076 Results.EnterNewScope();
9077
9078 // Make sure that we ignore the class we're currently defining.
9079 NamedDecl *CurClass = SemaRef.LookupSingleName(
9080 SemaRef.TUScope, ClassName, ClassNameLoc, Sema::LookupOrdinaryName);
9081 if (CurClass && isa<ObjCInterfaceDecl>(CurClass))
9082 Results.Ignore(CurClass);
9083
9084 if (CodeCompleter->includeGlobals()) {
9085 // Add all classes.
9086 AddInterfaceResults(getASTContext().getTranslationUnitDecl(),
9087 SemaRef.CurContext, false, false, Results);
9088 }
9089
9090 Results.ExitScope();
9091
9093 Results.getCompletionContext(), Results.data(),
9094 Results.size());
9095}
9096
9098 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
9099 CodeCompleter->getCodeCompletionTUInfo(),
9101 Results.EnterNewScope();
9102
9103 if (CodeCompleter->includeGlobals()) {
9104 // Add all unimplemented classes.
9105 AddInterfaceResults(getASTContext().getTranslationUnitDecl(),
9106 SemaRef.CurContext, false, true, Results);
9107 }
9108
9109 Results.ExitScope();
9110
9112 Results.getCompletionContext(), Results.data(),
9113 Results.size());
9114}
9115
9117 Scope *S, IdentifierInfo *ClassName, SourceLocation ClassNameLoc) {
9119
9120 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
9121 CodeCompleter->getCodeCompletionTUInfo(),
9123
9124 // Ignore any categories we find that have already been implemented by this
9125 // interface.
9127 NamedDecl *CurClass = SemaRef.LookupSingleName(
9128 SemaRef.TUScope, ClassName, ClassNameLoc, Sema::LookupOrdinaryName);
9130 dyn_cast_or_null<ObjCInterfaceDecl>(CurClass)) {
9131 for (const auto *Cat : Class->visible_categories())
9132 CategoryNames.insert(Cat->getIdentifier());
9133 }
9134
9135 // Add all of the categories we know about.
9136 Results.EnterNewScope();
9137 TranslationUnitDecl *TU = getASTContext().getTranslationUnitDecl();
9138 for (const auto *D : TU->decls())
9139 if (const auto *Category = dyn_cast<ObjCCategoryDecl>(D))
9140 if (CategoryNames.insert(Category->getIdentifier()).second)
9141 Results.AddResult(Result(Category, Results.getBasePriority(Category),
9142 /*Qualifier=*/std::nullopt),
9143 SemaRef.CurContext, nullptr, false);
9144 Results.ExitScope();
9145
9147 Results.getCompletionContext(), Results.data(),
9148 Results.size());
9149}
9150
9152 Scope *S, IdentifierInfo *ClassName, SourceLocation ClassNameLoc) {
9154
9155 // Find the corresponding interface. If we couldn't find the interface, the
9156 // program itself is ill-formed. However, we'll try to be helpful still by
9157 // providing the list of all of the categories we know about.
9158 NamedDecl *CurClass = SemaRef.LookupSingleName(
9159 SemaRef.TUScope, ClassName, ClassNameLoc, Sema::LookupOrdinaryName);
9160 ObjCInterfaceDecl *Class = dyn_cast_or_null<ObjCInterfaceDecl>(CurClass);
9161 if (!Class)
9162 return CodeCompleteObjCInterfaceCategory(S, ClassName, ClassNameLoc);
9163
9164 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
9165 CodeCompleter->getCodeCompletionTUInfo(),
9167
9168 // Add all of the categories that have corresponding interface
9169 // declarations in this class and any of its superclasses, except for
9170 // already-implemented categories in the class itself.
9172 Results.EnterNewScope();
9173 bool IgnoreImplemented = true;
9174 while (Class) {
9175 for (const auto *Cat : Class->visible_categories()) {
9176 if ((!IgnoreImplemented || !Cat->getImplementation()) &&
9177 CategoryNames.insert(Cat->getIdentifier()).second)
9178 Results.AddResult(Result(Cat, Results.getBasePriority(Cat),
9179 /*Qualifier=*/std::nullopt),
9180 SemaRef.CurContext, nullptr, false);
9181 }
9182
9183 Class = Class->getSuperClass();
9184 IgnoreImplemented = false;
9185 }
9186 Results.ExitScope();
9187
9189 Results.getCompletionContext(), Results.data(),
9190 Results.size());
9191}
9192
9195 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
9196 CodeCompleter->getCodeCompletionTUInfo(), CCContext);
9197
9198 // Figure out where this @synthesize lives.
9199 ObjCContainerDecl *Container =
9200 dyn_cast_or_null<ObjCContainerDecl>(SemaRef.CurContext);
9201 if (!Container || (!isa<ObjCImplementationDecl>(Container) &&
9202 !isa<ObjCCategoryImplDecl>(Container)))
9203 return;
9204
9205 // Ignore any properties that have already been implemented.
9206 Container = getContainerDef(Container);
9207 for (const auto *D : Container->decls())
9208 if (const auto *PropertyImpl = dyn_cast<ObjCPropertyImplDecl>(D))
9209 Results.Ignore(PropertyImpl->getPropertyDecl());
9210
9211 // Add any properties that we find.
9212 AddedPropertiesSet AddedProperties;
9213 Results.EnterNewScope();
9214 if (ObjCImplementationDecl *ClassImpl =
9215 dyn_cast<ObjCImplementationDecl>(Container))
9216 AddObjCProperties(CCContext, ClassImpl->getClassInterface(), false,
9217 /*AllowNullaryMethods=*/false, SemaRef.CurContext,
9218 AddedProperties, Results);
9219 else
9220 AddObjCProperties(CCContext,
9221 cast<ObjCCategoryImplDecl>(Container)->getCategoryDecl(),
9222 false, /*AllowNullaryMethods=*/false, SemaRef.CurContext,
9223 AddedProperties, Results);
9224 Results.ExitScope();
9225
9227 Results.getCompletionContext(), Results.data(),
9228 Results.size());
9229}
9230
9232 Scope *S, IdentifierInfo *PropertyName) {
9234 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
9235 CodeCompleter->getCodeCompletionTUInfo(),
9237
9238 // Figure out where this @synthesize lives.
9239 ObjCContainerDecl *Container =
9240 dyn_cast_or_null<ObjCContainerDecl>(SemaRef.CurContext);
9241 if (!Container || (!isa<ObjCImplementationDecl>(Container) &&
9242 !isa<ObjCCategoryImplDecl>(Container)))
9243 return;
9244
9245 // Figure out which interface we're looking into.
9246 ObjCInterfaceDecl *Class = nullptr;
9247 if (ObjCImplementationDecl *ClassImpl =
9248 dyn_cast<ObjCImplementationDecl>(Container))
9249 Class = ClassImpl->getClassInterface();
9250 else
9252 ->getCategoryDecl()
9253 ->getClassInterface();
9254
9255 // Determine the type of the property we're synthesizing.
9256 QualType PropertyType = getASTContext().getObjCIdType();
9257 if (Class) {
9258 if (ObjCPropertyDecl *Property = Class->FindPropertyDeclaration(
9260 PropertyType =
9261 Property->getType().getNonReferenceType().getUnqualifiedType();
9262
9263 // Give preference to ivars
9264 Results.setPreferredType(PropertyType);
9265 }
9266 }
9267
9268 // Add all of the instance variables in this class and its superclasses.
9269 Results.EnterNewScope();
9270 bool SawSimilarlyNamedIvar = false;
9271 std::string NameWithPrefix;
9272 NameWithPrefix += '_';
9273 NameWithPrefix += PropertyName->getName();
9274 std::string NameWithSuffix = PropertyName->getName().str();
9275 NameWithSuffix += '_';
9276 for (; Class; Class = Class->getSuperClass()) {
9277 for (ObjCIvarDecl *Ivar = Class->all_declared_ivar_begin(); Ivar;
9278 Ivar = Ivar->getNextIvar()) {
9279 Results.AddResult(Result(Ivar, Results.getBasePriority(Ivar),
9280 /*Qualifier=*/std::nullopt),
9281 SemaRef.CurContext, nullptr, false);
9282
9283 // Determine whether we've seen an ivar with a name similar to the
9284 // property.
9285 if ((PropertyName == Ivar->getIdentifier() ||
9286 NameWithPrefix == Ivar->getName() ||
9287 NameWithSuffix == Ivar->getName())) {
9288 SawSimilarlyNamedIvar = true;
9289
9290 // Reduce the priority of this result by one, to give it a slight
9291 // advantage over other results whose names don't match so closely.
9292 if (Results.size() &&
9293 Results.data()[Results.size() - 1].Kind ==
9295 Results.data()[Results.size() - 1].Declaration == Ivar)
9296 Results.data()[Results.size() - 1].Priority--;
9297 }
9298 }
9299 }
9300
9301 if (!SawSimilarlyNamedIvar) {
9302 // Create ivar result _propName, that the user can use to synthesize
9303 // an ivar of the appropriate type.
9304 unsigned Priority = CCP_MemberDeclaration + 1;
9306 CodeCompletionAllocator &Allocator = Results.getAllocator();
9307 CodeCompletionBuilder Builder(Allocator, Results.getCodeCompletionTUInfo(),
9308 Priority, CXAvailability_Available);
9309
9311 Builder.AddResultTypeChunk(GetCompletionTypeString(
9312 PropertyType, getASTContext(), Policy, Allocator));
9313 Builder.AddTypedTextChunk(Allocator.CopyString(NameWithPrefix));
9314 Results.AddResult(
9315 Result(Builder.TakeString(), Priority, CXCursor_ObjCIvarDecl));
9316 }
9317
9318 Results.ExitScope();
9319
9321 Results.getCompletionContext(), Results.data(),
9322 Results.size());
9323}
9324
9325// Mapping from selectors to the methods that implement that selector, along
9326// with the "in original class" flag.
9327typedef llvm::DenseMap<Selector,
9328 llvm::PointerIntPair<ObjCMethodDecl *, 1, bool>>
9330
9331/// Find all of the methods that reside in the given container
9332/// (and its superclasses, protocols, etc.) that meet the given
9333/// criteria. Insert those methods into the map of known methods,
9334/// indexed by selector so they can be easily found.
9336 ObjCContainerDecl *Container,
9337 std::optional<bool> WantInstanceMethods,
9338 QualType ReturnType,
9339 KnownMethodsMap &KnownMethods,
9340 bool InOriginalClass = true) {
9341 if (ObjCInterfaceDecl *IFace = dyn_cast<ObjCInterfaceDecl>(Container)) {
9342 // Make sure we have a definition; that's what we'll walk.
9343 if (!IFace->hasDefinition())
9344 return;
9345
9346 IFace = IFace->getDefinition();
9347 Container = IFace;
9348
9349 const ObjCList<ObjCProtocolDecl> &Protocols =
9350 IFace->getReferencedProtocols();
9351 for (ObjCList<ObjCProtocolDecl>::iterator I = Protocols.begin(),
9352 E = Protocols.end();
9353 I != E; ++I)
9354 FindImplementableMethods(Context, *I, WantInstanceMethods, ReturnType,
9355 KnownMethods, InOriginalClass);
9356
9357 // Add methods from any class extensions and categories.
9358 for (auto *Cat : IFace->visible_categories()) {
9359 FindImplementableMethods(Context, Cat, WantInstanceMethods, ReturnType,
9360 KnownMethods, false);
9361 }
9362
9363 // Visit the superclass.
9364 if (IFace->getSuperClass())
9365 FindImplementableMethods(Context, IFace->getSuperClass(),
9366 WantInstanceMethods, ReturnType, KnownMethods,
9367 false);
9368 }
9369
9370 if (ObjCCategoryDecl *Category = dyn_cast<ObjCCategoryDecl>(Container)) {
9371 // Recurse into protocols.
9372 const ObjCList<ObjCProtocolDecl> &Protocols =
9373 Category->getReferencedProtocols();
9374 for (ObjCList<ObjCProtocolDecl>::iterator I = Protocols.begin(),
9375 E = Protocols.end();
9376 I != E; ++I)
9377 FindImplementableMethods(Context, *I, WantInstanceMethods, ReturnType,
9378 KnownMethods, InOriginalClass);
9379
9380 // If this category is the original class, jump to the interface.
9381 if (InOriginalClass && Category->getClassInterface())
9382 FindImplementableMethods(Context, Category->getClassInterface(),
9383 WantInstanceMethods, ReturnType, KnownMethods,
9384 false);
9385 }
9386
9387 if (ObjCProtocolDecl *Protocol = dyn_cast<ObjCProtocolDecl>(Container)) {
9388 // Make sure we have a definition; that's what we'll walk.
9389 if (!Protocol->hasDefinition())
9390 return;
9391 Protocol = Protocol->getDefinition();
9392 Container = Protocol;
9393
9394 // Recurse into protocols.
9395 const ObjCList<ObjCProtocolDecl> &Protocols =
9396 Protocol->getReferencedProtocols();
9397 for (ObjCList<ObjCProtocolDecl>::iterator I = Protocols.begin(),
9398 E = Protocols.end();
9399 I != E; ++I)
9400 FindImplementableMethods(Context, *I, WantInstanceMethods, ReturnType,
9401 KnownMethods, false);
9402 }
9403
9404 // Add methods in this container. This operation occurs last because
9405 // we want the methods from this container to override any methods
9406 // we've previously seen with the same selector.
9407 for (auto *M : Container->methods()) {
9408 if (!WantInstanceMethods || M->isInstanceMethod() == *WantInstanceMethods) {
9409 if (!ReturnType.isNull() &&
9410 !Context.hasSameUnqualifiedType(ReturnType, M->getReturnType()))
9411 continue;
9412
9413 KnownMethods[M->getSelector()] =
9414 KnownMethodsMap::mapped_type(M, InOriginalClass);
9415 }
9416 }
9417}
9418
9419/// Add the parenthesized return or parameter type chunk to a code
9420/// completion string.
9421static void AddObjCPassingTypeChunk(QualType Type, unsigned ObjCDeclQuals,
9422 ASTContext &Context,
9423 const PrintingPolicy &Policy,
9424 CodeCompletionBuilder &Builder) {
9425 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9426 std::string Quals = formatObjCParamQualifiers(ObjCDeclQuals, Type);
9427 if (!Quals.empty())
9428 Builder.AddTextChunk(Builder.getAllocator().CopyString(Quals));
9429 Builder.AddTextChunk(
9430 GetCompletionTypeString(Type, Context, Policy, Builder.getAllocator()));
9431 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9432}
9433
9434/// Determine whether the given class is or inherits from a class by
9435/// the given name.
9436static bool InheritsFromClassNamed(ObjCInterfaceDecl *Class, StringRef Name) {
9437 if (!Class)
9438 return false;
9439
9440 if (Class->getIdentifier() && Class->getIdentifier()->getName() == Name)
9441 return true;
9442
9443 return InheritsFromClassNamed(Class->getSuperClass(), Name);
9444}
9445
9446/// Add code completions for Objective-C Key-Value Coding (KVC) and
9447/// Key-Value Observing (KVO).
9449 bool IsInstanceMethod,
9450 QualType ReturnType, ASTContext &Context,
9451 VisitedSelectorSet &KnownSelectors,
9452 ResultBuilder &Results) {
9453 IdentifierInfo *PropName = Property->getIdentifier();
9454 if (!PropName || PropName->getLength() == 0)
9455 return;
9456
9457 PrintingPolicy Policy = getCompletionPrintingPolicy(Results.getSema());
9458
9459 // Builder that will create each code completion.
9461 CodeCompletionAllocator &Allocator = Results.getAllocator();
9462 CodeCompletionBuilder Builder(Allocator, Results.getCodeCompletionTUInfo());
9463
9464 // The selector table.
9465 SelectorTable &Selectors = Context.Selectors;
9466
9467 // The property name, copied into the code completion allocation region
9468 // on demand.
9469 struct KeyHolder {
9470 CodeCompletionAllocator &Allocator;
9471 StringRef Key;
9472 const char *CopiedKey;
9473
9474 KeyHolder(CodeCompletionAllocator &Allocator, StringRef Key)
9475 : Allocator(Allocator), Key(Key), CopiedKey(nullptr) {}
9476
9477 operator const char *() {
9478 if (CopiedKey)
9479 return CopiedKey;
9480
9481 return CopiedKey = Allocator.CopyString(Key);
9482 }
9483 } Key(Allocator, PropName->getName());
9484
9485 // The uppercased name of the property name.
9486 std::string UpperKey = std::string(PropName->getName());
9487 if (!UpperKey.empty())
9488 UpperKey[0] = toUppercase(UpperKey[0]);
9489
9490 bool ReturnTypeMatchesProperty =
9491 ReturnType.isNull() ||
9492 Context.hasSameUnqualifiedType(ReturnType.getNonReferenceType(),
9493 Property->getType());
9494 bool ReturnTypeMatchesVoid = ReturnType.isNull() || ReturnType->isVoidType();
9495
9496 // Add the normal accessor -(type)key.
9497 if (IsInstanceMethod &&
9498 KnownSelectors.insert(Selectors.getNullarySelector(PropName)).second &&
9499 ReturnTypeMatchesProperty && !Property->getGetterMethodDecl()) {
9500 if (ReturnType.isNull())
9501 AddObjCPassingTypeChunk(Property->getType(), /*Quals=*/0, Context, Policy,
9502 Builder);
9503
9504 Builder.AddTypedTextChunk(Key);
9505 Results.AddResult(Result(Builder.TakeString(), CCP_CodePattern,
9507 }
9508
9509 // If we have an integral or boolean property (or the user has provided
9510 // an integral or boolean return type), add the accessor -(type)isKey.
9511 if (IsInstanceMethod &&
9512 ((!ReturnType.isNull() &&
9513 (ReturnType->isIntegerType() || ReturnType->isBooleanType())) ||
9514 (ReturnType.isNull() && (Property->getType()->isIntegerType() ||
9515 Property->getType()->isBooleanType())))) {
9516 std::string SelectorName = (Twine("is") + UpperKey).str();
9517 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9518 if (KnownSelectors.insert(Selectors.getNullarySelector(SelectorId))
9519 .second) {
9520 if (ReturnType.isNull()) {
9521 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9522 Builder.AddTextChunk("BOOL");
9523 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9524 }
9525
9526 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorId->getName()));
9527 Results.AddResult(Result(Builder.TakeString(), CCP_CodePattern,
9529 }
9530 }
9531
9532 // Add the normal mutator.
9533 if (IsInstanceMethod && ReturnTypeMatchesVoid &&
9534 !Property->getSetterMethodDecl()) {
9535 std::string SelectorName = (Twine("set") + UpperKey).str();
9536 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9537 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId)).second) {
9538 if (ReturnType.isNull()) {
9539 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9540 Builder.AddTextChunk("void");
9541 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9542 }
9543
9544 Builder.AddTypedTextChunk(
9545 Allocator.CopyString(SelectorId->getName() + ":"));
9546 AddObjCPassingTypeChunk(Property->getType(), /*Quals=*/0, Context, Policy,
9547 Builder);
9548 Builder.AddTextChunk(Key);
9549 Results.AddResult(Result(Builder.TakeString(), CCP_CodePattern,
9551 }
9552 }
9553
9554 // Indexed and unordered accessors
9555 unsigned IndexedGetterPriority = CCP_CodePattern;
9556 unsigned IndexedSetterPriority = CCP_CodePattern;
9557 unsigned UnorderedGetterPriority = CCP_CodePattern;
9558 unsigned UnorderedSetterPriority = CCP_CodePattern;
9559 if (const auto *ObjCPointer =
9560 Property->getType()->getAs<ObjCObjectPointerType>()) {
9561 if (ObjCInterfaceDecl *IFace = ObjCPointer->getInterfaceDecl()) {
9562 // If this interface type is not provably derived from a known
9563 // collection, penalize the corresponding completions.
9564 if (!InheritsFromClassNamed(IFace, "NSMutableArray")) {
9565 IndexedSetterPriority += CCD_ProbablyNotObjCCollection;
9566 if (!InheritsFromClassNamed(IFace, "NSArray"))
9567 IndexedGetterPriority += CCD_ProbablyNotObjCCollection;
9568 }
9569
9570 if (!InheritsFromClassNamed(IFace, "NSMutableSet")) {
9571 UnorderedSetterPriority += CCD_ProbablyNotObjCCollection;
9572 if (!InheritsFromClassNamed(IFace, "NSSet"))
9573 UnorderedGetterPriority += CCD_ProbablyNotObjCCollection;
9574 }
9575 }
9576 } else {
9577 IndexedGetterPriority += CCD_ProbablyNotObjCCollection;
9578 IndexedSetterPriority += CCD_ProbablyNotObjCCollection;
9579 UnorderedGetterPriority += CCD_ProbablyNotObjCCollection;
9580 UnorderedSetterPriority += CCD_ProbablyNotObjCCollection;
9581 }
9582
9583 // Add -(NSUInteger)countOf<key>
9584 if (IsInstanceMethod &&
9585 (ReturnType.isNull() || ReturnType->isIntegerType())) {
9586 std::string SelectorName = (Twine("countOf") + UpperKey).str();
9587 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9588 if (KnownSelectors.insert(Selectors.getNullarySelector(SelectorId))
9589 .second) {
9590 if (ReturnType.isNull()) {
9591 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9592 Builder.AddTextChunk("NSUInteger");
9593 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9594 }
9595
9596 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorId->getName()));
9597 Results.AddResult(
9598 Result(Builder.TakeString(),
9599 std::min(IndexedGetterPriority, UnorderedGetterPriority),
9601 }
9602 }
9603
9604 // Indexed getters
9605 // Add -(id)objectInKeyAtIndex:(NSUInteger)index
9606 if (IsInstanceMethod &&
9607 (ReturnType.isNull() || ReturnType->isObjCObjectPointerType())) {
9608 std::string SelectorName = (Twine("objectIn") + UpperKey + "AtIndex").str();
9609 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9610 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId)).second) {
9611 if (ReturnType.isNull()) {
9612 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9613 Builder.AddTextChunk("id");
9614 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9615 }
9616
9617 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9618 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9619 Builder.AddTextChunk("NSUInteger");
9620 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9621 Builder.AddTextChunk("index");
9622 Results.AddResult(Result(Builder.TakeString(), IndexedGetterPriority,
9624 }
9625 }
9626
9627 // Add -(NSArray *)keyAtIndexes:(NSIndexSet *)indexes
9628 if (IsInstanceMethod &&
9629 (ReturnType.isNull() ||
9630 (ReturnType->isObjCObjectPointerType() &&
9631 ReturnType->castAs<ObjCObjectPointerType>()->getInterfaceDecl() &&
9632 ReturnType->castAs<ObjCObjectPointerType>()
9634 ->getName() == "NSArray"))) {
9635 std::string SelectorName = (Twine(Property->getName()) + "AtIndexes").str();
9636 IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9637 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId)).second) {
9638 if (ReturnType.isNull()) {
9639 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9640 Builder.AddTextChunk("NSArray *");
9641 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9642 }
9643
9644 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9645 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9646 Builder.AddTextChunk("NSIndexSet *");
9647 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9648 Builder.AddTextChunk("indexes");
9649 Results.AddResult(Result(Builder.TakeString(), IndexedGetterPriority,
9651 }
9652 }
9653
9654 // Add -(void)getKey:(type **)buffer range:(NSRange)inRange
9655 if (IsInstanceMethod && ReturnTypeMatchesVoid) {
9656 std::string SelectorName = (Twine("get") + UpperKey).str();
9657 const IdentifierInfo *SelectorIds[2] = {&Context.Idents.get(SelectorName),
9658 &Context.Idents.get("range")};
9659
9660 if (KnownSelectors.insert(Selectors.getSelector(2, SelectorIds)).second) {
9661 if (ReturnType.isNull()) {
9662 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9663 Builder.AddTextChunk("void");
9664 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9665 }
9666
9667 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9668 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9669 Builder.AddPlaceholderChunk("object-type");
9670 Builder.AddTextChunk(" **");
9671 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9672 Builder.AddTextChunk("buffer");
9674 Builder.AddTypedTextChunk("range:");
9675 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9676 Builder.AddTextChunk("NSRange");
9677 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9678 Builder.AddTextChunk("inRange");
9679 Results.AddResult(Result(Builder.TakeString(), IndexedGetterPriority,
9681 }
9682 }
9683
9684 // Mutable indexed accessors
9685
9686 // - (void)insertObject:(type *)object inKeyAtIndex:(NSUInteger)index
9687 if (IsInstanceMethod && ReturnTypeMatchesVoid) {
9688 std::string SelectorName = (Twine("in") + UpperKey + "AtIndex").str();
9689 const IdentifierInfo *SelectorIds[2] = {&Context.Idents.get("insertObject"),
9690 &Context.Idents.get(SelectorName)};
9691
9692 if (KnownSelectors.insert(Selectors.getSelector(2, SelectorIds)).second) {
9693 if (ReturnType.isNull()) {
9694 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9695 Builder.AddTextChunk("void");
9696 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9697 }
9698
9699 Builder.AddTypedTextChunk("insertObject:");
9700 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9701 Builder.AddPlaceholderChunk("object-type");
9702 Builder.AddTextChunk(" *");
9703 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9704 Builder.AddTextChunk("object");
9706 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9707 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9708 Builder.AddPlaceholderChunk("NSUInteger");
9709 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9710 Builder.AddTextChunk("index");
9711 Results.AddResult(Result(Builder.TakeString(), IndexedSetterPriority,
9713 }
9714 }
9715
9716 // - (void)insertKey:(NSArray *)array atIndexes:(NSIndexSet *)indexes
9717 if (IsInstanceMethod && ReturnTypeMatchesVoid) {
9718 std::string SelectorName = (Twine("insert") + UpperKey).str();
9719 const IdentifierInfo *SelectorIds[2] = {&Context.Idents.get(SelectorName),
9720 &Context.Idents.get("atIndexes")};
9721
9722 if (KnownSelectors.insert(Selectors.getSelector(2, SelectorIds)).second) {
9723 if (ReturnType.isNull()) {
9724 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9725 Builder.AddTextChunk("void");
9726 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9727 }
9728
9729 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9730 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9731 Builder.AddTextChunk("NSArray *");
9732 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9733 Builder.AddTextChunk("array");
9735 Builder.AddTypedTextChunk("atIndexes:");
9736 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9737 Builder.AddPlaceholderChunk("NSIndexSet *");
9738 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9739 Builder.AddTextChunk("indexes");
9740 Results.AddResult(Result(Builder.TakeString(), IndexedSetterPriority,
9742 }
9743 }
9744
9745 // -(void)removeObjectFromKeyAtIndex:(NSUInteger)index
9746 if (IsInstanceMethod && ReturnTypeMatchesVoid) {
9747 std::string SelectorName =
9748 (Twine("removeObjectFrom") + UpperKey + "AtIndex").str();
9749 const IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9750 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId)).second) {
9751 if (ReturnType.isNull()) {
9752 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9753 Builder.AddTextChunk("void");
9754 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9755 }
9756
9757 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9758 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9759 Builder.AddTextChunk("NSUInteger");
9760 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9761 Builder.AddTextChunk("index");
9762 Results.AddResult(Result(Builder.TakeString(), IndexedSetterPriority,
9764 }
9765 }
9766
9767 // -(void)removeKeyAtIndexes:(NSIndexSet *)indexes
9768 if (IsInstanceMethod && ReturnTypeMatchesVoid) {
9769 std::string SelectorName = (Twine("remove") + UpperKey + "AtIndexes").str();
9770 const IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9771 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId)).second) {
9772 if (ReturnType.isNull()) {
9773 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9774 Builder.AddTextChunk("void");
9775 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9776 }
9777
9778 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9779 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9780 Builder.AddTextChunk("NSIndexSet *");
9781 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9782 Builder.AddTextChunk("indexes");
9783 Results.AddResult(Result(Builder.TakeString(), IndexedSetterPriority,
9785 }
9786 }
9787
9788 // - (void)replaceObjectInKeyAtIndex:(NSUInteger)index withObject:(id)object
9789 if (IsInstanceMethod && ReturnTypeMatchesVoid) {
9790 std::string SelectorName =
9791 (Twine("replaceObjectIn") + UpperKey + "AtIndex").str();
9792 const IdentifierInfo *SelectorIds[2] = {&Context.Idents.get(SelectorName),
9793 &Context.Idents.get("withObject")};
9794
9795 if (KnownSelectors.insert(Selectors.getSelector(2, SelectorIds)).second) {
9796 if (ReturnType.isNull()) {
9797 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9798 Builder.AddTextChunk("void");
9799 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9800 }
9801
9802 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9803 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9804 Builder.AddPlaceholderChunk("NSUInteger");
9805 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9806 Builder.AddTextChunk("index");
9808 Builder.AddTypedTextChunk("withObject:");
9809 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9810 Builder.AddTextChunk("id");
9811 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9812 Builder.AddTextChunk("object");
9813 Results.AddResult(Result(Builder.TakeString(), IndexedSetterPriority,
9815 }
9816 }
9817
9818 // - (void)replaceKeyAtIndexes:(NSIndexSet *)indexes withKey:(NSArray *)array
9819 if (IsInstanceMethod && ReturnTypeMatchesVoid) {
9820 std::string SelectorName1 =
9821 (Twine("replace") + UpperKey + "AtIndexes").str();
9822 std::string SelectorName2 = (Twine("with") + UpperKey).str();
9823 const IdentifierInfo *SelectorIds[2] = {&Context.Idents.get(SelectorName1),
9824 &Context.Idents.get(SelectorName2)};
9825
9826 if (KnownSelectors.insert(Selectors.getSelector(2, SelectorIds)).second) {
9827 if (ReturnType.isNull()) {
9828 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9829 Builder.AddTextChunk("void");
9830 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9831 }
9832
9833 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName1 + ":"));
9834 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9835 Builder.AddPlaceholderChunk("NSIndexSet *");
9836 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9837 Builder.AddTextChunk("indexes");
9839 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName2 + ":"));
9840 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9841 Builder.AddTextChunk("NSArray *");
9842 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9843 Builder.AddTextChunk("array");
9844 Results.AddResult(Result(Builder.TakeString(), IndexedSetterPriority,
9846 }
9847 }
9848
9849 // Unordered getters
9850 // - (NSEnumerator *)enumeratorOfKey
9851 if (IsInstanceMethod &&
9852 (ReturnType.isNull() ||
9853 (ReturnType->isObjCObjectPointerType() &&
9854 ReturnType->castAs<ObjCObjectPointerType>()->getInterfaceDecl() &&
9855 ReturnType->castAs<ObjCObjectPointerType>()
9857 ->getName() == "NSEnumerator"))) {
9858 std::string SelectorName = (Twine("enumeratorOf") + UpperKey).str();
9859 const IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9860 if (KnownSelectors.insert(Selectors.getNullarySelector(SelectorId))
9861 .second) {
9862 if (ReturnType.isNull()) {
9863 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9864 Builder.AddTextChunk("NSEnumerator *");
9865 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9866 }
9867
9868 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName));
9869 Results.AddResult(Result(Builder.TakeString(), UnorderedGetterPriority,
9871 }
9872 }
9873
9874 // - (type *)memberOfKey:(type *)object
9875 if (IsInstanceMethod &&
9876 (ReturnType.isNull() || ReturnType->isObjCObjectPointerType())) {
9877 std::string SelectorName = (Twine("memberOf") + UpperKey).str();
9878 const IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9879 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId)).second) {
9880 if (ReturnType.isNull()) {
9881 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9882 Builder.AddPlaceholderChunk("object-type");
9883 Builder.AddTextChunk(" *");
9884 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9885 }
9886
9887 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9888 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9889 if (ReturnType.isNull()) {
9890 Builder.AddPlaceholderChunk("object-type");
9891 Builder.AddTextChunk(" *");
9892 } else {
9893 Builder.AddTextChunk(GetCompletionTypeString(
9894 ReturnType, Context, Policy, Builder.getAllocator()));
9895 }
9896 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9897 Builder.AddTextChunk("object");
9898 Results.AddResult(Result(Builder.TakeString(), UnorderedGetterPriority,
9900 }
9901 }
9902
9903 // Mutable unordered accessors
9904 // - (void)addKeyObject:(type *)object
9905 if (IsInstanceMethod && ReturnTypeMatchesVoid) {
9906 std::string SelectorName =
9907 (Twine("add") + UpperKey + Twine("Object")).str();
9908 const IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9909 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId)).second) {
9910 if (ReturnType.isNull()) {
9911 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9912 Builder.AddTextChunk("void");
9913 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9914 }
9915
9916 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9917 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9918 Builder.AddPlaceholderChunk("object-type");
9919 Builder.AddTextChunk(" *");
9920 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9921 Builder.AddTextChunk("object");
9922 Results.AddResult(Result(Builder.TakeString(), UnorderedSetterPriority,
9924 }
9925 }
9926
9927 // - (void)addKey:(NSSet *)objects
9928 if (IsInstanceMethod && ReturnTypeMatchesVoid) {
9929 std::string SelectorName = (Twine("add") + UpperKey).str();
9930 const IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9931 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId)).second) {
9932 if (ReturnType.isNull()) {
9933 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9934 Builder.AddTextChunk("void");
9935 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9936 }
9937
9938 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9939 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9940 Builder.AddTextChunk("NSSet *");
9941 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9942 Builder.AddTextChunk("objects");
9943 Results.AddResult(Result(Builder.TakeString(), UnorderedSetterPriority,
9945 }
9946 }
9947
9948 // - (void)removeKeyObject:(type *)object
9949 if (IsInstanceMethod && ReturnTypeMatchesVoid) {
9950 std::string SelectorName =
9951 (Twine("remove") + UpperKey + Twine("Object")).str();
9952 const IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9953 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId)).second) {
9954 if (ReturnType.isNull()) {
9955 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9956 Builder.AddTextChunk("void");
9957 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9958 }
9959
9960 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9961 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9962 Builder.AddPlaceholderChunk("object-type");
9963 Builder.AddTextChunk(" *");
9964 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9965 Builder.AddTextChunk("object");
9966 Results.AddResult(Result(Builder.TakeString(), UnorderedSetterPriority,
9968 }
9969 }
9970
9971 // - (void)removeKey:(NSSet *)objects
9972 if (IsInstanceMethod && ReturnTypeMatchesVoid) {
9973 std::string SelectorName = (Twine("remove") + UpperKey).str();
9974 const IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9975 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId)).second) {
9976 if (ReturnType.isNull()) {
9977 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9978 Builder.AddTextChunk("void");
9979 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9980 }
9981
9982 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
9983 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9984 Builder.AddTextChunk("NSSet *");
9985 Builder.AddChunk(CodeCompletionString::CK_RightParen);
9986 Builder.AddTextChunk("objects");
9987 Results.AddResult(Result(Builder.TakeString(), UnorderedSetterPriority,
9989 }
9990 }
9991
9992 // - (void)intersectKey:(NSSet *)objects
9993 if (IsInstanceMethod && ReturnTypeMatchesVoid) {
9994 std::string SelectorName = (Twine("intersect") + UpperKey).str();
9995 const IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
9996 if (KnownSelectors.insert(Selectors.getUnarySelector(SelectorId)).second) {
9997 if (ReturnType.isNull()) {
9998 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
9999 Builder.AddTextChunk("void");
10000 Builder.AddChunk(CodeCompletionString::CK_RightParen);
10001 }
10002
10003 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName + ":"));
10004 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
10005 Builder.AddTextChunk("NSSet *");
10006 Builder.AddChunk(CodeCompletionString::CK_RightParen);
10007 Builder.AddTextChunk("objects");
10008 Results.AddResult(Result(Builder.TakeString(), UnorderedSetterPriority,
10010 }
10011 }
10012
10013 // Key-Value Observing
10014 // + (NSSet *)keyPathsForValuesAffectingKey
10015 if (!IsInstanceMethod &&
10016 (ReturnType.isNull() ||
10017 (ReturnType->isObjCObjectPointerType() &&
10018 ReturnType->castAs<ObjCObjectPointerType>()->getInterfaceDecl() &&
10019 ReturnType->castAs<ObjCObjectPointerType>()
10021 ->getName() == "NSSet"))) {
10022 std::string SelectorName =
10023 (Twine("keyPathsForValuesAffecting") + UpperKey).str();
10024 const IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
10025 if (KnownSelectors.insert(Selectors.getNullarySelector(SelectorId))
10026 .second) {
10027 if (ReturnType.isNull()) {
10028 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
10029 Builder.AddTextChunk("NSSet<NSString *> *");
10030 Builder.AddChunk(CodeCompletionString::CK_RightParen);
10031 }
10032
10033 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName));
10034 Results.AddResult(Result(Builder.TakeString(), CCP_CodePattern,
10036 }
10037 }
10038
10039 // + (BOOL)automaticallyNotifiesObserversForKey
10040 if (!IsInstanceMethod &&
10041 (ReturnType.isNull() || ReturnType->isIntegerType() ||
10042 ReturnType->isBooleanType())) {
10043 std::string SelectorName =
10044 (Twine("automaticallyNotifiesObserversOf") + UpperKey).str();
10045 const IdentifierInfo *SelectorId = &Context.Idents.get(SelectorName);
10046 if (KnownSelectors.insert(Selectors.getNullarySelector(SelectorId))
10047 .second) {
10048 if (ReturnType.isNull()) {
10049 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
10050 Builder.AddTextChunk("BOOL");
10051 Builder.AddChunk(CodeCompletionString::CK_RightParen);
10052 }
10053
10054 Builder.AddTypedTextChunk(Allocator.CopyString(SelectorName));
10055 Results.AddResult(Result(Builder.TakeString(), CCP_CodePattern,
10057 }
10058 }
10059}
10060
10062 Scope *S, std::optional<bool> IsInstanceMethod, ParsedType ReturnTy) {
10063 ASTContext &Context = getASTContext();
10064 // Determine the return type of the method we're declaring, if
10065 // provided.
10066 QualType ReturnType = SemaRef.GetTypeFromParser(ReturnTy);
10067 Decl *IDecl = nullptr;
10068 if (SemaRef.CurContext->isObjCContainer()) {
10069 ObjCContainerDecl *OCD = dyn_cast<ObjCContainerDecl>(SemaRef.CurContext);
10070 IDecl = OCD;
10071 }
10072 // Determine where we should start searching for methods.
10073 ObjCContainerDecl *SearchDecl = nullptr;
10074 bool IsInImplementation = false;
10075 if (Decl *D = IDecl) {
10076 if (ObjCImplementationDecl *Impl = dyn_cast<ObjCImplementationDecl>(D)) {
10077 SearchDecl = Impl->getClassInterface();
10078 IsInImplementation = true;
10079 } else if (ObjCCategoryImplDecl *CatImpl =
10080 dyn_cast<ObjCCategoryImplDecl>(D)) {
10081 SearchDecl = CatImpl->getCategoryDecl();
10082 IsInImplementation = true;
10083 } else
10084 SearchDecl = dyn_cast<ObjCContainerDecl>(D);
10085 }
10086
10087 if (!SearchDecl && S) {
10088 if (DeclContext *DC = S->getEntity())
10089 SearchDecl = dyn_cast<ObjCContainerDecl>(DC);
10090 }
10091
10092 if (!SearchDecl) {
10095 return;
10096 }
10097
10098 // Find all of the methods that we could declare/implement here.
10099 KnownMethodsMap KnownMethods;
10100 FindImplementableMethods(Context, SearchDecl, IsInstanceMethod, ReturnType,
10101 KnownMethods);
10102
10103 // Add declarations or definitions for each of the known methods.
10105 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
10106 CodeCompleter->getCodeCompletionTUInfo(),
10108 Results.EnterNewScope();
10110 for (KnownMethodsMap::iterator M = KnownMethods.begin(),
10111 MEnd = KnownMethods.end();
10112 M != MEnd; ++M) {
10113 ObjCMethodDecl *Method = M->second.getPointer();
10114 CodeCompletionBuilder Builder(Results.getAllocator(),
10115 Results.getCodeCompletionTUInfo());
10116
10117 // Add the '-'/'+' prefix if it wasn't provided yet.
10118 if (!IsInstanceMethod) {
10119 Builder.AddTextChunk(Method->isInstanceMethod() ? "-" : "+");
10121 }
10122
10123 // If the result type was not already provided, add it to the
10124 // pattern as (type).
10125 if (ReturnType.isNull()) {
10126 QualType ResTy = Method->getSendResultType().stripObjCKindOfType(Context);
10127 AttributedType::stripOuterNullability(ResTy);
10128 AddObjCPassingTypeChunk(ResTy, Method->getObjCDeclQualifier(), Context,
10129 Policy, Builder);
10130 }
10131
10132 Selector Sel = Method->getSelector();
10133
10134 if (Sel.isUnarySelector()) {
10135 // Unary selectors have no arguments.
10136 Builder.AddTypedTextChunk(
10137 Builder.getAllocator().CopyString(Sel.getNameForSlot(0)));
10138 } else {
10139 // Add all parameters to the pattern.
10140 unsigned I = 0;
10141 for (ObjCMethodDecl::param_iterator P = Method->param_begin(),
10142 PEnd = Method->param_end();
10143 P != PEnd; (void)++P, ++I) {
10144 // Add the part of the selector name.
10145 if (I == 0)
10146 Builder.AddTypedTextChunk(
10147 Builder.getAllocator().CopyString(Sel.getNameForSlot(I) + ":"));
10148 else if (I < Sel.getNumArgs()) {
10150 Builder.AddTypedTextChunk(
10151 Builder.getAllocator().CopyString(Sel.getNameForSlot(I) + ":"));
10152 } else
10153 break;
10154
10155 // Add the parameter type.
10156 QualType ParamType;
10157 if ((*P)->getObjCDeclQualifier() & Decl::OBJC_TQ_CSNullability)
10158 ParamType = (*P)->getType();
10159 else
10160 ParamType = (*P)->getOriginalType();
10161 ParamType = ParamType.substObjCTypeArgs(
10163 AttributedType::stripOuterNullability(ParamType);
10164 AddObjCPassingTypeChunk(ParamType, (*P)->getObjCDeclQualifier(),
10165 Context, Policy, Builder);
10166
10167 if (IdentifierInfo *Id = (*P)->getIdentifier())
10168 Builder.AddTextChunk(
10169 Builder.getAllocator().CopyString(Id->getName()));
10170 }
10171 }
10172
10173 if (Method->isVariadic()) {
10174 if (Method->param_size() > 0)
10175 Builder.AddChunk(CodeCompletionString::CK_Comma);
10176 Builder.AddTextChunk("...");
10177 }
10178
10179 if (IsInImplementation && Results.includeCodePatterns()) {
10180 // We will be defining the method here, so add a compound statement.
10182 Builder.AddChunk(CodeCompletionString::CK_LeftBrace);
10184 if (!Method->getReturnType()->isVoidType()) {
10185 // If the result type is not void, add a return clause.
10186 Builder.AddTextChunk("return");
10188 Builder.AddPlaceholderChunk("expression");
10189 Builder.AddChunk(CodeCompletionString::CK_SemiColon);
10190 } else
10191 Builder.AddPlaceholderChunk("statements");
10192
10194 Builder.AddChunk(CodeCompletionString::CK_RightBrace);
10195 }
10196
10197 unsigned Priority = CCP_CodePattern;
10198 auto R = Result(Builder.TakeString(), Method, Priority);
10199 if (!M->second.getInt())
10200 setInBaseClass(R);
10201 Results.AddResult(std::move(R));
10202 }
10203
10204 // Add Key-Value-Coding and Key-Value-Observing accessor methods for all of
10205 // the properties in this class and its categories.
10206 if (Context.getLangOpts().ObjC) {
10208 Containers.push_back(SearchDecl);
10209
10210 VisitedSelectorSet KnownSelectors;
10211 for (KnownMethodsMap::iterator M = KnownMethods.begin(),
10212 MEnd = KnownMethods.end();
10213 M != MEnd; ++M)
10214 KnownSelectors.insert(M->first);
10215
10216 ObjCInterfaceDecl *IFace = dyn_cast<ObjCInterfaceDecl>(SearchDecl);
10217 if (!IFace)
10218 if (ObjCCategoryDecl *Category = dyn_cast<ObjCCategoryDecl>(SearchDecl))
10219 IFace = Category->getClassInterface();
10220
10221 if (IFace)
10222 llvm::append_range(Containers, IFace->visible_categories());
10223
10224 if (IsInstanceMethod) {
10225 for (unsigned I = 0, N = Containers.size(); I != N; ++I)
10226 for (auto *P : Containers[I]->instance_properties())
10227 AddObjCKeyValueCompletions(P, *IsInstanceMethod, ReturnType, Context,
10228 KnownSelectors, Results);
10229 }
10230 }
10231
10232 Results.ExitScope();
10233
10235 Results.getCompletionContext(), Results.data(),
10236 Results.size());
10237}
10238
10240 Scope *S, bool IsInstanceMethod, bool AtParameterName, ParsedType ReturnTy,
10242 // If we have an external source, load the entire class method
10243 // pool from the AST file.
10244 if (SemaRef.ExternalSource) {
10245 for (uint32_t I = 0, N = SemaRef.ExternalSource->GetNumExternalSelectors();
10246 I != N; ++I) {
10247 Selector Sel = SemaRef.ExternalSource->GetExternalSelector(I);
10248 if (Sel.isNull() || SemaRef.ObjC().MethodPool.count(Sel))
10249 continue;
10250
10251 SemaRef.ObjC().ReadMethodPool(Sel);
10252 }
10253 }
10254
10255 // Build the set of methods we can see.
10257 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
10258 CodeCompleter->getCodeCompletionTUInfo(),
10260
10261 if (ReturnTy)
10262 Results.setPreferredType(
10263 SemaRef.GetTypeFromParser(ReturnTy).getNonReferenceType());
10264
10265 Results.EnterNewScope();
10266 for (SemaObjC::GlobalMethodPool::iterator
10267 M = SemaRef.ObjC().MethodPool.begin(),
10268 MEnd = SemaRef.ObjC().MethodPool.end();
10269 M != MEnd; ++M) {
10270 for (ObjCMethodList *MethList = IsInstanceMethod ? &M->second.first
10271 : &M->second.second;
10272 MethList && MethList->getMethod(); MethList = MethList->getNext()) {
10273 if (!isAcceptableObjCMethod(MethList->getMethod(), MK_Any, SelIdents))
10274 continue;
10275
10276 if (AtParameterName) {
10277 // Suggest parameter names we've seen before.
10278 unsigned NumSelIdents = SelIdents.size();
10279 if (NumSelIdents &&
10280 NumSelIdents <= MethList->getMethod()->param_size()) {
10281 ParmVarDecl *Param =
10282 MethList->getMethod()->parameters()[NumSelIdents - 1];
10283 if (Param->getIdentifier()) {
10284 CodeCompletionBuilder Builder(Results.getAllocator(),
10285 Results.getCodeCompletionTUInfo());
10286 Builder.AddTypedTextChunk(Builder.getAllocator().CopyString(
10287 Param->getIdentifier()->getName()));
10288 Results.AddResult(Builder.TakeString());
10289 }
10290 }
10291
10292 continue;
10293 }
10294
10295 Result R(MethList->getMethod(),
10296 Results.getBasePriority(MethList->getMethod()),
10297 /*Qualifier=*/std::nullopt);
10298 R.StartParameter = SelIdents.size();
10299 R.AllParametersAreInformative = false;
10300 R.DeclaringEntity = true;
10301 Results.MaybeAddResult(R, SemaRef.CurContext);
10302 }
10303 }
10304
10305 Results.ExitScope();
10306
10307 if (!AtParameterName && !SelIdents.empty() &&
10308 SelIdents.front()->getName().starts_with("init")) {
10309 for (const auto &M : SemaRef.PP.macros()) {
10310 if (M.first->getName() != "NS_DESIGNATED_INITIALIZER")
10311 continue;
10312 Results.EnterNewScope();
10313 CodeCompletionBuilder Builder(Results.getAllocator(),
10314 Results.getCodeCompletionTUInfo());
10315 Builder.AddTypedTextChunk(
10316 Builder.getAllocator().CopyString(M.first->getName()));
10317 Results.AddResult(CodeCompletionResult(Builder.TakeString(), CCP_Macro,
10319 Results.ExitScope();
10320 }
10321 }
10322
10324 Results.getCompletionContext(), Results.data(),
10325 Results.size());
10326}
10327
10329 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
10330 CodeCompleter->getCodeCompletionTUInfo(),
10332 Results.EnterNewScope();
10333
10334 // #if <condition>
10335 CodeCompletionBuilder Builder(Results.getAllocator(),
10336 Results.getCodeCompletionTUInfo());
10337 Builder.AddTypedTextChunk("if");
10339 Builder.AddPlaceholderChunk("condition");
10340 Results.AddResult(Builder.TakeString());
10341
10342 // #ifdef <macro>
10343 Builder.AddTypedTextChunk("ifdef");
10345 Builder.AddPlaceholderChunk("macro");
10346 Results.AddResult(Builder.TakeString());
10347
10348 // #ifndef <macro>
10349 Builder.AddTypedTextChunk("ifndef");
10351 Builder.AddPlaceholderChunk("macro");
10352 Results.AddResult(Builder.TakeString());
10353
10354 if (InConditional) {
10355 // #elif <condition>
10356 Builder.AddTypedTextChunk("elif");
10358 Builder.AddPlaceholderChunk("condition");
10359 Results.AddResult(Builder.TakeString());
10360
10361 // #elifdef <macro>
10362 Builder.AddTypedTextChunk("elifdef");
10364 Builder.AddPlaceholderChunk("macro");
10365 Results.AddResult(Builder.TakeString());
10366
10367 // #elifndef <macro>
10368 Builder.AddTypedTextChunk("elifndef");
10370 Builder.AddPlaceholderChunk("macro");
10371 Results.AddResult(Builder.TakeString());
10372
10373 // #else
10374 Builder.AddTypedTextChunk("else");
10375 Results.AddResult(Builder.TakeString());
10376
10377 // #endif
10378 Builder.AddTypedTextChunk("endif");
10379 Results.AddResult(Builder.TakeString());
10380 }
10381
10382 // #include "header"
10383 Builder.AddTypedTextChunk("include");
10385 Builder.AddTextChunk("\"");
10386 Builder.AddPlaceholderChunk("header");
10387 Builder.AddTextChunk("\"");
10388 Results.AddResult(Builder.TakeString());
10389
10390 // #include <header>
10391 Builder.AddTypedTextChunk("include");
10393 Builder.AddTextChunk("<");
10394 Builder.AddPlaceholderChunk("header");
10395 Builder.AddTextChunk(">");
10396 Results.AddResult(Builder.TakeString());
10397
10398 // #define <macro>
10399 Builder.AddTypedTextChunk("define");
10401 Builder.AddPlaceholderChunk("macro");
10402 Results.AddResult(Builder.TakeString());
10403
10404 // #define <macro>(<args>)
10405 Builder.AddTypedTextChunk("define");
10407 Builder.AddPlaceholderChunk("macro");
10408 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
10409 Builder.AddPlaceholderChunk("args");
10410 Builder.AddChunk(CodeCompletionString::CK_RightParen);
10411 Results.AddResult(Builder.TakeString());
10412
10413 // #undef <macro>
10414 Builder.AddTypedTextChunk("undef");
10416 Builder.AddPlaceholderChunk("macro");
10417 Results.AddResult(Builder.TakeString());
10418
10419 // #line <number>
10420 Builder.AddTypedTextChunk("line");
10422 Builder.AddPlaceholderChunk("number");
10423 Results.AddResult(Builder.TakeString());
10424
10425 // #line <number> "filename"
10426 Builder.AddTypedTextChunk("line");
10428 Builder.AddPlaceholderChunk("number");
10430 Builder.AddTextChunk("\"");
10431 Builder.AddPlaceholderChunk("filename");
10432 Builder.AddTextChunk("\"");
10433 Results.AddResult(Builder.TakeString());
10434
10435 // #error <message>
10436 Builder.AddTypedTextChunk("error");
10438 Builder.AddPlaceholderChunk("message");
10439 Results.AddResult(Builder.TakeString());
10440
10441 // #pragma <arguments>
10442 Builder.AddTypedTextChunk("pragma");
10444 Builder.AddPlaceholderChunk("arguments");
10445 Results.AddResult(Builder.TakeString());
10446
10447 if (getLangOpts().ObjC) {
10448 // #import "header"
10449 Builder.AddTypedTextChunk("import");
10451 Builder.AddTextChunk("\"");
10452 Builder.AddPlaceholderChunk("header");
10453 Builder.AddTextChunk("\"");
10454 Results.AddResult(Builder.TakeString());
10455
10456 // #import <header>
10457 Builder.AddTypedTextChunk("import");
10459 Builder.AddTextChunk("<");
10460 Builder.AddPlaceholderChunk("header");
10461 Builder.AddTextChunk(">");
10462 Results.AddResult(Builder.TakeString());
10463 }
10464
10465 // #include_next "header"
10466 Builder.AddTypedTextChunk("include_next");
10468 Builder.AddTextChunk("\"");
10469 Builder.AddPlaceholderChunk("header");
10470 Builder.AddTextChunk("\"");
10471 Results.AddResult(Builder.TakeString());
10472
10473 // #include_next <header>
10474 Builder.AddTypedTextChunk("include_next");
10476 Builder.AddTextChunk("<");
10477 Builder.AddPlaceholderChunk("header");
10478 Builder.AddTextChunk(">");
10479 Results.AddResult(Builder.TakeString());
10480
10481 // #warning <message>
10482 Builder.AddTypedTextChunk("warning");
10484 Builder.AddPlaceholderChunk("message");
10485 Results.AddResult(Builder.TakeString());
10486
10487 if (getLangOpts().C23) {
10488 // #embed "file"
10489 Builder.AddTypedTextChunk("embed");
10491 Builder.AddTextChunk("\"");
10492 Builder.AddPlaceholderChunk("file");
10493 Builder.AddTextChunk("\"");
10494 Results.AddResult(Builder.TakeString());
10495
10496 // #embed <file>
10497 Builder.AddTypedTextChunk("embed");
10499 Builder.AddTextChunk("<");
10500 Builder.AddPlaceholderChunk("file");
10501 Builder.AddTextChunk(">");
10502 Results.AddResult(Builder.TakeString());
10503 }
10504
10505 // Note: #ident and #sccs are such crazy anachronisms that we don't provide
10506 // completions for them. And __include_macros is a Clang-internal extension
10507 // that we don't want to encourage anyone to use.
10508
10509 // FIXME: we don't support #assert or #unassert, so don't suggest them.
10510 Results.ExitScope();
10511
10513 Results.getCompletionContext(), Results.data(),
10514 Results.size());
10515}
10516
10523
10525 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
10526 CodeCompleter->getCodeCompletionTUInfo(),
10529 if (!IsDefinition && CodeCompleter->includeMacros()) {
10530 // Add just the names of macros, not their arguments.
10531 CodeCompletionBuilder Builder(Results.getAllocator(),
10532 Results.getCodeCompletionTUInfo());
10533 Results.EnterNewScope();
10534 for (const auto &M : SemaRef.PP.macros()) {
10535 Builder.AddTypedTextChunk(
10536 Builder.getAllocator().CopyString(M.first->getName()));
10537 Results.AddResult(CodeCompletionResult(
10538 Builder.TakeString(), CCP_CodePattern, CXCursor_MacroDefinition));
10539 }
10540 Results.ExitScope();
10541 } else if (IsDefinition) {
10542 // FIXME: Can we detect when the user just wrote an include guard above?
10543 }
10544
10546 Results.getCompletionContext(), Results.data(),
10547 Results.size());
10548}
10549
10551 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
10552 CodeCompleter->getCodeCompletionTUInfo(),
10554
10555 if (CodeCompleter->includeMacros())
10556 AddMacroResults(SemaRef.PP, Results, CodeCompleter->loadExternal(), true);
10557
10558 // defined (<macro>)
10559 Results.EnterNewScope();
10560 CodeCompletionBuilder Builder(Results.getAllocator(),
10561 Results.getCodeCompletionTUInfo());
10562 Builder.AddTypedTextChunk("defined");
10564 Builder.AddChunk(CodeCompletionString::CK_LeftParen);
10565 Builder.AddPlaceholderChunk("macro");
10566 Builder.AddChunk(CodeCompletionString::CK_RightParen);
10567 Results.AddResult(Builder.TakeString());
10568 Results.ExitScope();
10569
10571 Results.getCompletionContext(), Results.data(),
10572 Results.size());
10573}
10574
10576 Scope *S, IdentifierInfo *Macro, MacroInfo *MacroInfo, unsigned Argument) {
10577 // FIXME: In the future, we could provide "overload" results, much like we
10578 // do for function calls.
10579
10580 // Now just ignore this. There will be another code-completion callback
10581 // for the expanded tokens.
10582}
10583
10584// This handles completion inside an #include filename, e.g. #include <foo/ba
10585// We look for the directory "foo" under each directory on the include path,
10586// list its files, and reassemble the appropriate #include.
10588 bool Angled) {
10589 // RelDir should use /, but unescaped \ is possible on windows!
10590 // Our completions will normalize to / for simplicity, this case is rare.
10591 std::string RelDir = llvm::sys::path::convert_to_slash(Dir);
10592 // We need the native slashes for the actual file system interactions.
10593 SmallString<128> NativeRelDir = StringRef(RelDir);
10594 llvm::sys::path::native(NativeRelDir);
10595 llvm::vfs::FileSystem &FS =
10596 SemaRef.getSourceManager().getFileManager().getVirtualFileSystem();
10597
10598 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
10599 CodeCompleter->getCodeCompletionTUInfo(),
10601 llvm::DenseSet<StringRef> SeenResults; // To deduplicate results.
10602
10603 // Helper: adds one file or directory completion result.
10604 auto AddCompletion = [&](StringRef Filename, bool IsDirectory) {
10605 SmallString<64> TypedChunk = Filename;
10606 // Directory completion is up to the slash, e.g. <sys/
10607 TypedChunk.push_back(IsDirectory ? '/' : Angled ? '>' : '"');
10608 auto R = SeenResults.insert(TypedChunk);
10609 if (R.second) { // New completion
10610 const char *InternedTyped = Results.getAllocator().CopyString(TypedChunk);
10611 *R.first = InternedTyped; // Avoid dangling StringRef.
10612 CodeCompletionBuilder Builder(CodeCompleter->getAllocator(),
10613 CodeCompleter->getCodeCompletionTUInfo());
10614 Builder.AddTypedTextChunk(InternedTyped);
10615 // The result is a "Pattern", which is pretty opaque.
10616 // We may want to include the real filename to allow smart ranking.
10617 Results.AddResult(CodeCompletionResult(Builder.TakeString()));
10618 }
10619 };
10620
10621 // Helper: scans IncludeDir for nice files, and adds results for each.
10622 auto AddFilesFromIncludeDir = [&](StringRef IncludeDir,
10623 bool IsSystem,
10624 DirectoryLookup::LookupType_t LookupType) {
10625 llvm::SmallString<128> Dir = IncludeDir;
10626 if (!NativeRelDir.empty()) {
10627 if (LookupType == DirectoryLookup::LT_Framework) {
10628 // For a framework dir, #include <Foo/Bar/> actually maps to
10629 // a path of Foo.framework/Headers/Bar/.
10630 auto Begin = llvm::sys::path::begin(NativeRelDir);
10631 auto End = llvm::sys::path::end(NativeRelDir);
10632
10633 llvm::sys::path::append(Dir, *Begin + ".framework", "Headers");
10634 llvm::sys::path::append(Dir, ++Begin, End);
10635 } else {
10636 llvm::sys::path::append(Dir, NativeRelDir);
10637 }
10638 }
10639
10640 const StringRef &Dirname = llvm::sys::path::filename(Dir);
10641 const bool isQt = Dirname.starts_with("Qt") || Dirname == "ActiveQt";
10642 const bool ExtensionlessHeaders =
10643 IsSystem || isQt || Dir.ends_with(".framework/Headers") ||
10644 IncludeDir.ends_with("/include") || IncludeDir.ends_with("\\include");
10645 std::error_code EC;
10646 unsigned Count = 0;
10647 for (auto It = FS.dir_begin(Dir, EC);
10648 !EC && It != llvm::vfs::directory_iterator(); It.increment(EC)) {
10649 if (++Count == 2500) // If we happen to hit a huge directory,
10650 break; // bail out early so we're not too slow.
10651 StringRef Filename = llvm::sys::path::filename(It->path());
10652
10653 // To know whether a symlink should be treated as file or a directory, we
10654 // have to stat it. This should be cheap enough as there shouldn't be many
10655 // symlinks.
10656 llvm::sys::fs::file_type Type = It->type();
10657 if (Type == llvm::sys::fs::file_type::symlink_file) {
10658 if (auto FileStatus = FS.status(It->path()))
10659 Type = FileStatus->getType();
10660 }
10661 switch (Type) {
10662 case llvm::sys::fs::file_type::directory_file:
10663 // All entries in a framework directory must have a ".framework" suffix,
10664 // but the suffix does not appear in the source code's include/import.
10665 if (LookupType == DirectoryLookup::LT_Framework &&
10666 NativeRelDir.empty() && !Filename.consume_back(".framework"))
10667 break;
10668
10669 AddCompletion(Filename, /*IsDirectory=*/true);
10670 break;
10671 case llvm::sys::fs::file_type::regular_file: {
10672 // Only files that really look like headers. (Except in special dirs).
10673 const bool IsHeader = Filename.ends_with_insensitive(".h") ||
10674 Filename.ends_with_insensitive(".hh") ||
10675 Filename.ends_with_insensitive(".hpp") ||
10676 Filename.ends_with_insensitive(".hxx") ||
10677 Filename.ends_with_insensitive(".inc") ||
10678 (ExtensionlessHeaders && !Filename.contains('.'));
10679 if (!IsHeader)
10680 break;
10681 AddCompletion(Filename, /*IsDirectory=*/false);
10682 break;
10683 }
10684 default:
10685 break;
10686 }
10687 }
10688 };
10689
10690 // Helper: adds results relative to IncludeDir, if possible.
10691 auto AddFilesFromDirLookup = [&](const DirectoryLookup &IncludeDir,
10692 bool IsSystem) {
10693 switch (IncludeDir.getLookupType()) {
10695 // header maps are not (currently) enumerable.
10696 break;
10698 AddFilesFromIncludeDir(IncludeDir.getDirRef()->getName(), IsSystem,
10700 break;
10702 AddFilesFromIncludeDir(IncludeDir.getFrameworkDirRef()->getName(),
10704 break;
10705 }
10706 };
10707
10708 // Finally with all our helpers, we can scan the include path.
10709 // Do this in standard order so deduplication keeps the right file.
10710 // (In case we decide to add more details to the results later).
10711 const auto &S = SemaRef.PP.getHeaderSearchInfo();
10712 using llvm::make_range;
10713 if (!Angled) {
10714 // The current directory is on the include path for "quoted" includes.
10715 if (auto CurFile = SemaRef.PP.getCurrentFileLexer()->getFileEntry())
10716 AddFilesFromIncludeDir(CurFile->getDir().getName(), false,
10718 for (const auto &D : make_range(S.quoted_dir_begin(), S.quoted_dir_end()))
10719 AddFilesFromDirLookup(D, false);
10720 }
10721 for (const auto &D : make_range(S.angled_dir_begin(), S.angled_dir_end()))
10722 AddFilesFromDirLookup(D, false);
10723 for (const auto &D : make_range(S.system_dir_begin(), S.system_dir_end()))
10724 AddFilesFromDirLookup(D, true);
10725
10727 Results.getCompletionContext(), Results.data(),
10728 Results.size());
10729}
10730
10736
10738 ResultBuilder Results(SemaRef, CodeCompleter->getAllocator(),
10739 CodeCompleter->getCodeCompletionTUInfo(),
10741 Results.EnterNewScope();
10742 static const char *Platforms[] = {"macOS", "iOS", "watchOS", "tvOS"};
10743 for (const char *Platform : llvm::ArrayRef(Platforms)) {
10744 Results.AddResult(CodeCompletionResult(Platform));
10745 Results.AddResult(CodeCompletionResult(Results.getAllocator().CopyString(
10746 Twine(Platform) + "ApplicationExtension")));
10747 }
10748 Results.ExitScope();
10750 Results.getCompletionContext(), Results.data(),
10751 Results.size());
10752}
10753
10755 CodeCompletionAllocator &Allocator, CodeCompletionTUInfo &CCTUInfo,
10757 ResultBuilder Builder(SemaRef, Allocator, CCTUInfo,
10759 if (!CodeCompleter || CodeCompleter->includeGlobals()) {
10760 CodeCompletionDeclConsumer Consumer(
10761 Builder, getASTContext().getTranslationUnitDecl());
10762 SemaRef.LookupVisibleDecls(getASTContext().getTranslationUnitDecl(),
10763 Sema::LookupAnyName, Consumer,
10764 !CodeCompleter || CodeCompleter->loadExternal());
10765 }
10766
10767 if (!CodeCompleter || CodeCompleter->includeMacros())
10768 AddMacroResults(SemaRef.PP, Builder,
10769 !CodeCompleter || CodeCompleter->loadExternal(), true);
10770
10771 Results.clear();
10772 Results.insert(Results.end(), Builder.data(),
10773 Builder.data() + Builder.size());
10774}
10775
10777 CodeCompleteConsumer *CompletionConsumer)
10778 : SemaBase(S), CodeCompleter(CompletionConsumer),
10779 Resolver(S.getASTContext()) {}
This file provides AST data structures related to concepts.
bool TraverseNestedNameSpecifierLoc(NestedNameSpecifierLoc QualifierLoc)
static Decl::Kind getKind(const Decl *D)
Defines the C++ Decl subclasses, other than those for templates (found in DeclTemplate....
This file defines the classes used to store parsed information about declaration-specifiers and decla...
Defines the C++ template declaration subclasses.
Defines the ExceptionSpecificationType enumeration and various utility functions.
Defines the clang::Expr interface and subclasses for C++ expressions.
Defines Expressions and AST nodes for C++2a concepts.
bool Optional
Is optional and can be removed.
Token Tok
The Token.
Result
Implement __builtin_bit_cast and related operations.
#define X(type, name)
Definition Value.h:97
llvm::MachO::Record Record
Definition MachO.h:31
Defines the clang::MacroInfo and clang::MacroDirective classes.
Defines an enumeration for C++ overloaded operators.
Defines the clang::Preprocessor interface.
static AccessResult IsAccessible(Sema &S, const EffectiveContext &EC, AccessTarget &Entity, TemplateSpecCandidateSet *FailedTSC)
Determines whether the accessed entity is accessible.
CastType
Definition SemaCast.cpp:50
static QualType getPreferredArgumentTypeForMessageSend(ResultBuilder &Results, unsigned NumSelIdents)
Given a set of code-completion results for the argument of a message send, determine the preferred ty...
static void printOverrideString(const CodeCompletionString &CCS, std::string &BeforeName, std::string &NameAndSignature)
static bool isConstructor(const Decl *ND)
static void findTypeLocationForBlockDecl(const TypeSourceInfo *TSInfo, FunctionTypeLoc &Block, FunctionProtoTypeLoc &BlockProto, bool SuppressBlock=false)
Tries to find the most appropriate type location for an Objective-C block placeholder.
static bool isObjCReceiverType(ASTContext &C, QualType T)
static void AddMacroResults(Preprocessor &PP, ResultBuilder &Results, bool LoadExternal, bool IncludeUndefined, bool TargetTypeIsPointer=false)
static std::string formatTemplateParameterPlaceholder(const NamedDecl *Param, bool &Optional, const PrintingPolicy &Policy)
static std::string formatBlockPlaceholder(const PrintingPolicy &Policy, const NamedDecl *BlockDecl, FunctionTypeLoc &Block, FunctionProtoTypeLoc &BlockProto, bool SuppressBlockName=false, bool SuppressBlock=false, std::optional< ArrayRef< QualType > > ObjCSubsts=std::nullopt)
Returns a placeholder string that corresponds to an Objective-C block declaration.
static void AddQualifierToCompletionString(CodeCompletionBuilder &Result, NestedNameSpecifier Qualifier, bool QualifierIsInformative, ASTContext &Context, const PrintingPolicy &Policy)
Add a qualifier to the given code-completion string, if the provided nested-name-specifier is non-NUL...
static void AddObjCTopLevelResults(ResultBuilder &Results, bool NeedAt)
llvm::SmallPtrSet< const IdentifierInfo *, 16 > AddedPropertiesSet
The set of properties that have already been added, referenced by property name.
static bool argMatchesTemplateParams(const ParsedTemplateArgument &Arg, unsigned Index, const TemplateParameterList &Params)
static void setInBaseClass(ResultBuilder::Result &R)
static void AddObjCMethods(ObjCContainerDecl *Container, bool WantInstanceMethods, ObjCMethodKind WantKind, ArrayRef< const IdentifierInfo * > SelIdents, DeclContext *CurContext, VisitedSelectorSet &Selectors, bool AllowSameLength, ResultBuilder &Results, bool InOriginalClass=true, bool IsRootClass=false)
Add all of the Objective-C methods in the given Objective-C container to the set of results.
static bool shouldIgnoreDueToReservedName(const NamedDecl *ND, Sema &SemaRef)
static CodeCompletionString * createTemplateSignatureString(const TemplateDecl *TD, CodeCompletionBuilder &Builder, unsigned CurrentArg, const PrintingPolicy &Policy)
static QualType getParamType(Sema &SemaRef, ArrayRef< ResultCandidate > Candidates, unsigned N)
Get the type of the Nth parameter from a given set of overload candidates.
static void AddStorageSpecifiers(SemaCodeCompletion::ParserCompletionContext CCC, const LangOptions &LangOpts, ResultBuilder &Results)
static const NamedDecl * extractFunctorCallOperator(const NamedDecl *ND)
static void AddFunctionSpecifiers(SemaCodeCompletion::ParserCompletionContext CCC, const LangOptions &LangOpts, ResultBuilder &Results)
static QualType ProduceSignatureHelp(Sema &SemaRef, MutableArrayRef< ResultCandidate > Candidates, unsigned CurrentArg, SourceLocation OpenParLoc, bool Braced)
static std::string FormatFunctionParameter(const PrintingPolicy &Policy, const DeclaratorDecl *Param, bool SuppressName=false, bool SuppressBlock=false, std::optional< ArrayRef< QualType > > ObjCSubsts=std::nullopt)
static void AddFunctionParameterChunks(Preprocessor &PP, const PrintingPolicy &Policy, const FunctionDecl *Function, CodeCompletionBuilder &Result, unsigned Start=0, bool InOptional=false, bool FunctionCanBeCall=true, bool IsInDeclarationContext=false)
Add function parameter chunks to the given code completion string.
static RecordDecl * getAsRecordDecl(QualType BaseType, HeuristicResolver &Resolver)
static void AddOverrideResults(ResultBuilder &Results, const CodeCompletionContext &CCContext, CodeCompletionBuilder &Builder)
static std::string formatObjCParamQualifiers(unsigned ObjCQuals, QualType &Type)
llvm::SmallPtrSet< Selector, 16 > VisitedSelectorSet
A set of selectors, which is used to avoid introducing multiple completions with the same selector in...
static void AddOverloadAggregateChunks(const RecordDecl *RD, const PrintingPolicy &Policy, CodeCompletionBuilder &Result, unsigned CurrentArg)
static void AddTypedefResult(ResultBuilder &Results)
static void AddPrettyFunctionResults(const LangOptions &LangOpts, ResultBuilder &Results)
static void AddObjCPassingTypeChunk(QualType Type, unsigned ObjCDeclQuals, ASTContext &Context, const PrintingPolicy &Policy, CodeCompletionBuilder &Builder)
Add the parenthesized return or parameter type chunk to a code completion string.
static void AddObjCKeyValueCompletions(ObjCPropertyDecl *Property, bool IsInstanceMethod, QualType ReturnType, ASTContext &Context, VisitedSelectorSet &KnownSelectors, ResultBuilder &Results)
Add code completions for Objective-C Key-Value Coding (KVC) and Key-Value Observing (KVO).
static void AddObjCStatementResults(ResultBuilder &Results, bool NeedAt)
static QualType getDesignatedType(ASTContext &Context, QualType BaseType, const Designation &Desig, HeuristicResolver &Resolver, llvm::function_ref< const FieldDecl *(RecordDecl *, const Designator &)> LookupField)
static bool ObjCPropertyFlagConflicts(unsigned Attributes, unsigned NewFlag)
Determine whether the addition of the given flag to an Objective-C property's attributes will cause a...
static void AddEnumerators(ResultBuilder &Results, ASTContext &Context, EnumDecl *Enum, DeclContext *CurContext, const CoveredEnumerators &Enumerators)
llvm::DenseMap< Selector, llvm::PointerIntPair< ObjCMethodDecl *, 1, bool > > KnownMethodsMap
static const FunctionProtoType * TryDeconstructFunctionLike(QualType T)
Try to find a corresponding FunctionProtoType for function-like types (e.g.
static DeclContext::lookup_result getConstructors(ASTContext &Context, const CXXRecordDecl *Record)
static void AddResultTypeChunk(ASTContext &Context, const PrintingPolicy &Policy, const NamedDecl *ND, QualType BaseType, CodeCompletionBuilder &Result)
If the given declaration has an associated type, add it as a result type chunk.
static void AddObjCVisibilityResults(const LangOptions &LangOpts, ResultBuilder &Results, bool NeedAt)
static void addThisCompletion(Sema &S, ResultBuilder &Results)
Add a completion for "this", if we're in a member function.
static NestedNameSpecifier getRequiredQualification(ASTContext &Context, const DeclContext *CurContext, const DeclContext *TargetContext)
Compute the qualification required to get from the current context (CurContext) to the target context...
static void AddObjCImplementationResults(const LangOptions &LangOpts, ResultBuilder &Results, bool NeedAt)
static ObjCMethodDecl * AddSuperSendCompletion(Sema &S, bool NeedSuperKeyword, ArrayRef< const IdentifierInfo * > SelIdents, ResultBuilder &Results)
static void AddRecordMembersCompletionResults(Sema &SemaRef, ResultBuilder &Results, Scope *S, QualType BaseType, ExprValueKind BaseKind, RecordDecl *RD, std::optional< FixItHint > AccessOpFixIt)
static void AddObjCBlockCall(ASTContext &Context, const PrintingPolicy &Policy, CodeCompletionBuilder &Builder, const NamedDecl *BD, const FunctionTypeLoc &BlockLoc, const FunctionProtoTypeLoc &BlockProtoLoc)
Adds a block invocation code completion result for the given block declaration BD.
static void AddLambdaCompletion(ResultBuilder &Results, llvm::ArrayRef< QualType > Parameters, const LangOptions &LangOpts)
Adds a pattern completion for a lambda expression with the specified parameter types and placeholders...
static void AddTypeSpecifierResults(const LangOptions &LangOpts, ResultBuilder &Results)
Add type specifiers for the current language as keyword results.
static std::optional< unsigned > getNextAggregateIndexAfterDesignatedInit(const ResultCandidate &Aggregate, ArrayRef< Expr * > Args)
static std::string GetDefaultValueString(const ParmVarDecl *Param, const SourceManager &SM, const LangOptions &LangOpts)
static void AddFunctionTypeQualsToCompletionString(CodeCompletionBuilder &Result, const FunctionDecl *Function, bool AsInformativeChunks=true)
static CodeCompletionContext mapCodeCompletionContext(Sema &S, SemaCodeCompletion::ParserCompletionContext PCC)
static void AddInterfaceResults(DeclContext *Ctx, DeclContext *CurContext, bool OnlyForwardDeclarations, bool OnlyUnimplemented, ResultBuilder &Results)
Add all of the Objective-C interface declarations that we find in the given (translation unit) contex...
static OverloadCompare compareOverloads(const CXXMethodDecl &Candidate, const CXXMethodDecl &Incumbent, const Qualifiers &ObjectQuals, ExprValueKind ObjectKind, const ASTContext &Ctx)
static const FieldDecl * lookupDirectField(RecordDecl *RD, const Designator &D)
static void AddTemplateParameterChunks(ASTContext &Context, const PrintingPolicy &Policy, const TemplateDecl *Template, CodeCompletionBuilder &Result, unsigned MaxParameters=0, unsigned Start=0, bool InDefaultArg=false, bool AsInformativeChunk=false)
Add template parameter chunks to the given code completion string.
static void FindImplementableMethods(ASTContext &Context, ObjCContainerDecl *Container, std::optional< bool > WantInstanceMethods, QualType ReturnType, KnownMethodsMap &KnownMethods, bool InOriginalClass=true)
Find all of the methods that reside in the given container (and its superclasses, protocols,...
static bool anyNullArguments(ArrayRef< Expr * > Args)
static const char * noUnderscoreAttrScope(llvm::StringRef Scope)
static void AddFunctionTypeQuals(CodeCompletionBuilder &Result, const Qualifiers Quals, bool AsInformativeChunk=true)
static void MaybeAddSentinel(Preprocessor &PP, const NamedDecl *FunctionOrMethod, CodeCompletionBuilder &Result)
static void AddOverloadParameterChunks(ASTContext &Context, const PrintingPolicy &Policy, const FunctionDecl *Function, const FunctionProtoType *Prototype, FunctionProtoTypeLoc PrototypeLoc, CodeCompletionBuilder &Result, unsigned CurrentArg, unsigned Start=0, bool InOptional=false)
Add function overload parameter chunks to the given code completion string.
static void AddObjCProperties(const CodeCompletionContext &CCContext, ObjCContainerDecl *Container, bool AllowCategories, bool AllowNullaryMethods, DeclContext *CurContext, AddedPropertiesSet &AddedProperties, ResultBuilder &Results, bool IsBaseExprStatement=false, bool IsClassProperty=false, bool InOriginalClass=true)
static void HandleCodeCompleteResults(Sema *S, CodeCompleteConsumer *CodeCompleter, const CodeCompletionContext &Context, CodeCompletionResult *Results, unsigned NumResults)
static void AddTypeQualifierResults(DeclSpec &DS, ResultBuilder &Results, const LangOptions &LangOpts)
static void MaybeAddOverrideCalls(Sema &S, DeclContext *InContext, ResultBuilder &Results)
If we're in a C++ virtual member function, add completion results that invoke the functions we overri...
static ObjCContainerDecl * getContainerDef(ObjCContainerDecl *Container)
Retrieve the container definition, if any?
static const char * underscoreAttrScope(llvm::StringRef Scope)
static bool isAcceptableObjCMethod(ObjCMethodDecl *Method, ObjCMethodKind WantKind, ArrayRef< const IdentifierInfo * > SelIdents, bool AllowSameLength=true)
static void AddFunctionExceptSpecToCompletionString(std::string &NameAndSignature, const FunctionDecl *Function)
static void AddObjCExpressionResults(ResultBuilder &Results, bool NeedAt)
static bool WantTypesInContext(SemaCodeCompletion::ParserCompletionContext CCC, const LangOptions &LangOpts)
CodeCompleteConsumer::OverloadCandidate ResultCandidate
static std::string templateResultType(const TemplateDecl *TD, const PrintingPolicy &Policy)
static void AddTypedNameChunk(ASTContext &Context, const PrintingPolicy &Policy, const NamedDecl *ND, CodeCompletionBuilder &Result)
Add the name of the given declaration.
static void AddClassMessageCompletions(Sema &SemaRef, Scope *S, ParsedType Receiver, ArrayRef< const IdentifierInfo * > SelIdents, bool AtArgumentExpression, bool IsSuper, ResultBuilder &Results)
static const char * GetCompletionTypeString(QualType T, ASTContext &Context, const PrintingPolicy &Policy, CodeCompletionAllocator &Allocator)
Retrieve the string representation of the given type as a string that has the appropriate lifetime fo...
static bool InheritsFromClassNamed(ObjCInterfaceDecl *Class, StringRef Name)
Determine whether the given class is or inherits from a class by the given name.
#define OBJC_AT_KEYWORD_NAME(NeedAt, Keyword)
Macro that optionally prepends an "@" to the string literal passed in via Keyword,...
static bool isAcceptableObjCSelector(Selector Sel, ObjCMethodKind WantKind, ArrayRef< const IdentifierInfo * > SelIdents, bool AllowSameLength=true)
static QualType getPreferredTypeOfBinaryRHS(Sema &S, Expr *LHS, tok::TokenKind Op)
static void AddOrdinaryNameResults(SemaCodeCompletion::ParserCompletionContext CCC, Scope *S, Sema &SemaRef, ResultBuilder &Results)
Add language constructs that show up for "ordinary" names.
static QualType getPreferredTypeOfUnaryArg(Sema &S, QualType ContextType, tok::TokenKind Op)
Get preferred type for an argument of an unary expression.
static void AddUsingAliasResult(CodeCompletionBuilder &Builder, ResultBuilder &Results)
static ObjCInterfaceDecl * GetAssumedMessageSendExprType(Expr *E)
When we have an expression with type "id", we may assume that it has some more-specific class type ba...
ObjCMethodKind
Describes the kind of Objective-C method that we want to find via code completion.
@ MK_OneArgSelector
One-argument selector.
@ MK_ZeroArgSelector
Zero-argument (unary) selector.
@ MK_Any
Any kind of method, provided it means other specified criteria.
static void mergeCandidatesWithResults(Sema &SemaRef, SmallVectorImpl< ResultCandidate > &Results, OverloadCandidateSet &CandidateSet, SourceLocation Loc, size_t ArgSize)
static void AddProtocolResults(DeclContext *Ctx, DeclContext *CurContext, bool OnlyForwardDeclarations, ResultBuilder &Results)
Add all of the protocol declarations that we find in the given (translation unit) context.
static void AddStaticAssertResult(CodeCompletionBuilder &Builder, ResultBuilder &Results, const LangOptions &LangOpts)
static void AddObjCInterfaceResults(const LangOptions &LangOpts, ResultBuilder &Results, bool NeedAt)
static bool isNamespaceScope(Scope *S)
Determine whether this scope denotes a namespace.
static PrintingPolicy getCompletionPrintingPolicy(const ASTContext &Context, const Preprocessor &PP)
This file declares facilities that support code completion.
This file declares semantic analysis for Objective-C.
static TemplateDecl * getDescribedTemplate(Decl *Templated)
Defines various enumerations that describe declaration and type specifiers.
C Language Family Type Representation.
friend bool operator!=(const iterator &X, const iterator &Y)
iterator(const NamedDecl *SingleDecl, unsigned Index)
iterator(const DeclIndexPair *Iterator)
friend bool operator==(const iterator &X, const iterator &Y)
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Definition ASTContext.h:239
static CanQualType getCanonicalType(QualType T)
Return the canonical (structural) type corresponding to the specified potentially non-canonical type ...
QualType getPointerType(QualType T) const
Return the uniqued reference to the type for a pointer to the specified type.
QualType getBaseElementType(const ArrayType *VAT) const
Return the innermost element type of an array type.
QualType getPointerDiffType() const
Return the unique type for "ptrdiff_t" (C99 7.17) defined in <stddef.h>.
CanQualType BoolTy
CanQualType IntTy
QualType getTagType(ElaboratedTypeKeyword Keyword, NestedNameSpecifier Qualifier, const TagDecl *TD, bool OwnsTag) const
static bool hasSameUnqualifiedType(QualType T1, QualType T2)
Determine whether the given types are equivalent after cvr-qualifiers have been removed.
const RawComment * getRawCommentForAnyRedecl(RawCommentLookupKey Key, const Decl **OriginalDecl=nullptr) const
Return the documentation comment attached to a given declaration or macro.
PtrTy get() const
Definition Ownership.h:171
bool isInvalid() const
Definition Ownership.h:167
bool isUsable() const
Definition Ownership.h:169
Represents an array type, per C99 6.7.5.2 - Array Declarators.
Definition TypeBase.h:3800
QualType getElementType() const
Definition TypeBase.h:3812
Syntax
The style used to specify an attribute.
Type source information for an attributed type.
Definition TypeLoc.h:1008
Represents a block literal declaration, which is like an unnamed FunctionDecl.
Definition Decl.h:4807
Wrapper for source info for block pointers.
Definition TypeLoc.h:1557
Pointer to a block type.
Definition TypeBase.h:3633
This class is used for builtin types like 'int'.
Definition TypeBase.h:3241
Represents a base class of a C++ class.
Definition DeclCXX.h:146
Represents a C++ constructor within a class.
Definition DeclCXX.h:2641
bool isArrow() const
Determine whether this member expression used the '->' operator; otherwise, it used the '.
Definition ExprCXX.h:4022
DeclarationName getMember() const
Retrieve the name of the member that this expression refers to.
Definition ExprCXX.h:4061
Represents a static or instance method of a struct/union/class.
Definition DeclCXX.h:2149
overridden_method_range overridden_methods() const
Definition DeclCXX.cpp:2828
RefQualifierKind getRefQualifier() const
Retrieve the ref-qualifier associated with this method.
Definition DeclCXX.h:2342
Qualifiers getMethodQualifiers() const
Definition DeclCXX.h:2327
Represents a C++ struct/union/class.
Definition DeclCXX.h:258
bool isAggregate() const
Determine whether this class is an aggregate (C++ [dcl.init.aggr]), which is a class with no user-dec...
Definition DeclCXX.h:1152
base_class_range bases()
Definition DeclCXX.h:608
CXXRecordDecl * getDefinition() const
Definition DeclCXX.h:548
base_class_range vbases()
Definition DeclCXX.h:625
CXXRecordDecl * getCanonicalDecl() override
Retrieves the "canonical" declaration of the given declaration.
Definition DeclCXX.h:522
bool isDerivedFrom(const CXXRecordDecl *Base) const
Determine whether this class is derived from the class Base.
Represents a C++ nested-name-specifier or a global scope specifier.
Definition DeclSpec.h:76
NestedNameSpecifier getScopeRep() const
Retrieve the representation of the nested-name-specifier.
Definition DeclSpec.h:97
bool isInvalid() const
An error occurred during parsing of the scope specifier.
Definition DeclSpec.h:186
bool isEmpty() const
No scope specifier.
Definition DeclSpec.h:181
Expr * getCallee()
Definition Expr.h:3134
arg_range arguments()
Definition Expr.h:3239
bool isNull() const
CaseStmt - Represent a case statement.
Definition Stmt.h:1932
Expr * getLHS()
Definition Stmt.h:2015
Represents a byte-granular source range.
static CharSourceRange getTokenRange(SourceRange R)
Declaration of a class template.
CodeCompletionString * CreateSignatureString(unsigned CurrentArg, Sema &S, CodeCompletionAllocator &Allocator, CodeCompletionTUInfo &CCTUInfo, bool IncludeBriefComments, bool Braced) const
Create a new code-completion string that describes the function signature of this overload candidate.
const FunctionType * getFunctionType() const
Retrieve the function type of the entity, regardless of how the function is stored.
CandidateKind getKind() const
Determine the kind of overload candidate.
const RecordDecl * getAggregate() const
Retrieve the aggregate type being initialized.
FunctionDecl * getFunction() const
Retrieve the function overload candidate or the templated function declaration for a function templat...
const FunctionProtoTypeLoc getFunctionProtoTypeLoc() const
Retrieve the function ProtoTypeLoc candidate.
@ CK_Aggregate
The candidate is aggregate initialization of a record type.
@ CK_Template
The candidate is a template, template arguments are being completed.
unsigned getNumParams() const
Get the number of parameters in this signature.
Abstract interface for a consumer of code-completion information.
bool includeGlobals() const
Whether to include global (top-level) declaration results.
virtual void ProcessCodeCompleteResults(Sema &S, CodeCompletionContext Context, CodeCompletionResult *Results, unsigned NumResults)
Process the finalized code-completion results.
bool loadExternal() const
Hint whether to load data from the external AST in order to provide full results.
virtual void ProcessOverloadCandidates(Sema &S, unsigned CurrentArg, OverloadCandidate *Candidates, unsigned NumCandidates, SourceLocation OpenParLoc, bool Braced)
An allocator used specifically for the purpose of code completion.
const char * CopyString(const Twine &String)
Copy the given string into this allocator.
A builder class used to construct new code-completion strings.
CodeCompletionString * TakeString()
Take the resulting completion string.
void AddPlaceholderChunk(const char *Placeholder)
Add a new placeholder chunk.
void AddTextChunk(const char *Text)
Add a new text chunk.
void AddCurrentParameterChunk(const char *CurrentParameter)
Add a new current-parameter chunk.
void AddOptionalChunk(CodeCompletionString *Optional)
Add a new optional chunk.
void AddTypedTextChunk(const char *Text)
Add a new typed-text chunk.
void AddChunk(CodeCompletionString::ChunkKind CK, const char *Text="")
Add a new chunk.
CodeCompletionAllocator & getAllocator() const
Retrieve the allocator into which the code completion strings should be allocated.
The context in which code completion occurred, so that the code-completion consumer can process the r...
Kind getKind() const
Retrieve the kind of code-completion context.
void setCXXScopeSpecifier(CXXScopeSpec SS)
Sets the scope specifier that comes before the completion token.
@ CCC_TypeQualifiers
Code completion within a type-qualifier list.
@ CCC_ObjCMessageReceiver
Code completion occurred where an Objective-C message receiver is expected.
@ CCC_PreprocessorExpression
Code completion occurred within a preprocessor expression.
@ CCC_ObjCCategoryName
Code completion where an Objective-C category name is expected.
@ CCC_ObjCIvarList
Code completion occurred within the instance variable list of an Objective-C interface,...
@ CCC_Statement
Code completion occurred where a statement (or declaration) is expected in a function,...
@ CCC_Type
Code completion occurred where a type name is expected.
@ CCC_ArrowMemberAccess
Code completion occurred on the right-hand side of a member access expression using the arrow operato...
@ CCC_ClassStructUnion
Code completion occurred within a class, struct, or union.
@ CCC_ObjCInterface
Code completion occurred within an Objective-C interface, protocol, or category interface.
@ CCC_ObjCPropertyAccess
Code completion occurred on the right-hand side of an Objective-C property access expression.
@ CCC_Expression
Code completion occurred where an expression is expected.
@ CCC_SelectorName
Code completion for a selector, as in an @selector expression.
@ CCC_TopLevelOrExpression
Code completion at a top level, i.e.
@ CCC_EnumTag
Code completion occurred after the "enum" keyword, to indicate an enumeration name.
@ CCC_UnionTag
Code completion occurred after the "union" keyword, to indicate a union name.
@ CCC_ParenthesizedExpression
Code completion in a parenthesized expression, which means that we may also have types here in C and ...
@ CCC_TopLevel
Code completion occurred within a "top-level" completion context, e.g., at namespace or global scope.
@ CCC_ClassOrStructTag
Code completion occurred after the "struct" or "class" keyword, to indicate a struct or class name.
@ CCC_ObjCClassMessage
Code completion where an Objective-C class message is expected.
@ CCC_ObjCImplementation
Code completion occurred within an Objective-C implementation or category implementation.
@ CCC_IncludedFile
Code completion inside the filename part of a include directive.
@ CCC_ObjCInstanceMessage
Code completion where an Objective-C instance message is expected.
@ CCC_SymbolOrNewName
Code completion occurred where both a new name and an existing symbol is permissible.
@ CCC_Recovery
An unknown context, in which we are recovering from a parsing error and don't know which completions ...
@ CCC_ObjCProtocolName
Code completion occurred where a protocol name is expected.
@ CCC_NewName
Code completion occurred where a new name is expected.
@ CCC_MacroNameUse
Code completion occurred where a macro name is expected (without any arguments, in the case of a func...
@ CCC_Symbol
Code completion occurred where an existing name(such as type, functionor variable) is expected.
@ CCC_Attribute
Code completion of an attribute name.
@ CCC_Other
An unspecified code-completion context.
@ CCC_DotMemberAccess
Code completion occurred on the right-hand side of a member access expression using the dot operator.
@ CCC_MacroName
Code completion occurred where an macro is being defined.
@ CCC_Namespace
Code completion occurred where a namespace or namespace alias is expected.
@ CCC_PreprocessorDirective
Code completion occurred where a preprocessor directive is expected.
@ CCC_NaturalLanguage
Code completion occurred in a context where natural language is expected, e.g., a comment or string l...
@ CCC_ObjCInterfaceName
Code completion where the name of an Objective-C class is expected.
QualType getBaseType() const
Retrieve the type of the base object in a member-access expression.
bool wantConstructorResults() const
Determines whether we want C++ constructors as results within this context.
Captures a result of code completion.
bool DeclaringEntity
Whether we're completing a declaration of the given entity, rather than a use of that entity.
ResultKind Kind
The kind of result stored here.
const char * Keyword
When Kind == RK_Keyword, the string representing the keyword or symbol's spelling.
CXAvailabilityKind Availability
The availability of this result.
CodeCompletionString * CreateCodeCompletionString(Sema &S, const CodeCompletionContext &CCContext, CodeCompletionAllocator &Allocator, CodeCompletionTUInfo &CCTUInfo, bool IncludeBriefComments)
Create a new code-completion string that describes how to insert this result into a program.
bool QualifierIsInformative
Whether this result was found via lookup into a base class.
NestedNameSpecifier Qualifier
If the result should have a nested-name-specifier, this is it.
const NamedDecl * Declaration
When Kind == RK_Declaration or RK_Pattern, the declaration we are referring to.
CodeCompletionString * createCodeCompletionStringForDecl(Preprocessor &PP, ASTContext &Ctx, CodeCompletionBuilder &Result, bool IncludeBriefComments, const CodeCompletionContext &CCContext, PrintingPolicy &Policy)
CodeCompletionString * CreateCodeCompletionStringForMacro(Preprocessor &PP, CodeCompletionAllocator &Allocator, CodeCompletionTUInfo &CCTUInfo)
Creates a new code-completion string for the macro result.
unsigned StartParameter
Specifies which parameter (of a function, Objective-C method, macro, etc.) we should start with when ...
unsigned Priority
The priority of this particular code-completion result.
bool StartsNestedNameSpecifier
Whether this declaration is the beginning of a nested-name-specifier and, therefore,...
CodeCompletionString * Pattern
When Kind == RK_Pattern, the code-completion string that describes the completion text to insert.
bool FunctionCanBeCall
When completing a function, whether it can be a call.
bool AllParametersAreInformative
Whether all parameters (of a function, Objective-C method, etc.) should be considered "informative".
CodeCompletionString * createCodeCompletionStringForOverride(Preprocessor &PP, ASTContext &Ctx, CodeCompletionBuilder &Result, bool IncludeBriefComments, const CodeCompletionContext &CCContext, PrintingPolicy &Policy)
const IdentifierInfo * Macro
When Kind == RK_Macro, the identifier that refers to a macro.
@ RK_Pattern
Refers to a precomputed pattern.
@ RK_Declaration
Refers to a declaration.
@ RK_Keyword
Refers to a keyword or symbol.
A "string" used to describe how code completion can be performed for an entity.
@ CK_Optional
A code completion string that is entirely optional.
@ CK_CurrentParameter
A piece of text that describes the parameter that corresponds to the code-completion location within ...
@ CK_Comma
A comma separator (',').
@ CK_Placeholder
A string that acts as a placeholder for, e.g., a function call argument.
@ CK_LeftParen
A left parenthesis ('(').
@ CK_HorizontalSpace
Horizontal whitespace (' ').
@ CK_RightAngle
A right angle bracket ('>').
@ CK_LeftBracket
A left bracket ('[').
@ CK_RightParen
A right parenthesis (')').
@ CK_RightBrace
A right brace ('}').
@ CK_VerticalSpace
Vertical whitespace ('\n' or '\r\n', depending on the platform).
@ CK_TypedText
The piece of text that the user is expected to type to match the code-completion string,...
@ CK_RightBracket
A right bracket (']').
@ CK_LeftAngle
A left angle bracket ('<').
Expr * getConstraintExpr() const
const TypeClass * getTypePtr() const
Definition TypeLoc.h:433
static DeclAccessPair make(NamedDecl *D, AccessSpecifier AS)
specific_decl_iterator - Iterates over a subrange of declarations stored in a DeclContext,...
Definition DeclBase.h:2423
DeclContext - This is used only as base class of specific decl types that can act as declaration cont...
Definition DeclBase.h:1466
DeclContext * getParent()
getParent - Returns the containing DeclContext.
Definition DeclBase.h:2126
bool Equals(const DeclContext *DC) const
Determine whether this declaration context is equivalent to the declaration context DC.
Definition DeclBase.h:2259
bool isRequiresExprBody() const
Definition DeclBase.h:2211
bool isFileContext() const
Definition DeclBase.h:2197
DeclContextLookupResult lookup_result
Definition DeclBase.h:2607
ASTContext & getParentASTContext() const
Definition DeclBase.h:2155
bool isDependentContext() const
Determines whether this context is dependent on a template parameter.
lookup_result lookup(DeclarationName Name) const
lookup - Find the declarations (if any) with the given Name in this context.
bool isTranslationUnit() const
Definition DeclBase.h:2202
bool isRecord() const
Definition DeclBase.h:2206
DeclContext * getRedeclContext()
getRedeclContext - Retrieve the context in which an entity conflicts with other entities of the same ...
decl_iterator decls_end() const
Definition DeclBase.h:2405
decl_range decls() const
decls_begin/decls_end - Iterate over the declarations stored in this context.
Definition DeclBase.h:2403
bool isFunctionOrMethod() const
Definition DeclBase.h:2178
bool Encloses(const DeclContext *DC) const
Determine whether this declaration context semantically encloses the declaration context DC.
decl_iterator decls_begin() const
iterator begin()
Definition DeclGroup.h:95
Captures information about "declaration specifiers".
Definition DeclSpec.h:220
static const TST TST_typename
Definition DeclSpec.h:279
TST getTypeSpecType() const
Definition DeclSpec.h:522
static const TST TST_interface
Definition DeclSpec.h:277
unsigned getTypeQualifiers() const
getTypeQualifiers - Return a set of TQs.
Definition DeclSpec.h:602
static const TST TST_union
Definition DeclSpec.h:275
TSC getTypeSpecComplex() const
Definition DeclSpec.h:518
ParsedType getRepAsType() const
Definition DeclSpec.h:532
static const TST TST_enum
Definition DeclSpec.h:274
static const TST TST_class
Definition DeclSpec.h:278
TypeSpecifierType TST
Definition DeclSpec.h:250
unsigned getParsedSpecifiers() const
Return a bitmask of which flavors of specifiers this DeclSpec includes.
Definition DeclSpec.cpp:442
bool isTypeAltiVecVector() const
Definition DeclSpec.h:523
TypeSpecifierSign getTypeSpecSign() const
Definition DeclSpec.h:519
static const TST TST_struct
Definition DeclSpec.h:276
Decl - This represents one declaration (or definition), e.g.
Definition DeclBase.h:86
FriendObjectKind getFriendObjectKind() const
Determines whether this declaration is the object of a friend declaration and, if so,...
Definition DeclBase.h:1243
T * getAttr() const
Definition DeclBase.h:581
ASTContext & getASTContext() const LLVM_READONLY
Definition DeclBase.cpp:550
@ FOK_Undeclared
A friend of a previously-undeclared entity.
Definition DeclBase.h:1236
FunctionDecl * getAsFunction() LLVM_READONLY
Returns the function itself, or the templated function if this is a function template.
Definition DeclBase.cpp:273
ObjCDeclQualifier
ObjCDeclQualifier - 'Qualifiers' written next to the return and parameter types in method declaration...
Definition DeclBase.h:198
@ OBJC_TQ_CSNullability
The nullability qualifier is set when the nullability of the result or parameter was expressed via a ...
Definition DeclBase.h:210
unsigned getIdentifierNamespace() const
Definition DeclBase.h:906
llvm::iterator_range< specific_attr_iterator< T > > specific_attrs() const
Definition DeclBase.h:567
SourceLocation getLocation() const
Definition DeclBase.h:447
@ IDNS_Ordinary
Ordinary names.
Definition DeclBase.h:144
@ IDNS_Member
Members, declared with object declarations within tag definitions.
Definition DeclBase.h:136
@ IDNS_ObjCProtocol
Objective C @protocol.
Definition DeclBase.h:147
@ IDNS_Namespace
Namespaces, declared with 'namespace foo {}'.
Definition DeclBase.h:140
@ IDNS_LocalExtern
This declaration is a function-local extern declaration of a variable or function.
Definition DeclBase.h:175
@ IDNS_Tag
Tags, declared with 'struct foo;' and referenced with 'struct foo'.
Definition DeclBase.h:125
DeclContext * getDeclContext()
Definition DeclBase.h:456
AccessSpecifier getAccess() const
Definition DeclBase.h:515
DeclContext * getLexicalDeclContext()
getLexicalDeclContext - The declaration context where this Decl was lexically declared (LexicalDC).
Definition DeclBase.h:935
virtual Decl * getCanonicalDecl()
Retrieves the "canonical" declaration of the given declaration.
Definition DeclBase.h:995
Kind getKind() const
Definition DeclBase.h:450
The name of a declaration.
IdentifierInfo * getAsIdentifierInfo() const
Retrieve the IdentifierInfo * stored in this declaration name, or null if this declaration name isn't...
void print(raw_ostream &OS, const PrintingPolicy &Policy) const
OverloadedOperatorKind getCXXOverloadedOperator() const
If this name is the name of an overloadable operator in C++ (e.g., operator+), retrieve the kind of o...
QualType getCXXNameType() const
If this name is one of the C++ names (of a constructor, destructor, or conversion function),...
NameKind getNameKind() const
Determine what kind of name this is.
bool isIdentifier() const
Predicate functions for querying what type of name this is.
Represents a ValueDecl that came out of a declarator.
Definition Decl.h:781
Information about one declarator, including the parsed type information and the identifier.
Definition DeclSpec.h:1952
bool isFunctionDeclarator(unsigned &idx) const
isFunctionDeclarator - This method returns true if the declarator is a function declarator (looking t...
Definition DeclSpec.h:2508
DeclaratorContext getContext() const
Definition DeclSpec.h:2124
bool isCtorOrDtor()
Returns true if this declares a constructor or a destructor.
Definition DeclSpec.cpp:410
UnqualifiedId & getName()
Retrieve the name specified by this declarator.
Definition DeclSpec.h:2118
bool isStaticMember()
Returns true if this declares a static member.
Definition DeclSpec.cpp:389
DeclaratorChunk::FunctionTypeInfo & getFunctionTypeInfo()
getFunctionTypeInfo - Retrieves the function type info object (looking through parentheses).
Definition DeclSpec.h:2539
NestedNameSpecifier getQualifier() const
Retrieve the nested-name-specifier that qualifies this declaration.
Definition ExprCXX.h:3615
DeclarationName getDeclName() const
Retrieve the name that this expression refers to.
Definition ExprCXX.h:3602
Designation - Represent a full designation, which is a sequence of designators.
Definition Designator.h:221
const Designator & getDesignator(unsigned Idx) const
Definition Designator.h:232
unsigned getNumDesignators() const
Definition Designator.h:231
Designator - A designator in a C99 designated initializer.
Definition Designator.h:38
const IdentifierInfo * getFieldDecl() const
Definition Designator.h:123
DirectoryLookup - This class represents one entry in the search list that specifies the search order ...
virtual bool TraverseNestedNameSpecifierLoc(NestedNameSpecifierLoc NNS)
Represents an enum.
Definition Decl.h:4146
This represents one expression.
Definition Expr.h:113
Expr * IgnoreParenCasts() LLVM_READONLY
Skip past any parentheses and casts which might surround this expression until reaching a fixed point...
Definition Expr.cpp:3128
bool isTypeDependent() const
Determines whether the type of this expression depends on.
Definition Expr.h:195
QualType getType() const
Definition Expr.h:145
virtual Selector GetExternalSelector(uint32_t ID)
Resolve a selector ID into a selector.
virtual uint32_t GetNumExternalSelectors()
Returns the number of selectors known to the external AST source.
Represents a member of a struct/union/class.
Definition Decl.h:3295
static FixItHint CreateReplacement(CharSourceRange RemoveRange, StringRef Code)
Create a code modification hint that replaces the given source range with the given code string.
Definition Diagnostic.h:142
Represents a function declaration or definition.
Definition Decl.h:2059
const ParmVarDecl * getParamDecl(unsigned i) const
Definition Decl.h:2928
unsigned getMinRequiredArguments() const
Returns the minimum number of arguments needed to call this function.
Definition Decl.cpp:3891
ArrayRef< ParmVarDecl * > parameters() const
Definition Decl.h:2905
bool isVariadic() const
Whether this function is variadic.
Definition Decl.cpp:3121
unsigned getNumParams() const
Return the number of parameters this function must have based on its FunctionType.
Definition Decl.cpp:3870
Represents a prototype with parameter type info, e.g.
Definition TypeBase.h:5385
ExceptionSpecInfo getExceptionSpecInfo() const
Return all the available information about this type's exception spec.
Definition TypeBase.h:5718
bool isVariadic() const
Whether this function prototype is variadic.
Definition TypeBase.h:5789
Declaration of a template function.
Wrapper for source info for functions.
Definition TypeLoc.h:1675
unsigned getNumParams() const
Definition TypeLoc.h:1747
ParmVarDecl * getParam(unsigned i) const
Definition TypeLoc.h:1753
TypeLoc getReturnLoc() const
Definition TypeLoc.h:1756
FunctionType - C99 6.7.5.3 - Function Declarators.
Definition TypeBase.h:4581
QualType getReturnType() const
Definition TypeBase.h:4921
QualType simplifyType(QualType Type, const Expr *E, bool UnwrapPointer)
TagDecl * resolveTypeToTagDecl(QualType T) const
QualType resolveExprToType(const Expr *E) const
One of these records is kept for each identifier that is lexed.
unsigned getLength() const
Efficiently return the length of this identifier info.
bool isStr(const char(&Str)[StrLen]) const
Return true if this is the identifier for the specified string.
StringRef deuglifiedName() const
If the identifier is an "uglified" reserved name, return a cleaned form.
StringRef getName() const
Return the actual identifier string.
A simple pair of identifier info and location.
const TypeClass * getTypePtr() const
Definition TypeLoc.h:526
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
static StringRef getSourceText(CharSourceRange Range, const SourceManager &SM, const LangOptions &LangOpts, bool *Invalid=nullptr)
Returns a string for the source that the range encompasses.
Definition Lexer.cpp:1075
Represents the results of name lookup.
Definition Lookup.h:147
Encapsulates the data about a macro definition (e.g.
Definition MacroInfo.h:40
bool isC99Varargs() const
Definition MacroInfo.h:208
bool isFunctionLike() const
Definition MacroInfo.h:202
param_iterator param_begin() const
Definition MacroInfo.h:183
IdentifierInfo *const * param_iterator
Parameters - The list of parameters for a function-like macro.
Definition MacroInfo.h:181
bool isVariadic() const
Definition MacroInfo.h:210
param_iterator param_end() const
Definition MacroInfo.h:184
bool isUsedForHeaderGuard() const
Determine whether this macro was used for a header guard.
Definition MacroInfo.h:295
Describes a module or submodule.
Definition Module.h:340
@ AllVisible
All of the names in this module are visible.
Definition Module.h:647
ModuleKind Kind
The kind of this module.
Definition Module.h:385
llvm::iterator_range< submodule_iterator > submodules()
Definition Module.h:1067
@ ImplicitGlobalModuleFragment
This is an implicit fragment of the global module which contains only language linkage declarations (...
Definition Module.h:381
@ ModulePartitionInterface
This is a C++20 module partition interface.
Definition Module.h:366
@ ModuleInterfaceUnit
This is a C++20 module interface unit.
Definition Module.h:360
@ PrivateModuleFragment
This is the private module fragment within some C++ module.
Definition Module.h:376
@ ExplicitGlobalModuleFragment
This is the explicit Global Module Fragment of a modular TU.
Definition Module.h:373
This represents a decl that may have a name.
Definition Decl.h:275
NamedDecl * getUnderlyingDecl()
Looks through UsingDecls and ObjCCompatibleAliasDecls for the underlying named decl.
Definition Decl.h:488
IdentifierInfo * getIdentifier() const
Get the identifier that names this declaration, if there is one.
Definition Decl.h:296
StringRef getName() const
Get the name of identifier for this declaration as a StringRef.
Definition Decl.h:302
DeclarationName getDeclName() const
Get the actual, stored name of the declaration, which may be a special name.
Definition Decl.h:341
std::string getNameAsString() const
Get a human-readable name for the declaration, even if it is one of the special kinds of names (C++ c...
Definition Decl.h:318
ReservedIdentifierStatus isReserved(const LangOptions &LangOpts) const
Determine if the declaration obeys the reserved identifier rules of the given language.
Definition Decl.cpp:1133
Represent a C++ namespace.
Definition Decl.h:593
NestedNameSpecifier getNestedNameSpecifier() const
Retrieve the nested-name-specifier to which this instance refers.
Represents a C++ nested name specifier, such as "\::std::vector<int>::".
void print(raw_ostream &OS, const PrintingPolicy &Policy, bool ResolveTemplateArguments=false, bool PrintFinalScopeResOp=true) const
Print this nested name specifier to the given output stream.
bool isDependent() const
Whether this nested name specifier refers to a dependent type or not.
NonTypeTemplateParmDecl - Declares a non-type template parameter, e.g., "Size" in.
ObjCCategoryDecl - Represents a category declaration.
Definition DeclObjC.h:2335
ObjCCategoryImplDecl - An object of this class encapsulates a category @implementation declaration.
Definition DeclObjC.h:2551
ObjCContainerDecl - Represents a container for method declarations.
Definition DeclObjC.h:954
method_range methods() const
Definition DeclObjC.h:1022
instprop_range instance_properties() const
Definition DeclObjC.h:988
classprop_range class_properties() const
Definition DeclObjC.h:1005
Captures information about "declaration specifiers" specific to Objective-C.
Definition DeclSpec.h:911
ObjCPropertyAttribute::Kind getPropertyAttributes() const
Definition DeclSpec.h:945
ObjCDeclQualifier getObjCDeclQualifier() const
Definition DeclSpec.h:935
ObjCImplementationDecl - Represents a class definition - this is where method definitions are specifi...
Definition DeclObjC.h:2603
Represents an ObjC class declaration.
Definition DeclObjC.h:1160
bool hasDefinition() const
Determine whether this class has been defined.
Definition DeclObjC.h:1534
protocol_range protocols() const
Definition DeclObjC.h:1365
known_categories_range known_categories() const
Definition DeclObjC.h:1693
ObjCImplementationDecl * getImplementation() const
visible_categories_range visible_categories() const
Definition DeclObjC.h:1659
ObjCInterfaceDecl * getSuperClass() const
Definition DeclObjC.cpp:349
ObjCIvarDecl - Represents an ObjC instance variable.
Definition DeclObjC.h:1958
ObjCList - This is a simple template class used to hold various lists of decls etc,...
Definition DeclObjC.h:82
iterator end() const
Definition DeclObjC.h:91
iterator begin() const
Definition DeclObjC.h:90
T *const * iterator
Definition DeclObjC.h:88
@ SuperInstance
The receiver is the instance of the superclass object.
Definition ExprObjC.h:986
@ Instance
The receiver is an object instance.
Definition ExprObjC.h:980
@ SuperClass
The receiver is a superclass.
Definition ExprObjC.h:983
@ Class
The receiver is a class.
Definition ExprObjC.h:977
ObjCMethodDecl - Represents an instance or class method declaration.
Definition DeclObjC.h:140
unsigned param_size() const
Definition DeclObjC.h:350
param_const_iterator param_end() const
Definition DeclObjC.h:361
param_const_iterator param_begin() const
Definition DeclObjC.h:357
bool isVariadic() const
Definition DeclObjC.h:434
const ParmVarDecl *const * param_const_iterator
Definition DeclObjC.h:352
Selector getSelector() const
Definition DeclObjC.h:330
bool isInstanceMethod() const
Definition DeclObjC.h:429
ParmVarDecl *const * param_iterator
Definition DeclObjC.h:353
ObjCInterfaceDecl * getClassInterface()
Represents a pointer to an Objective C object.
Definition TypeBase.h:8059
ObjCInterfaceDecl * getInterfaceDecl() const
If this pointer points to an Objective @interface type, gets the declaration for that interface.
Definition TypeBase.h:8111
qual_range quals() const
Definition TypeBase.h:8178
Represents one property declaration in an Objective-C interface.
Definition DeclObjC.h:734
static ObjCPropertyDecl * findPropertyDecl(const DeclContext *DC, const IdentifierInfo *propertyID, ObjCPropertyQueryKind queryKind)
Lookup a property by name in the specified DeclContext.
Definition DeclObjC.cpp:176
Selector getGetterName() const
Definition DeclObjC.h:891
Represents an Objective-C protocol declaration.
Definition DeclObjC.h:2090
void * getAsOpaquePtr() const
Definition Ownership.h:91
PtrTy get() const
Definition Ownership.h:81
static OpaquePtr make(QualType P)
Definition Ownership.h:61
OverloadCandidateSet - A set of overload candidates, used in C++ overload resolution (C++ 13....
Definition Overload.h:1161
@ CSK_CodeCompletion
When doing overload resolution during code completion, we want to show all viable candidates,...
Definition Overload.h:1191
CandidateSetKind getKind() const
Definition Overload.h:1350
Represents a parameter to a function.
Definition Decl.h:1820
Represents the parsed form of a C++ template argument.
KindType getKind() const
Determine what kind of template argument we have.
@ Type
A template type parameter, stored as a type.
@ Template
A template template argument, stored as a template name.
@ NonType
A non-type template parameter, stored as an expression.
PointerType - C99 6.7.5.1 - Pointer Declarators.
Definition TypeBase.h:3396
void enterFunctionArgument(SourceLocation Tok, llvm::function_ref< QualType()> ComputeType)
Computing a type for the function argument may require running overloading, so we postpone its comput...
void enterCondition(Sema &S, SourceLocation Tok)
void enterTypeCast(SourceLocation Tok, QualType CastType)
Handles all type casts, including C-style cast, C++ casts, etc.
void enterMemAccess(Sema &S, SourceLocation Tok, Expr *Base)
void enterSubscript(Sema &S, SourceLocation Tok, Expr *LHS)
void enterUnary(Sema &S, SourceLocation Tok, tok::TokenKind OpKind, SourceLocation OpLoc)
void enterReturn(Sema &S, SourceLocation Tok)
void enterDesignatedInitializer(SourceLocation Tok, QualType BaseType, const Designation &D)
Handles e.g. BaseType{ .D = Tok...
void enterBinary(Sema &S, SourceLocation Tok, Expr *LHS, tok::TokenKind Op)
void enterParenExpr(SourceLocation Tok, SourceLocation LParLoc)
void enterVariableInit(SourceLocation Tok, Decl *D)
QualType get(SourceLocation Tok) const
Get the expected type associated with this location, if any.
Definition Sema.h:335
Engages in a tight little dance with the lexer to efficiently preprocess tokens.
const MacroInfo * getMacroInfo(const IdentifierInfo *II) const
llvm::iterator_range< macro_iterator > macros(bool IncludeExternalMacros=true) const
SourceManager & getSourceManager() const
MacroDefinition getMacroDefinition(const IdentifierInfo *II)
bool isMacroDefined(StringRef Id)
const LangOptions & getLangOpts() const
bool isCodeCompletionReached() const
Returns true if code-completion is enabled and we have hit the code-completion point.
A (possibly-)qualified type.
Definition TypeBase.h:938
bool isNull() const
Return true if this QualType doesn't point to a type yet.
Definition TypeBase.h:1005
const Type * getTypePtr() const
Retrieves a pointer to the underlying (unqualified) type.
Definition TypeBase.h:8418
void print(raw_ostream &OS, const PrintingPolicy &Policy, const Twine &PlaceHolder=Twine(), unsigned Indentation=0) const
void getAsStringInternal(std::string &Str, const PrintingPolicy &Policy) const
QualType getNonReferenceType() const
If Type is a reference type (e.g., const int&), returns the type that the reference refers to ("const...
Definition TypeBase.h:8603
QualType substObjCTypeArgs(ASTContext &ctx, ArrayRef< QualType > typeArgs, ObjCSubstitutionContext context) const
Substitute type arguments for the Objective-C type parameters used in the subject type.
Definition Type.cpp:1714
static std::string getAsString(SplitQualType split, const PrintingPolicy &Policy)
Definition TypeBase.h:1348
Wrapper of type source information for a type with non-trivial direct qualifiers.
Definition TypeLoc.h:300
The collection of all-type qualifiers we support.
Definition TypeBase.h:332
bool hasOnlyConst() const
Definition TypeBase.h:459
bool hasConst() const
Definition TypeBase.h:458
bool compatiblyIncludes(Qualifiers other, const ASTContext &Ctx) const
Determines if these qualifiers compatibly include another set.
Definition TypeBase.h:728
bool hasRestrict() const
Definition TypeBase.h:478
bool hasVolatile() const
Definition TypeBase.h:468
bool hasOnlyVolatile() const
Definition TypeBase.h:469
bool hasOnlyRestrict() const
Definition TypeBase.h:479
Represents a struct/union/class.
Definition Decl.h:4460
bool isLambda() const
Determine whether this record is a class describing a lambda function object.
Definition Decl.cpp:5310
field_range fields() const
Definition Decl.h:4663
Base for LValueReferenceType and RValueReferenceType.
Definition TypeBase.h:3658
QualType getPointeeType() const
Definition TypeBase.h:3680
Scope - A scope is a transient data structure that is used while parsing the program.
Definition Scope.h:41
bool isClassScope() const
isClassScope - Return true if this scope is a class/struct/union scope.
Definition Scope.h:414
const Scope * getFnParent() const
getFnParent - Return the closest scope that is a function body.
Definition Scope.h:284
unsigned getFlags() const
getFlags - Return the flags for this scope.
Definition Scope.h:269
Scope * getContinueParent()
getContinueParent - Return the closest scope that a continue statement would be affected by.
Definition Scope.h:294
bool isDeclScope(const Decl *D) const
isDeclScope - Return true if this is the scope that the specified decl is declared in.
Definition Scope.h:384
DeclContext * getEntity() const
Get the entity corresponding to this scope.
Definition Scope.h:387
bool isTemplateParamScope() const
isTemplateParamScope - Return true if this scope is a C++ template parameter scope.
Definition Scope.h:467
Scope * getBreakParent()
getBreakParent - Return the closest scope that a break statement would be affected by.
Definition Scope.h:308
decl_range decls() const
Definition Scope.h:342
const Scope * getParent() const
getParent - Return the scope that this is nested in.
Definition Scope.h:280
bool isClassInheritanceScope() const
Determines whether this scope is between inheritance colon and the real class/struct definition.
Definition Scope.h:418
@ FunctionPrototypeScope
This is a scope that corresponds to the parameters within a function prototype.
Definition Scope.h:85
@ AtCatchScope
This is a scope that corresponds to the Objective-C @catch statement.
Definition Scope.h:95
@ TemplateParamScope
This is a scope that corresponds to the template parameters of a C++ template.
Definition Scope.h:81
@ ClassScope
The scope of a struct/union/class definition.
Definition Scope.h:69
@ DeclScope
This is a scope that can contain a declaration.
Definition Scope.h:63
This table allows us to fully hide how we implement multi-keyword caching.
Selector getNullarySelector(const IdentifierInfo *ID)
Selector getSelector(unsigned NumArgs, const IdentifierInfo **IIV)
Can create any sort of selector.
Selector getUnarySelector(const IdentifierInfo *ID)
Smart pointer class that efficiently represents Objective-C method names.
StringRef getNameForSlot(unsigned argIndex) const
Retrieve the name at a given position in the selector.
const IdentifierInfo * getIdentifierInfoForSlot(unsigned argIndex) const
Retrieve the identifier at a given position in the selector.
bool isUnarySelector() const
bool isNull() const
Determine whether this is the empty selector.
unsigned getNumArgs() const
SemaBase(Sema &S)
Definition SemaBase.cpp:7
ASTContext & getASTContext() const
Definition SemaBase.cpp:9
Sema & SemaRef
Definition SemaBase.h:40
const LangOptions & getLangOpts() const
Definition SemaBase.cpp:11
void CodeCompleteObjCInstanceMessage(Scope *S, Expr *Receiver, ArrayRef< const IdentifierInfo * > SelIdents, bool AtArgumentExpression, ObjCInterfaceDecl *Super=nullptr)
void CodeCompleteObjCPropertySynthesizeIvar(Scope *S, IdentifierInfo *PropertyName)
void CodeCompleteAttribute(AttributeCommonInfo::Syntax Syntax, AttributeCompletion Completion=AttributeCompletion::Attribute, const IdentifierInfo *Scope=nullptr)
QualType ProduceTemplateArgumentSignatureHelp(TemplateTy, ArrayRef< ParsedTemplateArgument >, SourceLocation LAngleLoc)
QualType ProduceCtorInitMemberSignatureHelp(Decl *ConstructorDecl, CXXScopeSpec SS, ParsedType TemplateTypeTy, ArrayRef< Expr * > ArgExprs, IdentifierInfo *II, SourceLocation OpenParLoc, bool Braced)
void CodeCompleteObjCClassForwardDecl(Scope *S)
void CodeCompleteNamespaceAliasDecl(Scope *S)
void GatherGlobalCodeCompletions(CodeCompletionAllocator &Allocator, CodeCompletionTUInfo &CCTUInfo, SmallVectorImpl< CodeCompletionResult > &Results)
void CodeCompleteQualifiedId(Scope *S, CXXScopeSpec &SS, bool EnteringContext, bool IsUsingDeclaration, bool IsAddressOfOperand, bool IsInDeclarationContext, QualType BaseType, QualType PreferredType)
void CodeCompleteObjCAtStatement(Scope *S)
void CodeCompleteObjCMessageReceiver(Scope *S)
void CodeCompleteUsingDirective(Scope *S)
void CodeCompleteObjCProtocolDecl(Scope *S)
void CodeCompleteObjCPropertyFlags(Scope *S, ObjCDeclSpec &ODS)
ParserCompletionContext
Describes the context in which code completion occurs.
@ PCC_LocalDeclarationSpecifiers
Code completion occurs within a sequence of declaration specifiers within a function,...
@ PCC_MemberTemplate
Code completion occurs following one or more template headers within a class.
@ PCC_Condition
Code completion occurs within the condition of an if, while, switch, or for statement.
@ PCC_ParenthesizedExpression
Code completion occurs in a parenthesized expression, which might also be a type cast.
@ PCC_TopLevelOrExpression
Code completion occurs at top-level in a REPL session.
@ PCC_Class
Code completion occurs within a class, struct, or union.
@ PCC_ForInit
Code completion occurs at the beginning of the initialization statement (or expression) in a for loop...
@ PCC_Type
Code completion occurs where only a type is permitted.
@ PCC_ObjCImplementation
Code completion occurs within an Objective-C implementation or category implementation.
@ PCC_ObjCInterface
Code completion occurs within an Objective-C interface, protocol, or category.
@ PCC_Namespace
Code completion occurs at top-level or namespace context.
@ PCC_Expression
Code completion occurs within an expression.
@ PCC_RecoveryInFunction
Code completion occurs within the body of a function on a recovery path, where we do not have a speci...
@ PCC_ObjCInstanceVariableList
Code completion occurs within the list of instance variables in an Objective-C interface,...
@ PCC_Template
Code completion occurs following one or more template headers.
@ PCC_Statement
Code completion occurs within a statement, which may also be an expression or a declaration.
void CodeCompleteObjCAtDirective(Scope *S)
void CodeCompleteObjCPropertySetter(Scope *S)
void CodeCompleteLambdaIntroducer(Scope *S, LambdaIntroducer &Intro, bool AfterAmpersand)
void CodeCompleteObjCImplementationCategory(Scope *S, IdentifierInfo *ClassName, SourceLocation ClassNameLoc)
void CodeCompleteObjCInterfaceDecl(Scope *S)
void CodeCompleteFunctionQualifiers(DeclSpec &DS, Declarator &D, const VirtSpecifiers *VS=nullptr)
void CodeCompletePreprocessorMacroName(bool IsDefinition)
void CodeCompleteInPreprocessorConditionalExclusion(Scope *S)
void CodeCompleteObjCAtExpression(Scope *S)
void CodeCompleteTypeQualifiers(DeclSpec &DS)
void CodeCompleteObjCPropertyDefinition(Scope *S)
void CodeCompleteExpression(Scope *S, const CodeCompleteExpressionData &Data, bool IsAddressOfOperand=false)
Perform code-completion in an expression context when we know what type we're looking for.
void CodeCompleteObjCSuperMessage(Scope *S, SourceLocation SuperLoc, ArrayRef< const IdentifierInfo * > SelIdents, bool AtArgumentExpression)
CodeCompleteConsumer * CodeCompleter
Code-completion consumer.
void CodeCompleteAfterFunctionEquals(Declarator &D)
QualType ProduceConstructorSignatureHelp(QualType Type, SourceLocation Loc, ArrayRef< Expr * > Args, SourceLocation OpenParLoc, bool Braced)
OpaquePtr< TemplateName > TemplateTy
QualType ProduceCallSignatureHelp(Expr *Fn, ArrayRef< Expr * > Args, SourceLocation OpenParLoc)
Determines the preferred type of the current function argument, by examining the signatures of all po...
void CodeCompleteObjCMethodDeclSelector(Scope *S, bool IsInstanceMethod, bool AtParameterName, ParsedType ReturnType, ArrayRef< const IdentifierInfo * > SelIdents)
void CodeCompleteIncludedFile(llvm::StringRef Dir, bool IsAngled)
void CodeCompletePreprocessorMacroArgument(Scope *S, IdentifierInfo *Macro, MacroInfo *MacroInfo, unsigned Argument)
void CodeCompleteModuleImport(SourceLocation ImportLoc, ModuleIdPath Path)
void CodeCompleteObjCInterfaceCategory(Scope *S, IdentifierInfo *ClassName, SourceLocation ClassNameLoc)
void CodeCompleteObjCSelector(Scope *S, ArrayRef< const IdentifierInfo * > SelIdents)
void CodeCompleteConstructorInitializer(Decl *Constructor, ArrayRef< CXXCtorInitializer * > Initializers)
void CodeCompleteObjCImplementationDecl(Scope *S)
void CodeCompleteAfterIf(Scope *S, bool IsBracedThen)
void CodeCompleteObjCMethodDecl(Scope *S, std::optional< bool > IsInstanceMethod, ParsedType ReturnType)
void CodeCompleteOrdinaryName(Scope *S, ParserCompletionContext CompletionContext)
OpaquePtr< DeclGroupRef > DeclGroupPtrTy
void CodeCompleteObjCClassPropertyRefExpr(Scope *S, const IdentifierInfo &ClassName, SourceLocation ClassNameLoc, bool IsBaseExprStatement)
void CodeCompleteInitializer(Scope *S, Decl *D)
void CodeCompleteObjCProtocolReferences(ArrayRef< IdentifierLoc > Protocols)
void CodeCompleteDesignator(const QualType BaseType, llvm::ArrayRef< Expr * > InitExprs, const Designation &D)
Trigger code completion for a record of BaseType.
void CodeCompletePreprocessorDirective(bool InConditional)
SemaCodeCompletion(Sema &S, CodeCompleteConsumer *CompletionConsumer)
void CodeCompleteOffsetOfDesignator(QualType BaseType, const Designation &D)
Trigger code completion for a position inside a __builtin_offsetof member designator (after the type'...
void CodeCompleteBracketDeclarator(Scope *S)
void CodeCompleteObjCSuperclass(Scope *S, IdentifierInfo *ClassName, SourceLocation ClassNameLoc)
void CodeCompleteKeywordAfterIf(bool AfterExclaim) const
void CodeCompleteObjCAtVisibility(Scope *S)
void CodeCompleteTag(Scope *S, unsigned TagSpec)
void CodeCompleteObjCClassMessage(Scope *S, ParsedType Receiver, ArrayRef< const IdentifierInfo * > SelIdents, bool AtArgumentExpression, bool IsSuper=false)
void CodeCompleteObjCForCollection(Scope *S, DeclGroupPtrTy IterationVar)
void CodeCompleteMemberReferenceExpr(Scope *S, Expr *Base, Expr *OtherOpBase, SourceLocation OpLoc, bool IsArrow, bool IsBaseExprStatement, QualType PreferredType)
void CodeCompleteObjCPassingType(Scope *S, ObjCDeclSpec &DS, bool IsParameter)
void CodeCompleteObjCPropertyGetter(Scope *S)
void CodeCompleteDeclSpec(Scope *S, DeclSpec &DS, bool AllowNonIdentifiers, bool AllowNestedNameSpecifiers)
void CodeCompletePostfixExpression(Scope *S, ExprResult LHS, QualType PreferredType)
GlobalMethodPool MethodPool
Method Pool - allows efficient lookup when typechecking messages to "id".
Definition SemaObjC.h:220
void ReadMethodPool(Selector Sel)
Read the contents of the method pool for a given selector from external storage.
Sema - This implements semantic analysis and AST building for C.
Definition Sema.h:863
QualType getCurrentThisType()
Try to retrieve the type of the 'this' pointer.
bool IsOverload(FunctionDecl *New, FunctionDecl *Old, bool UseMemberUsingDeclRules, bool ConsiderCudaAttrs=true)
@ LookupOrdinaryName
Ordinary name lookup, which finds ordinary names (functions, variables, typedefs, etc....
Definition Sema.h:9370
@ LookupNestedNameSpecifierName
Look up of a name that precedes the '::' scope resolution operator in C++.
Definition Sema.h:9389
@ LookupMemberName
Member name lookup, which finds the names of class/struct/union members.
Definition Sema.h:9378
@ LookupTagName
Tag name lookup, which finds the names of enums, classes, structs, and unions.
Definition Sema.h:9373
@ LookupAnyName
Look up any declaration with any name.
Definition Sema.h:9415
Preprocessor & getPreprocessor() const
Definition Sema.h:934
ASTContext & Context
Definition Sema.h:1304
SemaObjC & ObjC()
Definition Sema.h:1516
ASTContext & getASTContext() const
Definition Sema.h:935
PrintingPolicy getPrintingPolicy() const
Retrieve a suitable printing policy for diagnostics.
Definition Sema.h:1208
ObjCMethodDecl * getCurMethodDecl()
getCurMethodDecl - If inside of a method body, this returns a pointer to the method decl for the meth...
Definition Sema.cpp:1773
const LangOptions & getLangOpts() const
Definition Sema.h:928
void LookupVisibleDecls(Scope *S, LookupNameKind Kind, VisibleDeclConsumer &Consumer, bool IncludeGlobalScope=true, bool LoadExternal=true)
SemaCodeCompletion & CodeCompletion()
Definition Sema.h:1466
Preprocessor & PP
Definition Sema.h:1303
sema::FunctionScopeInfo * getCurFunction() const
Definition Sema.h:1339
Module * getCurrentModule() const
Get the module unit whose scope we are currently within.
Definition Sema.h:9898
sema::BlockScopeInfo * getCurBlock()
Retrieve the current block, if any.
Definition Sema.cpp:2674
DeclContext * CurContext
CurContext - This is the current declaration context of parsing.
Definition Sema.h:1444
ExternalSemaSource * getExternalSource() const
Definition Sema.h:938
bool isAcceptableNestedNameSpecifier(const NamedDecl *SD, bool *CanCorrect=nullptr)
Determines whether the given declaration is an valid acceptable result for name lookup of a nested-na...
SourceManager & SourceMgr
Definition Sema.h:1307
static QualType GetTypeFromParser(ParsedType Ty, TypeSourceInfo **TInfo=nullptr)
void MarkDeducedTemplateParameters(const FunctionTemplateDecl *FunctionTemplate, llvm::SmallBitVector &Deduced)
Definition Sema.h:13001
Encodes a location in the source.
This class handles loading and caching of source files into memory.
SourceLocation getSpellingLoc(SourceLocation Loc) const
Given a SourceLocation object, return the spelling location referenced by the ID.
bool isInSystemHeader(SourceLocation Loc) const
Returns if a SourceLocation is in a system header.
A trivial tuple used to represent a source range.
SwitchStmt - This represents a 'switch' stmt.
Definition Stmt.h:2521
Represents the declaration of a struct/union/class/enum.
Definition Decl.h:3852
bool isCompleteDefinition() const
Return true if this decl has its body fully specified.
Definition Decl.h:3953
bool isUnion() const
Definition Decl.h:4063
A convenient class for passing around template argument information.
Represents a template argument.
QualType getAsType() const
Retrieve the type for a type template argument.
@ Type
The template argument is a type.
ArgKind getKind() const
Return the kind of stored template argument.
The base class of all kinds of template declarations (e.g., class, function, etc.).
TemplateParameterList * getTemplateParameters() const
Get the list of template parameters.
Represents a C++ template name within the type system.
Stores a list of template parameters for a TemplateDecl and its derived classes.
NamedDecl * getParam(unsigned Idx)
NamedDecl ** iterator
Iterates through the template parameters in this list.
bool hasParameterPack() const
Determine whether this template parameter list contains a parameter pack.
ArrayRef< NamedDecl * > asArray()
TemplateTemplateParmDecl - Declares a template template parameter, e.g., "T" in.
bool hasDefaultArgument() const
Determine whether this template parameter has a default argument.
Declaration of a template type parameter.
The top declaration context.
Definition Decl.h:106
void print(llvm::raw_ostream &OS, const PrintingPolicy &Policy) const
Definition ASTConcept.h:282
Represents a declaration of a type.
Definition Decl.h:3648
Base wrapper for a particular "section" of type source info.
Definition TypeLoc.h:59
UnqualTypeLoc getUnqualifiedLoc() const
Skips past any qualifiers, if this is qualified.
Definition TypeLoc.h:349
QualType getType() const
Get the type for which this source info wrapper provides information.
Definition TypeLoc.h:133
T getAs() const
Convert to the specified TypeLoc type, returning a null TypeLoc if this TypeLoc is not of the desired...
Definition TypeLoc.h:89
TypeLoc IgnoreParens() const
Definition TypeLoc.h:1468
T getAsAdjusted() const
Convert to the specified TypeLoc type, returning a null TypeLoc if this TypeLoc is not of the desired...
Definition TypeLoc.h:2766
A container of type source information.
Definition TypeBase.h:8389
TypeLoc getTypeLoc() const
Return the TypeLoc wrapper for the type source info.
Definition TypeLoc.h:267
The base class of the type hierarchy.
Definition TypeBase.h:1879
bool isBlockPointerType() const
Definition TypeBase.h:8675
bool isVoidType() const
Definition TypeBase.h:9027
bool isBooleanType() const
Definition TypeBase.h:9164
const ObjCObjectPointerType * getAsObjCQualifiedIdType() const
Definition Type.cpp:1948
CXXRecordDecl * getAsCXXRecordDecl() const
Retrieves the CXXRecordDecl that this type refers to, either because the type is a RecordType or beca...
Definition Type.h:26
RecordDecl * getAsRecordDecl() const
Retrieves the RecordDecl this type refers to.
Definition Type.h:41
bool isPointerType() const
Definition TypeBase.h:8655
CanQualType getCanonicalTypeUnqualified() const
bool isIntegerType() const
isIntegerType() does not include complex integers (a GCC extension).
Definition TypeBase.h:9071
const T * castAs() const
Member-template castAs<specific type>.
Definition TypeBase.h:9321
const ObjCObjectPointerType * getAsObjCInterfacePointerType() const
Definition Type.cpp:1976
NestedNameSpecifier getPrefix() const
If this type represents a qualified-id, this returns its nested name specifier.
Definition Type.cpp:2003
QualType getPointeeType() const
If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee.
Definition Type.cpp:789
bool isIntegralOrEnumerationType() const
Determine whether this type is an integral or enumeration type.
Definition TypeBase.h:9149
bool isObjCObjectOrInterfaceType() const
Definition TypeBase.h:8842
bool isMemberPointerType() const
Definition TypeBase.h:8736
bool isObjCIdType() const
Definition TypeBase.h:8867
bool isObjCObjectPointerType() const
Definition TypeBase.h:8834
bool isObjCQualifiedClassType() const
Definition TypeBase.h:8861
bool isObjCClassType() const
Definition TypeBase.h:8873
std::optional< ArrayRef< QualType > > getObjCSubstitutions(const DeclContext *dc) const
Retrieve the set of substitutions required when accessing a member of the Objective-C receiver type t...
Definition Type.cpp:1753
const T * getAs() const
Member-template getAs<specific type>'.
Definition TypeBase.h:9254
Wrapper for source info for typedefs.
Definition TypeLoc.h:777
Represents a C++ unqualified-id that has been parsed.
Definition DeclSpec.h:1039
void setIdentifier(const IdentifierInfo *Id, SourceLocation IdLoc)
Specify that this unqualified-id was parsed as an identifier.
Definition DeclSpec.h:1127
void append(iterator I, iterator E)
A set of unresolved declarations.
Represents a shadow declaration implicitly introduced into a scope by a (resolved) using-declaration ...
Definition DeclCXX.h:3428
Represent the declaration of a variable (in which case it is an lvalue) a function (in which case it ...
Definition Decl.h:713
QualType getType() const
Definition Decl.h:724
QualType getType() const
Definition Value.cpp:238
Represents a C++11 virt-specifier-seq.
Definition DeclSpec.h:2832
bool isOverrideSpecified() const
Definition DeclSpec.h:2851
bool isFinalSpecified() const
Definition DeclSpec.h:2854
Consumes visible declarations found when searching for all visible names within a given scope or cont...
Definition Lookup.h:838
Retains information about a block that is currently being parsed.
Definition ScopeInfo.h:791
QualType ReturnType
ReturnType - The target type of return statements in this context, or null if unknown.
Definition ScopeInfo.h:733
SmallVector< SwitchInfo, 8 > SwitchStack
SwitchStack - This is the current set of active switch statements in the block.
Definition ScopeInfo.h:214
@ CXCursor_ObjCInterfaceDecl
An Objective-C @interface.
Definition Index.h:1220
@ CXCursor_Namespace
A C++ namespace.
Definition Index.h:1242
@ CXCursor_TypedefDecl
A typedef.
Definition Index.h:1238
@ CXCursor_CXXAccessSpecifier
An access specifier.
Definition Index.h:1276
@ CXCursor_EnumConstantDecl
An enumerator constant.
Definition Index.h:1212
@ CXCursor_ConversionFunction
A C++ conversion function.
Definition Index.h:1250
@ CXCursor_ConceptDecl
a concept declaration.
Definition Index.h:2320
@ CXCursor_ClassTemplate
A C++ class template.
Definition Index.h:1260
@ CXCursor_UnionDecl
A C or C++ union.
Definition Index.h:1201
@ CXCursor_ObjCSynthesizeDecl
An Objective-C @synthesize definition.
Definition Index.h:1272
@ CXCursor_ParmDecl
A function or method parameter.
Definition Index.h:1218
@ CXCursor_FieldDecl
A field (in C) or non-static data member (in C++) in a struct, union, or C++ class.
Definition Index.h:1210
@ CXCursor_CXXMethod
A C++ class method.
Definition Index.h:1240
@ CXCursor_EnumDecl
An enumeration.
Definition Index.h:1205
@ CXCursor_ObjCClassMethodDecl
An Objective-C class method.
Definition Index.h:1232
@ CXCursor_TranslationUnit
Cursor that represents the translation unit itself.
Definition Index.h:2241
@ CXCursor_ClassTemplatePartialSpecialization
A C++ class template partial specialization.
Definition Index.h:1262
@ CXCursor_ObjCProtocolDecl
An Objective-C @protocol declaration.
Definition Index.h:1224
@ CXCursor_FunctionTemplate
A C++ function template.
Definition Index.h:1258
@ CXCursor_ObjCImplementationDecl
An Objective-C @implementation.
Definition Index.h:1234
@ CXCursor_NonTypeTemplateParameter
A C++ non-type template parameter.
Definition Index.h:1254
@ CXCursor_FunctionDecl
A function.
Definition Index.h:1214
@ CXCursor_ObjCPropertyDecl
An Objective-C @property declaration.
Definition Index.h:1226
@ CXCursor_Destructor
A C++ destructor.
Definition Index.h:1248
@ CXCursor_ObjCIvarDecl
An Objective-C instance variable.
Definition Index.h:1228
@ CXCursor_TypeAliasTemplateDecl
Definition Index.h:2308
@ CXCursor_ObjCCategoryImplDecl
An Objective-C @implementation for a category.
Definition Index.h:1236
@ CXCursor_ObjCDynamicDecl
An Objective-C @dynamic definition.
Definition Index.h:1274
@ CXCursor_MacroDefinition
Definition Index.h:2296
@ CXCursor_VarDecl
A variable.
Definition Index.h:1216
@ CXCursor_TemplateTypeParameter
A C++ template type parameter.
Definition Index.h:1252
@ CXCursor_TemplateTemplateParameter
A C++ template template parameter.
Definition Index.h:1256
@ CXCursor_UnexposedDecl
A declaration whose specific kind is not exposed via this interface.
Definition Index.h:1197
@ CXCursor_ObjCInstanceMethodDecl
An Objective-C instance method.
Definition Index.h:1230
@ CXCursor_StructDecl
A C or C++ struct.
Definition Index.h:1199
@ CXCursor_UsingDeclaration
A C++ using declaration.
Definition Index.h:1268
@ CXCursor_LinkageSpec
A linkage specification, e.g.
Definition Index.h:1244
@ CXCursor_ClassDecl
A C++ class.
Definition Index.h:1203
@ CXCursor_ObjCCategoryDecl
An Objective-C @interface for a category.
Definition Index.h:1222
@ CXCursor_StaticAssert
A static_assert or _Static_assert node.
Definition Index.h:2312
@ CXCursor_ModuleImportDecl
A module import declaration.
Definition Index.h:2307
@ CXCursor_MemberRef
A reference to a member of a struct, union, or class that occurs in some non-expression context,...
Definition Index.h:1316
@ CXCursor_NamespaceAlias
A C++ namespace alias declaration.
Definition Index.h:1264
@ CXCursor_Constructor
A C++ constructor.
Definition Index.h:1246
@ CXCursor_FriendDecl
a friend declaration.
Definition Index.h:2316
@ CXCursor_TypeAliasDecl
A C++ alias declaration.
Definition Index.h:1270
@ CXCursor_UsingDirective
A C++ using directive.
Definition Index.h:1266
@ CXAvailability_Available
The entity is available.
Definition Index.h:134
@ CXAvailability_Deprecated
The entity is available, but has been deprecated (and its use is not recommended).
Definition Index.h:139
@ CXAvailability_NotAvailable
The entity is not available; any use of it will be an error.
Definition Index.h:143
@ kind_nullability
Indicates that the nullability of the type was spelled with a property attribute rather than a type q...
const internal::VariadicAllOfMatcher< Type > type
Matches Types in the clang AST.
@ OS
Indicates that the tracking object is a descendant of a referenced-counted OSObject,...
bool Alloc(InterpState &S, CodePtr OpPC, const Descriptor *Desc)
Definition Interp.h:3945
bool Add(InterpState &S, CodePtr OpPC)
Definition Interp.h:418
TokenKind
Provides a simple uniform namespace for tokens from all C languages.
Definition TokenKinds.h:33
Top level wrappers for InstallAPI frontend operations.
CanQual< Type > CanQualType
Represents a canonical, potentially-qualified type.
@ OO_None
Not an overloaded operator.
@ NUM_OVERLOADED_OPERATORS
bool isa(CodeGen::Address addr)
Definition Address.h:330
@ CPlusPlus23
@ CPlusPlus20
@ CPlusPlus
@ CPlusPlus11
@ CPlusPlus17
@ CCP_Type
Priority for a type.
@ CCP_ObjC_cmd
Priority for the Objective-C "_cmd" implicit parameter.
@ CCP_Keyword
Priority for a language keyword (that isn't any of the other categories).
@ CCP_Macro
Priority for a preprocessor macro.
@ CCP_LocalDeclaration
Priority for a declaration that is in the local scope.
@ CCP_Unlikely
Priority for a result that isn't likely to be what the user wants, but is included for completeness.
@ CCP_NestedNameSpecifier
Priority for a nested-name-specifier.
@ CCP_SuperCompletion
Priority for a send-to-super completion.
@ CCP_NextInitializer
Priority for the next initialization in a constructor initializer list.
@ CCP_Declaration
Priority for a non-type declaration.
@ CCP_Constant
Priority for a constant value (e.g., enumerator).
@ CCP_MemberDeclaration
Priority for a member declaration found from the current method or member function.
@ CCP_EnumInCase
Priority for an enumeration constant inside a switch whose condition is of the enumeration type.
@ CCP_CodePattern
Priority for a code pattern.
@ Specialization
We are substituting template parameters for template arguments in order to form a template specializa...
Definition Template.h:50
bool isBetterOverloadCandidate(Sema &S, const OverloadCandidate &Cand1, const OverloadCandidate &Cand2, SourceLocation Loc, OverloadCandidateSet::CandidateSetKind Kind, bool PartialOverloading=false)
isBetterOverloadCandidate - Determines whether the first overload candidate is a better candidate tha...
bool isReservedInAllContexts(ReservedIdentifierStatus Status)
Determine whether an identifier is reserved in all contexts.
ArrayRef< IdentifierLoc > ModuleIdPath
A sequence of identifier/location pairs used to describe a particular module or submodule,...
@ Nullable
Values of this type can be null.
Definition Specifiers.h:351
@ Unspecified
Whether values of this type can be null is (explicitly) unspecified.
Definition Specifiers.h:356
@ NonNull
Values of this type can never be null.
Definition Specifiers.h:349
CXCursorKind getCursorKindForDecl(const Decl *D)
Determine the libclang cursor kind associated with the given declaration.
RefQualifierKind
The kind of C++11 ref-qualifier associated with a function type.
Definition TypeBase.h:1799
@ RQ_None
No ref-qualifier was provided.
Definition TypeBase.h:1801
@ RQ_LValue
An lvalue ref-qualifier was provided (&).
Definition TypeBase.h:1804
@ RQ_RValue
An rvalue ref-qualifier was provided (&&).
Definition TypeBase.h:1807
const RawComment * getParameterComment(const ASTContext &Ctx, const CodeCompleteConsumer::OverloadCandidate &Result, unsigned ArgIndex)
Get the documentation comment used to produce CodeCompletionString::BriefComment for OverloadCandidat...
@ LCK_This
Capturing the *this object by reference.
Definition Lambda.h:34
@ CCD_SelectorMatch
The selector of the given message exactly matches the selector of the current method,...
@ CCD_ObjectQualifierMatch
The result is a C++ non-static member function whose qualifiers exactly match the object type on whic...
@ CCD_bool_in_ObjC
Adjustment to the "bool" type in Objective-C, where the typedef "BOOL" is preferred.
@ CCD_InBaseClass
The result is in a base class.
@ CCD_ProbablyNotObjCCollection
Adjustment for KVC code pattern priorities when it doesn't look like the.
@ CCD_BlockPropertySetter
An Objective-C block property completed as a setter with a block placeholder.
@ CCD_MethodAsProperty
An Objective-C method being used as a property.
@ IK_ConstructorName
A constructor name.
Definition DeclSpec.h:1025
@ IK_DestructorName
A destructor name.
Definition DeclSpec.h:1029
@ IK_OperatorFunctionId
An overloaded operator name, e.g., operator+.
Definition DeclSpec.h:1019
nullptr
This class represents a compute construct, representing a 'Kind' of ‘parallel’, 'serial',...
@ Property
The type of a property.
Definition TypeBase.h:912
@ Parameter
The parameter type of a method or function.
Definition TypeBase.h:909
@ Result
The result type of a method or function.
Definition TypeBase.h:906
SimplifiedTypeClass
A simplified classification of types used when determining "similar" types for code completion.
const FunctionProtoType * T
@ Template
We are parsing a template declaration.
Definition Parser.h:81
const RawComment * getPatternCompletionComment(const ASTContext &Ctx, const NamedDecl *Decl)
Get the documentation comment used to produce CodeCompletionString::BriefComment for RK_Pattern.
@ Interface
The "__interface" keyword.
Definition TypeBase.h:6013
@ Struct
The "struct" keyword.
Definition TypeBase.h:6010
@ Class
The "class" keyword.
Definition TypeBase.h:6019
@ Union
The "union" keyword.
Definition TypeBase.h:6016
@ Enum
The "enum" keyword.
Definition TypeBase.h:6022
LLVM_READONLY char toUppercase(char c)
Converts the given ASCII character to its uppercase equivalent.
Definition CharInfo.h:233
@ NonType
The name was classified as a specific non-type, non-template declaration.
Definition Sema.h:562
@ Type
The name was classified as a type.
Definition Sema.h:558
@ OverloadSet
The name was classified as an overload set, and an expression representing that overload set has been...
Definition Sema.h:575
const RawComment * getCompletionComment(const ASTContext &Ctx, const NamedDecl *Decl)
Get the documentation comment used to produce CodeCompletionString::BriefComment for RK_Declaration.
@ CCF_ExactTypeMatch
Divide by this factor when a code-completion result's type exactly matches the type we expect.
@ CCF_SimilarTypeMatch
Divide by this factor when a code-completion result's type is similar to the type we expect (e....
SimplifiedTypeClass getSimplifiedTypeClass(CanQualType T)
Determine the simplified type class of the given canonical type.
@ Deduced
The normal deduced case.
Definition TypeBase.h:1818
@ LCD_ByCopy
Definition Lambda.h:24
ExprValueKind
The categorization of expression values, currently following the C++11 scheme.
Definition Specifiers.h:133
@ VK_XValue
An x-value expression is a reference to an object with independent storage but which can be "moved",...
Definition Specifiers.h:145
@ VK_LValue
An l-value expression is a reference to an object with independent storage.
Definition Specifiers.h:140
unsigned getMacroUsagePriority(StringRef MacroName, const LangOptions &LangOpts, bool PreferredTypeIsPointer=false)
Determine the priority to be given to a macro code completion result with the given name.
bool shouldEnforceArgLimit(bool PartialOverloading, FunctionDecl *Function)
llvm::StringRef getAsString(SyncScope S)
Definition SyncScope.h:63
DynamicRecursiveASTVisitorBase< false > DynamicRecursiveASTVisitor
U cast(CodeGen::Address addr)
Definition Address.h:327
@ Enumerator
Enumerator value with fixed underlying type.
Definition Sema.h:834
QualType getDeclUsageType(ASTContext &C, NestedNameSpecifier Qualifier, const NamedDecl *ND)
Determine the type that this declaration will have if it is used as a type or in an expression.
OpaquePtr< QualType > ParsedType
An opaque type for threading parsed type information through the parser.
Definition Ownership.h:230
@ Interface
The "__interface" keyword introduces the elaborated-type-specifier.
Definition TypeBase.h:5988
@ None
No keyword precedes the qualified type name.
Definition TypeBase.h:6004
@ Class
The "class" keyword introduces the elaborated-type-specifier.
Definition TypeBase.h:5994
@ Enum
The "enum" keyword introduces the elaborated-type-specifier.
Definition TypeBase.h:5997
ReservedIdentifierStatus
ActionResult< Expr * > ExprResult
Definition Ownership.h:249
@ EST_BasicNoexcept
noexcept
@ EST_NoexceptTrue
noexcept(expression), evals to 'true'
__UINTPTR_TYPE__ uintptr_t
An unsigned integer type with the property that any valid pointer to void can be converted to this ty...
__packed_splat4 __packed_splat2 __packed_splat8 __packed_splat4 __packed_splat2 __packed_splat4 __packed_splat2 __packed_splat8 __packed_splat4 uint32_t
#define false
Definition stdbool.h:26
CodeCompleteExpressionData(QualType PreferredType=QualType(), bool IsParenthesized=false)
unsigned NumParams
NumParams - This is the number of formal parameters specified by the declarator.
Definition DeclSpec.h:1447
Represents a complete lambda introducer.
Definition DeclSpec.h:2884
SmallVector< LambdaCapture, 4 > Captures
Definition DeclSpec.h:2909
LambdaCaptureDefault Default
Definition DeclSpec.h:2908
a linked list of methods with the same selector name but different signatures.
OverloadCandidate - A single candidate in an overload set (C++ 13.3).
Definition Overload.h:934
static ArrayRef< const ParsedAttrInfo * > getAllBuiltin()
Describes how types, statements, expressions, and declarations should be printed.
unsigned SuppressUnwrittenScope
Suppress printing parts of scope specifiers that are never written, e.g., for anonymous namespaces.
unsigned CleanUglifiedParameters
Whether to strip underscores when printing reserved parameter names.
unsigned SuppressStrongLifetime
When true, suppress printing of the __strong lifetime qualifier in ARC.
@ Plain
E.g., (anonymous enum)/(unnamed struct)/etc.
unsigned SuppressTemplateArgsInCXXConstructors
When true, suppresses printing template arguments in names of C++ constructors.