Skip to content

Commit

Permalink
single dns config per network
Browse files Browse the repository at this point in the history
  • Loading branch information
glimberg committed Aug 12, 2020
1 parent 058d888 commit c0c215c
Show file tree
Hide file tree
Showing 9 changed files with 76 additions and 147 deletions.
25 changes: 9 additions & 16 deletions controller/EmbeddedNetworkController.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1711,25 +1711,18 @@ void EmbeddedNetworkController::_request(
}
}

if(dns.is_array()) {
nc->dnsCount = 0;
for(unsigned int p=0; p < dns.size(); ++p) {
json &d = dns[p];
if (d.is_object()) {
std::string domain = OSUtils::jsonString(d["domain"],"");
memcpy(nc->dns[nc->dnsCount].domain, domain.c_str(), domain.size());
json &addrArray = d["servers"];
if (addrArray.is_array()) {
for(unsigned int j = 0; j < addrArray.size() && j < ZT_MAX_DNS_SERVERS; ++j) {
json &addr = addrArray[j];
nc->dns[nc->dnsCount].server_addr[j] = InetAddress(OSUtils::jsonString(addr,"").c_str());
}
}
++nc->dnsCount;
if(dns.is_object()) {
std::string domain = OSUtils::jsonString(dns["domain"],"");
memcpy(nc->dns.domain, domain.c_str(), domain.size());
json &addrArray = dns["servers"];
if (addrArray.is_array()) {
for(unsigned int j = 0; j < addrArray.size() && j < ZT_MAX_DNS_SERVERS; ++j) {
json &addr = addrArray[j];
nc->dns.server_addr[j] = InetAddress(OSUtils::jsonString(addr,"").c_str());
}
}
} else {
dns = json::array();
dns = json::object();
}

// Issue a certificate of ownership for all static IPs
Expand Down
87 changes: 29 additions & 58 deletions controller/PostgreSQL.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -447,12 +447,12 @@ void PostgreSQL::initializeNetworks(PGconn *conn)
}

n = PQntuples(r2);
config["dns"] = json::array();
for (int j = 0; j < n; ++j) {

if (n > 1) {
fprintf(stderr, "ERROR: invalid number of DNS configurations for network %s. Must be 0 or 1\n", nwid.c_str());
} else if (n == 1) {
json obj;
std::string domain = PQgetvalue(r2, j, 0);
std::string serverList = PQgetvalue(r2, j, 1);
std::string domain = PQgetvalue(r2, 0, 0);
std::string serverList = PQgetvalue(r2, 0, 1);
auto servers = json::array();
if (serverList.rfind("{",0) != std::string::npos) {
serverList = serverList.substr(1, serverList.size()-2);
Expand All @@ -465,7 +465,7 @@ void PostgreSQL::initializeNetworks(PGconn *conn)
}
obj["domain"] = domain;
obj["servers"] = servers;
config["dns"].push_back(obj);
config["dns"] = obj;
}

PQclear(r2);
Expand Down Expand Up @@ -1461,67 +1461,38 @@ void PostgreSQL::commitThread()
config = nullptr;
continue;
}
auto dns = (*config)["dns"];
std::string domain = dns["domain"];
std::stringstream servers;
servers << "{";
for (auto j = dns["servers"].begin(); j < dns["servers"].end(); ++j) {
servers << *j;
if ( (j+1) != dns["servers"].end()) {
servers << ",";
}
}
servers << "}";

const char *p[3] = {
id.c_str(),
domain.c_str(),
servers.str().c_str()
};

res = PQexecParams(conn,
"DELETE FROM ztc_network_dns WHERE network_id = $1",
1,
res = PQexecParams(conn, "INSERT INTO ztc_network_dns (network_id, domain, servers) VALUES ($1, $2, $3) ON CONFLICT (network_id) DO UPDATE SET domain = EXCLUDED.domain, servers = EXCLUDED.servers",
3,
NULL,
params,
p,
NULL,
NULL,
0);

if (PQresultStatus(res) != PGRES_COMMAND_OK) {
fprintf(stderr, "ERROR: Error updating dns: %s\n", PQresultErrorMessage(res));
fprintf(stderr, "ERROR: Error updating DNS: %s\n", PQresultErrorMessage(res));
PQclear(res);
PQclear(PQexec(conn, "ROLLBACK"));
delete config;
config = nullptr;
continue;
}

auto dns = (*config)["dns"];
err = false;
for (auto i = dns.begin(); i < dns.end(); ++i) {
std::string domain = (*i)["domain"];
std::stringstream servers;
servers << "{";
for (auto j = dns["servers"].begin(); j < dns["servers"].end(); ++j) {
servers << *j;
if ( (j+1) != dns["servers"].end()) {
servers << ",";
}
}
servers << "}";

const char *p[3] = {
id.c_str(),
domain.c_str(),
servers.str().c_str()
};

res = PQexecParams(conn, "INSERT INTO ztc_network_dns (network_id, domain, servers) VALUES ($1, $2, $3)",
3,
NULL,
p,
NULL,
NULL,
0);
if (PQresultStatus(res) != PGRES_COMMAND_OK) {
fprintf(stderr, "ERROR: Error updating DNS: %s\n", PQresultErrorMessage(res));
PQclear(res);
err = true;
break;
}
PQclear(res);
}
if (err) {
PQclear(PQexec(conn, "ROLLBACK"));
delete config;
config = nullptr;
continue;
err = true;
break;
}
PQclear(res);

res = PQexec(conn, "COMMIT");
if (PQresultStatus(res) != PGRES_COMMAND_OK) {
Expand Down
12 changes: 1 addition & 11 deletions include/ZeroTierOne.h
Original file line number Diff line number Diff line change
Expand Up @@ -125,11 +125,6 @@ extern "C" {
*/
#define ZT_MAX_NETWORK_ROUTES 32

/**
* Maximum number of pushed DNS configurations on a network
*/
#define ZT_MAX_NETWORK_DNS 32

/**
* Maximum number of statically assigned IP addresses per network endpoint using ZT address management (not DHCP)
*/
Expand Down Expand Up @@ -1339,16 +1334,11 @@ typedef struct
uint64_t mac; /* MAC in lower 48 bits */
uint32_t adi; /* Additional distinguishing information, usually zero except for IPv4 ARP groups */
} multicastSubscriptions[ZT_MAX_MULTICAST_SUBSCRIPTIONS];

/**
* Number of ZT-pushed DNS configuraitons
*/
unsigned int dnsCount;

/**
* Network specific DNS configuration
*/
ZT_VirtualNetworkDNS dns[ZT_MAX_NETWORK_DNS];
ZT_VirtualNetworkDNS dns;
} ZT_VirtualNetworkConfig;

/**
Expand Down
28 changes: 12 additions & 16 deletions node/DNS.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -29,28 +29,24 @@ namespace ZeroTier {
class DNS {
public:
template<unsigned int C>
static inline void serializeDNS(Buffer<C> &b, const ZT_VirtualNetworkDNS *dns, unsigned int dnsCount)
static inline void serializeDNS(Buffer<C> &b, const ZT_VirtualNetworkDNS *dns)
{
for(unsigned int i = 0; i < dnsCount; ++i) {
b.append(dns[i].domain, 128);
for(unsigned int j = 0; j < ZT_MAX_DNS_SERVERS; ++j) {
InetAddress tmp(dns[i].server_addr[j]);
tmp.serialize(b);
}
b.append(dns->domain, 128);
for(unsigned int j = 0; j < ZT_MAX_DNS_SERVERS; ++j) {
InetAddress tmp(dns->server_addr[j]);
tmp.serialize(b);
}
}

template<unsigned int C>
static inline void deserializeDNS(const Buffer<C> &b, unsigned int &p, ZT_VirtualNetworkDNS *dns, const unsigned int dnsCount)
static inline void deserializeDNS(const Buffer<C> &b, unsigned int &p, ZT_VirtualNetworkDNS *dns)
{
memset(dns, 0, sizeof(ZT_VirtualNetworkDNS)*ZT_MAX_NETWORK_DNS);
for(unsigned int i = 0; i < dnsCount; ++i) {
char *d = (char*)b.data()+p;
memcpy(dns[i].domain, d, 128);
p += 128;
for (unsigned int j = 0; j < ZT_MAX_DNS_SERVERS; ++j) {
p += reinterpret_cast<InetAddress *>(&(dns[i].server_addr[j]))->deserialize(b, p);
}
char *d = (char*)b.data()+p;
memset(dns, 0, sizeof(ZT_VirtualNetworkDNS));
memcpy(dns->domain, d, 128);
p += 128;
for (unsigned int j = 0; j < ZT_MAX_DNS_SERVERS; ++j) {
p += reinterpret_cast<InetAddress *>(&(dns->server_addr[j]))->deserialize(b, p);
}
}
};
Expand Down
6 changes: 1 addition & 5 deletions node/Network.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1428,11 +1428,7 @@ void Network::_externalConfig(ZT_VirtualNetworkConfig *ec) const
ec->multicastSubscriptions[i].adi = _myMulticastGroups[i].adi();
}

ec->dnsCount = _config.dnsCount;
fprintf(stderr, "Network::_externalConfig dnsCount: %d\n", ec->dnsCount);
if (ec->dnsCount > 0) {
memcpy(&ec->dns, &_config.dns, sizeof(ZT_VirtualNetworkDNS));
}
memcpy(&ec->dns, &_config.dns, sizeof(ZT_VirtualNetworkDNS));
}

void Network::_sendUpdatesToMembers(void *tPtr,const MulticastGroup *const newMulticastGroup)
Expand Down
13 changes: 4 additions & 9 deletions node/NetworkConfig.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -177,12 +177,9 @@ bool NetworkConfig::toDictionary(Dictionary<ZT_NETWORKCONFIG_DICT_CAPACITY> &d,b
}

tmp->clear();
if (dnsCount > 0) {
tmp->append(dnsCount);
DNS::serializeDNS(*tmp, dns, dnsCount);
if (tmp->size()) {
if (!d.add(ZT_NETWORKCONFIG_DICT_KEY_DNS,*tmp)) return false;
}
DNS::serializeDNS(*tmp, &dns);
if (tmp->size()) {
if (!d.add(ZT_NETWORKCONFIG_DICT_KEY_DNS,*tmp)) return false;
}

delete tmp;
Expand Down Expand Up @@ -366,9 +363,7 @@ bool NetworkConfig::fromDictionary(const Dictionary<ZT_NETWORKCONFIG_DICT_CAPACI

if (d.get(ZT_NETWORKCONFIG_DICT_KEY_DNS, *tmp)) {
unsigned int p = 0;
this->dnsCount = tmp->at<unsigned int>(p);
p += sizeof(unsigned int);
DNS::deserializeDNS(*tmp, p, dns, (this->dnsCount <= ZT_MAX_NETWORK_DNS) ? this->dnsCount : ZT_MAX_NETWORK_DNS);
DNS::deserializeDNS(*tmp, p, &dns);
}
}

Expand Down
4 changes: 2 additions & 2 deletions node/NetworkConfig.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -240,7 +240,7 @@ class NetworkConfig
memset(routes, 0, sizeof(ZT_VirtualNetworkRoute)*ZT_MAX_NETWORK_ROUTES);
memset(staticIps, 0, sizeof(InetAddress)*ZT_MAX_ZT_ASSIGNED_ADDRESSES);
memset(rules, 0, sizeof(ZT_VirtualNetworkRule)*ZT_MAX_NETWORK_RULES);
memset(dns, 0, sizeof(ZT_VirtualNetworkDNS)*ZT_MAX_NETWORK_DNS);
memset(&dns, 0, sizeof(ZT_VirtualNetworkDNS));
}

/**
Expand Down Expand Up @@ -603,7 +603,7 @@ class NetworkConfig
/**
* ZT pushed DNS configuration
*/
ZT_VirtualNetworkDNS dns[ZT_MAX_NETWORK_DNS];
ZT_VirtualNetworkDNS dns;
};

} // namespace ZeroTier
Expand Down
1 change: 0 additions & 1 deletion osdep/MacDNSHelper.mm
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,6 @@
CFDictionaryRef dict = CFDictionaryCreate(NULL,
(const void**)keys, (const void**)values, 2, &kCFCopyStringDictionaryKeyCallBacks,
&kCFTypeDictionaryValueCallBacks);
CFShow(dict);

char buf[256] = {0};
sprintf(buf, "State:/Network/Service/%.16llx/DNS", nwid);
Expand Down
47 changes: 18 additions & 29 deletions service/OneService.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -232,20 +232,19 @@ static void _networkToJson(nlohmann::json &nj,const ZT_VirtualNetworkConfig *nc,
}
nj["multicastSubscriptions"] = mca;

nj["dns"] = nlohmann::json::array();
for(unsigned int i=0;i<nc->dnsCount;++i) {
nlohmann::json m;
m["domain"] = nc->dns[i].domain;
m["servers"] = nlohmann::json::array();
for(int j=0;j<ZT_MAX_DNS_SERVERS;++j) {

InetAddress a(nc->dns[i].server_addr[j]);
if (a.isV4() || a.isV6()) {
char buf[256];
m["servers"].push_back(a.toIpString(buf));
}
nlohmann::json m;
m["domain"] = nc->dns.domain;
m["servers"] = nlohmann::json::array();
for(int j=0;j<ZT_MAX_DNS_SERVERS;++j) {

InetAddress a(nc->dns.server_addr[j]);
if (a.isV4() || a.isV6()) {
char buf[256];
m["servers"].push_back(a.toIpString(buf));
}
}
nj["dns"] = m;

}

static void _peerToJson(nlohmann::json &pj,const ZT_Peer *peer)
Expand Down Expand Up @@ -2002,25 +2001,15 @@ class OneServiceImpl : public OneService
}

if (syncDns) {
char buf[128];
if (n.config.dnsCount > ZT_MAX_NETWORK_DNS) {
fprintf(stderr, "ERROR: %d records > max %d. Skipping DNS\n", n.config.dnsCount, ZT_MAX_NETWORK_DNS);
return;
}
fprintf(stderr, "Syncing %d DNS configurations for network [%.16llx]\n", n.config.dnsCount, n.config.nwid);
for (int i = 0; i < n.config.dnsCount; ++i) {
if (strlen(n.config.dns[i].domain) != 0) {
fprintf(stderr, "Syncing DNS for domain: %s\n", n.config.dns[i].domain);
std::vector<InetAddress> servers;
for (int j = 0; j < ZT_MAX_DNS_SERVERS; ++j) {
InetAddress a(n.config.dns[i].server_addr[j]);
if (a.isV4() || a.isV6()) {
fprintf(stderr, "\t Server %d: %s\n", j+1, a.toIpString(buf));
servers.push_back(a);
}
if (strlen(n.config.dns.domain) != 0) {
std::vector<InetAddress> servers;
for (int j = 0; j < ZT_MAX_DNS_SERVERS; ++j) {
InetAddress a(n.config.dns.server_addr[j]);
if (a.isV4() || a.isV6()) {
servers.push_back(a);
}
n.tap->setDns(n.config.dns[i].domain, servers);
}
n.tap->setDns(n.config.dns.domain, servers);
}
}
}
Expand Down

0 comments on commit c0c215c

Please sign in to comment.