Applied styling rules from .clang-format

This commit is contained in:
Joseph Henry
2021-04-17 23:46:21 -07:00
parent 8e7bcdb16a
commit a5121b1e3c
22 changed files with 3215 additions and 2231 deletions

View File

@@ -86,14 +86,15 @@
* *
*/ */
#include "ZeroTierSockets.h"
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include "ZeroTierSockets.h" struct Node {
Node() : online(false), joinedAtLeastOneNetwork(false), id(0)
struct Node {
{ }
Node() : online(false), joinedAtLeastOneNetwork(false), id(0) {}
bool online; bool online;
bool joinedAtLeastOneNetwork; bool joinedAtLeastOneNetwork;
uint64_t id; uint64_t id;
@@ -104,9 +105,9 @@ struct Node
to ensure timely receipt of future events. You should not call libzt API functions from to ensure timely receipt of future events. You should not call libzt API functions from
this function unless it's something trivial like zts_inet_ntop() or similar that has this function unless it's something trivial like zts_inet_ntop() or similar that has
no state-change implications. */ no state-change implications. */
void on_zts_event(void *msgPtr) void on_zts_event(void* msgPtr)
{ {
struct zts_callback_msg *msg = (struct zts_callback_msg *)msgPtr; struct zts_callback_msg* msg = (struct zts_callback_msg*)msgPtr;
// Node events // Node events
if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) { if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) {
@@ -115,25 +116,34 @@ void on_zts_event(void *msgPtr)
myNode.online = true; myNode.online = true;
} }
if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) { if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) {
printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, firewall, etc. What ports are you blocking?\n"); printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, "
"firewall, etc. What ports are you blocking?\n");
myNode.online = false; myNode.online = false;
} }
// Virtual network events // Virtual network events
if (msg->eventCode == ZTS_EVENT_NETWORK_NOT_FOUND) { if (msg->eventCode == ZTS_EVENT_NETWORK_NOT_FOUND) {
printf("ZTS_EVENT_NETWORK_NOT_FOUND --- Are you sure %llx is a valid network?\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_NOT_FOUND --- Are you sure %llx is a valid network?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) { if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) {
printf("ZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a few seconds...\n", msg->network->nwid); printf(
"ZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a "
"few seconds...\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) { if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) {
printf("ZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. Did you authorize the node yet?\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. "
"Did you authorize the node yet?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) {
printf("ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent over network %llx\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent "
"over network %llx\n",
msg->network->nwid);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) { if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) {
@@ -142,24 +152,25 @@ void on_zts_event(void *msgPtr)
// Network stack events // Network stack events
if (msg->eventCode == ZTS_EVENT_NETIF_UP) { if (msg->eventCode == ZTS_EVENT_NETIF_UP) {
printf("ZTS_EVENT_NETIF_UP --- network=%llx, mac=%llx, mtu=%d\n", printf(
msg->netif->nwid, "ZTS_EVENT_NETIF_UP --- network=%llx, mac=%llx, mtu=%d\n",
msg->netif->mac, msg->netif->nwid,
msg->netif->mtu); msg->netif->mac,
msg->netif->mtu);
} }
if (msg->eventCode == ZTS_EVENT_NETIF_DOWN) { if (msg->eventCode == ZTS_EVENT_NETIF_DOWN) {
printf("ZTS_EVENT_NETIF_DOWN --- network=%llx, mac=%llx\n", printf(
msg->netif->nwid, "ZTS_EVENT_NETIF_DOWN --- network=%llx, mac=%llx\n",
msg->netif->mac); msg->netif->nwid,
msg->netif->mac);
} }
// Address events // Address events
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_NEW_IP6 --- Join %llx and ping me at %s\n", printf("ZTS_EVENT_ADDR_NEW_IP6 --- Join %llx and ping me at %s\n", msg->addr->nwid, ipstr);
msg->addr->nwid, ipstr);
} }
// Peer events // Peer events
@@ -170,19 +181,23 @@ void on_zts_event(void *msgPtr)
return; return;
} }
if (msg->eventCode == ZTS_EVENT_PEER_DIRECT) { if (msg->eventCode == ZTS_EVENT_PEER_DIRECT) {
printf("ZTS_EVENT_PEER_DIRECT --- A direct path is known for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_DIRECT --- A direct path is known for node=%llx\n",
msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_RELAY) { if (msg->eventCode == ZTS_EVENT_PEER_RELAY) {
printf("ZTS_EVENT_PEER_RELAY --- No direct path to node=%llx\n", msg->peer->address); printf("ZTS_EVENT_PEER_RELAY --- No direct path to node=%llx\n", msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) {
printf("ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered for "
"node=%llx\n",
msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) {
printf("ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died for node=%llx\n",
msg->peer->address);
} }
} }
} }
@@ -212,46 +227,55 @@ be taken to avoid exposing vulnerable services or sharing unwanted files or othe
*/ */
int main(int argc, char **argv) int main(int argc, char** argv)
{ {
if (argc != 5) { if (argc != 5) {
printf("\nlibzt example\n"); printf("\nlibzt example\n");
printf("adhoc <config_file_path> <adhocStartPort> <adhocEndPort> <ztServicePort>\n"); printf("adhoc <config_file_path> <adhocStartPort> <adhocEndPort> <ztServicePort>\n");
exit(0); exit(0);
} }
int adhocStartPort = atoi(argv[2]); // Start of port range your application will use int adhocStartPort = atoi(argv[2]); // Start of port range your application will use
int adhocEndPort = atoi(argv[3]); // End of port range your application will use int adhocEndPort = atoi(argv[3]); // End of port range your application will use
int ztServicePort = atoi(argv[4]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994) int ztServicePort = atoi(
argv[4]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994)
uint64_t adhoc_nwid = zts_generate_adhoc_nwid_from_range(adhocStartPort, adhocEndPort); uint64_t adhoc_nwid = zts_generate_adhoc_nwid_from_range(adhocStartPort, adhocEndPort);
int err = ZTS_ERR_OK; int err = ZTS_ERR_OK;
// If disabled: (network) details will NOT be written to or read from (networks.d/). It may take slightly longer to start the node // If disabled: (network) details will NOT be written to or read from (networks.d/). It may take
// slightly longer to start the node
zts_allow_network_caching(1); zts_allow_network_caching(1);
// If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take slightly longer to contact a remote peer // If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take
// slightly longer to contact a remote peer
zts_allow_peer_caching(1); zts_allow_peer_caching(1);
// If disabled: Settings will NOT be read from local.conf // If disabled: Settings will NOT be read from local.conf
zts_allow_local_conf(1); zts_allow_local_conf(1);
if((err = zts_start(argv[1], &on_zts_event, ztServicePort)) != ZTS_ERR_OK) { if ((err = zts_start(argv[1], &on_zts_event, ztServicePort)) != ZTS_ERR_OK) {
printf("Unable to start service, error = %d. Exiting.\n", err); printf("Unable to start service, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Waiting for node to come online...\n"); printf("Waiting for node to come online...\n");
while (!myNode.online) { zts_delay_ms(50); } while (! myNode.online) {
zts_delay_ms(50);
}
printf("This node's identity is stored in %s\n", argv[1]); printf("This node's identity is stored in %s\n", argv[1]);
if((err = zts_join(adhoc_nwid)) != ZTS_ERR_OK) { if ((err = zts_join(adhoc_nwid)) != ZTS_ERR_OK) {
printf("Unable to join network, error = %d. Exiting.\n", err); printf("Unable to join network, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Joining network %llx\n", adhoc_nwid); printf("Joining network %llx\n", adhoc_nwid);
while (!myNode.joinedAtLeastOneNetwork) { zts_delay_ms(50); } while (! myNode.joinedAtLeastOneNetwork) {
zts_delay_ms(50);
}
// Idle and just show callback events, stack statistics, etc // Idle and just show callback events, stack statistics, etc
printf("Node will now idle...\n"); printf("Node will now idle...\n");
while (true) { zts_delay_ms(1000); } while (true) {
zts_delay_ms(1000);
}
// Shut down service and stack threads // Shut down service and stack threads

View File

@@ -1,17 +1,16 @@
#include "ZeroTierSockets.h"
#include <iomanip>
#include <iostream>
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include <string> #include <string>
#include <iomanip>
#include <iostream>
#include "ZeroTierSockets.h"
// For optional JSON parsing // For optional JSON parsing
#include "../ext/ZeroTierOne/ext/json/json.hpp" #include "../ext/ZeroTierOne/ext/json/json.hpp"
void process_response(char *response, int http_response_code) void process_response(char* response, int http_response_code)
{ {
if (http_response_code == 0) { if (http_response_code == 0) {
// Request failed at library level, do nothing. There would be no HTTP code at this point. // Request failed at library level, do nothing. There would be no HTTP code at this point.
@@ -23,22 +22,22 @@ void process_response(char *response, int http_response_code)
return; return;
} }
nlohmann::json res = nlohmann::json::parse(response); nlohmann::json res = nlohmann::json::parse(response);
if (!res.is_object()) { if (! res.is_object()) {
fprintf(stderr, "Unable to parse (root element is not a JSON object)"); fprintf(stderr, "Unable to parse (root element is not a JSON object)");
} }
// Pretty print JSON blob // Pretty print JSON blob
std::cout << std::setw(4) << res << std::endl; std::cout << std::setw(4) << res << std::endl;
} }
int main(int argc, char **argv) int main(int argc, char** argv)
{ {
if (argc != 3) { if (argc != 3) {
printf("\nlibzt example central API client\n"); printf("\nlibzt example central API client\n");
printf("centralapi <central_url> <api_token>\n"); printf("centralapi <central_url> <api_token>\n");
exit(0); exit(0);
} }
std::string central_url = argv[1]; // API endpoint std::string central_url = argv[1]; // API endpoint
std::string api_token = argv[2]; // User token (generate at my.zerotier.com) std::string api_token = argv[2]; // User token (generate at my.zerotier.com)
/** /**
* This example demonstrates how to use the ZeroTier Central API to: * This example demonstrates how to use the ZeroTier Central API to:
@@ -67,12 +66,17 @@ int main(int argc, char **argv)
// Provide URL to Central API server and user API token generated at https://my.zerotier.com // Provide URL to Central API server and user API token generated at https://my.zerotier.com
printf("Initializing Central API client...\n"); printf("Initializing Central API client...\n");
if ((err = zts_central_init(central_url.c_str(), api_token.c_str(), rbuf, ZTS_CENTRAL_RESP_BUF_DEFAULT_SZ)) != ZTS_ERR_OK) { if ((err = zts_central_init(
central_url.c_str(),
api_token.c_str(),
rbuf,
ZTS_CENTRAL_RESP_BUF_DEFAULT_SZ))
!= ZTS_ERR_OK) {
fprintf(stderr, "Error while initializing client's Central API parameters\n"); fprintf(stderr, "Error while initializing client's Central API parameters\n");
return 0; return 0;
} }
zts_central_set_verbose(false); // (optiona) Turn on reporting from libcurl zts_central_set_verbose(false); // (optiona) Turn on reporting from libcurl
zts_central_set_access_mode(ZTS_CENTRAL_READ | ZTS_CENTRAL_WRITE); zts_central_set_access_mode(ZTS_CENTRAL_READ | ZTS_CENTRAL_WRITE);
int http_res_code = 0; int http_res_code = 0;
@@ -81,7 +85,8 @@ int main(int argc, char **argv)
printf("Requesting Central API server status (/api/status):\n"); printf("Requesting Central API server status (/api/status):\n");
if ((err = zts_central_get_status(&http_res_code)) != ZTS_ERR_OK) { if ((err = zts_central_get_status(&http_res_code)) != ZTS_ERR_OK) {
fprintf(stderr, "Error (%d) making the request.\n", err); fprintf(stderr, "Error (%d) making the request.\n", err);
} else { }
else {
process_response(rbuf, http_res_code); process_response(rbuf, http_res_code);
} }
// Get network config // Get network config
@@ -89,15 +94,18 @@ int main(int argc, char **argv)
printf("Requesting network config: /api/network/%llx\n", nwid); printf("Requesting network config: /api/network/%llx\n", nwid);
if ((err = zts_central_get_network(&http_res_code, nwid)) != ZTS_ERR_OK) { if ((err = zts_central_get_network(&http_res_code, nwid)) != ZTS_ERR_OK) {
fprintf(stderr, "Error (%d) making the request.\n", err); fprintf(stderr, "Error (%d) making the request.\n", err);
} else { }
else {
process_response(rbuf, http_res_code); process_response(rbuf, http_res_code);
} }
// Authorize a node on a network // Authorize a node on a network
int64_t nodeid = 0x9934343434; int64_t nodeid = 0x9934343434;
printf("Authorizing: /api/network/%llx/member/%llx\n", nwid, nodeid); printf("Authorizing: /api/network/%llx/member/%llx\n", nwid, nodeid);
if ((err = zts_central_set_node_auth(&http_res_code, nwid, nodeid, ZTS_CENTRAL_NODE_AUTH_TRUE)) != ZTS_ERR_OK) { if ((err = zts_central_set_node_auth(&http_res_code, nwid, nodeid, ZTS_CENTRAL_NODE_AUTH_TRUE))
!= ZTS_ERR_OK) {
fprintf(stderr, "Error (%d) making the request.\n", err); fprintf(stderr, "Error (%d) making the request.\n", err);
} else { }
else {
process_response(rbuf, http_res_code); process_response(rbuf, http_res_code);
} }

View File

@@ -2,16 +2,17 @@
* libzt API example * libzt API example
*/ */
#include "ZeroTierSockets.h"
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include <string> #include <string>
#include "ZeroTierSockets.h" struct Node {
Node() : online(false), joinedAtLeastOneNetwork(false), id(0)
struct Node {
{ }
Node() : online(false), joinedAtLeastOneNetwork(false), id(0) {}
bool online; bool online;
bool joinedAtLeastOneNetwork; bool joinedAtLeastOneNetwork;
uint64_t id; uint64_t id;
@@ -22,9 +23,9 @@ struct Node
to ensure timely receipt of future events. You should not call libzt API functions from to ensure timely receipt of future events. You should not call libzt API functions from
this function unless it's something trivial like zts_inet_ntop() or similar that has this function unless it's something trivial like zts_inet_ntop() or similar that has
no state-change implications. */ no state-change implications. */
void on_zts_event(void *msgPtr) void on_zts_event(void* msgPtr)
{ {
struct zts_callback_msg *msg = (struct zts_callback_msg *)msgPtr; struct zts_callback_msg* msg = (struct zts_callback_msg*)msgPtr;
// Node events // Node events
if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) { if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) {
@@ -33,7 +34,8 @@ void on_zts_event(void *msgPtr)
myNode.online = true; myNode.online = true;
} }
if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) { if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) {
printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, firewall, etc. What ports are you blocking?\n"); printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, "
"firewall, etc. What ports are you blocking?\n");
myNode.online = false; myNode.online = false;
} }
if (msg->eventCode == ZTS_EVENT_NODE_NORMAL_TERMINATION) { if (msg->eventCode == ZTS_EVENT_NODE_NORMAL_TERMINATION) {
@@ -42,24 +44,34 @@ void on_zts_event(void *msgPtr)
// Virtual network events // Virtual network events
if (msg->eventCode == ZTS_EVENT_NETWORK_NOT_FOUND) { if (msg->eventCode == ZTS_EVENT_NETWORK_NOT_FOUND) {
printf("ZTS_EVENT_NETWORK_NOT_FOUND --- Are you sure %llx is a valid network?\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_NOT_FOUND --- Are you sure %llx is a valid network?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) { if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) {
printf("ZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a few seconds...\n", msg->network->nwid); printf(
"ZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a "
"few seconds...\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) { if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) {
printf("ZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. Did you authorize the node yet?\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. "
"Did you authorize the node yet?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP4) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP4) {
printf("ZTS_EVENT_NETWORK_READY_IP4 --- Network config received. IPv4 traffic can now be sent over network %llx\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_READY_IP4 --- Network config received. IPv4 traffic can now be sent "
"over network %llx\n",
msg->network->nwid);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) {
printf("ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent over network %llx\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent "
"over network %llx\n",
msg->network->nwid);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) { if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) {
@@ -69,31 +81,41 @@ void on_zts_event(void *msgPtr)
// Address events // Address events
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP4) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP4) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(msg->addr->addr); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_NEW_IP4 --- This node's virtual address on network %llx is %s\n", printf(
msg->addr->nwid, ipstr); "ZTS_EVENT_ADDR_NEW_IP4 --- This node's virtual address on network %llx is %s\n",
msg->addr->nwid,
ipstr);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_NEW_IP6 --- This node's virtual address on network %llx is %s\n", printf(
msg->addr->nwid, ipstr); "ZTS_EVENT_ADDR_NEW_IP6 --- This node's virtual address on network %llx is %s\n",
msg->addr->nwid,
ipstr);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP4) { if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP4) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(msg->addr->addr); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_REMOVED_IP4 --- The virtual address %s for this node on network %llx has been removed.\n", printf(
ipstr, msg->addr->nwid); "ZTS_EVENT_ADDR_REMOVED_IP4 --- The virtual address %s for this node on network %llx "
"has been removed.\n",
ipstr,
msg->addr->nwid);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP6) { if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_REMOVED_IP6 --- The virtual address %s for this node on network %llx has been removed.\n", printf(
ipstr, msg->addr->nwid); "ZTS_EVENT_ADDR_REMOVED_IP6 --- The virtual address %s for this node on network %llx "
"has been removed.\n",
ipstr,
msg->addr->nwid);
} }
// Peer events // Peer events
if (msg->peer) { if (msg->peer) {
@@ -103,19 +125,23 @@ void on_zts_event(void *msgPtr)
return; return;
} }
if (msg->eventCode == ZTS_EVENT_PEER_DIRECT) { if (msg->eventCode == ZTS_EVENT_PEER_DIRECT) {
printf("ZTS_EVENT_PEER_DIRECT --- A direct path is known for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_DIRECT --- A direct path is known for node=%llx\n",
msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_RELAY) { if (msg->eventCode == ZTS_EVENT_PEER_RELAY) {
printf("ZTS_EVENT_PEER_RELAY --- No direct path to node=%llx\n", msg->peer->address); printf("ZTS_EVENT_PEER_RELAY --- No direct path to node=%llx\n", msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) {
printf("ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered for "
"node=%llx\n",
msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) {
printf("ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died for node=%llx\n",
msg->peer->address);
} }
} }
} }
@@ -202,17 +228,18 @@ void on_zts_event(void *msgPtr)
* *
*/ */
int main(int argc, char **argv) int main(int argc, char** argv)
{ {
if (argc != 6) { if (argc != 6) {
printf("\nlibzt example client\n"); printf("\nlibzt example client\n");
printf("client <config_file_path> <nwid> <remoteAddr> <remotePort> <ztServicePort>\n"); printf("client <config_file_path> <nwid> <remoteAddr> <remotePort> <ztServicePort>\n");
exit(0); exit(0);
} }
uint64_t nwid = strtoull(argv[2],NULL,16); // Network ID to join uint64_t nwid = strtoull(argv[2], NULL, 16); // Network ID to join
std::string remoteAddr = argv[3]; // Remote application's virtual ZT address std::string remoteAddr = argv[3]; // Remote application's virtual ZT address
int remotePort = atoi(argv[4]); // Port the application will try to connect to the server on int remotePort = atoi(argv[4]); // Port the application will try to connect to the server on
int ztServicePort = atoi(argv[5]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994) int ztServicePort = atoi(
argv[5]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994)
struct zts_sockaddr_in in4; struct zts_sockaddr_in in4;
in4.sin_port = htons(remotePort); in4.sin_port = htons(remotePort);
@@ -227,33 +254,39 @@ int main(int argc, char **argv)
int err = ZTS_ERR_OK; int err = ZTS_ERR_OK;
// If disabled: (network) details will NOT be written to or read from (networks.d/). It may take slightly longer to start the node // If disabled: (network) details will NOT be written to or read from (networks.d/). It may take
// slightly longer to start the node
zts_allow_network_caching(1); zts_allow_network_caching(1);
// If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take slightly longer to contact a remote peer // If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take
// slightly longer to contact a remote peer
zts_allow_peer_caching(1); zts_allow_peer_caching(1);
// If disabled: Settings will NOT be read from local.conf // If disabled: Settings will NOT be read from local.conf
zts_allow_local_conf(1); zts_allow_local_conf(1);
if((err = zts_start(argv[1], &on_zts_event, ztServicePort)) != ZTS_ERR_OK) { if ((err = zts_start(argv[1], &on_zts_event, ztServicePort)) != ZTS_ERR_OK) {
printf("Unable to start service, error = %d. Exiting.\n", err); printf("Unable to start service, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Waiting for node to come online...\n"); printf("Waiting for node to come online...\n");
while (!myNode.online) { zts_delay_ms(50); } while (! myNode.online) {
zts_delay_ms(50);
}
printf("This node's identity is stored in %s\n", argv[1]); printf("This node's identity is stored in %s\n", argv[1]);
if((err = zts_join(nwid)) != ZTS_ERR_OK) { if ((err = zts_join(nwid)) != ZTS_ERR_OK) {
printf("Unable to join network, error = %d. Exiting.\n", err); printf("Unable to join network, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Joining network %llx\n", nwid); printf("Joining network %llx\n", nwid);
printf("Don't forget to authorize this device in my.zerotier.com or the web API!\n"); printf("Don't forget to authorize this device in my.zerotier.com or the web API!\n");
while (!myNode.joinedAtLeastOneNetwork) { zts_delay_ms(50); } while (! myNode.joinedAtLeastOneNetwork) {
zts_delay_ms(50);
}
// Socket-like API example // Socket-like API example
char *msgStr = (char*)"Welcome to the machine"; char* msgStr = (char*)"Welcome to the machine";
int bytes=0, fd; int bytes = 0, fd;
char recvBuf[128]; char recvBuf[128];
memset(recvBuf, 0, sizeof(recvBuf)); memset(recvBuf, 0, sizeof(recvBuf));
@@ -264,13 +297,19 @@ int main(int argc, char **argv)
// Retries are often required since ZT uses transport-triggered links (explained above) // Retries are often required since ZT uses transport-triggered links (explained above)
for (;;) { for (;;) {
printf("Connecting to remote host...\n"); printf("Connecting to remote host...\n");
if ((err = zts_connect(fd, (const struct zts_sockaddr *)&in4, sizeof(in4))) < 0) { if ((err = zts_connect(fd, (const struct zts_sockaddr*)&in4, sizeof(in4))) < 0) {
printf("Error connecting to remote host (fd=%d, ret=%d, zts_errno=%d). Trying again.\n", printf(
fd, err, zts_errno); "Error connecting to remote host (fd=%d, ret=%d, zts_errno=%d). Trying again.\n",
fd,
err,
zts_errno);
zts_close(fd); zts_close(fd);
printf("Creating socket...\n"); printf("Creating socket...\n");
if ((fd = zts_socket(ZTS_AF_INET, ZTS_SOCK_STREAM, 0)) < 0) { if ((fd = zts_socket(ZTS_AF_INET, ZTS_SOCK_STREAM, 0)) < 0) {
printf("Error creating ZeroTier socket (fd=%d, zts_errno=%d). Exiting.\n", fd, zts_errno); printf(
"Error creating ZeroTier socket (fd=%d, zts_errno=%d). Exiting.\n",
fd,
zts_errno);
exit(1); exit(1);
} }
zts_delay_ms(250); zts_delay_ms(250);
@@ -281,14 +320,22 @@ int main(int argc, char **argv)
} }
} }
printf("Sending message string to server...\n"); printf("Sending message string to server...\n");
if((bytes = zts_write(fd, msgStr, strlen(msgStr))) < 0) { if ((bytes = zts_write(fd, msgStr, strlen(msgStr))) < 0) {
printf("Error writing to socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n", fd, bytes, zts_errno); printf(
"Error writing to socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
bytes,
zts_errno);
exit(1); exit(1);
} }
printf("Sent %d bytes: %s\n", bytes, msgStr); printf("Sent %d bytes: %s\n", bytes, msgStr);
printf("Reading message string from server...\n"); printf("Reading message string from server...\n");
if((bytes = zts_read(fd, recvBuf, sizeof(recvBuf))) < 0) { if ((bytes = zts_read(fd, recvBuf, sizeof(recvBuf))) < 0) {
printf("Error writing to socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n", fd, bytes, zts_errno); printf(
"Error writing to socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
bytes,
zts_errno);
exit(1); exit(1);
} }
printf("Read %d bytes: %s\n", bytes, recvBuf); printf("Read %d bytes: %s\n", bytes, recvBuf);

View File

@@ -86,55 +86,64 @@
* *
*/ */
#include "ZeroTierSockets.h"
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string> #include <string>
#include "ZeroTierSockets.h"
#ifdef __WINDOWS__ #ifdef __WINDOWS__
#include "winsock.h" #include "winsock.h"
#endif #endif
struct Node struct Node {
{ Node() : online(false), joinedAtLeastOneNetwork(false), id(0)
Node() : online(false), joinedAtLeastOneNetwork(false), id(0) {} {
}
bool online; bool online;
bool joinedAtLeastOneNetwork; bool joinedAtLeastOneNetwork;
uint64_t id; uint64_t id;
// etc // etc
} myNode; } myNode;
void printNodeDetails(const char *msgStr, struct zts_node_details *d) void printNodeDetails(const char* msgStr, struct zts_node_details* d)
{ {
printf("\n%s\n", msgStr); printf("\n%s\n", msgStr);
printf("\t- id : %llx\n", d->address); printf("\t- id : %llx\n", d->address);
printf("\t- version : %d.%d.%d\n", d->versionMajor, d->versionMinor, d->versionRev); printf(
"\t- version : %d.%d.%d\n",
d->versionMajor,
d->versionMinor,
d->versionRev);
printf("\t- primaryPort : %d\n", d->primaryPort); printf("\t- primaryPort : %d\n", d->primaryPort);
printf("\t- secondaryPort : %d\n", d->secondaryPort); printf("\t- secondaryPort : %d\n", d->secondaryPort);
} }
void printPeerDetails(const char *msgStr, struct zts_peer_details *d) void printPeerDetails(const char* msgStr, struct zts_peer_details* d)
{ {
printf("\n%s\n", msgStr); printf("\n%s\n", msgStr);
printf("\t- peer : %llx\n", d->address); printf("\t- peer : %llx\n", d->address);
printf("\t- role : %llx\n", d->role); printf("\t- role : %llx\n", d->role);
printf("\t- latency : %d\n", d->latency); printf("\t- latency : %d\n", d->latency);
printf("\t- version : %d.%d.%d\n", d->versionMajor, d->versionMinor, d->versionRev); printf(
"\t- version : %d.%d.%d\n",
d->versionMajor,
d->versionMinor,
d->versionRev);
printf("\t- pathCount : %d\n", d->pathCount); printf("\t- pathCount : %d\n", d->pathCount);
printf("\t- paths:\n"); printf("\t- paths:\n");
// Print all known paths for each peer // Print all known paths for each peer
for (unsigned int j=0; j<d->pathCount; j++) { for (unsigned int j = 0; j < d->pathCount; j++) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
int port = 0; int port = 0;
struct zts_sockaddr *sa = (struct zts_sockaddr *)&(d->paths[j].address); struct zts_sockaddr* sa = (struct zts_sockaddr*)&(d->paths[j].address);
if (sa->sa_family == ZTS_AF_INET) { if (sa->sa_family == ZTS_AF_INET) {
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)sa; struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)sa;
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
port = ntohs(in4->sin_port); port = ntohs(in4->sin_port);
} }
if (sa->sa_family == ZTS_AF_INET6) { if (sa->sa_family == ZTS_AF_INET6) {
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)sa; struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)sa;
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
} }
printf("\t - %15s : %6d\n", ipstr, port); printf("\t - %15s : %6d\n", ipstr, port);
@@ -142,7 +151,7 @@ void printPeerDetails(const char *msgStr, struct zts_peer_details *d)
printf("\n"); printf("\n");
} }
void printNetworkDetails(const char *msgStr, struct zts_network_details *d) void printNetworkDetails(const char* msgStr, struct zts_network_details* d)
{ {
printf("\n%s\n", msgStr); printf("\n%s\n", msgStr);
printf("\t- nwid : %llx\n", d->nwid); printf("\t- nwid : %llx\n", d->nwid);
@@ -159,54 +168,57 @@ void printNetworkDetails(const char *msgStr, struct zts_network_details *d)
printf("\t- routeCount : %d\n", d->routeCount); printf("\t- routeCount : %d\n", d->routeCount);
printf("\t- multicastSubscriptionCount : %d\n", d->multicastSubscriptionCount); printf("\t- multicastSubscriptionCount : %d\n", d->multicastSubscriptionCount);
for (int i=0; i<d->multicastSubscriptionCount; i++) { for (int i = 0; i < d->multicastSubscriptionCount; i++) {
printf("\t - mac=%llx, adi=%x\n", d->multicastSubscriptions[i].mac, d->multicastSubscriptions[i].adi); printf(
"\t - mac=%llx, adi=%x\n",
d->multicastSubscriptions[i].mac,
d->multicastSubscriptions[i].adi);
} }
printf("\t- addresses:\n"); printf("\t- addresses:\n");
for (int i=0; i<d->assignedAddressCount; i++) { for (int i = 0; i < d->assignedAddressCount; i++) {
if (d->assignedAddresses[i].ss_family == ZTS_AF_INET) { if (d->assignedAddresses[i].ss_family == ZTS_AF_INET) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(d->assignedAddresses[i]); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(d->assignedAddresses[i]);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("\t - %s\n",ipstr); printf("\t - %s\n", ipstr);
} }
if (d->assignedAddresses[i].ss_family == ZTS_AF_INET6) { if (d->assignedAddresses[i].ss_family == ZTS_AF_INET6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(d->assignedAddresses[i]); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(d->assignedAddresses[i]);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("\t - %s\n",ipstr); printf("\t - %s\n", ipstr);
} }
} }
printf("\t- routes:\n"); printf("\t- routes:\n");
for (int i=0; i<d->routeCount; i++) { for (int i = 0; i < d->routeCount; i++) {
if (d->routes[i].target.ss_family == ZTS_AF_INET) { if (d->routes[i].target.ss_family == ZTS_AF_INET) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(d->routes[i].target); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(d->routes[i].target);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("\t - target : %s\n",ipstr); printf("\t - target : %s\n", ipstr);
in4 = (struct zts_sockaddr_in*)&(d->routes[i].via); in4 = (struct zts_sockaddr_in*)&(d->routes[i].via);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("\t - via : %s\n",ipstr); printf("\t - via : %s\n", ipstr);
} }
if (d->routes[i].target.ss_family == ZTS_AF_INET6) { if (d->routes[i].target.ss_family == ZTS_AF_INET6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(d->routes[i].target); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(d->routes[i].target);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("\t - target : %s\n",ipstr); printf("\t - target : %s\n", ipstr);
in6 = (struct zts_sockaddr_in6*)&(d->routes[i].via); in6 = (struct zts_sockaddr_in6*)&(d->routes[i].via);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("\t - via : %s\n",ipstr); printf("\t - via : %s\n", ipstr);
} }
printf("\t - flags : %d\n", d->routes[i].flags); printf("\t - flags : %d\n", d->routes[i].flags);
printf("\t - metric : %d\n", d->routes[i].metric); printf("\t - metric : %d\n", d->routes[i].metric);
} }
} }
void printNetifDetails(const char *msgStr, struct zts_netif_details *d) void printNetifDetails(const char* msgStr, struct zts_netif_details* d)
{ {
printf("\n%s\n", msgStr); printf("\n%s\n", msgStr);
printf("\t- nwid : %llx\n", d->nwid); printf("\t- nwid : %llx\n", d->nwid);
@@ -218,9 +230,9 @@ void printNetifDetails(const char *msgStr, struct zts_netif_details *d)
to ensure timely receipt of future events. You should not call libzt API functions from to ensure timely receipt of future events. You should not call libzt API functions from
this function unless it's something trivial like zts_inet_ntop() or similar that has this function unless it's something trivial like zts_inet_ntop() or similar that has
no state-change implications. */ no state-change implications. */
void on_zts_event(void *msgPtr) void on_zts_event(void* msgPtr)
{ {
struct zts_callback_msg *msg = (struct zts_callback_msg *)msgPtr; struct zts_callback_msg* msg = (struct zts_callback_msg*)msgPtr;
printf("eventCode=%d\n", msg->eventCode); printf("eventCode=%d\n", msg->eventCode);
// Node events // Node events
@@ -230,33 +242,44 @@ void on_zts_event(void *msgPtr)
myNode.online = true; myNode.online = true;
} }
if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) { if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) {
printf("\nZTS_EVENT_NODE_OFFLINE --- Check your Internet connection, router, firewall, etc. What ports are you blocking?\n"); printf("\nZTS_EVENT_NODE_OFFLINE --- Check your Internet connection, router, firewall, "
"etc. What ports are you blocking?\n");
myNode.online = false; myNode.online = false;
} }
if (msg->eventCode == ZTS_EVENT_NODE_NORMAL_TERMINATION) { if (msg->eventCode == ZTS_EVENT_NODE_NORMAL_TERMINATION) {
printf("\nZTS_EVENT_NODE_NORMAL_TERMINATION -- A call to zts_start() will restart ZeroTier.\n"); printf("\nZTS_EVENT_NODE_NORMAL_TERMINATION -- A call to zts_start() will restart "
"ZeroTier.\n");
myNode.online = false; myNode.online = false;
} }
// Virtual network events // Virtual network events
if (msg->eventCode == ZTS_EVENT_NETWORK_NOT_FOUND) { if (msg->eventCode == ZTS_EVENT_NETWORK_NOT_FOUND) {
printf("\nZTS_EVENT_NETWORK_NOT_FOUND --- Are you sure %llx is a valid network?\n", printf(
msg->network->nwid); "\nZTS_EVENT_NETWORK_NOT_FOUND --- Are you sure %llx is a valid network?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) { if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) {
printf("\nZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a few seconds...\n", printf(
msg->network->nwid); "\nZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a "
"few seconds...\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) { if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) {
printf("\nZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. Did you authorize the node yet?\n", printf(
msg->network->nwid); "\nZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. "
"Did you authorize the node yet?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP4) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP4) {
printNetworkDetails("ZTS_EVENT_NETWORK_READY_IP4 --- Network config received.", msg->network); printNetworkDetails(
"ZTS_EVENT_NETWORK_READY_IP4 --- Network config received.",
msg->network);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) {
printNetworkDetails("ZTS_EVENT_NETWORK_READY_IP6 --- Network config received.", msg->network); printNetworkDetails(
"ZTS_EVENT_NETWORK_READY_IP6 --- Network config received.",
msg->network);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) { if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) {
@@ -269,31 +292,41 @@ void on_zts_event(void *msgPtr)
// Address events // Address events
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP4) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP4) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(msg->addr->addr); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("\nZTS_EVENT_ADDR_ADDED_IP4 --- This node's virtual address on network %llx is %s\n", printf(
msg->addr->nwid, ipstr); "\nZTS_EVENT_ADDR_ADDED_IP4 --- This node's virtual address on network %llx is %s\n",
msg->addr->nwid,
ipstr);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("\nZTS_EVENT_ADDR_ADDED_IP6 --- This node's virtual address on network %llx is %s\n", printf(
msg->addr->nwid, ipstr); "\nZTS_EVENT_ADDR_ADDED_IP6 --- This node's virtual address on network %llx is %s\n",
msg->addr->nwid,
ipstr);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP4) { if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP4) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(msg->addr->addr); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("\nZTS_EVENT_ADDR_REMOVED_IP4 --- The virtual address %s for this node on network %llx has been removed.\n", printf(
ipstr, msg->addr->nwid); "\nZTS_EVENT_ADDR_REMOVED_IP4 --- The virtual address %s for this node on network %llx "
"has been removed.\n",
ipstr,
msg->addr->nwid);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP6) { if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("\nZTS_EVENT_ADDR_REMOVED_IP6 --- The virtual address %s for this node on network %llx has been removed.\n", printf(
ipstr, msg->addr->nwid); "\nZTS_EVENT_ADDR_REMOVED_IP6 --- The virtual address %s for this node on network %llx "
"has been removed.\n",
ipstr,
msg->addr->nwid);
} }
// Peer events // Peer events
@@ -310,7 +343,9 @@ void on_zts_event(void *msgPtr)
printPeerDetails("ZTS_EVENT_PEER_RELAY --- No direct path known.", msg->peer); printPeerDetails("ZTS_EVENT_PEER_RELAY --- No direct path known.", msg->peer);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) {
printPeerDetails("ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered.", msg->peer); printPeerDetails(
"ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered.",
msg->peer);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) {
printPeerDetails("ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died.", msg->peer); printPeerDetails("ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died.", msg->peer);
@@ -338,16 +373,17 @@ void on_zts_event(void *msgPtr)
printf("\nZTS_EVENT_STACK_UP --- No action required.\n"); printf("\nZTS_EVENT_STACK_UP --- No action required.\n");
} }
if (msg->eventCode == ZTS_EVENT_STACK_DOWN) { if (msg->eventCode == ZTS_EVENT_STACK_DOWN) {
printf("\nZTS_EVENT_STACK_DOWN --- No action required. An app restart is needed to use ZeroTier again.\n"); printf("\nZTS_EVENT_STACK_DOWN --- No action required. An app restart is needed to use "
"ZeroTier again.\n");
} }
} }
void get6PLANEAddressOfPeer(uint64_t peerId, uint64_t nwId) void get6PLANEAddressOfPeer(uint64_t peerId, uint64_t nwId)
{ {
char peerAddrStr[ZTS_INET6_ADDRSTRLEN] = {0}; char peerAddrStr[ZTS_INET6_ADDRSTRLEN] = { 0 };
struct zts_sockaddr_storage sixplane_addr; struct zts_sockaddr_storage sixplane_addr;
zts_get_6plane_addr(&sixplane_addr, nwId, peerId); zts_get_6plane_addr(&sixplane_addr, nwId, peerId);
struct zts_sockaddr_in6 *p6 = (struct zts_sockaddr_in6*)&sixplane_addr; struct zts_sockaddr_in6* p6 = (struct zts_sockaddr_in6*)&sixplane_addr;
zts_inet_ntop(ZTS_AF_INET6, &(p6->sin6_addr), peerAddrStr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(p6->sin6_addr), peerAddrStr, ZTS_INET6_ADDRSTRLEN);
printf("6PLANE address of peer is: %s\n", peerAddrStr); printf("6PLANE address of peer is: %s\n", peerAddrStr);
} }
@@ -358,7 +394,8 @@ void display_stack_stats()
{ {
int err = 0; int err = 0;
// Count received pings // Count received pings
if ((err = zts_get_protocol_stats(ZTS_STATS_PROTOCOL_ICMP, &protoSpecificStats)) != ZTS_ERR_OK) { if ((err = zts_get_protocol_stats(ZTS_STATS_PROTOCOL_ICMP, &protoSpecificStats))
!= ZTS_ERR_OK) {
printf("zts_get_proto_stats()=%d", err); printf("zts_get_proto_stats()=%d", err);
return; return;
} }
@@ -371,7 +408,7 @@ void display_stack_stats()
printf("tcp.drop=%d\n", protoSpecificStats.drop); printf("tcp.drop=%d\n", protoSpecificStats.drop);
} }
int main(int argc, char **argv) int main(int argc, char** argv)
{ {
if (argc != 4) { if (argc != 4) {
printf("\nlibzt example server\n"); printf("\nlibzt example server\n");
@@ -379,52 +416,59 @@ int main(int argc, char **argv)
exit(0); exit(0);
} }
std::string configPath = std::string(argv[1]); std::string configPath = std::string(argv[1]);
uint64_t nwid = strtoull(argv[2],NULL,16); // Network ID to join uint64_t nwid = strtoull(argv[2], NULL, 16); // Network ID to join
int ztServicePort = atoi(argv[3]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994) int ztServicePort = atoi(
argv[3]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994)
// Bring up ZeroTier service and join network // Bring up ZeroTier service and join network
int err = ZTS_ERR_OK; int err = ZTS_ERR_OK;
// If disabled: (network) details will NOT be written to or read from (networks.d/). It may take slightly longer to start the node // If disabled: (network) details will NOT be written to or read from (networks.d/). It may take
// slightly longer to start the node
zts_allow_network_caching(1); zts_allow_network_caching(1);
// If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take slightly longer to contact a remote peer // If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take
// slightly longer to contact a remote peer
zts_allow_peer_caching(1); zts_allow_peer_caching(1);
// If disabled: Settings will NOT be read from local.conf // If disabled: Settings will NOT be read from local.conf
zts_allow_local_conf(1); zts_allow_local_conf(1);
if((err = zts_start(configPath.c_str(), &on_zts_event, ztServicePort)) != ZTS_ERR_OK) { if ((err = zts_start(configPath.c_str(), &on_zts_event, ztServicePort)) != ZTS_ERR_OK) {
printf("Unable to start service, error = %d. Exiting.\n", err); printf("Unable to start service, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Waiting for node to come online...\n"); printf("Waiting for node to come online...\n");
while (!myNode.online) { zts_delay_ms(50); } while (! myNode.online) {
zts_delay_ms(50);
}
printf("This node's identity is stored in %s\n", argv[1]); printf("This node's identity is stored in %s\n", argv[1]);
if((err = zts_join(nwid)) != ZTS_ERR_OK) { if ((err = zts_join(nwid)) != ZTS_ERR_OK) {
printf("Unable to join network, error = %d. Exiting.\n", err); printf("Unable to join network, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Joining network %llx\n", nwid); printf("Joining network %llx\n", nwid);
printf("Don't forget to authorize this device in my.zerotier.com or the web API!\n"); printf("Don't forget to authorize this device in my.zerotier.com or the web API!\n");
while (!myNode.joinedAtLeastOneNetwork) { zts_delay_ms(50); } while (! myNode.joinedAtLeastOneNetwork) {
zts_delay_ms(50);
}
// Idle and just show callback events, stack statistics, etc // Idle and just show callback events, stack statistics, etc
// Alternatively, this is where you could start making calls to the socket API // Alternatively, this is where you could start making calls to the socket API
/* /*
while(true) { while(true) {
display_stack_stats(); display_stack_stats();
zts_delay_ms(1000); zts_delay_ms(1000);
} }
*/ */
int delay = 500000; int delay = 500000;
printf("This program will delay for %d seconds and then shut down.\n", (delay / 1000)); printf("This program will delay for %d seconds and then shut down.\n", (delay / 1000));
zts_delay_ms(delay); zts_delay_ms(delay);
//printf("Leaving network %llx\n", nwid); // printf("Leaving network %llx\n", nwid);
//zts_leave(nwid); // zts_leave(nwid);
//zts_delay_ms(3000); /* added for demo purposes so that events show up */ // zts_delay_ms(3000); /* added for demo purposes so that events show up */
printf("Stopping ZeroTier\n"); printf("Stopping ZeroTier\n");
zts_stop(); zts_stop();
zts_delay_ms(delay); /* added for demo purposes so that events show up */ zts_delay_ms(delay); /* added for demo purposes so that events show up */

View File

@@ -86,14 +86,15 @@
* *
*/ */
#include "ZeroTierSockets.h"
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include "ZeroTierSockets.h" struct Node {
Node() : online(false), joinedAtLeastOneNetwork(false), id(0)
struct Node {
{ }
Node() : online(false), joinedAtLeastOneNetwork(false), id(0) {}
bool online; bool online;
bool joinedAtLeastOneNetwork; bool joinedAtLeastOneNetwork;
uint64_t id; uint64_t id;
@@ -104,9 +105,9 @@ struct Node
to ensure timely receipt of future events. You should not call libzt API functions from to ensure timely receipt of future events. You should not call libzt API functions from
this function unless it's something trivial like zts_inet_ntop() or similar that has this function unless it's something trivial like zts_inet_ntop() or similar that has
no state-change implications. */ no state-change implications. */
void on_zts_event(void *msgPtr) void on_zts_event(void* msgPtr)
{ {
struct zts_callback_msg *msg = (struct zts_callback_msg *)msgPtr; struct zts_callback_msg* msg = (struct zts_callback_msg*)msgPtr;
if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) { if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) {
printf("ZTS_EVENT_NODE_ONLINE --- This node's ID is %llx\n", msg->node->address); printf("ZTS_EVENT_NODE_ONLINE --- This node's ID is %llx\n", msg->node->address);
@@ -114,19 +115,27 @@ void on_zts_event(void *msgPtr)
myNode.online = true; myNode.online = true;
} }
if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) { if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) {
printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, firewall, etc. What ports are you blocking?\n"); printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, "
"firewall, etc. What ports are you blocking?\n");
myNode.online = false; myNode.online = false;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) { if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) {
printf("ZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a few seconds...\n", msg->network->nwid); printf(
"ZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a "
"few seconds...\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) { if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) {
printf("ZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. Did you authorize the node yet?\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. "
"Did you authorize the node yet?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) {
printf("ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent over network %llx\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent "
"over network %llx\n",
msg->network->nwid);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) { if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) {
@@ -134,17 +143,15 @@ void on_zts_event(void *msgPtr)
} }
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP4) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP4) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(msg->addr->addr); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_NEW_IP4 --- Join %llx and ping me at %s\n", printf("ZTS_EVENT_ADDR_NEW_IP4 --- Join %llx and ping me at %s\n", msg->addr->nwid, ipstr);
msg->addr->nwid, ipstr);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_NEW_IP6 --- Join %llx and ping me at %s\n", printf("ZTS_EVENT_ADDR_NEW_IP6 --- Join %llx and ping me at %s\n", msg->addr->nwid, ipstr);
msg->addr->nwid, ipstr);
} }
// Peer events // Peer events
if (msg->peer) { if (msg->peer) {
@@ -154,62 +161,75 @@ void on_zts_event(void *msgPtr)
return; return;
} }
if (msg->eventCode == ZTS_EVENT_PEER_DIRECT) { if (msg->eventCode == ZTS_EVENT_PEER_DIRECT) {
printf("ZTS_EVENT_PEER_DIRECT --- A direct path is known for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_DIRECT --- A direct path is known for node=%llx\n",
msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_RELAY) { if (msg->eventCode == ZTS_EVENT_PEER_RELAY) {
printf("ZTS_EVENT_PEER_RELAY --- No direct path to node=%llx\n", msg->peer->address); printf("ZTS_EVENT_PEER_RELAY --- No direct path to node=%llx\n", msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) {
printf("ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered for "
"node=%llx\n",
msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) {
printf("ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died for node=%llx\n",
msg->peer->address);
} }
} }
} }
int main(int argc, char **argv) int main(int argc, char** argv)
{ {
if (argc != 3) { if (argc != 3) {
printf("\nlibzt example\n"); printf("\nlibzt example\n");
printf("earthtest <config_file_path> <ztServicePort>\n"); printf("earthtest <config_file_path> <ztServicePort>\n");
exit(0); exit(0);
} }
int ztServicePort = atoi(argv[2]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994) int ztServicePort = atoi(
argv[2]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994)
int err = ZTS_ERR_OK; int err = ZTS_ERR_OK;
// If disabled: (network) details will NOT be written to or read from (networks.d/). It may take slightly longer to start the node // If disabled: (network) details will NOT be written to or read from (networks.d/). It may take
// slightly longer to start the node
zts_allow_network_caching(1); zts_allow_network_caching(1);
// If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take slightly longer to contact a remote peer // If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take
// slightly longer to contact a remote peer
zts_allow_peer_caching(1); zts_allow_peer_caching(1);
// If disabled: Settings will NOT be read from local.conf // If disabled: Settings will NOT be read from local.conf
zts_allow_local_conf(1); zts_allow_local_conf(1);
if((err = zts_start(argv[1], &on_zts_event, ztServicePort)) != ZTS_ERR_OK) { if ((err = zts_start(argv[1], &on_zts_event, ztServicePort)) != ZTS_ERR_OK) {
printf("Unable to start service, error = %d. Exiting.\n", err); printf("Unable to start service, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Waiting for node to come online...\n"); printf("Waiting for node to come online...\n");
while (!myNode.online) { zts_delay_ms(50); } while (! myNode.online) {
zts_delay_ms(50);
}
printf("This node's identity is stored in %s\n", argv[1]); printf("This node's identity is stored in %s\n", argv[1]);
uint64_t nwid = 0x8056c2e21c000001; uint64_t nwid = 0x8056c2e21c000001;
if((err = zts_join(nwid)) != ZTS_ERR_OK) { if ((err = zts_join(nwid)) != ZTS_ERR_OK) {
printf("Unable to join network, error = %d. Exiting.\n", err); printf("Unable to join network, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Joining network %llx\n", nwid); printf("Joining network %llx\n", nwid);
while (!myNode.joinedAtLeastOneNetwork) { zts_delay_ms(50); } while (! myNode.joinedAtLeastOneNetwork) {
zts_delay_ms(50);
}
// Idle and just show callback events, stack statistics, etc // Idle and just show callback events, stack statistics, etc
printf("Node will now idle...\n"); printf("Node will now idle...\n");
while (true) { zts_delay_ms(1000); } while (true) {
zts_delay_ms(1000);
}
// Shut down service and stack threads // Shut down service and stack threads

View File

@@ -5,15 +5,16 @@
* local storage. In this mode you are responsible for saving keys. * local storage. In this mode you are responsible for saving keys.
*/ */
#include "ZeroTierSockets.h"
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include "ZeroTierSockets.h" struct Node {
Node() : online(false), joinedAtLeastOneNetwork(false), id(0)
struct Node {
{ }
Node() : online(false), joinedAtLeastOneNetwork(false), id(0) {}
bool online; bool online;
bool joinedAtLeastOneNetwork; bool joinedAtLeastOneNetwork;
uint64_t id; uint64_t id;
@@ -24,9 +25,9 @@ struct Node
to ensure timely receipt of future events. You should not call libzt API functions from to ensure timely receipt of future events. You should not call libzt API functions from
this function unless it's something trivial like zts_inet_ntop() or similar that has this function unless it's something trivial like zts_inet_ntop() or similar that has
no state-change implications. */ no state-change implications. */
void on_zts_event(void *msgPtr) void on_zts_event(void* msgPtr)
{ {
struct zts_callback_msg *msg = (struct zts_callback_msg *)msgPtr; struct zts_callback_msg* msg = (struct zts_callback_msg*)msgPtr;
if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) { if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) {
printf("ZTS_EVENT_NODE_ONLINE --- This node's ID is %llx\n", msg->node->address); printf("ZTS_EVENT_NODE_ONLINE --- This node's ID is %llx\n", msg->node->address);
@@ -34,36 +35,39 @@ void on_zts_event(void *msgPtr)
myNode.online = true; myNode.online = true;
} }
if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) { if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) {
printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, firewall, etc. What ports are you blocking?\n"); printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, "
"firewall, etc. What ports are you blocking?\n");
myNode.online = false; myNode.online = false;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) {
printf("ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent over network %llx\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent "
"over network %llx\n",
msg->network->nwid);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
} }
#define KEY_BUF_LEN 2048 #define KEY_BUF_LEN 2048
int main(int argc, char **argv) int main(int argc, char** argv)
{ {
if (argc != 3) { if (argc != 3) {
printf("\nlibzt example\n"); printf("\nlibzt example\n");
printf("earthtest <config_file_path> <ztServicePort>\n"); printf("earthtest <config_file_path> <ztServicePort>\n");
exit(0); exit(0);
} }
int ztServicePort = atoi(argv[2]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994) int ztServicePort = atoi(
argv[2]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994)
int err = ZTS_ERR_OK; int err = ZTS_ERR_OK;
// BEGIN key handling // BEGIN key handling
// Do not allow ZT to write anything to disk // Do not allow ZT to write anything to disk
zts_disable_local_storage(1); zts_disable_local_storage(1);
// Buffer used to store identity keypair (if someone can read this, they can impersonate your node!) // Buffer used to store identity keypair (if someone can read this, they can impersonate your
// node!)
char keypair[KEY_BUF_LEN]; char keypair[KEY_BUF_LEN];
memset(keypair, 0, KEY_BUF_LEN); memset(keypair, 0, KEY_BUF_LEN);
@@ -77,15 +81,18 @@ int main(int argc, char **argv)
printf("\n\nVerifying ident...\n"); printf("\n\nVerifying ident...\n");
if (zts_verify_identity(keypair)) { if (zts_verify_identity(keypair)) {
printf("\tIdentity is valid\n"); printf("\tIdentity is valid\n");
} else { }
else {
printf("\tIdentity is invalid\n"); printf("\tIdentity is invalid\n");
} }
printf("\n\nStarting node with generated identity...\n"); printf("\n\nStarting node with generated identity...\n");
zts_start_with_identity(keypair, keypair_len, &on_zts_event, ztServicePort); zts_start_with_identity(keypair, keypair_len, &on_zts_event, ztServicePort);
printf("\n\nWaiting for node to come online...\n"); printf("\n\nWaiting for node to come online...\n");
while (!myNode.online) { zts_delay_ms(50); } while (! myNode.online) {
zts_delay_ms(50);
}
printf("\n\nAs a test, copy node's identity keypair back into buffer...\n"); printf("\n\nAs a test, copy node's identity keypair back into buffer...\n");
memset(keypair, 0, KEY_BUF_LEN); memset(keypair, 0, KEY_BUF_LEN);
@@ -93,23 +100,25 @@ int main(int argc, char **argv)
zts_get_node_identity(keypair, &keypair_len); zts_get_node_identity(keypair, &keypair_len);
printf("keypair(len=%d) = [%s]\n", keypair_len, keypair); printf("keypair(len=%d) = [%s]\n", keypair_len, keypair);
// END key handling // END key handling
uint64_t nwid = 0x8056c2e21c000001; uint64_t nwid = 0x8056c2e21c000001;
if((err = zts_join(nwid)) != ZTS_ERR_OK) { if ((err = zts_join(nwid)) != ZTS_ERR_OK) {
printf("Unable to join network, error = %d. Exiting.\n", err); printf("Unable to join network, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Joining network %llx\n", nwid); printf("Joining network %llx\n", nwid);
while (!myNode.joinedAtLeastOneNetwork) { zts_delay_ms(50); } while (! myNode.joinedAtLeastOneNetwork) {
zts_delay_ms(50);
}
// Idle and just show callback events, stack statistics, etc // Idle and just show callback events, stack statistics, etc
printf("Node will now idle...\n"); printf("Node will now idle...\n");
while (true) { zts_delay_ms(1000); } while (true) {
zts_delay_ms(1000);
}
// Shut down service and stack threads // Shut down service and stack threads

View File

@@ -84,16 +84,17 @@
* *
*/ */
#include "ZeroTierSockets.h"
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include <string> #include <string>
#include "ZeroTierSockets.h" struct Node {
Node() : online(false), joinedAtLeastOneNetwork(false), id(0)
struct Node {
{ }
Node() : online(false), joinedAtLeastOneNetwork(false), id(0) {}
bool online; bool online;
bool joinedAtLeastOneNetwork; bool joinedAtLeastOneNetwork;
uint64_t id; uint64_t id;
@@ -104,9 +105,9 @@ struct Node
to ensure timely receipt of future events. You should not call libzt API functions from to ensure timely receipt of future events. You should not call libzt API functions from
this function unless it's something trivial like zts_inet_ntop() or similar that has this function unless it's something trivial like zts_inet_ntop() or similar that has
no state-change implications. */ no state-change implications. */
void on_zts_event(void *msgPtr) void on_zts_event(void* msgPtr)
{ {
struct zts_callback_msg *msg = (struct zts_callback_msg *)msgPtr; struct zts_callback_msg* msg = (struct zts_callback_msg*)msgPtr;
// Node events // Node events
if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) { if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) {
@@ -115,7 +116,8 @@ void on_zts_event(void *msgPtr)
myNode.online = true; myNode.online = true;
} }
if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) { if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) {
printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, firewall, etc. What ports are you blocking?\n"); printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, "
"firewall, etc. What ports are you blocking?\n");
myNode.online = false; myNode.online = false;
} }
if (msg->eventCode == ZTS_EVENT_NODE_NORMAL_TERMINATION) { if (msg->eventCode == ZTS_EVENT_NODE_NORMAL_TERMINATION) {
@@ -125,25 +127,34 @@ void on_zts_event(void *msgPtr)
// Virtual network events // Virtual network events
if (msg->eventCode == ZTS_EVENT_NETWORK_NOT_FOUND) { if (msg->eventCode == ZTS_EVENT_NETWORK_NOT_FOUND) {
printf("ZTS_EVENT_NETWORK_NOT_FOUND --- Are you sure %llx is a valid network?\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_NOT_FOUND --- Are you sure %llx is a valid network?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) { if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) {
printf("ZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a few seconds...\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a "
"few seconds...\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) { if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) {
printf("ZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. Did you authorize the node yet?\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. "
"Did you authorize the node yet?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP4) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP4) {
printf("ZTS_EVENT_NETWORK_READY_IP4 --- Network config received. IPv4 traffic can now be sent over network %llx\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_READY_IP4 --- Network config received. IPv4 traffic can now be sent "
"over network %llx\n",
msg->network->nwid);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) {
printf("ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent over network %llx\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent "
"over network %llx\n",
msg->network->nwid);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) { if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) {
@@ -153,31 +164,41 @@ void on_zts_event(void *msgPtr)
// Address events // Address events
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP4) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP4) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(msg->addr->addr); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_NEW_IP4 --- This node's virtual address on network %llx is %s\n", printf(
msg->addr->nwid, ipstr); "ZTS_EVENT_ADDR_NEW_IP4 --- This node's virtual address on network %llx is %s\n",
msg->addr->nwid,
ipstr);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_NEW_IP6 --- This node's virtual address on network %llx is %s\n", printf(
msg->addr->nwid, ipstr); "ZTS_EVENT_ADDR_NEW_IP6 --- This node's virtual address on network %llx is %s\n",
msg->addr->nwid,
ipstr);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP4) { if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP4) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(msg->addr->addr); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_REMOVED_IP4 --- The virtual address %s for this node on network %llx has been removed.\n", printf(
ipstr, msg->addr->nwid); "ZTS_EVENT_ADDR_REMOVED_IP4 --- The virtual address %s for this node on network %llx "
"has been removed.\n",
ipstr,
msg->addr->nwid);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP6) { if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_REMOVED_IP6 --- The virtual address %s for this node on network %llx has been removed.\n", printf(
ipstr, msg->addr->nwid); "ZTS_EVENT_ADDR_REMOVED_IP6 --- The virtual address %s for this node on network %llx "
"has been removed.\n",
ipstr,
msg->addr->nwid);
} }
// Peer events // Peer events
@@ -188,34 +209,40 @@ void on_zts_event(void *msgPtr)
return; return;
} }
if (msg->eventCode == ZTS_EVENT_PEER_DIRECT) { if (msg->eventCode == ZTS_EVENT_PEER_DIRECT) {
printf("ZTS_EVENT_PEER_DIRECT --- A direct path is known for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_DIRECT --- A direct path is known for node=%llx\n",
msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_RELAY) { if (msg->eventCode == ZTS_EVENT_PEER_RELAY) {
printf("ZTS_EVENT_PEER_RELAY --- No direct path to node=%llx\n", msg->peer->address); printf("ZTS_EVENT_PEER_RELAY --- No direct path to node=%llx\n", msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) {
printf("ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered for "
"node=%llx\n",
msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) {
printf("ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died for node=%llx\n",
msg->peer->address);
} }
} }
} }
int main(int argc, char **argv) int main(int argc, char** argv)
{ {
if (argc != 6) { if (argc != 6) {
printf("\nlibzt example non-blocking client\n"); printf("\nlibzt example non-blocking client\n");
printf("nonblockingclient <config_file_path> <nwid> <remoteAddr> <remotePort> <ztServicePort>\n"); printf("nonblockingclient <config_file_path> <nwid> <remoteAddr> <remotePort> "
"<ztServicePort>\n");
exit(0); exit(0);
} }
uint64_t nwid = strtoull(argv[2],NULL,16); // Network ID to join uint64_t nwid = strtoull(argv[2], NULL, 16); // Network ID to join
std::string remoteAddr = argv[3]; // Remote application's virtual ZT address std::string remoteAddr = argv[3]; // Remote application's virtual ZT address
int remotePort = atoi(argv[4]); // Port the application will try to connect to the server on int remotePort = atoi(argv[4]); // Port the application will try to connect to the server on
int ztServicePort = atoi(argv[5]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994) int ztServicePort = atoi(
argv[5]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994)
struct zts_sockaddr_in in4; struct zts_sockaddr_in in4;
in4.sin_port = htons(remotePort); in4.sin_port = htons(remotePort);
@@ -230,33 +257,39 @@ int main(int argc, char **argv)
int err = ZTS_ERR_OK; int err = ZTS_ERR_OK;
// If disabled: (network) details will NOT be written to or read from (networks.d/). It may take slightly longer to start the node // If disabled: (network) details will NOT be written to or read from (networks.d/). It may take
// slightly longer to start the node
zts_allow_network_caching(1); zts_allow_network_caching(1);
// If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take slightly longer to contact a remote peer // If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take
// slightly longer to contact a remote peer
zts_allow_peer_caching(1); zts_allow_peer_caching(1);
// If disabled: Settings will NOT be read from local.conf // If disabled: Settings will NOT be read from local.conf
zts_allow_local_conf(1); zts_allow_local_conf(1);
if((err = zts_start(argv[1], &on_zts_event, ztServicePort)) != ZTS_ERR_OK) { if ((err = zts_start(argv[1], &on_zts_event, ztServicePort)) != ZTS_ERR_OK) {
printf("Unable to start service, error = %d. Exiting.\n", err); printf("Unable to start service, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Waiting for node to come online...\n"); printf("Waiting for node to come online...\n");
while (!myNode.online) { zts_delay_ms(50); } while (! myNode.online) {
zts_delay_ms(50);
}
printf("This node's identity is stored in %s\n", argv[1]); printf("This node's identity is stored in %s\n", argv[1]);
if((err = zts_join(nwid)) != ZTS_ERR_OK) { if ((err = zts_join(nwid)) != ZTS_ERR_OK) {
printf("Unable to join network, error = %d. Exiting.\n", err); printf("Unable to join network, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Joining network %llx\n", nwid); printf("Joining network %llx\n", nwid);
printf("Don't forget to authorize this device in my.zerotier.com or the web API!\n"); printf("Don't forget to authorize this device in my.zerotier.com or the web API!\n");
while (!myNode.joinedAtLeastOneNetwork) { zts_delay_ms(50); } while (! myNode.joinedAtLeastOneNetwork) {
zts_delay_ms(50);
}
// Socket-like API example // Socket-like API example
char *msgStr = (char*)"Welcome to the machine"; char* msgStr = (char*)"Welcome to the machine";
int bytes=0, fd; int bytes = 0, fd;
char recvBuf[128]; char recvBuf[128];
memset(recvBuf, 0, sizeof(recvBuf)); memset(recvBuf, 0, sizeof(recvBuf));
@@ -267,13 +300,19 @@ int main(int argc, char **argv)
// Retries are often required since ZT uses transport-triggered links (explained above) // Retries are often required since ZT uses transport-triggered links (explained above)
for (;;) { for (;;) {
printf("Connecting to remote host...\n"); printf("Connecting to remote host...\n");
if ((err = zts_connect(fd, (const struct zts_sockaddr *)&in4, sizeof(in4))) < 0) { if ((err = zts_connect(fd, (const struct zts_sockaddr*)&in4, sizeof(in4))) < 0) {
printf("Error connecting to remote host (fd=%d, ret=%d, zts_errno=%d). Trying again.\n", printf(
fd, err, zts_errno); "Error connecting to remote host (fd=%d, ret=%d, zts_errno=%d). Trying again.\n",
fd,
err,
zts_errno);
zts_close(fd); zts_close(fd);
printf("Creating socket...\n"); printf("Creating socket...\n");
if ((fd = zts_socket(ZTS_AF_INET, ZTS_SOCK_STREAM, 0)) < 0) { if ((fd = zts_socket(ZTS_AF_INET, ZTS_SOCK_STREAM, 0)) < 0) {
printf("Error creating ZeroTier socket (fd=%d, zts_errno=%d). Exiting.\n", fd, zts_errno); printf(
"Error creating ZeroTier socket (fd=%d, zts_errno=%d). Exiting.\n",
fd,
zts_errno);
exit(1); exit(1);
} }
zts_delay_ms(250); zts_delay_ms(250);
@@ -286,9 +325,13 @@ int main(int argc, char **argv)
// Wait random intervals to send a message to the server // Wait random intervals to send a message to the server
// The non-blocking aspect of this example is server-side // The non-blocking aspect of this example is server-side
while(1) { while (1) {
if((bytes = zts_send(fd, msgStr, strlen(msgStr), 0)) < 0) { if ((bytes = zts_send(fd, msgStr, strlen(msgStr), 0)) < 0) {
printf("Error writing to socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n", fd, bytes, zts_errno); printf(
"Error writing to socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
bytes,
zts_errno);
exit(1); exit(1);
} }
printf("zts_send()=%d\n", bytes); printf("zts_send()=%d\n", bytes);

View File

@@ -84,15 +84,16 @@
* *
*/ */
#include "ZeroTierSockets.h"
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include "ZeroTierSockets.h" struct Node {
Node() : online(false), joinedAtLeastOneNetwork(false), id(0)
struct Node {
{ }
Node() : online(false), joinedAtLeastOneNetwork(false), id(0) {}
bool online; bool online;
bool joinedAtLeastOneNetwork; bool joinedAtLeastOneNetwork;
uint64_t id; uint64_t id;
@@ -103,9 +104,9 @@ struct Node
to ensure timely receipt of future events. You should not call libzt API functions from to ensure timely receipt of future events. You should not call libzt API functions from
this function unless it's something trivial like zts_inet_ntop() or similar that has this function unless it's something trivial like zts_inet_ntop() or similar that has
no state-change implications. */ no state-change implications. */
void on_zts_event(void *msgPtr) void on_zts_event(void* msgPtr)
{ {
struct zts_callback_msg *msg = (struct zts_callback_msg *)msgPtr; struct zts_callback_msg* msg = (struct zts_callback_msg*)msgPtr;
// Node events // Node events
if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) { if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) {
@@ -114,7 +115,8 @@ void on_zts_event(void *msgPtr)
myNode.online = true; myNode.online = true;
} }
if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) { if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) {
printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, firewall, etc. What ports are you blocking?\n"); printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, "
"firewall, etc. What ports are you blocking?\n");
myNode.online = false; myNode.online = false;
} }
if (msg->eventCode == ZTS_EVENT_NODE_NORMAL_TERMINATION) { if (msg->eventCode == ZTS_EVENT_NODE_NORMAL_TERMINATION) {
@@ -124,25 +126,34 @@ void on_zts_event(void *msgPtr)
// Virtual network events // Virtual network events
if (msg->eventCode == ZTS_EVENT_NETWORK_NOT_FOUND) { if (msg->eventCode == ZTS_EVENT_NETWORK_NOT_FOUND) {
printf("ZTS_EVENT_NETWORK_NOT_FOUND --- Are you sure %llx is a valid network?\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_NOT_FOUND --- Are you sure %llx is a valid network?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) { if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) {
printf("ZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a few seconds...\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a "
"few seconds...\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) { if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) {
printf("ZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. Did you authorize the node yet?\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. "
"Did you authorize the node yet?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP4) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP4) {
printf("ZTS_EVENT_NETWORK_READY_IP4 --- Network config received. IPv4 traffic can now be sent over network %llx\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_READY_IP4 --- Network config received. IPv4 traffic can now be sent "
"over network %llx\n",
msg->network->nwid);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) {
printf("ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent over network %llx\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent "
"over network %llx\n",
msg->network->nwid);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) { if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) {
@@ -152,31 +163,41 @@ void on_zts_event(void *msgPtr)
// Address events // Address events
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP4) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP4) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(msg->addr->addr); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_NEW_IP4 --- This node's virtual address on network %llx is %s\n", printf(
msg->addr->nwid, ipstr); "ZTS_EVENT_ADDR_NEW_IP4 --- This node's virtual address on network %llx is %s\n",
msg->addr->nwid,
ipstr);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_NEW_IP6 --- This node's virtual address on network %llx is %s\n", printf(
msg->addr->nwid, ipstr); "ZTS_EVENT_ADDR_NEW_IP6 --- This node's virtual address on network %llx is %s\n",
msg->addr->nwid,
ipstr);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP4) { if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP4) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(msg->addr->addr); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_REMOVED_IP4 --- The virtual address %s for this node on network %llx has been removed.\n", printf(
ipstr, msg->addr->nwid); "ZTS_EVENT_ADDR_REMOVED_IP4 --- The virtual address %s for this node on network %llx "
"has been removed.\n",
ipstr,
msg->addr->nwid);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP6) { if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_REMOVED_IP6 --- The virtual address %s for this node on network %llx has been removed.\n", printf(
ipstr, msg->addr->nwid); "ZTS_EVENT_ADDR_REMOVED_IP6 --- The virtual address %s for this node on network %llx "
"has been removed.\n",
ipstr,
msg->addr->nwid);
} }
// Peer events // Peer events
@@ -187,33 +208,38 @@ void on_zts_event(void *msgPtr)
return; return;
} }
if (msg->eventCode == ZTS_EVENT_PEER_DIRECT) { if (msg->eventCode == ZTS_EVENT_PEER_DIRECT) {
printf("ZTS_EVENT_PEER_DIRECT --- A direct path is known for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_DIRECT --- A direct path is known for node=%llx\n",
msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_RELAY) { if (msg->eventCode == ZTS_EVENT_PEER_RELAY) {
printf("ZTS_EVENT_PEER_RELAY --- No direct path to node=%llx\n", msg->peer->address); printf("ZTS_EVENT_PEER_RELAY --- No direct path to node=%llx\n", msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) {
printf("ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered for "
"node=%llx\n",
msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) {
printf("ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died for node=%llx\n",
msg->peer->address);
} }
} }
} }
int main(int argc, char **argv) int main(int argc, char** argv)
{ {
if (argc != 5) { if (argc != 5) {
printf("\nlibzt example non-blocking server\n"); printf("\nlibzt example non-blocking server\n");
printf("nonblockingserver <config_file_path> <nwid> <serverBindPort> <ztServicePort>\n"); printf("nonblockingserver <config_file_path> <nwid> <serverBindPort> <ztServicePort>\n");
exit(0); exit(0);
} }
uint64_t nwid = strtoull(argv[2],NULL,16); // Network ID to join uint64_t nwid = strtoull(argv[2], NULL, 16); // Network ID to join
int serverBindPort = atoi(argv[3]); // Port the application should bind to int serverBindPort = atoi(argv[3]); // Port the application should bind to
int ztServicePort = atoi(argv[4]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994) int ztServicePort = atoi(
argv[4]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994)
struct zts_sockaddr_in in4, acc_in4; struct zts_sockaddr_in in4, acc_in4;
in4.sin_port = htons(serverBindPort); in4.sin_port = htons(serverBindPort);
@@ -229,51 +255,73 @@ int main(int argc, char **argv)
int fd, accfd; int fd, accfd;
int err = ZTS_ERR_OK; int err = ZTS_ERR_OK;
// If disabled: (network) details will NOT be written to or read from (networks.d/). It may take slightly longer to start the node // If disabled: (network) details will NOT be written to or read from (networks.d/). It may take
// slightly longer to start the node
zts_allow_network_caching(1); zts_allow_network_caching(1);
// If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take slightly longer to contact a remote peer // If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take
// slightly longer to contact a remote peer
zts_allow_peer_caching(1); zts_allow_peer_caching(1);
// If disabled: Settings will NOT be read from local.conf // If disabled: Settings will NOT be read from local.conf
zts_allow_local_conf(1); zts_allow_local_conf(1);
if((err = zts_start(argv[1], &on_zts_event, ztServicePort)) != ZTS_ERR_OK) { if ((err = zts_start(argv[1], &on_zts_event, ztServicePort)) != ZTS_ERR_OK) {
printf("Unable to start service, error = %d. Exiting.\n", err); printf("Unable to start service, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Waiting for node to come online...\n"); printf("Waiting for node to come online...\n");
while (!myNode.online) { zts_delay_ms(50); } while (! myNode.online) {
zts_delay_ms(50);
}
printf("This node ID is %llx\n", myNode.id); printf("This node ID is %llx\n", myNode.id);
printf("This node's identity is stored in %s\n", argv[1]); printf("This node's identity is stored in %s\n", argv[1]);
if((err = zts_join(nwid)) != ZTS_ERR_OK) { if ((err = zts_join(nwid)) != ZTS_ERR_OK) {
printf("Unable to join network, error = %d. Exiting.\n", err); printf("Unable to join network, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Joining network %llx\n", nwid); printf("Joining network %llx\n", nwid);
printf("Don't forget to authorize this device in my.zerotier.com or the web API!\n"); printf("Don't forget to authorize this device in my.zerotier.com or the web API!\n");
while (!myNode.joinedAtLeastOneNetwork) { zts_delay_ms(50); } while (! myNode.joinedAtLeastOneNetwork) {
zts_delay_ms(50);
}
// Socket-like API example // Socket-like API example
printf("Creating socket...\n"); printf("Creating socket...\n");
if ((fd = zts_socket(ZTS_AF_INET, ZTS_SOCK_STREAM, 0)) < 0) { if ((fd = zts_socket(ZTS_AF_INET, ZTS_SOCK_STREAM, 0)) < 0) {
printf("Error creating ZeroTier socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",fd, err, zts_errno); printf(
"Error creating ZeroTier socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
err,
zts_errno);
exit(1); exit(1);
} }
printf("Binding...\n"); printf("Binding...\n");
if ((err = zts_bind(fd, (struct zts_sockaddr *)&in4, sizeof(struct zts_sockaddr_in)) < 0)) { if ((err = zts_bind(fd, (struct zts_sockaddr*)&in4, sizeof(struct zts_sockaddr_in)) < 0)) {
printf("Error binding to interface (fd=%d, ret=%d, zts_errno=%d). Exiting.\n", fd, err, zts_errno); printf(
"Error binding to interface (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
err,
zts_errno);
exit(1); exit(1);
} }
printf("Listening...\n"); printf("Listening...\n");
int backlog = 100; int backlog = 100;
if ((err = zts_listen(fd, backlog)) < 0) { if ((err = zts_listen(fd, backlog)) < 0) {
printf("Error placing socket in LISTENING state (fd=%d, ret=%d, zts_errno=%d). Exiting.\n", fd, err, zts_errno); printf(
"Error placing socket in LISTENING state (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
err,
zts_errno);
exit(1); exit(1);
} }
zts_socklen_t client_addrlen = sizeof(zts_sockaddr_in); zts_socklen_t client_addrlen = sizeof(zts_sockaddr_in);
if ((accfd = zts_accept(fd, (struct zts_sockaddr *)&acc_in4, &client_addrlen)) < 0) { if ((accfd = zts_accept(fd, (struct zts_sockaddr*)&acc_in4, &client_addrlen)) < 0) {
printf("Error accepting connection (fd=%d, ret=%d, zts_errno=%d). Exiting.\n", fd, err, zts_errno); printf(
"Error accepting connection (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
err,
zts_errno);
} }
zts_socklen_t peer_addrlen = sizeof(struct zts_sockaddr_storage); zts_socklen_t peer_addrlen = sizeof(struct zts_sockaddr_storage);
@@ -283,7 +331,7 @@ int main(int argc, char **argv)
zts_inet_ntop(ZTS_AF_INET, &(acc_in4.sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(acc_in4.sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("Accepted connection from %s:%d\n", ipstr, ntohs(acc_in4.sin_port)); printf("Accepted connection from %s:%d\n", ipstr, ntohs(acc_in4.sin_port));
int bytes=0; int bytes = 0;
char recvBuf[128]; char recvBuf[128];
memset(recvBuf, 0, sizeof(recvBuf)); memset(recvBuf, 0, sizeof(recvBuf));
@@ -293,7 +341,7 @@ int main(int argc, char **argv)
if (false) { if (false) {
zts_fcntl(fd, ZTS_F_SETFL, ZTS_O_NONBLOCK); zts_fcntl(fd, ZTS_F_SETFL, ZTS_O_NONBLOCK);
zts_fcntl(accfd, ZTS_F_SETFL, ZTS_O_NONBLOCK); zts_fcntl(accfd, ZTS_F_SETFL, ZTS_O_NONBLOCK);
while(1) { while (1) {
bytes = zts_recv(accfd, recvBuf, sizeof(recvBuf), 0); bytes = zts_recv(accfd, recvBuf, sizeof(recvBuf), 0);
printf("zts_recv(%d, ...)=%d\n", accfd, bytes); printf("zts_recv(%d, ...)=%d\n", accfd, bytes);
zts_delay_ms(100); zts_delay_ms(100);
@@ -311,21 +359,18 @@ int main(int argc, char **argv)
zts_fd_set active_fd_set, read_fd_set; zts_fd_set active_fd_set, read_fd_set;
ZTS_FD_ZERO(&active_fd_set); ZTS_FD_ZERO(&active_fd_set);
ZTS_FD_SET(accfd, &active_fd_set); ZTS_FD_SET(accfd, &active_fd_set);
while (1) while (1) {
{
read_fd_set = active_fd_set; read_fd_set = active_fd_set;
if ((result = zts_select(ZTS_FD_SETSIZE, &read_fd_set, NULL, NULL, &tv) < 0)) if ((result = zts_select(ZTS_FD_SETSIZE, &read_fd_set, NULL, NULL, &tv) < 0)) {
{ // perror ("select");
//perror ("select"); exit(1);
exit (1);
} }
for (int i=0; i<ZTS_FD_SETSIZE; i++) { for (int i = 0; i < ZTS_FD_SETSIZE; i++) {
if (ZTS_FD_ISSET(i, &read_fd_set)) if (ZTS_FD_ISSET(i, &read_fd_set)) {
{
bytes = zts_recv(accfd, recvBuf, sizeof(recvBuf), 0); bytes = zts_recv(accfd, recvBuf, sizeof(recvBuf), 0);
printf("zts_recv(%d, ...)=%d\n", i, bytes); printf("zts_recv(%d, ...)=%d\n", i, bytes);
} }
//ZTS_FD_CLR(i, &active_fd_set); // ZTS_FD_CLR(i, &active_fd_set);
} }
} }
} }
@@ -342,12 +387,11 @@ int main(int argc, char **argv)
numfds++; numfds++;
int result = 0; int result = 0;
int timeout_ms = 50; int timeout_ms = 50;
while(1) { while (1) {
result = zts_poll(poll_set, numfds, timeout_ms); result = zts_poll(poll_set, numfds, timeout_ms);
printf("zts_poll()=%d\n", result); printf("zts_poll()=%d\n", result);
for(int i = 0; i < numfds; i++) for (int i = 0; i < numfds; i++) {
{ if (poll_set[i].revents & ZTS_POLLIN) {
if(poll_set[i].revents & ZTS_POLLIN) {
bytes = zts_recv(poll_set[i].fd, recvBuf, sizeof(recvBuf), 0); bytes = zts_recv(poll_set[i].fd, recvBuf, sizeof(recvBuf), 0);
printf("zts_recv(%d, ...)=%d\n", i, bytes); printf("zts_recv(%d, ...)=%d\n", i, bytes);
} }

View File

@@ -2,16 +2,17 @@
* libzt API example * libzt API example
*/ */
#include "ZeroTierSockets.h"
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include <string> #include <string>
#include "ZeroTierSockets.h" struct Node {
Node() : online(false), joinedAtLeastOneNetwork(false), id(0)
struct Node {
{ }
Node() : online(false), joinedAtLeastOneNetwork(false), id(0) {}
bool online; bool online;
bool joinedAtLeastOneNetwork; bool joinedAtLeastOneNetwork;
uint64_t id; uint64_t id;
@@ -22,9 +23,9 @@ struct Node
to ensure timely receipt of future events. You should not call libzt API functions from to ensure timely receipt of future events. You should not call libzt API functions from
this function unless it's something trivial like zts_inet_ntop() or similar that has this function unless it's something trivial like zts_inet_ntop() or similar that has
no state-change implications. */ no state-change implications. */
void on_zts_event(void *msgPtr) void on_zts_event(void* msgPtr)
{ {
struct zts_callback_msg *msg = (struct zts_callback_msg *)msgPtr; struct zts_callback_msg* msg = (struct zts_callback_msg*)msgPtr;
// Node events // Node events
if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) { if (msg->eventCode == ZTS_EVENT_NODE_ONLINE) {
@@ -33,7 +34,8 @@ void on_zts_event(void *msgPtr)
myNode.online = true; myNode.online = true;
} }
if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) { if (msg->eventCode == ZTS_EVENT_NODE_OFFLINE) {
printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, firewall, etc. What ports are you blocking?\n"); printf("ZTS_EVENT_NODE_OFFLINE --- Check your physical Internet connection, router, "
"firewall, etc. What ports are you blocking?\n");
myNode.online = false; myNode.online = false;
} }
if (msg->eventCode == ZTS_EVENT_NODE_NORMAL_TERMINATION) { if (msg->eventCode == ZTS_EVENT_NODE_NORMAL_TERMINATION) {
@@ -42,24 +44,34 @@ void on_zts_event(void *msgPtr)
// Virtual network events // Virtual network events
if (msg->eventCode == ZTS_EVENT_NETWORK_NOT_FOUND) { if (msg->eventCode == ZTS_EVENT_NETWORK_NOT_FOUND) {
printf("ZTS_EVENT_NETWORK_NOT_FOUND --- Are you sure %llx is a valid network?\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_NOT_FOUND --- Are you sure %llx is a valid network?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) { if (msg->eventCode == ZTS_EVENT_NETWORK_REQ_CONFIG) {
printf("ZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a few seconds...\n", msg->network->nwid); printf(
"ZTS_EVENT_NETWORK_REQ_CONFIG --- Requesting config for network %llx, please wait a "
"few seconds...\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) { if (msg->eventCode == ZTS_EVENT_NETWORK_ACCESS_DENIED) {
printf("ZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. Did you authorize the node yet?\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_ACCESS_DENIED --- Access to virtual network %llx has been denied. "
"Did you authorize the node yet?\n",
msg->network->nwid);
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP4) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP4) {
printf("ZTS_EVENT_NETWORK_READY_IP4 --- Network config received. IPv4 traffic can now be sent over network %llx\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_READY_IP4 --- Network config received. IPv4 traffic can now be sent "
"over network %llx\n",
msg->network->nwid);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) { if (msg->eventCode == ZTS_EVENT_NETWORK_READY_IP6) {
printf("ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent over network %llx\n", printf(
msg->network->nwid); "ZTS_EVENT_NETWORK_READY_IP6 --- Network config received. IPv6 traffic can now be sent "
"over network %llx\n",
msg->network->nwid);
myNode.joinedAtLeastOneNetwork = true; myNode.joinedAtLeastOneNetwork = true;
} }
if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) { if (msg->eventCode == ZTS_EVENT_NETWORK_DOWN) {
@@ -69,31 +81,41 @@ void on_zts_event(void *msgPtr)
// Address events // Address events
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP4) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP4) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(msg->addr->addr); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_NEW_IP4 --- This node's virtual address on network %llx is %s\n", printf(
msg->addr->nwid, ipstr); "ZTS_EVENT_ADDR_NEW_IP4 --- This node's virtual address on network %llx is %s\n",
msg->addr->nwid,
ipstr);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) { if (msg->eventCode == ZTS_EVENT_ADDR_ADDED_IP6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_NEW_IP6 --- This node's virtual address on network %llx is %s\n", printf(
msg->addr->nwid, ipstr); "ZTS_EVENT_ADDR_NEW_IP6 --- This node's virtual address on network %llx is %s\n",
msg->addr->nwid,
ipstr);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP4) { if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP4) {
char ipstr[ZTS_INET_ADDRSTRLEN]; char ipstr[ZTS_INET_ADDRSTRLEN];
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)&(msg->addr->addr); struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), ipstr, ZTS_INET_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_REMOVED_IP4 --- The virtual address %s for this node on network %llx has been removed.\n", printf(
ipstr, msg->addr->nwid); "ZTS_EVENT_ADDR_REMOVED_IP4 --- The virtual address %s for this node on network %llx "
"has been removed.\n",
ipstr,
msg->addr->nwid);
} }
if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP6) { if (msg->eventCode == ZTS_EVENT_ADDR_REMOVED_IP6) {
char ipstr[ZTS_INET6_ADDRSTRLEN]; char ipstr[ZTS_INET6_ADDRSTRLEN];
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr); struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)&(msg->addr->addr);
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN); zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), ipstr, ZTS_INET6_ADDRSTRLEN);
printf("ZTS_EVENT_ADDR_REMOVED_IP6 --- The virtual address %s for this node on network %llx has been removed.\n", printf(
ipstr, msg->addr->nwid); "ZTS_EVENT_ADDR_REMOVED_IP6 --- The virtual address %s for this node on network %llx "
"has been removed.\n",
ipstr,
msg->addr->nwid);
} }
// Peer events // Peer events
if (msg->peer) { if (msg->peer) {
@@ -103,19 +125,23 @@ void on_zts_event(void *msgPtr)
return; return;
} }
if (msg->eventCode == ZTS_EVENT_PEER_DIRECT) { if (msg->eventCode == ZTS_EVENT_PEER_DIRECT) {
printf("ZTS_EVENT_PEER_DIRECT --- A direct path is known for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_DIRECT --- A direct path is known for node=%llx\n",
msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_RELAY) { if (msg->eventCode == ZTS_EVENT_PEER_RELAY) {
printf("ZTS_EVENT_PEER_RELAY --- No direct path to node=%llx\n", msg->peer->address); printf("ZTS_EVENT_PEER_RELAY --- No direct path to node=%llx\n", msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DISCOVERED) {
printf("ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_PATH_DISCOVERED --- A new direct path was discovered for "
"node=%llx\n",
msg->peer->address);
} }
if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) { if (msg->eventCode == ZTS_EVENT_PEER_PATH_DEAD) {
printf("ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died for node=%llx\n", printf(
msg->peer->address); "ZTS_EVENT_PEER_PATH_DEAD --- A direct path has died for node=%llx\n",
msg->peer->address);
} }
} }
} }
@@ -202,16 +228,17 @@ void on_zts_event(void *msgPtr)
* *
*/ */
int main(int argc, char **argv) int main(int argc, char** argv)
{ {
if (argc != 5) { if (argc != 5) {
printf("\nlibzt example server\n"); printf("\nlibzt example server\n");
printf("server <config_file_path> <nwid> <serverBindPort> <ztServicePort>\n"); printf("server <config_file_path> <nwid> <serverBindPort> <ztServicePort>\n");
exit(0); exit(0);
} }
uint64_t nwid = strtoull(argv[2],NULL,16); // Network ID to join uint64_t nwid = strtoull(argv[2], NULL, 16); // Network ID to join
int serverBindPort = atoi(argv[3]); // Port the application should bind to int serverBindPort = atoi(argv[3]); // Port the application should bind to
int ztServicePort = atoi(argv[4]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994) int ztServicePort = atoi(
argv[4]); // Port ZT uses to send encrypted UDP packets to peers (try something like 9994)
struct zts_sockaddr_in in4, acc_in4; struct zts_sockaddr_in in4, acc_in4;
in4.sin_port = htons(serverBindPort); in4.sin_port = htons(serverBindPort);
@@ -227,56 +254,78 @@ int main(int argc, char **argv)
int fd, accfd; int fd, accfd;
int err = ZTS_ERR_OK; int err = ZTS_ERR_OK;
// If disabled: (network) details will NOT be written to or read from (networks.d/). It may take slightly longer to start the node // If disabled: (network) details will NOT be written to or read from (networks.d/). It may take
// slightly longer to start the node
zts_allow_network_caching(1); zts_allow_network_caching(1);
// If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take slightly longer to contact a remote peer // If disabled: (peer) details will NOT be written to or read from (peers.d/). It may take
// slightly longer to contact a remote peer
zts_allow_peer_caching(1); zts_allow_peer_caching(1);
// If disabled: Settings will NOT be read from local.conf // If disabled: Settings will NOT be read from local.conf
zts_allow_local_conf(1); zts_allow_local_conf(1);
if((err = zts_start(argv[1], &on_zts_event, ztServicePort)) != ZTS_ERR_OK) { if ((err = zts_start(argv[1], &on_zts_event, ztServicePort)) != ZTS_ERR_OK) {
printf("Unable to start service, error = %d. Exiting.\n", err); printf("Unable to start service, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Waiting for node to come online...\n"); printf("Waiting for node to come online...\n");
while (!myNode.online) { zts_delay_ms(50); } while (! myNode.online) {
zts_delay_ms(50);
}
printf("This node's identity is stored in %s\n", argv[1]); printf("This node's identity is stored in %s\n", argv[1]);
if((err = zts_join(nwid)) != ZTS_ERR_OK) { if ((err = zts_join(nwid)) != ZTS_ERR_OK) {
printf("Unable to join network, error = %d. Exiting.\n", err); printf("Unable to join network, error = %d. Exiting.\n", err);
exit(1); exit(1);
} }
printf("Joining network %llx\n", nwid); printf("Joining network %llx\n", nwid);
printf("Don't forget to authorize this device in my.zerotier.com or the web API!\n"); printf("Don't forget to authorize this device in my.zerotier.com or the web API!\n");
while (!myNode.joinedAtLeastOneNetwork) { zts_delay_ms(50); } while (! myNode.joinedAtLeastOneNetwork) {
zts_delay_ms(50);
}
// Socket-like API example // Socket-like API example
printf("Creating socket...\n"); printf("Creating socket...\n");
if ((fd = zts_socket(ZTS_AF_INET, ZTS_SOCK_STREAM, 0)) < 0) { if ((fd = zts_socket(ZTS_AF_INET, ZTS_SOCK_STREAM, 0)) < 0) {
printf("Error creating ZeroTier socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",fd, err, zts_errno); printf(
"Error creating ZeroTier socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
err,
zts_errno);
exit(1); exit(1);
} }
printf("Binding...\n"); printf("Binding...\n");
if ((err = zts_bind(fd, (struct zts_sockaddr *)&in4, sizeof(struct zts_sockaddr_in)) < 0)) { if ((err = zts_bind(fd, (struct zts_sockaddr*)&in4, sizeof(struct zts_sockaddr_in)) < 0)) {
printf("Error binding to interface (fd=%d, ret=%d, zts_errno=%d). Exiting.\n", fd, err, zts_errno); printf(
"Error binding to interface (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
err,
zts_errno);
exit(1); exit(1);
} }
printf("Listening...\n"); printf("Listening...\n");
int backlog = 100; int backlog = 100;
if ((err = zts_listen(fd, backlog)) < 0) { if ((err = zts_listen(fd, backlog)) < 0) {
printf("Error placing socket in LISTENING state (fd=%d, ret=%d, zts_errno=%d). Exiting.\n", fd, err, zts_errno); printf(
"Error placing socket in LISTENING state (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
err,
zts_errno);
exit(1); exit(1);
} }
int bytes=0; int bytes = 0;
char recvBuf[128]; char recvBuf[128];
memset(recvBuf, 0, sizeof(recvBuf)); memset(recvBuf, 0, sizeof(recvBuf));
while (true) { while (true) {
zts_socklen_t client_addrlen = sizeof(zts_sockaddr_in); zts_socklen_t client_addrlen = sizeof(zts_sockaddr_in);
if ((accfd = zts_accept(fd, (struct zts_sockaddr *)&acc_in4, &client_addrlen)) < 0) { if ((accfd = zts_accept(fd, (struct zts_sockaddr*)&acc_in4, &client_addrlen)) < 0) {
printf("Error accepting connection (fd=%d, ret=%d, zts_errno=%d). Exiting.\n", fd, err, zts_errno); printf(
"Error accepting connection (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
err,
zts_errno);
} }
zts_socklen_t peer_addrlen = sizeof(struct zts_sockaddr_storage); zts_socklen_t peer_addrlen = sizeof(struct zts_sockaddr_storage);
zts_getpeername(accfd, (struct zts_sockaddr*)&acc_in4, &peer_addrlen); zts_getpeername(accfd, (struct zts_sockaddr*)&acc_in4, &peer_addrlen);
@@ -287,14 +336,22 @@ int main(int argc, char **argv)
printf("Accepted connection from %s:%d\n", ipstr, ntohs(acc_in4.sin_port)); printf("Accepted connection from %s:%d\n", ipstr, ntohs(acc_in4.sin_port));
printf("Reading message string from client...\n"); printf("Reading message string from client...\n");
if((bytes = zts_read(accfd, recvBuf, sizeof(recvBuf))) < 0) { if ((bytes = zts_read(accfd, recvBuf, sizeof(recvBuf))) < 0) {
printf("Error writing to socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n", fd, bytes, zts_errno); printf(
"Error writing to socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
bytes,
zts_errno);
exit(1); exit(1);
} }
printf("Read %d bytes: %s\n", bytes, recvBuf); printf("Read %d bytes: %s\n", bytes, recvBuf);
printf("Sending message string to client...\n"); printf("Sending message string to client...\n");
if((bytes = zts_write(accfd, recvBuf, bytes)) < 0) { if ((bytes = zts_write(accfd, recvBuf, bytes)) < 0) {
printf("Error writing to socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n", fd, bytes, zts_errno); printf(
"Error writing to socket (fd=%d, ret=%d, zts_errno=%d). Exiting.\n",
fd,
bytes,
zts_errno);
exit(1); exit(1);
} }
printf("Sent %d bytes: %s\n", bytes, recvBuf); printf("Sent %d bytes: %s\n", bytes, recvBuf);

File diff suppressed because it is too large Load Diff

View File

@@ -16,20 +16,20 @@
#ifdef ZTS_ENABLE_CENTRAL_API #ifdef ZTS_ENABLE_CENTRAL_API
#include <stdio.h> #include "Debug.hpp"
#include <curl/curl.h> #include "Mutex.hpp"
#include <string.h> #include "ZeroTierSockets.h"
#include <iomanip>
#include <iostream>
#include "Mutex.hpp" #include <curl/curl.h>
#include "Debug.hpp" #include <iomanip>
#include "ZeroTierSockets.h" #include <iostream>
#include <stdio.h>
#include <string.h>
char api_url[ZTS_CENRTAL_MAX_URL_LEN]; char api_url[ZTS_CENRTAL_MAX_URL_LEN];
char api_token[ZTS_CENTRAL_TOKEN_LEN+1]; char api_token[ZTS_CENTRAL_TOKEN_LEN + 1];
char *_resp_buf; char* _resp_buf;
int _resp_buf_len; int _resp_buf_len;
int _resp_buf_offset; int _resp_buf_offset;
@@ -41,19 +41,19 @@ using namespace ZeroTier;
Mutex _responseBuffer_m; Mutex _responseBuffer_m;
#ifdef __cplusplus #ifdef __cplusplus
extern "C" { extern "C" {
#endif #endif
size_t on_data(void *buffer, size_t size, size_t nmemb, void *userp) size_t on_data(void* buffer, size_t size, size_t nmemb, void* userp)
{ {
DEBUG_INFO("buf=%p,size=%zu,nmemb=%zu,userp=%p", buffer, size, nmemb, userp); DEBUG_INFO("buf=%p,size=%zu,nmemb=%zu,userp=%p", buffer, size, nmemb, userp);
int byte_count = (size * nmemb); int byte_count = (size * nmemb);
if (_resp_buf_offset + byte_count >= _resp_buf_len) { if (_resp_buf_offset + byte_count >= _resp_buf_len) {
DEBUG_ERROR("Out of buffer space. Cannot store response from server"); DEBUG_ERROR("Out of buffer space. Cannot store response from server");
return 0; // Signal to libcurl that our buffer is full (triggers a write error.) return 0; // Signal to libcurl that our buffer is full (triggers a write error.)
} }
memcpy(_resp_buf+_resp_buf_offset, buffer, byte_count); memcpy(_resp_buf + _resp_buf_offset, buffer, byte_count);
_resp_buf_offset += byte_count; _resp_buf_offset += byte_count;
return byte_count; return byte_count;
} }
@@ -76,10 +76,13 @@ void zts_central_clear_resp_buf()
} }
int zts_central_init( int zts_central_init(
const char *url_str, const char *token_str, char *resp_buf, uint32_t resp_buf_len) const char* url_str,
const char* token_str,
char* resp_buf,
uint32_t resp_buf_len)
{ {
_access_modes = ZTS_CENTRAL_READ; // Defauly read-only _access_modes = ZTS_CENTRAL_READ; // Defauly read-only
_bIsVerbose = 0; // Default disable libcurl verbose output _bIsVerbose = 0; // Default disable libcurl verbose output
Mutex::Lock _l(_responseBuffer_m); Mutex::Lock _l(_responseBuffer_m);
if (resp_buf_len == 0) { if (resp_buf_len == 0) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
@@ -93,14 +96,16 @@ int zts_central_init(
int url_len = strlen(url_str); int url_len = strlen(url_str);
if (url_len < 3 || url_len > ZTS_CENRTAL_MAX_URL_LEN) { if (url_len < 3 || url_len > ZTS_CENRTAL_MAX_URL_LEN) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} else { }
else {
memset(api_url, 0, ZTS_CENRTAL_MAX_URL_LEN); memset(api_url, 0, ZTS_CENRTAL_MAX_URL_LEN);
memcpy(api_url, url_str, url_len); memcpy(api_url, url_str, url_len);
} }
int token_len = strlen(token_str); int token_len = strlen(token_str);
if (token_len != ZTS_CENTRAL_TOKEN_LEN) { if (token_len != ZTS_CENTRAL_TOKEN_LEN) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} else { }
else {
memset(api_token, 0, ZTS_CENTRAL_TOKEN_LEN); memset(api_token, 0, ZTS_CENTRAL_TOKEN_LEN);
memcpy(api_token, token_str, token_len); memcpy(api_token, token_str, token_len);
} }
@@ -113,19 +118,24 @@ void zts_central_cleanup()
curl_global_cleanup(); curl_global_cleanup();
} }
int _central_req(int request_type, char *central_str, int _central_req(
char *api_route_str, char *token_str, int *response_code, char *post_data) int request_type,
char* central_str,
char* api_route_str,
char* token_str,
int* response_code,
char* post_data)
{ {
int err = ZTS_ERR_OK; int err = ZTS_ERR_OK;
if (!_bInit) { if (! _bInit) {
DEBUG_ERROR("Error: Central API must be initialized first. Call zts_central_init()"); DEBUG_ERROR("Error: Central API must be initialized first. Call zts_central_init()");
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (request_type == ZTS_HTTP_GET && !(_access_modes & ZTS_CENTRAL_READ)) { if (request_type == ZTS_HTTP_GET && ! (_access_modes & ZTS_CENTRAL_READ)) {
DEBUG_ERROR("Error: Incorrect access mode. Need (ZTS_CENTRAL_READ) permission"); DEBUG_ERROR("Error: Incorrect access mode. Need (ZTS_CENTRAL_READ) permission");
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (request_type == ZTS_HTTP_POST && !(_access_modes & ZTS_CENTRAL_WRITE)) { if (request_type == ZTS_HTTP_POST && ! (_access_modes & ZTS_CENTRAL_WRITE)) {
DEBUG_ERROR("Error: Incorrect access mode. Need (ZTS_CENTRAL_WRITE) permission"); DEBUG_ERROR("Error: Incorrect access mode. Need (ZTS_CENTRAL_WRITE) permission");
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
@@ -144,14 +154,14 @@ int _central_req(int request_type, char *central_str,
strcpy(req_url, central_str); strcpy(req_url, central_str);
strcat(req_url, api_route_str); strcat(req_url, api_route_str);
CURL *curl; CURL* curl;
CURLcode res; CURLcode res;
curl = curl_easy_init(); curl = curl_easy_init();
if (!curl) { if (! curl) {
return ZTS_ERR_GENERAL; return ZTS_ERR_GENERAL;
} }
struct curl_slist *hs=NULL; struct curl_slist* hs = NULL;
char auth_str[ZTS_CENTRAL_TOKEN_LEN + 32]; char auth_str[ZTS_CENTRAL_TOKEN_LEN + 32];
if (token_strlen == ZTS_CENTRAL_TOKEN_LEN) { if (token_strlen == ZTS_CENTRAL_TOKEN_LEN) {
memset(auth_str, 0, ZTS_CENTRAL_TOKEN_LEN + 32); memset(auth_str, 0, ZTS_CENTRAL_TOKEN_LEN + 32);
@@ -184,19 +194,20 @@ int _central_req(int request_type, char *central_str,
if (request_type == ZTS_HTTP_DELETE) { if (request_type == ZTS_HTTP_DELETE) {
curl_easy_setopt(curl, CURLOPT_CUSTOMREQUEST, "DELETE"); curl_easy_setopt(curl, CURLOPT_CUSTOMREQUEST, "DELETE");
} }
//curl_easy_setopt(curl, CURLOPT_FAILONERROR, 1L); // Consider 400-500 series code as failures // curl_easy_setopt(curl, CURLOPT_FAILONERROR, 1L); // Consider 400-500 series code as failures
// Perform request // Perform request
res = curl_easy_perform(curl); res = curl_easy_perform(curl);
if(res == CURLE_OK) { if (res == CURLE_OK) {
//char* url; // char* url;
double elapsed_time = 0.0; double elapsed_time = 0.0;
long hrc = 0; long hrc = 0;
curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &hrc); curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &hrc);
curl_easy_getinfo(curl, CURLINFO_TOTAL_TIME, &elapsed_time); curl_easy_getinfo(curl, CURLINFO_TOTAL_TIME, &elapsed_time);
DEBUG_INFO("Req. took %f second(s). HTTP code (%ld)", elapsed_time, hrc); DEBUG_INFO("Req. took %f second(s). HTTP code (%ld)", elapsed_time, hrc);
*response_code = hrc; *response_code = hrc;
//curl_easy_getinfo(curl, CURLINFO_EFFECTIVE_URL, &url); // curl_easy_getinfo(curl, CURLINFO_EFFECTIVE_URL, &url);
} else { }
else {
DEBUG_ERROR("%s", curl_easy_strerror(res)); DEBUG_ERROR("%s", curl_easy_strerror(res));
err = ZTS_ERR_SERVICE; err = ZTS_ERR_SERVICE;
} }
@@ -204,7 +215,7 @@ int _central_req(int request_type, char *central_str,
return err; return err;
} }
int zts_get_last_resp_buf(char *dest_buffer, int dest_buf_len) int zts_get_last_resp_buf(char* dest_buffer, int dest_buf_len)
{ {
if (dest_buf_len <= _resp_buf_offset) { if (dest_buf_len <= _resp_buf_offset) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
@@ -214,73 +225,63 @@ int zts_get_last_resp_buf(char *dest_buffer, int dest_buf_len)
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
int zts_central_get_status(int *resp_code) int zts_central_get_status(int* resp_code)
{ {
return _central_req( return _central_req(ZTS_HTTP_GET, api_url, (char*)"/api/status", api_token, resp_code, NULL);
ZTS_HTTP_GET, api_url, (char*)"/api/status", api_token, resp_code, NULL);
} }
int zts_central_get_self(int *resp_code) int zts_central_get_self(int* resp_code)
{ {
return _central_req( return _central_req(ZTS_HTTP_GET, api_url, (char*)"/api/self", api_token, resp_code, NULL);
ZTS_HTTP_GET, api_url, (char*)"/api/self", api_token, resp_code, NULL);
} }
int zts_central_get_network(int *resp_code, uint64_t nwid) int zts_central_get_network(int* resp_code, uint64_t nwid)
{ {
char req[64]; char req[64];
sprintf(req, "/api/network/%llx", nwid); sprintf(req, "/api/network/%llx", nwid);
return _central_req( return _central_req(ZTS_HTTP_GET, api_url, req, api_token, resp_code, NULL);
ZTS_HTTP_GET, api_url, req, api_token, resp_code, NULL);
} }
int zts_central_update_network(int *resp_code, uint64_t nwid) int zts_central_update_network(int* resp_code, uint64_t nwid)
{ {
char req[64]; char req[64];
sprintf(req, "/api/network/%llx", nwid); sprintf(req, "/api/network/%llx", nwid);
return _central_req( return _central_req(ZTS_HTTP_POST, api_url, req, api_token, resp_code, NULL);
ZTS_HTTP_POST, api_url, req, api_token, resp_code, NULL);
} }
int zts_central_delete_network(int *resp_code, uint64_t nwid) int zts_central_delete_network(int* resp_code, uint64_t nwid)
{ {
char req[64]; char req[64];
sprintf(req, "/api/network/%llx", nwid); sprintf(req, "/api/network/%llx", nwid);
return _central_req( return _central_req(ZTS_HTTP_DELETE, api_url, req, api_token, resp_code, NULL);
ZTS_HTTP_DELETE, api_url, req, api_token, resp_code, NULL);
} }
int zts_central_get_networks(int *resp_code) int zts_central_get_networks(int* resp_code)
{ {
return _central_req( return _central_req(ZTS_HTTP_GET, api_url, (char*)"/api/network", api_token, resp_code, NULL);
ZTS_HTTP_GET, api_url, (char*)"/api/network", api_token, resp_code, NULL);
} }
int zts_central_get_member(int *resp_code, uint64_t nwid, uint64_t nodeid) int zts_central_get_member(int* resp_code, uint64_t nwid, uint64_t nodeid)
{ {
if (nwid == 0 || nodeid == 0) { if (nwid == 0 || nodeid == 0) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
char req[64]; char req[64];
sprintf(req, "/api/network/%llx/member/%llx", nwid, nodeid); sprintf(req, "/api/network/%llx/member/%llx", nwid, nodeid);
return _central_req( return _central_req(ZTS_HTTP_GET, api_url, req, api_token, resp_code, NULL);
ZTS_HTTP_GET, api_url, req, api_token, resp_code, NULL);
} }
int zts_central_update_member( int zts_central_update_member(int* resp_code, uint64_t nwid, uint64_t nodeid, char* post_data)
int *resp_code, uint64_t nwid, uint64_t nodeid, char *post_data)
{ {
if (nwid == 0 || nodeid == 0 || post_data == NULL) { if (nwid == 0 || nodeid == 0 || post_data == NULL) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
char req[64]; char req[64];
sprintf(req, "/api/network/%llx/member/%llx", nwid, nodeid); sprintf(req, "/api/network/%llx/member/%llx", nwid, nodeid);
return _central_req( return _central_req(ZTS_HTTP_POST, api_url, req, api_token, resp_code, post_data);
ZTS_HTTP_POST, api_url, req, api_token, resp_code, post_data);
} }
int zts_central_set_node_auth( int zts_central_set_node_auth(int* resp_code, uint64_t nwid, uint64_t nodeid, uint8_t is_authed)
int *resp_code, uint64_t nwid, uint64_t nodeid, uint8_t is_authed)
{ {
if (is_authed != 0 && is_authed != 1) { if (is_authed != 0 && is_authed != 1) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
@@ -295,17 +296,16 @@ int zts_central_set_node_auth(
return zts_central_update_member(resp_code, nwid, nodeid, config_data); return zts_central_update_member(resp_code, nwid, nodeid, config_data);
} }
int zts_central_get_members_of_network(int *resp_code, uint64_t nwid) int zts_central_get_members_of_network(int* resp_code, uint64_t nwid)
{ {
char req[64]; char req[64];
sprintf(req, "/api/network/%llx/member", nwid); sprintf(req, "/api/network/%llx/member", nwid);
return _central_req( return _central_req(ZTS_HTTP_GET, api_url, req, api_token, resp_code, NULL);
ZTS_HTTP_GET, api_url, req, api_token, resp_code, NULL);
} }
#ifdef __cplusplus #ifdef __cplusplus
} // extern "C" } // extern "C"
#endif #endif
#endif // ZTS_ENABLE_CENTRAL_API #endif // ZTS_ENABLE_CENTRAL_API
#endif // _H #endif // _H

View File

@@ -17,21 +17,20 @@
* Node / Network control interface * Node / Network control interface
*/ */
#include "Constants.hpp"
#include "Debug.hpp"
#include "Events.hpp"
#include "Mutex.hpp"
#include "Node.hpp"
#include "NodeService.hpp"
#include "OSUtils.hpp"
#include "Signals.hpp"
#include "VirtualTap.hpp"
#include "ZeroTierSockets.h"
#include <inttypes.h> #include <inttypes.h>
#include <sys/types.h> #include <sys/types.h>
#include "Constants.hpp"
#include "Node.hpp"
#include "Mutex.hpp"
#include "OSUtils.hpp"
#include "ZeroTierSockets.h"
#include "Debug.hpp"
#include "NodeService.hpp"
#include "VirtualTap.hpp"
#include "Events.hpp"
#include "Signals.hpp"
using namespace ZeroTier; using namespace ZeroTier;
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
@@ -39,7 +38,7 @@ using namespace ZeroTier;
#endif #endif
#ifdef __WINDOWS__ #ifdef __WINDOWS__
#include <Windows.h> #include <Windows.h>
WSADATA wsaData; WSADATA wsaData;
#endif #endif
@@ -47,37 +46,36 @@ WSADATA wsaData;
#define ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS 1 #define ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS 1
#endif #endif
namespace ZeroTier namespace ZeroTier {
{ extern NodeService* service;
extern NodeService *service; extern Mutex serviceLock;
extern Mutex serviceLock;
#ifdef ZTS_ENABLE_PYTHON #ifdef ZTS_ENABLE_PYTHON
#endif #endif
#ifdef ZTS_ENABLE_PINVOKE #ifdef ZTS_ENABLE_PINVOKE
extern void (*_userEventCallback)(void *); extern void (*_userEventCallback)(void*);
#endif #endif
#ifdef ZTS_C_API_ONLY #ifdef ZTS_C_API_ONLY
extern void (*_userEventCallback)(void *); extern void (*_userEventCallback)(void*);
#endif #endif
extern uint8_t allowNetworkCaching; extern uint8_t allowNetworkCaching;
extern uint8_t allowPeerCaching; extern uint8_t allowPeerCaching;
extern uint8_t allowLocalConf; extern uint8_t allowLocalConf;
extern uint8_t disableLocalStorage; // Off by default extern uint8_t disableLocalStorage; // Off by default
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
// References to JNI objects and VM kept for future callbacks // References to JNI objects and VM kept for future callbacks
JavaVM *jvm = NULL; JavaVM* jvm = NULL;
jobject objRef = NULL; jobject objRef = NULL;
jmethodID _userCallbackMethodRef = NULL; jmethodID _userCallbackMethodRef = NULL;
#endif #endif
extern uint8_t _serviceStateFlags; extern uint8_t _serviceStateFlags;
} } // namespace ZeroTier
#ifdef __cplusplus #ifdef __cplusplus
extern "C" { extern "C" {
#endif #endif
int zts_generate_orphan_identity(char *key_pair_str, uint16_t *key_buf_len) int zts_generate_orphan_identity(char* key_pair_str, uint16_t* key_buf_len)
{ {
if (*key_buf_len < ZT_IDENTITY_STRING_BUFFER_LENGTH || key_pair_str == NULL) { if (*key_buf_len < ZT_IDENTITY_STRING_BUFFER_LENGTH || key_pair_str == NULL) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
@@ -85,7 +83,7 @@ int zts_generate_orphan_identity(char *key_pair_str, uint16_t *key_buf_len)
Identity id; Identity id;
id.generate(); id.generate();
char idtmp[1024]; char idtmp[1024];
std::string idser = id.toString(true,idtmp); std::string idser = id.toString(true, idtmp);
uint16_t key_pair_len = idser.length(); uint16_t key_pair_len = idser.length();
if (key_pair_len > *key_buf_len) { if (key_pair_len > *key_buf_len) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
@@ -95,7 +93,7 @@ int zts_generate_orphan_identity(char *key_pair_str, uint16_t *key_buf_len)
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
int zts_verify_identity(const char *key_pair_str) int zts_verify_identity(const char* key_pair_str)
{ {
if (key_pair_str == NULL || strlen(key_pair_str) > ZT_IDENTITY_STRING_BUFFER_LENGTH) { if (key_pair_str == NULL || strlen(key_pair_str) > ZT_IDENTITY_STRING_BUFFER_LENGTH) {
return false; return false;
@@ -109,13 +107,13 @@ int zts_verify_identity(const char *key_pair_str)
return false; return false;
} }
int zts_get_node_identity(char *key_pair_str, uint16_t *key_buf_len) int zts_get_node_identity(char* key_pair_str, uint16_t* key_buf_len)
{ {
Mutex::Lock _l(serviceLock); Mutex::Lock _l(serviceLock);
if (*key_buf_len == 0 || key_pair_str == NULL) { if (*key_buf_len == 0 || key_pair_str == NULL) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
if (!service) { if (! service) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
service->getIdentity(key_pair_str, key_buf_len); service->getIdentity(key_pair_str, key_buf_len);
@@ -124,25 +122,34 @@ int zts_get_node_identity(char *key_pair_str, uint16_t *key_buf_len)
// TODO: This logic should be further generalized in the next API redesign // TODO: This logic should be further generalized in the next API redesign
#ifdef ZTS_ENABLE_PYTHON #ifdef ZTS_ENABLE_PYTHON
int zts_start_with_identity(const char *key_pair_str, uint16_t key_buf_len, int zts_start_with_identity(
PythonDirectorCallbackClass *callback, uint16_t port) const char* key_pair_str,
uint16_t key_buf_len,
PythonDirectorCallbackClass* callback,
uint16_t port)
#endif #endif
#ifdef ZTS_ENABLE_PINVOKE #ifdef ZTS_ENABLE_PINVOKE
int zts_start_with_identity(const char *key_pair_str, uint16_t key_buf_len, int zts_start_with_identity(
CppCallback callback, uint16_t port) const char* key_pair_str,
uint16_t key_buf_len,
CppCallback callback,
uint16_t port)
#endif #endif
#ifdef ZTS_C_API_ONLY #ifdef ZTS_C_API_ONLY
int zts_start_with_identity(const char *key_pair_str, uint16_t key_buf_len, int zts_start_with_identity(
void (*callback)(void *), uint16_t port) const char* key_pair_str,
uint16_t key_buf_len,
void (*callback)(void*),
uint16_t port)
#endif #endif
{ {
if (!zts_verify_identity(key_pair_str)) { if (! zts_verify_identity(key_pair_str)) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
Mutex::Lock _l(serviceLock); Mutex::Lock _l(serviceLock);
#ifdef ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS #ifdef ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS
_install_signal_handlers(); _install_signal_handlers();
#endif // ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS #endif // ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS
_lwip_driver_init(); _lwip_driver_init();
if (service || _getState(ZTS_STATE_NODE_RUNNING)) { if (service || _getState(ZTS_STATE_NODE_RUNNING)) {
// Service is already initialized // Service is already initialized
@@ -154,12 +161,12 @@ int zts_start_with_identity(const char *key_pair_str, uint16_t key_buf_len,
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
_userEventCallback = callback; _userEventCallback = callback;
if (!_isCallbackRegistered()) { if (! _isCallbackRegistered()) {
// Must have a callback // Must have a callback
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
serviceParameters *params = new serviceParameters(); serviceParameters* params = new serviceParameters();
params->port = port; params->port = port;
params->path.clear(); params->path.clear();
@@ -170,7 +177,7 @@ int zts_start_with_identity(const char *key_pair_str, uint16_t key_buf_len,
id.toString(true, params->secretIdentityStr); id.toString(true, params->secretIdentityStr);
} }
} }
if (!id) { if (! id) {
delete params; delete params;
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
@@ -203,7 +210,7 @@ int zts_start_with_identity(const char *key_pair_str, uint16_t key_buf_len,
_clrState(ZTS_STATE_CALLBACKS_RUNNING); _clrState(ZTS_STATE_CALLBACKS_RUNNING);
_clrState(ZTS_STATE_NODE_RUNNING); _clrState(ZTS_STATE_NODE_RUNNING);
_clearRegisteredCallback(); _clearRegisteredCallback();
//delete params; // delete params;
} }
return retval; return retval;
} }
@@ -211,7 +218,7 @@ int zts_start_with_identity(const char *key_pair_str, uint16_t key_buf_len,
int zts_allow_network_caching(uint8_t allowed = 1) int zts_allow_network_caching(uint8_t allowed = 1)
{ {
Mutex::Lock _l(serviceLock); Mutex::Lock _l(serviceLock);
if(!service) { if (! service) {
allowNetworkCaching = allowed; allowNetworkCaching = allowed;
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
@@ -221,7 +228,7 @@ int zts_allow_network_caching(uint8_t allowed = 1)
int zts_allow_peer_caching(uint8_t allowed = 1) int zts_allow_peer_caching(uint8_t allowed = 1)
{ {
Mutex::Lock _l(serviceLock); Mutex::Lock _l(serviceLock);
if(!service) { if (! service) {
allowPeerCaching = allowed; allowPeerCaching = allowed;
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
@@ -231,7 +238,7 @@ int zts_allow_peer_caching(uint8_t allowed = 1)
int zts_allow_local_conf(uint8_t allowed = 1) int zts_allow_local_conf(uint8_t allowed = 1)
{ {
Mutex::Lock _l(serviceLock); Mutex::Lock _l(serviceLock);
if(!service) { if (! service) {
allowLocalConf = allowed; allowLocalConf = allowed;
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
@@ -241,7 +248,7 @@ int zts_allow_local_conf(uint8_t allowed = 1)
int zts_disable_local_storage(uint8_t disabled) int zts_disable_local_storage(uint8_t disabled)
{ {
Mutex::Lock _l(serviceLock); Mutex::Lock _l(serviceLock);
if(!service) { if (! service) {
disableLocalStorage = disabled; disableLocalStorage = disabled;
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
@@ -249,19 +256,19 @@ int zts_disable_local_storage(uint8_t disabled)
} }
#ifdef ZTS_ENABLE_PYTHON #ifdef ZTS_ENABLE_PYTHON
int zts_start(const char *path, PythonDirectorCallbackClass *callback, uint16_t port) int zts_start(const char* path, PythonDirectorCallbackClass* callback, uint16_t port)
#endif #endif
#ifdef ZTS_ENABLE_PINVOKE #ifdef ZTS_ENABLE_PINVOKE
int zts_start(const char *path, CppCallback callback, uint16_t port) int zts_start(const char* path, CppCallback callback, uint16_t port)
#endif #endif
#ifdef ZTS_C_API_ONLY #ifdef ZTS_C_API_ONLY
int zts_start(const char *path, void (*callback)(void *), uint16_t port) int zts_start(const char* path, void (*callback)(void*), uint16_t port)
#endif #endif
{ {
Mutex::Lock _l(serviceLock); Mutex::Lock _l(serviceLock);
#ifdef ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS #ifdef ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS
_install_signal_handlers(); _install_signal_handlers();
#endif // ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS #endif // ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS
_lwip_driver_init(); _lwip_driver_init();
if (service || _getState(ZTS_STATE_NODE_RUNNING)) { if (service || _getState(ZTS_STATE_NODE_RUNNING)) {
// Service is already initialized // Service is already initialized
@@ -273,14 +280,14 @@ int zts_start(const char *path, void (*callback)(void *), uint16_t port)
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
_userEventCallback = callback; _userEventCallback = callback;
if (!_isCallbackRegistered()) { if (! _isCallbackRegistered()) {
// Must have a callback // Must have a callback
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
if (!path) { if (! path) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
serviceParameters *params = new serviceParameters(); serviceParameters* params = new serviceParameters();
params->port = port; params->port = port;
params->path = std::string(path); params->path = std::string(path);
@@ -316,25 +323,30 @@ int zts_start(const char *path, void (*callback)(void *), uint16_t port)
_clrState(ZTS_STATE_CALLBACKS_RUNNING); _clrState(ZTS_STATE_CALLBACKS_RUNNING);
_clrState(ZTS_STATE_NODE_RUNNING); _clrState(ZTS_STATE_NODE_RUNNING);
_clearRegisteredCallback(); _clearRegisteredCallback();
//delete params; // delete params;
} }
return retval; return retval;
} }
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_start( JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_start(
JNIEnv *env, jobject thisObj, jstring path, jobject callback, jint port) JNIEnv* env,
jobject thisObj,
jstring path,
jobject callback,
jint port)
{ {
if (!path) { if (! path) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
jclass eventListenerClass = env->GetObjectClass(callback); jclass eventListenerClass = env->GetObjectClass(callback);
if(eventListenerClass == NULL) { if (eventListenerClass == NULL) {
DEBUG_ERROR("Couldn't find class for ZeroTierEventListener instance"); DEBUG_ERROR("Couldn't find class for ZeroTierEventListener instance");
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
jmethodID eventListenerCallbackMethod = env->GetMethodID(eventListenerClass, "onZeroTierEvent", "(JI)V"); jmethodID eventListenerCallbackMethod =
if(eventListenerCallbackMethod == NULL) { env->GetMethodID(eventListenerClass, "onZeroTierEvent", "(JI)V");
if (eventListenerCallbackMethod == NULL) {
DEBUG_ERROR("Couldn't find onZeroTierEvent method"); DEBUG_ERROR("Couldn't find onZeroTierEvent method");
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
@@ -342,7 +354,7 @@ JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_start(
objRef = env->NewGlobalRef(callback); objRef = env->NewGlobalRef(callback);
_userCallbackMethodRef = eventListenerCallbackMethod; _userCallbackMethodRef = eventListenerCallbackMethod;
const char* utf_string = env->GetStringUTFChars(path, NULL); const char* utf_string = env->GetStringUTFChars(path, NULL);
if (!utf_string) { if (! utf_string) {
return ZTS_ERR_GENERAL; return ZTS_ERR_GENERAL;
} }
// using _userCallbackMethodRef // using _userCallbackMethodRef
@@ -366,8 +378,7 @@ int zts_stop()
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
JNIEXPORT void JNICALL Java_com_zerotier_libzt_ZeroTier_stop( JNIEXPORT void JNICALL Java_com_zerotier_libzt_ZeroTier_stop(JNIEnv* env, jobject thisObj)
JNIEnv *env, jobject thisObj)
{ {
zts_stop(); zts_stop();
} }
@@ -414,8 +425,7 @@ int zts_restart()
#endif #endif
} }
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
JNIEXPORT void JNICALL Java_com_zerotier_libzt_ZeroTier_restart( JNIEXPORT void JNICALL Java_com_zerotier_libzt_ZeroTier_restart(JNIEnv* env, jobject thisObj)
JNIEnv *env, jobject thisObj)
{ {
zts_restart(); zts_restart();
} }
@@ -423,7 +433,7 @@ JNIEXPORT void JNICALL Java_com_zerotier_libzt_ZeroTier_restart(
int zts_free() int zts_free()
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (_getState(ZTS_STATE_FREE_CALLED)) { if (_getState(ZTS_STATE_FREE_CALLED)) {
@@ -436,8 +446,7 @@ int zts_free()
return err; return err;
} }
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
JNIEXPORT void JNICALL Java_com_zerotier_libzt_ZeroTier_free( JNIEXPORT void JNICALL Java_com_zerotier_libzt_ZeroTier_free(JNIEnv* env, jobject thisObj)
JNIEnv *env, jobject thisObj)
{ {
zts_free(); zts_free();
} }
@@ -448,8 +457,7 @@ JNIEXPORT void JNICALL Java_com_zerotier_libzt_ZeroTier_free(
* Called from Java, saves a static reference to the VM so it can be used * Called from Java, saves a static reference to the VM so it can be used
* later to call a user-specified callback method from C. * later to call a user-specified callback method from C.
*/ */
JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_init( JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_init(JNIEnv* env, jobject thisObj)
JNIEnv *env, jobject thisObj)
{ {
jint rs = env->GetJavaVM(&jvm); jint rs = env->GetJavaVM(&jvm);
return rs != JNI_OK ? ZTS_ERR_GENERAL : ZTS_ERR_OK; return rs != JNI_OK ? ZTS_ERR_GENERAL : ZTS_ERR_OK;
@@ -459,7 +467,7 @@ JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_init(
int zts_join(const uint64_t networkId) int zts_join(const uint64_t networkId)
{ {
Mutex::Lock _l(serviceLock); Mutex::Lock _l(serviceLock);
if (!_canPerformServiceOperation()) { if (! _canPerformServiceOperation()) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
else { else {
@@ -468,8 +476,8 @@ int zts_join(const uint64_t networkId)
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_join( JNIEXPORT jint JNICALL
JNIEnv *env, jobject thisObj, jlong networkId) Java_com_zerotier_libzt_ZeroTier_join(JNIEnv* env, jobject thisObj, jlong networkId)
{ {
return zts_join((uint64_t)networkId); return zts_join((uint64_t)networkId);
} }
@@ -478,7 +486,7 @@ JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_join(
int zts_leave(const uint64_t networkId) int zts_leave(const uint64_t networkId)
{ {
Mutex::Lock _l(serviceLock); Mutex::Lock _l(serviceLock);
if (!_canPerformServiceOperation()) { if (! _canPerformServiceOperation()) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
else { else {
@@ -487,8 +495,8 @@ int zts_leave(const uint64_t networkId)
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_leave( JNIEXPORT jint JNICALL
JNIEnv *env, jobject thisObj, jlong networkId) Java_com_zerotier_libzt_ZeroTier_leave(JNIEnv* env, jobject thisObj, jlong networkId)
{ {
return zts_leave((uint64_t)networkId); return zts_leave((uint64_t)networkId);
} }
@@ -497,10 +505,11 @@ JNIEXPORT jint JNICALL Java_com_zerotier_libzt_ZeroTier_leave(
int zts_orbit(uint64_t moonWorldId, uint64_t moonSeed) int zts_orbit(uint64_t moonWorldId, uint64_t moonSeed)
{ {
Mutex::Lock _l(serviceLock); Mutex::Lock _l(serviceLock);
void *tptr = NULL; void* tptr = NULL;
if (!_canPerformServiceOperation()) { if (! _canPerformServiceOperation()) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} else { }
else {
service->getNode()->orbit(tptr, moonWorldId, moonSeed); service->getNode()->orbit(tptr, moonWorldId, moonSeed);
} }
return ZTS_ERR_OK; return ZTS_ERR_OK;
@@ -511,10 +520,11 @@ int zts_orbit(uint64_t moonWorldId, uint64_t moonSeed)
int zts_deorbit(uint64_t moonWorldId) int zts_deorbit(uint64_t moonWorldId)
{ {
Mutex::Lock _l(serviceLock); Mutex::Lock _l(serviceLock);
void *tptr = NULL; void* tptr = NULL;
if (!_canPerformServiceOperation()) { if (! _canPerformServiceOperation()) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} else { }
else {
service->getNode()->deorbit(tptr, moonWorldId); service->getNode()->deorbit(tptr, moonWorldId);
} }
return ZTS_ERR_OK; return ZTS_ERR_OK;
@@ -522,24 +532,30 @@ int zts_deorbit(uint64_t moonWorldId)
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
#endif #endif
int zts_get_6plane_addr(struct zts_sockaddr_storage *addr, const uint64_t networkId, const uint64_t nodeId) int zts_get_6plane_addr(
struct zts_sockaddr_storage* addr,
const uint64_t networkId,
const uint64_t nodeId)
{ {
if (!addr || !networkId || !nodeId) { if (! addr || ! networkId || ! nodeId) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
InetAddress _6planeAddr = InetAddress::makeIpv66plane(networkId,nodeId); InetAddress _6planeAddr = InetAddress::makeIpv66plane(networkId, nodeId);
struct sockaddr_in6 *in6 = (struct sockaddr_in6*)addr; struct sockaddr_in6* in6 = (struct sockaddr_in6*)addr;
memcpy(in6->sin6_addr.s6_addr, _6planeAddr.rawIpData(), sizeof(struct in6_addr)); memcpy(in6->sin6_addr.s6_addr, _6planeAddr.rawIpData(), sizeof(struct in6_addr));
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
int zts_get_rfc4193_addr(struct zts_sockaddr_storage *addr, const uint64_t networkId, const uint64_t nodeId) int zts_get_rfc4193_addr(
struct zts_sockaddr_storage* addr,
const uint64_t networkId,
const uint64_t nodeId)
{ {
if (!addr || !networkId || !nodeId) { if (! addr || ! networkId || ! nodeId) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
InetAddress _rfc4193Addr = InetAddress::makeIpv6rfc4193(networkId,nodeId); InetAddress _rfc4193Addr = InetAddress::makeIpv6rfc4193(networkId, nodeId);
struct sockaddr_in6 *in6 = (struct sockaddr_in6*)addr; struct sockaddr_in6* in6 = (struct sockaddr_in6*)addr;
memcpy(in6->sin6_addr.s6_addr, _rfc4193Addr.rawIpData(), sizeof(struct in6_addr)); memcpy(in6->sin6_addr.s6_addr, _rfc4193Addr.rawIpData(), sizeof(struct in6_addr));
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
@@ -552,11 +568,11 @@ uint64_t zts_generate_adhoc_nwid_from_range(uint16_t startPortOfRange, uint16_t
} }
#ifdef __WINDOWS__ #ifdef __WINDOWS__
#include <windows.h> #include <windows.h>
#elif _POSIX_C_SOURCE >= 199309L #elif _POSIX_C_SOURCE >= 199309L
#include <time.h> // for nanosleep #include <time.h> // for nanosleep
#else #else
#include <unistd.h> // for usleep #include <unistd.h> // for usleep
#endif #endif
void zts_delay_ms(long milliseconds) void zts_delay_ms(long milliseconds)

View File

@@ -25,24 +25,26 @@
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
#if defined(__linux__) || defined(__APPLE__) #if defined(__linux__) || defined(__APPLE__)
#include <sys/syscall.h> #include <pthread.h>
#include <pthread.h> #include <sys/syscall.h>
#include <unistd.h> #include <unistd.h>
#endif #endif
#include <string.h> #include <string.h>
#define ZT_MSG_ERROR true // Errors #define ZT_MSG_ERROR true // Errors
#define ZT_MSG_INFO true // Information which is generally useful to any developer #define ZT_MSG_INFO true // Information which is generally useful to any developer
#define ZT_MSG_TEST true // For use in selftest #define ZT_MSG_TEST true // For use in selftest
#define ZT_MSG_TRANSFER true // RX/TX specific statements #define ZT_MSG_TRANSFER true // RX/TX specific statements
#define ZT_COLOR true #define ZT_COLOR true
// Debug output colors // Debug output colors
#if defined(__APPLE__) #if defined(__APPLE__)
#include "TargetConditionals.h" #include "TargetConditionals.h"
#endif #endif
#if defined(ZT_COLOR) && !defined(_WIN32) && !defined(__ANDROID__) && !defined(TARGET_OS_IPHONE) && !defined(TARGET_IPHONE_SIMULATOR) && !defined(__APP_FRAMEWORK__) #if defined(ZT_COLOR) && ! defined(_WIN32) && ! defined(__ANDROID__) \
&& ! defined(TARGET_OS_IPHONE) && ! defined(TARGET_IPHONE_SIMULATOR) \
&& ! defined(__APP_FRAMEWORK__)
#define ZT_RED "\x1B[31m" #define ZT_RED "\x1B[31m"
#define ZT_GRN "\x1B[32m" #define ZT_GRN "\x1B[32m"
#define ZT_YEL "\x1B[33m" #define ZT_YEL "\x1B[33m"
@@ -62,28 +64,47 @@
#define ZT_RESET #define ZT_RESET
#endif #endif
#define ZT_FILENAME (strrchr(__FILE__, '/') ? strrchr(__FILE__, '/') + 1 : __FILE__) // short #define ZT_FILENAME (strrchr(__FILE__, '/') ? strrchr(__FILE__, '/') + 1 : __FILE__) // short
#if defined(__JNI_LIB__) #if defined(__JNI_LIB__)
#include <jni.h> #include <jni.h>
#endif #endif
#if defined(__ANDROID__) #if defined(__ANDROID__)
#include <android/log.h> #include <android/log.h>
#define ZT_LOG_TAG "ZTSDK" #define ZT_LOG_TAG "ZTSDK"
#endif #endif
#if defined(LIBZT_DEBUG) || defined(LIBZT_TRACE) || defined(__NATIVETEST__) #if defined(LIBZT_DEBUG) || defined(LIBZT_TRACE) || defined(__NATIVETEST__)
// //
#if ZT_MSG_ERROR == true #if ZT_MSG_ERROR == true
#if defined(__ANDROID__) #if defined(__ANDROID__)
#define DEBUG_ERROR(fmt, args...) ((void)__android_log_print(ANDROID_LOG_VERBOSE, ZT_LOG_TAG, \ #define DEBUG_ERROR(fmt, args...) \
"%17s:%5d:%20s: " fmt "\n", ZT_FILENAME, __LINE__, __FUNCTION__, ##args)) ((void)__android_log_print( \
ANDROID_LOG_VERBOSE, \
ZT_LOG_TAG, \
"%17s:%5d:%20s: " fmt "\n", \
ZT_FILENAME, \
__LINE__, \
__FUNCTION__, \
##args))
#elif defined(_WIN32) #elif defined(_WIN32)
#define DEBUG_ERROR(fmt, ...) fprintf(stderr, ZT_RED "%17s:%5d:%25s: " fmt "\n" \ #define DEBUG_ERROR(fmt, ...) \
ZT_RESET, ZT_FILENAME, __LINE__, __FUNCTION__, __VA_ARGS__) fprintf( \
stderr, \
ZT_RED "%17s:%5d:%25s: " fmt "\n" ZT_RESET, \
ZT_FILENAME, \
__LINE__, \
__FUNCTION__, \
__VA_ARGS__)
#else #else
#define DEBUG_ERROR(fmt, args ...) fprintf(stderr, ZT_RED "%17s:%5d:%25s: " fmt "\n" \ #define DEBUG_ERROR(fmt, args...) \
ZT_RESET, ZT_FILENAME, __LINE__, __FUNCTION__, ##args) fprintf( \
stderr, \
ZT_RED "%17s:%5d:%25s: " fmt "\n" ZT_RESET, \
ZT_FILENAME, \
__LINE__, \
__FUNCTION__, \
##args)
#endif #endif
#else #else
#define DEBUG_ERROR(fmt, args...) #define DEBUG_ERROR(fmt, args...)
@@ -92,14 +113,33 @@
// //
#if ZT_MSG_TEST == true #if ZT_MSG_TEST == true
#if defined(__ANDROID__) #if defined(__ANDROID__)
#define DEBUG_TEST(fmt, args...) ((void)__android_log_print(ANDROID_LOG_VERBOSE, ZT_LOG_TAG, \ #define DEBUG_TEST(fmt, args...) \
"%17s:%5d:%25s: " fmt "\n", ZT_FILENAME, __LINE__, __FUNCTION__, ##args)) ((void)__android_log_print( \
ANDROID_LOG_VERBOSE, \
ZT_LOG_TAG, \
"%17s:%5d:%25s: " fmt "\n", \
ZT_FILENAME, \
__LINE__, \
__FUNCTION__, \
##args))
#elif defined(_WIN32) #elif defined(_WIN32)
#define DEBUG_TEST(fmt, ...) fprintf(stderr, ZT_CYN "%17s:%5d:%25s: " fmt "\n" \ #define DEBUG_TEST(fmt, ...) \
ZT_RESET, ZT_FILENAME, __LINE__, __FUNCTION__, __VA_ARGS__) fprintf( \
stderr, \
ZT_CYN "%17s:%5d:%25s: " fmt "\n" ZT_RESET, \
ZT_FILENAME, \
__LINE__, \
__FUNCTION__, \
__VA_ARGS__)
#else #else
#define DEBUG_TEST(fmt, args ...) fprintf(stderr, ZT_CYN "%17s:%5d:%25s: " fmt "\n" \ #define DEBUG_TEST(fmt, args...) \
ZT_RESET, ZT_FILENAME, __LINE__, __FUNCTION__, ##args) fprintf( \
stderr, \
ZT_CYN "%17s:%5d:%25s: " fmt "\n" ZT_RESET, \
ZT_FILENAME, \
__LINE__, \
__FUNCTION__, \
##args)
#endif #endif
#else #else
#define DEBUG_TEST(fmt, args...) #define DEBUG_TEST(fmt, args...)
@@ -108,14 +148,33 @@
// //
#if ZT_MSG_INFO == true #if ZT_MSG_INFO == true
#if defined(__ANDROID__) #if defined(__ANDROID__)
#define DEBUG_INFO(fmt, args...) ((void)__android_log_print(ANDROID_LOG_VERBOSE, ZT_LOG_TAG, \ #define DEBUG_INFO(fmt, args...) \
"%17s:%5d:%20s: " fmt "\n", ZT_FILENAME, __LINE__, __FUNCTION__, ##args)) ((void)__android_log_print( \
ANDROID_LOG_VERBOSE, \
ZT_LOG_TAG, \
"%17s:%5d:%20s: " fmt "\n", \
ZT_FILENAME, \
__LINE__, \
__FUNCTION__, \
##args))
#elif defined(_WIN32) #elif defined(_WIN32)
#define DEBUG_INFO(fmt, ...) fprintf(stderr, ZT_WHT "%17s:%5d:%25s: " fmt "\n" \ #define DEBUG_INFO(fmt, ...) \
ZT_RESET, ZT_FILENAME, __LINE__, __FUNCTION__, __VA_ARGS__) fprintf( \
stderr, \
ZT_WHT "%17s:%5d:%25s: " fmt "\n" ZT_RESET, \
ZT_FILENAME, \
__LINE__, \
__FUNCTION__, \
__VA_ARGS__)
#else #else
#define DEBUG_INFO(fmt, args ...) fprintf(stderr, ZT_WHT "%17s:%5d:%25s: " fmt "\n" \ #define DEBUG_INFO(fmt, args...) \
ZT_RESET, ZT_FILENAME, __LINE__, __FUNCTION__, ##args) fprintf( \
stderr, \
ZT_WHT "%17s:%5d:%25s: " fmt "\n" ZT_RESET, \
ZT_FILENAME, \
__LINE__, \
__FUNCTION__, \
##args)
#endif #endif
#else #else
#define DEBUG_INFO(fmt, args...) #define DEBUG_INFO(fmt, args...)
@@ -124,19 +183,38 @@
// //
#if ZT_MSG_TRANSFER == true #if ZT_MSG_TRANSFER == true
#if defined(__ANDROID__) #if defined(__ANDROID__)
#define DEBUG_TRANS(fmt, args...) ((void)__android_log_print(ANDROID_LOG_VERBOSE, ZT_LOG_TAG, \ #define DEBUG_TRANS(fmt, args...) \
"%17s:%5d:%25s: " fmt "\n", ZT_FILENAME, __LINE__, __FUNCTION__, ##args)) ((void)__android_log_print( \
ANDROID_LOG_VERBOSE, \
ZT_LOG_TAG, \
"%17s:%5d:%25s: " fmt "\n", \
ZT_FILENAME, \
__LINE__, \
__FUNCTION__, \
##args))
#elif defined(_WIN32) #elif defined(_WIN32)
#define DEBUG_TRANS(fmt, ...) fprintf(stderr, ZT_GRN "%17s:%5d:%25s: " fmt "\n" \ #define DEBUG_TRANS(fmt, ...) \
ZT_RESET, ZT_FILENAME, __LINE__, __FUNCTION__, __VA_ARGS__) fprintf( \
stderr, \
ZT_GRN "%17s:%5d:%25s: " fmt "\n" ZT_RESET, \
ZT_FILENAME, \
__LINE__, \
__FUNCTION__, \
__VA_ARGS__)
#else #else
#define DEBUG_TRANS(fmt, args ...) fprintf(stderr, ZT_GRN "%17s:%5d:%25s: " fmt "\n" \ #define DEBUG_TRANS(fmt, args...) \
ZT_RESET, ZT_FILENAME, __LINE__, __FUNCTION__, ##args) fprintf( \
stderr, \
ZT_GRN "%17s:%5d:%25s: " fmt "\n" ZT_RESET, \
ZT_FILENAME, \
__LINE__, \
__FUNCTION__, \
##args)
#endif #endif
#else #else
#define DEBUG_TRANS(fmt, args...) #define DEBUG_TRANS(fmt, args...)
#endif #endif
#else // !LIBZT_DEBUG || !__NATIVE_TEST__ #else // !LIBZT_DEBUG || !__NATIVE_TEST__
#if defined(_WIN32) #if defined(_WIN32)
#define DEBUG_ERROR(...) #define DEBUG_ERROR(...)
#define DEBUG_TEST(...) #define DEBUG_TEST(...)
@@ -150,4 +228,4 @@
#endif #endif
#endif #endif
#endif // _H #endif // _H

View File

@@ -24,31 +24,33 @@
#endif #endif
#include "Constants.hpp" #include "Constants.hpp"
#include "Node.hpp"
#include "OSUtils.hpp"
#include "Debug.hpp" #include "Debug.hpp"
#include "Events.hpp" #include "Events.hpp"
#include "ZeroTierSockets.h" #include "Node.hpp"
#include "NodeService.hpp" #include "NodeService.hpp"
#include "OSUtils.hpp"
#include "ZeroTierSockets.h"
#define NODE_EVENT_TYPE(code) code >= ZTS_EVENT_NODE_UP && code <= ZTS_EVENT_NODE_NORMAL_TERMINATION #define NODE_EVENT_TYPE(code) code >= ZTS_EVENT_NODE_UP&& code <= ZTS_EVENT_NODE_NORMAL_TERMINATION
#define NETWORK_EVENT_TYPE(code) code >= ZTS_EVENT_NETWORK_NOT_FOUND && code <= ZTS_EVENT_NETWORK_UPDATE #define NETWORK_EVENT_TYPE(code) \
#define STACK_EVENT_TYPE(code) code >= ZTS_EVENT_STACK_UP && code <= ZTS_EVENT_STACK_DOWN code >= ZTS_EVENT_NETWORK_NOT_FOUND&& code <= ZTS_EVENT_NETWORK_UPDATE
#define NETIF_EVENT_TYPE(code) code >= ZTS_EVENT_NETIF_UP && code <= ZTS_EVENT_NETIF_LINK_DOWN #define STACK_EVENT_TYPE(code) code >= ZTS_EVENT_STACK_UP&& code <= ZTS_EVENT_STACK_DOWN
#define PEER_EVENT_TYPE(code) code >= ZTS_EVENT_PEER_DIRECT && code <= ZTS_EVENT_PEER_PATH_DEAD #define NETIF_EVENT_TYPE(code) code >= ZTS_EVENT_NETIF_UP&& code <= ZTS_EVENT_NETIF_LINK_DOWN
#define ROUTE_EVENT_TYPE(code) code >= ZTS_EVENT_ROUTE_ADDED && code <= ZTS_EVENT_ROUTE_REMOVED #define PEER_EVENT_TYPE(code) code >= ZTS_EVENT_PEER_DIRECT&& code <= ZTS_EVENT_PEER_PATH_DEAD
#define ADDR_EVENT_TYPE(code) code >= ZTS_EVENT_ADDR_ADDED_IP4 && code <= ZTS_EVENT_ADDR_REMOVED_IP6 #define ROUTE_EVENT_TYPE(code) code >= ZTS_EVENT_ROUTE_ADDED&& code <= ZTS_EVENT_ROUTE_REMOVED
#define ADDR_EVENT_TYPE(code) code >= ZTS_EVENT_ADDR_ADDED_IP4&& code <= ZTS_EVENT_ADDR_REMOVED_IP6
#ifdef ZTS_ENABLE_PYTHON #ifdef ZTS_ENABLE_PYTHON
#include "Python.h" #include "Python.h"
PythonDirectorCallbackClass *_userEventCallback = NULL; PythonDirectorCallbackClass* _userEventCallback = NULL;
void PythonDirectorCallbackClass::on_zerotier_event(struct zts_callback_msg *msg) { } void PythonDirectorCallbackClass::on_zerotier_event(struct zts_callback_msg* msg)
{
}
#endif #endif
namespace ZeroTier { namespace ZeroTier {
extern NodeService *service; extern NodeService* service;
// Global state variable shared between Socket, Control, Event and NodeService logic. // Global state variable shared between Socket, Control, Event and NodeService logic.
uint8_t _serviceStateFlags; uint8_t _serviceStateFlags;
@@ -57,32 +59,38 @@ uint8_t _serviceStateFlags;
Mutex _callbackLock; Mutex _callbackLock;
#ifdef ZTS_ENABLE_PINVOKE #ifdef ZTS_ENABLE_PINVOKE
void (*_userEventCallback)(void *); void (*_userEventCallback)(void*);
#endif #endif
#ifdef ZTS_C_API_ONLY #ifdef ZTS_C_API_ONLY
void (*_userEventCallback)(void *); void (*_userEventCallback)(void*);
#endif #endif
moodycamel::ConcurrentQueue<struct zts_callback_msg*> _callbackMsgQueue; moodycamel::ConcurrentQueue<struct zts_callback_msg*> _callbackMsgQueue;
void _enqueueEvent(int16_t eventCode, void *arg) void _enqueueEvent(int16_t eventCode, void* arg)
{ {
struct zts_callback_msg *msg = new zts_callback_msg(); struct zts_callback_msg* msg = new zts_callback_msg();
msg->eventCode = eventCode; msg->eventCode = eventCode;
if (NODE_EVENT_TYPE(eventCode)) { if (NODE_EVENT_TYPE(eventCode)) {
msg->node = (struct zts_node_details*)arg; msg->node = (struct zts_node_details*)arg;
} if (NETWORK_EVENT_TYPE(eventCode)) { }
if (NETWORK_EVENT_TYPE(eventCode)) {
msg->network = (struct zts_network_details*)arg; msg->network = (struct zts_network_details*)arg;
} if (STACK_EVENT_TYPE(eventCode)) { }
if (STACK_EVENT_TYPE(eventCode)) {
/* nothing to convey to user */ /* nothing to convey to user */
} if (NETIF_EVENT_TYPE(eventCode)) { }
if (NETIF_EVENT_TYPE(eventCode)) {
msg->netif = (struct zts_netif_details*)arg; msg->netif = (struct zts_netif_details*)arg;
} if (ROUTE_EVENT_TYPE(eventCode)) { }
if (ROUTE_EVENT_TYPE(eventCode)) {
msg->route = (struct zts_virtual_network_route*)arg; msg->route = (struct zts_virtual_network_route*)arg;
} if (PEER_EVENT_TYPE(eventCode)) { }
if (PEER_EVENT_TYPE(eventCode)) {
msg->peer = (struct zts_peer_details*)arg; msg->peer = (struct zts_peer_details*)arg;
} if (ADDR_EVENT_TYPE(eventCode)) { }
if (ADDR_EVENT_TYPE(eventCode)) {
msg->addr = (struct zts_addr_details*)arg; msg->addr = (struct zts_addr_details*)arg;
} }
@@ -95,20 +103,32 @@ void _enqueueEvent(int16_t eventCode, void *arg)
} }
} }
void _freeEvent(struct zts_callback_msg *msg) void _freeEvent(struct zts_callback_msg* msg)
{ {
if (!msg) { if (! msg) {
return; return;
} }
if (msg->node) { delete msg->node; } if (msg->node) {
if (msg->network) { delete msg->network; } delete msg->node;
if (msg->netif) { delete msg->netif; } }
if (msg->route) { delete msg->route; } if (msg->network) {
if (msg->peer) { delete msg->peer; } delete msg->network;
if (msg->addr) { delete msg->addr; } }
if (msg->netif) {
delete msg->netif;
}
if (msg->route) {
delete msg->route;
}
if (msg->peer) {
delete msg->peer;
}
if (msg->addr) {
delete msg->addr;
}
} }
void _passDequeuedEventToUser(struct zts_callback_msg *msg) void _passDequeuedEventToUser(struct zts_callback_msg* msg)
{ {
bool bShouldStopCallbackThread = (msg->eventCode == ZTS_EVENT_STACK_DOWN); bool bShouldStopCallbackThread = (msg->eventCode == ZTS_EVENT_STACK_DOWN);
#ifdef ZTS_ENABLE_PYTHON #ifdef ZTS_ENABLE_PYTHON
@@ -117,14 +137,14 @@ void _passDequeuedEventToUser(struct zts_callback_msg *msg)
PyGILState_Release(state); PyGILState_Release(state);
#endif #endif
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
if(_userCallbackMethodRef) { if (_userCallbackMethodRef) {
JNIEnv *env; JNIEnv* env;
#if defined(__ANDROID__) #if defined(__ANDROID__)
jint rs = jvm->AttachCurrentThread(&env, NULL); jint rs = jvm->AttachCurrentThread(&env, NULL);
#else #else
jint rs = jvm->AttachCurrentThread((void **)&env, NULL); jint rs = jvm->AttachCurrentThread((void**)&env, NULL);
#endif #endif
assert (rs == JNI_OK); assert(rs == JNI_OK);
uint64_t arg = 0; uint64_t arg = 0;
uint64_t id = 0; uint64_t id = 0;
if (NODE_EVENT_TYPE(msg->eventCode)) { if (NODE_EVENT_TYPE(msg->eventCode)) {
@@ -138,7 +158,7 @@ void _passDequeuedEventToUser(struct zts_callback_msg *msg)
} }
env->CallVoidMethod(objRef, _userCallbackMethodRef, id, msg->eventCode); env->CallVoidMethod(objRef, _userCallbackMethodRef, id, msg->eventCode);
} }
#endif // ZTS_ENABLE_JAVA #endif // ZTS_ENABLE_JAVA
#ifdef ZTS_ENABLE_PINVOKE #ifdef ZTS_ENABLE_PINVOKE
if (_userEventCallback) { if (_userEventCallback) {
_userEventCallback(msg); _userEventCallback(msg);
@@ -175,7 +195,7 @@ void _clearRegisteredCallback()
_callbackLock.lock(); _callbackLock.lock();
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
objRef = NULL; objRef = NULL;
_userCallbackMethodRef = NULL; _userCallbackMethodRef = NULL;
#else #else
_userEventCallback = NULL; _userEventCallback = NULL;
#endif #endif
@@ -184,28 +204,23 @@ void _clearRegisteredCallback()
int _canPerformServiceOperation() int _canPerformServiceOperation()
{ {
return service return service && service->isRunning() && service->getNode() && service->getNode()->online()
&& service->isRunning() && ! _getState(ZTS_STATE_FREE_CALLED);
&& service->getNode()
&& service->getNode()->online()
&& !_getState(ZTS_STATE_FREE_CALLED);
} }
#define RESET_FLAGS( ) _serviceStateFlags = 0; #define RESET_FLAGS() _serviceStateFlags = 0;
#define SET_FLAGS(f) _serviceStateFlags |= f; #define SET_FLAGS(f) _serviceStateFlags |= f;
#define CLR_FLAGS(f) _serviceStateFlags &= ~f; #define CLR_FLAGS(f) _serviceStateFlags &= ~f;
#define GET_FLAGS(f) ((_serviceStateFlags & f) > 0) #define GET_FLAGS(f) ((_serviceStateFlags & f) > 0)
void _setState(uint8_t newFlags) void _setState(uint8_t newFlags)
{ {
if ((newFlags ^ _serviceStateFlags) & ZTS_STATE_NET_SERVICE_RUNNING) { if ((newFlags ^ _serviceStateFlags) & ZTS_STATE_NET_SERVICE_RUNNING) {
return; // No effect. Not allowed to set this flag manually return; // No effect. Not allowed to set this flag manually
} }
SET_FLAGS(newFlags); SET_FLAGS(newFlags);
if ( GET_FLAGS(ZTS_STATE_NODE_RUNNING) if (GET_FLAGS(ZTS_STATE_NODE_RUNNING) && GET_FLAGS(ZTS_STATE_STACK_RUNNING)
&& GET_FLAGS(ZTS_STATE_STACK_RUNNING) && ! (GET_FLAGS(ZTS_STATE_FREE_CALLED))) {
&& !(GET_FLAGS(ZTS_STATE_FREE_CALLED)))
{
SET_FLAGS(ZTS_STATE_NET_SERVICE_RUNNING); SET_FLAGS(ZTS_STATE_NET_SERVICE_RUNNING);
} }
else { else {
@@ -216,13 +231,11 @@ void _setState(uint8_t newFlags)
void _clrState(uint8_t newFlags) void _clrState(uint8_t newFlags)
{ {
if (newFlags & ZTS_STATE_NET_SERVICE_RUNNING) { if (newFlags & ZTS_STATE_NET_SERVICE_RUNNING) {
return; // No effect. Not allowed to set this flag manually return; // No effect. Not allowed to set this flag manually
} }
CLR_FLAGS(newFlags); CLR_FLAGS(newFlags);
if ( GET_FLAGS(ZTS_STATE_NODE_RUNNING) if (GET_FLAGS(ZTS_STATE_NODE_RUNNING) && GET_FLAGS(ZTS_STATE_STACK_RUNNING)
&& GET_FLAGS(ZTS_STATE_STACK_RUNNING) && ! (GET_FLAGS(ZTS_STATE_FREE_CALLED))) {
&& !(GET_FLAGS(ZTS_STATE_FREE_CALLED)))
{
SET_FLAGS(ZTS_STATE_NET_SERVICE_RUNNING); SET_FLAGS(ZTS_STATE_NET_SERVICE_RUNNING);
} }
else { else {
@@ -238,15 +251,14 @@ bool _getState(uint8_t testFlags)
#if defined(__WINDOWS__) #if defined(__WINDOWS__)
DWORD WINAPI _runCallbacks(LPVOID thread_id) DWORD WINAPI _runCallbacks(LPVOID thread_id)
#else #else
void *_runCallbacks(void *thread_id) void* _runCallbacks(void* thread_id)
#endif #endif
{ {
#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 (_getState(ZTS_STATE_CALLBACKS_RUNNING) || _callbackMsgQueue.size_approx() > 0) while (_getState(ZTS_STATE_CALLBACKS_RUNNING) || _callbackMsgQueue.size_approx() > 0) {
{ struct zts_callback_msg* msg;
struct zts_callback_msg *msg;
size_t sz = _callbackMsgQueue.size_approx(); size_t sz = _callbackMsgQueue.size_approx();
for (size_t j = 0; j < sz; j++) { for (size_t j = 0; j < sz; j++) {
if (_callbackMsgQueue.try_dequeue(msg)) { if (_callbackMsgQueue.try_dequeue(msg)) {
@@ -256,14 +268,14 @@ void *_runCallbacks(void *thread_id)
delete msg; delete msg;
} }
} }
zts_delay_ms(ZTS_CALLBACK_PROCESSING_INTERVAL); zts_delay_ms(ZTS_CALLBACK_PROCESSING_INTERVAL);
} }
#if ZTS_ENABLE_JAVA #if ZTS_ENABLE_JAVA
JNIEnv *env; JNIEnv* env;
jint rs = jvm->DetachCurrentThread(); jint rs = jvm->DetachCurrentThread();
pthread_exit(0); pthread_exit(0);
#endif #endif
return NULL; return NULL;
} }
} // namespace ZeroTier } // namespace ZeroTier

View File

@@ -20,13 +20,13 @@
#ifndef ZT_EVENTS_HPP #ifndef ZT_EVENTS_HPP
#define ZT_EVENTS_HPP #define ZT_EVENTS_HPP
#include <string>
#include "Constants.hpp" #include "Constants.hpp"
#include "ZeroTierSockets.h" #include "ZeroTierSockets.h"
#include <string>
#ifdef __WINDOWS__ #ifdef __WINDOWS__
#include <BaseTsd.h> #include <BaseTsd.h>
#endif #endif
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
@@ -34,17 +34,17 @@
#endif #endif
namespace ZeroTier { namespace ZeroTier {
#define ZTS_STATE_NODE_RUNNING 0x01 #define ZTS_STATE_NODE_RUNNING 0x01
#define ZTS_STATE_STACK_RUNNING 0x02 #define ZTS_STATE_STACK_RUNNING 0x02
#define ZTS_STATE_NET_SERVICE_RUNNING 0x04 #define ZTS_STATE_NET_SERVICE_RUNNING 0x04
#define ZTS_STATE_CALLBACKS_RUNNING 0x08 #define ZTS_STATE_CALLBACKS_RUNNING 0x08
#define ZTS_STATE_FREE_CALLED 0x10 #define ZTS_STATE_FREE_CALLED 0x10
#ifdef ZTS_ENABLE_JAVA #ifdef ZTS_ENABLE_JAVA
// References to JNI objects and VM kept for future callbacks // References to JNI objects and VM kept for future callbacks
extern JavaVM *jvm; extern JavaVM* jvm;
extern jobject objRef; extern jobject objRef;
extern jmethodID _userCallbackMethodRef; extern jmethodID _userCallbackMethodRef;
#endif #endif
/** /**
@@ -55,17 +55,17 @@ namespace ZeroTier {
/** /**
* Enqueue an event to be sent to the user application * Enqueue an event to be sent to the user application
*/ */
void _enqueueEvent(int16_t eventCode, void *arg); void _enqueueEvent(int16_t eventCode, void* arg);
/** /**
* Send callback message to user application * Send callback message to user application
*/ */
void _passDequeuedEventToUser(struct ::zts_callback_msg *msg); void _passDequeuedEventToUser(struct ::zts_callback_msg* msg);
/** /**
* Free memory occupied by callback structures * Free memory occupied by callback structures
*/ */
void _freeEvent(struct ::zts_callback_msg *msg); void _freeEvent(struct ::zts_callback_msg* msg);
/** /**
* Return whether a callback method has been set * Return whether a callback method has been set
@@ -103,9 +103,9 @@ DWORD WINAPI _runCallbacks(LPVOID thread_id);
/** /**
* Event callback thread * Event callback thread
*/ */
void *_runCallbacks(void *thread_id); void* _runCallbacks(void* thread_id);
#endif #endif
} // namespace ZeroTier } // namespace ZeroTier
#endif // _H #endif // _H

File diff suppressed because it is too large Load Diff

View File

@@ -20,27 +20,27 @@
#ifndef ZT_NODE_SERVICE_HPP #ifndef ZT_NODE_SERVICE_HPP
#define ZT_NODE_SERVICE_HPP #define ZT_NODE_SERVICE_HPP
#include "Constants.hpp"
#include "InetAddress.hpp"
#include "Mutex.hpp"
#include "Node.hpp"
#include "ZeroTierSockets.h"
#include <string> #include <string>
#include <vector> #include <vector>
#include "Constants.hpp" #define ZTS_SERVICE_THREAD_NAME "ZTServiceThread"
#include "Node.hpp" #define ZTS_EVENT_CALLBACK_THREAD_NAME "ZTEventCallbackThread"
#include "InetAddress.hpp"
#include "Mutex.hpp"
#include "ZeroTierSockets.h"
#define ZTS_SERVICE_THREAD_NAME "ZTServiceThread"
#define ZTS_EVENT_CALLBACK_THREAD_NAME "ZTEventCallbackThread"
// Interface metric for ZeroTier taps -- this ensures that if we are on WiFi and also // Interface metric for ZeroTier taps -- this ensures that if we are on WiFi and also
// bridged via ZeroTier to the same LAN traffic will (if the OS is sane) prefer WiFi. // bridged via ZeroTier to the same LAN traffic will (if the OS is sane) prefer WiFi.
#define ZT_IF_METRIC 5000 #define ZT_IF_METRIC 5000
// How often to check for new multicast subscriptions on a tap device // How often to check for new multicast subscriptions on a tap device
#define ZT_TAP_CHECK_MULTICAST_INTERVAL 5000 #define ZT_TAP_CHECK_MULTICAST_INTERVAL 5000
// How often to check for local interface addresses // How often to check for local interface addresses
#define ZT_LOCAL_INTERFACE_CHECK_INTERVAL 60000 #define ZT_LOCAL_INTERFACE_CHECK_INTERVAL 60000
#ifdef __WINDOWS__ #ifdef __WINDOWS__
#include <Windows.h> #include <Windows.h>
#endif #endif
namespace ZeroTier { namespace ZeroTier {
@@ -48,10 +48,8 @@ namespace ZeroTier {
/** /**
* Local service for ZeroTier One as system VPN/NFV provider * Local service for ZeroTier One as system VPN/NFV provider
*/ */
class NodeService class NodeService {
{ public:
public:
uint16_t _userProvidedPort; uint16_t _userProvidedPort;
std::string _userProvidedPath; std::string _userProvidedPath;
char _userProvidedPublicIdentity[ZT_IDENTITY_STRING_BUFFER_LENGTH]; char _userProvidedPublicIdentity[ZT_IDENTITY_STRING_BUFFER_LENGTH];
@@ -60,8 +58,7 @@ public:
/** /**
* Returned by node main if/when it terminates * Returned by node main if/when it terminates
*/ */
enum ReasonForTermination enum ReasonForTermination {
{
/** /**
* Instance is still running * Instance is still running
*/ */
@@ -86,8 +83,7 @@ public:
/** /**
* Local settings for each network * Local settings for each network
*/ */
struct NetworkSettings struct NetworkSettings {
{
/** /**
* Allow this network to configure IP addresses and routes? * Allow this network to configure IP addresses and routes?
*/ */
@@ -128,7 +124,7 @@ public:
* @param hp Home path * @param hp Home path
* @param port TCP and UDP port for packets and HTTP control (if 0, pick random port) * @param port TCP and UDP port for packets and HTTP control (if 0, pick random port)
*/ */
static NodeService *newInstance(const char *hp,unsigned int port); static NodeService* newInstance(const char* hp, unsigned int port);
virtual ~NodeService(); virtual ~NodeService();
@@ -152,7 +148,8 @@ public:
virtual std::string fatalErrorMessage() const = 0; virtual std::string fatalErrorMessage() const = 0;
/** /**
* @return System device name corresponding with a given ZeroTier network ID or empty string if not opened yet or network ID not found * @return System device name corresponding with a given ZeroTier network ID or empty string if
* not opened yet or network ID not found
*/ */
virtual std::string portDeviceName(uint64_t nwid) const = 0; virtual std::string portDeviceName(uint64_t nwid) const = 0;
@@ -164,16 +161,16 @@ public:
/** /**
* @return Reference to the Node * @return Reference to the Node
*/ */
virtual Node * getNode() = 0; virtual Node* getNode() = 0;
/** /**
* Fills out a structure with network-specific route information * Fills out a structure with network-specific route information
*/ */
virtual void getRoutes(uint64_t nwid, void *routeArray, unsigned int *numRoutes) = 0; virtual void getRoutes(uint64_t nwid, void* routeArray, unsigned int* numRoutes) = 0;
virtual void join(uint64_t nwid) = 0; virtual void join(uint64_t nwid) = 0;
virtual void leave(uint64_t nwid) = 0; virtual void leave(uint64_t nwid) = 0;
virtual void getIdentity(char *key_pair_str, uint16_t *key_buf_len) = 0; virtual void getIdentity(char* key_pair_str, uint16_t* key_buf_len) = 0;
/** /**
* Terminate background service (can be called from other threads) * Terminate background service (can be called from other threads)
@@ -187,23 +184,32 @@ public:
* @param settings Buffer to fill with local network settings * @param settings Buffer to fill with local network settings
* @return True if network was found and settings is filled * @return True if network was found and settings is filled
*/ */
virtual bool getNetworkSettings(const uint64_t nwid,NetworkSettings &settings) const = 0; virtual bool getNetworkSettings(const uint64_t nwid, NetworkSettings& settings) const = 0;
/** /**
* @return True if service is still running * @return True if service is still running
*/ */
inline bool isRunning() const { return (this->reasonForTermination() == ONE_STILL_RUNNING); } inline bool isRunning() const
{
return (this->reasonForTermination() == ONE_STILL_RUNNING);
}
protected: protected:
NodeService() {} NodeService()
{
}
private: private:
NodeService(const NodeService &one) {} NodeService(const NodeService& one)
inline NodeService &operator=(const NodeService &one) { return *this; } {
}
inline NodeService& operator=(const NodeService& one)
{
return *this;
}
}; };
struct serviceParameters struct serviceParameters {
{
int port; int port;
std::string path; std::string path;
char publicIdentityStr[ZT_IDENTITY_STRING_BUFFER_LENGTH]; char publicIdentityStr[ZT_IDENTITY_STRING_BUFFER_LENGTH];
@@ -216,9 +222,9 @@ DWORD WINAPI _runNodeService(LPVOID arg);
/** /**
* NodeService thread * NodeService thread
*/ */
void *_runNodeService(void *arg); void* _runNodeService(void* arg);
#endif #endif
} // namespace ZeroTier } // namespace ZeroTier
#endif #endif

View File

@@ -18,22 +18,23 @@
*/ */
#ifdef ZTS_ENABLE_PYTHON #ifdef ZTS_ENABLE_PYTHON
/** /**
* In some situations (Python comes to mind) a signal may not make its * In some situations (Python comes to mind) a signal may not make its
* way to libzt, for this reason we make sure to define a custom signal * way to libzt, for this reason we make sure to define a custom signal
* handler that can at least process SIGTERMs * handler that can at least process SIGTERMs
*/ */
#define ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS 1 #define ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS 1
#endif #endif
#ifdef ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS #ifdef ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS
#include "ZeroTierSockets.h" #include "Signals.hpp"
#include "Signals.hpp"
#include <signal.h> #include "ZeroTierSockets.h"
#include <execinfo.h>
#include <cstdlib> #include <cstdlib>
#include <execinfo.h>
#include <signal.h>
void _signal_handler(int signal) void _signal_handler(int signal)
{ {
@@ -41,24 +42,24 @@ void _signal_handler(int signal)
switch(signal) switch(signal)
{ {
case SIGINT: case SIGINT:
fprintf(stderr, "SIGINT\n"); fprintf(stderr, "SIGINT\n");
break; break;
case SIGABRT: case SIGABRT:
fprintf(stderr, "SIGABRT\n"); fprintf(stderr, "SIGABRT\n");
break; break;
case SIGILL: case SIGILL:
fprintf(stderr, "SIGILL\n"); fprintf(stderr, "SIGILL\n");
break; break;
case SIGSEGV: case SIGSEGV:
fprintf(stderr, "SIGSEGV\n"); fprintf(stderr, "SIGSEGV\n");
break; break;
case SIGFPE: case SIGFPE:
fprintf(stderr, "SIGFPE\n"); fprintf(stderr, "SIGFPE\n");
break; break;
case SIGTERM: case SIGTERM:
default: default:
fprintf(stderr, "SIGTERM\n"); fprintf(stderr, "SIGTERM\n");
break; break;
} }
*/ */
exit(signal); exit(signal);

View File

@@ -36,6 +36,6 @@ void _signal_handler(int signal);
*/ */
void _install_signal_handlers(); void _install_signal_handlers();
#endif // ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS #endif // ZTS_ENABLE_CUSTOM_SIGNAL_HANDLERS
#endif // _H #endif // _H

View File

@@ -18,14 +18,14 @@
*/ */
#include "lwip/sockets.h" #include "lwip/sockets.h"
#include "lwip/def.h"
#include "lwip/inet.h"
#include "lwip/stats.h"
#include "lwip/netdb.h"
#include "lwip/dns.h"
#include "lwip/ip_addr.h"
#include "ZeroTierSockets.h" #include "ZeroTierSockets.h"
#include "lwip/def.h"
#include "lwip/dns.h"
#include "lwip/inet.h"
#include "lwip/ip_addr.h"
#include "lwip/netdb.h"
#include "lwip/stats.h"
#define ZTS_STATE_NODE_RUNNING 0x01 #define ZTS_STATE_NODE_RUNNING 0x01
#define ZTS_STATE_STACK_RUNNING 0x02 #define ZTS_STATE_STACK_RUNNING 0x02
@@ -45,54 +45,53 @@ extern "C" {
int zts_socket(const int socket_family, const int socket_type, const int protocol) int zts_socket(const int socket_family, const int socket_type, const int protocol)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
return lwip_socket(socket_family, socket_type, protocol); return lwip_socket(socket_family, socket_type, protocol);
} }
int zts_connect(int fd, const struct zts_sockaddr *addr, zts_socklen_t addrlen) int zts_connect(int fd, const struct zts_sockaddr* addr, zts_socklen_t addrlen)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (!addr) { if (! addr) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
if (addrlen > (int)sizeof(struct zts_sockaddr_storage) if (addrlen > (int)sizeof(struct zts_sockaddr_storage)
|| addrlen < (int)sizeof(struct zts_sockaddr_in)) { || addrlen < (int)sizeof(struct zts_sockaddr_in)) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return lwip_connect(fd, (sockaddr*)addr, addrlen); return lwip_connect(fd, (sockaddr*)addr, addrlen);
} }
int zts_connect_easy(int fd, int family, char *ipstr, int port, int timeout_ms) { int zts_connect_easy(int fd, int family, char* ipstr, int port, int timeout_ms)
{
if (timeout_ms < 0) { if (timeout_ms < 0) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
if (timeout_ms == 0) { if (timeout_ms == 0) {
timeout_ms = 30000; // Default timeout_ms = 30000; // Default
} }
int div = 4; // Must be > 0, Four connection attempts per second int div = 4; // Must be > 0, Four connection attempts per second
int n_tries = (timeout_ms / 1000) * div; int n_tries = (timeout_ms / 1000) * div;
int connect_delay = 1000 / div; int connect_delay = 1000 / div;
int err = ZTS_ERR_SOCKET; int err = ZTS_ERR_SOCKET;
zts_socklen_t addrlen = 0; zts_socklen_t addrlen = 0;
struct zts_sockaddr_storage ss; struct zts_sockaddr_storage ss;
struct zts_sockaddr *sa = NULL; struct zts_sockaddr* sa = NULL;
if (family == ZTS_AF_INET) { if (family == ZTS_AF_INET) {
addrlen = sizeof(ss); addrlen = sizeof(ss);
ipstr2sockaddr( ipstr2sockaddr(family, ipstr, port, (struct zts_sockaddr*)&ss, &addrlen);
family, ipstr, port, (struct zts_sockaddr *)&ss, &addrlen); sa = (struct zts_sockaddr*)&ss;
sa = (struct zts_sockaddr *)&ss;
} }
if (family == ZTS_AF_INET6) { if (family == ZTS_AF_INET6) {
addrlen = sizeof(ss); addrlen = sizeof(ss);
ipstr2sockaddr( ipstr2sockaddr(family, ipstr, port, (struct zts_sockaddr*)&ss, &addrlen);
family, ipstr, port, (struct zts_sockaddr *)&ss, &addrlen); sa = (struct zts_sockaddr*)&ss;
sa = (struct zts_sockaddr *)&ss;
} }
if (addrlen > 0 && sa != NULL) { if (addrlen > 0 && sa != NULL) {
if (zts_get_blocking(fd)) { if (zts_get_blocking(fd)) {
@@ -100,44 +99,42 @@ int zts_connect_easy(int fd, int family, char *ipstr, int port, int timeout_ms)
err = zts_connect(fd, sa, addrlen); err = zts_connect(fd, sa, addrlen);
zts_delay_ms(connect_delay); zts_delay_ms(connect_delay);
n_tries--; n_tries--;
} } while ((err < 0) && (zts_errno != 0) && (n_tries > 0));
while ((err < 0) && (zts_errno != 0) && (n_tries > 0));
} }
return err; return err;
} }
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
int zts_bind(int fd, const struct zts_sockaddr *addr, zts_socklen_t addrlen) int zts_bind(int fd, const struct zts_sockaddr* addr, zts_socklen_t addrlen)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (!addr) { if (! addr) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
if (addrlen > (int)sizeof(struct zts_sockaddr_storage) if (addrlen > (int)sizeof(struct zts_sockaddr_storage)
|| addrlen < (int)sizeof(struct zts_sockaddr_in)) { || addrlen < (int)sizeof(struct zts_sockaddr_in)) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return lwip_bind(fd, (sockaddr*)addr, addrlen); return lwip_bind(fd, (sockaddr*)addr, addrlen);
} }
int zts_bind_easy(int fd, int family, char *ipstr, int port) { int zts_bind_easy(int fd, int family, char* ipstr, int port)
{
if (family == ZTS_AF_INET) { if (family == ZTS_AF_INET) {
struct zts_sockaddr_in in4; struct zts_sockaddr_in in4;
zts_socklen_t addrlen = sizeof(in4); zts_socklen_t addrlen = sizeof(in4);
ipstr2sockaddr( ipstr2sockaddr(family, ipstr, port, (struct zts_sockaddr*)&in4, &addrlen);
family, ipstr, port, (struct zts_sockaddr *)&in4, &addrlen); struct zts_sockaddr* sa = (struct zts_sockaddr*)&in4;
struct zts_sockaddr *sa = (struct zts_sockaddr *)&in4;
return zts_bind(fd, sa, addrlen); return zts_bind(fd, sa, addrlen);
} }
if (family == ZTS_AF_INET6) { if (family == ZTS_AF_INET6) {
struct zts_sockaddr_in6 in6; struct zts_sockaddr_in6 in6;
zts_socklen_t addrlen = sizeof(in6); zts_socklen_t addrlen = sizeof(in6);
ipstr2sockaddr( ipstr2sockaddr(family, ipstr, port, (struct zts_sockaddr*)&in6, &addrlen);
family, ipstr, port, (struct zts_sockaddr *)&in6, &addrlen); struct zts_sockaddr* sa = (struct zts_sockaddr*)&in6;
struct zts_sockaddr *sa = (struct zts_sockaddr *)&in6;
return zts_bind(fd, sa, addrlen); return zts_bind(fd, sa, addrlen);
} }
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
@@ -145,21 +142,21 @@ int zts_bind_easy(int fd, int family, char *ipstr, int port) {
int zts_listen(int fd, int backlog) int zts_listen(int fd, int backlog)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
return lwip_listen(fd, backlog); return lwip_listen(fd, backlog);
} }
int zts_accept(int fd, struct zts_sockaddr *addr, zts_socklen_t *addrlen) int zts_accept(int fd, struct zts_sockaddr* addr, zts_socklen_t* addrlen)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
return lwip_accept(fd, (sockaddr*)addr, (socklen_t*)addrlen); return lwip_accept(fd, (sockaddr*)addr, (socklen_t*)addrlen);
} }
int zts_accept_easy(int fd, char *remoteIpStr, int len, int *port) int zts_accept_easy(int fd, char* remoteIpStr, int len, int* port)
{ {
if (len != ZTS_INET6_ADDRSTRLEN) { if (len != ZTS_INET6_ADDRSTRLEN) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
@@ -171,65 +168,61 @@ int zts_accept_easy(int fd, char *remoteIpStr, int len, int *port)
zts_socklen_t addrlen = sizeof(ss); zts_socklen_t addrlen = sizeof(ss);
int acc_fd = zts_accept(fd, (zts_sockaddr*)&ss, (zts_socklen_t*)&addrlen); int acc_fd = zts_accept(fd, (zts_sockaddr*)&ss, (zts_socklen_t*)&addrlen);
struct zts_sockaddr *sa = (struct zts_sockaddr *)&ss; struct zts_sockaddr* sa = (struct zts_sockaddr*)&ss;
if (sa->sa_family == ZTS_AF_INET) { if (sa->sa_family == ZTS_AF_INET) {
struct zts_sockaddr_in *in4 = (struct zts_sockaddr_in*)sa; struct zts_sockaddr_in* in4 = (struct zts_sockaddr_in*)sa;
zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), zts_inet_ntop(ZTS_AF_INET, &(in4->sin_addr), remoteIpStr, ZTS_INET_ADDRSTRLEN);
remoteIpStr, ZTS_INET_ADDRSTRLEN);
*port = ntohs(in4->sin_port); *port = ntohs(in4->sin_port);
} }
if (sa->sa_family == ZTS_AF_INET6) { if (sa->sa_family == ZTS_AF_INET6) {
struct zts_sockaddr_in6 *in6 = (struct zts_sockaddr_in6*)sa; struct zts_sockaddr_in6* in6 = (struct zts_sockaddr_in6*)sa;
zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), zts_inet_ntop(ZTS_AF_INET6, &(in6->sin6_addr), remoteIpStr, ZTS_INET6_ADDRSTRLEN);
remoteIpStr, ZTS_INET6_ADDRSTRLEN);
*port = ntohs(in6->sin6_port); *port = ntohs(in6->sin6_port);
} }
return acc_fd; return acc_fd;
} }
int zts_setsockopt( int zts_setsockopt(int fd, int level, int optname, const void* optval, zts_socklen_t optlen)
int fd, int level, int optname, const void *optval,zts_socklen_t optlen)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
return lwip_setsockopt(fd, level, optname, optval, optlen); return lwip_setsockopt(fd, level, optname, optval, optlen);
} }
int zts_getsockopt( int zts_getsockopt(int fd, int level, int optname, void* optval, zts_socklen_t* optlen)
int fd, int level, int optname, void *optval, zts_socklen_t *optlen)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
return lwip_getsockopt(fd, level, optname, optval, (socklen_t*)optlen); return lwip_getsockopt(fd, level, optname, optval, (socklen_t*)optlen);
} }
int zts_getsockname(int fd, struct zts_sockaddr *addr, zts_socklen_t *addrlen) int zts_getsockname(int fd, struct zts_sockaddr* addr, zts_socklen_t* addrlen)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (!addr) { if (! addr) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
if (*addrlen > (int)sizeof(struct zts_sockaddr_storage) if (*addrlen > (int)sizeof(struct zts_sockaddr_storage)
|| *addrlen < (int)sizeof(struct zts_sockaddr_in)) { || *addrlen < (int)sizeof(struct zts_sockaddr_in)) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return lwip_getsockname(fd, (sockaddr*)addr, (socklen_t*)addrlen); return lwip_getsockname(fd, (sockaddr*)addr, (socklen_t*)addrlen);
} }
int zts_getpeername(int fd, struct zts_sockaddr *addr, zts_socklen_t *addrlen) int zts_getpeername(int fd, struct zts_sockaddr* addr, zts_socklen_t* addrlen)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (!addr) { if (! addr) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
if (*addrlen > (int)sizeof(struct zts_sockaddr_storage) if (*addrlen > (int)sizeof(struct zts_sockaddr_storage)
|| *addrlen < (int)sizeof(struct zts_sockaddr_in)) { || *addrlen < (int)sizeof(struct zts_sockaddr_in)) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return lwip_getpeername(fd, (sockaddr*)addr, (socklen_t*)addrlen); return lwip_getpeername(fd, (sockaddr*)addr, (socklen_t*)addrlen);
@@ -237,156 +230,172 @@ int zts_getpeername(int fd, struct zts_sockaddr *addr, zts_socklen_t *addrlen)
int zts_close(int fd) int zts_close(int fd)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
return lwip_close(fd); return lwip_close(fd);
} }
int zts_select( int zts_select(
int nfds, zts_fd_set *readfds, zts_fd_set *writefds, zts_fd_set *exceptfds, int nfds,
struct zts_timeval *timeout) zts_fd_set* readfds,
zts_fd_set* writefds,
zts_fd_set* exceptfds,
struct zts_timeval* timeout)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
return lwip_select( return lwip_select(
nfds, (fd_set*)readfds, (fd_set*)writefds, (fd_set*)exceptfds, (timeval*)timeout); nfds,
(fd_set*)readfds,
(fd_set*)writefds,
(fd_set*)exceptfds,
(timeval*)timeout);
} }
int zts_fcntl(int fd, int cmd, int flags) int zts_fcntl(int fd, int cmd, int flags)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
return lwip_fcntl(fd, cmd, flags); return lwip_fcntl(fd, cmd, flags);
} }
int zts_poll(struct zts_pollfd *fds, nfds_t nfds, int timeout) int zts_poll(struct zts_pollfd* fds, nfds_t nfds, int timeout)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
return lwip_poll((pollfd*)fds, nfds, timeout); return lwip_poll((pollfd*)fds, nfds, timeout);
} }
int zts_ioctl(int fd, unsigned long request, void *argp) int zts_ioctl(int fd, unsigned long request, void* argp)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (!argp) { if (! argp) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return lwip_ioctl(fd, request, argp); return lwip_ioctl(fd, request, argp);
} }
ssize_t zts_send(int fd, const void *buf, size_t len, int flags) ssize_t zts_send(int fd, const void* buf, size_t len, int flags)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (!buf) { if (! buf) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return lwip_send(fd, buf, len, flags); return lwip_send(fd, buf, len, flags);
} }
ssize_t zts_sendto(int fd, const void *buf, size_t len, int flags, ssize_t zts_sendto(
const struct zts_sockaddr *addr,zts_socklen_t addrlen) int fd,
const void* buf,
size_t len,
int flags,
const struct zts_sockaddr* addr,
zts_socklen_t addrlen)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (!addr || !buf) { if (! addr || ! buf) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
if (addrlen > (int)sizeof(struct zts_sockaddr_storage) if (addrlen > (int)sizeof(struct zts_sockaddr_storage)
|| addrlen < (int)sizeof(struct zts_sockaddr_in)) { || addrlen < (int)sizeof(struct zts_sockaddr_in)) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return lwip_sendto(fd, buf, len, flags, (sockaddr*)addr, addrlen); return lwip_sendto(fd, buf, len, flags, (sockaddr*)addr, addrlen);
} }
ssize_t zts_sendmsg(int fd, const struct zts_msghdr *msg, int flags) ssize_t zts_sendmsg(int fd, const struct zts_msghdr* msg, int flags)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
return lwip_sendmsg(fd, (const struct msghdr *)msg, flags); return lwip_sendmsg(fd, (const struct msghdr*)msg, flags);
} }
ssize_t zts_recv(int fd, void *buf, size_t len, int flags) ssize_t zts_recv(int fd, void* buf, size_t len, int flags)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (!buf) { if (! buf) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return lwip_recv(fd, buf, len, flags); return lwip_recv(fd, buf, len, flags);
} }
ssize_t zts_recvfrom(int fd, void *buf, size_t len, int flags, ssize_t zts_recvfrom(
struct zts_sockaddr *addr, zts_socklen_t *addrlen) int fd,
void* buf,
size_t len,
int flags,
struct zts_sockaddr* addr,
zts_socklen_t* addrlen)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (!buf) { if (! buf) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return lwip_recvfrom( return lwip_recvfrom(fd, buf, len, flags, (sockaddr*)addr, (socklen_t*)addrlen);
fd, buf, len, flags, (sockaddr*)addr, (socklen_t*)addrlen);
} }
ssize_t zts_recvmsg(int fd, struct zts_msghdr *msg, int flags) ssize_t zts_recvmsg(int fd, struct zts_msghdr* msg, int flags)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (!msg) { if (! msg) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return lwip_recvmsg(fd, (struct msghdr *)msg, flags); return lwip_recvmsg(fd, (struct msghdr*)msg, flags);
} }
ssize_t zts_read(int fd, void *buf, size_t len) ssize_t zts_read(int fd, void* buf, size_t len)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (!buf) { if (! buf) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return lwip_read(fd, buf, len); return lwip_read(fd, buf, len);
} }
ssize_t zts_readv(int fd, const struct zts_iovec *iov, int iovcnt) ssize_t zts_readv(int fd, const struct zts_iovec* iov, int iovcnt)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
return lwip_readv(fd, (iovec*)iov, iovcnt); return lwip_readv(fd, (iovec*)iov, iovcnt);
} }
ssize_t zts_write(int fd, const void *buf, size_t len) ssize_t zts_write(int fd, const void* buf, size_t len)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (!buf) { if (! buf) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return lwip_write(fd, buf, len); return lwip_write(fd, buf, len);
} }
ssize_t zts_writev(int fd, const struct zts_iovec *iov, int iovcnt) ssize_t zts_writev(int fd, const struct zts_iovec* iov, int iovcnt)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
@@ -395,72 +404,76 @@ ssize_t zts_writev(int fd, const struct zts_iovec *iov, int iovcnt)
int zts_shutdown(int fd, int how) int zts_shutdown(int fd, int how)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
return lwip_shutdown(fd, how); return lwip_shutdown(fd, how);
} }
struct zts_hostent *zts_gethostbyname(const char *name) struct zts_hostent* zts_gethostbyname(const char* name)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return NULL; return NULL;
} }
if (!name) { if (! name) {
return NULL; return NULL;
} }
return (struct zts_hostent *)lwip_gethostbyname(name); return (struct zts_hostent*)lwip_gethostbyname(name);
} }
int zts_dns_set_server(uint8_t index, const zts_ip_addr *addr) int zts_dns_set_server(uint8_t index, const zts_ip_addr* addr)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (index >= DNS_MAX_SERVERS) { if (index >= DNS_MAX_SERVERS) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
if (!addr) { if (! addr) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
dns_setserver(index, (const ip_addr_t *)addr); dns_setserver(index, (const ip_addr_t*)addr);
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
const zts_ip_addr *zts_dns_get_server(uint8_t index) const zts_ip_addr* zts_dns_get_server(uint8_t index)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return NULL; return NULL;
} }
if (index >= DNS_MAX_SERVERS) { if (index >= DNS_MAX_SERVERS) {
return NULL; return NULL;
} }
return (const zts_ip_addr *)dns_getserver(index); return (const zts_ip_addr*)dns_getserver(index);
} }
char *zts_ipaddr_ntoa(const zts_ip_addr *addr) char* zts_ipaddr_ntoa(const zts_ip_addr* addr)
{ {
return ipaddr_ntoa((ip_addr_t *)addr); return ipaddr_ntoa((ip_addr_t*)addr);
} }
int zts_ipaddr_aton(const char *cp, zts_ip_addr *addr) int zts_ipaddr_aton(const char* cp, zts_ip_addr* addr)
{ {
return ipaddr_aton(cp, (ip_addr_t *)addr); return ipaddr_aton(cp, (ip_addr_t*)addr);
} }
const char *zts_inet_ntop( const char* zts_inet_ntop(int family, const void* src, char* dst, zts_socklen_t size)
int family, const void *src, char *dst, zts_socklen_t size)
{ {
return lwip_inet_ntop(family,src,dst,size); return lwip_inet_ntop(family, src, dst, size);
} }
int zts_inet_pton(int family, const char *src, void *dst) int zts_inet_pton(int family, const char* src, void* dst)
{ {
return lwip_inet_pton(family,src,dst); return lwip_inet_pton(family, src, dst);
} }
int ipstr2sockaddr( int ipstr2sockaddr(
int family, char *src_ipstr, int port, struct zts_sockaddr *dest_addr, zts_socklen_t *addrlen) { int family,
char* src_ipstr,
int port,
struct zts_sockaddr* dest_addr,
zts_socklen_t* addrlen)
{
if (family == ZTS_AF_INET) { if (family == ZTS_AF_INET) {
struct zts_sockaddr_in in4; struct zts_sockaddr_in in4;
in4.sin_port = htons(port); in4.sin_port = htons(port);
@@ -470,7 +483,7 @@ int ipstr2sockaddr(
#else #else
zts_inet_pton(family, src_ipstr, &(in4.sin_addr.s_addr)); zts_inet_pton(family, src_ipstr, &(in4.sin_addr.s_addr));
#endif #endif
dest_addr = (struct zts_sockaddr *)&in4; dest_addr = (struct zts_sockaddr*)&in4;
*addrlen = sizeof(in4); *addrlen = sizeof(in4);
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
@@ -483,7 +496,7 @@ int ipstr2sockaddr(
#else #else
zts_inet_pton(family, src_ipstr, &(in6.sin6_addr)); zts_inet_pton(family, src_ipstr, &(in6.sin6_addr));
#endif #endif
dest_addr = (struct zts_sockaddr *)&in6; dest_addr = (struct zts_sockaddr*)&in6;
*addrlen = sizeof(in6); *addrlen = sizeof(in6);
return ZTS_ERR_OK; return ZTS_ERR_OK;
} }
@@ -495,39 +508,39 @@ int ipstr2sockaddr(
//----------------------------------------------------------------------------// //----------------------------------------------------------------------------//
/** /**
* Helper functions that simplify API wrapper generation and usage in other * Helper functions that simplify API wrapper generation and usage in other
* non-C-like languages. Use simple integer types instead of bit flags, limit * non-C-like languages. Use simple integer types instead of bit flags, limit
* the number of operations each function performs, prevent the user from * the number of operations each function performs, prevent the user from
* needing to manipulate the content of structures in a non-native language. * needing to manipulate the content of structures in a non-native language.
*/ */
int zts_set_no_delay(int fd, int enabled) { int zts_set_no_delay(int fd, int enabled)
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { {
if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (enabled != 0 && enabled != 1) { if (enabled != 0 && enabled != 1) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return zts_setsockopt( return zts_setsockopt(fd, ZTS_IPPROTO_TCP, ZTS_TCP_NODELAY, (void*)&enabled, sizeof(int));
fd, ZTS_IPPROTO_TCP, ZTS_TCP_NODELAY, (void *)&enabled, sizeof(int));
} }
int zts_get_no_delay(int fd) int zts_get_no_delay(int fd)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
int err, optval = 0; int err, optval = 0;
zts_socklen_t len = sizeof(optval); zts_socklen_t len = sizeof(optval);
if ((err = zts_getsockopt( if ((err = zts_getsockopt(fd, ZTS_IPPROTO_TCP, ZTS_TCP_NODELAY, (void*)&optval, &len)) < 0) {
fd, ZTS_IPPROTO_TCP, ZTS_TCP_NODELAY, (void *)&optval, &len)) < 0) {
return err; return err;
} }
return optval != 0; return optval != 0;
} }
int zts_set_linger(int fd, int enabled, int value) { int zts_set_linger(int fd, int enabled, int value)
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { {
if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (enabled != 0 && enabled != 1) { if (enabled != 0 && enabled != 1) {
@@ -539,20 +552,18 @@ int zts_set_linger(int fd, int enabled, int value) {
struct zts_linger linger; struct zts_linger linger;
linger.l_onoff = enabled; linger.l_onoff = enabled;
linger.l_linger = value; linger.l_linger = value;
return zts_setsockopt( return zts_setsockopt(fd, ZTS_SOL_SOCKET, ZTS_SO_LINGER, (void*)&linger, sizeof(linger));
fd, ZTS_SOL_SOCKET, ZTS_SO_LINGER, (void *)&linger, sizeof(linger));
} }
int zts_get_linger_enabled(int fd) int zts_get_linger_enabled(int fd)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
int err; int err;
struct zts_linger linger; struct zts_linger linger;
zts_socklen_t len = sizeof(linger); zts_socklen_t len = sizeof(linger);
if ((err = zts_getsockopt( if ((err = zts_getsockopt(fd, ZTS_SOL_SOCKET, ZTS_SO_LINGER, (void*)&linger, &len)) < 0) {
fd, ZTS_SOL_SOCKET, ZTS_SO_LINGER, (void *)&linger, &len)) < 0) {
return err; return err;
} }
return linger.l_onoff; return linger.l_onoff;
@@ -560,14 +571,13 @@ int zts_get_linger_enabled(int fd)
int zts_get_linger_value(int fd) int zts_get_linger_value(int fd)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
int err; int err;
struct zts_linger linger; struct zts_linger linger;
zts_socklen_t len = sizeof(linger); zts_socklen_t len = sizeof(linger);
if ((err = zts_getsockopt( if ((err = zts_getsockopt(fd, ZTS_SOL_SOCKET, ZTS_SO_LINGER, (void*)&linger, &len)) < 0) {
fd, ZTS_SOL_SOCKET, ZTS_SO_LINGER, (void *)&linger, &len)) < 0) {
return err; return err;
} }
return linger.l_linger; return linger.l_linger;
@@ -575,26 +585,24 @@ int zts_get_linger_value(int fd)
int zts_set_reuse_addr(int fd, int enabled) int zts_set_reuse_addr(int fd, int enabled)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (enabled != 0 && enabled != 1) { if (enabled != 0 && enabled != 1) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return zts_setsockopt( return zts_setsockopt(fd, ZTS_SOL_SOCKET, ZTS_SO_REUSEADDR, (void*)&enabled, sizeof(enabled));
fd, ZTS_SOL_SOCKET, ZTS_SO_REUSEADDR, (void *)&enabled, sizeof(enabled));
} }
int zts_get_reuse_addr(int fd) int zts_get_reuse_addr(int fd)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
int err; int err;
int optval = 0; int optval = 0;
zts_socklen_t optlen = sizeof(optval); zts_socklen_t optlen = sizeof(optval);
if ((err = zts_getsockopt( if ((err = zts_getsockopt(fd, ZTS_SOL_SOCKET, ZTS_SO_REUSEADDR, (void*)&optval, &optlen)) < 0) {
fd, ZTS_SOL_SOCKET, ZTS_SO_REUSEADDR, (void *)&optval, &optlen)) < 0) {
return err; return err;
} }
return optval != 0; return optval != 0;
@@ -602,7 +610,7 @@ int zts_get_reuse_addr(int fd)
int zts_set_recv_timeout(int fd, int seconds, int microseconds) int zts_set_recv_timeout(int fd, int seconds, int microseconds)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (seconds < 0 || microseconds < 0) { if (seconds < 0 || microseconds < 0) {
@@ -611,28 +619,26 @@ int zts_set_recv_timeout(int fd, int seconds, int microseconds)
struct timeval tv; struct timeval tv;
tv.tv_sec = seconds; tv.tv_sec = seconds;
tv.tv_usec = microseconds; tv.tv_usec = microseconds;
return zts_setsockopt( return zts_setsockopt(fd, SOL_SOCKET, SO_RCVTIMEO, (void*)&tv, sizeof(tv));
fd, SOL_SOCKET, SO_RCVTIMEO, (void *)&tv, sizeof(tv));
} }
int zts_get_recv_timeout(int fd) int zts_get_recv_timeout(int fd)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
struct timeval tv; struct timeval tv;
zts_socklen_t optlen = sizeof(tv); zts_socklen_t optlen = sizeof(tv);
int err; int err;
if ((err = zts_getsockopt( if ((err = zts_getsockopt(fd, SOL_SOCKET, SO_RCVTIMEO, (void*)&tv, &optlen)) < 0) {
fd, SOL_SOCKET, SO_RCVTIMEO, (void *)&tv, &optlen)) < 0) {
return err; return err;
} }
return tv.tv_sec; // TODO microseconds return tv.tv_sec; // TODO microseconds
} }
int zts_set_send_timeout(int fd, int seconds, int microseconds) int zts_set_send_timeout(int fd, int seconds, int microseconds)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (seconds < 0 || microseconds < 0) { if (seconds < 0 || microseconds < 0) {
@@ -641,46 +647,42 @@ int zts_set_send_timeout(int fd, int seconds, int microseconds)
struct timeval tv; struct timeval tv;
tv.tv_sec = seconds; tv.tv_sec = seconds;
tv.tv_usec = microseconds; tv.tv_usec = microseconds;
return zts_setsockopt( return zts_setsockopt(fd, SOL_SOCKET, SO_SNDTIMEO, (void*)&tv, sizeof(tv));
fd, SOL_SOCKET, SO_SNDTIMEO, (void *)&tv, sizeof(tv));
} }
int zts_get_send_timeout(int fd) int zts_get_send_timeout(int fd)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
struct zts_timeval tv; struct zts_timeval tv;
zts_socklen_t optlen = sizeof(tv); zts_socklen_t optlen = sizeof(tv);
int err; int err;
if ((err = zts_getsockopt( if ((err = zts_getsockopt(fd, SOL_SOCKET, SO_SNDTIMEO, (void*)&tv, &optlen)) < 0) {
fd, SOL_SOCKET, SO_SNDTIMEO, (void *)&tv, &optlen)) < 0) {
return err; return err;
} }
return tv.tv_sec; // TODO microseconds return tv.tv_sec; // TODO microseconds
} }
int zts_set_send_buf_size(int fd, int size) int zts_set_send_buf_size(int fd, int size)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (size < 0) { if (size < 0) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return zts_setsockopt( return zts_setsockopt(fd, SOL_SOCKET, SO_SNDBUF, (void*)&size, sizeof(int));
fd, SOL_SOCKET, SO_SNDBUF, (void *)&size, sizeof(int));
} }
int zts_get_send_buf_size(int fd) int zts_get_send_buf_size(int fd)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
int err, optval = 0; int err, optval = 0;
zts_socklen_t optlen = sizeof(optval); zts_socklen_t optlen = sizeof(optval);
if ((err = zts_getsockopt( if ((err = zts_getsockopt(fd, SOL_SOCKET, SO_SNDBUF, (char*)&optval, &optlen)) < 0) {
fd, SOL_SOCKET, SO_SNDBUF, (char *)&optval, &optlen)) < 0) {
return err; return err;
} }
return optval; return optval;
@@ -688,25 +690,23 @@ int zts_get_send_buf_size(int fd)
int zts_set_recv_buf_size(int fd, int size) int zts_set_recv_buf_size(int fd, int size)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (size < 0) { if (size < 0) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
return zts_setsockopt( return zts_setsockopt(fd, SOL_SOCKET, SO_RCVBUF, (void*)&size, sizeof(int));
fd, SOL_SOCKET, SO_RCVBUF, (void *)&size, sizeof(int));
} }
int zts_get_recv_buf_size(int fd) int zts_get_recv_buf_size(int fd)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
int err, optval = 0; int err, optval = 0;
zts_socklen_t optlen = sizeof(optval); zts_socklen_t optlen = sizeof(optval);
if ((err = zts_getsockopt( if ((err = zts_getsockopt(fd, SOL_SOCKET, SO_RCVBUF, (char*)&optval, &optlen)) < 0) {
fd, SOL_SOCKET, SO_RCVBUF, (char *)&optval, &optlen)) < 0) {
return err; return err;
} }
return optval; return optval;
@@ -714,7 +714,7 @@ int zts_get_recv_buf_size(int fd)
int zts_set_ttl(int fd, int ttl) int zts_set_ttl(int fd, int ttl)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (ttl < 0 || ttl > 255) { if (ttl < 0 || ttl > 255) {
@@ -725,7 +725,7 @@ int zts_set_ttl(int fd, int ttl)
int zts_get_ttl(int fd) int zts_get_ttl(int fd)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
int err, ttl = 0; int err, ttl = 0;
@@ -738,14 +738,14 @@ int zts_get_ttl(int fd)
int zts_set_blocking(int fd, int enabled) int zts_set_blocking(int fd, int enabled)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (enabled != 0 && enabled != 1) { if (enabled != 0 && enabled != 1) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
int flags = zts_fcntl(fd, ZTS_F_GETFL, 0); int flags = zts_fcntl(fd, ZTS_F_GETFL, 0);
if (!enabled) { if (! enabled) {
return zts_fcntl(fd, ZTS_F_SETFL, flags | ZTS_O_NONBLOCK); return zts_fcntl(fd, ZTS_F_SETFL, flags | ZTS_O_NONBLOCK);
} }
else { else {
@@ -756,40 +756,38 @@ int zts_set_blocking(int fd, int enabled)
int zts_get_blocking(int fd) int zts_get_blocking(int fd)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
int flags = zts_fcntl(fd, ZTS_F_GETFL, 0); int flags = zts_fcntl(fd, ZTS_F_GETFL, 0);
if (flags < 0) { if (flags < 0) {
return flags; return flags;
} }
return !(flags & ZTS_O_NONBLOCK); return ! (flags & ZTS_O_NONBLOCK);
} }
int zts_set_keepalive(int fd, int enabled) int zts_set_keepalive(int fd, int enabled)
{ {
// //
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
if (enabled != 0 && enabled != 1) { if (enabled != 0 && enabled != 1) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
int keepalive = enabled; int keepalive = enabled;
return zts_setsockopt( return zts_setsockopt(fd, ZTS_SOL_SOCKET, ZTS_SO_KEEPALIVE, &keepalive, sizeof(keepalive));
fd, ZTS_SOL_SOCKET, ZTS_SO_KEEPALIVE, &keepalive , sizeof(keepalive));
} }
int zts_get_keepalive(int fd) int zts_get_keepalive(int fd)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
int err; int err;
int optval = 0; int optval = 0;
zts_socklen_t optlen = sizeof(optval); zts_socklen_t optlen = sizeof(optval);
if ((err = zts_getsockopt( if ((err = zts_getsockopt(fd, ZTS_SOL_SOCKET, ZTS_SO_KEEPALIVE, (void*)&optval, &optlen)) < 0) {
fd, ZTS_SOL_SOCKET, ZTS_SO_KEEPALIVE, (void *)&optval, &optlen)) < 0) {
return err; return err;
} }
return optval != 0; return optval != 0;
@@ -803,13 +801,13 @@ int zts_get_keepalive(int fd)
extern struct stats_ lwip_stats; extern struct stats_ lwip_stats;
int zts_get_all_stats(struct zts_stats *statsDest) int zts_get_all_stats(struct zts_stats* statsDest)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
#if LWIP_STATS #if LWIP_STATS
if (!statsDest) { if (! statsDest) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
memset(statsDest, 0, sizeof(struct zts_stats)); memset(statsDest, 0, sizeof(struct zts_stats));
@@ -819,7 +817,7 @@ int zts_get_all_stats(struct zts_stats *statsDest)
memcpy(&(statsDest->ip_frag), &(lwip_stats.ip_frag), sizeof(struct stats_proto)); memcpy(&(statsDest->ip_frag), &(lwip_stats.ip_frag), sizeof(struct stats_proto));
memcpy(&(statsDest->ip), &(lwip_stats.ip), sizeof(struct stats_proto)); memcpy(&(statsDest->ip), &(lwip_stats.ip), sizeof(struct stats_proto));
memcpy(&(statsDest->icmp), &(lwip_stats.icmp), sizeof(struct stats_proto)); memcpy(&(statsDest->icmp), &(lwip_stats.icmp), sizeof(struct stats_proto));
//memcpy(&(statsDest->igmp), &(lwip_stats.igmp), sizeof(struct stats_igmp)); // memcpy(&(statsDest->igmp), &(lwip_stats.igmp), sizeof(struct stats_igmp));
memcpy(&(statsDest->udp), &(lwip_stats.udp), sizeof(struct stats_proto)); memcpy(&(statsDest->udp), &(lwip_stats.udp), sizeof(struct stats_proto));
memcpy(&(statsDest->tcp), &(lwip_stats.tcp), sizeof(struct stats_proto)); memcpy(&(statsDest->tcp), &(lwip_stats.tcp), sizeof(struct stats_proto));
// mem omitted // mem omitted
@@ -835,23 +833,22 @@ int zts_get_all_stats(struct zts_stats *statsDest)
// Copy ZT stats // Copy ZT stats
// ... // ...
return ZTS_ERR_OK; return ZTS_ERR_OK;
#else #else
return ZTS_ERR_NO_RESULT; return ZTS_ERR_NO_RESULT;
#endif #endif
} }
int zts_get_protocol_stats(int protocolType, void *protoStatsDest) int zts_get_protocol_stats(int protocolType, void* protoStatsDest)
{ {
if (!(_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) { if (! (_serviceStateFlags & ZTS_STATE_NET_SERVICE_RUNNING)) {
return ZTS_ERR_SERVICE; return ZTS_ERR_SERVICE;
} }
#if LWIP_STATS #if LWIP_STATS
if (!protoStatsDest) { if (! protoStatsDest) {
return ZTS_ERR_ARG; return ZTS_ERR_ARG;
} }
memset(protoStatsDest, 0, sizeof(struct stats_proto)); memset(protoStatsDest, 0, sizeof(struct stats_proto));
switch (protocolType) switch (protocolType) {
{
case ZTS_STATS_PROTOCOL_LINK: case ZTS_STATS_PROTOCOL_LINK:
memcpy(protoStatsDest, &(lwip_stats.link), sizeof(struct stats_proto)); memcpy(protoStatsDest, &(lwip_stats.link), sizeof(struct stats_proto));
break; break;
@@ -882,19 +879,18 @@ int zts_get_protocol_stats(int protocolType, void *protoStatsDest)
case ZTS_STATS_PROTOCOL_IP6_FRAG: case ZTS_STATS_PROTOCOL_IP6_FRAG:
memcpy(protoStatsDest, &(lwip_stats.ip6_frag), sizeof(struct stats_proto)); memcpy(protoStatsDest, &(lwip_stats.ip6_frag), sizeof(struct stats_proto));
break; break;
default: default: return ZTS_ERR_ARG;
return ZTS_ERR_ARG;
} }
return ZTS_ERR_OK; return ZTS_ERR_OK;
#else #else
return ZTS_ERR_NO_RESULT; return ZTS_ERR_NO_RESULT;
#endif #endif
} }
#endif // ZTS_ENABLE_STATS #endif // ZTS_ENABLE_STATS
#ifdef __cplusplus #ifdef __cplusplus
} }
#endif #endif
} // namespace ZeroTier } // namespace ZeroTier

View File

@@ -18,30 +18,30 @@
*/ */
#include "Constants.hpp" #include "Constants.hpp"
#include "MAC.hpp"
#include "Mutex.hpp"
#include "InetAddress.hpp" #include "InetAddress.hpp"
#include "MAC.hpp"
#include "MulticastGroup.hpp" #include "MulticastGroup.hpp"
#include "Mutex.hpp"
#include "lwip/netif.h"
#include "lwip/etharp.h" #include "lwip/etharp.h"
#include "lwip/sys.h"
#include "lwip/ethip6.h" #include "lwip/ethip6.h"
#include "lwip/netif.h"
#include "lwip/sys.h"
#include "lwip/tcpip.h" #include "lwip/tcpip.h"
#include "netif/ethernet.h" #include "netif/ethernet.h"
#ifdef LWIP_STATS #ifdef LWIP_STATS
#include "lwip/stats.h" #include "lwip/stats.h"
#endif #endif
#include "Debug.hpp"
#include "Events.hpp"
#include "VirtualTap.hpp" #include "VirtualTap.hpp"
#include "ZeroTierSockets.h" #include "ZeroTierSockets.h"
#include "Events.hpp"
#include "Debug.hpp"
#if defined(__WINDOWS__) #if defined(__WINDOWS__)
#include <time.h> #include "Synchapi.h"
#include "Synchapi.h"
#include <time.h>
#endif #endif
#define ZTS_TAP_THREAD_POLLING_INTERVAL 50 #define ZTS_TAP_THREAD_POLLING_INTERVAL 50
@@ -49,33 +49,41 @@
namespace ZeroTier { namespace ZeroTier {
extern void _enqueueEvent(int16_t eventCode, void *arg = NULL); extern void _enqueueEvent(int16_t eventCode, void* arg = NULL);
/** /**
* 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
* virtual network joined. It will be destroyed upon leave(). * virtual network joined. It will be destroyed upon leave().
*/ */
VirtualTap::VirtualTap( VirtualTap::VirtualTap(
const char *homePath, const char* homePath,
const MAC &mac, const MAC& mac,
unsigned int mtu, unsigned int mtu,
unsigned int metric, unsigned int metric,
uint64_t nwid, uint64_t nwid,
const char *friendlyName, const char* friendlyName,
void (*handler)(void *,void*,uint64_t,const MAC &,const MAC &, void (*handler)(
unsigned int,unsigned int,const void *,unsigned int), void*,
void *arg) : void*,
_handler(handler), uint64_t,
_homePath(homePath), const MAC&,
_arg(arg), const MAC&,
_initialized(false), unsigned int,
_enabled(true), unsigned int,
_run(true), const void*,
_mac(mac), unsigned int),
_mtu(mtu), void* arg)
_nwid(nwid), : _handler(handler)
_unixListenSocket((PhySocket *)0), , _homePath(homePath)
_phy(this,false,true) , _arg(arg)
, _initialized(false)
, _enabled(true)
, _run(true)
, _mac(mac)
, _mtu(mtu)
, _nwid(nwid)
, _unixListenSocket((PhySocket*)0)
, _phy(this, false, true)
{ {
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);
@@ -89,11 +97,11 @@ VirtualTap::VirtualTap(
VirtualTap::~VirtualTap() VirtualTap::~VirtualTap()
{ {
struct zts_network_details *nd = new zts_network_details; struct zts_network_details* nd = new zts_network_details;
nd->nwid = _nwid; nd->nwid = _nwid;
_run = false; _run = false;
#ifndef __WINDOWS__ #ifndef __WINDOWS__
::write(_shutdownSignalPipe[1],"\0",1); ::write(_shutdownSignalPipe[1], "\0", 1);
#endif #endif
_phy.whack(); _phy.whack();
_lwip_remove_netif(netif4); _lwip_remove_netif(netif4);
@@ -128,7 +136,9 @@ bool VirtualTap::hasIpv4Addr()
Mutex::Lock _l(_ips_m); Mutex::Lock _l(_ips_m);
std::vector<InetAddress>::iterator it(_ips.begin()); std::vector<InetAddress>::iterator it(_ips.begin());
while (it != _ips.end()) { while (it != _ips.end()) {
if ((*it).isV4()) { return true; } if ((*it).isV4()) {
return true;
}
++it; ++it;
} }
return false; return false;
@@ -139,17 +149,19 @@ bool VirtualTap::hasIpv6Addr()
Mutex::Lock _l(_ips_m); Mutex::Lock _l(_ips_m);
std::vector<InetAddress>::iterator it(_ips.begin()); std::vector<InetAddress>::iterator it(_ips.begin());
while (it != _ips.end()) { while (it != _ips.end()) {
if ((*it).isV6()) { return true; } if ((*it).isV6()) {
return true;
}
++it; ++it;
} }
return false; return false;
} }
bool VirtualTap::addIp(const InetAddress &ip) bool VirtualTap::addIp(const InetAddress& ip)
{ {
char ipbuf[128]; char ipbuf[128];
//ip.toString(ipbuf); // ip.toString(ipbuf);
//DEBUG_INFO("addr=%s", ipbuf); // DEBUG_INFO("addr=%s", ipbuf);
/* Limit address assignments to one per type. /* Limit address assignments to one per type.
This limitation can be removed if some changes This limitation can be removed if some changes
@@ -169,18 +181,18 @@ bool VirtualTap::addIp(const InetAddress &ip)
if (_ips.size() >= ZT_MAX_ZT_ASSIGNED_ADDRESSES) { if (_ips.size() >= ZT_MAX_ZT_ASSIGNED_ADDRESSES) {
return false; return false;
} }
if (std::find(_ips.begin(),_ips.end(),ip) == _ips.end()) { if (std::find(_ips.begin(), _ips.end(), ip) == _ips.end()) {
_lwip_init_interface((void*)this, ip); _lwip_init_interface((void*)this, ip);
_ips.push_back(ip); _ips.push_back(ip);
std::sort(_ips.begin(),_ips.end()); std::sort(_ips.begin(), _ips.end());
} }
return true; return true;
} }
bool VirtualTap::removeIp(const InetAddress &ip) bool VirtualTap::removeIp(const InetAddress& ip)
{ {
Mutex::Lock _l(_ips_m); Mutex::Lock _l(_ips_m);
if (std::find(_ips.begin(),_ips.end(),ip) != _ips.end()) { if (std::find(_ips.begin(), _ips.end(), ip) != _ips.end()) {
std::vector<InetAddress>::iterator i(std::find(_ips.begin(), _ips.end(), ip)); std::vector<InetAddress>::iterator i(std::find(_ips.begin(), _ips.end(), ip));
_lwip_remove_address_from_netif((void*)this, ip); _lwip_remove_address_from_netif((void*)this, ip);
_ips.erase(i); _ips.erase(i);
@@ -194,8 +206,12 @@ std::vector<InetAddress> VirtualTap::ips() const
return _ips; return _ips;
} }
void VirtualTap::put(const MAC &from,const MAC &to,unsigned int etherType, void VirtualTap::put(
const void *data,unsigned int len) const MAC& from,
const MAC& to,
unsigned int etherType,
const void* data,
unsigned int len)
{ {
if (len && _enabled) { if (len && _enabled) {
_lwip_eth_rx(this, from, to, etherType, data, len); _lwip_eth_rx(this, from, to, etherType, data, len);
@@ -207,29 +223,32 @@ std::string VirtualTap::deviceName() const
return _dev; return _dev;
} }
void VirtualTap::setFriendlyName(const char *friendlyName) void VirtualTap::setFriendlyName(const char* friendlyName)
{ {
DEBUG_INFO("%s", friendlyName); DEBUG_INFO("%s", friendlyName);
} }
void VirtualTap::scanMulticastGroups(std::vector<MulticastGroup> &added, void VirtualTap::scanMulticastGroups(
std::vector<MulticastGroup> &removed) std::vector<MulticastGroup>& added,
std::vector<MulticastGroup>& removed)
{ {
std::vector<MulticastGroup> newGroups; std::vector<MulticastGroup> newGroups;
Mutex::Lock _l(_multicastGroups_m); Mutex::Lock _l(_multicastGroups_m);
// TODO: get multicast subscriptions // TODO: get multicast subscriptions
std::vector<InetAddress> allIps(ips()); std::vector<InetAddress> allIps(ips());
for (std::vector<InetAddress>::iterator ip(allIps.begin());ip!=allIps.end();++ip) for (std::vector<InetAddress>::iterator ip(allIps.begin()); ip != allIps.end(); ++ip)
newGroups.push_back(MulticastGroup::deriveMulticastGroupForAddressResolution(*ip)); newGroups.push_back(MulticastGroup::deriveMulticastGroupForAddressResolution(*ip));
std::sort(newGroups.begin(),newGroups.end()); std::sort(newGroups.begin(), newGroups.end());
for (std::vector<MulticastGroup>::iterator m(newGroups.begin());m!=newGroups.end();++m) { for (std::vector<MulticastGroup>::iterator m(newGroups.begin()); m != newGroups.end(); ++m) {
if (!std::binary_search(_multicastGroups.begin(),_multicastGroups.end(),*m)) if (! std::binary_search(_multicastGroups.begin(), _multicastGroups.end(), *m))
added.push_back(*m); added.push_back(*m);
} }
for (std::vector<MulticastGroup>::iterator m(_multicastGroups.begin());m!=_multicastGroups.end();++m) { for (std::vector<MulticastGroup>::iterator m(_multicastGroups.begin());
if (!std::binary_search(newGroups.begin(),newGroups.end(),*m)) m != _multicastGroups.end();
++m) {
if (! std::binary_search(newGroups.begin(), newGroups.end(), *m))
removed.push_back(*m); removed.push_back(*m);
} }
_multicastGroups.swap(newGroups); _multicastGroups.swap(newGroups);
@@ -240,16 +259,15 @@ void VirtualTap::setMtu(unsigned int mtu)
_mtu = mtu; _mtu = mtu;
} }
void VirtualTap::threadMain() void VirtualTap::threadMain() throw()
throw()
{ {
fd_set readfds,nullfds; fd_set readfds, nullfds;
struct timeval tv; struct timeval tv;
tv.tv_sec = 0; tv.tv_sec = 0;
tv.tv_usec = 0; tv.tv_usec = 0;
FD_ZERO(&readfds); FD_ZERO(&readfds);
FD_ZERO(&nullfds); FD_ZERO(&nullfds);
int nfds = (int)std::max(_shutdownSignalPipe[0],0) + 1; int nfds = (int)std::max(_shutdownSignalPipe[0], 0) + 1;
#if defined(__linux__) #if defined(__linux__)
pthread_setname_np(pthread_self(), vtap_full_name); pthread_setname_np(pthread_self(), vtap_full_name);
#endif #endif
@@ -257,31 +275,54 @@ void VirtualTap::threadMain()
pthread_setname_np(vtap_full_name); pthread_setname_np(vtap_full_name);
#endif #endif
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);
// writes to shutdown pipe terminate thread // writes to shutdown pipe terminate thread
if (FD_ISSET(_shutdownSignalPipe[0],&readfds)) { if (FD_ISSET(_shutdownSignalPipe[0], &readfds)) {
break; break;
} }
#if defined(__WINDOWS__) #if defined(__WINDOWS__)
Sleep(ZTS_TAP_THREAD_POLLING_INTERVAL); Sleep(ZTS_TAP_THREAD_POLLING_INTERVAL);
#else #else
struct timespec sleepValue = {0}; struct timespec sleepValue = { 0 };
sleepValue.tv_nsec = ZTS_TAP_THREAD_POLLING_INTERVAL * 500000; sleepValue.tv_nsec = ZTS_TAP_THREAD_POLLING_INTERVAL * 500000;
nanosleep(&sleepValue, NULL); nanosleep(&sleepValue, NULL);
#endif #endif
} }
} }
void VirtualTap::phyOnDatagram(PhySocket *sock,void **uptr,const struct sockaddr *local_address, void VirtualTap::phyOnDatagram(
const struct sockaddr *from,void *data,unsigned long len) {} PhySocket* sock,
void VirtualTap::phyOnTcpConnect(PhySocket *sock,void **uptr,bool success) {} void** uptr,
void VirtualTap::phyOnTcpAccept(PhySocket *sockL,PhySocket *sockN,void **uptrL,void **uptrN, const struct sockaddr* local_address,
const struct sockaddr *from) {} const struct sockaddr* from,
void VirtualTap::phyOnTcpClose(PhySocket *sock,void **uptr) {} void* data,
void VirtualTap::phyOnTcpData(PhySocket *sock,void **uptr,void *data,unsigned long len) {} unsigned long len)
void VirtualTap::phyOnTcpWritable(PhySocket *sock,void **uptr) {} {
void VirtualTap::phyOnUnixClose(PhySocket *sock,void **uptr) {} }
void VirtualTap::phyOnTcpConnect(PhySocket* sock, void** uptr, bool success)
{
}
void VirtualTap::phyOnTcpAccept(
PhySocket* sockL,
PhySocket* sockN,
void** uptrL,
void** uptrN,
const struct sockaddr* from)
{
}
void VirtualTap::phyOnTcpClose(PhySocket* sock, void** uptr)
{
}
void VirtualTap::phyOnTcpData(PhySocket* sock, void** uptr, void* data, unsigned long len)
{
}
void VirtualTap::phyOnTcpWritable(PhySocket* sock, void** uptr)
{
}
void VirtualTap::phyOnUnixClose(PhySocket* sock, void** uptr)
{
}
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
// Netif driver code for lwIP network stack // // Netif driver code for lwIP network stack //
@@ -297,17 +338,17 @@ int netifCount = 0;
Mutex stackLock; Mutex stackLock;
// Callback for when the TCPIP thread has been successfully started // Callback for when the TCPIP thread has been successfully started
static void _tcpip_init_done(void *arg) static void _tcpip_init_done(void* arg)
{ {
sys_sem_t *sem; sys_sem_t* sem;
sem = (sys_sem_t *)arg; sem = (sys_sem_t*)arg;
_setState(ZTS_STATE_STACK_RUNNING); _setState(ZTS_STATE_STACK_RUNNING);
_has_started = true; _has_started = true;
_enqueueEvent(ZTS_EVENT_STACK_UP); _enqueueEvent(ZTS_EVENT_STACK_UP);
sys_sem_signal(sem); sys_sem_signal(sem);
} }
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(), ZTS_LWIP_DRIVER_THREAD_NAME); pthread_setname_np(pthread_self(), ZTS_LWIP_DRIVER_THREAD_NAME);
@@ -323,7 +364,7 @@ static void _main_lwip_driver_loop(void *arg)
tcpip_init(_tcpip_init_done, &sem); tcpip_init(_tcpip_init_done, &sem);
sys_sem_wait(&sem); sys_sem_wait(&sem);
// Main loop // Main loop
while(_getState(ZTS_STATE_STACK_RUNNING)) { while (_getState(ZTS_STATE_STACK_RUNNING)) {
zts_delay_ms(LWIP_DRIVER_LOOP_INTERVAL); zts_delay_ms(LWIP_DRIVER_LOOP_INTERVAL);
} }
_has_exited = true; _has_exited = true;
@@ -346,10 +387,14 @@ void _lwip_driver_init()
} }
Mutex::Lock _l(stackLock); Mutex::Lock _l(stackLock);
#if defined(__WINDOWS__) #if defined(__WINDOWS__)
sys_init(); // Required for win32 init of critical sections sys_init(); // Required for win32 init of critical sections
#endif #endif
sys_thread_new(ZTS_LWIP_DRIVER_THREAD_NAME, _main_lwip_driver_loop, sys_thread_new(
NULL, DEFAULT_THREAD_STACKSIZE, DEFAULT_THREAD_PRIO); ZTS_LWIP_DRIVER_THREAD_NAME,
_main_lwip_driver_loop,
NULL,
DEFAULT_THREAD_STACKSIZE,
DEFAULT_THREAD_PRIO);
} }
void _lwip_driver_shutdown() void _lwip_driver_shutdown()
@@ -362,16 +407,18 @@ void _lwip_driver_shutdown()
_clrState(ZTS_STATE_STACK_RUNNING); _clrState(ZTS_STATE_STACK_RUNNING);
// Wait until the main lwIP thread has exited // Wait until the main lwIP thread has exited
if (_has_started) { if (_has_started) {
while (!_has_exited) { zts_delay_ms(LWIP_DRIVER_LOOP_INTERVAL); } while (! _has_exited) {
zts_delay_ms(LWIP_DRIVER_LOOP_INTERVAL);
}
} }
} }
void _lwip_remove_netif(void *netif) void _lwip_remove_netif(void* netif)
{ {
if (!netif) { if (! netif) {
return; return;
} }
struct netif *n = (struct netif*)netif; struct netif* n = (struct netif*)netif;
LOCK_TCPIP_CORE(); LOCK_TCPIP_CORE();
netif_remove(n); netif_remove(n);
netif_set_down(n); netif_set_down(n);
@@ -379,32 +426,32 @@ void _lwip_remove_netif(void *netif)
UNLOCK_TCPIP_CORE(); UNLOCK_TCPIP_CORE();
} }
err_t _lwip_eth_tx(struct netif *n, struct pbuf *p) err_t _lwip_eth_tx(struct netif* n, struct pbuf* p)
{ {
if (!n) { if (! n) {
return ERR_IF; return ERR_IF;
} }
struct pbuf *q; struct pbuf* q;
char buf[ZT_MAX_MTU+32]; char buf[ZT_MAX_MTU + 32];
char *bufptr; char* bufptr;
int totalLength = 0; int totalLength = 0;
VirtualTap *tap = (VirtualTap*)n->state; VirtualTap* tap = (VirtualTap*)n->state;
bufptr = buf; bufptr = buf;
for (q = p; q != NULL; q = q->next) { for (q = p; q != NULL; q = q->next) {
memcpy(bufptr, q->payload, q->len); memcpy(bufptr, q->payload, q->len);
bufptr += q->len; bufptr += q->len;
totalLength += q->len; totalLength += q->len;
} }
struct eth_hdr *ethhdr; struct eth_hdr* ethhdr;
ethhdr = (struct eth_hdr *)buf; ethhdr = (struct eth_hdr*)buf;
MAC src_mac; MAC src_mac;
MAC dest_mac; MAC dest_mac;
src_mac.setTo(ethhdr->src.addr, 6); src_mac.setTo(ethhdr->src.addr, 6);
dest_mac.setTo(ethhdr->dest.addr, 6); dest_mac.setTo(ethhdr->dest.addr, 6);
char *data = buf + sizeof(struct eth_hdr); char* data = buf + sizeof(struct eth_hdr);
int len = totalLength - sizeof(struct eth_hdr); int len = totalLength - sizeof(struct eth_hdr);
int proto = Utils::ntoh((uint16_t)ethhdr->type); int proto = 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);
@@ -412,30 +459,42 @@ err_t _lwip_eth_tx(struct netif *n, struct pbuf *p)
char flagbuf[32]; char flagbuf[32];
memset(&flagbuf, 0, 32); memset(&flagbuf, 0, 32);
char macBuf[ZTS_MAC_ADDRSTRLEN], nodeBuf[16]; char macBuf[ZTS_MAC_ADDRSTRLEN], nodeBuf[16];
snprintf(macBuf, ZTS_MAC_ADDRSTRLEN, "%02x:%02x:%02x:%02x:%02x:%02x", snprintf(
ethhdr->dest.addr[0], ethhdr->dest.addr[1], ethhdr->dest.addr[2], macBuf,
ethhdr->dest.addr[3], ethhdr->dest.addr[4], ethhdr->dest.addr[5]); ZTS_MAC_ADDRSTRLEN,
"%02x:%02x:%02x:%02x:%02x:%02x",
ethhdr->dest.addr[0],
ethhdr->dest.addr[1],
ethhdr->dest.addr[2],
ethhdr->dest.addr[3],
ethhdr->dest.addr[4],
ethhdr->dest.addr[5]);
MAC mac; MAC mac;
mac.setTo(ethhdr->dest.addr, 6); mac.setTo(ethhdr->dest.addr, 6);
mac.toAddress(tap->_nwid).toString(nodeBuf); mac.toAddress(tap->_nwid).toString(nodeBuf);
/* /*
DEBUG_TRANS("len=%5d dst=%s [%s TX <-- %s] ethertype=0x%04x %s", totalLength, macBuf, nodeBuf, tap->nodeId().c_str(), DEBUG_TRANS("len=%5d dst=%s [%s TX <-- %s] ethertype=0x%04x %s", totalLength, macBuf,
Utils::ntoh(ethhdr->type), flagbuf); nodeBuf, tap->nodeId().c_str(), Utils::ntoh(ethhdr->type), flagbuf);
*/ */
} }
return ERR_OK; return ERR_OK;
} }
void _lwip_eth_rx(VirtualTap *tap, const MAC &from, const MAC &to, unsigned int etherType, void _lwip_eth_rx(
const void *data, unsigned int len) VirtualTap* tap,
const MAC& from,
const MAC& to,
unsigned int etherType,
const void* data,
unsigned int len)
{ {
#ifdef LWIP_STATS #ifdef LWIP_STATS
stats_display(); stats_display();
#endif #endif
if (!_getState(ZTS_STATE_STACK_RUNNING)) { if (! _getState(ZTS_STATE_STACK_RUNNING)) {
return; 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);
@@ -445,20 +504,27 @@ void _lwip_eth_rx(VirtualTap *tap, const MAC &from, const MAC &to, unsigned int
char flagbuf[32]; char flagbuf[32];
memset(&flagbuf, 0, 32); memset(&flagbuf, 0, 32);
char macBuf[ZTS_MAC_ADDRSTRLEN], nodeBuf[16]; char macBuf[ZTS_MAC_ADDRSTRLEN], nodeBuf[16];
snprintf(macBuf, ZTS_MAC_ADDRSTRLEN, "%02x:%02x:%02x:%02x:%02x:%02x", snprintf(
ethhdr.dest.addr[0], ethhdr.dest.addr[1], ethhdr.dest.addr[2], macBuf,
ethhdr.dest.addr[3], ethhdr.dest.addr[4], ethhdr.dest.addr[5]); ZTS_MAC_ADDRSTRLEN,
"%02x:%02x:%02x:%02x:%02x:%02x",
ethhdr.dest.addr[0],
ethhdr.dest.addr[1],
ethhdr.dest.addr[2],
ethhdr.dest.addr[3],
ethhdr.dest.addr[4],
ethhdr.dest.addr[5]);
MAC mac; MAC mac;
mac.setTo(ethhdr.src.addr, 6); mac.setTo(ethhdr.src.addr, 6);
mac.toAddress(tap->_nwid).toString(nodeBuf); mac.toAddress(tap->_nwid).toString(nodeBuf);
/* /*
DEBUG_TRANS("len=%5d dst=%s [%s RX --> %s] ethertype=0x%04x %s", len, macBuf, nodeBuf, tap->nodeId().c_str(), DEBUG_TRANS("len=%5d dst=%s [%s RX --> %s] ethertype=0x%04x %s", len, macBuf, nodeBuf,
Utils::ntoh(ethhdr.type), flagbuf); tap->nodeId().c_str(), Utils::ntoh(ethhdr.type), flagbuf);
*/ */
} }
p = pbuf_alloc(PBUF_RAW, (uint16_t)len+sizeof(struct eth_hdr), PBUF_RAM); p = pbuf_alloc(PBUF_RAW, (uint16_t)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");
return; return;
} }
@@ -471,14 +537,14 @@ void _lwip_eth_rx(VirtualTap *tap, const MAC &from, const MAC &to, unsigned int
return; return;
} }
// Copy frame data into pbuf // Copy frame data into pbuf
const char *dataptr = reinterpret_cast<const char *>(data); const char* dataptr = reinterpret_cast<const char*>(data);
memcpy(q->payload,&ethhdr,sizeof(ethhdr)); memcpy(q->payload, &ethhdr, sizeof(ethhdr));
int remainingPayloadSpace = q->len - sizeof(ethhdr); int remainingPayloadSpace = q->len - sizeof(ethhdr);
memcpy((char*)q->payload + sizeof(ethhdr),dataptr,remainingPayloadSpace); memcpy((char*)q->payload + sizeof(ethhdr), dataptr, remainingPayloadSpace);
dataptr += remainingPayloadSpace; dataptr += remainingPayloadSpace;
// Remaining pbufs (if any) get rest of data // Remaining pbufs (if any) get rest of data
while ((q = q->next)) { while ((q = q->next)) {
memcpy(q->payload,dataptr,q->len); memcpy(q->payload, dataptr, q->len);
dataptr += q->len; dataptr += q->len;
} }
// Feed packet into stack // Feed packet into stack
@@ -486,7 +552,8 @@ void _lwip_eth_rx(VirtualTap *tap, const MAC &from, const MAC &to, unsigned int
if (Utils::ntoh(ethhdr.type) == 0x800 || Utils::ntoh(ethhdr.type) == 0x806) { if (Utils::ntoh(ethhdr.type) == 0x800 || Utils::ntoh(ethhdr.type) == 0x806) {
if (tap->netif4) { if (tap->netif4) {
if ((err = ((struct netif *)tap->netif4)->input(p, (struct netif *)tap->netif4)) != ERR_OK) { if ((err = ((struct netif*)tap->netif4)->input(p, (struct netif*)tap->netif4))
!= ERR_OK) {
DEBUG_ERROR("packet input error (%d)", err); DEBUG_ERROR("packet input error (%d)", err);
pbuf_free(p); pbuf_free(p);
} }
@@ -494,7 +561,8 @@ void _lwip_eth_rx(VirtualTap *tap, const MAC &from, const MAC &to, unsigned int
} }
if (Utils::ntoh(ethhdr.type) == 0x86DD) { if (Utils::ntoh(ethhdr.type) == 0x86DD) {
if (tap->netif6) { if (tap->netif6) {
if ((err = ((struct netif *)tap->netif6)->input(p, (struct netif *)tap->netif6)) != ERR_OK) { if ((err = ((struct netif*)tap->netif6)->input(p, (struct netif*)tap->netif6))
!= ERR_OK) {
DEBUG_ERROR("packet input error (%d)", err); DEBUG_ERROR("packet input error (%d)", err);
pbuf_free(p); pbuf_free(p);
} }
@@ -502,9 +570,9 @@ void _lwip_eth_rx(VirtualTap *tap, const MAC &from, const MAC &to, unsigned int
} }
} }
bool _lwip_is_netif_up(void *n) bool _lwip_is_netif_up(void* n)
{ {
if (!n) { if (! n) {
return false; return false;
} }
LOCK_TCPIP_CORE(); LOCK_TCPIP_CORE();
@@ -516,112 +584,102 @@ bool _lwip_is_netif_up(void *n)
/* /*
static struct zts_netif_details *_lwip_prepare_netif_status_msg(struct netif *n) static struct zts_netif_details *_lwip_prepare_netif_status_msg(struct netif *n)
{ {
if (!n || !n->state) { if (!n || !n->state) {
return NULL; return NULL;
} }
VirtualTap *tap = (VirtualTap *)n->state; VirtualTap *tap = (VirtualTap *)n->state;
struct zts_netif_details *details = new zts_netif_details(); struct zts_netif_details *details = new zts_netif_details();
details->nwid = tap->_nwid; details->nwid = tap->_nwid;
memcpy(&(details->mac), n->hwaddr, n->hwaddr_len); memcpy(&(details->mac), n->hwaddr, n->hwaddr_len);
details->mtu = n->mtu; details->mtu = n->mtu;
return details; return details;
} }
static void _netif_remove_callback(struct netif *n) static void _netif_remove_callback(struct netif *n)
{ {
// Called from core, no need to lock // Called from core, no need to lock
if (!n || !n->state) { if (!n || !n->state) {
return; return;
} }
VirtualTap *tap = (VirtualTap *)n->state; VirtualTap *tap = (VirtualTap *)n->state;
struct zts_netif_details *details = new zts_netif_details(); struct zts_netif_details *details = new zts_netif_details();
details->nwid = tap->_nwid; details->nwid = tap->_nwid;
details->mac = 0; details->mac = 0;
details->mtu = 0; details->mtu = 0;
_enqueueEvent(ZTS_EVENT_NETIF_REMOVED, (void*)details); _enqueueEvent(ZTS_EVENT_NETIF_REMOVED, (void*)details);
} }
static void _netif_status_callback(struct netif *n) static void _netif_status_callback(struct netif *n)
{ {
// Called from core, no need to lock // Called from core, no need to lock
if (!n) { if (!n) {
return; return;
} if (netif_is_up(n)) { } if (netif_is_up(n)) {
_enqueueEvent(ZTS_EVENT_NETIF_UP, (void*)_lwip_prepare_netif_status_msg(n)); _enqueueEvent(ZTS_EVENT_NETIF_UP, (void*)_lwip_prepare_netif_status_msg(n));
} else { } else {
_enqueueEvent(ZTS_EVENT_NETIF_DOWN, (void*)_lwip_prepare_netif_status_msg(n)); _enqueueEvent(ZTS_EVENT_NETIF_DOWN, (void*)_lwip_prepare_netif_status_msg(n));
} }
} }
static void _netif_link_callback(struct netif *n) static void _netif_link_callback(struct netif *n)
{ {
// Called from core, no need to lock // Called from core, no need to lock
if (!n) { if (!n) {
return; return;
} if (netif_is_link_up(n)) { } if (netif_is_link_up(n)) {
_enqueueEvent(ZTS_EVENT_NETIF_LINK_UP, (void*)_lwip_prepare_netif_status_msg(n)); _enqueueEvent(ZTS_EVENT_NETIF_LINK_UP, (void*)_lwip_prepare_netif_status_msg(n));
} else { } else {
_enqueueEvent(ZTS_EVENT_NETIF_LINK_DOWN, (void*)_lwip_prepare_netif_status_msg(n)); _enqueueEvent(ZTS_EVENT_NETIF_LINK_DOWN, (void*)_lwip_prepare_netif_status_msg(n));
} }
} }
*/ */
static err_t _netif_init4(struct netif *n) static err_t _netif_init4(struct netif* n)
{ {
if (!n || !n->state) { if (! n || ! n->state) {
return ERR_IF; return ERR_IF;
} }
// Called from core, no need to lock // Called from core, no need to lock
VirtualTap *tap = (VirtualTap*)(n->state); VirtualTap* tap = (VirtualTap*)(n->state);
n->hwaddr_len = 6; n->hwaddr_len = 6;
n->name[0] = '4'; n->name[0] = '4';
n->name[1] = 'a'+netifCount; n->name[1] = 'a' + netifCount;
n->linkoutput = _lwip_eth_tx; n->linkoutput = _lwip_eth_tx;
n->output = etharp_output; n->output = etharp_output;
n->mtu = std::min(LWIP_MTU,(int)tap->_mtu); n->mtu = std::min(LWIP_MTU, (int)tap->_mtu);
n->flags = NETIF_FLAG_BROADCAST n->flags = NETIF_FLAG_BROADCAST | NETIF_FLAG_ETHARP | NETIF_FLAG_ETHERNET | NETIF_FLAG_IGMP
| NETIF_FLAG_ETHARP | NETIF_FLAG_MLD6 | NETIF_FLAG_LINK_UP | NETIF_FLAG_UP;
| NETIF_FLAG_ETHERNET
| NETIF_FLAG_IGMP
| NETIF_FLAG_MLD6
| NETIF_FLAG_LINK_UP
| NETIF_FLAG_UP;
n->hwaddr_len = sizeof(n->hwaddr); n->hwaddr_len = sizeof(n->hwaddr);
tap->_mac.copyTo(n->hwaddr, n->hwaddr_len); tap->_mac.copyTo(n->hwaddr, n->hwaddr_len);
return ERR_OK; return ERR_OK;
} }
static err_t _netif_init6(struct netif *n) static err_t _netif_init6(struct netif* n)
{ {
if (!n || !n->state) { if (! n || ! n->state) {
return ERR_IF; return ERR_IF;
} }
n->hwaddr_len = sizeof(n->hwaddr); n->hwaddr_len = sizeof(n->hwaddr);
VirtualTap *tap = (VirtualTap*)(n->state); VirtualTap* tap = (VirtualTap*)(n->state);
tap->_mac.copyTo(n->hwaddr, n->hwaddr_len); tap->_mac.copyTo(n->hwaddr, n->hwaddr_len);
// Called from core, no need to lock // Called from core, no need to lock
n->hwaddr_len = 6; n->hwaddr_len = 6;
n->name[0] = '6'; n->name[0] = '6';
n->name[1] = 'a'+netifCount; n->name[1] = 'a' + netifCount;
n->linkoutput = _lwip_eth_tx; n->linkoutput = _lwip_eth_tx;
n->output_ip6 = ethip6_output; n->output_ip6 = ethip6_output;
n->mtu = std::min(LWIP_MTU,(int)tap->_mtu); n->mtu = std::min(LWIP_MTU, (int)tap->_mtu);
n->flags = NETIF_FLAG_BROADCAST n->flags = NETIF_FLAG_BROADCAST | NETIF_FLAG_ETHARP | NETIF_FLAG_ETHERNET | NETIF_FLAG_IGMP
| NETIF_FLAG_ETHARP | NETIF_FLAG_MLD6 | NETIF_FLAG_LINK_UP | NETIF_FLAG_UP;
| NETIF_FLAG_ETHERNET
| NETIF_FLAG_IGMP
| NETIF_FLAG_MLD6
| NETIF_FLAG_LINK_UP
| NETIF_FLAG_UP;
return ERR_OK; return ERR_OK;
} }
void _lwip_init_interface(void *tapref, const InetAddress &ip) void _lwip_init_interface(void* tapref, const InetAddress& ip)
{ {
char macbuf[ZTS_MAC_ADDRSTRLEN]; char macbuf[ZTS_MAC_ADDRSTRLEN];
VirtualTap *vtap = (VirtualTap*)tapref; VirtualTap* vtap = (VirtualTap*)tapref;
struct netif *n = NULL; struct netif* n = NULL;
bool isNewNetif = false; bool isNewNetif = false;
if (ip.isV4()) { if (ip.isV4()) {
@@ -639,21 +697,28 @@ void _lwip_init_interface(void *tapref, const InetAddress &ip)
netif_set_link_callback(n, _netif_link_callback); netif_set_link_callback(n, _netif_link_callback);
*/ */
static ip4_addr_t ip4, netmask, gw; static ip4_addr_t ip4, netmask, gw;
IP4_ADDR(&gw,127,0,0,1); IP4_ADDR(&gw, 127, 0, 0, 1);
ip4.addr = *((u32_t *)ip.rawIpData()); ip4.addr = *((u32_t*)ip.rawIpData());
netmask.addr = *((u32_t *)ip.netmask().rawIpData()); netmask.addr = *((u32_t*)ip.netmask().rawIpData());
LOCK_TCPIP_CORE(); LOCK_TCPIP_CORE();
netif_add(n, &ip4, &netmask, &gw, (void*)vtap, _netif_init4, tcpip_input); netif_add(n, &ip4, &netmask, &gw, (void*)vtap, _netif_init4, tcpip_input);
vtap->netif4 = (void*)n; vtap->netif4 = (void*)n;
UNLOCK_TCPIP_CORE(); UNLOCK_TCPIP_CORE();
snprintf(macbuf, ZTS_MAC_ADDRSTRLEN, "%02x:%02x:%02x:%02x:%02x:%02x", snprintf(
n->hwaddr[0], n->hwaddr[1], n->hwaddr[2], macbuf,
n->hwaddr[3], n->hwaddr[4], n->hwaddr[5]); ZTS_MAC_ADDRSTRLEN,
"%02x:%02x:%02x:%02x:%02x:%02x",
n->hwaddr[0],
n->hwaddr[1],
n->hwaddr[2],
n->hwaddr[3],
n->hwaddr[4],
n->hwaddr[5]);
/* /*
char nmbuf[INET6_ADDRSTRLEN]; char nmbuf[INET6_ADDRSTRLEN];
char ipbuf[INET6_ADDRSTRLEN]; char ipbuf[INET6_ADDRSTRLEN];
DEBUG_INFO("initialized netif=%p as [mac=%s, addr=%s, nm=%s, tap=%p]",n, DEBUG_INFO("initialized netif=%p as [mac=%s, addr=%s, nm=%s, tap=%p]",n,
macbuf, ip.toString(ipbuf), ip.netmask().toString(nmbuf), vtap); macbuf, ip.toString(ipbuf), ip.netmask().toString(nmbuf), vtap);
*/ */
} }
if (ip.isV6()) { if (ip.isV6()) {
@@ -664,11 +729,11 @@ void _lwip_init_interface(void *tapref, const InetAddress &ip)
n = new struct netif; n = new struct netif;
isNewNetif = true; isNewNetif = true;
netifCount++; netifCount++;
}/* } /*
netif_set_status_callback(n, _netif_status_callback); netif_set_status_callback(n, _netif_status_callback);
netif_set_remove_callback(n, _netif_remove_callback); netif_set_remove_callback(n, _netif_remove_callback);
netif_set_link_callback(n, _netif_link_callback); netif_set_link_callback(n, _netif_link_callback);
*/ */
static ip6_addr_t ip6; static ip6_addr_t ip6;
memcpy(&(ip6.addr), ip.rawIpData(), sizeof(ip6.addr)); memcpy(&(ip6.addr), ip.rawIpData(), sizeof(ip6.addr));
LOCK_TCPIP_CORE(); LOCK_TCPIP_CORE();
@@ -682,26 +747,33 @@ void _lwip_init_interface(void *tapref, const InetAddress &ip)
netif_set_up(n); netif_set_up(n);
netif_set_default(n); netif_set_default(n);
} }
netif_add_ip6_address(n,&ip6,NULL); netif_add_ip6_address(n, &ip6, NULL);
n->output_ip6 = ethip6_output; n->output_ip6 = ethip6_output;
UNLOCK_TCPIP_CORE(); UNLOCK_TCPIP_CORE();
snprintf(macbuf, ZTS_MAC_ADDRSTRLEN, "%02x:%02x:%02x:%02x:%02x:%02x", snprintf(
n->hwaddr[0], n->hwaddr[1], n->hwaddr[2], macbuf,
n->hwaddr[3], n->hwaddr[4], n->hwaddr[5]); ZTS_MAC_ADDRSTRLEN,
"%02x:%02x:%02x:%02x:%02x:%02x",
n->hwaddr[0],
n->hwaddr[1],
n->hwaddr[2],
n->hwaddr[3],
n->hwaddr[4],
n->hwaddr[5]);
/* /*
DEBUG_INFO("initialized netif=%p as [mac=%s, addr=%s, tap=%p]", n, DEBUG_INFO("initialized netif=%p as [mac=%s, addr=%s, tap=%p]", n,
macbuf, ip.toString(ipbuf), vtap); macbuf, ip.toString(ipbuf), vtap);
*/ */
} }
} }
void _lwip_remove_address_from_netif(void *tapref, const InetAddress &ip) void _lwip_remove_address_from_netif(void* tapref, const InetAddress& ip)
{ {
if (!tapref) { if (! tapref) {
return; return;
} }
VirtualTap *vtap = (VirtualTap*)tapref; VirtualTap* vtap = (VirtualTap*)tapref;
struct netif *n = NULL; struct netif* n = NULL;
/* When true multi-homing is implemented this will need to /* When true multi-homing is implemented this will need to
be a bit more sophisticated */ be a bit more sophisticated */
if (ip.isV4()) { if (ip.isV4()) {
@@ -714,10 +786,10 @@ void _lwip_remove_address_from_netif(void *tapref, const InetAddress &ip)
n = (struct netif*)vtap->netif6; n = (struct netif*)vtap->netif6;
} }
} }
if (!n) { if (! n) {
return; return;
} }
_lwip_remove_netif(n); _lwip_remove_netif(n);
} }
} // namespace ZeroTier } // namespace ZeroTier

View File

@@ -39,21 +39,28 @@ struct InetAddress;
* A virtual tap device. The ZeroTier Node Service will create one per * A virtual tap device. The ZeroTier Node Service will create one per
* joined network. It will be destroyed upon leave(). * joined network. It will be destroyed upon leave().
*/ */
class VirtualTap class VirtualTap {
{ friend class Phy<VirtualTap*>;
friend class Phy<VirtualTap *>;
public: public:
VirtualTap( VirtualTap(
const char *homePath, const char* homePath,
const MAC &mac, const MAC& mac,
unsigned int mtu, unsigned int mtu,
unsigned int metric, unsigned int metric,
uint64_t nwid, uint64_t nwid,
const char *friendlyName, const char* friendlyName,
void (*handler)(void *, void *, uint64_t, const MAC &, void (*handler)(
const MAC &, unsigned int, unsigned int, const void *, unsigned int), void*,
void *arg); void*,
uint64_t,
const MAC&,
const MAC&,
unsigned int,
unsigned int,
const void*,
unsigned int),
void* arg);
~VirtualTap(); ~VirtualTap();
@@ -63,7 +70,7 @@ public:
/** /**
* Mutex for protecting IP address container for this tap. * Mutex for protecting IP address container for this tap.
*/ */
Mutex _ips_m; // Public because we want it accessible by the driver layer Mutex _ips_m; // Public because we want it accessible by the driver layer
/** /**
* Return whether this tap has been assigned an IPv4 address. * Return whether this tap has been assigned an IPv4 address.
@@ -79,18 +86,18 @@ public:
* Adds an address to the user-space stack interface associated with this VirtualTap * Adds an address to the user-space stack interface associated with this VirtualTap
* - Starts VirtualTap main thread ONLY if successful * - Starts VirtualTap main thread ONLY if successful
*/ */
bool addIp(const InetAddress &ip); bool addIp(const InetAddress& ip);
/** /**
* Removes an address from the user-space stack interface associated with this VirtualTap * Removes an address from the user-space stack interface associated with this VirtualTap
*/ */
bool removeIp(const InetAddress &ip); bool removeIp(const InetAddress& ip);
/** /**
* Presents data to the user-space stack * Presents data to the user-space stack
*/ */
void put(const MAC &from,const MAC &to,unsigned int etherType,const void *data, void
unsigned int len); put(const MAC& from, const MAC& to, unsigned int etherType, const void* data, unsigned int len);
/** /**
* Get VirtualTap device name (e.g. 'libzt17d72843bc2c5760') * Get VirtualTap device name (e.g. 'libzt17d72843bc2c5760')
@@ -100,13 +107,13 @@ public:
/** /**
* Set friendly name * Set friendly name
*/ */
void setFriendlyName(const char *friendlyName); void setFriendlyName(const char* friendlyName);
/** /**
* Scan multicast groups * Scan multicast groups
*/ */
void scanMulticastGroups(std::vector<MulticastGroup> &added, void
std::vector<MulticastGroup> &removed); scanMulticastGroups(std::vector<MulticastGroup>& added, std::vector<MulticastGroup>& removed);
/** /**
* Set MTU * Set MTU
@@ -116,17 +123,24 @@ public:
/** /**
* Calls main network stack loops * Calls main network stack loops
*/ */
void threadMain() void threadMain() throw();
throw();
/** /**
* For moving data onto the ZeroTier virtual wire * For moving data onto the ZeroTier virtual wire
*/ */
void (*_handler)(void *, void *, uint64_t, const MAC &, const MAC &, unsigned int, unsigned int, void (*_handler)(
const void *, unsigned int); void*,
void*,
uint64_t,
const MAC&,
const MAC&,
unsigned int,
unsigned int,
const void*,
unsigned int);
void *netif4 = NULL; void* netif4 = NULL;
void *netif6 = NULL; void* netif6 = NULL;
/** /**
* The last time that this virtual tap received a network config update from the core * The last time that this virtual tap received a network config update from the core
@@ -143,21 +157,21 @@ public:
std::vector<InetAddress> _ips; std::vector<InetAddress> _ips;
std::string _homePath; std::string _homePath;
void *_arg; void* _arg;
volatile bool _initialized; volatile bool _initialized;
volatile bool _enabled; volatile bool _enabled;
volatile bool _run; volatile bool _run;
MAC _mac; MAC _mac;
unsigned int _mtu; unsigned int _mtu;
uint64_t _nwid; uint64_t _nwid;
PhySocket *_unixListenSocket; PhySocket* _unixListenSocket;
Phy<VirtualTap *> _phy; Phy<VirtualTap*> _phy;
Thread _thread; Thread _thread;
int _shutdownSignalPipe[2]; int _shutdownSignalPipe[2];
std::string _dev; // path to Unix domain socket std::string _dev; // path to Unix domain socket
std::vector<MulticastGroup> _multicastGroups; std::vector<MulticastGroup> _multicastGroups;
Mutex _multicastGroups_m; Mutex _multicastGroups_m;
@@ -166,15 +180,24 @@ public:
// Not used in this implementation // // Not used in this implementation //
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
void phyOnDatagram(PhySocket *sock,void **uptr,const struct sockaddr *local_address, void phyOnDatagram(
const struct sockaddr *from,void *data,unsigned long len); PhySocket* sock,
void phyOnTcpConnect(PhySocket *sock,void **uptr,bool success); void** uptr,
void phyOnTcpAccept(PhySocket *sockL,PhySocket *sockN,void **uptrL,void **uptrN, const struct sockaddr* local_address,
const struct sockaddr *from); const struct sockaddr* from,
void phyOnTcpClose(PhySocket *sock,void **uptr); void* data,
void phyOnTcpData(PhySocket *sock,void **uptr,void *data,unsigned long len); unsigned long len);
void phyOnTcpWritable(PhySocket *sock,void **uptr); void phyOnTcpConnect(PhySocket* sock, void** uptr, bool success);
void phyOnUnixClose(PhySocket *sock,void **uptr); void phyOnTcpAccept(
PhySocket* sockL,
PhySocket* sockN,
void** uptrL,
void** uptrN,
const struct sockaddr* from);
void phyOnTcpClose(PhySocket* sock, void** uptr);
void phyOnTcpData(PhySocket* sock, void** uptr, void* data, unsigned long len);
void phyOnTcpWritable(PhySocket* sock, void** uptr);
void phyOnUnixClose(PhySocket* sock, void** uptr);
}; };
/** /**
@@ -182,7 +205,7 @@ public:
* *
* @usage This is a convenience function to encapsulate a macro * @usage This is a convenience function to encapsulate a macro
*/ */
bool _lwip_is_netif_up(void *netif); 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
@@ -206,28 +229,29 @@ bool _lwip_is_up();
/** /**
* @brief Initialize network stack semaphores, threads, and timers. * @brief Initialize network stack semaphores, threads, and timers.
* *
* @usage This is called during the initial setup of each VirtualTap but is only allowed to execute once * @usage This is called during the initial setup of each VirtualTap but is only allowed to execute
* once
*/ */
void _lwip_driver_init(); void _lwip_driver_init();
/** /**
* @brief Shutdown the stack as completely as possible (not officially supported by lwIP) * @brief Shutdown the stack as completely as possible (not officially supported by lwIP)
* *
* @usage This is to be called after it is determined that no further network activity will take place. * @usage This is to be called after it is determined that no further network activity will take
* The tcpip thread will be stopped, all interfaces will be brought down and all resources will * place. The tcpip thread will be stopped, all interfaces will be brought down and all resources
* be deallocated. A full application restart will be required to bring the stack back online. * will be deallocated. A full application restart will be required to bring the stack back online.
*/ */
void _lwip_driver_shutdown(); void _lwip_driver_shutdown();
/** /**
* @brief Requests that a netif be brought down and removed. * @brief Requests that a netif be brought down and removed.
*/ */
void _lwip_remove_netif(void *netif); void _lwip_remove_netif(void* netif);
/** /**
* @brief Starts DHCP timers * @brief Starts DHCP timers
*/ */
void _lwip_start_dhcp(void *netif); void _lwip_start_dhcp(void* netif);
/** /**
* @brief Called when the status of a netif changes: * @brief Called when the status of a netif changes:
@@ -235,21 +259,22 @@ void _lwip_start_dhcp(void *netif);
* - Address changes while up (ZTS_EVENT_NETIF_NEW_ADDRESS) * - Address changes while up (ZTS_EVENT_NETIF_NEW_ADDRESS)
*/ */
#if LWIP_NETIF_STATUS_CALLBACK #if LWIP_NETIF_STATUS_CALLBACK
static void _netif_status_callback(struct netif *netif); static void _netif_status_callback(struct netif* netif);
#endif #endif
/** /**
* @brief Called when a netif is removed (ZTS_EVENT_NETIF_INTERFACE_REMOVED) * @brief Called when a netif is removed (ZTS_EVENT_NETIF_INTERFACE_REMOVED)
*/ */
#if LWIP_NETIF_REMOVE_CALLBACK #if LWIP_NETIF_REMOVE_CALLBACK
static void _netif_remove_callback(struct netif *netif); static void _netif_remove_callback(struct netif* netif);
#endif #endif
/** /**
* @brief Called when a link is brought up or down (ZTS_EVENT_NETIF_LINK_UP, ZTS_EVENT_NETIF_LINK_DOWN) * @brief Called when a link is brought up or down (ZTS_EVENT_NETIF_LINK_UP,
* ZTS_EVENT_NETIF_LINK_DOWN)
*/ */
#if LWIP_NETIF_LINK_CALLBACK #if LWIP_NETIF_LINK_CALLBACK
static void _netif_link_callback(struct netif *netif); static void _netif_link_callback(struct netif* netif);
#endif #endif
/** /**
@@ -258,7 +283,7 @@ static void _netif_link_callback(struct netif *netif);
* @param tapref Reference to VirtualTap that will be responsible for sending and receiving data * @param tapref Reference to VirtualTap that will be responsible for sending and receiving data
* @param ip Virtual IP address for this ZeroTier VirtualTap interface * @param ip Virtual IP address for this ZeroTier VirtualTap interface
*/ */
void _lwip_init_interface(void *tapref, const InetAddress &ip); void _lwip_init_interface(void* tapref, const InetAddress& ip);
/** /**
* @brief Remove an assigned address from an lwIP netif * @brief Remove an assigned address from an lwIP netif
@@ -266,17 +291,19 @@ void _lwip_init_interface(void *tapref, const InetAddress &ip);
* @param tapref Reference to VirtualTap * @param tapref Reference to VirtualTap
* @param ip Virtual IP address to remove from this interface * @param ip Virtual IP address to remove from this interface
*/ */
void _lwip_remove_address_from_netif(void *tapref, const InetAddress &ip); void _lwip_remove_address_from_netif(void* tapref, 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.
* *
* @usage This shall only be called from the stack or the stack driver. Not the application thread. * @usage This shall only be called from the stack or the stack driver. Not the application thread.
* @param netif Transmits an outgoing Ethernet fram from the network stack onto the ZeroTier virtual wire * @param netif Transmits an outgoing Ethernet fram from the network stack onto the ZeroTier virtual
* wire
* @param p A pointer to the beginning of a chain pf struct pbufs * @param p A pointer to the beginning of a chain pf struct pbufs
* @return * @return
*/ */
err_t _lwip_eth_tx(struct netif *netif, struct pbuf *p); err_t _lwip_eth_tx(struct netif* netif, struct pbuf* p);
/** /**
* @brief Receives incoming Ethernet frames from the ZeroTier virtual wire * @brief Receives incoming Ethernet frames from the ZeroTier virtual wire
@@ -289,10 +316,14 @@ err_t _lwip_eth_tx(struct netif *netif, struct pbuf *p);
* @param data Pointer to Ethernet frame * @param data Pointer to Ethernet frame
* @param len Length of Ethernet frame * @param len Length of Ethernet frame
*/ */
void _lwip_eth_rx(VirtualTap *tap, const MAC &from, const MAC &to, unsigned int etherType, void _lwip_eth_rx(
const void *data, unsigned int len); VirtualTap* tap,
const MAC& from,
const MAC& to,
unsigned int etherType,
const void* data,
unsigned int len);
} // namespace ZeroTier } // namespace ZeroTier
#endif // _H
#endif // _H