Fixed non-determinism in genesis creation

This commit is contained in:
StephenButtolph 2020-04-03 15:50:29 -04:00
parent 4050be294b
commit dce704e8f0
4 changed files with 133 additions and 65 deletions

View File

@ -6,6 +6,7 @@ package genesis
import (
"testing"
"github.com/ava-labs/gecko/ids"
"github.com/ava-labs/gecko/vms/avm"
"github.com/ava-labs/gecko/vms/evm"
"github.com/ava-labs/gecko/vms/platformvm"
@ -106,9 +107,74 @@ func TestAliases(t *testing.T) {
}
func TestGenesis(t *testing.T) {
genesisBytes, _ := Genesis(LocalID)
genesisBytes, err := Genesis(LocalID)
if err != nil {
t.Fatal(err)
}
genesis := platformvm.Genesis{}
if err := platformvm.Codec.Unmarshal(genesisBytes, &genesis); err != nil {
t.Fatal(err)
}
}
func TestVMGenesis(t *testing.T) {
tests := []struct {
networkID uint32
vmID ids.ID
expectedID string
}{
{
networkID: CascadeID,
vmID: avm.ID,
expectedID: "2aJ8wzhzbDWB9utBtA4h1oqcrXJRWfj8RakJfJSo3M16i3Vk5N",
},
{
networkID: LocalID,
vmID: avm.ID,
expectedID: "4R5p2RXDGLqaifZE4hHWH9owe34pfoBULn1DrQTWivjg8o4aH",
},
}
for _, test := range tests {
genesisTx, err := VMGenesis(test.networkID, test.vmID)
if err != nil {
t.Fatal(err)
}
if result := genesisTx.ID().String(); test.expectedID != result {
t.Fatalf("%s genesisID with networkID %d was expected to be %s but was %s",
test.vmID,
test.networkID,
test.expectedID,
result)
}
}
}
func TestAVAAssetID(t *testing.T) {
tests := []struct {
networkID uint32
expectedID string
}{
{
networkID: CascadeID,
expectedID: "4AXHxutuTMNdMqLkniJhmX5M1dgtVx3Gs1LNfJZcnE3P5ewSp",
},
{
networkID: LocalID,
expectedID: "n8XH5JY1EX5VYqDeAhB4Zd4GKxi9UNQy6oPpMsCAj1Q6xkiiL",
},
}
for _, test := range tests {
avaID, err := AVAAssetID(test.networkID)
if err != nil {
t.Fatal(err)
}
if result := avaID.String(); test.expectedID != result {
t.Fatalf("AVA assetID with networkID %d was expected to be %s but was %s",
test.networkID,
test.expectedID,
result)
}
}
}

View File

@ -38,7 +38,9 @@ func (sr *ChainRouter) AddChain(chain *handler.Handler) {
sr.lock.Lock()
defer sr.lock.Unlock()
sr.chains[chain.Context().ChainID.Key()] = chain
chainID := chain.Context().ChainID
sr.log.Debug("Adding %s to the routing table", chainID)
sr.chains[chainID.Key()] = chain
}
// RemoveChain removes the specified chain so that incoming

View File

@ -77,78 +77,78 @@ func (*StaticService) BuildGenesis(_ *http.Request, args *BuildGenesisArgs, repl
Denomination: byte(assetDefinition.Denomination),
},
}
for assetType, initialStates := range assetDefinition.InitialState {
switch assetType {
case "fixedCap":
initialState := &InitialState{
FxID: 0, // TODO: Should lookup secp256k1fx FxID
}
for _, state := range initialStates {
b, err := json.Marshal(state)
if err != nil {
return err
}
holder := Holder{}
if err := json.Unmarshal(b, &holder); err != nil {
return err
}
cb58 := formatting.CB58{}
if err := cb58.FromString(holder.Address); err != nil {
return err
}
addr, err := ids.ToShortID(cb58.Bytes)
if err != nil {
return err
}
initialState.Outs = append(initialState.Outs, &secp256k1fx.TransferOutput{
Amt: uint64(holder.Amount),
OutputOwners: secp256k1fx.OutputOwners{
Threshold: 1,
Addrs: []ids.ShortID{addr},
},
})
}
initialState.Sort(c)
asset.States = append(asset.States, initialState)
case "variableCap":
initialState := &InitialState{
FxID: 0, // TODO: Should lookup secp256k1fx FxID
}
for _, state := range initialStates {
b, err := json.Marshal(state)
if err != nil {
return err
}
owners := Owners{}
if err := json.Unmarshal(b, &owners); err != nil {
return err
}
out := &secp256k1fx.MintOutput{
OutputOwners: secp256k1fx.OutputOwners{
Threshold: 1,
},
}
for _, address := range owners.Minters {
if len(assetDefinition.InitialState) > 0 {
initialState := &InitialState{
FxID: 0, // TODO: Should lookup secp256k1fx FxID
}
for assetType, initialStates := range assetDefinition.InitialState {
switch assetType {
case "fixedCap":
for _, state := range initialStates {
b, err := json.Marshal(state)
if err != nil {
return err
}
holder := Holder{}
if err := json.Unmarshal(b, &holder); err != nil {
return err
}
cb58 := formatting.CB58{}
if err := cb58.FromString(address); err != nil {
if err := cb58.FromString(holder.Address); err != nil {
return err
}
addr, err := ids.ToShortID(cb58.Bytes)
if err != nil {
return err
}
out.Addrs = append(out.Addrs, addr)
initialState.Outs = append(initialState.Outs, &secp256k1fx.TransferOutput{
Amt: uint64(holder.Amount),
OutputOwners: secp256k1fx.OutputOwners{
Threshold: 1,
Addrs: []ids.ShortID{addr},
},
})
}
out.Sort()
case "variableCap":
initialState := &InitialState{
FxID: 0, // TODO: Should lookup secp256k1fx FxID
}
for _, state := range initialStates {
b, err := json.Marshal(state)
if err != nil {
return err
}
owners := Owners{}
if err := json.Unmarshal(b, &owners); err != nil {
return err
}
initialState.Outs = append(initialState.Outs, out)
out := &secp256k1fx.MintOutput{
OutputOwners: secp256k1fx.OutputOwners{
Threshold: 1,
},
}
for _, address := range owners.Minters {
cb58 := formatting.CB58{}
if err := cb58.FromString(address); err != nil {
return err
}
addr, err := ids.ToShortID(cb58.Bytes)
if err != nil {
return err
}
out.Addrs = append(out.Addrs, addr)
}
out.Sort()
initialState.Outs = append(initialState.Outs, out)
}
default:
return errUnknownAssetType
}
initialState.Sort(c)
asset.States = append(asset.States, initialState)
default:
return errUnknownAssetType
}
initialState.Sort(c)
asset.States = append(asset.States, initialState)
}
asset.Sort()
g.Txs = append(g.Txs, &asset)

View File

@ -137,8 +137,8 @@ func (*StaticService) BuildGenesis(_ *http.Request, args *BuildGenesisArgs, repl
return errAccountHasNoValue
}
accounts = append(accounts, newAccount(
account.Address, // ID
0, // nonce
account.Address, // ID
0, // nonce
uint64(account.Balance), // balance
))
}