void PeerSet::TimerEntry (boost::weak_ptr<PeerSet> wptr, const boost::system::error_code& result) { if (result == boost::asio::error::operation_aborted) return; boost::shared_ptr<PeerSet> ptr = wptr.lock (); if (ptr) { if (ptr->mTxnData) { getApp().getJobQueue ().addJob (jtTXN_DATA, "timerEntryTxn", BIND_TYPE (&PeerSet::TimerJobEntry, P_1, ptr)); } else { int jc = getApp().getJobQueue ().getJobCountTotal (jtLEDGER_DATA); if (jc > 4) { WriteLog (lsDEBUG, InboundLedger) << "Deferring PeerSet timer due to load"; ptr->setTimer (); } else getApp().getJobQueue ().addJob (jtLEDGER_DATA, "timerEntryLgr", BIND_TYPE (&PeerSet::TimerJobEntry, P_1, ptr)); } } }
/** We received a TMLedgerData from a peer. */ bool gotLedgerData (LedgerHash const& hash, boost::shared_ptr<Peer> peer, boost::shared_ptr<protocol::TMLedgerData> packet_ptr) { protocol::TMLedgerData& packet = *packet_ptr; WriteLog (lsTRACE, InboundLedger) << "Got data (" << packet.nodes ().size () << ") for acquiring ledger: " << hash; InboundLedger::pointer ledger = find (hash); if (!ledger) { WriteLog (lsTRACE, InboundLedger) << "Got data for ledger we're no longer acquiring"; // If it's state node data, stash it because it still might be useful if (packet.type () == protocol::liAS_NODE) { getApp().getJobQueue().addJob(jtLEDGER_DATA, "gotStaleData", BIND_TYPE(&InboundLedgers::gotStaleData, this, packet_ptr)); } return false; } // Stash the data for later processing and see if we need to dispatch if (ledger->gotData(boost::weak_ptr<Peer>(peer), packet_ptr)) getApp().getJobQueue().addJob (jtLEDGER_DATA, "processLedgerData", BIND_TYPE (&InboundLedgers::doLedgerData, this, P_1, hash)); return true; }
void ConsensusTransSetSF::gotNode (bool fromFilter, const SHAMapNode& id, uint256 const& nodeHash, Blob& nodeData, SHAMapTreeNode::TNType type) { if (fromFilter) return; m_nodeCache.insert (nodeHash, nodeData); if ((type == SHAMapTreeNode::tnTRANSACTION_NM) && (nodeData.size () > 16)) { // this is a transaction, and we didn't have it WriteLog (lsDEBUG, TransactionAcquire) << "Node on our acquiring TX set is TXN we may not have"; try { Serializer s (nodeData.begin () + 4, nodeData.end ()); // skip prefix SerializerIterator sit (s); SerializedTransaction::pointer stx = boost::make_shared<SerializedTransaction> (boost::ref (sit)); assert (stx->getTransactionID () == nodeHash); getApp().getJobQueue ().addJob (jtTRANSACTION, "TXS->TXN", BIND_TYPE (&NetworkOPs::submitTransaction, &getApp().getOPs (), P_1, stx)); } catch (...) { WriteLog (lsWARNING, TransactionAcquire) << "Fetched invalid transaction in proposed set"; } } }
void RPCSub::send (const Json::Value& jvObj, bool broadcast) { boost::mutex::scoped_lock sl (mLockInfo); if (RPC_EVENT_QUEUE_MAX == mDeque.size ()) { // Drop the previous event. WriteLog (lsWARNING, RPCSub) << boost::str (boost::format ("callRPC drop")); mDeque.pop_back (); } WriteLog (broadcast ? lsDEBUG : lsINFO, RPCSub) << boost::str (boost::format ("callRPC push: %s") % jvObj); mDeque.push_back (std::make_pair (mSeq++, jvObj)); if (!mSending) { // Start a sending thread. mSending = true; WriteLog (lsINFO, RPCSub) << boost::str (boost::format ("callRPC start")); getApp().getJobQueue ().addJob ( jtCLIENT, "RPCSub::sendThread", BIND_TYPE (&RPCSub::sendThread, this)); } }
void OrderBookDB::update (Ledger::pointer ledger) { boost::unordered_set< uint256 > seen; boost::unordered_map< currencyIssuer_t, std::vector<OrderBook::pointer> > destMap; boost::unordered_map< currencyIssuer_t, std::vector<OrderBook::pointer> > sourceMap; boost::unordered_set< currencyIssuer_t > XRPBooks; WriteLog (lsDEBUG, OrderBookDB) << "OrderBookDB::update>"; // walk through the entire ledger looking for orderbook entries int books = 0; try { ledger->visitStateItems(BIND_TYPE(&updateHelper, P_1, boost::ref(seen), boost::ref(destMap), boost::ref(sourceMap), boost::ref(XRPBooks), boost::ref(books))); } catch (const SHAMapMissingNode&) { WriteLog (lsINFO, OrderBookDB) << "OrderBookDB::update encountered a missing node"; ScopedLockType sl (mLock, __FILE__, __LINE__); mSeq = 0; return; } WriteLog (lsDEBUG, OrderBookDB) << "OrderBookDB::update< " << books << " books found"; { ScopedLockType sl (mLock, __FILE__, __LINE__); mXRPBooks.swap(XRPBooks); mSourceMap.swap(sourceMap); mDestMap.swap(destMap); } getApp().getLedgerMaster().newOrderBookDB(); }
void OrderBookDB::setup (Ledger::ref ledger) { { ScopedLockType sl (mLock, __FILE__, __LINE__); // Do a full update every 256 ledgers if (mSeq != 0) { if (ledger->getLedgerSeq () == mSeq) return; if ((ledger->getLedgerSeq () > mSeq) && ((ledger->getLedgerSeq () - mSeq) < 256)) return; if ((ledger->getLedgerSeq () < mSeq) && ((mSeq - ledger->getLedgerSeq ()) < 16)) return; } WriteLog (lsDEBUG, OrderBookDB) << "Advancing from " << mSeq << " to " << ledger->getLedgerSeq(); mSeq = ledger->getLedgerSeq (); } if (getConfig().RUN_STANDALONE) update(ledger); else getApp().getJobQueue().addJob(jtUPDATE_PF, "OrderBookDB::update", BIND_TYPE(&OrderBookDB::update, this, ledger)); }
void RPCCall::fromNetwork ( boost::asio::io_service& io_service, const std::string& strIp, const int iPort, const std::string& strUsername, const std::string& strPassword, const std::string& strPath, const std::string& strMethod, const Json::Value& jvParams, const bool bSSL, FUNCTION_TYPE<void (const Json::Value& jvInput)> callbackFuncP) { // Connect to localhost if (!getConfig ().QUIET) { Log::out() << "Connecting to: " << strIp << ":" << iPort; // Log::out() << "Username: "******":" << strPassword; // Log::out() << "Path: " << strPath; // Log::out() << "Method: " << strMethod; } // HTTP basic authentication std::string strUserPass64 = RPCParser::EncodeBase64 (strUsername + ":" + strPassword); std::map<std::string, std::string> mapRequestHeaders; mapRequestHeaders["Authorization"] = std::string ("Basic ") + strUserPass64; // Send request // Log(lsDEBUG) << "requesting" << std::endl; // WriteLog (lsDEBUG, RPCParser) << "send request " << strMethod << " : " << strRequest << std::endl; const int RPC_REPLY_MAX_BYTES (128*1024*1024); const int RPC_NOTIFY_SECONDS (30); HTTPClient::request ( bSSL, io_service, strIp, iPort, BIND_TYPE ( &RPCCallImp::onRequest, strMethod, jvParams, mapRequestHeaders, strPath, P_1, P_2), RPC_REPLY_MAX_BYTES, boost::posix_time::seconds (RPC_NOTIFY_SECONDS), BIND_TYPE (&RPCCallImp::onResponse, callbackFuncP, P_1, P_2, P_3)); }
void TransactionAcquire::done () { // We hold a PeerSet lock and so cannot acquire the master lock here SHAMap::pointer map; if (mFailed) { WriteLog (lsWARNING, TransactionAcquire) << "Failed to acquire TX set " << mHash; } else { WriteLog (lsINFO, TransactionAcquire) << "Acquired TX set " << mHash; mMap->setImmutable (); map = mMap; } getApp().getIOService ().post (BIND_TYPE (&TACompletionHandler, mHash, map)); }
void SqliteDatabase::doHook (const char* db, int pages) { if (pages < 1000) return; { ScopedLockType sl (m_walMutex); if (walRunning) return; walRunning = true; } if (mWalQ) { mWalQ->addJob (jtWAL, std::string ("WAL:") + mHost, BIND_TYPE (&SqliteDatabase::runWal, this)); } else { notify(); } }
void SqliteDatabase::doHook (const char* db, int pages) { if (pages < 1000) return; { boost::mutex::scoped_lock sl (walMutex); if (walRunning) return; walRunning = true; } if (mWalQ) { mWalQ->addJob (jtWAL, std::string ("WAL:") + mHost, BIND_TYPE (&SqliteDatabase::runWal, this)); } else { m_thread.call (&SqliteDatabase::runWal, this); } }
int RPCCall::fromCommandLine (const std::vector<std::string>& vCmd) { Json::Value jvOutput; int nRet = 0; Json::Value jvRequest (Json::objectValue); try { RPCParser rpParser; Json::Value jvRpcParams (Json::arrayValue); if (vCmd.empty ()) return 1; // 1 = print usage. for (int i = 1; i != vCmd.size (); i++) jvRpcParams.append (vCmd[i]); Json::Value jvRpc = Json::Value (Json::objectValue); jvRpc["method"] = vCmd[0]; jvRpc["params"] = jvRpcParams; jvRequest = rpParser.parseCommand (vCmd[0], jvRpcParams, true); WriteLog (lsTRACE, RPCParser) << "RPC Request: " << jvRequest << std::endl; if (jvRequest.isMember ("error")) { jvOutput = jvRequest; jvOutput["rpc"] = jvRpc; } else { Json::Value jvParams (Json::arrayValue); jvParams.append (jvRequest); if (!getConfig ().RPC_ADMIN_USER.empty ()) jvRequest["admin_user"] = getConfig ().RPC_ADMIN_USER; if (!getConfig ().RPC_ADMIN_PASSWORD.empty ()) jvRequest["admin_password"] = getConfig ().RPC_ADMIN_PASSWORD; boost::asio::io_service isService; fromNetwork ( isService, getConfig ().getRpcIP (), getConfig ().getRpcPort (), getConfig ().RPC_USER, getConfig ().RPC_PASSWORD, "", jvRequest.isMember ("method") // Allow parser to rewrite method. ? jvRequest["method"].asString () : vCmd[0], jvParams, // Parsed, execute. false, BIND_TYPE (RPCCallImp::callRPCHandler, &jvOutput, P_1)); isService.run (); // This blocks until there is no more outstanding async calls. if (jvOutput.isMember ("result")) { // Had a successful JSON-RPC 2.0 call. jvOutput = jvOutput["result"]; // jvOutput may report a server side error. // It should report "status". } else { // Transport error. Json::Value jvRpcError = jvOutput; jvOutput = rpcError (rpcJSON_RPC); jvOutput["result"] = jvRpcError; } // If had an error, supply invokation in result. if (jvOutput.isMember ("error")) { jvOutput["rpc"] = jvRpc; // How the command was seen as method + params. jvOutput["request_sent"] = jvRequest; // How the command was translated. } } if (jvOutput.isMember ("error")) { jvOutput["status"] = "error"; nRet = jvOutput.isMember ("error_code") ? lexicalCast <int> (jvOutput["error_code"].asString ()) : 1; } // YYY We could have a command line flag for single line output for scripts. // YYY We would intercept output here and simplify it. } catch (std::exception& e) { jvOutput = rpcError (rpcINTERNAL); jvOutput["error_what"] = e.what (); nRet = rpcINTERNAL; } catch (...) { jvOutput = rpcError (rpcINTERNAL); jvOutput["error_what"] = "exception"; nRet = rpcINTERNAL; } std::cout << jvOutput.toStyledString (); return nRet; }
std::list<SHAMap::fetchPackEntry_t> SHAMap::getFetchPack (SHAMap* have, bool includeLeaves, int max) { std::list<fetchPackEntry_t> ret; getFetchPack (have, includeLeaves, max, BIND_TYPE (addFPtoList, boost::ref (ret), P_1, P_2)); return ret; }