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

Implement transaction lock zmq notifications #903

Merged
merged 6 commits into from
Jul 15, 2016
Merged
Show file tree
Hide file tree
Changes from 2 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
1 change: 1 addition & 0 deletions doc/zmq.md
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ the commandline or in the configuration file.
Currently, the following notifications are supported:

-zmqpubhashtx=address
-zmqpubhashtxlock=address
-zmqpubhashblock=address
-zmqpubrawblock=address
-zmqpubrawtx=address
Expand Down
1 change: 1 addition & 0 deletions src/init.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -481,6 +481,7 @@ std::string HelpMessage(HelpMessageMode mode)
strUsage += HelpMessageGroup(_("ZeroMQ notification options:"));
strUsage += HelpMessageOpt("-zmqpubhashblock=<address>", _("Enable publish hash block in <address>"));
strUsage += HelpMessageOpt("-zmqpubhashtx=<address>", _("Enable publish hash transaction in <address>"));
strUsage += HelpMessageOpt("-zmqpubhashtxlock=<address>", _("Enable publish hash transaction (locked via InastantSend) in <address>"));

Choose a reason for hiding this comment

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

InstantSend :)

Copy link
Author

Choose a reason for hiding this comment

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

ooops :)

strUsage += HelpMessageOpt("-zmqpubrawblock=<address>", _("Enable publish raw block in <address>"));
strUsage += HelpMessageOpt("-zmqpubrawtx=<address>", _("Enable publish raw transaction in <address>"));
#endif
Expand Down
7 changes: 6 additions & 1 deletion src/instantx.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -386,11 +386,12 @@ void UpdateLockedTransaction(CTransaction& tx, bool fForceNotification) {
// there must be a successfully verified lock request
if (!mapTxLockReq.count(txHash)) return;

int nSignatures = GetTransactionLockSignatures(txHash);

#ifdef ENABLE_WALLET
if(pwalletMain && pwalletMain->UpdatedTransaction(txHash)){
// bumping this to update UI
nCompleteTXLocks++;
int nSignatures = GetTransactionLockSignatures(txHash);
// a transaction lock must have enough signatures to trigger this notification
if(nSignatures == INSTANTX_SIGNATURES_REQUIRED || (fForceNotification && nSignatures > INSTANTX_SIGNATURES_REQUIRED)) {
// notify an external script once threshold is reached
Expand All @@ -403,6 +404,10 @@ void UpdateLockedTransaction(CTransaction& tx, bool fForceNotification) {
}
}
#endif

if(nSignatures == INSTANTX_SIGNATURES_REQUIRED || (fForceNotification && nSignatures > INSTANTX_SIGNATURES_REQUIRED)) {
GetMainSignals().NotifyTransactionLock(txHash);
}
}

void LockTransactionInputs(CTransaction& tx) {
Expand Down
3 changes: 3 additions & 0 deletions src/validationinterface.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ CMainSignals& GetMainSignals()
void RegisterValidationInterface(CValidationInterface* pwalletIn) {
g_signals.UpdatedBlockTip.connect(boost::bind(&CValidationInterface::UpdatedBlockTip, pwalletIn, _1));
g_signals.SyncTransaction.connect(boost::bind(&CValidationInterface::SyncTransaction, pwalletIn, _1, _2));
g_signals.NotifyTransactionLock.connect(boost::bind(&CValidationInterface::NotifyTransactionLock, pwalletIn, _1));
g_signals.UpdatedTransaction.connect(boost::bind(&CValidationInterface::UpdatedTransaction, pwalletIn, _1));
g_signals.SetBestChain.connect(boost::bind(&CValidationInterface::SetBestChain, pwalletIn, _1));
g_signals.Inventory.connect(boost::bind(&CValidationInterface::Inventory, pwalletIn, _1));
Expand All @@ -32,6 +33,7 @@ void UnregisterValidationInterface(CValidationInterface* pwalletIn) {
g_signals.Inventory.disconnect(boost::bind(&CValidationInterface::Inventory, pwalletIn, _1));
g_signals.SetBestChain.disconnect(boost::bind(&CValidationInterface::SetBestChain, pwalletIn, _1));
g_signals.UpdatedTransaction.disconnect(boost::bind(&CValidationInterface::UpdatedTransaction, pwalletIn, _1));
g_signals.NotifyTransactionLock.disconnect(boost::bind(&CValidationInterface::NotifyTransactionLock, pwalletIn, _1));
g_signals.SyncTransaction.disconnect(boost::bind(&CValidationInterface::SyncTransaction, pwalletIn, _1, _2));
g_signals.UpdatedBlockTip.disconnect(boost::bind(&CValidationInterface::UpdatedBlockTip, pwalletIn, _1));
}
Expand All @@ -44,6 +46,7 @@ void UnregisterAllValidationInterfaces() {
g_signals.Inventory.disconnect_all_slots();
g_signals.SetBestChain.disconnect_all_slots();
g_signals.UpdatedTransaction.disconnect_all_slots();
g_signals.NotifyTransactionLock.disconnect_all_slots();
g_signals.SyncTransaction.disconnect_all_slots();
g_signals.UpdatedBlockTip.disconnect_all_slots();
}
Expand Down
3 changes: 3 additions & 0 deletions src/validationinterface.h
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ class CValidationInterface {
protected:
virtual void UpdatedBlockTip(const CBlockIndex *pindex) {}
virtual void SyncTransaction(const CTransaction &tx, const CBlock *pblock) {}
virtual void NotifyTransactionLock(const uint256 &hash) {}
virtual void SetBestChain(const CBlockLocator &locator) {}
virtual bool UpdatedTransaction(const uint256 &hash) { return false;}
virtual void Inventory(const uint256 &hash) {}
Expand All @@ -50,6 +51,8 @@ struct CMainSignals {
boost::signals2::signal<void (const CBlockIndex *)> UpdatedBlockTip;
/** Notifies listeners of updated transaction data (transaction, and optionally the block it is found in. */
boost::signals2::signal<void (const CTransaction &, const CBlock *)> SyncTransaction;
/** Notifies listeners of an updated transaction lock without new data. */
boost::signals2::signal<void (const uint256 &)> NotifyTransactionLock;
/** Notifies listeners of an updated transaction without new data (for now: a coinbase potentially becoming visible). */
boost::signals2::signal<bool (const uint256 &)> UpdatedTransaction;
/** Notifies listeners of a new active block chain. */
Expand Down
5 changes: 5 additions & 0 deletions src/zmq/zmqabstractnotifier.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,3 +20,8 @@ bool CZMQAbstractNotifier::NotifyTransaction(const CTransaction &/*transaction*/
{
return true;
}

bool CZMQAbstractNotifier::NotifyTransactionLock(const uint256 &/*hash*/)
{
return true;
}
1 change: 1 addition & 0 deletions src/zmq/zmqabstractnotifier.h
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ class CZMQAbstractNotifier

virtual bool NotifyBlock(const CBlockIndex *pindex);
virtual bool NotifyTransaction(const CTransaction &transaction);
virtual bool NotifyTransactionLock(const uint256 &hash);

protected:
void *psocket;
Expand Down
18 changes: 18 additions & 0 deletions src/zmq/zmqnotificationinterface.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ CZMQNotificationInterface* CZMQNotificationInterface::CreateWithArguments(const

factories["pubhashblock"] = CZMQAbstractNotifier::Create<CZMQPublishHashBlockNotifier>;
factories["pubhashtx"] = CZMQAbstractNotifier::Create<CZMQPublishHashTransactionNotifier>;
factories["pubhashtxlock"] = CZMQAbstractNotifier::Create<CZMQPublishHashTransactionLockNotifier>;
factories["pubrawblock"] = CZMQAbstractNotifier::Create<CZMQPublishRawBlockNotifier>;
factories["pubrawtx"] = CZMQAbstractNotifier::Create<CZMQPublishRawTransactionNotifier>;

Expand Down Expand Up @@ -158,3 +159,20 @@ void CZMQNotificationInterface::SyncTransaction(const CTransaction &tx, const CB
}
}
}

void CZMQNotificationInterface::NotifyTransactionLock(const uint256 &hash)
{
for (std::list<CZMQAbstractNotifier*>::iterator i = notifiers.begin(); i!=notifiers.end(); )
{
CZMQAbstractNotifier *notifier = *i;
if (notifier->NotifyTransactionLock(hash))
{
i++;
}
else
{
notifier->Shutdown();
i = notifiers.erase(i);
}
}
}
1 change: 1 addition & 0 deletions src/zmq/zmqnotificationinterface.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ class CZMQNotificationInterface : public CValidationInterface
// CValidationInterface
void SyncTransaction(const CTransaction &tx, const CBlock *pblock);
void UpdatedBlockTip(const CBlockIndex *pindex);
void NotifyTransactionLock(const uint256 &hash);

private:
CZMQNotificationInterface();
Expand Down
10 changes: 10 additions & 0 deletions src/zmq/zmqpublishnotifier.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -139,6 +139,16 @@ bool CZMQPublishHashTransactionNotifier::NotifyTransaction(const CTransaction &t
return rc == 0;
}

bool CZMQPublishHashTransactionLockNotifier::NotifyTransactionLock(const uint256 &hash)
{
LogPrint("zmq", "zmq: Publish hashtxlock %s\n", hash.GetHex());
char data[32];
for (unsigned int i = 0; i < 32; i++)
data[31 - i] = hash.begin()[i];
int rc = zmq_send_multipart(psocket, "hashtxlock", 6, data, 32, 0);
return rc == 0;
}

bool CZMQPublishRawBlockNotifier::NotifyBlock(const CBlockIndex *pindex)
{
LogPrint("zmq", "zmq: Publish rawblock %s\n", pindex->GetBlockHash().GetHex());
Expand Down
6 changes: 6 additions & 0 deletions src/zmq/zmqpublishnotifier.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,12 @@ class CZMQPublishHashTransactionNotifier : public CZMQAbstractPublishNotifier
bool NotifyTransaction(const CTransaction &transaction);
};

class CZMQPublishHashTransactionLockNotifier : public CZMQAbstractPublishNotifier
{
public:
bool NotifyTransactionLock(const uint256 &hash);
};

class CZMQPublishRawBlockNotifier : public CZMQAbstractPublishNotifier
{
public:
Expand Down