Skip to content

Commit

Permalink
[c++1z] When initializing a const-qualified class type, don't forget …
Browse files Browse the repository at this point in the history
…to add on

the requested cv-qualifiers after construction. This usually doesn't matter,
but it does matter within a ?: operator.

llvm-svn: 290227
  • Loading branch information
zygoloid committed Dec 21, 2016
1 parent bde7a3f commit 16d3150
Show file tree
Hide file tree
Showing 3 changed files with 16 additions and 13 deletions.
3 changes: 1 addition & 2 deletions clang/lib/Sema/SemaExprCXX.cpp
Expand Up @@ -5199,8 +5199,7 @@ static bool TryClassUnification(Sema &Self, Expr *From, Expr *To,
//
// This actually refers very narrowly to the lvalue-to-rvalue conversion, not
// to the array-to-pointer or function-to-pointer conversions.
if (!TTy->getAs<TagType>())
TTy = TTy.getUnqualifiedType();
TTy = TTy.getNonLValueExprType(Self.Context);

InitializedEntity Entity = InitializedEntity::InitializeTemporary(TTy);
InitializationSequence InitSeq(Self, Entity, Kind, From);
Expand Down
16 changes: 5 additions & 11 deletions clang/lib/Sema/SemaInit.cpp
Expand Up @@ -3609,17 +3609,7 @@ static void TryConstructorInitialization(Sema &S,
UnwrappedArgs.size() == 1 && UnwrappedArgs[0]->isRValue() &&
S.Context.hasSameUnqualifiedType(UnwrappedArgs[0]->getType(), DestType)) {
// Convert qualifications if necessary.
QualType InitType = UnwrappedArgs[0]->getType();
ImplicitConversionSequence ICS;
ICS.setStandard();
ICS.Standard.setAsIdentityConversion();
ICS.Standard.setFromType(InitType);
ICS.Standard.setAllToTypes(InitType);
if (!S.Context.hasSameType(InitType, DestType)) {
ICS.Standard.Third = ICK_Qualification;
ICS.Standard.setToType(2, DestType);
}
Sequence.AddConversionSequenceStep(ICS, DestType);
Sequence.AddQualificationConversionStep(DestType, VK_RValue);
if (ILE)
Sequence.RewrapReferenceInitList(DestType, ILE);
return;
Expand Down Expand Up @@ -4790,6 +4780,8 @@ static void TryUserDefinedConversion(Sema &S,
// FIXME: Mark this copy as extraneous.
if (!S.getLangOpts().CPlusPlus1z)
Sequence.AddFinalCopy(DestType);
else if (DestType.hasQualifiers())
Sequence.AddQualificationConversionStep(DestType, VK_RValue);
return;
}

Expand All @@ -4812,6 +4804,8 @@ static void TryUserDefinedConversion(Sema &S,
Function->getReturnType()->isReferenceType() ||
!S.Context.hasSameUnqualifiedType(ConvType, DestType))
Sequence.AddFinalCopy(DestType);
else if (!S.Context.hasSameType(ConvType, DestType))
Sequence.AddQualificationConversionStep(DestType, VK_RValue);
return;
}

Expand Down
10 changes: 10 additions & 0 deletions clang/test/CXX/expr/expr.cond/p4.cpp
@@ -0,0 +1,10 @@
// RUN: %clang_cc1 -std=c++98 -verify %s
// RUN: %clang_cc1 -std=c++1z -verify %s

// expected-no-diagnostics

struct A { A(); A(int); };
void f() {
const A a;
true ? a : 0;
}

0 comments on commit 16d3150

Please sign in to comment.