Commit Graph

126 Commits

Author SHA1 Message Date
John McCall
0c3c62bd73 [NFC] Rename isPackExpansion -> isOrigPackExpansion for clarity 2023-03-22 15:40:02 -04:00
John McCall
f99efc2f94 Fix unsafeGetSubstFieldType to propagate a substitution map in
whichever case it happens to be in.

This is a basic fix so that parallel walks on tuples and function
types in the substituted type will work .  Separately, though, I
do not think the places that use this really need to be passed an
orig type; this is used for computing type properties, and I am
not aware of any reason we should need an orig type to compute
type properties.  Additionally, the orig types computed by this
function are not really correct because of the substitution being
done in some cases, so it'd be very nice to rip this all out.
I'm not good to look into that right now, though.
2023-03-22 15:40:02 -04:00
John McCall
bbc682822a [NFC] Change the printing of AbstractionPattern to include the sub map 2023-03-22 15:40:02 -04:00
John McCall
5cf05f501b Implement arity reabstraction for closures 2023-03-21 22:23:45 -04:00
John McCall
5f1a669f2f [NFC] Change the existing client of forEachFunctionParam
Yeah, this is much cleaner.
2023-03-20 16:01:54 -04:00
John McCall
2e4ad65889 [NFC] Change forEachFunctionParam to only ignore the final orig parameter
and not also drop a subst parameter.

This turned out to be more convenient for certain clients (e.g. SILGenPoly)
than requiring the full subst param list to be passed in.  These clients
want to process the subst param list separately, and dropping self early
can be convenient for that.  The only fundamental reason we need this
flag is for working with the orig type, so just use it for that; clients
that need to use this feature can reasonably be expected to cooperate.
2023-03-20 13:36:40 -04:00
John McCall
2172c0ae52 [NFC] Provide a more generator-like interface for traversing orig+subst function parameters
This is necessary because the use patterns in SILGenPoly require
walking two orig+subst sequences in parallel, which poses problems
for a callback-centric design like the one I addded before.  An
inversion of control is necessary; this is basically a manual
coroutine.  But frankly it's a nicer interface than the callback
design, too; I switched the implementation of forEachFunctionParam
to use the generator just to avoid code duplication, but I might
try to remove it and switch all the clients over to the generator.
The main problems with the callback design are that (1) I wasn't
sure which values clients would want, and the result is that there
are a *lot* of parameters and (2) (relatedly) the types of those
parameters have to be written out explicitly, and some of them
are quite large.  The generator code is just much nicer.  Maybe
I can still give the generator a little unparameterized callback
to keep lexical loops simple.

I'll need to do this same thing for tuples.  One at a time.
2023-03-20 13:36:40 -04:00
John McCall
3342d67161 Fix the creation of substituted abstraction patterns for expansions 2023-03-17 22:07:10 -04:00
John McCall
72cc8dcb1e [NFC] Rewrite the subst-type extracttor to be a CanTypeVisitor 2023-03-16 15:56:46 -04:00
John McCall
f3e7daf478 [NFC] Remove the now-dead PackExpanded accessors from AbstractionPattern 2023-03-16 01:38:46 -04:00
John McCall
4499e3d055 [NFC] Introduce new APIs for traversing orig/subst parameters in parallel 2023-03-16 01:38:46 -04:00
John McCall
9ab4dc494c [NFC] Add better APIs for parallel destructuring of orig+subst types
As I've been iterating on this work, I've been gradually mulling these
over, and I think this is the way to go for now.  These should make it
a lot less cumbersome to write these kinds of traversals correctly.

