Merge pull request #686 from simonduq/contrib/cc1200-tsch

TSCH support for CC1200
This commit is contained in:
George Oikonomou 2018-10-11 00:42:26 +01:00 committed by GitHub
commit 1db3ce4157
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
30 changed files with 840 additions and 216 deletions

View File

@ -37,10 +37,13 @@
#define RTIMER_ARCH_SECOND 32768
/*---------------------------------------------------------------------------*/
/* 352us from calling transmit() until the SFD byte has been sent */
#define RADIO_DELAY_BEFORE_TX ((unsigned)US_TO_RTIMERTICKS(352))
#define CC2538_DELAY_BEFORE_TX ((unsigned)US_TO_RTIMERTICKS(352))
/* 192us as in datasheet but ACKs are not always received, so adjusted to 250us */
#define RADIO_DELAY_BEFORE_RX ((unsigned)US_TO_RTIMERTICKS(250))
#define RADIO_DELAY_BEFORE_DETECT 0
#define CC2538_DELAY_BEFORE_RX ((unsigned)US_TO_RTIMERTICKS(250))
#define CC2538_DELAY_BEFORE_DETECT 0
/* Frame filtering done in software */
#define TSCH_CONF_HW_FRAME_FILTERING 0
#ifndef TSCH_CONF_BASE_DRIFT_PPM
/* The drift compared to "true" 10ms slots.
* Enable adaptive sync to enable compensation for this.
@ -54,9 +57,6 @@
#define TSCH_CONF_BASE_DRIFT_PPM -977
#endif
#if MAC_CONF_WITH_TSCH
#define TSCH_CONF_HW_FRAME_FILTERING 0
#endif /* MAC_CONF_WITH_TSCH */
/*---------------------------------------------------------------------------*/
#define SPI_CONF_CONTROLLER_COUNT 2
/*---------------------------------------------------------------------------*/

View File

@ -42,6 +42,7 @@
#include "net/packetbuf.h"
#include "net/linkaddr.h"
#include "net/netstack.h"
#include "net/mac/tsch/tsch.h"
#include "sys/energest.h"
#include "dev/cc2538-rf.h"
#include "dev/rfcore.h"
@ -862,6 +863,20 @@ get_value(radio_param_t param, radio_value_t *value)
case RADIO_CONST_TXPOWER_MAX:
*value = OUTPUT_POWER_MAX;
return RADIO_RESULT_OK;
case RADIO_CONST_PHY_OVERHEAD:
*value = (radio_value_t)3; /* 1 len byte, 2 bytes CRC */
case RADIO_CONST_BYTE_AIR_TIME:
*value = (radio_value_t)32; /* 250kbps data rate. One byte = 32us.*/
return RADIO_RESULT_OK;
case RADIO_CONST_DELAY_BEFORE_TX:
*value = (radio_value_t)CC2538_DELAY_BEFORE_TX;
return RADIO_RESULT_OK;
case RADIO_CONST_DELAY_BEFORE_RX:
*value = (radio_value_t)CC2538_DELAY_BEFORE_RX;
return RADIO_RESULT_OK;
case RADIO_CONST_DELAY_BEFORE_DETECT:
*value = (radio_value_t)CC2538_DELAY_BEFORE_DETECT;
return RADIO_RESULT_OK;
default:
return RADIO_RESULT_NOT_SUPPORTED;
}
@ -957,6 +972,16 @@ get_object(radio_param_t param, void *dest, size_t size)
return RADIO_RESULT_OK;
}
#if MAC_CONF_WITH_TSCH
if(param == RADIO_CONST_TSCH_TIMING) {
if(size != sizeof(uint16_t *) || !dest) {
return RADIO_RESULT_INVALID_VALUE;
}
*(const uint16_t **)dest = tsch_timeslot_timing_us_10000;
return RADIO_RESULT_OK;
}
#endif /* MAC_CONF_WITH_TSCH */
return RADIO_RESULT_NOT_SUPPORTED;
}
/*---------------------------------------------------------------------------*/

View File

