PacketDecoder.cpp 32 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708
  1. /*
  2. * ZeroTier One - Global Peer to Peer Ethernet
  3. * Copyright (C) 2012-2013 ZeroTier Networks LLC
  4. *
  5. * This program is free software: you can redistribute it and/or modify
  6. * it under the terms of the GNU General Public License as published by
  7. * the Free Software Foundation, either version 3 of the License, or
  8. * (at your option) any later version.
  9. *
  10. * This program is distributed in the hope that it will be useful,
  11. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. * GNU General Public License for more details.
  14. *
  15. * You should have received a copy of the GNU General Public License
  16. * along with this program. If not, see <http://www.gnu.org/licenses/>.
  17. *
  18. * --
  19. *
  20. * ZeroTier may be used and distributed under the terms of the GPLv3, which
  21. * are available at: http://www.gnu.org/licenses/gpl-3.0.html
  22. *
  23. * If you would like to embed ZeroTier into a commercial application or
  24. * redistribute it in a modified binary form, please contact ZeroTier Networks
  25. * LLC. Start here: http://www.zerotier.com/
  26. */
  27. #include "../version.h"
  28. #include "Constants.hpp"
  29. #include "Defaults.hpp"
  30. #include "RuntimeEnvironment.hpp"
  31. #include "Topology.hpp"
  32. #include "PacketDecoder.hpp"
  33. #include "Switch.hpp"
  34. #include "Peer.hpp"
  35. #include "NodeConfig.hpp"
  36. #include "Filter.hpp"
  37. #include "Service.hpp"
  38. #include "Demarc.hpp"
  39. namespace ZeroTier {
  40. bool PacketDecoder::tryDecode(const RuntimeEnvironment *_r)
  41. throw(std::out_of_range,std::runtime_error)
  42. {
  43. if ((!encrypted())&&(verb() == Packet::VERB_HELLO)) {
  44. // Unencrypted HELLOs are handled here since they are used to
  45. // populate our identity cache in the first place. _doHELLO() is special
  46. // in that it contains its own authentication logic.
  47. TRACE("HELLO from %s(%s)",source().toString().c_str(),_remoteAddress.toString().c_str());
  48. return _doHELLO(_r);
  49. }
  50. SharedPtr<Peer> peer = _r->topology->getPeer(source());
  51. if (peer) {
  52. // Resume saved intermediate decode state?
  53. if (_step == DECODE_WAITING_FOR_MULTICAST_FRAME_ORIGINAL_SENDER_LOOKUP) {
  54. // In this state we have already authenticated and decrypted the
  55. // packet and are waiting for the lookup of the original sender
  56. // for a multicast frame. So check to see if we've got it.
  57. return _doMULTICAST_FRAME(_r,peer);
  58. }
  59. if (!dearmor(peer->key())) {
  60. TRACE("dropped packet from %s(%s), MAC authentication failed (size: %u)",source().toString().c_str(),_remoteAddress.toString().c_str(),size());
  61. return true;
  62. }
  63. if (!uncompress()) {
  64. TRACE("dropped packet from %s(%s), compressed data invalid",source().toString().c_str(),_remoteAddress.toString().c_str());
  65. return true;
  66. }
  67. Packet::Verb v = verb();
  68. // Once a packet is determined to be basically valid, it can be used
  69. // to passively learn a new network path to the sending peer. It
  70. // also results in statistics updates.
  71. peer->onReceive(_r,_localPort,_remoteAddress,hops(),v,Utils::now());
  72. switch(v) {
  73. case Packet::VERB_NOP:
  74. TRACE("NOP from %s(%s)",source().toString().c_str(),_remoteAddress.toString().c_str());
  75. return true;
  76. case Packet::VERB_HELLO:
  77. return _doHELLO(_r); // legal, but why? :)
  78. case Packet::VERB_ERROR:
  79. return _doERROR(_r,peer);
  80. case Packet::VERB_OK:
  81. return _doOK(_r,peer);
  82. case Packet::VERB_WHOIS:
  83. return _doWHOIS(_r,peer);
  84. case Packet::VERB_RENDEZVOUS:
  85. return _doRENDEZVOUS(_r,peer);
  86. case Packet::VERB_FRAME:
  87. return _doFRAME(_r,peer);
  88. case Packet::VERB_PROXY_FRAME:
  89. return _doPROXY_FRAME(_r,peer);
  90. case Packet::VERB_MULTICAST_FRAME:
  91. return _doMULTICAST_FRAME(_r,peer);
  92. case Packet::VERB_MULTICAST_LIKE:
  93. return _doMULTICAST_LIKE(_r,peer);
  94. case Packet::VERB_NETWORK_MEMBERSHIP_CERTIFICATE:
  95. return _doNETWORK_MEMBERSHIP_CERTIFICATE(_r,peer);
  96. case Packet::VERB_NETWORK_CONFIG_REQUEST:
  97. return _doNETWORK_CONFIG_REQUEST(_r,peer);
  98. case Packet::VERB_NETWORK_CONFIG_REFRESH:
  99. return _doNETWORK_CONFIG_REFRESH(_r,peer);
  100. default:
  101. // This might be something from a new or old version of the protocol.
  102. // Technically it passed MAC so the packet is still valid, but we
  103. // ignore it.
  104. TRACE("ignored unrecognized verb %.2x from %s(%s)",(unsigned int)v,source().toString().c_str(),_remoteAddress.toString().c_str());
  105. return true;
  106. }
  107. } else {
  108. _step = DECODE_WAITING_FOR_SENDER_LOOKUP; // should already be this...
  109. _r->sw->requestWhois(source());
  110. return false;
  111. }
  112. }
  113. void PacketDecoder::_CBaddPeerFromHello(void *arg,const SharedPtr<Peer> &p,Topology::PeerVerifyResult result)
  114. {
  115. _CBaddPeerFromHello_Data *req = (_CBaddPeerFromHello_Data *)arg;
  116. const RuntimeEnvironment *_r = req->renv;
  117. try {
  118. switch(result) {
  119. case Topology::PEER_VERIFY_ACCEPTED_NEW:
  120. case Topology::PEER_VERIFY_ACCEPTED_ALREADY_HAVE:
  121. case Topology::PEER_VERIFY_ACCEPTED_DISPLACED_INVALID_ADDRESS: {
  122. _r->sw->doAnythingWaitingForPeer(p);
  123. Packet outp(req->source,_r->identity.address(),Packet::VERB_OK);
  124. outp.append((unsigned char)Packet::VERB_HELLO);
  125. outp.append(req->helloPacketId);
  126. outp.append(req->helloTimestamp);
  127. outp.append((unsigned char)ZT_PROTO_VERSION);
  128. outp.append((unsigned char)ZEROTIER_ONE_VERSION_MAJOR);
  129. outp.append((unsigned char)ZEROTIER_ONE_VERSION_MINOR);
  130. outp.append((uint16_t)ZEROTIER_ONE_VERSION_REVISION);
  131. outp.armor(p->key(),true);
  132. _r->demarc->send(req->localPort,req->remoteAddress,outp.data(),outp.size(),-1);
  133. } break;
  134. case Topology::PEER_VERIFY_REJECTED_INVALID_IDENTITY: {
  135. Packet outp(req->source,_r->identity.address(),Packet::VERB_ERROR);
  136. outp.append((unsigned char)Packet::VERB_HELLO);
  137. outp.append(req->helloPacketId);
  138. outp.append((unsigned char)Packet::ERROR_IDENTITY_INVALID);
  139. outp.armor(p->key(),true);
  140. _r->demarc->send(req->localPort,req->remoteAddress,outp.data(),outp.size(),-1);
  141. } break;
  142. case Topology::PEER_VERIFY_REJECTED_DUPLICATE:
  143. case Topology::PEER_VERIFY_REJECTED_DUPLICATE_TRIAGED: {
  144. Packet outp(req->source,_r->identity.address(),Packet::VERB_ERROR);
  145. outp.append((unsigned char)Packet::VERB_HELLO);
  146. outp.append(req->helloPacketId);
  147. outp.append((unsigned char)Packet::ERROR_IDENTITY_COLLISION);
  148. outp.armor(p->key(),true);
  149. _r->demarc->send(req->localPort,req->remoteAddress,outp.data(),outp.size(),-1);
  150. } break;
  151. }
  152. } catch ( ... ) {
  153. TRACE("unexpected exception in addPeer() result callback for peer received via HELLO");
  154. }
  155. delete req;
  156. }
  157. void PacketDecoder::_CBaddPeerFromWhois(void *arg,const SharedPtr<Peer> &p,Topology::PeerVerifyResult result)
  158. {
  159. const RuntimeEnvironment *_r = (const RuntimeEnvironment *)arg;
  160. try {
  161. switch(result) {
  162. case Topology::PEER_VERIFY_ACCEPTED_NEW:
  163. case Topology::PEER_VERIFY_ACCEPTED_ALREADY_HAVE:
  164. case Topology::PEER_VERIFY_ACCEPTED_DISPLACED_INVALID_ADDRESS:
  165. _r->sw->doAnythingWaitingForPeer(p);
  166. break;
  167. default:
  168. break;
  169. }
  170. } catch ( ... ) {
  171. TRACE("unexpected exception in addPeer() result callback for peer received via OK(WHOIS)");
  172. }
  173. }
  174. bool PacketDecoder::_doERROR(const RuntimeEnvironment *_r,const SharedPtr<Peer> &peer)
  175. {
  176. try {
  177. Packet::Verb inReVerb = (Packet::Verb)(*this)[ZT_PROTO_VERB_ERROR_IDX_IN_RE_VERB];
  178. Packet::ErrorCode errorCode = (Packet::ErrorCode)(*this)[ZT_PROTO_VERB_ERROR_IDX_ERROR_CODE];
  179. TRACE("ERROR %s from %s(%s) in-re %s",Packet::errorString(errorCode),source().toString().c_str(),_remoteAddress.toString().c_str(),Packet::verbString(inReVerb));
  180. switch(errorCode) {
  181. case Packet::ERROR_OBJ_NOT_FOUND:
  182. if (inReVerb == Packet::VERB_WHOIS) {
  183. // TODO: abort WHOIS if sender is a supernode
  184. }
  185. break;
  186. case Packet::ERROR_IDENTITY_COLLISION:
  187. case Packet::ERROR_IDENTITY_INVALID:
  188. // TODO: if it comes from a supernode, regenerate a new identity
  189. break;
  190. case Packet::ERROR_NO_MEMBER_CERTIFICATE:
  191. // TODO: send member certificate
  192. break;
  193. default:
  194. break;
  195. }
  196. } catch (std::exception &ex) {
  197. TRACE("dropped ERROR from %s(%s): unexpected exception: %s",source().toString().c_str(),_remoteAddress.toString().c_str(),ex.what());
  198. } catch ( ... ) {
  199. TRACE("dropped ERROR from %s(%s): unexpected exception: (unknown)",source().toString().c_str(),_remoteAddress.toString().c_str());
  200. }
  201. return true;
  202. }
  203. bool PacketDecoder::_doHELLO(const RuntimeEnvironment *_r)
  204. {
  205. try {
  206. //unsigned int protoVersion = (*this)[ZT_PROTO_VERB_HELLO_IDX_PROTOCOL_VERSION];
  207. unsigned int vMajor = (*this)[ZT_PROTO_VERB_HELLO_IDX_MAJOR_VERSION];
  208. unsigned int vMinor = (*this)[ZT_PROTO_VERB_HELLO_IDX_MINOR_VERSION];
  209. unsigned int vRevision = at<uint16_t>(ZT_PROTO_VERB_HELLO_IDX_REVISION);
  210. uint64_t timestamp = at<uint64_t>(ZT_PROTO_VERB_HELLO_IDX_TIMESTAMP);
  211. Identity id(*this,ZT_PROTO_VERB_HELLO_IDX_IDENTITY);
  212. // Initial sniff test for valid addressing and that this is indeed the
  213. // submitter's identity.
  214. if ((id.address().isReserved())||(id.address() != source())) {
  215. #ifdef ZT_TRACE
  216. if (id.address().isReserved()) {
  217. TRACE("dropped HELLO from %s(%s): identity has reserved address",source().toString().c_str(),_remoteAddress.toString().c_str());
  218. } else {
  219. TRACE("dropped HELLO from %s(%s): identity is not for sender of packet (HELLO is a self-announcement)",source().toString().c_str(),_remoteAddress.toString().c_str());
  220. }
  221. #endif
  222. return true;
  223. }
  224. // Is this a HELLO for a peer we already know? If so just update its
  225. // packet receive stats and send an OK.
  226. SharedPtr<Peer> existingPeer(_r->topology->getPeer(id.address()));
  227. if ((existingPeer)&&(existingPeer->identity() == id)) {
  228. existingPeer->onReceive(_r,_localPort,_remoteAddress,hops(),Packet::VERB_HELLO,Utils::now());
  229. existingPeer->setRemoteVersion(vMajor,vMinor,vRevision);
  230. Packet outp(source(),_r->identity.address(),Packet::VERB_OK);
  231. outp.append((unsigned char)Packet::VERB_HELLO);
  232. outp.append(packetId());
  233. outp.append(timestamp);
  234. outp.append((unsigned char)ZT_PROTO_VERSION);
  235. outp.append((unsigned char)ZEROTIER_ONE_VERSION_MAJOR);
  236. outp.append((unsigned char)ZEROTIER_ONE_VERSION_MINOR);
  237. outp.append((uint16_t)ZEROTIER_ONE_VERSION_REVISION);
  238. outp.armor(existingPeer->key(),true);
  239. _r->demarc->send(_localPort,_remoteAddress,outp.data(),outp.size(),-1);
  240. return true;
  241. }
  242. SharedPtr<Peer> candidate(new Peer(_r->identity,id));
  243. candidate->setPathAddress(_remoteAddress,false);
  244. candidate->setRemoteVersion(vMajor,vMinor,vRevision);
  245. _CBaddPeerFromHello_Data *arg = new _CBaddPeerFromHello_Data;
  246. arg->renv = _r;
  247. arg->source = source();
  248. arg->remoteAddress = _remoteAddress;
  249. arg->localPort = _localPort;
  250. arg->vMajor = vMajor;
  251. arg->vMinor = vMinor;
  252. arg->vRevision = vRevision;
  253. arg->helloPacketId = packetId();
  254. arg->helloTimestamp = timestamp;
  255. _r->topology->addPeer(candidate,&PacketDecoder::_CBaddPeerFromHello,arg);
  256. } catch (std::exception &ex) {
  257. TRACE("dropped HELLO from %s(%s): %s",source().toString().c_str(),_remoteAddress.toString().c_str(),ex.what());
  258. } catch ( ... ) {
  259. TRACE("dropped HELLO from %s(%s): unexpected exception",source().toString().c_str(),_remoteAddress.toString().c_str());
  260. }
  261. return true;
  262. }
  263. bool PacketDecoder::_doOK(const RuntimeEnvironment *_r,const SharedPtr<Peer> &peer)
  264. {
  265. try {
  266. Packet::Verb inReVerb = (Packet::Verb)(*this)[ZT_PROTO_VERB_OK_IDX_IN_RE_VERB];
  267. switch(inReVerb) {
  268. case Packet::VERB_HELLO: {
  269. // OK from HELLO permits computation of latency.
  270. unsigned int latency = std::min((unsigned int)(Utils::now() - at<uint64_t>(ZT_PROTO_VERB_HELLO__OK__IDX_TIMESTAMP)),(unsigned int)0xffff);
  271. unsigned int vMajor = (*this)[ZT_PROTO_VERB_HELLO__OK__IDX_MAJOR_VERSION];
  272. unsigned int vMinor = (*this)[ZT_PROTO_VERB_HELLO__OK__IDX_MINOR_VERSION];
  273. unsigned int vRevision = at<uint16_t>(ZT_PROTO_VERB_HELLO__OK__IDX_REVISION);
  274. TRACE("%s(%s): OK(HELLO), latency: %u, version %u.%u.%u",source().toString().c_str(),_remoteAddress.toString().c_str(),latency,vMajor,vMinor,vRevision);
  275. peer->setLatency(_remoteAddress,latency);
  276. peer->setRemoteVersion(vMajor,vMinor,vRevision);
  277. } break;
  278. case Packet::VERB_WHOIS: {
  279. TRACE("%s(%s): OK(%s)",source().toString().c_str(),_remoteAddress.toString().c_str(),Packet::verbString(inReVerb));
  280. if (_r->topology->isSupernode(source())) {
  281. // Right now, only supernodes are queried for WHOIS so we only
  282. // accept OK(WHOIS) from supernodes. Otherwise peers could
  283. // potentially cache-poison.
  284. _r->topology->addPeer(SharedPtr<Peer>(new Peer(_r->identity,Identity(*this,ZT_PROTO_VERB_WHOIS__OK__IDX_IDENTITY))),&PacketDecoder::_CBaddPeerFromWhois,const_cast<void *>((const void *)_r));
  285. }
  286. } break;
  287. case Packet::VERB_NETWORK_CONFIG_REQUEST: {
  288. SharedPtr<Network> nw(_r->nc->network(at<uint64_t>(ZT_PROTO_VERB_NETWORK_CONFIG_REQUEST__OK__IDX_NETWORK_ID)));
  289. if ((nw)&&(nw->controller() == source())) {
  290. // OK(NETWORK_CONFIG_REQUEST) is only accepted from a network's
  291. // controller.
  292. unsigned int dictlen = at<uint16_t>(ZT_PROTO_VERB_NETWORK_CONFIG_REQUEST__OK__IDX_DICT_LEN);
  293. std::string dict((const char *)field(ZT_PROTO_VERB_NETWORK_CONFIG_REQUEST__OK__IDX_DICT,dictlen),dictlen);
  294. if (dict.length()) {
  295. Network::Config netconf(dict);
  296. TRACE("got network configuration for network %.16llx from %s",(unsigned long long)nw->id(),source().toString().c_str());
  297. nw->setConfiguration(netconf);
  298. }
  299. }
  300. } break;
  301. default:
  302. //TRACE("%s(%s): OK(%s)",source().toString().c_str(),_remoteAddress.toString().c_str(),Packet::verbString(inReVerb));
  303. break;
  304. }
  305. } catch (std::exception &ex) {
  306. TRACE("dropped OK from %s(%s): unexpected exception: %s",source().toString().c_str(),_remoteAddress.toString().c_str(),ex.what());
  307. } catch ( ... ) {
  308. TRACE("dropped OK from %s(%s): unexpected exception: (unknown)",source().toString().c_str(),_remoteAddress.toString().c_str());
  309. }
  310. return true;
  311. }
  312. bool PacketDecoder::_doWHOIS(const RuntimeEnvironment *_r,const SharedPtr<Peer> &peer)
  313. {
  314. if (payloadLength() == ZT_ADDRESS_LENGTH) {
  315. SharedPtr<Peer> p(_r->topology->getPeer(Address(payload(),ZT_ADDRESS_LENGTH)));
  316. if (p) {
  317. Packet outp(source(),_r->identity.address(),Packet::VERB_OK);
  318. outp.append((unsigned char)Packet::VERB_WHOIS);
  319. outp.append(packetId());
  320. p->identity().serialize(outp,false);
  321. outp.armor(peer->key(),true);
  322. _r->demarc->send(_localPort,_remoteAddress,outp.data(),outp.size(),-1);
  323. TRACE("sent WHOIS response to %s for %s",source().toString().c_str(),Address(payload(),ZT_ADDRESS_LENGTH).toString().c_str());
  324. } else {
  325. Packet outp(source(),_r->identity.address(),Packet::VERB_ERROR);
  326. outp.append((unsigned char)Packet::VERB_WHOIS);
  327. outp.append(packetId());
  328. outp.append((unsigned char)Packet::ERROR_OBJ_NOT_FOUND);
  329. outp.append(payload(),ZT_ADDRESS_LENGTH);
  330. outp.armor(peer->key(),true);
  331. _r->demarc->send(_localPort,_remoteAddress,outp.data(),outp.size(),-1);
  332. TRACE("sent WHOIS ERROR to %s for %s (not found)",source().toString().c_str(),Address(payload(),ZT_ADDRESS_LENGTH).toString().c_str());
  333. }
  334. } else {
  335. TRACE("dropped WHOIS from %s(%s): missing or invalid address",source().toString().c_str(),_remoteAddress.toString().c_str());
  336. }
  337. return true;
  338. }
  339. bool PacketDecoder::_doRENDEZVOUS(const RuntimeEnvironment *_r,const SharedPtr<Peer> &peer)
  340. {
  341. try {
  342. /*
  343. * At the moment, we only obey RENDEZVOUS if it comes from a designated
  344. * supernode. If relay offloading is implemented to scale the net, this
  345. * will need reconsideration.
  346. *
  347. * The reason is that RENDEZVOUS could technically be used to cause a
  348. * peer to send a weird encrypted UDP packet to an arbitrary IP:port.
  349. * The sender of RENDEZVOUS has no control over the content of this
  350. * packet, but it's still maybe something we want to not allow just
  351. * anyone to order due to possible DDOS or network forensic implications.
  352. * So if we diversify relays, we'll need some way of deciding whether the
  353. * sender is someone we should trust with a RENDEZVOUS hint.
  354. */
  355. if (_r->topology->isSupernode(source())) {
  356. Address with(field(ZT_PROTO_VERB_RENDEZVOUS_IDX_ZTADDRESS,ZT_ADDRESS_LENGTH),ZT_ADDRESS_LENGTH);
  357. SharedPtr<Peer> withPeer(_r->topology->getPeer(with));
  358. if (withPeer) {
  359. unsigned int port = at<uint16_t>(ZT_PROTO_VERB_RENDEZVOUS_IDX_PORT);
  360. unsigned int addrlen = (*this)[ZT_PROTO_VERB_RENDEZVOUS_IDX_ADDRLEN];
  361. if ((port > 0)&&((addrlen == 4)||(addrlen == 16))) {
  362. InetAddress atAddr(field(ZT_PROTO_VERB_RENDEZVOUS_IDX_ADDRESS,addrlen),addrlen,port);
  363. TRACE("RENDEZVOUS from %s says %s might be at %s, starting NAT-t",source().toString().c_str(),with.toString().c_str(),atAddr.toString().c_str());
  364. _r->sw->contact(withPeer,atAddr);
  365. } else {
  366. TRACE("dropped corrupt RENDEZVOUS from %s(%s) (bad address or port)",source().toString().c_str(),_remoteAddress.toString().c_str());
  367. }
  368. } else {
  369. TRACE("ignored RENDEZVOUS from %s(%s) to meet unknown peer %s",source().toString().c_str(),_remoteAddress.toString().c_str(),with.toString().c_str());
  370. }
  371. } else {
  372. TRACE("ignored RENDEZVOUS from %s(%s): source not supernode",source().toString().c_str(),_remoteAddress.toString().c_str());
  373. }
  374. } catch (std::exception &ex) {
  375. TRACE("dropped RENDEZVOUS from %s(%s): %s",source().toString().c_str(),_remoteAddress.toString().c_str(),ex.what());
  376. } catch ( ... ) {
  377. TRACE("dropped RENDEZVOUS from %s(%s): unexpected exception",source().toString().c_str(),_remoteAddress.toString().c_str());
  378. }
  379. return true;
  380. }
  381. bool PacketDecoder::_doFRAME(const RuntimeEnvironment *_r,const SharedPtr<Peer> &peer)
  382. {
  383. try {
  384. SharedPtr<Network> network(_r->nc->network(at<uint64_t>(ZT_PROTO_VERB_FRAME_IDX_NETWORK_ID)));
  385. if (network) {
  386. if (network->isAllowed(source())) {
  387. unsigned int etherType = at<uint16_t>(ZT_PROTO_VERB_FRAME_IDX_ETHERTYPE);
  388. if (network->permitsEtherType(etherType)) {
  389. network->tap().put(source().toMAC(),network->tap().mac(),etherType,data() + ZT_PROTO_VERB_FRAME_IDX_PAYLOAD,size() - ZT_PROTO_VERB_FRAME_IDX_PAYLOAD);
  390. } else if (size() > ZT_PROTO_VERB_FRAME_IDX_PAYLOAD) {
  391. TRACE("dropped FRAME from %s: ethernet type %u not allowed on network %.16llx",source().toString().c_str(),etherType,(unsigned long long)network->id());
  392. }
  393. // Source moves "closer" to us in multicast propagation priority when
  394. // we receive unicast frames from it. This is called "implicit social
  395. // ordering" in other docs.
  396. _r->mc->bringCloser(network->id(),source());
  397. } else {
  398. TRACE("dropped FRAME from %s(%s): not a member of closed network %llu",source().toString().c_str(),_remoteAddress.toString().c_str(),network->id());
  399. Packet outp(source(),_r->identity.address(),Packet::VERB_ERROR);
  400. outp.append((unsigned char)Packet::VERB_FRAME);
  401. outp.append(packetId());
  402. outp.append((unsigned char)Packet::ERROR_NO_MEMBER_CERTIFICATE);
  403. outp.append(network->id());
  404. outp.armor(peer->key(),true);
  405. _r->demarc->send(_localPort,_remoteAddress,outp.data(),outp.size(),-1);
  406. }
  407. } else {
  408. TRACE("dropped FRAME from %s(%s): network %llu unknown",source().toString().c_str(),_remoteAddress.toString().c_str(),at<uint64_t>(ZT_PROTO_VERB_FRAME_IDX_NETWORK_ID));
  409. }
  410. } catch (std::exception &ex) {
  411. TRACE("dropped FRAME from %s(%s): unexpected exception: %s",source().toString().c_str(),_remoteAddress.toString().c_str(),ex.what());
  412. } catch ( ... ) {
  413. TRACE("dropped FRAME from %s(%s): unexpected exception: (unknown)",source().toString().c_str(),_remoteAddress.toString().c_str());
  414. }
  415. return true;
  416. }
  417. bool PacketDecoder::_doPROXY_FRAME(const RuntimeEnvironment *_r,const SharedPtr<Peer> &peer)
  418. {
  419. // TODO: bridging is not implemented yet
  420. return true;
  421. }
  422. bool PacketDecoder::_doMULTICAST_FRAME(const RuntimeEnvironment *_r,const SharedPtr<Peer> &peer)
  423. {
  424. try {
  425. Address origin(Address(field(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_ORIGIN,ZT_PROTO_VERB_MULTICAST_FRAME_LEN_ORIGIN),ZT_ADDRESS_LENGTH));
  426. SharedPtr<Peer> originPeer(_r->topology->getPeer(origin));
  427. if (!originPeer) {
  428. // We must have the origin's identity in order to authenticate a multicast
  429. _r->sw->requestWhois(origin);
  430. _step = DECODE_WAITING_FOR_MULTICAST_FRAME_ORIGINAL_SENDER_LOOKUP; // causes processing to come back here
  431. return false;
  432. }
  433. unsigned int depth = at<uint16_t>(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_PROPAGATION_DEPTH);
  434. unsigned char *fifo = field(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_PROPAGATION_FIFO,ZT_PROTO_VERB_MULTICAST_FRAME_LEN_PROPAGATION_FIFO);
  435. unsigned char *bloom = field(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_PROPAGATION_BLOOM,ZT_PROTO_VERB_MULTICAST_FRAME_LEN_PROPAGATION_BLOOM);
  436. uint64_t nwid = at<uint64_t>(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_NETWORK_ID);
  437. uint16_t bloomNonce = at<uint16_t>(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_PROPAGATION_BLOOM_NONCE);
  438. unsigned int prefixBits = (*this)[ZT_PROTO_VERB_MULTICAST_FRAME_IDX_PROPAGATION_PREFIX_BITS];
  439. unsigned int prefix = (*this)[ZT_PROTO_VERB_MULTICAST_FRAME_IDX_PROPAGATION_PREFIX];
  440. uint64_t guid = at<uint64_t>(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_GUID);
  441. MAC sourceMac(field(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_SOURCE_MAC,ZT_PROTO_VERB_MULTICAST_FRAME_LEN_SOURCE_MAC));
  442. MulticastGroup dest(MAC(field(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_DEST_MAC,ZT_PROTO_VERB_MULTICAST_FRAME_LEN_DEST_MAC)),at<uint32_t>(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_DEST_ADI));
  443. unsigned int etherType = at<uint16_t>(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_ETHERTYPE);
  444. unsigned int frameLen = at<uint16_t>(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_FRAME_LEN);
  445. unsigned char *frame = field(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_FRAME,frameLen);
  446. unsigned int signatureLen = at<uint16_t>(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_FRAME + frameLen);
  447. unsigned char *signature = field(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_FRAME + frameLen + 2,signatureLen);
  448. unsigned int signedPartLen = (ZT_PROTO_VERB_MULTICAST_FRAME_IDX_FRAME - ZT_PROTO_VERB_MULTICAST_FRAME_IDX__START_OF_SIGNED_PORTION) + frameLen;
  449. if (!originPeer->identity().verify(field(ZT_PROTO_VERB_MULTICAST_FRAME_IDX__START_OF_SIGNED_PORTION,signedPartLen),signedPartLen,signature,signatureLen)) {
  450. TRACE("dropped MULTICAST_FRAME from %s(%s): failed signature verification, claims to be from %s",source().toString().c_str(),_remoteAddress.toString().c_str(),origin.toString().c_str());
  451. return true;
  452. }
  453. #ifdef ZT_TRACE_MULTICAST
  454. char mct[256];
  455. Utils::snprintf(mct,sizeof(mct),"%c %s <- %.16llx %.16llx %s via %s depth:%u len:%u",(_r->topology->amSupernode() ? 'S' : '-'),_r->identity.address().toString().c_str(),nwid,guid,origin.toString().c_str(),source().toString().c_str(),depth,frameLen);
  456. _r->demarc->send(Demarc::ANY_PORT,ZT_DEFAULTS.multicastTraceWatcher,mct,strlen(mct),-1);
  457. #endif
  458. if (!dest.mac().isMulticast()) {
  459. TRACE("dropped MULTICAST_FRAME from %s(%s): %s is not a multicast/broadcast address",source().toString().c_str(),_remoteAddress.toString().c_str(),dest.mac().toString().c_str());
  460. return true;
  461. }
  462. bool rateLimitsExceeded = false;
  463. unsigned int maxDepth = ZT_MULTICAST_GLOBAL_MAX_DEPTH;
  464. if ((origin == _r->identity.address())||(_r->mc->deduplicate(nwid,guid))) {
  465. // Ordinary frames will drop duplicates. Supernodes keep propagating
  466. // them since they're used as hubs to link disparate clusters of
  467. // members of the same multicast group.
  468. if (!_r->topology->amSupernode()) {
  469. TRACE("dropped MULTICAST_FRAME from %s(%s): duplicate",source().toString().c_str(),_remoteAddress.toString().c_str());
  470. return true;
  471. }
  472. } else {
  473. // Supernodes however won't do this more than once. If the supernode
  474. // does happen to be a member of the network -- which is usually not
  475. // true -- we don't want to see a ton of copies of the same frame on
  476. // its tap device. Also double or triple counting bandwidth metrics
  477. // for the same frame would not be fair.
  478. SharedPtr<Network> network(_r->nc->network(nwid));
  479. if (network) {
  480. maxDepth = network->multicastDepth(); // pull from network config if available
  481. if (!network->isAllowed(origin)) {
  482. TRACE("didn't inject MULTICAST_FRAME from %s(%s) into %.16llx: sender %s not allowed or we don't have a certificate",source().toString().c_str(),nwid,_remoteAddress.toString().c_str(),origin.toString().c_str());
  483. Packet outp(source(),_r->identity.address(),Packet::VERB_ERROR);
  484. outp.append((unsigned char)Packet::VERB_FRAME);
  485. outp.append(packetId());
  486. outp.append((unsigned char)Packet::ERROR_NO_MEMBER_CERTIFICATE);
  487. outp.append(nwid);
  488. outp.armor(peer->key(),true);
  489. _r->demarc->send(_localPort,_remoteAddress,outp.data(),outp.size(),-1);
  490. // We do not terminate here, since if the member just has an out of
  491. // date cert or hasn't sent us a cert yet we still want to propagate
  492. // the message so multicast works.
  493. } else if ((!network->permitsBridging())&&(!origin.wouldHaveMac(sourceMac))) {
  494. TRACE("didn't inject MULTICAST_FRAME from %s(%s) into %.16llx: source mac %s doesn't belong to %s, and bridging is not supported on network",source().toString().c_str(),nwid,_remoteAddress.toString().c_str(),sourceMac.toString().c_str(),origin.toString().c_str());
  495. } else if (!network->permitsEtherType(etherType)) {
  496. TRACE("didn't inject MULTICAST_FRAME from %s(%s) into %.16llx: ethertype %u is not allowed",source().toString().c_str(),nwid,_remoteAddress.toString().c_str(),etherType);
  497. } else if (!network->updateAndCheckMulticastBalance(origin,dest,frameLen)) {
  498. rateLimitsExceeded = true;
  499. } else {
  500. network->tap().put(sourceMac,dest.mac(),etherType,frame,frameLen);
  501. }
  502. }
  503. }
  504. // We can only really know if rate limit was exceeded if we're a member of
  505. // this network. This will nearly always be true for anyone getting a
  506. // multicast except supernodes, so the net effect will be to truncate
  507. // multicast propagation if the rate limit is exceeded.
  508. if (rateLimitsExceeded) {
  509. TRACE("dropped MULTICAST_FRAME from %s(%s): rate limits exceeded for sender %s",source().toString().c_str(),_remoteAddress.toString().c_str(),origin.toString().c_str());
  510. return true;
  511. }
  512. if (depth == 0xffff) {
  513. TRACE("not forwarding MULTICAST_FRAME from %s(%s): depth == 0xffff (do not forward)",source().toString().c_str(),_remoteAddress.toString().c_str());
  514. return true;
  515. }
  516. if (++depth > maxDepth) {
  517. TRACE("not forwarding MULTICAST_FRAME from %s(%s): max propagation depth reached",source().toString().c_str(),_remoteAddress.toString().c_str());
  518. return true;
  519. }
  520. setAt(ZT_PROTO_VERB_MULTICAST_FRAME_IDX_PROPAGATION_DEPTH,(uint16_t)depth);
  521. // New FIFO with room for one extra, since head will be next hop
  522. unsigned char newFifo[ZT_PROTO_VERB_MULTICAST_FRAME_LEN_PROPAGATION_FIFO + ZT_ADDRESS_LENGTH];
  523. unsigned char *newFifoPtr = newFifo;
  524. unsigned char *newFifoEnd = newFifoPtr + sizeof(newFifo);
  525. for(unsigned int i=0;i<ZT_PROTO_VERB_MULTICAST_FRAME_LEN_PROPAGATION_FIFO;) {
  526. unsigned int j = i;
  527. i += ZT_ADDRESS_LENGTH;
  528. unsigned char zm = 0;
  529. while (j != i)
  530. zm |= (*(newFifoPtr++) = fifo[j++]);
  531. if (!zm) // stop at zero address
  532. break;
  533. }
  534. // Add any next hops we know about to FIFO
  535. _r->mc->getNextHops(nwid,dest,Multicaster::AddToPropagationQueue(&newFifoPtr,newFifoEnd,bloom,bloomNonce,origin,prefixBits,prefix));
  536. // Zero-terminate new FIFO if not completely full
  537. while (newFifoPtr != newFifoEnd)
  538. *(newFifoPtr++) = (unsigned char)0;
  539. // First element in newFifo[] is next hop
  540. Address nextHop(newFifo,ZT_ADDRESS_LENGTH);
  541. if ((!nextHop)&&(!_r->topology->amSupernode())) {
  542. SharedPtr<Peer> supernode(_r->topology->getBestSupernode(&origin,1,true));
  543. if (supernode)
  544. nextHop = supernode->address();
  545. }
  546. if ((!nextHop)||(nextHop == _r->identity.address())) { // check against our addr is a sanity check
  547. TRACE("not forwarding MULTICAST_FRAME from %s(%s): no next hop",source().toString().c_str(),_remoteAddress.toString().c_str());
  548. return true;
  549. }
  550. // The rest of newFifo[] goes back into the packet
  551. memcpy(fifo,newFifo + ZT_ADDRESS_LENGTH,ZT_PROTO_VERB_MULTICAST_FRAME_LEN_PROPAGATION_FIFO);
  552. #ifdef ZT_TRACE_MULTICAST
  553. char mct[256];
  554. Utils::snprintf(mct,sizeof(mct),"%c %s -> %.16llx %.16llx %s via %s",(_r->topology->amSupernode() ? 'S' : '-'),_r->identity.address().toString().c_str(),nwid,guid,origin.toString().c_str(),nextHop.toString().c_str());
  555. _r->demarc->send(Demarc::ANY_PORT,ZT_DEFAULTS.multicastTraceWatcher,mct,strlen(mct),-1);
  556. #endif
  557. // Send to next hop, reusing this packet as scratch space
  558. newInitializationVector();
  559. setDestination(nextHop);
  560. setSource(_r->identity.address());
  561. compress(); // note: bloom filters and empty FIFOs are highly compressable!
  562. _r->sw->send(*this,true);
  563. return true;
  564. } catch (std::exception &ex) {
  565. TRACE("dropped MULTICAST_FRAME from %s(%s): unexpected exception: %s",source().toString().c_str(),_remoteAddress.toString().c_str(),ex.what());
  566. } catch ( ... ) {
  567. TRACE("dropped MULTICAST_FRAME from %s(%s): unexpected exception: (unknown)",source().toString().c_str(),_remoteAddress.toString().c_str());
  568. }
  569. return true;
  570. }
  571. bool PacketDecoder::_doMULTICAST_LIKE(const RuntimeEnvironment *_r,const SharedPtr<Peer> &peer)
  572. {
  573. try {
  574. unsigned int ptr = ZT_PACKET_IDX_PAYLOAD;
  575. if (ptr >= size())
  576. return true;
  577. uint64_t now = Utils::now();
  578. Address src(source());
  579. // Iterate through 18-byte network,MAC,ADI tuples
  580. for(;;) {
  581. _r->mc->likesGroup(at<uint64_t>(ptr),src,MulticastGroup(MAC(field(ptr + 8,6)),at<uint32_t>(ptr + 14)),now);
  582. if ((ptr += 18) >= size())
  583. break;
  584. }
  585. } catch (std::exception &ex) {
  586. TRACE("dropped MULTICAST_LIKE from %s(%s): unexpected exception: %s",source().toString().c_str(),_remoteAddress.toString().c_str(),ex.what());
  587. } catch ( ... ) {
  588. TRACE("dropped MULTICAST_LIKE from %s(%s): unexpected exception: (unknown)",source().toString().c_str(),_remoteAddress.toString().c_str());
  589. }
  590. return true;
  591. }
  592. bool PacketDecoder::_doNETWORK_MEMBERSHIP_CERTIFICATE(const RuntimeEnvironment *_r,const SharedPtr<Peer> &peer)
  593. {
  594. // TODO: not implemented yet, will be needed for private networks.
  595. return true;
  596. }
  597. bool PacketDecoder::_doNETWORK_CONFIG_REQUEST(const RuntimeEnvironment *_r,const SharedPtr<Peer> &peer)
  598. {
  599. try {
  600. uint64_t nwid = at<uint64_t>(ZT_PROTO_VERB_NETWORK_CONFIG_REQUEST_IDX_NETWORK_ID);
  601. #ifndef __WINDOWS__
  602. if (_r->netconfService) {
  603. char tmp[128];
  604. unsigned int dictLen = at<uint16_t>(ZT_PROTO_VERB_NETWORK_CONFIG_REQUEST_IDX_DICT_LEN);
  605. Dictionary request;
  606. if (dictLen)
  607. request["meta"] = std::string((const char *)field(ZT_PROTO_VERB_NETWORK_CONFIG_REQUEST_IDX_DICT,dictLen),dictLen);
  608. request["type"] = "netconf-request";
  609. request["peerId"] = peer->identity().toString(false);
  610. Utils::snprintf(tmp,sizeof(tmp),"%llx",(unsigned long long)nwid);
  611. request["nwid"] = tmp;
  612. Utils::snprintf(tmp,sizeof(tmp),"%llx",(unsigned long long)packetId());
  613. request["requestId"] = tmp;
  614. //TRACE("to netconf:\n%s",request.toString().c_str());
  615. _r->netconfService->send(request);
  616. } else {
  617. #endif // !__WINDOWS__
  618. Packet outp(source(),_r->identity.address(),Packet::VERB_ERROR);
  619. outp.append((unsigned char)Packet::VERB_NETWORK_CONFIG_REQUEST);
  620. outp.append(packetId());
  621. outp.append((unsigned char)Packet::ERROR_UNSUPPORTED_OPERATION);
  622. outp.append(nwid);
  623. outp.armor(peer->key(),true);
  624. _r->demarc->send(_localPort,_remoteAddress,outp.data(),outp.size(),-1);
  625. #ifndef __WINDOWS__
  626. }
  627. #endif // !__WINDOWS__
  628. } catch (std::exception &exc) {
  629. TRACE("dropped NETWORK_CONFIG_REQUEST from %s(%s): unexpected exception: %s",source().toString().c_str(),_remoteAddress.toString().c_str(),exc.what());
  630. } catch ( ... ) {
  631. TRACE("dropped NETWORK_CONFIG_REQUEST from %s(%s): unexpected exception: (unknown)",source().toString().c_str(),_remoteAddress.toString().c_str());
  632. }
  633. return true;
  634. }
  635. bool PacketDecoder::_doNETWORK_CONFIG_REFRESH(const RuntimeEnvironment *_r,const SharedPtr<Peer> &peer)
  636. {
  637. try {
  638. uint64_t nwid = at<uint64_t>(ZT_PROTO_VERB_NETWORK_CONFIG_REFRESH_IDX_NETWORK_ID);
  639. SharedPtr<Network> nw(_r->nc->network(nwid));
  640. if ((nw)&&(source() == nw->controller())) // only respond to requests from controller
  641. nw->requestConfiguration();
  642. } catch (std::exception &exc) {
  643. TRACE("dropped NETWORK_CONFIG_REFRESH from %s(%s): unexpected exception: %s",source().toString().c_str(),_remoteAddress.toString().c_str(),exc.what());
  644. } catch ( ... ) {
  645. TRACE("dropped NETWORK_CONFIG_REFRESH from %s(%s): unexpected exception: (unknown)",source().toString().c_str(),_remoteAddress.toString().c_str());
  646. }
  647. return true;
  648. }
  649. } // namespace ZeroTier