aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJerry DeLisle <jvdelisle@gcc.gnu.org>2011-05-05 01:19:30 +0000
committerJerry DeLisle <jvdelisle@gcc.gnu.org>2011-05-05 01:19:30 +0000
commitd6b872ad5e5461b690e76fba943a1d28c27af301 (patch)
tree236b42840d3e2743ad9a751a7e8f9b567fd5a53d
parentc5c04a8fd89112435221124534214530d9121cc3 (diff)
downloadgcc-d6b872ad5e5461b690e76fba943a1d28c27af301.zip
gcc-d6b872ad5e5461b690e76fba943a1d28c27af301.tar.gz
gcc-d6b872ad5e5461b690e76fba943a1d28c27af301.tar.bz2
re PR libfortran/48787 (Invalid UP/DOWN rounding with F editing)
2011-05-04 Jerry DeLisle <jvdelisle@gcc.gnu.org> PR libgfortran/48787 * io/write_float.def (output_float): Adjust up and down rounding for cases where 'd' = 0. Gather common code to one location. From-SVN: r173408
-rw-r--r--libgfortran/ChangeLog6
-rw-r--r--libgfortran/io/write_float.def30
2 files changed, 24 insertions, 12 deletions
diff --git a/libgfortran/ChangeLog b/libgfortran/ChangeLog
index 5b737225..7e081cc 100644
--- a/libgfortran/ChangeLog
+++ b/libgfortran/ChangeLog
@@ -1,3 +1,9 @@
+2011-05-04 Jerry DeLisle <jvdelisle@gcc.gnu.org>
+
+ PR libgfortran/48787
+ * io/write_float.def (output_float): Adjust up and down rounding for
+ cases where 'd' = 0. Gather common code to one location.
+
2011-05-01 Jerry DeLisle <jvdelisle@gcc.gnu.org>
PR libgfortran/48787
diff --git a/libgfortran/io/write_float.def b/libgfortran/io/write_float.def
index 7f3cedd..7ab70d2 100644
--- a/libgfortran/io/write_float.def
+++ b/libgfortran/io/write_float.def
@@ -221,6 +221,7 @@ output_float (st_parameter_dt *dtp, const fnode *f, char *buffer, size_t size,
if (zero_flag)
goto skip;
+
/* Round the value. The value being rounded is an unsigned magnitude.
The ROUND_COMPATIBLE is rounding away from zero when there is a tie. */
switch (dtp->u.p.current_unit->round_status)
@@ -230,19 +231,11 @@ output_float (st_parameter_dt *dtp, const fnode *f, char *buffer, size_t size,
case ROUND_UP:
if (sign_bit)
goto skip;
- rchar = '0';
- /* Scan for trailing zeros to see if we really need to round it. */
- for(i = nbefore + nafter; i < ndigits; i++)
- {
- if (digits[i] != '0')
- goto do_rnd;
- }
- goto skip;
+ goto updown;
case ROUND_DOWN:
if (!sign_bit)
goto skip;
- rchar = '0';
- break;
+ goto updown;
case ROUND_NEAREST:
/* Round compatible unless there is a tie. A tie is a 5 with
all trailing zero's. */
@@ -254,7 +247,7 @@ output_float (st_parameter_dt *dtp, const fnode *f, char *buffer, size_t size,
if (digits[i] != '0')
goto do_rnd;
}
- /* It is a tie so round to even. */
+ /* It is a tie so round to even. */
switch (digits[nafter + nbefore - 1])
{
case '1':
@@ -274,8 +267,21 @@ output_float (st_parameter_dt *dtp, const fnode *f, char *buffer, size_t size,
case ROUND_UNSPECIFIED:
case ROUND_COMPATIBLE:
rchar = '5';
- /* Just fall through and do the actual rounding. */
+ goto do_rnd;
+ }
+
+ updown:
+
+ rchar = '0';
+ if (w > 0 && d == 0 && p == 0)
+ nbefore = 1;
+ /* Scan for trailing zeros to see if we really need to round it. */
+ for(i = nbefore + nafter; i < ndigits; i++)
+ {
+ if (digits[i] != '0')
+ goto do_rnd;
}
+ goto skip;
do_rnd: