Skip to content

Commit cfb6bfc

Browse files
authored
merge main into amd-staging (#354)
2 parents 83f7f2e + 53ce339 commit cfb6bfc

File tree

161 files changed

+4373
-1485
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

161 files changed

+4373
-1485
lines changed

clang/include/clang/Sema/Sema.h

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1321,15 +1321,11 @@ class Sema final : public SemaBase {
13211321

13221322
/// Callback to the parser to parse templated functions when needed.
13231323
typedef void LateTemplateParserCB(void *P, LateParsedTemplate &LPT);
1324-
typedef void LateTemplateParserCleanupCB(void *P);
13251324
LateTemplateParserCB *LateTemplateParser;
1326-
LateTemplateParserCleanupCB *LateTemplateParserCleanup;
13271325
void *OpaqueParser;
13281326

1329-
void SetLateTemplateParser(LateTemplateParserCB *LTP,
1330-
LateTemplateParserCleanupCB *LTPCleanup, void *P) {
1327+
void SetLateTemplateParser(LateTemplateParserCB *LTP, void *P) {
13311328
LateTemplateParser = LTP;
1332-
LateTemplateParserCleanup = LTPCleanup;
13331329
OpaqueParser = P;
13341330
}
13351331

clang/lib/Analysis/FlowSensitive/Models/UncheckedStatusOrAccessModel.cpp

Lines changed: 159 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -137,6 +137,37 @@ static auto valueOperatorCall() {
137137
isStatusOrOperatorCallWithName("->")));
138138
}
139139

140+
static clang::ast_matchers::TypeMatcher statusType() {
141+
using namespace ::clang::ast_matchers; // NOLINT: Too many names
142+
return hasCanonicalType(qualType(hasDeclaration(statusClass())));
143+
}
144+
145+
static auto isComparisonOperatorCall(llvm::StringRef operator_name) {
146+
using namespace ::clang::ast_matchers; // NOLINT: Too many names
147+
return cxxOperatorCallExpr(
148+
hasOverloadedOperatorName(operator_name), argumentCountIs(2),
149+
hasArgument(0, anyOf(hasType(statusType()), hasType(statusOrType()))),
150+
hasArgument(1, anyOf(hasType(statusType()), hasType(statusOrType()))));
151+
}
152+
153+
static auto isOkStatusCall() {
154+
using namespace ::clang::ast_matchers; // NOLINT: Too many names
155+
return callExpr(callee(functionDecl(hasName("::absl::OkStatus"))));
156+
}
157+
158+
static auto isNotOkStatusCall() {
159+
using namespace ::clang::ast_matchers; // NOLINT: Too many names
160+
return callExpr(callee(functionDecl(hasAnyName(
161+
"::absl::AbortedError", "::absl::AlreadyExistsError",
162+
"::absl::CancelledError", "::absl::DataLossError",
163+
"::absl::DeadlineExceededError", "::absl::FailedPreconditionError",
164+
"::absl::InternalError", "::absl::InvalidArgumentError",
165+
"::absl::NotFoundError", "::absl::OutOfRangeError",
166+
"::absl::PermissionDeniedError", "::absl::ResourceExhaustedError",
167+
"::absl::UnauthenticatedError", "::absl::UnavailableError",
168+
"::absl::UnimplementedError", "::absl::UnknownError"))));
169+
}
170+
140171
static auto
141172
buildDiagnoseMatchSwitch(const UncheckedStatusOrAccessModelOptions &Options) {
142173
return CFGMatchSwitchBuilder<const Environment,
@@ -312,6 +343,118 @@ static void transferStatusUpdateCall(const CXXMemberCallExpr *Expr,
312343
State.Env.setValue(locForOk(*ThisLoc), NewVal);
313344
}
314345

346+
static BoolValue *evaluateStatusEquality(RecordStorageLocation &LhsStatusLoc,
347+
RecordStorageLocation &RhsStatusLoc,
348+
Environment &Env) {
349+
auto &A = Env.arena();
350+
// Logically, a Status object is composed of an error code that could take one
351+
// of multiple possible values, including the "ok" value. We track whether a
352+
// Status object has an "ok" value and represent this as an `ok` bit. Equality
353+
// of Status objects compares their error codes. Therefore, merely comparing
354+
// the `ok` bits isn't sufficient: when two Status objects are assigned non-ok
355+
// error codes the equality of their respective error codes matters. Since we
356+
// only track the `ok` bits, we can't make any conclusions about equality when
357+
// we know that two Status objects have non-ok values.
358+
359+
auto &LhsOkVal = valForOk(LhsStatusLoc, Env);
360+
auto &RhsOkVal = valForOk(RhsStatusLoc, Env);
361+
362+
auto &Res = Env.makeAtomicBoolValue();
363+
364+
// lhs && rhs => res (a.k.a. !res => !lhs || !rhs)
365+
Env.assume(A.makeImplies(A.makeAnd(LhsOkVal.formula(), RhsOkVal.formula()),
366+
Res.formula()));
367+
// res => (lhs == rhs)
368+
Env.assume(A.makeImplies(
369+
Res.formula(), A.makeEquals(LhsOkVal.formula(), RhsOkVal.formula())));
370+
371+
return &Res;
372+
}
373+
374+
static BoolValue *
375+
evaluateStatusOrEquality(RecordStorageLocation &LhsStatusOrLoc,
376+
RecordStorageLocation &RhsStatusOrLoc,
377+
Environment &Env) {
378+
auto &A = Env.arena();
379+
// Logically, a StatusOr<T> object is composed of two values - a Status and a
380+
// value of type T. Equality of StatusOr objects compares both values.
381+
// Therefore, merely comparing the `ok` bits of the Status values isn't
382+
// sufficient. When two StatusOr objects are engaged, the equality of their
383+
// respective values of type T matters. Similarly, when two StatusOr objects
384+
// have Status values that have non-ok error codes, the equality of the error
385+
// codes matters. Since we only track the `ok` bits of the Status values, we
386+
// can't make any conclusions about equality when we know that two StatusOr
387+
// objects are engaged or when their Status values contain non-ok error codes.
388+
auto &LhsOkVal = valForOk(locForStatus(LhsStatusOrLoc), Env);
389+
auto &RhsOkVal = valForOk(locForStatus(RhsStatusOrLoc), Env);
390+
auto &res = Env.makeAtomicBoolValue();
391+
392+
// res => (lhs == rhs)
393+
Env.assume(A.makeImplies(
394+
res.formula(), A.makeEquals(LhsOkVal.formula(), RhsOkVal.formula())));
395+
return &res;
396+
}
397+
398+
static BoolValue *evaluateEquality(const Expr *LhsExpr, const Expr *RhsExpr,
399+
Environment &Env) {
400+
// Check the type of both sides in case an operator== is added that admits
401+
// different types.
402+
if (isStatusOrType(LhsExpr->getType()) &&
403+
isStatusOrType(RhsExpr->getType())) {
404+
auto *LhsStatusOrLoc = Env.get<RecordStorageLocation>(*LhsExpr);
405+
if (LhsStatusOrLoc == nullptr)
406+
return nullptr;
407+
auto *RhsStatusOrLoc = Env.get<RecordStorageLocation>(*RhsExpr);
408+
if (RhsStatusOrLoc == nullptr)
409+
return nullptr;
410+
411+
return evaluateStatusOrEquality(*LhsStatusOrLoc, *RhsStatusOrLoc, Env);
412+
}
413+
if (isStatusType(LhsExpr->getType()) && isStatusType(RhsExpr->getType())) {
414+
auto *LhsStatusLoc = Env.get<RecordStorageLocation>(*LhsExpr);
415+
if (LhsStatusLoc == nullptr)
416+
return nullptr;
417+
418+
auto *RhsStatusLoc = Env.get<RecordStorageLocation>(*RhsExpr);
419+
if (RhsStatusLoc == nullptr)
420+
return nullptr;
421+
422+
return evaluateStatusEquality(*LhsStatusLoc, *RhsStatusLoc, Env);
423+
}
424+
return nullptr;
425+
}
426+
427+
static void transferComparisonOperator(const CXXOperatorCallExpr *Expr,
428+
LatticeTransferState &State,
429+
bool IsNegative) {
430+
auto *LhsAndRhsVal =
431+
evaluateEquality(Expr->getArg(0), Expr->getArg(1), State.Env);
432+
if (LhsAndRhsVal == nullptr)
433+
return;
434+
435+
if (IsNegative)
436+
State.Env.setValue(*Expr, State.Env.makeNot(*LhsAndRhsVal));
437+
else
438+
State.Env.setValue(*Expr, *LhsAndRhsVal);
439+
}
440+
441+
static void transferOkStatusCall(const CallExpr *Expr,
442+
const MatchFinder::MatchResult &,
443+
LatticeTransferState &State) {
444+
auto &OkVal =
445+
initializeStatus(State.Env.getResultObjectLocation(*Expr), State.Env);
446+
State.Env.assume(OkVal.formula());
447+
}
448+
449+
static void transferNotOkStatusCall(const CallExpr *Expr,
450+
const MatchFinder::MatchResult &,
451+
LatticeTransferState &State) {
452+
auto &OkVal =
453+
initializeStatus(State.Env.getResultObjectLocation(*Expr), State.Env);
454+
auto &A = State.Env.arena();
455+
State.Env.assume(A.makeNot(OkVal.formula()));
456+
}
457+
315458
CFGMatchSwitch<LatticeTransferState>
316459
buildTransferMatchSwitch(ASTContext &Ctx,
317460
CFGMatchSwitchBuilder<LatticeTransferState> Builder) {
@@ -325,6 +468,22 @@ buildTransferMatchSwitch(ASTContext &Ctx,
325468
transferStatusOkCall)
326469
.CaseOfCFGStmt<CXXMemberCallExpr>(isStatusMemberCallWithName("Update"),
327470
transferStatusUpdateCall)
471+
.CaseOfCFGStmt<CXXOperatorCallExpr>(
472+
isComparisonOperatorCall("=="),
473+
[](const CXXOperatorCallExpr *Expr, const MatchFinder::MatchResult &,
474+
LatticeTransferState &State) {
475+
transferComparisonOperator(Expr, State,
476+
/*IsNegative=*/false);
477+
})
478+
.CaseOfCFGStmt<CXXOperatorCallExpr>(
479+
isComparisonOperatorCall("!="),
480+
[](const CXXOperatorCallExpr *Expr, const MatchFinder::MatchResult &,
481+
LatticeTransferState &State) {
482+
transferComparisonOperator(Expr, State,
483+
/*IsNegative=*/true);
484+
})
485+
.CaseOfCFGStmt<CallExpr>(isOkStatusCall(), transferOkStatusCall)
486+
.CaseOfCFGStmt<CallExpr>(isNotOkStatusCall(), transferNotOkStatusCall)
328487
.Build();
329488
}
330489

clang/lib/CIR/CodeGen/CIRGenAsm.cpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -117,9 +117,9 @@ mlir::LogicalResult CIRGenFunction::emitAsmStmt(const AsmStmt &s) {
117117

118118
bool hasSideEffect = s.isVolatile() || s.getNumOutputs() == 0;
119119

120-
cir::InlineAsmOp ia = builder.create<cir::InlineAsmOp>(
121-
getLoc(s.getAsmLoc()), resultType, operands, asmString, constraints,
122-
hasSideEffect, inferFlavor(cgm, s), mlir::ArrayAttr());
120+
cir::InlineAsmOp ia = cir::InlineAsmOp::create(
121+
builder, getLoc(s.getAsmLoc()), resultType, operands, asmString,
122+
constraints, hasSideEffect, inferFlavor(cgm, s), mlir::ArrayAttr());
123123

124124
if (isGCCAsmGoto) {
125125
assert(!cir::MissingFeatures::asmGoto());

clang/lib/CIR/CodeGen/CIRGenBuiltin.cpp

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -46,9 +46,9 @@ static RValue emitBuiltinBitOp(CIRGenFunction &cgf, const CallExpr *e,
4646
Op op;
4747
if constexpr (std::is_same_v<Op, cir::BitClzOp> ||
4848
std::is_same_v<Op, cir::BitCtzOp>)
49-
op = builder.create<Op>(cgf.getLoc(e->getSourceRange()), arg, poisonZero);
49+
op = Op::create(builder, cgf.getLoc(e->getSourceRange()), arg, poisonZero);
5050
else
51-
op = builder.create<Op>(cgf.getLoc(e->getSourceRange()), arg);
51+
op = Op::create(builder, cgf.getLoc(e->getSourceRange()), arg);
5252

5353
mlir::Value result = op.getResult();
5454
mlir::Type exprTy = cgf.convertType(e->getType());
@@ -67,8 +67,8 @@ RValue CIRGenFunction::emitRotate(const CallExpr *e, bool isRotateLeft) {
6767
// to the type of input when necessary.
6868
assert(!cir::MissingFeatures::msvcBuiltins());
6969

70-
auto r = builder.create<cir::RotateOp>(getLoc(e->getSourceRange()), input,
71-
amount, isRotateLeft);
70+
auto r = cir::RotateOp::create(builder, getLoc(e->getSourceRange()), input,
71+
amount, isRotateLeft);
7272
return RValue::get(r);
7373
}
7474

@@ -227,14 +227,14 @@ RValue CIRGenFunction::emitBuiltinExpr(const GlobalDecl &gd, unsigned builtinID,
227227
return RValue::get(nullptr);
228228

229229
mlir::Value argValue = emitCheckedArgForAssume(e->getArg(0));
230-
builder.create<cir::AssumeOp>(loc, argValue);
230+
cir::AssumeOp::create(builder, loc, argValue);
231231
return RValue::get(nullptr);
232232
}
233233

234234
case Builtin::BI__builtin_assume_separate_storage: {
235235
mlir::Value value0 = emitScalarExpr(e->getArg(0));
236236
mlir::Value value1 = emitScalarExpr(e->getArg(1));
237-
builder.create<cir::AssumeSepStorageOp>(loc, value0, value1);
237+
cir::AssumeSepStorageOp::create(builder, loc, value0, value1);
238238
return RValue::get(nullptr);
239239
}
240240

@@ -363,8 +363,8 @@ RValue CIRGenFunction::emitBuiltinExpr(const GlobalDecl &gd, unsigned builtinID,
363363
probability);
364364
}
365365

366-
auto result = builder.create<cir::ExpectOp>(
367-
loc, argValue.getType(), argValue, expectedValue, probAttr);
366+
auto result = cir::ExpectOp::create(builder, loc, argValue.getType(),
367+
argValue, expectedValue, probAttr);
368368
return RValue::get(result);
369369
}
370370

@@ -375,15 +375,15 @@ RValue CIRGenFunction::emitBuiltinExpr(const GlobalDecl &gd, unsigned builtinID,
375375
case Builtin::BI_byteswap_ulong:
376376
case Builtin::BI_byteswap_uint64: {
377377
mlir::Value arg = emitScalarExpr(e->getArg(0));
378-
return RValue::get(builder.create<cir::ByteSwapOp>(loc, arg));
378+
return RValue::get(cir::ByteSwapOp::create(builder, loc, arg));
379379
}
380380

381381
case Builtin::BI__builtin_bitreverse8:
382382
case Builtin::BI__builtin_bitreverse16:
383383
case Builtin::BI__builtin_bitreverse32:
384384
case Builtin::BI__builtin_bitreverse64: {
385385
mlir::Value arg = emitScalarExpr(e->getArg(0));
386-
return RValue::get(builder.create<cir::BitReverseOp>(loc, arg));
386+
return RValue::get(cir::BitReverseOp::create(builder, loc, arg));
387387
}
388388

389389
case Builtin::BI__builtin_rotateleft8:

clang/lib/CIR/CodeGen/CIRGenCXX.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -151,7 +151,7 @@ static void emitDeclDestroy(CIRGenFunction &cgf, const VarDecl *vd,
151151
// Don't confuse lexical cleanup.
152152
builder.clearInsertionPoint();
153153
} else {
154-
builder.create<cir::YieldOp>(addr.getLoc());
154+
cir::YieldOp::create(builder, addr.getLoc());
155155
}
156156
}
157157

clang/lib/CIR/CodeGen/CIRGenClass.cpp

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -725,8 +725,9 @@ void CIRGenFunction::emitCXXAggrConstructorCall(
725725
// Emit the constructor call that will execute for every array element.
726726
mlir::Value arrayOp =
727727
builder.createPtrBitcast(arrayBase.getPointer(), arrayTy);
728-
builder.create<cir::ArrayCtor>(
729-
*currSrcLoc, arrayOp, [&](mlir::OpBuilder &b, mlir::Location loc) {
728+
cir::ArrayCtor::create(
729+
builder, *currSrcLoc, arrayOp,
730+
[&](mlir::OpBuilder &b, mlir::Location loc) {
730731
mlir::BlockArgument arg =
731732
b.getInsertionBlock()->addArgument(ptrToElmType, loc);
732733
Address curAddr = Address(arg, elementType, eltAlignment);
@@ -738,7 +739,7 @@ void CIRGenFunction::emitCXXAggrConstructorCall(
738739
emitCXXConstructorCall(ctor, Ctor_Complete,
739740
/*ForVirtualBase=*/false,
740741
/*Delegating=*/false, currAVS, e);
741-
builder.create<cir::YieldOp>(loc);
742+
cir::YieldOp::create(builder, loc);
742743
});
743744
}
744745
}

clang/lib/CIR/CodeGen/CIRGenExpr.cpp

Lines changed: 15 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -251,8 +251,8 @@ void CIRGenFunction::emitStoreThroughLValue(RValue src, LValue dst,
251251
const mlir::Location loc = dst.getVectorPointer().getLoc();
252252
const mlir::Value vector =
253253
builder.createLoad(loc, dst.getVectorAddress());
254-
const mlir::Value newVector = builder.create<cir::VecInsertOp>(
255-
loc, vector, src.getValue(), dst.getVectorIdx());
254+
const mlir::Value newVector = cir::VecInsertOp::create(
255+
builder, loc, vector, src.getValue(), dst.getVectorIdx());
256256
builder.createStore(loc, newVector, dst.getVectorAddress());
257257
return;
258258
}
@@ -615,8 +615,8 @@ RValue CIRGenFunction::emitLoadOfLValue(LValue lv, SourceLocation loc) {
615615
if (lv.isVectorElt()) {
616616
const mlir::Value load =
617617
builder.createLoad(getLoc(loc), lv.getVectorAddress());
618-
return RValue::get(builder.create<cir::VecExtractOp>(getLoc(loc), load,
619-
lv.getVectorIdx()));
618+
return RValue::get(cir::VecExtractOp::create(builder, getLoc(loc), load,
619+
lv.getVectorIdx()));
620620
}
621621

622622
cgm.errorNYI(loc, "emitLoadOfLValue");
@@ -1685,8 +1685,8 @@ CIRGenCallee CIRGenFunction::emitDirectCallee(const GlobalDecl &gd) {
16851685
mlir::OpBuilder::InsertionGuard guard(builder);
16861686
builder.setInsertionPointToStart(cgm.getModule().getBody());
16871687

1688-
clone = builder.create<cir::FuncOp>(calleeFunc.getLoc(), fdInlineName,
1689-
calleeFunc.getFunctionType());
1688+
clone = cir::FuncOp::create(builder, calleeFunc.getLoc(), fdInlineName,
1689+
calleeFunc.getFunctionType());
16901690
clone.setLinkageAttr(cir::GlobalLinkageKindAttr::get(
16911691
&cgm.getMLIRContext(), cir::GlobalLinkageKind::InternalLinkage));
16921692
clone.setSymVisibility("private");
@@ -1778,8 +1778,8 @@ RValue CIRGenFunction::emitCall(clang::QualType calleeTy,
17781778
mlir::Operation *fn = callee.getFunctionPointer();
17791779
mlir::Value addr;
17801780
if (auto funcOp = mlir::dyn_cast<cir::FuncOp>(fn)) {
1781-
addr = builder.create<cir::GetGlobalOp>(
1782-
getLoc(e->getSourceRange()),
1781+
addr = cir::GetGlobalOp::create(
1782+
builder, getLoc(e->getSourceRange()),
17831783
cir::PointerType::get(funcOp.getFunctionType()), funcOp.getSymName());
17841784
} else {
17851785
addr = fn->getResult(0);
@@ -1996,9 +1996,9 @@ cir::IfOp CIRGenFunction::emitIfOnBoolExpr(
19961996

19971997
// Emit the code with the fully general case.
19981998
mlir::Value condV = emitOpOnBoolExpr(loc, cond);
1999-
return builder.create<cir::IfOp>(loc, condV, elseLoc.has_value(),
2000-
/*thenBuilder=*/thenBuilder,
2001-
/*elseBuilder=*/elseBuilder);
1999+
return cir::IfOp::create(builder, loc, condV, elseLoc.has_value(),
2000+
/*thenBuilder=*/thenBuilder,
2001+
/*elseBuilder=*/elseBuilder);
20022002
}
20032003

20042004
/// TODO(cir): see EmitBranchOnBoolExpr for extra ideas).
@@ -2025,12 +2025,12 @@ mlir::Value CIRGenFunction::emitOpOnBoolExpr(mlir::Location loc,
20252025
loc, condV, /*thenBuilder=*/
20262026
[this, trueExpr](mlir::OpBuilder &b, mlir::Location loc) {
20272027
mlir::Value lhs = emitScalarExpr(trueExpr);
2028-
b.create<cir::YieldOp>(loc, lhs);
2028+
cir::YieldOp::create(b, loc, lhs);
20292029
},
20302030
/*elseBuilder=*/
20312031
[this, falseExpr](mlir::OpBuilder &b, mlir::Location loc) {
20322032
mlir::Value rhs = emitScalarExpr(falseExpr);
2033-
b.create<cir::YieldOp>(loc, rhs);
2033+
cir::YieldOp::create(b, loc, rhs);
20342034
})
20352035
.getResult();
20362036

@@ -2211,8 +2211,8 @@ Address CIRGenFunction::emitLoadOfReference(LValue refLVal, mlir::Location loc,
22112211
cgm.errorNYI(loc, "load of volatile reference");
22122212

22132213
cir::LoadOp load =
2214-
builder.create<cir::LoadOp>(loc, refLVal.getAddress().getElementType(),
2215-
refLVal.getAddress().getPointer());
2214+
cir::LoadOp::create(builder, loc, refLVal.getAddress().getElementType(),
2215+
refLVal.getAddress().getPointer());
22162216

22172217
assert(!cir::MissingFeatures::opTBAA());
22182218

0 commit comments

Comments
 (0)