@@ -54,7 +54,10 @@ const (
54
54
MaxTxStatus = 256 // Amount of transactions to queried per request
55
55
)
56
56
57
- var errTooManyInvalidRequest = errors .New ("too many invalid requests made" )
57
+ var (
58
+ errTooManyInvalidRequest = errors .New ("too many invalid requests made" )
59
+ errFullClientPool = errors .New ("client pool is full" )
60
+ )
58
61
59
62
// serverHandler is responsible for serving light client and process
60
63
// all incoming light requests.
@@ -124,23 +127,26 @@ func (h *serverHandler) handle(p *peer) error {
124
127
}
125
128
defer p .fcClient .Disconnect ()
126
129
130
+ // Disconnect the inbound peer if it's rejected by clientPool
131
+ if ! h .server .clientPool .connect (p , 0 ) {
132
+ p .Log ().Debug ("Light Ethereum peer registration failed" , "err" , errFullClientPool )
133
+ return errFullClientPool
134
+ }
127
135
// Register the peer locally
128
136
if err := h .server .peers .Register (p ); err != nil {
137
+ h .server .clientPool .disconnect (p )
129
138
p .Log ().Error ("Light Ethereum peer registration failed" , "err" , err )
130
139
return err
131
140
}
132
141
clientConnectionGauge .Update (int64 (h .server .peers .Len ()))
133
142
134
- // add dummy balance tracker for tests
135
- if p .balanceTracker == nil {
136
- p .balanceTracker = & balanceTracker {}
137
- p .balanceTracker .init (& mclock.System {}, 1 )
138
- }
143
+ var wg sync.WaitGroup // Wait group used to track all in-flight task routines.
139
144
140
145
connectedAt := mclock .Now ()
141
146
defer func () {
142
- p . balanceTracker = nil
147
+ wg . Wait () // Ensure all background task routines have exited.
143
148
h .server .peers .Unregister (p .id )
149
+ h .server .clientPool .disconnect (p )
144
150
clientConnectionGauge .Update (int64 (h .server .peers .Len ()))
145
151
connectionTimer .Update (time .Duration (mclock .Now () - connectedAt ))
146
152
}()
@@ -153,7 +159,7 @@ func (h *serverHandler) handle(p *peer) error {
153
159
return err
154
160
default :
155
161
}
156
- if err := h .handleMsg (p ); err != nil {
162
+ if err := h .handleMsg (p , & wg ); err != nil {
157
163
p .Log ().Debug ("Light Ethereum message handling failed" , "err" , err )
158
164
return err
159
165
}
@@ -162,7 +168,7 @@ func (h *serverHandler) handle(p *peer) error {
162
168
163
169
// handleMsg is invoked whenever an inbound message is received from a remote
164
170
// peer. The remote connection is torn down upon returning any error.
165
- func (h * serverHandler ) handleMsg (p * peer ) error {
171
+ func (h * serverHandler ) handleMsg (p * peer , wg * sync. WaitGroup ) error {
166
172
// Read the next message from the remote peer, and ensure it's fully consumed
167
173
msg , err := p .rw .ReadMsg ()
168
174
if err != nil {
@@ -243,7 +249,7 @@ func (h *serverHandler) handleMsg(p *peer) error {
243
249
// Feed cost tracker request serving statistic.
244
250
h .server .costTracker .updateStats (msg .Code , amount , servingTime , realCost )
245
251
// Reduce priority "balance" for the specific peer.
246
- p . balanceTracker . requestCost (realCost )
252
+ h . server . clientPool . requestCost (p , realCost )
247
253
}
248
254
if reply != nil {
249
255
p .queueSend (func () {
@@ -273,7 +279,9 @@ func (h *serverHandler) handleMsg(p *peer) error {
273
279
}
274
280
query := req .Query
275
281
if accept (req .ReqID , query .Amount , MaxHeaderFetch ) {
282
+ wg .Add (1 )
276
283
go func () {
284
+ defer wg .Done ()
277
285
hashMode := query .Origin .Hash != (common.Hash {})
278
286
first := true
279
287
maxNonCanonical := uint64 (100 )
@@ -387,7 +395,9 @@ func (h *serverHandler) handleMsg(p *peer) error {
387
395
)
388
396
reqCnt := len (req .Hashes )
389
397
if accept (req .ReqID , uint64 (reqCnt ), MaxBodyFetch ) {
398
+ wg .Add (1 )
390
399
go func () {
400
+ defer wg .Done ()
391
401
for i , hash := range req .Hashes {
392
402
if i != 0 && ! task .waitOrStop () {
393
403
sendResponse (req .ReqID , 0 , nil , task .servingTime )
@@ -433,7 +443,9 @@ func (h *serverHandler) handleMsg(p *peer) error {
433
443
)
434
444
reqCnt := len (req .Reqs )
435
445
if accept (req .ReqID , uint64 (reqCnt ), MaxCodeFetch ) {
446
+ wg .Add (1 )
436
447
go func () {
448
+ defer wg .Done ()
437
449
for i , request := range req .Reqs {
438
450
if i != 0 && ! task .waitOrStop () {
439
451
sendResponse (req .ReqID , 0 , nil , task .servingTime )
@@ -502,7 +514,9 @@ func (h *serverHandler) handleMsg(p *peer) error {
502
514
)
503
515
reqCnt := len (req .Hashes )
504
516
if accept (req .ReqID , uint64 (reqCnt ), MaxReceiptFetch ) {
517
+ wg .Add (1 )
505
518
go func () {
519
+ defer wg .Done ()
506
520
for i , hash := range req .Hashes {
507
521
if i != 0 && ! task .waitOrStop () {
508
522
sendResponse (req .ReqID , 0 , nil , task .servingTime )
@@ -557,7 +571,9 @@ func (h *serverHandler) handleMsg(p *peer) error {
557
571
)
558
572
reqCnt := len (req .Reqs )
559
573
if accept (req .ReqID , uint64 (reqCnt ), MaxProofsFetch ) {
574
+ wg .Add (1 )
560
575
go func () {
576
+ defer wg .Done ()
561
577
nodes := light .NewNodeSet ()
562
578
563
579
for i , request := range req .Reqs {
@@ -658,7 +674,9 @@ func (h *serverHandler) handleMsg(p *peer) error {
658
674
)
659
675
reqCnt := len (req .Reqs )
660
676
if accept (req .ReqID , uint64 (reqCnt ), MaxHelperTrieProofsFetch ) {
677
+ wg .Add (1 )
661
678
go func () {
679
+ defer wg .Done ()
662
680
var (
663
681
lastIdx uint64
664
682
lastType uint
@@ -725,7 +743,9 @@ func (h *serverHandler) handleMsg(p *peer) error {
725
743
}
726
744
reqCnt := len (req .Txs )
727
745
if accept (req .ReqID , uint64 (reqCnt ), MaxTxSend ) {
746
+ wg .Add (1 )
728
747
go func () {
748
+ defer wg .Done ()
729
749
stats := make ([]light.TxStatus , len (req .Txs ))
730
750
for i , tx := range req .Txs {
731
751
if i != 0 && ! task .waitOrStop () {
@@ -771,7 +791,9 @@ func (h *serverHandler) handleMsg(p *peer) error {
771
791
}
772
792
reqCnt := len (req .Hashes )
773
793
if accept (req .ReqID , uint64 (reqCnt ), MaxTxStatus ) {
794
+ wg .Add (1 )
774
795
go func () {
796
+ defer wg .Done ()
775
797
stats := make ([]light.TxStatus , len (req .Hashes ))
776
798
for i , hash := range req .Hashes {
777
799
if i != 0 && ! task .waitOrStop () {
0 commit comments