@ -36,6 +36,10 @@
/*---------------------------------------------------------------------------*/
/* TSCH related defines */
/* 1 len byte, 2 bytes CRC */
#define RADIO_PHY_OVERHEAD 3
/* 250kbps data rate. One byte = 32us */
#define RADIO_BYTE_AIR_TIME 32
/* Delay between GO signal and SFD */
#define RADIO_DELAY_BEFORE_TX ((unsigned)US_TO_RTIMERTICKS(81))
/* Delay between GO signal and start listening.

View File

@ -57,6 +57,10 @@
/*---------------------------------------------------------------------------*/
/* TSCH related defines */
/* 1 len byte, 2 bytes CRC */
#define RADIO_PHY_OVERHEAD 3
/* 250kbps data rate. One byte = 32us */
#define RADIO_BYTE_AIR_TIME 32
/* Delay between GO signal and SFD */
#define RADIO_DELAY_BEFORE_TX ((unsigned)US_TO_RTIMERTICKS(81))
/* Delay between GO signal and start listening.

View File

@ -34,6 +34,7 @@
#include "cc1200-rf-cfg.h"
#include "cc1200-const.h"
#include "net/mac/tsch/tsch.h"
/*
* This is a setup for the following configuration:
@ -62,7 +63,53 @@
/*---------------------------------------------------------------------------*/
static const char rf_cfg_descriptor[] = "802.15.4g 863-870MHz MR-FSK mode #1";
/*---------------------------------------------------------------------------*/
/*
/* 1 byte time: 160 usec */
#define CC1200_TSCH_PREAMBLE_LENGTH 800 /* 5 bytes */
#define CC1200_TSCH_CONF_RX_WAIT 2200
#define CC1200_TSCH_CONF_RX_ACK_WAIT 400
#define CC1200_TSCH_DEFAULT_TS_CCA_OFFSET 1800
#define CC1200_TSCH_DEFAULT_TS_CCA 128
#define CC1200_TSCH_DEFAULT_TS_TX_OFFSET 3800
#define CC1200_TSCH_DEFAULT_TS_RX_OFFSET (CC1200_TSCH_DEFAULT_TS_TX_OFFSET - CC1200_TSCH_PREAMBLE_LENGTH - (CC1200_TSCH_CONF_RX_WAIT / 2))
#define CC1200_TSCH_DEFAULT_TS_RX_ACK_DELAY (CC1200_TSCH_DEFAULT_TS_TX_ACK_DELAY - CC1200_TSCH_PREAMBLE_LENGTH - (CC1200_TSCH_CONF_RX_ACK_WAIT / 2))
#define CC1200_TSCH_DEFAULT_TS_TX_ACK_DELAY 3000
#define CC1200_TSCH_DEFAULT_TS_RX_WAIT (CC1200_TSCH_PREAMBLE_LENGTH + CC1200_TSCH_CONF_RX_WAIT)
#define CC1200_TSCH_DEFAULT_TS_ACK_WAIT (CC1200_TSCH_PREAMBLE_LENGTH + CC1200_TSCH_CONF_RX_ACK_WAIT)
#define CC1200_TSCH_DEFAULT_TS_RX_TX 192
#define CC1200_TSCH_DEFAULT_TS_MAX_ACK 3360 /* 17+1+3 bytes at 50 kbps */
#define CC1200_TSCH_DEFAULT_TS_MAX_TX 20800 /* 126+1+3 bytes at 50 kbps */
#define CC1200_TSCH_DEFAULT_SLACK_TIME 500
/* Timeslot length: 31460 usec */
#define CC1200_TSCH_DEFAULT_TS_TIMESLOT_LENGTH \
( CC1200_TSCH_DEFAULT_TS_TX_OFFSET \
+ CC1200_TSCH_DEFAULT_TS_MAX_TX \
+ CC1200_TSCH_DEFAULT_TS_TX_ACK_DELAY \
+ CC1200_TSCH_DEFAULT_TS_MAX_ACK \
+ CC1200_TSCH_DEFAULT_SLACK_TIME \
)
/* TSCH timeslot timing (mircoseconds) */
static const uint16_t cc1200_50kbps_tsch_timing[tsch_ts_elements_count] = {
CC1200_TSCH_DEFAULT_TS_CCA_OFFSET,
CC1200_TSCH_DEFAULT_TS_CCA,
CC1200_TSCH_DEFAULT_TS_TX_OFFSET,
CC1200_TSCH_DEFAULT_TS_RX_OFFSET,
CC1200_TSCH_DEFAULT_TS_RX_ACK_DELAY,
CC1200_TSCH_DEFAULT_TS_TX_ACK_DELAY,
CC1200_TSCH_DEFAULT_TS_RX_WAIT,
CC1200_TSCH_DEFAULT_TS_ACK_WAIT,
CC1200_TSCH_DEFAULT_TS_RX_TX,
CC1200_TSCH_DEFAULT_TS_MAX_ACK,
CC1200_TSCH_DEFAULT_TS_MAX_TX,
CC1200_TSCH_DEFAULT_TS_TIMESLOT_LENGTH,
};
/*
* Register settings exported from SmartRF Studio using the standard template
* "trxEB RF Settings Performance Line".
*/
@ -159,6 +206,11 @@ const cc1200_rf_cfg_t cc1200_802154g_863_870_fsk_50kbps = {
.size_of_register_settings = sizeof(preferredSettings),
.tx_pkt_lifetime = (RTIMER_SECOND / 20),
.tx_rx_turnaround = (RTIMER_SECOND / 100),
/* Includes 3 Bytes preamble + 2 Bytes SFD, at 160usec per byte = 800 usec */
/* Includes time to completion of "Wait for TX to start" if cc1200.c: 397 usec */
.delay_before_tx = ((unsigned)US_TO_RTIMERTICKS(800 + 397 + 423)),
.delay_before_rx = (unsigned)US_TO_RTIMERTICKS(400),
.delay_before_detect = 0,
.chan_center_freq0 = RF_CFG_CHAN_CENTER_F0,
.chan_spacing = RF_CFG_CHAN_SPACING,
.min_channel = RF_CFG_MIN_CHANNEL,
@ -166,5 +218,7 @@ const cc1200_rf_cfg_t cc1200_802154g_863_870_fsk_50kbps = {
.max_txpower = RF_CFG_MAX_TXPOWER,
.cca_threshold = RF_CFG_CCA_THRESHOLD,
.rssi_offset = RF_CFG_RSSI_OFFSET,
.bitrate = 50000,
.tsch_timing = cc1200_50kbps_tsch_timing,
};
/*---------------------------------------------------------------------------*/

View File

@ -0,0 +1,176 @@
/*
* Copyright (c) 2015, Weptech elektronik GmbH Germany
* http://www.weptech.de
*
* 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. Neither the name of the copyright holder 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 HOLDER 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.
*
* This file is part of the Contiki operating system.
*/
#include "cc1200-rf-cfg.h"
#include "cc1200-const.h"
#include "net/mac/tsch/tsch.h"
/*
* Register settings exported from SmartRF Studio using the standard 1000kpbs 868MHz template
*/
/* Base frequency in kHz */
#define RF_CFG_CHAN_CENTER_F0 863125
/* Channel spacing in Hz */
#define RF_CFG_CHAN_SPACING 1666667
/* The minimum channel */
#define RF_CFG_MIN_CHANNEL 0
/* The maximum channel */
#define RF_CFG_MAX_CHANNEL 3
/* The maximum output power in dBm */
#define RF_CFG_MAX_TXPOWER CC1200_CONST_TX_POWER_MAX
/* The carrier sense level used for CCA in dBm */
#define RF_CFG_CCA_THRESHOLD (-91)
/* The RSSI offset in dBm */
#define RF_CFG_RSSI_OFFSET (-81)
/*---------------------------------------------------------------------------*/
static const char rf_cfg_descriptor[] = "868MHz 2-GFSK 1000 kbps";
/*---------------------------------------------------------------------------*/
/* 1 byte time: 8 usec */
#define CC1200_TSCH_PREAMBLE_LENGTH 800 /* 5 bytes */
#define CC1200_TSCH_CONF_RX_WAIT 2200
#define CC1200_TSCH_CONF_RX_ACK_WAIT 400
#define CC1200_TSCH_DEFAULT_TS_CCA_OFFSET 1800
#define CC1200_TSCH_DEFAULT_TS_CCA 128
#define CC1200_TSCH_DEFAULT_TS_TX_OFFSET 2200
#define CC1200_TSCH_DEFAULT_TS_RX_OFFSET (CC1200_TSCH_DEFAULT_TS_TX_OFFSET - CC1200_TSCH_PREAMBLE_LENGTH - (CC1200_TSCH_CONF_RX_WAIT / 2))
#define CC1200_TSCH_DEFAULT_TS_RX_ACK_DELAY (CC1200_TSCH_DEFAULT_TS_TX_ACK_DELAY - CC1200_TSCH_PREAMBLE_LENGTH - (CC1200_TSCH_CONF_RX_ACK_WAIT / 2))
#define CC1200_TSCH_DEFAULT_TS_TX_ACK_DELAY 1900
#define CC1200_TSCH_DEFAULT_TS_RX_WAIT (CC1200_TSCH_PREAMBLE_LENGTH + CC1200_TSCH_CONF_RX_WAIT)
#define CC1200_TSCH_DEFAULT_TS_ACK_WAIT (CC1200_TSCH_PREAMBLE_LENGTH + CC1200_TSCH_CONF_RX_ACK_WAIT)
#define CC1200_TSCH_DEFAULT_TS_RX_TX 192
#define CC1200_TSCH_DEFAULT_TS_MAX_ACK 168 /* 17+1+3 bytes at 1000 kbps */
#define CC1200_TSCH_DEFAULT_TS_MAX_TX 1040 /* 126+1+3 bytes at 1000 kbps */
#define CC1200_TSCH_DEFAULT_SLACK_TIME 500
/* Timeslot length: 5808 usec */
#define CC1200_TSCH_DEFAULT_TS_TIMESLOT_LENGTH \
( CC1200_TSCH_DEFAULT_TS_TX_OFFSET \
+ CC1200_TSCH_DEFAULT_TS_MAX_TX \
+ CC1200_TSCH_DEFAULT_TS_TX_ACK_DELAY \
+ CC1200_TSCH_DEFAULT_TS_MAX_ACK \
+ CC1200_TSCH_DEFAULT_SLACK_TIME \
)
/* TSCH timeslot timing (in rtimer ticks) */
static const uint16_t cc1200_1000kbps_tsch_timing[tsch_ts_elements_count] = {
CC1200_TSCH_DEFAULT_TS_CCA_OFFSET,
CC1200_TSCH_DEFAULT_TS_CCA,
CC1200_TSCH_DEFAULT_TS_TX_OFFSET,
CC1200_TSCH_DEFAULT_TS_RX_OFFSET,
CC1200_TSCH_DEFAULT_TS_RX_ACK_DELAY,
CC1200_TSCH_DEFAULT_TS_TX_ACK_DELAY,
CC1200_TSCH_DEFAULT_TS_RX_WAIT,
CC1200_TSCH_DEFAULT_TS_ACK_WAIT,
CC1200_TSCH_DEFAULT_TS_RX_TX,
CC1200_TSCH_DEFAULT_TS_MAX_ACK,
CC1200_TSCH_DEFAULT_TS_MAX_TX,
CC1200_TSCH_DEFAULT_TS_TIMESLOT_LENGTH,
};
static const registerSetting_t preferredSettings[]=
{
{CC1200_IOCFG2, 0x06},
{CC1200_SYNC_CFG1, 0xA8},
{CC1200_DEVIATION_M, 0x47},
{CC1200_MODCFG_DEV_E, 0x2F},
{CC1200_DCFILT_CFG, 0x1E},
{CC1200_PREAMBLE_CFG0, 0x8A},
{CC1200_IQIC, 0x00},
{CC1200_CHAN_BW, 0x01},
{CC1200_MDMCFG1, 0x42},
{CC1200_MDMCFG0, 0x05},
{CC1200_SYMBOL_RATE2, 0xC9},
{CC1200_SYMBOL_RATE1, 0x99},
{CC1200_SYMBOL_RATE0, 0x99},
{CC1200_AGC_REF, 0x2F},
{CC1200_AGC_CS_THR, 0xF8},
{CC1200_AGC_CFG2, 0x60},
{CC1200_AGC_CFG1, 0x12},
{CC1200_AGC_CFG0, 0x84},
{CC1200_FIFO_CFG, 0x00},
{CC1200_FS_CFG, 0x12},
{CC1200_PKT_CFG2, 0x00},
{CC1200_PKT_CFG0, 0x20},
{CC1200_PKT_LEN, 0xFF},
{CC1200_FREQOFF_CFG, 0x23},
{CC1200_MDMCFG2, 0x00},
{CC1200_FREQ2, 0x56},
{CC1200_FREQ1, 0xCC},
{CC1200_FREQ0, 0xCC},
{CC1200_IF_ADC1, 0xEE},
{CC1200_IF_ADC0, 0x10},
{CC1200_FS_DIG1, 0x04},
{CC1200_FS_DIG0, 0xA3},
{CC1200_FS_CAL1, 0x40},
{CC1200_FS_CAL0, 0x0E},
{CC1200_FS_DIVTWO, 0x03},
{CC1200_FS_DSM0, 0x33},
{CC1200_FS_DVC1, 0xF7},
{CC1200_FS_DVC0, 0x0F},
{CC1200_FS_PFD, 0x00},
{CC1200_FS_PRE, 0x6E},
{CC1200_FS_REG_DIV_CML, 0x1C},
{CC1200_FS_SPARE, 0xAC},
{CC1200_FS_VCO0, 0xB5},
{CC1200_IFAMP, 0x0D},
{CC1200_XOSC5, 0x0E},
{CC1200_XOSC1, 0x03},
};
/*---------------------------------------------------------------------------*/
/* Global linkage: symbol name must be different in each exported file! */
const cc1200_rf_cfg_t cc1200_868_4gfsk_1000kbps = {
.cfg_descriptor = rf_cfg_descriptor,
.register_settings = preferredSettings,
.size_of_register_settings = sizeof(preferredSettings),
.tx_pkt_lifetime = (RTIMER_SECOND),
.tx_rx_turnaround = (RTIMER_SECOND / 100),
/* Includes 3 Bytes preamble + 2 Bytes SFD, at 8usec per byte = 40 usec */
/* Includes time to completion of "Wait for TX to start" if cc1200.c: 397 usec */
.delay_before_tx = ((unsigned)US_TO_RTIMERTICKS(40 + 397 + 207)),
.delay_before_rx = (unsigned)US_TO_RTIMERTICKS(400),
.delay_before_detect = 0,
.chan_center_freq0 = RF_CFG_CHAN_CENTER_F0,
.chan_spacing = RF_CFG_CHAN_SPACING,
.min_channel = RF_CFG_MIN_CHANNEL,
.max_channel = RF_CFG_MAX_CHANNEL,
.max_txpower = RF_CFG_MAX_TXPOWER,
.cca_threshold = RF_CFG_CCA_THRESHOLD,
.rssi_offset = RF_CFG_RSSI_OFFSET,
.bitrate = 1000000,
.tsch_timing = cc1200_1000kbps_tsch_timing,
};
/*---------------------------------------------------------------------------*/

View File

@ -126,6 +126,9 @@ const cc1200_rf_cfg_t cc1200_868_fsk_1_2kbps = {
.size_of_register_settings = sizeof(preferredSettings),
.tx_pkt_lifetime = (2 * RTIMER_SECOND),
.tx_rx_turnaround = (RTIMER_SECOND / 2),
.delay_before_tx = 0,
.delay_before_rx = 0,
.delay_before_detect = 0,
.chan_center_freq0 = RF_CFG_CHAN_CENTER_F0,
.chan_spacing = RF_CFG_CHAN_SPACING,
.min_channel = RF_CFG_MIN_CHANNEL,
@ -133,5 +136,7 @@ const cc1200_rf_cfg_t cc1200_868_fsk_1_2kbps = {
.max_txpower = RF_CFG_MAX_TXPOWER,
.cca_threshold = RF_CFG_CCA_THRESHOLD,
.rssi_offset = RF_CFG_RSSI_OFFSET,
.bitrate = 1200,
.tsch_timing = NULL,
};
/*---------------------------------------------------------------------------*/

View File

@ -69,6 +69,13 @@ typedef struct cc1200_rf_cfg {
rtimer_clock_t tx_pkt_lifetime;
/* The maximum time it takes to switch from Tx to Rx */
rtimer_clock_t tx_rx_turnaround;
/* The delay between a call to transmit() and end of SFD */
rtimer_clock_t delay_before_tx;
/* Delay between GO signal and start listening
* Measured 104us: between GO signal and start listening */
rtimer_clock_t delay_before_rx;
/* Delay between the SFD finishes arriving and it is detected in software */
rtimer_clock_t delay_before_detect;
/* Base frequency in kHz */
uint32_t chan_center_freq0;
/* Channel spacing in Hz */
@ -87,6 +94,10 @@ typedef struct cc1200_rf_cfg {
/* The RSSI offset in dBm.
* -99 when MDMCFG1.DVGA_GAIN=00, -81 when MDMCFG1.DVGA_GAIN=01 */
int8_t rssi_offset;
/* The bitrate in bps */
uint32_t bitrate;
/* TSCH timeslot timing */
const uint16_t *tsch_timing;
} cc1200_rf_cfg_t;
/*---------------------------------------------------------------------------*/
#endif /* CC1200_RF_CFG_H */

View File

@ -47,6 +47,9 @@
#include <string.h>
#include <stdio.h>
static int16_t rssi;
static rtimer_clock_t sfd_timestamp = 0;
/*---------------------------------------------------------------------------*/
/* Various implementation specific defines */
/*---------------------------------------------------------------------------*/
@ -57,7 +60,7 @@
* - 2: Print errors + warnings (recoverable errors)
* - 3: Print errors + warnings + information (what's going on...)
*/
#define DEBUG_LEVEL 2
#define DEBUG_LEVEL 0
/*
* RF test mode. Blocks inside "configure()".
* - Set this parameter to 1 in order to produce an modulated carrier (PN9)
@ -79,6 +82,14 @@
#define CC1200_RF_CFG cc1200_802154g_863_870_fsk_50kbps
#endif
#endif
/*
* When set, a software buffer is used to store outgoing packets before copying
* to Tx FIFO. This enabled sending packets larger than the FIFO. When unset,
* no buffer is used; instead, the payload is copied directly to the Tx FIFO.
* This is requried by TSCH, for shorter and more predictable delay in the Tx
* chain. This, however, restircts the payload length to the Tx FIFO size.
*/
#define CC1200_WITH_TX_BUF (!MAC_CONF_WITH_TSCH)
/*
* Set this parameter to 1 in order to use the MARC_STATE register when
* polling the chips's status. Else use the status byte returned when sending
@ -93,7 +104,11 @@
*
* TODO: Option to be removed upon approval of the driver
*/
#if MAC_CONF_WITH_TSCH
#define USE_SFSTXON 0
#else /* MAC_CONF_WITH_TSCH */
#define USE_SFSTXON 1
#endif /* MAC_CONF_WITH_TSCH */
/*---------------------------------------------------------------------------*/
/* Phy header length */
#if CC1200_802154G
@ -133,7 +148,15 @@
/* Use GPIO2 as RX / TX FIFO threshold indicator pin */
#define GPIO2_IOCFG CC1200_IOCFG_RXFIFO_THR
/* This is the FIFO threshold we use */
#if MAC_CONF_WITH_TSCH
#if CC1200_802154G
#define FIFO_THRESHOLD 1
#else
#define FIFO_THRESHOLD 0
#endif
#else /* MAC_CONF_WITH_TSCH */
#define FIFO_THRESHOLD 32
#endif /* MAC_CONF_WITH_TSCH */
/* Turn on RX after packet reception */
#define RXOFF_MODE_RX 1
/* Let the CC1200 append RSSI + LQI */
@ -249,6 +272,8 @@ extern const cc1200_rf_cfg_t CC1200_RF_CFG;
#define RF_UPDATE_CHANNEL 0x10
/* SPI was locked when calling RX interrupt, let the pollhandler do the job */
#define RF_POLL_RX_INTERRUPT 0x20
/* Ongoing reception */
#define RF_RX_ONGOING 0x40
/* Force calibration in case we don't use CC1200 AUTOCAL + timeout */
#if !CC1200_AUTOCAL
#if CC1200_CAL_TIMEOUT_SECONDS
@ -381,10 +406,14 @@ extern const cc1200_rf_cfg_t CC1200_RF_CFG;
/*---------------------------------------------------------------------------*/
/* Flag indicating whether non-interrupt routines are using SPI */
static volatile uint8_t spi_locked = 0;
#if CC1200_WITH_TX_BUF
/* Packet buffer for transmission, filled within prepare() */
static uint8_t tx_pkt[CC1200_MAX_PAYLOAD_LEN];
#endif /* CC1200_WITH_TX_BUF */
/* The number of bytes waiting in tx_pkt */
static uint16_t tx_pkt_len;
/* Number of bytes from tx_pkt left to write to FIFO */
uint16_t bytes_left_to_write;
/* Packet buffer for reception */
static uint8_t rx_pkt[CC1200_MAX_PAYLOAD_LEN + APPENDIX_LEN];
/* The number of bytes placed in rx_pkt */
@ -422,6 +451,9 @@ static struct etimer et;
/* Init the radio. */
static int
init(void);
/* Prepare and copy PHY header to Tx FIFO */
static int
copy_header_to_tx_fifo(unsigned short payload_len);
/* Prepare the radio with a packet to be sent. */
static int
prepare(const void *payload, unsigned short payload_len);
@ -530,7 +562,7 @@ idle_calibrate_rx(void);
/* Restart RX from within RX interrupt. */
static void
rx_rx(void);
/* Fill TX FIFO, start TX and wait for TX to complete (blocking!). */
/* Fill TX FIFO (if not already done), start TX and wait for TX to complete (blocking!). */
static int
idle_tx_rx(const uint8_t *payload, uint16_t payload_len);
/* Update TX power */
@ -624,7 +656,7 @@ pollhandler(void)
set_channel(new_rf_channel);
}
if(rx_pkt_len > 0) {
if((rx_mode_value & RADIO_RX_MODE_POLL_MODE) == 0 && rx_pkt_len > 0) {
int len;
@ -722,10 +754,67 @@ prepare(const void *payload, unsigned short payload_len)
}
tx_pkt_len = payload_len;
#if CC1200_WITH_TX_BUF
/* Copy payload to buffer, will be sent later */
memcpy(tx_pkt, payload, tx_pkt_len);
#else /* CC1200_WITH_TX_BUF */
#if (CC1200_MAX_PAYLOAD_LEN > (CC1200_FIFO_SIZE - PHR_LEN))
#error CC1200 max payload too large
#else
/* Copy header and payload directly to Radio Tx FIFO (127 bytes max) */
copy_header_to_tx_fifo(payload_len);
burst_write(CC1200_TXFIFO, payload, payload_len);
#endif
#endif /* CC1200_WITH_TX_BUF */
return RADIO_TX_OK;
}
/*---------------------------------------------------------------------------*/
/* Prepare the radio with a packet to be sent. */
static int
copy_header_to_tx_fifo(unsigned short payload_len)
{
#if CC1200_802154G
/* Prepare PHR for 802.15.4g frames */
struct {
uint8_t phra;
uint8_t phrb;
} phr;
#if CC1200_802154G_CRC16
payload_len += 2;
#else
payload_len += 4;
#endif
/* Frame length */
phr.phrb = (uint8_t)(payload_len & 0x00FF);
phr.phra = (uint8_t)((payload_len >> 8) & 0x0007);
#if CC1200_802154G_WHITENING
/* Enable Whitening */
phr.phra |= (1 << 3);
#endif /* #if CC1200_802154G_WHITENING */
#if CC1200_802154G_CRC16
/* FCS type 1, 2 Byte CRC */
phr.phra |= (1 << 4);
#endif /* #if CC1200_802154G_CRC16 */
#endif /* #if CC1200_802154G */
idle();
rf_flags &= ~RF_RX_PROCESSING_PKT;
strobe(CC1200_SFRX);
/* Flush TX FIFO */
strobe(CC1200_SFTX);
#if CC1200_802154G
/* Write PHR */
burst_write(CC1200_TXFIFO, (uint8_t *)&phr, PHR_LEN);
#else
/* Write length byte */
burst_write(CC1200_TXFIFO, (uint8_t *)&payload_len, PHR_LEN);
#endif /* #if CC1200_802154G */
return 0;
}
/*---------------------------------------------------------------------------*/
/* Send the packet that has previously been prepared. */
@ -735,6 +824,7 @@ transmit(unsigned short transmit_len)
uint8_t was_off = 0;
int ret = RADIO_TX_OK;
int txret;
INFO("RF: Transmit (%d)\n", transmit_len);
@ -790,7 +880,12 @@ transmit(unsigned short transmit_len)
#endif
/* Send data using TX FIFO */
if(idle_tx_rx((const uint8_t *)tx_pkt, tx_pkt_len) == RADIO_TX_OK) {
#if CC1200_WITH_TX_BUF
txret = idle_tx_rx(tx_pkt, tx_pkt_len);
#else /* CC1200_WITH_TX_BUF */
txret = idle_tx_rx(NULL, tx_pkt_len);
#endif /* CC1200_WITH_TX_BUF */
if(txret == RADIO_TX_OK) {
/*
* TXOFF_MODE is set to RX,
@ -861,7 +956,7 @@ read(void *buf, unsigned short buf_len)
if(rx_pkt_len > 0) {
int8_t rssi = rx_pkt[rx_pkt_len - 2];
rssi = (int8_t)rx_pkt[rx_pkt_len - 2] + (int)CC1200_RF_CFG.rssi_offset;
/* CRC is already checked */
uint8_t crc_lqi = rx_pkt[rx_pkt_len - 1];
@ -1009,9 +1104,16 @@ receiving_packet(void)
static int
pending_packet(void)
{
int ret;
ret = ((rx_pkt_len != 0) ? 1 : 0);
if(ret == 0 && !SPI_IS_LOCKED()) {
LOCK_SPI();
ret = (single_read(CC1200_NUM_RXBYTES) > 0);
RELEASE_SPI();
}
INFO("RF: Pending (%d)\n", ((rx_pkt_len != 0) ? 1 : 0));
return (rx_pkt_len != 0) ? 1 : 0;
INFO("RF: Pending (%d)\n", ret);
return ret;
}
/*---------------------------------------------------------------------------*/
@ -1038,6 +1140,7 @@ on(void)
RF_ASSERT((cc1200_arch_gpio0_read_pin() == 0));
cc1200_arch_spi_deselect();
rf_flags = RF_INITIALIZED;
rf_flags |= RF_ON;
/* Radio is IDLE now, re-configure GPIO0 (modified inside off()) */
@ -1080,6 +1183,16 @@ off(void)
idle();
if(single_read(CC1200_NUM_RXBYTES) > 0) {
RELEASE_SPI();
/* In case there is something in the Rx FIFO, read it */
cc1200_rx_interrupt();
if(SPI_IS_LOCKED()) {
return 0;
}
LOCK_SPI();
}
/*
* As we use GPIO as CHIP_RDYn signal on wake-up / on(),
* we re-configure it for CHIP_RDYn.
@ -1106,6 +1219,40 @@ off(void)
}
/*---------------------------------------------------------------------------*/
/**
* \brief Reads the current signal strength (RSSI)
* \return The current RSSI in dBm
*
* This function reads the current RSSI on the currently configured
* channel.
*/
static int16_t
get_rssi(void)
{
int16_t rssi0, rssi1;
uint8_t was_off = 0;
/* If we are off, turn on first */
if(!(rf_flags & RF_ON)) {
was_off = 1;
on();
}
/* Wait for CARRIER_SENSE_VALID signal */
BUSYWAIT_UNTIL(((rssi0 = single_read(CC1200_RSSI0))
& CC1200_CARRIER_SENSE_VALID),
RTIMER_SECOND / 100);
RF_ASSERT(rssi0 & CC1200_CARRIER_SENSE_VALID);
rssi1 = (int8_t)single_read(CC1200_RSSI1) + (int)CC1200_RF_CFG.rssi_offset;
/* If we were off, turn back off */
if(was_off) {
off();
}
return rssi1;
}
/*---------------------------------------------------------------------------*/
/* Get a radio parameter value. */
static radio_result_t
get_value(radio_param_t param, radio_value_t *value)
@ -1156,6 +1303,13 @@ get_value(radio_param_t param, radio_value_t *value)
return RADIO_RESULT_OK;
case RADIO_PARAM_RSSI:
*value = get_rssi();
return RADIO_RESULT_OK;
case RADIO_PARAM_LAST_RSSI:
*value = (radio_value_t)rssi;
return RADIO_RESULT_OK;
case RADIO_PARAM_64BIT_ADDR:
return RADIO_RESULT_NOT_SUPPORTED;
@ -1180,6 +1334,34 @@ get_value(radio_param_t param, radio_value_t *value)
*value = (radio_value_t)CC1200_RF_CFG.max_txpower;
return RADIO_RESULT_OK;
case RADIO_CONST_PHY_OVERHEAD:
#if CC1200_802154G
#if CC1200_802154G_CRC16
*value = (radio_value_t)4; /* 2 bytes PHR, 2 bytes CRC */
#else
*value = (radio_value_t)6; /* 2 bytes PHR, 4 bytes CRC */
#endif
#else
*value = (radio_value_t)3; /* 1 len byte, 2 bytes CRC */
#endif
return RADIO_RESULT_OK;
case RADIO_CONST_BYTE_AIR_TIME:
*value = (radio_value_t)8*1000*1000 / CC1200_RF_CFG.bitrate;
return RADIO_RESULT_OK;
case RADIO_CONST_DELAY_BEFORE_TX:
*value = (radio_value_t)CC1200_RF_CFG.delay_before_tx;
return RADIO_RESULT_OK;
case RADIO_CONST_DELAY_BEFORE_RX:
*value = (radio_value_t)CC1200_RF_CFG.delay_before_rx;
return RADIO_RESULT_OK;
case RADIO_CONST_DELAY_BEFORE_DETECT:
*value = (radio_value_t)CC1200_RF_CFG.delay_before_detect;
return RADIO_RESULT_OK;
default:
return RADIO_RESULT_NOT_SUPPORTED;
@ -1282,6 +1464,23 @@ set_value(radio_param_t param, radio_value_t value)
static radio_result_t
get_object(radio_param_t param, void *dest, size_t size)
{
if(param == RADIO_PARAM_LAST_PACKET_TIMESTAMP) {
if(size != sizeof(rtimer_clock_t) || !dest) {
return RADIO_RESULT_INVALID_VALUE;
}
*(rtimer_clock_t *)dest = sfd_timestamp;
return RADIO_RESULT_OK;
}
#if MAC_CONF_WITH_TSCH
if(param == RADIO_CONST_TSCH_TIMING) {
if(size != sizeof(uint16_t *) || !dest) {
return RADIO_RESULT_INVALID_VALUE;
}
*(const uint16_t **)dest = CC1200_RF_CFG.tsch_timing;
return RADIO_RESULT_OK;
}
#endif /* MAC_CONF_WITH_TSCH */
return RADIO_RESULT_NOT_SUPPORTED;
@ -1764,75 +1963,25 @@ rx_rx(void)
}
/*---------------------------------------------------------------------------*/
/* Fill TX FIFO, start TX and wait for TX to complete (blocking!). */
/* Fill TX FIFO (if not already done), start TX and wait for TX to complete (blocking!). */
static int
idle_tx_rx(const uint8_t *payload, uint16_t payload_len)
{
#if (CC1200_MAX_PAYLOAD_LEN > (CC1200_FIFO_SIZE - PHR_LEN))
uint16_t bytes_left_to_write;
uint8_t to_write;
const uint8_t *p;
#endif
#if CC1200_802154G
/* Prepare PHR for 802.15.4g frames */
struct {
uint8_t phra;
uint8_t phrb;
} phr;
#if CC1200_802154G_CRC16
payload_len += 2;
#else
payload_len += 4;
#endif
/* Frame length */
phr.phrb = (uint8_t)(payload_len & 0x00FF);
phr.phra = (uint8_t)((payload_len >> 8) & 0x0007);
#if CC1200_802154G_WHITENING
/* Enable Whitening */
phr.phra |= (1 << 3);
#endif /* #if CC1200_802154G_WHITENING */
#if CC1200_802154G_CRC16
/* FCS type 1, 2 Byte CRC */
phr.phra |= (1 << 4);
#endif /* #if CC1200_802154G_CRC16 */
#endif /* #if CC1200_802154G */
/* Prepare for RX */
rf_flags &= ~RF_RX_PROCESSING_PKT;
strobe(CC1200_SFRX);
/* Flush TX FIFO */
strobe(CC1200_SFTX);
#if USE_SFSTXON
/*
* Enable synthesizer. Saves us a few µs especially if it takes
* long enough to fill the FIFO. This strobe must not be
* send before SFTX!
*/
strobe(CC1200_SFSTXON);
#endif
/* Configure GPIO0 to detect TX state */
single_write(CC1200_IOCFG0, CC1200_IOCFG_MARC_2PIN_STATUS_0);
#if (CC1200_MAX_PAYLOAD_LEN > (CC1200_FIFO_SIZE - PHR_LEN))
/*
* We already checked that GPIO2 is used if
* CC1200_MAX_PAYLOAD_LEN > 127 / 126 in the header of this file
*/
single_write(CC1200_IOCFG2, CC1200_IOCFG_TXFIFO_THR);
#endif
#if CC1200_802154G
/* Write PHR */
burst_write(CC1200_TXFIFO, (uint8_t *)&phr, PHR_LEN);
#else
/* Write length byte */
burst_write(CC1200_TXFIFO, (uint8_t *)&payload_len, PHR_LEN);
#endif /* #if CC1200_802154G */
#if CC1200_WITH_TX_BUF
/* Prepare and write header */
copy_header_to_tx_fifo(payload_len);
/*
* Fill FIFO with data. If SPI is slow it might make sense
@ -1849,6 +1998,7 @@ idle_tx_rx(const uint8_t *payload, uint16_t payload_len)
#else
burst_write(CC1200_TXFIFO, payload, payload_len);
#endif
#endif /* CC1200_WITH_TX_BUF */
#if USE_SFSTXON
/* Wait for synthesizer to be ready */
@ -1888,7 +2038,7 @@ idle_tx_rx(const uint8_t *payload, uint16_t payload_len)
}
#if (CC1200_MAX_PAYLOAD_LEN > (CC1200_FIFO_SIZE - PHR_LEN))
#if (CC1200_MAX_PAYLOAD_LEN > (CC1200_FIFO_SIZE - PHR_LEN)) && CC1200_WITH_TX_BUF
if(bytes_left_to_write != 0) {
rtimer_clock_t t0;
uint8_t s;
@ -2026,6 +2176,9 @@ set_channel(uint8_t channel)
uint8_t was_off = 0;
uint32_t freq;
channel %= (CC1200_RF_CFG.max_channel - CC1200_RF_CFG.min_channel + 1);
channel += CC1200_RF_CFG.min_channel;
#if 0
/*
* We explicitly allow a channel update even if the channel does not change.
@ -2156,6 +2309,7 @@ addr_check_auto_ack(uint8_t *frame, uint16_t frame_len)
idle();
#endif
prepare((const uint8_t *)ack, ACK_LEN);
idle_tx_rx((const uint8_t *)ack, ACK_LEN);
/* rx_rx() will follow */
@ -2204,6 +2358,23 @@ cc1200_rx_interrupt(void)
*/
static uint8_t buf[CC1200_MAX_PAYLOAD_LEN + APPENDIX_LEN];
/*
* If CC1200_USE_GPIO2 is enabled, we come here either once RX FIFO
* threshold is reached (GPIO2 rising edge)
* or at the end of the packet (GPIO0 falling edge).
*/
#if CC1200_USE_GPIO2
int gpio2 = cc1200_arch_gpio2_read_pin();
int gpio0 = cc1200_arch_gpio0_read_pin();
if((rf_flags & RF_RX_ONGOING) == 0 && gpio2 > 0) {
rf_flags |= RF_RX_ONGOING;
sfd_timestamp = RTIMER_NOW();
}
if(gpio0 == 0) {
rf_flags &= ~RF_RX_ONGOING;
}
#endif
if(SPI_IS_LOCKED()) {
/*

View File

@ -0,0 +1,61 @@
/*
* Copyright (c) 2018, RISE SICS.
* 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. Neither the name of the Institute 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 INSTITUTE 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 INSTITUTE 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.
*
* This file is part of the Contiki operating system.
*
*/
/**
* \file
* IEEE 802.15.4 TSCH timeslot timings for 15ms slots
* \author
* Simon Duquennoy <simon.duquennoy@ri.se>
*
*/
#include "contiki.h"
#include "net/mac/tsch/tsch.h"
/**
* \brief 15ms TSCH timeslot timings, required for cc2420 platforms as
* they are unable to keep up with the defulat 10ms timeslots.
*/
const uint16_t tsch_timeslot_timing_us_15000[tsch_ts_elements_count] = {
1800, /* CCAOffset */
128, /* CCA */
4000, /* TxOffset */
(4000 - (TSCH_CONF_RX_WAIT / 2)), /* RxOffset */
3600, /* RxAckDelay */
4000, /* TxAckDelay */
TSCH_CONF_RX_WAIT, /* RxWait */
800, /* AckWait */
2072, /* RxTx */
2400, /* MaxAck */
4256, /* MaxTx */
15000, /* TimeslotLength */
};

View File

@ -0,0 +1,35 @@
/*
* Copyright (c) 2018, RISE SICS.
* 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. Neither the name of the Institute 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 INSTITUTE 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 INSTITUTE 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.
*
* This file is part of the Contiki operating system.
*
*/
#include "contiki.h"
extern const uint16_t tsch_timeslot_timing_us_15000[];

View File

@ -96,9 +96,6 @@ static const struct output_config output_power[] = {
void cc2420_arch_init(void);
/* XXX hack: these will be made as Chameleon packet attributes */
rtimer_clock_t cc2420_time_of_arrival, cc2420_time_of_departure;
int cc2420_authority_level_of_sender;
volatile uint8_t cc2420_sfd_counter;

View File

@ -102,9 +102,6 @@ int cc2420_get_txpower(void);
*/
int cc2420_interrupt(void);
/* XXX hack: these will be made as Chameleon packet attributes */
extern rtimer_clock_t cc2420_time_of_arrival,
cc2420_time_of_departure;
extern int cc2420_authority_level_of_sender;
int cc2420_on(void);

View File

@ -122,6 +122,10 @@ typedef unsigned long clock_time_t;
/* Use 64-bit rtimer (default in Contiki-NG is 32) */
#define RTIMER_CONF_CLOCK_SIZE 8
/* 1 len byte, 2 bytes CRC */
#define RADIO_PHY_OVERHEAD 3
/* 250kbps data rate. One byte = 32us */
#define RADIO_BYTE_AIR_TIME 32
#define RADIO_DELAY_BEFORE_TX 0
#define RADIO_DELAY_BEFORE_RX 0
#define RADIO_DELAY_BEFORE_DETECT 0

View File

@ -38,6 +38,10 @@
#undef putchar
/* 1 len byte, 2 bytes CRC */
#define RADIO_PHY_OVERHEAD 3
/* 250kbps data rate. One byte = 32us */
#define RADIO_BYTE_AIR_TIME 32
/* Delay between GO signal and SFD
* Measured 153us between GO and preamble. Add 5 bytes (preamble + SFD) air time: 153+5*32 = 313 */
#define RADIO_DELAY_BEFORE_TX ((unsigned)US_TO_RTIMERTICKS(313))

View File

@ -17,11 +17,14 @@
#define NETSTACK_CONF_RADIO cc2420_driver
#endif /* NETSTACK_CONF_RADIO */
/* Symbol for the TSCH 15ms timeslot timing template */
#define TSCH_CONF_ARCH_HDR_PATH "dev/cc2420/cc2420-tsch-15ms.h"
/* The TSCH default slot length of 10ms is a bit too short for this platform,
* use 15ms instead. */
#ifndef TSCH_CONF_DEFAULT_TIMESLOT_LENGTH
#define TSCH_CONF_DEFAULT_TIMESLOT_LENGTH 15000
#endif /* TSCH_CONF_DEFAULT_TIMESLOT_LENGTH */
#ifndef TSCH_CONF_DEFAULT_TIMESLOT_TIMING
#define TSCH_CONF_DEFAULT_TIMESLOT_TIMING tsch_timeslot_timing_us_15000
#endif /* TSCH_CONF_DEFAULT_TIMESLOT_TIMING */
/* Save RAM through a smaller uIP buffer */
#ifndef UIP_CONF_BUFFER_SIZE

View File

@ -43,6 +43,7 @@
#include "lib/random.h"
#include "net/netstack.h"
#include "net/mac/framer/frame802154.h"
#include "net/mac/tsch/tsch.h"
#if NETSTACK_CONF_WITH_IPV6
#include "net/ipv6/uip-ds6.h"

View File

@ -43,6 +43,11 @@
* Definitions below are dictated by the hardware and not really
* changeable!
*/
/* 1 len byte, 2 bytes CRC */
#define RADIO_PHY_OVERHEAD 3
/* 250kbps data rate. One byte = 32us */
#define RADIO_BYTE_AIR_TIME 32
/* Delay between GO signal and SFD: radio fixed delay + 4Bytes preample + 1B SFD -- 1Byte time is 32us
* ~327us + 129preample = 456 us */
#define RADIO_DELAY_BEFORE_TX ((unsigned)US_TO_RTIMERTICKS(456))

View File

@ -55,6 +55,25 @@
#endif /* PROJECT_CONF_PATH */
/*---------------------------------------------------------------------------*/
#include "cc2538-def.h"
unsigned radio_phy_overhead(void);
unsigned radio_byte_air_time(void);
unsigned radio_delay_before_tx(void);
unsigned radio_delay_before_rx(void);
unsigned radio_delay_before_detect(void);
uint16_t *radio_tsch_timeslot_timing(void);
/** @} */
/*---------------------------------------------------------------------------*/
#define RADIO_PHY_OVERHEAD radio_phy_overhead()
#define RADIO_BYTE_AIR_TIME radio_byte_air_time()
#define RADIO_DELAY_BEFORE_TX radio_delay_before_tx()
#define RADIO_DELAY_BEFORE_RX radio_delay_before_rx()
#define RADIO_DELAY_BEFORE_DETECT radio_delay_before_detect()
#define TSCH_CONF_DEFAULT_TIMESLOT_TIMING radio_tsch_timeslot_timing()
/*---------------------------------------------------------------------------*/
/**
* \name Serial Boot Loader Backdoor configuration

View File

@ -257,6 +257,48 @@ platform_idle()
lpm_enter();
}
/*---------------------------------------------------------------------------*/
unsigned
radio_phy_overhead(void) {
radio_value_t ret;
NETSTACK_RADIO.get_value(RADIO_CONST_PHY_OVERHEAD, &ret);
return (unsigned)ret;
}
/*---------------------------------------------------------------------------*/
unsigned
radio_byte_air_time(void) {
radio_value_t ret;
NETSTACK_RADIO.get_value(RADIO_CONST_BYTE_AIR_TIME, &ret);
return (unsigned)ret;
}
/*---------------------------------------------------------------------------*/
unsigned
radio_delay_before_tx(void) {
radio_value_t ret;
NETSTACK_RADIO.get_value(RADIO_CONST_DELAY_BEFORE_TX, &ret);
return (unsigned)ret;
}
/*---------------------------------------------------------------------------*/
unsigned
radio_delay_before_rx(void) {
radio_value_t ret;
NETSTACK_RADIO.get_value(RADIO_CONST_DELAY_BEFORE_RX, &ret);
return (unsigned)ret;
}
/*---------------------------------------------------------------------------*/
unsigned
radio_delay_before_detect(void) {
radio_value_t ret;
NETSTACK_RADIO.get_value(RADIO_CONST_DELAY_BEFORE_DETECT, &ret);
return (unsigned)ret;
}
/*---------------------------------------------------------------------------*/
uint16_t *
radio_tsch_timeslot_timing(void) {
uint16_t *ret;
NETSTACK_RADIO.get_object(RADIO_CONST_TSCH_TIMING, &ret, sizeof(ret));
return ret;
}
/*---------------------------------------------------------------------------*/
/**
* @}
* @}

View File

@ -74,33 +74,4 @@
#endif /* WITH_SECURITY */
/*******************************************************/
/************* Other system configuration **************/
/*******************************************************/
#if CONTIKI_TARGET_Z1
/* Save some space to fit the limited RAM of the z1 */
#define UIP_CONF_TCP 0
#define QUEUEBUF_CONF_NUM 2
#define NETSTACK_MAX_ROUTE_ENTRIES 2
#define NBR_TABLE_CONF_MAX_NEIGHBORS 2
#define UIP_CONF_ND6_SEND_NA 0
#define SICSLOWPAN_CONF_FRAG 0
#if WITH_SECURITY
/* Note: on sky or z1 in cooja, crypto operations are done in S/W and
* cannot be accommodated in normal slots. Use 65ms slots instead, and
* a very short 6TiSCH minimal schedule length */
#define TSCH_CONF_DEFAULT_TIMESLOT_LENGTH 65000
#define TSCH_SCHEDULE_CONF_DEFAULT_LENGTH 2
#endif /* WITH_SECURITY */
#endif /* CONTIKI_TARGET_Z1 */
#if CONTIKI_TARGET_CC2538DK || CONTIKI_TARGET_ZOUL || \
CONTIKI_TARGET_OPENMOTE_CC2538
#define TSCH_CONF_HW_FRAME_FILTERING 0
#endif /* CONTIKI_TARGET_CC2538DK || CONTIKI_TARGET_ZOUL \
|| CONTIKI_TARGET_OPENMOTE_CC2538 */
#endif /* PROJECT_CONF_H_ */

View File

@ -194,7 +194,7 @@ PROCESS_THREAD(node_process, ev, data)
if (host_found) {
/* Make sample count dependent on asn. After a disconnect, waveforms remain
synchronous. Use node_mac to create phase offset between waveforms in different nodes */
sample_count = ((tsch_current_asn.ls4b/((1000/(TSCH_CONF_DEFAULT_TIMESLOT_LENGTH/1000)))/INTERVAL)+node_mac[7]) % (SIZE_OF_WAVEFORM-1);
sample_count = ((tsch_current_asn.ls4b/((1000/(tsch_timing_us[tsch_ts_timeslot_length]/1000)))/INTERVAL)+node_mac[7]) % (SIZE_OF_WAVEFORM-1);
printf("%d sec. waveform=%s. cnt=%d. value=%d\n", total_time, waveform_table[selected_waveform].str, sample_count, waveform_table[selected_waveform].table[sample_count]);
my_sprintf(udp_buf, waveform_table[selected_waveform].table[sample_count]);
uip_udp_packet_send(udp_conn_tx, udp_buf, strlen(udp_buf));

View File

@ -183,7 +183,14 @@ enum {
/* The minimum transmission power in dBm. */
RADIO_CONST_TXPOWER_MIN,
/* The maximum transmission power in dBm. */
RADIO_CONST_TXPOWER_MAX
RADIO_CONST_TXPOWER_MAX,
RADIO_CONST_TSCH_TIMING,
RADIO_CONST_PHY_OVERHEAD,
RADIO_CONST_BYTE_AIR_TIME,
RADIO_CONST_DELAY_BEFORE_TX,
RADIO_CONST_DELAY_BEFORE_RX,
RADIO_CONST_DELAY_BEFORE_DETECT,
};
/* Radio power modes */

View File

@ -151,7 +151,7 @@
#ifdef TSCH_CONF_HOPPING_SEQUENCE_MAX_LEN
#define TSCH_HOPPING_SEQUENCE_MAX_LEN TSCH_CONF_HOPPING_SEQUENCE_MAX_LEN
#else
#define TSCH_HOPPING_SEQUENCE_MAX_LEN 16
#define TSCH_HOPPING_SEQUENCE_MAX_LEN sizeof(TSCH_DEFAULT_HOPPING_SEQUENCE)
#endif
/******** Configuration: association *******/
@ -415,12 +415,12 @@ by default, useful in case of duplicate seqno */
#define TSCH_RADIO_ON_DURING_TIMESLOT 0
#endif
/* Timeslot timing */
#ifndef TSCH_CONF_DEFAULT_TIMESLOT_LENGTH
#define TSCH_CONF_DEFAULT_TIMESLOT_LENGTH 10000
#endif /* TSCH_CONF_DEFAULT_TIMESLOT_LENGTH */
/* TSCH timeslot timing template */
#ifdef TSCH_CONF_DEFAULT_TIMESLOT_TIMING
#define TSCH_DEFAULT_TIMESLOT_TIMING TSCH_CONF_DEFAULT_TIMESLOT_TIMING
#else
#define TSCH_DEFAULT_TIMESLOT_TIMING tsch_timeslot_timing_us_10000
#endif
/* Configurable Rx guard time is micro-seconds */
#ifndef TSCH_CONF_RX_WAIT

View File

@ -75,87 +75,16 @@
#define TSCH_TIMESYNC_MEASUREMENT_ERROR US_TO_RTIMERTICKS(32)
/* The approximate number of slots per second */
#define TSCH_SLOTS_PER_SECOND (1000000 / TSCH_DEFAULT_TS_TIMESLOT_LENGTH)
#define TSCH_SLOTS_PER_SECOND (1000000 / tsch_timing_us[tsch_ts_timeslot_length])
/* Calculate packet tx/rx duration in rtimer ticks based on sent
* packet len in bytes with 802.15.4 250kbps data rate.
* One byte = 32us. Add two bytes for CRC and one for len field */
#define TSCH_PACKET_DURATION(len) US_TO_RTIMERTICKS(32 * ((len) + 3))
#define TSCH_PACKET_DURATION(len) US_TO_RTIMERTICKS(RADIO_BYTE_AIR_TIME * ((len) + RADIO_PHY_OVERHEAD))
/* Convert rtimer ticks to clock and vice versa */
#define TSCH_CLOCK_TO_TICKS(c) (((c) * RTIMER_SECOND) / CLOCK_SECOND)
#define TSCH_CLOCK_TO_SLOTS(c, timeslot_length) (TSCH_CLOCK_TO_TICKS(c) / timeslot_length)
/* The default timeslot timing in the standard is a guard time of
* 2200 us, a Tx offset of 2120 us and a Rx offset of 1120 us.
* As a result, the listening device has a guard time not centered
* on the expected Tx time. This is to be fixed in the next iteration
* of the standard. This can be enabled with:
* #define TSCH_DEFAULT_TS_TX_OFFSET 2120
* #define TSCH_DEFAULT_TS_RX_OFFSET 1120
* #define TSCH_DEFAULT_TS_RX_WAIT 2200
*
* Instead, we align the Rx guard time on expected Tx time. The Rx
* guard time is user-configurable with TSCH_CONF_RX_WAIT.
* (TS_TX_OFFSET - (TS_RX_WAIT / 2)) instead */
#if TSCH_CONF_DEFAULT_TIMESLOT_LENGTH == 10000
/* Default timeslot timing as per IEEE 802.15.4e */
#define TSCH_DEFAULT_TS_CCA_OFFSET 1800
#define TSCH_DEFAULT_TS_CCA 128
#define TSCH_DEFAULT_TS_TX_OFFSET 2120
#define TSCH_DEFAULT_TS_RX_OFFSET (TSCH_DEFAULT_TS_TX_OFFSET - (TSCH_CONF_RX_WAIT / 2))
#define TSCH_DEFAULT_TS_RX_ACK_DELAY 800
#define TSCH_DEFAULT_TS_TX_ACK_DELAY 1000
#define TSCH_DEFAULT_TS_RX_WAIT TSCH_CONF_RX_WAIT
#define TSCH_DEFAULT_TS_ACK_WAIT 400
#define TSCH_DEFAULT_TS_RX_TX 192
#define TSCH_DEFAULT_TS_MAX_ACK 2400
#define TSCH_DEFAULT_TS_MAX_TX 4256
#define TSCH_DEFAULT_TS_TIMESLOT_LENGTH 10000
#elif TSCH_CONF_DEFAULT_TIMESLOT_LENGTH == 15000
/* Default timeslot timing for platforms requiring 15ms slots */
#define TSCH_DEFAULT_TS_CCA_OFFSET 1800
#define TSCH_DEFAULT_TS_CCA 128
#define TSCH_DEFAULT_TS_TX_OFFSET 4000
#define TSCH_DEFAULT_TS_RX_OFFSET (TSCH_DEFAULT_TS_TX_OFFSET - (TSCH_CONF_RX_WAIT / 2))
#define TSCH_DEFAULT_TS_RX_ACK_DELAY 3600
#define TSCH_DEFAULT_TS_TX_ACK_DELAY 4000
#define TSCH_DEFAULT_TS_RX_WAIT TSCH_CONF_RX_WAIT
#define TSCH_DEFAULT_TS_ACK_WAIT 800
#define TSCH_DEFAULT_TS_RX_TX 2072
#define TSCH_DEFAULT_TS_MAX_ACK 2400
#define TSCH_DEFAULT_TS_MAX_TX 4256
#define TSCH_DEFAULT_TS_TIMESLOT_LENGTH 15000
#elif TSCH_CONF_DEFAULT_TIMESLOT_LENGTH == 65000U
/* 65ms timeslot, i.e. nearly the max length allowed by standard (16-bit unsigned in micro-seconds).
* Useful for running link-layer security on sky in Cooja, where only S/W security is supported.
* Note: this slot timing would require a total of 120ms. If a slot overlaps with the next active slot,
* the latter will be skipped.
* This configuration is mostly a work-around to test link-layer security in Cooja, it is recommended
* to use it with a 6TiSCH minimal schedule of length >= 2. */
#define TSCH_DEFAULT_TS_CCA_OFFSET 1800
#define TSCH_DEFAULT_TS_CCA 128
#define TSCH_DEFAULT_TS_TX_OFFSET 52000
#define TSCH_DEFAULT_TS_RX_OFFSET (TSCH_DEFAULT_TS_TX_OFFSET - (TSCH_CONF_RX_WAIT / 2))
#define TSCH_DEFAULT_TS_RX_ACK_DELAY 58600
#define TSCH_DEFAULT_TS_TX_ACK_DELAY 59000
#define TSCH_DEFAULT_TS_RX_WAIT TSCH_CONF_RX_WAIT
#define TSCH_DEFAULT_TS_ACK_WAIT 800
#define TSCH_DEFAULT_TS_RX_TX 2072
#define TSCH_DEFAULT_TS_MAX_ACK 2400
#define TSCH_DEFAULT_TS_MAX_TX 4256
#define TSCH_DEFAULT_TS_TIMESLOT_LENGTH 65000
#else
#error "TSCH: Unsupported default timeslot length"
#endif
#endif /* __TSCH_CONST_H__ */
/** @} */

View File

@ -94,7 +94,7 @@
/* Truncate received drift correction information to maximum half
* of the guard time (one fourth of TSCH_DEFAULT_TS_RX_WAIT) */
#define SYNC_IE_BOUND ((int32_t)US_TO_RTIMERTICKS(TSCH_DEFAULT_TS_RX_WAIT / 4))
#define SYNC_IE_BOUND ((int32_t)US_TO_RTIMERTICKS(tsch_timing_us[tsch_ts_rx_wait] / 4))
/* By default: check that rtimer runs at >=32kHz and use a guard time of 10us */
#if RTIMER_SECOND < (32 * 1024)
@ -789,6 +789,8 @@ PT_THREAD(tsch_rx_slot(struct pt *pt, struct rtimer *t))
#endif
packet_duration = TSCH_PACKET_DURATION(current_input->len);
/* limit packet_duration to its max value */
packet_duration = MIN(packet_duration, tsch_timing[tsch_ts_max_tx]);
if(!frame_valid) {
TSCH_LOG_ADD(tsch_log_message,

View File

@ -0,0 +1,79 @@
/*
* Copyright (c) 2018, RISE SICS.
* 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. Neither the name of the Institute 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 INSTITUTE 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 INSTITUTE 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.
*
* This file is part of the Contiki operating system.
*
*/
/**
* \file
* IEEE 802.15.4 TSCH timeslot timings
* \author
* Simon Duquennoy <simon.duquennoy@ri.se>
*
*/
/**
* \addtogroup tsch
* @{
*/
#include "contiki.h"
#include "net/mac/tsch/tsch.h"
/**
* \brief The default timeslot timing in the standard is a guard time of
* 2200 us, a Tx offset of 2120 us and a Rx offset of 1120 us.
* As a result, the listening device has a guard time not centered
* on the expected Tx time. This is to be fixed in the next iteration
* of the standard. This can be enabled with:
* TxOffset: 2120
* RxOffset: 1120
* RxWait: 2200
*
* Instead, we align the Rx guard time on expected Tx time. The Rx
* guard time is user-configurable with TSCH_CONF_RX_WAIT.
* (TxOffset - (RxWait / 2)) instead
*/
const uint16_t tsch_timeslot_timing_us_10000[tsch_ts_elements_count] = {
1800, /* CCAOffset */
128, /* CCA */
2120, /* TxOffset */
(2120 - (TSCH_CONF_RX_WAIT / 2)), /* RxOffset */
800, /* RxAckDelay */
1000, /* TxAckDelay */
TSCH_CONF_RX_WAIT, /* RxWait */
400, /* AckWait */
192, /* RxTx */
2400, /* MaxAck */
4256, /* MaxTx */
10000, /* TimeslotLength */
};
/** @} */

View File

@ -102,20 +102,9 @@ uint8_t tsch_hopping_sequence[TSCH_HOPPING_SEQUENCE_MAX_LEN];
struct tsch_asn_divisor_t tsch_hopping_sequence_length;
/* Default TSCH timeslot timing (in micro-second) */
static const uint16_t tsch_default_timing_us[tsch_ts_elements_count] = {
TSCH_DEFAULT_TS_CCA_OFFSET,
TSCH_DEFAULT_TS_CCA,
TSCH_DEFAULT_TS_TX_OFFSET,
TSCH_DEFAULT_TS_RX_OFFSET,
TSCH_DEFAULT_TS_RX_ACK_DELAY,
TSCH_DEFAULT_TS_TX_ACK_DELAY,
TSCH_DEFAULT_TS_RX_WAIT,
TSCH_DEFAULT_TS_ACK_WAIT,
TSCH_DEFAULT_TS_RX_TX,
TSCH_DEFAULT_TS_MAX_ACK,
TSCH_DEFAULT_TS_MAX_TX,
TSCH_DEFAULT_TS_TIMESLOT_LENGTH,
};
static const uint16_t *tsch_default_timing_us;
/* TSCH timeslot timing (in micro-second) */
uint16_t tsch_timing_us[tsch_ts_elements_count];
/* TSCH timeslot timing (in rtimer ticks) */
rtimer_clock_t tsch_timing[tsch_ts_elements_count];
@ -231,8 +220,10 @@ tsch_reset(void)
TSCH_ASN_INIT(tsch_current_asn, 0, 0);
current_link = NULL;
/* Reset timeslot timing to defaults */
tsch_default_timing_us = TSCH_DEFAULT_TIMESLOT_TIMING;
for(i = 0; i < tsch_ts_elements_count; i++) {
tsch_timing[i] = US_TO_RTIMERTICKS(tsch_default_timing_us[i]);
tsch_timing_us[i] = tsch_default_timing_us[i];
tsch_timing[i] = US_TO_RTIMERTICKS(tsch_timing_us[i]);
}
#ifdef TSCH_CALLBACK_LEAVING_NETWORK
TSCH_CALLBACK_LEAVING_NETWORK();
@ -581,10 +572,11 @@ tsch_associate(const struct input_packet *input_eb, rtimer_clock_t timestamp)
/* TSCH timeslot timing */
for(i = 0; i < tsch_ts_elements_count; i++) {
if(ies.ie_tsch_timeslot_id == 0) {
tsch_timing[i] = US_TO_RTIMERTICKS(tsch_default_timing_us[i]);
tsch_timing_us[i] = tsch_default_timing_us[i];
} else {
tsch_timing[i] = US_TO_RTIMERTICKS(ies.ie_tsch_timeslot[i]);
tsch_timing_us[i] = ies.ie_tsch_timeslot[i];
}
tsch_timing[i] = US_TO_RTIMERTICKS(tsch_timing_us[i]);
}
/* TSCH hopping sequence */
@ -730,11 +722,11 @@ PT_THREAD(tsch_scan(struct pt *pt))
/* Pick a channel at random in TSCH_JOIN_HOPPING_SEQUENCE */
uint8_t scan_channel = TSCH_JOIN_HOPPING_SEQUENCE[
random_rand() % sizeof(TSCH_JOIN_HOPPING_SEQUENCE)];
if(current_channel != scan_channel) {
NETSTACK_RADIO.set_value(RADIO_PARAM_CHANNEL, scan_channel);
current_channel = scan_channel;
LOG_INFO("scanning on channel %u\n", scan_channel);
}
NETSTACK_RADIO.set_value(RADIO_PARAM_CHANNEL, scan_channel);
current_channel = scan_channel;
LOG_INFO("scanning on channel %u\n", scan_channel);
current_channel_since = now_time;
}
@ -749,16 +741,26 @@ PT_THREAD(tsch_scan(struct pt *pt))
}
if(is_packet_pending) {
rtimer_clock_t t1;
/* Read packet */
input_eb.len = NETSTACK_RADIO.read(input_eb.payload, TSCH_PACKET_MAX_LEN);
/* Save packet timestamp */
NETSTACK_RADIO.get_object(RADIO_PARAM_LAST_PACKET_TIMESTAMP, &t0, sizeof(rtimer_clock_t));
t1 = RTIMER_NOW();
/* Parse EB and attempt to associate */
LOG_INFO("scan: received packet (%u bytes) on channel %u\n", input_eb.len, current_channel);
tsch_associate(&input_eb, t0);
/* Sanity-check the timestamp */
if(ABS(RTIMER_CLOCK_DIFF(t0, t1)) < tsch_timing[tsch_ts_timeslot_length]) {
tsch_associate(&input_eb, t0);
} else {
LOG_WARN("scan: dropping packet, timestamp too far from current time %u %u\n",
(unsigned)t0,
(unsigned)t1
);
}
}
if(tsch_is_associated) {
@ -897,6 +899,12 @@ tsch_init(void)
radio_value_t radio_tx_mode;
rtimer_clock_t t;
/* Check that the platform provides a TSCH timeslot timing template */
if(TSCH_DEFAULT_TIMESLOT_TIMING == NULL) {
LOG_ERR("! platform does not provide a timeslot timing template.\n");
return;
}
/* Radio Rx mode */
if(NETSTACK_RADIO.get_value(RADIO_PARAM_RX_MODE, &radio_rx_mode) != RADIO_RESULT_OK) {
LOG_ERR("! radio does not support getting RADIO_PARAM_RX_MODE. Abort init.\n");
@ -937,6 +945,7 @@ tsch_init(void)
/* Check max hopping sequence length vs default sequence length */
if(TSCH_HOPPING_SEQUENCE_MAX_LEN < sizeof(TSCH_DEFAULT_HOPPING_SEQUENCE)) {
LOG_ERR("! TSCH_HOPPING_SEQUENCE_MAX_LEN < sizeof(TSCH_DEFAULT_HOPPING_SEQUENCE). Abort init.\n");
return;
}
/* Init the queuebuf and TSCH sub-modules */

View File

@ -70,6 +70,11 @@ frequency hopping for enhanced reliability.
#include "sys/cooja_mt.h"
#endif /* CONTIKI_TARGET_COOJA */
/* Include Arch-Specific conf */
#ifdef TSCH_CONF_ARCH_HDR_PATH
#include TSCH_CONF_ARCH_HDR_PATH
#endif /* TSCH_CONF_ARCH_HDR_PATH */
/*********** Macros *********/
/* Wait for a condition with timeout t0+offset. */
@ -170,6 +175,8 @@ extern uint8_t tsch_current_channel;
/* TSCH channel hopping sequence */
extern uint8_t tsch_hopping_sequence[TSCH_HOPPING_SEQUENCE_MAX_LEN];
extern struct tsch_asn_divisor_t tsch_hopping_sequence_length;
/* TSCH timeslot timing (in micro-second) */
uint16_t tsch_timing_us[tsch_ts_elements_count];
/* TSCH timeslot timing (in rtimer ticks) */
extern rtimer_clock_t tsch_timing[tsch_ts_elements_count];
/* Statistics on the current session */
@ -178,6 +185,8 @@ extern unsigned long rx_count;
extern unsigned long sync_count;
extern int32_t min_drift_seen;
extern int32_t max_drift_seen;
/* The TSCH standard 10ms timeslot timing */
extern const uint16_t tsch_timeslot_timing_us_10000[tsch_ts_elements_count];
/* TSCH processes */
PROCESS_NAME(tsch_process);

View File

@ -54,10 +54,10 @@
##### "TSCH_CONF_MAX_EB_PERIOD": _______________ -> TSCH_MAX_EB_PERIOD
#endif
#if TSCH_CONF_DEFAULT_TIMESLOT_LENGTH
##### "TSCH_CONF_DEFAULT_TIMESLOT_LENGTH": _____ == TSCH_CONF_DEFAULT_TIMESLOT_LENGTH
#ifdef TSCH_CONF_DEFAULT_TIMESLOT_TIMING
##### "TSCH_CONF_DEFAULT_TIMESLOT_TIMING": _____ == TSCH_CONF_DEFAULT_TIMESLOT_TIMING
#else
##### "TSCH_CONF_DEFAULT_TIMESLOT_LENGTH": _____ -> TSCH_DEFAULT_TIMESLOT_LENGTH
##### "TSCH_CONF_DEFAULT_TIMESLOT_TIMING": _____ -> TSCH_DEFAULT_TIMESLOT_TIMING
#endif
#ifdef TSCH_SCHEDULE_CONF_DEFAULT_LENGTH