Improved callback logic. Simplified lwip driver.
This commit is contained in:
@@ -37,10 +37,19 @@ index 74c22d33..58979e26 100644
|
|||||||
if (nqcb->oldQueues[i]->byteLength > maxQueueLength) {
|
if (nqcb->oldQueues[i]->byteLength > maxQueueLength) {
|
||||||
maxQueueLength = nqcb->oldQueues[i]->byteLength;
|
maxQueueLength = nqcb->oldQueues[i]->byteLength;
|
||||||
diff --git a/service/OneService.cpp b/service/OneService.cpp
|
diff --git a/service/OneService.cpp b/service/OneService.cpp
|
||||||
index a1c53764..757863a8 100644
|
index a1c53764..e3034059 100644
|
||||||
--- a/service/OneService.cpp
|
--- a/service/OneService.cpp
|
||||||
+++ b/service/OneService.cpp
|
+++ b/service/OneService.cpp
|
||||||
@@ -2244,6 +2244,12 @@ public:
|
@@ -625,6 +625,8 @@ public:
|
||||||
|
break;
|
||||||
|
if (!pkt)
|
||||||
|
break;
|
||||||
|
+ if (!_run)
|
||||||
|
+ break;
|
||||||
|
|
||||||
|
const ZT_ResultCode rc = _node->processWirePacket(nullptr,pkt->now,pkt->sock,&(pkt->from),pkt->data,pkt->size,&_nextBackgroundTaskDeadline);
|
||||||
|
{
|
||||||
|
@@ -2244,6 +2246,12 @@ public:
|
||||||
#endif
|
#endif
|
||||||
syncManagedStuff(n,true,true);
|
syncManagedStuff(n,true,true);
|
||||||
n.tap->setMtu(nwc->mtu);
|
n.tap->setMtu(nwc->mtu);
|
||||||
|
|||||||
@@ -33,6 +33,18 @@
|
|||||||
#ifndef LIBZT_CONSTANTS_HPP
|
#ifndef LIBZT_CONSTANTS_HPP
|
||||||
#define LIBZT_CONSTANTS_HPP
|
#define LIBZT_CONSTANTS_HPP
|
||||||
|
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
// Callbacks //
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
#define ZTS_NODE_CALLBACKS 1
|
||||||
|
#define ZTS_NETWORK_CALLBACKS 1
|
||||||
|
#define ZTS_NETIF_CALLBACKS 1
|
||||||
|
#define ZTS_PEER_CALLBACKS 1
|
||||||
|
|
||||||
|
#define ZTS_CALLBACK_PROCESSING_INTERVAL ZTS_WRAPPER_CHECK_INTERVAL // 100 // ms
|
||||||
|
#define ZTS_CALLBACK_MSG_QUEUE_LEN 256
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
// Error codes returned by ZeroTier and the libzt API //
|
// Error codes returned by ZeroTier and the libzt API //
|
||||||
// See ext/ZeroTierOne/include/ZeroTierOne.h //
|
// See ext/ZeroTierOne/include/ZeroTierOne.h //
|
||||||
@@ -40,25 +52,45 @@
|
|||||||
|
|
||||||
typedef int zts_err_t;
|
typedef int zts_err_t;
|
||||||
|
|
||||||
#define ZTS_ERR_OK 0 // Everything is ok
|
#define ZTS_ERR_OK 0 // Everything is ok
|
||||||
#define ZTS_ERR_INVALID_ARG -1 // A parameter provided by the user application is invalid (e.g. our of range, NULL, etc)
|
#define ZTS_ERR_INVALID_ARG -1 // A parameter provided by the user application is invalid (e.g. our of range, NULL, etc)
|
||||||
#define ZTS_ERR_SERVICE -2 // The service isn't initialized or is for some other reason currently unavailable
|
#define ZTS_ERR_SERVICE -2 // The service isn't initialized or is for some other reason currently unavailable
|
||||||
#define ZTS_ERR_INVALID_OP -3 // For some reason this API operation is not permitted (perhaps the service is still starting?)
|
#define ZTS_ERR_INVALID_OP -3 // For some reason this API operation is not permitted (perhaps the service is still starting?)
|
||||||
|
|
||||||
#define ZTS_EVENT_NODE_ONLINE 0x01 // Node is online
|
#define ZTS_EVENT_NONE 0x00000000
|
||||||
#define ZTS_EVENT_NODE_OFFLINE 0x02 // Node is offline
|
// Node-specific events
|
||||||
#define ZTS_EVENT_NODE_DOWN 0x03 // Node is shutting down
|
#define ZTS_EVENT_NODE_ONLINE 0x00000001 // Node is online
|
||||||
#define ZTS_EVENT_NODE_IDENTITY_COLLISION 0x04 // Identity collision - check for duplicate instances
|
#define ZTS_EVENT_NODE_OFFLINE 0x00000002 // Node is offline
|
||||||
#define ZTS_EVENT_NODE_UNRECOVERABLE_ERROR 0x05 // Something is seriously wrong
|
#define ZTS_EVENT_NODE_DOWN 0x00000004 // Node is shutting down
|
||||||
#define ZTS_EVENT_NODE_NORMAL_TERMINATION 0x06 // Service thread has stopped
|
#define ZTS_EVENT_NODE_IDENTITY_COLLISION 0x00000008 // Identity collision - check for duplicate instances
|
||||||
|
#define ZTS_EVENT_NODE_UNRECOVERABLE_ERROR 0x00000010 // Something is seriously wrong
|
||||||
#define ZTS_EVENT_NETWORK_NOT_FOUND 0x07
|
#define ZTS_EVENT_NODE_NORMAL_TERMINATION 0x00000020 // Service thread has stopped
|
||||||
#define ZTS_EVENT_NETWORK_CLIENT_TOO_OLD 0x08
|
// Network-specific events
|
||||||
#define ZTS_EVENT_NETWORK_REQUESTING_CONFIG 0x09
|
#define ZTS_EVENT_NETWORK_NOT_FOUND 0x00000080
|
||||||
#define ZTS_EVENT_NETWORK_OK 0x0a
|
#define ZTS_EVENT_NETWORK_CLIENT_TOO_OLD 0x00000100
|
||||||
#define ZTS_EVENT_NETWORK_ACCESS_DENIED 0x0b
|
#define ZTS_EVENT_NETWORK_REQUESTING_CONFIG 0x00000200
|
||||||
#define ZTS_EVENT_NETWORK_READY 0x0c
|
#define ZTS_EVENT_NETWORK_OK 0x00000400
|
||||||
#define ZTS_EVENT_NETWORK_DOWN 0x0d
|
#define ZTS_EVENT_NETWORK_ACCESS_DENIED 0x00000800
|
||||||
|
#define ZTS_EVENT_NETWORK_READY_IP4 0x00001000
|
||||||
|
#define ZTS_EVENT_NETWORK_READY_IP6 0x00002000
|
||||||
|
#define ZTS_EVENT_NETWORK_DOWN 0x00004000
|
||||||
|
#define ZTS_EVENT_NETWORK_STATUS_CHANGE ZTS_EVENT_NETWORK_NOT_FOUND | ZTS_EVENT_NETWORK_CLIENT_TOO_OLD | ZTS_EVENT_NETWORK_REQUESTING_CONFIG | ZTS_EVENT_NETWORK_OK | ZTS_EVENT_NETWORK_ACCESS_DENIED
|
||||||
|
// lwIP netif events
|
||||||
|
#define ZTS_EVENT_NETIF_UP_IP4 0x00100000
|
||||||
|
#define ZTS_EVENT_NETIF_UP_IP6 0x00200000
|
||||||
|
#define ZTS_EVENT_NETIF_DOWN_IP4 0x00400000
|
||||||
|
#define ZTS_EVENT_NETIF_DOWN_IP6 0x00800000
|
||||||
|
#define ZTS_EVENT_NETIF_REMOVED 0x01000000
|
||||||
|
#define ZTS_EVENT_NETIF_LINK_UP 0x02000000
|
||||||
|
#define ZTS_EVENT_NETIF_LINK_DOWN 0x04000000
|
||||||
|
#define ZTS_EVENT_NETIF_NEW_ADDRESS 0x08000000
|
||||||
|
#define ZTS_EVENT_NETIF_STATUS_CHANGE ZTS_EVENT_NETIF_UP_IP4 | ZTS_EVENT_NETIF_UP_IP6 | ZTS_EVENT_NETIF_DOWN_IP4 | ZTS_EVENT_NETIF_DOWN_IP6 | ZTS_EVENT_NETIF_LINK_UP | ZTS_EVENT_NETIF_LINK_DOWN
|
||||||
|
//
|
||||||
|
#define ZTS_EVENT_GENERIC_DOWN ZTS_EVENT_NETWORK_DOWN | ZTS_EVENT_NETIF_DOWN_IP4 | ZTS_EVENT_NETIF_DOWN_IP6 | ZTS_EVENT_NETIF_LINK_DOWN
|
||||||
|
// Peer events
|
||||||
|
#define ZTS_EVENT_PEER_P2P 0x20000000
|
||||||
|
#define ZTS_EVENT_PEER_RELAY 0x40000000
|
||||||
|
#define ZTS_EVENT_PEER_UNREACHABLE 0x80000000 // Not yet supported
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
// libzt config //
|
// libzt config //
|
||||||
|
|||||||
@@ -39,6 +39,8 @@
|
|||||||
#include <sys/socket.h>
|
#include <sys/socket.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
namespace ZeroTier {
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
// Subset of: ZeroTierOne.h //
|
// Subset of: ZeroTierOne.h //
|
||||||
// We redefine a few ZT structures here so that we don't need to drag the //
|
// We redefine a few ZT structures here so that we don't need to drag the //
|
||||||
@@ -208,4 +210,6 @@ struct zts_peer_list
|
|||||||
unsigned long peerCount;
|
unsigned long peerCount;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
} // namespace ZeroTier
|
||||||
|
|
||||||
#endif // _H
|
#endif // _H
|
||||||
@@ -33,6 +33,10 @@
|
|||||||
#ifndef LIBZT_SERVICE_CONTROLS_HPP
|
#ifndef LIBZT_SERVICE_CONTROLS_HPP
|
||||||
#define LIBZT_SERVICE_CONTROLS_HPP
|
#define LIBZT_SERVICE_CONTROLS_HPP
|
||||||
|
|
||||||
|
#include "Constants.hpp"
|
||||||
|
|
||||||
|
namespace ZeroTier {
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
#ifdef ADD_EXPORTS
|
#ifdef ADD_EXPORTS
|
||||||
#define ZT_SOCKET_API __declspec(dllexport)
|
#define ZT_SOCKET_API __declspec(dllexport)
|
||||||
@@ -45,8 +49,6 @@
|
|||||||
#define ZTCALL
|
#define ZTCALL
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
void api_sleep(int interval_ms);
|
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
// ZeroTier Service Controls //
|
// ZeroTier Service Controls //
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
@@ -386,4 +388,6 @@ void _hibernate_if_needed();
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
} // namespace ZeroTier
|
||||||
|
|
||||||
#endif // _H
|
#endif // _H
|
||||||
@@ -78,33 +78,9 @@ public:
|
|||||||
|
|
||||||
~VirtualTap();
|
~VirtualTap();
|
||||||
|
|
||||||
/**
|
|
||||||
* A state will only be reported via callback if it differs from this value. Subsequently this
|
|
||||||
* value will be updated.
|
|
||||||
*/
|
|
||||||
int _lastReportedStatus;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The last time that this virtual tap received a network config update from the core
|
|
||||||
*/
|
|
||||||
uint64_t _lastConfigUpdateTime = 0;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The last time that a callback notification was sent to the user application signalling
|
|
||||||
* that this interface is ready to process traffic.
|
|
||||||
*/
|
|
||||||
uint64_t _lastReadyReportTime = 0;
|
|
||||||
|
|
||||||
void lastConfigUpdate(uint64_t lastConfigUpdateTime);
|
|
||||||
|
|
||||||
void setEnabled(bool en);
|
void setEnabled(bool en);
|
||||||
bool enabled() const;
|
bool enabled() const;
|
||||||
|
|
||||||
/**
|
|
||||||
* Registers a device with the given address
|
|
||||||
*/
|
|
||||||
void registerIpWithStack(const InetAddress &ip);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Adds an address to the userspace stack interface associated with this VirtualTap
|
* Adds an address to the userspace stack interface associated with this VirtualTap
|
||||||
* - Starts VirtualTap main thread ONLY if successful
|
* - Starts VirtualTap main thread ONLY if successful
|
||||||
@@ -178,6 +154,48 @@ public:
|
|||||||
void phyOnUnixData(PhySocket *sock, void **uptr, void *data, ssize_t len);
|
void phyOnUnixData(PhySocket *sock, void **uptr, void *data, ssize_t len);
|
||||||
void phyOnUnixWritable(PhySocket *sock, void **uptr, bool stack_invoked);
|
void phyOnUnixWritable(PhySocket *sock, void **uptr, bool stack_invoked);
|
||||||
|
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
// Lower-level lwIP netif handling and traffic handling readiness //
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
void *netif4 = NULL;
|
||||||
|
void *netif6 = NULL;
|
||||||
|
|
||||||
|
bool netif4WasUpLastCheck = false;
|
||||||
|
bool netif6WasUpLastCheck = false;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Notes the current state of the lower level lwIP netif and reports if a state change
|
||||||
|
* has happened since the last check. This method is likely temporary.
|
||||||
|
*/
|
||||||
|
uint64_t recognizeLowerLevelInterfaceStateChange(void *n);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A state will only be reported via callback if it differs from this value. Subsequently this
|
||||||
|
* value will be updated.
|
||||||
|
*/
|
||||||
|
//int _lastReportedStatus;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The last time that this virtual tap received a network config update from the core
|
||||||
|
*/
|
||||||
|
uint64_t _lastConfigUpdateTime = 0;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The last time that a callback notification was sent to the user application signalling
|
||||||
|
* that this interface is ready to process traffic.
|
||||||
|
*/
|
||||||
|
uint64_t _lastReadyReportTime = 0;
|
||||||
|
|
||||||
|
void lastConfigUpdate(uint64_t lastConfigUpdateTime);
|
||||||
|
|
||||||
|
int _networkStatus = 0;
|
||||||
|
int _netifStatus = 0;
|
||||||
|
/**
|
||||||
|
* Returns whether or not this interface is ready for traffic.
|
||||||
|
*/
|
||||||
|
bool isReady();
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
// Vars //
|
// Vars //
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|||||||
@@ -1,62 +0,0 @@
|
|||||||
/*
|
|
||||||
* ZeroTier SDK - Network Virtualization Everywhere
|
|
||||||
* Copyright (C) 2011-2019 ZeroTier, Inc. https://www.zerotier.com/
|
|
||||||
*
|
|
||||||
* 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 <http://www.gnu.org/licenses/>.
|
|
||||||
*
|
|
||||||
* --
|
|
||||||
*
|
|
||||||
* You can be released from the requirements of the license by purchasing
|
|
||||||
* a commercial license. Buying such a license is mandatory as soon as you
|
|
||||||
* develop commercial closed-source software that incorporates or links
|
|
||||||
* directly against ZeroTier software without disclosing the source code
|
|
||||||
* of your own application.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @file
|
|
||||||
*
|
|
||||||
* Management of virtual tap interfaces
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef LIBZT_VIRTUAL_TAP_MANAGER_H
|
|
||||||
#define LIBZT_VIRTUAL_TAP_MANAGER_H
|
|
||||||
|
|
||||||
#include "VirtualTap.hpp"
|
|
||||||
#include "OneService.hpp"
|
|
||||||
|
|
||||||
namespace ZeroTier {
|
|
||||||
|
|
||||||
class VirtualTap;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Static utility class for safely handling VirtualTap(s)
|
|
||||||
*/
|
|
||||||
class VirtualTapManager
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
|
|
||||||
static void add_tap(VirtualTap *tap);
|
|
||||||
static VirtualTap *getTapByNWID(uint64_t nwid);
|
|
||||||
static size_t get_vtaps_size();
|
|
||||||
static void remove_by_nwid(uint64_t nwid);
|
|
||||||
static void clear();
|
|
||||||
static void get_network_details_helper(void *zt1ServiceRef, uint64_t nwid, struct zts_network_details *nd);
|
|
||||||
static void get_network_details(void *zt1ServiceRef, uint64_t nwid, struct zts_network_details *nd);
|
|
||||||
static void get_all_network_details(void *zt1ServiceRef, struct zts_network_details *nds, int *num);
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace ZeroTier
|
|
||||||
|
|
||||||
#endif // _H
|
|
||||||
@@ -37,11 +37,31 @@
|
|||||||
#include "lwip/err.h"
|
#include "lwip/err.h"
|
||||||
|
|
||||||
namespace ZeroTier {
|
namespace ZeroTier {
|
||||||
class MAC;
|
|
||||||
class Mutex;
|
class MAC;
|
||||||
class VirtualTap;
|
class Mutex;
|
||||||
struct InetAddress;
|
class VirtualTap;
|
||||||
}
|
struct InetAddress;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Structure used to associate packets with interfaces.
|
||||||
|
*/
|
||||||
|
struct zts_sorted_packet
|
||||||
|
{
|
||||||
|
// lwIP pbuf containing packet (originally encapsulated by ZT packet)
|
||||||
|
struct pbuf *p;
|
||||||
|
// ZT VirtualTap from which this packet originates
|
||||||
|
ZeroTier::VirtualTap *vtap;
|
||||||
|
// lwIP netif we should accept this packet on
|
||||||
|
struct netif *n;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Return whether a given netif's NETIF_FLAG_UP flag is set
|
||||||
|
*
|
||||||
|
* @usage This is a convenience function to encapsulate a macro
|
||||||
|
*/
|
||||||
|
bool lwip_is_netif_up(void *netif);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Increase the delay multiplier for the main driver loop
|
* @brief Increase the delay multiplier for the main driver loop
|
||||||
@@ -76,15 +96,14 @@ void lwip_driver_init();
|
|||||||
void lwip_driver_shutdown();
|
void lwip_driver_shutdown();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Bring all interfaces down belonging to the given virtual tap interface
|
* @brief Bring down and delete all interfaces belonging to the given virtual tap
|
||||||
*
|
*
|
||||||
* @usage This is to be called when the application desires to stop all traffic processing in the
|
* @usage This is to be called when the application desires to stop all traffic processing in the
|
||||||
* stack. Unlike lwip_driver_shutdown(), the application can easily resume traffic processing
|
* stack. Unlike lwip_driver_shutdown(), the application can easily resume traffic processing
|
||||||
* by re-adding a virtual tap (and associated lwip netifs)
|
* by re-adding a virtual tap (and associated lwip netifs)
|
||||||
* @return
|
* @return
|
||||||
*/
|
*/
|
||||||
void lwip_driver_set_tap_interfaces_down(void *tapref);
|
void lwip_dispose_of_netifs(void *tapref);
|
||||||
void lwip_driver_set_all_interfaces_down();
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Initialize and start the DNS client
|
* @brief Initialize and start the DNS client
|
||||||
@@ -128,7 +147,7 @@ static void netif_link_callback(struct netif *netif);
|
|||||||
* @param ip Virtual IP address for this ZeroTier VirtualTap interface
|
* @param ip Virtual IP address for this ZeroTier VirtualTap interface
|
||||||
* @return
|
* @return
|
||||||
*/
|
*/
|
||||||
void lwip_init_interface(void *tapref, const ZeroTier::MAC &mac, const ZeroTier::InetAddress &ip);
|
void lwip_init_interface(void *tapref, const MAC &mac, const InetAddress &ip);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Called from the stack, outbound ethernet frames from the network stack enter the ZeroTier virtual wire here.
|
* @brief Called from the stack, outbound ethernet frames from the network stack enter the ZeroTier virtual wire here.
|
||||||
@@ -152,7 +171,9 @@ err_t lwip_eth_tx(struct netif *netif, struct pbuf *p);
|
|||||||
* @param len Length of Ethernet frame
|
* @param len Length of Ethernet frame
|
||||||
* @return
|
* @return
|
||||||
*/
|
*/
|
||||||
void lwip_eth_rx(ZeroTier::VirtualTap *tap, const ZeroTier::MAC &from, const ZeroTier::MAC &to, unsigned int etherType,
|
void lwip_eth_rx(VirtualTap *tap, const MAC &from, const MAC &to, unsigned int etherType,
|
||||||
const void *data, unsigned int len);
|
const void *data, unsigned int len);
|
||||||
|
|
||||||
|
} // namespace ZeroTier
|
||||||
|
|
||||||
#endif // _H
|
#endif // _H
|
||||||
|
|||||||
@@ -53,7 +53,7 @@
|
|||||||
*/
|
*/
|
||||||
#if __ANDROID__
|
#if __ANDROID__
|
||||||
#define LWIP_PROVIDE_ERRNO 1
|
#define LWIP_PROVIDE_ERRNO 1
|
||||||
//#define SOCKLEN_T_DEFINED
|
#define SOCKLEN_T_DEFINED
|
||||||
#elif !defined(_MSC_VER)
|
#elif !defined(_MSC_VER)
|
||||||
#define LWIP_PROVIDE_ERRNO 1
|
#define LWIP_PROVIDE_ERRNO 1
|
||||||
#endif
|
#endif
|
||||||
@@ -61,7 +61,7 @@
|
|||||||
/**
|
/**
|
||||||
* Disable assertions
|
* Disable assertions
|
||||||
*/
|
*/
|
||||||
#define LWIP_NOASSERT 0
|
#define LWIP_NOASSERT 1
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Don't redefine byte-order functions if they're already available
|
* Don't redefine byte-order functions if they're already available
|
||||||
@@ -103,6 +103,33 @@
|
|||||||
*/
|
*/
|
||||||
#define LWIP_DBG_HALT 0x08U
|
#define LWIP_DBG_HALT 0x08U
|
||||||
|
|
||||||
|
/*------------------------------------------------------------------------------
|
||||||
|
---------------------------------- Timers --------------------------------------
|
||||||
|
------------------------------------------------------------------------------*/
|
||||||
|
/*
|
||||||
|
Be careful about setting this too small. lwIP just counts the number
|
||||||
|
of times its timer is called and uses this to control time sensitive
|
||||||
|
operations (such as TCP retransmissions), rather than actually
|
||||||
|
measuring time using something more accurate. If you call the timer
|
||||||
|
functions very frequently you may see things (such as retransmissions)
|
||||||
|
happening sooner than they should.
|
||||||
|
*/
|
||||||
|
/* these are originally defined in tcp_impl.h */
|
||||||
|
#ifndef TCP_TMR_INTERVAL
|
||||||
|
/* The TCP timer interval in milliseconds. */
|
||||||
|
#define TCP_TMR_INTERVAL 250
|
||||||
|
#endif /* TCP_TMR_INTERVAL */
|
||||||
|
|
||||||
|
#ifndef TCP_FAST_INTERVAL
|
||||||
|
/* the fine grained timeout in milliseconds */
|
||||||
|
#define TCP_FAST_INTERVAL TCP_TMR_INTERVAL
|
||||||
|
#endif /* TCP_FAST_INTERVAL */
|
||||||
|
|
||||||
|
#ifndef TCP_SLOW_INTERVALs
|
||||||
|
/* the coarse grained timeout in milliseconds */
|
||||||
|
#define TCP_SLOW_INTERVAL (2*TCP_TMR_INTERVAL)
|
||||||
|
#endif /* TCP_SLOW_INTERVAL */
|
||||||
|
|
||||||
/*------------------------------------------------------------------------------
|
/*------------------------------------------------------------------------------
|
||||||
----------------------- Below: Modified contents of opt.h ----------------------
|
----------------------- Below: Modified contents of opt.h ----------------------
|
||||||
------------------------------------------------------------------------------*/
|
------------------------------------------------------------------------------*/
|
||||||
@@ -243,7 +270,7 @@
|
|||||||
* Your system should provide mutexes supporting priority inversion to use this.
|
* Your system should provide mutexes supporting priority inversion to use this.
|
||||||
*/
|
*/
|
||||||
#if !defined LWIP_TCPIP_CORE_LOCKING || defined __DOXYGEN__
|
#if !defined LWIP_TCPIP_CORE_LOCKING || defined __DOXYGEN__
|
||||||
#define LWIP_TCPIP_CORE_LOCKING 0
|
#define LWIP_TCPIP_CORE_LOCKING 1
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -350,7 +377,7 @@
|
|||||||
* a lot of data that needs to be copied, this should be set high.
|
* a lot of data that needs to be copied, this should be set high.
|
||||||
*/
|
*/
|
||||||
#if !defined MEM_SIZE || defined __DOXYGEN__
|
#if !defined MEM_SIZE || defined __DOXYGEN__
|
||||||
#define MEM_SIZE 1600
|
#define MEM_SIZE 1024 * 1024
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -464,7 +491,7 @@
|
|||||||
* this should be set high.
|
* this should be set high.
|
||||||
*/
|
*/
|
||||||
#if !defined MEMP_NUM_PBUF || defined __DOXYGEN__
|
#if !defined MEMP_NUM_PBUF || defined __DOXYGEN__
|
||||||
#define MEMP_NUM_PBUF 16
|
#define MEMP_NUM_PBUF 1024
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -472,7 +499,7 @@
|
|||||||
* (requires the LWIP_RAW option)
|
* (requires the LWIP_RAW option)
|
||||||
*/
|
*/
|
||||||
#if !defined MEMP_NUM_RAW_PCB || defined __DOXYGEN__
|
#if !defined MEMP_NUM_RAW_PCB || defined __DOXYGEN__
|
||||||
#define MEMP_NUM_RAW_PCB 4
|
#define MEMP_NUM_RAW_PCB 1024
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -481,7 +508,7 @@
|
|||||||
* (requires the LWIP_UDP option)
|
* (requires the LWIP_UDP option)
|
||||||
*/
|
*/
|
||||||
#if !defined MEMP_NUM_UDP_PCB || defined __DOXYGEN__
|
#if !defined MEMP_NUM_UDP_PCB || defined __DOXYGEN__
|
||||||
#define MEMP_NUM_UDP_PCB 4
|
#define MEMP_NUM_UDP_PCB 1024
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -489,7 +516,7 @@
|
|||||||
* (requires the LWIP_TCP option)
|
* (requires the LWIP_TCP option)
|
||||||
*/
|
*/
|
||||||
#if !defined MEMP_NUM_TCP_PCB || defined __DOXYGEN__
|
#if !defined MEMP_NUM_TCP_PCB || defined __DOXYGEN__
|
||||||
#define MEMP_NUM_TCP_PCB 5
|
#define MEMP_NUM_TCP_PCB 1024
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -497,7 +524,7 @@
|
|||||||
* (requires the LWIP_TCP option)
|
* (requires the LWIP_TCP option)
|
||||||
*/
|
*/
|
||||||
#if !defined MEMP_NUM_TCP_PCB_LISTEN || defined __DOXYGEN__
|
#if !defined MEMP_NUM_TCP_PCB_LISTEN || defined __DOXYGEN__
|
||||||
#define MEMP_NUM_TCP_PCB_LISTEN 8
|
#define MEMP_NUM_TCP_PCB_LISTEN 1024
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -505,7 +532,7 @@
|
|||||||
* (requires the LWIP_TCP option)
|
* (requires the LWIP_TCP option)
|
||||||
*/
|
*/
|
||||||
#if !defined MEMP_NUM_TCP_SEG || defined __DOXYGEN__
|
#if !defined MEMP_NUM_TCP_SEG || defined __DOXYGEN__
|
||||||
#define MEMP_NUM_TCP_SEG 16
|
#define MEMP_NUM_TCP_SEG 1024
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -523,7 +550,7 @@
|
|||||||
* reassembly (whole packets, not fragments!)
|
* reassembly (whole packets, not fragments!)
|
||||||
*/
|
*/
|
||||||
#if !defined MEMP_NUM_REASSDATA || defined __DOXYGEN__
|
#if !defined MEMP_NUM_REASSDATA || defined __DOXYGEN__
|
||||||
#define MEMP_NUM_REASSDATA 5
|
#define MEMP_NUM_REASSDATA 16
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -585,7 +612,7 @@
|
|||||||
* (only needed if you use the sequential API, like api_lib.c)
|
* (only needed if you use the sequential API, like api_lib.c)
|
||||||
*/
|
*/
|
||||||
#if !defined MEMP_NUM_NETCONN || defined __DOXYGEN__
|
#if !defined MEMP_NUM_NETCONN || defined __DOXYGEN__
|
||||||
#define MEMP_NUM_NETCONN 4
|
#define MEMP_NUM_NETCONN 256
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -603,7 +630,7 @@
|
|||||||
* (only needed if you use tcpip.c)
|
* (only needed if you use tcpip.c)
|
||||||
*/
|
*/
|
||||||
#if !defined MEMP_NUM_TCPIP_MSG_API || defined __DOXYGEN__
|
#if !defined MEMP_NUM_TCPIP_MSG_API || defined __DOXYGEN__
|
||||||
#define MEMP_NUM_TCPIP_MSG_API 8
|
#define MEMP_NUM_TCPIP_MSG_API 64
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -612,7 +639,7 @@
|
|||||||
* (only needed if you use tcpip.c)
|
* (only needed if you use tcpip.c)
|
||||||
*/
|
*/
|
||||||
#if !defined MEMP_NUM_TCPIP_MSG_INPKT || defined __DOXYGEN__
|
#if !defined MEMP_NUM_TCPIP_MSG_INPKT || defined __DOXYGEN__
|
||||||
#define MEMP_NUM_TCPIP_MSG_INPKT 8
|
#define MEMP_NUM_TCPIP_MSG_INPKT 64
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -635,7 +662,7 @@
|
|||||||
* PBUF_POOL_SIZE: the number of buffers in the pbuf pool.
|
* PBUF_POOL_SIZE: the number of buffers in the pbuf pool.
|
||||||
*/
|
*/
|
||||||
#if !defined PBUF_POOL_SIZE || defined __DOXYGEN__
|
#if !defined PBUF_POOL_SIZE || defined __DOXYGEN__
|
||||||
#define PBUF_POOL_SIZE 16
|
#define PBUF_POOL_SIZE 128
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/** MEMP_NUM_API_MSG: the number of concurrently active calls to various
|
/** MEMP_NUM_API_MSG: the number of concurrently active calls to various
|
||||||
@@ -689,7 +716,7 @@
|
|||||||
* ARP_TABLE_SIZE: Number of active MAC-IP address pairs cached.
|
* ARP_TABLE_SIZE: Number of active MAC-IP address pairs cached.
|
||||||
*/
|
*/
|
||||||
#if !defined ARP_TABLE_SIZE || defined __DOXYGEN__
|
#if !defined ARP_TABLE_SIZE || defined __DOXYGEN__
|
||||||
#define ARP_TABLE_SIZE 10
|
#define ARP_TABLE_SIZE 64
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/** the time an ARP entry stays valid after its last update,
|
/** the time an ARP entry stays valid after its last update,
|
||||||
@@ -847,7 +874,7 @@
|
|||||||
* (PBUF_POOL_SIZE > 2 * IP_REASS_MAX_PBUFS)!
|
* (PBUF_POOL_SIZE > 2 * IP_REASS_MAX_PBUFS)!
|
||||||
*/
|
*/
|
||||||
#if !defined IP_REASS_MAX_PBUFS || defined __DOXYGEN__
|
#if !defined IP_REASS_MAX_PBUFS || defined __DOXYGEN__
|
||||||
#define IP_REASS_MAX_PBUFS 10
|
#define IP_REASS_MAX_PBUFS 32
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -1292,7 +1319,7 @@
|
|||||||
* will be TCP_WND >> TCP_RCV_SCALE
|
* will be TCP_WND >> TCP_RCV_SCALE
|
||||||
*/
|
*/
|
||||||
#if !defined TCP_WND || defined __DOXYGEN__
|
#if !defined TCP_WND || defined __DOXYGEN__
|
||||||
#define TCP_WND (4 * TCP_MSS)
|
#define TCP_WND 0xffff // (4 * TCP_MSS)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -1306,7 +1333,7 @@
|
|||||||
* TCP_SYNMAXRTX: Maximum number of retransmissions of SYN segments.
|
* TCP_SYNMAXRTX: Maximum number of retransmissions of SYN segments.
|
||||||
*/
|
*/
|
||||||
#if !defined TCP_SYNMAXRTX || defined __DOXYGEN__
|
#if !defined TCP_SYNMAXRTX || defined __DOXYGEN__
|
||||||
#define TCP_SYNMAXRTX 6
|
#define TCP_SYNMAXRTX 12 // 6
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -1367,7 +1394,7 @@
|
|||||||
* To achieve good performance, this should be at least 2 * TCP_MSS.
|
* To achieve good performance, this should be at least 2 * TCP_MSS.
|
||||||
*/
|
*/
|
||||||
#if !defined TCP_SND_BUF || defined __DOXYGEN__
|
#if !defined TCP_SND_BUF || defined __DOXYGEN__
|
||||||
#define TCP_SND_BUF (2 * TCP_MSS)
|
#define TCP_SND_BUF 1024 * 32 // (2 * TCP_MSS)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -1375,7 +1402,7 @@
|
|||||||
* as much as (2 * TCP_SND_BUF/TCP_MSS) for things to work.
|
* as much as (2 * TCP_SND_BUF/TCP_MSS) for things to work.
|
||||||
*/
|
*/
|
||||||
#if !defined TCP_SND_QUEUELEN || defined __DOXYGEN__
|
#if !defined TCP_SND_QUEUELEN || defined __DOXYGEN__
|
||||||
#define TCP_SND_QUEUELEN ((4 * (TCP_SND_BUF) + (TCP_MSS - 1))/(TCP_MSS))
|
#define TCP_SND_QUEUELEN 1024 // ((4 * (TCP_SND_BUF) + (TCP_MSS - 1))/(TCP_MSS))
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -1689,7 +1716,7 @@
|
|||||||
* if you have a tiny ARP table or if there never are concurrent connections.
|
* if you have a tiny ARP table or if there never are concurrent connections.
|
||||||
*/
|
*/
|
||||||
#if !defined LWIP_NETIF_HWADDRHINT || defined __DOXYGEN__
|
#if !defined LWIP_NETIF_HWADDRHINT || defined __DOXYGEN__
|
||||||
#define LWIP_NETIF_HWADDRHINT 0
|
#define LWIP_NETIF_HWADDRHINT 1
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -2005,7 +2032,7 @@
|
|||||||
* (only used if you use sockets.c)
|
* (only used if you use sockets.c)
|
||||||
*/
|
*/
|
||||||
#if !defined LWIP_COMPAT_SOCKETS || defined __DOXYGEN__
|
#if !defined LWIP_COMPAT_SOCKETS || defined __DOXYGEN__
|
||||||
#define LWIP_COMPAT_SOCKETS 1
|
#define LWIP_COMPAT_SOCKETS 0
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -2014,7 +2041,7 @@
|
|||||||
* names (read, write & close). (only used if you use sockets.c)
|
* names (read, write & close). (only used if you use sockets.c)
|
||||||
*/
|
*/
|
||||||
#if !defined LWIP_POSIX_SOCKETS_IO_NAMES || defined __DOXYGEN__
|
#if !defined LWIP_POSIX_SOCKETS_IO_NAMES || defined __DOXYGEN__
|
||||||
#define LWIP_POSIX_SOCKETS_IO_NAMES 1
|
#define LWIP_POSIX_SOCKETS_IO_NAMES 0
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -2152,7 +2179,7 @@
|
|||||||
* LWIP_STATS==1: Enable statistics collection in lwip_stats.
|
* LWIP_STATS==1: Enable statistics collection in lwip_stats.
|
||||||
*/
|
*/
|
||||||
#if !defined LWIP_STATS || defined __DOXYGEN__
|
#if !defined LWIP_STATS || defined __DOXYGEN__
|
||||||
#define LWIP_STATS 1
|
#define LWIP_STATS 0
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if LWIP_STATS
|
#if LWIP_STATS
|
||||||
@@ -2161,7 +2188,7 @@
|
|||||||
* LWIP_STATS_DISPLAY==1: Compile in the statistics output functions.
|
* LWIP_STATS_DISPLAY==1: Compile in the statistics output functions.
|
||||||
*/
|
*/
|
||||||
#if !defined LWIP_STATS_DISPLAY || defined __DOXYGEN__
|
#if !defined LWIP_STATS_DISPLAY || defined __DOXYGEN__
|
||||||
#define LWIP_STATS_DISPLAY 1
|
#define LWIP_STATS_DISPLAY 0
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -3572,4 +3599,4 @@
|
|||||||
* @}
|
* @}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#endif /* LWIP_HDR_OPT_H */
|
#endif /* LWIP_HDR_OPT_H */
|
||||||
@@ -37,10 +37,11 @@
|
|||||||
#include "ZeroTierOne.h"
|
#include "ZeroTierOne.h"
|
||||||
|
|
||||||
#include "Constants.hpp"
|
#include "Constants.hpp"
|
||||||
#include "VirtualTapManager.hpp"
|
|
||||||
#include "lwIP.h"
|
#include "lwIP.h"
|
||||||
#include "OSUtils.hpp"
|
#include "OSUtils.hpp"
|
||||||
#include "ServiceControls.hpp"
|
#include "ServiceControls.hpp"
|
||||||
|
#include "VirtualTap.hpp"
|
||||||
|
#include "Defs.hpp"
|
||||||
|
|
||||||
#include "lwip/stats.h"
|
#include "lwip/stats.h"
|
||||||
|
|
||||||
@@ -53,8 +54,14 @@ WSADATA wsaData;
|
|||||||
#include <jni.h>
|
#include <jni.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
struct zts_network_details;
|
||||||
|
struct zts_peer_details;
|
||||||
|
struct zts_network_details;
|
||||||
|
|
||||||
namespace ZeroTier {
|
namespace ZeroTier {
|
||||||
|
|
||||||
|
class VirtualTap;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* A lock used to protect any call which relies on the presence of a valid pointer
|
* A lock used to protect any call which relies on the presence of a valid pointer
|
||||||
* to the ZeroTier service.
|
* to the ZeroTier service.
|
||||||
@@ -91,6 +98,7 @@ Mutex _vtaps_lock;
|
|||||||
// Global reference to ZeroTier service
|
// Global reference to ZeroTier service
|
||||||
OneService *zt1Service;
|
OneService *zt1Service;
|
||||||
|
|
||||||
|
|
||||||
// User-provided callback for ZeroTier events
|
// User-provided callback for ZeroTier events
|
||||||
void (*_userCallbackFunc)(uint64_t, int);
|
void (*_userCallbackFunc)(uint64_t, int);
|
||||||
#ifdef SDK_JNI
|
#ifdef SDK_JNI
|
||||||
@@ -99,9 +107,8 @@ static JavaVM *jvm = NULL;
|
|||||||
jobject objRef = NULL;
|
jobject objRef = NULL;
|
||||||
jmethodID _userCallbackMethodRef = NULL;
|
jmethodID _userCallbackMethodRef = NULL;
|
||||||
#endif
|
#endif
|
||||||
}
|
|
||||||
|
|
||||||
using namespace ZeroTier;
|
std::map<uint64_t, bool> peerCache;
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
// Internal ZeroTier Service Controls (user application shall not use these)//
|
// Internal ZeroTier Service Controls (user application shall not use these)//
|
||||||
@@ -112,8 +119,8 @@ std::queue<std::pair<uint64_t, int>*> _callbackMsgQueue;
|
|||||||
void _push_callback_event(uint64_t nwid, int eventCode)
|
void _push_callback_event(uint64_t nwid, int eventCode)
|
||||||
{
|
{
|
||||||
_callback_lock.lock();
|
_callback_lock.lock();
|
||||||
if (_callbackMsgQueue.size() >= 128) {
|
if (_callbackMsgQueue.size() >= ZTS_CALLBACK_MSG_QUEUE_LEN) {
|
||||||
DEBUG_ERROR("too many callback messages in queue");
|
DEBUG_ERROR("too many callback messages in queue (see: ZTS_CALLBACK_MSG_QUEUE_LEN)");
|
||||||
_callback_lock.unlock();
|
_callback_lock.unlock();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -132,7 +139,7 @@ void _process_callback_event_helper(uint64_t nwid, int eventCode)
|
|||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
if (_userCallbackFunc) {
|
if (_userCallbackFunc) {
|
||||||
_userCallbackFunc((uint64_t)0, ZTS_EVENT_NODE_OFFLINE);
|
_userCallbackFunc(nwid, eventCode);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
@@ -192,11 +199,13 @@ int _zts_can_perform_service_operation()
|
|||||||
|
|
||||||
void _hibernate_if_needed()
|
void _hibernate_if_needed()
|
||||||
{
|
{
|
||||||
if (VirtualTapManager::get_vtaps_size()) {
|
_vtaps_lock.lock();
|
||||||
|
if (vtapMap.size()) {
|
||||||
lwip_wake_driver();
|
lwip_wake_driver();
|
||||||
} else {
|
} else {
|
||||||
lwip_hibernate_driver();
|
lwip_hibernate_driver();
|
||||||
}
|
}
|
||||||
|
_vtaps_lock.unlock();
|
||||||
}
|
}
|
||||||
#ifdef SDK_JNI
|
#ifdef SDK_JNI
|
||||||
#endif
|
#endif
|
||||||
@@ -204,7 +213,7 @@ void _hibernate_if_needed()
|
|||||||
/*
|
/*
|
||||||
* Monitors the conditions required for triggering callbacks into user code. This was made
|
* Monitors the conditions required for triggering callbacks into user code. This was made
|
||||||
* into its own thread to prevent user application abuse of callbacks from affecting
|
* into its own thread to prevent user application abuse of callbacks from affecting
|
||||||
* the timing of more sensitive aspects of the library such as polling and RX/TX of packets
|
* the timing of more sensitive aspects of the library such as polling and packet processing
|
||||||
*/
|
*/
|
||||||
#if defined(_WIN32)
|
#if defined(_WIN32)
|
||||||
DWORD WINAPI _zts_monitor_callback_conditions(LPVOID thread_id)
|
DWORD WINAPI _zts_monitor_callback_conditions(LPVOID thread_id)
|
||||||
@@ -215,74 +224,188 @@ void *_zts_monitor_callback_conditions(void *thread_id)
|
|||||||
#if defined(__APPLE__)
|
#if defined(__APPLE__)
|
||||||
pthread_setname_np(ZTS_EVENT_CALLBACK_THREAD_NAME);
|
pthread_setname_np(ZTS_EVENT_CALLBACK_THREAD_NAME);
|
||||||
#endif
|
#endif
|
||||||
while (!_serviceIsShuttingDown)
|
|
||||||
|
while (true)
|
||||||
{
|
{
|
||||||
|
if (_serviceIsShuttingDown) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
_service_lock.lock();
|
||||||
|
_callback_lock.lock();
|
||||||
|
|
||||||
|
#if ZTS_NODE_CALLBACKS
|
||||||
|
// ZT Node states
|
||||||
if (!_zts_node_online()) {
|
if (!_zts_node_online()) {
|
||||||
if (_nodeIsOnlineToggle) {
|
if (_nodeIsOnlineToggle) {
|
||||||
_nodeIsOnlineToggle = false;
|
_nodeIsOnlineToggle = false;
|
||||||
_process_callback_event((uint64_t)0, ZTS_EVENT_NODE_OFFLINE);
|
_process_callback_event_helper((uint64_t)0, ZTS_EVENT_NODE_OFFLINE);
|
||||||
|
}
|
||||||
|
_service_lock.unlock();
|
||||||
|
_callback_lock.unlock();
|
||||||
|
_api_sleep(ZTS_CALLBACK_PROCESSING_INTERVAL);
|
||||||
|
// Only process pending network callbacks if the node is online
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (_zts_node_online()) {
|
||||||
|
uint64_t nodeId = 0;
|
||||||
|
if (_zts_can_perform_service_operation()) {
|
||||||
|
nodeId = zt1Service->getNode()->address();
|
||||||
}
|
}
|
||||||
} if (_zts_node_online()) { // Only process pending network callbacks if the node is online
|
|
||||||
if (!_nodeIsOnlineToggle) {
|
if (!_nodeIsOnlineToggle) {
|
||||||
_nodeIsOnlineToggle = true;
|
_nodeIsOnlineToggle = true;
|
||||||
_process_callback_event((uint64_t)0, ZTS_EVENT_NODE_ONLINE);
|
_process_callback_event_helper(nodeId, ZTS_EVENT_NODE_ONLINE);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
// First, handle queued messages from other threads
|
// Handle messages placed in the message queue
|
||||||
_callback_lock.lock();
|
while (_callbackMsgQueue.size()) {
|
||||||
while (_callbackMsgQueue.size()) {
|
std::pair<uint64_t,int> *msg = _callbackMsgQueue.front();
|
||||||
std::pair<uint64_t,int> *msg = _callbackMsgQueue.front();
|
_callbackMsgQueue.pop();
|
||||||
_callbackMsgQueue.pop();
|
#if ZTS_NETIF_CALLBACKS
|
||||||
_process_callback_event_helper(msg->first, msg->second);
|
// lwIP netif
|
||||||
delete msg;
|
if (msg->second & (ZTS_EVENT_NETIF_STATUS_CHANGE)) {
|
||||||
}
|
_vtaps_lock.lock();
|
||||||
_callback_lock.unlock();
|
if (!vtapMap.count(msg->first)) {
|
||||||
|
if (msg->second & (ZTS_EVENT_GENERIC_DOWN)) {
|
||||||
// Second, inspect network states for changes we should report
|
_process_callback_event_helper(msg->first, msg->second);
|
||||||
_vtaps_lock.lock();
|
|
||||||
ZT_VirtualNetworkList *nl = zt1Service->getNode()->networks();
|
|
||||||
for(unsigned long i=0;i<nl->networkCount;++i) {
|
|
||||||
OneService::NetworkSettings localSettings;
|
|
||||||
zt1Service->getNetworkSettings(nl->networks[i].nwid,localSettings);
|
|
||||||
if (vtapMap[nl->networks[i].nwid]->_lastReportedStatus != nl->networks[i].status) {
|
|
||||||
switch (nl->networks[i].status) {
|
|
||||||
case ZT_NETWORK_STATUS_NOT_FOUND:
|
|
||||||
_process_callback_event(nl->networks[i].nwid, ZTS_EVENT_NETWORK_NOT_FOUND);
|
|
||||||
break;
|
|
||||||
case ZT_NETWORK_STATUS_CLIENT_TOO_OLD:
|
|
||||||
_process_callback_event(nl->networks[i].nwid, ZTS_EVENT_NETWORK_CLIENT_TOO_OLD);
|
|
||||||
break;
|
|
||||||
case ZT_NETWORK_STATUS_REQUESTING_CONFIGURATION:
|
|
||||||
_process_callback_event(nl->networks[i].nwid, ZTS_EVENT_NETWORK_REQUESTING_CONFIG);
|
|
||||||
break;
|
|
||||||
case ZT_NETWORK_STATUS_OK:
|
|
||||||
_process_callback_event(nl->networks[i].nwid, ZTS_EVENT_NETWORK_OK);
|
|
||||||
break;
|
|
||||||
case ZT_NETWORK_STATUS_ACCESS_DENIED:
|
|
||||||
_process_callback_event(nl->networks[i].nwid, ZTS_EVENT_NETWORK_ACCESS_DENIED);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
vtapMap[nl->networks[i].nwid]->_lastReportedStatus = nl->networks[i].status;
|
delete msg;
|
||||||
|
msg = NULL;
|
||||||
|
_vtaps_lock.unlock();
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
|
if (msg->second == ZTS_EVENT_NETIF_UP_IP4 && vtapMap[msg->first]->_networkStatus == ZTS_EVENT_NETWORK_OK) {
|
||||||
|
_process_callback_event_helper(msg->first, ZTS_EVENT_NETWORK_READY_IP4);
|
||||||
|
}
|
||||||
|
if (msg->second == ZTS_EVENT_NETIF_UP_IP6 && vtapMap[msg->first]->_networkStatus == ZTS_EVENT_NETWORK_OK) {
|
||||||
|
_process_callback_event_helper(msg->first, ZTS_EVENT_NETWORK_READY_IP6);
|
||||||
|
}
|
||||||
|
if (msg->second & (ZTS_EVENT_NETIF_STATUS_CHANGE)) {
|
||||||
|
vtapMap[msg->first]->_netifStatus = msg->second;
|
||||||
|
}
|
||||||
|
_vtaps_lock.unlock();
|
||||||
|
_process_callback_event_helper(msg->first, msg->second);
|
||||||
}
|
}
|
||||||
zt1Service->getNode()->freeQueryResult((void *)nl);
|
#endif // ZTS_NETIF_CALLBACKS
|
||||||
// Finally, check for a more useful definition of "readiness"
|
delete msg;
|
||||||
|
msg = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
#if ZTS_NETIF_CALLBACKS // Section for non-queued lwIP netif messages
|
||||||
|
// lwIP netif states
|
||||||
|
_vtaps_lock.lock();
|
||||||
|
if (vtapMap.size()) {
|
||||||
std::map<uint64_t, VirtualTap*>::iterator it;
|
std::map<uint64_t, VirtualTap*>::iterator it;
|
||||||
for (it = vtapMap.begin(); it != vtapMap.end(); it++) {
|
for (it = vtapMap.begin(); it != vtapMap.end(); it++) {
|
||||||
VirtualTap *tap = it->second;
|
VirtualTap *vtap = (VirtualTap*)it->second;
|
||||||
if (tap->_lastConfigUpdateTime > 0 && !tap->_lastReadyReportTime && tap->_ips.size() > 0) {
|
uint64_t eventCode = vtap->recognizeLowerLevelInterfaceStateChange(vtap->netif4);
|
||||||
tap->_lastReadyReportTime = tap->_lastConfigUpdateTime;
|
if (eventCode != ZTS_EVENT_NONE) {
|
||||||
_process_callback_event(tap->_nwid, ZTS_EVENT_NETWORK_READY);
|
_process_callback_event_helper(vtap->_nwid, eventCode);
|
||||||
|
}
|
||||||
|
eventCode = vtap->recognizeLowerLevelInterfaceStateChange(vtap->netif6);
|
||||||
|
if (eventCode != ZTS_EVENT_NONE) {
|
||||||
|
_process_callback_event_helper(vtap->_nwid, eventCode);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
_vtaps_lock.unlock();
|
|
||||||
}
|
}
|
||||||
// Doesn't need to happen as often as other API operations
|
_vtaps_lock.unlock();
|
||||||
_api_sleep(ZTS_WRAPPER_CHECK_INTERVAL);
|
#endif // ZTS_NETIF_CALLBACKS
|
||||||
|
|
||||||
|
#if ZTS_PEER_CALLBACKS
|
||||||
|
// TODO: Add peerCache clearning mechanism
|
||||||
|
// TODO: Add ZTS_EVENT_PEER_NEW message?
|
||||||
|
ZT_PeerList *pl = zt1Service->getNode()->peers();
|
||||||
|
if (pl) {
|
||||||
|
for(unsigned long i=0;i<pl->peerCount;++i) {
|
||||||
|
if (!peerCache.count(pl->peers[i].address)) { // Add first entry
|
||||||
|
if (pl->peers[i].pathCount > 0) {
|
||||||
|
_process_callback_event_helper(pl->peers[i].address, ZTS_EVENT_PEER_P2P);
|
||||||
|
}
|
||||||
|
if (pl->peers[i].pathCount == 0) {
|
||||||
|
_process_callback_event_helper(pl->peers[i].address, ZTS_EVENT_PEER_RELAY);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (peerCache[pl->peers[i].address] == 0 && pl->peers[i].pathCount > 0) {
|
||||||
|
_process_callback_event_helper(pl->peers[i].address, ZTS_EVENT_PEER_P2P);
|
||||||
|
}
|
||||||
|
if (peerCache[pl->peers[i].address] > 0 && pl->peers[i].pathCount == 0) {
|
||||||
|
_process_callback_event_helper(pl->peers[i].address, ZTS_EVENT_PEER_RELAY);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
peerCache[pl->peers[i].address] = pl->peers[i].pathCount;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
zt1Service->getNode()->freeQueryResult((void *)pl);
|
||||||
|
#endif // ZTS_PEER_CALLBACKS
|
||||||
|
|
||||||
|
#if ZTS_NETWORK_CALLBACKS
|
||||||
|
|
||||||
|
_vtaps_lock.lock();
|
||||||
|
// Second, inspect network states for changes we should report
|
||||||
|
// TODO: Use proper ZT callback mechanism
|
||||||
|
// TODO: _push_callback_event(_nwid, ZTS_EVENT_NETWORK_DOWN);
|
||||||
|
ZT_VirtualNetworkList *nl = zt1Service->getNode()->networks();
|
||||||
|
for(unsigned long i=0;i<nl->networkCount;++i) {
|
||||||
|
OneService::NetworkSettings localSettings;
|
||||||
|
zt1Service->getNetworkSettings(nl->networks[i].nwid,localSettings);
|
||||||
|
if (!vtapMap.count(nl->networks[i].nwid)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (vtapMap[nl->networks[i].nwid]->_networkStatus == nl->networks[i].status) {
|
||||||
|
continue; // no state change
|
||||||
|
}
|
||||||
|
VirtualTap *vtap = vtapMap[nl->networks[i].nwid];
|
||||||
|
uint64_t nwid = nl->networks[i].nwid;
|
||||||
|
switch (nl->networks[i].status) {
|
||||||
|
case ZT_NETWORK_STATUS_NOT_FOUND:
|
||||||
|
_process_callback_event_helper(nwid, ZTS_EVENT_NETWORK_NOT_FOUND);
|
||||||
|
break;
|
||||||
|
case ZT_NETWORK_STATUS_CLIENT_TOO_OLD:
|
||||||
|
_process_callback_event_helper(nwid, ZTS_EVENT_NETWORK_CLIENT_TOO_OLD);
|
||||||
|
break;
|
||||||
|
case ZT_NETWORK_STATUS_REQUESTING_CONFIGURATION:
|
||||||
|
_process_callback_event_helper(nwid, ZTS_EVENT_NETWORK_REQUESTING_CONFIG);
|
||||||
|
break;
|
||||||
|
case ZT_NETWORK_STATUS_OK:
|
||||||
|
if (vtap->netif4 && lwip_is_netif_up(vtap->netif4)) {
|
||||||
|
_process_callback_event_helper(nwid, ZTS_EVENT_NETWORK_READY_IP4);
|
||||||
|
}
|
||||||
|
if (vtap->netif6 && lwip_is_netif_up(vtap->netif6)) {
|
||||||
|
_process_callback_event_helper(nwid, ZTS_EVENT_NETWORK_READY_IP6);
|
||||||
|
}
|
||||||
|
_process_callback_event_helper(nwid, ZTS_EVENT_NETWORK_OK);
|
||||||
|
break;
|
||||||
|
case ZT_NETWORK_STATUS_ACCESS_DENIED:
|
||||||
|
_process_callback_event_helper(nwid, ZTS_EVENT_NETWORK_ACCESS_DENIED);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
vtapMap[nwid]->_networkStatus = nl->networks[i].status;
|
||||||
|
}
|
||||||
|
_vtaps_lock.unlock();
|
||||||
|
zt1Service->getNode()->freeQueryResult((void *)nl);
|
||||||
|
|
||||||
|
#endif // ZTS_NETWORK_CALLBACKS
|
||||||
|
|
||||||
|
// Finally, check for a more useful definition of "readiness"
|
||||||
|
/*
|
||||||
|
std::map<uint64_t, VirtualTap*>::iterator it;
|
||||||
|
for (it = vtapMap.begin(); it != vtapMap.end(); it++) {
|
||||||
|
VirtualTap *tap = it->second;
|
||||||
|
if (tap->_lastConfigUpdateTime > 0 && !tap->_lastReadyReportTime && tap->_ips.size() > 0) {
|
||||||
|
tap->_lastReadyReportTime = tap->_lastConfigUpdateTime;
|
||||||
|
_process_callback_event(tap->_nwid, ZTS_EVENT_NETWORK_READY);
|
||||||
|
}
|
||||||
|
}*/
|
||||||
|
_service_lock.unlock();
|
||||||
|
_callback_lock.unlock();
|
||||||
|
_api_sleep(ZTS_CALLBACK_PROCESSING_INTERVAL);
|
||||||
}
|
}
|
||||||
DEBUG_ERROR("exiting from monitor loop");
|
DEBUG_INFO("exited from callback processing loop");
|
||||||
|
pthread_exit(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Starts a ZeroTier service in the background
|
// Starts a ZeroTier service in the background
|
||||||
@@ -306,7 +429,6 @@ void *_zts_start_service(void *thread_id)
|
|||||||
DEBUG_INFO("service already started, doing nothing");
|
DEBUG_INFO("service already started, doing nothing");
|
||||||
retval = NULL;
|
retval = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
std::vector<std::string> hpsp(OSUtils::split(homeDir.c_str(), ZT_PATH_SEPARATOR_S,"",""));
|
std::vector<std::string> hpsp(OSUtils::split(homeDir.c_str(), ZT_PATH_SEPARATOR_S,"",""));
|
||||||
std::string ptmp;
|
std::string ptmp;
|
||||||
@@ -367,10 +489,11 @@ void *_zts_start_service(void *thread_id)
|
|||||||
_service_lock.unlock();
|
_service_lock.unlock();
|
||||||
_serviceIsShuttingDown = false;
|
_serviceIsShuttingDown = false;
|
||||||
_process_callback_event((uint64_t)0, ZTS_EVENT_NODE_DOWN);
|
_process_callback_event((uint64_t)0, ZTS_EVENT_NODE_DOWN);
|
||||||
|
DEBUG_INFO("exiting zt service thread");
|
||||||
} catch ( ... ) {
|
} catch ( ... ) {
|
||||||
DEBUG_ERROR("unexpected exception starting ZeroTier instance");
|
DEBUG_ERROR("unexpected exception starting ZeroTier instance");
|
||||||
}
|
}
|
||||||
pthread_exit(NULL);
|
pthread_exit(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
@@ -434,7 +557,11 @@ JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_get_1service_1port(
|
|||||||
zts_err_t zts_join(const uint64_t nwid, int blocking)
|
zts_err_t zts_join(const uint64_t nwid, int blocking)
|
||||||
{
|
{
|
||||||
zts_err_t retval = ZTS_ERR_OK;
|
zts_err_t retval = ZTS_ERR_OK;
|
||||||
retval = VirtualTapManager::get_vtaps_size() >= ZTS_MAX_JOINED_NETWORKS ? ZTS_ERR_INVALID_OP : ZTS_ERR_OK;
|
|
||||||
|
_vtaps_lock.lock();
|
||||||
|
retval = vtapMap.size() >= ZTS_MAX_JOINED_NETWORKS ? ZTS_ERR_INVALID_OP : ZTS_ERR_OK;
|
||||||
|
_vtaps_lock.unlock();
|
||||||
|
|
||||||
if (retval == ZTS_ERR_OK) {
|
if (retval == ZTS_ERR_OK) {
|
||||||
_service_lock.lock();
|
_service_lock.lock();
|
||||||
if (blocking) {
|
if (blocking) {
|
||||||
@@ -463,7 +590,6 @@ zts_err_t zts_join(const uint64_t nwid, int blocking)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
_service_lock.unlock();
|
_service_lock.unlock();
|
||||||
_hibernate_if_needed();
|
|
||||||
}
|
}
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
@@ -504,8 +630,9 @@ zts_err_t zts_leave(const uint64_t nwid, int blocking)
|
|||||||
zt1Service->getNode()->leave(nwid, NULL, NULL);
|
zt1Service->getNode()->leave(nwid, NULL, NULL);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
VirtualTapManager::remove_by_nwid(nwid);
|
_vtaps_lock.lock();
|
||||||
_hibernate_if_needed();
|
vtapMap.erase(nwid);
|
||||||
|
_vtaps_lock.unlock();
|
||||||
_service_lock.unlock();
|
_service_lock.unlock();
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
@@ -520,6 +647,7 @@ JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_leave(
|
|||||||
zts_err_t zts_leave_all(int blocking)
|
zts_err_t zts_leave_all(int blocking)
|
||||||
{
|
{
|
||||||
zts_err_t retval = ZTS_ERR_OK;
|
zts_err_t retval = ZTS_ERR_OK;
|
||||||
|
/*
|
||||||
if (!zt1Service || _freeHasBeenCalled || _serviceIsShuttingDown) {
|
if (!zt1Service || _freeHasBeenCalled || _serviceIsShuttingDown) {
|
||||||
retval = ZTS_ERR_SERVICE;
|
retval = ZTS_ERR_SERVICE;
|
||||||
}
|
}
|
||||||
@@ -531,6 +659,8 @@ zts_err_t zts_leave_all(int blocking)
|
|||||||
zts_leave(nds[i].nwid);
|
zts_leave(nds[i].nwid);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
#ifdef SDK_JNI
|
#ifdef SDK_JNI
|
||||||
@@ -588,7 +718,9 @@ JNIEXPORT jboolean JNICALL Java_com_zerotier_libzt_ZeroTier_core_1running(
|
|||||||
int zts_ready()
|
int zts_ready()
|
||||||
{
|
{
|
||||||
_service_lock.lock();
|
_service_lock.lock();
|
||||||
bool stackRunning = VirtualTapManager::get_vtaps_size() > 0 ? true : false;
|
_vtaps_lock.lock();
|
||||||
|
bool stackRunning = vtapMap.size() > 0 ? true : false;
|
||||||
|
_vtaps_lock.unlock();
|
||||||
_service_lock.unlock();
|
_service_lock.unlock();
|
||||||
return zts_core_running() && stackRunning;
|
return zts_core_running() && stackRunning;
|
||||||
}
|
}
|
||||||
@@ -693,8 +825,6 @@ zts_err_t zts_start_with_callback(const char *path, void (*callback)(uint64_t, i
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
_startup_lock.unlock();
|
_startup_lock.unlock();
|
||||||
// if (blocking && retval == ZTS_ERR_OK) { DEBUG_INFO("node=%llx online", (unsigned long long)zts_get_node_id());}
|
|
||||||
_hibernate_if_needed();
|
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -754,7 +884,6 @@ zts_err_t zts_startjoin(const char *path, const uint64_t nwid)
|
|||||||
retval = ZTS_ERR_SERVICE;
|
retval = ZTS_ERR_SERVICE;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
_hibernate_if_needed();
|
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
#ifdef SDK_JNI
|
#ifdef SDK_JNI
|
||||||
@@ -773,11 +902,26 @@ zts_err_t zts_stop(int blocking)
|
|||||||
{
|
{
|
||||||
zts_err_t retval = ZTS_ERR_OK;
|
zts_err_t retval = ZTS_ERR_OK;
|
||||||
_service_lock.lock();
|
_service_lock.lock();
|
||||||
|
// leave all networks
|
||||||
|
/*
|
||||||
|
_vtaps_lock.lock();
|
||||||
|
if (vtapMap.size()) {
|
||||||
|
std::map<uint64_t, VirtualTap*>::iterator it;
|
||||||
|
for (it = vtapMap.begin(); it != vtapMap.end(); it++) {
|
||||||
|
VirtualTap *vtap = (VirtualTap*)it->second;
|
||||||
|
zt1Service->getNode()->leave(vtap->_nwid, NULL, NULL);
|
||||||
|
}
|
||||||
|
vtapMap.clear();
|
||||||
|
}
|
||||||
|
_vtaps_lock.unlock();
|
||||||
|
*/
|
||||||
|
// begin shutdown
|
||||||
|
peerCache.clear(); // TODO: Ensure this is locked correctly
|
||||||
bool didStop = false;
|
bool didStop = false;
|
||||||
if (_zts_can_perform_service_operation()) {
|
if (_zts_can_perform_service_operation()) {
|
||||||
didStop = true;
|
_serviceIsShuttingDown = true;
|
||||||
zt1Service->terminate();
|
zt1Service->terminate();
|
||||||
VirtualTapManager::clear();
|
didStop = true;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
// Nothing to do
|
// Nothing to do
|
||||||
@@ -791,7 +935,6 @@ zts_err_t zts_stop(int blocking)
|
|||||||
// Block until ZT service thread successfully exits
|
// Block until ZT service thread successfully exits
|
||||||
pthread_join(service_thread, NULL);
|
pthread_join(service_thread, NULL);
|
||||||
}
|
}
|
||||||
_hibernate_if_needed();
|
|
||||||
_clear_registered_callback();
|
_clear_registered_callback();
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
@@ -898,7 +1041,9 @@ zts_err_t zts_get_num_joined_networks()
|
|||||||
retval = ZTS_ERR_SERVICE;
|
retval = ZTS_ERR_SERVICE;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
retval = VirtualTapManager::get_vtaps_size();
|
_vtaps_lock.lock();
|
||||||
|
retval = vtapMap.size();
|
||||||
|
_vtaps_lock.unlock();
|
||||||
}
|
}
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
@@ -910,8 +1055,50 @@ JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_get_1num_1joined_1networ
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
// Network Details //
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
void __get_network_details_helper(uint64_t nwid, struct zts_network_details *nd)
|
||||||
|
{
|
||||||
|
socklen_t addrlen;
|
||||||
|
VirtualTap *tap = vtapMap[nwid];
|
||||||
|
nd->nwid = tap->_nwid;
|
||||||
|
nd->mtu = tap->_mtu;
|
||||||
|
// assigned addresses
|
||||||
|
nd->num_addresses = tap->_ips.size() < ZTS_MAX_ASSIGNED_ADDRESSES ? tap->_ips.size() : ZTS_MAX_ASSIGNED_ADDRESSES;
|
||||||
|
for (int j=0; j<nd->num_addresses; j++) {
|
||||||
|
addrlen = tap->_ips[j].isV4() ? sizeof(struct sockaddr_in) : sizeof(struct sockaddr_in6);
|
||||||
|
memcpy(&(nd->addr[j]), &(tap->_ips[j]), addrlen);
|
||||||
|
}
|
||||||
|
// routes
|
||||||
|
nd->num_routes = ZTS_MAX_NETWORK_ROUTES;;
|
||||||
|
zt1Service->getRoutes(nwid, (ZT_VirtualNetworkRoute*)&(nd->routes)[0], &(nd->num_routes));
|
||||||
|
}
|
||||||
|
|
||||||
|
void _get_network_details(uint64_t nwid, struct zts_network_details *nd)
|
||||||
|
{
|
||||||
|
_vtaps_lock.lock();
|
||||||
|
__get_network_details_helper(nwid, nd);
|
||||||
|
_vtaps_lock.unlock();
|
||||||
|
}
|
||||||
|
|
||||||
|
void _get_all_network_details(struct zts_network_details *nds, int *num)
|
||||||
|
{
|
||||||
|
_vtaps_lock.lock();
|
||||||
|
*num = vtapMap.size();
|
||||||
|
int idx = 0;
|
||||||
|
std::map<uint64_t, VirtualTap*>::iterator it;
|
||||||
|
for (it = vtapMap.begin(); it != vtapMap.end(); it++) {
|
||||||
|
_get_network_details(it->first, &nds[idx]);
|
||||||
|
idx++;
|
||||||
|
}
|
||||||
|
_vtaps_lock.unlock();
|
||||||
|
}
|
||||||
|
|
||||||
zts_err_t zts_get_network_details(uint64_t nwid, struct zts_network_details *nd)
|
zts_err_t zts_get_network_details(uint64_t nwid, struct zts_network_details *nd)
|
||||||
{
|
{
|
||||||
|
_service_lock.lock();
|
||||||
zts_err_t retval = ZTS_ERR_OK;
|
zts_err_t retval = ZTS_ERR_OK;
|
||||||
if (!nd || nwid == 0) {
|
if (!nd || nwid == 0) {
|
||||||
retval = ZTS_ERR_INVALID_ARG;
|
retval = ZTS_ERR_INVALID_ARG;
|
||||||
@@ -920,8 +1107,9 @@ zts_err_t zts_get_network_details(uint64_t nwid, struct zts_network_details *nd)
|
|||||||
retval = ZTS_ERR_SERVICE;
|
retval = ZTS_ERR_SERVICE;
|
||||||
}
|
}
|
||||||
if (retval == ZTS_ERR_OK) {
|
if (retval == ZTS_ERR_OK) {
|
||||||
VirtualTapManager::get_network_details(zt1Service, nwid, nd);
|
_get_network_details(nwid, nd);
|
||||||
}
|
}
|
||||||
|
_service_lock.unlock();
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
#ifdef SDK_JNI
|
#ifdef SDK_JNI
|
||||||
@@ -929,6 +1117,7 @@ zts_err_t zts_get_network_details(uint64_t nwid, struct zts_network_details *nd)
|
|||||||
|
|
||||||
zts_err_t zts_get_all_network_details(struct zts_network_details *nds, int *num)
|
zts_err_t zts_get_all_network_details(struct zts_network_details *nds, int *num)
|
||||||
{
|
{
|
||||||
|
_service_lock.lock();
|
||||||
zts_err_t retval = ZTS_ERR_OK;
|
zts_err_t retval = ZTS_ERR_OK;
|
||||||
if (!nds || !num) {
|
if (!nds || !num) {
|
||||||
retval = ZTS_ERR_INVALID_ARG;
|
retval = ZTS_ERR_INVALID_ARG;
|
||||||
@@ -937,13 +1126,18 @@ zts_err_t zts_get_all_network_details(struct zts_network_details *nds, int *num)
|
|||||||
retval = ZTS_ERR_SERVICE;
|
retval = ZTS_ERR_SERVICE;
|
||||||
}
|
}
|
||||||
if (retval == ZTS_ERR_OK) {
|
if (retval == ZTS_ERR_OK) {
|
||||||
VirtualTapManager::get_all_network_details(zt1Service, nds, num);
|
_get_all_network_details(nds, num);
|
||||||
}
|
}
|
||||||
|
_service_lock.unlock();
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
#ifdef SDK_JNI
|
#ifdef SDK_JNI
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
// HTTP Backplane //
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
zts_err_t zts_enable_http_backplane_mgmt()
|
zts_err_t zts_enable_http_backplane_mgmt()
|
||||||
{
|
{
|
||||||
zts_err_t retval = ZTS_ERR_OK;
|
zts_err_t retval = ZTS_ERR_OK;
|
||||||
@@ -979,3 +1173,5 @@ zts_err_t zts_disable_http_backplane_mgmt()
|
|||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
} // namespace ZeroTier
|
||||||
@@ -36,10 +36,11 @@
|
|||||||
#include "OSUtils.hpp"
|
#include "OSUtils.hpp"
|
||||||
|
|
||||||
#include "Constants.hpp" // libzt
|
#include "Constants.hpp" // libzt
|
||||||
|
#include "ServiceControls.hpp"
|
||||||
|
#include "OneService.hpp"
|
||||||
extern void _push_callback_event(uint64_t nwid, int eventCode);
|
extern void _push_callback_event(uint64_t nwid, int eventCode);
|
||||||
|
|
||||||
#include "Mutex.hpp"
|
#include "Mutex.hpp"
|
||||||
#include "VirtualTapManager.hpp"
|
|
||||||
#include "lwIP.h"
|
#include "lwIP.h"
|
||||||
|
|
||||||
#ifdef _MSC_VER
|
#ifdef _MSC_VER
|
||||||
@@ -48,8 +49,12 @@ extern void _push_callback_event(uint64_t nwid, int eventCode);
|
|||||||
|
|
||||||
namespace ZeroTier {
|
namespace ZeroTier {
|
||||||
|
|
||||||
|
class VirtualTap;
|
||||||
|
|
||||||
extern OneService *zt1Service;
|
extern OneService *zt1Service;
|
||||||
extern void (*_userCallbackFunc)(uint64_t, int);
|
extern void (*_userCallbackFunc)(uint64_t, int);
|
||||||
|
extern std::map<uint64_t, VirtualTap*> vtapMap;
|
||||||
|
extern Mutex _vtaps_lock;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A virtual tap device. The ZeroTier core service creates one of these for each
|
* A virtual tap device. The ZeroTier core service creates one of these for each
|
||||||
@@ -77,28 +82,59 @@ VirtualTap::VirtualTap(
|
|||||||
_unixListenSocket((PhySocket *)0),
|
_unixListenSocket((PhySocket *)0),
|
||||||
_phy(this,false,true)
|
_phy(this,false,true)
|
||||||
{
|
{
|
||||||
VirtualTapManager::add_tap(this);
|
|
||||||
memset(vtap_full_name, 0, sizeof(vtap_full_name));
|
memset(vtap_full_name, 0, sizeof(vtap_full_name));
|
||||||
snprintf(vtap_full_name, sizeof(vtap_full_name), "libzt%llx", (unsigned long long)_nwid);
|
snprintf(vtap_full_name, sizeof(vtap_full_name), "libzt%llx", (unsigned long long)_nwid);
|
||||||
_dev = vtap_full_name;
|
_dev = vtap_full_name;
|
||||||
::pipe(_shutdownSignalPipe);
|
::pipe(_shutdownSignalPipe);
|
||||||
|
|
||||||
|
_vtaps_lock.lock();
|
||||||
|
vtapMap[_nwid] = this;
|
||||||
|
_vtaps_lock.unlock();
|
||||||
|
|
||||||
lwip_driver_init();
|
lwip_driver_init();
|
||||||
// start virtual tap thread and stack I/O loops
|
// Start virtual tap thread and stack I/O loops
|
||||||
_thread = Thread::start(this);
|
_thread = Thread::start(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
VirtualTap::~VirtualTap()
|
VirtualTap::~VirtualTap()
|
||||||
{
|
{
|
||||||
_push_callback_event(_nwid, ZTS_EVENT_NETWORK_DOWN);
|
|
||||||
lwip_driver_set_tap_interfaces_down(this);
|
|
||||||
_run = false;
|
_run = false;
|
||||||
::write(_shutdownSignalPipe[1],"\0",1);
|
::write(_shutdownSignalPipe[1],"\0",1);
|
||||||
_phy.whack();
|
_phy.whack();
|
||||||
|
lwip_dispose_of_netifs(this);
|
||||||
Thread::join(_thread);
|
Thread::join(_thread);
|
||||||
::close(_shutdownSignalPipe[0]);
|
::close(_shutdownSignalPipe[0]);
|
||||||
::close(_shutdownSignalPipe[1]);
|
::close(_shutdownSignalPipe[1]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uint64_t VirtualTap::recognizeLowerLevelInterfaceStateChange(void *n)
|
||||||
|
{
|
||||||
|
if (!n) {
|
||||||
|
return ZTS_EVENT_NONE;
|
||||||
|
}
|
||||||
|
if (n == netif4) {
|
||||||
|
if (netif4WasUpLastCheck && !lwip_is_netif_up(netif4)) {
|
||||||
|
netif4WasUpLastCheck = false;
|
||||||
|
return ZTS_EVENT_NETIF_DOWN_IP4;
|
||||||
|
}
|
||||||
|
if (!netif4WasUpLastCheck && lwip_is_netif_up(netif4)) {
|
||||||
|
netif4WasUpLastCheck = true;
|
||||||
|
return ZTS_EVENT_NETIF_UP_IP4;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (n == netif6) {
|
||||||
|
if (netif6WasUpLastCheck && !lwip_is_netif_up(netif6)) {
|
||||||
|
netif6WasUpLastCheck = false;
|
||||||
|
return ZTS_EVENT_NETIF_DOWN_IP6;
|
||||||
|
}
|
||||||
|
if (!netif6WasUpLastCheck && lwip_is_netif_up(netif6)) {
|
||||||
|
netif6WasUpLastCheck = true;
|
||||||
|
return ZTS_EVENT_NETIF_UP_IP6;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return ZTS_EVENT_NONE;
|
||||||
|
}
|
||||||
|
|
||||||
void VirtualTap::lastConfigUpdate(uint64_t lastConfigUpdateTime)
|
void VirtualTap::lastConfigUpdate(uint64_t lastConfigUpdateTime)
|
||||||
{
|
{
|
||||||
_lastConfigUpdateTime = lastConfigUpdateTime;
|
_lastConfigUpdateTime = lastConfigUpdateTime;
|
||||||
@@ -114,20 +150,15 @@ bool VirtualTap::enabled() const
|
|||||||
return _enabled;
|
return _enabled;
|
||||||
}
|
}
|
||||||
|
|
||||||
void VirtualTap::registerIpWithStack(const InetAddress &ip)
|
|
||||||
{
|
|
||||||
lwip_init_interface((void*)this, this->_mac, ip);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool VirtualTap::addIp(const InetAddress &ip)
|
bool VirtualTap::addIp(const InetAddress &ip)
|
||||||
{
|
{
|
||||||
char ipbuf[INET6_ADDRSTRLEN];
|
char ipbuf[INET6_ADDRSTRLEN];
|
||||||
Mutex::Lock _l(_ips_m);
|
Mutex::Lock _l(_ips_m);
|
||||||
registerIpWithStack(ip);
|
|
||||||
if (std::find(_ips.begin(),_ips.end(),ip) == _ips.end()) {
|
if (std::find(_ips.begin(),_ips.end(),ip) == _ips.end()) {
|
||||||
_ips.push_back(ip);
|
_ips.push_back(ip);
|
||||||
std::sort(_ips.begin(),_ips.end());
|
std::sort(_ips.begin(),_ips.end());
|
||||||
}
|
}
|
||||||
|
lwip_init_interface((void*)this, this->_mac, ip);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -231,7 +262,8 @@ void VirtualTap::threadMain()
|
|||||||
while (true) {
|
while (true) {
|
||||||
FD_SET(_shutdownSignalPipe[0],&readfds);
|
FD_SET(_shutdownSignalPipe[0],&readfds);
|
||||||
select(nfds,&readfds,&nullfds,&nullfds,&tv);
|
select(nfds,&readfds,&nullfds,&nullfds,&tv);
|
||||||
if (FD_ISSET(_shutdownSignalPipe[0],&readfds)) { // writes to shutdown pipe terminate thread
|
// writes to shutdown pipe terminate thread
|
||||||
|
if (FD_ISSET(_shutdownSignalPipe[0],&readfds)) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
#ifdef _MSC_VER
|
#ifdef _MSC_VER
|
||||||
|
|||||||
@@ -1,116 +0,0 @@
|
|||||||
/*
|
|
||||||
* ZeroTier SDK - Network Virtualization Everywhere
|
|
||||||
* Copyright (C) 2011-2019 ZeroTier, Inc. https://www.zerotier.com/
|
|
||||||
*
|
|
||||||
* 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 <http://www.gnu.org/licenses/>.
|
|
||||||
*
|
|
||||||
* --
|
|
||||||
*
|
|
||||||
* You can be released from the requirements of the license by purchasing
|
|
||||||
* a commercial license. Buying such a license is mandatory as soon as you
|
|
||||||
* develop commercial closed-source software that incorporates or links
|
|
||||||
* directly against ZeroTier software without disclosing the source code
|
|
||||||
* of your own application.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @file
|
|
||||||
*
|
|
||||||
* Management of virtual tap interfaces
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "VirtualTap.hpp"
|
|
||||||
#include "VirtualTapManager.hpp"
|
|
||||||
#include "ServiceControls.hpp"
|
|
||||||
#include "OneService.hpp"
|
|
||||||
|
|
||||||
namespace ZeroTier {
|
|
||||||
|
|
||||||
extern std::map<uint64_t, VirtualTap*> vtapMap;
|
|
||||||
extern Mutex _vtaps_lock;
|
|
||||||
extern void (*_userCallbackFunc)(uint64_t, int);
|
|
||||||
|
|
||||||
class VirtualTap;
|
|
||||||
|
|
||||||
void VirtualTapManager::add_tap(VirtualTap *tap) {
|
|
||||||
_vtaps_lock.lock();
|
|
||||||
vtapMap[tap->_nwid] = tap;
|
|
||||||
_vtaps_lock.unlock();
|
|
||||||
}
|
|
||||||
|
|
||||||
VirtualTap *VirtualTapManager::getTapByNWID(uint64_t nwid) {
|
|
||||||
_vtaps_lock.lock();
|
|
||||||
VirtualTap *s, *tap = vtapMap[nwid];
|
|
||||||
_vtaps_lock.unlock();
|
|
||||||
return tap;
|
|
||||||
}
|
|
||||||
|
|
||||||
size_t VirtualTapManager::get_vtaps_size() {
|
|
||||||
size_t sz;
|
|
||||||
_vtaps_lock.lock();
|
|
||||||
sz = vtapMap.size();
|
|
||||||
_vtaps_lock.unlock();
|
|
||||||
return sz;
|
|
||||||
}
|
|
||||||
|
|
||||||
void VirtualTapManager::remove_by_nwid(uint64_t nwid) {
|
|
||||||
_vtaps_lock.lock();
|
|
||||||
vtapMap.erase(nwid);
|
|
||||||
_vtaps_lock.unlock();
|
|
||||||
}
|
|
||||||
|
|
||||||
void VirtualTapManager::clear() {
|
|
||||||
_vtaps_lock.lock();
|
|
||||||
vtapMap.clear();
|
|
||||||
_vtaps_lock.unlock();
|
|
||||||
}
|
|
||||||
|
|
||||||
void VirtualTapManager::get_network_details_helper(void *zt1ServiceRef, uint64_t nwid, struct zts_network_details *nd)
|
|
||||||
{
|
|
||||||
socklen_t addrlen;
|
|
||||||
VirtualTap *tap = vtapMap[nwid];
|
|
||||||
nd->nwid = tap->_nwid;
|
|
||||||
nd->mtu = tap->_mtu;
|
|
||||||
// assigned addresses
|
|
||||||
nd->num_addresses = tap->_ips.size() < ZTS_MAX_ASSIGNED_ADDRESSES ? tap->_ips.size() : ZTS_MAX_ASSIGNED_ADDRESSES;
|
|
||||||
for (int j=0; j<nd->num_addresses; j++) {
|
|
||||||
addrlen = tap->_ips[j].isV4() ? sizeof(struct sockaddr_in) : sizeof(struct sockaddr_in6);
|
|
||||||
memcpy(&(nd->addr[j]), &(tap->_ips[j]), addrlen);
|
|
||||||
}
|
|
||||||
// routes
|
|
||||||
nd->num_routes = ZTS_MAX_NETWORK_ROUTES;
|
|
||||||
OneService *zt1Service = (OneService*)zt1ServiceRef;
|
|
||||||
zt1Service->getRoutes(nwid, (ZT_VirtualNetworkRoute*)&(nd->routes)[0], &(nd->num_routes));
|
|
||||||
}
|
|
||||||
|
|
||||||
void VirtualTapManager::get_network_details(void *zt1ServiceRef, uint64_t nwid, struct zts_network_details *nd) {
|
|
||||||
_vtaps_lock.lock();
|
|
||||||
get_network_details_helper(zt1ServiceRef, nwid, nd);
|
|
||||||
_vtaps_lock.unlock();
|
|
||||||
}
|
|
||||||
|
|
||||||
void VirtualTapManager::get_all_network_details(void *zt1ServiceRef, struct zts_network_details *nds, int *num) {
|
|
||||||
|
|
||||||
_vtaps_lock.lock();
|
|
||||||
*num = vtapMap.size();
|
|
||||||
int idx = 0;
|
|
||||||
std::map<uint64_t, VirtualTap*>::iterator it;
|
|
||||||
for (it = vtapMap.begin(); it != vtapMap.end(); it++) {
|
|
||||||
get_network_details(zt1ServiceRef, it->first, &nds[idx]);
|
|
||||||
idx++;
|
|
||||||
}
|
|
||||||
_vtaps_lock.unlock();
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace ZeroTier
|
|
||||||
276
src/lwIP.cpp
276
src/lwIP.cpp
@@ -60,28 +60,22 @@
|
|||||||
|
|
||||||
#if defined(_WIN32)
|
#if defined(_WIN32)
|
||||||
#include <time.h>
|
#include <time.h>
|
||||||
void ms_sleep(unsigned long ms)
|
|
||||||
{
|
|
||||||
Sleep(ms);
|
|
||||||
}
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
std::queue<struct pbuf *> rx_queue;
|
namespace ZeroTier {
|
||||||
|
|
||||||
ZeroTier::Mutex _rx_input_lock_m;
|
|
||||||
|
|
||||||
bool main_loop_exited = false;
|
bool main_loop_exited = false;
|
||||||
bool lwip_driver_initialized = false;
|
bool lwip_driver_initialized = false;
|
||||||
bool has_already_been_initialized = false;
|
bool has_already_been_initialized = false;
|
||||||
int hibernationDelayMultiplier = 1;
|
int hibernationDelayMultiplier = 1;
|
||||||
|
|
||||||
ZeroTier::Mutex driver_m;
|
Mutex driver_m;
|
||||||
|
|
||||||
ZeroTier::MAC _mac; // TODO: Should remove this
|
std::queue<struct zts_sorted_packet*> rx_queue;
|
||||||
|
ZeroTier::Mutex _rx_input_lock_m;
|
||||||
std::vector<struct netif *> lwip_netifs;
|
|
||||||
|
|
||||||
extern void _push_callback_event(uint64_t nwid, int eventCode);
|
extern void _push_callback_event(uint64_t nwid, int eventCode);
|
||||||
|
extern void _process_callback_event_helper(uint64_t nwid, int eventCode);
|
||||||
|
|
||||||
void lwip_hibernate_driver()
|
void lwip_hibernate_driver()
|
||||||
{
|
{
|
||||||
@@ -108,10 +102,8 @@ void my_tcpip_callback(void *arg)
|
|||||||
if (main_loop_exited) {
|
if (main_loop_exited) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
// stats_display();
|
|
||||||
err_t err = ERR_OK;
|
err_t err = ERR_OK;
|
||||||
int loop_score = LWIP_FRAMES_HANDLED_PER_CORE_CALL; // max num of packets to read per polling call
|
int loop_score = LWIP_FRAMES_HANDLED_PER_CORE_CALL; // max num of packets to read per polling call
|
||||||
// TODO: Optimize (use Ringbuffer)
|
|
||||||
while (loop_score > 0) {
|
while (loop_score > 0) {
|
||||||
// TODO: Swap this block out for a thread-safe container
|
// TODO: Swap this block out for a thread-safe container
|
||||||
_rx_input_lock_m.lock();
|
_rx_input_lock_m.lock();
|
||||||
@@ -119,75 +111,32 @@ void my_tcpip_callback(void *arg)
|
|||||||
_rx_input_lock_m.unlock();
|
_rx_input_lock_m.unlock();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
struct pbuf *p = rx_queue.front();
|
struct zts_sorted_packet *sp = rx_queue.front();
|
||||||
|
struct pbuf *p = sp->p;
|
||||||
rx_queue.pop();
|
rx_queue.pop();
|
||||||
_rx_input_lock_m.unlock();
|
_rx_input_lock_m.unlock();
|
||||||
|
// Feed packet into appropriate lwIP netif
|
||||||
// Packet routing logic. Inputs packet into correct lwip netif interface depending on protocol type
|
if (sp->p && sp->n) {
|
||||||
struct ip_hdr *iphdr;
|
if ((err = sp->n->input(sp->p, sp->n)) != ERR_OK) {
|
||||||
switch (((struct eth_hdr *)p->payload)->type)
|
DEBUG_ERROR("packet input error (p=%p, n=%p)=%d", p, sp->n, err);
|
||||||
{
|
pbuf_free(p);
|
||||||
case PP_HTONS(ETHTYPE_IPV6): {
|
}
|
||||||
iphdr = (struct ip_hdr *)((char *)p->payload + SIZEOF_ETH_HDR);
|
sp->p = NULL;
|
||||||
for (size_t i=0; i<lwip_netifs.size(); i++) {
|
|
||||||
if (lwip_netifs[i]->output_ip6 &&
|
|
||||||
lwip_netifs[i]->output_ip6 == ethip6_output) {
|
|
||||||
// TODO: Check prefix match?
|
|
||||||
if ((err = lwip_netifs[i]->input(p, lwip_netifs[i])) != ERR_OK) {
|
|
||||||
DEBUG_ERROR("packet input error (ipv6, p=%p, netif=%p)=%d", p, &lwip_netifs[i], err);
|
|
||||||
pbuf_free(p);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} break;
|
|
||||||
case PP_HTONS(ETHTYPE_IP): {
|
|
||||||
iphdr = (struct ip_hdr *)((char *)p->payload + SIZEOF_ETH_HDR);
|
|
||||||
for (size_t i=0; i<lwip_netifs.size(); i++) {
|
|
||||||
if (lwip_netifs[i]->output &&
|
|
||||||
lwip_netifs[i]->output == etharp_output) {
|
|
||||||
if (lwip_netifs[i]->ip_addr.u_addr.ip4.addr == iphdr->dest.addr ||
|
|
||||||
ip4_addr_isbroadcast_u32(iphdr->dest.addr, lwip_netifs[i])) {
|
|
||||||
if ((err = lwip_netifs[i]->input(p, lwip_netifs[i])) != ERR_OK) {
|
|
||||||
DEBUG_ERROR("packet input error (ipv4, p=%p, netif=%p)=%d", p, &lwip_netifs[i], err);
|
|
||||||
pbuf_free(p);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} break;
|
|
||||||
case PP_HTONS(ETHTYPE_ARP): {
|
|
||||||
for (size_t i=0; i<lwip_netifs.size(); i++) {
|
|
||||||
if (lwip_netifs[i]->state) {
|
|
||||||
//pbuf_ref(p);
|
|
||||||
if ((err = lwip_netifs[i]->input(p, lwip_netifs[i])) != ERR_OK) {
|
|
||||||
DEBUG_ERROR("packet input error (arp, p=%p, netif=%p)=%d", p, &lwip_netifs[i], err);
|
|
||||||
pbuf_free(p);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
} break;
|
|
||||||
default:
|
|
||||||
DEBUG_INFO("unhandled packet type (p=%p)", p);
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
//
|
delete sp;
|
||||||
p = NULL;
|
sp = NULL;
|
||||||
loop_score--;
|
loop_score--;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// main thread which starts the initialization process
|
// Main thread which starts the initialization process
|
||||||
static void main_lwip_driver_loop(void *arg)
|
static void main_lwip_driver_loop(void *arg)
|
||||||
{
|
{
|
||||||
#if defined(__linux__)
|
#if defined(__linux__)
|
||||||
pthread_setname_np(pthread_self(), "lwip_driver_loop");
|
pthread_setname_np(pthread_self(), "lwipDriver");
|
||||||
#endif
|
#endif
|
||||||
#if defined(__APPLE__)
|
#if defined(__APPLE__)
|
||||||
pthread_setname_np("lwip_driver_loop");
|
pthread_setname_np("lwipDriver");
|
||||||
#endif
|
#endif
|
||||||
sys_sem_t sem;
|
sys_sem_t sem;
|
||||||
LWIP_UNUSED_ARG(arg);
|
LWIP_UNUSED_ARG(arg);
|
||||||
@@ -199,7 +148,7 @@ static void main_lwip_driver_loop(void *arg)
|
|||||||
sys_sem_wait(&sem);
|
sys_sem_wait(&sem);
|
||||||
while(lwip_driver_initialized) {
|
while(lwip_driver_initialized) {
|
||||||
#if defined(_WIN32)
|
#if defined(_WIN32)
|
||||||
ms_sleep(LWIP_GUARDED_BUF_CHECK_INTERVAL*hibernationDelayMultiplier);
|
Sleep(LWIP_GUARDED_BUF_CHECK_INTERVAL*hibernationDelayMultiplier);
|
||||||
#else
|
#else
|
||||||
usleep(LWIP_GUARDED_BUF_CHECK_INTERVAL*1000*hibernationDelayMultiplier);
|
usleep(LWIP_GUARDED_BUF_CHECK_INTERVAL*1000*hibernationDelayMultiplier);
|
||||||
#endif
|
#endif
|
||||||
@@ -247,34 +196,22 @@ void lwip_driver_shutdown()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void lwip_driver_set_all_interfaces_down()
|
void lwip_dispose_of_netifs(void *tapref)
|
||||||
{
|
{
|
||||||
for (size_t i=0; i<lwip_netifs.size(); i++) {
|
ZeroTier::VirtualTap *vtap = (ZeroTier::VirtualTap*)tapref;
|
||||||
if (lwip_netifs[i]) {
|
if (vtap->netif4) {
|
||||||
netif_remove(lwip_netifs[i]);
|
netif_remove((struct netif*)(vtap->netif4));
|
||||||
netif_set_down(lwip_netifs[i]);
|
netif_set_down((struct netif*)(vtap->netif4));
|
||||||
netif_set_link_down(lwip_netifs[i]);
|
netif_set_link_down((struct netif*)(vtap->netif4));
|
||||||
delete lwip_netifs[i];
|
delete vtap->netif4;
|
||||||
}
|
vtap->netif4 = NULL;
|
||||||
}
|
}
|
||||||
lwip_netifs.clear();
|
if (vtap->netif6) {
|
||||||
}
|
netif_remove((struct netif*)(vtap->netif6));
|
||||||
|
netif_set_down((struct netif*)(vtap->netif6));
|
||||||
void lwip_driver_set_tap_interfaces_down(void *tapref)
|
netif_set_link_down((struct netif*)(vtap->netif6));
|
||||||
{
|
delete vtap->netif6;
|
||||||
int sz_i = lwip_netifs.size();
|
vtap->netif6 = NULL;
|
||||||
std::vector<struct netif*>::iterator iter;
|
|
||||||
for (iter = lwip_netifs.begin(); iter != lwip_netifs.end(); ) {
|
|
||||||
struct netif *lp = *(iter);
|
|
||||||
if (lp->state == tapref) {
|
|
||||||
netif_remove(lp);
|
|
||||||
netif_set_down(lp);
|
|
||||||
netif_set_link_down(lp);
|
|
||||||
iter = lwip_netifs.erase(iter);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
++iter;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -304,7 +241,7 @@ err_t lwip_eth_tx(struct netif *netif, struct pbuf *p)
|
|||||||
int len = totalLength - sizeof(struct eth_hdr);
|
int len = totalLength - sizeof(struct eth_hdr);
|
||||||
int proto = ZeroTier::Utils::ntoh((uint16_t)ethhdr->type);
|
int proto = ZeroTier::Utils::ntoh((uint16_t)ethhdr->type);
|
||||||
tap->_handler(tap->_arg, NULL, tap->_nwid, src_mac, dest_mac, proto, 0, data, len);
|
tap->_handler(tap->_arg, NULL, tap->_nwid, src_mac, dest_mac, proto, 0, data, len);
|
||||||
|
/*
|
||||||
if (ZT_MSG_TRANSFER == true) {
|
if (ZT_MSG_TRANSFER == true) {
|
||||||
char flagbuf[32];
|
char flagbuf[32];
|
||||||
memset(&flagbuf, 0, 32);
|
memset(&flagbuf, 0, 32);
|
||||||
@@ -318,6 +255,7 @@ err_t lwip_eth_tx(struct netif *netif, struct pbuf *p)
|
|||||||
DEBUG_TRANS("len=%5d dst=%s [%s TX <-- %s] proto=0x%04x %s", totalLength, macBuf, nodeBuf, tap->nodeId().c_str(),
|
DEBUG_TRANS("len=%5d dst=%s [%s TX <-- %s] proto=0x%04x %s", totalLength, macBuf, nodeBuf, tap->nodeId().c_str(),
|
||||||
ZeroTier::Utils::ntoh(ethhdr->type), flagbuf);
|
ZeroTier::Utils::ntoh(ethhdr->type), flagbuf);
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
return ERR_OK;
|
return ERR_OK;
|
||||||
@@ -326,23 +264,18 @@ err_t lwip_eth_tx(struct netif *netif, struct pbuf *p)
|
|||||||
void lwip_eth_rx(ZeroTier::VirtualTap *tap, const ZeroTier::MAC &from, const ZeroTier::MAC &to, unsigned int etherType,
|
void lwip_eth_rx(ZeroTier::VirtualTap *tap, const ZeroTier::MAC &from, const ZeroTier::MAC &to, unsigned int etherType,
|
||||||
const void *data, unsigned int len)
|
const void *data, unsigned int len)
|
||||||
{
|
{
|
||||||
if (!lwip_netifs.size()) {
|
|
||||||
DEBUG_ERROR("there are no netifs set up to handle this packet. ignoring.");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
struct pbuf *p,*q;
|
struct pbuf *p,*q;
|
||||||
struct eth_hdr ethhdr;
|
struct eth_hdr ethhdr;
|
||||||
from.copyTo(ethhdr.src.addr, 6);
|
from.copyTo(ethhdr.src.addr, 6);
|
||||||
to.copyTo(ethhdr.dest.addr, 6);
|
to.copyTo(ethhdr.dest.addr, 6);
|
||||||
ethhdr.type = ZeroTier::Utils::hton((uint16_t)etherType);
|
ethhdr.type = ZeroTier::Utils::hton((uint16_t)etherType);
|
||||||
|
/*
|
||||||
if (ZT_MSG_TRANSFER == true) {
|
if (ZT_MSG_TRANSFER == true) {
|
||||||
char flagbuf[32];
|
char flagbuf[32];
|
||||||
memset(&flagbuf, 0, 32);
|
memset(&flagbuf, 0, 32);
|
||||||
char macBuf[ZTS_MAC_ADDRSTRLEN], nodeBuf[ZTS_ID_LEN];
|
char macBuf[ZTS_MAC_ADDRSTRLEN], nodeBuf[ZTS_ID_LEN];
|
||||||
snprintf(macBuf, ZTS_MAC_ADDRSTRLEN, "%02x:%02x:%02x:%02x:%02x:%02x",
|
snprintf(macBuf, ZTS_MAC_ADDRSTRLEN, "%02x:%02x:%02x:%02x:%02x:%02x",
|
||||||
ethhdr.dest.addr[0], ethhdr.dest.addr[1], ethhdr.dest.addr[2],
|
ethhdr.dest.addr[0], ethhdr.dest.addr[1], ethhdr.dest.addr[2],
|
||||||
ethhdr.dest.addr[3], ethhdr.dest.addr[4], ethhdr.dest.addr[5]);
|
ethhdr.dest.addr[3], ethhdr.dest.addr[4], ethhdr.dest.addr[5]);
|
||||||
ZeroTier::MAC mac;
|
ZeroTier::MAC mac;
|
||||||
mac.setTo(ethhdr.src.addr, 6);
|
mac.setTo(ethhdr.src.addr, 6);
|
||||||
@@ -350,7 +283,20 @@ void lwip_eth_rx(ZeroTier::VirtualTap *tap, const ZeroTier::MAC &from, const Zer
|
|||||||
DEBUG_TRANS("len=%5d dst=%s [%s RX --> %s] proto=0x%04x %s", len, macBuf, nodeBuf, tap->nodeId().c_str(),
|
DEBUG_TRANS("len=%5d dst=%s [%s RX --> %s] proto=0x%04x %s", len, macBuf, nodeBuf, tap->nodeId().c_str(),
|
||||||
ZeroTier::Utils::ntoh(ethhdr.type), flagbuf);
|
ZeroTier::Utils::ntoh(ethhdr.type), flagbuf);
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
|
if (etherType == 0x0800 || etherType == 0x0806) { // ip4 or ARP
|
||||||
|
if (!tap->netif4) {
|
||||||
|
DEBUG_ERROR("dropped packet: no netif to accept this packet (etherType=%x) on this vtap (%p)", etherType, tap);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (etherType == 0x86DD) { // ip6
|
||||||
|
if (!tap->netif6) {
|
||||||
|
DEBUG_ERROR("dropped packet: no netif to accept this packet (etherType=%x) on this vtap (%p)", etherType, tap);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
p = pbuf_alloc(PBUF_RAW, len+sizeof(struct eth_hdr), PBUF_RAM);
|
p = pbuf_alloc(PBUF_RAW, len+sizeof(struct eth_hdr), PBUF_RAM);
|
||||||
if (!p) {
|
if (!p) {
|
||||||
DEBUG_ERROR("dropped packet: unable to allocate memory for pbuf");
|
DEBUG_ERROR("dropped packet: unable to allocate memory for pbuf");
|
||||||
@@ -374,6 +320,7 @@ void lwip_eth_rx(ZeroTier::VirtualTap *tap, const ZeroTier::MAC &from, const Zer
|
|||||||
memcpy(q->payload,dataptr,q->len);
|
memcpy(q->payload,dataptr,q->len);
|
||||||
dataptr += q->len;
|
dataptr += q->len;
|
||||||
}
|
}
|
||||||
|
|
||||||
_rx_input_lock_m.lock();
|
_rx_input_lock_m.lock();
|
||||||
if (rx_queue.size() >= LWIP_MAX_GUARDED_RX_BUF_SZ) {
|
if (rx_queue.size() >= LWIP_MAX_GUARDED_RX_BUF_SZ) {
|
||||||
DEBUG_INFO("dropped packet: rx_queue is full (>= %d)", LWIP_MAX_GUARDED_RX_BUF_SZ);
|
DEBUG_INFO("dropped packet: rx_queue is full (>= %d)", LWIP_MAX_GUARDED_RX_BUF_SZ);
|
||||||
@@ -382,7 +329,26 @@ void lwip_eth_rx(ZeroTier::VirtualTap *tap, const ZeroTier::MAC &from, const Zer
|
|||||||
p = NULL;
|
p = NULL;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
rx_queue.push(p);
|
|
||||||
|
// Construct a pre-sorted packet for lwIP packet feeder timeout
|
||||||
|
struct zts_sorted_packet *sp = new struct zts_sorted_packet;
|
||||||
|
sp->p = p;
|
||||||
|
sp->vtap=tap;
|
||||||
|
|
||||||
|
switch (etherType)
|
||||||
|
{
|
||||||
|
case 0x0800: // ip4
|
||||||
|
case 0x0806: // ARP
|
||||||
|
sp->n = (struct netif *)tap->netif4;
|
||||||
|
break;
|
||||||
|
case 0x86DD: // ip6
|
||||||
|
sp->n = (struct netif *)tap->netif6;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
DEBUG_ERROR("dropped packet: unhandled (etherType=%x)", etherType);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
rx_queue.push(sp);
|
||||||
_rx_input_lock_m.unlock();
|
_rx_input_lock_m.unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -406,6 +372,11 @@ static void print_netif_info(struct netif *netif) {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool lwip_is_netif_up(void *netif)
|
||||||
|
{
|
||||||
|
return netif_is_up((struct netif*)netif);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Called when the status of a netif changes:
|
* Called when the status of a netif changes:
|
||||||
* - Interface is up/down (ZTS_EVENT_NETIF_UP, ZTS_EVENT_NETIF_DOWN)
|
* - Interface is up/down (ZTS_EVENT_NETIF_UP, ZTS_EVENT_NETIF_DOWN)
|
||||||
@@ -413,21 +384,33 @@ static void print_netif_info(struct netif *netif) {
|
|||||||
*/
|
*/
|
||||||
static void netif_status_callback(struct netif *netif)
|
static void netif_status_callback(struct netif *netif)
|
||||||
{
|
{
|
||||||
|
// TODO: It appears that there may be a bug in lwIP's handling of callbacks for netifs
|
||||||
|
// configured to handle ipv4 traffic. For this reason a temporary measure of checking
|
||||||
|
// the status of the interfaces ourselves from the service is used.
|
||||||
if (!netif->state) {
|
if (!netif->state) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
ZeroTier::VirtualTap *tap = (ZeroTier::VirtualTap *)netif->state;
|
ZeroTier::VirtualTap *tap = (ZeroTier::VirtualTap *)netif->state;
|
||||||
// TODO: The following events may be triggered when there's simply a new
|
|
||||||
// address assignment, state will be kept in the virtual tap instead of
|
|
||||||
// at this lower level. This will allow us to filter out redundant events
|
|
||||||
if (netif->flags & NETIF_FLAG_UP) {
|
if (netif->flags & NETIF_FLAG_UP) {
|
||||||
_push_callback_event(tap->_nwid, ZTS_EVENT_NETIF_UP);
|
ZeroTier::VirtualTap *vtap = (ZeroTier::VirtualTap*)netif->state;
|
||||||
|
if (netif == vtap->netif6) {
|
||||||
|
// DEBUG_INFO("netif=%p, vtap->netif6=%p", netif, vtap->netif6);
|
||||||
|
_push_callback_event(tap->_nwid, ZTS_EVENT_NETIF_UP_IP6);
|
||||||
|
}
|
||||||
|
if (netif == vtap->netif4) {
|
||||||
|
// DEBUG_INFO("netif=%p, vtap->netif4=%p", netif, vtap->netif4);
|
||||||
|
_push_callback_event(tap->_nwid, ZTS_EVENT_NETIF_UP_IP4);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if (!(netif->flags & NETIF_FLAG_UP)) {
|
if (!(netif->flags & NETIF_FLAG_UP)) {
|
||||||
_push_callback_event(tap->_nwid, ZTS_EVENT_NETIF_DOWN);
|
if (netif->flags & NETIF_FLAG_MLD6) {
|
||||||
|
_push_callback_event(tap->_nwid, ZTS_EVENT_NETIF_DOWN_IP6);
|
||||||
|
} else {
|
||||||
|
_push_callback_event(tap->_nwid, ZTS_EVENT_NETIF_DOWN_IP4);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
// TODO: ZTS_EVENT_NETIF_NEW_ADDRESS
|
// TODO: ZTS_EVENT_NETIF_NEW_ADDRESS
|
||||||
print_netif_info(netif);
|
//print_netif_info(netif);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -440,7 +423,7 @@ static void netif_remove_callback(struct netif *netif)
|
|||||||
}
|
}
|
||||||
ZeroTier::VirtualTap *tap = (ZeroTier::VirtualTap *)netif->state;
|
ZeroTier::VirtualTap *tap = (ZeroTier::VirtualTap *)netif->state;
|
||||||
_push_callback_event(tap->_nwid, ZTS_EVENT_NETIF_REMOVED);
|
_push_callback_event(tap->_nwid, ZTS_EVENT_NETIF_REMOVED);
|
||||||
print_netif_info(netif);
|
//print_netif_info(netif);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -458,14 +441,14 @@ static void netif_link_callback(struct netif *netif)
|
|||||||
if (netif->flags & NETIF_FLAG_LINK_UP) {
|
if (netif->flags & NETIF_FLAG_LINK_UP) {
|
||||||
_push_callback_event(tap->_nwid, ZTS_EVENT_NETIF_LINK_DOWN);
|
_push_callback_event(tap->_nwid, ZTS_EVENT_NETIF_LINK_DOWN);
|
||||||
}
|
}
|
||||||
print_netif_info(netif);
|
//print_netif_info(netif);
|
||||||
}
|
}
|
||||||
|
|
||||||
static err_t netif_init_4(struct netif *netif)
|
static err_t netif_init_4(struct netif *netif)
|
||||||
{
|
{
|
||||||
netif->hwaddr_len = 6;
|
netif->hwaddr_len = 6;
|
||||||
netif->name[0] = 'e';
|
netif->name[0] = 'z';
|
||||||
netif->name[1] = '0'+lwip_netifs.size();
|
netif->name[1] = '4';
|
||||||
netif->linkoutput = lwip_eth_tx;
|
netif->linkoutput = lwip_eth_tx;
|
||||||
netif->output = etharp_output;
|
netif->output = etharp_output;
|
||||||
netif->mtu = ZT_MAX_MTU;
|
netif->mtu = ZT_MAX_MTU;
|
||||||
@@ -475,7 +458,6 @@ static err_t netif_init_4(struct netif *netif)
|
|||||||
| NETIF_FLAG_IGMP
|
| NETIF_FLAG_IGMP
|
||||||
| NETIF_FLAG_LINK_UP
|
| NETIF_FLAG_LINK_UP
|
||||||
| NETIF_FLAG_UP;
|
| NETIF_FLAG_UP;
|
||||||
_mac.copyTo(netif->hwaddr, netif->hwaddr_len);
|
|
||||||
netif->hwaddr_len = sizeof(netif->hwaddr);
|
netif->hwaddr_len = sizeof(netif->hwaddr);
|
||||||
return ERR_OK;
|
return ERR_OK;
|
||||||
}
|
}
|
||||||
@@ -483,8 +465,8 @@ static err_t netif_init_4(struct netif *netif)
|
|||||||
static err_t netif_init_6(struct netif *netif)
|
static err_t netif_init_6(struct netif *netif)
|
||||||
{
|
{
|
||||||
netif->hwaddr_len = 6;
|
netif->hwaddr_len = 6;
|
||||||
netif->name[0] = 'e';
|
netif->name[0] = 'z';
|
||||||
netif->name[1] = '0'+(char)lwip_netifs.size();
|
netif->name[1] = '6';
|
||||||
netif->linkoutput = lwip_eth_tx;
|
netif->linkoutput = lwip_eth_tx;
|
||||||
netif->output = etharp_output;
|
netif->output = etharp_output;
|
||||||
netif->output_ip6 = ethip6_output;
|
netif->output_ip6 = ethip6_output;
|
||||||
@@ -494,7 +476,6 @@ static err_t netif_init_6(struct netif *netif)
|
|||||||
| NETIF_FLAG_ETHERNET
|
| NETIF_FLAG_ETHERNET
|
||||||
| NETIF_FLAG_IGMP
|
| NETIF_FLAG_IGMP
|
||||||
| NETIF_FLAG_MLD6;
|
| NETIF_FLAG_MLD6;
|
||||||
_mac.copyTo(netif->hwaddr, netif->hwaddr_len);
|
|
||||||
netif->hwaddr_len = sizeof(netif->hwaddr);
|
netif->hwaddr_len = sizeof(netif->hwaddr);
|
||||||
return ERR_OK;
|
return ERR_OK;
|
||||||
}
|
}
|
||||||
@@ -503,10 +484,7 @@ void lwip_init_interface(void *tapref, const ZeroTier::MAC &mac, const ZeroTier:
|
|||||||
{
|
{
|
||||||
char ipbuf[INET6_ADDRSTRLEN];
|
char ipbuf[INET6_ADDRSTRLEN];
|
||||||
char macbuf[ZTS_MAC_ADDRSTRLEN];
|
char macbuf[ZTS_MAC_ADDRSTRLEN];
|
||||||
struct netif *lwipdev = new struct netif;
|
struct netif *n = new struct netif;
|
||||||
lwip_netifs.push_back(lwipdev);
|
|
||||||
|
|
||||||
_mac = mac;
|
|
||||||
|
|
||||||
if (ip.isV4()) {
|
if (ip.isV4()) {
|
||||||
char nmbuf[INET6_ADDRSTRLEN];
|
char nmbuf[INET6_ADDRSTRLEN];
|
||||||
@@ -514,37 +492,47 @@ void lwip_init_interface(void *tapref, const ZeroTier::MAC &mac, const ZeroTier:
|
|||||||
IP4_ADDR(&gw,127,0,0,1);
|
IP4_ADDR(&gw,127,0,0,1);
|
||||||
ipaddr.addr = *((u32_t *)ip.rawIpData());
|
ipaddr.addr = *((u32_t *)ip.rawIpData());
|
||||||
netmask.addr = *((u32_t *)ip.netmask().rawIpData());
|
netmask.addr = *((u32_t *)ip.netmask().rawIpData());
|
||||||
netif_add(lwipdev, &ipaddr, &netmask, &gw, NULL, netif_init_4, tcpip_input);
|
netif_add(n, &ipaddr, &netmask, &gw, NULL, netif_init_4, tcpip_input);
|
||||||
lwipdev->state = tapref;
|
n->state = tapref;
|
||||||
|
mac.copyTo(n->hwaddr, n->hwaddr_len);
|
||||||
snprintf(macbuf, ZTS_MAC_ADDRSTRLEN, "%02x:%02x:%02x:%02x:%02x:%02x",
|
snprintf(macbuf, ZTS_MAC_ADDRSTRLEN, "%02x:%02x:%02x:%02x:%02x:%02x",
|
||||||
lwipdev->hwaddr[0], lwipdev->hwaddr[1], lwipdev->hwaddr[2],
|
n->hwaddr[0], n->hwaddr[1], n->hwaddr[2],
|
||||||
lwipdev->hwaddr[3], lwipdev->hwaddr[4], lwipdev->hwaddr[5]);
|
n->hwaddr[3], n->hwaddr[4], n->hwaddr[5]);
|
||||||
DEBUG_INFO("initialized netif as [mac=%s, addr=%s, nm=%s]",
|
DEBUG_INFO("initialized netif as [mac=%s, addr=%s, nm=%s]",
|
||||||
macbuf, ip.toString(ipbuf), ip.netmask().toString(nmbuf));
|
macbuf, ip.toString(ipbuf), ip.netmask().toString(nmbuf));
|
||||||
|
netif_set_up(n);
|
||||||
|
netif_set_link_up(n);
|
||||||
|
ZeroTier::VirtualTap *vtap = (ZeroTier::VirtualTap*)tapref;
|
||||||
|
vtap->netif4 = (void*)n;
|
||||||
}
|
}
|
||||||
if (ip.isV6())
|
if (ip.isV6())
|
||||||
{
|
{
|
||||||
static ip6_addr_t ipaddr;
|
static ip6_addr_t ipaddr;
|
||||||
memcpy(&(ipaddr.addr), ip.rawIpData(), sizeof(ipaddr.addr));
|
memcpy(&(ipaddr.addr), ip.rawIpData(), sizeof(ipaddr.addr));
|
||||||
lwipdev->ip6_autoconfig_enabled = 1;
|
n->ip6_autoconfig_enabled = 1;
|
||||||
netif_add(lwipdev, NULL, NULL, NULL, NULL, netif_init_6, tcpip_input);
|
netif_add(n, NULL, NULL, NULL, NULL, netif_init_6, tcpip_input);
|
||||||
netif_ip6_addr_set(lwipdev, 1, &ipaddr);
|
netif_ip6_addr_set(n, 1, &ipaddr);
|
||||||
lwipdev->state = tapref;
|
n->state = tapref;
|
||||||
netif_create_ip6_linklocal_address(lwipdev, 1);
|
mac.copyTo(n->hwaddr, n->hwaddr_len);
|
||||||
netif_ip6_addr_set_state(lwipdev, 0, IP6_ADDR_TENTATIVE);
|
netif_create_ip6_linklocal_address(n, 1);
|
||||||
netif_ip6_addr_set_state(lwipdev, 1, IP6_ADDR_TENTATIVE);
|
netif_ip6_addr_set_state(n, 0, IP6_ADDR_TENTATIVE);
|
||||||
netif_set_default(lwipdev);
|
netif_ip6_addr_set_state(n, 1, IP6_ADDR_TENTATIVE);
|
||||||
netif_set_up(lwipdev);
|
netif_set_default(n);
|
||||||
netif_set_link_up(lwipdev);
|
netif_set_up(n);
|
||||||
|
netif_set_link_up(n);
|
||||||
snprintf(macbuf, ZTS_MAC_ADDRSTRLEN, "%02x:%02x:%02x:%02x:%02x:%02x",
|
snprintf(macbuf, ZTS_MAC_ADDRSTRLEN, "%02x:%02x:%02x:%02x:%02x:%02x",
|
||||||
lwipdev->hwaddr[0], lwipdev->hwaddr[1], lwipdev->hwaddr[2],
|
n->hwaddr[0], n->hwaddr[1], n->hwaddr[2],
|
||||||
lwipdev->hwaddr[3], lwipdev->hwaddr[4], lwipdev->hwaddr[5]);
|
n->hwaddr[3], n->hwaddr[4], n->hwaddr[5]);
|
||||||
DEBUG_INFO("initialized netif as [mac=%s, addr=%s]",
|
DEBUG_INFO("initialized netif as [mac=%s, addr=%s]",
|
||||||
macbuf, ip.toString(ipbuf));
|
macbuf, ip.toString(ipbuf));
|
||||||
|
ZeroTier::VirtualTap *vtap = (ZeroTier::VirtualTap*)tapref;
|
||||||
|
vtap->netif6 = (void*)n;
|
||||||
}
|
}
|
||||||
// Set netif callbacks, these will be used to inform decisions made
|
// Set netif callbacks, these will be used to inform decisions made
|
||||||
// by the higher level callback monitor thread
|
// by the higher level callback monitor thread
|
||||||
netif_set_status_callback(lwipdev, netif_status_callback);
|
netif_set_status_callback(n, netif_status_callback);
|
||||||
netif_set_remove_callback(lwipdev, netif_remove_callback);
|
netif_set_remove_callback(n, netif_remove_callback);
|
||||||
netif_set_link_callback(lwipdev, netif_link_callback);
|
netif_set_link_callback(n, netif_link_callback);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
} // namespace ZeroTier
|
||||||
Reference in New Issue
Block a user