Skip to content

Commit c31a894

Browse files
committed
Update on "[CIR][CIRGen][NFC] Return scope result in compound stmt builders"
Instead of returning a boolean indicating whether the statement was handled, returns the ReturnExpr of the statement if there is one. It also adds some extra bookkeeping to ensure that the result is returned when needed. This allows for better support of GCC's `ExprStmt` extension. The logical result was not used: it was handled but it would never fail. Any errors within builders should likely be handled with asserts and unreachables since they imply a programmer's error in the code. [ghstack-poisoned]
2 parents f83402e + d7f9bf1 commit c31a894

37 files changed

+401
-851
lines changed

.github/workflows/pr-code-format.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ permissions:
66
jobs:
77
code_formatter:
88
runs-on: ubuntu-latest
9-
if: github.repository == 'llvm/llvm-project'
9+
if: github.repository == 'llvm/clangir'
1010
steps:
1111
- name: Fetch LLVM sources
1212
uses: actions/checkout@v4

clang/include/clang/CIR/Dialect/IR/CIRDialect.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,9 +18,9 @@
1818
#include "mlir/IR/BuiltinTypes.h"
1919
#include "mlir/IR/Dialect.h"
2020
#include "mlir/IR/OpDefinition.h"
21-
#include "mlir/Interfaces/FunctionInterfaces.h"
2221
#include "mlir/Interfaces/CallInterfaces.h"
2322
#include "mlir/Interfaces/ControlFlowInterfaces.h"
23+
#include "mlir/Interfaces/FunctionInterfaces.h"
2424
#include "mlir/Interfaces/InferTypeOpInterface.h"
2525
#include "mlir/Interfaces/LoopLikeInterface.h"
2626
#include "mlir/Interfaces/SideEffectInterfaces.h"

clang/include/clang/CIR/Dialect/IR/CIROps.td

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -582,6 +582,25 @@ def TernaryOp : CIR_Op<"ternary",
582582
}];
583583
}
584584

585+
//===----------------------------------------------------------------------===//
586+
// ConditionOp
587+
//===----------------------------------------------------------------------===//
588+
589+
def ConditionOp : CIR_Op<"condition", [
590+
Terminator,
591+
DeclareOpInterfaceMethods<RegionBranchTerminatorOpInterface,
592+
["getSuccessorRegions"]>
593+
]> {
594+
let summary = "Loop continuation condition.";
595+
let description = [{
596+
The `cir.condition` termintes loop's conditional regions. It takes a single
597+
`cir.bool` operand. if the operand is true, the loop continues, otherwise
598+
it terminates.
599+
}];
600+
let arguments = (ins CIR_BoolType:$condition);
601+
let assemblyFormat = " `(` $condition `)` attr-dict ";
602+
}
603+
585604
//===----------------------------------------------------------------------===//
586605
// YieldOp
587606
//===----------------------------------------------------------------------===//

clang/include/clang/CIR/Dialect/IR/CIRTypesDetails.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
//===- CIRTypesDetails.h - Details of CIR dialect types -----------*- C++ -*-===//
1+
//===- CIRTypesDetails.h - Details of CIR dialect types ---------*- C++ -*-===//
22
//
33
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
44
// See https://llvm.org/LICENSE.txt for license information.

clang/lib/CIR/CodeGen/CIRAsm.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -41,8 +41,8 @@ mlir::LogicalResult CIRGenFunction::buildAsmStmt(const AsmStmt &S) {
4141

4242
AsmDialect AsmDialect = inferDialect(CGM, S);
4343

44-
builder.create<mlir::cir::InlineAsmOp>(
45-
getLoc(S.getAsmLoc()), ResultType, AsmString, AsmDialect);
44+
builder.create<mlir::cir::InlineAsmOp>(getLoc(S.getAsmLoc()), ResultType,
45+
AsmString, AsmDialect);
4646

4747
return mlir::success();
4848
}

clang/lib/CIR/CodeGen/CIRGenBuilder.h

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -578,6 +578,11 @@ class CIRGenBuilderTy : public CIRBaseBuilderTy {
578578
return create<mlir::cir::CopyOp>(dst.getLoc(), dst, src);
579579
}
580580

