mirror of
https://github.com/Qortal/altcoinj.git
synced 2025-02-12 18:25:51 +00:00
Fix race condition on PeerGroup shutdown.
peers can be null in handlePeerDeath if we are shutting down. Remove redundant numPeers() - use numConnectedPeers(). Rename getPeers() to getConnectedPeers() Resolves issue 147.
This commit is contained in:
parent
789798bae0
commit
bb97da6a5a
@ -688,6 +688,8 @@ public class Peer {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Terminates the network connection and stops the message handling loop.
|
* Terminates the network connection and stops the message handling loop.
|
||||||
|
*
|
||||||
|
* <p>This does not wait for the loop to terminate.
|
||||||
*/
|
*/
|
||||||
public synchronized void disconnect() {
|
public synchronized void disconnect() {
|
||||||
running = false;
|
running = false;
|
||||||
|
@ -271,22 +271,14 @@ public class PeerGroup {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a newly allocated list containing the currently connected peers. If all you care about is the count,
|
* Returns a newly allocated list containing the currently connected peers. If all you care about is the count,
|
||||||
* use numPeers().
|
* use numConnectedPeers().
|
||||||
*/
|
*/
|
||||||
public synchronized List<Peer> getPeers() {
|
public synchronized List<Peer> getConnectedPeers() {
|
||||||
ArrayList<Peer> result = new ArrayList<Peer>(peers.size());
|
ArrayList<Peer> result = new ArrayList<Peer>(peers.size());
|
||||||
result.addAll(peers);
|
result.addAll(peers);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns the number of currently connected peers. To be informed when this count changes, register a
|
|
||||||
* {@link PeerEventListener} and use the onPeerConnected/onPeerDisconnected methods.
|
|
||||||
*/
|
|
||||||
public synchronized int numPeers() {
|
|
||||||
return peers.size();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add an address to the list of potential peers to connect to
|
* Add an address to the list of potential peers to connect to
|
||||||
*/
|
*/
|
||||||
@ -312,10 +304,12 @@ public class PeerGroup {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Stop this PeerGroup.<p>
|
* Stop this PeerGroup.
|
||||||
*
|
*
|
||||||
* The peer group will be asynchronously shut down. After it is shut down all peers will be disconnected and no
|
* <p>The peer group will be asynchronously shut down. Some time after it is shut down all peers
|
||||||
* threads will be running.
|
* will be disconnected and no threads will be running.
|
||||||
|
*
|
||||||
|
* <p>It is an error to call any other method on PeerGroup after calling this one.
|
||||||
*/
|
*/
|
||||||
public synchronized void stop() {
|
public synchronized void stop() {
|
||||||
if (running) {
|
if (running) {
|
||||||
@ -375,9 +369,14 @@ public class PeerGroup {
|
|||||||
removeEventListener(wallet.getPeerEventListener());
|
removeEventListener(wallet.getPeerEventListener());
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Returns how many remote nodes this peer group is connected to. */
|
/**
|
||||||
public int numConnectedPeers() {
|
* Returns the number of currently connected peers. To be informed when this count changes, register a
|
||||||
return peers.size();
|
* {@link PeerEventListener} and use the onPeerConnected/onPeerDisconnected methods.
|
||||||
|
*/
|
||||||
|
public synchronized int numConnectedPeers() {
|
||||||
|
synchronized (peers) {
|
||||||
|
return peers.size();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public synchronized boolean isRunning() {
|
public synchronized boolean isRunning() {
|
||||||
@ -434,6 +433,9 @@ public class PeerGroup {
|
|||||||
}
|
}
|
||||||
} catch (InterruptedException ex) {
|
} catch (InterruptedException ex) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// We were asked to stop. Reset running flag and disconnect all peers. Peers could
|
||||||
|
// still linger until their event loop is scheduled.
|
||||||
synchronized (PeerGroup.this) {
|
synchronized (PeerGroup.this) {
|
||||||
running = false;
|
running = false;
|
||||||
peerPool.shutdown();
|
peerPool.shutdown();
|
||||||
@ -708,6 +710,10 @@ public class PeerGroup {
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected synchronized void handlePeerDeath(final Peer peer) {
|
protected synchronized void handlePeerDeath(final Peer peer) {
|
||||||
|
if (!isRunning()) {
|
||||||
|
log.info("Peer death while shutting down");
|
||||||
|
return;
|
||||||
|
}
|
||||||
assert !peers.contains(peer);
|
assert !peers.contains(peer);
|
||||||
if (peer == downloadPeer) {
|
if (peer == downloadPeer) {
|
||||||
log.info("Download peer died. Picking a new one.");
|
log.info("Download peer died. Picking a new one.");
|
||||||
|
@ -115,8 +115,8 @@ public class PeerGroupTest extends TestWithNetworkConnections {
|
|||||||
peerGroup.addPeer(p2);
|
peerGroup.addPeer(p2);
|
||||||
|
|
||||||
// Check the peer accessors.
|
// Check the peer accessors.
|
||||||
assertEquals(2, peerGroup.numPeers());
|
assertEquals(2, peerGroup.numConnectedPeers());
|
||||||
Set<Peer> tmp = new HashSet<Peer>(peerGroup.getPeers());
|
Set<Peer> tmp = new HashSet<Peer>(peerGroup.getConnectedPeers());
|
||||||
Set<Peer> expectedPeers = new HashSet<Peer>();
|
Set<Peer> expectedPeers = new HashSet<Peer>();
|
||||||
expectedPeers.add(p1);
|
expectedPeers.add(p1);
|
||||||
expectedPeers.add(p2);
|
expectedPeers.add(p2);
|
||||||
@ -145,7 +145,7 @@ public class PeerGroupTest extends TestWithNetworkConnections {
|
|||||||
peerGroup.start();
|
peerGroup.start();
|
||||||
peerGroup.addPeer(p1);
|
peerGroup.addPeer(p1);
|
||||||
peerGroup.addPeer(p2);
|
peerGroup.addPeer(p2);
|
||||||
assertEquals(2, peerGroup.numPeers());
|
assertEquals(2, peerGroup.numConnectedPeers());
|
||||||
|
|
||||||
// Set up a little block chain. We heard about b1 but not b2 (it is pending download). b3 is solved whilst we
|
// Set up a little block chain. We heard about b1 but not b2 (it is pending download). b3 is solved whilst we
|
||||||
// are downloading the chain.
|
// are downloading the chain.
|
||||||
|
Loading…
x
Reference in New Issue
Block a user