Unverified Commit dbb60dcf authored by vipwzw's avatar vipwzw Committed by GitHub

Merge pull request #1123 from zhengjunhe/withdraw_opt_1217

Withdraw opt 1217
parents 960cd88a d940ed32
......@@ -210,3 +210,37 @@ func CreateNewBridgeToken(cmd *cobra.Command, _ []string) {
}
callContractAndSignWrite(cmd, packData, contract, "create_bridge_token")
}
func SetWithdrawProxyCmd() *cobra.Command {
cmd := &cobra.Command{
Use: "set_withdraw_proxy",
Short: "set withdraw proxy on chain33, and it's should be done by operator",
Run: SetWithdrawProxy,
}
addSetWithdrawProxyFlags(cmd)
return cmd
}
func addSetWithdrawProxyFlags(cmd *cobra.Command) {
cmd.Flags().StringP("address", "a", "", "withdraw address")
_ = cmd.MarkFlagRequired("address")
cmd.Flags().StringP("contract", "c", "", "bridgebank contract address")
_ = cmd.MarkFlagRequired("contract")
cmd.Flags().StringP("key", "k", "", "the deployer private key")
_ = cmd.MarkFlagRequired("key")
cmd.Flags().StringP("note", "n", "", "transaction note info (optional)")
cmd.Flags().Float64P("fee", "f", 0, "contract gas fee (optional)")
}
func SetWithdrawProxy(cmd *cobra.Command, _ []string) {
contract, _ := cmd.Flags().GetString("contract")
withdrawAddr, _ := cmd.Flags().GetString("address")
parameter := fmt.Sprintf("setWithdrawProxy(%s)", withdrawAddr)
_, packData, err := evmAbi.Pack(parameter, generated.BridgeBankABI, false)
if nil != err {
fmt.Println("setWithdrawProxy", "Failed to do abi.Pack due to:", err.Error())
return
}
callContractAndSignWrite(cmd, packData, contract, "set_withdraw_proxy")
}
......@@ -146,10 +146,6 @@ multisignAddrs=["168Sn1DXnLrZHTcAM9stD6t2P49fNuJfJ9", "13KTf57aCkVVJYNJBXBBveiA5
15XsGjTbV6SxQtDE1SC5oaHx8HbseQ4Lf9 -- bridge_token 地址
```
***
***
#### 离线多签设置
* 离线创建交易
......
......@@ -35,6 +35,7 @@ func Boss4xOfflineCmd() *cobra.Command {
ConfigLockedTokenOfflineSaveCmd(),
CreateMultisignTransferCmd(),
MultisignTransferCmd(),
SetWithdrawProxyCmd(),
)
return cmd
}
......
......@@ -7,4 +7,4 @@ initPowers=[25, 25, 25, 25]
# 主链symbol
symbol="ETH"
# 离线多签地址
multisignAddrs=["0x4c85848a7E2985B76f06a7Ed338FCB3aF94a7DCf", "0x6F163E6daf0090D897AD7016484f10e0cE844994", "0xbc333839E37bc7fAAD0137aBaE2275030555101f", "0x495953A743ef169EC5D4aC7b5F786BF2Bd56aFd5"]
\ No newline at end of file
multisignAddrs=["0x4c85848a7E2985B76f06a7Ed338FCB3aF94a7DCf", "0x6F163E6daf0090D897AD7016484f10e0cE844994", "0x0921948C0d25BBbe85285CB5975677503319F02A", "0x69921517970a28b73ac5E4C8ac8Fd135A80D2be1"]
\ No newline at end of file
......@@ -34,6 +34,7 @@ func ConfigplatformTokenSymbol(cmd *cobra.Command, _ []string) {
symbol, _ := cmd.Flags().GetString("symbol")
deployAddr, _ := cmd.Flags().GetString("deployAddr")
contract, _ := cmd.Flags().GetString("contract")
chainEthId, _ := cmd.Flags().GetInt64("chainEthId")
bridgeAbi, err := abi.JSON(strings.NewReader(generated.BridgeBankABI))
if err != nil {
......@@ -46,5 +47,5 @@ func ConfigplatformTokenSymbol(cmd *cobra.Command, _ []string) {
panic(err)
}
CreateTxInfoAndWrite(abiData, deployAddr, contract, "set_symbol", url)
CreateTxInfoAndWrite(abiData, deployAddr, contract, "set_symbol", url, chainEthId)
}
......@@ -6,6 +6,7 @@ import (
"math/big"
"strings"
bep20 "github.com/33cn/plugin/plugin/dapp/cross2eth/contracts/bep20/generated"
"github.com/33cn/plugin/plugin/dapp/cross2eth/contracts/contracts4eth/generated"
erc20 "github.com/33cn/plugin/plugin/dapp/cross2eth/contracts/erc20/generated"
tetherUSDT "github.com/33cn/plugin/plugin/dapp/cross2eth/contracts/usdt/generated"
......@@ -31,6 +32,86 @@ import (
./boss4x ethereum offline send -f deploysigntxs.txt
*/
func DeployBEP20Cmd() *cobra.Command {
cmd := &cobra.Command{
Use: "deploy_bep20",
Short: "deploy BEP20 contracts",
Run: DeployBEP20,
}
DeployBEP20Flags(cmd)
return cmd
}
func DeployBEP20Flags(cmd *cobra.Command) {
cmd.Flags().StringP("deployAddr", "a", "", "addr to deploy contract ")
_ = cmd.MarkFlagRequired("deployAddr")
cmd.Flags().StringP("owner", "o", "", "owner address")
_ = cmd.MarkFlagRequired("owner")
cmd.Flags().StringP("symbol", "s", "", "BEP20 symbol")
_ = cmd.MarkFlagRequired("symbol")
cmd.Flags().StringP("totalSupply", "m", "0", "total supply")
_ = cmd.MarkFlagRequired("totalSupply")
cmd.Flags().IntP("decimal", "d", 8, "decimal")
_ = cmd.MarkFlagRequired("decimal")
}
func DeployBEP20(cmd *cobra.Command, _ []string) {
url, _ := cmd.Flags().GetString("rpc_laddr_ethereum")
deployerAddr, _ := cmd.Flags().GetString("deployAddr")
owner, _ := cmd.Flags().GetString("owner")
symbol, _ := cmd.Flags().GetString("symbol")
totalSupply, _ := cmd.Flags().GetString("totalSupply")
decimal, _ := cmd.Flags().GetInt("decimal")
bnAmount := big.NewInt(1)
bnAmount, _ = bnAmount.SetString(utils.TrimZeroAndDot(totalSupply), 10)
client, err := ethclient.Dial(url)
if err != nil {
fmt.Println("ethclient Dial error", err.Error())
return
}
symbol = strings.ToUpper(symbol)
ctx := context.Background()
startNonce, err := client.PendingNonceAt(ctx, common.HexToAddress(deployerAddr))
if nil != err {
fmt.Println("PendingNonceAt error", err.Error())
return
}
var infos []*DeployInfo
parsed, err := abi.JSON(strings.NewReader(bep20.BEP20TokenABI))
if err != nil {
fmt.Println("abi.JSON(strings.NewReader(erc20.ERC20ABI)) error", err.Error())
return
}
bin := common.FromHex(bep20.BEP20TokenBin)
BEP20OwnerAddr := common.HexToAddress(owner)
//constructor (string memory name_, string memory symbol_,uint256 totalSupply_, uint8 decimals_, address owner_) public {
tokenName := symbol + " Token"
packdata, err := parsed.Pack("", tokenName, symbol, bnAmount, uint8(decimal), BEP20OwnerAddr)
if err != nil {
fmt.Println("Pack error", err.Error())
return
}
BEP20Addr := crypto.CreateAddress(common.HexToAddress(deployerAddr), startNonce)
deployInfo := DeployInfo{
PackData: append(bin, packdata...),
ContractorAddr: BEP20Addr,
Name: "BEP20: " + symbol,
Nonce: startNonce,
To: nil,
}
infos = append(infos, &deployInfo)
fileName := fmt.Sprintf("deployBEP20%s.txt", symbol)
err = NewTxWrite(infos, common.HexToAddress(deployerAddr), url, fileName)
if err != nil {
fmt.Println("NewTxWrite error", err.Error())
return
}
}
func DeployERC20Cmd() *cobra.Command {
cmd := &cobra.Command{
Use: "create_erc20",
......@@ -201,6 +282,7 @@ func AddToken2LockListTx(cmd *cobra.Command, _ []string) {
deployAddr, _ := cmd.Flags().GetString("deployAddr")
token, _ := cmd.Flags().GetString("token")
contract, _ := cmd.Flags().GetString("contract")
chainEthId, _ := cmd.Flags().GetInt64("chainEthId")
bridgeAbi, err := abi.JSON(strings.NewReader(generated.BridgeBankABI))
if err != nil {
......@@ -214,7 +296,7 @@ func AddToken2LockListTx(cmd *cobra.Command, _ []string) {
return
}
CreateTxInfoAndWrite(abiData, deployAddr, contract, "create_add_lock_list", url)
CreateTxInfoAndWrite(abiData, deployAddr, contract, "create_add_lock_list", url, chainEthId)
}
func CreateBridgeTokenTxCmd() *cobra.Command {
......@@ -241,6 +323,7 @@ func CreateBridgeTokenTx(cmd *cobra.Command, _ []string) {
symbol, _ := cmd.Flags().GetString("symbol")
deployAddr, _ := cmd.Flags().GetString("deployAddr")
contract, _ := cmd.Flags().GetString("contract")
chainEthId, _ := cmd.Flags().GetInt64("chainEthId")
bridgeAbi, err := abi.JSON(strings.NewReader(generated.BridgeBankABI))
if err != nil {
......@@ -253,5 +336,5 @@ func CreateBridgeTokenTx(cmd *cobra.Command, _ []string) {
fmt.Println("bridgeAbi.Pack createNewBridgeToken Err:", err)
return
}
CreateTxInfoAndWrite(abiData, deployAddr, contract, "create_bridge_token", url)
CreateTxInfoAndWrite(abiData, deployAddr, contract, "create_bridge_token", url, chainEthId)
}
......@@ -58,6 +58,7 @@ func cfgAccountTx(cmd *cobra.Command, _ []string) {
address, _ := cmd.Flags().GetString("address")
deployAddr, _ := cmd.Flags().GetString("deployAddr")
contract, _ := cmd.Flags().GetString("contract")
chainEthId, _ := cmd.Flags().GetInt64("chainEthId")
bridgeAbi, err := abi.JSON(strings.NewReader(generated.BridgeBankABI))
if err != nil {
......@@ -70,7 +71,7 @@ func cfgAccountTx(cmd *cobra.Command, _ []string) {
panic(err)
}
CreateTxInfoAndWrite(abiData, deployAddr, contract, "set_offline_addr", url)
CreateTxInfoAndWrite(abiData, deployAddr, contract, "set_offline_addr", url, chainEthId)
}
func SetupCmd() *cobra.Command {
......@@ -96,6 +97,7 @@ func SetupOwner(cmd *cobra.Command, _ []string) {
url, _ := cmd.Flags().GetString("rpc_laddr_ethereum")
multisign, _ := cmd.Flags().GetString("multisign")
deployAddr, _ := cmd.Flags().GetString("deployAddr")
chainEthId, _ := cmd.Flags().GetInt64("chainEthId")
owner, _ := cmd.Flags().GetString("owner")
owners := strings.Split(owner, ",")
......@@ -118,6 +120,6 @@ func SetupOwner(cmd *cobra.Command, _ []string) {
return
}
CreateTxInfoAndWrite(abiData, deployAddr, multisign, "multisign_setup", url)
CreateTxInfoAndWrite(abiData, deployAddr, multisign, "multisign_setup", url, chainEthId)
}
......@@ -53,6 +53,7 @@ func ConfigLockedTokenOfflineSave(cmd *cobra.Command, _ []string) {
percents, _ := cmd.Flags().GetUint8("percents")
deployAddr, _ := cmd.Flags().GetString("deployAddr")
contract, _ := cmd.Flags().GetString("contract")
chainEthId, _ := cmd.Flags().GetInt64("chainEthId")
d, err := utils.GetDecimalsFromNode(token, url)
if err != nil {
......@@ -86,5 +87,5 @@ func ConfigLockedTokenOfflineSave(cmd *cobra.Command, _ []string) {
panic(err)
}
CreateTxInfoAndWrite(abiData, deployAddr, contract, "set_offline_token", url)
CreateTxInfoAndWrite(abiData, deployAddr, contract, "set_offline_token", url, chainEthId)
}
......@@ -34,6 +34,7 @@ func DeployOfflineContractsCmd() *cobra.Command {
CreateCmd(), //构造交易
CreateWithFileCmd(),
DeployERC20Cmd(),
DeployBEP20Cmd(),
DeployTetherUSDTCmd(),
//CreateCfgAccountTxCmd(), // set_offline_addr 设置离线多签地址
//SetupCmd(),
......@@ -71,7 +72,7 @@ type DeployConfigInfo struct {
MultisignAddrs []string `toml:"multisignAddrs"`
}
func CreateTxInfoAndWrite(abiData []byte, deployAddr, contract, name, url string) {
func CreateTxInfoAndWrite(abiData []byte, deployAddr, contract, name, url string, chainEthId int64) {
client, err := ethclient.Dial(url)
if err != nil {
fmt.Println("Dial Err:", err)
......@@ -96,14 +97,21 @@ func CreateTxInfoAndWrite(abiData []byte, deployAddr, contract, name, url string
msg.To = &contracAddr
msg.Value = big.NewInt(0)
//估算gas
gasLimit, err := client.EstimateGas(context.Background(), msg)
var gasLimit uint64
// 模拟节点测试
if chainEthId == 1337 {
gasLimit = uint64(500 * 10000)
} else {
gasLimit, err = client.EstimateGas(context.Background(), msg)
if err != nil {
fmt.Println("EstimateGas Err:", err)
return
}
gasLimit = uint64(1.2 * float64(gasLimit))
if gasLimit < 100*10000 {
gasLimit = 100 * 10000
}
}
ntx := types.NewTx(&types.LegacyTx{
Nonce: nonce,
......
......@@ -246,6 +246,7 @@ func addCreateMultisignTransferTxFlags(cmd *cobra.Command) {
func CreateMultisignTransferTx(cmd *cobra.Command, _ []string) {
url, _ := cmd.Flags().GetString("rpc_laddr_ethereum")
chainEthId, _ := cmd.Flags().GetInt64("chainEthId")
txFilePath, _ := cmd.Flags().GetString("file")
client, err := ethclient.Dial(url)
......@@ -282,7 +283,7 @@ func CreateMultisignTransferTx(cmd *cobra.Command, _ []string) {
return
}
CreateTxInfoAndWrite(gnoData, txinfo.SendAddr, txinfo.CrontractAddr, "create_multisign_tx", url)
CreateTxInfoAndWrite(gnoData, txinfo.SendAddr, txinfo.CrontractAddr, "create_multisign_tx", url, chainEthId)
}
func buildSigs(data []byte, privateKeys []string) ([]byte, error) {
......
......@@ -5,6 +5,11 @@ services:
entrypoint: ["node", "/app/ganache-core.docker.cli.js", "-a", "20", "-b", "2", "--debug", "-m", "coast bar giraffe art venue decide symbol law visual crater vital fold", "-e", "1000"]
image: trufflesuite/ganache-cli:latest
ebrelayerproxy:
build:
context: .
dockerfile: Dockerfile-cross2eth
ebrelayera:
build:
context: .
......
......@@ -23,9 +23,6 @@ source "./offlinePublic.sh"
ethereumUSDTERC20TokenAddr=""
chain33USDTBridgeTokenAddr=""
chain33ID=0
maturityDegree=10
# ETH 部署合约者的私钥 用于部署合约时签名使用
ethDeployAddr="0x8AFDADFC88a1087c9A1D6c0F5Dd04634b87F303a"
ethDeployKey="0x8656d2bc732a8a816a461ba5e2d8aac7c7f85c26a813df30d5327210465eb230"
......@@ -70,6 +67,18 @@ source "./offlinePublic.sh"
chain33ReceiverAddr="12qyocayNF7Lv6C9qW4avxs2E7U41fKSfv"
chain33ReceiverAddrKey="4257d8692ef7fe13c68b65d6a52f03933db2fa5ce8faf210b5b8b80c721ced01"
ethValidatorAddrp="0x0c05ba5c230fdaa503b53702af1962e08d0c60bf"
ethValidatorAddrKeyp="9dc6df3a8ab139a54d8a984f54958ae0661f880229bf3bdbb886b87d58b56a08"
chain33Validatorp="1GTxrmuWiXavhcvsaH5w9whgVxUrWsUMdV"
chain33ValidatorKeyp="0xd627968e445f2a41c92173225791bae1ba42126ae96c32f28f97ff8f226e5c68"
chain33Validatorsp="1Hf1wnnr6XaYy5Sf3HhAfT4N8JYV4sMh9J"
chain33ValidatorKeysp="0x1dadb7cbad8ea3f968cfad40ac32981def6215690618e62c48e816e7c732a8c2"
chain33ID=0
maturityDegree=10
validatorPwd="123456fzm"
}
function start_docker_ebrelayerA() {
......@@ -79,9 +88,8 @@ function start_docker_ebrelayerA() {
sleep 5
}
# start ebrelayer B C D
function updata_toml_start_bcd() {
for name in b c d; do
function updata_toml() {
local name=$1
local file="./relayer$name.toml"
cp './relayer.toml' "${file}"
......@@ -98,26 +106,23 @@ function updata_toml_start_bcd() {
line=$(delete_line_show "${file}" "pushBind")
sed -i ''"${line}"' a pushBind="'"${pushHost}"':20000"' "${file}"
}
# start ebrelayer B C D
function updata_toml_start_bcd() {
for name in b c d; do
updata_toml $name
local file="./relayer$name.toml"
docker cp "${file}" "${dockerNamePrefix}_ebrelayer${name}_1":/root/relayer.toml
start_docker_ebrelayer "${dockerNamePrefix}_ebrelayer${name}_1" "/root/ebrelayer" "./ebrelayer${name}.log"
# shellcheck disable=SC2034
CLI="docker exec ${dockerNamePrefix}_ebrelayer${name}_1 /root/ebcli_A"
result=$(${CLI} set_pwd -p 123456hzj)
cli_ret "${result}" "set_pwd"
result=$(${CLI} unlock -p 123456hzj)
cli_ret "${result}" "unlock"
eval chain33ValidatorKey=\$chain33ValidatorKey${name}
# shellcheck disable=SC2154
result=$(${CLI} chain33 import_privatekey -k "${chain33ValidatorKey}")
cli_ret "${result}" "chain33 import_privatekey"
eval ethValidatorAddrKey=\$ethValidatorAddrKey${name}
# shellcheck disable=SC2154
result=$(${CLI} ethereum import_privatekey -k "${ethValidatorAddrKey}")
cli_ret "${result}" "ethereum import_privatekey"
init_validator_relayer "${CLI}" "${validatorPwd}" "${chain33ValidatorKey}" "${ethValidatorAddrKey}"
done
}
......@@ -127,7 +132,7 @@ function restart_ebrelayerA() {
sleep 1
start_docker_ebrelayerA
result=$(${CLIA} unlock -p 123456hzj)
result=$(${CLIA} unlock -p "${validatorPwd}")
cli_ret "${result}" "unlock"
}
......@@ -252,73 +257,59 @@ function TestChain33ToEthAssets() {
#}
# eth to chain33 在以太坊上锁定 ETH 资产,然后在 chain33 上 burn
function TestETH2Chain33Assets() {
echo -e "${GRE}=========== $FUNCNAME begin ===========${NOC}"
echo -e "${GRE}=========== eth to chain33 在以太坊上锁定 ETH 资产,然后在 chain33 上 burn ===========${NOC}"
# 查询 ETH 这端 bridgeBank 地址原来是 0
result=$(${CLIA} ethereum balance -o "${ethBridgeBank}")
cli_ret "${result}" "balance" ".balance" "0"
# ETH 这端 lock 11个
result=$(${CLIA} ethereum lock -m 11 -k "${ethTestAddrKey1}" -r "${chain33ReceiverAddr}")
result=$(${CLIA} ethereum lock -m 0.002 -k "${ethTestAddrKey1}" -r "${chain33ReceiverAddr}")
cli_ret "${result}" "lock"
# eth 等待 2 个区块
sleep 4
# 查询 ETH 这端 bridgeBank 地址 11
result=$(${CLIA} ethereum balance -o "${ethBridgeBank}")
cli_ret "${result}" "balance" ".balance" "11"
cli_ret "${result}" "balance" ".balance" "0.002"
sleep ${maturityDegree}
# chain33 chain33EthBridgeTokenAddr(ETH合约中)查询 lock 金额
result=$(${Chain33Cli} evm query -a "${chain33EthBridgeTokenAddr}" -c "${chain33DeployAddr}" -b "balanceOf(${chain33ReceiverAddr})")
# 结果是 11 * le8
is_equal "${result}" "1100000000"
# is_equal "${result}" "2000000000000000"
# 原来的数额
result=$(${CLIA} ethereum balance -o "${ethTestAddr2}")
cli_ret "${result}" "balance" ".balance" "1000"
echo '#5.burn ETH from Chain33 ETH(Chain33)-----> Ethereum'
result=$(${CLIA} chain33 burn -m 5 -k "${chain33ReceiverAddrKey}" -r "${ethTestAddr2}" -t "${chain33EthBridgeTokenAddr}")
result=$(${CLIA} chain33 burn -m 0.0003 -k "${chain33ReceiverAddrKey}" -r "${ethTestAddr2}" -t "${chain33EthBridgeTokenAddr}")
cli_ret "${result}" "burn"
sleep ${maturityDegree}
echo "check the balance on chain33"
result=$(${Chain33Cli} evm query -a "${chain33EthBridgeTokenAddr}" -c "${chain33DeployAddr}" -b "balanceOf(${chain33ReceiverAddr})")
# 结果是 11-5 * le8
is_equal "${result}" "600000000"
# is_equal "${result}" "1700000000000000"
# 查询 ETH 这端 bridgeBank 地址 0
result=$(${CLIA} ethereum balance -o "${ethBridgeBank}")
cli_ret "${result}" "balance" ".balance" "6"
# 比之前多 5
result=$(${CLIA} ethereum balance -o "${ethTestAddr2}")
cli_ret "${result}" "balance" ".balance" "1005"
cli_ret "${result}" "balance" ".balance" "0.0017"
echo '#5.burn ETH from Chain33 ETH(Chain33)-----> Ethereum 6'
result=$(${CLIA} chain33 burn -m 6 -k "${chain33ReceiverAddrKey}" -r "${ethTestAddr2}" -t "${chain33EthBridgeTokenAddr}")
result=$(${CLIA} chain33 burn -m 0.0017 -k "${chain33ReceiverAddrKey}" -r "${ethTestAddr2}" -t "${chain33EthBridgeTokenAddr}")
cli_ret "${result}" "burn"
sleep ${maturityDegree}
echo "check the balance on chain33"
result=$(${Chain33Cli} evm query -a "${chain33EthBridgeTokenAddr}" -c "${chain33DeployAddr}" -b "balanceOf(${chain33ReceiverAddr})")
# 结果是 11-5 * le8
is_equal "${result}" "0"
# 查询 ETH 这端 bridgeBank 地址 0
result=$(${CLIA} ethereum balance -o "${ethBridgeBank}")
cli_ret "${result}" "balance" ".balance" "0"
# 比之前多 5
result=$(${CLIA} ethereum balance -o "${ethTestAddr2}")
cli_ret "${result}" "balance" ".balance" "1011"
echo -e "${GRE}=========== $FUNCNAME end ===========${NOC}"
}
......@@ -854,6 +845,7 @@ function get_cli() {
Para8801Cli="./chain33-cli --rpc_laddr http://${docker_chain33_ip}:8901 --paraName user.p.para."
Para8901Cli="./chain33-cli --rpc_laddr http://${docker_chain33_ip}:8901 --paraName user.p.para."
CLIP="docker exec ${dockerNamePrefix}_ebrelayerproxy_1 /root/ebcli_A"
CLIA="docker exec ${dockerNamePrefix}_ebrelayera_1 /root/ebcli_A"
CLIB="docker exec ${dockerNamePrefix}_ebrelayerb_1 /root/ebcli_A"
CLIC="docker exec ${dockerNamePrefix}_ebrelayerc_1 /root/ebcli_A"
......
......@@ -73,23 +73,31 @@ function OfflineDeploy() {
echo -e "${GRE}=========== $FUNCNAME end ===========${NOC}"
}
# shellcheck disable=SC2120
function InitRelayerA() {
echo -e "${GRE}=========== $FUNCNAME begin ===========${NOC}"
result=$(${CLIA} set_pwd -p 123456hzj)
# init $1 CLI $2 pwd $3 chain33ValidatorKey $4 ethValidatorAddrKey
function init_validator_relayer() {
local CLI=$1
local pwd=$2
local chain33ValidatorKey=$3
local ethValidatorAddrKey=$4
result=$(${CLI} set_pwd -p "${pwd}")
cli_ret "${result}" "set_pwd"
result=$(${CLIA} unlock -p 123456hzj)
result=$(${CLI} unlock -p "${pwd}")
cli_ret "${result}" "unlock"
# shellcheck disable=SC2154
result=$(${CLIA} chain33 import_privatekey -k "${chain33ValidatorKeya}")
result=$(${CLI} chain33 import_privatekey -k "${chain33ValidatorKey}")
cli_ret "${result}" "chain33 import_privatekey"
# shellcheck disable=SC2154
result=$(${CLIA} ethereum import_privatekey -k "${ethValidatorAddrKeya}")
result=$(${CLI} ethereum import_privatekey -k "${ethValidatorAddrKey}")
cli_ret "${result}" "ethereum import_privatekey"
}
# shellcheck disable=SC2120
function InitRelayerA() {
echo -e "${GRE}=========== $FUNCNAME begin ===========${NOC}"
# shellcheck disable=SC2154
init_validator_relayer "${CLIA}" "${validatorPwd}" "${chain33ValidatorKeya}" "${ethValidatorAddrKeya}"
${CLIA} chain33 multisign set_multiSign -a "${multisignChain33Addr}"
......
......@@ -202,7 +202,8 @@ function start_ebrelayer_and_unlock() {
local CLI="./ebcli_$1"
local count=0
while true; do
result=$(${CLI} relayer unlock -p 123456hzj | jq -r .isOK)
# shellcheck disable=SC2154
result=$(${CLI} relayer unlock -p "${validatorPwd}" | jq -r .isOK)
if [[ ${result} == "true" ]]; then
break
fi
......@@ -225,7 +226,7 @@ function start_ebrelayer_and_setpwd_unlock() {
local CLI="./ebcli_$1"
local count=0
while true; do
result=$(${CLI} relayer set_pwd -p 123456hzj | jq -r .isOK)
result=$(${CLI} relayer set_pwd -p "${validatorPwd}" | jq -r .isOK)
if [[ ${result} == "true" ]]; then
break
fi
......@@ -241,7 +242,7 @@ function start_ebrelayer_and_setpwd_unlock() {
count=0
while true; do
result=$(${CLI} relayer unlock -p 123456hzj | jq -r .isOK)
result=$(${CLI} relayer unlock -p "${validatorPwd}" | jq -r .isOK)
if [[ ${result} == "true" ]]; then
break
fi
......
......@@ -19,12 +19,12 @@ source "./publicTest.sh"
ethMultisignA=0x4c85848a7E2985B76f06a7Ed338FCB3aF94a7DCf
ethMultisignB=0x6F163E6daf0090D897AD7016484f10e0cE844994
ethMultisignC=0xbc333839E37bc7fAAD0137aBaE2275030555101f
ethMultisignD=0x495953A743ef169EC5D4aC7b5F786BF2Bd56aFd5
ethMultisignC=0x0921948C0d25BBbe85285CB5975677503319F02A
ethMultisignD=0x69921517970a28b73ac5E4C8ac8Fd135A80D2be1
ethMultisignKeyA=0x5e8aadb91eaa0fce4df0bcc8bd1af9e703a1d6db78e7a4ebffd6cf045e053574
ethMultisignKeyB=0x0504bcb22b21874b85b15f1bfae19ad62fc2ad89caefc5344dc669c57efa60db
ethMultisignKeyC=0x0c61f5a879d70807686e43eccc1f52987a15230ae0472902834af4d1933674f2
ethMultisignKeyD=0x2809477ede1261da21270096776ba7dc68b89c9df5f029965eaa5fe7f0b80697
ethMultisignKeyC=0x5a43f2c8724f60ea5d6b87ad424daa73639a5fc76702edd3e5eaed37aaffdf49
ethMultisignKeyD=0x03b28c0fc78c6ebae719b559b0781db24644b655d4bd58e5cf2311c9f03baa3d
}
maturityDegree=10
......@@ -66,7 +66,8 @@ function kill_ebrelayerD() {
function start_ebrelayerC() {
nohup ./relayer_C/ebrelayer ./relayer_C/relayer.toml >./relayer_C/cross2eth_C.log 2>&1 &
sleep 2
${CLIC} unlock -p 123456hzj
# shellcheck disable=SC2154
${CLIC} unlock -p "${validatorPwd}"
${Chain33Cli} send coins transfer -a 1 -n note -t 12qyocayNF7Lv6C9qW4avxs2E7U41fKSfv -k 14KEKbYtKKQm4wMthSK9J4La4nAiidGozt
${Chain33Cli} send coins transfer -a 1 -n note -t 12qyocayNF7Lv6C9qW4avxs2E7U41fKSfv -k 14KEKbYtKKQm4wMthSK9J4La4nAiidGozt
sleep ${maturityDegree}
......@@ -76,7 +77,7 @@ function start_ebrelayerC() {
function start_ebrelayerD() {
nohup ./relayer_D/ebrelayer ./relayer_D/relayer.toml >./relayer_D/cross2eth_D.log 2>&1 &
sleep 2
${CLID} unlock -p 123456hzj
${CLID} unlock -p "${validatorPwd}"
${Chain33Cli} send coins transfer -a 1 -n note -t 12qyocayNF7Lv6C9qW4avxs2E7U41fKSfv -k 14KEKbYtKKQm4wMthSK9J4La4nAiidGozt
${Chain33Cli} send coins transfer -a 1 -n note -t 12qyocayNF7Lv6C9qW4avxs2E7U41fKSfv -k 14KEKbYtKKQm4wMthSK9J4La4nAiidGozt
sleep ${maturityDegree}
......@@ -86,10 +87,10 @@ function start_ebrelayerD() {
function InitAndDeploy() {
echo -e "${GRE}=========== $FUNCNAME begin ===========${NOC}"
result=$(${CLIA} set_pwd -p 123456hzj)
result=$(${CLIA} set_pwd -p "${validatorPwd}")
cli_ret "${result}" "set_pwd"
result=$(${CLIA} unlock -p 123456hzj)
result=$(${CLIA} unlock -p "${validatorPwd}")
cli_ret "${result}" "unlock"
# shellcheck disable=SC2154
......@@ -287,10 +288,10 @@ function updata_toml_start_BCD() {
sleep 2
CLI="./ebcli_$name"
result=$(${CLI} set_pwd -p 123456hzj)
result=$(${CLI} set_pwd -p "${validatorPwd}")
cli_ret "${result}" "set_pwd"
result=$(${CLI} unlock -p 123456hzj)
result=$(${CLI} unlock -p "${validatorPwd}")
cli_ret "${result}" "unlock"
eval chain33ValidatorKey=\$chain33ValidatorKey${name}
......@@ -358,7 +359,7 @@ function StartRelayerAndDeploy() {
kill_ebrelayer ebrelayer
start_ebrelayerA
result=$(${CLIA} unlock -p 123456hzj)
result=$(${CLIA} unlock -p "${validatorPwd}")
cli_ret "${result}" "unlock"
# start ebrelayer B C D
......@@ -424,7 +425,7 @@ function InitChain33Validator() {
}
# 导入 chain33Validators 私钥生成地址
for name in a b c d; do
for name in a b c d p sp; do
eval chain33ValidatorKey=\$chain33ValidatorKey${name}
eval chain33Validator=\$chain33Validator${name}
result=$(${Chain33Cli} account import_key -k "${chain33ValidatorKey}" -l validator$name)
......@@ -526,7 +527,7 @@ function StartOneRelayer() {
kill_ebrelayer ebrelayer
start_ebrelayerA
result=$(${CLIA} unlock -p 123456hzj)
result=$(${CLIA} unlock -p "${validatorPwd}")
cli_ret "${result}" "unlock"
# 设置 token 地址
......
......@@ -352,14 +352,24 @@ contract BEP20Token is Context, IBEP20, Ownable {
string private _symbol;
string private _name;
constructor() public {
_name = "BUSD Token";
_symbol = "BUSD";
_decimals = 18;
_totalSupply = 31000000000000000000000000;
_balances[msg.sender] = _totalSupply;
emit Transfer(address(0), msg.sender, _totalSupply);
// constructor() public {
// _name = "BUSD Token";
// _symbol = "BUSD";
// _decimals = 18;
// _totalSupply = 31000000000000000000000000;
// _balances[msg.sender] = _totalSupply;
//
// emit Transfer(address(0), msg.sender, _totalSupply);
// }
constructor (string memory name_, string memory symbol_,uint256 totalSupply_, uint8 decimals_, address owner_) public {
_name = name_;
_symbol = symbol_;
_decimals = decimals_;
_totalSupply = totalSupply_;
_balances[owner_] = totalSupply_;
emit Transfer(address(0), owner_, totalSupply_);
}
/**
......
......@@ -106,6 +106,17 @@ contract BridgeBank is EthereumBank, Chain33Bank {
}
/*
* @dev: set a proxy address to receive and it's transfer asset on Ethereum
*
* @param _proxyReceiver: The address to receive asset
* @return: indicate whether set successfully or not
*/
function setWithdrawProxy(address payable _proxyReceiver) public onlyOperator
{
proxyReceiver = _proxyReceiver;
}
/*
* @dev: Mints new BankTokens
*
* @param _ethereumSender: The sender's Ethereum address in bytes.
......@@ -137,7 +148,7 @@ contract BridgeBank is EthereumBank, Chain33Bank {
* @dev: Burns bank tokens
*
* @param _ethereumReceiver: The _ethereum receiver address in bytes.
* @param _ethereumTokenAddress: The currency type
* @param _ethereumTokenAddress: The token address mint on chain33 and it's origin from Ethereum
* @param _amount: number of ethereum tokens to be burned
*/
function burnBridgeTokens(
......@@ -156,6 +167,28 @@ contract BridgeBank is EthereumBank, Chain33Bank {
}
/*
* @dev: withdraw asset via Proxy
*
* @param _ethereumReceiver: The _ethereum receiver address in bytes.
* @param _bridgeTokenAddress: The bridge Token Address issued in chain33 and it's origin from Ethereum/BSC
* @param _amount: number of bridge tokens to be transferred to proxy address
*/
function withdrawViaProxy(
bytes memory _ethereumReceiver,
address _bridgeTokenAddress,
uint256 _amount
)
public
{
return withdrawEthereumTokens(
msg.sender,
_ethereumReceiver,
_bridgeTokenAddress,
_amount
);
}
/*
* @dev: addToken2LockList used to add token with the specified address to be
* allowed locked from Ethereum
*
......
......@@ -14,11 +14,12 @@ contract EthereumBank {
using SafeMath for uint256;
uint256 public bridgeTokenCount;
address payable proxyReceiver;
mapping(address => bool) public bridgeTokenWhitelist;
mapping(bytes32 => bool) public bridgeTokenCreated;
mapping(bytes32 => EthereumDeposit) ethereumDeposits;
mapping(bytes32 => EthereumBurn) ethereumBurns;
mapping(address => DepositBurnCount) depositBurnCounts;
mapping(address => DepositBurnWithdrawCount) depositBurnWithdrawCounts;
mapping(bytes32 => address) public token2address;
struct EthereumDeposit {
......@@ -30,9 +31,11 @@ contract EthereumBank {
uint256 nonce;
}
struct DepositBurnCount {
struct DepositBurnWithdrawCount {
uint256 depositCount;
uint256 burnCount;
uint256 withdrawCount;
}
struct EthereumBurn {
......@@ -67,6 +70,16 @@ contract EthereumBank {
uint256 _nonce
);
event LogEthereumTokenWithdraw(
address _bridgeToken,
string _symbol,
uint256 _amount,
address _ownerFrom,
bytes _ethereumReceiver,
address _proxyReceiver,
uint256 _nonce
);
/*
* @dev: Modifier to make sure this symbol not created now
*/
......@@ -127,9 +140,9 @@ contract EthereumBank {
internal
returns(bytes32)
{
DepositBurnCount memory depositBurnCount = depositBurnCounts[_token];
DepositBurnWithdrawCount memory depositBurnCount = depositBurnWithdrawCounts[_token];
depositBurnCount.depositCount = depositBurnCount.depositCount.add(1);
depositBurnCounts[_token] = depositBurnCount;
depositBurnWithdrawCounts[_token] = depositBurnCount;
bytes32 depositID = keccak256(
abi.encodePacked(
......@@ -217,7 +230,8 @@ contract EthereumBank {
bridgeTokenWhitelist[newBridgeTokenAddress] = true;
bytes32 symHash = keccak256(abi.encodePacked(_symbol));
bridgeTokenCreated[symHash] = true;
depositBurnCounts[newBridgeTokenAddress] = DepositBurnCount(
depositBurnWithdrawCounts[newBridgeTokenAddress] = DepositBurnWithdrawCount(
uint256(0),
uint256(0),
uint256(0));
token2address[symHash] = newBridgeTokenAddress;
......@@ -284,7 +298,7 @@ contract EthereumBank {
* @param _from: The address to be burned from
* @param _ethereumReceiver: The receiver's Ethereum address in bytes.
* @param _ethereumTokenAddress: The token address of ethereum asset issued on chain33
* @param _amount: number of ethereum tokens to be minted
* @param _amount: number of ethereum tokens to be burned
*/
function burnEthereumTokens(
address payable _from,
......@@ -304,13 +318,13 @@ contract EthereumBank {
BridgeToken bridgeTokenInstance = BridgeToken(_ethereumTokenAddress);
bridgeTokenInstance.burnFrom(_from, _amount);
DepositBurnCount memory depositBurnCount = depositBurnCounts[_ethereumTokenAddress];
DepositBurnWithdrawCount memory depositBurnCount = depositBurnWithdrawCounts[_ethereumTokenAddress];
require(
depositBurnCount.burnCount + 1 > depositBurnCount.burnCount,
"burn nonce is not available"
);
depositBurnCount.burnCount = depositBurnCount.burnCount.add(1);
depositBurnCounts[_ethereumTokenAddress] = depositBurnCount;
depositBurnWithdrawCounts[_ethereumTokenAddress] = depositBurnCount;
newEthereumBurn(
_ethereumReceiver,
......@@ -331,6 +345,49 @@ contract EthereumBank {
}
/*
* @dev: withdraw ethereum tokens
*
* @param _from: The address to be withdrew from
* @param _ethereumReceiver: The receiver's Ethereum address in bytes.
* @param _bridgeTokenAddress: The token address of ethereum asset issued on chain33
* @param _amount: number of ethereum tokens to be withdrew
*/
function withdrawEthereumTokens(
address payable _from,
bytes memory _ethereumReceiver,
address _bridgeTokenAddress,
uint256 _amount
)
internal
{
require(proxyReceiver != address(0), "proxy receiver hasn't been set");
// Must be whitelisted bridge token
require(bridgeTokenWhitelist[_bridgeTokenAddress], "Token must be a whitelisted bridge token");
// burn bridge tokens
BridgeToken bridgeTokenInstance = BridgeToken(_bridgeTokenAddress);
bridgeTokenInstance.transferFrom(_from, proxyReceiver, _amount);
DepositBurnWithdrawCount memory wdCount = depositBurnWithdrawCounts[_bridgeTokenAddress];
require(
wdCount.withdrawCount + 1 > wdCount.withdrawCount,
"withdraw nonce is not available"
);
wdCount.withdrawCount = wdCount.withdrawCount.add(1);
depositBurnWithdrawCounts[_bridgeTokenAddress] = wdCount;
emit LogEthereumTokenWithdraw(
_bridgeTokenAddress,
bridgeTokenInstance.symbol(),
_amount,
_from,
_ethereumReceiver,
proxyReceiver,
wdCount.withdrawCount
);
}
/*
* @dev: Checks if an individual EthereumDeposit exists.
*
* @param _id: The unique EthereumDeposit's id.
......
This source diff could not be displayed because it is too large. You can view the blob instead.
......@@ -31,6 +31,7 @@ func Chain33RelayerCmd() *cobra.Command {
TokenAddressCmd(),
MultiSignCmd(),
ResendChain33EventCmd(),
WithdrawFromChain33Cmd(),
)
return cmd
......@@ -415,3 +416,48 @@ func resendChain33Event(cmd *cobra.Command, args []string) {
ctx := jsonclient.NewRPCCtx(rpcLaddr, "Manager.ResendChain33Event", resendChain33EventReq, &res)
ctx.Run()
}
func WithdrawFromChain33Cmd() *cobra.Command {
cmd := &cobra.Command{
Use: "withdraw",
Short: "async withdraw the asset from chain33 to make it unlocked on ethereum",
Run: WithdrawFromChain33,
}
addWithdrawFromChain33Flags(cmd)
return cmd
}
//addWithdrawFromChain33CmdFlags ...
func addWithdrawFromChain33Flags(cmd *cobra.Command) {
cmd.Flags().StringP("key", "k", "", "owner private key for chain33")
_ = cmd.MarkFlagRequired("key")
cmd.Flags().StringP("token", "t", "", "token address")
_ = cmd.MarkFlagRequired("token")
cmd.Flags().StringP("receiver", "r", "", "receiver address on Ethereum")
_ = cmd.MarkFlagRequired("receiver")
cmd.Flags().Float64P("amount", "m", float64(0), "amount")
_ = cmd.MarkFlagRequired("amount")
}
func WithdrawFromChain33(cmd *cobra.Command, args []string) {
rpcLaddr, _ := cmd.Flags().GetString("rpc_laddr")
key, _ := cmd.Flags().GetString("key")
tokenAddr, _ := cmd.Flags().GetString("token")
amount, _ := cmd.Flags().GetFloat64("amount")
receiver, _ := cmd.Flags().GetString("receiver")
d, err := utils.SimpleGetDecimals(tokenAddr)
if err != nil {
fmt.Println("get decimals err")
return
}
para := ebTypes.WithdrawFromChain33{
OwnerKey: key,
TokenAddr: tokenAddr,
Amount: utils.ToWei(amount, d).String(),
EthereumReceiver: receiver,
}
var res rpctypes.Reply
ctx := jsonclient.NewRPCCtx(rpcLaddr, "Manager.WithdrawFromChain33", para, &res)
ctx.Run()
}
......@@ -51,6 +51,7 @@ func EthereumRelayerCmd() *cobra.Command {
MultiSignEthCmd(),
TransferEthCmd(),
ConfigplatformTokenSymbolCmd(),
CfgWithdrawCmd(),
)
return cmd
......@@ -1161,3 +1162,42 @@ func SetEthMultiSignAddr(cmd *cobra.Command, _ []string) {
ctx := jsonclient.NewRPCCtx(rpcLaddr, "Manager.SetEthMultiSignAddr", address, &res)
ctx.Run()
}
func CfgWithdrawCmd() *cobra.Command {
cmd := &cobra.Command{
Use: "cfgWithdraw",
Short: "cfg withdraw fee",
Run: CfgWithdraw,
}
addCfgWithdrawFlags(cmd)
return cmd
}
func addCfgWithdrawFlags(cmd *cobra.Command) {
cmd.Flags().StringP("symbol", "s", "", "symbol")
_ = cmd.MarkFlagRequired("symbol")
cmd.Flags().Float64P("fee", "f", 0, "fee amount")
_ = cmd.MarkFlagRequired("fee")
cmd.Flags().Float64P("amount", "a", 0, "accumulative amount allowed to be withdrew per day")
_ = cmd.MarkFlagRequired("amount")
cmd.Flags().Int8P("decimal", "d", 0, "token decimal")
_ = cmd.MarkFlagRequired("decimal")
}
func CfgWithdraw(cmd *cobra.Command, _ []string) {
rpcLaddr, _ := cmd.Flags().GetString("rpc_laddr")
symbol, _ := cmd.Flags().GetString("symbol")
fee, _ := cmd.Flags().GetFloat64("fee")
amount, _ := cmd.Flags().GetFloat64("amount")
decimal, _ := cmd.Flags().GetInt8("decimal")
req := &ebTypes.CfgWithdrawReq{
Symbol: symbol,
FeeAmount: utils.ToWei(fee, int64(decimal)).String(),
AmountPerDay: utils.ToWei(amount, int64(decimal)).String(),
}
var res rpctypes.Reply
ctx := jsonclient.NewRPCCtx(rpcLaddr, "Manager.CfgWithdraw", req, &res)
ctx.Run()
}
......@@ -25,7 +25,7 @@ func ShowStaticsFlags(cmd *cobra.Command) {
cmd.Flags().StringP("symbol", "s", "", "token symbol(optional)")
cmd.Flags().Int32P("from", "f", 0, "source chain, 0=ethereum, and 1=chain33")
_ = cmd.MarkFlagRequired("from")
cmd.Flags().Int32P("operation", "o", 0, "operation type, 1=burn, and 2=lock")
cmd.Flags().Int32P("operation", "o", 0, "operation type, 1=burn, 2=lock, 3=withdraw")
_ = cmd.MarkFlagRequired("operation")
cmd.Flags().Int32P("status", "u", 0, "show with specified status, default to show all, 1=pending, 2=successful, 3=failed")
cmd.Flags().Int32P("count", "n", 0, "count to show, default to show all")
......
......@@ -64,7 +64,6 @@ done
```
***
### 启动 relayer B C D
......@@ -91,4 +90,41 @@ done
./ebcli_A ethereum import_privatekey -k "${ethValidatorAddrKeya}"
```
#### 运行持续启动 relayer B C D
\ No newline at end of file
***
### 启动代理 relayer proxy
#### 修改 relayer.toml 配置文件
先 cp relayerA 的配置文件, 然后修改以下字段:
|字段|说明|
|----|----|
|pushName|4 个 relayer 不同相同, `sed -i 's/^pushName=.*/pushName="XXX"/g' relayer.toml`|
|ProcessWithDraw|改为 true|
|chain33Host|平行链的 host 地址, 默认: http://localhost:8801, 选任意一个 chain33 平行链地址就可以|
|deploy4chain33|[deploy4chain33] 下字段全部删除, 只需 relayer A 配置一次就可以|
|deploy|[deploy] 下字段全部删除, 只需 relayer A 配置一次就可以|
#### 首次启动 relayer 进行设置
同上...
#### 设置 chain33 代理地址, 及手续费设置
```shell
# 设置 withdraw 的手续费及每日转帐最大值
result=$(${CLIP} ethereum cfgWithdraw -f 1 -s ETH -a 100 -d 18)
Flags:
-a, --amount float 每日最大值
-d, --decimal int8 token 精度
-f, --fee float 手续费
-s, --symbol string symbol
# 设置 chain33 代理地址
${Boss4xCLI} chain33 offline set_withdraw_proxy -c "${chain33BridgeBank}" -a "${chain33Validatorsp}" -k "${chain33DeployKey}" -n "set_withdraw_proxy:${chain33Validatorsp}"
Flags:
-a, --address string withdraw address
-c, --contract string bridgebank contract address
-f, --fee float contract gas fee (optional)
-k, --key string the deployer private key
-n, --note string transaction note info (optional)
```
\ No newline at end of file
......@@ -98,6 +98,7 @@ func main() {
BlockInterval: cfg.EthBlockFetchPeriod,
EthBridgeClaimChan: ethBridgeClaimChan,
Chain33MsgChan: chain33MsgChan,
ProcessWithDraw: cfg.ProcessWithDraw,
}
ethRelayerService := ethRelayer.StartEthereumRelayer(ethStartPara)
......
......@@ -46,6 +46,7 @@ message RelayerConfig {
string bridgeRegistryOnChain33 = 12;
string chainName = 13;
int32 chainID4Chain33 = 14;
bool processWithDraw = 15;
}
message SyncTxReceiptConfig {
......
......@@ -246,3 +246,42 @@ message ResendChain33EventReq {
int64 height = 1;
}
message CfgWithdrawReq {
string symbol = 1;
string feeAmount = 2;
string amountPerDay = 3;
}
message withdrawPara {
string fee = 1;
string amountPerDay = 2;
}
message WithdrawSymbol2Para {
map<string, withdrawPara> symbol2Para = 1;
}
message WithdrawTx {
string chain33Sender = 1;
string ethereumReceiver = 2;
string symbol = 4;
string amount = 5;
int64 nonce = 6;
string txHashOnChain33 = 7;
string txHashOnEthereum = 8;
int32 year = 9;
int32 month = 10;
int32 day = 11;
int32 status = 12;
string statusDescription = 13;
string errorDescription = 14;
}
message WithdrawFromChain33 {
string ownerKey = 1;
string tokenAddr = 2;
string amount = 3;
string ethereumReceiver = 4;
}
......@@ -9,6 +9,7 @@ EthMaturityDegree=10
EthBlockFetchPeriod=5000
BridgeRegistryOnChain33=""
BridgeRegistry=""
ProcessWithDraw=false
[SyncTxConfig]
chain33Host="http://localhost:8801"
......@@ -28,7 +29,7 @@ startSyncHash=""
[deploy4chain33]
#合约部署人员私钥,用于部署合约时签名使用
operatorAddr="14KEKbYtKKQm4wMthSK9J4La4nAiidGozt"
#验证人地址,至少配置3个以上,即大于等于3
#验证人地址,至少配置3个以上,即大于等于3
validatorsAddr=["14KEKbYtKKQm4wMthSK9J4La4nAiidGozt", "13KTf57aCkVVJYNJBXBBveiA5V811SrLcT", "1JQwQWsShTHC4zxHzbUfYQK4kRBriUQdEe", "1NHuKqoKe3hyv52PF8XBAyaTmJWAqA2Jbb"]
#验证人权重
initPowers=[96, 1, 1, 1]
......@@ -36,7 +37,7 @@ initPowers=[96, 1, 1, 1]
[deploy]
#合约部署人员私钥,用于部署合约时签名使用
operatorAddr="0x8afdadfc88a1087c9a1d6c0f5dd04634b87f303a"
#验证人地址,至少配置3个以上,即大于等于3
#验证人地址,至少配置3个以上,即大于等于3
validatorsAddr=["0x92C8b16aFD6d423652559C6E266cBE1c29Bfd84f", "0x0df9a824699bc5878232c9e612fe1a5346a5a368", "0xcb074cb21cdddf3ce9c3c0a7ac4497d633c9d9f1", "0xd9dab021e74ecf475788ed7b61356056b2095830"]
#验证人权重
initPowers=[96, 1, 1, 1]
......
......@@ -51,6 +51,7 @@ type Relayer4Chain33 struct {
unlockChan chan int
bridgeBankEventLockSig string
bridgeBankEventBurnSig string
bridgeBankEventWithdrawSig string
bridgeBankAbi abi.ABI
deployInfo *ebTypes.Deploy
totalTx4RelayEth2chai33 int64
......@@ -235,12 +236,14 @@ func (chain33Relayer *Relayer4Chain33) onNewHeightProc(currentHeight int64) {
evmEventType = events.Chain33EventLogBurn
} else if chain33Relayer.bridgeBankEventLockSig == common.ToHex(evmlog.Topic[0]) {
evmEventType = events.Chain33EventLogLock
} else if chain33Relayer.bridgeBankEventWithdrawSig == common.ToHex(evmlog.Topic[0]) {
evmEventType = events.Chain33EventLogWithdraw
} else {
continue
}
if err := chain33Relayer.handleBurnLockEvent(evmEventType, evmlog.Data, tx.Hash()); nil != err {
errInfo := fmt.Sprintf("Failed to handleBurnLockEvent due to:%s", err.Error())
if err := chain33Relayer.handleBurnLockWithdrawEvent(evmEventType, evmlog.Data, tx.Hash()); nil != err {
errInfo := fmt.Sprintf("Failed to handleBurnLockWithdrawEvent due to:%s", err.Error())
panic(errInfo)
}
}
......@@ -251,8 +254,8 @@ func (chain33Relayer *Relayer4Chain33) onNewHeightProc(currentHeight int64) {
}
// handleBurnLockMsg : parse event data as a Chain33Msg, package it into a ProphecyClaim, then relay tx to the Ethereum Network
func (chain33Relayer *Relayer4Chain33) handleBurnLockEvent(evmEventType events.Chain33EvmEvent, data []byte, chain33TxHash []byte) error {
relayerLog.Info("handleBurnLockEvent", "Received tx with hash", ethCommon.Bytes2Hex(chain33TxHash))
func (chain33Relayer *Relayer4Chain33) handleBurnLockWithdrawEvent(evmEventType events.Chain33EvmEvent, data []byte, chain33TxHash []byte) error {
relayerLog.Info("handleBurnLockWithdrawEvent", "Received tx with hash", ethCommon.Bytes2Hex(chain33TxHash))
// Parse the witnessed event's data into a new Chain33Msg
chain33Msg, err := events.ParseBurnLock4chain33(evmEventType, data, chain33Relayer.bridgeBankAbi, chain33TxHash)
......@@ -306,11 +309,13 @@ func (chain33Relayer *Relayer4Chain33) ResendChain33Event(height int64) (err err
evmEventType = events.Chain33EventLogBurn
} else if chain33Relayer.bridgeBankEventLockSig == common.ToHex(evmlog.Topic[0]) {
evmEventType = events.Chain33EventLogLock
} else if chain33Relayer.bridgeBankEventWithdrawSig == common.ToHex(evmlog.Topic[0]) {
evmEventType = events.Chain33EventLogWithdraw
} else {
continue
}
if err := chain33Relayer.handleBurnLockEvent(evmEventType, evmlog.Data, tx.Hash()); nil != err {
if err := chain33Relayer.handleBurnLockWithdrawEvent(evmEventType, evmlog.Data, tx.Hash()); nil != err {
return err
}
}
......@@ -634,3 +639,9 @@ func (chain33Relayer *Relayer4Chain33) SetMultiSignAddr(address string) {
chain33Relayer.setMultiSignAddress(address)
}
func (chain33Relayer *Relayer4Chain33) WithdrawFromChain33(ownerPrivateKey, tokenAddr, ethereumReceiver, amount string) (string, error) {
bn := big.NewInt(1)
bn, _ = bn.SetString(utils.TrimZeroAndDot(amount), 10)
return withdrawAsync(ownerPrivateKey, tokenAddr, ethereumReceiver, bn.Int64(), chain33Relayer.bridgeBankAddr, chain33Relayer.chainName, chain33Relayer.rpcLaddr)
}
......@@ -20,8 +20,11 @@ func (relayer *Relayer4Chain33) prePareSubscribeEvent() {
relayer.bridgeBankEventLockSig = contractABI.Events[eventName].ID.Hex()
eventName = events.Chain33EventLogBurn.String()
relayer.bridgeBankEventBurnSig = contractABI.Events[eventName].ID.Hex()
eventName = events.Chain33EventLogWithdraw.String()
relayer.bridgeBankEventWithdrawSig = contractABI.Events[eventName].ID.Hex()
relayer.bridgeBankAbi = contractABI
relayerLog.Info("prePareSubscribeEvent", "bridgeBankEventLockSig", relayer.bridgeBankEventLockSig,
"bridgeBankEventBurnSig", relayer.bridgeBankEventBurnSig)
"bridgeBankEventBurnSig", relayer.bridgeBankEventBurnSig, "bridgeBankEventWithdrawSig", relayer.bridgeBankEventWithdrawSig)
}
......@@ -8,7 +8,6 @@ import (
dbm "github.com/33cn/chain33/common/db"
"github.com/33cn/chain33/types"
"github.com/33cn/plugin/plugin/dapp/cross2eth/ebrelayer/utils"
"github.com/pkg/errors"
)
// SeqType
......@@ -106,13 +105,17 @@ func (syncTx *EVMTxLogs) SaveAndSyncTxs2Relayer() {
// 处理输入流程
func (syncTx *EVMTxLogs) dealEVMTxLogs(evmTxLogsInBlks *types.EVMTxLogsInBlks) {
count, start, evmTxLogsParsed, err := parseEvmTxLogsInBlks(evmTxLogsInBlks, syncTx.seqNum)
if err != nil {
resultCh <- err
count, start, evmTxLogsParsed := parseEvmTxLogsInBlks(evmTxLogsInBlks, syncTx.seqNum)
txReceiptCount := len(evmTxLogsParsed)
//重复注册推送接收保护,允许同一个中继服务在使用一段时间后,使用不同的推送名字重新进行注册,这样重复推送忽略就可以
//需要进行ack,否则该节点的推送将会停止
if 0 == txReceiptCount {
resultCh <- nil
return
}
var height int64
for i := 0; i < count; i++ {
for i := 0; i < txReceiptCount; i++ {
txsPerBlock := evmTxLogsParsed[i]
if txsPerBlock.AddDelType == SeqTypeAdd {
syncTx.setTxLogsPerBlock(txsPerBlock)
......@@ -206,7 +209,7 @@ func (syncTx *EVMTxLogs) delTxReceipts(height int64) {
}
// 检查输入是否有问题, 并解析输入
func parseEvmTxLogsInBlks(evmTxLogs *types.EVMTxLogsInBlks, seqNumLast int64) (count int, start int64, txsWithReceipt []*types.EVMTxLogPerBlk, err error) {
func parseEvmTxLogsInBlks(evmTxLogs *types.EVMTxLogsInBlks, seqNumLast int64) (count int, start int64, txsWithReceipt []*types.EVMTxLogPerBlk) {
count = len(evmTxLogs.Logs4EVMPerBlk)
txsWithReceipt = make([]*types.EVMTxLogPerBlk, 0)
start = math.MaxInt64
......@@ -230,9 +233,9 @@ func parseEvmTxLogsInBlks(evmTxLogs *types.EVMTxLogsInBlks, seqNumLast int64) (c
"height", evmTxLogs.Logs4EVMPerBlk[i].Height, "seqOpType", seqOperationType[evmTxLogs.Logs4EVMPerBlk[i].AddDelType-1])
}
if len(txsWithReceipt) != count {
err = errors.New("duplicate block's tx logs")
return
if 0 == len(txsWithReceipt) {
log.Error("parseEvmTxLogsInBlks", "the valid number of tx receipt is", 0)
}
return
}
......@@ -646,3 +646,48 @@ func sendQuery(rpcAddr, funcName string, request types.Message, result proto.Mes
}
return true
}
func withdrawAsync(ownerPrivateKeyStr, tokenAddrstr, ethereumReceiver string, amount int64, bridgeBankAddr string, chainName, rpcURL string) (string, error) {
var driver secp256k1.Driver
privateKeySli, err := chain33Common.FromHex(ownerPrivateKeyStr)
if nil != err {
return "", err
}
ownerPrivateKey, err := driver.PrivKeyFromBytes(privateKeySli)
if nil != err {
return "", err
}
approveTxHash, err := approve(ownerPrivateKey, tokenAddrstr, bridgeBankAddr, chainName, rpcURL, amount)
if err != nil {
chain33txLog.Error("withdrawAsync", "failed to send approve tx due to:", err.Error())
return "", err
}
chain33txLog.Debug("withdrawAsync", "approve with tx hash", approveTxHash)
withdrawTxHash, err := withdrawViaProxy(ownerPrivateKey, bridgeBankAddr, ethereumReceiver, tokenAddrstr, chainName, rpcURL, amount)
if err != nil {
chain33txLog.Error("withdrawAsync", "failed to send withdraw tx due to:", err.Error())
return "", err
}
chain33txLog.Debug("withdrawAsync", "withdraw with tx hash", withdrawTxHash)
return withdrawTxHash, err
}
func withdrawViaProxy(privateKey chain33Crypto.PrivKey, contractAddr, ethereumReceiver, ethereumTokenAddress, chainName, rpcURL string, amount int64) (string, error) {
//function withdrawViaProxy(
// bytes memory _ethereumReceiver,
// address _bridgeTokenAddress,
// uint256 _amount
//)
parameter := fmt.Sprintf("withdrawViaProxy(%s, %s, %d)", ethereumReceiver, ethereumTokenAddress, amount)
note := parameter
_, packData, err := evmAbi.Pack(parameter, generated.BridgeBankABI, false)
if nil != err {
chain33txLog.Info("withdraw", "Failed to do abi.Pack due to:", err.Error())
return "", err
}
return sendEvmTx(privateKey, contractAddr, chainName, rpcURL, note, packData, 0)
}
......@@ -29,7 +29,7 @@ import (
var (
chain33Addr = "14KEKbYtKKQm4wMthSK9J4La4nAiidGozt"
//ethAddr = "0x92C8b16aFD6d423652559C6E266cBE1c29Bfd84f"
ethTokenAddr = "0x0000000000000000000000000000000000000000"
//EthNullAddr = "0x0000000000000000000000000000000000000000"
)
type suiteContracts struct {
......@@ -81,7 +81,7 @@ func (c *suiteContracts) Test_LogLockToEthBridgeClaim() {
event := &events.LockEvent{
From: c.para.InitValidators[0],
To: to,
Token: common.HexToAddress(ethTokenAddr),
Token: common.HexToAddress(EthNullAddr),
Symbol: "eth",
Value: big.NewInt(10000 * 10000 * 10000),
Nonce: big.NewInt(1),
......@@ -91,7 +91,7 @@ func (c *suiteContracts) Test_LogLockToEthBridgeClaim() {
assert.NotEmpty(c.T(), witnessClaim)
assert.Equal(c.T(), witnessClaim.EthereumChainID, int64(1))
assert.Equal(c.T(), witnessClaim.BridgeBrankAddr, c.x2EthDeployInfo.BridgeBank.Address.String())
assert.Equal(c.T(), witnessClaim.TokenAddr, ethTokenAddr)
assert.Equal(c.T(), witnessClaim.TokenAddr, EthNullAddr)
assert.Equal(c.T(), witnessClaim.Symbol, event.Symbol)
assert.Equal(c.T(), witnessClaim.EthereumSender, event.From.String())
//assert.Equal(c.T(), witnessClaim.Chain33Receiver, string(event.To))
......@@ -110,7 +110,7 @@ func (c *suiteContracts) Test_LogBurnToEthBridgeClaim() {
event := &events.BurnEvent{
OwnerFrom: c.para.InitValidators[0],
Chain33Receiver: to,
Token: common.HexToAddress(ethTokenAddr),
Token: common.HexToAddress(EthNullAddr),
Symbol: "bty",
Amount: big.NewInt(100),
Nonce: big.NewInt(2),
......@@ -120,7 +120,7 @@ func (c *suiteContracts) Test_LogBurnToEthBridgeClaim() {
assert.NotEmpty(c.T(), witnessClaim)
assert.Equal(c.T(), witnessClaim.EthereumChainID, int64(1))
assert.Equal(c.T(), witnessClaim.BridgeBrankAddr, c.x2EthDeployInfo.BridgeBank.Address.String())
assert.Equal(c.T(), witnessClaim.TokenAddr, ethTokenAddr)
assert.Equal(c.T(), witnessClaim.TokenAddr, EthNullAddr)
assert.Equal(c.T(), witnessClaim.Symbol, event.Symbol)
assert.Equal(c.T(), witnessClaim.EthereumSender, event.OwnerFrom.String())
//assert.Equal(c.T(), witnessClaim.Chain33Receiver, string(event.Chain33Receiver))
......
......@@ -9,9 +9,7 @@ import (
//const ...
const (
X2Eth = "x2ethereum"
BurnAction = "Chain33ToEthBurn"
LockAction = "Chain33ToEthLock"
EthNullAddr = "0x0000000000000000000000000000000000000000"
)
// OracleClaim : contains data required to make an OracleClaim
......@@ -31,3 +29,17 @@ type ProphecyClaim struct {
Amount *big.Int
chain33TxHash []byte
}
type WithdrawStatus int32
const (
WDError = WithdrawStatus(1)
WDPending = WithdrawStatus(2)
WDFailed = WithdrawStatus(3)
WDSuccess = WithdrawStatus(4)
)
// 此处的名字命令不能随意改动,需要与合约event中的命名完全一致
func (d WithdrawStatus) String() string {
return [...]string{"undefined", "Error,not submitted to ethereum", "Pending", "Submitted to ethereum, but Failed", "Success"}[d]
}
......@@ -8,6 +8,8 @@ import (
"sync"
"time"
"github.com/ethereum/go-ethereum/core/types"
"github.com/33cn/plugin/plugin/dapp/cross2eth/ebrelayer/relayer/ethereum/ethinterface"
"github.com/ethereum/go-ethereum"
"github.com/ethereum/go-ethereum/accounts/abi/bind"
......@@ -145,3 +147,40 @@ func GetEthTxStatus(client ethinterface.EthClientSpec, txhash common.Hash) strin
return status
}
func NewTransferTx(clientSpec ethinterface.EthClientSpec, from, to common.Address, input []byte, value *big.Int) (*types.Transaction, error) {
price, err := clientSpec.SuggestGasPrice(context.Background())
if err != nil {
return nil, err
}
nonce, err := getNonce(from, clientSpec)
if err != nil {
return nil, err
}
var gas uint64 = 21000
if input != nil {
//var msg ethereum.CallMsg
//msg.To = &to
//msg.Data = input
//gas, err = clientSpec.EstimateGas(context.Background(), msg)
//if err != nil {
// //return nil,err
// txslog.Error("handleLogWithdraw", "EstimateGas err", err)
// gas = 80000
//}
//实际测试"cumulativeGasUsed": "0xdc82",
gas = uint64(80000)
}
ntx := types.NewTx(&types.LegacyTx{
Nonce: nonce.Uint64(),
GasPrice: price,
To: &to,
Data: input,
Value: value,
Gas: gas,
})
return ntx, nil
}
......@@ -4,6 +4,7 @@ import (
"encoding/json"
"errors"
"fmt"
"math/big"
"github.com/ethereum/go-ethereum/common"
......@@ -27,6 +28,9 @@ var (
ethLockTxUpdateTxIndex = []byte("eth-ethLockTxUpdateTxIndex")
ethBurnTxUpdateTxIndex = []byte("eth-ethBurnTxUpdateTxIndex")
multiSignAddressPrefix = []byte("eth-multiSignAddress")
withdrawParaKey = []byte("eth-withdrawPara")
withdrawTokenPrefix = []byte("eth-withdrawToken")
withdrawTokenListPrefix = []byte("eth-withdrawTokenList")
)
func ethTokenSymbol2AddrKey(symbol string) []byte {
......@@ -383,3 +387,102 @@ func (ethRelayer *Relayer4Ethereum) getMultiSignAddress() string {
}
return string(bytes)
}
func (ethRelayer *Relayer4Ethereum) setWithdrawFee(symbol2Para map[string]*ebTypes.WithdrawPara) error {
withdrawSymbol2Fee := &ebTypes.WithdrawSymbol2Para{
Symbol2Para: symbol2Para,
}
bytes := chain33Types.Encode(withdrawSymbol2Fee)
return ethRelayer.db.Set(withdrawParaKey, bytes)
}
func (ethRelayer *Relayer4Ethereum) restoreWithdrawFee() map[string]*ebTypes.WithdrawPara {
bytes, _ := ethRelayer.db.Get(withdrawParaKey)
if 0 == len(bytes) {
result := make(map[string]*ebTypes.WithdrawPara)
return result
}
var withdrawSymbol2Para ebTypes.WithdrawSymbol2Para
if err := chain33Types.Decode(bytes, &withdrawSymbol2Para); nil != err {
result := make(map[string]*ebTypes.WithdrawPara)
return result
}
return withdrawSymbol2Para.Symbol2Para
}
func (ethRelayer *Relayer4Ethereum) restoreWithdrawFeeInINt() map[string]*WithdrawFeeAndQuota {
withdrawPara := ethRelayer.restoreWithdrawFee()
res := make(map[string]*WithdrawFeeAndQuota)
for symbol, para := range withdrawPara {
feeInt, _ := big.NewInt(0).SetString(para.Fee, 10)
amountPerDayInt, _ := big.NewInt(0).SetString(para.AmountPerDay, 10)
res[symbol] = &WithdrawFeeAndQuota{
Fee: feeInt,
AmountPerDay: amountPerDayInt,
}
}
return res
}
func calcWithdrawKey(chain33Sender, symbol string, year, month, day int, nonce int64) []byte {
return []byte(fmt.Sprintf("%s-%s-%s-%d-%d-%d-%d", withdrawTokenPrefix, chain33Sender, symbol, year, month, day, nonce))
}
func calcWithdrawKeyPrefix(chain33Sender, symbol string, year, month, day int) []byte {
return []byte(fmt.Sprintf("%s-%s-%s-%d-%d-%d", withdrawTokenPrefix, chain33Sender, symbol, year, month, day))
}
func calcWithdrawListKey(nonce int64) []byte {
return []byte(fmt.Sprintf("%s-%d", withdrawTokenListPrefix, nonce))
}
func (ethRelayer *Relayer4Ethereum) setWithdraw(withdrawTx *ebTypes.WithdrawTx) error {
chain33Sender := withdrawTx.Chain33Sender
symbol := withdrawTx.Symbol
year := withdrawTx.Year
month := withdrawTx.Month
day := withdrawTx.Day
key := calcWithdrawKey(chain33Sender, symbol, int(year), int(month), int(day), withdrawTx.Nonce)
bytes := chain33Types.Encode(withdrawTx)
if err := ethRelayer.db.Set(key, bytes); nil != err {
return err
}
//保存按照次序提币的交易,方便查询
listKey := calcWithdrawListKey(withdrawTx.Nonce)
listData := key
return ethRelayer.db.Set(listKey, listData)
}
func (ethRelayer *Relayer4Ethereum) getWithdrawsWithinSameDay(withdrawTx *ebTypes.WithdrawTx) (*big.Int, error) {
chain33Sender := withdrawTx.Chain33Sender
symbol := withdrawTx.Symbol
year := withdrawTx.Year
month := withdrawTx.Month
day := withdrawTx.Day
prefix := calcWithdrawKeyPrefix(chain33Sender, symbol, int(year), int(month), int(day))
helper := dbm.NewListHelper(ethRelayer.db)
datas := helper.List(prefix, nil, 100, dbm.ListASC)
if nil == datas {
return big.NewInt(0), nil
}
withdrawTotal := big.NewInt(0)
for _, data := range datas {
var info ebTypes.WithdrawTx
err := chain33Types.Decode(data, &info)
if nil != err {
return big.NewInt(0), err
}
AmountInt, _ := big.NewInt(0).SetString(info.Amount, 0)
withdrawTotal.Add(withdrawTotal, AmountInt)
}
return withdrawTotal, nil
}
......@@ -18,11 +18,13 @@ const (
Chain33EventLogLock
//在chain33的evm合约中产生了burn事件
Chain33EventLogBurn
//在chain33的evm合约中产生了withdraw事件
Chain33EventLogWithdraw
)
// String : returns the event type as a string
func (d Chain33EvmEvent) String() string {
return [...]string{"unknown-event", "LogLock", "LogEthereumTokenBurn"}[d]
return [...]string{"unknown-event", "LogLock", "LogEthereumTokenBurn", "LogEthereumTokenWithdraw"}[d]
}
// Chain33Msg : contains data from MsgBurn and MsgLock events
......@@ -47,6 +49,17 @@ type LockEventOnChain33 struct {
Nonce *big.Int
}
// 发生在chain33 evm上的withdraw事件,当用户发起通过代理人提币交易时,则弹射出该事件信息
type WithdrawEventOnChain33 struct {
BridgeToken chain33EvmCommon.Hash160Address
Symbol string
Amount *big.Int
OwnerFrom chain33EvmCommon.Hash160Address
EthereumReceiver []byte
ProxyReceiver chain33EvmCommon.Hash160Address
Nonce *big.Int
}
// 发生在chain33evm上的burn事件,当eth/erc20资产需要提币回到以太坊链上时,会发生该种事件
type BurnEventOnChain33 struct {
Token chain33EvmCommon.Hash160Address
......@@ -94,12 +107,29 @@ func UnpackChain33LogBurn(contractAbi abi.ABI, eventName string, eventData []byt
return burnEvent, nil
}
// ParseBurnLock4chain33 ParseBurnLockTxReceipt : parses data from a Burn/Lock event witnessed on chain33 into a Chain33Msg struct
func UnpackLogWithdraw(contractAbi abi.ABI, eventName string, eventData []byte) (withdrawEvent *WithdrawEventOnChain33, err error) {
withdrawEvent = &WithdrawEventOnChain33{}
err = contractAbi.UnpackIntoInterface(withdrawEvent, eventName, eventData)
if err != nil {
eventsLog.Error("UnpackLogWithdraw", "Failed to unpack abi due to:", err.Error())
return nil, err
}
eventsLog.Info("UnpackLogWithdraw", "bridge token addr on chain33 evm", withdrawEvent.BridgeToken.ToAddress().String(),
"symbol", withdrawEvent.Symbol,
"Amount", withdrawEvent.Amount.String(),
"Owner address from chain33", withdrawEvent.OwnerFrom.ToAddress().String(),
"EthereumReceiver", common.BytesToAddress(withdrawEvent.EthereumReceiver).String(),
"ProxyReceiver", withdrawEvent.ProxyReceiver.ToAddress().String(),
"nonce", withdrawEvent.Nonce.String())
return withdrawEvent, nil
}
// ParseBurnLock4chain33 ParseBurnLockTxReceipt : parses data from a Burn/Lock/Withdraw event witnessed on chain33 into a Chain33Msg struct
func ParseBurnLock4chain33(evmEventType Chain33EvmEvent, data []byte, bridgeBankAbi abi.ABI, chain33TxHash []byte) (*Chain33Msg, error) {
if Chain33EventLogLock == evmEventType {
lockEvent, err := UnpackChain33LogLock(bridgeBankAbi, evmEventType.String(), data)
if nil != err {
eventsLog.Error("UnpackChain33LogLock", "failed due to", err.Error())
return nil, err
}
......@@ -118,7 +148,6 @@ func ParseBurnLock4chain33(evmEventType Chain33EvmEvent, data []byte, bridgeBank
} else if Chain33EventLogBurn == evmEventType {
burnEvent, err := UnpackChain33LogBurn(bridgeBankAbi, evmEventType.String(), data)
if nil != err {
eventsLog.Error("UnpackChain33LogBurn", "failed due to", err.Error())
return nil, err
}
......@@ -133,6 +162,24 @@ func ParseBurnLock4chain33(evmEventType Chain33EvmEvent, data []byte, bridgeBank
Nonce: burnEvent.Nonce.Int64(),
}
return chain33Msg, nil
} else if Chain33EventLogWithdraw == evmEventType {
burnEvent, err := UnpackLogWithdraw(bridgeBankAbi, evmEventType.String(), data)
if nil != err {
return nil, err
}
chain33Msg := &Chain33Msg{
ClaimType: ClaimTypeWithdraw,
Chain33Sender: burnEvent.OwnerFrom.ToAddress(),
EthereumReceiver: common.BytesToAddress(burnEvent.EthereumReceiver),
TokenContractAddress: burnEvent.BridgeToken.ToAddress(),
Symbol: burnEvent.Symbol,
Amount: burnEvent.Amount,
TxHash: chain33TxHash,
Nonce: burnEvent.Nonce.Int64(),
}
return chain33Msg, nil
}
return nil, errors.New("unknown-event")
......
......@@ -13,6 +13,7 @@ const (
ClaimTypeUnknown = ClaimType(0)
ClaimTypeBurn = ClaimType(1)
ClaimTypeLock = ClaimType(2)
ClaimTypeWithdraw = ClaimType(3)
)
const (
......@@ -30,5 +31,5 @@ func (d Event) String() string {
}
func (d ClaimType) String() string {
return [...]string{"unknown-LOG", "burn", "lock"}[d]
return [...]string{"unknown-LOG", "burn", "lock", "withdraw"}[d]
}
......@@ -1075,3 +1075,37 @@ func (manager *Manager) SetEthMultiSignAddr(multiSignAddr string, result *interf
}
return nil
}
func (manager *Manager) CfgWithdraw(cfgWithdrawReq *relayerTypes.CfgWithdrawReq, result *interface{}) error {
manager.mtx.Lock()
defer manager.mtx.Unlock()
if err := manager.checkPermission(); nil != err {
return err
}
err := manager.ethRelayer.CfgWithdraw(cfgWithdrawReq.Symbol, cfgWithdrawReq.FeeAmount, cfgWithdrawReq.AmountPerDay)
resultCfg := true
if err != nil {
resultCfg = false
}
*result = rpctypes.Reply{
IsOk: resultCfg,
}
return nil
}
func (manager *Manager) WithdrawFromChain33(burn relayerTypes.BurnFromChain33, result *interface{}) error {
manager.mtx.Lock()
defer manager.mtx.Unlock()
if err := manager.checkPermission(); nil != err {
return err
}
txhash, err := manager.chain33Relayer.WithdrawFromChain33(burn.OwnerKey, burn.TokenAddr, burn.EthereumReceiver, burn.Amount)
if nil != err {
return err
}
*result = rpctypes.Reply{
IsOk: true,
Msg: txhash,
}
return nil
}
This source diff could not be displayed because it is too large. You can view the blob instead.
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