From fb5bbca1d94b775bc1b75838ce727d9b57750d7d Mon Sep 17 00:00:00 2001 From: goldsimon Date: Mon, 26 Feb 2018 20:38:41 +0100 Subject: [PATCH] lowpan6.c: move IEEE 802.15.4 definitions to their own header file This is mainly a preparation to merge the two 6LoWPAN netifs --- src/include/netif/ieee802154.h | 113 +++++++++++++++++++++++++++++++++ src/netif/lowpan6.c | 25 +++++--- 2 files changed, 130 insertions(+), 8 deletions(-) create mode 100644 src/include/netif/ieee802154.h diff --git a/src/include/netif/ieee802154.h b/src/include/netif/ieee802154.h new file mode 100644 index 00000000..87d19063 --- /dev/null +++ b/src/include/netif/ieee802154.h @@ -0,0 +1,113 @@ +/** + * @file + * Definitions for IEEE 802.15.4 MAC frames + */ + +/* + * Copyright (c) 2018 Simon Goldschmidt. + * 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. The name of the author may not be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``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 AUTHOR 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. + * + * This file is part of the lwIP TCP/IP stack. + * + * Author: Simon Goldschmidt + * + */ +#ifndef LWIP_HDR_NETIF_IEEE802154_H +#define LWIP_HDR_NETIF_IEEE802154_H + +#include "lwip/opt.h" + +/** Helper define for a MAC address, which can be encoded as 0, 2 or 8 bytes */ +struct ieee_802154_addr { + /* encoded length of the address */ + u8_t addr_len; + /* address bytes */ + u8_t addr[8]; +}; + +#ifdef PACK_STRUCT_USE_INCLUDES +# include "arch/bpstruct.h" +#endif +PACK_STRUCT_BEGIN +/** General MAC frame format + * This shows the full featured header, mainly for documentation. + * Some fields are omitted or shortened to achieve frame compression. + */ +struct ieee_802154_hdr { + /** See IEEE_802154_FC_* defines */ + PACK_STRUCT_FIELD(u16_t frame_control); + /** Sequence number is omitted if IEEE_802154_FC_SEQNO_SUPPR is set in frame_control */ + PACK_STRUCT_FLD_8(u8_t sequence_number); + /** Destination PAN ID is omitted if Destination Addressing Mode is 0 */ + PACK_STRUCT_FIELD(u16_t destination_pan_id); + /** Destination Address is omitted if Destination Addressing Mode is 0 */ + PACK_STRUCT_FLD_8(u8_t destination_address[8]); + /** Source PAN ID is omitted if Source Addressing Mode is 0 + or if IEEE_802154_FC_PANID_COMPR is set in frame control*/ + PACK_STRUCT_FIELD(u16_t source_pan_id); + /** Source Address is omitted if Source Addressing Mode is 0 */ + PACK_STRUCT_FLD_8(u8_t source_address[8]); + /* The rest is variable */ +} PACK_STRUCT_STRUCT; +PACK_STRUCT_END +#ifdef PACK_STRUCT_USE_INCLUDES +# include "arch/epstruct.h" +#endif + +/* Addressing modes (2 bits) */ +#define IEEE_802154_ADDR_MODE_NO_ADDR 0x00 /* PAN ID and address fields are not present */ +#define IEEE_802154_ADDR_MODE_RESERVED 0x01 /* Reserved */ +#define IEEE_802154_ADDR_MODE_SHORT 0x02 /* Address field contains a short address (16 bit) */ +#define IEEE_802154_ADDR_MODE_EXT 0x03 /* Address field contains an extended address (64 bit) */ + +/* IEEE 802.15.4 Frame Control definitions (2 bytes; see IEEE 802.15.4-2015 ch. 7.2.1) */ +#define IEEE_802154_FC_FT_MASK 0x0007 /* bits 0..2: Frame Type */ +#define IEEE_802154_FC_FT_BEACON 0x00 +#define IEEE_802154_FC_FT_DATA 0x01 +#define IEEE_802154_FC_FT_ACK 0x02 +#define IEEE_802154_FC_FT_MAC_CMD 0x03 +#define IEEE_802154_FC_FT_RESERVED 0x04 +#define IEEE_802154_FC_FT_MULTIPURPOSE 0x05 +#define IEEE_802154_FC_FT_FRAG 0x06 +#define IEEE_802154_FC_FT_EXT 0x07 +#define IEEE_802154_FC_SEC_EN 0x0008 /* bit 3: Security Enabled */ +#define IEEE_802154_FC_FRAME_PEND 0x1000 /* bit 4: Frame Pending */ +#define IEEE_802154_FC_ACK_REQ 0x2000 /* bit 5: AR (ACK required) */ +#define IEEE_802154_FC_PANID_COMPR 0x4000 /* bit 6: PAN ID Compression (src and dst are equal, src PAN ID omitted) */ +#define IEEE_802154_FC_RESERVED 0x8000 +#define IEEE_802154_FC_SEQNO_SUPPR 0x0100 /* bit 8: Sequence Number Suppression */ +#define IEEE_802154_FC_IE_PRESENT 0x0200 /* bit 9: IE Present */ +#define IEEE_802154_FC_DST_ADDR_MODE_MASK 0x0c00 /* bits 10..11: Destination Addressing Mode */ +#define IEEE_802154_FC_DST_ADDR_MODE_NO_ADDR (IEEE_802154_ADDR_MODE_NO_ADDR << 10) +#define IEEE_802154_FC_DST_ADDR_MODE_SHORT (IEEE_802154_ADDR_MODE_SHORT << 10) +#define IEEE_802154_FC_DST_ADDR_MODE_EXT (IEEE_802154_ADDR_MODE_EXT << 10) +#define IEEE_802154_FC_FRAME_VERSION_MASK 0x3000 /* bits 12..13: Frame Version */ +#define IEEE_802154_FC_FRAME_VERSION_GET(x) (((x) & IEEE_802154_FC_FRAME_VERSION_MASK) >> 12) +#define IEEE_802154_FC_SRC_ADDR_MODE_MASK 0xc000 /* bits 14..15: Source Addressing Mode */ +#define IEEE_802154_FC_SRC_ADDR_MODE_SHORT (IEEE_802154_ADDR_MODE_SHORT << 14) +#define IEEE_802154_FC_SRC_ADDR_MODE_EXT (IEEE_802154_ADDR_MODE_EXT << 14) + + +#endif /* LWIP_HDR_NETIF_IEEE802154_H */ diff --git a/src/netif/lowpan6.c b/src/netif/lowpan6.c index da6880b5..e04c68d7 100644 --- a/src/netif/lowpan6.c +++ b/src/netif/lowpan6.c @@ -61,15 +61,12 @@ #include "lwip/udp.h" #include "lwip/tcpip.h" #include "lwip/snmp.h" +#include "netif/ieee802154.h" #include -struct ieee_802154_addr { - u8_t addr_len; - u8_t addr[8]; -}; - -/** This is a helper struct. +/** This is a helper struct for reassembly of fragments + * (IEEE 802.15.4 limits to 127 bytes) */ struct lowpan6_reass_helper { struct pbuf *pbuf; @@ -1017,6 +1014,7 @@ lowpan6_input(struct pbuf *p, struct netif *netif) { u8_t *puc; s8_t i; + u16_t frame_control, addr_mode; struct ieee_802154_addr src, dest; u16_t datagram_size, datagram_offset, datagram_tag; struct lowpan6_reass_helper *lrh, *lrh_temp; @@ -1025,15 +1023,21 @@ lowpan6_input(struct pbuf *p, struct netif *netif) /* Analyze header. @todo validate. */ puc = (u8_t *)p->payload; + frame_control = puc[0] | (puc[1] << 8); datagram_offset = 5; - if ((puc[1] & 0x0c) == 0x0c) { + addr_mode = frame_control & IEEE_802154_FC_DST_ADDR_MODE_MASK; + if (addr_mode == IEEE_802154_FC_DST_ADDR_MODE_EXT) { + /* extended address (64 bit) */ dest.addr_len = 8; + /* reverse memcpy: */ for (i = 0; i < 8; i++) { dest.addr[i] = puc[datagram_offset + 7 - i]; } datagram_offset += 8; } else { + /* short address (16 bit) */ dest.addr_len = 2; + /* reverse memcpy: */ dest.addr[0] = puc[datagram_offset + 1]; dest.addr[1] = puc[datagram_offset]; datagram_offset += 2; @@ -1041,14 +1045,19 @@ lowpan6_input(struct pbuf *p, struct netif *netif) datagram_offset += 2; /* skip PAN ID. */ - if ((puc[1] & 0xc0) == 0xc0) { + addr_mode = frame_control & IEEE_802154_FC_SRC_ADDR_MODE_MASK; + if (addr_mode == IEEE_802154_FC_SRC_ADDR_MODE_EXT) { + /* extended address (64 bit) */ src.addr_len = 8; + /* reverse memcpy: */ for (i = 0; i < 8; i++) { src.addr[i] = puc[datagram_offset + 7 - i]; } datagram_offset += 8; } else { + /* short address (16 bit) */ src.addr_len = 2; + /* reverse memcpy: */ src.addr[0] = puc[datagram_offset + 1]; src.addr[1] = puc[datagram_offset]; datagram_offset += 2;