synthetic commit to import ieee branch from old repo

This commit is contained in:
Sebastien Lorquet
2016-06-01 12:12:21 +02:00
parent 2f974ffeaf
commit b0afc4807d
15 changed files with 3362 additions and 216 deletions
+6
View File
@@ -11,4 +11,10 @@ config IEEE802154_MRF24J40
---help---
This selection enables support for the Microchip MRF24J40 device.
config IEEE802154_AT86RF233
bool "ATMEL RF233 IEEE 802.15.4 transceiver"
default n
---help---
This selection enables support for the Atmel RF233 device.
endif # DRIVERS_IEEE802154
+4
View File
@@ -45,6 +45,10 @@ ifeq ($(CONFIG_IEEE802154_MRF24J40),y)
CSRCS += mrf24j40.c
endif
ifeq ($(CONFIG_IEEE802154_AT86RF233),y)
CSRCS += at86rf23x.c
endif
# Include IEEE 802.15.4 build support
DEPPATH += --dep-path wireless$(DELIM)ieee802154
File diff suppressed because it is too large Load Diff
+204
View File
@@ -0,0 +1,204 @@
/*
* at86rf23x.h
*
* Created on: Feb 24, 2016
* Author: poppe
*/
#ifndef APPS_EXTERNAL_IEEE_AT86RF23X_H_
#define APPS_EXTERNAL_IEEE_AT86RF23X_H_
#define RF23X_SPI_REG_READ 0x80
#define RF23X_SPI_REG_WRITE 0xC0
#define RF23X_SPI_FRAME_WRITE 0x60
#define RF23X_SPI_FRAME_READ 0x20
#define RF23X_SPI_SRAM_READ 0x00
#define RF23X_SPI_SRAM_WRITE 0x40
/* us Times Constants for the RF233 */
#define RF23X_TIME_RESET_BOOT 510
#define RF23X_TIME_FORCE_TRXOFF 100
#define RF23X_TIME_P_ON_TO_TRXOFF 510
#define RF23X_TIME_SLEEP_TO_TRXOFF 1200
#define RF23X_TIME_RESET 6
#define RF23X_TIME_ED_MEASUREMENT 140
#define RF23X_TIME_CCA 140
#define RF23X_TIME_PLL_LOCK 150
#define RF23X_TIME_FTN_TUNNING 25
#define RF23X_TIME_NOCLK_TO_WAKE 6
#define RF23X_TIME_CMD_FORCE_TRX_OFF 1
#define RF23X_TIME_TRXOFF_TO_PLL 180
#define RF23X_TIME_TRANSITION_PLL_ACTIVE 1
#define RF23X_TIME_TRXOFF_TO_SLEEP 1200
#define RF23X_MAX_RETRY_RESET_TO_TRX_OFF 5
#define RF23X_REG_TRXSTATUS 0x01
#define RF23X_REG_TRXSTATE 0x02
#define RF23X_REG_TRXCTRL0 0x03
#define RF23X_REG_TRXCTRL1 0x04
#define RF23X_REG_TXPWR 0x05
#define RF23X_REG_RSSI 0x06
#define RF23X_REG_EDLEVEL 0x07
#define RF23X_REG_CCA 0x08
#define RF23X_REG_THRES 0x09
#define RF23X_REG_RXCTRL 0x0a
#define RF23X_REG_SFD 0x0b
#define RF23X_REG_TRXCTRL2 0x0c
#define RF23X_REG_ANT_DIV 0x0d
#define RF23X_REG_IRQ_MASK 0x0e
#define RF23X_REG_IRQ_STATUS 0x0f
#define RF23X_REG_VREG_CTRL 0x10
#define RF23X_REG_BATMON 0x11
#define RF23X_REG_XOSC_CTRL 0x12
#define RF23X_REG_CCCTRL0 0x13
#define RF23X_REG_CCCTRL1 0x14
#define RF23X_REG_RXSYN 0x15
#define RF23X_REG_TRXRPC 0x16
#define RF23X_REG_XAHCTRL1 0x17
#define RF23X_REG_FTNCTRL 0x18
#define RF23X_REG_XAHCTRL2 0x19
#define RF23X_REG_PLLCF 0x1a
#define RF23X_REG_PLLDCU 0x1b
#define RF23X_REG_PART 0x1c
#define RF23X_REG_VERSION 0x1d
#define RF23X_REG_MANID0 0x1e
#define RF23X_REG_MANID1 0x1f
#define RF23X_REG_SADDR0 0x20
#define RF23X_REG_SADDR1 0x21
#define RF23X_REG_PANID0 0x22
#define RF23X_REG_PANID1 0x23
#define RF23X_REG_IEEEADDR0 0x24
#define RF23X_REG_IEEEADDR1 0x25
#define RF23X_REG_IEEEADDR2 0x26
#define RF23X_REG_IEEEADDR3 0x27
#define RF23X_REG_IEEEADDR4 0x28
#define RF23X_REG_IEEEADDR5 0x29
#define RF23X_REG_IEEEADDR6 0x2a
#define RF23X_REG_IEEEADDR7 0x2b
#define RF23X_REG_XAHCTRL0 0x2c
#define RF23X_REG_CSMASEED0 0x2d
#define RF23X_REG_CSMASEED1 0x2e
#define RF23X_REG_CSMABE 0x2f
#define RF23X_REG_TSTCTRLDIGI 0x36
#define RF23X_REG_TSTAGC 0x3c
#define RF23X_REG_SDM 0x3d
#define RF23X_REG_PHYTXTIME 0x3b
#define RF23X_REG_PHYPMUVALUE 0x3b
#define RF23X_TRXSTATUS_POS 0
#define RF23X_TRXSTATUS_MASK 0x1f
#define RF23X_TRXSTATUS_STATUS RF23X_REG_TRXSTATUS, RF23X_TRXSTATUS_POS, RF23X_TRXSTATUS_MASK
#define RF23X_TRXCMD_POS 0
#define RF23X_TRXCMD_MASK 0x1f
#define RF23X_TRXCMD_STATE RF23X_REG_TRXSTATE, RF23X_TRXCMD_POS, RF23X_TRXCMD_MASK
#define RF23X_TXPWR_POS_4 0x00
#define RF23X_TXPWR_POS_3_7 0x01
#define RF23X_TXPWR_POS_3_4 0x02
#define RF23X_TXPWR_POS_3 0x03
#define RF23X_TXPWR_POS_2_5 0x04
#define RF23X_TXPWR_POS_2 0x05
#define RF23X_TXPWR_POS_1 0x06
#define RF23X_TXPWR_0 0x07
#define RF23X_TXPWR_NEG_1 0x08
#define RF23X_TXPWR_NEG_2 0x09
#define RF23X_TXPWR_NEG_3 0x0a
#define RF23X_TXPWR_NEG_4 0x0b
#define RF23X_TXPWR_NEG_6 0x0c
#define RF23X_TXPWR_NEG_8 0x0d
#define RF23X_TXPWR_NEG_12 0x0e
#define RF23X_TXPWR_NEG_17 0x0f
/****************************************************************************
* CCA_STATUS
****************************************************************************/
#define RF23X_CCA_MODE_CS_OR_ED 0x00
#define RF23X_CCA_MODE_ED 0x01
#define RF23X_CCA_MODE_CS 0x02
#define RF23X_CCA_MODE_CS_AND_ED 0x03
#define RF23X_CCA_CHANNEL_POS 0
#define RF23X_CCA_CHANNEL_MASK 0x1f
#define RF23X_CCA_BITS_CHANNEL RF23X_REG_CCA, RF23X_CCA_CHANNEL_POS, RF23X_CCA_CHANNEL_MASK
#define RF23X_CCA_MODE_POS 5
#define RF23X_CCA_MODE_MASK 0x03
#define RF23X_CCA_BITS_MODE RF23X_REG_CCA, RF23X_CCA_MODE_POS, RF23X_CCA_MODE_MASK
/****************************************************************************
* XAH CTRL 1
****************************************************************************/
#define RF23X_XAHCTRL1_PROM_MODE_POS 1
#define RF23X_XAHCTRL1_PROM_MODE_MASK 0x01
#define RF23X_XAHCTRL1_BITS_PROM_MODE RF23X_REG_XAHCTRL1, RF23X_XAHCTRL1_PROM_MODE_POS, RF23X_XAHCTRL1_PROM_MODE_MASK
/****************************************************************************
* CSMA SEED 0
****************************************************************************/
/****************************************************************************
* CSMA SEED 1
****************************************************************************/
#define RF23X_CSMASEED1_IAMCOORD_POS 3
#define RF23X_CSMASEED1_IAMCOORD_MASK 0x1
#define RF23X_CSMASEED1_IAMCOORD_BITS RF23X_REG_CSMASEED1, RF23X_CSMASEED1_IAMCOORD_POS, RF23X_CSMASEED1_IAMCOORD_MASK
#define RF23X_CSMASEED1_AACK_DIS_ACK_POS
#define RF23X_CSMASEED1_AACK_SET_PD_POS
#define RF23X_CSMASEED1_AACK_FVN_MODE_POS
#define RF23X_CSMASEED1_
/****************************************************************************
* TRX Status
****************************************************************************/
#define TRX_STATUS_PON 0x00
#define TRX_STATUS_BUSYRX 0x01
#define TRX_STATUS_BUSYTX 0x02
#define TRX_STATUS_RXON 0x06
#define TRX_STATUS_TRXOFF 0x08
#define TRX_STATUS_PLLON 0x09
#define TRX_STATUS_SLEEP 0x0f
#define TRX_STATUS_DEEPSLEEP 0x10
#define TRX_STATUS_BUSYRXACK 0x11
#define TRX_STATUS_BUSYTXARET 0x12
#define TRX_STATUS_RXAACKON 0x16
#define TRX_STATUS_TXARETON 0x19
#define TRX_STATUS_STATEINTRANS 0x1f
/****************************************************************************
* TRX Command
****************************************************************************/
#define TRX_CMD_NOP 0x00
#define TRX_CMD_TX 0x02
#define TRX_CMD_FORCETRXOFF 0x03
#define TRX_CMD_FORCE_PLLON 0x04
#define TRX_CMD_RX_ON 0x06
#define TRX_CMD_TRXOFF 0x08
#define TRX_CMD_PLL_ON 0x09
#define TRX_CMD_PREP_DEEPSLEEP 0x10
#define TRX_CMD_RX_AACK_ON 0x16
#define TRX_CMD_TX_ARET_ON 0x19
/****************************************************************************
* IRQ MASK 0x0E
****************************************************************************/
#define RF23X_IRQ_MASK_LOCK_PLL (1<<0)
#define RF23X_IRQ_MASK_UNLOCK_PLL (1<<1)
#define RF23X_IRQ_MASK_RX_START (1<<2)
#define RF23X_IRQ_MASK_TRX_END (1<<3)
#define RF23X_IRQ_MASK_CCA_ED_DONE (1<<4)
#define RF23X_IRQ_MASK_AMI (1<<5)
#define RF23X_IRQ_MASK_TRX_UR (1<<6)
#define RF23X_IRQ_MASK_BAT_LOW (1<<7)
#define RF23X_IRQ_MASK_DEFAULT (RF23X_IRQ_MASK_TRX_END)
#endif /* APPS_EXTERNAL_IEEE_AT86RF23X_H_ */
File diff suppressed because it is too large Load Diff
+35 -24
View File
@@ -97,18 +97,22 @@
#define MRF24J40_BBREG6 0x3E
#define MRF24J40_CCAEDTH 0x3F
#define MRF24J40_RFCON0 0x80000200
#define MRF24J40_RFCON1 0x80000201
#define MRF24J40_RFCON2 0x80000202
#define MRF24J40_RFCON3 0x80000203
#define MRF24J40_RFCON5 0x80000205
#define MRF24J40_RFCON6 0x80000206
#define MRF24J40_RFCON7 0x80000207
#define MRF24J40_RFCON8 0x80000208
#define MRF24J40_SLPCAL0 0x80000209
#define MRF24J40_SLPCAL1 0x8000020A
#define MRF24J40_SLPCAL2 0x8000020B
#define MRF24J40_RFSTATE 0x8000020F
#define MRF24J40_TXBUF_BASE 0x80000000
#define MRF24J40_LONGREG_BASE 0x80000200
#define MRF24J40_RXBUF_BASE 0x80000300
#define MRF24J40_RFCON0 (MRF24J40_LONGREG_BASE + 0x00)
#define MRF24J40_RFCON1 (MRF24J40_LONGREG_BASE + 0x01)
#define MRF24J40_RFCON2 (MRF24J40_LONGREG_BASE + 0x02)
#define MRF24J40_RFCON3 (MRF24J40_LONGREG_BASE + 0x03)
#define MRF24J40_RFCON5 (MRF24J40_LONGREG_BASE + 0x05)
#define MRF24J40_RFCON6 (MRF24J40_LONGREG_BASE + 0x06)
#define MRF24J40_RFCON7 (MRF24J40_LONGREG_BASE + 0x07)
#define MRF24J40_RFCON8 (MRF24J40_LONGREG_BASE + 0x08)
#define MRF24J40_SLPCAL0 (MRF24J40_LONGREG_BASE + 0x09)
#define MRF24J40_SLPCAL1 (MRF24J40_LONGREG_BASE + 0x0A)
#define MRF24J40_SLPCAL2 (MRF24J40_LONGREG_BASE + 0x0B)
#define MRF24J40_RFSTATE (MRF24J40_LONGREG_BASE + 0x0F)
#define MRF24J40_RSSI 0x80000210
#define MRF24J40_SLPCON0 0x80000211
#define MRF24J40_SLPCON1 0x80000220
@@ -147,18 +151,18 @@
/* INTSTAT bits */
#define MRF24J40_INTSTAT_SLPIF 0x80
#define MRF24J40_INTSTAT_WAKEIF 0x40
#define MRF24J40_INTSTAT_HSYMTMRIF 0x20
#define MRF24J40_INTSTAT_SECIF 0x10
#define MRF24J40_INTSTAT_RXIF 0x08
#define MRF24J40_INTSTAT_TXG2IF 0x04
#define MRF24J40_INTSTAT_TXG1IF 0x02
#define MRF24J40_INTSTAT_TXNIF 0x01
#define MRF24J40_INTSTAT_TXNIF (1 << 0)
#define MRF24J40_INTSTAT_TXG1IF (1 << 1)
#define MRF24J40_INTSTAT_TXG2IF (1 << 2)
#define MRF24J40_INTSTAT_RXIF (1 << 3)
#define MRF24J40_INTSTAT_SECIF (1 << 4)
#define MRF24J40_INTSTAT_HSYMTMRIF (1 << 5)
#define MRF24J40_INTSTAT_WAKEIF (1 << 6)
#define MRF24J40_INTSTAT_SLPIF (1 << 7)
/* RXMCR bits */
#define MRF24J40_RXMCR_PROMI 0x01 /* Enable promisc mode (rx all valid packets) */
#define MRF24J40_RXMCR_PROMI (1 << 0) /* Enable promisc mode (rx all valid packets) */
#define MRF24J40_RXMCR_ERRPKT 0x02 /* Do not check CRC */
#define MRF24J40_RXMCR_COORD 0x04 /* Enable coordinator mode ??? DIFFERENCE ??? - not used in datasheet! */
#define MRF24J40_RXMCR_PANCOORD 0x08 /* Enable PAN coordinator mode ??? DIFFERENCE ??? */
@@ -166,7 +170,7 @@
/* TXMCR bits */
#define MRF24J40_TXMCR_CSMABF0 0x01
#define MRF24J40_TXMCR_CSMABF0 (1 << 0)
#define MRF24J40_TXMCR_CSMABF1 0x02
#define MRF24J40_TXMCR_CSMABF2 0x04
#define MRF24J40_TXMCR_MACMINBE0 0x08
@@ -184,7 +188,7 @@
#define MRF24J40_INTCON_RXIE 0x08
#define MRF24J40_INTCON_TXG2IE 0x04
#define MRF24J40_INTCON_TXG1IE 0x02
#define MRF24J40_INTCON_TXNIE 0x01
#define MRF24J40_INTCON_TXNIE (1 << 0)
/* BBREG1 bits */
@@ -197,10 +201,17 @@
/* TXNCON bits */
#define MRF24J40_TXNCON_TXNTRIG 0x01 /* Trigger packet tx, automatically cleared */
#define MRF24J40_TXNCON_TXNTRIG (1 << 0) /* Trigger packet tx, automatically cleared */
#define MRF24J40_TXNCON_TXNSECEN 0x02 /* Enable security */
#define MRF24J40_TXNCON_TXNACKREQ 0x04 /* An ACK is requested for this pkt */
#define MRF24J40_TXNCON_INDIRECT 0x08 /* Activate indirect tx bit (for coordinators) */
#define MRF24J40_TXNCON_FPSTAT 0x10 /* Status of the frame pending big in txed acks */
/* TXSTAT bits */
#define MRF24J40_TXSTAT_TXNSTAT (1 << 0)
#define MRF24J40_TXSTAT_CCAFAIL (1 << 5)
#define MRF24J40_TXSTAT_X_SHIFT 6
#define MRF24J40_TXSTAT_X_MASK (3 << MRF24J40_TXSTAT_X_SHIFT)
#endif /* __DRIVERS_IEEE802154_MRF24J40_H */
+7
View File
@@ -83,6 +83,7 @@
#define _LOOPBASE (0x1e00) /* Loop device commands */
#define _MODEMBASE (0x1f00) /* Modem ioctl commands */
#define _I2CBASE (0x2000) /* I2C driver commands */
#define _MAC854BASE (0x2100) /* 802.15.4 device ioctl commands */
/* boardctl commands share the same number space */
@@ -381,6 +382,12 @@
#define _I2CIOCVALID(c) (_IOC_TYPE(c)==_I2CBASE)
#define _I2CIOC(nr) _IOC(_I2CBASE,nr)
/* 802.15.4 MAC driver ioctl definitions *******************************************/
/* (see nuttx/ieee802154/ieee802154_dev.h */
#define _MAC854IOCVALID(c) (_IOC_TYPE(c)==_MAC854BASE)
#define _MAC854IOC(nr) _IOC(_MAC854BASE,nr)
/* boardctl() command definitions *******************************************/
#define _BOARDIOCVALID(c) (_IOC_TYPE(c)==_BOARDBASE)
@@ -0,0 +1,100 @@
/****************************************************************************
* include/nuttx/ieee802154/at86rf23x.h
*
* Copyright (C) 2014-2015 Gregory Nutt. All rights reserved.
* Copyright (C) 2014-2015 Sebastien Lorquet. All rights reserved.
* Author: Sebastien Lorquet <sebastien@lorquet.fr>
*
* 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. Neither the name NuttX nor the names of its contributors may be
* used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "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
* COPYRIGHT OWNER OR CONTRIBUTORS 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.
*
****************************************************************************/
#ifndef __INCLUDE_NUTTX_IEEE802154_AT86RF23X_H
#define __INCLUDE_NUTTX_IEEE802154_AT86RF23X_H
/* The at86rf23x provides interrupts to the MCU via a GPIO pin. The
* following structure provides an MCU-independent mechanixm for controlling
* the at86rf23x GPIO interrupt.
*
* The at86rf23x interrupt is an active low, *level* interrupt. From Datasheet:
* "Note 1: The INTEDGE polarity defaults to:
* 0 = Falling Edge. Ensure that the inter-
* rupt polarity matches the interrupt pin
* polarity of the host microcontroller.
* Note 2: The INT pin will remain high or low,
* depending on INTEDGE polarity setting,
* until INTSTAT register is read."
*/
struct at86rf23x_lower_s
{
int (*irq)(FAR const struct at86rf23x_lower_s *lower, xcpt_t handler, int state);
void (*slptr)(FAR const struct at86rf23x_lower_s *lower, int state);
void (*reset)(FAR const struct at86rf23x_lower_s *lower, int state);
};
#ifdef __cplusplus
#define EXTERN extern "C"
extern "C" {
#else
#define EXTERN extern
#endif
/****************************************************************************
* Public Function Prototypes
****************************************************************************/
/****************************************************************************
* Function: at86rf23x_init
*
* Description:
* Initialize the IEEE802.15.4 driver. The at86rf23x device is assumed to be
* in the post-reset state upon entry to this function.
*
* Parameters:
* spi - A reference to the platform's SPI driver for the at86rf23x
* lower - The MCU-specific interrupt used to control low-level MCU
* functions (i.e., at86rf23x GPIO interrupts).
* devno - If more than one at86rf23x is supported, then this is the
* zero based number that identifies the at86rf23x;
*
* Returned Value:
* OK on success; Negated errno on failure.
*
* Assumptions:
*
****************************************************************************/
FAR struct ieee802154_dev_s *at86rf23x_init(FAR struct spi_dev_s *spi, FAR const struct at86rf23x_lower_s *lower);
#undef EXTERN
#ifdef __cplusplus
}
#endif
#endif /* __INCLUDE_NUTTX_IEEE802154__AT86RF23X_H */
@@ -0,0 +1,368 @@
/****************************************************************************
* include/nuttx/wireless/ieee802154/ieee802154_mac.h
*
* Copyright (C) 2016 Sebastien Lorquet. All rights reserved.
* Author: Sebastien Lorquet <sebastien@lorquet.fr>
*
* 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. Neither the name NuttX nor the names of its contributors may be
* used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "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
* COPYRIGHT OWNER OR CONTRIBUTORS 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.
*
****************************************************************************/
#ifndef __INCLUDE_NUTTX_WIRELESS_IEEE802154_IEEE802154_MAC_H
#define __INCLUDE_NUTTX_WIRELESS_IEEE802154_IEEE802154_MAC_H
/****************************************************************************
* Included Files
****************************************************************************/
#include <nuttx/config.h>
#include <stdint.h>
#include <stdbool.h>
/****************************************************************************
* Pre-Processor Definitions
****************************************************************************/
/* Configuration ************************************************************/
/* None at the moment */
/* IEEE 802.15.4 MAC Interface **********************************************/
/* Some addresses */
#define IEEE802154_PAN_UNSPEC (uint16_t)0xFFFF
#define IEEE802154_SADDR_UNSPEC (uint16_t)0xFFFF
#define IEEE802154_SADDR_BCAST (uint16_t)0xFFFE
#define IEEE802154_EADDR_UNSPEC (uint8_t*)"\xff\xff\xff\xff\xff\xff\xff\xff"
/* IEEE 802.15.4 MAC status codes */
enum
{
MAC802154_STATUS_OK = 0,
MAC802154_STATUS_BEACON_LOSS = 0xE0,
MAC802154_STATUS_CHANNEL_ACCESS_FAILURE,
MAC802154_STATUS_DENIED,
MAC802154_STATUS_DISABLE_TRX_FAILURE,
MAC802154_STATUS_FAILED_SECURITY_CHECK,
MAC802154_STATUS_FRAME_TOO_LONG,
MAC802154_STATUS_INVALID_GTS,
MAC802154_STATUS_INVALID_HANDLE,
MAC802154_STATUS_INVALID_PARAMETER,
MAC802154_STATUS_NO_ACK,
MAC802154_STATUS_NO_BEACON,
MAC802154_STATUS_NO_DATA,
MAC802154_STATUS_NO_SHORT_ADDRESS,
MAC802154_STATUS_OUT_OF_CAP,
MAC802154_STATUS_PAN_ID_CONFLICT,
MAC802154_STATUS_REALIGNMENT,
MAC802154_STATUS_TRANSACTION_EXPIRED,
MAC802154_STATUS_TRANSACTION_OVERFLOW,
MAC802154_STATUS_TX_ACTIVE,
MAC802154_STATUS_UNAVAILABLE_KEY,
MAC802154_STATUS_UNSUPPORTED_ATTRIBUTE
};
/* IEEE 802.15.4 PHY constants */
#define MAC802154_aMaxPHYPacketSize 127
#define MAC802154_aTurnaroundTime 12 /*symbol periods*/
/* IEEE 802.15.4 MAC constants */
#define MAC802154_aBaseSlotDuration 60
#define MAC802154_aNumSuperframeSlots 16
#define MAC802154_aBaseSuperframeDuration (MAC802154_aBaseSlotDuration * MAC802154_aNumSuperframeSlots)
#define MAC802154_aMaxBE 5
#define MAC802154_aMaxBeaconOverhead 75
#define MAC802154_aMaxBeaconPayloadLength (MAC802154_aMaxPHYPacketSize - MAC802154_aMaxBeaconOverhead)
#define MAC802154_aGTSDescPersistenceTime 4
#define MAC802154_aMaxFrameOverhead 25
#define MAC802154_aMaxFrameResponseTime 1220
#define MAC802154_aMaxFrameRetries 3
#define MAC802154_aMaxLostBeacons 4
#define MAC802154_aMaxMACFrameSize (MAC802154_aMaxPHYPacketSize - MAC802154_aMaxFrameOverhead)
#define MAC802154_aMaxSIFSFrameSize 18
#define MAC802154_aMinCAPLength 440
#define MAC802154_aMinLIFSPeriod 40
#define MAC802154_aMinSIFSPeriod 12
#define MAC802154_aResponseWaitTime (32 * MAC802154_aBaseSuperframeDuration)
#define MAC802154_aUnitBackoffPeriod 20
/* IEEE 802.15.4 PHY/MAC PIB attributes IDs */
enum
{
MAC802154_phyCurrentChannel = 0x00,
MAC802154_phyChannelsSupported,
MAC802154_phyTransmitPower,
MAC802154_phyCCAMode,
MAC802154_macAckWaitDuration = 0x40,
MAC802154_macAssociationPermit,
MAC802154_macAutoRequest,
MAC802154_macBattLifeExt,
MAC802154_macBattLifeExtPeriods,
MAC802154_macBeaconPayload,
MAC802154_macBeaconPayloadLength,
MAC802154_macBeaconOrder,
MAC802154_macBeaconTxTime,
MAC802154_macBSN,
MAC802154_macCoordExtendedAddress,
MAC802154_macCoordShortAddress,
MAC802154_macDSN,
MAC802154_macGTSPermit,
MAC802154_macMaxCSMABackoffs,
MAC802154_macMinBE,
MAC802154_macPANId,
MAC802154_macPromiscuousMode,
MAC802154_macRxOnWhenIdle,
MAC802154_macShortAddress,
MAC802154_macSuperframeOrder,
MAC802154_macTransactionPersistenceTime,
MAC802154_macACLEntryDescriptorSet = 0x70,
MAC802154_macACLEntryDescriptorSetSize,
MAC802154_macDefaultSecurity,
MAC802154_macDefaultSecurityMaterialLength,
MAC802154_macDefaultSecurityMaterial,
MAC802154_macDefaultSecuritySuite,
MAC802154_macSecurityMode
};
/****************************************************************************
* Public Types
****************************************************************************/
/* IEEE 802.15.4 Device address
* The addresses in ieee802154 have several formats:
* No address : [none]
* Short address + PAN id : PPPP/SSSS
* Extended address + PAN id : PPPP/LLLLLLLLLLLLLLLL
*/
struct ieee802154_addr_s
{
uint8_t ia_len; /* structure length, 0/2/8 */
uint16_t ia_panid; /* PAN identifier, can be IEEE802154_PAN_UNSPEC */
union {
uint16_t _ia_saddr; /* short address */
uint8_t _ia_eaddr[8]; /* extended address */
} ia_addr;
#define ia_saddr ia_addr._ia_saddr
#define ia_eaddr ia_addr._ia_eaddr
};
#define IEEE802154_ADDRSTRLEN 22 /* (2*2+1+8*2, PPPP/EEEEEEEEEEEEEEEE) */
/* Operations */
struct ieee802154_mac_s;
struct ieee802154_macops_s
{
/* Requests, confirmed asynchronously via callbacks */
CODE int req_data (struct ieee802154_mac_s *mac, /* Transmit a data frame */
uint8_t handle,
uint8_t *buf,
int len);
CODE int req_purge (struct ieee802154_mac_s *mac, /* Cancel transmission of a data frame */
uint8_t handle);
CODE int req_associate (struct ieee802154_mac_s *mac, /* Start association with coordinator */
uint16_t panid,
uint8_t *coordeadr);
CODE int req_disassociate(struct ieee802154_mac_s *mac, /* Start disassociation with coordinator */
uint8_t *eadr,
uint8_t reason);
CODE int req_get (struct ieee802154_mac_s *mac, /* Read the PIB */
int attribute);
CODE int req_gts (struct ieee802154_mac_s *mac, /* Allocate or deallocate a GTS */
uint8_t* characteristics);
CODE int req_reset (struct ieee802154_mac_s *mac, /* MAC layer reset */
bool setdefaults);
CODE int req_rxenable (struct ieee802154_mac_s *mac, /* PHY receiver control */
bool deferrable,
int ontime,
int duration);
CODE int req_scan (struct ieee802154_mac_s *mac, /* Start a network scan */
uint8_t type,
uint32_t channels,
int duration);
CODE int req_set (struct ieee802154_mac_s *mac, /* Change the PIB */
int attribute,
uint8_t *value,
int valuelen);
CODE int req_start (struct ieee802154_mac_s *mac,
uint16_t panid,
int channel,
uint8_t bo,
uint8_t fo,
bool coord,
bool batext,
bool realign);
CODE int req_sync (struct ieee802154_mac_s *mac,
int channel,
bool track);
CODE int req_poll (struct ieee802154_mac_s *mac,
uint8_t *coordaddr);
/* Synchronous Responses to Indications received via callbacks */
CODE int rsp_associate (struct ieee802154_mac_s *mac, /* Reply to an association request */
uint8_t eadr,
uint16_t saddr,
int status);
CODE int rsp_orphan (struct ieee802154_mac_s *mac, /* Orphan device management */
uint8_t *orphanaddr,
uint16_t saddr,
bool associated);
};
/* Notifications */
struct ieee802154_maccb_s
{
/* Asynchronous confirmations to requests */
CODE int conf_data (struct ieee802154_mac_s *mac, /* Data frame was received by remote device */
uint8_t *buf,
int len);
CODE int conf_purge (struct ieee802154_mac_s *mac, /* Data frame was purged */
uint8_t handle,
int status);
CODE int conf_associate (struct ieee802154_mac_s *mac, /* Association request completed */
uint16_t saddr,
int status);
CODE int conf_disassociate(struct ieee802154_mac_s *mac, /* Disassociation request completed */
int status);
CODE int conf_get (struct ieee802154_mac_s *mac, /* PIB data returned */
int status,
int attribute,
uint8_t *value,
int valuelen);
CODE int conf_gts (struct ieee802154_mac_s *mac, /* GTS management completed */
uint8_t *characteristics,
int status);
CODE int conf_reset (struct ieee802154_mac_s *mac, /* MAC reset completed */
int status);
CODE int conf_rxenable (struct ieee802154_mac_s *mac,
int status);
CODE int conf_scan (struct ieee802154_mac_s *mac,
int status,
uint8_t type,
uint32_t unscanned,
int rsltsize,
uint8_t *edlist,
uint8_t *pandescs);
CODE int conf_set (struct ieee802154_mac_s *mac,
int status, int attribute);
CODE int conf_start (struct ieee802154_mac_s *mac,
int status);
CODE int conf_poll (struct ieee802154_mac_s *mac,
int status);
/* Asynchronous event indications, replied to synchronously with responses */
CODE int ind_data (struct ieee802154_mac_s *mac, /* Data frame received */
uint8_t *buf,
int len);
CODE int ind_associate (struct ieee802154_mac_s *mac, /* Association request received */
uint16_t clipanid,
uint8_t *clieaddr);
CODE int ind_disassociate (struct ieee802154_mac_s *mac, /* Disassociation request received */
uint8_t *eadr,
uint8_t reason);
CODE int ind_beaconnotify (struct ieee802154_mac_s *mac, /* Beacon notification */
uint8_t *bsn,
uint_t *pandesc,
uint8_t *sdu,
int sdulen);
CODE int ind_gts (struct ieee802154_mac_s *mac, /* GTS management request received */
uint8_t *devaddr,
uint8_t *characteristics);
CODE int ind_orphan (struct ieee802154_mac_s *mac, /* Orphan device detected */
uint8_t *orphanaddr);
CODE int ind_commstatus (struct ieee802154_mac_s *mac,
uint16_t panid,
uint8_t *src,
uint8_t *dst,
int status);
CODE int ind_syncloss (struct ieee802154_mac_s *mac,
int reason);
};
struct ieee802154_radio_s;
struct ieee802154_mac_s
{
struct ieee802154_radio_s *radio;
struct ieee802154_macops_s ops;
struct ieee802154_maccb_s cbs;
};
#ifdef __cplusplus
#define EXTERN extern "C"
extern "C"
{
#else
#define EXTERN extern
#endif
/****************************************************************************
* Public Function Prototypes
****************************************************************************/
/*
* Instanciate a 802.15.4 MAC from a 802.15.4 radio device.
* To create a 802.15.4 MAC, you need to pass:
* - an instance of a radio driver in radiodev
* - a pointer to a structure that contains MAC callback routines to
* handle confirmations and indications. NULL entries indicate no callback.
* In return you get a mac structure that has pointers to MAC operations and
* responses.
* This API does not create any device accessible to userspace. If you want to
* call these APIs from userspace, you have to wrap your mac in a character
* device via mac802154_device.c .
*/
FAR struct ieee802154_mac_s * mac802154_register(FAR struct ieee802154_radio_s *radiodev, struct ieee802154_maccb_s *callbacks);
#undef EXTERN
#ifdef __cplusplus
}
#endif
#endif /* __INCLUDE_NUTTX_WIRELESS_IEEE802154_MRF24J40_H */
@@ -33,8 +33,8 @@
*
****************************************************************************/
#ifndef __INCLUDE_NUTTX_WIRELESS_IEEE802154_IEEE802154_H
#define __INCLUDE_NUTTX_WIRELESS_IEEE802154_IEEE802154_H
#ifndef __INCLUDE_NUTTX_WIRELESS_IEEE802154_IEEE802154_RADIO_H
#define __INCLUDE_NUTTX_WIRELESS_IEEE802154_IEEE802154_RADIO_H
/****************************************************************************
* Included Files
@@ -48,70 +48,13 @@
/****************************************************************************
* Pre-Processor Definitions
****************************************************************************/
/* Configuration ************************************************************/
/* None at the moment */
/* IEEE 802.15.4 MAC Interface **********************************************/
/* IEEE 802.15.4 Radio Interface **********************************************/
/* Frame control field masks, 2 bytes
* Seee IEEE 802.15.4/2003 7.2.1.1 page 112
*/
#define IEEE802154_FC1_FTYPE 0x03 /* Frame type, bits 0-2 */
#define IEEE802154_FC1_SEC 0x08 /* Security Enabled, bit 3 */
#define IEEE802154_FC1_PEND 0x10 /* Frame pending, bit 4 */
#define IEEE802154_FC1_ACKREQ 0x20 /* Acknowledge request, bit 5 */
#define IEEE802154_FC1_INTRA 0x40 /* Intra PAN, bit 6 */
#define IEEE802154_FC2_DADDR 0x0C /* Dest addressing mode, bits 10-11 */
#define IEEE802154_FC2_VERSION 0x30 /* Source addressing mode, bits 12-13 */
#define IEEE802154_FC2_SADDR 0xC0 /* Source addressing mode, bits 14-15 */
/* Frame Type */
#define IEEE802154_FRAME_BEACON 0x00
#define IEEE802154_FRAME_DATA 0x01
#define IEEE802154_FRAME_ACK 0x02
#define IEEE802154_FRAME_COMMAND 0x03
/* Security Enabled */
#define IEEE802154_SEC_OFF 0x00
#define IEEE802154_SEC_ON 0x08
/* Flags */
#define IEEE802154_PEND 0x10
#define IEEE802154_ACK_REQ 0x20
#define IEEE802154_INTRA 0x40
/* Dest Addressing modes */
#define IEEE802154_DADDR_NONE 0x00
#define IEEE802154_DADDR_SHORT 0x08
#define IEEE802154_DADDR_EXT 0x0A
/* Src Addressing modes */
#define IEEE802154_SADDR_NONE 0x00
#define IEEE802154_SADDR_SHORT 0x80
#define IEEE802154_SADDR_EXT 0xA0
/* Some addresses */
#define IEEE802154_PAN_DEFAULT (uint16_t)0xFFFF
#define IEEE802154_SADDR_UNSPEC (uint16_t)0xFFFF
#define IEEE802154_SADDR_BCAST (uint16_t)0xFFFE
#define IEEE802154_EADDR_UNSPEC (uint8_t*)"\xff\xff\xff\xff\xff\xff\xff\xff"
#define IEEE802154_CMD_ASSOC_REQ 0x01
#define IEEE802154_CMD_ASSOC_RSP 0x02
#define IEEE802154_CMD_DIS_NOT 0x03
#define IEEE802154_CMD_DATA_REQ 0x04
#define IEEE802154_CMD_PANID_CONF_NOT 0x05
#define IEEE802154_CMD_ORPHAN_NOT 0x06
#define IEEE802154_CMD_BEACON_REQ 0x07
#define IEEE802154_CMD_COORD_REALIGN 0x08
#define IEEE802154_CMD_GTS_REQ 0x09
/* This layer only knows radio frames. There are no 802.15.4 specific bits
* at this layer. */
/* Device modes */
@@ -135,73 +78,75 @@ struct ieee802154_cca_s
{
uint8_t use_ed : 1; /* CCA using ED */
uint8_t use_cs : 1; /* CCA using carrier sense */
uint8_t edth; /* Energy detection threshold for CCA */
uint8_t csth; /* Carrier sense threshold for CCA */
uint8_t edth; /* Energy detection threshold for CCA */
uint8_t csth; /* Carrier sense threshold for CCA */
};
struct ieee802154_dev_s;
struct ieee802154_radio_s;
struct ieee802154_devops_s
struct ieee802154_radioops_s
{
CODE int (*setchannel)(FAR struct ieee802154_dev_s *dev, uint8_t channel);
CODE int (*getchannel)(FAR struct ieee802154_dev_s *dev,
CODE int (*setchannel)(FAR struct ieee802154_radio_s *dev, uint8_t channel);
CODE int (*getchannel)(FAR struct ieee802154_radio_s *dev,
FAR uint8_t *channel);
CODE int (*setpanid)(FAR struct ieee802154_dev_s *dev, uint16_t panid);
CODE int (*getpanid)(FAR struct ieee802154_dev_s *dev,
CODE int (*setpanid)(FAR struct ieee802154_radio_s *dev, uint16_t panid);
CODE int (*getpanid)(FAR struct ieee802154_radio_s *dev,
FAR uint16_t *panid);
CODE int (*setsaddr)(FAR struct ieee802154_dev_s *dev, uint16_t saddr);
CODE int (*getsaddr)(FAR struct ieee802154_dev_s *dev,
CODE int (*setsaddr)(FAR struct ieee802154_radio_s *dev, uint16_t saddr);
CODE int (*getsaddr)(FAR struct ieee802154_radio_s *dev,
FAR uint16_t *saddr);
CODE int (*seteaddr)(FAR struct ieee802154_dev_s *dev,
CODE int (*seteaddr)(FAR struct ieee802154_radio_s *dev,
FAR uint8_t *laddr);
CODE int (*geteaddr)(FAR struct ieee802154_dev_s *dev,
CODE int (*geteaddr)(FAR struct ieee802154_radio_s *dev,
FAR uint8_t *laddr);
CODE int (*setpromisc)(FAR struct ieee802154_dev_s *dev, bool promisc);
CODE int (*getpromisc)(FAR struct ieee802154_dev_s *dev,
CODE int (*setpromisc)(FAR struct ieee802154_radio_s *dev, bool promisc);
CODE int (*getpromisc)(FAR struct ieee802154_radio_s *dev,
FAR bool *promisc);
CODE int (*setdevmode)(FAR struct ieee802154_dev_s *dev, uint8_t devmode);
CODE int (*getdevmode)(FAR struct ieee802154_dev_s *dev,
CODE int (*setdevmode)(FAR struct ieee802154_radio_s *dev, uint8_t devmode);
CODE int (*getdevmode)(FAR struct ieee802154_radio_s *dev,
FAR uint8_t *devmode);
CODE int (*settxpower)(FAR struct ieee802154_dev_s *dev,
CODE int (*settxpower)(FAR struct ieee802154_radio_s *dev,
int32_t txpwr); /* unit = 1 mBm = 1/100 dBm */
CODE int (*gettxpower)(FAR struct ieee802154_dev_s *dev,
CODE int (*gettxpower)(FAR struct ieee802154_radio_s *dev,
FAR int32_t *txpwr);
CODE int (*setcca)(FAR struct ieee802154_dev_s *dev,
CODE int (*setcca)(FAR struct ieee802154_radio_s *dev,
FAR struct ieee802154_cca_s *cca);
CODE int (*getcca)(FAR struct ieee802154_dev_s *dev,
CODE int (*getcca)(FAR struct ieee802154_radio_s *dev,
FAR struct ieee802154_cca_s *cca);
CODE int (*ioctl)(FAR struct ieee802154_dev_s *ieee, int cmd,
CODE int (*ioctl)(FAR struct ieee802154_radio_s *ieee, int cmd,
unsigned long arg);
CODE int (*energydetect)(FAR struct ieee802154_dev_s *dev,
CODE int (*energydetect)(FAR struct ieee802154_radio_s *dev,
FAR uint8_t *energy);
CODE int (*rxenable)(FAR struct ieee802154_dev_s *dev, bool state,
CODE int (*rxenable)(FAR struct ieee802154_radio_s *dev, bool state,
FAR struct ieee802154_packet_s *packet);
CODE int (*transmit)(FAR struct ieee802154_dev_s *dev,
CODE int (*transmit)(FAR struct ieee802154_radio_s *dev,
FAR struct ieee802154_packet_s *packet);
/*TODO beacon/sf order*/
};
struct ieee802154_dev_s
struct ieee802154_radio_s
{
FAR const struct ieee802154_devops_s *ops;
FAR const struct ieee802154_radioops_s *ops;
/* Packet reception management */
struct ieee802154_packet_s *rxbuf;
sem_t rxsem;
struct ieee802154_packet_s *rxbuf; /* packet reception buffer, filled by rx interrupt, NULL if rx not enabled */
sem_t rxsem; /* Semaphore posted after reception of a packet */
/* Packet transmission management */
sem_t txsem;
bool txok; /* Last transmission status, filled by tx interrupt */
bool txbusy; /* Last transmission failed because channel busy */
uint8_t txretries; /* Last transmission required this much retries */
sem_t txsem; /* Semaphore posted after transmission of a packet */
};
#ifdef __cplusplus
@@ -221,4 +166,4 @@ extern "C"
}
#endif
#endif /* __INCLUDE_NUTTX_WIRELESS_IEEE802154_MRF24J40_H */
#endif /* __INCLUDE_NUTTX_WIRELESS_IEEE802154_IEEE802154_RADIO_H */
+1 -1
View File
@@ -100,7 +100,7 @@ extern "C"
****************************************************************************/
struct spi_dev_s; /* Forward reference */
FAR struct ieee802154_dev_s *mrf24j40_init(FAR struct spi_dev_s *spi,
FAR struct ieee802154_radio_s *mrf24j40_init(FAR struct spi_dev_s *spi,
FAR const struct mrf24j40_lower_s *lower);
#undef EXTERN
+18
View File
@@ -12,4 +12,22 @@ config IEEE802154
if IEEE802154
config IEEE802154_MAC
bool "Generic Media Access Control layer for 802.15.4 radios"
default n
depends on IEEE802154
---help---
Enables a Media Access Controller for any IEEE802.15.4 radio
device. This in turn can be used by higher layer entities
such as 6lowpan. It is not required to use 802.15.4 radios,
but is strongly suggested to ensure exchange of valid frames.
config IEEE802154_DEV
bool "Debug character driver for ieee802.15.4 radio interfaces"
default n
depends on IEEE802154
---help---
Enables a device driver to expose ieee802.15.4 radio controls
to user space as IOCTLs.
endif # IEEE802154
+9
View File
@@ -36,9 +36,18 @@
ifeq ($(CONFIG_IEEE802154),y)
# Include IEEE 802.15.4 support
CSRCS =
# Include wireless devices build support
ifeq ($(CONFIG_IEEE802154_MAC),y)
CSRCS += ieee802154/mac802154.c
endif
ifeq ($(CONFIG_IEEE802154_DEV),y)
CSRCS += ieee802154/ieee802154_device.c
endif
DEPPATH += --dep-path wireless/ieee802154
VPATH += :wireless/ieee802154
CFLAGS += ${shell $(INCDIR) $(INCDIROPT) "$(CC)" $(TOPDIR)$(DELIM)wireless$(DELIM)ieee802154}
+374
View File
@@ -0,0 +1,374 @@
/****************************************************************************
* drivers/ieee802154/ieee802154_device.c
*
* Copyright (C) 2014-2015 Gregory Nutt. All rights reserved.
* Copyright (C) 2014-2015 Sebastien Lorquet. All rights reserved.
* Author: Sebastien Lorquet <sebastien@lorquet.fr>
*
* 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. Neither the name NuttX nor the names of its contributors may be
* used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "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
* COPYRIGHT OWNER OR CONTRIBUTORS 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.
*
****************************************************************************/
#include <nuttx/config.h>
#include <stdint.h>
#include <stdio.h>
#include <string.h>
#include <errno.h>
#include <time.h>
#include <nuttx/arch.h>
#include <nuttx/kmalloc.h>
#include <nuttx/wireless/ieee802154/ieee802154_radio.h>
#include <nuttx/ieee802154/ieee802154_dev.h>
struct ieee802154_devwrapper_s
{
FAR struct ieee802154_radio_s *child;
sem_t devsem; /* Device access serialization semaphore */
int opened; /* this device can only be opened once */
};
/* when rx interrupt is complete, it calls sem_post(&dev->rxsem); */
/* when tx interrupt is complete, it calls sem_post(&dev->txsem); */
static void ieee802154dev_semtake(FAR struct ieee802154_devwrapper_s *dev);
static int ieee802154dev_open (FAR struct file *filep);
static int ieee802154dev_close (FAR struct file *filep);
static ssize_t ieee802154dev_read (FAR struct file *filep, FAR char *buffer, size_t len);
static ssize_t ieee802154dev_write (FAR struct file *filep, FAR const char *buffer, size_t len);
static int ieee802154dev_ioctl (FAR struct file *filep, int cmd, unsigned long arg);
/****************************************************************************
* Private Data
****************************************************************************/
static const struct file_operations ieee802154dev_fops =
{
ieee802154dev_open , /* open */
ieee802154dev_close, /* close */
ieee802154dev_read , /* read */
ieee802154dev_write, /* write */
0 , /* seek */
ieee802154dev_ioctl /* ioctl */
#ifndef CONFIG_DISABLE_POLL
, 0 /* poll */
#endif
};
/****************************************************************************
* Name: ieee802154dev_semtake
*
* Description:
* Acquire the semaphore used for access serialization.
*
****************************************************************************/
static void ieee802154dev_semtake(FAR struct ieee802154_devwrapper_s *dev)
{
/* Take the semaphore (perhaps waiting) */
while (sem_wait(&dev->devsem) != 0)
{
/* The only case that an error should occur here is if
* the wait was awakened by a signal.
*/
ASSERT(errno == EINTR);
}
}
/****************************************************************************
* Name: ieee802154dev_semgive
*
* Description:
* Release the semaphore used for access serialization.
*
****************************************************************************/
static inline void ieee802154dev_semgive(FAR struct ieee802154_devwrapper_s *dev)
{
sem_post(&dev->devsem);
}
/****************************************************************************
* Name: ieee802154dev_open
*
* Description:
* Open the MRF24J40 device.
*
****************************************************************************/
static int ieee802154dev_open(FAR struct file *filep)
{
FAR struct inode *inode = filep->f_inode;
FAR struct ieee802154_devwrapper_s *dev = inode->i_private;
ieee802154dev_semtake(dev);
if (dev->opened)
{
return -EMFILE;
}
else
{
/* Enable interrupts (only rx for now)*/
//mrf24j40_setreg(dev->spi, MRF24J40_INTCON, ~(MRF24J40_INTCON_RXIE) );
//dev->lower->enable(dev->lower, TRUE);
dev->opened = TRUE;
}
ieee802154dev_semgive(dev);
return OK;
}
/****************************************************************************
* Name: ieee802154dev_close
*
* Description:
* Close the MRF24J40 device.
*
****************************************************************************/
static int ieee802154dev_close(FAR struct file *filep)
{
FAR struct inode *inode = filep->f_inode;
FAR struct ieee802154_devwrapper_s *dev = inode->i_private;
int ret = OK;
ieee802154dev_semtake(dev);
if(!dev->opened)
{
ret = -EIO;
}
else
{
/* Disable interrupts */
//mrf24j40_setreg(dev->spi, MRF24J40_INTCON, 0xFF );
//dev->lower->enable(dev->lower, FALSE);
dev->opened = FALSE;
}
ieee802154dev_semgive(dev);
return ret;
}
/****************************************************************************
* Name: ieee802154dev_read
*
* Description:
* Return the last received packet.
* TODO: Return a packet from the receive queue. The buffer must be a pointer to a
* struct ieee802154_packet_s structure, with a correct length.
*
****************************************************************************/
static ssize_t ieee802154dev_read(FAR struct file *filep, FAR char *buffer, size_t len)
{
FAR struct inode *inode = filep->f_inode;
FAR struct ieee802154_devwrapper_s *dev = inode->i_private;
int ret = OK;
FAR struct ieee802154_packet_s *buf = (FAR struct ieee802154_packet_s*)buffer;
if (len<sizeof(struct ieee802154_packet_s))
{
ret = -EINVAL;
goto done;
}
ret = dev->child->ops->rxenable(dev->child, 1, buf);
#if 0
if (ret < 0)
{
goto done;
}
#endif
/* if no packet is received, this will produce -EAGAIN
* The user is responsible for sleeping until sth arrives
*/
#if 0
ret = sem_trywait(&dev->child->rxsem);
#else
ret = sem_wait(&dev->child->rxsem);
#endif
if (ret < 0)
{
ret = -errno;
goto done;
}
/* disable read until we have process the current read */
dev->child->ops->rxenable(dev->child, 0, NULL);
ret = buf->len;
done:
return ret;
}
/****************************************************************************
* Name: ieee802154dev_write
*
* Description:
* Send a packet immediately.
* TODO: Put a packet in the send queue. The packet will be sent as soon as possible.
* The buffer must point to a struct ieee802154_packet_s with the correct length.
*
****************************************************************************/
static ssize_t ieee802154dev_write(FAR struct file *filep, FAR const char *buffer, size_t len)
{
FAR struct inode *inode = filep->f_inode;
FAR struct ieee802154_devwrapper_s *dev = inode->i_private;
FAR struct ieee802154_packet_s *packet;
int ret = OK;
/* TODO: Make this an option or have a new method of doing timeout from ioctrl */
FAR struct timespec timeout;
timeout.tv_sec = 1;
timeout.tv_nsec = 0;
/* sanity checks */
if (len<sizeof(struct ieee802154_packet_s))
{
ret = -EINVAL;
// goto done;
/* TODO Double check I like having assert here. It is a bigger problem if buffers are to small */
DEBUGASSERT(0);
}
packet = (FAR struct ieee802154_packet_s*) buffer;
if (packet->len > 125) /* Max len 125, 2 FCS bytes auto added by mrf*/
{
ret = -EPERM;
// goto done;
DEBUGASSERT(0);
}
/* Copy packet to normal device TX fifo.
* Beacons and GTS transmission will be handled via IOCTLs
*/
ret = dev->child->ops->transmit(dev->child, packet);
if(ret != packet->len)
{
ret = -EPERM;
goto done;
}
if(sem_timedwait(&dev->child->txsem, &timeout))
{
dbg("Radio Device timedout on Tx\n");
}
done:
/* okay, tx interrupt received. check transmission status to decide success. */
return ret;
}
/****************************************************************************
* Name: ieee802154dev_ioctl
*
* Description:
* Control the MRF24J40 device. This is where the real operations happen.
*
****************************************************************************/
static int ieee802154dev_ioctl(FAR struct file *filep, int cmd, unsigned long arg)
{
FAR struct inode *inode = filep->f_inode;
FAR struct ieee802154_devwrapper_s *dev = inode->i_private;
FAR struct ieee802154_radio_s *child = dev->child;
int ret = OK;
switch(cmd)
{
case MAC854IOCSCHAN : ret = child->ops->setchannel (child, (uint8_t) arg); break;
case MAC854IOCGCHAN : ret = child->ops->getchannel (child, (FAR uint8_t*) arg); break;
case MAC854IOCSPANID : ret = child->ops->setpanid (child, (uint16_t) arg); break;
case MAC854IOCGPANID : ret = child->ops->getpanid (child, (FAR uint16_t*) arg); break;
case MAC854IOCSSADDR : ret = child->ops->setsaddr (child, (uint16_t) arg); break;
case MAC854IOCGSADDR : ret = child->ops->getsaddr (child, (FAR uint16_t*) arg); break;
case MAC854IOCSEADDR : ret = child->ops->seteaddr (child, (FAR uint8_t*) arg); break;
case MAC854IOCGEADDR : ret = child->ops->geteaddr (child, (FAR uint8_t*) arg); break;
case MAC854IOCSPROMISC: ret = child->ops->setpromisc (child, (bool) arg); break;
case MAC854IOCGPROMISC: ret = child->ops->getpromisc (child, (FAR bool*) arg); break;
case MAC854IOCSDEVMODE: ret = child->ops->setdevmode (child, (uint8_t) arg); break;
case MAC854IOCGDEVMODE: ret = child->ops->getdevmode (child, (FAR uint8_t*) arg); break;
case MAC854IOCSTXP : ret = child->ops->settxpower (child, (int32_t) arg); break;
case MAC854IOCGTXP : ret = child->ops->gettxpower (child, (FAR int32_t*) arg); break;
case MAC854IOCSCCA : ret = child->ops->setcca (child, (FAR struct ieee802154_cca_s*)arg); break;
case MAC854IOCGCCA : ret = child->ops->getcca (child, (FAR struct ieee802154_cca_s*)arg); break;
case MAC854IOCGED : ret = child->ops->energydetect(child, (FAR uint8_t*) arg); break;
default : ret = child->ops->ioctl (child, cmd, arg);
}
return ret;
}
/****************************************************************************
* Name: ieee802154dev_register
*
* Description:
* Register /dev/ieee%d
*
****************************************************************************/
int ieee802154_register(FAR struct ieee802154_radio_s *ieee, unsigned int minor)
{
char devname[16];
FAR struct ieee802154_devwrapper_s *dev;
dev = kmm_zalloc(sizeof(struct ieee802154_devwrapper_s));
if (!dev)
{
return -ENOMEM;
}
dev->child = ieee;
sem_init(&dev->devsem , 0, 1); /* Allow the device to be opened once before blocking */
sprintf(devname, "/dev/ieee%d", minor);
return register_driver(devname, &ieee802154dev_fops, 0666, dev);
}
File diff suppressed because it is too large Load Diff