--- ntrack-rtnetlink.c.orig 2011-11-13 02:26:31.000000000 +0100 +++ ntrack-rtnetlink.c 2014-10-25 17:10:37.944887418 +0200 @@ -751,6 +751,7 @@ int topa6_count = 0; int topl6_count = 0; + int retVal; memset (&topr4, 0, sizeof (topr4)); memset (&topa4, 0, sizeof (topa4)); @@ -762,6 +763,8 @@ sort_routes_by_prio (); + retVal = NTRACK_STATE_OFFLINE; + i = 0; while (__HAS_ROUTE (i)) { struct _rtroute route; @@ -775,7 +778,6 @@ topr4[topr4_count++] = route; if (route.msg.rtm_table == RT_TABLE_MAIN && - route.msg.rtm_dst_len == 0 && route.msg.rtm_family == AF_INET6) topr6[topr6_count++] = route; } @@ -826,18 +828,20 @@ (topa4[i].msg.ifa_index > 0)) { /* has interface and carrier, online */ ipstat4[i] = NTRACK_STATE_ONLINE; - } + } + if (!(topl4[i].msg.ifi_flags & IFF_LOWER_UP) && (topa4[i].msg.ifa_index > 0)) { /* no carrier on link, blocked */ ipstat4[i] = NTRACK_STATE_ONLINE; - } + } + if (!(topl4[i].msg.ifi_flags & IFF_LOWER_UP) && !(topl4[i].msg.ifi_flags & IFF_UP) && (topa4[i].msg.ifa_index > 0)) { /* no link, offline */ ipstat4[i] = NTRACK_STATE_OFFLINE; - } + } } ipstat6[0] = NTRACK_STATE_OFFLINE; @@ -848,55 +852,86 @@ (topa6[i].msg.ifa_index > 0)) { /* has interface and carrier, online */ ipstat6[i] = NTRACK_STATE_ONLINE; - } + } + if (!(topl6[i].msg.ifi_flags & IFF_LOWER_UP) && (topa6[i].msg.ifa_index > 0)) { /* no carrier on link, blocked */ ipstat6[i] = NTRACK_STATE_BLOCKED; - } + } + if (!(topl6[i].msg.ifi_flags & IFF_LOWER_UP) && (topa6[i].msg.ifa_index == 0)) { /* no link, offline */ ipstat6[i] = NTRACK_STATE_OFFLINE; - } + } } - for (i = 0; i < topr4_count; i++) { - if (ipstat4[i] != NTRACK_STATE_BLOCKED) - break; - } + if (topr4_count) { + for (i = 0; i < topr4_count; i++) { + if (ipstat4[i] != NTRACK_STATE_BLOCKED) + break; + } - if (topr4_count > 0 && ipstat4[i] == NTRACK_STATE_UNKNOWN) { - return -1; - } + if (topr4_count > 0 && ipstat4[i] == NTRACK_STATE_UNKNOWN) { + return -1; + } - D ("tmr_1: %d, i: %d, ipstat4: %d\n", nl_info->topmostr, i, ipstat4[i]); + D ("tmr_1: %d, i: %d, ipstat4: %d\n", nl_info->topmostr, i, ipstat4[i]); - if (nl_info->topmostr < 0 && topr4_count > 0 && ipstat4[i] != NTRACK_STATE_OFFLINE) { - nl_info->topmostr = topl4[i].msg.ifi_index; - op_default_route_appeared ((struct _ntrack_monitor_arch *) monitor, nl_info); - } + if (nl_info->topmostr < 0 && topr4_count > 0 && ipstat4[i] != NTRACK_STATE_OFFLINE) { + nl_info->topmostr = topl4[i].msg.ifi_index; + op_default_route_appeared ((struct _ntrack_monitor_arch *) monitor, nl_info); + } - if ((nl_info->topmostr == -2 || nl_info->topmostr >=0) && (topr4_count == 0 || ipstat4[i] == NTRACK_STATE_OFFLINE)) { - nl_info->topmostr = -1; - op_default_route_disappeared ((struct _ntrack_monitor_arch *) monitor, nl_info); - } + if ((nl_info->topmostr == -2 || nl_info->topmostr >=0) && (topr4_count == 0 || ipstat4[i] == NTRACK_STATE_OFFLINE)) { + nl_info->topmostr = -1; + op_default_route_disappeared ((struct _ntrack_monitor_arch *) monitor, nl_info); + } + + if (nl_info->topmostr >=0 && topr4_count > 0 && topl4[i].msg.ifi_index != nl_info->topmostr && ipstat4[i] != NTRACK_STATE_OFFLINE) { + nl_info->topmostr = topl4[i].msg.ifi_index; + op_default_route_changed ((struct _ntrack_monitor_arch *) monitor, nl_info); + } - if (nl_info->topmostr >=0 && topr4_count > 0 && topl4[i].msg.ifi_index != nl_info->topmostr && ipstat4[i] != NTRACK_STATE_OFFLINE) { - nl_info->topmostr = topl4[i].msg.ifi_index; - op_default_route_changed ((struct _ntrack_monitor_arch *) monitor, nl_info); + D ("tmr_2: %d, i: %d, ipstat4: %d\n", nl_info->topmostr, i, ipstat4[i]); + + retVal = topr4_count == 0 ? NTRACK_STATE_OFFLINE : ipstat4[nl_info->topmostr]; } - D ("tmr_2: %d, i: %d, ipstat4: %d\n", nl_info->topmostr, i, ipstat4[i]); + if (topr6_count) { + for (i = 0; i < topr6_count; i++) { + if (ipstat6[i] != NTRACK_STATE_BLOCKED) + break; + } - for (i = 0; i < topr6_count; i++) { - if (ipstat6[i] == NTRACK_STATE_BLOCKED) - continue; + if (topr6_count > 0 && ipstat6[i] == NTRACK_STATE_UNKNOWN) { + return -1; + } + + D ("tmr_1: %d, i: %d, ipstat6: %d\n", nl_info->topmostr, i, ipstat6[i]); + + if (nl_info->topmostr < 0 && topr6_count > 0 && ipstat6[i] != NTRACK_STATE_OFFLINE) { + nl_info->topmostr = topl6[i].msg.ifi_index; + op_default_route_appeared ((struct _ntrack_monitor_arch *) monitor, nl_info); + } + + if ((nl_info->topmostr == -2 || nl_info->topmostr >=0) && (topr6_count == 0 || ipstat6[i] == NTRACK_STATE_OFFLINE)) { + nl_info->topmostr = -1; + op_default_route_disappeared ((struct _ntrack_monitor_arch *) monitor, nl_info); + } + + if (nl_info->topmostr >=0 && topr6_count > 0 && topl4[i].msg.ifi_index != nl_info->topmostr && ipstat6[i] != NTRACK_STATE_OFFLINE) { + nl_info->topmostr = topl6[i].msg.ifi_index; + op_default_route_changed ((struct _ntrack_monitor_arch *) monitor, nl_info); + } + + D ("tmr_2: %d, i: %d, ipstat6: %d\n", nl_info->topmostr, i, ipstat6[i]); + + retVal = topr6_count == 0 ? NTRACK_STATE_OFFLINE : ipstat6[nl_info->topmostr]; } - D ("connectivity: %d = %d\n", ipstat4[i],topr4_count); - - return topr4_count == 0 ? NTRACK_STATE_OFFLINE : ipstat4[nl_info->topmostr]; + return retVal; } static int