@@ -3370,7 +3370,11 @@ namespace {
3370
3370
3371
3371
// / Emit diagnostics for incorrect usage of SWIFT_RETURNS_RETAINED and
3372
3372
// / SWIFT_RETURNS_UNRETAINED
3373
- void checkBridgingAttrs (const clang::FunctionDecl *decl) {
3373
+ void checkBridgingAttrs (const clang::NamedDecl *decl) {
3374
+ assert (isa<clang::FunctionDecl>(decl) ||
3375
+ isa<clang::ObjCMethodDecl>(decl) &&
3376
+ " checkBridgingAttrs called with a clang::NamedDecl which is "
3377
+ " neither clang::FunctionDecl nor clang::ObjCMethodDecl" );
3374
3378
bool returnsRetainedAttrIsPresent = false ;
3375
3379
bool returnsUnretainedAttrIsPresent = false ;
3376
3380
if (decl->hasAttrs ()) {
@@ -3386,14 +3390,29 @@ namespace {
3386
3390
}
3387
3391
3388
3392
HeaderLoc loc (decl->getLocation ());
3389
- if (isForeignReferenceTypeWithoutImmortalAttrs (decl->getReturnType ())) {
3393
+ bool isForeignReferenceReturnType = false ;
3394
+ if (const auto *funcDecl = dyn_cast<clang::FunctionDecl>(decl)) {
3395
+ if (isForeignReferenceTypeWithoutImmortalAttrs (
3396
+ funcDecl->getReturnType ())) {
3397
+ isForeignReferenceReturnType = true ;
3398
+ }
3399
+ } else if (const auto *objCMethodDecl =
3400
+ dyn_cast<clang::ObjCMethodDecl>(decl)) {
3401
+ if (isForeignReferenceTypeWithoutImmortalAttrs (
3402
+ objCMethodDecl->getReturnType ())) {
3403
+ isForeignReferenceReturnType = true ;
3404
+ }
3405
+ }
3406
+
3407
+ if (isForeignReferenceReturnType) {
3390
3408
if (returnsRetainedAttrIsPresent && returnsUnretainedAttrIsPresent) {
3391
3409
Impl.diagnose (loc, diag::both_returns_retained_returns_unretained,
3392
3410
decl);
3393
3411
} else if (!returnsRetainedAttrIsPresent &&
3394
3412
!returnsUnretainedAttrIsPresent) {
3395
- bool unannotatedCxxAPIWarningNeeded = false ;
3396
- if (!isa<clang::CXXDeductionGuideDecl>(decl)) {
3413
+ bool unannotatedAPIWarningNeeded = false ;
3414
+ if (isa<clang::FunctionDecl>(decl) &&
3415
+ !isa<clang::CXXDeductionGuideDecl>(decl)) {
3397
3416
if (const auto *methodDecl = dyn_cast<clang::CXXMethodDecl>(decl)) {
3398
3417
// FIXME: In the future we should support SWIFT_RETURNS_RETAINED
3399
3418
// and SWIFT_RETURNS_UNRETAINED for overloaded C++ operators
@@ -3403,15 +3422,17 @@ namespace {
3403
3422
!methodDecl->isOverloadedOperator () &&
3404
3423
methodDecl->isUserProvided ()) {
3405
3424
// normal c++ member method
3406
- unannotatedCxxAPIWarningNeeded = true ;
3425
+ unannotatedAPIWarningNeeded = true ;
3407
3426
}
3408
3427
} else {
3409
- // global or top-level function
3410
- unannotatedCxxAPIWarningNeeded = true ;
3428
+ // global or top-level C/C++ function
3429
+ unannotatedAPIWarningNeeded = true ;
3411
3430
}
3431
+ } else if (isa<clang::ObjCMethodDecl>(decl)) {
3432
+ unannotatedAPIWarningNeeded = true ;
3412
3433
}
3413
3434
3414
- if (unannotatedCxxAPIWarningNeeded ) {
3435
+ if (unannotatedAPIWarningNeeded ) {
3415
3436
HeaderLoc loc (decl->getLocation ());
3416
3437
Impl.diagnose (loc, diag::no_returns_retained_returns_unretained,
3417
3438
decl);
@@ -4510,6 +4531,8 @@ namespace {
4510
4531
if (!dc)
4511
4532
return nullptr ;
4512
4533
4534
+ checkBridgingAttrs (decl);
4535
+
4513
4536
// While importing the DeclContext, we might have imported the decl
4514
4537
// itself.
4515
4538
auto Known = Impl.importDeclCached (decl, getVersion ());
0 commit comments