|
|
|
|
@ -109,7 +109,12 @@ LinuxEthernetTap::LinuxEthernetTap(
|
|
|
|
|
if (!recalledDevice) { |
|
|
|
|
int devno = 0; |
|
|
|
|
do { |
|
|
|
|
#ifdef __SYNOLOGY__ |
|
|
|
|
devno+=50; // Arbitrary number to prevent interface name conflicts
|
|
|
|
|
Utils::snprintf(ifr.ifr_name,sizeof(ifr.ifr_name),"eth%d",devno++); |
|
|
|
|
#else |
|
|
|
|
Utils::snprintf(ifr.ifr_name,sizeof(ifr.ifr_name),"zt%d",devno++); |
|
|
|
|
#endif |
|
|
|
|
Utils::snprintf(procpath,sizeof(procpath),"/proc/sys/net/ipv4/conf/%s",ifr.ifr_name); |
|
|
|
|
} while (stat(procpath,&sbuf) == 0); // try zt#++ until we find one that does not exist
|
|
|
|
|
} |
|
|
|
|
@ -215,16 +220,65 @@ static bool ___removeIp(const std::string &_dev,const InetAddress &ip)
|
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
bool LinuxEthernetTap::addIpSyn(std::vector<InetAddress> ips) |
|
|
|
|
{ |
|
|
|
|
// Here we fill out interface config (ifcfg-dev) to prevent it from being killed
|
|
|
|
|
std::string filepath = "/etc/sysconfig/network-scripts/ifcfg-"+_dev; |
|
|
|
|
std::string cfg_contents = "DEVICE="+_dev+"\nBOOTPROTO=static"; |
|
|
|
|
int ip4=0,ip6=0,ip4_tot=0,ip6_tot=0; |
|
|
|
|
|
|
|
|
|
long cpid = (long)vfork(); |
|
|
|
|
if (cpid == 0) { |
|
|
|
|
OSUtils::redirectUnixOutputs("/dev/null",(const char *)0); |
|
|
|
|
setenv("PATH", "/sbin:/bin:/usr/sbin:/usr/bin", 1); |
|
|
|
|
// We must know if there is at least (one) of each protocol version so we
|
|
|
|
|
// can properly enumerate address/netmask combinations in the ifcfg-dev file
|
|
|
|
|
for(int i=0; i<ips.size(); i++) { |
|
|
|
|
if (ips[i].isV4()) |
|
|
|
|
ip4_tot++; |
|
|
|
|
else |
|
|
|
|
ip6_tot++; |
|
|
|
|
} |
|
|
|
|
// Assemble and write contents of ifcfg-dev file
|
|
|
|
|
for(int i=0; i<ips.size(); i++) { |
|
|
|
|
if (ips[i].isV4()) { |
|
|
|
|
std::string numstr4 = ip4_tot > 1 ? std::to_string(ip4) : ""; |
|
|
|
|
cfg_contents += "\nIPADDR"+numstr4+"="+ips[i].toIpString() |
|
|
|
|
+ "\nNETMASK"+numstr4+"="+ips[i].netmask().toIpString()+"\n"; |
|
|
|
|
ip4++; |
|
|
|
|
} |
|
|
|
|
else { |
|
|
|
|
std::string numstr6 = ip6_tot > 1 ? std::to_string(ip6) : ""; |
|
|
|
|
cfg_contents += "\nIPV6ADDR"+numstr6+"="+ips[i].toIpString() |
|
|
|
|
+ "\nNETMASK"+numstr6+"="+ips[i].netmask().toIpString()+"\n"; |
|
|
|
|
ip6++; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
OSUtils::writeFile(filepath.c_str(), cfg_contents.c_str(), cfg_contents.length()); |
|
|
|
|
// Finaly, add IPs
|
|
|
|
|
for(int i=0; i<ips.size(); i++){ |
|
|
|
|
if (ips[i].isV4()) |
|
|
|
|
::execlp("ip","ip","addr","add",ips[i].toString().c_str(),"broadcast",ips[i].broadcast().toIpString().c_str(),"dev",_dev.c_str(),(const char *)0); |
|
|
|
|
else |
|
|
|
|
::execlp("ip","ip","addr","add",ips[i].toString().c_str(),"dev",_dev.c_str(),(const char *)0);
|
|
|
|
|
} |
|
|
|
|
::_exit(-1); |
|
|
|
|
} else if (cpid > 0) { |
|
|
|
|
int exitcode = -1; |
|
|
|
|
::waitpid(cpid,&exitcode,0); |
|
|
|
|
return (exitcode == 0); |
|
|
|
|
} |
|
|
|
|
return true; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
bool LinuxEthernetTap::addIp(const InetAddress &ip) |
|
|
|
|
{ |
|
|
|
|
if (!ip) |
|
|
|
|
return false; |
|
|
|
|
|
|
|
|
|
std::vector<InetAddress> allIps(ips()); |
|
|
|
|
#ifndef __SYNOLOGY__ |
|
|
|
|
if (std::binary_search(allIps.begin(),allIps.end(),ip)) |
|
|
|
|
return true; |
|
|
|
|
#endif |
|
|
|
|
|
|
|
|
|
// Remove and reconfigure if address is the same but netmask is different
|
|
|
|
|
for(std::vector<InetAddress>::iterator i(allIps.begin());i!=allIps.end();++i) { |
|
|
|
|
|