https://github.com/xlauko updated https://github.com/llvm/llvm-project/pull/220883
>From 68259ebd3af190400f2ac45531bd227d1874de55 Mon Sep 17 00:00:00 2001 From: Henrich Lauko <[email protected]> Date: Thu, 3 Sep 2026 12:44:31 +0000 Subject: [PATCH] [CIR] Migrate seven operation enums off IntegerAttr CastKind, DynamicCastKind, CmpOpKind, ComplexRangeKind, InitCatchKind, CaseOpKind and AwaitKind generated IntegerAttr subclasses. The operations printed them symbolically, but in an attribute dictionary `cir.cast bitcast` was stored as `kind = 1 : i32`. Each enum now sets genSpecializedAttr = 0 and gains a CIR_EnumAttr wrapper, and the operations wrap the argument in `enum()` to keep the bare keyword, giving spellings like `#cir.cast<bitcast>`. Mnemonics drop the suffix the C++ class name carries. DynamicCastKind spells out `dynamic_cast`, since `dyn_cast` is taken by the operation and by `#cir.dyn_cast_info`. CUDADeviceVarKind gets no wrapper, being only a raw parameter of CIR_CUDAVarRegistrationInfoAttr. Operation syntax is unchanged, and enum-attrs.cir covers the new spellings. --- .../clang/CIR/Dialect/IR/CIRCUDAAttrs.td | 7 +- clang/include/clang/CIR/Dialect/IR/CIROps.td | 82 +++++++++++++------ clang/test/CIR/IR/enum-attrs.cir | 65 +++++++++++++++ 3 files changed, 126 insertions(+), 28 deletions(-) create mode 100644 clang/test/CIR/IR/enum-attrs.cir diff --git a/clang/include/clang/CIR/Dialect/IR/CIRCUDAAttrs.td b/clang/include/clang/CIR/Dialect/IR/CIRCUDAAttrs.td index 73dd7baaa5caa..2d5f70ec9c3ad 100644 --- a/clang/include/clang/CIR/Dialect/IR/CIRCUDAAttrs.td +++ b/clang/include/clang/CIR/Dialect/IR/CIRCUDAAttrs.td @@ -68,14 +68,15 @@ def CIR_CUDABinaryHandleAttr : CIR_Attr< let assemblyFormat = "`<` $name `>`"; } -// Enum for device variable kinds -def CIR_CUDADeviceVarKind : I32EnumAttr<"CUDADeviceVarKind", +// No wrapper attribute: the kind is only ever printed by +// CIR_CUDAVarRegistrationInfoAttr's own assembly format. +def CIR_CUDADeviceVarKind : CIR_I32EnumAttr<"CUDADeviceVarKind", "CUDA device variable kind", [ I32EnumAttrCase<"Variable", 0>, I32EnumAttrCase<"Surface", 1>, // Future I32EnumAttrCase<"Texture", 2>, // Future ]> { - let cppNamespace = "::cir"; + let genSpecializedAttr = 0; } // Attribute carrying device variable registration flags diff --git a/clang/include/clang/CIR/Dialect/IR/CIROps.td b/clang/include/clang/CIR/Dialect/IR/CIROps.td index 5c2c948742f08..1a4afd3b53d8b 100644 --- a/clang/include/clang/CIR/Dialect/IR/CIROps.td +++ b/clang/include/clang/CIR/Dialect/IR/CIROps.td @@ -242,7 +242,11 @@ def CIR_CastKind : CIR_I32EnumAttr<"CastKind", "cast kind", [ // Enums below are specific to CIR and don't have a correspondence to classic // codegen: I32EnumAttrCase<"bool_to_float", 1000>, -]>; +]> { + let genSpecializedAttr = 0; +} + +def CIR_CastKindAttr : CIR_EnumAttr<CIR_CastKind, "cast">; def CIR_CastOp : CIR_Op<"cast", !listconcat([ DeclareOpInterfaceMethods<PromotableOpInterface> @@ -302,12 +306,12 @@ def CIR_CastOp : CIR_Op<"cast", !listconcat([ ``` }]; - let arguments = (ins CIR_CastKind:$kind, CIR_AnyType:$src, + let arguments = (ins CIR_CastKindAttr:$kind, CIR_AnyType:$src, OptionalAttr<CIR_FenvAttr>:$fenv); let results = (outs CIR_AnyType:$result); let assemblyFormat = [{ - $kind $src `:` type($src) `->` type($result) attr-dict + enum($kind) $src `:` type($src) `->` type($result) attr-dict }]; let builders = [ @@ -395,7 +399,12 @@ def CIR_DynamicCastKind : CIR_I32EnumAttr< "DynamicCastKind", "dynamic cast kind", [ I32EnumAttrCase<"Ptr", 0, "ptr">, I32EnumAttrCase<"Ref", 1, "ref"> -]>; +]> { + let genSpecializedAttr = 0; +} + +def CIR_DynamicCastKindAttr + : CIR_EnumAttr<CIR_DynamicCastKind, "dynamic_cast">; def CIR_DynamicCastOp : CIR_Op<"dyn_cast"> { let summary = "Perform dynamic cast on record pointers"; @@ -450,7 +459,7 @@ def CIR_DynamicCastOp : CIR_Op<"dyn_cast"> { }]; let arguments = (ins - CIR_DynamicCastKind:$kind, + CIR_DynamicCastKindAttr:$kind, CIR_PtrToRecordType:$src, OptionalAttr<CIR_DynamicCastInfoAttr>:$info, UnitAttr:$relative_layout @@ -461,7 +470,7 @@ def CIR_DynamicCastOp : CIR_Op<"dyn_cast"> { ); let assemblyFormat = [{ - $kind (`relative_layout` $relative_layout^)? $src + enum($kind) (`relative_layout` $relative_layout^)? $src `:` qualified(type($src)) `->` qualified(type($result)) (qualified($info)^)? attr-dict }]; @@ -1513,7 +1522,11 @@ def CIR_CaseOpKind : CIR_I32EnumAttr<"CaseOpKind", "case kind", [ I32EnumAttrCase<"Equal", 1, "equal">, I32EnumAttrCase<"Anyof", 2, "anyof">, I32EnumAttrCase<"Range", 3, "range"> -]>; +]> { + let genSpecializedAttr = 0; +} + +def CIR_CaseOpKindAttr : CIR_EnumAttr<CIR_CaseOpKind, "case">; def CIR_CaseOp : CIR_Op<"case", [ DeclareOpInterfaceMethods<RegionBranchOpInterface, ["getSuccessorInputs"]>, @@ -1537,10 +1550,11 @@ def CIR_CaseOp : CIR_Op<"case", [ Each case region must be explicitly terminated. }]; - let arguments = (ins ArrayAttr:$value, CIR_CaseOpKind:$kind); + let arguments = (ins ArrayAttr:$value, CIR_CaseOpKindAttr:$kind); let regions = (region AnyRegion:$caseRegion); - let assemblyFormat = "`(` $kind `,` $value `)` $caseRegion attr-dict"; + let assemblyFormat = + "`(` enum($kind) `,` $value `)` $caseRegion attr-dict"; let skipDefaultBuilders = 1; let builders = [ @@ -2522,7 +2536,11 @@ def CIR_CmpOpKind : CIR_I32EnumAttr<"CmpOpKind", "compare operation kind", [ I32EnumAttrCase<"ne", 5>, I32EnumAttrCase<"one", 6>, I32EnumAttrCase<"uno", 7> -]>; +]> { + let genSpecializedAttr = 0; +} + +def CIR_CmpOpKindAttr : CIR_EnumAttr<CIR_CmpOpKind, "cmp">; def CIR_CmpOp : CIR_Op<"cmp", !listconcat([SameTypeOperands], CIR_FenvOpTraits)> { @@ -2561,7 +2579,7 @@ def CIR_CmpOp : CIR_Op<"cmp", }]; let arguments = (ins - CIR_CmpOpKind:$kind, + CIR_CmpOpKindAttr:$kind, CIR_ComparableType:$lhs, CIR_ComparableType:$rhs, OptionalAttr<CIR_FenvAttr>:$fenv @@ -2570,7 +2588,7 @@ def CIR_CmpOp : CIR_Op<"cmp", let results = (outs CIR_BoolType:$result); let assemblyFormat = [{ - $kind $lhs `,` $rhs `:` type($lhs) attr-dict + enum($kind) $lhs `,` $rhs `:` type($lhs) attr-dict }]; let builders = [ @@ -4718,7 +4736,11 @@ def CIR_AwaitKind : CIR_I32EnumAttr<"AwaitKind", "await kind", [ I32EnumAttrCase<"User", 1, "user">, I32EnumAttrCase<"Yield", 2, "yield">, I32EnumAttrCase<"Final", 3, "final"> -]>; +]> { + let genSpecializedAttr = 0; +} + +def CIR_AwaitKindAttr : CIR_EnumAttr<CIR_AwaitKind, "await">; def CIR_AwaitOp : CIR_Op<"await",[ DeclareOpInterfaceMethods<RegionBranchOpInterface, ["getSuccessorInputs"]>, @@ -4774,12 +4796,12 @@ def CIR_AwaitOp : CIR_Op<"await",[ as part of the enclosing await scope. }]; - let arguments = (ins CIR_AwaitKind:$kind); + let arguments = (ins CIR_AwaitKindAttr:$kind); let regions = (region SizedRegion<1>:$ready, SizedRegion<1>:$suspend, SizedRegion<1>:$resume); let assemblyFormat = [{ - `(` $kind `,` + `(` enum($kind) `,` `ready` `:` $ready `,` `suspend` `:` $suspend `,` `resume` `:` $resume `,` @@ -5919,7 +5941,7 @@ def CIR_VecCmpOp : CIR_Op<"vec.cmp", }]; let arguments = (ins - CIR_CmpOpKind:$kind, + CIR_CmpOpKindAttr:$kind, CIR_VectorType:$lhs, CIR_VectorType:$rhs, OptionalAttr<CIR_FenvAttr>:$fenv @@ -5928,7 +5950,7 @@ def CIR_VecCmpOp : CIR_Op<"vec.cmp", let results = (outs CIR_VectorType:$result); let assemblyFormat = [{ - `(` $kind `,` $lhs `,` $rhs `)` `:` qualified(type($lhs)) `,` + `(` enum($kind) `,` $lhs `,` $rhs `)` `:` qualified(type($lhs)) `,` qualified(type($result)) attr-dict }]; @@ -6502,20 +6524,26 @@ def CIR_ComplexRangeKind : CIR_I32EnumAttr< I32EnumAttrCase<"Improved", 1, "improved">, I32EnumAttrCase<"Promoted", 2, "promoted">, I32EnumAttrCase<"Basic", 3, "basic">, -]>; +]> { + let genSpecializedAttr = 0; +} + +def CIR_ComplexRangeKindAttr + : CIR_EnumAttr<CIR_ComplexRangeKind, "complex_range">; class CIR_ComplexRangeBinOp<string mnemonic> : CIR_Op<mnemonic, [Pure, SameOperandsAndResultType]> { let arguments = (ins CIR_ComplexType:$lhs, CIR_ComplexType:$rhs, - CIR_ComplexRangeKind:$range + CIR_ComplexRangeKindAttr:$range ); let results = (outs CIR_ComplexType:$result); let assemblyFormat = [{ - $lhs `,` $rhs `range` `(` $range `)` `:` qualified(type($result)) attr-dict + $lhs `,` $rhs `range` `(` enum($range) `)` `:` qualified(type($result)) + attr-dict }]; let hasLLVMLowering = false; @@ -8703,7 +8731,11 @@ def CIR_InitCatchKind : CIR_I32EnumAttr< I32EnumAttrCase<"Objc", 3, "objc">, I32EnumAttrCase<"TrivialCopy", 4, "trivial_copy">, I32EnumAttrCase<"NonTrivialCopy", 5, "non_trivial_copy">, -]>; +]> { + let genSpecializedAttr = 0; +} + +def CIR_InitCatchKindAttr : CIR_EnumAttr<CIR_InitCatchKind, "init_catch">; def CIR_InitCatchParamOp : CIR_Op<"init_catch_param"> { let summary = "Initialize a catch parameter from the exception pointer"; @@ -8733,11 +8765,11 @@ def CIR_InitCatchParamOp : CIR_Op<"init_catch_param"> { let arguments = (ins CIR_PointerType:$exn_ptr, CIR_PointerType:$param_addr, - CIR_InitCatchKind:$kind + CIR_InitCatchKindAttr:$kind ); let assemblyFormat = [{ - $kind $exn_ptr `to` $param_addr `:` + enum($kind) $exn_ptr `to` $param_addr `:` qualified(type($exn_ptr)) `,` qualified(type($param_addr)) attr-dict }]; @@ -8783,12 +8815,12 @@ def CIR_ConstructCatchParamOp : CIR_Op<"construct_catch_param", [ let arguments = (ins CIR_EhTokenType:$eh_token, CIR_PointerType:$param_addr, - CIR_InitCatchKind:$kind, + CIR_InitCatchKindAttr:$kind, OptionalAttr<FlatSymbolRefAttr>:$copy_fn ); let assemblyFormat = [{ - $kind $eh_token `to` $param_addr `using` ($copy_fn^)? `:` + enum($kind) $eh_token `to` $param_addr `using` ($copy_fn^)? `:` qualified(type($param_addr)) attr-dict }]; diff --git a/clang/test/CIR/IR/enum-attrs.cir b/clang/test/CIR/IR/enum-attrs.cir new file mode 100644 index 0000000000000..d8972ea918707 --- /dev/null +++ b/clang/test/CIR/IR/enum-attrs.cir @@ -0,0 +1,65 @@ +// RUN: cir-opt %s --verify-roundtrip | FileCheck %s + +// Enum attributes that operations print as a bare keyword must still have a +// readable standalone spelling for when they show up in an attribute +// dictionary. These used to be IntegerAttr subclasses, which printed as +// `2 : i32`. + +module { + +// CHECK-LABEL: cir.func @cast_attr() { +cir.func @cast_attr() { + // CHECK: cir.return {cir.test = [#cir.cast<bitcast>, #cir.cast<integral>, #cir.cast<bool_to_float>]} + cir.return {cir.test = [#cir.cast<bitcast>, #cir.cast<integral>, + #cir.cast<bool_to_float>]} +} + +// CHECK-LABEL: cir.func @dynamic_cast_attr() { +cir.func @dynamic_cast_attr() { + // CHECK: cir.return {cir.test = [#cir.dynamic_cast<ptr>, #cir.dynamic_cast<ref>]} + cir.return {cir.test = [#cir.dynamic_cast<ptr>, + #cir.dynamic_cast<ref>]} +} + +// CHECK-LABEL: cir.func @cmp_attr() { +cir.func @cmp_attr() { + // CHECK: cir.return {cir.test = [#cir.cmp<lt>, #cir.cmp<eq>, #cir.cmp<uno>]} + cir.return {cir.test = [#cir.cmp<lt>, #cir.cmp<eq>, + #cir.cmp<uno>]} +} + +// CHECK-LABEL: cir.func @complex_range_attr() { +cir.func @complex_range_attr() { + // CHECK: cir.return {cir.test = [#cir.complex_range<full>, #cir.complex_range<basic>]} + cir.return {cir.test = [#cir.complex_range<full>, + #cir.complex_range<basic>]} +} + +// CHECK-LABEL: cir.func @init_catch_attr() { +cir.func @init_catch_attr() { + // CHECK: cir.return {cir.test = [#cir.init_catch<reference>, #cir.init_catch<non_trivial_copy>]} + cir.return {cir.test = [#cir.init_catch<reference>, + #cir.init_catch<non_trivial_copy>]} +} + +// CHECK-LABEL: cir.func @case_attr() { +cir.func @case_attr() { + // CHECK: cir.return {cir.test = [#cir.case<default>, #cir.case<anyof>, #cir.case<range>]} + cir.return {cir.test = [#cir.case<default>, #cir.case<anyof>, + #cir.case<range>]} +} + +// CHECK-LABEL: cir.func @await_attr() { +cir.func @await_attr() { + // CHECK: cir.return {cir.test = [#cir.await<init>, #cir.await<final>]} + cir.return {cir.test = [#cir.await<init>, #cir.await<final>]} +} + +// CHECK-LABEL: cir.func @tls_model_attr() { +cir.func @tls_model_attr() { + // CHECK: cir.return {cir.test = [#cir.tls_model<tls_dyn>, #cir.tls_model<tls_local_exec>]} + cir.return {cir.test = [#cir.tls_model<tls_dyn>, + #cir.tls_model<tls_local_exec>]} +} + +} _______________________________________________ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
