@@ -280,15 +280,13 @@ class ClassfileParser(
280280 addConstructorTypeParams(denot)
281281 }
282282
283- denot.info = pool.getType(in.nextChar)
283+ val isVarargs = denot.is(Flags .Method ) && (jflags & JAVA_ACC_VARARGS ) != 0
284+ denot.info = pool.getType(in.nextChar, isVarargs)
284285 if (isEnum) denot.info = ConstantType (Constant (sym))
285286 if (isConstructor) normalizeConstructorParams()
286- denot.info = translateTempPoly(parseAttributes(sym, denot.info))
287+ denot.info = translateTempPoly(parseAttributes(sym, denot.info, isVarargs ))
287288 if (isConstructor) normalizeConstructorInfo()
288289
289- if (denot.is(Flags .Method ) && (jflags & JAVA_ACC_VARARGS ) != 0 )
290- denot.info = arrayToRepeated(denot.info)
291-
292290 if (ctx.explicitNulls) denot.info = JavaNullInterop .nullifyMember(denot.symbol, denot.info, isEnum)
293291
294292 // seal java enums
@@ -324,7 +322,7 @@ class ClassfileParser(
324322 case BOOL_TAG => defn.BooleanType
325323 }
326324
327- private def sigToType (sig : SimpleName , owner : Symbol = null )(using Context ): Type = {
325+ private def sigToType (sig : SimpleName , owner : Symbol = null , isVarargs : Boolean = false )(using Context ): Type = {
328326 var index = 0
329327 val end = sig.length
330328 def accept (ch : Char ): Unit = {
@@ -395,13 +393,42 @@ class ClassfileParser(
395393 val elemtp = sig2type(tparams, skiptvs)
396394 defn.ArrayOf (elemtp.translateJavaArrayElementType)
397395 case '(' =>
398- // we need a method symbol. given in line 486 by calling getType(methodSym, ..)
396+ def isMethodEnd (i : Int ) = sig(i) == ')'
397+ def isArray (i : Int ) = sig(i) == '['
398+
399+ /** Is this a repeated parameter type?
400+ * This is true if we're in a vararg method and this is the last parameter.
401+ */
402+ def isRepeatedParam (i : Int ): Boolean =
403+ if ! isVarargs then return false
404+ var cur = i
405+ // Repeated parameters are represented as arrays
406+ if ! isArray(cur) then return false
407+ // Handle nested arrays: int[]...
408+ while isArray(cur) do
409+ cur += 1
410+ // Simple check to see if we're the last parameter: there should be no
411+ // array in the signature until the method end.
412+ while ! isMethodEnd(cur) do
413+ if isArray(cur) then return false
414+ cur += 1
415+ true
416+ end isRepeatedParam
417+
399418 val paramtypes = new ListBuffer [Type ]()
400419 var paramnames = new ListBuffer [TermName ]()
401- while (sig( index) != ')' ) {
420+ while ! isMethodEnd( index) do
402421 paramnames += nme.syntheticParamName(paramtypes.length)
403- paramtypes += objToAny(sig2type(tparams, skiptvs))
404- }
422+ paramtypes += {
423+ if isRepeatedParam(index) then
424+ index += 1
425+ val elemType = sig2type(tparams, skiptvs)
426+ // `ElimRepeated` is responsible for correctly erasing this.
427+ defn.RepeatedParamType .appliedTo(elemType)
428+ else
429+ objToAny(sig2type(tparams, skiptvs))
430+ }
431+
405432 index += 1
406433 val restype = sig2type(tparams, skiptvs)
407434 JavaMethodType (paramnames.toList, paramtypes.toList, restype)
@@ -574,7 +601,7 @@ class ClassfileParser(
574601 None // ignore malformed annotations
575602 }
576603
577- def parseAttributes (sym : Symbol , symtype : Type )(using Context ): Type = {
604+ def parseAttributes (sym : Symbol , symtype : Type , isVarargs : Boolean = false )(using Context ): Type = {
578605 var newType = symtype
579606
580607 def parseAttribute (): Unit = {
@@ -584,7 +611,7 @@ class ClassfileParser(
584611 attrName match {
585612 case tpnme.SignatureATTR =>
586613 val sig = pool.getExternalName(in.nextChar)
587- newType = sigToType(sig, sym)
614+ newType = sigToType(sig, sym, isVarargs )
588615 if (ctx.debug && ctx.verbose)
589616 println(" " + sym + " ; signature = " + sig + " type = " + newType)
590617 case tpnme.SyntheticATTR =>
@@ -1103,8 +1130,8 @@ class ClassfileParser(
11031130 c
11041131 }
11051132
1106- def getType (index : Int )(using Context ): Type =
1107- sigToType(getExternalName(index))
1133+ def getType (index : Int , isVarargs : Boolean = false )(using Context ): Type =
1134+ sigToType(getExternalName(index), isVarargs = isVarargs )
11081135
11091136 def getSuperClass (index : Int )(using Context ): Symbol = {
11101137 assert(index != 0 , " attempt to parse java.lang.Object from classfile" )
0 commit comments