/// <inheritdoc/> public void Start() { this.asyncLoop = this.asyncLoopFactory.Run("Notify", async token => { await this.Notify(this.nodeLifetime.ApplicationStopping); }, this.nodeLifetime.ApplicationStopping); }
/// <inheritdoc /> public void Start() { this.asyncLoop = this.asyncProvider.CreateAndRunAsyncLoop(nameof(PartialTransactionRequester), async token => { await this.BroadcastPartialTransactionsAsync().ConfigureAwait(false); }, this.nodeLifetime.ApplicationStopping, TimeBetweenQueries); }
///<inheritdoc/> public void StopMining() { this.miningCancellationTokenSource.Cancel(); this.miningLoop?.Dispose(); this.miningLoop = null; this.miningCancellationTokenSource.Dispose(); this.miningCancellationTokenSource = null; }
/// <inheritdoc /> public void Stop() { if (this.asyncLoop != null) { this.asyncLoop.Dispose(); this.asyncLoop = null; } }
/// <inheritdoc/> public void Start() { this.asyncLoop = this.asyncProvider.CreateAndRunAsyncLoop("Notify", async token => { await this.Notify(this.nodeLifetime.ApplicationStopping); }, this.nodeLifetime.ApplicationStopping); }
/// <inheritdoc /> public void Start() { this.asyncLoop = this.asyncProvider.CreateAndRunAsyncLoop(nameof(MempoolCleaner), async token => { await this.CleanMempoolAsync().ConfigureAwait(false); }, this.nodeLifetime.ApplicationStopping, TimeBetweenQueries); }
/// <inheritdoc/> public void StartConnectAsync() { this.asyncLoop = this.asyncLoopFactory.Run($"{this.GetType().Name}.{nameof(this.ConnectAsync)}", async token => { await this.ConnectAsync(); }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpans.Second); }
/// <inheritdoc /> public void Start() { this.asyncLoop = this.asyncProvider.CreateAndRunAsyncLoop(nameof(PartialTransactionRequester), token => { this.BroadcastPartialTransactionsAsync().GetAwaiter().GetResult(); return(Task.CompletedTask); }, this.nodeLifetime.ApplicationStopping, TimeBetweenQueries); }
/// <inheritdoc /> public void Start() { this.broadcastFullySignedTransfersTask = this.asyncProvider.CreateAndRunAsyncLoop($"{nameof(SignedMultisigTransactionBroadcaster)}.{nameof(this.broadcastFullySignedTransfersTask)}", async token => { await this.BroadcastFullySignedTransfersAsync().ConfigureAwait(false); }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpan.FromSeconds(RefreshDelaySeconds)); }
/// <summary> /// Starts the loop to refresh the whitelist. /// </summary> private void StartWhitelistRefreshLoop() { this.whitelistRefreshLoop = this.asyncLoopFactory.Run($"{nameof(DnsFeature)}.WhitelistRefreshLoop", token => { this.whitelistManager.RefreshWhitelist(); return(Task.CompletedTask); }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpan.FromSeconds(30)); }
/// <inheritdoc /> public void Start() { this.asyncLoop = this.asyncLoopFactory.Run(nameof(PartialTransactionRequester), _ => { this.BroadcastTransactionsAsync().GetAwaiter().GetResult(); return(Task.CompletedTask); }, this.nodeLifetime.ApplicationStopping, TimeBetweenQueries); }
/// <summary> /// Executes DownloadAndStoreBlocks() /// </summary> private void StartLoop() { this.asyncLoop = this.asyncLoopFactory.Run($"{this.StoreName}.DownloadAndStoreBlocks", async token => { await DownloadAndStoreBlocksAsync(this.nodeLifetime.ApplicationStopping, false).ConfigureAwait(false); }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpans.Second, startAfter: TimeSpans.FiveSeconds); }
/// <inheritdoc/> public void Initialize() { this.PrunedUpToHeaderTip = this.chainState.BlockStoreTip.GetAncestor(this.prunedBlockRepository.PrunedTip.Height); this.asyncLoop = this.asyncProvider.CreateAndRunAsyncLoop($"{this.GetType().Name}.{nameof(this.PruneBlocksAsync)}", async token => { await this.PruneBlocksAsync().ConfigureAwait(false); }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpans.TenSeconds); }
/// <inheritdoc /> public void Stop() { if (this.asyncLoop != null) { this.asyncLoop.Dispose(); this.asyncLoop = null; } this.signals.OnTransactionReceived.Detach(this.ProcessTransaction); this.signals.OnBlockConnected.Detach(this.OnBlockConnected); }
/// <inheritdoc /> public void Stop() { if (this.asyncLoop != null) { this.asyncLoop.Dispose(); this.asyncLoop = null; } this.signals.Unsubscribe(this.transactionReceivedSubscription); this.signals.Unsubscribe(this.blockConnectedSubscription); }
/// <summary> /// Starts a loop that warns user via console message about problems with system time settings. /// </summary> private void StartWarningLoop() { this.logger.LogTrace("()"); this.warningLoop = this.asyncLoopFactory.Run($"{nameof(TimeSyncBehavior)}.WarningLoop", token => { this.logger.LogTrace("()"); if (!this.SwitchedOffLimitReached) { bool timeOffsetWrong = false; double timeOffsetSeconds = 0; lock (this.lockObject) { timeOffsetSeconds = this.timeOffset.TotalSeconds; timeOffsetWrong = timeOffsetSeconds > TimeOffsetWarningThresholdSeconds; } if (timeOffsetWrong) { this.logger.LogCritical(Environment.NewLine + "============================== W A R N I N G ! ==============================" + Environment.NewLine + "Your system time is very different from the time of other network nodes." + Environment.NewLine + "It differs from the network median time by {0} seconds." + Environment.NewLine + "To prevent problems, adjust your system time or check the -synctime command line argument," + Environment.NewLine + "and restart the node." + Environment.NewLine + "=============================================================================" + Environment.NewLine, timeOffsetSeconds); } } else { this.logger.LogCritical(Environment.NewLine + "============================== W A R N I N G ! ==============================" + Environment.NewLine + "Your system time is very different from the time of other network nodes." + Environment.NewLine + "Your time difference to the network median time is over the allowed maximum of {0} seconds." + Environment.NewLine + "The time syncing feature has been switched off as it is no longer considered safe." + Environment.NewLine + "It is likely that you will now reject new blocks or be unable to mine new blocks." + Environment.NewLine + "You need to adjust your system time or check the -synctime command line argument," + Environment.NewLine + "and restart the node." + Environment.NewLine + "=============================================================================" + Environment.NewLine, MaxTimeOffsetSeconds); } this.logger.LogTrace("(-)"); return(Task.CompletedTask); }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpan.FromSeconds(57.3), // Weird number to prevent collisions with some other periodic console outputs. startAfter: TimeSpans.FiveSeconds); this.logger.LogTrace("(-)"); }
/// <inheritdoc/> public void Initialize() { this.PrunedUpToHeaderTip = this.chainState.BlockStoreTip.GetAncestor(this.prunedBlockRepository.PrunedTip.Height); this.asyncLoop = this.asyncProvider.CreateAndRunAsyncLoop($"{this.GetType().Name}.{nameof(this.PruneBlocks)}", token => { this.PruneBlocks(); return(Task.CompletedTask); }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpans.TenSeconds); }
/// <summary> /// Starts an asynchronous loop that periodicly tries to discover new peers to add to the /// <see cref="PeerAddressManager"/>. /// </summary> public void DiscoverPeers() { this.asyncLoop = this.asyncLoopFactory.Run(nameof(this.DiscoverPeersAsync), async token => { if (this.peerAddressManager.Peers.Count < this.peersToFind) { await this.DiscoverPeersAsync(); } }, this.nodeLifetime.ApplicationStopping, TimeSpans.Minute); }
/// <inheritdoc /> public void Mine(Script reserveScript) { if (this.miningLoop != null) { return; } this.miningCancellationTokenSource = CancellationTokenSource.CreateLinkedTokenSource(this.nodeLifetime.ApplicationStopping); this.miningLoop = this.asyncProvider.CreateAndRunAsyncLoop("PowMining.Mine", token => { try { GenerateBlocks(new ReserveScript { ReserveFullNodeScript = reserveScript }, int.MaxValue, int.MaxValue); } catch (OperationCanceledException) { // Application stopping, nothing to do as the loop will be stopped. } catch (MinerException me) { // Block not accepted by peers or invalid. Should not halt mining. this.logger.LogDebug("Miner exception occurred in miner loop: {0}", me.ToString()); } catch (ConsensusErrorException cee) { // Issues constructing block or verifying it. Should not halt mining. this.logger.LogDebug("Consensus error exception occurred in miner loop: {0}", cee.ToString()); } catch (ConsensusException ce) { // All consensus exceptions should be ignored. It means that the miner // run into problems while constructing block or verifying it // but it should not halted the staking operation. this.logger.LogDebug("Consensus exception occurred in miner loop: {0}", ce.ToString()); } catch { this.logger.LogTrace("(-)[UNHANDLED_EXCEPTION]"); throw; } return(Task.CompletedTask); }, this.miningCancellationTokenSource.Token, TimeSpans.Second, TimeSpans.TenSeconds); }
/// <summary> /// Initializes node's chain repository. /// Creates periodic task to persist changes to the database. /// </summary> private async Task StartChainAsync() { if (!Directory.Exists(this.dataFolder.ChainPath)) { this.logger.LogInformation("Creating {0}.", this.dataFolder.ChainPath); Directory.CreateDirectory(this.dataFolder.ChainPath); } if (!Directory.Exists(this.dataFolder.KeyValueRepositoryPath)) { this.logger.LogInformation("Creating {0}.", this.dataFolder.KeyValueRepositoryPath); Directory.CreateDirectory(this.dataFolder.KeyValueRepositoryPath); } this.logger.LogInformation("Loading finalized block height."); await this.finalizedBlockInfoRepository.LoadFinalizedBlockInfoAsync(this.network).ConfigureAwait(false); this.logger.LogInformation("Loading chain."); ChainedHeader chainTip = await this.chainRepository.LoadAsync(this.chainIndexer.Genesis).ConfigureAwait(false); this.chainIndexer.Initialize(chainTip); this.logger.LogInformation("Chain loaded at height {0}.", this.chainIndexer.Height); this.flushChainLoop = this.asyncProvider.CreateAndRunAsyncLoop("FlushChain", async token => { await this.chainRepository.SaveAsync(this.chainIndexer).ConfigureAwait(false); if (this.provenBlockHeaderStore != null) { await this.provenBlockHeaderStore.SaveAsync().ConfigureAwait(false); } // Get latest flags (often cached) and persist. if (this.consensusManager.Tip != null) { var flags = this.nodeDeployments.GetFlags(this.consensusManager.Tip); if (this.deploymentFlags == null || flags.ScriptFlags != this.deploymentFlags.ScriptFlags) { // Update the persistent disk cache of Flags when we retrieve it. this.keyValueRepo.SaveValueJson("deploymentflags", flags); // Update the local cached copy used to validate against. We don't want to persist to disk unless the flags actually has changed. this.deploymentFlags = flags; } } }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpan.FromMinutes(1.0), startAfter: TimeSpan.FromMinutes(1.0)); }
/// <inheritdoc /> public override void Initialize() { this.connectionManager.Parameters.TemplateBehaviors.Add(new DropNodesBehaviour(this.chain, this.connectionManager, this.loggerFactory)); this.walletManager.Start(); this.walletSyncManager.Start(); this.asyncLoop = this.StartDeploymentsChecksLoop(); this.walletFeePolicy.Start(); this.connectionManager.Parameters.TemplateBehaviors.Add(this.broadcasterBehavior); }
/// <summary> /// Starts the loop to refresh the whitelist. /// </summary> private void StartWhitelistRefreshLoop() { this.logger.LogTrace("()"); this.whitelistRefreshLoop = this.asyncLoopFactory.Run($"{nameof(DnsFeature)}.WhitelistRefreshLoop", token => { this.whitelistManager.RefreshWhitelist(); return(Task.CompletedTask); }, this.nodeLifetime.ApplicationStopping, repeatEvery: new TimeSpan(0, 0, 30)); this.logger.LogTrace("(-)"); }
public void Init(ClientEventBroadcasterSettings broadcasterSettings) { this.logger.LogDebug($"Initialising SignalR Broadcaster {this.GetType().Name}"); this.asyncLoop = this.asyncProvider.CreateAndRunAsyncLoop( $"Broadcast {this.GetType().Name}", async token => { foreach (IClientEvent clientEvent in this.GetMessages()) { await this.eventsHub.SendToClientsAsync(clientEvent).ConfigureAwait(false); } }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpan.FromSeconds(Math.Max(broadcasterSettings.BroadcastFrequencySeconds, 5))); }
/// <inheritdoc/> public void StartConnectAsync(NetworkPeerConnectionParameters parameters, PeerAddressManagerBehaviourMode mode) { this.parentParameters = parameters; this.CurrentParameters = this.parentParameters.Clone(); this.CurrentParameters.ConnectCancellation = this.nodeLifetime.ApplicationStopping; this.CurrentParameters.PeerAddressManagerBehaviour().Mode = mode; this.CurrentParameters.TemplateBehaviors.Add(new PeerConnectorBehaviour(this)); this.asyncLoop = this.asyncLoopFactory.Run($"{this.GetType().Name}.{nameof(this.ConnectAsync)}", async token => { await this.ConnectAsync(); }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpans.Second); }
/// <inheritdoc /> public override Task InitializeAsync() { this.connectionManager.Parameters.TemplateBehaviors.Add(new DropNodesBehaviour(this.chain, this.connectionManager, this.loggerFactory)); this.walletSettings.IsLightWallet = true; this.walletManager.Start(); this.walletSyncManager.Start(); this.asyncLoop = this.StartDeploymentsChecksLoop(); this.walletFeePolicy.Start(); this.connectionManager.Parameters.TemplateBehaviors.Add(this.broadcasterBehavior); return(Task.CompletedTask); }
private void StartFeeFilterBroadcast(INetworkPeer sender) { if (this.settings.FeeFilter) { INetworkPeer peer = sender; if (peer.PeerVersion != null && peer.PeerVersion.Relay && peer.PeerVersion.Version >= ProtocolVersion.FEEFILTER_VERSION) { if (this.asyncLoop != null) { this.asyncLoop = this.asyncProvider.CreateAndRunAsyncLoop($"MemoryPool.FeeFilter:{peer.Connection.Id}", async token => { if (this.initialBlockDownloadState.IsInitialBlockDownload()) { return; } var feeRate = await this.mempoolManager.GetMempoolMinFeeAsync(MempoolValidator.DefaultMaxMempoolSize * 1000000).ConfigureAwait(false); var currentFilter = feeRate.FeePerK; // We always have a fee filter of at least minRelayTxFee Money filterToSend = Math.Max(currentFilter, new FeeRate(this.network.MinRelayTxFee).FeePerK); if (filterToSend != this.lastSendFilter) { INetworkPeer peer = this.AttachedPeer; if (peer != null && peer.IsConnected) { this.logger.LogDebug("Sending for transaction data from peer '{0}'.", peer.RemoteSocketEndpoint); var filterPayload = new FeeFilterPayload() { NewFeeFilter = filterToSend }; await peer.SendMessageAsync(filterPayload).ConfigureAwait(false); this.lastSendFilter = filterToSend; } } }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpan.FromMinutes(10), startAfter: TimeSpans.TenSeconds); } } } }
private async Task OnStateChangedAsync(INetworkPeer sender, NetworkPeerState arg) { if (arg == NetworkPeerState.HandShaked) { this.StartFeeFilterBroadcast(sender); } if (arg == NetworkPeerState.Disconnecting) { if (this.asyncLoop != null) { this.asyncLoop?.Dispose(); this.asyncLoop = null; } } }
/// <summary> /// Starts the loop to save the masterfile. /// </summary> private void StartSaveMasterfileLoop() { this.saveMasterfileLoop = this.asyncProvider.CreateAndRunAsyncLoop($"{nameof(DnsFeature)}.WhitelistRefreshLoop", token => { string path = Path.Combine(this.dataFolders.DnsMasterFilePath, DnsFeature.DnsMasterFileName); this.logger.LogInformation("Saving cached DNS masterfile to {0}", path); using (var stream = new FileStream(path, FileMode.Create, FileAccess.Write, FileShare.Write)) { this.MasterFile.Save(stream); } return(Task.CompletedTask); }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpan.FromSeconds(SaveMasterfileRate)); }
public void Init(ClientEventBroadcasterSettings broadcasterSettings) { this.log.LogDebug($"Initialising Web Socket Broadcaster {this.GetType().Name}"); this.asyncLoop = this.asyncProvider.CreateAndRunAsyncLoop( $"Broadcast {this.GetType().Name}", async token => { foreach (EventBase clientEvent in this.GetMessages()) { this.eventsHub.OnEvent(clientEvent); } }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpan.FromSeconds(Math.Max(broadcasterSettings.BroadcastFrequencySeconds, 5)), startAfter: TimeSpans.FiveSeconds); }
/// <summary> /// Starts a loop to periodically log statistics about node's status very couple of seconds. /// <para> /// These logs are also displayed on the console. /// </para> /// </summary> private void StartPeriodicLog() { IAsyncLoop periodicLogLoop = this.AsyncLoopFactory.Run("PeriodicLog", (cancellation) => { string stats = this.nodeStats.GetStats(); this.logger.LogInformation(stats); this.LastLogOutput = stats; return(Task.CompletedTask); }, this.nodeLifetime.ApplicationStopping, repeatEvery: TimeSpans.FiveSeconds, startAfter: TimeSpans.FiveSeconds); this.Resources.Add(periodicLogLoop); }