From 72c26c0d47eb850db18b784403260bce0632c478 Mon Sep 17 00:00:00 2001 From: Reid Kleckner Date: Wed, 2 Oct 2013 15:19:23 +0000 Subject: [PATCH] Accept #pragma warning(push, 0) without warning This partially addresses PR17435, but it doesn't actually implement the pragma. If we implement it, we should map levels 1-4 to something like -Wall and level 0 to something like -w. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@191833 91177308-0d34-0410-b5e6-96231b3b80d8 --- include/clang/Basic/DiagnosticLexKinds.td | 2 +- lib/Frontend/PrintPreprocessedOutput.cpp | 2 +- lib/Lex/Pragma.cpp | 22 +++++++++++----------- test/Preprocessor/pragma_microsoft.c | 7 ++++++- test/Preprocessor/pragma_microsoft.cpp | 2 +- 5 files changed, 20 insertions(+), 15 deletions(-) diff --git a/include/clang/Basic/DiagnosticLexKinds.td b/include/clang/Basic/DiagnosticLexKinds.td index eafe6c0da2..2603307775 100644 --- a/include/clang/Basic/DiagnosticLexKinds.td +++ b/include/clang/Basic/DiagnosticLexKinds.td @@ -422,7 +422,7 @@ def warn_pragma_warning_spec_invalid : " 'error', 'once', 'suppress', 1, 2, 3, or 4">, InGroup; def warn_pragma_warning_push_level : - ExtWarn<"#pragma warning(push, level) requires a level between 1 and 4">, + ExtWarn<"#pragma warning(push, level) requires a level between 0 and 4">, InGroup; def warn_pragma_warning_expected_number : ExtWarn<"#pragma warning expected a warning number">, diff --git a/lib/Frontend/PrintPreprocessedOutput.cpp b/lib/Frontend/PrintPreprocessedOutput.cpp index ecdfb095e6..3545d70744 100644 --- a/lib/Frontend/PrintPreprocessedOutput.cpp +++ b/lib/Frontend/PrintPreprocessedOutput.cpp @@ -528,7 +528,7 @@ void PrintPPOutputPPCallbacks::PragmaWarningPush(SourceLocation Loc, startNewLineIfNeeded(); MoveToLine(Loc); OS << "#pragma warning(push"; - if (Level) + if (Level >= 0) OS << ", " << Level; OS << ')'; setEmittedDirectiveOnThisLine(); diff --git a/lib/Lex/Pragma.cpp b/lib/Lex/Pragma.cpp index 4c6d889bf3..f1d8fa1f73 100644 --- a/lib/Lex/Pragma.cpp +++ b/lib/Lex/Pragma.cpp @@ -1007,22 +1007,22 @@ public: } }; -// Returns 0 on failure. -static unsigned LexSimpleUint(Preprocessor &PP, Token &Tok) { +// Returns -1 on failure. +static int LexSimpleInt(Preprocessor &PP, Token &Tok) { assert(Tok.is(tok::numeric_constant)); SmallString<8> IntegerBuffer; bool NumberInvalid = false; StringRef Spelling = PP.getSpelling(Tok, IntegerBuffer, &NumberInvalid); if (NumberInvalid) - return 0; + return -1; NumericLiteralParser Literal(Spelling, Tok.getLocation(), PP); if (Literal.hadError || !Literal.isIntegerLiteral() || Literal.hasUDSuffix()) - return 0; + return -1; llvm::APInt APVal(32, 0); if (Literal.GetIntegerValue(APVal)) - return 0; + return -1; PP.Lex(Tok); - return unsigned(APVal.getLimitedValue(UINT_MAX)); + return int(APVal.getLimitedValue(INT_MAX)); } /// "\#pragma warning(...)". MSVC's diagnostics do not map cleanly to clang's @@ -1055,13 +1055,13 @@ struct PragmaWarningHandler : public PragmaHandler { if (II->isStr("push")) { // #pragma warning( push[ ,n ] ) - unsigned Level = 0; + int Level = -1; PP.Lex(Tok); if (Tok.is(tok::comma)) { PP.Lex(Tok); if (Tok.is(tok::numeric_constant)) - Level = LexSimpleUint(PP, Tok); - if (Level < 1 || Level > 4) { + Level = LexSimpleInt(PP, Tok); + if (Level < 0 || Level > 4) { PP.Diag(Tok, diag::warn_pragma_warning_push_level); return; } @@ -1104,8 +1104,8 @@ struct PragmaWarningHandler : public PragmaHandler { SmallVector Ids; PP.Lex(Tok); while (Tok.is(tok::numeric_constant)) { - unsigned Id = LexSimpleUint(PP, Tok); - if (Id == 0 || Id >= INT_MAX) { + int Id = LexSimpleInt(PP, Tok); + if (Id <= 0) { PP.Diag(Tok, diag::warn_pragma_warning_expected_number); return; } diff --git a/test/Preprocessor/pragma_microsoft.c b/test/Preprocessor/pragma_microsoft.c index c7bf3c47be..e30069c1c5 100644 --- a/test/Preprocessor/pragma_microsoft.c +++ b/test/Preprocessor/pragma_microsoft.c @@ -98,15 +98,20 @@ void g() {} #pragma warning(default : 321) #pragma warning(pop) +#pragma warning(push, 0) +// FIXME: We could probably support pushing warning level 0. +#pragma warning(pop) + #pragma warning // expected-warning {{expected '('}} #pragma warning( // expected-warning {{expected 'push', 'pop', 'default', 'disable', 'error', 'once', 'suppress', 1, 2, 3, or 4}} #pragma warning() // expected-warning {{expected 'push', 'pop', 'default', 'disable', 'error', 'once', 'suppress', 1, 2, 3, or 4}} #pragma warning(push 4) // expected-warning {{expected ')'}} #pragma warning(push // expected-warning {{expected ')'}} -#pragma warning(push, 5) // expected-warning {{requires a level between 1 and 4}} +#pragma warning(push, 5) // expected-warning {{requires a level between 0 and 4}} #pragma warning(pop, 1) // expected-warning {{expected ')'}} #pragma warning(push, 1) asdf // expected-warning {{extra tokens at end of #pragma warning directive}} #pragma warning(disable 4705) // expected-warning {{expected ':'}} #pragma warning(disable : 0) // expected-warning {{expected a warning number}} #pragma warning(default 321) // expected-warning {{expected ':'}} #pragma warning(asdf : 321) // expected-warning {{expected 'push', 'pop'}} +#pragma warning(push, -1) // expected-warning {{requires a level between 0 and 4}} diff --git a/test/Preprocessor/pragma_microsoft.cpp b/test/Preprocessor/pragma_microsoft.cpp index 5bc1ccc4ce..e097d69a20 100644 --- a/test/Preprocessor/pragma_microsoft.cpp +++ b/test/Preprocessor/pragma_microsoft.cpp @@ -1,3 +1,3 @@ // RUN: %clang_cc1 %s -fsyntax-only -std=c++11 -verify -fms-extensions -#pragma warning(push, 4_D) // expected-warning {{requires a level between 1 and 4}} +#pragma warning(push, 4_D) // expected-warning {{requires a level between 0 and 4}} -- 2.40.0