github.com/annchain/OG@v0.0.9/common/math/bigint.go (about)

     1  // Copyright © 2019 Annchain Authors <EMAIL ADDRESS>
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //     http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  package math
    15  
    16  import (
    17  	"encoding/json"
    18  	"fmt"
    19  	"math/big"
    20  )
    21  
    22  // DO NOT USE MSGP FOR AUTO-GENERATING HERE.
    23  // THE bigint_gen.go has been modified intentionally to adapt big.Int
    24  
    25  // FORBID: go:generate msgp
    26  // FORBID: msgp:tuple BigInt
    27  
    28  // A BigInt represents an unsigned multi-precision integer.
    29  // The BigInt should always be unsigned since the sign of the number is not serialized.
    30  type BigInt struct {
    31  	Value *big.Int
    32  }
    33  
    34  // NewBigInt allocates and returns a new BigInt set to x.
    35  func NewBigInt(x int64) *BigInt {
    36  	return &BigInt{big.NewInt(x)}
    37  }
    38  
    39  // NewBigInt allocates and returns a new BigInt set to x.
    40  func NewBigIntFromString(x string, base int) (*BigInt, bool) {
    41  	v, success := big.NewInt(0).SetString(x, base)
    42  	return &BigInt{v}, success
    43  }
    44  
    45  // NewBigInt allocates and returns a new BigInt set to x.
    46  func NewBigIntFromBigInt(x *big.Int) *BigInt {
    47  	return &BigInt{big.NewInt(0).SetBytes(x.Bytes())}
    48  }
    49  
    50  // GetBytes returns the absolute value of x as a big-endian byte slice.
    51  func (bi *BigInt) GetBytes() []byte {
    52  	return bi.Value.Bytes()
    53  }
    54  
    55  // String returns the value of x as a formatted decimal string.
    56  func (bi *BigInt) String() string {
    57  	return bi.Value.String()
    58  }
    59  
    60  // GetInt64 returns the int64 representation of x. If x cannot be represented in
    61  // an int64, the result is undefined.
    62  func (bi *BigInt) GetInt64() int64 {
    63  	return bi.Value.Int64()
    64  }
    65  
    66  // SetInt64 sets the big int to x.
    67  func (bi *BigInt) SetInt64(x int64) {
    68  	bi.Value.SetInt64(x)
    69  }
    70  
    71  // GetSigBytes returns the bytes of bigint. This bytes are for signatures only.
    72  func (bi *BigInt) GetSigBytes() []byte {
    73  	if bi.GetInt64() == 0 {
    74  		return []byte{0}
    75  	}
    76  	return bi.GetBytes()
    77  }
    78  
    79  // Sign returns:
    80  //
    81  //	-1 if x <  0
    82  //	 0 if x == 0
    83  //	+1 if x >  0
    84  //
    85  func (bi *BigInt) Sign() int {
    86  	return bi.Value.Sign()
    87  }
    88  
    89  // Set sets bi to x and returns bi.
    90  func (bi *BigInt) Set(x *BigInt) *BigInt {
    91  	bi.Value.Set(x.Value)
    92  	return bi
    93  }
    94  
    95  // Add sets bi to the sum (bi + increment) and returns bi.
    96  func (bi *BigInt) Add(increment *BigInt) *BigInt {
    97  	return NewBigIntFromBigInt(new(big.Int).Add(bi.Value, increment.Value))
    98  }
    99  
   100  // Sub sets bi to the difference (bi - decrement) and returns bi.
   101  func (bi *BigInt) Sub(decrement *BigInt) *BigInt {
   102  	return NewBigIntFromBigInt(new(big.Int).Sub(bi.Value, decrement.Value))
   103  }
   104  
   105  // SetString sets the big int to x.
   106  //
   107  // The string prefix determines the actual conversion base. A prefix of "0x" or
   108  // "0X" selects base 16; the "0" prefix selects base 8, and a "0b" or "0B" prefix
   109  // selects base 2. Otherwise the selected base is 10.
   110  func (bi *BigInt) SetString(x string, base int) {
   111  	if bi.Value == nil {
   112  		bi.Value = big.NewInt(0)
   113  	}
   114  	bi.Value.SetString(x, base)
   115  }
   116  
   117  // GetString returns the value of x as a formatted string in some number base.
   118  func (bi *BigInt) GetString(base int) string {
   119  	return bi.Value.Text(base)
   120  }
   121  
   122  func (bi *BigInt) MarshalJSON() ([]byte, error) {
   123  	res := fmt.Sprintf("%d", bi.Value)
   124  	//fmt.Println("Marshaling into ", res)
   125  	return json.Marshal(res)
   126  }
   127  
   128  func (bi *BigInt) UnmarshalJSON(b []byte) error {
   129  	var val string
   130  	err := json.Unmarshal(b, &val)
   131  	if err != nil {
   132  		panic(err)
   133  	}
   134  
   135  	bi.SetString(val, 10)
   136  	return nil
   137  }
   138  
   139  var (
   140  	// number of bits in a big.Word
   141  	wordBits = 32 << (uint64(^big.Word(0)) >> 63)
   142  	// number of bytes in a big.Word
   143  	wordBytes = wordBits / 8
   144  )
   145  
   146  // PaddedBigBytes encodes a big integer as a big-endian byte slice. The length
   147  // of the slice is at least n bytes.
   148  func PaddedBigBytes(bigint *big.Int, n int) []byte {
   149  	if bigint.BitLen()/8 >= n {
   150  		return bigint.Bytes()
   151  	}
   152  	ret := make([]byte, n)
   153  	ReadBits(bigint, ret)
   154  	return ret
   155  }
   156  
   157  // ReadBits encodes the absolute value of bigint as big-endian bytes. Callers must ensure
   158  // that buf has enough space. If buf is too short the result will be incomplete.
   159  func ReadBits(bigint *big.Int, buf []byte) {
   160  	i := len(buf)
   161  	for _, d := range bigint.Bits() {
   162  		for j := 0; j < wordBytes && i > 0; j++ {
   163  			i--
   164  			buf[i] = byte(d)
   165  			d >>= 8
   166  		}
   167  	}
   168  }
   169  
   170  // ParseBig256 parses s as a 256 bit integer in decimal or hexadecimal syntax.
   171  // Leading zeros are accepted. The empty string parses as zero.
   172  func ParseBig256(s string) (*big.Int, bool) {
   173  	if s == "" {
   174  		return new(big.Int), true
   175  	}
   176  	var bigint *big.Int
   177  	var ok bool
   178  	if len(s) >= 2 && (s[:2] == "0x" || s[:2] == "0X") {
   179  		bigint, ok = new(big.Int).SetString(s[2:], 16)
   180  	} else {
   181  		bigint, ok = new(big.Int).SetString(s, 10)
   182  	}
   183  	if ok && bigint.BitLen() > 256 {
   184  		bigint, ok = nil, false
   185  	}
   186  	return bigint, ok
   187  }
   188  
   189  // MustParseBig256 parses s as a 256 bit big integer and panics if the string is invalid.
   190  func MustParseBig256(s string) *big.Int {
   191  	v, ok := ParseBig256(s)
   192  	if !ok {
   193  		panic("invalid 256 bit integer: " + s)
   194  	}
   195  	return v
   196  }