Skip to content

Commit 8cb1746

Browse files
committed
If a macro has been #undef'd in a precompiled header, we still need to
write out the macro history for that macro. Similarly, we need to cope with reading a macro definition that has been #undef'd. Take advantage of this new ability so that global code-completion results can refer to #undef'd macros, rather than losing them entirely. For multiply defined/#undef'd macros, we will still get the wrong result, but it's better than getting no result. llvm-svn: 165502
1 parent 97e5949 commit 8cb1746

File tree

5 files changed

+22
-19
lines changed

5 files changed

+22
-19
lines changed

clang/include/clang/Basic/IdentifierTable.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -147,6 +147,9 @@ class IdentifierInfo {
147147
bool hadMacroDefinition() const {
148148
return HadMacro;
149149
}
150+
void setHadMacroDefinition(bool Val) {
151+
HadMacro = Val;
152+
}
150153

151154
/// getTokenID - If this is a source-language token (e.g. 'for'), this API
152155
/// can be used to cause the lexer to map identifiers to source-language

clang/lib/Sema/SemaCodeComplete.cpp

Lines changed: 12 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -2495,7 +2495,7 @@ CodeCompletionResult::CreateCodeCompletionString(ASTContext &Ctx,
24952495
}
24962496

24972497
if (Kind == RK_Macro) {
2498-
MacroInfo *MI = PP.getMacroInfo(Macro);
2498+
MacroInfo *MI = PP.getMacroInfoHistory(Macro);
24992499
assert(MI && "Not a macro?");
25002500

25012501
Result.AddTypedTextChunk(
@@ -2902,6 +2902,7 @@ CXCursorKind clang::getCursorKindForDecl(Decl *D) {
29022902
}
29032903

29042904
static void AddMacroResults(Preprocessor &PP, ResultBuilder &Results,
2905+
bool IncludeUndefined,
29052906
bool TargetTypeIsPointer = false) {
29062907
typedef CodeCompletionResult Result;
29072908

@@ -2910,11 +2911,8 @@ static void AddMacroResults(Preprocessor &PP, ResultBuilder &Results,
29102911
for (Preprocessor::macro_iterator M = PP.macro_begin(),
29112912
MEnd = PP.macro_end();
29122913
M != MEnd; ++M) {
2913-
// FIXME: Eventually, we'd want to be able to look back to the macro
2914-
// definition that was actually active at the point of code completion (even
2915-
// if that macro has since been #undef'd).
2916-
if (M->first->hasMacroDefinition())
2917-
Results.AddResult(Result(M->first,
2914+
if (IncludeUndefined || M->first->hasMacroDefinition())
2915+
Results.AddResult(Result(M->first,
29182916
getMacroUsagePriority(M->first->getName(),
29192917
PP.getLangOpts(),
29202918
TargetTypeIsPointer)));
@@ -3213,7 +3211,7 @@ void Sema::CodeCompleteOrdinaryName(Scope *S,
32133211
}
32143212

32153213
if (CodeCompleter->includeMacros())
3216-
AddMacroResults(PP, Results);
3214+
AddMacroResults(PP, Results, false);
32173215

32183216
HandleCodeCompleteResults(this, CodeCompleter, Results.getCompletionContext(),
32193217
Results.data(),Results.size());
@@ -3344,7 +3342,7 @@ void Sema::CodeCompleteExpression(Scope *S,
33443342
AddPrettyFunctionResults(PP.getLangOpts(), Results);
33453343

33463344
if (CodeCompleter->includeMacros())
3347-
AddMacroResults(PP, Results, PreferredTypeIsPointer);
3345+
AddMacroResults(PP, Results, false, PreferredTypeIsPointer);
33483346
HandleCodeCompleteResults(this, CodeCompleter,
33493347
CodeCompletionContext(CodeCompletionContext::CCC_Expression,
33503348
Data.PreferredType),
@@ -3736,7 +3734,7 @@ void Sema::CodeCompleteCase(Scope *S) {
37363734
//so only say we include macros if the code completer says we do
37373735
enum CodeCompletionContext::Kind kind = CodeCompletionContext::CCC_Other;
37383736
if (CodeCompleter->includeMacros()) {
3739-
AddMacroResults(PP, Results);
3737+
AddMacroResults(PP, Results, false);
37403738
kind = CodeCompletionContext::CCC_OtherWithMacros;
37413739
}
37423740

@@ -3959,7 +3957,7 @@ void Sema::CodeCompleteAfterIf(Scope *S) {
39593957
AddPrettyFunctionResults(PP.getLangOpts(), Results);
39603958

39613959
if (CodeCompleter->includeMacros())
3962-
AddMacroResults(PP, Results);
3960+
AddMacroResults(PP, Results, false);
39633961

39643962
HandleCodeCompleteResults(this, CodeCompleter, Results.getCompletionContext(),
39653963
Results.data(),Results.size());
@@ -4960,7 +4958,7 @@ void Sema::CodeCompleteObjCPassingType(Scope *S, ObjCDeclSpec &DS,
49604958
CodeCompleter->includeGlobals());
49614959

49624960
if (CodeCompleter->includeMacros())
4963-
AddMacroResults(PP, Results);
4961+
AddMacroResults(PP, Results, false);
49644962

49654963
HandleCodeCompleteResults(this, CodeCompleter,
49664964
CodeCompletionContext::CCC_Type,
@@ -5190,7 +5188,7 @@ void Sema::CodeCompleteObjCMessageReceiver(Scope *S) {
51905188
Results.ExitScope();
51915189

51925190
if (CodeCompleter->includeMacros())
5193-
AddMacroResults(PP, Results);
5191+
AddMacroResults(PP, Results, false);
51945192
HandleCodeCompleteResults(this, CodeCompleter, Results.getCompletionContext(),
51955193
Results.data(), Results.size());
51965194

@@ -7190,7 +7188,7 @@ void Sema::CodeCompletePreprocessorExpression() {
71907188
CodeCompletionContext::CCC_PreprocessorExpression);
71917189

71927190
if (!CodeCompleter || CodeCompleter->includeMacros())
7193-
AddMacroResults(PP, Results);
7191+
AddMacroResults(PP, Results, true);
71947192

71957193
// defined (<macro>)
71967194
Results.EnterNewScope();
@@ -7239,7 +7237,7 @@ void Sema::GatherGlobalCodeCompletions(CodeCompletionAllocator &Allocator,
72397237
}
72407238

72417239
if (!CodeCompleter || CodeCompleter->includeMacros())
7242-
AddMacroResults(PP, Builder);
7240+
AddMacroResults(PP, Builder, true);
72437241

72447242
Results.clear();
72457243
Results.insert(Results.end(),

clang/lib/Serialization/ASTReader.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1460,6 +1460,8 @@ void ASTReader::setIdentifierIsMacro(IdentifierInfo *II, ModuleFile &F,
14601460
if (Visible) {
14611461
// Note that this identifier has a macro definition.
14621462
II->setHasMacroDefinition(true);
1463+
} else {
1464+
II->setHadMacroDefinition(true);
14631465
}
14641466

14651467
// Adjust the offset to a global offset.

clang/lib/Serialization/ASTWriter.cpp

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1698,14 +1698,13 @@ void ASTWriter::WritePreprocessor(const Preprocessor &PP, bool IsModule) {
16981698
IdentifierInfo *Name
16991699
= const_cast<IdentifierInfo *>(DeserializedMacroNames[I]);
17001700
if (Name->hadMacroDefinition() && MacroDefinitionsSeen.insert(Name))
1701-
MacrosToEmit.push_back(std::make_pair(Name, PP.getMacroInfo(Name)));
1701+
MacrosToEmit.push_back(std::make_pair(Name,
1702+
PP.getMacroInfoHistory(Name)));
17021703
}
17031704

17041705
for (unsigned I = 0, N = MacrosToEmit.size(); I != N; ++I) {
17051706
const IdentifierInfo *Name = MacrosToEmit[I].first;
17061707
MacroInfo *MI = MacrosToEmit[I].second;
1707-
if (!MI)
1708-
continue;
17091708

17101709
// History of macro definitions for this identifier in chronological order.
17111710
SmallVector<MacroInfo*, 8> MacroHistory;

clang/test/Index/complete-macros.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
// Note: the run lines follow their respective tests, since line/column
22
// matter in this test.
3-
43
#define FOO(Arg1,Arg2) foobar
54
#define nil 0
5+
#undef FOO
66
void f() {
77

88
}
@@ -25,7 +25,8 @@ void test_variadic() {
2525

2626
}
2727

28-
// RUN: c-index-test -code-completion-at=%s:7:1 %s | FileCheck -check-prefix=CHECK-CC1 %s
28+
// RUN: c-index-test -code-completion-at=%s:7:1 %s | FileCheck -check-prefix=CHECK-CC0 %s
29+
// CHECK-CC0-NOT: FOO
2930
// RUN: env CINDEXTEST_EDITING=1 CINDEXTEST_COMPLETION_CACHING=1 c-index-test -code-completion-at=%s:7:1 %s | FileCheck -check-prefix=CHECK-CC1 %s
3031
// CHECK-CC1: macro definition:{TypedText FOO}{LeftParen (}{Placeholder Arg1}{Comma , }{Placeholder Arg2}{RightParen )}
3132
// RUN: c-index-test -code-completion-at=%s:13:13 %s | FileCheck -check-prefix=CHECK-CC2 %s

0 commit comments

Comments
 (0)