From ca715fdd6b4550ac86e96547df29ec24e3fee84f Mon Sep 17 00:00:00 2001 From: Yasuyuki Tanaka Date: Tue, 6 Sep 2016 15:14:10 +0200 Subject: [PATCH 01/11] Use appropriate types for "value" of setInt{16,32,64}ValueOf() --- .../java/org/contikios/cooja/mote/memory/VarMemory.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tools/cooja/java/org/contikios/cooja/mote/memory/VarMemory.java b/tools/cooja/java/org/contikios/cooja/mote/memory/VarMemory.java index 65cff9af7..4e774c8f4 100644 --- a/tools/cooja/java/org/contikios/cooja/mote/memory/VarMemory.java +++ b/tools/cooja/java/org/contikios/cooja/mote/memory/VarMemory.java @@ -263,7 +263,7 @@ public class VarMemory extends Memory { * @param varName Variable name * @param value 16 bit integer value to write */ - public void setInt16ValueOf(String varName, byte value) + public void setInt16ValueOf(String varName, short value) throws UnknownVariableException { setInt16ValueOf(getVariable(varName).addr, value); } @@ -274,7 +274,7 @@ public class VarMemory extends Memory { * @param varName Variable name * @param value 32 bit integer value to write */ - public void setInt32ValueOf(String varName, byte value) + public void setInt32ValueOf(String varName, int value) throws UnknownVariableException { setInt32ValueOf(getVariable(varName).addr, value); } @@ -285,7 +285,7 @@ public class VarMemory extends Memory { * @param varName Variable name * @param value 64 bit integer value to write */ - public void setInt64ValueOf(String varName, byte value) + public void setInt64ValueOf(String varName, long value) throws UnknownVariableException { setInt64ValueOf(getVariable(varName).addr, value); } From 33e86042e537f057b080e66393812a92d3a373ae Mon Sep 17 00:00:00 2001 From: Yasuyuki Tanaka Date: Tue, 6 Sep 2016 15:14:10 +0200 Subject: [PATCH 02/11] Support RADIO_PARAM_LAST_PACKET_TIMESTAMP with get_object() --- platform/cooja/dev/cooja-radio.c | 9 ++++++++- .../cooja/contikimote/interfaces/ContikiRadio.java | 3 +++ 2 files changed, 11 insertions(+), 1 deletion(-) diff --git a/platform/cooja/dev/cooja-radio.c b/platform/cooja/dev/cooja-radio.c index 9a969016d..bb7ad5afd 100644 --- a/platform/cooja/dev/cooja-radio.c +++ b/platform/cooja/dev/cooja-radio.c @@ -55,6 +55,7 @@ const struct simInterface radio_interface; char simReceiving = 0; char simInDataBuffer[COOJA_RADIO_BUFSIZE]; int simInSize = 0; +rtimer_clock_t simLastPacketTimestamp = 0; char simOutDataBuffer[COOJA_RADIO_BUFSIZE]; int simOutSize = 0; char simRadioHWOn = 1; @@ -287,7 +288,13 @@ 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) { - return RADIO_RESULT_NOT_SUPPORTED; + if(param == RADIO_PARAM_LAST_PACKET_TIMESTAMP) { + if(size != sizeof(rtimer_clock_t) || !dest) { + return RADIO_RESULT_INVALID_VALUE; + } + *(rtimer_clock_t *)dest = (rtimer_clock_t)simLastPacketTimestamp; + return RADIO_RESULT_OK; + } } /*---------------------------------------------------------------------------*/ static radio_result_t diff --git a/tools/cooja/java/org/contikios/cooja/contikimote/interfaces/ContikiRadio.java b/tools/cooja/java/org/contikios/cooja/contikimote/interfaces/ContikiRadio.java index bbc4a2abd..dd0775225 100644 --- a/tools/cooja/java/org/contikios/cooja/contikimote/interfaces/ContikiRadio.java +++ b/tools/cooja/java/org/contikios/cooja/contikimote/interfaces/ContikiRadio.java @@ -62,6 +62,7 @@ import org.contikios.cooja.util.CCITT_CRC; *

*

  • int simInSize (size of received data packet) *
  • byte[] simInDataBuffer (data of received data packet) + *
  • int64_t simLastPacketTimestamp (timestamp of the last received data packet) *

    *

  • int simOutSize (size of transmitted data packet) *
  • byte[] simOutDataBuffer (data of transmitted data packet) @@ -190,6 +191,8 @@ public class ContikiRadio extends Radio implements ContikiMoteInterface, PolledA lastEventTime = mote.getSimulation().getSimulationTime(); lastEvent = RadioEvent.RECEPTION_STARTED; + myMoteMemory.setInt64ValueOf("simLastPacketTimestamp", lastEventTime); + this.setChanged(); this.notifyObservers(); } From 830753f360ec83c4013cd9ea82a92d6e20c310d4 Mon Sep 17 00:00:00 2001 From: Yasuyuki Tanaka Date: Tue, 6 Sep 2016 15:14:10 +0200 Subject: [PATCH 03/11] cooja-radio: enable to turn off the turnaround and CCA features --- platform/cooja/dev/cooja-radio.c | 11 ++++------- platform/cooja/dev/cooja-radio.h | 12 ++++++++++++ 2 files changed, 16 insertions(+), 7 deletions(-) diff --git a/platform/cooja/dev/cooja-radio.c b/platform/cooja/dev/cooja-radio.c index bb7ad5afd..d1b0471a3 100644 --- a/platform/cooja/dev/cooja-radio.c +++ b/platform/cooja/dev/cooja-radio.c @@ -46,9 +46,6 @@ #define COOJA_RADIO_BUFSIZE PACKETBUF_SIZE #define CCA_SS_THRESHOLD -95 -#define WITH_TURNAROUND 1 -#define WITH_SEND_CCA 1 - const struct simInterface radio_interface; /* COOJA */ @@ -174,14 +171,14 @@ radio_send(const void *payload, unsigned short payload_len) int radiostate = simRadioHWOn; /* Simulate turnaround time of 2ms for packets, 1ms for acks*/ -#if WITH_TURNAROUND +#if COOJA_SIMULATE_TURNAROUND simProcessRunValue = 1; cooja_mt_yield(); if(payload_len > 3) { simProcessRunValue = 1; cooja_mt_yield(); } -#endif /* WITH_TURNAROUND */ +#endif /* COOJA_SIMULATE_TURNAROUND */ if(!simRadioHWOn) { /* Turn on radio temporarily */ @@ -198,11 +195,11 @@ radio_send(const void *payload, unsigned short payload_len) } /* Transmit on CCA */ -#if WITH_SEND_CCA +#if COOJA_TRANSMIT_ON_CCA if(!channel_clear()) { return RADIO_TX_COLLISION; } -#endif /* WITH_SEND_CCA */ +#endif /* COOJA_TRANSMIT_ON_CCA */ /* Copy packet data to temporary storage */ memcpy(simOutDataBuffer, payload, payload_len); diff --git a/platform/cooja/dev/cooja-radio.h b/platform/cooja/dev/cooja-radio.h index b6bfb3aaf..a65a61bb1 100644 --- a/platform/cooja/dev/cooja-radio.h +++ b/platform/cooja/dev/cooja-radio.h @@ -36,6 +36,18 @@ #include "contiki.h" #include "dev/radio.h" +#ifdef COOJA_CONF_SIMULATE_TURNAROUND +#define COOJA_SIMULATE_TURNAROUND COOJA_CONF_SIMULATE_TURNAROUND +#else +#define COOJA_SIMULATE_TURNAROUND 1 +#endif + +#ifdef COOJA_CONF_TRANSMIT_ON_CCA +#define COOJA_TRANSMIT_ON_CCA COOJA_CONF_TRANSMIT_ON_CCA +#else +#define COOJA_TRANSMIT_ON_CCA 1 +#endif + extern const struct radio_driver cooja_radio_driver; /** From 671b1cd9b86d5e3ac86885d8fbf6ceb83c136889 Mon Sep 17 00:00:00 2001 From: Yasuyuki Tanaka Date: Tue, 6 Sep 2016 15:14:10 +0200 Subject: [PATCH 04/11] Support the radio features required for TSCH --- platform/cooja/dev/cooja-radio.c | 109 +++++++++++++++++++++++++++++-- 1 file changed, 103 insertions(+), 6 deletions(-) diff --git a/platform/cooja/dev/cooja-radio.c b/platform/cooja/dev/cooja-radio.c index d1b0471a3..56ff00aba 100644 --- a/platform/cooja/dev/cooja-radio.c +++ b/platform/cooja/dev/cooja-radio.c @@ -64,8 +64,37 @@ int simLQI = 105; static const void *pending_data; -PROCESS(cooja_radio_process, "cooja radio process"); +/* If we are in the polling mode, poll_mode is 1; otherwise 0 */ +static int poll_mode = 0; /* default 0, disabled */ +static int auto_ack = 0; /* AUTO_ACK is not supported; always 0 */ +static int addr_filter = 0; /* ADDRESS_FILTER is not supported; always 0 */ +static int send_on_cca = (COOJA_TRANSMIT_ON_CCA != 0); +PROCESS(cooja_radio_process, "cooja radio process"); +/*---------------------------------------------------------------------------*/ +static void +set_send_on_cca(uint8_t enable) +{ + send_on_cca = enable; +} +/*---------------------------------------------------------------------------*/ +static void +set_frame_filtering(int enable) +{ + addr_filter = enable; +} +/*---------------------------------------------------------------------------*/ +static void +set_auto_ack(int enable) +{ + auto_ack = enable; +} +/*---------------------------------------------------------------------------*/ +static void +set_poll_mode(int enable) +{ + poll_mode = enable; +} /*---------------------------------------------------------------------------*/ void radio_set_channel(int channel) @@ -150,8 +179,10 @@ radio_read(void *buf, unsigned short bufsize) memcpy(buf, simInDataBuffer, simInSize); simInSize = 0; - packetbuf_set_attr(PACKETBUF_ATTR_RSSI, simSignalStrength); - packetbuf_set_attr(PACKETBUF_ATTR_LINK_QUALITY, simLQI); + if(!poll_mode) { + packetbuf_set_attr(PACKETBUF_ATTR_RSSI, simSignalStrength); + packetbuf_set_attr(PACKETBUF_ATTR_LINK_QUALITY, simLQI); + } return tmp; } @@ -196,7 +227,7 @@ radio_send(const void *payload, unsigned short payload_len) /* Transmit on CCA */ #if COOJA_TRANSMIT_ON_CCA - if(!channel_clear()) { + if(send_on_cca && !channel_clear()) { return RADIO_TX_COLLISION; } #endif /* COOJA_TRANSMIT_ON_CCA */ @@ -251,6 +282,9 @@ PROCESS_THREAD(cooja_radio_process, ev, data) while(1) { PROCESS_YIELD_UNTIL(ev == PROCESS_EVENT_POLL); + if(poll_mode) { + continue; + } packetbuf_clear(); len = radio_read(packetbuf_dataptr(), PACKETBUF_SIZE); @@ -273,13 +307,75 @@ init(void) static radio_result_t get_value(radio_param_t param, radio_value_t *value) { - return RADIO_RESULT_NOT_SUPPORTED; + switch(param) { + case RADIO_PARAM_RX_MODE: + *value = 0; + if(addr_filter) { + *value |= RADIO_RX_MODE_ADDRESS_FILTER; + } + if(auto_ack) { + *value |= RADIO_RX_MODE_AUTOACK; + } + if(poll_mode) { + *value |= RADIO_RX_MODE_POLL_MODE; + } + return RADIO_RESULT_OK; + case RADIO_PARAM_TX_MODE: + *value = 0; + if(send_on_cca) { + *value |= RADIO_TX_MODE_SEND_ON_CCA; + } + return RADIO_RESULT_OK; + case RADIO_PARAM_LAST_RSSI: + *value = simSignalStrength; + return RADIO_RESULT_OK; + case RADIO_PARAM_LAST_LINK_QUALITY: + *value = simLQI; + return RADIO_RESULT_OK; + default: + return RADIO_RESULT_NOT_SUPPORTED; + } } /*---------------------------------------------------------------------------*/ static radio_result_t set_value(radio_param_t param, radio_value_t value) { - return RADIO_RESULT_NOT_SUPPORTED; + switch(param) { + case RADIO_PARAM_RX_MODE: + if(value & ~(RADIO_RX_MODE_ADDRESS_FILTER | + RADIO_RX_MODE_AUTOACK | RADIO_RX_MODE_POLL_MODE)) { + return RADIO_RESULT_INVALID_VALUE; + } + + /* Only disabling is acceptable for RADIO_RX_MODE_ADDRESS_FILTER */ + if ((value & RADIO_RX_MODE_ADDRESS_FILTER) != 0) { + return RADIO_RESULT_NOT_SUPPORTED; + } + set_frame_filtering((value & RADIO_RX_MODE_ADDRESS_FILTER) != 0); + + /* Only disabling is acceptable for RADIO_RX_MODE_AUTOACK */ + if ((value & RADIO_RX_MODE_ADDRESS_FILTER) != 0) { + return RADIO_RESULT_NOT_SUPPORTED; + } + set_auto_ack((value & RADIO_RX_MODE_AUTOACK) != 0); + + set_poll_mode((value & RADIO_RX_MODE_POLL_MODE) != 0); + return RADIO_RESULT_OK; + case RADIO_PARAM_TX_MODE: + if(value & ~(RADIO_TX_MODE_SEND_ON_CCA)) { + return RADIO_RESULT_INVALID_VALUE; + } + set_send_on_cca((value & RADIO_TX_MODE_SEND_ON_CCA) != 0); + return RADIO_RESULT_OK; + case RADIO_PARAM_CHANNEL: + if(value < 11 || value > 26) { + return RADIO_RESULT_INVALID_VALUE; + } + radio_set_channel(value); + return RADIO_RESULT_OK; + default: + return RADIO_RESULT_NOT_SUPPORTED; + } } /*---------------------------------------------------------------------------*/ static radio_result_t @@ -292,6 +388,7 @@ get_object(radio_param_t param, void *dest, size_t size) *(rtimer_clock_t *)dest = (rtimer_clock_t)simLastPacketTimestamp; return RADIO_RESULT_OK; } + return RADIO_RESULT_NOT_SUPPORTED; } /*---------------------------------------------------------------------------*/ static radio_result_t From 38c538205426738b36cde608b62c66d7c6d708fd Mon Sep 17 00:00:00 2001 From: Yasuyuki Tanaka Date: Tue, 6 Sep 2016 15:14:10 +0200 Subject: [PATCH 05/11] Add timing macros required for TSCH --- platform/cooja/contiki-conf.h | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/platform/cooja/contiki-conf.h b/platform/cooja/contiki-conf.h index 91c93a3b4..7d107a0b1 100644 --- a/platform/cooja/contiki-conf.h +++ b/platform/cooja/contiki-conf.h @@ -203,6 +203,10 @@ typedef unsigned long clock_time_t; typedef unsigned long rtimer_clock_t; #define RTIMER_CLOCK_DIFF(a,b) ((signed long)((a)-(b))) +#define RADIO_DELAY_BEFORE_TX 0 +#define RADIO_DELAY_BEFORE_RX 0 +#define RADIO_DELAY_BEFORE_DETECT 0 + #define AODV_COMPLIANCE #define AODV_NUM_RT_ENTRIES 32 From 958ff6e4f643fe86c84507e5cdde99b53a2d0c0a Mon Sep 17 00:00:00 2001 From: Yasuyuki Tanaka Date: Tue, 6 Sep 2016 15:14:10 +0200 Subject: [PATCH 06/11] Fix indentation in cooja-radio.c --- platform/cooja/dev/cooja-radio.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/platform/cooja/dev/cooja-radio.c b/platform/cooja/dev/cooja-radio.c index 56ff00aba..51c4160a6 100644 --- a/platform/cooja/dev/cooja-radio.c +++ b/platform/cooja/dev/cooja-radio.c @@ -124,7 +124,7 @@ radio_signal_strength_current(void) int radio_LQI(void) { - return simLQI; + return simLQI; } /*---------------------------------------------------------------------------*/ static int @@ -416,5 +416,5 @@ const struct radio_driver cooja_radio_driver = }; /*---------------------------------------------------------------------------*/ SIM_INTERFACE(radio_interface, - doInterfaceActionsBeforeTick, - doInterfaceActionsAfterTick); + doInterfaceActionsBeforeTick, + doInterfaceActionsAfterTick); From 02012086645caa73eccf218bdb630aaa105b23c2 Mon Sep 17 00:00:00 2001 From: Yasuyuki Tanaka Date: Tue, 6 Sep 2016 15:14:10 +0200 Subject: [PATCH 07/11] TSCH: manage busy waiting on Cooja motes --- core/net/mac/tsch/tsch-private.h | 13 ++++++++++++- core/net/mac/tsch/tsch-slot-operation.c | 16 ++++++++++++++-- 2 files changed, 26 insertions(+), 3 deletions(-) diff --git a/core/net/mac/tsch/tsch-private.h b/core/net/mac/tsch/tsch-private.h index 4a26abff3..44c928ae7 100644 --- a/core/net/mac/tsch/tsch-private.h +++ b/core/net/mac/tsch/tsch-private.h @@ -48,6 +48,10 @@ #include "net/linkaddr.h" #include "net/mac/tsch/tsch-asn.h" #include "net/mac/tsch/tsch-conf.h" +#if CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 +#include "lib/simEnvChange.h" +#include "sys/cooja_mt.h" +#endif /* CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 */ /************ Types ***********/ @@ -109,7 +113,14 @@ void tsch_disassociate(void); #define TSCH_CLOCK_TO_SLOTS(c, timeslot_length) (TSCH_CLOCK_TO_TICKS(c) / timeslot_length) /* Wait for a condition with timeout t0+offset. */ +#if CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 +#define BUSYWAIT_UNTIL_ABS(cond, t0, offset) \ + while(!(cond) && RTIMER_CLOCK_LT(RTIMER_NOW(), (t0) + (offset))) { \ + simProcessRunValue = 1; \ + cooja_mt_yield(); \ + }; +#else #define BUSYWAIT_UNTIL_ABS(cond, t0, offset) \ while(!(cond) && RTIMER_CLOCK_LT(RTIMER_NOW(), (t0) + (offset))) ; - +#endif /* CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 */ #endif /* __TSCH_PRIVATE_H__ */ diff --git a/core/net/mac/tsch/tsch-slot-operation.c b/core/net/mac/tsch/tsch-slot-operation.c index 62a7942f4..90e0fcad0 100644 --- a/core/net/mac/tsch/tsch-slot-operation.c +++ b/core/net/mac/tsch/tsch-slot-operation.c @@ -54,6 +54,10 @@ #include "net/mac/tsch/tsch-packet.h" #include "net/mac/tsch/tsch-security.h" #include "net/mac/tsch/tsch-adaptive-timesync.h" +#if CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 +#include "lib/simEnvChange.h" +#include "sys/cooja_mt.h" +#endif /* CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 */ #if TSCH_LOG_LEVEL >= 1 #define DEBUG DEBUG_PRINT @@ -104,7 +108,10 @@ #if RTIMER_SECOND < (32 * 1024) #error "TSCH: RTIMER_SECOND < (32 * 1024)" #endif -#if RTIMER_SECOND >= 200000 +#if CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 +/* Use 0 usec guard time for Cooja Mote with a 1 MHz Rtimer*/ +#define RTIMER_GUARD 0u +#elif RTIMER_SECOND >= 200000 #define RTIMER_GUARD (RTIMER_SECOND / 100000) #else #define RTIMER_GUARD 2u @@ -200,7 +207,12 @@ tsch_get_lock(void) if(tsch_in_slot_operation) { busy_wait = 1; busy_wait_time = RTIMER_NOW(); - while(tsch_in_slot_operation); + while(tsch_in_slot_operation) { +#if CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 + simProcessRunValue = 1; + cooja_mt_yield(); +#endif /* CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 */ + } busy_wait_time = RTIMER_NOW() - busy_wait_time; } if(!tsch_locked) { From 6d51c5f58e78d02b2e782849c7f64792dc63b301 Mon Sep 17 00:00:00 2001 From: Yasuyuki Tanaka Date: Tue, 6 Sep 2016 15:14:10 +0200 Subject: [PATCH 08/11] Reimplement Rtimer of Cooja mote as a microsecond resolution timer --- platform/cooja-ip64/contiki-cooja-ip64-main.c | 19 ++------- platform/cooja/contiki-conf.h | 4 +- platform/cooja/contiki-cooja-main.c | 19 ++------- platform/cooja/lib/simEnvChange.c | 2 +- platform/cooja/lib/simEnvChange.h | 2 +- platform/cooja/rtimer-arch.c | 35 ++++++---------- platform/cooja/rtimer-arch.h | 5 ++- .../contikimote/interfaces/ContikiClock.java | 40 +++++++++++++------ 8 files changed, 55 insertions(+), 71 deletions(-) diff --git a/platform/cooja-ip64/contiki-cooja-ip64-main.c b/platform/cooja-ip64/contiki-cooja-ip64-main.c index 02576a3be..d2d42ae9f 100644 --- a/platform/cooja-ip64/contiki-cooja-ip64-main.c +++ b/platform/cooja-ip64/contiki-cooja-ip64-main.c @@ -376,9 +376,6 @@ Java_org_contikios_cooja_corecomm_CLASSNAME_setMemory(JNIEnv *env, jobject obj, JNIEXPORT void JNICALL Java_org_contikios_cooja_corecomm_CLASSNAME_tick(JNIEnv *env, jobject obj) { - clock_time_t nextEtimer; - rtimer_clock_t nextRtimer; - simProcessRunValue = 0; /* Let all simulation interfaces act first */ @@ -403,21 +400,11 @@ Java_org_contikios_cooja_corecomm_CLASSNAME_tick(JNIEnv *env, jobject obj) doActionsAfterTick(); /* Do we have any pending timers */ - simEtimerPending = etimer_pending() || rtimer_arch_pending(); - if(!simEtimerPending) { - return; - } + simEtimerPending = etimer_pending(); /* Save nearest expiration time */ - nextEtimer = etimer_next_expiration_time() - (clock_time_t) simCurrentTime; - nextRtimer = rtimer_arch_next() - (rtimer_clock_t) simCurrentTime; - if(etimer_pending() && rtimer_arch_pending()) { - simNextExpirationTime = MIN(nextEtimer, nextRtimer); - } else if(etimer_pending()) { - simNextExpirationTime = nextEtimer; - } else if(rtimer_arch_pending()) { - simNextExpirationTime = nextRtimer; - } + simEtimerNextExpirationTime = etimer_next_expiration_time(); + } /*---------------------------------------------------------------------------*/ /** diff --git a/platform/cooja/contiki-conf.h b/platform/cooja/contiki-conf.h index 7d107a0b1..430f27a69 100644 --- a/platform/cooja/contiki-conf.h +++ b/platform/cooja/contiki-conf.h @@ -200,8 +200,8 @@ typedef unsigned short uip_stats_t; #define CLOCK_CONF_SECOND 1000L typedef unsigned long clock_time_t; -typedef unsigned long rtimer_clock_t; -#define RTIMER_CLOCK_DIFF(a,b) ((signed long)((a)-(b))) +typedef uint64_t rtimer_clock_t; +#define RTIMER_CLOCK_DIFF(a,b) ((int64_t)((a)-(b))) #define RADIO_DELAY_BEFORE_TX 0 #define RADIO_DELAY_BEFORE_RX 0 diff --git a/platform/cooja/contiki-cooja-main.c b/platform/cooja/contiki-cooja-main.c index 40dd49d1c..9a1e60e4c 100644 --- a/platform/cooja/contiki-cooja-main.c +++ b/platform/cooja/contiki-cooja-main.c @@ -452,9 +452,6 @@ Java_org_contikios_cooja_corecomm_CLASSNAME_setMemory(JNIEnv *env, jobject obj, JNIEXPORT void JNICALL Java_org_contikios_cooja_corecomm_CLASSNAME_tick(JNIEnv *env, jobject obj) { - clock_time_t nextEtimer; - rtimer_clock_t nextRtimer; - simProcessRunValue = 0; /* Let all simulation interfaces act first */ @@ -479,21 +476,11 @@ Java_org_contikios_cooja_corecomm_CLASSNAME_tick(JNIEnv *env, jobject obj) doActionsAfterTick(); /* Do we have any pending timers */ - simEtimerPending = etimer_pending() || rtimer_arch_pending(); - if(!simEtimerPending) { - return; - } + simEtimerPending = etimer_pending(); /* Save nearest expiration time */ - nextEtimer = etimer_next_expiration_time() - (clock_time_t) simCurrentTime; - nextRtimer = rtimer_arch_next() - (rtimer_clock_t) simCurrentTime; - if(etimer_pending() && rtimer_arch_pending()) { - simNextExpirationTime = MIN(nextEtimer, nextRtimer); - } else if(etimer_pending()) { - simNextExpirationTime = nextEtimer; - } else if(rtimer_arch_pending()) { - simNextExpirationTime = nextRtimer; - } + simEtimerNextExpirationTime = etimer_next_expiration_time(); + } /*---------------------------------------------------------------------------*/ /** diff --git a/platform/cooja/lib/simEnvChange.c b/platform/cooja/lib/simEnvChange.c index c9fbd438f..f6060b449 100644 --- a/platform/cooja/lib/simEnvChange.c +++ b/platform/cooja/lib/simEnvChange.c @@ -40,7 +40,7 @@ char simDontFallAsleep = 0; int simProcessRunValue; int simEtimerPending; -clock_time_t simNextExpirationTime; +clock_time_t simEtimerNextExpirationTime; void doActionsBeforeTick() { // Poll all interfaces to do their thing before the tick diff --git a/platform/cooja/lib/simEnvChange.h b/platform/cooja/lib/simEnvChange.h index 35189a42d..7723eb16f 100644 --- a/platform/cooja/lib/simEnvChange.h +++ b/platform/cooja/lib/simEnvChange.h @@ -42,7 +42,7 @@ struct simInterface { // Variable for keeping the last process_run() return value extern int simProcessRunValue; extern int simEtimerPending; -extern clock_time_t simNextExpirationTime; +extern clock_time_t simEtimerNextExpirationTime; extern clock_time_t simCurrentTime; // Variable that when set to != 0, stops the mote from falling asleep next tick diff --git a/platform/cooja/rtimer-arch.c b/platform/cooja/rtimer-arch.c index dff66fdc7..9d4f77646 100644 --- a/platform/cooja/rtimer-arch.c +++ b/platform/cooja/rtimer-arch.c @@ -48,46 +48,44 @@ #define PRINTF(...) #endif -extern clock_time_t simCurrentTime; - -static int pending_rtimer = 0; -static rtimer_clock_t next_rtimer = 0; -static clock_time_t last_rtimer_now = 0; +/* COOJA */ +int simRtimerPending; +rtimer_clock_t simRtimerNextExpirationTime; +rtimer_clock_t simRtimerCurrentTicks; /*---------------------------------------------------------------------------*/ void rtimer_arch_init(void) { - next_rtimer = 0; - last_rtimer_now = 0; - pending_rtimer = 0; + simRtimerNextExpirationTime = 0; + simRtimerPending = 0; } /*---------------------------------------------------------------------------*/ void rtimer_arch_schedule(rtimer_clock_t t) { - next_rtimer = t; - pending_rtimer = 1; + simRtimerNextExpirationTime = t; + simRtimerPending = 1; } /*---------------------------------------------------------------------------*/ rtimer_clock_t rtimer_arch_next(void) { - return next_rtimer; + return simRtimerNextExpirationTime; } /*---------------------------------------------------------------------------*/ int rtimer_arch_pending(void) { - return pending_rtimer; + return simRtimerPending; } /*---------------------------------------------------------------------------*/ int rtimer_arch_check(void) { - if (simCurrentTime == next_rtimer) { + if (simRtimerCurrentTicks == simRtimerNextExpirationTime) { /* Execute rtimer */ - pending_rtimer = 0; + simRtimerPending = 0; rtimer_run_next(); return 1; } @@ -97,14 +95,7 @@ rtimer_arch_check(void) rtimer_clock_t rtimer_arch_now(void) { - if(last_rtimer_now == simCurrentTime) { - /* Yield to COOJA, to allow time to change */ - simProcessRunValue = 1; - simNextExpirationTime = simCurrentTime + 1; - cooja_mt_yield(); - } - last_rtimer_now = simCurrentTime; - return simCurrentTime; + return simRtimerCurrentTicks; } /*---------------------------------------------------------------------------*/ diff --git a/platform/cooja/rtimer-arch.h b/platform/cooja/rtimer-arch.h index 616ad4185..390e1ac56 100644 --- a/platform/cooja/rtimer-arch.h +++ b/platform/cooja/rtimer-arch.h @@ -36,7 +36,10 @@ #include "contiki-conf.h" #include "sys/clock.h" -#define RTIMER_ARCH_SECOND CLOCK_CONF_SECOND +#define RTIMER_ARCH_SECOND UINT64_C(1000000) + +#define US_TO_RTIMERTICKS(US) (US) +#define RTIMERTICKS_TO_US(T) (T) rtimer_clock_t rtimer_arch_now(void); int rtimer_arch_check(void); diff --git a/tools/cooja/java/org/contikios/cooja/contikimote/interfaces/ContikiClock.java b/tools/cooja/java/org/contikios/cooja/contikimote/interfaces/ContikiClock.java index b033ef06d..97cbc61c3 100644 --- a/tools/cooja/java/org/contikios/cooja/contikimote/interfaces/ContikiClock.java +++ b/tools/cooja/java/org/contikios/cooja/contikimote/interfaces/ContikiClock.java @@ -52,8 +52,11 @@ import org.contikios.cooja.mote.memory.VarMemory; * Contiki variables: *
      *
    • clock_time_t simCurrentTime - *
    • clock_time_t simNextExpirationTime - *
    • int simProcessRunValue + *
    • rtimer_clock_t simRtimerCurrentTicks + *
    • clock_time_t simEtimerNextExpirationTime + *
    • rtimer_clock_t simEtimerNextExpirationTime + *
    • int simEtimerProcessRunValue + *
    • int simRtimerProcessRunValue *
    • int simEtimerPending *
    * @@ -125,16 +128,24 @@ public class ContikiClock extends Clock implements ContikiMoteInterface, PolledB public void doActionsBeforeTick() { /* Update time */ - setTime(mote.getSimulation().getSimulationTime() + timeDrift); + long currentSimulationTime = simulation.getSimulationTime(); + setTime(currentSimulationTime + timeDrift); + moteMem.setInt64ValueOf("simRtimerCurrentTicks", currentSimulationTime); } public void doActionsAfterTick() { + long currentSimulationTime = mote.getSimulation().getSimulationTime(); + + /* Always schedule for Rtimer if anything pending */ + if (moteMem.getIntValueOf("simRtimerPending") != 0) { + mote.scheduleNextWakeup(moteMem.getInt64ValueOf("simRtimerNextExpirationTime")); + } /* Request next tick for remaining events / timers */ int processRunValue = moteMem.getIntValueOf("simProcessRunValue"); if (processRunValue != 0) { /* Handle next Contiki event in one millisecond */ - mote.scheduleNextWakeup(simulation.getSimulationTime() + Simulation.MILLISECOND); + mote.scheduleNextWakeup(currentSimulationTime + Simulation.MILLISECOND); return; } @@ -144,15 +155,20 @@ public class ContikiClock extends Clock implements ContikiMoteInterface, PolledB return; } - /* Request tick next wakeup time */ - int nextExpirationTime = moteMem.getIntValueOf("simNextExpirationTime"); - if (nextExpirationTime <= 0) { - /*logger.warn("Event timer already expired, but has been delayed: " + nextExpirationTime);*/ - mote.scheduleNextWakeup(simulation.getSimulationTime() + Simulation.MILLISECOND); - return; + /* Request tick next wakeup time for Etimer */ + long etimerNextExpirationTime = (long)moteMem.getInt32ValueOf("simEtimerNextExpirationTime") * Simulation.MILLISECOND; + long etimerTimeToNextExpiration = etimerNextExpirationTime - moteTime; + if (etimerTimeToNextExpiration <= 0) { + /* logger.warn(mote.getID() + ": Event timer already expired, but has been delayed: " + etimerTimeToNextExpiration); */ + /* Wake up in one millisecond to handle a missed Etimer task + * which may be blocked by busy waiting such as one in + * radio_send(). Scheduling it in a shorter time than one + * millisecond, e.g., one microsecond, seems to be worthless and + * it would cause unnecessary CPU usage. */ + mote.scheduleNextWakeup(currentSimulationTime + Simulation.MILLISECOND); + } else { + mote.scheduleNextWakeup(currentSimulationTime + etimerTimeToNextExpiration); } - - mote.scheduleNextWakeup(simulation.getSimulationTime() + Simulation.MILLISECOND*nextExpirationTime); } From 6869dc7004db1987ef290d37481cb5d1b4761db8 Mon Sep 17 00:00:00 2001 From: Yasuyuki Tanaka Date: Tue, 6 Sep 2016 15:14:10 +0200 Subject: [PATCH 09/11] Yield inside busywaiting loops under cooja-ip64 (nullrdc.c) The while loops waiting ACK_WAIT_TIME and AFTER_ACK_DETECTED_WAIT_TIME cause infinite loop under the cooja-ip64 platform. This is because RTIMER_NOW(), rtimer_arch_now(), has been changed not to call cooja_mt_yield() in it since rtimer was reimplemented as a higher resolution timer. In order to avoid the infinite loop, cooja_mt_yield() needs to be called inside the while loops under the platform as well as the cooja platform. --- core/net/mac/nullrdc.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/core/net/mac/nullrdc.c b/core/net/mac/nullrdc.c index 5cec23a3d..a8d83aa66 100644 --- a/core/net/mac/nullrdc.c +++ b/core/net/mac/nullrdc.c @@ -46,10 +46,10 @@ #include "net/rime/rimestats.h" #include -#if CONTIKI_TARGET_COOJA +#if CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 #include "lib/simEnvChange.h" #include "sys/cooja_mt.h" -#endif /* CONTIKI_TARGET_COOJA */ +#endif /* CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 */ #define DEBUG 0 #if DEBUG @@ -158,10 +158,10 @@ send_one_packet(mac_callback_t sent, void *ptr) wt = RTIMER_NOW(); watchdog_periodic(); while(RTIMER_CLOCK_LT(RTIMER_NOW(), wt + ACK_WAIT_TIME)) { -#if CONTIKI_TARGET_COOJA +#if CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 simProcessRunValue = 1; cooja_mt_yield(); -#endif /* CONTIKI_TARGET_COOJA */ +#endif /* CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 */ } ret = MAC_TX_NOACK; @@ -176,10 +176,10 @@ send_one_packet(mac_callback_t sent, void *ptr) watchdog_periodic(); while(RTIMER_CLOCK_LT(RTIMER_NOW(), wt + AFTER_ACK_DETECTED_WAIT_TIME)) { - #if CONTIKI_TARGET_COOJA + #if CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 simProcessRunValue = 1; cooja_mt_yield(); - #endif /* CONTIKI_TARGET_COOJA */ + #endif /* CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 */ } } From 0ff474e39386acaecd6558128c5fedb9c3b45fc8 Mon Sep 17 00:00:00 2001 From: Yasuyuki Tanaka Date: Tue, 6 Sep 2016 15:14:10 +0200 Subject: [PATCH 10/11] Fix indentation in nullrdc.c --- core/net/mac/nullrdc.c | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/core/net/mac/nullrdc.c b/core/net/mac/nullrdc.c index a8d83aa66..7ba62a428 100644 --- a/core/net/mac/nullrdc.c +++ b/core/net/mac/nullrdc.c @@ -176,10 +176,10 @@ send_one_packet(mac_callback_t sent, void *ptr) watchdog_periodic(); while(RTIMER_CLOCK_LT(RTIMER_NOW(), wt + AFTER_ACK_DETECTED_WAIT_TIME)) { - #if CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 - simProcessRunValue = 1; - cooja_mt_yield(); - #endif /* CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 */ +#if CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 + simProcessRunValue = 1; + cooja_mt_yield(); +#endif /* CONTIKI_TARGET_COOJA || CONTIKI_TARGET_COOJA_IP64 */ } } @@ -195,8 +195,8 @@ send_one_packet(mac_callback_t sent, void *ptr) } } } else { - PRINTF("nullrdc tx noack\n"); - } + PRINTF("nullrdc tx noack\n"); + } } break; case RADIO_TX_COLLISION: @@ -303,7 +303,7 @@ packet_input(void) } #endif /* RDC_WITH_DUPLICATE_DETECTION */ #endif /* NULLRDC_802154_AUTOACK */ - + #if NULLRDC_SEND_802154_ACK { frame802154_t info154; From 30ddd97124a70239536eb32c305e515f5adc54c6 Mon Sep 17 00:00:00 2001 From: Yasuyuki Tanaka Date: Tue, 6 Sep 2016 15:14:10 +0200 Subject: [PATCH 11/11] TSCH: add a sample .csc file and configuration for Cooja mote --- examples/ipv6/rpl-tsch/project-conf.h | 4 + examples/ipv6/rpl-tsch/rpl-tsch-cooja.csc | 279 ++++++++++++++++++++++ 2 files changed, 283 insertions(+) create mode 100644 examples/ipv6/rpl-tsch/rpl-tsch-cooja.csc diff --git a/examples/ipv6/rpl-tsch/project-conf.h b/examples/ipv6/rpl-tsch/project-conf.h index d1af39604..972e86c3d 100644 --- a/examples/ipv6/rpl-tsch/project-conf.h +++ b/examples/ipv6/rpl-tsch/project-conf.h @@ -181,4 +181,8 @@ #endif /* CONTIKI_TARGET_CC2538DK || CONTIKI_TARGET_ZOUL \ || CONTIKI_TARGET_OPENMOTE_CC2538 */ +#if CONTIKI_TARGET_COOJA +#define COOJA_CONF_SIMULATE_TURNAROUND 0 +#endif /* CONTIKI_TARGET_COOJA */ + #endif /* __PROJECT_CONF_H__ */ diff --git a/examples/ipv6/rpl-tsch/rpl-tsch-cooja.csc b/examples/ipv6/rpl-tsch/rpl-tsch-cooja.csc new file mode 100644 index 000000000..a07dd15bd --- /dev/null +++ b/examples/ipv6/rpl-tsch/rpl-tsch-cooja.csc @@ -0,0 +1,279 @@ + + + [APPS_DIR]/mrm + [APPS_DIR]/mspsim + [APPS_DIR]/avrora + [APPS_DIR]/serial_socket + [APPS_DIR]/collect-view + [APPS_DIR]/powertracker + [APPS_DIR]/radiologger-headless + + RPL+TSCH + 123456 + 1000000 + + org.contikios.cooja.radiomediums.UDGM + 50.0 + 100.0 + 1.0 + 1.0 + + + 40000 + + + org.contikios.cooja.contikimote.ContikiMoteType + mtype660 + Cooja Mote Type #z11 + [CONTIKI_DIR]/examples/ipv6/rpl-tsch/node.c + make TARGET=cooja clean + make TARGET=cooja node.cooja + org.contikios.cooja.interfaces.Position + org.contikios.cooja.interfaces.Battery + org.contikios.cooja.contikimote.interfaces.ContikiVib + org.contikios.cooja.contikimote.interfaces.ContikiMoteID + org.contikios.cooja.contikimote.interfaces.ContikiRS232 + org.contikios.cooja.contikimote.interfaces.ContikiBeeper + org.contikios.cooja.interfaces.RimeAddress + org.contikios.cooja.contikimote.interfaces.ContikiIPAddress + org.contikios.cooja.contikimote.interfaces.ContikiRadio + org.contikios.cooja.contikimote.interfaces.ContikiButton + org.contikios.cooja.contikimote.interfaces.ContikiPIR + org.contikios.cooja.contikimote.interfaces.ContikiClock + org.contikios.cooja.contikimote.interfaces.ContikiLED + org.contikios.cooja.contikimote.interfaces.ContikiCFS + org.contikios.cooja.interfaces.Mote2MoteRelations + org.contikios.cooja.interfaces.MoteAttributes + false + + + + org.contikios.cooja.interfaces.Position + -1.285769821276336 + 38.58045647334346 + 0.0 + + + org.contikios.cooja.contikimote.interfaces.ContikiMoteID + 1 + + + org.contikios.cooja.contikimote.interfaces.ContikiRadio + 250.0 + + mtype660 + + + + org.contikios.cooja.interfaces.Position + -19.324109516886306 + 76.23135780254927 + 0.0 + + + org.contikios.cooja.contikimote.interfaces.ContikiMoteID + 2 + + + org.contikios.cooja.contikimote.interfaces.ContikiRadio + 250.0 + + mtype660 + + + + org.contikios.cooja.interfaces.Position + 5.815501305791592 + 76.77463755494317 + 0.0 + + + org.contikios.cooja.contikimote.interfaces.ContikiMoteID + 3 + + + org.contikios.cooja.contikimote.interfaces.ContikiRadio + 250.0 + + mtype660 + + + + org.contikios.cooja.interfaces.Position + 31.920697784030082 + 50.5212265977149 + 0.0 + + + org.contikios.cooja.contikimote.interfaces.ContikiMoteID + 4 + + + org.contikios.cooja.contikimote.interfaces.ContikiRadio + 250.0 + + mtype660 + + + + org.contikios.cooja.interfaces.Position + 47.21747673247198 + 30.217765340599726 + 0.0 + + + org.contikios.cooja.contikimote.interfaces.ContikiMoteID + 5 + + + org.contikios.cooja.contikimote.interfaces.ContikiRadio + 250.0 + + mtype660 + + + + org.contikios.cooja.interfaces.Position + 10.622284947035123 + 109.81862399725188 + 0.0 + + + org.contikios.cooja.contikimote.interfaces.ContikiMoteID + 6 + + + org.contikios.cooja.contikimote.interfaces.ContikiRadio + 250.0 + + mtype660 + + + + org.contikios.cooja.interfaces.Position + 52.41150716335335 + 109.93228340481916 + 0.0 + + + org.contikios.cooja.contikimote.interfaces.ContikiMoteID + 7 + + + org.contikios.cooja.contikimote.interfaces.ContikiRadio + 250.0 + + mtype660 + + + + org.contikios.cooja.interfaces.Position + 70.18727461718498 + 70.06861701541145 + 0.0 + + + org.contikios.cooja.contikimote.interfaces.ContikiMoteID + 8 + + + org.contikios.cooja.contikimote.interfaces.ContikiRadio + 250.0 + + mtype660 + + + + org.contikios.cooja.interfaces.Position + 80.29870484201041 + 99.37351603835938 + 0.0 + + + org.contikios.cooja.contikimote.interfaces.ContikiMoteID + 9 + + + org.contikios.cooja.contikimote.interfaces.ContikiRadio + 250.0 + + mtype660 + + + + org.contikios.cooja.plugins.SimControl + 242 + 4 + 160 + 11 + 241 + + + org.contikios.cooja.plugins.Visualizer + + true + org.contikios.cooja.plugins.skins.IDVisualizerSkin + org.contikios.cooja.plugins.skins.GridVisualizerSkin + org.contikios.cooja.plugins.skins.TrafficVisualizerSkin + org.contikios.cooja.plugins.skins.UDGMVisualizerSkin + 1.7405603810040515 0.0 0.0 1.7405603810040515 47.95980153208088 -42.576134155447555 + + 236 + 3 + 230 + 1 + 1 + + + org.contikios.cooja.plugins.LogListener + + + + + + 1031 + 0 + 394 + 273 + 6 + + + org.contikios.cooja.plugins.TimeLine + + 0 + 1 + 2 + 3 + 4 + 5 + 6 + 7 + 8 + + + + 16529.88882215865 + + 1304 + 2 + 311 + 0 + 412 + + + org.contikios.cooja.plugins.RadioLogger + + 150 + + false + false + + + 500 + 1 + 300 + 30 + 442 + + +