581+
/// Create a loop condition.
582+
mlir::cir::ConditionOp createCondition(mlir::Value condition) {
583+
return create<mlir::cir::ConditionOp>(condition.getLoc(), condition);
584+
}
585+
581586
mlir::cir::MemCpyOp createMemCpy(mlir::Location loc, mlir::Value dst,
582587
mlir::Value src, mlir::Value len) {
583588
return create<mlir::cir::MemCpyOp>(loc, dst, src, len);
@@ -787,10 +792,10 @@ class CIRGenBuilderTy : public CIRBaseBuilderTy {
787792
return create<mlir::cir::StackSaveOp>(loc, ty);
788793
}
789794

790-
mlir::cir::StackRestoreOp createStackRestore(mlir::Location loc, mlir::Value v) {
795+
mlir::cir::StackRestoreOp createStackRestore(mlir::Location loc,
796+
mlir::Value v) {
791797
return create<mlir::cir::StackRestoreOp>(loc, v);
792798
}
793-
794799
};
795800

796801
} // namespace cir

clang/lib/CIR/CodeGen/CIRGenCoroutine.cpp

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -194,10 +194,9 @@ CIRGenFunction::buildCoroAllocBuiltinCall(mlir::Location loc) {
194194

195195
mlir::cir::FuncOp fnOp;
196196
if (!builtin) {
197-
fnOp = CGM.createCIRFunction(
198-
loc, CGM.builtinCoroAlloc,
199-
mlir::cir::FuncType::get({int32Ty}, boolTy),
200-
/*FD=*/nullptr);
197+
fnOp = CGM.createCIRFunction(loc, CGM.builtinCoroAlloc,
198+
mlir::cir::FuncType::get({int32Ty}, boolTy),
199+
/*FD=*/nullptr);
201200
assert(fnOp && "should always succeed");
202201
fnOp.setBuiltinAttr(mlir::UnitAttr::get(builder.getContext()));
203202
} else
@@ -217,8 +216,7 @@ CIRGenFunction::buildCoroBeginBuiltinCall(mlir::Location loc,
217216
if (!builtin) {
218217
fnOp = CGM.createCIRFunction(
219218
loc, CGM.builtinCoroBegin,
220-
mlir::cir::FuncType::get({int32Ty, VoidPtrTy},
221-
VoidPtrTy),
219+
mlir::cir::FuncType::get({int32Ty, VoidPtrTy}, VoidPtrTy),
222220
/*FD=*/nullptr);
223221
assert(fnOp && "should always succeed");
224222
fnOp.setBuiltinAttr(mlir::UnitAttr::get(builder.getContext()));

clang/lib/CIR/CodeGen/CIRGenDecl.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -892,7 +892,7 @@ struct CallCleanupFunction final : EHScopeStack::Cleanup {
892892
/// Push the standard destructor for the given type as
893893
/// at least a normal cleanup.
894894
void CIRGenFunction::pushDestroy(QualType::DestructionKind dtorKind,
895-
Address addr, QualType type) {
895+
Address addr, QualType type) {
896896
assert(dtorKind && "cannot push destructor for trivial type");
897897

898898
CleanupKind cleanupKind = getCleanupKind(dtorKind);

clang/lib/CIR/CodeGen/CIRGenExpr.cpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -234,8 +234,8 @@ Address CIRGenFunction::getAddrOfBitFieldStorage(LValue base,
234234

235235
auto fieldPtr =
236236
mlir::cir::PointerType::get(getBuilder().getContext(), fieldType);
237-
auto sea = getBuilder().createGetMember(
238-
loc, fieldPtr, base.getPointer(), field->getName(), index);
237+
auto sea = getBuilder().createGetMember(loc, fieldPtr, base.getPointer(),
238+
field->getName(), index);
239239

240240
return Address(sea, CharUnits::One());
241241
}
@@ -341,7 +341,7 @@ LValue CIRGenFunction::buildLValueForField(LValue base,
341341
if (!IsInPreservedAIRegion &&
342342
(!getDebugInfo() || !rec->hasAttr<BPFPreserveAccessIndexAttr>())) {
343343
llvm::StringRef fieldName = field->getName();
344-
auto& layout = CGM.getTypes().getCIRGenRecordLayout(field->getParent());
344+
auto &layout = CGM.getTypes().getCIRGenRecordLayout(field->getParent());
345345
unsigned fieldIndex = layout.getCIRFieldNo(field);
346346

347347
if (CGM.LambdaFieldToName.count(field))
@@ -396,7 +396,7 @@ LValue CIRGenFunction::buildLValueForFieldInitialization(
396396
if (!FieldType->isReferenceType())
397397
return buildLValueForField(Base, Field);
398398

399-
auto& layout = CGM.getTypes().getCIRGenRecordLayout(Field->getParent());
399+
auto &layout = CGM.getTypes().getCIRGenRecordLayout(Field->getParent());
400400
unsigned FieldIndex = layout.getCIRFieldNo(Field);
401401

402402
Address V = buildAddrOfFieldStorage(*this, Base.getAddress(), Field,

clang/lib/CIR/CodeGen/CIRGenExprAgg.cpp

Lines changed: 35 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -60,37 +60,36 @@ static bool isBlockVarRef(const Expr *E) {
6060
// FIXME: pointer arithmetic?
6161
return false;
6262

63-
// Check both sides of a conditional operator.
64-
} else if (const AbstractConditionalOperator *op
65-
= dyn_cast<AbstractConditionalOperator>(E)) {
66-
return isBlockVarRef(op->getTrueExpr())
67-
|| isBlockVarRef(op->getFalseExpr());
68-
69-
// OVEs are required to support BinaryConditionalOperators.
70-
} else if (const OpaqueValueExpr *op
71-
= dyn_cast<OpaqueValueExpr>(E)) {
63+
// Check both sides of a conditional operator.
64+
} else if (const AbstractConditionalOperator *op =
65+
dyn_cast<AbstractConditionalOperator>(E)) {
66+
return isBlockVarRef(op->getTrueExpr()) ||
67+
isBlockVarRef(op->getFalseExpr());
68+
69+
// OVEs are required to support BinaryConditionalOperators.
70+
} else if (const OpaqueValueExpr *op = dyn_cast<OpaqueValueExpr>(E)) {
7271
if (const Expr *src = op->getSourceExpr())
7372
return isBlockVarRef(src);
7473

75-
// Casts are necessary to get things like (*(int*)&var) = foo().
76-
// We don't really care about the kind of cast here, except
77-
// we don't want to look through l2r casts, because it's okay
78-
// to get the *value* in a __block variable.
74+
// Casts are necessary to get things like (*(int*)&var) = foo().
75+
// We don't really care about the kind of cast here, except
76+
// we don't want to look through l2r casts, because it's okay
77+
// to get the *value* in a __block variable.
7978
} else if (const CastExpr *cast = dyn_cast<CastExpr>(E)) {
8079
if (cast->getCastKind() == CK_LValueToRValue)
8180
return false;
8281
return isBlockVarRef(cast->getSubExpr());
8382

84-
// Handle unary operators. Again, just aggressively look through
85-
// it, ignoring the operation.
83+
// Handle unary operators. Again, just aggressively look through
84+
// it, ignoring the operation.
8685
} else if (const UnaryOperator *uop = dyn_cast<UnaryOperator>(E)) {
8786
return isBlockVarRef(uop->getSubExpr());
8887

89-
// Look into the base of a field access.
88+
// Look into the base of a field access.
9089
} else if (const MemberExpr *mem = dyn_cast<MemberExpr>(E)) {
9190
return isBlockVarRef(mem->getBase());
9291

93-
// Look into the base of a subscript.
92+
// Look into the base of a subscript.
9493
} else if (const ArraySubscriptExpr *sub = dyn_cast<ArraySubscriptExpr>(E)) {
9594
return isBlockVarRef(sub->getBase());
9695
}
@@ -113,7 +112,8 @@ class AggExprEmitter : public StmtVisitor<AggExprEmitter> {
113112
llvm::function_ref<RValue(ReturnValueSlot)> Fn);
114113

115114
AggValueSlot EnsureSlot(mlir::Location loc, QualType T) {
116-
if (!Dest.isIgnored()) return Dest;
115+
if (!Dest.isIgnored())
116+
return Dest;
117117
return CGF.CreateAggTemp(T, loc, "agg.tmp.ensured");
118118
}
119119

@@ -213,11 +213,11 @@ class AggExprEmitter : public StmtVisitor<AggExprEmitter> {
213213
// For an assignment to work, the value on the right has
214214
// to be compatible with the value on the left.
215215
assert(CGF.getContext().hasSameUnqualifiedType(E->getLHS()->getType(),
216-
E->getRHS()->getType())
217-
&& "Invalid assignment");
216+
E->getRHS()->getType()) &&
217+
"Invalid assignment");
218218

219219
if (isBlockVarRef(E->getLHS()) &&
220-
E->getRHS()->HasSideEffects(CGF.getContext())) {
220+
E->getRHS()->HasSideEffects(CGF.getContext())) {
221221
llvm_unreachable("NYI");
222222
}
223223

@@ -233,12 +233,11 @@ class AggExprEmitter : public StmtVisitor<AggExprEmitter> {
233233

234234
// Codegen the RHS so that it stores directly into the LHS.
235235
AggValueSlot lhsSlot = AggValueSlot::forLValue(
236-
lhs, AggValueSlot::IsDestructed, AggValueSlot::DoesNotNeedGCBarriers,
237-
AggValueSlot::IsAliased, AggValueSlot::MayOverlap);
236+
lhs, AggValueSlot::IsDestructed, AggValueSlot::DoesNotNeedGCBarriers,
237+
AggValueSlot::IsAliased, AggValueSlot::MayOverlap);
238238

239239
// A non-volatile aggregate destination might have volatile member.
240-
if (!lhsSlot.isVolatile() &&
241-
CGF.hasVolatileMember(E->getLHS()->getType()))
240+
if (!lhsSlot.isVolatile() && CGF.hasVolatileMember(E->getLHS()->getType()))
242241
assert(!UnimplementedFeature::atomicTypes());
243242

244243
CGF.buildAggExpr(E->getRHS(), lhsSlot);
@@ -247,10 +246,10 @@ class AggExprEmitter : public StmtVisitor<AggExprEmitter> {
247246
buildFinalDestCopy(E->getType(), lhs);
248247

249248
if (!Dest.isIgnored() && !Dest.isExternallyDestructed() &&
250-
E->getType().isDestructedType() == QualType::DK_nontrivial_c_struct)
249+
E->getType().isDestructedType() == QualType::DK_nontrivial_c_struct)
251250
CGF.pushDestroy(QualType::DK_nontrivial_c_struct, Dest.getAddress(),
252-
E->getType());
253-
}
251+
E->getType());
252+
}
254253

255254
void VisitBinComma(const BinaryOperator *E) { llvm_unreachable("NYI"); }
256255
void VisitBinCmp(const BinaryOperator *E) { llvm_unreachable("NYI"); }
@@ -356,8 +355,8 @@ void AggExprEmitter::buildFinalDestCopy(QualType type, const LValue &src,
356355
assert(!UnimplementedFeature::volatileTypes());
357356

358357
if (SrcValueKind == EVK_RValue) {
359-
if (type.isNonTrivialToPrimitiveDestructiveMove() == QualType::PCK_Struct) {
360-
llvm_unreachable("move assignment/move ctor for rvalue is NYI");
358+
if (type.isNonTrivialToPrimitiveDestructiveMove() == QualType::PCK_Struct) {
359+
llvm_unreachable("move assignment/move ctor for rvalue is NYI");
361360
}
362361
} else {
363362
if (type.isNonTrivialToPrimitiveCopy() == QualType::PCK_Struct)
@@ -672,8 +671,8 @@ void AggExprEmitter::VisitLambdaExpr(LambdaExpr *E) {
672671
}
673672

674673
// Emit initialization
675-
LValue LV = CGF.buildLValueForFieldInitialization(
676-
SlotLV, *CurField, fieldName);
674+
LValue LV =
675+
CGF.buildLValueForFieldInitialization(SlotLV, *CurField, fieldName);
677676
if (CurField->hasCapturedVLAType()) {
678677
llvm_unreachable("NYI");
679678
}
@@ -820,8 +819,8 @@ void AggExprEmitter::withReturnValueSlot(
820819
if (!UseTemp) {
821820
RetAddr = Dest.getAddress();
822821
} else {
823-
RetAddr = CGF.CreateMemTemp(RetTy, CGF.getLoc(E->getSourceRange()),
824-
"tmp", &RetAddr);
822+
RetAddr = CGF.CreateMemTemp(RetTy, CGF.getLoc(E->getSourceRange()), "tmp",
823+
&RetAddr);
825824
assert(!UnimplementedFeature::shouldEmitLifetimeMarkers() && "NYI");
826825
}
827826

@@ -940,8 +939,8 @@ void AggExprEmitter::VisitCXXParenListOrInitListExpr(
940939
if (curInitIndex == NumInitElements && Dest.isZeroed() &&
941940
CGF.getTypes().isZeroInitializable(ExprToVisit->getType()))
942941
break;
943-
LValue LV = CGF.buildLValueForFieldInitialization(
944-
DestLV, field, field->getName());
942+
LValue LV =
943+
CGF.buildLValueForFieldInitialization(DestLV, field, field->getName());
945944
// We never generate write-barries for initialized fields.
946945
assert(!UnimplementedFeature::setNonGC());
947946

clang/lib/CIR/CodeGen/CIRGenExprConst.cpp

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -907,7 +907,7 @@ class ConstExprEmitter
907907
// Look through the temporary; it's just converting the value to an lvalue
908908
// to pass it to the constructor.
909909
if (auto *MTE = dyn_cast<MaterializeTemporaryExpr>(Arg))
910-
return Visit(MTE->getSubExpr(), Ty);
910+
return Visit(MTE->getSubExpr(), Ty);
911911
// Don't try to support arbitrary lvalue-to-rvalue conversions for now.
912912
return nullptr;
913913
}
@@ -1074,8 +1074,7 @@ class ConstantLValueEmitter
10741074
ConstantLValue applyOffset(ConstantLValue &C) {
10751075

10761076
// Handle attribute constant LValues.
1077-
if (auto Attr =
1078-
C.Value.dyn_cast<mlir::Attribute>()) {
1077+
if (auto Attr = C.Value.dyn_cast<mlir::Attribute>()) {
10791078
if (auto GV = Attr.dyn_cast<mlir::cir::GlobalViewAttr>()) {
10801079
auto baseTy = GV.getType().cast<mlir::cir::PointerType>().getPointee();
10811080
auto destTy = CGM.getTypes().convertTypeForMem(DestType);
@@ -1338,7 +1337,7 @@ mlir::Attribute ConstantEmitter::tryEmitPrivateForVarInit(const VarDecl &D) {
13381337
}
13391338
InConstantContext = D.hasConstantInitialization();
13401339

1341-
const Expr * E = D.getInit();
1340+
const Expr *E = D.getInit();
13421341
assert(E && "No initializer to emit");
13431342

13441343
QualType destType = D.getType();

clang/lib/CIR/CodeGen/CIRGenFunction.h

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -771,7 +771,7 @@ class CIRGenFunction : public CIRGenTypeCache {
771771
/// Create a check for a function parameter that may potentially be
772772
/// declared as non-null.
773773
void buildNonNullArgCheck(RValue RV, QualType ArgType, SourceLocation ArgLoc,
774-
AbstractCallee AC, unsigned ParmNum);
774+
AbstractCallee AC, unsigned ParmNum);
775775

776776
void buildCallArg(CallArgList &args, const clang::Expr *E,
777777
clang::QualType ArgType);
@@ -1364,7 +1364,7 @@ class CIRGenFunction : public CIRGenTypeCache {
13641364
AggValueSlot::Overlap_t getOverlapForFieldInit(const FieldDecl *FD);
13651365
LValue buildLValueForField(LValue Base, const clang::FieldDecl *Field);
13661366
LValue buildLValueForBitField(LValue base, const FieldDecl *field);
1367-
1367+
13681368
/// Like buildLValueForField, excpet that if the Field is a reference, this
13691369
/// will return the address of the reference and not the address of the value
13701370
/// stored in the reference.
@@ -1522,8 +1522,8 @@ class CIRGenFunction : public CIRGenTypeCache {
15221522

15231523
static Destroyer destroyCXXObject;
15241524

1525-
void pushDestroy(QualType::DestructionKind dtorKind,
1526-
Address addr, QualType type);
1525+
void pushDestroy(QualType::DestructionKind dtorKind, Address addr,
1526+
QualType type);
15271527

15281528
void pushDestroy(CleanupKind kind, Address addr, QualType type,
15291529
Destroyer *destroyer, bool useEHCleanupForArray);

clang/lib/CIR/CodeGen/CIRGenModule.cpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -100,10 +100,10 @@ CIRGenModule::CIRGenModule(mlir::MLIRContext &context,
100100
const clang::CodeGenOptions &CGO,
101101
DiagnosticsEngine &Diags)
102102
: builder(context, *this), astCtx(astctx), langOpts(astctx.getLangOpts()),
103-
codeGenOpts(CGO), theModule{mlir::ModuleOp::create(
104-
builder.getUnknownLoc())},
105-
Diags(Diags), target(astCtx.getTargetInfo()),
106-
ABI(createCXXABI(*this)), genTypes{*this}, VTables{*this} {
103+
codeGenOpts(CGO),
104+
theModule{mlir::ModuleOp::create(builder.getUnknownLoc())}, Diags(Diags),
105+
target(astCtx.getTargetInfo()), ABI(createCXXABI(*this)), genTypes{*this},
106+
VTables{*this} {
107107

108108
// Initialize CIR signed integer types cache.
109109
SInt8Ty =

0 commit comments

Comments
 (0)