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

Handle pre & headers sync states, add header verification to Block Clock verification progress #277

Draft
wants to merge 2 commits into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions src/qml/components/BlockClock.qml
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ Item {
property alias subText: subText.text
property int headerSize: 32
property bool connected: nodeModel.numOutboundPeers > 0
property bool synced: nodeModel.verificationProgress > 0.999
property bool synced: !nodeModel.inIBD
property string syncProgress: formatProgressPercentage(nodeModel.verificationProgress * 100)
property bool paused: false
property var syncState: formatRemainingSyncTime(nodeModel.remainingSyncTime)
Expand All @@ -49,7 +49,7 @@ Item {
verificationProgress: nodeModel.verificationProgress
paused: root.paused
connected: root.connected
synced: nodeModel.verificationProgress > 0.999
synced: root.synced
backgroundColor: Theme.color.neutral2
timeTickColor: Theme.color.neutral5
confirmationColors: Theme.color.confirmationColors
Expand Down
89 changes: 85 additions & 4 deletions src/qml/models/nodemodel.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ NodeModel::NodeModel(interfaces::Node& node)
: m_node{node}
{
ConnectToBlockTipSignal();
ConnectToHeaderTipSignal();
ConnectToNumConnectionsChangedSignal();
}

Expand All @@ -31,6 +32,15 @@ void NodeModel::setBlockTipHeight(int new_height)
}
}


void NodeModel::setInIBD(bool new_ibd)
{
if (new_ibd != m_in_ibd) {
m_in_ibd = new_ibd;
Q_EMIT inIBDChanged();
}
}

void NodeModel::setNumOutboundPeers(int new_num)
{
if (new_num != m_num_outbound_peers) {
Expand All @@ -39,6 +49,47 @@ void NodeModel::setNumOutboundPeers(int new_num)
}
}

void NodeModel::setInHeaderSync(bool new_in_header_sync)
{
if (new_in_header_sync != m_in_header_sync) {
m_in_header_sync = new_in_header_sync;
Q_EMIT inHeaderSyncChanged();
}
}

void NodeModel::setHeaderSyncProgress(int64_t header_height, const QDateTime& block_date)
{
int estimated_headers_left = block_date.secsTo(QDateTime::currentDateTime()) / Params().GetConsensus().nPowTargetSpacing;
double new_header_sync_progress = (100.0 / (header_height + estimated_headers_left) * header_height) / 10000;

if (new_header_sync_progress != m_header_sync_progress) {
m_header_sync_progress = new_header_sync_progress;
setVerificationProgress(0.0);
Q_EMIT headerSyncProgressChanged();
}
}

void NodeModel::setInPreHeaderSync(bool new_in_pre_header_sync)
{
if (new_in_pre_header_sync != m_in_pre_header_sync) {
m_in_pre_header_sync = new_in_pre_header_sync;
Q_EMIT inPreHeaderSyncChanged();
}
}

void NodeModel::setPreHeaderSyncProgress(int64_t header_height, const QDateTime& block_date)
{
int estimated_headers_left = block_date.secsTo(QDateTime::currentDateTime()) / Params().GetConsensus().nPowTargetSpacing;
double new_pre_header_sync_progress = (100.0 / (header_height + estimated_headers_left) * header_height) / 10000;

if (new_pre_header_sync_progress != m_pre_header_sync_progress) {
m_pre_header_sync_progress = new_pre_header_sync_progress;
setVerificationProgress(0.0);
Q_EMIT preHeaderSyncProgressChanged();

}
}

void NodeModel::setRemainingSyncTime(double new_progress)
{
int currentTime = QDateTime::currentDateTime().toMSecsSinceEpoch();
Expand Down Expand Up @@ -74,12 +125,19 @@ void NodeModel::setRemainingSyncTime(double new_progress)
}
}
}

void NodeModel::setVerificationProgress(double new_progress)
{
if (new_progress != m_verification_progress) {
setRemainingSyncTime(new_progress);
double header_progress = m_header_sync_progress + m_pre_header_sync_progress;
if (!m_in_header_sync && !m_in_pre_header_sync) {
if (new_progress != m_verification_progress) {
setRemainingSyncTime(new_progress);

m_verification_progress = new_progress;
m_verification_progress = header_progress + (new_progress - header_progress);
Q_EMIT verificationProgressChanged();
}
} else {
m_verification_progress = header_progress;
Q_EMIT verificationProgressChanged();
}
}
Expand Down Expand Up @@ -139,13 +197,36 @@ void NodeModel::ConnectToBlockTipSignal()
[this](SynchronizationState state, interfaces::BlockTip tip, double verification_progress) {
QMetaObject::invokeMethod(this, [=] {
setBlockTipHeight(tip.block_height);
setInIBD(m_node.isInitialBlockDownload());
setVerificationProgress(verification_progress);

setInHeaderSync(false);
setInPreHeaderSync(false);
Q_EMIT setTimeRatioList(tip.block_time);
});
});
}

