Skip to content

Commit eaa8348

Browse files
committed
Updating for review feedback
1 parent f4e6d9f commit eaa8348

File tree

8 files changed

+69
-92
lines changed

8 files changed

+69
-92
lines changed

clang/docs/CXXTypeAwareAllocators.rst

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ performed through specific interfaces, or explicitly via global ``new`` and
3333

3434
P2719 introduces a type-identity tag as valid parameter type for all allocation
3535
operators. This tag is a default initialized value of type
36-
`std::type_identity<T>` where T is the type being allocated or deallocated.
36+
``std::type_identity<T>`` where T is the type being allocated or deallocated.
3737
Unlike the other placement arguments this tag is passed as the first parameter
3838
to the operator.
3939

@@ -67,12 +67,12 @@ by using templates. In addition to adding the type-identity tag, P2719 allows
6767
the tag parameter to be a dependent specialization of `std::type_identity`,
6868
updates the overload resolution rules to support full template deduction and
6969
constraint semantics, and updates the definition of usual deallocation functions
70-
to include `operator delete` definitions that are templatized on the
70+
to include ``operator delete`` definitions that are templatized on the
7171
type-identity tag.
7272

7373
This allows arbitrarily constrained definitions of the operators that resolve
7474
as would be expected for any other template function resolution, e.g (only
75-
showing `operator new` for brevity)
75+
showing ``operator new`` for brevity)
7676

7777
.. code-block:: c++
7878

@@ -132,7 +132,7 @@ is avoiding dynamic dispatch.
132132
Subclassing and polymorphism
133133
----------------------------
134134

135-
While a type aware operator new will always receive the exact type being
135+
While a type aware ``operator new`` will always receive the exact type being
136136
allocated, deletion is limited to awareness of the dynamic type of an object.
137137
If deletion is performed via a virtual call, the type-identity tag passed to
138138
the type aware ``operator delete`` will be the dynamic type of the object.

clang/include/clang/AST/Decl.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2530,6 +2530,7 @@ class FunctionDecl : public DeclaratorDecl,
25302530
/// Determine whether this is a destroying operator delete.
25312531
bool isDestroyingOperatorDelete() const;
25322532

2533+
/// Determine whether this is a type aware operator new or delete.
25332534
bool isTypeAwareOperatorNewOrDelete() const;
25342535

25352536
/// Compute the language linkage.

