Skip to content
This repository was archived by the owner on Nov 1, 2021. It is now read-only.

Commit ce3b2b0

Browse files
author
Eli Friedman
committed
[Preprocessor] Preserve #pragma clang assume_nonnull in preprocessed output
Patch by Zbigniew Sarbinowski! Differential Revision: https://reviews.llvm.org/D37861 git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@314364 91177308-0d34-0410-b5e6-96231b3b80d8
1 parent 619b769 commit ce3b2b0

File tree

4 files changed

+57
-0
lines changed

4 files changed

+57
-0
lines changed

include/clang/Lex/PPCallbacks.h

+18
Original file line numberDiff line numberDiff line change
@@ -235,6 +235,14 @@ class PPCallbacks {
235235
virtual void PragmaWarningPop(SourceLocation Loc) {
236236
}
237237

238+
/// \brief Callback invoked when a \#pragma clang assume_nonnull begin directive
239+
/// is read.
240+
virtual void PragmaAssumeNonNullBegin(SourceLocation Loc) {}
241+
242+
/// \brief Callback invoked when a \#pragma clang assume_nonnull end directive
243+
/// is read.
244+
virtual void PragmaAssumeNonNullEnd(SourceLocation Loc) {}
245+
238246
/// \brief Called by Preprocessor::HandleMacroExpandedIdentifier when a
239247
/// macro invocation is found.
240248
virtual void MacroExpands(const Token &MacroNameTok,
@@ -446,6 +454,16 @@ class PPChainedCallbacks : public PPCallbacks {
446454
Second->PragmaWarningPop(Loc);
447455
}
448456

457+
void PragmaAssumeNonNullBegin(SourceLocation Loc) override {
458+
First->PragmaAssumeNonNullBegin(Loc);
459+
Second->PragmaAssumeNonNullBegin(Loc);
460+
}
461+
462+
void PragmaAssumeNonNullEnd(SourceLocation Loc) override {
463+
First->PragmaAssumeNonNullEnd(Loc);
464+
Second->PragmaAssumeNonNullEnd(Loc);
465+
}
466+
449467
void MacroExpands(const Token &MacroNameTok, const MacroDefinition &MD,
450468
SourceRange Range, const MacroArgs *Args) override {
451469
First->MacroExpands(MacroNameTok, MD, Range, Args);

lib/Frontend/PrintPreprocessedOutput.cpp

+18
Original file line numberDiff line numberDiff line change
@@ -143,6 +143,8 @@ class PrintPPOutputPPCallbacks : public PPCallbacks {
143143
ArrayRef<int> Ids) override;
144144
void PragmaWarningPush(SourceLocation Loc, int Level) override;
145145
void PragmaWarningPop(SourceLocation Loc) override;
146+
void PragmaAssumeNonNullBegin(SourceLocation Loc) override;
147+
void PragmaAssumeNonNullEnd(SourceLocation Loc) override;
146148

147149
bool HandleFirstTokOnLine(Token &Tok);
148150

@@ -549,6 +551,22 @@ void PrintPPOutputPPCallbacks::PragmaWarningPop(SourceLocation Loc) {
549551
setEmittedDirectiveOnThisLine();
550552
}
551553

554+
void PrintPPOutputPPCallbacks::
555+
PragmaAssumeNonNullBegin(SourceLocation Loc) {
556+
startNewLineIfNeeded();
557+
MoveToLine(Loc);
558+
OS << "#pragma clang assume_nonnull begin";
559+
setEmittedDirectiveOnThisLine();
560+
}
561+
562+
void PrintPPOutputPPCallbacks::
563+
PragmaAssumeNonNullEnd(SourceLocation Loc) {
564+
startNewLineIfNeeded();
565+
MoveToLine(Loc);
566+
OS << "#pragma clang assume_nonnull end";
567+
setEmittedDirectiveOnThisLine();
568+
}
569+
552570
/// HandleFirstTokOnLine - When emitting a preprocessed file in -E mode, this
553571
/// is called for the first token on each new line. If this really is the start
554572
/// of a new logical line, handle it and return true, otherwise return false.

lib/Lex/Pragma.cpp

+5
Original file line numberDiff line numberDiff line change
@@ -1725,6 +1725,7 @@ struct PragmaAssumeNonNullHandler : public PragmaHandler {
17251725

17261726
// The start location we want after processing this.
17271727
SourceLocation NewLoc;
1728+
PPCallbacks *Callbacks = PP.getPPCallbacks();
17281729

17291730
if (IsBegin) {
17301731
// Complain about attempts to re-enter an audit.
@@ -1733,13 +1734,17 @@ struct PragmaAssumeNonNullHandler : public PragmaHandler {
17331734
PP.Diag(BeginLoc, diag::note_pragma_entered_here);
17341735
}
17351736
NewLoc = Loc;
1737+
if (Callbacks)
1738+
Callbacks->PragmaAssumeNonNullBegin(NewLoc);
17361739
} else {
17371740
// Complain about attempts to leave an audit that doesn't exist.
17381741
if (!BeginLoc.isValid()) {
17391742
PP.Diag(Loc, diag::err_pp_unmatched_end_of_assume_nonnull);
17401743
return;
17411744
}
17421745
NewLoc = SourceLocation();
1746+
if (Callbacks)
1747+
Callbacks->PragmaAssumeNonNullEnd(NewLoc);
17431748
}
17441749

17451750
PP.setPragmaAssumeNonNullLoc(NewLoc);
+16
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
// RUN: %clang_cc1 -fsyntax-only -verify %s
2+
// RUN: %clang_cc1 -E %s | FileCheck %s
3+
4+
// CHECK: #pragma clang assume_nonnull begin
5+
#pragma clang assume_nonnull begin
6+
7+
int bar(int * ip) { return *ip; }
8+
9+
// CHECK: #pragma clang assume_nonnull end
10+
#pragma clang assume_nonnull end
11+
12+
int foo(int * _Nonnull ip) { return *ip; }
13+
14+
int main() {
15+
return bar(0) + foo(0); // expected-warning 2 {{null passed to a callee that requires a non-null argument}}
16+
}

0 commit comments

Comments
 (0)