Have consensus use the config for validation and use uint160 for peerIDs.

This commit is contained in:
Arthur Britto
2012-06-13 15:51:30 -07:00
parent 5aaeef3a50
commit 368e5a0acc
6 changed files with 69 additions and 43 deletions

View File

@@ -118,10 +118,10 @@ bool TransactionAcquire::takeNodes(const std::list<SHAMapNode>& nodeIDs,
}
}
void LCTransaction::setVote(const uint256& peer, bool votesYes)
void LCTransaction::setVote(const uint160& peer, bool votesYes)
{
std::pair<boost::unordered_map<uint256, bool>::iterator, bool> res =
mVotes.insert(std::make_pair<uint256, bool>(peer, votesYes));
std::pair<boost::unordered_map<uint160, bool>::iterator, bool> res =
mVotes.insert(std::make_pair<uint160, bool>(peer, votesYes));
if (res.second)
{ // new vote
@@ -182,14 +182,13 @@ LedgerConsensus::LedgerConsensus(Ledger::pointer previousLedger, uint32 closeTim
void LedgerConsensus::takeInitialPosition(Ledger::pointer initialLedger)
{
CKey::pointer nodePrivKey = boost::make_shared<CKey>();
nodePrivKey->MakeNewKey(); // FIXME
// XXX Don't even start if no VALIDATION_SEED.
SHAMap::pointer initialSet = initialLedger->peekTransactionMap()->snapShot(false);
uint256 txSet = initialSet->getHash();
assert (initialLedger->getParentHash() == mPreviousLedger->getHash());
mOurPosition = boost::make_shared<LedgerProposal>(nodePrivKey, initialLedger->getParentHash(), txSet);
mOurPosition = boost::make_shared<LedgerProposal>(theConfig.VALIDATION_SEED, initialLedger->getParentHash(), txSet);
mapComplete(txSet, initialSet);
propose(std::vector<uint256>(), std::vector<uint256>());
}
@@ -234,8 +233,8 @@ void LedgerConsensus::mapComplete(const uint256& hash, SHAMap::pointer map)
mComplete[map->getHash()] = map;
// Adjust tracking for each peer that takes this position
std::vector<uint256> peers;
for (boost::unordered_map<uint256, LedgerProposal::pointer>::iterator it = mPeerPositions.begin(),
std::vector<uint160> peers;
for (boost::unordered_map<uint160, LedgerProposal::pointer>::iterator it = mPeerPositions.begin(),
end = mPeerPositions.end(); it != end; ++it)
{
if (it->second->getCurrentHash() == map->getHash())
@@ -256,13 +255,13 @@ void LedgerConsensus::sendHaveTxSet(const uint256& hash, bool direct)
theApp->getConnectionPool().relayMessage(NULL, packet);
}
void LedgerConsensus::adjustCount(SHAMap::pointer map, const std::vector<uint256>& peers)
void LedgerConsensus::adjustCount(SHAMap::pointer map, const std::vector<uint160>& peers)
{ // Adjust the counts on all disputed transactions based on the set of peers taking this position
for (boost::unordered_map<uint256, LCTransaction::pointer>::iterator it = mDisputes.begin(), end = mDisputes.end();
it != end; ++it)
{
bool setHas = map->hasItem(it->second->getTransactionID());
for(std::vector<uint256>::const_iterator pit = peers.begin(), pend = peers.end(); pit != pend; ++pit)
for(std::vector<uint160>::const_iterator pit = peers.begin(), pend = peers.end(); pit != pend; ++pit)
it->second->setVote(*pit, setHas);
}
}
@@ -489,7 +488,7 @@ void LedgerConsensus::addDisputedTransaction(const uint256& txID, const std::vec
LCTransaction::pointer txn = boost::make_shared<LCTransaction>(txID, tx, ourPosition);
mDisputes[txID] = txn;
for (boost::unordered_map<uint256, LedgerProposal::pointer>::iterator pit = mPeerPositions.begin(),
for (boost::unordered_map<uint160, LedgerProposal::pointer>::iterator pit = mPeerPositions.begin(),
pend = mPeerPositions.end(); pit != pend; ++pit)
{
boost::unordered_map<uint256, SHAMap::pointer>::const_iterator cit =
@@ -719,7 +718,7 @@ void LedgerConsensus::accept(SHAMap::pointer set)
}
#endif
SerializedValidation v(newLCLHash, mOurPosition->peekKey(), true);
SerializedValidation v(newLCLHash, mOurPosition->peekSeed(), true);
std::vector<unsigned char> validation = v.getSigned();
newcoin::TMValidation val;
val.set_validation(&validation[0], validation.size());
@@ -732,3 +731,4 @@ void LedgerConsensus::endConsensus()
{
theApp->getOPs().endConsensus();
}
// vim:ts=4

View File

@@ -48,7 +48,7 @@ protected:
int mYays, mNays;
bool mOurPosition;
std::vector<unsigned char> transaction;
boost::unordered_map<uint256, bool> mVotes;
boost::unordered_map<uint160, bool> mVotes;
public:
typedef boost::shared_ptr<LCTransaction> pointer;
@@ -60,7 +60,7 @@ public:
bool getOurPosition() const { return mOurPosition; }
const std::vector<unsigned char>& peekTransaction() { return transaction; }
void setVote(const uint256& peer, bool votesYes);
void setVote(const uint160& peer, bool votesYes);
bool updatePosition(int timePassed);
int getAgreeLevel();
@@ -86,7 +86,7 @@ protected:
LedgerProposal::pointer mOurPosition;
// Convergence tracking, trusted peers indexed by hash of public key
boost::unordered_map<uint256, LedgerProposal::pointer> mPeerPositions;
boost::unordered_map<uint160, LedgerProposal::pointer> mPeerPositions;
// Transaction Sets, indexed by hash of transaction tree
boost::unordered_map<uint256, SHAMap::pointer> mComplete;
@@ -107,7 +107,7 @@ protected:
SHAMap::pointer find(const uint256& hash);
void addDisputedTransaction(const uint256&, const std::vector<unsigned char>& transaction);
void adjustCount(SHAMap::pointer map, const std::vector<uint256>& peers);
void adjustCount(SHAMap::pointer map, const std::vector<uint160>& peers);
void propose(const std::vector<uint256>& addedTx, const std::vector<uint256>& removedTx);
void addPosition(LedgerProposal&, bool ours);

View File

@@ -7,34 +7,44 @@
#include "Application.h"
LedgerProposal::LedgerProposal(const uint256& pLgr, uint32 seq, const uint256& tx, const std::string& pubKey) :
mPreviousLedger(pLgr), mCurrentHash(tx), mProposeSeq(seq), mKey(boost::make_shared<CKey>())
mPreviousLedger(pLgr), mCurrentHash(tx), mProposeSeq(seq)
{
if (!mKey->SetPubKey(pubKey))
throw std::runtime_error("Invalid public key in proposal");
mPreviousLedger = theApp->getMasterLedger().getClosedLedger()->getHash();
mPeerID = Serializer::getSHA512Half(mKey->GetPubKey());
// XXX Make caller give us a vuc for pubkey.
mPublicKey.setNodePublic(strCopy(pubKey));
// XXX Validate key.
// if (!mKey->SetPubKey(pubKey))
// throw std::runtime_error("Invalid public key in proposal");
mPreviousLedger = theApp->getMasterLedger().getClosedLedger()->getHash();
mPeerID = mPublicKey.getNodeID();
}
LedgerProposal::LedgerProposal(CKey::pointer mPrivateKey, const uint256& prevLgr, const uint256& position) :
mPreviousLedger(prevLgr), mCurrentHash(position), mProposeSeq(0), mKey(mPrivateKey)
LedgerProposal::LedgerProposal(const NewcoinAddress& naSeed, const uint256& prevLgr, const uint256& position) :
mPreviousLedger(prevLgr), mCurrentHash(position), mProposeSeq(0)
{
mPeerID = Serializer::getSHA512Half(mKey->GetPubKey());
mSeed = naSeed;
mPublicKey = NewcoinAddress::createNodePublic(naSeed);
mPrivateKey = NewcoinAddress::createNodePrivate(naSeed);
mPeerID = mPublicKey.getNodeID();
}
uint256 LedgerProposal::getSigningHash() const
{
Serializer s(72);
s.add32(sProposeMagic);
s.add32(mProposeSeq);
s.add256(mPreviousLedger);
s.add256(mCurrentHash);
return s.getSHA512Half();
}
bool LedgerProposal::checkSign(const std::string& signature)
{
return mKey->Verify(getSigningHash(), signature);
return mPublicKey.verifyNodePublic(getSigningHash(), signature);
}
void LedgerProposal::changePosition(const uint256& newPosition)
@@ -46,7 +56,13 @@ void LedgerProposal::changePosition(const uint256& newPosition)
std::vector<unsigned char> LedgerProposal::sign(void)
{
std::vector<unsigned char> ret;
if (!mKey->Sign(getSigningHash(), ret))
throw std::runtime_error("unable to sign proposal");
mPrivateKey.signNodePrivate(getSigningHash(), ret);
// XXX If this can fail, find out sooner.
// if (!mPrivateKey.signNodePrivate(getSigningHash(), ret))
// throw std::runtime_error("unable to sign proposal");
return ret;
}
// vim:ts=4

View File

@@ -5,17 +5,20 @@
#include <boost/shared_ptr.hpp>
#include "uint256.h"
#include "key.h"
#include "NewcoinAddress.h"
#include "Serializer.h"
class LedgerProposal
{
protected:
uint256 mPeerID, mPreviousLedger, mCurrentHash;
uint256 mPreviousLedger, mCurrentHash;
uint32 mProposeSeq;
CKey::pointer mKey;
uint160 mPeerID;
NewcoinAddress mPublicKey; // Peer
NewcoinAddress mPrivateKey; // Our's
NewcoinAddress mSeed; // Our's
static const uint32 sProposeMagic = 0x50525000; // PRP
@@ -27,20 +30,22 @@ public:
LedgerProposal(const uint256& prevLgr, uint32 proposeSeq, const uint256& propose, const std::string& pubKey);
// our first proposal
LedgerProposal(CKey::pointer privateKey, const uint256& prevLedger, const uint256& position);
LedgerProposal(const NewcoinAddress& naSeed, const uint256& prevLedger, const uint256& position);
uint256 getSigningHash() const;
bool checkSign(const std::string& signature);
const uint256& getPeerID() const { return mPeerID; }
const uint160& getPeerID() const { return mPeerID; }
const uint256& getCurrentHash() const { return mCurrentHash; }
const uint256& getPrevLedger() const { return mPreviousLedger; }
uint32 getProposeSeq() const { return mProposeSeq; }
CKey::pointer peekKey() { return mKey; }
std::vector<unsigned char> getPubKey() const { return mKey->GetPubKey(); }
const NewcoinAddress& peekSeed() const { return mSeed; }
std::vector<unsigned char> getPubKey() const { return mPublicKey.getNodePublic(); }
std::vector<unsigned char> sign();
void changePosition(const uint256& newPosition);
};
#endif
// vim:ts=4

View File

@@ -18,22 +18,26 @@ SerializedValidation::SerializedValidation(SerializerIterator& sit, bool checkSi
if (!isValid()) throw std::runtime_error("Invalid validation");
}
SerializedValidation::SerializedValidation(const uint256& ledgerHash, CKey::pointer nodeKey, bool isFull)
SerializedValidation::SerializedValidation(const uint256& ledgerHash, const NewcoinAddress& naSeed, bool isFull)
: STObject(sValidationFormat), mSignature("Signature")
{
setValueFieldH256(sfLedgerHash, ledgerHash);
setValueFieldVL(sfSigningKey, nodeKey->GetPubKey());
setValueFieldVL(sfSigningKey, NewcoinAddress::createNodePublic(naSeed).getNodePublic());
if (!isFull) setFlag(sFullFlag);
if (!nodeKey->Sign(getSigningHash(), mSignature.peekValue()))
throw std::runtime_error("Unable to sign validation");
NewcoinAddress::createNodePrivate(naSeed).signNodePrivate(getSigningHash(), mSignature.peekValue());
// XXX Check if this can fail.
// if (!NewcoinAddress::createNodePrivate(naSeed).signNodePrivate(getSigningHash(), mSignature.peekValue()))
// throw std::runtime_error("Unable to sign validation");
}
uint256 SerializedValidation::getSigningHash() const
{
Serializer s;
s.add32(sValidationMagic);
add(s);
return s.getSHA512Half();
}
@@ -46,9 +50,9 @@ bool SerializedValidation::isValid() const
{
try
{
CKey pubKey;
return pubKey.SetPubKey(getValueFieldVL(sfSigningKey)) &&
pubKey.Verify(getSigningHash(), mSignature.peekValue());
NewcoinAddress naPublicKey = NewcoinAddress::createNodePublic(getValueFieldVL(sfSigningKey));
return naPublicKey.isValid() && naPublicKey.verifyNodePublic(getSigningHash(), mSignature.peekValue());
}
catch (...)
{

View File

@@ -2,6 +2,7 @@
#define __VALIDATION__
#include "SerializedObject.h"
#include "NewcoinAddress.h"
class SerializedValidation : public STObject
{
@@ -19,7 +20,7 @@ public:
SerializedValidation(SerializerIterator& sit, bool checkSignature = true);
SerializedValidation(const Serializer& s, bool checkSignature = true);
SerializedValidation(const uint256& ledgerHash, CKey::pointer nodeKey, bool isFull);
SerializedValidation(const uint256& ledgerHash, const NewcoinAddress& naSeed, bool isFull);
uint256 getLedgerHash() const;
NewcoinAddress getSignerPublic() const;