@@ -8948,7 +8948,7 @@ namespace ts {
8948
8948
8949
8949
if (isSimpleTypeRelatedTo(source, target, relation, reportErrors ? reportError : undefined)) return Ternary.True;
8950
8950
8951
- if (source.flags & TypeFlags.MarkerType && target.flags & TypeFlags.MarkerType) {
8951
+ if (source.flags & TypeFlags.MarkerType && target.flags & TypeFlags.MarkerType && !(source.flags & TypeFlags.Object || target.flags & TypeFlags.Object) ) {
8952
8952
return source === markerSubType && target === markerSuperType ? Ternary.True : Ternary.False;
8953
8953
}
8954
8954
@@ -9414,9 +9414,11 @@ namespace ts {
9414
9414
}
9415
9415
}
9416
9416
else {
9417
- if (getObjectFlags(source) & ObjectFlags.Reference && getObjectFlags(target) & ObjectFlags.Reference && (<TypeReference>source).target === (<TypeReference>target).target) {
9418
- // We have type references to the same generic type. Obtain the variance information for the
9419
- // type parameters and relate the type arguments accordingly.
9417
+ if (getObjectFlags(source) & ObjectFlags.Reference && getObjectFlags(target) & ObjectFlags.Reference && (<TypeReference>source).target === (<TypeReference>target).target &&
9418
+ !(source.flags & TypeFlags.MarkerType || target.flags & TypeFlags.MarkerType)) {
9419
+ // We have type references to the same generic type, and the type references are not marker
9420
+ // type references (which we always compare structurally). Obtain the variance information
9421
+ // for the type parameters and relate the type arguments accordingly.
9420
9422
const variances = getVariances((<TypeReference>source).target);
9421
9423
if (result = typeArgumentsRelatedTo(<TypeReference>source, <TypeReference>target, variances, reportErrors)) {
9422
9424
return result;
@@ -9841,8 +9843,12 @@ namespace ts {
9841
9843
}
9842
9844
}
9843
9845
9844
- function getVarianceType(type: GenericType, source: TypeParameter, target: Type) {
9845
- return createTypeReference(type, map(type.typeParameters, t => t === source ? target : t));
9846
+ // Return a type reference where the source type parameter is replaced with the target marker
9847
+ // type, and flag the result as a marker type reference.
9848
+ function getMarkerTypeReference(type: GenericType, source: TypeParameter, target: Type) {
9849
+ const result = createTypeReference(type, map(type.typeParameters, t => t === source ? target : t));
9850
+ result.flags |= TypeFlags.MarkerType;
9851
+ return result;
9846
9852
}
9847
9853
9848
9854
// Return an array containing the variance of each type parameter. The variance is effectively
@@ -9867,15 +9873,15 @@ namespace ts {
9867
9873
// We first compare instantiations where the type parameter is replaced with
9868
9874
// marker types that have a known subtype relationship. From this we can infer
9869
9875
// invariance, covariance, contravariance or bivariance.
9870
- const typeWithSuper = getVarianceType (type, tp, markerSuperType);
9871
- const typeWithSub = getVarianceType (type, tp, markerSubType);
9876
+ const typeWithSuper = getMarkerTypeReference (type, tp, markerSuperType);
9877
+ const typeWithSub = getMarkerTypeReference (type, tp, markerSubType);
9872
9878
let variance = (isTypeAssignableTo(typeWithSub, typeWithSuper) ? Variance.Covariant : 0) |
9873
9879
(isTypeAssignableTo(typeWithSuper, typeWithSub) ? Variance.Contravariant : 0);
9874
9880
// If the instantiations appear to be related bivariantly, it may be because the
9875
9881
// type parameter is omnivariant (i.e. it isn't witnessed anywhere in the generic
9876
9882
// type). To determine this we compare instantiations where the type parameter is
9877
9883
// replaced with marker types that are known to be unrelated.
9878
- if (variance === Variance.Bivariant && isTypeAssignableTo(getVarianceType (type, tp, markerOtherType), typeWithSuper)) {
9884
+ if (variance === Variance.Bivariant && isTypeAssignableTo(getMarkerTypeReference (type, tp, markerOtherType), typeWithSuper)) {
9879
9885
variance = Variance.Omnivariant;
9880
9886
}
9881
9887
variances.push(variance);
0 commit comments