diff --git a/Makefile.dep b/Makefile.dep index 9b01c11117a1443d3d76a90abc273a295deaccd4..e0f0641169df1fb615f71c7685d888472b58d72e 100644 --- a/Makefile.dep +++ b/Makefile.dep @@ -245,11 +245,11 @@ ifneq (,$(filter gnrc_icmpv6,$(USEMODULE))) endif ifneq (,$(filter gnrc_rpl_srh,$(USEMODULE))) - USEMODULE += ipv6_ext_rh + USEMODULE += gnrc_ipv6_ext_rh endif -ifneq (,$(filter ipv6_ext_rh,$(USEMODULE))) - USEMODULE += ipv6_ext +ifneq (,$(filter gnrc_ipv6_ext_rh,$(USEMODULE))) + USEMODULE += gnrc_ipv6_ext endif ifneq (,$(filter gnrc_ipv6_ext,$(USEMODULE))) diff --git a/sys/Makefile b/sys/Makefile index bab6d947837d8e43f9d67dfab3059edd5fcc882e..ff28ad84c0409b6b37f5f6fb16525f1e5dbbf40f 100644 --- a/sys/Makefile +++ b/sys/Makefile @@ -43,12 +43,6 @@ endif ifneq (,$(filter ipv6_addr,$(USEMODULE))) DIRS += net/network_layer/ipv6/addr endif -ifneq (,$(filter ipv6_ext_rh,$(USEMODULE))) - DIRS += net/network_layer/ipv6/ext/rh -endif -ifneq (,$(filter ipv6_ext,$(USEMODULE))) - DIRS += net/network_layer/ipv6/ext -endif ifneq (,$(filter ipv6_hdr,$(USEMODULE))) DIRS += net/network_layer/ipv6/hdr endif diff --git a/sys/include/net/gnrc/ipv6/ext.h b/sys/include/net/gnrc/ipv6/ext.h index 84fdf17d83b93f838c49530eb38d09c9cf333924..e772e7f7eb41fa6759a2430c78aa43eb75a7827a 100644 --- a/sys/include/net/gnrc/ipv6/ext.h +++ b/sys/include/net/gnrc/ipv6/ext.h @@ -31,6 +31,10 @@ #include "net/gnrc/pkt.h" #include "net/ipv6/ext.h" +#ifdef MODULE_GNRC_IPV6_EXT_RH +#include "net/gnrc/ipv6/ext/rh.h" +#endif + #ifdef __cplusplus extern "C" { #endif diff --git a/sys/include/net/gnrc/ipv6/ext/rh.h b/sys/include/net/gnrc/ipv6/ext/rh.h new file mode 100644 index 0000000000000000000000000000000000000000..7a31355583617cadd3f22d28faa2077fea3c7322 --- /dev/null +++ b/sys/include/net/gnrc/ipv6/ext/rh.h @@ -0,0 +1,73 @@ +/* + * Copyright (C) 2018 Freie Universität Berlin + * + * 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. + */ + +/** + * @defgroup net_gnrc_ipv6_ext_rh Support for IPv6 routing header extension + * @ingroup net_gnrc_ipv6_ext + * @brief GNRC implementation of IPv6 routing header extension. + * @{ + * + * @file + * @brief GNRC routing extension header definitions. + * + * @author Martine Lenders <m.lenders@fu-berlin.de> + */ +#ifndef NET_GNRC_IPV6_EXT_RH_H +#define NET_GNRC_IPV6_EXT_RH_H + +#include "net/ipv6/hdr.h" + +#include "net/ipv6/ext/rh.h" + +#ifdef __cplusplus +extern "C" { +#endif + +enum { + /** + * @brief An error occurred during routing header processing + */ + GNRC_IPV6_EXT_RH_ERROR = 0, + /** + * @brief The routing header was successfully processed and this node + * is the destination (i.e. ipv6_ext_rh_t::seg_left == 0) + */ + GNRC_IPV6_EXT_RH_AT_DST, + /** + * @brief The routing header was successfully processed and the packet + * was forwarded to another node or should be forwarded to another + * node. + * + * When @ref gnrc_ipv6_ext_rh_process() returns this value, the packet was + * already forwarded to another node. Implementations for specific routing + * header types should leave the forwarding to the calling @ref + * gnrc_ipv6_ext_rh_process() and should return @ref + * GNRC_IPV6_EXT_RH_FORWARDED if they want the packet to be forwarded. They + * should however set ipv6_hdr_t::dst accordingly. + */ + GNRC_IPV6_EXT_RH_FORWARDED, +}; + +/** + * @brief Process the routing header of an IPv6 packet. + * + * @param[in, out] ipv6 An IPv6 packet. + * @param[in] ext A routing header of @p ipv6. + * + * @return @ref GNRC_IPV6_EXT_RH_AT_DST, on success + * @return @ref GNRC_IPV6_EXT_RH_FORWARDED, when @p pkt was forwarded + * @return @ref GNRC_IPV6_EXT_RH_ERROR, on error + */ +int gnrc_ipv6_ext_rh_process(ipv6_hdr_t *ipv6, ipv6_ext_rh_t *ext); + +#ifdef __cplusplus +} +#endif + +#endif /* NET_GNRC_IPV6_EXT_RH_H */ +/** @} */ diff --git a/sys/include/net/gnrc/rpl/srh.h b/sys/include/net/gnrc/rpl/srh.h index 5078198d4d0f9a4e4c911d847074869d3bae4ee8..d9938fc2e9c44049907ba5bee0e07a489536f1e6 100644 --- a/sys/include/net/gnrc/rpl/srh.h +++ b/sys/include/net/gnrc/rpl/srh.h @@ -60,9 +60,9 @@ typedef struct __attribute__((packed)) { * @param[in,out] ipv6 The IPv6 header of the incoming packet. * @param[in] rh A RPL source routing header. * - * @return EXT_RH_CODE_ERROR - * @return EXT_RH_CODE_FORWARD - * @return EXT_RH_CODE_OK + * @return @ref GNRC_IPV6_EXT_RH_AT_DST, on success + * @return @ref GNRC_IPV6_EXT_RH_FORWARDED, when @p pkt *should be* forwarded + * @return @ref GNRC_IPV6_EXT_RH_ERROR, on error */ int gnrc_rpl_srh_process(ipv6_hdr_t *ipv6, gnrc_rpl_srh_t *rh); diff --git a/sys/include/net/ipv6/ext/rh.h b/sys/include/net/ipv6/ext/rh.h index 39848d6c8c77d952e8079693e6ba2fb3d94bba86..882b57b392a12cf2fd5896e0d282a172956a63c4 100644 --- a/sys/include/net/ipv6/ext/rh.h +++ b/sys/include/net/ipv6/ext/rh.h @@ -1,5 +1,6 @@ /* - * Copyright (C) 2015 Martine Lenders <mlenders@inf.fu-berlin.de> + * Copyright (C) 2015 Cenk Gündoğan <cnkgndgn@gmail.com> + * Copyright (C) 2018 Freie Universität Berlin * * 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 @@ -9,13 +10,14 @@ /** * @defgroup net_ipv6_ext_rh IPv6 routing header extension * @ingroup net_ipv6_ext - * @brief Implementation of IPv6 routing header extension. + * @brief Definitions for IPv6 routing header extension. * @{ * * @file * @brief Routing extension header definitions. * - * @author Martine Lenders <mlenders@inf.fu-berlin.de> + * @author Cenk Gündoğan <cnkgndgn@gmail.com> + * @author Martine Lenders <m.lenders@fu-berlin.de> */ #ifndef NET_IPV6_EXT_RH_H #define NET_IPV6_EXT_RH_H @@ -30,17 +32,6 @@ extern "C" { #endif -/** - * @name Return codes for routing header processing - * @{ - */ -#define EXT_RH_CODE_ERROR (-1) -#define EXT_RH_CODE_FORWARD (0) -#define EXT_RH_CODE_OK (1) -/** - * @} - */ - /** * @brief IPv6 routing extension header. * @@ -55,18 +46,6 @@ typedef struct __attribute__((packed)) { uint8_t seg_left; /**< number of route segments remaining */ } ipv6_ext_rh_t; -/** - * @brief Process the routing header of an IPv6 packet. - * - * @param[in, out] ipv6 An IPv6 packet. - * @param[in] ext A routing header of @p ipv6. - * - * @return EXT_RH_CODE_ERROR - * @return EXT_RH_CODE_FORWARD - * @return EXT_RH_CODE_OK - */ -int ipv6_ext_rh_process(ipv6_hdr_t *ipv6, ipv6_ext_rh_t *ext); - #ifdef __cplusplus } #endif diff --git a/sys/net/gnrc/Makefile b/sys/net/gnrc/Makefile index 372b1e3b737729dfabe02585949b2d15f86ed02d..eeae57137e7641f85c9b3bf1acbd779c153ec220 100644 --- a/sys/net/gnrc/Makefile +++ b/sys/net/gnrc/Makefile @@ -13,6 +13,9 @@ endif ifneq (,$(filter gnrc_ipv6_ext,$(USEMODULE))) DIRS += network_layer/ipv6/ext endif +ifneq (,$(filter gnrc_ipv6_ext_rh,$(USEMODULE))) + DIRS += network_layer/ipv6/ext/rh +endif ifneq (,$(filter gnrc_ipv6_hdr,$(USEMODULE))) DIRS += network_layer/ipv6/hdr endif diff --git a/sys/net/gnrc/network_layer/ipv6/ext/gnrc_ipv6_ext.c b/sys/net/gnrc/network_layer/ipv6/ext/gnrc_ipv6_ext.c index 9458869bfc31cba95b5202abc1b437dad6816714..fadfb28b4ef503ae123b66f2e71979829dc44a85 100644 --- a/sys/net/gnrc/network_layer/ipv6/ext/gnrc_ipv6_ext.c +++ b/sys/net/gnrc/network_layer/ipv6/ext/gnrc_ipv6_ext.c @@ -18,30 +18,25 @@ #include "net/gnrc/netif.h" #include "net/gnrc/pktbuf.h" #include "net/gnrc/ipv6.h" +#include "net/gnrc/ipv6/ext/rh.h" #include "net/gnrc/ipv6/ext.h" #define ENABLE_DEBUG (0) #include "debug.h" -#ifdef MODULE_GNRC_RPL_SRH - -enum gnrc_ipv6_ext_demux_status { - GNRC_IPV6_EXT_OK, - GNRC_IPV6_EXT_FORWARDED, - GNRC_IPV6_EXT_ERROR, -}; - -static enum gnrc_ipv6_ext_demux_status _handle_rh(gnrc_pktsnip_t *current, gnrc_pktsnip_t *pkt) +#ifdef MODULE_GNRC_IPV6_EXT_RH +static int _handle_rh(gnrc_pktsnip_t *current, gnrc_pktsnip_t *pkt) { gnrc_pktsnip_t *ipv6; ipv6_ext_t *ext = (ipv6_ext_t *) current->data; size_t current_offset; ipv6_hdr_t *hdr; + int res; /* check seg_left early to avoid duplicating the packet */ if (((ipv6_ext_rh_t *)ext)->seg_left == 0) { - return GNRC_IPV6_EXT_OK; + return GNRC_IPV6_EXT_RH_AT_DST; } /* We cannot use `gnrc_pktbuf_start_write` since it duplicates only @@ -54,7 +49,7 @@ static enum gnrc_ipv6_ext_demux_status _handle_rh(gnrc_pktsnip_t *current, gnrc_ if ((ipv6 = gnrc_pktbuf_duplicate_upto(pkt, GNRC_NETTYPE_IPV6)) == NULL) { DEBUG("ipv6: could not get a copy of pkt\n"); gnrc_pktbuf_release(pkt); - return GNRC_IPV6_EXT_ERROR; + return GNRC_IPV6_EXT_RH_ERROR; } pkt = ipv6; hdr = ipv6->data; @@ -65,30 +60,29 @@ static enum gnrc_ipv6_ext_demux_status _handle_rh(gnrc_pktsnip_t *current, gnrc_ hdr = ipv6->data; } - switch (ipv6_ext_rh_process(hdr, (ipv6_ext_rh_t *)ext)) { - case EXT_RH_CODE_ERROR: + switch ((res = gnrc_ipv6_ext_rh_process(hdr, (ipv6_ext_rh_t *)ext))) { + case GNRC_IPV6_EXT_RH_ERROR: /* TODO: send ICMPv6 error codes */ gnrc_pktbuf_release(pkt); - return GNRC_IPV6_EXT_ERROR; + break; - case EXT_RH_CODE_FORWARD: + case GNRC_IPV6_EXT_RH_FORWARDED: /* forward packet */ if (!gnrc_netapi_dispatch_receive(GNRC_NETTYPE_IPV6, GNRC_NETREG_DEMUX_CTX_ALL, pkt)) { DEBUG("ipv6: could not dispatch packet to the ipv6 thread\n"); gnrc_pktbuf_release(pkt); } - return GNRC_IPV6_EXT_FORWARDED; + break; - case EXT_RH_CODE_OK: + case GNRC_IPV6_EXT_RH_AT_DST: /* this should not happen since we checked seg_left early */ gnrc_pktbuf_release(pkt); - return GNRC_IPV6_EXT_ERROR; + break; } - return GNRC_IPV6_EXT_OK; + return res; } - -#endif +#endif /* MODULE_GNRC_IPV6_EXT_RH */ /** * @brief marks IPv6 extension header if needed. @@ -183,7 +177,7 @@ void gnrc_ipv6_ext_demux(gnrc_netif_t *netif, switch (nh) { case PROTNUM_IPV6_EXT_RH: -#ifdef MODULE_GNRC_RPL_SRH +#ifdef MODULE_GNRC_IPV6_EXT_RH /* if current != pkt, size is already checked */ if (current == pkt && !_has_valid_size(pkt, nh)) { DEBUG("ipv6_ext: invalid size\n"); @@ -192,7 +186,7 @@ void gnrc_ipv6_ext_demux(gnrc_netif_t *netif, } switch (_handle_rh(current, pkt)) { - case GNRC_IPV6_EXT_OK: + case GNRC_IPV6_EXT_RH_AT_DST: /* We are the final destination. So proceeds like normal packet. */ nh = ext->nh; DEBUG("ipv6_ext: next header = %" PRIu8 "\n", nh); @@ -205,17 +199,17 @@ void gnrc_ipv6_ext_demux(gnrc_netif_t *netif, return; - case GNRC_IPV6_EXT_ERROR: + case GNRC_IPV6_EXT_RH_ERROR: /* already released by _handle_rh, so no release here */ return; - case GNRC_IPV6_EXT_FORWARDED: + case GNRC_IPV6_EXT_RH_FORWARDED: /* the packet is forwarded and released. finish processing */ return; } break; -#endif +#endif /* MODULE_GNRC_IPV6_EXT_RH */ case PROTNUM_IPV6_EXT_HOPOPT: case PROTNUM_IPV6_EXT_DST: diff --git a/sys/net/network_layer/ipv6/ext/Makefile b/sys/net/gnrc/network_layer/ipv6/ext/rh/Makefile similarity index 57% rename from sys/net/network_layer/ipv6/ext/Makefile rename to sys/net/gnrc/network_layer/ipv6/ext/rh/Makefile index 35b590050ef685c6451228a2953d7b75a056a29c..66206685832dc108cc75f95f678ad7d9a245cc18 100644 --- a/sys/net/network_layer/ipv6/ext/Makefile +++ b/sys/net/gnrc/network_layer/ipv6/ext/rh/Makefile @@ -1,3 +1,3 @@ -MODULE = ipv6_ext +MODULE = gnrc_ipv6_ext_rh include $(RIOTBASE)/Makefile.base diff --git a/sys/net/network_layer/ipv6/ext/rh/ipv6_ext_rh.c b/sys/net/gnrc/network_layer/ipv6/ext/rh/gnrc_ipv6_ext_rh.c similarity index 81% rename from sys/net/network_layer/ipv6/ext/rh/ipv6_ext_rh.c rename to sys/net/gnrc/network_layer/ipv6/ext/rh/gnrc_ipv6_ext_rh.c index 187a5c8056f4d2f044d4802cb6ab0c57994cfd6e..e00cf2d03fdf8b104b97b1d3fb6a0d2153f30d67 100644 --- a/sys/net/network_layer/ipv6/ext/rh/ipv6_ext_rh.c +++ b/sys/net/gnrc/network_layer/ipv6/ext/rh/gnrc_ipv6_ext_rh.c @@ -16,10 +16,10 @@ #include "net/protnum.h" #include "net/ipv6/ext.h" -#include "net/ipv6/ext/rh.h" +#include "net/gnrc/ipv6/ext/rh.h" #include "net/gnrc/rpl/srh.h" -int ipv6_ext_rh_process(ipv6_hdr_t *hdr, ipv6_ext_rh_t *ext) +int gnrc_ipv6_ext_rh_process(ipv6_hdr_t *hdr, ipv6_ext_rh_t *ext) { (void) hdr; @@ -32,7 +32,7 @@ int ipv6_ext_rh_process(ipv6_hdr_t *hdr, ipv6_ext_rh_t *ext) default: break; } - return EXT_RH_CODE_ERROR; + return GNRC_IPV6_EXT_RH_ERROR; } /** @} */ diff --git a/sys/net/gnrc/routing/rpl/srh/gnrc_rpl_srh.c b/sys/net/gnrc/routing/rpl/srh/gnrc_rpl_srh.c index c1e5deaa2607c7aa1b99fe6f17403f669a215f3c..753d5bf65e0b9255e0808e7a433c1f119d3b5d92 100644 --- a/sys/net/gnrc/routing/rpl/srh/gnrc_rpl_srh.c +++ b/sys/net/gnrc/routing/rpl/srh/gnrc_rpl_srh.c @@ -14,7 +14,7 @@ #include <string.h> #include "net/gnrc/netif/internal.h" -#include "net/ipv6/ext/rh.h" +#include "net/gnrc/ipv6/ext/rh.h" #include "net/gnrc/rpl/srh.h" #define ENABLE_DEBUG (0) @@ -29,7 +29,7 @@ static char addr_str[IPV6_ADDR_MAX_STR_LEN]; int gnrc_rpl_srh_process(ipv6_hdr_t *ipv6, gnrc_rpl_srh_t *rh) { if (rh->seg_left == 0) { - return EXT_RH_CODE_OK; + return GNRC_IPV6_EXT_RH_AT_DST; } uint8_t n = (((rh->len * 8) - GNRC_RPL_SRH_PADDING(rh->pad_resv) - @@ -45,7 +45,7 @@ int gnrc_rpl_srh_process(ipv6_hdr_t *ipv6, gnrc_rpl_srh_t *rh) if (rh->seg_left > n) { DEBUG("RPL SRH: number of segments left > number of addresses - discard\n"); /* TODO ICMP Parameter Problem - Code 0 */ - return EXT_RH_CODE_ERROR; + return GNRC_IPV6_EXT_RH_ERROR; } rh->seg_left--; @@ -58,7 +58,7 @@ int gnrc_rpl_srh_process(ipv6_hdr_t *ipv6, gnrc_rpl_srh_t *rh) if (ipv6_addr_is_multicast(&ipv6->dst) || ipv6_addr_is_multicast(&addr)) { DEBUG("RPL SRH: found a multicast address - discard\n"); /* TODO discard the packet */ - return EXT_RH_CODE_ERROR; + return GNRC_IPV6_EXT_RH_ERROR; } /* check if multiple addresses of my interface exist */ @@ -75,7 +75,7 @@ int gnrc_rpl_srh_process(ipv6_hdr_t *ipv6, gnrc_rpl_srh_t *rh) if (found && ((k - found_pos) > 1)) { DEBUG("RPL SRH: found multiple addresses that belong to me - discard\n"); /* TODO send an ICMP Parameter Problem (Code 0) and discard the packet */ - return EXT_RH_CODE_ERROR; + return GNRC_IPV6_EXT_RH_ERROR; } found_pos = k; found = true; @@ -89,7 +89,7 @@ int gnrc_rpl_srh_process(ipv6_hdr_t *ipv6, gnrc_rpl_srh_t *rh) ipv6->dst = addr; - return EXT_RH_CODE_FORWARD; + return GNRC_IPV6_EXT_RH_FORWARDED; } /** @} */ diff --git a/sys/net/network_layer/ipv6/ext/rh/Makefile b/sys/net/network_layer/ipv6/ext/rh/Makefile deleted file mode 100644 index aeefa0b6a9278836ced4411f513a81eaf78bd0a2..0000000000000000000000000000000000000000 --- a/sys/net/network_layer/ipv6/ext/rh/Makefile +++ /dev/null @@ -1,3 +0,0 @@ -MODULE = ipv6_ext_rh - -include $(RIOTBASE)/Makefile.base diff --git a/tests/unittests/tests-rpl_srh/tests-rpl_srh.c b/tests/unittests/tests-rpl_srh/tests-rpl_srh.c index 5bc75a28c16334fdbec696f09c554b476f9202df..8c7f1a2986530c70d6a1357a7c95fd177d2d2cb0 100644 --- a/tests/unittests/tests-rpl_srh/tests-rpl_srh.c +++ b/tests/unittests/tests-rpl_srh/tests-rpl_srh.c @@ -19,6 +19,7 @@ #include "net/ipv6/ext.h" #include "net/ipv6/hdr.h" #include "net/gnrc/rpl/srh.h" +#include "net/gnrc/ipv6/ext/rh.h" #include "unittests-constants.h" #include "tests-rpl_srh.h" @@ -61,13 +62,13 @@ static void test_rpl_srh_nexthop_no_prefix_elided(void) /* first hop */ res = gnrc_rpl_srh_process(&hdr, srh); - TEST_ASSERT_EQUAL_INT(res, EXT_RH_CODE_FORWARD); + TEST_ASSERT_EQUAL_INT(res, GNRC_IPV6_EXT_RH_FORWARDED); TEST_ASSERT_EQUAL_INT(SRH_SEG_LEFT - 1, srh->seg_left); TEST_ASSERT(ipv6_addr_equal(&hdr.dst, &expected1)); /* second hop */ res = gnrc_rpl_srh_process(&hdr, srh); - TEST_ASSERT_EQUAL_INT(res, EXT_RH_CODE_FORWARD); + TEST_ASSERT_EQUAL_INT(res, GNRC_IPV6_EXT_RH_FORWARDED); TEST_ASSERT_EQUAL_INT(SRH_SEG_LEFT - 2, srh->seg_left); TEST_ASSERT(ipv6_addr_equal(&hdr.dst, &expected2)); } @@ -94,13 +95,13 @@ static void test_rpl_srh_nexthop_prefix_elided(void) /* first hop */ res = gnrc_rpl_srh_process(&hdr, srh); - TEST_ASSERT_EQUAL_INT(res, EXT_RH_CODE_FORWARD); + TEST_ASSERT_EQUAL_INT(res, GNRC_IPV6_EXT_RH_FORWARDED); TEST_ASSERT_EQUAL_INT(SRH_SEG_LEFT - 1, srh->seg_left); TEST_ASSERT(ipv6_addr_equal(&hdr.dst, &expected1)); /* second hop */ res = gnrc_rpl_srh_process(&hdr, srh); - TEST_ASSERT_EQUAL_INT(res, EXT_RH_CODE_FORWARD); + TEST_ASSERT_EQUAL_INT(res, GNRC_IPV6_EXT_RH_FORWARDED); TEST_ASSERT_EQUAL_INT(SRH_SEG_LEFT - 2, srh->seg_left); TEST_ASSERT(ipv6_addr_equal(&hdr.dst, &expected2)); }