[llvm] [TableGen] Resolve arguments with fields in records (PR #107829)
Akshat Oke via llvm-commits
llvm-commits at lists.llvm.org
Mon Sep 9 02:26:45 PDT 2024
https://github.com/Akshat-Oke created https://github.com/llvm/llvm-project/pull/107829
Previously, instantiating an anonymous record happened in two steps:
1. Resolve the arguments with a `MapResolver`
2. Resolve the fields with a `RecordResolver`.
In 1, the `MapResolver` cannot resolve references to fields and in 2 the `RecordResolver` cannot resolve references to arguments. This was leading to incomplete resolution in `llvm/test/TableGen/record-recursion.td` (simplified test-case from #91050 ) like so:
1. `MapResolver` fails to resolve the `if` condition since it references the field `v`.
2. Resolving `SumTillN<!sub(n, 1)>.ret)` fails as it references the argument `n` and the `RecordResolver` doesn't know about it.
This patch merges the two steps into one where arguments and fields are resolved by the `RecordResolver` itself.
>From eb0123c5a4945015926f18b78f885746f67204aa Mon Sep 17 00:00:00 2001
From: Akshat Oke <Akshat.Oke at amd.com>
Date: Mon, 9 Sep 2024 06:16:35 +0000
Subject: [PATCH] [TableGen] Resolve arguments with fields in records
---
llvm/include/llvm/TableGen/Record.h | 5 ++++-
llvm/lib/TableGen/Record.cpp | 12 +++++++++---
llvm/test/TableGen/record-recursion.td | 11 +++++++++++
3 files changed, 24 insertions(+), 4 deletions(-)
create mode 100644 llvm/test/TableGen/record-recursion.td
diff --git a/llvm/include/llvm/TableGen/Record.h b/llvm/include/llvm/TableGen/Record.h
index 98c8fd0ca051f9..287f457b8efd31 100644
--- a/llvm/include/llvm/TableGen/Record.h
+++ b/llvm/include/llvm/TableGen/Record.h
@@ -2289,9 +2289,12 @@ class RecordResolver final : public Resolver {
DenseMap<Init *, Init *> Cache;
SmallVector<Init *, 4> Stack;
Init *Name = nullptr;
+ // Cache is for fields, ArgumentResolver is for arguments.
+ MapResolver *ArgumentResolver;
public:
- explicit RecordResolver(Record &R) : Resolver(&R) {}
+ explicit RecordResolver(Record &R, MapResolver *ArgumentResolver = nullptr)
+ : Resolver(&R), ArgumentResolver(ArgumentResolver) {}
void setName(Init *NewName) { Name = NewName; }
diff --git a/llvm/lib/TableGen/Record.cpp b/llvm/lib/TableGen/Record.cpp
index 85516b7b9f20aa..4c1b9902a9b238 100644
--- a/llvm/lib/TableGen/Record.cpp
+++ b/llvm/lib/TableGen/Record.cpp
@@ -2321,8 +2321,6 @@ DefInit *VarDefInit::instantiate() {
R.set(Arg->getName(), Arg->getValue());
}
- NewRec->resolveReferences(R);
-
// Add superclasses.
ArrayRef<std::pair<Record *, SMRange>> SCs = Class->getSuperClasses();
for (const auto &SCPair : SCs)
@@ -2332,7 +2330,10 @@ DefInit *VarDefInit::instantiate() {
Class, SMRange(Class->getLoc().back(), Class->getLoc().back()));
// Resolve internal references and store in record keeper
- NewRec->resolveReferences();
+ RecordResolver RR(*NewRec, &R);
+ RR.setFinal(true);
+ NewRec->resolveReferences(RR);
+
Records.addDef(std::move(NewRecOwner));
// Check the assertions.
@@ -3348,6 +3349,11 @@ Init *RecordResolver::resolve(Init *VarName) {
if (Val)
return Val;
+ if (ArgumentResolver && (Val = ArgumentResolver->resolve(VarName))) {
+ Cache[VarName] = Val;
+ return Val;
+ }
+
if (llvm::is_contained(Stack, VarName))
return nullptr; // prevent infinite recursion
diff --git a/llvm/test/TableGen/record-recursion.td b/llvm/test/TableGen/record-recursion.td
new file mode 100644
index 00000000000000..96ca9df62105a1
--- /dev/null
+++ b/llvm/test/TableGen/record-recursion.td
@@ -0,0 +1,11 @@
+// RUN: llvm-tblgen %s | FileCheck %s
+
+class SumTillN<int n> {
+ int v = !add(n, 0);
+ int ret = !if(!gt(v, 0), !add(v, SumTillN<!sub(n, 1)>.ret), v);
+}
+
+// CHECK: def SumTill4
+// CHECK-NEXT: int v = 3;
+// CHECK-NEXT: int ret = 6;
+def SumTill4 : SumTillN<3>;
More information about the llvm-commits
mailing list