Skip to content

Commit

Permalink
[CIR] Remove redundant result type of cir.const operation (#581)
Browse files Browse the repository at this point in the history
  • Loading branch information
orbiri authored and lanza committed Nov 2, 2024
1 parent 66ac32a commit bc84943
Show file tree
Hide file tree
Showing 136 changed files with 649 additions and 669 deletions.
4 changes: 2 additions & 2 deletions clang/include/clang/CIR/Dialect/Builder/CIRBaseBuilder.h
Original file line number Diff line number Diff line change
Expand Up @@ -328,8 +328,8 @@ class CIRBaseBuilderTy : public mlir::OpBuilder {
}

mlir::TypedAttr getConstPtrAttr(mlir::Type t, uint64_t v) {
assert(t.isa<mlir::cir::PointerType>() && "expected cir.ptr");
return mlir::cir::ConstPtrAttr::get(getContext(), t, v);
return mlir::cir::ConstPtrAttr::get(getContext(),
t.cast<mlir::cir::PointerType>(), v);
}

// Creates constant nullptr for pointer type ty.
Expand Down
15 changes: 12 additions & 3 deletions clang/include/clang/CIR/Dialect/IR/CIRAttrs.td
Original file line number Diff line number Diff line change
Expand Up @@ -248,20 +248,29 @@ def FPAttr : CIR_Attr<"FP", "fp", [TypedAttrInterface]> {

def ConstPtrAttr : CIR_Attr<"ConstPtr", "ptr", [TypedAttrInterface]> {
let summary = "Holds a constant pointer value";
let parameters = (ins AttributeSelfTypeParameter<"">:$type, "uint64_t":$value);
let parameters = (ins
AttributeSelfTypeParameter<"", "::mlir::cir::PointerType">:$type,
"uint64_t":$value);
let description = [{
A pointer attribute is a literal attribute that represents an integral
value of a pointer type.
}];
let builders = [
AttrBuilderWithInferredContext<(ins "Type":$type, "uint64_t":$value), [{
return $_get(type.getContext(), type, value);
return $_get(type.getContext(), type.cast<mlir::cir::PointerType>(), value);
}]>,
AttrBuilder<(ins "Type":$type,
"uint64_t":$value), [{
return $_get($_ctxt, type.cast<mlir::cir::PointerType>(), value);
}]>,
];
let extraClassDeclaration = [{
bool isNullValue() const { return getValue() == 0; }
}];
let hasCustomAssemblyFormat = 1;

let assemblyFormat = [{
`<` custom<ConstPtr>($value) `>`
}];
}

//===----------------------------------------------------------------------===//
Expand Down
47 changes: 22 additions & 25 deletions clang/include/clang/CIR/Dialect/IR/CIROps.td
Original file line number Diff line number Diff line change
Expand Up @@ -264,7 +264,7 @@ def PtrStrideOp : CIR_Op<"ptr_stride",
a stride (second operand).

```mlir
%3 = cir.const(0 : i32) : i32
%3 = cir.const 0 : i32
%4 = cir.ptr_stride(%2 : !cir.ptr<i32>, %3 : i32), !cir.ptr<i32>
```
}];
Expand Down Expand Up @@ -293,7 +293,7 @@ def PtrStrideOp : CIR_Op<"ptr_stride",
//===----------------------------------------------------------------------===//

def ConstantOp : CIR_Op<"const",
[ConstantLike, Pure]> {
[ConstantLike, Pure, AllTypesMatch<["value", "res"]>]> {
// FIXME: Use SameOperandsAndResultType or similar and prevent eye bleeding
// type repetition in the assembly form.

Expand All @@ -303,9 +303,9 @@ def ConstantOp : CIR_Op<"const",
attached to the operation as an attribute.

```mlir
%0 = cir.const(42 : i32) : i32
%1 = cir.const(4.2 : f32) : f32
%2 = cir.const(nullptr : !cir.ptr<i32>) : !cir.ptr<i32>
%0 = cir.const 42 : i32
%1 = cir.const 4.2 : f32
%2 = cir.const nullptr : !cir.ptr<i32>
```
}];

