[PATCH] D64874: [Sema] Improve handling of function pointer conversions

2019-11-16 Thread Mark de Wever via Phabricator via cfe-commits
Mordante added a comment.

@rsmith I now have commit access so I can commit the patch. Any suggestions 
regarding the previous remark?


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D64874/new/

https://reviews.llvm.org/D64874



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D64874: [Sema] Improve handling of function pointer conversions

2019-10-12 Thread Mark de Wever via Phabricator via cfe-commits
Mordante updated this revision to Diff 224753.
Mordante added a comment.

Removed the language version test.

I also added `clang/test/CXX/conv/conv.fctptr/template-noreturn.cpp` to show 
this is not enough to allow `noreturn` to all language versions, so this file 
should not be committed.

Do you want me to look at a way to allow the `noreturn` for C++98/C++11? If yes 
I prefer to make that a separate commit.

AFAIK the `[[noreturn]]` conversion is a clang extension, should I file a DR 
for the standard? AFAIK there isn't one yet.

If you still like the patch could you commit it (except 
`clang/test/CXX/conv/conv.fctptr/template-noreturn.cpp`) since I don't have 
commit access?


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D64874/new/

https://reviews.llvm.org/D64874

Files:
  clang/lib/Sema/SemaTemplate.cpp
  clang/test/CXX/conv/conv.fctptr/template-noexcept.cpp
  clang/test/CXX/conv/conv.fctptr/template-noreturn.cpp

Index: clang/test/CXX/conv/conv.fctptr/template-noreturn.cpp
===
--- /dev/null
+++ clang/test/CXX/conv/conv.fctptr/template-noreturn.cpp
@@ -0,0 +1,36 @@
+// RUN: %clang_cc1 -std=c++11 -fsyntax-only -verify %s
+// RUN: %clang_cc1 -std=c++14 -fsyntax-only -verify %s
+// RUN: %clang_cc1 -std=c++17 -fsyntax-only -verify %s
+// RUN: %clang_cc1 -std=c++2a -fsyntax-only -verify %s
+
+typedef int (*fp)();
+typedef int (*fpnr)() __attribute__((noreturn));
+#if __cplusplus < 201703L
+// expected-note@+2 {{template parameter is declared here}}
+#endif
+template 
+struct FP {};
+
+#if __cplusplus < 201703L
+// expected-note@+2 {{template parameter is declared here}}
+#endif
+template 
+struct FPNR {};
+
+int f();
+int fnr() __attribute__((noreturn));
+
+FP<&f> fp_valid;
+FPNR<&fnr> fpnr_valid;
+
+#if __cplusplus < 201703L
+// expected-error@+2 {{non-type template argument of type 'int (*)() __attribute__((noreturn))' cannot be converted to a value of type 'fp' (aka 'int (*)()')}}
+#endif
+FP<&fnr> fp_invalid_before_cxx17;
+
+#if __cplusplus < 201703L
+// expected-error@+4 {{non-type template argument of type 'int (*)()' cannot be converted to a value of type 'fpnr' (aka 'int (*)() __attribute__((noreturn))')}}
+#else
+// expected-error@+2 {{value of type 'int (*)()' is not implicitly convertible to 'fpnr' (aka 'int (*)() __attribute__((noreturn))')}}
+#endif
+FPNR<&f> fpnr_invalid;
Index: clang/test/CXX/conv/conv.fctptr/template-noexcept.cpp
===
--- /dev/null
+++ clang/test/CXX/conv/conv.fctptr/template-noexcept.cpp
@@ -0,0 +1,44 @@
+// RUN: %clang_cc1 -std=c++11 -fsyntax-only -verify %s
+// RUN: %clang_cc1 -std=c++14 -fsyntax-only -verify %s
+// RUN: %clang_cc1 -std=c++17 -fsyntax-only -verify %s
+// RUN: %clang_cc1 -std=c++2a -fsyntax-only -verify %s
+
+// Starting with C++17 the noexcept is part of the function signature but
+// a noexcept function can be converted to a noexcept(false) function.
+// The tests were added for PR40024.
+
+#if __cplusplus < 201703L
+// expected-no-diagnostics
+#endif
+
+namespace valid_conversion {
+struct S {
+  int f(void) noexcept { return 110; }
+} s;
+
+template 
+int f10(void) { return (s.*a)(); }
+
+int foo(void) {
+  return f10<&S::f>();
+}
+} // namespace valid_conversion
+
+namespace invalid_conversion {
+struct S {
+  int f(void) { return 110; }
+} s;
+
+#if __cplusplus >= 201703L
+// expected-note@+3 {{candidate template ignored: invalid explicitly-specified argument for template parameter 'a'}}
+#endif
+template 
+int f10(void) { return (s.*a)(); }
+
+#if __cplusplus >= 201703L
+// expected-error@+3 {{no matching function for call to 'f10'}}
+#endif
+int foo(void) {
+  return f10<&S::f>();
+}
+} // namespace invalid_conversion
Index: clang/lib/Sema/SemaTemplate.cpp
===
--- clang/lib/Sema/SemaTemplate.cpp
+++ clang/lib/Sema/SemaTemplate.cpp
@@ -6991,6 +6991,13 @@
 ObjCLifetimeConversion))
 RefExpr = ImpCastExprToType(RefExpr.get(), ParamType.getUnqualifiedType(), CK_NoOp);
 
