block_sync.rs 2.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960
  1. use crate::{
  2. consensus::{
  3. block::{BlockOrder, BlockResponse},
  4. ValidatorStatePtr,
  5. },
  6. net, Result,
  7. };
  8. use log::{debug, info, warn};
  9. /// async task used for block syncing.
  10. pub async fn block_sync_task(p2p: net::P2pPtr, state: ValidatorStatePtr) -> Result<()> {
  11. info!("Starting blockchain sync...");
  12. // we retrieve p2p network connected channels, so we can use it to
  13. // parallelize downloads.
  14. // Using len here because is_empty() uses unstable library feature
  15. // called 'exact_size_is_empty'.
  16. if p2p.channels().lock().await.values().len() != 0 {
  17. // Currently we will just use the last channel
  18. let channel = p2p.channels().lock().await.values().last().unwrap().clone();
  19. // Communication setup
  20. let msg_subsystem = channel.get_message_subsystem();
  21. msg_subsystem.add_dispatch::<BlockResponse>().await;
  22. let response_sub = channel.subscribe_msg::<BlockResponse>().await?;
  23. // Node sends the last known block hash of the canonical blockchain
  24. // and loops until the response is the same block (used to utilize
  25. // batch requests).
  26. let mut last = state.read().await.blockchain.last()?;
  27. info!("Last known block: {:?} - {:?}", last.0, last.1);
  28. loop {
  29. // Node creates a `BlockOrder` and sends it
  30. let order = BlockOrder { slot: last.0, block: last.1 };
  31. channel.send(order).await?;
  32. // Node stores response data.
  33. let resp = response_sub.receive().await?;
  34. // Verify and store retrieved blocks
  35. debug!("block_sync_task(): Processing received blocks");
  36. state.write().await.receive_blocks(&resp.blocks).await?;
  37. let last_received = state.read().await.blockchain.last()?;
  38. info!("Last received block: {:?} - {:?}", last_received.0, last_received.1);
  39. if last == last_received {
  40. break
  41. }
  42. last = last_received;
  43. }
  44. } else {
  45. warn!("Node is not connected to other nodes");
  46. }
  47. info!("Blockchain synced!");
  48. Ok(())
  49. }