(sc balancer.SubConn, scs balancer.SubConnState)
| 336 | } |
| 337 | |
| 338 | func (lb *lbBalancer) updateSubConnState(sc balancer.SubConn, scs balancer.SubConnState) { |
| 339 | s := scs.ConnectivityState |
| 340 | if lb.logger.V(2) { |
| 341 | lb.logger.Infof("SubConn state change: %p, %v", sc, s) |
| 342 | } |
| 343 | lb.mu.Lock() |
| 344 | defer lb.mu.Unlock() |
| 345 | |
| 346 | oldS, ok := lb.scStates[sc] |
| 347 | if !ok { |
| 348 | if lb.logger.V(2) { |
| 349 | lb.logger.Infof("Received state change for an unknown SubConn: %p, %v", sc, s) |
| 350 | } |
| 351 | return |
| 352 | } |
| 353 | lb.scStates[sc] = s |
| 354 | switch s { |
| 355 | case connectivity.Idle: |
| 356 | sc.Connect() |
| 357 | case connectivity.Shutdown: |
| 358 | // When an address was removed by resolver, b called Shutdown but kept |
| 359 | // the sc's state in scStates. Remove state for this sc here. |
| 360 | delete(lb.scStates, sc) |
| 361 | case connectivity.TransientFailure: |
| 362 | lb.connErr = scs.ConnectionError |
| 363 | } |
| 364 | // Force regenerate picker if |
| 365 | // - this sc became ready from not-ready |
| 366 | // - this sc became not-ready from ready |
| 367 | lb.updateStateAndPicker((oldS == connectivity.Ready) != (s == connectivity.Ready), false) |
| 368 | |
| 369 | // Enter fallback when the aggregated state is not Ready and the connection |
| 370 | // to remote balancer is lost. |
| 371 | if lb.state != connectivity.Ready { |
| 372 | if !lb.inFallback && !lb.remoteBalancerConnected { |
| 373 | // Enter fallback. |
| 374 | lb.refreshSubConns(lb.resolvedBackendAddrs, true, lb.usePickFirst) |
| 375 | } |
| 376 | } |
| 377 | } |
| 378 | |
| 379 | // updateStateAndPicker re-calculate the aggregated state, and regenerate picker |
| 380 | // if overall state is changed. |
no test coverage detected