The intent is to the sunset the existing expanded-components stuff
after I do a similar pass for function parameters.
2023-03-16 00:19:30 -04:00
Slava Pestov
783d9987f2 SIL: Introduce SameShape requirements in SubstFunctionTypePatternVisitor 2023-03-15 11:59:47 -04:00
Slava Pestov
3266a8254b SIL: Unwrap reference to value parameter packs in TypeConverter::getAbstractionPattern() 2023-03-13 19:04:15 -04:00
John McCall
a15a2e86fe Add a helper function for checking if a tuple AP contains expansions 2023-03-09 02:16:09 -05:00
John McCall
dc477a0fd2 Merge pull request #64167 from rjmccall/variadic-results
Implement the caller side of return types containing variadic packs
2023-03-07 11:20:46 -05:00
John McCall
81d9e6865a Add a couple convenience APIs for working with abstraction patterns 2023-03-07 03:15:31 -05:00
Holly Borla
fa3ffc6a44 [SILGen] Update a few callers of SubstitutionMap::get to use getSingletonPackExpansion,
and update variadic generics SILGen tests for the representation change.
2023-03-06 22:05:11 -08:00
John McCall
bd53f5d5df Allow AbstractionPattern to optionally carry substitutions
This allows the AP to answer questions like how many
elements/parameters in the substituted type correspond to
this pack expansion.

I've threaded this through a lot of cases for foreign patterns
that probably won't ever need it.
2023-02-24 15:02:09 -05:00
John McCall
d25a8aec8b Add explicit lowering for value packs and pack expansions.
- SILPackType carries whether the elements are stored directly
  in the pack, which we're not currently using in the lowering,
  but it's probably something we'll want in the final ABI.
  Having this also makes it clear that we're doing the right
  thing with substitution and element lowering.  I also toyed
  with making this a scalar type, which made it necessary in
  various places, although eventually I pulled back to the
  design where we always use packs as addresses.

- Pack boundaries are a core ABI concept, so the lowering has
  to wrap parameter pack expansions up as packs.  There are huge
  unimplemented holes here where the abstraction pattern will
  need to tell us how many elements to gather into the pack,
  but a naive approach is good enough to get things off the
  ground.

- Pack conventions are related to the existing parameter and
  result conventions, but they're different on enough grounds
  that they deserve to be separated.
2023-01-29 03:29:06 -05:00
Slava Pestov
38169afc06 SIL: Simplify SubstFunctionTypePatternVisitor 2022-12-08 20:07:16 -05:00
Slava Pestov
f9141e1aa1 SIL: Stub out type lowering of function types containing pack expansions 2022-12-06 14:15:07 -05:00
Erik Eckstein
ab1b343dad use new llvm::Optional API
`getValue` -> `value`
`getValueOr` -> `value_or`
`hasValue` -> `has_value`
`map` -> `transform`

The old API will be deprecated in the rebranch.
To avoid merge conflicts, use the new API already in the main branch.

rdar://102362022
2022-11-21 19:44:24 +01:00
Slava Pestov
09b061bd0d SIL: Preliminary type lowering for PackType and PackExpansionType 2022-11-08 19:09:07 -05:00
Holly Borla
38a2c8218b [Requirement] Rename RequirementKind::SameCount to SameShape. 2022-10-06 20:48:40 -07:00
Slava Pestov
5c32f2136e AST: Introduce RequirementKind::SameCount 2022-08-23 11:12:00 -04:00
Slava Pestov
9d96ed940f AST: Rename 'canonical wrt. generic signature' to 'reduced'
We had two notions of canonical types, one is the structural property
where it doesn't contain sugared types, the other one where it does
not contain reducible type parameters with respect to a generic
signature.

Rename the second one to a 'reduced type'.
2022-08-09 12:46:31 -04:00
Hamish Knight
9da53193da [AST] Remove ParameterTypeFlags from ParenType and TupleType
The last clients that relied on stashing parameter
type flags on these types are now gone.
2022-08-02 13:56:32 +01:00
Michael Gottesman
198b974622 Merge pull request #59859 from gottesmm/pr-276c4e4220a25490659a285e8b94a36bd28ffede
[no-implicit-copy] Rename SILMoveOnlyType -> SILMoveOnlyWrappedType.
2022-07-01 23:17:43 -07:00
Michael Gottesman
8f3fe63fed [no-implicit-copy] Rename SILMoveOnlyType -> SILMoveOnlyWrappedType.
Since I am beginning to prepare for adding real move only types to the language,
I am renaming everything that has to do with copyable types "move only wrapped"
values instead of move only. The hope is this reduces/prevents any confusion in
between the two.
2022-07-01 17:26:13 -07:00
Doug Gregor
bf9b4e3612 Merge pull request #59819 from jckarter/missing-sendable-conformance-in-subst-function-type
SIL: Allow missing Sendable conformances when building abstraction pattern for function type lowering.
2022-07-01 07:32:40 -07:00
Joe Groff
8a4743a525 SIL: Allow missing Sendable conformances when building abstraction pattern for function type lowering.
Fixes rdar://95979338.
2022-06-30 13:51:26 -07:00
Robert Widmann
ce4afc7e4d Recurse Into Existential Types With Generic Structure
Before the introduction of parameterized existential types, there
was no generic structure under these types. Now that there is, we'll
need to recurse into them to pick up any latent generic types
and lower them appropriately.

