+
+LIST(routelist);
+MEMB(routememb, uip_ds6_route_t, UIP_DS6_ROUTE_NB);
+
+LIST(defaultrouterlist);
+MEMB(defaultroutermemb, uip_ds6_defrt_t, UIP_DS6_DEFRT_NB);
+
+LIST(notificationlist);
+
+#define DEBUG DEBUG_NONE
+#include "net/uip-debug.h"
+
+/*---------------------------------------------------------------------------*/
+static void
+call_route_callback(int event, uip_ipaddr_t *route,
+ uip_ipaddr_t *nexthop)
+{
+ int num;
+ struct uip_ds6_notification *n;
+ for(n = list_head(notificationlist);
+ n != NULL;
+ n = list_item_next(n)) {
+ if(event == UIP_DS6_NOTIFICATION_DEFRT_ADD ||
+ event == UIP_DS6_NOTIFICATION_DEFRT_RM) {
+ num = list_length(defaultrouterlist);
+ } else {
+ num = list_length(routelist);
+ }
+ n->callback(event, route, nexthop, num);
+ }
+}
+/*---------------------------------------------------------------------------*/
+void
+uip_ds6_notification_add(struct uip_ds6_notification *n,
+ uip_ds6_notification_callback c)
+{
+ if(n != NULL && c != NULL) {
+ n->callback = c;
+ list_add(notificationlist, n);
+ }
+}
+/*---------------------------------------------------------------------------*/
+void
+uip_ds6_notification_rm(struct uip_ds6_notification *n)
+{
+ list_remove(notificationlist, n);
+}
+/*---------------------------------------------------------------------------*/
+void
+uip_ds6_route_init(void)
+{
+ memb_init(&routememb);
+ list_init(routelist);
+
+ memb_init(&defaultroutermemb);
+ list_init(defaultrouterlist);
+
+ list_init(notificationlist);
+}
+/*---------------------------------------------------------------------------*/
+uip_ds6_route_t *
+uip_ds6_route_list_head(void)
+{
+ return list_head(routelist);
+}
+/*---------------------------------------------------------------------------*/
+int
+uip_ds6_route_num_routes(void)
+{
+ return list_length(routelist);
+}
+/*---------------------------------------------------------------------------*/
+uip_ds6_route_t *
+uip_ds6_route_lookup(uip_ipaddr_t *addr)
+{
+ uip_ds6_route_t *r;
+ uip_ds6_route_t *found_route;
+ uint8_t longestmatch;
+
+ PRINTF("uip-ds6-route: Looking up route for ");
+ PRINT6ADDR(addr);
+ PRINTF("\n");
+
+
+ found_route = NULL;
+ longestmatch = 0;
+ for(r = list_head(routelist);
+ r != NULL;
+ r = list_item_next(r)) {
+ if(r->length >= longestmatch &&
+ uip_ipaddr_prefixcmp(addr, &r->ipaddr, r->length)) {
+ longestmatch = r->length;
+ found_route = r;
+ }
+
+ }
+
+ if(found_route != NULL) {
+ PRINTF("uip-ds6-route: Found route:");
+ PRINT6ADDR(addr);
+ PRINTF(" via ");
+ PRINT6ADDR(&found_route->nexthop);
+ PRINTF("\n");
+ } else {
+ PRINTF("uip-ds6-route: No route found\n");
+ }
+
+ return found_route;
+}
+/*---------------------------------------------------------------------------*/
+uip_ds6_route_t *
+uip_ds6_route_add(uip_ipaddr_t *ipaddr, uint8_t length,
+ uip_ipaddr_t *nexthop, uint8_t metric)
+{
+ uip_ds6_route_t *r;
+
+ /* First make sure that we don't add a route twice. If we find an
+ existing route for our destination, we'll just update the old
+ one. */
+ r = uip_ds6_route_lookup(ipaddr);
+ if(r != NULL) {
+ PRINTF("uip_ds6_route_add: old route already found, updating this one instead: ");
+ PRINT6ADDR(ipaddr);
+ PRINTF("\n");
+ } else {
+ /* Allocate a routing entry and add the route to the list */
+ r = memb_alloc(&routememb);
+ if(r == NULL) {
+ PRINTF("uip_ds6_route_add: could not allocate memory for new route to ");
+ PRINT6ADDR(ipaddr);
+ PRINTF(", dropping it\n");
+ return NULL;
+ }
+ list_add(routelist, r);
+
+ PRINTF("uip_ds6_route_add num %d\n", list_length(routelist));
+ }
+
+ uip_ipaddr_copy(&(r->ipaddr), ipaddr);
+ r->length = length;
+ uip_ipaddr_copy(&(r->nexthop), nexthop);
+ r->metric = metric;
+
+#ifdef UIP_DS6_ROUTE_STATE_TYPE
+ memset(&r->state, 0, sizeof(UIP_DS6_ROUTE_STATE_TYPE));
+#endif
+
+ PRINTF("uip_ds6_route_add: adding route: ");
+ PRINT6ADDR(ipaddr);
+ PRINTF(" via ");
+ PRINT6ADDR(nexthop);
+ PRINTF("\n");
+ ANNOTATE("#L %u 1;blue\n", nexthop->u8[sizeof(uip_ipaddr_t) - 1]);
+
+ call_route_callback(UIP_DS6_NOTIFICATION_ROUTE_ADD, ipaddr, nexthop);
+
+ return r;
+}
+
+/*---------------------------------------------------------------------------*/
+void
+uip_ds6_route_rm(uip_ds6_route_t *route)
+{
+ uip_ds6_route_t *r;
+ /* Make sure that the route is in the list before removing it. */
+ for(r = list_head(routelist);
+ r != NULL;
+ r = list_item_next(r)) {
+ if(r == route) {
+ list_remove(routelist, route);
+ memb_free(&routememb, route);
+
+ PRINTF("uip_ds6_route_rm num %d\n", list_length(routelist));
+
+ call_route_callback(UIP_DS6_NOTIFICATION_ROUTE_RM,
+ &route->ipaddr, &route->nexthop);
+#if (DEBUG & DEBUG_ANNOTATE) == DEBUG_ANNOTATE
+ /* we need to check if this was the last route towards "nexthop" */
+ /* if so - remove that link (annotation) */
+ for(r = list_head(routelist);
+ r != NULL;
+ r = list_item_next(r)) {
+ if(uip_ipaddr_cmp(&r->nexthop, &route->nexthop)) {
+ /* we found another link using the specific nexthop, so keep the #L */
+ return;
+ }
+ }
+ ANNOTATE("#L %u 0\n", route->nexthop.u8[sizeof(uip_ipaddr_t) - 1]);
+#endif
+ return;
+ }
+ }
+}
+/*---------------------------------------------------------------------------*/
+void
+uip_ds6_route_rm_by_nexthop(uip_ipaddr_t *nexthop)
+{
+ uip_ds6_route_t *r;
+
+ r = list_head(routelist);
+ while(r != NULL) {
+ if(uip_ipaddr_cmp(&r->nexthop, nexthop)) {
+ list_remove(routelist, r);
+ call_route_callback(UIP_DS6_NOTIFICATION_ROUTE_RM,
+ &r->ipaddr, &r->nexthop);
+ r = list_head(routelist);
+ } else {
+ r = list_item_next(r);
+ }
+ }
+}
+/*---------------------------------------------------------------------------*/
+uip_ds6_defrt_t *
+uip_ds6_defrt_add(uip_ipaddr_t *ipaddr, unsigned long interval)
+{
+ uip_ds6_defrt_t *d;
+
+ d = uip_ds6_defrt_lookup(ipaddr);
+ if(d == NULL) {
+ d = memb_alloc(&defaultroutermemb);
+ if(d == NULL) {
+ PRINTF("uip_ds6_defrt_add: could not add default route to ");
+ PRINT6ADDR(ipaddr);
+ PRINTF(", out of memory\n");
+ return NULL;
+ } else {
+ PRINTF("uip_ds6_defrt_add: adding default route to ");
+ PRINT6ADDR(ipaddr);
+ PRINTF("\n");
+ }
+
+ list_push(defaultrouterlist, d);
+ }
+
+ uip_ipaddr_copy(&d->ipaddr, ipaddr);
+ if(interval != 0) {
+ stimer_set(&d->lifetime, interval);
+ d->isinfinite = 0;
+ } else {
+ d->isinfinite = 1;
+ }
+
+ ANNOTATE("#L %u 1\n", ipaddr->u8[sizeof(uip_ipaddr_t) - 1]);
+
+ call_route_callback(UIP_DS6_NOTIFICATION_DEFRT_ADD, ipaddr, ipaddr);
+
+ return d;
+}
+/*---------------------------------------------------------------------------*/
+void
+uip_ds6_defrt_rm(uip_ds6_defrt_t *defrt)
+{
+ uip_ds6_defrt_t *d;
+ /* Make sure that the defrt is in the list before we remove it. */
+ for(d = list_head(defaultrouterlist);
+ d != NULL;
+ d = list_item_next(d)) {
+ if(d == defrt) {
+ PRINTF("Removing default route\n");
+ list_remove(defaultrouterlist, defrt);
+ memb_free(&defaultroutermemb, defrt);
+ ANNOTATE("#L %u 0\n", defrt->ipaddr.u8[sizeof(uip_ipaddr_t) - 1]);
+ call_route_callback(UIP_DS6_NOTIFICATION_DEFRT_RM,
+ &defrt->ipaddr, &defrt->ipaddr);
+ return;
+ }
+ }
+}
+/*---------------------------------------------------------------------------*/
+uip_ds6_defrt_t *
+uip_ds6_defrt_lookup(uip_ipaddr_t *ipaddr)
+{
+ uip_ds6_defrt_t *d;
+ for(d = list_head(defaultrouterlist);
+ d != NULL;
+ d = list_item_next(d)) {
+ if(uip_ipaddr_cmp(&d->ipaddr, ipaddr)) {
+ return d;
+ }
+ }
+ return NULL;
+}
+/*---------------------------------------------------------------------------*/
+uip_ipaddr_t *
+uip_ds6_defrt_choose(void)
+{
+ uip_ds6_defrt_t *d;
+ uip_ds6_nbr_t *bestnbr;
+ uip_ipaddr_t *addr;
+
+ addr = NULL;
+ for(d = list_head(defaultrouterlist);
+ d != NULL;
+ d = list_item_next(d)) {
+ PRINTF("Defrt, IP address ");
+ PRINT6ADDR(&d->ipaddr);
+ PRINTF("\n");
+ bestnbr = uip_ds6_nbr_lookup(&d->ipaddr);
+ if(bestnbr != NULL && bestnbr->state != NBR_INCOMPLETE) {
+ PRINTF("Defrt found, IP address ");
+ PRINT6ADDR(&d->ipaddr);
+ PRINTF("\n");
+ return &d->ipaddr;
+ } else {
+ addr = &d->ipaddr;
+ PRINTF("Defrt INCOMPLETE found, IP address ");
+ PRINT6ADDR(&d->ipaddr);
+ PRINTF("\n");
+ }
+ }
+ return addr;
+}
+/*---------------------------------------------------------------------------*/
+void
+uip_ds6_defrt_periodic(void)
+{
+ uip_ds6_defrt_t *d;
+ d = list_head(defaultrouterlist);
+ while(d != NULL) {
+ if(!d->isinfinite &&
+ stimer_expired(&d->lifetime)) {
+ PRINTF("uip_ds6_defrt_periodic: defrt lifetime expired\n");
+ uip_ds6_defrt_rm(d);
+ d = list_head(defaultrouterlist);
+ } else {
+ d = list_item_next(d);
+ }
+ }
+}
+/*---------------------------------------------------------------------------*/
+
+
diff --git a/core/net/uip-ds6-route.h b/core/net/uip-ds6-route.h
new file mode 100644
index 000000000..59e13db81
--- /dev/null
+++ b/core/net/uip-ds6-route.h
@@ -0,0 +1,132 @@
+/*
+ * Copyright (c) 2012, Thingsquare, http://www.thingsquare.com/.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * 3. Neither the name of the copyright holder nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ */
+#ifndef UIP_DS6_ROUTE_H
+#define UIP_DS6_ROUTE_H
+
+void uip_ds6_route_init(void);
+
+
+/* Event constants for the uip-ds6 route notification interface. The
+ notification interface allows for a user program to be notified via
+ a callback when a route has been added or removed and when the
+ system has added or removed a default route. */
+#define UIP_DS6_NOTIFICATION_DEFRT_ADD 0
+#define UIP_DS6_NOTIFICATION_DEFRT_RM 1
+#define UIP_DS6_NOTIFICATION_ROUTE_ADD 2
+#define UIP_DS6_NOTIFICATION_ROUTE_RM 3
+
+typedef void (* uip_ds6_notification_callback)(int event,
+ uip_ipaddr_t *route,
+ uip_ipaddr_t *nexthop,
+ int num_routes);
+struct uip_ds6_notification {
+ struct uip_ds6_notification *next;
+ uip_ds6_notification_callback callback;
+};
+
+void uip_ds6_notification_add(struct uip_ds6_notification *n,
+ uip_ds6_notification_callback c);
+/*--------------------------------------------------*/
+
+
+/* Routing table */
+#define UIP_DS6_ROUTE_NBS 0
+#ifndef UIP_CONF_DS6_ROUTE_NBU
+#define UIP_DS6_ROUTE_NBU 4
+#else
+#define UIP_DS6_ROUTE_NBU UIP_CONF_DS6_ROUTE_NBU
+#endif
+#define UIP_DS6_ROUTE_NB UIP_DS6_ROUTE_NBS + UIP_DS6_ROUTE_NBU
+
+/** \brief define some additional RPL related route state and
+ * neighbor callback for RPL - if not a DS6_ROUTE_STATE is already set */
+#ifndef UIP_DS6_ROUTE_STATE_TYPE
+#define UIP_DS6_ROUTE_STATE_TYPE rpl_route_entry_t
+/* Needed for the extended route entry state when using ContikiRPL */
+typedef struct rpl_route_entry {
+ uint32_t lifetime;
+ uint32_t saved_lifetime;
+ void *dag;
+ uint8_t learned_from;
+} rpl_route_entry_t;
+#endif /* UIP_DS6_ROUTE_STATE_TYPE */
+
+
+
+/** \brief An entry in the routing table */
+typedef struct uip_ds6_route {
+ struct uip_ds6_route *next;
+ uip_ipaddr_t ipaddr;
+ uip_ipaddr_t nexthop;
+ uint8_t length;
+ uint8_t metric;
+#ifdef UIP_DS6_ROUTE_STATE_TYPE
+ UIP_DS6_ROUTE_STATE_TYPE state;
+#endif
+} uip_ds6_route_t;
+
+
+
+/** \brief An entry in the default router list */
+typedef struct uip_ds6_defrt {
+ struct uip_ds6_defrt *next;
+ uip_ipaddr_t ipaddr;
+ struct stimer lifetime;
+ uint8_t isinfinite;
+} uip_ds6_defrt_t;
+
+/** \name Default router list basic routines */
+/** @{ */
+uip_ds6_defrt_t *uip_ds6_defrt_add(uip_ipaddr_t *ipaddr,
+ unsigned long interval);
+void uip_ds6_defrt_rm(uip_ds6_defrt_t *defrt);
+uip_ds6_defrt_t *uip_ds6_defrt_lookup(uip_ipaddr_t *ipaddr);
+uip_ipaddr_t *uip_ds6_defrt_choose(void);
+
+void uip_ds6_defrt_periodic(void);
+/** @} */
+
+
+/** \name Routing Table basic routines */
+/** @{ */
+uip_ds6_route_t *uip_ds6_route_lookup(uip_ipaddr_t *destipaddr);
+uip_ds6_route_t *uip_ds6_route_add(uip_ipaddr_t *ipaddr, uint8_t length,
+ uip_ipaddr_t *next_hop, uint8_t metric);
+void uip_ds6_route_rm(uip_ds6_route_t *route);
+void uip_ds6_route_rm_by_nexthop(uip_ipaddr_t *nexthop);
+
+int uip_ds6_route_num_routes(void);
+uip_ds6_route_t *uip_ds6_route_list_head(void);
+
+/** @} */
+
+#endif /* UIP_DS6_ROUTE_H */
diff --git a/core/net/uip-ds6.c b/core/net/uip-ds6.c
index 056c74cd0..16cc67606 100644
--- a/core/net/uip-ds6.c
+++ b/core/net/uip-ds6.c
@@ -75,9 +75,9 @@ static uint8_t rscount; /** \brief numbe
/** @{ */
uip_ds6_netif_t uip_ds6_if; /** \brief The single interface */
uip_ds6_nbr_t uip_ds6_nbr_cache[UIP_DS6_NBR_NB]; /** \brief Neighor cache */
-uip_ds6_defrt_t uip_ds6_defrt_list[UIP_DS6_DEFRT_NB]; /** \brief Default rt list */
+//uip_ds6_defrt_t uip_ds6_defrt_list[UIP_DS6_DEFRT_NB]; /** \brief Default rt list */
uip_ds6_prefix_t uip_ds6_prefix_list[UIP_DS6_PREFIX_NB]; /** \brief Prefix list */
-uip_ds6_route_t uip_ds6_routing_table[UIP_DS6_ROUTE_NB]; /** \brief Routing table */
+//uip_ds6_route_t uip_ds6_routing_table[UIP_DS6_ROUTE_NB]; /** \brief Routing table */
/* Used by Cooja to enable extraction of addresses from memory.*/
uint8_t uip_ds6_addr_size;
@@ -89,28 +89,29 @@ uint8_t uip_ds6_netif_addr_list_offset;
static uip_ipaddr_t loc_fipaddr;
/* Pointers used in this file */
-static uip_ipaddr_t *locipaddr;
static uip_ds6_addr_t *locaddr;
static uip_ds6_maddr_t *locmaddr;
static uip_ds6_aaddr_t *locaaddr;
static uip_ds6_prefix_t *locprefix;
static uip_ds6_nbr_t *locnbr;
static uip_ds6_defrt_t *locdefrt;
-static uip_ds6_route_t *locroute;
/*---------------------------------------------------------------------------*/
void
uip_ds6_init(void)
{
+
+ uip_ds6_route_init();
+
PRINTF("Init of IPv6 data structures\n");
PRINTF("%u neighbors\n%u default routers\n%u prefixes\n%u routes\n%u unicast addresses\n%u multicast addresses\n%u anycast addresses\n",
UIP_DS6_NBR_NB, UIP_DS6_DEFRT_NB, UIP_DS6_PREFIX_NB, UIP_DS6_ROUTE_NB,
UIP_DS6_ADDR_NB, UIP_DS6_MADDR_NB, UIP_DS6_AADDR_NB);
memset(uip_ds6_nbr_cache, 0, sizeof(uip_ds6_nbr_cache));
- memset(uip_ds6_defrt_list, 0, sizeof(uip_ds6_defrt_list));
+ // memset(uip_ds6_defrt_list, 0, sizeof(uip_ds6_defrt_list));
memset(uip_ds6_prefix_list, 0, sizeof(uip_ds6_prefix_list));
memset(&uip_ds6_if, 0, sizeof(uip_ds6_if));
- memset(uip_ds6_routing_table, 0, sizeof(uip_ds6_routing_table));
+ // memset(uip_ds6_routing_table, 0, sizeof(uip_ds6_routing_table));
uip_ds6_addr_size = sizeof(struct uip_ds6_addr);
uip_ds6_netif_addr_list_offset = offsetof(struct uip_ds6_netif, addr_list);
@@ -174,13 +175,14 @@ uip_ds6_periodic(void)
}
/* Periodic processing on default routers */
- for(locdefrt = uip_ds6_defrt_list;
+ uip_ds6_defrt_periodic();
+ /* for(locdefrt = uip_ds6_defrt_list;
locdefrt < uip_ds6_defrt_list + UIP_DS6_DEFRT_NB; locdefrt++) {
if((locdefrt->isused) && (!locdefrt->isinfinite) &&
(stimer_expired(&(locdefrt->lifetime)))) {
uip_ds6_defrt_rm(locdefrt);
}
- }
+ }*/
#if !UIP_CONF_ROUTER
/* Periodic processing on prefixes */
@@ -398,86 +400,6 @@ uip_ds6_nbr_ll_lookup(uip_lladdr_t *lladdr)
}
/*---------------------------------------------------------------------------*/
-uip_ds6_defrt_t *
-uip_ds6_defrt_add(uip_ipaddr_t *ipaddr, unsigned long interval)
-{
- if(uip_ds6_list_loop
- ((uip_ds6_element_t *)uip_ds6_defrt_list, UIP_DS6_DEFRT_NB,
- sizeof(uip_ds6_defrt_t), ipaddr, 128,
- (uip_ds6_element_t **)&locdefrt) == FREESPACE) {
- locdefrt->isused = 1;
- uip_ipaddr_copy(&locdefrt->ipaddr, ipaddr);
- if(interval != 0) {
- stimer_set(&locdefrt->lifetime, interval);
- locdefrt->isinfinite = 0;
- } else {
- locdefrt->isinfinite = 1;
- }
-
- PRINTF("Adding defrouter with ip addr ");
- PRINT6ADDR(&locdefrt->ipaddr);
- PRINTF("\n");
-
- ANNOTATE("#L %u 1\n", ipaddr->u8[sizeof(uip_ipaddr_t) - 1]);
-
- return locdefrt;
- }
- return NULL;
-}
-
-/*---------------------------------------------------------------------------*/
-void
-uip_ds6_defrt_rm(uip_ds6_defrt_t *defrt)
-{
- if(defrt != NULL) {
- defrt->isused = 0;
- ANNOTATE("#L %u 0\n", defrt->ipaddr.u8[sizeof(uip_ipaddr_t) - 1]);
- }
- return;
-}
-
-/*---------------------------------------------------------------------------*/
-uip_ds6_defrt_t *
-uip_ds6_defrt_lookup(uip_ipaddr_t *ipaddr)
-{
- if(uip_ds6_list_loop((uip_ds6_element_t *)uip_ds6_defrt_list,
- UIP_DS6_DEFRT_NB, sizeof(uip_ds6_defrt_t), ipaddr, 128,
- (uip_ds6_element_t **)&locdefrt) == FOUND) {
- return locdefrt;
- }
- return NULL;
-}
-
-/*---------------------------------------------------------------------------*/
-uip_ipaddr_t *
-uip_ds6_defrt_choose(void)
-{
- uip_ds6_nbr_t *bestnbr;
-
- locipaddr = NULL;
- for(locdefrt = uip_ds6_defrt_list;
- locdefrt < uip_ds6_defrt_list + UIP_DS6_DEFRT_NB; locdefrt++) {
- if(locdefrt->isused) {
- PRINTF("Defrt, IP address ");
- PRINT6ADDR(&locdefrt->ipaddr);
- PRINTF("\n");
- bestnbr = uip_ds6_nbr_lookup(&locdefrt->ipaddr);
- if(bestnbr != NULL && bestnbr->state != NBR_INCOMPLETE) {
- PRINTF("Defrt found, IP address ");
- PRINT6ADDR(&locdefrt->ipaddr);
- PRINTF("\n");
- return &locdefrt->ipaddr;
- } else {
- locipaddr = &locdefrt->ipaddr;
- PRINTF("Defrt INCOMPLETE found, IP address ");
- PRINT6ADDR(&locdefrt->ipaddr);
- PRINTF("\n");
- }
- }
- }
- return locipaddr;
-}
-
#if UIP_CONF_ROUTER
/*---------------------------------------------------------------------------*/
uip_ds6_prefix_t *
@@ -744,104 +666,6 @@ uip_ds6_aaddr_lookup(uip_ipaddr_t *ipaddr)
return NULL;
}
-/*---------------------------------------------------------------------------*/
-uip_ds6_route_t *
-uip_ds6_route_lookup(uip_ipaddr_t *destipaddr)
-{
- uip_ds6_route_t *locrt = NULL;
- uint8_t longestmatch = 0;
-
- PRINTF("DS6: Looking up route for ");
- PRINT6ADDR(destipaddr);
- PRINTF("\n");
-
- for(locroute = uip_ds6_routing_table;
- locroute < uip_ds6_routing_table + UIP_DS6_ROUTE_NB; locroute++) {
- if((locroute->isused) && (locroute->length >= longestmatch)
- &&
- (uip_ipaddr_prefixcmp
- (destipaddr, &locroute->ipaddr, locroute->length))) {
- longestmatch = locroute->length;
- locrt = locroute;
- }
- }
-
- if(locrt != NULL) {
- PRINTF("DS6: Found route:");
- PRINT6ADDR(destipaddr);
- PRINTF(" via ");
- PRINT6ADDR(&locrt->nexthop);
- PRINTF("\n");
- } else {
- PRINTF("DS6: No route found\n");
- }
-
- return locrt;
-}
-
-/*---------------------------------------------------------------------------*/
-uip_ds6_route_t *
-uip_ds6_route_add(uip_ipaddr_t *ipaddr, uint8_t length, uip_ipaddr_t *nexthop,
- uint8_t metric)
-{
- if(uip_ds6_list_loop
- ((uip_ds6_element_t *)uip_ds6_routing_table, UIP_DS6_ROUTE_NB,
- sizeof(uip_ds6_route_t), ipaddr, length,
- (uip_ds6_element_t **)&locroute) == FREESPACE) {
- locroute->isused = 1;
- uip_ipaddr_copy(&(locroute->ipaddr), ipaddr);
- locroute->length = length;
- uip_ipaddr_copy(&(locroute->nexthop), nexthop);
- locroute->metric = metric;
-
-#ifdef UIP_DS6_ROUTE_STATE_TYPE
- memset(&locroute->state, 0, sizeof(UIP_DS6_ROUTE_STATE_TYPE));
-#endif
-
- PRINTF("DS6: adding route: ");
- PRINT6ADDR(ipaddr);
- PRINTF(" via ");
- PRINT6ADDR(nexthop);
- PRINTF("\n");
- ANNOTATE("#L %u 1;blue\n", nexthop->u8[sizeof(uip_ipaddr_t) - 1]);
- }
-
- return locroute;
-}
-
-/*---------------------------------------------------------------------------*/
-void
-uip_ds6_route_rm(uip_ds6_route_t *route)
-{
- route->isused = 0;
-#if (DEBUG & DEBUG_ANNOTATE) == DEBUG_ANNOTATE
- /* we need to check if this was the last route towards "nexthop" */
- /* if so - remove that link (annotation) */
- for(locroute = uip_ds6_routing_table;
- locroute < uip_ds6_routing_table + UIP_DS6_ROUTE_NB;
- locroute++) {
- if(locroute->isused && uip_ipaddr_cmp(&locroute->nexthop, &route->nexthop)) {
- /* we found another link using the specific nexthop, so keep the #L */
- return;
- }
- }
- ANNOTATE("#L %u 0\n",route->nexthop.u8[sizeof(uip_ipaddr_t) - 1]);
-#endif
-}
-/*---------------------------------------------------------------------------*/
-void
-uip_ds6_route_rm_by_nexthop(uip_ipaddr_t *nexthop)
-{
- for(locroute = uip_ds6_routing_table;
- locroute < uip_ds6_routing_table + UIP_DS6_ROUTE_NB;
- locroute++) {
- if(locroute->isused && uip_ipaddr_cmp(&locroute->nexthop, nexthop)) {
- locroute->isused = 0;
- }
- }
- ANNOTATE("#L %u 0\n",nexthop->u8[sizeof(uip_ipaddr_t) - 1]);
-}
-
/*---------------------------------------------------------------------------*/
void
uip_ds6_select_src(uip_ipaddr_t *src, uip_ipaddr_t *dst)
diff --git a/core/net/uip-ds6.h b/core/net/uip-ds6.h
index a9ffb0e55..b697b45ac 100644
--- a/core/net/uip-ds6.h
+++ b/core/net/uip-ds6.h
@@ -46,6 +46,7 @@
#include "sys/stimer.h"
/* The size of uip_ds6_addr_t depends on UIP_ND6_DEF_MAXDADNS. Include uip-nd6.h to define it. */
#include "net/uip-nd6.h"
+#include "net/uip-ds6-route.h"
/*--------------------------------------------------*/
/** Configuration. For all tables (Neighbor cache, Prefix List, Routing Table,
@@ -82,15 +83,6 @@
#endif
#define UIP_DS6_PREFIX_NB UIP_DS6_PREFIX_NBS + UIP_DS6_PREFIX_NBU
-/* Routing table */
-#define UIP_DS6_ROUTE_NBS 0
-#ifndef UIP_CONF_DS6_ROUTE_NBU
-#define UIP_DS6_ROUTE_NBU 4
-#else
-#define UIP_DS6_ROUTE_NBU UIP_CONF_DS6_ROUTE_NBU
-#endif
-#define UIP_DS6_ROUTE_NB UIP_DS6_ROUTE_NBS + UIP_DS6_ROUTE_NBU
-
/* Unicast address list*/
#define UIP_DS6_ADDR_NBS 1
#ifndef UIP_CONF_DS6_ADDR_NBU
@@ -158,9 +150,8 @@
#define FOUND 0
#define FREESPACE 1
#define NOSPACE 2
-
-
/*--------------------------------------------------*/
+
#if UIP_CONF_IPV6_QUEUE_PKT
#include "net/uip-packetqueue.h"
#endif /*UIP_CONF_QUEUE_PKT */
@@ -181,14 +172,6 @@ typedef struct uip_ds6_nbr {
#endif /*UIP_CONF_QUEUE_PKT */
} uip_ds6_nbr_t;
-/** \brief An entry in the default router list */
-typedef struct uip_ds6_defrt {
- uint8_t isused;
- uip_ipaddr_t ipaddr;
- struct stimer lifetime;
- uint8_t isinfinite;
-} uip_ds6_defrt_t;
-
/** \brief A prefix list entry */
#if UIP_CONF_ROUTER
typedef struct uip_ds6_prefix {
@@ -236,19 +219,6 @@ typedef struct uip_ds6_maddr {
uip_ipaddr_t ipaddr;
} uip_ds6_maddr_t;
-/** \brief define some additional RPL related route state and
- * neighbor callback for RPL - if not a DS6_ROUTE_STATE is already set */
-#ifndef UIP_DS6_ROUTE_STATE_TYPE
-#define UIP_DS6_ROUTE_STATE_TYPE rpl_route_entry_t
-/* Needed for the extended route entry state when using ContikiRPL */
-typedef struct rpl_route_entry {
- uint32_t lifetime;
- uint32_t saved_lifetime;
- void *dag;
- uint8_t learned_from;
-} rpl_route_entry_t;
-#endif /* UIP_DS6_ROUTE_STATE_TYPE */
-
/* only define the callback if RPL is active */
#if UIP_CONF_IPV6_RPL
#ifndef UIP_CONF_DS6_NEIGHBOR_STATE_CHANGED
@@ -258,18 +228,6 @@ typedef struct rpl_route_entry {
-/** \brief An entry in the routing table */
-typedef struct uip_ds6_route {
- uint8_t isused;
- uip_ipaddr_t ipaddr;
- uint8_t length;
- uint8_t metric;
- uip_ipaddr_t nexthop;
-#ifdef UIP_DS6_ROUTE_STATE_TYPE
- UIP_DS6_ROUTE_STATE_TYPE state;
-#endif
-} uip_ds6_route_t;
-
/** \brief Interface structure (contains all the interface variables) */
typedef struct uip_ds6_netif {
uint32_t link_mtu;
@@ -325,15 +283,6 @@ uip_ds6_nbr_t *uip_ds6_nbr_ll_lookup(uip_lladdr_t *lladdr);
/** @} */
-/** \name Default router list basic routines */
-/** @{ */
-uip_ds6_defrt_t *uip_ds6_defrt_add(uip_ipaddr_t *ipaddr,
- unsigned long interval);
-void uip_ds6_defrt_rm(uip_ds6_defrt_t *defrt);
-uip_ds6_defrt_t *uip_ds6_defrt_lookup(uip_ipaddr_t *ipaddr);
-uip_ipaddr_t *uip_ds6_defrt_choose(void);
-
-/** @} */
/** \name Prefix list basic routines */
/** @{ */
@@ -381,16 +330,6 @@ uip_ds6_aaddr_t *uip_ds6_aaddr_lookup(uip_ipaddr_t *ipaddr);
/** @} */
-/** \name Routing Table basic routines */
-/** @{ */
-uip_ds6_route_t *uip_ds6_route_lookup(uip_ipaddr_t *destipaddr);
-uip_ds6_route_t *uip_ds6_route_add(uip_ipaddr_t *ipaddr, uint8_t length,
- uip_ipaddr_t *next_hop, uint8_t metric);
-void uip_ds6_route_rm(uip_ds6_route_t *route);
-void uip_ds6_route_rm_by_nexthop(uip_ipaddr_t *nexthop);
-
-/** @} */
-
/** \brief set the last 64 bits of an IP address based on the MAC address */
void uip_ds6_set_addr_iid(uip_ipaddr_t *ipaddr, uip_lladdr_t *lladdr);
diff --git a/core/net/uip-icmp6.c b/core/net/uip-icmp6.c
index 4d6ae90b3..59a71013d 100644
--- a/core/net/uip-icmp6.c
+++ b/core/net/uip-icmp6.c
@@ -102,7 +102,7 @@ uip_icmp6_echo_request_input(void)
if(uip_ext_len > 0) {
#if UIP_CONF_IPV6_RPL
- if ((temp_ext_len=rpl_invert_header())) {
+ if((temp_ext_len = rpl_invert_header())) {
/* If there were other extension headers*/
UIP_FIRST_EXT_BUF->next = UIP_PROTO_ICMP6;
if (uip_ext_len != temp_ext_len) {
@@ -118,7 +118,7 @@ uip_icmp6_echo_request_input(void)
(uint8_t *)UIP_ICMP_BUF + UIP_ICMPH_LEN,
(uip_len - UIP_IPH_LEN - temp_ext_len - UIP_ICMPH_LEN));
}
- uip_ext_len=temp_ext_len;
+ uip_ext_len = temp_ext_len;
} else {
#endif /* UIP_CONF_IPV6_RPL */
/* If there were extension headers*/
diff --git a/core/net/uip-nd6.h b/core/net/uip-nd6.h
index c62e0363e..265c4f3db 100644
--- a/core/net/uip-nd6.h
+++ b/core/net/uip-nd6.h
@@ -98,17 +98,25 @@
/** \name RFC 4861 Node constant */
#define UIP_ND6_MAX_MULTICAST_SOLICIT 3
+
+#ifdef UIP_CONF_ND6_MAX_UNICAST_SOLICIT
+#define UIP_ND6_MAX_UNICAST_SOLICIT UIP_CONF_ND6_MAX_UNICAST_SOLICIT
+#else /* UIP_CONF_ND6_MAX_UNICAST_SOLICIT */
#define UIP_ND6_MAX_UNICAST_SOLICIT 3
+#endif /* UIP_CONF_ND6_MAX_UNICAST_SOLICIT */
+
#ifdef UIP_CONF_ND6_REACHABLE_TIME
#define UIP_ND6_REACHABLE_TIME UIP_CONF_ND6_REACHABLE_TIME
#else
#define UIP_ND6_REACHABLE_TIME 30000
#endif
+
#ifdef UIP_CONF_ND6_RETRANS_TIMER
#define UIP_ND6_RETRANS_TIMER UIP_CONF_ND6_RETRANS_TIMER
#else
#define UIP_ND6_RETRANS_TIMER 1000
#endif
+
#define UIP_ND6_DELAY_FIRST_PROBE_TIME 5
#define UIP_ND6_MIN_RANDOM_FACTOR(x) (x / 2)
#define UIP_ND6_MAX_RANDOM_FACTOR(x) ((x) + (x) / 2)
diff --git a/core/net/uip-split.c b/core/net/uip-split.c
index cbcc48e15..4d247e478 100644
--- a/core/net/uip-split.c
+++ b/core/net/uip-split.c
@@ -43,6 +43,12 @@
#define BUF ((struct uip_tcpip_hdr *)&uip_buf[UIP_LLH_LEN])
+#ifdef UIP_SPLIT_CONF_SIZE
+#define UIP_SPLIT_SIZE UIP_SPLIT_CONF_SIZE
+#else /* UIP_SPLIT_CONF_SIZE */
+#define UIP_SPLIT_SIZE UIP_TCP_MSS
+#endif /* UIP_SPLIT_CONF_SIZE */
+
/*-----------------------------------------------------------------------------*/
void
uip_split_output(void)
@@ -50,9 +56,11 @@ uip_split_output(void)
#if UIP_TCP
uint16_t tcplen, len1, len2;
- /* We only try to split maximum sized TCP segments. */
+ /* We only split TCP segments that are larger than or equal to
+ UIP_SPLIT_SIZE, which is configurable through
+ UIP_SPLIT_CONF_SIZE. */
if(BUF->proto == UIP_PROTO_TCP &&
- uip_len == UIP_TCP_MSS + UIP_TCPIP_HLEN) {
+ uip_len >= UIP_SPLIT_SIZE + UIP_TCPIP_HLEN) {
tcplen = uip_len - UIP_TCPIP_HLEN;
/* Split the segment in two. If the original packet length was
diff --git a/core/net/uip.h b/core/net/uip.h
index d938f9df0..a9aef800d 100644
--- a/core/net/uip.h
+++ b/core/net/uip.h
@@ -59,21 +59,19 @@
* Representation of an IP address.
*
*/
-#if UIP_CONF_IPV6
+typedef union uip_ip4addr_t {
+ uint8_t u8[4]; /* Initializer, must come first. */
+ uint16_t u16[2];
+} uip_ip4addr_t;
+
typedef union uip_ip6addr_t {
- uint8_t u8[16]; /* Initializer, must come first!!! */
+ uint8_t u8[16]; /* Initializer, must come first. */
uint16_t u16[8];
} uip_ip6addr_t;
+#if UIP_CONF_IPV6
typedef uip_ip6addr_t uip_ipaddr_t;
#else /* UIP_CONF_IPV6 */
-typedef union uip_ip4addr_t {
- uint8_t u8[4]; /* Initializer, must come first!!! */
- uint16_t u16[2];
-#if 0
- uint32_t u32;
-#endif
-} uip_ip4addr_t;
typedef uip_ip4addr_t uip_ipaddr_t;
#endif /* UIP_CONF_IPV6 */
@@ -988,6 +986,12 @@ struct uip_udp_conn *uip_udp_new(const uip_ipaddr_t *ripaddr, uint16_t rport);
#ifndef uip_ipaddr_copy
#define uip_ipaddr_copy(dest, src) (*(dest) = *(src))
#endif
+#ifndef uip_ip4addr_copy
+#define uip_ip4addr_copy(dest, src) (*(dest) = *(src))
+#endif
+#ifndef uip_ip6addr_copy
+#define uip_ip6addr_copy(dest, src) (*(dest) = *(src))
+#endif
/**
* Compare two IP addresses
@@ -1009,11 +1013,14 @@ struct uip_udp_conn *uip_udp_new(const uip_ipaddr_t *ripaddr, uint16_t rport);
*
* \hideinitializer
*/
-#if !UIP_CONF_IPV6
-#define uip_ipaddr_cmp(addr1, addr2) ((addr1)->u16[0] == (addr2)->u16[0] && \
+#define uip_ip4addr_cmp(addr1, addr2) ((addr1)->u16[0] == (addr2)->u16[0] && \
(addr1)->u16[1] == (addr2)->u16[1])
+#define uip_ip6addr_cmp(addr1, addr2) (memcmp(addr1, addr2, sizeof(uip_ip6addr_t)) == 0)
+
+#if !UIP_CONF_IPV6
+#define uip_ipaddr_cmp(addr1, addr2) uip_ip4addr_cmp(addr1, addr2)
#else /* !UIP_CONF_IPV6 */
-#define uip_ipaddr_cmp(addr1, addr2) (memcmp(addr1, addr2, sizeof(uip_ip6addr_t)) == 0)
+#define uip_ipaddr_cmp(addr1, addr2) uip_ip6addr_cmp(addr1, addr2)
#endif /* !UIP_CONF_IPV6 */
/**
@@ -1040,15 +1047,15 @@ struct uip_udp_conn *uip_udp_new(const uip_ipaddr_t *ripaddr, uint16_t rport);
*
* \hideinitializer
*/
-#if !UIP_CONF_IPV6
+
#define uip_ipaddr_maskcmp(addr1, addr2, mask) \
(((((uint16_t *)addr1)[0] & ((uint16_t *)mask)[0]) == \
(((uint16_t *)addr2)[0] & ((uint16_t *)mask)[0])) && \
((((uint16_t *)addr1)[1] & ((uint16_t *)mask)[1]) == \
(((uint16_t *)addr2)[1] & ((uint16_t *)mask)[1])))
-#else
+
#define uip_ipaddr_prefixcmp(addr1, addr2, length) (memcmp(addr1, addr2, length>>3) == 0)
-#endif
+
/**
diff --git a/core/net/uip6.c b/core/net/uip6.c
index e18defdec..af6f442e0 100644
--- a/core/net/uip6.c
+++ b/core/net/uip6.c
@@ -855,7 +855,7 @@ ext_hdr_options_process(void)
case UIP_EXT_HDR_OPT_RPL:
PRINTF("Processing RPL option\n");
if(rpl_verify_header(uip_ext_opt_offset)) {
- PRINTF("RPL Option Error : Dropping Packet");
+ PRINTF("RPL Option Error: Dropping Packet\n");
return 1;
}
uip_ext_opt_offset += (UIP_EXT_HDR_OPT_RPL_BUF->opt_len) + 2;
@@ -1123,17 +1123,19 @@ uip_process(uint8_t flag)
if(*uip_next_hdr == UIP_PROTO_HBHO) {
#if UIP_CONF_IPV6_CHECKS
uip_ext_bitmap |= UIP_EXT_HDR_BITMAP_HBHO;
-#endif /*UIP_CONF_IPV6_CHECKS*/
+#endif /* UIP_CONF_IPV6_CHECKS */
switch(ext_hdr_options_process()) {
case 0:
- /*continue*/
+ /* continue */
uip_next_hdr = &UIP_EXT_BUF->next;
uip_ext_len += (UIP_EXT_BUF->len << 3) + 8;
break;
case 1:
- /*silently discard*/
+ PRINTF("Dropping packet after extension header processing\n");
+ /* silently discard */
goto drop;
case 2:
+ PRINTF("Sending error message after extension header processing\n");
/* send icmp error message (created in ext_hdr_options_process)
* and discard*/
goto send;
@@ -1448,6 +1450,11 @@ uip_process(uint8_t flag)
#if UIP_UDP_CHECKSUMS
uip_len = uip_len - UIP_IPUDPH_LEN;
uip_appdata = &uip_buf[UIP_IPUDPH_LEN + UIP_LLH_LEN];
+ /* XXX hack: UDP/IPv6 receivers should drop packets with UDP
+ checksum 0. Here, we explicitly receive UDP packets with checksum
+ 0. This is to be able to debug code that for one reason or
+ another miscomputes UDP checksums. The reception of zero UDP
+ checksums should be turned into a configration option. */
if(UIP_UDP_BUF->udpchksum != 0 && uip_udpchksum() != 0xffff) {
UIP_STAT(++uip_stat.udp.drop);
UIP_STAT(++uip_stat.udp.chkerr);
@@ -2211,19 +2218,18 @@ uip_process(uint8_t flag)
UIP_TCP_BUF->seqno[3] = uip_connr->snd_nxt[3];
UIP_IP_BUF->proto = UIP_PROTO_TCP;
-
+
UIP_TCP_BUF->srcport = uip_connr->lport;
UIP_TCP_BUF->destport = uip_connr->rport;
-
uip_ipaddr_copy(&UIP_IP_BUF->destipaddr, &uip_connr->ripaddr);
- uip_ds6_select_src(&UIP_IP_BUF->srcipaddr,&UIP_IP_BUF->destipaddr);
- PRINTF("Sending TCP packet to");
+ uip_ds6_select_src(&UIP_IP_BUF->srcipaddr, &UIP_IP_BUF->destipaddr);
+ PRINTF("Sending TCP packet to ");
PRINT6ADDR(&UIP_IP_BUF->destipaddr);
- PRINTF("from");
+ PRINTF(" from ");
PRINT6ADDR(&UIP_IP_BUF->srcipaddr);
PRINTF("\n");
-
+
if(uip_connr->tcpstateflags & UIP_STOPPED) {
/* If the connection has issued uip_stop(), we advertise a zero
window so that the remote host will stop sending data. */
diff --git a/core/net/uiplib.c b/core/net/uiplib.c
index 88911d2bc..b062b0867 100644
--- a/core/net/uiplib.c
+++ b/core/net/uiplib.c
@@ -42,9 +42,8 @@
/*-----------------------------------------------------------------------------------*/
int
-uiplib_ipaddrconv(const char *addrstr, uip_ipaddr_t *ipaddr)
+uiplib_ip6addrconv(const char *addrstr, uip_ip6addr_t *ipaddr)
{
-#if UIP_CONF_IPV6
uint16_t value;
int tmp, zero;
unsigned int len;
@@ -54,7 +53,7 @@ uiplib_ipaddrconv(const char *addrstr, uip_ipaddr_t *ipaddr)
zero = -1;
if(*addrstr == '[') addrstr++;
- for(len = 0; len < sizeof(uip_ipaddr_t) - 1; addrstr++) {
+ for(len = 0; len < sizeof(uip_ip6addr_t) - 1; addrstr++) {
c = *addrstr;
if(c == ':' || c == '\0' || c == ']' || c == '/') {
ipaddr->u8[len] = (value >> 8) & 0xff;
@@ -91,45 +90,63 @@ uiplib_ipaddrconv(const char *addrstr, uip_ipaddr_t *ipaddr)
PRINTF("uiplib: too large address\n");
return 0;
}
- if(len < sizeof(uip_ipaddr_t)) {
+ if(len < sizeof(uip_ip6addr_t)) {
if(zero < 0) {
PRINTF("uiplib: too short address\n");
return 0;
}
- memmove(&ipaddr->u8[zero + sizeof(uip_ipaddr_t) - len],
+ memmove(&ipaddr->u8[zero + sizeof(uip_ip6addr_t) - len],
&ipaddr->u8[zero], len - zero);
- memset(&ipaddr->u8[zero], 0, sizeof(uip_ipaddr_t) - len);
+ memset(&ipaddr->u8[zero], 0, sizeof(uip_ip6addr_t) - len);
}
-#else /* UIP_CONF_IPV6 */
-
+ return 1;
+}
+/*-----------------------------------------------------------------------------------*/
+/* Parse a IPv4-address from a string. Returns the number of characters read
+ * for the address. */
+int
+uiplib_ip4addrconv(const char *addrstr, uip_ip4addr_t *ipaddr)
+{
unsigned char tmp;
char c;
unsigned char i, j;
+ uint8_t charsread = 0;
tmp = 0;
-
+
for(i = 0; i < 4; ++i) {
j = 0;
do {
c = *addrstr;
++j;
if(j > 4) {
- return 0;
+ return 0;
}
- if(c == '.' || c == 0) {
- ipaddr->u8[i] = tmp;
- tmp = 0;
+ if(c == '.' || c == 0 || c == ' ') {
+ ipaddr->u8[i] = tmp;
+ tmp = 0;
} else if(c >= '0' && c <= '9') {
- tmp = (tmp * 10) + (c - '0');
+ tmp = (tmp * 10) + (c - '0');
} else {
- return 0;
+ return 0;
}
++addrstr;
- } while(c != '.' && c != 0);
+ ++charsread;
+ } while(c != '.' && c != 0 && c != ' ');
+
}
+ return charsread-1;
+}
+/*-----------------------------------------------------------------------------------*/
+int
+uiplib_ipaddrconv(const char *addrstr, uip_ipaddr_t *ipaddr)
+{
+#if UIP_CONF_IPV6
+ return uiplib_ip6addrconv(addrstr, ipaddr);
+#else /* UIP_CONF_IPV6 */
+ return uiplib_ip4addrconv(addrstr, ipaddr);
#endif /* UIP_CONF_IPV6 */
- return 1;
}
/*-----------------------------------------------------------------------------------*/
diff --git a/core/net/uiplib.h b/core/net/uiplib.h
index 508c83db4..f9ba9a3bf 100644
--- a/core/net/uiplib.h
+++ b/core/net/uiplib.h
@@ -60,7 +60,7 @@
* \param addrstr A pointer to a string containing the IP address in
* textual form.
*
- * \param addr A pointer to a uip_ipaddr_t that will be filled in with
+ * \param addr A pointer to a uip_ip4addr_t that will be filled in with
* the numerical representation of the address.
*
* \retval 0 If the IP address could not be parsed.
@@ -68,6 +68,8 @@
*/
CCIF int uiplib_ipaddrconv(const char *addrstr, uip_ipaddr_t *addr);
+CCIF int uiplib_ip4addrconv(const char *addrstr, uip_ip4addr_t *addr);
+CCIF int uiplib_ip6addrconv(const char *addrstr, uip_ip6addr_t *addr);
/** @} */
#endif /* __UIPLIB_H__ */
diff --git a/examples/ipv6/native-border-router/border-router.c b/examples/ipv6/native-border-router/border-router.c
index e3f5af2ac..b8d01f2bb 100644
--- a/examples/ipv6/native-border-router/border-router.c
+++ b/examples/ipv6/native-border-router/border-router.c
@@ -149,6 +149,7 @@ static
PT_THREAD(generate_routes(struct httpd_state *s))
{
static int i;
+ static uip_ds6_route_t *r;
PSOCK_BEGIN(&s->sout);
SEND_STRING(&s->sout, TOP);
@@ -169,19 +170,19 @@ PT_THREAD(generate_routes(struct httpd_state *s))
ADD("Routes");
SEND_STRING(&s->sout, buf);
blen = 0;
- for(i = 0; i < UIP_DS6_ROUTE_NB; i++) {
- if(uip_ds6_routing_table[i].isused) {
- ipaddr_add(&uip_ds6_routing_table[i].ipaddr);
- ADD("/%u (via ", uip_ds6_routing_table[i].length);
- ipaddr_add(&uip_ds6_routing_table[i].nexthop);
- if(uip_ds6_routing_table[i].state.lifetime < 600) {
- ADD(") %lus\n", (unsigned long)uip_ds6_routing_table[i].state.lifetime);
- } else {
- ADD(")\n");
- }
- SEND_STRING(&s->sout, buf);
- blen = 0;
+ for(r = uip_ds6_route_list_head();
+ r != NULL;
+ r = list_item_next(r)) {
+ ipaddr_add(&r->ipaddr);
+ ADD("/%u (via ", r->length);
+ ipaddr_add(&r->nexthop);
+ if(r->state.lifetime < 600) {
+ ADD(") %lus\n", (unsigned long)r->state.lifetime);
+ } else {
+ ADD(")\n");
}
+ SEND_STRING(&s->sout, buf);
+ blen = 0;
}
ADD("
");
//if(blen > 0) {
diff --git a/examples/ipv6/rpl-border-router/border-router.c b/examples/ipv6/rpl-border-router/border-router.c
index 3c3a60de5..9a40f84a1 100644
--- a/examples/ipv6/rpl-border-router/border-router.c
+++ b/examples/ipv6/rpl-border-router/border-router.c
@@ -57,7 +57,6 @@
uint16_t dag_id[] = {0x1111, 0x1100, 0, 0, 0, 0, 0, 0x0011};
extern uip_ds6_nbr_t uip_ds6_nbr_cache[];
-extern uip_ds6_route_t uip_ds6_routing_table[];
static uip_ipaddr_t prefix;
static uint8_t prefix_set;
@@ -149,6 +148,7 @@ static
PT_THREAD(generate_routes(struct httpd_state *s))
{
static int i;
+ static uip_ds6_route_t *r;
#if BUF_USES_STACK
char buf[256];
#endif
@@ -220,45 +220,45 @@ PT_THREAD(generate_routes(struct httpd_state *s))
#else
blen = 0;
#endif
- for(i = 0; i < UIP_DS6_ROUTE_NB; i++) {
- if(uip_ds6_routing_table[i].isused) {
+
+ for(r = uip_ds6_route_list_head(); r != NULL; r = list_item_next(r)) {
+
#if BUF_USES_STACK
#if WEBSERVER_CONF_ROUTE_LINKS
- ADD("");
- ipaddr_add(&uip_ds6_routing_table[i].ipaddr);
- ADD("");
+ ADD("ipaddr);
+ ADD("]/status.shtml>");
+ ipaddr_add(&r->ipaddr);
+ ADD("");
#else
- ipaddr_add(&uip_ds6_routing_table[i].ipaddr);
+ ipaddr_add(&r->ipaddr);
#endif
#else
#if WEBSERVER_CONF_ROUTE_LINKS
- ADD("");
- SEND_STRING(&s->sout, buf); //TODO: why tunslip6 needs an output here, wpcapslip does not
- blen = 0;
- ipaddr_add(&uip_ds6_routing_table[i].ipaddr);
- ADD("");
+ ADD("ipaddr);
+ ADD("]/status.shtml>");
+ SEND_STRING(&s->sout, buf); //TODO: why tunslip6 needs an output here, wpcapslip does not
+ blen = 0;
+ ipaddr_add(&r->ipaddr);
+ ADD("");
#else
- ipaddr_add(&uip_ds6_routing_table[i].ipaddr);
+ ipaddr_add(&r->ipaddr);
#endif
#endif
- ADD("/%u (via ", uip_ds6_routing_table[i].length);
- ipaddr_add(&uip_ds6_routing_table[i].nexthop);
- if(1 || (uip_ds6_routing_table[i].state.lifetime < 600)) {
- ADD(") %lus\n", uip_ds6_routing_table[i].state.lifetime);
- } else {
- ADD(")\n");
- }
- SEND_STRING(&s->sout, buf);
-#if BUF_USES_STACK
- bufptr = buf; bufend = bufptr + sizeof(buf);
-#else
- blen = 0;
-#endif
+ ADD("/%u (via ", r->length);
+ ipaddr_add(&r->nexthop);
+ if(1 || (r->state.lifetime < 600)) {
+ ADD(") %lus\n", r->state.lifetime);
+ } else {
+ ADD(")\n");
}
+ SEND_STRING(&s->sout, buf);
+#if BUF_USES_STACK
+ bufptr = buf; bufend = bufptr + sizeof(buf);
+#else
+ blen = 0;
+#endif
}
ADD("");
diff --git a/examples/ipv6/rpl-collect/udp-sender.c b/examples/ipv6/rpl-collect/udp-sender.c
index fa5c80790..113afdc4a 100644
--- a/examples/ipv6/rpl-collect/udp-sender.c
+++ b/examples/ipv6/rpl-collect/udp-sender.c
@@ -70,7 +70,8 @@ void
collect_common_net_print(void)
{
rpl_dag_t *dag;
- int i;
+ uip_ds6_route_t *r;
+
/* Let's suppose we have only one instance */
dag = rpl_get_any_dag();
if(dag->preferred_parent != NULL) {
@@ -78,12 +79,10 @@ collect_common_net_print(void)
PRINT6ADDR(&dag->preferred_parent->addr);
PRINTF("\n");
}
- PRINTF("Route entries:\n");
- for(i = 0; i < UIP_DS6_ROUTE_NB; i++) {
- if(uip_ds6_routing_table[i].isused) {
- PRINT6ADDR(&uip_ds6_routing_table[i].ipaddr);
- PRINTF("\n");
- }
+ for(r = uip_ds6_route_list_head();
+ r != NULL;
+ r = list_item_next(r)) {
+ PRINT6ADDR(&r->ipaddr);
}
PRINTF("---\n");
}
diff --git a/platform/avr-atmega128rfa1/contiki-main.c b/platform/avr-atmega128rfa1/contiki-main.c
index 995960151..05a9ee392 100644
--- a/platform/avr-atmega128rfa1/contiki-main.c
+++ b/platform/avr-atmega128rfa1/contiki-main.c
@@ -536,17 +536,22 @@ extern uip_ds6_netif_t uip_ds6_if;
}
if (j) PRINTF(" ");
PRINTF("\nRoutes [%u max]\n",UIP_DS6_ROUTE_NB);
- for(i = 0,j=1; i < UIP_DS6_ROUTE_NB; i++) {
- if(uip_ds6_routing_table[i].isused) {
- ipaddr_add(&uip_ds6_routing_table[i].ipaddr);
- PRINTF("/%u (via ", uip_ds6_routing_table[i].length);
- ipaddr_add(&uip_ds6_routing_table[i].nexthop);
+ {
+ uip_ds6_route_t *r;
+ PRINTF("\nRoutes [%u max]\n",UIP_DS6_ROUTE_NB);
+ j = 1;
+ for(r = uip_ds6_route_list_head();
+ r != NULL;
+ r = list_item_next(r)) {
+ ipaddr_add(&r->ipaddr);
+ PRINTF("/%u (via ", r->length);
+ ipaddr_add(&r->nexthop);
// if(uip_ds6_routing_table[i].state.lifetime < 600) {
- PRINTF(") %lus\n", uip_ds6_routing_table[i].state.lifetime);
- // } else {
- // PRINTF(")\n");
- // }
- j=0;
+ PRINTF(") %lus\n", r->state.lifetime);
+ // } else {
+ // PRINTF(")\n");
+ // }
+ j = 0;
}
}
if (j) PRINTF(" ");
diff --git a/platform/avr-raven/apps/raven-webserver/httpd-cgi.c b/platform/avr-raven/apps/raven-webserver/httpd-cgi.c
index 793aefbe3..a9ed784f8 100644
--- a/platform/avr-raven/apps/raven-webserver/httpd-cgi.c
+++ b/platform/avr-raven/apps/raven-webserver/httpd-cgi.c
@@ -354,23 +354,25 @@ PT_THREAD(neighbors(struct httpd_state *s, char *ptr))
static unsigned short
make_routes(void *p)
{
-static const char httpd_cgi_rtes1[] HTTPD_STRING_ATTR = "(%u (via ";
-static const char httpd_cgi_rtes2[] HTTPD_STRING_ATTR = ") %lus
";
-static const char httpd_cgi_rtes3[] HTTPD_STRING_ATTR = ")
";
-uint8_t i,j=0;
-uint16_t numprinted;
+ static const char httpd_cgi_rtes1[] HTTPD_STRING_ATTR = "(%u (via ";
+ static const char httpd_cgi_rtes2[] HTTPD_STRING_ATTR = ") %lus
";
+ static const char httpd_cgi_rtes3[] HTTPD_STRING_ATTR = ")
";
+ uint8_t i,j=0;
+ uint16_t numprinted;
+ uip_ds6_route_t *r;
+
numprinted = httpd_snprintf((char *)uip_appdata, uip_mss(),httpd_cgi_addrh);
- for (i=0; iipaddr, uip_appdata + numprinted);
+ numprinted += httpd_snprintf((char *)uip_appdata+numprinted, uip_mss()-numprinted, httpd_cgi_rtes1, r->length);
+ numprinted += httpd_cgi_sprint_ip6(r->nexthop, uip_appdata + numprinted);
+ if(r->state.lifetime < 3600) {
+ numprinted += httpd_snprintf((char *)uip_appdata+numprinted, uip_mss()-numprinted, httpd_cgi_rtes2, r->state.lifetime);
+ } else {
+ numprinted += httpd_snprintf((char *)uip_appdata+numprinted, uip_mss()-numprinted, httpd_cgi_rtes3);
}
}
if (j==0) numprinted += httpd_snprintf((char *)uip_appdata+numprinted, uip_mss()-numprinted, httpd_cgi_addrn);
diff --git a/platform/avr-raven/contiki-raven-main.c b/platform/avr-raven/contiki-raven-main.c
index 1d939ebc9..c9521c124 100644
--- a/platform/avr-raven/contiki-raven-main.c
+++ b/platform/avr-raven/contiki-raven-main.c
@@ -531,18 +531,22 @@ extern uip_ds6_netif_t uip_ds6_if;
}
}
if (j) PRINTF(" ");
- PRINTF("\nRoutes [%u max]\n",UIP_DS6_ROUTE_NB);
- for(i = 0,j=1; i < UIP_DS6_ROUTE_NB; i++) {
- if(uip_ds6_routing_table[i].isused) {
- ipaddr_add(&uip_ds6_routing_table[i].ipaddr);
- PRINTF("/%u (via ", uip_ds6_routing_table[i].length);
- ipaddr_add(&uip_ds6_routing_table[i].nexthop);
+ {
+ uip_ds6_route_t *r;
+ PRINTF("\nRoutes [%u max]\n",UIP_DS6_ROUTE_NB);
+ j = 1;
+ for(r = uip_ds6_route_list_head();
+ r != NULL;
+ r = list_item_next(r)) {
+ ipaddr_add(&r->ipaddr);
+ PRINTF("/%u (via ", r->length);
+ ipaddr_add(&r->nexthop);
// if(uip_ds6_routing_table[i].state.lifetime < 600) {
- PRINTF(") %lus\n", uip_ds6_routing_table[i].state.lifetime);
- // } else {
- // PRINTF(")\n");
- // }
- j=0;
+ PRINTF(") %lus\n", r->state.lifetime);
+ // } else {
+ // PRINTF(")\n");
+ // }
+ j = 0;
}
}
if (j) PRINTF(" ");
diff --git a/platform/redbee-econotag/contiki-mc1322x-main.c b/platform/redbee-econotag/contiki-mc1322x-main.c
index f3bc8f5a3..d43d34661 100644
--- a/platform/redbee-econotag/contiki-mc1322x-main.c
+++ b/platform/redbee-econotag/contiki-mc1322x-main.c
@@ -614,18 +614,23 @@ extern uip_ds6_netif_t uip_ds6_if;
}
}
if (j) printf(" ");
- printf("\nRoutes [%u max]\n",UIP_DS6_ROUTE_NB);
- for(i = 0,j=1; i < UIP_DS6_ROUTE_NB; i++) {
- if(uip_ds6_routing_table[i].isused) {
- uip_debug_ipaddr_print(&uip_ds6_routing_table[i].ipaddr);
- printf("/%u (via ", uip_ds6_routing_table[i].length);
- uip_debug_ipaddr_print(&uip_ds6_routing_table[i].nexthop);
+ PRINTF("\nRoutes [%u max]\n",UIP_DS6_ROUTE_NB);
+ {
+ uip_ds6_route_t *r;
+ PRINTF("\nRoutes [%u max]\n",UIP_DS6_ROUTE_NB);
+ j = 1;
+ for(r = uip_ds6_route_list_head();
+ r != NULL;
+ r = list_item_next(r)) {
+ ipaddr_add(&r->ipaddr);
+ PRINTF("/%u (via ", r->length);
+ ipaddr_add(&r->nexthop);
// if(uip_ds6_routing_table[i].state.lifetime < 600) {
- printf(") %lus\n", uip_ds6_routing_table[i].state.lifetime);
- // } else {
- // printf(")\n");
- // }
- j=0;
+ PRINTF(") %lus\n", r->state.lifetime);
+ // } else {
+ // PRINTF(")\n");
+ // }
+ j = 0;
}
}
if (j) printf(" ");