void NodeModel::ConnectToHeaderTipSignal()
{
assert(!m_handler_notify_header_tip);

m_handler_notify_header_tip = m_node.handleNotifyHeaderTip(
[this](SynchronizationState sync_state, interfaces::BlockTip tip, bool presync) {
setInIBD(m_node.isInitialBlockDownload());
QMetaObject::invokeMethod(this, [=] {
if (presync) {
setInHeaderSync(false);
setInPreHeaderSync(true);
setPreHeaderSyncProgress(tip.block_height, QDateTime::fromSecsSinceEpoch(tip.block_time));
} else {
setInHeaderSync(true);
setInPreHeaderSync(false);
setHeaderSyncProgress(tip.block_height, QDateTime::fromSecsSinceEpoch(tip.block_time));
}
});
});
}

void NodeModel::ConnectToNumConnectionsChangedSignal()
{
assert(!m_handler_notify_num_peers_changed);
Expand Down
27 changes: 27 additions & 0 deletions src/qml/models/nodemodel.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,8 +28,13 @@ class NodeModel : public QObject
Q_OBJECT
Q_PROPERTY(int blockTipHeight READ blockTipHeight NOTIFY blockTipHeightChanged)
Q_PROPERTY(QString fullClientVersion READ fullClientVersion CONSTANT)
Q_PROPERTY(bool inIBD READ inIBD NOTIFY inIBDChanged)
Q_PROPERTY(int numOutboundPeers READ numOutboundPeers NOTIFY numOutboundPeersChanged)
Q_PROPERTY(int maxNumOutboundPeers READ maxNumOutboundPeers CONSTANT)
Q_PROPERTY(bool inHeaderSync READ inHeaderSync WRITE setInHeaderSync NOTIFY inHeaderSyncChanged)
Q_PROPERTY(double headerSyncProgress READ headerSyncProgress NOTIFY headerSyncProgressChanged)
Q_PROPERTY(bool inPreHeaderSync READ inPreHeaderSync WRITE setInPreHeaderSync NOTIFY inPreHeaderSyncChanged)
Q_PROPERTY(double preHeaderSyncProgress READ preHeaderSyncProgress NOTIFY preHeaderSyncProgressChanged)
Q_PROPERTY(int remainingSyncTime READ remainingSyncTime NOTIFY remainingSyncTimeChanged)
Q_PROPERTY(double verificationProgress READ verificationProgress NOTIFY verificationProgressChanged)
Q_PROPERTY(bool pause READ pause WRITE setPause NOTIFY pauseChanged)
Expand All @@ -40,9 +45,19 @@ class NodeModel : public QObject
int blockTipHeight() const { return m_block_tip_height; }
void setBlockTipHeight(int new_height);
QString fullClientVersion() const { return QString::fromStdString(FormatFullVersion()); }
bool inIBD() const { return m_in_ibd; }
void setInIBD(bool new_ibd);
int numOutboundPeers() const { return m_num_outbound_peers; }
void setNumOutboundPeers(int new_num);
int maxNumOutboundPeers() const { return m_max_num_outbound_peers; }
bool inHeaderSync() const { return m_in_header_sync; }
void setInHeaderSync(bool new_in_header_sync);
double headerSyncProgress() const { return m_header_sync_progress; }
void setHeaderSyncProgress(int64_t header_height, const QDateTime& block_date);
bool inPreHeaderSync() const { return m_in_pre_header_sync; }
void setInPreHeaderSync(bool new_in_pre_header_sync);
double preHeaderSyncProgress() const { return m_pre_header_sync_progress; }
void setPreHeaderSyncProgress(int64_t header_height, const QDateTime& block_date);
int remainingSyncTime() const { return m_remaining_sync_time; }
void setRemainingSyncTime(double new_progress);
double verificationProgress() const { return m_verification_progress; }
Expand All @@ -64,7 +79,12 @@ public Q_SLOTS:

Q_SIGNALS:
void blockTipHeightChanged();
void inIBDChanged();
void numOutboundPeersChanged();
void inHeaderSyncChanged();
void headerSyncProgressChanged();
void inPreHeaderSyncChanged();
void preHeaderSyncProgressChanged();
void remainingSyncTimeChanged();
void requestedInitialize();
void requestedShutdown();
Expand All @@ -80,8 +100,13 @@ public Q_SLOTS:
private:
// Properties that are exposed to QML.
int m_block_tip_height{0};
bool m_in_ibd;
int m_num_outbound_peers{0};
static constexpr int m_max_num_outbound_peers{MAX_OUTBOUND_FULL_RELAY_CONNECTIONS + MAX_BLOCK_RELAY_ONLY_CONNECTIONS};
bool m_in_header_sync;
double m_header_sync_progress;
bool m_in_pre_header_sync;
double m_pre_header_sync_progress;
int m_remaining_sync_time{0};
double m_verification_progress{0.0};
bool m_pause{false};
Expand All @@ -92,9 +117,11 @@ public Q_SLOTS:

interfaces::Node& m_node;
std::unique_ptr<interfaces::Handler> m_handler_notify_block_tip;
std::unique_ptr<interfaces::Handler> m_handler_notify_header_tip;
std::unique_ptr<interfaces::Handler> m_handler_notify_num_peers_changed;

void ConnectToBlockTipSignal();
void ConnectToHeaderTipSignal();
void ConnectToNumConnectionsChangedSignal();
};

Expand Down