summaryrefslogtreecommitdiffstats
path: root/lib/Sema/SemaTemplateDeduction.cpp
diff options
context:
space:
mode:
authorDouglas Gregor <dgregor@apple.com>2013-11-08 02:04:24 +0000
committerDouglas Gregor <dgregor@apple.com>2013-11-08 02:04:24 +0000
commit3940e3b9c7cc89284117112e07ad1c925dcd0ab4 (patch)
tree1a839cc4fe9e59e230bbf276bdee7322fad09c96 /lib/Sema/SemaTemplateDeduction.cpp
parent80aecf578fa0b24e1f4280820a1b6f1bf34862e0 (diff)
Objective-C++ ARC: Improve the conversion to a const __unsafe_unretained reference.
Under ARC++, a reference to a const Objective-C pointer is implicitly treated as __unsafe_unretained, and can be initialized with (e.g.) a __strong lvalue. Make sure this behavior does not break template argument deduction and (related) that partial ordering still prefers a 'T* const&' template over a 'T const&' template when this case kicks in. Fixes <rdar://problem/14467941>. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@194239 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Sema/SemaTemplateDeduction.cpp')
-rw-r--r--lib/Sema/SemaTemplateDeduction.cpp17
1 files changed, 10 insertions, 7 deletions
diff --git a/lib/Sema/SemaTemplateDeduction.cpp b/lib/Sema/SemaTemplateDeduction.cpp
index 6e510c2dbc..b401db21a8 100644
--- a/lib/Sema/SemaTemplateDeduction.cpp
+++ b/lib/Sema/SemaTemplateDeduction.cpp
@@ -2687,13 +2687,16 @@ CheckOriginalCallArgDeduction(Sema &S, Sema::OriginalCallArg OriginalArg,
Qualifiers AQuals = A.getQualifiers();
Qualifiers DeducedAQuals = DeducedA.getQualifiers();
- // Under Objective-C++ ARC, the deduced type may have implicitly been
- // given strong lifetime. If so, update the original qualifiers to
- // include this strong lifetime.
+ // Under Objective-C++ ARC, the deduced type may have implicitly
+ // been given strong or (when dealing with a const reference)
+ // unsafe_unretained lifetime. If so, update the original
+ // qualifiers to include this lifetime.
if (S.getLangOpts().ObjCAutoRefCount &&
- DeducedAQuals.getObjCLifetime() == Qualifiers::OCL_Strong &&
- AQuals.getObjCLifetime() == Qualifiers::OCL_None) {
- AQuals.setObjCLifetime(Qualifiers::OCL_Strong);
+ ((DeducedAQuals.getObjCLifetime() == Qualifiers::OCL_Strong &&
+ AQuals.getObjCLifetime() == Qualifiers::OCL_None) ||
+ (DeducedAQuals.hasConst() &&
+ DeducedAQuals.getObjCLifetime() == Qualifiers::OCL_ExplicitNone))) {
+ AQuals.setObjCLifetime(DeducedAQuals.getObjCLifetime());
}
if (AQuals == DeducedAQuals) {
@@ -2714,7 +2717,7 @@ CheckOriginalCallArgDeduction(Sema &S, Sema::OriginalCallArg OriginalArg,
//
// Also allow conversions which merely strip [[noreturn]] from function types
// (recursively) as an extension.
- // FIXME: Currently, this doesn't place nicely with qualfication conversions.
+ // FIXME: Currently, this doesn't play nicely with qualification conversions.
bool ObjCLifetimeConversion = false;
QualType ResultTy;
if ((A->isAnyPointerType() || A->isMemberPointerType()) &&