clang/include/clang/AST/Type.h

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2633,7 +2633,6 @@ class alignas(TypeAlignment) Type : public ExtQualsTypeCommonBase {
26332633
bool isTypedefNameType() const; // typedef or alias template
26342634

26352635
bool isTypeIdentitySpecialization() const; // std::type_identity<X> for any X
2636-
bool isDestroyingDeleteT() const; // std::destroying_delete_t
26372636

26382637
#define IMAGE_TYPE(ImgType, Id, SingletonId, Access, Suffix) \
26392638
bool is##Id##Type() const;
@@ -2699,8 +2698,6 @@ class alignas(TypeAlignment) Type : public ExtQualsTypeCommonBase {
26992698
return static_cast<TypeDependence>(TypeBits.Dependence);
27002699
}
27012700

2702-
const TemplateDecl *getSpecializedTemplateDecl() const;
2703-
27042701
/// Whether this type is an error type.
27052702
bool containsErrors() const {
27062703
return getDependence() & TypeDependence::Error;

clang/include/clang/Sema/Sema.h

Lines changed: 3 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -4786,14 +4786,10 @@ class Sema final : public SemaBase {
47864786
EnumDecl *getStdAlignValT() const;
47874787
const ClassTemplateDecl *getStdTypeIdentity() const;
47884788
ClassTemplateDecl *getStdTypeIdentity();
4789-
std::optional<QualType> instantiateSpecializedTypeIdentity(QualType Subject);
4790-
bool isTypeIdentitySpecialization(QualType Type) const;
4791-
bool isTypeAwareOperatorNewOrDelete(const FunctionDecl *FnDecl) const;
4792-
bool isTypeAwareOperatorNewOrDelete(const FunctionTemplateDecl *FnDecl) const;
47934789
bool isTypeAwareOperatorNewOrDelete(const NamedDecl *FnDecl) const;
4794-
std::optional<FunctionDecl *>
4795-
instantiateTypeAwareUsualDelete(FunctionTemplateDecl *FnDecl,
4796-
QualType AllocType);
4790+
QualType instantiateSpecializedTypeIdentity(QualType Subject);
4791+
FunctionDecl *instantiateTypeAwareUsualDelete(FunctionTemplateDecl *FnDecl,
4792+
QualType AllocType);
47974793

47984794
ValueDecl *tryLookupUnambiguousFieldDecl(RecordDecl *ClassDecl,
47994795
const IdentifierInfo *MemberOrBase);

clang/lib/AST/Type.cpp

Lines changed: 6 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -3130,8 +3130,8 @@ bool Type::isStdByteType() const {
31303130
return false;
31313131
}
31323132

3133-
const TemplateDecl *Type::getSpecializedTemplateDecl() const {
3134-
const Type *DesugaredType = getUnqualifiedDesugaredType();
3133+
static const TemplateDecl *getSpecializedTemplateType(const Type *T) {
3134+
const Type *DesugaredType = T->getUnqualifiedDesugaredType();
31353135
if (const auto *Specialization =
31363136
DesugaredType->getAs<TemplateSpecializationType>())
31373137
return Specialization->getTemplateName().getAsTemplateDecl();
@@ -3143,15 +3143,11 @@ const TemplateDecl *Type::getSpecializedTemplateDecl() const {
31433143
}
31443144

31453145
bool Type::isTypeIdentitySpecialization() const {
3146-
const TemplateDecl *SpecializedDecl = getSpecializedTemplateDecl();
3147-
if (!SpecializedDecl)
3146+
const TemplateDecl *STDecl = getSpecializedTemplateType(this);
3147+
if (!STDecl)
31483148
return false;
3149-
IdentifierInfo *II = SpecializedDecl->getIdentifier();
3150-
if (!II)
3151-
return false;
3152-
if (!SpecializedDecl->isInStdNamespace())
3153-
return false;
3154-
return II->isStr("type_identity");
3149+
IdentifierInfo *II = STDecl->getIdentifier();
3150+
return II && STDecl->isInStdNamespace() && II->isStr("type_identity");
31553151
}
31563152

31573153
bool Type::isSpecifierType() const {

clang/lib/Sema/SemaCoroutine.cpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1595,12 +1595,12 @@ bool CoroutineStmtBuilder::makeNewAndDeleteExpr() {
15951595
SmallVector<Expr *, 3> NewArgs;
15961596
auto BuildTypeIdentityArg = [PromiseType](Sema &S,
15971597
SourceLocation Loc) -> Expr * {
1598-
std::optional<QualType> SpecializedTypeIdentity =
1598+
QualType SpecializedTypeIdentity =
15991599
S.instantiateSpecializedTypeIdentity(PromiseType);
1600-
if (!SpecializedTypeIdentity)
1600+
if (SpecializedTypeIdentity.isNull())
16011601
return nullptr;
16021602
TypeSourceInfo *SpecializedTypeInfo =
1603-
S.Context.getTrivialTypeSourceInfo(*SpecializedTypeIdentity, Loc);
1603+
S.Context.getTrivialTypeSourceInfo(SpecializedTypeIdentity, Loc);
16041604
ExprResult TypeIdentity =
16051605
S.BuildCXXTypeConstructExpr(SpecializedTypeInfo, Loc, {}, Loc, false);
16061606
if (TypeIdentity.isInvalid())
@@ -1649,7 +1649,7 @@ bool CoroutineStmtBuilder::makeNewAndDeleteExpr() {
16491649
// used, the size of the block is passed as the corresponding argument.
16501650
const auto *OpDeleteType =
16511651
OpDeleteQualType.getTypePtr()->castAs<FunctionProtoType>();
1652-
if (S.isTypeAwareOperatorNewOrDelete(OperatorDelete)) {
1652+
if (OperatorDelete->isTypeAwareOperatorNewOrDelete()) {
16531653
Expr *TypeIdentity = BuildTypeIdentityArg(S, Loc);
16541654
if (!TypeIdentity)
16551655
return false;

clang/lib/Sema/SemaDeclCXX.cpp

Lines changed: 24 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -10872,7 +10872,7 @@ bool Sema::CheckDestructor(CXXDestructorDecl *Destructor) {
1087210872
// first parameter, perform that conversion now.
1087310873
if (OperatorDelete->isDestroyingOperatorDelete()) {
1087410874
unsigned PointerParam = 0;
10875-
if (isTypeAwareOperatorNewOrDelete(OperatorDelete))
10875+
if (OperatorDelete->isTypeAwareOperatorNewOrDelete())
1087610876
++PointerParam;
1087710877
QualType ParamType =
1087810878
OperatorDelete->getParamDecl(PointerParam)->getType();
@@ -16127,72 +16127,53 @@ bool Sema::CompleteConstructorCall(CXXConstructorDecl *Constructor,
1612716127
return Invalid;
1612816128
}
1612916129

16130-
bool Sema::isTypeIdentitySpecialization(QualType Type) const {
16131-
const ClassTemplateDecl *TypeIdentity = getStdTypeIdentity();
16132-
if (!TypeIdentity)
16133-
return false;
16134-
const TemplateDecl *SpecializedDecl = Type->getSpecializedTemplateDecl();
16135-
return TypeIdentity == SpecializedDecl;
16136-
}
16137-
16138-
bool Sema::isTypeAwareOperatorNewOrDelete(const FunctionDecl *FnDecl) const {
16139-
// Type aware operators
16140-
if (FnDecl->getNumParams() < 2)
16141-
return false;
16142-
const ParmVarDecl *ParamDecl = FnDecl->getParamDecl(0);
16143-
return isTypeIdentitySpecialization(ParamDecl->getType());
16144-
}
16145-
16146-
bool Sema::isTypeAwareOperatorNewOrDelete(
16147-
const FunctionTemplateDecl *FTD) const {
16148-
return isTypeAwareOperatorNewOrDelete(FTD->getTemplatedDecl());
16149-
}
16150-
1615116130
bool Sema::isTypeAwareOperatorNewOrDelete(const NamedDecl *ND) const {
16131+
const FunctionDecl *FnDecl = nullptr;
1615216132
if (auto *FTD = dyn_cast<FunctionTemplateDecl>(ND))
16153-
return isTypeAwareOperatorNewOrDelete(FTD->getTemplatedDecl());
16154-
if (auto *FnDecl = dyn_cast<FunctionDecl>(ND))
16155-
return isTypeAwareOperatorNewOrDelete(FnDecl);
16156-
return false;
16133+
FnDecl = FTD->getTemplatedDecl();
16134+
else if (auto *FD = dyn_cast<FunctionDecl>(ND))
16135+
FnDecl = FD;
16136+
16137+
return FnDecl->isTypeAwareOperatorNewOrDelete();
1615716138
}
1615816139

16159-
std::optional<FunctionDecl *>
16140+
FunctionDecl *
1616016141
Sema::instantiateTypeAwareUsualDelete(FunctionTemplateDecl *FnTemplateDecl,
1616116142
QualType DeallocType) {
1616216143
if (!isTypeAwareAllocation(allocationModeInCurrentContext()))
16163-
return std::nullopt;
16144+
return nullptr;
1616416145

1616516146
TemplateParameterList *TemplateParameters =
1616616147
FnTemplateDecl->getTemplateParameters();
1616716148
if (TemplateParameters->hasParameterPack())
16168-
return std::nullopt;
16149+
return nullptr;
1616916150

1617016151
FunctionDecl *FnDecl = FnTemplateDecl->getTemplatedDecl();
16171-
if (!isTypeAwareOperatorNewOrDelete(FnDecl))
16172-
return std::nullopt;
16152+
if (!FnDecl->isTypeAwareOperatorNewOrDelete())
16153+
return nullptr;
1617316154

1617416155
if (FnDecl->isVariadic())
16175-
return std::nullopt;
16156+
return nullptr;
1617616157

1617716158
unsigned NumParams = FnDecl->getNumParams();
1617816159
if (NumParams < 2)
16179-
return std::nullopt;
16160+
return nullptr;
1618016161

1618116162
for (size_t Idx = 1; Idx < NumParams; ++Idx) {
1618216163
// A type aware allocation is only usual if the only dependent parameter is
1618316164
// the first parameter.
1618416165
const ParmVarDecl *ParamDecl = FnDecl->getParamDecl(Idx);
1618516166
if (ParamDecl->getType()->isDependentType())
16186-
return std::nullopt;
16167+
return nullptr;
1618716168
}
1618816169

16189-
std::optional<QualType> SpecializedTypeIdentity =
16170+
QualType SpecializedTypeIdentity =
1619016171
instantiateSpecializedTypeIdentity(DeallocType);
16191-
if (!SpecializedTypeIdentity)
16192-
return std::nullopt;
16172+
if (SpecializedTypeIdentity.isNull())
16173+
return nullptr;
1619316174
SmallVector<QualType, 4> ArgTypes;
1619416175
ArgTypes.reserve(NumParams);
16195-
ArgTypes.push_back(*SpecializedTypeIdentity);
16176+
ArgTypes.push_back(SpecializedTypeIdentity);
1619616177
ArgTypes.push_back(FnDecl->getParamDecl(1)->getType());
1619716178
unsigned UsualParamsIdx = 2;
1619816179
if (UsualParamsIdx < NumParams && FnDecl->isDestroyingOperatorDelete()) {
@@ -16218,7 +16199,7 @@ Sema::instantiateTypeAwareUsualDelete(FunctionTemplateDecl *FnTemplateDecl,
1621816199
}
1621916200

1622016201
if (UsualParamsIdx != NumParams)
16221-
return std::nullopt;
16202+
return nullptr;
1622216203

1622316204
FunctionProtoType::ExtProtoInfo EPI;
1622416205
QualType ExpectedFunctionType =
@@ -16228,24 +16209,23 @@ Sema::instantiateTypeAwareUsualDelete(FunctionTemplateDecl *FnTemplateDecl,
1622816209
FunctionDecl *Result;
1622916210
if (DeduceTemplateArguments(FnTemplateDecl, nullptr, ExpectedFunctionType,
1623016211
Result, Info) != TemplateDeductionResult::Success)
16231-
return std::nullopt;
16212+
return nullptr;
1623216213
return Result;
1623316214
}
1623416215

16235-
std::optional<QualType>
16236-
Sema::instantiateSpecializedTypeIdentity(QualType Subject) {
16216+
QualType Sema::instantiateSpecializedTypeIdentity(QualType Subject) {
1623716217
assert(clang::isTypeAwareAllocation(allocationModeInCurrentContext()));
1623816218
ClassTemplateDecl *TypeIdentity = getStdTypeIdentity();
1623916219
if (!TypeIdentity)
16240-
return std::nullopt;
16220+
return QualType();
1624116221

1624216222
auto TN = TemplateName(TypeIdentity);
1624316223
TemplateArgumentListInfo Arguments;
1624416224
Arguments.addArgument(getTrivialTemplateArgumentLoc(
1624516225
TemplateArgument(Subject), QualType(), SourceLocation()));
1624616226
QualType Result = CheckTemplateIdType(TN, SourceLocation(), Arguments);
1624716227
if (Result.isNull())
16248-
return std::nullopt;
16228+
return QualType();
1624916229
return Result;
1625016230
}
1625116231

0 commit comments

Comments
 (0)