Import latest fixes to libiberty from GCC.
[external/binutils.git] / libiberty / testsuite / test-strtol.c
1 /* Test program for strtol family of funtions,
2    Copyright (C) 2014-2017 Free Software Foundation, Inc.
3    Written by Yury Gribov <y.gribov@samsung.com>
4
5    This file is part of the libiberty library, which is part of GCC.
6
7    This file is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License as published by
9    the Free Software Foundation; either version 2 of the License, or
10    (at your option) any later version.
11
12    In addition to the permissions in the GNU General Public License, the
13    Free Software Foundation gives you unlimited permission to link the
14    compiled version of this file into combinations with other programs,
15    and to distribute those combinations without any restriction coming
16    from the use of this file.  (The General Public License restrictions
17    do apply in other respects; for example, they cover modification of
18    the file, and distribution when not linked into a combined
19    executable.)
20
21    This program is distributed in the hope that it will be useful,
22    but WITHOUT ANY WARRANTY; without even the implied warranty of
23    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
24    GNU General Public License for more details.
25
26    You should have received a copy of the GNU General Public License
27    along with this program; if not, write to the Free Software
28    Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. 
29 */
30
31 #ifdef HAVE_CONFIG_H
32 #include "config.h"
33 #endif
34 #include "libiberty.h"
35 #include <stdio.h>
36 #include <errno.h>
37 #ifdef HAVE_STDLIB_H
38 #include <stdlib.h>
39 #endif
40 #ifdef HAVE_STRING_H
41 #include <string.h>
42 #endif
43 #ifdef HAVE_UNISTD_H
44 #include <unistd.h>
45 #endif
46
47 #ifndef EXIT_SUCCESS
48 #define EXIT_SUCCESS 0
49 #endif
50
51 #ifndef EXIT_FAILURE
52 #define EXIT_FAILURE 1
53 #endif
54
55
56 /* Test input data. */
57
58 enum conversion_fun
59 {
60   STRTOL,
61   STRTOLL,
62   STRTOUL,
63   STRTOULL,
64 };
65
66 #ifdef HAVE_LONG_LONG
67 typedef unsigned long long integer_type;
68 #else
69 typedef unsigned long integer_type;
70 #endif
71
72 struct test_data_t
73 {
74   enum conversion_fun fun;
75   const char *nptr;
76   int base;
77   integer_type res;
78   int errnum;
79 };
80
81 const struct test_data_t test_data[] = {
82   { STRTOL,  "0x123",       0, 0x123L,        0      },
83   { STRTOL,  "123",         0, 123L,          0      },
84   { STRTOL,  "0123",        0, 0123L,         0      },
85   { STRTOL,  "0x7FFFFFFF",  0, 0x7fffffffL,   0      },
86   { STRTOL,  "-0x80000000", 0, -0x80000000L,  0      },
87   { STRTOUL, "0x123",       0, 0x123UL,       0      },
88   { STRTOUL, "123",         0, 123UL,         0      },
89   { STRTOUL, "0123",        0, 0123UL,        0      },
90   { STRTOUL, "0xFFFFFFFF",  0, 0xffffffffUL,  0      },
91 #if SIZEOF_LONG == 4
92   { STRTOL,  "0x80000000",  0, 0x7fffffffL,   ERANGE },
93   { STRTOL,  "-0x80000001", 0, -0x80000000L,  ERANGE },
94   { STRTOUL, "0x100000000", 0, 0xffffffffUL,  ERANGE },
95 #endif
96 #ifdef HAVE_LONG_LONG
97   { STRTOLL,  "0x123",               0, 0x123LL,               0      },
98   { STRTOLL,  "123",                 0, 123LL,                 0      },
99   { STRTOLL,  "0123",                0, 0123LL,                0      },
100   { STRTOLL,  "0x7FFFFFFFFFFFFFFF",  0, 0x7fffffffffffffffLL,  0      },
101   { STRTOLL,  "-0x8000000000000000", 0, -0x8000000000000000LL, 0      },
102   { STRTOULL, "0x123",               0, 0x123ULL,              0      },
103   { STRTOULL, "123",                 0, 123ULL,                0      },
104   { STRTOULL, "0123",                0, 0123ULL,               0      },
105   { STRTOULL, "0xFFFFFFFFFFFFFFFF",  0, 0xffffffffffffffffULL, 0      },
106 #if SIZEOF_LONG_LONG == 8
107   { STRTOLL,  "0x8000000000000000",  0, 0x7fffffffffffffffLL,  ERANGE },
108   { STRTOLL,  "-0x8000000000000001", 0, -0x8000000000000000LL, ERANGE },
109   { STRTOULL, "0x10000000000000000", 0, 0xffffffffffffffffULL, ERANGE },
110 #endif
111 #endif
112 };
113
114 /* run_tests:
115     Run conversion function
116     Compare results
117     Return number of fails */
118
119 int
120 run_tests (const struct test_data_t *test_data, size_t ntests)
121 {
122   int fails = 0, failed;
123   size_t i;
124
125   for (i = 0; i < ntests; ++i)
126     {
127       integer_type res;
128       int saved_errno;
129
130       errno = 0;
131
132       switch (test_data[i].fun)
133         {
134         case STRTOL:
135           res = (unsigned long) strtol (test_data[i].nptr,
136                                         0, test_data[i].base);
137           break;
138         case STRTOUL:
139           res = strtoul (test_data[i].nptr, 0, test_data[i].base);
140           break;
141 #ifdef HAVE_LONG_LONG
142         case STRTOLL:
143           res = strtoll (test_data[i].nptr, 0, test_data[i].base);
144           break;
145         case STRTOULL:
146           res = strtoull (test_data[i].nptr, 0, test_data[i].base);
147           break;
148 #endif
149         }
150
151       saved_errno = errno;
152
153       failed = 0;
154
155       /* Compare result */
156       if (res != test_data[i].res)
157         {
158           printf ("FAIL: test-strtol-%zd. Results don't match.\n", i);
159           failed++;
160         }
161
162       /* Compare errno */
163       if (saved_errno != test_data[i].errnum)
164         {
165           printf ("FAIL: test-strtol-%zd. Errnos don't match.\n", i);
166           failed++;
167         }
168
169       if (!failed)
170         printf ("PASS: test-strtol-%zd.\n", i);
171       else
172         fails++;
173     }
174
175   return fails;
176 }
177
178 int 
179 main(int argc, char **argv)
180 {
181   int fails;
182   fails = run_tests (test_data, sizeof (test_data) / sizeof (test_data[0]));
183   exit (fails ? EXIT_FAILURE : EXIT_SUCCESS);
184 }
185