[PATCH 1/3] Fix fcvt to only show 'ndigit' past decimal

classic Classic list List threaded Threaded
7 messages Options
Reply | Threaded
Open this post in threaded view
|

[PATCH 1/3] Fix fcvt to only show 'ndigit' past decimal

Keith Packard
Even if the number is really small and this means showing *no* digits.
This makes newlib match glibc, and the fcvt posix man page.

Signed-off-by: Keith Packard <[hidden email]>
---
 newlib/libc/stdlib/ecvtbuf.c | 9 +--------
 1 file changed, 1 insertion(+), 8 deletions(-)

diff --git a/newlib/libc/stdlib/ecvtbuf.c b/newlib/libc/stdlib/ecvtbuf.c
index e3d7b55d8..0a5d41a0f 100644
--- a/newlib/libc/stdlib/ecvtbuf.c
+++ b/newlib/libc/stdlib/ecvtbuf.c
@@ -235,14 +235,7 @@ fcvtbuf (double invalue,
 
   save = fcvt_buf;
 
-  if (invalue < 1.0 && invalue > -1.0)
-    {
-      p = _dtoa_r (reent, invalue, 2, ndigit, decpt, sign, &end);
-    }
-  else
-    {
-      p = _dtoa_r (reent, invalue, 3, ndigit, decpt, sign, &end);
-    }
+  p = _dtoa_r (invalue, 3, ndigit, decpt, sign, &end);
 
   /* Now copy */
 
--
2.24.0

Reply | Threaded
Open this post in threaded view
|

[PATCH 2/3] Fix gcvt to always show 'ndigits' of precision

Keith Packard
Leading zeros after the decimal point should not count
towards the 'ndigits' limit.

This makes gcvt match glibc and the posix gcvt man page.

Signed-off-by: Keith Packard <[hidden email]>
---
 newlib/libc/stdlib/ecvtbuf.c | 18 +++++++-----------
 1 file changed, 7 insertions(+), 11 deletions(-)

diff --git a/newlib/libc/stdlib/ecvtbuf.c b/newlib/libc/stdlib/ecvtbuf.c
index 0a5d41a0f..8936363ce 100644
--- a/newlib/libc/stdlib/ecvtbuf.c
+++ b/newlib/libc/stdlib/ecvtbuf.c
@@ -349,15 +349,10 @@ _gcvt (struct _reent *ptr,
       char *end;
       char *p;
 
-      if (invalue < 1.0)
- {
-  /* what we want is ndigits after the point */
-  p = _dtoa_r (ptr, invalue, 3, ndigit, &decpt, &sign, &end);
- }
-      else
- {
-  p = _dtoa_r (ptr, invalue, 2, ndigit, &decpt, &sign, &end);
- }
+      /* We always want ndigits of precision, even if that means printing
+       * a bunch of leading zeros for numbers < 1.0
+       */
+      p = _dtoa_r (invalue, 2, ndigit, &decpt, &sign, &end);
 
       if (decpt == 9999)
  {
@@ -383,11 +378,12 @@ _gcvt (struct _reent *ptr,
   if (buf == save)
     *buf++ = '0';
   *buf++ = '.';
-  while (decpt < 0 && ndigit > 0)
+
+  /* Leading zeros don't count towards 'ndigit' */
+  while (decpt < 0)
     {
       *buf++ = '0';
       decpt++;
-      ndigit--;
     }
 
   /* Print rest of stuff */
--
2.24.0

Reply | Threaded
Open this post in threaded view
|

[PATCH 3/3] Don't display trailing '.' in _dcvt

Keith Packard
In reply to this post by Keith Packard
In the two helper functions that _dcvt calls for 'f' and 'e' mode, if
there are no digits to display after the decimal point, don't add one.

Signed-off-by: Keith Packard <[hidden email]>
---
 newlib/libc/stdlib/ecvtbuf.c | 15 ++++++++++++---
 1 file changed, 12 insertions(+), 3 deletions(-)

diff --git a/newlib/libc/stdlib/ecvtbuf.c b/newlib/libc/stdlib/ecvtbuf.c
index 8936363ce..356c31b98 100644
--- a/newlib/libc/stdlib/ecvtbuf.c
+++ b/newlib/libc/stdlib/ecvtbuf.c
@@ -93,7 +93,8 @@ print_f (struct _reent *ptr,
     {
       if (p == start)
  *buf++ = '0';
-      *buf++ = '.';
+      if (decpt < 0 && ndigit > 0)
+ *buf++ = '.';
       while (decpt < 0 && ndigit > 0)
  {
   *buf++ = '0';
@@ -148,11 +149,15 @@ print_e (struct _reent *ptr,
     }
 
   *buf++ = *p++;
-  if (dot || ndigit != 0)
-    *buf++ = '.';
+  if (ndigit > 0)
+    dot = 1;
 
   while (*p && ndigit > 0)
     {
+      if (dot) {
+ *buf++ = '.';
+ dot = 0;
+      }
       *buf++ = *p++;
       ndigit--;
     }
@@ -168,6 +173,10 @@ print_e (struct _reent *ptr,
     {
       while (ndigit > 0)
  {
+  if  (dot) {
+    *buf++ = '.';
+    dot = 0;
+  }
   *buf++ = '0';
   ndigit--;
  }
--
2.24.0

Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] Fix fcvt to only show 'ndigit' past decimal

Corinna Vinschen
In reply to this post by Keith Packard
Hi Keith,

On Dec 17 22:00, Keith Packard wrote:

> Even if the number is really small and this means showing *no* digits.
> This makes newlib match glibc, and the fcvt posix man page.
>
> Signed-off-by: Keith Packard <[hidden email]>
> ---
>  newlib/libc/stdlib/ecvtbuf.c | 9 +--------
>  1 file changed, 1 insertion(+), 8 deletions(-)
>
> diff --git a/newlib/libc/stdlib/ecvtbuf.c b/newlib/libc/stdlib/ecvtbuf.c
> index e3d7b55d8..0a5d41a0f 100644
> --- a/newlib/libc/stdlib/ecvtbuf.c
> +++ b/newlib/libc/stdlib/ecvtbuf.c
> @@ -235,14 +235,7 @@ fcvtbuf (double invalue,
>  
>    save = fcvt_buf;
>  
> -  if (invalue < 1.0 && invalue > -1.0)
> -    {
> -      p = _dtoa_r (reent, invalue, 2, ndigit, decpt, sign, &end);
> -    }
> -  else
> -    {
> -      p = _dtoa_r (reent, invalue, 3, ndigit, decpt, sign, &end);
> -    }
> +  p = _dtoa_r (invalue, 3, ndigit, decpt, sign, &end);
                ^^^^^
There's a reent ptr missing in this call.  I'm puzzled that this
compiled for you.


Corinna

--
Corinna Vinschen
Cygwin Maintainer
Red Hat

signature.asc (849 bytes) Download Attachment
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 2/3] Fix gcvt to always show 'ndigits' of precision

Corinna Vinschen
In reply to this post by Keith Packard
On Dec 17 22:00, Keith Packard wrote:

> Leading zeros after the decimal point should not count
> towards the 'ndigits' limit.
>
> This makes gcvt match glibc and the posix gcvt man page.
>
> Signed-off-by: Keith Packard <[hidden email]>
> ---
>  newlib/libc/stdlib/ecvtbuf.c | 18 +++++++-----------
>  1 file changed, 7 insertions(+), 11 deletions(-)
>
> diff --git a/newlib/libc/stdlib/ecvtbuf.c b/newlib/libc/stdlib/ecvtbuf.c
> index 0a5d41a0f..8936363ce 100644
> --- a/newlib/libc/stdlib/ecvtbuf.c
> +++ b/newlib/libc/stdlib/ecvtbuf.c
> @@ -349,15 +349,10 @@ _gcvt (struct _reent *ptr,
>        char *end;
>        char *p;
>  
> -      if (invalue < 1.0)
> - {
> -  /* what we want is ndigits after the point */
> -  p = _dtoa_r (ptr, invalue, 3, ndigit, &decpt, &sign, &end);
> - }
> -      else
> - {
> -  p = _dtoa_r (ptr, invalue, 2, ndigit, &decpt, &sign, &end);
> - }
> +      /* We always want ndigits of precision, even if that means printing
> +       * a bunch of leading zeros for numbers < 1.0
> +       */
> +      p = _dtoa_r (invalue, 2, ndigit, &decpt, &sign, &end);
                   ^^^^^
                same here.


Corinna

--
Corinna Vinschen
Cygwin Maintainer
Red Hat

signature.asc (849 bytes) Download Attachment
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] Fix fcvt to only show 'ndigit' past decimal

Keith Packard
In reply to this post by Corinna Vinschen
Corinna Vinschen <[hidden email]> writes:

> There's a reent ptr missing in this call.  I'm puzzled that this
> compiled for you.

I'm rebasing fixes from a version of this code which uses TLS instead of
reent as I don't have any way of running the tests using the newlib
codebase. I messed up the rebase this time. Just trying to keep the two
versions in sync by sending all of my fixes along.

Sorry for wasting your time! The next version has actually been
compiled...

--
-keith

signature.asc (847 bytes) Download Attachment
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] Fix fcvt to only show 'ndigit' past decimal

Corinna Vinschen
On Dec 18 08:48, Keith Packard wrote:

> Corinna Vinschen <[hidden email]> writes:
>
> > There's a reent ptr missing in this call.  I'm puzzled that this
> > compiled for you.
>
> I'm rebasing fixes from a version of this code which uses TLS instead of
> reent as I don't have any way of running the tests using the newlib
> codebase. I messed up the rebase this time. Just trying to keep the two
> versions in sync by sending all of my fixes along.
>
> Sorry for wasting your time! The next version has actually been
> compiled...
No worries, I pushed all three patches now.


Thanks,
Corinna

--
Corinna Vinschen
Cygwin Maintainer
Red Hat

signature.asc (849 bytes) Download Attachment