[llvm] [TableGen] Short-circuit !cond operator (PR #208942)
Kevin Bravo via llvm-commits
llvm-commits at lists.llvm.org
Sun Jul 12 23:38:43 PDT 2026
https://github.com/kbrav updated https://github.com/llvm/llvm-project/pull/208942
>From 305f9ebe1d5761cedb880e8687c9cf0bbfc859be Mon Sep 17 00:00:00 2001
From: kbrav <kbravjr at gmail.com>
Date: Sat, 11 Jul 2026 13:37:00 -0400
Subject: [PATCH 1/3] [TableGen] Short-circuit !cond operator
---
llvm/lib/TableGen/Record.cpp | 11 +++++++++++
llvm/test/TableGen/true-false.td | 13 +++++++++++--
2 files changed, 22 insertions(+), 2 deletions(-)
diff --git a/llvm/lib/TableGen/Record.cpp b/llvm/lib/TableGen/Record.cpp
index e9d7febf12272..af076b5ae9475 100644
--- a/llvm/lib/TableGen/Record.cpp
+++ b/llvm/lib/TableGen/Record.cpp
@@ -2735,6 +2735,17 @@ const Init *CondOpInit::resolveReferences(Resolver &R) const {
NewConds.push_back(NewCond);
Changed |= NewCond != Cond;
+ // Short-circuit if this cond is true.
+ if (auto *NewCondVal = dyn_cast_or_null<IntInit>(
+ NewCond->convertInitializerTo(IntRecTy::get(getRecordKeeper())))) {
+ if (NewCondVal->getValue()) {
+ NewVals.push_back(Val->resolveReferences(R));
+ Changed = 1;
+ // Don't push the rest of the conds and values.
+ break;
+ }
+ }
+
const Init *NewVal = Val->resolveReferences(R);
NewVals.push_back(NewVal);
Changed |= NewVal != Val;
diff --git a/llvm/test/TableGen/true-false.td b/llvm/test/TableGen/true-false.td
index 5fa5702314489..f4110fab5054b 100644
--- a/llvm/test/TableGen/true-false.td
+++ b/llvm/test/TableGen/true-false.td
@@ -67,13 +67,15 @@ def rec7 {
bits<3> flags = { true, false, true };
}
-// `!and` and `!or` should be short-circuited such that any of the `!head` or
-// `!tail` on empty list below will never be evaluated.
+// `!and`, `!or`, and '!cond' should be short-circuited 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 = [];
+// CHECK: C = 0;
+// CHECK: D = 1;
class Foo <list<int> seq = []> {
bit v = !and(false, !head(seq));
@@ -82,6 +84,13 @@ class Foo <list<int> seq = []> {
bit unresolved = !ne(!find(NAME, "BAR"), -1);
list<int> newSeq = !if(!and(false, unresolved), !tail(seq), seq);
list<int> newSeq2 = !if(!or(-1, unresolved), seq, !tail(seq));
+
+ int C = !cond(!eq(!size(seq), 0): 0,
+ !eq(!size(!tail(seq)), 1) : 1,
+ !eq(!size(!tail(seq)), 2): 2);
+ int D = !cond(!eq(!size(seq), 1): 0,
+ !eq(!size(seq), 0): 1,
+ !eq(!size(!tail(seq)), 2): 2);
}
def rec8 : Foo<>;
>From 04ead99412e1e7c27497c8344a310f14866940f7 Mon Sep 17 00:00:00 2001
From: kbrav <kbravjr at gmail.com>
Date: Sat, 11 Jul 2026 15:53:20 -0400
Subject: [PATCH 2/3] Move short-circuit check to after `Val` resolution
---
llvm/lib/TableGen/Record.cpp | 9 ++++-----
1 file changed, 4 insertions(+), 5 deletions(-)
diff --git a/llvm/lib/TableGen/Record.cpp b/llvm/lib/TableGen/Record.cpp
index af076b5ae9475..b35e7be87a7ff 100644
--- a/llvm/lib/TableGen/Record.cpp
+++ b/llvm/lib/TableGen/Record.cpp
@@ -2735,20 +2735,19 @@ const Init *CondOpInit::resolveReferences(Resolver &R) const {
NewConds.push_back(NewCond);
Changed |= NewCond != Cond;
+ const Init *NewVal = Val->resolveReferences(R);
+ NewVals.push_back(NewVal);
+ Changed |= NewVal != Val;
+
// Short-circuit if this cond is true.
if (auto *NewCondVal = dyn_cast_or_null<IntInit>(
NewCond->convertInitializerTo(IntRecTy::get(getRecordKeeper())))) {
if (NewCondVal->getValue()) {
- NewVals.push_back(Val->resolveReferences(R));
Changed = 1;
// Don't push the rest of the conds and values.
break;
}
}
-
- const Init *NewVal = Val->resolveReferences(R);
- NewVals.push_back(NewVal);
- Changed |= NewVal != Val;
}
if (Changed)
>From e230e9fa5ae62c0f99ae058326316d4eb9910726 Mon Sep 17 00:00:00 2001
From: kbrav <kbravjr at gmail.com>
Date: Mon, 13 Jul 2026 02:38:16 -0400
Subject: [PATCH 3/3] release note
---
llvm/docs/ReleaseNotes.md | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/llvm/docs/ReleaseNotes.md b/llvm/docs/ReleaseNotes.md
index 3ca9f5166ad95..38724a2efaeb9 100644
--- a/llvm/docs/ReleaseNotes.md
+++ b/llvm/docs/ReleaseNotes.md
@@ -185,6 +185,10 @@ Makes programs 10x faster by doing Special New Thing.
* Outer let statements use ``ID{n-m}`` instead of ``ID<n-m>`` to be consistent
with inner let statements.
+* `!cond` operator short-circuits at the first `true` condition. Subsequent
+ `condition : value` pairs, along with their corresponding side effects,
+ are left unresolved.
+
### Changes to Interprocedural Optimizations
### Changes to Vectorizers
More information about the llvm-commits
mailing list