A couple of bugfixes

* Fix a bug where pollfds would be changed while in the poll_all
    loop. This issue didn't exist before 'auto' was implemented.

  * Fix so 'auto' rules won't try to forward Neighbor Solicitation
    Packages through proxy's interface.

  * Some code cleanup.
This commit is contained in:
Daniel Adolfsson 2012-02-07 21:26:43 +01:00
parent 13b81fdd97
commit 0dbc3e288a
5 changed files with 39 additions and 32 deletions

View File

@ -219,12 +219,12 @@ bool address::parse_string(const std::string& str)
return false; return false;
} }
* b++ =* p++; *b++ =* p++;
sz++; sz++;
} }
* b = '\0'; *b = '\0';
if (inet_pton(AF_INET6, buf,& _addr) <= 0) { if (inet_pton(AF_INET6, buf,& _addr) <= 0) {
return false; return false;
@ -245,24 +245,27 @@ bool address::parse_string(const std::string& str)
if (*p++ != '/') if (*p++ != '/')
return false; return false;
while (*p && isspace(*p)) while (*p && isspace(*p)) {
p++; p++;
}
sz = 0; sz = 0;
b = buf; b = buf;
while (*p) { while (*p) {
if (!isdigit(*p)) if (!isdigit(*p)) {
return false; return false;
}
if (sz > 3) if (sz > 3) {
return false; return false;
}
* b++ =* p++; *b++ =* p++;
sz++; sz++;
} }
* b = '\0'; *b = '\0';
prefix(atoi(buf)); prefix(atoi(buf));

View File

@ -169,7 +169,7 @@ ptr<iface> iface::open_pfd(const std::string& name)
ifa->_pfd = fd; ifa->_pfd = fd;
fixup_pollfds(); _map_dirty = true;
return ifa; return ifa;
} }
@ -273,7 +273,7 @@ ptr<iface> iface::open_ifd(const std::string& name)
memcpy(&ifa->hwaddr, ifr.ifr_hwaddr.sa_data, sizeof(struct ether_addr)); memcpy(&ifa->hwaddr, ifr.ifr_hwaddr.sa_data, sizeof(struct ether_addr));
fixup_pollfds(); _map_dirty = true;
return ifa; return ifa;
} }
@ -453,10 +453,6 @@ ssize_t iface::read_advert(address& saddr, address& taddr)
void iface::fixup_pollfds() void iface::fixup_pollfds()
{ {
if (_map_dirty) {
clean();
}
_pollfds.resize(_map.size()* 2); _pollfds.resize(_map.size()* 2);
int i = 0; int i = 0;
@ -493,7 +489,7 @@ void iface::add_session(const ptr<session>& se)
_sessions.push_back(se); _sessions.push_back(se);
} }
void iface::clean() void iface::cleanup()
{ {
for (std::map<std::string, weak_ptr<iface> >::iterator it = _map.begin(); for (std::map<std::string, weak_ptr<iface> >::iterator it = _map.begin();
it != _map.end(); it++) { it != _map.end(); it++) {
@ -501,14 +497,14 @@ void iface::clean()
_map.erase(it); _map.erase(it);
} }
} }
_map_dirty = false;
} }
int iface::poll_all() int iface::poll_all()
{ {
if (_map_dirty) { if (_map_dirty) {
cleanup();
fixup_pollfds(); fixup_pollfds();
_map_dirty = false;
} }
if (_pollfds.size() == 0) { if (_pollfds.size() == 0) {

View File

@ -81,7 +81,7 @@ private:
// Updates the array above. // Updates the array above.
static void fixup_pollfds(); static void fixup_pollfds();
static void clean(); static void cleanup();
// Weak pointer so this object can reference itself. // Weak pointer so this object can reference itself.
weak_ptr<iface> _ptr; weak_ptr<iface> _ptr;

View File

@ -94,7 +94,7 @@ void proxy::handle_solicit(const address& saddr, const address& daddr,
for (std::list<ptr<rule> >::iterator it = _rules.begin(); for (std::list<ptr<rule> >::iterator it = _rules.begin();
it != _rules.end(); it++) { it != _rules.end(); it++) {
ptr<rule> ru =* it; ptr<rule> ru = *it;
logger::debug() << "checking " << ru->addr() << " against " << taddr; logger::debug() << "checking " << ru->addr() << " against " << taddr;
@ -104,13 +104,16 @@ void proxy::handle_solicit(const address& saddr, const address& daddr,
} }
if (ru->is_auto()) { if (ru->is_auto()) {
ptr<iface> ifa = route::find_and_open(taddr); ptr<route> rt = route::find(taddr);
// If we could find a route matching our rule in /proc/net/ipv6_route, if (rt->ifname() == _ifa->name()) {
// and it's not the same interface as the one pr (proxy) is using. logger::debug() << "skipping route since it's using interface " << rt->ifname();
if (ifa && (ifa != ru->ifa())) { } else {
se->add_iface(ifa); ptr<iface> ifa = rt->ifa();
continue;
if (ifa && (ifa != ru->ifa())) {
se->add_iface(ifa);
}
} }
} else if (!ru->ifa()) { } else if (!ru->ifa()) {
// This rule doesn't have an interface, and thus we'll consider // This rule doesn't have an interface, and thus we'll consider

View File

@ -36,23 +36,27 @@ route::route(const address& addr, const std::string& ifname) :
size_t route::hexdec(const char* str, unsigned char* buf, size_t size) size_t route::hexdec(const char* str, unsigned char* buf, size_t size)
{ {
for (size_t i = 0; ; i++) { for (size_t i = 0; ; i++) {
if (i >= size) if (i >= size) {
return i; return i;
}
char c1 = tolower(str[i* 2]), c2 = tolower(str[i* 2 + 1]); char c1 = tolower(str[i* 2]), c2 = tolower(str[i* 2 + 1]);
if (!isxdigit(c1) || !isxdigit(c2)) if (!isxdigit(c1) || !isxdigit(c2)) {
return i; return i;
}
if ((c1 >= '0') && (c1 <= '9')) if ((c1 >= '0') && (c1 <= '9')) {
buf[i] = (c1 - '0') << 4; buf[i] = (c1 - '0') << 4;
else } else {
buf[i] = ((c1 - 'a') + 10) << 4; buf[i] = ((c1 - 'a') + 10) << 4;
}
if ((c2 >= '0') && (c2 <= '9')) if ((c2 >= '0') && (c2 <= '9')) {
buf[i] |= c2 - '0'; buf[i] |= c2 - '0';
else } else {
buf[i] |= (c2 - 'a') + 10; buf[i] |= (c2 - 'a') + 10;
}
} }
} }
@ -89,8 +93,9 @@ void route::load(const std::string& path)
char buf[1024]; char buf[1024];
ifs.getline(buf, sizeof(buf)); ifs.getline(buf, sizeof(buf));
if (ifs.gcount() < 149) if (ifs.gcount() < 149) {
continue; continue;
}
address addr; address addr;
@ -127,7 +132,7 @@ void route::update(int elapsed_time)
ptr<route> route::create(const address& addr, const std::string& ifname) ptr<route> route::create(const address& addr, const std::string& ifname)
{ {
ptr<route> rt(new route(addr, ifname)); ptr<route> rt(new route(addr, ifname));
logger::debug() << "route::create() addr=" << addr << ", ifname=" << ifname; // logger::debug() << "route::create() addr=" << addr << ", ifname=" << ifname;
_routes.push_back(rt); _routes.push_back(rt);
return rt; return rt;
} }