Improved callback logic. Simplified lwip driver.

This commit is contained in:
Joseph Henry
2019-01-31 03:08:48 -08:00
parent d715ebd461
commit 292fcdda2c
12 changed files with 644 additions and 491 deletions

View File

@@ -33,6 +33,18 @@
#ifndef 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 //
// See ext/ZeroTierOne/include/ZeroTierOne.h //
@@ -40,25 +52,45 @@
typedef int zts_err_t;
#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_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_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_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_EVENT_NODE_ONLINE 0x01 // Node is online
#define ZTS_EVENT_NODE_OFFLINE 0x02 // Node is offline
#define ZTS_EVENT_NODE_DOWN 0x03 // Node is shutting down
#define ZTS_EVENT_NODE_IDENTITY_COLLISION 0x04 // Identity collision - check for duplicate instances
#define ZTS_EVENT_NODE_UNRECOVERABLE_ERROR 0x05 // Something is seriously wrong
#define ZTS_EVENT_NODE_NORMAL_TERMINATION 0x06 // Service thread has stopped
#define ZTS_EVENT_NETWORK_NOT_FOUND 0x07
#define ZTS_EVENT_NETWORK_CLIENT_TOO_OLD 0x08
#define ZTS_EVENT_NETWORK_REQUESTING_CONFIG 0x09
#define ZTS_EVENT_NETWORK_OK 0x0a
#define ZTS_EVENT_NETWORK_ACCESS_DENIED 0x0b
#define ZTS_EVENT_NETWORK_READY 0x0c
#define ZTS_EVENT_NETWORK_DOWN 0x0d
#define ZTS_EVENT_NONE 0x00000000
// Node-specific events
#define ZTS_EVENT_NODE_ONLINE 0x00000001 // Node is online
#define ZTS_EVENT_NODE_OFFLINE 0x00000002 // Node is offline
#define ZTS_EVENT_NODE_DOWN 0x00000004 // Node is shutting down
#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_NODE_NORMAL_TERMINATION 0x00000020 // Service thread has stopped
// Network-specific events
#define ZTS_EVENT_NETWORK_NOT_FOUND 0x00000080
#define ZTS_EVENT_NETWORK_CLIENT_TOO_OLD 0x00000100
#define ZTS_EVENT_NETWORK_REQUESTING_CONFIG 0x00000200
#define ZTS_EVENT_NETWORK_OK 0x00000400
#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 //

View File

@@ -39,6 +39,8 @@
#include <sys/socket.h>
#endif
namespace ZeroTier {
//////////////////////////////////////////////////////////////////////////////
// Subset of: ZeroTierOne.h //
// 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;
};
} // namespace ZeroTier
#endif // _H

View File

@@ -33,6 +33,10 @@
#ifndef LIBZT_SERVICE_CONTROLS_HPP
#define LIBZT_SERVICE_CONTROLS_HPP
#include "Constants.hpp"
namespace ZeroTier {
#ifdef _WIN32
#ifdef ADD_EXPORTS
#define ZT_SOCKET_API __declspec(dllexport)
@@ -45,8 +49,6 @@
#define ZTCALL
#endif
void api_sleep(int interval_ms);
//////////////////////////////////////////////////////////////////////////////
// ZeroTier Service Controls //
//////////////////////////////////////////////////////////////////////////////
@@ -386,4 +388,6 @@ void _hibernate_if_needed();
}
#endif
} // namespace ZeroTier
#endif // _H

View File

@@ -78,33 +78,9 @@ public:
~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);
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
* - Starts VirtualTap main thread ONLY if successful
@@ -178,6 +154,48 @@ public:
void phyOnUnixData(PhySocket *sock, void **uptr, void *data, ssize_t len);
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 //
//////////////////////////////////////////////////////////////////////////////

View File

@@ -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

View File

