@@ -81,6 +81,9 @@ object Typer {
8181 /** Indicates that a definition was copied over from the parent refinements */
8282 val RefinementFromParent = new Property .StickyKey [Unit ]
8383
84+ /** Indicates that an expression is explicitly ascribed to [[Unit ]] type. */
85+ val AscribedToUnit = new Property .StickyKey [Unit ]
86+
8487 /** An attachment on a Select node with an `apply` field indicating that the `apply`
8588 * was inserted by the Typer.
8689 */
@@ -1193,7 +1196,10 @@ class Typer(@constructorOnly nestingLevel: Int = 0) extends Namer
11931196 else tpt
11941197 val expr1 =
11951198 if isWildcard then tree.expr.withType(underlyingTreeTpe.tpe)
1196- else typed(tree.expr, underlyingTreeTpe.tpe.widenSkolem)
1199+ else
1200+ if underlyingTreeTpe.tpe.isRef(defn.UnitClass ) then
1201+ untpd.unsplice(tree.expr).putAttachment(AscribedToUnit , ())
1202+ typed(tree.expr, underlyingTreeTpe.tpe.widenSkolem)
11971203 assignType(cpy.Typed (tree)(expr1, tpt), underlyingTreeTpe)
11981204 .withNotNullInfo(expr1.notNullInfo)
11991205 }
@@ -3377,7 +3383,7 @@ class Typer(@constructorOnly nestingLevel: Int = 0) extends Namer
33773383 else if (ctx.mode.is(Mode .Pattern ))
33783384 typedUnApply(cpy.Apply (tree)(op, l :: r :: Nil ), pt)
33793385 else {
3380- val app = typedApply(desugar.binop(l, op, r), pt)
3386+ val app = typedApply(desugar.binop(l, op, r).withAttachmentsFrom(tree) , pt)
33813387 if op.name.isRightAssocOperatorName && ! ctx.mode.is(Mode .QuotedExprPattern ) then
33823388 val defs = new mutable.ListBuffer [Tree ]
33833389 def lift (app : Tree ): Tree = (app : @ unchecked) match
@@ -4581,9 +4587,14 @@ class Typer(@constructorOnly nestingLevel: Int = 0) extends Namer
45814587 // so will take the code path that decides on inlining
45824588 val tree1 = adapt(tree, WildcardType , locked)
45834589 checkStatementPurity(tree1)(tree, ctx.owner, isUnitExpr = true )
4584- if (! ctx.isAfterTyper && ! tree.isInstanceOf [Inlined ] && ctx.settings.Whas .valueDiscard && ! isThisTypeResult(tree)) {
4590+
4591+ if ctx.settings.Whas .valueDiscard
4592+ && ! ctx.isAfterTyper
4593+ && ! tree.isInstanceOf [Inlined ]
4594+ && ! isThisTypeResult(tree)
4595+ && ! tree.hasAttachment(AscribedToUnit ) then
45854596 report.warning(ValueDiscarding (tree.tpe), tree.srcPos)
4586- }
4597+
45874598 return tpd.Block (tree1 :: Nil , unitLiteral)
45884599 }
45894600
@@ -4839,6 +4850,9 @@ class Typer(@constructorOnly nestingLevel: Int = 0) extends Namer
48394850 // sometimes we do not have the original anymore and use the transformed tree instead.
48404851 // But taken together, the two criteria are quite accurate.
48414852 missingArgs(tree, tree.tpe.widen)
4853+ case _ if tree.hasAttachment(AscribedToUnit ) =>
4854+ // The tree was ascribed to `Unit` explicitly to silence the warning.
4855+ ()
48424856 case _ if isUnitExpr =>
48434857 report.warning(PureUnitExpression (original, tree.tpe), original.srcPos)
48444858 case _ =>
0 commit comments