From 94bccaef692bb0dfe47c149d2f3c4c1476e3e0ea Mon Sep 17 00:00:00 2001 From: kusy Date: Thu, 16 Jul 2009 06:59:38 +0000 Subject: [PATCH] Reorganizing directory: enabling LPL, 32khz clock for certain platforms. Patches thanks to Thomas Schmidt --- apps/tests/TestFtsp/Ftsp/FtspDataAnalyzer.m | 60 ++ apps/tests/TestFtsp/Ftsp/FtspDataLogger.java | 120 +++ apps/tests/TestFtsp/Ftsp/FtspDataLogger.py | 33 + apps/tests/TestFtsp/Ftsp/Makefile | 17 + apps/tests/TestFtsp/Ftsp/README.MATLAB.txt | 46 ++ apps/tests/TestFtsp/Ftsp/README.txt | 93 +++ apps/tests/TestFtsp/Ftsp/TestFtsp.h | 46 ++ apps/tests/TestFtsp/Ftsp/TestFtspAppC.nc | 53 ++ apps/tests/TestFtsp/Ftsp/TestFtspC.nc | 87 ++ apps/tests/TestFtsp/FtspLpl/FtspDataLogger.py | 33 + apps/tests/TestFtsp/FtspLpl/Makefile | 16 + apps/tests/TestFtsp/FtspLpl/README | 31 + apps/tests/TestFtsp/FtspLpl/TestFtsp.h | 49 ++ apps/tests/TestFtsp/FtspLpl/TestFtspAppC.nc | 67 ++ apps/tests/TestFtsp/FtspLpl/TestFtspC.nc | 124 +++ apps/tests/TestFtsp/FtspLpl/TestFtspMsg.py | 744 ++++++++++++++++++ apps/tests/TestFtsp/FtspLplBeaconer/Makefile | 7 + .../FtspLplBeaconer/RadioCountToLeds.h | 41 + .../FtspLplBeaconer/RadioCountToLedsAppC.nc | 74 ++ .../FtspLplBeaconer/RadioCountToLedsC.nc | 148 ++++ 20 files changed, 1889 insertions(+) create mode 100755 apps/tests/TestFtsp/Ftsp/FtspDataAnalyzer.m create mode 100755 apps/tests/TestFtsp/Ftsp/FtspDataLogger.java create mode 100755 apps/tests/TestFtsp/Ftsp/FtspDataLogger.py create mode 100755 apps/tests/TestFtsp/Ftsp/Makefile create mode 100755 apps/tests/TestFtsp/Ftsp/README.MATLAB.txt create mode 100755 apps/tests/TestFtsp/Ftsp/README.txt create mode 100755 apps/tests/TestFtsp/Ftsp/TestFtsp.h create mode 100755 apps/tests/TestFtsp/Ftsp/TestFtspAppC.nc create mode 100755 apps/tests/TestFtsp/Ftsp/TestFtspC.nc create mode 100755 apps/tests/TestFtsp/FtspLpl/FtspDataLogger.py create mode 100755 apps/tests/TestFtsp/FtspLpl/Makefile create mode 100755 apps/tests/TestFtsp/FtspLpl/README create mode 100755 apps/tests/TestFtsp/FtspLpl/TestFtsp.h create mode 100755 apps/tests/TestFtsp/FtspLpl/TestFtspAppC.nc create mode 100755 apps/tests/TestFtsp/FtspLpl/TestFtspC.nc create mode 100755 apps/tests/TestFtsp/FtspLpl/TestFtspMsg.py create mode 100755 apps/tests/TestFtsp/FtspLplBeaconer/Makefile create mode 100755 apps/tests/TestFtsp/FtspLplBeaconer/RadioCountToLeds.h create mode 100755 apps/tests/TestFtsp/FtspLplBeaconer/RadioCountToLedsAppC.nc create mode 100755 apps/tests/TestFtsp/FtspLplBeaconer/RadioCountToLedsC.nc diff --git a/apps/tests/TestFtsp/Ftsp/FtspDataAnalyzer.m b/apps/tests/TestFtsp/Ftsp/FtspDataAnalyzer.m new file mode 100755 index 00000000..94dda15f --- /dev/null +++ b/apps/tests/TestFtsp/Ftsp/FtspDataAnalyzer.m @@ -0,0 +1,60 @@ +%load file written out by FtspDataLogger.java class +%arg0 - filename, e.g. '1205543689171.report' +function FTSPDataAnalyzer(file, varargin) +[c1 c2 c3 c4 c5]= textread(file, '%u %u %u %u %u', 'commentstyle', 'shell'); +data = [c2 c3 c4 c5]; %skipping the first column (java time) +data1 = sortrows(sortrows(data,1),2); +newdata = []; + +row=1; +newrow=1; +unsynced=0; +while (row<=size(data1,1)) + + seqnum=data1(row,2); + + data2=[]; + row2=1; + tmprow1=row; + while (row <= size(data1,1) && data1(row,2)==seqnum) + if (data1(row,4)==0) + data2(row2,1)=data1(row,3); + row2= row2+ 1; + else + unsynced=unsynced+1; + end + row = row + 1; + end + + if (row2>1) + row2size=row2-1; + rcvdsize=row-tmprow1; + newdata(newrow,1) = seqnum; + newdata(newrow,2) = mad(data2(1:row2size,1)); + newdata(newrow,3) = mean(data2(1:row2size,1)); + newdata(newrow,4) = row2size/rcvdsize; + newrow = newrow + 1; + end +end + +if (length(newdata)==0) + disp('no data found (at least one data point from a synchronized mote is required)!'); +else + newsize=newrow-1; + subplot(3,1,1); + plot(newdata(1:newsize,1),newdata(1:newsize,2)); + title(sprintf('TimeSync Errors')); + subplot(3,1,2); + plot(newdata(1:newsize,1),newdata(1:newsize,3)); + title(sprintf('Avg Glob Time')); + subplot(3,1,3); + plot(newdata(1:newsize,1),newdata(1:newsize,4),'b-'); + title(sprintf('%% Synced Motes')); + + disp(sprintf('total unsycned num %d (all %d)',unsynced,newsize)); + disp(sprintf('avg %0.3f',mean(newdata(1:newsize,2)))); + disp(sprintf('max %d',max(newdata(1:newsize,2)))); + savedata = newdata(1:newsize,:); + save data.out savedata -ASCII; +end + \ No newline at end of file diff --git a/apps/tests/TestFtsp/Ftsp/FtspDataLogger.java b/apps/tests/TestFtsp/Ftsp/FtspDataLogger.java new file mode 100755 index 00000000..168fa0fb --- /dev/null +++ b/apps/tests/TestFtsp/Ftsp/FtspDataLogger.java @@ -0,0 +1,120 @@ +/* tab:4 + * "Copyright (c) 2000-2003 The Regents of the University of California. + * All rights reserved. + * + * Permission to use, copy, modify, and distribute this software and its + * documentation for any purpose, without fee, and without written agreement is + * hereby granted, provided that the above copyright notice, the following + * two paragraphs and the author appear in all copies of this software. + * + * IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + * OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + * CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY + * AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS." + * + * Copyright (c) 2002-2007 Intel Corporation + * All rights reserved. + * + * This file is distributed under the terms in the attached INTEL-LICENSE + * file. If you do not find these files, copies can be found by writing to + * Intel Research Berkeley, 2150 Shattuck Avenue, Suite 1300, Berkeley, CA, + * 94704. Attention: Intel License Inquiry. + */ + + +/** + * @author Brano Kusy + */ + +import java.io.FileOutputStream; +import java.io.PrintStream; +import net.tinyos.message.*; +import net.tinyos.util.*; + +public class FtspDataLogger implements MessageListener { + public class RunWhenShuttingDown extends Thread { + public void run() + { + System.out.println("Control-C caught. Shutting down..."); + if (outReport!=null) + outReport.close(); + } + } + + MoteIF mote; // For talking to the antitheft root node + + void connect() + { + try { + mote = new MoteIF(PrintStreamMessenger.err); + mote.registerListener(new TestFtspMsg(), this); + System.out.println("Connection ok!"); + } + catch(Exception e) { + e.printStackTrace(); + System.exit(2); + } + } + PrintStream outReport = null; + + public FtspDataLogger() { + connect(); + Runtime.getRuntime().addShutdownHook(new RunWhenShuttingDown()); + String name=""+System.currentTimeMillis(); + try + { + outReport = new PrintStream(new FileOutputStream(name+".report")); + outReport.println("#[JAVA_TIME] [NODE_ID] [SEQ_NUM] [GLOB_TIME] [IS_TIME_VALID]"); + } + catch (Exception e) + { + System.out.println("FtspDataLogger.FtspDataLogger(): "+e.toString()); + } + } + + public void writeReprot(TestFtspMsg tspr) + { + String foo = (System.currentTimeMillis() + +" "+tspr.get_src_addr()+" "+tspr.get_counter() + +" "+tspr.get_global_rx_timestamp()+" "+tspr.get_is_synced()); + outReport.println(foo); + System.out.println(foo); + outReport.flush(); + } + + public void writeFullReprot(TestFtspMsg tspr) + { + String foo = (System.currentTimeMillis() + +" "+tspr.get_src_addr() + +" "+tspr.get_counter() + +" "+tspr.get_local_rx_timestamp() + +" "+tspr.get_global_rx_timestamp() + +" "+tspr.get_skew_times_1000000() + +" "+tspr.get_is_synced() + +" "+tspr.get_ftsp_root_addr() + +" "+tspr.get_ftsp_seq() + +" "+tspr.get_ftsp_table_entries()); + outReport.println(foo); + System.out.println(foo); + outReport.flush(); + } + + public void messageReceived(int dest_addr, Message msg) + { + if (msg instanceof TestFtspMsg) + //writeFullReprot((TestFtspMsg)msg); + writeReprot((TestFtspMsg)msg); + } + + /* Just start the app... */ + public static void main(String[] args) + { + new FtspDataLogger(); + } +} \ No newline at end of file diff --git a/apps/tests/TestFtsp/Ftsp/FtspDataLogger.py b/apps/tests/TestFtsp/Ftsp/FtspDataLogger.py new file mode 100755 index 00000000..0c5687b4 --- /dev/null +++ b/apps/tests/TestFtsp/Ftsp/FtspDataLogger.py @@ -0,0 +1,33 @@ +#!/usr/bin/env python + +import sys, time +import tos + +AM_TEST_FTSP_MSG = 137 + +class FtspMsg(tos.Packet): + def __init__(self, packet = None): + tos.Packet.__init__(self, + [('src_addr', 'int', 2), + ('counter', 'int', 2), + ('local_rx_timestamp', 'int', 4), + ('global_rx_timestamp', 'int', 4), + ('skew_times_1000000', 'int', 4), + ('is_synced', 'int', 1), + ('ftsp_root_addr', 'int', 2), + ('ftsp_seq', 'int', 1), + ('ftsp_table_entries', 'int', 2)], + packet) + +if '-h' in sys.argv: + print "Usage:", sys.argv[0], "serial@/dev/ttyUSB0:57600" + sys.exit() + +am = tos.AM() + +while True: + p = am.read() + if p and p.type == AM_TEST_FTSP_MSG: + msg = FtspMsg(p.data) + print int(time.time()), msg.src_addr, msg.counter, msg.global_rx_timestamp, msg.is_synced + #print msg diff --git a/apps/tests/TestFtsp/Ftsp/Makefile b/apps/tests/TestFtsp/Ftsp/Makefile new file mode 100755 index 00000000..25cb7202 --- /dev/null +++ b/apps/tests/TestFtsp/Ftsp/Makefile @@ -0,0 +1,17 @@ +BUILD_EXTRA_DEPS = FtspDataLogger.class +CLEAN_EXTRA = *.class TestFtspMsg.java + +FtspDataLogger.class: TestFtspMsg.java + javac *.java + +TestFtspMsg.java: TestFtsp.h + mig java -target=$(PLATFORM) $(CFLAGS) -java-classname=TestFtspMsg TestFtsp.h test_ftsp_msg -o $@ + +COMPONENT=TestFtspAppC + +PFLAGS += -DTIMESYNC_RATE=3 +#PFLAGS += -DTIMESYNC_DEBUG + +PFLAGS += -I$(TOSDIR)/lib/ftsp -I$(TOSDIR)/../apps/RadioCountToLeds + +include $(MAKERULES) diff --git a/apps/tests/TestFtsp/Ftsp/README.MATLAB.txt b/apps/tests/TestFtsp/Ftsp/README.MATLAB.txt new file mode 100755 index 00000000..0535549a --- /dev/null +++ b/apps/tests/TestFtsp/Ftsp/README.MATLAB.txt @@ -0,0 +1,46 @@ +FtspDataAnalyzer.m + +------------------------------------------------------------------------------- +Author/Contact: +--------------- + Brano Kusy: branislav.kusy@gmail.com + +------------------------------------------------------------------------------- +DESCRIPTION: +------------ + +FtspDataAnalyzer.m works with data logs collected by FtspDataLogger.java and +calculates the maximum and average timesync error over time. + +------------------------------------------------------------------------------- +STEP BY STEP GUIDE TO RUN OUR TEST SCENARIO: +-------------------------------------------- +1. program and start motes as described in ./README.txt +2. start SerialForwarder and FtspDataLogger.java as described in ./README.txt +3. 'current_time.report' file (where current_time is a number) is created in ./ + this file is updated with data in the real time +4. let the experiment run for some time +5. start matlab and enter (assuming your current_time was 1206126224593) + FTSPDataAnalyzer('1206126224593.report') + this will plot the mean absolute timesync error, global time, and number of + synced motes; this can be done while experiment is running +6. Matlab also creates data.out file which contains data in the following format + #seqNum mean_abs_error global_time num_synced_motes + mean_abs_error is calculated as mean absolute deviation from the mean (mad) + +Simulating multi-hop: +1. define TIMESYNC_DEBUG in the Makefile +2. recompile and upload TestFTSP app to n motes with special NODE_IDs: + using 'make micaz reinstall.0xAB', nodes 0xAB and 0xCD can communicate + iff 2D grid coordinates (A,B) and (C,D) are neighbors in a 2D grid + +------------------------------------------------------------------------------- +EVALUATION: +-------------------------------------------- + - deployment setup: 11 nodes in a 5x3 grid using simulated multi-hop (4 points + were vacant as we only used 11 nodes). the max number of hops was 5. + - parameters: sync period 10sec, polling period 3 sec + - experiment length: 100 minutes + - results (1 jiffy is ~30.5 us) + 1.53 jiffy avg error (~50us) + 3.5 jiffy max error (~100us) \ No newline at end of file diff --git a/apps/tests/TestFtsp/Ftsp/README.txt b/apps/tests/TestFtsp/Ftsp/README.txt new file mode 100755 index 00000000..b011bc39 --- /dev/null +++ b/apps/tests/TestFtsp/Ftsp/README.txt @@ -0,0 +1,93 @@ +TestFtsp + +------------------------------------------------------------------------------- +Author/Contact: +--------------- + Brano Kusy: branislav.kusy@gmail.com + Janos Sallai: janos.sallai@vanderbilt.edu + Miklos Maroti: mmaroti@gmail.com + +------------------------------------------------------------------------------- +DESCRIPTION: +------------ + The TestFtsp application tests the Flooding Time Synchronization Protocol + (FTSP) implementation. A network of motes programmed with TestFtsp run the + FTSP protocol to time synchronize, and sends to the base station the global + reception timestamps of messages broadcast by a dedicated beacon mote + programmed with RadioCountToLeds. Ideally, the global reception timestamps of + the same RadioCountToLeds message should agree for all TestFtsp motes (with a + small synchronization error). + +------------------------------------------------------------------------------- +SUPPORTED PLATFORMS: +-------------------------------------------- + The supported platforms are micaz, telosb and iris. + +------------------------------------------------------------------------------- +STEP BY STEP GUIDE TO RUN OUR TEST SCENARIO: +-------------------------------------------- + - program one mote with apps/RadioCountToLeds + - program multiple motes with TestFtsp + - program a mote with apps/BaseStation, leave it on the programming board + - turn on all the motes + - start the FtspDataLogger java application (type "java FtspDataLogger") + +------------------------------------------------------------------------------- +REPORTED DATA: +-------------- + The most important reported data is the global time of arrival of the beacons. + The beacon msg arrives to all clients at the same time instant, thus reported + global times should be the same for all clients for the same sequence number. + + Each message contains: + - the time of message reception by the java app [JAVA_TIME] + - the node ID of the mote that is sending this report [NODE_ID] + - the sequence number of the RadioCountToLeds message that is increased + for each new polling msg [SEQ_NUM] + - the global time when the polling message arrived [GLOB_TIME] + - a result_t value indicating if the timestamp is valid [IS_TIME_VALID] + (a result_t of 0 denotes a valid timestamp) + +If the application is running correctly, then the output should show +reports from the different FTSP nodes with valid timestamps and similar +global time values. For example, this is a trace with two FTSP nodes, +with IDs 1 and 5: + +1214516486569 1 10916 433709 0 +1214516486569 5 10916 433709 0 +1214516486809 5 10917 433964 0 +1214516486809 1 10917 433963 0 +1214516487045 5 10918 434210 0 +1214516487053 1 10918 434210 0 +1214516487285 1 10919 434454 0 +1214516487293 5 10919 434455 0 + +One way to test if FTSP is operating correctly is to turn off one of +the FTSP nodes. For a short time, that node's global times will differ +significantly and its valid flag will not be 0. For example, this +is what it looks like when node 1 in the earlier trace is reset: + +1214516490953 5 10934 438208 0 +1214516491201 5 10935 438460 0 +1214516491441 5 10936 438712 0 +1214516491685 5 10937 438964 0 +1214516492169 5 10939 439455 0 +1214516492417 1 10940 243 1 +1214516492421 5 10940 439706 0 +1214516492665 5 10941 439960 0 +1214516492669 1 10941 497 1 +1214516492905 5 10942 440213 0 +... +1214516497541 1 10961 5495 1 +1214516497549 5 10961 444958 0 +1214516497793 1 10962 5747 1 +1214516498025 1 10963 445456 0 +1214516498033 5 10963 445455 0 +1214516498277 5 10964 445705 0 +1214516498285 1 10964 445707 0 +1214516498521 1 10965 445964 0 + +This output is also saved in a file named 'current_timestamp.report'. +'.report' files can be used with the FtspDataAnalyzer.m Matlab +application. Mean absolute timesync error, global time, and % of +synced motes will be plotted. diff --git a/apps/tests/TestFtsp/Ftsp/TestFtsp.h b/apps/tests/TestFtsp/Ftsp/TestFtsp.h new file mode 100755 index 00000000..cc241ab6 --- /dev/null +++ b/apps/tests/TestFtsp/Ftsp/TestFtsp.h @@ -0,0 +1,46 @@ +/* + * Copyright (c) 2002, Vanderbilt University + * All rights reserved. + * + * Permission to use, copy, modify, and distribute this software and its + * documentation for any purpose, without fee, and without written agreement is + * hereby granted, provided that the above copyright notice, the following + * two paragraphs and the author appear in all copies of this software. + * + * IN NO EVENT SHALL THE VANDERBILT UNIVERSITY BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + * OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE VANDERBILT + * UNIVERSITY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * THE VANDERBILT UNIVERSITY SPECIFICALLY DISCLAIMS ANY WARRANTIES, + * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY + * AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE VANDERBILT UNIVERSITY HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. + * + * @author: Miklos Maroti, Brano Kusy (kusy@isis.vanderbilt.edu) + * Ported to T2: 3/17/08 by Brano Kusy (branislav.kusy@gmail.com) + */ + +#ifndef TEST_FTSP_H +#define TEST_FTSP_H + +typedef nx_struct test_ftsp_msg +{ + nx_uint16_t src_addr; + nx_uint16_t counter; + nx_uint32_t local_rx_timestamp; + nx_uint32_t global_rx_timestamp; + nx_int32_t skew_times_1000000; + nx_uint8_t is_synced; + nx_uint16_t ftsp_root_addr; + nx_uint8_t ftsp_seq; + nx_uint8_t ftsp_table_entries; +} test_ftsp_msg_t; + +enum +{ + AM_TEST_FTSP_MSG = 137 +}; + +#endif diff --git a/apps/tests/TestFtsp/Ftsp/TestFtspAppC.nc b/apps/tests/TestFtsp/Ftsp/TestFtspAppC.nc new file mode 100755 index 00000000..d30adcd8 --- /dev/null +++ b/apps/tests/TestFtsp/Ftsp/TestFtspAppC.nc @@ -0,0 +1,53 @@ +/* + * Copyright (c) 2002, Vanderbilt University + * All rights reserved. + * + * Permission to use, copy, modify, and distribute this software and its + * documentation for any purpose, without fee, and without written agreement is + * hereby granted, provided that the above copyright notice, the following + * two paragraphs and the author appear in all copies of this software. + * + * IN NO EVENT SHALL THE VANDERBILT UNIVERSITY BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + * OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE VANDERBILT + * UNIVERSITY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * THE VANDERBILT UNIVERSITY SPECIFICALLY DISCLAIMS ANY WARRANTIES, + * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY + * AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE VANDERBILT UNIVERSITY HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. + * + * @author: Miklos Maroti, Brano Kusy (kusy@isis.vanderbilt.edu) + * Ported to T2: 3/17/08 by Brano Kusy (branislav.kusy@gmail.com) + */ + +#include "TestFtsp.h" +#include "RadioCountToLeds.h" + +configuration TestFtspAppC { +} + +implementation { + components MainC, TimeSyncC; + + MainC.SoftwareInit -> TimeSyncC; + TimeSyncC.Boot -> MainC; + + components TestFtspC as App; + App.Boot -> MainC; + + components ActiveMessageC; + App.RadioControl -> ActiveMessageC; + App.Receive -> ActiveMessageC.Receive[AM_RADIO_COUNT_MSG]; + App.AMSend -> ActiveMessageC.AMSend[AM_TEST_FTSP_MSG]; + App.Packet -> ActiveMessageC; + App.PacketTimeStamp -> ActiveMessageC; + + components LedsC; + + App.GlobalTime -> TimeSyncC; + App.TimeSyncInfo -> TimeSyncC; + App.Leds -> LedsC; + +} diff --git a/apps/tests/TestFtsp/Ftsp/TestFtspC.nc b/apps/tests/TestFtsp/Ftsp/TestFtspC.nc new file mode 100755 index 00000000..304da1be --- /dev/null +++ b/apps/tests/TestFtsp/Ftsp/TestFtspC.nc @@ -0,0 +1,87 @@ +/* + * Copyright (c) 2002, Vanderbilt University + * All rights reserved. + * + * Permission to use, copy, modify, and distribute this software and its + * documentation for any purpose, without fee, and without written agreement is + * hereby granted, provided that the above copyright notice, the following + * two paragraphs and the author appear in all copies of this software. + * + * IN NO EVENT SHALL THE VANDERBILT UNIVERSITY BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + * OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE VANDERBILT + * UNIVERSITY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * THE VANDERBILT UNIVERSITY SPECIFICALLY DISCLAIMS ANY WARRANTIES, + * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY + * AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE VANDERBILT UNIVERSITY HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. + * + * @author: Miklos Maroti, Brano Kusy (kusy@isis.vanderbilt.edu) + * Ported to T2: 3/17/08 by Brano Kusy (branislav.kusy@gmail.com) + */ + +#include "TestFtsp.h" +#include "RadioCountToLeds.h" + +module TestFtspC +{ + uses + { + interface GlobalTime; + interface TimeSyncInfo; + interface Receive; + interface AMSend; + interface Packet; + interface Leds; + interface PacketTimeStamp; + interface Boot; + interface SplitControl as RadioControl; + } +} + +implementation +{ + message_t msg; + bool locked = FALSE; + + event void Boot.booted() { + call RadioControl.start(); + } + + event message_t* Receive.receive(message_t* msgPtr, void* payload, uint8_t len) + { + call Leds.led0Toggle(); + if (!locked && call PacketTimeStamp.isValid(msgPtr)) { + radio_count_msg_t* rcm = (radio_count_msg_t*)call Packet.getPayload(msgPtr, sizeof(radio_count_msg_t)); + test_ftsp_msg_t* report = (test_ftsp_msg_t*)call Packet.getPayload(&msg, sizeof(test_ftsp_msg_t)); + + uint32_t rxTimestamp = call PacketTimeStamp.timestamp(msgPtr); + + report->src_addr = TOS_NODE_ID; + report->counter = rcm->counter; + report->local_rx_timestamp = rxTimestamp; + report->is_synced = call GlobalTime.local2Global(&rxTimestamp); + report->global_rx_timestamp = rxTimestamp; + report->skew_times_1000000 = (uint32_t)call TimeSyncInfo.getSkew()*1000000UL; + report->ftsp_root_addr = call TimeSyncInfo.getRootID(); + report->ftsp_seq = call TimeSyncInfo.getSeqNum(); + report->ftsp_table_entries = call TimeSyncInfo.getNumEntries(); + + if (call AMSend.send(AM_BROADCAST_ADDR, &msg, sizeof(test_ftsp_msg_t)) == SUCCESS) { + locked = TRUE; + } + } + + return msgPtr; + } + + event void AMSend.sendDone(message_t* ptr, error_t success) { + locked = FALSE; + return; + } + + event void RadioControl.startDone(error_t err) {} + event void RadioControl.stopDone(error_t error){} +} diff --git a/apps/tests/TestFtsp/FtspLpl/FtspDataLogger.py b/apps/tests/TestFtsp/FtspLpl/FtspDataLogger.py new file mode 100755 index 00000000..0c5687b4 --- /dev/null +++ b/apps/tests/TestFtsp/FtspLpl/FtspDataLogger.py @@ -0,0 +1,33 @@ +#!/usr/bin/env python + +import sys, time +import tos + +AM_TEST_FTSP_MSG = 137 + +class FtspMsg(tos.Packet): + def __init__(self, packet = None): + tos.Packet.__init__(self, + [('src_addr', 'int', 2), + ('counter', 'int', 2), + ('local_rx_timestamp', 'int', 4), + ('global_rx_timestamp', 'int', 4), + ('skew_times_1000000', 'int', 4), + ('is_synced', 'int', 1), + ('ftsp_root_addr', 'int', 2), + ('ftsp_seq', 'int', 1), + ('ftsp_table_entries', 'int', 2)], + packet) + +if '-h' in sys.argv: + print "Usage:", sys.argv[0], "serial@/dev/ttyUSB0:57600" + sys.exit() + +am = tos.AM() + +while True: + p = am.read() + if p and p.type == AM_TEST_FTSP_MSG: + msg = FtspMsg(p.data) + print int(time.time()), msg.src_addr, msg.counter, msg.global_rx_timestamp, msg.is_synced + #print msg diff --git a/apps/tests/TestFtsp/FtspLpl/Makefile b/apps/tests/TestFtsp/FtspLpl/Makefile new file mode 100755 index 00000000..99629881 --- /dev/null +++ b/apps/tests/TestFtsp/FtspLpl/Makefile @@ -0,0 +1,16 @@ +SENSORBOARD=quantoplus + +COMPONENT=TestFtspAppC + +PFLAGS += -DTIMESYNC_RATE=10 +#PFLAGS += -DTIMESYNC_DEBUG +#PFLAGS += -DCC2420_CHANNEL=26 +CFLAGS += -DTOSH_DATA_LENGTH=50 +#CFLAGS += -DCOUNT_LOG + +PFLAGS += -I$(TOSDIR)/lib/ftsp -I$(TOSDIR)/../apps/RadioCountToLeds -I$(TOSDIR)/lib/printf + +CFLAGS += -DLPL_INTERVAL=200 +CFLAGS += -DLOW_POWER_LISTENING + +include $(MAKERULES) diff --git a/apps/tests/TestFtsp/FtspLpl/README b/apps/tests/TestFtsp/FtspLpl/README new file mode 100755 index 00000000..24c080c7 --- /dev/null +++ b/apps/tests/TestFtsp/FtspLpl/README @@ -0,0 +1,31 @@ +First, program several nodes with this TestFtsp application. In addition, +you will need one TinyOS Basestation that listens for messages, and one +beacon node. Program the beacon node with the RadioCountToLed application +from the TestFtsp32kLplBeaconer directory. This is a special modification of +the RadioCountToLed code which allows to evaluate a duty-cycled ftsp +network. The regular RadioCountToLed code doesn't work, since a LPL +broadcast message gets transmitted more than just once. Thus, there is a +disambiguity in which precise broadcast message was actually timestamped by +the TestFtsp application. The modifications take care of this by using the +TimeSyncAMSend interface and setting an arbitrary event time. Thus, on +reception, the TestFtsp code can account for this delayed send. + +To evaluate the synchronization precision, use the FtspDataLogger.py +application. First, you will need a serial forwarder that connects to the +BaseStation node. Then, run the python application like this: +python FtspDataLogger.py sf@localhost:9002 + +You should now see messages coming in, one per line. The first value is the +current time as a unix timestamp. The last line is a binary value indicating +if there was some missed data, and thus the values are not good (indicated +by a 1), or if all the nodes are synchronized and we received a value for +each and every one of them (indicated by a 0). + +Note!!!!! +- the basestation should also define + CFLAGS += -DTOSH_DATA_LENGTH=50 + in the makefile. Else, the reports will not fit into 1 tinyos message, and + they will get silently dropped. +- 32k timesync only works for certain platforms (those that provide 32khz + counter), if your platform does not support the counter, LPL still works, + but you need to use TMilli timesync diff --git a/apps/tests/TestFtsp/FtspLpl/TestFtsp.h b/apps/tests/TestFtsp/FtspLpl/TestFtsp.h new file mode 100755 index 00000000..57cd25cf --- /dev/null +++ b/apps/tests/TestFtsp/FtspLpl/TestFtsp.h @@ -0,0 +1,49 @@ +/* + * Copyright (c) 2002, Vanderbilt University + * All rights reserved. + * + * Permission to use, copy, modify, and distribute this software and its + * documentation for any purpose, without fee, and without written agreement is + * hereby granted, provided that the above copyright notice, the following + * two paragraphs and the author appear in all copies of this software. + * + * IN NO EVENT SHALL THE VANDERBILT UNIVERSITY BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + * OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE VANDERBILT + * UNIVERSITY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * THE VANDERBILT UNIVERSITY SPECIFICALLY DISCLAIMS ANY WARRANTIES, + * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY + * AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE VANDERBILT UNIVERSITY HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. + * + * @author: Miklos Maroti, Brano Kusy (kusy@isis.vanderbilt.edu) + * Ported to T2: 3/17/08 by Brano Kusy (branislav.kusy@gmail.com) + */ + +#ifndef TEST_FTSP_H +#define TEST_FTSP_H + +typedef nx_struct test_ftsp_msg +{ + nx_uint16_t src_addr; + nx_uint16_t counter; + nx_uint32_t local_rx_timestamp; + nx_uint32_t global_rx_timestamp; + nx_int32_t skew_times_1000000; + nx_float skew; + nx_uint8_t is_synced; + nx_uint16_t ftsp_root_addr; + nx_uint8_t ftsp_seq; + nx_uint8_t ftsp_table_entries; + nx_uint32_t localAverage; + nx_int32_t offsetAverage; +} test_ftsp_msg_t; + +enum +{ + AM_TEST_FTSP_MSG = 137 +}; + +#endif diff --git a/apps/tests/TestFtsp/FtspLpl/TestFtspAppC.nc b/apps/tests/TestFtsp/FtspLpl/TestFtspAppC.nc new file mode 100755 index 00000000..fbb75400 --- /dev/null +++ b/apps/tests/TestFtsp/FtspLpl/TestFtspAppC.nc @@ -0,0 +1,67 @@ +/* + * Copyright (c) 2002, Vanderbilt University + * All rights reserved. + * + * Permission to use, copy, modify, and distribute this software and its + * documentation for any purpose, without fee, and without written agreement is + * hereby granted, provided that the above copyright notice, the following + * two paragraphs and the author appear in all copies of this software. + * + * IN NO EVENT SHALL THE VANDERBILT UNIVERSITY BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + * OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE VANDERBILT + * UNIVERSITY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * THE VANDERBILT UNIVERSITY SPECIFICALLY DISCLAIMS ANY WARRANTIES, + * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY + * AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE VANDERBILT UNIVERSITY HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. + * + * @author: Miklos Maroti, Brano Kusy (kusy@isis.vanderbilt.edu) + * Ported to T2: 3/17/08 by Brano Kusy (branislav.kusy@gmail.com) + * Adapted for LPL: 6/16/09 by Thomas Schmid (thomas.schmid@ucla.edu) + */ + +#include "TestFtsp.h" +#include "RadioCountToLeds.h" + +configuration TestFtspAppC { +} + +implementation { + components MainC, TimeSync32kC; + + MainC.SoftwareInit -> TimeSync32kC; + TimeSync32kC.Boot -> MainC; + + components TestFtspC as App; + App.Boot -> MainC; + + components ActiveMessageC; + components TimeSyncMessageC; + App.RadioControl -> ActiveMessageC; + App.Receive -> TimeSyncMessageC.Receive[AM_RADIO_COUNT_MSG]; + App.TimeSyncPacket -> TimeSyncMessageC; + App.AMSend -> ActiveMessageC.AMSend[AM_TEST_FTSP_MSG]; + App.Packet -> ActiveMessageC; + App.PacketTimeStamp -> ActiveMessageC; + + components RandomC; + App.Random -> RandomC; + + components new TimerMilliC() as Timer0; + App.RandomTimer -> Timer0; + + components LedsC; + + App.GlobalTime -> TimeSync32kC; + App.TimeSyncInfo -> TimeSync32kC; + App.Leds -> LedsC; + +#ifdef LOW_POWER_LISTENING + components CC2420ActiveMessageC; + App.LowPowerListening -> CC2420ActiveMessageC; +#endif + +} diff --git a/apps/tests/TestFtsp/FtspLpl/TestFtspC.nc b/apps/tests/TestFtsp/FtspLpl/TestFtspC.nc new file mode 100755 index 00000000..ed8f504d --- /dev/null +++ b/apps/tests/TestFtsp/FtspLpl/TestFtspC.nc @@ -0,0 +1,124 @@ +/* + * Copyright (c) 2002, Vanderbilt University + * All rights reserved. + * + * Permission to use, copy, modify, and distribute this software and its + * documentation for any purpose, without fee, and without written agreement is + * hereby granted, provided that the above copyright notice, the following + * two paragraphs and the author appear in all copies of this software. + * + * IN NO EVENT SHALL THE VANDERBILT UNIVERSITY BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + * OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE VANDERBILT + * UNIVERSITY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * THE VANDERBILT UNIVERSITY SPECIFICALLY DISCLAIMS ANY WARRANTIES, + * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY + * AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE VANDERBILT UNIVERSITY HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. + * + * @author: Miklos Maroti, Brano Kusy (kusy@isis.vanderbilt.edu) + * Ported to T2: 3/17/08 by Brano Kusy (branislav.kusy@gmail.com) + * Ported for LPL: Thomas Schmid (thomas.schmid@ucla.edu) + */ + +#include "TestFtsp.h" +#include "RadioCountToLeds.h" + +module TestFtspC +{ + uses + { + interface GlobalTime; + interface TimeSyncInfo; + interface Receive; + interface AMSend; + interface Packet; + interface Leds; + interface PacketTimeStamp; + interface Boot; + interface SplitControl as RadioControl; + interface Timer as RandomTimer; + interface Random; + + interface TimeSyncPacket; + +#ifdef LOW_POWER_LISTENING + interface LowPowerListening; +#endif + + } +} + +implementation +{ + enum { + ACT_TESTFTSP = 0x11, + }; + + message_t msg; + bool locked = FALSE; + test_ftsp_msg_t* report; + + event void Boot.booted() { + call RadioControl.start(); + } + + event message_t* Receive.receive(message_t* msgPtr, void* payload, uint8_t len) + { + if (!(call PacketTimeStamp.isValid(msgPtr))){ + call Leds.led1Toggle(); + } + if (!locked && call PacketTimeStamp.isValid(msgPtr)) { + radio_count_msg_t* rcm = (radio_count_msg_t*)call Packet.getPayload(msgPtr, sizeof(radio_count_msg_t)); + if(call TimeSyncPacket.isValid(msgPtr)) { + uint32_t rxTimestamp = call TimeSyncPacket.eventTime(msgPtr); + report = (test_ftsp_msg_t*)call Packet.getPayload(&msg, sizeof(test_ftsp_msg_t)); + + report->src_addr = TOS_NODE_ID; + report->counter = rcm->counter; + report->local_rx_timestamp = rxTimestamp; + report->is_synced = call GlobalTime.local2Global(&rxTimestamp); + report->global_rx_timestamp = rxTimestamp; + report->skew_times_1000000 = (uint32_t)call TimeSyncInfo.getSkew()*1000000UL; + report->skew = call TimeSyncInfo.getSkew(); + report->ftsp_root_addr = call TimeSyncInfo.getRootID(); + report->ftsp_seq = call TimeSyncInfo.getSeqNum(); + report->ftsp_table_entries = call TimeSyncInfo.getNumEntries(); + report->localAverage = call TimeSyncInfo.getSyncPoint(); + report->offsetAverage = call TimeSyncInfo.getOffset(); + + locked = TRUE; + call RandomTimer.startOneShot(call Random.rand16() % (64)); + } + } + + return msgPtr; + } + + event void RandomTimer.fired() + { +#ifdef LOW_POWER_LISTENING + call LowPowerListening.setRxSleepInterval(&msg, LPL_INTERVAL); +#endif + if(locked && (call AMSend.send(4000, &msg, sizeof(test_ftsp_msg_t)) == SUCCESS)){ + call Leds.led2On(); + } else { + locked = FALSE; + } + } + + event void AMSend.sendDone(message_t* ptr, error_t success) { + locked = FALSE; + call Leds.led2Off(); + return; + } + + event void RadioControl.startDone(error_t err) { +#ifdef LOW_POWER_LISTENING + call LowPowerListening.setLocalSleepInterval(LPL_INTERVAL); +#endif + } + event void RadioControl.stopDone(error_t error){} +} diff --git a/apps/tests/TestFtsp/FtspLpl/TestFtspMsg.py b/apps/tests/TestFtsp/FtspLpl/TestFtspMsg.py new file mode 100755 index 00000000..0223c4d3 --- /dev/null +++ b/apps/tests/TestFtsp/FtspLpl/TestFtspMsg.py @@ -0,0 +1,744 @@ +# +# This class is automatically generated by mig. DO NOT EDIT THIS FILE. +# This class implements a Python interface to the 'TestFtspMsg' +# message type. +# + +import tinyos.message.Message + +# The default size of this message type in bytes. +DEFAULT_MESSAGE_SIZE = 33 + +# The Active Message type associated with this message. +AM_TYPE = 137 + +class TestFtspMsg(tinyos.message.Message.Message): + # Create a new TestFtspMsg of size 33. + def __init__(self, data="", addr=None, gid=None, base_offset=0, data_length=33): + tinyos.message.Message.Message.__init__(self, data, addr, gid, base_offset, data_length) + self.amTypeSet(AM_TYPE) + + # Get AM_TYPE + def get_amType(cls): + return AM_TYPE + + get_amType = classmethod(get_amType) + + # + # Return a String representation of this message. Includes the + # message type name and the non-indexed field values. + # + def __str__(self): + s = "Message \n" + try: + s += " [src_addr=0x%x]\n" % (self.get_src_addr()) + except: + pass + try: + s += " [counter=0x%x]\n" % (self.get_counter()) + except: + pass + try: + s += " [local_rx_timestamp=0x%x]\n" % (self.get_local_rx_timestamp()) + except: + pass + try: + s += " [global_rx_timestamp=0x%x]\n" % (self.get_global_rx_timestamp()) + except: + pass + try: + s += " [skew_times_1000000=0x%x]\n" % (self.get_skew_times_1000000()) + except: + pass + try: + s += " [skew=0x%x]\n" % (self.get_skew()) + except: + pass + try: + s += " [is_synced=0x%x]\n" % (self.get_is_synced()) + except: + pass + try: + s += " [ftsp_root_addr=0x%x]\n" % (self.get_ftsp_root_addr()) + except: + pass + try: + s += " [ftsp_seq=0x%x]\n" % (self.get_ftsp_seq()) + except: + pass + try: + s += " [ftsp_table_entries=0x%x]\n" % (self.get_ftsp_table_entries()) + except: + pass + try: + s += " [localAverage=0x%x]\n" % (self.get_localAverage()) + except: + pass + try: + s += " [offsetAverage=0x%x]\n" % (self.get_offsetAverage()) + except: + pass + return s + + # Message-type-specific access methods appear below. + + # + # Accessor methods for field: src_addr + # Field type: int + # Offset (bits): 0 + # Size (bits): 16 + # + + # + # Return whether the field 'src_addr' is signed (False). + # + def isSigned_src_addr(self): + return False + + # + # Return whether the field 'src_addr' is an array (False). + # + def isArray_src_addr(self): + return False + + # + # Return the offset (in bytes) of the field 'src_addr' + # + def offset_src_addr(self): + return (0 / 8) + + # + # Return the offset (in bits) of the field 'src_addr' + # + def offsetBits_src_addr(self): + return 0 + + # + # Return the value (as a int) of the field 'src_addr' + # + def get_src_addr(self): + return self.getUIntElement(self.offsetBits_src_addr(), 16, 1) + + # + # Set the value of the field 'src_addr' + # + def set_src_addr(self, value): + self.setUIntElement(self.offsetBits_src_addr(), 16, value, 1) + + # + # Return the size, in bytes, of the field 'src_addr' + # + def size_src_addr(self): + return (16 / 8) + + # + # Return the size, in bits, of the field 'src_addr' + # + def sizeBits_src_addr(self): + return 16 + + # + # Accessor methods for field: counter + # Field type: int + # Offset (bits): 16 + # Size (bits): 16 + # + + # + # Return whether the field 'counter' is signed (False). + # + def isSigned_counter(self): + return False + + # + # Return whether the field 'counter' is an array (False). + # + def isArray_counter(self): + return False + + # + # Return the offset (in bytes) of the field 'counter' + # + def offset_counter(self): + return (16 / 8) + + # + # Return the offset (in bits) of the field 'counter' + # + def offsetBits_counter(self): + return 16 + + # + # Return the value (as a int) of the field 'counter' + # + def get_counter(self): + return self.getUIntElement(self.offsetBits_counter(), 16, 1) + + # + # Set the value of the field 'counter' + # + def set_counter(self, value): + self.setUIntElement(self.offsetBits_counter(), 16, value, 1) + + # + # Return the size, in bytes, of the field 'counter' + # + def size_counter(self): + return (16 / 8) + + # + # Return the size, in bits, of the field 'counter' + # + def sizeBits_counter(self): + return 16 + + # + # Accessor methods for field: local_rx_timestamp + # Field type: long + # Offset (bits): 32 + # Size (bits): 32 + # + + # + # Return whether the field 'local_rx_timestamp' is signed (False). + # + def isSigned_local_rx_timestamp(self): + return False + + # + # Return whether the field 'local_rx_timestamp' is an array (False). + # + def isArray_local_rx_timestamp(self): + return False + + # + # Return the offset (in bytes) of the field 'local_rx_timestamp' + # + def offset_local_rx_timestamp(self): + return (32 / 8) + + # + # Return the offset (in bits) of the field 'local_rx_timestamp' + # + def offsetBits_local_rx_timestamp(self): + return 32 + + # + # Return the value (as a long) of the field 'local_rx_timestamp' + # + def get_local_rx_timestamp(self): + return self.getUIntElement(self.offsetBits_local_rx_timestamp(), 32, 1) + + # + # Set the value of the field 'local_rx_timestamp' + # + def set_local_rx_timestamp(self, value): + self.setUIntElement(self.offsetBits_local_rx_timestamp(), 32, value, 1) + + # + # Return the size, in bytes, of the field 'local_rx_timestamp' + # + def size_local_rx_timestamp(self): + return (32 / 8) + + # + # Return the size, in bits, of the field 'local_rx_timestamp' + # + def sizeBits_local_rx_timestamp(self): + return 32 + + # + # Accessor methods for field: global_rx_timestamp + # Field type: long + # Offset (bits): 64 + # Size (bits): 32 + # + + # + # Return whether the field 'global_rx_timestamp' is signed (False). + # + def isSigned_global_rx_timestamp(self): + return False + + # + # Return whether the field 'global_rx_timestamp' is an array (False). + # + def isArray_global_rx_timestamp(self): + return False + + # + # Return the offset (in bytes) of the field 'global_rx_timestamp' + # + def offset_global_rx_timestamp(self): + return (64 / 8) + + # + # Return the offset (in bits) of the field 'global_rx_timestamp' + # + def offsetBits_global_rx_timestamp(self): + return 64 + + # + # Return the value (as a long) of the field 'global_rx_timestamp' + # + def get_global_rx_timestamp(self): + return self.getUIntElement(self.offsetBits_global_rx_timestamp(), 32, 1) + + # + # Set the value of the field 'global_rx_timestamp' + # + def set_global_rx_timestamp(self, value): + self.setUIntElement(self.offsetBits_global_rx_timestamp(), 32, value, 1) + + # + # Return the size, in bytes, of the field 'global_rx_timestamp' + # + def size_global_rx_timestamp(self): + return (32 / 8) + + # + # Return the size, in bits, of the field 'global_rx_timestamp' + # + def sizeBits_global_rx_timestamp(self): + return 32 + + # + # Accessor methods for field: skew_times_1000000 + # Field type: int + # Offset (bits): 96 + # Size (bits): 32 + # + + # + # Return whether the field 'skew_times_1000000' is signed (False). + # + def isSigned_skew_times_1000000(self): + return False + + # + # Return whether the field 'skew_times_1000000' is an array (False). + # + def isArray_skew_times_1000000(self): + return False + + # + # Return the offset (in bytes) of the field 'skew_times_1000000' + # + def offset_skew_times_1000000(self): + return (96 / 8) + + # + # Return the offset (in bits) of the field 'skew_times_1000000' + # + def offsetBits_skew_times_1000000(self): + return 96 + + # + # Return the value (as a int) of the field 'skew_times_1000000' + # + def get_skew_times_1000000(self): + return self.getSIntElement(self.offsetBits_skew_times_1000000(), 32, 1) + + # + # Set the value of the field 'skew_times_1000000' + # + def set_skew_times_1000000(self, value): + self.setSIntElement(self.offsetBits_skew_times_1000000(), 32, value, 1) + + # + # Return the size, in bytes, of the field 'skew_times_1000000' + # + def size_skew_times_1000000(self): + return (32 / 8) + + # + # Return the size, in bits, of the field 'skew_times_1000000' + # + def sizeBits_skew_times_1000000(self): + return 32 + + # + # Accessor methods for field: skew + # Field type: int + # Offset (bits): 128 + # Size (bits): 32 + # + + # + # Return whether the field 'skew' is signed (False). + # + def isSigned_skew(self): + return False + + # + # Return whether the field 'skew' is an array (False). + # + def isArray_skew(self): + return False + + # + # Return the offset (in bytes) of the field 'skew' + # + def offset_skew(self): + return (128 / 8) + + # + # Return the offset (in bits) of the field 'skew' + # + def offsetBits_skew(self): + return 128 + + # + # Return the value (as a int) of the field 'skew' + # + def get_skew(self): + return self.getFloatElement(self.offsetBits_skew(), 32, 0) + + # + # Set the value of the field 'skew' + # + def set_skew(self, value): + self.setSIntElement(self.offsetBits_skew(), 32, value, 1) + + # + # Return the size, in bytes, of the field 'skew' + # + def size_skew(self): + return (32 / 8) + + # + # Return the size, in bits, of the field 'skew' + # + def sizeBits_skew(self): + return 32 + + # + # Accessor methods for field: is_synced + # Field type: short + # Offset (bits): 160 + # Size (bits): 8 + # + + # + # Return whether the field 'is_synced' is signed (False). + # + def isSigned_is_synced(self): + return False + + # + # Return whether the field 'is_synced' is an array (False). + # + def isArray_is_synced(self): + return False + + # + # Return the offset (in bytes) of the field 'is_synced' + # + def offset_is_synced(self): + return (160 / 8) + + # + # Return the offset (in bits) of the field 'is_synced' + # + def offsetBits_is_synced(self): + return 160 + + # + # Return the value (as a short) of the field 'is_synced' + # + def get_is_synced(self): + return self.getUIntElement(self.offsetBits_is_synced(), 8, 1) + + # + # Set the value of the field 'is_synced' + # + def set_is_synced(self, value): + self.setUIntElement(self.offsetBits_is_synced(), 8, value, 1) + + # + # Return the size, in bytes, of the field 'is_synced' + # + def size_is_synced(self): + return (8 / 8) + + # + # Return the size, in bits, of the field 'is_synced' + # + def sizeBits_is_synced(self): + return 8 + + # + # Accessor methods for field: ftsp_root_addr + # Field type: int + # Offset (bits): 168 + # Size (bits): 16 + # + + # + # Return whether the field 'ftsp_root_addr' is signed (False). + # + def isSigned_ftsp_root_addr(self): + return False + + # + # Return whether the field 'ftsp_root_addr' is an array (False). + # + def isArray_ftsp_root_addr(self): + return False + + # + # Return the offset (in bytes) of the field 'ftsp_root_addr' + # + def offset_ftsp_root_addr(self): + return (168 / 8) + + # + # Return the offset (in bits) of the field 'ftsp_root_addr' + # + def offsetBits_ftsp_root_addr(self): + return 168 + + # + # Return the value (as a int) of the field 'ftsp_root_addr' + # + def get_ftsp_root_addr(self): + return self.getUIntElement(self.offsetBits_ftsp_root_addr(), 16, 1) + + # + # Set the value of the field 'ftsp_root_addr' + # + def set_ftsp_root_addr(self, value): + self.setUIntElement(self.offsetBits_ftsp_root_addr(), 16, value, 1) + + # + # Return the size, in bytes, of the field 'ftsp_root_addr' + # + def size_ftsp_root_addr(self): + return (16 / 8) + + # + # Return the size, in bits, of the field 'ftsp_root_addr' + # + def sizeBits_ftsp_root_addr(self): + return 16 + + # + # Accessor methods for field: ftsp_seq + # Field type: short + # Offset (bits): 184 + # Size (bits): 8 + # + + # + # Return whether the field 'ftsp_seq' is signed (False). + # + def isSigned_ftsp_seq(self): + return False + + # + # Return whether the field 'ftsp_seq' is an array (False). + # + def isArray_ftsp_seq(self): + return False + + # + # Return the offset (in bytes) of the field 'ftsp_seq' + # + def offset_ftsp_seq(self): + return (184 / 8) + + # + # Return the offset (in bits) of the field 'ftsp_seq' + # + def offsetBits_ftsp_seq(self): + return 184 + + # + # Return the value (as a short) of the field 'ftsp_seq' + # + def get_ftsp_seq(self): + return self.getUIntElement(self.offsetBits_ftsp_seq(), 8, 1) + + # + # Set the value of the field 'ftsp_seq' + # + def set_ftsp_seq(self, value): + self.setUIntElement(self.offsetBits_ftsp_seq(), 8, value, 1) + + # + # Return the size, in bytes, of the field 'ftsp_seq' + # + def size_ftsp_seq(self): + return (8 / 8) + + # + # Return the size, in bits, of the field 'ftsp_seq' + # + def sizeBits_ftsp_seq(self): + return 8 + + # + # Accessor methods for field: ftsp_table_entries + # Field type: short + # Offset (bits): 192 + # Size (bits): 8 + # + + # + # Return whether the field 'ftsp_table_entries' is signed (False). + # + def isSigned_ftsp_table_entries(self): + return False + + # + # Return whether the field 'ftsp_table_entries' is an array (False). + # + def isArray_ftsp_table_entries(self): + return False + + # + # Return the offset (in bytes) of the field 'ftsp_table_entries' + # + def offset_ftsp_table_entries(self): + return (192 / 8) + + # + # Return the offset (in bits) of the field 'ftsp_table_entries' + # + def offsetBits_ftsp_table_entries(self): + return 192 + + # + # Return the value (as a short) of the field 'ftsp_table_entries' + # + def get_ftsp_table_entries(self): + return self.getUIntElement(self.offsetBits_ftsp_table_entries(), 8, 1) + + # + # Set the value of the field 'ftsp_table_entries' + # + def set_ftsp_table_entries(self, value): + self.setUIntElement(self.offsetBits_ftsp_table_entries(), 8, value, 1) + + # + # Return the size, in bytes, of the field 'ftsp_table_entries' + # + def size_ftsp_table_entries(self): + return (8 / 8) + + # + # Return the size, in bits, of the field 'ftsp_table_entries' + # + def sizeBits_ftsp_table_entries(self): + return 8 + + # + # Accessor methods for field: localAverage + # Field type: long + # Offset (bits): 200 + # Size (bits): 32 + # + + # + # Return whether the field 'localAverage' is signed (False). + # + def isSigned_localAverage(self): + return False + + # + # Return whether the field 'localAverage' is an array (False). + # + def isArray_localAverage(self): + return False + + # + # Return the offset (in bytes) of the field 'localAverage' + # + def offset_localAverage(self): + return (200 / 8) + + # + # Return the offset (in bits) of the field 'localAverage' + # + def offsetBits_localAverage(self): + return 200 + + # + # Return the value (as a long) of the field 'localAverage' + # + def get_localAverage(self): + return self.getUIntElement(self.offsetBits_localAverage(), 32, 1) + + # + # Set the value of the field 'localAverage' + # + def set_localAverage(self, value): + self.setUIntElement(self.offsetBits_localAverage(), 32, value, 1) + + # + # Return the size, in bytes, of the field 'localAverage' + # + def size_localAverage(self): + return (32 / 8) + + # + # Return the size, in bits, of the field 'localAverage' + # + def sizeBits_localAverage(self): + return 32 + + # + # Accessor methods for field: offsetAverage + # Field type: int + # Offset (bits): 232 + # Size (bits): 32 + # + + # + # Return whether the field 'offsetAverage' is signed (False). + # + def isSigned_offsetAverage(self): + return False + + # + # Return whether the field 'offsetAverage' is an array (False). + # + def isArray_offsetAverage(self): + return False + + # + # Return the offset (in bytes) of the field 'offsetAverage' + # + def offset_offsetAverage(self): + return (232 / 8) + + # + # Return the offset (in bits) of the field 'offsetAverage' + # + def offsetBits_offsetAverage(self): + return 232 + + # + # Return the value (as a int) of the field 'offsetAverage' + # + def get_offsetAverage(self): + return self.getSIntElement(self.offsetBits_offsetAverage(), 32, 1) + + # + # Set the value of the field 'offsetAverage' + # + def set_offsetAverage(self, value): + self.setSIntElement(self.offsetBits_offsetAverage(), 32, value, 1) + + # + # Return the size, in bytes, of the field 'offsetAverage' + # + def size_offsetAverage(self): + return (32 / 8) + + # + # Return the size, in bits, of the field 'offsetAverage' + # + def sizeBits_offsetAverage(self): + return 32 + diff --git a/apps/tests/TestFtsp/FtspLplBeaconer/Makefile b/apps/tests/TestFtsp/FtspLplBeaconer/Makefile new file mode 100755 index 00000000..a935c01e --- /dev/null +++ b/apps/tests/TestFtsp/FtspLplBeaconer/Makefile @@ -0,0 +1,7 @@ +COMPONENT=RadioCountToLedsAppC + +CFLAGS += -DLPL_INTERVAL=200 +CFLAGS += -DLOW_POWER_LISTENING + +include $(MAKERULES) + diff --git a/apps/tests/TestFtsp/FtspLplBeaconer/RadioCountToLeds.h b/apps/tests/TestFtsp/FtspLplBeaconer/RadioCountToLeds.h new file mode 100755 index 00000000..8d29f3fb --- /dev/null +++ b/apps/tests/TestFtsp/FtspLplBeaconer/RadioCountToLeds.h @@ -0,0 +1,41 @@ +/* + * "Copyright (c) 2004-2005 The Regents of the University of California. + * All rights reserved. + * + * Permission to use, copy, modify, and distribute this software and its + * documentation for any purpose, without fee, and without written agreement is + * hereby granted, provided that the above copyright notice, the following + * two paragraphs and the author appear in all copies of this software. + * + * IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + * OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + * CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY + * AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS." + * + * Copyright (c) 2002-2003 Intel Corporation + * All rights reserved. + * + * This file is distributed under the terms in the attached INTEL-LICENSE + * file. If you do not find these files, copies can be found by writing to + * Intel Research Berkeley, 2150 Shattuck Avenue, Suite 1300, Berkeley, CA, + * 94704. Attention: Intel License Inquiry. + */ + +#ifndef RADIO_COUNT_TO_LEDS_H +#define RADIO_COUNT_TO_LEDS_H + +typedef nx_struct radio_count_msg { + nx_uint16_t counter; +} radio_count_msg_t; + +enum { + AM_RADIO_COUNT_MSG = 6, +}; + +#endif diff --git a/apps/tests/TestFtsp/FtspLplBeaconer/RadioCountToLedsAppC.nc b/apps/tests/TestFtsp/FtspLplBeaconer/RadioCountToLedsAppC.nc new file mode 100755 index 00000000..13f36670 --- /dev/null +++ b/apps/tests/TestFtsp/FtspLplBeaconer/RadioCountToLedsAppC.nc @@ -0,0 +1,74 @@ +// $Id$ + +/* tab:4 + * "Copyright (c) 2000-2005 The Regents of the University of California. + * All rights reserved. + * + * Permission to use, copy, modify, and distribute this software and its + * documentation for any purpose, without fee, and without written agreement is + * hereby granted, provided that the above copyright notice, the following + * two paragraphs and the author appear in all copies of this software. + * + * IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + * OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + * CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY + * AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS." + * + * Copyright (c) 2002-2003 Intel Corporation + * All rights reserved. + * + * This file is distributed under the terms in the attached INTEL-LICENSE + * file. If you do not find these files, copies can be found by writing to + * Intel Research Berkeley, 2150 Shattuck Avenue, Suite 1300, Berkeley, CA, + * 94704. Attention: Intel License Inquiry. + */ + +#include "RadioCountToLeds.h" +#include "Timer.h" + +/** + * Configuration for the RadioCountToLeds application. RadioCountToLeds + * maintains a 4Hz counter, broadcasting its value in an AM packet + * every time it gets updated. A RadioCountToLeds node that hears a counter + * displays the bottom three bits on its LEDs. This application is a useful + * test to show that basic AM communication and timers work. + * + * @author Philip Levis + * @date June 6 2005 + */ + +configuration RadioCountToLedsAppC {} +implementation { + components MainC, new RadioCountToLedsC(T32khz) as App, LedsC; + components new AMReceiverC(AM_RADIO_COUNT_MSG); + components new TimerMilliC(); + components TimeSyncMessageC as ActiveMessageC; + + App.Boot -> MainC.Boot; + + App.Receive -> AMReceiverC; + App.AMSend -> ActiveMessageC.TimeSyncAMSend32khz[AM_RADIO_COUNT_MSG]; + App.AMControl -> ActiveMessageC; + App.Leds -> LedsC; + App.MilliTimer -> TimerMilliC; + App.Packet -> ActiveMessageC; + + components Counter32khz32C, new CounterToLocalTimeC(T32khz) as LocalTime32khzC; + LocalTime32khzC.Counter -> Counter32khz32C; + App.LocalTime -> LocalTime32khzC; + + +#ifdef LOW_POWER_LISTENING + components CC2420ActiveMessageC; + App.LowPowerListening -> CC2420ActiveMessageC; +#endif + +} + + diff --git a/apps/tests/TestFtsp/FtspLplBeaconer/RadioCountToLedsC.nc b/apps/tests/TestFtsp/FtspLplBeaconer/RadioCountToLedsC.nc new file mode 100755 index 00000000..436c4ed0 --- /dev/null +++ b/apps/tests/TestFtsp/FtspLplBeaconer/RadioCountToLedsC.nc @@ -0,0 +1,148 @@ +// $Id$ + +/* tab:4 + * "Copyright (c) 2000-2005 The Regents of the University of California. + * All rights reserved. + * + * Permission to use, copy, modify, and distribute this software and its + * documentation for any purpose, without fee, and without written agreement is + * hereby granted, provided that the above copyright notice, the following + * two paragraphs and the author appear in all copies of this software. + * + * IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT + * OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF + * CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, + * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY + * AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS." + * + * Copyright (c) 2002-2003 Intel Corporation + * All rights reserved. + * + * This file is distributed under the terms in the attached INTEL-LICENSE + * file. If you do not find these files, copies can be found by writing to + * Intel Research Berkeley, 2150 Shattuck Avenue, Suite 1300, Berkeley, CA, + * 94704. Attention: Intel License Inquiry. + */ + +#include "Timer.h" +#include "RadioCountToLeds.h" + +/** + * Implementation of the RadioCountToLeds application. RadioCountToLeds + * maintains a 4Hz counter, broadcasting its value in an AM packet + * every time it gets updated. A RadioCountToLeds node that hears a counter + * displays the bottom three bits on its LEDs. This application is a useful + * test to show that basic AM communication and timers work. + * + * @author Philip Levis + * @date June 6 2005 + */ + +generic module RadioCountToLedsC(typedef precision_tag) @safe() { + uses { + interface Leds; + interface Boot; + interface Receive; + interface TimeSyncAMSend as AMSend; + interface Timer as MilliTimer; + interface SplitControl as AMControl; + interface Packet; + + interface LocalTime as LocalTime; + + +#ifdef LOW_POWER_LISTENING + interface LowPowerListening; +#endif + + } +} +implementation { + + message_t packet; + + bool locked; + uint16_t counter = 0; + + event void Boot.booted() { + call AMControl.start(); + } + + event void AMControl.startDone(error_t err) { + if (err == SUCCESS) { + call MilliTimer.startPeriodic(2*1024); + } + else { + call AMControl.start(); + } + } + + event void AMControl.stopDone(error_t err) { + // do nothing + } + + event void MilliTimer.fired() { + uint32_t time = call LocalTime.get(); + counter++; + dbg("RadioCountToLedsC", "RadioCountToLedsC: timer fired, counter is %hu.\n", counter); + if (locked) { + return; + } + else { + radio_count_msg_t* rcm = (radio_count_msg_t*)call Packet.getPayload(&packet, sizeof(radio_count_msg_t)); + if (rcm == NULL) { + return; + } + + rcm->counter = counter; +#ifdef LOW_POWER_LISTENING + call LowPowerListening.setRxSleepInterval(&packet, LPL_INTERVAL); +#endif + + if (call AMSend.send(AM_BROADCAST_ADDR, &packet, sizeof(radio_count_msg_t), time) == SUCCESS) { + dbg("RadioCountToLedsC", "RadioCountToLedsC: packet sent.\n", counter); + locked = TRUE; + } + } + } + + event message_t* Receive.receive(message_t* bufPtr, + void* payload, uint8_t len) { + dbg("RadioCountToLedsC", "Received packet of length %hhu.\n", len); + if (len != sizeof(radio_count_msg_t)) {return bufPtr;} + else { + radio_count_msg_t* rcm = (radio_count_msg_t*)payload; + if (rcm->counter & 0x1) { + call Leds.led0On(); + } + else { + call Leds.led0Off(); + } + if (rcm->counter & 0x2) { + call Leds.led1On(); + } + else { + call Leds.led1Off(); + } + if (rcm->counter & 0x4) { + call Leds.led2On(); + } + else { + call Leds.led2Off(); + } + return bufPtr; + } + } + + event void AMSend.sendDone(message_t* bufPtr, error_t error) { + if (&packet == bufPtr) { + locked = FALSE; + } + } + +} -- 2.39.2