[llvm-branch-commits] [clang] [CIR] Migrate MemOrder and SyncScopeKind off IntegerAttr (PR #220884)
via llvm-branch-commits
llvm-branch-commits at lists.llvm.org
Thu Sep 3 12:53:37 PDT 2026
llvmorg-github-actions[bot] wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-clang
Author: Henrich Lauko (xlauko)
<details>
<summary>Changes</summary>
MemOrder and SyncScopeKind, the enums the atomic operations share, generated
IntegerAttr subclasses with no dialect spelling of their own.
Both now set genSpecializedAttr = 0 and gain CIR_EnumAttr wrappers, spelling
`#cir.mem_order<seq_cst>` and `#cir.sync_scope<system>`, and the atomic
operations wrap their arguments in `enum()` to keep the bare keyword.
---
Full diff: https://github.com/llvm/llvm-project/pull/220884.diff
2 Files Affected:
- (modified) clang/include/clang/CIR/Dialect/IR/CIROps.td (+38-30)
- (modified) clang/test/CIR/IR/enum-attrs.cir (+28)
``````````diff
diff --git a/clang/include/clang/CIR/Dialect/IR/CIROps.td b/clang/include/clang/CIR/Dialect/IR/CIROps.td
index 1a4afd3b53d8b..bf2c38ef67f0c 100644
--- a/clang/include/clang/CIR/Dialect/IR/CIROps.td
+++ b/clang/include/clang/CIR/Dialect/IR/CIROps.td
@@ -642,7 +642,11 @@ def CIR_MemOrder : CIR_I32EnumAttr<
I32EnumAttrCase<"Release", 3, "release">,
I32EnumAttrCase<"AcquireRelease", 4, "acq_rel">,
I32EnumAttrCase<"SequentiallyConsistent", 5, "seq_cst">
-]>;
+]> {
+ let genSpecializedAttr = 0;
+}
+
+def CIR_MemOrderAttr : CIR_EnumAttr<CIR_MemOrder, "mem_order">;
//===----------------------------------------------------------------------===//
// C/C++ sync scope definitions
@@ -669,7 +673,11 @@ def CIR_SyncScopeKind : CIR_I32EnumAttr<"SyncScopeKind", "sync scope kind", [
I32EnumAttrCase<"OpenCLDevice", 13, "opencl_device">,
I32EnumAttrCase<"OpenCLAllSVMDevices", 14, "opencl_all_svm_devices">,
I32EnumAttrCase<"OpenCLSubGroup", 15, "opencl_sub_group">,
-]>;
+]> {
+ let genSpecializedAttr = 0;
+}
+
+def CIR_SyncScopeKindAttr : CIR_EnumAttr<CIR_SyncScopeKind, "sync_scope">;
//===----------------------------------------------------------------------===//
// AllocaOp
@@ -810,8 +818,8 @@ def CIR_LoadOp : CIR_Op<"load", [
UnitAttr:$is_volatile,
UnitAttr:$is_nontemporal,
OptionalAttr<I64Attr>:$alignment,
- OptionalAttr<CIR_SyncScopeKind>:$sync_scope,
- OptionalAttr<CIR_MemOrder>:$mem_order,
+ OptionalAttr<CIR_SyncScopeKindAttr>:$sync_scope,
+ OptionalAttr<CIR_MemOrderAttr>:$mem_order,
UnitAttr:$invariant);
let results = (outs CIR_AnyType:$result);
@@ -821,8 +829,8 @@ def CIR_LoadOp : CIR_Op<"load", [
(`nontemporal` $is_nontemporal^)?
(`invariant` $invariant^)?
(`align` `(` $alignment^ `)`)?
- (`syncscope` `(` $sync_scope^ `)`)?
- (`atomic` `(` $mem_order^ `)`)?
+ (`syncscope` `(` enum($sync_scope)^ `)`)?
+ (`atomic` `(` enum($mem_order)^ `)`)?
$addr `:` qualified(type($addr)) `,` type($result) attr-dict
}];
@@ -913,15 +921,15 @@ def CIR_StoreOp : CIR_Op<"store", [
UnitAttr:$is_volatile,
UnitAttr:$is_nontemporal,
OptionalAttr<I64Attr>:$alignment,
- OptionalAttr<CIR_SyncScopeKind>:$sync_scope,
- OptionalAttr<CIR_MemOrder>:$mem_order);
+ OptionalAttr<CIR_SyncScopeKindAttr>:$sync_scope,
+ OptionalAttr<CIR_MemOrderAttr>:$mem_order);
let assemblyFormat = [{
(`volatile` $is_volatile^)?
(`nontemporal` $is_nontemporal^)?
(`align` `(` $alignment^ `)`)?
- (`syncscope` `(` $sync_scope^ `)`)?
- (`atomic` `(` $mem_order^ `)`)?
+ (`syncscope` `(` enum($sync_scope)^ `)`)?
+ (`atomic` `(` enum($mem_order)^ `)`)?
$value `,` $addr attr-dict `:` type($value) `,` qualified(type($addr))
}];
@@ -8918,15 +8926,15 @@ def CIR_AtomicFetchOp : CIR_Op<"atomic.fetch", [
Arg<CIR_PtrToIntOrFloatType, "", [MemRead, MemWrite]>:$ptr,
CIR_AnyIntOrFloatType:$val,
CIR_AtomicFetchKind:$binop,
- Arg<CIR_MemOrder, "memory order">:$mem_order,
- Arg<CIR_SyncScopeKind, "synchronization scope">:$sync_scope,
+ Arg<CIR_MemOrderAttr, "memory order">:$mem_order,
+ Arg<CIR_SyncScopeKindAttr, "synchronization scope">:$sync_scope,
UnitAttr:$is_volatile,
UnitAttr:$fetch_first
);
let assemblyFormat = [{
- $binop $mem_order
- `syncscope` `(` $sync_scope `)`
+ $binop enum($mem_order)
+ `syncscope` `(` enum($sync_scope) `)`
(`fetch_first` $fetch_first^)?
$ptr `,` $val
(`volatile` $is_volatile^)?
@@ -8974,14 +8982,14 @@ def CIR_AtomicXchgOp : CIR_Op<"atomic.xchg", [
let arguments = (ins
Arg<CIR_PointerType, "", [MemRead, MemWrite]>:$ptr,
CIR_AnyType:$val,
- Arg<CIR_MemOrder, "memory order">:$mem_order,
- CIR_SyncScopeKind:$sync_scope,
+ Arg<CIR_MemOrderAttr, "memory order">:$mem_order,
+ CIR_SyncScopeKindAttr:$sync_scope,
UnitAttr:$is_volatile
);
let assemblyFormat = [{
- $mem_order
- `syncscope` `(` $sync_scope `)`
+ enum($mem_order)
+ `syncscope` `(` enum($sync_scope) `)`
(`volatile` $is_volatile^)?
$ptr `,` $val
`:` functional-type(operands, results) attr-dict
@@ -9038,17 +9046,17 @@ def CIR_AtomicCmpXchgOp : CIR_Op<"atomic.cmpxchg", [
let arguments = (ins Arg<CIR_PointerType, "", [MemRead, MemWrite]>:$ptr,
CIR_AnyType:$expected,
CIR_AnyType:$desired,
- Arg<CIR_MemOrder, "success memory order">:$succ_order,
- Arg<CIR_MemOrder, "failure memory order">:$fail_order,
- CIR_SyncScopeKind:$sync_scope,
+ Arg<CIR_MemOrderAttr, "success memory order">:$succ_order,
+ Arg<CIR_MemOrderAttr, "failure memory order">:$fail_order,
+ CIR_SyncScopeKindAttr:$sync_scope,
OptionalAttr<I64Attr>:$alignment,
UnitAttr:$weak,
UnitAttr:$is_volatile);
let assemblyFormat = [{
(`weak` $weak^)?
- `success` `(` $succ_order `)` `failure` `(` $fail_order `)`
- `syncscope` `(` $sync_scope `)`
+ `success` `(` enum($succ_order) `)` `failure` `(` enum($fail_order) `)`
+ `syncscope` `(` enum($sync_scope) `)`
$ptr `,` $expected `,` $desired
(`align` `(` $alignment^ `)`)?
(`volatile` $is_volatile^)?
@@ -9075,7 +9083,7 @@ def CIR_AtomicTestAndSetOp : CIR_Op<"atomic.test_and_set"> {
let arguments = (ins
Arg<CIR_PtrToType<CIR_SInt8>, "", [MemRead, MemWrite]>:$ptr,
- Arg<CIR_MemOrder, "memory order">:$mem_order,
+ Arg<CIR_MemOrderAttr, "memory order">:$mem_order,
OptionalAttr<I64Attr>:$alignment,
UnitAttr:$is_volatile
);
@@ -9083,7 +9091,7 @@ def CIR_AtomicTestAndSetOp : CIR_Op<"atomic.test_and_set"> {
let results = (outs CIR_BoolType:$result);
let assemblyFormat = [{
- $mem_order $ptr
+ enum($mem_order) $ptr
(`volatile` $is_volatile^)?
`:` qualified(type($ptr)) `->` qualified(type($result)) attr-dict
}];
@@ -9106,13 +9114,13 @@ def CIR_AtomicClearOp : CIR_Op<"atomic.clear"> {
let arguments = (ins
Arg<CIR_PtrToType<CIR_SInt8>, "", [MemRead, MemWrite]>:$ptr,
- Arg<CIR_MemOrder, "memory order">:$mem_order,
+ Arg<CIR_MemOrderAttr, "memory order">:$mem_order,
OptionalAttr<I64Attr>:$alignment,
UnitAttr:$is_volatile
);
let assemblyFormat = [{
- $mem_order $ptr
+ enum($mem_order) $ptr
(`volatile` $is_volatile^)?
`:` qualified(type($ptr)) attr-dict
}];
@@ -9139,12 +9147,12 @@ def CIR_AtomicFenceOp : CIR_Op<"atomic.fence"> {
}];
let arguments = (ins
- Arg<CIR_MemOrder, "memory order">:$ordering,
- OptionalAttr<CIR_SyncScopeKind>:$syncscope
+ Arg<CIR_MemOrderAttr, "memory order">:$ordering,
+ OptionalAttr<CIR_SyncScopeKindAttr>:$syncscope
);
let assemblyFormat = [{
- (`syncscope` `(` $syncscope^ `)`)? $ordering attr-dict
+ (`syncscope` `(` enum($syncscope)^ `)`)? enum($ordering) attr-dict
}];
}
diff --git a/clang/test/CIR/IR/enum-attrs.cir b/clang/test/CIR/IR/enum-attrs.cir
index cf8a2f9055484..30f72ce8643fe 100644
--- a/clang/test/CIR/IR/enum-attrs.cir
+++ b/clang/test/CIR/IR/enum-attrs.cir
@@ -5,6 +5,8 @@
// dictionary. These used to be IntegerAttr subclasses, which printed as
// `2 : i32`.
+!s32i = !cir.int<s, 32>
+
module {
// CHECK: cir.func @cast_attr() {
@@ -62,4 +64,30 @@ cir.func @tls_model_attr() {
#cir.tls_model<tls_local_exec>]}
}
+// CHECK: cir.func @mem_order_attr() {
+// CHECK: cir.return {cir.test = [#cir.mem_order<relaxed>, #cir.mem_order<acq_rel>, #cir.mem_order<seq_cst>]}
+cir.func @mem_order_attr() {
+ cir.return {cir.test = [#cir.mem_order<relaxed>, #cir.mem_order<acq_rel>,
+ #cir.mem_order<seq_cst>]}
+}
+
+// CHECK: cir.func @sync_scope_attr() {
+// CHECK: cir.return {cir.test = [#cir.sync_scope<single_thread>, #cir.sync_scope<hip_workgroup>, #cir.sync_scope<opencl_all_svm_devices>]}
+cir.func @sync_scope_attr() {
+ cir.return {cir.test = [#cir.sync_scope<single_thread>,
+ #cir.sync_scope<hip_workgroup>,
+ #cir.sync_scope<opencl_all_svm_devices>]}
+}
+
+// The operations themselves keep printing a bare keyword.
+
+// CHECK: cir.func @mem_order_sync_scope_ops(%arg0: !cir.ptr<!s32i>) {
+// CHECK: %0 = cir.load syncscope(system) atomic(seq_cst) %arg0 : !cir.ptr<!s32i>, !s32i
+// CHECK: cir.atomic.fence syncscope(system) seq_cst
+cir.func @mem_order_sync_scope_ops(%arg0: !cir.ptr<!s32i>) {
+ %0 = cir.load syncscope(system) atomic(seq_cst) %arg0 : !cir.ptr<!s32i>, !s32i
+ cir.atomic.fence syncscope(system) seq_cst
+ cir.return
+}
+
}
``````````
</details>
https://github.com/llvm/llvm-project/pull/220884
More information about the llvm-branch-commits
mailing list