@@ -37,11 +37,31 @@
#include "lwip/err.h"
namespace ZeroTier {
class MAC;
class Mutex;
class VirtualTap;
struct InetAddress;
}
class MAC;
class Mutex;
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
@@ -76,15 +96,14 @@ void lwip_driver_init();
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
* stack. Unlike lwip_driver_shutdown(), the application can easily resume traffic processing
* by re-adding a virtual tap (and associated lwip netifs)
* @return
*/
void lwip_driver_set_tap_interfaces_down(void *tapref);
void lwip_driver_set_all_interfaces_down();
void lwip_dispose_of_netifs(void *tapref);
/**
* @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
* @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.
@@ -152,7 +171,9 @@ err_t lwip_eth_tx(struct netif *netif, struct pbuf *p);
* @param len Length of Ethernet frame
* @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);
} // namespace ZeroTier
#endif // _H

View File

@@ -53,7 +53,7 @@
*/
#if __ANDROID__
#define LWIP_PROVIDE_ERRNO 1
//#define SOCKLEN_T_DEFINED
#define SOCKLEN_T_DEFINED
#elif !defined(_MSC_VER)
#define LWIP_PROVIDE_ERRNO 1
#endif
@@ -61,7 +61,7 @@
/**
* Disable assertions
*/
#define LWIP_NOASSERT 0
#define LWIP_NOASSERT 1
/**
* Don't redefine byte-order functions if they're already available
@@ -103,6 +103,33 @@
*/
#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 ----------------------
------------------------------------------------------------------------------*/
@@ -243,7 +270,7 @@
* Your system should provide mutexes supporting priority inversion to use this.
*/
#if !defined LWIP_TCPIP_CORE_LOCKING || defined __DOXYGEN__
#define LWIP_TCPIP_CORE_LOCKING 0
#define LWIP_TCPIP_CORE_LOCKING 1
#endif
/**
@@ -350,7 +377,7 @@
* a lot of data that needs to be copied, this should be set high.
*/
#if !defined MEM_SIZE || defined __DOXYGEN__
#define MEM_SIZE 1600
#define MEM_SIZE 1024 * 1024
#endif
/**
@@ -464,7 +491,7 @@
* this should be set high.
*/
#if !defined MEMP_NUM_PBUF || defined __DOXYGEN__
#define MEMP_NUM_PBUF 16
#define MEMP_NUM_PBUF 1024
#endif
/**
@@ -472,7 +499,7 @@
* (requires the LWIP_RAW option)
*/
#if !defined MEMP_NUM_RAW_PCB || defined __DOXYGEN__
#define MEMP_NUM_RAW_PCB 4
#define MEMP_NUM_RAW_PCB 1024
#endif
/**
@@ -481,7 +508,7 @@
* (requires the LWIP_UDP option)
*/
#if !defined MEMP_NUM_UDP_PCB || defined __DOXYGEN__
#define MEMP_NUM_UDP_PCB 4
#define MEMP_NUM_UDP_PCB 1024
#endif
/**
@@ -489,7 +516,7 @@
* (requires the LWIP_TCP option)
*/
#if !defined MEMP_NUM_TCP_PCB || defined __DOXYGEN__
#define MEMP_NUM_TCP_PCB 5
#define MEMP_NUM_TCP_PCB 1024
#endif
/**
@@ -497,7 +524,7 @@
* (requires the LWIP_TCP option)
*/
#if !defined MEMP_NUM_TCP_PCB_LISTEN || defined __DOXYGEN__
#define MEMP_NUM_TCP_PCB_LISTEN 8
#define MEMP_NUM_TCP_PCB_LISTEN 1024
#endif
/**
@@ -505,7 +532,7 @@
* (requires the LWIP_TCP option)
*/
#if !defined MEMP_NUM_TCP_SEG || defined __DOXYGEN__
#define MEMP_NUM_TCP_SEG 16
#define MEMP_NUM_TCP_SEG 1024
#endif
/**
@@ -523,7 +550,7 @@
* reassembly (whole packets, not fragments!)
*/
#if !defined MEMP_NUM_REASSDATA || defined __DOXYGEN__
#define MEMP_NUM_REASSDATA 5
#define MEMP_NUM_REASSDATA 16
#endif
/**
@@ -585,7 +612,7 @@
* (only needed if you use the sequential API, like api_lib.c)
*/
#if !defined MEMP_NUM_NETCONN || defined __DOXYGEN__
#define MEMP_NUM_NETCONN 4
#define MEMP_NUM_NETCONN 256
#endif
/**
@@ -603,7 +630,7 @@
* (only needed if you use tcpip.c)
*/
#if !defined MEMP_NUM_TCPIP_MSG_API || defined __DOXYGEN__
#define MEMP_NUM_TCPIP_MSG_API 8
#define MEMP_NUM_TCPIP_MSG_API 64
#endif
/**
@@ -612,7 +639,7 @@
* (only needed if you use tcpip.c)
*/
#if !defined MEMP_NUM_TCPIP_MSG_INPKT || defined __DOXYGEN__
#define MEMP_NUM_TCPIP_MSG_INPKT 8
#define MEMP_NUM_TCPIP_MSG_INPKT 64
#endif
/**
@@ -635,7 +662,7 @@
* PBUF_POOL_SIZE: the number of buffers in the pbuf pool.
*/
#if !defined PBUF_POOL_SIZE || defined __DOXYGEN__
#define PBUF_POOL_SIZE 16
#define PBUF_POOL_SIZE 128
#endif
/** 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.
*/
#if !defined ARP_TABLE_SIZE || defined __DOXYGEN__
#define ARP_TABLE_SIZE 10
#define ARP_TABLE_SIZE 64
#endif
/** the time an ARP entry stays valid after its last update,
@@ -847,7 +874,7 @@
* (PBUF_POOL_SIZE > 2 * IP_REASS_MAX_PBUFS)!
*/
#if !defined IP_REASS_MAX_PBUFS || defined __DOXYGEN__
#define IP_REASS_MAX_PBUFS 10
#define IP_REASS_MAX_PBUFS 32
#endif
/**
@@ -1292,7 +1319,7 @@
* will be TCP_WND >> TCP_RCV_SCALE
*/
#if !defined TCP_WND || defined __DOXYGEN__
#define TCP_WND (4 * TCP_MSS)
#define TCP_WND 0xffff // (4 * TCP_MSS)
#endif
/**
@@ -1306,7 +1333,7 @@
* TCP_SYNMAXRTX: Maximum number of retransmissions of SYN segments.
*/
#if !defined TCP_SYNMAXRTX || defined __DOXYGEN__
#define TCP_SYNMAXRTX 6
#define TCP_SYNMAXRTX 12 // 6
#endif
/**
@@ -1367,7 +1394,7 @@
* To achieve good performance, this should be at least 2 * TCP_MSS.
*/
#if !defined TCP_SND_BUF || defined __DOXYGEN__
#define TCP_SND_BUF (2 * TCP_MSS)
#define TCP_SND_BUF 1024 * 32 // (2 * TCP_MSS)
#endif
/**
@@ -1375,7 +1402,7 @@
* as much as (2 * TCP_SND_BUF/TCP_MSS) for things to work.
*/
#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
/**
@@ -1689,7 +1716,7 @@
* if you have a tiny ARP table or if there never are concurrent connections.
*/
#if !defined LWIP_NETIF_HWADDRHINT || defined __DOXYGEN__
#define LWIP_NETIF_HWADDRHINT 0
#define LWIP_NETIF_HWADDRHINT 1
#endif
/**
@@ -2005,7 +2032,7 @@
* (only used if you use sockets.c)
*/
#if !defined LWIP_COMPAT_SOCKETS || defined __DOXYGEN__
#define LWIP_COMPAT_SOCKETS 1
#define LWIP_COMPAT_SOCKETS 0
#endif
/**
@@ -2014,7 +2041,7 @@
* names (read, write & close). (only used if you use sockets.c)
*/
#if !defined LWIP_POSIX_SOCKETS_IO_NAMES || defined __DOXYGEN__
#define LWIP_POSIX_SOCKETS_IO_NAMES 1
#define LWIP_POSIX_SOCKETS_IO_NAMES 0
#endif
/**
@@ -2152,7 +2179,7 @@
* LWIP_STATS==1: Enable statistics collection in lwip_stats.
*/
#if !defined LWIP_STATS || defined __DOXYGEN__
#define LWIP_STATS 1
#define LWIP_STATS 0
#endif
#if LWIP_STATS
@@ -2161,7 +2188,7 @@
* LWIP_STATS_DISPLAY==1: Compile in the statistics output functions.
*/
#if !defined LWIP_STATS_DISPLAY || defined __DOXYGEN__
#define LWIP_STATS_DISPLAY 1
#define LWIP_STATS_DISPLAY 0
#endif
/**
@@ -3572,4 +3599,4 @@
* @}
*/
#endif /* LWIP_HDR_OPT_H */
#endif /* LWIP_HDR_OPT_H */