cprover
string2int.cpp
Go to the documentation of this file.
1 /*******************************************************************\
2 
3 Module:
4 
5 Author: Michael Tautschnig, michael.tautschnig@cs.ox.ac.uk
6 
7 \*******************************************************************/
8 
9 #include "string2int.h"
10 
11 #include <cerrno>
12 #include <cstdlib>
13 #include <limits>
14 
15 #include "invariant.h"
16 
17 template <typename T>
18 inline T str2number(const char *str, int base, bool safe)
19 {
20  int errno_bak=errno;
21  errno=0;
22  char *endptr;
23 // _strtoi64 is available in Visual Studio, but not yet in MINGW
24 #ifdef _MSC_VER
25  const __int64 val=_strtoi64(str, &endptr, base);
26 #else
27  const long long val=strtoll(str, &endptr, base);
28 #endif
29 
30  if(safe)
31  {
32  CHECK_RETURN(0==errno);
33  errno=errno_bak;
34  CHECK_RETURN(endptr!=str);
35  if(std::numeric_limits<T>::min()==0)
36  {
37  // unsigned
38  CHECK_RETURN(val>=0);
40  (unsigned long long)(T)val<=
41  (unsigned long long)std::numeric_limits<T>::max());
42  }
43  else
44  {
45  // signed
46  CHECK_RETURN(val<=(long long)std::numeric_limits<T>::max());
47  CHECK_RETURN(val>=(long long)std::numeric_limits<T>::min());
48  }
49  }
50 
51  return (T)val;
52 }
53 
54 unsigned safe_string2unsigned(const std::string &str, int base)
55 {
56  return str2number<unsigned>(str.c_str(), base, true);
57 }
58 
59 std::size_t safe_string2size_t(const std::string &str, int base)
60 {
61  return str2number<std::size_t>(str.c_str(), base, true);
62 }
63 
64 int unsafe_string2int(const std::string &str, int base)
65 {
66  return str2number<int>(str.c_str(), base, false);
67 }
68 
69 unsigned unsafe_string2unsigned(const std::string &str, int base)
70 {
71  return str2number<unsigned>(str.c_str(), base, false);
72 }
73 
74 std::size_t unsafe_string2size_t(const std::string &str, int base)
75 {
76  return str2number<std::size_t>(str.c_str(), base, false);
77 }
78 
79 signed long long int unsafe_string2signedlonglong(
80  const std::string &str,
81  int base)
82 {
83  return str2number<signed long long int>(str.c_str(), base, false);
84 }
85 
86 unsigned long long int unsafe_string2unsignedlonglong(
87  const std::string &str,
88  int base)
89 {
90  return str2number<unsigned long long int>(str.c_str(), base, false);
91 }
unsigned unsafe_string2unsigned(const std::string &str, int base)
Definition: string2int.cpp:69
std::size_t safe_string2size_t(const std::string &str, int base)
Definition: string2int.cpp:59
signed long long int unsafe_string2signedlonglong(const std::string &str, int base)
Definition: string2int.cpp:79
T str2number(const char *str, int base, bool safe)
Definition: string2int.cpp:18
#define CHECK_RETURN(CONDITION)
Definition: invariant.h:470
unsigned long long int unsafe_string2unsignedlonglong(const std::string &str, int base)
Definition: string2int.cpp:86
std::size_t unsafe_string2size_t(const std::string &str, int base)
Definition: string2int.cpp:74
unsigned safe_string2unsigned(const std::string &str, int base)
Definition: string2int.cpp:54
int unsafe_string2int(const std::string &str, int base)
Definition: string2int.cpp:64