Implement forwarding error handling: if a packet changes direction, we set the FWD_ERR flag. If we see the FWD_ERR flag, we drop the route that we sent it to. If we are the root node, we also initiate a global repair.
This commit is contained in:
parent
abb3ef9b3b
commit
d830e9df3f
1 changed files with 47 additions and 17 deletions
|
@ -75,12 +75,6 @@ rpl_verify_header(int uip_ext_opt_offset)
|
|||
return 1;
|
||||
}
|
||||
|
||||
if(UIP_EXT_HDR_OPT_RPL_BUF->flags & RPL_HDR_OPT_FWD_ERR) {
|
||||
PRINTF("RPL: Forward error!\n");
|
||||
/* We should try to repair it, not implemented for the moment */
|
||||
return 2;
|
||||
}
|
||||
|
||||
instance = rpl_get_instance(UIP_EXT_HDR_OPT_RPL_BUF->instance);
|
||||
if(instance == NULL) {
|
||||
PRINTF("RPL: Unknown instance: %u\n",
|
||||
|
@ -88,6 +82,31 @@ rpl_verify_header(int uip_ext_opt_offset)
|
|||
return 1;
|
||||
}
|
||||
|
||||
if(UIP_EXT_HDR_OPT_RPL_BUF->flags & RPL_HDR_OPT_FWD_ERR) {
|
||||
PRINTF("RPL: Forward error!\n");
|
||||
/* We should try to repair it by removing the neighbor that caused
|
||||
the packet to be forwareded in the first place. We drop any
|
||||
routes that go through the neighbor that sent the packet to
|
||||
us. */
|
||||
uip_ds6_route_t *route;
|
||||
route = uip_ds6_route_lookup(&UIP_IP_BUF->destipaddr);
|
||||
if(route != NULL) {
|
||||
uip_ds6_route_rm(route);
|
||||
|
||||
/* If we are the root and just needed to remove a DAO route,
|
||||
chances are that the network needs to be repaired. The
|
||||
rpl_repair_root() function will cause a global repair if we
|
||||
happen to be the root node of the dag. */
|
||||
PRINTF("RPL: initiate global repair\n");
|
||||
rpl_repair_root(instance->instance_id);
|
||||
}
|
||||
|
||||
/* Remove the forwarding error flag and return 0 to let the packet
|
||||
be forwarded again. */
|
||||
UIP_EXT_HDR_OPT_RPL_BUF->flags &= ~RPL_HDR_OPT_FWD_ERR;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(!instance->current_dag->joined) {
|
||||
PRINTF("RPL: No DAG in the instance\n");
|
||||
return 1;
|
||||
|
@ -191,18 +210,29 @@ rpl_update_header_empty(void)
|
|||
PRINTF("RPL: Updating RPL option\n");
|
||||
UIP_EXT_HDR_OPT_RPL_BUF->senderrank = instance->current_dag->rank;
|
||||
|
||||
|
||||
/* Check the direction of the down flag, as per Section 11.2.2.3,
|
||||
which states that if a packet is going down it should in
|
||||
general not go back up again. If this happens, a
|
||||
RPL_HDR_OPT_FWD_ERR should be flagged. */
|
||||
if((UIP_EXT_HDR_OPT_RPL_BUF->flags & RPL_HDR_OPT_DOWN)) {
|
||||
if(uip_ds6_route_lookup(&UIP_IP_BUF->destipaddr) == NULL) {
|
||||
UIP_EXT_HDR_OPT_RPL_BUF->flags |= RPL_HDR_OPT_FWD_ERR;
|
||||
PRINTF("RPL forwarding error\n");
|
||||
}
|
||||
} else {
|
||||
/* Set the down extension flag correctly as described in Section
|
||||
11.2 of RFC6550. If the packet progresses along a DAO route,
|
||||
the down flag should be set. */
|
||||
|
||||
if(uip_ds6_route_lookup(&UIP_IP_BUF->destipaddr) == NULL) {
|
||||
/* No route was found, so this packet will go towards the RPL
|
||||
root. If so, we should not set the down flag. */
|
||||
UIP_EXT_HDR_OPT_RPL_BUF->flags &= ~RPL_HDR_OPT_DOWN;
|
||||
PRINTF("RPL option going up\n");
|
||||
} else {
|
||||
/* A DAO route was found so we set the down flag. */
|
||||
UIP_EXT_HDR_OPT_RPL_BUF->flags |= RPL_HDR_OPT_DOWN;
|
||||
PRINTF("RPL option going down\n");
|
||||
}
|
||||
}
|
||||
|
||||
uip_ext_len = last_uip_ext_len;
|
||||
|
|
Loading…
Reference in a new issue