@@ -235,8 +235,7 @@ class ClassfileParser(
235
235
getOwner(jflags), preName.name, sflags, completer,
236
236
getPrivateWithin(jflags), coord = start)
237
237
238
- val isVarargs = sflags.is(Flags .Method ) && (jflags & JAVA_ACC_VARARGS ) != 0
239
- completer.attrCompleter = parseAttributes(member, isVarargs)
238
+ completer.attrCompleter = parseAttributes(member)
240
239
241
240
getScope(jflags).enter(member)
242
241
@@ -291,7 +290,7 @@ class ClassfileParser(
291
290
val isVarargs = denot.is(Flags .Method ) && (jflags & JAVA_ACC_VARARGS ) != 0
292
291
denot.info = sigToType(sig, isVarargs = isVarargs)
293
292
if (isConstructor) normalizeConstructorParams()
294
- denot.info = translateTempPoly(attrCompleter.complete(denot.info))
293
+ denot.info = translateTempPoly(attrCompleter.complete(denot.info, isVarargs ))
295
294
if (isConstructor) normalizeConstructorInfo()
296
295
297
296
if (ctx.explicitNulls) denot.info = JavaNullInterop .nullifyMember(denot.symbol, denot.info, isEnum)
@@ -628,36 +627,49 @@ class ClassfileParser(
628
627
None // ignore malformed annotations
629
628
}
630
629
631
- abstract class AttributeCompleter {
630
+ class AttributeCompleter (sym : Symbol ) {
631
+ var codeAttribute : Boolean = false
632
+ var sig : String = null
632
633
var constant : Constant = null
633
634
var exceptions : List [NameOrString ] = Nil
634
- def complete (tp : Type )(using Context ): Type
635
- }
635
+ var annotations : List [Annotation ] = Nil
636
+ def complete (tp : Type , isVarargs : Boolean = false )(using Context ): Type = {
637
+ // flag test will trigger completion and cycles, thus have to be lazy
638
+ if (codeAttribute && sym.owner.isAllOf(Flags .JavaInterface )) {
639
+ sym.resetFlag(Flags .Deferred )
640
+ sym.owner.resetFlag(Flags .PureInterface )
641
+ report.log(s " $sym in ${sym.owner} is a java 8+ default method. " )
642
+ }
636
643
637
- // invariant: `in` and `ctx` should not be captured inside the result function
638
- def parseAttributes (sym : Symbol , isVarargs : Boolean = false )(using ctx : Context , in : DataReader ): AttributeCompleter = {
639
- var typeUpdate : Option [Context ?=> Type ] = None
640
- var delayedWork : List [Context ?=> Unit ] = Nil
641
- val res = new AttributeCompleter {
642
- def complete (tp : Type )(using Context ): Type = {
643
- val updatedType =
644
- if typeUpdate.isEmpty then tp
645
- else typeUpdate.get
646
-
647
- val newType =
648
- if this .constant != null then
649
- val ct = convertTo(this .constant, updatedType)
650
- if ct != null then ConstantType (ct) else updatedType
651
- else updatedType
652
-
653
- exceptions.foreach { ex =>
654
- val cls = getClassSymbol(ex.name)
655
- sym.addAnnotation(ThrowsAnnotation (cls.asClass))
644
+ val updatedType =
645
+ if sig == null then tp
646
+ else {
647
+ val newType = sigToType(sig, sym, isVarargs)
648
+ if (ctx.debug && ctx.verbose)
649
+ println(" " + sym + " ; signature = " + sig + " type = " + newType)
650
+ newType
656
651
}
657
- delayedWork.foreach(_.apply)
658
- cook.apply(newType)
652
+
653
+ val newType =
654
+ if this .constant != null then
655
+ val ct = convertTo(this .constant, updatedType)
656
+ if ct != null then ConstantType (ct) else updatedType
657
+ else updatedType
658
+
659
+ annotations.foreach(annot => sym.addAnnotation(annot))
660
+
661
+ exceptions.foreach { ex =>
662
+ val cls = getClassSymbol(ex.name)
663
+ sym.addAnnotation(ThrowsAnnotation (cls.asClass))
659
664
}
665
+
666
+ cook.apply(newType)
660
667
}
668
+ }
669
+
670
+ // invariant: `in` and `ctx` should not be captured inside the result function
671
+ def parseAttributes (sym : Symbol )(using ctx : Context , in : DataReader ): AttributeCompleter = {
672
+ val res = new AttributeCompleter (sym)
661
673
662
674
def parseAttribute (): Unit = {
663
675
val attrName = pool.getName(in.nextChar).name.toTypeName
@@ -666,12 +678,7 @@ class ClassfileParser(
666
678
attrName match {
667
679
case tpnme.SignatureATTR =>
668
680
val sig = pool.getExternalName(in.nextChar)
669
- typeUpdate = Some {
670
- val newType = sigToType(sig.value, sym, isVarargs)
671
- if (ctx.debug && ctx.verbose)
672
- println(" " + sym + " ; signature = " + sig + " type = " + newType)
673
- newType
674
- }
681
+ res.sig = sig.value
675
682
676
683
case tpnme.SyntheticATTR =>
677
684
sym.setFlag(Flags .SyntheticArtifact )
@@ -682,7 +689,7 @@ class ClassfileParser(
682
689
case tpnme.DeprecatedATTR =>
683
690
val msg = Literal (Constant (" see corresponding Javadoc for more information." ))
684
691
val since = Literal (Constant (" " ))
685
- delayedWork ::= sym.addAnnotation( Annotation (defn.DeprecatedAnnot , msg, since) )
692
+ res.annotations ::= Annotation (defn.DeprecatedAnnot , msg, since)
686
693
687
694
case tpnme.ConstantValueATTR =>
688
695
val c = pool.getConstant(in.nextChar)
@@ -708,14 +715,7 @@ class ClassfileParser(
708
715
709
716
case tpnme.CodeATTR =>
710
717
in.skip(attrLen)
711
- // flag test will trigger completion and cycles, thus have to be lazy
712
- delayedWork ::= {
713
- if (sym.owner.isAllOf(Flags .JavaInterface )) {
714
- sym.resetFlag(Flags .Deferred )
715
- sym.owner.resetFlag(Flags .PureInterface )
716
- report.log(s " $sym in ${sym.owner} is a java 8+ default method. " )
717
- }
718
- }
718
+ res.codeAttribute = true
719
719
720
720
case _ =>
721
721
}
0 commit comments