sixlowpan_framer.c 9.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309
  1. /****************************************************************************
  2. * net/sixlowpan/sixlowpan_framer.c
  3. *
  4. * Copyright (C) 2017 Gregory Nutt. All rights reserved.
  5. * Author: Gregory Nutt <gnutt@nuttx.org>
  6. *
  7. * Redistribution and use in source and binary forms, with or without
  8. * modification, are permitted provided that the following conditions
  9. * are met:
  10. *
  11. * 1. Redistributions of source code must retain the above copyright
  12. * notice, this list of conditions and the following disclaimer.
  13. * 2. Redistributions in binary form must reproduce the above copyright
  14. * notice, this list of conditions and the following disclaimer in
  15. * the documentation and/or other materials provided with the
  16. * distribution.
  17. * 3. Neither the name NuttX nor the names of its contributors may be
  18. * used to endorse or promote products derived from this software
  19. * without specific prior written permission.
  20. *
  21. * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  22. * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  23. * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
  24. * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
  25. * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
  26. * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
  27. * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
  28. * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
  29. * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  30. * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
  31. * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
  32. * POSSIBILITY OF SUCH DAMAGE.
  33. *
  34. ****************************************************************************/
  35. /****************************************************************************
  36. * Included Files
  37. ****************************************************************************/
  38. #include <nuttx/config.h>
  39. #include <stdbool.h>
  40. #include <string.h>
  41. #include <assert.h>
  42. #include <errno.h>
  43. #include <debug.h>
  44. #include "nuttx/net/net.h"
  45. #include "nuttx/net/radiodev.h"
  46. #include "nuttx/wireless/ieee802154/ieee802154_mac.h"
  47. #include "sixlowpan/sixlowpan_internal.h"
  48. #ifdef CONFIG_NET_6LOWPAN
  49. /****************************************************************************
  50. * Public Functions
  51. ****************************************************************************/
  52. /****************************************************************************
  53. * Name: sixlowpan_anyaddrnull
  54. *
  55. * Description:
  56. * If the destination address is all zero in the MAC header buf, then it is
  57. * broadcast on the 802.15.4 network.
  58. *
  59. * Input Parameters:
  60. * addr - The address to check
  61. * addrlen - The length of the address in bytes
  62. *
  63. * Returned Value:
  64. * True if the address is all zero.
  65. *
  66. ****************************************************************************/
  67. static bool sixlowpan_anyaddrnull(FAR const uint8_t *addr, uint8_t addrlen)
  68. {
  69. while (addrlen-- > 0)
  70. {
  71. if (addr[addrlen] != 0x00)
  72. {
  73. return false;
  74. }
  75. }
  76. return true;
  77. }
  78. /****************************************************************************
  79. * Name: sixlowpan_saddrnull
  80. *
  81. * Description:
  82. * If the destination address is all zero in the MAC header buf, then it is
  83. * broadcast on the 802.15.4 network.
  84. *
  85. * Input Parameters:
  86. * eaddr - The short address to check
  87. *
  88. * Returned Value:
  89. * The address length associated with the address mode.
  90. *
  91. ****************************************************************************/
  92. static inline bool sixlowpan_saddrnull(FAR const uint8_t *saddr)
  93. {
  94. return sixlowpan_anyaddrnull(saddr, NET_6LOWPAN_SADDRSIZE);
  95. }
  96. /****************************************************************************
  97. * Name: sixlowpan_eaddrnull
  98. *
  99. * Description:
  100. * If the destination address is all zero in the MAC header buf, then it is
  101. * broadcast on the 802.15.4 network.
  102. *
  103. * Input Parameters:
  104. * eaddr - The extended address to check
  105. *
  106. * Returned Value:
  107. * The address length associated with the address mode.
  108. *
  109. ****************************************************************************/
  110. static inline bool sixlowpan_eaddrnull(FAR const uint8_t *eaddr)
  111. {
  112. return sixlowpan_anyaddrnull(eaddr, NET_6LOWPAN_EADDRSIZE);
  113. }
  114. /****************************************************************************
  115. * Public Functions
  116. ****************************************************************************/
  117. /****************************************************************************
  118. * Name: sixlowpan_meta_data
  119. *
  120. * Description:
  121. * Based on the collected attributes and addresses, construct the MAC meta
  122. * data structure that we need to interface with the IEEE802.15.4 MAC.
  123. *
  124. * Input Parameters:
  125. * radio - Radio network driver state instance.
  126. * pktmeta - Meta-data specific to the current outgoing frame
  127. * meta - Location to return the corresponding meta data.
  128. *
  129. * Returned Value:
  130. * Ok is returned on success; Othewise a negated errno value is returned.
  131. *
  132. * Assumptions:
  133. * Called with the network locked.
  134. *
  135. ****************************************************************************/
  136. #ifdef CONFIG_WIRELESS_IEEE802154
  137. int sixlowpan_meta_data(FAR struct radio_driver_s *radio,
  138. FAR const struct ieee802_txmetadata_s *pktmeta,
  139. FAR struct ieee802154_frame_meta_s *meta)
  140. {
  141. bool rcvrnull;
  142. /* Initialize all settings to all zero */
  143. memset(meta, 0, sizeof(struct ieee802154_frame_meta_s));
  144. /* Source address mode */
  145. meta->srcmode = pktmeta->sextended != 0 ?
  146. IEEE802154_ADDRMODE_EXTENDED :
  147. IEEE802154_ADDRMODE_SHORT;
  148. /* Check for a broadcast destination address (all zero) */
  149. if (pktmeta->dextended != 0)
  150. {
  151. /* Extended destination address mode */
  152. rcvrnull = sixlowpan_eaddrnull(pktmeta->dest.nm_addr);
  153. }
  154. else
  155. {
  156. /* Short destination address mode */
  157. rcvrnull = sixlowpan_saddrnull(pktmeta->dest.nm_addr);
  158. }
  159. if (!rcvrnull)
  160. {
  161. meta->flags.ackreq = TRUE;
  162. }
  163. /* Destination address */
  164. /* If the output address is NULL, then it is broadcast on the 802.15.4
  165. * network.
  166. */
  167. if (rcvrnull)
  168. {
  169. /* Broadcast requires short address mode. */
  170. meta->destaddr.mode = IEEE802154_ADDRMODE_SHORT;
  171. meta->destaddr.saddr[0] = 0xff;
  172. meta->destaddr.saddr[1] = 0xff;
  173. }
  174. else if (pktmeta->dextended != 0)
  175. {
  176. /* Extended destination address mode */
  177. meta->destaddr.mode = IEEE802154_ADDRMODE_EXTENDED;
  178. /* 802.15.4 layer expects address in Little-Endian byte order */
  179. meta->destaddr.eaddr[0] = pktmeta->dest.nm_addr[7];
  180. meta->destaddr.eaddr[1] = pktmeta->dest.nm_addr[6];
  181. meta->destaddr.eaddr[2] = pktmeta->dest.nm_addr[5];
  182. meta->destaddr.eaddr[3] = pktmeta->dest.nm_addr[4];
  183. meta->destaddr.eaddr[4] = pktmeta->dest.nm_addr[3];
  184. meta->destaddr.eaddr[5] = pktmeta->dest.nm_addr[2];
  185. meta->destaddr.eaddr[6] = pktmeta->dest.nm_addr[1];
  186. meta->destaddr.eaddr[7] = pktmeta->dest.nm_addr[0];
  187. }
  188. else
  189. {
  190. /* Short destination address mode */
  191. meta->destaddr.mode = IEEE802154_ADDRMODE_SHORT;
  192. /* 802.15.4 layer expects address in Little-Endian byte order */
  193. meta->destaddr.saddr[0] = pktmeta->dest.nm_addr[1];
  194. meta->destaddr.saddr[1] = pktmeta->dest.nm_addr[0];
  195. }
  196. /* 802.15.4 layer expects address in Little-Endian byte order */
  197. meta->destaddr.panid[0] = pktmeta->dpanid[1];
  198. meta->destaddr.panid[1] = pktmeta->dpanid[0];
  199. /* Handle associated with MSDU. Will increment once per packet, not
  200. * necesarily per frame: The same MSDU handle will be used for each
  201. * fragment of a disassembled packet.
  202. */
  203. meta->handle = radio->r_msdu_handle++;
  204. #ifdef CONFIG_IEEE802154_SECURITY
  205. # warning CONFIG_IEEE802154_SECURITY not yet supported
  206. #endif
  207. #ifdef CONFIG_IEEE802154_UWB
  208. # warning CONFIG_IEEE802154_UWB not yet supported
  209. #endif
  210. /* Ranging left zero */
  211. return OK;
  212. }
  213. #endif
  214. /****************************************************************************
  215. * Name: sixlowpan_frame_hdrlen
  216. *
  217. * Description:
  218. * This function is before the first frame has been sent in order to
  219. * determine what the size of the IEEE802.15.4 header will be. No frame
  220. * buffer is required to make this determination.
  221. *
  222. * Input Parameters:
  223. * radio - A reference IEEE802.15.4 MAC network device structure.
  224. * meta - Meta data that describes the MAC header
  225. *
  226. * Returned Value:
  227. * The frame header length is returnd on success; otherwise, a negated
  228. * errno value is return on failure.
  229. *
  230. ****************************************************************************/
  231. int sixlowpan_frame_hdrlen(FAR struct radio_driver_s *radio,
  232. FAR const void *meta)
  233. {
  234. return radio->r_get_mhrlen(radio, meta);
  235. }
  236. /****************************************************************************
  237. * Name: sixlowpan_frame_submit
  238. *
  239. * Description:
  240. * This function is called after eiether (1) the IEEE802.15.4 MAC driver
  241. * polls for TX data or (2) after the IEEE802.15.4 MAC driver provides a
  242. * new incoming frame and the network responds with an outgoing packet. It
  243. * submits any new outgoing frame to the MAC.
  244. *
  245. * Input Parameters:
  246. * radio - A reference to a radio network device instance.
  247. * meta - Meta data that describes the MAC header
  248. * frame - The IOB containing the frame to be submitted.
  249. *
  250. * Returned Value:
  251. * Zero (OK) is returned on success; otherwise, a negated errno value is
  252. * return on any failure.
  253. *
  254. ****************************************************************************/
  255. int sixlowpan_frame_submit(FAR struct radio_driver_s *radio,
  256. FAR const void *meta, FAR struct iob_s *frame)
  257. {
  258. return radio->r_req_data(radio, meta, frame);
  259. }
  260. #endif /* CONFIG_NET_6LOWPAN */