+  // Starting with C++17 the noexcept is part of the function signature but
+  // a noexcept function can be converted to a noexcept(false) function.
+  QualType ResultTy;
+  if (IsFunctionConversion(((Expr *)RefExpr.get())->getType(),
+   ParamType.getUnqualifiedType(), ResultTy))
+RefExpr = ImpCastExprToType(RefExpr.get(), ResultTy, CK_NoOp);
+
   assert(!RefExpr.isInvalid() &&
  Context.hasSameType(((Expr*) RefExpr.get())->getType(),
  ParamType.getUnqualifiedType()));
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D64874: [Sema] Improve handling of function pointer conversions

2019-10-04 Thread Richard Smith - zygoloid via Phabricator via cfe-commits
rsmith accepted this revision.
rsmith added a comment.
This revision is now accepted and ready to land.

LGTM, though I'd like to see this generalized to handle noreturn too.




Comment at: clang/lib/Sema/SemaTemplate.cpp:6997
+  QualType ResultTy;
+  if (getLangOpts().CPlusPlus17 &&
+  IsFunctionConversion(((Expr *)RefExpr.get())->getType(),

Can we remove the check for C++17 here? I would expect we want to consider the 
other kind of function conversion (from noreturn function to 
potentially-returning function) here too, and that applies in all language 
modes.

Testcase for that bug:

```
template struct X {};
int f() __attribute__((noreturn));
X<&f> x;
```


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D64874/new/

https://reviews.llvm.org/D64874



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D64874: [Sema] Improve handling of function pointer conversions

2019-08-31 Thread Mark de Wever via Phabricator via cfe-commits
Mordante updated this revision to Diff 218215.
Mordante added a comment.

Addresses the review remarks:

- resultTy -> ResultTy
- Move all unit tests in one file
- Change the unit test to use `-verify` instead of `FileCheck`
- Use PR40024 instead of link to Bugzilla


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D64874/new/

https://reviews.llvm.org/D64874

Files:
  clang/lib/Sema/SemaTemplate.cpp
  clang/test/CXX/conv/conv.fctptr/template-noexcept.cpp


Index: clang/test/CXX/conv/conv.fctptr/template-noexcept.cpp
===
--- /dev/null
+++ clang/test/CXX/conv/conv.fctptr/template-noexcept.cpp
@@ -0,0 +1,44 @@
+// RUN: %clang_cc1 -std=c++11 -fsyntax-only -verify %s
+// RUN: %clang_cc1 -std=c++14 -fsyntax-only -verify %s
+// RUN: %clang_cc1 -std=c++17 -fsyntax-only -verify %s
+// RUN: %clang_cc1 -std=c++2a -fsyntax-only -verify %s
+
+// Starting with C++17 the noexcept is part of the function signature but
+// a noexcept function can be converted to a noexcept(false) function.
+// The tests were added for PR40024.
+
+#if __cplusplus < 201703L
+// expected-no-diagnostics
+#endif
+
+namespace valid_conversion {
+struct S {
+  int f(void) noexcept { return 110; }
+} s;
+
+template 
+int f10(void) { return (s.*a)(); }
+
+int foo(void) {
+  return f10<&S::f>();
+}
+} // namespace valid_conversion
+
+namespace invalid_conversion {
+struct S {
+  int f(void) { return 110; }
+} s;
+
+#if __cplusplus >= 201703L
+// expected-note@+3 {{candidate template ignored: invalid explicitly-specified 
argument for template parameter 'a'}}
+#endif
+template 
+int f10(void) { return (s.*a)(); }
+
+#if __cplusplus >= 201703L
+// expected-error@+3 {{no matching function for call to 'f10'}}
+#endif
+int foo(void) {
+  return f10<&S::f>();
+}
+} // namespace invalid_conversion
Index: clang/lib/Sema/SemaTemplate.cpp
===
--- clang/lib/Sema/SemaTemplate.cpp
+++ clang/lib/Sema/SemaTemplate.cpp
@@ -6991,6 +6991,14 @@
 ObjCLifetimeConversion))
 RefExpr = ImpCastExprToType(RefExpr.get(), 
ParamType.getUnqualifiedType(), CK_NoOp);
 
