Skip to content

Commit b607b9c

Browse files
committed
Merge branch 'hotfix_submitter_hang'
* hotfix_submitter_hang: choose simple strategy, drop current claim if a tx is not verified in time setting version to 0.2.1 working rebroadcast tx add timeout to tx watcher
2 parents bc8a75f + a60f58d commit b607b9c

7 files changed

Lines changed: 86 additions & 10 deletions

File tree

compile.sh

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,5 +11,5 @@ mustrun build/env.sh go get -v github.com/ethereum/go-ethereum
1111
mustrun build/env.sh go get -v golang.org/x/crypto/ssh/terminal
1212
mustrun build/env.sh go get -v gopkg.in/urfave/cli.v1
1313
echo "Compiling SmartPool client..."
14-
mustrun build/env.sh go build -o smartpool cmd/ropsten/ropsten.go
14+
mustrun build/env.sh go build -ldflags -s -o smartpool cmd/ropsten/ropsten.go
1515
echo "Done. You can run SmartPool by ./smartpool --help"

ethereum/geth/geth_contract_client.go

Lines changed: 20 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -57,9 +57,13 @@ func (cc *GethContractClient) Register(paymentAddress common.Address) error {
5757
return err
5858
}
5959
smartpool.Output.Printf("Registering address %s to SmartPool contract by tx: %s\n", paymentAddress.Hex(), tx.Hash().Hex())
60-
errCode, errInfo := NewTxWatcher(
60+
errCode, errInfo, err := NewTxWatcher(
6161
tx, cc.node, blockNo, RegisterEventTopic,
6262
cc.sender.Big()).Wait()
63+
if err != nil {
64+
smartpool.Output.Printf("Tx: %s was not approved by the network in time.\n", tx.Hash().Hex())
65+
return err
66+
}
6367
if errCode.Cmp(common.Big0) != 0 {
6468
smartpool.Output.Printf("Error code: 0x%s - Error info: 0x%s\n", errCode.Text(16), errInfo.Text(16))
6569
return errors.New(ErrorMsg(errCode, errInfo))
@@ -94,9 +98,13 @@ func (cc *GethContractClient) SubmitClaim(
9498
smartpool.Output.Printf("Submitting claim failed. Error: %s\n", err)
9599
return err
96100
}
97-
errCode, errInfo := NewTxWatcher(
101+
errCode, errInfo, err := NewTxWatcher(
98102
tx, cc.node, blockNo, SubmitClaimEventTopic,
99103
cc.sender.Big()).Wait()
104+
if err != nil {
105+
smartpool.Output.Printf("Tx: %s was not approved by the network in time.\n", tx.Hash().Hex())
106+
return err
107+
}
100108
if errCode.Cmp(common.Big0) != 0 {
101109
smartpool.Output.Printf("Error code: 0x%s - Error info: 0x%s\n", errCode.Text(16), errInfo.Text(16))
102110
return errors.New(ErrorMsg(errCode, errInfo))
@@ -124,9 +132,13 @@ func (cc *GethContractClient) VerifyClaim(
124132
smartpool.Output.Printf("Verifying claim failed. Error: %s\n", err)
125133
return err
126134
}
127-
errCode, errInfo := NewTxWatcher(
135+
errCode, errInfo, err := NewTxWatcher(
128136
tx, cc.node, blockNo, VerifyClaimEventTopic,
129137
cc.sender.Big()).Wait()
138+
if err != nil {
139+
smartpool.Output.Printf("Tx: %s was not approved by the network in time.\n", tx.Hash().Hex())
140+
return err
141+
}
130142
if errCode.Cmp(common.Big0) != 0 {
131143
smartpool.Output.Printf("Error code: 0x%s - Error info: 0x%s\n", errCode.Text(16), errInfo.Text(16))
132144
return errors.New(ErrorMsg(errCode, errInfo))
@@ -146,9 +158,13 @@ func (cc *GethContractClient) SetEpochData(merkleRoot []*big.Int, fullSizeIn128R
146158
smartpool.Output.Printf("Setting epoch data. Error: %s\n", err)
147159
return err
148160
}
149-
errCode, errInfo := NewTxWatcher(
161+
errCode, errInfo, err := NewTxWatcher(
150162
tx, cc.node, blockNo, SetEpochDataEventTopic,
151163
cc.sender.Big()).Wait()
164+
if err != nil {
165+
smartpool.Output.Printf("Tx: %s was not approved by the network in time.\n", tx.Hash().Hex())
166+
return err
167+
}
152168
if errCode.Cmp(common.Big0) != 0 {
153169
smartpool.Output.Printf("Error code: 0x%s - Error info: 0x%s\n", errCode.Text(16), errInfo.Text(16))
154170
return errors.New(ErrorMsg(errCode, errInfo))

ethereum/geth/rpc.go

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -233,6 +233,13 @@ func (g *GethRPC) SetExtradata(extradata string) error {
233233
return err
234234
}
235235

236+
func (g *GethRPC) Broadcast(data []byte) (common.Hash, error) {
237+
hash := common.Hash{}
238+
err := g.client.Call(&hash, "eth_sendRawTransaction",
239+
fmt.Sprintf("0x%s", common.Bytes2Hex(data)))
240+
return hash, err
241+
}
242+
236243
func NewGethRPC(endpoint, contractAddr, extraData string, diff *big.Int) (*GethRPC, error) {
237244
client, err := rpc.DialHTTP(endpoint)
238245
if err != nil {

ethereum/geth/txwatcher.go

Lines changed: 41 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,11 @@
11
package geth
22

33
import (
4+
"bytes"
5+
"errors"
6+
"github.com/SmartPool/smartpool-client"
47
"github.com/SmartPool/smartpool-client/ethereum"
8+
"github.com/ethereum/go-ethereum/common"
59
"github.com/ethereum/go-ethereum/core/types"
610
"math/big"
711
"time"
@@ -36,10 +40,44 @@ func (tw *TxWatcher) loop() {
3640
}
3741
}
3842

39-
func (tw *TxWatcher) Wait() (*big.Int, *big.Int) {
43+
func (tw *TxWatcher) WaitAndRetry() (*big.Int, *big.Int, error) {
44+
errCode, errInfo, err := tw.Wait()
45+
if err != nil {
46+
smartpool.Output.Printf("Rebroadcast tx: %s...\n", tw.tx.Hash().Hex())
47+
buff := bytes.NewBuffer([]byte{})
48+
err = tw.tx.EncodeRLP(buff)
49+
if err != nil {
50+
return nil, nil, err
51+
}
52+
hash, err := tw.node.Broadcast(buff.Bytes())
53+
if err != nil {
54+
smartpool.Output.Printf("Broadcast error: %s\n", err)
55+
return nil, nil, err
56+
}
57+
if hash.Big().Cmp(common.Big0) == 0 {
58+
return nil, nil, errors.New("Rebroadcast tx got 0 tx hash. This is not supposed to happend.")
59+
}
60+
return tw.Wait()
61+
} else {
62+
return errCode, errInfo, err
63+
}
64+
}
65+
66+
func (tw *TxWatcher) Wait() (*big.Int, *big.Int, error) {
67+
timeout := make(chan bool, 1)
4068
go tw.loop()
41-
<-tw.verChan
42-
return tw.node.GetLog(tw.block, tw.event, tw.sender)
69+
go func() {
70+
time.Sleep(10 * time.Minute)
71+
timeout <- true
72+
}()
73+
select {
74+
case <-tw.verChan:
75+
break
76+
case <-timeout:
77+
return nil, nil, errors.New("timeout error")
78+
}
79+
errCode, errInfo := tw.node.GetLog(tw.block, tw.event, tw.sender)
80+
return errCode, errInfo, nil
4381
}
4482

4583
func NewTxWatcher(

ethereum/rpc_client.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,4 +18,5 @@ type RPCClient interface {
1818
GetLog(from *big.Int, event *big.Int, sender *big.Int) (*big.Int, *big.Int)
1919
SetEtherbase(etherbase common.Address) error
2020
SetExtradata(extradata string) error
21+
Broadcast(raw []byte) (common.Hash, error)
2122
}

protocol/smartpool.go

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -164,6 +164,20 @@ func (sp *SmartPool) Submit() (bool, error) {
164164
return true, nil
165165
}
166166

167+
func (sp *SmartPool) shouldStop(err error) bool {
168+
if err == nil {
169+
return false
170+
}
171+
if err.Error() == "timeout error" {
172+
smartpool.Output.Printf("The tx might not be verified. Current claim is dropped. Continue with next claim.\n")
173+
return false
174+
} else if sp.HotStop {
175+
return true
176+
} else {
177+
return false
178+
}
179+
}
180+
167181
func (sp *SmartPool) actOnTick() {
168182
defer func() {
169183
if r := recover(); r != nil {
@@ -183,7 +197,7 @@ func (sp *SmartPool) actOnTick() {
183197
sp.PoolMonitor.ContractAddress().Hex(),
184198
sp.PoolMonitor.ContractAddress().Hex())
185199
}
186-
if err != nil && sp.HotStop {
200+
if sp.shouldStop(err) {
187201
smartpool.Output.Printf("SmartPool stopped. If you want SmartPool to keep running, please use \"--no-hot-stop\" to disable Hot Stop mode.\n")
188202
break
189203
}

version.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
11
package smartpool
22

3-
const VERSION = "0.2.0"
3+
const VERSION = "0.2.1"

0 commit comments

Comments
 (0)