BitShares-Core  4.0.0
BitShares blockchain implementation and command-line interface software
bigint.cpp
Go to the documentation of this file.
1 #include <fc/crypto/bigint.hpp>
2 #include <openssl/bn.h>
3 #include <fc/variant.hpp>
4 #include <fc/crypto/base64.hpp>
5 
7 
8 #include <boost/endian/buffers.hpp>
9 
10 namespace fc {
11  bigint::bigint( const char* bige, uint32_t l ) {
12  n = BN_bin2bn( (const unsigned char*)bige, l, NULL );
13  FC_ASSERT( n != nullptr );
14  }
15  bigint::bigint( const std::vector<char>& bige ) {
16  n = BN_bin2bn( (const unsigned char*)bige.data(), bige.size(), NULL );
17  FC_ASSERT( n != nullptr );
18  }
20  {
21  n = BN_dup(in);
22  }
24  :n(BN_new())
25  { }
26 
28  {
29  return BN_dup( n );
30  }
31 
32  bigint::bigint(uint64_t value)
33  {
34  boost::endian::big_uint64_buf_t big_endian_value;
35  big_endian_value = value;
36  n = BN_bin2bn((const unsigned char*)&big_endian_value, sizeof(big_endian_value), NULL);
37  }
38 
39  bigint::bigint( const bigint& c ) {
40  n = BN_dup( c.n );
41  }
42 
44  n = b.n;
45  b.n = 0;
46  }
47 
49  if(n!=0) BN_free(n);
50  }
51 
52  bool bigint::is_negative()const { return BN_is_negative(n); }
53 
54  int64_t bigint::to_int64() const
55  {
56  FC_ASSERT(BN_num_bits(n) <= 63);
57  size_t size = BN_num_bytes(n);
58  boost::endian::big_int64_buf_t abs_value;
59  abs_value = 0;
60  BN_bn2bin(n, (unsigned char*)&abs_value + (sizeof(abs_value) - size));
61  return BN_is_negative(n) ? -abs_value.value() : abs_value.value();
62  }
63 
64  int64_t bigint::log2()const { return BN_num_bits(n); }
65  bool bigint::operator < ( const bigint& c )const {
66  return BN_cmp( n, c.n ) < 0;
67  }
68  bool bigint::operator > ( const bigint& c )const {
69  return BN_cmp( n, c.n ) > 0;
70  }
71  bool bigint::operator >= ( const bigint& c )const {
72  return BN_cmp( n, c.n ) >= 0;
73  }
74  bool bigint::operator == ( const bigint& c )const {
75  return BN_cmp( n, c.n ) == 0;
76  }
77  bool bigint::operator != ( const bigint& c )const {
78  return BN_cmp( n, c.n ) != 0;
79  }
80  bigint::operator bool()const
81  {
82  return !BN_is_zero( n );
83  }
85  {
86  bigint tmp = *this;
87  *this = *this + bigint(1);
88  return tmp;
89  }
91  {
92  return *this = *this + bigint(1);
93  }
95  {
96  bigint tmp = *this;
97  *this = *this - bigint(1);
98  return tmp;
99  }
101  {
102  return *this = *this - bigint(1);
103  }
104 
105  bigint bigint::operator + ( const bigint& a )const {
106  bigint tmp(*this);
107  BN_add( tmp.n, n, a.n );
108  return tmp;
109  }
111  bigint tmp(*this);
112  BN_add( tmp.n, n, a.n );
113  std::swap(*this,tmp);
114  return *this;
115  }
117  bigint tmp(*this);
118  BN_sub( tmp.n, n, a.n );
119  std::swap(*this,tmp);
120  return *this;
121  }
122 
123 
124  bigint bigint::operator * ( const bigint& a )const {
125  BN_CTX* ctx = BN_CTX_new();
126  bigint tmp(*this);
127  BN_mul( tmp.n, n, a.n, ctx );
128  BN_CTX_free(ctx);
129  return tmp;
130  }
131  bigint bigint::operator / ( const bigint& a ) const {
132  BN_CTX* ctx = BN_CTX_new();
133  bigint tmp;
134  BN_div( tmp.n, NULL, n, a.n, ctx );
135  BN_CTX_free(ctx);
136  return tmp;
137  }
138  bigint bigint::operator % ( const bigint& a ) const {
139  BN_CTX* ctx = BN_CTX_new();
140  bigint tmp;
141  BN_mod( tmp.n, n, a.n, ctx );
142  BN_CTX_free(ctx);
143  return tmp;
144  }
145 
147  BN_CTX* ctx = BN_CTX_new();
148  bigint tmp;
149  BN_div( tmp.n, NULL, n, a.n, ctx );
150  std::swap( tmp.n, n );
151  BN_CTX_free(ctx);
152  return tmp;
153  }
155  auto tmp = *this * a;
156  *this = std::move(tmp);
157  return *this;
158  }
160  {
161  bigint tmp;
162  BN_rshift( tmp.n, n, i );
163  std::swap(*this,tmp);
164  return *this;
165  }
166 
168  {
169  bigint tmp;
170  FC_ASSERT( tmp.n != nullptr );
171  FC_ASSERT( n != nullptr );
172  BN_lshift( tmp.n, n, i );
173  std::swap(*this,tmp);
174  return *this;
175  }
176 
177  bigint bigint::operator - ( const bigint& a )const {
178  bigint tmp;
179  BN_sub( tmp.n, n, a.n );
180  return tmp;
181  }
182  bigint bigint::exp( const bigint& a )const
183  {
184  BN_CTX* ctx = BN_CTX_new();
185  bigint tmp;
186  BN_exp( tmp.n, n, a.n, ctx );
187  BN_CTX_free(ctx);
188  return tmp;
189  }
190 
191 
193  if( &a == this )
194  return *this;
195  std::swap( a.n, n );
196  return *this;
197  }
199  if( &a == this )
200  return *this;
201  BN_copy( n, a.n );
202  return *this;
203  }
204  bigint::operator std::string()const {
205  return BN_bn2dec(n);
206  }
207 
208  bigint::operator std::vector<char>()const {
209  std::vector<char> to(BN_num_bytes(n));
210  BN_bn2bin(n,(unsigned char*)to.data());
211  return to;
212  }
213 
215  void to_variant( const bigint& bi, variant& v, uint32_t max_depth )
216  {
217  std::vector<char> ve = bi;
218  v = fc::variant(base64_encode((unsigned char*)ve.data(),ve.size()));
219  }
220 
222  void from_variant( const variant& v, bigint& bi, uint32_t max_depth )
223  {
224  if( v.is_numeric() ) bi = bigint( static_cast<unsigned long>(v.as_uint64()) );
225  else
226  {
227  std::string b64 = v.as_string();
228  std::string bin = base64_decode(b64);
229  bi = bigint(bin.c_str(), bin.size() );
230  }
231  }
232 
233 } // namespace fc
bigint exp(const bigint &c) const
Definition: bigint.cpp:182
bigint operator/(const bigint &a) const
Definition: bigint.cpp:131
bool operator<(const bigint &c) const
Definition: bigint.cpp:65
bool is_numeric() const
Definition: variant.cpp:348
bool operator==(const bigint &c) const
Definition: bigint.cpp:74
BIGNUM * dup() const
Definition: bigint.cpp:27
bigint operator*=(const bigint &a)
Definition: bigint.cpp:154
std::string base64_encode(unsigned char const *bytes_to_encode, unsigned int in_len)
Definition: base64.cpp:51
uint64_t as_uint64() const
Definition: variant.cpp:398
bigint & operator=(const bigint &a)
Definition: bigint.cpp:198
bigint & operator++()
Definition: bigint.cpp:90
bigint operator+(const bigint &a) const
Definition: bigint.cpp:105
bool is_negative() const
Definition: bigint.cpp:52
int64_t to_int64() const
Definition: bigint.cpp:54
void to_variant(const flat_set< T, A... > &var, variant &vo, uint32_t _max_depth)
Definition: flat.hpp:105
bigint operator*(const bigint &a) const
Definition: bigint.cpp:124
bigint & operator<<=(uint32_t i)
Definition: bigint.cpp:167
int64_t log2() const
Definition: bigint.cpp:64
bigint & operator-=(const bigint &a)
Definition: bigint.cpp:116
#define FC_ASSERT(TEST,...)
Checks a condition and throws an assert_exception if the test is FALSE.
Definition: exception.hpp:345
bool operator>=(const bigint &c) const
Definition: bigint.cpp:71
bigint operator%(const bigint &a) const
Definition: bigint.cpp:138
stores null, int64, uint64, double, bool, string, std::vector<variant>, and variant_object&#39;s.
Definition: variant.hpp:198
bigint operator/=(const bigint &a)
Definition: bigint.cpp:146
Defines exception&#39;s used by fc.
bigint & operator+=(const bigint &a)
Definition: bigint.cpp:110
bigint & operator>>=(uint32_t i)
Definition: bigint.cpp:159
void from_variant(const variant &var, flat_set< T, A... > &vo, uint32_t _max_depth)
Definition: flat.hpp:116
bignum_st BIGNUM
Definition: bigint.hpp:6
bigint & operator--()
Definition: bigint.cpp:100
Definition: api.hpp:15
std::string base64_decode(const std::string &encoded_string)
Definition: base64.cpp:96
bigint operator-(const bigint &a) const
Definition: bigint.cpp:177
std::string as_string() const
Definition: variant.cpp:469
bool operator!=(const bigint &c) const
Definition: bigint.cpp:77
bool operator>(const bigint &c) const
Definition: bigint.cpp:68