The orphan rules currently forbid trait impls of this form:
impl<T: LocalTrait> ForeignTrait for T { /* ... */ }
But, we could allow it without risking incoherence as long as the crate only implements LocalTrait
for local types.
The orphan rules currently forbid trait impls of this form:
impl<T: LocalTrait> ForeignTrait for T { /* ... */ }
But, we could allow it without risking incoherence as long as the crate only implements LocalTrait
for local types.
It would have the same pitfalls as a blanket impl impl<T> LocalTrait for T
, of course, meaning that such an impl can't be added except in the version that introduces LocalTrait
, but this does seem reasonably useful.
On the other hand, though, Rust generally prefers to avoid reasoning about involved impl disjointness, as that can easily introduce errors at a distance.
A different idea that I had previously is to introduce #[fundamental] trait
, with the logical semantics being that adding impls of the trait is considered a breaking change just like removing an impl is. This means that a blanket impl over a fundamental trait can be treated for the purpose of coherence to be identical to an impl using each impl block for the fundamental trait. (Well, at least if it's also sealed; I haven't fully considered what coherence reasoning needs to look like when downstream crates can impl the fundamental trait for their types.)
That already exists (unstably); Sized
and the Fn
traits are fundamental, and coherence takes that into account.
To go well this would also need to keep LocalTrait
from having blanket impls from OtherForeignTrait
and to keep other foreign crates from implementing LocalTrait
on their own types, so I think it needs something on the trait too in order to allowed.
IIRC the #[sealed] trait
discussions talked about potentially doing something like this.
No, it should not prevent this. Downstream crates should be able to implement LocalTrait
for their own types, as long as they don’t also provide a conflicting ForeignTrait
impl. (As @CAD97 said, the impl<T: LocalTrait> ForeignTrait for T
would be a breaking change to add except in the version that introduces LocalTrait
, but that’s fine.)
There doesn't seem to be a tracking issue for stabilising fundamental
. The linked issue from there is a closed issue about the problem, not the tracking issue.
Is it intended to be perma-unstable for some reason? If so why (I could see custom smart pointers wanting to opt in)?
This tracking issue exists, but I don't know the answers to your questions.