/
contract.go
86 lines (75 loc) · 2.36 KB
/
contract.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
package types
import (
"encoding/binary"
wasmvmtypes "github.com/CosmWasm/wasmvm/types"
"github.com/tendermint/tendermint/crypto"
sdk "github.com/cosmos/cosmos-sdk/types"
)
// NewCodeInfo fills a new Contract struct
func NewCodeInfo(codeID uint64, codeHash []byte, creator sdk.AccAddress) CodeInfo {
return CodeInfo{
CodeID: codeID,
CodeHash: codeHash,
Creator: creator.String(),
}
}
// NewContractInfo creates a new instance of a given WASM contract info
func NewContractInfo(codeID uint64, address, creator, admin sdk.AccAddress, initMsg []byte) ContractInfo {
var adminAddr string
if !admin.Empty() {
adminAddr = admin.String()
}
return ContractInfo{
Address: address.String(),
CodeID: codeID,
Creator: creator.String(),
Admin: adminAddr,
InitMsg: initMsg,
}
}
// NewEnv initializes the environment for a contract instance
func NewEnv(ctx sdk.Context, contractAddr sdk.AccAddress) wasmvmtypes.Env {
env := wasmvmtypes.Env{
Block: wasmvmtypes.BlockInfo{
Height: uint64(ctx.BlockHeight()),
Time: uint64(ctx.BlockTime().UnixNano()),
ChainID: ctx.ChainID(),
},
Contract: wasmvmtypes.ContractInfo{
Address: contractAddr.String(),
},
}
return env
}
// NewInfo initializes the MessageInfo for a contract instance
func NewInfo(creator sdk.AccAddress, deposit sdk.Coins) wasmvmtypes.MessageInfo {
return wasmvmtypes.MessageInfo{
Sender: creator.String(),
Funds: NewWasmCoins(deposit),
}
}
// NewWasmCoins translates between Cosmos SDK coins and Wasm coins
func NewWasmCoins(cosmosCoins sdk.Coins) (wasmCoins []wasmvmtypes.Coin) {
for _, coin := range cosmosCoins {
wasmCoin := wasmvmtypes.Coin{
Denom: coin.Denom,
Amount: coin.Amount.String(),
}
wasmCoins = append(wasmCoins, wasmCoin)
}
return wasmCoins
}
// GenerateContractAddress generates a contract address from codeID + instanceID
// and increases last instanceID
func GenerateContractAddress(codeID uint64, instanceID uint64) sdk.AccAddress {
// NOTE: It is possible to get a duplicate address if either codeID or instanceID
// overflow 32 bits. This is highly improbable, but something that could be refactored.
contractID := codeID<<32 + instanceID
return addrFromUint64(contractID)
}
func addrFromUint64(id uint64) sdk.AccAddress {
addr := make([]byte, 20)
addr[0] = 'C'
binary.PutUvarint(addr[1:], id)
return sdk.AccAddress(crypto.AddressHash(addr))
}