A Discrete-Event Network Simulator
API
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Groups Pages
int64x64.cc
Go to the documentation of this file.
1 #include "int64x64.h"
2 #include <stdint.h>
3 #include <iostream>
4 #include <sstream>
5 #include "assert.h"
6 
7 namespace ns3 {
8 
9 static uint8_t MostSignificantDigit (uint64_t value)
10 {
11  uint8_t n = 0;
12  do
13  {
14  n++;
15  value /= 10;
16  } while (value != 0);
17  return n;
18 }
19 
20 static uint64_t PowerOfTen (uint8_t n)
21 {
22  uint64_t retval = 1;
23  while (n > 0)
24  {
25  retval *= 10;
26  n--;
27  }
28  return retval;
29 }
30 
31 std::ostream &operator << (std::ostream &os, const int64x64_t &value)
32 {
33  int64_t hi = value.GetHigh ();
34  os << ((hi<0) ? "-" : "+") << ((hi<0) ? -hi : hi) << ".";
35  uint64_t low = value.GetLow ();
36  uint8_t msd = MostSignificantDigit (~((uint64_t)0));
37  do
38  {
39  msd--;
40  uint64_t pow = PowerOfTen (msd);
41  uint8_t digit = low / pow;
42  NS_ASSERT (digit < 10);
43  os << (uint16_t) digit;
44  low -= digit * pow;
45  } while (msd > 0 && low > 0);
46  return os;
47 }
48 
49 static uint64_t ReadDigits (std::string str)
50 {
51  const char *buf = str.c_str ();
52  uint64_t retval = 0;
53  while (*buf != 0)
54  {
55  retval *= 10;
56  retval += *buf - 0x30;
57  buf++;
58  }
59  return retval;
60 }
61 
62 std::istream &operator >> (std::istream &is, int64x64_t &value)
63 {
64  std::string str;
65 
66  is >> str;
67  bool negative;
68  // skip heading spaces
69  std::string::size_type cur;
70  cur = str.find_first_not_of (" ");
71  std::string::size_type next;
72  // first, remove the sign.
73  next = str.find ("-", cur);
74  if (next != std::string::npos)
75  {
76  negative = true;
77  next++;
78  }
79  else
80  {
81  next = str.find ("+", cur);
82  if (next != std::string::npos)
83  {
84  next++;
85  }
86  else
87  {
88  next = cur;
89  }
90  negative = false;
91  }
92  cur = next;
93  int64_t hi;
94  uint64_t lo;
95  next = str.find (".", cur);
96  if (next != std::string::npos)
97  {
98  hi = ReadDigits (str.substr (cur, next-cur));
99  lo = ReadDigits (str.substr (next+1, str.size ()-(next+1)));
100  }
101  else
102  {
103  hi = ReadDigits (str.substr (cur, str.size ()-cur));
104  lo = 0;
105  }
106  hi = negative ? -hi : hi;
107  value = int64x64_t (hi, lo);
108  return is;
109 }
110 
111 } // namespace ns3