diff --git a/node/Demarc.cpp b/node/Demarc.cpp deleted file mode 100644 index ef5c8948c..000000000 --- a/node/Demarc.cpp +++ /dev/null @@ -1,216 +0,0 @@ -/* - * ZeroTier One - Global Peer to Peer Ethernet - * Copyright (C) 2011-2014 ZeroTier Networks LLC - * - * This program is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see . - * - * -- - * - * ZeroTier may be used and distributed under the terms of the GPLv3, which - * are available at: http://www.gnu.org/licenses/gpl-3.0.html - * - * If you would like to embed ZeroTier into a commercial application or - * redistribute it in a modified binary form, please contact ZeroTier Networks - * LLC. Start here: http://www.zerotier.com/ - */ - -#include - -#include "Constants.hpp" - -#ifdef __WINDOWS__ -#include -#include -#endif - -#include "Demarc.hpp" -#include "RuntimeEnvironment.hpp" -#include "Logger.hpp" -#include "UdpSocket.hpp" -#include "InetAddress.hpp" -#include "Switch.hpp" -#include "Buffer.hpp" -#include "CMWC4096.hpp" - -namespace ZeroTier { - -const Demarc::Port Demarc::ANY_PORT = (Port)0xffffffffffffffffULL; -const Demarc::Port Demarc::NULL_PORT = (Port)0; - -Demarc::Demarc(const RuntimeEnvironment *renv) : - _r(renv) -{ -} - -Demarc::~Demarc() -{ - for(std::map< Port,DemarcPortObj >::iterator pe(_ports.begin());pe!=_ports.end();++pe) { - switch (pe->second.type) { - case PORT_TYPE_UDP_SOCKET_V4: - case PORT_TYPE_UDP_SOCKET_V6: - delete ((UdpSocket *)pe->second.obj); - break; - case PORT_TYPE_LOCAL_ETHERNET: - case PORT_TYPE_RELAY_TUNNEL: - break; - } - } -} - -std::string Demarc::describe(Demarc::Port p) -{ - char buf[64]; - switch ((DemarcPortType)(((uint64_t)p) >> 60)) { - case PORT_TYPE_UDP_SOCKET_V4: - Utils::snprintf(buf,sizeof(buf),"udp/4/%d",(int)((uint64_t)p & 0xffff)); - return std::string(buf); - case PORT_TYPE_UDP_SOCKET_V6: - Utils::snprintf(buf,sizeof(buf),"udp/6/%d",(int)((uint64_t)p & 0xffff)); - return std::string(buf); - case PORT_TYPE_LOCAL_ETHERNET: - return std::string("ethernet"); - case PORT_TYPE_RELAY_TUNNEL: - return std::string("relay"); - } - return std::string("(null)"); -} - -bool Demarc::has(Port p) const - throw() -{ - Mutex::Lock _l(_ports_m); - return (_ports.count(p) != 0); -} - -bool Demarc::bindLocalUdp(unsigned int localPort) -{ - Mutex::Lock _l(_ports_m); - - uint64_t v4p = ((uint64_t)PORT_TYPE_UDP_SOCKET_V4 << 60) | (uint64_t)localPort; - uint64_t v6p = ((uint64_t)PORT_TYPE_UDP_SOCKET_V6 << 60) | (uint64_t)localPort; - if ((_ports.count((Port)v4p))||(_ports.count((Port)v6p))) - return true; // port already bound - - UdpSocket *v4 = (UdpSocket *)0; - try { - DemarcPortObj *v4r = &(_ports[(Port)v4p]); - v4r->port = (Port)v4p; - v4r->parent = this; - v4r->obj = v4 = new UdpSocket(false,localPort,false,&Demarc::_CBudpSocketPacketHandler,v4r); - v4r->type = PORT_TYPE_UDP_SOCKET_V4; - } catch ( ... ) { - _ports.erase((Port)v4p); - v4 = (UdpSocket *)0; - } - - UdpSocket *v6 = (UdpSocket *)0; - try { - DemarcPortObj *v6r = &(_ports[(Port)v6p]); - v6r->port = (Port)v6p; - v6r->parent = this; - v6r->obj = v6 = new UdpSocket(false,localPort,true,&Demarc::_CBudpSocketPacketHandler,v6r); - v6r->type = PORT_TYPE_UDP_SOCKET_V6; - } catch ( ... ) { - _ports.erase((Port)v6p); - v6 = (UdpSocket *)0; - } - - return ((v4)||(v6)); -} - -Demarc::Port Demarc::pick(const InetAddress &to) const - throw() -{ - Mutex::Lock _l(_ports_m); - try { - std::vector< std::map< Port,DemarcPortObj >::const_iterator > possibilities; - for(std::map< Port,DemarcPortObj >::const_iterator pe(_ports.begin());pe!=_ports.end();++pe) { - switch (pe->second.type) { - case PORT_TYPE_UDP_SOCKET_V4: - if (to.isV4()) - possibilities.push_back(pe); - break; - case PORT_TYPE_UDP_SOCKET_V6: - if (to.isV6()) - possibilities.push_back(pe); - break; - default: - break; - } - } - if (possibilities.size()) - return possibilities[_r->prng->next32() % possibilities.size()]->first; - else return NULL_PORT; - } catch ( ... ) { - return NULL_PORT; - } -} - -Demarc::Port Demarc::send(Demarc::Port fromPort,const InetAddress &to,const void *data,unsigned int len,int hopLimit) const - throw() -{ - _ports_m.lock(); - - std::map< Port,DemarcPortObj >::const_iterator pe(_ports.find(fromPort)); - if (pe == _ports.end()) { - try { - std::vector< std::map< Port,DemarcPortObj >::const_iterator > possibilities; - for(pe=_ports.begin();pe!=_ports.end();++pe) { - switch (pe->second.type) { - case PORT_TYPE_UDP_SOCKET_V4: - if (to.isV4()) - possibilities.push_back(pe); - break; - case PORT_TYPE_UDP_SOCKET_V6: - if (to.isV6()) - possibilities.push_back(pe); - break; - default: - break; - } - } - if (possibilities.size()) - pe = possibilities[_r->prng->next32() % possibilities.size()]; - else { - _ports_m.unlock(); - return NULL_PORT; - } - } catch ( ... ) { - _ports_m.unlock(); - return NULL_PORT; - } - } - - switch (pe->second.type) { - case PORT_TYPE_UDP_SOCKET_V4: - case PORT_TYPE_UDP_SOCKET_V6: - _ports_m.unlock(); - if (((UdpSocket *)pe->second.obj)->send(to,data,len,hopLimit)) - return pe->first; - return NULL_PORT; - default: - break; - } - - _ports_m.unlock(); - return NULL_PORT; -} - -void Demarc::_CBudpSocketPacketHandler(UdpSocket *sock,void *arg,const InetAddress &from,const void *data,unsigned int len) -{ - if (!((DemarcPortObj *)arg)->parent->_r->shutdownInProgress) - ((DemarcPortObj *)arg)->parent->_r->sw->onRemotePacket(((DemarcPortObj *)arg)->port,from,Buffer<4096>(data,len)); -} - -} // namespace ZeroTier diff --git a/node/Demarc.hpp b/node/Demarc.hpp deleted file mode 100644 index 6654016c2..000000000 --- a/node/Demarc.hpp +++ /dev/null @@ -1,174 +0,0 @@ -/* - * ZeroTier One - Global Peer to Peer Ethernet - * Copyright (C) 2011-2014 ZeroTier Networks LLC - * - * This program is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see . - * - * -- - * - * ZeroTier may be used and distributed under the terms of the GPLv3, which - * are available at: http://www.gnu.org/licenses/gpl-3.0.html - * - * If you would like to embed ZeroTier into a commercial application or - * redistribute it in a modified binary form, please contact ZeroTier Networks - * LLC. Start here: http://www.zerotier.com/ - */ - -#ifndef ZT_DEMARC_HPP -#define ZT_DEMARC_HPP - -#include -#include - -#include -#include - -#include "Mutex.hpp" -#include "InetAddress.hpp" - -namespace ZeroTier { - -class RuntimeEnvironment; -class UdpSocket; - -/** - * Local demarcation point - * - * This holds and provides unique identifiers for all local communication - * endpoints, such as UDP sockets, raw Ethernet sockets, tunnels to a relay - * server, etc. It permits other code to refer to these via Port and forget - * about what they actually are. - * - * All ports are closed when this class is destroyed. - * - * Its name "demarcation point" comes from the telco/cable terminology for - * the box where wires terminate at a customer's property. - */ -class Demarc -{ -public: - /** - * Local demarcation port - * - * NULL_PORT is zero so this can be used in if(port) to check for - * a valid/known port. - */ - typedef uint64_t Port; - - /** - * Port identifier used to refer to any port - */ - static const Port ANY_PORT; - - /** - * Port identifier used to refer to null port / port not found - */ - static const Port NULL_PORT; - - Demarc(const RuntimeEnvironment *renv); - ~Demarc(); - - /** - * Describe a port - * - * This can describe even ports that are not bound, e.g. from serialized - * data. - * - * @param p Port - * @return Human-readable description of port - */ - static std::string describe(Port p); - - /** - * @param p Port to check - * @return True if this port is bound/connected/etc. - */ - bool has(Port p) const - throw(); - - /** - * Bind local UDP port for both IPv4 and IPv6 traffic - * - * @param localPort Local IP port - * @return True if successfully bound, or if already bound - */ - bool bindLocalUdp(unsigned int localPort); - - /** - * Pick a port to send to an address of a given type - * - * @param to Destination address - * @return Port or NULL_PORT if none - */ - Port pick(const InetAddress &to) const - throw(); - - /** - * Send a packet - * - * If fromPort is ANY_PORT or if the port is not found, a random port is - * chosen from those available matching the characteristics of the address - * in 'to'. - * - * @param fromPort Port to send from - * @param to Destination IP/port - * @param data Data to send - * @param len Length of data in bytes - * @param hopLimit IP hop limit for UDP packets or -1 for max/unlimited - * @return Port actually sent from or NULL_PORT on failure - */ - Port send(Port fromPort,const InetAddress &to,const void *data,unsigned int len,int hopLimit) const - throw(); - - /** - * @param p Port - * @return 64-bit integer suitable for serialization - */ - static inline uint64_t portToInt(const Port p) throw() { return (uint64_t)p; } - - /** - * @param p 64-bit integer from serialized representation - * @return Port suitable for use in code - */ - static inline Port intToPort(const uint64_t p) throw() { return (Port)p; } - -private: - const RuntimeEnvironment *_r; - - static void _CBudpSocketPacketHandler(UdpSocket *sock,void *arg,const InetAddress &from,const void *data,unsigned int len); - - enum DemarcPortType - { - PORT_TYPE_UDP_SOCKET_V4 = 1, - PORT_TYPE_UDP_SOCKET_V6 = 2, - PORT_TYPE_LOCAL_ETHERNET = 3, - PORT_TYPE_RELAY_TUNNEL = 4 - }; - - // Variant holding instances of UdpSocket, etc. - struct DemarcPortObj - { - Demarc::Port port; - Demarc *parent; - void *obj; - DemarcPortType type; - }; - - std::map< Port,DemarcPortObj > _ports; - Mutex _ports_m; -}; - -} // namespace ZeroTier - -#endif