Fabcoin Core  0.16.2
P2P Digital Currency
WhisperPeer.cpp
Go to the documentation of this file.
1 /*
2  This file is part of cpp-ethereum.
3 
4  cpp-ethereum is free software: you can redistribute it and/or modify
5  it under the terms of the GNU General Public License as published by
6  the Free Software Foundation, either version 3 of the License, or
7  (at your option) any later version.
8 
9  cpp-ethereum is distributed in the hope that it will be useful,
10  but WITHOUT ANY WARRANTY; without even the implied warranty of
11  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  GNU General Public License for more details.
13 
14  You should have received a copy of the GNU General Public License
15  along with cpp-ethereum. If not, see <http://www.gnu.org/licenses/>.
16 */
22 #include <libdevcore/Log.h>
23 #include <libp2p/All.h>
24 #include "WhisperHost.h"
25 
26 using namespace std;
27 using namespace dev;
28 using namespace dev::p2p;
29 using namespace dev::shh;
30 
31 WhisperPeer::WhisperPeer(std::shared_ptr<SessionFace> _s, HostCapabilityFace* _h, unsigned _i, CapDesc const&, uint16_t _capID):
32  Capability(_s, _h, _i, _capID)
33 {
34  RLPStream s;
35  sealAndSend(prep(s, StatusPacket, 1) << version());
37 }
38 
40 {
41 }
42 
44 {
45  return static_cast<WhisperHost*>(Capability::hostCapability());
46 }
47 
48 bool WhisperPeer::interpret(unsigned _id, RLP const& _r)
49 {
50  switch (_id)
51  {
52  case StatusPacket:
53  {
54  auto protocolVersion = _r[0].toInt<unsigned>();
55 
56  clog(NetMessageSummary) << "Status: " << protocolVersion;
57 
58  if (protocolVersion != version())
59  disable("Invalid protocol version.");
60 
61  for (auto const& m: host()->all())
62  {
63  Guard l(x_unseen);
64  m_unseen.insert(make_pair(0, m.first));
65  }
66 
67  if (session()->id() < host()->host()->id())
68  sendMessages();
69 
71  break;
72  }
73  case MessagesPacket:
74  {
75  for (auto i: _r)
76  host()->inject(Envelope(i), this);
77  break;
78  }
79  case TopicFilterPacket:
80  {
82  break;
83  }
84  default:
85  return false;
86  }
87  return true;
88 }
89 
91 {
94 
95  multimap<unsigned, h256> available;
97  m_unseen.swap(available);
98 
99  RLPStream amalg;
100 
101  // send the highest rated messages first
102  for (auto i = available.rbegin(); i != available.rend(); ++i)
103  host()->streamMessage(i->second, amalg);
104 
105  unsigned msgCount = available.size();
106  if (msgCount)
107  {
108  RLPStream s;
109  prep(s, MessagesPacket, msgCount).appendRaw(amalg.out(), msgCount);
110  sealAndSend(s);
111  }
112 }
113 
115 {
116  unsigned rate = ratingForPeer(_m);
117  Guard l(x_unseen);
118  m_unseen.insert(make_pair(rate, _h));
119 }
120 
121 unsigned WhisperPeer::ratingForPeer(Envelope const& e) const
122 {
123  // we try to estimate, how valuable this nessage will be for the remote peer,
124  // according to the following criteria:
125  // 1. bloom filter
126  // 2. time to live
127  // 3. proof of work
128 
129  unsigned rating = 0;
130 
131  if (e.matchesBloomFilter(bloom()))
132  ++rating;
133 
134  rating *= 256;
135  unsigned ttlReward = (256 > e.ttl() ? 256 - e.ttl() : 0);
136  rating += ttlReward;
137 
138  rating *= 256;
139  rating += e.workProved();
140  return rating;
141 }
142 
144 {
147 
148  RLPStream s;
149  prep(s, TopicFilterPacket, 1);
150  s << _bloom;
151  sealAndSend(s);
152 }
153 
Adapted from code found on http://stackoverflow.com/questions/180947/base64-decode-snippet-in-c Origi...
Definition: Arith256.cpp:15
WhisperHost * host() const
Definition: WhisperPeer.cpp:43
virtual void inject(Envelope const &_e, WhisperPeer *_from=nullptr) override
Definition: WhisperHost.cpp:55
unsigned ratingForPeer(Envelope const &e) const
std::pair< std::string, u256 > CapDesc
Definition: Common.h:142
void streamMessage(h256 _m, RLPStream &_s) const
Definition: WhisperHost.cpp:43
bytes const & out() const
Read the byte stream.
Definition: RLP.h:433
virtual bool interpret(unsigned _id, RLP const &) override
Definition: WhisperPeer.cpp:48
static u256 version()
Definition: WhisperPeer.h:56
std::hash for asio::adress
Definition: Common.h:323
Definition: Eth.h:45
dev::Mutex x_advertiseTopicsOfInterest
Definition: WhisperPeer.h:76
std::multimap< unsigned, h256 > m_unseen
Rated according to what they want.
Definition: WhisperPeer.h:70
TopicBloomFilterHash bloom() const
Definition: WhisperPeer.h:58
#define DEV_GUARDED(MUTEX)
Simple block guard.
Definition: Guards.h:144
std::lock_guard< std::mutex > Guard
Definition: Guards.h:41
void noteAdvertiseTopicsOfInterest()
Definition: WhisperPeer.h:60
void setBloom(TopicBloomFilterHash const &_b)
Definition: WhisperPeer.h:67
unsigned workProved() const
Definition: Message.cpp:155
#define clog(X)
Definition: Log.h:295
#define e(i)
Definition: sha.cpp:733
bool matchesBloomFilter(TopicBloomFilterHash const &f) const
Definition: Message.cpp:184
void noteNewMessage(h256 _h, Envelope const &_m)
unsigned ttl() const
Definition: Message.h:75
void sendTopicsOfInterest(TopicBloomFilterHash const &_bloom)
sends our bloom filter to remote peer
bool m_advertiseTopicsOfInterest
Definition: WhisperPeer.h:77
_T toInt(int _flags=Strict) const
Converts to int of type given; if isString(), decodes as big-endian bytestream.
Definition: RLP.h:275
Class for writing to an RLP bytestream.
Definition: RLP.h:383
RLPStream & appendRaw(bytesConstRef _rlp, size_t _itemCount=1)
Appends raw (pre-serialised) RLP data. Use with caution.
Definition: RLP.cpp:230
Class for interpreting Recursive Linear-Prefix Data.
Definition: RLP.h:64