@@ -3527,10 +3527,17 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> {
35273527 return Ok(param_type);
35283528 }
35293529
3530- Type::KnownInstance(known_instance)
3530+ Type::KnownInstance(known_instance @ KnownInstanceType::TypeVar(typevar) )
35313531 if known_instance.class(self.db()) == KnownClass::ParamSpec =>
35323532 {
3533- // TODO: Emit diagnostic: "ParamSpec "P" is unbound"
3533+ if let Some(diagnostic_builder) =
3534+ self.context.report_lint(&INVALID_TYPE_FORM, expr)
3535+ {
3536+ diagnostic_builder.into_diagnostic(format_args!(
3537+ "ParamSpec `{}` is unbound",
3538+ typevar.name(self.db())
3539+ ));
3540+ }
35343541 return Err(());
35353542 }
35363543
@@ -11609,6 +11616,17 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> {
1160911616 generic_context: GenericContext<'db>,
1161011617 specialize: impl FnOnce(&[Option<Type<'db>>]) -> Type<'db>,
1161111618 ) -> Type<'db> {
11619+ enum ExplicitSpecializationError {
11620+ InvalidParamSpec,
11621+ UnsatisfiedBound,
11622+ UnsatisfiedConstraints,
11623+ /// These two errors override the errors above, causing all specializations to be `Unknown`.
11624+ MissingTypeVars,
11625+ TooManyArguments,
11626+ /// This error overrides the errors above, causing the type itself to be `Unknown`.
11627+ NonGeneric,
11628+ }
11629+
1161211630 fn add_typevar_definition<'db>(
1161311631 db: &'db dyn Db,
1161411632 diagnostic: &mut Diagnostic,
@@ -11661,7 +11679,7 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> {
1166111679 }
1166211680 };
1166311681
11664- let mut has_error = false ;
11682+ let mut error: Option<ExplicitSpecializationError> = None ;
1166511683
1166611684 for (index, item) in typevars.zip_longest(type_arguments.iter()).enumerate() {
1166711685 match item {
@@ -11677,8 +11695,8 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> {
1167711695 ) {
1167811696 Ok(paramspec_value) => paramspec_value,
1167911697 Err(()) => {
11680- has_error = true ;
11681- Type::unknown()
11698+ error = Some(ExplicitSpecializationError::InvalidParamSpec) ;
11699+ Type::paramspec_value_callable(db, Parameters:: unknown() )
1168211700 }
1168311701 }
1168411702 } else {
@@ -11710,8 +11728,10 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> {
1171011728 ));
1171111729 add_typevar_definition(db, &mut diagnostic, typevar);
1171211730 }
11713- has_error = true;
11714- continue;
11731+ error = Some(ExplicitSpecializationError::UnsatisfiedBound);
11732+ specialization_types.push(Some(Type::unknown()));
11733+ } else {
11734+ specialization_types.push(Some(provided_type));
1171511735 }
1171611736 }
1171711737 Some(TypeVarBoundOrConstraints::Constraints(constraints)) => {
@@ -11744,14 +11764,16 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> {
1174411764 ));
1174511765 add_typevar_definition(db, &mut diagnostic, typevar);
1174611766 }
11747- has_error = true;
11748- continue;
11767+ error = Some(ExplicitSpecializationError::UnsatisfiedConstraints);
11768+ specialization_types.push(Some(Type::unknown()));
11769+ } else {
11770+ specialization_types.push(Some(provided_type));
1174911771 }
1175011772 }
11751- None => {}
11773+ None => {
11774+ specialization_types.push(Some(provided_type));
11775+ }
1175211776 }
11753-
11754- specialization_types.push(Some(provided_type));
1175511777 }
1175611778 EitherOrBoth::Left(typevar) => {
1175711779 if typevar.default_type(db).is_none() {
@@ -11786,33 +11808,53 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> {
1178611808 }
1178711809 ));
1178811810 }
11789- has_error = true ;
11811+ error = Some(ExplicitSpecializationError::MissingTypeVars) ;
1179011812 }
1179111813
1179211814 if let Some(first_excess_type_argument_index) = first_excess_type_argument_index {
11793- let node = get_node(first_excess_type_argument_index);
11794- if let Some(builder) = self.context.report_lint(&INVALID_TYPE_ARGUMENTS, node) {
11795- let description = CallableDescription::new(db, value_ty);
11796- builder.into_diagnostic(format_args!(
11797- "Too many type arguments{}: expected {}, got {}",
11798- if let Some(CallableDescription { kind, name }) = description {
11799- format!(" to {kind} `{name}`")
11800- } else {
11801- String::new()
11802- },
11803- if typevar_with_defaults == 0 {
11804- format!("{typevars_len}")
11815+ if typevars_len == 0 {
11816+ // Type parameter list cannot be empty, so if we reach here, `value_ty` is not a generic type.
11817+ if let Some(builder) = self
11818+ .context
11819+ .report_lint(&NON_SUBSCRIPTABLE, &*subscript.value)
11820+ {
11821+ if value_ty.is_generic_alias() {
11822+ builder.into_diagnostic(format_args!(
11823+ "Cannot subscript non-generic type alias: `{}` is already specialized",
11824+ value_ty.display(db),
11825+ ));
1180511826 } else {
11806- format!(
11807- "between {} and {}",
11808- typevars_len - typevar_with_defaults,
11809- typevars_len
11810- )
11811- },
11812- type_arguments.len(),
11813- ));
11827+ builder.into_diagnostic(format_args!(
11828+ "Cannot subscript non-generic type alias"
11829+ ));
11830+ }
11831+ }
11832+ error = Some(ExplicitSpecializationError::NonGeneric);
11833+ } else {
11834+ let node = get_node(first_excess_type_argument_index);
11835+ if let Some(builder) = self.context.report_lint(&INVALID_TYPE_ARGUMENTS, node) {
11836+ let description = CallableDescription::new(db, value_ty);
11837+ builder.into_diagnostic(format_args!(
11838+ "Too many type arguments{}: expected {}, got {}",
11839+ if let Some(CallableDescription { kind, name }) = description {
11840+ format!(" to {kind} `{name}`")
11841+ } else {
11842+ String::new()
11843+ },
11844+ if typevar_with_defaults == 0 {
11845+ format!("{typevars_len}")
11846+ } else {
11847+ format!(
11848+ "between {} and {}",
11849+ typevars_len - typevar_with_defaults,
11850+ typevars_len
11851+ )
11852+ },
11853+ type_arguments.len(),
11854+ ));
11855+ }
11856+ error = Some(ExplicitSpecializationError::TooManyArguments);
1181411857 }
11815- has_error = true;
1181611858 }
1181711859
1181811860 if store_inferred_type_arguments {
@@ -11822,21 +11864,31 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> {
1182211864 );
1182311865 }
1182411866
11825- if has_error {
11826- let unknowns = generic_context
11827- .variables(self.db())
11828- .map(|typevar| {
11829- Some(if typevar.is_paramspec(db) {
11830- Type::paramspec_value_callable(db, Parameters::unknown())
11831- } else {
11832- Type::unknown()
11867+ match error {
11868+ Some(ExplicitSpecializationError::NonGeneric) => Type::unknown(),
11869+ Some(
11870+ ExplicitSpecializationError::MissingTypeVars
11871+ | ExplicitSpecializationError::TooManyArguments,
11872+ ) => {
11873+ let unknowns = generic_context
11874+ .variables(self.db())
11875+ .map(|typevar| {
11876+ Some(if typevar.is_paramspec(db) {
11877+ Type::paramspec_value_callable(db, Parameters::unknown())
11878+ } else {
11879+ Type::unknown()
11880+ })
1183311881 })
11834- })
11835- .collect::<Vec<_>>();
11836- return specialize(&unknowns);
11882+ .collect::<Vec<_>>();
11883+ specialize(&unknowns)
11884+ }
11885+ Some(
11886+ ExplicitSpecializationError::UnsatisfiedBound
11887+ | ExplicitSpecializationError::UnsatisfiedConstraints
11888+ | ExplicitSpecializationError::InvalidParamSpec,
11889+ )
11890+ | None => specialize(&specialization_types),
1183711891 }
11838-
11839- specialize(&specialization_types)
1184011892 }
1184111893
1184211894 fn infer_subscript_expression_types(
0 commit comments