summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMichał Zieliński <michal@zielinscy.org.pl>2017-01-22 23:02:34 +0100
committerMichał Zieliński <michal@zielinscy.org.pl>2017-01-23 12:16:40 +0100
commit8f2a42d1ad84e5dba590e7f593d8a46cc81389b3 (patch)
treee61e1ff9fb430eb1d9eadf16ed5daacfa9551071
parent9a475eeff90a181af0661b87b09af7337e39167a (diff)
downloadinfinitytier-8f2a42d1ad84e5dba590e7f593d8a46cc81389b3.tar.gz
infinitytier-8f2a42d1ad84e5dba590e7f593d8a46cc81389b3.zip
allow user to specify arbitrary allowed IP networks in allowManaged
-rw-r--r--node/Buffer.hpp10
-rw-r--r--service/ControlPlane.cpp11
-rw-r--r--service/OneService.cpp41
-rw-r--r--service/OneService.hpp7
4 files changed, 60 insertions, 9 deletions
diff --git a/node/Buffer.hpp b/node/Buffer.hpp
index 0b171592..1a478894 100644
--- a/node/Buffer.hpp
+++ b/node/Buffer.hpp
@@ -61,11 +61,11 @@ public:
// STL container idioms
typedef unsigned char value_type;
typedef unsigned char * pointer;
- typedef const unsigned char * const_pointer;
- typedef unsigned char & reference;
- typedef const unsigned char & const_reference;
- typedef unsigned char * iterator;
- typedef const unsigned char * const_iterator;
+ typedef const char * const_pointer;
+ typedef char & reference;
+ typedef const char & const_reference;
+ typedef char * iterator;
+ typedef const char * const_iterator;
typedef unsigned int size_type;
typedef int difference_type;
typedef std::reverse_iterator<iterator> reverse_iterator;
diff --git a/service/ControlPlane.cpp b/service/ControlPlane.cpp
index 86158a91..27027d3b 100644
--- a/service/ControlPlane.cpp
+++ b/service/ControlPlane.cpp
@@ -121,6 +121,15 @@ static void _jsonAppend(unsigned int depth,std::string &buf,const ZT_VirtualNetw
case ZT_NETWORK_TYPE_PUBLIC: ntype = "PUBLIC"; break;
}
+ std::string allowManaged = (localSettings.allowManaged) ? "true" : "false";
+ if (localSettings.allowManagedWhitelist.size() != 0) {
+ allowManaged = "";
+ for (InetAddress address : localSettings.allowManagedWhitelist) {
+ if (allowManaged.size() != 0) allowManaged += ',';
+ allowManaged += address.toIpString() + "/" + std::to_string(address.netmaskBits());
+ }
+ }
+
Utils::snprintf(json,sizeof(json),
"%s{\n"
"%s\t\"id\": \"%.16llx\",\n"
@@ -158,7 +167,7 @@ static void _jsonAppend(unsigned int depth,std::string &buf,const ZT_VirtualNetw
prefix,_jsonEnumerate(nc->assignedAddresses,nc->assignedAddressCount).c_str(),
prefix,_jsonEnumerate(nc->routes,nc->routeCount).c_str(),
prefix,_jsonEscape(portDeviceName).c_str(),
- prefix,(localSettings.allowManaged) ? "true" : "false",
+ prefix,allowManaged.c_str(),
prefix,(localSettings.allowGlobal) ? "true" : "false",
prefix,(localSettings.allowDefault) ? "true" : "false",
prefix);
diff --git a/service/OneService.cpp b/service/OneService.cpp
index 93f5b5f0..603234a2 100644
--- a/service/OneService.cpp
+++ b/service/OneService.cpp
@@ -1039,6 +1039,18 @@ public:
{
if (!n.settings.allowManaged)
return false;
+
+ if (n.settings.allowManagedWhitelist.size() > 0) {
+ bool allowed = false;
+ for (InetAddress addr : n.settings.allowManagedWhitelist) {
+ if (addr.containsAddress(target) && addr.netmaskBits() <= target.netmaskBits()) {
+ allowed = true;
+ break;
+ }
+ }
+ if (!allowed) return false;
+ }
+
if (target.isDefaultRoute())
return n.settings.allowDefault;
switch(target.ipScope()) {
@@ -1423,9 +1435,32 @@ public:
if (OSUtils::readFile(nlcpath,nlcbuf)) {
Dictionary<4096> nc;
nc.load(nlcbuf.c_str());
- n.settings.allowManaged = nc.getB("allowManaged",true);
- n.settings.allowGlobal = nc.getB("allowGlobal",false);
- n.settings.allowDefault = nc.getB("allowDefault",false);
+ Buffer<1024> allowManaged;
+ if (nc.get("allowManaged", allowManaged) && allowManaged.size() != 0) {
+ std::string addresses (allowManaged.begin(), allowManaged.size());
+ if (allowManaged.size() <= 5) { // untidy parsing for backward compatibility
+ if (allowManaged[0] == '1' || allowManaged[0] == 't' || allowManaged[0] == 'T') {
+ n.settings.allowManaged = true;
+ } else {
+ n.settings.allowManaged = false;
+ }
+ } else {
+ // this should be a list of IP addresses
+ n.settings.allowManaged = true;
+ size_t pos = 0;
+ while (true) {
+ size_t nextPos = addresses.find(',', pos);
+ std::string address = addresses.substr(pos, (nextPos == std::string::npos ? addresses.size() : nextPos) - pos);
+ n.settings.allowManagedWhitelist.push_back(InetAddress(address));
+ if (nextPos == std::string::npos) break;
+ pos = nextPos + 1;
+ }
+ }
+ } else {
+ n.settings.allowManaged = true;
+ }
+ n.settings.allowGlobal = nc.getB("allowGlobal", false);
+ n.settings.allowDefault = nc.getB("allowDefault", false);
}
} catch (std::exception &exc) {
#ifdef __WINDOWS__
diff --git a/service/OneService.hpp b/service/OneService.hpp
index 7aa3b361..88225da4 100644
--- a/service/OneService.hpp
+++ b/service/OneService.hpp
@@ -20,6 +20,7 @@
#define ZT_ONESERVICE_HPP
#include <string>
+#include <vector>
namespace ZeroTier {
@@ -66,6 +67,12 @@ public:
bool allowManaged;
/**
+ * Whitelist of addresses that can be configured by this network.
+ * If empty and allowManaged is true, allow all private/pseudoprivate addresses.
+ */
+ std::vector<InetAddress> allowManagedWhitelist;
+
+ /**
* Allow configuration of IPs and routes within global (Internet) IP space?
*/
bool allowGlobal;