Hi SIL experts,
I wonder how to reabstract values from type A to type B during SILGen?
A: $(Float) -> (Float, @owned @callee_guaranteed (Float) -> Float) B: $(Float) -> (Float, @owned @callee_guaranteed (@in_guaranteed Float) -> @out Float)
The main difficulty: SILGen reabstraction utilities involve AST types and abstraction patterns, not SIL types. There is a corresponding AST type and abstraction pattern for B, but they are simply
(Float) -> (Float, (Float) -> Float).
I want to force the returned function type to be maximally indirect
(@in_guaranteed Float) -> @out Float. What is the best way to do this?
- Opaque abstraction pattern is not appropriate because that causes the entire function type to be maximally indirect, not just the returned function type:
$(@in_guaranteed Float) -> @out (Float, @callee_guaranteed (@in_guaranteed Float) -> @out Float).
- We could adapt the rest of our infrastructure to work with entirely maximally indirect function types, but I wonder if we can avoid this if possible for efficiency/simplicity.
- Invariants are that arguments of B can have same abstraction as arguments of B, and returned tuple type of B can always be direct.
- We could manually construct a generic function type
<T>(Float) -> (Float, (T) -> T)and use that as an abstraction pattern for type B, but this feels quite hacky.
Context: I'm working on the differentiable programming project.
- Derivative functions return a "linear approximation function".
- We want to standardize all "returned linear approximation function types" to be maximally indirect in SIL to fix a sleuth of abstraction mismatch bugs - see issue description here for more details.
Any help would be appreciated!