Expand All @@ -315,9 +315,7 @@ def ConstantOp : CIR_Op<"const",
// The constant operation returns a single value of CIR_AnyType.
let results = (outs CIR_AnyType:$res);

let assemblyFormat = [{
`(` custom<ConstantValue>($value) `)` attr-dict `:` type($res)
}];
let assemblyFormat = "attr-dict $value";

let hasVerifier = 1;

Expand Down Expand Up @@ -1111,13 +1109,13 @@ def BitClrsbOp : CIR_BitOp<"bit.clrsb", AnyTypeOf<[SInt32, SInt64]>> {
!s32i = !cir.int<s, 32>

// %0 = 0xDEADBEEF, 0b1101_1110_1010_1101_1011_1110_1110_1111
%0 = cir.const(#cir.int<3735928559> : !s32i) : !s32i
%0 = cir.const #cir.int<3735928559> : !s32i
// %1 will be 1 because there is 1 bit following the most significant bit
// that is identical to it.
%1 = cir.bit.clrsb(%0 : !s32i) : !s32i

// %2 = 1, 0b0000_0000_0000_0000_0000_0000_0000_0001
%2 = cir.const(#cir.int<1> : !s32i) : !s32i
%2 = cir.const #cir.int<1> : !s32i
// %3 will be 30
%3 = cir.bit.clrsb(%2 : !s32i) : !s32i
```
Expand All @@ -1142,7 +1140,7 @@ def BitClzOp : CIR_BitOp<"bit.clz", AnyTypeOf<[UInt16, UInt32, UInt64]>> {
!u32i = !cir.int<u, 32>

// %0 = 0b0000_0000_0000_0000_0000_0000_0000_1000
%0 = cir.const(#cir.int<8> : !u32i) : !u32i
%0 = cir.const #cir.int<8> : !u32i
// %1 will be 28
%1 = cir.bit.clz(%0 : !u32i) : !s32i
```
Expand All @@ -1167,7 +1165,7 @@ def BitCtzOp : CIR_BitOp<"bit.ctz", AnyTypeOf<[UInt16, UInt32, UInt64]>> {
!u32i = !cir.int<u, 32>

// %0 = 0b1000
%0 = cir.const(#cir.int<8> : !u32i) : !u32i
%0 = cir.const #cir.int<8> : !u32i
// %1 will be 3
%1 = cir.bit.ctz(%0 : !u32i) : !s32i
```
Expand All @@ -1190,7 +1188,7 @@ def BitFfsOp : CIR_BitOp<"bit.ffs", AnyTypeOf<[SInt32, SInt64]>> {
!s32i = !cir.int<s, 32>

// %0 = 0x0010_1000
%0 = cir.const(#cir.int<40> : !s32i) : !s32i
%0 = cir.const #cir.int<40> : !s32i
// #1 will be 4 since the 4th least significant bit is 1.
%1 = cir.bit.ffs(%0 : !s32i) : !s32i
```
Expand All @@ -1212,9 +1210,9 @@ def BitParityOp : CIR_BitOp<"bit.parity", AnyTypeOf<[UInt32, UInt64]>> {
!u32i = !cir.int<u, 32>

// %0 = 0x0110_1000
%0 = cir.const(#cir.int<104> : !u32i) : !s32i
%0 = cir.const #cir.int<104> : !u32i
// %1 will be 1 since there are 3 1-bits in %0
%1 = cir.bit.parity(%0 : !u32i) : !s32i
%1 = cir.bit.parity(%0 : !u32i) : !u32i
```
}];
}
Expand All @@ -1230,13 +1228,12 @@ def BitPopcountOp
Example:

```mlir
!s32i = !cir.int<s, 32>
!u32i = !cir.int<u, 32>

// %0 = 0x0110_1000
%0 = cir.const(#cir.int<104> : !u32i) : !s32i
%0 = cir.const #cir.int<104> : !u32i
// %1 will be 3 since there are 3 1-bits in %0
%1 = cir.bit.popcount(%0 : !u32i) : !s32i
%1 = cir.bit.popcount(%0 : !u32i) : !u32i
```
}];
}
Expand All @@ -1260,7 +1257,7 @@ def ByteswapOp : CIR_Op<"bswap", [Pure, SameOperandsAndResultType]> {
!u32i = !cir.int<u, 32>

// %0 = 0x12345678
%0 = cir.const(#cir.int<305419896> : !u32i) : !u32i
%0 = cir.const #cir.int<305419896> : !u32i

// %1 should be 0x78563412
%1 = cir.bswap(%0 : !u32i) : !u32i
Expand Down Expand Up @@ -1302,12 +1299,12 @@ def CmpThreeWayOp : CIR_Op<"cmp3way", [Pure, SameTypeOperands]> {
#cmp3way_strong = #cmp3way_info<strong, lt = -1, eq = 0, gt = 1>
#cmp3way_partial = #cmp3way_info<strong, lt = -1, eq = 0, gt = 1, unordered = 2>

%0 = cir.const(#cir.int<0> : !s32i) : !s32i
%1 = cir.const(#cir.int<1> : !s32i) : !s32i
%0 = cir.const #cir.int<0> : !s32i
%1 = cir.const #cir.int<1> : !s32i
%2 = cir.cmp3way(%0 : !s32i, %1, #cmp3way_strong) : !s8i

%3 = cir.const(#cir.fp<0.0> : !cir.float) : !cir.float
%4 = cir.const(#cir.fp<1.0> : !cir.float) : !cir.float
%3 = cir.const #cir.fp<0.0> : !cir.float
%4 = cir.const #cir.fp<1.0> : !cir.float
%5 = cir.cmp3way(%3 : !cir.float, %4, #cmp3way_partial) : !s8i
```
}];
Expand Down Expand Up @@ -1961,7 +1958,7 @@ def SetBitfieldOp : CIR_Op<"set_bitfield"> {
!struct_type = !cir.struct<struct "S" {!cir.int<u, 32>, !cir.int<u, 32>, !cir.int<u, 16>} #cir.record.decl.ast>
#bfi_d = #cir.bitfield_info<name = "d", storage_type = !u32i, size = 2, offset = 17, is_signed = true>

%1 = cir.const(#cir.int<3> : !s32i) : !s32i
%1 = cir.const #cir.int<3> : !s32i
%2 = cir.load %0 : !cir.ptr<!cir.ptr<!struct_type>>, !cir.ptr<!struct_type>
%3 = cir.get_member %2[1] {name = "d"} : !cir.ptr<!struct_type> -> !cir.ptr<!u32i>
%4 = cir.set_bitfield(#bfi_d, %3 : !cir.ptr<!u32i>, %1 : !s32i) -> !s32i
Expand Down Expand Up @@ -3045,7 +3042,7 @@ def MemCpyOp : CIR_Op<"libc.memcpy"> {

```mlir
// Copying 2 bytes from one array to a struct:
%2 = cir.const(#cir.int<2> : !u32i) : !u32i
%2 = cir.const #cir.int<2> : !u32i
cir.libc.memcpy %2 bytes from %arr to %struct : !cir.ptr<!arr> -> !cir.ptr<!struct>
```
}];
Expand Down
2 changes: 1 addition & 1 deletion clang/lib/CIR/CodeGen/CIRGenExprAgg.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -464,7 +464,7 @@ void AggExprEmitter::buildArrayInit(Address DestPtr, mlir::cir::ArrayType AType,
mlir::Value element = begin;

// Don't build the 'one' before the cycle to avoid
// emmiting the redundant cir.const(1) instrs.
// emmiting the redundant `cir.const 1` instrs.
mlir::Value one;

// Emit the explicit initializers.
Expand Down
37 changes: 14 additions & 23 deletions clang/lib/CIR/Dialect/IR/CIRAttrs.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,11 @@ static mlir::ParseResult
parseFloatLiteral(mlir::AsmParser &parser,
mlir::FailureOr<llvm::APFloat> &value, mlir::Type ty);

static mlir::ParseResult parseConstPtr(mlir::AsmParser &parser,
uint64_t &value);

static void printConstPtr(mlir::AsmPrinter &p, uint64_t value);

#define GET_ATTRDEF_CLASSES
#include "clang/CIR/Dialect/IR/CIROpsAttributes.cpp.inc"

Expand Down Expand Up @@ -213,37 +218,23 @@ void LangAttr::print(AsmPrinter &printer) const {
// ConstPtrAttr definitions
//===----------------------------------------------------------------------===//

Attribute ConstPtrAttr::parse(AsmParser &parser, Type odsType) {
uint64_t value;

if (!odsType.isa<cir::PointerType>())
return {};

// Consume the '<' symbol.
if (parser.parseLess())
return {};
// TODO: Consider encoding the null value differently and use conditional
// assembly format instead of custom parsing/printing.
static ParseResult parseConstPtr(AsmParser &parser, uint64_t &value) {

if (parser.parseOptionalKeyword("null").succeeded()) {
value = 0;
} else {
if (parser.parseInteger(value))
parser.emitError(parser.getCurrentLocation(), "expected integer value");
return success();
}

// Consume the '>' symbol.
if (parser.parseGreater())
return {};

return ConstPtrAttr::get(odsType, value);
return parser.parseInteger(value);
}

void ConstPtrAttr::print(AsmPrinter &printer) const {
printer << '<';
if (isNullValue())
printer << "null";
static void printConstPtr(AsmPrinter &p, uint64_t value) {
if (!value)
p << "null";
else
printer << getValue();
printer << '>';
p << value;
}

//===----------------------------------------------------------------------===//
Expand Down
29 changes: 12 additions & 17 deletions clang/lib/CIR/Dialect/IR/CIRDialect.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -364,23 +364,6 @@ LogicalResult ConstantOp::verify() {
return checkConstantTypes(getOperation(), getType(), getValue());
}

static ParseResult parseConstantValue(OpAsmParser &parser,
mlir::Attribute &valueAttr) {
NamedAttrList attr;
return parser.parseAttribute(valueAttr, "value", attr);
}

// FIXME: create a CIRConstAttr and hide this away for both global
// initialization and cir.const operation.
static void printConstant(OpAsmPrinter &p, Attribute value) {
p.printAttribute(value);
}

static void printConstantValue(OpAsmPrinter &p, cir::ConstantOp op,
Attribute value) {
printConstant(p, value);
}

OpFoldResult ConstantOp::fold(FoldAdaptor /*adaptor*/) { return getValue(); }

//===----------------------------------------------------------------------===//
Expand Down Expand Up @@ -1487,6 +1470,18 @@ ::llvm::SmallVector<Region *> ForOp::getLoopRegions() { return {&getBody()}; }
// GlobalOp
//===----------------------------------------------------------------------===//

static ParseResult parseConstantValue(OpAsmParser &parser,
mlir::Attribute &valueAttr) {
NamedAttrList attr;
return parser.parseAttribute(valueAttr, "value", attr);
}

// FIXME: create a CIRConstAttr and hide this away for both global
// initialization and cir.const operation.
static void printConstant(OpAsmPrinter &p, Attribute value) {
p.printAttribute(value);
}

static void printGlobalOpTypeAndInitialValue(OpAsmPrinter &p, GlobalOp op,
TypeAttr type, Attribute initAttr,
mlir::Region &ctorRegion,
Expand Down
4 changes: 2 additions & 2 deletions clang/lib/CIR/Lowering/DirectToLLVM/LowerToLLVM.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3178,10 +3178,10 @@ static void buildCtorDtorList(
// cir.func @foo(%arg0: !s32i) -> !s32i {
// %4 = cir.cast(int_to_bool, %arg0 : !s32i), !cir.bool
// cir.if %4 {
// %5 = cir.const(#cir.int<1> : !s32i) : !s32i
// %5 = cir.const #cir.int<1> : !s32i
// cir.return %5 : !s32i
// } else {
// %5 = cir.const(#cir.int<0> : !s32i) : !s32i
// %5 = cir.const #cir.int<0> : !s32i
// cir.return %5 : !s32i
// }
// cir.return %arg0 : !s32i
Expand Down
4 changes: 2 additions & 2 deletions clang/test/CIR/CodeGen/OpenMP/parallel.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -18,10 +18,10 @@ void omp_parallel_2() {
// CHECK: omp.parallel {
// CHECK-NEXT: cir.scope {
// CHECK-NEXT: %[[XVarDecl:.+]] = {{.*}} ["x", init]
// CHECK-NEXT: %[[C1:.+]] = cir.const(#cir.int<1> : !s32i)
// CHECK-NEXT: %[[C1:.+]] = cir.const #cir.int<1> : !s32i
// CHECK-NEXT: cir.store %[[C1]], %[[XVarDecl]]
// CHECK-NEXT: %[[XVal:.+]] = cir.load %[[XVarDecl]]
// CHECK-NEXT: %[[COne:.+]] = cir.const(#cir.int<1> : !s32i)
// CHECK-NEXT: %[[COne:.+]] = cir.const #cir.int<1> : !s32i
// CHECK-NEXT: %[[BinOpVal:.+]] = cir.binop(add, %[[XVal]], %[[COne]])
// CHECK-NEXT: cir.store %[[BinOpVal]], %[[YVarDecl]]
// CHECK-NEXT: }
Expand Down
8 changes: 4 additions & 4 deletions clang/test/CIR/CodeGen/String.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -22,10 +22,10 @@ void test() {
// CHECK-NEXT: cir.store %arg0, %0
// CHECK-NEXT: %1 = cir.load %0
// CHECK-NEXT: %2 = cir.get_member %1[0] {name = "storage"}
// CHECK-NEXT: %3 = cir.const(#cir.ptr<null> : !cir.ptr<!s8i>) : !cir.ptr<!s8i>
// CHECK-NEXT: %3 = cir.const #cir.ptr<null> : !cir.ptr<!s8i>
// CHECK-NEXT: cir.store %3, %2 : !cir.ptr<!s8i>, !cir.ptr<!cir.ptr<!s8i>>
// CHECK-NEXT: %4 = cir.get_member %1[1] {name = "size"} : !cir.ptr<!ty_22String22> -> !cir.ptr<!s64i>
// CHECK-NEXT: %5 = cir.const(#cir.int<0> : !s32i) : !s32i
// CHECK-NEXT: %5 = cir.const #cir.int<0> : !s32i
// CHECK-NEXT: %6 = cir.cast(integral, %5 : !s32i), !s64i
// CHECK-NEXT: cir.store %6, %4 : !s64i, !cir.ptr<!s64i>
// CHECK-NEXT: cir.return
Expand All @@ -37,7 +37,7 @@ void test() {
// CHECK-NEXT: cir.store %arg1, %1
// CHECK-NEXT: %2 = cir.load %0
// CHECK-NEXT: %3 = cir.get_member %2[0] {name = "storage"}
// CHECK-NEXT: %4 = cir.const(#cir.ptr<null> : !cir.ptr<!s8i>)
// CHECK-NEXT: %4 = cir.const #cir.ptr<null> : !cir.ptr<!s8i>
// CHECK-NEXT: cir.store %4, %3
// CHECK-NEXT: %5 = cir.get_member %2[1] {name = "size"} : !cir.ptr<!ty_22String22> -> !cir.ptr<!s64i>
// CHECK-NEXT: %6 = cir.load %1 : !cir.ptr<!s32i>, !s32i
Expand All @@ -53,7 +53,7 @@ void test() {
// CHECK-NEXT: cir.store %arg1, %1 : !cir.ptr<!s8i>, !cir.ptr<!cir.ptr<!s8i>>
// CHECK-NEXT: %2 = cir.load %0 : !cir.ptr<!cir.ptr<!ty_22String22>>, !cir.ptr<!ty_22String22>
// CHECK-NEXT: %3 = cir.get_member %2[0] {name = "storage"} : !cir.ptr<!ty_22String22> -> !cir.ptr<!cir.ptr<!s8i>>
// CHECK-NEXT: %4 = cir.const(#cir.ptr<null> : !cir.ptr<!s8i>) : !cir.ptr<!s8i>
// CHECK-NEXT: %4 = cir.const #cir.ptr<null> : !cir.ptr<!s8i>
// CHECK-NEXT: cir.store %4, %3 : !cir.ptr<!s8i>, !cir.ptr<!cir.ptr<!s8i>>
// CHECK-NEXT: cir.return

Expand Down
6 changes: 3 additions & 3 deletions clang/test/CIR/CodeGen/agg-copy.c
Original file line number Diff line number Diff line change
Expand Up @@ -15,10 +15,10 @@ typedef struct {
// CHECK: cir.store %arg0, [[TMP0]] : !cir.ptr<!ty_22A22>, !cir.ptr<!cir.ptr<!ty_22A22>>
// CHECK: cir.store %arg1, [[TMP1]] : !cir.ptr<!ty_22A22>, !cir.ptr<!cir.ptr<!ty_22A22>>
// CHECK: [[TMP2:%.*]] = cir.load [[TMP0]] : !cir.ptr<!cir.ptr<!ty_22A22>>, !cir.ptr<!ty_22A22>
// CHECK: [[TMP3:%.*]] = cir.const(#cir.int<1> : !s32i) : !s32i
// CHECK: [[TMP3:%.*]] = cir.const #cir.int<1> : !s32i
// CHECK: [[TMP4:%.*]] = cir.ptr_stride([[TMP2]] : !cir.ptr<!ty_22A22>, [[TMP3]] : !s32i), !cir.ptr<!ty_22A22>
// CHECK: [[TMP5:%.*]] = cir.load [[TMP1]] : !cir.ptr<!cir.ptr<!ty_22A22>>, !cir.ptr<!ty_22A22>
// CHECK: [[TMP6:%.*]] = cir.const(#cir.int<1> : !s32i) : !s32i
// CHECK: [[TMP6:%.*]] = cir.const #cir.int<1> : !s32i
// CHECK: [[TMP7:%.*]] = cir.ptr_stride([[TMP5]] : !cir.ptr<!ty_22A22>, [[TMP6]] : !s32i), !cir.ptr<!ty_22A22>
// CHECK: cir.copy [[TMP7]] to [[TMP4]] : !cir.ptr<!ty_22A22>
void foo1(A* a1, A* a2) {
Expand Down Expand Up @@ -68,7 +68,7 @@ A create() { A a; return a; }
// CHECK: [[TMP1:%.*]] = cir.alloca !ty_22A22, !cir.ptr<!ty_22A22>, ["tmp"] {alignment = 4 : i64}
// CHECK: [[TMP2:%.*]] = cir.call @create() : () -> !ty_22A22
// CHECK: cir.store [[TMP2]], [[TMP1]] : !ty_22A22, !cir.ptr<!ty_22A22>
// CHECK: cir.copy [[TMP1]] to [[TMP0]] : !cir.ptr<!ty_22A22>
// CHECK: cir.copy [[TMP1]] to [[TMP0]] : !cir.ptr<!ty_22A22>
void foo5() {
A a;
a = create();
Expand Down
Loading

0 comments on commit bc84943

Please sign in to comment.