diff --git a/Makefile.dep b/Makefile.dep index 0895d9992bf9f6286c26cea7fe76e846231cb775..6fbd8a1e6f60a5a89715808faffeafb6ef84ebdb 100644 --- a/Makefile.dep +++ b/Makefile.dep @@ -127,6 +127,7 @@ ifneq (,$(filter gnrc_rpl,$(USEMODULE))) USEMODULE += gnrc_ipv6_nib USEMODULE += trickle USEMODULE += xtimer + USEMODULE += evtimer endif ifneq (,$(filter trickle,$(USEMODULE))) diff --git a/sys/include/net/gnrc/rpl.h b/sys/include/net/gnrc/rpl.h index ef0d62ccaf50fa30bcc3106ea724e14f2f5b7753..35a1bf463031aee2093490bb36315d60cb918c06 100644 --- a/sys/include/net/gnrc/rpl.h +++ b/sys/include/net/gnrc/rpl.h @@ -1,7 +1,7 @@ /* * Copyright (C) 2013 - 2014 INRIA. * Copyright (C) 2015 Martine Lenders <mlenders@inf.fu-berlin.de> - * Copyright (C) 2015 Cenk Gündoğan <cnkgndgn@gmail.com> + * Copyright (C) 2015 - 2018 Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> * * This file is subject to the terms and conditions of the GNU Lesser * General Public License v2.1. See the file LICENSE in the top level @@ -92,7 +92,7 @@ * @author Eric Engel <eric.engel@fu-berlin.de> * @author Fabian Brandt <fabianbr@zedat.fu-berlin.de> * @author Martine Lenders <mlenders@inf.fu-berlin.de> - * @author Cenk Gündoğan <cnkgndgn@gmail.com> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #ifndef NET_GNRC_RPL_H @@ -326,23 +326,37 @@ static inline bool GNRC_RPL_COUNTER_GREATER_THAN(uint8_t A, uint8_t B) * @{ */ #ifndef GNRC_RPL_DAO_SEND_RETRIES -#define GNRC_RPL_DAO_SEND_RETRIES (4) +#define GNRC_RPL_DAO_SEND_RETRIES (4) #endif -#ifndef GNRC_RPL_DEFAULT_WAIT_FOR_DAO_ACK -#define GNRC_RPL_DEFAULT_WAIT_FOR_DAO_ACK (3) +#ifndef GNRC_RPL_DAO_ACK_DELAY +#define GNRC_RPL_DAO_ACK_DELAY (3000UL) #endif -#ifndef GNRC_RPL_REGULAR_DAO_INTERVAL -#define GNRC_RPL_REGULAR_DAO_INTERVAL (60) +#ifndef GNRC_RPL_DAO_DELAY_LONG +/** + * @brief Long delay for DAOs in milli seconds + */ +#define GNRC_RPL_DAO_DELAY_LONG (60000UL) +#endif +#ifndef GNRC_RPL_DAO_DELAY_DEFAULT +/** + * @brief Default delay for DAOs in milli seconds + */ +#define GNRC_RPL_DAO_DELAY_DEFAULT (1000UL) #endif -#ifndef GNRC_RPL_DEFAULT_DAO_DELAY -#define GNRC_RPL_DEFAULT_DAO_DELAY (1) +#ifndef GNRC_RPL_DAO_DELAY_JITTER +/** + * @brief Jitter for DAOs in milli seconds + */ +#define GNRC_RPL_DAO_DELAY_JITTER (1000UL) #endif /** @} */ /** - * @brief Cleanup timeout in seconds + * @brief Cleanup interval in milliseconds. */ -#define GNRC_RPL_CLEANUP_TIME (5) +#ifndef GNRC_RPL_CLEANUP_TIME +#define GNRC_RPL_CLEANUP_TIME (5 * MS_PER_SEC) +#endif /** * @name Node Status @@ -453,6 +467,13 @@ extern const ipv6_addr_t ipv6_addr_all_rpl_nodes; extern netstats_rpl_t gnrc_rpl_netstats; #endif +/** + * @brief Number of DIS retries before parent times out + */ +#ifndef GNRC_RPL_PARENT_TIMEOUT_DIS_RETRIES +#define GNRC_RPL_PARENT_TIMEOUT_DIS_RETRIES (3) +#endif + /** * @brief Initialization of the RPL thread. * diff --git a/sys/include/net/gnrc/rpl/p2p_structs.h b/sys/include/net/gnrc/rpl/p2p_structs.h index 0fcc42b752c90a03e73000bca041afedd2187db1..dd3fe94ef086dbfc22224269aad5f3030d927a30 100644 --- a/sys/include/net/gnrc/rpl/p2p_structs.h +++ b/sys/include/net/gnrc/rpl/p2p_structs.h @@ -1,5 +1,5 @@ /* - * Copyright (C) 2016 Cenk Gündoğan <mail@cgundogan.de> + * Copyright (C) 2016 Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> * * This file is subject to the terms and conditions of the GNU Lesser * General Public License v2.1. See the file LICENSE in the top level @@ -15,7 +15,7 @@ * * Header file, which defines all structs used by P2P-RPL. * - * @author Cenk Gündoğan <mail@cgundogan.de> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #ifndef NET_GNRC_RPL_P2P_STRUCTS_H diff --git a/sys/include/net/gnrc/rpl/structs.h b/sys/include/net/gnrc/rpl/structs.h index 230371d601b8face84e6886e9c00db3e5f4b1651..f0e4118e9e2abe31d51a89acbe90b9f04887401e 100644 --- a/sys/include/net/gnrc/rpl/structs.h +++ b/sys/include/net/gnrc/rpl/structs.h @@ -1,6 +1,7 @@ /* - * Copyright (C) 2013 INRIA. - * Copyright (C) 2015 Cenk Gündoğan <cnkgndgn@gmail.com> + * Copyright (C) 2017 HAW Hamburg + * Copyright (C) 2015–2018 Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> + * Copyright (C) 2013 INRIA. * * This file is subject to the terms and conditions of the GNU Lesser * General Public License v2.1. See the file LICENSE in the top level @@ -17,7 +18,7 @@ * Header file, which defines all structs used by RPL. * * @author Eric Engel <eric.engel@fu-berlin.de> - * @author Cenk Gündoğan <cnkgndgn@gmail.com> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #ifndef NET_GNRC_RPL_STRUCTS_H @@ -29,7 +30,8 @@ extern "C" { #include "byteorder.h" #include "net/ipv6/addr.h" -#include "xtimer.h" +#include "evtimer.h" +#include "evtimer_msg.h" #include "trickle.h" /** @@ -221,14 +223,17 @@ typedef struct gnrc_rpl_instance gnrc_rpl_instance_t; * @cond INTERNAL */ struct gnrc_rpl_parent { gnrc_rpl_parent_t *next; /**< pointer to the next parent */ - uint8_t state; /**< 0 for unsued, 1 for used */ + uint8_t state; /**< see @ref gnrc_rpl_parent_states */ ipv6_addr_t addr; /**< link-local IPv6 address of this parent */ uint8_t dtsn; /**< last seen dtsn of this parent */ uint16_t rank; /**< rank of the parent */ gnrc_rpl_dodag_t *dodag; /**< DODAG the parent belongs to */ - uint32_t lifetime; /**< lifetime of this parent in seconds */ - double link_metric; /**< metric of the link */ + double link_metric; /**< metric of the link */ uint8_t link_metric_type; /**< type of the metric */ + /** + * @brief Parent timeout events (see @ref GNRC_RPL_MSG_TYPE_PARENT_TIMEOUT) + */ + evtimer_msg_event_t timeout_event; }; /** * @endcond @@ -289,7 +294,7 @@ struct gnrc_rpl_dodag { bool dao_ack_received; /**< flag to check for DAO-ACK */ uint8_t dio_opts; /**< options in the next DIO (see @ref GNRC_RPL_REQ_DIO_OPTS "DIO Options") */ - uint8_t dao_time; /**< time to schedule a DAO in seconds */ + evtimer_msg_event_t dao_event; /**< DAO TX events (see @ref GNRC_RPL_MSG_TYPE_DODAG_DAO_TX) */ trickle_t trickle; /**< trickle representation */ }; @@ -301,7 +306,10 @@ struct gnrc_rpl_instance { gnrc_rpl_of_t *of; /**< configured Objective Function */ uint16_t min_hop_rank_inc; /**< minimum hop rank increase */ uint16_t max_rank_inc; /**< max increase in the rank */ - int8_t cleanup; /**< cleanup time in seconds */ + /** + * @brief Instance cleanup events (see @ref GNRC_RPL_MSG_TYPE_INSTANCE_CLEANUP) + */ + evtimer_msg_event_t cleanup_event; }; /** * @endcond diff --git a/sys/net/gnrc/routing/rpl/gnrc_rpl.c b/sys/net/gnrc/routing/rpl/gnrc_rpl.c index 0af0cb6aa6a6c772f05e2972098c574195971a0c..a82a166c01ae90b3aa23ffd6efb6288e6a7e853b 100644 --- a/sys/net/gnrc/routing/rpl/gnrc_rpl.c +++ b/sys/net/gnrc/routing/rpl/gnrc_rpl.c @@ -1,5 +1,6 @@ /* - * Copyright (C) 2015 Cenk Gündoğan <cnkgndgn@gmail.com> + * Copyright (C) 2018 HAW Hamburg + * Copyright (C) 2015–2017 Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> * * This file is subject to the terms and conditions of the GNU Lesser * General Public License v2.1. See the file LICENSE in the top level @@ -11,7 +12,7 @@ * * @file * - * @author Cenk Gündoğan <cnkgndgn@gmail.com> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #include "net/icmpv6.h" @@ -19,6 +20,9 @@ #include "net/gnrc/netif/internal.h" #include "net/gnrc.h" #include "mutex.h" +#include "evtimer.h" +#include "random.h" +#include "gnrc_rpl_internal/globals.h" #include "net/gnrc/rpl.h" #ifdef MODULE_GNRC_RPL_P2P @@ -32,9 +36,11 @@ static char _stack[GNRC_RPL_STACK_SIZE]; kernel_pid_t gnrc_rpl_pid = KERNEL_PID_UNDEF; const ipv6_addr_t ipv6_addr_all_rpl_nodes = GNRC_RPL_ALL_NODES_ADDR; +#ifdef MODULE_GNRC_RPL_P2P static uint32_t _lt_time = GNRC_RPL_LIFETIME_UPDATE_STEP * US_PER_SEC; static xtimer_t _lt_timer; static msg_t _lt_msg = { .type = GNRC_RPL_MSG_TYPE_LIFETIME_UPDATE }; +#endif static msg_t _msg_q[GNRC_RPL_MSG_QUEUE_SIZE]; static gnrc_netreg_entry_t _me_reg; static mutex_t _inst_id_mutex = MUTEX_INIT; @@ -47,11 +53,15 @@ gnrc_rpl_parent_t gnrc_rpl_parents[GNRC_RPL_PARENTS_NUMOF]; netstats_rpl_t gnrc_rpl_netstats; #endif +#ifdef MODULE_GNRC_RPL_P2P static void _update_lifetime(void); +#endif static void _dao_handle_send(gnrc_rpl_dodag_t *dodag); static void _receive(gnrc_pktsnip_t *pkt); static void *_event_loop(void *args); +evtimer_msg_t gnrc_rpl_evtimer; + kernel_pid_t gnrc_rpl_init(kernel_pid_t if_pid) { /* check if RPL was initialized before */ @@ -73,7 +83,10 @@ kernel_pid_t gnrc_rpl_init(kernel_pid_t if_pid) gnrc_netreg_register(GNRC_NETTYPE_ICMPV6, &_me_reg); gnrc_rpl_of_manager_init(); + evtimer_init_msg(&gnrc_rpl_evtimer); +#ifdef MODULE_GNRC_RPL_P2P xtimer_set_msg(&_lt_timer, _lt_time, &_lt_msg, gnrc_rpl_pid); +#endif #ifdef MODULE_NETSTATS_RPL memset(&gnrc_rpl_netstats, 0, sizeof(gnrc_rpl_netstats)); @@ -196,6 +209,35 @@ static void _receive(gnrc_pktsnip_t *icmpv6) gnrc_pktbuf_release(icmpv6); } +static void _parent_timeout(gnrc_rpl_parent_t *parent) +{ + if (!parent || (parent->state == GNRC_RPL_PARENT_UNUSED)) { + return; + } + + evtimer_del(&gnrc_rpl_evtimer, (evtimer_event_t *)&parent->timeout_event); + + if (parent->state == GNRC_RPL_PARENT_ACTIVE) { + parent->state = GNRC_RPL_PARENT_STALE; + } + + if ((parent->state >= GNRC_RPL_PARENT_STALE) && + (parent->state < GNRC_RPL_PARENT_TIMEOUT)) { + parent->state++; + gnrc_rpl_send_DIS(parent->dodag->instance, &parent->addr); + } + else { + gnrc_rpl_dodag_t *dodag = parent->dodag; + gnrc_rpl_parent_remove(parent); + gnrc_rpl_parent_update(dodag, NULL); + return; + } + + ((evtimer_event_t *)&(parent->timeout_event))->offset = GNRC_RPL_PARENT_PROBE_INTERVAL; + parent->timeout_event.msg.type = GNRC_RPL_MSG_TYPE_PARENT_TIMEOUT; + evtimer_add_msg(&gnrc_rpl_evtimer, &parent->timeout_event, gnrc_rpl_pid); +} + static void *_event_loop(void *args) { msg_t msg, reply; @@ -207,16 +249,38 @@ static void *_event_loop(void *args) reply.type = GNRC_NETAPI_MSG_TYPE_ACK; trickle_t *trickle; + gnrc_rpl_parent_t *parent; + gnrc_rpl_instance_t *instance; + /* start event loop */ while (1) { DEBUG("RPL: waiting for incoming message.\n"); msg_receive(&msg); switch (msg.type) { +#ifdef MODULE_GNRC_RPL_P2P case GNRC_RPL_MSG_TYPE_LIFETIME_UPDATE: DEBUG("RPL: GNRC_RPL_MSG_TYPE_LIFETIME_UPDATE received\n"); _update_lifetime(); break; +#endif + case GNRC_RPL_MSG_TYPE_PARENT_TIMEOUT: + DEBUG("RPL: GNRC_RPL_MSG_TYPE_PARENT_TIMEOUT received\n"); + parent = msg.content.ptr; + _parent_timeout(parent); + break; + case GNRC_RPL_MSG_TYPE_DODAG_DAO_TX: + DEBUG("RPL: GNRC_RPL_MSG_TYPE_DODAG_DAO_TX received\n"); + instance = msg.content.ptr; + _dao_handle_send(&instance->dodag); + break; + case GNRC_RPL_MSG_TYPE_INSTANCE_CLEANUP: + DEBUG("RPL: GNRC_RPL_MSG_TYPE_INSTANCE_CLEANUP received\n"); + instance = msg.content.ptr; + if (instance->dodag.parents == NULL) { + gnrc_rpl_instance_remove(instance); + } + break; case GNRC_RPL_MSG_TYPE_TRICKLE_MSG: DEBUG("RPL: GNRC_RPL_MSG_TYPE_TRICKLE_MSG received\n"); trickle = msg.content.ptr; @@ -244,73 +308,44 @@ static void *_event_loop(void *args) return NULL; } +#ifdef MODULE_GNRC_RPL_P2P void _update_lifetime(void) { - gnrc_rpl_parent_t *parent; - gnrc_rpl_instance_t *inst; - - for (uint8_t i = 0; i < GNRC_RPL_PARENTS_NUMOF; ++i) { - parent = &gnrc_rpl_parents[i]; - if (parent->state != 0) { - if (parent->lifetime > GNRC_RPL_LIFETIME_UPDATE_STEP) { - if (parent->lifetime <= (2 * GNRC_RPL_LIFETIME_UPDATE_STEP)) { - gnrc_rpl_send_DIS(parent->dodag->instance, &parent->addr); - } - parent->lifetime -= GNRC_RPL_LIFETIME_UPDATE_STEP; - } - else { - gnrc_rpl_dodag_t *dodag = parent->dodag; - gnrc_rpl_parent_remove(parent); - gnrc_rpl_parent_update(dodag, NULL); - } - } - } - - for (int i = 0; i < GNRC_RPL_INSTANCES_NUMOF; ++i) { - inst = &gnrc_rpl_instances[i]; - if (inst->state != 0) { - if ((inst->cleanup > 0) && (inst->dodag.parents == NULL) && - (inst->dodag.my_rank == GNRC_RPL_INFINITE_RANK)) { - inst->cleanup -= GNRC_RPL_LIFETIME_UPDATE_STEP; - if (inst->cleanup <= 0) { - /* no parents - delete this instance and DODAG */ - gnrc_rpl_instance_remove(inst); - continue; - } - } - - if (inst->dodag.dao_time > GNRC_RPL_LIFETIME_UPDATE_STEP) { - inst->dodag.dao_time -= GNRC_RPL_LIFETIME_UPDATE_STEP; - } - else { - _dao_handle_send(&inst->dodag); - } - } - } - -#ifdef MODULE_GNRC_RPL_P2P gnrc_rpl_p2p_update(); -#endif xtimer_set_msg(&_lt_timer, _lt_time, &_lt_msg, gnrc_rpl_pid); } +#endif void gnrc_rpl_delay_dao(gnrc_rpl_dodag_t *dodag) { - dodag->dao_time = GNRC_RPL_DEFAULT_DAO_DELAY; + evtimer_del(&gnrc_rpl_evtimer, (evtimer_event_t *)&dodag->dao_event); + ((evtimer_event_t *)&(dodag->dao_event))->offset = random_uint32_range( + GNRC_RPL_DAO_DELAY_DEFAULT, + GNRC_RPL_DAO_DELAY_DEFAULT + GNRC_RPL_DAO_DELAY_JITTER + ); + evtimer_add_msg(&gnrc_rpl_evtimer, &dodag->dao_event, gnrc_rpl_pid); dodag->dao_counter = 0; dodag->dao_ack_received = false; } void gnrc_rpl_long_delay_dao(gnrc_rpl_dodag_t *dodag) { - dodag->dao_time = GNRC_RPL_REGULAR_DAO_INTERVAL; + evtimer_del(&gnrc_rpl_evtimer, (evtimer_event_t *)&dodag->dao_event); + ((evtimer_event_t *)&(dodag->dao_event))->offset = random_uint32_range( + GNRC_RPL_DAO_DELAY_LONG, + GNRC_RPL_DAO_DELAY_LONG + GNRC_RPL_DAO_DELAY_JITTER + ); + evtimer_add_msg(&gnrc_rpl_evtimer, &dodag->dao_event, gnrc_rpl_pid); dodag->dao_counter = 0; dodag->dao_ack_received = false; } void _dao_handle_send(gnrc_rpl_dodag_t *dodag) { + if (dodag->node_status == GNRC_RPL_ROOT_NODE) { + return; + } #ifdef MODULE_GNRC_RPL_P2P if (dodag->instance->mop == GNRC_RPL_P2P_MOP) { return; @@ -319,7 +354,9 @@ void _dao_handle_send(gnrc_rpl_dodag_t *dodag) if ((dodag->dao_ack_received == false) && (dodag->dao_counter < GNRC_RPL_DAO_SEND_RETRIES)) { dodag->dao_counter++; gnrc_rpl_send_DAO(dodag->instance, NULL, dodag->default_lifetime); - dodag->dao_time = GNRC_RPL_DEFAULT_WAIT_FOR_DAO_ACK; + evtimer_del(&gnrc_rpl_evtimer, (evtimer_event_t *)&dodag->dao_event); + ((evtimer_event_t *)&(dodag->dao_event))->offset = GNRC_RPL_DAO_ACK_DELAY; + evtimer_add_msg(&gnrc_rpl_evtimer, &dodag->dao_event, gnrc_rpl_pid); } else if (dodag->dao_ack_received == false) { gnrc_rpl_long_delay_dao(dodag); diff --git a/sys/net/gnrc/routing/rpl/gnrc_rpl_auto_init.c b/sys/net/gnrc/routing/rpl/gnrc_rpl_auto_init.c index 84de487cd9e6a615b2c10a41c311d0ca543c4963..f6f2ea4c67ea2c1496e8fc58b53eeb02400da9b0 100644 --- a/sys/net/gnrc/routing/rpl/gnrc_rpl_auto_init.c +++ b/sys/net/gnrc/routing/rpl/gnrc_rpl_auto_init.c @@ -1,5 +1,5 @@ /* - * Copyright (C) 2016 Cenk Gündoğan <mail@cgundogan.de> + * Copyright (C) 2016 Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> * * This file is subject to the terms and conditions of the GNU Lesser * General Public License v2.1. See the file LICENSE in the top level @@ -14,7 +14,7 @@ * @file * @brief Auto initialization for gnrc_rpl * - * @author Cenk Gündoğan <mail@cgundogan.de> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #ifdef MODULE_AUTO_INIT_GNRC_RPL diff --git a/sys/net/gnrc/routing/rpl/gnrc_rpl_control_messages.c b/sys/net/gnrc/routing/rpl/gnrc_rpl_control_messages.c index 0bee108ac34a2b18ef7efc2a29a7dfcd183f6759..1e454ecbe2df2f15c384cdd4969c7237402377e8 100644 --- a/sys/net/gnrc/routing/rpl/gnrc_rpl_control_messages.c +++ b/sys/net/gnrc/routing/rpl/gnrc_rpl_control_messages.c @@ -1,6 +1,7 @@ /* - * Copyright (C) 2013 - 2014 INRIA. - * Copyright (C) 2015 Cenk Gündoğan <cnkgndgn@gmail.com> + * Copyright (C) 2018 HAW Hamburg + * Copyright (C) 2015–2017 Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> + * Copyright (C) 2013–2014 INRIA. * * This file is subject to the terms and conditions of the GNU Lesser General * Public License v2.1. See the file LICENSE in the top level directory for more @@ -12,7 +13,7 @@ * * @file * - * @author Cenk Gündoğan <cnkgndgn@gmail.com> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #include "net/af.h" @@ -23,6 +24,7 @@ #include "net/gnrc/netif/internal.h" #include "net/gnrc.h" #include "net/eui64.h" +#include "gnrc_rpl_internal/globals.h" #ifdef MODULE_NETSTATS_RPL #include "gnrc_rpl_internal/netstats.h" @@ -687,7 +689,7 @@ void gnrc_rpl_recv_DIO(gnrc_rpl_dio_t *dio, kernel_pid_t iface, ipv6_addr_t *src /* sender of incoming DIO is not a parent of mine (anymore) and has an INFINITE rank and I have a rank != INFINITE_RANK */ - if (parent->state == 0) { + if (parent->state == GNRC_RPL_PARENT_UNUSED) { if ((byteorder_ntohs(dio->rank) == GNRC_RPL_INFINITE_RANK) && (dodag->my_rank != GNRC_RPL_INFINITE_RANK)) { trickle_reset_timer(&dodag->trickle); diff --git a/sys/net/gnrc/routing/rpl/gnrc_rpl_dodag.c b/sys/net/gnrc/routing/rpl/gnrc_rpl_dodag.c index 6a5ead9f2da33506b27e9bb59fd70def6462d2aa..6197a402727106d12dbf9c6d79c5f80d3206b4aa 100644 --- a/sys/net/gnrc/routing/rpl/gnrc_rpl_dodag.c +++ b/sys/net/gnrc/routing/rpl/gnrc_rpl_dodag.c @@ -1,6 +1,7 @@ /** - * Copyright (C) 2013, 2014 INRIA. - * Copyright (C) 2015 Cenk Gündoğan <cnkgndgn@gmail.com> + * Copyright (C) 2018 HAW Hamburg + * Copyright (C) 2015–2017 Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> + * Copyright (C) 2013–2014 INRIA. * * This file is subject to the terms and conditions of the GNU Lesser * General Public License v2.1. See the file LICENSE in the top level @@ -12,7 +13,7 @@ * * @file * @author Eric Engel <eric.engel@fu-berlin.de> - * @author Cenk Gündoğan <cnkgndgn@gmail.com> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #include <stdbool.h> @@ -21,6 +22,7 @@ #include "net/gnrc/netif/internal.h" #include "net/gnrc/rpl/dodag.h" #include "net/gnrc/rpl/structs.h" +#include "gnrc_rpl_internal/globals.h" #include "utlist.h" #include "net/gnrc/rpl.h" @@ -86,6 +88,7 @@ bool gnrc_rpl_instance_add(uint8_t instance_id, gnrc_rpl_instance_t **inst) (*inst)->max_rank_inc = GNRC_RPL_DEFAULT_MAX_RANK_INCREASE; (*inst)->min_hop_rank_inc = GNRC_RPL_DEFAULT_MIN_HOP_RANK_INCREASE; (*inst)->dodag.parents = NULL; + (*inst)->cleanup_event.msg.content.ptr = (*inst); return true; } @@ -150,6 +153,8 @@ bool gnrc_rpl_dodag_init(gnrc_rpl_instance_t *instance, ipv6_addr_t *dodag_id, k dodag->dao_counter = 0; dodag->instance = instance; dodag->iface = iface; + dodag->dao_event.msg.content.ptr = instance; + dodag->dao_event.msg.type = GNRC_RPL_MSG_TYPE_DODAG_DAO_TX; if ((netif != NULL) && !(netif->flags & GNRC_NETIF_FLAGS_IPV6_FORWARDING)) { gnrc_rpl_leaf_operation(dodag); @@ -198,8 +203,13 @@ bool gnrc_rpl_parent_add_by_addr(gnrc_rpl_dodag_t *dodag, ipv6_addr_t *addr, if (*parent != NULL) { (*parent)->dodag = dodag; LL_APPEND(dodag->parents, *parent); - (*parent)->state = 1; + (*parent)->state = GNRC_RPL_PARENT_ACTIVE; (*parent)->addr = *addr; + (*parent)->rank = GNRC_RPL_INFINITE_RANK; + evtimer_del((evtimer_t *)(&gnrc_rpl_evtimer), (evtimer_event_t *)(&(*parent)->timeout_event)); + ((evtimer_event_t *)(&(*parent)->timeout_event))->next = NULL; + (*parent)->timeout_event.msg.type = GNRC_RPL_MSG_TYPE_PARENT_TIMEOUT; + (*parent)->timeout_event.msg.content.ptr = (*parent); return true; } @@ -220,13 +230,13 @@ bool gnrc_rpl_parent_remove(gnrc_rpl_parent_t *parent) /* set the default route to the next parent for now */ if (parent->next) { - uint32_t now = xtimer_now_usec() / US_PER_SEC; gnrc_ipv6_nib_ft_add(NULL, 0, &parent->next->addr, dodag->iface, - (parent->next->lifetime - now)); + dodag->default_lifetime * dodag->lifetime_unit * MS_PER_SEC); } } LL_DELETE(dodag->parents, parent); + evtimer_del((evtimer_t *)(&gnrc_rpl_evtimer), (evtimer_event_t *)&parent->timeout_event); memset(parent, 0, sizeof(gnrc_rpl_parent_t)); return true; } @@ -245,15 +255,22 @@ void gnrc_rpl_local_repair(gnrc_rpl_dodag_t *dodag) if (dodag->my_rank != GNRC_RPL_INFINITE_RANK) { dodag->my_rank = GNRC_RPL_INFINITE_RANK; trickle_reset_timer(&dodag->trickle); - dodag->instance->cleanup = GNRC_RPL_CLEANUP_TIME; + evtimer_del((evtimer_t *)(&gnrc_rpl_evtimer), (evtimer_event_t *)&dodag->instance->cleanup_event); + ((evtimer_event_t *)&(dodag->instance->cleanup_event))->offset = GNRC_RPL_CLEANUP_TIME; + dodag->instance->cleanup_event.msg.type = GNRC_RPL_MSG_TYPE_INSTANCE_CLEANUP; + evtimer_add_msg(&gnrc_rpl_evtimer, &dodag->instance->cleanup_event, gnrc_rpl_pid); } } void gnrc_rpl_parent_update(gnrc_rpl_dodag_t *dodag, gnrc_rpl_parent_t *parent) { /* update Parent lifetime */ - if (parent != NULL) { - parent->lifetime = dodag->default_lifetime * dodag->lifetime_unit; + if ((parent != NULL) && (parent->state != GNRC_RPL_PARENT_UNUSED)) { + parent->state = GNRC_RPL_PARENT_ACTIVE; + evtimer_del((evtimer_t *)(&gnrc_rpl_evtimer), (evtimer_event_t *)&parent->timeout_event); + ((evtimer_event_t *)&(parent->timeout_event))->offset = dodag->default_lifetime * dodag->lifetime_unit * MS_PER_SEC; + parent->timeout_event.msg.type = GNRC_RPL_MSG_TYPE_PARENT_TIMEOUT; + evtimer_add_msg(&gnrc_rpl_evtimer, &parent->timeout_event, gnrc_rpl_pid); #ifdef MODULE_GNRC_RPL_P2P if (dodag->instance->mop != GNRC_RPL_P2P_MOP) { #endif diff --git a/sys/net/gnrc/routing/rpl/gnrc_rpl_internal/globals.h b/sys/net/gnrc/routing/rpl/gnrc_rpl_internal/globals.h new file mode 100644 index 0000000000000000000000000000000000000000..a6b66be4391f9edd5ee4103f0c3c083e0bd78754 --- /dev/null +++ b/sys/net/gnrc/routing/rpl/gnrc_rpl_internal/globals.h @@ -0,0 +1,85 @@ +/* + * Copyright (C) 2018 HAW Hamburg + * + * This file is subject to the terms and conditions of the GNU Lesser + * General Public License v2.1. See the file LICENSE in the top level + * directory for more details. + */ + +/** + * @ingroup net_gnrc_rpl + * @{ + * + * @file + * @brief Internal globals for RPL + * + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> + */ + +#ifndef GLOBALS_H +#define GLOBALS_H + +#include "evtimer.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @brief Event queue for msg events. + */ +extern evtimer_msg_t gnrc_rpl_evtimer; + +/** + * @defgroup gnrc_rpl_events RPL events + * Events for RPL. + * @{ + */ +/** + * @brief Message type for parent timeouts. + */ +#define GNRC_RPL_MSG_TYPE_PARENT_TIMEOUT (0x0904) +/** + * @brief Message type for instance cleanup. + */ +#define GNRC_RPL_MSG_TYPE_INSTANCE_CLEANUP (0x0905) +/** + * @brief Message type for DAO transmissions. + */ +#define GNRC_RPL_MSG_TYPE_DODAG_DAO_TX (0x0906) +/** @} */ + +/** + * @brief Interval in milliseconds to probe a parent with DIS messages. + */ +#define GNRC_RPL_PARENT_PROBE_INTERVAL (2 * MS_PER_SEC) + +/** + * @defgroup gnrc_rpl_parent_states Parent states + * State of a RPL parent + * @{ + */ +/** + * @brief Parent is unused. + */ +#define GNRC_RPL_PARENT_UNUSED (0) +/** + * @brief Parent is active. + */ +#define GNRC_RPL_PARENT_ACTIVE (1) +/** + * @brief Parent is stale. + */ +#define GNRC_RPL_PARENT_STALE (2) +/** + * @brief Parent has timed out. + */ +#define GNRC_RPL_PARENT_TIMEOUT (GNRC_RPL_PARENT_STALE + GNRC_RPL_PARENT_TIMEOUT_DIS_RETRIES) +/** @} */ + +#ifdef __cplusplus +} +#endif + +#endif /* GLOBALS_H */ +/** @} */ diff --git a/sys/net/gnrc/routing/rpl/gnrc_rpl_internal/netstats.h b/sys/net/gnrc/routing/rpl/gnrc_rpl_internal/netstats.h index fa66537da2f4e19440936068fd6237d3bf631bbd..37bc0cc6e7efee751368870dafdfcb3e91c2e5b7 100644 --- a/sys/net/gnrc/routing/rpl/gnrc_rpl_internal/netstats.h +++ b/sys/net/gnrc/routing/rpl/gnrc_rpl_internal/netstats.h @@ -1,5 +1,5 @@ /* - * Copyright (C) 2016 Cenk Gündoğan <mail@cgundogan.de> + * Copyright (C) 2016 Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> * * This file is subject to the terms and conditions of the GNU Lesser * General Public License v2.1. See the file LICENSE in the top level @@ -13,7 +13,7 @@ * @file * @brief RPL control message statistics functions * - * @author Cenk Gündoğan <mail@cgundogan.de> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #ifndef NETSTATS_H diff --git a/sys/net/gnrc/routing/rpl/gnrc_rpl_internal/validation.h b/sys/net/gnrc/routing/rpl/gnrc_rpl_internal/validation.h index 724dd754fdb2d8ffead0067dc921c312e8811e6a..e2f42f38bdb7a868d4ce73a3eb94290663d8a427 100644 --- a/sys/net/gnrc/routing/rpl/gnrc_rpl_internal/validation.h +++ b/sys/net/gnrc/routing/rpl/gnrc_rpl_internal/validation.h @@ -1,5 +1,5 @@ /* - * Copyright (C) 2016 Cenk Gündoğan <mail@cgundogan.de> + * Copyright (C) 2016 Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> * * This file is subject to the terms and conditions of the GNU Lesser * General Public License v2.1. See the file LICENSE in the top level @@ -13,7 +13,7 @@ * @file * @brief RPL control message validation functions * - * @author Cenk Gündoğan <mail@cgundogan.de> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #ifndef VALIDATION_H diff --git a/sys/net/gnrc/routing/rpl/gnrc_rpl_validation.c b/sys/net/gnrc/routing/rpl/gnrc_rpl_validation.c index 43ef51f10dcefd72ff007cb7d5434ceea7ac0a6d..5b042a4e434413990ca66a19ed62ce16a195e1c5 100644 --- a/sys/net/gnrc/routing/rpl/gnrc_rpl_validation.c +++ b/sys/net/gnrc/routing/rpl/gnrc_rpl_validation.c @@ -1,5 +1,5 @@ /* - * Copyright (C) 2016 Cenk Gündoğan <mail@cgundogan.de> + * Copyright (C) 2016 Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> * * This file is subject to the terms and conditions of the GNU Lesser General * Public License v2.1. See the file LICENSE in the top level directory for more @@ -11,7 +11,7 @@ * * @file * - * @author Cenk Gündoğan <mail@cgundogan.de> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #include "net/gnrc/icmpv6.h" diff --git a/sys/net/gnrc/routing/rpl/p2p/gnrc_rpl_p2p.c b/sys/net/gnrc/routing/rpl/p2p/gnrc_rpl_p2p.c index 02f82216020eb76749cd77a752888459d4e4e559..9d8eaca00d577a888d1162d7434a00a07f614aff 100644 --- a/sys/net/gnrc/routing/rpl/p2p/gnrc_rpl_p2p.c +++ b/sys/net/gnrc/routing/rpl/p2p/gnrc_rpl_p2p.c @@ -1,5 +1,5 @@ /* - * Copyright (C) 2016 Cenk Gündoğan <mail@cgundogan.de> + * Copyright (C) 2016 Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> * * This file is subject to the terms and conditions of the GNU Lesser * General Public License v2.1. See the file LICENSE in the top level @@ -11,7 +11,7 @@ * * @file * - * @author Cenk Gündoğan <mail@cgundogan.de> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #include "net/icmpv6.h" diff --git a/sys/net/gnrc/routing/rpl/p2p/gnrc_rpl_p2p_dodag.c b/sys/net/gnrc/routing/rpl/p2p/gnrc_rpl_p2p_dodag.c index 3d4b93f9b59aed360a3f29d8c6662c27b2b7493a..b0eb5e1e6b83b8ac08054ec8dd3b7399bca2d738 100644 --- a/sys/net/gnrc/routing/rpl/p2p/gnrc_rpl_p2p_dodag.c +++ b/sys/net/gnrc/routing/rpl/p2p/gnrc_rpl_p2p_dodag.c @@ -1,5 +1,5 @@ /** - * Copyright (C) 2016 Cenk Gündoğan <mail@cgundogan.de> + * Copyright (C) 2016 Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> * * This file is subject to the terms and conditions of the GNU Lesser * General Public License v2.1. See the file LICENSE in the top level @@ -10,7 +10,7 @@ * @{ * * @file - * @author Cenk Gündoğan <mail@cgundogan.de> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #include <string.h> diff --git a/sys/shell/commands/sc_gnrc_rpl.c b/sys/shell/commands/sc_gnrc_rpl.c index 7167b877d834a39d76b8d784683225d7dcc8d603..b16d533de5e6d2414b3ad21411109fff18358942 100644 --- a/sys/shell/commands/sc_gnrc_rpl.c +++ b/sys/shell/commands/sc_gnrc_rpl.c @@ -1,5 +1,6 @@ /* - * Copyright (C) 2015 Cenk Gündoğan <cnkgndgn@gmail.com> + * Copyright (C) 2018 HAW Hamburg + * Copyright (C) 2015–2017 Cenk Gündoğan <mail-github@cgundogan.de> * * This file is subject to the terms and conditions of the GNU Lesser General * Public License v2.1. See the file LICENSE in the top level directory for @@ -12,7 +13,7 @@ * * @file * - * @author Cenk Gündoğan <cnkgndgn@gmail.com> + * @author Cenk Gündoğan <cenk.guendogan@haw-hamburg.de> */ #include <string.h> @@ -255,7 +256,6 @@ int _gnrc_rpl_dodag_show(void) gnrc_rpl_dodag_t *dodag = NULL; char addr_str[IPV6_ADDR_MAX_STR_LEN]; - int8_t cleanup; uint64_t tc, xnow = xtimer_now_usec64(); for (uint8_t i = 0; i < GNRC_RPL_INSTANCES_NUMOF; ++i) { @@ -274,14 +274,12 @@ int _gnrc_rpl_dodag_show(void) | dodag->trickle.msg_timer.target) - xnow; tc = (int64_t) tc < 0 ? 0 : tc / US_PER_SEC; - cleanup = dodag->instance->cleanup < 0 ? 0 : dodag->instance->cleanup; - - printf("\tdodag [%s | R: %d | OP: %s | PIO: %s | CL: %ds | " + printf("\tdodag [%s | R: %d | OP: %s | PIO: %s | " "TR(I=[%d,%d], k=%d, c=%d, TC=%" PRIu32 "s)]\n", ipv6_addr_to_str(addr_str, &dodag->dodag_id, sizeof(addr_str)), dodag->my_rank, (dodag->node_status == GNRC_RPL_LEAF_NODE ? "Leaf" : "Router"), ((dodag->dio_opts & GNRC_RPL_REQ_DIO_OPT_PREFIX_INFO) ? "on" : "off"), - (int) cleanup, (1 << dodag->dio_min), dodag->dio_interval_doubl, dodag->trickle.k, + (1 << dodag->dio_min), dodag->dio_interval_doubl, dodag->trickle.k, dodag->trickle.c, (uint32_t) (tc & 0xFFFFFFFF)); #ifdef MODULE_GNRC_RPL_P2P @@ -296,9 +294,9 @@ int _gnrc_rpl_dodag_show(void) gnrc_rpl_parent_t *parent; LL_FOREACH(gnrc_rpl_instances[i].dodag.parents, parent) { - printf("\t\tparent [addr: %s | rank: %d | lifetime: %" PRIu32 "s]\n", + printf("\t\tparent [addr: %s | rank: %d]\n", ipv6_addr_to_str(addr_str, &parent->addr, sizeof(addr_str)), - parent->rank, parent->lifetime); + parent->rank); } } return 0;