6loWPAN: Add an IOCTL to set the IEEE802.15.4 PAN ID

This commit is contained in:
Gregory Nutt
2017-04-19 18:06:43 -06:00
parent 6a2c43b0c1
commit 9281cd558e
5 changed files with 146 additions and 36 deletions
+6
View File
@@ -233,6 +233,12 @@
#define _MTDIOCVALID(c) (_IOC_TYPE(c)==_MTDIOCBASE) #define _MTDIOCVALID(c) (_IOC_TYPE(c)==_MTDIOCBASE)
#define _MTDIOC(nr) _IOC(_MTDIOCBASE,nr) #define _MTDIOC(nr) _IOC(_MTDIOCBASE,nr)
/* Socket IOCTLs ************************************************************/
/* See include/nuttx/net/ioctl.h */
#define _SIOCVALID(c) (_IOC_TYPE(c)==_SIOCBASE)
#define _SIOC(nr) _IOC(_SIOCBASE,nr)
/* NuttX ARP driver ioctl definitions (see netinet/arp.h) *******************/ /* NuttX ARP driver ioctl definitions (see netinet/arp.h) *******************/
#define _ARPIOCVALID(c) (_IOC_TYPE(c)==_ARPIOCBASE) #define _ARPIOCVALID(c) (_IOC_TYPE(c)==_ARPIOCBASE)
-3
View File
@@ -51,9 +51,6 @@
* masks, and hardware address, and a few others * masks, and hardware address, and a few others
*/ */
#define _SIOCVALID(c) (_IOC_TYPE(c)==_SIOCBASE)
#define _SIOC(nr) _IOC(_SIOCBASE,nr)
/* IPv4 interface control operations */ /* IPv4 interface control operations */
#define SIOCGIFADDR _SIOC(0x0001) /* Get IP address */ #define SIOCGIFADDR _SIOC(0x0001) /* Get IP address */
+59 -12
View File
@@ -37,8 +37,8 @@
* (when applicable). * (when applicable).
*/ */
#ifndef __INCLUDE_NUTTX_WIRELESS_H #ifndef __INCLUDE_NUTTX_WIRELESS_WIRELESS_H
#define __INCLUDE_NUTTX_WIRELESS_H #define __INCLUDE_NUTTX_WIRELESS_WIRELESS_H
/************************************************************************************ /************************************************************************************
* Included Files * Included Files
@@ -63,6 +63,7 @@
* interface. * interface.
*/ */
/* IEEE802.11 */
/* Wireless identification */ /* Wireless identification */
#define SIOCSIWCOMMIT _WLIOC(0x0001) /* Commit pending changes to driver */ #define SIOCSIWCOMMIT _WLIOC(0x0001) /* Commit pending changes to driver */
@@ -153,8 +154,24 @@
#define SIOCSIWPMKSA _WLIOC(0x0032) /* PMKSA cache operation */ #define SIOCSIWPMKSA _WLIOC(0x0032) /* PMKSA cache operation */
#define WL_FIRSTCHAR 0x0033 /* IEEE802.15.4 6loWPAN
#define WL_NNETCMDS 0x0032 *
* IEEE802.15.4 IOCTLs may be directed at one of three layers:
*
* 1. To the 6loWPAN network layer, as documented here,
* 2. To the IEEE802.15.4 MAC layer, as documented in,
* include/nuttx/wireless/ieee802154/ioeee802154_mac.h, or to
* 3. To the IEEE802.15.4 radio device layer, as documented in,
* include/nuttx/wireless/ieee802154/ioeee802154_radio.h.
*
* SIOCSWPANID - Join the specified PAN ID
*/
#define SIOCSWPANID _WLIOC(0x0033) /* Join PAN ID */
#define SIOCGWPANID _WLIOC(0x0034) /* Return PAN ID */
#define WL_FIRSTCHAR 0x0035
#define WL_NNETCMDS 0x0034
/* Character Driver IOCTL commands *************************************************/ /* Character Driver IOCTL commands *************************************************/
/* Non-compatible, NuttX only IOCTL definitions for use with low-level wireless /* Non-compatible, NuttX only IOCTL definitions for use with low-level wireless
@@ -162,23 +179,23 @@
* requires a file descriptor created by the open() interface. * requires a file descriptor created by the open() interface.
*/ */
#define WLIOC_SETRADIOFREQ _WLIOC(0x0033) /* arg: Pointer to uint32_t, frequency #define WLIOC_SETRADIOFREQ _WLIOC(0x0035) /* arg: Pointer to uint32_t, frequency
* value (in Mhz) */ * value (in Mhz) */
#define WLIOC_GETRADIOFREQ _WLIOC(0x0034) /* arg: Pointer to uint32_t, frequency #define WLIOC_GETRADIOFREQ _WLIOC(0x0036) /* arg: Pointer to uint32_t, frequency
* value (in Mhz) */ * value (in Mhz) */
#define WLIOC_SETADDR _WLIOC(0x0035) /* arg: Pointer to address value, format #define WLIOC_SETADDR _WLIOC(0x0037) /* arg: Pointer to address value, format
* of the address is driver specific */ * of the address is driver specific */
#define WLIOC_GETADDR _WLIOC(0x0036) /* arg: Pointer to address value, format #define WLIOC_GETADDR _WLIOC(0x0038) /* arg: Pointer to address value, format
* of the address is driver specific */ * of the address is driver specific */
#define WLIOC_SETTXPOWER _WLIOC(0x0037) /* arg: Pointer to int32_t, output power #define WLIOC_SETTXPOWER _WLIOC(0x0039) /* arg: Pointer to int32_t, output power
* (in dBm) */ * (in dBm) */
#define WLIOC_GETTXPOWER _WLIOC(0x0038) /* arg: Pointer to int32_t, output power #define WLIOC_GETTXPOWER _WLIOC(0x003a) /* arg: Pointer to int32_t, output power
* (in dBm) */ * (in dBm) */
/* Device-specific IOCTL commands **************************************************/ /* Device-specific IOCTL commands **************************************************/
#define WL_FIRST 0x0001 /* First common command */ #define WL_FIRST 0x0001 /* First common command */
#define WL_NCMDS 0x0038 /* Number of common commands */ #define WL_NCMDS 0x003a /* Number of common commands */
/* User defined ioctl commands are also supported. These will be forwarded /* User defined ioctl commands are also supported. These will be forwarded
* by the upper-half QE driver to the lower-half QE driver via the ioctl() * by the upper-half QE driver to the lower-half QE driver via the ioctl()
@@ -355,5 +372,35 @@ struct iw_event
union iwreq_data u; /* Fixed IOCTL payload */ union iwreq_data u; /* Fixed IOCTL payload */
}; };
/* 6loWPAN */
/* This structure is used with the SIOCSWPANID IOCTL command to select the
* PAN ID to join.
*/
struct sixlowpan_panid_s
{
uint16_t panid; /* The PAN ID to join */
};
/* This union defines the data payload of an 6loWPAN or SIOCGWPANID ioctl
* command and is used in struct sixlowpan_req_s below.
*/
union sixlowpan_data
{
struct sixlowpan_panid_s panid; /* PAN ID to join */
};
/* This is the structure used to exchange data in wireless IOCTLs. This
* structure is the same as 'struct ifreq', but defined for use with
* 6loWPAN IOCTLs.
*/
struct sixlowpan_req_s
{
char ifr_name[IFNAMSIZ]; /* Interface name, e.g. "wpan0" */
union sixlowpan_data u; /* Data payload */
};
#endif /* CONFIG_DRIVERS_WIRELESS */ #endif /* CONFIG_DRIVERS_WIRELESS */
#endif /* __INCLUDE_NUTTX_WIRELESS_H */ #endif /* __INCLUDE_NUTTX_WIRELESS_WIRELESS_H */
+79 -19
View File
@@ -61,6 +61,7 @@
#ifdef CONFIG_NET_6LOWPAN #ifdef CONFIG_NET_6LOWPAN
# include <nuttx/net/sixlowpan.h> # include <nuttx/net/sixlowpan.h>
# include <nuttx/wireless/wireless.h>
#endif #endif
#ifdef CONFIG_NET_IGMP #ifdef CONFIG_NET_IGMP
@@ -321,32 +322,73 @@ static void ioctl_set_ipv6addr(FAR net_ipv6addr_t outaddr,
#endif #endif
/**************************************************************************** /****************************************************************************
* Name: netdev_wifr_dev * Name: netdev_sixlowpan_ioctl
* *
* Description: * Description:
* Verify the struct iwreq and get the Wireless device. * Perform 6loWPAN network device specific operations.
* *
* Parameters: * Parameters:
* req - The argument of the ioctl cmd * psock Socket structure
* dev Ethernet driver device structure
* cmd The ioctl command
* req The argument of the ioctl cmd
* *
* Return: * Return:
* A pointer to the driver structure on success; NULL on failure. * >=0 on success (positive non-zero values are cmd-specific)
* Negated errno returned on failure.
* *
****************************************************************************/ ****************************************************************************/
#if defined(CONFIG_NETDEV_IOCTL) && defined(CONFIG_NETDEV_WIRELESS_IOCTL) #if defined(CONFIG_NETDEV_IOCTL) && defined(CONFIG_NET_6LOWPAN)
static FAR struct net_driver_s *netdev_wifr_dev(FAR struct iwreq *req) static int netdev_sixlowpan_ioctl(FAR struct socket *psock, int cmd,
FAR struct sixlowpan_req_s *req)
{ {
if (req != NULL) FAR struct ieee802154_driver_s *ieee;
{ int ret = -ENOTTY;
/* Find the network device associated with the device name
* in the request data.
*/
return netdev_findbyname(req->ifrn_name); /* Verify that this is a valid wireless network IOCTL command */
if (_WLIOCVALID(cmd) && (unsigned)_IOC_NR(cmd) <= WL_NNETCMDS)
{
switch (cmd)
{
case SIOCSWPANID: /* Join PAN ID */
{
ieee = (FAR struct ieee802154_driver_s *)netdev_findbyname(req->ifr_name);
if (ieee == NULL)
{
ret = -ENODEV;
}
else
{
ieee->i_panid = req->u.panid.panid;
ret = OK;
}
}
break;
case SIOCGWPANID: /* Return PAN ID */
{
ieee = (FAR struct ieee802154_driver_s *)netdev_findbyname(req->ifr_name);
if (ieee == NULL)
{
ret = -ENODEV;
}
else
{
req->u.panid.panid = ieee->i_panid;
ret = OK;
}
}
break;
default:
return -ENOTTY;
}
} }
return NULL; return ret;
} }
#endif #endif
@@ -381,8 +423,8 @@ static int netdev_wifr_ioctl(FAR struct socket *psock, int cmd,
{ {
/* Get the wireless device associated with the IOCTL command */ /* Get the wireless device associated with the IOCTL command */
dev = netdev_wifr_dev(req); dev = netdev_findbyname(req->ifrn_name);
if (dev) if (dev != NULL)
{ {
/* Just forward the IOCTL to the wireless driver */ /* Just forward the IOCTL to the wireless driver */
@@ -1209,7 +1251,11 @@ int psock_ioctl(FAR struct socket *psock, int cmd, unsigned long arg)
* non-NULL. * non-NULL.
*/ */
#ifdef CONFIG_DRIVERS_WIRELESS
if (!_SIOCVALID(cmd) && !_WLIOCVALID(cmd))
#else
if (!_SIOCVALID(cmd)) if (!_SIOCVALID(cmd))
#endif
{ {
ret = -ENOTTY; ret = -ENOTTY;
goto errout; goto errout;
@@ -1227,13 +1273,27 @@ int psock_ioctl(FAR struct socket *psock, int cmd, unsigned long arg)
ret = netdev_ifr_ioctl(psock, cmd, (FAR struct ifreq *)((uintptr_t)arg)); ret = netdev_ifr_ioctl(psock, cmd, (FAR struct ifreq *)((uintptr_t)arg));
#if defined(CONFIG_NETDEV_IOCTL) && defined(CONFIG_NETDEV_WIRELESS_IOCTL) #if defined(CONFIG_NETDEV_IOCTL) && defined(CONFIG_NET_6LOWPAN)
/* Check a wireless network command */ /* Check for a 6loWPAN network command */
if (ret == -ENOTTY) if (ret == -ENOTTY)
{ {
ret = netdev_wifr_ioctl(psock, cmd, FAR struct sixlowpan_req_s *slpreq;
(FAR struct iwreq *)((uintptr_t)arg));
slpreq = (FAR struct sixlowpan_req_s *)((uintptr_t)arg);
ret = netdev_sixlowpan_ioctl(psock, cmd, slpreq);
}
#endif
#if defined(CONFIG_NETDEV_IOCTL) && defined(CONFIG_NETDEV_WIRELESS_IOCTL)
/* Check for a wireless network command */
if (ret == -ENOTTY)
{
FAR struct iwreq *wifrreq;
wifrreq = (FAR struct sixlowpan_req_s *)((uintptr_t)arg);
ret = netdev_wifr_ioctl(psock, cmd, wifrreq);
} }
#endif #endif
+2 -2
View File
@@ -47,7 +47,7 @@ The length of the fragment header length is four bytes for the first header
(FRAG1) and five bytes for all subsequent headers (FRAGN). For example, (FRAG1) and five bytes for all subsequent headers (FRAGN). For example,
this is a HC1 compressed first frame of a packet this is a HC1 compressed first frame of a packet
41 88 01 0000 3412 cdab ### 9-byte MAC header 41 88 01 cefa 3412 cdab ### 9-byte MAC header
c50e 000b ### 4-byte FRAG1 header c50e 000b ### 4-byte FRAG1 header
42 ### SIXLOWPAN_DISPATCH_HC1 42 ### SIXLOWPAN_DISPATCH_HC1
fb ### RIME_HC1_HC_UDP_HC1_ENCODING fb ### RIME_HC1_HC_UDP_HC1_ENCODING
@@ -64,7 +64,7 @@ this is a HC1 compressed first frame of a packet
This is the second frame of the same transfer: This is the second frame of the same transfer:
41 88 01 0000 3412 cdab ### 9-byte MAC header 41 88 01 cefa 3412 cdab ### 9-byte MAC header
e50e 000b 0a ### 5 byte FRAGN header e50e 000b 0a ### 5 byte FRAGN header
42 ### SIXLOWPAN_DISPATCH_HC1 42 ### SIXLOWPAN_DISPATCH_HC1
fb ### RIME_HC1_HC_UDP_HC1_ENCODING fb ### RIME_HC1_HC_UDP_HC1_ENCODING