3535import java .util .List ;
3636import java .util .Set ;
3737
38+ import static jdk .internal .constant .PrimitiveClassDescImpl .*;
39+
3840/**
3941 * Helper methods for the implementation of {@code java.lang.constant}.
4042 */
@@ -269,59 +271,40 @@ public static String dropFirstAndLastChar(String s) {
269271 return s .substring (1 , s .length () - 1 );
270272 }
271273
272- /**
273- * Parses a method descriptor string, and return a list of field descriptor
274- * strings, return type first, then parameter types
275- *
276- * @param descriptor the descriptor string
277- * @return the list of types
278- * @throws IllegalArgumentException if the descriptor string is not valid
279- */
280- public static List <ClassDesc > parseMethodDescriptor (String descriptor ) {
281- int cur = 0 , end = descriptor .length ();
282- ArrayList <ClassDesc > ptypes = new ArrayList <>();
283- ptypes .add (null ); // placeholder for return type
284-
285- if (cur >= end || descriptor .charAt (cur ) != '(' )
286- throw new IllegalArgumentException ("Bad method descriptor: " + descriptor );
287-
288- ++cur ; // skip '('
289- while (cur < end && descriptor .charAt (cur ) != ')' ) {
290- int len = skipOverFieldSignature (descriptor , cur , end , false );
291- if (len == 0 )
292- throw new IllegalArgumentException ("Bad method descriptor: " + descriptor );
293- ptypes .add (resolveClassDesc (descriptor , cur , len ));
294- cur += len ;
295- }
296- if (cur >= end )
297- throw new IllegalArgumentException ("Bad method descriptor: " + descriptor );
298- ++cur ; // skip ')'
299-
300- int rLen = skipOverFieldSignature (descriptor , cur , end , true );
301- if (rLen == 0 || cur + rLen != end )
302- throw new IllegalArgumentException ("Bad method descriptor: " + descriptor );
303- ptypes .set (0 , resolveClassDesc (descriptor , cur , rLen ));
304- return ptypes ;
274+ public static PrimitiveClassDescImpl forPrimitiveType (String descriptor , int offset ) {
275+ return switch (descriptor .charAt (offset )) {
276+ case JVM_SIGNATURE_BYTE -> CD_byte ;
277+ case JVM_SIGNATURE_CHAR -> CD_char ;
278+ case JVM_SIGNATURE_FLOAT -> CD_float ;
279+ case JVM_SIGNATURE_DOUBLE -> CD_double ;
280+ case JVM_SIGNATURE_INT -> CD_int ;
281+ case JVM_SIGNATURE_LONG -> CD_long ;
282+ case JVM_SIGNATURE_SHORT -> CD_short ;
283+ case JVM_SIGNATURE_VOID -> CD_void ;
284+ case JVM_SIGNATURE_BOOLEAN -> CD_boolean ;
285+ default -> throw badMethodDescriptor (descriptor );
286+ };
305287 }
306288
307- private static ClassDesc resolveClassDesc (String descriptor , int start , int len ) {
289+ static ClassDesc resolveClassDesc (String descriptor , int start , int len ) {
308290 if (len == 1 ) {
309- return Wrapper . forPrimitiveType (descriptor . charAt ( start )). basicClassDescriptor ( );
291+ return forPrimitiveType (descriptor , start );
310292 }
311- // Pre-verified in parseMethodDescriptor; avoid redundant verification
293+
294+ // Pre-verified in MethodTypeDescImpl#ofDescriptor; avoid redundant verification
312295 return ReferenceClassDescImpl .ofValidated (descriptor .substring (start , start + len ));
313296 }
314297
298+ static IllegalArgumentException badMethodDescriptor (String descriptor ) {
299+ return new IllegalArgumentException ("Bad method descriptor: " + descriptor );
300+ }
301+
315302 private static final char JVM_SIGNATURE_ARRAY = '[' ;
316303 private static final char JVM_SIGNATURE_BYTE = 'B' ;
317304 private static final char JVM_SIGNATURE_CHAR = 'C' ;
318305 private static final char JVM_SIGNATURE_CLASS = 'L' ;
319- private static final char JVM_SIGNATURE_ENDCLASS = ';' ;
320- private static final char JVM_SIGNATURE_ENUM = 'E' ;
321306 private static final char JVM_SIGNATURE_FLOAT = 'F' ;
322307 private static final char JVM_SIGNATURE_DOUBLE = 'D' ;
323- private static final char JVM_SIGNATURE_FUNC = '(' ;
324- private static final char JVM_SIGNATURE_ENDFUNC = ')' ;
325308 private static final char JVM_SIGNATURE_INT = 'I' ;
326309 private static final char JVM_SIGNATURE_LONG = 'J' ;
327310 private static final char JVM_SIGNATURE_SHORT = 'S' ;
@@ -334,17 +317,22 @@ private static ClassDesc resolveClassDesc(String descriptor, int start, int len)
334317 * @param descriptor the descriptor string
335318 * @param start the starting index into the string
336319 * @param end the ending index within the string
337- * @param voidOK is void acceptable?
338320 * @return the length of the descriptor, or 0 if it is not a descriptor
339321 * @throws IllegalArgumentException if the descriptor string is not valid
340322 */
341- @ SuppressWarnings ("fallthrough" )
342- static int skipOverFieldSignature (String descriptor , int start , int end , boolean voidOK ) {
323+ static int skipOverFieldSignature (String descriptor , int start , int end ) {
343324 int arrayDim = 0 ;
344325 int index = start ;
345- while (index < end ) {
346- switch (descriptor .charAt (index )) {
347- case JVM_SIGNATURE_VOID : if (!voidOK ) { return 0 ; }
326+ if (index < end ) {
327+ char ch ;
328+ while ((ch = descriptor .charAt (index ++)) == JVM_SIGNATURE_ARRAY ) {
329+ arrayDim ++;
330+ }
331+ if (arrayDim > MAX_ARRAY_TYPE_DESC_DIMENSIONS ) {
332+ throw maxArrayTypeDescDimensions ();
333+ }
334+
335+ switch (ch ) {
348336 case JVM_SIGNATURE_BOOLEAN :
349337 case JVM_SIGNATURE_BYTE :
350338 case JVM_SIGNATURE_CHAR :
@@ -353,16 +341,16 @@ static int skipOverFieldSignature(String descriptor, int start, int end, boolean
353341 case JVM_SIGNATURE_FLOAT :
354342 case JVM_SIGNATURE_LONG :
355343 case JVM_SIGNATURE_DOUBLE :
356- return index - start + 1 ;
344+ return index - start ;
357345 case JVM_SIGNATURE_CLASS :
358346 // state variable for detection of illegal states, such as:
359347 // empty unqualified name, '//', leading '/', or trailing '/'
360348 boolean legal = false ;
361- while (++ index < end ) {
362- switch (descriptor .charAt (index )) {
349+ while (index < end ) {
350+ switch (descriptor .charAt (index ++ )) {
363351 case ';' -> {
364352 // illegal state on parser exit indicates empty unqualified name or trailing '/'
365- return legal ? index - start + 1 : 0 ;
353+ return legal ? index - start : 0 ;
366354 }
367355 case '.' , '[' -> {
368356 // do not permit '.' or '['
@@ -377,21 +365,17 @@ static int skipOverFieldSignature(String descriptor, int start, int end, boolean
377365 legal = true ;
378366 }
379367 }
380- return 0 ;
381- case JVM_SIGNATURE_ARRAY :
382- arrayDim ++;
383- if (arrayDim > MAX_ARRAY_TYPE_DESC_DIMENSIONS ) {
384- throw new IllegalArgumentException (String .format ("Cannot create an array type descriptor with more than %d dimensions" ,
385- ConstantUtils .MAX_ARRAY_TYPE_DESC_DIMENSIONS ));
386- }
387- // The rest of what's there better be a legal descriptor
388- index ++;
389- voidOK = false ;
390368 break ;
391369 default :
392- return 0 ;
370+ break ;
393371 }
394372 }
395373 return 0 ;
396374 }
375+
376+ private static IllegalArgumentException maxArrayTypeDescDimensions () {
377+ return new IllegalArgumentException (String .format (
378+ "Cannot create an array type descriptor with more than %d dimensions" ,
379+ ConstantUtils .MAX_ARRAY_TYPE_DESC_DIMENSIONS ));
380+ }
397381}
0 commit comments