1#include <stdlib.h>
 2#ifdef __wasilibc_unmodified_upstream // Changes to optimize printf/scanf when long double isn't needed
 3#else
 4#include "printscan.h"
 5#define __NEED_locale_t
 6#include <bits/alltypes.h>
 7#endif
 8#include "shgetc.h"
 9#include "floatscan.h"
10#include "stdio_impl.h"
11
12#if defined(__wasilibc_printscan_no_long_double)
13static long_double strtox(const char *s, char **p, int prec)
14#else
15static long double strtox(const char *s, char **p, int prec)
16#endif
17{
18	FILE f;
19	sh_fromstring(&f, s);
20	shlim(&f, 0);
21#if defined(__wasilibc_printscan_no_long_double)
22	long_double y = __floatscan(&f, prec, 1);
23#else
24	long double y = __floatscan(&f, prec, 1);
25#endif
26	off_t cnt = shcnt(&f);
27	if (p) *p = cnt ? (char *)s + cnt : (char *)s;
28	return y;
29}
30
31float strtof(const char *restrict s, char **restrict p)
32{
33	return strtox(s, p, 0);
34}
35
36double strtod(const char *restrict s, char **restrict p)
37{
38	return strtox(s, p, 1);
39}
40
41long double strtold(const char *restrict s, char **restrict p)
42{
43#if defined(__wasilibc_printscan_no_long_double)
44	long_double_not_supported();
45#else
46	return strtox(s, p, 2);
47#endif
48}