Skip to content

Commit 5672c69

Browse files
authored
Merge pull request #17123 from CodaFi/unexpected-parentheticals
Don't flatten input types in ObjC representation check
2 parents fc23f34 + e15e293 commit 5672c69

File tree

3 files changed

+39
-25
lines changed

3 files changed

+39
-25
lines changed

lib/AST/Type.cpp

Lines changed: 28 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1955,30 +1955,41 @@ getForeignRepresentable(Type type, ForeignLanguage language,
19551955
break;
19561956
}
19571957

1958+
auto success = [](bool anyStaticBridged,
1959+
bool anyBridged,
1960+
bool isBlock) -> std::pair<ForeignRepresentableKind,
1961+
ProtocolConformance *> {
1962+
// We have something representable; check how it is representable.
1963+
return { anyStaticBridged ? ForeignRepresentableKind::StaticBridged
1964+
: anyBridged ? ForeignRepresentableKind::Bridged
1965+
: isBlock ? ForeignRepresentableKind::Object
1966+
: ForeignRepresentableKind::Trivial,
1967+
nullptr };
1968+
};
1969+
1970+
// HACK: In Swift 3 mode, we accepted (Void) -> Void for () -> Void
1971+
if (dc->getASTContext().isSwiftVersion3()
1972+
&& functionType->getParams().size() == 1
1973+
&& functionType->getParams()[0].getLabel().empty()
1974+
&& functionType->getParams()[0].getType()->isVoid()
1975+
&& functionType->getResult()->isVoid()) {
1976+
return success(anyStaticBridged, anyBridged, isBlock);
1977+
}
1978+
19581979
// Look at the result type.
19591980
Type resultType = functionType->getResult();
19601981
if (!resultType->isVoid() && recurse(resultType))
19611982
return failure();
19621983

1963-
// Look at the input types.
1964-
Type inputType = functionType->getInput();
1965-
if (auto inputTuple = inputType->getAs<TupleType>()) {
1966-
for (const auto &elt : inputTuple->getElements()) {
1967-
if (elt.isVararg())
1968-
return failure();
1969-
if (recurse(elt.getType()))
1970-
return failure();
1971-
}
1972-
} else if (recurse(inputType)) {
1973-
return failure();
1984+
// Look at the input params.
1985+
for (const auto &param : functionType->getParams()) {
1986+
if (param.isVariadic())
1987+
return failure();
1988+
if (recurse(param.getType()))
1989+
return failure();
19741990
}
19751991

1976-
// We have something representable; check how it is representable.
1977-
return { anyStaticBridged ? ForeignRepresentableKind::StaticBridged
1978-
: anyBridged ? ForeignRepresentableKind::Bridged
1979-
: isBlock ? ForeignRepresentableKind::Object
1980-
: ForeignRepresentableKind::Trivial,
1981-
nullptr };
1992+
return success(anyStaticBridged, anyBridged, isBlock);
19821993
}
19831994

19841995
// Give special dispensation to builtin types for testing purposes.

test/ClangImporter/objc_parse.swift

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -633,6 +633,17 @@ class NewtypeUser {
633633
@objc func intNewtypeDictionary(a: [MyInt: NSObject]) {} // expected-error {{method cannot be marked @objc because the type of the parameter cannot be represented in Objective-C}}
634634
@objc func cfNewtype(a: CFNewType) {}
635635
@objc func cfNewtypeArray(a: [CFNewType]) {} // expected-error {{method cannot be marked @objc because the type of the parameter cannot be represented in Objective-C}}
636+
637+
typealias MyTuple = (Int, AnyObject?)
638+
typealias MyNamedTuple = (a: Int, b: AnyObject?)
639+
640+
@objc func blockWithTypealias(_ input: @escaping (MyTuple) -> MyInt) {}
641+
// expected-error@-1{{method cannot be marked @objc because the type of the parameter cannot be represented in Objective-C}}
642+
// expected-note@-2{{function types cannot be represented in Objective-C}}
643+
644+
@objc func blockWithTypealiasWithNames(_ input: (MyNamedTuple) -> MyInt) {}
645+
// expected-error@-1{{method cannot be marked @objc because the type of the parameter cannot be represented in Objective-C}}
646+
// expected-note@-2{{function types cannot be represented in Objective-C}}
636647
}
637648

638649
func testTypeAndValue() {

test/PrintAsObjC/blocks.swift

Lines changed: 0 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,6 @@
1010

1111
import ObjectiveC
1212

13-
typealias MyTuple = (Int, AnyObject?)
14-
typealias MyNamedTuple = (a: Int, b: AnyObject?)
1513
typealias MyInt = Int
1614
typealias MyBlockWithEscapingParam = (@escaping () -> ()) -> Int
1715
typealias MyBlockWithNoescapeParam = (() -> ()) -> Int
@@ -60,9 +58,6 @@ typealias MyBlockWithNoescapeParam = (() -> ()) -> Int
6058
@objc func returnsBlockWithTwoInputs() -> ((NSObject, NSObject) -> ())? {
6159
return nil
6260
}
63-
64-
// CHECK-NEXT: - (void)blockWithTypealias:(NSInteger (^ _Nonnull)(NSInteger, id _Nullable))input;
65-
@objc func blockWithTypealias(_ input: @escaping (MyTuple) -> MyInt) {}
6661

6762
// CHECK-NEXT: - (void)blockWithSimpleTypealias:(NSInteger (^ _Nonnull)(NSInteger))input;
6863
@objc func blockWithSimpleTypealias(_ input: @escaping (MyInt) -> MyInt) {}
@@ -78,9 +73,6 @@ typealias MyBlockWithNoescapeParam = (() -> ()) -> Int
7873
return nil
7974
}
8075

81-
// CHECK-NEXT: - (void)blockWithTypealiasWithNames:(SWIFT_NOESCAPE NSInteger (^ _Nonnull)(NSInteger a, id _Nullable b))input;
82-
@objc func blockWithTypealiasWithNames(_ input: (MyNamedTuple) -> MyInt) {}
83-
8476
// CHECK-NEXT: - (void)blockWithKeyword:(SWIFT_NOESCAPE NSInteger (^ _Nonnull)(NSInteger))_Nullable_;
8577
@objc func blockWithKeyword(_ _Nullable: (_ `class`: Int) -> Int) {}
8678

0 commit comments

Comments
 (0)