@@ -45,10 +45,6 @@ template <class Emitter> class DeclScope final : public LocalScope<Emitter> {
45
45
Ctx->InitStack .push_back (InitLink::Decl (VD));
46
46
}
47
47
48
- void addExtended (const Scope::Local &Local) override {
49
- return this ->addLocal (Local);
50
- }
51
-
52
48
~DeclScope () {
53
49
this ->Ctx ->InitializingDecl = OldInitializingDecl;
54
50
this ->Ctx ->InitStack .pop_back ();
@@ -2021,6 +2017,45 @@ bool Compiler<Emitter>::visitArrayElemInit(unsigned ElemIndex, const Expr *Init,
2021
2017
return this ->emitFinishInitPop (Init);
2022
2018
}
2023
2019
2020
+ template <class Emitter >
2021
+ bool Compiler<Emitter>::visitCallArgs(ArrayRef<const Expr *> Args,
2022
+ const FunctionDecl *FuncDecl) {
2023
+ assert (VarScope->getKind () == ScopeKind::Call);
2024
+ llvm::BitVector NonNullArgs = collectNonNullArgs (FuncDecl, Args);
2025
+
2026
+ unsigned ArgIndex = 0 ;
2027
+ for (const Expr *Arg : Args) {
2028
+ if (std::optional<PrimType> T = classify (Arg)) {
2029
+ if (!this ->visit (Arg))
2030
+ return false ;
2031
+ } else {
2032
+
2033
+ std::optional<unsigned > LocalIndex = allocateLocal (
2034
+ Arg, Arg->getType (), /* ExtendingDecl=*/ nullptr , ScopeKind::Call);
2035
+ if (!LocalIndex)
2036
+ return false ;
2037
+
2038
+ if (!this ->emitGetPtrLocal (*LocalIndex, Arg))
2039
+ return false ;
2040
+ InitLinkScope<Emitter> ILS (this , InitLink::Temp (*LocalIndex));
2041
+ if (!this ->visitInitializer (Arg))
2042
+ return false ;
2043
+ }
2044
+
2045
+ if (FuncDecl && NonNullArgs[ArgIndex]) {
2046
+ PrimType ArgT = classify (Arg).value_or (PT_Ptr);
2047
+ if (ArgT == PT_Ptr) {
2048
+ if (!this ->emitCheckNonNullArg (ArgT, Arg))
2049
+ return false ;
2050
+ }
2051
+ }
2052
+
2053
+ ++ArgIndex;
2054
+ }
2055
+
2056
+ return true ;
2057
+ }
2058
+
2024
2059
template <class Emitter >
2025
2060
bool Compiler<Emitter>::VisitInitListExpr(const InitListExpr *E) {
2026
2061
return this ->visitInitList (E->inits (), E->getArrayFiller (), E);
@@ -4343,7 +4378,7 @@ bool Compiler<Emitter>::emitConst(const APSInt &Value, const Expr *E) {
4343
4378
template <class Emitter >
4344
4379
unsigned Compiler<Emitter>::allocateLocalPrimitive(
4345
4380
DeclTy &&Src, PrimType Ty, bool IsConst, const ValueDecl *ExtendingDecl,
4346
- bool IsConstexprUnknown) {
4381
+ ScopeKind SC, bool IsConstexprUnknown) {
4347
4382
// Make sure we don't accidentally register the same decl twice.
4348
4383
if (const auto *VD =
4349
4384
dyn_cast_if_present<ValueDecl>(Src.dyn_cast <const Decl *>())) {
@@ -4364,14 +4399,14 @@ unsigned Compiler<Emitter>::allocateLocalPrimitive(
4364
4399
if (ExtendingDecl)
4365
4400
VarScope->addExtended (Local, ExtendingDecl);
4366
4401
else
4367
- VarScope->add (Local, false );
4402
+ VarScope->addForScopeKind (Local, SC );
4368
4403
return Local.Offset ;
4369
4404
}
4370
4405
4371
4406
template <class Emitter >
4372
4407
std::optional<unsigned >
4373
4408
Compiler<Emitter>::allocateLocal(DeclTy &&Src, QualType Ty,
4374
- const ValueDecl *ExtendingDecl,
4409
+ const ValueDecl *ExtendingDecl, ScopeKind SC,
4375
4410
bool IsConstexprUnknown) {
4376
4411
// Make sure we don't accidentally register the same decl twice.
4377
4412
if ([[maybe_unused]] const auto *VD =
@@ -4409,7 +4444,7 @@ Compiler<Emitter>::allocateLocal(DeclTy &&Src, QualType Ty,
4409
4444
if (ExtendingDecl)
4410
4445
VarScope->addExtended (Local, ExtendingDecl);
4411
4446
else
4412
- VarScope->add (Local, false );
4447
+ VarScope->addForScopeKind (Local, SC );
4413
4448
return Local.Offset ;
4414
4449
}
4415
4450
@@ -4676,7 +4711,7 @@ VarCreationState Compiler<Emitter>::visitVarDecl(const VarDecl *VD,
4676
4711
if (VarT) {
4677
4712
unsigned Offset = this ->allocateLocalPrimitive (
4678
4713
VD, *VarT, VD->getType ().isConstQualified (), nullptr ,
4679
- IsConstexprUnknown);
4714
+ ScopeKind::Block, IsConstexprUnknown);
4680
4715
if (Init) {
4681
4716
// If this is a toplevel declaration, create a scope for the
4682
4717
// initializer.
@@ -4692,8 +4727,9 @@ VarCreationState Compiler<Emitter>::visitVarDecl(const VarDecl *VD,
4692
4727
}
4693
4728
}
4694
4729
} else {
4695
- if (std::optional<unsigned > Offset = this ->allocateLocal (
4696
- VD, VD->getType (), nullptr , IsConstexprUnknown)) {
4730
+ if (std::optional<unsigned > Offset =
4731
+ this ->allocateLocal (VD, VD->getType (), nullptr , ScopeKind::Block,
4732
+ IsConstexprUnknown)) {
4697
4733
if (!Init)
4698
4734
return true ;
4699
4735
@@ -4881,26 +4917,28 @@ bool Compiler<Emitter>::VisitCallExpr(const CallExpr *E) {
4881
4917
if (FuncDecl) {
4882
4918
if (unsigned BuiltinID = FuncDecl->getBuiltinID ())
4883
4919
return VisitBuiltinCallExpr (E, BuiltinID);
4884
- }
4885
4920
4886
- // Calls to replaceable operator new/operator delete.
4887
- if (FuncDecl &&
4888
- FuncDecl->isUsableAsGlobalAllocationFunctionInConstantEvaluation ()) {
4889
- if (FuncDecl->getDeclName ().isAnyOperatorNew ()) {
4890
- return VisitBuiltinCallExpr (E, Builtin::BI__builtin_operator_new);
4891
- } else {
4892
- assert (FuncDecl->getDeclName ().getCXXOverloadedOperator () == OO_Delete);
4893
- return VisitBuiltinCallExpr (E, Builtin::BI__builtin_operator_delete);
4921
+ // Calls to replaceable operator new/operator delete.
4922
+ if (FuncDecl->isUsableAsGlobalAllocationFunctionInConstantEvaluation ()) {
4923
+ if (FuncDecl->getDeclName ().isAnyOperatorNew ()) {
4924
+ return VisitBuiltinCallExpr (E, Builtin::BI__builtin_operator_new);
4925
+ } else {
4926
+ assert (FuncDecl->getDeclName ().getCXXOverloadedOperator () == OO_Delete);
4927
+ return VisitBuiltinCallExpr (E, Builtin::BI__builtin_operator_delete);
4928
+ }
4929
+ }
4930
+
4931
+ // Explicit calls to trivial destructors
4932
+ if (const auto *DD = dyn_cast<CXXDestructorDecl>(FuncDecl);
4933
+ DD && DD->isTrivial ()) {
4934
+ const auto *MemberCall = cast<CXXMemberCallExpr>(E);
4935
+ if (!this ->visit (MemberCall->getImplicitObjectArgument ()))
4936
+ return false ;
4937
+ return this ->emitCheckDestruction (E) && this ->emitPopPtr (E);
4894
4938
}
4895
4939
}
4896
- // Explicit calls to trivial destructors
4897
- if (const auto *DD = dyn_cast_if_present<CXXDestructorDecl>(FuncDecl);
4898
- DD && DD->isTrivial ()) {
4899
- const auto *MemberCall = cast<CXXMemberCallExpr>(E);
4900
- if (!this ->visit (MemberCall->getImplicitObjectArgument ()))
4901
- return false ;
4902
- return this ->emitCheckDestruction (E) && this ->emitPopPtr (E);
4903
- }
4940
+
4941
+ BlockScope<Emitter> CallScope (this , ScopeKind::Call);
4904
4942
4905
4943
QualType ReturnType = E->getCallReturnType (Ctx.getASTContext ());
4906
4944
std::optional<PrimType> T = classify (ReturnType);
@@ -4996,23 +5034,8 @@ bool Compiler<Emitter>::VisitCallExpr(const CallExpr *E) {
4996
5034
return false ;
4997
5035
}
4998
5036
4999
- llvm::BitVector NonNullArgs = collectNonNullArgs (FuncDecl, Args);
5000
- // Put arguments on the stack.
5001
- unsigned ArgIndex = 0 ;
5002
- for (const auto *Arg : Args) {
5003
- if (!this ->visit (Arg))
5004
- return false ;
5005
-
5006
- // If we know the callee already, check the known parametrs for nullability.
5007
- if (FuncDecl && NonNullArgs[ArgIndex]) {
5008
- PrimType ArgT = classify (Arg).value_or (PT_Ptr);
5009
- if (ArgT == PT_Ptr) {
5010
- if (!this ->emitCheckNonNullArg (ArgT, Arg))
5011
- return false ;
5012
- }
5013
- }
5014
- ++ArgIndex;
5015
- }
5037
+ if (!this ->visitCallArgs (Args, FuncDecl))
5038
+ return false ;
5016
5039
5017
5040
// Undo the argument reversal we did earlier.
5018
5041
if (IsAssignmentOperatorCall) {
@@ -5088,9 +5111,9 @@ bool Compiler<Emitter>::VisitCallExpr(const CallExpr *E) {
5088
5111
5089
5112
// Cleanup for discarded return values.
5090
5113
if (DiscardResult && !ReturnType->isVoidType () && T)
5091
- return this ->emitPop (*T, E);
5114
+ return this ->emitPop (*T, E) && CallScope. destroyLocals () ;
5092
5115
5093
- return true ;
5116
+ return CallScope. destroyLocals () ;
5094
5117
}
5095
5118
5096
5119
template <class Emitter >
0 commit comments