@@ -3827,16 +3827,29 @@ private Type invokedClosureFnTypeAt(InvokedClosureExpr ce, TypePath path) {
38273827 _, path , result )
38283828}
38293829
3830+ /**
3831+ * Gets the root type of a closure.
3832+ *
3833+ * We model closures as `dyn Fn` trait object types. A closure might implement
3834+ * only `Fn`, `FnMut`, or `FnOnce`. But since `Fn` is a subtrait of the others,
3835+ * giving closures the type `dyn Fn` works well in practice -- even if not
3836+ * entirely accurate.
3837+ */
3838+ private DynTraitType closureRootType ( ) {
3839+ result = TDynTraitType ( any ( FnTrait t ) ) // always exists because of the mention in `builtins/mentions.rs`
3840+ }
3841+
38303842/** Gets the path to a closure's return type. */
38313843private TypePath closureReturnPath ( ) {
3832- result = TypePath:: singleton ( getDynTraitTypeParameter ( any ( FnOnceTrait t ) .getOutputType ( ) ) )
3844+ result =
3845+ TypePath:: singleton ( TDynTraitTypeParameter ( any ( FnTrait t ) , any ( FnOnceTrait t ) .getOutputType ( ) ) )
38333846}
38343847
3835- /** Gets the path to a closure with arity `arity`s `index`th parameter type. */
3848+ /** Gets the path to a closure with arity `arity`' s `index`th parameter type. */
38363849pragma [ nomagic]
38373850private TypePath closureParameterPath ( int arity , int index ) {
38383851 result =
3839- TypePath:: cons ( TDynTraitTypeParameter ( _, any ( FnOnceTrait t ) .getTypeParam ( ) ) ,
3852+ TypePath:: cons ( TDynTraitTypeParameter ( _, any ( FnTrait t ) .getTypeParam ( ) ) ,
38403853 TypePath:: singleton ( getTupleTypeParameter ( arity , index ) ) )
38413854}
38423855
@@ -3874,9 +3887,7 @@ private Type inferDynamicCallExprType(Expr n, TypePath path) {
38743887 or
38753888 // _If_ the invoked expression has the type of a closure, then we propagate
38763889 // the surrounding types into the closure.
3877- exists ( int arity , TypePath path0 |
3878- ce .getTypeAt ( TypePath:: nil ( ) ) .( DynTraitType ) .getTrait ( ) instanceof FnOnceTrait
3879- |
3890+ exists ( int arity , TypePath path0 | ce .getTypeAt ( TypePath:: nil ( ) ) = closureRootType ( ) |
38803891 // Propagate the type of arguments to the parameter types of closure
38813892 exists ( int index , ArgList args |
38823893 n = ce and
@@ -3900,10 +3911,10 @@ private Type inferClosureExprType(AstNode n, TypePath path) {
39003911 exists ( ClosureExpr ce |
39013912 n = ce and
39023913 path .isEmpty ( ) and
3903- result = TDynTraitType ( any ( FnOnceTrait t ) ) // always exists because of the mention in `builtins/mentions.rs`
3914+ result = closureRootType ( )
39043915 or
39053916 n = ce and
3906- path = TypePath:: singleton ( TDynTraitTypeParameter ( _, any ( FnOnceTrait t ) .getTypeParam ( ) ) ) and
3917+ path = TypePath:: singleton ( TDynTraitTypeParameter ( _, any ( FnTrait t ) .getTypeParam ( ) ) ) and
39073918 result .( TupleType ) .getArity ( ) = ce .getNumberOfParams ( )
39083919 or
39093920 // Propagate return type annotation to body
0 commit comments