+  // Starting with C++17 the noexcept is part of the function signature but
+  // a noexcept function can be converted to a noexcept(false) function.
+  QualType ResultTy;
+  if (getLangOpts().CPlusPlus17 &&
+  IsFunctionConversion(((Expr *)RefExpr.get())->getType(),
+   ParamType.getUnqualifiedType(), ResultTy))
+RefExpr = ImpCastExprToType(RefExpr.get(), ResultTy, CK_NoOp);
+
   assert(!RefExpr.isInvalid() &&
  Context.hasSameType(((Expr*) RefExpr.get())->getType(),
  ParamType.getUnqualifiedType()));


Index: clang/test/CXX/conv/conv.fctptr/template-noexcept.cpp
===
--- /dev/null
+++ clang/test/CXX/conv/conv.fctptr/template-noexcept.cpp
@@ -0,0 +1,44 @@
+// RUN: %clang_cc1 -std=c++11 -fsyntax-only -verify %s
+// RUN: %clang_cc1 -std=c++14 -fsyntax-only -verify %s
+// RUN: %clang_cc1 -std=c++17 -fsyntax-only -verify %s
+// RUN: %clang_cc1 -std=c++2a -fsyntax-only -verify %s
+
+// Starting with C++17 the noexcept is part of the function signature but
+// a noexcept function can be converted to a noexcept(false) function.
+// The tests were added for PR40024.
+
+#if __cplusplus < 201703L
+// expected-no-diagnostics
+#endif
+
+namespace valid_conversion {
+struct S {
+  int f(void) noexcept { return 110; }
+} s;
+
+template 
+int f10(void) { return (s.*a)(); }
+
+int foo(void) {
+  return f10<&S::f>();
+}
+} // namespace valid_conversion
+
+namespace invalid_conversion {
+struct S {
+  int f(void) { return 110; }
+} s;
+
+#if __cplusplus >= 201703L
+// expected-note@+3 {{candidate template ignored: invalid explicitly-specified argument for template parameter 'a'}}
+#endif
+template 
+int f10(void) { return (s.*a)(); }
+
+#if __cplusplus >= 201703L
+// expected-error@+3 {{no matching function for call to 'f10'}}
+#endif
+int foo(void) {
+  return f10<&S::f>();
+}
+} // namespace invalid_conversion
Index: clang/lib/Sema/SemaTemplate.cpp
===
--- clang/lib/Sema/SemaTemplate.cpp
+++ clang/lib/Sema/SemaTemplate.cpp
@@ -6991,6 +6991,14 @@
 ObjCLifetimeConversion))
 RefExpr = ImpCastExprToType(RefExpr.get(), ParamType.getUnqualifiedType(), CK_NoOp);
 
+  // Starting with C++17 the noexcept is part of the function signature but
+  // a noexcept function can be converted to a noexcept(false) function.
+  QualType ResultTy;
+  if (getLangOpts().CPlusPlus17 &&
+  IsFunctionConversion(((Expr *)RefExpr.get())->getType(),
+   ParamType.getUnqualifiedType(), ResultTy))
+RefExpr = ImpCastExprToType(RefExpr.get(), ResultTy, 

[PATCH] D64874: [Sema] Improve handling of function pointer conversions

2019-08-29 Thread Richard Smith - zygoloid via Phabricator via cfe-commits
rsmith added inline comments.



Comment at: clang/lib/Sema/SemaTemplate.cpp:6996
+  // a noexcept function can be converted to a noexcept(false) function.
+  QualType resultTy;
+  if (getLangOpts().CPlusPlus17 &&

Please capitalize local variable names to match the local convention.



Comment at: clang/test/CXX/conv/conv.fctptr/template-noexcept-invalid.cpp:8
+// a noexcept function can be converted to a noexcept(false) function.
+// The tests were added for https://bugs.llvm.org/show_bug.cgi?id=40024
+// Tests the no longer valid function pointer conversions

You can just say PR40024 instead of spelling out the complete URL. That'll also 
work better if we migrate our bug tracker to a different system one day. 
(Incidentally, llvm.org/PR40024 works too.)



Comment at: clang/test/CXX/conv/conv.fctptr/template-noexcept-invalid.cpp:22
+
+// CHECK: error: no matching function for call to 'f10'

Please use a `-verify` test for this instead of `FileCheck`, and combine the 
`-valid` and `-invalid` testcases into the same test file.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D64874/new/

https://reviews.llvm.org/D64874



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits