[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-28 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 created this revision.
appmonster007 added a reviewer: aaron.ballman.
appmonster007 added a project: clang.
Herald added a project: All.
appmonster007 requested review of this revision.
Herald added a subscriber: cfe-commits.

Fixing issue "incorrect -Winfinite-recursion warning on potentially-unevaluated 
operand #21668”

By having dedicated visit function (`VisitCXXTypeidExpr`) for `typeid`, instead 
of using default (`VisitStmt`).
In this new function we skip over CFG build for unevaluated operands of `typeid`


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D128747

Files:
  clang/lib/Analysis/CFG.cpp
  clang/test/SemaCXX/warn-infinite-recursion.cpp


Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -1,5 +1,7 @@
 // RUN: %clang_cc1 %s -fsyntax-only -verify -Winfinite-recursion
 
+#include 
+
 void a() {  // expected-warning{{call itself}}
   a();
 }
@@ -171,3 +173,18 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+struct Q {
+  virtual ~Q(){};
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) {
+  typeid(evaluated_recursive_function(x));
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  typeid(unevaluated_recursive_function());
+  return 0;
+}
\ No newline at end of file
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,28 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   polymorphic class type [...] [the] expression is an unevaluated
+  //   operand. [...]
+  // We add only potentially evaluated statements to block to avoid
+  // CFG generation for unevaluated operands.
+  if (S && !S->isTypeDependent()) {
+if (S->isPotentiallyEvaluated()) {
+  return VisitChildren(S);
+}
+  }
+
+  // Return block without CFG for unevaluated operands.
+  return Block;
+}
+
 CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
   CFGBlock *LoopSuccessor = nullptr;
 


Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -1,5 +1,7 @@
 // RUN: %clang_cc1 %s -fsyntax-only -verify -Winfinite-recursion
 
+#include 
+
 void a() {  // expected-warning{{call itself}}
   a();
 }
@@ -171,3 +173,18 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+struct Q {
+  virtual ~Q(){};
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) {
+  typeid(evaluated_recursive_function(x));
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  typeid(unevaluated_recursive_function());
+  return 0;
+}
\ No newline at end of file
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,28 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to 

