Could borrow checking with origins unblock sound specialization
bjorn3:
Because it would require needlessly duplicating functions for every instantiation
No, it wouldn't. Under refined proposal (dropping same origin dispatch), the solver makes the specialization decision before lifetime erasure and bakes it into MIR as a direct function call. Codegen never looks at lifetimes to decide anything.
No function body is ever duplicated based on lifetimes. If a generic function has T: 'static in its where clause, the solver picks the specialized impl for every call into that function, because every T entering it is 'static by construction. One copy per concrete type, same as today. If the function doesn't have the bound, the solver falls back to the default. Also one copy. There's no case where the monomorphizer produces two copies differing only in lifetime. @robofinch raised valid point though that this would "expose" internal workings of the borrow checker to the actual code execution.
bjorn3:
And it is incompatible with HRTB
It is compatible: inside takes_callback(f: for<'a> fn(&'a u8)), the solver sees for<'a>, which means "must work for all lifetimes." There's no 'static bound, no concrete lifetime visible. The solver falls back to the default impl which is one function body. The HRTB case is just another instance of "generic context where the solver doesn't have the information, so it uses the default." The single function pointer is never asked to behave differently for different lifetimes.
Just to reiterate:
Serhii:
We are not demanding that codegen monomorphizes on all origins in general. Origins participate in specialization dispatch only in the three narrow cases listed below (
'static, same-origin, and explicitly declared outlives bounds).
Or did I miss something?
Discussion in the ATmosphere