rdar://94320481
2022-06-18 12:36:50 -06:00
Michael Gottesman
8216a2a816 [move-only] Rename AbstractionPattern move only wrapper add/remove methods to match SILType's
Just forgot to change these when I changed the name of the SILType methods. In
summary:

1. withoutMoveOnly -> removingMoveOnlyWrapper
2. withMoveOnly -> addingMoveOnlyWrapper
2022-06-15 14:15:21 -07:00
zoecarver
9c32aace6c [nfc] Remove dead operator code pt. 1 2022-06-10 13:33:29 -07:00
Michael Gottesman
02759d150b [move-only] Add methods to AbstractionPattern to add/remove the move only bit.
The names are AbstractionPattern::with{,out}MoveOnly().
2022-06-03 11:27:16 -07:00
Robert Widmann
4efcb825f5 Unlock Opaque Types in Parameterized Protocols
Represent this in much the same way that collections do by creating an opaque value representing the source argument, and a conversion expression representing the destination argument.
2022-03-08 23:45:37 -08:00
Robert Widmann
e5bfda7c6e Merge pull request #40587 from CodaFi/substitute-teacher
Initial Semantics for Variadic Generics
2021-12-20 11:25:25 -08:00
Robert Widmann
06bc38f5a2 Model PackExpansion Types
A PackExpansionType is the interface type of the explicit expansion of a
corresponding set of variadic generic parameters.
Pack expansions are spelled as single-element tuples with a single variadic
component in most contexts except functions where they are allowed to appear without parentheses to match normal variadic declaration syntax.

```
func expand<T...>(_ xs: T...) -> (T...)
                        ~~~~     ~~~~~~
```

A pack expansion type comes equipped with a pattern type spelled before
the ellipses - `T` in the examples above. This pattern type is the subject
of the expansion of the pack that is tripped when its variadic generic
parameter is substituted for a `PackType`.
2021-12-16 00:34:09 -08:00
Robert Widmann
746aa1fb58 Model Pack Types
A pack type looks a lot like a tuple in the surface language, except there
is no way for the user to spell a pack. Pack types are created by the solver
when it encounters an apply of a variadic generic function, as in

```
func print<T...>(_ xs: T...) {}
// Creates a pack type <String, Int, String>
print("Macs say Hello in", 42, " different languages")
```

Pack types substituted into the variadic generic arguments of a
PackExpansionType "trip" the pack expansion and cause it to produce a
new pack type with the pack expansion pattern applied.

```
typealias Foo<T...> = (T?...)
Foo<Int, String, Int> // Forces expansion to (Int?, String?, Int?)
```
2021-12-16 00:25:34 -08:00
Slava Pestov
20a913d208 SIL: Workaround for GenericSignatureBuilder bug
The GSB will drop same-type requirements sometimes, when the
right hand side is smaller than the left. Change the order
when adding these requirements, which seems to work well
enough for my reduced testcase.

Also, ensure that everything works correctly with the
RequirementMachine, which doesn't have the same underlying
problems with same-type requirement handling.

