diff --git a/sys/net/gnrc/network_layer/ipv6/nib/nib.c b/sys/net/gnrc/network_layer/ipv6/nib/nib.c index 89ff7c82653b..4016bfddf3fb 100644 --- a/sys/net/gnrc/network_layer/ipv6/nib/nib.c +++ b/sys/net/gnrc/network_layer/ipv6/nib/nib.c @@ -1332,8 +1332,6 @@ static bool _resolve_addr(const ipv6_addr_t *dst, gnrc_netif_t *netif, gnrc_pktsnip_t *pkt, gnrc_ipv6_nib_nc_t *nce, _nib_onl_entry_t *entry) { - bool res = false; - if ((netif != NULL) && (netif->device_type == NETDEV_TYPE_SLIP)) { /* XXX: Linux doesn't do neighbor discovery for SLIP so no use sending * NS and since SLIP doesn't have link-layer addresses anyway, we can @@ -1343,54 +1341,57 @@ static bool _resolve_addr(const ipv6_addr_t *dst, gnrc_netif_t *netif, nce->l2addr_len = 0; return true; } - else if (_resolve_from_nc(netif, entry)) { + + /* first check if address is cached */ + if (_resolve_addr_from_nc(netif, entry)) { DEBUG("nib: resolve address %s%%%u from neighbor cache\n", ipv6_addr_to_str(addr_str, &entry->ipv6, sizeof(addr_str)), _nib_onl_get_if(entry)); _nib_nc_get(entry, nce); - res = true; + return true; } - else if (!(res = _resolve_addr_from_ipv6(dst, netif, nce))) { -#if IS_ACTIVE(CONFIG_GNRC_IPV6_NIB_ARSM) - bool reset = false; -#endif /* CONFIG_GNRC_IPV6_NIB_ARSM */ - DEBUG("nib: resolve address %s by probing neighbors\n", - ipv6_addr_to_str(addr_str, dst, sizeof(addr_str))); + /* directly resolve 6lo address */ + if (_resolve_addr_from_ipv6(dst, netif, nce)) { + return true; + } + + bool reset = false; + DEBUG("nib: resolve address %s by probing neighbors\n", + ipv6_addr_to_str(addr_str, dst, sizeof(addr_str))); + if (entry == NULL) { + entry = _nib_nc_add(dst, netif ? netif->pid : 0, + GNRC_IPV6_NIB_NC_INFO_NUD_STATE_INCOMPLETE); if (entry == NULL) { - entry = _nib_nc_add(dst, (netif != NULL) ? netif->pid : 0, - GNRC_IPV6_NIB_NC_INFO_NUD_STATE_INCOMPLETE); - if (entry == NULL) { - DEBUG("nib: can't resolve address, neighbor cache full\n"); - gnrc_pktbuf_release(pkt); - return false; - } -#if IS_ACTIVE(CONFIG_GNRC_IPV6_NIB_ROUTER) - if (netif != NULL) { - _call_route_info_cb(netif, - GNRC_IPV6_NIB_ROUTE_INFO_TYPE_NSC, - dst, - (void *)GNRC_IPV6_NIB_NC_INFO_NUD_STATE_INCOMPLETE); - } -#endif /* CONFIG_GNRC_IPV6_NIB_ROUTER */ -#if IS_ACTIVE(CONFIG_GNRC_IPV6_NIB_ARSM) - reset = true; -#endif /* CONFIG_GNRC_IPV6_NIB_ARSM */ - } -#if IS_ACTIVE(CONFIG_GNRC_IPV6_NIB_ARSM) - else if (_get_nud_state(entry) == GNRC_IPV6_NIB_NC_INFO_NUD_STATE_UNREACHABLE) { - /* reduce back-off to possibly resolve neighbor sooner again */ - entry->ns_sent = 3; - } -#endif /* CONFIG_GNRC_IPV6_NIB_ARSM */ - if (pkt != NULL && !_enqueue_for_resolve(netif, pkt, entry)) { + DEBUG("nib: can't resolve address, neighbor cache full\n"); + gnrc_pktbuf_release(pkt); return false; } + if (IS_ACTIVE(CONFIG_GNRC_IPV6_NIB_ROUTER) && netif != NULL) { + _call_route_info_cb(netif, + GNRC_IPV6_NIB_ROUTE_INFO_TYPE_NSC, + dst, + (void *)GNRC_IPV6_NIB_NC_INFO_NUD_STATE_INCOMPLETE); + } + reset = true; + } #if IS_ACTIVE(CONFIG_GNRC_IPV6_NIB_ARSM) + else if (_get_nud_state(entry) == GNRC_IPV6_NIB_NC_INFO_NUD_STATE_UNREACHABLE) { + /* reduce back-off to possibly resolve neighbor sooner again */ + entry->ns_sent = 3; + } +#endif + + /* queue packet as we have to do address resolution first */ + if (pkt != NULL && !_enqueue_for_resolve(netif, pkt, entry)) { + return false; + } + + if (IS_ACTIVE(CONFIG_GNRC_IPV6_NIB_ARSM)) { _probe_nbr(entry, reset); -#endif /* CONFIG_GNRC_IPV6_NIB_ARSM */ } - return res; + + return false; } static void _handle_snd_na(gnrc_pktsnip_t *pkt)