diff --git a/clang/include/clang/CIR/Dialect/IR/CIROps.td b/clang/include/clang/CIR/Dialect/IR/CIROps.td index 8b75b667aec7..e570b9d42e6c 100644 --- a/clang/include/clang/CIR/Dialect/IR/CIROps.td +++ b/clang/include/clang/CIR/Dialect/IR/CIROps.td @@ -580,6 +580,12 @@ def CIR_AllocaOp : CIR_Op<"alloca", [ The presence of the `const` attribute indicates that the local variable is declared with C/C++ `const` keyword. + The presence of the `tmp` attribute indicates that the allocation + represents a compiler-generated temporary (e.g., from MaterializeTemporaryExpr, + aggregate temporaries, reference binding temporaries). This is used by the + lifetime checker to identify temporaries that may be skipped for certain + analyses. + The `dynAllocSize` specifies the size to dynamically allocate on the stack and ignores the allocation size based on the original type. This is useful when handling VLAs and is omitted when declaring regular local variables. @@ -604,6 +610,7 @@ def CIR_AllocaOp : CIR_Op<"alloca", [ StrAttr:$name, UnitAttr:$init, UnitAttr:$constant, + UnitAttr:$tmp, ConfinedAttr, [IntMinValue<0>]>:$alignment, OptionalAttr:$annotations, OptionalAttr:$ast @@ -637,13 +644,12 @@ def CIR_AllocaOp : CIR_Op<"alloca", [ bool isDynamic() { return (bool)getDynAllocSize(); } }]; + // Custom parse/print allows flags in any order and supports tmp-only or + // init/const-only spellings, which the compact format can't express. let assemblyFormat = [{ $allocaType `,` qualified(type($addr)) `,` ($dynAllocSize^ `:` type($dynAllocSize) `,`)? - `[` $name - (`,` `init` $init^)? - (`,` `const` $constant^)? - `]` + custom($name, $init, $constant, $tmp) ($annotations^)? (`ast` $ast^)? attr-dict }]; diff --git a/clang/lib/CIR/CodeGen/CIRGenAtomic.cpp b/clang/lib/CIR/CodeGen/CIRGenAtomic.cpp index 3d7c6595ad8a..49f4598d0a93 100644 --- a/clang/lib/CIR/CodeGen/CIRGenAtomic.cpp +++ b/clang/lib/CIR/CodeGen/CIRGenAtomic.cpp @@ -263,7 +263,7 @@ class AtomicInfo { // This function emits any expression (scalar, complex, or aggregate) // into a temporary alloca. static Address emitValToTemp(CIRGenFunction &CGF, Expr *E) { - Address DeclPtr = CGF.CreateMemTemp( + Address DeclPtr = CGF.CreateMemTempWithName( E->getType(), CGF.getLoc(E->getSourceRange()), ".atomictmp"); CGF.emitAnyExprToMem(E, DeclPtr, E->getType().getQualifiers(), /*Init*/ true); @@ -322,7 +322,7 @@ Address AtomicInfo::convertToAtomicIntPointer(Address Addr) const { } Address AtomicInfo::CreateTempAlloca() const { - Address TempAlloca = CGF.CreateMemTemp( + Address TempAlloca = CGF.CreateMemTempWithName( (LVal.isBitField() && ValueSizeInBits > AtomicSizeInBits) ? ValueTy : AtomicTy, getAtomicAlignment(), loc, "atomic-temp"); @@ -1031,7 +1031,8 @@ RValue CIRGenFunction::emitAtomicExpr(AtomicExpr *E) { if (ShouldCastToIntPtrTy) Dest = Atomics.castToAtomicIntPointer(Dest); } else if (E->isCmpXChg()) - Dest = CreateMemTemp(RValTy, getLoc(E->getSourceRange()), "cmpxchg.bool"); + Dest = CreateMemTempWithName(RValTy, getLoc(E->getSourceRange()), + "cmpxchg.bool"); else if (!RValTy->isVoidType()) { Dest = Atomics.CreateTempAlloca(); if (ShouldCastToIntPtrTy) diff --git a/clang/lib/CIR/CodeGen/CIRGenBuiltinX86.cpp b/clang/lib/CIR/CodeGen/CIRGenBuiltinX86.cpp index ff735a5e0182..80b687136413 100644 --- a/clang/lib/CIR/CodeGen/CIRGenBuiltinX86.cpp +++ b/clang/lib/CIR/CodeGen/CIRGenBuiltinX86.cpp @@ -570,7 +570,7 @@ mlir::Value CIRGenFunction::emitX86BuiltinExpr(unsigned BuiltinID, case X86::BI_mm_setcsr: case X86::BI__builtin_ia32_ldmxcsr: { Address tmp = - CreateMemTemp(E->getArg(0)->getType(), getLoc(E->getExprLoc())); + CreateMemTempWithName(E->getArg(0)->getType(), getLoc(E->getExprLoc())); builder.createStore(getLoc(E->getExprLoc()), Ops[0], tmp); return cir::LLVMIntrinsicCallOp::create( builder, getLoc(E->getExprLoc()), @@ -580,7 +580,7 @@ mlir::Value CIRGenFunction::emitX86BuiltinExpr(unsigned BuiltinID, } case X86::BI_mm_getcsr: case X86::BI__builtin_ia32_stmxcsr: { - Address tmp = CreateMemTemp(E->getType(), getLoc(E->getExprLoc())); + Address tmp = CreateMemTempWithName(E->getType(), getLoc(E->getExprLoc())); cir::LLVMIntrinsicCallOp::create(builder, getLoc(E->getExprLoc()), builder.getStringAttr("x86.sse.stmxcsr"), builder.getVoidTy(), tmp.getPointer()) diff --git a/clang/lib/CIR/CodeGen/CIRGenCall.cpp b/clang/lib/CIR/CodeGen/CIRGenCall.cpp index 369ccb9a5401..e677eca2857e 100644 --- a/clang/lib/CIR/CodeGen/CIRGenCall.cpp +++ b/clang/lib/CIR/CodeGen/CIRGenCall.cpp @@ -499,7 +499,7 @@ RValue CIRGenFunction::emitCall(const CIRGenFunctionInfo &CallInfo, // FIXME: Avoid the conversion through memory if possible. Address Src = Address::invalid(); if (!I->isAggregate()) { - Src = CreateMemTemp(I->Ty, loc, "coerce"); + Src = CreateMemTempWithName(I->Ty, loc, "coerce"); I->copyInto(*this, Src, loc); } else { Src = I->hasLValue() ? I->getKnownLValue().getAddress() @@ -698,7 +698,7 @@ RValue CIRGenFunction::emitCall(const CIRGenFunctionInfo &CallInfo, bool DestIsVolatile = ReturnValue.isVolatile(); if (!DestPtr.isValid()) { - DestPtr = CreateMemTemp(RetTy, callLoc, getCounterAggTmpAsString()); + DestPtr = CreateAggTempAddressWithAutoName(RetTy, callLoc); DestIsVolatile = false; } @@ -721,7 +721,7 @@ RValue CIRGenFunction::emitCall(const CIRGenFunctionInfo &CallInfo, Address DestPtr = ReturnValue.getValue(); if (!DestPtr.isValid()) - DestPtr = CreateMemTemp(RetTy, callLoc, "tmp.try.call.res"); + DestPtr = CreateMemTempWithName(RetTy, callLoc, "tmp.try.call.res"); return getRValueThroughMemory(callLoc, builder, Results[0], DestPtr); } @@ -832,8 +832,8 @@ RValue CIRGenFunction::emitAnyExprToTemp(const Expr *E) { AggValueSlot AggSlot = AggValueSlot::ignored(); if (hasAggregateEvaluationKind(E->getType())) - AggSlot = CreateAggTemp(E->getType(), getLoc(E->getSourceRange()), - getCounterAggTmpAsString()); + AggSlot = + CreateAggTempWithAutoName(E->getType(), getLoc(E->getSourceRange())); return emitAnyExpr(E, AggSlot); } @@ -1413,7 +1413,7 @@ CIRGenTypes::arrangeFunctionDeclaration(const FunctionDecl *FD) { RValue CallArg::getRValue(CIRGenFunction &CGF, mlir::Location loc) const { if (!HasLV) return RV; - LValue Copy = CGF.makeAddrLValue(CGF.CreateMemTemp(Ty, loc), Ty); + LValue Copy = CGF.makeAddrLValue(CGF.CreateMemTempWithName(Ty, loc), Ty); CGF.emitAggregateCopy(Copy, LV, Ty, AggValueSlot::DoesNotOverlap, LV.isVolatile()); IsUsed = true; diff --git a/clang/lib/CIR/CodeGen/CIRGenClass.cpp b/clang/lib/CIR/CodeGen/CIRGenClass.cpp index beb4f48987a3..ded7394546ac 100644 --- a/clang/lib/CIR/CodeGen/CIRGenClass.cpp +++ b/clang/lib/CIR/CodeGen/CIRGenClass.cpp @@ -1046,8 +1046,8 @@ void CIRGenFunction::emitLambdaDelegatingInvokeBody(const CXXMethodDecl *MD) { QualType LambdaType = getContext().getCanonicalTagType(Lambda); QualType ThisType = getContext().getPointerType(LambdaType); - Address ThisPtr = - CreateMemTemp(LambdaType, getLoc(MD->getSourceRange()), "unused.capture"); + Address ThisPtr = CreateMemTempWithName( + LambdaType, getLoc(MD->getSourceRange()), "unused.capture"); CallArgs.add(RValue::get(ThisPtr.getPointer()), ThisType); // Add the rest of the parameters. diff --git a/clang/lib/CIR/CodeGen/CIRGenExpr.cpp b/clang/lib/CIR/CodeGen/CIRGenExpr.cpp index 47b135088945..ff7b3bb54a3c 100644 --- a/clang/lib/CIR/CodeGen/CIRGenExpr.cpp +++ b/clang/lib/CIR/CodeGen/CIRGenExpr.cpp @@ -492,8 +492,8 @@ LValue CIRGenFunction::emitCompoundLiteralLValue(const CompoundLiteralExpr *E) { llvm_unreachable("NYI"); } - Address DeclPtr = CreateMemTemp(E->getType(), getLoc(E->getSourceRange()), - ".compoundliteral"); + Address DeclPtr = CreateMemTempWithName( + E->getType(), getLoc(E->getSourceRange()), ".compoundliteral"); const Expr *InitExpr = E->getInitializer(); LValue Result = makeAddrLValue(DeclPtr, E->getType(), AlignmentSource::Decl); @@ -722,7 +722,7 @@ void CIRGenFunction::emitStoreOfScalar(mlir::Value value, Address addr, // Update the alloca with more info on initialization. assert(addr.getPointer() && "expected pointer to exist"); auto SrcAlloca = addr.getDefiningOp(); - if (currVarDecl && SrcAlloca) { + if (currVarDecl && SrcAlloca && !SrcAlloca.getTmpAttr()) { const VarDecl *VD = currVarDecl; assert(VD && "VarDecl expected"); SrcAlloca.setInit(VD->hasInit()); @@ -1360,7 +1360,7 @@ LValue CIRGenFunction::emitExtVectorElementExpr(const ExtVectorElementExpr *E) { // Store the vector to memory (because LValue wants an address). QualType BaseTy = E->getBase()->getType(); - Address VecMem = CreateMemTemp(BaseTy, Vec.getLoc(), "tmp"); + Address VecMem = CreateMemTempWithName(BaseTy, Vec.getLoc(), "tmp"); builder.createStore(Vec.getLoc(), Vec, VecMem); base = makeAddrLValue(VecMem, BaseTy, AlignmentSource::Decl); } @@ -1550,8 +1550,8 @@ RValue CIRGenFunction::emitAnyExpr(const Expr *E, AggValueSlot aggSlot, return RValue::getComplex(emitComplexExpr(E)); case cir::TEK_Aggregate: { if (!ignoreResult && aggSlot.isIgnored()) - aggSlot = CreateAggTemp(E->getType(), getLoc(E->getSourceRange()), - getCounterAggTmpAsString()); + aggSlot = + CreateAggTempWithAutoName(E->getType(), getLoc(E->getSourceRange())); emitAggExpr(E, aggSlot); return aggSlot.asRValue(); } @@ -2451,8 +2451,8 @@ static Address createReferenceTemporary(CIRGenFunction &CGF, mlir::OpBuilder::InsertPoint ip; if (extDeclAlloca) ip = {extDeclAlloca->getBlock(), extDeclAlloca->getIterator()}; - return CGF.CreateMemTemp(Ty, CGF.getLoc(M->getSourceRange()), - CGF.getCounterRefTmpAsString(), Alloca, ip); + return CGF.CreateRefTempWithAutoName(Ty, CGF.getLoc(M->getSourceRange()), + Alloca, ip); } case SD_Thread: case SD_Static: { @@ -3056,7 +3056,8 @@ mlir::Value CIRGenFunction::emitOpOnBoolExpr(mlir::Location loc, mlir::Value CIRGenFunction::emitAlloca(StringRef name, mlir::Type ty, mlir::Location loc, CharUnits alignment, bool insertIntoFnEntryBlock, - mlir::Value arraySize) { + mlir::Value arraySize, + bool isTemporary) { mlir::Block *entryBlock = insertIntoFnEntryBlock ? getCurFunctionEntryBlock() : currLexScope->getEntryBlock(); @@ -3072,13 +3073,15 @@ mlir::Value CIRGenFunction::emitAlloca(StringRef name, mlir::Type ty, } return emitAlloca(name, ty, loc, alignment, - builder.getBestAllocaInsertPoint(entryBlock), arraySize); + builder.getBestAllocaInsertPoint(entryBlock), arraySize, + isTemporary); } mlir::Value CIRGenFunction::emitAlloca(StringRef name, mlir::Type ty, mlir::Location loc, CharUnits alignment, mlir::OpBuilder::InsertPoint ip, - mlir::Value arraySize) { + mlir::Value arraySize, + bool isTemporary) { // CIR uses its own alloca AS rather than follow the target data layout like // original CodeGen. The data layout awareness should be done in the lowering // pass instead. @@ -3091,10 +3094,16 @@ mlir::Value CIRGenFunction::emitAlloca(StringRef name, mlir::Type ty, builder.restoreInsertionPoint(ip); addr = builder.createAlloca(loc, /*addr type*/ localVarPtrTy, /*var type*/ ty, name, alignIntAttr, arraySize); + auto alloca = addr.getDefiningOp(); + if (currVarDecl) { - auto alloca = addr.getDefiningOp(); alloca.setAstAttr(ASTVarDeclAttr::get(&getMLIRContext(), currVarDecl)); } + + // Set temporary attribute based on semantic information. + // Currently used for ref.tmp*/agg.tmp*; other scratch temps are unmarked. + if (isTemporary) + alloca.setTmpAttr(builder.getUnitAttr()); } return addr; } @@ -3102,9 +3111,10 @@ mlir::Value CIRGenFunction::emitAlloca(StringRef name, mlir::Type ty, mlir::Value CIRGenFunction::emitAlloca(StringRef name, QualType ty, mlir::Location loc, CharUnits alignment, bool insertIntoFnEntryBlock, - mlir::Value arraySize) { + mlir::Value arraySize, + bool isTemporary) { return emitAlloca(name, convertType(ty), loc, alignment, - insertIntoFnEntryBlock, arraySize); + insertIntoFnEntryBlock, arraySize, isTemporary); } mlir::Value CIRGenFunction::emitLoadOfScalar(LValue lvalue, @@ -3262,34 +3272,61 @@ void CIRGenFunction::emitUnreachable(SourceLocation Loc) { // CIR builder helpers //===----------------------------------------------------------------------===// -Address CIRGenFunction::CreateMemTemp(QualType Ty, mlir::Location Loc, - const Twine &Name, Address *Alloca, - mlir::OpBuilder::InsertPoint ip) { +Address CIRGenFunction::CreateMemTempWithName(QualType Ty, mlir::Location Loc, + const Twine &Name, + Address *Alloca, + mlir::OpBuilder::InsertPoint ip, + bool isTemporary) { // FIXME: Should we prefer the preferred type alignment here? - return CreateMemTemp(Ty, getContext().getTypeAlignInChars(Ty), Loc, Name, - Alloca, ip); + return CreateMemTempWithName(Ty, getContext().getTypeAlignInChars(Ty), Loc, + Name, Alloca, ip, isTemporary); } -Address CIRGenFunction::CreateMemTemp(QualType Ty, CharUnits Align, - mlir::Location Loc, const Twine &Name, - Address *Alloca, - mlir::OpBuilder::InsertPoint ip) { +Address CIRGenFunction::CreateMemTempWithName( + QualType Ty, CharUnits Align, mlir::Location Loc, const Twine &Name, + Address *Alloca, mlir::OpBuilder::InsertPoint ip, bool isTemporary) { + // CreateMemTempWithName may be used for compiler-generated temporaries + // (ref.tmp*/agg.tmp*). Other scratch allocas are not marked temporary yet. Address Result = CreateTempAlloca(convertTypeForMem(Ty), /*destAS=*/{}, Align, Loc, Name, - /*ArraySize=*/nullptr, Alloca, ip); + /*ArraySize=*/nullptr, Alloca, ip, isTemporary); if (Ty->isConstantMatrixType()) { assert(0 && "NYI"); } return Result; } +Address +CIRGenFunction::CreateRefTempWithAutoName(QualType Ty, mlir::Location Loc, + Address *Alloca, + mlir::OpBuilder::InsertPoint ip) { + return CreateMemTempWithName(Ty, Loc, getCounterRefTmpAsString(), Alloca, ip, + /*isTemporary=*/true); +} + +Address CIRGenFunction::CreateAggTempAddressWithAutoName( + QualType Ty, mlir::Location Loc, Address *Alloca, + mlir::OpBuilder::InsertPoint ip) { + return CreateMemTempWithName(Ty, Loc, getCounterAggTmpAsString(), Alloca, ip, + /*isTemporary=*/true); +} + +AggValueSlot CIRGenFunction::CreateAggTempWithAutoName(QualType Ty, + mlir::Location Loc, + Address *Alloca) { + return CreateAggTempWithName(Ty, Loc, getCounterAggTmpAsString(), Alloca); +} + /// This creates a alloca and inserts it into the entry block of the /// current region. Address CIRGenFunction::CreateTempAllocaWithoutCast( mlir::Type Ty, CharUnits Align, mlir::Location Loc, const Twine &Name, - mlir::Value ArraySize, mlir::OpBuilder::InsertPoint ip) { - auto Alloca = ip.isSet() ? CreateTempAlloca(Ty, Loc, Name, ip, ArraySize) - : CreateTempAlloca(Ty, Loc, Name, ArraySize); + mlir::Value ArraySize, mlir::OpBuilder::InsertPoint ip, bool isTemporary) { + auto Alloca = + ip.isSet() + ? CreateTempAlloca(Ty, Loc, Name, ip, ArraySize, isTemporary) + : CreateTempAlloca(Ty, Loc, Name, ArraySize, + /*insertIntoFnEntryBlock=*/false, isTemporary); Alloca.setAlignmentAttr(CGM.getSize(Align)); return Address(Alloca, Ty, Align); } @@ -3340,9 +3377,9 @@ Address CIRGenFunction::maybeCastStackAddressSpace( Address CIRGenFunction::CreateTempAlloca( mlir::Type Ty, mlir::ptr::MemorySpaceAttrInterface destAS, CharUnits Align, mlir::Location Loc, const Twine &Name, mlir::Value ArraySize, - Address *AllocaAddr, mlir::OpBuilder::InsertPoint ip) { - Address Alloca = - CreateTempAllocaWithoutCast(Ty, Align, Loc, Name, ArraySize, ip); + Address *AllocaAddr, mlir::OpBuilder::InsertPoint ip, bool isTemporary) { + Address Alloca = CreateTempAllocaWithoutCast(Ty, Align, Loc, Name, ArraySize, + ip, isTemporary); if (AllocaAddr) *AllocaAddr = Alloca; return maybeCastStackAddressSpace(Alloca, destAS, ArraySize); @@ -3352,42 +3389,40 @@ Address CIRGenFunction::CreateTempAlloca(mlir::Type Ty, CharUnits Align, mlir::Location Loc, const Twine &Name, mlir::Value ArraySize, Address *AllocaAddr, - mlir::OpBuilder::InsertPoint ip) { + mlir::OpBuilder::InsertPoint ip, + bool isTemporary) { return CreateTempAlloca(Ty, /*destAS=*/{}, Align, Loc, Name, ArraySize, - AllocaAddr, ip); + AllocaAddr, ip, isTemporary); } /// This creates an alloca and inserts it into the entry block if \p ArraySize /// is nullptr, otherwise inserts it at the current insertion point of the /// builder. -cir::AllocaOp CIRGenFunction::CreateTempAlloca(mlir::Type Ty, - mlir::Location Loc, - const Twine &Name, - mlir::Value ArraySize, - bool insertIntoFnEntryBlock) { +cir::AllocaOp CIRGenFunction::CreateTempAlloca( + mlir::Type Ty, mlir::Location Loc, const Twine &Name, mlir::Value ArraySize, + bool insertIntoFnEntryBlock, bool isTemporary) { return emitAlloca(Name.str(), Ty, Loc, CharUnits(), insertIntoFnEntryBlock, - ArraySize) + ArraySize, isTemporary) .getDefiningOp(); } /// This creates an alloca and inserts it into the provided insertion point -cir::AllocaOp CIRGenFunction::CreateTempAlloca(mlir::Type Ty, - mlir::Location Loc, - const Twine &Name, - mlir::OpBuilder::InsertPoint ip, - mlir::Value ArraySize) { +cir::AllocaOp CIRGenFunction::CreateTempAlloca( + mlir::Type Ty, mlir::Location Loc, const Twine &Name, + mlir::OpBuilder::InsertPoint ip, mlir::Value ArraySize, bool isTemporary) { assert(ip.isSet() && "Insertion point is not set"); - return emitAlloca(Name.str(), Ty, Loc, CharUnits(), ip, ArraySize) + return emitAlloca(Name.str(), Ty, Loc, CharUnits(), ip, ArraySize, + isTemporary) .getDefiningOp(); } /// Just like CreateTempAlloca above, but place the alloca into the function /// entry basic block instead. cir::AllocaOp CIRGenFunction::CreateTempAllocaInFnEntryBlock( - mlir::Type Ty, mlir::Location Loc, const Twine &Name, - mlir::Value ArraySize) { + mlir::Type Ty, mlir::Location Loc, const Twine &Name, mlir::Value ArraySize, + bool isTemporary) { return CreateTempAlloca(Ty, Loc, Name, ArraySize, - /*insertIntoFnEntryBlock=*/true); + /*insertIntoFnEntryBlock=*/true, isTemporary); } /// Given an object of the given canonical type, can we safely copy a diff --git a/clang/lib/CIR/CodeGen/CIRGenExprAgg.cpp b/clang/lib/CIR/CodeGen/CIRGenExprAgg.cpp index bd6802a8f523..d67cf2c5c344 100644 --- a/clang/lib/CIR/CodeGen/CIRGenExprAgg.cpp +++ b/clang/lib/CIR/CodeGen/CIRGenExprAgg.cpp @@ -115,13 +115,13 @@ class AggExprEmitter : public StmtVisitor { AggValueSlot EnsureSlot(mlir::Location loc, QualType T) { if (!Dest.isIgnored()) return Dest; - return CGF.CreateAggTemp(T, loc, "agg.tmp.ensured"); + return CGF.CreateAggTempWithName(T, loc, "agg.tmp.ensured"); } void EnsureDest(mlir::Location loc, QualType T) { if (!Dest.isIgnored()) return; - Dest = CGF.CreateAggTemp(T, loc, "agg.tmp.ensured"); + Dest = CGF.CreateAggTempWithName(T, loc, "agg.tmp.ensured"); } public: @@ -1168,8 +1168,8 @@ void AggExprEmitter::withReturnValueSlot( if (!UseTemp) { RetAddr = Dest.getAddress(); } else { - RetAddr = CGF.CreateMemTemp(RetTy, CGF.getLoc(E->getSourceRange()), "tmp", - &RetAddr); + RetAddr = CGF.CreateMemTempWithName(RetTy, CGF.getLoc(E->getSourceRange()), + "tmp", &RetAddr); assert(!cir::MissingFeatures::shouldEmitLifetimeMarkers() && "NYI"); } @@ -1798,7 +1798,8 @@ CIRGenFunction::getOverlapForFieldInit(const FieldDecl *FD) { LValue CIRGenFunction::emitAggExprToLValue(const Expr *E) { assert(hasAggregateEvaluationKind(E->getType()) && "Invalid argument!"); - Address Temp = CreateMemTemp(E->getType(), getLoc(E->getSourceRange())); + Address Temp = + CreateMemTempWithName(E->getType(), getLoc(E->getSourceRange())); LValue LV = makeAddrLValue(Temp, E->getType()); emitAggExpr(E, AggValueSlot::forLValue(LV, AggValueSlot::IsNotDestructed, AggValueSlot::DoesNotNeedGCBarriers, diff --git a/clang/lib/CIR/CodeGen/CIRGenFunction.cpp b/clang/lib/CIR/CodeGen/CIRGenFunction.cpp index 825d3052b1f8..40b69a7135aa 100644 --- a/clang/lib/CIR/CodeGen/CIRGenFunction.cpp +++ b/clang/lib/CIR/CodeGen/CIRGenFunction.cpp @@ -276,7 +276,8 @@ void CIRGenFunction::emitAndUpdateRetAlloca(QualType ty, mlir::Location loc, ++NumReturnExprs; } else { Address allocaAddr = Address::invalid(); - ReturnValue = CreateMemTemp(ty, alignment, loc, "__retval", &allocaAddr); + ReturnValue = + CreateMemTempWithName(ty, alignment, loc, "__retval", &allocaAddr); FnRetAlloca = allocaAddr.getPointer(); // Tell the epilog emitter to autorelease the result. We do this now so @@ -296,8 +297,8 @@ mlir::LogicalResult CIRGenFunction::declare(const Decl *var, QualType ty, assert(!symbolTable.count(var) && "not supposed to be available just yet"); Address allocaAddr = Address::invalid(); - Address result = - CreateMemTemp(ty, alignment, loc, namedVar->getName(), &allocaAddr); + Address result = CreateMemTempWithName(ty, alignment, loc, + namedVar->getName(), &allocaAddr); addr = result.getPointer(); if (auto allocaOp = result.getAllocaOp()) { diff --git a/clang/lib/CIR/CodeGen/CIRGenFunction.h b/clang/lib/CIR/CodeGen/CIRGenFunction.h index 557a90518e98..35e508b880aa 100644 --- a/clang/lib/CIR/CodeGen/CIRGenFunction.h +++ b/clang/lib/CIR/CodeGen/CIRGenFunction.h @@ -1762,15 +1762,18 @@ class CIRGenFunction : public CIRGenTypeCache { mlir::Value emitAlloca(llvm::StringRef name, clang::QualType ty, mlir::Location loc, clang::CharUnits alignment, bool insertIntoFnEntryBlock = false, - mlir::Value arraySize = nullptr); + mlir::Value arraySize = nullptr, + bool isTemporary = false); mlir::Value emitAlloca(llvm::StringRef name, mlir::Type ty, mlir::Location loc, clang::CharUnits alignment, bool insertIntoFnEntryBlock = false, - mlir::Value arraySize = nullptr); + mlir::Value arraySize = nullptr, + bool isTemporary = false); mlir::Value emitAlloca(llvm::StringRef name, mlir::Type ty, mlir::Location loc, clang::CharUnits alignment, mlir::OpBuilder::InsertPoint ip, - mlir::Value arraySize = nullptr); + mlir::Value arraySize = nullptr, + bool isTemporary = false); /// Emit code to compute the specified expression which can have any type. The /// result is returned as an RValue struct. If this is an aggregate @@ -2589,22 +2592,23 @@ class CIRGenFunction : public CIRGenTypeCache { cir::AllocaOp CreateTempAlloca(mlir::Type Ty, mlir::Location Loc, const Twine &Name = "tmp", mlir::Value ArraySize = nullptr, - bool insertIntoFnEntryBlock = false); + bool insertIntoFnEntryBlock = false, + bool isTemporary = false); cir::AllocaOp CreateTempAllocaInFnEntryBlock(mlir::Type Ty, mlir::Location Loc, const Twine &Name = "tmp", - mlir::Value ArraySize = nullptr); + mlir::Value ArraySize = nullptr, + bool isTemporary = false); cir::AllocaOp CreateTempAlloca(mlir::Type Ty, mlir::Location Loc, const Twine &Name = "tmp", mlir::OpBuilder::InsertPoint ip = {}, - mlir::Value ArraySize = nullptr); - Address CreateTempAlloca(mlir::Type Ty, - mlir::ptr::MemorySpaceAttrInterface destAS, - CharUnits align, mlir::Location Loc, - const Twine &Name = "tmp", - mlir::Value ArraySize = nullptr, - Address *Alloca = nullptr, - mlir::OpBuilder::InsertPoint ip = {}); + mlir::Value ArraySize = nullptr, + bool isTemporary = false); + Address CreateTempAlloca( + mlir::Type Ty, mlir::ptr::MemorySpaceAttrInterface destAS, + CharUnits align, mlir::Location Loc, const Twine &Name = "tmp", + mlir::Value ArraySize = nullptr, Address *Alloca = nullptr, + mlir::OpBuilder::InsertPoint ip = {}, bool isTemporary = false); /// CreateTempAlloca - This creates a alloca and inserts it into the entry /// block. The alloca is casted to default address space if necessary. @@ -2615,13 +2619,15 @@ class CIRGenFunction : public CIRGenTypeCache { const Twine &Name = "tmp", mlir::Value ArraySize = nullptr, Address *Alloca = nullptr, - mlir::OpBuilder::InsertPoint ip = {}); + mlir::OpBuilder::InsertPoint ip = {}, + bool isTemporary = false); Address CreateTempAllocaWithoutCast(mlir::Type Ty, CharUnits align, mlir::Location Loc, const Twine &Name = "tmp", mlir::Value ArraySize = nullptr, - mlir::OpBuilder::InsertPoint ip = {}); + mlir::OpBuilder::InsertPoint ip = {}, + bool isTemporary = false); /// If \p alloca is not in the destination address space, insert an address /// space cast. The returned Address will have the destination address space @@ -2632,33 +2638,48 @@ class CIRGenFunction : public CIRGenTypeCache { Address alloca, mlir::ptr::MemorySpaceAttrInterface destLangAS = {}, mlir::Value arraySize = {}); - /// Create a temporary memory object of the given type, with - /// appropriate alignmen and cast it to the default address space. Returns - /// the original alloca instruction by \p Alloca if it is not nullptr. - Address CreateMemTemp(QualType T, mlir::Location Loc, - const Twine &Name = "tmp", Address *Alloca = nullptr, - mlir::OpBuilder::InsertPoint ip = {}); - Address CreateMemTemp(QualType T, CharUnits Align, mlir::Location Loc, - const Twine &Name = "tmp", Address *Alloca = nullptr, - mlir::OpBuilder::InsertPoint ip = {}); - - /// Create a temporary memory object of the given type, with - /// appropriate alignment without casting it to the default address space. + /// Create a temporary memory object with an explicit name, cast to the + /// default address space. Returns the original alloca via \p Alloca. + Address CreateMemTempWithName(QualType T, mlir::Location Loc, + const Twine &Name = "tmp", + Address *Alloca = nullptr, + mlir::OpBuilder::InsertPoint ip = {}, + bool isTemporary = false); + Address CreateMemTempWithName(QualType T, CharUnits Align, mlir::Location Loc, + const Twine &Name = "tmp", + Address *Alloca = nullptr, + mlir::OpBuilder::InsertPoint ip = {}, + bool isTemporary = false); + + /// Create compiler-generated temporaries with auto-named ref.tmp*/agg.tmp*. + Address CreateRefTempWithAutoName(QualType T, mlir::Location Loc, + Address *Alloca = nullptr, + mlir::OpBuilder::InsertPoint ip = {}); + Address + CreateAggTempAddressWithAutoName(QualType T, mlir::Location Loc, + Address *Alloca = nullptr, + mlir::OpBuilder::InsertPoint ip = {}); + AggValueSlot CreateAggTempWithAutoName(QualType T, mlir::Location Loc, + Address *Alloca = nullptr); + + /// Create a temporary memory object with an explicit name, without casting + /// it to the default address space. Address CreateMemTempWithoutCast(QualType T, mlir::Location Loc, const Twine &Name = "tmp"); Address CreateMemTempWithoutCast(QualType T, CharUnits Align, mlir::Location Loc, const Twine &Name = "tmp"); - /// Create a temporary memory object for the given - /// aggregate type. - AggValueSlot CreateAggTemp(QualType T, mlir::Location Loc, - const Twine &Name = "tmp", - Address *Alloca = nullptr) { + /// Create an aggregate temporary slot with an explicit name. + AggValueSlot CreateAggTempWithName(QualType T, mlir::Location Loc, + const Twine &Name = "tmp", + Address *Alloca = nullptr) { return AggValueSlot::forAddr( - CreateMemTemp(T, Loc, Name, Alloca), T.getQualifiers(), - AggValueSlot::IsNotDestructed, AggValueSlot::DoesNotNeedGCBarriers, - AggValueSlot::IsNotAliased, AggValueSlot::DoesNotOverlap); + CreateMemTempWithName(T, Loc, Name, Alloca, /*ip=*/{}, + /*isTemporary=*/true), + T.getQualifiers(), AggValueSlot::IsNotDestructed, + AggValueSlot::DoesNotNeedGCBarriers, AggValueSlot::IsNotAliased, + AggValueSlot::DoesNotOverlap); } private: diff --git a/clang/lib/CIR/CodeGen/CIRGenStmt.cpp b/clang/lib/CIR/CodeGen/CIRGenStmt.cpp index 6d765ee7cc35..1afdfb5046b1 100644 --- a/clang/lib/CIR/CodeGen/CIRGenStmt.cpp +++ b/clang/lib/CIR/CodeGen/CIRGenStmt.cpp @@ -52,7 +52,7 @@ Address CIRGenFunction::emitCompoundStmtWithoutScope(const CompoundStmt &S, // We can't return an RValue here because there might be cleanups at // the end of the StmtExpr. Because of that, we have to emit the result // here into a temporary alloca. - retAlloca = CreateMemTemp(exprTy, getLoc(E->getSourceRange())); + retAlloca = CreateMemTempWithName(exprTy, getLoc(E->getSourceRange())); emitAnyExprToMem(E, retAlloca, Qualifiers(), /*IsInit*/ false); } diff --git a/clang/lib/CIR/Dialect/IR/CIRDialect.cpp b/clang/lib/CIR/Dialect/IR/CIRDialect.cpp index b7bbc009c664..9020cb78d00a 100644 --- a/clang/lib/CIR/Dialect/IR/CIRDialect.cpp +++ b/clang/lib/CIR/Dialect/IR/CIRDialect.cpp @@ -355,6 +355,88 @@ void printGlobalAddressSpaceValue(mlir::AsmPrinter &printer, cir::GlobalOp op, // AllocaOp //===----------------------------------------------------------------------===// +// Custom parser/printer to allow flags in any order (tmp/init/const) and +// support single-flag spellings that the compact format can't represent. +static mlir::ParseResult parseAllocaNameAndFlags(mlir::OpAsmParser &parser, + mlir::StringAttr &nameAttr, + mlir::UnitAttr &initAttr, + mlir::UnitAttr &constAttr, + mlir::UnitAttr &tmpAttr) { + if (parser.parseLSquare()) + return mlir::failure(); + if (parser.parseAttribute(nameAttr)) + return mlir::failure(); + + auto setAttr = [&](llvm::StringRef keyword) -> mlir::ParseResult { + if (keyword == "tmp") { + if (tmpAttr) + return parser.emitError(parser.getCurrentLocation(), + "duplicate 'tmp' flag"); + tmpAttr = parser.getBuilder().getUnitAttr(); + return mlir::success(); + } + if (keyword == "init") { + if (initAttr) + return parser.emitError(parser.getCurrentLocation(), + "duplicate 'init' flag"); + initAttr = parser.getBuilder().getUnitAttr(); + return mlir::success(); + } + if (keyword == "const") { + if (constAttr) + return parser.emitError(parser.getCurrentLocation(), + "duplicate 'const' flag"); + constAttr = parser.getBuilder().getUnitAttr(); + return mlir::success(); + } + return parser.emitError(parser.getCurrentLocation(), + "expected one of: tmp, init, const"); + }; + + if (succeeded(parser.parseOptionalComma())) { + while (true) { + llvm::StringRef keyword; + if (parser.parseKeyword(&keyword)) + return mlir::failure(); + if (failed(setAttr(keyword))) + return mlir::failure(); + if (parser.parseOptionalComma().failed()) + break; + } + } + + if (parser.parseRSquare()) + return mlir::failure(); + return mlir::success(); +} + +static void printAllocaNameAndFlags(mlir::OpAsmPrinter &printer, + cir::AllocaOp op, mlir::StringAttr nameAttr, + mlir::UnitAttr initAttr, + mlir::UnitAttr constAttr, + mlir::UnitAttr tmpAttr) { + printer << "["; + printer.printAttribute(nameAttr); + + if (tmpAttr || initAttr || constAttr) { + printer << ", "; + bool printed = false; + auto printFlag = [&](llvm::StringRef name, mlir::UnitAttr attr) { + if (!attr) + return; + printer << (printed ? ", " : ""); + printer << name; + printed = true; + }; + + printFlag("tmp", tmpAttr); + printFlag("init", initAttr); + printFlag("const", constAttr); + } + + printer << "]"; +} + void cir::AllocaOp::build(::mlir::OpBuilder &odsBuilder, ::mlir::OperationState &odsState, ::mlir::Type addr, ::mlir::Type allocaType, ::llvm::StringRef name, diff --git a/clang/lib/CIR/Dialect/Transforms/LifetimeCheck.cpp b/clang/lib/CIR/Dialect/Transforms/LifetimeCheck.cpp index 9f4716295358..e311a5cebc9f 100644 --- a/clang/lib/CIR/Dialect/Transforms/LifetimeCheck.cpp +++ b/clang/lib/CIR/Dialect/Transforms/LifetimeCheck.cpp @@ -980,12 +980,9 @@ bool LifetimeCheckPass::isSkippableTemporary(mlir::Value v) { if (!allocaOp) return false; - auto name = allocaOp.getName(); - // Temporaries have names starting with "ref.tmp" - // FIXME: "ref.tmp" naming is not reliable. Consider adding a unit attribute - // is_temporary to AllocaOp that is set by CIRGen to definitively mark - // temporaries. This would be more robust than string prefix matching. - if (!name.starts_with("ref.tmp")) + // Check if this allocation is marked as a temporary by CIRGen. + // Currently covers ref.tmp*/agg.tmp*; other scratch temps are not marked yet. + if (!allocaOp.getTmp()) return false; // Don't skip coroutine tasks - they need lifetime tracking even as @@ -2026,8 +2023,8 @@ void LifetimeCheckPass::checkForOwnerAndPointerArguments(CallOp callOp, ptrsToDeref.insert(arg); if (aggregates.count(arg)) { int memberIdx = 0; - auto sTy = - mlir::dyn_cast(mlir::cast(arg.getType()).getPointee()); + auto sTy = mlir::dyn_cast( + mlir::cast(arg.getType()).getPointee()); assert(sTy && "expected record type"); for (auto m : sTy.getMembers()) { auto ptrMemberAddr = aggregates[arg][memberIdx]; diff --git a/clang/test/CIR/CallConvLowering/x86_64/basic.cpp b/clang/test/CIR/CallConvLowering/x86_64/basic.cpp index 21e2cb483698..776c0a60b01f 100644 --- a/clang/test/CIR/CallConvLowering/x86_64/basic.cpp +++ b/clang/test/CIR/CallConvLowering/x86_64/basic.cpp @@ -103,8 +103,8 @@ struct S1 { // CHECK: %[[#V1:]] = cir.cast bitcast %[[#V0]] : !cir.ptr -> !cir.ptr // CHECK: cir.store{{.*}} %arg0, %[[#V1]] : !u64i, !cir.ptr // CHECK: %[[#V2:]] = cir.alloca !rec_S1, !cir.ptr, ["__retval"] {alignment = 4 : i64} -// CHECK: %[[#V3:]] = cir.alloca !rec_S1, !cir.ptr, ["agg.tmp0"] {alignment = 4 : i64} -// CHECK: %[[#V4:]] = cir.alloca !rec_S1, !cir.ptr, ["agg.tmp1"] {alignment = 4 : i64} +// CHECK: %[[#V3:]] = cir.alloca !rec_S1, !cir.ptr, ["agg.tmp0", tmp] {alignment = 4 : i64} +// CHECK: %[[#V4:]] = cir.alloca !rec_S1, !cir.ptr, ["agg.tmp1", tmp] {alignment = 4 : i64} S1 s1(S1 arg) { /// Cast argument and result of the function call to the expected types. @@ -148,8 +148,8 @@ struct S2 { // CHECK: cir.libc.memcpy %[[#F6]] bytes from %[[#F4]] to %[[#F5]] S2 s2(S2 arg) { // CHECK: %[[#F7:]] = cir.alloca !rec_S2, !cir.ptr, ["__retval"] {alignment = 4 : i64} - // CHECK: %[[#F8:]] = cir.alloca !rec_S2, !cir.ptr, ["agg.tmp0"] {alignment = 4 : i64} - // CHECK: %[[#F9:]] = cir.alloca !rec_S2, !cir.ptr, ["agg.tmp1"] {alignment = 4 : i64} + // CHECK: %[[#F8:]] = cir.alloca !rec_S2, !cir.ptr, ["agg.tmp0", tmp] {alignment = 4 : i64} + // CHECK: %[[#F9:]] = cir.alloca !rec_S2, !cir.ptr, ["agg.tmp1", tmp] {alignment = 4 : i64} // CHECK: %[[#F10:]] = cir.alloca !rec_anon_struct, !cir.ptr, ["tmp"] {alignment = 8 : i64} // CHECK: %[[#F11:]] = cir.alloca !rec_S2, !cir.ptr, ["tmp"] {alignment = 4 : i64} // CHECK: %[[#F12:]] = cir.alloca !rec_anon_struct, !cir.ptr, ["tmp"] {alignment = 8 : i64} diff --git a/clang/test/CIR/CodeGen/abstract-cond.c b/clang/test/CIR/CodeGen/abstract-cond.c index 3c2ef4b2d1ae..c6ab69ce3002 100644 --- a/clang/test/CIR/CodeGen/abstract-cond.c +++ b/clang/test/CIR/CodeGen/abstract-cond.c @@ -14,7 +14,7 @@ int f6(int a0, struct s6 a1, struct s6 a2) { // CIR: %[[A1:.*]] = cir.alloca !rec_s6, !cir.ptr, ["a1" // CIR: %[[A2:.*]] = cir.alloca !rec_s6, !cir.ptr, ["a2" // CIR: cir.scope { -// CIR: %[[TMP:.*]] = cir.alloca !rec_s6, !cir.ptr, ["ref.tmp0"] +// CIR: %[[TMP:.*]] = cir.alloca !rec_s6, !cir.ptr, ["ref.tmp0", tmp] // CIR: %[[LOAD_A0:.*]] = cir.load{{.*}} %[[A0]] : !cir.ptr, !s32i // CIR: %[[COND:.*]] = cir.cast int_to_bool %[[LOAD_A0]] : !s32i -> !cir.bool // CIR: cir.if %[[COND]] { diff --git a/clang/test/CIR/CodeGen/agg-init.cpp b/clang/test/CIR/CodeGen/agg-init.cpp index 577f67e73529..cca69ada2acd 100644 --- a/clang/test/CIR/CodeGen/agg-init.cpp +++ b/clang/test/CIR/CodeGen/agg-init.cpp @@ -17,7 +17,7 @@ typedef struct yep_ { void use() { yop{}; } // CHECK: cir.func {{.*}} @_Z3usev() -// CHECK: %0 = cir.alloca !rec_yep_, !cir.ptr, ["agg.tmp.ensured"] {alignment = 4 : i64} +// CHECK: %0 = cir.alloca !rec_yep_, !cir.ptr, ["agg.tmp.ensured", tmp] {alignment = 4 : i64} // CHECK: %1 = cir.get_member %0[0] {name = "Status"} : !cir.ptr -> !cir.ptr // CHECK: %2 = cir.const #cir.int<0> : !u32i // CHECK: cir.store{{.*}} %2, %1 : !u32i, !cir.ptr diff --git a/clang/test/CIR/CodeGen/assign-operator.cpp b/clang/test/CIR/CodeGen/assign-operator.cpp index c633556a9107..4f51d06762b3 100644 --- a/clang/test/CIR/CodeGen/assign-operator.cpp +++ b/clang/test/CIR/CodeGen/assign-operator.cpp @@ -83,7 +83,7 @@ int main() { // CHECK: %5 = cir.cast array_to_ptrdecay %4 : !cir.ptr> -> !cir.ptr // CHECK: cir.call @_ZN6StringC2EPKc(%3, %5) : (!cir.ptr, !cir.ptr) -> () // CHECK: cir.scope { -// CHECK: %6 = cir.alloca !rec_StringView, !cir.ptr, ["ref.tmp0"] {alignment = 8 : i64} +// CHECK: %6 = cir.alloca !rec_StringView, !cir.ptr, ["ref.tmp0", tmp] {alignment = 8 : i64} // CHECK: cir.call @_ZN10StringViewC2ERK6String(%6, %3) : (!cir.ptr, !cir.ptr) -> () // CHECK: %7 = cir.call @_ZN10StringViewaSEOS_(%1, %6) : (!cir.ptr, !cir.ptr) -> !cir.ptr // CHECK: } diff --git a/clang/test/CIR/CodeGen/cast.c b/clang/test/CIR/CodeGen/cast.c index 9839998f7db7..eb790ff46ef0 100644 --- a/clang/test/CIR/CodeGen/cast.c +++ b/clang/test/CIR/CodeGen/cast.c @@ -11,7 +11,7 @@ int cstyle_cast_lvalue(A a) { // CHECK: cir.func {{.*}} @cstyle_cast_lvalue(%arg0: !rec_A loc({{.*}})) // CHECK: [[ALLOC_A:%.*]] = cir.alloca !rec_A, !cir.ptr, ["a", init] {alignment = 4 : i64} // CHECK: [[ALLOC_RET:%.*]] = cir.alloca !s32i, !cir.ptr, ["__retval"] {alignment = 4 : i64} -// CHECK: [[REF_TMP:%.*]] = cir.alloca !rec_A, !cir.ptr, ["ref.tmp0"] {alignment = 4 : i64} +// CHECK: [[REF_TMP:%.*]] = cir.alloca !rec_A, !cir.ptr, ["ref.tmp0", tmp] {alignment = 4 : i64} // CHECK: cir.copy [[ALLOC_A]] to [[REF_TMP]] : !cir.ptr // CHECK: [[X_ADDR:%.*]] = cir.get_member [[REF_TMP]][0] {name = "x"} : !cir.ptr -> !cir.ptr // CHECK: [[X:%.*]] = cir.load{{.*}} [[X_ADDR]] : !cir.ptr, !s32i diff --git a/clang/test/CIR/CodeGen/compound-literal.c b/clang/test/CIR/CodeGen/compound-literal.c index 11f202d890a6..6e5a6223c5d3 100644 --- a/clang/test/CIR/CodeGen/compound-literal.c +++ b/clang/test/CIR/CodeGen/compound-literal.c @@ -77,7 +77,7 @@ void split_large_page(unsigned long addr, pgprot_t prot) // CIR: cir.store{{.*}} {{.*}}, %[[VAL_2]] : !u64i, !cir.ptr // CIR: cir.store{{.*}} {{.*}}, %[[VAL_3]] : !rec_pgprot_t, !cir.ptr // CIR: {{.*}} = cir.scope { -// CIR: %[[VAL_4:.*]] = cir.alloca !rec_pgprot_t, !cir.ptr, ["ref.tmp0"] {alignment = 8 : i64} loc(#loc64) +// CIR: %[[VAL_4:.*]] = cir.alloca !rec_pgprot_t, !cir.ptr, ["ref.tmp0", tmp] {alignment = 8 : i64} loc(#loc64) // CIR: %[[VAL_5:.*]] = cir.load{{.*}} %[[VAL_2]] : !cir.ptr, !u64i // CIR: %[[VAL_6:.*]] = cir.cast int_to_bool %[[VAL_5]] : !u64i -> !cir.bool // CIR: cir.if %[[VAL_6]] { diff --git a/clang/test/CIR/CodeGen/cond.cpp b/clang/test/CIR/CodeGen/cond.cpp index 660292b7e5fc..64c42952d431 100644 --- a/clang/test/CIR/CodeGen/cond.cpp +++ b/clang/test/CIR/CodeGen/cond.cpp @@ -21,7 +21,7 @@ min(const unsigned long& __a, const unsigned long& __b) { // CHECK: cir.store{{.*}} %arg0, %0 : !cir.ptr, !cir.ptr> // CHECK: cir.store{{.*}} %arg1, %1 : !cir.ptr, !cir.ptr> // CHECK: cir.scope { -// CHECK: %4 = cir.alloca !rec___less, !cir.ptr, ["ref.tmp0"] {alignment = 1 : i64} +// CHECK: %4 = cir.alloca !rec___less, !cir.ptr, ["ref.tmp0", tmp] {alignment = 1 : i64} // CHECK: %5 = cir.load %1 : !cir.ptr>, !cir.ptr // CHECK: %6 = cir.load %0 : !cir.ptr>, !cir.ptr // CHECK: %7 = cir.call @_ZNK6__lessclERKmS1_(%4, %5, %6) : (!cir.ptr, !cir.ptr, !cir.ptr) -> !cir.bool diff --git a/clang/test/CIR/CodeGen/conditional-cleanup.cpp b/clang/test/CIR/CodeGen/conditional-cleanup.cpp index 5235dc89159f..0094f4085b97 100644 --- a/clang/test/CIR/CodeGen/conditional-cleanup.cpp +++ b/clang/test/CIR/CodeGen/conditional-cleanup.cpp @@ -32,9 +32,9 @@ namespace test7 { // CIR-LABEL: _ZN5test74testEv // CIR: %[[RET_VAL:.*]] = cir.alloca !cir.ptr, !cir.ptr>, ["__retval"] {alignment = 8 : i64} // CIR: cir.scope { -// CIR: %[[TMP_A0:.*]] = cir.alloca ![[A]], !cir.ptr, ["ref.tmp0"] {alignment = 1 : i64} +// CIR: %[[TMP_A0:.*]] = cir.alloca ![[A]], !cir.ptr, ["ref.tmp0", tmp] {alignment = 1 : i64} // CIR: %[[CLEANUP_COND_OUTER:.*]] = cir.alloca !cir.bool, !cir.ptr, ["cleanup.cond"] {alignment = 1 : i64} -// CIR: %[[TMP_A1:.*]] = cir.alloca ![[A]], !cir.ptr, ["ref.tmp1"] {alignment = 1 : i64} +// CIR: %[[TMP_A1:.*]] = cir.alloca ![[A]], !cir.ptr, ["ref.tmp1", tmp] {alignment = 1 : i64} // CIR: %[[CLEANUP_COND_INNER:.*]] = cir.alloca !cir.bool, !cir.ptr, ["cleanup.cond"] {alignment = 1 : i64} // CIR: %[[FALSE0:.*]] = cir.const #false // CIR: %[[TRUE0:.*]] = cir.const #true @@ -88,10 +88,10 @@ namespace test7 { // CIR_EH: %[[VAL_0:.*]] = cir.alloca !cir.ptr, !cir.ptr>, ["__retval"] {alignment = 8 : i64} // CIR_EH: cir.scope { // CIR_EH: %[[VAL_1:.*]] = cir.alloca !cir.bool, !cir.ptr, ["cleanup.cond"] {alignment = 1 : i64} -// CIR_EH: %[[VAL_2:.*]] = cir.alloca !rec_test73A3AA, !cir.ptr, ["ref.tmp0"] {alignment = 1 : i64} +// CIR_EH: %[[VAL_2:.*]] = cir.alloca !rec_test73A3AA, !cir.ptr, ["ref.tmp0", tmp] {alignment = 1 : i64} // CIR_EH: %[[VAL_3:.*]] = cir.alloca !cir.bool, !cir.ptr, ["cleanup.cond"] {alignment = 1 : i64} // CIR_EH: %[[VAL_4:.*]] = cir.alloca !cir.bool, !cir.ptr, ["cleanup.cond"] {alignment = 1 : i64} -// CIR_EH: %[[VAL_5:.*]] = cir.alloca !rec_test73A3AA, !cir.ptr, ["ref.tmp1"] {alignment = 1 : i64} +// CIR_EH: %[[VAL_5:.*]] = cir.alloca !rec_test73A3AA, !cir.ptr, ["ref.tmp1", tmp] {alignment = 1 : i64} // CIR_EH: %[[VAL_6:.*]] = cir.alloca !cir.bool, !cir.ptr, ["cleanup.cond"] {alignment = 1 : i64} // CIR_EH: %[[VAL_7:.*]] = cir.const #[[$ATTR_0]] // CIR_EH: %[[VAL_8:.*]] = cir.const #[[$ATTR_3]] diff --git a/clang/test/CIR/CodeGen/coro-task.cpp b/clang/test/CIR/CodeGen/coro-task.cpp index ec428a340450..6a9755970431 100644 --- a/clang/test/CIR/CodeGen/coro-task.cpp +++ b/clang/test/CIR/CodeGen/coro-task.cpp @@ -184,9 +184,9 @@ VoidTask silly_task() { // holding coroutine handle and the suspend_always struct. // CHECK: cir.scope { -// CHECK: %[[#SuspendAlwaysAddr:]] = cir.alloca ![[SuspendAlways]], {{.*}} ["ref.tmp0"] {alignment = 1 : i64} -// CHECK: %[[#CoroHandleVoidAddr:]] = cir.alloca ![[CoroHandleVoid]], {{.*}} ["agg.tmp0"] {alignment = 1 : i64} -// CHECK: %[[#CoroHandlePromiseAddr:]] = cir.alloca ![[CoroHandlePromise]], {{.*}} ["agg.tmp1"] {alignment = 1 : i64} +// CHECK: %[[#SuspendAlwaysAddr:]] = cir.alloca ![[SuspendAlways]], {{.*}} ["ref.tmp0", tmp] {alignment = 1 : i64} +// CHECK: %[[#CoroHandleVoidAddr:]] = cir.alloca ![[CoroHandleVoid]], {{.*}} ["agg.tmp0", tmp] {alignment = 1 : i64} +// CHECK: %[[#CoroHandlePromiseAddr:]] = cir.alloca ![[CoroHandlePromise]], {{.*}} ["agg.tmp1", tmp] {alignment = 1 : i64} // Effectively execute `coawait promise_type::initial_suspend()` by calling initial_suspend() and getting // the suspend_always struct to use for cir.await. Note that we return by-value since we defer ABI lowering @@ -314,7 +314,7 @@ folly::coro::Task go1() { // The call to go(1) has its own scope due to full-expression rules. // CHECK: cir.scope { -// CHECK: %[[#OneAddr:]] = cir.alloca !s32i, !cir.ptr, ["ref.tmp1", init] {alignment = 4 : i64} +// CHECK: %[[#OneAddr:]] = cir.alloca !s32i, !cir.ptr, ["ref.tmp1", tmp] {alignment = 4 : i64} // CHECK: %[[#One:]] = cir.const #cir.int<1> : !s32i // CHECK: cir.store{{.*}} %[[#One]], %[[#OneAddr]] : !s32i, !cir.ptr // CHECK: %[[#IntTaskTmp:]] = cir.call @_Z2goRKi(%[[#OneAddr]]) : (!cir.ptr) -> ![[IntTask]] @@ -356,7 +356,7 @@ folly::coro::Task go4() { // CHECK: } // CHECK: %12 = cir.scope { -// CHECK: %17 = cir.alloca !rec_anon2E2, !cir.ptr, ["ref.tmp1"] {alignment = 1 : i64} +// CHECK: %17 = cir.alloca !rec_anon2E2, !cir.ptr, ["ref.tmp1", tmp] {alignment = 1 : i64} // Get the lambda invoker ptr via `lambda operator folly::coro::Task (*)(int const&)()` // CHECK: %18 = cir.call @_ZZ3go4vENK3$_0cvPFN5folly4coro4TaskIiEERKiEEv(%17) : (!cir.ptr) -> !cir.ptr) -> ![[IntTask]]>> @@ -365,7 +365,7 @@ folly::coro::Task go4() { // CHECK: } // CHECK: cir.store{{.*}} %12, %3 : !cir.ptr) -> ![[IntTask]]>>, !cir.ptr) -> ![[IntTask]]>>> // CHECK: cir.scope { -// CHECK: %17 = cir.alloca !s32i, !cir.ptr, ["ref.tmp2", init] {alignment = 4 : i64} +// CHECK: %17 = cir.alloca !s32i, !cir.ptr, ["ref.tmp2", tmp] {alignment = 4 : i64} // CHECK: %18 = cir.load{{.*}} %3 : !cir.ptr) -> ![[IntTask]]>>>, !cir.ptr) -> ![[IntTask]]>> // CHECK: %19 = cir.const #cir.int<3> : !s32i // CHECK: cir.store{{.*}} %19, %17 : !s32i, !cir.ptr diff --git a/clang/test/CIR/CodeGen/derived-to-base.cpp b/clang/test/CIR/CodeGen/derived-to-base.cpp index d7b43e5b14d5..e411d9ee5b29 100644 --- a/clang/test/CIR/CodeGen/derived-to-base.cpp +++ b/clang/test/CIR/CodeGen/derived-to-base.cpp @@ -112,7 +112,7 @@ void vcall(C1 &c1) { // CHECK: %0 = cir.alloca !cir.ptr, !cir.ptr>, ["c1", init, const] {alignment = 8 : i64} // CHECK: %1 = cir.alloca !rec_buffy, !cir.ptr, ["b"] {alignment = 8 : i64} // CHECK: %2 = cir.alloca !s32i, !cir.ptr, ["e"] {alignment = 4 : i64} -// CHECK: %3 = cir.alloca !rec_buffy, !cir.ptr, ["agg.tmp0"] {alignment = 8 : i64} +// CHECK: %3 = cir.alloca !rec_buffy, !cir.ptr, ["agg.tmp0", tmp] {alignment = 8 : i64} // CHECK: cir.store %arg0, %0 : !cir.ptr, !cir.ptr> // CHECK: %4 = cir.load{{.*}} %0 : !cir.ptr>, !cir.ptr // CHECK: %5 = cir.load{{.*}} %2 : !cir.ptr, !s32i @@ -143,7 +143,7 @@ class B : public A { // CHECK: cir.store %arg0, %0 : !cir.ptr, !cir.ptr> // CHECK: %1 = cir.load{{.*}} deref %0 : !cir.ptr>, !cir.ptr // CHECK: cir.scope { -// CHECK: %2 = cir.alloca !rec_A, !cir.ptr, ["ref.tmp0"] {alignment = 8 : i64} +// CHECK: %2 = cir.alloca !rec_A, !cir.ptr, ["ref.tmp0", tmp] {alignment = 8 : i64} // CHECK: %3 = cir.base_class_addr %1 : !cir.ptr nonnull [0] -> !cir.ptr // Call @A::A(A const&) diff --git a/clang/test/CIR/CodeGen/dtors.cpp b/clang/test/CIR/CodeGen/dtors.cpp index 39c00110926d..785fffa704fe 100644 --- a/clang/test/CIR/CodeGen/dtors.cpp +++ b/clang/test/CIR/CodeGen/dtors.cpp @@ -66,7 +66,7 @@ bool bar() { return foo(1) || foo(2); } // CHECK: cir.func {{.*}} @_Z3barv() // CHECK: %[[V0:.*]] = cir.alloca !cir.bool, !cir.ptr, ["__retval"] {alignment = 1 : i64} // CHECK: cir.scope { -// CHECK: %[[V2:.*]] = cir.alloca !rec_X, !cir.ptr, ["ref.tmp0"] {alignment = 4 : i64} +// CHECK: %[[V2:.*]] = cir.alloca !rec_X, !cir.ptr, ["ref.tmp0", tmp] {alignment = 4 : i64} // CHECK: %[[V3:.*]] = cir.const #cir.int<1> : !s32i // CHECK: cir.call @_ZN1XC2Ei(%[[V2]], %[[V3]]) : (!cir.ptr, !s32i) -> () // CHECK: %[[V4:.*]] = cir.call @_Z3fooRK1X(%[[V2]]) : (!cir.ptr) -> !cir.bool @@ -74,7 +74,7 @@ bool bar() { return foo(1) || foo(2); } // CHECK: %[[V6:.*]] = cir.const #true // CHECK: cir.yield %[[V6]] : !cir.bool // CHECK: }, false { -// CHECK: %[[V6:.*]] = cir.alloca !rec_X, !cir.ptr, ["ref.tmp1"] {alignment = 4 : i64} +// CHECK: %[[V6:.*]] = cir.alloca !rec_X, !cir.ptr, ["ref.tmp1", tmp] {alignment = 4 : i64} // CHECK: %[[V7:.*]] = cir.const #cir.int<2> : !s32i // CHECK: cir.call @_ZN1XC2Ei(%[[V6]], %[[V7]]) : (!cir.ptr, !s32i) -> () // CHECK: %[[V8:.*]] = cir.call @_Z3fooRK1X(%[[V6]]) : (!cir.ptr) -> !cir.bool @@ -185,7 +185,7 @@ void m() { G l(j); } // CHECK: %[[V2:.*]] = cir.load{{.*}} %[[V0]] : !cir.ptr>, !cir.ptr // Trivial default constructor call is lowered away. // CHECK: %[[V3:.*]] = cir.scope { -// CHECK: %[[V4:.*]] = cir.alloca !rec_A2, !cir.ptr, ["agg.tmp0"] {alignment = 1 : i64} +// CHECK: %[[V4:.*]] = cir.alloca !rec_A2, !cir.ptr, ["agg.tmp0", tmp] {alignment = 1 : i64} // CHECK: %[[V5:.*]] = cir.load{{.*}} %[[V4]] : !cir.ptr, !rec_A2 // CHECK: %[[V6:.*]] = cir.call @_ZN1G1kE2A2(%[[V2]], %[[V5]]) : (!cir.ptr, !rec_A2) -> !s64i // CHECK: cir.call @_ZN2A2D1Ev(%[[V4]]) : (!cir.ptr) -> () diff --git a/clang/test/CIR/CodeGen/fullexpr.cpp b/clang/test/CIR/CodeGen/fullexpr.cpp index 128ad6a54aae..94022e264434 100644 --- a/clang/test/CIR/CodeGen/fullexpr.cpp +++ b/clang/test/CIR/CodeGen/fullexpr.cpp @@ -16,7 +16,7 @@ int go1() { // CHECK: cir.func {{.*}} @_Z3go1v() -> !s32i // CHECK: %[[#XAddr:]] = cir.alloca !s32i, !cir.ptr, ["x", init] {alignment = 4 : i64} // CHECK: %[[#RVal:]] = cir.scope { -// CHECK-NEXT: %[[#TmpAddr:]] = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", init] {alignment = 4 : i64} +// CHECK-NEXT: %[[#TmpAddr:]] = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", tmp] {alignment = 4 : i64} // CHECK-NEXT: %[[#One:]] = cir.const #cir.int<1> : !s32i // CHECK-NEXT: cir.store{{.*}} %[[#One]], %[[#TmpAddr]] : !s32i, !cir.ptr // CHECK-NEXT: %[[#RValTmp:]] = cir.call @_Z2goRKi(%[[#TmpAddr]]) : (!cir.ptr) -> !s32i @@ -25,7 +25,7 @@ int go1() { // CHECK-NEXT: cir.store{{.*}} %[[#RVal]], %[[#XAddr]] : !s32i, !cir.ptr // FLAT: cir.func {{.*}} @_Z3go1v() -> !s32i -// FLAT: %[[#TmpAddr:]] = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", init] {alignment = 4 : i64} +// FLAT: %[[#TmpAddr:]] = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", tmp] {alignment = 4 : i64} // FLAT: %[[#XAddr:]] = cir.alloca !s32i, !cir.ptr, ["x", init] {alignment = 4 : i64} // FLAT: cir.br ^[[before_body:.*]]{{ loc.*}} // FLAT-NEXT: ^[[before_body]]: // pred: ^bb0 diff --git a/clang/test/CIR/CodeGen/goto.cpp b/clang/test/CIR/CodeGen/goto.cpp index 1ed592b2d5f7..3eb22a8b3319 100644 --- a/clang/test/CIR/CodeGen/goto.cpp +++ b/clang/test/CIR/CodeGen/goto.cpp @@ -305,7 +305,7 @@ void foo() { // NOFLAT: cir.func {{.*}} @_Z3foov() // NOFLAT: cir.scope { -// NOFLAT: %0 = cir.alloca !rec_S, !cir.ptr, ["agg.tmp0"] +// NOFLAT: %0 = cir.alloca !rec_S, !cir.ptr, ["agg.tmp0", tmp] // NOFLAT: cir.br ^bb1 // NOFLAT: ^bb1: // NOFLAT: cir.label "label" diff --git a/clang/test/CIR/CodeGen/lambda.cpp b/clang/test/CIR/CodeGen/lambda.cpp index 35cfd054db34..c58713461cea 100644 --- a/clang/test/CIR/CodeGen/lambda.cpp +++ b/clang/test/CIR/CodeGen/lambda.cpp @@ -149,7 +149,7 @@ int f() { // CHECK-LABEL: @_Z1fv() // CHECK-NEXT: %0 = cir.alloca !s32i, !cir.ptr, ["__retval"] {alignment = 4 : i64} // CHECK-NEXT: cir.scope { -// CHECK-NEXT: %2 = cir.alloca !rec_anon2E4, !cir.ptr, ["ref.tmp0"] {alignment = 8 : i64} +// CHECK-NEXT: %2 = cir.alloca !rec_anon2E4, !cir.ptr, ["ref.tmp0", tmp] {alignment = 8 : i64} // CHECK-NEXT: %3 = cir.call @_Z2g2v() : () -> !rec_anon2E4 // CHECK-NEXT: cir.store{{.*}} %3, %2 : !rec_anon2E4, !cir.ptr // CHECK-NEXT: %4 = cir.call @_ZZ2g2vENK3$_0clEv(%2) : (!cir.ptr) -> !s32i @@ -212,7 +212,7 @@ int g3() { // 1. Use `operator int (*)(int const&)()` to retrieve the fnptr to `__invoke()`. // CHECK: %3 = cir.scope { -// CHECK: %7 = cir.alloca !rec_anon2E5, !cir.ptr, ["ref.tmp0"] {alignment = 1 : i64} +// CHECK: %7 = cir.alloca !rec_anon2E5, !cir.ptr, ["ref.tmp0", tmp] {alignment = 1 : i64} // CHECK: %8 = cir.call @_ZZ2g3vENK3$_0cvPFiRKiEEv(%7) : (!cir.ptr) -> !cir.ptr) -> !s32i>> // CHECK: %9 = cir.unary(plus, %8) : !cir.ptr) -> !s32i>>, !cir.ptr) -> !s32i>> // CHECK: cir.yield %9 : !cir.ptr) -> !s32i>> @@ -221,7 +221,7 @@ int g3() { // 2. Load ptr to `__invoke()`. // CHECK: cir.store{{.*}} %3, %1 : !cir.ptr) -> !s32i>>, !cir.ptr) -> !s32i>>> // CHECK: %4 = cir.scope { -// CHECK: %7 = cir.alloca !s32i, !cir.ptr, ["ref.tmp1", init] {alignment = 4 : i64} +// CHECK: %7 = cir.alloca !s32i, !cir.ptr, ["ref.tmp1", tmp] {alignment = 4 : i64} // CHECK: %8 = cir.load{{.*}} %1 : !cir.ptr) -> !s32i>>>, !cir.ptr) -> !s32i>> // CHECK: %9 = cir.const #cir.int<3> : !s32i // CHECK: cir.store{{.*}} %9, %7 : !s32i, !cir.ptr @@ -327,7 +327,7 @@ struct A { // A::foo() // CHECK-LABEL: @_ZN1A3fooEv -// CHECK: [[THIS_ARG:%.*]] = cir.alloca !rec_anon2E7, !cir.ptr, ["ref.tmp0"] {alignment = 4 : i64} +// CHECK: [[THIS_ARG:%.*]] = cir.alloca !rec_anon2E7, !cir.ptr, ["ref.tmp0", tmp] {alignment = 4 : i64} // CHECK: cir.call @_ZZN1A3fooEvENKUlvE_clEv([[THIS_ARG]]) : (!cir.ptr) -> !s32i // LLVM-LABEL: _ZN1A3fooEv @@ -365,7 +365,7 @@ struct A { // A::bar() // CHECK-LABEL: _ZN1A3barEv -// CHECK: [[THIS_ARG:%.*]] = cir.alloca !rec_anon2E8, !cir.ptr, ["ref.tmp0"] {alignment = 8 : i64} +// CHECK: [[THIS_ARG:%.*]] = cir.alloca !rec_anon2E8, !cir.ptr, ["ref.tmp0", tmp] {alignment = 8 : i64} // CHECK: cir.call @_ZZN1A3barEvENKUlvE_clEv([[THIS_ARG]]) // LLVM-LABEL: _ZN1A3barEv diff --git a/clang/test/CIR/CodeGen/materialize-temporary.cpp b/clang/test/CIR/CodeGen/materialize-temporary.cpp index 5aac04c32a7e..edd6ba54a014 100644 --- a/clang/test/CIR/CodeGen/materialize-temporary.cpp +++ b/clang/test/CIR/CodeGen/materialize-temporary.cpp @@ -7,7 +7,7 @@ int get_value() { return 42; } void test_const_ref_binding() { // CHECK-LABEL: cir.func{{.*}} @{{.*}}test_const_ref_bindingv const int &x = 5; - // CHECK: %{{.*}} = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", init] + // CHECK: %{{.*}} = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", tmp] // CHECK: %{{.*}} = cir.alloca !cir.ptr, !cir.ptr>, ["x", init, const] // CHECK: cir.scope { // CHECK: %{{.*}} = cir.const #cir.int<5> : !s32i @@ -18,7 +18,7 @@ void test_const_ref_binding() { void test_const_ref_expr() { // CHECK-LABEL: cir.func{{.*}} @{{.*}}test_const_ref_exprv const int &y = get_value(); - // CHECK: %{{.*}} = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", init] + // CHECK: %{{.*}} = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", tmp] // CHECK: %{{.*}} = cir.alloca !cir.ptr, !cir.ptr>, ["y", init, const] // CHECK: cir.scope { // CHECK: %{{.*}} = cir.call @{{.*}}get_valuev() @@ -29,7 +29,8 @@ void test_const_ref_arithmetic() { // CHECK-LABEL: cir.func{{.*}} @{{.*}}test_const_ref_arithmeticv int a = 10; const int &z = a + 5; - // CHECK: %{{.*}} = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", init] + // CHECK: %{{.*}} = cir.alloca !s32i, !cir.ptr, ["a", init] + // CHECK: %{{.*}} = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", tmp] // CHECK: %{{.*}} = cir.alloca !cir.ptr, !cir.ptr>, ["z", init, const] // CHECK: cir.scope { // CHECK: %{{.*}} = cir.load {{.*}} %{{.*}} @@ -49,6 +50,6 @@ void test_const_ref_struct() { // CHECK-LABEL: cir.func{{.*}} @{{.*}}test_const_ref_structv const S &s = make_s(); // Temporary S object should be materialized - // CHECK: %{{.*}} = cir.alloca {{.*}}, !cir.ptr<{{.*}}rec_S{{.*}}>, ["ref.tmp0"] + // CHECK: %{{.*}} = cir.alloca {{.*}}, !cir.ptr<{{.*}}rec_S{{.*}}>, ["ref.tmp0", tmp] // CHECK: %{{.*}} = cir.alloca !cir.ptr<{{.*}}>, !cir.ptr>, ["s", init, const] } diff --git a/clang/test/CIR/CodeGen/move.cpp b/clang/test/CIR/CodeGen/move.cpp index 074a3fa54f00..3e3a3e82169b 100644 --- a/clang/test/CIR/CodeGen/move.cpp +++ b/clang/test/CIR/CodeGen/move.cpp @@ -29,7 +29,7 @@ void t() { // be useful at least for the lifetime checker. // CHECK: cir.func {{.*}} @_Z1tv() -// CHECK: %[[#Addr:]] = cir.alloca ![[StdString]], {{.*}} ["ref.tmp0"] +// CHECK: %[[#Addr:]] = cir.alloca ![[StdString]], {{.*}} ["ref.tmp0", tmp] // CHECK: %[[#RValStr:]] = cir.call @_Z6getstrv() : () -> ![[StdString]] // CHECK: cir.store{{.*}} %[[#RValStr]], %[[#Addr]] // CHECK: cir.call @_Z7emplaceOSt6string(%[[#Addr]]) diff --git a/clang/test/CIR/CodeGen/nrvo-eh.cpp b/clang/test/CIR/CodeGen/nrvo-eh.cpp index 214f5a086cf3..bb8f4f47a639 100644 --- a/clang/test/CIR/CodeGen/nrvo-eh.cpp +++ b/clang/test/CIR/CodeGen/nrvo-eh.cpp @@ -22,7 +22,7 @@ std::vector test_nrvo() { // CIR: cir.store{{.*}} %[[FALSE]], %[[NRVO_FLAG]] : !cir.bool, !cir.ptr // CIR: cir.call @_ZNSt6vectorIPKcEC1Ev(%[[RESULT]]) : (!cir.ptr) -> () // CIR: cir.scope { -// CIR: %[[REF_TMP:.*]] = cir.alloca !cir.ptr, !cir.ptr>, ["ref.tmp0"] +// CIR: %[[REF_TMP:.*]] = cir.alloca !cir.ptr, !cir.ptr>, ["ref.tmp0", tmp] // CIR: %[[STR:.*]] = cir.get_global @".str" : !cir.ptr> // CIR: %[[PTR_DECAY:.*]] = cir.cast array_to_ptrdecay %[[STR]] : !cir.ptr> -> !cir.ptr // CIR: cir.store{{.*}} %[[PTR_DECAY]], %[[REF_TMP]] : !cir.ptr, !cir.ptr> diff --git a/clang/test/CIR/CodeGen/nrvo.cpp b/clang/test/CIR/CodeGen/nrvo.cpp index 0e8bb76062f3..27dfe4a97f27 100644 --- a/clang/test/CIR/CodeGen/nrvo.cpp +++ b/clang/test/CIR/CodeGen/nrvo.cpp @@ -22,7 +22,7 @@ std::vector test_nrvo() { // CIR: cir.store{{.*}} %[[FALSE]], %[[NRVO_FLAG]] : !cir.bool, !cir.ptr // CIR: cir.call @_ZNSt6vectorIPKcEC1Ev(%[[RESULT]]) : (!cir.ptr) -> () // CIR: cir.scope { -// CIR: %[[REF_TMP:.*]] = cir.alloca !cir.ptr, !cir.ptr>, ["ref.tmp0"] +// CIR: %[[REF_TMP:.*]] = cir.alloca !cir.ptr, !cir.ptr>, ["ref.tmp0", tmp] // CIR: %[[STR:.*]] = cir.get_global @".str" : !cir.ptr> // CIR: %[[PTR_DECAY:.*]] = cir.cast array_to_ptrdecay %[[STR]] : !cir.ptr> -> !cir.ptr // CIR: cir.store{{.*}} %[[PTR_DECAY]], %[[REF_TMP]] : !cir.ptr, !cir.ptr> diff --git a/clang/test/CIR/CodeGen/paren-list-init.cpp b/clang/test/CIR/CodeGen/paren-list-init.cpp index aa5bc1ca2f24..d4997e58c238 100644 --- a/clang/test/CIR/CodeGen/paren-list-init.cpp +++ b/clang/test/CIR/CodeGen/paren-list-init.cpp @@ -27,7 +27,7 @@ void make1() { // CIR: %[[VEC:.*]] = cir.alloca ![[VecType]], !cir.ptr // CIR: cir.call @_ZN3VecC1Ev(%[[VEC]]) : (!cir.ptr) // CIR: cir.scope { -// CIR: %[[AGG_TMP:.*]] = cir.alloca ![[S1]], !cir.ptr, ["agg.tmp.ensured"] +// CIR: %[[AGG_TMP:.*]] = cir.alloca ![[S1]], !cir.ptr, ["agg.tmp.ensured", tmp] // CIR: %[[FIELD:.*]] = cir.get_member %[[AGG_TMP]][0] {name = "v"} : !cir.ptr -> !cir.ptr // CIR: cir.call @_ZN3VecC1EOS_(%[[FIELD]], %[[VEC]]) : (!cir.ptr, !cir.ptr) -> () // CIR: cir.call @_ZN2S1D1Ev(%[[AGG_TMP]]) : (!cir.ptr) -> () @@ -41,7 +41,7 @@ void make1() { // Construct v // CIR_EH: cir.call @_ZN3VecC1Ev(%[[VEC]]) : (!cir.ptr) -> () // CIR_EH: cir.scope { -// CIR_EH: %1 = cir.alloca ![[S1]], !cir.ptr, ["agg.tmp.ensured"] +// CIR_EH: %1 = cir.alloca ![[S1]], !cir.ptr, ["agg.tmp.ensured", tmp] // CIR_EH: %2 = cir.get_member %1[0] {name = "v"} : !cir.ptr -> !cir.ptr // CIR_EH: cir.try synthetic cleanup { diff --git a/clang/test/CIR/CodeGen/rangefor.cpp b/clang/test/CIR/CodeGen/rangefor.cpp index 1ff8c7978f89..6509fbea8406 100644 --- a/clang/test/CIR/CodeGen/rangefor.cpp +++ b/clang/test/CIR/CodeGen/rangefor.cpp @@ -51,7 +51,7 @@ void init(unsigned numImages) { // CHECK: %12 = cir.call @_ZNK17__vector_iteratorI6triplePS0_RS0_EdeEv(%5) : (!cir.ptr) -> !cir.ptr // CHECK: cir.store{{.*}} %12, %7 : !cir.ptr, !cir.ptr> // CHECK: cir.scope { -// CHECK: %13 = cir.alloca !rec_triple, !cir.ptr, ["ref.tmp0"] {alignment = 8 : i64} +// CHECK: %13 = cir.alloca !rec_triple, !cir.ptr, ["ref.tmp0", tmp] {alignment = 8 : i64} // CHECK: %14 = cir.const #cir.zero : !rec_triple // CHECK: cir.store{{.*}} %14, %13 : !rec_triple, !cir.ptr // CHECK: %15 = cir.get_member %13[0] {name = "type"} : !cir.ptr -> !cir.ptr diff --git a/clang/test/CIR/CodeGen/stmt-expr.c b/clang/test/CIR/CodeGen/stmt-expr.c index cad7fc7eb1d6..4f8f34d3ab82 100644 --- a/clang/test/CIR/CodeGen/stmt-expr.c +++ b/clang/test/CIR/CodeGen/stmt-expr.c @@ -24,7 +24,7 @@ struct S { int x; }; int test3() { return ({ struct S s = {1}; s; }).x; } // CHECK: @test3 // CHECK: cir.scope { -// CHECK: %[[#REF_TMP:]] = cir.alloca !rec_S, !cir.ptr, ["ref.tmp0"] +// CHECK: %[[#REF_TMP:]] = cir.alloca !rec_S, !cir.ptr, ["ref.tmp0", tmp] // CHECK: cir.scope { // CHECK: %[[#VAR:]] = cir.alloca !rec_S, !cir.ptr // [...] diff --git a/clang/test/CIR/CodeGen/struct.cpp b/clang/test/CIR/CodeGen/struct.cpp index deb4d174c6fb..6310ce200abe 100644 --- a/clang/test/CIR/CodeGen/struct.cpp +++ b/clang/test/CIR/CodeGen/struct.cpp @@ -150,7 +150,7 @@ void h() { S s; } // CHECK: cir.func {{.*}} @_Z1hv() // CHECK: %0 = cir.alloca !rec_S, !cir.ptr, ["s", init] {alignment = 1 : i64} -// CHECK: %1 = cir.alloca !rec_A, !cir.ptr, ["agg.tmp0"] {alignment = 4 : i64} +// CHECK: %1 = cir.alloca !rec_A, !cir.ptr, ["agg.tmp0", tmp] {alignment = 4 : i64} // CHECK: %2 = cir.call @_Z11get_defaultv() : () -> !rec_A // CHECK: cir.store{{.*}} %2, %1 : !rec_A, !cir.ptr // CHECK: %3 = cir.load{{.*}} %1 : !cir.ptr, !rec_A diff --git a/clang/test/CIR/CodeGen/temporaries.cpp b/clang/test/CIR/CodeGen/temporaries.cpp index 1d147f085fda..c7c1fd5a70de 100644 --- a/clang/test/CIR/CodeGen/temporaries.cpp +++ b/clang/test/CIR/CodeGen/temporaries.cpp @@ -24,8 +24,8 @@ void f() { // Trivial default constructor call is lowered away. // CIR-NEXT: cir.func {{.*}} @_Z1fv() {{.*}} { // CIR-NEXT: cir.scope { -// CIR-NEXT: %[[ONE:[0-9]+]] = cir.alloca !rec_E, !cir.ptr, ["agg.tmp.ensured"] {alignment = 1 : i64} -// CIR-NEXT: %[[TWO:[0-9]+]] = cir.alloca !rec_E, !cir.ptr, ["ref.tmp0"] {alignment = 1 : i64} +// CIR-NEXT: %[[ONE:[0-9]+]] = cir.alloca !rec_E, !cir.ptr, ["agg.tmp.ensured", tmp] {alignment = 1 : i64} +// CIR-NEXT: %[[TWO:[0-9]+]] = cir.alloca !rec_E, !cir.ptr, ["ref.tmp0", tmp] {alignment = 1 : i64} // CIR-NEXT: %[[THREE:[0-9]+]] = cir.call @_ZN1EntEv(%[[TWO]]) : (!cir.ptr) -> !rec_E // CIR-NEXT: cir.store{{.*}} %[[THREE]], %[[ONE]] : !rec_E, !cir.ptr // CIR-NEXT: cir.call @_ZN1ED1Ev(%[[ONE]]) : (!cir.ptr) -> () extra(#fn_attr) @@ -35,7 +35,7 @@ void f() { // CIR-NEXT: } // CIR_EH-LABEL: @_Z1fv -// CIR_EH: %[[AGG_TMP:.*]] = cir.alloca {{.*}} ["agg.tmp.ensured"] +// CIR_EH: %[[AGG_TMP:.*]] = cir.alloca {{.*}} ["agg.tmp.ensured", tmp] // CIR_EH: cir.try synthetic cleanup { // CIR_EH: %[[RVAL:.*]] = cir.call exception {{.*}} cleanup { // CIR_EH: cir.call @_ZN1ED1Ev diff --git a/clang/test/CIR/CodeGen/temporary-materialization.cpp b/clang/test/CIR/CodeGen/temporary-materialization.cpp index 4a8f3208ade4..96c64a8da803 100644 --- a/clang/test/CIR/CodeGen/temporary-materialization.cpp +++ b/clang/test/CIR/CodeGen/temporary-materialization.cpp @@ -10,7 +10,7 @@ int test() { // CHECK: cir.func {{.*}} @_Z4testv() // CHECK-NEXT: %{{.+}} = cir.alloca !s32i, !cir.ptr, ["__retval"] {alignment = 4 : i64} -// CHECK-NEXT: %[[#TEMP_SLOT:]] = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", init] {alignment = 4 : i64} +// CHECK-NEXT: %[[#TEMP_SLOT:]] = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", tmp] {alignment = 4 : i64} // CHECK-NEXT: %[[#x:]] = cir.alloca !cir.ptr, !cir.ptr>, ["x", init, const] {alignment = 8 : i64} // CHECK-NEXT: cir.scope { // CHECK-NEXT: %[[#TEMP_VALUE:]] = cir.call @_Z8make_intv() : () -> !s32i @@ -32,7 +32,7 @@ int test_scoped() { // CHECK-NEXT: %{{.+}} = cir.alloca !s32i, !cir.ptr, ["__retval"] {alignment = 4 : i64} // CHECK-NEXT: %{{.+}} = cir.alloca !s32i, !cir.ptr, ["x", init] {alignment = 4 : i64} // CHECK: cir.scope { -// CHECK-NEXT: %[[#TEMP_SLOT:]] = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", init] {alignment = 4 : i64} +// CHECK-NEXT: %[[#TEMP_SLOT:]] = cir.alloca !s32i, !cir.ptr, ["ref.tmp0", tmp] {alignment = 4 : i64} // CHECK-NEXT: %[[#y:]] = cir.alloca !cir.ptr, !cir.ptr>, ["y", init, const] {alignment = 8 : i64} // CHECK-NEXT: cir.scope { // CHECK-NEXT: %[[#TEMP_VALUE:]] = cir.call @_Z8make_intv() : () -> !s32i diff --git a/clang/test/CIR/CodeGen/try-catch-dtors.cpp b/clang/test/CIR/CodeGen/try-catch-dtors.cpp index 44dc524d91a0..c0796d25517d 100644 --- a/clang/test/CIR/CodeGen/try-catch-dtors.cpp +++ b/clang/test/CIR/CodeGen/try-catch-dtors.cpp @@ -83,7 +83,7 @@ void yo2() { // CIR: cir.try { // CIR: cir.call exception @_ZN3VecC1Ev // CIR: cir.scope { -// CIR: cir.alloca ![[S1:.*]], !cir.ptr, ["agg.tmp.ensured"] +// CIR: cir.alloca ![[S1:.*]], !cir.ptr, ["agg.tmp.ensured", tmp] // CIR: cir.call exception @_ZN3VecC1EOS_{{.*}} cleanup { // CIR: cir.call @_ZN3VecD1Ev // CIR: cir.yield @@ -353,7 +353,7 @@ void d() { // CIR: %[[V0:.*]] = cir.alloca !rec_C, !cir.ptr, ["a"] {alignment = 1 : i64} // CIR-NEXT: %[[V1:.*]] = cir.alloca !rec_C, !cir.ptr, ["b"] {alignment = 1 : i64} // CIR-NEXT: cir.scope { -// CIR-NEXT: %[[V2:.*]] = cir.alloca !rec_C, !cir.ptr, ["agg.tmp0"] {alignment = 1 : i64} +// CIR-NEXT: %[[V2:.*]] = cir.alloca !rec_C, !cir.ptr, ["agg.tmp0", tmp] {alignment = 1 : i64} // CIR-NEXT: cir.copy %[[V1]] to %[[V2]] : !cir.ptr // CIR-NEXT: %[[V3:.*]] = cir.load{{.*}} %[[V2]] : !cir.ptr, !rec_C // CIR-NEXT: cir.try synthetic cleanup { diff --git a/clang/test/CIR/CodeGen/vtable-rtti.cpp b/clang/test/CIR/CodeGen/vtable-rtti.cpp index cb56a4c9c9ac..d2c41f8abcac 100644 --- a/clang/test/CIR/CodeGen/vtable-rtti.cpp +++ b/clang/test/CIR/CodeGen/vtable-rtti.cpp @@ -55,7 +55,7 @@ class B : public A // // CHECK: cir.func {{.*}} @_Z3foov() // CHECK: cir.scope { -// CHECK: %0 = cir.alloca !rec_B, !cir.ptr, ["agg.tmp.ensured"] {alignment = 8 : i64} +// CHECK: %0 = cir.alloca !rec_B, !cir.ptr, ["agg.tmp.ensured", tmp] {alignment = 8 : i64} // CHECK: %1 = cir.const #cir.zero : ![[ClassB]] // CHECK: cir.store{{.*}} %1, %0 : ![[ClassB]], !cir.ptr // CHECK: cir.call @_ZN1BC2Ev(%0) : (!cir.ptr) -> ()