Fixes rdar://86431977.
2021-12-15 23:17:39 -05:00
Joe Groff
5c404acbde SIL: More robust substituted function type lowering.
This change separates out the formation of the generic signature and
substitutions for a SIL substituted function type as a pre-pass
before doing the actual function type lowering. The only input we
really need to form this signature is the original abstraction pattern
that a type is being lowered against, and pre-computing it should make
the code less side-effecty and confusing. It also allows us to handle
generic nominal types in a more robust way; we transfer over all of
the nominal type requirements to the generalized generic signature,
then when recursively visiting the bindings, we same-type-constrain
the generic parameters used in those requirements to the newly-generalized
generic arguments. This ensures that the minimized signature preserves
any non-trivial requirements imposed by the nominal type, such as
conditional conformances on its type arguments, same-type constraints
among associated types, etc.

This approach does lead to less-than-optimal generalized generic
signatures getting generated, since nominal type generic arguments
get same-type-bound either to other generic arguments or fixed to
concrete types almost always. It would be useful to do a minimization
pass on the final generic signature to eliminate these unnecessary
generic arguments, but that can be done in a follow-up PR.
2021-11-10 12:45:34 -08:00
Robert Widmann
e545d7f760 Lift getCanonicalTypeInContext up to GenericSignature 2021-09-20 15:43:07 -07:00
Joe Groff
fdc0e08d60 SILGen: Emit literal closures at the abstraction level of their context.
Literal closures are only ever directly referenced in the context of the expression they're written in,
so it's wasteful to emit them at their fully-substituted calling convention and then reabstract them if
they're passed directly to a generic function. Avoid this by saving the abstraction pattern of the context
before emitting the closure, and then lowering its main entry point's calling convention at that
level of abstraction. Generalize some of the prolog/epilog code to handle converting arguments and returns
to the correct representation for a different abstraction level.
2021-09-09 13:42:02 -07:00
Joe Groff
3abe16f40f Revert "SILGen: Emit literal closures at the abstraction level of their context. [take 2]" (#39228) 2021-09-09 11:53:43 -05:00
Joe Groff
43506a29a2 SILGen: Emit literal closures at the abstraction level of their context.
Literal closures are only ever directly referenced in the context of the expression they're written in,
so it's wasteful to emit them at their fully-substituted calling convention and then reabstract them if
they're passed directly to a generic function. Avoid this by saving the abstraction pattern of the context
before emitting the closure, and then lowering its main entry point's calling convention at that
level of abstraction. Generalize some of the prolog/epilog code to handle converting arguments and returns
to the correct representation for a different abstraction level.
2021-09-07 11:55:29 -07:00
Holly Borla
86e1014399 Revert " SILGen: Emit literal closures at the abstraction level of their context." 2021-08-18 09:03:23 -07:00
Joe Groff
309500d4bf SILGen: Emit literal closures at the abstraction level of their context.
Literal closures are only ever directly referenced in the context of the expression they're written in,
so it's wasteful to emit them at their fully-substituted calling convention and then reabstract them if
they're passed directly to a generic function. Avoid this by saving the abstraction pattern of the context
before emitting the closure, and then lowering its main entry point's calling convention at that
level of abstraction. Generalize some of the prolog/epilog code to handle converting arguments and returns
to the correct representation for a different abstraction level.
2021-08-16 09:39:19 -07:00
Nate Chandler
e349fd0cae [SIL] Fixed return index for call-as-async (BOOL, Error, Value) case.
When converting an ObjC method type which is being called as async to a
Swift function type, some of the values passed to the ObjC method's
completion handler are converted to return values of the Swift function.
The flag and error parameters, however, if present, are ignored.

When abstracting the result type for the Swift method, the formal type
of the corresponding parameter in the ObjC method's completion handler
is used.  Digging out that parameter entails indexing into the
parameters of the completion handler.  Previously, the indexing logic
relied on the error appearing before the flag if both appeared before
the value of interest.  Here, the indexing is tweaked to check both
special indices for each possible index until the first that matches
neither is found.

rdar://81625544
2021-08-10 12:50:22 -07:00
nate-chandler
8345174bae Merge pull request #38370 from nate-chandler/rdar79383990
[SILGen] Used formal type when bridging completion handler arguments.
2021-07-26 10:57:49 -07:00