[PATCH] D16533: Bug 20796 - GCC's -Wstrict-prototypes warning not implemented in Clang
This revision was automatically updated to reflect the committed changes. Closed by commit rL288896: Implement the -Wstrict-prototypes warning (authored by arphaman). Changed prior to commit: https://reviews.llvm.org/D16533?vs=80285=80560#toc Repository: rL LLVM https://reviews.llvm.org/D16533 Files: cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td cfe/trunk/lib/Sema/SemaDecl.cpp cfe/trunk/lib/Sema/SemaType.cpp cfe/trunk/test/Sema/warn-strict-prototypes.c cfe/trunk/test/Sema/warn-strict-prototypes.m Index: cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td === --- cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td +++ cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td @@ -4411,6 +4411,10 @@ InGroup>, DefaultIgnore; def note_declaration_not_a_prototype : Note< "this declaration is not a prototype; add 'void' to make it a prototype for a zero-parameter function">; +def warn_strict_prototypes : Warning< + "this %select{function declaration is not|" + "old-style function definition is not preceded by}0 a prototype">, + InGroup >, DefaultIgnore; def warn_missing_variable_declarations : Warning< "no previous extern declaration for non-static variable %0">, InGroup >, DefaultIgnore; Index: cfe/trunk/test/Sema/warn-strict-prototypes.m === --- cfe/trunk/test/Sema/warn-strict-prototypes.m +++ cfe/trunk/test/Sema/warn-strict-prototypes.m @@ -0,0 +1,20 @@ +// RUN: %clang_cc1 -fsyntax-only -Wstrict-prototypes -verify -fblocks %s + +@interface Foo + +@property (nonatomic, copy) void (^noProtoBlock)(); // expected-warning {{this function declaration is not a prototype}} +@property (nonatomic, copy) void (^block)(void); // no warning + +- doStuff:(void (^)()) completionHandler; // expected-warning {{this function declaration is not a prototype}} +- doOtherStuff:(void (^)(void)) completionHandler; // no warning + +@end + +void foo() { + void (^block)() = // expected-warning {{this function declaration is not a prototype}} +^void(int arg) { // no warning + }; + void (^block2)(void) = // no warning + ^void() { // expected-warning {{this function declaration is not a prototype}} + }; +} Index: cfe/trunk/test/Sema/warn-strict-prototypes.c === --- cfe/trunk/test/Sema/warn-strict-prototypes.c +++ cfe/trunk/test/Sema/warn-strict-prototypes.c @@ -0,0 +1,62 @@ +// RUN: %clang_cc1 -fsyntax-only -Wstrict-prototypes -verify %s +// RUN: %clang_cc1 -fsyntax-only -Wstrict-prototypes -fdiagnostics-parseable-fixits %s 2>&1 | FileCheck %s + +// function declaration with unspecified params +void foo1(); // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:11-[[@LINE-1]]:11}:"void" +// function declaration with 0 params +void foo2(void); + +// function definition with 0 params(for both cases), +// valid according to 6.7.5.3/14 +void foo1() {} +void foo2(void) {} + +// function type typedef unspecified params +typedef void foo3(); // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:19-[[@LINE-1]]:19}:"void" + +// global fp unspecified params +void (*foo4)(); // expected-warning {{this function declaration is not a prototype}} +// CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:14-[[@LINE-1]]:14}:"void" + +// struct member fp unspecified params +struct { void (*foo5)(); } s; // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:23-[[@LINE-1]]:23}:"void" + +// param fp unspecified params +void bar2(void (*foo6)()) { // expected-warning {{this function declaration is not a prototype}} +// CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:24-[[@LINE-1]]:24}:"void" + // local fp unspecified params + void (*foo7)() = 0; // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:16-[[@LINE-1]]:16}:"void" + // array fp unspecified params + void (*foo8[2])() = {0}; // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:19-[[@LINE-1]]:19}:"void" +} + +// function type cast using using an anonymous function declaration +void bar3(void) { + // casting function w/out prototype to unspecified params function type + (void)(void(*)()) foo1; // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:18-[[@LINE-1]]:18}:"void" + // .. specified params + (void)(void(*)(void)) foo1; +} + +// K
[PATCH] D16533: Bug 20796 - GCC's -Wstrict-prototypes warning not implemented in Clang
bruno accepted this revision. bruno added a comment. This revision is now accepted and ready to land. LGTM Repository: rL LLVM https://reviews.llvm.org/D16533 ___ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D16533: Bug 20796 - GCC's -Wstrict-prototypes warning not implemented in Clang
arphaman updated this revision to Diff 80285. arphaman marked 2 inline comments as done. arphaman added a comment. The updated patch addresses Bruno's comments. Repository: rL LLVM https://reviews.llvm.org/D16533 Files: include/clang/Basic/DiagnosticSemaKinds.td lib/Sema/SemaDecl.cpp lib/Sema/SemaType.cpp test/Sema/warn-strict-prototypes.c test/Sema/warn-strict-prototypes.m Index: test/Sema/warn-strict-prototypes.m === --- /dev/null +++ test/Sema/warn-strict-prototypes.m @@ -0,0 +1,20 @@ +// RUN: %clang_cc1 -fsyntax-only -Wstrict-prototypes -verify -fblocks %s + +@interface Foo + +@property (nonatomic, copy) void (^noProtoBlock)(); // expected-warning {{this function declaration is not a prototype}} +@property (nonatomic, copy) void (^block)(void); // no warning + +- doStuff:(void (^)()) completionHandler; // expected-warning {{this function declaration is not a prototype}} +- doOtherStuff:(void (^)(void)) completionHandler; // no warning + +@end + +void foo() { + void (^block)() = // expected-warning {{this function declaration is not a prototype}} +^void(int arg) { // no warning + }; + void (^block2)(void) = // no warning + ^void() { // expected-warning {{this function declaration is not a prototype}} + }; +} Index: test/Sema/warn-strict-prototypes.c === --- /dev/null +++ test/Sema/warn-strict-prototypes.c @@ -0,0 +1,62 @@ +// RUN: %clang_cc1 -fsyntax-only -Wstrict-prototypes -verify %s +// RUN: %clang_cc1 -fsyntax-only -Wstrict-prototypes -fdiagnostics-parseable-fixits %s 2>&1 | FileCheck %s + +// function declaration with unspecified params +void foo1(); // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:11-[[@LINE-1]]:11}:"void" +// function declaration with 0 params +void foo2(void); + +// function definition with 0 params(for both cases), +// valid according to 6.7.5.3/14 +void foo1() {} +void foo2(void) {} + +// function type typedef unspecified params +typedef void foo3(); // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:19-[[@LINE-1]]:19}:"void" + +// global fp unspecified params +void (*foo4)(); // expected-warning {{this function declaration is not a prototype}} +// CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:14-[[@LINE-1]]:14}:"void" + +// struct member fp unspecified params +struct { void (*foo5)(); } s; // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:23-[[@LINE-1]]:23}:"void" + +// param fp unspecified params +void bar2(void (*foo6)()) { // expected-warning {{this function declaration is not a prototype}} +// CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:24-[[@LINE-1]]:24}:"void" + // local fp unspecified params + void (*foo7)() = 0; // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:16-[[@LINE-1]]:16}:"void" + // array fp unspecified params + void (*foo8[2])() = {0}; // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:19-[[@LINE-1]]:19}:"void" +} + +// function type cast using using an anonymous function declaration +void bar3(void) { + // casting function w/out prototype to unspecified params function type + (void)(void(*)()) foo1; // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:18-[[@LINE-1]]:18}:"void" + // .. specified params + (void)(void(*)(void)) foo1; +} + +// K function definition not preceded by full prototype +int foo9(a, b) // expected-warning {{old-style function definition is not preceded by a prototype}} + int a, b; +{ + return a + b; +} + +// Function declaration with no types +void foo10(); // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:12-[[@LINE-1]]:12}:"void" +// K function definition with incomplete param list declared +void foo10(p, p2) void *p; {} // expected-warning {{old-style function definition is not preceded by a prototype}} + +// K function definition with previous prototype declared is not diagnosed. +void foo11(int p, int p2); +void foo11(p, p2) int p; int p2; {} Index: lib/Sema/SemaType.cpp === --- lib/Sema/SemaType.cpp +++ lib/Sema/SemaType.cpp @@ -4320,6 +4320,19 @@ if (FTI.isAmbiguous) warnAboutAmbiguousFunction(S, D, DeclType, T); + // GNU warning -Wstrict-prototypes + // Warn if a function declaration is without a prototype. + // This warning is issued for all kinds of
[PATCH] D16533: Bug 20796 - GCC's -Wstrict-prototypes warning not implemented in Clang
bruno added a comment. Hi Alex, thanks for following up with this! Comment at: lib/Sema/SemaDecl.cpp:11819 + // Warn if K function is defined without previous declaration + // declaration. This warning is issued only if the difinition itself + // does not provide a prototype. Only K definitions do not There's an extra 'declaration' here Comment at: lib/Sema/SemaType.cpp:4189 + if (D.getFunctionDefinitionKind() == FDK_Declaration && + FTI.NumParams == 0 && !LangOpts.CPlusPlus) { +S.Diag(DeclType.Loc, diag::warn_strict_prototypes) No need for the curly braces here! Repository: rL LLVM https://reviews.llvm.org/D16533 ___ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D16533: Bug 20796 - GCC's -Wstrict-prototypes warning not implemented in Clang
arphaman added a comment. Ping Repository: rL LLVM https://reviews.llvm.org/D16533 ___ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D16533: Bug 20796 - GCC's -Wstrict-prototypes warning not implemented in Clang
arphaman added reviewers: rsmith, bruno. arphaman set the repository for this revision to rL LLVM. arphaman updated this revision to Diff 77351. arphaman added a comment. I rebased the patch, adjusted the test and added a test case for Objective-C blocks. Repository: rL LLVM https://reviews.llvm.org/D16533 Files: include/clang/Basic/DiagnosticSemaKinds.td lib/Sema/SemaDecl.cpp lib/Sema/SemaType.cpp test/Sema/warn-strict-prototypes.c test/Sema/warn-strict-prototypes.m Index: test/Sema/warn-strict-prototypes.m === --- /dev/null +++ test/Sema/warn-strict-prototypes.m @@ -0,0 +1,20 @@ +// RUN: %clang_cc1 -fsyntax-only -Wstrict-prototypes -verify -fblocks %s + +@interface Foo + +@property (nonatomic, copy) void (^noProtoBlock)(); // expected-warning {{this function declaration is not a prototype}} +@property (nonatomic, copy) void (^block)(void); // no warning + +- doStuff:(void (^)()) completionHandler; // expected-warning {{this function declaration is not a prototype}} +- doOtherStuff:(void (^)(void)) completionHandler; // no warning + +@end + +void foo() { + void (^block)() = // expected-warning {{this function declaration is not a prototype}} +^void(int arg) { // no warning + }; + void (^block2)(void) = // no warning + ^void() { // expected-warning {{this function declaration is not a prototype}} + }; +} Index: test/Sema/warn-strict-prototypes.c === --- /dev/null +++ test/Sema/warn-strict-prototypes.c @@ -0,0 +1,62 @@ +// RUN: %clang_cc1 -fsyntax-only -Wstrict-prototypes -verify %s +// RUN: %clang_cc1 -fsyntax-only -Wstrict-prototypes -fdiagnostics-parseable-fixits %s 2>&1 | FileCheck %s + +// function declaration with unspecified params +void foo1(); // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:11-[[@LINE-1]]:11}:"void" +// function declaration with 0 params +void foo2(void); + +// function definition with 0 params(for both cases), +// valid according to 6.7.5.3/14 +void foo1() {} +void foo2(void) {} + +// function type typedef unspecified params +typedef void foo3(); // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:19-[[@LINE-1]]:19}:"void" + +// global fp unspecified params +void (*foo4)(); // expected-warning {{this function declaration is not a prototype}} +// CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:14-[[@LINE-1]]:14}:"void" + +// struct member fp unspecified params +struct { void (*foo5)(); } s; // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:23-[[@LINE-1]]:23}:"void" + +// param fp unspecified params +void bar2(void (*foo6)()) { // expected-warning {{this function declaration is not a prototype}} +// CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:24-[[@LINE-1]]:24}:"void" + // local fp unspecified params + void (*foo7)() = 0; // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:16-[[@LINE-1]]:16}:"void" + // array fp unspecified params + void (*foo8[2])() = {0}; // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:19-[[@LINE-1]]:19}:"void" +} + +// function type cast using using an anonymous function declaration +void bar3(void) { + // casting function w/out prototype to unspecified params function type + (void)(void(*)()) foo1; // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:18-[[@LINE-1]]:18}:"void" + // .. specified params + (void)(void(*)(void)) foo1; +} + +// K function definition not preceded by full prototype +int foo9(a, b) // expected-warning {{old-style function definition is not preceded by a prototype}} + int a, b; +{ + return a + b; +} + +// Function declaration with no types +void foo10(); // expected-warning {{this function declaration is not a prototype}} + // CHECK: fix-it:"{{.*}}":{[[@LINE-1]]:12-[[@LINE-1]]:12}:"void" +// K function definition with incomplete param list declared +void foo10(p, p2) void *p; {} // expected-warning {{old-style function definition is not preceded by a prototype}} + +// K function definition with previous prototype declared is not diagnosed. +void foo11(int p, int p2); +void foo11(p, p2) int p; int p2; {} Index: lib/Sema/SemaType.cpp === --- lib/Sema/SemaType.cpp +++ lib/Sema/SemaType.cpp @@ -4177,6 +4177,20 @@ if (FTI.isAmbiguous) warnAboutAmbiguousFunction(S, D, DeclType, T); + // GNU warning -Wstrict-prototypes + // Warn if
[PATCH] D16533: Bug 20796 - GCC's -Wstrict-prototypes warning not implemented in Clang
arphaman added a comment. Hi Paul, Are you planning to work on this patch? If not, can I take a shot at it? Cheers, Alex https://reviews.llvm.org/D16533 ___ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
Re: [PATCH] D16533: Bug 20796 - GCC's -Wstrict-prototypes warning not implemented in Clang
bruno added a subscriber: bruno. bruno added a comment. Hi Paul, I'm interested in this patch. Do you have any plans to wrap it up? https://reviews.llvm.org/D16533 ___ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
RE: [PATCH] D16533: Bug 20796 - GCC's -Wstrict-prototypes warning not implemented in Clang
Thanks for the fast review. > On Mon, Jan 25, 2016 at 03:18:31PM +, Paul Titei via cfe-commits wrote: > > +// function definition with 0 params(for both cases), valid according > > +to 6.7.5.3/14 void foo1() {} > I still want to get a warning for this. At best it is inconsistent. I agree this is inconsistent with GCC behavior of this warning which warns even for void main(){}. But from what I understand the standard makes a distinction between unspecified parameters in declaration VS definitions (C99 6.7.5.3/14): "An empty list in a function declarator that is part of a definition of that function specifies that the function has no parameters." As opposed with: "The empty list in a function declarator that is not part of a definition of that function specifies that no information about the number or types of the parameters is supplied." > > +// Function declaration with no types void foo10(); // > > +expected-warning{{this function declaration is not a prototype}} > > + // CHECK: fix-it:"{{.*}}":{70:12-70:12}:"void" > > +// K function definition with incomplete param list declared void > > +foo10(p, p2) void *p; {} // expected-warning{{old-style function > > +definition is not preceded by a prototype}} > > + > > +// Prototype declaration > > +void foo11(int p, int p2); > > +// K function definition with previous prototype declared is not > > diagnosed. > > +void foo11(p, p2) int p; int p2; {} > Same here. I'm perfectly happy if that is a separate option though. It would make sense to not diagnose this last case since there is there is a previous prototype. Also GCC does not diagnose this: "An old-style function definition is permitted without a warning if preceded by a declaration that specifies the argument types." Paul Titei National Instruments Romania S.R.L. -- B-dul 21 Decembrie 1989, nr. 77, A2 Cluj-Napoca 400604, Romania C.I.F.: RO17961616 | O.R.C.: J12/3337/2005 Telefon: +40 264 406428 | Fax: +40 264 406429 E-mail: office.c...@ni.com Web: romania.ni.com Vanzari si suport tehnic: Telefon gratuit : 0800 070071 E-mail vanzari: ni.roma...@ni.com E-mail suport tehnic: techsupp...@ni.com ___ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
Re: [PATCH] D16533: Bug 20796 - GCC's -Wstrict-prototypes warning not implemented in Clang
Thanks for working on this! On Mon, Jan 25, 2016 at 03:18:31PM +, Paul Titei via cfe-commits wrote: > +// function definition with 0 params(for both cases), valid according to > 6.7.5.3/14 > +void foo1() {} I still want to get a warning for this. At best it is inconsistent. > +// Function declaration with no types > +void foo10(); // expected-warning{{this function declaration is not a > prototype}} > + // CHECK: fix-it:"{{.*}}":{70:12-70:12}:"void" > +// K function definition with incomplete param list declared > +void foo10(p, p2) void *p; {} // expected-warning{{old-style function > definition is not preceded by a prototype}} > + > +// Prototype declaration > +void foo11(int p, int p2); > +// K function definition with previous prototype declared is not diagnosed. > +void foo11(p, p2) int p; int p2; {} Same here. I'm perfectly happy if that is a separate option though. Joerg ___ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
Re: [PATCH] D16533: Bug 20796 - GCC's -Wstrict-prototypes warning not implemented in Clang
thakis added a subscriber: thakis. thakis added a comment. (This is http://llvm.org/PR20796, which has some discussion and test cases. If you haven't, maybe you want to look at the test cases there. It's possible they're a subset of your test though.) http://reviews.llvm.org/D16533 ___ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits