Skip to content

Commit

Permalink
Check New tree for ill-formed module instantiations
Browse files Browse the repository at this point in the history
  • Loading branch information
nicolasstucki committed May 25, 2023
1 parent 4f3632f commit 61190e6
Show file tree
Hide file tree
Showing 9 changed files with 70 additions and 0 deletions.
12 changes: 12 additions & 0 deletions compiler/src/dotty/tools/dotc/transform/TreeChecker.scala
Original file line number Diff line number Diff line change
Expand Up @@ -495,6 +495,18 @@ object TreeChecker {
assert(tree.qual.typeOpt.isInstanceOf[ThisType], i"expect prefix of Super to be This, actual = ${tree.qual}")
super.typedSuper(tree, pt)

override def typedNew(tree: untpd.New, pt: Type)(using Context): Tree =
val tree1 = super.typedNew(tree, pt).asInstanceOf[tpd.New]
val sym = tree1.tpe.typeSymbol
if postTyperPhase <= ctx.phase then // postTyper checks that `New` nodes can be instantiated
assert(!tree1.tpe.isInstanceOf[TermRef], s"New should not have a TermRef type: ${tree1.tpe}")
assert(
!sym.is(Module)
|| ctx.erasedTypes // TODO add check for module initialization after erasure (LazyVals transformation)
|| ctx.owner == sym.companionModule,
i"new of $sym module should only exist in ${sym.companionModule} but was in ${ctx.owner}")
tree1

override def typedApply(tree: untpd.Apply, pt: Type)(using Context): Tree = tree match
case Apply(Select(qual, nme.CONSTRUCTOR), _)
if !ctx.phase.erasedTypes
Expand Down
11 changes: 11 additions & 0 deletions tests/neg-macros/i17545a/Macro_1.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import scala.quoted.*

object InvokeConstructor {
inline def apply[A] = ${ constructorMacro[A] }

def constructorMacro[A: Type](using Quotes) = {
import quotes.reflect.*
val tpe = TypeRepr.of[A]
New(Inferred(tpe)).select(tpe.typeSymbol.primaryConstructor).appliedToArgs(Nil).asExprOf[A]
}
}
4 changes: 4 additions & 0 deletions tests/neg-macros/i17545a/Test_2.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
case object WhateverA

def testA =
val whateverA: WhateverA.type = InvokeConstructor[WhateverA.type] // error
11 changes: 11 additions & 0 deletions tests/neg-macros/i17545b/Macro_1.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import scala.quoted.*

object InvokeConstructor {
inline def apply[A] = ${ constructorMacro[A] }

def constructorMacro[A: Type](using Quotes) = {
import quotes.reflect.*
val tpe = TypeRepr.of[A]
New(Inferred(tpe)).select(tpe.typeSymbol.primaryConstructor).appliedToArgs(Nil).asExprOf[A]
}
}
3 changes: 3 additions & 0 deletions tests/neg-macros/i17545b/Test_2.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
def testB =
case object WhateverB
val whateverB: WhateverB.type = InvokeConstructor[WhateverB.type] // error
11 changes: 11 additions & 0 deletions tests/neg-macros/i17545c/Macro_1.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import scala.quoted.*

object InvokeConstructor {
inline def apply[A] = ${ constructorMacro[A] }

def constructorMacro[A: Type](using Quotes) = {
import quotes.reflect.*
val tpe = TypeRepr.of[A].termSymbol.moduleClass.typeRef
New(Inferred(tpe)).select(tpe.typeSymbol.primaryConstructor).appliedToArgs(Nil).asExprOf[A]
}
}
4 changes: 4 additions & 0 deletions tests/neg-macros/i17545c/Test_2.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
case object WhateverA

def testA =
val whateverA: WhateverA.type = InvokeConstructor[WhateverA.type] // error
11 changes: 11 additions & 0 deletions tests/neg-macros/i17545d/Macro_1.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import scala.quoted.*

object InvokeConstructor {
inline def apply[A] = ${ constructorMacro[A] }

def constructorMacro[A: Type](using Quotes) = {
import quotes.reflect.*
val tpe = TypeRepr.of[A].termSymbol.moduleClass.typeRef
New(Inferred(tpe)).select(tpe.typeSymbol.primaryConstructor).appliedToArgs(Nil).asExprOf[A]
}
}
3 changes: 3 additions & 0 deletions tests/neg-macros/i17545d/Test_2.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
def testB =
case object WhateverB
val whateverB: WhateverB.type = InvokeConstructor[WhateverB.type] // error

0 comments on commit 61190e6

Please sign in to comment.