113113#define DCH_MAX_ITEM_SIZ 12 /* max localized day name */
114114#define NUM_MAX_ITEM_SIZ 8 /* roman number (RN has 15 chars) */
115115
116+ /* ----------
117+ * More is in float.c
118+ * ----------
119+ */
120+ #define MAXFLOATWIDTH 60
121+ #define MAXDOUBLEWIDTH 500
122+
116123
117124/* ----------
118125 * Format parser structs
@@ -5207,7 +5214,8 @@ int4_to_char(PG_FUNCTION_ARGS)
52075214 /* we can do it easily because float8 won't lose any precision */
52085215 float8 val = (float8 ) value ;
52095216
5210- orgnum = psprintf ("%+.*e" , Num .post , val );
5217+ orgnum = (char * ) palloc (MAXDOUBLEWIDTH + 1 );
5218+ snprintf (orgnum , MAXDOUBLEWIDTH + 1 , "%+.*e" , Num .post , val );
52115219
52125220 /*
52135221 * Swap a leading positive sign for a space.
@@ -5406,6 +5414,7 @@ float4_to_char(PG_FUNCTION_ARGS)
54065414 numstr = orgnum = int_to_roman ((int ) rint (value ));
54075415 else if (IS_EEEE (& Num ))
54085416 {
5417+ numstr = orgnum = (char * ) palloc (MAXDOUBLEWIDTH + 1 );
54095418 if (isnan (value ) || is_infinite (value ))
54105419 {
54115420 /*
@@ -5419,29 +5428,15 @@ float4_to_char(PG_FUNCTION_ARGS)
54195428 }
54205429 else
54215430 {
5422- numstr = psprintf ("%+.*e" , Num .post , value );
5423-
5424- /* prevent the display of imprecise/junk digits */
5425- if (Num .pre + Num .post > FLT_DIG )
5426- {
5427- int digits = 0 ;
5428- char * numstr_p ;
5429-
5430- for (numstr_p = numstr ; * numstr_p && * numstr_p != 'e' ; numstr_p ++ )
5431- {
5432- if (isdigit (* numstr_p ))
5433- {
5434- if (++ digits > FLT_DIG )
5435- * numstr_p = '0' ;
5436- }
5437- }
5438- }
5431+ snprintf (orgnum , MAXDOUBLEWIDTH + 1 , "%+.*e" , Num .post , value );
54395432
54405433 /*
54415434 * Swap a leading positive sign for a space.
54425435 */
5443- if (* numstr == '+' )
5444- * numstr = ' ' ;
5436+ if (* orgnum == '+' )
5437+ * orgnum = ' ' ;
5438+
5439+ numstr = orgnum ;
54455440 }
54465441 }
54475442 else
@@ -5457,24 +5452,16 @@ float4_to_char(PG_FUNCTION_ARGS)
54575452 Num .pre += Num .multi ;
54585453 }
54595454
5460- /* let psprintf() do the rounding */
5461- orgnum = psprintf ("%.*f" , Num .post , val );
5455+ orgnum = (char * ) palloc (MAXFLOATWIDTH + 1 );
5456+ snprintf (orgnum , MAXFLOATWIDTH + 1 , "%.0f" , fabs (val ));
5457+ numstr_pre_len = strlen (orgnum );
54625458
5463- /* prevent the display of imprecise/junk digits */
5464- if (Num .pre + Num .post > FLT_DIG )
5465- {
5466- int digits = 0 ;
5467- char * orgnum_p ;
5468-
5469- for (orgnum_p = orgnum ; * orgnum_p ; orgnum_p ++ )
5470- {
5471- if (isdigit (* orgnum_p ))
5472- {
5473- if (++ digits > FLT_DIG )
5474- * orgnum_p = '0' ;
5475- }
5476- }
5477- }
5459+ /* adjust post digits to fit max float digits */
5460+ if (numstr_pre_len >= FLT_DIG )
5461+ Num .post = 0 ;
5462+ else if (numstr_pre_len + Num .post > FLT_DIG )
5463+ Num .post = FLT_DIG - numstr_pre_len ;
5464+ snprintf (orgnum , MAXFLOATWIDTH + 1 , "%.*f" , Num .post , val );
54785465
54795466 if (* orgnum == '-' )
54805467 { /* < 0 */
@@ -5533,6 +5520,7 @@ float8_to_char(PG_FUNCTION_ARGS)
55335520 numstr = orgnum = int_to_roman ((int ) rint (value ));
55345521 else if (IS_EEEE (& Num ))
55355522 {
5523+ numstr = orgnum = (char * ) palloc (MAXDOUBLEWIDTH + 1 );
55365524 if (isnan (value ) || is_infinite (value ))
55375525 {
55385526 /*
@@ -5546,29 +5534,15 @@ float8_to_char(PG_FUNCTION_ARGS)
55465534 }
55475535 else
55485536 {
5549- numstr = psprintf ("%+.*e" , Num .post , value );
5550-
5551- /* prevent the display of imprecise/junk digits */
5552- if (Num .pre + Num .post > DBL_DIG )
5553- {
5554- int digits = 0 ;
5555- char * numstr_p ;
5556-
5557- for (numstr_p = numstr ; * numstr_p && * numstr_p != 'e' ; numstr_p ++ )
5558- {
5559- if (isdigit (* numstr_p ))
5560- {
5561- if (++ digits > DBL_DIG )
5562- * numstr_p = '0' ;
5563- }
5564- }
5565- }
5537+ snprintf (orgnum , MAXDOUBLEWIDTH + 1 , "%+.*e" , Num .post , value );
55665538
55675539 /*
55685540 * Swap a leading positive sign for a space.
55695541 */
5570- if (* numstr == '+' )
5571- * numstr = ' ' ;
5542+ if (* orgnum == '+' )
5543+ * orgnum = ' ' ;
5544+
5545+ numstr = orgnum ;
55725546 }
55735547 }
55745548 else
@@ -5583,25 +5557,15 @@ float8_to_char(PG_FUNCTION_ARGS)
55835557 val = value * multi ;
55845558 Num .pre += Num .multi ;
55855559 }
5586-
5587- /* let psprintf() do the rounding */
5588- orgnum = psprintf ("%.*f" , Num .post , val );
5589-
5590- /* prevent the display of imprecise/junk digits */
5591- if (Num .pre + Num .post > DBL_DIG )
5592- {
5593- int digits = 0 ;
5594- char * orgnum_p ;
5595-
5596- for (orgnum_p = orgnum ; * orgnum_p ; orgnum_p ++ )
5597- {
5598- if (isdigit (* orgnum_p ))
5599- {
5600- if (++ digits > DBL_DIG )
5601- * orgnum_p = '0' ;
5602- }
5603- }
5604- }
5560+ orgnum = (char * ) palloc (MAXDOUBLEWIDTH + 1 );
5561+ numstr_pre_len = snprintf (orgnum , MAXDOUBLEWIDTH + 1 , "%.0f" , fabs (val ));
5562+
5563+ /* adjust post digits to fit max double digits */
5564+ if (numstr_pre_len >= DBL_DIG )
5565+ Num .post = 0 ;
5566+ else if (numstr_pre_len + Num .post > DBL_DIG )
5567+ Num .post = DBL_DIG - numstr_pre_len ;
5568+ snprintf (orgnum , MAXDOUBLEWIDTH + 1 , "%.*f" , Num .post , val );
56055569
56065570 if (* orgnum == '-' )
56075571 { /* < 0 */
0 commit comments