gitee.com/lh-her-team/common@v1.5.1/evmutils/tools.go (about)

     1  /*
     2   * Copyright 2020 The SealEVM Authors
     3   *
     4   *  Licensed under the Apache License, Version 2.0 (the "License");
     5   *  you may not use this file except in compliance with the License.
     6   *  You may obtain a copy of the License at
     7   *
     8   *  http://www.apache.org/licenses/LICENSE-2.0
     9   *
    10   *  Unless required by applicable law or agreed to in writing, software
    11   *  distributed under the License is distributed on an "AS IS" BASIS,
    12   *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13   *  See the License for the specific language governing permissions and
    14   *  limitations under the License.
    15   */
    16  
    17  package evmutils
    18  
    19  import (
    20  	"crypto/ecdsa"
    21  	"crypto/elliptic"
    22  	"encoding/hex"
    23  	"fmt"
    24  
    25  	"gitee.com/lh-her-team/common/crypto"
    26  
    27  	"github.com/tjfoc/gmsm/sm2"
    28  	"golang.org/x/crypto/sha3"
    29  )
    30  
    31  const (
    32  	hashLength    = 32
    33  	AddressLength = 20
    34  )
    35  
    36  type Address [AddressLength]byte
    37  
    38  func (a *Address) SetBytes(b []byte) {
    39  	if len(b) > len(a) {
    40  		b = b[len(b)-AddressLength:]
    41  	}
    42  	copy(a[AddressLength-len(b):], b)
    43  }
    44  
    45  func (a *Address) String() string {
    46  	return hex.EncodeToString(a[:])
    47  }
    48  
    49  var (
    50  	BlankHash = make([]byte, hashLength)
    51  	ZeroHash  = Keccak256(nil)
    52  )
    53  
    54  // EVMIntToHashBytes returns the absolute value of x as a big-endian fixed length byte slice.
    55  func EVMIntToHashBytes(i *Int) [hashLength]byte {
    56  	iBytes := i.Bytes()
    57  	iLen := len(iBytes)
    58  	var hash [hashLength]byte
    59  	if iLen > hashLength {
    60  		copy(hash[:], iBytes[iLen-hashLength:])
    61  	} else {
    62  		copy(hash[hashLength-iLen:], iBytes)
    63  	}
    64  	return hash
    65  }
    66  
    67  // EthHashBytesToEVMInt EVMIntToHashBytes reverse
    68  func EthHashBytesToEVMInt(hash [hashLength]byte) (*Int, error) {
    69  	return HashBytesToEVMInt(hash[:])
    70  }
    71  
    72  // HashBytesToEVMInt byte to bigInt
    73  func HashBytesToEVMInt(hash []byte) (*Int, error) {
    74  	i := New(0)
    75  	i.SetBytes(hash[:])
    76  	return i, nil
    77  }
    78  
    79  // BytesDataToEVMIntHash fixed length bytes
    80  func BytesDataToEVMIntHash(data []byte) *Int {
    81  	var hashBytes []byte
    82  	srcLen := len(data)
    83  	if srcLen < hashLength {
    84  		hashBytes = LeftPaddingSlice(data, hashLength)
    85  	} else {
    86  		hashBytes = data[:hashLength]
    87  	}
    88  	i := New(0)
    89  	i.SetBytes(hashBytes)
    90  	return i
    91  }
    92  
    93  func GetDataFrom(src []byte, offset uint64, size uint64) []byte {
    94  	ret := make([]byte, size)
    95  	dLen := uint64(len(src))
    96  	if dLen < offset {
    97  		return ret
    98  	}
    99  	end := offset + size
   100  	if dLen < end {
   101  		end = dLen
   102  	}
   103  	copy(ret, src[offset:end])
   104  	return ret
   105  }
   106  
   107  func LeftPaddingSlice(src []byte, toSize int) []byte {
   108  	sLen := len(src)
   109  	if toSize <= sLen {
   110  		return src
   111  	}
   112  	ret := make([]byte, toSize)
   113  	copy(ret[toSize-sLen:], src)
   114  	return ret
   115  }
   116  
   117  func RightPaddingSlice(src []byte, toSize int) []byte {
   118  	sLen := len(src)
   119  	if toSize <= sLen {
   120  		return src
   121  	}
   122  	ret := make([]byte, toSize)
   123  	copy(ret, src)
   124  	return ret
   125  }
   126  
   127  func Keccak256(data []byte) []byte {
   128  	hasher := sha3.NewLegacyKeccak256()
   129  	hasher.Write(data)
   130  	return hasher.Sum(nil)
   131  }
   132  
   133  // LeftPadBytes zero-pads slice to the left up to length l.
   134  func LeftPadBytes(slice []byte, l int) []byte {
   135  	if l <= len(slice) {
   136  		return slice
   137  	}
   138  	padded := make([]byte, l)
   139  	copy(padded[l-len(slice):], slice)
   140  	return padded
   141  }
   142  
   143  // MakeAddressFromHex any hex str make an evm.Int
   144  func MakeAddressFromHex(str string) (*Int, error) {
   145  	data, err := FromHex(str)
   146  	if err != nil {
   147  		return nil, err
   148  	}
   149  	return MakeAddress(data), nil
   150  }
   151  
   152  // MakeAddressFromString any str make an evm.Int
   153  func MakeAddressFromString(str string) (*Int, error) {
   154  	return MakeAddress([]byte(str)), nil
   155  }
   156  
   157  // MakeAddress any byte make an evm.Int
   158  func MakeAddress(data []byte) *Int {
   159  	address := Keccak256(data)
   160  	addr := hex.EncodeToString(address)[24:]
   161  	return FromHexString(addr)
   162  }
   163  
   164  // BytesToAddress any byte set to an evm address
   165  func BytesToAddress(b []byte) Address {
   166  	var a Address
   167  	a.SetBytes(b)
   168  	return a
   169  }
   170  
   171  // StringToAddress any string make an evm address
   172  func StringToAddress(s string) (Address, error) {
   173  	addrInt, err := MakeAddressFromString(s)
   174  	if err != nil {
   175  		var a Address
   176  		return a, err
   177  	}
   178  	return BigToAddress(addrInt), nil
   179  }
   180  
   181  // HexToAddress direct convert hex to an evm address,直接将十六进制字符串转换为Address类型
   182  func HexToAddress(s string) (Address, error) {
   183  	addrInt, err := FromHex(s)
   184  	if err != nil {
   185  		var a Address
   186  		return a, err
   187  	}
   188  	return BytesToAddress(addrInt), nil
   189  }
   190  
   191  // MakeHexToAddress 基于十六进制数据,经过Hash计算获得一个EVM地址
   192  // @param s
   193  // @return Address
   194  // @return error
   195  func MakeHexToAddress(s string) (Address, error) {
   196  	addrInt, err := MakeAddressFromHex(s)
   197  	if err != nil {
   198  		var a Address
   199  		return a, err
   200  	}
   201  	return BigToAddress(addrInt), nil
   202  }
   203  
   204  // BigToAddress math.bigInt to evm address
   205  func BigToAddress(b *Int) Address {
   206  	return BytesToAddress(b.Bytes())
   207  }
   208  
   209  func FromHex(s string) ([]byte, error) {
   210  	if Has0xPrefix(s) {
   211  		s = s[2:]
   212  	}
   213  	if len(s)%2 == 1 {
   214  		s = "0" + s
   215  	}
   216  	return hex.DecodeString(s)
   217  }
   218  
   219  func Has0xPrefix(str string) bool {
   220  	return len(str) >= 2 && str[0] == '0' && (str[1] == 'x' || str[1] == 'X')
   221  }
   222  
   223  //MarshalPublicKey serialize pk to bytes
   224  func MarshalPublicKey(pk crypto.PublicKey) (pkBytes []byte, err error) {
   225  	pub := pk.ToStandardKey()
   226  	switch k := pub.(type) {
   227  	case *sm2.PublicKey:
   228  		pkBytes = elliptic.Marshal(k.Curve, k.X, k.Y)
   229  	case *ecdsa.PublicKey:
   230  		pkBytes = elliptic.Marshal(k.Curve, k.X, k.Y)
   231  	default:
   232  		return nil, fmt.Errorf("unsupported public key type [%T]", k)
   233  	}
   234  	return pkBytes, nil
   235  }