-
Notifications
You must be signed in to change notification settings - Fork 213
Specify that an implicit forwarder is generated for covariant-by-class, *and* for covariant-by-declaration #925
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
Is this strictly a specification issue or is there implementation work implied? |
The topic is that it is in some cases unsound to inherit an implementation, and we have no specification text indicating that this is sometimes an error, and sometimes we require the implementations to generate a forwarding method that performs the check. The current specification actually (but tacitly) implies that we would always generate a forwarding method if needed. So we have a clear specification-or-implementation issue at hand: Either we need to say when it's an error, or we need to ask tool teams to generate those extra forwarding stubs. But we decided (here) to make it an error when the reason to need the dynamic check is that a parameter is covariant-by-declaration. So I believe that we can say that there definitely is a specification element to this issue. For the implementation effort, we'd certainly look at existing tests. Considering the tests in
The test
|
Spec update in #1770. Tests https://dart-review.googlesource.com/c/sdk/+/208504. Discussion still ongoing. |
Closing: The language team decided that the error should be eliminated, and instead the correct behavior is to generate a forwarding stub such that the required dynamic checks are performed. Cf. #47072. |
[Edit Sep 2021: Said forwarders have actually been generated for a while by the CFE; the language team decided that it should then be allowed, so the CFE does not need to report the error. Changed the title to reflect this update. The implementation is handled in dart-lang/sdk#47072.]
Cf. this comment, the language team decided that it is a compile-time error to inherit a method implementation
C.f
that has a parameterp
which is not covariant into a classD
such that the member signature off
in the interface ofD
has the modifiercovariant
onp
(which just means thatp
is covariant-by-declaration as seen fromD
).But it is not an error when
p
is covariant-by-class as seen fromD
.Here is an example of the first situation:
Here is an example of the second situation, involving covariance-by-class:
One way to see what is going on is to consider the implementation: In the first example, it is unsound for
C.f
to be used directly as the implementation ofD.f
. This is becauseD.f
may be called with an actual argument whose static type isA
, and it is up to the implementation ofD.f
to check that it is actually aB
, but the declaration ofC.f
has no information to justify the addition of such a dynamic check to the body.In the second example the same soundness problem arises, but because of the actual usage of code with this structure we decided that we would handle the soundness issue by generating a forwarding stub
D.f
which checks the dynamic type of the actual argument and then invokesC.f
.A question arises in the situation where a parameter is covariant-by-class as well as covariant-by-declaration:
In this situation the fact that
x
is covariant-by-class inI
justifies the generation of a forwarding stub, but note that the stub should check that the actual argumentis B
and then forward by callingsuper.f(x)
, such that the invocation ofC.f
is sound without further argument type checks.This mechanism is not currently specified: The language specification tacitly implies that a forwarding stub is generated in all cases (because otherwise a soundness issue would arise, and there is no explicit language making any of the cases an error).
Additional related issues: dart-lang/sdk#31580, dart-lang/sdk#31596, dart-lang/sdk#34329, dart-lang/sdk#41371.
The text was updated successfully, but these errors were encountered: