]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/m2/gm2-libs-ch/ldtoa.cc
Update copyright years.
[thirdparty/gcc.git] / gcc / m2 / gm2-libs-ch / ldtoa.cc
CommitLineData
1eee94d3
GM
1/* ldtoa.c provide long double floating point string conversion routines.
2
a945c346 3Copyright (C) 2009-2024 Free Software Foundation, Inc.
1eee94d3
GM
4Contributed by Gaius Mulley <gaius@glam.ac.uk>.
5
6This file is part of GNU Modula-2.
7
8GNU Modula-2 is free software; you can redistribute it and/or modify
9it under the terms of the GNU General Public License as published by
10the Free Software Foundation; either version 3, or (at your option)
11any later version.
12
13GNU Modula-2 is distributed in the hope that it will be useful, but
14WITHOUT ANY WARRANTY; without even the implied warranty of
15MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16General Public License for more details.
17
18Under Section 7 of GPL version 3, you are granted additional
19permissions described in the GCC Runtime Library Exception, version
203.1, as published by the Free Software Foundation.
21
22You should have received a copy of the GNU General Public License and
23a copy of the GCC Runtime Library Exception along with this program;
24see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
25<http://www.gnu.org/licenses/>. */
26
27#include "config.h"
28#include "system.h"
29#include "ansidecl.h"
30
62ed1066
GM
31#define LIBNAME "m2pim"
32
1eee94d3
GM
33#include "gm2-libs-host.h"
34#include "m2rts.h"
35
36# ifdef __cplusplus
37extern "C" {
38# endif
39
40#define MAX_FP_DIGITS 500
41
42typedef enum Mode { maxsignicant, decimaldigits } Mode;
43
44extern int dtoa_calcmaxsig (char *p, int ndigits);
45extern int dtoa_calcdecimal (char *p, int str_size, int ndigits);
8804eb0b 46extern bool dtoa_calcsign (char *p, int str_size);
1eee94d3
GM
47
48/* maxsignicant: return a string containing max(1,ndigits)
49 significant digits. The return string contains the string
50 produced by snprintf. decimaldigits: return a string produced by
51 fcvt. The string will contain ndigits past the decimal point
52 (ndigits may be negative). */
53
54long double
8f1711ef 55ldtoa_strtold (const char *s, bool *error)
1eee94d3
GM
56{
57 char *endp;
58 long double d;
59
60 errno = 0;
61#if defined(HAVE_STRTOLD)
62 d = strtold (s, &endp);
63#else
64 /* fall back to using strtod. */
65 d = (long double)strtod (s, &endp);
66#endif
67 if (endp != NULL && (*endp == '\0'))
68 *error = (errno != 0);
69 else
8f1711ef 70 *error = true;
1eee94d3
GM
71 return d;
72}
73
74char *
8804eb0b 75ldtoa_ldtoa (long double d, int mode, int ndigits, int *decpt, bool *sign)
1eee94d3
GM
76{
77 char format[50];
78 char *p;
79 int r;
80 switch (mode)
81 {
82
83 case maxsignicant:
84 ndigits += 20; /* enough for exponent. */
85 p = (char *) malloc (ndigits);
86 snprintf (format, 50, "%s%d%s", "%.", ndigits - 20, "LE");
87 snprintf (p, ndigits, format, d);
88 *sign = dtoa_calcsign (p, ndigits);
89 *decpt = dtoa_calcmaxsig (p, ndigits);
90 return p;
91 case decimaldigits:
92 p = (char *) malloc (MAX_FP_DIGITS + 20);
93 snprintf (format, 50, "%s%d%s", "%.", MAX_FP_DIGITS, "LE");
94 snprintf (p, MAX_FP_DIGITS + 20, format, d);
95 *sign = dtoa_calcsign (p, MAX_FP_DIGITS + 20);
96 *decpt = dtoa_calcdecimal (p, MAX_FP_DIGITS + 20, ndigits);
97 return p;
98 default:
99 abort ();
100 }
101}
102
103/* GNU Modula-2 hooks */
104
105void
106_M2_ldtoa_init (int, char **, char **)
107{
108}
109
110void
111_M2_ldtoa_finish (int, char **, char **)
112{
113}
114
115void
116_M2_ldtoa_dep (void)
117{
118}
119
120# ifdef __cplusplus
121}
122
ec6d1fc0
IS
123extern "C" void __attribute__((__constructor__))
124_M2_ldtoa_ctor (void)
1eee94d3 125{
62ed1066 126 M2RTS_RegisterModule ("ldtoa", LIBNAME, _M2_ldtoa_init, _M2_ldtoa_finish,
1eee94d3
GM
127 _M2_ldtoa_dep);
128}
129
130#else
131void
132_M2_ldtoa_ctor (void)
133{
134}
135
136# endif