[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-28 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 updated this revision to Diff 440819.
appmonster007 added a comment.

fixed warning comments for test cases


Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

Files:
  clang/lib/Analysis/CFG.cpp
  clang/test/SemaCXX/warn-infinite-recursion.cpp


Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -1,5 +1,7 @@
 // RUN: %clang_cc1 %s -fsyntax-only -verify -Winfinite-recursion
 
+#include 
+
 void a() {  // expected-warning{{call itself}}
   a();
 }
@@ -171,3 +173,18 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+struct Q {
+  virtual ~Q(){};
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) {  // expected-warning{{call itself}}
+  (void)typeid(evaluated_recursive_function(x));  // expected-warning 
{{expression with side effects will be evaluated despite being used as an 
operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
\ No newline at end of file
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,28 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   polymorphic class type [...] [the] expression is an unevaluated
+  //   operand. [...]
+  // We add only potentially evaluated statements to block to avoid
+  // CFG generation for unevaluated operands.
+  if (S && !S->isTypeDependent()) {
+if (S->isPotentiallyEvaluated()) {
+  return VisitChildren(S);
+}
+  }
+
+  // Return block without CFG for unevaluated operands.
+  return Block;
+}
+
 CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
   CFGBlock *LoopSuccessor = nullptr;
 


Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -1,5 +1,7 @@
 // RUN: %clang_cc1 %s -fsyntax-only -verify -Winfinite-recursion
 
+#include 
+
 void a() {  // expected-warning{{call itself}}
   a();
 }
@@ -171,3 +173,18 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+struct Q {
+  virtual ~Q(){};
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) {  // expected-warning{{call itself}}
+  (void)typeid(evaluated_recursive_function(x));  // expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
\ No newline at end of file
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,28 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expressio

[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-28 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 updated this revision to Diff 440835.
appmonster007 added a comment.

included typeinfo file, in clang/test/SemaCXX directory


Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

Files:
  clang/lib/Analysis/CFG.cpp
  clang/test/SemaCXX/typeinfo
  clang/test/SemaCXX/warn-infinite-recursion.cpp

Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -1,5 +1,7 @@
 // RUN: %clang_cc1 %s -fsyntax-only -verify -Winfinite-recursion
 
+#include 
+
 void a() {  // expected-warning{{call itself}}
   a();
 }
@@ -171,3 +173,18 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+struct Q {
+  virtual ~Q(){};
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) {  // expected-warning{{call itself}}
+  (void)typeid(evaluated_recursive_function(x));  // expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
\ No newline at end of file
Index: clang/test/SemaCXX/typeinfo
===
--- /dev/null
+++ clang/test/SemaCXX/typeinfo
@@ -0,0 +1,16 @@
+namespace std {
+  class type_info {
+  public:
+virtual ~type_info();
+const char* name() const { return __name; }
+bool operator==(const type_info& __arg) const {
+ return __name == __arg.__name;
+}
+
+bool operator!=(const type_info& __arg) const {
+  return !operator==(__arg);
+}
+  protected:
+const char *__name;
+  };
+}
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,28 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   polymorphic class type [...] [the] expression is an unevaluated
+  //   operand. [...]
+  // We add only potentially evaluated statements to block to avoid
+  // CFG generation for unevaluated operands.
+  if (S && !S->isTypeDependent()) {
+if (S->isPotentiallyEvaluated()) {
+  return VisitChildren(S);
+}
+  }
+
+  // Return block without CFG for unevaluated operands.
+  return Block;
+}
+
 CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
   CFGBlock *LoopSuccessor = nullptr;
 
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-28 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 updated this revision to Diff 440845.
appmonster007 added a comment.

#include "typeinfo"


Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

Files:
  clang/lib/Analysis/CFG.cpp
  clang/test/SemaCXX/typeinfo
  clang/test/SemaCXX/warn-infinite-recursion.cpp

Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -1,5 +1,7 @@
 // RUN: %clang_cc1 %s -fsyntax-only -verify -Winfinite-recursion
 
+#include "typeinfo"
+
 void a() {  // expected-warning{{call itself}}
   a();
 }
@@ -171,3 +173,18 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+struct Q {
+  virtual ~Q(){};
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) {  // expected-warning{{call itself}}
+  (void)typeid(evaluated_recursive_function(x));  // expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
\ No newline at end of file
Index: clang/test/SemaCXX/typeinfo
===
--- /dev/null
+++ clang/test/SemaCXX/typeinfo
@@ -0,0 +1,16 @@
+namespace std {
+  class type_info {
+  public:
+virtual ~type_info();
+const char* name() const { return __name; }
+bool operator==(const type_info& __arg) const {
+ return __name == __arg.__name;
+}
+
+bool operator!=(const type_info& __arg) const {
+  return !operator==(__arg);
+}
+  protected:
+const char *__name;
+  };
+}
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,28 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   polymorphic class type [...] [the] expression is an unevaluated
+  //   operand. [...]
+  // We add only potentially evaluated statements to block to avoid
+  // CFG generation for unevaluated operands.
+  if (S && !S->isTypeDependent()) {
+if (S->isPotentiallyEvaluated()) {
+  return VisitChildren(S);
+}
+  }
+
+  // Return block without CFG for unevaluated operands.
+  return Block;
+}
+
 CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
   CFGBlock *LoopSuccessor = nullptr;
 
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-28 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 added inline comments.



Comment at: clang/test/SemaCXX/warn-infinite-recursion.cpp:3
 
+#include "typeinfo"
+

`#include ` resulted in 'typeinfo' file not found with  
include; use "quotes" instead


Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

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


[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-28 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 updated this revision to Diff 440856.

Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

Files:
  clang/lib/Analysis/CFG.cpp
  clang/test/SemaCXX/warn-infinite-recursion.cpp


Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -1,5 +1,7 @@
 // RUN: %clang_cc1 %s -fsyntax-only -verify -Winfinite-recursion
 
+#include "typeinfo"
+
 void a() {  // expected-warning{{call itself}}
   a();
 }
@@ -171,3 +173,18 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+struct Q {
+  virtual ~Q(){};
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) { // expected-warning{{call 
itself}}
+  (void)typeid(evaluated_recursive_function(x)); // expected-warning 
{{expression with side effects will be evaluated despite being used as an 
operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
\ No newline at end of file
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,28 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   polymorphic class type [...] [the] expression is an unevaluated
+  //   operand. [...]
+  // We add only potentially evaluated statements to block to avoid
+  // CFG generation for unevaluated operands.
+  if (S && !S->isTypeDependent()) {
+if (S->isPotentiallyEvaluated()) {
+  return VisitChildren(S);
+}
+  }
+
+  // Return block without CFG for unevaluated operands.
+  return Block;
+}
+
 CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
   CFGBlock *LoopSuccessor = nullptr;
 


Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -1,5 +1,7 @@
 // RUN: %clang_cc1 %s -fsyntax-only -verify -Winfinite-recursion
 
+#include "typeinfo"
+
 void a() {  // expected-warning{{call itself}}
   a();
 }
@@ -171,3 +173,18 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+struct Q {
+  virtual ~Q(){};
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) { // expected-warning{{call itself}}
+  (void)typeid(evaluated_recursive_function(x)); // expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
\ No newline at end of file
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,28 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   p

[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-28 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 updated this revision to Diff 440859.

Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

Files:
  clang/lib/Analysis/CFG.cpp
  clang/test/SemaCXX/typeinfo
  clang/test/SemaCXX/warn-infinite-recursion.cpp

Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -1,5 +1,7 @@
 // RUN: %clang_cc1 %s -fsyntax-only -verify -Winfinite-recursion
 
+#include "typeinfo"
+
 void a() {  // expected-warning{{call itself}}
   a();
 }
@@ -171,3 +173,18 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+struct Q {
+  virtual ~Q(){};
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) { // expected-warning{{call itself}}
+  (void)typeid(evaluated_recursive_function(x)); // expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
\ No newline at end of file
Index: clang/test/SemaCXX/typeinfo
===
--- /dev/null
+++ clang/test/SemaCXX/typeinfo
@@ -0,0 +1,16 @@
+namespace std {
+  class type_info {
+  public:
+virtual ~type_info();
+const char* name() const { return __name; }
+bool operator==(const type_info& __arg) const {
+ return __name == __arg.__name;
+}
+
+bool operator!=(const type_info& __arg) const {
+  return !operator==(__arg);
+}
+  protected:
+const char *__name;
+  };
+}
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,28 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   polymorphic class type [...] [the] expression is an unevaluated
+  //   operand. [...]
+  // We add only potentially evaluated statements to block to avoid
+  // CFG generation for unevaluated operands.
+  if (S && !S->isTypeDependent()) {
+if (S->isPotentiallyEvaluated()) {
+  return VisitChildren(S);
+}
+  }
+
+  // Return block without CFG for unevaluated operands.
+  return Block;
+}
+
 CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
   CFGBlock *LoopSuccessor = nullptr;
 
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-29 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 updated this revision to Diff 440992.
appmonster007 added a comment.

inserted bullet point for `-Winfinite-recursion` diagnostics fix, where 
diagnostic will not warn for unevaluated operands of ``typeid`` expression, 
under "Improvements to Clang’s diagnostics" in clang/docs/ReleaseNotes.rst

fixed issue with typeinfo header, just included it directly in 
`warn-infinite-recursion.cpp` file

fixed recommended minor changes


Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

Files:
  clang/docs/ReleaseNotes.rst
  clang/lib/Analysis/CFG.cpp
  clang/test/SemaCXX/warn-infinite-recursion.cpp

Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -171,3 +171,35 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+namespace std {
+class type_info {
+public:
+  virtual ~type_info();
+  const char *name() const { return __name; }
+  bool operator==(const type_info &__arg) const {
+return __name == __arg.__name;
+  }
+
+  bool operator!=(const type_info &__arg) const {
+return !operator==(__arg);
+  }
+
+protected:
+  const char *__name;
+};
+} // namespace std
+struct Q {
+  virtual ~Q(){};
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) { // expected-warning{{call itself}}
+  (void)typeid(evaluated_recursive_function(x)); // expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,25 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   polymorphic class type [...] [the] expression is an unevaluated
+  //   operand. [...]
+  // We add only potentially evaluated statements to the block to avoid
+  // CFG generation for unevaluated operands.
+  if (S && !S->isTypeDependent() && S->isPotentiallyEvaluated())
+return VisitChildren(S);
+
+  // Return block without CFG for unevaluated operands.
+  return Block;
+}
+
 CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
   CFGBlock *LoopSuccessor = nullptr;
 
Index: clang/docs/ReleaseNotes.rst
===
--- clang/docs/ReleaseNotes.rst
+++ clang/docs/ReleaseNotes.rst
@@ -267,6 +267,10 @@
 - When using class templates without arguments, clang now tells developers
   that template arguments are missing in certain contexts.
   This fixes `Issue 55962 `_.
+- The ``-Winfinite-recursion`` diagnostic will not warn for 
+  unevaluated operands of ``typeid`` expression. Unevaluated 
+  operands of ``typeid`` expression are skipped for the CFG build. 
+  This fixes `Issue 21668 `_.
 
 Non-comprehensive list of changes in this release
 -
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-29 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 updated this revision to Diff 440997.
appmonster007 marked an inline comment as done.

Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

Files:
  clang/docs/ReleaseNotes.rst
  clang/lib/Analysis/CFG.cpp
  clang/test/SemaCXX/warn-infinite-recursion.cpp

Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -171,3 +171,35 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+namespace std {
+class type_info {
+public:
+  virtual ~type_info();
+  const char *name() const { return __name; }
+  bool operator==(const type_info &__arg) const {
+return __name == __arg.__name;
+  }
+
+  bool operator!=(const type_info &__arg) const {
+return !operator==(__arg);
+  }
+
+protected:
+  const char *__name;
+};
+} // namespace std
+struct Q {
+  virtual ~Q() = default;
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) { // expected-warning{{call itself}}
+  (void)typeid(evaluated_recursive_function(x)); // expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,25 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   polymorphic class type [...] [the] expression is an unevaluated
+  //   operand. [...]
+  // We add only potentially evaluated statements to the block to avoid
+  // CFG generation for unevaluated operands.
+  if (S && !S->isTypeDependent() && S->isPotentiallyEvaluated())
+return VisitChildren(S);
+
+  // Return block without CFG for unevaluated operands.
+  return Block;
+}
+
 CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
   CFGBlock *LoopSuccessor = nullptr;
 
Index: clang/docs/ReleaseNotes.rst
===
--- clang/docs/ReleaseNotes.rst
+++ clang/docs/ReleaseNotes.rst
@@ -267,6 +267,10 @@
 - When using class templates without arguments, clang now tells developers
   that template arguments are missing in certain contexts.
   This fixes `Issue 55962 `_.
+- The ``-Winfinite-recursion`` diagnostic will not warn for 
+  unevaluated operands of ``typeid`` expression. Unevaluated 
+  operands of ``typeid`` expression are skipped for the CFG build. 
+  This fixes `Issue 21668 `_.
 
 Non-comprehensive list of changes in this release
 -
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-29 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 updated this revision to Diff 440999.

Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

Files:
  clang/docs/ReleaseNotes.rst
  clang/lib/Analysis/CFG.cpp
  clang/test/SemaCXX/warn-infinite-recursion.cpp

Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -171,3 +171,35 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+namespace std {
+class type_info {
+public:
+  virtual ~type_info();
+  const char *name() const { return __name; }
+  bool operator==(const type_info &__arg) const {
+return __name == __arg.__name;
+  }
+
+  bool operator!=(const type_info &__arg) const {
+return !operator==(__arg);
+  }
+
+protected:
+  const char *__name;
+};
+} // namespace std
+struct Q {
+  virtual ~Q() = default;
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) { // expected-warning{{call itself}}
+  (void)typeid(evaluated_recursive_function(x)); // expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,25 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   polymorphic class type [...] [the] expression is an unevaluated
+  //   operand. [...]
+  // We add only potentially evaluated statements to the block to avoid
+  // CFG generation for unevaluated operands.
+  if (S && !S->isTypeDependent() && S->isPotentiallyEvaluated())
+return VisitChildren(S);
+
+  // Return block without CFG for unevaluated operands.
+  return Block;
+}
+
 CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
   CFGBlock *LoopSuccessor = nullptr;
 
Index: clang/docs/ReleaseNotes.rst
===
--- clang/docs/ReleaseNotes.rst
+++ clang/docs/ReleaseNotes.rst
@@ -267,6 +267,10 @@
 - When using class templates without arguments, clang now tells developers
   that template arguments are missing in certain contexts.
   This fixes `Issue 55962 `_.
+- The ``-Winfinite-recursion`` diagnostic will not warn for
+  unevaluated operands of ``typeid`` expression. Unevaluated
+  operands of ``typeid`` expression are skipped for the CFG build.
+  This fixes `Issue 21668 `_.
 
 Non-comprehensive list of changes in this release
 -
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-29 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 updated this revision to Diff 441005.

Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

Files:
  clang/docs/ReleaseNotes.rst
  clang/lib/Analysis/CFG.cpp
  clang/test/SemaCXX/warn-infinite-recursion.cpp

Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -171,3 +171,35 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+namespace std {
+class type_info {
+public:
+  virtual ~type_info();
+  const char *name() const { return __name; }
+  bool operator==(const type_info &__arg) const {
+return __name == __arg.__name;
+  }
+
+  bool operator!=(const type_info &__arg) const {
+return !operator==(__arg);
+  }
+
+protected:
+  const char *__name;
+};
+} // namespace std
+struct Q {
+  virtual ~Q() = default;
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) { // expected-warning{{call itself}}
+  (void)typeid(evaluated_recursive_function(x)); // expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,25 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   polymorphic class type [...] [the] expression is an unevaluated
+  //   operand. [...]
+  // We add only potentially evaluated statements to the block to avoid
+  // CFG generation for unevaluated operands.
+  if (S && !S->isTypeDependent() && S->isPotentiallyEvaluated())
+return VisitChildren(S);
+
+  // Return block without CFG for unevaluated operands.
+  return Block;
+}
+
 CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
   CFGBlock *LoopSuccessor = nullptr;
 
Index: clang/docs/ReleaseNotes.rst
===
--- clang/docs/ReleaseNotes.rst
+++ clang/docs/ReleaseNotes.rst
@@ -267,6 +267,10 @@
 - When using class templates without arguments, clang now tells developers
   that template arguments are missing in certain contexts.
   This fixes `Issue 55962 `_.
+- The ``-Winfinite-recursion`` diagnostic will not warn for
+  unevaluated operands of ``typeid`` expression. Unevaluated
+  operands of ``typeid`` expression are skipped for the CFG build.
+  This fixes `Issue 21668 `_.
 
 Non-comprehensive list of changes in this release
 -
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-29 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 updated this revision to Diff 441014.

Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

Files:
  clang/docs/ReleaseNotes.rst
  clang/lib/Analysis/CFG.cpp
  clang/test/SemaCXX/warn-infinite-recursion.cpp

Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -171,3 +171,35 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+namespace std {
+class type_info {
+public:
+  virtual ~type_info();
+  const char *name() const { return __name; }
+  bool operator==(const type_info &__arg) const {
+return __name == __arg.__name;
+  }
+
+  bool operator!=(const type_info &__arg) const {
+return !operator==(__arg);
+  }
+
+protected:
+  const char *__name;
+};
+} // namespace std
+struct Q {
+  virtual ~Q() = default;
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) { // expected-warning{{call itself}}
+  (void)typeid(evaluated_recursive_function(x)); // expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,25 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   polymorphic class type [...] [the] expression is an unevaluated
+  //   operand. [...]
+  // We add only potentially evaluated statements to the block to avoid
+  // CFG generation for unevaluated operands.
+  if (S && !S->isTypeDependent() && S->isPotentiallyEvaluated())
+return VisitChildren(S);
+
+  // Return block without CFG for unevaluated operands.
+  return Block;
+}
+
 CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
   CFGBlock *LoopSuccessor = nullptr;
 
Index: clang/docs/ReleaseNotes.rst
===
--- clang/docs/ReleaseNotes.rst
+++ clang/docs/ReleaseNotes.rst
@@ -275,6 +275,10 @@
   This fixes `Issue 55962 `_.
 - Printable Unicode characters within `static_assert` messages are no longer
   escaped.
+- The ``-Winfinite-recursion`` diagnostic will not warn for
+  unevaluated operands of ``typeid`` expression. Unevaluated
+  operands of ``typeid`` expression are skipped for the CFG build.
+  This fixes `Issue 21668 `_.
 
 Non-comprehensive list of changes in this release
 -
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-29 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 added a comment.

Name : Prathit Aswar
github username :   appmonster007
email :  snaswar0...@gmail.com


Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

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


[PATCH] D128747: ISSUE - incorrect -Winfinite-recursion warning on potentially-unevaluated operand #21668

2022-06-29 Thread Prathit Aswar via Phabricator via cfe-commits
appmonster007 updated this revision to Diff 441075.

Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D128747

Files:
  clang/docs/ReleaseNotes.rst
  clang/lib/Analysis/CFG.cpp
  clang/test/SemaCXX/warn-infinite-recursion.cpp

Index: clang/test/SemaCXX/warn-infinite-recursion.cpp
===
--- clang/test/SemaCXX/warn-infinite-recursion.cpp
+++ clang/test/SemaCXX/warn-infinite-recursion.cpp
@@ -171,3 +171,35 @@
 }
 
 int wrapper_sum = test_wrapper<2>();  // expected-note{{instantiation}}
+
+namespace std {
+class type_info {
+public:
+  virtual ~type_info();
+  const char *name() const { return __name; }
+  bool operator==(const type_info &__arg) const {
+return __name == __arg.__name;
+  }
+
+  bool operator!=(const type_info &__arg) const {
+return !operator==(__arg);
+  }
+
+protected:
+  const char *__name;
+};
+} // namespace std
+struct Q {
+  virtual ~Q() = default;
+};
+
+Q q;
+Q &evaluated_recursive_function(int x) { // expected-warning{{call itself}}
+  (void)typeid(evaluated_recursive_function(x)); // expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}}
+  return q;
+}
+
+int unevaluated_recursive_function() {
+  (void)typeid(unevaluated_recursive_function());
+  return 0;
+}
Index: clang/lib/Analysis/CFG.cpp
===
--- clang/lib/Analysis/CFG.cpp
+++ clang/lib/Analysis/CFG.cpp
@@ -564,6 +564,7 @@
 AddStmtChoice asc);
   CFGBlock *VisitCXXThrowExpr(CXXThrowExpr *T);
   CFGBlock *VisitCXXTryStmt(CXXTryStmt *S);
+  CFGBlock *VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc);
   CFGBlock *VisitDeclStmt(DeclStmt *DS);
   CFGBlock *VisitDeclSubExpr(DeclStmt *DS);
   CFGBlock *VisitDefaultStmt(DefaultStmt *D);
@@ -2220,6 +2221,9 @@
 case Stmt::CXXTryStmtClass:
   return VisitCXXTryStmt(cast(S));
 
+case Stmt::CXXTypeidExprClass:
+  return VisitCXXTypeidExpr(cast(S), asc);
+
 case Stmt::CXXForRangeStmtClass:
   return VisitCXXForRangeStmt(cast(S));
 
@@ -4045,6 +4049,25 @@
   return VisitStmt(T, AddStmtChoice::AlwaysAdd);
 }
 
+CFGBlock *CFGBuilder::VisitCXXTypeidExpr(CXXTypeidExpr *S, AddStmtChoice asc) {
+  if (asc.alwaysAdd(*this, S)) {
+autoCreateBlock();
+appendStmt(Block, S);
+  }
+
+  // C++ [expr.typeid]p3:
+  //   When typeid is applied to an expression other than an glvalue of a
+  //   polymorphic class type [...] [the] expression is an unevaluated
+  //   operand. [...]
+  // We add only potentially evaluated statements to the block to avoid
+  // CFG generation for unevaluated operands.
+  if (S && !S->isTypeDependent() && S->isPotentiallyEvaluated())
+return VisitChildren(S);
+
+  // Return block without CFG for unevaluated operands.
+  return Block;
+}
+
 CFGBlock *CFGBuilder::VisitDoStmt(DoStmt *D) {
   CFGBlock *LoopSuccessor = nullptr;
 
Index: clang/docs/ReleaseNotes.rst
===
--- clang/docs/ReleaseNotes.rst
+++ clang/docs/ReleaseNotes.rst
@@ -275,6 +275,10 @@
   This fixes `Issue 55962 `_.
 - Printable Unicode characters within `static_assert` messages are no longer
   escaped.
+- The ``-Winfinite-recursion`` diagnostic no longer warns about
+  unevaluated operands of a ``typeid`` expression, as they are now
+  modeled correctly in the CFG. This fixes
+  `Issue 21668 `_.
 
 Non-comprehensive list of changes in this release
 -
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits