diff --git a/src/Lean/Elab/Extra.lean b/src/Lean/Elab/Extra.lean index 61edbb147a..9aab4b8135 100644 --- a/src/Lean/Elab/Extra.lean +++ b/src/Lean/Elab/Extra.lean @@ -26,12 +26,10 @@ private def throwForInFailure (forInInstance : Expr) : TermElabM Expr := @[builtin_term_elab forInMacro] def elabForIn : TermElab := fun stx expectedType? => do match stx with | `(for_in% $col $init $body) => - match (← isLocalIdent? col) with - | none => elabTerm (← `(let col := $col; for_in% col $init $body)) expectedType? - | some colFVar => tryPostponeIfNoneOrMVar expectedType? + let colE ← elabTerm col none let m ← getMonadForIn expectedType? - let colType ← inferType colFVar + let colType ← inferType colE let elemType ← mkFreshExprMVar (mkSort (mkLevelSucc (← mkFreshLevelMVar))) let forInInstance ← try mkAppM ``ForIn #[m, colType, elemType] @@ -42,7 +40,7 @@ private def throwForInFailure (forInInstance : Expr) : TermElabM Expr := let forInFn ← mkConst ``forIn elabAppArgs forInFn (namedArgs := #[{ name := `m, val := Arg.expr m}, { name := `α, val := Arg.expr elemType }, { name := `self, val := Arg.expr inst }]) - (args := #[Arg.stx col, Arg.stx init, Arg.stx body]) + (args := #[Arg.expr colE, Arg.stx init, Arg.stx body]) (expectedType? := expectedType?) (explicit := false) (ellipsis := false) (resultIsOutParamSupport := false) | .undef => tryPostpone; throwForInFailure forInInstance @@ -52,12 +50,10 @@ private def throwForInFailure (forInInstance : Expr) : TermElabM Expr := @[builtin_term_elab forInMacro'] def elabForIn' : TermElab := fun stx expectedType? => do match stx with | `(for_in'% $col $init $body) => - match (← isLocalIdent? col) with - | none => elabTerm (← `(let col := $col; for_in'% col $init $body)) expectedType? - | some colFVar => tryPostponeIfNoneOrMVar expectedType? + let colE ← elabTerm col none let m ← getMonadForIn expectedType? - let colType ← inferType colFVar + let colType ← inferType colE let elemType ← mkFreshExprMVar (mkSort (mkLevelSucc (← mkFreshLevelMVar))) let forInInstance ← try @@ -70,7 +66,7 @@ private def throwForInFailure (forInInstance : Expr) : TermElabM Expr := let forInFn ← mkConst ``forIn' elabAppArgs forInFn (namedArgs := #[{ name := `m, val := Arg.expr m}, { name := `α, val := Arg.expr elemType}, { name := `self, val := Arg.expr inst }]) - (args := #[Arg.expr colFVar, Arg.stx init, Arg.stx body]) + (args := #[Arg.expr colE, Arg.stx init, Arg.stx body]) (expectedType? := expectedType?) (explicit := false) (ellipsis := false) (resultIsOutParamSupport := false) | .undef => tryPostpone; throwForInFailure forInInstance diff --git a/tests/lean/run/forInColErr.lean b/tests/lean/run/forInColErr.lean new file mode 100644 index 0000000000..f75ecf3673 --- /dev/null +++ b/tests/lean/run/forInColErr.lean @@ -0,0 +1,79 @@ +set_option pp.mvars.anonymous false + +/-- +error: failed to construct 'ForIn' instance for collection + ?_ +and monad + Id +-/ +#guard_msgs in +example {c} := Id.run do + for x in c do + pure () + pure () + + +/-- +error: don't know how to synthesize implicit argument 'ρ' + @forIn Id (List ?_) ?_ instForInOfForIn' PUnit Id.instMonad [] PUnit.unit fun x r => do + pure () + pure (ForInStep.yield PUnit.unit) +context: +⊢ Type _ +--- +error: failed to infer binder type +--- +error: don't know how to synthesize implicit argument 'α' + @List.nil ?_ +context: +⊢ Type _ +-/ +#guard_msgs in +example : Unit := Id.run do + for x in [] do + pure () + pure () + +/-- +error: failed to construct `ForIn'` instance for collection + ?_ +and monad + Id +-/ +#guard_msgs in +example {c} := Id.run do + for h : x in c do + pure () + pure () + +/-- +error: don't know how to synthesize implicit argument 'd' + @forIn' Id (List ?_) ?_ inferInstance List.instForIn'InferInstanceMembership PUnit Id.instMonad [] PUnit.unit + fun x h r => do + pure () + pure (ForInStep.yield PUnit.unit) +context: +⊢ outParam (Membership ?_ (List ?_)) +--- +error: don't know how to synthesize implicit argument 'ρ' + @forIn' Id (List ?_) ?_ inferInstance List.instForIn'InferInstanceMembership PUnit Id.instMonad [] PUnit.unit + fun x h r => do + pure () + pure (ForInStep.yield PUnit.unit) +context: +⊢ Type _ +--- +error: failed to infer binder type +--- +error: failed to infer binder type +--- +error: don't know how to synthesize implicit argument 'α' + @List.nil ?_ +context: +⊢ Type _ +-/ +#guard_msgs in +example : Unit := Id.run do + for h : x in [] do + pure () + pure ()