[llvm] [TableGen] Avoid evaluating RHS of a BinOp until short-circuit is complete (PR #144021)

Min-Yih Hsu via llvm-commits llvm-commits at lists.llvm.org
Fri Jun 13 09:55:10 PDT 2025


================
@@ -67,13 +67,18 @@ def rec7 {
   bits<3> flags = { true, false, true };
 }
 
-// `!and` and `!or` should be short-circuit such that `!tail` on empty list will never
-// be evaluated.
+// `!and` and `!or` should be short-circuit such that any of the `!head` or
+// `!tail` on empty list below will never be evaluated.
 // CHECK: def rec8
+// CHECK:   bit v = 0;
+// CHECK:   int v2 = -1;
 // CHECK:   list<int> newSeq = [];
 // CHECK:   list<int> newSeq2 = [];
 
 class Foo <list<int> seq = []> {
+  bit v = !and(false, !head(seq));
+  int v2 = !or(-1, !head(seq));
----------------
mshockwave wrote:

> Can we add one test that `!head` on constants

Oh, the `!head(seq)` in `bit v = !and(false, !head(seq));` will actually be folded into a constant right away, should it ever be evaluated. So this case is already covered.
As an analogy, you can try `bit v = !and(!not(!empty(seq)), !head(seq));` and it will not evaluate `!head(seq)` with this patch (because if `!empty(seq)` is not folded into constant right away, short circuit in this patch will not kick in). TableGen has been pretty good at folding / resolving as early as possible, only directives like `NAME` will guarantee not to be resolved right away, hence its usage in my test.

https://github.com/llvm/llvm-project/pull/144021


More information about the llvm-commits mailing list