mirror of
https://github.com/espressif/openthread.git
synced 2026-10-20 14:38:15 +00:00
Add diagnostics module in OpenThread (#343)
* Add diagnostics module in OpenThread - provide the same diagnostics interface for both CLI and NCP usage - implement common diagnostics features based on existing platform interface defined in 'include/platform/' - other more platform specific diagnostics features will be processed under platform layer - update CLI interface to support diagnostics feature - update both Posix and CC2538 platform to support diagnostics feature * Add diagnostics module unit test - move platform.h from "examples/platform" to "include/platform" - add test_diag.cpp to test diagnostics module * Add a configuration option that would enable/disable diagnostics module Add --enable-diag configuration option to enable/disable diagnostics module when building OpenThread.
This commit is contained in:
@@ -33,6 +33,7 @@ AM_MAKEFLAGS = --no-print-directory
|
||||
AM_DISTCHECK_CONFIGURE_FLAGS = \
|
||||
--enable-cli \
|
||||
--enable-ncp \
|
||||
--enable-diag \
|
||||
--with-examples=posix \
|
||||
$(NULL)
|
||||
|
||||
|
||||
@@ -428,6 +428,37 @@ AM_CONDITIONAL([OPENTHREAD_ENABLE_NCP], [test "${enable_ncp}" != "no"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_NCP_SPI], [test "${enable_ncp}" = "spi"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_NCP_UART], [test "${enable_ncp}" = "uart"])
|
||||
|
||||
#
|
||||
# Diagnostics Library
|
||||
#
|
||||
|
||||
AC_ARG_ENABLE(diag,
|
||||
[AS_HELP_STRING([--enable-diag],[Enable diagnostics suport @<:@default=no@:>@.])],
|
||||
[
|
||||
case "${enableval}" in
|
||||
|
||||
no|yes)
|
||||
enable_diag=${enableval}
|
||||
;;
|
||||
|
||||
*)
|
||||
AC_MSG_ERROR([Invalid value ${enable_diag} for --enable-diag])
|
||||
;;
|
||||
esac
|
||||
],
|
||||
[enable_diag=no])
|
||||
|
||||
if test "$enable_diag" = "yes"; then
|
||||
OPENTHREAD_ENABLE_DIAG=1
|
||||
else
|
||||
OPENTHREAD_ENABLE_DIAG=0
|
||||
fi
|
||||
|
||||
AC_MSG_RESULT(${enable_diag})
|
||||
AC_SUBST(OPENTHREAD_ENABLE_DIAG)
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_DIAG], [test "${enable_diag}" = "yes"])
|
||||
AC_DEFINE_UNQUOTED([OPENTHREAD_ENABLE_DIAG],[${OPENTHREAD_ENABLE_DIAG}],[Define to 1 if you want to use diagnostics module])
|
||||
|
||||
#
|
||||
# Examples
|
||||
#
|
||||
@@ -596,6 +627,7 @@ src/Makefile
|
||||
src/cli/Makefile
|
||||
src/ncp/Makefile
|
||||
src/core/Makefile
|
||||
src/diag/Makefile
|
||||
third_party/Makefile
|
||||
third_party/mbedtls/Makefile
|
||||
examples/Makefile
|
||||
@@ -670,6 +702,7 @@ AC_MSG_NOTICE([
|
||||
Pretty check args : ${PRETTY_CHECK_ARGS:--}
|
||||
OpenThread CLI support : ${enable_cli}
|
||||
OpenThread NCP support : ${enable_ncp}
|
||||
OpenThread Diagnostics support : ${enable_diag}
|
||||
OpenThread examples : ${OPENTHREAD_EXAMPLES}
|
||||
OpenThread platform information : ${PLATFORM_INFO}
|
||||
|
||||
|
||||
@@ -44,6 +44,7 @@ BuildJobs ?= 99
|
||||
configure_OPTIONS = \
|
||||
--enable-cli \
|
||||
--enable-ncp \
|
||||
--enable-diag \
|
||||
--with-examples=cc2538 \
|
||||
--with-platform-info=CC2538 \
|
||||
$(NULL)
|
||||
|
||||
@@ -89,6 +89,7 @@ TargetTuple = $(shell ${AbsTopSourceDir}/third_party/nlbuild
|
||||
configure_OPTIONS = \
|
||||
--enable-cli \
|
||||
--enable-ncp \
|
||||
--enable-diag \
|
||||
--with-examples=posix \
|
||||
--with-platform-info=POSIX \
|
||||
$(NULL)
|
||||
|
||||
@@ -46,6 +46,12 @@ ot_cli_LDADD = \
|
||||
ot_cli_LDFLAGS = \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_ENABLE_DIAG
|
||||
ot_cli_LDADD += \
|
||||
$(top_builddir)/src/diag/libopenthread-diag.a \
|
||||
$(NULL)
|
||||
endif
|
||||
|
||||
if OPENTHREAD_EXAMPLES_POSIX
|
||||
ot_cli_LDADD += \
|
||||
$(top_builddir)/examples/platforms/posix/libopenthread-posix.a \
|
||||
|
||||
@@ -27,8 +27,10 @@
|
||||
*/
|
||||
|
||||
#include <openthread.h>
|
||||
#include <openthread-config.h>
|
||||
#include <openthread-diag.h>
|
||||
#include <cli/cli-uart.h>
|
||||
#include <platform.h>
|
||||
#include <platform/platform.h>
|
||||
|
||||
void otSignalTaskletPending(void)
|
||||
{
|
||||
@@ -40,6 +42,10 @@ int main(int argc, char *argv[])
|
||||
otEnable();
|
||||
otCliUartInit();
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
diagInit();
|
||||
#endif
|
||||
|
||||
while (1)
|
||||
{
|
||||
otProcessNextTasklet();
|
||||
|
||||
@@ -46,6 +46,12 @@ ot_ncp_LDADD = \
|
||||
ot_ncp_LDFLAGS = \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_ENABLE_DIAG
|
||||
ot_ncp_LDADD += \
|
||||
$(top_builddir)/src/diag/libopenthread-diag.a \
|
||||
$(NULL)
|
||||
endif
|
||||
|
||||
if OPENTHREAD_EXAMPLES_POSIX
|
||||
ot_ncp_LDADD += \
|
||||
$(top_builddir)/examples/platforms/posix/libopenthread-posix.a \
|
||||
|
||||
@@ -27,8 +27,10 @@
|
||||
*/
|
||||
|
||||
#include <openthread.h>
|
||||
#include <openthread-config.h>
|
||||
#include <openthread-diag.h>
|
||||
#include <ncp/ncp.h>
|
||||
#include <platform.h>
|
||||
#include <platform/platform.h>
|
||||
|
||||
void otSignalTaskletPending(void)
|
||||
{
|
||||
@@ -40,6 +42,10 @@ int main(int argc, char *argv[])
|
||||
otEnable();
|
||||
otNcpInit();
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
diagInit();
|
||||
#endif
|
||||
|
||||
while (1)
|
||||
{
|
||||
otProcessNextTasklet();
|
||||
|
||||
@@ -45,10 +45,6 @@ if OPENTHREAD_EXAMPLES_CC2538
|
||||
SUBDIRS = cc2538
|
||||
endif
|
||||
|
||||
noinst_HEADERS = \
|
||||
platform.h \
|
||||
$(NULL)
|
||||
|
||||
# Always pretty (e.g. for 'make pretty') these subdirectories.
|
||||
|
||||
PRETTY_SUBDIRS = \
|
||||
|
||||
@@ -46,6 +46,12 @@ libopenthread_cc2538_a_SOURCES = \
|
||||
startup-gcc.c \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_ENABLE_DIAG
|
||||
libopenthread_cc2538_a_SOURCES += \
|
||||
diag.c \
|
||||
$(NULL)
|
||||
endif
|
||||
|
||||
noinst_HEADERS = \
|
||||
cc2538-reg.h \
|
||||
platform-cc2538.h \
|
||||
|
||||
@@ -35,7 +35,9 @@
|
||||
#include <stdbool.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include <openthread-config.h>
|
||||
#include <platform/alarm.h>
|
||||
#include <platform/diag.h>
|
||||
#include "platform-cc2538.h"
|
||||
|
||||
enum
|
||||
@@ -99,7 +101,18 @@ void cc2538AlarmProcess(void)
|
||||
if (fire)
|
||||
{
|
||||
sIsRunning = false;
|
||||
otPlatAlarmFired();
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
|
||||
if (otPlatDiagModeGet())
|
||||
{
|
||||
otPlatDiagAlarmFired();
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
otPlatAlarmFired();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,59 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Nest Labs, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. Neither the name of the copyright holder nor the
|
||||
* names of its contributors may be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <stdbool.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
#include <platform/alarm.h>
|
||||
#include "platform-cc2538.h"
|
||||
|
||||
/**
|
||||
* diagnostics mode flag.
|
||||
*
|
||||
*/
|
||||
static bool sDiagMode = false;
|
||||
|
||||
void otPlatDiagProcess(int argc, char *argv[], char *aOutput)
|
||||
{
|
||||
// add more plarform specific diagnostics features here
|
||||
|
||||
sprintf(aOutput, "diag feature '%s' is not supported\r\n", argv[0]);
|
||||
(void)argc;
|
||||
}
|
||||
|
||||
void otPlatDiagModeSet(bool aMode)
|
||||
{
|
||||
sDiagMode = aMode;
|
||||
}
|
||||
|
||||
bool otPlatDiagModeGet()
|
||||
{
|
||||
return sDiagMode;
|
||||
}
|
||||
@@ -33,9 +33,11 @@
|
||||
*/
|
||||
|
||||
#include <openthread-types.h>
|
||||
#include <openthread-config.h>
|
||||
|
||||
#include <common/code_utils.hpp>
|
||||
#include <platform/radio.h>
|
||||
#include <platform/diag.h>
|
||||
#include "platform-cc2538.h"
|
||||
|
||||
enum
|
||||
@@ -371,7 +373,17 @@ void cc2538RadioProcess(void)
|
||||
|
||||
if ((sState == kStateReceive) && (sReceiveFrame.mLength > 0))
|
||||
{
|
||||
otPlatRadioReceiveDone(&sReceiveFrame, sReceiveError);
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
|
||||
if (otPlatDiagModeGet())
|
||||
{
|
||||
otPlatDiagRadioReceiveDone(&sReceiveFrame, sReceiveError);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
otPlatRadioReceiveDone(&sReceiveFrame, sReceiveError);
|
||||
}
|
||||
}
|
||||
|
||||
if (sState == kStateTransmit)
|
||||
@@ -379,14 +391,36 @@ void cc2538RadioProcess(void)
|
||||
if (sTransmitError != kThreadError_None || (sTransmitFrame.mPsdu[0] & IEEE802154_ACK_REQUEST) == 0)
|
||||
{
|
||||
sState = kStateReceive;
|
||||
otPlatRadioTransmitDone(false, sTransmitError);
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
|
||||
if (otPlatDiagModeGet())
|
||||
{
|
||||
otPlatDiagRadioTransmitDone(false, sTransmitError);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
otPlatRadioTransmitDone(false, sTransmitError);
|
||||
}
|
||||
}
|
||||
else if (sReceiveFrame.mLength == IEEE802154_ACK_LENGTH &&
|
||||
(sReceiveFrame.mPsdu[0] & IEEE802154_FRAME_TYPE_MASK) == IEEE802154_FRAME_TYPE_ACK &&
|
||||
(sReceiveFrame.mPsdu[IEEE802154_DSN_OFFSET] == sTransmitFrame.mPsdu[IEEE802154_DSN_OFFSET]))
|
||||
{
|
||||
sState = kStateReceive;
|
||||
otPlatRadioTransmitDone((sReceiveFrame.mPsdu[0] & IEEE802154_FRAME_PENDING) != 0, sTransmitError);
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
|
||||
if (otPlatDiagModeGet())
|
||||
{
|
||||
otPlatDiagRadioTransmitDone((sReceiveFrame.mPsdu[0] & IEEE802154_FRAME_PENDING) != 0, sTransmitError);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
otPlatRadioTransmitDone((sReceiveFrame.mPsdu[0] & IEEE802154_FRAME_PENDING) != 0, sTransmitError);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -46,6 +46,12 @@ libopenthread_posix_a_SOURCES = \
|
||||
uart.c \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_ENABLE_DIAG
|
||||
libopenthread_posix_a_SOURCES += \
|
||||
diag.c \
|
||||
$(NULL)
|
||||
endif
|
||||
|
||||
if OPENTHREAD_ENABLE_NCP_SPI
|
||||
libopenthread_posix_a_SOURCES += \
|
||||
spi-stubs.c \
|
||||
|
||||
@@ -31,7 +31,9 @@
|
||||
#include <string.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
#include <openthread-config.h>
|
||||
#include <platform/alarm.h>
|
||||
#include <platform/diag.h>
|
||||
#include "platform-posix.h"
|
||||
|
||||
static bool s_is_running = false;
|
||||
@@ -106,7 +108,18 @@ void posixAlarmProcess(void)
|
||||
if (remaining <= 0)
|
||||
{
|
||||
s_is_running = false;
|
||||
otPlatAlarmFired();
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
|
||||
if (otPlatDiagModeGet())
|
||||
{
|
||||
otPlatDiagAlarmFired();
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
otPlatAlarmFired();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,58 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Nest Labs, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. Neither the name of the copyright holder nor the
|
||||
* names of its contributors may be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <stdbool.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
#include <platform/alarm.h>
|
||||
#include "platform-posix.h"
|
||||
|
||||
/**
|
||||
* diagnostics mode flag.
|
||||
*
|
||||
*/
|
||||
static bool sDiagMode = false;
|
||||
|
||||
void otPlatDiagProcess(int argc, char *argv[], char *aOutput)
|
||||
{
|
||||
// no more diagnostics features for Posix platform
|
||||
sprintf(aOutput, "diag feature '%s' is not supported\r\n", argv[0]);
|
||||
(void)argc;
|
||||
}
|
||||
|
||||
void otPlatDiagModeSet(bool aMode)
|
||||
{
|
||||
sDiagMode = aMode;
|
||||
}
|
||||
|
||||
bool otPlatDiagModeGet()
|
||||
{
|
||||
return sDiagMode;
|
||||
}
|
||||
@@ -39,7 +39,9 @@
|
||||
#include <sys/stat.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include <openthread-config.h>
|
||||
#include <platform/radio.h>
|
||||
#include <platform/diag.h>
|
||||
|
||||
#include <common/code_utils.hpp>
|
||||
#include "platform-posix.h"
|
||||
@@ -456,7 +458,18 @@ void radioReceive(void)
|
||||
{
|
||||
sState = kStateReceive;
|
||||
sAckWait = false;
|
||||
otPlatRadioTransmitDone(isFramePending(sReceiveFrame.mPsdu), kThreadError_None);
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
|
||||
if (otPlatDiagModeGet())
|
||||
{
|
||||
otPlatDiagRadioTransmitDone(isFramePending(sReceiveFrame.mPsdu), kThreadError_None);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
otPlatRadioTransmitDone(isFramePending(sReceiveFrame.mPsdu), kThreadError_None);
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (sState == kStateReceive &&
|
||||
@@ -478,7 +491,18 @@ void radioSendMessage(void)
|
||||
if (!sAckWait)
|
||||
{
|
||||
sState = kStateReceive;
|
||||
otPlatRadioTransmitDone(false, kThreadError_None);
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
|
||||
if (otPlatDiagModeGet())
|
||||
{
|
||||
otPlatDiagRadioTransmitDone(false, kThreadError_None);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
otPlatRadioTransmitDone(false, kThreadError_None);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -609,5 +633,16 @@ void radioProcessFrame(void)
|
||||
|
||||
exit:
|
||||
|
||||
otPlatRadioReceiveDone(error == kThreadError_None ? &sReceiveFrame : NULL, error);
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
|
||||
if (otPlatDiagModeGet())
|
||||
{
|
||||
otPlatDiagRadioReceiveDone(error == kThreadError_None ? &sReceiveFrame : NULL, error);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
otPlatRadioReceiveDone(error == kThreadError_None ? &sReceiveFrame : NULL, error);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -57,6 +57,7 @@ PRETTY_SUBDIRS = \
|
||||
|
||||
include_HEADERS = \
|
||||
openthread.h \
|
||||
openthread-diag.h \
|
||||
openthread-types.h \
|
||||
$(NULL)
|
||||
|
||||
|
||||
@@ -0,0 +1,52 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Nest Labs, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. Neither the name of the copyright holder nor the
|
||||
* names of its contributors may be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file
|
||||
* @brief
|
||||
* This file defines the top-level functions for the OpenThread diagnostics library.
|
||||
*/
|
||||
|
||||
#ifndef OPENTHREAD_DIAG_H_
|
||||
#define OPENTHREAD_DIAG_H_
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
void diagInit();
|
||||
|
||||
char *diagProcessCmd(int argc, char *argv[]);
|
||||
|
||||
bool isDiagEnabled();
|
||||
|
||||
#ifdef __cplusplus
|
||||
} // extern "C"
|
||||
#endif
|
||||
|
||||
#endif // OPENTHREAD_DIAG_H_
|
||||
@@ -30,8 +30,10 @@ include $(abs_top_nlbuild_autotools_dir)/automake/pre.am
|
||||
|
||||
ot_platform_headers =\
|
||||
alarm.h \
|
||||
diag.h \
|
||||
misc.h \
|
||||
logging.h \
|
||||
platform.h \
|
||||
radio.h \
|
||||
random.h \
|
||||
uart.h \
|
||||
|
||||
@@ -77,6 +77,11 @@ uint32_t otPlatAlarmGetNow(void);
|
||||
*/
|
||||
extern void otPlatAlarmFired(void);
|
||||
|
||||
/**
|
||||
* Signal diagnostics module that the alarm has fired.
|
||||
*/
|
||||
extern void otPlatDiagAlarmFired(void);
|
||||
|
||||
/**
|
||||
* @}
|
||||
*
|
||||
|
||||
@@ -0,0 +1,79 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Nest Labs, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. Neither the name of the copyright holder nor the
|
||||
* names of its contributors may be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file
|
||||
* @brief
|
||||
* This file defines the platform diag interface.
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef DIAG_H_
|
||||
#define DIAG_H_
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @defgroup diag Diag
|
||||
* @ingroup platform
|
||||
*
|
||||
* @brief
|
||||
* This module includes the platform abstraction for diagnostics features.
|
||||
*
|
||||
* @{
|
||||
*
|
||||
*/
|
||||
|
||||
/**
|
||||
* Process the platform specific diagnostics features.
|
||||
*
|
||||
* @param[in] argc The argument counter of diagnostics command line.
|
||||
* @param[in] argv The argument vector of diagnostics command line.
|
||||
* @param[out] aOutput The diagnostics execution result.
|
||||
*/
|
||||
void otPlatDiagProcess(int argc, char *argv[], char *aOutput);
|
||||
|
||||
/**
|
||||
* Set diagnostics mode.
|
||||
*/
|
||||
void otPlatDiagModeSet(bool aMode);
|
||||
|
||||
/**
|
||||
* Get diagnostics mode.
|
||||
*/
|
||||
bool otPlatDiagModeGet(void);
|
||||
|
||||
#ifdef __cplusplus
|
||||
} // end of extern "C"
|
||||
#endif
|
||||
|
||||
#endif
|
||||
@@ -29,12 +29,17 @@
|
||||
/**
|
||||
* @file
|
||||
* @brief
|
||||
* This file includes the posix platform-specific initializers.
|
||||
* This file defines the platform-specific initializers.
|
||||
*/
|
||||
|
||||
#ifndef PLATFORM_H_
|
||||
#define PLATFORM_H_
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
/**
|
||||
* This function performs all platform-specific initialization.
|
||||
*
|
||||
@@ -47,4 +52,8 @@ void PlatformInit(int argc, char *argv[]);
|
||||
*/
|
||||
void PlatformProcessDrivers(void);
|
||||
|
||||
#ifdef __cplusplus
|
||||
} // end of extern "C"
|
||||
#endif
|
||||
|
||||
#endif // PLATFORM_H_
|
||||
@@ -298,6 +298,28 @@ bool otPlatRadioGetPromiscuous(void);
|
||||
*/
|
||||
void otPlatRadioSetPromiscuous(bool aEnable);
|
||||
|
||||
/**
|
||||
* The radio driver calls this method to notify OpenThread diagnostics module that the transmission has completed.
|
||||
*
|
||||
* @param[in] aFramePending TRUE if an ACK frame was received and the Frame Pending bit was set.
|
||||
* @param[in] aError ::kThreadError_None when the frame was transmitted, ::kThreadError_NoAck when the frame was
|
||||
* transmitted but no ACK was received, ::kThreadError_ChannelAccessFailure when the transmission
|
||||
* could not take place due to activity on the channel, ::kThreadError_Abort when transmission was
|
||||
* aborted for other reasons.
|
||||
*
|
||||
*/
|
||||
extern void otPlatDiagRadioTransmitDone(bool aFramePending, ThreadError aError);
|
||||
|
||||
/**
|
||||
* The radio driver calls this method to notify OpenThread diagnostics module of a received packet.
|
||||
*
|
||||
* @param[in] aPacket A pointer to the received packet or NULL if the receive operation was aborted.
|
||||
* @param[in] aError ::kThreadError_None when successfully received a frame, ::kThreadError_Abort when reception
|
||||
* was aborted and a frame was not received.
|
||||
*
|
||||
*/
|
||||
extern void otPlatDiagRadioReceiveDone(RadioPacket *aPacket, ThreadError aError);
|
||||
|
||||
/**
|
||||
* @}
|
||||
*
|
||||
|
||||
@@ -34,6 +34,7 @@ DIST_SUBDIRS = \
|
||||
cli \
|
||||
core \
|
||||
ncp \
|
||||
diag \
|
||||
$(NULL)
|
||||
|
||||
# Always build (e.g. for 'make all') these subdirectories.
|
||||
@@ -50,6 +51,10 @@ if OPENTHREAD_ENABLE_NCP
|
||||
SUBDIRS += ncp
|
||||
endif
|
||||
|
||||
if OPENTHREAD_ENABLE_DIAG
|
||||
SUBDIRS += diag
|
||||
endif
|
||||
|
||||
# Always pretty (e.g. for 'make pretty') these subdirectories.
|
||||
|
||||
PRETTY_SUBDIRS = \
|
||||
|
||||
@@ -38,6 +38,7 @@ OpenThread test scripts use the CLI to execute test cases.
|
||||
* [thread](#thread)
|
||||
* [version](#version)
|
||||
* [whitelist](#whitelist)
|
||||
* [diag](#diag)
|
||||
|
||||
## OpenThread Command Details
|
||||
|
||||
@@ -680,3 +681,11 @@ Remove an IEEE 802.15.4 Extended Address from the whitelist.
|
||||
> whitelist remove dead00beef00cafe
|
||||
Done
|
||||
```
|
||||
|
||||
### diag
|
||||
|
||||
Diagnostics module is enabled only when building OpenThread with --enable-diag option.
|
||||
Go [diagnostics module][1] for more information.
|
||||
|
||||
[1]:../diag/README.md
|
||||
|
||||
|
||||
+17
-1
@@ -36,7 +36,7 @@
|
||||
#include <string.h>
|
||||
|
||||
#include <openthread.h>
|
||||
#include <openthread-config.h>
|
||||
#include <openthread-diag.h>
|
||||
|
||||
#include "cli.hpp"
|
||||
#include "cli_dataset.hpp"
|
||||
@@ -86,6 +86,9 @@ const struct Command Interpreter::sCommands[] =
|
||||
{ "thread", &ProcessThread },
|
||||
{ "version", &ProcessVersion },
|
||||
{ "whitelist", &ProcessWhitelist },
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
{ "diag", &ProcessDiag },
|
||||
#endif
|
||||
};
|
||||
|
||||
otNetifAddress Interpreter::sAddress;
|
||||
@@ -1477,6 +1480,14 @@ exit:
|
||||
AppendResult(error);
|
||||
}
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
void Interpreter::ProcessDiag(int argc, char *argv[])
|
||||
{
|
||||
// all diagnostics related features are processed within diagnostics module
|
||||
sServer->OutputFormat("%s\r\n", diagProcessCmd(argc, argv));
|
||||
}
|
||||
#endif
|
||||
|
||||
void Interpreter::ProcessLine(char *aBuf, uint16_t aBufLength, Server &aServer)
|
||||
{
|
||||
char *argv[kMaxArgs];
|
||||
@@ -1504,6 +1515,11 @@ void Interpreter::ProcessLine(char *aBuf, uint16_t aBufLength, Server &aServer)
|
||||
|
||||
cmd = aBuf;
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
VerifyOrExit((!isDiagEnabled() || (strcmp(cmd, "diag") == 0)),
|
||||
sServer->OutputFormat("under diagnostics mode, execute 'diag stop' before running any other commands.\r\n"));
|
||||
#endif
|
||||
|
||||
for (unsigned int i = 0; i < sizeof(sCommands) / sizeof(sCommands[0]); i++)
|
||||
{
|
||||
if (strcmp(cmd, sCommands[i].mName) == 0)
|
||||
|
||||
@@ -39,6 +39,7 @@
|
||||
#include <cli/cli_server.hpp>
|
||||
#include <net/icmp6.hpp>
|
||||
#include <common/timer.hpp>
|
||||
#include <openthread-config.h>
|
||||
|
||||
namespace Thread {
|
||||
|
||||
@@ -157,6 +158,10 @@ private:
|
||||
static void ProcessVersion(int argc, char *argv[]);
|
||||
static void ProcessWhitelist(int argc, char *argv[]);
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
static void ProcessDiag(int argc, char *argv[]);
|
||||
#endif
|
||||
|
||||
static void HandleEchoResponse(void *aContext, Message &aMessage, const Ip6::MessageInfo &aMessageInfo);
|
||||
static void HandlePingTimer(void *aContext);
|
||||
static void HandleActiveScanResult(otActiveScanResult *aResult);
|
||||
|
||||
@@ -0,0 +1,53 @@
|
||||
#
|
||||
# Copyright (c) 2016, Nest Labs, Inc.
|
||||
# All rights reserved.
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are met:
|
||||
# 1. Redistributions of source code must retain the above copyright
|
||||
# notice, this list of conditions and the following disclaimer.
|
||||
# 2. Redistributions in binary form must reproduce the above copyright
|
||||
# notice, this list of conditions and the following disclaimer in the
|
||||
# documentation and/or other materials provided with the distribution.
|
||||
# 3. Neither the name of the copyright holder nor the
|
||||
# names of its contributors may be used to endorse or promote products
|
||||
# derived from this software without specific prior written permission.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
# ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||
# LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
# POSSIBILITY OF SUCH DAMAGE.
|
||||
#
|
||||
|
||||
include $(abs_top_nlbuild_autotools_dir)/automake/pre.am
|
||||
|
||||
lib_LIBRARIES = libopenthread-diag.a
|
||||
|
||||
libopenthread_diag_a_CPPFLAGS = \
|
||||
-I$(top_srcdir)/include \
|
||||
-I$(top_srcdir)/src \
|
||||
-I$(top_srcdir)/src/core \
|
||||
$(OPENTHREAD_TARGET_DEFINES) \
|
||||
$(NULL)
|
||||
|
||||
libopenthread_diag_a_SOURCES = \
|
||||
openthread-diag.cpp \
|
||||
diag_process.cpp \
|
||||
$(NULL)
|
||||
|
||||
noinst_HEADERS = \
|
||||
diag_process.hpp \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_BUILD_COVERAGE
|
||||
CLEANFILES = $(wildcard *.gcda *.gcno)
|
||||
endif # OPENTHREAD_BUILD_COVERAGE
|
||||
|
||||
include $(abs_top_nlbuild_autotools_dir)/automake/post.am
|
||||
@@ -0,0 +1,143 @@
|
||||
# OpenThread Diagnostics Module Reference
|
||||
|
||||
The OpenThread diagnostics module is a tool for debugging platform hardware manually, and it will also be used during manufacturing process, to verify platform hardware performance.
|
||||
|
||||
The diagnostics module supports common diagnostics features that are listed below, and it also provides a mechanism for expanding platform specific diagnostics features.
|
||||
|
||||
|
||||
## Common Diagnostics Command List
|
||||
|
||||
* [diag](#diag)
|
||||
* [diag start](#diag start)
|
||||
* [diag channel](#diag channel)
|
||||
* [diag channel \<channel\>](#diag channel \<channel\>)
|
||||
* [diag power](#diag power)
|
||||
* [diag power \<power\>](#diag power \<power\>)
|
||||
* [diag send \<packets\> \<length\>](#diag send \<packets\> \<length\>)
|
||||
* [diag repeat \<delay\> \<length\>](#diag repeat \<delay\> \<length\>)
|
||||
* [diag repeat stop](#diag repeat stop)
|
||||
* [diag sleep](#diag sleep)
|
||||
* [diag stats](#diag stats)
|
||||
* [diag stop](#diag stop)
|
||||
|
||||
|
||||
### diag
|
||||
|
||||
Show diagnostics mode status.
|
||||
|
||||
```bash
|
||||
> diag
|
||||
diagnostics mode is disabled
|
||||
```
|
||||
|
||||
### diag start
|
||||
|
||||
Start diagnostics mode.
|
||||
|
||||
```bash
|
||||
> diag start
|
||||
start diagnostics mode
|
||||
status 0x00
|
||||
```
|
||||
|
||||
### diag channel
|
||||
|
||||
Get the IEEE 802.15.4 Channel value for diagnostics module.
|
||||
|
||||
```bash
|
||||
> diag channel
|
||||
channel: 11
|
||||
```
|
||||
|
||||
### diag channel \<channel\>
|
||||
|
||||
Set the IEEE 802.15.4 Channel value for diagnostics module.
|
||||
|
||||
```bash
|
||||
> diag channel 11
|
||||
set channel to 11
|
||||
status 0x00
|
||||
```
|
||||
|
||||
### diag power
|
||||
|
||||
Get the tx power value(dBm) for diagnostics module.
|
||||
|
||||
```bash
|
||||
> diag power
|
||||
tx power: -10 dBm
|
||||
```
|
||||
|
||||
### diag power \<power\>
|
||||
|
||||
Set the tx power value(dBm) for diagnostics module.
|
||||
|
||||
```bash
|
||||
> diag power -10
|
||||
set tx power to -10 dBm
|
||||
status 0x00
|
||||
```
|
||||
|
||||
### diag send \<packets\> \<length\>
|
||||
|
||||
Transmit a fixed number of packets with fixed length.
|
||||
|
||||
```bash
|
||||
> diag send 20 100
|
||||
sending 0x14 packet(s), length 0x64
|
||||
status 0x00
|
||||
```
|
||||
|
||||
### diag repeat \<delay\> \<length\>
|
||||
|
||||
Transmit packets repeatedly with a fixed interval.
|
||||
|
||||
```bash
|
||||
> diag repeat 100 100
|
||||
sending packets of length 0x64 at the delay of 0x64 ms
|
||||
status 0x00
|
||||
```
|
||||
|
||||
### diag repeat stop
|
||||
|
||||
Stop repeated packet transmission.
|
||||
|
||||
```bash
|
||||
> diag repeat stop
|
||||
repeated packet transmission is stopped
|
||||
status 0x00
|
||||
```
|
||||
|
||||
### diag sleep
|
||||
|
||||
Enter radio sleep mode.
|
||||
|
||||
```bash
|
||||
> diag sleep
|
||||
sleeping now...
|
||||
```
|
||||
|
||||
### diag stats
|
||||
|
||||
Print statistics during diagnostics mode.
|
||||
|
||||
```bash
|
||||
> diag stats
|
||||
received packets: 10
|
||||
sent packets: 10
|
||||
first received packet: rssi=-65, lqi=101
|
||||
```
|
||||
|
||||
### diag stop
|
||||
|
||||
Stop diagnostics mode and print statistics.
|
||||
|
||||
```bash
|
||||
> diag stop
|
||||
received packets: 10
|
||||
sent packets: 10
|
||||
first received packet: rssi=-65, lqi=101
|
||||
|
||||
stop diagnostics mode
|
||||
status 0x00
|
||||
```
|
||||
@@ -0,0 +1,383 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Nest Labs, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. Neither the name of the copyright holder nor the
|
||||
* names of its contributors may be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file
|
||||
* This file implements the diagnostics module.
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <common/code_utils.hpp>
|
||||
|
||||
#include "diag_process.hpp"
|
||||
|
||||
namespace Thread {
|
||||
namespace Diagnostics {
|
||||
|
||||
const struct Command Diag::sCommands[] =
|
||||
{
|
||||
{ "start", &ProcessStart },
|
||||
{ "stop", &ProcessStop },
|
||||
{ "channel", &ProcessChannel },
|
||||
{ "power", &ProcessPower },
|
||||
{ "send", &ProcessSend },
|
||||
{ "repeat", &ProcessRepeat },
|
||||
{ "sleep", &ProcessSleep },
|
||||
{ "stats", &ProcessStats },
|
||||
};
|
||||
|
||||
char Diag::sDiagOutput[MAX_DIAG_OUTPUT];
|
||||
struct DiagStats Diag::sStats;
|
||||
|
||||
int8_t Diag::sTxPower;
|
||||
uint8_t Diag::sChannel;
|
||||
uint8_t Diag::sTxLen;
|
||||
uint32_t Diag::sTxPeriod;
|
||||
uint32_t Diag::sTxPackets;
|
||||
|
||||
void Diag::Init()
|
||||
{
|
||||
sChannel = 20;
|
||||
sTxPower = 0;
|
||||
sTxPeriod = 0;
|
||||
sTxLen = 0;
|
||||
sTxPackets = 0;
|
||||
memset(&sStats, 0, sizeof(struct DiagStats));
|
||||
}
|
||||
|
||||
char *Diag::ProcessCmd(int argc, char *argv[])
|
||||
{
|
||||
unsigned int i;
|
||||
|
||||
if (argc == 0)
|
||||
{
|
||||
sprintf(sDiagOutput, "diagnostics mode is %s\r\n", otPlatDiagModeGet() ? "enabled" : "disabled");
|
||||
}
|
||||
else
|
||||
{
|
||||
for (i = 0; i < sizeof(sCommands) / sizeof(sCommands[0]); i++)
|
||||
{
|
||||
if (strcmp(argv[0], sCommands[i].mName) == 0)
|
||||
{
|
||||
sCommands[i].mCommand(argc - 1, &argv[1], sDiagOutput);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// more platform specific features will be processed under platform layer
|
||||
if (i == sizeof(sCommands) / sizeof(sCommands[0]))
|
||||
{
|
||||
otPlatDiagProcess(argc, argv, sDiagOutput);
|
||||
}
|
||||
}
|
||||
|
||||
return sDiagOutput;
|
||||
}
|
||||
|
||||
bool Diag::isEnabled()
|
||||
{
|
||||
return otPlatDiagModeGet();
|
||||
}
|
||||
|
||||
void Diag::AppendErrorResult(ThreadError aError, char *aOutput)
|
||||
{
|
||||
if (aError != kThreadError_None)
|
||||
{
|
||||
sprintf(aOutput, "failed\r\nstatus %#x\r\n", aError);
|
||||
}
|
||||
}
|
||||
|
||||
void Diag::ProcessStart(int argc, char *argv[], char *aOutput)
|
||||
{
|
||||
ThreadError error = kThreadError_None;
|
||||
|
||||
// enable radio
|
||||
otPlatRadioEnable();
|
||||
|
||||
// enable promiscuous mode
|
||||
otPlatRadioSetPromiscuous(true);
|
||||
|
||||
// stop timer
|
||||
otPlatAlarmStop();
|
||||
|
||||
// start to listen on the default channel
|
||||
SuccessOrExit(error = otPlatRadioReceive(sChannel));
|
||||
|
||||
// enable diagnostics mode
|
||||
otPlatDiagModeSet(true);
|
||||
|
||||
memset(&sStats, 0, sizeof(struct DiagStats));
|
||||
|
||||
sprintf(aOutput, "start diagnostics mode\r\nstatus 0x%02x\r\n", error);
|
||||
|
||||
exit:
|
||||
(void)argc;
|
||||
(void)argv;
|
||||
AppendErrorResult(error, aOutput);
|
||||
}
|
||||
|
||||
void Diag::ProcessStop(int argc, char *argv[], char *aOutput)
|
||||
{
|
||||
ThreadError error = kThreadError_None;
|
||||
|
||||
VerifyOrExit(otPlatDiagModeGet(), error = kThreadError_InvalidState);
|
||||
|
||||
otPlatAlarmStop();
|
||||
otPlatDiagModeSet(false);
|
||||
otPlatRadioSetPromiscuous(false);
|
||||
|
||||
sprintf(aOutput, "received packets: %d\r\nsent packets: %d\r\nfirst received packet: rssi=%d, lqi=%d\r\n\nstop diagnostics mode\r\nstatus 0x%02x\r\n",
|
||||
static_cast<int>(sStats.received_packets), static_cast<int>(sStats.sent_packets), static_cast<int>(sStats.first_rssi),
|
||||
static_cast<int>(sStats.first_lqi), error);
|
||||
|
||||
exit:
|
||||
(void)argc;
|
||||
(void)argv;
|
||||
AppendErrorResult(error, aOutput);
|
||||
}
|
||||
|
||||
ThreadError Diag::ParseLong(char *argv, long &value)
|
||||
{
|
||||
char *endptr;
|
||||
value = strtol(argv, &endptr, 0);
|
||||
return (*endptr == '\0') ? kThreadError_None : kThreadError_Parse;
|
||||
}
|
||||
|
||||
void Diag::TxPacket()
|
||||
{
|
||||
RadioPacket *packet = otPlatRadioGetTransmitBuffer();
|
||||
|
||||
if (sTxPackets > 0)
|
||||
{
|
||||
sTxPackets--;
|
||||
}
|
||||
|
||||
packet->mLength = sTxLen;
|
||||
packet->mChannel = sChannel;
|
||||
packet->mPower = sTxPower;
|
||||
|
||||
for (uint8_t i = 0; i < sTxLen; i++)
|
||||
{
|
||||
packet->mPsdu[i] = i;
|
||||
}
|
||||
|
||||
otPlatRadioTransmit();
|
||||
}
|
||||
|
||||
void Diag::ProcessChannel(int argc, char *argv[], char *aOutput)
|
||||
{
|
||||
ThreadError error = kThreadError_None;
|
||||
|
||||
VerifyOrExit(otPlatDiagModeGet(), error = kThreadError_InvalidState);
|
||||
|
||||
if (argc == 0)
|
||||
{
|
||||
sprintf(aOutput, "channel: %d\r\n", sChannel);
|
||||
}
|
||||
else
|
||||
{
|
||||
long value;
|
||||
|
||||
SuccessOrExit(error = ParseLong(argv[0], value));
|
||||
VerifyOrExit(value >= kPhyMinChannel && value <= kPhyMaxChannel, error = kThreadError_InvalidArgs);
|
||||
sChannel = static_cast<uint8_t>(value);
|
||||
|
||||
// listen on the set channel immediately
|
||||
otPlatRadioReceive(sChannel);
|
||||
sprintf(aOutput, "set channel to %d\r\nstatus 0x%02x\r\n", sChannel, error);
|
||||
}
|
||||
|
||||
exit:
|
||||
AppendErrorResult(error, aOutput);
|
||||
}
|
||||
|
||||
void Diag::ProcessPower(int argc, char *argv[], char *aOutput)
|
||||
{
|
||||
ThreadError error = kThreadError_None;
|
||||
|
||||
VerifyOrExit(otPlatDiagModeGet(), error = kThreadError_InvalidState);
|
||||
|
||||
if (argc == 0)
|
||||
{
|
||||
sprintf(aOutput, "tx power: %d dBm\r\n", sTxPower);
|
||||
}
|
||||
else
|
||||
{
|
||||
long value;
|
||||
|
||||
SuccessOrExit(error = ParseLong(argv[0], value));
|
||||
sTxPower = static_cast<int8_t>(value);
|
||||
sprintf(aOutput, "set tx power to %d dBm\r\nstatus 0x%02x\r\n", sTxPower, error);
|
||||
}
|
||||
|
||||
exit:
|
||||
AppendErrorResult(error, aOutput);
|
||||
}
|
||||
|
||||
void Diag::ProcessSend(int argc, char *argv[], char *aOutput)
|
||||
{
|
||||
ThreadError error = kThreadError_None;
|
||||
long value;
|
||||
|
||||
VerifyOrExit(otPlatDiagModeGet(), error = kThreadError_InvalidState);
|
||||
VerifyOrExit(argc == 2, error = kThreadError_InvalidArgs);
|
||||
|
||||
SuccessOrExit(error = ParseLong(argv[0], value));
|
||||
sTxPackets = static_cast<uint32_t>(value);
|
||||
|
||||
SuccessOrExit(error = ParseLong(argv[1], value));
|
||||
VerifyOrExit(value <= kMaxPHYPacketSize, error = kThreadError_InvalidArgs);
|
||||
sTxLen = static_cast<uint8_t>(value);
|
||||
|
||||
sprintf(aOutput, "sending %#x packet(s), length %#x\r\nstatus 0x%02x\r\n", static_cast<int>(sTxPackets), static_cast<int>(sTxLen), error);
|
||||
TxPacket();
|
||||
|
||||
exit:
|
||||
AppendErrorResult(error, aOutput);
|
||||
}
|
||||
|
||||
void Diag::ProcessRepeat(int argc, char *argv[], char *aOutput)
|
||||
{
|
||||
ThreadError error = kThreadError_None;
|
||||
|
||||
VerifyOrExit(otPlatDiagModeGet(), error = kThreadError_InvalidState);
|
||||
VerifyOrExit(argc > 0, error = kThreadError_InvalidArgs);
|
||||
|
||||
if (strcmp(argv[0], "stop") == 0)
|
||||
{
|
||||
otPlatAlarmStop();
|
||||
sprintf(aOutput, "repeated packet transmission is stopped\r\nstatus 0x%02x\r\n", error);
|
||||
}
|
||||
else
|
||||
{
|
||||
long value;
|
||||
|
||||
VerifyOrExit(argc == 2, error = kThreadError_InvalidArgs);
|
||||
|
||||
SuccessOrExit(error = ParseLong(argv[0], value));
|
||||
sTxPeriod = static_cast<uint32_t>(value);
|
||||
|
||||
SuccessOrExit(error = ParseLong(argv[1], value));
|
||||
VerifyOrExit(value <= kMaxPHYPacketSize, error = kThreadError_InvalidArgs);
|
||||
sTxLen = static_cast<uint8_t>(value);
|
||||
|
||||
uint32_t now = otPlatAlarmGetNow();
|
||||
otPlatAlarmStartAt(now, sTxPeriod);
|
||||
sprintf(aOutput, "sending packets of length %#x at the delay of %#x ms\r\nstatus 0x%02x\r\n", static_cast<int>(sTxLen), static_cast<int>(sTxPeriod), error);
|
||||
}
|
||||
|
||||
exit:
|
||||
AppendErrorResult(error, aOutput);
|
||||
}
|
||||
|
||||
void Diag::ProcessSleep(int argc, char *argv[], char *aOutput)
|
||||
{
|
||||
ThreadError error = kThreadError_None;
|
||||
|
||||
VerifyOrExit(otPlatDiagModeGet(), error = kThreadError_InvalidState);
|
||||
|
||||
otPlatRadioSleep();
|
||||
sprintf(aOutput, "sleeping now...\r\n");
|
||||
|
||||
exit:
|
||||
(void)argc;
|
||||
(void)argv;
|
||||
AppendErrorResult(error, aOutput);
|
||||
}
|
||||
|
||||
void Diag::ProcessStats(int argc, char *argv[], char *aOutput)
|
||||
{
|
||||
ThreadError error = kThreadError_None;
|
||||
|
||||
VerifyOrExit(otPlatDiagModeGet(), error = kThreadError_InvalidState);
|
||||
|
||||
sprintf(aOutput, "received packets: %d\r\nsent packets: %d\r\nfirst received packet: rssi=%d, lqi=%d\r\n",
|
||||
static_cast<int>(sStats.received_packets), static_cast<int>(sStats.sent_packets),
|
||||
static_cast<int>(sStats.first_rssi), static_cast<int>(sStats.first_lqi));
|
||||
|
||||
exit:
|
||||
(void)argc;
|
||||
(void)argv;
|
||||
AppendErrorResult(error, aOutput);
|
||||
}
|
||||
|
||||
void Diag::DiagTransmitDone(bool aRxPending, ThreadError aError)
|
||||
{
|
||||
if (!aRxPending && aError == kThreadError_None)
|
||||
{
|
||||
sStats.sent_packets++;
|
||||
|
||||
if (sTxPackets > 0)
|
||||
{
|
||||
TxPacket();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Diag::DiagReceiveDone(RadioPacket *aFrame, ThreadError aError)
|
||||
{
|
||||
if (aError == kThreadError_None)
|
||||
{
|
||||
// for sensitivity test, only record the rssi and lqi for the first packet
|
||||
if (sStats.received_packets == 0)
|
||||
{
|
||||
sStats.first_rssi = aFrame->mPower;
|
||||
sStats.first_lqi = aFrame->mLqi;
|
||||
}
|
||||
|
||||
sStats.received_packets++;
|
||||
}
|
||||
}
|
||||
|
||||
void Diag::AlarmFired()
|
||||
{
|
||||
uint32_t now = otPlatAlarmGetNow();
|
||||
|
||||
TxPacket();
|
||||
otPlatAlarmStartAt(now, sTxPeriod);
|
||||
}
|
||||
|
||||
extern "C" void otPlatDiagAlarmFired()
|
||||
{
|
||||
Diag::AlarmFired();
|
||||
}
|
||||
|
||||
extern "C" void otPlatDiagRadioTransmitDone(bool aRxPending, ThreadError aError)
|
||||
{
|
||||
Diag::DiagTransmitDone(aRxPending, aError);
|
||||
}
|
||||
|
||||
extern "C" void otPlatDiagRadioReceiveDone(RadioPacket *aFrame, ThreadError aError)
|
||||
{
|
||||
Diag::DiagReceiveDone(aFrame, aError);
|
||||
}
|
||||
|
||||
} // namespace Diagnostics
|
||||
} // namespace Thread
|
||||
@@ -0,0 +1,99 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Nest Labs, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. Neither the name of the copyright holder nor the
|
||||
* names of its contributors may be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file
|
||||
* This file contains definitions for the diagnostics module.
|
||||
*/
|
||||
|
||||
#ifndef DIAG_PROCESS_HPP_
|
||||
#define DIAG_PROCESS_HPP_
|
||||
|
||||
#include <stdarg.h>
|
||||
#include <platform/radio.h>
|
||||
#include <platform/alarm.h>
|
||||
#include <platform/diag.h>
|
||||
|
||||
namespace Thread {
|
||||
|
||||
namespace Diagnostics {
|
||||
|
||||
#define MAX_DIAG_OUTPUT 256
|
||||
|
||||
struct Command
|
||||
{
|
||||
const char *mName; ///< A pointer to the command string.
|
||||
void (*mCommand)(int argc, char *argv[], char *aOutput); ///< A function pointer to process the command.
|
||||
};
|
||||
|
||||
struct DiagStats
|
||||
{
|
||||
uint32_t received_packets;
|
||||
uint32_t sent_packets;
|
||||
int8_t first_rssi;
|
||||
uint8_t first_lqi;
|
||||
};
|
||||
|
||||
class Diag
|
||||
{
|
||||
public:
|
||||
static void Init();
|
||||
static char *ProcessCmd(int argc, char *argv[]);
|
||||
static bool isEnabled();
|
||||
|
||||
static void DiagTransmitDone(bool aRxPending, ThreadError aError);
|
||||
static void DiagReceiveDone(RadioPacket *aFrame, ThreadError aError);
|
||||
static void AlarmFired();
|
||||
|
||||
private:
|
||||
static void AppendErrorResult(ThreadError error, char *aOutput);
|
||||
static void ProcessSleep(int argc, char *argv[], char *aOutput);
|
||||
static void ProcessStart(int argc, char *argv[], char *aOutput);
|
||||
static void ProcessStop(int argc, char *argv[], char *aOutput);
|
||||
static void ProcessSend(int argc, char *argv[], char *aOutput);
|
||||
static void ProcessRepeat(int argc, char *argv[], char *aOutput);
|
||||
static void ProcessStats(int argc, char *argv[], char *aOutput);
|
||||
static void ProcessChannel(int argc, char *argv[], char *aOutput);
|
||||
static void ProcessPower(int argc, char *argv[], char *aOutput);
|
||||
static void TxPacket();
|
||||
static ThreadError ParseLong(char *aString, long &aLong);
|
||||
|
||||
static char sDiagOutput[];
|
||||
static const struct Command sCommands[];
|
||||
static struct DiagStats sStats;
|
||||
static int8_t sTxPower;
|
||||
static uint8_t sChannel;
|
||||
static uint8_t sTxLen;
|
||||
static uint32_t sTxPeriod;
|
||||
static uint32_t sTxPackets;
|
||||
};
|
||||
|
||||
} // namespace Diagnostics
|
||||
} // namespace Thread
|
||||
|
||||
#endif // CLI_HPP_
|
||||
@@ -0,0 +1,69 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Nest Labs, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. Neither the name of the copyright holder nor the
|
||||
* names of its contributors may be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file
|
||||
* This file implements the top-level interface to diagnostics module.
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <openthread-diag.h>
|
||||
#include <diag_process.hpp>
|
||||
|
||||
namespace Thread {
|
||||
|
||||
namespace Diagnostics {
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
void diagInit()
|
||||
{
|
||||
Diag::Init();
|
||||
}
|
||||
|
||||
char *diagProcessCmd(int argc, char *argv[])
|
||||
{
|
||||
return Diag::ProcessCmd(argc, argv);
|
||||
}
|
||||
|
||||
bool isDiagEnabled()
|
||||
{
|
||||
return Diag::isEnabled();
|
||||
}
|
||||
|
||||
#ifdef __cplusplus
|
||||
} // extern "C"
|
||||
#endif
|
||||
|
||||
} // namespace Diagnostics
|
||||
} // namespace Thread
|
||||
@@ -75,6 +75,12 @@ check_PROGRAMS = \
|
||||
test-toolchain \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_ENABLE_DIAG
|
||||
check_PROGRAMS += \
|
||||
test-diag \
|
||||
$(NULL)
|
||||
endif
|
||||
|
||||
if OPENTHREAD_ENABLE_NCP
|
||||
|
||||
COMMON_LDADD += \
|
||||
@@ -129,6 +135,13 @@ test_timer_SOURCES = test_timer.cpp
|
||||
test_toolchain_LDADD = $(COMMON_LDADD)
|
||||
test_toolchain_SOURCES = test_toolchain.cpp
|
||||
|
||||
if OPENTHREAD_ENABLE_DIAG
|
||||
test_diag_LDADD = $(top_builddir)/src/diag/libopenthread-diag.a \
|
||||
$(top_builddir)/examples/platforms/posix/libopenthread-posix.a \
|
||||
$(NULL)
|
||||
test_diag_SOURCES = test_diag.cpp
|
||||
endif
|
||||
|
||||
endif # OPENTHREAD_BUILD_TESTS
|
||||
|
||||
include $(abs_top_nlbuild_autotools_dir)/automake/post.am
|
||||
|
||||
@@ -0,0 +1,191 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Nest Labs, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. Neither the name of the copyright holder nor the
|
||||
* names of its contributors may be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "test_util.h"
|
||||
#include <string.h>
|
||||
#include <openthread-diag.h>
|
||||
#include <platform/platform.h>
|
||||
#include <platform/radio.h>
|
||||
|
||||
extern "C" void otSignalTaskletPending(void)
|
||||
{
|
||||
}
|
||||
|
||||
extern "C" bool otAreTaskletsPending(void)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
extern "C" void otPlatUartSendDone(void)
|
||||
{
|
||||
}
|
||||
|
||||
extern "C" void otPlatUartReceived(const uint8_t *aBuf, uint16_t aBufLength)
|
||||
{
|
||||
(void)aBuf;
|
||||
(void)aBufLength;
|
||||
}
|
||||
|
||||
extern "C" void otPlatAlarmFired()
|
||||
{
|
||||
}
|
||||
|
||||
extern "C" void otPlatRadioTransmitDone(bool aRxPending, ThreadError aError)
|
||||
{
|
||||
(void)aRxPending;
|
||||
(void)aError;
|
||||
}
|
||||
|
||||
extern "C" void otPlatRadioReceiveDone(RadioPacket *aFrame, ThreadError aError)
|
||||
{
|
||||
(void)aFrame;
|
||||
(void)aError;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* diagnostics module tests
|
||||
*/
|
||||
void TestDiag()
|
||||
{
|
||||
static const struct
|
||||
{
|
||||
const char *command;
|
||||
const char *output;
|
||||
} tests[] =
|
||||
{
|
||||
{
|
||||
"diag\n",
|
||||
"diagnostics mode is disabled\r\n",
|
||||
},
|
||||
{
|
||||
"diag send 10 100\n",
|
||||
"failed\r\nstatus 0xe\r\n",
|
||||
},
|
||||
{
|
||||
"diag start\n",
|
||||
"start diagnostics mode\r\nstatus 0x00\r\n",
|
||||
},
|
||||
{
|
||||
"diag\n",
|
||||
"diagnostics mode is enabled\r\n",
|
||||
},
|
||||
{
|
||||
"diag channel 10\n",
|
||||
"failed\r\nstatus 0x7\r\n",
|
||||
},
|
||||
{
|
||||
"diag channel 11\n",
|
||||
"set channel to 11\r\nstatus 0x00\r\n",
|
||||
},
|
||||
{
|
||||
"diag channel\n",
|
||||
"channel: 11\r\n",
|
||||
},
|
||||
{
|
||||
"diag power -10\n",
|
||||
"set tx power to -10 dBm\r\nstatus 0x00\r\n",
|
||||
},
|
||||
{
|
||||
"diag power\n",
|
||||
"tx power: -10 dBm\r\n",
|
||||
},
|
||||
{
|
||||
"diag stats\n",
|
||||
"received packets: 0\r\nsent packets: 0\r\nfirst received packet: rssi=0, lqi=0\r\n",
|
||||
},
|
||||
{
|
||||
"diag send 20 100\n",
|
||||
"sending 0x14 packet(s), length 0x64\r\nstatus 0x00\r\n",
|
||||
},
|
||||
{
|
||||
"diag repeat 100 100\n",
|
||||
"sending packets of length 0x64 at the delay of 0x64 ms\r\nstatus 0x00\r\n"
|
||||
},
|
||||
{
|
||||
"diag sleep\n",
|
||||
"sleeping now...\r\n",
|
||||
},
|
||||
{
|
||||
"diag stop\n",
|
||||
"received packets: 0\r\nsent packets: 0\r\nfirst received packet: rssi=0, lqi=0\r\n\nstop diagnostics mode\r\nstatus 0x00\r\n",
|
||||
},
|
||||
{
|
||||
"diag\n",
|
||||
"diagnostics mode is disabled\r\n",
|
||||
},
|
||||
};
|
||||
|
||||
// initialize platform layer
|
||||
int argc = 2;
|
||||
char *argv[2] = {(char *)"test_diag", (char *)"1"};
|
||||
PlatformInit(argc, argv);
|
||||
|
||||
// initialize diagnostics module
|
||||
diagInit();
|
||||
|
||||
// test diagnostics commands
|
||||
VerifyOrQuit(!isDiagEnabled(), "diagnostics mode shoud be disabled as default\n");
|
||||
|
||||
for (unsigned int i = 0; i < sizeof(tests) / sizeof(tests[0]); i++)
|
||||
{
|
||||
char string[50];
|
||||
int length = strlen(tests[i].command);
|
||||
|
||||
char *cmd;
|
||||
char *argv[8];
|
||||
int argc = 0;
|
||||
char *output = NULL;
|
||||
|
||||
memcpy(string, tests[i].command, length + 1);
|
||||
|
||||
for (cmd = string + 1; (cmd < string + length) && (cmd != NULL); ++cmd)
|
||||
{
|
||||
if (*cmd == ' ' || *cmd == '\r' || *cmd == '\n')
|
||||
{
|
||||
*cmd = '\0';
|
||||
}
|
||||
|
||||
if (*(cmd - 1) == '\0' && *cmd != ' ')
|
||||
{
|
||||
argv[argc++] = cmd;
|
||||
}
|
||||
}
|
||||
|
||||
output = diagProcessCmd(argc, argv);
|
||||
VerifyOrQuit(memcmp(output, tests[i].output, strlen(tests[i].output)) == 0,
|
||||
"Test Diagnostics module failed\r\n");
|
||||
}
|
||||
}
|
||||
|
||||
int main(void)
|
||||
{
|
||||
TestDiag();
|
||||
printf("All tests passed\n");
|
||||
return 0;
|
||||
}
|
||||
@@ -59,6 +59,22 @@ extern "C" void otPlatUartReceived(const uint8_t *aBuf, uint16_t aBufLength)
|
||||
(void)aBufLength;
|
||||
}
|
||||
|
||||
extern "C" void otPlatDiagAlarmFired()
|
||||
{
|
||||
}
|
||||
|
||||
extern "C" void otPlatDiagRadioTransmitDone(bool aRxPending, ThreadError aError)
|
||||
{
|
||||
(void)aRxPending;
|
||||
(void)aError;
|
||||
}
|
||||
|
||||
extern "C" void otPlatDiagRadioReceiveDone(RadioPacket *aFrame, ThreadError aError)
|
||||
{
|
||||
(void)aFrame;
|
||||
(void)aError;
|
||||
}
|
||||
|
||||
ThreadNetif sMockThreadNetif;
|
||||
Lowpan::Lowpan sMockLowpan(sMockThreadNetif);
|
||||
|
||||
|
||||
@@ -36,6 +36,10 @@ extern"C" void otSignalTaskletPending(void)
|
||||
{
|
||||
}
|
||||
|
||||
extern "C" void otPlatDiagAlarmFired()
|
||||
{
|
||||
}
|
||||
|
||||
void TestMessage(void)
|
||||
{
|
||||
Thread::Message *message;
|
||||
|
||||
@@ -40,6 +40,10 @@ extern"C" void otSignalTaskletPending(void)
|
||||
{
|
||||
}
|
||||
|
||||
extern "C" void otPlatDiagAlarmFired()
|
||||
{
|
||||
}
|
||||
|
||||
enum
|
||||
{
|
||||
kTestBufferSize = 101, // Size of backed buffer for NcpFrameBuffer.
|
||||
|
||||
Reference in New Issue
Block a user