xbolva00 updated this revision to Diff 511498.
xbolva00 added a comment.
Herald added subscribers: llvm-commits, pengfei, hiraditya.
Herald added a project: LLVM.
Added location when emiting diagnostic about failed TCO in the backend.


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

https://reviews.llvm.org/D147714

Files:
  clang/include/clang/Basic/Attr.td
  clang/include/clang/Basic/AttrDocs.td
  clang/include/clang/Sema/Sema.h
  clang/lib/Sema/SemaStmt.cpp
  clang/test/SemaCXX/attr-musttail.cpp
  llvm/lib/Target/X86/X86ISelLowering.cpp
  llvm/test/CodeGen/X86/tailcc-notail.ll

Index: llvm/test/CodeGen/X86/tailcc-notail.ll
===================================================================
--- llvm/test/CodeGen/X86/tailcc-notail.ll
+++ llvm/test/CodeGen/X86/tailcc-notail.ll
@@ -1,6 +1,6 @@
 ; RUN: not --crash llc -mtriple=x86_64-linux-gnu %s -o - 2>&1 | FileCheck %s
 
-; CHECK: LLVM ERROR: failed to perform tail call elimination on a call site marked musttail
+; CHECK: error: {{.*}} in function caller {{.*}}: failed to perform tail call elimination on a call site marked musttail
 declare tailcc [16 x i64] @callee()
 define tailcc [16 x i64] @caller() {
   %res = musttail call tailcc [16 x i64] @callee()
Index: llvm/lib/Target/X86/X86ISelLowering.cpp
===================================================================
--- llvm/lib/Target/X86/X86ISelLowering.cpp
+++ llvm/lib/Target/X86/X86ISelLowering.cpp
@@ -4507,7 +4507,7 @@
   }
 
   if (IsMustTail && !isTailCall)
-    report_fatal_error("failed to perform tail call elimination on a call "
+    errorUnsupported(DAG, dl, "failed to perform tail call elimination on a call "
                        "site marked musttail");
 
   assert(!(isVarArg && canGuaranteeTCO(CallConv)) &&
Index: clang/test/SemaCXX/attr-musttail.cpp
===================================================================
--- clang/test/SemaCXX/attr-musttail.cpp
+++ clang/test/SemaCXX/attr-musttail.cpp
@@ -6,6 +6,7 @@
   [[clang::musttail(1, 2)]] return ReturnsInt1(); // expected-error {{'musttail' attribute takes no arguments}}
   [[clang::musttail]] return 5;                   // expected-error {{'musttail' attribute requires that the return value is the result of a function call}}
   [[clang::musttail]] return ReturnsInt1();
+  [[clang::nonportable_musttail]] return ReturnsInt1();
 }
 
 void NoFunctionCall() {
@@ -20,6 +21,11 @@
   return NoParams();  // expected-error {{cannot perform a tail call to function 'NoParams' because its signature is incompatible with the calling function}}
 }
 
+void TestParamArityMismatchNonPortable(int x) {
+  [[clang::nonportable_musttail]]
+  return NoParams();
+}
+
 void LongParam(long x); // expected-note {{target function has type mismatch at 1st parameter (expected 'long' but has 'int')}}
 void TestParamTypeMismatch(int x) {
   [[clang::musttail]]  // expected-note {{tail call required by 'musttail' attribute here}}
@@ -267,3 +273,17 @@
 void TestCallNonValue() {
   [[clang::musttail]] return ns; // expected-error {{unexpected namespace name 'ns': expected expression}}
 }
+
+struct Foo {
+  int foo(int) { return 0; }
+};
+
+struct Bar {
+  Foo foo;
+  int bar(int);
+};
+
+int Bar::bar(int x) {
+  [[clang::nonportable_musttail]]
+  return foo.foo(x);
+}
Index: clang/lib/Sema/SemaStmt.cpp
===================================================================
--- clang/lib/Sema/SemaStmt.cpp
+++ clang/lib/Sema/SemaStmt.cpp
@@ -586,7 +586,7 @@
   // attributes lands.
   for (const auto *A : Attrs) {
     if (A->getKind() == attr::MustTail) {
-      if (!checkAndRewriteMustTailAttr(SubStmt, *A)) {
+      if (!checkAndRewriteMustTailAttr(SubStmt, *cast<MustTailAttr>(A))) {
         return SubStmt;
       }
       setFunctionHasMustTail();
@@ -608,7 +608,7 @@
   return SubStmt;
 }
 
-bool Sema::checkAndRewriteMustTailAttr(Stmt *St, const Attr &MTA) {
+bool Sema::checkAndRewriteMustTailAttr(Stmt *St, const MustTailAttr &MTA) {
   ReturnStmt *R = cast<ReturnStmt>(St);
   Expr *E = R->getRetValue();
 
@@ -633,7 +633,7 @@
   return true;
 }
 
-bool Sema::checkMustTailAttr(const Stmt *St, const Attr &MTA) {
+bool Sema::checkMustTailAttr(const Stmt *St, const MustTailAttr &MTA) {
   assert(!CurContext->isDependentContext() &&
          "musttail cannot be checked from a dependent context");
 
@@ -846,6 +846,9 @@
     return true;
   };
 
+  if (MTA.isNonPortableMustTail())
+    return true;
+
   PartialDiagnostic PD = PDiag(diag::note_musttail_mismatch);
   if (!CheckTypesMatch(CallerType, CalleeType, PD)) {
     if (const auto *ND = dyn_cast_or_null<NamedDecl>(CE->getCalleeDecl()))
Index: clang/include/clang/Sema/Sema.h
===================================================================
--- clang/include/clang/Sema/Sema.h
+++ clang/include/clang/Sema/Sema.h
@@ -12351,12 +12351,12 @@
   /// issuing a diagnostic and returning false if not. In the success case,
   /// the statement is rewritten to remove implicit nodes from the return
   /// value.
-  bool checkAndRewriteMustTailAttr(Stmt *St, const Attr &MTA);
+  bool checkAndRewriteMustTailAttr(Stmt *St, const MustTailAttr &MTA);
 
 private:
   /// Check whether the given statement can have musttail applied to it,
   /// issuing a diagnostic and returning false if not.
-  bool checkMustTailAttr(const Stmt *St, const Attr &MTA);
+  bool checkMustTailAttr(const Stmt *St, const MustTailAttr &MTA);
 
 public:
   /// Check to see if a given expression could have '.c_str()' called on it.
Index: clang/include/clang/Basic/AttrDocs.td
===================================================================
--- clang/include/clang/Basic/AttrDocs.td
+++ clang/include/clang/Basic/AttrDocs.td
@@ -605,7 +605,8 @@
 old style K&R C function declarations.
 
 ``clang::musttail`` provides assurances that the tail call can be optimized on
-all targets, not just one.
+all targets, not just one. If you care about one target and you do not need
+these assurances, use ``clang::nonportable_musttail``.
   }];
 }
 
Index: clang/include/clang/Basic/Attr.td
===================================================================
--- clang/include/clang/Basic/Attr.td
+++ clang/include/clang/Basic/Attr.td
@@ -1470,8 +1470,9 @@
 }
 
 def MustTail : StmtAttr {
-  let Spellings = [Clang<"musttail">];
+  let Spellings = [Clang<"musttail">, Clang<"nonportable_musttail">];
   let Documentation = [MustTailDocs];
+  let Accessors = [Accessor<"isNonPortableMustTail", [Clang<"nonportable_musttail">]>];
   let Subjects = SubjectList<[ReturnStmt], ErrorDiag, "return statements">;
 }
 
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to