Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Wrap ChainSyncer::state in an Arc<Mutex<_>> and set it to Follow accordingly #914

Merged
merged 1 commit into from
Jan 7, 2021

Conversation

timvermeulen
Copy link
Contributor

Summary of changes
Changes introduced in this pull request:

  • Wraps ChainSyncer::state in an Arc<Mutex<_>>
  • Passes this mutex to each sync worker, which will set the state to ::Follow when SyncWorker::sync completes succesfully

Reference issue to close (if applicable)

Closes #876

Comment on lines +427 to +430
if *self.state.lock().await == ChainSyncState::Bootstrap {
if let Some(best_target) = self.select_sync_target().await {
self.schedule_tipset(best_target).await;
self.state = ChainSyncState::Initial;
*self.state.lock().await = ChainSyncState::Initial;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I believe this keeps the lock and will deadlock here, has this been tested?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not tested, but I'm quite certain that if *self.state.lock().await does not keep the guard around since it's not bound to a variable, if that's what you're referring to. (playground that uses std's Mutex)

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've had issues with async-std mutexes holding the lock in this exact case in the past, not sure if it's changed or only applies to RwLock but can double check

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nvm, there was a specific case where it deadlocked similar to this, and moving the read outside of the if removed the deadlock, I just tested and this works

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh yeah, I can totally see that happening. Thanks for pointing it out either way, I could have easily messed this up

@@ -78,7 +78,7 @@ impl Default for SyncConfig {
/// messages to be able to do the initial sync.
pub struct ChainSyncer<DB, TBeacon, V, M> {
/// State of general `ChainSync` protocol.
state: ChainSyncState,
state: Arc<Mutex<ChainSyncState>>,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is mutex over rwlock required?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It is not, but does RwLock have any benefits if we're not expecting concurrent reads?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah I just was asking because there doesn't seem to be a reason to have the additional constraint (just thinking for future proofing)

It's definitely fine if this stays as is, this will probably be replaced in the future anyway

@timvermeulen timvermeulen merged commit 05b282d into main Jan 7, 2021
@timvermeulen timvermeulen deleted the tim/chain-follow branch January 7, 2021 01:09
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Transition from 'Initial Sync' to 'Chain Follow'
2 participants