@@ -1402,6 +1402,38 @@ static bool diagnoseAvailability(Type ty, IdentTypeRepr *IdType, SourceLoc Loc,
1402
1402
return false ;
1403
1403
}
1404
1404
1405
+ // / Whether the given DC is a noescape-by-default context, i.e. not a property
1406
+ // / setter
1407
+ static bool isDefaultNoEscapeContext (const DeclContext *DC) {
1408
+ auto funcDecl = dyn_cast<FuncDecl>(DC);
1409
+ return !funcDecl || !funcDecl->isSetter ();
1410
+ }
1411
+
1412
+ // Hack to apply context-specific @escaping to an AST function type.
1413
+ static Type adjustFunctionExtInfo (DeclContext *DC,
1414
+ Type ty,
1415
+ TypeResolutionOptions options) {
1416
+ // Remember whether this is a function parameter.
1417
+ bool isFunctionParam =
1418
+ options.contains (TR_FunctionInput) ||
1419
+ options.contains (TR_ImmediateFunctionInput);
1420
+
1421
+ bool defaultNoEscape = isFunctionParam && isDefaultNoEscapeContext (DC);
1422
+
1423
+ // Desugar here
1424
+ auto *funcTy = ty->castTo <FunctionType>();
1425
+ auto extInfo = funcTy->getExtInfo ();
1426
+ if (defaultNoEscape && !extInfo.isNoEscape ()) {
1427
+ extInfo = extInfo.withNoEscape ();
1428
+
1429
+ // We lost the sugar to flip the isNoEscape bit
1430
+ return FunctionType::get (funcTy->getInput (), funcTy->getResult (), extInfo);
1431
+ }
1432
+
1433
+ // Note: original sugared type
1434
+ return ty;
1435
+ }
1436
+
1405
1437
// / \brief Returns a valid type or ErrorType in case of an error.
1406
1438
Type TypeChecker::resolveIdentifierType (
1407
1439
DeclContext *DC,
@@ -1432,6 +1464,11 @@ Type TypeChecker::resolveIdentifierType(
1432
1464
return ErrorType::get (Context);
1433
1465
}
1434
1466
1467
+ // Hack to apply context-specific @escaping to a typealias with an underlying
1468
+ // function type.
1469
+ if (result->is <FunctionType>())
1470
+ result = adjustFunctionExtInfo (DC, result, options);
1471
+
1435
1472
// We allow a type to conform to a protocol that is less available than
1436
1473
// the type itself. This enables a type to retroactively model or directly
1437
1474
// conform to a protocol only available on newer OSes and yet still be used on
@@ -1637,29 +1674,20 @@ Type TypeChecker::resolveType(TypeRepr *TyR, DeclContext *DC,
1637
1674
return result;
1638
1675
}
1639
1676
1640
- // / Whether the given DC is a noescape-by-default context, i.e. not a property
1641
- // / setter
1642
- static bool isDefaultNoEscapeContext (const DeclContext *DC) {
1643
- auto funcDecl = dyn_cast<FuncDecl>(DC);
1644
- return !funcDecl || !funcDecl->isSetter ();
1645
- }
1646
-
1647
1677
Type TypeResolver::resolveType (TypeRepr *repr, TypeResolutionOptions options) {
1648
1678
assert (repr && " Cannot validate null TypeReprs!" );
1649
1679
1650
1680
// If we know the type representation is invalid, just return an
1651
1681
// error type.
1652
1682
if (repr->isInvalid ()) return ErrorType::get (TC.Context );
1653
1683
1654
- // Remember whether this is a function parameter.
1655
- bool isFunctionParam =
1656
- options.contains (TR_FunctionInput) ||
1657
- options.contains (TR_ImmediateFunctionInput);
1658
-
1659
1684
// Strip the "is function input" bits unless this is a type that knows about
1660
1685
// them.
1661
- if (!isa<InOutTypeRepr>(repr) && !isa<TupleTypeRepr>(repr) &&
1662
- !isa<AttributedTypeRepr>(repr)) {
1686
+ if (!isa<InOutTypeRepr>(repr) &&
1687
+ !isa<TupleTypeRepr>(repr) &&
1688
+ !isa<AttributedTypeRepr>(repr) &&
1689
+ !isa<FunctionTypeRepr>(repr) &&
1690
+ !isa<IdentTypeRepr>(repr)) {
1663
1691
options -= TR_ImmediateFunctionInput;
1664
1692
options -= TR_FunctionInput;
1665
1693
}
@@ -1686,11 +1714,10 @@ Type TypeResolver::resolveType(TypeRepr *repr, TypeResolutionOptions options) {
1686
1714
case TypeReprKind::Function:
1687
1715
if (!(options & TR_SILType)) {
1688
1716
// Default non-escaping for closure parameters
1689
- auto info = AnyFunctionType::ExtInfo ().withNoEscape (
1690
- isFunctionParam &&
1691
- isDefaultNoEscapeContext (DC));
1692
- return resolveASTFunctionType (cast<FunctionTypeRepr>(repr), options,
1693
- info);
1717
+ auto result = resolveASTFunctionType (cast<FunctionTypeRepr>(repr), options);
1718
+ if (result && result->is <FunctionType>())
1719
+ return adjustFunctionExtInfo (DC, result, options);
1720
+ return result;
1694
1721
}
1695
1722
return resolveSILFunctionType (cast<FunctionTypeRepr>(repr), options);
1696
1723
@@ -1747,8 +1774,6 @@ Type TypeResolver::resolveAttributedType(TypeAttributes &attrs,
1747
1774
bool isFunctionParam =
1748
1775
options.contains (TR_FunctionInput) ||
1749
1776
options.contains (TR_ImmediateFunctionInput);
1750
- options -= TR_ImmediateFunctionInput;
1751
- options -= TR_FunctionInput;
1752
1777
1753
1778
// The type we're working with, in case we want to build it differently
1754
1779
// based on the attributes we see.
@@ -1772,7 +1797,11 @@ Type TypeResolver::resolveAttributedType(TypeAttributes &attrs,
1772
1797
if (base) {
1773
1798
Optional<MetatypeRepresentation> storedRepr;
1774
1799
// The instance type is not a SIL type.
1775
- auto instanceOptions = options - TR_SILType;
1800
+ auto instanceOptions = options;
1801
+ instanceOptions -= TR_SILType;
1802
+ instanceOptions -= TR_ImmediateFunctionInput;
1803
+ instanceOptions -= TR_FunctionInput;
1804
+
1776
1805
auto instanceTy = resolveType (base, instanceOptions);
1777
1806
if (!instanceTy || instanceTy->is <ErrorType>())
1778
1807
return instanceTy;
@@ -1901,10 +1930,6 @@ Type TypeResolver::resolveAttributedType(TypeAttributes &attrs,
1901
1930
1902
1931
ty = resolveSILFunctionType (fnRepr, options, extInfo, calleeConvention);
1903
1932
if (!ty || ty->is <ErrorType>()) return ty;
1904
-
1905
- for (auto i : FunctionAttrs)
1906
- attrs.clearAttribute (i);
1907
- attrs.convention = None;
1908
1933
} else if (hasFunctionAttr && fnRepr) {
1909
1934
1910
1935
FunctionType::Representation rep = FunctionType::Representation::Swift;
@@ -1948,29 +1973,54 @@ Type TypeResolver::resolveAttributedType(TypeAttributes &attrs,
1948
1973
.fixItReplace (resultRange, " Never" );
1949
1974
}
1950
1975
1951
- bool defaultNoEscape = false ;
1952
- if (isFunctionParam && !attrs.has (TAK_escaping)) {
1953
- defaultNoEscape = isDefaultNoEscapeContext (DC);
1954
- }
1955
-
1956
- if (isFunctionParam && attrs.has (TAK_noescape) &&
1957
- isDefaultNoEscapeContext (DC)) {
1976
+ if (attrs.has (TAK_noescape)) {
1958
1977
// FIXME: diagnostic to tell user this is redundant and drop it
1959
1978
}
1960
1979
1961
1980
// Resolve the function type directly with these attributes.
1962
1981
FunctionType::ExtInfo extInfo (rep,
1963
1982
attrs.has (TAK_autoclosure),
1964
- defaultNoEscape | attrs.has (TAK_noescape),
1983
+ attrs.has (TAK_noescape),
1965
1984
fnRepr->throws ());
1966
1985
1967
1986
ty = resolveASTFunctionType (fnRepr, options, extInfo);
1968
1987
if (!ty || ty->is <ErrorType>()) return ty;
1988
+ }
1969
1989
1970
- for (auto i : FunctionAttrs)
1971
- attrs.clearAttribute (i);
1972
- attrs.convention = None;
1973
- } else if (hasFunctionAttr) {
1990
+ auto instanceOptions = options;
1991
+ instanceOptions -= TR_ImmediateFunctionInput;
1992
+ instanceOptions -= TR_FunctionInput;
1993
+
1994
+ // If we didn't build the type differently above, we might have
1995
+ // a typealias pointing at a function type with the @escaping
1996
+ // attribute. Resolve the type as if it were in non-parameter
1997
+ // context, and then set isNoEscape if @escaping is not present.
1998
+ if (!ty) ty = resolveType (repr, instanceOptions);
1999
+ if (!ty || ty->is <ErrorType>()) return ty;
2000
+
2001
+ // Handle @escaping
2002
+ if (hasFunctionAttr && ty->is <FunctionType>()) {
2003
+ if (attrs.has (TAK_escaping)) {
2004
+ // The attribute is meaningless except on parameter types.
2005
+ if (!isFunctionParam) {
2006
+ auto &SM = TC.Context .SourceMgr ;
2007
+ auto loc = attrs.getLoc (TAK_escaping);
2008
+ auto attrRange = SourceRange (
2009
+ loc.getAdvancedLoc (-1 ),
2010
+ Lexer::getLocForEndOfToken (SM, loc));
2011
+
2012
+ TC.diagnose (loc, diag::escaping_function_type)
2013
+ .fixItRemove (attrRange);
2014
+ }
2015
+
2016
+ attrs.clearAttribute (TAK_escaping);
2017
+ } else {
2018
+ // No attribute; set the isNoEscape bit if we're in parameter context.
2019
+ ty = adjustFunctionExtInfo (DC, ty, options);
2020
+ }
2021
+ }
2022
+
2023
+ if (hasFunctionAttr && !fnRepr) {
1974
2024
// @autoclosure usually auto-implies @noescape, don't complain about both
1975
2025
// of them.
1976
2026
if (attrs.has (TAK_autoclosure))
@@ -1983,11 +2033,11 @@ Type TypeResolver::resolveAttributedType(TypeAttributes &attrs,
1983
2033
attrs.clearAttribute (i);
1984
2034
}
1985
2035
}
1986
- }
1987
-
1988
- // If we didn't build the type differently above, build it normally now.
1989
- if (!ty) ty = resolveType (repr, options) ;
1990
- if (!ty || ty-> is <ErrorType>()) return ty;
2036
+ } else if (hasFunctionAttr && fnRepr) {
2037
+ for ( auto i : FunctionAttrs)
2038
+ attrs. clearAttribute (i);
2039
+ attrs. convention = None ;
2040
+ }
1991
2041
1992
2042
// In SIL, handle @opened (n), which creates an existential archetype.
1993
2043
if (attrs.has (TAK_opened)) {
@@ -2036,6 +2086,9 @@ Type TypeResolver::resolveAttributedType(TypeAttributes &attrs,
2036
2086
Type TypeResolver::resolveASTFunctionType (FunctionTypeRepr *repr,
2037
2087
TypeResolutionOptions options,
2038
2088
FunctionType::ExtInfo extInfo) {
2089
+ options -= TR_ImmediateFunctionInput;
2090
+ options -= TR_FunctionInput;
2091
+
2039
2092
Type inputTy = resolveType (repr->getArgsTypeRepr (),
2040
2093
options | TR_ImmediateFunctionInput);
2041
2094
if (!inputTy || inputTy->is <ErrorType>()) return inputTy;
@@ -2100,6 +2153,9 @@ Type TypeResolver::resolveSILFunctionType(FunctionTypeRepr *repr,
2100
2153
TypeResolutionOptions options,
2101
2154
SILFunctionType::ExtInfo extInfo,
2102
2155
ParameterConvention callee) {
2156
+ options -= TR_ImmediateFunctionInput;
2157
+ options -= TR_FunctionInput;
2158
+
2103
2159
bool hasError = false ;
2104
2160
2105
2161
SmallVector<SILParameterInfo, 4 > params;
@@ -2428,9 +2484,12 @@ Type TypeResolver::resolveTupleType(TupleTypeRepr *repr,
2428
2484
2429
2485
// If this is the top level of a function input list, peel off the
2430
2486
// ImmediateFunctionInput marker and install a FunctionInput one instead.
2431
- auto elementOptions = withoutContext (options);
2432
- if (options & TR_ImmediateFunctionInput)
2433
- elementOptions |= TR_FunctionInput;
2487
+ auto elementOptions = options;
2488
+ if (!repr->isParenType ()) {
2489
+ elementOptions = withoutContext (elementOptions);
2490
+ if (options & TR_ImmediateFunctionInput)
2491
+ elementOptions |= TR_FunctionInput;
2492
+ }
2434
2493
2435
2494
for (auto tyR : repr->getElements ()) {
2436
2495
NamedTypeRepr *namedTyR = dyn_cast<NamedTypeRepr>(tyR);
0 commit comments