From 73a8a6e05144d0ef759d573d146f6b6c2cbca66f Mon Sep 17 00:00:00 2001 From: Fengyun Liu Date: Wed, 30 Nov 2022 22:38:01 +0100 Subject: [PATCH 1/3] Fix #16438: Ignore erroneous parent call in init check --- .../src/dotty/tools/dotc/transform/init/Semantic.scala | 10 +++++++--- tests/neg/i16438.scala | 4 ++++ 2 files changed, 11 insertions(+), 3 deletions(-) create mode 100644 tests/neg/i16438.scala diff --git a/compiler/src/dotty/tools/dotc/transform/init/Semantic.scala b/compiler/src/dotty/tools/dotc/transform/init/Semantic.scala index a48aa77fe79f..10eb28943770 100644 --- a/compiler/src/dotty/tools/dotc/transform/init/Semantic.scala +++ b/compiler/src/dotty/tools/dotc/transform/init/Semantic.scala @@ -1663,9 +1663,13 @@ object Semantic: // term arguments to B. That can only be done in a concrete class. val tref = typeRefOf(klass.typeRef.baseType(mixin).typeConstructor) val ctor = tref.classSymbol.primaryConstructor - if ctor.exists then extendTrace(superParent) { - superCall(tref, ctor, Nil, tasks) - } + if ctor.exists && ctor.paramSymss.isEmpty then + // The parameter check of traits comes late in the mixin phase. + // To avoid crash we ignore the initialization check for erroneous + // parent call code. See tests/neg/i16438.scala. + extendTrace(superParent) { + superCall(tref, ctor, args = Nil, tasks) + } } // initialize super classes after outers are set diff --git a/tests/neg/i16438.scala b/tests/neg/i16438.scala new file mode 100644 index 000000000000..33873b13384b --- /dev/null +++ b/tests/neg/i16438.scala @@ -0,0 +1,4 @@ +// scalac: -Ysafe-init +trait ATrait(val string: String, val int: Int) +trait AnotherTrait( override val string: String, override val int: Int) extends ATrait +case class ACaseClass(override val string: String) extends AnotherTrait(string, 3) // error From c57e8eb3a6769a8e036d3a86cef1b5a0fabd2cc4 Mon Sep 17 00:00:00 2001 From: Fengyun Liu Date: Thu, 1 Dec 2022 08:04:06 +0100 Subject: [PATCH 2/3] Supply dummy arguments for the call --- .../dotty/tools/dotc/transform/init/Semantic.scala | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/compiler/src/dotty/tools/dotc/transform/init/Semantic.scala b/compiler/src/dotty/tools/dotc/transform/init/Semantic.scala index 10eb28943770..4a2408483c1b 100644 --- a/compiler/src/dotty/tools/dotc/transform/init/Semantic.scala +++ b/compiler/src/dotty/tools/dotc/transform/init/Semantic.scala @@ -855,7 +855,7 @@ object Semantic: // init "fake" param fields for parameters of primary and secondary constructors def addParamsAsFields(args: List[Value], ref: Ref, ctorDef: DefDef) = val params = ctorDef.termParamss.flatten.map(_.symbol) - assert(args.size == params.size, "arguments = " + args.size + ", params = " + params.size) + assert(args.size == params.size, "arguments = " + args.size + ", params = " + params.size + ", ctro = " + ctor.show) for (param, value) <- params.zip(args) do ref.updateField(param, value) printer.println(param.show + " initialized with " + value) @@ -1663,12 +1663,13 @@ object Semantic: // term arguments to B. That can only be done in a concrete class. val tref = typeRefOf(klass.typeRef.baseType(mixin).typeConstructor) val ctor = tref.classSymbol.primaryConstructor - if ctor.exists && ctor.paramSymss.isEmpty then + if ctor.exists then // The parameter check of traits comes late in the mixin phase. - // To avoid crash we ignore the initialization check for erroneous - // parent call code. See tests/neg/i16438.scala. + // To avoid crash we supply hot values for erroneous parent calls. + // See tests/neg/i16438.scala. + val args: List[ArgInfo] = ctor.info.paramInfoss.flatten.map(_ => ArgInfo(Hot, Trace.empty)) extendTrace(superParent) { - superCall(tref, ctor, args = Nil, tasks) + superCall(tref, ctor, args, tasks) } } From d0b4ac2941d906ffb86a96370e21b2820aca1cc6 Mon Sep 17 00:00:00 2001 From: Fengyun Liu Date: Sun, 4 Dec 2022 18:24:28 +0100 Subject: [PATCH 3/3] Fix typo Co-authored-by: 110416 --- compiler/src/dotty/tools/dotc/transform/init/Semantic.scala | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/compiler/src/dotty/tools/dotc/transform/init/Semantic.scala b/compiler/src/dotty/tools/dotc/transform/init/Semantic.scala index 4a2408483c1b..eb1692e00a12 100644 --- a/compiler/src/dotty/tools/dotc/transform/init/Semantic.scala +++ b/compiler/src/dotty/tools/dotc/transform/init/Semantic.scala @@ -855,7 +855,7 @@ object Semantic: // init "fake" param fields for parameters of primary and secondary constructors def addParamsAsFields(args: List[Value], ref: Ref, ctorDef: DefDef) = val params = ctorDef.termParamss.flatten.map(_.symbol) - assert(args.size == params.size, "arguments = " + args.size + ", params = " + params.size + ", ctro = " + ctor.show) + assert(args.size == params.size, "arguments = " + args.size + ", params = " + params.size + ", ctor = " + ctor.show) for (param, value) <- params.zip(args) do ref.updateField(param, value) printer.println(param.show + " initialized with " + value)