From 567787f679e9255bc1f68c9be1bdb24482f27f9f Mon Sep 17 00:00:00 2001 From: noti0na1 Date: Thu, 18 Mar 2021 14:39:26 -0400 Subject: [PATCH 1/5] Fix parsing Java annotation values --- .../tools/dotc/parsing/JavaParsers.scala | 47 +++++++------------ 1 file changed, 17 insertions(+), 30 deletions(-) diff --git a/compiler/src/dotty/tools/dotc/parsing/JavaParsers.scala b/compiler/src/dotty/tools/dotc/parsing/JavaParsers.scala index 8322c75e5e2d..c9514eeb7cd4 100644 --- a/compiler/src/dotty/tools/dotc/parsing/JavaParsers.scala +++ b/compiler/src/dotty/tools/dotc/parsing/JavaParsers.scala @@ -359,19 +359,6 @@ object JavaParsers { * but instead we skip entire annotation silently. */ def annotation(): Option[Tree] = { - object LiteralT: - def unapply(token: Token) = Option(token match { - case TRUE => true - case FALSE => false - case CHARLIT => in.name(0) - case INTLIT => in.intVal(false).toInt - case LONGLIT => in.intVal(false) - case FLOATLIT => in.floatVal(false).toFloat - case DOUBLELIT => in.floatVal(false) - case STRINGLIT => in.name.toString - case _ => null - }).map(Constant(_)) - def classOrId(): Tree = val id = qualId() if in.lookaheadToken == CLASS then @@ -398,17 +385,17 @@ object JavaParsers { } def argValue(): Option[Tree] = - val tree = in.token match { - case LiteralT(c) => - val tree = atSpan(in.offset)(Literal(c)) - in.nextToken() - Some(tree) - case AT => - in.nextToken() - annotation() - case IDENTIFIER => Some(classOrId()) - case LBRACE => array() - case _ => None + val tree = tryConstant match { + case Some(c) => + Some(atSpan(in.offset)(Literal(c))) + case _ => in.token match { + case AT => + in.nextToken() + annotation() + case IDENTIFIER => Some(classOrId()) + case LBRACE => array() + case _ => None + } } if in.token == COMMA || in.token == RBRACE || in.token == RPAREN then tree @@ -716,11 +703,7 @@ object JavaParsers { in.nextToken() // EQUALS if (mods.is(Flags.JavaStatic) && mods.is(Flags.Final)) { - val neg = in.token match { - case MINUS | BANG => in.nextToken(); true - case _ => false - } - tryLiteral(neg).map(forConst).getOrElse(tpt1) + tryConstant.map(forConst).getOrElse(tpt1) } else tpt1 } @@ -976,7 +959,11 @@ object JavaParsers { case _ => in.nextToken(); syntaxError("illegal start of type declaration", skipIt = true); List(errorTypeTree) } - def tryLiteral(negate: Boolean = false): Option[Constant] = { + def tryConstant: Option[Constant] = { + val negate = in.token match { + case MINUS | BANG => in.nextToken(); true + case _ => false + } val l = in.token match { case TRUE => !negate case FALSE => negate From 269b35054fca42347d14b6e83a0d5d0c5fa540bd Mon Sep 17 00:00:00 2001 From: noti0na1 Date: Wed, 18 Aug 2021 14:43:01 +0000 Subject: [PATCH 2/5] Add test file --- tests/run/fix-annot-arg-value-in-java/AnnoMacro.scala | 10 ++++++++++ tests/run/fix-annot-arg-value-in-java/J.java | 8 ++++++++ tests/run/fix-annot-arg-value-in-java/S.scala | 3 +++ 3 files changed, 21 insertions(+) create mode 100644 tests/run/fix-annot-arg-value-in-java/AnnoMacro.scala create mode 100644 tests/run/fix-annot-arg-value-in-java/J.java create mode 100644 tests/run/fix-annot-arg-value-in-java/S.scala diff --git a/tests/run/fix-annot-arg-value-in-java/AnnoMacro.scala b/tests/run/fix-annot-arg-value-in-java/AnnoMacro.scala new file mode 100644 index 000000000000..472525d7a1d2 --- /dev/null +++ b/tests/run/fix-annot-arg-value-in-java/AnnoMacro.scala @@ -0,0 +1,10 @@ +import scala.quoted.* + +inline def annots(inline c: String): List[String] = ${ annotsImpl('c) } + +def annotsImpl(c: Expr[String])(using Quotes): Expr[List[String]] = + import quotes.reflect.* + // println(c.valueOrError) + val a = Symbol.requiredClass(c.valueOrError).declaredMethods.map(_.annotations.toString) + // println(a) + Expr(a) \ No newline at end of file diff --git a/tests/run/fix-annot-arg-value-in-java/J.java b/tests/run/fix-annot-arg-value-in-java/J.java new file mode 100644 index 000000000000..f028a0b1a80d --- /dev/null +++ b/tests/run/fix-annot-arg-value-in-java/J.java @@ -0,0 +1,8 @@ +public class J { + @SuppressWarnings(value = "a") + public void f1() {} + @SuppressWarnings("b") + public void f2() {} + @SuppressWarnings({"c", "d"}) + public void f3() {} +} \ No newline at end of file diff --git a/tests/run/fix-annot-arg-value-in-java/S.scala b/tests/run/fix-annot-arg-value-in-java/S.scala new file mode 100644 index 000000000000..0bbb1d51db14 --- /dev/null +++ b/tests/run/fix-annot-arg-value-in-java/S.scala @@ -0,0 +1,3 @@ +@main def Test = + println("adasdasdasdasdasdasdas") + println(annots("J")) \ No newline at end of file From df97004dccd76921c5330ae28aa67094133d41e3 Mon Sep 17 00:00:00 2001 From: noti0na1 Date: Wed, 18 Aug 2021 15:12:33 +0000 Subject: [PATCH 3/5] Add checkfile --- tests/run/annot-arg-value-in-java.check | 4 ++++ .../AnnoMacro.scala | 5 +---- .../J.java | 0 tests/run/annot-arg-value-in-java/S.scala | 4 ++++ tests/run/fix-annot-arg-value-in-java/S.scala | 3 --- 5 files changed, 9 insertions(+), 7 deletions(-) create mode 100644 tests/run/annot-arg-value-in-java.check rename tests/run/{fix-annot-arg-value-in-java => annot-arg-value-in-java}/AnnoMacro.scala (56%) rename tests/run/{fix-annot-arg-value-in-java => annot-arg-value-in-java}/J.java (100%) create mode 100644 tests/run/annot-arg-value-in-java/S.scala delete mode 100644 tests/run/fix-annot-arg-value-in-java/S.scala diff --git a/tests/run/annot-arg-value-in-java.check b/tests/run/annot-arg-value-in-java.check new file mode 100644 index 000000000000..95c3e152e02a --- /dev/null +++ b/tests/run/annot-arg-value-in-java.check @@ -0,0 +1,4 @@ +J: +List(Apply(Select(New(Ident(SuppressWarnings)),),List(NamedArg(value,JavaSeqLiteral(List(Literal(Constant(a))), TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String)]))))) +List(Apply(Select(New(Ident(SuppressWarnings)),),List(NamedArg(value,JavaSeqLiteral(List(Literal(Constant(b))), TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String)]))))) +List(Apply(Select(New(Ident(SuppressWarnings)),),List(NamedArg(value,Apply(Apply(TypeApply(Select(Select(Select(Ident(_root_),scala),Array),apply),List(TypeTree[TypeVar(TypeParamRef(T) -> TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String))])),List(Typed(SeqLiteral(List(Literal(Constant(c)), Literal(Constant(d))),TypeTree[TypeVar(TypeParamRef(T) -> TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String))]),TypeTree[AppliedType(TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class ),List(TypeVar(TypeParamRef(T) -> TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String))))]))),List(Apply(TypeApply(Select(Ident(ClassTag),apply),List(TypeTree[TypeVar(TypeParamRef(T) -> TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String))])),List(Literal(Constant(TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String))))))))))) diff --git a/tests/run/fix-annot-arg-value-in-java/AnnoMacro.scala b/tests/run/annot-arg-value-in-java/AnnoMacro.scala similarity index 56% rename from tests/run/fix-annot-arg-value-in-java/AnnoMacro.scala rename to tests/run/annot-arg-value-in-java/AnnoMacro.scala index 472525d7a1d2..50e1fc7f77cd 100644 --- a/tests/run/fix-annot-arg-value-in-java/AnnoMacro.scala +++ b/tests/run/annot-arg-value-in-java/AnnoMacro.scala @@ -4,7 +4,4 @@ inline def annots(inline c: String): List[String] = ${ annotsImpl('c) } def annotsImpl(c: Expr[String])(using Quotes): Expr[List[String]] = import quotes.reflect.* - // println(c.valueOrError) - val a = Symbol.requiredClass(c.valueOrError).declaredMethods.map(_.annotations.toString) - // println(a) - Expr(a) \ No newline at end of file + Expr(Symbol.requiredClass(c.valueOrError).declaredMethods.map(_.annotations.toString)) \ No newline at end of file diff --git a/tests/run/fix-annot-arg-value-in-java/J.java b/tests/run/annot-arg-value-in-java/J.java similarity index 100% rename from tests/run/fix-annot-arg-value-in-java/J.java rename to tests/run/annot-arg-value-in-java/J.java diff --git a/tests/run/annot-arg-value-in-java/S.scala b/tests/run/annot-arg-value-in-java/S.scala new file mode 100644 index 000000000000..2eae74de88ad --- /dev/null +++ b/tests/run/annot-arg-value-in-java/S.scala @@ -0,0 +1,4 @@ +@main def Test = + inline val c = "J" + println(c + ":") + annots(c).foreach(println) \ No newline at end of file diff --git a/tests/run/fix-annot-arg-value-in-java/S.scala b/tests/run/fix-annot-arg-value-in-java/S.scala deleted file mode 100644 index 0bbb1d51db14..000000000000 --- a/tests/run/fix-annot-arg-value-in-java/S.scala +++ /dev/null @@ -1,3 +0,0 @@ -@main def Test = - println("adasdasdasdasdasdasdas") - println(annots("J")) \ No newline at end of file From 7e39e73d3035fa5f19fd88df2c2b96d2b238b7c9 Mon Sep 17 00:00:00 2001 From: noti0na1 Date: Thu, 19 Aug 2021 05:25:15 +0000 Subject: [PATCH 4/5] Add tests for int, bool, and double --- .../run-macros/annot-arg-value-in-java.check | 11 +++++++++ .../annot-arg-value-in-java/AnnoMacro.scala | 11 +++++++++ .../annot-arg-value-in-java/Annot.java | 5 ++++ .../run-macros/annot-arg-value-in-java/J.java | 23 +++++++++++++++++++ .../annot-arg-value-in-java/S.scala | 9 ++++++++ tests/run/annot-arg-value-in-java.check | 4 ---- .../annot-arg-value-in-java/AnnoMacro.scala | 7 ------ tests/run/annot-arg-value-in-java/J.java | 8 ------- tests/run/annot-arg-value-in-java/S.scala | 4 ---- 9 files changed, 59 insertions(+), 23 deletions(-) create mode 100644 tests/run-macros/annot-arg-value-in-java.check create mode 100644 tests/run-macros/annot-arg-value-in-java/AnnoMacro.scala create mode 100644 tests/run-macros/annot-arg-value-in-java/Annot.java create mode 100644 tests/run-macros/annot-arg-value-in-java/J.java create mode 100644 tests/run-macros/annot-arg-value-in-java/S.scala delete mode 100644 tests/run/annot-arg-value-in-java.check delete mode 100644 tests/run/annot-arg-value-in-java/AnnoMacro.scala delete mode 100644 tests/run/annot-arg-value-in-java/J.java delete mode 100644 tests/run/annot-arg-value-in-java/S.scala diff --git a/tests/run-macros/annot-arg-value-in-java.check b/tests/run-macros/annot-arg-value-in-java.check new file mode 100644 index 000000000000..d49aaf91ae6a --- /dev/null +++ b/tests/run-macros/annot-arg-value-in-java.check @@ -0,0 +1,11 @@ +J: +new java.lang.SuppressWarnings(value = "a") +new java.lang.SuppressWarnings(value = "b") +new java.lang.SuppressWarnings(value = _root_.scala.Array.apply[java.lang.String]("c", "d")(scala.reflect.ClassTag.apply[java.lang.String](classOf[java.lang.String]))) +JOtherTypes: +new Annot(value = 1, _, _) +new Annot(value = -2, _, _) +new Annot(_, m = false, _) +new Annot(_, m = true, _) +new Annot(_, _, n = 1.1) +new Annot(_, _, n = -2.1) \ No newline at end of file diff --git a/tests/run-macros/annot-arg-value-in-java/AnnoMacro.scala b/tests/run-macros/annot-arg-value-in-java/AnnoMacro.scala new file mode 100644 index 000000000000..7528653ef903 --- /dev/null +++ b/tests/run-macros/annot-arg-value-in-java/AnnoMacro.scala @@ -0,0 +1,11 @@ +import scala.quoted.* + +inline def showAnnots(inline c: String): Unit = ${ showAnnotsImpl('c) } + +def showAnnotsImpl(c: Expr[String])(using Quotes): Expr[Unit] = + import quotes.reflect.* + val al = Expr(Symbol.requiredClass(c.valueOrError).declaredMethods.flatMap(_.annotations.map(_.show))) + '{ + println($c + ":") + $al.foreach(println) + } \ No newline at end of file diff --git a/tests/run-macros/annot-arg-value-in-java/Annot.java b/tests/run-macros/annot-arg-value-in-java/Annot.java new file mode 100644 index 000000000000..2764bf8c8324 --- /dev/null +++ b/tests/run-macros/annot-arg-value-in-java/Annot.java @@ -0,0 +1,5 @@ +public @interface Annot { + int value() default 0; + boolean m() default false; + double n() default 0; +} \ No newline at end of file diff --git a/tests/run-macros/annot-arg-value-in-java/J.java b/tests/run-macros/annot-arg-value-in-java/J.java new file mode 100644 index 000000000000..d1234e080258 --- /dev/null +++ b/tests/run-macros/annot-arg-value-in-java/J.java @@ -0,0 +1,23 @@ +public class J { + @SuppressWarnings(value = "a") + public void f1() {} + @SuppressWarnings("b") + public void f2() {} + @SuppressWarnings({"c", "d"}) + public void f3() {} +} + +class JOtherTypes { + @Annot(1) + public void f1() {} + @Annot(-2) + public void f2() {} + @Annot(m = false) + public void f3() {} + @Annot(m = true) + public void f4() {} + @Annot(n = 1.1) + public void f5() {} + @Annot(n = -2.1) + public void f6() {} +} \ No newline at end of file diff --git a/tests/run-macros/annot-arg-value-in-java/S.scala b/tests/run-macros/annot-arg-value-in-java/S.scala new file mode 100644 index 000000000000..f6b88437c097 --- /dev/null +++ b/tests/run-macros/annot-arg-value-in-java/S.scala @@ -0,0 +1,9 @@ +// Display annotation arguments in Java + +// inline def showAnnots(inline c: String): Unit = +// println(c + ":") +// annots(c).foreach(println) + +@main def Test = + showAnnots("J") + showAnnots("JOtherTypes") diff --git a/tests/run/annot-arg-value-in-java.check b/tests/run/annot-arg-value-in-java.check deleted file mode 100644 index 95c3e152e02a..000000000000 --- a/tests/run/annot-arg-value-in-java.check +++ /dev/null @@ -1,4 +0,0 @@ -J: -List(Apply(Select(New(Ident(SuppressWarnings)),),List(NamedArg(value,JavaSeqLiteral(List(Literal(Constant(a))), TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String)]))))) -List(Apply(Select(New(Ident(SuppressWarnings)),),List(NamedArg(value,JavaSeqLiteral(List(Literal(Constant(b))), TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String)]))))) -List(Apply(Select(New(Ident(SuppressWarnings)),),List(NamedArg(value,Apply(Apply(TypeApply(Select(Select(Select(Ident(_root_),scala),Array),apply),List(TypeTree[TypeVar(TypeParamRef(T) -> TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String))])),List(Typed(SeqLiteral(List(Literal(Constant(c)), Literal(Constant(d))),TypeTree[TypeVar(TypeParamRef(T) -> TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String))]),TypeTree[AppliedType(TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class ),List(TypeVar(TypeParamRef(T) -> TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String))))]))),List(Apply(TypeApply(Select(Ident(ClassTag),apply),List(TypeTree[TypeVar(TypeParamRef(T) -> TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String))])),List(Literal(Constant(TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class String))))))))))) diff --git a/tests/run/annot-arg-value-in-java/AnnoMacro.scala b/tests/run/annot-arg-value-in-java/AnnoMacro.scala deleted file mode 100644 index 50e1fc7f77cd..000000000000 --- a/tests/run/annot-arg-value-in-java/AnnoMacro.scala +++ /dev/null @@ -1,7 +0,0 @@ -import scala.quoted.* - -inline def annots(inline c: String): List[String] = ${ annotsImpl('c) } - -def annotsImpl(c: Expr[String])(using Quotes): Expr[List[String]] = - import quotes.reflect.* - Expr(Symbol.requiredClass(c.valueOrError).declaredMethods.map(_.annotations.toString)) \ No newline at end of file diff --git a/tests/run/annot-arg-value-in-java/J.java b/tests/run/annot-arg-value-in-java/J.java deleted file mode 100644 index f028a0b1a80d..000000000000 --- a/tests/run/annot-arg-value-in-java/J.java +++ /dev/null @@ -1,8 +0,0 @@ -public class J { - @SuppressWarnings(value = "a") - public void f1() {} - @SuppressWarnings("b") - public void f2() {} - @SuppressWarnings({"c", "d"}) - public void f3() {} -} \ No newline at end of file diff --git a/tests/run/annot-arg-value-in-java/S.scala b/tests/run/annot-arg-value-in-java/S.scala deleted file mode 100644 index 2eae74de88ad..000000000000 --- a/tests/run/annot-arg-value-in-java/S.scala +++ /dev/null @@ -1,4 +0,0 @@ -@main def Test = - inline val c = "J" - println(c + ":") - annots(c).foreach(println) \ No newline at end of file From 3dce00c23f97e418c326aae72a06d17fd442c090 Mon Sep 17 00:00:00 2001 From: noti0na1 Date: Thu, 19 Aug 2021 05:38:07 +0000 Subject: [PATCH 5/5] Remove unnecessary comments --- tests/run-macros/annot-arg-value-in-java/S.scala | 4 ---- 1 file changed, 4 deletions(-) diff --git a/tests/run-macros/annot-arg-value-in-java/S.scala b/tests/run-macros/annot-arg-value-in-java/S.scala index f6b88437c097..8b4369df97b1 100644 --- a/tests/run-macros/annot-arg-value-in-java/S.scala +++ b/tests/run-macros/annot-arg-value-in-java/S.scala @@ -1,9 +1,5 @@ // Display annotation arguments in Java -// inline def showAnnots(inline c: String): Unit = -// println(c + ":") -// annots(c).foreach(println) - @main def Test = showAnnots("J") showAnnots("JOtherTypes")