Commit 8560f422 authored by 张振华's avatar 张振华

Merge branch 'master' into guess-rpc-test

parents 0de07833 9332bf5a
......@@ -198,13 +198,14 @@ func (client *client) InitBlock() {
}
if block == nil {
startSeq := client.GetStartSeq(startHeight)
startSeq, mainHash := client.GetStartSeq(startHeight)
// 创世区块
newblock := &types.Block{}
newblock.Height = 0
newblock.BlockTime = genesisBlockTime
newblock.ParentHash = zeroHash[:]
newblock.MainHash = zeroHash[:]
newblock.MainHash = mainHash
newblock.MainHeight = startHeight
tx := client.CreateGenesisTx()
newblock.Txs = tx
newblock.TxHash = merkle.CalcMerkleRoot(newblock.Txs)
......@@ -219,9 +220,9 @@ func (client *client) InitBlock() {
}
// GetStartSeq get startSeq in mainchain
func (client *client) GetStartSeq(height int64) int64 {
func (client *client) GetStartSeq(height int64) (int64, []byte) {
if height == 0 {
return 0
return 0, nil
}
lastHeight, err := client.GetLastHeightOnMainChain()
......@@ -248,12 +249,12 @@ func (client *client) GetStartSeq(height int64) int64 {
hint.Stop()
plog.Info(fmt.Sprintf("lastHeight more than %d blocks after startHeight", minBlockNum), "lastHeight", lastHeight, "startHeight", height)
seq, err := client.GetSeqByHeightOnMainChain(height)
seq, hash, err := client.GetSeqByHeightOnMainChain(height)
if err != nil {
panic(err)
}
plog.Info("the start sequence in mainchain", "startHeight", height, "startSeq", seq)
return seq
return seq, hash
}
func (client *client) CreateGenesisTx() (ret []*types.Transaction) {
......@@ -306,33 +307,42 @@ func (client *client) GetBlockByHeight(height int64) (*types.Block, error) {
return blockDetails.Items[0].Block, nil
}
func (client *client) getLastBlockInfo() (int64, *types.Block, error) {
lastBlock, err := client.RequestLastBlock()
// 获取上一个平行链对应主链seq,hash信息
// 对于平行链创世区块特殊场景:
// 1,创世区块seq从-1开始,也就是从主链0高度同步区块,主链seq从0开始,平行链对seq=0的区块校验时候做特殊处理,不校验parentHash
// 2,创世区块seq不是-1, 也就是从主链seq=n高度同步区块,此时创世区块记录了起始高度对应的主链hash,通过hash获取当前seq,然后创世区块需要倒退一个seq,lastSeq=n-1,
// 因为对于云端主链节点,创世区块记录seq在不同主链节点上差异很大,通过记录的主链hash获取的真实seq-1来使用,主链hash使用对应区块的parenthash做校验目的
func (client *client) getLastBlockMainInfo() (int64, []byte, error) {
lastSeq, lastBlock, err := client.getLastBlockInfo()
if err != nil {
plog.Error("Parachain RequestLastBlock fail", "err", err)
return -2, nil, err
}
blockedSeq, err := client.GetBlockedSeq(lastBlock.Hash())
if lastBlock.Height == 0 && lastSeq > -1 {
mainBlock, err := client.GetBlockOnMainByHash(lastBlock.MainHash)
if err != nil {
plog.Error("Parachain GetBlockedSeq fail", "err", err)
return -2, nil, err
}
// 平行链创世区块特殊场景:
// 1,创世区块seq从-1开始,也就是从主链0高度同步区块,主链seq从0开始,平行链对seq=0的区块做特殊处理,不校验parentHash
// 2,创世区块seq不是-1, 也就是从主链seq=n高度同步区块,此时创世区块倒退一个seq,blockedSeq=n-1,
// 由于创世区块本身没有记录主块hash,需要通过最初记录的seq获取,有可能n-1 seq 是回退block 获取的Hash不对,这里获取主链第n seq的parentHash
// 在genesis create时候直接设mainhash也可以,但是会导致已有平行链所有block hash变化
if lastBlock.Height == 0 && blockedSeq > -1 {
main, err := client.GetBlockOnMainBySeq(blockedSeq + 1)
mainSeq, err := client.GetSeqByHashOnMainChain(lastBlock.MainHash)
if err != nil {
return -2, nil, err
}
lastBlock.MainHash = main.Detail.Block.ParentHash
lastBlock.MainHeight = main.Detail.Block.Height - 1
return blockedSeq, lastBlock, nil
return mainSeq - 1, mainBlock.ParentHash, nil
}
return lastSeq, lastBlock.MainHash, nil
}
func (client *client) getLastBlockInfo() (int64, *types.Block, error) {
lastBlock, err := client.RequestLastBlock()
if err != nil {
plog.Error("Parachain RequestLastBlock fail", "err", err)
return -2, nil, err
}
blockedSeq, err := client.GetBlockedSeq(lastBlock.Hash())
if err != nil {
plog.Error("Parachain GetBlockedSeq fail", "err", err)
return -2, nil, err
}
return blockedSeq, lastBlock, nil
}
......@@ -365,13 +375,13 @@ func (client *client) GetLastSeqOnMainChain() (int64, error) {
return seq.Data, nil
}
func (client *client) GetSeqByHeightOnMainChain(height int64) (int64, error) {
func (client *client) GetSeqByHeightOnMainChain(height int64) (int64, []byte, error) {
hash, err := client.GetHashByHeightOnMainChain(height)
if err != nil {
return -1, err
return -1, nil, err
}
seq, err := client.GetSeqByHashOnMainChain(hash)
return seq, err
return seq, hash, err
}
func (client *client) GetHashByHeightOnMainChain(height int64) ([]byte, error) {
......@@ -410,6 +420,16 @@ func (client *client) GetBlockOnMainBySeq(seq int64) (*types.BlockSeq, error) {
return blockSeq, nil
}
func (client *client) GetBlockOnMainByHash(hash []byte) (*types.Block, error) {
blocks, err := client.grpcClient.GetBlockByHashes(context.Background(), &types.ReqHashes{Hashes: [][]byte{hash}})
if err != nil || blocks.Items[0] == nil {
plog.Error("GetBlockOnMainByHash Not found", "blockhash", common.ToHex(hash))
return nil, err
}
return blocks.Items[0].Block, nil
}
// preBlockHash to identify the same main node
func (client *client) RequestTx(currSeq int64, preMainBlockHash []byte) ([]*types.Transaction, *types.BlockSeq, error) {
plog.Debug("Para consensus RequestTx")
......@@ -466,13 +486,13 @@ func (client *client) RequestTx(currSeq int64, preMainBlockHash []byte) ([]*type
// for genesis seq=-1 scenario, mainHash not care, as the 0 seq instead of -1
// not seq=-1 scenario, mainHash needed
func (client *client) syncFromGenesisBlock() (int64, []byte, error) {
lastSeq, lastBlock, err := client.getLastBlockInfo()
lastSeq, lastMainHash, err := client.getLastBlockMainInfo()
if err != nil {
plog.Error("Parachain getLastBlockInfo fail", "err", err)
return -2, nil, err
}
plog.Info("syncFromGenesisBlock sync from height 0")
return lastSeq + 1, lastBlock.MainHash, nil
return lastSeq + 1, lastMainHash, nil
}
// search base on para block but not last MainBlockHash, last MainBlockHash can not back tracing
......@@ -561,12 +581,11 @@ func (client *client) removeBlocks(endHeight int64) error {
func (client *client) CreateBlock() {
incSeqFlag := true
//system startup, take the last added block's seq is ok
currSeq, lastBlock, err := client.getLastBlockInfo()
currSeq, lastSeqMainHash, err := client.getLastBlockMainInfo()
if err != nil {
plog.Error("Parachain getLastBlockInfo fail", "err", err.Error())
return
}
lastSeqMainHash := lastBlock.MainHash
for {
//should be lastSeq but not LastBlockSeq as del block case the seq is not equal
lastSeq, err := client.GetLastSeq()
......@@ -660,15 +679,6 @@ func (client *client) addMinerTx(preStateHash []byte, block *types.Block, main *
MainBlockHeight: main.Detail.Block.Height,
}
//获取当前区块的所有原始tx hash 和跨链hash作为bitmap base hashs,因为有可能在执行过程中有些tx 执行error被剔除掉
if main.Detail.Block.Height >= mainForkParacrossCommitTx {
for _, tx := range txs {
status.TxHashs = append(status.TxHashs, tx.Hash())
}
txHashs := paraexec.FilterParaCrossTxHashes(types.GetTitle(), txs)
status.CrossTxHashs = append(status.CrossTxHashs, txHashs...)
}
tx, err := pt.CreateRawMinerTx(&pt.ParacrossMinerAction{
Status: status,
IsSelfConsensus: isParaSelfConsensusForked(status.MainBlockHeight),
......
......@@ -13,8 +13,12 @@ import (
"testing"
"time"
apimocks "github.com/33cn/chain33/client/mocks"
"github.com/33cn/chain33/common/address"
"github.com/33cn/chain33/common/crypto"
"github.com/33cn/chain33/queue"
qmocks "github.com/33cn/chain33/queue/mocks"
drivers "github.com/33cn/chain33/system/consensus"
"github.com/33cn/chain33/types"
typesmocks "github.com/33cn/chain33/types/mocks"
paraexec "github.com/33cn/plugin/plugin/dapp/paracross/executor"
......@@ -220,3 +224,43 @@ func TestAddMinerTx(t *testing.T) {
assert.False(t, ret)
}
func initBlock() {
println("initblock")
}
func TestGetLastBlockInfo(t *testing.T) {
para := new(client)
baseCli := drivers.NewBaseClient(&types.Consensus{Name: "name"})
para.BaseClient = baseCli
grpcClient := &typesmocks.Chain33Client{}
qClient := &qmocks.Client{}
para.InitClient(qClient, initBlock)
api := &apimocks.QueueProtocolAPI{}
para.SetAPI(api)
para.grpcClient = grpcClient
block := &types.Block{Height: 0}
msg := queue.NewMessage(0, "", 1, block)
qClient.On("NewMessage", mock.Anything, mock.Anything, mock.Anything).Return(msg)
qClient.On("Send", mock.Anything, mock.Anything).Return(nil)
qClient.On("Wait", mock.Anything).Return(msg, nil)
api.On("GetSequenceByHash", mock.Anything).Return(&types.Int64{Data: int64(1)}, nil)
mainBlock := &types.Block{ParentHash: []byte("phash")}
mainDetail := &types.BlockDetail{Block: mainBlock}
blocks := &types.BlockDetails{}
blocks.Items = append(blocks.Items, mainDetail)
grpcClient.On("GetBlockByHashes", mock.Anything, mock.Anything).Return(blocks, nil)
grpcClient.On("GetSequenceByHash", mock.Anything, mock.Anything).Return(&types.Int64{Data: int64(10)}, nil)
mainSeq, hash, err := para.getLastBlockMainInfo()
assert.NoError(t, err)
assert.Equal(t, int64(9), mainSeq)
assert.Equal(t, []byte("phash"), hash)
}
#!/usr/bin/env bash
# shellcheck disable=SC2128
set -e
set +e
set -o pipefail
set -x
MAIN_HTTP=""
CASE_ERR=""
......
all:
chmod +x ./build.sh
./build.sh $(OUT) $(FLAG)
\ No newline at end of file
#!/usr/bin/env bash
strpwd=$(pwd)
strcmd=${strpwd##*dapp/}
strapp=${strcmd%/cmd*}
OUT_DIR="${1}/$strapp"
#FLAG=$2
mkdir -p "${OUT_DIR}"
cp ./build/* "${OUT_DIR}"
OUT_TESTDIR="${1}/dapptest/$strapp"
mkdir -p "${OUT_TESTDIR}"
chmod +x ./build/test-rpc.sh
cp ./build/test-rpc.sh "${OUT_TESTDIR}"
#!/usr/bin/env bash
# shellcheck disable=SC2128
MAIN_HTTP=""
CASE_ERR=""
evm_createContract_unsignedTx="0a0365766d129407228405608060405234801561001057600080fd5b50610264806100206000396000f3fe608060405234801561001057600080fd5b50600436106100365760003560e01c8063b8e010de1461003b578063cc80f6f314610045575b600080fd5b6100436100c2565b005b61004d610109565b6040805160208082528351818301528351919283929083019185019080838360005b8381101561008757818101518382015260200161006f565b50505050905090810190601f1680156100b45780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b60408051808201909152600d8082527f5468697320697320746573742e000000000000000000000000000000000000006020909201918252610106916000916101a0565b50565b60008054604080516020601f60026000196101006001881615020190951694909404938401819004810282018101909252828152606093909290918301828280156101955780601f1061016a57610100808354040283529160200191610195565b820191906000526020600020905b81548152906001019060200180831161017857829003601f168201915b505050505090505b90565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f106101e157805160ff191683800117855561020e565b8280016001018555821561020e579182015b8281111561020e5782518255916020019190600101906101f3565b5061021a92915061021e565b5090565b61019d91905b8082111561021a576000815560010161022456fea165627a7a72305820fec5dd5ca2cb47523ba08c04749bc5c14c435afee039f3047c2b7ea2faca737800293a8a025b7b22636f6e7374616e74223a66616c73652c22696e70757473223a5b5d2c226e616d65223a22736574222c226f757470757473223a5b5d2c2270617961626c65223a66616c73652c2273746174654d75746162696c697479223a226e6f6e70617961626c65222c2274797065223a2266756e6374696f6e227d2c7b22636f6e7374616e74223a747275652c22696e70757473223a5b5d2c226e616d65223a2273686f77222c226f757470757473223a5b7b226e616d65223a22222c2274797065223a22737472696e67227d5d2c2270617961626c65223a66616c73652c2273746174654d75746162696c697479223a2276696577222c2274797065223a2266756e6374696f6e227d5d20c0c7ee04309aedc4bcfba5beca5f3a223139746a5335316b6a7772436f535153313355336f7765376759424c6653666f466d"
evm_createContract_para_unsignedTx="0a0f757365722e702e706172612e65766d129407228405608060405234801561001057600080fd5b50610264806100206000396000f3fe608060405234801561001057600080fd5b50600436106100365760003560e01c8063b8e010de1461003b578063cc80f6f314610045575b600080fd5b6100436100c2565b005b61004d610109565b6040805160208082528351818301528351919283929083019185019080838360005b8381101561008757818101518382015260200161006f565b50505050905090810190601f1680156100b45780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b60408051808201909152600d8082527f5468697320697320746573742e000000000000000000000000000000000000006020909201918252610106916000916101a0565b50565b60008054604080516020601f60026000196101006001881615020190951694909404938401819004810282018101909252828152606093909290918301828280156101955780601f1061016a57610100808354040283529160200191610195565b820191906000526020600020905b81548152906001019060200180831161017857829003601f168201915b505050505090505b90565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f106101e157805160ff191683800117855561020e565b8280016001018555821561020e579182015b8281111561020e5782518255916020019190600101906101f3565b5061021a92915061021e565b5090565b61019d91905b8082111561021a576000815560010161022456fea165627a7a7230582080ff1004de2195e6c08d0d0a65484b3d393c99c280e305cb383dbc89343cdd6a00293a8a025b7b22636f6e7374616e74223a66616c73652c22696e70757473223a5b5d2c226e616d65223a22736574222c226f757470757473223a5b5d2c2270617961626c65223a66616c73652c2273746174654d75746162696c697479223a226e6f6e70617961626c65222c2274797065223a2266756e6374696f6e227d2c7b22636f6e7374616e74223a747275652c22696e70757473223a5b5d2c226e616d65223a2273686f77222c226f757470757473223a5b7b226e616d65223a22222c2274797065223a22737472696e67227d5d2c2270617961626c65223a66616c73652c2273746174654d75746162696c697479223a2276696577222c2274797065223a2266756e6374696f6e227d5d20c0c7ee0430e1c7facdc1f199956c3a2231483969326a67464a594e5167573350695468694337796b7a5663653570764b7478"
evm_creatorAddr="14KEKbYtKKQm4wMthSK9J4La4nAiidGozt"
evm_contractAddr=""
evm_addr=""
#color
RED='\033[1;31m'
GRE='\033[1;32m'
NOC='\033[0m'
# $2=0 means true, other false
function echo_rst() {
if [ "$2" -eq 0 ]; then
echo -e "${GRE}$1 ok${NOC}"
else
echo -e "${RED}$1 fail${NOC}"
CASE_ERR="FAIL"
fi
}
function chain33_ImportPrivkey() {
local pri=$2
local acc=$3
local req='"method":"Chain33.ImportPrivkey", "params":[{"privkey":"'"$pri"'", "label":"admin"}]'
echo "#request: $req"
resp=$(curl -ksd "{$req}" "$1")
echo "#response: $resp"
ok=$(jq '(.error|not) and (.result.label=="admin") and (.result.acc.addr == "'"$acc"'")' <<<"$resp")
[ "$ok" == true ]
echo_rst "$FUNCNAME" "$?"
}
function Chain33_SendToAddress() {
local from="$1"
local to="$2"
local amount=$3
local req='"method":"Chain33.SendToAddress", "params":[{"from":"'"$from"'","to":"'"$to"'", "amount":'"$amount"', "note":"test\n"}]'
# echo "#request: $req"
resp=$(curl -ksd "{$req}" "${MAIN_HTTP}")
# echo "#response: $resp"
ok=$(jq '(.error|not) and (.result.hash|length==66)' <<<"$resp")
[ "$ok" == true ]
echo_rst "$FUNCNAME" "$?"
hash=$(jq '(.result.hash)' <<<"$resp")
echo "hash=$hash"
# query_tx "$hash"
}
function chain33_unlock() {
ok=$(curl -k -s --data-binary '{"jsonrpc":"2.0","id":2,"method":"Chain33.UnLock","params":[{"passwd":"1314fuzamei","timeout":0}]}' -H 'content-type:text/plain;' ${MAIN_HTTP} | jq -r ".result.isOK")
[ "$ok" == true ]
rst=$?
echo_rst "$FUNCNAME" "$rst"
}
function block_wait() {
local req='"method":"Chain33.GetLastHeader","params":[]'
cur_height=$(curl -ksd "{$req}" ${MAIN_HTTP} | jq ".result.height")
expect=$((cur_height + ${1}))
local count=0
while true; do
new_height=$(curl -ksd "{$req}" ${MAIN_HTTP} | jq ".result.height")
if [ "${new_height}" -ge "${expect}" ]; then
break
fi
count=$((count + 1))
sleep 1
done
echo "wait new block $count s, cur height=$expect,old=$cur_height"
}
function evm_createContract() {
validator=$1
expectRes=$2
if [ "$ispara" == "true" ]; then
paraName="user.p.para."
signRawTx "${evm_createContract_para_unsignedTx}" "${evm_creatorAddr}"
else
signRawTx "${evm_createContract_unsignedTx}" "${evm_creatorAddr}"
fi
echo_rst "CreateContract signRawTx" "$?"
sendSignedTx
echo_rst "CreateContract sendSignedTx" "$?"
block_wait 2
queryTransaction "${validator}" "${expectRes}"
echo_rst "CreateContract queryExecRes" "$?"
}
function evm_addressCheck() {
res=$(curl -s --data-binary '{"jsonrpc":"2.0","id":2,"method":"Chain33.Query","params":[{"execer":"evm","funcName":"CheckAddrExists","payload":{"addr":"'${evm_contractAddr}'"}}]}' -H 'content-type:text/plain;' ${MAIN_HTTP})
bContract=$(echo "${res}" | jq -r ".result.contract")
contractAddr=$(echo "${res}" | jq -r ".result.contractAddr")
if [ "${bContract}" == "true" ] && [ "${contractAddr}" == "${evm_contractAddr}" ]; then
echo_rst "evm address check" 0
else
echo_rst "evm address check" 1
fi
return
}
function evm_callContract() {
op=$1
validator=$2
expectRes=$3
if [ "${op}" == "preExec" ]; then
unsignedTx=$(curl -s --data-binary '{"jsonrpc":"2.0","id":2,"method":"evm.EvmCallTx","params":[{"fee":1,"caller":"'${evm_creatorAddr}'", "expire":"120s", "exec":"'${evm_addr}'", "abi": "set()"}]}' -H 'content-type:text/plain;' ${MAIN_HTTP} | jq -r ".result")
elif [ "${op}" == "Exec" ]; then
unsignedTx=$(curl -s --data-binary '{"jsonrpc":"2.0","id":2,"method":"evm.EvmCallTx","params":[{"fee":1,"caller":"'${evm_creatorAddr}'", "expire":"120s", "exec":"'${evm_addr}'", "abi": "show()"}]}' -H 'content-type:text/plain;' ${MAIN_HTTP} | jq -r ".result")
else
rst=1
echo_rst "CallContract invalid param" "$rst"
return
fi
signRawTx "${unsignedTx}" "${evm_creatorAddr}"
rst=$?
echo_rst "CallContract signRawTx" "$rst"
if [ ${rst} == 1 ]; then
return
fi
sendSignedTx
echo_rst "CallContract sendSignedTx" "$?"
block_wait 2
queryTransaction "${validator}" "${expectRes}"
echo_rst "CallContract queryExecRes" "$?"
}
function evm_abiGet() {
abiInfo=$(curl -s --data-binary '{"jsonrpc":"2.0","id":2,"method":"Chain33.Query","params":[{"execer":"evm","funcName":"QueryABI","payload":{"address":"'${evm_contractAddr}'"}}]}' -H 'content-type:text/plain;' ${MAIN_HTTP})
res=$(echo "${abiInfo}" | jq -r ".result" | jq -r 'has("abi")')
if [ "${res}" == "true" ]; then
echo_rst "CallContract queryExecRes" 0
else
echo_rst "CallContract queryExecRes" 1
fi
return
}
function evm_transfer() {
validator=$1
expectRes=$2
unsignedTx=$(curl -s --data-binary '{"jsonrpc":"2.0","id":2,"method":"evm.EvmTransferTx","params":[{"amount":1,"caller":"'${evm_creatorAddr}'","expire":"", "exec":"'${evm_addr}'", "paraName": "'${paraName}'"}]}' -H 'content-type:text/plain;' ${MAIN_HTTP} | jq -r ".result")
if [ "${unsignedTx}" == "" ]; then
rst=1
echo_rst "evm transfer create tx" "$rst"
return
fi
signRawTx "${unsignedTx}" "${evm_creatorAddr}"
echo_rst "evm transfer signRawTx" "$?"
sendSignedTx
echo_rst "evm transfer sendSignedTx" "$?"
block_wait 2
queryTransaction "${validator}" "${expectRes}"
echo_rst "evm transfer queryExecRes" "$?"
}
function evm_getBalance() {
expectBalance=$1
echo "This is evm get balance test."
res=$(curl -s --data-binary '{"jsonrpc":"2.0","id":2,"method":"Chain33.GetBalance","params":[{"addresses":["'${evm_creatorAddr}'"],"execer":"'${evm_addr}'", "paraName": "'${paraName}'"}]}' -H 'content-type:text/plain;' ${MAIN_HTTP})
balance=$(echo "${res}" | jq -r ".result[0].balance")
addr=$(echo "${res}" | jq -r ".result[0].addr")
if [ "${balance}" == "${expectBalance}" ] && [ "${addr}" == "${evm_creatorAddr}" ]; then
echo_rst "evm getBalance" 0
else
echo_rst "evm getBalance" 1
fi
}
function evm_withDraw() {
validator=$1
expectRes=$2
unsignedTx=$(curl -s --data-binary '{"jsonrpc":"2.0","id":2,"method":"evm.EvmWithdrawTx","params":[{"amount":1,"caller":"'${evm_creatorAddr}'","expire":"", "exec":"'${evm_addr}'", "paraName":"'${paraName}'"}]}' -H 'content-type:text/plain;' ${MAIN_HTTP} | jq -r ".result")
if [ "${unsignedTx}" == "" ]; then
rst=1
echo_rst "evm withdraw create tx" "$rst"
return
fi
signRawTx "${unsignedTx}" "${evm_creatorAddr}"
echo_rst "evm withdraw signRawTx" "$?"
sendSignedTx
echo_rst "evm withdraw sendSignedTx" "$?"
block_wait 2
queryTransaction "${validator}" "${expectRes}"
echo_rst "evm withdraw queryExecRes" "$?"
}
function signRawTx() {
unsignedTx=$1
addr=$2
signedTx=$(curl -s --data-binary '{"jsonrpc":"2.0","id":2,"method":"Chain33.SignRawTx","params":[{"addr":"'"${addr}"'","txHex":"'"${unsignedTx}"'","expire":"120s"}]}' -H 'content-type:text/plain;' ${MAIN_HTTP} | jq -r ".result")
if [ "$signedTx" == "null" ]; then
return 1
else
return 0
fi
}
function sendSignedTx() {
txHash=$(curl -s --data-binary '{"jsonrpc":"2.0","id":2,"method":"Chain33.SendTransaction","params":[{"token":"","data":"'"${signedTx}"'"}]}' -H 'content-type:text/plain;' ${MAIN_HTTP} | jq -r ".result")
if [ "$txHash" == "null" ]; then
return 1
else
return 0
fi
}
# 查询交易的执行结果
# 根据传入的规则,校验查询的结果 (参数1: 校验规则 参数2: 预期匹配结果)
function queryTransaction() {
validators=$1
expectRes=$2
echo "txhash=${txHash}"
res=$(curl -s --data-binary '{"jsonrpc":"2.0","id":2,"method":"Chain33.QueryTransaction","params":[{"hash":"'"${txHash}"'"}]}' -H 'content-type:text/plain;' ${MAIN_HTTP})
times=$(echo "${validators}" | awk -F '|' '{print NF}')
for ((i = 1; i <= times; i++)); do
validator=$(echo "${validators}" | awk -F '|' '{print $'$i'}')
res=$(echo "${res}" | ${validator})
done
if [ "${res}" != "${expectRes}" ]; then
return 1
else
res=$(curl -s --data-binary '{"jsonrpc":"2.0","id":2,"method":"Chain33.QueryTransaction","params":[{"hash":"'"${txHash}"'"}]}' -H 'content-type:text/plain;' ${MAIN_HTTP})
if [ "${evm_addr}" == "" ]; then
if [ "$ispara" == "true" ]; then
evm_addr=$(echo "${res}" | jq -r ".result.receipt.logs[0].log.contractName")
else
evm_addr=$(echo "${res}" | jq -r ".result.receipt.logs[1].log.contractName")
fi
fi
if [ "${evm_contractAddr}" == "" ]; then
if [ "$ispara" == "true" ]; then
evm_contractAddr=$(echo "${res}" | jq -r ".result.receipt.logs[0].log.contractAddr")
else
evm_contractAddr=$(echo "${res}" | jq -r ".result.receipt.logs[1].log.contractAddr")
fi
fi
return 0
fi
}
function init() {
ispara=$(echo '"'"${MAIN_HTTP}"'"' | jq '.|contains("8901")')
echo "ipara=$ispara"
from="14KEKbYtKKQm4wMthSK9J4La4nAiidGozt"
local evm_addr=""
if [ "$ispara" == "true" ]; then
evm_addr=$(curl -ksd '{"method":"Chain33.ConvertExectoAddr","params":[{"execname":"user.p.para.evm"}]}' ${MAIN_HTTP} | jq -r ".result")
Chain33_SendToAddress "$from" "$evm_addr" 10000000000
else
evm_addr=$(curl -ksd '{"method":"Chain33.ConvertExectoAddr","params":[{"execname":"evm"}]}' ${MAIN_HTTP} | jq -r ".result")
fi
echo "evm=$evm_addr"
Chain33_SendToAddress "$from" "$evm_addr" 10000000000
block_wait 2
}
function run_test() {
local ip=$1
evm_createContract "jq -r .result.receipt.tyName" "ExecOk"
evm_addressCheck
if [ "$ispara" == "true" ]; then
evm_callContract preExec "jq -r .result.receipt.logs[0].tyName" "LogEVMStateChangeItem"
evm_callContract Exec "jq -r .result.receipt.logs[0].log.jsonRet | jq -r .[0].value" "This is test."
else
evm_callContract preExec "jq -r .result.receipt.logs[1].tyName" "LogEVMStateChangeItem"
evm_callContract Exec "jq -r .result.receipt.logs[1].log.jsonRet | jq -r .[0].value" "This is test."
fi
evm_abiGet
evm_transfer "jq -r .result.receipt.tyName" "ExecOk"
evm_getBalance 100000000
evm_withDraw "jq -r .result.receipt.tyName" "ExecOk"
evm_getBalance 0
}
function main() {
local ip=$1
MAIN_HTTP=$ip
echo "=========== # evm rpc test ============="
echo "main_ip=$MAIN_HTTP"
init
run_test "$MAIN_HTTP"
if [ -n "$CASE_ERR" ]; then
echo -e "${RED}=============Evm Rpc Test Fail=============${NOC}"
exit 1
else
echo -e "${GRE}=============Evm Rpc Test Pass==============${NOC}"
fi
}
main "$1"
......@@ -8,6 +8,7 @@ import (
"github.com/33cn/chain33/pluginmgr"
"github.com/33cn/plugin/plugin/dapp/evm/commands"
"github.com/33cn/plugin/plugin/dapp/evm/executor"
"github.com/33cn/plugin/plugin/dapp/evm/rpc"
"github.com/33cn/plugin/plugin/dapp/evm/types"
)
......@@ -17,6 +18,6 @@ func init() {
ExecName: executor.GetName(),
Exec: executor.Init,
Cmd: commands.EvmCmd,
RPC: nil,
RPC: rpc.Init,
})
}
......@@ -147,3 +147,35 @@ message EvmQueryResp {
string rawData = 4;
string jsonData = 5;
}
message EvmContractCreateReq {
string code = 1;
int64 fee = 2;
string note = 3;
string alias = 4;
string caller = 5;
string abi = 6;
string expire = 7;
string paraName = 8;
}
message EvmContractCallReq {
uint64 amount = 1;
string code = 2;
int64 fee = 3;
string note = 4;
string caller = 5;
string abi = 6;
string exec = 7;
string expire = 8;
string paraName = 9;
}
message EvmContractTransferReq {
string caller = 1;
float amount = 2;
string exec = 3;
string expire = 4;
bool isWithdraw = 5;
string paraName = 6;
}
\ No newline at end of file
// Copyright Fuzamei Corp. 2018 All Rights Reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package rpc
import (
"context"
"encoding/hex"
"github.com/33cn/chain33/types"
evm "github.com/33cn/plugin/plugin/dapp/evm/types"
)
// EvmCreateTx 创建Evm合约接口
func (c *Jrpc) EvmCreateTx(parm *evm.EvmContractCreateReq, result *interface{}) error {
if parm == nil {
return types.ErrInvalidParam
}
reply, err := c.cli.Create(context.Background(), *parm)
if err != nil {
return err
}
*result = hex.EncodeToString(reply.Data)
return nil
}
// EvmCallTx 调用Evm合约接口
func (c *Jrpc) EvmCallTx(parm *evm.EvmContractCallReq, result *interface{}) error {
if parm == nil {
return types.ErrInvalidParam
}
reply, err := c.cli.Call(context.Background(), *parm)
if err != nil {
return err
}
*result = hex.EncodeToString(reply.Data)
return nil
}
// EvmTransferTx Evm转账接口
func (c *Jrpc) EvmTransferTx(parm *evm.EvmContractTransferReq, result *interface{}) error {
if parm == nil {
return types.ErrInvalidParam
}
reply, err := c.cli.Transfer(context.Background(), *parm, false)
if err != nil {
return err
}
*result = hex.EncodeToString(reply.Data)
return nil
}
// EvmWithdrawTx Evm转账接口
func (c *Jrpc) EvmWithdrawTx(parm *evm.EvmContractTransferReq, result *interface{}) error {
if parm == nil {
return types.ErrInvalidParam
}
reply, err := c.cli.Transfer(context.Background(), *parm, true)
if err != nil {
return err
}
*result = hex.EncodeToString(reply.Data)
return nil
}
// Copyright Fuzamei Corp. 2018 All Rights Reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package rpc
import (
"context"
"fmt"
"math/rand"
"os"
"time"
"github.com/33cn/chain33/common"
"github.com/33cn/chain33/common/address"
cty "github.com/33cn/chain33/system/dapp/coins/types"
"github.com/33cn/chain33/types"
evmtypes "github.com/33cn/plugin/plugin/dapp/evm/types"
)
// CreateEvmCallTx 创建未签名的调用evm交易
func (c *channelClient) Create(ctx context.Context, in evmtypes.EvmContractCreateReq) (*types.UnsignTx, error) {
bCode, err := common.FromHex(in.Code)
if err != nil {
fmt.Fprintln(os.Stderr, "parse evm code error", err)
return nil, err
}
action := evmtypes.EVMContractAction{Amount: 0, Code: bCode, GasLimit: 0, GasPrice: 0, Note: in.Note, Abi: in.Abi}
execer := types.ExecName(in.ParaName + "evm")
addr := address.ExecAddress(types.ExecName(in.ParaName + "evm"))
tx := &types.Transaction{Execer: []byte(execer), Payload: types.Encode(&action), Fee: 0, To: addr}
tx.Fee, _ = tx.GetRealFee(types.GInt("MinFee"))
if tx.Fee < in.Fee {
tx.Fee += in.Fee
}
random := rand.New(rand.NewSource(time.Now().UnixNano()))
tx.Nonce = random.Int63()
txHex := types.Encode(tx)
return &types.UnsignTx{Data: txHex}, nil
}
func (c *channelClient) Call(ctx context.Context, in evmtypes.EvmContractCallReq) (*types.UnsignTx, error) {
amountInt64 := in.Amount * 1e4 * 1e4
feeInt64 := in.Fee * 1e4 * 1e4
toAddr := address.ExecAddress(in.Exec)
bCode, err := common.FromHex(in.Code)
if err != nil {
fmt.Fprintln(os.Stderr, "parse evm code error", err)
return nil, err
}
action := evmtypes.EVMContractAction{Amount: amountInt64, Code: bCode, GasLimit: 0, GasPrice: 0, Note: in.Note, Abi: in.Abi}
tx := &types.Transaction{Execer: []byte(in.Exec), Payload: types.Encode(&action), Fee: 0, To: toAddr}
tx.Fee, _ = tx.GetRealFee(types.GInt("MinFee"))
if tx.Fee < feeInt64 {
tx.Fee += feeInt64
}
random := rand.New(rand.NewSource(time.Now().UnixNano()))
tx.Nonce = random.Int63()
txHex := types.Encode(tx)
return &types.UnsignTx{Data: txHex}, nil
}
func (c *channelClient) Transfer(ctx context.Context, in evmtypes.EvmContractTransferReq, isWithdraw bool) (*types.UnsignTx, error) {
var tx *types.Transaction
transfer := &cty.CoinsAction{}
amountInt64 := int64(in.Amount*1e4) * 1e4
execName := in.Exec
if isWithdraw {
transfer.Value = &cty.CoinsAction_Withdraw{Withdraw: &types.AssetsWithdraw{Amount: amountInt64, ExecName: execName, To: address.ExecAddress(execName)}}
transfer.Ty = cty.CoinsActionWithdraw
} else {
transfer.Value = &cty.CoinsAction_TransferToExec{TransferToExec: &types.AssetsTransferToExec{Amount: amountInt64, ExecName: execName, To: address.ExecAddress(execName)}}
transfer.Ty = cty.CoinsActionTransferToExec
}
if in.ParaName == "" {
tx = &types.Transaction{Execer: []byte(types.ExecName(in.ParaName + "coins")), Payload: types.Encode(transfer), To: address.ExecAddress(execName)}
} else {
tx = &types.Transaction{Execer: []byte(types.ExecName(in.ParaName + "coins")), Payload: types.Encode(transfer), To: address.ExecAddress(types.ExecName(in.ParaName + "coins"))}
}
var err error
tx.Fee, err = tx.GetRealFee(types.GInt("MinFee"))
if err != nil {
return nil, err
}
random := rand.New(rand.NewSource(time.Now().UnixNano()))
tx.Nonce = random.Int63()
txHex := types.Encode(tx)
return &types.UnsignTx{Data: txHex}, nil
}
// Copyright Fuzamei Corp. 2018 All Rights Reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package rpc
import (
"github.com/33cn/chain33/rpc/types"
)
// Jrpc json rpc struct
type Jrpc struct {
cli *channelClient
}
// Grpc grpc struct
type Grpc struct {
*channelClient
}
type channelClient struct {
types.ChannelClient
}
// Init init grpc param
func Init(name string, s types.RPCServer) {
cli := &channelClient{}
grpc := &Grpc{channelClient: cli}
cli.Init(name, s, &Jrpc{cli: cli}, grpc)
}
......@@ -1184,6 +1184,283 @@ func (m *EvmQueryResp) GetJsonData() string {
return ""
}
type EvmContractCreateReq struct {
Code string `protobuf:"bytes,1,opt,name=code,proto3" json:"code,omitempty"`
Fee int64 `protobuf:"varint,2,opt,name=fee,proto3" json:"fee,omitempty"`
Note string `protobuf:"bytes,3,opt,name=note,proto3" json:"note,omitempty"`
Alias string `protobuf:"bytes,4,opt,name=alias,proto3" json:"alias,omitempty"`
Caller string `protobuf:"bytes,5,opt,name=caller,proto3" json:"caller,omitempty"`
Abi string `protobuf:"bytes,6,opt,name=abi,proto3" json:"abi,omitempty"`
Expire string `protobuf:"bytes,7,opt,name=expire,proto3" json:"expire,omitempty"`
ParaName string `protobuf:"bytes,8,opt,name=paraName,proto3" json:"paraName,omitempty"`
XXX_NoUnkeyedLiteral struct{} `json:"-"`
XXX_unrecognized []byte `json:"-"`
XXX_sizecache int32 `json:"-"`
}
func (m *EvmContractCreateReq) Reset() { *m = EvmContractCreateReq{} }
func (m *EvmContractCreateReq) String() string { return proto.CompactTextString(m) }
func (*EvmContractCreateReq) ProtoMessage() {}
func (*EvmContractCreateReq) Descriptor() ([]byte, []int) {
return fileDescriptor_74353de561acd7c6, []int{19}
}
func (m *EvmContractCreateReq) XXX_Unmarshal(b []byte) error {
return xxx_messageInfo_EvmContractCreateReq.Unmarshal(m, b)
}
func (m *EvmContractCreateReq) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
return xxx_messageInfo_EvmContractCreateReq.Marshal(b, m, deterministic)
}
func (m *EvmContractCreateReq) XXX_Merge(src proto.Message) {
xxx_messageInfo_EvmContractCreateReq.Merge(m, src)
}
func (m *EvmContractCreateReq) XXX_Size() int {
return xxx_messageInfo_EvmContractCreateReq.Size(m)
}
func (m *EvmContractCreateReq) XXX_DiscardUnknown() {
xxx_messageInfo_EvmContractCreateReq.DiscardUnknown(m)
}
var xxx_messageInfo_EvmContractCreateReq proto.InternalMessageInfo
func (m *EvmContractCreateReq) GetCode() string {
if m != nil {
return m.Code
}
return ""
}
func (m *EvmContractCreateReq) GetFee() int64 {
if m != nil {
return m.Fee
}
return 0
}
func (m *EvmContractCreateReq) GetNote() string {
if m != nil {
return m.Note
}
return ""
}
func (m *EvmContractCreateReq) GetAlias() string {
if m != nil {
return m.Alias
}
return ""
}
func (m *EvmContractCreateReq) GetCaller() string {
if m != nil {
return m.Caller
}
return ""
}
func (m *EvmContractCreateReq) GetAbi() string {
if m != nil {
return m.Abi
}
return ""
}
func (m *EvmContractCreateReq) GetExpire() string {
if m != nil {
return m.Expire
}
return ""
}
func (m *EvmContractCreateReq) GetParaName() string {
if m != nil {
return m.ParaName
}
return ""
}
type EvmContractCallReq struct {
Amount uint64 `protobuf:"varint,1,opt,name=amount,proto3" json:"amount,omitempty"`
Code string `protobuf:"bytes,2,opt,name=code,proto3" json:"code,omitempty"`
Fee int64 `protobuf:"varint,3,opt,name=fee,proto3" json:"fee,omitempty"`
Note string `protobuf:"bytes,4,opt,name=note,proto3" json:"note,omitempty"`
Caller string `protobuf:"bytes,5,opt,name=caller,proto3" json:"caller,omitempty"`
Abi string `protobuf:"bytes,6,opt,name=abi,proto3" json:"abi,omitempty"`
Exec string `protobuf:"bytes,7,opt,name=exec,proto3" json:"exec,omitempty"`
Expire string `protobuf:"bytes,8,opt,name=expire,proto3" json:"expire,omitempty"`
ParaName string `protobuf:"bytes,9,opt,name=paraName,proto3" json:"paraName,omitempty"`
XXX_NoUnkeyedLiteral struct{} `json:"-"`
XXX_unrecognized []byte `json:"-"`
XXX_sizecache int32 `json:"-"`
}
func (m *EvmContractCallReq) Reset() { *m = EvmContractCallReq{} }
func (m *EvmContractCallReq) String() string { return proto.CompactTextString(m) }
func (*EvmContractCallReq) ProtoMessage() {}
func (*EvmContractCallReq) Descriptor() ([]byte, []int) {
return fileDescriptor_74353de561acd7c6, []int{20}
}
func (m *EvmContractCallReq) XXX_Unmarshal(b []byte) error {
return xxx_messageInfo_EvmContractCallReq.Unmarshal(m, b)
}
func (m *EvmContractCallReq) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
return xxx_messageInfo_EvmContractCallReq.Marshal(b, m, deterministic)
}
func (m *EvmContractCallReq) XXX_Merge(src proto.Message) {
xxx_messageInfo_EvmContractCallReq.Merge(m, src)
}
func (m *EvmContractCallReq) XXX_Size() int {
return xxx_messageInfo_EvmContractCallReq.Size(m)
}
func (m *EvmContractCallReq) XXX_DiscardUnknown() {
xxx_messageInfo_EvmContractCallReq.DiscardUnknown(m)
}
var xxx_messageInfo_EvmContractCallReq proto.InternalMessageInfo
func (m *EvmContractCallReq) GetAmount() uint64 {
if m != nil {
return m.Amount
}
return 0
}
func (m *EvmContractCallReq) GetCode() string {
if m != nil {
return m.Code
}
return ""
}
func (m *EvmContractCallReq) GetFee() int64 {
if m != nil {
return m.Fee
}
return 0
}
func (m *EvmContractCallReq) GetNote() string {
if m != nil {
return m.Note
}
return ""
}
func (m *EvmContractCallReq) GetCaller() string {
if m != nil {
return m.Caller
}
return ""
}
func (m *EvmContractCallReq) GetAbi() string {
if m != nil {
return m.Abi
}
return ""
}
func (m *EvmContractCallReq) GetExec() string {
if m != nil {
return m.Exec
}
return ""
}
func (m *EvmContractCallReq) GetExpire() string {
if m != nil {
return m.Expire
}
return ""
}
func (m *EvmContractCallReq) GetParaName() string {
if m != nil {
return m.ParaName
}
return ""
}
type EvmContractTransferReq struct {
Caller string `protobuf:"bytes,1,opt,name=caller,proto3" json:"caller,omitempty"`
Amount float32 `protobuf:"fixed32,2,opt,name=amount,proto3" json:"amount,omitempty"`
Exec string `protobuf:"bytes,3,opt,name=exec,proto3" json:"exec,omitempty"`
Expire string `protobuf:"bytes,4,opt,name=expire,proto3" json:"expire,omitempty"`
IsWithdraw bool `protobuf:"varint,5,opt,name=isWithdraw,proto3" json:"isWithdraw,omitempty"`
ParaName string `protobuf:"bytes,6,opt,name=paraName,proto3" json:"paraName,omitempty"`
XXX_NoUnkeyedLiteral struct{} `json:"-"`
XXX_unrecognized []byte `json:"-"`
XXX_sizecache int32 `json:"-"`
}
func (m *EvmContractTransferReq) Reset() { *m = EvmContractTransferReq{} }
func (m *EvmContractTransferReq) String() string { return proto.CompactTextString(m) }
func (*EvmContractTransferReq) ProtoMessage() {}
func (*EvmContractTransferReq) Descriptor() ([]byte, []int) {
return fileDescriptor_74353de561acd7c6, []int{21}
}
func (m *EvmContractTransferReq) XXX_Unmarshal(b []byte) error {
return xxx_messageInfo_EvmContractTransferReq.Unmarshal(m, b)
}
func (m *EvmContractTransferReq) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
return xxx_messageInfo_EvmContractTransferReq.Marshal(b, m, deterministic)
}
func (m *EvmContractTransferReq) XXX_Merge(src proto.Message) {
xxx_messageInfo_EvmContractTransferReq.Merge(m, src)
}
func (m *EvmContractTransferReq) XXX_Size() int {
return xxx_messageInfo_EvmContractTransferReq.Size(m)
}
func (m *EvmContractTransferReq) XXX_DiscardUnknown() {
xxx_messageInfo_EvmContractTransferReq.DiscardUnknown(m)
}
var xxx_messageInfo_EvmContractTransferReq proto.InternalMessageInfo
func (m *EvmContractTransferReq) GetCaller() string {
if m != nil {
return m.Caller
}
return ""
}
func (m *EvmContractTransferReq) GetAmount() float32 {
if m != nil {
return m.Amount
}
return 0
}
func (m *EvmContractTransferReq) GetExec() string {
if m != nil {
return m.Exec
}
return ""
}
func (m *EvmContractTransferReq) GetExpire() string {
if m != nil {
return m.Expire
}
return ""
}
func (m *EvmContractTransferReq) GetIsWithdraw() bool {
if m != nil {
return m.IsWithdraw
}
return false
}
func (m *EvmContractTransferReq) GetParaName() string {
if m != nil {
return m.ParaName
}
return ""
}
func init() {
proto.RegisterType((*EVMContractObject)(nil), "types.EVMContractObject")
proto.RegisterType((*EVMContractData)(nil), "types.EVMContractData")
......@@ -1206,63 +1483,76 @@ func init() {
proto.RegisterType((*EvmQueryAbiResp)(nil), "types.EvmQueryAbiResp")
proto.RegisterType((*EvmQueryReq)(nil), "types.EvmQueryReq")
proto.RegisterType((*EvmQueryResp)(nil), "types.EvmQueryResp")
proto.RegisterType((*EvmContractCreateReq)(nil), "types.EvmContractCreateReq")
proto.RegisterType((*EvmContractCallReq)(nil), "types.EvmContractCallReq")
proto.RegisterType((*EvmContractTransferReq)(nil), "types.EvmContractTransferReq")
}
func init() { proto.RegisterFile("evmcontract.proto", fileDescriptor_74353de561acd7c6) }
var fileDescriptor_74353de561acd7c6 = []byte{
// 833 bytes of a gzipped FileDescriptorProto
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xcc, 0x56, 0x4b, 0x6f, 0x2b, 0x35,
0x18, 0xd5, 0x24, 0x93, 0xc7, 0x7c, 0x09, 0xb7, 0xad, 0x81, 0x32, 0xaa, 0x58, 0x44, 0x16, 0x17,
0xa2, 0x2b, 0x11, 0xa1, 0xcb, 0x06, 0x5d, 0x09, 0xa4, 0x28, 0x77, 0x54, 0x90, 0x08, 0x0f, 0x57,
0x64, 0xef, 0xcc, 0x98, 0x74, 0xda, 0xcc, 0x83, 0xb1, 0x27, 0x28, 0x5b, 0xd6, 0x2c, 0x59, 0xb2,
0x63, 0xc9, 0x92, 0x1d, 0x3f, 0x87, 0x15, 0x3f, 0x03, 0x7d, 0x1e, 0xcf, 0x2b, 0x4d, 0x2a, 0x21,
0x55, 0x88, 0x55, 0x7d, 0xec, 0x63, 0xfb, 0x9c, 0xf9, 0xce, 0xe7, 0x06, 0x2e, 0xc4, 0x2e, 0xf2,
0x93, 0x58, 0x65, 0xdc, 0x57, 0xb3, 0x34, 0x4b, 0x54, 0x42, 0x7a, 0x6a, 0x9f, 0x0a, 0x49, 0x7f,
0xb2, 0xe0, 0xc2, 0x5b, 0x2d, 0x17, 0x66, 0xf1, 0xeb, 0xf5, 0x9d, 0xf0, 0x15, 0x21, 0x60, 0xf3,
0x20, 0xc8, 0x5c, 0x6b, 0x62, 0x4d, 0x1d, 0xa6, 0xc7, 0xe4, 0x05, 0xd8, 0x01, 0x57, 0xdc, 0xed,
0x4c, 0xac, 0xe9, 0xe8, 0xe5, 0xe5, 0x4c, 0xef, 0x9f, 0x35, 0xf6, 0xbe, 0xe6, 0x8a, 0x33, 0xcd,
0x21, 0x1f, 0x42, 0x4f, 0x2a, 0xae, 0x84, 0xdb, 0xd5, 0xe4, 0x77, 0x1e, 0x92, 0x6f, 0x70, 0x99,
0x15, 0x2c, 0xfa, 0xbb, 0x05, 0x67, 0x07, 0x07, 0x11, 0x17, 0x06, 0x7e, 0x26, 0xb8, 0x4a, 0x4a,
0x15, 0x25, 0x44, 0x71, 0x31, 0x8f, 0x84, 0x16, 0xe2, 0x30, 0x3d, 0x26, 0x6f, 0x41, 0x8f, 0x6f,
0x43, 0x2e, 0xf5, 0x85, 0x0e, 0x2b, 0x40, 0x65, 0xc3, 0x6e, 0xd8, 0x20, 0x60, 0xfb, 0x49, 0x20,
0xdc, 0xde, 0xc4, 0x9a, 0x8e, 0x99, 0x1e, 0x93, 0x2b, 0x18, 0xe2, 0xdf, 0xcf, 0xb9, 0xbc, 0x75,
0xfb, 0x7a, 0xbe, 0xc2, 0xe4, 0x1c, 0xba, 0x7c, 0x1d, 0xba, 0x03, 0x7d, 0x04, 0x0e, 0xe9, 0x5f,
0x16, 0x9c, 0x1f, 0x3a, 0x41, 0x01, 0x71, 0x12, 0xfb, 0x42, 0x8b, 0xb5, 0x59, 0x01, 0xf0, 0x60,
0x99, 0x87, 0x7e, 0x18, 0x88, 0x40, 0xcb, 0x1d, 0xb2, 0x0a, 0x93, 0x09, 0x8c, 0xa4, 0x4a, 0x32,
0xbe, 0x29, 0xee, 0xed, 0xea, 0x7b, 0x9b, 0x53, 0xe4, 0x33, 0x18, 0x18, 0xe8, 0xda, 0x93, 0xee,
0x74, 0xf4, 0xf2, 0xbd, 0x13, 0xdf, 0x71, 0x76, 0x53, 0xd0, 0xbc, 0x58, 0x65, 0x7b, 0x56, 0x6e,
0xba, 0x7a, 0x05, 0xe3, 0xe6, 0x02, 0x5a, 0xb9, 0x17, 0x7b, 0xf3, 0x39, 0x71, 0x88, 0xaa, 0x77,
0x7c, 0x9b, 0x17, 0xdf, 0x72, 0xcc, 0x0a, 0xf0, 0xaa, 0xf3, 0x89, 0x45, 0xff, 0x68, 0xe7, 0x62,
0xee, 0xab, 0x30, 0x89, 0xc9, 0x25, 0xf4, 0x79, 0x94, 0xe4, 0xb1, 0x32, 0x36, 0x0d, 0x42, 0x9f,
0x1b, 0x2e, 0xbf, 0x0c, 0xa3, 0x50, 0xe9, 0xa3, 0x6c, 0x56, 0x61, 0xb3, 0xf6, 0x4d, 0x16, 0xfa,
0x45, 0x1c, 0xde, 0x60, 0x15, 0xae, 0x8a, 0x61, 0x37, 0x8a, 0x51, 0x95, 0xb2, 0x77, 0x50, 0xca,
0x38, 0x51, 0x42, 0x97, 0x07, 0x8b, 0x9e, 0x28, 0x71, 0xa4, 0x34, 0x7f, 0x5a, 0x40, 0x98, 0xf0,
0x45, 0x98, 0xaa, 0x86, 0x78, 0x94, 0xed, 0xf3, 0xed, 0x56, 0x94, 0x51, 0x32, 0x88, 0x50, 0x18,
0x97, 0x5d, 0xf1, 0x55, 0x9d, 0xa8, 0xd6, 0x5c, 0x93, 0x33, 0xc7, 0x2c, 0x75, 0xdb, 0x1c, 0x9c,
0xc3, 0xac, 0xe6, 0x52, 0x04, 0xd7, 0x5c, 0x6a, 0x27, 0x36, 0x2b, 0x21, 0x4a, 0xcc, 0x84, 0x32,
0x61, 0xc3, 0x21, 0x72, 0xef, 0x64, 0x12, 0x33, 0xa1, 0x8c, 0x97, 0x12, 0xd2, 0xef, 0x81, 0x78,
0xab, 0xa5, 0x2e, 0xe8, 0xe2, 0x96, 0xc7, 0x1b, 0xf1, 0x85, 0x12, 0xd1, 0x91, 0xa2, 0x5d, 0xc1,
0x30, 0xcd, 0xc4, 0xaa, 0x51, 0xb7, 0x0a, 0x6b, 0xb5, 0x79, 0x96, 0x89, 0x58, 0x15, 0xeb, 0x45,
0xaa, 0x5a, 0x73, 0xf4, 0x57, 0x4b, 0x5f, 0xd4, 0xec, 0xb6, 0x45, 0x14, 0xfc, 0x27, 0x0d, 0xe7,
0x9c, 0x68, 0x38, 0xa7, 0x6e, 0x38, 0xfa, 0xb7, 0x05, 0x6f, 0x1e, 0x06, 0x1c, 0xf5, 0x3d, 0x49,
0x87, 0x39, 0xed, 0x0e, 0x9b, 0x1f, 0x76, 0xd8, 0x07, 0x27, 0x3a, 0x6c, 0x11, 0x05, 0x4f, 0xd3,
0x64, 0x4e, 0xb3, 0xc9, 0x7e, 0xb3, 0xe0, 0xed, 0x87, 0x71, 0x45, 0xb3, 0xff, 0x8b, 0xc4, 0x3a,
0x3a, 0xb1, 0xf4, 0x39, 0x9c, 0x2d, 0x6e, 0x85, 0x7f, 0xef, 0xad, 0x96, 0xb8, 0x97, 0x89, 0x1f,
0x8e, 0xfd, 0x7f, 0xa0, 0xbf, 0x58, 0x70, 0xde, 0xe6, 0xc9, 0xb4, 0x28, 0x74, 0x71, 0xaf, 0x26,
0x0f, 0x59, 0x85, 0x1f, 0xe8, 0xec, 0x1c, 0xd1, 0x79, 0xe8, 0xb7, 0x7b, 0xc4, 0xef, 0xbb, 0xe0,
0xe8, 0xf4, 0x69, 0x42, 0x91, 0xbc, 0x7a, 0x82, 0xee, 0xe1, 0xc2, 0x93, 0x2a, 0x8c, 0xb8, 0x12,
0xde, 0x6a, 0x79, 0xcd, 0x25, 0xea, 0x7f, 0x06, 0x1d, 0x95, 0x18, 0xf5, 0x1d, 0x95, 0x54, 0x19,
0xed, 0x34, 0xde, 0xa1, 0xba, 0x04, 0xdd, 0x56, 0x09, 0xea, 0x37, 0xd0, 0x6e, 0xbd, 0x81, 0xe6,
0x35, 0xea, 0xd5, 0xaf, 0xd1, 0xfb, 0x40, 0x0e, 0xaf, 0x96, 0x29, 0xf2, 0x36, 0x5c, 0x9a, 0x14,
0xe3, 0x90, 0x3e, 0x87, 0x91, 0xb7, 0x8b, 0x5e, 0x8b, 0x75, 0xbe, 0x41, 0x71, 0x97, 0xd0, 0x4f,
0x52, 0x8c, 0xa1, 0xe6, 0xf4, 0x98, 0x41, 0xf4, 0x23, 0x18, 0xd7, 0x34, 0x99, 0x62, 0xbc, 0x03,
0x04, 0x18, 0xd0, 0x5c, 0x1a, 0x37, 0xcd, 0x29, 0xfa, 0x02, 0x9e, 0x79, 0xbb, 0xe8, 0xdb, 0x5c,
0x64, 0xfb, 0xf9, 0x3a, 0xc4, 0xb3, 0x5d, 0x18, 0x60, 0xb1, 0x84, 0x2c, 0xf9, 0x25, 0xa4, 0x9f,
0xc2, 0x59, 0x8b, 0x2b, 0xd3, 0xd3, 0xe4, 0xd2, 0x6b, 0xa7, 0xf6, 0xfa, 0x9d, 0xf6, 0xa0, 0xb7,
0x3f, 0x7a, 0x0f, 0x76, 0x43, 0x18, 0xa7, 0xb9, 0x2a, 0xbb, 0x41, 0x83, 0x53, 0x1f, 0x9b, 0xfe,
0x6c, 0x69, 0xd3, 0xe6, 0xdc, 0x47, 0x35, 0xfd, 0xab, 0x83, 0xf1, 0x9c, 0x8c, 0xff, 0x88, 0x6f,
0x9f, 0x89, 0x4c, 0x09, 0x31, 0xb2, 0xf8, 0x22, 0xeb, 0xa5, 0xa2, 0x98, 0x15, 0x5e, 0xf7, 0xf5,
0x6f, 0xa7, 0x8f, 0xff, 0x09, 0x00, 0x00, 0xff, 0xff, 0x22, 0x7b, 0xc5, 0xdf, 0x50, 0x09, 0x00,
0x00,
// 1004 bytes of a gzipped FileDescriptorProto
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xcc, 0x56, 0xcf, 0x8f, 0xdb, 0x44,
0x14, 0x96, 0x63, 0x27, 0x1b, 0xbf, 0x0d, 0xed, 0xae, 0x29, 0x4b, 0xb4, 0x42, 0x28, 0xb2, 0x28,
0xac, 0x2a, 0xb1, 0x42, 0xe5, 0x82, 0x2a, 0x81, 0xb4, 0x4a, 0xa3, 0x82, 0xc4, 0xf2, 0x63, 0x0a,
0xe1, 0x3c, 0xb1, 0x67, 0xb3, 0x6e, 0xe3, 0x1f, 0xcc, 0x4c, 0xd2, 0xe6, 0xca, 0x99, 0x23, 0x47,
0x6e, 0x1c, 0xb9, 0x20, 0x71, 0xe3, 0xcc, 0x1f, 0xc1, 0x99, 0x13, 0x7f, 0x06, 0x7a, 0xcf, 0x63,
0x7b, 0xec, 0x4d, 0x2a, 0x90, 0x2a, 0xc4, 0x29, 0xf3, 0xcd, 0x3c, 0xcf, 0x7c, 0xdf, 0xbc, 0xef,
0xbd, 0x09, 0x1c, 0x8b, 0x4d, 0x1a, 0xe5, 0x99, 0x96, 0x3c, 0xd2, 0xe7, 0x85, 0xcc, 0x75, 0x1e,
0xf4, 0xf5, 0xb6, 0x10, 0x2a, 0xfc, 0xce, 0x81, 0xe3, 0xd9, 0xfc, 0x72, 0x6a, 0x16, 0x3f, 0x5f,
0x3c, 0x11, 0x91, 0x0e, 0x02, 0xf0, 0x78, 0x1c, 0xcb, 0xb1, 0x33, 0x71, 0xce, 0x7c, 0x46, 0xe3,
0xe0, 0x1e, 0x78, 0x31, 0xd7, 0x7c, 0xdc, 0x9b, 0x38, 0x67, 0x87, 0xf7, 0x4f, 0xce, 0xe9, 0xfb,
0x73, 0xeb, 0xdb, 0x87, 0x5c, 0x73, 0x46, 0x31, 0xc1, 0xbb, 0xd0, 0x57, 0x9a, 0x6b, 0x31, 0x76,
0x29, 0xf8, 0xf5, 0x9b, 0xc1, 0x8f, 0x71, 0x99, 0x95, 0x51, 0xe1, 0xcf, 0x0e, 0xdc, 0xee, 0x6c,
0x14, 0x8c, 0xe1, 0x20, 0x92, 0x82, 0xeb, 0xbc, 0x62, 0x51, 0x41, 0x24, 0x97, 0xf1, 0x54, 0x10,
0x11, 0x9f, 0xd1, 0x38, 0xb8, 0x03, 0x7d, 0xbe, 0x4a, 0xb8, 0xa2, 0x03, 0x7d, 0x56, 0x82, 0x5a,
0x86, 0x67, 0xc9, 0x08, 0xc0, 0x8b, 0xf2, 0x58, 0x8c, 0xfb, 0x13, 0xe7, 0x6c, 0xc4, 0x68, 0x1c,
0x9c, 0xc2, 0x10, 0x7f, 0x3f, 0xe6, 0xea, 0x7a, 0x3c, 0xa0, 0xf9, 0x1a, 0x07, 0x47, 0xe0, 0xf2,
0x45, 0x32, 0x3e, 0xa0, 0x2d, 0x70, 0x18, 0xfe, 0xe9, 0xc0, 0x51, 0x57, 0x09, 0x12, 0xc8, 0xf2,
0x2c, 0x12, 0x44, 0xd6, 0x63, 0x25, 0xc0, 0x8d, 0xd5, 0x3a, 0x89, 0x92, 0x58, 0xc4, 0x44, 0x77,
0xc8, 0x6a, 0x1c, 0x4c, 0xe0, 0x50, 0xe9, 0x5c, 0xf2, 0x65, 0x79, 0xae, 0x4b, 0xe7, 0xda, 0x53,
0xc1, 0x47, 0x70, 0x60, 0xe0, 0xd8, 0x9b, 0xb8, 0x67, 0x87, 0xf7, 0xdf, 0xda, 0x73, 0x8f, 0xe7,
0x8f, 0xcb, 0xb0, 0x59, 0xa6, 0xe5, 0x96, 0x55, 0x1f, 0x9d, 0x3e, 0x80, 0x91, 0xbd, 0x80, 0x52,
0x9e, 0x8a, 0xad, 0xb9, 0x4e, 0x1c, 0x22, 0xeb, 0x0d, 0x5f, 0xad, 0xcb, 0xbb, 0x1c, 0xb1, 0x12,
0x3c, 0xe8, 0x7d, 0xe0, 0x84, 0xbf, 0xb6, 0x7d, 0x71, 0x11, 0xe9, 0x24, 0xcf, 0x82, 0x13, 0x18,
0xf0, 0x34, 0x5f, 0x67, 0xda, 0xc8, 0x34, 0x08, 0x75, 0x2e, 0xb9, 0xfa, 0x34, 0x49, 0x13, 0x4d,
0x5b, 0x79, 0xac, 0xc6, 0x66, 0xed, 0x0b, 0x99, 0x44, 0xa5, 0x1d, 0x5e, 0x61, 0x35, 0xae, 0x93,
0xe1, 0x59, 0xc9, 0xa8, 0x53, 0xd9, 0xef, 0xa4, 0x32, 0xcb, 0xb5, 0xa0, 0xf4, 0x60, 0xd2, 0x73,
0x2d, 0x76, 0xa4, 0xe6, 0x37, 0x07, 0x02, 0x26, 0x22, 0x91, 0x14, 0xda, 0x22, 0x8f, 0xb4, 0x23,
0xbe, 0x5a, 0x89, 0xca, 0x4a, 0x06, 0x05, 0x21, 0x8c, 0xaa, 0xaa, 0xf8, 0xac, 0x71, 0x54, 0x6b,
0xce, 0x8e, 0xb9, 0x40, 0x2f, 0xb9, 0xed, 0x18, 0x9c, 0x43, 0xaf, 0xae, 0x95, 0x88, 0x1f, 0x71,
0x45, 0x4a, 0x3c, 0x56, 0x41, 0xa4, 0x28, 0x85, 0x36, 0x66, 0xc3, 0x21, 0xc6, 0x3e, 0x51, 0x79,
0xc6, 0x84, 0x36, 0x5a, 0x2a, 0x18, 0x5e, 0x41, 0x30, 0x9b, 0x5f, 0x52, 0x42, 0xa7, 0xd7, 0x3c,
0x5b, 0x8a, 0x4f, 0xb4, 0x48, 0x77, 0x24, 0xed, 0x14, 0x86, 0x85, 0x14, 0x73, 0x2b, 0x6f, 0x35,
0x26, 0xb6, 0x6b, 0x29, 0x45, 0xa6, 0xcb, 0xf5, 0xd2, 0x55, 0xad, 0xb9, 0xf0, 0x47, 0x87, 0x0e,
0xb2, 0xab, 0x6d, 0x9a, 0xc6, 0xff, 0x49, 0xc1, 0xf9, 0x7b, 0x0a, 0xce, 0x6f, 0x0a, 0x2e, 0xfc,
0xcb, 0x81, 0x57, 0xbb, 0x06, 0x47, 0x7e, 0x2f, 0xa5, 0xc2, 0xfc, 0x76, 0x85, 0x5d, 0x74, 0x2b,
0xec, 0x9d, 0x3d, 0x15, 0x36, 0x4d, 0xe3, 0x97, 0x53, 0x64, 0xbe, 0x5d, 0x64, 0x3f, 0x39, 0xf0,
0xda, 0x4d, 0xbb, 0xa2, 0xd8, 0xff, 0x85, 0x63, 0x7d, 0x72, 0x6c, 0x78, 0x17, 0x6e, 0x4f, 0xaf,
0x45, 0xf4, 0x74, 0x36, 0xbf, 0xc4, 0x6f, 0x99, 0xf8, 0x76, 0xd7, 0xfb, 0x10, 0xfe, 0xe0, 0xc0,
0x51, 0x3b, 0x4e, 0x15, 0x65, 0xa2, 0xcb, 0x73, 0x29, 0x78, 0xc8, 0x6a, 0x7c, 0x83, 0x67, 0x6f,
0x07, 0xcf, 0xae, 0x5e, 0x77, 0x87, 0xde, 0x37, 0xc0, 0x27, 0xf7, 0x51, 0x40, 0xe9, 0xbc, 0x66,
0x22, 0xdc, 0xc2, 0xf1, 0x4c, 0xe9, 0x24, 0xe5, 0x5a, 0xcc, 0xe6, 0x97, 0x8f, 0xb8, 0x42, 0xfe,
0xb7, 0xa0, 0xa7, 0x73, 0xc3, 0xbe, 0xa7, 0xf3, 0xda, 0xa3, 0x3d, 0xab, 0x0f, 0x35, 0x29, 0x70,
0x5b, 0x29, 0x68, 0x7a, 0xa0, 0xd7, 0xea, 0x81, 0xa6, 0x1b, 0xf5, 0x9b, 0x6e, 0xf4, 0x36, 0x04,
0xdd, 0xa3, 0x55, 0x81, 0x71, 0x4b, 0xae, 0x8c, 0x8b, 0x71, 0x18, 0xde, 0x85, 0xc3, 0xd9, 0x26,
0x7d, 0x28, 0x16, 0xeb, 0x25, 0x92, 0x3b, 0x81, 0x41, 0x5e, 0xa0, 0x0d, 0x29, 0xa6, 0xcf, 0x0c,
0x0a, 0xdf, 0x83, 0x51, 0x13, 0xa6, 0x0a, 0xb4, 0x77, 0x8c, 0x00, 0x0d, 0xba, 0x56, 0x46, 0x8d,
0x3d, 0x15, 0xde, 0x83, 0x5b, 0xb3, 0x4d, 0xfa, 0xe5, 0x5a, 0xc8, 0xed, 0xc5, 0x22, 0xc1, 0xbd,
0xc7, 0x70, 0x80, 0xc9, 0x12, 0xaa, 0x8a, 0xaf, 0x60, 0xf8, 0x21, 0xdc, 0x6e, 0xc5, 0xaa, 0x62,
0x7f, 0x70, 0xa5, 0xb5, 0xd7, 0x68, 0xfd, 0x9a, 0x34, 0xd0, 0xe7, 0x2f, 0x3c, 0x07, 0xab, 0x21,
0xc9, 0x8a, 0xb5, 0xae, 0xaa, 0x81, 0xc0, 0xbe, 0xcb, 0x0e, 0xbf, 0x77, 0x48, 0xb4, 0xd9, 0xf7,
0x85, 0x9c, 0xfe, 0xd5, 0xc6, 0xb8, 0x8f, 0xe4, 0xcf, 0xb0, 0xf7, 0x19, 0xcb, 0x54, 0x10, 0x2d,
0x8b, 0x1d, 0x99, 0x96, 0xca, 0x64, 0xd6, 0x38, 0xfc, 0xdd, 0x81, 0x3b, 0xb3, 0x4d, 0x5a, 0x57,
0x2a, 0x36, 0x48, 0x61, 0x0a, 0x82, 0x0c, 0xe4, 0x58, 0x4d, 0xee, 0x08, 0xdc, 0x2b, 0x51, 0x7a,
0xca, 0x65, 0x38, 0xac, 0x1f, 0x31, 0xd7, 0x7a, 0xc4, 0xea, 0x46, 0xea, 0xd9, 0x8d, 0xb4, 0xa1,
0xdd, 0x6f, 0xd1, 0x36, 0x17, 0x3f, 0xa8, 0x2f, 0x1e, 0x23, 0xc5, 0xf3, 0x22, 0x91, 0xc2, 0xbc,
0x83, 0x06, 0xd1, 0x2b, 0xc1, 0x25, 0xa7, 0xa2, 0x18, 0x96, 0x32, 0x2a, 0x1c, 0xfe, 0x81, 0x2f,
0x80, 0x25, 0x83, 0xaf, 0x56, 0xc6, 0x78, 0x3b, 0x5f, 0x77, 0xbb, 0x3a, 0x3a, 0xe2, 0xdc, 0x9b,
0xe2, 0x3c, 0x4b, 0xdc, 0x3f, 0x97, 0x11, 0x80, 0x27, 0x9e, 0x8b, 0xc8, 0x88, 0xa0, 0xb1, 0x25,
0x6d, 0xb8, 0x57, 0x9a, 0xdf, 0x91, 0xf6, 0x8b, 0x03, 0x27, 0x96, 0xb4, 0xaf, 0x24, 0xcf, 0xd4,
0x95, 0x90, 0x46, 0xde, 0xce, 0x9e, 0xda, 0xc8, 0x46, 0x81, 0x3d, 0x5b, 0x36, 0x51, 0x72, 0x77,
0x52, 0xf2, 0x5a, 0x94, 0xde, 0x04, 0x48, 0xd4, 0x37, 0x89, 0xbe, 0x8e, 0x25, 0x7f, 0x46, 0x62,
0x87, 0xcc, 0x9a, 0x69, 0x51, 0x1e, 0xb4, 0x29, 0x2f, 0x06, 0xf4, 0x87, 0xfc, 0xfd, 0xbf, 0x03,
0x00, 0x00, 0xff, 0xff, 0x77, 0x17, 0xf5, 0x15, 0xa5, 0x0b, 0x00, 0x00,
}
File mode changed from 100644 to 100755
File mode changed from 100644 to 100755
......@@ -7,7 +7,7 @@ PARA_CLI4="docker exec ${NODE4} /root/chain33-para-cli"
MAIN_CLI="docker exec ${NODE3} /root/chain33-cli"
PARANAME="para"
PARA_COIN_FROZEN="20.0000"
PARA_COIN_FROZEN="5.0000"
xsedfix=""
if [ "$(uname)" == "Darwin" ]; then
......@@ -120,11 +120,6 @@ function para_transfer() {
block_wait "${CLI}" 2
echo "=========== # main chain send to paracross ============="
main_transfer2paracross "0x6da92a632ab7deb67d38c0f6560bcfed28167998f6496db64c258d5e8393a81b"
main_transfer2paracross "0x19c069234f9d3e61135fefbeb7791b149cdf6af536f26bebb310d4cd22c3fee4"
main_transfer2paracross "0x7a80a1f75d7360c6123c32a78ecf978c1ac55636f87892df38d8b85a9aeff115"
main_transfer2paracross "0xcacb1f5d51700aea07fca2246ab43b0917d70405c65edea9b5063d72eb5c6b71"
#1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY test
main_transfer2paracross "0x9c451df9e5cb05b88b28729aeaaeb3169a2414097401fcb4c79c1971df734588"
#1Ka7EPFRqs3v9yreXG6qA4RQbNmbPJCZPj
......@@ -164,7 +159,7 @@ function para_transfer2account() {
function main_transfer2paracross() {
echo "addr=${1}"
local coins=20
local coins=5
if [ "$#" -ge 2 ]; then
coins="$2"
fi
......@@ -181,7 +176,7 @@ function para_transfer2exec() {
function para_create_nodegroup_test() {
echo "=========== # para chain create node group ============="
##apply
txhash=$(${PARA_CLI} send para nodegroup -o 1 -a "1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4,1JRNjdEqp4LJ5fqycUBm9ayCKSeeskgMKR,1NLHPEcbTWWxxU3dGUZBhayjrCHD3psX7k,1MCftFynyvG2F4ED5mdHYgziDxx6vDrScs" -c 20 -k 0x6da92a632ab7deb67d38c0f6560bcfed28167998f6496db64c258d5e8393a81b)
txhash=$(${PARA_CLI} send para nodegroup -o 1 -a "1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4,1JRNjdEqp4LJ5fqycUBm9ayCKSeeskgMKR,1NLHPEcbTWWxxU3dGUZBhayjrCHD3psX7k,1MCftFynyvG2F4ED5mdHYgziDxx6vDrScs" -c 5 -k 0xd165c84ed37c2a427fea487470ee671b7a0495d68d82607cafbc6348bf23bec5)
echo "tx=$txhash"
query_tx "${PARA_CLI}" "${txhash}"
status=$(${PARA_CLI} para nodegroup_status -t user.p.para. | jq -r ".status")
......@@ -189,15 +184,15 @@ function para_create_nodegroup_test() {
echo "status not apply status=$status"
exit 1
fi
balance=$(${CLI} account balance -a 1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4 -e paracross | jq -r ".frozen")
if [ "$balance" != "$PARA_COIN_FROZEN" ]; then
balance=$(${CLI} account balance -a 1Ka7EPFRqs3v9yreXG6qA4RQbNmbPJCZPj -e paracross | jq -r ".frozen")
if [ "$balance" != "20.0000" ]; then
echo "apply coinfrozen error balance=$balance"
exit 1
fi
echo "=========== # para chain quit node group ============="
##quit
txhash=$(${PARA_CLI} send para nodegroup -o 3 -a "1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4,1JRNjdEqp4LJ5fqycUBm9ayCKSeeskgMKR,1NLHPEcbTWWxxU3dGUZBhayjrCHD3psX7k,1MCftFynyvG2F4ED5mdHYgziDxx6vDrScs" -c 20 -k 0x6da92a632ab7deb67d38c0f6560bcfed28167998f6496db64c258d5e8393a81b)
txhash=$(${PARA_CLI} send para nodegroup -o 3 -a "1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4,1JRNjdEqp4LJ5fqycUBm9ayCKSeeskgMKR,1NLHPEcbTWWxxU3dGUZBhayjrCHD3psX7k,1MCftFynyvG2F4ED5mdHYgziDxx6vDrScs" -c 5 -k 0xd165c84ed37c2a427fea487470ee671b7a0495d68d82607cafbc6348bf23bec5)
echo "tx=$txhash"
query_tx "${PARA_CLI}" "${txhash}"
status=$(${PARA_CLI} para nodegroup_status -t user.p.para. | jq -r ".status")
......@@ -205,8 +200,8 @@ function para_create_nodegroup_test() {
echo "status not quit status=$status"
exit 1
fi
balance=$(${CLI} account balance -a 1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4 -e paracross | jq -r ".balance")
if [ "$balance" != "$PARA_COIN_FROZEN" ]; then
balance=$(${CLI} account balance -a 1Ka7EPFRqs3v9yreXG6qA4RQbNmbPJCZPj -e paracross | jq -r ".balance")
if [ "$balance" != "100.0000" ]; then
echo "quit coinfrozen error balance=$balance"
exit 1
fi
......@@ -218,7 +213,7 @@ function para_create_nodegroup() {
echo "=========== # para chain create node group again ============="
##apply
txhash=$(${PARA_CLI} send para nodegroup -o 1 -a "1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4,1JRNjdEqp4LJ5fqycUBm9ayCKSeeskgMKR,1NLHPEcbTWWxxU3dGUZBhayjrCHD3psX7k,1MCftFynyvG2F4ED5mdHYgziDxx6vDrScs" -c 20 -k 0x6da92a632ab7deb67d38c0f6560bcfed28167998f6496db64c258d5e8393a81b)
txhash=$(${PARA_CLI} send para nodegroup -o 1 -a "1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY,1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4,1JRNjdEqp4LJ5fqycUBm9ayCKSeeskgMKR,1NLHPEcbTWWxxU3dGUZBhayjrCHD3psX7k,1MCftFynyvG2F4ED5mdHYgziDxx6vDrScs" -c 5 -k 0xd165c84ed37c2a427fea487470ee671b7a0495d68d82607cafbc6348bf23bec5)
echo "tx=$txhash"
query_tx "${PARA_CLI}" "${txhash}"
status=$(${PARA_CLI} para nodegroup_status -t user.p.para. | jq -r ".status")
......@@ -229,7 +224,7 @@ function para_create_nodegroup() {
echo "=========== # para chain approve node group ============="
##approve
txhash=$(${PARA_CLI} send para nodegroup -o 2 -a "1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4, 1JRNjdEqp4LJ5fqycUBm9ayCKSeeskgMKR, 1NLHPEcbTWWxxU3dGUZBhayjrCHD3psX7k, 1MCftFynyvG2F4ED5mdHYgziDxx6vDrScs," -k 0xc34b5d9d44ac7b754806f761d3d4d2c4fe5214f6b074c19f069c4f5c2a29c8cc)
txhash=$(${PARA_CLI} send para nodegroup -o 2 -a "1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY,1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4, 1JRNjdEqp4LJ5fqycUBm9ayCKSeeskgMKR, 1NLHPEcbTWWxxU3dGUZBhayjrCHD3psX7k, 1MCftFynyvG2F4ED5mdHYgziDxx6vDrScs," -k 0xc34b5d9d44ac7b754806f761d3d4d2c4fe5214f6b074c19f069c4f5c2a29c8cc)
echo "tx=$txhash"
query_tx "${PARA_CLI}" "${txhash}"
......@@ -243,7 +238,7 @@ function para_create_nodegroup() {
echo "=========== # para chain quit node group fail ============="
##quit fail
txhash=$(${PARA_CLI} send para nodegroup -o 3 -a "1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4,1JRNjdEqp4LJ5fqycUBm9ayCKSeeskgMKR,1NLHPEcbTWWxxU3dGUZBhayjrCHD3psX7k,1MCftFynyvG2F4ED5mdHYgziDxx6vDrScs" -k 0x6da92a632ab7deb67d38c0f6560bcfed28167998f6496db64c258d5e8393a81b)
txhash=$(${PARA_CLI} send para nodegroup -o 3 -a "1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY,1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4,1JRNjdEqp4LJ5fqycUBm9ayCKSeeskgMKR,1NLHPEcbTWWxxU3dGUZBhayjrCHD3psX7k,1MCftFynyvG2F4ED5mdHYgziDxx6vDrScs" -k 0x6da92a632ab7deb67d38c0f6560bcfed28167998f6496db64c258d5e8393a81b)
echo "tx=$txhash"
query_tx "${CLI}" "${txhash}"
status=$(${CLI} para nodegroup_status -t user.p.para. | jq -r ".status")
......@@ -251,8 +246,8 @@ function para_create_nodegroup() {
echo "status quit not approve status=$status"
exit 1
fi
balance=$(${CLI} account balance -a 1KSBd17H7ZK8iT37aJztFB22XGwsPTdwE4 -e paracross | jq -r ".frozen")
if [ "$balance" != "$PARA_COIN_FROZEN" ]; then
balance=$(${CLI} account balance -a 1Ka7EPFRqs3v9yreXG6qA4RQbNmbPJCZPj -e paracross | jq -r ".frozen")
if [ "$balance" != "25.0000" ]; then
echo "quit fail coinfrozen error balance=$balance"
exit 1
fi
......@@ -510,7 +505,7 @@ function para_nodemanage_node_join() {
fi
echo "=========== # para chain new node join ============="
hash=$(${PARA_CLI} send para node -o join -c 20 -a 1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY -k 0x9c451df9e5cb05b88b28729aeaaeb3169a2414097401fcb4c79c1971df734588)
hash=$(${PARA_CLI} send para node -o join -c 5 -a 1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY -k 0x9c451df9e5cb05b88b28729aeaaeb3169a2414097401fcb4c79c1971df734588)
echo "${hash}"
query_tx "${PARA_CLI}" "${hash}"
......@@ -520,29 +515,16 @@ function para_nodemanage_node_join() {
exit 1
fi
# status=$(${PARA_CLI} para node_list -t user.p.para. -s 1 | jq -r '.addrs[]|.applyAddr|contains("1E5")')
# if [ "${status}" != true ]; then
# echo "wrong join status"
# ${PARA_CLI} para node_list -t user.p.para. -s 1
# exit 1
# fi
}
function para_nodemanage_node_behalf_join() {
echo "================# para node behalf join test ================="
balance=$(${CLI} account balance -a 1Ka7EPFRqs3v9yreXG6qA4RQbNmbPJCZPj -e paracross | jq -r ".balance")
if [ "$balance" != "100.0000" ]; then
echo "balance coinfrozen error balance=$balance"
exit 1
fi
echo "=========== # para chain new node join 1 ============="
hash=$(${PARA_CLI} send para node -o join -c 20 -a 1Luh4AziYyaC5zP3hUXtXFZS873xAxm6rH -k 0xd165c84ed37c2a427fea487470ee671b7a0495d68d82607cafbc6348bf23bec5)
hash=$(${PARA_CLI} send para node -o join -c 8 -a 1Luh4AziYyaC5zP3hUXtXFZS873xAxm6rH -k 0xd165c84ed37c2a427fea487470ee671b7a0495d68d82607cafbc6348bf23bec5)
echo "${hash}"
query_tx "${PARA_CLI}" "${hash}"
balance=$(${CLI} account balance -a 1Ka7EPFRqs3v9yreXG6qA4RQbNmbPJCZPj -e paracross | jq -r ".frozen")
if [ "$balance" != "$PARA_COIN_FROZEN" ]; then
if [ "$balance" != "28.0000" ]; then
echo "1Ka frozen coinfrozen error balance=$balance"
exit 1
fi
......@@ -554,22 +536,27 @@ function para_nodemanage_node_behalf_join() {
fi
echo "=========== # para chain new node join 2============="
hash=$(${PARA_CLI} send para node -o join -c 20 -a 1NNaYHkscJaLJ2wUrFNeh6cQXBS4TrFYeB -k 0xd165c84ed37c2a427fea487470ee671b7a0495d68d82607cafbc6348bf23bec5)
hash=$(${PARA_CLI} send para node -o join -c 9 -a 1NNaYHkscJaLJ2wUrFNeh6cQXBS4TrFYeB -k 0xd165c84ed37c2a427fea487470ee671b7a0495d68d82607cafbc6348bf23bec5)
echo "${hash}"
query_tx "${PARA_CLI}" "${hash}"
balance=$(${CLI} account balance -a 1Ka7EPFRqs3v9yreXG6qA4RQbNmbPJCZPj -e paracross | jq -r ".frozen")
if [ "$balance" != "40.0000" ]; then
if [ "$balance" != "37.0000" ]; then
echo "frozen coinfrozen error balance=$balance"
exit 1
fi
# status=$(${PARA_CLI} para node_list -t user.p.para. -s 1 | jq -r '.addrs[]|.applyAddr|contains("1NN")')
# if [ "${status}" != true ]; then
# echo "wrong join status"
# ${PARA_CLI} para node_list -t user.p.para. -s 1
# exit 1
# fi
echo "=========== # para chain node 1 quit ============="
hash=$(${PARA_CLI} send para node -o quit -a 1Luh4AziYyaC5zP3hUXtXFZS873xAxm6rH -k 0xfdf2bbff853ecff2e7b86b2a8b45726c6538ca7d1403dc94e50131ef379bdca0)
echo "${hash}"
query_tx "${PARA_CLI}" "${hash}"
balance=$(${CLI} account balance -a 1Ka7EPFRqs3v9yreXG6qA4RQbNmbPJCZPj -e paracross | jq -r ".frozen")
if [ "$balance" != "29.0000" ]; then
echo "unfrozen coinfrozen error balance=$balance"
exit 1
fi
}
function para_nodemanage_quit_test() {
......@@ -593,14 +580,43 @@ function para_nodemanage_quit_test() {
exit 1
fi
para_nodemanage_node_behalf_join
echo "=========== # para chain other node quit ============="
hash=$(${PARA_CLI} send para node -o quit -a 1Luh4AziYyaC5zP3hUXtXFZS873xAxm6rH -k 0xfdf2bbff853ecff2e7b86b2a8b45726c6538ca7d1403dc94e50131ef379bdca0)
}
function para_nodegroup_behalf_quit_test() {
echo "=========== # para chain behalf node quit ============="
hash=$(${PARA_CLI} send para node -o quit -a 1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY -k 0x9c451df9e5cb05b88b28729aeaaeb3169a2414097401fcb4c79c1971df734588)
echo "${hash}"
query_tx "${PARA_CLI}" "${hash}"
status=$(${PARA_CLI} para node_status -t user.p.para. -a 1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY | jq -r ".status")
if [ "${status}" != "3" ]; then
echo "wrong vote status"
${PARA_CLI} para node_status -t user.p.para. -a 1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY
exit 1
fi
${PARA_CLI} send para node -o vote -a 1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY -v yes -k 0x6da92a632ab7deb67d38c0f6560bcfed28167998f6496db64c258d5e8393a81b
${PARA_CLI} send para node -o vote -a 1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY -v yes -k 0x19c069234f9d3e61135fefbeb7791b149cdf6af536f26bebb310d4cd22c3fee4
hash=$(${PARA_CLI} send para node -o vote -a 1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY -v yes -k 0x7a80a1f75d7360c6123c32a78ecf978c1ac55636f87892df38d8b85a9aeff115)
echo "${hash}"
query_tx "${PARA_CLI}" "${hash}"
status=$(${PARA_CLI} para node_status -t user.p.para. -a 1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY | jq -r ".status")
if [ "${status}" != "4" ]; then
echo "wrong vote status"
${PARA_CLI} para node_status -t user.p.para. -a 1E5saiXVb9mW8wcWUUZjsHJPZs5GmdzuSY
exit 1
fi
node=$(${PARA_CLI} para nodegroup_addrs -t user.p.para. | jq -r '.value|contains("1E5")')
if [ "${node}" == "true" ]; then
echo "wrong node group addr"
${PARA_CLI} para nodegroup_addrs -t user.p.para.
exit 1
fi
balance=$(${CLI} account balance -a 1Ka7EPFRqs3v9yreXG6qA4RQbNmbPJCZPj -e paracross | jq -r ".frozen")
if [ "$balance" != "$PARA_COIN_FROZEN" ]; then
if [ "$balance" != "20.0000" ]; then
echo "unfrozen coinfrozen error balance=$balance"
exit 1
fi
......@@ -672,6 +688,8 @@ function para_nodemanage_test() {
fi
echo "=========== # para chain behalf node vote test ============="
para_nodemanage_node_behalf_join
${PARA_CLI} send para node -o vote -a 1NNaYHkscJaLJ2wUrFNeh6cQXBS4TrFYeB -v yes -k 0x6da92a632ab7deb67d38c0f6560bcfed28167998f6496db64c258d5e8393a81b
${PARA_CLI} send para node -o vote -a 1NNaYHkscJaLJ2wUrFNeh6cQXBS4TrFYeB -v yes -k 0x19c069234f9d3e61135fefbeb7791b149cdf6af536f26bebb310d4cd22c3fee4
hash=$(${PARA_CLI} send para node -o vote -a 1NNaYHkscJaLJ2wUrFNeh6cQXBS4TrFYeB -v yes -k 0x7a80a1f75d7360c6123c32a78ecf978c1ac55636f87892df38d8b85a9aeff115)
......@@ -705,7 +723,7 @@ function para_nodemanage_test() {
query_tx "${PARA_CLI}" "${hash}"
balance=$(${CLI} account balance -a 1Ka7EPFRqs3v9yreXG6qA4RQbNmbPJCZPj -e paracross | jq -r ".frozen")
if [ "$balance" != "0.0000" ]; then
if [ "$balance" != "20.0000" ]; then
echo "unfrozen coinfrozen error balance=$balance"
exit 1
fi
......@@ -727,6 +745,7 @@ function para_nodemanage_test() {
function para_test() {
echo "=========== # para chain test ============="
para_nodegroup_behalf_quit_test
para_nodemanage_test
token_create "${PARA_CLI}"
token_transfer "${PARA_CLI}"
......@@ -738,8 +757,9 @@ function paracross() {
if [ "${2}" == "init" ]; then
para_init
elif [ "${2}" == "config" ]; then
para_transfer
para_set_wallet
para_transfer
elif [ "${2}" == "test" ]; then
para_test "${1}"
dapp_rpc_test "${3}"
......
......@@ -5,6 +5,8 @@
package executor
import (
"bytes"
"github.com/33cn/chain33/common"
"github.com/33cn/chain33/types"
"github.com/33cn/chain33/util"
......@@ -125,22 +127,41 @@ func (e *Paracross) ExecLocal_AssetWithdraw(payload *types.AssetsWithdraw, tx *t
return nil, nil
}
func setMinerTxResult(payload *pt.ParacrossMinerAction, txs []*types.Transaction, receipts []*types.ReceiptData) {
var curTxHashs, paraTxHashs [][]byte
func setMinerTxResult(payload *pt.ParacrossMinerAction, txs []*types.Transaction, receipts []*types.ReceiptData) error {
isCommitTx := make(map[string]bool)
var curTxHashs, paraTxHashs, crossTxHashs [][]byte
for _, tx := range txs {
hash := tx.Hash()
curTxHashs = append(curTxHashs, hash)
//对user.p.xx.paracross ,actionTy==commit 的tx不需要再发回主链
if types.IsMyParaExecName(string(tx.Execer)) && bytes.HasSuffix(tx.Execer, []byte(pt.ParaX)) {
var payload pt.ParacrossAction
err := types.Decode(tx.Payload, &payload)
if err != nil {
clog.Error("setMinerTxResult", "txHash", common.ToHex(hash))
return err
}
if payload.Ty == pt.ParacrossActionCommit {
isCommitTx[string(hash)] = true
}
}
//跨链交易包含了主链交易,需要过滤出来
if types.IsMyParaExecName(string(tx.Execer)) {
if types.IsMyParaExecName(string(tx.Execer)) && !isCommitTx[string(hash)] {
paraTxHashs = append(paraTxHashs, hash)
}
}
crossTxHashs := FilterParaMainCrossTxHashes(types.GetTitle(), txs)
totalCrossTxHashs := FilterParaMainCrossTxHashes(types.GetTitle(), txs)
for _, crossHash := range totalCrossTxHashs {
if !isCommitTx[string(crossHash)] {
crossTxHashs = append(crossTxHashs, crossHash)
}
}
payload.Status.TxHashs = paraTxHashs
payload.Status.TxResult = util.CalcBitMap(paraTxHashs, curTxHashs, receipts)
payload.Status.CrossTxHashs = crossTxHashs
payload.Status.CrossTxResult = util.CalcBitMap(crossTxHashs, curTxHashs, receipts)
return nil
}
func setMinerTxResultFork(payload *pt.ParacrossMinerAction, txs []*types.Transaction, receipts []*types.ReceiptData) {
......@@ -149,16 +170,16 @@ func setMinerTxResultFork(payload *pt.ParacrossMinerAction, txs []*types.Transac
hash := tx.Hash()
curTxHashs = append(curTxHashs, hash)
}
baseTxHashs := payload.Status.TxHashs
baseCrossTxHashs := payload.Status.CrossTxHashs
baseCrossTxHashs := FilterParaCrossTxHashes(types.GetTitle(), txs)
//主链自己过滤平行链tx, 对平行链执行失败的tx主链无法识别,主链和平行链需要获取相同的最初的tx map
//全部平行链tx结果
payload.Status.TxResult = util.CalcBitMap(baseTxHashs, curTxHashs, receipts)
payload.Status.TxResult = util.CalcBitMap(curTxHashs, curTxHashs, receipts)
//跨链tx结果
payload.Status.CrossTxResult = util.CalcBitMap(baseCrossTxHashs, curTxHashs, receipts)
payload.Status.TxHashs = [][]byte{CalcTxHashsHash(baseTxHashs)}
payload.Status.TxHashs = [][]byte{CalcTxHashsHash(curTxHashs)}
payload.Status.CrossTxHashs = [][]byte{CalcTxHashsHash(baseCrossTxHashs)}
}
......@@ -177,7 +198,10 @@ func (e *Paracross) ExecLocal_Miner(payload *pt.ParacrossMinerAction, tx *types.
if payload.Status.MainBlockHeight >= forkHeight {
setMinerTxResultFork(payload, txs[1:], e.GetReceipt()[1:])
} else {
setMinerTxResult(payload, txs[1:], e.GetReceipt()[1:])
err := setMinerTxResult(payload, txs[1:], e.GetReceipt()[1:])
if err != nil {
return nil, err
}
}
set.KV = append(set.KV, &types.KeyValue{
......
......@@ -488,10 +488,14 @@ func (s *VoteTestSuite) TestVoteTx() {
tx7, err := createAssetTransferTx(s.Suite, PrivKeyC, nil)
s.Nil(err)
tx8, err := createCrossCommitTx(s.Suite)
s.Nil(err)
txs := []*types.Transaction{tx, tx1, tx2}
txs = append(txs, txGroup34...)
txs = append(txs, txGroup56...)
txs = append(txs, tx7)
txs = append(txs, tx8)
s.exec.SetTxs(txs)
//for i,tx := range txs{
......@@ -508,7 +512,8 @@ func (s *VoteTestSuite) TestVoteTx() {
recpt5 := &types.ReceiptData{Ty: types.ExecPack}
recpt6 := &types.ReceiptData{Ty: types.ExecPack}
recpt7 := &types.ReceiptData{Ty: types.ExecOk}
receipts := []*types.ReceiptData{recpt0, recpt1, recpt2, recpt3, recpt4, recpt5, recpt6, recpt7}
recpt8 := &types.ReceiptData{Ty: types.ExecOk}
receipts := []*types.ReceiptData{recpt0, recpt1, recpt2, recpt3, recpt4, recpt5, recpt6, recpt7, recpt8}
s.exec.SetReceipt(receipts)
set, err := s.exec.ExecLocal(tx, recpt0, 0)
s.Nil(err)
......@@ -697,6 +702,24 @@ func createCrossParaTx(s suite.Suite, to []byte) (*types.Transaction, error) {
return tx, nil
}
func createCrossCommitTx(s suite.Suite) (*types.Transaction, error) {
status := &pt.ParacrossNodeStatus{MainBlockHash: []byte("hash"), MainBlockHeight: 0, Title: Title}
tx, err := pt.CreateRawCommitTx4MainChain(status, Title+pt.ParaX, 0)
assert.Nil(s.T(), err, "create asset transfer failed")
if err != nil {
return nil, err
}
//tx, err = signTx(s, tx, privFrom)
//assert.Nil(s.T(), err, "sign asset transfer failed")
//if err != nil {
// return nil, err
//}
return tx, nil
}
func createTxsGroup(s suite.Suite, txs []*types.Transaction) ([]*types.Transaction, error) {
group, err := types.CreateTxGroup(txs)
if err != nil {
......
......@@ -165,7 +165,7 @@ func (a *action) nodeJoin(config *pt.ParaNodeAddrConfig) (*types.Receipt, error)
receipt := &types.Receipt{Ty: types.ExecOk}
if !types.IsPara() {
r, err := a.nodeGroupCoinsFrozen([]string{a.fromaddr}, config.CoinsFrozen)
r, err := a.nodeGroupCoinsFrozen(a.fromaddr, config.CoinsFrozen, 1)
if err != nil {
return nil, err
}
......@@ -258,7 +258,7 @@ func (a *action) nodeQuit(config *pt.ParaNodeAddrConfig) (*types.Receipt, error)
//still adding status, quit directly
receipt := &types.Receipt{Ty: types.ExecOk}
if !types.IsPara() {
r, err := a.nodeGroupCoinsActive([]string{stat.FromAddr}, stat.CoinsFrozen)
r, err := a.nodeGroupCoinsActive(stat.FromAddr, stat.CoinsFrozen, 1)
if err != nil {
return nil, err
}
......@@ -438,7 +438,7 @@ func (a *action) nodeVote(config *pt.ParaNodeAddrConfig) (*types.Receipt, error)
stat.Status = pt.ParacrossNodeQuited
if !types.IsPara() {
r, err := a.nodeGroupCoinsActive([]string{stat.FromAddr}, stat.CoinsFrozen)
r, err := a.nodeGroupCoinsActive(stat.FromAddr, stat.CoinsFrozen, 1)
if err != nil {
return nil, err
}
......@@ -546,40 +546,35 @@ func (a *action) checkNodeGroupExist(title string) error {
return nil
}
func (a *action) nodeGroupCoinsFrozen(addrs []string, configCoinsFrozen int64) (*types.Receipt, error) {
func (a *action) nodeGroupCoinsFrozen(createAddr string, configCoinsFrozen int64, nodeCounts int64) (*types.Receipt, error) {
receipt := &types.Receipt{}
confCoins := conf.GInt("nodeGroupFrozenCoins")
if configCoinsFrozen < confCoins {
return nil, pt.ErrParaNodeGroupFrozenCoinsNotEnough
}
if configCoinsFrozen == 0 {
clog.Info("node group apply configCoinsFrozen is 0")
return receipt, nil
}
var logs []*types.ReceiptLog
var kv []*types.KeyValue
realExec := string(types.GetRealExecName(a.tx.Execer))
realExecAddr := dapp.ExecAddress(realExec)
for _, addr := range addrs {
r, err := a.coinsAccount.ExecFrozen(addr, realExecAddr, configCoinsFrozen)
r, err := a.coinsAccount.ExecFrozen(createAddr, realExecAddr, nodeCounts*configCoinsFrozen)
if err != nil {
clog.Error("node group apply", "addr", addr, "realExec", realExec, "realAddr", realExecAddr, "amount", configCoinsFrozen)
clog.Error("node group apply", "addr", createAddr, "realExec", realExec, "realAddr", realExecAddr, "amount", configCoinsFrozen)
return nil, err
}
logs = append(logs, r.Logs...)
kv = append(kv, r.KV...)
}
receipt.KV = append(receipt.KV, kv...)
receipt.Logs = append(receipt.Logs, logs...)
receipt.KV = append(receipt.KV, r.KV...)
receipt.Logs = append(receipt.Logs, r.Logs...)
return receipt, nil
}
func (a *action) nodeGroupCoinsActive(addrs []string, configCoinsFrozen int64) (*types.Receipt, error) {
func (a *action) nodeGroupCoinsActive(createAddr string, configCoinsFrozen int64, nodeCount int64) (*types.Receipt, error) {
receipt := &types.Receipt{}
var logs []*types.ReceiptLog
var kv []*types.KeyValue
realExec := string(types.GetRealExecName(a.tx.Execer))
realExecAddr := dapp.ExecAddress(realExec)
......@@ -587,17 +582,15 @@ func (a *action) nodeGroupCoinsActive(addrs []string, configCoinsFrozen int64) (
return receipt, nil
}
for _, addr := range addrs {
r, err := a.coinsAccount.ExecActive(addr, realExecAddr, configCoinsFrozen)
r, err := a.coinsAccount.ExecActive(createAddr, realExecAddr, nodeCount*configCoinsFrozen)
if err != nil {
clog.Error("node group apply", "addr", addr, "realExec", realExec, "realAddr", realExecAddr, "amount", configCoinsFrozen)
clog.Error("node group apply", "addr", createAddr,
"realExec", realExec, "realAddr", realExecAddr, "amount", configCoinsFrozen, "nodeCount", nodeCount)
return nil, err
}
logs = append(logs, r.Logs...)
kv = append(kv, r.KV...)
}
receipt.KV = append(receipt.KV, kv...)
receipt.Logs = append(receipt.Logs, logs...)
receipt.KV = append(receipt.KV, r.KV...)
receipt.Logs = append(receipt.Logs, r.Logs...)
return receipt, nil
}
......@@ -617,7 +610,7 @@ func (a *action) nodeGroupApply(config *pt.ParaNodeGroupConfig) (*types.Receipt,
receipt := &types.Receipt{Ty: types.ExecOk}
//main chain
if !types.IsPara() {
r, err := a.nodeGroupCoinsFrozen(addrs, config.CoinsFrozen)
r, err := a.nodeGroupCoinsFrozen(a.fromaddr, config.CoinsFrozen, int64(len(addrs)))
if err != nil {
return nil, err
}
......@@ -631,7 +624,8 @@ func (a *action) nodeGroupApply(config *pt.ParaNodeGroupConfig) (*types.Receipt,
ApplyAddr: strings.Join(addrs, ","),
CoinsFrozen: config.CoinsFrozen,
MainHeight: a.exec.GetMainHeight(),
EmptyBlockInterval: config.EmptyBlockInterval}
EmptyBlockInterval: config.EmptyBlockInterval,
FromAddr: a.fromaddr}
saveNodeGroup(a.db, config.Title, stat)
r := makeParaNodeGroupApplyReiceipt(config.Title, a.fromaddr, status, stat, pt.TyLogParaNodeGroupApply)
receipt.KV = append(receipt.KV, r.KV...)
......@@ -650,6 +644,11 @@ func (a *action) nodeGroupQuit(config *pt.ParaNodeGroupConfig) (*types.Receipt,
return nil, pt.ErrParaNodeGroupStatusWrong
}
if status.FromAddr != a.fromaddr {
clog.Error("node group create addr err", "createAddr", status.FromAddr, "currAddr", a.fromaddr)
return nil, types.ErrNotAllow
}
applyAddrs, err := checkNodeGroupAddrsMatch(status.ApplyAddr, config.Addrs)
if err != nil {
return nil, err
......@@ -658,7 +657,7 @@ func (a *action) nodeGroupQuit(config *pt.ParaNodeGroupConfig) (*types.Receipt,
receipt := &types.Receipt{Ty: types.ExecOk}
//main chain
if !types.IsPara() {
r, err := a.nodeGroupCoinsActive(applyAddrs, status.CoinsFrozen)
r, err := a.nodeGroupCoinsActive(a.fromaddr, status.CoinsFrozen, int64(len(applyAddrs)))
if err != nil {
return nil, err
}
......@@ -671,7 +670,8 @@ func (a *action) nodeGroupQuit(config *pt.ParaNodeGroupConfig) (*types.Receipt,
ApplyAddr: status.ApplyAddr,
CoinsFrozen: status.CoinsFrozen,
MainHeight: a.exec.GetMainHeight(),
EmptyBlockInterval: status.EmptyBlockInterval}
EmptyBlockInterval: status.EmptyBlockInterval,
FromAddr: a.fromaddr}
saveNodeGroup(a.db, config.Title, stat)
r := makeParaNodeGroupApplyReiceipt(config.Title, a.fromaddr, status, stat, pt.TyLogParaNodeGroupQuit)
receipt.KV = append(receipt.KV, r.KV...)
......@@ -734,7 +734,7 @@ func (a *action) nodeGroupApprove(config *pt.ParaNodeGroupConfig) (*types.Receip
receipt := &types.Receipt{Ty: types.ExecOk}
//create the node group
r, err := a.nodeGroupCreate(config.Title, applyAddrs, config.CoinsFrozen)
r, err := a.nodeGroupCreate(config.Title, applyAddrs, status.CoinsFrozen, status.FromAddr)
if err != nil {
return nil, err
}
......@@ -746,7 +746,8 @@ func (a *action) nodeGroupApprove(config *pt.ParaNodeGroupConfig) (*types.Receip
ApplyAddr: status.ApplyAddr,
CoinsFrozen: status.CoinsFrozen,
MainHeight: a.exec.GetMainHeight(),
EmptyBlockInterval: status.EmptyBlockInterval}
EmptyBlockInterval: status.EmptyBlockInterval,
FromAddr: status.FromAddr}
saveNodeGroup(a.db, config.Title, stat)
r = makeParaNodeGroupApplyReiceipt(config.Title, a.fromaddr, status, stat, pt.TyLogParaNodeGroupApprove)
receipt.KV = append(receipt.KV, r.KV...)
......@@ -755,7 +756,7 @@ func (a *action) nodeGroupApprove(config *pt.ParaNodeGroupConfig) (*types.Receip
return receipt, nil
}
func (a *action) nodeGroupCreate(title string, nodes []string, coinFrozen int64) (*types.Receipt, error) {
func (a *action) nodeGroupCreate(title string, nodes []string, coinFrozen int64, createAddr string) (*types.Receipt, error) {
var item types.ConfigItem
key := calcParaNodeGroupKey(title)
item.Key = string(key)
......@@ -774,7 +775,8 @@ func (a *action) nodeGroupCreate(title string, nodes []string, coinFrozen int64)
Title: title,
ApplyAddr: addr,
Votes: &pt.ParaNodeVoteDetail{},
CoinsFrozen: coinFrozen}
CoinsFrozen: coinFrozen,
FromAddr: createAddr}
saveNodeAddr(a.db, title, addr, stat)
config := &pt.ParaNodeAddrConfig{
Title: title,
......@@ -799,10 +801,6 @@ func (a *action) NodeGroupConfig(config *pt.ParaNodeGroupConfig) (*types.Receipt
}
if config.Op == pt.ParacrossNodeGroupApply {
if !strings.Contains(config.Addrs, a.fromaddr) {
clog.Error("node group apply fromaddr not one of apply addrs", "addr", a.fromaddr, "apply", config.Addrs)
return nil, types.ErrNotAllow
}
err := a.checkNodeGroupExist(config.Title)
if err != nil {
return nil, err
......@@ -817,10 +815,6 @@ func (a *action) NodeGroupConfig(config *pt.ParaNodeGroupConfig) (*types.Receipt
return a.nodeGroupApprove(config)
} else if config.Op == pt.ParacrossNodeGroupQuit {
if !strings.Contains(config.Addrs, a.fromaddr) {
clog.Error("node group apply fromaddr not one of apply addrs", "addr", a.fromaddr, "apply", config.Addrs)
return nil, types.ErrNotAllow
}
return a.nodeGroupQuit(config)
}
......
......@@ -99,6 +99,7 @@ message ParaNodeGroupStatus {
int64 coinsFrozen = 4;
uint32 emptyBlockInterval = 5;
int64 mainHeight = 6;
string fromAddr = 7;
}
message ReceiptParaNodeGroupConfig {
......
......@@ -742,6 +742,7 @@ type ParaNodeGroupStatus struct {
CoinsFrozen int64 `protobuf:"varint,4,opt,name=coinsFrozen,proto3" json:"coinsFrozen,omitempty"`
EmptyBlockInterval uint32 `protobuf:"varint,5,opt,name=emptyBlockInterval,proto3" json:"emptyBlockInterval,omitempty"`
MainHeight int64 `protobuf:"varint,6,opt,name=mainHeight,proto3" json:"mainHeight,omitempty"`
FromAddr string `protobuf:"bytes,7,opt,name=fromAddr,proto3" json:"fromAddr,omitempty"`
XXX_NoUnkeyedLiteral struct{} `json:"-"`
XXX_unrecognized []byte `json:"-"`
XXX_sizecache int32 `json:"-"`
......@@ -814,6 +815,13 @@ func (m *ParaNodeGroupStatus) GetMainHeight() int64 {
return 0
}
func (m *ParaNodeGroupStatus) GetFromAddr() string {
if m != nil {
return m.FromAddr
}
return ""
}
type ReceiptParaNodeGroupConfig struct {
Addr string `protobuf:"bytes,1,opt,name=addr,proto3" json:"addr,omitempty"`
Config *ParaNodeGroupConfig `protobuf:"bytes,2,opt,name=config,proto3" json:"config,omitempty"`
......@@ -2396,111 +2404,111 @@ func init() {
func init() { proto.RegisterFile("paracross.proto", fileDescriptor_6a397e38c9ea6747) }
var fileDescriptor_6a397e38c9ea6747 = []byte{
// 1655 bytes of a gzipped FileDescriptorProto
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xd4, 0x18, 0x4b, 0x6f, 0x1b, 0xc7,
0x99, 0xcb, 0xa7, 0xf8, 0xe9, 0x3d, 0xb6, 0x64, 0x9a, 0x75, 0x5d, 0x62, 0xe1, 0x16, 0x42, 0xd1,
0xca, 0xae, 0x54, 0xb8, 0x28, 0x8c, 0xa2, 0x95, 0x65, 0x5b, 0x14, 0xfc, 0x40, 0xb1, 0x52, 0x1f,
0x97, 0x00, 0x59, 0x93, 0x23, 0x69, 0x11, 0x72, 0x77, 0xbd, 0x33, 0xb4, 0xa5, 0xdc, 0x02, 0x24,
0xf9, 0x23, 0xc9, 0x39, 0x97, 0x00, 0x39, 0x07, 0x39, 0x26, 0x87, 0x1c, 0xf2, 0x13, 0xf2, 0x47,
0x82, 0xef, 0x9b, 0xd9, 0xd9, 0x99, 0x25, 0xc5, 0x38, 0x42, 0x80, 0x20, 0x37, 0x7e, 0xdf, 0x7c,
0xef, 0x37, 0x17, 0x56, 0xd3, 0x30, 0x0b, 0x07, 0x59, 0x22, 0xc4, 0x76, 0x9a, 0x25, 0x32, 0x61,
0x0d, 0x79, 0x91, 0x72, 0xd1, 0x5d, 0x97, 0x59, 0x18, 0x8b, 0x70, 0x20, 0xa3, 0x24, 0x56, 0x2f,
0xdd, 0xa5, 0x41, 0x32, 0x1e, 0x1b, 0x68, 0xed, 0xe5, 0x28, 0x19, 0xbc, 0x37, 0x38, 0x0b, 0xa3,
0x1c, 0xb3, 0xc2, 0xcf, 0xf9, 0x60, 0x22, 0x93, 0x4c, 0xc1, 0xfe, 0x33, 0xd8, 0xfc, 0x77, 0x2e,
0xfc, 0x48, 0x86, 0x72, 0x22, 0x1e, 0x71, 0x19, 0x46, 0x23, 0xc1, 0xae, 0x43, 0x23, 0x1c, 0x0e,
0x33, 0xd1, 0xf1, 0x7a, 0xb5, 0xad, 0x76, 0xa0, 0x00, 0x76, 0x0b, 0xda, 0x24, 0xb3, 0x1f, 0x8a,
0xb3, 0x4e, 0xb5, 0x57, 0xdb, 0x5a, 0x0a, 0x0a, 0x84, 0xff, 0x85, 0x07, 0x1b, 0x46, 0x5c, 0x9f,
0x47, 0xa7, 0x67, 0x52, 0x09, 0x65, 0x9b, 0xd0, 0x14, 0xf4, 0xab, 0xe3, 0xf5, 0xbc, 0xad, 0x46,
0xa0, 0x21, 0xd4, 0x22, 0x23, 0x39, 0xe2, 0x9d, 0x6a, 0xcf, 0x43, 0x2d, 0x04, 0x20, 0xf5, 0x19,
0x71, 0x77, 0x6a, 0x3d, 0x6f, 0xab, 0x16, 0x68, 0x88, 0xfd, 0x0d, 0x5a, 0x43, 0x65, 0x5e, 0xa7,
0xde, 0xf3, 0xb6, 0x16, 0x77, 0x7e, 0xbb, 0x4d, 0x91, 0xd8, 0x9e, 0xed, 0x43, 0x90, 0x53, 0xb3,
0xdb, 0x00, 0xe3, 0x30, 0x8a, 0x95, 0x49, 0x9d, 0x06, 0x09, 0xb5, 0x30, 0xfe, 0x3b, 0xb0, 0x5a,
0x12, 0x51, 0x58, 0xe6, 0xcd, 0xb6, 0xac, 0xea, 0x58, 0xe6, 0xc4, 0x05, 0x8d, 0x76, 0xe2, 0xf2,
0xa9, 0x07, 0x1d, 0x23, 0x7f, 0x3f, 0x89, 0x05, 0x8f, 0xc5, 0x64, 0xbe, 0xa2, 0x1e, 0x2c, 0x52,
0xde, 0xfa, 0xb6, 0x36, 0x1b, 0xc5, 0xee, 0xc0, 0xf2, 0x40, 0x89, 0xea, 0xdb, 0xb1, 0x72, 0x91,
0xec, 0x8f, 0xb0, 0xa6, 0x11, 0x0f, 0x8d, 0x7d, 0x75, 0x52, 0x34, 0x85, 0xf7, 0x3f, 0xf6, 0x80,
0xa1, 0x99, 0x2f, 0x92, 0x21, 0xdf, 0x1b, 0x0e, 0xb3, 0xfd, 0x24, 0x3e, 0x89, 0x4e, 0x2f, 0x31,
0x70, 0x05, 0xaa, 0x49, 0xaa, 0xd3, 0x56, 0x4d, 0x52, 0xc6, 0xa0, 0x8e, 0x25, 0x42, 0x56, 0xb4,
0x03, 0xfa, 0x8d, 0x9c, 0xaf, 0xc3, 0xd1, 0x84, 0x6b, 0x8d, 0x0a, 0x20, 0xd7, 0x92, 0x28, 0x16,
0x4f, 0xb2, 0xe4, 0x7d, 0x1e, 0xeb, 0x6c, 0xd8, 0x28, 0xff, 0x5f, 0x85, 0x1d, 0xff, 0x4d, 0x24,
0x57, 0xe9, 0xbc, 0xa4, 0x22, 0x51, 0x47, 0x22, 0xb9, 0xa0, 0x6a, 0x44, 0x1d, 0x08, 0xf8, 0xdf,
0x96, 0x5c, 0xb9, 0x52, 0x19, 0xde, 0x82, 0x76, 0x98, 0xa6, 0xa3, 0x8b, 0xbd, 0xc2, 0xaf, 0x02,
0x51, 0x76, 0xa3, 0x3e, 0xe5, 0x06, 0xbb, 0x9b, 0x9b, 0xd6, 0xa0, 0x62, 0xbd, 0x69, 0x15, 0xab,
0xeb, 0x9a, 0xb6, 0x9a, 0x75, 0x61, 0xe1, 0x24, 0x4b, 0xc6, 0xa4, 0xaf, 0x49, 0xfa, 0x0c, 0xec,
0x7f, 0xe5, 0xc1, 0x46, 0xc0, 0x07, 0x3c, 0x4a, 0x65, 0x2e, 0x40, 0xe7, 0x27, 0x8f, 0xbc, 0x67,
0x45, 0xfe, 0x2f, 0xd0, 0x1c, 0xd0, 0x2b, 0x79, 0x34, 0xad, 0xbb, 0x48, 0x6f, 0xa0, 0x09, 0xd9,
0x9f, 0xa1, 0x9e, 0x66, 0xfc, 0x35, 0x39, 0x3a, 0x9b, 0x41, 0x05, 0x31, 0x20, 0x32, 0xb6, 0x0b,
0xad, 0xc1, 0x24, 0xcb, 0x78, 0x2c, 0x75, 0x2f, 0xce, 0xe1, 0xc8, 0x29, 0xfd, 0x08, 0x6e, 0x96,
0x7c, 0xc0, 0x20, 0x04, 0x7c, 0x90, 0x64, 0x43, 0xc7, 0x7b, 0xcf, 0xf5, 0x1e, 0xdf, 0x30, 0x44,
0xf4, 0xa6, 0x72, 0x64, 0xe0, 0xa2, 0xca, 0x6a, 0x94, 0x53, 0x05, 0xf8, 0xdf, 0x7b, 0x70, 0x63,
0x86, 0xae, 0x47, 0x49, 0xcc, 0x2f, 0xa9, 0xe8, 0xdb, 0x00, 0x32, 0xcc, 0x4e, 0xb9, 0xb4, 0xb4,
0x58, 0x18, 0x7a, 0x4f, 0x64, 0x38, 0x42, 0x51, 0x42, 0x2b, 0xb3, 0x30, 0x58, 0x2e, 0x04, 0xa1,
0x1a, 0x8a, 0x49, 0x23, 0x28, 0x10, 0xe8, 0xc1, 0x38, 0x11, 0x92, 0x1e, 0x1b, 0xf4, 0x68, 0x60,
0xd6, 0x81, 0x16, 0x7a, 0x13, 0x08, 0xa9, 0xd3, 0x9e, 0x83, 0xa8, 0x73, 0x98, 0xc4, 0x5c, 0xc5,
0xb1, 0xd3, 0x52, 0x3a, 0x0b, 0x8c, 0xff, 0x89, 0x07, 0xd7, 0x72, 0xf7, 0x0e, 0xb2, 0x64, 0x92,
0xbe, 0x65, 0xcf, 0x2e, 0x53, 0xcf, 0x9a, 0x8e, 0x52, 0xc5, 0xad, 0x3b, 0xea, 0xc7, 0x0b, 0x7b,
0x1b, 0x18, 0x1f, 0xa7, 0xf2, 0x82, 0x46, 0xc7, 0x61, 0x2c, 0x79, 0xf6, 0x3a, 0x1c, 0x91, 0x57,
0xcb, 0xc1, 0x8c, 0x17, 0xff, 0xbb, 0xb2, 0x95, 0xbf, 0x48, 0x3b, 0xfe, 0x44, 0xab, 0x4b, 0x4b,
0xa3, 0x39, 0xb5, 0x34, 0xbe, 0xf6, 0xa0, 0x5b, 0xaa, 0x30, 0x3b, 0x05, 0xb3, 0xda, 0x72, 0xa7,
0xd4, 0x96, 0xdd, 0x52, 0xcf, 0x58, 0xfc, 0xa6, 0x2f, 0xb7, 0x9d, 0xbe, 0x9c, 0xc9, 0xe1, 0x34,
0xe6, 0x5f, 0xcb, 0x8d, 0x39, 0x8f, 0xc5, 0x74, 0xe6, 0xff, 0xe1, 0x7a, 0xc0, 0x5f, 0x99, 0x25,
0x85, 0x74, 0x87, 0xf1, 0x49, 0x72, 0x49, 0x21, 0xe5, 0xbe, 0x55, 0x2d, 0xdf, 0x8a, 0x64, 0xd6,
0xec, 0x64, 0xfa, 0x87, 0xb0, 0x19, 0x70, 0x91, 0x3a, 0xa2, 0xf7, 0xa8, 0xd0, 0xee, 0xda, 0x03,
0x7d, 0xee, 0x00, 0x51, 0x74, 0xfe, 0x53, 0x6c, 0xe9, 0x92, 0x28, 0xf2, 0x46, 0xb0, 0x7b, 0xae,
0xac, 0x79, 0x3e, 0x6b, 0x61, 0x1f, 0x79, 0xb0, 0x8e, 0xcf, 0x94, 0xf4, 0x9d, 0xe7, 0x61, 0x14,
0x3f, 0x0f, 0x53, 0x6b, 0xc1, 0x7b, 0x97, 0x2f, 0x78, 0xe5, 0x76, 0x81, 0x28, 0x95, 0x4a, 0xad,
0x5c, 0x2a, 0xd4, 0xfc, 0x08, 0x15, 0xdb, 0xd7, 0xc0, 0xfe, 0x23, 0xb5, 0xa9, 0x0a, 0x33, 0x28,
0xee, 0xdb, 0xd0, 0x88, 0x24, 0x1f, 0xe7, 0xfe, 0x74, 0x2c, 0x7f, 0x1c, 0x83, 0x03, 0x45, 0xe6,
0x7f, 0x5e, 0x53, 0x2d, 0x66, 0xe2, 0xa2, 0x5b, 0xec, 0x0e, 0x2c, 0xa3, 0xa6, 0x62, 0xf9, 0x7b,
0x74, 0x9c, 0xb8, 0x48, 0xb6, 0x05, 0xab, 0x05, 0xc2, 0xbe, 0x38, 0xca, 0xe8, 0xa2, 0x1e, 0x6a,
0xb3, 0xcf, 0xa2, 0xba, 0x13, 0x35, 0x1f, 0x96, 0xd2, 0x8c, 0x17, 0xca, 0x1b, 0xa4, 0xdc, 0xc1,
0xb9, 0x91, 0x6d, 0x96, 0x4e, 0x27, 0x2d, 0x01, 0x9d, 0xe1, 0x44, 0xd0, 0x32, 0x12, 0x0c, 0x0e,
0x25, 0x08, 0x43, 0xb0, 0xa0, 0x24, 0x18, 0x04, 0xc6, 0x5e, 0x9e, 0xef, 0x27, 0x93, 0x58, 0x8a,
0x4e, 0x9b, 0x9a, 0xdd, 0xc0, 0xea, 0x2d, 0xe0, 0x62, 0x32, 0x92, 0x1d, 0x20, 0x46, 0x03, 0xe3,
0x50, 0x96, 0xe7, 0x28, 0x41, 0x74, 0x16, 0xe9, 0xd0, 0xcd, 0x41, 0xba, 0xbc, 0x30, 0xcc, 0xc7,
0x39, 0xeb, 0x92, 0x8a, 0xa9, 0x83, 0x44, 0xcb, 0x35, 0x42, 0x09, 0x59, 0x26, 0x21, 0x0e, 0xce,
0x7f, 0x6a, 0xdd, 0xcb, 0xfb, 0xc9, 0x78, 0x1c, 0xc9, 0x3d, 0xba, 0xe6, 0x71, 0x50, 0x58, 0x93,
0xd1, 0xad, 0xe7, 0x52, 0x8a, 0x4d, 0xa3, 0x49, 0xb8, 0x6e, 0x9e, 0x9f, 0x47, 0x31, 0xcf, 0xae,
0x2e, 0x0b, 0x0b, 0x22, 0x12, 0x47, 0x7c, 0x74, 0x62, 0xae, 0x55, 0x2a, 0x88, 0x85, 0xa0, 0x8c,
0xf6, 0xbf, 0xa9, 0x5b, 0xb7, 0xb3, 0xd6, 0x78, 0x1f, 0xc7, 0x1c, 0x7a, 0xa3, 0x35, 0xde, 0x2a,
0x6b, 0xb4, 0x7d, 0xed, 0x57, 0x02, 0x4d, 0xcd, 0x76, 0xa1, 0x31, 0x46, 0xc3, 0xf5, 0xac, 0xfb,
0x4d, 0x99, 0xcd, 0xf2, 0xaa, 0x5f, 0x09, 0x14, 0x2d, 0xfb, 0x07, 0x2c, 0x87, 0x42, 0x70, 0x79,
0x8c, 0x7f, 0x86, 0x4e, 0x78, 0xa6, 0xa7, 0xde, 0x86, 0x66, 0xde, 0xc3, 0x37, 0x91, 0x3f, 0xf6,
0x2b, 0x81, 0x4b, 0x6d, 0xd8, 0xff, 0x17, 0xc9, 0xb3, 0x61, 0x16, 0xbe, 0xd1, 0xc7, 0x9a, 0xcb,
0x9e, 0x3f, 0x1a, 0xf6, 0x1c, 0xc1, 0x76, 0x61, 0x41, 0xe6, 0x8a, 0x9b, 0xf3, 0x15, 0x1b, 0x42,
0x64, 0x7a, 0x93, 0xab, 0x6b, 0xcd, 0x57, 0x67, 0x08, 0xd9, 0x63, 0x58, 0xc9, 0x05, 0x1c, 0x27,
0x8f, 0xcf, 0xf9, 0x80, 0x4a, 0xbd, 0x88, 0x92, 0xab, 0x4f, 0x91, 0xf4, 0x2b, 0x41, 0x89, 0x89,
0x3d, 0x00, 0x88, 0xcd, 0xed, 0x48, 0x0d, 0x31, 0xef, 0x3a, 0xec, 0x57, 0x02, 0x8b, 0x9c, 0x3d,
0x81, 0xd5, 0xd8, 0x5d, 0x53, 0xd4, 0x36, 0x73, 0x17, 0x59, 0xbf, 0x12, 0x94, 0x99, 0xf0, 0x10,
0x91, 0x17, 0x54, 0x51, 0x8d, 0xa0, 0x2a, 0x2f, 0x1e, 0xb6, 0xf4, 0x09, 0x87, 0x3b, 0x75, 0xd3,
0xda, 0xa9, 0x56, 0xb1, 0x5c, 0xb6, 0x4f, 0x75, 0x69, 0x57, 0xdf, 0xba, 0xb4, 0xef, 0x39, 0xfb,
0x74, 0xaa, 0x34, 0xed, 0xbf, 0xad, 0x7a, 0xa3, 0xde, 0x2f, 0x6f, 0xd4, 0xf9, 0x4c, 0x66, 0xa7,
0x3e, 0x75, 0x2e, 0xf6, 0xa2, 0x82, 0xaf, 0xd4, 0xdd, 0x1f, 0x56, 0x71, 0x43, 0xbb, 0xd2, 0xe8,
0x98, 0x75, 0xcf, 0x52, 0x6f, 0xea, 0x2c, 0xed, 0xc1, 0x22, 0x41, 0x2a, 0x8c, 0x3a, 0xe8, 0x36,
0x8a, 0xfd, 0x01, 0x56, 0xf0, 0x14, 0x3d, 0x0a, 0xc7, 0x5c, 0x13, 0xa9, 0x0d, 0x5e, 0xc2, 0x16,
0xb3, 0xbf, 0x3e, 0x7b, 0xf6, 0x37, 0xca, 0x1b, 0xb3, 0x98, 0xca, 0xcd, 0x79, 0x53, 0xb9, 0x35,
0x67, 0x2a, 0x2f, 0xb8, 0x53, 0xd9, 0x7f, 0x77, 0xba, 0x3e, 0xf4, 0xdf, 0x87, 0x9f, 0xa9, 0x3e,
0xfc, 0xdf, 0xc3, 0xa2, 0x79, 0x3e, 0x3e, 0x47, 0xf7, 0xd4, 0xdc, 0xd7, 0x82, 0x35, 0xe4, 0x1f,
0xe0, 0x2d, 0x52, 0x1c, 0x4c, 0xc7, 0x18, 0x8b, 0xf2, 0x8e, 0x7c, 0x9b, 0x4f, 0x07, 0xfe, 0x07,
0x55, 0x58, 0x77, 0xae, 0x9a, 0x5f, 0x57, 0x56, 0xdb, 0x57, 0xcd, 0x6a, 0xdb, 0xca, 0xea, 0x01,
0x5c, 0x73, 0x42, 0x40, 0xd1, 0xc4, 0x56, 0x6d, 0x92, 0x35, 0xe5, 0x2b, 0x68, 0x2a, 0x5c, 0x81,
0xa6, 0x53, 0x2d, 0x57, 0xce, 0x0a, 0x5a, 0x36, 0x3b, 0x27, 0x53, 0x57, 0x9d, 0xf3, 0xd9, 0xe6,
0xb3, 0x2a, 0xac, 0x14, 0xab, 0x0d, 0xc7, 0x2b, 0x16, 0x19, 0xfe, 0x27, 0xcd, 0x8b, 0x0c, 0x7f,
0xd3, 0x30, 0x4b, 0xf2, 0x2f, 0x21, 0x32, 0xc1, 0xd4, 0x45, 0x66, 0x84, 0x53, 0xd0, 0x17, 0x02,
0x0b, 0x63, 0x55, 0x54, 0x9d, 0x34, 0x6a, 0x08, 0xf1, 0xe1, 0x18, 0x63, 0x95, 0x87, 0x5c, 0x41,
0xa8, 0x93, 0xe3, 0xb8, 0x57, 0xd1, 0xa6, 0xdf, 0x74, 0x6c, 0x5f, 0x8c, 0x5f, 0x26, 0x23, 0x0a,
0x73, 0x3b, 0xd0, 0x90, 0x95, 0x36, 0x70, 0xd2, 0x46, 0x9f, 0x81, 0x30, 0xdd, 0x18, 0x2d, 0x7d,
0xe1, 0x6d, 0x10, 0xc5, 0x14, 0x1e, 0xed, 0x4f, 0xc3, 0x2c, 0xd4, 0x54, 0x9b, 0xea, 0x98, 0x2d,
0x30, 0x78, 0x18, 0x89, 0xc9, 0x60, 0xc0, 0x85, 0xe8, 0xdc, 0x20, 0xe7, 0x72, 0x70, 0xe7, 0xcb,
0x2a, 0xb4, 0xcd, 0xb7, 0x4a, 0xf6, 0x4f, 0x58, 0x38, 0xe0, 0x92, 0x52, 0xc0, 0xd6, 0x4c, 0xe6,
0x5e, 0x1d, 0xc9, 0x2c, 0x8a, 0x4f, 0xbb, 0xbf, 0x9b, 0xbe, 0x09, 0x9c, 0xef, 0x62, 0x7e, 0x85,
0xfd, 0x1d, 0xe0, 0x59, 0x24, 0xa4, 0x2e, 0x86, 0xe5, 0x42, 0xc4, 0x8b, 0x68, 0xd4, 0xed, 0xce,
0xaa, 0x05, 0x45, 0xea, 0x57, 0xd8, 0x33, 0x58, 0xc9, 0x75, 0xe7, 0x5e, 0x15, 0xec, 0xb3, 0x9a,
0xb6, 0x7b, 0x69, 0x6d, 0xf9, 0x15, 0xf6, 0x00, 0xd6, 0x0e, 0xb8, 0xa4, 0x0a, 0x30, 0xe7, 0xdd,
0x4a, 0x21, 0x0f, 0xb3, 0xd7, 0xdd, 0x28, 0xfb, 0x43, 0xe4, 0x7e, 0x85, 0xfd, 0x09, 0x9a, 0x87,
0xe2, 0xe8, 0x22, 0x1e, 0x94, 0x3d, 0x58, 0xd7, 0xe0, 0xa1, 0xd8, 0x0f, 0x27, 0xa7, 0x67, 0xf2,
0x3f, 0xa9, 0x5f, 0x79, 0xd9, 0xa4, 0xef, 0xb2, 0xbb, 0x3f, 0x04, 0x00, 0x00, 0xff, 0xff, 0x59,
0x3c, 0x11, 0x4f, 0xf4, 0x15, 0x00, 0x00,
// 1658 bytes of a gzipped FileDescriptorProto
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xd4, 0x18, 0xdb, 0x6e, 0x1b, 0xc7,
0x95, 0xcb, 0xab, 0x78, 0x74, 0x1f, 0x5b, 0x32, 0xcd, 0xba, 0x2e, 0xb1, 0x70, 0x0b, 0xa1, 0x68,
0x65, 0x57, 0x2a, 0x5c, 0x14, 0x46, 0xd1, 0xca, 0xb2, 0x2d, 0x0a, 0xbe, 0xa0, 0x58, 0xa9, 0x97,
0x97, 0x00, 0x59, 0x93, 0x23, 0x69, 0x11, 0x72, 0x77, 0xbd, 0x33, 0xb4, 0xa5, 0xbc, 0x05, 0x48,
0xf2, 0x23, 0xc9, 0x73, 0x5e, 0x02, 0xe4, 0x39, 0xc8, 0x63, 0xf2, 0x90, 0x8f, 0xc8, 0x07, 0xe4,
0x17, 0x82, 0x73, 0x66, 0x76, 0x76, 0x66, 0x49, 0x31, 0x8e, 0x10, 0x20, 0xc8, 0x1b, 0xcf, 0x99,
0x73, 0xbf, 0x73, 0x61, 0x35, 0x0d, 0xb3, 0x70, 0x90, 0x25, 0x42, 0x6c, 0xa7, 0x59, 0x22, 0x13,
0xd6, 0x90, 0x17, 0x29, 0x17, 0xdd, 0x75, 0x99, 0x85, 0xb1, 0x08, 0x07, 0x32, 0x4a, 0x62, 0xf5,
0xd2, 0x5d, 0x1a, 0x24, 0xe3, 0xb1, 0x81, 0xd6, 0x5e, 0x8e, 0x92, 0xc1, 0x7b, 0x83, 0xb3, 0x30,
0xca, 0x31, 0x2b, 0xfc, 0x9c, 0x0f, 0x26, 0x32, 0xc9, 0x14, 0xec, 0x3f, 0x83, 0xcd, 0x7f, 0xe7,
0xc2, 0x8f, 0x64, 0x28, 0x27, 0xe2, 0x11, 0x97, 0x61, 0x34, 0x12, 0xec, 0x3a, 0x34, 0xc2, 0xe1,
0x30, 0x13, 0x1d, 0xaf, 0x57, 0xdb, 0x6a, 0x07, 0x0a, 0x60, 0xb7, 0xa0, 0x4d, 0x32, 0xfb, 0xa1,
0x38, 0xeb, 0x54, 0x7b, 0xb5, 0xad, 0xa5, 0xa0, 0x40, 0xf8, 0x5f, 0x78, 0xb0, 0x61, 0xc4, 0xf5,
0x79, 0x74, 0x7a, 0x26, 0x95, 0x50, 0xb6, 0x09, 0x4d, 0x41, 0xbf, 0x3a, 0x5e, 0xcf, 0xdb, 0x6a,
0x04, 0x1a, 0x42, 0x2d, 0x32, 0x92, 0x23, 0xde, 0xa9, 0xf6, 0x3c, 0xd4, 0x42, 0x00, 0x52, 0x9f,
0x11, 0x77, 0xa7, 0xd6, 0xf3, 0xb6, 0x6a, 0x81, 0x86, 0xd8, 0xdf, 0xa0, 0x35, 0x54, 0xe6, 0x75,
0xea, 0x3d, 0x6f, 0x6b, 0x71, 0xe7, 0xb7, 0xdb, 0x14, 0x89, 0xed, 0xd9, 0x3e, 0x04, 0x39, 0x35,
0xbb, 0x0d, 0x30, 0x0e, 0xa3, 0x58, 0x99, 0xd4, 0x69, 0x90, 0x50, 0x0b, 0xe3, 0xbf, 0x03, 0xab,
0x25, 0x11, 0x85, 0x65, 0xde, 0x6c, 0xcb, 0xaa, 0x8e, 0x65, 0x4e, 0x5c, 0xd0, 0x68, 0x27, 0x2e,
0x9f, 0x7a, 0xd0, 0x31, 0xf2, 0xf7, 0x93, 0x58, 0xf0, 0x58, 0x4c, 0xe6, 0x2b, 0xea, 0xc1, 0x22,
0xe5, 0xad, 0x6f, 0x6b, 0xb3, 0x51, 0xec, 0x0e, 0x2c, 0x0f, 0x94, 0xa8, 0xbe, 0x1d, 0x2b, 0x17,
0xc9, 0xfe, 0x08, 0x6b, 0x1a, 0xf1, 0xd0, 0xd8, 0x57, 0x27, 0x45, 0x53, 0x78, 0xff, 0x63, 0x0f,
0x18, 0x9a, 0xf9, 0x22, 0x19, 0xf2, 0xbd, 0xe1, 0x30, 0xdb, 0x4f, 0xe2, 0x93, 0xe8, 0xf4, 0x12,
0x03, 0x57, 0xa0, 0x9a, 0xa4, 0x3a, 0x6d, 0xd5, 0x24, 0x65, 0x0c, 0xea, 0x58, 0x22, 0x64, 0x45,
0x3b, 0xa0, 0xdf, 0xc8, 0xf9, 0x3a, 0x1c, 0x4d, 0xb8, 0xd6, 0xa8, 0x00, 0x72, 0x2d, 0x89, 0x62,
0xf1, 0x24, 0x4b, 0xde, 0xe7, 0xb1, 0xce, 0x86, 0x8d, 0xf2, 0xff, 0x55, 0xd8, 0xf1, 0xdf, 0x44,
0x72, 0x95, 0xce, 0x4b, 0x2a, 0x12, 0x75, 0x24, 0x92, 0x0b, 0xaa, 0x46, 0xd4, 0x81, 0x80, 0xff,
0x6d, 0xc9, 0x95, 0x2b, 0x95, 0xe1, 0x2d, 0x68, 0x87, 0x69, 0x3a, 0xba, 0xd8, 0x2b, 0xfc, 0x2a,
0x10, 0x65, 0x37, 0xea, 0x53, 0x6e, 0xb0, 0xbb, 0xb9, 0x69, 0x0d, 0x2a, 0xd6, 0x9b, 0x56, 0xb1,
0xba, 0xae, 0x69, 0xab, 0x59, 0x17, 0x16, 0x4e, 0xb2, 0x64, 0x4c, 0xfa, 0x9a, 0xa4, 0xcf, 0xc0,
0xfe, 0x57, 0x1e, 0x6c, 0x04, 0x7c, 0xc0, 0xa3, 0x54, 0xe6, 0x02, 0x74, 0x7e, 0xf2, 0xc8, 0x7b,
0x56, 0xe4, 0xff, 0x02, 0xcd, 0x01, 0xbd, 0x92, 0x47, 0xd3, 0xba, 0x8b, 0xf4, 0x06, 0x9a, 0x90,
0xfd, 0x19, 0xea, 0x69, 0xc6, 0x5f, 0x93, 0xa3, 0xb3, 0x19, 0x54, 0x10, 0x03, 0x22, 0x63, 0xbb,
0xd0, 0x1a, 0x4c, 0xb2, 0x8c, 0xc7, 0x52, 0xf7, 0xe2, 0x1c, 0x8e, 0x9c, 0xd2, 0x8f, 0xe0, 0x66,
0xc9, 0x07, 0x0c, 0x42, 0xc0, 0x07, 0x49, 0x36, 0x74, 0xbc, 0xf7, 0x5c, 0xef, 0xf1, 0x0d, 0x43,
0x44, 0x6f, 0x2a, 0x47, 0x06, 0x2e, 0xaa, 0xac, 0x46, 0x39, 0x55, 0x80, 0xff, 0x9d, 0x07, 0x37,
0x66, 0xe8, 0x7a, 0x94, 0xc4, 0xfc, 0x92, 0x8a, 0xbe, 0x0d, 0x20, 0xc3, 0xec, 0x94, 0x4b, 0x4b,
0x8b, 0x85, 0xa1, 0xf7, 0x44, 0x86, 0x23, 0x14, 0x25, 0xb4, 0x32, 0x0b, 0x83, 0xe5, 0x42, 0x10,
0xaa, 0xa1, 0x98, 0x34, 0x82, 0x02, 0x81, 0x1e, 0x8c, 0x13, 0x21, 0xe9, 0xb1, 0x41, 0x8f, 0x06,
0x66, 0x1d, 0x68, 0xa1, 0x37, 0x81, 0x90, 0x3a, 0xed, 0x39, 0x88, 0x3a, 0x87, 0x49, 0xcc, 0x55,
0x1c, 0x3b, 0x2d, 0xa5, 0xb3, 0xc0, 0xf8, 0x9f, 0x78, 0x70, 0x2d, 0x77, 0xef, 0x20, 0x4b, 0x26,
0xe9, 0x5b, 0xf6, 0xec, 0x32, 0xf5, 0xac, 0xe9, 0x28, 0x55, 0xdc, 0xba, 0xa3, 0x7e, 0xbc, 0xb0,
0xb7, 0x81, 0xf1, 0x71, 0x2a, 0x2f, 0x68, 0x74, 0x1c, 0xc6, 0x92, 0x67, 0xaf, 0xc3, 0x11, 0x79,
0xb5, 0x1c, 0xcc, 0x78, 0xf1, 0xbf, 0x2f, 0x5b, 0xf9, 0x8b, 0xb4, 0xe3, 0x4f, 0xb4, 0xba, 0xb4,
0x34, 0x9a, 0xe5, 0xa5, 0xe1, 0xd4, 0x6b, 0xab, 0xd4, 0xad, 0x5f, 0x7b, 0xd0, 0x2d, 0x55, 0x9f,
0x9d, 0x9e, 0x59, 0x2d, 0xbb, 0x53, 0x6a, 0xd9, 0x6e, 0xa9, 0x9f, 0x2c, 0x7e, 0xd3, 0xb3, 0xdb,
0x4e, 0xcf, 0xce, 0xe4, 0x70, 0x9a, 0xf6, 0xaf, 0xe5, 0xa6, 0x9d, 0xc7, 0x62, 0xba, 0xf6, 0xff,
0x70, 0x3d, 0xe0, 0xaf, 0xcc, 0x02, 0x43, 0xba, 0xc3, 0xf8, 0x24, 0xb9, 0xa4, 0xc8, 0x72, 0xdf,
0xaa, 0x96, 0x6f, 0x45, 0xa2, 0x6b, 0x76, 0xa2, 0xfd, 0x43, 0xd8, 0x0c, 0xb8, 0x48, 0x1d, 0xd1,
0x7b, 0x54, 0x84, 0x77, 0xed, 0x61, 0x3f, 0x77, 0xb8, 0x28, 0x3a, 0xff, 0x29, 0xb6, 0x7b, 0x49,
0x14, 0x79, 0x23, 0xd8, 0x3d, 0x57, 0xd6, 0x3c, 0x9f, 0xb5, 0xb0, 0x8f, 0x3c, 0x58, 0xc7, 0x67,
0x2a, 0x88, 0x9d, 0xe7, 0x61, 0x14, 0x3f, 0x0f, 0x53, 0x6b, 0xf9, 0x7b, 0x97, 0x2f, 0x7f, 0xe5,
0x76, 0x81, 0x28, 0x95, 0x51, 0x6d, 0x56, 0x19, 0x11, 0x54, 0x6c, 0x66, 0x03, 0xfb, 0x8f, 0xd4,
0x16, 0x2b, 0xcc, 0xa0, 0xb8, 0x6f, 0x43, 0x23, 0x92, 0x7c, 0x9c, 0xfb, 0xd3, 0xb1, 0xfc, 0x71,
0x0c, 0x0e, 0x14, 0x99, 0xff, 0x79, 0x4d, 0xb5, 0x9f, 0x89, 0x8b, 0x6e, 0xbf, 0x3b, 0xb0, 0x8c,
0x9a, 0x8a, 0xc3, 0xc0, 0xa3, 0xc3, 0xc5, 0x45, 0xb2, 0x2d, 0x58, 0x2d, 0x10, 0xf6, 0x35, 0x52,
0x46, 0x17, 0xf5, 0x50, 0x9b, 0x7d, 0x32, 0xd5, 0x9d, 0xa8, 0xf9, 0xb0, 0x94, 0x66, 0xbc, 0x50,
0xde, 0x20, 0xe5, 0x0e, 0xce, 0x8d, 0x6c, 0xb3, 0x74, 0x56, 0x69, 0x09, 0xe8, 0x0c, 0x27, 0x82,
0x96, 0x91, 0x60, 0x70, 0x28, 0x41, 0x18, 0x82, 0x05, 0x25, 0xc1, 0x20, 0x30, 0xf6, 0xf2, 0x7c,
0x3f, 0x99, 0xc4, 0x52, 0x74, 0xda, 0x34, 0x08, 0x0c, 0xac, 0xde, 0x02, 0x2e, 0x26, 0x23, 0xd9,
0x01, 0x62, 0x34, 0x30, 0x0e, 0x6c, 0x79, 0x8e, 0x12, 0x44, 0x67, 0x91, 0x8e, 0xe0, 0x1c, 0xa4,
0xab, 0x0c, 0xc3, 0x7c, 0x9c, 0xb3, 0x2e, 0xa9, 0x98, 0x3a, 0x48, 0xb4, 0x5c, 0x23, 0x94, 0x90,
0x65, 0x12, 0xe2, 0xe0, 0xfc, 0xa7, 0xd6, 0x2d, 0xbd, 0x9f, 0x8c, 0xc7, 0x91, 0xdc, 0xa3, 0x4b,
0x1f, 0x07, 0x85, 0x35, 0x35, 0xdd, 0x7a, 0x2e, 0xa5, 0xd8, 0x34, 0x9a, 0x84, 0xeb, 0xe6, 0xf9,
0x79, 0x14, 0xf3, 0xec, 0xea, 0xb2, 0xb0, 0x20, 0x22, 0x71, 0xc4, 0x47, 0x27, 0xe6, 0x92, 0xa5,
0x82, 0x58, 0x08, 0xca, 0x68, 0xff, 0x9b, 0xba, 0x75, 0x57, 0x6b, 0x8d, 0xf7, 0x71, 0xcc, 0xa1,
0x37, 0x5a, 0xe3, 0xad, 0xb2, 0x46, 0xdb, 0xd7, 0x7e, 0x25, 0xd0, 0xd4, 0x6c, 0x17, 0x1a, 0x63,
0x34, 0x5c, 0xcf, 0xba, 0xdf, 0x94, 0xd9, 0x2c, 0xaf, 0xfa, 0x95, 0x40, 0xd1, 0xb2, 0x7f, 0xc0,
0x72, 0x28, 0x04, 0x97, 0xc7, 0xf8, 0x47, 0xe9, 0x84, 0x67, 0x7a, 0xea, 0x6d, 0x68, 0xe6, 0x3d,
0x7c, 0x13, 0xf9, 0x63, 0xbf, 0x12, 0xb8, 0xd4, 0x86, 0xfd, 0x7f, 0x91, 0x3c, 0x1b, 0x66, 0xe1,
0x1b, 0x7d, 0xc8, 0xb9, 0xec, 0xf9, 0xa3, 0x61, 0xcf, 0x11, 0x6c, 0x17, 0x16, 0x64, 0xae, 0xb8,
0x39, 0x5f, 0xb1, 0x21, 0x44, 0xa6, 0x37, 0xb9, 0xba, 0xd6, 0x7c, 0x75, 0x86, 0x90, 0x3d, 0x86,
0x95, 0x5c, 0xc0, 0x71, 0xf2, 0xf8, 0x9c, 0x0f, 0xa8, 0xd4, 0x8b, 0x28, 0xb9, 0xfa, 0x14, 0x49,
0xbf, 0x12, 0x94, 0x98, 0xd8, 0x03, 0x80, 0xd8, 0xdc, 0x95, 0xd4, 0x10, 0xf3, 0x2e, 0xc7, 0x7e,
0x25, 0xb0, 0xc8, 0xd9, 0x13, 0x58, 0x8d, 0xdd, 0x35, 0x45, 0x6d, 0x33, 0x77, 0x91, 0xf5, 0x2b,
0x41, 0x99, 0x09, 0x8f, 0x14, 0x79, 0x41, 0x15, 0xd5, 0x08, 0xaa, 0xf2, 0xe2, 0x61, 0x4b, 0x9f,
0x77, 0xb8, 0x53, 0x37, 0xad, 0x9d, 0x6a, 0x15, 0xcb, 0x65, 0xfb, 0x54, 0x97, 0x76, 0xf5, 0xad,
0x4b, 0xfb, 0x9e, 0xb3, 0x4f, 0xa7, 0x4a, 0xd3, 0xfe, 0x4b, 0xab, 0x37, 0xea, 0xfd, 0xf2, 0x46,
0x9d, 0xcf, 0x64, 0x76, 0xea, 0x53, 0xe7, 0x9a, 0x2f, 0x2a, 0xf8, 0x4a, 0xdd, 0xfd, 0x61, 0x15,
0x37, 0xb4, 0x2b, 0x8d, 0x0e, 0x5d, 0xf7, 0x64, 0xf5, 0xa6, 0x4e, 0xd6, 0x1e, 0x2c, 0x12, 0xa4,
0xc2, 0xa8, 0x83, 0x6e, 0xa3, 0xd8, 0x1f, 0x60, 0x05, 0xcf, 0xd4, 0xa3, 0x70, 0xcc, 0x35, 0x91,
0xda, 0xe0, 0x25, 0x6c, 0x31, 0xfb, 0xeb, 0xb3, 0x67, 0x7f, 0xa3, 0xbc, 0x31, 0x8b, 0xa9, 0xdc,
0x9c, 0x37, 0x95, 0x5b, 0x73, 0xa6, 0xf2, 0x82, 0x3b, 0x95, 0xfd, 0x77, 0xa7, 0xeb, 0x43, 0xff,
0xb5, 0xf8, 0x99, 0xea, 0xc3, 0xff, 0x3d, 0x2c, 0x9a, 0xe7, 0xe3, 0x73, 0x74, 0x4f, 0xcd, 0x7d,
0x2d, 0x58, 0x43, 0xfe, 0x01, 0xde, 0x22, 0xc5, 0xc1, 0x74, 0x8c, 0xb1, 0x28, 0xef, 0xc8, 0xb7,
0xf9, 0xac, 0xe0, 0x7f, 0x50, 0x85, 0x75, 0xe7, 0xaa, 0xf9, 0x75, 0x65, 0xb5, 0x7d, 0xd5, 0xac,
0xb6, 0xad, 0xac, 0x1e, 0xc0, 0x35, 0x27, 0x04, 0x14, 0x4d, 0x6c, 0xd5, 0x26, 0x59, 0x53, 0xbe,
0x82, 0xa6, 0xc2, 0x15, 0x68, 0x3a, 0xd5, 0x72, 0xe5, 0xac, 0xa0, 0x65, 0xb3, 0x73, 0x32, 0x75,
0xd5, 0x39, 0x9f, 0x74, 0x3e, 0xab, 0xc2, 0x4a, 0xb1, 0xda, 0x70, 0xbc, 0x62, 0x91, 0xe1, 0xfd,
0x9f, 0x17, 0x19, 0xfe, 0xa6, 0x61, 0x96, 0xe4, 0x5f, 0x49, 0x64, 0x82, 0xa9, 0x8b, 0xcc, 0x08,
0xa7, 0xa0, 0x2f, 0x04, 0x16, 0xc6, 0xaa, 0xa8, 0x3a, 0x69, 0xd4, 0x10, 0xe2, 0xc3, 0x31, 0xc6,
0x2a, 0x0f, 0xb9, 0x82, 0x50, 0x27, 0xc7, 0x71, 0xaf, 0xa2, 0x4d, 0xbf, 0xe9, 0xd8, 0xbe, 0x18,
0xbf, 0x4c, 0x46, 0xfa, 0x5f, 0x89, 0x86, 0xac, 0xb4, 0x81, 0x93, 0x36, 0xfa, 0x44, 0x84, 0xe9,
0xc6, 0x68, 0xe9, 0x0b, 0x6f, 0x83, 0x28, 0xa6, 0xf0, 0x68, 0x7f, 0x1a, 0x66, 0xa1, 0xa6, 0xda,
0x54, 0xc7, 0x6c, 0x81, 0xc1, 0xc3, 0x48, 0x4c, 0x06, 0x03, 0x2e, 0x44, 0xe7, 0x06, 0x39, 0x97,
0x83, 0x3b, 0x5f, 0x56, 0xa1, 0x6d, 0xbe, 0x63, 0xb2, 0x7f, 0xc2, 0xc2, 0x01, 0x97, 0x94, 0x02,
0xb6, 0x66, 0x32, 0xf7, 0xea, 0x48, 0x66, 0x51, 0x7c, 0xda, 0xfd, 0xdd, 0xf4, 0x4d, 0xe0, 0x7c,
0x33, 0xf3, 0x2b, 0xec, 0xef, 0x00, 0xcf, 0x22, 0x21, 0x75, 0x31, 0x2c, 0x17, 0x22, 0x5e, 0x44,
0xa3, 0x6e, 0x77, 0x56, 0x2d, 0x28, 0x52, 0xbf, 0xc2, 0x9e, 0xc1, 0x4a, 0xae, 0x3b, 0xf7, 0xaa,
0x60, 0x9f, 0xd5, 0xb4, 0xdd, 0x4b, 0x6b, 0xcb, 0xaf, 0xb0, 0x07, 0xb0, 0x76, 0xc0, 0x25, 0x55,
0x80, 0x39, 0xef, 0x56, 0x0a, 0x79, 0x98, 0xbd, 0xee, 0x46, 0xd9, 0x1f, 0x22, 0xf7, 0x2b, 0xec,
0x4f, 0xd0, 0x3c, 0x14, 0x47, 0x17, 0xf1, 0xa0, 0xec, 0xc1, 0xba, 0x06, 0x0f, 0xc5, 0x7e, 0x38,
0x39, 0x3d, 0x93, 0xff, 0x49, 0xfd, 0xca, 0xcb, 0x26, 0x7d, 0xb3, 0xdd, 0xfd, 0x21, 0x00, 0x00,
0xff, 0xff, 0x3c, 0x99, 0x53, 0x18, 0x10, 0x16, 0x00, 0x00,
}
// Reference imports to suppress errors if they are not otherwise used.
......
......@@ -26,7 +26,7 @@ func init() {
types.RegistorExecutor(ParaX, NewType())
types.RegisterDappFork(ParaX, "Enable", 0)
types.RegisterDappFork(ParaX, "ForkParacrossWithdrawFromParachain", 1298600)
types.RegisterDappFork(ParaX, ForkCommitTx, types.MaxHeight)
types.RegisterDappFork(ParaX, ForkCommitTx, 1850000)
}
// GetExecName get para exec name
......
......@@ -202,6 +202,7 @@ ForkStateDBSet=-1 #fork 6.2
ForkLocalDBAccess=-1 #fork 6.2
ForkBlockCheck=-1 #fork 6.2
ForkBase58AddressCheck=-1 #fork6.2
ForkEnableParaRegExec=0
[fork.sub.coins]
Enable=0
[fork.sub.ticket]
......
......@@ -108,11 +108,11 @@ func (t *token) getAccountTokenAssets(req *tokenty.ReqAccountTokenAssets) (types
return nil, err
}
var acc1 *types.Account
if req.Execer != "" {
execaddress := address.ExecAddress(req.Execer)
acc1 = acc.LoadExecAccount(req.Address, execaddress)
} else if req.Execer == t.GetName() {
if req.Execer == t.GetName() {
acc1 = acc.LoadAccount(req.Address)
} else if req.Execer != "" {
execAddress := address.ExecAddress(req.Execer)
acc1 = acc.LoadExecAccount(req.Address, execAddress)
}
if acc1 == nil {
continue
......
......@@ -152,6 +152,9 @@ func TestToken(t *testing.T) {
set, err := exec.ExecLocal(createTx, receiptDate, int(1))
assert.Nil(t, err)
assert.NotNil(t, set)
for _, kv := range set.KV {
kvdb.Set(kv.Key, kv.Value)
}
p2 := &pty.TokenFinishCreate{
Symbol: Symbol,
......@@ -176,13 +179,16 @@ func TestToken(t *testing.T) {
stateDB.Set(kv.Key, kv.Value)
}
accDB, _ := account.NewAccountDB(pty.TokenX, Symbol, stateDB)
accChcek := accDB.LoadAccount(string(Nodes[0]))
assert.Equal(t, tokenTotal, accChcek.Balance)
accCheck := accDB.LoadAccount(string(Nodes[0]))
assert.Equal(t, tokenTotal, accCheck.Balance)
receiptDate = &types.ReceiptData{Ty: receipt.Ty, Logs: receipt.Logs}
set, err = exec.ExecLocal(createTx2, receiptDate, int(1))
assert.Nil(t, err)
assert.NotNil(t, set)
for _, kv := range set.KV {
kvdb.Set(kv.Key, kv.Value)
}
// mint burn
p3 := &pty.TokenMint{
......@@ -208,13 +214,16 @@ func TestToken(t *testing.T) {
stateDB.Set(kv.Key, kv.Value)
}
accChcek = accDB.LoadAccount(string(Nodes[0]))
assert.Equal(t, tokenTotal+tokenMint, accChcek.Balance)
accCheck = accDB.LoadAccount(string(Nodes[0]))
assert.Equal(t, tokenTotal+tokenMint, accCheck.Balance)
receiptDate = &types.ReceiptData{Ty: receipt.Ty, Logs: receipt.Logs}
set, err = exec.ExecLocal(createTx3, receiptDate, int(1))
assert.Nil(t, err)
assert.NotNil(t, set)
for _, kv := range set.KV {
kvdb.Set(kv.Key, kv.Value)
}
p4 := &pty.TokenBurn{
Symbol: Symbol,
......@@ -238,13 +247,31 @@ func TestToken(t *testing.T) {
for _, kv := range receipt.KV {
stateDB.Set(kv.Key, kv.Value)
}
accChcek = accDB.LoadAccount(string(Nodes[0]))
assert.Equal(t, tokenTotal+tokenMint-tokenBurn, accChcek.Balance)
accCheck = accDB.LoadAccount(string(Nodes[0]))
assert.Equal(t, tokenTotal+tokenMint-tokenBurn, accCheck.Balance)
receiptDate = &types.ReceiptData{Ty: receipt.Ty, Logs: receipt.Logs}
set, err = exec.ExecLocal(createTx4, receiptDate, int(1))
assert.Nil(t, err)
assert.NotNil(t, set)
for _, kv := range set.KV {
kvdb.Set(kv.Key, kv.Value)
}
tokenExec, ok := exec.(*token)
assert.True(t, ok)
in := pty.ReqAccountTokenAssets{
Address: string(Nodes[0]),
Execer: pty.TokenX,
}
out, err := tokenExec.Query_GetAccountTokenAssets(&in)
assert.Nil(t, err)
reply := out.(*pty.ReplyAccountTokenAssets)
assert.Equal(t, 1, len(reply.TokenAssets))
assert.NotEqual(t, 0, reply.TokenAssets[0].Account.Balance)
assert.Equal(t, string(Nodes[0]), reply.TokenAssets[0].Account.Addr)
t.Log(reply.TokenAssets)
}
func signTx(tx *types.Transaction, hexPrivKey string) (*types.Transaction, error) {
......
......@@ -61,7 +61,7 @@ func DisableLog() {
func init() {
drivers.Reg("kvmvccmavl", New)
types.RegisterDappFork("store-kvmvccmavl", "ForkKvmvccmavl", types.MaxHeight)
types.RegisterDappFork("store-kvmvccmavl", "ForkKvmvccmavl", 186*10000)
}
// KVmMavlStore provide kvmvcc and mavl store interface implementation
......
......@@ -129,12 +129,8 @@ func (m *mockBlockChain) SetQueueClient(q queue.Queue) {
msg.ReplyErr("Do not support", types.ErrInvalidParam)
}
case types.EventLocalList:
if req, ok := msg.GetData().(*types.LocalDBList); ok {
if len(req.Key) > 0 && bytes.Equal(req.Key, []byte("Statistics:TicketInfoOrder:Addr:case1")) {
msg.Reply(client.NewMessage(blockchainKey, types.EventReplyQuery, &types.TicketMinerInfo{}))
} else {
if _, ok := msg.GetData().(*types.LocalDBList); ok {
msg.Reply(client.NewMessage(blockchainKey, types.EventReplyQuery, &types.LocalReplyValue{}))
}
} else {
msg.ReplyErr("Do not support", types.ErrInvalidParam)
}
......
......@@ -76,17 +76,15 @@ func (j *JSONRPCServer) Listen() (int, error) {
}
//格式做一个检查
client, err := parseJSONRpcParams(data)
errstr := "nil"
if err != nil {
errstr = err.Error()
err = fmt.Errorf(`invalid json request err:%s`, err.Error())
log.Debug("JSONRPCServer", "request", string(data), "parseErr", err)
writeError(w, r, 0, err.Error())
return
}
funcName := strings.Split(client.Method, ".")[len(strings.Split(client.Method, "."))-1]
if !checkFilterPrintFuncBlacklist(funcName) {
log.Debug("JSONRPCServer", "request", string(data), "err", errstr)
}
if err != nil {
writeError(w, r, 0, fmt.Sprintf(`parse request err %s`, err.Error()))
return
log.Debug("JSONRPCServer", "request", string(data))
}
//Release local request
ipaddr := net.ParseIP(ip)
......
......@@ -215,7 +215,7 @@ func createTxGroup(cmd *cobra.Command, args []string) {
fmt.Fprintln(os.Stderr, err)
return
}
err = group.Check(0, types.GInt("MinFee"), types.GInt("MaxFee"))
err = group.CheckWithFork(true, true, 0, types.GInt("MinFee"), types.GInt("MaxFee"))
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
......
......@@ -9,15 +9,9 @@ import (
"fmt"
"os"
"strconv"
"time"
"github.com/33cn/chain33/common/address"
"github.com/33cn/chain33/rpc/jsonclient"
"math/big"
"github.com/33cn/chain33/common"
"github.com/33cn/chain33/common/difficulty"
"github.com/33cn/chain33/rpc/jsonclient"
rpctypes "github.com/33cn/chain33/rpc/types"
commandtypes "github.com/33cn/chain33/system/dapp/commands/types"
"github.com/33cn/chain33/types"
......@@ -34,10 +28,6 @@ func StatCmd() *cobra.Command {
cmd.AddCommand(
GetTotalCoinsCmd(),
GetTicketStatCmd(),
GetTicketInfoCmd(),
GetTicketInfoListCmd(),
GetMinerStatCmd(),
GetExecBalanceCmd(),
)
......@@ -213,437 +203,6 @@ func totalCoins(cmd *cobra.Command, args []string) {
fmt.Println(string(data))
}
// GetTicketStatCmd get ticket stat
func GetTicketStatCmd() *cobra.Command {
cmd := &cobra.Command{
Use: "ticket_stat",
Short: "Get ticket statistics by addr",
Run: ticketStat,
}
addTicketStatCmdFlags(cmd)
return cmd
}
func addTicketStatCmdFlags(cmd *cobra.Command) {
cmd.Flags().StringP("addr", "a", "", "addr")
cmd.MarkFlagRequired("addr")
}
func ticketStat(cmd *cobra.Command, args []string) {
rpcAddr, _ := cmd.Flags().GetString("rpc_laddr")
addr, _ := cmd.Flags().GetString("addr")
rpc, err := jsonclient.NewJSONClient(rpcAddr)
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
key := []byte("Statistics:TicketStat:Addr:" + addr)
fmt.Println(string(key))
params := types.LocalDBGet{Keys: [][]byte{key}}
var res types.TicketStatistic
err = rpc.Call("Chain33.QueryTicketStat", params, &res)
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
var resp commandtypes.GetTicketStatisticResult
resp.CurrentOpenCount = res.CurrentOpenCount
resp.TotalMinerCount = res.TotalMinerCount
resp.TotalCloseCount = res.TotalCancleCount
data, err := json.MarshalIndent(resp, "", " ")
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
fmt.Println(string(data))
}
// GetTicketInfoCmd get a ticket information
func GetTicketInfoCmd() *cobra.Command {
cmd := &cobra.Command{
Use: "ticket_info",
Short: "Get ticket info by ticket_id",
Run: ticketInfo,
}
addTicketInfoCmdFlags(cmd)
return cmd
}
func addTicketInfoCmdFlags(cmd *cobra.Command) {
cmd.Flags().StringP("ticket_id", "t", "", "ticket_id")
cmd.MarkFlagRequired("ticket_id")
}
func ticketInfo(cmd *cobra.Command, args []string) {
rpcAddr, _ := cmd.Flags().GetString("rpc_laddr")
ticketID, _ := cmd.Flags().GetString("ticket_id")
rpc, err := jsonclient.NewJSONClient(rpcAddr)
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
key := []byte("Statistics:TicketInfo:TicketId:" + ticketID)
fmt.Println(string(key))
params := types.LocalDBGet{Keys: [][]byte{key}}
var res types.TicketMinerInfo
err = rpc.Call("Chain33.QueryTicketInfo", params, &res)
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
var resp commandtypes.GetTicketMinerInfoResult
resp.TicketID = res.TicketId
switch res.Status {
case 1:
resp.Status = "openTicket"
case 2:
resp.Status = "minerTicket"
case 3:
resp.Status = "closeTicket"
}
switch res.PrevStatus {
case 1:
resp.PrevStatus = "openTicket"
case 2:
resp.PrevStatus = "minerTicket"
case 3:
resp.PrevStatus = "closeTicket"
}
resp.IsGenesis = res.IsGenesis
resp.CreateTime = time.Unix(res.CreateTime, 0).Format("20060102150405")
resp.MinerTime = time.Unix(res.MinerTime, 0).Format("20060102150405")
resp.CloseTime = time.Unix(res.CloseTime, 0).Format("20060102150405")
resp.MinerValue = res.MinerValue
resp.MinerAddress = res.MinerAddress
data, err := json.MarshalIndent(resp, "", " ")
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
fmt.Println(string(data))
}
// GetTicketInfoListCmd get ticket information list
func GetTicketInfoListCmd() *cobra.Command {
cmd := &cobra.Command{
Use: "ticket_info_list",
Short: "Get ticket info list by ticket_id",
Run: ticketInfoList,
}
addTicketInfoListCmdFlags(cmd)
return cmd
}
func addTicketInfoListCmdFlags(cmd *cobra.Command) {
cmd.Flags().StringP("addr", "a", "", "addr")
cmd.MarkFlagRequired("addr")
cmd.Flags().Int32P("count", "c", 10, "count")
//cmd.MarkFlagRequired("count")
cmd.Flags().Int32P("direction", "d", 1, "query direction (0: pre page, 1: next page)")
cmd.Flags().StringP("create_time", "r", "", "create_time")
cmd.Flags().StringP("ticket_id", "t", "", "ticket_id")
}
func ticketInfoList(cmd *cobra.Command, args []string) {
rpcAddr, _ := cmd.Flags().GetString("rpc_laddr")
addr, _ := cmd.Flags().GetString("addr")
count, _ := cmd.Flags().GetInt32("count")
direction, _ := cmd.Flags().GetInt32("direction")
createTime, _ := cmd.Flags().GetString("create_time")
ticketID, _ := cmd.Flags().GetString("ticket_id")
if count <= 0 {
fmt.Fprintln(os.Stderr, fmt.Errorf("input err, count:%v", count))
return
}
rpc, err := jsonclient.NewJSONClient(rpcAddr)
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
var key []byte
prefix := []byte("Statistics:TicketInfoOrder:Addr:" + addr)
if ticketID != "" && createTime != "" {
key = []byte("Statistics:TicketInfoOrder:Addr:" + addr + ":CreateTime:" + createTime + ":TicketId:" + ticketID)
}
fmt.Println(string(prefix))
fmt.Println(string(key))
params := types.LocalDBList{Prefix: prefix, Key: key, Direction: direction, Count: count}
var res []types.TicketMinerInfo
err = rpc.Call("Chain33.QueryTicketInfoList", params, &res)
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
var resp []commandtypes.GetTicketMinerInfoResult
for _, v := range res {
var ticket commandtypes.GetTicketMinerInfoResult
ticket.TicketID = v.TicketId
switch v.Status {
case 1:
ticket.Status = "openTicket"
case 2:
ticket.Status = "minerTicket"
case 3:
ticket.Status = "closeTicket"
}
switch v.PrevStatus {
case 1:
ticket.PrevStatus = "openTicket"
case 2:
ticket.PrevStatus = "minerTicket"
case 3:
ticket.PrevStatus = "closeTicket"
}
ticket.IsGenesis = v.IsGenesis
ticket.CreateTime = time.Unix(v.CreateTime, 0).Format("20060102150405")
if v.MinerTime != 0 {
ticket.MinerTime = time.Unix(v.MinerTime, 0).Format("20060102150405")
}
if v.CloseTime != 0 {
ticket.CloseTime = time.Unix(v.CloseTime, 0).Format("20060102150405")
}
ticket.MinerValue = v.MinerValue
ticket.MinerAddress = v.MinerAddress
resp = append(resp, ticket)
}
data, err := json.MarshalIndent(resp, "", " ")
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
fmt.Println(string(data))
}
// GetMinerStatCmd get miner stat
func GetMinerStatCmd() *cobra.Command {
cmd := &cobra.Command{
Use: "miner",
Short: "Get miner statistic",
Run: minerStat,
}
addMinerStatCmdFlags(cmd)
return cmd
}
func addMinerStatCmdFlags(cmd *cobra.Command) {
cmd.Flags().StringP("addr", "a", "", "addr")
cmd.MarkFlagRequired("addr")
cmd.Flags().Int64P("height", "t", 0, "start block height")
cmd.MarkFlagRequired("height")
}
func minerStat(cmd *cobra.Command, args []string) {
rpcAddr, _ := cmd.Flags().GetString("rpc_laddr")
addr, _ := cmd.Flags().GetString("addr")
height, _ := cmd.Flags().GetInt64("height")
if err := address.CheckAddress(addr); err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
if height <= 0 {
fmt.Fprintln(os.Stderr, fmt.Errorf("input err, height:%v", height))
return
}
rpc, err := jsonclient.NewJSONClient(rpcAddr)
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
// 获取最新高度
var lastheader rpctypes.Header
err = rpc.Call("Chain33.GetLastHeader", nil, &lastheader)
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
// 循环取难度区间
var diffList []difficultyRange
var diff difficultyRange
startH := height
diffListLoop:
for {
endH := startH + 10
if endH > lastheader.Height {
endH = lastheader.Height
}
params := types.ReqBlocks{
Start: startH,
End: endH,
IsDetail: false,
}
var respHeaders rpctypes.Headers
err = rpc.Call("Chain33.GetHeaders", params, &respHeaders)
if err != nil {
fmt.Fprintln(os.Stderr, err)
return
}
for _, h := range respHeaders.Items {
if diff.bits != h.Difficulty {
diff.timestamp = h.BlockTime
diff.height = h.Height
diff.bits = h.Difficulty
diff.diff = difficulty.CompactToBig(diff.bits)
diffList = append(diffList, diff)
}
}
if len(respHeaders.Items) < 10 || endH+1 > lastheader.Height {
// 最后一个点,记录截止时间
diff.timestamp = respHeaders.Items[len(respHeaders.Items)-1].BlockTime
diffList = append(diffList, diff)
break diffListLoop
}
startH = endH + 1
}
// 统计挖矿概率
bigOne := big.NewInt(1)
oneLsh256 := new(big.Int).Lsh(bigOne, 256)
oneLsh256.Sub(oneLsh256, bigOne)
resp := new(MinerResult)
resp.Expect = new(big.Float).SetInt64(0)
var key []byte
prefix := []byte("Statistics:TicketInfoOrder:Addr:" + addr)
for {
params := types.LocalDBList{Prefix: prefix, Key: key, Direction: 1, Count: 10}
var res []types.TicketMinerInfo
err = rpc.Call("Chain33.QueryTicketInfoList", params, &res)
if err != nil {
fmt.Fprintln(os.Stderr, fmt.Errorf("QueryTicketInfoList failed:%v", err))
fmt.Fprintln(os.Stderr, err)
return
}
for _, v := range res {
if v.CreateTime < diffList[0].timestamp-types.GetP(diffList[0].height).TicketFrozenTime {
continue
}
//找到开始挖矿的难度坐标
var pos int
for i := range diffList {
//创建时间+冻结时间<右节点
if v.CreateTime >= diffList[i].timestamp-types.GetP(diffList[i].height).TicketFrozenTime {
continue
} else {
pos = i - 1
break
}
}
diffList2 := diffList[pos:]
//没有挖到,还在挖
if v.CloseTime == 0 && v.MinerTime == 0 {
for i := range diffList2 {
if i == 0 {
continue
}
probability := new(big.Float).Quo(new(big.Float).SetInt(diffList2[i-1].diff), new(big.Float).SetInt(oneLsh256))
if i == 1 {
resp.Expect = resp.Expect.Add(resp.Expect, probability.Mul(probability, new(big.Float).SetInt64(diffList2[i].timestamp-v.CreateTime-types.GetP(diffList2[i-1].height).TicketFrozenTime)))
} else {
resp.Expect = resp.Expect.Add(resp.Expect, probability.Mul(probability, new(big.Float).SetInt64(diffList2[i].timestamp-diffList2[i-1].timestamp)))
}
}
}
//没有挖到,主动关闭
if v.MinerTime == 0 && v.CloseTime != 0 {
for i := range diffList2 {
if i == 0 {
continue
}
probability := new(big.Float).Quo(new(big.Float).SetInt(diffList2[i-1].diff), new(big.Float).SetInt(oneLsh256))
if i == 1 {
resp.Expect = resp.Expect.Add(resp.Expect, probability.Mul(probability, new(big.Float).SetInt64(diffList2[i].timestamp-v.CreateTime-types.GetP(diffList2[i-1].height).TicketFrozenTime)))
} else {
if v.CloseTime <= diffList2[i].timestamp {
resp.Expect = resp.Expect.Add(resp.Expect, probability.Mul(probability, new(big.Float).SetInt64(v.CloseTime-diffList2[i-1].timestamp)))
break
} else {
resp.Expect = resp.Expect.Add(resp.Expect, probability.Mul(probability, new(big.Float).SetInt64(diffList2[i].timestamp-diffList2[i-1].timestamp)))
}
}
}
}
//挖到
if v.MinerTime != 0 {
for i := range diffList2 {
if i == 0 {
continue
}
probability := new(big.Float).Quo(new(big.Float).SetInt(diffList2[i-1].diff), new(big.Float).SetInt(oneLsh256))
if i == 1 {
resp.Expect = resp.Expect.Add(resp.Expect, probability.Mul(probability, new(big.Float).SetInt64(diffList2[i].timestamp-v.CreateTime-types.GetP(diffList2[i-1].height).TicketFrozenTime)))
} else {
if v.MinerTime <= diffList2[i].timestamp {
resp.Expect = resp.Expect.Add(resp.Expect, probability.Mul(probability, new(big.Float).SetInt64(v.MinerTime-diffList2[i-1].timestamp)))
break
} else {
resp.Expect = resp.Expect.Add(resp.Expect, probability.Mul(probability, new(big.Float).SetInt64(diffList2[i].timestamp-diffList2[i-1].timestamp)))
}
}
}
resp.Actual++
}
}
if len(res) < 10 {
break
}
key = []byte("Statistics:TicketInfoOrder:Addr:" + addr + ":CreateTime:" + time.Unix(res[len(res)-1].CreateTime, 0).Format("20060102150405") + ":TicketId:" + res[len(res)-1].TicketId)
}
expect := resp.Expect.Text('f', 2)
fmt.Println("Expect:", expect)
fmt.Println("Actual:", resp.Actual)
e, _ := strconv.ParseFloat(expect, 64)
fmt.Printf("Deviation:%+.3f%%\n", (float64(resp.Actual)/e-1.0)*100.0)
}
type difficultyRange struct {
timestamp int64
height int64
bits uint32
diff *big.Int
}
// MinerResult defiles miner command
type MinerResult struct {
Expect *big.Float
Actual int64
}
// GetExecBalanceCmd get exec-addr balance of specific addr
func GetExecBalanceCmd() *cobra.Command {
cmd := &cobra.Command{
......
......@@ -148,26 +148,6 @@ type GetTotalCoinsResult struct {
DifferenceAmount string `json:"differenceAmount,omitempty"`
}
// GetTicketStatisticResult defines ticketstatistic result rpc command
type GetTicketStatisticResult struct {
CurrentOpenCount int64 `json:"currentOpenCount"`
TotalMinerCount int64 `json:"totalMinerCount"`
TotalCloseCount int64 `json:"totalCloseCount"`
}
// GetTicketMinerInfoResult defines ticker minerinformation result rpc command
type GetTicketMinerInfoResult struct {
TicketID string `json:"ticketId"`
Status string `json:"status"`
PrevStatus string `json:"prevStatus"`
IsGenesis bool `json:"isGenesis"`
CreateTime string `json:"createTime"`
MinerTime string `json:"minerTime"`
CloseTime string `json:"closeTime"`
MinerValue int64 `json:"minerValue,omitempty"`
MinerAddress string `json:"minerAddress,omitempty"`
}
// UTXOGlobalIndex defines utxo globalindex command
type UTXOGlobalIndex struct {
// Height int64 `json:"height,omitempty"`
......
......@@ -35,20 +35,28 @@ func Register(name string, create DriverCreate, height int64) {
if _, dup := registedExecDriver[name]; dup {
panic("Execute: Register called twice for driver " + name)
}
driverWithHeight := &driverWithHeight{
driverHeight := &driverWithHeight{
create: create,
height: height,
}
registedExecDriver[name] = driverWithHeight
registedExecDriver[name] = driverHeight
//考虑到前期平行链兼容性和防止误操作(平行链下转账到一个主链合约),也会注册主链合约(不带前缀)的地址
registerAddress(name)
execDrivers[ExecAddress(name)] = driverHeight
if types.IsPara() {
paraHeight := types.GetFork("ForkEnableParaRegExec")
if paraHeight < height {
paraHeight = height
}
//平行链的合约地址是通过user.p.x.name计算的
paraDriverName := types.ExecName(name)
registerAddress(paraDriverName)
execDrivers[ExecAddress(paraDriverName)] = driverWithHeight
execDrivers[ExecAddress(paraDriverName)] = &driverWithHeight{
create: create,
height: paraHeight,
}
}
//考虑到前期平行链兼容性和防止误操作(平行链下转账到一个主链合约),也会注册主链合约(不带前缀)的地址
registerAddress(name)
execDrivers[ExecAddress(name)] = driverWithHeight
}
// LoadDriver load driver
......
......@@ -214,6 +214,8 @@ func SetTestNetFork() {
systemFork.SetFork("chain33", "ForkLocalDBAccess", 1572391)
systemFork.SetFork("chain33", "ForkTxGroupPara", 1687250)
systemFork.SetFork("chain33", "ForkBase58AddressCheck", 1800000)
//这个fork只影响平行链,注册类似user.p.x.exec的driver,新开的平行链设为0即可,老的平行链要设置新的高度
systemFork.SetFork("chain33", "ForkEnableParaRegExec", 0)
}
......
......@@ -34,33 +34,6 @@ message IterateRangeByStateHash {
int64 count = 4;
}
message TicketStatistic {
//当前在挖的ticket
int64 currentOpenCount = 1;
//一共挖到的ticket
int64 totalMinerCount = 2;
//一共取消的ticket
int64 totalCancleCount = 3;
}
message TicketMinerInfo {
string ticketId = 1;
// 1 -> 可挖矿 2 -> 已挖成功 3-> 已关闭
int32 status = 2;
int32 prevStatus = 3;
// genesis 创建的私钥比较特殊
bool isGenesis = 4;
//创建ticket时间
int64 createTime = 5;
// ticket挖矿时间
int64 minerTime = 6;
//关闭ticket时间
int64 closeTime = 7;
//挖到的币的数目
int64 minerValue = 8;
string minerAddress = 9;
}
message TotalAmount {
// 统计的总数
int64 total = 1;
......
......@@ -269,173 +269,6 @@ func (m *IterateRangeByStateHash) GetCount() int64 {
return 0
}
type TicketStatistic struct {
//当前在挖的ticket
CurrentOpenCount int64 `protobuf:"varint,1,opt,name=currentOpenCount,proto3" json:"currentOpenCount,omitempty"`
//一共挖到的ticket
TotalMinerCount int64 `protobuf:"varint,2,opt,name=totalMinerCount,proto3" json:"totalMinerCount,omitempty"`
//一共取消的ticket
TotalCancleCount int64 `protobuf:"varint,3,opt,name=totalCancleCount,proto3" json:"totalCancleCount,omitempty"`
XXX_NoUnkeyedLiteral struct{} `json:"-"`
XXX_unrecognized []byte `json:"-"`
XXX_sizecache int32 `json:"-"`
}
func (m *TicketStatistic) Reset() { *m = TicketStatistic{} }
func (m *TicketStatistic) String() string { return proto.CompactTextString(m) }
func (*TicketStatistic) ProtoMessage() {}
func (*TicketStatistic) Descriptor() ([]byte, []int) {
return fileDescriptor_405f6cee9ed2da7e, []int{4}
}
func (m *TicketStatistic) XXX_Unmarshal(b []byte) error {
return xxx_messageInfo_TicketStatistic.Unmarshal(m, b)
}
func (m *TicketStatistic) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
return xxx_messageInfo_TicketStatistic.Marshal(b, m, deterministic)
}
func (m *TicketStatistic) XXX_Merge(src proto.Message) {
xxx_messageInfo_TicketStatistic.Merge(m, src)
}
func (m *TicketStatistic) XXX_Size() int {
return xxx_messageInfo_TicketStatistic.Size(m)
}
func (m *TicketStatistic) XXX_DiscardUnknown() {
xxx_messageInfo_TicketStatistic.DiscardUnknown(m)
}
var xxx_messageInfo_TicketStatistic proto.InternalMessageInfo
func (m *TicketStatistic) GetCurrentOpenCount() int64 {
if m != nil {
return m.CurrentOpenCount
}
return 0
}
func (m *TicketStatistic) GetTotalMinerCount() int64 {
if m != nil {
return m.TotalMinerCount
}
return 0
}
func (m *TicketStatistic) GetTotalCancleCount() int64 {
if m != nil {
return m.TotalCancleCount
}
return 0
}
type TicketMinerInfo struct {
TicketId string `protobuf:"bytes,1,opt,name=ticketId,proto3" json:"ticketId,omitempty"`
// 1 -> 可挖矿 2 -> 已挖成功 3-> 已关闭
Status int32 `protobuf:"varint,2,opt,name=status,proto3" json:"status,omitempty"`
PrevStatus int32 `protobuf:"varint,3,opt,name=prevStatus,proto3" json:"prevStatus,omitempty"`
// genesis 创建的私钥比较特殊
IsGenesis bool `protobuf:"varint,4,opt,name=isGenesis,proto3" json:"isGenesis,omitempty"`
//创建ticket时间
CreateTime int64 `protobuf:"varint,5,opt,name=createTime,proto3" json:"createTime,omitempty"`
// ticket挖矿时间
MinerTime int64 `protobuf:"varint,6,opt,name=minerTime,proto3" json:"minerTime,omitempty"`
//关闭ticket时间
CloseTime int64 `protobuf:"varint,7,opt,name=closeTime,proto3" json:"closeTime,omitempty"`
//挖到的币的数目
MinerValue int64 `protobuf:"varint,8,opt,name=minerValue,proto3" json:"minerValue,omitempty"`
MinerAddress string `protobuf:"bytes,9,opt,name=minerAddress,proto3" json:"minerAddress,omitempty"`
XXX_NoUnkeyedLiteral struct{} `json:"-"`
XXX_unrecognized []byte `json:"-"`
XXX_sizecache int32 `json:"-"`
}
func (m *TicketMinerInfo) Reset() { *m = TicketMinerInfo{} }
func (m *TicketMinerInfo) String() string { return proto.CompactTextString(m) }
func (*TicketMinerInfo) ProtoMessage() {}
func (*TicketMinerInfo) Descriptor() ([]byte, []int) {
return fileDescriptor_405f6cee9ed2da7e, []int{5}
}
func (m *TicketMinerInfo) XXX_Unmarshal(b []byte) error {
return xxx_messageInfo_TicketMinerInfo.Unmarshal(m, b)
}
func (m *TicketMinerInfo) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
return xxx_messageInfo_TicketMinerInfo.Marshal(b, m, deterministic)
}
func (m *TicketMinerInfo) XXX_Merge(src proto.Message) {
xxx_messageInfo_TicketMinerInfo.Merge(m, src)
}
func (m *TicketMinerInfo) XXX_Size() int {
return xxx_messageInfo_TicketMinerInfo.Size(m)
}
func (m *TicketMinerInfo) XXX_DiscardUnknown() {
xxx_messageInfo_TicketMinerInfo.DiscardUnknown(m)
}
var xxx_messageInfo_TicketMinerInfo proto.InternalMessageInfo
func (m *TicketMinerInfo) GetTicketId() string {
if m != nil {
return m.TicketId
}
return ""
}
func (m *TicketMinerInfo) GetStatus() int32 {
if m != nil {
return m.Status
}
return 0
}
func (m *TicketMinerInfo) GetPrevStatus() int32 {
if m != nil {
return m.PrevStatus
}
return 0
}
func (m *TicketMinerInfo) GetIsGenesis() bool {
if m != nil {
return m.IsGenesis
}
return false
}
func (m *TicketMinerInfo) GetCreateTime() int64 {
if m != nil {
return m.CreateTime
}
return 0
}
func (m *TicketMinerInfo) GetMinerTime() int64 {
if m != nil {
return m.MinerTime
}
return 0
}
func (m *TicketMinerInfo) GetCloseTime() int64 {
if m != nil {
return m.CloseTime
}
return 0
}
func (m *TicketMinerInfo) GetMinerValue() int64 {
if m != nil {
return m.MinerValue
}
return 0
}
func (m *TicketMinerInfo) GetMinerAddress() string {
if m != nil {
return m.MinerAddress
}
return ""
}
type TotalAmount struct {
// 统计的总数
Total int64 `protobuf:"varint,1,opt,name=total,proto3" json:"total,omitempty"`
......@@ -448,7 +281,7 @@ func (m *TotalAmount) Reset() { *m = TotalAmount{} }
func (m *TotalAmount) String() string { return proto.CompactTextString(m) }
func (*TotalAmount) ProtoMessage() {}
func (*TotalAmount) Descriptor() ([]byte, []int) {
return fileDescriptor_405f6cee9ed2da7e, []int{6}
return fileDescriptor_405f6cee9ed2da7e, []int{4}
}
func (m *TotalAmount) XXX_Unmarshal(b []byte) error {
......@@ -494,7 +327,7 @@ func (m *ReqGetExecBalance) Reset() { *m = ReqGetExecBalance{} }
func (m *ReqGetExecBalance) String() string { return proto.CompactTextString(m) }
func (*ReqGetExecBalance) ProtoMessage() {}
func (*ReqGetExecBalance) Descriptor() ([]byte, []int) {
return fileDescriptor_405f6cee9ed2da7e, []int{7}
return fileDescriptor_405f6cee9ed2da7e, []int{5}
}
func (m *ReqGetExecBalance) XXX_Unmarshal(b []byte) error {
......@@ -577,7 +410,7 @@ func (m *ExecBalanceItem) Reset() { *m = ExecBalanceItem{} }
func (m *ExecBalanceItem) String() string { return proto.CompactTextString(m) }
func (*ExecBalanceItem) ProtoMessage() {}
func (*ExecBalanceItem) Descriptor() ([]byte, []int) {
return fileDescriptor_405f6cee9ed2da7e, []int{8}
return fileDescriptor_405f6cee9ed2da7e, []int{6}
}
func (m *ExecBalanceItem) XXX_Unmarshal(b []byte) error {
......@@ -635,7 +468,7 @@ func (m *ReplyGetExecBalance) Reset() { *m = ReplyGetExecBalance{} }
func (m *ReplyGetExecBalance) String() string { return proto.CompactTextString(m) }
func (*ReplyGetExecBalance) ProtoMessage() {}
func (*ReplyGetExecBalance) Descriptor() ([]byte, []int) {
return fileDescriptor_405f6cee9ed2da7e, []int{9}
return fileDescriptor_405f6cee9ed2da7e, []int{7}
}
func (m *ReplyGetExecBalance) XXX_Unmarshal(b []byte) error {
......@@ -696,8 +529,6 @@ func init() {
proto.RegisterType((*ReqGetTotalCoins)(nil), "types.ReqGetTotalCoins")
proto.RegisterType((*ReplyGetTotalCoins)(nil), "types.ReplyGetTotalCoins")
proto.RegisterType((*IterateRangeByStateHash)(nil), "types.IterateRangeByStateHash")
proto.RegisterType((*TicketStatistic)(nil), "types.TicketStatistic")
proto.RegisterType((*TicketMinerInfo)(nil), "types.TicketMinerInfo")
proto.RegisterType((*TotalAmount)(nil), "types.TotalAmount")
proto.RegisterType((*ReqGetExecBalance)(nil), "types.ReqGetExecBalance")
proto.RegisterType((*ExecBalanceItem)(nil), "types.ExecBalanceItem")
......@@ -707,45 +538,34 @@ func init() {
func init() { proto.RegisterFile("statistic.proto", fileDescriptor_405f6cee9ed2da7e) }
var fileDescriptor_405f6cee9ed2da7e = []byte{
// 637 bytes of a gzipped FileDescriptorProto
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x9c, 0x54, 0xcd, 0x6e, 0xd3, 0x40,
0x10, 0x96, 0xeb, 0x3a, 0x4d, 0xa7, 0x95, 0x12, 0x96, 0xaa, 0x58, 0x88, 0x9f, 0xca, 0x5c, 0x2a,
0x84, 0x52, 0x89, 0x48, 0xdc, 0xdb, 0x88, 0x96, 0x08, 0x21, 0x24, 0xb7, 0xe2, 0x80, 0xc4, 0x61,
0xbb, 0x99, 0xb6, 0x16, 0xf6, 0x3a, 0x78, 0xc7, 0x55, 0xc2, 0x63, 0xc0, 0x23, 0xf0, 0x1c, 0x1c,
0x78, 0x33, 0xb4, 0xe3, 0x8d, 0x7f, 0x52, 0x7a, 0xe1, 0xb6, 0xdf, 0x37, 0x3b, 0xbf, 0x3b, 0xdf,
0xc2, 0xc0, 0x90, 0xa4, 0xc4, 0x50, 0xa2, 0x46, 0xf3, 0x22, 0xa7, 0x5c, 0x04, 0xb4, 0x9c, 0xa3,
0x89, 0xde, 0x40, 0xff, 0x22, 0x27, 0x99, 0x9e, 0x22, 0x8a, 0x21, 0xf8, 0x57, 0x88, 0xa1, 0x77,
0xe0, 0x1d, 0xfa, 0xb1, 0x3d, 0x8a, 0x10, 0xb6, 0x68, 0x31, 0xc9, 0x4b, 0x4d, 0xe1, 0x06, 0xb3,
0x2b, 0x18, 0xfd, 0xf0, 0x60, 0x18, 0xe3, 0xb7, 0x33, 0x24, 0x76, 0x9f, 0xe4, 0x89, 0x36, 0x62,
0x1f, 0x7a, 0x66, 0x99, 0x5d, 0xe6, 0x29, 0xc7, 0xd8, 0x8e, 0x1d, 0x12, 0x4f, 0x60, 0xdb, 0xa6,
0xc7, 0x77, 0xd2, 0xdc, 0x70, 0xa0, 0xdd, 0xb8, 0x21, 0xc4, 0x63, 0xe8, 0x1b, 0x92, 0x05, 0xbd,
0xc7, 0x65, 0xe8, 0xb3, 0xb1, 0xc6, 0x62, 0x0f, 0x02, 0xc5, 0xe9, 0x37, 0x39, 0x7d, 0x05, 0x6c,
0x1e, 0x5c, 0xa0, 0xc2, 0x22, 0x0c, 0xaa, 0x3c, 0x15, 0x8a, 0x34, 0x88, 0x18, 0xe7, 0xe9, 0xb2,
0x5b, 0x55, 0x1d, 0xc3, 0x6b, 0xc7, 0x18, 0x82, 0xaf, 0xcb, 0xcc, 0xb5, 0x65, 0x8f, 0x36, 0xaa,
0xcc, 0xf8, 0xa2, 0xcf, 0xa4, 0x43, 0x76, 0x08, 0x1a, 0x17, 0x5c, 0xde, 0x26, 0x97, 0xb7, 0x82,
0x51, 0x09, 0x8f, 0xa6, 0x84, 0x85, 0x24, 0x8c, 0xa5, 0xbe, 0xc6, 0x93, 0xe5, 0x79, 0xdd, 0x54,
0xa7, 0x65, 0x6f, 0xbd, 0xe5, 0x3d, 0x08, 0xb8, 0x45, 0x37, 0x8c, 0x0a, 0xd8, 0x92, 0x50, 0xcf,
0xdc, 0x0c, 0xec, 0xf1, 0xdf, 0xed, 0x47, 0x3f, 0x3d, 0x18, 0x5c, 0x24, 0xea, 0x2b, 0xd2, 0xf9,
0xea, 0x51, 0xc5, 0x4b, 0x18, 0xaa, 0xb2, 0x28, 0x50, 0xd3, 0xc7, 0x39, 0xea, 0x49, 0xab, 0xdf,
0x3b, 0xbc, 0x38, 0x84, 0x01, 0xd9, 0xf1, 0x7c, 0x48, 0x34, 0x16, 0xed, 0xd7, 0x5d, 0xa7, 0x6d,
0x54, 0xa6, 0x26, 0x52, 0xab, 0x14, 0x27, 0xad, 0xe1, 0xdc, 0xe1, 0xa3, 0x5f, 0x1b, 0xab, 0xaa,
0x38, 0xc0, 0x54, 0x5f, 0xe5, 0xf6, 0x69, 0x89, 0xa9, 0xe9, 0xcc, 0xad, 0x44, 0x8d, 0x79, 0x59,
0x48, 0x52, 0x69, 0x38, 0x79, 0x10, 0x3b, 0x24, 0x9e, 0x01, 0xcc, 0x0b, 0xbc, 0x3d, 0xaf, 0x6c,
0x3e, 0xdb, 0x5a, 0x8c, 0x9d, 0x6c, 0x62, 0xce, 0x50, 0xa3, 0x49, 0x0c, 0xcf, 0xa5, 0x1f, 0x37,
0x84, 0xf5, 0x56, 0x05, 0x4a, 0xc2, 0x8b, 0x24, 0x43, 0x5e, 0x0f, 0x3f, 0x6e, 0x31, 0xd6, 0x3b,
0xb3, 0xe5, 0xb1, 0xb9, 0xc7, 0xe6, 0x86, 0xb0, 0x56, 0x95, 0xe6, 0xa6, 0x72, 0xde, 0xaa, 0xac,
0x35, 0x61, 0x63, 0xf3, 0xd5, 0x4f, 0x32, 0x2d, 0x31, 0xec, 0x57, 0xb1, 0x1b, 0x46, 0x44, 0xb0,
0xcb, 0xe8, 0x78, 0x36, 0x2b, 0xd0, 0x98, 0x70, 0x9b, 0x3b, 0xee, 0x70, 0xd1, 0x0b, 0xd8, 0xe1,
0xd5, 0x3c, 0xae, 0x76, 0x6b, 0x0f, 0x02, 0x1e, 0xe4, 0x6a, 0x37, 0x19, 0x44, 0x7f, 0x3c, 0x78,
0x50, 0x89, 0xeb, 0xed, 0x02, 0xd5, 0x89, 0x4c, 0xa5, 0x56, 0xf8, 0x9f, 0xea, 0x12, 0xb0, 0x29,
0x67, 0xb3, 0xc2, 0x6d, 0x15, 0x9f, 0xed, 0xb3, 0x58, 0xc5, 0xd8, 0x9a, 0xdc, 0x4a, 0xd7, 0xf8,
0x3e, 0x6d, 0x35, 0xab, 0xd8, 0x6b, 0xab, 0xa8, 0xa5, 0x8d, 0xad, 0xae, 0x36, 0xbe, 0xc0, 0xa0,
0x55, 0xfc, 0x94, 0x30, 0xeb, 0xa4, 0xf5, 0xee, 0xa6, 0xbd, 0x2a, 0xf2, 0xef, 0xa8, 0xdd, 0x2a,
0x3a, 0xc4, 0xa2, 0x54, 0x94, 0xdc, 0x62, 0x2d, 0x4a, 0x46, 0xd1, 0x6f, 0x0f, 0x1e, 0xae, 0xb4,
0xbe, 0x36, 0x24, 0x27, 0x62, 0xaf, 0x23, 0xe2, 0x08, 0x76, 0xab, 0xd3, 0x69, 0x3b, 0x4b, 0x87,
0x6b, 0xee, 0x1c, 0xb7, 0x33, 0x76, 0xb8, 0xfb, 0x3f, 0x03, 0xf1, 0x0a, 0x82, 0x84, 0x30, 0x33,
0x61, 0x70, 0xe0, 0x1f, 0xee, 0xbc, 0xde, 0x1f, 0xf1, 0x07, 0x3b, 0x5a, 0x1b, 0x42, 0x5c, 0x5d,
0x3a, 0x79, 0xfe, 0xf9, 0xe9, 0x75, 0x42, 0x37, 0xe5, 0xe5, 0x48, 0xe5, 0xd9, 0xd1, 0x78, 0xac,
0xf4, 0x91, 0xba, 0x91, 0x89, 0x1e, 0x8f, 0x8f, 0xd8, 0xef, 0xb2, 0xc7, 0xdf, 0xf4, 0xf8, 0x6f,
0x00, 0x00, 0x00, 0xff, 0xff, 0xbf, 0x11, 0x9f, 0xa6, 0xb9, 0x05, 0x00, 0x00,
// 460 bytes of a gzipped FileDescriptorProto
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x9c, 0x53, 0xc1, 0x6e, 0xd3, 0x40,
0x10, 0xd5, 0xe2, 0x38, 0x6d, 0xa7, 0x95, 0x1a, 0x96, 0xa8, 0x58, 0x08, 0x44, 0x65, 0x2e, 0x3d,
0xa0, 0x44, 0xc2, 0x12, 0xf7, 0xa4, 0xa2, 0x50, 0x71, 0x33, 0x9c, 0x90, 0x38, 0x6c, 0x36, 0xd3,
0xc6, 0x52, 0xbc, 0x0e, 0xf6, 0x04, 0xc5, 0x7c, 0x06, 0xff, 0xc3, 0x81, 0x3f, 0x43, 0x3b, 0xbb,
0x76, 0xec, 0x40, 0x2f, 0xdc, 0xe6, 0x8d, 0xd7, 0xf3, 0xe6, 0xbd, 0xb7, 0x0b, 0xe7, 0x15, 0x29,
0xca, 0x2a, 0xca, 0xf4, 0x64, 0x53, 0x16, 0x54, 0xc8, 0x90, 0xea, 0x0d, 0x56, 0xf1, 0x5b, 0x38,
0xfe, 0x5c, 0x90, 0x5a, 0xdf, 0x20, 0xca, 0x11, 0x04, 0x77, 0x88, 0x91, 0xb8, 0x14, 0x57, 0x41,
0x6a, 0x4b, 0x19, 0xc1, 0x11, 0xed, 0xae, 0x8b, 0xad, 0xa1, 0xe8, 0x11, 0x77, 0x1b, 0x18, 0xff,
0x14, 0x30, 0x4a, 0xf1, 0xdb, 0x7b, 0x24, 0xfe, 0xfd, 0xba, 0xc8, 0x4c, 0x25, 0x2f, 0x60, 0x58,
0xd5, 0xf9, 0xa2, 0x58, 0xf3, 0x8c, 0x93, 0xd4, 0x23, 0xf9, 0x1c, 0x4e, 0x2c, 0x3d, 0x7e, 0x50,
0xd5, 0x8a, 0x07, 0x9d, 0xa5, 0xfb, 0x86, 0x7c, 0x06, 0xc7, 0x15, 0xa9, 0x92, 0x3e, 0x62, 0x1d,
0x05, 0xfc, 0xb1, 0xc5, 0x72, 0x0c, 0xa1, 0x66, 0xfa, 0x01, 0xd3, 0x3b, 0x60, 0x79, 0x70, 0x87,
0x1a, 0xcb, 0x28, 0x74, 0x3c, 0x0e, 0xc5, 0x06, 0x64, 0x8a, 0x9b, 0x75, 0xdd, 0xdf, 0xaa, 0x9d,
0x21, 0xba, 0x33, 0x46, 0x10, 0x98, 0x6d, 0xee, 0x65, 0xd9, 0xd2, 0x4e, 0x55, 0x39, 0x1f, 0x0c,
0xb8, 0xe9, 0x91, 0x35, 0xc1, 0xe0, 0x8e, 0xd7, 0x1b, 0xf0, 0x7a, 0x0d, 0x8c, 0xb7, 0xf0, 0xf4,
0x96, 0xb0, 0x54, 0x84, 0xa9, 0x32, 0xf7, 0x38, 0xaf, 0x3f, 0xb5, 0xa2, 0x7a, 0x92, 0xc5, 0xa1,
0xe4, 0x31, 0x84, 0x2c, 0xd1, 0x9b, 0xe1, 0x80, 0x5d, 0x09, 0xcd, 0xd2, 0x7b, 0x60, 0xcb, 0x7f,
0xcb, 0x8f, 0x5f, 0xc1, 0x29, 0xcb, 0x9b, 0xb9, 0xfd, 0xc6, 0x10, 0x92, 0x85, 0x8d, 0x3e, 0x06,
0xf1, 0x6f, 0x01, 0x8f, 0x5d, 0x40, 0xef, 0x76, 0xa8, 0xe7, 0x6a, 0xad, 0x8c, 0xc6, 0xff, 0x4c,
0x48, 0xc2, 0x40, 0x2d, 0x97, 0xa5, 0xdf, 0x8c, 0x6b, 0x9b, 0x9a, 0x75, 0x7d, 0x66, 0xfb, 0xce,
0x96, 0x16, 0x3f, 0x94, 0xcf, 0x5e, 0xce, 0xb0, 0x9b, 0x44, 0xc7, 0xdf, 0xa3, 0xbe, 0xbf, 0x5f,
0xe1, 0xbc, 0xb3, 0xfc, 0x2d, 0x61, 0xde, 0xa3, 0x15, 0x7f, 0xd3, 0xde, 0x95, 0xc5, 0x0f, 0x34,
0x3e, 0x55, 0x8f, 0x38, 0x58, 0x4d, 0xd9, 0x77, 0x6c, 0x83, 0x65, 0x14, 0xff, 0x12, 0xf0, 0xa4,
0xb9, 0x2f, 0x07, 0x26, 0xf9, 0x8b, 0x20, 0x7a, 0x17, 0x21, 0x86, 0x33, 0x57, 0xdd, 0x74, 0x59,
0x7a, 0xbd, 0xfd, 0x99, 0x59, 0x97, 0xb1, 0xd7, 0x7b, 0xf8, 0x42, 0xc9, 0xd7, 0x10, 0x66, 0x84,
0x79, 0x15, 0x85, 0x97, 0xc1, 0xd5, 0xe9, 0x9b, 0x8b, 0x09, 0x3f, 0xd2, 0xc9, 0x81, 0x09, 0xa9,
0x3b, 0x34, 0x7f, 0xf9, 0xe5, 0xc5, 0x7d, 0x46, 0xab, 0xed, 0x62, 0xa2, 0x8b, 0x7c, 0x9a, 0x24,
0xda, 0x4c, 0xf5, 0x4a, 0x65, 0x26, 0x49, 0xa6, 0xfc, 0xdf, 0x62, 0xc8, 0x4f, 0x3d, 0xf9, 0x13,
0x00, 0x00, 0xff, 0xff, 0x5a, 0x92, 0xa1, 0xd5, 0xfd, 0x03, 0x00, 0x00,
}
......@@ -176,6 +176,7 @@ ForkMultiSignAddress=1298600
ForkBlockCheck=1725000
ForkLocalDBAccess=1
ForkBase58AddressCheck=1800000
ForkEnableParaRegExec=0
[fork.sub.coins]
Enable=0
......
......@@ -197,6 +197,7 @@ ForkMultiSignAddress=1298600
ForkBlockCheck=1
ForkLocalDBAccess=0
ForkBase58AddressCheck=1800000
ForkEnableParaRegExec=0
[fork.sub.coins]
Enable=0
......
......@@ -11,7 +11,7 @@ import (
"reflect"
"time"
"github.com/hashicorp/golang-lru"
lru "github.com/hashicorp/golang-lru"
"strconv"
......@@ -172,8 +172,8 @@ func (txgroup *Transactions) IsExpire(height, blocktime int64) bool {
return false
}
//Check height == 0 的时候,不做检查
func (txgroup *Transactions) Check(height, minfee, maxFee int64) error {
//CheckWithFork 和fork 无关的有个检查函数
func (txgroup *Transactions) CheckWithFork(checkFork, paraFork bool, height, minfee, maxFee int64) error {
txs := txgroup.Txs
if len(txs) < 2 {
return ErrTxGroupCountLessThanTwo
......@@ -193,7 +193,7 @@ func (txgroup *Transactions) Check(height, minfee, maxFee int64) error {
}
//txgroup 只允许一条平行链的交易, 且平行链txgroup须全部是平行链tx
//如果平行链已经在主链分叉高度前运行了一段时间且有跨链交易,平行链需要自己设置这个fork
if IsFork(height, "ForkTxGroupPara") {
if paraFork {
if len(para) > 1 {
tlog.Info("txgroup has multi para transaction")
return ErrTxGroupParaCount
......@@ -225,7 +225,7 @@ func (txgroup *Transactions) Check(height, minfee, maxFee int64) error {
if txs[0].Fee < totalfee {
return ErrTxFeeTooLow
}
if txs[0].Fee > maxFee && maxFee > 0 && IsFork(height, "ForkBlockCheck") {
if txs[0].Fee > maxFee && maxFee > 0 && checkFork {
return ErrTxFeeTooHigh
}
//检查hash是否符合要求
......@@ -261,6 +261,13 @@ func (txgroup *Transactions) Check(height, minfee, maxFee int64) error {
return nil
}
//Check height == 0 的时候,不做检查
func (txgroup *Transactions) Check(height, minfee, maxFee int64) error {
paraFork := IsFork(height, "ForkTxGroupPara")
checkFork := IsFork(height, "ForkBlockCheck")
return txgroup.CheckWithFork(checkFork, paraFork, height, minfee, maxFee)
}
//TransactionCache 交易缓存结构
type TransactionCache struct {
*Transaction
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment