diff options
-rw-r--r-- | include/clang/Basic/DiagnosticGroups.td | 1 | ||||
-rw-r--r-- | include/clang/Basic/DiagnosticLexKinds.td | 7 | ||||
-rw-r--r-- | lib/Lex/PPDirectives.cpp | 21 | ||||
-rw-r--r-- | test/Lexer/builtin_redef.c | 19 | ||||
-rw-r--r-- | test/Misc/warning-flags.c | 3 |
5 files changed, 37 insertions, 14 deletions
diff --git a/include/clang/Basic/DiagnosticGroups.td b/include/clang/Basic/DiagnosticGroups.td index 69af407342..7b921953ff 100644 --- a/include/clang/Basic/DiagnosticGroups.td +++ b/include/clang/Basic/DiagnosticGroups.td @@ -39,6 +39,7 @@ def NullConversion : DiagGroup<"null-conversion">; def ImplicitConversionFloatingPointToBool : DiagGroup<"implicit-conversion-floating-point-to-bool">; def BadArrayNewLength : DiagGroup<"bad-array-new-length">; +def BuiltinMacroRedefined : DiagGroup<"builtin-macro-redefined">; def BuiltinRequiresHeader : DiagGroup<"builtin-requires-header">; def C99Compat : DiagGroup<"c99-compat">; def CXXCompat: DiagGroup<"c++-compat">; diff --git a/include/clang/Basic/DiagnosticLexKinds.td b/include/clang/Basic/DiagnosticLexKinds.td index 7281d07a3b..f693257ec9 100644 --- a/include/clang/Basic/DiagnosticLexKinds.td +++ b/include/clang/Basic/DiagnosticLexKinds.td @@ -253,9 +253,10 @@ def pp_pragma_sysheader_in_main_file : Warning< def pp_poisoning_existing_macro : Warning<"poisoning existing macro">; def pp_out_of_date_dependency : Warning< "current file is older than dependency %0">; -def pp_undef_builtin_macro : Warning<"undefining builtin macro">; -def pp_redef_builtin_macro : Warning<"redefining builtin macro">, - InGroup<DiagGroup<"builtin-macro-redefined">>; +def ext_pp_undef_builtin_macro : ExtWarn<"undefining builtin macro">, + InGroup<BuiltinMacroRedefined>; +def ext_pp_redef_builtin_macro : ExtWarn<"redefining builtin macro">, + InGroup<BuiltinMacroRedefined>; def pp_disabled_macro_expansion : Warning< "disabled expansion of recursive macro">, DefaultIgnore, InGroup<DiagGroup<"disabled-macro-expansion">>; diff --git a/lib/Lex/PPDirectives.cpp b/lib/Lex/PPDirectives.cpp index 07f24c8200..8379ca8719 100644 --- a/lib/Lex/PPDirectives.cpp +++ b/lib/Lex/PPDirectives.cpp @@ -143,15 +143,14 @@ void Preprocessor::ReadMacroName(Token &MacroNameTok, char isDefineUndef) { Diag(MacroNameTok, diag::err_pp_macro_not_identifier); // Fall through on error. } else if (isDefineUndef && II->getPPKeywordID() == tok::pp_defined) { - // Error if defining "defined": C99 6.10.8.4. + // Error if defining "defined": C99 6.10.8/4, C++ [cpp.predefined]p4. Diag(MacroNameTok, diag::err_defined_macro_name); - } else if (isDefineUndef && II->hasMacroDefinition() && + } else if (isDefineUndef == 2 && II->hasMacroDefinition() && getMacroInfo(II)->isBuiltinMacro()) { - // Error if defining "__LINE__" and other builtins: C99 6.10.8.4. - if (isDefineUndef == 1) - Diag(MacroNameTok, diag::pp_redef_builtin_macro); - else - Diag(MacroNameTok, diag::pp_undef_builtin_macro); + // Warn if undefining "__LINE__" and other builtins, per C99 6.10.8/4 + // and C++ [cpp.predefined]p4], but allow it as an extension. + Diag(MacroNameTok, diag::ext_pp_undef_builtin_macro); + return; } else { // Okay, we got a good identifier node. Return it. return; @@ -1925,10 +1924,14 @@ void Preprocessor::HandleDefineDirective(Token &DefineTok) { if (!OtherMI->isUsed() && OtherMI->isWarnIfUnused()) Diag(OtherMI->getDefinitionLoc(), diag::pp_macro_not_used); + // Warn if defining "__LINE__" and other builtins, per C99 6.10.8/4 and + // C++ [cpp.predefined]p4, but allow it as an extension. + if (OtherMI->isBuiltinMacro()) + Diag(MacroNameTok, diag::ext_pp_redef_builtin_macro); // Macros must be identical. This means all tokens and whitespace // separation must be the same. C99 6.10.3.2. - if (!OtherMI->isAllowRedefinitionsWithoutWarning() && - !MI->isIdenticalTo(*OtherMI, *this)) { + else if (!OtherMI->isAllowRedefinitionsWithoutWarning() && + !MI->isIdenticalTo(*OtherMI, *this)) { Diag(MI->getDefinitionLoc(), diag::ext_pp_macro_redef) << MacroNameTok.getIdentifierInfo(); Diag(OtherMI->getDefinitionLoc(), diag::note_previous_definition); diff --git a/test/Lexer/builtin_redef.c b/test/Lexer/builtin_redef.c new file mode 100644 index 0000000000..c9351dc4a6 --- /dev/null +++ b/test/Lexer/builtin_redef.c @@ -0,0 +1,19 @@ +// RUN: %clang_cc1 %s -D__TIME__=1234 -U__DATE__ -E 2>&1 | FileCheck %s --check-prefix=CHECK-OUT +// RUN: %clang_cc1 %s -D__TIME__=1234 -U__DATE__ -E 2>&1 | FileCheck %s --check-prefix=CHECK-WARN +// RUN: %clang_cc1 %s -D__TIME__=1234 -U__DATE__ -E 2>&1 -pedantic-errors | FileCheck %s --check-prefix=CHECK-ERR + +// CHECK-WARN: <command line>:{{.*}} warning: redefining builtin macro +// CHECK-WARN: <command line>:{{.*}} warning: undefining builtin macro + +// CHECK-ERR: <command line>:{{.*}} error: redefining builtin macro +// CHECK-ERR: <command line>:{{.*}} error: undefining builtin macro + +int n = __TIME__; +__DATE__ + +#define __FILE__ "my file" +// CHECK-WARN: :[[@LINE-1]]:9: warning: redefining builtin macro +// CHECK-ERR: :[[@LINE-2]]:9: error: redefining builtin macro + +// CHECK-OUT: int n = 1234; +// CHECK-OUT: __DATE__ diff --git a/test/Misc/warning-flags.c b/test/Misc/warning-flags.c index 265e178fa7..931de8365b 100644 --- a/test/Misc/warning-flags.c +++ b/test/Misc/warning-flags.c @@ -18,7 +18,7 @@ This test serves two purposes: The list of warnings below should NEVER grow. It should gradually shrink to 0. -CHECK: Warnings without flags (145): +CHECK: Warnings without flags (144): CHECK-NEXT: ext_delete_void_ptr_operand CHECK-NEXT: ext_enum_friend CHECK-NEXT: ext_expected_semi_decl_list @@ -44,7 +44,6 @@ CHECK-NEXT: pp_out_of_date_dependency CHECK-NEXT: pp_poisoning_existing_macro CHECK-NEXT: pp_pragma_once_in_main_file CHECK-NEXT: pp_pragma_sysheader_in_main_file -CHECK-NEXT: pp_undef_builtin_macro CHECK-NEXT: w_asm_qualifier_ignored CHECK-NEXT: warn_accessor_property_type_mismatch CHECK-NEXT: warn_anon_bitfield_width_exceeds_type_size |