@@ -59,8 +59,10 @@ public static RuntimeScalar sprintf(RuntimeScalar runtimeScalar, RuntimeList lis
5959 result .append (literal );
6060 charsWritten += literal .length ();
6161 } else if (element instanceof FormatSpecifier spec ) {
62+ System .err .println ("DEBUG: Processing spec: " + spec .raw + ", isValid=" + spec .isValid );
6263 // Check if this is an overlapping specifier (warning only, no output)
6364 if (spec .isOverlapping ) {
65+ System .err .println ("DEBUG: Skipping overlapping spec" );
6466 // Only generate warning, don't add to output
6567 if (!spec .isValid ) {
6668 // Just generate the warning, don't add to result
@@ -72,6 +74,7 @@ public static RuntimeScalar sprintf(RuntimeScalar runtimeScalar, RuntimeList lis
7274
7375 // Check if spec is invalid FIRST
7476 if (!spec .isValid ) {
77+ System .err .println ("DEBUG: Processing invalid spec" );
7578 String formatted = processFormatSpecifier (spec , list , argIndex , formatter );
7679 result .append (formatted );
7780 charsWritten += formatted .length ();
@@ -109,6 +112,7 @@ public static RuntimeScalar sprintf(RuntimeScalar runtimeScalar, RuntimeList lis
109112 continue ; // Skip to next format element
110113 } else {
111114 ProcessResult processResult = processFormatSpecifierTracked (spec , list , argIndex , formatter );
115+ System .err .println ("DEBUG: Called processFormatSpecifierTracked" );
112116 result .append (processResult .formatted );
113117 charsWritten += processResult .formatted .length ();
114118
@@ -186,16 +190,17 @@ private static void handlePercentN(FormatSpecifier spec,
186190 /**
187191 * Process a single format specifier with tracking.
188192 */
189- private static ProcessResult processFormatSpecifierTracked (
190- FormatSpecifier spec ,
191- RuntimeList list ,
192- int sepArgIndex ,
193- SprintfValueFormatter formatter ) {
193+ private static ProcessResult processFormatSpecifierTracked (
194+ FormatSpecifier spec ,
195+ RuntimeList list ,
196+ int sepArgIndex ,
197+ SprintfValueFormatter formatter ) {
194198
195- String formatted = processFormatSpecifier (spec , list , sepArgIndex , formatter , -1 );
199+ System .err .println ("DEBUG: processFormatSpecifierTracked called for: " + spec .raw );
200+ String formatted = processFormatSpecifier (spec , list , sepArgIndex , formatter , -1 );
196201
197- // Calculate max arg index used
198- int maxUsed = -1 ;
202+ // Calculate max arg index used
203+ int maxUsed = -1 ;
199204
200205 // Handle %% - literal percent sign
201206 if (spec .conversionChar == '%' ) {
@@ -236,9 +241,6 @@ private static ProcessResult processFormatSpecifierTracked(
236241 return new ProcessResult (formatted , maxUsed );
237242 }
238243
239- // Track all consumed arguments properly
240- FormatArguments args = extractFormatArguments (spec , list , sepArgIndex );
241-
242244 // Track width argument if consumed
243245 if (spec .widthFromArg ) {
244246 if (spec .widthArgIndex != null ) {
@@ -273,8 +275,13 @@ private static ProcessResult processFormatSpecifierTracked(
273275 }
274276
275277 // Track value argument
276- if (args .valueArgIndex < list .size ()) {
277- maxUsed = Math .max (maxUsed , args .valueArgIndex );
278+ if (spec .parameterIndex != null ) {
279+ maxUsed = Math .max (maxUsed , spec .parameterIndex - 1 );
280+ } else {
281+ int valuePos = sepArgIndex ;
282+ if (spec .widthFromArg && spec .widthArgIndex == null ) valuePos ++;
283+ if (spec .precisionFromArg && spec .precisionArgIndex == null ) valuePos ++;
284+ maxUsed = Math .max (maxUsed , valuePos );
278285 }
279286
280287 return new ProcessResult (formatted , maxUsed );
@@ -297,7 +304,7 @@ private static String processFormatSpecifier(
297304 SprintfValueFormatter formatter ,
298305 int maxArgIndexUsed ) {
299306
300- // System.err.println("DEBUG processFormatSpecifier: raw='" + spec.raw + "', isValid=" + spec.isValid + ", errorMessage=" + spec.errorMessage );
307+ System .err .println ("DEBUG: processFormatSpecifier start for: " + spec .raw );
301308
302309 // Handle invalid specifiers FIRST (before %% check)
303310 if (!spec .isValid ) {
@@ -307,6 +314,7 @@ private static String processFormatSpecifier(
307314 // Handle %% - literal percent sign
308315 if (spec .conversionChar == '%' ) {
309316 if (spec .widthFromArg ) {
317+ System .err .println ("DEBUG: About to call extractFormatArguments" );
310318 FormatArguments args = extractFormatArguments (spec , list , sepArgIndex );
311319 // Consume the width argument but still return %
312320 }
@@ -319,6 +327,7 @@ private static String processFormatSpecifier(
319327 }
320328
321329 // Process width, precision, and value arguments
330+ System .err .println ("DEBUG: About to call extractFormatArguments" );
322331 FormatArguments args = extractFormatArguments (spec , list , sepArgIndex );
323332
324333 // Check for missing value argument
@@ -399,15 +408,21 @@ private static FormatArguments extractFormatArguments(
399408 RuntimeList list ,
400409 int argIndex ) {
401410
411+ System .err .println ("DEBUG: extractFormatArguments start - argIndex=" + argIndex );
412+ System .err .println ("DEBUG: spec.widthFromArg=" + spec .widthFromArg + ", spec.widthArgIndex=" + spec .widthArgIndex );
413+
402414 FormatArguments args = new FormatArguments ();
403415 int currentArgIndex = argIndex ;
404416
405417 // Process width
406418 if (spec .widthFromArg ) {
407419 int widthArgIndex ;
408420 if (spec .widthArgIndex != null ) {
409- // Explicit index like %*2$d
421+ // Explicit index like %*2$d - positional parameter
410422 widthArgIndex = spec .widthArgIndex - 1 ;
423+ System .err .println ("DEBUG: Positional width at index " + widthArgIndex );
424+ // DON'T increment currentArgIndex or consumedArgs for positional
425+ // because it's not consuming from the sequential stream
411426 } else if (spec .parameterIndex != null ) {
412427 // When we have %2$*d, the width comes from the current position
413428 widthArgIndex = currentArgIndex ;
@@ -434,12 +449,15 @@ private static FormatArguments extractFormatArguments(
434449 args .width = spec .width ;
435450 }
436451
437- // Process precision
452+ System .err .println ("DEBUG: After width processing: consumedArgs=" + args .consumedArgs );
453+
454+ // Process precision (similar logic)
438455 if (spec .precisionFromArg ) {
439456 int precArgIndex ;
440457 if (spec .precisionArgIndex != null ) {
441- // Explicit index like %.*2$d
458+ // Explicit index like %.*2$d - positional parameter
442459 precArgIndex = spec .precisionArgIndex - 1 ;
460+ // DON'T increment currentArgIndex or consumedArgs for positional
443461 } else if (spec .parameterIndex != null ) {
444462 // When we have %2$.*d, precision comes from current position
445463 precArgIndex = currentArgIndex ;
@@ -465,13 +483,17 @@ private static FormatArguments extractFormatArguments(
465483 args .precision = spec .precision ;
466484 }
467485
486+ System .err .println ("DEBUG: Before valueArgIndex calc - argIndex=" + argIndex + ", consumedArgs=" + args .consumedArgs );
487+
468488 // Determine value argument index
469489 if (spec .parameterIndex != null ) {
470490 args .valueArgIndex = spec .parameterIndex - 1 ;
471491 } else {
472492 args .valueArgIndex = argIndex + args .consumedArgs ;
473493 }
474494
495+ System .err .println ("DEBUG: Calculated valueArgIndex=" + args .valueArgIndex + ", list.size()=" + list .size ());
496+
475497 return args ;
476498 }
477499
0 commit comments